]> git.karo-electronics.de Git - karo-tx-linux.git/blob - drivers/iio/imu/adis.c
staging:iio: Move adis library out of staging
[karo-tx-linux.git] / drivers / iio / imu / adis.c
1 /*
2  * Common library for ADIS16XXX devices
3  *
4  * Copyright 2012 Analog Devices Inc.
5  *   Author: Lars-Peter Clausen <lars@metafoo.de>
6  *
7  * Licensed under the GPL-2 or later.
8  */
9
10 #include <linux/delay.h>
11 #include <linux/mutex.h>
12 #include <linux/device.h>
13 #include <linux/kernel.h>
14 #include <linux/spi/spi.h>
15 #include <linux/slab.h>
16 #include <linux/sysfs.h>
17 #include <linux/module.h>
18 #include <asm/unaligned.h>
19
20 #include <linux/iio/iio.h>
21 #include <linux/iio/sysfs.h>
22 #include <linux/iio/buffer.h>
23 #include <linux/iio/imu/adis.h>
24
25 #define ADIS_MSC_CTRL_DATA_RDY_EN       BIT(2)
26 #define ADIS_MSC_CTRL_DATA_RDY_POL_HIGH BIT(1)
27 #define ADIS_MSC_CTRL_DATA_RDY_DIO2     BIT(0)
28 #define ADIS_GLOB_CMD_SW_RESET          BIT(7)
29
30 /**
31  * adis_write_reg_8() - Write single byte to a register
32  * @adis: The adis device
33  * @reg: The address of the register to be written
34  * @val: The value to write
35  */
36 int adis_write_reg_8(struct adis *adis, unsigned int reg, uint8_t val)
37 {
38         int ret;
39
40         mutex_lock(&adis->txrx_lock);
41         adis->tx[0] = ADIS_WRITE_REG(reg);
42         adis->tx[1] = val;
43
44         ret = spi_write(adis->spi, adis->tx, 2);
45         mutex_unlock(&adis->txrx_lock);
46
47         return ret;
48 }
49 EXPORT_SYMBOL_GPL(adis_write_reg_8);
50
51 /**
52  * adis_write_reg_16() - Write 2 bytes to a pair of registers
53  * @adis: The adis device
54  * @reg: The address of the lower of the two registers
55  * @val: Value to be written
56  */
57 int adis_write_reg_16(struct adis *adis, unsigned int reg, uint16_t value)
58 {
59         int ret;
60         struct spi_message msg;
61         struct spi_transfer xfers[] = {
62                 {
63                         .tx_buf = adis->tx,
64                         .bits_per_word = 8,
65                         .len = 2,
66                         .cs_change = 1,
67                         .delay_usecs = adis->data->write_delay,
68                 }, {
69                         .tx_buf = adis->tx + 2,
70                         .bits_per_word = 8,
71                         .len = 2,
72                         .delay_usecs = adis->data->write_delay,
73                 },
74         };
75
76         mutex_lock(&adis->txrx_lock);
77         adis->tx[0] = ADIS_WRITE_REG(reg);
78         adis->tx[1] = value & 0xff;
79         adis->tx[2] = ADIS_WRITE_REG(reg + 1);
80         adis->tx[3] = (value >> 8) & 0xff;
81
82         spi_message_init(&msg);
83         spi_message_add_tail(&xfers[0], &msg);
84         spi_message_add_tail(&xfers[1], &msg);
85         ret = spi_sync(adis->spi, &msg);
86         mutex_unlock(&adis->txrx_lock);
87
88         return ret;
89 }
90 EXPORT_SYMBOL_GPL(adis_write_reg_16);
91
92 /**
93  * adis_read_reg_16() - read 2 bytes from a 16-bit register
94  * @adis: The adis device
95  * @reg: The address of the lower of the two registers
96  * @val: The value read back from the device
97  */
98 int adis_read_reg_16(struct adis *adis, unsigned int reg, uint16_t *val)
99 {
100         struct spi_message msg;
101         int ret;
102         struct spi_transfer xfers[] = {
103                 {
104                         .tx_buf = adis->tx,
105                         .bits_per_word = 8,
106                         .len = 2,
107                         .cs_change = 1,
108                         .delay_usecs = adis->data->read_delay,
109                 }, {
110                         .rx_buf = adis->rx,
111                         .bits_per_word = 8,
112                         .len = 2,
113                         .delay_usecs = adis->data->read_delay,
114                 },
115         };
116
117         mutex_lock(&adis->txrx_lock);
118         adis->tx[0] = ADIS_READ_REG(reg);
119         adis->tx[1] = 0;
120
121         spi_message_init(&msg);
122         spi_message_add_tail(&xfers[0], &msg);
123         spi_message_add_tail(&xfers[1], &msg);
124         ret = spi_sync(adis->spi, &msg);
125         if (ret) {
126                 dev_err(&adis->spi->dev, "Failed to read 16 bit register 0x%02X: %d\n",
127                                 reg, ret);
128                 goto error_ret;
129         }
130         *val = get_unaligned_be16(adis->rx);
131
132 error_ret:
133         mutex_unlock(&adis->txrx_lock);
134         return ret;
135 }
136 EXPORT_SYMBOL_GPL(adis_read_reg_16);
137
138 /**
139  * adis_enable_irq() - Enable or disable data ready IRQ
140  * @adis: The adis device
141  * @enable: Whether to enable the IRQ
142  *
143  * Returns 0 on success, negative error code otherwise
144  */
145 int adis_enable_irq(struct adis *adis, bool enable)
146 {
147         int ret = 0;
148         uint16_t msc;
149
150         ret = adis_read_reg_16(adis, adis->data->msc_ctrl_reg, &msc);
151         if (ret)
152                 goto error_ret;
153
154         msc |= ADIS_MSC_CTRL_DATA_RDY_POL_HIGH;
155         msc &= ~ADIS_MSC_CTRL_DATA_RDY_DIO2;
156         if (enable)
157                 msc |= ADIS_MSC_CTRL_DATA_RDY_EN;
158         else
159                 msc &= ~ADIS_MSC_CTRL_DATA_RDY_EN;
160
161         ret = adis_write_reg_16(adis, adis->data->msc_ctrl_reg, msc);
162
163 error_ret:
164         return ret;
165 }
166 EXPORT_SYMBOL(adis_enable_irq);
167
168 /**
169  * adis_check_status() - Check the device for error conditions
170  * @adis: The adis device
171  *
172  * Returns 0 on success, a negative error code otherwise
173  */
174 int adis_check_status(struct adis *adis)
175 {
176         uint16_t status;
177         int ret;
178         int i;
179
180         ret = adis_read_reg_16(adis, adis->data->diag_stat_reg, &status);
181         if (ret < 0)
182                 return ret;
183
184         status &= adis->data->status_error_mask;
185
186         if (status == 0)
187                 return 0;
188
189         for (i = 0; i < 16; ++i) {
190                 if (status & BIT(i)) {
191                         dev_err(&adis->spi->dev, "%s.\n",
192                                 adis->data->status_error_msgs[i]);
193                 }
194         }
195
196         return -EIO;
197 }
198 EXPORT_SYMBOL_GPL(adis_check_status);
199
200 /**
201  * adis_reset() - Reset the device
202  * @adis: The adis device
203  *
204  * Returns 0 on success, a negative error code otherwise
205  */
206 int adis_reset(struct adis *adis)
207 {
208         int ret;
209
210         ret = adis_write_reg_8(adis, adis->data->glob_cmd_reg,
211                         ADIS_GLOB_CMD_SW_RESET);
212         if (ret)
213                 dev_err(&adis->spi->dev, "Failed to reset device: %d\n", ret);
214
215         return ret;
216 }
217 EXPORT_SYMBOL_GPL(adis_reset);
218
219 static int adis_self_test(struct adis *adis)
220 {
221         int ret;
222
223         ret = adis_write_reg_16(adis, adis->data->msc_ctrl_reg,
224                         adis->data->self_test_mask);
225         if (ret) {
226                 dev_err(&adis->spi->dev, "Failed to initiate self test: %d\n",
227                         ret);
228                 return ret;
229         }
230
231         msleep(adis->data->startup_delay);
232
233         return adis_check_status(adis);
234 }
235
236 /**
237  * adis_inital_startup() - Performs device self-test
238  * @adis: The adis device
239  *
240  * Returns 0 if the device is operational, a negative error code otherwise.
241  *
242  * This function should be called early on in the device initialization sequence
243  * to ensure that the device is in a sane and known state and that it is usable.
244  */
245 int adis_initial_startup(struct adis *adis)
246 {
247         int ret;
248
249         ret = adis_self_test(adis);
250         if (ret) {
251                 dev_err(&adis->spi->dev, "Self-test failed, trying reset.\n");
252                 adis_reset(adis);
253                 msleep(adis->data->startup_delay);
254                 ret = adis_self_test(adis);
255                 if (ret) {
256                         dev_err(&adis->spi->dev, "Second self-test failed, giving up.\n");
257                         return ret;
258                 }
259         }
260
261         return 0;
262 }
263 EXPORT_SYMBOL_GPL(adis_initial_startup);
264
265 /**
266  * adis_single_conversion() - Performs a single sample conversion
267  * @indio_dev: The IIO device
268  * @chan: The IIO channel
269  * @error_mask: Mask for the error bit
270  * @val: Result of the conversion
271  *
272  * Returns IIO_VAL_INT on success, a negative error code otherwise.
273  *
274  * The function performs a single conversion on a given channel and post
275  * processes the value accordingly to the channel spec. If a error_mask is given
276  * the function will check if the mask is set in the returned raw value. If it
277  * is set the function will perform a self-check. If the device does not report
278  * a error bit in the channels raw value set error_mask to 0.
279  */
280 int adis_single_conversion(struct iio_dev *indio_dev,
281         const struct iio_chan_spec *chan, unsigned int error_mask, int *val)
282 {
283         struct adis *adis = iio_device_get_drvdata(indio_dev);
284         uint16_t val16;
285         int ret;
286
287         mutex_lock(&indio_dev->mlock);
288
289         ret = adis_read_reg_16(adis, chan->address, &val16);
290         if (ret)
291                 goto err_unlock;
292
293         if (val16 & error_mask) {
294                 ret = adis_check_status(adis);
295                 if (ret)
296                         goto err_unlock;
297         }
298
299         if (chan->scan_type.sign == 's')
300                 *val = sign_extend32(val16, chan->scan_type.realbits - 1);
301         else
302                 *val = val16 & ((1 << chan->scan_type.realbits) - 1);
303
304         ret = IIO_VAL_INT;
305 err_unlock:
306         mutex_unlock(&indio_dev->mlock);
307         return ret;
308 }
309 EXPORT_SYMBOL_GPL(adis_single_conversion);
310
311 /**
312  * adis_init() - Initialize adis device structure
313  * @adis:       The adis device
314  * @indio_dev:  The iio device
315  * @spi:        The spi device
316  * @data:       Chip specific data
317  *
318  * Returns 0 on success, a negative error code otherwise.
319  *
320  * This function must be called, before any other adis helper function may be
321  * called.
322  */
323 int adis_init(struct adis *adis, struct iio_dev *indio_dev,
324         struct spi_device *spi, const struct adis_data *data)
325 {
326         mutex_init(&adis->txrx_lock);
327         adis->spi = spi;
328         adis->data = data;
329         iio_device_set_drvdata(indio_dev, adis);
330
331         return adis_enable_irq(adis, false);
332 }
333 EXPORT_SYMBOL_GPL(adis_init);
334
335 MODULE_LICENSE("GPL");
336 MODULE_AUTHOR("Lars-Peter Clausen <lars@metafoo.de>");
337 MODULE_DESCRIPTION("Common library code for ADIS16XXX devices");