xref: /plan9/sys/src/cmd/aux/mouse.c (revision 219b2ee8daee37f4aad58d63f21287faa8e4ffdc)
1bd389b36SDavid du Colombier #include <u.h>
2bd389b36SDavid du Colombier #include <libc.h>
3*219b2ee8SDavid du Colombier #include <libg.h>
4bd389b36SDavid du Colombier 
5bd389b36SDavid du Colombier enum
6bd389b36SDavid du Colombier {
7bd389b36SDavid du Colombier 	Sleep500	= 500,
8bd389b36SDavid du Colombier 	Sleep1000	= 1000,
9bd389b36SDavid du Colombier 	Sleep2000	= 2000,
10*219b2ee8SDavid du Colombier 
11*219b2ee8SDavid du Colombier 	TIMEOUT		= 5000,		/* timeout for writes */
12bd389b36SDavid du Colombier };
13bd389b36SDavid du Colombier 
14bd389b36SDavid du Colombier char *speeds[] =
15bd389b36SDavid du Colombier {
16bd389b36SDavid du Colombier 	"b1200",
17bd389b36SDavid du Colombier 	"b2400",
18bd389b36SDavid du Colombier 	"b4800",
19bd389b36SDavid du Colombier 	"b9600",
20bd389b36SDavid du Colombier 	0,
21bd389b36SDavid du Colombier };
22bd389b36SDavid du Colombier 
23*219b2ee8SDavid du Colombier typedef struct Trans {
24*219b2ee8SDavid du Colombier 	Point off, num, den;
25*219b2ee8SDavid du Colombier } Trans;
26*219b2ee8SDavid du Colombier 
27*219b2ee8SDavid du Colombier Trans	trans = {-46, 509, 559, 399, 4239, -3017};
28*219b2ee8SDavid du Colombier int	button2;
29*219b2ee8SDavid du Colombier 
30bd389b36SDavid du Colombier #define DEBUG if(debug)
31bd389b36SDavid du Colombier 
32bd389b36SDavid du Colombier int can9600;	/* true if type W mouse can be set to 9600 */
33bd389b36SDavid du Colombier int debug;
34*219b2ee8SDavid du Colombier int dontset;	/* true if we shouldn't try to set the mouse type */
35bd389b36SDavid du Colombier 
36bd389b36SDavid du Colombier static void
37bd389b36SDavid du Colombier usage(void)
38bd389b36SDavid du Colombier {
39bd389b36SDavid du Colombier 	fprint(2, "%s: usage: %s [device]\n", argv0, argv0);
40bd389b36SDavid du Colombier 	exits("usage");
41bd389b36SDavid du Colombier }
42bd389b36SDavid du Colombier 
43bd389b36SDavid du Colombier static void
44bd389b36SDavid du Colombier catch(void *a, char *msg)
45bd389b36SDavid du Colombier {
46bd389b36SDavid du Colombier 	USED(a, msg);
47*219b2ee8SDavid du Colombier 	if(strstr(msg, "alarm"))
48bd389b36SDavid du Colombier 		noted(NCONT);
49*219b2ee8SDavid du Colombier 	noted(NDFLT);
50bd389b36SDavid du Colombier }
51bd389b36SDavid du Colombier 
52bd389b36SDavid du Colombier static void
53bd389b36SDavid du Colombier dumpbuf(char *buf, int nbytes, char *s)
54bd389b36SDavid du Colombier {
55bd389b36SDavid du Colombier 	print(s);
56*219b2ee8SDavid du Colombier 	while(nbytes-- > 0)
57bd389b36SDavid du Colombier 		print("#%ux ", *buf++ & 0xFF);
58bd389b36SDavid du Colombier 	print("\n");
59bd389b36SDavid du Colombier }
60bd389b36SDavid du Colombier 
61*219b2ee8SDavid du Colombier static long
62*219b2ee8SDavid du Colombier timedwrite(int fd, void *p, int n)
63*219b2ee8SDavid du Colombier {
64*219b2ee8SDavid du Colombier 	long rv;
65*219b2ee8SDavid du Colombier 
66*219b2ee8SDavid du Colombier 	alarm(TIMEOUT);
67*219b2ee8SDavid du Colombier 	rv = write(fd, p, n);
68*219b2ee8SDavid du Colombier 	alarm(0);
69*219b2ee8SDavid du Colombier 	if(rv < 0){
70*219b2ee8SDavid du Colombier 		fprint(2, "%s: timed out\n", argv0);
71*219b2ee8SDavid du Colombier 		exits("timeout");
72*219b2ee8SDavid du Colombier 	}
73*219b2ee8SDavid du Colombier 	return rv;
74*219b2ee8SDavid du Colombier }
75*219b2ee8SDavid du Colombier 
76bd389b36SDavid du Colombier static int
77bd389b36SDavid du Colombier readbyte(int fd)
78bd389b36SDavid du Colombier {
79bd389b36SDavid du Colombier 	uchar c;
80bd389b36SDavid du Colombier 	char buf[ERRLEN];
81bd389b36SDavid du Colombier 
82bd389b36SDavid du Colombier 	alarm(200);
83bd389b36SDavid du Colombier 	if(read(fd, &c, sizeof(c)) == -1){
84bd389b36SDavid du Colombier 		alarm(0);
85bd389b36SDavid du Colombier 		errstr(buf);
86bd389b36SDavid du Colombier 		if(strcmp(buf, "interrupted") == 0)
87bd389b36SDavid du Colombier 			return -1;
88bd389b36SDavid du Colombier 		fprint(2, "%s: readbyte failed - %s\n", argv0, buf);
89bd389b36SDavid du Colombier 		exits("read");
90bd389b36SDavid du Colombier 	}
91bd389b36SDavid du Colombier 	alarm(0);
92bd389b36SDavid du Colombier 	return c;
93bd389b36SDavid du Colombier }
94bd389b36SDavid du Colombier 
95bd389b36SDavid du Colombier static int
96*219b2ee8SDavid du Colombier slowread(int fd, char *buf, int nbytes, char *msg)
97bd389b36SDavid du Colombier {
98bd389b36SDavid du Colombier 	char *p;
99bd389b36SDavid du Colombier 	int c;
100bd389b36SDavid du Colombier 
101*219b2ee8SDavid du Colombier 	for(p = buf; nbytes > 1 && (c = readbyte(fd)) != -1; *p++ = c, nbytes--)
102bd389b36SDavid du Colombier 		;
103bd389b36SDavid du Colombier 	*p = 0;
104*219b2ee8SDavid du Colombier 	DEBUG dumpbuf(buf, p-buf, msg);
105bd389b36SDavid du Colombier 	return p-buf;
106bd389b36SDavid du Colombier }
107bd389b36SDavid du Colombier 
108bd389b36SDavid du Colombier static void
109bd389b36SDavid du Colombier toggleRTS(int fd)
110bd389b36SDavid du Colombier {
111bd389b36SDavid du Colombier 	/*
112bd389b36SDavid du Colombier 	 *
113bd389b36SDavid du Colombier 	 * reset the mouse (toggle RTS)
114bd389b36SDavid du Colombier 	 * must be >100mS
115bd389b36SDavid du Colombier 	 */
116*219b2ee8SDavid du Colombier 	timedwrite(fd, "d0", 2);
117*219b2ee8SDavid du Colombier 	timedwrite(fd, "r0", 2);
118bd389b36SDavid du Colombier 	sleep(Sleep500);
119*219b2ee8SDavid du Colombier 	timedwrite(fd, "d1", 2);
120*219b2ee8SDavid du Colombier 	timedwrite(fd, "r1", 2);
121bd389b36SDavid du Colombier 	sleep(Sleep500);
122bd389b36SDavid du Colombier }
123bd389b36SDavid du Colombier 
124bd389b36SDavid du Colombier static void
125bd389b36SDavid du Colombier setupeia(int fd, char *baud, char *bits)
126bd389b36SDavid du Colombier {
127*219b2ee8SDavid du Colombier 	alarm(TIMEOUT);
128bd389b36SDavid du Colombier 	/*
129bd389b36SDavid du Colombier 	 * set the speed to 1200/2400/4800/9600 baud,
130bd389b36SDavid du Colombier 	 * 7/8-bit data, one stop bit and no parity
131bd389b36SDavid du Colombier 	 */
132bd389b36SDavid du Colombier 	DEBUG print("setupeia(%s,%s)\n", baud, bits);
133*219b2ee8SDavid du Colombier 	timedwrite(fd, baud, strlen(baud));
134*219b2ee8SDavid du Colombier 	timedwrite(fd, bits, strlen(bits));
135*219b2ee8SDavid du Colombier 	timedwrite(fd, "s1", 2);
136*219b2ee8SDavid du Colombier 	timedwrite(fd, "pn", 2);
137*219b2ee8SDavid du Colombier 	alarm(0);
138bd389b36SDavid du Colombier }
139bd389b36SDavid du Colombier 
140bd389b36SDavid du Colombier /*
141bd389b36SDavid du Colombier  *  check for a types M, M3, & W
142bd389b36SDavid du Colombier  *
143bd389b36SDavid du Colombier  *  we talk to all these mice using 1200 baud
144bd389b36SDavid du Colombier  */
145bd389b36SDavid du Colombier int
146bd389b36SDavid du Colombier MorW(int ctl, int data)
147bd389b36SDavid du Colombier {
148bd389b36SDavid du Colombier 	char buf[256];
149bd389b36SDavid du Colombier 	int c;
150bd389b36SDavid du Colombier 
151bd389b36SDavid du Colombier 	/*
152bd389b36SDavid du Colombier 	 * set up for type M, V or W
153bd389b36SDavid du Colombier 	 * flush any pending data
154bd389b36SDavid du Colombier 	 */
155bd389b36SDavid du Colombier 	setupeia(ctl, "b1200", "l7");
156bd389b36SDavid du Colombier 	toggleRTS(ctl);
157*219b2ee8SDavid du Colombier 	while(slowread(data, buf, sizeof(buf), "flush: ") > 0)
158*219b2ee8SDavid du Colombier 		;
159bd389b36SDavid du Colombier 	toggleRTS(ctl);
160bd389b36SDavid du Colombier 
161bd389b36SDavid du Colombier 	/*
162bd389b36SDavid du Colombier 	 * see if there's any data from the mouse
163bd389b36SDavid du Colombier 	 * (type M, V and W mice)
164bd389b36SDavid du Colombier 	 */
165*219b2ee8SDavid du Colombier 	c = slowread(data, buf, sizeof(buf), "check M: ");
166bd389b36SDavid du Colombier 
167bd389b36SDavid du Colombier 	/*
168bd389b36SDavid du Colombier 	 * type M, V and W mice return "M" or "M3" after reset.
169bd389b36SDavid du Colombier 	 * check for type W by sending a 'Send Standard Configuration'
170bd389b36SDavid du Colombier 	 * command, "*?".
171*219b2ee8SDavid du Colombier 	 *
172*219b2ee8SDavid du Colombier 	 * the second check is a kludge for some type W mice on next's
173*219b2ee8SDavid du Colombier 	 * that send a garbage character back before the "M3".
174bd389b36SDavid du Colombier 	 */
175*219b2ee8SDavid du Colombier 	if((c > 0 && buf[0] == 'M') || (c > 1 && buf[1] == 'M')){
176*219b2ee8SDavid du Colombier 		timedwrite(data, "*?", 2);
177*219b2ee8SDavid du Colombier 		c = slowread(data, buf, sizeof(buf), "check W: ");
178bd389b36SDavid du Colombier 		/*
179bd389b36SDavid du Colombier 		 * 4 bytes back
180bd389b36SDavid du Colombier 		 * indicates a type W mouse
181bd389b36SDavid du Colombier 		 */
182*219b2ee8SDavid du Colombier 		if(c == 4){
183bd389b36SDavid du Colombier 			if(buf[1] & (1<<4))
184bd389b36SDavid du Colombier 				can9600 = 1;
185bd389b36SDavid du Colombier 			setupeia(ctl, "b1200", "l8");
186*219b2ee8SDavid du Colombier 			timedwrite(data, "*U", 2);
187*219b2ee8SDavid du Colombier 			slowread(data, buf, sizeof(buf), "check W: ");
188bd389b36SDavid du Colombier 			return 'W';
189bd389b36SDavid du Colombier 		}
190bd389b36SDavid du Colombier 		return 'M';
191bd389b36SDavid du Colombier 	}
192bd389b36SDavid du Colombier 	return 0;
193bd389b36SDavid du Colombier }
194bd389b36SDavid du Colombier 
195bd389b36SDavid du Colombier /*
196bd389b36SDavid du Colombier  *  check for type C by seeing if it responds to the status
197bd389b36SDavid du Colombier  *  command "s".  the mouse is at an unknown speed so we
198bd389b36SDavid du Colombier  *  have to check all possible speeds.
199bd389b36SDavid du Colombier  */
200bd389b36SDavid du Colombier int
201bd389b36SDavid du Colombier C(int ctl, int data)
202bd389b36SDavid du Colombier {
203bd389b36SDavid du Colombier 	char **s;
204bd389b36SDavid du Colombier 	int c;
205bd389b36SDavid du Colombier 	char buf[256];
206bd389b36SDavid du Colombier 
207bd389b36SDavid du Colombier 	sleep(100);
208bd389b36SDavid du Colombier 	for(s = speeds; *s; s++){
209bd389b36SDavid du Colombier 		DEBUG print("%s\n", *s);
210bd389b36SDavid du Colombier 		setupeia(ctl, *s, "l8");
211*219b2ee8SDavid du Colombier 		timedwrite(data, "s", 1);
212*219b2ee8SDavid du Colombier 		c = slowread(data, buf, sizeof(buf), "check C: ");
213bd389b36SDavid du Colombier 		if(c >= 1 && (*buf & 0xBF) == 0x0F){
214bd389b36SDavid du Colombier 			sleep(100);
215*219b2ee8SDavid du Colombier 			timedwrite(data, "*n", 2);
216bd389b36SDavid du Colombier 			sleep(100);
217bd389b36SDavid du Colombier 			setupeia(ctl, "b1200", "l8");
218*219b2ee8SDavid du Colombier 			timedwrite(data, "s", 1);
219*219b2ee8SDavid du Colombier 			c = slowread(data, buf, sizeof(buf), "recheck C: ");
220bd389b36SDavid du Colombier 			if(c >= 1 && (*buf & 0xBF) == 0x0F){
221*219b2ee8SDavid du Colombier 				timedwrite(data, "U", 1);
222bd389b36SDavid du Colombier 				return 'C';
223bd389b36SDavid du Colombier 			}
224bd389b36SDavid du Colombier 		}
225bd389b36SDavid du Colombier 		sleep(100);
226bd389b36SDavid du Colombier 	}
227bd389b36SDavid du Colombier 
228bd389b36SDavid du Colombier 	return 0;
229bd389b36SDavid du Colombier }
230bd389b36SDavid du Colombier 
231bd389b36SDavid du Colombier char *bauderr = "mouse: can't set baud rate, mouse at 1200\n";
232bd389b36SDavid du Colombier 
233bd389b36SDavid du Colombier void
234bd389b36SDavid du Colombier Cbaud(int ctl, int data, int baud)
235bd389b36SDavid du Colombier {
236bd389b36SDavid du Colombier 	char buf[32];
237bd389b36SDavid du Colombier 
238bd389b36SDavid du Colombier 	switch(baud){
239bd389b36SDavid du Colombier 	case 0:
240bd389b36SDavid du Colombier 	case 1200:
241bd389b36SDavid du Colombier 		return;
242bd389b36SDavid du Colombier 	case 2400:
243bd389b36SDavid du Colombier 		buf[1] = 'o';
244bd389b36SDavid du Colombier 		break;
245bd389b36SDavid du Colombier 	case 4800:
246bd389b36SDavid du Colombier 		buf[1] = 'p';
247bd389b36SDavid du Colombier 		break;
248bd389b36SDavid du Colombier 	case 9600:
249bd389b36SDavid du Colombier 		buf[1] = 'q';
250bd389b36SDavid du Colombier 		break;
251bd389b36SDavid du Colombier 	default:
252bd389b36SDavid du Colombier 		fprint(2, bauderr);
253bd389b36SDavid du Colombier 		return;
254bd389b36SDavid du Colombier 	}
255bd389b36SDavid du Colombier 
256bd389b36SDavid du Colombier 	buf[0] = '*';
257bd389b36SDavid du Colombier 	buf[2] = 0;
258bd389b36SDavid du Colombier 	sleep(100);
259*219b2ee8SDavid du Colombier 	timedwrite(data, buf, 2);
260bd389b36SDavid du Colombier 	sleep(100);
261*219b2ee8SDavid du Colombier 	timedwrite(data, buf, 2);
262bd389b36SDavid du Colombier 	sprint(buf, "b%d", baud);
263bd389b36SDavid du Colombier 	setupeia(ctl, buf, "l8");
264bd389b36SDavid du Colombier }
265bd389b36SDavid du Colombier 
266bd389b36SDavid du Colombier void
267bd389b36SDavid du Colombier Wbaud(int ctl, int data, int baud)
268bd389b36SDavid du Colombier {
269bd389b36SDavid du Colombier 	char buf[32];
270bd389b36SDavid du Colombier 
271bd389b36SDavid du Colombier 	switch(baud){
272bd389b36SDavid du Colombier 	case 0:
273bd389b36SDavid du Colombier 	case 1200:
274bd389b36SDavid du Colombier 		return;
275bd389b36SDavid du Colombier 	case 9600:
276bd389b36SDavid du Colombier 		if(can9600)
277bd389b36SDavid du Colombier 			break;
278bd389b36SDavid du Colombier 		/* fall through */
279bd389b36SDavid du Colombier 	default:
280bd389b36SDavid du Colombier 		fprint(2, bauderr);
281bd389b36SDavid du Colombier 		return;
282bd389b36SDavid du Colombier 	}
283*219b2ee8SDavid du Colombier 	timedwrite(data, "*q", 2);
284bd389b36SDavid du Colombier 	setupeia(ctl, "b9600", "l8");
285*219b2ee8SDavid du Colombier 	slowread(data, buf, sizeof(buf), "setbaud: ");
286*219b2ee8SDavid du Colombier }
287*219b2ee8SDavid du Colombier 
288*219b2ee8SDavid du Colombier Mouse
289*219b2ee8SDavid du Colombier rawpen(int fd)
290*219b2ee8SDavid du Colombier {
291*219b2ee8SDavid du Colombier 	Mouse	m;
292*219b2ee8SDavid du Colombier 	int	i, n;
293*219b2ee8SDavid du Colombier 	char	buf[10];
294*219b2ee8SDavid du Colombier 
295*219b2ee8SDavid du Colombier 	while (1) {
296*219b2ee8SDavid du Colombier 		while ((n = read(fd, buf, sizeof buf)) < 5)
297*219b2ee8SDavid du Colombier 			;
298*219b2ee8SDavid du Colombier 		for (i = 0; i < n && (buf[i]&0xa0) != 0xa0; i++)
299*219b2ee8SDavid du Colombier 			;
300*219b2ee8SDavid du Colombier 		if (i+5 > n)
301*219b2ee8SDavid du Colombier 			continue;
302*219b2ee8SDavid du Colombier 		m.buttons = buf[i]&7;
303*219b2ee8SDavid du Colombier 		button2 = m.buttons&2;
304*219b2ee8SDavid du Colombier 		m.xy.x = (buf[i+1]&0x7f) | (buf[i+2]&0x7f) << 7;
305*219b2ee8SDavid du Colombier 		m.xy.y = (buf[i+3]&0x7f) | (buf[i+4]&0x7f) << 7;
306*219b2ee8SDavid du Colombier 		return m;
307*219b2ee8SDavid du Colombier 	}
308*219b2ee8SDavid du Colombier }
309*219b2ee8SDavid du Colombier 
310*219b2ee8SDavid du Colombier void
311*219b2ee8SDavid du Colombier cross(Point p)
312*219b2ee8SDavid du Colombier {
313*219b2ee8SDavid du Colombier 	segment(&screen, Pt(p.x-20, p.y), Pt(p.x+20, p.y), 0xff, S^D);
314*219b2ee8SDavid du Colombier 	segment(&screen, Pt(p.x, p.y-20), Pt(p.x, p.y+20), 0xff, S^D);
315*219b2ee8SDavid du Colombier 	bflush();
316*219b2ee8SDavid du Colombier }
317*219b2ee8SDavid du Colombier 
318*219b2ee8SDavid du Colombier void
319*219b2ee8SDavid du Colombier dot(Point p)
320*219b2ee8SDavid du Colombier {
321*219b2ee8SDavid du Colombier 	static	Point	old;
322*219b2ee8SDavid du Colombier 
323*219b2ee8SDavid du Colombier 	point(&screen, old, 0xff, S^D);
324*219b2ee8SDavid du Colombier 	old = p;
325*219b2ee8SDavid du Colombier 	point(&screen, old, 0xff, S^D);
326*219b2ee8SDavid du Colombier 	bflush();
327*219b2ee8SDavid du Colombier }
328*219b2ee8SDavid du Colombier 
329*219b2ee8SDavid du Colombier Point
330*219b2ee8SDavid du Colombier k2s(Trans t, Point p)
331*219b2ee8SDavid du Colombier {
332*219b2ee8SDavid du Colombier 	p.x = t.off.x + (p.x*t.num.x)/t.den.x;
333*219b2ee8SDavid du Colombier 	p.y = t.off.y + (p.y*t.num.y)/t.den.y;
334*219b2ee8SDavid du Colombier 	return p;
335*219b2ee8SDavid du Colombier }
336*219b2ee8SDavid du Colombier 
337*219b2ee8SDavid du Colombier Point
338*219b2ee8SDavid du Colombier hair(Point p, int fd)
339*219b2ee8SDavid du Colombier {
340*219b2ee8SDavid du Colombier 	Mouse	m;
341*219b2ee8SDavid du Colombier 
342*219b2ee8SDavid du Colombier 	cross(p);
343*219b2ee8SDavid du Colombier 	do {
344*219b2ee8SDavid du Colombier 		m = rawpen(fd);
345*219b2ee8SDavid du Colombier 		dot(k2s(trans, m.xy));
346*219b2ee8SDavid du Colombier 	} while ((m.buttons&1) == 0 && !button2);
347*219b2ee8SDavid du Colombier 	while (rawpen(fd).buttons&1)
348*219b2ee8SDavid du Colombier 		;
349*219b2ee8SDavid du Colombier 	cross(p);
350*219b2ee8SDavid du Colombier 	dot(k2s(trans, m.xy));
351*219b2ee8SDavid du Colombier 	return m.xy;
352bd389b36SDavid du Colombier }
353bd389b36SDavid du Colombier 
354bd389b36SDavid du Colombier void
355bd389b36SDavid du Colombier main(int argc, char *argv[])
356bd389b36SDavid du Colombier {
357bd389b36SDavid du Colombier 	char *p;
358bd389b36SDavid du Colombier 	int baud;
359bd389b36SDavid du Colombier 	int conf, ctl, data, def, type;
360bd389b36SDavid du Colombier 	char buf[256];
361bd389b36SDavid du Colombier 
362bd389b36SDavid du Colombier 	def = 0;
363bd389b36SDavid du Colombier 	baud = 0;
364bd389b36SDavid du Colombier 	ARGBEGIN{
365bd389b36SDavid du Colombier 	case 'b':
366bd389b36SDavid du Colombier 		baud = atoi(ARGF());
367bd389b36SDavid du Colombier 		break;
368bd389b36SDavid du Colombier 	case 'd':
369bd389b36SDavid du Colombier 		p = ARGF();
370bd389b36SDavid du Colombier 		def = *p;
371bd389b36SDavid du Colombier 		break;
372*219b2ee8SDavid du Colombier 	case 'n':
373*219b2ee8SDavid du Colombier 		dontset = 1;
374*219b2ee8SDavid du Colombier 		break;
375bd389b36SDavid du Colombier 	case 'D':
376bd389b36SDavid du Colombier 		debug = 1;
377bd389b36SDavid du Colombier 		break;
378bd389b36SDavid du Colombier 	default:
379bd389b36SDavid du Colombier 		usage();
380bd389b36SDavid du Colombier 	}ARGEND
381bd389b36SDavid du Colombier 
382bd389b36SDavid du Colombier 	p = "0";
383bd389b36SDavid du Colombier 	if(argc)
384bd389b36SDavid du Colombier 		p = *argv;
385bd389b36SDavid du Colombier 
386bd389b36SDavid du Colombier 	if((conf = open("#b/mousectl", OWRITE)) == -1){
387bd389b36SDavid du Colombier 		fprint(2, "%s: can't open #b/mousectl - %r\n", argv0);
388*219b2ee8SDavid du Colombier 		if(dontset == 0)
389bd389b36SDavid du Colombier 			exits("open #b");
390bd389b36SDavid du Colombier 	}
391bd389b36SDavid du Colombier 
392bd389b36SDavid du Colombier 	if(strcmp(p, "ps2") == 0){
393bd389b36SDavid du Colombier 		if(write(conf, "ps2", 3) < 0){
394bd389b36SDavid du Colombier 			fprint(2, "%s: error setting mouse type - %r\n", argv0);
395bd389b36SDavid du Colombier 			exits("write conf");
396bd389b36SDavid du Colombier 		}
397bd389b36SDavid du Colombier 		exits(0);
398bd389b36SDavid du Colombier 	}
399bd389b36SDavid du Colombier 
400bd389b36SDavid du Colombier 	sprint(buf, "#t/eia%sctl", p);
401bd389b36SDavid du Colombier 	if((ctl = open(buf, ORDWR)) == -1){
402bd389b36SDavid du Colombier 		fprint(2, "%s: can't open %s - %r\n", argv0, buf);
403bd389b36SDavid du Colombier 		exits("open ctl");
404bd389b36SDavid du Colombier 	}
405bd389b36SDavid du Colombier 	sprint(buf, "#t/eia%s", p);
406bd389b36SDavid du Colombier 	if((data = open(buf, ORDWR)) == -1){
407bd389b36SDavid du Colombier 		fprint(2, "%s: can't open %s - %r\n", argv0, buf);
408bd389b36SDavid du Colombier 		exits("open data");
409bd389b36SDavid du Colombier 	}
410bd389b36SDavid du Colombier 
411bd389b36SDavid du Colombier 	notify(catch);
412bd389b36SDavid du Colombier 
413bd389b36SDavid du Colombier 	type = MorW(ctl, data);
414bd389b36SDavid du Colombier 	if(type == 0)
415bd389b36SDavid du Colombier 		type = C(ctl, data);
416bd389b36SDavid du Colombier 	if(type == 0){
417*219b2ee8SDavid du Colombier 		/* with the default we can't assume anything */
418*219b2ee8SDavid du Colombier 		baud = 0;
419*219b2ee8SDavid du Colombier 
420bd389b36SDavid du Colombier 		/* try the default */
421bd389b36SDavid du Colombier 		switch(def){
422bd389b36SDavid du Colombier 		case 'C':
423bd389b36SDavid du Colombier 			setupeia(ctl, "b1200", "l8");
424bd389b36SDavid du Colombier 			break;
425bd389b36SDavid du Colombier 		case 'M':
426bd389b36SDavid du Colombier 			setupeia(ctl, "b1200", "l7");
427bd389b36SDavid du Colombier 			break;
428bd389b36SDavid du Colombier 		}
429*219b2ee8SDavid du Colombier 
430bd389b36SDavid du Colombier 		type = def;
431bd389b36SDavid du Colombier 	}
432bd389b36SDavid du Colombier 
433bd389b36SDavid du Colombier 	sprint(buf, "serial %s", p);
434bd389b36SDavid du Colombier 	switch(type){
435bd389b36SDavid du Colombier 	case 0:
436*219b2ee8SDavid du Colombier 		fprint(2, "%s: Unknown mouse type\n", argv0);
437bd389b36SDavid du Colombier 		exits("no mouse");
438bd389b36SDavid du Colombier 	case 'C':
439*219b2ee8SDavid du Colombier 		DEBUG print("Logitech 5 byte mouse\n");
440bd389b36SDavid du Colombier 		Cbaud(ctl, data, baud);
441bd389b36SDavid du Colombier 		break;
442bd389b36SDavid du Colombier 	case 'W':
443*219b2ee8SDavid du Colombier 		DEBUG print("Type W mouse\n");
444bd389b36SDavid du Colombier 		Wbaud(ctl, data, baud);
445bd389b36SDavid du Colombier 		break;
446bd389b36SDavid du Colombier 	case 'M':
447*219b2ee8SDavid du Colombier 		DEBUG print("Microsoft compatible mouse\n");
448bd389b36SDavid du Colombier 		strcat(buf, " M");
449bd389b36SDavid du Colombier 		break;
450bd389b36SDavid du Colombier 	}
451bd389b36SDavid du Colombier 	DEBUG fprint(2, "mouse configured as '%s'\n", buf);
452*219b2ee8SDavid du Colombier 	if(dontset == 0 && write(conf, buf, strlen(buf)) < 0){
453bd389b36SDavid du Colombier 		fprint(2, "%s: error setting mouse type - %r\n", argv0);
454bd389b36SDavid du Colombier 		exits("write conf");
455bd389b36SDavid du Colombier 	}
456bd389b36SDavid du Colombier 	exits(0);
457bd389b36SDavid du Colombier }
458