|
@@ -171,33 +171,23 @@ static int tweak_set_configuration_cmd(struct urb *urb)
|
|
|
|
|
|
static int tweak_reset_device_cmd(struct urb *urb)
|
|
|
{
|
|
|
- struct usb_ctrlrequest *req;
|
|
|
- __u16 value;
|
|
|
- __u16 index;
|
|
|
- int ret;
|
|
|
-
|
|
|
- req = (struct usb_ctrlrequest *) urb->setup_packet;
|
|
|
- value = le16_to_cpu(req->wValue);
|
|
|
- index = le16_to_cpu(req->wIndex);
|
|
|
-
|
|
|
- usbip_uinfo("reset_device (port %d) to %s\n", index,
|
|
|
- dev_name(&urb->dev->dev));
|
|
|
+ struct stub_priv *priv = (struct stub_priv *) urb->context;
|
|
|
+ struct stub_device *sdev = priv->sdev;
|
|
|
|
|
|
- /* all interfaces should be owned by usbip driver, so just reset it. */
|
|
|
- ret = usb_lock_device_for_reset(urb->dev, NULL);
|
|
|
- if (ret < 0) {
|
|
|
- dev_err(&urb->dev->dev, "lock for reset\n");
|
|
|
- return ret;
|
|
|
- }
|
|
|
-
|
|
|
- /* try to reset the device */
|
|
|
- ret = usb_reset_device(urb->dev);
|
|
|
- if (ret < 0)
|
|
|
- dev_err(&urb->dev->dev, "device reset\n");
|
|
|
+ usbip_uinfo("reset_device %s\n", dev_name(&urb->dev->dev));
|
|
|
|
|
|
- usb_unlock_device(urb->dev);
|
|
|
-
|
|
|
- return ret;
|
|
|
+ /*
|
|
|
+ * usb_lock_device_for_reset caused a deadlock: it causes the driver
|
|
|
+ * to unbind. In the shutdown the rx thread is signalled to shut down
|
|
|
+ * but this thread is pending in the usb_lock_device_for_reset.
|
|
|
+ *
|
|
|
+ * Instead queue the reset.
|
|
|
+ *
|
|
|
+ * Unfortunatly an existing usbip connection will be dropped due to
|
|
|
+ * driver unbinding.
|
|
|
+ */
|
|
|
+ usb_queue_reset_device(sdev->interface);
|
|
|
+ return 0;
|
|
|
}
|
|
|
|
|
|
/*
|