aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/input/misc
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/input/misc')
-rw-r--r--drivers/input/misc/apanel.c24
-rw-r--r--drivers/input/misc/bma150.c9
-rw-r--r--drivers/input/misc/pwm-vibra.c19
-rw-r--r--drivers/input/misc/uinput.c5
4 files changed, 25 insertions, 32 deletions
diff --git a/drivers/input/misc/apanel.c b/drivers/input/misc/apanel.c
index 094bddf56755..c1e66f45d552 100644
--- a/drivers/input/misc/apanel.c
+++ b/drivers/input/misc/apanel.c
@@ -22,7 +22,6 @@
22#include <linux/io.h> 22#include <linux/io.h>
23#include <linux/input-polldev.h> 23#include <linux/input-polldev.h>
24#include <linux/i2c.h> 24#include <linux/i2c.h>
25#include <linux/workqueue.h>
26#include <linux/leds.h> 25#include <linux/leds.h>
27 26
28#define APANEL_NAME "Fujitsu Application Panel" 27#define APANEL_NAME "Fujitsu Application Panel"
@@ -59,8 +58,6 @@ struct apanel {
59 struct i2c_client *client; 58 struct i2c_client *client;
60 unsigned short keymap[MAX_PANEL_KEYS]; 59 unsigned short keymap[MAX_PANEL_KEYS];
61 u16 nkeys; 60 u16 nkeys;
62 u16 led_bits;
63 struct work_struct led_work;
64 struct led_classdev mail_led; 61 struct led_classdev mail_led;
65}; 62};
66 63
@@ -109,25 +106,13 @@ static void apanel_poll(struct input_polled_dev *ipdev)
109 report_key(idev, ap->keymap[i]); 106 report_key(idev, ap->keymap[i]);
110} 107}
111 108
112/* Track state changes of LED */ 109static int mail_led_set(struct led_classdev *led,
113static void led_update(struct work_struct *work)
114{
115 struct apanel *ap = container_of(work, struct apanel, led_work);
116
117 i2c_smbus_write_word_data(ap->client, 0x10, ap->led_bits);
118}
119
120static void mail_led_set(struct led_classdev *led,
121 enum led_brightness value) 110 enum led_brightness value)
122{ 111{
123 struct apanel *ap = container_of(led, struct apanel, mail_led); 112 struct apanel *ap = container_of(led, struct apanel, mail_led);
113 u16 led_bits = value != LED_OFF ? 0x8000 : 0x0000;
124 114
125 if (value != LED_OFF) 115 return i2c_smbus_write_word_data(ap->client, 0x10, led_bits);
126 ap->led_bits |= 0x8000;
127 else
128 ap->led_bits &= ~0x8000;
129
130 schedule_work(&ap->led_work);
131} 116}
132 117
133static int apanel_remove(struct i2c_client *client) 118static int apanel_remove(struct i2c_client *client)
@@ -179,7 +164,7 @@ static struct apanel apanel = {
179 }, 164 },
180 .mail_led = { 165 .mail_led = {
181 .name = "mail:blue", 166 .name = "mail:blue",
182 .brightness_set = mail_led_set, 167 .brightness_set_blocking = mail_led_set,
183 }, 168 },
184}; 169};
185 170
@@ -235,7 +220,6 @@ static int apanel_probe(struct i2c_client *client,
235 if (err) 220 if (err)
236 goto out3; 221 goto out3;
237 222
238 INIT_WORK(&ap->led_work, led_update);
239 if (device_chip[APANEL_DEV_LED] != CHIP_NONE) { 223 if (device_chip[APANEL_DEV_LED] != CHIP_NONE) {
240 err = led_classdev_register(&client->dev, &ap->mail_led); 224 err = led_classdev_register(&client->dev, &ap->mail_led);
241 if (err) 225 if (err)
diff --git a/drivers/input/misc/bma150.c b/drivers/input/misc/bma150.c
index 1efcfdf9f8a8..dd9dd4e40827 100644
--- a/drivers/input/misc/bma150.c
+++ b/drivers/input/misc/bma150.c
@@ -481,13 +481,14 @@ static int bma150_register_input_device(struct bma150_data *bma150)
481 idev->close = bma150_irq_close; 481 idev->close = bma150_irq_close;
482 input_set_drvdata(idev, bma150); 482 input_set_drvdata(idev, bma150);
483 483
484 bma150->input = idev;
485
484 error = input_register_device(idev); 486 error = input_register_device(idev);
485 if (error) { 487 if (error) {
486 input_free_device(idev); 488 input_free_device(idev);
487 return error; 489 return error;
488 } 490 }
489 491
490 bma150->input = idev;
491 return 0; 492 return 0;
492} 493}
493 494
@@ -510,15 +511,15 @@ static int bma150_register_polled_device(struct bma150_data *bma150)
510 511
511 bma150_init_input_device(bma150, ipoll_dev->input); 512 bma150_init_input_device(bma150, ipoll_dev->input);
512 513
514 bma150->input_polled = ipoll_dev;
515 bma150->input = ipoll_dev->input;
516
513 error = input_register_polled_device(ipoll_dev); 517 error = input_register_polled_device(ipoll_dev);
514 if (error) { 518 if (error) {
515 input_free_polled_device(ipoll_dev); 519 input_free_polled_device(ipoll_dev);
516 return error; 520 return error;
517 } 521 }
518 522
519 bma150->input_polled = ipoll_dev;
520 bma150->input = ipoll_dev->input;
521
522 return 0; 523 return 0;
523} 524}
524 525
diff --git a/drivers/input/misc/pwm-vibra.c b/drivers/input/misc/pwm-vibra.c
index 55da191ae550..dbb6d9e1b947 100644
--- a/drivers/input/misc/pwm-vibra.c
+++ b/drivers/input/misc/pwm-vibra.c
@@ -34,6 +34,7 @@ struct pwm_vibrator {
34 struct work_struct play_work; 34 struct work_struct play_work;
35 u16 level; 35 u16 level;
36 u32 direction_duty_cycle; 36 u32 direction_duty_cycle;
37 bool vcc_on;
37}; 38};
38 39
39static int pwm_vibrator_start(struct pwm_vibrator *vibrator) 40static int pwm_vibrator_start(struct pwm_vibrator *vibrator)
@@ -42,10 +43,13 @@ static int pwm_vibrator_start(struct pwm_vibrator *vibrator)
42 struct pwm_state state; 43 struct pwm_state state;
43 int err; 44 int err;
44 45
45 err = regulator_enable(vibrator->vcc); 46 if (!vibrator->vcc_on) {
46 if (err) { 47 err = regulator_enable(vibrator->vcc);
47 dev_err(pdev, "failed to enable regulator: %d", err); 48 if (err) {
48 return err; 49 dev_err(pdev, "failed to enable regulator: %d", err);
50 return err;
51 }
52 vibrator->vcc_on = true;
49 } 53 }
50 54
51 pwm_get_state(vibrator->pwm, &state); 55 pwm_get_state(vibrator->pwm, &state);
@@ -76,11 +80,14 @@ static int pwm_vibrator_start(struct pwm_vibrator *vibrator)
76 80
77static void pwm_vibrator_stop(struct pwm_vibrator *vibrator) 81static void pwm_vibrator_stop(struct pwm_vibrator *vibrator)
78{ 82{
79 regulator_disable(vibrator->vcc);
80
81 if (vibrator->pwm_dir) 83 if (vibrator->pwm_dir)
82 pwm_disable(vibrator->pwm_dir); 84 pwm_disable(vibrator->pwm_dir);
83 pwm_disable(vibrator->pwm); 85 pwm_disable(vibrator->pwm);
86
87 if (vibrator->vcc_on) {
88 regulator_disable(vibrator->vcc);
89 vibrator->vcc_on = false;
90 }
84} 91}
85 92
86static void pwm_vibrator_play_work(struct work_struct *work) 93static void pwm_vibrator_play_work(struct work_struct *work)
diff --git a/drivers/input/misc/uinput.c b/drivers/input/misc/uinput.c
index 8ec483e8688b..26ec603fe220 100644
--- a/drivers/input/misc/uinput.c
+++ b/drivers/input/misc/uinput.c
@@ -39,6 +39,7 @@
39#include <linux/init.h> 39#include <linux/init.h>
40#include <linux/fs.h> 40#include <linux/fs.h>
41#include <linux/miscdevice.h> 41#include <linux/miscdevice.h>
42#include <linux/overflow.h>
42#include <linux/input/mt.h> 43#include <linux/input/mt.h>
43#include "../input-compat.h" 44#include "../input-compat.h"
44 45
@@ -405,7 +406,7 @@ static int uinput_open(struct inode *inode, struct file *file)
405static int uinput_validate_absinfo(struct input_dev *dev, unsigned int code, 406static int uinput_validate_absinfo(struct input_dev *dev, unsigned int code,
406 const struct input_absinfo *abs) 407 const struct input_absinfo *abs)
407{ 408{
408 int min, max; 409 int min, max, range;
409 410
410 min = abs->minimum; 411 min = abs->minimum;
411 max = abs->maximum; 412 max = abs->maximum;
@@ -417,7 +418,7 @@ static int uinput_validate_absinfo(struct input_dev *dev, unsigned int code,
417 return -EINVAL; 418 return -EINVAL;
418 } 419 }
419 420
420 if (abs->flat > max - min) { 421 if (!check_sub_overflow(max, min, &range) && abs->flat > range) {
421 printk(KERN_DEBUG 422 printk(KERN_DEBUG
422 "%s: abs_flat #%02x out of range: %d (min:%d/max:%d)\n", 423 "%s: abs_flat #%02x out of range: %d (min:%d/max:%d)\n",
423 UINPUT_NAME, code, abs->flat, min, max); 424 UINPUT_NAME, code, abs->flat, min, max);