Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 29 Jul 2004 02:32:08 +0900
From:      Norikatsu Shigemura <nork@FreeBSD.org>
To:        freebsd-stable@FreeBSD.org
Subject:   TEST PLEASE: Synaptics Touchpad on 4-stable
Message-ID:  <20040729023208.51e1cd3b.nork@FreeBSD.org>

next in thread | raw e-mail | index | archive | help

[-- Attachment #1 --]
	I wrote synaptic touchpad driver for 4-stable, based on
	Arne Schwabe's driver.  I don't have synaptic touchpad
	on 4-stable.  I just did compile test.  I don't know
	whether or not good :-).  So please test.

[-- Attachment #2 --]
--- src/sys/isa/psm.c.orig	Tue Jul 20 03:52:45 2004
+++ src/sys/isa/psm.c	Thu Jul 29 02:17:20 2004
@@ -159,6 +159,7 @@
     struct resource *intr;	/* IRQ resource */
     void	  *ih;		/* interrupt handle */
     mousehw_t     hw;		/* hardware information */
+    synapticshw_t synhw;	/* Synaptics specific hardware information */
     mousemode_t   mode;		/* operation mode */
     mousemode_t   dflt_mode;	/* default operation mode */
     mousestatus_t status;	/* accumulated mouse movement */
@@ -277,6 +278,7 @@
 static probefunc_t enable_4dmouse;
 static probefunc_t enable_4dplus;
 static probefunc_t enable_mmanplus;
+static probefunc_t enable_synaptics;
 static probefunc_t enable_versapad;
 static int tame_mouse __P((struct psm_softc *, mousestatus_t *, unsigned char *));
 
@@ -310,6 +312,8 @@
       0x80, MOUSE_PS2_PACKETSIZE, enable_kmouse, },
     { MOUSE_MODEL_VERSAPAD,		/* Interlink electronics VersaPad */
       0xe8, MOUSE_PS2VERSA_PACKETSIZE, enable_versapad, },
+    { MOUSE_MODEL_SYNAPTICS,		/* Synaptics Touchpad */
+      0xc0, MOUSE_SYNAPTICS_PACKETSIZE, enable_synaptics, },
     { MOUSE_MODEL_GENERIC,
       0xc0, MOUSE_PS2_PACKETSIZE, NULL, },
 };
@@ -579,6 +583,7 @@
         { MOUSE_MODEL_EXPLORER,		"IntelliMouse Explorer" },
         { MOUSE_MODEL_4D,		"4D Mouse" },
         { MOUSE_MODEL_4DPLUS,		"4D+ Mouse" },
+        { MOUSE_MODEL_SYNAPTICS,	"Synaptics Touchpad" },
         { MOUSE_MODEL_GENERIC,		"Generic PS/2 mouse" },
         { MOUSE_MODEL_UNKNOWN,		NULL },
     };
@@ -1683,6 +1688,12 @@
 	splx(s);
         break;
 
+    case MOUSE_SYNGETHWINFO:
+       s = spltty();
+       *(synapticshw_t *)addr = sc->synhw;
+       splx(s);
+       break;
+
     case OLD_MOUSE_GETMODE:
 	s = spltty();
 	switch (sc->mode.level) {
@@ -1860,6 +1871,28 @@
 	unblock_mouse_data(sc, command_byte);
 	break;
 
+    case MOUSE_SYNAPTICS_CMD:
+       if (sc->hw.model != MOUSE_MODEL_SYNAPTICS || sc->mode.level < PSM_LEVEL_NATIVE)
+           return EINVAL;
+
+       mouse_ext_command(sc->kbdc, *(int *)addr); 
+       set_mouse_sampling_rate(sc->kbdc, 0x0014);
+       break;
+
+    case MOUSE_SYNAPTICS_INFO:
+       if (sc->hw.model != MOUSE_MODEL_SYNAPTICS || sc->mode.level < PSM_LEVEL_NATIVE)
+           return EINVAL;
+
+       mouse_ext_command(sc->kbdc, *(int *)addr); 
+       send_aux_command(sc->kbdc, PSMC_SEND_DEV_STATUS);
+       set_mouse_sampling_rate(sc->kbdc, 0x0014);
+       break;
+
+    case MOUSE_SYNAPTICS_ENABLE_PASSTHROUGH:
+       if (sc->hw.model != MOUSE_MODEL_SYNAPTICS || sc->mode.level < PSM_LEVEL_NATIVE)
+               return EINVAL;
+       break;
+
 #if (defined(MOUSE_SETRESOLUTION))
     case MOUSE_SETRESOLUTION:
 	mode.resolution = *(int *)addr;
@@ -1992,7 +2025,7 @@
     register struct psm_softc *sc = arg;
     mousestatus_t ms;
     struct timeval tv;
-    int x, y, z;
+    int x, y, z, w;
     int c;
     int l;
     int x0, y0;
@@ -2325,6 +2358,86 @@
 	    }
 	    break;
 
