Skip to content

Commit a254a9d

Browse files
committed
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid
Pull HID fixes from Jiri Kosina: - memory leak fix for hid-elo driver (Dongliang Mu) - fix for hangs on newer AMD platforms with amd_sfh-driven hardware (Basavaraj Natikar ) - locking fix in i2c-hid (Daniel Thompson) - a few device-ID specific quirks * 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid: HID: amd_sfh: Add interrupt handler to process interrupts HID: amd_sfh: Add functionality to clear interrupts HID: amd_sfh: Disable the interrupt for all command HID: amd_sfh: Correct the structure field name HID: amd_sfh: Handle amd_sfh work buffer in PM ops HID:Add support for UGTABLET WP5540 HID: amd_sfh: Add illuminance mask to limit ALS max value HID: amd_sfh: Increase sensor command timeout HID: i2c-hid: goodix: Fix a lockdep splat HID: elo: fix memory leak in elo_probe HID: apple: Set the tilde quirk flag on the Wellspring 5 and later
2 parents 705d84a + 7f016b3 commit a254a9d

File tree

8 files changed

+102
-29
lines changed

8 files changed

+102
-29
lines changed

drivers/hid/amd-sfh-hid/amd_sfh_pcie.c

Lines changed: 73 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,11 +37,11 @@ static int amd_sfh_wait_response_v2(struct amd_mp2_dev *mp2, u8 sid, u32 sensor_
3737
{
3838
union cmd_response cmd_resp;
3939

40-
/* Get response with status within a max of 800 ms timeout */
40+
/* Get response with status within a max of 1600 ms timeout */
4141
if (!readl_poll_timeout(mp2->mmio + AMD_P2C_MSG(0), cmd_resp.resp,
4242
(cmd_resp.response_v2.response == sensor_sts &&
4343
cmd_resp.response_v2.status == 0 && (sid == 0xff ||
44-
cmd_resp.response_v2.sensor_id == sid)), 500, 800000))
44+
cmd_resp.response_v2.sensor_id == sid)), 500, 1600000))
4545
return cmd_resp.response_v2.response;
4646

4747
return SENSOR_DISABLED;
@@ -53,6 +53,7 @@ static void amd_start_sensor_v2(struct amd_mp2_dev *privdata, struct amd_mp2_sen
5353

5454
cmd_base.ul = 0;
5555
cmd_base.cmd_v2.cmd_id = ENABLE_SENSOR;
56+
cmd_base.cmd_v2.intr_disable = 1;
5657
cmd_base.cmd_v2.period = info.period;
5758
cmd_base.cmd_v2.sensor_id = info.sensor_idx;
5859
cmd_base.cmd_v2.length = 16;
@@ -70,6 +71,7 @@ static void amd_stop_sensor_v2(struct amd_mp2_dev *privdata, u16 sensor_idx)
7071

7172
cmd_base.ul = 0;
7273
cmd_base.cmd_v2.cmd_id = DISABLE_SENSOR;
74+
cmd_base.cmd_v2.intr_disable = 1;
7375
cmd_base.cmd_v2.period = 0;
7476
cmd_base.cmd_v2.sensor_id = sensor_idx;
7577
cmd_base.cmd_v2.length = 16;
@@ -83,12 +85,51 @@ static void amd_stop_all_sensor_v2(struct amd_mp2_dev *privdata)
8385
union sfh_cmd_base cmd_base;
8486

8587
cmd_base.cmd_v2.cmd_id = STOP_ALL_SENSORS;
88+
cmd_base.cmd_v2.intr_disable = 1;
8689
cmd_base.cmd_v2.period = 0;
8790
cmd_base.cmd_v2.sensor_id = 0;
8891

8992
writel(cmd_base.ul, privdata->mmio + AMD_C2P_MSG0);
9093
}
9194

