1 /* 2 * USB Human Interaction Device: keyboard and mouse. 3 * 4 * If there's no usb keyboard, it tries to setup the mouse, if any. 5 * It should be started at boot time. 6 * 7 * Mouse events are converted to the format of mouse(3)'s 8 * mousein file. 9 * Keyboard keycodes are translated to scan codes and sent to kbin(3). 10 * 11 */ 12 13 #include <u.h> 14 #include <libc.h> 15 #include <thread.h> 16 #include "usb.h" 17 #include "hid.h" 18 19 enum 20 { 21 Awakemsg=0xdeaddead, 22 Diemsg = 0xbeefbeef, 23 }; 24 25 typedef struct KDev KDev; 26 typedef struct Kin Kin; 27 28 struct KDev 29 { 30 Dev* dev; /* usb device*/ 31 Dev* ep; /* endpoint to get events */ 32 Kin* in; /* used to send events to kernel */ 33 Channel*repeatc; /* only for keyboard */ 34 int accel; /* only for mouse */ 35 }; 36 37 /* 38 * Kbdin and mousein files must be shared among all instances. 39 */ 40 struct Kin 41 { 42 int ref; 43 int fd; 44 char* name; 45 }; 46 47 /* 48 * Map for the logitech bluetooth mouse with 8 buttons and wheels. 49 * { ptr ->mouse} 50 * { 0x01, 0x01 }, // left 51 * { 0x04, 0x02 }, // middle 52 * { 0x02, 0x04 }, // right 53 * { 0x40, 0x08 }, // up 54 * { 0x80, 0x10 }, // down 55 * { 0x10, 0x08 }, // side up 56 * { 0x08, 0x10 }, // side down 57 * { 0x20, 0x02 }, // page 58 * besides wheel and regular up/down report the 4th byte as 1/-1 59 */ 60 61 /* 62 * key code to scan code; for the page table used by 63 * the logitech bluetooth keyboard. 64 */ 65 static char sctab[256] = 66 { 67 [0x00] 0x0, 0x0, 0x0, 0x0, 0x1e, 0x30, 0x2e, 0x20, 68 [0x08] 0x12, 0x21, 0x22, 0x23, 0x17, 0x24, 0x25, 0x26, 69 [0x10] 0x32, 0x31, 0x18, 0x19, 0x10, 0x13, 0x1f, 0x14, 70 [0x18] 0x16, 0x2f, 0x11, 0x2d, 0x15, 0x2c, 0x2, 0x3, 71 [0x20] 0x4, 0x5, 0x6, 0x7, 0x8, 0x9, 0xa, 0xb, 72 [0x28] 0x1c, 0x1, 0xe, 0xf, 0x39, 0xc, 0xd, 0x1a, 73 [0x30] 0x1b, 0x2b, 0x2b, 0x27, 0x28, 0x29, 0x33, 0x34, 74 [0x38] 0x35, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 0x40, 75 [0x40] 0x41, 0x42, 0x43, 0x44, 0x57, 0x58, 0x63, 0x46, 76 [0x48] 0x77, 0x52, 0x47, 0x49, 0x53, 0x4f, 0x51, 0x4d, 77 [0x50] 0x4b, 0x50, 0x48, 0x45, 0x35, 0x37, 0x4a, 0x4e, 78 [0x58] 0x1c, 0x4f, 0x50, 0x51, 0x4b, 0x4c, 0x4d, 0x47, 79 [0x60] 0x48, 0x49, 0x52, 0x53, 0x56, 0x7f, 0x74, 0x75, 80 [0x68] 0x55, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, 81 [0x70] 0x78, 0x79, 0x7a, 0x7b, 0x0, 0x0, 0x0, 0x0, 82 [0x78] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x71, 83 [0x80] 0x73, 0x72, 0x0, 0x0, 0x0, 0x7c, 0x0, 0x0, 84 [0x88] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 85 [0x90] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 86 [0x98] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 87 [0xa0] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 88 [0xa8] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 89 [0xb0] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 90 [0xb8] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 91 [0xc0] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 92 [0xc8] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 93 [0xd0] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 94 [0xd8] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 95 [0xe0] 0x1d, 0x2a, 0x38, 0x7d, 0x61, 0x36, 0x64, 0x7e, 96 [0xe8] 0x0, 0x0, 0x0, 0x0, 0x0, 0x73, 0x72, 0x71, 97 [0xf0] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 98 [0xf8] 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 99 }; 100 101 static QLock inlck; 102 static Kin kbdin = 103 { 104 .ref = 0, 105 .name = "#Ι/kbin", 106 .fd = -1, 107 }; 108 static Kin ptrin = 109 { 110 .ref = 0, 111 .name = "#m/mousein", 112 .fd = -1, 113 }; 114 115 static int kbdebug; 116 117 static int 118 setbootproto(KDev* f, int eid) 119 { 120 int r, id; 121 122 r = Rh2d|Rclass|Riface; 123 id = f->dev->usb->ep[eid]->iface->id; 124 return usbcmd(f->dev, r, Setproto, Bootproto, id, nil, 0); 125 } 126 127 /* 128 * Try to recover from a babble error. A port reset is the only way out. 129 * BUG: we should be careful not to reset a bundle with several devices. 130 */ 131 static void 132 recoverkb(KDev *f) 133 { 134 int i; 135 136 close(f->dev->dfd); /* it's for usbd now */ 137 devctl(f->dev, "reset"); 138 for(i = 0; i < 10; i++){ 139 sleep(500); 140 if(opendevdata(f->dev, ORDWR) >= 0){ 141 setbootproto(f, f->ep->id); 142 break; 143 } 144 /* else usbd still working... */ 145 } 146 } 147 148 static void 149 kbfatal(KDev *kd, char *sts) 150 { 151 Dev *dev; 152 153 if(sts != nil) 154 fprint(2, "kb: fatal: %s\n", sts); 155 else 156 fprint(2, "kb: exiting\n"); 157 if(kd->repeatc != nil) 158 nbsendul(kd->repeatc, Diemsg); 159 dev = kd->dev; 160 kd->dev = nil; 161 if(kd->ep != nil) 162 closedev(kd->ep); 163 kd->ep = nil; 164 devctl(dev, "detach"); 165 closedev(dev); 166 /* 167 * free(kd); done by closedev. 168 */ 169 threadexits(sts); 170 } 171 172 static int 173 scale(KDev *f, int x) 174 { 175 int sign = 1; 176 177 if(x < 0){ 178 sign = -1; 179 x = -x; 180 } 181 switch(x){ 182 case 0: 183 case 1: 184 case 2: 185 case 3: 186 break; 187 case 4: 188 x = 6 + (f->accel>>2); 189 break; 190 case 5: 191 x = 9 + (f->accel>>1); 192 break; 193 default: 194 x *= MaxAcc; 195 break; 196 } 197 return sign*x; 198 } 199 200 /* 201 * ps2 mouse is processed mostly at interrupt time. 202 * for usb we do what we can. 203 */ 204 static void 205 sethipri(void) 206 { 207 char fn[30]; 208 int fd; 209 210 snprint(fn, sizeof(fn), "/proc/%d/ctl", getpid()); 211 fd = open(fn, OWRITE); 212 if(fd < 0) 213 return; 214 fprint(fd, "pri 13"); 215 close(fd); 216 } 217 218 static void 219 ptrwork(void* a) 220 { 221 static char maptab[] = {0x0, 0x1, 0x4, 0x5, 0x2, 0x3, 0x6, 0x7}; 222 int x, y, b, c, ptrfd; 223 int mfd, nerrs; 224 char buf[32]; 225 char mbuf[80]; 226 KDev* f = a; 227 int hipri; 228 229 hipri = nerrs = 0; 230 ptrfd = f->ep->dfd; 231 mfd = f->in->fd; 232 233 if(f->ep->maxpkt < 3 || f->ep->maxpkt > sizeof buf) 234 kbfatal(f, "weird mouse maxpkt"); 235 for(;;){ 236 memset(buf, 0, sizeof buf); 237 if(f->ep == nil) 238 kbfatal(f, nil); 239 c = read(ptrfd, buf, f->ep->maxpkt); 240 assert(f->dev != nil); 241 assert(f->ep != nil); 242 if(c < 0){ 243 dprint(2, "kb: mouse: %s: read: %r\n", f->ep->dir); 244 if(++nerrs < 3){ 245 recoverkb(f); 246 continue; 247 } 248 } 249 if(c <= 0) 250 kbfatal(f, nil); 251 if(c < 3) 252 continue; 253 if(f->accel){ 254 x = scale(f, buf[1]); 255 y = scale(f, buf[2]); 256 }else{ 257 x = buf[1]; 258 y = buf[2]; 259 } 260 b = maptab[buf[0] & 0x7]; 261 if(c > 3 && buf[3] == 1) /* up */ 262 b |= 0x08; 263 if(c > 3 && buf[3] == -1) /* down */ 264 b |= 0x10; 265 if(kbdebug > 1) 266 fprint(2, "kb: m%11d %11d %11d\n", x, y, b); 267 seprint(mbuf, mbuf+sizeof(mbuf), "m%11d %11d %11d", x, y,b); 268 if(write(mfd, mbuf, strlen(mbuf)) < 0) 269 kbfatal(f, "mousein i/o"); 270 if(hipri == 0){ 271 sethipri(); 272 hipri = 1; 273 } 274 } 275 } 276 277 static void 278 stoprepeat(KDev *f) 279 { 280 sendul(f->repeatc, Awakemsg); 281 } 282 283 static void 284 startrepeat(KDev *f, uchar esc1, uchar sc) 285 { 286 ulong c; 287 288 if(esc1) 289 c = SCesc1 << 8 | (sc & 0xff); 290 else 291 c = sc; 292 sendul(f->repeatc, c); 293 } 294 295 static void 296 putscan(int kbinfd, uchar esc, uchar sc) 297 { 298 uchar s[2] = {SCesc1, 0}; 299 300 if(sc == 0x41){ 301 kbdebug += 2; 302 return; 303 } 304 if(sc == 0x42){ 305 kbdebug = 0; 306 return; 307 } 308 if(kbdebug) 309 fprint(2, "sc: %x %x\n", (esc? SCesc1: 0), sc); 310 s[1] = sc; 311 if(esc && sc != 0) 312 write(kbinfd, s, 2); 313 else if(sc != 0) 314 write(kbinfd, s+1, 1); 315 } 316 317 static void 318 repeatproc(void* a) 319 { 320 KDev *f; 321 Channel *repeatc; 322 int kbdinfd; 323 ulong l, t, i; 324 uchar esc1, sc; 325 326 /* 327 * too many jumps here. 328 * Rewrite instead of debug, if needed. 329 */ 330 f = a; 331 repeatc = f->repeatc; 332 kbdinfd = f->in->fd; 333 l = Awakemsg; 334 Repeat: 335 if(l == Diemsg) 336 goto Abort; 337 while(l == Awakemsg) 338 l = recvul(repeatc); 339 if(l == Diemsg) 340 goto Abort; 341 esc1 = l >> 8; 342 sc = l; 343 t = 160; 344 for(;;){ 345 for(i = 0; i < t; i += 5){ 346 if(l = nbrecvul(repeatc)) 347 goto Repeat; 348 sleep(5); 349 } 350 putscan(kbdinfd, esc1, sc); 351 t = 30; 352 } 353 Abort: 354 chanfree(repeatc); 355 threadexits("aborted"); 356 357 } 358 359 360 #define hasesc1(sc) (((sc) > 0x47) || ((sc) == 0x38)) 361 362 static void 363 putmod(int fd, uchar mods, uchar omods, uchar mask, uchar esc, uchar sc) 364 { 365 /* BUG: Should be a single write */ 366 if((mods&mask) && !(omods&mask)) 367 putscan(fd, esc, sc); 368 if(!(mods&mask) && (omods&mask)) 369 putscan(fd, esc, Keyup|sc); 370 } 371 372 /* 373 * This routine diffs the state with the last known state 374 * and invents the scan codes that would have been sent 375 * by a non-usb keyboard in that case. This also requires supplying 376 * the extra esc1 byte as well as keyup flags. 377 * The aim is to allow future addition of other keycode pages 378 * for other keyboards. 379 */ 380 static uchar 381 putkeys(KDev *f, uchar buf[], uchar obuf[], int n, uchar dk) 382 { 383 int i, j; 384 uchar uk; 385 int fd; 386 387 fd = f->in->fd; 388 putmod(fd, buf[0], obuf[0], Mctrl, 0, SCctrl); 389 putmod(fd, buf[0], obuf[0], (1<<Mlshift), 0, SClshift); 390 putmod(fd, buf[0], obuf[0], (1<<Mrshift), 0, SCrshift); 391 putmod(fd, buf[0], obuf[0], Mcompose, 0, SCcompose); 392 putmod(fd, buf[0], obuf[0], Maltgr, 1, SCcompose); 393 394 /* Report key downs */ 395 for(i = 2; i < n; i++){ 396 for(j = 2; j < n; j++) 397 if(buf[i] == obuf[j]) 398 break; 399 if(j == n && buf[i] != 0){ 400 dk = sctab[buf[i]]; 401 putscan(fd, hasesc1(dk), dk); 402 startrepeat(f, hasesc1(dk), dk); 403 } 404 } 405 406 /* Report key ups */ 407 uk = 0; 408 for(i = 2; i < n; i++){ 409 for(j = 2; j < n; j++) 410 if(obuf[i] == buf[j]) 411 break; 412 if(j == n && obuf[i] != 0){ 413 uk = sctab[obuf[i]]; 414 putscan(fd, hasesc1(uk), uk|Keyup); 415 } 416 } 417 if(uk && (dk == 0 || dk == uk)){ 418 stoprepeat(f); 419 dk = 0; 420 } 421 return dk; 422 } 423 424 static int 425 kbdbusy(uchar* buf, int n) 426 { 427 int i; 428 429 for(i = 1; i < n; i++) 430 if(buf[i] == 0 || buf[i] != buf[0]) 431 return 0; 432 return 1; 433 } 434 435 static void 436 kbdwork(void *a) 437 { 438 int c, i, kbdfd, nerrs; 439 uchar dk, buf[64], lbuf[64]; 440 char err[128]; 441 KDev *f = a; 442 443 kbdfd = f->ep->dfd; 444 445 if(f->ep->maxpkt < 3 || f->ep->maxpkt > sizeof buf) 446 kbfatal(f, "weird maxpkt"); 447 448 f->repeatc = chancreate(sizeof(ulong), 0); 449 if(f->repeatc == nil) 450 kbfatal(f, "chancreate failed"); 451 452 proccreate(repeatproc, f, Stack); 453 memset(lbuf, 0, sizeof lbuf); 454 dk = nerrs = 0; 455 for(;;){ 456 memset(buf, 0, sizeof buf); 457 c = read(kbdfd, buf, f->ep->maxpkt); 458 assert(f->dev != nil); 459 assert(f->ep != nil); 460 if(c < 0){ 461 rerrstr(err, sizeof(err)); 462 fprint(2, "kb: %s: read: %s\n", f->ep->dir, err); 463 if(strstr(err, "babble") != 0 && ++nerrs < 3){ 464 recoverkb(f); 465 continue; 466 } 467 } 468 if(c <= 0) 469 kbfatal(f, nil); 470 if(c < 3) 471 continue; 472 if(kbdbusy(buf + 2, c - 2)) 473 continue; 474 if(usbdebug > 2 || kbdebug > 1){ 475 fprint(2, "kbd mod %x: ", buf[0]); 476 for(i = 2; i < c; i++) 477 fprint(2, "kc %x ", buf[i]); 478 fprint(2, "\n"); 479 } 480 dk = putkeys(f, buf, lbuf, f->ep->maxpkt, dk); 481 memmove(lbuf, buf, c); 482 nerrs = 0; 483 } 484 } 485 486 static void 487 freekdev(void *a) 488 { 489 KDev *kd; 490 491 kd = a; 492 if(kd->in != nil){ 493 qlock(&inlck); 494 if(--kd->in->ref == 0){ 495 close(kd->in->fd); 496 kd->in->fd = -1; 497 } 498 qunlock(&inlck); 499 } 500 dprint(2, "freekdev\n"); 501 free(kd); 502 } 503 504 static void 505 kbstart(Dev *d, Ep *ep, Kin *in, void (*f)(void*), int accel) 506 { 507 KDev *kd; 508 509 qlock(&inlck); 510 if(in->fd < 0){ 511 in->fd = open(in->name, OWRITE); 512 if(in->fd < 0){ 513 fprint(2, "kb: %s: %r\n", in->name); 514 qunlock(&inlck); 515 return; 516 } 517 } 518 in->ref++; /* for kd->in = in */ 519 qunlock(&inlck); 520 kd = d->aux = emallocz(sizeof(KDev), 1); 521 d->free = freekdev; 522 kd->in = in; 523 kd->dev = d; 524 if(setbootproto(kd, ep->id) < 0){ 525 fprint(2, "kb: %s: bootproto: %r\n", d->dir); 526 return; 527 } 528 kd->accel = accel; 529 kd->ep = openep(d, ep->id); 530 if(kd->ep == nil){ 531 fprint(2, "kb: %s: openep %d: %r\n", d->dir, ep->id); 532 return; 533 } 534 if(opendevdata(kd->ep, OREAD) < 0){ 535 fprint(2, "kb: %s: opendevdata: %r\n", kd->ep->dir); 536 closedev(kd->ep); 537 kd->ep = nil; 538 return; 539 } 540 541 incref(d); 542 proccreate(f, kd, Stack); 543 } 544 545 static int 546 usage(void) 547 { 548 werrstr("usage: usb/kb [-dkm] [-a n] [-N nb]"); 549 return -1; 550 } 551 552 int 553 kbmain(Dev *d, int argc, char* argv[]) 554 { 555 int i, kena, pena, accel, devid; 556 Usbdev *ud; 557 Ep *ep; 558 559 kena = pena = 1; 560 accel = 0; 561 devid = d->id; 562 ARGBEGIN{ 563 case 'a': 564 accel = strtol(EARGF(usage()), nil, 0); 565 break; 566 case 'd': 567 kbdebug++; 568 break; 569 case 'k': 570 kena = 1; 571 pena = 0; 572 break; 573 case 'm': 574 kena = 0; 575 pena = 1; 576 break; 577 case 'N': 578 devid = atoi(EARGF(usage())); /* ignore dev number */ 579 break; 580 default: 581 return usage(); 582 }ARGEND; 583 if(argc != 0){ 584 return usage(); 585 } 586 USED(devid); 587 ud = d->usb; 588 d->aux = nil; 589 dprint(2, "kb: main: dev %s ref %ld\n", d->dir, d->ref); 590 for(i = 0; i < nelem(ud->ep); i++){ 591 if((ep = ud->ep[i]) == nil) 592 break; 593 if(kena && ep->type == Eintr && ep->dir == Ein) 594 if(ep->iface->csp == KbdCSP) 595 kbstart(d, ep, &kbdin, kbdwork, accel); 596 if(pena && ep->type == Eintr && ep->dir == Ein) 597 if(ep->iface->csp == PtrCSP) 598 kbstart(d, ep, &ptrin, ptrwork, accel); 599 } 600 return 0; 601 } 602