+       case MOUSE_MODEL_SYNAPTICS:
+           /* TouchPad PS/2 absolute mode message format
+            *
+            *  Bits:        7   6   5   4   3   2   1   0 (LSB)
+            *  ------------------------------------------------
+            *  ipacket[0]:  1   0  W3  W2   0  W1   R   L
+            *  ipacket[1]: Yb  Ya  Y9  Y8  Xb  Xa  X9  X8
+            *  ipacket[2]: Z7  Z6  Z5  Z4  Z3  Z2  Z1  Z0
+            *  ipacket[3]:  1   1  Yc  Xc   0  W0   D   U
+            *  ipacket[4]: X7  X6  X5  X4  X3  X2  X1  X0
+            *  ipacket[5]: Y7  Y6  Y5  Y4  Y3  Y2  Y1  Y0
+            *
+            * Legend:
+            *  L: left physical mouse button
+            *  R: right physical mouse button
+            *  D: down button
+            *  U: up button
+            *  W: "wrist" value
+            *  X: x position
+            *  Y: x position
+            *  Z: pressure
+            *
+            * Absolute reportable limits:    0 - 6143.
+            * Typical bezel limites:      1472 - 5472.
+            * Typical edge marings:       1632 - 5312.
+            * w = 3 Passthrough Packet
+            * (I hope I guessed right, but looks as if I had luck :))
+            *
+            * Byte 2,5,6 == Byte 1,2,3 of "Guest"
+            */
+
+           /* Sanity check for out of sync packets. */
+           if ((sc->ipacket[0] & 0xc8) != 0x80 || (sc->ipacket[3] & 0xc8) != 0xc0)
+               continue;
+
+           x = y = x0 = y0 = 0;
+
+           /* pressure */
+           z = sc->ipacket[2];
+           w = ((sc->ipacket[0] & 0x30) >> 2) |
+               ((sc->ipacket[0] & 0x04) >> 1) |
+               ((sc->ipacket[3] & 0x04) >> 2);
+
+           ms.button = 0;
+           if (sc->ipacket[0] & 0x01)
+               ms.button |= MOUSE_BUTTON1DOWN;
+           if (sc->ipacket[0] & 0x02)
+               ms.button |= MOUSE_BUTTON3DOWN;
+
+           if ((sc->ipacket[3] & 0x01) && !(sc->ipacket[0] & 0x01))
+               ms.button |= MOUSE_BUTTON2DOWN;
+           if ((sc->ipacket[3] & 0x02) && !(sc->ipacket[0] & 0x02))
+               ms.button |= MOUSE_BUTTON4DOWN;
+
+           /* There is a finger on the pad */
+           if ((w >= 4 && w <= 7) && (z >= 16 && z < 200) ) {
+               x0 = ((sc->ipacket[3] & 0x10) << 8) | ((sc->ipacket[1] & 0x0f) << 8) |
+                   sc->ipacket[4];
+               y0 = ((sc->ipacket[3] & 0x20) << 7) | ((sc->ipacket[1] & 0xf0) << 4) |
+                   sc->ipacket[5];
+
+               if (sc->flags & PSM_FLAGS_FINGERDOWN) {
+                   x0 = (x0 + sc->xold * 3) / 4;
+                   y0 = (y0 + sc->yold * 3) / 4;
+
+                   x = (x0 - sc->xold) / 4;
+                   y = (y0 - sc->yold) / 4;
+               } else {
+                   sc->flags |= PSM_FLAGS_FINGERDOWN;
+               }
+
+               sc->xold = x0;
+               sc->yold = y0;
+           } else {
+               sc->flags &= ~PSM_FLAGS_FINGERDOWN;
+           }
+           z = 0;
+           break;
+
+
 	case MOUSE_MODEL_GENERIC:
 	default:
 	    break;
