Skip to content

Commit 7287904

Browse files
committed
Merge tag 'for-linus-2023011801' of git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid
Pull HID fixes from Jiri Kosina: - fixes for potential empty list handling in HID core (Pietro Borrello) - fix for NULL pointer dereference in betop driver that could be triggered by malicious device (Pietro Borrello) - fixes for handling calibration data preventing division by zero in Playstation driver (Roderick Colenbrander) - fix for memory leak on error path in amd-sfh driver (Basavaraj Natikar) - other few assorted small fixes and device ID-specific handling * tag 'for-linus-2023011801' of git://git.kernel.org/pub/scm/linux/kernel/git/hid/hid: HID: betop: check shape of output reports HID: playstation: sanity check DualSense calibration data. HID: playstation: sanity check DualShock4 calibration data. HID: uclogic: Add support for XP-PEN Deco 01 V2 HID: revert CHERRY_MOUSE_000C quirk HID: check empty report_list in bigben_probe() HID: check empty report_list in hid_validate_values() HID: amd_sfh: Fix warning unwind goto HID: intel_ish-hid: Add check for ishtp_dma_tx_map
2 parents 7026172 + 3782c0d commit 7287904

File tree

11 files changed

+96
-14
lines changed

11 files changed

+96
-14
lines changed

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

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -282,7 +282,7 @@ int amd_sfh_hid_client_init(struct amd_mp2_dev *privdata)
282282
}
283283
rc = mp2_ops->get_rep_desc(cl_idx, cl_data->report_descr[i]);
284284
if (rc)
285-
return rc;
285+
goto cleanup;
286286
mp2_ops->start(privdata, info);
287287
status = amd_sfh_wait_for_response
288288
(privdata, cl_data->sensor_idx[i], SENSOR_ENABLED);

drivers/hid/amd-sfh-hid/sfh1_1/amd_sfh_init.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -160,7 +160,7 @@ static int amd_sfh1_1_hid_client_init(struct amd_mp2_dev *privdata)
160160
}
161161
rc = mp2_ops->get_rep_desc(cl_idx, cl_data->report_descr[i]);
162162
if (rc)
163-
return rc;
163+
goto cleanup;
164164

165165
writel(0, privdata->mmio + AMD_P2C_MSG(0));
166166
mp2_ops->start(privdata, info);

drivers/hid/hid-betopff.c

Lines changed: 9 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,6 @@ static int betopff_init(struct hid_device *hid)
6060
struct list_head *report_list =
6161
&hid->report_enum[HID_OUTPUT_REPORT].report_list;
6262
struct input_dev *dev;
63-
int field_count = 0;
6463
int error;
6564
int i, j;
6665

@@ -86,19 +85,21 @@ static int betopff_init(struct hid_device *hid)
8685
* -----------------------------------------
8786
* Do init them with default value.
8887
*/
88+
if (report->maxfield < 4) {
89+
hid_err(hid, "not enough fields in the report: %d\n",
90+
report->maxfield);
91+
return -ENODEV;
92+
}
8993
for (i = 0; i < report->maxfield; i++) {
94+
if (report->field[i]->report_count < 1) {
95+
hid_err(hid, "no values in the field\n");
96+
return -ENODEV;
97+
}
9098
for (j = 0; j < report->field[i]->report_count; j++) {
9199
report->field[i]->value[j] = 0x00;
92-
field_count++;
93100
}
94101
}
95102

96-
if (field_count < 4) {
97-
hid_err(hid, "not enough fields in the report: %d\n",
98-
field_count);
99-
return -ENODEV;
100-
}
101-
102103
betopff = kzalloc(sizeof(*betopff), GFP_KERNEL);
103104
if (!betopff)
104105
return -ENOMEM;

drivers/hid/hid-bigbenff.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -344,6 +344,11 @@ static int bigben_probe(struct hid_device *hid,
344344
}
345345

