From e3d16adf08a4976a34519b9f9259f1fd7e66af24 Mon Sep 17 00:00:00 2001 From: h0tw4t3r Date: Wed, 20 Mar 2019 00:41:22 +0200 Subject: [PATCH 1/6] ELAN touchpad i2c_hid bugs fix --- drivers/hid/hid-ids.h | 2 ++ drivers/hid/i2c-hid/i2c-hid-core.c | 22 +++++++++------------- 2 files changed, 11 insertions(+), 13 deletions(-) diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index b6d93f4ad037e4..a475f72fc6ec5a 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h @@ -385,6 +385,8 @@ #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_73F7 0x73f7 #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_A001 0xa001 +#define I2C_PRODUCT_ID_ELAN_TOUCHPAD 0x303e + #define USB_VENDOR_ID_ELAN 0x04f3 #define USB_DEVICE_ID_TOSHIBA_CLICK_L9W 0x0401 #define USB_DEVICE_ID_HP_X2 0x074d diff --git a/drivers/hid/i2c-hid/i2c-hid-core.c b/drivers/hid/i2c-hid/i2c-hid-core.c index 90164fed08d35e..22580ebc3336af 100644 --- a/drivers/hid/i2c-hid/i2c-hid-core.c +++ b/drivers/hid/i2c-hid/i2c-hid-core.c @@ -50,7 +50,7 @@ #define I2C_HID_QUIRK_NO_IRQ_AFTER_RESET BIT(1) #define I2C_HID_QUIRK_NO_RUNTIME_PM BIT(2) #define I2C_HID_QUIRK_DELAY_AFTER_SLEEP BIT(3) -#define I2C_HID_QUIRK_BOGUS_IRQ BIT(4) +#define I2C_HID_QUIRK_FORCE_TRIGGER_FALLING BIT(4) /* flags */ #define I2C_HID_STARTED 0 @@ -182,8 +182,8 @@ static const struct i2c_hid_quirks { I2C_HID_QUIRK_NO_RUNTIME_PM }, { I2C_VENDOR_ID_GOODIX, I2C_DEVICE_ID_GOODIX_01F0, I2C_HID_QUIRK_NO_RUNTIME_PM }, - { USB_VENDOR_ID_ELAN, HID_ANY_ID, - I2C_HID_QUIRK_BOGUS_IRQ }, + { USB_VENDOR_ID_ELAN, I2C_PRODUCT_ID_ELAN_TOUCHPAD, + I2C_HID_QUIRK_FORCE_TRIGGER_FALLING }, { 0, 0 } }; @@ -508,12 +508,6 @@ static void i2c_hid_get_input(struct i2c_hid *ihid) return; } - if (ihid->quirks & I2C_HID_QUIRK_BOGUS_IRQ && ret_size == 0xffff) { - dev_warn_once(&ihid->client->dev, "%s: IRQ triggered but " - "there's no data\n", __func__); - return; - } - if ((ret_size > size) || (ret_size < 2)) { dev_err(&ihid->client->dev, "%s: incomplete report (%d/%d)\n", __func__, size, ret_size); @@ -854,6 +848,8 @@ static int i2c_hid_init_irq(struct i2c_client *client) if (!irq_get_trigger_type(client->irq)) irqflags = IRQF_TRIGGER_LOW; + if (ihid->quirks & I2C_HID_QUIRK_FORCE_TRIGGER_FALLING) + irqflags = IRQF_TRIGGER_FALLING; ret = request_threaded_irq(client->irq, NULL, i2c_hid_irq, irqflags | IRQF_ONESHOT, client->name, ihid); @@ -1123,10 +1119,6 @@ static int i2c_hid_probe(struct i2c_client *client, if (ret < 0) goto err_pm; - ret = i2c_hid_init_irq(client); - if (ret < 0) - goto err_pm; - hid = hid_allocate_device(); if (IS_ERR(hid)) { ret = PTR_ERR(hid); @@ -1149,6 +1141,10 @@ static int i2c_hid_probe(struct i2c_client *client, ihid->quirks = i2c_hid_lookup_quirk(hid->vendor, hid->product); + ret = i2c_hid_init_irq(client); + if (ret < 0) + goto err_pm; + ret = hid_add_device(hid); if (ret) { if (ret != -ENODEV) From d7eb86db17b5e65ef787a8e6b16daba26af93fad Mon Sep 17 00:00:00 2001 From: h0tw4t3r Date: Wed, 20 Mar 2019 11:30:36 +0200 Subject: [PATCH 2/6] i2c-hid: Requested changes --- drivers/hid/hid-ids.h | 2 +- drivers/hid/i2c-hid/i2c-hid-core.c | 9 ++++++--- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index a475f72fc6ec5a..6780e3eec6db74 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h @@ -385,7 +385,7 @@ #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_73F7 0x73f7 #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_A001 0xa001 -#define I2C_PRODUCT_ID_ELAN_TOUCHPAD 0x303e +#define USB_DEVICE_ID_ELAN_TOUCHPAD 0x303e #define USB_VENDOR_ID_ELAN 0x04f3 #define USB_DEVICE_ID_TOSHIBA_CLICK_L9W 0x0401 diff --git a/drivers/hid/i2c-hid/i2c-hid-core.c b/drivers/hid/i2c-hid/i2c-hid-core.c index 22580ebc3336af..14b01b36ff81ea 100644 --- a/drivers/hid/i2c-hid/i2c-hid-core.c +++ b/drivers/hid/i2c-hid/i2c-hid-core.c @@ -50,7 +50,8 @@ #define I2C_HID_QUIRK_NO_IRQ_AFTER_RESET BIT(1) #define I2C_HID_QUIRK_NO_RUNTIME_PM BIT(2) #define I2C_HID_QUIRK_DELAY_AFTER_SLEEP BIT(3) -#define I2C_HID_QUIRK_FORCE_TRIGGER_FALLING BIT(4) +#define I2C_HID_QUIRK_BOGUS_IRQ BIT(4) +#define I2C_HID_QUIRK_FORCE_TRIGGER_FALLING BIT(5) /* flags */ #define I2C_HID_STARTED 0 @@ -182,8 +183,10 @@ static const struct i2c_hid_quirks { I2C_HID_QUIRK_NO_RUNTIME_PM }, { I2C_VENDOR_ID_GOODIX, I2C_DEVICE_ID_GOODIX_01F0, I2C_HID_QUIRK_NO_RUNTIME_PM }, - { USB_VENDOR_ID_ELAN, I2C_PRODUCT_ID_ELAN_TOUCHPAD, - I2C_HID_QUIRK_FORCE_TRIGGER_FALLING }, + { USB_VENDOR_ID_ELAN, HID_ANY_ID, + I2C_HID_QUIRK_BOGUS_IRQ }, + { USB_VENDOR_ID_ELAN, USB_DEVICE_ID_ELAN_TOUCHPAD, + I2C_HID_QUIRK_BOGUS_IRQ | I2C_HID_QUIRK_FORCE_TRIGGER_FALLING }, { 0, 0 } }; From b7a1b0003033628cca680478a049877585eddfb2 Mon Sep 17 00:00:00 2001 From: h0tw4t3r Date: Wed, 20 Mar 2019 11:34:35 +0200 Subject: [PATCH 3/6] i2c-hid: revert BOGUS_IRQ check --- drivers/hid/i2c-hid/i2c-hid-core.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/drivers/hid/i2c-hid/i2c-hid-core.c b/drivers/hid/i2c-hid/i2c-hid-core.c index 14b01b36ff81ea..d19bd888ce2b9a 100644 --- a/drivers/hid/i2c-hid/i2c-hid-core.c +++ b/drivers/hid/i2c-hid/i2c-hid-core.c @@ -511,6 +511,12 @@ static void i2c_hid_get_input(struct i2c_hid *ihid) return; } + if (ihid->quirks & I2C_HID_QUIRK_BOGUS_IRQ && ret_size == 0xffff) { + dev_warn_once(&ihid->client->dev, "%s: IRQ triggered but " + "there's no data\n", __func__); + return; + } + if ((ret_size > size) || (ret_size < 2)) { dev_err(&ihid->client->dev, "%s: incomplete report (%d/%d)\n", __func__, size, ret_size); From 14a6666990511cbde6c9f0cbeb2b4a22dfa4b68e Mon Sep 17 00:00:00 2001 From: h0tw4t3r Date: Wed, 20 Mar 2019 11:56:44 +0200 Subject: [PATCH 4/6] i2c-hid: define and quirk sections moved --- drivers/hid/hid-ids.h | 2 +- drivers/hid/i2c-hid/i2c-hid-core.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index 6780e3eec6db74..8d42d432e5a372 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h @@ -385,12 +385,12 @@ #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_73F7 0x73f7 #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_A001 0xa001 -#define USB_DEVICE_ID_ELAN_TOUCHPAD 0x303e #define USB_VENDOR_ID_ELAN 0x04f3 #define USB_DEVICE_ID_TOSHIBA_CLICK_L9W 0x0401 #define USB_DEVICE_ID_HP_X2 0x074d #define USB_DEVICE_ID_HP_X2_10_COVER 0x0755 +#define USB_DEVICE_ID_ELAN_TOUCHPAD 0x303e #define USB_VENDOR_ID_ELECOM 0x056e #define USB_DEVICE_ID_ELECOM_BM084 0x0061 diff --git a/drivers/hid/i2c-hid/i2c-hid-core.c b/drivers/hid/i2c-hid/i2c-hid-core.c index d19bd888ce2b9a..16b55c45e2e8fc 100644 --- a/drivers/hid/i2c-hid/i2c-hid-core.c +++ b/drivers/hid/i2c-hid/i2c-hid-core.c @@ -183,10 +183,10 @@ static const struct i2c_hid_quirks { I2C_HID_QUIRK_NO_RUNTIME_PM }, { I2C_VENDOR_ID_GOODIX, I2C_DEVICE_ID_GOODIX_01F0, I2C_HID_QUIRK_NO_RUNTIME_PM }, - { USB_VENDOR_ID_ELAN, HID_ANY_ID, - I2C_HID_QUIRK_BOGUS_IRQ }, { USB_VENDOR_ID_ELAN, USB_DEVICE_ID_ELAN_TOUCHPAD, I2C_HID_QUIRK_BOGUS_IRQ | I2C_HID_QUIRK_FORCE_TRIGGER_FALLING }, + { USB_VENDOR_ID_ELAN, HID_ANY_ID, + I2C_HID_QUIRK_BOGUS_IRQ }, { 0, 0 } }; From 844193c744e892881503e853fc507a36f773d0b3 Mon Sep 17 00:00:00 2001 From: h0tw4t3r Date: Wed, 20 Mar 2019 12:01:29 +0200 Subject: [PATCH 5/6] i2c-hid: extra newline fix --- drivers/hid/hid-ids.h | 1 - 1 file changed, 1 deletion(-) diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index 8d42d432e5a372..dc44b5661669a6 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h @@ -385,7 +385,6 @@ #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_73F7 0x73f7 #define USB_DEVICE_ID_DWAV_EGALAX_MULTITOUCH_A001 0xa001 - #define USB_VENDOR_ID_ELAN 0x04f3 #define USB_DEVICE_ID_TOSHIBA_CLICK_L9W 0x0401 #define USB_DEVICE_ID_HP_X2 0x074d From f7ee5a1d5eebb5a3d9e204a8824eef7d6a182daf Mon Sep 17 00:00:00 2001 From: h0tw4t3r Date: Wed, 20 Mar 2019 20:24:50 +0200 Subject: [PATCH 6/6] i2c-hid: Benjamin Tissoires changes applied --- drivers/hid/hid-ids.h | 2 +- drivers/hid/i2c-hid/i2c-hid-core.c | 14 +++++++------- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index dc44b5661669a6..660b4e0e912e7c 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h @@ -389,7 +389,7 @@ #define USB_DEVICE_ID_TOSHIBA_CLICK_L9W 0x0401 #define USB_DEVICE_ID_HP_X2 0x074d #define USB_DEVICE_ID_HP_X2_10_COVER 0x0755 -#define USB_DEVICE_ID_ELAN_TOUCHPAD 0x303e +#define I2C_DEVICE_ID_ELAN_TOUCHPAD 0x303e #define USB_VENDOR_ID_ELECOM 0x056e #define USB_DEVICE_ID_ELECOM_BM084 0x0061 diff --git a/drivers/hid/i2c-hid/i2c-hid-core.c b/drivers/hid/i2c-hid/i2c-hid-core.c index 16b55c45e2e8fc..adeb2b43a25b64 100644 --- a/drivers/hid/i2c-hid/i2c-hid-core.c +++ b/drivers/hid/i2c-hid/i2c-hid-core.c @@ -50,7 +50,7 @@ #define I2C_HID_QUIRK_NO_IRQ_AFTER_RESET BIT(1) #define I2C_HID_QUIRK_NO_RUNTIME_PM BIT(2) #define I2C_HID_QUIRK_DELAY_AFTER_SLEEP BIT(3) -#define I2C_HID_QUIRK_BOGUS_IRQ BIT(4) +#define I2C_HID_QUIRK_BOGUS_IRQ BIT(4) #define I2C_HID_QUIRK_FORCE_TRIGGER_FALLING BIT(5) /* flags */ @@ -1131,7 +1131,7 @@ static int i2c_hid_probe(struct i2c_client *client, hid = hid_allocate_device(); if (IS_ERR(hid)) { ret = PTR_ERR(hid); - goto err_irq; + goto err_pm; } ihid->hid = hid; @@ -1152,13 +1152,13 @@ static int i2c_hid_probe(struct i2c_client *client, ret = i2c_hid_init_irq(client); if (ret < 0) - goto err_pm; + goto err_mem_free; ret = hid_add_device(hid); if (ret) { if (ret != -ENODEV) hid_err(client, "can't add hid device: %d\n", ret); - goto err_mem_free; + goto err_irq; } if (!(ihid->quirks & I2C_HID_QUIRK_NO_RUNTIME_PM)) @@ -1166,12 +1166,12 @@ static int i2c_hid_probe(struct i2c_client *client, return 0; +err_irq: + free_irq(client->irq, ihid); + err_mem_free: hid_destroy_device(hid); -err_irq: - free_irq(client->irq, ihid); - err_pm: pm_runtime_put_noidle(&client->dev); pm_runtime_disable(&client->dev);