aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/hid
diff options
context:
space:
mode:
authorHenrik Rydberg <rydberg@euromail.se>2012-09-01 14:11:34 -0400
committerHenrik Rydberg <rydberg@euromail.se>2012-09-19 13:50:20 -0400
commit76f5902aebdabcac5b1c34b8d9a238bad397364f (patch)
tree9d8aa7531ceff493700d59ae988fa9545b3029cd /drivers/hid
parent7e55bdedfa4a72baa0d4fec8d0948cb65342a9a0 (diff)
HID: hid-multitouch: Simplify setup and frame synchronization
With the input_configured() callback in place, the setup and frame synchronization can be simplified. The input device initialization is moved to mt_input_configured(), to make sure the full HID report has been seen. Reviewed-and-tested-by: Benjamin Tissoires <benjamin.tissoires@enac.fr> Acked-by: Jiri Kosina <jkosina@suse.cz> Signed-off-by: Henrik Rydberg <rydberg@euromail.se>
Diffstat (limited to 'drivers/hid')
-rw-r--r--drivers/hid/hid-multitouch.c67
1 files changed, 38 insertions, 29 deletions
diff --git a/drivers/hid/hid-multitouch.c b/drivers/hid/hid-multitouch.c
index c400d9008774..1df86a7536b8 100644
--- a/drivers/hid/hid-multitouch.c
+++ b/drivers/hid/hid-multitouch.c
@@ -92,8 +92,10 @@ struct mt_device {
92 __u8 touches_by_report; /* how many touches are present in one report: 92 __u8 touches_by_report; /* how many touches are present in one report:
93 * 1 means we should use a serial protocol 93 * 1 means we should use a serial protocol
94 * > 1 means hybrid (multitouch) protocol */ 94 * > 1 means hybrid (multitouch) protocol */
95 bool serial_maybe; /* need to check for serial protocol */
95 bool curvalid; /* is the current contact valid? */ 96 bool curvalid; /* is the current contact valid? */
96 struct mt_slot *slots; 97 struct mt_slot *slots;
98 unsigned mt_flags; /* flags to pass to input-mt */
97}; 99};
98 100
99/* classes of device behavior */ 101/* classes of device behavior */
@@ -319,24 +321,16 @@ static int mt_input_mapping(struct hid_device *hdev, struct hid_input *hi,
319 * We need to ignore fields that belong to other collections 321 * We need to ignore fields that belong to other collections
320 * such as Mouse that might have the same GenericDesktop usages. */ 322 * such as Mouse that might have the same GenericDesktop usages. */
321 if (field->application == HID_DG_TOUCHSCREEN) 323 if (field->application == HID_DG_TOUCHSCREEN)
322 set_bit(INPUT_PROP_DIRECT, hi->input->propbit); 324 td->mt_flags |= INPUT_MT_DIRECT;
323 else if (field->application != HID_DG_TOUCHPAD) 325 else if (field->application != HID_DG_TOUCHPAD)
324 return 0; 326 return 0;
325 327
326 /* In case of an indirect device (touchpad), we need to add 328 /*
327 * specific BTN_TOOL_* to be handled by the synaptics xorg 329 * Model touchscreens providing buttons as touchpads.
328 * driver.
329 * We also consider that touchscreens providing buttons are touchpads.
330 */ 330 */
331 if (field->application == HID_DG_TOUCHPAD || 331 if (field->application == HID_DG_TOUCHPAD ||
332 (usage->hid & HID_USAGE_PAGE) == HID_UP_BUTTON || 332 (usage->hid & HID_USAGE_PAGE) == HID_UP_BUTTON)
333 cls->is_indirect) { 333 td->mt_flags |= INPUT_MT_POINTER;
334 set_bit(INPUT_PROP_POINTER, hi->input->propbit);
335 set_bit(BTN_TOOL_FINGER, hi->input->keybit);
336 set_bit(BTN_TOOL_DOUBLETAP, hi->input->keybit);
337 set_bit(BTN_TOOL_TRIPLETAP, hi->input->keybit);
338 set_bit(BTN_TOOL_QUADTAP, hi->input->keybit);
339 }
340 334
341 /* eGalax devices provide a Digitizer.Stylus input which overrides 335 /* eGalax devices provide a Digitizer.Stylus input which overrides
342 * the correct Digitizers.Finger X/Y ranges. 336 * the correct Digitizers.Finger X/Y ranges.
@@ -353,8 +347,6 @@ static int mt_input_mapping(struct hid_device *hdev, struct hid_input *hi,
353 EV_ABS, ABS_MT_POSITION_X); 347 EV_ABS, ABS_MT_POSITION_X);
354 set_abs(hi->input, ABS_MT_POSITION_X, field, 348 set_abs(hi->input, ABS_MT_POSITION_X, field,
355 cls->sn_move); 349 cls->sn_move);
356 /* touchscreen emulation */
357 set_abs(hi->input, ABS_X, field, cls->sn_move);
358 mt_store_field(usage, td, hi); 350 mt_store_field(usage, td, hi);
359 td->last_field_index = field->index; 351 td->last_field_index = field->index;
360 return 1; 352 return 1;
@@ -363,8 +355,6 @@ static int mt_input_mapping(struct hid_device *hdev, struct hid_input *hi,
363 EV_ABS, ABS_MT_POSITION_Y); 355 EV_ABS, ABS_MT_POSITION_Y);
364 set_abs(hi->input, ABS_MT_POSITION_Y, field, 356 set_abs(hi->input, ABS_MT_POSITION_Y, field,
365 cls->sn_move); 357 cls->sn_move);
366 /* touchscreen emulation */
367 set_abs(hi->input, ABS_Y, field, cls->sn_move);
368 mt_store_field(usage, td, hi); 358 mt_store_field(usage, td, hi);
369 td->last_field_index = field->index; 359 td->last_field_index = field->index;
370 return 1; 360 return 1;
@@ -388,9 +378,6 @@ static int mt_input_mapping(struct hid_device *hdev, struct hid_input *hi,
388 td->last_field_index = field->index; 378 td->last_field_index = field->index;
389 return 1; 379 return 1;
390 case HID_DG_CONTACTID: 380 case HID_DG_CONTACTID:
391 if (!td->maxcontacts)
392 td->maxcontacts = MT_DEFAULT_MAXCONTACT;
393 input_mt_init_slots(hi->input, td->maxcontacts, 0);
394 mt_store_field(usage, td, hi); 381 mt_store_field(usage, td, hi);
395 td->last_field_index = field->index; 382 td->last_field_index = field->index;
396 td->touches_by_report++; 383 td->touches_by_report++;
@@ -418,9 +405,6 @@ static int mt_input_mapping(struct hid_device *hdev, struct hid_input *hi,
418 EV_ABS, ABS_MT_PRESSURE); 405 EV_ABS, ABS_MT_PRESSURE);
419 set_abs(hi->input, ABS_MT_PRESSURE, field, 406 set_abs(hi->input, ABS_MT_PRESSURE, field,
420 cls->sn_pressure); 407 cls->sn_pressure);
421 /* touchscreen emulation */
422 set_abs(hi->input, ABS_PRESSURE, field,
423 cls->sn_pressure);
424 mt_store_field(usage, td, hi); 408 mt_store_field(usage, td, hi);
425 td->last_field_index = field->index; 409 td->last_field_index = field->index;
426 return 1; 410 return 1;
@@ -536,7 +520,7 @@ static void mt_emit_event(struct mt_device *td, struct input_dev *input)
536 520
537 } 521 }
538 522
539 input_mt_report_pointer_emulation(input, true); 523 input_mt_sync_frame(input);
540 input_sync(input); 524 input_sync(input);
541 td->num_received = 0; 525 td->num_received = 0;
542} 526}
@@ -685,6 +669,32 @@ static void mt_post_parse(struct mt_device *td)
685 } 669 }
686} 670}
687 671
672static void mt_input_configured(struct hid_device *hdev, struct hid_input *hi)
673
674{
675 struct mt_device *td = hid_get_drvdata(hdev);
676 struct mt_class *cls = &td->mtclass;
677 struct input_dev *input = hi->input;
678
679 /* Only initialize slots for MT input devices */
680 if (!test_bit(ABS_MT_POSITION_X, input->absbit))
681 return;
682
683 if (!td->maxcontacts)
684 td->maxcontacts = MT_DEFAULT_MAXCONTACT;
685
686 mt_post_parse(td);
687 if (td->serial_maybe)
688 mt_post_parse_default_settings(td);
689
690 if (cls->is_indirect)
691 td->mt_flags |= INPUT_MT_POINTER;
692
693 input_mt_init_slots(input, td->maxcontacts, td->mt_flags);
694
695 td->mt_flags = 0;
696}
697
688static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id) 698static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id)
689{ 699{
690 int ret, i; 700 int ret, i;
@@ -722,6 +732,9 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id)
722 goto fail; 732 goto fail;
723 } 733 }
724 734
735 if (id->vendor == HID_ANY_ID && id->product == HID_ANY_ID)
736 td->serial_maybe = true;
737
725 ret = hid_parse(hdev); 738 ret = hid_parse(hdev);
726 if (ret != 0) 739 if (ret != 0)
727 goto fail; 740 goto fail;
@@ -730,11 +743,6 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id)
730 if (ret) 743 if (ret)
731 goto fail; 744 goto fail;
732 745
733 mt_post_parse(td);
734
735 if (id->vendor == HID_ANY_ID && id->product == HID_ANY_ID)
736 mt_post_parse_default_settings(td);
737
738 td->slots = kzalloc(td->maxcontacts * sizeof(struct mt_slot), 746 td->slots = kzalloc(td->maxcontacts * sizeof(struct mt_slot),
739 GFP_KERNEL); 747 GFP_KERNEL);
740 if (!td->slots) { 748 if (!td->slots) {
@@ -1087,6 +1095,7 @@ static struct hid_driver mt_driver = {
1087 .remove = mt_remove, 1095 .remove = mt_remove,
1088 .input_mapping = mt_input_mapping, 1096 .input_mapping = mt_input_mapping,
1089 .input_mapped = mt_input_mapped, 1097 .input_mapped = mt_input_mapped,
1098 .input_configured = mt_input_configured,
1090 .feature_mapping = mt_feature_mapping, 1099 .feature_mapping = mt_feature_mapping,
1091 .usage_table = mt_grabbed_usages, 1100 .usage_table = mt_grabbed_usages,
1092 .event = mt_event, 1101 .event = mt_event,