|
@@ -4,7 +4,7 @@
|
|
|
* Copyright (c) 1999 Andreas Gal
|
|
|
* Copyright (c) 2000-2005 Vojtech Pavlik <vojtech@suse.cz>
|
|
|
* Copyright (c) 2005 Michael Haboustak <mike-@cinci.rr.com> for Concept2, Inc
|
|
|
- * Copyright (c) 2006 Jiri Kosina
|
|
|
+ * Copyright (c) 2006-2007 Jiri Kosina
|
|
|
*/
|
|
|
|
|
|
/*
|
|
@@ -27,9 +27,6 @@
|
|
|
#include <linux/input.h>
|
|
|
#include <linux/wait.h>
|
|
|
|
|
|
-#undef DEBUG
|
|
|
-#undef DEBUG_DATA
|
|
|
-
|
|
|
#include <linux/usb.h>
|
|
|
|
|
|
#include <linux/hid.h>
|
|
@@ -758,6 +755,8 @@ void usbhid_init_reports(struct hid_device *hid)
|
|
|
|
|
|
#define USB_VENDOR_ID_LOGITECH 0x046d
|
|
|
#define USB_DEVICE_ID_LOGITECH_USB_RECEIVER 0xc101
|
|
|
+#define USB_DEVICE_ID_LOGITECH_USB_RECEIVER_2 0xc517
|
|
|
+#define USB_DEVICE_ID_DINOVO_EDGE 0xc714
|
|
|
|
|
|
#define USB_VENDOR_ID_IMATION 0x0718
|
|
|
#define USB_DEVICE_ID_DISC_STAKKA 0xd000
|
|
@@ -778,6 +777,8 @@ static const struct hid_blacklist {
|
|
|
unsigned quirks;
|
|
|
} hid_blacklist[] = {
|
|
|
|
|
|
+ { USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_DINOVO_EDGE, HID_QUIRK_DUPLICATE_USAGES },
|
|
|
+
|
|
|
{ USB_VENDOR_ID_AIPTEK, USB_DEVICE_ID_AIPTEK_01, HID_QUIRK_IGNORE },
|
|
|
{ USB_VENDOR_ID_AIPTEK, USB_DEVICE_ID_AIPTEK_10, HID_QUIRK_IGNORE },
|
|
|
{ USB_VENDOR_ID_AIPTEK, USB_DEVICE_ID_AIPTEK_20, HID_QUIRK_IGNORE },
|
|
@@ -944,6 +945,7 @@ static const struct hid_blacklist {
|
|
|
{ USB_VENDOR_ID_TURBOX, USB_DEVICE_ID_TURBOX_KEYBOARD, HID_QUIRK_NOGET },
|
|
|
|
|
|
{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_USB_RECEIVER, HID_QUIRK_BAD_RELATIVE_KEYS },
|
|
|
+ { USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_USB_RECEIVER_2, HID_QUIRK_LOGITECH_S510_DESCRIPTOR },
|
|
|
|
|
|
{ USB_VENDOR_ID_PANTHERLORD, USB_DEVICE_ID_PANTHERLORD_TWIN_USB_JOYSTICK, HID_QUIRK_MULTI_INPUT | HID_QUIRK_SKIP_OUTPUT_REPORTS },
|
|
|
|
|
@@ -1041,6 +1043,22 @@ static void hid_fixup_sony_ps3_controller(struct usb_device *dev, int ifnum)
|
|
|
kfree(buf);
|
|
|
}
|
|
|
|
|
|
+/*
|
|
|
+ * Logitech S510 keyboard sends in report #3 keys which are far
|
|
|
+ * above the logical maximum described in descriptor. This extends
|
|
|
+ * the original value of 0x28c of logical maximum to 0x104d
|
|
|
+ */
|
|
|
+static void hid_fixup_s510_descriptor(unsigned char *rdesc, int rsize)
|
|
|
+{
|
|
|
+ if (rsize >= 90 && rdesc[83] == 0x26
|
|
|
+ && rdesc[84] == 0x8c
|
|
|
+ && rdesc[85] == 0x02) {
|
|
|
+ info("Fixing up Logitech S510 report descriptor");
|
|
|
+ rdesc[84] = rdesc[89] = 0x4d;
|
|
|
+ rdesc[85] = rdesc[90] = 0x10;
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
static struct hid_device *usb_hid_configure(struct usb_interface *intf)
|
|
|
{
|
|
|
struct usb_host_interface *interface = intf->cur_altsetting;
|
|
@@ -1109,7 +1127,10 @@ static struct hid_device *usb_hid_configure(struct usb_interface *intf)
|
|
|
if ((quirks & HID_QUIRK_CYMOTION))
|
|
|
hid_fixup_cymotion_descriptor(rdesc, rsize);
|
|
|
|
|
|
-#ifdef DEBUG_DATA
|
|
|
+ if (quirks & HID_QUIRK_LOGITECH_S510_DESCRIPTOR)
|
|
|
+ hid_fixup_s510_descriptor(rdesc, rsize);
|
|
|
+
|
|
|
+#ifdef CONFIG_HID_DEBUG
|
|
|
printk(KERN_DEBUG __FILE__ ": report descriptor (size %u, read %d) = ", rsize, n);
|
|
|
for (n = 0; n < rsize; n++)
|
|
|
printk(" %02x", (unsigned char) rdesc[n]);
|
|
@@ -1225,8 +1246,8 @@ static struct hid_device *usb_hid_configure(struct usb_interface *intf)
|
|
|
le16_to_cpu(dev->descriptor.idProduct));
|
|
|
|
|
|
hid->bus = BUS_USB;
|
|
|
- hid->vendor = dev->descriptor.idVendor;
|
|
|
- hid->product = dev->descriptor.idProduct;
|
|
|
+ hid->vendor = le16_to_cpu(dev->descriptor.idVendor);
|
|
|
+ hid->product = le16_to_cpu(dev->descriptor.idProduct);
|
|
|
|
|
|
usb_make_path(dev, hid->phys, sizeof(hid->phys));
|
|
|
strlcat(hid->phys, "/input", sizeof(hid->phys));
|