diff options
| -rw-r--r-- | drivers/hid/hid-multitouch.c | 31 |
1 files changed, 30 insertions, 1 deletions
diff --git a/drivers/hid/hid-multitouch.c b/drivers/hid/hid-multitouch.c index 099a7ada13c7..55551746d235 100644 --- a/drivers/hid/hid-multitouch.c +++ b/drivers/hid/hid-multitouch.c | |||
| @@ -44,6 +44,7 @@ | |||
| 44 | #include <linux/slab.h> | 44 | #include <linux/slab.h> |
| 45 | #include <linux/usb.h> | 45 | #include <linux/usb.h> |
| 46 | #include <linux/input/mt.h> | 46 | #include <linux/input/mt.h> |
| 47 | #include <linux/string.h> | ||
| 47 | 48 | ||
| 48 | 49 | ||
| 49 | MODULE_AUTHOR("Stephane Chatty <chatty@enac.fr>"); | 50 | MODULE_AUTHOR("Stephane Chatty <chatty@enac.fr>"); |
| @@ -260,6 +261,14 @@ static struct mt_class mt_classes[] = { | |||
| 260 | { } | 261 | { } |
| 261 | }; | 262 | }; |
| 262 | 263 | ||
| 264 | static void mt_free_input_name(struct hid_input *hi) | ||
| 265 | { | ||
| 266 | struct hid_device *hdev = hi->report->device; | ||
| 267 | |||
| 268 | if (hi->input->name != hdev->name) | ||
| 269 | kfree(hi->input->name); | ||
| 270 | } | ||
| 271 | |||
| 263 | static ssize_t mt_show_quirks(struct device *dev, | 272 | static ssize_t mt_show_quirks(struct device *dev, |
| 264 | struct device_attribute *attr, | 273 | struct device_attribute *attr, |
| 265 | char *buf) | 274 | char *buf) |
| @@ -403,6 +412,12 @@ static void mt_pen_report(struct hid_device *hid, struct hid_report *report) | |||
| 403 | static void mt_pen_input_configured(struct hid_device *hdev, | 412 | static void mt_pen_input_configured(struct hid_device *hdev, |
| 404 | struct hid_input *hi) | 413 | struct hid_input *hi) |
| 405 | { | 414 | { |
| 415 | char *name = kzalloc(strlen(hi->input->name) + 5, GFP_KERNEL); | ||
| 416 | if (name) { | ||
| 417 | sprintf(name, "%s Pen", hi->input->name); | ||
| 418 | mt_free_input_name(hi); | ||
| 419 | hi->input->name = name; | ||
| 420 | } | ||
| 406 | } | 421 | } |
| 407 | 422 | ||
| 408 | static int mt_touch_input_mapping(struct hid_device *hdev, struct hid_input *hi, | 423 | static int mt_touch_input_mapping(struct hid_device *hdev, struct hid_input *hi, |
| @@ -903,6 +918,10 @@ static void mt_post_parse(struct mt_device *td) | |||
| 903 | static void mt_input_configured(struct hid_device *hdev, struct hid_input *hi) | 918 | static void mt_input_configured(struct hid_device *hdev, struct hid_input *hi) |
| 904 | { | 919 | { |
| 905 | struct mt_device *td = hid_get_drvdata(hdev); | 920 | struct mt_device *td = hid_get_drvdata(hdev); |
| 921 | char *name = kstrdup(hdev->name, GFP_KERNEL); | ||
| 922 | |||
| 923 | if (name) | ||
| 924 | hi->input->name = name; | ||
| 906 | 925 | ||
| 907 | if (hi->report->id == td->mt_report_id) | 926 | if (hi->report->id == td->mt_report_id) |
| 908 | mt_touch_input_configured(hdev, hi); | 927 | mt_touch_input_configured(hdev, hi); |
| @@ -916,6 +935,7 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | |||
| 916 | int ret, i; | 935 | int ret, i; |
| 917 | struct mt_device *td; | 936 | struct mt_device *td; |
| 918 | struct mt_class *mtclass = mt_classes; /* MT_CLS_DEFAULT */ | 937 | struct mt_class *mtclass = mt_classes; /* MT_CLS_DEFAULT */ |
| 938 | struct hid_input *hi; | ||
| 919 | 939 | ||
| 920 | for (i = 0; mt_classes[i].name ; i++) { | 940 | for (i = 0; mt_classes[i].name ; i++) { |
| 921 | if (id->driver_data == mt_classes[i].name) { | 941 | if (id->driver_data == mt_classes[i].name) { |
| @@ -966,7 +986,7 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | |||
| 966 | 986 | ||
| 967 | ret = hid_hw_start(hdev, HID_CONNECT_DEFAULT); | 987 | ret = hid_hw_start(hdev, HID_CONNECT_DEFAULT); |
| 968 | if (ret) | 988 | if (ret) |
| 969 | goto fail; | 989 | goto hid_fail; |
| 970 | 990 | ||
| 971 | ret = sysfs_create_group(&hdev->dev.kobj, &mt_attribute_group); | 991 | ret = sysfs_create_group(&hdev->dev.kobj, &mt_attribute_group); |
| 972 | 992 | ||
| @@ -978,6 +998,9 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) | |||
| 978 | 998 | ||
| 979 | return 0; | 999 | return 0; |
| 980 | 1000 | ||
| 1001 | hid_fail: | ||
| 1002 | list_for_each_entry(hi, &hdev->inputs, list) | ||
| 1003 | mt_free_input_name(hi); | ||
| 981 | fail: | 1004 | fail: |
| 982 | kfree(td->fields); | 1005 | kfree(td->fields); |
| 983 | kfree(td); | 1006 | kfree(td); |
| @@ -1007,8 +1030,14 @@ static int mt_resume(struct hid_device *hdev) | |||
| 1007 | static void mt_remove(struct hid_device *hdev) | 1030 | static void mt_remove(struct hid_device *hdev) |
| 1008 | { | 1031 | { |
| 1009 | struct mt_device *td = hid_get_drvdata(hdev); | 1032 | struct mt_device *td = hid_get_drvdata(hdev); |
| 1033 | struct hid_input *hi; | ||
| 1034 | |||
| 1010 | sysfs_remove_group(&hdev->dev.kobj, &mt_attribute_group); | 1035 | sysfs_remove_group(&hdev->dev.kobj, &mt_attribute_group); |
| 1011 | hid_hw_stop(hdev); | 1036 | hid_hw_stop(hdev); |
| 1037 | |||
| 1038 | list_for_each_entry(hi, &hdev->inputs, list) | ||
| 1039 | mt_free_input_name(hi); | ||
| 1040 | |||
| 1012 | kfree(td); | 1041 | kfree(td); |
| 1013 | hid_set_drvdata(hdev, NULL); | 1042 | hid_set_drvdata(hdev, NULL); |
| 1014 | } | 1043 | } |
