This patch addresses a bug in certain Elantech-V1 touchpads, which report
invalid position data at the start of single-finger touches.
The patch is derived from this proposal
https://marc.info/?l=openbsd-tech&m=159957752322249&w=2
This version also removes two bits of obsolete code. wsmouse ignores
coordinate values when a driver signals that a contact has been released
(reporting any coordinates just avoids a branch in the caller code). Sorry
for coupling these issues, but opportunities for tests with v1- or v2-models
are rare.
OK?
Index: pms.c
===================================================================
RCS file: /cvs/src/sys/dev/pckbc/pms.c,v
retrieving revision 1.94
diff -u -p -r1.94 pms.c
--- pms.c 10 Aug 2020 21:55:59 -0000 1.94
+++ pms.c 12 Sep 2020 21:09:03 -0000
@@ -142,6 +142,7 @@ struct elantech_softc {
int max_x, max_y;
int old_x, old_y;
+ int initial_pkt;
};
#define ELANTECH_IS_CLICKPAD(sc) (((sc)->elantech->fw_version & 0x1000) != 0)
@@ -2443,15 +2444,29 @@ pms_proc_elantech_v1(struct pms_softc *s
else
w = (sc->packet[0] & 0xc0) >> 6;
+ /*
+ * Firmwares 0x20022 and 0x20600 have a bug, position data in the
+ * first two reports for single-touch contacts may be corrupt.
+ */
+ if (elantech->fw_version == 0x20022 ||
+ elantech->fw_version == 0x20600) {
+ if (w == 1) {
+ if (elantech->initial_pkt < 2) {
+ elantech->initial_pkt++;
+ return;
+ }
+ } else if (elantech->initial_pkt) {
+ elantech->initial_pkt = 0;
+ }
+ }
+
/* Hardware version 1 doesn't report pressure. */
if (w) {
x = ((sc->packet[1] & 0x0c) << 6) | sc->packet[2];
y = ((sc->packet[1] & 0x03) << 8) | sc->packet[3];
z = SYNAPTICS_PRESSURE;
} else {
- x = elantech->old_x;
- y = elantech->old_y;
- z = 0;
+ x = y = z = 0;
}
WSMOUSE_TOUCH(sc->sc_wsmousedev, buttons, x, y, z, w);
@@ -2488,9 +2503,7 @@ pms_proc_elantech_v2(struct pms_softc *s
y = (((sc->packet[0] & 0x20) << 3) | sc->packet[2]) << 2;
z = SYNAPTICS_PRESSURE;
} else {
- x = elantech->old_x;
- y = elantech->old_y;
- z = 0;
+ x = y = z = 0;
}
WSMOUSE_TOUCH(sc->sc_wsmousedev, buttons, x, y, z, w);