diff options
author | Dmitry Torokhov <dmitry.torokhov@gmail.com> | 2012-10-30 03:20:56 -0400 |
---|---|---|
committer | Dmitry Torokhov <dmitry.torokhov@gmail.com> | 2012-10-30 03:20:56 -0400 |
commit | 53279f36dccffc26ff536003fd6bb97cc21c3b82 (patch) | |
tree | 9d16e497c0e4158c7c054c479bd0e9ff0388d7bb /drivers/input | |
parent | a6e8c0a25377e27958b11b20e1927885ae7c9857 (diff) | |
parent | 8f0d8163b50e01f398b14bcd4dc039ac5ab18d64 (diff) |
Merge tag 'v3.7-rc3' into next to sync up with recent USB and MFD changes
Diffstat (limited to 'drivers/input')
33 files changed, 430 insertions, 205 deletions
diff --git a/drivers/input/evdev.c b/drivers/input/evdev.c index 6ae2ac47c9c8..f0f8928b3c8a 100644 --- a/drivers/input/evdev.c +++ b/drivers/input/evdev.c | |||
@@ -292,7 +292,6 @@ static int evdev_release(struct inode *inode, struct file *file) | |||
292 | kfree(client); | 292 | kfree(client); |
293 | 293 | ||
294 | evdev_close_device(evdev); | 294 | evdev_close_device(evdev); |
295 | put_device(&evdev->dev); | ||
296 | 295 | ||
297 | return 0; | 296 | return 0; |
298 | } | 297 | } |
@@ -331,7 +330,6 @@ static int evdev_open(struct inode *inode, struct file *file) | |||
331 | file->private_data = client; | 330 | file->private_data = client; |
332 | nonseekable_open(inode, file); | 331 | nonseekable_open(inode, file); |
333 | 332 | ||
334 | get_device(&evdev->dev); | ||
335 | return 0; | 333 | return 0; |
336 | 334 | ||
337 | err_free_client: | 335 | err_free_client: |
@@ -1001,6 +999,7 @@ static int evdev_connect(struct input_handler *handler, struct input_dev *dev, | |||
1001 | goto err_free_evdev; | 999 | goto err_free_evdev; |
1002 | 1000 | ||
1003 | cdev_init(&evdev->cdev, &evdev_fops); | 1001 | cdev_init(&evdev->cdev, &evdev_fops); |
1002 | evdev->cdev.kobj.parent = &evdev->dev.kobj; | ||
1004 | error = cdev_add(&evdev->cdev, evdev->dev.devt, 1); | 1003 | error = cdev_add(&evdev->cdev, evdev->dev.devt, 1); |
1005 | if (error) | 1004 | if (error) |
1006 | goto err_unregister_handle; | 1005 | goto err_unregister_handle; |
diff --git a/drivers/input/joydev.c b/drivers/input/joydev.c index b62b5891f399..f362883c94e3 100644 --- a/drivers/input/joydev.c +++ b/drivers/input/joydev.c | |||
@@ -243,7 +243,6 @@ static int joydev_release(struct inode *inode, struct file *file) | |||
243 | kfree(client); | 243 | kfree(client); |
244 | 244 | ||
245 | joydev_close_device(joydev); | 245 | joydev_close_device(joydev); |
246 | put_device(&joydev->dev); | ||
247 | 246 | ||
248 | return 0; | 247 | return 0; |
249 | } | 248 | } |
@@ -270,7 +269,6 @@ static int joydev_open(struct inode *inode, struct file *file) | |||
270 | file->private_data = client; | 269 | file->private_data = client; |
271 | nonseekable_open(inode, file); | 270 | nonseekable_open(inode, file); |
272 | 271 | ||
273 | get_device(&joydev->dev); | ||
274 | return 0; | 272 | return 0; |
275 | 273 | ||
276 | err_free_client: | 274 | err_free_client: |
@@ -858,6 +856,7 @@ static int joydev_connect(struct input_handler *handler, struct input_dev *dev, | |||
858 | goto err_free_joydev; | 856 | goto err_free_joydev; |
859 | 857 | ||
860 | cdev_init(&joydev->cdev, &joydev_fops); | 858 | cdev_init(&joydev->cdev, &joydev_fops); |
859 | joydev->cdev.kobj.parent = &joydev->dev.kobj; | ||
861 | error = cdev_add(&joydev->cdev, joydev->dev.devt, 1); | 860 | error = cdev_add(&joydev->cdev, joydev->dev.devt, 1); |
862 | if (error) | 861 | if (error) |
863 | goto err_unregister_handle; | 862 | goto err_unregister_handle; |
diff --git a/drivers/input/keyboard/Kconfig b/drivers/input/keyboard/Kconfig index f483ce65157f..5a83afb31219 100644 --- a/drivers/input/keyboard/Kconfig +++ b/drivers/input/keyboard/Kconfig | |||
@@ -533,7 +533,7 @@ config KEYBOARD_DAVINCI | |||
533 | 533 | ||
534 | config KEYBOARD_OMAP | 534 | config KEYBOARD_OMAP |
535 | tristate "TI OMAP keypad support" | 535 | tristate "TI OMAP keypad support" |
536 | depends on (ARCH_OMAP1 || ARCH_OMAP2) | 536 | depends on ARCH_OMAP1 |
537 | select INPUT_MATRIXKMAP | 537 | select INPUT_MATRIXKMAP |
538 | help | 538 | help |
539 | Say Y here if you want to use the OMAP keypad. | 539 | Say Y here if you want to use the OMAP keypad. |
diff --git a/drivers/input/keyboard/davinci_keyscan.c b/drivers/input/keyboard/davinci_keyscan.c index 9d82b3aeff5e..d5bacbb479b0 100644 --- a/drivers/input/keyboard/davinci_keyscan.c +++ b/drivers/input/keyboard/davinci_keyscan.c | |||
@@ -36,7 +36,7 @@ | |||
36 | 36 | ||
37 | #include <mach/hardware.h> | 37 | #include <mach/hardware.h> |
38 | #include <mach/irqs.h> | 38 | #include <mach/irqs.h> |
39 | #include <mach/keyscan.h> | 39 | #include <linux/platform_data/keyscan-davinci.h> |
40 | 40 | ||
41 | /* Key scan registers */ | 41 | /* Key scan registers */ |
42 | #define DAVINCI_KEYSCAN_KEYCTRL 0x0000 | 42 | #define DAVINCI_KEYSCAN_KEYCTRL 0x0000 |
diff --git a/drivers/input/keyboard/ep93xx_keypad.c b/drivers/input/keyboard/ep93xx_keypad.c index c46fc8185469..7363402de8d4 100644 --- a/drivers/input/keyboard/ep93xx_keypad.c +++ b/drivers/input/keyboard/ep93xx_keypad.c | |||
@@ -29,7 +29,7 @@ | |||
29 | #include <linux/slab.h> | 29 | #include <linux/slab.h> |
30 | 30 | ||
31 | #include <mach/hardware.h> | 31 | #include <mach/hardware.h> |
32 | #include <mach/ep93xx_keypad.h> | 32 | #include <linux/platform_data/keypad-ep93xx.h> |
33 | 33 | ||
34 | /* | 34 | /* |
35 | * Keypad Interface Register offsets | 35 | * Keypad Interface Register offsets |
diff --git a/drivers/input/keyboard/imx_keypad.c b/drivers/input/keyboard/imx_keypad.c index ff4c0a87a25f..cdc252612c0b 100644 --- a/drivers/input/keyboard/imx_keypad.c +++ b/drivers/input/keyboard/imx_keypad.c | |||
@@ -358,6 +358,7 @@ static void imx_keypad_inhibit(struct imx_keypad *keypad) | |||
358 | /* Inhibit KDI and KRI interrupts. */ | 358 | /* Inhibit KDI and KRI interrupts. */ |
359 | reg_val = readw(keypad->mmio_base + KPSR); | 359 | reg_val = readw(keypad->mmio_base + KPSR); |
360 | reg_val &= ~(KBD_STAT_KRIE | KBD_STAT_KDIE); | 360 | reg_val &= ~(KBD_STAT_KRIE | KBD_STAT_KDIE); |
361 | reg_val |= KBD_STAT_KPKR | KBD_STAT_KPKD; | ||
361 | writew(reg_val, keypad->mmio_base + KPSR); | 362 | writew(reg_val, keypad->mmio_base + KPSR); |
362 | 363 | ||
363 | /* Colums as open drain and disable all rows */ | 364 | /* Colums as open drain and disable all rows */ |
@@ -515,7 +516,9 @@ static int __devinit imx_keypad_probe(struct platform_device *pdev) | |||
515 | input_set_drvdata(input_dev, keypad); | 516 | input_set_drvdata(input_dev, keypad); |
516 | 517 | ||
517 | /* Ensure that the keypad will stay dormant until opened */ | 518 | /* Ensure that the keypad will stay dormant until opened */ |
519 | clk_prepare_enable(keypad->clk); | ||
518 | imx_keypad_inhibit(keypad); | 520 | imx_keypad_inhibit(keypad); |
521 | clk_disable_unprepare(keypad->clk); | ||
519 | 522 | ||
520 | error = request_irq(irq, imx_keypad_irq_handler, 0, | 523 | error = request_irq(irq, imx_keypad_irq_handler, 0, |
521 | pdev->name, keypad); | 524 | pdev->name, keypad); |
diff --git a/drivers/input/keyboard/nomadik-ske-keypad.c b/drivers/input/keyboard/nomadik-ske-keypad.c index a880e7414202..49f5fa64e0b1 100644 --- a/drivers/input/keyboard/nomadik-ske-keypad.c +++ b/drivers/input/keyboard/nomadik-ske-keypad.c | |||
@@ -20,7 +20,7 @@ | |||
20 | #include <linux/clk.h> | 20 | #include <linux/clk.h> |
21 | #include <linux/module.h> | 21 | #include <linux/module.h> |
22 | 22 | ||
23 | #include <plat/ske.h> | 23 | #include <linux/platform_data/keypad-nomadik-ske.h> |
24 | 24 | ||
25 | /* SKE_CR bits */ | 25 | /* SKE_CR bits */ |
26 | #define SKE_KPMLT (0x1 << 6) | 26 | #define SKE_KPMLT (0x1 << 6) |
diff --git a/drivers/input/keyboard/omap-keypad.c b/drivers/input/keyboard/omap-keypad.c index b03c5b954864..4a5fcc8026f5 100644 --- a/drivers/input/keyboard/omap-keypad.c +++ b/drivers/input/keyboard/omap-keypad.c | |||
@@ -35,13 +35,9 @@ | |||
35 | #include <linux/mutex.h> | 35 | #include <linux/mutex.h> |
36 | #include <linux/errno.h> | 36 | #include <linux/errno.h> |
37 | #include <linux/slab.h> | 37 | #include <linux/slab.h> |
38 | #include <asm/gpio.h> | 38 | #include <linux/gpio.h> |
39 | #include <plat/keypad.h> | 39 | #include <linux/platform_data/gpio-omap.h> |
40 | #include <plat/menelaus.h> | 40 | #include <linux/platform_data/keypad-omap.h> |
41 | #include <asm/irq.h> | ||
42 | #include <mach/hardware.h> | ||
43 | #include <asm/io.h> | ||
44 | #include <plat/mux.h> | ||
45 | 41 | ||
46 | #undef NEW_BOARD_LEARNING_MODE | 42 | #undef NEW_BOARD_LEARNING_MODE |
47 | 43 | ||
@@ -96,28 +92,8 @@ static u8 get_row_gpio_val(struct omap_kp *omap_kp) | |||
96 | 92 | ||
97 | static irqreturn_t omap_kp_interrupt(int irq, void *dev_id) | 93 | static irqreturn_t omap_kp_interrupt(int irq, void *dev_id) |
98 | { | 94 | { |
99 | struct omap_kp *omap_kp = dev_id; | ||
100 | |||
101 | /* disable keyboard interrupt and schedule for handling */ | 95 | /* disable keyboard interrupt and schedule for handling */ |
102 | if (cpu_is_omap24xx()) { | 96 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); |
103 | int i; | ||
104 | |||
105 | for (i = 0; i < omap_kp->rows; i++) { | ||
106 | int gpio_irq = gpio_to_irq(row_gpios[i]); | ||
107 | /* | ||
108 | * The interrupt which we're currently handling should | ||
109 | * be disabled _nosync() to avoid deadlocks waiting | ||
110 | * for this handler to complete. All others should | ||
111 | * be disabled the regular way for SMP safety. | ||
112 | */ | ||
113 | if (gpio_irq == irq) | ||
114 | disable_irq_nosync(gpio_irq); | ||
115 | else | ||
116 | disable_irq(gpio_irq); | ||
117 | } | ||
118 | } else | ||
119 | /* disable keyboard interrupt and schedule for handling */ | ||
120 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); | ||
121 | 97 | ||
122 | tasklet_schedule(&kp_tasklet); | 98 | tasklet_schedule(&kp_tasklet); |
123 | 99 | ||
@@ -133,33 +109,22 @@ static void omap_kp_scan_keypad(struct omap_kp *omap_kp, unsigned char *state) | |||
133 | { | 109 | { |
134 | int col = 0; | 110 | int col = 0; |
135 | 111 | ||
136 | /* read the keypad status */ | 112 | /* disable keyboard interrupt and schedule for handling */ |
137 | if (cpu_is_omap24xx()) { | 113 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); |
138 | /* read the keypad status */ | ||
139 | for (col = 0; col < omap_kp->cols; col++) { | ||
140 | set_col_gpio_val(omap_kp, ~(1 << col)); | ||
141 | state[col] = ~(get_row_gpio_val(omap_kp)) & 0xff; | ||
142 | } | ||
143 | set_col_gpio_val(omap_kp, 0); | ||
144 | |||
145 | } else { | ||
146 | /* disable keyboard interrupt and schedule for handling */ | ||
147 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); | ||
148 | 114 | ||
149 | /* read the keypad status */ | 115 | /* read the keypad status */ |
150 | omap_writew(0xff, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBC); | 116 | omap_writew(0xff, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBC); |
151 | for (col = 0; col < omap_kp->cols; col++) { | 117 | for (col = 0; col < omap_kp->cols; col++) { |
152 | omap_writew(~(1 << col) & 0xff, | 118 | omap_writew(~(1 << col) & 0xff, |
153 | OMAP1_MPUIO_BASE + OMAP_MPUIO_KBC); | 119 | OMAP1_MPUIO_BASE + OMAP_MPUIO_KBC); |
154 | 120 | ||
155 | udelay(omap_kp->delay); | 121 | udelay(omap_kp->delay); |
156 | 122 | ||
157 | state[col] = ~omap_readw(OMAP1_MPUIO_BASE + | 123 | state[col] = ~omap_readw(OMAP1_MPUIO_BASE + |
158 | OMAP_MPUIO_KBR_LATCH) & 0xff; | 124 | OMAP_MPUIO_KBR_LATCH) & 0xff; |
159 | } | ||
160 | omap_writew(0x00, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBC); | ||
161 | udelay(2); | ||
162 | } | 125 | } |
126 | omap_writew(0x00, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBC); | ||
127 | udelay(2); | ||
163 | } | 128 | } |
164 | 129 | ||
165 | static void omap_kp_tasklet(unsigned long data) | 130 | static void omap_kp_tasklet(unsigned long data) |
@@ -222,14 +187,8 @@ static void omap_kp_tasklet(unsigned long data) | |||
222 | mod_timer(&omap_kp_data->timer, jiffies + delay); | 187 | mod_timer(&omap_kp_data->timer, jiffies + delay); |
223 | } else { | 188 | } else { |
224 | /* enable interrupts */ | 189 | /* enable interrupts */ |
225 | if (cpu_is_omap24xx()) { | 190 | omap_writew(0, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); |
226 | int i; | 191 | kp_cur_group = -1; |
227 | for (i = 0; i < omap_kp_data->rows; i++) | ||
228 | enable_irq(gpio_to_irq(row_gpios[i])); | ||
229 | } else { | ||
230 | omap_writew(0, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); | ||
231 | kp_cur_group = -1; | ||
232 | } | ||
233 | } | 192 | } |
234 | } | 193 | } |
235 | 194 | ||
@@ -242,6 +201,7 @@ static ssize_t omap_kp_enable_show(struct device *dev, | |||
242 | static ssize_t omap_kp_enable_store(struct device *dev, struct device_attribute *attr, | 201 | static ssize_t omap_kp_enable_store(struct device *dev, struct device_attribute *attr, |
243 | const char *buf, size_t count) | 202 | const char *buf, size_t count) |
244 | { | 203 | { |
204 | struct omap_kp *omap_kp = dev_get_drvdata(dev); | ||
245 | int state; | 205 | int state; |
246 | 206 | ||
247 | if (sscanf(buf, "%u", &state) != 1) | 207 | if (sscanf(buf, "%u", &state) != 1) |
@@ -253,9 +213,9 @@ static ssize_t omap_kp_enable_store(struct device *dev, struct device_attribute | |||
253 | mutex_lock(&kp_enable_mutex); | 213 | mutex_lock(&kp_enable_mutex); |
254 | if (state != kp_enable) { | 214 | if (state != kp_enable) { |
255 | if (state) | 215 | if (state) |
256 | enable_irq(INT_KEYBOARD); | 216 | enable_irq(omap_kp->irq); |
257 | else | 217 | else |
258 | disable_irq(INT_KEYBOARD); | 218 | disable_irq(omap_kp->irq); |
259 | kp_enable = state; | 219 | kp_enable = state; |
260 | } | 220 | } |
261 | mutex_unlock(&kp_enable_mutex); | 221 | mutex_unlock(&kp_enable_mutex); |
@@ -289,7 +249,7 @@ static int __devinit omap_kp_probe(struct platform_device *pdev) | |||
289 | struct omap_kp *omap_kp; | 249 | struct omap_kp *omap_kp; |
290 | struct input_dev *input_dev; | 250 | struct input_dev *input_dev; |
291 | struct omap_kp_platform_data *pdata = pdev->dev.platform_data; | 251 | struct omap_kp_platform_data *pdata = pdev->dev.platform_data; |
292 | int i, col_idx, row_idx, irq_idx, ret; | 252 | int i, col_idx, row_idx, ret; |
293 | unsigned int row_shift, keycodemax; | 253 | unsigned int row_shift, keycodemax; |
294 | 254 | ||
295 | if (!pdata->rows || !pdata->cols || !pdata->keymap_data) { | 255 | if (!pdata->rows || !pdata->cols || !pdata->keymap_data) { |
@@ -314,8 +274,7 @@ static int __devinit omap_kp_probe(struct platform_device *pdev) | |||
314 | omap_kp->input = input_dev; | 274 | omap_kp->input = input_dev; |
315 | 275 | ||
316 | /* Disable the interrupt for the MPUIO keyboard */ | 276 | /* Disable the interrupt for the MPUIO keyboard */ |
317 | if (!cpu_is_omap24xx()) | 277 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); |
318 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); | ||
319 | 278 | ||
320 | if (pdata->delay) | 279 | if (pdata->delay) |
321 | omap_kp->delay = pdata->delay; | 280 | omap_kp->delay = pdata->delay; |
@@ -328,31 +287,8 @@ static int __devinit omap_kp_probe(struct platform_device *pdev) | |||
328 | omap_kp->rows = pdata->rows; | 287 | omap_kp->rows = pdata->rows; |
329 | omap_kp->cols = pdata->cols; | 288 | omap_kp->cols = pdata->cols; |
330 | 289 | ||
331 | if (cpu_is_omap24xx()) { | 290 | col_idx = 0; |
332 | /* Cols: outputs */ | 291 | row_idx = 0; |
333 | for (col_idx = 0; col_idx < omap_kp->cols; col_idx++) { | ||
334 | if (gpio_request(col_gpios[col_idx], "omap_kp_col") < 0) { | ||
335 | printk(KERN_ERR "Failed to request" | ||
336 | "GPIO%d for keypad\n", | ||
337 | col_gpios[col_idx]); | ||
338 | goto err1; | ||
339 | } | ||
340 | gpio_direction_output(col_gpios[col_idx], 0); | ||
341 | } | ||
342 | /* Rows: inputs */ | ||
343 | for (row_idx = 0; row_idx < omap_kp->rows; row_idx++) { | ||
344 | if (gpio_request(row_gpios[row_idx], "omap_kp_row") < 0) { | ||
345 | printk(KERN_ERR "Failed to request" | ||
346 | "GPIO%d for keypad\n", | ||
347 | row_gpios[row_idx]); | ||
348 | goto err2; | ||
349 | } | ||
350 | gpio_direction_input(row_gpios[row_idx]); | ||
351 | } | ||
352 | } else { | ||
353 | col_idx = 0; | ||
354 | row_idx = 0; | ||
355 | } | ||
356 | 292 | ||
357 | setup_timer(&omap_kp->timer, omap_kp_timer, (unsigned long)omap_kp); | 293 | setup_timer(&omap_kp->timer, omap_kp_timer, (unsigned long)omap_kp); |
358 | 294 | ||
@@ -394,27 +330,16 @@ static int __devinit omap_kp_probe(struct platform_device *pdev) | |||
394 | 330 | ||
395 | /* scan current status and enable interrupt */ | 331 | /* scan current status and enable interrupt */ |
396 | omap_kp_scan_keypad(omap_kp, keypad_state); | 332 | omap_kp_scan_keypad(omap_kp, keypad_state); |
397 | if (!cpu_is_omap24xx()) { | 333 | omap_kp->irq = platform_get_irq(pdev, 0); |
398 | omap_kp->irq = platform_get_irq(pdev, 0); | 334 | if (omap_kp->irq >= 0) { |
399 | if (omap_kp->irq >= 0) { | 335 | if (request_irq(omap_kp->irq, omap_kp_interrupt, 0, |
400 | if (request_irq(omap_kp->irq, omap_kp_interrupt, 0, | 336 | "omap-keypad", omap_kp) < 0) |
401 | "omap-keypad", omap_kp) < 0) | 337 | goto err4; |
402 | goto err4; | ||
403 | } | ||
404 | omap_writew(0, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); | ||
405 | } else { | ||
406 | for (irq_idx = 0; irq_idx < omap_kp->rows; irq_idx++) { | ||
407 | if (request_irq(gpio_to_irq(row_gpios[irq_idx]), | ||
408 | omap_kp_interrupt, | ||
409 | IRQF_TRIGGER_FALLING, | ||
410 | "omap-keypad", omap_kp) < 0) | ||
411 | goto err5; | ||
412 | } | ||
413 | } | 338 | } |
339 | omap_writew(0, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); | ||
340 | |||
414 | return 0; | 341 | return 0; |
415 | err5: | 342 | |
416 | for (i = irq_idx - 1; i >= 0; i--) | ||
417 | free_irq(row_gpios[i], omap_kp); | ||
418 | err4: | 343 | err4: |
419 | input_unregister_device(omap_kp->input); | 344 | input_unregister_device(omap_kp->input); |
420 | input_dev = NULL; | 345 | input_dev = NULL; |
@@ -423,7 +348,6 @@ err3: | |||
423 | err2: | 348 | err2: |
424 | for (i = row_idx - 1; i >= 0; i--) | 349 | for (i = row_idx - 1; i >= 0; i--) |
425 | gpio_free(row_gpios[i]); | 350 | gpio_free(row_gpios[i]); |
426 | err1: | ||
427 | for (i = col_idx - 1; i >= 0; i--) | 351 | for (i = col_idx - 1; i >= 0; i--) |
428 | gpio_free(col_gpios[i]); | 352 | gpio_free(col_gpios[i]); |
429 | 353 | ||
@@ -439,18 +363,8 @@ static int __devexit omap_kp_remove(struct platform_device *pdev) | |||
439 | 363 | ||
440 | /* disable keypad interrupt handling */ | 364 | /* disable keypad interrupt handling */ |
441 | tasklet_disable(&kp_tasklet); | 365 | tasklet_disable(&kp_tasklet); |
442 | if (cpu_is_omap24xx()) { | 366 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); |
443 | int i; | 367 | free_irq(omap_kp->irq, omap_kp); |
444 | for (i = 0; i < omap_kp->cols; i++) | ||
445 | gpio_free(col_gpios[i]); | ||
446 | for (i = 0; i < omap_kp->rows; i++) { | ||
447 | gpio_free(row_gpios[i]); | ||
448 | free_irq(gpio_to_irq(row_gpios[i]), omap_kp); | ||
449 | } | ||
450 | } else { | ||
451 | omap_writew(1, OMAP1_MPUIO_BASE + OMAP_MPUIO_KBD_MASKIT); | ||
452 | free_irq(omap_kp->irq, omap_kp); | ||
453 | } | ||
454 | 368 | ||
455 | del_timer_sync(&omap_kp->timer); | 369 | del_timer_sync(&omap_kp->timer); |
456 | tasklet_kill(&kp_tasklet); | 370 | tasklet_kill(&kp_tasklet); |
diff --git a/drivers/input/keyboard/pxa27x_keypad.c b/drivers/input/keyboard/pxa27x_keypad.c index 7f7b72464a37..803ff6fe021e 100644 --- a/drivers/input/keyboard/pxa27x_keypad.c +++ b/drivers/input/keyboard/pxa27x_keypad.c | |||
@@ -32,7 +32,7 @@ | |||
32 | #include <asm/mach/map.h> | 32 | #include <asm/mach/map.h> |
33 | 33 | ||
34 | #include <mach/hardware.h> | 34 | #include <mach/hardware.h> |
35 | #include <plat/pxa27x_keypad.h> | 35 | #include <linux/platform_data/keypad-pxa27x.h> |
36 | /* | 36 | /* |
37 | * Keypad Controller registers | 37 | * Keypad Controller registers |
38 | */ | 38 | */ |
diff --git a/drivers/input/keyboard/pxa930_rotary.c b/drivers/input/keyboard/pxa930_rotary.c index d7f1134b789e..41488f9add20 100644 --- a/drivers/input/keyboard/pxa930_rotary.c +++ b/drivers/input/keyboard/pxa930_rotary.c | |||
@@ -15,7 +15,7 @@ | |||
15 | #include <linux/io.h> | 15 | #include <linux/io.h> |
16 | #include <linux/slab.h> | 16 | #include <linux/slab.h> |
17 | 17 | ||
18 | #include <mach/pxa930_rotary.h> | 18 | #include <linux/platform_data/keyboard-pxa930_rotary.h> |
19 | 19 | ||
20 | #define SBCR (0x04) | 20 | #define SBCR (0x04) |
21 | #define ERCR (0x0c) | 21 | #define ERCR (0x0c) |
diff --git a/drivers/input/keyboard/qt2160.c b/drivers/input/keyboard/qt2160.c index 73ea4b04d4fb..031eed739903 100644 --- a/drivers/input/keyboard/qt2160.c +++ b/drivers/input/keyboard/qt2160.c | |||
@@ -156,8 +156,7 @@ static irqreturn_t qt2160_irq(int irq, void *_qt2160) | |||
156 | 156 | ||
157 | spin_lock_irqsave(&qt2160->lock, flags); | 157 | spin_lock_irqsave(&qt2160->lock, flags); |
158 | 158 | ||
159 | __cancel_delayed_work(&qt2160->dwork); | 159 | mod_delayed_work(system_wq, &qt2160->dwork, 0); |
160 | schedule_delayed_work(&qt2160->dwork, 0); | ||
161 | 160 | ||
162 | spin_unlock_irqrestore(&qt2160->lock, flags); | 161 | spin_unlock_irqrestore(&qt2160->lock, flags); |
163 | 162 | ||
diff --git a/drivers/input/keyboard/spear-keyboard.c b/drivers/input/keyboard/spear-keyboard.c index 72ef01be3360..c7ca97f44bfb 100644 --- a/drivers/input/keyboard/spear-keyboard.c +++ b/drivers/input/keyboard/spear-keyboard.c | |||
@@ -24,7 +24,7 @@ | |||
24 | #include <linux/pm_wakeup.h> | 24 | #include <linux/pm_wakeup.h> |
25 | #include <linux/slab.h> | 25 | #include <linux/slab.h> |
26 | #include <linux/types.h> | 26 | #include <linux/types.h> |
27 | #include <plat/keyboard.h> | 27 | #include <linux/platform_data/keyboard-spear.h> |
28 | 28 | ||
29 | /* Keyboard Registers */ | 29 | /* Keyboard Registers */ |
30 | #define MODE_CTL_REG 0x00 | 30 | #define MODE_CTL_REG 0x00 |
diff --git a/drivers/input/keyboard/w90p910_keypad.c b/drivers/input/keyboard/w90p910_keypad.c index 085ede4d972d..e0f6cd1ad0fd 100644 --- a/drivers/input/keyboard/w90p910_keypad.c +++ b/drivers/input/keyboard/w90p910_keypad.c | |||
@@ -21,7 +21,7 @@ | |||
21 | #include <linux/io.h> | 21 | #include <linux/io.h> |
22 | #include <linux/slab.h> | 22 | #include <linux/slab.h> |
23 | 23 | ||
24 | #include <mach/w90p910_keypad.h> | 24 | #include <linux/platform_data/keypad-w90p910.h> |
25 | 25 | ||
26 | /* Keypad Interface Control Registers */ | 26 | /* Keypad Interface Control Registers */ |
27 | #define KPI_CONF 0x00 | 27 | #define KPI_CONF 0x00 |
diff --git a/drivers/input/misc/ab8500-ponkey.c b/drivers/input/misc/ab8500-ponkey.c index f06231b7cab1..84ec691c05aa 100644 --- a/drivers/input/misc/ab8500-ponkey.c +++ b/drivers/input/misc/ab8500-ponkey.c | |||
@@ -74,8 +74,8 @@ static int __devinit ab8500_ponkey_probe(struct platform_device *pdev) | |||
74 | 74 | ||
75 | ponkey->idev = input; | 75 | ponkey->idev = input; |
76 | ponkey->ab8500 = ab8500; | 76 | ponkey->ab8500 = ab8500; |
77 | ponkey->irq_dbf = ab8500_irq_get_virq(ab8500, irq_dbf); | 77 | ponkey->irq_dbf = irq_dbf; |
78 | ponkey->irq_dbr = ab8500_irq_get_virq(ab8500, irq_dbr); | 78 | ponkey->irq_dbr = irq_dbr; |
79 | 79 | ||
80 | input->name = "AB8500 POn(PowerOn) Key"; | 80 | input->name = "AB8500 POn(PowerOn) Key"; |
81 | input->dev.parent = &pdev->dev; | 81 | input->dev.parent = &pdev->dev; |
diff --git a/drivers/input/misc/atlas_btns.c b/drivers/input/misc/atlas_btns.c index 601f7372f9c4..26f13131639a 100644 --- a/drivers/input/misc/atlas_btns.c +++ b/drivers/input/misc/atlas_btns.c | |||
@@ -151,22 +151,7 @@ static struct acpi_driver atlas_acpi_driver = { | |||
151 | .remove = atlas_acpi_button_remove, | 151 | .remove = atlas_acpi_button_remove, |
152 | }, | 152 | }, |
153 | }; | 153 | }; |
154 | 154 | module_acpi_driver(atlas_acpi_driver); | |
155 | static int __init atlas_acpi_init(void) | ||
156 | { | ||
157 | if (acpi_disabled) | ||
158 | return -ENODEV; | ||
159 | |||
160 | return acpi_bus_register_driver(&atlas_acpi_driver); | ||
161 | } | ||
162 | |||
163 | static void __exit atlas_acpi_exit(void) | ||
164 | { | ||
165 | acpi_bus_unregister_driver(&atlas_acpi_driver); | ||
166 | } | ||
167 | |||
168 | module_init(atlas_acpi_init); | ||
169 | module_exit(atlas_acpi_exit); | ||
170 | 155 | ||
171 | MODULE_AUTHOR("Jaya Kumar"); | 156 | MODULE_AUTHOR("Jaya Kumar"); |
172 | MODULE_LICENSE("GPL"); | 157 | MODULE_LICENSE("GPL"); |
diff --git a/drivers/input/misc/twl4030-vibra.c b/drivers/input/misc/twl4030-vibra.c index fc0ed9b43424..2194a3c7236a 100644 --- a/drivers/input/misc/twl4030-vibra.c +++ b/drivers/input/misc/twl4030-vibra.c | |||
@@ -26,6 +26,7 @@ | |||
26 | #include <linux/module.h> | 26 | #include <linux/module.h> |
27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
28 | #include <linux/platform_device.h> | 28 | #include <linux/platform_device.h> |
29 | #include <linux/of.h> | ||
29 | #include <linux/workqueue.h> | 30 | #include <linux/workqueue.h> |
30 | #include <linux/i2c/twl.h> | 31 | #include <linux/i2c/twl.h> |
31 | #include <linux/mfd/twl4030-audio.h> | 32 | #include <linux/mfd/twl4030-audio.h> |
@@ -194,13 +195,26 @@ static int twl4030_vibra_resume(struct device *dev) | |||
194 | static SIMPLE_DEV_PM_OPS(twl4030_vibra_pm_ops, | 195 | static SIMPLE_DEV_PM_OPS(twl4030_vibra_pm_ops, |
195 | twl4030_vibra_suspend, twl4030_vibra_resume); | 196 | twl4030_vibra_suspend, twl4030_vibra_resume); |
196 | 197 | ||
198 | static bool twl4030_vibra_check_coexist(struct twl4030_vibra_data *pdata, | ||
199 | struct device_node *node) | ||
200 | { | ||
201 | if (pdata && pdata->coexist) | ||
202 | return true; | ||
203 | |||
204 | if (of_find_node_by_name(node, "codec")) | ||
205 | return true; | ||
206 | |||
207 | return false; | ||
208 | } | ||
209 | |||
197 | static int __devinit twl4030_vibra_probe(struct platform_device *pdev) | 210 | static int __devinit twl4030_vibra_probe(struct platform_device *pdev) |
198 | { | 211 | { |
199 | struct twl4030_vibra_data *pdata = pdev->dev.platform_data; | 212 | struct twl4030_vibra_data *pdata = pdev->dev.platform_data; |
213 | struct device_node *twl4030_core_node = pdev->dev.parent->of_node; | ||
200 | struct vibra_info *info; | 214 | struct vibra_info *info; |
201 | int ret; | 215 | int ret; |
202 | 216 | ||
203 | if (!pdata) { | 217 | if (!pdata && !twl4030_core_node) { |
204 | dev_dbg(&pdev->dev, "platform_data not available\n"); | 218 | dev_dbg(&pdev->dev, "platform_data not available\n"); |
205 | return -EINVAL; | 219 | return -EINVAL; |
206 | } | 220 | } |
@@ -210,7 +224,7 @@ static int __devinit twl4030_vibra_probe(struct platform_device *pdev) | |||
210 | return -ENOMEM; | 224 | return -ENOMEM; |
211 | 225 | ||
212 | info->dev = &pdev->dev; | 226 | info->dev = &pdev->dev; |
213 | info->coexist = pdata->coexist; | 227 | info->coexist = twl4030_vibra_check_coexist(pdata, twl4030_core_node); |
214 | INIT_WORK(&info->play_work, vibra_play_work); | 228 | INIT_WORK(&info->play_work, vibra_play_work); |
215 | 229 | ||
216 | info->input_dev = input_allocate_device(); | 230 | info->input_dev = input_allocate_device(); |
diff --git a/drivers/input/mouse/pxa930_trkball.c b/drivers/input/mouse/pxa930_trkball.c index a9e4bfdf31f4..4fe055f2c536 100644 --- a/drivers/input/mouse/pxa930_trkball.c +++ b/drivers/input/mouse/pxa930_trkball.c | |||
@@ -20,7 +20,7 @@ | |||
20 | #include <linux/slab.h> | 20 | #include <linux/slab.h> |
21 | 21 | ||
22 | #include <mach/hardware.h> | 22 | #include <mach/hardware.h> |
23 | #include <mach/pxa930_trkball.h> | 23 | #include <linux/platform_data/mouse-pxa930_trkball.h> |
24 | 24 | ||
25 | /* Trackball Controller Register Definitions */ | 25 | /* Trackball Controller Register Definitions */ |
26 | #define TBCR (0x000C) | 26 | #define TBCR (0x000C) |
diff --git a/drivers/input/mouse/rpcmouse.c b/drivers/input/mouse/rpcmouse.c index 272deddc8db6..21c60fea5d31 100644 --- a/drivers/input/mouse/rpcmouse.c +++ b/drivers/input/mouse/rpcmouse.c | |||
@@ -42,7 +42,7 @@ static irqreturn_t rpcmouse_irq(int irq, void *dev_id) | |||
42 | 42 | ||
43 | x = (short) iomd_readl(IOMD_MOUSEX); | 43 | x = (short) iomd_readl(IOMD_MOUSEX); |
44 | y = (short) iomd_readl(IOMD_MOUSEY); | 44 | y = (short) iomd_readl(IOMD_MOUSEY); |
45 | b = (short) (__raw_readl(0xe0310000) ^ 0x70); | 45 | b = (short) (__raw_readl(IOMEM(0xe0310000)) ^ 0x70); |
46 | 46 | ||
47 | dx = x - rpcmouse_lastx; | 47 | dx = x - rpcmouse_lastx; |
48 | dy = y - rpcmouse_lasty; | 48 | dy = y - rpcmouse_lasty; |
diff --git a/drivers/input/mouse/sentelic.c b/drivers/input/mouse/sentelic.c index b47155d8bc8c..e582922bacf7 100644 --- a/drivers/input/mouse/sentelic.c +++ b/drivers/input/mouse/sentelic.c | |||
@@ -721,6 +721,17 @@ static psmouse_ret_t fsp_process_byte(struct psmouse *psmouse) | |||
721 | 721 | ||
722 | switch (psmouse->packet[0] >> FSP_PKT_TYPE_SHIFT) { | 722 | switch (psmouse->packet[0] >> FSP_PKT_TYPE_SHIFT) { |
723 | case FSP_PKT_TYPE_ABS: | 723 | case FSP_PKT_TYPE_ABS: |
724 | |||
725 | if ((packet[0] == 0x48 || packet[0] == 0x49) && | ||
726 | packet[1] == 0 && packet[2] == 0) { | ||
727 | /* | ||
728 | * Ignore coordinate noise when finger leaving the | ||
729 | * surface, otherwise cursor may jump to upper-left | ||
730 | * corner. | ||
731 | */ | ||
732 | packet[3] &= 0xf0; | ||
733 | } | ||
734 | |||
724 | abs_x = GET_ABS_X(packet); | 735 | abs_x = GET_ABS_X(packet); |
725 | abs_y = GET_ABS_Y(packet); | 736 | abs_y = GET_ABS_Y(packet); |
726 | 737 | ||
diff --git a/drivers/input/mouse/synaptics.c b/drivers/input/mouse/synaptics.c index 37033ade79d3..12d12ca3fee0 100644 --- a/drivers/input/mouse/synaptics.c +++ b/drivers/input/mouse/synaptics.c | |||
@@ -53,14 +53,19 @@ | |||
53 | #define ABS_POS_BITS 13 | 53 | #define ABS_POS_BITS 13 |
54 | 54 | ||
55 | /* | 55 | /* |
56 | * Any position values from the hardware above the following limits are | 56 | * These values should represent the absolute maximum value that will |
57 | * treated as "wrapped around negative" values that have been truncated to | 57 | * be reported for a positive position value. Some Synaptics firmware |
58 | * the 13-bit reporting range of the hardware. These are just reasonable | 58 | * uses this value to indicate a finger near the edge of the touchpad |
59 | * guesses and can be adjusted if hardware is found that operates outside | 59 | * whose precise position cannot be determined. |
60 | * of these parameters. | 60 | * |
61 | * At least one touchpad is known to report positions in excess of this | ||
62 | * value which are actually negative values truncated to the 13-bit | ||
63 | * reporting range. These values have never been observed to be lower | ||
64 | * than 8184 (i.e. -8), so we treat all values greater than 8176 as | ||
65 | * negative and any other value as positive. | ||
61 | */ | 66 | */ |
62 | #define X_MAX_POSITIVE (((1 << ABS_POS_BITS) + XMAX) / 2) | 67 | #define X_MAX_POSITIVE 8176 |
63 | #define Y_MAX_POSITIVE (((1 << ABS_POS_BITS) + YMAX) / 2) | 68 | #define Y_MAX_POSITIVE 8176 |
64 | 69 | ||
65 | /***************************************************************************** | 70 | /***************************************************************************** |
66 | * Stuff we need even when we do not want native Synaptics support | 71 | * Stuff we need even when we do not want native Synaptics support |
@@ -604,11 +609,21 @@ static int synaptics_parse_hw_state(const unsigned char buf[], | |||
604 | hw->right = (buf[0] & 0x02) ? 1 : 0; | 609 | hw->right = (buf[0] & 0x02) ? 1 : 0; |
605 | } | 610 | } |
606 | 611 | ||
607 | /* Convert wrap-around values to negative */ | 612 | /* |
613 | * Convert wrap-around values to negative. (X|Y)_MAX_POSITIVE | ||
614 | * is used by some firmware to indicate a finger at the edge of | ||
615 | * the touchpad whose precise position cannot be determined, so | ||
616 | * convert these values to the maximum axis value. | ||
617 | */ | ||
608 | if (hw->x > X_MAX_POSITIVE) | 618 | if (hw->x > X_MAX_POSITIVE) |
609 | hw->x -= 1 << ABS_POS_BITS; | 619 | hw->x -= 1 << ABS_POS_BITS; |
620 | else if (hw->x == X_MAX_POSITIVE) | ||
621 | hw->x = XMAX; | ||
622 | |||
610 | if (hw->y > Y_MAX_POSITIVE) | 623 | if (hw->y > Y_MAX_POSITIVE) |
611 | hw->y -= 1 << ABS_POS_BITS; | 624 | hw->y -= 1 << ABS_POS_BITS; |
625 | else if (hw->y == Y_MAX_POSITIVE) | ||
626 | hw->y = YMAX; | ||
612 | 627 | ||
613 | return 0; | 628 | return 0; |
614 | } | 629 | } |
diff --git a/drivers/input/mouse/synaptics_i2c.c b/drivers/input/mouse/synaptics_i2c.c index f14675702c0f..063a174d3a88 100644 --- a/drivers/input/mouse/synaptics_i2c.c +++ b/drivers/input/mouse/synaptics_i2c.c | |||
@@ -376,12 +376,7 @@ static void synaptics_i2c_reschedule_work(struct synaptics_i2c *touch, | |||
376 | 376 | ||
377 | spin_lock_irqsave(&touch->lock, flags); | 377 | spin_lock_irqsave(&touch->lock, flags); |
378 | 378 | ||
379 | /* | 379 | mod_delayed_work(system_wq, &touch->dwork, delay); |
380 | * If work is already scheduled then subsequent schedules will not | ||
381 | * change the scheduled time that's why we have to cancel it first. | ||
382 | */ | ||
383 | __cancel_delayed_work(&touch->dwork); | ||
384 | schedule_delayed_work(&touch->dwork, delay); | ||
385 | 380 | ||
386 | spin_unlock_irqrestore(&touch->lock, flags); | 381 | spin_unlock_irqrestore(&touch->lock, flags); |
387 | } | 382 | } |
diff --git a/drivers/input/mousedev.c b/drivers/input/mousedev.c index a1b4c37956b2..8f02e3d0e712 100644 --- a/drivers/input/mousedev.c +++ b/drivers/input/mousedev.c | |||
@@ -523,7 +523,6 @@ static int mousedev_release(struct inode *inode, struct file *file) | |||
523 | kfree(client); | 523 | kfree(client); |
524 | 524 | ||
525 | mousedev_close_device(mousedev); | 525 | mousedev_close_device(mousedev); |
526 | put_device(&mousedev->dev); | ||
527 | 526 | ||
528 | return 0; | 527 | return 0; |
529 | } | 528 | } |
@@ -558,7 +557,6 @@ static int mousedev_open(struct inode *inode, struct file *file) | |||
558 | file->private_data = client; | 557 | file->private_data = client; |
559 | nonseekable_open(inode, file); | 558 | nonseekable_open(inode, file); |
560 | 559 | ||
561 | get_device(&mousedev->dev); | ||
562 | return 0; | 560 | return 0; |
563 | 561 | ||
564 | err_free_client: | 562 | err_free_client: |
@@ -892,6 +890,7 @@ static struct mousedev *mousedev_create(struct input_dev *dev, | |||
892 | } | 890 | } |
893 | 891 | ||
894 | cdev_init(&mousedev->cdev, &mousedev_fops); | 892 | cdev_init(&mousedev->cdev, &mousedev_fops); |
893 | mousedev->cdev.kobj.parent = &mousedev->dev.kobj; | ||
895 | error = cdev_add(&mousedev->cdev, mousedev->dev.devt, 1); | 894 | error = cdev_add(&mousedev->cdev, mousedev->dev.devt, 1); |
896 | if (error) | 895 | if (error) |
897 | goto err_unregister_handle; | 896 | goto err_unregister_handle; |
diff --git a/drivers/input/serio/ambakmi.c b/drivers/input/serio/ambakmi.c index 2ffd110bd5bc..2e77246c2e5a 100644 --- a/drivers/input/serio/ambakmi.c +++ b/drivers/input/serio/ambakmi.c | |||
@@ -72,7 +72,7 @@ static int amba_kmi_open(struct serio *io) | |||
72 | unsigned int divisor; | 72 | unsigned int divisor; |
73 | int ret; | 73 | int ret; |
74 | 74 | ||
75 | ret = clk_enable(kmi->clk); | 75 | ret = clk_prepare_enable(kmi->clk); |
76 | if (ret) | 76 | if (ret) |
77 | goto out; | 77 | goto out; |
78 | 78 | ||
@@ -92,7 +92,7 @@ static int amba_kmi_open(struct serio *io) | |||
92 | return 0; | 92 | return 0; |
93 | 93 | ||
94 | clk_disable: | 94 | clk_disable: |
95 | clk_disable(kmi->clk); | 95 | clk_disable_unprepare(kmi->clk); |
96 | out: | 96 | out: |
97 | return ret; | 97 | return ret; |
98 | } | 98 | } |
@@ -104,7 +104,7 @@ static void amba_kmi_close(struct serio *io) | |||
104 | writeb(0, KMICR); | 104 | writeb(0, KMICR); |
105 | 105 | ||
106 | free_irq(kmi->irq, kmi); | 106 | free_irq(kmi->irq, kmi); |
107 | clk_disable(kmi->clk); | 107 | clk_disable_unprepare(kmi->clk); |
108 | } | 108 | } |
109 | 109 | ||
110 | static int __devinit amba_kmi_probe(struct amba_device *dev, | 110 | static int __devinit amba_kmi_probe(struct amba_device *dev, |
diff --git a/drivers/input/serio/ams_delta_serio.c b/drivers/input/serio/ams_delta_serio.c index f5fbdf94de3b..45887e31242a 100644 --- a/drivers/input/serio/ams_delta_serio.c +++ b/drivers/input/serio/ams_delta_serio.c | |||
@@ -27,7 +27,7 @@ | |||
27 | #include <linux/module.h> | 27 | #include <linux/module.h> |
28 | 28 | ||
29 | #include <asm/mach-types.h> | 29 | #include <asm/mach-types.h> |
30 | #include <plat/board-ams-delta.h> | 30 | #include <mach/board-ams-delta.h> |
31 | 31 | ||
32 | #include <mach/ams-delta-fiq.h> | 32 | #include <mach/ams-delta-fiq.h> |
33 | 33 | ||
diff --git a/drivers/input/serio/i8042-x86ia64io.h b/drivers/input/serio/i8042-x86ia64io.h index 5ec774d6c82b..d6cc77a53c7e 100644 --- a/drivers/input/serio/i8042-x86ia64io.h +++ b/drivers/input/serio/i8042-x86ia64io.h | |||
@@ -177,6 +177,20 @@ static const struct dmi_system_id __initconst i8042_dmi_noloop_table[] = { | |||
177 | }, | 177 | }, |
178 | }, | 178 | }, |
179 | { | 179 | { |
180 | /* Gigabyte T1005 - defines wrong chassis type ("Other") */ | ||
181 | .matches = { | ||
182 | DMI_MATCH(DMI_SYS_VENDOR, "GIGABYTE"), | ||
183 | DMI_MATCH(DMI_PRODUCT_NAME, "T1005"), | ||
184 | }, | ||
185 | }, | ||
186 | { | ||
187 | /* Gigabyte T1005M/P - defines wrong chassis type ("Other") */ | ||
188 | .matches = { | ||
189 | DMI_MATCH(DMI_SYS_VENDOR, "GIGABYTE"), | ||
190 | DMI_MATCH(DMI_PRODUCT_NAME, "T1005M/P"), | ||
191 | }, | ||
192 | }, | ||
193 | { | ||
180 | .matches = { | 194 | .matches = { |
181 | DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), | 195 | DMI_MATCH(DMI_SYS_VENDOR, "Hewlett-Packard"), |
182 | DMI_MATCH(DMI_PRODUCT_NAME, "HP Pavilion dv9700"), | 196 | DMI_MATCH(DMI_PRODUCT_NAME, "HP Pavilion dv9700"), |
@@ -321,6 +335,12 @@ static const struct dmi_system_id __initconst i8042_dmi_nomux_table[] = { | |||
321 | }, | 335 | }, |
322 | { | 336 | { |
323 | .matches = { | 337 | .matches = { |
338 | DMI_MATCH(DMI_SYS_VENDOR, "TOSHIBA"), | ||
339 | DMI_MATCH(DMI_PRODUCT_NAME, "SATELLITE C850D"), | ||
340 | }, | ||
341 | }, | ||
342 | { | ||
343 | .matches = { | ||
324 | DMI_MATCH(DMI_SYS_VENDOR, "ALIENWARE"), | 344 | DMI_MATCH(DMI_SYS_VENDOR, "ALIENWARE"), |
325 | DMI_MATCH(DMI_PRODUCT_NAME, "Sentia"), | 345 | DMI_MATCH(DMI_PRODUCT_NAME, "Sentia"), |
326 | }, | 346 | }, |
diff --git a/drivers/input/tablet/wacom_sys.c b/drivers/input/tablet/wacom_sys.c index 9edf9806cff9..2c1e12bf2ab4 100644 --- a/drivers/input/tablet/wacom_sys.c +++ b/drivers/input/tablet/wacom_sys.c | |||
@@ -391,7 +391,7 @@ static int wacom_parse_hid(struct usb_interface *intf, | |||
391 | features->pktlen = WACOM_PKGLEN_TPC2FG; | 391 | features->pktlen = WACOM_PKGLEN_TPC2FG; |
392 | } | 392 | } |
393 | 393 | ||
394 | if (features->type == MTSCREEN) | 394 | if (features->type == MTSCREEN || WACOM_24HDT) |
395 | features->pktlen = WACOM_PKGLEN_MTOUCH; | 395 | features->pktlen = WACOM_PKGLEN_MTOUCH; |
396 | 396 | ||
397 | if (features->type == BAMBOO_PT) { | 397 | if (features->type == BAMBOO_PT) { |
@@ -402,6 +402,14 @@ static int wacom_parse_hid(struct usb_interface *intf, | |||
402 | features->x_max = | 402 | features->x_max = |
403 | get_unaligned_le16(&report[i + 8]); | 403 | get_unaligned_le16(&report[i + 8]); |
404 | i += 15; | 404 | i += 15; |
405 | } else if (features->type == WACOM_24HDT) { | ||
406 | features->x_max = | ||
407 | get_unaligned_le16(&report[i + 3]); | ||
408 | features->x_phy = | ||
409 | get_unaligned_le16(&report[i + 8]); | ||
410 | features->unit = report[i - 1]; | ||
411 | features->unitExpo = report[i - 3]; | ||
412 | i += 12; | ||
405 | } else { | 413 | } else { |
406 | features->x_max = | 414 | features->x_max = |
407 | get_unaligned_le16(&report[i + 3]); | 415 | get_unaligned_le16(&report[i + 3]); |
@@ -434,6 +442,12 @@ static int wacom_parse_hid(struct usb_interface *intf, | |||
434 | features->y_phy = | 442 | features->y_phy = |
435 | get_unaligned_le16(&report[i + 6]); | 443 | get_unaligned_le16(&report[i + 6]); |
436 | i += 7; | 444 | i += 7; |
445 | } else if (type == WACOM_24HDT) { | ||
446 | features->y_max = | ||
447 | get_unaligned_le16(&report[i + 3]); | ||
448 | features->y_phy = | ||
449 | get_unaligned_le16(&report[i - 2]); | ||
450 | i += 7; | ||
437 | } else if (type == BAMBOO_PT) { | 451 | } else if (type == BAMBOO_PT) { |
438 | features->y_phy = | 452 | features->y_phy = |
439 | get_unaligned_le16(&report[i + 3]); | 453 | get_unaligned_le16(&report[i + 3]); |
@@ -541,6 +555,9 @@ static int wacom_query_tablet_data(struct usb_interface *intf, struct wacom_feat | |||
541 | /* MT Tablet PC touch */ | 555 | /* MT Tablet PC touch */ |
542 | return wacom_set_device_mode(intf, 3, 4, 4); | 556 | return wacom_set_device_mode(intf, 3, 4, 4); |
543 | } | 557 | } |
558 | else if (features->type == WACOM_24HDT) { | ||
559 | return wacom_set_device_mode(intf, 18, 3, 2); | ||
560 | } | ||
544 | } else if (features->device_type == BTN_TOOL_PEN) { | 561 | } else if (features->device_type == BTN_TOOL_PEN) { |
545 | if (features->type <= BAMBOO_PT && features->type != WIRELESS) { | 562 | if (features->type <= BAMBOO_PT && features->type != WIRELESS) { |
546 | return wacom_set_device_mode(intf, 2, 2, 2); | 563 | return wacom_set_device_mode(intf, 2, 2, 2); |
@@ -613,6 +630,30 @@ struct wacom_usbdev_data { | |||
613 | static LIST_HEAD(wacom_udev_list); | 630 | static LIST_HEAD(wacom_udev_list); |
614 | static DEFINE_MUTEX(wacom_udev_list_lock); | 631 | static DEFINE_MUTEX(wacom_udev_list_lock); |
615 | 632 | ||
633 | static struct usb_device *wacom_get_sibling(struct usb_device *dev, int vendor, int product) | ||
634 | { | ||
635 | int port1; | ||
636 | struct usb_device *sibling; | ||
637 | |||
638 | if (vendor == 0 && product == 0) | ||
639 | return dev; | ||
640 | |||
641 | if (dev->parent == NULL) | ||
642 | return NULL; | ||
643 | |||
644 | usb_hub_for_each_child(dev->parent, port1, sibling) { | ||
645 | struct usb_device_descriptor *d; | ||
646 | if (sibling == NULL) | ||
647 | continue; | ||
648 | |||
649 | d = &sibling->descriptor; | ||
650 | if (d->idVendor == vendor && d->idProduct == product) | ||
651 | return sibling; | ||
652 | } | ||
653 | |||
654 | return NULL; | ||
655 | } | ||
656 | |||
616 | static struct wacom_usbdev_data *wacom_get_usbdev_data(struct usb_device *dev) | 657 | static struct wacom_usbdev_data *wacom_get_usbdev_data(struct usb_device *dev) |
617 | { | 658 | { |
618 | struct wacom_usbdev_data *data; | 659 | struct wacom_usbdev_data *data; |
@@ -1257,13 +1298,19 @@ static int wacom_probe(struct usb_interface *intf, const struct usb_device_id *i | |||
1257 | strlcpy(wacom_wac->name, features->name, sizeof(wacom_wac->name)); | 1298 | strlcpy(wacom_wac->name, features->name, sizeof(wacom_wac->name)); |
1258 | 1299 | ||
1259 | if (features->quirks & WACOM_QUIRK_MULTI_INPUT) { | 1300 | if (features->quirks & WACOM_QUIRK_MULTI_INPUT) { |
1301 | struct usb_device *other_dev; | ||
1302 | |||
1260 | /* Append the device type to the name */ | 1303 | /* Append the device type to the name */ |
1261 | strlcat(wacom_wac->name, | 1304 | strlcat(wacom_wac->name, |
1262 | features->device_type == BTN_TOOL_PEN ? | 1305 | features->device_type == BTN_TOOL_PEN ? |
1263 | " Pen" : " Finger", | 1306 | " Pen" : " Finger", |
1264 | sizeof(wacom_wac->name)); | 1307 | sizeof(wacom_wac->name)); |
1265 | 1308 | ||
1266 | error = wacom_add_shared_data(wacom_wac, dev); | 1309 | |
1310 | other_dev = wacom_get_sibling(dev, features->oVid, features->oPid); | ||
1311 | if (other_dev == NULL || wacom_get_usbdev_data(other_dev) == NULL) | ||
1312 | other_dev = dev; | ||
1313 | error = wacom_add_shared_data(wacom_wac, other_dev); | ||
1267 | if (error) | 1314 | if (error) |
1268 | goto fail3; | 1315 | goto fail3; |
1269 | } | 1316 | } |
diff --git a/drivers/input/tablet/wacom_wac.c b/drivers/input/tablet/wacom_wac.c index b989bbfe0dc8..aa6010131179 100644 --- a/drivers/input/tablet/wacom_wac.c +++ b/drivers/input/tablet/wacom_wac.c | |||
@@ -611,7 +611,7 @@ static int wacom_intuos_irq(struct wacom_wac *wacom) | |||
611 | input_report_abs(input, ABS_WHEEL, 0); | 611 | input_report_abs(input, ABS_WHEEL, 0); |
612 | } | 612 | } |
613 | 613 | ||
614 | if (data[2] | (data[3] & 0x01) | data[4]) { | 614 | if (data[2] | (data[3] & 0x01) | data[4] | data[5]) { |
615 | input_report_key(input, wacom->tool[1], 1); | 615 | input_report_key(input, wacom->tool[1], 1); |
616 | input_report_abs(input, ABS_MISC, PAD_DEVICE_ID); | 616 | input_report_abs(input, ABS_MISC, PAD_DEVICE_ID); |
617 | } else { | 617 | } else { |
@@ -806,6 +806,70 @@ static int find_slot_from_contactid(struct wacom_wac *wacom, int contactid) | |||
806 | return -1; | 806 | return -1; |
807 | } | 807 | } |
808 | 808 | ||
809 | static int int_dist(int x1, int y1, int x2, int y2) | ||
810 | { | ||
811 | int x = x2 - x1; | ||
812 | int y = y2 - y1; | ||
813 | |||
814 | return int_sqrt(x*x + y*y); | ||
815 | } | ||
816 | |||
817 | static int wacom_24hdt_irq(struct wacom_wac *wacom) | ||
818 | { | ||
819 | struct input_dev *input = wacom->input; | ||
820 | char *data = wacom->data; | ||
821 | int i; | ||
822 | int current_num_contacts = data[61]; | ||
823 | int contacts_to_send = 0; | ||
824 | |||
825 | /* | ||
826 | * First packet resets the counter since only the first | ||
827 | * packet in series will have non-zero current_num_contacts. | ||
828 | */ | ||
829 | if (current_num_contacts) | ||
830 | wacom->num_contacts_left = current_num_contacts; | ||
831 | |||
832 | /* There are at most 4 contacts per packet */ | ||
833 | contacts_to_send = min(4, wacom->num_contacts_left); | ||
834 | |||
835 | for (i = 0; i < contacts_to_send; i++) { | ||
836 | int offset = (WACOM_BYTES_PER_24HDT_PACKET * i) + 1; | ||
837 | bool touch = data[offset] & 0x1 && !wacom->shared->stylus_in_proximity; | ||
838 | int id = data[offset + 1]; | ||
839 | int slot = find_slot_from_contactid(wacom, id); | ||
840 | |||
841 | if (slot < 0) | ||
842 | continue; | ||
843 | input_mt_slot(input, slot); | ||
844 | input_mt_report_slot_state(input, MT_TOOL_FINGER, touch); | ||
845 | |||
846 | if (touch) { | ||
847 | int t_x = le16_to_cpup((__le16 *)&data[offset + 2]); | ||
848 | int c_x = le16_to_cpup((__le16 *)&data[offset + 4]); | ||
849 | int t_y = le16_to_cpup((__le16 *)&data[offset + 6]); | ||
850 | int c_y = le16_to_cpup((__le16 *)&data[offset + 8]); | ||
851 | int w = le16_to_cpup((__le16 *)&data[offset + 10]); | ||
852 | int h = le16_to_cpup((__le16 *)&data[offset + 12]); | ||
853 | |||
854 | input_report_abs(input, ABS_MT_POSITION_X, t_x); | ||
855 | input_report_abs(input, ABS_MT_POSITION_Y, t_y); | ||
856 | input_report_abs(input, ABS_MT_TOUCH_MAJOR, min(w,h)); | ||
857 | input_report_abs(input, ABS_MT_WIDTH_MAJOR, min(w, h) + int_dist(t_x, t_y, c_x, c_y)); | ||
858 | input_report_abs(input, ABS_MT_WIDTH_MINOR, min(w, h)); | ||
859 | input_report_abs(input, ABS_MT_ORIENTATION, w > h); | ||
860 | } | ||
861 | wacom->slots[slot] = touch ? id : -1; | ||
862 | } | ||
863 | |||
864 | input_mt_report_pointer_emulation(input, true); | ||
865 | |||
866 | wacom->num_contacts_left -= contacts_to_send; | ||
867 | if (wacom->num_contacts_left <= 0) | ||
868 | wacom->num_contacts_left = 0; | ||
869 | |||
870 | return 1; | ||
871 | } | ||
872 | |||
809 | static int wacom_mt_touch(struct wacom_wac *wacom) | 873 | static int wacom_mt_touch(struct wacom_wac *wacom) |
810 | { | 874 | { |
811 | struct input_dev *input = wacom->input; | 875 | struct input_dev *input = wacom->input; |
@@ -1255,6 +1319,10 @@ void wacom_wac_irq(struct wacom_wac *wacom_wac, size_t len) | |||
1255 | sync = wacom_intuos_irq(wacom_wac); | 1319 | sync = wacom_intuos_irq(wacom_wac); |
1256 | break; | 1320 | break; |
1257 | 1321 | ||
1322 | case WACOM_24HDT: | ||
1323 | sync = wacom_24hdt_irq(wacom_wac); | ||
1324 | break; | ||
1325 | |||
1258 | case INTUOS5S: | 1326 | case INTUOS5S: |
1259 | case INTUOS5: | 1327 | case INTUOS5: |
1260 | case INTUOS5L: | 1328 | case INTUOS5L: |
@@ -1340,7 +1408,8 @@ void wacom_setup_device_quirks(struct wacom_features *features) | |||
1340 | 1408 | ||
1341 | /* these device have multiple inputs */ | 1409 | /* these device have multiple inputs */ |
1342 | if (features->type >= WIRELESS || | 1410 | if (features->type >= WIRELESS || |
1343 | (features->type >= INTUOS5S && features->type <= INTUOS5L)) | 1411 | (features->type >= INTUOS5S && features->type <= INTUOS5L) || |
1412 | (features->oVid && features->oPid)) | ||
1344 | features->quirks |= WACOM_QUIRK_MULTI_INPUT; | 1413 | features->quirks |= WACOM_QUIRK_MULTI_INPUT; |
1345 | 1414 | ||
1346 | /* quirk for bamboo touch with 2 low res touches */ | 1415 | /* quirk for bamboo touch with 2 low res touches */ |
@@ -1575,6 +1644,15 @@ int wacom_setup_input_capabilities(struct input_dev *input_dev, | |||
1575 | __set_bit(INPUT_PROP_POINTER, input_dev->propbit); | 1644 | __set_bit(INPUT_PROP_POINTER, input_dev->propbit); |
1576 | break; | 1645 | break; |
1577 | 1646 | ||
1647 | case WACOM_24HDT: | ||
1648 | if (features->device_type == BTN_TOOL_FINGER) { | ||
1649 | input_set_abs_params(input_dev, ABS_MT_TOUCH_MAJOR, 0, features->x_max, 0, 0); | ||
1650 | input_set_abs_params(input_dev, ABS_MT_WIDTH_MAJOR, 0, features->x_max, 0, 0); | ||
1651 | input_set_abs_params(input_dev, ABS_MT_WIDTH_MINOR, 0, features->y_max, 0, 0); | ||
1652 | input_set_abs_params(input_dev, ABS_MT_ORIENTATION, 0, 1, 0, 0); | ||
1653 | } | ||
1654 | /* fall through */ | ||
1655 | |||
1578 | case MTSCREEN: | 1656 | case MTSCREEN: |
1579 | if (features->device_type == BTN_TOOL_FINGER) { | 1657 | if (features->device_type == BTN_TOOL_FINGER) { |
1580 | wacom_wac->slots = kmalloc(features->touch_max * | 1658 | wacom_wac->slots = kmalloc(features->touch_max * |
@@ -1869,8 +1947,11 @@ static const struct wacom_features wacom_features_0xF4 = | |||
1869 | { "Wacom Cintiq 24HD", WACOM_PKGLEN_INTUOS, 104480, 65600, 2047, | 1947 | { "Wacom Cintiq 24HD", WACOM_PKGLEN_INTUOS, 104480, 65600, 2047, |
1870 | 63, WACOM_24HD, WACOM_INTUOS3_RES, WACOM_INTUOS3_RES }; | 1948 | 63, WACOM_24HD, WACOM_INTUOS3_RES, WACOM_INTUOS3_RES }; |
1871 | static const struct wacom_features wacom_features_0xF8 = | 1949 | static const struct wacom_features wacom_features_0xF8 = |
1872 | { "Wacom Cintiq 24HD touch", WACOM_PKGLEN_INTUOS, 104480, 65600, 2047, | 1950 | { "Wacom Cintiq 24HD touch", WACOM_PKGLEN_INTUOS, 104480, 65600, 2047, /* Pen */ |
1873 | 63, WACOM_24HD, WACOM_INTUOS3_RES, WACOM_INTUOS3_RES }; | 1951 | 63, WACOM_24HD, WACOM_INTUOS3_RES, WACOM_INTUOS3_RES, .oVid = USB_VENDOR_ID_WACOM, .oPid = 0xf6 }; |
1952 | static const struct wacom_features wacom_features_0xF6 = | ||
1953 | { "Wacom Cintiq 24HD touch", .type = WACOM_24HDT, /* Touch */ | ||
1954 | .oVid = USB_VENDOR_ID_WACOM, .oPid = 0xf8, .touch_max = 10 }; | ||
1874 | static const struct wacom_features wacom_features_0x3F = | 1955 | static const struct wacom_features wacom_features_0x3F = |
1875 | { "Wacom Cintiq 21UX", WACOM_PKGLEN_INTUOS, 87200, 65600, 1023, | 1956 | { "Wacom Cintiq 21UX", WACOM_PKGLEN_INTUOS, 87200, 65600, 1023, |
1876 | 63, CINTIQ, WACOM_INTUOS3_RES, WACOM_INTUOS3_RES }; | 1957 | 63, CINTIQ, WACOM_INTUOS3_RES, WACOM_INTUOS3_RES }; |
@@ -2113,6 +2194,7 @@ const struct usb_device_id wacom_ids[] = { | |||
2113 | { USB_DEVICE_WACOM(0x47) }, | 2194 | { USB_DEVICE_WACOM(0x47) }, |
2114 | { USB_DEVICE_WACOM(0xF4) }, | 2195 | { USB_DEVICE_WACOM(0xF4) }, |
2115 | { USB_DEVICE_WACOM(0xF8) }, | 2196 | { USB_DEVICE_WACOM(0xF8) }, |
2197 | { USB_DEVICE_WACOM(0xF6) }, | ||
2116 | { USB_DEVICE_WACOM(0xFA) }, | 2198 | { USB_DEVICE_WACOM(0xFA) }, |
2117 | { USB_DEVICE_LENOVO(0x6004) }, | 2199 | { USB_DEVICE_LENOVO(0x6004) }, |
2118 | { } | 2200 | { } |
diff --git a/drivers/input/tablet/wacom_wac.h b/drivers/input/tablet/wacom_wac.h index 96c185cc301e..345f1e76975e 100644 --- a/drivers/input/tablet/wacom_wac.h +++ b/drivers/input/tablet/wacom_wac.h | |||
@@ -29,6 +29,7 @@ | |||
29 | 29 | ||
30 | /* wacom data size per MT contact */ | 30 | /* wacom data size per MT contact */ |
31 | #define WACOM_BYTES_PER_MT_PACKET 11 | 31 | #define WACOM_BYTES_PER_MT_PACKET 11 |
32 | #define WACOM_BYTES_PER_24HDT_PACKET 14 | ||
32 | 33 | ||
33 | /* device IDs */ | 34 | /* device IDs */ |
34 | #define STYLUS_DEVICE_ID 0x02 | 35 | #define STYLUS_DEVICE_ID 0x02 |
@@ -49,6 +50,7 @@ | |||
49 | #define WACOM_REPORT_TPCHID 15 | 50 | #define WACOM_REPORT_TPCHID 15 |
50 | #define WACOM_REPORT_TPCST 16 | 51 | #define WACOM_REPORT_TPCST 16 |
51 | #define WACOM_REPORT_TPC1FGE 18 | 52 | #define WACOM_REPORT_TPC1FGE 18 |
53 | #define WACOM_REPORT_24HDT 1 | ||
52 | 54 | ||
53 | /* device quirks */ | 55 | /* device quirks */ |
54 | #define WACOM_QUIRK_MULTI_INPUT 0x0001 | 56 | #define WACOM_QUIRK_MULTI_INPUT 0x0001 |
@@ -81,6 +83,7 @@ enum { | |||
81 | WACOM_MO, | 83 | WACOM_MO, |
82 | WIRELESS, | 84 | WIRELESS, |
83 | BAMBOO_PT, | 85 | BAMBOO_PT, |
86 | WACOM_24HDT, | ||
84 | TABLETPC, /* add new TPC below */ | 87 | TABLETPC, /* add new TPC below */ |
85 | TABLETPCE, | 88 | TABLETPCE, |
86 | TABLETPC2FG, | 89 | TABLETPC2FG, |
@@ -109,6 +112,8 @@ struct wacom_features { | |||
109 | int distance_fuzz; | 112 | int distance_fuzz; |
110 | unsigned quirks; | 113 | unsigned quirks; |
111 | unsigned touch_max; | 114 | unsigned touch_max; |
115 | int oVid; | ||
116 | int oPid; | ||
112 | }; | 117 | }; |
113 | 118 | ||
114 | struct wacom_shared { | 119 | struct wacom_shared { |
diff --git a/drivers/input/touchscreen/88pm860x-ts.c b/drivers/input/touchscreen/88pm860x-ts.c index 05f30b73c3c3..326218dbd6e6 100644 --- a/drivers/input/touchscreen/88pm860x-ts.c +++ b/drivers/input/touchscreen/88pm860x-ts.c | |||
@@ -10,6 +10,7 @@ | |||
10 | */ | 10 | */ |
11 | #include <linux/kernel.h> | 11 | #include <linux/kernel.h> |
12 | #include <linux/module.h> | 12 | #include <linux/module.h> |
13 | #include <linux/of.h> | ||
13 | #include <linux/platform_device.h> | 14 | #include <linux/platform_device.h> |
14 | #include <linux/i2c.h> | 15 | #include <linux/i2c.h> |
15 | #include <linux/input.h> | 16 | #include <linux/input.h> |
@@ -113,14 +114,69 @@ static void pm860x_touch_close(struct input_dev *dev) | |||
113 | pm860x_set_bits(touch->i2c, MEAS_EN3, data, 0); | 114 | pm860x_set_bits(touch->i2c, MEAS_EN3, data, 0); |
114 | } | 115 | } |
115 | 116 | ||
117 | #ifdef CONFIG_OF | ||
118 | static int __devinit pm860x_touch_dt_init(struct platform_device *pdev, | ||
119 | struct pm860x_chip *chip, | ||
120 | int *res_x) | ||
121 | { | ||
122 | struct device_node *np = pdev->dev.parent->of_node; | ||
123 | struct i2c_client *i2c = (chip->id == CHIP_PM8607) ? chip->client \ | ||
124 | : chip->companion; | ||
125 | int data, n, ret; | ||
126 | if (!np) | ||
127 | return -ENODEV; | ||
128 | np = of_find_node_by_name(np, "touch"); | ||
129 | if (!np) { | ||
130 | dev_err(&pdev->dev, "Can't find touch node\n"); | ||
131 | return -EINVAL; | ||
132 | } | ||
133 | /* set GPADC MISC1 register */ | ||
134 | data = 0; | ||
135 | if (!of_property_read_u32(np, "marvell,88pm860x-gpadc-prebias", &n)) | ||
136 | data |= (n << 1) & PM8607_GPADC_PREBIAS_MASK; | ||
137 | if (!of_property_read_u32(np, "marvell,88pm860x-gpadc-slot-cycle", &n)) | ||
138 | data |= (n << 3) & PM8607_GPADC_SLOT_CYCLE_MASK; | ||
139 | if (!of_property_read_u32(np, "marvell,88pm860x-gpadc-off-scale", &n)) | ||
140 | data |= (n << 5) & PM8607_GPADC_OFF_SCALE_MASK; | ||
141 | if (!of_property_read_u32(np, "marvell,88pm860x-gpadc-sw-cal", &n)) | ||
142 | data |= (n << 7) & PM8607_GPADC_SW_CAL_MASK; | ||
143 | if (data) { | ||
144 | ret = pm860x_reg_write(i2c, PM8607_GPADC_MISC1, data); | ||
145 | if (ret < 0) | ||
146 | return -EINVAL; | ||
147 | } | ||
148 | /* set tsi prebias time */ | ||
149 | if (!of_property_read_u32(np, "marvell,88pm860x-tsi-prebias", &data)) { | ||
150 | ret = pm860x_reg_write(i2c, PM8607_TSI_PREBIAS, data); | ||
151 | if (ret < 0) | ||
152 | return -EINVAL; | ||
153 | } | ||
154 | /* set prebias & prechg time of pen detect */ | ||
155 | data = 0; | ||
156 | if (!of_property_read_u32(np, "marvell,88pm860x-pen-prebias", &n)) | ||
157 | data |= n & PM8607_PD_PREBIAS_MASK; | ||
158 | if (!of_property_read_u32(np, "marvell,88pm860x-pen-prechg", &n)) | ||
159 | data |= n & PM8607_PD_PRECHG_MASK; | ||
160 | if (data) { | ||
161 | ret = pm860x_reg_write(i2c, PM8607_PD_PREBIAS, data); | ||
162 | if (ret < 0) | ||
163 | return -EINVAL; | ||
164 | } | ||
165 | of_property_read_u32(np, "marvell,88pm860x-resistor-X", res_x); | ||
166 | return 0; | ||
167 | } | ||
168 | #else | ||
169 | #define pm860x_touch_dt_init(x, y, z) (-1) | ||
170 | #endif | ||
171 | |||
116 | static int __devinit pm860x_touch_probe(struct platform_device *pdev) | 172 | static int __devinit pm860x_touch_probe(struct platform_device *pdev) |
117 | { | 173 | { |
118 | struct pm860x_chip *chip = dev_get_drvdata(pdev->dev.parent); | 174 | struct pm860x_chip *chip = dev_get_drvdata(pdev->dev.parent); |
119 | struct pm860x_platform_data *pm860x_pdata = \ | 175 | struct pm860x_touch_pdata *pdata = pdev->dev.platform_data; |
120 | pdev->dev.parent->platform_data; | ||
121 | struct pm860x_touch_pdata *pdata = NULL; | ||
122 | struct pm860x_touch *touch; | 176 | struct pm860x_touch *touch; |
123 | int irq, ret; | 177 | struct i2c_client *i2c = (chip->id == CHIP_PM8607) ? chip->client \ |
178 | : chip->companion; | ||
179 | int irq, ret, res_x = 0, data = 0; | ||
124 | 180 | ||
125 | irq = platform_get_irq(pdev, 0); | 181 | irq = platform_get_irq(pdev, 0); |
126 | if (irq < 0) { | 182 | if (irq < 0) { |
@@ -128,16 +184,55 @@ static int __devinit pm860x_touch_probe(struct platform_device *pdev) | |||
128 | return -EINVAL; | 184 | return -EINVAL; |
129 | } | 185 | } |
130 | 186 | ||
131 | if (!pm860x_pdata) { | 187 | if (pm860x_touch_dt_init(pdev, chip, &res_x)) { |
132 | dev_err(&pdev->dev, "platform data is missing\n"); | 188 | if (pdata) { |
133 | return -EINVAL; | 189 | /* set GPADC MISC1 register */ |
134 | } | 190 | data = 0; |
135 | 191 | data |= (pdata->gpadc_prebias << 1) | |
136 | pdata = pm860x_pdata->touch; | 192 | & PM8607_GPADC_PREBIAS_MASK; |
137 | if (!pdata) { | 193 | data |= (pdata->slot_cycle << 3) |
138 | dev_err(&pdev->dev, "touchscreen data is missing\n"); | 194 | & PM8607_GPADC_SLOT_CYCLE_MASK; |
139 | return -EINVAL; | 195 | data |= (pdata->off_scale << 5) |
196 | & PM8607_GPADC_OFF_SCALE_MASK; | ||
197 | data |= (pdata->sw_cal << 7) | ||
198 | & PM8607_GPADC_SW_CAL_MASK; | ||
199 | if (data) { | ||
200 | ret = pm860x_reg_write(i2c, | ||
201 | PM8607_GPADC_MISC1, data); | ||
202 | if (ret < 0) | ||
203 | return -EINVAL; | ||
204 | } | ||
205 | /* set tsi prebias time */ | ||
206 | if (pdata->tsi_prebias) { | ||
207 | data = pdata->tsi_prebias; | ||
208 | ret = pm860x_reg_write(i2c, | ||
209 | PM8607_TSI_PREBIAS, data); | ||
210 | if (ret < 0) | ||
211 | return -EINVAL; | ||
212 | } | ||
213 | /* set prebias & prechg time of pen detect */ | ||
214 | data = 0; | ||
215 | data |= pdata->pen_prebias | ||
216 | & PM8607_PD_PREBIAS_MASK; | ||
217 | data |= (pdata->pen_prechg << 5) | ||
218 | & PM8607_PD_PRECHG_MASK; | ||
219 | if (data) { | ||
220 | ret = pm860x_reg_write(i2c, | ||
221 | PM8607_PD_PREBIAS, data); | ||
222 | if (ret < 0) | ||
223 | return -EINVAL; | ||
224 | } | ||
225 | res_x = pdata->res_x; | ||
226 | } else { | ||
227 | dev_err(&pdev->dev, "failed to get platform data\n"); | ||
228 | return -EINVAL; | ||
229 | } | ||
140 | } | 230 | } |
231 | /* enable GPADC */ | ||
232 | ret = pm860x_set_bits(i2c, PM8607_GPADC_MISC1, PM8607_GPADC_EN, | ||
233 | PM8607_GPADC_EN); | ||
234 | if (ret) | ||
235 | return ret; | ||
141 | 236 | ||
142 | touch = kzalloc(sizeof(struct pm860x_touch), GFP_KERNEL); | 237 | touch = kzalloc(sizeof(struct pm860x_touch), GFP_KERNEL); |
143 | if (touch == NULL) | 238 | if (touch == NULL) |
@@ -158,9 +253,9 @@ static int __devinit pm860x_touch_probe(struct platform_device *pdev) | |||
158 | touch->idev->open = pm860x_touch_open; | 253 | touch->idev->open = pm860x_touch_open; |
159 | touch->idev->close = pm860x_touch_close; | 254 | touch->idev->close = pm860x_touch_close; |
160 | touch->chip = chip; | 255 | touch->chip = chip; |
161 | touch->i2c = (chip->id == CHIP_PM8607) ? chip->client : chip->companion; | 256 | touch->i2c = i2c; |
162 | touch->irq = irq + chip->irq_base; | 257 | touch->irq = irq; |
163 | touch->res_x = pdata->res_x; | 258 | touch->res_x = res_x; |
164 | input_set_drvdata(touch->idev, touch); | 259 | input_set_drvdata(touch->idev, touch); |
165 | 260 | ||
166 | ret = request_threaded_irq(touch->irq, NULL, pm860x_touch_handler, | 261 | ret = request_threaded_irq(touch->irq, NULL, pm860x_touch_handler, |
diff --git a/drivers/input/touchscreen/edt-ft5x06.c b/drivers/input/touchscreen/edt-ft5x06.c index bcaea7a5e02b..d9c6007e445f 100644 --- a/drivers/input/touchscreen/edt-ft5x06.c +++ b/drivers/input/touchscreen/edt-ft5x06.c | |||
@@ -558,9 +558,12 @@ static ssize_t edt_ft5x06_debugfs_raw_data_read(struct file *file, | |||
558 | } | 558 | } |
559 | 559 | ||
560 | read = min_t(size_t, count, tsdata->raw_bufsize - *off); | 560 | read = min_t(size_t, count, tsdata->raw_bufsize - *off); |
561 | error = copy_to_user(buf, tsdata->raw_buffer + *off, read); | 561 | if (copy_to_user(buf, tsdata->raw_buffer + *off, read)) { |
562 | if (!error) | 562 | error = -EFAULT; |
563 | *off += read; | 563 | goto out; |
564 | } | ||
565 | |||
566 | *off += read; | ||
564 | out: | 567 | out: |
565 | mutex_unlock(&tsdata->mutex); | 568 | mutex_unlock(&tsdata->mutex); |
566 | return error ?: read; | 569 | return error ?: read; |
@@ -594,6 +597,7 @@ edt_ft5x06_ts_teardown_debugfs(struct edt_ft5x06_ts_data *tsdata) | |||
594 | { | 597 | { |
595 | if (tsdata->debug_dir) | 598 | if (tsdata->debug_dir) |
596 | debugfs_remove_recursive(tsdata->debug_dir); | 599 | debugfs_remove_recursive(tsdata->debug_dir); |
600 | kfree(tsdata->raw_buffer); | ||
597 | } | 601 | } |
598 | 602 | ||
599 | #else | 603 | #else |
@@ -835,7 +839,6 @@ static int __devexit edt_ft5x06_ts_remove(struct i2c_client *client) | |||
835 | if (gpio_is_valid(pdata->reset_pin)) | 839 | if (gpio_is_valid(pdata->reset_pin)) |
836 | gpio_free(pdata->reset_pin); | 840 | gpio_free(pdata->reset_pin); |
837 | 841 | ||
838 | kfree(tsdata->raw_buffer); | ||
839 | kfree(tsdata); | 842 | kfree(tsdata); |
840 | 843 | ||
841 | return 0; | 844 | return 0; |
diff --git a/drivers/input/touchscreen/s3c2410_ts.c b/drivers/input/touchscreen/s3c2410_ts.c index b3c66d4d02f6..549fa29548f8 100644 --- a/drivers/input/touchscreen/s3c2410_ts.c +++ b/drivers/input/touchscreen/s3c2410_ts.c | |||
@@ -37,7 +37,7 @@ | |||
37 | 37 | ||
38 | #include <plat/adc.h> | 38 | #include <plat/adc.h> |
39 | #include <plat/regs-adc.h> | 39 | #include <plat/regs-adc.h> |
40 | #include <plat/ts.h> | 40 | #include <linux/platform_data/touchscreen-s3c2410.h> |
41 | 41 | ||
42 | #define TSC_SLEEP (S3C2410_ADCTSC_PULL_UP_DISABLE | S3C2410_ADCTSC_XY_PST(0)) | 42 | #define TSC_SLEEP (S3C2410_ADCTSC_PULL_UP_DISABLE | S3C2410_ADCTSC_XY_PST(0)) |
43 | 43 | ||
diff --git a/drivers/input/touchscreen/usbtouchscreen.c b/drivers/input/touchscreen/usbtouchscreen.c index e32709e0dd65..721fdb3597ca 100644 --- a/drivers/input/touchscreen/usbtouchscreen.c +++ b/drivers/input/touchscreen/usbtouchscreen.c | |||
@@ -304,6 +304,45 @@ static int e2i_read_data(struct usbtouch_usb *dev, unsigned char *pkt) | |||
304 | #define EGALAX_PKT_TYPE_REPT 0x80 | 304 | #define EGALAX_PKT_TYPE_REPT 0x80 |
305 | #define EGALAX_PKT_TYPE_DIAG 0x0A | 305 | #define EGALAX_PKT_TYPE_DIAG 0x0A |
306 | 306 | ||
307 | static int egalax_init(struct usbtouch_usb *usbtouch) | ||
308 | { | ||
309 | int ret, i; | ||
310 | unsigned char *buf; | ||
311 | struct usb_device *udev = interface_to_usbdev(usbtouch->interface); | ||
312 | |||
313 | /* | ||
314 | * An eGalax diagnostic packet kicks the device into using the right | ||
315 | * protocol. We send a "check active" packet. The response will be | ||
316 | * read later and ignored. | ||
317 | */ | ||
318 | |||
319 | buf = kmalloc(3, GFP_KERNEL); | ||
320 | if (!buf) | ||
321 | return -ENOMEM; | ||
322 | |||
323 | buf[0] = EGALAX_PKT_TYPE_DIAG; | ||
324 | buf[1] = 1; /* length */ | ||
325 | buf[2] = 'A'; /* command - check active */ | ||
326 | |||
327 | for (i = 0; i < 3; i++) { | ||
328 | ret = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), | ||
329 | 0, | ||
330 | USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE, | ||
331 | 0, 0, buf, 3, | ||
332 | USB_CTRL_SET_TIMEOUT); | ||
333 | if (ret >= 0) { | ||
334 | ret = 0; | ||
335 | break; | ||
336 | } | ||
337 | if (ret != -EPIPE) | ||
338 | break; | ||
339 | } | ||
340 | |||
341 | kfree(buf); | ||
342 | |||
343 | return ret; | ||
344 | } | ||
345 | |||
307 | static int egalax_read_data(struct usbtouch_usb *dev, unsigned char *pkt) | 346 | static int egalax_read_data(struct usbtouch_usb *dev, unsigned char *pkt) |
308 | { | 347 | { |
309 | if ((pkt[0] & EGALAX_PKT_TYPE_MASK) != EGALAX_PKT_TYPE_REPT) | 348 | if ((pkt[0] & EGALAX_PKT_TYPE_MASK) != EGALAX_PKT_TYPE_REPT) |
@@ -1056,6 +1095,7 @@ static struct usbtouch_device_info usbtouch_dev_info[] = { | |||
1056 | .process_pkt = usbtouch_process_multi, | 1095 | .process_pkt = usbtouch_process_multi, |
1057 | .get_pkt_len = egalax_get_pkt_len, | 1096 | .get_pkt_len = egalax_get_pkt_len, |
1058 | .read_data = egalax_read_data, | 1097 | .read_data = egalax_read_data, |
1098 | .init = egalax_init, | ||
1059 | }, | 1099 | }, |
1060 | #endif | 1100 | #endif |
1061 | 1101 | ||
diff --git a/drivers/input/touchscreen/wm831x-ts.c b/drivers/input/touchscreen/wm831x-ts.c index 362f78d4507f..c7eee56d0087 100644 --- a/drivers/input/touchscreen/wm831x-ts.c +++ b/drivers/input/touchscreen/wm831x-ts.c | |||
@@ -221,7 +221,7 @@ static void wm831x_ts_input_close(struct input_dev *idev) | |||
221 | synchronize_irq(wm831x_ts->pd_irq); | 221 | synchronize_irq(wm831x_ts->pd_irq); |
222 | 222 | ||
223 | /* Make sure the IRQ completion work is quiesced */ | 223 | /* Make sure the IRQ completion work is quiesced */ |
224 | flush_work_sync(&wm831x_ts->pd_data_work); | 224 | flush_work(&wm831x_ts->pd_data_work); |
225 | 225 | ||
226 | /* If we ended up with the pen down then make sure we revert back | 226 | /* If we ended up with the pen down then make sure we revert back |
227 | * to pen detection state for the next time we start up. | 227 | * to pen detection state for the next time we start up. |