@@ -2541,6 +2654,127 @@
         return FALSE;
     if ((status[1] == PSMD_RES_LOW) || (status[2] == 100))
         return FALSE;
+    return TRUE;
+}
+
+
+/* Synaptics Touchpad */
+static int
+enable_synaptics(struct psm_softc *sc)
+{
+    int status[3];
+
+    KBDC kbdc = sc->kbdc;
+
+    disable_aux_dev(kbdc);
+    set_mouse_scaling(kbdc, 1);	/* Just to be on the safe side */
+ 
+    if(!mouse_ext_command(kbdc, 0))
+	return FALSE;
+
+    if( get_mouse_status(kbdc, status, 0, 3) != 3)
+	return FALSE;
+
+    if(status[1] != 0x47)	/* If it is a Synaptics byte2 is $47 */
+	return FALSE;
+
+    /* Identify the Touchpad version number */
+    sc->synhw.infoMinor = status[0];	/* the first Byte contains the minor version number */
+    /* the lower 4 bits of third Byte contain the infoMajor */
+    /* the upper 4 bits of third Byte contain the (obsolte) infoModelCode */
+    sc->synhw.infoMajor = status[2] & 0x0f;
+    if(verbose >= 2) {
+	printf("Synaptics Touchpad:\n");
+	printf("  Version: %d.%d\n", sc->synhw.infoMajor, sc->synhw.infoMinor);
+    }
+
+    if(sc->synhw.infoMajor < 4) {
+	printf("Synaptics prior Version 4 detected, this is not (yet?) supported\n");
+	return FALSE;
+    }
+
+    if(!mouse_ext_command(kbdc, 3))
+	return FALSE;
+
+    if(get_mouse_status(kbdc, status, 0, 3) != 3)
+	return FALSE;
+
+    if((status[1] & 0x01) != 0) {
+	printf("  Could not read Model id Bytes from the Touchpad");
+	return FALSE;
+    }
+
+    sc->synhw.infoRot180   = (status[0] & 0x80) >> 7;
+    sc->synhw.infoPortrait = (status[0] & 0x40) >> 6;
+    sc->synhw.infoSensor   =  status[0] & 0x3f;
+    sc->synhw.infoHardware = (status[1] & 0xfe) >> 1;
+    sc->synhw.infoNewAbs   = (status[2] & 0x80) >> 7;
+    sc->synhw.capPen       = (status[2] & 0x40) >> 6;
+    sc->synhw.infoSimplC   = (status[2] & 0x20) >> 5;
+    sc->synhw.infoGeometry =  status[2] & 0x0f;
+    if(verbose >= 2) {
+	printf("  Model id: %02x %02x %02x\n", status[0] , status[1] , status[2]);
+	printf(" infoRot180: %d\n",sc->synhw.infoRot180);
+	printf(" infoPortrait: %d\n",sc->synhw.infoPortrait);
+	printf(" infoSensor: %d\n",sc->synhw.infoSensor);
+	printf(" infoHardware: %d\n",sc->synhw.infoHardware);
+	printf(" infoNewAbs: %d\n",sc->synhw.infoNewAbs);
+	printf(" capPen: %d\n",sc->synhw.capPen);
+	printf(" infoSimplC: %d\n",sc->synhw.infoSimplC);
+	printf(" infoGeometry: %d\n",sc->synhw.infoGeometry);
+    }
+
+    if(!mouse_ext_command(kbdc, 2))
+	return FALSE;
+
+    if(get_mouse_status(kbdc, status, 0, 3) != 3)
+	return FALSE;
+
+    if(status[1] != 0x47) {
+	printf("  Could not read Capabilities from the Touchpad\n");
+	return FALSE;
+    }
+
+    sc->synhw.capExtended    = (status[0] & 0x80) >> 7;
+    sc->synhw.capPassthrough = (status[2] & 0x80) >> 7;
+    sc->synhw.capSleep       = (status[2] & 0x10) >> 4;
+    sc->synhw.capFourButtons = (status[2] & 0x08) >> 3;
+    sc->synhw.capMultiFinger = (status[2] & 0x02) >> 1;
+    sc->synhw.capPalmDetect  = (status[2] & 0x01);
+    if(verbose >= 2) {
+	printf("  Capability Bytes: %02x %02x %02x\n", status[0], status[1], status[2]);
+    }
+
+
+    if(!mouse_ext_command(kbdc, 1))
+	return FALSE;
+
+    if(get_mouse_status(kbdc, status, 0, 3) != 3)
+	return FALSE;
+
+    if(status[0] != 0x3b || status[1] != 0x47) {
+	printf("  Could not read Mode Byte from the Touchpad\n");
+	return FALSE;
+    }
+
+    if(verbose >= 2)
+      printf("  Mode Byte set by Bios: %02x\n" , status[2]);
+
+    /* Mode Byte
+	1 (absolute)
+	1 rate (0 = 40/1 = 80)
+	0
+	0 (reserved)
+	0 (Sleep (Only buttons))
+	0 DisGest (not for absolute Mode)
+	0 pktsize (0 for ps2)
+	1 wmode
+     */
+    sc->hw.buttons = 3;
+
+    mouse_ext_command(kbdc, 0xc1);	/* encode mode byte */
+    set_mouse_sampling_rate(kbdc, 0x0014); /* set mode byte */
+
     return TRUE;
 }
 
