aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/input
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2009-12-16 13:31:44 -0500
committerLinus Torvalds <torvalds@linux-foundation.org>2009-12-16 13:31:44 -0500
commit238ccbb050a243e935bb3fc679c2e4bbff7004aa (patch)
tree3381b895861f625b1524acfd32d4a90eb79108bd /drivers/input
parentc5113e3d66d7c7140fe854c7638a27eb3a23fd7d (diff)
parent1d9f26262aef6d63ff65eba0fd5f1583f342b69b (diff)
Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input
* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/dtor/input: (22 commits) Input: ALPS - add interleaved protocol support (Dell E6x00 series) Input: keyboard - don't override beep with a bell Input: altera_ps2 - fix test of unsigned in altera_ps2_probe() Input: add mc13783 touchscreen driver Input: ep93xx_keypad - update driver to new core support Input: wacom - separate pen from express keys on Graphire Input: wacom - add defines for data packet report IDs Input: wacom - add support for new LCD tablets Input: wacom - add defines for packet lengths of various devices Input: wacom - ensure the device is initialized properly upon resume Input: at32psif - do not sleep in atomic context Input: i8042 - add Gigabyte M1022M to the noloop list Input: i8042 - allow installing platform filters for incoming data Input: i8042 - fix locking in interrupt routine Input: ALPS - do not set REL_X/REL_Y capabilities on the touchpad Input: document use of input_event() function Input: sa1111ps2 - annotate probe() and remove() methods Input: ambakmi - annotate probe() and remove() methods Input: gscps2 - fix probe() and remove() annotations Input: altera_ps2 - add annotations to probe and remove methods ...
Diffstat (limited to 'drivers/input')
-rw-r--r--drivers/input/input.c10
-rw-r--r--drivers/input/keyboard/ep93xx_keypad.c150
-rw-r--r--drivers/input/mouse/alps.c265
-rw-r--r--drivers/input/mouse/alps.h1
-rw-r--r--drivers/input/serio/altera_ps2.c15
-rw-r--r--drivers/input/serio/ambakmi.c9
-rw-r--r--drivers/input/serio/at32psif.c3
-rw-r--r--drivers/input/serio/gscps2.c6
-rw-r--r--drivers/input/serio/hil_mlc.c8
-rw-r--r--drivers/input/serio/i8042-x86ia64io.h8
-rw-r--r--drivers/input/serio/i8042.c88
-rw-r--r--drivers/input/serio/sa1111ps2.c10
-rw-r--r--drivers/input/tablet/wacom.h11
-rw-r--r--drivers/input/tablet/wacom_sys.c231
-rw-r--r--drivers/input/tablet/wacom_wac.c368
-rw-r--r--drivers/input/tablet/wacom_wac.h29
-rw-r--r--drivers/input/touchscreen/Kconfig12
-rw-r--r--drivers/input/touchscreen/Makefile1
-rw-r--r--drivers/input/touchscreen/mc13783_ts.c258
19 files changed, 1111 insertions, 372 deletions
diff --git a/drivers/input/input.c b/drivers/input/input.c
index 5c16001959cc..ab060710688f 100644
--- a/drivers/input/input.c
+++ b/drivers/input/input.c
@@ -296,9 +296,15 @@ static void input_handle_event(struct input_dev *dev,
296 * @value: value of the event 296 * @value: value of the event
297 * 297 *
298 * This function should be used by drivers implementing various input 298 * This function should be used by drivers implementing various input
299 * devices. See also input_inject_event(). 299 * devices to report input events. See also input_inject_event().
300 *
301 * NOTE: input_event() may be safely used right after input device was
302 * allocated with input_allocate_device(), even before it is registered
303 * with input_register_device(), but the event will not reach any of the
304 * input handlers. Such early invocation of input_event() may be used
305 * to 'seed' initial state of a switch or initial position of absolute
306 * axis, etc.
300 */ 307 */
301
302void input_event(struct input_dev *dev, 308void input_event(struct input_dev *dev,
303 unsigned int type, unsigned int code, int value) 309 unsigned int type, unsigned int code, int value)
304{ 310{
diff --git a/drivers/input/keyboard/ep93xx_keypad.c b/drivers/input/keyboard/ep93xx_keypad.c
index 181d30e3018e..e45740429f7e 100644
--- a/drivers/input/keyboard/ep93xx_keypad.c
+++ b/drivers/input/keyboard/ep93xx_keypad.c
@@ -22,11 +22,11 @@
22 22
23#include <linux/platform_device.h> 23#include <linux/platform_device.h>
24#include <linux/interrupt.h> 24#include <linux/interrupt.h>
25#include <linux/input.h>
26#include <linux/clk.h> 25#include <linux/clk.h>
26#include <linux/io.h>
27#include <linux/input/matrix_keypad.h>
27 28
28#include <mach/hardware.h> 29#include <mach/hardware.h>
29#include <mach/gpio.h>
30#include <mach/ep93xx_keypad.h> 30#include <mach/ep93xx_keypad.h>
31 31
32/* 32/*
@@ -60,38 +60,37 @@
60#define KEY_REG_KEY1_MASK (0x0000003f) 60#define KEY_REG_KEY1_MASK (0x0000003f)
61#define KEY_REG_KEY1_SHIFT (0) 61#define KEY_REG_KEY1_SHIFT (0)
62 62
63#define keypad_readl(off) __raw_readl(keypad->mmio_base + (off)) 63#define EP93XX_MATRIX_SIZE (EP93XX_MATRIX_ROWS * EP93XX_MATRIX_COLS)
64#define keypad_writel(v, off) __raw_writel((v), keypad->mmio_base + (off))
65
66#define MAX_MATRIX_KEY_NUM (MAX_MATRIX_KEY_ROWS * MAX_MATRIX_KEY_COLS)
67 64
68struct ep93xx_keypad { 65struct ep93xx_keypad {
69 struct ep93xx_keypad_platform_data *pdata; 66 struct ep93xx_keypad_platform_data *pdata;
70
71 struct clk *clk;
72 struct input_dev *input_dev; 67 struct input_dev *input_dev;
68 struct clk *clk;
69
73 void __iomem *mmio_base; 70 void __iomem *mmio_base;
74 71
75 int irq; 72 unsigned int matrix_keycodes[EP93XX_MATRIX_SIZE];
76 int enabled;
77 73
78 int key1; 74 int key1;
79 int key2; 75 int key2;
80 76
81 unsigned int matrix_keycodes[MAX_MATRIX_KEY_NUM]; 77 int irq;
78
79 bool enabled;
82}; 80};
83 81
84static void ep93xx_keypad_build_keycode(struct ep93xx_keypad *keypad) 82static void ep93xx_keypad_build_keycode(struct ep93xx_keypad *keypad)
85{ 83{
86 struct ep93xx_keypad_platform_data *pdata = keypad->pdata; 84 struct ep93xx_keypad_platform_data *pdata = keypad->pdata;
87 struct input_dev *input_dev = keypad->input_dev; 85 struct input_dev *input_dev = keypad->input_dev;
86 unsigned int *key;
88 int i; 87 int i;
89 88
90 for (i = 0; i < pdata->matrix_key_map_size; i++) { 89 key = &pdata->matrix_key_map[0];
91 unsigned int key = pdata->matrix_key_map[i]; 90 for (i = 0; i < pdata->matrix_key_map_size; i++, key++) {
92 int row = (key >> 28) & 0xf; 91 int row = KEY_ROW(*key);
93 int col = (key >> 24) & 0xf; 92 int col = KEY_COL(*key);
94 int code = key & 0xffffff; 93 int code = KEY_VAL(*key);
95 94
96 keypad->matrix_keycodes[(row << 3) + col] = code; 95 keypad->matrix_keycodes[(row << 3) + col] = code;
97 __set_bit(code, input_dev->keybit); 96 __set_bit(code, input_dev->keybit);
@@ -102,9 +101,11 @@ static irqreturn_t ep93xx_keypad_irq_handler(int irq, void *dev_id)
102{ 101{
103 struct ep93xx_keypad *keypad = dev_id; 102 struct ep93xx_keypad *keypad = dev_id;
104 struct input_dev *input_dev = keypad->input_dev; 103 struct input_dev *input_dev = keypad->input_dev;
105 unsigned int status = keypad_readl(KEY_REG); 104 unsigned int status;
106 int keycode, key1, key2; 105 int keycode, key1, key2;
107 106
107 status = __raw_readl(keypad->mmio_base + KEY_REG);
108
108 keycode = (status & KEY_REG_KEY1_MASK) >> KEY_REG_KEY1_SHIFT; 109 keycode = (status & KEY_REG_KEY1_MASK) >> KEY_REG_KEY1_SHIFT;
109 key1 = keypad->matrix_keycodes[keycode]; 110 key1 = keypad->matrix_keycodes[keycode];
110 111
@@ -152,7 +153,10 @@ static void ep93xx_keypad_config(struct ep93xx_keypad *keypad)
152 struct ep93xx_keypad_platform_data *pdata = keypad->pdata; 153 struct ep93xx_keypad_platform_data *pdata = keypad->pdata;
153 unsigned int val = 0; 154 unsigned int val = 0;
154 155
155 clk_set_rate(keypad->clk, pdata->flags & EP93XX_KEYPAD_KDIV); 156 if (pdata->flags & EP93XX_KEYPAD_KDIV)
157 clk_set_rate(keypad->clk, EP93XX_KEYTCHCLK_DIV4);
158 else
159 clk_set_rate(keypad->clk, EP93XX_KEYTCHCLK_DIV16);
156 160
157 if (pdata->flags & EP93XX_KEYPAD_DISABLE_3_KEY) 161 if (pdata->flags & EP93XX_KEYPAD_DISABLE_3_KEY)
158 val |= KEY_INIT_DIS3KY; 162 val |= KEY_INIT_DIS3KY;
@@ -167,7 +171,7 @@ static void ep93xx_keypad_config(struct ep93xx_keypad *keypad)
167 171
168 val |= ((pdata->prescale << KEY_INIT_PRSCL_SHIFT) & KEY_INIT_PRSCL_MASK); 172 val |= ((pdata->prescale << KEY_INIT_PRSCL_SHIFT) & KEY_INIT_PRSCL_MASK);
169 173
170 keypad_writel(val, KEY_INIT); 174 __raw_writel(val, keypad->mmio_base + KEY_INIT);
171} 175}
172 176
173static int ep93xx_keypad_open(struct input_dev *pdev) 177static int ep93xx_keypad_open(struct input_dev *pdev)
@@ -177,7 +181,7 @@ static int ep93xx_keypad_open(struct input_dev *pdev)
177 if (!keypad->enabled) { 181 if (!keypad->enabled) {
178 ep93xx_keypad_config(keypad); 182 ep93xx_keypad_config(keypad);
179 clk_enable(keypad->clk); 183 clk_enable(keypad->clk);
180 keypad->enabled = 1; 184 keypad->enabled = true;
181 } 185 }
182 186
183 return 0; 187 return 0;
@@ -189,7 +193,7 @@ static void ep93xx_keypad_close(struct input_dev *pdev)
189 193
190 if (keypad->enabled) { 194 if (keypad->enabled) {
191 clk_disable(keypad->clk); 195 clk_disable(keypad->clk);
192 keypad->enabled = 0; 196 keypad->enabled = false;
193 } 197 }
194} 198}
195 199
@@ -211,7 +215,7 @@ static int ep93xx_keypad_suspend(struct platform_device *pdev,
211 215
212 if (keypad->enabled) { 216 if (keypad->enabled) {
213 clk_disable(keypad->clk); 217 clk_disable(keypad->clk);
214 keypad->enabled = 0; 218 keypad->enabled = false;
215 } 219 }
216 220
217 mutex_unlock(&input_dev->mutex); 221 mutex_unlock(&input_dev->mutex);
@@ -236,7 +240,7 @@ static int ep93xx_keypad_resume(struct platform_device *pdev)
236 if (!keypad->enabled) { 240 if (!keypad->enabled) {
237 ep93xx_keypad_config(keypad); 241 ep93xx_keypad_config(keypad);
238 clk_enable(keypad->clk); 242 clk_enable(keypad->clk);
239 keypad->enabled = 1; 243 keypad->enabled = true;
240 } 244 }
241 } 245 }
242 246
@@ -252,88 +256,56 @@ static int ep93xx_keypad_resume(struct platform_device *pdev)
252static int __devinit ep93xx_keypad_probe(struct platform_device *pdev) 256static int __devinit ep93xx_keypad_probe(struct platform_device *pdev)
253{ 257{
254 struct ep93xx_keypad *keypad; 258 struct ep93xx_keypad *keypad;
255 struct ep93xx_keypad_platform_data *pdata = pdev->dev.platform_data;
256 struct input_dev *input_dev; 259 struct input_dev *input_dev;
257 struct resource *res; 260 struct resource *res;
258 int irq, err, i, gpio; 261 int err;
259
260 if (!pdata ||
261 !pdata->matrix_key_rows ||
262 pdata->matrix_key_rows > MAX_MATRIX_KEY_ROWS ||
263 !pdata->matrix_key_cols ||
264 pdata->matrix_key_cols > MAX_MATRIX_KEY_COLS) {
265 dev_err(&pdev->dev, "invalid or missing platform data\n");
266 return -EINVAL;
267 }
268 262
269 keypad = kzalloc(sizeof(struct ep93xx_keypad), GFP_KERNEL); 263 keypad = kzalloc(sizeof(struct ep93xx_keypad), GFP_KERNEL);
270 if (!keypad) { 264 if (!keypad)
271 dev_err(&pdev->dev, "failed to allocate driver data\n");
272 return -ENOMEM; 265 return -ENOMEM;
273 }
274 266
275 keypad->pdata = pdata; 267 keypad->pdata = pdev->dev.platform_data;
268 if (!keypad->pdata) {
269 err = -EINVAL;
270 goto failed_free;
271 }
276 272
277 irq = platform_get_irq(pdev, 0); 273 keypad->irq = platform_get_irq(pdev, 0);
278 if (irq < 0) { 274 if (!keypad->irq) {
279 dev_err(&pdev->dev, "failed to get keypad irq\n");
280 err = -ENXIO; 275 err = -ENXIO;
281 goto failed_free; 276 goto failed_free;
282 } 277 }
283 278
284 res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 279 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
285 if (!res) { 280 if (!res) {
286 dev_err(&pdev->dev, "failed to get I/O memory\n");
287 err = -ENXIO; 281 err = -ENXIO;
288 goto failed_free; 282 goto failed_free;
289 } 283 }
290 284
291 res = request_mem_region(res->start, resource_size(res), pdev->name); 285 res = request_mem_region(res->start, resource_size(res), pdev->name);
292 if (!res) { 286 if (!res) {
293 dev_err(&pdev->dev, "failed to request I/O memory\n");
294 err = -EBUSY; 287 err = -EBUSY;
295 goto failed_free; 288 goto failed_free;
296 } 289 }
297 290
298 keypad->mmio_base = ioremap(res->start, resource_size(res)); 291 keypad->mmio_base = ioremap(res->start, resource_size(res));
299 if (keypad->mmio_base == NULL) { 292 if (keypad->mmio_base == NULL) {
300 dev_err(&pdev->dev, "failed to remap I/O memory\n");
301 err = -ENXIO; 293 err = -ENXIO;
302 goto failed_free_mem; 294 goto failed_free_mem;
303 } 295 }
304 296
305 /* Request the needed GPIO's */ 297 err = ep93xx_keypad_acquire_gpio(pdev);
306 gpio = EP93XX_GPIO_LINE_ROW0; 298 if (err)
307 for (i = 0; i < keypad->pdata->matrix_key_rows; i++, gpio++) { 299 goto failed_free_io;
308 err = gpio_request(gpio, pdev->name);
309 if (err) {
310 dev_err(&pdev->dev, "failed to request gpio-%d\n",
311 gpio);
312 goto failed_free_rows;
313 }
314 }
315
316 gpio = EP93XX_GPIO_LINE_COL0;
317 for (i = 0; i < keypad->pdata->matrix_key_cols; i++, gpio++) {
318 err = gpio_request(gpio, pdev->name);
319 if (err) {
320 dev_err(&pdev->dev, "failed to request gpio-%d\n",
321 gpio);
322 goto failed_free_cols;
323 }
324 }
325 300
326 keypad->clk = clk_get(&pdev->dev, "key_clk"); 301 keypad->clk = clk_get(&pdev->dev, NULL);
327 if (IS_ERR(keypad->clk)) { 302 if (IS_ERR(keypad->clk)) {
328 dev_err(&pdev->dev, "failed to get keypad clock\n");
329 err = PTR_ERR(keypad->clk); 303 err = PTR_ERR(keypad->clk);
330 goto failed_free_io; 304 goto failed_free_gpio;
331 } 305 }
332 306
333 /* Create and register the input driver */
334 input_dev = input_allocate_device(); 307 input_dev = input_allocate_device();
335 if (!input_dev) { 308 if (!input_dev) {
336 dev_err(&pdev->dev, "failed to allocate input device\n");
337 err = -ENOMEM; 309 err = -ENOMEM;
338 goto failed_put_clk; 310 goto failed_put_clk;
339 } 311 }
@@ -358,44 +330,29 @@ static int __devinit ep93xx_keypad_probe(struct platform_device *pdev)
358 ep93xx_keypad_build_keycode(keypad); 330 ep93xx_keypad_build_keycode(keypad);
359 platform_set_drvdata(pdev, keypad); 331 platform_set_drvdata(pdev, keypad);
360 332
361 err = request_irq(irq, ep93xx_keypad_irq_handler, IRQF_DISABLED, 333 err = request_irq(keypad->irq, ep93xx_keypad_irq_handler,
362 pdev->name, keypad); 334 IRQF_DISABLED, pdev->name, keypad);
363 if (err) { 335 if (err)
364 dev_err(&pdev->dev, "failed to request IRQ\n");
365 goto failed_free_dev; 336 goto failed_free_dev;
366 }
367
368 keypad->irq = irq;
369 337
370 /* Register the input device */
371 err = input_register_device(input_dev); 338 err = input_register_device(input_dev);
372 if (err) { 339 if (err)
373 dev_err(&pdev->dev, "failed to register input device\n");
374 goto failed_free_irq; 340 goto failed_free_irq;
375 }
376 341
377 device_init_wakeup(&pdev->dev, 1); 342 device_init_wakeup(&pdev->dev, 1);
378 343
379 return 0; 344 return 0;
380 345
381failed_free_irq: 346failed_free_irq:
382 free_irq(irq, pdev); 347 free_irq(keypad->irq, pdev);
383 platform_set_drvdata(pdev, NULL); 348 platform_set_drvdata(pdev, NULL);
384failed_free_dev: 349failed_free_dev:
385 input_free_device(input_dev); 350 input_free_device(input_dev);
386failed_put_clk: 351failed_put_clk:
387 clk_put(keypad->clk); 352 clk_put(keypad->clk);
353failed_free_gpio:
354 ep93xx_keypad_release_gpio(pdev);
388failed_free_io: 355failed_free_io:
389 i = keypad->pdata->matrix_key_cols - 1;
390 gpio = EP93XX_GPIO_LINE_COL0 + i;
391failed_free_cols:
392 for ( ; i >= 0; i--, gpio--)
393 gpio_free(gpio);
394 i = keypad->pdata->matrix_key_rows - 1;
395 gpio = EP93XX_GPIO_LINE_ROW0 + i;
396failed_free_rows:
397 for ( ; i >= 0; i--, gpio--)
398 gpio_free(gpio);
399 iounmap(keypad->mmio_base); 356 iounmap(keypad->mmio_base);
400failed_free_mem: 357failed_free_mem:
401 release_mem_region(res->start, resource_size(res)); 358 release_mem_region(res->start, resource_size(res));
@@ -408,7 +365,6 @@ static int __devexit ep93xx_keypad_remove(struct platform_device *pdev)
408{ 365{
409 struct ep93xx_keypad *keypad = platform_get_drvdata(pdev); 366 struct ep93xx_keypad *keypad = platform_get_drvdata(pdev);
410 struct resource *res; 367 struct resource *res;
411 int i, gpio;
412 368
413 free_irq(keypad->irq, pdev); 369 free_irq(keypad->irq, pdev);
414 370
@@ -420,15 +376,7 @@ static int __devexit ep93xx_keypad_remove(struct platform_device *pdev)
420 376
421 input_unregister_device(keypad->input_dev); 377 input_unregister_device(keypad->input_dev);
422 378
423 i = keypad->pdata->matrix_key_cols - 1; 379 ep93xx_keypad_release_gpio(pdev);
424 gpio = EP93XX_GPIO_LINE_COL0 + i;
425 for ( ; i >= 0; i--, gpio--)
426 gpio_free(gpio);
427
428 i = keypad->pdata->matrix_key_rows - 1;
429 gpio = EP93XX_GPIO_LINE_ROW0 + i;
430 for ( ; i >= 0; i--, gpio--)
431 gpio_free(gpio);
432 380
433 iounmap(keypad->mmio_base); 381 iounmap(keypad->mmio_base);
434 382
diff --git a/drivers/input/mouse/alps.c b/drivers/input/mouse/alps.c
index a3f492a50850..f93c2c0daf1f 100644
--- a/drivers/input/mouse/alps.c
+++ b/drivers/input/mouse/alps.c
@@ -5,6 +5,7 @@
5 * Copyright (c) 2003-2005 Peter Osterlund <petero2@telia.com> 5 * Copyright (c) 2003-2005 Peter Osterlund <petero2@telia.com>
6 * Copyright (c) 2004 Dmitry Torokhov <dtor@mail.ru> 6 * Copyright (c) 2004 Dmitry Torokhov <dtor@mail.ru>
7 * Copyright (c) 2005 Vojtech Pavlik <vojtech@suse.cz> 7 * Copyright (c) 2005 Vojtech Pavlik <vojtech@suse.cz>
8 * Copyright (c) 2009 Sebastian Kapfer <sebastian_kapfer@gmx.net>
8 * 9 *
9 * ALPS detection, tap switching and status querying info is taken from 10 * ALPS detection, tap switching and status querying info is taken from
10 * tpconfig utility (by C. Scott Ananian and Bruce Kall). 11 * tpconfig utility (by C. Scott Ananian and Bruce Kall).
@@ -28,7 +29,6 @@
28#define dbg(format, arg...) do {} while (0) 29#define dbg(format, arg...) do {} while (0)
29#endif 30#endif
30 31
31
32#define ALPS_OLDPROTO 0x01 /* old style input */ 32#define ALPS_OLDPROTO 0x01 /* old style input */
33#define ALPS_DUALPOINT 0x02 /* touchpad has trackstick */ 33#define ALPS_DUALPOINT 0x02 /* touchpad has trackstick */
34#define ALPS_PASS 0x04 /* device has a pass-through port */ 34#define ALPS_PASS 0x04 /* device has a pass-through port */
@@ -37,7 +37,8 @@
37#define ALPS_FW_BK_1 0x10 /* front & back buttons present */ 37#define ALPS_FW_BK_1 0x10 /* front & back buttons present */
38#define ALPS_FW_BK_2 0x20 /* front & back buttons present */ 38#define ALPS_FW_BK_2 0x20 /* front & back buttons present */
39#define ALPS_FOUR_BUTTONS 0x40 /* 4 direction button present */ 39#define ALPS_FOUR_BUTTONS 0x40 /* 4 direction button present */
40 40#define ALPS_PS2_INTERLEAVED 0x80 /* 3-byte PS/2 packet interleaved with
41 6-byte ALPS packet */
41 42
42static const struct alps_model_info alps_model_data[] = { 43static const struct alps_model_info alps_model_data[] = {
43 { { 0x32, 0x02, 0x14 }, 0xf8, 0xf8, ALPS_PASS | ALPS_DUALPOINT }, /* Toshiba Salellite Pro M10 */ 44 { { 0x32, 0x02, 0x14 }, 0xf8, 0xf8, ALPS_PASS | ALPS_DUALPOINT }, /* Toshiba Salellite Pro M10 */
@@ -58,7 +59,9 @@ static const struct alps_model_info alps_model_data[] = {
58 { { 0x20, 0x02, 0x0e }, 0xf8, 0xf8, ALPS_PASS | ALPS_DUALPOINT }, /* XXX */ 59 { { 0x20, 0x02, 0x0e }, 0xf8, 0xf8, ALPS_PASS | ALPS_DUALPOINT }, /* XXX */
59 { { 0x22, 0x02, 0x0a }, 0xf8, 0xf8, ALPS_PASS | ALPS_DUALPOINT }, 60 { { 0x22, 0x02, 0x0a }, 0xf8, 0xf8, ALPS_PASS | ALPS_DUALPOINT },
60 { { 0x22, 0x02, 0x14 }, 0xff, 0xff, ALPS_PASS | ALPS_DUALPOINT }, /* Dell Latitude D600 */ 61 { { 0x22, 0x02, 0x14 }, 0xff, 0xff, ALPS_PASS | ALPS_DUALPOINT }, /* Dell Latitude D600 */
61 { { 0x62, 0x02, 0x14 }, 0xcf, 0xcf, ALPS_PASS | ALPS_DUALPOINT }, /* Dell Latitude E6500 */ 62 /* Dell Latitude E5500, E6400, E6500, Precision M4400 */
63 { { 0x62, 0x02, 0x14 }, 0xcf, 0xcf,
64 ALPS_PASS | ALPS_DUALPOINT | ALPS_PS2_INTERLEAVED },
62 { { 0x73, 0x02, 0x50 }, 0xcf, 0xcf, ALPS_FOUR_BUTTONS }, /* Dell Vostro 1400 */ 65 { { 0x73, 0x02, 0x50 }, 0xcf, 0xcf, ALPS_FOUR_BUTTONS }, /* Dell Vostro 1400 */
63}; 66};
64 67
@@ -69,20 +72,88 @@ static const struct alps_model_info alps_model_data[] = {
69 */ 72 */
70 73
71/* 74/*
72 * ALPS abolute Mode - new format 75 * PS/2 packet format
76 *
77 * byte 0: 0 0 YSGN XSGN 1 M R L
78 * byte 1: X7 X6 X5 X4 X3 X2 X1 X0
79 * byte 2: Y7 Y6 Y5 Y4 Y3 Y2 Y1 Y0
80 *
81 * Note that the device never signals overflow condition.
82 *
83 * ALPS absolute Mode - new format
73 * 84 *
74 * byte 0: 1 ? ? ? 1 ? ? ? 85 * byte 0: 1 ? ? ? 1 ? ? ?
75 * byte 1: 0 x6 x5 x4 x3 x2 x1 x0 86 * byte 1: 0 x6 x5 x4 x3 x2 x1 x0
76 * byte 2: 0 x10 x9 x8 x7 ? fin ges 87 * byte 2: 0 x10 x9 x8 x7 ? fin ges
77 * byte 3: 0 y9 y8 y7 1 M R L 88 * byte 3: 0 y9 y8 y7 1 M R L
78 * byte 4: 0 y6 y5 y4 y3 y2 y1 y0 89 * byte 4: 0 y6 y5 y4 y3 y2 y1 y0
79 * byte 5: 0 z6 z5 z4 z3 z2 z1 z0 90 * byte 5: 0 z6 z5 z4 z3 z2 z1 z0
80 * 91 *
92 * Dualpoint device -- interleaved packet format
93 *
94 * byte 0: 1 1 0 0 1 1 1 1
95 * byte 1: 0 x6 x5 x4 x3 x2 x1 x0
96 * byte 2: 0 x10 x9 x8 x7 0 fin ges
97 * byte 3: 0 0 YSGN XSGN 1 1 1 1
98 * byte 4: X7 X6 X5 X4 X3 X2 X1 X0
99 * byte 5: Y7 Y6 Y5 Y4 Y3 Y2 Y1 Y0
100 * byte 6: 0 y9 y8 y7 1 m r l
101 * byte 7: 0 y6 y5 y4 y3 y2 y1 y0
102 * byte 8: 0 z6 z5 z4 z3 z2 z1 z0
103 *
104 * CAPITALS = stick, miniscules = touchpad
105 *
81 * ?'s can have different meanings on different models, 106 * ?'s can have different meanings on different models,
82 * such as wheel rotation, extra buttons, stick buttons 107 * such as wheel rotation, extra buttons, stick buttons
83 * on a dualpoint, etc. 108 * on a dualpoint, etc.
84 */ 109 */
85 110
111static bool alps_is_valid_first_byte(const struct alps_model_info *model,
112 unsigned char data)
113{
114 return (data & model->mask0) == model->byte0;
115}
116
117static void alps_report_buttons(struct psmouse *psmouse,
118 struct input_dev *dev1, struct input_dev *dev2,
119 int left, int right, int middle)
120{
121 struct alps_data *priv = psmouse->private;
122 const struct alps_model_info *model = priv->i;
123
124 if (model->flags & ALPS_PS2_INTERLEAVED) {
125 struct input_dev *dev;
126
127 /*
128 * If shared button has already been reported on the
129 * other device (dev2) then this event should be also
130 * sent through that device.
131 */
132 dev = test_bit(BTN_LEFT, dev2->key) ? dev2 : dev1;
133 input_report_key(dev, BTN_LEFT, left);
134
135 dev = test_bit(BTN_RIGHT, dev2->key) ? dev2 : dev1;
136 input_report_key(dev, BTN_RIGHT, right);
137
138 dev = test_bit(BTN_MIDDLE, dev2->key) ? dev2 : dev1;
139 input_report_key(dev, BTN_MIDDLE, middle);
140
141 /*
142 * Sync the _other_ device now, we'll do the first
143 * device later once we report the rest of the events.
144 */
145 input_sync(dev2);
146 } else {
147 /*
148 * For devices with non-interleaved packets we know what
149 * device buttons belong to so we can simply report them.
150 */
151 input_report_key(dev1, BTN_LEFT, left);
152 input_report_key(dev1, BTN_RIGHT, right);
153 input_report_key(dev1, BTN_MIDDLE, middle);
154 }
155}
156
86static void alps_process_packet(struct psmouse *psmouse) 157static void alps_process_packet(struct psmouse *psmouse)
87{ 158{
88 struct alps_data *priv = psmouse->private; 159 struct alps_data *priv = psmouse->private;
@@ -93,18 +164,6 @@ static void alps_process_packet(struct psmouse *psmouse)
93 int x, y, z, ges, fin, left, right, middle; 164 int x, y, z, ges, fin, left, right, middle;
94 int back = 0, forward = 0; 165 int back = 0, forward = 0;
95 166
96 if ((packet[0] & 0xc8) == 0x08) { /* 3-byte PS/2 packet */
97 input_report_key(dev2, BTN_LEFT, packet[0] & 1);
98 input_report_key(dev2, BTN_RIGHT, packet[0] & 2);
99 input_report_key(dev2, BTN_MIDDLE, packet[0] & 4);
100 input_report_rel(dev2, REL_X,
101 packet[1] ? packet[1] - ((packet[0] << 4) & 0x100) : 0);
102 input_report_rel(dev2, REL_Y,
103 packet[2] ? ((packet[0] << 3) & 0x100) - packet[2] : 0);
104 input_sync(dev2);
105 return;
106 }
107
108 if (model->flags & ALPS_OLDPROTO) { 167 if (model->flags & ALPS_OLDPROTO) {
109 left = packet[2] & 0x10; 168 left = packet[2] & 0x10;
110 right = packet[2] & 0x08; 169 right = packet[2] & 0x08;
@@ -140,18 +199,13 @@ static void alps_process_packet(struct psmouse *psmouse)
140 input_report_rel(dev2, REL_X, (x > 383 ? (x - 768) : x)); 199 input_report_rel(dev2, REL_X, (x > 383 ? (x - 768) : x));
141 input_report_rel(dev2, REL_Y, -(y > 255 ? (y - 512) : y)); 200 input_report_rel(dev2, REL_Y, -(y > 255 ? (y - 512) : y));
142 201
143 input_report_key(dev2, BTN_LEFT, left); 202 alps_report_buttons(psmouse, dev2, dev, left, right, middle);
144 input_report_key(dev2, BTN_RIGHT, right);
145 input_report_key(dev2, BTN_MIDDLE, middle);
146 203
147 input_sync(dev);
148 input_sync(dev2); 204 input_sync(dev2);
149 return; 205 return;
150 } 206 }
151 207
152 input_report_key(dev, BTN_LEFT, left); 208 alps_report_buttons(psmouse, dev, dev2, left, right, middle);
153 input_report_key(dev, BTN_RIGHT, right);
154 input_report_key(dev, BTN_MIDDLE, middle);
155 209
156 /* Convert hardware tap to a reasonable Z value */ 210 /* Convert hardware tap to a reasonable Z value */
157 if (ges && !fin) 211 if (ges && !fin)
@@ -202,25 +256,168 @@ static void alps_process_packet(struct psmouse *psmouse)
202 input_sync(dev); 256 input_sync(dev);
203} 257}
204 258
259static void alps_report_bare_ps2_packet(struct psmouse *psmouse,
260 unsigned char packet[],
261 bool report_buttons)
262{
263 struct alps_data *priv = psmouse->private;
264 struct input_dev *dev2 = priv->dev2;
265
266 if (report_buttons)
267 alps_report_buttons(psmouse, dev2, psmouse->dev,
268 packet[0] & 1, packet[0] & 2, packet[0] & 4);
269
270 input_report_rel(dev2, REL_X,
271 packet[1] ? packet[1] - ((packet[0] << 4) & 0x100) : 0);
272 input_report_rel(dev2, REL_Y,
273 packet[2] ? ((packet[0] << 3) & 0x100) - packet[2] : 0);
274
275 input_sync(dev2);
276}
277
278static psmouse_ret_t alps_handle_interleaved_ps2(struct psmouse *psmouse)
279{
280 struct alps_data *priv = psmouse->private;
281
282 if (psmouse->pktcnt < 6)
283 return PSMOUSE_GOOD_DATA;
284
285 if (psmouse->pktcnt == 6) {
286 /*
287 * Start a timer to flush the packet if it ends up last
288 * 6-byte packet in the stream. Timer needs to fire
289 * psmouse core times out itself. 20 ms should be enough
290 * to decide if we are getting more data or not.
291 */
292 mod_timer(&priv->timer, jiffies + msecs_to_jiffies(20));
293 return PSMOUSE_GOOD_DATA;
294 }
295
296 del_timer(&priv->timer);
297
298 if (psmouse->packet[6] & 0x80) {
299
300 /*
301 * Highest bit is set - that means we either had
302 * complete ALPS packet and this is start of the
303 * next packet or we got garbage.
304 */
305
306 if (((psmouse->packet[3] |
307 psmouse->packet[4] |
308 psmouse->packet[5]) & 0x80) ||
309 (!alps_is_valid_first_byte(priv->i, psmouse->packet[6]))) {
310 dbg("refusing packet %x %x %x %x "
311 "(suspected interleaved ps/2)\n",
312 psmouse->packet[3], psmouse->packet[4],
313 psmouse->packet[5], psmouse->packet[6]);
314 return PSMOUSE_BAD_DATA;
315 }
316
317 alps_process_packet(psmouse);
318
319 /* Continue with the next packet */
320 psmouse->packet[0] = psmouse->packet[6];
321 psmouse->pktcnt = 1;
322
323 } else {
324
325 /*
326 * High bit is 0 - that means that we indeed got a PS/2
327 * packet in the middle of ALPS packet.
328 *
329 * There is also possibility that we got 6-byte ALPS
330 * packet followed by 3-byte packet from trackpoint. We
331 * can not distinguish between these 2 scenarios but
332 * becase the latter is unlikely to happen in course of
333 * normal operation (user would need to press all
334 * buttons on the pad and start moving trackpoint
335 * without touching the pad surface) we assume former.
336 * Even if we are wrong the wost thing that would happen
337 * the cursor would jump but we should not get protocol
338 * desynchronization.
339 */
340
341 alps_report_bare_ps2_packet(psmouse, &psmouse->packet[3],
342 false);
343
344 /*
345 * Continue with the standard ALPS protocol handling,
346 * but make sure we won't process it as an interleaved
347 * packet again, which may happen if all buttons are
348 * pressed. To avoid this let's reset the 4th bit which
349 * is normally 1.
350 */
351 psmouse->packet[3] = psmouse->packet[6] & 0xf7;
352 psmouse->pktcnt = 4;
353 }
354
355 return PSMOUSE_GOOD_DATA;
356}
357
358static void alps_flush_packet(unsigned long data)
359{
360 struct psmouse *psmouse = (struct psmouse *)data;
361
362 serio_pause_rx(psmouse->ps2dev.serio);
363
364 if (psmouse->pktcnt == 6) {
365
366 /*
367 * We did not any more data in reasonable amount of time.
368 * Validate the last 3 bytes and process as a standard
369 * ALPS packet.
370 */
371 if ((psmouse->packet[3] |
372 psmouse->packet[4] |
373 psmouse->packet[5]) & 0x80) {
374 dbg("refusing packet %x %x %x "
375 "(suspected interleaved ps/2)\n",
376 psmouse->packet[3], psmouse->packet[4],
377 psmouse->packet[5]);
378 } else {
379 alps_process_packet(psmouse);
380 }
381 psmouse->pktcnt = 0;
382 }
383
384 serio_continue_rx(psmouse->ps2dev.serio);
385}
386
205static psmouse_ret_t alps_process_byte(struct psmouse *psmouse) 387static psmouse_ret_t alps_process_byte(struct psmouse *psmouse)
206{ 388{
207 struct alps_data *priv = psmouse->private; 389 struct alps_data *priv = psmouse->private;
390 const struct alps_model_info *model = priv->i;
208 391
209 if ((psmouse->packet[0] & 0xc8) == 0x08) { /* PS/2 packet */ 392 if ((psmouse->packet[0] & 0xc8) == 0x08) { /* PS/2 packet */
210 if (psmouse->pktcnt == 3) { 393 if (psmouse->pktcnt == 3) {
211 alps_process_packet(psmouse); 394 alps_report_bare_ps2_packet(psmouse, psmouse->packet,
395 true);
212 return PSMOUSE_FULL_PACKET; 396 return PSMOUSE_FULL_PACKET;
213 } 397 }
214 return PSMOUSE_GOOD_DATA; 398 return PSMOUSE_GOOD_DATA;
215 } 399 }
216 400
217 if ((psmouse->packet[0] & priv->i->mask0) != priv->i->byte0) 401 /* Check for PS/2 packet stuffed in the middle of ALPS packet. */
402
403 if ((model->flags & ALPS_PS2_INTERLEAVED) &&
404 psmouse->pktcnt >= 4 && (psmouse->packet[3] & 0x0f) == 0x0f) {
405 return alps_handle_interleaved_ps2(psmouse);
406 }
407
408 if (!alps_is_valid_first_byte(model, psmouse->packet[0])) {
409 dbg("refusing packet[0] = %x (mask0 = %x, byte0 = %x)\n",
410 psmouse->packet[0], model->mask0, model->byte0);
218 return PSMOUSE_BAD_DATA; 411 return PSMOUSE_BAD_DATA;
412 }
219 413
220 /* Bytes 2 - 6 should have 0 in the highest bit */ 414 /* Bytes 2 - 6 should have 0 in the highest bit */
221 if (psmouse->pktcnt >= 2 && psmouse->pktcnt <= 6 && 415 if (psmouse->pktcnt >= 2 && psmouse->pktcnt <= 6 &&
222 (psmouse->packet[psmouse->pktcnt - 1] & 0x80)) 416 (psmouse->packet[psmouse->pktcnt - 1] & 0x80)) {
417 dbg("refusing packet[%i] = %x\n",
418 psmouse->pktcnt - 1, psmouse->packet[psmouse->pktcnt - 1]);
223 return PSMOUSE_BAD_DATA; 419 return PSMOUSE_BAD_DATA;
420 }
224 421
225 if (psmouse->pktcnt == 6) { 422 if (psmouse->pktcnt == 6) {
226 alps_process_packet(psmouse); 423 alps_process_packet(psmouse);
@@ -459,6 +656,7 @@ static void alps_disconnect(struct psmouse *psmouse)
459 struct alps_data *priv = psmouse->private; 656 struct alps_data *priv = psmouse->private;
460 657
461 psmouse_reset(psmouse); 658 psmouse_reset(psmouse);
659 del_timer_sync(&priv->timer);
462 input_unregister_device(priv->dev2); 660 input_unregister_device(priv->dev2);
463 kfree(priv); 661 kfree(priv);
464} 662}
@@ -476,6 +674,8 @@ int alps_init(struct psmouse *psmouse)
476 goto init_fail; 674 goto init_fail;
477 675
478 priv->dev2 = dev2; 676 priv->dev2 = dev2;
677 setup_timer(&priv->timer, alps_flush_packet, (unsigned long)psmouse);
678
479 psmouse->private = priv; 679 psmouse->private = priv;
480 680
481 model = alps_get_model(psmouse, &version); 681 model = alps_get_model(psmouse, &version);
@@ -487,6 +687,17 @@ int alps_init(struct psmouse *psmouse)
487 if (alps_hw_init(psmouse)) 687 if (alps_hw_init(psmouse))
488 goto init_fail; 688 goto init_fail;
489 689
690 /*
691 * Undo part of setup done for us by psmouse core since touchpad
692 * is not a relative device.
693 */
694 __clear_bit(EV_REL, dev1->evbit);
695 __clear_bit(REL_X, dev1->relbit);
696 __clear_bit(REL_Y, dev1->relbit);
697
698 /*
699 * Now set up our capabilities.
700 */
490 dev1->evbit[BIT_WORD(EV_KEY)] |= BIT_MASK(EV_KEY); 701 dev1->evbit[BIT_WORD(EV_KEY)] |= BIT_MASK(EV_KEY);
491 dev1->keybit[BIT_WORD(BTN_TOUCH)] |= BIT_MASK(BTN_TOUCH); 702 dev1->keybit[BIT_WORD(BTN_TOUCH)] |= BIT_MASK(BTN_TOUCH);
492 dev1->keybit[BIT_WORD(BTN_TOOL_FINGER)] |= BIT_MASK(BTN_TOOL_FINGER); 703 dev1->keybit[BIT_WORD(BTN_TOOL_FINGER)] |= BIT_MASK(BTN_TOOL_FINGER);
diff --git a/drivers/input/mouse/alps.h b/drivers/input/mouse/alps.h
index bc87936fee1a..904ed8b3c8be 100644
--- a/drivers/input/mouse/alps.h
+++ b/drivers/input/mouse/alps.h
@@ -23,6 +23,7 @@ struct alps_data {
23 char phys[32]; /* Phys */ 23 char phys[32]; /* Phys */
24 const struct alps_model_info *i;/* Info */ 24 const struct alps_model_info *i;/* Info */
25 int prev_fin; /* Finger bit from previous packet */ 25 int prev_fin; /* Finger bit from previous packet */
26 struct timer_list timer;
26}; 27};
27 28
28#ifdef CONFIG_MOUSE_PS2_ALPS 29#ifdef CONFIG_MOUSE_PS2_ALPS
diff --git a/drivers/input/serio/altera_ps2.c b/drivers/input/serio/altera_ps2.c
index f479ea50919f..320b7ca48bf8 100644
--- a/drivers/input/serio/altera_ps2.c
+++ b/drivers/input/serio/altera_ps2.c
@@ -79,11 +79,11 @@ static void altera_ps2_close(struct serio *io)
79/* 79/*
80 * Add one device to this driver. 80 * Add one device to this driver.
81 */ 81 */
82static int altera_ps2_probe(struct platform_device *pdev) 82static int __devinit altera_ps2_probe(struct platform_device *pdev)
83{ 83{
84 struct ps2if *ps2if; 84 struct ps2if *ps2if;
85 struct serio *serio; 85 struct serio *serio;
86 int error; 86 int error, irq;
87 87
88 ps2if = kzalloc(sizeof(struct ps2if), GFP_KERNEL); 88 ps2if = kzalloc(sizeof(struct ps2if), GFP_KERNEL);
89 serio = kzalloc(sizeof(struct serio), GFP_KERNEL); 89 serio = kzalloc(sizeof(struct serio), GFP_KERNEL);
@@ -108,11 +108,13 @@ static int altera_ps2_probe(struct platform_device *pdev)
108 goto err_free_mem; 108 goto err_free_mem;
109 } 109 }
110 110
111 ps2if->irq = platform_get_irq(pdev, 0); 111
112 if (ps2if->irq < 0) { 112 irq = platform_get_irq(pdev, 0);
113 if (irq < 0) {
113 error = -ENXIO; 114 error = -ENXIO;
114 goto err_free_mem; 115 goto err_free_mem;
115 } 116 }
117 ps2if->irq = irq;
116 118
117 if (!request_mem_region(ps2if->iomem_res->start, 119 if (!request_mem_region(ps2if->iomem_res->start,
118 resource_size(ps2if->iomem_res), pdev->name)) { 120 resource_size(ps2if->iomem_res), pdev->name)) {
@@ -155,7 +157,7 @@ static int altera_ps2_probe(struct platform_device *pdev)
155/* 157/*
156 * Remove one device from this driver. 158 * Remove one device from this driver.
157 */ 159 */
158static int altera_ps2_remove(struct platform_device *pdev) 160static int __devexit altera_ps2_remove(struct platform_device *pdev)
159{ 161{
160 struct ps2if *ps2if = platform_get_drvdata(pdev); 162 struct ps2if *ps2if = platform_get_drvdata(pdev);
161 163
@@ -175,9 +177,10 @@ static int altera_ps2_remove(struct platform_device *pdev)
175 */ 177 */
176static struct platform_driver altera_ps2_driver = { 178static struct platform_driver altera_ps2_driver = {
177 .probe = altera_ps2_probe, 179 .probe = altera_ps2_probe,
178 .remove = altera_ps2_remove, 180 .remove = __devexit_p(altera_ps2_remove),
179 .driver = { 181 .driver = {
180 .name = DRV_NAME, 182 .name = DRV_NAME,
183 .owner = THIS_MODULE,
181 }, 184 },
182}; 185};
183 186
diff --git a/drivers/input/serio/ambakmi.c b/drivers/input/serio/ambakmi.c
index 89b394183a75..92563a681d65 100644
--- a/drivers/input/serio/ambakmi.c
+++ b/drivers/input/serio/ambakmi.c
@@ -107,7 +107,7 @@ static void amba_kmi_close(struct serio *io)
107 clk_disable(kmi->clk); 107 clk_disable(kmi->clk);
108} 108}
109 109
110static int amba_kmi_probe(struct amba_device *dev, struct amba_id *id) 110static int __devinit amba_kmi_probe(struct amba_device *dev, struct amba_id *id)
111{ 111{
112 struct amba_kmi_port *kmi; 112 struct amba_kmi_port *kmi;
113 struct serio *io; 113 struct serio *io;
@@ -134,7 +134,7 @@ static int amba_kmi_probe(struct amba_device *dev, struct amba_id *id)
134 io->port_data = kmi; 134 io->port_data = kmi;
135 io->dev.parent = &dev->dev; 135 io->dev.parent = &dev->dev;
136 136
137 kmi->io = io; 137 kmi->io = io;
138 kmi->base = ioremap(dev->res.start, resource_size(&dev->res)); 138 kmi->base = ioremap(dev->res.start, resource_size(&dev->res));
139 if (!kmi->base) { 139 if (!kmi->base) {
140 ret = -ENOMEM; 140 ret = -ENOMEM;
@@ -162,7 +162,7 @@ static int amba_kmi_probe(struct amba_device *dev, struct amba_id *id)
162 return ret; 162 return ret;
163} 163}
164 164
165static int amba_kmi_remove(struct amba_device *dev) 165static int __devexit amba_kmi_remove(struct amba_device *dev)
166{ 166{
167 struct amba_kmi_port *kmi = amba_get_drvdata(dev); 167 struct amba_kmi_port *kmi = amba_get_drvdata(dev);
168 168
@@ -197,10 +197,11 @@ static struct amba_id amba_kmi_idtable[] = {
197static struct amba_driver ambakmi_driver = { 197static struct amba_driver ambakmi_driver = {
198 .drv = { 198 .drv = {
199 .name = "kmi-pl050", 199 .name = "kmi-pl050",
200 .owner = THIS_MODULE,
200 }, 201 },
201 .id_table = amba_kmi_idtable, 202 .id_table = amba_kmi_idtable,
202 .probe = amba_kmi_probe, 203 .probe = amba_kmi_probe,
203 .remove = amba_kmi_remove, 204 .remove = __devexit_p(amba_kmi_remove),
204 .resume = amba_kmi_resume, 205 .resume = amba_kmi_resume,
205}; 206};
206 207
diff --git a/drivers/input/serio/at32psif.c b/drivers/input/serio/at32psif.c
index a6fb7a3dcc46..b54452a8c771 100644
--- a/drivers/input/serio/at32psif.c
+++ b/drivers/input/serio/at32psif.c
@@ -137,7 +137,7 @@ static int psif_write(struct serio *io, unsigned char val)
137 spin_lock_irqsave(&psif->lock, flags); 137 spin_lock_irqsave(&psif->lock, flags);
138 138
139 while (!(psif_readl(psif, SR) & PSIF_BIT(TXEMPTY)) && timeout--) 139 while (!(psif_readl(psif, SR) & PSIF_BIT(TXEMPTY)) && timeout--)
140 msleep(10); 140 udelay(50);
141 141
142 if (timeout >= 0) { 142 if (timeout >= 0) {
143 psif_writel(psif, THR, val); 143 psif_writel(psif, THR, val);
@@ -352,6 +352,7 @@ static struct platform_driver psif_driver = {
352 .remove = __exit_p(psif_remove), 352 .remove = __exit_p(psif_remove),
353 .driver = { 353 .driver = {
354 .name = "atmel_psif", 354 .name = "atmel_psif",
355 .owner = THIS_MODULE,
355 }, 356 },
356 .suspend = psif_suspend, 357 .suspend = psif_suspend,
357 .resume = psif_resume, 358 .resume = psif_resume,
diff --git a/drivers/input/serio/gscps2.c b/drivers/input/serio/gscps2.c
index bd0f92d9f40f..06addfa7cc47 100644
--- a/drivers/input/serio/gscps2.c
+++ b/drivers/input/serio/gscps2.c
@@ -6,7 +6,7 @@
6 * Copyright (c) 2002 Thibaut Varene <varenet@parisc-linux.org> 6 * Copyright (c) 2002 Thibaut Varene <varenet@parisc-linux.org>
7 * 7 *
8 * Pieces of code based on linux-2.4's hp_mouse.c & hp_keyb.c 8 * Pieces of code based on linux-2.4's hp_mouse.c & hp_keyb.c
9 * Copyright (c) 1999 Alex deVries <alex@onefishtwo.ca> 9 * Copyright (c) 1999 Alex deVries <alex@onefishtwo.ca>
10 * Copyright (c) 1999-2000 Philipp Rumpf <prumpf@tux.org> 10 * Copyright (c) 1999-2000 Philipp Rumpf <prumpf@tux.org>
11 * Copyright (c) 2000 Xavier Debacker <debackex@esiee.fr> 11 * Copyright (c) 2000 Xavier Debacker <debackex@esiee.fr>
12 * Copyright (c) 2000-2001 Thomas Marteau <marteaut@esiee.fr> 12 * Copyright (c) 2000-2001 Thomas Marteau <marteaut@esiee.fr>
@@ -326,7 +326,7 @@ static void gscps2_close(struct serio *port)
326 * @return: success/error report 326 * @return: success/error report
327 */ 327 */
328 328
329static int __init gscps2_probe(struct parisc_device *dev) 329static int __devinit gscps2_probe(struct parisc_device *dev)
330{ 330{
331 struct gscps2port *ps2port; 331 struct gscps2port *ps2port;
332 struct serio *serio; 332 struct serio *serio;
@@ -443,7 +443,7 @@ static struct parisc_driver parisc_ps2_driver = {
443 .name = "gsc_ps2", 443 .name = "gsc_ps2",
444 .id_table = gscps2_device_tbl, 444 .id_table = gscps2_device_tbl,
445 .probe = gscps2_probe, 445 .probe = gscps2_probe,
446 .remove = gscps2_remove, 446 .remove = __devexit_p(gscps2_remove),
447}; 447};
448 448
449static int __init gscps2_init(void) 449static int __init gscps2_init(void)
diff --git a/drivers/input/serio/hil_mlc.c b/drivers/input/serio/hil_mlc.c
index 7ba9f2b2c041..6cd03ebaf5fb 100644
--- a/drivers/input/serio/hil_mlc.c
+++ b/drivers/input/serio/hil_mlc.c
@@ -993,10 +993,8 @@ int hil_mlc_unregister(hil_mlc *mlc)
993 993
994static int __init hil_mlc_init(void) 994static int __init hil_mlc_init(void)
995{ 995{
996 init_timer(&hil_mlcs_kicker); 996 setup_timer(&hil_mlcs_kicker, &hil_mlcs_timer, 0);
997 hil_mlcs_kicker.expires = jiffies + HZ; 997 mod_timer(&hil_mlcs_kicker, jiffies + HZ);
998 hil_mlcs_kicker.function = &hil_mlcs_timer;
999 add_timer(&hil_mlcs_kicker);
1000 998
1001 tasklet_enable(&hil_mlcs_tasklet); 999 tasklet_enable(&hil_mlcs_tasklet);
1002 1000
@@ -1005,7 +1003,7 @@ static int __init hil_mlc_init(void)
1005 1003
1006static void __exit hil_mlc_exit(void) 1004static void __exit hil_mlc_exit(void)
1007{ 1005{
1008 del_timer(&hil_mlcs_kicker); 1006 del_timer_sync(&hil_mlcs_kicker);
1009 1007
1010 tasklet_disable(&hil_mlcs_tasklet); 1008 tasklet_disable(&hil_mlcs_tasklet);
1011 tasklet_kill(&hil_mlcs_tasklet); 1009 tasklet_kill(&hil_mlcs_tasklet);
diff --git a/drivers/input/serio/i8042-x86ia64io.h b/drivers/input/serio/i8042-x86ia64io.h
index 7fbffe431bc5..64b688daf48a 100644
--- a/drivers/input/serio/i8042-x86ia64io.h
+++ b/drivers/input/serio/i8042-x86ia64io.h
@@ -158,6 +158,14 @@ static const struct dmi_system_id __initconst i8042_dmi_noloop_table[] = {
158 }, 158 },
159 }, 159 },
160 { 160 {
161 /* Gigabyte M1022M netbook */
162 .matches = {
163 DMI_MATCH(DMI_BOARD_VENDOR, "Gigabyte Technology Co.,Ltd."),
164 DMI_MATCH(DMI_BOARD_NAME, "M1022E"),
165 DMI_MATCH(DMI_BOARD_VERSION, "1.02"),
166 },
167 },
168 {
161 .matches = { 169 .matches = {
162 DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), 170 DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"),
163 DMI_MATCH(DMI_PRODUCT_NAME, "HP Pavilion dv9700"), 171 DMI_MATCH(DMI_PRODUCT_NAME, "HP Pavilion dv9700"),
diff --git a/drivers/input/serio/i8042.c b/drivers/input/serio/i8042.c
index 1df02d25aca5..d84a36e545f6 100644
--- a/drivers/input/serio/i8042.c
+++ b/drivers/input/serio/i8042.c
@@ -126,6 +126,8 @@ static unsigned char i8042_suppress_kbd_ack;
126static struct platform_device *i8042_platform_device; 126static struct platform_device *i8042_platform_device;
127 127
128static irqreturn_t i8042_interrupt(int irq, void *dev_id); 128static irqreturn_t i8042_interrupt(int irq, void *dev_id);
129static bool (*i8042_platform_filter)(unsigned char data, unsigned char str,
130 struct serio *serio);
129 131
130void i8042_lock_chip(void) 132void i8042_lock_chip(void)
131{ 133{
@@ -139,6 +141,48 @@ void i8042_unlock_chip(void)
139} 141}
140EXPORT_SYMBOL(i8042_unlock_chip); 142EXPORT_SYMBOL(i8042_unlock_chip);
141 143
144int i8042_install_filter(bool (*filter)(unsigned char data, unsigned char str,
145 struct serio *serio))
146{
147 unsigned long flags;
148 int ret = 0;
149
150 spin_lock_irqsave(&i8042_lock, flags);
151
152 if (i8042_platform_filter) {
153 ret = -EBUSY;
154 goto out;
155 }
156
157 i8042_platform_filter = filter;
158
159out:
160 spin_unlock_irqrestore(&i8042_lock, flags);
161 return ret;
162}
163EXPORT_SYMBOL(i8042_install_filter);
164
165int i8042_remove_filter(bool (*filter)(unsigned char data, unsigned char str,
166 struct serio *port))
167{
168 unsigned long flags;
169 int ret = 0;
170
171 spin_lock_irqsave(&i8042_lock, flags);
172
173 if (i8042_platform_filter != filter) {
174 ret = -EINVAL;
175 goto out;
176 }
177
178 i8042_platform_filter = NULL;
179
180out:
181 spin_unlock_irqrestore(&i8042_lock, flags);
182 return ret;
183}
184EXPORT_SYMBOL(i8042_remove_filter);
185
142/* 186/*
143 * The i8042_wait_read() and i8042_wait_write functions wait for the i8042 to 187 * The i8042_wait_read() and i8042_wait_write functions wait for the i8042 to
144 * be ready for reading values from it / writing values to it. 188 * be ready for reading values from it / writing values to it.
@@ -369,6 +413,31 @@ static void i8042_stop(struct serio *serio)
369} 413}
370 414
371/* 415/*
416 * i8042_filter() filters out unwanted bytes from the input data stream.
417 * It is called from i8042_interrupt and thus is running with interrupts
418 * off and i8042_lock held.
419 */
420static bool i8042_filter(unsigned char data, unsigned char str,
421 struct serio *serio)
422{
423 if (unlikely(i8042_suppress_kbd_ack)) {
424 if ((~str & I8042_STR_AUXDATA) &&
425 (data == 0xfa || data == 0xfe)) {
426 i8042_suppress_kbd_ack--;
427 dbg("Extra keyboard ACK - filtered out\n");
428 return true;
429 }
430 }
431
432 if (i8042_platform_filter && i8042_platform_filter(data, str, serio)) {
433 dbg("Filtered out by platfrom filter\n");
434 return true;
435 }
436
437 return false;
438}
439
440/*
372 * i8042_interrupt() is the most important function in this driver - 441 * i8042_interrupt() is the most important function in this driver -
373 * it handles the interrupts from the i8042, and sends incoming bytes 442 * it handles the interrupts from the i8042, and sends incoming bytes
374 * to the upper layers. 443 * to the upper layers.
@@ -377,13 +446,16 @@ static void i8042_stop(struct serio *serio)
377static irqreturn_t i8042_interrupt(int irq, void *dev_id) 446static irqreturn_t i8042_interrupt(int irq, void *dev_id)
378{ 447{
379 struct i8042_port *port; 448 struct i8042_port *port;
449 struct serio *serio;
380 unsigned long flags; 450 unsigned long flags;
381 unsigned char str, data; 451 unsigned char str, data;
382 unsigned int dfl; 452 unsigned int dfl;
383 unsigned int port_no; 453 unsigned int port_no;
454 bool filtered;
384 int ret = 1; 455 int ret = 1;
385 456
386 spin_lock_irqsave(&i8042_lock, flags); 457 spin_lock_irqsave(&i8042_lock, flags);
458
387 str = i8042_read_status(); 459 str = i8042_read_status();
388 if (unlikely(~str & I8042_STR_OBF)) { 460 if (unlikely(~str & I8042_STR_OBF)) {
389 spin_unlock_irqrestore(&i8042_lock, flags); 461 spin_unlock_irqrestore(&i8042_lock, flags);
@@ -391,8 +463,8 @@ static irqreturn_t i8042_interrupt(int irq, void *dev_id)
391 ret = 0; 463 ret = 0;
392 goto out; 464 goto out;
393 } 465 }
466
394 data = i8042_read_data(); 467 data = i8042_read_data();
395 spin_unlock_irqrestore(&i8042_lock, flags);
396 468
397 if (i8042_mux_present && (str & I8042_STR_AUXDATA)) { 469 if (i8042_mux_present && (str & I8042_STR_AUXDATA)) {
398 static unsigned long last_transmit; 470 static unsigned long last_transmit;
@@ -441,21 +513,19 @@ static irqreturn_t i8042_interrupt(int irq, void *dev_id)
441 } 513 }
442 514
443 port = &i8042_ports[port_no]; 515 port = &i8042_ports[port_no];
516 serio = port->exists ? port->serio : NULL;
444 517
445 dbg("%02x <- i8042 (interrupt, %d, %d%s%s)", 518 dbg("%02x <- i8042 (interrupt, %d, %d%s%s)",
446 data, port_no, irq, 519 data, port_no, irq,
447 dfl & SERIO_PARITY ? ", bad parity" : "", 520 dfl & SERIO_PARITY ? ", bad parity" : "",
448 dfl & SERIO_TIMEOUT ? ", timeout" : ""); 521 dfl & SERIO_TIMEOUT ? ", timeout" : "");
449 522
450 if (unlikely(i8042_suppress_kbd_ack)) 523 filtered = i8042_filter(data, str, serio);
451 if (port_no == I8042_KBD_PORT_NO && 524
452 (data == 0xfa || data == 0xfe)) { 525 spin_unlock_irqrestore(&i8042_lock, flags);
453 i8042_suppress_kbd_ack--;
454 goto out;
455 }
456 526
457 if (likely(port->exists)) 527 if (likely(port->exists && !filtered))
458 serio_interrupt(port->serio, data, dfl); 528 serio_interrupt(serio, data, dfl);
459 529
460 out: 530 out:
461 return IRQ_RETVAL(ret); 531 return IRQ_RETVAL(ret);
diff --git a/drivers/input/serio/sa1111ps2.c b/drivers/input/serio/sa1111ps2.c
index f412c69478a8..d55874e5d1c2 100644
--- a/drivers/input/serio/sa1111ps2.c
+++ b/drivers/input/serio/sa1111ps2.c
@@ -180,8 +180,8 @@ static void __devinit ps2_clear_input(struct ps2if *ps2if)
180 } 180 }
181} 181}
182 182
183static inline unsigned int 183static unsigned int __devinit ps2_test_one(struct ps2if *ps2if,
184ps2_test_one(struct ps2if *ps2if, unsigned int mask) 184 unsigned int mask)
185{ 185{
186 unsigned int val; 186 unsigned int val;
187 187
@@ -197,7 +197,7 @@ ps2_test_one(struct ps2if *ps2if, unsigned int mask)
197 * Test the keyboard interface. We basically check to make sure that 197 * Test the keyboard interface. We basically check to make sure that
198 * we can drive each line to the keyboard independently of each other. 198 * we can drive each line to the keyboard independently of each other.
199 */ 199 */
200static int __init ps2_test(struct ps2if *ps2if) 200static int __devinit ps2_test(struct ps2if *ps2if)
201{ 201{
202 unsigned int stat; 202 unsigned int stat;
203 int ret = 0; 203 int ret = 0;
@@ -312,7 +312,7 @@ static int __devinit ps2_probe(struct sa1111_dev *dev)
312/* 312/*
313 * Remove one device from this driver. 313 * Remove one device from this driver.
314 */ 314 */
315static int ps2_remove(struct sa1111_dev *dev) 315static int __devexit ps2_remove(struct sa1111_dev *dev)
316{ 316{
317 struct ps2if *ps2if = sa1111_get_drvdata(dev); 317 struct ps2if *ps2if = sa1111_get_drvdata(dev);
318 318
@@ -335,7 +335,7 @@ static struct sa1111_driver ps2_driver = {
335 }, 335 },
336 .devid = SA1111_DEVID_PS2, 336 .devid = SA1111_DEVID_PS2,
337 .probe = ps2_probe, 337 .probe = ps2_probe,
338 .remove = ps2_remove, 338 .remove = __devexit_p(ps2_remove),
339}; 339};
340 340
341static int __init ps2_init(void) 341static int __init ps2_init(void)
diff --git a/drivers/input/tablet/wacom.h b/drivers/input/tablet/wacom.h
index 9114ae1c7488..16310f368dab 100644
--- a/drivers/input/tablet/wacom.h
+++ b/drivers/input/tablet/wacom.h
@@ -1,7 +1,7 @@
1/* 1/*
2 * drivers/input/tablet/wacom.h 2 * drivers/input/tablet/wacom.h
3 * 3 *
4 * USB Wacom Graphire and Wacom Intuos tablet support 4 * USB Wacom tablet support
5 * 5 *
6 * Copyright (c) 2000-2004 Vojtech Pavlik <vojtech@ucw.cz> 6 * Copyright (c) 2000-2004 Vojtech Pavlik <vojtech@ucw.cz>
7 * Copyright (c) 2000 Andreas Bach Aaen <abach@stofanet.dk> 7 * Copyright (c) 2000 Andreas Bach Aaen <abach@stofanet.dk>
@@ -69,6 +69,9 @@
69 * v1.49 (pc) - Added support for USB Tablet PC (0x90, 0x93, and 0x9A) 69 * v1.49 (pc) - Added support for USB Tablet PC (0x90, 0x93, and 0x9A)
70 * v1.50 (pc) - Fixed a TabletPC touch bug in 2.6.28 70 * v1.50 (pc) - Fixed a TabletPC touch bug in 2.6.28
71 * v1.51 (pc) - Added support for Intuos4 71 * v1.51 (pc) - Added support for Intuos4
72 * v1.52 (pc) - Query Wacom data upon system resume
73 * - add defines for features->type
74 * - add new devices (0x9F, 0xE2, and 0XE3)
72 */ 75 */
73 76
74/* 77/*
@@ -89,9 +92,9 @@
89/* 92/*
90 * Version Information 93 * Version Information
91 */ 94 */
92#define DRIVER_VERSION "v1.51" 95#define DRIVER_VERSION "v1.52"
93#define DRIVER_AUTHOR "Vojtech Pavlik <vojtech@ucw.cz>" 96#define DRIVER_AUTHOR "Vojtech Pavlik <vojtech@ucw.cz>"
94#define DRIVER_DESC "USB Wacom Graphire and Wacom Intuos tablet driver" 97#define DRIVER_DESC "USB Wacom tablet driver"
95#define DRIVER_LICENSE "GPL" 98#define DRIVER_LICENSE "GPL"
96 99
97MODULE_AUTHOR(DRIVER_AUTHOR); 100MODULE_AUTHOR(DRIVER_AUTHOR);
@@ -133,6 +136,8 @@ extern void input_dev_i4s(struct input_dev *input_dev, struct wacom_wac *wacom_w
133extern void input_dev_i4(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 136extern void input_dev_i4(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
134extern void input_dev_pl(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 137extern void input_dev_pl(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
135extern void input_dev_pt(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 138extern void input_dev_pt(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
139extern void input_dev_tpc(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
140extern void input_dev_tpc2fg(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
136extern void input_dev_mo(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 141extern void input_dev_mo(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
137extern void input_dev_bee(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 142extern void input_dev_bee(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
138extern __u16 wacom_le16_to_cpu(unsigned char *data); 143extern __u16 wacom_le16_to_cpu(unsigned char *data);
diff --git a/drivers/input/tablet/wacom_sys.c b/drivers/input/tablet/wacom_sys.c
index ea30c983a33e..072f33b3b2b0 100644
--- a/drivers/input/tablet/wacom_sys.c
+++ b/drivers/input/tablet/wacom_sys.c
@@ -1,7 +1,7 @@
1/* 1/*
2 * drivers/input/tablet/wacom_sys.c 2 * drivers/input/tablet/wacom_sys.c
3 * 3 *
4 * USB Wacom Graphire and Wacom Intuos tablet support - system specific code 4 * USB Wacom tablet support - system specific code
5 */ 5 */
6 6
7/* 7/*
@@ -209,6 +209,7 @@ void input_dev_g(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
209 input_dev->keybit[BIT_WORD(BTN_MOUSE)] |= BIT_MASK(BTN_LEFT) | 209 input_dev->keybit[BIT_WORD(BTN_MOUSE)] |= BIT_MASK(BTN_LEFT) |
210 BIT_MASK(BTN_RIGHT) | BIT_MASK(BTN_MIDDLE); 210 BIT_MASK(BTN_RIGHT) | BIT_MASK(BTN_MIDDLE);
211 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_RUBBER) | 211 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_RUBBER) |
212 BIT_MASK(BTN_TOOL_PEN) | BIT_MASK(BTN_STYLUS) |
212 BIT_MASK(BTN_TOOL_MOUSE) | BIT_MASK(BTN_STYLUS2); 213 BIT_MASK(BTN_TOOL_MOUSE) | BIT_MASK(BTN_STYLUS2);
213 input_set_abs_params(input_dev, ABS_DISTANCE, 0, wacom_wac->features->distance_max, 0, 0); 214 input_set_abs_params(input_dev, ABS_DISTANCE, 0, wacom_wac->features->distance_max, 0, 0);
214} 215}
@@ -256,6 +257,7 @@ void input_dev_i(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
256 BIT_MASK(BTN_RIGHT) | BIT_MASK(BTN_MIDDLE) | 257 BIT_MASK(BTN_RIGHT) | BIT_MASK(BTN_MIDDLE) |
257 BIT_MASK(BTN_SIDE) | BIT_MASK(BTN_EXTRA); 258 BIT_MASK(BTN_SIDE) | BIT_MASK(BTN_EXTRA);
258 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_RUBBER) | 259 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_RUBBER) |
260 BIT_MASK(BTN_TOOL_PEN) | BIT_MASK(BTN_STYLUS) |
259 BIT_MASK(BTN_TOOL_MOUSE) | BIT_MASK(BTN_TOOL_BRUSH) | 261 BIT_MASK(BTN_TOOL_MOUSE) | BIT_MASK(BTN_TOOL_BRUSH) |
260 BIT_MASK(BTN_TOOL_PENCIL) | BIT_MASK(BTN_TOOL_AIRBRUSH) | 262 BIT_MASK(BTN_TOOL_PENCIL) | BIT_MASK(BTN_TOOL_AIRBRUSH) |
261 BIT_MASK(BTN_TOOL_LENS) | BIT_MASK(BTN_STYLUS2); 263 BIT_MASK(BTN_TOOL_LENS) | BIT_MASK(BTN_STYLUS2);
@@ -269,7 +271,8 @@ void input_dev_i(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
269 271
270void input_dev_pl(struct input_dev *input_dev, struct wacom_wac *wacom_wac) 272void input_dev_pl(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
271{ 273{
272 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_STYLUS2); 274 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_PEN) |
275 BIT_MASK(BTN_STYLUS) | BIT_MASK(BTN_STYLUS2);
273} 276}
274 277
275void input_dev_pt(struct input_dev *input_dev, struct wacom_wac *wacom_wac) 278void input_dev_pt(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
@@ -277,12 +280,32 @@ void input_dev_pt(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
277 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_RUBBER); 280 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_RUBBER);
278} 281}
279 282
283void input_dev_tpc(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
284{
285 if (wacom_wac->features->device_type == BTN_TOOL_DOUBLETAP ||
286 wacom_wac->features->device_type == BTN_TOOL_TRIPLETAP) {
287 input_set_abs_params(input_dev, ABS_RX, 0, wacom_wac->features->x_phy, 0, 0);
288 input_set_abs_params(input_dev, ABS_RY, 0, wacom_wac->features->y_phy, 0, 0);
289 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_DOUBLETAP);
290 }
291}
292
293void input_dev_tpc2fg(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
294{
295 if (wacom_wac->features->device_type == BTN_TOOL_TRIPLETAP) {
296 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_TRIPLETAP);
297 input_dev->evbit[0] |= BIT_MASK(EV_MSC);
298 input_dev->mscbit[0] |= BIT_MASK(MSC_SERIAL);
299 }
300}
301
280static int wacom_parse_hid(struct usb_interface *intf, struct hid_descriptor *hid_desc, 302static int wacom_parse_hid(struct usb_interface *intf, struct hid_descriptor *hid_desc,
281 struct wacom_wac *wacom_wac) 303 struct wacom_features *features)
282{ 304{
283 struct usb_device *dev = interface_to_usbdev(intf); 305 struct usb_device *dev = interface_to_usbdev(intf);
284 struct wacom_features *features = wacom_wac->features; 306 char limit = 0;
285 char limit = 0, result = 0; 307 /* result has to be defined as int for some devices */
308 int result = 0;
286 int i = 0, usage = WCM_UNDEFINED, finger = 0, pen = 0; 309 int i = 0, usage = WCM_UNDEFINED, finger = 0, pen = 0;
287 unsigned char *report; 310 unsigned char *report;
288 311
@@ -328,13 +351,24 @@ static int wacom_parse_hid(struct usb_interface *intf, struct hid_descriptor *hi
328 case HID_USAGE_X: 351 case HID_USAGE_X:
329 if (usage == WCM_DESKTOP) { 352 if (usage == WCM_DESKTOP) {
330 if (finger) { 353 if (finger) {
331 features->touch_x_max = 354 features->device_type = BTN_TOOL_DOUBLETAP;
332 features->touch_y_max = 355 if (features->type == TABLETPC2FG) {
333 wacom_le16_to_cpu(&report[i + 3]); 356 /* need to reset back */
357 features->pktlen = WACOM_PKGLEN_TPC2FG;
358 features->device_type = BTN_TOOL_TRIPLETAP;
359 }
334 features->x_max = 360 features->x_max =
361 wacom_le16_to_cpu(&report[i + 3]);
362 features->x_phy =
335 wacom_le16_to_cpu(&report[i + 6]); 363 wacom_le16_to_cpu(&report[i + 6]);
336 i += 7; 364 features->unit = report[i + 9];
365 features->unitExpo = report[i + 11];
366 i += 12;
337 } else if (pen) { 367 } else if (pen) {
368 /* penabled only accepts exact bytes of data */
369 if (features->type == TABLETPC2FG)
370 features->pktlen = WACOM_PKGLEN_PENABLED;
371 features->device_type = BTN_TOOL_PEN;
338 features->x_max = 372 features->x_max =
339 wacom_le16_to_cpu(&report[i + 3]); 373 wacom_le16_to_cpu(&report[i + 3]);
340 i += 4; 374 i += 4;
@@ -350,10 +384,35 @@ static int wacom_parse_hid(struct usb_interface *intf, struct hid_descriptor *hi
350 break; 384 break;
351 385
352 case HID_USAGE_Y: 386 case HID_USAGE_Y:
353 if (usage == WCM_DESKTOP) 387 if (usage == WCM_DESKTOP) {
354 features->y_max = 388 if (finger) {
355 wacom_le16_to_cpu(&report[i + 3]); 389 features->device_type = BTN_TOOL_DOUBLETAP;
356 i += 4; 390 if (features->type == TABLETPC2FG) {
391 /* need to reset back */
392 features->pktlen = WACOM_PKGLEN_TPC2FG;
393 features->device_type = BTN_TOOL_TRIPLETAP;
394 features->y_max =
395 wacom_le16_to_cpu(&report[i + 3]);
396 features->y_phy =
397 wacom_le16_to_cpu(&report[i + 6]);
398 i += 7;
399 } else {
400 features->y_max =
401 features->x_max;
402 features->y_phy =
403 wacom_le16_to_cpu(&report[i + 3]);
404 i += 4;
405 }
406 } else if (pen) {
407 /* penabled only accepts exact bytes of data */
408 if (features->type == TABLETPC2FG)
409 features->pktlen = WACOM_PKGLEN_PENABLED;
410 features->device_type = BTN_TOOL_PEN;
411 features->y_max =
412 wacom_le16_to_cpu(&report[i + 3]);
413 i += 4;
414 }
415 }
357 break; 416 break;
358 417
359 case HID_USAGE_FINGER: 418 case HID_USAGE_FINGER:
@@ -376,7 +435,7 @@ static int wacom_parse_hid(struct usb_interface *intf, struct hid_descriptor *hi
376 break; 435 break;
377 436
378 case HID_COLLECTION: 437 case HID_COLLECTION:
379 /* reset UsagePage ans Finger */ 438 /* reset UsagePage and Finger */
380 finger = usage = 0; 439 finger = usage = 0;
381 break; 440 break;
382 } 441 }
@@ -388,43 +447,92 @@ static int wacom_parse_hid(struct usb_interface *intf, struct hid_descriptor *hi
388 return result; 447 return result;
389} 448}
390 449
391static int wacom_query_tablet_data(struct usb_interface *intf) 450static int wacom_query_tablet_data(struct usb_interface *intf, struct wacom_features *features)
392{ 451{
393 unsigned char *rep_data; 452 unsigned char *rep_data;
394 int limit = 0; 453 int limit = 0, report_id = 2;
395 int error; 454 int error = -ENOMEM;
396 455
397 rep_data = kmalloc(2, GFP_KERNEL); 456 rep_data = kmalloc(2, GFP_KERNEL);
398 if (!rep_data) 457 if (!rep_data)
399 return -ENOMEM; 458 return error;
400 459
401 do { 460 /* ask to report tablet data if it is 2FGT or not a Tablet PC */
402 rep_data[0] = 2; 461 if (features->device_type == BTN_TOOL_TRIPLETAP) {
403 rep_data[1] = 2; 462 do {
404 error = usb_set_report(intf, WAC_HID_FEATURE_REPORT, 463 rep_data[0] = 3;
405 2, rep_data, 2); 464 rep_data[1] = 4;
406 if (error >= 0) 465 report_id = 3;
407 error = usb_get_report(intf, 466 error = usb_set_report(intf, WAC_HID_FEATURE_REPORT,
408 WAC_HID_FEATURE_REPORT, 2, 467 report_id, rep_data, 2);
409 rep_data, 2); 468 if (error >= 0)
410 } while ((error < 0 || rep_data[1] != 2) && limit++ < 5); 469 error = usb_get_report(intf,
470 WAC_HID_FEATURE_REPORT, report_id,
471 rep_data, 3);
472 } while ((error < 0 || rep_data[1] != 4) && limit++ < 5);
473 } else if (features->type != TABLETPC && features->type != TABLETPC2FG) {
474 do {
475 rep_data[0] = 2;
476 rep_data[1] = 2;
477 error = usb_set_report(intf, WAC_HID_FEATURE_REPORT,
478 report_id, rep_data, 2);
479 if (error >= 0)
480 error = usb_get_report(intf,
481 WAC_HID_FEATURE_REPORT, report_id,
482 rep_data, 2);
483 } while ((error < 0 || rep_data[1] != 2) && limit++ < 5);
484 }
411 485
412 kfree(rep_data); 486 kfree(rep_data);
413 487
414 return error < 0 ? error : 0; 488 return error < 0 ? error : 0;
415} 489}
416 490
491static int wacom_retrieve_hid_descriptor(struct usb_interface *intf,
492 struct wacom_features *features)
493{
494 int error = 0;
495 struct usb_host_interface *interface = intf->cur_altsetting;
496 struct hid_descriptor *hid_desc;
497
498 /* default device to penabled */
499 features->device_type = BTN_TOOL_PEN;
500
501 /* only Tablet PCs need to retrieve the info */
502 if ((features->type != TABLETPC) && (features->type != TABLETPC2FG))
503 goto out;
504
505 if (usb_get_extra_descriptor(interface, HID_DEVICET_HID, &hid_desc)) {
506 if (usb_get_extra_descriptor(&interface->endpoint[0],
507 HID_DEVICET_REPORT, &hid_desc)) {
508 printk("wacom: can not retrieve extra class descriptor\n");
509 error = 1;
510 goto out;
511 }
512 }
513 error = wacom_parse_hid(intf, hid_desc, features);
514 if (error)
515 goto out;
516
517 /* touch device found but size is not defined. use default */
518 if (features->device_type == BTN_TOOL_DOUBLETAP && !features->x_max) {
519 features->x_max = 1023;
520 features->y_max = 1023;
521 }
522
523 out:
524 return error;
525}
526
417static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *id) 527static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *id)
418{ 528{
419 struct usb_device *dev = interface_to_usbdev(intf); 529 struct usb_device *dev = interface_to_usbdev(intf);
420 struct usb_host_interface *interface = intf->cur_altsetting;
421 struct usb_endpoint_descriptor *endpoint; 530 struct usb_endpoint_descriptor *endpoint;
422 struct wacom *wacom; 531 struct wacom *wacom;
423 struct wacom_wac *wacom_wac; 532 struct wacom_wac *wacom_wac;
424 struct wacom_features *features; 533 struct wacom_features *features;
425 struct input_dev *input_dev; 534 struct input_dev *input_dev;
426 int error = -ENOMEM; 535 int error = -ENOMEM;
427 struct hid_descriptor *hid_desc;
428 536
429 wacom = kzalloc(sizeof(struct wacom), GFP_KERNEL); 537 wacom = kzalloc(sizeof(struct wacom), GFP_KERNEL);
430 wacom_wac = kzalloc(sizeof(struct wacom_wac), GFP_KERNEL); 538 wacom_wac = kzalloc(sizeof(struct wacom_wac), GFP_KERNEL);
@@ -432,7 +540,7 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
432 if (!wacom || !input_dev || !wacom_wac) 540 if (!wacom || !input_dev || !wacom_wac)
433 goto fail1; 541 goto fail1;
434 542
435 wacom_wac->data = usb_buffer_alloc(dev, 10, GFP_KERNEL, &wacom->data_dma); 543 wacom_wac->data = usb_buffer_alloc(dev, WACOM_PKGLEN_MAX, GFP_KERNEL, &wacom->data_dma);
436 if (!wacom_wac->data) 544 if (!wacom_wac->data)
437 goto fail1; 545 goto fail1;
438 546
@@ -448,7 +556,7 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
448 strlcat(wacom->phys, "/input0", sizeof(wacom->phys)); 556 strlcat(wacom->phys, "/input0", sizeof(wacom->phys));
449 557
450 wacom_wac->features = features = get_wacom_feature(id); 558 wacom_wac->features = features = get_wacom_feature(id);
451 BUG_ON(features->pktlen > 10); 559 BUG_ON(features->pktlen > WACOM_PKGLEN_MAX);
452 560
453 input_dev->name = wacom_wac->features->name; 561 input_dev->name = wacom_wac->features->name;
454 wacom->wacom_wac = wacom_wac; 562 wacom->wacom_wac = wacom_wac;
@@ -463,47 +571,24 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
463 571
464 endpoint = &intf->cur_altsetting->endpoint[0].desc; 572 endpoint = &intf->cur_altsetting->endpoint[0].desc;
465 573
466 /* Initialize touch_x_max and touch_y_max in case it is not defined */ 574 /* Retrieve the physical and logical size for OEM devices */
467 if (wacom_wac->features->type == TABLETPC) { 575 error = wacom_retrieve_hid_descriptor(intf, features);
468 features->touch_x_max = 1023; 576 if (error)
469 features->touch_y_max = 1023; 577 goto fail2;
470 } else {
471 features->touch_x_max = 0;
472 features->touch_y_max = 0;
473 }
474
475 /* TabletPC need to retrieve the physical and logical maximum from report descriptor */
476 if (wacom_wac->features->type == TABLETPC) {
477 if (usb_get_extra_descriptor(interface, HID_DEVICET_HID, &hid_desc)) {
478 if (usb_get_extra_descriptor(&interface->endpoint[0],
479 HID_DEVICET_REPORT, &hid_desc)) {
480 printk("wacom: can not retrive extra class descriptor\n");
481 goto fail2;
482 }
483 }
484 error = wacom_parse_hid(intf, hid_desc, wacom_wac);
485 if (error)
486 goto fail2;
487 }
488 578
489 input_dev->evbit[0] |= BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS); 579 input_dev->evbit[0] |= BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS);
490 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_PEN) | 580 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOUCH);
491 BIT_MASK(BTN_TOUCH) | BIT_MASK(BTN_STYLUS); 581
492 input_set_abs_params(input_dev, ABS_X, 0, features->x_max, 4, 0); 582 input_set_abs_params(input_dev, ABS_X, 0, features->x_max, 4, 0);
493 input_set_abs_params(input_dev, ABS_Y, 0, features->y_max, 4, 0); 583 input_set_abs_params(input_dev, ABS_Y, 0, features->y_max, 4, 0);
494 input_set_abs_params(input_dev, ABS_PRESSURE, 0, features->pressure_max, 0, 0); 584 input_set_abs_params(input_dev, ABS_PRESSURE, 0, features->pressure_max, 0, 0);
495 if (features->type == TABLETPC) {
496 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_DOUBLETAP);
497 input_set_abs_params(input_dev, ABS_RX, 0, features->touch_x_max, 4, 0);
498 input_set_abs_params(input_dev, ABS_RY, 0, features->touch_y_max, 4, 0);
499 }
500 input_dev->absbit[BIT_WORD(ABS_MISC)] |= BIT_MASK(ABS_MISC); 585 input_dev->absbit[BIT_WORD(ABS_MISC)] |= BIT_MASK(ABS_MISC);
501 586
502 wacom_init_input_dev(input_dev, wacom_wac); 587 wacom_init_input_dev(input_dev, wacom_wac);
503 588
504 usb_fill_int_urb(wacom->irq, dev, 589 usb_fill_int_urb(wacom->irq, dev,
505 usb_rcvintpipe(dev, endpoint->bEndpointAddress), 590 usb_rcvintpipe(dev, endpoint->bEndpointAddress),
506 wacom_wac->data, wacom_wac->features->pktlen, 591 wacom_wac->data, features->pktlen,
507 wacom_sys_irq, wacom, endpoint->bInterval); 592 wacom_sys_irq, wacom, endpoint->bInterval);
508 wacom->irq->transfer_dma = wacom->data_dma; 593 wacom->irq->transfer_dma = wacom->data_dma;
509 wacom->irq->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; 594 wacom->irq->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;
@@ -512,18 +597,14 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i
512 if (error) 597 if (error)
513 goto fail3; 598 goto fail3;
514 599
515 /* 600 /* Note that if query fails it is not a hard failure */
516 * Ask the tablet to report tablet data if it is not a Tablet PC. 601 wacom_query_tablet_data(intf, features);
517 * Note that if query fails it is not a hard failure.
518 */
519 if (wacom_wac->features->type != TABLETPC)
520 wacom_query_tablet_data(intf);
521 602
522 usb_set_intfdata(intf, wacom); 603 usb_set_intfdata(intf, wacom);
523 return 0; 604 return 0;
524 605
525 fail3: usb_free_urb(wacom->irq); 606 fail3: usb_free_urb(wacom->irq);
526 fail2: usb_buffer_free(dev, 10, wacom_wac->data, wacom->data_dma); 607 fail2: usb_buffer_free(dev, WACOM_PKGLEN_MAX, wacom_wac->data, wacom->data_dma);
527 fail1: input_free_device(input_dev); 608 fail1: input_free_device(input_dev);
528 kfree(wacom); 609 kfree(wacom);
529 kfree(wacom_wac); 610 kfree(wacom_wac);
@@ -539,7 +620,7 @@ static void wacom_disconnect(struct usb_interface *intf)
539 usb_kill_urb(wacom->irq); 620 usb_kill_urb(wacom->irq);
540 input_unregister_device(wacom->dev); 621 input_unregister_device(wacom->dev);
541 usb_free_urb(wacom->irq); 622 usb_free_urb(wacom->irq);
542 usb_buffer_free(interface_to_usbdev(intf), 10, 623 usb_buffer_free(interface_to_usbdev(intf), WACOM_PKGLEN_MAX,
543 wacom->wacom_wac->data, wacom->data_dma); 624 wacom->wacom_wac->data, wacom->data_dma);
544 kfree(wacom->wacom_wac); 625 kfree(wacom->wacom_wac);
545 kfree(wacom); 626 kfree(wacom);
@@ -559,12 +640,16 @@ static int wacom_suspend(struct usb_interface *intf, pm_message_t message)
559static int wacom_resume(struct usb_interface *intf) 640static int wacom_resume(struct usb_interface *intf)
560{ 641{
561 struct wacom *wacom = usb_get_intfdata(intf); 642 struct wacom *wacom = usb_get_intfdata(intf);
643 struct wacom_features *features = wacom->wacom_wac->features;
562 int rv; 644 int rv;
563 645
564 mutex_lock(&wacom->lock); 646 mutex_lock(&wacom->lock);
565 if (wacom->open) 647 if (wacom->open) {
566 rv = usb_submit_urb(wacom->irq, GFP_NOIO); 648 rv = usb_submit_urb(wacom->irq, GFP_NOIO);
567 else 649 /* switch to wacom mode if needed */
650 if (!wacom_retrieve_hid_descriptor(intf, features))
651 wacom_query_tablet_data(intf, features);
652 } else
568 rv = 0; 653 rv = 0;
569 mutex_unlock(&wacom->lock); 654 mutex_unlock(&wacom->lock);
570 655
diff --git a/drivers/input/tablet/wacom_wac.c b/drivers/input/tablet/wacom_wac.c
index c896d6a21b7e..1056f149fe31 100644
--- a/drivers/input/tablet/wacom_wac.c
+++ b/drivers/input/tablet/wacom_wac.c
@@ -1,7 +1,7 @@
1/* 1/*
2 * drivers/input/tablet/wacom_wac.c 2 * drivers/input/tablet/wacom_wac.c
3 * 3 *
4 * USB Wacom Graphire and Wacom Intuos tablet support - Wacom specific code 4 * USB Wacom tablet support - Wacom specific code
5 * 5 *
6 */ 6 */
7 7
@@ -58,16 +58,15 @@ static int wacom_pl_irq(struct wacom_wac *wacom, void *wcombo)
58 unsigned char *data = wacom->data; 58 unsigned char *data = wacom->data;
59 int prox, pressure; 59 int prox, pressure;
60 60
61 if (data[0] != 2) { 61 if (data[0] != WACOM_REPORT_PENABLED) {
62 dbg("wacom_pl_irq: received unknown report #%d", data[0]); 62 dbg("wacom_pl_irq: received unknown report #%d", data[0]);
63 return 0; 63 return 0;
64 } 64 }
65 65
66 prox = data[1] & 0x40; 66 prox = data[1] & 0x40;
67 67
68 wacom->id[0] = ERASER_DEVICE_ID;
69 if (prox) { 68 if (prox) {
70 69 wacom->id[0] = ERASER_DEVICE_ID;
71 pressure = (signed char)((data[7] << 1) | ((data[4] >> 2) & 1)); 70 pressure = (signed char)((data[7] << 1) | ((data[4] >> 2) & 1));
72 if (wacom->features->pressure_max > 255) 71 if (wacom->features->pressure_max > 255)
73 pressure = (pressure << 1) | ((data[4] >> 6) & 1); 72 pressure = (pressure << 1) | ((data[4] >> 6) & 1);
@@ -128,7 +127,7 @@ static int wacom_ptu_irq(struct wacom_wac *wacom, void *wcombo)
128{ 127{
129 unsigned char *data = wacom->data; 128 unsigned char *data = wacom->data;
130 129
131 if (data[0] != 2) { 130 if (data[0] != WACOM_REPORT_PENABLED) {
132 printk(KERN_INFO "wacom_ptu_irq: received unknown report #%d\n", data[0]); 131 printk(KERN_INFO "wacom_ptu_irq: received unknown report #%d\n", data[0]);
133 return 0; 132 return 0;
134 } 133 }
@@ -155,14 +154,16 @@ static int wacom_graphire_irq(struct wacom_wac *wacom, void *wcombo)
155{ 154{
156 unsigned char *data = wacom->data; 155 unsigned char *data = wacom->data;
157 int x, y, rw; 156 int x, y, rw;
157 static int penData = 0;
158 158
159 if (data[0] != 2) { 159 if (data[0] != WACOM_REPORT_PENABLED) {
160 dbg("wacom_graphire_irq: received unknown report #%d", data[0]); 160 dbg("wacom_graphire_irq: received unknown report #%d", data[0]);
161 return 0; 161 return 0;
162 } 162 }
163 163
164 if (data[1] & 0x80) { 164 if (data[1] & 0x80) {
165 /* in prox and not a pad data */ 165 /* in prox and not a pad data */
166 penData = 1;
166 167
167 switch ((data[1] >> 5) & 3) { 168 switch ((data[1] >> 5) & 3) {
168 169
@@ -232,7 +233,11 @@ static int wacom_graphire_irq(struct wacom_wac *wacom, void *wcombo)
232 switch (wacom->features->type) { 233 switch (wacom->features->type) {
233 case WACOM_G4: 234 case WACOM_G4:
234 if (data[7] & 0xf8) { 235 if (data[7] & 0xf8) {
235 wacom_input_sync(wcombo); /* sync last event */ 236 if (penData) {
237 wacom_input_sync(wcombo); /* sync last event */
238 if (!wacom->id[0])
239 penData = 0;
240 }
236 wacom->id[1] = PAD_DEVICE_ID; 241 wacom->id[1] = PAD_DEVICE_ID;
237 wacom_report_key(wcombo, BTN_0, (data[7] & 0x40)); 242 wacom_report_key(wcombo, BTN_0, (data[7] & 0x40));
238 wacom_report_key(wcombo, BTN_4, (data[7] & 0x80)); 243 wacom_report_key(wcombo, BTN_4, (data[7] & 0x80));
@@ -242,10 +247,15 @@ static int wacom_graphire_irq(struct wacom_wac *wacom, void *wcombo)
242 wacom_report_abs(wcombo, ABS_MISC, wacom->id[1]); 247 wacom_report_abs(wcombo, ABS_MISC, wacom->id[1]);
243 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0); 248 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0);
244 } else if (wacom->id[1]) { 249 } else if (wacom->id[1]) {
245 wacom_input_sync(wcombo); /* sync last event */ 250 if (penData) {
251 wacom_input_sync(wcombo); /* sync last event */
252 if (!wacom->id[0])
253 penData = 0;
254 }
246 wacom->id[1] = 0; 255 wacom->id[1] = 0;
247 wacom_report_key(wcombo, BTN_0, (data[7] & 0x40)); 256 wacom_report_key(wcombo, BTN_0, (data[7] & 0x40));
248 wacom_report_key(wcombo, BTN_4, (data[7] & 0x80)); 257 wacom_report_key(wcombo, BTN_4, (data[7] & 0x80));
258 wacom_report_rel(wcombo, REL_WHEEL, 0);
249 wacom_report_key(wcombo, BTN_TOOL_FINGER, 0); 259 wacom_report_key(wcombo, BTN_TOOL_FINGER, 0);
250 wacom_report_abs(wcombo, ABS_MISC, 0); 260 wacom_report_abs(wcombo, ABS_MISC, 0);
251 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0); 261 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0);
@@ -253,7 +263,11 @@ static int wacom_graphire_irq(struct wacom_wac *wacom, void *wcombo)
253 break; 263 break;
254 case WACOM_MO: 264 case WACOM_MO:
255 if ((data[7] & 0xf8) || (data[8] & 0xff)) { 265 if ((data[7] & 0xf8) || (data[8] & 0xff)) {
256 wacom_input_sync(wcombo); /* sync last event */ 266 if (penData) {
267 wacom_input_sync(wcombo); /* sync last event */
268 if (!wacom->id[0])
269 penData = 0;
270 }
257 wacom->id[1] = PAD_DEVICE_ID; 271 wacom->id[1] = PAD_DEVICE_ID;
258 wacom_report_key(wcombo, BTN_0, (data[7] & 0x08)); 272 wacom_report_key(wcombo, BTN_0, (data[7] & 0x08));
259 wacom_report_key(wcombo, BTN_1, (data[7] & 0x20)); 273 wacom_report_key(wcombo, BTN_1, (data[7] & 0x20));
@@ -264,7 +278,11 @@ static int wacom_graphire_irq(struct wacom_wac *wacom, void *wcombo)
264 wacom_report_abs(wcombo, ABS_MISC, wacom->id[1]); 278 wacom_report_abs(wcombo, ABS_MISC, wacom->id[1]);
265 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0); 279 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0);
266 } else if (wacom->id[1]) { 280 } else if (wacom->id[1]) {
267 wacom_input_sync(wcombo); /* sync last event */ 281 if (penData) {
282 wacom_input_sync(wcombo); /* sync last event */
283 if (!wacom->id[0])
284 penData = 0;
285 }
268 wacom->id[1] = 0; 286 wacom->id[1] = 0;
269 wacom_report_key(wcombo, BTN_0, (data[7] & 0x08)); 287 wacom_report_key(wcombo, BTN_0, (data[7] & 0x08));
270 wacom_report_key(wcombo, BTN_1, (data[7] & 0x20)); 288 wacom_report_key(wcombo, BTN_1, (data[7] & 0x20));
@@ -432,7 +450,8 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
432 unsigned int t; 450 unsigned int t;
433 int idx = 0, result; 451 int idx = 0, result;
434 452
435 if (data[0] != 2 && data[0] != 5 && data[0] != 6 && data[0] != 12) { 453 if (data[0] != WACOM_REPORT_PENABLED && data[0] != WACOM_REPORT_INTUOSREAD
454 && data[0] != WACOM_REPORT_INTUOSWRITE && data[0] != WACOM_REPORT_INTUOSPAD) {
436 dbg("wacom_intuos_irq: received unknown report #%d", data[0]); 455 dbg("wacom_intuos_irq: received unknown report #%d", data[0]);
437 return 0; 456 return 0;
438 } 457 }
@@ -442,7 +461,7 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
442 idx = data[1] & 0x01; 461 idx = data[1] & 0x01;
443 462
444 /* pad packets. Works as a second tool and is always in prox */ 463 /* pad packets. Works as a second tool and is always in prox */
445 if (data[0] == 12) { 464 if (data[0] == WACOM_REPORT_INTUOSPAD) {
446 /* initiate the pad as a device */ 465 /* initiate the pad as a device */
447 if (wacom->tool[1] != BTN_TOOL_FINGER) 466 if (wacom->tool[1] != BTN_TOOL_FINGER)
448 wacom->tool[1] = BTN_TOOL_FINGER; 467 wacom->tool[1] = BTN_TOOL_FINGER;
@@ -608,95 +627,163 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
608 return 1; 627 return 1;
609} 628}
610 629
630
631static void wacom_tpc_finger_in(struct wacom_wac *wacom, void *wcombo, char *data, int idx)
632{
633 wacom_report_abs(wcombo, ABS_X,
634 (data[2 + idx * 2] & 0xff) | ((data[3 + idx * 2] & 0x7f) << 8));
635 wacom_report_abs(wcombo, ABS_Y,
636 (data[6 + idx * 2] & 0xff) | ((data[7 + idx * 2] & 0x7f) << 8));
637 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]);
638 wacom_report_key(wcombo, wacom->tool[idx], 1);
639 if (idx)
640 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0);
641 else
642 wacom_report_key(wcombo, BTN_TOUCH, 1);
643}
644
645static void wacom_tpc_touch_out(struct wacom_wac *wacom, void *wcombo, int idx)
646{
647 wacom_report_abs(wcombo, ABS_X, 0);
648 wacom_report_abs(wcombo, ABS_Y, 0);
649 wacom_report_abs(wcombo, ABS_MISC, 0);
650 wacom_report_key(wcombo, wacom->tool[idx], 0);
651 if (idx)
652 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xf0);
653 else
654 wacom_report_key(wcombo, BTN_TOUCH, 0);
655 return;
656}
657
658static void wacom_tpc_touch_in(struct wacom_wac *wacom, void *wcombo)
659{
660 char *data = wacom->data;
661 struct urb *urb = ((struct wacom_combo *)wcombo)->urb;
662 static int firstFinger = 0;
663 static int secondFinger = 0;
664
665 wacom->tool[0] = BTN_TOOL_DOUBLETAP;
666 wacom->id[0] = TOUCH_DEVICE_ID;
667 wacom->tool[1] = BTN_TOOL_TRIPLETAP;
668
669 if (urb->actual_length != WACOM_PKGLEN_TPC1FG) {
670 switch (data[0]) {
671 case WACOM_REPORT_TPC1FG:
672 wacom_report_abs(wcombo, ABS_X, wacom_le16_to_cpu(&data[2]));
673 wacom_report_abs(wcombo, ABS_Y, wacom_le16_to_cpu(&data[4]));
674 wacom_report_abs(wcombo, ABS_PRESSURE, wacom_le16_to_cpu(&data[6]));
675 wacom_report_key(wcombo, BTN_TOUCH, wacom_le16_to_cpu(&data[6]));
676 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]);
677 wacom_report_key(wcombo, wacom->tool[0], 1);
678 break;
679 case WACOM_REPORT_TPC2FG:
680 /* keep this byte to send proper out-prox event */
681 wacom->id[1] = data[1] & 0x03;
682
683 if (data[1] & 0x01) {
684 wacom_tpc_finger_in(wacom, wcombo, data, 0);
685 firstFinger = 1;
686 } else if (firstFinger) {
687 wacom_tpc_touch_out(wacom, wcombo, 0);
688 }
689
690 if (data[1] & 0x02) {
691 /* sync first finger data */
692 if (firstFinger)
693 wacom_input_sync(wcombo);
694
695 wacom_tpc_finger_in(wacom, wcombo, data, 1);
696 secondFinger = 1;
697 } else if (secondFinger) {
698 /* sync first finger data */
699 if (firstFinger)
700 wacom_input_sync(wcombo);
701
702 wacom_tpc_touch_out(wacom, wcombo, 1);
703 secondFinger = 0;
704 }
705 if (!(data[1] & 0x01))
706 firstFinger = 0;
707 break;
708 }
709 } else {
710 wacom_report_abs(wcombo, ABS_X, wacom_le16_to_cpu(&data[1]));
711 wacom_report_abs(wcombo, ABS_Y, wacom_le16_to_cpu(&data[3]));
712 wacom_report_key(wcombo, BTN_TOUCH, 1);
713 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]);
714 wacom_report_key(wcombo, wacom->tool[0], 1);
715 }
716 return;
717}
718
611static int wacom_tpc_irq(struct wacom_wac *wacom, void *wcombo) 719static int wacom_tpc_irq(struct wacom_wac *wacom, void *wcombo)
612{ 720{
613 char *data = wacom->data; 721 char *data = wacom->data;
614 int prox = 0, pressure; 722 int prox = 0, pressure, idx = -1;
615 static int stylusInProx, touchInProx = 1, touchOut; 723 static int stylusInProx, touchInProx = 1, touchOut;
616 struct urb *urb = ((struct wacom_combo *)wcombo)->urb; 724 struct urb *urb = ((struct wacom_combo *)wcombo)->urb;
617 725
618 dbg("wacom_tpc_irq: received report #%d", data[0]); 726 dbg("wacom_tpc_irq: received report #%d", data[0]);
619 727
620 if (urb->actual_length == 5 || data[0] == 6) { /* Touch data */ 728 if (urb->actual_length == WACOM_PKGLEN_TPC1FG || /* single touch */
621 if (urb->actual_length == 5) { /* with touch */ 729 data[0] == WACOM_REPORT_TPC1FG || /* single touch */
622 prox = data[0] & 0x03; 730 data[0] == WACOM_REPORT_TPC2FG) { /* 2FG touch */
731 if (urb->actual_length == WACOM_PKGLEN_TPC1FG) { /* with touch */
732 prox = data[0] & 0x01;
623 } else { /* with capacity */ 733 } else { /* with capacity */
624 prox = data[1] & 0x03; 734 if (data[0] == WACOM_REPORT_TPC1FG)
735 /* single touch */
736 prox = data[1] & 0x01;
737 else
738 /* 2FG touch data */
739 prox = data[1] & 0x03;
625 } 740 }
626 741
627 if (!stylusInProx) { /* stylus not in prox */ 742 if (!stylusInProx) { /* stylus not in prox */
628 if (prox) { 743 if (prox) {
629 if (touchInProx) { 744 if (touchInProx) {
630 wacom->tool[1] = BTN_TOOL_DOUBLETAP; 745 wacom_tpc_touch_in(wacom, wcombo);
631 wacom->id[0] = TOUCH_DEVICE_ID;
632 if (urb->actual_length != 5) {
633 wacom_report_abs(wcombo, ABS_X, wacom_le16_to_cpu(&data[2]));
634 wacom_report_abs(wcombo, ABS_Y, wacom_le16_to_cpu(&data[4]));
635 wacom_report_abs(wcombo, ABS_PRESSURE, wacom_le16_to_cpu(&data[6]));
636 wacom_report_key(wcombo, BTN_TOUCH, wacom_le16_to_cpu(&data[6]));
637 } else {
638 wacom_report_abs(wcombo, ABS_X, wacom_le16_to_cpu(&data[1]));
639 wacom_report_abs(wcombo, ABS_Y, wacom_le16_to_cpu(&data[3]));
640 wacom_report_key(wcombo, BTN_TOUCH, 1);
641 }
642 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]);
643 wacom_report_key(wcombo, wacom->tool[1], prox & 0x01);
644 touchOut = 1; 746 touchOut = 1;
645 return 1; 747 return 1;
646 } 748 }
647 } else { 749 } else {
648 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]); 750 /* 2FGT out-prox */
649 wacom_report_key(wcombo, wacom->tool[1], prox & 0x01); 751 if (data[0] == WACOM_REPORT_TPC2FG) {
650 wacom_report_key(wcombo, BTN_TOUCH, 0); 752 idx = (wacom->id[1] & 0x01) - 1;
753 if (idx == 0) {
754 wacom_tpc_touch_out(wacom, wcombo, idx);
755 /* sync first finger event */
756 if (wacom->id[1] & 0x02)
757 wacom_input_sync(wcombo);
758 }
759 idx = (wacom->id[1] & 0x02) - 1;
760 if (idx == 1)
761 wacom_tpc_touch_out(wacom, wcombo, idx);
762 } else /* one finger touch */
763 wacom_tpc_touch_out(wacom, wcombo, 0);
651 touchOut = 0; 764 touchOut = 0;
652 touchInProx = 1; 765 touchInProx = 1;
653 return 1; 766 return 1;
654 } 767 }
655 } else if (touchOut || !prox) { /* force touch out-prox */ 768 } else if (touchOut || !prox) { /* force touch out-prox */
656 wacom_report_abs(wcombo, ABS_MISC, TOUCH_DEVICE_ID); 769 wacom_tpc_touch_out(wacom, wcombo, 0);
657 wacom_report_key(wcombo, wacom->tool[1], 0);
658 wacom_report_key(wcombo, BTN_TOUCH, 0);
659 touchOut = 0; 770 touchOut = 0;
660 touchInProx = 1; 771 touchInProx = 1;
661 return 1; 772 return 1;
662 } 773 }
663 } else if (data[0] == 2) { /* Penabled */ 774 } else if (data[0] == WACOM_REPORT_PENABLED) { /* Penabled */
664 prox = data[1] & 0x20; 775 prox = data[1] & 0x20;
665 776
666 touchInProx = 0; 777 touchInProx = 0;
667 778
668 wacom->id[0] = ERASER_DEVICE_ID;
669
670 /*
671 * if going from out of proximity into proximity select between the eraser
672 * and the pen based on the state of the stylus2 button, choose eraser if
673 * pressed else choose pen. if not a proximity change from out to in, send
674 * an out of proximity for previous tool then a in for new tool.
675 */
676 if (prox) { /* in prox */ 779 if (prox) { /* in prox */
677 if (!wacom->tool[0]) { 780 if (!wacom->id[0]) {
678 /* Going into proximity select tool */ 781 /* Going into proximity select tool */
679 wacom->tool[1] = (data[1] & 0x08) ? BTN_TOOL_RUBBER : BTN_TOOL_PEN; 782 wacom->tool[0] = (data[1] & 0x0c) ? BTN_TOOL_RUBBER : BTN_TOOL_PEN;
680 if (wacom->tool[1] == BTN_TOOL_PEN) 783 if (wacom->tool[0] == BTN_TOOL_PEN)
681 wacom->id[0] = STYLUS_DEVICE_ID; 784 wacom->id[0] = STYLUS_DEVICE_ID;
682 } else if (wacom->tool[1] == BTN_TOOL_RUBBER && !(data[1] & 0x08)) { 785 else
683 /* 786 wacom->id[0] = ERASER_DEVICE_ID;
684 * was entered with stylus2 pressed
685 * report out proximity for previous tool
686 */
687 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]);
688 wacom_report_key(wcombo, wacom->tool[1], 0);
689 wacom_input_sync(wcombo);
690
691 /* set new tool */
692 wacom->tool[1] = BTN_TOOL_PEN;
693 wacom->id[0] = STYLUS_DEVICE_ID;
694 return 0;
695 }
696 if (wacom->tool[1] != BTN_TOOL_RUBBER) {
697 /* Unknown tool selected default to pen tool */
698 wacom->tool[1] = BTN_TOOL_PEN;
699 wacom->id[0] = STYLUS_DEVICE_ID;
700 } 787 }
701 wacom_report_key(wcombo, BTN_STYLUS, data[1] & 0x02); 788 wacom_report_key(wcombo, BTN_STYLUS, data[1] & 0x02);
702 wacom_report_key(wcombo, BTN_STYLUS2, data[1] & 0x10); 789 wacom_report_key(wcombo, BTN_STYLUS2, data[1] & 0x10);
@@ -706,17 +793,21 @@ static int wacom_tpc_irq(struct wacom_wac *wacom, void *wcombo)
706 if (pressure < 0) 793 if (pressure < 0)
707 pressure = wacom->features->pressure_max + pressure + 1; 794 pressure = wacom->features->pressure_max + pressure + 1;
708 wacom_report_abs(wcombo, ABS_PRESSURE, pressure); 795 wacom_report_abs(wcombo, ABS_PRESSURE, pressure);
709 wacom_report_key(wcombo, BTN_TOUCH, pressure); 796 wacom_report_key(wcombo, BTN_TOUCH, data[1] & 0x05);
710 } else { 797 } else {
798 wacom_report_abs(wcombo, ABS_X, 0);
799 wacom_report_abs(wcombo, ABS_Y, 0);
711 wacom_report_abs(wcombo, ABS_PRESSURE, 0); 800 wacom_report_abs(wcombo, ABS_PRESSURE, 0);
712 wacom_report_key(wcombo, BTN_STYLUS, 0); 801 wacom_report_key(wcombo, BTN_STYLUS, 0);
713 wacom_report_key(wcombo, BTN_STYLUS2, 0); 802 wacom_report_key(wcombo, BTN_STYLUS2, 0);
714 wacom_report_key(wcombo, BTN_TOUCH, 0); 803 wacom_report_key(wcombo, BTN_TOUCH, 0);
804 wacom->id[0] = 0;
805 /* pen is out so touch can be enabled now */
806 touchInProx = 1;
715 } 807 }
716 wacom_report_key(wcombo, wacom->tool[1], prox); 808 wacom_report_key(wcombo, wacom->tool[0], prox);
717 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]); 809 wacom_report_abs(wcombo, ABS_MISC, wacom->id[0]);
718 stylusInProx = prox; 810 stylusInProx = prox;
719 wacom->tool[0] = prox;
720 return 1; 811 return 1;
721 } 812 }
722 return 0; 813 return 0;
@@ -751,6 +842,7 @@ int wacom_wac_irq(struct wacom_wac *wacom_wac, void *wcombo)
751 return wacom_intuos_irq(wacom_wac, wcombo); 842 return wacom_intuos_irq(wacom_wac, wcombo);
752 843
753 case TABLETPC: 844 case TABLETPC:
845 case TABLETPC2FG:
754 return wacom_tpc_irq(wacom_wac, wcombo); 846 return wacom_tpc_irq(wacom_wac, wcombo);
755 847
756 default: 848 default:
@@ -791,9 +883,17 @@ void wacom_init_input_dev(struct input_dev *input_dev, struct wacom_wac *wacom_w
791 input_dev_i4s(input_dev, wacom_wac); 883 input_dev_i4s(input_dev, wacom_wac);
792 input_dev_i(input_dev, wacom_wac); 884 input_dev_i(input_dev, wacom_wac);
793 break; 885 break;
886 case TABLETPC2FG:
887 input_dev_tpc2fg(input_dev, wacom_wac);
888 /* fall through */
889 case TABLETPC:
890 input_dev_tpc(input_dev, wacom_wac);
891 if (wacom_wac->features->device_type != BTN_TOOL_PEN)
892 break; /* no need to process stylus stuff */
893
894 /* fall through */
794 case PL: 895 case PL:
795 case PTU: 896 case PTU:
796 case TABLETPC:
797 input_dev_pl(input_dev, wacom_wac); 897 input_dev_pl(input_dev, wacom_wac);
798 /* fall through */ 898 /* fall through */
799 case PENPARTNER: 899 case PENPARTNER:
@@ -804,66 +904,69 @@ void wacom_init_input_dev(struct input_dev *input_dev, struct wacom_wac *wacom_w
804} 904}
805 905
806static struct wacom_features wacom_features[] = { 906static struct wacom_features wacom_features[] = {
807 { "Wacom Penpartner", 7, 5040, 3780, 255, 0, PENPARTNER }, 907 { "Wacom Penpartner", WACOM_PKGLEN_PENPRTN, 5040, 3780, 255, 0, PENPARTNER },
808 { "Wacom Graphire", 8, 10206, 7422, 511, 63, GRAPHIRE }, 908 { "Wacom Graphire", WACOM_PKGLEN_GRAPHIRE, 10206, 7422, 511, 63, GRAPHIRE },
809 { "Wacom Graphire2 4x5", 8, 10206, 7422, 511, 63, GRAPHIRE }, 909 { "Wacom Graphire2 4x5", WACOM_PKGLEN_GRAPHIRE, 10206, 7422, 511, 63, GRAPHIRE },
810 { "Wacom Graphire2 5x7", 8, 13918, 10206, 511, 63, GRAPHIRE }, 910 { "Wacom Graphire2 5x7", WACOM_PKGLEN_GRAPHIRE, 13918, 10206, 511, 63, GRAPHIRE },
811 { "Wacom Graphire3", 8, 10208, 7424, 511, 63, GRAPHIRE }, 911 { "Wacom Graphire3", WACOM_PKGLEN_GRAPHIRE, 10208, 7424, 511, 63, GRAPHIRE },
812 { "Wacom Graphire3 6x8", 8, 16704, 12064, 511, 63, GRAPHIRE }, 912 { "Wacom Graphire3 6x8", WACOM_PKGLEN_GRAPHIRE, 16704, 12064, 511, 63, GRAPHIRE },
813 { "Wacom Graphire4 4x5", 8, 10208, 7424, 511, 63, WACOM_G4 }, 913 { "Wacom Graphire4 4x5", WACOM_PKGLEN_GRAPHIRE, 10208, 7424, 511, 63, WACOM_G4 },
814 { "Wacom Graphire4 6x8", 8, 16704, 12064, 511, 63, WACOM_G4 }, 914 { "Wacom Graphire4 6x8", WACOM_PKGLEN_GRAPHIRE, 16704, 12064, 511, 63, WACOM_G4 },
815 { "Wacom BambooFun 4x5", 9, 14760, 9225, 511, 63, WACOM_MO }, 915 { "Wacom BambooFun 4x5", WACOM_PKGLEN_BBFUN, 14760, 9225, 511, 63, WACOM_MO },
816 { "Wacom BambooFun 6x8", 9, 21648, 13530, 511, 63, WACOM_MO }, 916 { "Wacom BambooFun 6x8", WACOM_PKGLEN_BBFUN, 21648, 13530, 511, 63, WACOM_MO },
817 { "Wacom Bamboo1 Medium",8, 16704, 12064, 511, 63, GRAPHIRE }, 917 { "Wacom Bamboo1 Medium", WACOM_PKGLEN_GRAPHIRE, 16704, 12064, 511, 63, GRAPHIRE },
818 { "Wacom Volito", 8, 5104, 3712, 511, 63, GRAPHIRE }, 918 { "Wacom Volito", WACOM_PKGLEN_GRAPHIRE, 5104, 3712, 511, 63, GRAPHIRE },
819 { "Wacom PenStation2", 8, 3250, 2320, 255, 63, GRAPHIRE }, 919 { "Wacom PenStation2", WACOM_PKGLEN_GRAPHIRE, 3250, 2320, 255, 63, GRAPHIRE },
820 { "Wacom Volito2 4x5", 8, 5104, 3712, 511, 63, GRAPHIRE }, 920 { "Wacom Volito2 4x5", WACOM_PKGLEN_GRAPHIRE, 5104, 3712, 511, 63, GRAPHIRE },
821 { "Wacom Volito2 2x3", 8, 3248, 2320, 511, 63, GRAPHIRE }, 921 { "Wacom Volito2 2x3", WACOM_PKGLEN_GRAPHIRE, 3248, 2320, 511, 63, GRAPHIRE },
822 { "Wacom PenPartner2", 8, 3250, 2320, 511, 63, GRAPHIRE }, 922 { "Wacom PenPartner2", WACOM_PKGLEN_GRAPHIRE, 3250, 2320, 511, 63, GRAPHIRE },
823 { "Wacom Bamboo", 9, 14760, 9225, 511, 63, WACOM_MO }, 923 { "Wacom Bamboo", WACOM_PKGLEN_BBFUN, 14760, 9225, 511, 63, WACOM_MO },
824 { "Wacom Bamboo1", 8, 5104, 3712, 511, 63, GRAPHIRE }, 924 { "Wacom Bamboo1", WACOM_PKGLEN_GRAPHIRE, 5104, 3712, 511, 63, GRAPHIRE },
825 { "Wacom Intuos 4x5", 10, 12700, 10600, 1023, 31, INTUOS }, 925 { "Wacom Intuos 4x5", WACOM_PKGLEN_INTUOS, 12700, 10600, 1023, 31, INTUOS },
826 { "Wacom Intuos 6x8", 10, 20320, 16240, 1023, 31, INTUOS }, 926 { "Wacom Intuos 6x8", WACOM_PKGLEN_INTUOS, 20320, 16240, 1023, 31, INTUOS },
827 { "Wacom Intuos 9x12", 10, 30480, 24060, 1023, 31, INTUOS }, 927 { "Wacom Intuos 9x12", WACOM_PKGLEN_INTUOS, 30480, 24060, 1023, 31, INTUOS },
828 { "Wacom Intuos 12x12", 10, 30480, 31680, 1023, 31, INTUOS }, 928 { "Wacom Intuos 12x12", WACOM_PKGLEN_INTUOS, 30480, 31680, 1023, 31, INTUOS },
829 { "Wacom Intuos 12x18", 10, 45720, 31680, 1023, 31, INTUOS }, 929 { "Wacom Intuos 12x18", WACOM_PKGLEN_INTUOS, 45720, 31680, 1023, 31, INTUOS },
830 { "Wacom PL400", 8, 5408, 4056, 255, 0, PL }, 930 { "Wacom PL400", WACOM_PKGLEN_GRAPHIRE, 5408, 4056, 255, 0, PL },
831 { "Wacom PL500", 8, 6144, 4608, 255, 0, PL }, 931 { "Wacom PL500", WACOM_PKGLEN_GRAPHIRE, 6144, 4608, 255, 0, PL },
832 { "Wacom PL600", 8, 6126, 4604, 255, 0, PL }, 932 { "Wacom PL600", WACOM_PKGLEN_GRAPHIRE, 6126, 4604, 255, 0, PL },
833 { "Wacom PL600SX", 8, 6260, 5016, 255, 0, PL }, 933 { "Wacom PL600SX", WACOM_PKGLEN_GRAPHIRE, 6260, 5016, 255, 0, PL },
834 { "Wacom PL550", 8, 6144, 4608, 511, 0, PL }, 934 { "Wacom PL550", WACOM_PKGLEN_GRAPHIRE, 6144, 4608, 511, 0, PL },
835 { "Wacom PL800", 8, 7220, 5780, 511, 0, PL }, 935 { "Wacom PL800", WACOM_PKGLEN_GRAPHIRE, 7220, 5780, 511, 0, PL },
836 { "Wacom PL700", 8, 6758, 5406, 511, 0, PL }, 936 { "Wacom PL700", WACOM_PKGLEN_GRAPHIRE, 6758, 5406, 511, 0, PL },
837 { "Wacom PL510", 8, 6282, 4762, 511, 0, PL }, 937 { "Wacom PL510", WACOM_PKGLEN_GRAPHIRE, 6282, 4762, 511, 0, PL },
838 { "Wacom DTU710", 8, 34080, 27660, 511, 0, PL }, 938 { "Wacom DTU710", WACOM_PKGLEN_GRAPHIRE, 34080, 27660, 511, 0, PL },
839 { "Wacom DTF521", 8, 6282, 4762, 511, 0, PL }, 939 { "Wacom DTF521", WACOM_PKGLEN_GRAPHIRE, 6282, 4762, 511, 0, PL },
840 { "Wacom DTF720", 8, 6858, 5506, 511, 0, PL }, 940 { "Wacom DTF720", WACOM_PKGLEN_GRAPHIRE, 6858, 5506, 511, 0, PL },
841 { "Wacom DTF720a", 8, 6858, 5506, 511, 0, PL }, 941 { "Wacom DTF720a", WACOM_PKGLEN_GRAPHIRE, 6858, 5506, 511, 0, PL },
842 { "Wacom Cintiq Partner",8, 20480, 15360, 511, 0, PTU }, 942 { "Wacom Cintiq Partner", WACOM_PKGLEN_GRAPHIRE, 20480, 15360, 511, 0, PTU },
843 { "Wacom Intuos2 4x5", 10, 12700, 10600, 1023, 31, INTUOS }, 943 { "Wacom Intuos2 4x5", WACOM_PKGLEN_INTUOS, 12700, 10600, 1023, 31, INTUOS },
844 { "Wacom Intuos2 6x8", 10, 20320, 16240, 1023, 31, INTUOS }, 944 { "Wacom Intuos2 6x8", WACOM_PKGLEN_INTUOS, 20320, 16240, 1023, 31, INTUOS },
845 { "Wacom Intuos2 9x12", 10, 30480, 24060, 1023, 31, INTUOS }, 945 { "Wacom Intuos2 9x12", WACOM_PKGLEN_INTUOS, 30480, 24060, 1023, 31, INTUOS },
846 { "Wacom Intuos2 12x12", 10, 30480, 31680, 1023, 31, INTUOS }, 946 { "Wacom Intuos2 12x12", WACOM_PKGLEN_INTUOS, 30480, 31680, 1023, 31, INTUOS },
847 { "Wacom Intuos2 12x18", 10, 45720, 31680, 1023, 31, INTUOS }, 947 { "Wacom Intuos2 12x18", WACOM_PKGLEN_INTUOS, 45720, 31680, 1023, 31, INTUOS },
848 { "Wacom Intuos3 4x5", 10, 25400, 20320, 1023, 63, INTUOS3S }, 948 { "Wacom Intuos3 4x5", WACOM_PKGLEN_INTUOS, 25400, 20320, 1023, 63, INTUOS3S },
849 { "Wacom Intuos3 6x8", 10, 40640, 30480, 1023, 63, INTUOS3 }, 949 { "Wacom Intuos3 6x8", WACOM_PKGLEN_INTUOS, 40640, 30480, 1023, 63, INTUOS3 },
850 { "Wacom Intuos3 9x12", 10, 60960, 45720, 1023, 63, INTUOS3 }, 950 { "Wacom Intuos3 9x12", WACOM_PKGLEN_INTUOS, 60960, 45720, 1023, 63, INTUOS3 },
851 { "Wacom Intuos3 12x12", 10, 60960, 60960, 1023, 63, INTUOS3L }, 951 { "Wacom Intuos3 12x12", WACOM_PKGLEN_INTUOS, 60960, 60960, 1023, 63, INTUOS3L },
852 { "Wacom Intuos3 12x19", 10, 97536, 60960, 1023, 63, INTUOS3L }, 952 { "Wacom Intuos3 12x19", WACOM_PKGLEN_INTUOS, 97536, 60960, 1023, 63, INTUOS3L },
853 { "Wacom Intuos3 6x11", 10, 54204, 31750, 1023, 63, INTUOS3 }, 953 { "Wacom Intuos3 6x11", WACOM_PKGLEN_INTUOS, 54204, 31750, 1023, 63, INTUOS3 },
854 { "Wacom Intuos3 4x6", 10, 31496, 19685, 1023, 63, INTUOS3S }, 954 { "Wacom Intuos3 4x6", WACOM_PKGLEN_INTUOS, 31496, 19685, 1023, 63, INTUOS3S },
855 { "Wacom Intuos4 4x6", 10, 31496, 19685, 2047, 63, INTUOS4S }, 955 { "Wacom Intuos4 4x6", WACOM_PKGLEN_INTUOS, 31496, 19685, 2047, 63, INTUOS4S },
856 { "Wacom Intuos4 6x9", 10, 44704, 27940, 2047, 63, INTUOS4 }, 956 { "Wacom Intuos4 6x9", WACOM_PKGLEN_INTUOS, 44704, 27940, 2047, 63, INTUOS4 },
857 { "Wacom Intuos4 8x13", 10, 65024, 40640, 2047, 63, INTUOS4L }, 957 { "Wacom Intuos4 8x13", WACOM_PKGLEN_INTUOS, 65024, 40640, 2047, 63, INTUOS4L },
858 { "Wacom Intuos4 12x19", 10, 97536, 60960, 2047, 63, INTUOS4L }, 958 { "Wacom Intuos4 12x19", WACOM_PKGLEN_INTUOS, 97536, 60960, 2047, 63, INTUOS4L },
859 { "Wacom Cintiq 21UX", 10, 87200, 65600, 1023, 63, CINTIQ }, 959 { "Wacom Cintiq 21UX", WACOM_PKGLEN_INTUOS, 87200, 65600, 1023, 63, CINTIQ },
860 { "Wacom Cintiq 20WSX", 10, 86680, 54180, 1023, 63, WACOM_BEE }, 960 { "Wacom Cintiq 20WSX", WACOM_PKGLEN_INTUOS, 86680, 54180, 1023, 63, WACOM_BEE },
861 { "Wacom Cintiq 12WX", 10, 53020, 33440, 1023, 63, WACOM_BEE }, 961 { "Wacom Cintiq 12WX", WACOM_PKGLEN_INTUOS, 53020, 33440, 1023, 63, WACOM_BEE },
862 { "Wacom DTU1931", 8, 37832, 30305, 511, 0, PL }, 962 { "Wacom DTU1931", WACOM_PKGLEN_GRAPHIRE, 37832, 30305, 511, 0, PL },
863 { "Wacom ISDv4 90", 8, 26202, 16325, 255, 0, TABLETPC }, 963 { "Wacom ISDv4 90", WACOM_PKGLEN_GRAPHIRE, 26202, 16325, 255, 0, TABLETPC },
864 { "Wacom ISDv4 93", 8, 26202, 16325, 255, 0, TABLETPC }, 964 { "Wacom ISDv4 93", WACOM_PKGLEN_GRAPHIRE, 26202, 16325, 255, 0, TABLETPC },
865 { "Wacom ISDv4 9A", 8, 26202, 16325, 255, 0, TABLETPC }, 965 { "Wacom ISDv4 9A", WACOM_PKGLEN_GRAPHIRE, 26202, 16325, 255, 0, TABLETPC },
866 { "Wacom Intuos2 6x8", 10, 20320, 16240, 1023, 31, INTUOS }, 966 { "Wacom ISDv4 9F", WACOM_PKGLEN_PENABLED, 26202, 16325, 255, 0, TABLETPC },
967 { "Wacom ISDv4 E2", WACOM_PKGLEN_TPC2FG, 26202, 16325, 255, 0, TABLETPC2FG },
968 { "Wacom ISDv4 E3", WACOM_PKGLEN_TPC2FG, 26202, 16325, 255, 0, TABLETPC2FG },
969 { "Wacom Intuos2 6x8", WACOM_PKGLEN_INTUOS, 20320, 16240, 1023, 31, INTUOS },
867 { } 970 { }
868}; 971};
869 972
@@ -927,6 +1030,9 @@ static struct usb_device_id wacom_ids[] = {
927 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x90) }, 1030 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x90) },
928 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x93) }, 1031 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x93) },
929 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x9A) }, 1032 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x9A) },
1033 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x9F) },
1034 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xE2) },
1035 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xE3) },
930 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x47) }, 1036 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x47) },
931 { } 1037 { }
932}; 1038};
diff --git a/drivers/input/tablet/wacom_wac.h b/drivers/input/tablet/wacom_wac.h
index c10235aba7e5..ee01e1902785 100644
--- a/drivers/input/tablet/wacom_wac.h
+++ b/drivers/input/tablet/wacom_wac.h
@@ -9,12 +9,33 @@
9#ifndef WACOM_WAC_H 9#ifndef WACOM_WAC_H
10#define WACOM_WAC_H 10#define WACOM_WAC_H
11 11
12/* maximum packet length for USB devices */
13#define WACOM_PKGLEN_MAX 32
14
15/* packet length for individual models */
16#define WACOM_PKGLEN_PENPRTN 7
17#define WACOM_PKGLEN_GRAPHIRE 8
18#define WACOM_PKGLEN_BBFUN 9
19#define WACOM_PKGLEN_INTUOS 10
20#define WACOM_PKGLEN_PENABLED 8
21#define WACOM_PKGLEN_TPC1FG 5
22#define WACOM_PKGLEN_TPC2FG 14
23
24/* device IDs */
12#define STYLUS_DEVICE_ID 0x02 25#define STYLUS_DEVICE_ID 0x02
13#define TOUCH_DEVICE_ID 0x03 26#define TOUCH_DEVICE_ID 0x03
14#define CURSOR_DEVICE_ID 0x06 27#define CURSOR_DEVICE_ID 0x06
15#define ERASER_DEVICE_ID 0x0A 28#define ERASER_DEVICE_ID 0x0A
16#define PAD_DEVICE_ID 0x0F 29#define PAD_DEVICE_ID 0x0F
17 30
31/* wacom data packet report IDs */
32#define WACOM_REPORT_PENABLED 2
33#define WACOM_REPORT_INTUOSREAD 5
34#define WACOM_REPORT_INTUOSWRITE 6
35#define WACOM_REPORT_INTUOSPAD 12
36#define WACOM_REPORT_TPC1FG 6
37#define WACOM_REPORT_TPC2FG 13
38
18enum { 39enum {
19 PENPARTNER = 0, 40 PENPARTNER = 0,
20 GRAPHIRE, 41 GRAPHIRE,
@@ -32,6 +53,7 @@ enum {
32 WACOM_BEE, 53 WACOM_BEE,
33 WACOM_MO, 54 WACOM_MO,
34 TABLETPC, 55 TABLETPC,
56 TABLETPC2FG,
35 MAX_TYPE 57 MAX_TYPE
36}; 58};
37 59
@@ -43,8 +65,11 @@ struct wacom_features {
43 int pressure_max; 65 int pressure_max;
44 int distance_max; 66 int distance_max;
45 int type; 67 int type;
46 int touch_x_max; 68 int device_type;
47 int touch_y_max; 69 int x_phy;
70 int y_phy;
71 unsigned char unit;
72 unsigned char unitExpo;
48}; 73};
49 74
50struct wacom_wac { 75struct wacom_wac {
diff --git a/drivers/input/touchscreen/Kconfig b/drivers/input/touchscreen/Kconfig
index 32fc8ba039aa..dfafc76da4fb 100644
--- a/drivers/input/touchscreen/Kconfig
+++ b/drivers/input/touchscreen/Kconfig
@@ -450,6 +450,18 @@ config TOUCHSCREEN_USB_COMPOSITE
450 To compile this driver as a module, choose M here: the 450 To compile this driver as a module, choose M here: the
451 module will be called usbtouchscreen. 451 module will be called usbtouchscreen.
452 452
453config TOUCHSCREEN_MC13783
454 tristate "Freescale MC13783 touchscreen input driver"
455 depends on MFD_MC13783
456 help
457 Say Y here if you have an Freescale MC13783 PMIC on your
458 board and want to use its touchscreen
459
460 If unsure, say N.
461
462 To compile this driver as a module, choose M here: the
463 module will be called mc13783_ts.
464
453config TOUCHSCREEN_USB_EGALAX 465config TOUCHSCREEN_USB_EGALAX
454 default y 466 default y
455 bool "eGalax, eTurboTouch CT-410/510/700 device support" if EMBEDDED 467 bool "eGalax, eTurboTouch CT-410/510/700 device support" if EMBEDDED
diff --git a/drivers/input/touchscreen/Makefile b/drivers/input/touchscreen/Makefile
index f1f59c9e1211..d61a3b4def9a 100644
--- a/drivers/input/touchscreen/Makefile
+++ b/drivers/input/touchscreen/Makefile
@@ -18,6 +18,7 @@ obj-$(CONFIG_TOUCHSCREEN_EETI) += eeti_ts.o
18obj-$(CONFIG_TOUCHSCREEN_ELO) += elo.o 18obj-$(CONFIG_TOUCHSCREEN_ELO) += elo.o
19obj-$(CONFIG_TOUCHSCREEN_FUJITSU) += fujitsu_ts.o 19obj-$(CONFIG_TOUCHSCREEN_FUJITSU) += fujitsu_ts.o
20obj-$(CONFIG_TOUCHSCREEN_INEXIO) += inexio.o 20obj-$(CONFIG_TOUCHSCREEN_INEXIO) += inexio.o
21obj-$(CONFIG_TOUCHSCREEN_MC13783) += mc13783_ts.o
21obj-$(CONFIG_TOUCHSCREEN_MCS5000) += mcs5000_ts.o 22obj-$(CONFIG_TOUCHSCREEN_MCS5000) += mcs5000_ts.o
22obj-$(CONFIG_TOUCHSCREEN_MIGOR) += migor_ts.o 23obj-$(CONFIG_TOUCHSCREEN_MIGOR) += migor_ts.o
23obj-$(CONFIG_TOUCHSCREEN_MTOUCH) += mtouch.o 24obj-$(CONFIG_TOUCHSCREEN_MTOUCH) += mtouch.o
diff --git a/drivers/input/touchscreen/mc13783_ts.c b/drivers/input/touchscreen/mc13783_ts.c
new file mode 100644
index 000000000000..be115b3b65eb
--- /dev/null
+++ b/drivers/input/touchscreen/mc13783_ts.c
@@ -0,0 +1,258 @@
1/*
2 * Driver for the Freescale Semiconductor MC13783 touchscreen.
3 *
4 * Copyright 2004-2007 Freescale Semiconductor, Inc. All Rights Reserved.
5 * Copyright (C) 2009 Sascha Hauer, Pengutronix
6 *
7 * Initial development of this code was funded by
8 * Phytec Messtechnik GmbH, http://www.phytec.de/
9 *
10 * This program is free software; you can redistribute it and/or modify it
11 * under the terms of the GNU General Public License version 2 as published by
12 * the Free Software Foundation.
13 */
14#include <linux/platform_device.h>
15#include <linux/mfd/mc13783.h>
16#include <linux/kernel.h>
17#include <linux/module.h>
18#include <linux/input.h>
19#include <linux/sched.h>
20#include <linux/init.h>
21
22#define MC13783_TS_NAME "mc13783-ts"
23
24#define DEFAULT_SAMPLE_TOLERANCE 300
25
26static unsigned int sample_tolerance = DEFAULT_SAMPLE_TOLERANCE;
27module_param(sample_tolerance, uint, S_IRUGO | S_IWUSR);
28MODULE_PARM_DESC(sample_tolerance,
29 "If the minimal and maximal value read out for one axis (out "
30 "of three) differ by this value (default: "
31 __stringify(DEFAULT_SAMPLE_TOLERANCE) ") or more, the reading "
32 "is supposed to be wrong and is discarded. Set to 0 to "
33 "disable this check.");
34
35struct mc13783_ts_priv {
36 struct input_dev *idev;
37 struct mc13783 *mc13783;
38 struct delayed_work work;
39 struct workqueue_struct *workq;
40 unsigned int sample[4];
41};
42
43static irqreturn_t mc13783_ts_handler(int irq, void *data)
44{
45 struct mc13783_ts_priv *priv = data;
46
47 mc13783_ackirq(priv->mc13783, irq);
48
49 /*
50 * Kick off reading coordinates. Note that if work happens already
51 * be queued for future execution (it rearms itself) it will not
52 * be rescheduled for immediate execution here. However the rearm
53 * delay is HZ / 50 which is acceptable.
54 */
55 queue_delayed_work(priv->workq, &priv->work, 0);
56
57 return IRQ_HANDLED;
58}
59
60#define sort3(a0, a1, a2) ({ \
61 if (a0 > a1) \
62 swap(a0, a1); \
63 if (a1 > a2) \
64 swap(a1, a2); \
65 if (a0 > a1) \
66 swap(a0, a1); \
67 })
68
69static void mc13783_ts_report_sample(struct mc13783_ts_priv *priv)
70{
71 struct input_dev *idev = priv->idev;
72 int x0, x1, x2, y0, y1, y2;
73 int cr0, cr1;
74
75 /*
76 * the values are 10-bit wide only, but the two least significant
77 * bits are for future 12 bit use and reading yields 0
78 */
79 x0 = priv->sample[0] & 0xfff;
80 x1 = priv->sample[1] & 0xfff;
81 x2 = priv->sample[2] & 0xfff;
82 y0 = priv->sample[3] & 0xfff;
83 y1 = (priv->sample[0] >> 12) & 0xfff;
84 y2 = (priv->sample[1] >> 12) & 0xfff;
85 cr0 = (priv->sample[2] >> 12) & 0xfff;
86 cr1 = (priv->sample[3] >> 12) & 0xfff;
87
88 dev_dbg(&idev->dev,
89 "x: (% 4d,% 4d,% 4d) y: (% 4d, % 4d,% 4d) cr: (% 4d, % 4d)\n",
90 x0, x1, x2, y0, y1, y2, cr0, cr1);
91
92 sort3(x0, x1, x2);
93 sort3(y0, y1, y2);
94
95 cr0 = (cr0 + cr1) / 2;
96
97 if (!cr0 || !sample_tolerance ||
98 (x2 - x0 < sample_tolerance &&
99 y2 - y0 < sample_tolerance)) {
100 /* report the median coordinate and average pressure */
101 if (cr0) {
102 input_report_abs(idev, ABS_X, x1);
103 input_report_abs(idev, ABS_Y, y1);
104
105 dev_dbg(&idev->dev, "report (%d, %d, %d)\n",
106 x1, y1, 0x1000 - cr0);
107 queue_delayed_work(priv->workq, &priv->work, HZ / 50);
108 } else
109 dev_dbg(&idev->dev, "report release\n");
110
111 input_report_abs(idev, ABS_PRESSURE,
112 cr0 ? 0x1000 - cr0 : cr0);
113 input_report_key(idev, BTN_TOUCH, cr0);
114 input_sync(idev);
115 } else
116 dev_dbg(&idev->dev, "discard event\n");
117}
118
119static void mc13783_ts_work(struct work_struct *work)
120{
121 struct mc13783_ts_priv *priv =
122 container_of(work, struct mc13783_ts_priv, work.work);
123 unsigned int mode = MC13783_ADC_MODE_TS;
124 unsigned int channel = 12;
125
126 if (mc13783_adc_do_conversion(priv->mc13783,
127 mode, channel, priv->sample) == 0)
128 mc13783_ts_report_sample(priv);
129}
130
131static int mc13783_ts_open(struct input_dev *dev)
132{
133 struct mc13783_ts_priv *priv = input_get_drvdata(dev);
134 int ret;
135
136 mc13783_lock(priv->mc13783);
137
138 mc13783_ackirq(priv->mc13783, MC13783_IRQ_TS);
139
140 ret = mc13783_irq_request(priv->mc13783, MC13783_IRQ_TS,
141 mc13783_ts_handler, MC13783_TS_NAME, priv);
142 if (ret)
143 goto out;
144
145 ret = mc13783_reg_rmw(priv->mc13783, MC13783_ADC0,
146 MC13783_ADC0_TSMOD_MASK, MC13783_ADC0_TSMOD0);
147 if (ret)
148 mc13783_irq_free(priv->mc13783, MC13783_IRQ_TS, priv);
149out:
150 mc13783_unlock(priv->mc13783);
151 return ret;
152}
153
154static void mc13783_ts_close(struct input_dev *dev)
155{
156 struct mc13783_ts_priv *priv = input_get_drvdata(dev);
157
158 mc13783_lock(priv->mc13783);
159 mc13783_reg_rmw(priv->mc13783, MC13783_ADC0,
160 MC13783_ADC0_TSMOD_MASK, 0);
161 mc13783_irq_free(priv->mc13783, MC13783_IRQ_TS, priv);
162 mc13783_unlock(priv->mc13783);
163
164 cancel_delayed_work_sync(&priv->work);
165}
166
167static int __init mc13783_ts_probe(struct platform_device *pdev)
168{
169 struct mc13783_ts_priv *priv;
170 struct input_dev *idev;
171 int ret = -ENOMEM;
172
173 priv = kzalloc(sizeof(*priv), GFP_KERNEL);
174 idev = input_allocate_device();
175 if (!priv || !idev)
176 goto err_free_mem;
177
178 INIT_DELAYED_WORK(&priv->work, mc13783_ts_work);
179 priv->mc13783 = dev_get_drvdata(pdev->dev.parent);
180 priv->idev = idev;
181
182 /*
183 * We need separate workqueue because mc13783_adc_do_conversion
184 * uses keventd and thus would deadlock.
185 */
186 priv->workq = create_singlethread_workqueue("mc13783_ts");
187 if (!priv->workq)
188 goto err_free_mem;
189
190 idev->name = MC13783_TS_NAME;
191 idev->dev.parent = &pdev->dev;
192
193 idev->evbit[0] = BIT_MASK(EV_KEY) | BIT_MASK(EV_ABS);
194 idev->keybit[BIT_WORD(BTN_TOUCH)] = BIT_MASK(BTN_TOUCH);
195 input_set_abs_params(idev, ABS_X, 0, 0xfff, 0, 0);
196 input_set_abs_params(idev, ABS_Y, 0, 0xfff, 0, 0);
197 input_set_abs_params(idev, ABS_PRESSURE, 0, 0xfff, 0, 0);
198
199 idev->open = mc13783_ts_open;
200 idev->close = mc13783_ts_close;
201
202 input_set_drvdata(idev, priv);
203
204 ret = input_register_device(priv->idev);
205 if (ret) {
206 dev_err(&pdev->dev,
207 "register input device failed with %d\n", ret);
208 goto err_destroy_wq;
209 }
210
211 platform_set_drvdata(pdev, priv);
212 return 0;
213
214err_destroy_wq:
215 destroy_workqueue(priv->workq);
216err_free_mem:
217 input_free_device(idev);
218 kfree(priv);
219 return ret;
220}
221
222static int __devexit mc13783_ts_remove(struct platform_device *pdev)
223{
224 struct mc13783_ts_priv *priv = platform_get_drvdata(pdev);
225
226 platform_set_drvdata(pdev, NULL);
227
228 destroy_workqueue(priv->workq);
229 input_unregister_device(priv->idev);
230 kfree(priv);
231
232 return 0;
233}
234
235static struct platform_driver mc13783_ts_driver = {
236 .remove = __devexit_p(mc13783_ts_remove),
237 .driver = {
238 .owner = THIS_MODULE,
239 .name = MC13783_TS_NAME,
240 },
241};
242
243static int __init mc13783_ts_init(void)
244{
245 return platform_driver_probe(&mc13783_ts_driver, &mc13783_ts_probe);
246}
247module_init(mc13783_ts_init);
248
249static void __exit mc13783_ts_exit(void)
250{
251 platform_driver_unregister(&mc13783_ts_driver);
252}
253module_exit(mc13783_ts_exit);
254
255MODULE_DESCRIPTION("MC13783 input touchscreen driver");
256MODULE_AUTHOR("Sascha Hauer <s.hauer@pengutronix.de>");
257MODULE_LICENSE("GPL v2");
258MODULE_ALIAS("platform:" MC13783_TS_NAME);