aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPing Cheng <pingc@wacom.com>2009-05-08 21:30:33 -0400
committerDmitry Torokhov <dmitry.torokhov@gmail.com>2009-05-08 21:33:43 -0400
commit6f660f12d703fa23069317f0a64c6b75d08c15c2 (patch)
tree03c2a5abb0566b49ddd5c7275928295c79dae760
parent9b771ac442a640999247314e8cdafd8943611700 (diff)
Input: wacom - add support for Intuos4 tablets
Signed-oof-by: Ping Cheng <pingc@wacom.com> Signed-off-by: Dmitry Torokhov <dtor@mail.ru>
-rw-r--r--drivers/input/tablet/wacom.h5
-rw-r--r--drivers/input/tablet/wacom_sys.c13
-rw-r--r--drivers/input/tablet/wacom_wac.c168
-rw-r--r--drivers/input/tablet/wacom_wac.h3
4 files changed, 148 insertions, 41 deletions
diff --git a/drivers/input/tablet/wacom.h b/drivers/input/tablet/wacom.h
index 9710bfd49cf9..9114ae1c7488 100644
--- a/drivers/input/tablet/wacom.h
+++ b/drivers/input/tablet/wacom.h
@@ -68,6 +68,7 @@
68 * v1.48 (pc) - Added support for Bamboo1, BambooFun, and Cintiq 12WX 68 * v1.48 (pc) - Added support for Bamboo1, BambooFun, and Cintiq 12WX
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 */ 72 */
72 73
73/* 74/*
@@ -88,7 +89,7 @@
88/* 89/*
89 * Version Information 90 * Version Information
90 */ 91 */
91#define DRIVER_VERSION "v1.50" 92#define DRIVER_VERSION "v1.51"
92#define DRIVER_AUTHOR "Vojtech Pavlik <vojtech@ucw.cz>" 93#define DRIVER_AUTHOR "Vojtech Pavlik <vojtech@ucw.cz>"
93#define DRIVER_DESC "USB Wacom Graphire and Wacom Intuos tablet driver" 94#define DRIVER_DESC "USB Wacom Graphire and Wacom Intuos tablet driver"
94#define DRIVER_LICENSE "GPL" 95#define DRIVER_LICENSE "GPL"
@@ -128,6 +129,8 @@ extern void input_dev_g(struct input_dev *input_dev, struct wacom_wac *wacom_wac
128extern void input_dev_i3s(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 129extern void input_dev_i3s(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
129extern void input_dev_i3(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 130extern void input_dev_i3(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
130extern void input_dev_i(struct input_dev *input_dev, struct wacom_wac *wacom_wac); 131extern void input_dev_i(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
132extern void input_dev_i4s(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
133extern void input_dev_i4(struct input_dev *input_dev, struct wacom_wac *wacom_wac);
131extern void input_dev_pl(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);
132extern void input_dev_pt(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);
133extern void input_dev_mo(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);
diff --git a/drivers/input/tablet/wacom_sys.c b/drivers/input/tablet/wacom_sys.c
index b8624f27abf9..a9d5031b855e 100644
--- a/drivers/input/tablet/wacom_sys.c
+++ b/drivers/input/tablet/wacom_sys.c
@@ -229,6 +229,19 @@ void input_dev_i3(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
229 input_set_abs_params(input_dev, ABS_RY, 0, 4096, 0, 0); 229 input_set_abs_params(input_dev, ABS_RY, 0, 4096, 0, 0);
230} 230}
231 231
232void input_dev_i4s(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
233{
234 input_dev->keybit[BIT_WORD(BTN_DIGI)] |= BIT_MASK(BTN_TOOL_FINGER);
235 input_dev->keybit[BIT_WORD(BTN_MISC)] |= BIT_MASK(BTN_0) | BIT_MASK(BTN_1) | BIT_MASK(BTN_2) | BIT_MASK(BTN_3);
236 input_dev->keybit[BIT_WORD(BTN_MISC)] |= BIT_MASK(BTN_4) | BIT_MASK(BTN_5) | BIT_MASK(BTN_6);
237 input_set_abs_params(input_dev, ABS_Z, -900, 899, 0, 0);
238}
239
240void input_dev_i4(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
241{
242 input_dev->keybit[BIT_WORD(BTN_MISC)] |= BIT_MASK(BTN_7) | BIT_MASK(BTN_8);
243}
244
232void input_dev_bee(struct input_dev *input_dev, struct wacom_wac *wacom_wac) 245void input_dev_bee(struct input_dev *input_dev, struct wacom_wac *wacom_wac)
233{ 246{
234 input_dev->keybit[BIT_WORD(BTN_MISC)] |= BIT_MASK(BTN_8) | BIT_MASK(BTN_9); 247 input_dev->keybit[BIT_WORD(BTN_MISC)] |= BIT_MASK(BTN_8) | BIT_MASK(BTN_9);
diff --git a/drivers/input/tablet/wacom_wac.c b/drivers/input/tablet/wacom_wac.c
index 2638811c61ac..2ff89904f26f 100644
--- a/drivers/input/tablet/wacom_wac.c
+++ b/drivers/input/tablet/wacom_wac.c
@@ -283,10 +283,11 @@ static int wacom_graphire_irq(struct wacom_wac *wacom, void *wcombo)
283static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo) 283static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
284{ 284{
285 unsigned char *data = wacom->data; 285 unsigned char *data = wacom->data;
286 int idx; 286 int idx = 0;
287 287
288 /* tool number */ 288 /* tool number */
289 idx = data[1] & 0x01; 289 if (wacom->features->type == INTUOS)
290 idx = data[1] & 0x01;
290 291
291 /* Enter report */ 292 /* Enter report */
292 if ((data[1] & 0xfc) == 0xc0) { 293 if ((data[1] & 0xfc) == 0xc0) {
@@ -299,6 +300,7 @@ static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
299 switch (wacom->id[idx]) { 300 switch (wacom->id[idx]) {
300 case 0x812: /* Inking pen */ 301 case 0x812: /* Inking pen */
301 case 0x801: /* Intuos3 Inking pen */ 302 case 0x801: /* Intuos3 Inking pen */
303 case 0x20802: /* Intuos4 Classic Pen */
302 case 0x012: 304 case 0x012:
303 wacom->tool[idx] = BTN_TOOL_PENCIL; 305 wacom->tool[idx] = BTN_TOOL_PENCIL;
304 break; 306 break;
@@ -308,6 +310,9 @@ static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
308 case 0x823: /* Intuos3 Grip Pen */ 310 case 0x823: /* Intuos3 Grip Pen */
309 case 0x813: /* Intuos3 Classic Pen */ 311 case 0x813: /* Intuos3 Classic Pen */
310 case 0x885: /* Intuos3 Marker Pen */ 312 case 0x885: /* Intuos3 Marker Pen */
313 case 0x802: /* Intuos4 Grip Pen Eraser */
314 case 0x804: /* Intuos4 Marker Pen */
315 case 0x40802: /* Intuos4 Classic Pen */
311 case 0x022: 316 case 0x022:
312 wacom->tool[idx] = BTN_TOOL_PEN; 317 wacom->tool[idx] = BTN_TOOL_PEN;
313 break; 318 break;
@@ -319,10 +324,12 @@ static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
319 case 0x09c: 324 case 0x09c:
320 case 0x094: 325 case 0x094:
321 case 0x017: /* Intuos3 2D Mouse */ 326 case 0x017: /* Intuos3 2D Mouse */
327 case 0x806: /* Intuos4 Mouse */
322 wacom->tool[idx] = BTN_TOOL_MOUSE; 328 wacom->tool[idx] = BTN_TOOL_MOUSE;
323 break; 329 break;
324 case 0x096: /* Lens cursor */ 330 case 0x096: /* Lens cursor */
325 case 0x097: /* Intuos3 Lens cursor */ 331 case 0x097: /* Intuos3 Lens cursor */
332 case 0x006: /* Intuos4 Lens cursor */
326 wacom->tool[idx] = BTN_TOOL_LENS; 333 wacom->tool[idx] = BTN_TOOL_LENS;
327 break; 334 break;
328 case 0x82a: /* Eraser */ 335 case 0x82a: /* Eraser */
@@ -333,12 +340,17 @@ static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
333 case 0x82b: /* Intuos3 Grip Pen Eraser */ 340 case 0x82b: /* Intuos3 Grip Pen Eraser */
334 case 0x81b: /* Intuos3 Classic Pen Eraser */ 341 case 0x81b: /* Intuos3 Classic Pen Eraser */
335 case 0x91b: /* Intuos3 Airbrush Eraser */ 342 case 0x91b: /* Intuos3 Airbrush Eraser */
343 case 0x80c: /* Intuos4 Marker Pen Eraser */
344 case 0x80a: /* Intuos4 Grip Pen Eraser */
345 case 0x4080a: /* Intuos4 Classic Pen Eraser */
346 case 0x90a: /* Intuos4 Airbrush Eraser */
336 wacom->tool[idx] = BTN_TOOL_RUBBER; 347 wacom->tool[idx] = BTN_TOOL_RUBBER;
337 break; 348 break;
338 case 0xd12: 349 case 0xd12:
339 case 0x912: 350 case 0x912:
340 case 0x112: 351 case 0x112:
341 case 0x913: /* Intuos3 Airbrush */ 352 case 0x913: /* Intuos3 Airbrush */
353 case 0x902: /* Intuos4 Airbrush */
342 wacom->tool[idx] = BTN_TOOL_AIRBRUSH; 354 wacom->tool[idx] = BTN_TOOL_AIRBRUSH;
343 break; 355 break;
344 default: /* Unknown tool */ 356 default: /* Unknown tool */
@@ -349,9 +361,15 @@ static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
349 361
350 /* Exit report */ 362 /* Exit report */
351 if ((data[1] & 0xfe) == 0x80) { 363 if ((data[1] & 0xfe) == 0x80) {
364 /*
365 * Reset all states otherwise we lose the initial states
366 * when in-prox next time
367 */
352 wacom_report_abs(wcombo, ABS_X, 0); 368 wacom_report_abs(wcombo, ABS_X, 0);
353 wacom_report_abs(wcombo, ABS_Y, 0); 369 wacom_report_abs(wcombo, ABS_Y, 0);
354 wacom_report_abs(wcombo, ABS_DISTANCE, 0); 370 wacom_report_abs(wcombo, ABS_DISTANCE, 0);
371 wacom_report_abs(wcombo, ABS_TILT_X, 0);
372 wacom_report_abs(wcombo, ABS_TILT_Y, 0);
355 if (wacom->tool[idx] >= BTN_TOOL_MOUSE) { 373 if (wacom->tool[idx] >= BTN_TOOL_MOUSE) {
356 wacom_report_key(wcombo, BTN_LEFT, 0); 374 wacom_report_key(wcombo, BTN_LEFT, 0);
357 wacom_report_key(wcombo, BTN_MIDDLE, 0); 375 wacom_report_key(wcombo, BTN_MIDDLE, 0);
@@ -362,8 +380,6 @@ static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
362 wacom_report_abs(wcombo, ABS_RZ, 0); 380 wacom_report_abs(wcombo, ABS_RZ, 0);
363 } else { 381 } else {
364 wacom_report_abs(wcombo, ABS_PRESSURE, 0); 382 wacom_report_abs(wcombo, ABS_PRESSURE, 0);
365 wacom_report_abs(wcombo, ABS_TILT_X, 0);
366 wacom_report_abs(wcombo, ABS_TILT_Y, 0);
367 wacom_report_key(wcombo, BTN_STYLUS, 0); 383 wacom_report_key(wcombo, BTN_STYLUS, 0);
368 wacom_report_key(wcombo, BTN_STYLUS2, 0); 384 wacom_report_key(wcombo, BTN_STYLUS2, 0);
369 wacom_report_key(wcombo, BTN_TOUCH, 0); 385 wacom_report_key(wcombo, BTN_TOUCH, 0);
@@ -372,6 +388,7 @@ static int wacom_intuos_inout(struct wacom_wac *wacom, void *wcombo)
372 wacom_report_key(wcombo, wacom->tool[idx], 0); 388 wacom_report_key(wcombo, wacom->tool[idx], 0);
373 wacom_report_abs(wcombo, ABS_MISC, 0); /* reset tool id */ 389 wacom_report_abs(wcombo, ABS_MISC, 0); /* reset tool id */
374 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, wacom->serial[idx]); 390 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, wacom->serial[idx]);
391 wacom->id[idx] = 0;
375 return 2; 392 return 2;
376 } 393 }
377 return 0; 394 return 0;
@@ -385,6 +402,8 @@ static void wacom_intuos_general(struct wacom_wac *wacom, void *wcombo)
385 /* general pen packet */ 402 /* general pen packet */
386 if ((data[1] & 0xb8) == 0xa0) { 403 if ((data[1] & 0xb8) == 0xa0) {
387 t = (data[6] << 2) | ((data[7] >> 6) & 3); 404 t = (data[6] << 2) | ((data[7] >> 6) & 3);
405 if (wacom->features->type >= INTUOS4S && wacom->features->type <= INTUOS4L)
406 t = (t << 1) | (data[1] & 1);
388 wacom_report_abs(wcombo, ABS_PRESSURE, t); 407 wacom_report_abs(wcombo, ABS_PRESSURE, t);
389 wacom_report_abs(wcombo, ABS_TILT_X, 408 wacom_report_abs(wcombo, ABS_TILT_X,
390 ((data[7] << 1) & 0x7e) | (data[8] >> 7)); 409 ((data[7] << 1) & 0x7e) | (data[8] >> 7));
@@ -409,7 +428,7 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
409{ 428{
410 unsigned char *data = wacom->data; 429 unsigned char *data = wacom->data;
411 unsigned int t; 430 unsigned int t;
412 int idx, result; 431 int idx = 0, result;
413 432
414 if (data[0] != 2 && data[0] != 5 && data[0] != 6 && data[0] != 12) { 433 if (data[0] != 2 && data[0] != 5 && data[0] != 6 && data[0] != 12) {
415 dbg("wacom_intuos_irq: received unknown report #%d", data[0]); 434 dbg("wacom_intuos_irq: received unknown report #%d", data[0]);
@@ -417,7 +436,8 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
417 } 436 }
418 437
419 /* tool number */ 438 /* tool number */
420 idx = data[1] & 0x01; 439 if (wacom->features->type == INTUOS)
440 idx = data[1] & 0x01;
421 441
422 /* pad packets. Works as a second tool and is always in prox */ 442 /* pad packets. Works as a second tool and is always in prox */
423 if (data[0] == 12) { 443 if (data[0] == 12) {
@@ -425,25 +445,51 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
425 if (wacom->tool[1] != BTN_TOOL_FINGER) 445 if (wacom->tool[1] != BTN_TOOL_FINGER)
426 wacom->tool[1] = BTN_TOOL_FINGER; 446 wacom->tool[1] = BTN_TOOL_FINGER;
427 447
428 wacom_report_key(wcombo, BTN_0, (data[5] & 0x01)); 448 if (wacom->features->type >= INTUOS4S && wacom->features->type <= INTUOS4L) {
429 wacom_report_key(wcombo, BTN_1, (data[5] & 0x02)); 449 wacom_report_key(wcombo, BTN_0, (data[2] & 0x01));
430 wacom_report_key(wcombo, BTN_2, (data[5] & 0x04)); 450 wacom_report_key(wcombo, BTN_1, (data[3] & 0x01));
431 wacom_report_key(wcombo, BTN_3, (data[5] & 0x08)); 451 wacom_report_key(wcombo, BTN_2, (data[3] & 0x02));
432 wacom_report_key(wcombo, BTN_4, (data[6] & 0x01)); 452 wacom_report_key(wcombo, BTN_3, (data[3] & 0x04));
433 wacom_report_key(wcombo, BTN_5, (data[6] & 0x02)); 453 wacom_report_key(wcombo, BTN_4, (data[3] & 0x08));
434 wacom_report_key(wcombo, BTN_6, (data[6] & 0x04)); 454 wacom_report_key(wcombo, BTN_5, (data[3] & 0x10));
435 wacom_report_key(wcombo, BTN_7, (data[6] & 0x08)); 455 wacom_report_key(wcombo, BTN_6, (data[3] & 0x20));
436 wacom_report_key(wcombo, BTN_8, (data[5] & 0x10)); 456 if (data[1] & 0x80) {
437 wacom_report_key(wcombo, BTN_9, (data[6] & 0x10)); 457 wacom_report_abs(wcombo, ABS_WHEEL, (data[1] & 0x7f));
438 wacom_report_abs(wcombo, ABS_RX, ((data[1] & 0x1f) << 8) | data[2]); 458 }
439 wacom_report_abs(wcombo, ABS_RY, ((data[3] & 0x1f) << 8) | data[4]); 459 if (wacom->features->type != INTUOS4S) {
440 460 wacom_report_key(wcombo, BTN_7, (data[3] & 0x40));
441 if ((data[5] & 0x1f) | (data[6] & 0x1f) | (data[1] & 0x1f) | 461 wacom_report_key(wcombo, BTN_8, (data[3] & 0x80));
442 data[2] | (data[3] & 0x1f) | data[4]) 462 }
443 wacom_report_key(wcombo, wacom->tool[1], 1); 463 if (data[1] | (data[2] & 0x01) | data[3]) {
444 else 464 wacom_report_key(wcombo, wacom->tool[1], 1);
445 wacom_report_key(wcombo, wacom->tool[1], 0); 465 wacom_report_abs(wcombo, ABS_MISC, PAD_DEVICE_ID);
446 wacom_report_abs(wcombo, ABS_MISC, PAD_DEVICE_ID); 466 } else {
467 wacom_report_key(wcombo, wacom->tool[1], 0);
468 wacom_report_abs(wcombo, ABS_MISC, 0);
469 }
470 } else {
471 wacom_report_key(wcombo, BTN_0, (data[5] & 0x01));
472 wacom_report_key(wcombo, BTN_1, (data[5] & 0x02));
473 wacom_report_key(wcombo, BTN_2, (data[5] & 0x04));
474 wacom_report_key(wcombo, BTN_3, (data[5] & 0x08));
475 wacom_report_key(wcombo, BTN_4, (data[6] & 0x01));
476 wacom_report_key(wcombo, BTN_5, (data[6] & 0x02));
477 wacom_report_key(wcombo, BTN_6, (data[6] & 0x04));
478 wacom_report_key(wcombo, BTN_7, (data[6] & 0x08));
479 wacom_report_key(wcombo, BTN_8, (data[5] & 0x10));
480 wacom_report_key(wcombo, BTN_9, (data[6] & 0x10));
481 wacom_report_abs(wcombo, ABS_RX, ((data[1] & 0x1f) << 8) | data[2]);
482 wacom_report_abs(wcombo, ABS_RY, ((data[3] & 0x1f) << 8) | data[4]);
483
484 if ((data[5] & 0x1f) | (data[6] & 0x1f) | (data[1] & 0x1f) |
485 data[2] | (data[3] & 0x1f) | data[4]) {
486 wacom_report_key(wcombo, wacom->tool[1], 1);
487 wacom_report_abs(wcombo, ABS_MISC, PAD_DEVICE_ID);
488 } else {
489 wacom_report_key(wcombo, wacom->tool[1], 0);
490 wacom_report_abs(wcombo, ABS_MISC, 0);
491 }
492 }
447 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xffffffff); 493 wacom_input_event(wcombo, EV_MSC, MSC_SERIAL, 0xffffffff);
448 return 1; 494 return 1;
449 } 495 }
@@ -453,10 +499,16 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
453 if (result) 499 if (result)
454 return result-1; 500 return result-1;
455 501
456 /* Only large I3 and I1 & I2 support Lense Cursor */ 502 /* don't proceed if we don't know the ID */
503 if (!wacom->id[idx])
504 return 0;
505
506 /* Only large Intuos support Lense Cursor */
457 if ((wacom->tool[idx] == BTN_TOOL_LENS) 507 if ((wacom->tool[idx] == BTN_TOOL_LENS)
458 && ((wacom->features->type == INTUOS3) 508 && ((wacom->features->type == INTUOS3)
459 || (wacom->features->type == INTUOS3S))) 509 || (wacom->features->type == INTUOS3S)
510 || (wacom->features->type == INTUOS4)
511 || (wacom->features->type == INTUOS4S)))
460 return 0; 512 return 0;
461 513
462 /* Cintiq doesn't send data when RDY bit isn't set */ 514 /* Cintiq doesn't send data when RDY bit isn't set */
@@ -476,8 +528,8 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
476 /* process general packets */ 528 /* process general packets */
477 wacom_intuos_general(wacom, wcombo); 529 wacom_intuos_general(wacom, wcombo);
478 530
479 /* 4D mouse, 2D mouse, marker pen rotation, or Lens cursor packets */ 531 /* 4D mouse, 2D mouse, marker pen rotation, tilt mouse, or Lens cursor packets */
480 if ((data[1] & 0xbc) == 0xa8 || (data[1] & 0xbe) == 0xb0) { 532 if ((data[1] & 0xbc) == 0xa8 || (data[1] & 0xbe) == 0xb0 || (data[1] & 0xbc) == 0xac) {
481 533
482 if (data[1] & 0x02) { 534 if (data[1] & 0x02) {
483 /* Rotation packet */ 535 /* Rotation packet */
@@ -506,20 +558,36 @@ static int wacom_intuos_irq(struct wacom_wac *wacom, void *wcombo)
506 wacom_report_abs(wcombo, ABS_THROTTLE, (data[8] & 0x08) ? -t : t); 558 wacom_report_abs(wcombo, ABS_THROTTLE, (data[8] & 0x08) ? -t : t);
507 559
508 } else if (wacom->tool[idx] == BTN_TOOL_MOUSE) { 560 } else if (wacom->tool[idx] == BTN_TOOL_MOUSE) {
509 /* 2D mouse packet */ 561 /* I4 mouse */
510 wacom_report_key(wcombo, BTN_LEFT, data[8] & 0x04); 562 if (wacom->features->type >= INTUOS4S && wacom->features->type <= INTUOS4L) {
511 wacom_report_key(wcombo, BTN_MIDDLE, data[8] & 0x08); 563 wacom_report_key(wcombo, BTN_LEFT, data[6] & 0x01);
512 wacom_report_key(wcombo, BTN_RIGHT, data[8] & 0x10); 564 wacom_report_key(wcombo, BTN_MIDDLE, data[6] & 0x02);
513 wacom_report_rel(wcombo, REL_WHEEL, (data[8] & 0x01) 565 wacom_report_key(wcombo, BTN_RIGHT, data[6] & 0x04);
566 wacom_report_rel(wcombo, REL_WHEEL, ((data[7] & 0x80) >> 7)
567 - ((data[7] & 0x40) >> 6));
568 wacom_report_key(wcombo, BTN_SIDE, data[6] & 0x08);
569 wacom_report_key(wcombo, BTN_EXTRA, data[6] & 0x10);
570
571 wacom_report_abs(wcombo, ABS_TILT_X,
572 ((data[7] << 1) & 0x7e) | (data[8] >> 7));
573 wacom_report_abs(wcombo, ABS_TILT_Y, data[8] & 0x7f);
574 } else {
575 /* 2D mouse packet */
576 wacom_report_key(wcombo, BTN_LEFT, data[8] & 0x04);
577 wacom_report_key(wcombo, BTN_MIDDLE, data[8] & 0x08);
578 wacom_report_key(wcombo, BTN_RIGHT, data[8] & 0x10);
579 wacom_report_rel(wcombo, REL_WHEEL, (data[8] & 0x01)
514 - ((data[8] & 0x02) >> 1)); 580 - ((data[8] & 0x02) >> 1));
515 581
516 /* I3 2D mouse side buttons */ 582 /* I3 2D mouse side buttons */
517 if (wacom->features->type >= INTUOS3S && wacom->features->type <= INTUOS3L) { 583 if (wacom->features->type >= INTUOS3S && wacom->features->type <= INTUOS3L) {
518 wacom_report_key(wcombo, BTN_SIDE, data[8] & 0x40); 584 wacom_report_key(wcombo, BTN_SIDE, data[8] & 0x40);
519 wacom_report_key(wcombo, BTN_EXTRA, data[8] & 0x20); 585 wacom_report_key(wcombo, BTN_EXTRA, data[8] & 0x20);
586 }
520 } 587 }
521 588 } else if ((wacom->features->type < INTUOS3S || wacom->features->type == INTUOS3L ||
522 } else if (wacom->features->type < INTUOS3S || wacom->features->type == INTUOS3L) { 589 wacom->features->type == INTUOS4L) &&
590 wacom->tool[idx] == BTN_TOOL_LENS) {
523 /* Lens cursor packets */ 591 /* Lens cursor packets */
524 wacom_report_key(wcombo, BTN_LEFT, data[8] & 0x01); 592 wacom_report_key(wcombo, BTN_LEFT, data[8] & 0x01);
525 wacom_report_key(wcombo, BTN_MIDDLE, data[8] & 0x02); 593 wacom_report_key(wcombo, BTN_MIDDLE, data[8] & 0x02);
@@ -581,6 +649,7 @@ static int wacom_tpc_irq(struct wacom_wac *wacom, void *wcombo)
581 } 649 }
582 } else if (touchOut || !prox) { /* force touch out-prox */ 650 } else if (touchOut || !prox) { /* force touch out-prox */
583 wacom_report_abs(wcombo, ABS_MISC, TOUCH_DEVICE_ID); 651 wacom_report_abs(wcombo, ABS_MISC, TOUCH_DEVICE_ID);
652 wacom_report_key(wcombo, wacom->tool[1], 0);
584 wacom_report_key(wcombo, BTN_TOUCH, 0); 653 wacom_report_key(wcombo, BTN_TOUCH, 0);
585 touchOut = 0; 654 touchOut = 0;
586 touchInProx = 1; 655 touchInProx = 1;
@@ -669,6 +738,9 @@ int wacom_wac_irq(struct wacom_wac *wacom_wac, void *wcombo)
669 case INTUOS3S: 738 case INTUOS3S:
670 case INTUOS3: 739 case INTUOS3:
671 case INTUOS3L: 740 case INTUOS3L:
741 case INTUOS4S:
742 case INTUOS4:
743 case INTUOS4L:
672 case CINTIQ: 744 case CINTIQ:
673 case WACOM_BEE: 745 case WACOM_BEE:
674 return wacom_intuos_irq(wacom_wac, wcombo); 746 return wacom_intuos_irq(wacom_wac, wcombo);
@@ -706,6 +778,14 @@ void wacom_init_input_dev(struct input_dev *input_dev, struct wacom_wac *wacom_w
706 case INTUOS: 778 case INTUOS:
707 input_dev_i(input_dev, wacom_wac); 779 input_dev_i(input_dev, wacom_wac);
708 break; 780 break;
781 case INTUOS4:
782 case INTUOS4L:
783 input_dev_i4(input_dev, wacom_wac);
784 /* fall through */
785 case INTUOS4S:
786 input_dev_i4s(input_dev, wacom_wac);
787 input_dev_i(input_dev, wacom_wac);
788 break;
709 case PL: 789 case PL:
710 case PTU: 790 case PTU:
711 case TABLETPC: 791 case TABLETPC:
@@ -766,6 +846,10 @@ static struct wacom_features wacom_features[] = {
766 { "Wacom Intuos3 12x19", 10, 97536, 60960, 1023, 63, INTUOS3L }, 846 { "Wacom Intuos3 12x19", 10, 97536, 60960, 1023, 63, INTUOS3L },
767 { "Wacom Intuos3 6x11", 10, 54204, 31750, 1023, 63, INTUOS3 }, 847 { "Wacom Intuos3 6x11", 10, 54204, 31750, 1023, 63, INTUOS3 },
768 { "Wacom Intuos3 4x6", 10, 31496, 19685, 1023, 63, INTUOS3S }, 848 { "Wacom Intuos3 4x6", 10, 31496, 19685, 1023, 63, INTUOS3S },
849 { "Wacom Intuos4 4x6", 10, 31496, 19685, 2047, 63, INTUOS4S },
850 { "Wacom Intuos4 6x9", 10, 44704, 27940, 2047, 63, INTUOS4 },
851 { "Wacom Intuos4 8x13", 10, 65024, 40640, 2047, 63, INTUOS4L },
852 { "Wacom Intuos4 12x19", 10, 97536, 60960, 2047, 63, INTUOS4L },
769 { "Wacom Cintiq 21UX", 10, 87200, 65600, 1023, 63, CINTIQ }, 853 { "Wacom Cintiq 21UX", 10, 87200, 65600, 1023, 63, CINTIQ },
770 { "Wacom Cintiq 20WSX", 10, 86680, 54180, 1023, 63, WACOM_BEE }, 854 { "Wacom Cintiq 20WSX", 10, 86680, 54180, 1023, 63, WACOM_BEE },
771 { "Wacom Cintiq 12WX", 10, 53020, 33440, 1023, 63, WACOM_BEE }, 855 { "Wacom Cintiq 12WX", 10, 53020, 33440, 1023, 63, WACOM_BEE },
@@ -825,6 +909,10 @@ static struct usb_device_id wacom_ids[] = {
825 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB4) }, 909 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB4) },
826 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB5) }, 910 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB5) },
827 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB7) }, 911 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB7) },
912 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB8) },
913 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xB9) },
914 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xBA) },
915 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xBB) },
828 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x3F) }, 916 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0x3F) },
829 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xC5) }, 917 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xC5) },
830 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xC6) }, 918 { USB_DEVICE(USB_VENDOR_ID_WACOM, 0xC6) },
diff --git a/drivers/input/tablet/wacom_wac.h b/drivers/input/tablet/wacom_wac.h
index f9c8b69673b7..c10235aba7e5 100644
--- a/drivers/input/tablet/wacom_wac.h
+++ b/drivers/input/tablet/wacom_wac.h
@@ -25,6 +25,9 @@ enum {
25 INTUOS3S, 25 INTUOS3S,
26 INTUOS3, 26 INTUOS3,
27 INTUOS3L, 27 INTUOS3L,
28 INTUOS4S,
29 INTUOS4,
30 INTUOS4L,
28 CINTIQ, 31 CINTIQ,
29 WACOM_BEE, 32 WACOM_BEE,
30 WACOM_MO, 33 WACOM_MO,