1 /* 2 * OLPC HGPK (XO-1) touchpad PS/2 mouse driver 3 * 4 * Copyright (c) 2006-2008 One Laptop Per Child 5 * Authors: 6 * Zephaniah E. Hull 7 * Andres Salomon <[email protected]> 8 * 9 * This driver is partly based on the ALPS driver, which is: 10 * 11 * Copyright (c) 2003 Neil Brown <[email protected]> 12 * Copyright (c) 2003-2005 Peter Osterlund <[email protected]> 13 * Copyright (c) 2004 Dmitry Torokhov <[email protected]> 14 * Copyright (c) 2005 Vojtech Pavlik <[email protected]> 15 * 16 * This program is free software; you can redistribute it and/or modify 17 * it under the terms of the GNU General Public License version 2 as 18 * published by the Free Software Foundation. 19 */ 20 21 /* 22 * The spec from ALPS is available from 23 * <http://wiki.laptop.org/go/Touch_Pad/Tablet>. It refers to this 24 * device as HGPK (Hybrid GS, PT, and Keymatrix). 25 * 26 * The earliest versions of the device had simultaneous reporting; that 27 * was removed. After that, the device used the Advanced Mode GS/PT streaming 28 * stuff. That turned out to be too buggy to support, so we've finally 29 * switched to Mouse Mode (which utilizes only the center 1/3 of the touchpad). 30 */ 31 32 #define DEBUG 33 #include <linux/slab.h> 34 #include <linux/input.h> 35 #include <linux/serio.h> 36 #include <linux/libps2.h> 37 #include <linux/delay.h> 38 #include <asm/olpc.h> 39 40 #include "psmouse.h" 41 #include "hgpk.h" 42 43 #define ILLEGAL_XY 999999 44 45 static bool tpdebug; 46 module_param(tpdebug, bool, 0644); 47 MODULE_PARM_DESC(tpdebug, "enable debugging, dumping packets to KERN_DEBUG."); 48 49 static int recalib_delta = 100; 50 module_param(recalib_delta, int, 0644); 51 MODULE_PARM_DESC(recalib_delta, 52 "packets containing a delta this large will be discarded, and a " 53 "recalibration may be scheduled."); 54 55 static int jumpy_delay = 20; 56 module_param(jumpy_delay, int, 0644); 57 MODULE_PARM_DESC(jumpy_delay, 58 "delay (ms) before recal after jumpiness detected"); 59 60 static int spew_delay = 1; 61 module_param(spew_delay, int, 0644); 62 MODULE_PARM_DESC(spew_delay, 63 "delay (ms) before recal after packet spew detected"); 64 65 static int recal_guard_time = 2000; 66 module_param(recal_guard_time, int, 0644); 67 MODULE_PARM_DESC(recal_guard_time, 68 "interval (ms) during which recal will be restarted if packet received"); 69 70 static int post_interrupt_delay = 1000; 71 module_param(post_interrupt_delay, int, 0644); 72 MODULE_PARM_DESC(post_interrupt_delay, 73 "delay (ms) before recal after recal interrupt detected"); 74 75 static char hgpk_mode_name[16]; 76 module_param_string(hgpk_mode, hgpk_mode_name, sizeof(hgpk_mode_name), 0644); 77 MODULE_PARM_DESC(hgpk_mode, 78 "default hgpk mode: mouse, glidesensor or pentablet"); 79 80 static int hgpk_default_mode = HGPK_MODE_MOUSE; 81 82 static const char * const hgpk_mode_names[] = { 83 [HGPK_MODE_MOUSE] = "Mouse", 84 [HGPK_MODE_GLIDESENSOR] = "GlideSensor", 85 [HGPK_MODE_PENTABLET] = "PenTablet", 86 }; 87 88 static int hgpk_mode_from_name(const char *buf, int len) 89 { 90 int i; 91 92 for (i = 0; i < ARRAY_SIZE(hgpk_mode_names); i++) { 93 const char *name = hgpk_mode_names[i]; 94 if (strlen(name) == len && !strncasecmp(name, buf, len)) 95 return i; 96 } 97 98 return HGPK_MODE_INVALID; 99 } 100 101 /* 102 * see if new value is within 20% of half of old value 103 */ 104 static int approx_half(int curr, int prev) 105 { 106 int belowhalf, abovehalf; 107 108 if (curr < 5 || prev < 5) 109 return 0; 110 111 belowhalf = (prev * 8) / 20; 112 abovehalf = (prev * 12) / 20; 113 114 return belowhalf < curr && curr <= abovehalf; 115 } 116 117 /* 118 * Throw out oddly large delta packets, and any that immediately follow whose 119 * values are each approximately half of the previous. It seems that the ALPS 120 * firmware emits errant packets, and they get averaged out slowly. 121 */ 122 static int hgpk_discard_decay_hack(struct psmouse *psmouse, int x, int y) 123 { 124 struct hgpk_data *priv = psmouse->private; 125 int avx, avy; 126 bool do_recal = false; 127 128 avx = abs(x); 129 avy = abs(y); 130 131 /* discard if too big, or half that but > 4 times the prev delta */ 132 if (avx > recalib_delta || 133 (avx > recalib_delta / 2 && ((avx / 4) > priv->xlast))) { 134 hgpk_err(psmouse, "detected %dpx jump in x\n", x); 135 priv->xbigj = avx; 136 } else if (approx_half(avx, priv->xbigj)) { 137 hgpk_err(psmouse, "detected secondary %dpx jump in x\n", x); 138 priv->xbigj = avx; 139 priv->xsaw_secondary++; 140 } else { 141 if (priv->xbigj && priv->xsaw_secondary > 1) 142 do_recal = true; 143 priv->xbigj = 0; 144 priv->xsaw_secondary = 0; 145 } 146 147 if (avy > recalib_delta || 148 (avy > recalib_delta / 2 && ((avy / 4) > priv->ylast))) { 149 hgpk_err(psmouse, "detected %dpx jump in y\n", y); 150 priv->ybigj = avy; 151 } else if (approx_half(avy, priv->ybigj)) { 152 hgpk_err(psmouse, "detected secondary %dpx jump in y\n", y); 153 priv->ybigj = avy; 154 priv->ysaw_secondary++; 155 } else { 156 if (priv->ybigj && priv->ysaw_secondary > 1) 157 do_recal = true; 158 priv->ybigj = 0; 159 priv->ysaw_secondary = 0; 160 } 161 162 priv->xlast = avx; 163 priv->ylast = avy; 164 165 if (do_recal && jumpy_delay) { 166 hgpk_err(psmouse, "scheduling recalibration\n"); 167 psmouse_queue_work(psmouse, &priv->recalib_wq, 168 msecs_to_jiffies(jumpy_delay)); 169 } 170 171 return priv->xbigj || priv->ybigj; 172 } 173 174 static void hgpk_reset_spew_detection(struct hgpk_data *priv) 175 { 176 priv->spew_count = 0; 177 priv->dupe_count = 0; 178 priv->x_tally = 0; 179 priv->y_tally = 0; 180 priv->spew_flag = NO_SPEW; 181 } 182 183 static void hgpk_reset_hack_state(struct psmouse *psmouse) 184 { 185 struct hgpk_data *priv = psmouse->private; 186 187 priv->abs_x = priv->abs_y = -1; 188 priv->xlast = priv->ylast = ILLEGAL_XY; 189 priv->xbigj = priv->ybigj = 0; 190 priv->xsaw_secondary = priv->ysaw_secondary = 0; 191 hgpk_reset_spew_detection(priv); 192 } 193 194 /* 195 * We have no idea why this particular hardware bug occurs. The touchpad 196 * will randomly start spewing packets without anything touching the 197 * pad. This wouldn't necessarily be bad, but it's indicative of a 198 * severely miscalibrated pad; attempting to use the touchpad while it's 199 * spewing means the cursor will jump all over the place, and act "drunk". 200 * 201 * The packets that are spewed tend to all have deltas between -2 and 2, and 202 * the cursor will move around without really going very far. It will 203 * tend to end up in the same location; if we tally up the changes over 204 * 100 packets, we end up w/ a final delta of close to 0. This happens 205 * pretty regularly when the touchpad is spewing, and is pretty hard to 206 * manually trigger (at least for *my* fingers). So, it makes a perfect 207 * scheme for detecting spews. 208 */ 209 static void hgpk_spewing_hack(struct psmouse *psmouse, 210 int l, int r, int x, int y) 211 { 212 struct hgpk_data *priv = psmouse->private; 213 214 /* ignore button press packets; many in a row could trigger 215 * a false-positive! */ 216 if (l || r) 217 return; 218 219 /* don't track spew if the workaround feature has been turned off */ 220 if (!spew_delay) 221 return; 222 223 if (abs(x) > 3 || abs(y) > 3) { 224 /* no spew, or spew ended */ 225 hgpk_reset_spew_detection(priv); 226 return; 227 } 228 229 /* Keep a tally of the overall delta to the cursor position caused by 230 * the spew */ 231 priv->x_tally += x; 232 priv->y_tally += y; 233 234 switch (priv->spew_flag) { 235 case NO_SPEW: 236 /* we're not spewing, but this packet might be the start */ 237 priv->spew_flag = MAYBE_SPEWING; 238 239 /* fall-through */ 240 241 case MAYBE_SPEWING: 242 priv->spew_count++; 243 244 if (priv->spew_count < SPEW_WATCH_COUNT) 245 break; 246 247 /* excessive spew detected, request recalibration */ 248 priv->spew_flag = SPEW_DETECTED; 249 250 /* fall-through */ 251 252 case SPEW_DETECTED: 253 /* only recalibrate when the overall delta to the cursor 254 * is really small. if the spew is causing significant cursor 255 * movement, it is probably a case of the user moving the 256 * cursor very slowly across the screen. */ 257 if (abs(priv->x_tally) < 3 && abs(priv->y_tally) < 3) { 258 hgpk_err(psmouse, "packet spew detected (%d,%d)\n", 259 priv->x_tally, priv->y_tally); 260 priv->spew_flag = RECALIBRATING; 261 psmouse_queue_work(psmouse, &priv->recalib_wq, 262 msecs_to_jiffies(spew_delay)); 263 } 264 265 break; 266 case RECALIBRATING: 267 /* we already detected a spew and requested a recalibration, 268 * just wait for the queue to kick into action. */ 269 break; 270 } 271 } 272 273 /* 274 * HGPK Mouse Mode format (standard mouse format, sans middle button) 275 * 276 * byte 0: y-over x-over y-neg x-neg 1 0 swr swl 277 * byte 1: x7 x6 x5 x4 x3 x2 x1 x0 278 * byte 2: y7 y6 y5 y4 y3 y2 y1 y0 279 * 280 * swr/swl are the left/right buttons. 281 * x-neg/y-neg are the x and y delta negative bits 282 * x-over/y-over are the x and y overflow bits 283 * 284 * --- 285 * 286 * HGPK Advanced Mode - single-mode format 287 * 288 * byte 0(PT): 1 1 0 0 1 1 1 1 289 * byte 0(GS): 1 1 1 1 1 1 1 1 290 * byte 1: 0 x6 x5 x4 x3 x2 x1 x0 291 * byte 2(PT): 0 0 x9 x8 x7 ? pt-dsw 0 292 * byte 2(GS): 0 x10 x9 x8 x7 ? gs-dsw pt-dsw 293 * byte 3: 0 y9 y8 y7 1 0 swr swl 294 * byte 4: 0 y6 y5 y4 y3 y2 y1 y0 295 * byte 5: 0 z6 z5 z4 z3 z2 z1 z0 296 * 297 * ?'s are not defined in the protocol spec, may vary between models. 298 * 299 * swr/swl are the left/right buttons. 300 * 301 * pt-dsw/gs-dsw indicate that the pt/gs sensor is detecting a 302 * pen/finger 303 */ 304 static bool hgpk_is_byte_valid(struct psmouse *psmouse, unsigned char *packet) 305 { 306 struct hgpk_data *priv = psmouse->private; 307 int pktcnt = psmouse->pktcnt; 308 bool valid; 309 310 switch (priv->mode) { 311 case HGPK_MODE_MOUSE: 312 valid = (packet[0] & 0x0C) == 0x08; 313 break; 314 315 case HGPK_MODE_GLIDESENSOR: 316 valid = pktcnt == 1 ? 317 packet[0] == HGPK_GS : !(packet[pktcnt - 1] & 0x80); 318 break; 319 320 case HGPK_MODE_PENTABLET: 321 valid = pktcnt == 1 ? 322 packet[0] == HGPK_PT : !(packet[pktcnt - 1] & 0x80); 323 break; 324 325 default: 326 valid = false; 327 break; 328 } 329 330 if (!valid) 331 hgpk_dbg(psmouse, 332 "bad data, mode %d (%d) %02x %02x %02x %02x %02x %02x\n", 333 priv->mode, pktcnt, 334 psmouse->packet[0], psmouse->packet[1], 335 psmouse->packet[2], psmouse->packet[3], 336 psmouse->packet[4], psmouse->packet[5]); 337 338 return valid; 339 } 340 341 static void hgpk_process_advanced_packet(struct psmouse *psmouse) 342 { 343 struct hgpk_data *priv = psmouse->private; 344 struct input_dev *idev = psmouse->dev; 345 unsigned char *packet = psmouse->packet; 346 int down = !!(packet[2] & 2); 347 int left = !!(packet[3] & 1); 348 int right = !!(packet[3] & 2); 349 int x = packet[1] | ((packet[2] & 0x78) << 4); 350 int y = packet[4] | ((packet[3] & 0x70) << 3); 351 352 if (priv->mode == HGPK_MODE_GLIDESENSOR) { 353 int pt_down = !!(packet[2] & 1); 354 int finger_down = !!(packet[2] & 2); 355 int z = packet[5]; 356 357 input_report_abs(idev, ABS_PRESSURE, z); 358 if (tpdebug) 359 hgpk_dbg(psmouse, "pd=%d fd=%d z=%d", 360 pt_down, finger_down, z); 361 } else { 362 /* 363 * PenTablet mode does not report pressure, so we don't 364 * report it here 365 */ 366 if (tpdebug) 367 hgpk_dbg(psmouse, "pd=%d ", down); 368 } 369 370 if (tpdebug) 371 hgpk_dbg(psmouse, "l=%d r=%d x=%d y=%d\n", left, right, x, y); 372 373 input_report_key(idev, BTN_TOUCH, down); 374 input_report_key(idev, BTN_LEFT, left); 375 input_report_key(idev, BTN_RIGHT, right); 376 377 /* 378 * If this packet says that the finger was removed, reset our position 379 * tracking so that we don't erroneously detect a jump on next press. 380 */ 381 if (!down) { 382 hgpk_reset_hack_state(psmouse); 383 goto done; 384 } 385 386 /* 387 * Weed out duplicate packets (we get quite a few, and they mess up 388 * our jump detection) 389 */ 390 if (x == priv->abs_x && y == priv->abs_y) { 391 if (++priv->dupe_count > SPEW_WATCH_COUNT) { 392 if (tpdebug) 393 hgpk_dbg(psmouse, "hard spew detected\n"); 394 priv->spew_flag = RECALIBRATING; 395 psmouse_queue_work(psmouse, &priv->recalib_wq, 396 msecs_to_jiffies(spew_delay)); 397 } 398 goto done; 399 } 400 401 /* not a duplicate, continue with position reporting */ 402 priv->dupe_count = 0; 403 404 /* Don't apply hacks in PT mode, it seems reliable */ 405 if (priv->mode != HGPK_MODE_PENTABLET && priv->abs_x != -1) { 406 int x_diff = priv->abs_x - x; 407 int y_diff = priv->abs_y - y; 408 if (hgpk_discard_decay_hack(psmouse, x_diff, y_diff)) { 409 if (tpdebug) 410 hgpk_dbg(psmouse, "discarding\n"); 411 goto done; 412 } 413 hgpk_spewing_hack(psmouse, left, right, x_diff, y_diff); 414 } 415 416 input_report_abs(idev, ABS_X, x); 417 input_report_abs(idev, ABS_Y, y); 418 priv->abs_x = x; 419 priv->abs_y = y; 420 421 done: 422 input_sync(idev); 423 } 424 425 static void hgpk_process_simple_packet(struct psmouse *psmouse) 426 { 427 struct input_dev *dev = psmouse->dev; 428 unsigned char *packet = psmouse->packet; 429 int left = packet[0] & 1; 430 int right = (packet[0] >> 1) & 1; 431 int x = packet[1] - ((packet[0] << 4) & 0x100); 432 int y = ((packet[0] << 3) & 0x100) - packet[2]; 433 434 if (hgpk_discard_decay_hack(psmouse, x, y)) { 435 if (tpdebug) 436 hgpk_dbg(psmouse, "discarding\n"); 437 return; 438 } 439 440 hgpk_spewing_hack(psmouse, left, right, x, y); 441 442 if (tpdebug) 443 hgpk_dbg(psmouse, "l=%d r=%d x=%d y=%d\n", left, right, x, y); 444 445 input_report_key(dev, BTN_LEFT, left); 446 input_report_key(dev, BTN_RIGHT, right); 447 448 input_report_rel(dev, REL_X, x); 449 input_report_rel(dev, REL_Y, y); 450 451 input_sync(dev); 452 } 453 454 static psmouse_ret_t hgpk_process_byte(struct psmouse *psmouse) 455 { 456 struct hgpk_data *priv = psmouse->private; 457 458 if (!hgpk_is_byte_valid(psmouse, psmouse->packet)) 459 return PSMOUSE_BAD_DATA; 460 461 if (psmouse->pktcnt >= psmouse->pktsize) { 462 if (priv->mode == HGPK_MODE_MOUSE) 463 hgpk_process_simple_packet(psmouse); 464 else 465 hgpk_process_advanced_packet(psmouse); 466 return PSMOUSE_FULL_PACKET; 467 } 468 469 if (priv->recalib_window) { 470 if (time_before(jiffies, priv->recalib_window)) { 471 /* 472 * ugh, got a packet inside our recalibration 473 * window, schedule another recalibration. 474 */ 475 hgpk_dbg(psmouse, 476 "packet inside calibration window, " 477 "queueing another recalibration\n"); 478 psmouse_queue_work(psmouse, &priv->recalib_wq, 479 msecs_to_jiffies(post_interrupt_delay)); 480 } 481 priv->recalib_window = 0; 482 } 483 484 return PSMOUSE_GOOD_DATA; 485 } 486 487 static int hgpk_select_mode(struct psmouse *psmouse) 488 { 489 struct ps2dev *ps2dev = &psmouse->ps2dev; 490 struct hgpk_data *priv = psmouse->private; 491 int i; 492 int cmd; 493 494 /* 495 * 4 disables to enable advanced mode 496 * then 3 0xf2 bytes as the preamble for GS/PT selection 497 */ 498 const int advanced_init[] = { 499 PSMOUSE_CMD_DISABLE, PSMOUSE_CMD_DISABLE, 500 PSMOUSE_CMD_DISABLE, PSMOUSE_CMD_DISABLE, 501 0xf2, 0xf2, 0xf2, 502 }; 503 504 switch (priv->mode) { 505 case HGPK_MODE_MOUSE: 506 psmouse->pktsize = 3; 507 break; 508 509 case HGPK_MODE_GLIDESENSOR: 510 case HGPK_MODE_PENTABLET: 511 psmouse->pktsize = 6; 512 513 /* Switch to 'Advanced mode.', four disables in a row. */ 514 for (i = 0; i < ARRAY_SIZE(advanced_init); i++) 515 if (ps2_command(ps2dev, NULL, advanced_init[i])) 516 return -EIO; 517 518 /* select between GlideSensor (mouse) or PenTablet */ 519 cmd = priv->mode == HGPK_MODE_GLIDESENSOR ? 520 PSMOUSE_CMD_SETSCALE11 : PSMOUSE_CMD_SETSCALE21; 521 522 if (ps2_command(ps2dev, NULL, cmd)) 523 return -EIO; 524 break; 525 526 default: 527 return -EINVAL; 528 } 529 530 return 0; 531 } 532 533 static void hgpk_setup_input_device(struct input_dev *input, 534 struct input_dev *old_input, 535 enum hgpk_mode mode) 536 { 537 if (old_input) { 538 input->name = old_input->name; 539 input->phys = old_input->phys; 540 input->id = old_input->id; 541 input->dev.parent = old_input->dev.parent; 542 } 543 544 memset(input->evbit, 0, sizeof(input->evbit)); 545 memset(input->relbit, 0, sizeof(input->relbit)); 546 memset(input->keybit, 0, sizeof(input->keybit)); 547 548 /* All modes report left and right buttons */ 549 __set_bit(EV_KEY, input->evbit); 550 __set_bit(BTN_LEFT, input->keybit); 551 __set_bit(BTN_RIGHT, input->keybit); 552 553 switch (mode) { 554 case HGPK_MODE_MOUSE: 555 __set_bit(EV_REL, input->evbit); 556 __set_bit(REL_X, input->relbit); 557 __set_bit(REL_Y, input->relbit); 558 break; 559 560 case HGPK_MODE_GLIDESENSOR: 561 __set_bit(BTN_TOUCH, input->keybit); 562 __set_bit(BTN_TOOL_FINGER, input->keybit); 563 564 __set_bit(EV_ABS, input->evbit); 565 566 /* GlideSensor has pressure sensor, PenTablet does not */ 567 input_set_abs_params(input, ABS_PRESSURE, 0, 15, 0, 0); 568 569 /* From device specs */ 570 input_set_abs_params(input, ABS_X, 0, 399, 0, 0); 571 input_set_abs_params(input, ABS_Y, 0, 290, 0, 0); 572 573 /* Calculated by hand based on usable size (52mm x 38mm) */ 574 input_abs_set_res(input, ABS_X, 8); 575 input_abs_set_res(input, ABS_Y, 8); 576 break; 577 578 case HGPK_MODE_PENTABLET: 579 __set_bit(BTN_TOUCH, input->keybit); 580 __set_bit(BTN_TOOL_FINGER, input->keybit); 581 582 __set_bit(EV_ABS, input->evbit); 583 584 /* From device specs */ 585 input_set_abs_params(input, ABS_X, 0, 999, 0, 0); 586 input_set_abs_params(input, ABS_Y, 5, 239, 0, 0); 587 588 /* Calculated by hand based on usable size (156mm x 38mm) */ 589 input_abs_set_res(input, ABS_X, 6); 590 input_abs_set_res(input, ABS_Y, 8); 591 break; 592 593 default: 594 BUG(); 595 } 596 } 597 598 static int hgpk_reset_device(struct psmouse *psmouse, bool recalibrate) 599 { 600 int err; 601 602 psmouse_reset(psmouse); 603 604 if (recalibrate) { 605 struct ps2dev *ps2dev = &psmouse->ps2dev; 606 607 /* send the recalibrate request */ 608 if (ps2_command(ps2dev, NULL, 0xf5) || 609 ps2_command(ps2dev, NULL, 0xf5) || 610 ps2_command(ps2dev, NULL, 0xe6) || 611 ps2_command(ps2dev, NULL, 0xf5)) { 612 return -1; 613 } 614 615 /* according to ALPS, 150mS is required for recalibration */ 616 msleep(150); 617 } 618 619 err = hgpk_select_mode(psmouse); 620 if (err) { 621 hgpk_err(psmouse, "failed to select mode\n"); 622 return err; 623 } 624 625 hgpk_reset_hack_state(psmouse); 626 627 return 0; 628 } 629 630 static int hgpk_force_recalibrate(struct psmouse *psmouse) 631 { 632 struct ps2dev *ps2dev = &psmouse->ps2dev; 633 struct hgpk_data *priv = psmouse->private; 634 int err; 635 636 /* C-series touchpads added the recalibrate command */ 637 if (psmouse->model < HGPK_MODEL_C) 638 return 0; 639 640 /* we don't want to race with the irq handler, nor with resyncs */ 641 psmouse_set_state(psmouse, PSMOUSE_INITIALIZING); 642 643 /* start by resetting the device */ 644 err = hgpk_reset_device(psmouse, true); 645 if (err) 646 return err; 647 648 /* 649 * XXX: If a finger is down during this delay, recalibration will 650 * detect capacitance incorrectly. This is a hardware bug, and 651 * we don't have a good way to deal with it. The 2s window stuff 652 * (below) is our best option for now. 653 */ 654 655 if (ps2_command(ps2dev, NULL, PSMOUSE_CMD_ENABLE)) 656 return -1; 657 658 psmouse_set_state(psmouse, PSMOUSE_ACTIVATED); 659 660 /* 661 * After we recalibrate, we shouldn't get any packets for 2s. If 662 * we do, it's likely that someone's finger was on the touchpad. 663 * If someone's finger *was* on the touchpad, it's probably 664 * miscalibrated. So, we should schedule another recalibration 665 */ 666 priv->recalib_window = jiffies + msecs_to_jiffies(recal_guard_time); 667 668 return 0; 669 } 670 671 /* 672 * This kills power to the touchpad; according to ALPS, current consumption 673 * goes down to 50uA after running this. To turn power back on, we drive 674 * MS-DAT low. 675 */ 676 static int hgpk_toggle_power(struct psmouse *psmouse, int enable) 677 { 678 struct ps2dev *ps2dev = &psmouse->ps2dev; 679 int timeo; 680 int err; 681 682 /* Added on D-series touchpads */ 683 if (psmouse->model < HGPK_MODEL_D) 684 return 0; 685 686 if (enable) { 687 psmouse_set_state(psmouse, PSMOUSE_INITIALIZING); 688 689 /* 690 * Sending a byte will drive MS-DAT low; this will wake up 691 * the controller. Once we get an ACK back from it, it 692 * means we can continue with the touchpad re-init. ALPS 693 * tells us that 1s should be long enough, so set that as 694 * the upper bound. 695 */ 696 for (timeo = 20; timeo > 0; timeo--) { 697 if (!ps2_sendbyte(&psmouse->ps2dev, 698 PSMOUSE_CMD_DISABLE, 20)) 699 break; 700 msleep(50); 701 } 702 703 err = hgpk_reset_device(psmouse, false); 704 if (err) { 705 hgpk_err(psmouse, "Failed to reset device!\n"); 706 return err; 707 } 708 709 /* should be all set, enable the touchpad */ 710 ps2_command(&psmouse->ps2dev, NULL, PSMOUSE_CMD_ENABLE); 711 psmouse_set_state(psmouse, PSMOUSE_ACTIVATED); 712 713 } else { 714 hgpk_dbg(psmouse, "Powering off touchpad.\n"); 715 psmouse_set_state(psmouse, PSMOUSE_IGNORE); 716 717 if (ps2_command(ps2dev, NULL, 0xec) || 718 ps2_command(ps2dev, NULL, 0xec) || 719 ps2_command(ps2dev, NULL, 0xea)) { 720 return -1; 721 } 722 723 /* probably won't see an ACK, the touchpad will be off */ 724 ps2_sendbyte(&psmouse->ps2dev, 0xec, 20); 725 } 726 727 return 0; 728 } 729 730 static int hgpk_poll(struct psmouse *psmouse) 731 { 732 /* We can't poll, so always return failure. */ 733 return -1; 734 } 735 736 static int hgpk_reconnect(struct psmouse *psmouse) 737 { 738 /* 739 * During suspend/resume the ps2 rails remain powered. We don't want 740 * to do a reset because it's flush data out of buffers; however, 741 * earlier prototypes (B1) had some brokenness that required a reset. 742 */ 743 if (olpc_board_at_least(olpc_board(0xb2))) 744 if (psmouse->ps2dev.serio->dev.power.power_state.event != 745 PM_EVENT_ON) 746 return 0; 747 748 return hgpk_reset_device(psmouse, false); 749 } 750 751 static ssize_t hgpk_show_powered(struct psmouse *psmouse, void *data, char *buf) 752 { 753 struct hgpk_data *priv = psmouse->private; 754 755 return sprintf(buf, "%d\n", priv->powered); 756 } 757 758 static ssize_t hgpk_set_powered(struct psmouse *psmouse, void *data, 759 const char *buf, size_t count) 760 { 761 struct hgpk_data *priv = psmouse->private; 762 unsigned long value; 763 int err; 764 765 err = strict_strtoul(buf, 10, &value); 766 if (err || value > 1) 767 return -EINVAL; 768 769 if (value != priv->powered) { 770 /* 771 * hgpk_toggle_power will deal w/ state so 772 * we're not racing w/ irq 773 */ 774 err = hgpk_toggle_power(psmouse, value); 775 if (!err) 776 priv->powered = value; 777 } 778 779 return err ? err : count; 780 } 781 782 __PSMOUSE_DEFINE_ATTR(powered, S_IWUSR | S_IRUGO, NULL, 783 hgpk_show_powered, hgpk_set_powered, false); 784 785 static ssize_t attr_show_mode(struct psmouse *psmouse, void *data, char *buf) 786 { 787 struct hgpk_data *priv = psmouse->private; 788 789 return sprintf(buf, "%s\n", hgpk_mode_names[priv->mode]); 790 } 791 792 static ssize_t attr_set_mode(struct psmouse *psmouse, void *data, 793 const char *buf, size_t len) 794 { 795 struct hgpk_data *priv = psmouse->private; 796 enum hgpk_mode old_mode = priv->mode; 797 enum hgpk_mode new_mode = hgpk_mode_from_name(buf, len); 798 struct input_dev *old_dev = psmouse->dev; 799 struct input_dev *new_dev; 800 int err; 801 802 if (new_mode == HGPK_MODE_INVALID) 803 return -EINVAL; 804 805 if (old_mode == new_mode) 806 return len; 807 808 new_dev = input_allocate_device(); 809 if (!new_dev) 810 return -ENOMEM; 811 812 psmouse_set_state(psmouse, PSMOUSE_INITIALIZING); 813 814 /* Switch device into the new mode */ 815 priv->mode = new_mode; 816 err = hgpk_reset_device(psmouse, false); 817 if (err) 818 goto err_try_restore; 819 820 hgpk_setup_input_device(new_dev, old_dev, new_mode); 821 822 psmouse_set_state(psmouse, PSMOUSE_CMD_MODE); 823 824 err = input_register_device(new_dev); 825 if (err) 826 goto err_try_restore; 827 828 psmouse->dev = new_dev; 829 input_unregister_device(old_dev); 830 831 return len; 832 833 err_try_restore: 834 input_free_device(new_dev); 835 priv->mode = old_mode; 836 hgpk_reset_device(psmouse, false); 837 838 return err; 839 } 840 841 PSMOUSE_DEFINE_ATTR(hgpk_mode, S_IWUSR | S_IRUGO, NULL, 842 attr_show_mode, attr_set_mode); 843 844 static ssize_t hgpk_trigger_recal_show(struct psmouse *psmouse, 845 void *data, char *buf) 846 { 847 return -EINVAL; 848 } 849 850 static ssize_t hgpk_trigger_recal(struct psmouse *psmouse, void *data, 851 const char *buf, size_t count) 852 { 853 struct hgpk_data *priv = psmouse->private; 854 unsigned long value; 855 int err; 856 857 err = strict_strtoul(buf, 10, &value); 858 if (err || value != 1) 859 return -EINVAL; 860 861 /* 862 * We queue work instead of doing recalibration right here 863 * to avoid adding locking to to hgpk_force_recalibrate() 864 * since workqueue provides serialization. 865 */ 866 psmouse_queue_work(psmouse, &priv->recalib_wq, 0); 867 return count; 868 } 869 870 __PSMOUSE_DEFINE_ATTR(recalibrate, S_IWUSR | S_IRUGO, NULL, 871 hgpk_trigger_recal_show, hgpk_trigger_recal, false); 872 873 static void hgpk_disconnect(struct psmouse *psmouse) 874 { 875 struct hgpk_data *priv = psmouse->private; 876 877 device_remove_file(&psmouse->ps2dev.serio->dev, 878 &psmouse_attr_powered.dattr); 879 device_remove_file(&psmouse->ps2dev.serio->dev, 880 &psmouse_attr_hgpk_mode.dattr); 881 882 if (psmouse->model >= HGPK_MODEL_C) 883 device_remove_file(&psmouse->ps2dev.serio->dev, 884 &psmouse_attr_recalibrate.dattr); 885 886 psmouse_reset(psmouse); 887 kfree(priv); 888 } 889 890 static void hgpk_recalib_work(struct work_struct *work) 891 { 892 struct delayed_work *w = to_delayed_work(work); 893 struct hgpk_data *priv = container_of(w, struct hgpk_data, recalib_wq); 894 struct psmouse *psmouse = priv->psmouse; 895 896 hgpk_dbg(psmouse, "recalibrating touchpad..\n"); 897 898 if (hgpk_force_recalibrate(psmouse)) 899 hgpk_err(psmouse, "recalibration failed!\n"); 900 } 901 902 static int hgpk_register(struct psmouse *psmouse) 903 { 904 struct hgpk_data *priv = psmouse->private; 905 int err; 906 907 /* register handlers */ 908 psmouse->protocol_handler = hgpk_process_byte; 909 psmouse->poll = hgpk_poll; 910 psmouse->disconnect = hgpk_disconnect; 911 psmouse->reconnect = hgpk_reconnect; 912 913 /* Disable the idle resync. */ 914 psmouse->resync_time = 0; 915 /* Reset after a lot of bad bytes. */ 916 psmouse->resetafter = 1024; 917 918 hgpk_setup_input_device(psmouse->dev, NULL, priv->mode); 919 920 err = device_create_file(&psmouse->ps2dev.serio->dev, 921 &psmouse_attr_powered.dattr); 922 if (err) { 923 hgpk_err(psmouse, "Failed creating 'powered' sysfs node\n"); 924 return err; 925 } 926 927 err = device_create_file(&psmouse->ps2dev.serio->dev, 928 &psmouse_attr_hgpk_mode.dattr); 929 if (err) { 930 hgpk_err(psmouse, "Failed creating 'hgpk_mode' sysfs node\n"); 931 goto err_remove_powered; 932 } 933 934 /* C-series touchpads added the recalibrate command */ 935 if (psmouse->model >= HGPK_MODEL_C) { 936 err = device_create_file(&psmouse->ps2dev.serio->dev, 937 &psmouse_attr_recalibrate.dattr); 938 if (err) { 939 hgpk_err(psmouse, 940 "Failed creating 'recalibrate' sysfs node\n"); 941 goto err_remove_mode; 942 } 943 } 944 945 return 0; 946 947 err_remove_mode: 948 device_remove_file(&psmouse->ps2dev.serio->dev, 949 &psmouse_attr_hgpk_mode.dattr); 950 err_remove_powered: 951 device_remove_file(&psmouse->ps2dev.serio->dev, 952 &psmouse_attr_powered.dattr); 953 return err; 954 } 955 956 int hgpk_init(struct psmouse *psmouse) 957 { 958 struct hgpk_data *priv; 959 int err; 960 961 priv = kzalloc(sizeof(struct hgpk_data), GFP_KERNEL); 962 if (!priv) { 963 err = -ENOMEM; 964 goto alloc_fail; 965 } 966 967 psmouse->private = priv; 968 969 priv->psmouse = psmouse; 970 priv->powered = true; 971 priv->mode = hgpk_default_mode; 972 INIT_DELAYED_WORK(&priv->recalib_wq, hgpk_recalib_work); 973 974 err = hgpk_reset_device(psmouse, false); 975 if (err) 976 goto init_fail; 977 978 err = hgpk_register(psmouse); 979 if (err) 980 goto init_fail; 981 982 return 0; 983 984 init_fail: 985 kfree(priv); 986 alloc_fail: 987 return err; 988 } 989 990 static enum hgpk_model_t hgpk_get_model(struct psmouse *psmouse) 991 { 992 struct ps2dev *ps2dev = &psmouse->ps2dev; 993 unsigned char param[3]; 994 995 /* E7, E7, E7, E9 gets us a 3 byte identifier */ 996 if (ps2_command(ps2dev, NULL, PSMOUSE_CMD_SETSCALE21) || 997 ps2_command(ps2dev, NULL, PSMOUSE_CMD_SETSCALE21) || 998 ps2_command(ps2dev, NULL, PSMOUSE_CMD_SETSCALE21) || 999 ps2_command(ps2dev, param, PSMOUSE_CMD_GETINFO)) { 1000 return -EIO; 1001 } 1002 1003 hgpk_dbg(psmouse, "ID: %02x %02x %02x\n", param[0], param[1], param[2]); 1004 1005 /* HGPK signature: 0x67, 0x00, 0x<model> */ 1006 if (param[0] != 0x67 || param[1] != 0x00) 1007 return -ENODEV; 1008 1009 hgpk_info(psmouse, "OLPC touchpad revision 0x%x\n", param[2]); 1010 1011 return param[2]; 1012 } 1013 1014 int hgpk_detect(struct psmouse *psmouse, bool set_properties) 1015 { 1016 int version; 1017 1018 version = hgpk_get_model(psmouse); 1019 if (version < 0) 1020 return version; 1021 1022 if (set_properties) { 1023 psmouse->vendor = "ALPS"; 1024 psmouse->name = "HGPK"; 1025 psmouse->model = version; 1026 } 1027 1028 return 0; 1029 } 1030 1031 void hgpk_module_init(void) 1032 { 1033 hgpk_default_mode = hgpk_mode_from_name(hgpk_mode_name, 1034 strlen(hgpk_mode_name)); 1035 if (hgpk_default_mode == HGPK_MODE_INVALID) { 1036 hgpk_default_mode = HGPK_MODE_MOUSE; 1037 strlcpy(hgpk_mode_name, hgpk_mode_names[HGPK_MODE_MOUSE], 1038 sizeof(hgpk_mode_name)); 1039 } 1040 } 1041