346346
report_list = &hid->report_enum[HID_OUTPUT_REPORT].report_list;
347+
if (list_empty(report_list)) {
348+
hid_err(hid, "no output report found\n");
349+
error = -ENODEV;
350+
goto error_hw_stop;
351+
}
347352
bigben->report = list_entry(report_list->next,
348353
struct hid_report, list);
349354

drivers/hid/hid-core.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -993,8 +993,8 @@ struct hid_report *hid_validate_values(struct hid_device *hid,
993993
* Validating on id 0 means we should examine the first
994994
* report in the list.
995995
*/
996-
report = list_entry(
997-
hid->report_enum[type].report_list.next,
996+
report = list_first_entry_or_null(
997+
&hid->report_enum[type].report_list,
998998
struct hid_report, list);
999999
} else {
10001000
report = hid->report_enum[type].report_id_hash[id];

drivers/hid/hid-ids.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -274,7 +274,6 @@
274274
#define USB_DEVICE_ID_CH_AXIS_295 0x001c
275275

276276
#define USB_VENDOR_ID_CHERRY 0x046a
277-
#define USB_DEVICE_ID_CHERRY_MOUSE_000C 0x000c
278277
#define USB_DEVICE_ID_CHERRY_CYMOTION 0x0023
279278
#define USB_DEVICE_ID_CHERRY_CYMOTION_SOLAR 0x0027
280279

@@ -1295,6 +1294,7 @@
12951294
#define USB_DEVICE_ID_UGEE_XPPEN_TABLET_G540 0x0075
12961295
#define USB_DEVICE_ID_UGEE_XPPEN_TABLET_G640 0x0094
12971296
#define USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO01 0x0042
1297+
#define USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO01_V2 0x0905
12981298
#define USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO_L 0x0935
12991299
#define USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO_PRO_S 0x0909
13001300
#define USB_DEVICE_ID_UGEE_XPPEN_TABLET_STAR06 0x0078

drivers/hid/hid-playstation.c

Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -944,6 +944,7 @@ ATTRIBUTE_GROUPS(ps_device);
944944

945945
static int dualsense_get_calibration_data(struct dualsense *ds)
946946
{
947+
struct hid_device *hdev = ds->base.hdev;
947948
short gyro_pitch_bias, gyro_pitch_plus, gyro_pitch_minus;
948949
short gyro_yaw_bias, gyro_yaw_plus, gyro_yaw_minus;
949950
short gyro_roll_bias, gyro_roll_plus, gyro_roll_minus;
@@ -954,6 +955,7 @@ static int dualsense_get_calibration_data(struct dualsense *ds)
954955
int speed_2x;
955956
int range_2g;
956957
int ret = 0;
958+
int i;
957959
uint8_t *buf;
958960

959961
buf = kzalloc(DS_FEATURE_REPORT_CALIBRATION_SIZE, GFP_KERNEL);
@@ -1005,6 +1007,21 @@ static int dualsense_get_calibration_data(struct dualsense *ds)
10051007
ds->gyro_calib_data[2].sens_numer = speed_2x*DS_GYRO_RES_PER_DEG_S;
10061008
ds->gyro_calib_data[2].sens_denom = gyro_roll_plus - gyro_roll_minus;
10071009

1010+
/*
1011+
* Sanity check gyro calibration data. This is needed to prevent crashes
1012+
* during report handling of virtual, clone or broken devices not implementing
1013+
* calibration data properly.
1014+
*/
1015+
for (i = 0; i < ARRAY_SIZE(ds->gyro_calib_data); i++) {
1016+
if (ds->gyro_calib_data[i].sens_denom == 0) {
1017+
hid_warn(hdev, "Invalid gyro calibration data for axis (%d), disabling calibration.",
1018+
ds->gyro_calib_data[i].abs_code);
1019+
ds->gyro_calib_data[i].bias = 0;
1020+
ds->gyro_calib_data[i].sens_numer = DS_GYRO_RANGE;
1021+
ds->gyro_calib_data[i].sens_denom = S16_MAX;
1022+
}
1023+
}
1024+
10081025
/*
10091026
* Set accelerometer calibration and normalization parameters.
10101027
* Data values will be normalized to 1/DS_ACC_RES_PER_G g.
@@ -1027,6 +1044,21 @@ static int dualsense_get_calibration_data(struct dualsense *ds)
10271044
ds->accel_calib_data[2].sens_numer = 2*DS_ACC_RES_PER_G;
10281045
ds->accel_calib_data[2].sens_denom = range_2g;
10291046

1047+
/*
1048+
* Sanity check accelerometer calibration data. This is needed to prevent crashes
1049+
* during report handling of virtual, clone or broken devices not implementing calibration
1050+
* data properly.
1051+
*/
1052+
for (i = 0; i < ARRAY_SIZE(ds->accel_calib_data); i++) {
1053+
if (ds->accel_calib_data[i].sens_denom == 0) {
1054+
hid_warn(hdev, "Invalid accelerometer calibration data for axis (%d), disabling calibration.",
1055+
ds->accel_calib_data[i].abs_code);
1056+
ds->accel_calib_data[i].bias = 0;
1057+
ds->accel_calib_data[i].sens_numer = DS_ACC_RANGE;
1058+
ds->accel_calib_data[i].sens_denom = S16_MAX;
1059+
}
1060+
}
1061+
10301062
err_free:
10311063
kfree(buf);
10321064
return ret;
@@ -1737,6 +1769,7 @@ static int dualshock4_get_calibration_data(struct dualshock4 *ds4)
17371769
int speed_2x;
17381770
int range_2g;
17391771
int ret = 0;
1772+
int i;
17401773
uint8_t *buf;
17411774

17421775
if (ds4->base.hdev->bus == BUS_USB) {
@@ -1830,6 +1863,21 @@ static int dualshock4_get_calibration_data(struct dualshock4 *ds4)
18301863
ds4->gyro_calib_data[2].sens_numer = speed_2x*DS4_GYRO_RES_PER_DEG_S;
18311864
ds4->gyro_calib_data[2].sens_denom = gyro_roll_plus - gyro_roll_minus;
18321865

1866+
/*
1867+
* Sanity check gyro calibration data. This is needed to prevent crashes
1868+
* during report handling of virtual, clone or broken devices not implementing
1869+
* calibration data properly.
1870+
*/
1871+
for (i = 0; i < ARRAY_SIZE(ds4->gyro_calib_data); i++) {
1872+
if (ds4->gyro_calib_data[i].sens_denom == 0) {
1873+
hid_warn(hdev, "Invalid gyro calibration data for axis (%d), disabling calibration.",
1874+
ds4->gyro_calib_data[i].abs_code);
1875+
ds4->gyro_calib_data[i].bias = 0;
1876+
ds4->gyro_calib_data[i].sens_numer = DS4_GYRO_RANGE;
1877+
ds4->gyro_calib_data[i].sens_denom = S16_MAX;
1878+
}
1879+
}
1880+
18331881
/*
18341882
* Set accelerometer calibration and normalization parameters.
18351883
* Data values will be normalized to 1/DS4_ACC_RES_PER_G g.
@@ -1852,6 +1900,21 @@ static int dualshock4_get_calibration_data(struct dualshock4 *ds4)
18521900
ds4->accel_calib_data[2].sens_numer = 2*DS4_ACC_RES_PER_G;
18531901
ds4->accel_calib_data[2].sens_denom = range_2g;
18541902

1903+
/*
1904+
* Sanity check accelerometer calibration data. This is needed to prevent crashes
1905+
* during report handling of virtual, clone or broken devices not implementing calibration
1906+
* data properly.
1907+
*/
1908+
for (i = 0; i < ARRAY_SIZE(ds4->accel_calib_data); i++) {
1909+
if (ds4->accel_calib_data[i].sens_denom == 0) {
1910+
hid_warn(hdev, "Invalid accelerometer calibration data for axis (%d), disabling calibration.",
1911+
ds4->accel_calib_data[i].abs_code);
1912+
ds4->accel_calib_data[i].bias = 0;
1913+
ds4->accel_calib_data[i].sens_numer = DS4_ACC_RANGE;
1914+
ds4->accel_calib_data[i].sens_denom = S16_MAX;
1915+
}
1916+
}
1917+
18551918
err_free:
18561919
kfree(buf);
18571920
return ret;

drivers/hid/hid-quirks.c

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,7 +54,6 @@ static const struct hid_device_id hid_quirks[] = {
5454
{ HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_FLIGHT_SIM_YOKE), HID_QUIRK_NOGET },
5555
{ HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_PRO_PEDALS), HID_QUIRK_NOGET },
5656
{ HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_PRO_THROTTLE), HID_QUIRK_NOGET },
57-
{ HID_USB_DEVICE(USB_VENDOR_ID_CHERRY, USB_DEVICE_ID_CHERRY_MOUSE_000C), HID_QUIRK_ALWAYS_POLL },
5857
{ HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K65RGB), HID_QUIRK_NO_INIT_REPORTS },
5958
{ HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K65RGB_RAPIDFIRE), HID_QUIRK_NO_INIT_REPORTS | HID_QUIRK_ALWAYS_POLL },
6059
{ HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K70RGB), HID_QUIRK_NO_INIT_REPORTS },

