Loading drivers/hid/hid-input.c +23 −13 Original line number Original line Diff line number Diff line Loading @@ -350,13 +350,13 @@ static int hidinput_query_battery_capacity(struct hid_device *dev) u8 *buf; u8 *buf; int ret; int ret; buf = kmalloc(2, GFP_KERNEL); buf = kmalloc(4, GFP_KERNEL); if (!buf) if (!buf) return -ENOMEM; return -ENOMEM; ret = hid_hw_raw_request(dev, dev->battery_report_id, buf, 2, ret = hid_hw_raw_request(dev, dev->battery_report_id, buf, 4, dev->battery_report_type, HID_REQ_GET_REPORT); dev->battery_report_type, HID_REQ_GET_REPORT); if (ret != 2) { if (ret < 2) { kfree(buf); kfree(buf); return -ENODATA; return -ENODATA; } } Loading Loading @@ -1560,21 +1560,12 @@ static bool __hidinput_change_resolution_multipliers(struct hid_device *hid, { { struct hid_usage *usage; struct hid_usage *usage; bool update_needed = false; bool update_needed = false; bool get_report_completed = false; int i, j; int i, j; if (report->maxfield == 0) if (report->maxfield == 0) return false; return false; /* * If we have more than one feature within this report we * need to fill in the bits from the others before we can * overwrite the ones for the Resolution Multiplier. */ if (report->maxfield > 1) { hid_hw_request(hid, report, HID_REQ_GET_REPORT); hid_hw_wait(hid); } for (i = 0; i < report->maxfield; i++) { for (i = 0; i < report->maxfield; i++) { __s32 value = use_logical_max ? __s32 value = use_logical_max ? report->field[i]->logical_maximum : report->field[i]->logical_maximum : Loading @@ -1593,6 +1584,25 @@ static bool __hidinput_change_resolution_multipliers(struct hid_device *hid, if (usage->hid != HID_GD_RESOLUTION_MULTIPLIER) if (usage->hid != HID_GD_RESOLUTION_MULTIPLIER) continue; continue; /* * If we have more than one feature within this * report we need to fill in the bits from the * others before we can overwrite the ones for the * Resolution Multiplier. * * But if we're not allowed to read from the device, * we just bail. Such a device should not exist * anyway. */ if (!get_report_completed && report->maxfield > 1) { if (hid->quirks & HID_QUIRK_NO_INIT_REPORTS) return update_needed; hid_hw_request(hid, report, HID_REQ_GET_REPORT); hid_hw_wait(hid); get_report_completed = true; } report->field[i]->value[j] = value; report->field[i]->value[j] = value; update_needed = true; update_needed = true; } } Loading drivers/hid/usbhid/hid-core.c +30 −25 Original line number Original line Diff line number Diff line Loading @@ -26,6 +26,7 @@ #include <linux/wait.h> #include <linux/wait.h> #include <linux/workqueue.h> #include <linux/workqueue.h> #include <linux/string.h> #include <linux/string.h> #include <linux/timekeeping.h> #include <linux/usb.h> #include <linux/usb.h> Loading Loading @@ -95,6 +96,18 @@ static int hid_start_in(struct hid_device *hid) set_bit(HID_NO_BANDWIDTH, &usbhid->iofl); set_bit(HID_NO_BANDWIDTH, &usbhid->iofl); } else { } else { clear_bit(HID_NO_BANDWIDTH, &usbhid->iofl); clear_bit(HID_NO_BANDWIDTH, &usbhid->iofl); if (test_bit(HID_RESUME_RUNNING, &usbhid->iofl)) { /* * In case events are generated while nobody was * listening, some are released when the device * is re-opened. Wait 50 msec for the queue to * empty before allowing events to go through * hid. */ usbhid->input_start_time = ktime_add_ms(ktime_get_coarse(), 50); } } } } } spin_unlock_irqrestore(&usbhid->lock, flags); spin_unlock_irqrestore(&usbhid->lock, flags); Loading Loading @@ -280,10 +293,14 @@ static void hid_irq_in(struct urb *urb) if (!test_bit(HID_OPENED, &usbhid->iofl)) if (!test_bit(HID_OPENED, &usbhid->iofl)) break; break; usbhid_mark_busy(usbhid); usbhid_mark_busy(usbhid); if (!test_bit(HID_RESUME_RUNNING, &usbhid->iofl)) { if (test_bit(HID_RESUME_RUNNING, &usbhid->iofl)) { if (ktime_before(ktime_get_coarse(), usbhid->input_start_time)) break; clear_bit(HID_RESUME_RUNNING, &usbhid->iofl); } hid_input_report(urb->context, HID_INPUT_REPORT, hid_input_report(urb->context, HID_INPUT_REPORT, urb->transfer_buffer, urb->transfer_buffer, urb->actual_length, 1); urb->actual_length, 1); /* /* * autosuspend refused while keys are pressed * autosuspend refused while keys are pressed * because most keyboards don't wake up when * because most keyboards don't wake up when Loading @@ -293,7 +310,6 @@ static void hid_irq_in(struct urb *urb) set_bit(HID_KEYS_PRESSED, &usbhid->iofl); set_bit(HID_KEYS_PRESSED, &usbhid->iofl); else else clear_bit(HID_KEYS_PRESSED, &usbhid->iofl); clear_bit(HID_KEYS_PRESSED, &usbhid->iofl); } break; break; case -EPIPE: /* stall */ case -EPIPE: /* stall */ usbhid_mark_busy(usbhid); usbhid_mark_busy(usbhid); Loading Loading @@ -720,17 +736,6 @@ static int usbhid_open(struct hid_device *hid) usb_autopm_put_interface(usbhid->intf); usb_autopm_put_interface(usbhid->intf); /* * In case events are generated while nobody was listening, * some are released when the device is re-opened. * Wait 50 msec for the queue to empty before allowing events * to go through hid. */ if (res == 0) msleep(50); clear_bit(HID_RESUME_RUNNING, &usbhid->iofl); Done: Done: mutex_unlock(&usbhid->mutex); mutex_unlock(&usbhid->mutex); return res; return res; Loading Loading @@ -1667,7 +1672,7 @@ struct usb_interface *usbhid_find_interface(int minor) static int __init hid_init(void) static int __init hid_init(void) { { int retval = -ENOMEM; int retval; retval = hid_quirks_init(quirks_param, BUS_USB, MAX_USBHID_BOOT_QUIRKS); retval = hid_quirks_init(quirks_param, BUS_USB, MAX_USBHID_BOOT_QUIRKS); if (retval) if (retval) Loading drivers/hid/usbhid/usbhid.h +2 −0 Original line number Original line Diff line number Diff line Loading @@ -13,6 +13,7 @@ #include <linux/types.h> #include <linux/types.h> #include <linux/slab.h> #include <linux/slab.h> #include <linux/ktime.h> #include <linux/list.h> #include <linux/list.h> #include <linux/mutex.h> #include <linux/mutex.h> #include <linux/timer.h> #include <linux/timer.h> Loading Loading @@ -83,6 +84,7 @@ struct usbhid_device { struct mutex mutex; /* start/stop/open/close */ struct mutex mutex; /* start/stop/open/close */ spinlock_t lock; /* fifo spinlock */ spinlock_t lock; /* fifo spinlock */ unsigned long iofl; /* I/O flags (CTRL_RUNNING, OUT_RUNNING) */ unsigned long iofl; /* I/O flags (CTRL_RUNNING, OUT_RUNNING) */ ktime_t input_start_time; /* When to start handling input */ struct timer_list io_retry; /* Retry timer */ struct timer_list io_retry; /* Retry timer */ unsigned long stop_retry; /* Time to give up, in jiffies */ unsigned long stop_retry; /* Time to give up, in jiffies */ unsigned int retry_delay; /* Delay length in ms */ unsigned int retry_delay; /* Delay length in ms */ Loading Loading
drivers/hid/hid-input.c +23 −13 Original line number Original line Diff line number Diff line Loading @@ -350,13 +350,13 @@ static int hidinput_query_battery_capacity(struct hid_device *dev) u8 *buf; u8 *buf; int ret; int ret; buf = kmalloc(2, GFP_KERNEL); buf = kmalloc(4, GFP_KERNEL); if (!buf) if (!buf) return -ENOMEM; return -ENOMEM; ret = hid_hw_raw_request(dev, dev->battery_report_id, buf, 2, ret = hid_hw_raw_request(dev, dev->battery_report_id, buf, 4, dev->battery_report_type, HID_REQ_GET_REPORT); dev->battery_report_type, HID_REQ_GET_REPORT); if (ret != 2) { if (ret < 2) { kfree(buf); kfree(buf); return -ENODATA; return -ENODATA; } } Loading Loading @@ -1560,21 +1560,12 @@ static bool __hidinput_change_resolution_multipliers(struct hid_device *hid, { { struct hid_usage *usage; struct hid_usage *usage; bool update_needed = false; bool update_needed = false; bool get_report_completed = false; int i, j; int i, j; if (report->maxfield == 0) if (report->maxfield == 0) return false; return false; /* * If we have more than one feature within this report we * need to fill in the bits from the others before we can * overwrite the ones for the Resolution Multiplier. */ if (report->maxfield > 1) { hid_hw_request(hid, report, HID_REQ_GET_REPORT); hid_hw_wait(hid); } for (i = 0; i < report->maxfield; i++) { for (i = 0; i < report->maxfield; i++) { __s32 value = use_logical_max ? __s32 value = use_logical_max ? report->field[i]->logical_maximum : report->field[i]->logical_maximum : Loading @@ -1593,6 +1584,25 @@ static bool __hidinput_change_resolution_multipliers(struct hid_device *hid, if (usage->hid != HID_GD_RESOLUTION_MULTIPLIER) if (usage->hid != HID_GD_RESOLUTION_MULTIPLIER) continue; continue; /* * If we have more than one feature within this * report we need to fill in the bits from the * others before we can overwrite the ones for the * Resolution Multiplier. * * But if we're not allowed to read from the device, * we just bail. Such a device should not exist * anyway. */ if (!get_report_completed && report->maxfield > 1) { if (hid->quirks & HID_QUIRK_NO_INIT_REPORTS) return update_needed; hid_hw_request(hid, report, HID_REQ_GET_REPORT); hid_hw_wait(hid); get_report_completed = true; } report->field[i]->value[j] = value; report->field[i]->value[j] = value; update_needed = true; update_needed = true; } } Loading
drivers/hid/usbhid/hid-core.c +30 −25 Original line number Original line Diff line number Diff line Loading @@ -26,6 +26,7 @@ #include <linux/wait.h> #include <linux/wait.h> #include <linux/workqueue.h> #include <linux/workqueue.h> #include <linux/string.h> #include <linux/string.h> #include <linux/timekeeping.h> #include <linux/usb.h> #include <linux/usb.h> Loading Loading @@ -95,6 +96,18 @@ static int hid_start_in(struct hid_device *hid) set_bit(HID_NO_BANDWIDTH, &usbhid->iofl); set_bit(HID_NO_BANDWIDTH, &usbhid->iofl); } else { } else { clear_bit(HID_NO_BANDWIDTH, &usbhid->iofl); clear_bit(HID_NO_BANDWIDTH, &usbhid->iofl); if (test_bit(HID_RESUME_RUNNING, &usbhid->iofl)) { /* * In case events are generated while nobody was * listening, some are released when the device * is re-opened. Wait 50 msec for the queue to * empty before allowing events to go through * hid. */ usbhid->input_start_time = ktime_add_ms(ktime_get_coarse(), 50); } } } } } spin_unlock_irqrestore(&usbhid->lock, flags); spin_unlock_irqrestore(&usbhid->lock, flags); Loading Loading @@ -280,10 +293,14 @@ static void hid_irq_in(struct urb *urb) if (!test_bit(HID_OPENED, &usbhid->iofl)) if (!test_bit(HID_OPENED, &usbhid->iofl)) break; break; usbhid_mark_busy(usbhid); usbhid_mark_busy(usbhid); if (!test_bit(HID_RESUME_RUNNING, &usbhid->iofl)) { if (test_bit(HID_RESUME_RUNNING, &usbhid->iofl)) { if (ktime_before(ktime_get_coarse(), usbhid->input_start_time)) break; clear_bit(HID_RESUME_RUNNING, &usbhid->iofl); } hid_input_report(urb->context, HID_INPUT_REPORT, hid_input_report(urb->context, HID_INPUT_REPORT, urb->transfer_buffer, urb->transfer_buffer, urb->actual_length, 1); urb->actual_length, 1); /* /* * autosuspend refused while keys are pressed * autosuspend refused while keys are pressed * because most keyboards don't wake up when * because most keyboards don't wake up when Loading @@ -293,7 +310,6 @@ static void hid_irq_in(struct urb *urb) set_bit(HID_KEYS_PRESSED, &usbhid->iofl); set_bit(HID_KEYS_PRESSED, &usbhid->iofl); else else clear_bit(HID_KEYS_PRESSED, &usbhid->iofl); clear_bit(HID_KEYS_PRESSED, &usbhid->iofl); } break; break; case -EPIPE: /* stall */ case -EPIPE: /* stall */ usbhid_mark_busy(usbhid); usbhid_mark_busy(usbhid); Loading Loading @@ -720,17 +736,6 @@ static int usbhid_open(struct hid_device *hid) usb_autopm_put_interface(usbhid->intf); usb_autopm_put_interface(usbhid->intf); /* * In case events are generated while nobody was listening, * some are released when the device is re-opened. * Wait 50 msec for the queue to empty before allowing events * to go through hid. */ if (res == 0) msleep(50); clear_bit(HID_RESUME_RUNNING, &usbhid->iofl); Done: Done: mutex_unlock(&usbhid->mutex); mutex_unlock(&usbhid->mutex); return res; return res; Loading Loading @@ -1667,7 +1672,7 @@ struct usb_interface *usbhid_find_interface(int minor) static int __init hid_init(void) static int __init hid_init(void) { { int retval = -ENOMEM; int retval; retval = hid_quirks_init(quirks_param, BUS_USB, MAX_USBHID_BOOT_QUIRKS); retval = hid_quirks_init(quirks_param, BUS_USB, MAX_USBHID_BOOT_QUIRKS); if (retval) if (retval) Loading
drivers/hid/usbhid/usbhid.h +2 −0 Original line number Original line Diff line number Diff line Loading @@ -13,6 +13,7 @@ #include <linux/types.h> #include <linux/types.h> #include <linux/slab.h> #include <linux/slab.h> #include <linux/ktime.h> #include <linux/list.h> #include <linux/list.h> #include <linux/mutex.h> #include <linux/mutex.h> #include <linux/timer.h> #include <linux/timer.h> Loading Loading @@ -83,6 +84,7 @@ struct usbhid_device { struct mutex mutex; /* start/stop/open/close */ struct mutex mutex; /* start/stop/open/close */ spinlock_t lock; /* fifo spinlock */ spinlock_t lock; /* fifo spinlock */ unsigned long iofl; /* I/O flags (CTRL_RUNNING, OUT_RUNNING) */ unsigned long iofl; /* I/O flags (CTRL_RUNNING, OUT_RUNNING) */ ktime_t input_start_time; /* When to start handling input */ struct timer_list io_retry; /* Retry timer */ struct timer_list io_retry; /* Retry timer */ unsigned long stop_retry; /* Time to give up, in jiffies */ unsigned long stop_retry; /* Time to give up, in jiffies */ unsigned int retry_delay; /* Delay length in ms */ unsigned int retry_delay; /* Delay length in ms */ Loading