--- src/sys/i386/include/mouse.h.orig	Tue Apr 16 01:54:14 2002
+++ src/sys/i386/include/mouse.h	Thu Jul 29 02:19:03 2004
@@ -40,6 +40,10 @@
 #define MOUSE_SETVARS		_IOW('M', 7, mousevar_t)
 #define MOUSE_READSTATE		_IOWR('M', 8, mousedata_t)
 #define MOUSE_READDATA		_IOWR('M', 9, mousedata_t)
+#define MOUSE_SYNAPTICS_CMD	_IOW('M', 10, char)
+#define MOUSE_SYNAPTICS_INFO	_IOW('M', 11, char)
+#define MOUSE_SYNAPTICS_ENABLE_PASSTHROUGH	_IOW('M', 12, char)
+#define MOUSE_SYNGETHWINFO	_IOR('M', 13, synapticshw_t)
 
 #if notyet
 #define MOUSE_SETRESOLUTION	_IOW('M', 10, int)
@@ -88,6 +92,25 @@
 				 */
 } mousehw_t;
 
+typedef struct synapticshw {
+	int infoMajor;
+	int infoMinor;
+	int infoRot180;
+	int infoPortrait;
+	int infoSensor;
+	int infoHardware;
+	int infoNewAbs;
+	int capPen;
+	int infoSimplC;
+	int infoGeometry;
+	int capExtended;
+	int capSleep;
+	int capFourButtons;
+	int capMultiFinger;
+	int capPalmDetect;
+	int capPassthrough;
+} synapticshw_t;
+
 /* iftype */
 #define MOUSE_IF_UNKNOWN	(-1)
 #define MOUSE_IF_SERIAL		0
@@ -119,6 +142,7 @@
 #define MOUSE_MODEL_EXPLORER		10
 #define MOUSE_MODEL_4D			11
 #define MOUSE_MODEL_4DPLUS		12