95+
static void amd_sfh_clear_intr_v2(struct amd_mp2_dev *privdata)
96+
{
97+
if (readl(privdata->mmio + AMD_P2C_MSG(4))) {
98+
writel(0, privdata->mmio + AMD_P2C_MSG(4));
99+
writel(0xf, privdata->mmio + AMD_P2C_MSG(5));
100+
}
101+
}
102+
103+
static void amd_sfh_clear_intr(struct amd_mp2_dev *privdata)
104+
{
105+
if (privdata->mp2_ops->clear_intr)
106+
privdata->mp2_ops->clear_intr(privdata);
107+
}
108+
109+
static irqreturn_t amd_sfh_irq_handler(int irq, void *data)
110+
{
111+
amd_sfh_clear_intr(data);
112+
113+
return IRQ_HANDLED;
114+
}
115+
116+
static int amd_sfh_irq_init_v2(struct amd_mp2_dev *privdata)
117+
{
118+
int rc;
119+
120+
pci_intx(privdata->pdev, true);
121+
122+
rc = devm_request_irq(&privdata->pdev->dev, privdata->pdev->irq,
123+
amd_sfh_irq_handler, 0, DRIVER_NAME, privdata);
124+
if (rc) {
125+
dev_err(&privdata->pdev->dev, "failed to request irq %d err=%d\n",
126+
privdata->pdev->irq, rc);
127+
return rc;
128+
}
129+
130+
return 0;
131+
}
132+
92133
void amd_start_sensor(struct amd_mp2_dev *privdata, struct amd_mp2_sensor_info info)
93134
{
94135
union sfh_cmd_param cmd_param;
@@ -193,13 +234,17 @@ static void amd_mp2_pci_remove(void *privdata)
193234
struct amd_mp2_dev *mp2 = privdata;
194235
amd_sfh_hid_client_deinit(privdata);
195236
mp2->mp2_ops->stop_all(mp2);
237+
pci_intx(mp2->pdev, false);
238+
amd_sfh_clear_intr(mp2);
196239
}
197240

198241
static const struct amd_mp2_ops amd_sfh_ops_v2 = {
199242
.start = amd_start_sensor_v2,
200243
.stop = amd_stop_sensor_v2,
201244
.stop_all = amd_stop_all_sensor_v2,
202245
.response = amd_sfh_wait_response_v2,
246+
.clear_intr = amd_sfh_clear_intr_v2,
247+
.init_intr = amd_sfh_irq_init_v2,
203248
};
204249

205250
static const struct amd_mp2_ops amd_sfh_ops = {
@@ -225,6 +270,14 @@ static void mp2_select_ops(struct amd_mp2_dev *privdata)
225270
}
226271
}
227272

273+
static int amd_sfh_irq_init(struct amd_mp2_dev *privdata)
274+
{
275+
if (privdata->mp2_ops->init_intr)
276+
return privdata->mp2_ops->init_intr(privdata);
277+
278+
return 0;
279+
}
280+
228281
static int amd_mp2_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id)
229282
{
230283
struct amd_mp2_dev *privdata;
@@ -261,9 +314,20 @@ static int amd_mp2_pci_probe(struct pci_dev *pdev, const struct pci_device_id *i
261314

262315
mp2_select_ops(privdata);
263316

317+
rc = amd_sfh_irq_init(privdata);
318+
if (rc) {
319+
dev_err(&pdev->dev, "amd_sfh_irq_init failed\n");
320+
return rc;
321+
}
322+
264323
rc = amd_sfh_hid_client_init(privdata);
265-
if (rc)
324+
if (rc) {
325+
amd_sfh_clear_intr(privdata);
326+
dev_err(&pdev->dev, "amd_sfh_hid_client_init failed\n");
266327
return rc;
328+
}
329+
330+
amd_sfh_clear_intr(privdata);
267331

268332
return devm_add_action_or_reset(&pdev->dev, amd_mp2_pci_remove, privdata);
269333
}
@@ -290,6 +354,9 @@ static int __maybe_unused amd_mp2_pci_resume(struct device *dev)
290354
}
291355
}
292356

357+
schedule_delayed_work(&cl_data->work_buffer, msecs_to_jiffies(AMD_SFH_IDLE_LOOP));
358+
amd_sfh_clear_intr(mp2);
359+
293360
return 0;
294361
}
295362

@@ -312,6 +379,9 @@ static int __maybe_unused amd_mp2_pci_suspend(struct device *dev)
312379
}
313380
}
314381

382+
cancel_delayed_work_sync(&cl_data->work_buffer);
383+
amd_sfh_clear_intr(mp2);
384+
315385
return 0;
316386
}
317387

