[PATCH 2/2] hid: multitouch: improve custom quirks kernel parameter

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



This allows a list of different quirks to be matched against
corresponding hardware ids in case there are multiple devices present on
the same system.

The code borrowed some idea from vfio_pci.c

Signed-off-by: Tao Jin <tao-j@xxxxxxxxxxx>
---
 drivers/hid/hid-multitouch.c | 32 ++++++++++++++++++++++++++------
 1 file changed, 26 insertions(+), 6 deletions(-)

diff --git a/drivers/hid/hid-multitouch.c b/drivers/hid/hid-multitouch.c
index c6d64f8..f662960 100644
--- a/drivers/hid/hid-multitouch.c
+++ b/drivers/hid/hid-multitouch.c
@@ -398,9 +398,9 @@ static const struct mt_class mt_classes[] = {
 	{ }
 };
 
-static int override_quirks = -1;
-module_param(override_quirks, int, 0444);
-MODULE_PARM_DESC(override_quirks, "Signed integer to override quirks in mtclass, must >= 0 to enable override.");
+static char override_quirks[128] = "";
+module_param_string(override_quirks, override_quirks, sizeof(override_quirks), 0444);
+MODULE_PARM_DESC(override_quirks, "List of quirks and corresponding device ids in hex to override quirks, format is \"wanted_quirks:vendor:product\", multiple comma separated entries can be specified.");
 
 static ssize_t mt_show_quirks(struct device *dev,
 			   struct device_attribute *attr,
@@ -1714,6 +1714,7 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id)
 	int ret, i;
 	struct mt_device *td;
 	const struct mt_class *mtclass = mt_classes; /* MT_CLS_DEFAULT */
+	char *p, *qk;
 
 	for (i = 0; mt_classes[i].name ; i++) {
 		if (id->driver_data == mt_classes[i].name) {
@@ -1753,9 +1754,28 @@ static int mt_probe(struct hid_device *hdev, const struct hid_device_id *id)
 	if (id->group != HID_GROUP_MULTITOUCH_WIN_8)
 		hdev->quirks |= HID_QUIRK_MULTI_INPUT;
 
-	if (override_quirks >= 0) {
-		hid_info(hdev, "overriding quirks with: %d(0x%x)", override_quirks, override_quirks);
-		td->mtclass.quirks = override_quirks;
+	p = override_quirks;
+	while ((qk = strsep(&p, ","))) {
+		__u32 wanted_quirks = 0;
+		__u32 vendor, product = HID_ANY_ID;
+		int fields;
+
+		if (!strlen(qk))
+			continue;
+
+		fields = sscanf(qk, "%x:%x:%x", &wanted_quirks,
+				&vendor, &product);
+
+		if (fields != 3) {
+			continue;
+		}
+
+		if (id->vendor == vendor && id->product == product) {
+			hid_info(hdev, "overriding quirks of %04x:%04x with: %x",
+					id->vendor, id->product, wanted_quirks);
+			td->mtclass.quirks = wanted_quirks;
+			break;
+		}
 	}
 
 	if (td->mtclass.quirks & MT_QUIRK_FORCE_MULTI_INPUT) {
-- 
2.35.1




[Index of Archives]     [Linux Media Devel]     [Linux USB Devel]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Linux Wireless Networking]     [Linux Omap]

  Powered by Linux