@@ -54,10 +54,10 @@ struct lenovo_drvdata {
54
54
/* 0: Up
55
55
* 1: Down (undecided)
56
56
* 2: Scrolling
57
- * 3: Patched firmware, disable workaround
58
57
*/
59
58
u8 middlebutton_state ;
60
59
bool fn_lock ;
60
+ bool middleclick_workaround_cptkbd ;
61
61
};
62
62
63
63
#define map_key_clear (c ) hid_map_usage_clear(hi, usage, bit, max, EV_KEY, (c))
@@ -621,6 +621,36 @@ static ssize_t attr_sensitivity_store_cptkbd(struct device *dev,
621
621
return count ;
622
622
}
623
623
624
+ static ssize_t attr_middleclick_workaround_show_cptkbd (struct device * dev ,
625
+ struct device_attribute * attr ,
626
+ char * buf )
627
+ {
628
+ struct hid_device * hdev = to_hid_device (dev );
629
+ struct lenovo_drvdata * cptkbd_data = hid_get_drvdata (hdev );
630
+
631
+ return snprintf (buf , PAGE_SIZE , "%u\n" ,
632
+ cptkbd_data -> middleclick_workaround_cptkbd );
633
+ }
634
+
635
+ static ssize_t attr_middleclick_workaround_store_cptkbd (struct device * dev ,
636
+ struct device_attribute * attr ,
637
+ const char * buf ,
638
+ size_t count )
639
+ {
640
+ struct hid_device * hdev = to_hid_device (dev );
641
+ struct lenovo_drvdata * cptkbd_data = hid_get_drvdata (hdev );
642
+ int value ;
643
+
644
+ if (kstrtoint (buf , 10 , & value ))
645
+ return - EINVAL ;
646
+ if (value < 0 || value > 1 )
647
+ return - EINVAL ;
648
+
649
+ cptkbd_data -> middleclick_workaround_cptkbd = !!value ;
650
+
651
+ return count ;
652
+ }
653
+
624
654
625
655
static struct device_attribute dev_attr_fn_lock =
626
656
__ATTR (fn_lock , S_IWUSR | S_IRUGO ,
@@ -632,10 +662,16 @@ static struct device_attribute dev_attr_sensitivity_cptkbd =
632
662
attr_sensitivity_show_cptkbd ,
633
663
attr_sensitivity_store_cptkbd );
634
664
665
+ static struct device_attribute dev_attr_middleclick_workaround_cptkbd =
666
+ __ATTR (middleclick_workaround , S_IWUSR | S_IRUGO ,
667
+ attr_middleclick_workaround_show_cptkbd ,
668
+ attr_middleclick_workaround_store_cptkbd );
669
+
635
670
636
671
static struct attribute * lenovo_attributes_cptkbd [] = {
637
672
& dev_attr_fn_lock .attr ,
638
673
& dev_attr_sensitivity_cptkbd .attr ,
674
+ & dev_attr_middleclick_workaround_cptkbd .attr ,
639
675
NULL
640
676
};
641
677
@@ -686,23 +722,7 @@ static int lenovo_event_cptkbd(struct hid_device *hdev,
686
722
{
687
723
struct lenovo_drvdata * cptkbd_data = hid_get_drvdata (hdev );
688
724
689
- if (cptkbd_data -> middlebutton_state != 3 ) {
690
- /* REL_X and REL_Y events during middle button pressed
691
- * are only possible on patched, bug-free firmware
692
- * so set middlebutton_state to 3
693
- * to never apply workaround anymore
694
- */
695
- if (hdev -> product == USB_DEVICE_ID_LENOVO_CUSBKBD &&
696
- cptkbd_data -> middlebutton_state == 1 &&
697
- usage -> type == EV_REL &&
698
- (usage -> code == REL_X || usage -> code == REL_Y )) {
699
- cptkbd_data -> middlebutton_state = 3 ;
700
- /* send middle button press which was hold before */
701
- input_event (field -> hidinput -> input ,
702
- EV_KEY , BTN_MIDDLE , 1 );
703
- input_sync (field -> hidinput -> input );
704
- }
705
-
725
+ if (cptkbd_data -> middleclick_workaround_cptkbd ) {
706
726
/* "wheel" scroll events */
707
727
if (usage -> type == EV_REL && (usage -> code == REL_WHEEL ||
708
728
usage -> code == REL_HWHEEL )) {
@@ -1166,6 +1186,7 @@ static int lenovo_probe_cptkbd(struct hid_device *hdev)
1166
1186
cptkbd_data -> middlebutton_state = 0 ;
1167
1187
cptkbd_data -> fn_lock = true;
1168
1188
cptkbd_data -> sensitivity = 0x05 ;
1189
+ cptkbd_data -> middleclick_workaround_cptkbd = true;
1169
1190
lenovo_features_set_cptkbd (hdev );
1170
1191
1171
1192
ret = sysfs_create_group (& hdev -> dev .kobj , & lenovo_attr_group_cptkbd );
0 commit comments