diff options
Diffstat (limited to 'drivers/hid/hid-multitouch.c')
-rw-r--r-- | drivers/hid/hid-multitouch.c | 107 |
1 files changed, 46 insertions, 61 deletions
diff --git a/drivers/hid/hid-multitouch.c b/drivers/hid/hid-multitouch.c index cb0e361d7a4b..ac28f08c3866 100644 --- a/drivers/hid/hid-multitouch.c +++ b/drivers/hid/hid-multitouch.c | |||
@@ -133,6 +133,7 @@ static void mt_post_parse(struct mt_device *td); | |||
133 | #define MT_CLS_NSMU 0x000a | 133 | #define MT_CLS_NSMU 0x000a |
134 | #define MT_CLS_DUAL_CONTACT_NUMBER 0x0010 | 134 | #define MT_CLS_DUAL_CONTACT_NUMBER 0x0010 |
135 | #define MT_CLS_DUAL_CONTACT_ID 0x0011 | 135 | #define MT_CLS_DUAL_CONTACT_ID 0x0011 |
136 | #define MT_CLS_WIN_8 0x0012 | ||
136 | 137 | ||
137 | /* vendor specific classes */ | 138 | /* vendor specific classes */ |
138 | #define MT_CLS_3M 0x0101 | 139 | #define MT_CLS_3M 0x0101 |
@@ -205,6 +206,11 @@ static struct mt_class mt_classes[] = { | |||
205 | MT_QUIRK_CONTACT_CNT_ACCURATE | | 206 | MT_QUIRK_CONTACT_CNT_ACCURATE | |
206 | MT_QUIRK_SLOT_IS_CONTACTID, | 207 | MT_QUIRK_SLOT_IS_CONTACTID, |
207 | .maxcontacts = 2 }, | 208 | .maxcontacts = 2 }, |
209 | { .name = MT_CLS_WIN_8, | ||
210 | .quirks = MT_QUIRK_ALWAYS_VALID | | ||
211 | MT_QUIRK_IGNORE_DUPLICATES | | ||
212 | MT_QUIRK_HOVERING | | ||
213 | MT_QUIRK_CONTACT_CNT_ACCURATE }, | ||
208 | 214 | ||
209 | /* | 215 | /* |
210 | * vendor specific classes | 216 | * vendor specific classes |
@@ -261,17 +267,6 @@ static struct mt_class mt_classes[] = { | |||
261 | { } | 267 | { } |
262 | }; | 268 | }; |
263 | 269 | ||
264 | static void mt_free_input_name(struct hid_input *hi) | ||
265 | { | ||
266 | struct hid_device *hdev = hi->report->device; | ||
267 | const char *name = hi->input->name; | ||
268 | |||
269 | if (name != hdev->name) { | ||
270 | hi->input->name = hdev->name; | ||
271 | kfree(name); | ||
272 | } | ||
273 | } | ||
274 | |||
275 | static ssize_t mt_show_quirks(struct device *dev, | 270 | static ssize_t mt_show_quirks(struct device *dev, |
276 | struct device_attribute *attr, | 271 | struct device_attribute *attr, |
277 | char *buf) | 272 | char *buf) |
@@ -343,19 +338,6 @@ static void mt_feature_mapping(struct hid_device *hdev, | |||
343 | td->maxcontacts = td->mtclass.maxcontacts; | 338 | td->maxcontacts = td->mtclass.maxcontacts; |
344 | 339 | ||
345 | break; | 340 | break; |
346 | case 0xff0000c5: | ||
347 | if (field->report_count == 256 && field->report_size == 8) { | ||
348 | /* Win 8 devices need special quirks */ | ||
349 | __s32 *quirks = &td->mtclass.quirks; | ||
350 | *quirks |= MT_QUIRK_ALWAYS_VALID; | ||
351 | *quirks |= MT_QUIRK_IGNORE_DUPLICATES; | ||
352 | *quirks |= MT_QUIRK_HOVERING; | ||
353 | *quirks |= MT_QUIRK_CONTACT_CNT_ACCURATE; | ||
354 | *quirks &= ~MT_QUIRK_NOT_SEEN_MEANS_UP; | ||
355 | *quirks &= ~MT_QUIRK_VALID_IS_INRANGE; | ||
356 | *quirks &= ~MT_QUIRK_VALID_IS_CONFIDENCE; | ||
357 | } | ||
358 | break; | ||
359 | } | 341 | } |
360 | } | 342 | } |
361 | 343 | ||
@@ -415,13 +397,6 @@ static void mt_pen_report(struct hid_device *hid, struct hid_report *report) | |||
415 | static void mt_pen_input_configured(struct hid_device *hdev, | 397 | static void mt_pen_input_configured(struct hid_device *hdev, |
416 | struct hid_input *hi) | 398 | struct hid_input *hi) |
417 | { | 399 | { |
418 | char *name = kzalloc(strlen(hi->input->name) + 5, GFP_KERNEL); | ||
419 | if (name) { | ||
420 | sprintf(name, "%s Pen", hi->input->name); | ||
421 | mt_free_input_name(hi); | ||
422 | hi->input->name = name; | ||
423 | } | ||
424 | |||
425 | /* force BTN_STYLUS to allow tablet matching in udev */ | 400 | /* force BTN_STYLUS to allow tablet matching in udev */ |
426 | __set_bit(BTN_STYLUS, hi->input->keybit); | 401 | __set_bit(BTN_STYLUS, hi->input->keybit); |
427 | } | 402 | } |
@@ -928,16 +903,26 @@ static void mt_post_parse(struct mt_device *td) | |||
928 | static void mt_input_configured(struct hid_device *hdev, struct hid_input *hi) | 903 | static void mt_input_configured(struct hid_device *hdev, struct hid_input *hi) |
929 | { | 904 | { |
930 | struct mt_device *td = hid_get_drvdata(hdev); | 905 | struct mt_device *td = hid_get_drvdata(hdev); |
931 | char *name = kstrdup(hdev->name, GFP_KERNEL); | 906 | char *name; |
932 | 907 | const char *suffix = NULL; | |
933 | if (name) | ||
934 | hi->input->name = name; | ||
935 | 908 | ||
936 | if (hi->report->id == td->mt_report_id) | 909 | if (hi->report->id == td->mt_report_id) |
937 | mt_touch_input_configured(hdev, hi); | 910 | mt_touch_input_configured(hdev, hi); |
938 | 911 | ||
939 | if (hi->report->id == td->pen_report_id) | 912 | if (hi->report->field[0]->physical == HID_DG_STYLUS) { |
913 | suffix = "Pen"; | ||
940 | mt_pen_input_configured(hdev, hi); | 914 | mt_pen_input_configured(hdev, hi); |
915 | } | ||
916 | |||
917 | if (suffix) { | ||
918 | name = devm_kzalloc(&hi->input->dev, | ||
919 | strlen(hdev->name) + strlen(suffix) + 2, | ||
920 | GFP_KERNEL); | ||
921 | if (name) { | ||
922 | sprintf(name, "%s %s", hdev->name, suffix); | ||
923 | hi->input->name = name; | ||
924 | } | ||
925 | } | ||
941 | } | 926 | } |
942 | 927 | ||
943 | static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | 928 | static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) |
@@ -945,7 +930,6 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | |||
945 | int ret, i; | 930 | int ret, i; |
946 | struct mt_device *td; | 931 | struct mt_device *td; |
947 | struct mt_class *mtclass = mt_classes; /* MT_CLS_DEFAULT */ | 932 | struct mt_class *mtclass = mt_classes; /* MT_CLS_DEFAULT */ |
948 | struct hid_input *hi; | ||
949 | 933 | ||
950 | for (i = 0; mt_classes[i].name ; i++) { | 934 | for (i = 0; mt_classes[i].name ; i++) { |
951 | if (id->driver_data == mt_classes[i].name) { | 935 | if (id->driver_data == mt_classes[i].name) { |
@@ -967,7 +951,19 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | |||
967 | hdev->quirks |= HID_QUIRK_MULTI_INPUT; | 951 | hdev->quirks |= HID_QUIRK_MULTI_INPUT; |
968 | hdev->quirks |= HID_QUIRK_NO_EMPTY_INPUT; | 952 | hdev->quirks |= HID_QUIRK_NO_EMPTY_INPUT; |
969 | 953 | ||
970 | td = kzalloc(sizeof(struct mt_device), GFP_KERNEL); | 954 | /* |
955 | * Handle special quirks for Windows 8 certified devices. | ||
956 | */ | ||
957 | if (id->group == HID_GROUP_MULTITOUCH_WIN_8) | ||
958 | /* | ||
959 | * Some multitouch screens do not like to be polled for input | ||
960 | * reports. Fortunately, the Win8 spec says that all touches | ||
961 | * should be sent during each report, making the initialization | ||
962 | * of input reports unnecessary. | ||
963 | */ | ||
964 | hdev->quirks |= HID_QUIRK_NO_INIT_INPUT_REPORTS; | ||
965 | |||
966 | td = devm_kzalloc(&hdev->dev, sizeof(struct mt_device), GFP_KERNEL); | ||
971 | if (!td) { | 967 | if (!td) { |
972 | dev_err(&hdev->dev, "cannot allocate multitouch data\n"); | 968 | dev_err(&hdev->dev, "cannot allocate multitouch data\n"); |
973 | return -ENOMEM; | 969 | return -ENOMEM; |
@@ -980,11 +976,11 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | |||
980 | td->pen_report_id = -1; | 976 | td->pen_report_id = -1; |
981 | hid_set_drvdata(hdev, td); | 977 | hid_set_drvdata(hdev, td); |
982 | 978 | ||
983 | td->fields = kzalloc(sizeof(struct mt_fields), GFP_KERNEL); | 979 | td->fields = devm_kzalloc(&hdev->dev, sizeof(struct mt_fields), |
980 | GFP_KERNEL); | ||
984 | if (!td->fields) { | 981 | if (!td->fields) { |
985 | dev_err(&hdev->dev, "cannot allocate multitouch fields data\n"); | 982 | dev_err(&hdev->dev, "cannot allocate multitouch fields data\n"); |
986 | ret = -ENOMEM; | 983 | return -ENOMEM; |
987 | goto fail; | ||
988 | } | 984 | } |
989 | 985 | ||
990 | if (id->vendor == HID_ANY_ID && id->product == HID_ANY_ID) | 986 | if (id->vendor == HID_ANY_ID && id->product == HID_ANY_ID) |
@@ -992,29 +988,22 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | |||
992 | 988 | ||
993 | ret = hid_parse(hdev); | 989 | ret = hid_parse(hdev); |
994 | if (ret != 0) | 990 | if (ret != 0) |
995 | goto fail; | 991 | return ret; |
996 | 992 | ||
997 | ret = hid_hw_start(hdev, HID_CONNECT_DEFAULT); | 993 | ret = hid_hw_start(hdev, HID_CONNECT_DEFAULT); |
998 | if (ret) | 994 | if (ret) |
999 | goto hid_fail; | 995 | return ret; |
1000 | 996 | ||
1001 | ret = sysfs_create_group(&hdev->dev.kobj, &mt_attribute_group); | 997 | ret = sysfs_create_group(&hdev->dev.kobj, &mt_attribute_group); |
1002 | 998 | ||
1003 | mt_set_maxcontacts(hdev); | 999 | mt_set_maxcontacts(hdev); |
1004 | mt_set_input_mode(hdev); | 1000 | mt_set_input_mode(hdev); |
1005 | 1001 | ||
1006 | kfree(td->fields); | 1002 | /* release .fields memory as it is not used anymore */ |
1003 | devm_kfree(&hdev->dev, td->fields); | ||
1007 | td->fields = NULL; | 1004 | td->fields = NULL; |
1008 | 1005 | ||
1009 | return 0; | 1006 | return 0; |
1010 | |||
1011 | hid_fail: | ||
1012 | list_for_each_entry(hi, &hdev->inputs, list) | ||
1013 | mt_free_input_name(hi); | ||
1014 | fail: | ||
1015 | kfree(td->fields); | ||
1016 | kfree(td); | ||
1017 | return ret; | ||
1018 | } | 1007 | } |
1019 | 1008 | ||
1020 | #ifdef CONFIG_PM | 1009 | #ifdef CONFIG_PM |
@@ -1039,17 +1028,8 @@ static int mt_resume(struct hid_device *hdev) | |||
1039 | 1028 | ||
1040 | static void mt_remove(struct hid_device *hdev) | 1029 | static void mt_remove(struct hid_device *hdev) |
1041 | { | 1030 | { |
1042 | struct mt_device *td = hid_get_drvdata(hdev); | ||
1043 | struct hid_input *hi; | ||
1044 | |||
1045 | sysfs_remove_group(&hdev->dev.kobj, &mt_attribute_group); | 1031 | sysfs_remove_group(&hdev->dev.kobj, &mt_attribute_group); |
1046 | list_for_each_entry(hi, &hdev->inputs, list) | ||
1047 | mt_free_input_name(hi); | ||
1048 | |||
1049 | hid_hw_stop(hdev); | 1032 | hid_hw_stop(hdev); |
1050 | |||
1051 | kfree(td); | ||
1052 | hid_set_drvdata(hdev, NULL); | ||
1053 | } | 1033 | } |
1054 | 1034 | ||
1055 | static const struct hid_device_id mt_devices[] = { | 1035 | static const struct hid_device_id mt_devices[] = { |
@@ -1371,6 +1351,11 @@ static const struct hid_device_id mt_devices[] = { | |||
1371 | 1351 | ||
1372 | /* Generic MT device */ | 1352 | /* Generic MT device */ |
1373 | { HID_DEVICE(HID_BUS_ANY, HID_GROUP_MULTITOUCH, HID_ANY_ID, HID_ANY_ID) }, | 1353 | { HID_DEVICE(HID_BUS_ANY, HID_GROUP_MULTITOUCH, HID_ANY_ID, HID_ANY_ID) }, |
1354 | |||
1355 | /* Generic Win 8 certified MT device */ | ||
1356 | { .driver_data = MT_CLS_WIN_8, | ||
1357 | HID_DEVICE(HID_BUS_ANY, HID_GROUP_MULTITOUCH_WIN_8, | ||
1358 | HID_ANY_ID, HID_ANY_ID) }, | ||
1374 | { } | 1359 | { } |
1375 | }; | 1360 | }; |
1376 | MODULE_DEVICE_TABLE(hid, mt_devices); | 1361 | MODULE_DEVICE_TABLE(hid, mt_devices); |