drivers/hid/amd-sfh-hid/amd_sfh_pcie.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ union sfh_cmd_base {
4949
} s;
5050
struct {
5151
u32 cmd_id : 4;
52-
u32 intr_enable : 1;
52+
u32 intr_disable : 1;
5353
u32 rsvd1 : 3;
5454
u32 length : 7;
5555
u32 mem_type : 1;
@@ -141,5 +141,7 @@ struct amd_mp2_ops {
141141
void (*stop)(struct amd_mp2_dev *privdata, u16 sensor_idx);
142142
void (*stop_all)(struct amd_mp2_dev *privdata);
143143
int (*response)(struct amd_mp2_dev *mp2, u8 sid, u32 sensor_sts);
144+
void (*clear_intr)(struct amd_mp2_dev *privdata);
145+
int (*init_intr)(struct amd_mp2_dev *privdata);
144146
};
145147
#endif

drivers/hid/amd-sfh-hid/hid_descriptor/amd_sfh_hid_desc.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
#define HID_USAGE_SENSOR_STATE_READY_ENUM 0x02
2828
#define HID_USAGE_SENSOR_STATE_INITIALIZING_ENUM 0x05
2929
#define HID_USAGE_SENSOR_EVENT_DATA_UPDATED_ENUM 0x04
30+
#define ILLUMINANCE_MASK GENMASK(14, 0)
3031

3132
int get_report_descriptor(int sensor_idx, u8 *rep_desc)
3233
{
@@ -246,7 +247,8 @@ u8 get_input_report(u8 current_index, int sensor_idx, int report_id, struct amd_
246247
get_common_inputs(&als_input.common_property, report_id);
247248
/* For ALS ,V2 Platforms uses C2P_MSG5 register instead of DRAM access method */
248249
if (supported_input == V2_STATUS)
249-
als_input.illuminance_value = (int)readl(privdata->mmio + AMD_C2P_MSG(5));
250+
als_input.illuminance_value =
251+
readl(privdata->mmio + AMD_C2P_MSG(5)) & ILLUMINANCE_MASK;
250252
else
251253
als_input.illuminance_value =
252254
(int)sensor_virt_addr[0] / AMD_SFH_FW_MULTIPLIER;

drivers/hid/hid-apple.c

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -691,49 +691,49 @@ static const struct hid_device_id apple_devices[] = {
691691
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_ANSI),
692692
.driver_data = APPLE_HAS_FN },
693693
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_ISO),
694-
.driver_data = APPLE_HAS_FN },
694+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
695695
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_JIS),
696696
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
697697
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_ANSI),
698698
.driver_data = APPLE_HAS_FN },
699699
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_ISO),
700-
.driver_data = APPLE_HAS_FN },
700+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
701701
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_JIS),
702702
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
703703
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_ANSI),
704704
.driver_data = APPLE_HAS_FN },
705705
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_ISO),
706-
.driver_data = APPLE_HAS_FN },
706+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
707707
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_JIS),
708708
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
709709
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ANSI),
710710
.driver_data = APPLE_HAS_FN },
711711
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ISO),
712-
.driver_data = APPLE_HAS_FN },
712+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
713713
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_JIS),
714714
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
715715
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING7_ANSI),
716716
.driver_data = APPLE_HAS_FN },
717717
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING7_ISO),
718-
.driver_data = APPLE_HAS_FN },
718+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
719719
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING7_JIS),
720720
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
721721
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING7A_ANSI),
722722
.driver_data = APPLE_HAS_FN },
723723
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING7A_ISO),
724-
.driver_data = APPLE_HAS_FN },
724+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
725725
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING7A_JIS),
726726
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
727727
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING8_ANSI),
728728
.driver_data = APPLE_HAS_FN },
729729
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING8_ISO),
730-
.driver_data = APPLE_HAS_FN },
730+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
731731
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING8_JIS),
732732
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
733733
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING9_ANSI),
734734
.driver_data = APPLE_HAS_FN },
735735
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING9_ISO),
736-
.driver_data = APPLE_HAS_FN },
736+
.driver_data = APPLE_HAS_FN | APPLE_ISO_TILDE_QUIRK },
737737
{ HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING9_JIS),
738738
.driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS },
739739
{ HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_ANSI),

drivers/hid/hid-elo.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -262,6 +262,7 @@ static int elo_probe(struct hid_device *hdev, const struct hid_device_id *id)
262262

263263
return 0;
264264
err_free:
265+
usb_put_dev(udev);
265266
kfree(priv);
266267
return ret;
267268
}

drivers/hid/hid-ids.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1370,6 +1370,7 @@
13701370
#define USB_VENDOR_ID_UGTIZER 0x2179
13711371
#define USB_DEVICE_ID_UGTIZER_TABLET_GP0610 0x0053
13721372
#define USB_DEVICE_ID_UGTIZER_TABLET_GT5040 0x0077
1373+
#define USB_DEVICE_ID_UGTIZER_TABLET_WP5540 0x0004
13731374

13741375
#define USB_VENDOR_ID_VIEWSONIC 0x0543
13751376
#define USB_DEVICE_ID_VIEWSONIC_PD1011 0xe621

