Well timed removal of USB cable leaves g_serial unusable.

* It is possible that the g_serial driver can recieve a request to handle
  SET_LINE_CODING in acm_setup() when the end-point is invalid.  Further more,
  acm_setup() will setup a completition handler for the request which results
  in the request becoming stuck.  Not certain what is racing where, but
  replacing the completion request with a memcpy() operation appears to avoid 
the
  problem completely.

Signed-off-by: Mark Ferrell <[email protected]>

---
 drivers/usb/gadget/f_acm.c |    8 +++++---
 1 file changed, 5 insertions(+), 3 deletions(-)

diff --git a/drivers/usb/gadget/f_acm.c b/drivers/usb/gadget/f_acm.c
index 4b7e33e..6cd2b69 100644
--- a/drivers/usb/gadget/f_acm.c
+++ b/drivers/usb/gadget/f_acm.c
@@ -363,9 +363,11 @@ static int acm_setup(struct usb_function *f, const struct 
usb_ctrlrequest *ctrl)
                                || w_index != acm->ctrl_id)
                        goto invalid;
 
-               value = w_length;
-               cdev->gadget->ep0->driver_data = acm;
-               req->complete = acm_complete_set_line_coding;
+               if (req->actual == sizeof(acm->port_line_coding)) {
+                       value = min_t(unsigned, w_length,
+                               sizeof(struct usb_cdc_line_coding));
+                       memcpy(&acm->port_line_coding, req->buf, value);
+               }
                break;
 
        /* GET_LINE_CODING ... return what host sent, or initial value */
-- 
tg: (37af71c..) upstream/usb/gadget/g_serial/bad_request (depends on: master)
--
To unsubscribe from this list: send the line "unsubscribe linux-usb" in
the body of a message to [email protected]
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to