drivers/hid/hid-uclogic-core.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -525,6 +525,8 @@ static const struct hid_device_id uclogic_devices[] = {
525525
USB_DEVICE_ID_UGEE_XPPEN_TABLET_G640) },
526526
{ HID_USB_DEVICE(USB_VENDOR_ID_UGEE,
527527
USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO01) },
528+
{ HID_USB_DEVICE(USB_VENDOR_ID_UGEE,
529+
USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO01_V2) },
528530
{ HID_USB_DEVICE(USB_VENDOR_ID_UGEE,
529531
USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO_L) },
530532
{ HID_USB_DEVICE(USB_VENDOR_ID_UGEE,

drivers/hid/hid-uclogic-params.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1655,6 +1655,8 @@ int uclogic_params_init(struct uclogic_params *params,
16551655
break;
16561656
case VID_PID(USB_VENDOR_ID_UGEE,
16571657
USB_DEVICE_ID_UGEE_PARBLO_A610_PRO):
1658+
case VID_PID(USB_VENDOR_ID_UGEE,
1659+
USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO01_V2):
16581660
case VID_PID(USB_VENDOR_ID_UGEE,
16591661
USB_DEVICE_ID_UGEE_XPPEN_TABLET_DECO_L):
16601662
case VID_PID(USB_VENDOR_ID_UGEE,

drivers/hid/intel-ish-hid/ishtp/dma-if.c

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,11 @@ void *ishtp_cl_get_dma_send_buf(struct ishtp_device *dev,
104104
int required_slots = (size / DMA_SLOT_SIZE)
105105
+ 1 * (size % DMA_SLOT_SIZE != 0);
106106

107+
if (!dev->ishtp_dma_tx_map) {
108+
dev_err(dev->devc, "Fail to allocate Tx map\n");
109+
return NULL;
110+
}
111+
107112
spin_lock_irqsave(&dev->ishtp_dma_tx_lock, flags);
108113
for (i = 0; i <= (dev->ishtp_dma_num_slots - required_slots); i++) {
109114
free = 1;
@@ -150,6 +155,11 @@ void ishtp_cl_release_dma_acked_mem(struct ishtp_device *dev,
150155
return;
151156
}
152157

158+
if (!dev->ishtp_dma_tx_map) {
159+
dev_err(dev->devc, "Fail to allocate Tx map\n");
160+
return;
161+
}
162+
153163
i = (msg_addr - dev->ishtp_host_dma_tx_buf) / DMA_SLOT_SIZE;
154164
spin_lock_irqsave(&dev->ishtp_dma_tx_lock, flags);
155165
for (j = 0; j < acked_slots; j++) {

0 commit comments

Comments
 (0)