1 | // SPDX-License-Identifier: GPL-2.0-or-later |
2 | /* |
3 | * Apple USB Touchpad (for post-February 2005 PowerBooks and MacBooks) driver |
4 | * |
5 | * Copyright (C) 2001-2004 Greg Kroah-Hartman (greg@kroah.com) |
6 | * Copyright (C) 2005-2008 Johannes Berg (johannes@sipsolutions.net) |
7 | * Copyright (C) 2005-2008 Stelian Pop (stelian@popies.net) |
8 | * Copyright (C) 2005 Frank Arnold (frank@scirocco-5v-turbo.de) |
9 | * Copyright (C) 2005 Peter Osterlund (petero2@telia.com) |
10 | * Copyright (C) 2005 Michael Hanselmann (linux-kernel@hansmi.ch) |
11 | * Copyright (C) 2006 Nicolas Boichat (nicolas@boichat.ch) |
12 | * Copyright (C) 2007-2008 Sven Anders (anders@anduras.de) |
13 | * |
14 | * Thanks to Alex Harper <basilisk@foobox.net> for his inputs. |
15 | */ |
16 | |
17 | #include <linux/kernel.h> |
18 | #include <linux/errno.h> |
19 | #include <linux/slab.h> |
20 | #include <linux/module.h> |
21 | #include <linux/usb/input.h> |
22 | |
23 | /* |
24 | * Note: We try to keep the touchpad aspect ratio while still doing only |
25 | * simple arithmetics: |
26 | * 0 <= x <= (xsensors - 1) * xfact |
27 | * 0 <= y <= (ysensors - 1) * yfact |
28 | */ |
29 | struct atp_info { |
30 | int xsensors; /* number of X sensors */ |
31 | int xsensors_17; /* 17" models have more sensors */ |
32 | int ysensors; /* number of Y sensors */ |
33 | int xfact; /* X multiplication factor */ |
34 | int yfact; /* Y multiplication factor */ |
35 | int datalen; /* size of USB transfers */ |
36 | void (*callback)(struct urb *); /* callback function */ |
37 | int fuzz; /* fuzz touchpad generates */ |
38 | }; |
39 | |
40 | static void atp_complete_geyser_1_2(struct urb *urb); |
41 | static void atp_complete_geyser_3_4(struct urb *urb); |
42 | |
43 | static const struct atp_info fountain_info = { |
44 | .xsensors = 16, |
45 | .xsensors_17 = 26, |
46 | .ysensors = 16, |
47 | .xfact = 64, |
48 | .yfact = 43, |
49 | .datalen = 81, |
50 | .callback = atp_complete_geyser_1_2, |
51 | .fuzz = 16, |
52 | }; |
53 | |
54 | static const struct atp_info geyser1_info = { |
55 | .xsensors = 16, |
56 | .xsensors_17 = 26, |
57 | .ysensors = 16, |
58 | .xfact = 64, |
59 | .yfact = 43, |
60 | .datalen = 81, |
61 | .callback = atp_complete_geyser_1_2, |
62 | .fuzz = 16, |
63 | }; |
64 | |
65 | static const struct atp_info geyser2_info = { |
66 | .xsensors = 15, |
67 | .xsensors_17 = 20, |
68 | .ysensors = 9, |
69 | .xfact = 64, |
70 | .yfact = 43, |
71 | .datalen = 64, |
72 | .callback = atp_complete_geyser_1_2, |
73 | .fuzz = 0, |
74 | }; |
75 | |
76 | static const struct atp_info geyser3_info = { |
77 | .xsensors = 20, |
78 | .ysensors = 10, |
79 | .xfact = 64, |
80 | .yfact = 64, |
81 | .datalen = 64, |
82 | .callback = atp_complete_geyser_3_4, |
83 | .fuzz = 0, |
84 | }; |
85 | |
86 | static const struct atp_info geyser4_info = { |
87 | .xsensors = 20, |
88 | .ysensors = 10, |
89 | .xfact = 64, |
90 | .yfact = 64, |
91 | .datalen = 64, |
92 | .callback = atp_complete_geyser_3_4, |
93 | .fuzz = 0, |
94 | }; |
95 | |
96 | #define ATP_DEVICE(prod, info) \ |
97 | { \ |
98 | .match_flags = USB_DEVICE_ID_MATCH_DEVICE | \ |
99 | USB_DEVICE_ID_MATCH_INT_CLASS | \ |
100 | USB_DEVICE_ID_MATCH_INT_PROTOCOL, \ |
101 | .idVendor = 0x05ac, /* Apple */ \ |
102 | .idProduct = (prod), \ |
103 | .bInterfaceClass = 0x03, \ |
104 | .bInterfaceProtocol = 0x02, \ |
105 | .driver_info = (unsigned long) &info, \ |
106 | } |
107 | |
108 | /* |
109 | * Table of devices (Product IDs) that work with this driver. |
110 | * (The names come from Info.plist in AppleUSBTrackpad.kext, |
111 | * According to Info.plist Geyser IV is the same as Geyser III.) |
112 | */ |
113 | |
114 | static const struct usb_device_id atp_table[] = { |
115 | /* PowerBooks Feb 2005, iBooks G4 */ |
116 | ATP_DEVICE(0x020e, fountain_info), /* FOUNTAIN ANSI */ |
117 | ATP_DEVICE(0x020f, fountain_info), /* FOUNTAIN ISO */ |
118 | ATP_DEVICE(0x030a, fountain_info), /* FOUNTAIN TP ONLY */ |
119 | ATP_DEVICE(0x030b, geyser1_info), /* GEYSER 1 TP ONLY */ |
120 | |
121 | /* PowerBooks Oct 2005 */ |
122 | ATP_DEVICE(0x0214, geyser2_info), /* GEYSER 2 ANSI */ |
123 | ATP_DEVICE(0x0215, geyser2_info), /* GEYSER 2 ISO */ |
124 | ATP_DEVICE(0x0216, geyser2_info), /* GEYSER 2 JIS */ |
125 | |
126 | /* Core Duo MacBook & MacBook Pro */ |
127 | ATP_DEVICE(0x0217, geyser3_info), /* GEYSER 3 ANSI */ |
128 | ATP_DEVICE(0x0218, geyser3_info), /* GEYSER 3 ISO */ |
129 | ATP_DEVICE(0x0219, geyser3_info), /* GEYSER 3 JIS */ |
130 | |
131 | /* Core2 Duo MacBook & MacBook Pro */ |
132 | ATP_DEVICE(0x021a, geyser4_info), /* GEYSER 4 ANSI */ |
133 | ATP_DEVICE(0x021b, geyser4_info), /* GEYSER 4 ISO */ |
134 | ATP_DEVICE(0x021c, geyser4_info), /* GEYSER 4 JIS */ |
135 | |
136 | /* Core2 Duo MacBook3,1 */ |
137 | ATP_DEVICE(0x0229, geyser4_info), /* GEYSER 4 HF ANSI */ |
138 | ATP_DEVICE(0x022a, geyser4_info), /* GEYSER 4 HF ISO */ |
139 | ATP_DEVICE(0x022b, geyser4_info), /* GEYSER 4 HF JIS */ |
140 | |
141 | /* Terminating entry */ |
142 | { } |
143 | }; |
144 | MODULE_DEVICE_TABLE(usb, atp_table); |
145 | |
146 | /* maximum number of sensors */ |
147 | #define ATP_XSENSORS 26 |
148 | #define ATP_YSENSORS 16 |
149 | |
150 | /* |
151 | * The largest possible bank of sensors with additional buffer of 4 extra values |
152 | * on either side, for an array of smoothed sensor values. |
153 | */ |
154 | #define ATP_SMOOTHSIZE 34 |
155 | |
156 | /* maximum pressure this driver will report */ |
157 | #define ATP_PRESSURE 300 |
158 | |
159 | /* |
160 | * Threshold for the touchpad sensors. Any change less than ATP_THRESHOLD is |
161 | * ignored. |
162 | */ |
163 | #define ATP_THRESHOLD 5 |
164 | |
165 | /* |
166 | * How far we'll bitshift our sensor values before averaging them. Mitigates |
167 | * rounding errors. |
168 | */ |
169 | #define ATP_SCALE 12 |
170 | |
171 | /* Geyser initialization constants */ |
172 | #define ATP_GEYSER_MODE_READ_REQUEST_ID 1 |
173 | #define ATP_GEYSER_MODE_WRITE_REQUEST_ID 9 |
174 | #define ATP_GEYSER_MODE_REQUEST_VALUE 0x300 |
175 | #define ATP_GEYSER_MODE_REQUEST_INDEX 0 |
176 | #define ATP_GEYSER_MODE_VENDOR_VALUE 0x04 |
177 | |
178 | /** |
179 | * enum atp_status_bits - status bit meanings |
180 | * |
181 | * These constants represent the meaning of the status bits. |
182 | * (only Geyser 3/4) |
183 | * |
184 | * @ATP_STATUS_BUTTON: The button was pressed |
185 | * @ATP_STATUS_BASE_UPDATE: Update of the base values (untouched pad) |
186 | * @ATP_STATUS_FROM_RESET: Reset previously performed |
187 | */ |
188 | enum atp_status_bits { |
189 | ATP_STATUS_BUTTON = BIT(0), |
190 | ATP_STATUS_BASE_UPDATE = BIT(2), |
191 | ATP_STATUS_FROM_RESET = BIT(4), |
192 | }; |
193 | |
194 | /* Structure to hold all of our device specific stuff */ |
195 | struct atp { |
196 | char phys[64]; |
197 | struct usb_device *udev; /* usb device */ |
198 | struct usb_interface *intf; /* usb interface */ |
199 | struct urb *urb; /* usb request block */ |
200 | u8 *data; /* transferred data */ |
201 | struct input_dev *input; /* input dev */ |
202 | const struct atp_info *info; /* touchpad model */ |
203 | bool open; |
204 | bool valid; /* are the samples valid? */ |
205 | bool size_detect_done; |
206 | bool overflow_warned; |
207 | int fingers_old; /* last reported finger count */ |
208 | int x_old; /* last reported x/y, */ |
209 | int y_old; /* used for smoothing */ |
210 | signed char xy_cur[ATP_XSENSORS + ATP_YSENSORS]; |
211 | signed char xy_old[ATP_XSENSORS + ATP_YSENSORS]; |
212 | int xy_acc[ATP_XSENSORS + ATP_YSENSORS]; |
213 | int smooth[ATP_SMOOTHSIZE]; |
214 | int smooth_tmp[ATP_SMOOTHSIZE]; |
215 | int idlecount; /* number of empty packets */ |
216 | struct work_struct work; |
217 | }; |
218 | |
219 | #define dbg_dump(msg, tab) \ |
220 | if (debug > 1) { \ |
221 | int __i; \ |
222 | printk(KERN_DEBUG "appletouch: %s", msg); \ |
223 | for (__i = 0; __i < ATP_XSENSORS + ATP_YSENSORS; __i++) \ |
224 | printk(" %02x", tab[__i]); \ |
225 | printk("\n"); \ |
226 | } |
227 | |
228 | #define dprintk(format, a...) \ |
229 | do { \ |
230 | if (debug) \ |
231 | printk(KERN_DEBUG format, ##a); \ |
232 | } while (0) |
233 | |
234 | MODULE_AUTHOR("Johannes Berg" ); |
235 | MODULE_AUTHOR("Stelian Pop" ); |
236 | MODULE_AUTHOR("Frank Arnold" ); |
237 | MODULE_AUTHOR("Michael Hanselmann" ); |
238 | MODULE_AUTHOR("Sven Anders" ); |
239 | MODULE_DESCRIPTION("Apple PowerBook and MacBook USB touchpad driver" ); |
240 | MODULE_LICENSE("GPL" ); |
241 | |
242 | /* |
243 | * Make the threshold a module parameter |
244 | */ |
245 | static int threshold = ATP_THRESHOLD; |
246 | module_param(threshold, int, 0644); |
247 | MODULE_PARM_DESC(threshold, "Discard any change in data from a sensor" |
248 | " (the trackpad has many of these sensors)" |
249 | " less than this value." ); |
250 | |
251 | static int debug; |
252 | module_param(debug, int, 0644); |
253 | MODULE_PARM_DESC(debug, "Activate debugging output" ); |
254 | |
255 | /* |
256 | * By default newer Geyser devices send standard USB HID mouse |
257 | * packets (Report ID 2). This code changes device mode, so it |
258 | * sends raw sensor reports (Report ID 5). |
259 | */ |
260 | static int atp_geyser_init(struct atp *dev) |
261 | { |
262 | struct usb_device *udev = dev->udev; |
263 | char *data; |
264 | int size; |
265 | int i; |
266 | int ret; |
267 | |
268 | data = kmalloc(size: 8, GFP_KERNEL); |
269 | if (!data) { |
270 | dev_err(&dev->intf->dev, "Out of memory\n" ); |
271 | return -ENOMEM; |
272 | } |
273 | |
274 | size = usb_control_msg(dev: udev, usb_rcvctrlpipe(udev, 0), |
275 | ATP_GEYSER_MODE_READ_REQUEST_ID, |
276 | USB_DIR_IN | USB_TYPE_CLASS | USB_RECIP_INTERFACE, |
277 | ATP_GEYSER_MODE_REQUEST_VALUE, |
278 | ATP_GEYSER_MODE_REQUEST_INDEX, data, size: 8, timeout: 5000); |
279 | |
280 | if (size != 8) { |
281 | dprintk("atp_geyser_init: read error\n" ); |
282 | for (i = 0; i < 8; i++) |
283 | dprintk("appletouch[%d]: %d\n" , i, data[i]); |
284 | |
285 | dev_err(&dev->intf->dev, "Failed to read mode from device.\n" ); |
286 | ret = -EIO; |
287 | goto out_free; |
288 | } |
289 | |
290 | /* Apply the mode switch */ |
291 | data[0] = ATP_GEYSER_MODE_VENDOR_VALUE; |
292 | |
293 | size = usb_control_msg(dev: udev, usb_sndctrlpipe(udev, 0), |
294 | ATP_GEYSER_MODE_WRITE_REQUEST_ID, |
295 | USB_DIR_OUT | USB_TYPE_CLASS | USB_RECIP_INTERFACE, |
296 | ATP_GEYSER_MODE_REQUEST_VALUE, |
297 | ATP_GEYSER_MODE_REQUEST_INDEX, data, size: 8, timeout: 5000); |
298 | |
299 | if (size != 8) { |
300 | dprintk("atp_geyser_init: write error\n" ); |
301 | for (i = 0; i < 8; i++) |
302 | dprintk("appletouch[%d]: %d\n" , i, data[i]); |
303 | |
304 | dev_err(&dev->intf->dev, "Failed to request geyser raw mode\n" ); |
305 | ret = -EIO; |
306 | goto out_free; |
307 | } |
308 | ret = 0; |
309 | out_free: |
310 | kfree(objp: data); |
311 | return ret; |
312 | } |
313 | |
314 | /* |
315 | * Reinitialise the device. This usually stops stream of empty packets |
316 | * coming from it. |
317 | */ |
318 | static void atp_reinit(struct work_struct *work) |
319 | { |
320 | struct atp *dev = container_of(work, struct atp, work); |
321 | int retval; |
322 | |
323 | dprintk("appletouch: putting appletouch to sleep (reinit)\n" ); |
324 | atp_geyser_init(dev); |
325 | |
326 | retval = usb_submit_urb(urb: dev->urb, GFP_ATOMIC); |
327 | if (retval) |
328 | dev_err(&dev->intf->dev, |
329 | "atp_reinit: usb_submit_urb failed with error %d\n" , |
330 | retval); |
331 | } |
332 | |
333 | static int atp_calculate_abs(struct atp *dev, int offset, int nb_sensors, |
334 | int fact, int *z, int *fingers) |
335 | { |
336 | int i, pass; |
337 | |
338 | /* |
339 | * Use offset to point xy_sensors at the first value in dev->xy_acc |
340 | * for whichever dimension we're looking at this particular go-round. |
341 | */ |
342 | int *xy_sensors = dev->xy_acc + offset; |
343 | |
344 | /* values to calculate mean */ |
345 | int pcum = 0, psum = 0; |
346 | int is_increasing = 0; |
347 | |
348 | *fingers = 0; |
349 | |
350 | for (i = 0; i < nb_sensors; i++) { |
351 | if (xy_sensors[i] < threshold) { |
352 | if (is_increasing) |
353 | is_increasing = 0; |
354 | |
355 | /* |
356 | * Makes the finger detection more versatile. For example, |
357 | * two fingers with no gap will be detected. Also, my |
358 | * tests show it less likely to have intermittent loss |
359 | * of multiple finger readings while moving around (scrolling). |
360 | * |
361 | * Changes the multiple finger detection to counting humps on |
362 | * sensors (transitions from nonincreasing to increasing) |
363 | * instead of counting transitions from low sensors (no |
364 | * finger reading) to high sensors (finger above |
365 | * sensor) |
366 | * |
367 | * - Jason Parekh <jasonparekh@gmail.com> |
368 | */ |
369 | |
370 | } else if (i < 1 || |
371 | (!is_increasing && xy_sensors[i - 1] < xy_sensors[i])) { |
372 | (*fingers)++; |
373 | is_increasing = 1; |
374 | } else if (i > 0 && (xy_sensors[i - 1] - xy_sensors[i] > threshold)) { |
375 | is_increasing = 0; |
376 | } |
377 | } |
378 | |
379 | if (*fingers < 1) /* No need to continue if no fingers are found. */ |
380 | return 0; |
381 | |
382 | /* |
383 | * Use a smoothed version of sensor data for movement calculations, to |
384 | * combat noise without needing to rely so heavily on a threshold. |
385 | * This improves tracking. |
386 | * |
387 | * The smoothed array is bigger than the original so that the smoothing |
388 | * doesn't result in edge values being truncated. |
389 | */ |
390 | |
391 | memset(dev->smooth, 0, 4 * sizeof(dev->smooth[0])); |
392 | /* Pull base values, scaled up to help avoid truncation errors. */ |
393 | for (i = 0; i < nb_sensors; i++) |
394 | dev->smooth[i + 4] = xy_sensors[i] << ATP_SCALE; |
395 | memset(&dev->smooth[nb_sensors + 4], 0, 4 * sizeof(dev->smooth[0])); |
396 | |
397 | for (pass = 0; pass < 4; pass++) { |
398 | /* Handle edge. */ |
399 | dev->smooth_tmp[0] = (dev->smooth[0] + dev->smooth[1]) / 2; |
400 | |
401 | /* Average values with neighbors. */ |
402 | for (i = 1; i < nb_sensors + 7; i++) |
403 | dev->smooth_tmp[i] = (dev->smooth[i - 1] + |
404 | dev->smooth[i] * 2 + |
405 | dev->smooth[i + 1]) / 4; |
406 | |
407 | /* Handle other edge. */ |
408 | dev->smooth_tmp[i] = (dev->smooth[i - 1] + dev->smooth[i]) / 2; |
409 | |
410 | memcpy(dev->smooth, dev->smooth_tmp, sizeof(dev->smooth)); |
411 | } |
412 | |
413 | for (i = 0; i < nb_sensors + 8; i++) { |
414 | /* |
415 | * Skip values if they're small enough to be truncated to 0 |
416 | * by scale. Mostly noise. |
417 | */ |
418 | if ((dev->smooth[i] >> ATP_SCALE) > 0) { |
419 | pcum += dev->smooth[i] * i; |
420 | psum += dev->smooth[i]; |
421 | } |
422 | } |
423 | |
424 | if (psum > 0) { |
425 | *z = psum >> ATP_SCALE; /* Scale down pressure output. */ |
426 | return pcum * fact / psum; |
427 | } |
428 | |
429 | return 0; |
430 | } |
431 | |
432 | static inline void atp_report_fingers(struct input_dev *input, int fingers) |
433 | { |
434 | input_report_key(dev: input, BTN_TOOL_FINGER, value: fingers == 1); |
435 | input_report_key(dev: input, BTN_TOOL_DOUBLETAP, value: fingers == 2); |
436 | input_report_key(dev: input, BTN_TOOL_TRIPLETAP, value: fingers > 2); |
437 | } |
438 | |
439 | /* Check URB status and for correct length of data package */ |
440 | |
441 | #define ATP_URB_STATUS_SUCCESS 0 |
442 | #define ATP_URB_STATUS_ERROR 1 |
443 | #define ATP_URB_STATUS_ERROR_FATAL 2 |
444 | |
445 | static int atp_status_check(struct urb *urb) |
446 | { |
447 | struct atp *dev = urb->context; |
448 | struct usb_interface *intf = dev->intf; |
449 | |
450 | switch (urb->status) { |
451 | case 0: |
452 | /* success */ |
453 | break; |
454 | case -EOVERFLOW: |
455 | if (!dev->overflow_warned) { |
456 | dev_warn(&intf->dev, |
457 | "appletouch: OVERFLOW with data length %d, actual length is %d\n" , |
458 | dev->info->datalen, dev->urb->actual_length); |
459 | dev->overflow_warned = true; |
460 | } |
461 | fallthrough; |
462 | case -ECONNRESET: |
463 | case -ENOENT: |
464 | case -ESHUTDOWN: |
465 | /* This urb is terminated, clean up */ |
466 | dev_dbg(&intf->dev, |
467 | "atp_complete: urb shutting down with status: %d\n" , |
468 | urb->status); |
469 | return ATP_URB_STATUS_ERROR_FATAL; |
470 | |
471 | default: |
472 | dev_dbg(&intf->dev, |
473 | "atp_complete: nonzero urb status received: %d\n" , |
474 | urb->status); |
475 | return ATP_URB_STATUS_ERROR; |
476 | } |
477 | |
478 | /* drop incomplete datasets */ |
479 | if (dev->urb->actual_length != dev->info->datalen) { |
480 | dprintk("appletouch: incomplete data package" |
481 | " (first byte: %d, length: %d).\n" , |
482 | dev->data[0], dev->urb->actual_length); |
483 | return ATP_URB_STATUS_ERROR; |
484 | } |
485 | |
486 | return ATP_URB_STATUS_SUCCESS; |
487 | } |
488 | |
489 | static void atp_detect_size(struct atp *dev) |
490 | { |
491 | int i; |
492 | |
493 | /* 17" Powerbooks have extra X sensors */ |
494 | for (i = dev->info->xsensors; i < ATP_XSENSORS; i++) { |
495 | if (dev->xy_cur[i]) { |
496 | |
497 | dev_info(&dev->intf->dev, |
498 | "appletouch: 17\" model detected.\n" ); |
499 | |
500 | input_set_abs_params(dev: dev->input, ABS_X, min: 0, |
501 | max: (dev->info->xsensors_17 - 1) * |
502 | dev->info->xfact - 1, |
503 | fuzz: dev->info->fuzz, flat: 0); |
504 | break; |
505 | } |
506 | } |
507 | } |
508 | |
509 | /* |
510 | * USB interrupt callback functions |
511 | */ |
512 | |
513 | /* Interrupt function for older touchpads: FOUNTAIN/GEYSER1/GEYSER2 */ |
514 | |
515 | static void atp_complete_geyser_1_2(struct urb *urb) |
516 | { |
517 | int x, y, x_z, y_z, x_f, y_f; |
518 | int retval, i, j; |
519 | int key, fingers; |
520 | struct atp *dev = urb->context; |
521 | int status = atp_status_check(urb); |
522 | |
523 | if (status == ATP_URB_STATUS_ERROR_FATAL) |
524 | return; |
525 | else if (status == ATP_URB_STATUS_ERROR) |
526 | goto exit; |
527 | |
528 | /* reorder the sensors values */ |
529 | if (dev->info == &geyser2_info) { |
530 | memset(dev->xy_cur, 0, sizeof(dev->xy_cur)); |
531 | |
532 | /* |
533 | * The values are laid out like this: |
534 | * Y1, Y2, -, Y3, Y4, -, ..., X1, X2, -, X3, X4, -, ... |
535 | * '-' is an unused value. |
536 | */ |
537 | |
538 | /* read X values */ |
539 | for (i = 0, j = 19; i < 20; i += 2, j += 3) { |
540 | dev->xy_cur[i] = dev->data[j]; |
541 | dev->xy_cur[i + 1] = dev->data[j + 1]; |
542 | } |
543 | |
544 | /* read Y values */ |
545 | for (i = 0, j = 1; i < 9; i += 2, j += 3) { |
546 | dev->xy_cur[ATP_XSENSORS + i] = dev->data[j]; |
547 | dev->xy_cur[ATP_XSENSORS + i + 1] = dev->data[j + 1]; |
548 | } |
549 | } else { |
550 | for (i = 0; i < 8; i++) { |
551 | /* X values */ |
552 | dev->xy_cur[i + 0] = dev->data[5 * i + 2]; |
553 | dev->xy_cur[i + 8] = dev->data[5 * i + 4]; |
554 | dev->xy_cur[i + 16] = dev->data[5 * i + 42]; |
555 | if (i < 2) |
556 | dev->xy_cur[i + 24] = dev->data[5 * i + 44]; |
557 | |
558 | /* Y values */ |
559 | dev->xy_cur[ATP_XSENSORS + i] = dev->data[5 * i + 1]; |
560 | dev->xy_cur[ATP_XSENSORS + i + 8] = dev->data[5 * i + 3]; |
561 | } |
562 | } |
563 | |
564 | dbg_dump("sample" , dev->xy_cur); |
565 | |
566 | if (!dev->valid) { |
567 | /* first sample */ |
568 | dev->valid = true; |
569 | dev->x_old = dev->y_old = -1; |
570 | |
571 | /* Store first sample */ |
572 | memcpy(dev->xy_old, dev->xy_cur, sizeof(dev->xy_old)); |
573 | |
574 | /* Perform size detection, if not done already */ |
575 | if (unlikely(!dev->size_detect_done)) { |
576 | atp_detect_size(dev); |
577 | dev->size_detect_done = true; |
578 | goto exit; |
579 | } |
580 | } |
581 | |
582 | for (i = 0; i < ATP_XSENSORS + ATP_YSENSORS; i++) { |
583 | /* accumulate the change */ |
584 | signed char change = dev->xy_old[i] - dev->xy_cur[i]; |
585 | dev->xy_acc[i] -= change; |
586 | |
587 | /* prevent down drifting */ |
588 | if (dev->xy_acc[i] < 0) |
589 | dev->xy_acc[i] = 0; |
590 | } |
591 | |
592 | memcpy(dev->xy_old, dev->xy_cur, sizeof(dev->xy_old)); |
593 | |
594 | dbg_dump("accumulator" , dev->xy_acc); |
595 | |
596 | x = atp_calculate_abs(dev, offset: 0, ATP_XSENSORS, |
597 | fact: dev->info->xfact, z: &x_z, fingers: &x_f); |
598 | y = atp_calculate_abs(dev, ATP_XSENSORS, ATP_YSENSORS, |
599 | fact: dev->info->yfact, z: &y_z, fingers: &y_f); |
600 | key = dev->data[dev->info->datalen - 1] & ATP_STATUS_BUTTON; |
601 | |
602 | fingers = max(x_f, y_f); |
603 | |
604 | if (x && y && fingers == dev->fingers_old) { |
605 | if (dev->x_old != -1) { |
606 | x = (dev->x_old * 7 + x) >> 3; |
607 | y = (dev->y_old * 7 + y) >> 3; |
608 | dev->x_old = x; |
609 | dev->y_old = y; |
610 | |
611 | if (debug > 1) |
612 | printk(KERN_DEBUG "appletouch: " |
613 | "X: %3d Y: %3d Xz: %3d Yz: %3d\n" , |
614 | x, y, x_z, y_z); |
615 | |
616 | input_report_key(dev: dev->input, BTN_TOUCH, value: 1); |
617 | input_report_abs(dev: dev->input, ABS_X, value: x); |
618 | input_report_abs(dev: dev->input, ABS_Y, value: y); |
619 | input_report_abs(dev: dev->input, ABS_PRESSURE, |
620 | min(ATP_PRESSURE, x_z + y_z)); |
621 | atp_report_fingers(input: dev->input, fingers); |
622 | } |
623 | dev->x_old = x; |
624 | dev->y_old = y; |
625 | |
626 | } else if (!x && !y) { |
627 | |
628 | dev->x_old = dev->y_old = -1; |
629 | dev->fingers_old = 0; |
630 | input_report_key(dev: dev->input, BTN_TOUCH, value: 0); |
631 | input_report_abs(dev: dev->input, ABS_PRESSURE, value: 0); |
632 | atp_report_fingers(input: dev->input, fingers: 0); |
633 | |
634 | /* reset the accumulator on release */ |
635 | memset(dev->xy_acc, 0, sizeof(dev->xy_acc)); |
636 | } |
637 | |
638 | if (fingers != dev->fingers_old) |
639 | dev->x_old = dev->y_old = -1; |
640 | dev->fingers_old = fingers; |
641 | |
642 | input_report_key(dev: dev->input, BTN_LEFT, value: key); |
643 | input_sync(dev: dev->input); |
644 | |
645 | exit: |
646 | retval = usb_submit_urb(urb: dev->urb, GFP_ATOMIC); |
647 | if (retval) |
648 | dev_err(&dev->intf->dev, |
649 | "atp_complete: usb_submit_urb failed with result %d\n" , |
650 | retval); |
651 | } |
652 | |
653 | /* Interrupt function for older touchpads: GEYSER3/GEYSER4 */ |
654 | |
655 | static void atp_complete_geyser_3_4(struct urb *urb) |
656 | { |
657 | int x, y, x_z, y_z, x_f, y_f; |
658 | int retval, i, j; |
659 | int key, fingers; |
660 | struct atp *dev = urb->context; |
661 | int status = atp_status_check(urb); |
662 | |
663 | if (status == ATP_URB_STATUS_ERROR_FATAL) |
664 | return; |
665 | else if (status == ATP_URB_STATUS_ERROR) |
666 | goto exit; |
667 | |
668 | /* Reorder the sensors values: |
669 | * |
670 | * The values are laid out like this: |
671 | * -, Y1, Y2, -, Y3, Y4, -, ..., -, X1, X2, -, X3, X4, ... |
672 | * '-' is an unused value. |
673 | */ |
674 | |
675 | /* read X values */ |
676 | for (i = 0, j = 19; i < 20; i += 2, j += 3) { |
677 | dev->xy_cur[i] = dev->data[j + 1]; |
678 | dev->xy_cur[i + 1] = dev->data[j + 2]; |
679 | } |
680 | /* read Y values */ |
681 | for (i = 0, j = 1; i < 9; i += 2, j += 3) { |
682 | dev->xy_cur[ATP_XSENSORS + i] = dev->data[j + 1]; |
683 | dev->xy_cur[ATP_XSENSORS + i + 1] = dev->data[j + 2]; |
684 | } |
685 | |
686 | dbg_dump("sample" , dev->xy_cur); |
687 | |
688 | /* Just update the base values (i.e. touchpad in untouched state) */ |
689 | if (dev->data[dev->info->datalen - 1] & ATP_STATUS_BASE_UPDATE) { |
690 | |
691 | dprintk("appletouch: updated base values\n" ); |
692 | |
693 | memcpy(dev->xy_old, dev->xy_cur, sizeof(dev->xy_old)); |
694 | goto exit; |
695 | } |
696 | |
697 | for (i = 0; i < ATP_XSENSORS + ATP_YSENSORS; i++) { |
698 | /* calculate the change */ |
699 | dev->xy_acc[i] = dev->xy_cur[i] - dev->xy_old[i]; |
700 | |
701 | /* this is a round-robin value, so couple with that */ |
702 | if (dev->xy_acc[i] > 127) |
703 | dev->xy_acc[i] -= 256; |
704 | |
705 | if (dev->xy_acc[i] < -127) |
706 | dev->xy_acc[i] += 256; |
707 | |
708 | /* prevent down drifting */ |
709 | if (dev->xy_acc[i] < 0) |
710 | dev->xy_acc[i] = 0; |
711 | } |
712 | |
713 | dbg_dump("accumulator" , dev->xy_acc); |
714 | |
715 | x = atp_calculate_abs(dev, offset: 0, ATP_XSENSORS, |
716 | fact: dev->info->xfact, z: &x_z, fingers: &x_f); |
717 | y = atp_calculate_abs(dev, ATP_XSENSORS, ATP_YSENSORS, |
718 | fact: dev->info->yfact, z: &y_z, fingers: &y_f); |
719 | |
720 | key = dev->data[dev->info->datalen - 1] & ATP_STATUS_BUTTON; |
721 | |
722 | fingers = max(x_f, y_f); |
723 | |
724 | if (x && y && fingers == dev->fingers_old) { |
725 | if (dev->x_old != -1) { |
726 | x = (dev->x_old * 7 + x) >> 3; |
727 | y = (dev->y_old * 7 + y) >> 3; |
728 | dev->x_old = x; |
729 | dev->y_old = y; |
730 | |
731 | if (debug > 1) |
732 | printk(KERN_DEBUG "appletouch: X: %3d Y: %3d " |
733 | "Xz: %3d Yz: %3d\n" , |
734 | x, y, x_z, y_z); |
735 | |
736 | input_report_key(dev: dev->input, BTN_TOUCH, value: 1); |
737 | input_report_abs(dev: dev->input, ABS_X, value: x); |
738 | input_report_abs(dev: dev->input, ABS_Y, value: y); |
739 | input_report_abs(dev: dev->input, ABS_PRESSURE, |
740 | min(ATP_PRESSURE, x_z + y_z)); |
741 | atp_report_fingers(input: dev->input, fingers); |
742 | } |
743 | dev->x_old = x; |
744 | dev->y_old = y; |
745 | |
746 | } else if (!x && !y) { |
747 | |
748 | dev->x_old = dev->y_old = -1; |
749 | dev->fingers_old = 0; |
750 | input_report_key(dev: dev->input, BTN_TOUCH, value: 0); |
751 | input_report_abs(dev: dev->input, ABS_PRESSURE, value: 0); |
752 | atp_report_fingers(input: dev->input, fingers: 0); |
753 | |
754 | /* reset the accumulator on release */ |
755 | memset(dev->xy_acc, 0, sizeof(dev->xy_acc)); |
756 | } |
757 | |
758 | if (fingers != dev->fingers_old) |
759 | dev->x_old = dev->y_old = -1; |
760 | dev->fingers_old = fingers; |
761 | |
762 | input_report_key(dev: dev->input, BTN_LEFT, value: key); |
763 | input_sync(dev: dev->input); |
764 | |
765 | /* |
766 | * Geysers 3/4 will continue to send packets continually after |
767 | * the first touch unless reinitialised. Do so if it's been |
768 | * idle for a while in order to avoid waking the kernel up |
769 | * several hundred times a second. |
770 | */ |
771 | |
772 | /* |
773 | * Button must not be pressed when entering suspend, |
774 | * otherwise we will never release the button. |
775 | */ |
776 | if (!x && !y && !key) { |
777 | dev->idlecount++; |
778 | if (dev->idlecount == 10) { |
779 | dev->x_old = dev->y_old = -1; |
780 | dev->idlecount = 0; |
781 | schedule_work(work: &dev->work); |
782 | /* Don't resubmit urb here, wait for reinit */ |
783 | return; |
784 | } |
785 | } else |
786 | dev->idlecount = 0; |
787 | |
788 | exit: |
789 | retval = usb_submit_urb(urb: dev->urb, GFP_ATOMIC); |
790 | if (retval) |
791 | dev_err(&dev->intf->dev, |
792 | "atp_complete: usb_submit_urb failed with result %d\n" , |
793 | retval); |
794 | } |
795 | |
796 | static int atp_open(struct input_dev *input) |
797 | { |
798 | struct atp *dev = input_get_drvdata(dev: input); |
799 | |
800 | if (usb_submit_urb(urb: dev->urb, GFP_KERNEL)) |
801 | return -EIO; |
802 | |
803 | dev->open = true; |
804 | return 0; |
805 | } |
806 | |
807 | static void atp_close(struct input_dev *input) |
808 | { |
809 | struct atp *dev = input_get_drvdata(dev: input); |
810 | |
811 | usb_kill_urb(urb: dev->urb); |
812 | cancel_work_sync(work: &dev->work); |
813 | dev->open = false; |
814 | } |
815 | |
816 | static int atp_handle_geyser(struct atp *dev) |
817 | { |
818 | if (dev->info != &fountain_info) { |
819 | /* switch to raw sensor mode */ |
820 | if (atp_geyser_init(dev)) |
821 | return -EIO; |
822 | |
823 | dev_info(&dev->intf->dev, "Geyser mode initialized.\n" ); |
824 | } |
825 | |
826 | return 0; |
827 | } |
828 | |
829 | static int atp_probe(struct usb_interface *iface, |
830 | const struct usb_device_id *id) |
831 | { |
832 | struct atp *dev; |
833 | struct input_dev *input_dev; |
834 | struct usb_device *udev = interface_to_usbdev(iface); |
835 | struct usb_host_interface *iface_desc; |
836 | struct usb_endpoint_descriptor *endpoint; |
837 | int int_in_endpointAddr = 0; |
838 | int i, error = -ENOMEM; |
839 | const struct atp_info *info = (const struct atp_info *)id->driver_info; |
840 | |
841 | /* set up the endpoint information */ |
842 | /* use only the first interrupt-in endpoint */ |
843 | iface_desc = iface->cur_altsetting; |
844 | for (i = 0; i < iface_desc->desc.bNumEndpoints; i++) { |
845 | endpoint = &iface_desc->endpoint[i].desc; |
846 | if (!int_in_endpointAddr && usb_endpoint_is_int_in(epd: endpoint)) { |
847 | /* we found an interrupt in endpoint */ |
848 | int_in_endpointAddr = endpoint->bEndpointAddress; |
849 | break; |
850 | } |
851 | } |
852 | if (!int_in_endpointAddr) { |
853 | dev_err(&iface->dev, "Could not find int-in endpoint\n" ); |
854 | return -EIO; |
855 | } |
856 | |
857 | /* allocate memory for our device state and initialize it */ |
858 | dev = kzalloc(size: sizeof(struct atp), GFP_KERNEL); |
859 | input_dev = input_allocate_device(); |
860 | if (!dev || !input_dev) { |
861 | dev_err(&iface->dev, "Out of memory\n" ); |
862 | goto err_free_devs; |
863 | } |
864 | |
865 | dev->udev = udev; |
866 | dev->intf = iface; |
867 | dev->input = input_dev; |
868 | dev->info = info; |
869 | dev->overflow_warned = false; |
870 | |
871 | dev->urb = usb_alloc_urb(iso_packets: 0, GFP_KERNEL); |
872 | if (!dev->urb) |
873 | goto err_free_devs; |
874 | |
875 | dev->data = usb_alloc_coherent(dev: dev->udev, size: dev->info->datalen, GFP_KERNEL, |
876 | dma: &dev->urb->transfer_dma); |
877 | if (!dev->data) |
878 | goto err_free_urb; |
879 | |
880 | usb_fill_int_urb(urb: dev->urb, dev: udev, |
881 | usb_rcvintpipe(udev, int_in_endpointAddr), |
882 | transfer_buffer: dev->data, buffer_length: dev->info->datalen, |
883 | complete_fn: dev->info->callback, context: dev, interval: 1); |
884 | |
885 | error = atp_handle_geyser(dev); |
886 | if (error) |
887 | goto err_free_buffer; |
888 | |
889 | usb_make_path(dev: udev, buf: dev->phys, size: sizeof(dev->phys)); |
890 | strlcat(p: dev->phys, q: "/input0" , avail: sizeof(dev->phys)); |
891 | |
892 | input_dev->name = "appletouch" ; |
893 | input_dev->phys = dev->phys; |
894 | usb_to_input_id(dev: dev->udev, id: &input_dev->id); |
895 | input_dev->dev.parent = &iface->dev; |
896 | |
897 | input_set_drvdata(dev: input_dev, data: dev); |
898 | |
899 | input_dev->open = atp_open; |
900 | input_dev->close = atp_close; |
901 | |
902 | set_bit(EV_ABS, addr: input_dev->evbit); |
903 | |
904 | input_set_abs_params(dev: input_dev, ABS_X, min: 0, |
905 | max: (dev->info->xsensors - 1) * dev->info->xfact - 1, |
906 | fuzz: dev->info->fuzz, flat: 0); |
907 | input_set_abs_params(dev: input_dev, ABS_Y, min: 0, |
908 | max: (dev->info->ysensors - 1) * dev->info->yfact - 1, |
909 | fuzz: dev->info->fuzz, flat: 0); |
910 | input_set_abs_params(dev: input_dev, ABS_PRESSURE, min: 0, ATP_PRESSURE, fuzz: 0, flat: 0); |
911 | |
912 | set_bit(EV_KEY, addr: input_dev->evbit); |
913 | set_bit(BTN_TOUCH, addr: input_dev->keybit); |
914 | set_bit(BTN_TOOL_FINGER, addr: input_dev->keybit); |
915 | set_bit(BTN_TOOL_DOUBLETAP, addr: input_dev->keybit); |
916 | set_bit(BTN_TOOL_TRIPLETAP, addr: input_dev->keybit); |
917 | set_bit(BTN_LEFT, addr: input_dev->keybit); |
918 | |
919 | INIT_WORK(&dev->work, atp_reinit); |
920 | |
921 | error = input_register_device(dev->input); |
922 | if (error) |
923 | goto err_free_buffer; |
924 | |
925 | /* save our data pointer in this interface device */ |
926 | usb_set_intfdata(intf: iface, data: dev); |
927 | |
928 | return 0; |
929 | |
930 | err_free_buffer: |
931 | usb_free_coherent(dev: dev->udev, size: dev->info->datalen, |
932 | addr: dev->data, dma: dev->urb->transfer_dma); |
933 | err_free_urb: |
934 | usb_free_urb(urb: dev->urb); |
935 | err_free_devs: |
936 | usb_set_intfdata(intf: iface, NULL); |
937 | kfree(objp: dev); |
938 | input_free_device(dev: input_dev); |
939 | return error; |
940 | } |
941 | |
942 | static void atp_disconnect(struct usb_interface *iface) |
943 | { |
944 | struct atp *dev = usb_get_intfdata(intf: iface); |
945 | |
946 | usb_set_intfdata(intf: iface, NULL); |
947 | if (dev) { |
948 | usb_kill_urb(urb: dev->urb); |
949 | input_unregister_device(dev->input); |
950 | usb_free_coherent(dev: dev->udev, size: dev->info->datalen, |
951 | addr: dev->data, dma: dev->urb->transfer_dma); |
952 | usb_free_urb(urb: dev->urb); |
953 | kfree(objp: dev); |
954 | } |
955 | dev_info(&iface->dev, "input: appletouch disconnected\n" ); |
956 | } |
957 | |
958 | static int atp_recover(struct atp *dev) |
959 | { |
960 | int error; |
961 | |
962 | error = atp_handle_geyser(dev); |
963 | if (error) |
964 | return error; |
965 | |
966 | if (dev->open && usb_submit_urb(urb: dev->urb, GFP_KERNEL)) |
967 | return -EIO; |
968 | |
969 | return 0; |
970 | } |
971 | |
972 | static int atp_suspend(struct usb_interface *iface, pm_message_t message) |
973 | { |
974 | struct atp *dev = usb_get_intfdata(intf: iface); |
975 | |
976 | usb_kill_urb(urb: dev->urb); |
977 | return 0; |
978 | } |
979 | |
980 | static int atp_resume(struct usb_interface *iface) |
981 | { |
982 | struct atp *dev = usb_get_intfdata(intf: iface); |
983 | |
984 | if (dev->open && usb_submit_urb(urb: dev->urb, GFP_KERNEL)) |
985 | return -EIO; |
986 | |
987 | return 0; |
988 | } |
989 | |
990 | static int atp_reset_resume(struct usb_interface *iface) |
991 | { |
992 | struct atp *dev = usb_get_intfdata(intf: iface); |
993 | |
994 | return atp_recover(dev); |
995 | } |
996 | |
997 | static struct usb_driver atp_driver = { |
998 | .name = "appletouch" , |
999 | .probe = atp_probe, |
1000 | .disconnect = atp_disconnect, |
1001 | .suspend = atp_suspend, |
1002 | .resume = atp_resume, |
1003 | .reset_resume = atp_reset_resume, |
1004 | .id_table = atp_table, |
1005 | }; |
1006 | |
1007 | module_usb_driver(atp_driver); |
1008 | |