From 615322f6ac358f9c94b483d0a16f3f46fcb27b1c Mon Sep 17 00:00:00 2001 From: Oliver Neukum Date: Mon, 29 Jun 2015 11:10:41 +0200 Subject: [PATCH 1/7] HID: usbhid: no flushing if device is already polled During open() it is unnecessary to wait for the device to flush stale inputs if the device is polled while closed due to a quirk or opening fails. Signed-off-by: Oliver Neukum Signed-off-by: Jiri Kosina --- drivers/hid/usbhid/hid-core.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/drivers/hid/usbhid/hid-core.c b/drivers/hid/usbhid/hid-core.c index bfbe1bedda7f..1a23d78fe5e7 100644 --- a/drivers/hid/usbhid/hid-core.c +++ b/drivers/hid/usbhid/hid-core.c @@ -710,7 +710,8 @@ int usbhid_open(struct hid_device *hid) * Wait 50 msec for the queue to empty before allowing events * to go through hid. */ - msleep(50); + if (res == 0 && !(hid->quirks & HID_QUIRK_ALWAYS_POLL)) + msleep(50); clear_bit(HID_RESUME_RUNNING, &usbhid->iofl); } done: From 67e123ff0e9a71fcf19f83827d59f73076f5bd1a Mon Sep 17 00:00:00 2001 From: Markus Elfring Date: Thu, 9 Jul 2015 08:08:15 +0200 Subject: [PATCH 2/7] HID: wacom: Delete unnecessary checks before the function call "input_free_device" The input_free_device() function tests whether its argument is NULL and then returns immediately. Thus the test around the call is not needed. This issue was detected by using the Coccinelle software. Signed-off-by: Markus Elfring Signed-off-by: Jiri Kosina --- drivers/hid/wacom_sys.c | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/drivers/hid/wacom_sys.c b/drivers/hid/wacom_sys.c index 4c0ffca97bef..936ad7770ec3 100644 --- a/drivers/hid/wacom_sys.c +++ b/drivers/hid/wacom_sys.c @@ -1149,12 +1149,9 @@ static void wacom_free_inputs(struct wacom *wacom) { struct wacom_wac *wacom_wac = &(wacom->wacom_wac); - if (wacom_wac->pen_input) - input_free_device(wacom_wac->pen_input); - if (wacom_wac->touch_input) - input_free_device(wacom_wac->touch_input); - if (wacom_wac->pad_input) - input_free_device(wacom_wac->pad_input); + input_free_device(wacom_wac->pen_input); + input_free_device(wacom_wac->touch_input); + input_free_device(wacom_wac->pad_input); wacom_wac->pen_input = NULL; wacom_wac->touch_input = NULL; wacom_wac->pad_input = NULL; From 3eb4351af42bd8b6de20daab07b204a85c35248f Mon Sep 17 00:00:00 2001 From: Dmitry Torokhov Date: Thu, 9 Jul 2015 14:33:21 -0700 Subject: [PATCH 3/7] HID: input: call input_sync() when automatically releasing a key We need to emit EV_SYN/SYN_REPORT between key press and release, otherwise userspace is allowed to "swallow" the event. [jkosina@suse.com: Dmitry says that he's observing this behavior with Plantronics headset] Signed-off-by: Dmitry Torokhov Signed-off-by: Jiri Kosina --- drivers/hid/hid-input.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/drivers/hid/hid-input.c b/drivers/hid/hid-input.c index 3511bbaba505..14aebe483219 100644 --- a/drivers/hid/hid-input.c +++ b/drivers/hid/hid-input.c @@ -1163,8 +1163,11 @@ void hidinput_hid_event(struct hid_device *hid, struct hid_field *field, struct input_event(input, usage->type, usage->code, value); - if ((field->flags & HID_MAIN_ITEM_RELATIVE) && (usage->type == EV_KEY)) + if ((field->flags & HID_MAIN_ITEM_RELATIVE) && + usage->type == EV_KEY && value) { + input_sync(input); input_event(input, usage->type, usage->code, 0); + } } void hidinput_report_event(struct hid_device *hid, struct hid_report *report) From ba53219809f4b3a08f21600a0f3b675620d518bc Mon Sep 17 00:00:00 2001 From: Benjamin Tissoires Date: Fri, 24 Jul 2015 12:02:22 -0400 Subject: [PATCH 4/7] HID: core: do not reject devices when they declare too many usages MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Some device present proprietary collections with a usage min of 0x00 and a usage max of 0xffff. hid-core currently reject them while most of the time this is harmless. Let's ignore the exceeding usages, and hope for the best. Reported-by: Simon Wörner Signed-off-by: Benjamin Tissoires Signed-off-by: Jiri Kosina --- drivers/hid/hid-core.c | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/drivers/hid/hid-core.c b/drivers/hid/hid-core.c index 157c62775053..b403fe2c5cbe 100644 --- a/drivers/hid/hid-core.c +++ b/drivers/hid/hid-core.c @@ -427,6 +427,7 @@ static int hid_parser_local(struct hid_parser *parser, struct hid_item *item) { __u32 data; unsigned n; + __u32 count; data = item_udata(item); @@ -490,6 +491,24 @@ static int hid_parser_local(struct hid_parser *parser, struct hid_item *item) if (item->size <= 2) data = (parser->global.usage_page << 16) + data; + count = data - parser->local.usage_minimum; + if (count + parser->local.usage_index >= HID_MAX_USAGES) { + /* + * We do not warn if the name is not set, we are + * actually pre-scanning the device. + */ + if (dev_name(&parser->device->dev)) + hid_warn(parser->device, + "ignoring exceeding usage max\n"); + data = HID_MAX_USAGES - parser->local.usage_index + + parser->local.usage_minimum - 1; + if (data <= 0) { + hid_err(parser->device, + "no more usage index available\n"); + return -1; + } + } + for (n = parser->local.usage_minimum; n <= data; n++) if (hid_add_usage(parser, n)) { dbg_hid("hid_add_usage failed\n"); From a1c173dac102d7d91e5cafdb8cb212300063eaa3 Mon Sep 17 00:00:00 2001 From: Jason Gerecke Date: Wed, 5 Aug 2015 15:45:30 -0700 Subject: [PATCH 5/7] HID: wacom: Do not repeatedly attempt to set device mode on error As an extension of aef3156d7, there is no sense in repeatedly calling the 'wacom_set_report' and 'wacom_get_report' functions if they return an error. Getting an error from them implies that the device is out to lunch: either a hard error code was returned or repeated attempts at recovering from a "soft" error all failed. In either case, doing even more retries is not likely to resolve whatever is wrong. Signed-off-by: Jason Gerecke Signed-off-by: Jiri Kosina --- drivers/hid/wacom_sys.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/hid/wacom_sys.c b/drivers/hid/wacom_sys.c index 936ad7770ec3..177e49b11e33 100644 --- a/drivers/hid/wacom_sys.c +++ b/drivers/hid/wacom_sys.c @@ -335,7 +335,7 @@ static int wacom_set_device_mode(struct hid_device *hdev, int report_id, if (error >= 0) error = wacom_get_report(hdev, HID_FEATURE_REPORT, rep_data, length, 1); - } while ((error < 0 || rep_data[1] != mode) && limit++ < WAC_MSG_RETRIES); + } while (error >= 0 && rep_data[1] != mode && limit++ < WAC_MSG_RETRIES); kfree(rep_data); From 3af4e5a95184d6d3c1c6a065f163faa174a96a1d Mon Sep 17 00:00:00 2001 From: Don Zickus Date: Mon, 10 Aug 2015 12:06:53 -0400 Subject: [PATCH 6/7] HID: usbhid: Fix the check for HID_RESET_PENDING in hid_io_error It was reported that after 10-20 reboots, a usb keyboard plugged into a docking station would not work unless it was replugged in. Using usbmon, it turns out the interrupt URBs were streaming with callback errors of -71 for some reason. The hid-core.c::hid_io_error was supposed to retry and then reset, but the reset wasn't really happening. The check for HID_NO_BANDWIDTH was inverted. Fix was simple. Tested by reporter and locally by me by unplugging a keyboard halfway until I could recreate a stream of errors but no disconnect. Signed-off-by: Don Zickus Cc: stable@vger.kernel.org Signed-off-by: Jiri Kosina --- drivers/hid/usbhid/hid-core.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/hid/usbhid/hid-core.c b/drivers/hid/usbhid/hid-core.c index 1a23d78fe5e7..36712e9f56c2 100644 --- a/drivers/hid/usbhid/hid-core.c +++ b/drivers/hid/usbhid/hid-core.c @@ -164,7 +164,7 @@ static void hid_io_error(struct hid_device *hid) if (time_after(jiffies, usbhid->stop_retry)) { /* Retries failed, so do a port reset unless we lack bandwidth*/ - if (test_bit(HID_NO_BANDWIDTH, &usbhid->iofl) + if (!test_bit(HID_NO_BANDWIDTH, &usbhid->iofl) && !test_and_set_bit(HID_RESET_PENDING, &usbhid->iofl)) { schedule_work(&usbhid->reset_work); From c9b57724b38d4c1555ee49418be3d76801e3327c Mon Sep 17 00:00:00 2001 From: Benjamin Tissoires Date: Fri, 21 Aug 2015 10:18:08 -0400 Subject: [PATCH 7/7] HID: quirks: add QUIRK_NOGET for an other TPV touchscreen Looks like 0x8882 needs the same quirk than 0x8883. Given that both devices claim they are "TPV OpticalTouchScreen" rename the 0x8883 to add its PID in the #define. Reported-by: Blaine Lee Signed-off-by: Benjamin Tissoires Signed-off-by: Jiri Kosina --- drivers/hid/hid-ids.h | 3 ++- drivers/hid/usbhid/hid-quirks.c | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index b04b0820d816..0de3284a3e24 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h @@ -922,7 +922,8 @@ #define USB_DEVICE_ID_TOUCHPACK_RTS 0x1688 #define USB_VENDOR_ID_TPV 0x25aa -#define USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN 0x8883 +#define USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8882 0x8882 +#define USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8883 0x8883 #define USB_VENDOR_ID_TURBOX 0x062a #define USB_DEVICE_ID_TURBOX_KEYBOARD 0x0201 diff --git a/drivers/hid/usbhid/hid-quirks.c b/drivers/hid/usbhid/hid-quirks.c index 53e7de7cb9e2..a983418114bb 100644 --- a/drivers/hid/usbhid/hid-quirks.c +++ b/drivers/hid/usbhid/hid-quirks.c @@ -114,7 +114,8 @@ static const struct hid_blacklist { { USB_VENDOR_ID_SUN, USB_DEVICE_ID_RARITAN_KVM_DONGLE, HID_QUIRK_NOGET }, { USB_VENDOR_ID_SYMBOL, USB_DEVICE_ID_SYMBOL_SCANNER_1, HID_QUIRK_NOGET }, { USB_VENDOR_ID_SYMBOL, USB_DEVICE_ID_SYMBOL_SCANNER_2, HID_QUIRK_NOGET }, - { USB_VENDOR_ID_TPV, USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_TPV, USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8882, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_TPV, USB_DEVICE_ID_TPV_OPTICAL_TOUCHSCREEN_8883, HID_QUIRK_NOGET }, { USB_VENDOR_ID_TURBOX, USB_DEVICE_ID_TURBOX_KEYBOARD, HID_QUIRK_NOGET }, { USB_VENDOR_ID_UCLOGIC, USB_DEVICE_ID_UCLOGIC_TABLET_KNA5, HID_QUIRK_MULTI_INPUT }, { USB_VENDOR_ID_UCLOGIC, USB_DEVICE_ID_UCLOGIC_TABLET_TWA60, HID_QUIRK_MULTI_INPUT },