drivers/hid/hid-quirks.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,7 @@ static const struct hid_device_id hid_quirks[] = {
187187
{ HID_USB_DEVICE(USB_VENDOR_ID_TURBOX, USB_DEVICE_ID_TURBOX_KEYBOARD), HID_QUIRK_NOGET },
188188
{ HID_USB_DEVICE(USB_VENDOR_ID_UCLOGIC, USB_DEVICE_ID_UCLOGIC_TABLET_KNA5), HID_QUIRK_MULTI_INPUT },
189189
{ HID_USB_DEVICE(USB_VENDOR_ID_UCLOGIC, USB_DEVICE_ID_UCLOGIC_TABLET_TWA60), HID_QUIRK_MULTI_INPUT },
190+
{ HID_USB_DEVICE(USB_VENDOR_ID_UGTIZER, USB_DEVICE_ID_UGTIZER_TABLET_WP5540), HID_QUIRK_MULTI_INPUT },
190191
{ HID_USB_DEVICE(USB_VENDOR_ID_WALTOP, USB_DEVICE_ID_WALTOP_MEDIA_TABLET_10_6_INCH), HID_QUIRK_MULTI_INPUT },
191192
{ HID_USB_DEVICE(USB_VENDOR_ID_WALTOP, USB_DEVICE_ID_WALTOP_MEDIA_TABLET_14_1_INCH), HID_QUIRK_MULTI_INPUT },
192193
{ HID_USB_DEVICE(USB_VENDOR_ID_WALTOP, USB_DEVICE_ID_WALTOP_SIRIUS_BATTERY_FREE_TABLET), HID_QUIRK_MULTI_INPUT },

drivers/hid/i2c-hid/i2c-hid-of-goodix.c

Lines changed: 12 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,6 @@ struct i2c_hid_of_goodix {
2727

2828
struct regulator *vdd;
2929
struct notifier_block nb;
30-
struct mutex regulator_mutex;
3130
struct gpio_desc *reset_gpio;
3231
const struct goodix_i2c_hid_timing_data *timings;
3332
};
@@ -67,8 +66,6 @@ static int ihid_goodix_vdd_notify(struct notifier_block *nb,
6766
container_of(nb, struct i2c_hid_of_goodix, nb);
6867
int ret = NOTIFY_OK;
6968

70-
mutex_lock(&ihid_goodix->regulator_mutex);
71-
7269
switch (event) {
7370
case REGULATOR_EVENT_PRE_DISABLE:
7471
gpiod_set_value_cansleep(ihid_goodix->reset_gpio, 1);
@@ -87,8 +84,6 @@ static int ihid_goodix_vdd_notify(struct notifier_block *nb,
8784
break;
8885
}
8986

90-
mutex_unlock(&ihid_goodix->regulator_mutex);
91-
9287
return ret;
9388
}
9489

@@ -102,8 +97,6 @@ static int i2c_hid_of_goodix_probe(struct i2c_client *client,
10297
if (!ihid_goodix)
10398
return -ENOMEM;
10499

105-
mutex_init(&ihid_goodix->regulator_mutex);
106-
107100
ihid_goodix->ops.power_up = goodix_i2c_hid_power_up;
108101
ihid_goodix->ops.power_down = goodix_i2c_hid_power_down;
109102

@@ -130,25 +123,28 @@ static int i2c_hid_of_goodix_probe(struct i2c_client *client,
130123
* long. Holding the controller in reset apparently draws extra
131124
* power.
132125
*/
133-
mutex_lock(&ihid_goodix->regulator_mutex);
134126
ihid_goodix->nb.notifier_call = ihid_goodix_vdd_notify;
135127
ret = devm_regulator_register_notifier(ihid_goodix->vdd, &ihid_goodix->nb);
136-
if (ret) {
137-
mutex_unlock(&ihid_goodix->regulator_mutex);
128+
if (ret)
138129
return dev_err_probe(&client->dev, ret,
139130
"regulator notifier request failed\n");
140-
}
141131

142132
/*
143133
* If someone else is holding the regulator on (or the regulator is
144134
* an always-on one) we might never be told to deassert reset. Do it
145-
* now. Here we'll assume that someone else might have _just
146-
* barely_ turned the regulator on so we'll do the full
147-
* "post_power_delay" just in case.
135+
* now... and temporarily bump the regulator reference count just to
136+
* make sure it is impossible for this to race with our own notifier!
137+
* We also assume that someone else might have _just barely_ turned
138+
* the regulator on so we'll do the full "post_power_delay" just in
139+
* case.
148140
*/
149-
if (ihid_goodix->reset_gpio && regulator_is_enabled(ihid_goodix->vdd))
141+
if (ihid_goodix->reset_gpio && regulator_is_enabled(ihid_goodix->vdd)) {
142+
ret = regulator_enable(ihid_goodix->vdd);
143+
if (ret)
144+
return ret;
150145
goodix_i2c_hid_deassert_reset(ihid_goodix, true);
151-
mutex_unlock(&ihid_goodix->regulator_mutex);
146+
regulator_disable(ihid_goodix->vdd);
147+
}
152148

153149
return i2c_hid_core_probe(client, &ihid_goodix->ops, 0x0001, 0);
154150
}

0 commit comments

Comments
 (0)