Commit e399396a authored by Dmitry Torokhov's avatar Dmitry Torokhov Committed by Jiri Kosina

HID: usbhid: remove custom locking from usbhid_open/close

Now that HID core enforces serialization of transport driver open/close
calls we can remove custom locking from usbhid driver.
Signed-off-by: default avatarDmitry Torokhov <dmitry.torokhov@gmail.com>
Reviewed-by: default avatarAndy Shevchenko <andy.shevchenko@gmail.com>
Reviewed-by: default avatarBenjamin Tissoires <benjamin.tissoires@redhat.com>
Signed-off-by: default avatarJiri Kosina <jkosina@suse.cz>
parent 85ae9113
...@@ -70,8 +70,6 @@ MODULE_PARM_DESC(quirks, "Add/modify USB HID quirks by specifying " ...@@ -70,8 +70,6 @@ MODULE_PARM_DESC(quirks, "Add/modify USB HID quirks by specifying "
/* /*
* Input submission and I/O error handler. * Input submission and I/O error handler.
*/ */
static DEFINE_MUTEX(hid_open_mut);
static void hid_io_error(struct hid_device *hid); static void hid_io_error(struct hid_device *hid);
static int hid_submit_out(struct hid_device *hid); static int hid_submit_out(struct hid_device *hid);
static int hid_submit_ctrl(struct hid_device *hid); static int hid_submit_ctrl(struct hid_device *hid);
...@@ -680,21 +678,22 @@ static int hid_get_class_descriptor(struct usb_device *dev, int ifnum, ...@@ -680,21 +678,22 @@ static int hid_get_class_descriptor(struct usb_device *dev, int ifnum,
static int usbhid_open(struct hid_device *hid) static int usbhid_open(struct hid_device *hid)
{ {
struct usbhid_device *usbhid = hid->driver_data; struct usbhid_device *usbhid = hid->driver_data;
int res = 0; int res;
if (hid->quirks & HID_QUIRK_ALWAYS_POLL)
return 0;
mutex_lock(&hid_open_mut);
if (!hid->open++) {
res = usb_autopm_get_interface(usbhid->intf); res = usb_autopm_get_interface(usbhid->intf);
/* the device must be awake to reliably request remote wakeup */ /* the device must be awake to reliably request remote wakeup */
if (res < 0) { if (res < 0)
hid->open--; return -EIO;
res = -EIO;
goto done;
}
usbhid->intf->needs_remote_wakeup = 1; usbhid->intf->needs_remote_wakeup = 1;
set_bit(HID_RESUME_RUNNING, &usbhid->iofl);
set_bit(HID_OPENED, &usbhid->iofl); set_bit(HID_OPENED, &usbhid->iofl);
set_bit(HID_IN_POLLING, &usbhid->iofl); set_bit(HID_IN_POLLING, &usbhid->iofl);
set_bit(HID_RESUME_RUNNING, &usbhid->iofl);
res = hid_start_in(hid); res = hid_start_in(hid);
if (res) { if (res) {
if (res != -ENOSPC) { if (res != -ENOSPC) {
...@@ -702,14 +701,13 @@ static int usbhid_open(struct hid_device *hid) ...@@ -702,14 +701,13 @@ static int usbhid_open(struct hid_device *hid)
res = 0; res = 0;
} else { } else {
/* no use opening if resources are insufficient */ /* no use opening if resources are insufficient */
hid->open--; res = -EBUSY;
clear_bit(HID_OPENED, &usbhid->iofl); clear_bit(HID_OPENED, &usbhid->iofl);
if (!(hid->quirks & HID_QUIRK_ALWAYS_POLL))
clear_bit(HID_IN_POLLING, &usbhid->iofl); clear_bit(HID_IN_POLLING, &usbhid->iofl);
res = -EBUSY;
usbhid->intf->needs_remote_wakeup = 0; usbhid->intf->needs_remote_wakeup = 0;
} }
} }
usb_autopm_put_interface(usbhid->intf); usb_autopm_put_interface(usbhid->intf);
/* /*
...@@ -718,12 +716,10 @@ static int usbhid_open(struct hid_device *hid) ...@@ -718,12 +716,10 @@ static int usbhid_open(struct hid_device *hid)
* Wait 50 msec for the queue to empty before allowing events * Wait 50 msec for the queue to empty before allowing events
* to go through hid. * to go through hid.
*/ */
if (res == 0 && !(hid->quirks & HID_QUIRK_ALWAYS_POLL)) if (res == 0)
msleep(50); msleep(50);
clear_bit(HID_RESUME_RUNNING, &usbhid->iofl); clear_bit(HID_RESUME_RUNNING, &usbhid->iofl);
}
done:
mutex_unlock(&hid_open_mut);
return res; return res;
} }
...@@ -731,27 +727,22 @@ static void usbhid_close(struct hid_device *hid) ...@@ -731,27 +727,22 @@ static void usbhid_close(struct hid_device *hid)
{ {
struct usbhid_device *usbhid = hid->driver_data; struct usbhid_device *usbhid = hid->driver_data;
mutex_lock(&hid_open_mut); if (hid->quirks & HID_QUIRK_ALWAYS_POLL)
return;
/* protecting hid->open to make sure we don't restart /*
* data acquistion due to a resumption we no longer * Make sure we don't restart data acquisition due to
* care about * a resumption we no longer care about by avoiding racing
* with hid_start_in().
*/ */
spin_lock_irq(&usbhid->lock); spin_lock_irq(&usbhid->lock);
if (!--hid->open) {
if (!(hid->quirks & HID_QUIRK_ALWAYS_POLL))
clear_bit(HID_IN_POLLING, &usbhid->iofl); clear_bit(HID_IN_POLLING, &usbhid->iofl);
clear_bit(HID_OPENED, &usbhid->iofl); clear_bit(HID_OPENED, &usbhid->iofl);
spin_unlock_irq(&usbhid->lock); spin_unlock_irq(&usbhid->lock);
hid_cancel_delayed_stuff(usbhid); hid_cancel_delayed_stuff(usbhid);
if (!(hid->quirks & HID_QUIRK_ALWAYS_POLL)) {
usb_kill_urb(usbhid->urbin); usb_kill_urb(usbhid->urbin);
usbhid->intf->needs_remote_wakeup = 0; usbhid->intf->needs_remote_wakeup = 0;
}
} else {
spin_unlock_irq(&usbhid->lock);
}
mutex_unlock(&hid_open_mut);
} }
/* /*
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment