Skip to contentSkip to conversation

Getting recent elantech touchpads to work with synaptics

PATCH New Florian Ragwitz 2 participants 9 messages Apr 24, 2010 – Apr 27, 2010

Subsystems (3)
lore
Share & tools
lore
#0 lore raw

The following 4 patches aim to improve various bits of the the elantech support in the psmouse driver in order to get it to work with recent elantech firmwares used in many touchpads of modern laptops. The list of those laptops includes almost all recent ASUS machines, including the UL{2,3,5,8}0- and and P-series, but also various others, like many Dell Inspiron machines.

[PATCH 1/4] Input: elantech - Assume all firmware versions >= 2.48 use 6 byte packets

This patch just fixes a minor thinko in the handling of v1 vs. v2 firmware versions.

[PATCH 2/4] Input: Add an option to force the use of the elantech extension

This adds a force_elantech options to the psmouse module, which allows to force the use of the elantech extension if a device responds to the elantech magic knock and firmware version request, but the driver doesn't know about the particular firmware version yet.

[PATCH 3/4] Input: elantech - Ignore high bits in the position coordinates

This change is what actually makes things work on new firmwares. The driver used to use too many of the bits sent by the device to compute the position coordinates. On old versions all those bits were always zero, so it didn't actually matter, but new versions apparently reuse the bits for something else, screwing up results.

[PATCH 4/4] Input: elantech - Whitelist new models with firmware version 4.1

This broadens the range of devices which are automatically recognized as elantech to include all devices reporting the bytes 0x04 0x01 0x01 upon a firmware version request. The check is intentionally rather strict, and I assume there's other devices out there, which report slightly different versions, but would still work, but given how easy it is to test those devices with the force_elantech option, I figured the check could be relaxed later, if necessary, and it'd be better to avoid recognizing non-elantech devices wrongly.

Those patches are only tested on machines with firmware version 4.1. They should also be tested on older firmware versions using the 6-byte packet format, like any ASUS Eee PC, before being applied.

--
BOFH excuse #196:
Me no internet, only janitor, me just wax floors.

#1 lore raw

PATCH 1/4 Input: elantech - Assume all firmware versions >= 2.48 use 6 byte packets

This way firmware versions with a major version > 2, but a minor version < 48, like version 4.1, will be recognized correctly.

---
 drivers/input/mouse/elantech.c |    3 ++-
 1 files changed, 2 insertions(+), 1 deletions(-)
drivers/input/mouse/elantech.c +2 -1
index a138b5d..07f6b17 100644
@@ -666,7 +666,8 @@ int elantech_init(struct psmouse *psmouse)
 	 * Assume every version greater than this is new EeePC style
 	 * hardware with 6 byte packets
 	 */
-	if (etd->fw_version_maj >= 0x02 && etd->fw_version_min >= 0x30) {
+	if ((etd->fw_version_maj == 0x02 && etd->fw_version_min >= 0x30) ||
+	    etd->fw_version_maj > 0x02) {
 		etd->hw_version = 2;
 		/* For now show extra debug information */
 		etd->debug = 1;
Signature · 1 line
1.7.0.5
#2 lore raw

PATCH 2/4 Input: Add an option to force the use of the elantech extension

In reply to Florian Ragwitz

Apparently hardware vendors now ship elantech touchpads with different version magic. This options allows for them to be tested easier with the current driver in order to add their magic to the whitelist later.

---
 drivers/input/mouse/elantech.c |   12 ++++++++++--
 1 files changed, 10 insertions(+), 2 deletions(-)
drivers/input/mouse/elantech.c +10 -2
index 07f6b17..bfd08c7 100644
@@ -25,6 +25,10 @@
 			printk(KERN_DEBUG format, ##arg);	\
 	} while (0)
 
+static unsigned int force_elantech;
+module_param_named(force_elantech, force_elantech, bool, 0644);
+MODULE_PARM_DESC(force_elantech, "Force the Elantech PS/2 protocol extension to be used, 1 = enabled, 0 = disabled (default).");
+
 /*
  * Send a Synaptics style sliced query command
  */
@@ -596,8 +600,12 @@ int elantech_detect(struct psmouse *psmouse, bool set_properties)
 		 param[0], param[1], param[2]);
 
 	if (param[0] == 0 || param[1] != 0) {
-		pr_debug("elantech.c: Probably not a real Elantech touchpad. Aborting.\n");
-		return -1;
+		if (!force_elantech) {
+			pr_debug("elantech.c: Probably not a real Elantech touchpad. Aborting.\n");
+			return -1;
+		}
+
+		pr_debug("elantech.c: Probably not a real Elantech touchpad. Enabling anyway due to force_elantech.\n");
 	}
 
 	if (set_properties) {
Signature · 1 line
1.7.0.5
#3 lore raw

PATCH 3/4 Input: elantech - Ignore high bits in the position coordinates

In reply to Florian Ragwitz

In older versions of the elantech hardware/firmware those bits always were unset, so it didn't actually matter, but newer versions seem to use those high bits for something else, screwing up the coordinates we report to the input layer for those devices.

---
 drivers/input/mouse/elantech.c |    8 ++++----
 1 files changed, 4 insertions(+), 4 deletions(-)
drivers/input/mouse/elantech.c +4 -4
index bfd08c7..254a967 100644
@@ -251,13 +251,13 @@ static void elantech_report_absolute_v2(struct psmouse *psmouse)
 
 	switch (fingers) {
 	case 1:
-		/* byte 1: x15 x14 x13 x12 x11 x10 x9  x8
+		/* byte 1:  .   .   .   .   .  x10 x9  x8
 		   byte 2: x7  x6  x5  x4  x4  x2  x1  x0 */
-		input_report_abs(dev, ABS_X, (packet[1] << 8) | packet[2]);
-		/* byte 4: y15 y14 y13 y12 y11 y10 y8  y8
+		input_report_abs(dev, ABS_X, ((packet[1] & 0x07) << 8) | packet[2]);
+		/* byte 4:  .   .   .   .   .   .  y8  y8
 		   byte 5: y7  y6  y5  y4  y3  y2  y1  y0 */
 		input_report_abs(dev, ABS_Y, ETP_YMAX_V2 -
-			((packet[4] << 8) | packet[5]));
+			(((packet[4] & 0x03) << 8) | packet[5]));
 		break;
 
 	case 2:
Signature · 1 line
1.7.0.5
#4 lore raw

PATCH 4/4 Input: elantech - Whitelist new models with firmware version 4.1

In reply to Florian Ragwitz

The check is intentionally quite strict. It will probably need to be relaxed later, but given how easy it is to test a non-whitelisted firmware with force_elantech, that's OK.

---
 drivers/input/mouse/elantech.c |    3 ++-
 1 files changed, 2 insertions(+), 1 deletions(-)
drivers/input/mouse/elantech.c +2 -1
index 254a967..70321b7 100644
@@ -599,7 +599,8 @@ int elantech_detect(struct psmouse *psmouse, bool set_properties)
 	pr_debug("elantech.c: Elantech version query result 0x%02x, 0x%02x, 0x%02x.\n",
 		 param[0], param[1], param[2]);
 
-	if (param[0] == 0 || param[1] != 0) {
+	if ((param[0] == 0 || param[1] != 0) &&
+	    (param[0] != 4 && param[1] != 1 && param[2] != 1)) {
 		if (!force_elantech) {
 			pr_debug("elantech.c: Probably not a real Elantech touchpad. Aborting.\n");
 			return -1;
Signature · 1 line
1.7.0.5
#5 lore raw
In reply to Florian Ragwitz

This set of patches is now confirmed to work on various models of the UL30, a K60IJ, and an UL80V-B2.

I also got a chance to test the modifications on an EeePc, where things still Just Work, just as without the patches applied.

Signature · 2 lines
BOFH excuse #121:
halon system went off and killed the operators.
maintainer
#6 lore raw
Quoted 6 lines · Florian Ragwitz

This set of patches is now confirmed to work on various models of the UL30, a K60IJ, and an UL80V-B2.

I also got a chance to test the modifications on an EeePc, where things still Just Work, just as without the patches applied.

Florian, great work. I will queue the patches for .34, I think is not too late.

Thanks!

Signature · 1 line
Dmitry
#7 lore raw
Quoted 2 lines · Dmitry Torokhov

Florian, great work. I will queue the patches for .34, I think is not too late.

Great news. Thank you!

I also just noticed my initial patch updated the comments about the packet structure in the source code, but failed to update the relevant docs in Documentation/.

The following patch does just that.

[PATCH] Update elantech documentation

Signature · 2 lines
BOFH excuse #390:
Increased sunspot activity.
#8 lore raw

PATCH 1/1 Update elantech documentation

In reply to Dmitry Torokhov
---
 Documentation/input/elantech.txt |    8 ++++----
 1 files changed, 4 insertions(+), 4 deletions(-)
Documentation/input/elantech.txt +4 -4
index a10c3b6..56941ae 100644
@@ -333,14 +333,14 @@ byte 0:
 byte 1:
 
    bit   7   6   5   4   3   2   1   0
-        x15 x14 x13 x12 x11 x10 x9  x8
+         .   .   .   .   .  x10 x9  x8
 
 byte 2:
 
    bit   7   6   5   4   3   2   1   0
         x7  x6  x5  x4  x4  x2  x1  x0
 
-         x15..x0 = absolute x value (horizontal)
+         x10..x0 = absolute x value (horizontal)
 
 byte 3:
 
@@ -350,14 +350,14 @@ byte 3:
 byte 4:
 
    bit   7   6   5   4   3   2   1   0
-        y15 y14 y13 y12 y11 y10 y8  y8
+         .   .   .   .   .   .  y9  y8
 
 byte 5:
 
    bit   7   6   5   4   3   2   1   0
         y7  y6  y5  y4  y3  y2  y1  y0
 
-         y15..y0 = absolute y value (vertical)
+         y9..y0 = absolute y value (vertical)
 
 
 4.2.2 Two finger touch
Signature · 1 line
1.7.1