Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 876a4256 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jikos/hid:
  HID: apple_fn_keys F5 and F6
  HID: remove quirk lookup from usbkbd/usbmouse
  HID: Add mapping of new KEY_MEDIA_REPEAT keycode
  HID: gyration remote support
  HID: gyration sleep button quirk
  HID: add quirk for Logitech DiNovo desktop
  HID: fix quirk handling in usbmouse/kbd
  HID: fix memory leak in hidraw_release
  HID: add n-trig digitizer usage
  HID: Invert HWHEEL mappings for some Logitech mice
  HID:usbkbd:mark usb_kbd_keycode array as const
  HID: add fn key support on Macbook Pro 4,1 and Macbook Air
  HID: remove unused variable from hiddev compat ioctl
  HID: fix compile issue in hiddev ioctl
  HID: Push down BKL into ioctl handler in hidraw
  HID: Switch hiddev to unlocked_ioctl
  HID: use get/put_unaligned_* helpers
  HID: fix report descriptor handling for MS Wireless model 1028
parents 7c1fed03 b22d8370
Loading
Loading
Loading
Loading
+5 −5
Original line number Diff line number Diff line
@@ -780,7 +780,7 @@ static __inline__ __u32 extract(__u8 *report, unsigned offset, unsigned n)
 */
static __inline__ void implement(__u8 *report, unsigned offset, unsigned n, __u32 value)
{
	__le64 x;
	u64 x;
	u64 m = (1ULL << n) - 1;

	if (n > 32)
@@ -796,10 +796,10 @@ static __inline__ void implement(__u8 *report, unsigned offset, unsigned n, __u3
	report += offset >> 3;
	offset &= 7;

	x = get_unaligned((__le64 *)report);
	x &= cpu_to_le64(~(m << offset));
	x |= cpu_to_le64(((u64) value) << offset);
	put_unaligned(x, (__le64 *) report);
	x = get_unaligned_le64(report);
	x &= ~(m << offset);
	x |= ((u64)value) << offset;
	put_unaligned_le64(x, report);
}

/*
+40 −0
Original line number Diff line number Diff line
@@ -89,6 +89,29 @@ static int quirk_logitech_ultrax_remote(struct hid_usage *usage, struct input_de
	return 1;
}

static int quirk_gyration_remote(struct hid_usage *usage, struct input_dev *input,
			      unsigned long **bit, int *max)
{
	if ((usage->hid & HID_USAGE_PAGE) != HID_UP_LOGIVENDOR)
		return 0;

	set_bit(EV_REP, input->evbit);
	switch(usage->hid & HID_USAGE) {
		/* Reported on Gyration MCE Remote */
		case 0x00d: map_key_clear(KEY_HOME);		break;
		case 0x024: map_key_clear(KEY_DVD);		break;
		case 0x025: map_key_clear(KEY_PVR);		break;
		case 0x046: map_key_clear(KEY_MEDIA);		break;
		case 0x047: map_key_clear(KEY_MP3);		break;
		case 0x049: map_key_clear(KEY_CAMERA);		break;
		case 0x04a: map_key_clear(KEY_VIDEO);		break;

		default:
			return 0;
	}
	return 1;
}

