1 // SPDX-License-Identifier: GPL-2.0
3 * Analog Devices AD7292 SPI ADC driver
5 * Copyright 2019 Analog Devices Inc.
8 #include <linux/bitfield.h>
9 #include <linux/device.h>
10 #include <linux/module.h>
11 #include <linux/regulator/consumer.h>
12 #include <linux/spi/spi.h>
14 #include <linux/iio/iio.h>
16 #define ADI_VENDOR_ID 0x0018
18 /* AD7292 registers definition */
19 #define AD7292_REG_VENDOR_ID 0x00
20 #define AD7292_REG_CONF_BANK 0x05
21 #define AD7292_REG_CONV_COMM 0x0E
22 #define AD7292_REG_ADC_CH(x) (0x10 + (x))
24 /* AD7292 configuration bank subregisters definition */
25 #define AD7292_BANK_REG_VIN_RNG0 0x10
26 #define AD7292_BANK_REG_VIN_RNG1 0x11
27 #define AD7292_BANK_REG_SAMP_MODE 0x12
29 #define AD7292_RD_FLAG_MSK(x) (BIT(7) | ((x) & 0x3F))
31 /* AD7292_REG_ADC_CONVERSION */
32 #define AD7292_ADC_DATA_MASK GENMASK(15, 6)
33 #define AD7292_ADC_DATA(x) FIELD_GET(AD7292_ADC_DATA_MASK, x)
35 /* AD7292_CHANNEL_SAMPLING_MODE */
36 #define AD7292_CH_SAMP_MODE(reg, ch) (((reg) >> 8) & BIT(ch))
38 /* AD7292_CHANNEL_VIN_RANGE */
39 #define AD7292_CH_VIN_RANGE(reg, ch) ((reg) & BIT(ch))
41 #define AD7292_VOLTAGE_CHAN(_chan) \
43 .type = IIO_VOLTAGE, \
44 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | \
45 BIT(IIO_CHAN_INFO_SCALE), \
50 static const struct iio_chan_spec ad7292_channels
[] = {
51 AD7292_VOLTAGE_CHAN(0),
52 AD7292_VOLTAGE_CHAN(1),
53 AD7292_VOLTAGE_CHAN(2),
54 AD7292_VOLTAGE_CHAN(3),
55 AD7292_VOLTAGE_CHAN(4),
56 AD7292_VOLTAGE_CHAN(5),
57 AD7292_VOLTAGE_CHAN(6),
58 AD7292_VOLTAGE_CHAN(7)
61 static const struct iio_chan_spec ad7292_channels_diff
[] = {
64 .info_mask_separate
= BIT(IIO_CHAN_INFO_RAW
),
70 AD7292_VOLTAGE_CHAN(2),
71 AD7292_VOLTAGE_CHAN(3),
72 AD7292_VOLTAGE_CHAN(4),
73 AD7292_VOLTAGE_CHAN(5),
74 AD7292_VOLTAGE_CHAN(6),
75 AD7292_VOLTAGE_CHAN(7)
79 struct spi_device
*spi
;
80 struct regulator
*reg
;
81 unsigned short vref_mv
;
83 __be16 d16 ____cacheline_aligned
;
87 static int ad7292_spi_reg_read(struct ad7292_state
*st
, unsigned int addr
)
91 st
->d8
[0] = AD7292_RD_FLAG_MSK(addr
);
93 ret
= spi_write_then_read(st
->spi
, st
->d8
, 1, &st
->d16
, 2);
97 return be16_to_cpu(st
->d16
);
100 static int ad7292_spi_subreg_read(struct ad7292_state
*st
, unsigned int addr
,
101 unsigned int sub_addr
, unsigned int len
)
103 unsigned int shift
= 16 - (8 * len
);
106 st
->d8
[0] = AD7292_RD_FLAG_MSK(addr
);
107 st
->d8
[1] = sub_addr
;
109 ret
= spi_write_then_read(st
->spi
, st
->d8
, 2, &st
->d16
, len
);
113 return (be16_to_cpu(st
->d16
) >> shift
);
116 static int ad7292_single_conversion(struct ad7292_state
*st
,
117 unsigned int chan_addr
)
121 struct spi_transfer t
[] = {
127 .unit
= SPI_DELAY_UNIT_USECS
135 st
->d8
[0] = chan_addr
;
136 st
->d8
[1] = AD7292_RD_FLAG_MSK(AD7292_REG_CONV_COMM
);
138 ret
= spi_sync_transfer(st
->spi
, t
, ARRAY_SIZE(t
));
143 return be16_to_cpu(st
->d16
);
146 static int ad7292_vin_range_multiplier(struct ad7292_state
*st
, int channel
)
148 int samp_mode
, range0
, range1
, factor
= 1;
151 * Every AD7292 ADC channel may have its input range adjusted according
152 * to the settings at the ADC sampling mode and VIN range subregisters.
153 * For a given channel, the minimum input range is equal to Vref, and it
154 * may be increased by a multiplier factor of 2 or 4 according to the
156 * If channel is being sampled with respect to AGND:
157 * factor = 4 if VIN range0 and VIN range1 equal 0
158 * factor = 2 if only one of VIN ranges equal 1
159 * factor = 1 if both VIN range0 and VIN range1 equal 1
160 * If channel is being sampled with respect to AVDD:
161 * factor = 4 if VIN range0 and VIN range1 equal 0
162 * Behavior is undefined if any of VIN range doesn't equal 0
165 samp_mode
= ad7292_spi_subreg_read(st
, AD7292_REG_CONF_BANK
,
166 AD7292_BANK_REG_SAMP_MODE
, 2);
171 range0
= ad7292_spi_subreg_read(st
, AD7292_REG_CONF_BANK
,
172 AD7292_BANK_REG_VIN_RNG0
, 2);
177 range1
= ad7292_spi_subreg_read(st
, AD7292_REG_CONF_BANK
,
178 AD7292_BANK_REG_VIN_RNG1
, 2);
183 if (AD7292_CH_SAMP_MODE(samp_mode
, channel
)) {
184 /* Sampling with respect to AGND */
185 if (!AD7292_CH_VIN_RANGE(range0
, channel
))
188 if (!AD7292_CH_VIN_RANGE(range1
, channel
))
192 /* Sampling with respect to AVDD */
193 if (AD7292_CH_VIN_RANGE(range0
, channel
) ||
194 AD7292_CH_VIN_RANGE(range1
, channel
))
203 static int ad7292_read_raw(struct iio_dev
*indio_dev
,
204 const struct iio_chan_spec
*chan
,
205 int *val
, int *val2
, long info
)
207 struct ad7292_state
*st
= iio_priv(indio_dev
);
208 unsigned int ch_addr
;
212 case IIO_CHAN_INFO_RAW
:
213 ch_addr
= AD7292_REG_ADC_CH(chan
->channel
);
214 ret
= ad7292_single_conversion(st
, ch_addr
);
218 *val
= AD7292_ADC_DATA(ret
);
221 case IIO_CHAN_INFO_SCALE
:
223 * To convert a raw value to standard units, the IIO defines
224 * this formula: Scaled value = (raw + offset) * scale.
225 * For the scale to be a correct multiplier for (raw + offset),
226 * it must be calculated as the input range divided by the
227 * number of possible distinct input values. Given the ADC data
228 * is 10 bit long, it may assume 2^10 distinct values.
229 * Hence, scale = range / 2^10. The IIO_VAL_FRACTIONAL_LOG2
230 * return type indicates to the IIO API to divide *val by 2 to
231 * the power of *val2 when returning from read_raw.
234 ret
= ad7292_vin_range_multiplier(st
, chan
->channel
);
238 *val
= st
->vref_mv
* ret
;
240 return IIO_VAL_FRACTIONAL_LOG2
;
247 static const struct iio_info ad7292_info
= {
248 .read_raw
= ad7292_read_raw
,
251 static void ad7292_regulator_disable(void *data
)
253 struct ad7292_state
*st
= data
;
255 regulator_disable(st
->reg
);
258 static int ad7292_probe(struct spi_device
*spi
)
260 struct ad7292_state
*st
;
261 struct iio_dev
*indio_dev
;
262 struct device_node
*child
;
263 bool diff_channels
= 0;
266 indio_dev
= devm_iio_device_alloc(&spi
->dev
, sizeof(*st
));
270 st
= iio_priv(indio_dev
);
273 ret
= ad7292_spi_reg_read(st
, AD7292_REG_VENDOR_ID
);
274 if (ret
!= ADI_VENDOR_ID
) {
275 dev_err(&spi
->dev
, "Wrong vendor id 0x%x\n", ret
);
279 st
->reg
= devm_regulator_get_optional(&spi
->dev
, "vref");
280 if (!IS_ERR(st
->reg
)) {
281 ret
= regulator_enable(st
->reg
);
284 "Failed to enable external vref supply\n");
288 ret
= devm_add_action_or_reset(&spi
->dev
,
289 ad7292_regulator_disable
, st
);
291 regulator_disable(st
->reg
);
295 ret
= regulator_get_voltage(st
->reg
);
299 st
->vref_mv
= ret
/ 1000;
301 /* Use the internal voltage reference. */
305 indio_dev
->name
= spi_get_device_id(spi
)->name
;
306 indio_dev
->modes
= INDIO_DIRECT_MODE
;
307 indio_dev
->info
= &ad7292_info
;
309 for_each_available_child_of_node(spi
->dev
.of_node
, child
) {
310 diff_channels
= of_property_read_bool(child
, "diff-channels");
318 indio_dev
->num_channels
= ARRAY_SIZE(ad7292_channels_diff
);
319 indio_dev
->channels
= ad7292_channels_diff
;
321 indio_dev
->num_channels
= ARRAY_SIZE(ad7292_channels
);
322 indio_dev
->channels
= ad7292_channels
;
325 return devm_iio_device_register(&spi
->dev
, indio_dev
);
328 static const struct spi_device_id ad7292_id_table
[] = {
332 MODULE_DEVICE_TABLE(spi
, ad7292_id_table
);
334 static const struct of_device_id ad7292_of_match
[] = {
335 { .compatible
= "adi,ad7292" },
338 MODULE_DEVICE_TABLE(of
, ad7292_of_match
);
340 static struct spi_driver ad7292_driver
= {
343 .of_match_table
= ad7292_of_match
,
345 .probe
= ad7292_probe
,
346 .id_table
= ad7292_id_table
,
348 module_spi_driver(ad7292_driver
);
350 MODULE_AUTHOR("Marcelo Schmitt <marcelo.schmitt1@gmail.com>");
351 MODULE_DESCRIPTION("Analog Devices AD7292 ADC driver");
352 MODULE_LICENSE("GPL v2");