aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/input/misc
diff options
context:
space:
mode:
authorDmitry Torokhov <dmitry.torokhov@gmail.com>2010-08-02 21:35:17 -0400
committerDmitry Torokhov <dmitry.torokhov@gmail.com>2010-08-02 21:35:17 -0400
commitd01d0756f75e7a5b4b43764ad45b83c4340f11d6 (patch)
tree90db2ff7ccb35a8fdcf98366e6404afe1f845bc4 /drivers/input/misc
parentb326b853dca2f410b254198ee89abad71a2f4668 (diff)
parent0d87c7228a49e8342d60dd552892e470e0b291fa (diff)
Merge branch 'next' into for-linus
Diffstat (limited to 'drivers/input/misc')
-rw-r--r--drivers/input/misc/Kconfig48
-rw-r--r--drivers/input/misc/Makefile4
-rw-r--r--drivers/input/misc/adxl34x-i2c.c163
-rw-r--r--drivers/input/misc/adxl34x-spi.c145
-rw-r--r--drivers/input/misc/adxl34x.c915
-rw-r--r--drivers/input/misc/adxl34x.h30
-rw-r--r--drivers/input/misc/atlas_btns.c38
-rw-r--r--drivers/input/misc/pwm-beeper.c199
-rw-r--r--drivers/input/misc/twl4030-pwrbutton.c12
-rw-r--r--drivers/input/misc/wistron_btns.c4
10 files changed, 1528 insertions, 30 deletions
diff --git a/drivers/input/misc/Kconfig b/drivers/input/misc/Kconfig
index c44b9eafc556..b49e23379723 100644
--- a/drivers/input/misc/Kconfig
+++ b/drivers/input/misc/Kconfig
@@ -327,6 +327,17 @@ config INPUT_PCF8574
327 To compile this driver as a module, choose M here: the 327 To compile this driver as a module, choose M here: the
328 module will be called pcf8574_keypad. 328 module will be called pcf8574_keypad.
329 329
330config INPUT_PWM_BEEPER
331 tristate "PWM beeper support"
332 depends on HAVE_PWM
333 help
334 Say Y here to get support for PWM based beeper devices.
335
336 If unsure, say N.
337
338 To compile this driver as a module, choose M here: the module will be
339 called pwm-beeper.
340
330config INPUT_GPIO_ROTARY_ENCODER 341config INPUT_GPIO_ROTARY_ENCODER
331 tristate "Rotary encoders connected to GPIO pins" 342 tristate "Rotary encoders connected to GPIO pins"
332 depends on GPIOLIB && GENERIC_GPIO 343 depends on GPIOLIB && GENERIC_GPIO
@@ -390,4 +401,41 @@ config INPUT_PCAP
390 To compile this driver as a module, choose M here: the 401 To compile this driver as a module, choose M here: the
391 module will be called pcap_keys. 402 module will be called pcap_keys.
392 403
404config INPUT_ADXL34X
405 tristate "Analog Devices ADXL34x Three-Axis Digital Accelerometer"
406 default n
407 help
408 Say Y here if you have a Accelerometer interface using the
409 ADXL345/6 controller, and your board-specific initialization
410 code includes that in its table of devices.
411
412 This driver can use either I2C or SPI communication to the
413 ADXL345/6 controller. Select the appropriate method for
414 your system.
415
416 If unsure, say N (but it's safe to say "Y").
417
418 To compile this driver as a module, choose M here: the
419 module will be called adxl34x.
420
421config INPUT_ADXL34X_I2C
422 tristate "support I2C bus connection"
423 depends on INPUT_ADXL34X && I2C
424 default y
425 help
426 Say Y here if you have ADXL345/6 hooked to an I2C bus.
427
428 To compile this driver as a module, choose M here: the
429 module will be called adxl34x-i2c.
430
431config INPUT_ADXL34X_SPI
432 tristate "support SPI bus connection"
433 depends on INPUT_ADXL34X && SPI
434 default y
435 help
436 Say Y here if you have ADXL345/6 hooked to a SPI bus.
437
438 To compile this driver as a module, choose M here: the
439 module will be called adxl34x-spi.
440
393endif 441endif
diff --git a/drivers/input/misc/Makefile b/drivers/input/misc/Makefile
index 71fe57d8023f..19ccca78fa76 100644
--- a/drivers/input/misc/Makefile
+++ b/drivers/input/misc/Makefile
@@ -8,6 +8,9 @@ obj-$(CONFIG_INPUT_88PM860X_ONKEY) += 88pm860x_onkey.o
8obj-$(CONFIG_INPUT_AD714X) += ad714x.o 8obj-$(CONFIG_INPUT_AD714X) += ad714x.o
9obj-$(CONFIG_INPUT_AD714X_I2C) += ad714x-i2c.o 9obj-$(CONFIG_INPUT_AD714X_I2C) += ad714x-i2c.o
10obj-$(CONFIG_INPUT_AD714X_SPI) += ad714x-spi.o 10obj-$(CONFIG_INPUT_AD714X_SPI) += ad714x-spi.o
11obj-$(CONFIG_INPUT_ADXL34X) += adxl34x.o
12obj-$(CONFIG_INPUT_ADXL34X_I2C) += adxl34x-i2c.o
13obj-$(CONFIG_INPUT_ADXL34X_SPI) += adxl34x-spi.o
11obj-$(CONFIG_INPUT_APANEL) += apanel.o 14obj-$(CONFIG_INPUT_APANEL) += apanel.o
12obj-$(CONFIG_INPUT_ATI_REMOTE) += ati_remote.o 15obj-$(CONFIG_INPUT_ATI_REMOTE) += ati_remote.o
13obj-$(CONFIG_INPUT_ATI_REMOTE2) += ati_remote2.o 16obj-$(CONFIG_INPUT_ATI_REMOTE2) += ati_remote2.o
@@ -26,6 +29,7 @@ obj-$(CONFIG_INPUT_PCF50633_PMU) += pcf50633-input.o
26obj-$(CONFIG_INPUT_PCF8574) += pcf8574_keypad.o 29obj-$(CONFIG_INPUT_PCF8574) += pcf8574_keypad.o
27obj-$(CONFIG_INPUT_PCSPKR) += pcspkr.o 30obj-$(CONFIG_INPUT_PCSPKR) += pcspkr.o
28obj-$(CONFIG_INPUT_POWERMATE) += powermate.o 31obj-$(CONFIG_INPUT_POWERMATE) += powermate.o
32obj-$(CONFIG_INPUT_PWM_BEEPER) += pwm-beeper.o
29obj-$(CONFIG_INPUT_RB532_BUTTON) += rb532_button.o 33obj-$(CONFIG_INPUT_RB532_BUTTON) += rb532_button.o
30obj-$(CONFIG_INPUT_GPIO_ROTARY_ENCODER) += rotary_encoder.o 34obj-$(CONFIG_INPUT_GPIO_ROTARY_ENCODER) += rotary_encoder.o
31obj-$(CONFIG_INPUT_SGI_BTNS) += sgi_btns.o 35obj-$(CONFIG_INPUT_SGI_BTNS) += sgi_btns.o
diff --git a/drivers/input/misc/adxl34x-i2c.c b/drivers/input/misc/adxl34x-i2c.c
new file mode 100644
index 000000000000..0779724af7e7
--- /dev/null
+++ b/drivers/input/misc/adxl34x-i2c.c
@@ -0,0 +1,163 @@
1/*
2 * ADLX345/346 Three-Axis Digital Accelerometers (I2C Interface)
3 *
4 * Enter bugs at http://blackfin.uclinux.org/
5 *
6 * Copyright (C) 2009 Michael Hennerich, Analog Devices Inc.
7 * Licensed under the GPL-2 or later.
8 */
9
10#include <linux/input.h> /* BUS_I2C */
11#include <linux/i2c.h>
12#include <linux/module.h>
13#include <linux/types.h>
14#include "adxl34x.h"
15
16static int adxl34x_smbus_read(struct device *dev, unsigned char reg)
17{
18 struct i2c_client *client = to_i2c_client(dev);
19
20 return i2c_smbus_read_byte_data(client, reg);
21}
22
23static int adxl34x_smbus_write(struct device *dev,
24 unsigned char reg, unsigned char val)
25{
26 struct i2c_client *client = to_i2c_client(dev);
27
28 return i2c_smbus_write_byte_data(client, reg, val);
29}
30
31static int adxl34x_smbus_read_block(struct device *dev,
32 unsigned char reg, int count,
33 void *buf)
34{
35 struct i2c_client *client = to_i2c_client(dev);
36
37 return i2c_smbus_read_i2c_block_data(client, reg, count, buf);
38}
39
40static int adxl34x_i2c_read_block(struct device *dev,
41 unsigned char reg, int count,
42 void *buf)
43{
44 struct i2c_client *client = to_i2c_client(dev);
45 int ret;
46
47 ret = i2c_master_send(client, &reg, 1);
48 if (ret < 0)
49 return ret;
50
51 ret = i2c_master_recv(client, buf, count);
52 if (ret < 0)
53 return ret;
54
55 if (ret != count)
56 return -EIO;
57
58 return 0;
59}
60
61static const struct adxl34x_bus_ops adxl34x_smbus_bops = {
62 .bustype = BUS_I2C,
63 .write = adxl34x_smbus_write,
64 .read = adxl34x_smbus_read,
65 .read_block = adxl34x_smbus_read_block,
66};
67
68static const struct adxl34x_bus_ops adxl34x_i2c_bops = {
69 .bustype = BUS_I2C,
70 .write = adxl34x_smbus_write,
71 .read = adxl34x_smbus_read,
72 .read_block = adxl34x_i2c_read_block,
73};
74
75static int __devinit adxl34x_i2c_probe(struct i2c_client *client,
76 const struct i2c_device_id *id)
77{
78 struct adxl34x *ac;
79 int error;
80
81 error = i2c_check_functionality(client->adapter,
82 I2C_FUNC_SMBUS_BYTE_DATA);
83 if (!error) {
84 dev_err(&client->dev, "SMBUS Byte Data not Supported\n");
85 return -EIO;
86 }
87
88 ac = adxl34x_probe(&client->dev, client->irq, false,
89 i2c_check_functionality(client->adapter,
90 I2C_FUNC_SMBUS_READ_I2C_BLOCK) ?
91 &adxl34x_smbus_bops : &adxl34x_i2c_bops);
92 if (IS_ERR(ac))
93 return PTR_ERR(ac);
94
95 i2c_set_clientdata(client, ac);
96
97 return 0;
98}
99
100static int __devexit adxl34x_i2c_remove(struct i2c_client *client)
101{
102 struct adxl34x *ac = i2c_get_clientdata(client);
103
104 return adxl34x_remove(ac);
105}
106
107#ifdef CONFIG_PM
108static int adxl34x_i2c_suspend(struct i2c_client *client, pm_message_t message)
109{
110 struct adxl34x *ac = i2c_get_clientdata(client);
111
112 adxl34x_suspend(ac);
113
114 return 0;
115}
116
117static int adxl34x_i2c_resume(struct i2c_client *client)
118{
119 struct adxl34x *ac = i2c_get_clientdata(client);
120
121 adxl34x_resume(ac);
122
123 return 0;
124}
125#else
126# define adxl34x_i2c_suspend NULL
127# define adxl34x_i2c_resume NULL
128#endif
129
130static const struct i2c_device_id adxl34x_id[] = {
131 { "adxl34x", 0 },
132 { }
133};
134
135MODULE_DEVICE_TABLE(i2c, adxl34x_id);
136
137static struct i2c_driver adxl34x_driver = {
138 .driver = {
139 .name = "adxl34x",
140 .owner = THIS_MODULE,
141 },
142 .probe = adxl34x_i2c_probe,
143 .remove = __devexit_p(adxl34x_i2c_remove),
144 .suspend = adxl34x_i2c_suspend,
145 .resume = adxl34x_i2c_resume,
146 .id_table = adxl34x_id,
147};
148
149static int __init adxl34x_i2c_init(void)
150{
151 return i2c_add_driver(&adxl34x_driver);
152}
153module_init(adxl34x_i2c_init);
154
155static void __exit adxl34x_i2c_exit(void)
156{
157 i2c_del_driver(&adxl34x_driver);
158}
159module_exit(adxl34x_i2c_exit);
160
161MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
162MODULE_DESCRIPTION("ADXL345/346 Three-Axis Digital Accelerometer I2C Bus Driver");
163MODULE_LICENSE("GPL");
diff --git a/drivers/input/misc/adxl34x-spi.c b/drivers/input/misc/adxl34x-spi.c
new file mode 100644
index 000000000000..782de9e89828
--- /dev/null
+++ b/drivers/input/misc/adxl34x-spi.c
@@ -0,0 +1,145 @@
1/*
2 * ADLX345/346 Three-Axis Digital Accelerometers (SPI Interface)
3 *
4 * Enter bugs at http://blackfin.uclinux.org/
5 *
6 * Copyright (C) 2009 Michael Hennerich, Analog Devices Inc.
7 * Licensed under the GPL-2 or later.
8 */
9
10#include <linux/input.h> /* BUS_SPI */
11#include <linux/module.h>
12#include <linux/spi/spi.h>
13#include <linux/types.h>
14#include "adxl34x.h"
15
16#define MAX_SPI_FREQ_HZ 5000000
17#define MAX_FREQ_NO_FIFODELAY 1500000
18#define ADXL34X_CMD_MULTB (1 << 6)
19#define ADXL34X_CMD_READ (1 << 7)
20#define ADXL34X_WRITECMD(reg) (reg & 0x3F)
21#define ADXL34X_READCMD(reg) (ADXL34X_CMD_READ | (reg & 0x3F))
22#define ADXL34X_READMB_CMD(reg) (ADXL34X_CMD_READ | ADXL34X_CMD_MULTB \
23 | (reg & 0x3F))
24
25static int adxl34x_spi_read(struct device *dev, unsigned char reg)
26{
27 struct spi_device *spi = to_spi_device(dev);
28 unsigned char cmd;
29
30 cmd = ADXL34X_READCMD(reg);
31
32 return spi_w8r8(spi, cmd);
33}
34
35static int adxl34x_spi_write(struct device *dev,
36 unsigned char reg, unsigned char val)
37{
38 struct spi_device *spi = to_spi_device(dev);
39 unsigned char buf[2];
40
41 buf[0] = ADXL34X_WRITECMD(reg);
42 buf[1] = val;
43
44 return spi_write(spi, buf, sizeof(buf));
45}
46
47static int adxl34x_spi_read_block(struct device *dev,
48 unsigned char reg, int count,
49 void *buf)
50{
51 struct spi_device *spi = to_spi_device(dev);
52 ssize_t status;
53
54 reg = ADXL34X_READMB_CMD(reg);
55 status = spi_write_then_read(spi, &reg, 1, buf, count);
56
57 return (status < 0) ? status : 0;
58}
59
60static const struct adxl34x_bus_ops adx134x_spi_bops = {
61 .bustype = BUS_SPI,
62 .write = adxl34x_spi_write,
63 .read = adxl34x_spi_read,
64 .read_block = adxl34x_spi_read_block,
65};
66
67static int __devinit adxl34x_spi_probe(struct spi_device *spi)
68{
69 struct adxl34x *ac;
70
71 /* don't exceed max specified SPI CLK frequency */
72 if (spi->max_speed_hz > MAX_SPI_FREQ_HZ) {
73 dev_err(&spi->dev, "SPI CLK %d Hz too fast\n", spi->max_speed_hz);
74 return -EINVAL;
75 }
76
77 ac = adxl34x_probe(&spi->dev, spi->irq,
78 spi->max_speed_hz > MAX_FREQ_NO_FIFODELAY,
79 &adx134x_spi_bops);
80
81 if (IS_ERR(ac))
82 return PTR_ERR(ac);
83
84 spi_set_drvdata(spi, ac);
85
86 return 0;
87}
88
89static int __devexit adxl34x_spi_remove(struct spi_device *spi)
90{
91 struct adxl34x *ac = dev_get_drvdata(&spi->dev);
92
93 return adxl34x_remove(ac);
94}
95
96#ifdef CONFIG_PM
97static int adxl34x_spi_suspend(struct spi_device *spi, pm_message_t message)
98{
99 struct adxl34x *ac = dev_get_drvdata(&spi->dev);
100
101 adxl34x_suspend(ac);
102
103 return 0;
104}
105
106static int adxl34x_spi_resume(struct spi_device *spi)
107{
108 struct adxl34x *ac = dev_get_drvdata(&spi->dev);
109
110 adxl34x_resume(ac);
111
112 return 0;
113}
114#else
115# define adxl34x_spi_suspend NULL
116# define adxl34x_spi_resume NULL
117#endif
118
119static struct spi_driver adxl34x_driver = {
120 .driver = {
121 .name = "adxl34x",
122 .bus = &spi_bus_type,
123 .owner = THIS_MODULE,
124 },
125 .probe = adxl34x_spi_probe,
126 .remove = __devexit_p(adxl34x_spi_remove),
127 .suspend = adxl34x_spi_suspend,
128 .resume = adxl34x_spi_resume,
129};
130
131static int __init adxl34x_spi_init(void)
132{
133 return spi_register_driver(&adxl34x_driver);
134}
135module_init(adxl34x_spi_init);
136
137static void __exit adxl34x_spi_exit(void)
138{
139 spi_unregister_driver(&adxl34x_driver);
140}
141module_exit(adxl34x_spi_exit);
142
143MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
144MODULE_DESCRIPTION("ADXL345/346 Three-Axis Digital Accelerometer SPI Bus Driver");
145MODULE_LICENSE("GPL");
diff --git a/drivers/input/misc/adxl34x.c b/drivers/input/misc/adxl34x.c
new file mode 100644
index 000000000000..e2ca01708080
--- /dev/null
+++ b/drivers/input/misc/adxl34x.c
@@ -0,0 +1,915 @@
1/*
2 * ADXL345/346 Three-Axis Digital Accelerometers
3 *
4 * Enter bugs at http://blackfin.uclinux.org/
5 *
6 * Copyright (C) 2009 Michael Hennerich, Analog Devices Inc.
7 * Licensed under the GPL-2 or later.
8 */
9
10#include <linux/device.h>
11#include <linux/init.h>
12#include <linux/delay.h>
13#include <linux/input.h>
14#include <linux/interrupt.h>
15#include <linux/irq.h>
16#include <linux/slab.h>
17#include <linux/workqueue.h>
18#include <linux/input/adxl34x.h>
19
20#include "adxl34x.h"
21
22/* ADXL345/6 Register Map */
23#define DEVID 0x00 /* R Device ID */
24#define THRESH_TAP 0x1D /* R/W Tap threshold */
25#define OFSX 0x1E /* R/W X-axis offset */
26#define OFSY 0x1F /* R/W Y-axis offset */
27#define OFSZ 0x20 /* R/W Z-axis offset */
28#define DUR 0x21 /* R/W Tap duration */
29#define LATENT 0x22 /* R/W Tap latency */
30#define WINDOW 0x23 /* R/W Tap window */
31#define THRESH_ACT 0x24 /* R/W Activity threshold */
32#define THRESH_INACT 0x25 /* R/W Inactivity threshold */
33#define TIME_INACT 0x26 /* R/W Inactivity time */
34#define ACT_INACT_CTL 0x27 /* R/W Axis enable control for activity and */
35 /* inactivity detection */
36#define THRESH_FF 0x28 /* R/W Free-fall threshold */
37#define TIME_FF 0x29 /* R/W Free-fall time */
38#define TAP_AXES 0x2A /* R/W Axis control for tap/double tap */
39#define ACT_TAP_STATUS 0x2B /* R Source of tap/double tap */
40#define BW_RATE 0x2C /* R/W Data rate and power mode control */
41#define POWER_CTL 0x2D /* R/W Power saving features control */
42#define INT_ENABLE 0x2E /* R/W Interrupt enable control */
43#define INT_MAP 0x2F /* R/W Interrupt mapping control */
44#define INT_SOURCE 0x30 /* R Source of interrupts */
45#define DATA_FORMAT 0x31 /* R/W Data format control */
46#define DATAX0 0x32 /* R X-Axis Data 0 */
47#define DATAX1 0x33 /* R X-Axis Data 1 */
48#define DATAY0 0x34 /* R Y-Axis Data 0 */
49#define DATAY1 0x35 /* R Y-Axis Data 1 */
50#define DATAZ0 0x36 /* R Z-Axis Data 0 */
51#define DATAZ1 0x37 /* R Z-Axis Data 1 */
52#define FIFO_CTL 0x38 /* R/W FIFO control */
53#define FIFO_STATUS 0x39 /* R FIFO status */
54#define TAP_SIGN 0x3A /* R Sign and source for tap/double tap */
55/* Orientation ADXL346 only */
56#define ORIENT_CONF 0x3B /* R/W Orientation configuration */
57#define ORIENT 0x3C /* R Orientation status */
58
59/* DEVIDs */
60#define ID_ADXL345 0xE5
61#define ID_ADXL346 0xE6
62
63/* INT_ENABLE/INT_MAP/INT_SOURCE Bits */
64#define DATA_READY (1 << 7)
65#define SINGLE_TAP (1 << 6)
66#define DOUBLE_TAP (1 << 5)
67#define ACTIVITY (1 << 4)
68#define INACTIVITY (1 << 3)
69#define FREE_FALL (1 << 2)
70#define WATERMARK (1 << 1)
71#define OVERRUN (1 << 0)
72
73/* ACT_INACT_CONTROL Bits */
74#define ACT_ACDC (1 << 7)
75#define ACT_X_EN (1 << 6)
76#define ACT_Y_EN (1 << 5)
77#define ACT_Z_EN (1 << 4)
78#define INACT_ACDC (1 << 3)
79#define INACT_X_EN (1 << 2)
80#define INACT_Y_EN (1 << 1)
81#define INACT_Z_EN (1 << 0)
82
83/* TAP_AXES Bits */
84#define SUPPRESS (1 << 3)
85#define TAP_X_EN (1 << 2)
86#define TAP_Y_EN (1 << 1)
87#define TAP_Z_EN (1 << 0)
88
89/* ACT_TAP_STATUS Bits */
90#define ACT_X_SRC (1 << 6)
91#define ACT_Y_SRC (1 << 5)
92#define ACT_Z_SRC (1 << 4)
93#define ASLEEP (1 << 3)
94#define TAP_X_SRC (1 << 2)
95#define TAP_Y_SRC (1 << 1)
96#define TAP_Z_SRC (1 << 0)
97
98/* BW_RATE Bits */
99#define LOW_POWER (1 << 4)
100#define RATE(x) ((x) & 0xF)
101
102/* POWER_CTL Bits */
103#define PCTL_LINK (1 << 5)
104#define PCTL_AUTO_SLEEP (1 << 4)
105#define PCTL_MEASURE (1 << 3)
106#define PCTL_SLEEP (1 << 2)
107#define PCTL_WAKEUP(x) ((x) & 0x3)
108
109/* DATA_FORMAT Bits */
110#define SELF_TEST (1 << 7)
111#define SPI (1 << 6)
112#define INT_INVERT (1 << 5)
113#define FULL_RES (1 << 3)
114#define JUSTIFY (1 << 2)
115#define RANGE(x) ((x) & 0x3)
116#define RANGE_PM_2g 0
117#define RANGE_PM_4g 1
118#define RANGE_PM_8g 2
119#define RANGE_PM_16g 3
120
121/*
122 * Maximum value our axis may get in full res mode for the input device
123 * (signed 13 bits)
124 */
125#define ADXL_FULLRES_MAX_VAL 4096
126
127/*
128 * Maximum value our axis may get in fixed res mode for the input device
129 * (signed 10 bits)
130 */
131#define ADXL_FIXEDRES_MAX_VAL 512
132
133/* FIFO_CTL Bits */
134#define FIFO_MODE(x) (((x) & 0x3) << 6)
135#define FIFO_BYPASS 0
136#define FIFO_FIFO 1
137#define FIFO_STREAM 2
138#define FIFO_TRIGGER 3
139#define TRIGGER (1 << 5)
140#define SAMPLES(x) ((x) & 0x1F)
141
142/* FIFO_STATUS Bits */
143#define FIFO_TRIG (1 << 7)
144#define ENTRIES(x) ((x) & 0x3F)
145
146/* TAP_SIGN Bits ADXL346 only */
147#define XSIGN (1 << 6)
148#define YSIGN (1 << 5)
149#define ZSIGN (1 << 4)
150#define XTAP (1 << 3)
151#define YTAP (1 << 2)
152#define ZTAP (1 << 1)
153
154/* ORIENT_CONF ADXL346 only */
155#define ORIENT_DEADZONE(x) (((x) & 0x7) << 4)
156#define ORIENT_DIVISOR(x) ((x) & 0x7)
157
158/* ORIENT ADXL346 only */
159#define ADXL346_2D_VALID (1 << 6)
160#define ADXL346_2D_ORIENT(x) (((x) & 0x3) >> 4)
161#define ADXL346_3D_VALID (1 << 3)
162#define ADXL346_3D_ORIENT(x) ((x) & 0x7)
163#define ADXL346_2D_PORTRAIT_POS 0 /* +X */
164#define ADXL346_2D_PORTRAIT_NEG 1 /* -X */
165#define ADXL346_2D_LANDSCAPE_POS 2 /* +Y */
166#define ADXL346_2D_LANDSCAPE_NEG 3 /* -Y */
167
168#define ADXL346_3D_FRONT 3 /* +X */
169#define ADXL346_3D_BACK 4 /* -X */
170#define ADXL346_3D_RIGHT 2 /* +Y */
171#define ADXL346_3D_LEFT 5 /* -Y */
172#define ADXL346_3D_TOP 1 /* +Z */
173#define ADXL346_3D_BOTTOM 6 /* -Z */
174
175#undef ADXL_DEBUG
176
177#define ADXL_X_AXIS 0
178#define ADXL_Y_AXIS 1
179#define ADXL_Z_AXIS 2
180
181#define AC_READ(ac, reg) ((ac)->bops->read((ac)->dev, reg))
182#define AC_WRITE(ac, reg, val) ((ac)->bops->write((ac)->dev, reg, val))
183
184struct axis_triple {
185 int x;
186 int y;
187 int z;
188};
189
190struct adxl34x {
191 struct device *dev;
192 struct input_dev *input;
193 struct mutex mutex; /* reentrant protection for struct */
194 struct adxl34x_platform_data pdata;
195 struct axis_triple swcal;
196 struct axis_triple hwcal;
197 struct axis_triple saved;
198 char phys[32];
199 unsigned orient2d_saved;
200 unsigned orient3d_saved;
201 bool disabled; /* P: mutex */
202 bool opened; /* P: mutex */
203 bool suspended; /* P: mutex */
204 bool fifo_delay;
205 int irq;
206 unsigned model;
207 unsigned int_mask;
208
209 const struct adxl34x_bus_ops *bops;
210};
211
212static const struct adxl34x_platform_data adxl34x_default_init = {
213 .tap_threshold = 35,
214 .tap_duration = 3,
215 .tap_latency = 20,
216 .tap_window = 20,
217 .tap_axis_control = ADXL_TAP_X_EN | ADXL_TAP_Y_EN | ADXL_TAP_Z_EN,
218 .act_axis_control = 0xFF,
219 .activity_threshold = 6,
220 .inactivity_threshold = 4,
221 .inactivity_time = 3,
222 .free_fall_threshold = 8,
223 .free_fall_time = 0x20,
224 .data_rate = 8,
225 .data_range = ADXL_FULL_RES,
226
227 .ev_type = EV_ABS,
228 .ev_code_x = ABS_X, /* EV_REL */
229 .ev_code_y = ABS_Y, /* EV_REL */
230 .ev_code_z = ABS_Z, /* EV_REL */
231
232 .ev_code_tap = {BTN_TOUCH, BTN_TOUCH, BTN_TOUCH}, /* EV_KEY {x,y,z} */
233 .power_mode = ADXL_AUTO_SLEEP | ADXL_LINK,
234 .fifo_mode = FIFO_STREAM,
235 .watermark = 0,
236};
237
238static void adxl34x_get_triple(struct adxl34x *ac, struct axis_triple *axis)
239{
240 short buf[3];
241
242 ac->bops->read_block(ac->dev, DATAX0, DATAZ1 - DATAX0 + 1, buf);
243
244 mutex_lock(&ac->mutex);
245 ac->saved.x = (s16) le16_to_cpu(buf[0]);
246 axis->x = ac->saved.x;
247
248 ac->saved.y = (s16) le16_to_cpu(buf[1]);
249 axis->y = ac->saved.y;
250
251 ac->saved.z = (s16) le16_to_cpu(buf[2]);
252 axis->z = ac->saved.z;
253 mutex_unlock(&ac->mutex);
254}
255
256static void adxl34x_service_ev_fifo(struct adxl34x *ac)
257{
258 struct adxl34x_platform_data *pdata = &ac->pdata;
259 struct axis_triple axis;
260
261 adxl34x_get_triple(ac, &axis);
262
263 input_event(ac->input, pdata->ev_type, pdata->ev_code_x,
264 axis.x - ac->swcal.x);
265 input_event(ac->input, pdata->ev_type, pdata->ev_code_y,
266 axis.y - ac->swcal.y);
267 input_event(ac->input, pdata->ev_type, pdata->ev_code_z,
268 axis.z - ac->swcal.z);
269}
270
271static void adxl34x_report_key_single(struct input_dev *input, int key)
272{
273 input_report_key(input, key, true);
274 input_sync(input);
275 input_report_key(input, key, false);
276}
277
278static void adxl34x_send_key_events(struct adxl34x *ac,
279 struct adxl34x_platform_data *pdata, int status, int press)
280{
281 int i;
282
283 for (i = ADXL_X_AXIS; i <= ADXL_Z_AXIS; i++) {
284 if (status & (1 << (ADXL_Z_AXIS - i)))
285 input_report_key(ac->input,
286 pdata->ev_code_tap[i], press);
287 }
288}
289
290static void adxl34x_do_tap(struct adxl34x *ac,
291 struct adxl34x_platform_data *pdata, int status)
292{
293 adxl34x_send_key_events(ac, pdata, status, true);
294 input_sync(ac->input);
295 adxl34x_send_key_events(ac, pdata, status, false);
296}
297
298static irqreturn_t adxl34x_irq(int irq, void *handle)
299{
300 struct adxl34x *ac = handle;
301 struct adxl34x_platform_data *pdata = &ac->pdata;
302 int int_stat, tap_stat, samples, orient, orient_code;
303
304 /*
305 * ACT_TAP_STATUS should be read before clearing the interrupt
306 * Avoid reading ACT_TAP_STATUS in case TAP detection is disabled
307 */
308
309 if (pdata->tap_axis_control & (TAP_X_EN | TAP_Y_EN | TAP_Z_EN))
310 tap_stat = AC_READ(ac, ACT_TAP_STATUS);
311 else
312 tap_stat = 0;
313
314 int_stat = AC_READ(ac, INT_SOURCE);
315
316 if (int_stat & FREE_FALL)
317 adxl34x_report_key_single(ac->input, pdata->ev_code_ff);
318
319 if (int_stat & OVERRUN)
320 dev_dbg(ac->dev, "OVERRUN\n");
321
322 if (int_stat & (SINGLE_TAP | DOUBLE_TAP)) {
323 adxl34x_do_tap(ac, pdata, tap_stat);
324
325 if (int_stat & DOUBLE_TAP)
326 adxl34x_do_tap(ac, pdata, tap_stat);
327 }
328
329 if (pdata->ev_code_act_inactivity) {
330 if (int_stat & ACTIVITY)
331 input_report_key(ac->input,
332 pdata->ev_code_act_inactivity, 1);
333 if (int_stat & INACTIVITY)
334 input_report_key(ac->input,
335 pdata->ev_code_act_inactivity, 0);
336 }
337
338 /*
339 * ORIENTATION SENSING ADXL346 only
340 */
341 if (pdata->orientation_enable) {
342 orient = AC_READ(ac, ORIENT);
343 if ((pdata->orientation_enable & ADXL_EN_ORIENTATION_2D) &&
344 (orient & ADXL346_2D_VALID)) {
345
346 orient_code = ADXL346_2D_ORIENT(orient);
347 /* Report orientation only when it changes */
348 if (ac->orient2d_saved != orient_code) {
349 ac->orient2d_saved = orient_code;
350 adxl34x_report_key_single(ac->input,
351 pdata->ev_codes_orient_2d[orient_code]);
352 }
353 }
354
355 if ((pdata->orientation_enable & ADXL_EN_ORIENTATION_3D) &&
356 (orient & ADXL346_3D_VALID)) {
357
358 orient_code = ADXL346_3D_ORIENT(orient) - 1;
359 /* Report orientation only when it changes */
360 if (ac->orient3d_saved != orient_code) {
361 ac->orient3d_saved = orient_code;
362 adxl34x_report_key_single(ac->input,
363 pdata->ev_codes_orient_3d[orient_code]);
364 }
365 }
366 }
367
368 if (int_stat & (DATA_READY | WATERMARK)) {
369
370 if (pdata->fifo_mode)
371 samples = ENTRIES(AC_READ(ac, FIFO_STATUS)) + 1;
372 else
373 samples = 1;
374
375 for (; samples > 0; samples--) {
376 adxl34x_service_ev_fifo(ac);
377 /*
378 * To ensure that the FIFO has
379 * completely popped, there must be at least 5 us between
380 * the end of reading the data registers, signified by the
381 * transition to register 0x38 from 0x37 or the CS pin
382 * going high, and the start of new reads of the FIFO or
383 * reading the FIFO_STATUS register. For SPI operation at
384 * 1.5 MHz or lower, the register addressing portion of the
385 * transmission is sufficient delay to ensure the FIFO has
386 * completely popped. It is necessary for SPI operation
387 * greater than 1.5 MHz to de-assert the CS pin to ensure a
388 * total of 5 us, which is at most 3.4 us at 5 MHz
389 * operation.
390 */
391 if (ac->fifo_delay && (samples > 1))
392 udelay(3);
393 }
394 }
395
396 input_sync(ac->input);
397
398 return IRQ_HANDLED;
399}
400
401static void __adxl34x_disable(struct adxl34x *ac)
402{
403 /*
404 * A '0' places the ADXL34x into standby mode
405 * with minimum power consumption.
406 */
407 AC_WRITE(ac, POWER_CTL, 0);
408}
409
410static void __adxl34x_enable(struct adxl34x *ac)
411{
412 AC_WRITE(ac, POWER_CTL, ac->pdata.power_mode | PCTL_MEASURE);
413}
414
415void adxl34x_suspend(struct adxl34x *ac)
416{
417 mutex_lock(&ac->mutex);
418
419 if (!ac->suspended && !ac->disabled && ac->opened)
420 __adxl34x_disable(ac);
421
422 ac->suspended = true;
423
424 mutex_unlock(&ac->mutex);
425}
426EXPORT_SYMBOL_GPL(adxl34x_suspend);
427
428void adxl34x_resume(struct adxl34x *ac)
429{
430 mutex_lock(&ac->mutex);
431
432 if (ac->suspended && !ac->disabled && ac->opened)
433 __adxl34x_enable(ac);
434
435 ac->suspended = false;
436
437 mutex_unlock(&ac->mutex);
438}
439EXPORT_SYMBOL_GPL(adxl34x_resume);
440
441static ssize_t adxl34x_disable_show(struct device *dev,
442 struct device_attribute *attr, char *buf)
443{
444 struct adxl34x *ac = dev_get_drvdata(dev);
445
446 return sprintf(buf, "%u\n", ac->disabled);
447}
448
449static ssize_t adxl34x_disable_store(struct device *dev,
450 struct device_attribute *attr,
451 const char *buf, size_t count)
452{
453 struct adxl34x *ac = dev_get_drvdata(dev);
454 unsigned long val;
455 int error;
456
457 error = strict_strtoul(buf, 10, &val);
458 if (error)
459 return error;
460
461 mutex_lock(&ac->mutex);
462
463 if (!ac->suspended && ac->opened) {
464 if (val) {
465 if (!ac->disabled)
466 __adxl34x_disable(ac);
467 } else {
468 if (ac->disabled)
469 __adxl34x_enable(ac);
470 }
471 }
472
473 ac->disabled = !!val;
474
475 mutex_unlock(&ac->mutex);
476
477 return count;
478}
479
480static DEVICE_ATTR(disable, 0664, adxl34x_disable_show, adxl34x_disable_store);
481
482static ssize_t adxl34x_calibrate_show(struct device *dev,
483 struct device_attribute *attr, char *buf)
484{
485 struct adxl34x *ac = dev_get_drvdata(dev);
486 ssize_t count;
487
488 mutex_lock(&ac->mutex);
489 count = sprintf(buf, "%d,%d,%d\n",
490 ac->hwcal.x * 4 + ac->swcal.x,
491 ac->hwcal.y * 4 + ac->swcal.y,
492 ac->hwcal.z * 4 + ac->swcal.z);
493 mutex_unlock(&ac->mutex);
494
495 return count;
496}
497
498static ssize_t adxl34x_calibrate_store(struct device *dev,
499 struct device_attribute *attr,
500 const char *buf, size_t count)
501{
502 struct adxl34x *ac = dev_get_drvdata(dev);
503
504 /*
505 * Hardware offset calibration has a resolution of 15.6 mg/LSB.
506 * We use HW calibration and handle the remaining bits in SW. (4mg/LSB)
507 */
508
509 mutex_lock(&ac->mutex);
510 ac->hwcal.x -= (ac->saved.x / 4);
511 ac->swcal.x = ac->saved.x % 4;
512
513 ac->hwcal.y -= (ac->saved.y / 4);
514 ac->swcal.y = ac->saved.y % 4;
515
516 ac->hwcal.z -= (ac->saved.z / 4);
517 ac->swcal.z = ac->saved.z % 4;
518
519 AC_WRITE(ac, OFSX, (s8) ac->hwcal.x);
520 AC_WRITE(ac, OFSY, (s8) ac->hwcal.y);
521 AC_WRITE(ac, OFSZ, (s8) ac->hwcal.z);
522 mutex_unlock(&ac->mutex);
523
524 return count;
525}
526
527static DEVICE_ATTR(calibrate, 0664,
528 adxl34x_calibrate_show, adxl34x_calibrate_store);
529
530static ssize_t adxl34x_rate_show(struct device *dev,
531 struct device_attribute *attr, char *buf)
532{
533 struct adxl34x *ac = dev_get_drvdata(dev);
534
535 return sprintf(buf, "%u\n", RATE(ac->pdata.data_rate));
536}
537
538static ssize_t adxl34x_rate_store(struct device *dev,
539 struct device_attribute *attr,
540 const char *buf, size_t count)
541{
542 struct adxl34x *ac = dev_get_drvdata(dev);
543 unsigned long val;
544 int error;
545
546 error = strict_strtoul(buf, 10, &val);
547 if (error)
548 return error;
549
550 mutex_lock(&ac->mutex);
551
552 ac->pdata.data_rate = RATE(val);
553 AC_WRITE(ac, BW_RATE,
554 ac->pdata.data_rate |
555 (ac->pdata.low_power_mode ? LOW_POWER : 0));
556
557 mutex_unlock(&ac->mutex);
558
559 return count;
560}
561
562static DEVICE_ATTR(rate, 0664, adxl34x_rate_show, adxl34x_rate_store);
563
564static ssize_t adxl34x_autosleep_show(struct device *dev,
565 struct device_attribute *attr, char *buf)
566{
567 struct adxl34x *ac = dev_get_drvdata(dev);
568
569 return sprintf(buf, "%u\n",
570 ac->pdata.power_mode & (PCTL_AUTO_SLEEP | PCTL_LINK) ? 1 : 0);
571}
572
573static ssize_t adxl34x_autosleep_store(struct device *dev,
574 struct device_attribute *attr,
575 const char *buf, size_t count)
576{
577 struct adxl34x *ac = dev_get_drvdata(dev);
578 unsigned long val;
579 int error;
580
581 error = strict_strtoul(buf, 10, &val);
582 if (error)
583 return error;
584
585 mutex_lock(&ac->mutex);
586
587 if (val)
588 ac->pdata.power_mode |= (PCTL_AUTO_SLEEP | PCTL_LINK);
589 else
590 ac->pdata.power_mode &= ~(PCTL_AUTO_SLEEP | PCTL_LINK);
591
592 if (!ac->disabled && !ac->suspended && ac->opened)
593 AC_WRITE(ac, POWER_CTL, ac->pdata.power_mode | PCTL_MEASURE);
594
595 mutex_unlock(&ac->mutex);
596
597 return count;
598}
599
600static DEVICE_ATTR(autosleep, 0664,
601 adxl34x_autosleep_show, adxl34x_autosleep_store);
602
603static ssize_t adxl34x_position_show(struct device *dev,
604 struct device_attribute *attr, char *buf)
605{
606 struct adxl34x *ac = dev_get_drvdata(dev);
607 ssize_t count;
608
609 mutex_lock(&ac->mutex);
610 count = sprintf(buf, "(%d, %d, %d)\n",
611 ac->saved.x, ac->saved.y, ac->saved.z);
612 mutex_unlock(&ac->mutex);
613
614 return count;
615}
616
617static DEVICE_ATTR(position, S_IRUGO, adxl34x_position_show, NULL);
618
619#ifdef ADXL_DEBUG
620static ssize_t adxl34x_write_store(struct device *dev,
621 struct device_attribute *attr,
622 const char *buf, size_t count)
623{
624 struct adxl34x *ac = dev_get_drvdata(dev);
625 unsigned long val;
626 int error;
627
628 /*
629 * This allows basic ADXL register write access for debug purposes.
630 */
631 error = strict_strtoul(buf, 16, &val);
632 if (error)
633 return error;
634
635 mutex_lock(&ac->mutex);
636 AC_WRITE(ac, val >> 8, val & 0xFF);
637 mutex_unlock(&ac->mutex);
638
639 return count;
640}
641
642static DEVICE_ATTR(write, 0664, NULL, adxl34x_write_store);
643#endif
644
645static struct attribute *adxl34x_attributes[] = {
646 &dev_attr_disable.attr,
647 &dev_attr_calibrate.attr,
648 &dev_attr_rate.attr,
649 &dev_attr_autosleep.attr,
650 &dev_attr_position.attr,
651#ifdef ADXL_DEBUG
652 &dev_attr_write.attr,
653#endif
654 NULL
655};
656
657static const struct attribute_group adxl34x_attr_group = {
658 .attrs = adxl34x_attributes,
659};
660
661static int adxl34x_input_open(struct input_dev *input)
662{
663 struct adxl34x *ac = input_get_drvdata(input);
664
665 mutex_lock(&ac->mutex);
666
667 if (!ac->suspended && !ac->disabled)
668 __adxl34x_enable(ac);
669
670 ac->opened = true;
671
672 mutex_unlock(&ac->mutex);
673
674 return 0;
675}
676
677static void adxl34x_input_close(struct input_dev *input)
678{
679 struct adxl34x *ac = input_get_drvdata(input);
680
681 mutex_lock(&ac->mutex);
682
683 if (!ac->suspended && !ac->disabled)
684 __adxl34x_disable(ac);
685
686 ac->opened = false;
687
688 mutex_unlock(&ac->mutex);
689}
690
691struct adxl34x *adxl34x_probe(struct device *dev, int irq,
692 bool fifo_delay_default,
693 const struct adxl34x_bus_ops *bops)
694{
695 struct adxl34x *ac;
696 struct input_dev *input_dev;
697 const struct adxl34x_platform_data *pdata;
698 int err, range, i;
699 unsigned char revid;
700
701 if (!irq) {
702 dev_err(dev, "no IRQ?\n");
703 err = -ENODEV;
704 goto err_out;
705 }
706
707 ac = kzalloc(sizeof(*ac), GFP_KERNEL);
708 input_dev = input_allocate_device();
709 if (!ac || !input_dev) {
710 err = -ENOMEM;
711 goto err_free_mem;
712 }
713
714 ac->fifo_delay = fifo_delay_default;
715
716 pdata = dev->platform_data;
717 if (!pdata) {
718 dev_dbg(dev,
719 "No platfrom data: Using default initialization\n");
720 pdata = &adxl34x_default_init;
721 }
722
723 ac->pdata = *pdata;
724 pdata = &ac->pdata;
725
726 ac->input = input_dev;
727 ac->disabled = true;
728 ac->dev = dev;
729 ac->irq = irq;
730 ac->bops = bops;
731
732 mutex_init(&ac->mutex);
733
734 input_dev->name = "ADXL34x accelerometer";
735 revid = ac->bops->read(dev, DEVID);
736
737 switch (revid) {
738 case ID_ADXL345:
739 ac->model = 345;
740 break;
741 case ID_ADXL346:
742 ac->model = 346;
743 break;
744 default:
745 dev_err(dev, "Failed to probe %s\n", input_dev->name);
746 err = -ENODEV;
747 goto err_free_mem;
748 }
749
750 snprintf(ac->phys, sizeof(ac->phys), "%s/input0", dev_name(dev));
751
752 input_dev->phys = ac->phys;
753 input_dev->dev.parent = dev;
754 input_dev->id.product = ac->model;
755 input_dev->id.bustype = bops->bustype;
756 input_dev->open = adxl34x_input_open;
757 input_dev->close = adxl34x_input_close;
758
759 input_set_drvdata(input_dev, ac);
760
761 __set_bit(ac->pdata.ev_type, input_dev->evbit);
762
763 if (ac->pdata.ev_type == EV_REL) {
764 __set_bit(REL_X, input_dev->relbit);
765 __set_bit(REL_Y, input_dev->relbit);
766 __set_bit(REL_Z, input_dev->relbit);
767 } else {
768 /* EV_ABS */
769 __set_bit(ABS_X, input_dev->absbit);
770 __set_bit(ABS_Y, input_dev->absbit);
771 __set_bit(ABS_Z, input_dev->absbit);
772
773 if (pdata->data_range & FULL_RES)
774 range = ADXL_FULLRES_MAX_VAL; /* Signed 13-bit */
775 else
776 range = ADXL_FIXEDRES_MAX_VAL; /* Signed 10-bit */
777
778 input_set_abs_params(input_dev, ABS_X, -range, range, 3, 3);
779 input_set_abs_params(input_dev, ABS_Y, -range, range, 3, 3);
780 input_set_abs_params(input_dev, ABS_Z, -range, range, 3, 3);
781 }
782
783 __set_bit(EV_KEY, input_dev->evbit);
784 __set_bit(pdata->ev_code_tap[ADXL_X_AXIS], input_dev->keybit);
785 __set_bit(pdata->ev_code_tap[ADXL_Y_AXIS], input_dev->keybit);
786 __set_bit(pdata->ev_code_tap[ADXL_Z_AXIS], input_dev->keybit);
787
788 if (pdata->ev_code_ff) {
789 ac->int_mask = FREE_FALL;
790 __set_bit(pdata->ev_code_ff, input_dev->keybit);
791 }
792
793 if (pdata->ev_code_act_inactivity)
794 __set_bit(pdata->ev_code_act_inactivity, input_dev->keybit);
795
796 ac->int_mask |= ACTIVITY | INACTIVITY;
797
798 if (pdata->watermark) {
799 ac->int_mask |= WATERMARK;
800 if (!FIFO_MODE(pdata->fifo_mode))
801 ac->pdata.fifo_mode |= FIFO_STREAM;
802 } else {
803 ac->int_mask |= DATA_READY;
804 }
805
806 if (pdata->tap_axis_control & (TAP_X_EN | TAP_Y_EN | TAP_Z_EN))
807 ac->int_mask |= SINGLE_TAP | DOUBLE_TAP;
808
809 if (FIFO_MODE(pdata->fifo_mode) == FIFO_BYPASS)
810 ac->fifo_delay = false;
811
812 ac->bops->write(dev, POWER_CTL, 0);
813
814 err = request_threaded_irq(ac->irq, NULL, adxl34x_irq,
815 IRQF_TRIGGER_HIGH | IRQF_ONESHOT,
816 dev_name(dev), ac);
817 if (err) {
818 dev_err(dev, "irq %d busy?\n", ac->irq);
819 goto err_free_mem;
820 }
821
822 err = sysfs_create_group(&dev->kobj, &adxl34x_attr_group);
823 if (err)
824 goto err_free_irq;
825
826 err = input_register_device(input_dev);
827 if (err)
828 goto err_remove_attr;
829
830 AC_WRITE(ac, THRESH_TAP, pdata->tap_threshold);
831 AC_WRITE(ac, OFSX, pdata->x_axis_offset);
832 ac->hwcal.x = pdata->x_axis_offset;
833 AC_WRITE(ac, OFSY, pdata->y_axis_offset);
834 ac->hwcal.y = pdata->y_axis_offset;
835 AC_WRITE(ac, OFSZ, pdata->z_axis_offset);
836 ac->hwcal.z = pdata->z_axis_offset;
837 AC_WRITE(ac, THRESH_TAP, pdata->tap_threshold);
838 AC_WRITE(ac, DUR, pdata->tap_duration);
839 AC_WRITE(ac, LATENT, pdata->tap_latency);
840 AC_WRITE(ac, WINDOW, pdata->tap_window);
841 AC_WRITE(ac, THRESH_ACT, pdata->activity_threshold);
842 AC_WRITE(ac, THRESH_INACT, pdata->inactivity_threshold);
843 AC_WRITE(ac, TIME_INACT, pdata->inactivity_time);
844 AC_WRITE(ac, THRESH_FF, pdata->free_fall_threshold);
845 AC_WRITE(ac, TIME_FF, pdata->free_fall_time);
846 AC_WRITE(ac, TAP_AXES, pdata->tap_axis_control);
847 AC_WRITE(ac, ACT_INACT_CTL, pdata->act_axis_control);
848 AC_WRITE(ac, BW_RATE, RATE(ac->pdata.data_rate) |
849 (pdata->low_power_mode ? LOW_POWER : 0));
850 AC_WRITE(ac, DATA_FORMAT, pdata->data_range);
851 AC_WRITE(ac, FIFO_CTL, FIFO_MODE(pdata->fifo_mode) |
852 SAMPLES(pdata->watermark));
853
854 if (pdata->use_int2) {
855 /* Map all INTs to INT2 */
856 AC_WRITE(ac, INT_MAP, ac->int_mask | OVERRUN);
857 } else {
858 /* Map all INTs to INT1 */
859 AC_WRITE(ac, INT_MAP, 0);
860 }
861
862 if (ac->model == 346 && ac->pdata.orientation_enable) {
863 AC_WRITE(ac, ORIENT_CONF,
864 ORIENT_DEADZONE(ac->pdata.deadzone_angle) |
865 ORIENT_DIVISOR(ac->pdata.divisor_length));
866
867 ac->orient2d_saved = 1234;
868 ac->orient3d_saved = 1234;
869
870 if (pdata->orientation_enable & ADXL_EN_ORIENTATION_3D)
871 for (i = 0; i < ARRAY_SIZE(pdata->ev_codes_orient_3d); i++)
872 __set_bit(pdata->ev_codes_orient_3d[i],
873 input_dev->keybit);
874
875 if (pdata->orientation_enable & ADXL_EN_ORIENTATION_2D)
876 for (i = 0; i < ARRAY_SIZE(pdata->ev_codes_orient_2d); i++)
877 __set_bit(pdata->ev_codes_orient_2d[i],
878 input_dev->keybit);
879 } else {
880 ac->pdata.orientation_enable = 0;
881 }
882
883 AC_WRITE(ac, INT_ENABLE, ac->int_mask | OVERRUN);
884
885 ac->pdata.power_mode &= (PCTL_AUTO_SLEEP | PCTL_LINK);
886
887 return ac;
888
889 err_remove_attr:
890 sysfs_remove_group(&dev->kobj, &adxl34x_attr_group);
891 err_free_irq:
892 free_irq(ac->irq, ac);
893 err_free_mem:
894 input_free_device(input_dev);
895 kfree(ac);
896 err_out:
897 return ERR_PTR(err);
898}
899EXPORT_SYMBOL_GPL(adxl34x_probe);
900
901int adxl34x_remove(struct adxl34x *ac)
902{
903 sysfs_remove_group(&ac->dev->kobj, &adxl34x_attr_group);
904 free_irq(ac->irq, ac);
905 input_unregister_device(ac->input);
906 dev_dbg(ac->dev, "unregistered accelerometer\n");
907 kfree(ac);
908
909 return 0;
910}
911EXPORT_SYMBOL_GPL(adxl34x_remove);
912
913MODULE_AUTHOR("Michael Hennerich <hennerich@blackfin.uclinux.org>");
914MODULE_DESCRIPTION("ADXL345/346 Three-Axis Digital Accelerometer Driver");
915MODULE_LICENSE("GPL");
diff --git a/drivers/input/misc/adxl34x.h b/drivers/input/misc/adxl34x.h
new file mode 100644
index 000000000000..bbbc80fda164
--- /dev/null
+++ b/drivers/input/misc/adxl34x.h
@@ -0,0 +1,30 @@
1/*
2 * ADXL345/346 Three-Axis Digital Accelerometers (I2C/SPI Interface)
3 *
4 * Enter bugs at http://blackfin.uclinux.org/
5 *
6 * Copyright (C) 2009 Michael Hennerich, Analog Devices Inc.
7 * Licensed under the GPL-2 or later.
8 */
9
10#ifndef _ADXL34X_H_
11#define _ADXL34X_H_
12
13struct device;
14struct adxl34x;
15
16struct adxl34x_bus_ops {
17 u16 bustype;
18 int (*read)(struct device *, unsigned char);
19 int (*read_block)(struct device *, unsigned char, int, void *);
20 int (*write)(struct device *, unsigned char, unsigned char);
21};
22
23void adxl34x_suspend(struct adxl34x *ac);
24void adxl34x_resume(struct adxl34x *ac);
25struct adxl34x *adxl34x_probe(struct device *dev, int irq,
26 bool fifo_delay_default,
27 const struct adxl34x_bus_ops *bops);
28int adxl34x_remove(struct adxl34x *ac);
29
30#endif
diff --git a/drivers/input/misc/atlas_btns.c b/drivers/input/misc/atlas_btns.c
index dfaa9a045ed8..601f7372f9c4 100644
--- a/drivers/input/misc/atlas_btns.c
+++ b/drivers/input/misc/atlas_btns.c
@@ -21,6 +21,8 @@
21 * 21 *
22 */ 22 */
23 23
24#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
25
24#include <linux/kernel.h> 26#include <linux/kernel.h>
25#include <linux/module.h> 27#include <linux/module.h>
26#include <linux/init.h> 28#include <linux/init.h>
@@ -60,12 +62,11 @@ static acpi_status acpi_atlas_button_handler(u32 function,
60 input_report_key(input_dev, atlas_keymap[code], key_down); 62 input_report_key(input_dev, atlas_keymap[code], key_down);
61 input_sync(input_dev); 63 input_sync(input_dev);
62 64
63 status = 0; 65 status = AE_OK;
64 } else { 66 } else {
65 printk(KERN_WARNING "atlas: shrugged on unexpected function" 67 pr_warn("shrugged on unexpected function: function=%x,address=%lx,value=%x\n",
66 ":function=%x,address=%lx,value=%x\n",
67 function, (unsigned long)address, (u32)*value); 68 function, (unsigned long)address, (u32)*value);
68 status = -EINVAL; 69 status = AE_BAD_PARAMETER;
69 } 70 }
70 71
71 return status; 72 return status;
@@ -79,7 +80,7 @@ static int atlas_acpi_button_add(struct acpi_device *device)
79 80
80 input_dev = input_allocate_device(); 81 input_dev = input_allocate_device();
81 if (!input_dev) { 82 if (!input_dev) {
82 printk(KERN_ERR "atlas: unable to allocate input device\n"); 83 pr_err("unable to allocate input device\n");
83 return -ENOMEM; 84 return -ENOMEM;
84 } 85 }
85 86
@@ -102,7 +103,7 @@ static int atlas_acpi_button_add(struct acpi_device *device)
102 103
103 err = input_register_device(input_dev); 104 err = input_register_device(input_dev);
104 if (err) { 105 if (err) {
105 printk(KERN_ERR "atlas: couldn't register input device\n"); 106 pr_err("couldn't register input device\n");
106 input_free_device(input_dev); 107 input_free_device(input_dev);
107 return err; 108 return err;
108 } 109 }
@@ -112,12 +113,12 @@ static int atlas_acpi_button_add(struct acpi_device *device)
112 0x81, &acpi_atlas_button_handler, 113 0x81, &acpi_atlas_button_handler,
113 &acpi_atlas_button_setup, device); 114 &acpi_atlas_button_setup, device);
114 if (ACPI_FAILURE(status)) { 115 if (ACPI_FAILURE(status)) {
115 printk(KERN_ERR "Atlas: Error installing addr spc handler\n"); 116 pr_err("error installing addr spc handler\n");
116 input_unregister_device(input_dev); 117 input_unregister_device(input_dev);
117 status = -EINVAL; 118 err = -EINVAL;
118 } 119 }
119 120
120 return status; 121 return err;
121} 122}
122 123
123static int atlas_acpi_button_remove(struct acpi_device *device, int type) 124static int atlas_acpi_button_remove(struct acpi_device *device, int type)
@@ -126,14 +127,12 @@ static int atlas_acpi_button_remove(struct acpi_device *device, int type)
126 127
127 status = acpi_remove_address_space_handler(device->handle, 128 status = acpi_remove_address_space_handler(device->handle,
128 0x81, &acpi_atlas_button_handler); 129 0x81, &acpi_atlas_button_handler);
129 if (ACPI_FAILURE(status)) { 130 if (ACPI_FAILURE(status))
130 printk(KERN_ERR "Atlas: Error removing addr spc handler\n"); 131 pr_err("error removing addr spc handler\n");
131 status = -EINVAL;
132 }
133 132
134 input_unregister_device(input_dev); 133 input_unregister_device(input_dev);
135 134
136 return status; 135 return 0;
137} 136}
138 137
139static const struct acpi_device_id atlas_device_ids[] = { 138static const struct acpi_device_id atlas_device_ids[] = {
@@ -145,6 +144,7 @@ MODULE_DEVICE_TABLE(acpi, atlas_device_ids);
145static struct acpi_driver atlas_acpi_driver = { 144static struct acpi_driver atlas_acpi_driver = {
146 .name = ACPI_ATLAS_NAME, 145 .name = ACPI_ATLAS_NAME,
147 .class = ACPI_ATLAS_CLASS, 146 .class = ACPI_ATLAS_CLASS,
147 .owner = THIS_MODULE,
148 .ids = atlas_device_ids, 148 .ids = atlas_device_ids,
149 .ops = { 149 .ops = {
150 .add = atlas_acpi_button_add, 150 .add = atlas_acpi_button_add,
@@ -154,18 +154,10 @@ static struct acpi_driver atlas_acpi_driver = {
154 154
155static int __init atlas_acpi_init(void) 155static int __init atlas_acpi_init(void)
156{ 156{
157 int result;
158
159 if (acpi_disabled) 157 if (acpi_disabled)
160 return -ENODEV; 158 return -ENODEV;
161 159
162 result = acpi_bus_register_driver(&atlas_acpi_driver); 160 return acpi_bus_register_driver(&atlas_acpi_driver);
163 if (result < 0) {
164 printk(KERN_ERR "Atlas ACPI: Unable to register driver\n");
165 return -ENODEV;
166 }
167
168 return 0;
169} 161}
170 162
171static void __exit atlas_acpi_exit(void) 163static void __exit atlas_acpi_exit(void)
diff --git a/drivers/input/misc/pwm-beeper.c b/drivers/input/misc/pwm-beeper.c
new file mode 100644
index 000000000000..57c294f07198
--- /dev/null
+++ b/drivers/input/misc/pwm-beeper.c
@@ -0,0 +1,199 @@
1/*
2 * Copyright (C) 2010, Lars-Peter Clausen <lars@metafoo.de>
3 * PWM beeper driver
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License as published by the
7 * Free Software Foundation; either version 2 of the License, or (at your
8 * option) any later version.
9 *
10 * You should have received a copy of the GNU General Public License along
11 * with this program; if not, write to the Free Software Foundation, Inc.,
12 * 675 Mass Ave, Cambridge, MA 02139, USA.
13 *
14 */
15
16#include <linux/input.h>
17#include <linux/module.h>
18#include <linux/kernel.h>
19#include <linux/platform_device.h>
20#include <linux/pwm.h>
21#include <linux/slab.h>
22
23struct pwm_beeper {
24 struct input_dev *input;
25 struct pwm_device *pwm;
26 unsigned long period;
27};
28
29#define HZ_TO_NANOSECONDS(x) (1000000000UL/(x))
30
31static int pwm_beeper_event(struct input_dev *input,
32 unsigned int type, unsigned int code, int value)
33{
34 int ret = 0;
35 struct pwm_beeper *beeper = input_get_drvdata(input);
36 unsigned long period;
37
38 if (type != EV_SND || value < 0)
39 return -EINVAL;
40
41 switch (code) {
42 case SND_BELL:
43 value = value ? 1000 : 0;
44 break;
45 case SND_TONE:
46 break;
47 default:
48 return -EINVAL;
49 }
50
51 if (value == 0) {
52 pwm_config(beeper->pwm, 0, 0);
53 pwm_disable(beeper->pwm);
54 } else {
55 period = HZ_TO_NANOSECONDS(value);
56 ret = pwm_config(beeper->pwm, period / 2, period);
57 if (ret)
58 return ret;
59 ret = pwm_enable(beeper->pwm);
60 if (ret)
61 return ret;
62 beeper->period = period;
63 }
64
65 return 0;
66}
67
68static int __devinit pwm_beeper_probe(struct platform_device *pdev)
69{
70 unsigned long pwm_id = (unsigned long)pdev->dev.platform_data;
71 struct pwm_beeper *beeper;
72 int error;
73
74 beeper = kzalloc(sizeof(*beeper), GFP_KERNEL);
75 if (!beeper)
76 return -ENOMEM;
77
78 beeper->pwm = pwm_request(pwm_id, "pwm beeper");
79
80 if (IS_ERR(beeper->pwm)) {
81 error = PTR_ERR(beeper->pwm);
82 dev_err(&pdev->dev, "Failed to request pwm device: %d\n", error);
83 goto err_free;
84 }
85
86 beeper->input = input_allocate_device();
87 if (!beeper->input) {
88 dev_err(&pdev->dev, "Failed to allocate input device\n");
89 error = -ENOMEM;
90 goto err_pwm_free;
91 }
92 beeper->input->dev.parent = &pdev->dev;
93
94 beeper->input->name = "pwm-beeper";
95 beeper->input->phys = "pwm/input0";
96 beeper->input->id.bustype = BUS_HOST;
97 beeper->input->id.vendor = 0x001f;
98 beeper->input->id.product = 0x0001;
99 beeper->input->id.version = 0x0100;
100
101 beeper->input->evbit[0] = BIT(EV_SND);
102 beeper->input->sndbit[0] = BIT(SND_TONE) | BIT(SND_BELL);
103
104 beeper->input->event = pwm_beeper_event;
105
106 input_set_drvdata(beeper->input, beeper);
107
108 error = input_register_device(beeper->input);
109 if (error) {
110 dev_err(&pdev->dev, "Failed to register input device: %d\n", error);
111 goto err_input_free;
112 }
113
114 platform_set_drvdata(pdev, beeper);
115
116 return 0;
117
118err_input_free:
119 input_free_device(beeper->input);
120err_pwm_free:
121 pwm_free(beeper->pwm);
122err_free:
123 kfree(beeper);
124
125 return error;
126}
127
128static int __devexit pwm_beeper_remove(struct platform_device *pdev)
129{
130 struct pwm_beeper *beeper = platform_get_drvdata(pdev);
131
132 platform_set_drvdata(pdev, NULL);
133 input_unregister_device(beeper->input);
134
135 pwm_disable(beeper->pwm);
136 pwm_free(beeper->pwm);
137
138 kfree(beeper);
139
140 return 0;
141}
142
143#ifdef CONFIG_PM
144static int pwm_beeper_suspend(struct device *dev)
145{
146 struct pwm_beeper *beeper = dev_get_drvdata(dev);
147
148 if (beeper->period)
149 pwm_disable(beeper->pwm);
150
151 return 0;
152}
153
154static int pwm_beeper_resume(struct device *dev)
155{
156 struct pwm_beeper *beeper = dev_get_drvdata(dev);
157
158 if (beeper->period) {
159 pwm_config(beeper->pwm, beeper->period / 2, beeper->period);
160 pwm_enable(beeper->pwm);
161 }
162
163 return 0;
164}
165
166static SIMPLE_DEV_PM_OPS(pwm_beeper_pm_ops,
167 pwm_beeper_suspend, pwm_beeper_resume);
168
169#define PWM_BEEPER_PM_OPS (&pwm_beeper_pm_ops)
170#else
171#define PWM_BEEPER_PM_OPS NULL
172#endif
173
174static struct platform_driver pwm_beeper_driver = {
175 .probe = pwm_beeper_probe,
176 .remove = __devexit_p(pwm_beeper_remove),
177 .driver = {
178 .name = "pwm-beeper",
179 .owner = THIS_MODULE,
180 .pm = PWM_BEEPER_PM_OPS,
181 },
182};
183
184static int __init pwm_beeper_init(void)
185{
186 return platform_driver_register(&pwm_beeper_driver);
187}
188module_init(pwm_beeper_init);
189
190static void __exit pwm_beeper_exit(void)
191{
192 platform_driver_unregister(&pwm_beeper_driver);
193}
194module_exit(pwm_beeper_exit);
195
196MODULE_AUTHOR("Lars-Peter Clausen <lars@metafoo.de>");
197MODULE_DESCRIPTION("PWM beeper driver");
198MODULE_LICENSE("GPL");
199MODULE_ALIAS("platform:pwm-beeper");
diff --git a/drivers/input/misc/twl4030-pwrbutton.c b/drivers/input/misc/twl4030-pwrbutton.c
index e9069b87fde2..f16972bddca4 100644
--- a/drivers/input/misc/twl4030-pwrbutton.c
+++ b/drivers/input/misc/twl4030-pwrbutton.c
@@ -52,7 +52,7 @@ static irqreturn_t powerbutton_irq(int irq, void *_pwr)
52 return IRQ_HANDLED; 52 return IRQ_HANDLED;
53} 53}
54 54
55static int __devinit twl4030_pwrbutton_probe(struct platform_device *pdev) 55static int __init twl4030_pwrbutton_probe(struct platform_device *pdev)
56{ 56{
57 struct input_dev *pwr; 57 struct input_dev *pwr;
58 int irq = platform_get_irq(pdev, 0); 58 int irq = platform_get_irq(pdev, 0);
@@ -95,7 +95,7 @@ free_input_dev:
95 return err; 95 return err;
96} 96}
97 97
98static int __devexit twl4030_pwrbutton_remove(struct platform_device *pdev) 98static int __exit twl4030_pwrbutton_remove(struct platform_device *pdev)
99{ 99{
100 struct input_dev *pwr = platform_get_drvdata(pdev); 100 struct input_dev *pwr = platform_get_drvdata(pdev);
101 int irq = platform_get_irq(pdev, 0); 101 int irq = platform_get_irq(pdev, 0);
@@ -106,9 +106,8 @@ static int __devexit twl4030_pwrbutton_remove(struct platform_device *pdev)
106 return 0; 106 return 0;
107} 107}
108 108
109struct platform_driver twl4030_pwrbutton_driver = { 109static struct platform_driver twl4030_pwrbutton_driver = {
110 .probe = twl4030_pwrbutton_probe, 110 .remove = __exit_p(twl4030_pwrbutton_remove),
111 .remove = __devexit_p(twl4030_pwrbutton_remove),
112 .driver = { 111 .driver = {
113 .name = "twl4030_pwrbutton", 112 .name = "twl4030_pwrbutton",
114 .owner = THIS_MODULE, 113 .owner = THIS_MODULE,
@@ -117,7 +116,8 @@ struct platform_driver twl4030_pwrbutton_driver = {
117 116
118static int __init twl4030_pwrbutton_init(void) 117static int __init twl4030_pwrbutton_init(void)
119{ 118{
120 return platform_driver_register(&twl4030_pwrbutton_driver); 119 return platform_driver_probe(&twl4030_pwrbutton_driver,
120 twl4030_pwrbutton_probe);
121} 121}
122module_init(twl4030_pwrbutton_init); 122module_init(twl4030_pwrbutton_init);
123 123
diff --git a/drivers/input/misc/wistron_btns.c b/drivers/input/misc/wistron_btns.c
index 4dac8b79fcd4..12501de0c5cd 100644
--- a/drivers/input/misc/wistron_btns.c
+++ b/drivers/input/misc/wistron_btns.c
@@ -1347,7 +1347,7 @@ static int __init wb_module_init(void)
1347 1347
1348 err = map_bios(); 1348 err = map_bios();
1349 if (err) 1349 if (err)
1350 return err; 1350 goto err_free_keymap;
1351 1351
1352 err = platform_driver_register(&wistron_driver); 1352 err = platform_driver_register(&wistron_driver);
1353 if (err) 1353 if (err)
@@ -1371,6 +1371,8 @@ static int __init wb_module_init(void)
1371 platform_driver_unregister(&wistron_driver); 1371 platform_driver_unregister(&wistron_driver);
1372 err_unmap_bios: 1372 err_unmap_bios:
1373 unmap_bios(); 1373 unmap_bios();
1374 err_free_keymap:
1375 kfree(keymap);
1374 1376
1375 return err; 1377 return err;
1376} 1378}