+#define MOUSE_MODEL_SYNAPTICS		13
 
 typedef struct mousemode {
 	int protocol;		/* MOUSE_PROTO_XXX */
@@ -184,6 +208,10 @@
 #define MOUSE_VARS_INPORT_SIG	0x00504e49	/* 'INP' */
 
 #endif /* MOUSE_GETVARS */
+
+/* Synaptics Touchpad */
+#define MOUSE_SYNAPTICS_PACKETSIZE	6
+/* Packetsize 6 is the real packetsize but that 3 works better :) */
 
 /* Microsoft Serial mouse data packet */
 #define MOUSE_MSS_PACKETSIZE	3

[-- Attachment #3 --]
# This is a shell archive.  Save it in a file, remove anything before
# this line, and then unpack it by entering "sh file".  Note, it may
# create directories; files and directories will be owned by you and
# have default permissions.
#
# This archive contains:
#
#	synaptics/Makefile
#	synaptics/distinfo
#	synaptics/pkg-descr
#	synaptics/pkg-plist
#
echo x - synaptics/Makefile
sed 's/^X//' >synaptics/Makefile << 'END-of-synaptics/Makefile'
X# New ports collection makefile for:    synaptics
X# Date created:				2004/01/02
X# Whom:					nork@FreeBSD.org
X#
X# $FreeBSD$
X#
X
XPORTNAME=	synaptics
XPORTVERSION=	0.12.5
XCATEGORIES=	x11-servers
XMASTER_SITES=	http://w1.894.telia.com/~u89404340/touchpad/files/
XEXTRACT_SUFX=	.tar.bz2
X
XPATCH_SITES=	http://www.plaisthos.de/freebsd/
XPATCHFILES=	synaptics.driver.patch
XPATCH_DIST_STRIP=	-p1
X
XMAINTAINER=	nork@FreeBSD.org
XCOMMENT=	Synaptics Touchpad driver for X
X
XUSE_BZIP2=	yes
XUSE_GMAKE=	yes
XUSE_X_PREFIX=	yes
X
X.include <bsd.port.pre.mk>
X.if	${X_WINDOW_SYSTEM:L} == xorg
XBUILD_DEPENDS=	${X11BASE}/bin/Xorg:${PORTSDIR}/x11-servers/xorg-server
X.elif	${X_WINDOW_SYSTEM:L} == xfree86-4
XBUILD_DEPENDS=	${X11BASE}/bin/XFree86:${PORTSDIR}/x11-servers/XFree86-4-Server
X.endif
XRUN_DEPENDS=	${BUILD_DEPENDS}
X
X#WRKSRC=		${WRKDIR}/${PORTNAME}
X
XALL_TARGET=	synaptics_drv.o
X
X#pre-everything::
X#	@if ! grep MOUSE_SYNAPTICS_CMD /usr/include/sys/mouse.h > /dev/null 2>&1; then \
X#		${ECHO_MSG} "Please get&apply a following patch for kernel:"; \
X#		${ECHO_MSG} "	http://www.plaisthos.de/synaptics/synaptics.kern.diff"; \
X#		${FALSE}; \
X#	fi
X
Xdo-install:
X	@${INSTALL_DATA} ${WRKSRC}/${ALL_TARGET} ${PREFIX}/lib/modules/input/
X
X.include <bsd.port.post.mk>
END-of-synaptics/Makefile
echo x - synaptics/distinfo
sed 's/^X//' >synaptics/distinfo << 'END-of-synaptics/distinfo'
XMD5 (synaptics-0.12.5.tar.bz2) = 52e2a6436f7e6d7ebb0c8068027c7c3f
XSIZE (synaptics-0.12.5.tar.bz2) = 105847
XMD5 (synaptics.driver.patch) = 3b382f08f9bae4a805110c80832b527d
XSIZE (synaptics.driver.patch) = 20679
END-of-synaptics/distinfo
echo x - synaptics/pkg-descr
sed 's/^X//' >synaptics/pkg-descr << 'END-of-synaptics/pkg-descr'
XThe Synaptics TouchPad driver for for XFree86 4.x. A Synaptics touchpad
Xby default operates in compatibility mode by emulating a standard mouse.
XHowever, by using a dedicated driver, more advanced features of the
Xtouchpad becomes available.
X
XWWW: http://w1.894.telia.com/~u89404340/touchpad/
END-of-synaptics/pkg-descr
echo x - synaptics/pkg-plist
sed 's/^X//' >synaptics/pkg-plist << 'END-of-synaptics/pkg-plist'
Xlib/modules/input/synaptics_drv.o
END-of-synaptics/pkg-plist
exit


Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20040729023208.51e1cd3b.nork>