0001
0002
0003
0004
0005
0006
0007
0008 #include <linux/device.h>
0009 #include <linux/hid.h>
0010 #include <linux/module.h>
0011 #include "hid-ids.h"
0012
0013 MODULE_AUTHOR("Bastien Nocera <hadess@hadess.net>");
0014 MODULE_DESCRIPTION("PS3 uDraw tablet driver");
0015 MODULE_LICENSE("GPL");
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032 enum {
0033 TOUCH_NONE,
0034 TOUCH_PEN,
0035 TOUCH_FINGER,
0036 TOUCH_TWOFINGER
0037 };
0038
0039 enum {
0040 AXIS_X,
0041 AXIS_Y,
0042 AXIS_Z
0043 };
0044
0045
0046
0047
0048
0049 static struct {
0050 int min;
0051 int max;
0052 } accel_limits[] = {
0053 [AXIS_X] = { 490, 534 },
0054 [AXIS_Y] = { 490, 534 },
0055 [AXIS_Z] = { 492, 536 }
0056 };
0057
0058 #define DEVICE_NAME "THQ uDraw Game Tablet for PS3"
0059
0060 #define RES_X 1920
0061 #define RES_Y 1080
0062
0063 #define WIDTH 160
0064 #define HEIGHT 90
0065 #define PRESSURE_OFFSET 113
0066 #define MAX_PRESSURE (255 - PRESSURE_OFFSET)
0067
0068 struct udraw {
0069 struct input_dev *joy_input_dev;
0070 struct input_dev *touch_input_dev;
0071 struct input_dev *pen_input_dev;
0072 struct input_dev *accel_input_dev;
0073 struct hid_device *hdev;
0074
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084 int last_one_finger_x;
0085 int last_one_finger_y;
0086 int last_two_finger_x;
0087 int last_two_finger_y;
0088 };
0089
0090 static int clamp_accel(int axis, int offset)
0091 {
0092 axis = clamp(axis,
0093 accel_limits[offset].min,
0094 accel_limits[offset].max);
0095 axis = (axis - accel_limits[offset].min) /
0096 ((accel_limits[offset].max -
0097 accel_limits[offset].min) * 0xFF);
0098 return axis;
0099 }
0100
0101 static int udraw_raw_event(struct hid_device *hdev, struct hid_report *report,
0102 u8 *data, int len)
0103 {
0104 struct udraw *udraw = hid_get_drvdata(hdev);
0105 int touch;
0106 int x, y, z;
0107
0108 if (len != 27)
0109 return 0;
0110
0111 if (data[11] == 0x00)
0112 touch = TOUCH_NONE;
0113 else if (data[11] == 0x40)
0114 touch = TOUCH_PEN;
0115 else if (data[11] == 0x80)
0116 touch = TOUCH_FINGER;
0117 else
0118 touch = TOUCH_TWOFINGER;
0119
0120
0121 input_report_key(udraw->joy_input_dev, BTN_WEST, data[0] & 1);
0122 input_report_key(udraw->joy_input_dev, BTN_SOUTH, !!(data[0] & 2));
0123 input_report_key(udraw->joy_input_dev, BTN_EAST, !!(data[0] & 4));
0124 input_report_key(udraw->joy_input_dev, BTN_NORTH, !!(data[0] & 8));
0125
0126 input_report_key(udraw->joy_input_dev, BTN_SELECT, !!(data[1] & 1));
0127 input_report_key(udraw->joy_input_dev, BTN_START, !!(data[1] & 2));
0128 input_report_key(udraw->joy_input_dev, BTN_MODE, !!(data[1] & 16));
0129
0130 x = y = 0;
0131 switch (data[2]) {
0132 case 0x0:
0133 y = -127;
0134 break;
0135 case 0x1:
0136 y = -127;
0137 x = 127;
0138 break;
0139 case 0x2:
0140 x = 127;
0141 break;
0142 case 0x3:
0143 y = 127;
0144 x = 127;
0145 break;
0146 case 0x4:
0147 y = 127;
0148 break;
0149 case 0x5:
0150 y = 127;
0151 x = -127;
0152 break;
0153 case 0x6:
0154 x = -127;
0155 break;
0156 case 0x7:
0157 y = -127;
0158 x = -127;
0159 break;
0160 default:
0161 break;
0162 }
0163
0164 input_report_abs(udraw->joy_input_dev, ABS_X, x);
0165 input_report_abs(udraw->joy_input_dev, ABS_Y, y);
0166
0167 input_sync(udraw->joy_input_dev);
0168
0169
0170 x = y = 0;
0171 if (touch != TOUCH_NONE) {
0172 if (data[15] != 0x0F)
0173 x = data[15] * 256 + data[17];
0174 if (data[16] != 0x0F)
0175 y = data[16] * 256 + data[18];
0176 }
0177
0178 if (touch == TOUCH_FINGER) {
0179
0180 udraw->last_one_finger_x = x;
0181 udraw->last_one_finger_y = y;
0182 udraw->last_two_finger_x = -1;
0183 udraw->last_two_finger_y = -1;
0184 } else if (touch == TOUCH_TWOFINGER) {
0185
0186
0187
0188
0189
0190
0191
0192
0193 if (udraw->last_two_finger_x == -1) {
0194
0195 udraw->last_two_finger_x = x;
0196 udraw->last_two_finger_y = y;
0197
0198 x = udraw->last_one_finger_x;
0199 y = udraw->last_one_finger_y;
0200 } else {
0201
0202
0203
0204
0205 x = x - (udraw->last_two_finger_x
0206 - udraw->last_one_finger_x);
0207 y = y - (udraw->last_two_finger_y
0208 - udraw->last_one_finger_y);
0209 }
0210 }
0211
0212
0213 if (touch == TOUCH_FINGER || touch == TOUCH_TWOFINGER) {
0214 input_report_key(udraw->touch_input_dev, BTN_TOUCH, 1);
0215 input_report_key(udraw->touch_input_dev, BTN_TOOL_FINGER,
0216 touch == TOUCH_FINGER);
0217 input_report_key(udraw->touch_input_dev, BTN_TOOL_DOUBLETAP,
0218 touch == TOUCH_TWOFINGER);
0219
0220 input_report_abs(udraw->touch_input_dev, ABS_X, x);
0221 input_report_abs(udraw->touch_input_dev, ABS_Y, y);
0222 } else {
0223 input_report_key(udraw->touch_input_dev, BTN_TOUCH, 0);
0224 input_report_key(udraw->touch_input_dev, BTN_TOOL_FINGER, 0);
0225 input_report_key(udraw->touch_input_dev, BTN_TOOL_DOUBLETAP, 0);
0226 }
0227 input_sync(udraw->touch_input_dev);
0228
0229
0230 if (touch == TOUCH_PEN) {
0231 int level;
0232
0233 level = clamp(data[13] - PRESSURE_OFFSET,
0234 0, MAX_PRESSURE);
0235
0236 input_report_key(udraw->pen_input_dev, BTN_TOUCH, (level != 0));
0237 input_report_key(udraw->pen_input_dev, BTN_TOOL_PEN, 1);
0238 input_report_abs(udraw->pen_input_dev, ABS_PRESSURE, level);
0239 input_report_abs(udraw->pen_input_dev, ABS_X, x);
0240 input_report_abs(udraw->pen_input_dev, ABS_Y, y);
0241 } else {
0242 input_report_key(udraw->pen_input_dev, BTN_TOUCH, 0);
0243 input_report_key(udraw->pen_input_dev, BTN_TOOL_PEN, 0);
0244 input_report_abs(udraw->pen_input_dev, ABS_PRESSURE, 0);
0245 }
0246 input_sync(udraw->pen_input_dev);
0247
0248
0249 x = (data[19] + (data[20] << 8));
0250 x = clamp_accel(x, AXIS_X);
0251 y = (data[21] + (data[22] << 8));
0252 y = clamp_accel(y, AXIS_Y);
0253 z = (data[23] + (data[24] << 8));
0254 z = clamp_accel(z, AXIS_Z);
0255 input_report_abs(udraw->accel_input_dev, ABS_X, x);
0256 input_report_abs(udraw->accel_input_dev, ABS_Y, y);
0257 input_report_abs(udraw->accel_input_dev, ABS_Z, z);
0258 input_sync(udraw->accel_input_dev);
0259
0260
0261 return 0;
0262 }
0263
0264 static int udraw_open(struct input_dev *dev)
0265 {
0266 struct udraw *udraw = input_get_drvdata(dev);
0267
0268 return hid_hw_open(udraw->hdev);
0269 }
0270
0271 static void udraw_close(struct input_dev *dev)
0272 {
0273 struct udraw *udraw = input_get_drvdata(dev);
0274
0275 hid_hw_close(udraw->hdev);
0276 }
0277
0278 static struct input_dev *allocate_and_setup(struct hid_device *hdev,
0279 const char *name)
0280 {
0281 struct input_dev *input_dev;
0282
0283 input_dev = devm_input_allocate_device(&hdev->dev);
0284 if (!input_dev)
0285 return NULL;
0286
0287 input_dev->name = name;
0288 input_dev->phys = hdev->phys;
0289 input_dev->dev.parent = &hdev->dev;
0290 input_dev->open = udraw_open;
0291 input_dev->close = udraw_close;
0292 input_dev->uniq = hdev->uniq;
0293 input_dev->id.bustype = hdev->bus;
0294 input_dev->id.vendor = hdev->vendor;
0295 input_dev->id.product = hdev->product;
0296 input_dev->id.version = hdev->version;
0297 input_set_drvdata(input_dev, hid_get_drvdata(hdev));
0298
0299 return input_dev;
0300 }
0301
0302 static bool udraw_setup_touch(struct udraw *udraw,
0303 struct hid_device *hdev)
0304 {
0305 struct input_dev *input_dev;
0306
0307 input_dev = allocate_and_setup(hdev, DEVICE_NAME " Touchpad");
0308 if (!input_dev)
0309 return false;
0310
0311 input_dev->evbit[0] = BIT(EV_ABS) | BIT(EV_KEY);
0312
0313 input_set_abs_params(input_dev, ABS_X, 0, RES_X, 1, 0);
0314 input_abs_set_res(input_dev, ABS_X, RES_X / WIDTH);
0315 input_set_abs_params(input_dev, ABS_Y, 0, RES_Y, 1, 0);
0316 input_abs_set_res(input_dev, ABS_Y, RES_Y / HEIGHT);
0317
0318 set_bit(BTN_TOUCH, input_dev->keybit);
0319 set_bit(BTN_TOOL_FINGER, input_dev->keybit);
0320 set_bit(BTN_TOOL_DOUBLETAP, input_dev->keybit);
0321
0322 set_bit(INPUT_PROP_POINTER, input_dev->propbit);
0323
0324 udraw->touch_input_dev = input_dev;
0325
0326 return true;
0327 }
0328
0329 static bool udraw_setup_pen(struct udraw *udraw,
0330 struct hid_device *hdev)
0331 {
0332 struct input_dev *input_dev;
0333
0334 input_dev = allocate_and_setup(hdev, DEVICE_NAME " Pen");
0335 if (!input_dev)
0336 return false;
0337
0338 input_dev->evbit[0] = BIT(EV_ABS) | BIT(EV_KEY);
0339
0340 input_set_abs_params(input_dev, ABS_X, 0, RES_X, 1, 0);
0341 input_abs_set_res(input_dev, ABS_X, RES_X / WIDTH);
0342 input_set_abs_params(input_dev, ABS_Y, 0, RES_Y, 1, 0);
0343 input_abs_set_res(input_dev, ABS_Y, RES_Y / HEIGHT);
0344 input_set_abs_params(input_dev, ABS_PRESSURE,
0345 0, MAX_PRESSURE, 0, 0);
0346
0347 set_bit(BTN_TOUCH, input_dev->keybit);
0348 set_bit(BTN_TOOL_PEN, input_dev->keybit);
0349
0350 set_bit(INPUT_PROP_POINTER, input_dev->propbit);
0351
0352 udraw->pen_input_dev = input_dev;
0353
0354 return true;
0355 }
0356
0357 static bool udraw_setup_accel(struct udraw *udraw,
0358 struct hid_device *hdev)
0359 {
0360 struct input_dev *input_dev;
0361
0362 input_dev = allocate_and_setup(hdev, DEVICE_NAME " Accelerometer");
0363 if (!input_dev)
0364 return false;
0365
0366 input_dev->evbit[0] = BIT(EV_ABS);
0367
0368
0369 input_set_abs_params(input_dev, ABS_X, -512, 512, 0, 0);
0370 input_set_abs_params(input_dev, ABS_Y, -512, 512, 0, 0);
0371 input_set_abs_params(input_dev, ABS_Z, -512, 512, 0, 0);
0372
0373 set_bit(INPUT_PROP_ACCELEROMETER, input_dev->propbit);
0374
0375 udraw->accel_input_dev = input_dev;
0376
0377 return true;
0378 }
0379
0380 static bool udraw_setup_joypad(struct udraw *udraw,
0381 struct hid_device *hdev)
0382 {
0383 struct input_dev *input_dev;
0384
0385 input_dev = allocate_and_setup(hdev, DEVICE_NAME " Joypad");
0386 if (!input_dev)
0387 return false;
0388
0389 input_dev->evbit[0] = BIT(EV_KEY) | BIT(EV_ABS);
0390
0391 set_bit(BTN_SOUTH, input_dev->keybit);
0392 set_bit(BTN_NORTH, input_dev->keybit);
0393 set_bit(BTN_EAST, input_dev->keybit);
0394 set_bit(BTN_WEST, input_dev->keybit);
0395 set_bit(BTN_SELECT, input_dev->keybit);
0396 set_bit(BTN_START, input_dev->keybit);
0397 set_bit(BTN_MODE, input_dev->keybit);
0398
0399 input_set_abs_params(input_dev, ABS_X, -127, 127, 0, 0);
0400 input_set_abs_params(input_dev, ABS_Y, -127, 127, 0, 0);
0401
0402 udraw->joy_input_dev = input_dev;
0403
0404 return true;
0405 }
0406
0407 static int udraw_probe(struct hid_device *hdev, const struct hid_device_id *id)
0408 {
0409 struct udraw *udraw;
0410 int ret;
0411
0412 udraw = devm_kzalloc(&hdev->dev, sizeof(struct udraw), GFP_KERNEL);
0413 if (!udraw)
0414 return -ENOMEM;
0415
0416 udraw->hdev = hdev;
0417 udraw->last_two_finger_x = -1;
0418 udraw->last_two_finger_y = -1;
0419
0420 hid_set_drvdata(hdev, udraw);
0421
0422 ret = hid_parse(hdev);
0423 if (ret) {
0424 hid_err(hdev, "parse failed\n");
0425 return ret;
0426 }
0427
0428 if (!udraw_setup_joypad(udraw, hdev) ||
0429 !udraw_setup_touch(udraw, hdev) ||
0430 !udraw_setup_pen(udraw, hdev) ||
0431 !udraw_setup_accel(udraw, hdev)) {
0432 hid_err(hdev, "could not allocate interfaces\n");
0433 return -ENOMEM;
0434 }
0435
0436 ret = input_register_device(udraw->joy_input_dev) ||
0437 input_register_device(udraw->touch_input_dev) ||
0438 input_register_device(udraw->pen_input_dev) ||
0439 input_register_device(udraw->accel_input_dev);
0440 if (ret) {
0441 hid_err(hdev, "failed to register interfaces\n");
0442 return ret;
0443 }
0444
0445 ret = hid_hw_start(hdev, HID_CONNECT_HIDRAW | HID_CONNECT_DRIVER);
0446 if (ret) {
0447 hid_err(hdev, "hw start failed\n");
0448 return ret;
0449 }
0450
0451 return 0;
0452 }
0453
0454 static const struct hid_device_id udraw_devices[] = {
0455 { HID_USB_DEVICE(USB_VENDOR_ID_THQ, USB_DEVICE_ID_THQ_PS3_UDRAW) },
0456 { }
0457 };
0458 MODULE_DEVICE_TABLE(hid, udraw_devices);
0459
0460 static struct hid_driver udraw_driver = {
0461 .name = "hid-udraw",
0462 .id_table = udraw_devices,
0463 .raw_event = udraw_raw_event,
0464 .probe = udraw_probe,
0465 };
0466 module_hid_driver(udraw_driver);