static int quirk_chicony_tactical_pad(struct hid_usage *usage, struct input_dev *input,
			      unsigned long **bit, int *max)
{
@@ -303,6 +326,9 @@ static int quirk_sunplus_wdesktop(struct hid_usage *usage, struct input_dev *inp
#define VENDOR_ID_EZKEY				0x0518
#define DEVICE_ID_BTC_8193			0x0002

#define VENDOR_ID_GYRATION			0x0c16
#define DEVICE_ID_GYRATION_REMOTE		0x0002

#define VENDOR_ID_LOGITECH			0x046d
#define DEVICE_ID_LOGITECH_RECEIVER		0xc101
#define DEVICE_ID_S510_RECEIVER			0xc50c
@@ -337,6 +363,8 @@ static const struct hid_input_blacklist {

	{ VENDOR_ID_EZKEY, DEVICE_ID_BTC_8193, quirk_btc_8193 },

	{ VENDOR_ID_GYRATION, DEVICE_ID_GYRATION_REMOTE, quirk_gyration_remote },

	{ VENDOR_ID_LOGITECH, DEVICE_ID_LOGITECH_RECEIVER, quirk_logitech_ultrax_remote },
	{ VENDOR_ID_LOGITECH, DEVICE_ID_S510_RECEIVER, quirk_logitech_wireless },
	{ VENDOR_ID_LOGITECH, DEVICE_ID_S510_RECEIVER_2, quirk_logitech_wireless },
@@ -438,6 +466,18 @@ int hidinput_event_quirks(struct hid_device *hid, struct hid_field *field, struc
		input_event(input, usage->type, REL_WHEEL, -value);
		return 1;
	}

	/* Gyration MCE remote "Sleep" key */
	if (hid->vendor == VENDOR_ID_GYRATION &&
	    hid->product == DEVICE_ID_GYRATION_REMOTE &&
	    (usage->hid & HID_USAGE_PAGE) == HID_UP_GENDESK &&
	    (usage->hid & 0xff) == 0x82) {
		input_event(input, usage->type, usage->code, 1);
		input_sync(input);
		input_event(input, usage->type, usage->code, 0);
		input_sync(input);
		return 1;
	}
	return 0;
}

+3 −0
Original line number Diff line number Diff line
@@ -100,6 +100,8 @@ static struct hidinput_key_translation apple_fn_keys[] = {
	{ KEY_F2,       KEY_BRIGHTNESSUP,   APPLE_FLAG_FKEY },
	{ KEY_F3,       KEY_FN_F5,          APPLE_FLAG_FKEY }, /* Expos */
	{ KEY_F4,       KEY_FN_F4,          APPLE_FLAG_FKEY }, /* Dashboard */
	{ KEY_F5,       KEY_KBDILLUMDOWN,   APPLE_FLAG_FKEY },
	{ KEY_F6,       KEY_KBDILLUMUP,     APPLE_FLAG_FKEY },
	{ KEY_F7,       KEY_PREVIOUSSONG,   APPLE_FLAG_FKEY },
	{ KEY_F8,       KEY_PLAYPAUSE,      APPLE_FLAG_FKEY },
	{ KEY_F9,       KEY_NEXTSONG,       APPLE_FLAG_FKEY },
@@ -612,6 +614,7 @@ static void hidinput_configure_usage(struct hid_input *hidinput, struct hid_fiel
				case 0x0b6: map_key_clear(KEY_PREVIOUSSONG);	break;
				case 0x0b7: map_key_clear(KEY_STOPCD);		break;
				case 0x0b8: map_key_clear(KEY_EJECTCD);		break;
				case 0x0bc: map_key_clear(KEY_MEDIA_REPEAT);	break;

				case 0x0cd: map_key_clear(KEY_PLAYPAUSE);	break;
			        case 0x0e0: map_abs_clear(ABS_VOLUME);		break;
+26 −22
Original line number Diff line number Diff line
@@ -105,6 +105,7 @@ out:
static ssize_t hidraw_write(struct file *file, const char __user *buffer, size_t count, loff_t *ppos)
{
	unsigned int minor = iminor(file->f_path.dentry->d_inode);
	/* FIXME: What stops hidraw_table going NULL */
	struct hid_device *dev = hidraw_table[minor]->hid;
	__u8 *buf;
	int ret = 0;
@@ -211,38 +212,43 @@ static int hidraw_release(struct inode * inode, struct file * file)
			kfree(list->hidraw);
	}

	kfree(list);

	return 0;
}

static int hidraw_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)
static long hidraw_ioctl(struct file *file, unsigned int cmd,
							unsigned long arg)
{
	struct inode *inode = file->f_path.dentry->d_inode;
	unsigned int minor = iminor(inode);
	long ret = 0;
	/* FIXME: What stops hidraw_table going NULL */
	struct hidraw *dev = hidraw_table[minor];
	void __user *user_arg = (void __user*) arg;

	lock_kernel();
	switch (cmd) {
		case HIDIOCGRDESCSIZE:
			if (put_user(dev->hid->rsize, (int __user *)arg))
				return -EFAULT;
			return 0;
				ret = -EFAULT;
			break;

		case HIDIOCGRDESC:
			{
				__u32 len;

				if (get_user(len, (int __user *)arg))
					return -EFAULT;

				if (len > HID_MAX_DESCRIPTOR_SIZE - 1)
					return -EINVAL;

				if (copy_to_user(user_arg + offsetof(
					ret = -EFAULT;
				else if (len > HID_MAX_DESCRIPTOR_SIZE - 1)
					ret = -EINVAL;
				else if (copy_to_user(user_arg + offsetof(
					struct hidraw_report_descriptor,
					value[0]),
					dev->hid->rdesc,
					min(dev->hid->rsize, len)))
						return -EFAULT;
				return 0;
					ret = -EFAULT;
				break;
			}
		case HIDIOCGRAWINFO:
			{
@@ -252,15 +258,13 @@ static int hidraw_ioctl(struct inode *inode, struct file *file, unsigned int cmd
				dinfo.vendor = dev->hid->vendor;
				dinfo.product = dev->hid->product;
				if (copy_to_user(user_arg, &dinfo, sizeof(dinfo)))
					return -EFAULT;

				return 0;
					ret = -EFAULT;
				break;
			}
		default:
			printk(KERN_EMERG "hidraw: unsupported ioctl() %x\n",
					cmd);
			ret = -ENOTTY;
	}
	return -EINVAL;
	return ret;
}

static const struct file_operations hidraw_ops = {
@@ -270,7 +274,7 @@ static const struct file_operations hidraw_ops = {
	.poll =         hidraw_poll,
	.open =         hidraw_open,
	.release =      hidraw_release,
	.ioctl =        hidraw_ioctl,
	.unlocked_ioctl = hidraw_ioctl,
};

void hidraw_report_event(struct hid_device *hid, u8 *data, int len)
+20 −2
Original line number Diff line number Diff line
@@ -69,12 +69,18 @@
#define USB_DEVICE_ID_APPLE_ALU_ANSI	0x0220
#define USB_DEVICE_ID_APPLE_ALU_ISO	0x0221
#define USB_DEVICE_ID_APPLE_ALU_JIS	0x0222
#define USB_DEVICE_ID_APPLE_WELLSPRING_ANSI	0x0223
#define USB_DEVICE_ID_APPLE_WELLSPRING_ISO	0x0224
#define USB_DEVICE_ID_APPLE_WELLSPRING_JIS	0x0225
#define USB_DEVICE_ID_APPLE_GEYSER4_HF_ANSI    0x0229
#define USB_DEVICE_ID_APPLE_GEYSER4_HF_ISO     0x022a
#define USB_DEVICE_ID_APPLE_GEYSER4_HF_JIS     0x022b
#define USB_DEVICE_ID_APPLE_ALU_WIRELESS_ANSI  0x022c
#define USB_DEVICE_ID_APPLE_ALU_WIRELESS_ISO   0x022d
#define USB_DEVICE_ID_APPLE_ALU_WIRELESS_JIS   0x022e
#define USB_DEVICE_ID_APPLE_WELLSPRING2_ANSI	0x0230
#define USB_DEVICE_ID_APPLE_WELLSPRING2_ISO	0x0231
#define USB_DEVICE_ID_APPLE_WELLSPRING2_JIS	0x0232
#define USB_DEVICE_ID_APPLE_FOUNTAIN_TP_ONLY	0x030a
#define USB_DEVICE_ID_APPLE_GEYSER1_TP_ONLY	0x030b
#define USB_DEVICE_ID_APPLE_IRCONTROL4	0x8242
@@ -241,6 +247,8 @@
#define USB_DEVICE_ID_LD_MACHINETEST	0x2040

#define USB_VENDOR_ID_LOGITECH		0x046d
#define USB_DEVICE_ID_LOGITECH_LX3	0xc044
#define USB_DEVICE_ID_LOGITECH_V150	0xc047
#define USB_DEVICE_ID_LOGITECH_RECEIVER	0xc101
#define USB_DEVICE_ID_LOGITECH_HARMONY  0xc110
#define USB_DEVICE_ID_LOGITECH_HARMONY_2 0xc111
@@ -314,6 +322,7 @@
#define USB_DEVICE_ID_S510_RECEIVER_2	0xc517
#define USB_DEVICE_ID_LOGITECH_CORDLESS_DESKTOP_LX500	0xc512
#define USB_DEVICE_ID_MX3000_RECEIVER	0xc513
#define USB_DEVICE_ID_DINOVO_DESKTOP	0xc704
#define USB_DEVICE_ID_DINOVO_EDGE	0xc714
#define USB_DEVICE_ID_DINOVO_MINI	0xc71f

@@ -444,6 +453,7 @@ static const struct hid_blacklist {
	{ USB_VENDOR_ID_SAITEK, USB_DEVICE_ID_SAITEK_RUMBLEPAD, HID_QUIRK_BADPAD },
	{ USB_VENDOR_ID_TOPMAX, USB_DEVICE_ID_TOPMAX_COBRAPAD, HID_QUIRK_BADPAD },

	{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_DINOVO_DESKTOP, HID_QUIRK_DUPLICATE_USAGES },
	{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_DINOVO_EDGE, HID_QUIRK_DUPLICATE_USAGES },
	{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_DINOVO_MINI, HID_QUIRK_DUPLICATE_USAGES },

@@ -593,6 +603,8 @@ static const struct hid_blacklist {

	{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_ELITE_KBD, HID_QUIRK_LOGITECH_IGNORE_DOUBLED_WHEEL | HID_QUIRK_LOGITECH_EXPANDED_KEYMAP },
	{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_CORDLESS_DESKTOP_LX500, HID_QUIRK_LOGITECH_IGNORE_DOUBLED_WHEEL | HID_QUIRK_LOGITECH_EXPANDED_KEYMAP },
	{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_LX3, HID_QUIRK_INVERT_HWHEEL },
	{ USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_LOGITECH_V150, HID_QUIRK_INVERT_HWHEEL },

	{ USB_VENDOR_ID_MICROSOFT, USB_DEVICE_ID_MS_NE4K, HID_QUIRK_MICROSOFT_KEYS },
	{ USB_VENDOR_ID_MICROSOFT, USB_DEVICE_ID_MS_LK6K, HID_QUIRK_MICROSOFT_KEYS },
@@ -642,6 +654,12 @@ static const struct hid_blacklist {
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_ANSI, HID_QUIRK_APPLE_NUMLOCK_EMULATION | HID_QUIRK_APPLE_HAS_FN },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_ISO, HID_QUIRK_APPLE_NUMLOCK_EMULATION | HID_QUIRK_APPLE_HAS_FN | HID_QUIRK_APPLE_ISO_KEYBOARD },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_JIS, HID_QUIRK_APPLE_NUMLOCK_EMULATION | HID_QUIRK_APPLE_HAS_FN },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ANSI, HID_QUIRK_APPLE_HAS_FN },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ISO, HID_QUIRK_APPLE_HAS_FN | HID_QUIRK_APPLE_ISO_KEYBOARD },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_JIS, HID_QUIRK_APPLE_HAS_FN },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_ANSI, HID_QUIRK_APPLE_HAS_FN },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_ISO, HID_QUIRK_APPLE_HAS_FN | HID_QUIRK_APPLE_ISO_KEYBOARD },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING2_JIS, HID_QUIRK_APPLE_HAS_FN },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_TP_ONLY, HID_QUIRK_APPLE_NUMLOCK_EMULATION | HID_QUIRK_APPLE_HAS_FN | HID_QUIRK_IGNORE_MOUSE },
	{ USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER1_TP_ONLY, HID_QUIRK_APPLE_NUMLOCK_EMULATION | HID_QUIRK_APPLE_HAS_FN | HID_QUIRK_IGNORE_MOUSE },

@@ -1128,7 +1146,7 @@ static void usbhid_fixup_microsoft_descriptor(unsigned char *rdesc, int rsize)
			 && rdesc[557] == 0x19
			 && rdesc[559] == 0x29) {
		printk(KERN_INFO "Fixing up Microsoft Wireless Receiver Model 1028 report descriptor\n");
		rdesc[284] = rdesc[304] = rdesc[558] = 0x35;
		rdesc[284] = rdesc[304] = rdesc[557] = 0x35;
		rdesc[352] = 0x36;
		rdesc[286] = rdesc[355] = 0x46;
		rdesc[306] = rdesc[559] = 0x45;
Loading