From: Greg Kroah-Hartman Date: Wed, 9 Apr 2014 22:32:49 +0000 (-0700) Subject: 3.4-stable patches X-Git-Tag: v3.10.37~24 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=7f5860a72cb7ae230d7d2712e57ec889d2ef92be;p=thirdparty%2Fkernel%2Fstable-queue.git 3.4-stable patches added patches: hid-add-quirk-for-freescale-i.mx28-rom-recovery.patch hid-add-support-for-sony-rf-receiver-with-usb-product-id-0x0374.patch hid-apple-add-apple-wireless-keyboard-2011-ansi-pid.patch hid-clean-up-quirk-for-sony-rf-receivers.patch hid-fix-return-value-of-hidraw_report_event-when-config_hidraw.patch hid-hidraw-add-proper-error-handling-to-raw-event-reporting.patch hid-hidraw-correctly-deallocate-memory-on-device-disconnect.patch hid-hidraw-fix-list-buffer-memleak.patch hid-hidraw-improve-error-handling-in-hidraw_init.patch hid-multitouch-validate-indexes-details.patch hid-usbhid-fix-build-problem.patch hid-usbhid-quirk-for-formosa-ir-receiver.patch hid-usbhid-quirk-for-msi-gx680r-led-panel.patch hid-validate-feature-and-input-report-details.patch intel_idle-check-cpu_idle_get_driver-for-null-before-dereferencing-it.patch --- diff --git a/queue-3.4/hid-add-quirk-for-freescale-i.mx28-rom-recovery.patch b/queue-3.4/hid-add-quirk-for-freescale-i.mx28-rom-recovery.patch new file mode 100644 index 00000000000..09a6d8a5378 --- /dev/null +++ b/queue-3.4/hid-add-quirk-for-freescale-i.mx28-rom-recovery.patch @@ -0,0 +1,50 @@ +From 2843b673d03421e0e73cf061820d1db328f7c8eb Mon Sep 17 00:00:00 2001 +From: Marek Vasut +Date: Sun, 5 Aug 2012 23:57:15 +0200 +Subject: HID: add quirk for Freescale i.MX28 ROM recovery + +From: Marek Vasut + +commit 2843b673d03421e0e73cf061820d1db328f7c8eb upstream. + +The USB recovery mode present in i.MX28 ROM emulates USB HID. +It needs this quirk to behave properly. + +Signed-off-by: Marek Vasut +Cc: Chen Peter +Cc: Greg KH +Cc: Jiri Kosina +[jkosina@suse.cz: fix alphabetical ordering] +Signed-off-by: Jiri Kosina +[bwh: Backported to 3.2: adjust context] +Signed-off-by: Ben Hutchings +[yjw: Backported to 3.4: adjust context] +Signed-off-by: Yijing Wang +Signed-off-by: Greg Kroah-Hartman +--- + drivers/hid/hid-ids.h | 3 +++ + drivers/hid/usbhid/hid-quirks.c | 1 + + 2 files changed, 4 insertions(+) + +--- a/drivers/hid/hid-ids.h ++++ b/drivers/hid/hid-ids.h +@@ -293,6 +293,9 @@ + #define USB_VENDOR_ID_FRUCTEL 0x25B6 + #define USB_DEVICE_ID_GAMETEL_MT_MODE 0x0002 + ++#define USB_VENDOR_ID_FREESCALE 0x15A2 ++#define USB_DEVICE_ID_FREESCALE_MX28 0x004F ++ + #define USB_VENDOR_ID_GAMERON 0x0810 + #define USB_DEVICE_ID_GAMERON_DUAL_PSX_ADAPTOR 0x0001 + #define USB_DEVICE_ID_GAMERON_DUAL_PCS_ADAPTOR 0x0002 +--- a/drivers/hid/usbhid/hid-quirks.c ++++ b/drivers/hid/usbhid/hid-quirks.c +@@ -70,6 +70,7 @@ static const struct hid_blacklist { + { USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_AXIS_295, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_DMI, USB_DEVICE_ID_DMI_ENC, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_ELO, USB_DEVICE_ID_ELO_TS2700, HID_QUIRK_NOGET }, ++ { USB_VENDOR_ID_FREESCALE, USB_DEVICE_ID_FREESCALE_MX28, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_MGE, USB_DEVICE_ID_MGE_UPS, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN1, HID_QUIRK_NO_INIT_REPORTS }, diff --git a/queue-3.4/hid-add-support-for-sony-rf-receiver-with-usb-product-id-0x0374.patch b/queue-3.4/hid-add-support-for-sony-rf-receiver-with-usb-product-id-0x0374.patch new file mode 100644 index 00000000000..4185b6a27fc --- /dev/null +++ b/queue-3.4/hid-add-support-for-sony-rf-receiver-with-usb-product-id-0x0374.patch @@ -0,0 +1,130 @@ +From 3207e0076af2a4565230f7c280675383321ecd16 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Fernando=20Luis=20V=C3=A1zquez=20Cao?= + +Date: Tue, 15 Jan 2013 19:40:48 +0900 +Subject: HID: add support for Sony RF receiver with USB product id 0x0374 + +From: =?UTF-8?q?Fernando=20Luis=20V=C3=A1zquez=20Cao?= + +commit a464918419f94a0043d2f549d6defb4c3f69f68a upstream. + +Some Vaio desktop computers, among them the VGC-LN51JGB multimedia PC, have +a RF receiver, multi-interface USB device 054c:0374, that is used to connect +a wireless keyboard and a wireless mouse. + +The keyboard works flawlessly, but the mouse (VGP-WMS3 in my case) does not +seem to be generating any pointer events. The problem is that the mouse pointer +is wrongly declared as a constant non-data variable in the report descriptor +(see lsusb and usbhid-dump output below), with the consequence that it is +ignored by the HID code. + +Add this device to the have-special-driver list and fix up the report +descriptor in the Sony-specific driver which happens to already have a fixup +for a similar firmware bug. + +# lsusb -vd 054C:0374 +Bus 003 Device 002: ID 054c:0374 Sony Corp. +Device Descriptor: + bLength 18 + bDescriptorType 1 + bcdUSB 2.00 + bDeviceClass 0 (Defined at Interface level) + bDeviceSubClass 0 + bDeviceProtocol 0 + bMaxPacketSize0 8 + idVendor 0x054c Sony Corp. + idProduct 0x0374 + iSerial 0 +[...] + Interface Descriptor: + bLength 9 + bDescriptorType 4 + bInterfaceNumber 1 + bAlternateSetting 0 + bNumEndpoints 1 + bInterfaceClass 3 Human Interface Device + bInterfaceSubClass 1 Boot Interface Subclass + bInterfaceProtocol 2 Mouse + iInterface 2 RF Receiver +[...] + Report Descriptor: (length is 100) +[...] + Item(Global): Usage Page, data= [ 0x01 ] 1 + Generic Desktop Controls + Item(Local ): Usage, data= [ 0x30 ] 48 + Direction-X + Item(Local ): Usage, data= [ 0x31 ] 49 + Direction-Y + Item(Global): Report Count, data= [ 0x02 ] 2 + Item(Global): Report Size, data= [ 0x08 ] 8 + Item(Global): Logical Minimum, data= [ 0x81 ] 129 + Item(Global): Logical Maximum, data= [ 0x7f ] 127 + Item(Main ): Input, data= [ 0x07 ] 7 + Constant Variable Relative No_Wrap Linear + Preferred_State No_Null_Position Non_Volatile Bitfield + +# usbhid-dump +003:002:001:DESCRIPTOR 1357910009.758544 + 05 01 09 02 A1 01 05 01 09 02 A1 02 85 01 09 01 + A1 00 05 09 19 01 29 05 95 05 75 01 15 00 25 01 + 81 02 75 03 95 01 81 01 05 01 09 30 09 31 95 02 + 75 08 15 81 25 7F 81 07 A1 02 85 01 09 38 35 00 + 45 00 15 81 25 7F 95 01 75 08 81 06 C0 A1 02 85 + 01 05 0C 15 81 25 7F 95 01 75 08 0A 38 02 81 06 + C0 C0 C0 C0 + +Cc: linux-input@vger.kernel.org +Cc: linux-usb@vger.kernel.org +Cc: linux-kernel@vger.kernel.org +Signed-off-by: Fernando Luis Vazquez Cao +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hid-core.c | 1 + + drivers/hid/hid-ids.h | 1 + + drivers/hid/hid-sony.c | 4 +++- + 3 files changed, 5 insertions(+), 1 deletion(-) + +--- a/drivers/hid/hid-core.c ++++ b/drivers/hid/hid-core.c +@@ -1619,6 +1619,7 @@ static const struct hid_device_id hid_ha + { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_NAVIGATION_CONTROLLER) }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_PS3_CONTROLLER) }, + { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGP_MOUSE) }, + { HID_USB_DEVICE(USB_VENDOR_ID_STANTUM, USB_DEVICE_ID_MTP) }, + { HID_USB_DEVICE(USB_VENDOR_ID_STANTUM_STM, USB_DEVICE_ID_MTP_STM) }, + { HID_USB_DEVICE(USB_VENDOR_ID_STANTUM_SITRONIX, USB_DEVICE_ID_MTP_SITRONIX) }, +--- a/drivers/hid/hid-ids.h ++++ b/drivers/hid/hid-ids.h +@@ -685,6 +685,7 @@ + + #define USB_VENDOR_ID_SONY 0x054c + #define USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE 0x024b ++#define USB_DEVICE_ID_SONY_VAIO_VGP_MOUSE 0x0374 + #define USB_DEVICE_ID_SONY_PS3_CONTROLLER 0x0268 + #define USB_DEVICE_ID_SONY_NAVIGATION_CONTROLLER 0x042f + +--- a/drivers/hid/hid-sony.c ++++ b/drivers/hid/hid-sony.c +@@ -46,7 +46,7 @@ static __u8 *sony_report_fixup(struct hi + + if ((sc->quirks & VAIO_RDESC_CONSTANT) && + *rsize >= 56 && rdesc[54] == 0x81 && rdesc[55] == 0x07) { +- hid_info(hdev, "Fixing up Sony Vaio VGX report descriptor\n"); ++ hid_info(hdev, "Fixing up Sony RF Receiver report descriptor\n"); + rdesc[55] = 0x06; + } + +@@ -218,6 +218,8 @@ static const struct hid_device_id sony_d + .driver_data = SIXAXIS_CONTROLLER_BT }, + { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGX_MOUSE), + .driver_data = VAIO_RDESC_CONSTANT }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_SONY, USB_DEVICE_ID_SONY_VAIO_VGP_MOUSE), ++ .driver_data = VAIO_RDESC_CONSTANT }, + { } + }; + MODULE_DEVICE_TABLE(hid, sony_devices); diff --git a/queue-3.4/hid-apple-add-apple-wireless-keyboard-2011-ansi-pid.patch b/queue-3.4/hid-apple-add-apple-wireless-keyboard-2011-ansi-pid.patch new file mode 100644 index 00000000000..f551e9add14 --- /dev/null +++ b/queue-3.4/hid-apple-add-apple-wireless-keyboard-2011-ansi-pid.patch @@ -0,0 +1,32 @@ +From fb3ea00df6b94b7a99dea1c26b8177ce4ef1b1f3 Mon Sep 17 00:00:00 2001 +From: Alexey Kaminsky +Date: Mon, 23 Apr 2012 18:02:18 +0200 +Subject: HID: apple: Add Apple wireless keyboard 2011 ANSI PID + +From: Alexey Kaminsky + +commit 0a97e1e9f9a6765e6243030ac42b04694f3f3647 upstream. + +Signed-off-by: Alexey Kaminsky +Signed-off-by: Jiri Kosina +[bwh: Backported to 3.2: add the device ID to hid-ids.h] +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hid-apple.c | 3 +++ + 1 file changed, 3 insertions(+) + +--- a/drivers/hid/hid-apple.c ++++ b/drivers/hid/hid-apple.c +@@ -480,6 +480,9 @@ static const struct hid_device_id apple_ + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2011_ISO), + .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN | + APPLE_ISO_KEYBOARD }, ++ { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, ++ USB_DEVICE_ID_APPLE_ALU_WIRELESS_2011_ANSI), ++ .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_JIS), + .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ANSI), diff --git a/queue-3.4/hid-clean-up-quirk-for-sony-rf-receivers.patch b/queue-3.4/hid-clean-up-quirk-for-sony-rf-receivers.patch new file mode 100644 index 00000000000..a1f34be9e1d --- /dev/null +++ b/queue-3.4/hid-clean-up-quirk-for-sony-rf-receivers.patch @@ -0,0 +1,51 @@ +From 76610d6dfbe4d5f47ce59582d99e1355efaea916 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Fernando=20Luis=20V=C3=A1zquez=20Cao?= + +Date: Tue, 22 Jan 2013 15:20:38 +0900 +Subject: HID: clean up quirk for Sony RF receivers + +From: =?UTF-8?q?Fernando=20Luis=20V=C3=A1zquez=20Cao?= + +commit 99d249021abd4341771523ed8dd7946276103432 upstream. + +Document what the fix-up is does and make it more robust by ensuring +that it is only applied to the USB interface that corresponds to the +mouse (sony_report_fixup() is called once per interface during probing). + +Cc: linux-input@vger.kernel.org +Cc: linux-usb@vger.kernel.org +Cc: linux-kernel@vger.kernel.org +Signed-off-by: Fernando Luis Vazquez Cao +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hid-sony.c | 14 ++++++++++++-- + 1 file changed, 12 insertions(+), 2 deletions(-) + +--- a/drivers/hid/hid-sony.c ++++ b/drivers/hid/hid-sony.c +@@ -44,9 +44,19 @@ static __u8 *sony_report_fixup(struct hi + { + struct sony_sc *sc = hid_get_drvdata(hdev); + +- if ((sc->quirks & VAIO_RDESC_CONSTANT) && +- *rsize >= 56 && rdesc[54] == 0x81 && rdesc[55] == 0x07) { ++ /* ++ * Some Sony RF receivers wrongly declare the mouse pointer as a ++ * a constant non-data variable. ++ */ ++ if ((sc->quirks & VAIO_RDESC_CONSTANT) && *rsize >= 56 && ++ /* usage page: generic desktop controls */ ++ /* rdesc[0] == 0x05 && rdesc[1] == 0x01 && */ ++ /* usage: mouse */ ++ rdesc[2] == 0x09 && rdesc[3] == 0x02 && ++ /* input (usage page for x,y axes): constant, variable, relative */ ++ rdesc[54] == 0x81 && rdesc[55] == 0x07) { + hid_info(hdev, "Fixing up Sony RF Receiver report descriptor\n"); ++ /* input: data, variable, relative */ + rdesc[55] = 0x06; + } + diff --git a/queue-3.4/hid-fix-return-value-of-hidraw_report_event-when-config_hidraw.patch b/queue-3.4/hid-fix-return-value-of-hidraw_report_event-when-config_hidraw.patch new file mode 100644 index 00000000000..0628ec33f60 --- /dev/null +++ b/queue-3.4/hid-fix-return-value-of-hidraw_report_event-when-config_hidraw.patch @@ -0,0 +1,35 @@ +From 9c48cc08ae1255d4b244529408f52d26673e1ccb Mon Sep 17 00:00:00 2001 +From: Jiri Kosina +Date: Mon, 30 Apr 2012 10:39:17 +0200 +Subject: HID: fix return value of hidraw_report_event() when !CONFIG_HIDRAW + +From: Jiri Kosina + +commit d6d7c873529abd622897cad5e36f1fd7d82f5110 upstream. + +Commit b6787242f327 ("HID: hidraw: add proper error handling to raw event +reporting") forgot to update the static inline version of +hidraw_report_event() for the case when CONFIG_HIDRAW is unset. Fix that +up. + +Reported-by: Stephen Rothwell +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + include/linux/hidraw.h | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/include/linux/hidraw.h ++++ b/include/linux/hidraw.h +@@ -82,7 +82,7 @@ void hidraw_disconnect(struct hid_device + #else + static inline int hidraw_init(void) { return 0; } + static inline void hidraw_exit(void) { } +-static inline int hidraw_report_event(struct hid_device *hid, u8 *data, int len) { } ++static inline int hidraw_report_event(struct hid_device *hid, u8 *data, int len) { return 0; } + static inline int hidraw_connect(struct hid_device *hid) { return -1; } + static inline void hidraw_disconnect(struct hid_device *hid) { } + #endif diff --git a/queue-3.4/hid-hidraw-add-proper-error-handling-to-raw-event-reporting.patch b/queue-3.4/hid-hidraw-add-proper-error-handling-to-raw-event-reporting.patch new file mode 100644 index 00000000000..251ed6bbefb --- /dev/null +++ b/queue-3.4/hid-hidraw-add-proper-error-handling-to-raw-event-reporting.patch @@ -0,0 +1,159 @@ +From fb1c3652bb3e6690e50520c2d9a1493f15d93722 Mon Sep 17 00:00:00 2001 +From: Jiri Kosina +Date: Fri, 27 Apr 2012 00:56:08 +0200 +Subject: HID: hidraw: add proper error handling to raw event reporting + +From: Jiri Kosina + +commit b6787242f32700377d3da3b8d788ab3928bab849 upstream. + +If kmemdup() in hidraw_report_event() fails, we are not propagating +this fact properly. + +Let hidraw_report_event() and hid_report_raw_event() return an error +value to the caller. + +Reported-by: Oliver Neukum +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hid-core.c | 16 +++++++++++----- + drivers/hid/hidraw.c | 19 +++++++++++++------ + include/linux/hid.h | 2 +- + include/linux/hidraw.h | 4 ++-- + 4 files changed, 27 insertions(+), 14 deletions(-) + +--- a/drivers/hid/hid-core.c ++++ b/drivers/hid/hid-core.c +@@ -1100,7 +1100,7 @@ static struct hid_report *hid_get_report + return report; + } + +-void hid_report_raw_event(struct hid_device *hid, int type, u8 *data, int size, ++int hid_report_raw_event(struct hid_device *hid, int type, u8 *data, int size, + int interrupt) + { + struct hid_report_enum *report_enum = hid->report_enum + type; +@@ -1108,10 +1108,11 @@ void hid_report_raw_event(struct hid_dev + unsigned int a; + int rsize, csize = size; + u8 *cdata = data; ++ int ret = 0; + + report = hid_get_report(report_enum, data); + if (!report) +- return; ++ goto out; + + if (report_enum->numbered) { + cdata++; +@@ -1131,14 +1132,19 @@ void hid_report_raw_event(struct hid_dev + + if ((hid->claimed & HID_CLAIMED_HIDDEV) && hid->hiddev_report_event) + hid->hiddev_report_event(hid, report); +- if (hid->claimed & HID_CLAIMED_HIDRAW) +- hidraw_report_event(hid, data, size); ++ if (hid->claimed & HID_CLAIMED_HIDRAW) { ++ ret = hidraw_report_event(hid, data, size); ++ if (ret) ++ goto out; ++ } + + for (a = 0; a < report->maxfield; a++) + hid_input_field(hid, report->field[a], cdata, interrupt); + + if (hid->claimed & HID_CLAIMED_INPUT) + hidinput_report_event(hid, report); ++out: ++ return ret; + } + EXPORT_SYMBOL_GPL(hid_report_raw_event); + +@@ -1215,7 +1221,7 @@ nomem: + } + } + +- hid_report_raw_event(hid, type, data, size, interrupt); ++ ret = hid_report_raw_event(hid, type, data, size, interrupt); + + unlock: + up(&hid->driver_lock); +--- a/drivers/hid/hidraw.c ++++ b/drivers/hid/hidraw.c +@@ -87,11 +87,13 @@ static ssize_t hidraw_read(struct file * + len = list->buffer[list->tail].len > count ? + count : list->buffer[list->tail].len; + +- if (copy_to_user(buffer, list->buffer[list->tail].value, len)) { +- ret = -EFAULT; +- goto out; ++ if (list->buffer[list->tail].value) { ++ if (copy_to_user(buffer, list->buffer[list->tail].value, len)) { ++ ret = -EFAULT; ++ goto out; ++ } ++ ret = len; + } +- ret = len; + + kfree(list->buffer[list->tail].value); + list->tail = (list->tail + 1) & (HIDRAW_BUFFER_SIZE - 1); +@@ -437,19 +439,24 @@ static const struct file_operations hidr + .llseek = noop_llseek, + }; + +-void hidraw_report_event(struct hid_device *hid, u8 *data, int len) ++int hidraw_report_event(struct hid_device *hid, u8 *data, int len) + { + struct hidraw *dev = hid->hidraw; + struct hidraw_list *list; ++ int ret = 0; + + list_for_each_entry(list, &dev->list, node) { +- list->buffer[list->head].value = kmemdup(data, len, GFP_ATOMIC); ++ if (!(list->buffer[list->head].value = kmemdup(data, len, GFP_ATOMIC))) { ++ ret = -ENOMEM; ++ break; ++ } + list->buffer[list->head].len = len; + list->head = (list->head + 1) & (HIDRAW_BUFFER_SIZE - 1); + kill_fasync(&list->fasync, SIGIO, POLL_IN); + } + + wake_up_interruptible(&dev->wait); ++ return ret; + } + EXPORT_SYMBOL_GPL(hidraw_report_event); + +--- a/include/linux/hid.h ++++ b/include/linux/hid.h +@@ -902,7 +902,7 @@ static inline int hid_hw_power(struct hi + return hdev->ll_driver->power ? hdev->ll_driver->power(hdev, level) : 0; + } + +-void hid_report_raw_event(struct hid_device *hid, int type, u8 *data, int size, ++int hid_report_raw_event(struct hid_device *hid, int type, u8 *data, int size, + int interrupt); + + extern int hid_generic_init(void); +--- a/include/linux/hidraw.h ++++ b/include/linux/hidraw.h +@@ -76,13 +76,13 @@ struct hidraw_list { + #ifdef CONFIG_HIDRAW + int hidraw_init(void); + void hidraw_exit(void); +-void hidraw_report_event(struct hid_device *, u8 *, int); ++int hidraw_report_event(struct hid_device *, u8 *, int); + int hidraw_connect(struct hid_device *); + void hidraw_disconnect(struct hid_device *); + #else + static inline int hidraw_init(void) { return 0; } + static inline void hidraw_exit(void) { } +-static inline void hidraw_report_event(struct hid_device *hid, u8 *data, int len) { } ++static inline int hidraw_report_event(struct hid_device *hid, u8 *data, int len) { } + static inline int hidraw_connect(struct hid_device *hid) { return -1; } + static inline void hidraw_disconnect(struct hid_device *hid) { } + #endif diff --git a/queue-3.4/hid-hidraw-correctly-deallocate-memory-on-device-disconnect.patch b/queue-3.4/hid-hidraw-correctly-deallocate-memory-on-device-disconnect.patch new file mode 100644 index 00000000000..e26ebf1ce65 --- /dev/null +++ b/queue-3.4/hid-hidraw-correctly-deallocate-memory-on-device-disconnect.patch @@ -0,0 +1,136 @@ +From 384a27453c74b2fc27063dd287acf72550a1ad0f Mon Sep 17 00:00:00 2001 +From: Manoj Chourasia +Date: Mon, 22 Jul 2013 15:33:13 +0530 +Subject: HID: hidraw: correctly deallocate memory on device disconnect + +From: Manoj Chourasia + +commit 212a871a3934beccf43431608c27ed2e05a476ec upstream. + +This changes puts the commit 4fe9f8e203f back in place +with the fixes for slab corruption because of the commit. + +When a device is unplugged, wait for all processes that +have opened the device to close before deallocating the device. + +This commit was solving kernel crash because of the corruption in +rb tree of vmalloc. The rootcause was the device data pointer was +geting excessed after the memory associated with hidraw was freed. + +The commit 4fe9f8e203f was buggy as it was also freeing the hidraw +first and then calling delete operation on the list associated with +that hidraw leading to slab corruption. + +Signed-off-by: Manoj Chourasia +Tested-by: Peter Wu +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hidraw.c | 60 +++++++++++++++++++++------------------------------ + 1 file changed, 25 insertions(+), 35 deletions(-) + +--- a/drivers/hid/hidraw.c ++++ b/drivers/hid/hidraw.c +@@ -113,7 +113,7 @@ static ssize_t hidraw_send_report(struct + __u8 *buf; + int ret = 0; + +- if (!hidraw_table[minor]) { ++ if (!hidraw_table[minor] || !hidraw_table[minor]->exist) { + ret = -ENODEV; + goto out; + } +@@ -261,7 +261,7 @@ static int hidraw_open(struct inode *ino + } + + mutex_lock(&minors_lock); +- if (!hidraw_table[minor]) { ++ if (!hidraw_table[minor] || !hidraw_table[minor]->exist) { + err = -ENODEV; + goto out_unlock; + } +@@ -295,39 +295,38 @@ out: + + } + ++static void drop_ref(struct hidraw *hidraw, int exists_bit) ++{ ++ if (exists_bit) { ++ hid_hw_close(hidraw->hid); ++ hidraw->exist = 0; ++ if (hidraw->open) ++ wake_up_interruptible(&hidraw->wait); ++ } else { ++ --hidraw->open; ++ } ++ ++ if (!hidraw->open && !hidraw->exist) { ++ device_destroy(hidraw_class, MKDEV(hidraw_major, hidraw->minor)); ++ hidraw_table[hidraw->minor] = NULL; ++ kfree(hidraw); ++ } ++} ++ + static int hidraw_release(struct inode * inode, struct file * file) + { + unsigned int minor = iminor(inode); +- struct hidraw *dev; + struct hidraw_list *list = file->private_data; +- int ret; +- int i; + + mutex_lock(&minors_lock); +- if (!hidraw_table[minor]) { +- ret = -ENODEV; +- goto unlock; +- } + + list_del(&list->node); +- dev = hidraw_table[minor]; +- if (!--dev->open) { +- if (list->hidraw->exist) { +- hid_hw_power(dev->hid, PM_HINT_NORMAL); +- hid_hw_close(dev->hid); +- } else { +- kfree(list->hidraw); +- } +- } +- +- for (i = 0; i < HIDRAW_BUFFER_SIZE; ++i) +- kfree(list->buffer[i].value); + kfree(list); +- ret = 0; +-unlock: +- mutex_unlock(&minors_lock); + +- return ret; ++ drop_ref(hidraw_table[minor], 0); ++ ++ mutex_unlock(&minors_lock); ++ return 0; + } + + static long hidraw_ioctl(struct file *file, unsigned int cmd, +@@ -531,18 +530,9 @@ void hidraw_disconnect(struct hid_device + struct hidraw *hidraw = hid->hidraw; + + mutex_lock(&minors_lock); +- hidraw->exist = 0; +- +- device_destroy(hidraw_class, MKDEV(hidraw_major, hidraw->minor)); + +- hidraw_table[hidraw->minor] = NULL; ++ drop_ref(hidraw, 1); + +- if (hidraw->open) { +- hid_hw_close(hid); +- wake_up_interruptible(&hidraw->wait); +- } else { +- kfree(hidraw); +- } + mutex_unlock(&minors_lock); + } + EXPORT_SYMBOL_GPL(hidraw_disconnect); diff --git a/queue-3.4/hid-hidraw-fix-list-buffer-memleak.patch b/queue-3.4/hid-hidraw-fix-list-buffer-memleak.patch new file mode 100644 index 00000000000..54566d64124 --- /dev/null +++ b/queue-3.4/hid-hidraw-fix-list-buffer-memleak.patch @@ -0,0 +1,71 @@ +From 3313aa9015c7c868a9bcdb7b1c143719d2873a66 Mon Sep 17 00:00:00 2001 +From: Matthieu CASTET +Date: Thu, 28 Jun 2012 16:51:56 +0200 +Subject: HID: hidraw: fix list->buffer memleak + +From: Matthieu CASTET + +commit 4c7b417ecb756e85dfc955b0e7a04fd45585533e upstream. + +If we don't read fast enough hidraw device, hidraw_report_event +will cycle and we will leak list->buffer. +Also list->buffer are not free on release. +After this patch, kmemleak report nothing. + +Signed-off-by: Matthieu CASTET +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hidraw.c | 12 +++++++++++- + 1 file changed, 11 insertions(+), 1 deletion(-) + +--- a/drivers/hid/hidraw.c ++++ b/drivers/hid/hidraw.c +@@ -96,6 +96,7 @@ static ssize_t hidraw_read(struct file * + } + + kfree(list->buffer[list->tail].value); ++ list->buffer[list->tail].value = NULL; + list->tail = (list->tail + 1) & (HIDRAW_BUFFER_SIZE - 1); + } + out: +@@ -300,6 +301,7 @@ static int hidraw_release(struct inode * + struct hidraw *dev; + struct hidraw_list *list = file->private_data; + int ret; ++ int i; + + mutex_lock(&minors_lock); + if (!hidraw_table[minor]) { +@@ -317,6 +319,9 @@ static int hidraw_release(struct inode * + kfree(list->hidraw); + } + } ++ ++ for (i = 0; i < HIDRAW_BUFFER_SIZE; ++i) ++ kfree(list->buffer[i].value); + kfree(list); + ret = 0; + unlock: +@@ -446,12 +451,17 @@ int hidraw_report_event(struct hid_devic + int ret = 0; + + list_for_each_entry(list, &dev->list, node) { ++ int new_head = (list->head + 1) & (HIDRAW_BUFFER_SIZE - 1); ++ ++ if (new_head == list->tail) ++ continue; ++ + if (!(list->buffer[list->head].value = kmemdup(data, len, GFP_ATOMIC))) { + ret = -ENOMEM; + break; + } + list->buffer[list->head].len = len; +- list->head = (list->head + 1) & (HIDRAW_BUFFER_SIZE - 1); ++ list->head = new_head; + kill_fasync(&list->fasync, SIGIO, POLL_IN); + } + diff --git a/queue-3.4/hid-hidraw-improve-error-handling-in-hidraw_init.patch b/queue-3.4/hid-hidraw-improve-error-handling-in-hidraw_init.patch new file mode 100644 index 00000000000..bd5e141efb1 --- /dev/null +++ b/queue-3.4/hid-hidraw-improve-error-handling-in-hidraw_init.patch @@ -0,0 +1,62 @@ +From 3084fc2f2e8cf84b1d0a66323c26943d5ca98860 Mon Sep 17 00:00:00 2001 +From: Alexey Khoroshilov +Date: Wed, 15 Aug 2012 23:31:45 +0400 +Subject: HID: hidraw: improve error handling in hidraw_init() + +From: Alexey Khoroshilov + +commit bcb4a75bde3821cecb17a71d287abfd6ef9bd68d upstream. + +Several improvements in error handling: +- do not report success if alloc_chrdev_region() failed +- check for error code of cdev_add() +- use unregister_chrdev_region() instead of unregister_chrdev() + if class_create() failed + +Found by Linux Driver Verification project (linuxtesting.org). + +Signed-off-by: Alexey Khoroshilov +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hidraw.c | 15 +++++++++++---- + 1 file changed, 11 insertions(+), 4 deletions(-) + +--- a/drivers/hid/hidraw.c ++++ b/drivers/hid/hidraw.c +@@ -559,21 +559,28 @@ int __init hidraw_init(void) + + if (result < 0) { + pr_warn("can't get major number\n"); +- result = 0; + goto out; + } + + hidraw_class = class_create(THIS_MODULE, "hidraw"); + if (IS_ERR(hidraw_class)) { + result = PTR_ERR(hidraw_class); +- unregister_chrdev(hidraw_major, "hidraw"); +- goto out; ++ goto error_cdev; + } + + cdev_init(&hidraw_cdev, &hidraw_ops); +- cdev_add(&hidraw_cdev, dev_id, HIDRAW_MAX_DEVICES); ++ result = cdev_add(&hidraw_cdev, dev_id, HIDRAW_MAX_DEVICES); ++ if (result < 0) ++ goto error_class; ++ + out: + return result; ++ ++error_class: ++ class_destroy(hidraw_class); ++error_cdev: ++ unregister_chrdev_region(dev_id, HIDRAW_MAX_DEVICES); ++ goto out; + } + + void hidraw_exit(void) diff --git a/queue-3.4/hid-multitouch-validate-indexes-details.patch b/queue-3.4/hid-multitouch-validate-indexes-details.patch new file mode 100644 index 00000000000..3e42c275325 --- /dev/null +++ b/queue-3.4/hid-multitouch-validate-indexes-details.patch @@ -0,0 +1,52 @@ +From 8821f5dc187bdf16cfb32ef5aa8c3035273fa79a Mon Sep 17 00:00:00 2001 +From: Benjamin Tissoires +Date: Wed, 11 Sep 2013 21:56:58 +0200 +Subject: HID: multitouch: validate indexes details + +From: Benjamin Tissoires + +commit 8821f5dc187bdf16cfb32ef5aa8c3035273fa79a upstream. + +When working on report indexes, always validate that they are in bounds. +Without this, a HID device could report a malicious feature report that +could trick the driver into a heap overflow: + +[ 634.885003] usb 1-1: New USB device found, idVendor=0596, idProduct=0500 +... +[ 676.469629] BUG kmalloc-192 (Tainted: G W ): Redzone overwritten + +Note that we need to change the indexes from s8 to s16 as they can +be between -1 and 255. + +CVE-2013-2897 + +Cc: stable@vger.kernel.org +Signed-off-by: Benjamin Tissoires +Acked-by: Kees Cook +Signed-off-by: Jiri Kosina +[bwh: Backported to 3.2: mt_device::{cc,cc_value,inputmode}_index do not + exist and the corresponding indices do not need to be validated. + mt_device::maxcontact_report_id does not exist either. So all we need + to do is to widen mt_device::inputmode.] +Signed-off-by: Ben Hutchings +[yjw: Backport to 3.4: maxcontact_report_id exists, + need to be validated] +Signed-off-by: Yijing Wang +Signed-off-by: Greg Kroah-Hartman +--- + drivers/hid/hid-multitouch.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +--- a/drivers/hid/hid-multitouch.c ++++ b/drivers/hid/hid-multitouch.c +@@ -82,8 +82,8 @@ struct mt_device { + multitouch fields */ + unsigned last_field_index; /* last field index of the report */ + unsigned last_slot_field; /* the last field of a slot */ +- __s8 inputmode; /* InputMode HID feature, -1 if non-existent */ +- __s8 maxcontact_report_id; /* Maximum Contact Number HID feature, ++ __s16 inputmode; /* InputMode HID feature, -1 if non-existent */ ++ __s16 maxcontact_report_id; /* Maximum Contact Number HID feature, + -1 if non-existent */ + __u8 num_received; /* how many contacts we received */ + __u8 num_expected; /* expected last contact index */ diff --git a/queue-3.4/hid-usbhid-fix-build-problem.patch b/queue-3.4/hid-usbhid-fix-build-problem.patch new file mode 100644 index 00000000000..d561c822089 --- /dev/null +++ b/queue-3.4/hid-usbhid-fix-build-problem.patch @@ -0,0 +1,34 @@ +From 1f276d988f8e6d1e6eb0837950a1e49a1c3b4bb8 Mon Sep 17 00:00:00 2001 +From: Jiri Kosina +Date: Mon, 18 Mar 2013 15:50:10 +0100 +Subject: HID: usbhid: fix build problem + +From: Jiri Kosina + +commit 570637dc8eeb2faba06228d497ff40bb019bcc93 upstream. + +Fix build problem caused by typo introduced by 620ae90ed8 +("HID: usbhid: quirk for MSI GX680R led panel"). + +Reported-by: fengguang.wu@intel.com +Signed-off-by: Jiri Kosina +[bwh: Backported to 3.2: adjust context] +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/usbhid/hid-quirks.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/hid/usbhid/hid-quirks.c ++++ b/drivers/hid/usbhid/hid-quirks.c +@@ -73,7 +73,7 @@ static const struct hid_blacklist { + { USB_VENDOR_ID_FORMOSA, USB_DEVICE_ID_FORMOSA_IR_RECEIVER, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_FREESCALE, USB_DEVICE_ID_FREESCALE_MX28, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_MGE, USB_DEVICE_ID_MGE_UPS, HID_QUIRK_NOGET }, +- { USB_VENDIR_ID_MSI, USB_DEVICE_ID_MSI_GX680R_LED_PANEL, HID_QUIRK_NO_INIT_REPORTS }, ++ { USB_VENDOR_ID_MSI, USB_DEVICE_ID_MSI_GX680R_LED_PANEL, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN1, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN2, HID_QUIRK_NO_INIT_REPORTS }, diff --git a/queue-3.4/hid-usbhid-quirk-for-formosa-ir-receiver.patch b/queue-3.4/hid-usbhid-quirk-for-formosa-ir-receiver.patch new file mode 100644 index 00000000000..d4cbcad0c5d --- /dev/null +++ b/queue-3.4/hid-usbhid-quirk-for-formosa-ir-receiver.patch @@ -0,0 +1,52 @@ +From 320cde19a4e8f122b19d2df7a5c00636e11ca3fb Mon Sep 17 00:00:00 2001 +From: Nicholas Santos +Date: Fri, 28 Dec 2012 22:07:02 -0500 +Subject: HID: usbhid: quirk for Formosa IR receiver + +From: Nicholas Santos + +commit 320cde19a4e8f122b19d2df7a5c00636e11ca3fb upstream. + +Patch to add the Formosa Industrial Computing, Inc. Infrared Receiver +[IR605A/Q] to hid-ids.h and hid-quirks.c. This IR receiver causes about a 10 +second timeout when the usbhid driver attempts to initialze the device. Adding +this device to the quirks list with HID_QUIRK_NO_INIT_REPORTS removes the +delay. + +Signed-off-by: Nicholas Santos +[jkosina@suse.cz: fix ordering] +Signed-off-by: Jiri Kosina +Signed-off-by: Nicholas Santos +[jkosina@suse.cz: fix ordering] +Signed-off-by: Jiri Kosina +Signed-off-by: Ben Hutchings +[yjw: Backported to 3.4: adjust context] +Signed-off-by: Yijing Wang +Signed-off-by: Greg Kroah-Hartman +--- + drivers/hid/hid-ids.h | 3 +++ + drivers/hid/usbhid/hid-quirks.c | 1 + + 2 files changed, 4 insertions(+) + +--- a/drivers/hid/hid-ids.h ++++ b/drivers/hid/hid-ids.h +@@ -293,6 +293,9 @@ + #define USB_VENDOR_ID_FRUCTEL 0x25B6 + #define USB_DEVICE_ID_GAMETEL_MT_MODE 0x0002 + ++#define USB_VENDOR_ID_FORMOSA 0x147a ++#define USB_DEVICE_ID_FORMOSA_IR_RECEIVER 0xe03e ++ + #define USB_VENDOR_ID_FREESCALE 0x15A2 + #define USB_DEVICE_ID_FREESCALE_MX28 0x004F + +--- a/drivers/hid/usbhid/hid-quirks.c ++++ b/drivers/hid/usbhid/hid-quirks.c +@@ -70,6 +70,7 @@ static const struct hid_blacklist { + { USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_AXIS_295, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_DMI, USB_DEVICE_ID_DMI_ENC, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_ELO, USB_DEVICE_ID_ELO_TS2700, HID_QUIRK_NOGET }, ++ { USB_VENDOR_ID_FORMOSA, USB_DEVICE_ID_FORMOSA_IR_RECEIVER, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_FREESCALE, USB_DEVICE_ID_FREESCALE_MX28, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_MGE, USB_DEVICE_ID_MGE_UPS, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN, HID_QUIRK_NO_INIT_REPORTS }, diff --git a/queue-3.4/hid-usbhid-quirk-for-msi-gx680r-led-panel.patch b/queue-3.4/hid-usbhid-quirk-for-msi-gx680r-led-panel.patch new file mode 100644 index 00000000000..4c283231ea7 --- /dev/null +++ b/queue-3.4/hid-usbhid-quirk-for-msi-gx680r-led-panel.patch @@ -0,0 +1,48 @@ +From 606eea676790b1dda873d58374ced37177f31a0d Mon Sep 17 00:00:00 2001 +From: Josh Boyer +Date: Mon, 18 Mar 2013 09:47:02 -0400 +Subject: HID: usbhid: quirk for MSI GX680R led panel + +From: Josh Boyer + +commit 620ae90ed8ca8b6e40cb9e10279b4f5ef9f0ab81 upstream. + +This keyboard backlight device causes a 10 second delay to boot. Add it +to the quirk list with HID_QUIRK_NO_INIT_REPORTS. + +This fixes Red Hat bugzilla https://bugzilla.redhat.com/show_bug.cgi?id=907221 + +Signed-off-by: Josh Boyer +Signed-off-by: Jiri Kosina +[bwh: Backported to 3.2: adjust context] +Signed-off-by: Ben Hutchings +Cc: Yijing Wang +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/hid/hid-ids.h | 3 +++ + drivers/hid/usbhid/hid-quirks.c | 1 + + 2 files changed, 4 insertions(+) + +--- a/drivers/hid/hid-ids.h ++++ b/drivers/hid/hid-ids.h +@@ -559,6 +559,9 @@ + #define USB_VENDOR_ID_MONTEREY 0x0566 + #define USB_DEVICE_ID_GENIUS_KB29E 0x3004 + ++#define USB_VENDOR_ID_MSI 0x1770 ++#define USB_DEVICE_ID_MSI_GX680R_LED_PANEL 0xff00 ++ + #define USB_VENDOR_ID_NATIONAL_SEMICONDUCTOR 0x0400 + #define USB_DEVICE_ID_N_S_HARMONY 0xc359 + +--- a/drivers/hid/usbhid/hid-quirks.c ++++ b/drivers/hid/usbhid/hid-quirks.c +@@ -73,6 +73,7 @@ static const struct hid_blacklist { + { USB_VENDOR_ID_FORMOSA, USB_DEVICE_ID_FORMOSA_IR_RECEIVER, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_FREESCALE, USB_DEVICE_ID_FREESCALE_MX28, HID_QUIRK_NOGET }, + { USB_VENDOR_ID_MGE, USB_DEVICE_ID_MGE_UPS, HID_QUIRK_NOGET }, ++ { USB_VENDIR_ID_MSI, USB_DEVICE_ID_MSI_GX680R_LED_PANEL, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN1, HID_QUIRK_NO_INIT_REPORTS }, + { USB_VENDOR_ID_PIXART, USB_DEVICE_ID_PIXART_OPTICAL_TOUCH_SCREEN2, HID_QUIRK_NO_INIT_REPORTS }, diff --git a/queue-3.4/hid-validate-feature-and-input-report-details.patch b/queue-3.4/hid-validate-feature-and-input-report-details.patch new file mode 100644 index 00000000000..fddd69e6b87 --- /dev/null +++ b/queue-3.4/hid-validate-feature-and-input-report-details.patch @@ -0,0 +1,108 @@ +From cc6b54aa54bf40b762cab45a9fc8aa81653146eb Mon Sep 17 00:00:00 2001 +From: Benjamin Tissoires +Date: Wed, 11 Sep 2013 21:56:57 +0200 +Subject: HID: validate feature and input report details + +From: Benjamin Tissoires + +commit cc6b54aa54bf40b762cab45a9fc8aa81653146eb upstream. + +When dealing with usage_index, be sure to properly use unsigned instead of +int to avoid overflows. + +When working on report fields, always validate that their report_counts are +in bounds. +Without this, a HID device could report a malicious feature report that +could trick the driver into a heap overflow: + +[ 634.885003] usb 1-1: New USB device found, idVendor=0596, idProduct=0500 +... +[ 676.469629] BUG kmalloc-192 (Tainted: G W ): Redzone overwritten + +CVE-2013-2897 + +Cc: stable@vger.kernel.org +Signed-off-by: Benjamin Tissoires +Acked-by: Kees Cook +Signed-off-by: Jiri Kosina +[bwh: Backported to 3.2: + - Drop inapplicable changes to hid_usage::usage_index initialisation and + to hid_report_raw_event() + - Adjust context in report_features() +Signed-off-by: Ben Hutchings +[yijingwang: Backported to 3.4: context adjust] +Signed-off-by: Yijing Wang +Signed-off-by: Greg Kroah-Hartman +--- + drivers/hid/hid-core.c | 9 +++++---- + drivers/hid/hid-input.c | 12 +++++++++++- + 2 files changed, 16 insertions(+), 5 deletions(-) + +--- a/drivers/hid/hid-core.c ++++ b/drivers/hid/hid-core.c +@@ -222,9 +222,9 @@ static int hid_add_field(struct hid_pars + { + struct hid_report *report; + struct hid_field *field; +- int usages; ++ unsigned usages; + unsigned offset; +- int i; ++ unsigned i; + + report = hid_register_report(parser->device, report_type, parser->global.report_id); + if (!report) { +@@ -244,7 +244,8 @@ static int hid_add_field(struct hid_pars + if (!parser->local.usage_index) /* Ignore padding fields */ + return 0; + +- usages = max_t(int, parser->local.usage_index, parser->global.report_count); ++ usages = max_t(unsigned, parser->local.usage_index, ++ parser->global.report_count); + + field = hid_register_field(report, usages, parser->global.report_count); + if (!field) +@@ -255,7 +256,7 @@ static int hid_add_field(struct hid_pars + field->application = hid_lookup_collection(parser, HID_COLLECTION_APPLICATION); + + for (i = 0; i < usages; i++) { +- int j = i; ++ unsigned j = i; + /* Duplicate the last usage we parsed if we have excess values */ + if (i >= parser->local.usage_index) + j = parser->local.usage_index - 1; +--- a/drivers/hid/hid-input.c ++++ b/drivers/hid/hid-input.c +@@ -459,6 +459,10 @@ static void hidinput_configure_usage(str + if (field->flags & HID_MAIN_ITEM_CONSTANT) + goto ignore; + ++ /* Ignore if report count is out of bounds. */ ++ if (field->report_count < 1) ++ goto ignore; ++ + /* only LED usages are supported in output fields */ + if (field->report_type == HID_OUTPUT_REPORT && + (usage->hid & HID_USAGE_PAGE) != HID_UP_LED) { +@@ -1119,7 +1123,12 @@ static void report_features(struct hid_d + + rep_enum = &hid->report_enum[HID_FEATURE_REPORT]; + list_for_each_entry(rep, &rep_enum->report_list, list) +- for (i = 0; i < rep->maxfield; i++) ++ for (i = 0; i < rep->maxfield; i++) { ++ ++ /* Ignore if report count is out of bounds. */ ++ if (rep->field[i]->report_count < 1) ++ continue; ++ + for (j = 0; j < rep->field[i]->maxusage; j++) { + /* Verify if Battery Strength feature is available */ + hidinput_setup_battery(hid, HID_FEATURE_REPORT, rep->field[i]); +@@ -1128,6 +1137,7 @@ static void report_features(struct hid_d + drv->feature_mapping(hid, rep->field[i], + rep->field[i]->usage + j); + } ++ } + } + + /* diff --git a/queue-3.4/intel_idle-check-cpu_idle_get_driver-for-null-before-dereferencing-it.patch b/queue-3.4/intel_idle-check-cpu_idle_get_driver-for-null-before-dereferencing-it.patch new file mode 100644 index 00000000000..fa0fd68f312 --- /dev/null +++ b/queue-3.4/intel_idle-check-cpu_idle_get_driver-for-null-before-dereferencing-it.patch @@ -0,0 +1,38 @@ +From 3735d524da64b70b41c764359da36f88aded3610 Mon Sep 17 00:00:00 2001 +From: Konrad Rzeszutek Wilk +Date: Thu, 16 Aug 2012 22:06:55 +0200 +Subject: intel_idle: Check cpu_idle_get_driver() for NULL before dereferencing it. + +From: Konrad Rzeszutek Wilk + +commit 3735d524da64b70b41c764359da36f88aded3610 upstream. + +If the machine is booted without any cpu_idle driver set +(b/c disable_cpuidle() has been called) we should follow +other users of cpu_idle API and check the return value +for NULL before using it. + +Reported-and-tested-by: Mark van Dijk +Suggested-by: Jan Beulich +Signed-off-by: Konrad Rzeszutek Wilk +Signed-off-by: Rafael J. Wysocki +Cc: Daniel Kiper +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/idle/intel_idle.c | 3 ++- + 1 file changed, 2 insertions(+), 1 deletion(-) + +--- a/drivers/idle/intel_idle.c ++++ b/drivers/idle/intel_idle.c +@@ -594,8 +594,9 @@ static int __init intel_idle_init(void) + intel_idle_cpuidle_driver_init(); + retval = cpuidle_register_driver(&intel_idle_driver); + if (retval) { ++ struct cpuidle_driver *drv = cpuidle_get_driver(); + printk(KERN_DEBUG PREFIX "intel_idle yielding to %s", +- cpuidle_get_driver()->name); ++ drv ? drv->name : "none"); + return retval; + } + diff --git a/queue-3.4/series b/queue-3.4/series index 421a2fa11de..b040002c80d 100644 --- a/queue-3.4/series +++ b/queue-3.4/series @@ -11,3 +11,18 @@ pps-add-pps_lookup_dev-function.patch pps-use-pps_lookup_dev-to-reduce-ldisc-coupling.patch pps-fix-a-use-after-free-bug-when-unregistering-a-source.patch selinux-correctly-label-proc-inodes-in-use-before-the-policy-is-loaded.patch +intel_idle-check-cpu_idle_get_driver-for-null-before-dereferencing-it.patch +hid-add-quirk-for-freescale-i.mx28-rom-recovery.patch +hid-usbhid-quirk-for-formosa-ir-receiver.patch +hid-validate-feature-and-input-report-details.patch +hid-multitouch-validate-indexes-details.patch +hid-hidraw-add-proper-error-handling-to-raw-event-reporting.patch +hid-fix-return-value-of-hidraw_report_event-when-config_hidraw.patch +hid-hidraw-fix-list-buffer-memleak.patch +hid-hidraw-improve-error-handling-in-hidraw_init.patch +hid-apple-add-apple-wireless-keyboard-2011-ansi-pid.patch +hid-add-support-for-sony-rf-receiver-with-usb-product-id-0x0374.patch +hid-clean-up-quirk-for-sony-rf-receivers.patch +hid-usbhid-quirk-for-msi-gx680r-led-panel.patch +hid-usbhid-fix-build-problem.patch +hid-hidraw-correctly-deallocate-memory-on-device-disconnect.patch