1 // SPDX-License-Identifier: GPL-2.0-only
3 * BMA220 Digital triaxial acceleration sensor driver
5 * Copyright (c) 2016,2020 Intel Corporation.
8 #include <linux/bits.h>
9 #include <linux/kernel.h>
10 #include <linux/mod_devicetable.h>
11 #include <linux/module.h>
12 #include <linux/types.h>
13 #include <linux/spi/spi.h>
15 #include <linux/iio/buffer.h>
16 #include <linux/iio/iio.h>
17 #include <linux/iio/sysfs.h>
18 #include <linux/iio/trigger_consumer.h>
19 #include <linux/iio/triggered_buffer.h>
21 #define BMA220_REG_ID 0x00
22 #define BMA220_REG_ACCEL_X 0x02
23 #define BMA220_REG_ACCEL_Y 0x03
24 #define BMA220_REG_ACCEL_Z 0x04
25 #define BMA220_REG_RANGE 0x11
26 #define BMA220_REG_SUSPEND 0x18
28 #define BMA220_CHIP_ID 0xDD
29 #define BMA220_READ_MASK BIT(7)
30 #define BMA220_RANGE_MASK GENMASK(1, 0)
31 #define BMA220_SUSPEND_SLEEP 0xFF
32 #define BMA220_SUSPEND_WAKE 0x00
34 #define BMA220_DEVICE_NAME "bma220"
36 #define BMA220_ACCEL_CHANNEL(index, reg, axis) { \
40 .channel2 = IIO_MOD_##axis, \
41 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), \
42 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE), \
43 .scan_index = index, \
49 .endianness = IIO_CPU, \
59 static const int bma220_scale_table
[][2] = {
60 {0, 623000}, {1, 248000}, {2, 491000}, {4, 983000},
64 struct spi_device
*spi_device
;
68 /* Ensure timestamp is naturally aligned. */
69 s64 timestamp
__aligned(8);
71 u8 tx_buf
[2] __aligned(IIO_DMA_MINALIGN
);
74 static const struct iio_chan_spec bma220_channels
[] = {
75 BMA220_ACCEL_CHANNEL(0, BMA220_REG_ACCEL_X
, X
),
76 BMA220_ACCEL_CHANNEL(1, BMA220_REG_ACCEL_Y
, Y
),
77 BMA220_ACCEL_CHANNEL(2, BMA220_REG_ACCEL_Z
, Z
),
78 IIO_CHAN_SOFT_TIMESTAMP(3),
81 static inline int bma220_read_reg(struct spi_device
*spi
, u8 reg
)
83 return spi_w8r8(spi
, reg
| BMA220_READ_MASK
);
86 static const unsigned long bma220_accel_scan_masks
[] = {
87 BIT(AXIS_X
) | BIT(AXIS_Y
) | BIT(AXIS_Z
),
91 static irqreturn_t
bma220_trigger_handler(int irq
, void *p
)
94 struct iio_poll_func
*pf
= p
;
95 struct iio_dev
*indio_dev
= pf
->indio_dev
;
96 struct bma220_data
*data
= iio_priv(indio_dev
);
97 struct spi_device
*spi
= data
->spi_device
;
99 mutex_lock(&data
->lock
);
100 data
->tx_buf
[0] = BMA220_REG_ACCEL_X
| BMA220_READ_MASK
;
101 ret
= spi_write_then_read(spi
, data
->tx_buf
, 1, &data
->scan
.chans
,
102 ARRAY_SIZE(bma220_channels
) - 1);
106 iio_push_to_buffers_with_timestamp(indio_dev
, &data
->scan
,
109 mutex_unlock(&data
->lock
);
110 iio_trigger_notify_done(indio_dev
->trig
);
115 static int bma220_read_raw(struct iio_dev
*indio_dev
,
116 struct iio_chan_spec
const *chan
,
117 int *val
, int *val2
, long mask
)
121 struct bma220_data
*data
= iio_priv(indio_dev
);
124 case IIO_CHAN_INFO_RAW
:
125 ret
= bma220_read_reg(data
->spi_device
, chan
->address
);
128 *val
= sign_extend32(ret
>> chan
->scan_type
.shift
,
129 chan
->scan_type
.realbits
- 1);
131 case IIO_CHAN_INFO_SCALE
:
132 ret
= bma220_read_reg(data
->spi_device
, BMA220_REG_RANGE
);
135 range_idx
= ret
& BMA220_RANGE_MASK
;
136 *val
= bma220_scale_table
[range_idx
][0];
137 *val2
= bma220_scale_table
[range_idx
][1];
138 return IIO_VAL_INT_PLUS_MICRO
;
144 static int bma220_write_raw(struct iio_dev
*indio_dev
,
145 struct iio_chan_spec
const *chan
,
146 int val
, int val2
, long mask
)
151 struct bma220_data
*data
= iio_priv(indio_dev
);
154 case IIO_CHAN_INFO_SCALE
:
155 for (i
= 0; i
< ARRAY_SIZE(bma220_scale_table
); i
++)
156 if (val
== bma220_scale_table
[i
][0] &&
157 val2
== bma220_scale_table
[i
][1]) {
164 mutex_lock(&data
->lock
);
165 data
->tx_buf
[0] = BMA220_REG_RANGE
;
166 data
->tx_buf
[1] = index
;
167 ret
= spi_write(data
->spi_device
, data
->tx_buf
,
168 sizeof(data
->tx_buf
));
170 dev_err(&data
->spi_device
->dev
,
171 "failed to set measurement range\n");
172 mutex_unlock(&data
->lock
);
180 static int bma220_read_avail(struct iio_dev
*indio_dev
,
181 struct iio_chan_spec
const *chan
,
182 const int **vals
, int *type
, int *length
,
186 case IIO_CHAN_INFO_SCALE
:
187 *vals
= (int *)bma220_scale_table
;
188 *type
= IIO_VAL_INT_PLUS_MICRO
;
189 *length
= ARRAY_SIZE(bma220_scale_table
) * 2;
190 return IIO_AVAIL_LIST
;
196 static const struct iio_info bma220_info
= {
197 .read_raw
= bma220_read_raw
,
198 .write_raw
= bma220_write_raw
,
199 .read_avail
= bma220_read_avail
,
202 static int bma220_init(struct spi_device
*spi
)
206 ret
= bma220_read_reg(spi
, BMA220_REG_ID
);
207 if (ret
!= BMA220_CHIP_ID
)
210 /* Make sure the chip is powered on */
211 ret
= bma220_read_reg(spi
, BMA220_REG_SUSPEND
);
212 if (ret
== BMA220_SUSPEND_WAKE
)
213 ret
= bma220_read_reg(spi
, BMA220_REG_SUSPEND
);
216 if (ret
== BMA220_SUSPEND_WAKE
)
222 static int bma220_power(struct spi_device
*spi
, bool up
)
227 * The chip can be suspended/woken up by a simple register read.
228 * So, we need up to 2 register reads of the suspend register
229 * to make sure that the device is in the desired state.
231 for (i
= 0; i
< 2; i
++) {
232 ret
= bma220_read_reg(spi
, BMA220_REG_SUSPEND
);
236 if (up
&& ret
== BMA220_SUSPEND_SLEEP
)
239 if (!up
&& ret
== BMA220_SUSPEND_WAKE
)
246 static void bma220_deinit(void *spi
)
248 bma220_power(spi
, false);
251 static int bma220_probe(struct spi_device
*spi
)
254 struct iio_dev
*indio_dev
;
255 struct bma220_data
*data
;
257 indio_dev
= devm_iio_device_alloc(&spi
->dev
, sizeof(*data
));
259 dev_err(&spi
->dev
, "iio allocation failed!\n");
263 data
= iio_priv(indio_dev
);
264 data
->spi_device
= spi
;
265 mutex_init(&data
->lock
);
267 indio_dev
->info
= &bma220_info
;
268 indio_dev
->name
= BMA220_DEVICE_NAME
;
269 indio_dev
->modes
= INDIO_DIRECT_MODE
;
270 indio_dev
->channels
= bma220_channels
;
271 indio_dev
->num_channels
= ARRAY_SIZE(bma220_channels
);
272 indio_dev
->available_scan_masks
= bma220_accel_scan_masks
;
274 ret
= bma220_init(data
->spi_device
);
278 ret
= devm_add_action_or_reset(&spi
->dev
, bma220_deinit
, spi
);
282 ret
= devm_iio_triggered_buffer_setup(&spi
->dev
, indio_dev
,
283 iio_pollfunc_store_time
,
284 bma220_trigger_handler
, NULL
);
286 dev_err(&spi
->dev
, "iio triggered buffer setup failed\n");
290 return devm_iio_device_register(&spi
->dev
, indio_dev
);
293 static int bma220_suspend(struct device
*dev
)
295 struct spi_device
*spi
= to_spi_device(dev
);
297 return bma220_power(spi
, false);
300 static int bma220_resume(struct device
*dev
)
302 struct spi_device
*spi
= to_spi_device(dev
);
304 return bma220_power(spi
, true);
306 static DEFINE_SIMPLE_DEV_PM_OPS(bma220_pm_ops
, bma220_suspend
, bma220_resume
);
308 static const struct spi_device_id bma220_spi_id
[] = {
313 static const struct acpi_device_id bma220_acpi_id
[] = {
317 MODULE_DEVICE_TABLE(spi
, bma220_spi_id
);
319 static struct spi_driver bma220_driver
= {
321 .name
= "bma220_spi",
322 .pm
= pm_sleep_ptr(&bma220_pm_ops
),
323 .acpi_match_table
= bma220_acpi_id
,
325 .probe
= bma220_probe
,
326 .id_table
= bma220_spi_id
,
328 module_spi_driver(bma220_driver
);
330 MODULE_AUTHOR("Tiberiu Breana <tiberiu.a.breana@intel.com>");
331 MODULE_DESCRIPTION("BMA220 acceleration sensor driver");
332 MODULE_LICENSE("GPL v2");