blob: 26011254ffbc040cbac633f72e52d9c354badcbd [file] [log] [blame]
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001/*
2 * Amlogic Meson Successive Approximation Register (SAR) A/D Converter
3 *
4 * Copyright (C) 2017 Martin Blumenstingl <martin.blumenstingl@googlemail.com>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 as
8 * published by the Free Software Foundation.
9 *
10 * You should have received a copy of the GNU General Public License
11 * along with this program. If not, see <http://www.gnu.org/licenses/>.
12 */
13
14#include <linux/bitfield.h>
15#include <linux/clk.h>
16#include <linux/clk-provider.h>
17#include <linux/delay.h>
18#include <linux/io.h>
19#include <linux/iio/iio.h>
20#include <linux/module.h>
Martin Blumenstingl723a61e2018-11-04 00:10:24 +010021#include <linux/nvmem-consumer.h>
Heiner Kallweit3af10912017-02-15 20:31:45 +010022#include <linux/interrupt.h>
Martin Blumenstingl3adbf342017-01-22 19:17:13 +010023#include <linux/of.h>
Heiner Kallweit3af10912017-02-15 20:31:45 +010024#include <linux/of_irq.h>
Martin Blumenstingl3adbf342017-01-22 19:17:13 +010025#include <linux/of_device.h>
26#include <linux/platform_device.h>
27#include <linux/regmap.h>
28#include <linux/regulator/consumer.h>
29
30#define MESON_SAR_ADC_REG0 0x00
31 #define MESON_SAR_ADC_REG0_PANEL_DETECT BIT(31)
32 #define MESON_SAR_ADC_REG0_BUSY_MASK GENMASK(30, 28)
33 #define MESON_SAR_ADC_REG0_DELTA_BUSY BIT(30)
34 #define MESON_SAR_ADC_REG0_AVG_BUSY BIT(29)
35 #define MESON_SAR_ADC_REG0_SAMPLE_BUSY BIT(28)
36 #define MESON_SAR_ADC_REG0_FIFO_FULL BIT(27)
37 #define MESON_SAR_ADC_REG0_FIFO_EMPTY BIT(26)
38 #define MESON_SAR_ADC_REG0_FIFO_COUNT_MASK GENMASK(25, 21)
39 #define MESON_SAR_ADC_REG0_ADC_BIAS_CTRL_MASK GENMASK(20, 19)
40 #define MESON_SAR_ADC_REG0_CURR_CHAN_ID_MASK GENMASK(18, 16)
41 #define MESON_SAR_ADC_REG0_ADC_TEMP_SEN_SEL BIT(15)
42 #define MESON_SAR_ADC_REG0_SAMPLING_STOP BIT(14)
43 #define MESON_SAR_ADC_REG0_CHAN_DELTA_EN_MASK GENMASK(13, 12)
44 #define MESON_SAR_ADC_REG0_DETECT_IRQ_POL BIT(10)
45 #define MESON_SAR_ADC_REG0_DETECT_IRQ_EN BIT(9)
46 #define MESON_SAR_ADC_REG0_FIFO_CNT_IRQ_MASK GENMASK(8, 4)
47 #define MESON_SAR_ADC_REG0_FIFO_IRQ_EN BIT(3)
48 #define MESON_SAR_ADC_REG0_SAMPLING_START BIT(2)
49 #define MESON_SAR_ADC_REG0_CONTINUOUS_EN BIT(1)
50 #define MESON_SAR_ADC_REG0_SAMPLE_ENGINE_ENABLE BIT(0)
51
52#define MESON_SAR_ADC_CHAN_LIST 0x04
53 #define MESON_SAR_ADC_CHAN_LIST_MAX_INDEX_MASK GENMASK(26, 24)
54 #define MESON_SAR_ADC_CHAN_LIST_ENTRY_MASK(_chan) \
55 (GENMASK(2, 0) << ((_chan) * 3))
56
57#define MESON_SAR_ADC_AVG_CNTL 0x08
58 #define MESON_SAR_ADC_AVG_CNTL_AVG_MODE_SHIFT(_chan) \
59 (16 + ((_chan) * 2))
60 #define MESON_SAR_ADC_AVG_CNTL_AVG_MODE_MASK(_chan) \
61 (GENMASK(17, 16) << ((_chan) * 2))
62 #define MESON_SAR_ADC_AVG_CNTL_NUM_SAMPLES_SHIFT(_chan) \
63 (0 + ((_chan) * 2))
64 #define MESON_SAR_ADC_AVG_CNTL_NUM_SAMPLES_MASK(_chan) \
65 (GENMASK(1, 0) << ((_chan) * 2))
66
67#define MESON_SAR_ADC_REG3 0x0c
68 #define MESON_SAR_ADC_REG3_CNTL_USE_SC_DLY BIT(31)
69 #define MESON_SAR_ADC_REG3_CLK_EN BIT(30)
70 #define MESON_SAR_ADC_REG3_BL30_INITIALIZED BIT(28)
71 #define MESON_SAR_ADC_REG3_CTRL_CONT_RING_COUNTER_EN BIT(27)
72 #define MESON_SAR_ADC_REG3_CTRL_SAMPLING_CLOCK_PHASE BIT(26)
73 #define MESON_SAR_ADC_REG3_CTRL_CHAN7_MUX_SEL_MASK GENMASK(25, 23)
74 #define MESON_SAR_ADC_REG3_DETECT_EN BIT(22)
75 #define MESON_SAR_ADC_REG3_ADC_EN BIT(21)
76 #define MESON_SAR_ADC_REG3_PANEL_DETECT_COUNT_MASK GENMASK(20, 18)
77 #define MESON_SAR_ADC_REG3_PANEL_DETECT_FILTER_TB_MASK GENMASK(17, 16)
78 #define MESON_SAR_ADC_REG3_ADC_CLK_DIV_SHIFT 10
79 #define MESON_SAR_ADC_REG3_ADC_CLK_DIV_WIDTH 5
80 #define MESON_SAR_ADC_REG3_BLOCK_DLY_SEL_MASK GENMASK(9, 8)
81 #define MESON_SAR_ADC_REG3_BLOCK_DLY_MASK GENMASK(7, 0)
82
83#define MESON_SAR_ADC_DELAY 0x10
84 #define MESON_SAR_ADC_DELAY_INPUT_DLY_SEL_MASK GENMASK(25, 24)
85 #define MESON_SAR_ADC_DELAY_BL30_BUSY BIT(15)
86 #define MESON_SAR_ADC_DELAY_KERNEL_BUSY BIT(14)
87 #define MESON_SAR_ADC_DELAY_INPUT_DLY_CNT_MASK GENMASK(23, 16)
88 #define MESON_SAR_ADC_DELAY_SAMPLE_DLY_SEL_MASK GENMASK(9, 8)
89 #define MESON_SAR_ADC_DELAY_SAMPLE_DLY_CNT_MASK GENMASK(7, 0)
90
91#define MESON_SAR_ADC_LAST_RD 0x14
92 #define MESON_SAR_ADC_LAST_RD_LAST_CHANNEL1_MASK GENMASK(23, 16)
93 #define MESON_SAR_ADC_LAST_RD_LAST_CHANNEL0_MASK GENMASK(9, 0)
94
95#define MESON_SAR_ADC_FIFO_RD 0x18
96 #define MESON_SAR_ADC_FIFO_RD_CHAN_ID_MASK GENMASK(14, 12)
97 #define MESON_SAR_ADC_FIFO_RD_SAMPLE_VALUE_MASK GENMASK(11, 0)
98
99#define MESON_SAR_ADC_AUX_SW 0x1c
Martin Blumenstinglab569a42017-10-31 21:01:47 +0100100 #define MESON_SAR_ADC_AUX_SW_MUX_SEL_CHAN_SHIFT(_chan) \
101 (8 + (((_chan) - 2) * 3))
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100102 #define MESON_SAR_ADC_AUX_SW_VREF_P_MUX BIT(6)
103 #define MESON_SAR_ADC_AUX_SW_VREF_N_MUX BIT(5)
104 #define MESON_SAR_ADC_AUX_SW_MODE_SEL BIT(4)
105 #define MESON_SAR_ADC_AUX_SW_YP_DRIVE_SW BIT(3)
106 #define MESON_SAR_ADC_AUX_SW_XP_DRIVE_SW BIT(2)
107 #define MESON_SAR_ADC_AUX_SW_YM_DRIVE_SW BIT(1)
108 #define MESON_SAR_ADC_AUX_SW_XM_DRIVE_SW BIT(0)
109
110#define MESON_SAR_ADC_CHAN_10_SW 0x20
111 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_MUX_SEL_MASK GENMASK(25, 23)
112 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_VREF_P_MUX BIT(22)
113 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_VREF_N_MUX BIT(21)
114 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_MODE_SEL BIT(20)
115 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_YP_DRIVE_SW BIT(19)
116 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_XP_DRIVE_SW BIT(18)
117 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_YM_DRIVE_SW BIT(17)
118 #define MESON_SAR_ADC_CHAN_10_SW_CHAN1_XM_DRIVE_SW BIT(16)
119 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_MUX_SEL_MASK GENMASK(9, 7)
120 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_VREF_P_MUX BIT(6)
121 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_VREF_N_MUX BIT(5)
122 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_MODE_SEL BIT(4)
123 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_YP_DRIVE_SW BIT(3)
124 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_XP_DRIVE_SW BIT(2)
125 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_YM_DRIVE_SW BIT(1)
126 #define MESON_SAR_ADC_CHAN_10_SW_CHAN0_XM_DRIVE_SW BIT(0)
127
128#define MESON_SAR_ADC_DETECT_IDLE_SW 0x24
129 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_SW_EN BIT(26)
130 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_MUX_MASK GENMASK(25, 23)
131 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_VREF_P_MUX BIT(22)
132 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_VREF_N_MUX BIT(21)
133 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_MODE_SEL BIT(20)
134 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_YP_DRIVE_SW BIT(19)
135 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_XP_DRIVE_SW BIT(18)
136 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_YM_DRIVE_SW BIT(17)
137 #define MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_XM_DRIVE_SW BIT(16)
138 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_MUX_SEL_MASK GENMASK(9, 7)
139 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_VREF_P_MUX BIT(6)
140 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_VREF_N_MUX BIT(5)
141 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_MODE_SEL BIT(4)
142 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_YP_DRIVE_SW BIT(3)
143 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_XP_DRIVE_SW BIT(2)
144 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_YM_DRIVE_SW BIT(1)
145 #define MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_XM_DRIVE_SW BIT(0)
146
147#define MESON_SAR_ADC_DELTA_10 0x28
148 #define MESON_SAR_ADC_DELTA_10_TEMP_SEL BIT(27)
149 #define MESON_SAR_ADC_DELTA_10_TS_REVE1 BIT(26)
150 #define MESON_SAR_ADC_DELTA_10_CHAN1_DELTA_VALUE_MASK GENMASK(25, 16)
151 #define MESON_SAR_ADC_DELTA_10_TS_REVE0 BIT(15)
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100152 #define MESON_SAR_ADC_DELTA_10_TS_C_MASK GENMASK(14, 11)
153 #define MESON_SAR_ADC_DELTA_10_TS_VBG_EN BIT(10)
154 #define MESON_SAR_ADC_DELTA_10_CHAN0_DELTA_VALUE_MASK GENMASK(9, 0)
155
156/*
157 * NOTE: registers from here are undocumented (the vendor Linux kernel driver
158 * and u-boot source served as reference). These only seem to be relevant on
159 * GXBB and newer.
160 */
161#define MESON_SAR_ADC_REG11 0x2c
162 #define MESON_SAR_ADC_REG11_BANDGAP_EN BIT(13)
163
164#define MESON_SAR_ADC_REG13 0x34
165 #define MESON_SAR_ADC_REG13_12BIT_CALIBRATION_MASK GENMASK(13, 8)
166
167#define MESON_SAR_ADC_MAX_FIFO_SIZE 32
Heiner Kallweit3af10912017-02-15 20:31:45 +0100168#define MESON_SAR_ADC_TIMEOUT 100 /* ms */
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100169#define MESON_SAR_ADC_VOLTAGE_AND_TEMP_CHANNEL 6
170#define MESON_SAR_ADC_TEMP_OFFSET 27
171
172/* temperature sensor calibration information in eFuse */
173#define MESON_SAR_ADC_EFUSE_BYTES 4
174#define MESON_SAR_ADC_EFUSE_BYTE3_UPPER_ADC_VAL GENMASK(6, 0)
175#define MESON_SAR_ADC_EFUSE_BYTE3_IS_CALIBRATED BIT(7)
176
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100177/* for use with IIO_VAL_INT_PLUS_MICRO */
178#define MILLION 1000000
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100179
180#define MESON_SAR_ADC_CHAN(_chan) { \
181 .type = IIO_VOLTAGE, \
182 .indexed = 1, \
183 .channel = _chan, \
Martin Blumenstingl827df052018-09-25 00:13:26 +0200184 .address = _chan, \
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100185 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | \
186 BIT(IIO_CHAN_INFO_AVERAGE_RAW), \
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100187 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE), \
188 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_CALIBBIAS) | \
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100189 BIT(IIO_CHAN_INFO_CALIBSCALE), \
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100190 .datasheet_name = "SAR_ADC_CH"#_chan, \
191}
192
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100193#define MESON_SAR_ADC_TEMP_CHAN(_chan) { \
194 .type = IIO_TEMP, \
195 .channel = _chan, \
196 .address = MESON_SAR_ADC_VOLTAGE_AND_TEMP_CHANNEL, \
197 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | \
198 BIT(IIO_CHAN_INFO_AVERAGE_RAW), \
199 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_OFFSET) | \
200 BIT(IIO_CHAN_INFO_SCALE), \
201 .info_mask_shared_by_all = BIT(IIO_CHAN_INFO_CALIBBIAS) | \
202 BIT(IIO_CHAN_INFO_CALIBSCALE), \
203 .datasheet_name = "TEMP_SENSOR", \
204}
205
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100206static const struct iio_chan_spec meson_sar_adc_iio_channels[] = {
207 MESON_SAR_ADC_CHAN(0),
208 MESON_SAR_ADC_CHAN(1),
209 MESON_SAR_ADC_CHAN(2),
210 MESON_SAR_ADC_CHAN(3),
211 MESON_SAR_ADC_CHAN(4),
212 MESON_SAR_ADC_CHAN(5),
213 MESON_SAR_ADC_CHAN(6),
214 MESON_SAR_ADC_CHAN(7),
215 IIO_CHAN_SOFT_TIMESTAMP(8),
216};
217
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100218static const struct iio_chan_spec meson_sar_adc_and_temp_iio_channels[] = {
219 MESON_SAR_ADC_CHAN(0),
220 MESON_SAR_ADC_CHAN(1),
221 MESON_SAR_ADC_CHAN(2),
222 MESON_SAR_ADC_CHAN(3),
223 MESON_SAR_ADC_CHAN(4),
224 MESON_SAR_ADC_CHAN(5),
225 MESON_SAR_ADC_CHAN(6),
226 MESON_SAR_ADC_CHAN(7),
227 MESON_SAR_ADC_TEMP_CHAN(8),
228 IIO_CHAN_SOFT_TIMESTAMP(9),
229};
230
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100231enum meson_sar_adc_avg_mode {
232 NO_AVERAGING = 0x0,
233 MEAN_AVERAGING = 0x1,
234 MEDIAN_AVERAGING = 0x2,
235};
236
237enum meson_sar_adc_num_samples {
238 ONE_SAMPLE = 0x0,
239 TWO_SAMPLES = 0x1,
240 FOUR_SAMPLES = 0x2,
241 EIGHT_SAMPLES = 0x3,
242};
243
244enum meson_sar_adc_chan7_mux_sel {
245 CHAN7_MUX_VSS = 0x0,
246 CHAN7_MUX_VDD_DIV4 = 0x1,
247 CHAN7_MUX_VDD_DIV2 = 0x2,
248 CHAN7_MUX_VDD_MUL3_DIV4 = 0x3,
249 CHAN7_MUX_VDD = 0x4,
250 CHAN7_MUX_CH7_INPUT = 0x7,
251};
252
Yixun Lan053ffe32018-03-26 16:46:27 +0800253struct meson_sar_adc_param {
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +0200254 bool has_bl30_integration;
Martin Blumenstinglfda29db2017-10-31 21:01:46 +0100255 unsigned long clock_rate;
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100256 u32 bandgap_reg;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100257 unsigned int resolution;
Martin Blumenstingl96748822017-10-31 21:01:45 +0100258 const struct regmap_config *regmap_config;
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100259 u8 temperature_trimming_bits;
260 unsigned int temperature_multiplier;
261 unsigned int temperature_divider;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100262};
263
Yixun Lan053ffe32018-03-26 16:46:27 +0800264struct meson_sar_adc_data {
265 const struct meson_sar_adc_param *param;
266 const char *name;
267};
268
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100269struct meson_sar_adc_priv {
270 struct regmap *regmap;
271 struct regulator *vref;
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200272 const struct meson_sar_adc_param *param;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100273 struct clk *clkin;
274 struct clk *core_clk;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100275 struct clk *adc_sel_clk;
276 struct clk *adc_clk;
277 struct clk_gate clk_gate;
278 struct clk *adc_div_clk;
279 struct clk_divider clk_div;
Heiner Kallweit3af10912017-02-15 20:31:45 +0100280 struct completion done;
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100281 int calibbias;
282 int calibscale;
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100283 bool temperature_sensor_calibrated;
284 u8 temperature_sensor_coefficient;
285 u16 temperature_sensor_adc_val;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100286};
287
Martin Blumenstingl96748822017-10-31 21:01:45 +0100288static const struct regmap_config meson_sar_adc_regmap_config_gxbb = {
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100289 .reg_bits = 8,
290 .val_bits = 32,
291 .reg_stride = 4,
292 .max_register = MESON_SAR_ADC_REG13,
293};
294
Martin Blumenstingl96748822017-10-31 21:01:45 +0100295static const struct regmap_config meson_sar_adc_regmap_config_meson8 = {
296 .reg_bits = 8,
297 .val_bits = 32,
298 .reg_stride = 4,
299 .max_register = MESON_SAR_ADC_DELTA_10,
300};
301
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100302static unsigned int meson_sar_adc_get_fifo_count(struct iio_dev *indio_dev)
303{
304 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
305 u32 regval;
306
307 regmap_read(priv->regmap, MESON_SAR_ADC_REG0, &regval);
308
309 return FIELD_GET(MESON_SAR_ADC_REG0_FIFO_COUNT_MASK, regval);
310}
311
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100312static int meson_sar_adc_calib_val(struct iio_dev *indio_dev, int val)
313{
314 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
315 int tmp;
316
317 /* use val_calib = scale * val_raw + offset calibration function */
318 tmp = div_s64((s64)val * priv->calibscale, MILLION) + priv->calibbias;
319
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200320 return clamp(tmp, 0, (1 << priv->param->resolution) - 1);
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100321}
322
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100323static int meson_sar_adc_wait_busy_clear(struct iio_dev *indio_dev)
324{
325 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
326 int regval, timeout = 10000;
327
328 /*
329 * NOTE: we need a small delay before reading the status, otherwise
330 * the sample engine may not have started internally (which would
331 * seem to us that sampling is already finished).
332 */
333 do {
334 udelay(1);
335 regmap_read(priv->regmap, MESON_SAR_ADC_REG0, &regval);
336 } while (FIELD_GET(MESON_SAR_ADC_REG0_BUSY_MASK, regval) && timeout--);
337
338 if (timeout < 0)
339 return -ETIMEDOUT;
340
341 return 0;
342}
343
344static int meson_sar_adc_read_raw_sample(struct iio_dev *indio_dev,
345 const struct iio_chan_spec *chan,
346 int *val)
347{
348 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
Heiner Kallweit6a882a22017-02-15 20:31:55 +0100349 int regval, fifo_chan, fifo_val, count;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100350
Heiner Kallweit3af10912017-02-15 20:31:45 +0100351 if(!wait_for_completion_timeout(&priv->done,
352 msecs_to_jiffies(MESON_SAR_ADC_TIMEOUT)))
353 return -ETIMEDOUT;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100354
Heiner Kallweit6a882a22017-02-15 20:31:55 +0100355 count = meson_sar_adc_get_fifo_count(indio_dev);
356 if (count != 1) {
357 dev_err(&indio_dev->dev,
358 "ADC FIFO has %d element(s) instead of one\n", count);
359 return -EINVAL;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100360 }
361
Heiner Kallweit6a882a22017-02-15 20:31:55 +0100362 regmap_read(priv->regmap, MESON_SAR_ADC_FIFO_RD, &regval);
363 fifo_chan = FIELD_GET(MESON_SAR_ADC_FIFO_RD_CHAN_ID_MASK, regval);
Martin Blumenstingl827df052018-09-25 00:13:26 +0200364 if (fifo_chan != chan->address) {
Heiner Kallweit6a882a22017-02-15 20:31:55 +0100365 dev_err(&indio_dev->dev,
Martin Blumenstingl827df052018-09-25 00:13:26 +0200366 "ADC FIFO entry belongs to channel %d instead of %lu\n",
367 fifo_chan, chan->address);
Heiner Kallweit6a882a22017-02-15 20:31:55 +0100368 return -EINVAL;
369 }
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100370
Heiner Kallweit6a882a22017-02-15 20:31:55 +0100371 fifo_val = FIELD_GET(MESON_SAR_ADC_FIFO_RD_SAMPLE_VALUE_MASK, regval);
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200372 fifo_val &= GENMASK(priv->param->resolution - 1, 0);
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100373 *val = meson_sar_adc_calib_val(indio_dev, fifo_val);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100374
375 return 0;
376}
377
378static void meson_sar_adc_set_averaging(struct iio_dev *indio_dev,
379 const struct iio_chan_spec *chan,
380 enum meson_sar_adc_avg_mode mode,
381 enum meson_sar_adc_num_samples samples)
382{
383 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
Martin Blumenstingl827df052018-09-25 00:13:26 +0200384 int val, address = chan->address;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100385
Martin Blumenstingl827df052018-09-25 00:13:26 +0200386 val = samples << MESON_SAR_ADC_AVG_CNTL_NUM_SAMPLES_SHIFT(address);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100387 regmap_update_bits(priv->regmap, MESON_SAR_ADC_AVG_CNTL,
Martin Blumenstingl827df052018-09-25 00:13:26 +0200388 MESON_SAR_ADC_AVG_CNTL_NUM_SAMPLES_MASK(address),
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100389 val);
390
Martin Blumenstingl827df052018-09-25 00:13:26 +0200391 val = mode << MESON_SAR_ADC_AVG_CNTL_AVG_MODE_SHIFT(address);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100392 regmap_update_bits(priv->regmap, MESON_SAR_ADC_AVG_CNTL,
Martin Blumenstingl827df052018-09-25 00:13:26 +0200393 MESON_SAR_ADC_AVG_CNTL_AVG_MODE_MASK(address), val);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100394}
395
396static void meson_sar_adc_enable_channel(struct iio_dev *indio_dev,
397 const struct iio_chan_spec *chan)
398{
399 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
400 u32 regval;
401
402 /*
403 * the SAR ADC engine allows sampling multiple channels at the same
404 * time. to keep it simple we're only working with one *internal*
405 * channel, which starts counting at index 0 (which means: count = 1).
406 */
407 regval = FIELD_PREP(MESON_SAR_ADC_CHAN_LIST_MAX_INDEX_MASK, 0);
408 regmap_update_bits(priv->regmap, MESON_SAR_ADC_CHAN_LIST,
409 MESON_SAR_ADC_CHAN_LIST_MAX_INDEX_MASK, regval);
410
411 /* map channel index 0 to the channel which we want to read */
412 regval = FIELD_PREP(MESON_SAR_ADC_CHAN_LIST_ENTRY_MASK(0),
Martin Blumenstingl827df052018-09-25 00:13:26 +0200413 chan->address);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100414 regmap_update_bits(priv->regmap, MESON_SAR_ADC_CHAN_LIST,
415 MESON_SAR_ADC_CHAN_LIST_ENTRY_MASK(0), regval);
416
417 regval = FIELD_PREP(MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_MUX_MASK,
Martin Blumenstingl827df052018-09-25 00:13:26 +0200418 chan->address);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100419 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DETECT_IDLE_SW,
420 MESON_SAR_ADC_DETECT_IDLE_SW_DETECT_MUX_MASK,
421 regval);
422
423 regval = FIELD_PREP(MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_MUX_SEL_MASK,
Martin Blumenstingl827df052018-09-25 00:13:26 +0200424 chan->address);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100425 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DETECT_IDLE_SW,
426 MESON_SAR_ADC_DETECT_IDLE_SW_IDLE_MUX_SEL_MASK,
427 regval);
428
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100429 if (chan->address == MESON_SAR_ADC_VOLTAGE_AND_TEMP_CHANNEL) {
430 if (chan->type == IIO_TEMP)
431 regval = MESON_SAR_ADC_DELTA_10_TEMP_SEL;
432 else
433 regval = 0;
434
435 regmap_update_bits(priv->regmap,
436 MESON_SAR_ADC_DELTA_10,
437 MESON_SAR_ADC_DELTA_10_TEMP_SEL, regval);
438 }
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100439}
440
441static void meson_sar_adc_set_chan7_mux(struct iio_dev *indio_dev,
442 enum meson_sar_adc_chan7_mux_sel sel)
443{
444 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
445 u32 regval;
446
447 regval = FIELD_PREP(MESON_SAR_ADC_REG3_CTRL_CHAN7_MUX_SEL_MASK, sel);
448 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG3,
449 MESON_SAR_ADC_REG3_CTRL_CHAN7_MUX_SEL_MASK, regval);
450
451 usleep_range(10, 20);
452}
453
454static void meson_sar_adc_start_sample_engine(struct iio_dev *indio_dev)
455{
456 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
457
Heiner Kallweit3af10912017-02-15 20:31:45 +0100458 reinit_completion(&priv->done);
459
460 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
461 MESON_SAR_ADC_REG0_FIFO_IRQ_EN,
462 MESON_SAR_ADC_REG0_FIFO_IRQ_EN);
463
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100464 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
465 MESON_SAR_ADC_REG0_SAMPLE_ENGINE_ENABLE,
466 MESON_SAR_ADC_REG0_SAMPLE_ENGINE_ENABLE);
467
468 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
469 MESON_SAR_ADC_REG0_SAMPLING_START,
470 MESON_SAR_ADC_REG0_SAMPLING_START);
471}
472
473static void meson_sar_adc_stop_sample_engine(struct iio_dev *indio_dev)
474{
475 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
476
477 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
Heiner Kallweit3af10912017-02-15 20:31:45 +0100478 MESON_SAR_ADC_REG0_FIFO_IRQ_EN, 0);
479
480 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100481 MESON_SAR_ADC_REG0_SAMPLING_STOP,
482 MESON_SAR_ADC_REG0_SAMPLING_STOP);
483
484 /* wait until all modules are stopped */
485 meson_sar_adc_wait_busy_clear(indio_dev);
486
487 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
488 MESON_SAR_ADC_REG0_SAMPLE_ENGINE_ENABLE, 0);
489}
490
491static int meson_sar_adc_lock(struct iio_dev *indio_dev)
492{
493 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
494 int val, timeout = 10000;
495
496 mutex_lock(&indio_dev->mlock);
497
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200498 if (priv->param->has_bl30_integration) {
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +0200499 /* prevent BL30 from using the SAR ADC while we are using it */
500 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
501 MESON_SAR_ADC_DELAY_KERNEL_BUSY,
502 MESON_SAR_ADC_DELAY_KERNEL_BUSY);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100503
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +0200504 /*
505 * wait until BL30 releases it's lock (so we can use the SAR
506 * ADC)
507 */
508 do {
509 udelay(1);
510 regmap_read(priv->regmap, MESON_SAR_ADC_DELAY, &val);
511 } while (val & MESON_SAR_ADC_DELAY_BL30_BUSY && timeout--);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100512
Dan Carpenter3c3e4b32018-03-08 12:31:53 +0300513 if (timeout < 0) {
514 mutex_unlock(&indio_dev->mlock);
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +0200515 return -ETIMEDOUT;
Dan Carpenter3c3e4b32018-03-08 12:31:53 +0300516 }
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +0200517 }
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100518
519 return 0;
520}
521
522static void meson_sar_adc_unlock(struct iio_dev *indio_dev)
523{
524 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
525
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200526 if (priv->param->has_bl30_integration)
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +0200527 /* allow BL30 to use the SAR ADC again */
528 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
529 MESON_SAR_ADC_DELAY_KERNEL_BUSY, 0);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100530
531 mutex_unlock(&indio_dev->mlock);
532}
533
534static void meson_sar_adc_clear_fifo(struct iio_dev *indio_dev)
535{
536 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
Martin Blumenstingl103a07d2017-06-04 15:28:23 +0200537 unsigned int count, tmp;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100538
539 for (count = 0; count < MESON_SAR_ADC_MAX_FIFO_SIZE; count++) {
540 if (!meson_sar_adc_get_fifo_count(indio_dev))
541 break;
542
Martin Blumenstingl103a07d2017-06-04 15:28:23 +0200543 regmap_read(priv->regmap, MESON_SAR_ADC_FIFO_RD, &tmp);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100544 }
545}
546
547static int meson_sar_adc_get_sample(struct iio_dev *indio_dev,
548 const struct iio_chan_spec *chan,
549 enum meson_sar_adc_avg_mode avg_mode,
550 enum meson_sar_adc_num_samples avg_samples,
551 int *val)
552{
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100553 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100554 int ret;
555
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100556 if (chan->type == IIO_TEMP && !priv->temperature_sensor_calibrated)
557 return -ENOTSUPP;
558
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100559 ret = meson_sar_adc_lock(indio_dev);
560 if (ret)
561 return ret;
562
563 /* clear the FIFO to make sure we're not reading old values */
564 meson_sar_adc_clear_fifo(indio_dev);
565
566 meson_sar_adc_set_averaging(indio_dev, chan, avg_mode, avg_samples);
567
568 meson_sar_adc_enable_channel(indio_dev, chan);
569
570 meson_sar_adc_start_sample_engine(indio_dev);
571 ret = meson_sar_adc_read_raw_sample(indio_dev, chan, val);
572 meson_sar_adc_stop_sample_engine(indio_dev);
573
574 meson_sar_adc_unlock(indio_dev);
575
576 if (ret) {
577 dev_warn(indio_dev->dev.parent,
Martin Blumenstingl827df052018-09-25 00:13:26 +0200578 "failed to read sample for channel %lu: %d\n",
579 chan->address, ret);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100580 return ret;
581 }
582
583 return IIO_VAL_INT;
584}
585
586static int meson_sar_adc_iio_info_read_raw(struct iio_dev *indio_dev,
587 const struct iio_chan_spec *chan,
588 int *val, int *val2, long mask)
589{
590 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
591 int ret;
592
593 switch (mask) {
594 case IIO_CHAN_INFO_RAW:
595 return meson_sar_adc_get_sample(indio_dev, chan, NO_AVERAGING,
596 ONE_SAMPLE, val);
597 break;
598
599 case IIO_CHAN_INFO_AVERAGE_RAW:
600 return meson_sar_adc_get_sample(indio_dev, chan,
601 MEAN_AVERAGING, EIGHT_SAMPLES,
602 val);
603 break;
604
605 case IIO_CHAN_INFO_SCALE:
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100606 if (chan->type == IIO_VOLTAGE) {
607 ret = regulator_get_voltage(priv->vref);
608 if (ret < 0) {
609 dev_err(indio_dev->dev.parent,
610 "failed to get vref voltage: %d\n",
611 ret);
612 return ret;
613 }
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100614
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100615 *val = ret / 1000;
616 *val2 = priv->param->resolution;
617 return IIO_VAL_FRACTIONAL_LOG2;
618 } else if (chan->type == IIO_TEMP) {
619 /* SoC specific multiplier and divider */
620 *val = priv->param->temperature_multiplier;
621 *val2 = priv->param->temperature_divider;
622
623 /* celsius to millicelsius */
624 *val *= 1000;
625
626 return IIO_VAL_FRACTIONAL;
627 } else {
628 return -EINVAL;
629 }
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100630
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100631 case IIO_CHAN_INFO_CALIBBIAS:
632 *val = priv->calibbias;
633 return IIO_VAL_INT;
634
635 case IIO_CHAN_INFO_CALIBSCALE:
636 *val = priv->calibscale / MILLION;
637 *val2 = priv->calibscale % MILLION;
638 return IIO_VAL_INT_PLUS_MICRO;
639
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100640 case IIO_CHAN_INFO_OFFSET:
641 *val = DIV_ROUND_CLOSEST(MESON_SAR_ADC_TEMP_OFFSET *
642 priv->param->temperature_divider,
643 priv->param->temperature_multiplier);
644 *val -= priv->temperature_sensor_adc_val;
645 return IIO_VAL_INT;
646
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100647 default:
648 return -EINVAL;
649 }
650}
651
652static int meson_sar_adc_clk_init(struct iio_dev *indio_dev,
653 void __iomem *base)
654{
655 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
656 struct clk_init_data init;
657 const char *clk_parents[1];
658
Rob Herring3921db42017-07-18 16:43:08 -0500659 init.name = devm_kasprintf(&indio_dev->dev, GFP_KERNEL, "%pOF#adc_div",
660 indio_dev->dev.of_node);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100661 init.flags = 0;
662 init.ops = &clk_divider_ops;
663 clk_parents[0] = __clk_get_name(priv->clkin);
664 init.parent_names = clk_parents;
665 init.num_parents = 1;
666
667 priv->clk_div.reg = base + MESON_SAR_ADC_REG3;
668 priv->clk_div.shift = MESON_SAR_ADC_REG3_ADC_CLK_DIV_SHIFT;
669 priv->clk_div.width = MESON_SAR_ADC_REG3_ADC_CLK_DIV_WIDTH;
670 priv->clk_div.hw.init = &init;
671 priv->clk_div.flags = 0;
672
673 priv->adc_div_clk = devm_clk_register(&indio_dev->dev,
674 &priv->clk_div.hw);
675 if (WARN_ON(IS_ERR(priv->adc_div_clk)))
676 return PTR_ERR(priv->adc_div_clk);
677
Rob Herring3921db42017-07-18 16:43:08 -0500678 init.name = devm_kasprintf(&indio_dev->dev, GFP_KERNEL, "%pOF#adc_en",
679 indio_dev->dev.of_node);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100680 init.flags = CLK_SET_RATE_PARENT;
681 init.ops = &clk_gate_ops;
682 clk_parents[0] = __clk_get_name(priv->adc_div_clk);
683 init.parent_names = clk_parents;
684 init.num_parents = 1;
685
686 priv->clk_gate.reg = base + MESON_SAR_ADC_REG3;
Martin Blumenstingl7a6b0422017-10-31 21:01:43 +0100687 priv->clk_gate.bit_idx = __ffs(MESON_SAR_ADC_REG3_CLK_EN);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100688 priv->clk_gate.hw.init = &init;
689
690 priv->adc_clk = devm_clk_register(&indio_dev->dev, &priv->clk_gate.hw);
691 if (WARN_ON(IS_ERR(priv->adc_clk)))
692 return PTR_ERR(priv->adc_clk);
693
694 return 0;
695}
696
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100697static int meson_sar_adc_temp_sensor_init(struct iio_dev *indio_dev)
698{
699 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
700 u8 *buf, trimming_bits, trimming_mask, upper_adc_val;
701 struct nvmem_cell *temperature_calib;
702 size_t read_len;
703 int ret;
704
705 temperature_calib = devm_nvmem_cell_get(&indio_dev->dev,
706 "temperature_calib");
707 if (IS_ERR(temperature_calib)) {
708 ret = PTR_ERR(temperature_calib);
709
710 /*
711 * leave the temperature sensor disabled if no calibration data
712 * was passed via nvmem-cells.
713 */
714 if (ret == -ENODEV)
715 return 0;
716
717 if (ret != -EPROBE_DEFER)
718 dev_err(indio_dev->dev.parent,
719 "failed to get temperature_calib cell\n");
720
721 return ret;
722 }
723
724 read_len = MESON_SAR_ADC_EFUSE_BYTES;
725 buf = nvmem_cell_read(temperature_calib, &read_len);
726 if (IS_ERR(buf)) {
727 dev_err(indio_dev->dev.parent,
728 "failed to read temperature_calib cell\n");
729 return PTR_ERR(buf);
730 } else if (read_len != MESON_SAR_ADC_EFUSE_BYTES) {
731 kfree(buf);
732 dev_err(indio_dev->dev.parent,
733 "invalid read size of temperature_calib cell\n");
734 return -EINVAL;
735 }
736
737 trimming_bits = priv->param->temperature_trimming_bits;
738 trimming_mask = BIT(trimming_bits) - 1;
739
740 priv->temperature_sensor_calibrated =
741 buf[3] & MESON_SAR_ADC_EFUSE_BYTE3_IS_CALIBRATED;
742 priv->temperature_sensor_coefficient = buf[2] & trimming_mask;
743
744 upper_adc_val = FIELD_GET(MESON_SAR_ADC_EFUSE_BYTE3_UPPER_ADC_VAL,
745 buf[3]);
746
747 priv->temperature_sensor_adc_val = buf[2];
748 priv->temperature_sensor_adc_val |= upper_adc_val << BITS_PER_BYTE;
749 priv->temperature_sensor_adc_val >>= trimming_bits;
750
751 kfree(buf);
752
753 return 0;
754}
755
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100756static int meson_sar_adc_init(struct iio_dev *indio_dev)
757{
758 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
Martin Blumenstinglab569a42017-10-31 21:01:47 +0100759 int regval, i, ret;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100760
761 /*
762 * make sure we start at CH7 input since the other muxes are only used
763 * for internal calibration.
764 */
765 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_CH7_INPUT);
766
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200767 if (priv->param->has_bl30_integration) {
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +0200768 /*
769 * leave sampling delay and the input clocks as configured by
770 * BL30 to make sure BL30 gets the values it expects when
771 * reading the temperature sensor.
772 */
773 regmap_read(priv->regmap, MESON_SAR_ADC_REG3, &regval);
774 if (regval & MESON_SAR_ADC_REG3_BL30_INITIALIZED)
775 return 0;
776 }
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100777
778 meson_sar_adc_stop_sample_engine(indio_dev);
779
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100780 /*
781 * disable this bit as seems to be only relevant for Meson6 (based
782 * on the vendor driver), which we don't support at the moment.
783 */
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100784 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100785 MESON_SAR_ADC_REG0_ADC_TEMP_SEN_SEL, 0);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100786
787 /* disable all channels by default */
788 regmap_write(priv->regmap, MESON_SAR_ADC_CHAN_LIST, 0x0);
789
790 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG3,
791 MESON_SAR_ADC_REG3_CTRL_SAMPLING_CLOCK_PHASE, 0);
792 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG3,
793 MESON_SAR_ADC_REG3_CNTL_USE_SC_DLY,
794 MESON_SAR_ADC_REG3_CNTL_USE_SC_DLY);
795
796 /* delay between two samples = (10+1) * 1uS */
797 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
798 MESON_SAR_ADC_DELAY_INPUT_DLY_CNT_MASK,
799 FIELD_PREP(MESON_SAR_ADC_DELAY_SAMPLE_DLY_CNT_MASK,
800 10));
801 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
802 MESON_SAR_ADC_DELAY_SAMPLE_DLY_SEL_MASK,
803 FIELD_PREP(MESON_SAR_ADC_DELAY_SAMPLE_DLY_SEL_MASK,
804 0));
805
806 /* delay between two samples = (10+1) * 1uS */
807 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
808 MESON_SAR_ADC_DELAY_INPUT_DLY_CNT_MASK,
809 FIELD_PREP(MESON_SAR_ADC_DELAY_INPUT_DLY_CNT_MASK,
810 10));
811 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELAY,
812 MESON_SAR_ADC_DELAY_INPUT_DLY_SEL_MASK,
813 FIELD_PREP(MESON_SAR_ADC_DELAY_INPUT_DLY_SEL_MASK,
814 1));
815
Martin Blumenstinglab569a42017-10-31 21:01:47 +0100816 /*
817 * set up the input channel muxes in MESON_SAR_ADC_CHAN_10_SW
818 * (0 = SAR_ADC_CH0, 1 = SAR_ADC_CH1)
819 */
820 regval = FIELD_PREP(MESON_SAR_ADC_CHAN_10_SW_CHAN0_MUX_SEL_MASK, 0);
821 regmap_update_bits(priv->regmap, MESON_SAR_ADC_CHAN_10_SW,
822 MESON_SAR_ADC_CHAN_10_SW_CHAN0_MUX_SEL_MASK,
823 regval);
824 regval = FIELD_PREP(MESON_SAR_ADC_CHAN_10_SW_CHAN1_MUX_SEL_MASK, 1);
825 regmap_update_bits(priv->regmap, MESON_SAR_ADC_CHAN_10_SW,
826 MESON_SAR_ADC_CHAN_10_SW_CHAN1_MUX_SEL_MASK,
827 regval);
828
829 /*
830 * set up the input channel muxes in MESON_SAR_ADC_AUX_SW
831 * (2 = SAR_ADC_CH2, 3 = SAR_ADC_CH3, ...) and enable
832 * MESON_SAR_ADC_AUX_SW_YP_DRIVE_SW and
833 * MESON_SAR_ADC_AUX_SW_XP_DRIVE_SW like the vendor driver.
834 */
835 regval = 0;
836 for (i = 2; i <= 7; i++)
837 regval |= i << MESON_SAR_ADC_AUX_SW_MUX_SEL_CHAN_SHIFT(i);
838 regval |= MESON_SAR_ADC_AUX_SW_YP_DRIVE_SW;
839 regval |= MESON_SAR_ADC_AUX_SW_XP_DRIVE_SW;
840 regmap_write(priv->regmap, MESON_SAR_ADC_AUX_SW, regval);
841
Martin Blumenstingl723a61e2018-11-04 00:10:24 +0100842 if (priv->temperature_sensor_calibrated) {
843 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELTA_10,
844 MESON_SAR_ADC_DELTA_10_TS_REVE1,
845 MESON_SAR_ADC_DELTA_10_TS_REVE1);
846 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELTA_10,
847 MESON_SAR_ADC_DELTA_10_TS_REVE0,
848 MESON_SAR_ADC_DELTA_10_TS_REVE0);
849
850 /*
851 * set bits [3:0] of the TSC (temperature sensor coefficient)
852 * to get the correct values when reading the temperature.
853 */
854 regval = FIELD_PREP(MESON_SAR_ADC_DELTA_10_TS_C_MASK,
855 priv->temperature_sensor_coefficient);
856 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELTA_10,
857 MESON_SAR_ADC_DELTA_10_TS_C_MASK, regval);
858 } else {
859 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELTA_10,
860 MESON_SAR_ADC_DELTA_10_TS_REVE1, 0);
861 regmap_update_bits(priv->regmap, MESON_SAR_ADC_DELTA_10,
862 MESON_SAR_ADC_DELTA_10_TS_REVE0, 0);
863 }
864
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100865 ret = clk_set_parent(priv->adc_sel_clk, priv->clkin);
866 if (ret) {
867 dev_err(indio_dev->dev.parent,
868 "failed to set adc parent to clkin\n");
869 return ret;
870 }
871
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200872 ret = clk_set_rate(priv->adc_clk, priv->param->clock_rate);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100873 if (ret) {
874 dev_err(indio_dev->dev.parent,
875 "failed to set adc clock rate\n");
876 return ret;
877 }
878
879 return 0;
880}
881
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100882static void meson_sar_adc_set_bandgap(struct iio_dev *indio_dev, bool on_off)
883{
884 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
Martin Blumenstingl057e5a12018-09-23 00:21:02 +0200885 const struct meson_sar_adc_param *param = priv->param;
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100886 u32 enable_mask;
887
Yixun Lan053ffe32018-03-26 16:46:27 +0800888 if (param->bandgap_reg == MESON_SAR_ADC_REG11)
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100889 enable_mask = MESON_SAR_ADC_REG11_BANDGAP_EN;
890 else
891 enable_mask = MESON_SAR_ADC_DELTA_10_TS_VBG_EN;
892
Yixun Lan053ffe32018-03-26 16:46:27 +0800893 regmap_update_bits(priv->regmap, param->bandgap_reg, enable_mask,
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100894 on_off ? enable_mask : 0);
895}
896
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100897static int meson_sar_adc_hw_enable(struct iio_dev *indio_dev)
898{
899 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
900 int ret;
Heiner Kallweit3af10912017-02-15 20:31:45 +0100901 u32 regval;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100902
903 ret = meson_sar_adc_lock(indio_dev);
904 if (ret)
905 goto err_lock;
906
907 ret = regulator_enable(priv->vref);
908 if (ret < 0) {
909 dev_err(indio_dev->dev.parent,
910 "failed to enable vref regulator\n");
911 goto err_vref;
912 }
913
914 ret = clk_prepare_enable(priv->core_clk);
915 if (ret) {
916 dev_err(indio_dev->dev.parent, "failed to enable core clk\n");
917 goto err_core_clk;
918 }
919
Heiner Kallweit3af10912017-02-15 20:31:45 +0100920 regval = FIELD_PREP(MESON_SAR_ADC_REG0_FIFO_CNT_IRQ_MASK, 1);
921 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG0,
922 MESON_SAR_ADC_REG0_FIFO_CNT_IRQ_MASK, regval);
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100923
924 meson_sar_adc_set_bandgap(indio_dev, true);
925
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100926 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG3,
927 MESON_SAR_ADC_REG3_ADC_EN,
928 MESON_SAR_ADC_REG3_ADC_EN);
929
930 udelay(5);
931
932 ret = clk_prepare_enable(priv->adc_clk);
933 if (ret) {
934 dev_err(indio_dev->dev.parent, "failed to enable adc clk\n");
935 goto err_adc_clk;
936 }
937
938 meson_sar_adc_unlock(indio_dev);
939
940 return 0;
941
942err_adc_clk:
943 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG3,
944 MESON_SAR_ADC_REG3_ADC_EN, 0);
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100945 meson_sar_adc_set_bandgap(indio_dev, false);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100946 clk_disable_unprepare(priv->core_clk);
947err_core_clk:
948 regulator_disable(priv->vref);
949err_vref:
950 meson_sar_adc_unlock(indio_dev);
951err_lock:
952 return ret;
953}
954
955static int meson_sar_adc_hw_disable(struct iio_dev *indio_dev)
956{
957 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
958 int ret;
959
960 ret = meson_sar_adc_lock(indio_dev);
961 if (ret)
962 return ret;
963
964 clk_disable_unprepare(priv->adc_clk);
965
966 regmap_update_bits(priv->regmap, MESON_SAR_ADC_REG3,
967 MESON_SAR_ADC_REG3_ADC_EN, 0);
Martin Blumenstingld85eed92017-10-31 21:01:44 +0100968
969 meson_sar_adc_set_bandgap(indio_dev, false);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100970
Martin Blumenstingl3adbf342017-01-22 19:17:13 +0100971 clk_disable_unprepare(priv->core_clk);
972
973 regulator_disable(priv->vref);
974
975 meson_sar_adc_unlock(indio_dev);
976
977 return 0;
978}
979
Heiner Kallweit3af10912017-02-15 20:31:45 +0100980static irqreturn_t meson_sar_adc_irq(int irq, void *data)
981{
982 struct iio_dev *indio_dev = data;
983 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
984 unsigned int cnt, threshold;
985 u32 regval;
986
987 regmap_read(priv->regmap, MESON_SAR_ADC_REG0, &regval);
988 cnt = FIELD_GET(MESON_SAR_ADC_REG0_FIFO_COUNT_MASK, regval);
989 threshold = FIELD_GET(MESON_SAR_ADC_REG0_FIFO_CNT_IRQ_MASK, regval);
990
991 if (cnt < threshold)
992 return IRQ_NONE;
993
994 complete(&priv->done);
995
996 return IRQ_HANDLED;
997}
998
Heiner Kallweit48ba7c32017-03-18 19:38:19 +0100999static int meson_sar_adc_calib(struct iio_dev *indio_dev)
1000{
1001 struct meson_sar_adc_priv *priv = iio_priv(indio_dev);
1002 int ret, nominal0, nominal1, value0, value1;
1003
1004 /* use points 25% and 75% for calibration */
Martin Blumenstingl057e5a12018-09-23 00:21:02 +02001005 nominal0 = (1 << priv->param->resolution) / 4;
1006 nominal1 = (1 << priv->param->resolution) * 3 / 4;
Heiner Kallweit48ba7c32017-03-18 19:38:19 +01001007
1008 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_VDD_DIV4);
1009 usleep_range(10, 20);
1010 ret = meson_sar_adc_get_sample(indio_dev,
Martin Blumenstinglbdd4b072018-09-25 00:13:25 +02001011 &indio_dev->channels[7],
Heiner Kallweit48ba7c32017-03-18 19:38:19 +01001012 MEAN_AVERAGING, EIGHT_SAMPLES, &value0);
1013 if (ret < 0)
1014 goto out;
1015
1016 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_VDD_MUL3_DIV4);
1017 usleep_range(10, 20);
1018 ret = meson_sar_adc_get_sample(indio_dev,
Martin Blumenstinglbdd4b072018-09-25 00:13:25 +02001019 &indio_dev->channels[7],
Heiner Kallweit48ba7c32017-03-18 19:38:19 +01001020 MEAN_AVERAGING, EIGHT_SAMPLES, &value1);
1021 if (ret < 0)
1022 goto out;
1023
1024 if (value1 <= value0) {
1025 ret = -EINVAL;
1026 goto out;
1027 }
1028
1029 priv->calibscale = div_s64((nominal1 - nominal0) * (s64)MILLION,
1030 value1 - value0);
1031 priv->calibbias = nominal0 - div_s64((s64)value0 * priv->calibscale,
1032 MILLION);
1033 ret = 0;
1034out:
1035 meson_sar_adc_set_chan7_mux(indio_dev, CHAN7_MUX_CH7_INPUT);
1036
1037 return ret;
1038}
1039
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001040static const struct iio_info meson_sar_adc_iio_info = {
1041 .read_raw = meson_sar_adc_iio_info_read_raw,
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001042};
1043
Yixun Lan053ffe32018-03-26 16:46:27 +08001044static const struct meson_sar_adc_param meson_sar_adc_meson8_param = {
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +02001045 .has_bl30_integration = false,
Martin Blumenstinglfda29db2017-10-31 21:01:46 +01001046 .clock_rate = 1150000,
Martin Blumenstingld85eed92017-10-31 21:01:44 +01001047 .bandgap_reg = MESON_SAR_ADC_DELTA_10,
Martin Blumenstingl96748822017-10-31 21:01:45 +01001048 .regmap_config = &meson_sar_adc_regmap_config_meson8,
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +02001049 .resolution = 10,
Martin Blumenstingl723a61e2018-11-04 00:10:24 +01001050 .temperature_trimming_bits = 4,
1051 .temperature_multiplier = 18 * 10000,
1052 .temperature_divider = 1024 * 10 * 85,
1053};
1054
1055static const struct meson_sar_adc_param meson_sar_adc_meson8b_param = {
1056 .has_bl30_integration = false,
1057 .clock_rate = 1150000,
1058 .bandgap_reg = MESON_SAR_ADC_DELTA_10,
1059 .regmap_config = &meson_sar_adc_regmap_config_meson8,
1060 .resolution = 10,
Yixun Lan053ffe32018-03-26 16:46:27 +08001061};
1062
1063static const struct meson_sar_adc_param meson_sar_adc_gxbb_param = {
1064 .has_bl30_integration = true,
1065 .clock_rate = 1200000,
1066 .bandgap_reg = MESON_SAR_ADC_REG11,
1067 .regmap_config = &meson_sar_adc_regmap_config_gxbb,
1068 .resolution = 10,
1069};
1070
1071static const struct meson_sar_adc_param meson_sar_adc_gxl_param = {
1072 .has_bl30_integration = true,
1073 .clock_rate = 1200000,
1074 .bandgap_reg = MESON_SAR_ADC_REG11,
1075 .regmap_config = &meson_sar_adc_regmap_config_gxbb,
1076 .resolution = 12,
1077};
1078
1079static const struct meson_sar_adc_data meson_sar_adc_meson8_data = {
1080 .param = &meson_sar_adc_meson8_param,
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +02001081 .name = "meson-meson8-saradc",
1082};
1083
1084static const struct meson_sar_adc_data meson_sar_adc_meson8b_data = {
Martin Blumenstingl723a61e2018-11-04 00:10:24 +01001085 .param = &meson_sar_adc_meson8b_param,
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +02001086 .name = "meson-meson8b-saradc",
1087};
1088
Martin Blumenstinglffc0d632018-07-21 21:40:49 +02001089static const struct meson_sar_adc_data meson_sar_adc_meson8m2_data = {
Martin Blumenstingl723a61e2018-11-04 00:10:24 +01001090 .param = &meson_sar_adc_meson8b_param,
Martin Blumenstinglffc0d632018-07-21 21:40:49 +02001091 .name = "meson-meson8m2-saradc",
1092};
1093
Martin Blumenstinglc1c2de32017-05-06 15:49:27 +02001094static const struct meson_sar_adc_data meson_sar_adc_gxbb_data = {
Yixun Lan053ffe32018-03-26 16:46:27 +08001095 .param = &meson_sar_adc_gxbb_param,
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001096 .name = "meson-gxbb-saradc",
1097};
1098
Martin Blumenstinglc1c2de32017-05-06 15:49:27 +02001099static const struct meson_sar_adc_data meson_sar_adc_gxl_data = {
Yixun Lan053ffe32018-03-26 16:46:27 +08001100 .param = &meson_sar_adc_gxl_param,
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001101 .name = "meson-gxl-saradc",
1102};
1103
Martin Blumenstinglc1c2de32017-05-06 15:49:27 +02001104static const struct meson_sar_adc_data meson_sar_adc_gxm_data = {
Yixun Lan053ffe32018-03-26 16:46:27 +08001105 .param = &meson_sar_adc_gxl_param,
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001106 .name = "meson-gxm-saradc",
1107};
1108
Xingyu Chenff632dd2018-03-26 16:46:29 +08001109static const struct meson_sar_adc_data meson_sar_adc_axg_data = {
1110 .param = &meson_sar_adc_gxl_param,
1111 .name = "meson-axg-saradc",
1112};
1113
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001114static const struct of_device_id meson_sar_adc_of_match[] = {
1115 {
Martin Blumenstingl6c76ed32017-05-06 15:49:29 +02001116 .compatible = "amlogic,meson8-saradc",
1117 .data = &meson_sar_adc_meson8_data,
1118 },
1119 {
1120 .compatible = "amlogic,meson8b-saradc",
1121 .data = &meson_sar_adc_meson8b_data,
1122 },
1123 {
Martin Blumenstinglffc0d632018-07-21 21:40:49 +02001124 .compatible = "amlogic,meson8m2-saradc",
1125 .data = &meson_sar_adc_meson8m2_data,
1126 },
1127 {
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001128 .compatible = "amlogic,meson-gxbb-saradc",
1129 .data = &meson_sar_adc_gxbb_data,
1130 }, {
1131 .compatible = "amlogic,meson-gxl-saradc",
1132 .data = &meson_sar_adc_gxl_data,
1133 }, {
1134 .compatible = "amlogic,meson-gxm-saradc",
1135 .data = &meson_sar_adc_gxm_data,
Xingyu Chenff632dd2018-03-26 16:46:29 +08001136 }, {
1137 .compatible = "amlogic,meson-axg-saradc",
1138 .data = &meson_sar_adc_axg_data,
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001139 },
1140 {},
1141};
1142MODULE_DEVICE_TABLE(of, meson_sar_adc_of_match);
1143
1144static int meson_sar_adc_probe(struct platform_device *pdev)
1145{
Martin Blumenstingl234c64a2018-09-23 00:21:01 +02001146 const struct meson_sar_adc_data *match_data;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001147 struct meson_sar_adc_priv *priv;
1148 struct iio_dev *indio_dev;
1149 struct resource *res;
1150 void __iomem *base;
Heiner Kallweit3af10912017-02-15 20:31:45 +01001151 int irq, ret;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001152
1153 indio_dev = devm_iio_device_alloc(&pdev->dev, sizeof(*priv));
1154 if (!indio_dev) {
1155 dev_err(&pdev->dev, "failed allocating iio device\n");
1156 return -ENOMEM;
1157 }
1158
1159 priv = iio_priv(indio_dev);
Heiner Kallweit3af10912017-02-15 20:31:45 +01001160 init_completion(&priv->done);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001161
Martin Blumenstingl234c64a2018-09-23 00:21:01 +02001162 match_data = of_device_get_match_data(&pdev->dev);
1163 if (!match_data) {
1164 dev_err(&pdev->dev, "failed to get match data\n");
Gustavo A. R. Silva2f9aeee2017-07-07 01:46:30 -05001165 return -ENODEV;
1166 }
1167
Martin Blumenstingl057e5a12018-09-23 00:21:02 +02001168 priv->param = match_data->param;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001169
Martin Blumenstingl057e5a12018-09-23 00:21:02 +02001170 indio_dev->name = match_data->name;
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001171 indio_dev->dev.parent = &pdev->dev;
1172 indio_dev->dev.of_node = pdev->dev.of_node;
1173 indio_dev->modes = INDIO_DIRECT_MODE;
1174 indio_dev->info = &meson_sar_adc_iio_info;
1175
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001176 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
1177 base = devm_ioremap_resource(&pdev->dev, res);
1178 if (IS_ERR(base))
1179 return PTR_ERR(base);
1180
Heiner Kallweit3af10912017-02-15 20:31:45 +01001181 irq = irq_of_parse_and_map(pdev->dev.of_node, 0);
1182 if (!irq)
1183 return -EINVAL;
1184
1185 ret = devm_request_irq(&pdev->dev, irq, meson_sar_adc_irq, IRQF_SHARED,
1186 dev_name(&pdev->dev), indio_dev);
1187 if (ret)
1188 return ret;
1189
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001190 priv->regmap = devm_regmap_init_mmio(&pdev->dev, base,
Martin Blumenstingl057e5a12018-09-23 00:21:02 +02001191 priv->param->regmap_config);
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001192 if (IS_ERR(priv->regmap))
1193 return PTR_ERR(priv->regmap);
1194
1195 priv->clkin = devm_clk_get(&pdev->dev, "clkin");
1196 if (IS_ERR(priv->clkin)) {
1197 dev_err(&pdev->dev, "failed to get clkin\n");
1198 return PTR_ERR(priv->clkin);
1199 }
1200
1201 priv->core_clk = devm_clk_get(&pdev->dev, "core");
1202 if (IS_ERR(priv->core_clk)) {
1203 dev_err(&pdev->dev, "failed to get core clk\n");
1204 return PTR_ERR(priv->core_clk);
1205 }
1206
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001207 priv->adc_clk = devm_clk_get(&pdev->dev, "adc_clk");
1208 if (IS_ERR(priv->adc_clk)) {
1209 if (PTR_ERR(priv->adc_clk) == -ENOENT) {
1210 priv->adc_clk = NULL;
1211 } else {
1212 dev_err(&pdev->dev, "failed to get adc clk\n");
1213 return PTR_ERR(priv->adc_clk);
1214 }
1215 }
1216
1217 priv->adc_sel_clk = devm_clk_get(&pdev->dev, "adc_sel");
1218 if (IS_ERR(priv->adc_sel_clk)) {
1219 if (PTR_ERR(priv->adc_sel_clk) == -ENOENT) {
1220 priv->adc_sel_clk = NULL;
1221 } else {
1222 dev_err(&pdev->dev, "failed to get adc_sel clk\n");
1223 return PTR_ERR(priv->adc_sel_clk);
1224 }
1225 }
1226
1227 /* on pre-GXBB SoCs the SAR ADC itself provides the ADC clock: */
1228 if (!priv->adc_clk) {
1229 ret = meson_sar_adc_clk_init(indio_dev, base);
1230 if (ret)
1231 return ret;
1232 }
1233
1234 priv->vref = devm_regulator_get(&pdev->dev, "vref");
1235 if (IS_ERR(priv->vref)) {
1236 dev_err(&pdev->dev, "failed to get vref regulator\n");
1237 return PTR_ERR(priv->vref);
1238 }
1239
Heiner Kallweit48ba7c32017-03-18 19:38:19 +01001240 priv->calibscale = MILLION;
1241
Martin Blumenstingl723a61e2018-11-04 00:10:24 +01001242 if (priv->param->temperature_trimming_bits) {
1243 ret = meson_sar_adc_temp_sensor_init(indio_dev);
1244 if (ret)
1245 return ret;
1246 }
1247
1248 if (priv->temperature_sensor_calibrated) {
1249 indio_dev->channels = meson_sar_adc_and_temp_iio_channels;
1250 indio_dev->num_channels =
1251 ARRAY_SIZE(meson_sar_adc_and_temp_iio_channels);
1252 } else {
1253 indio_dev->channels = meson_sar_adc_iio_channels;
1254 indio_dev->num_channels =
1255 ARRAY_SIZE(meson_sar_adc_iio_channels);
1256 }
1257
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001258 ret = meson_sar_adc_init(indio_dev);
1259 if (ret)
1260 goto err;
1261
1262 ret = meson_sar_adc_hw_enable(indio_dev);
1263 if (ret)
1264 goto err;
1265
Heiner Kallweit48ba7c32017-03-18 19:38:19 +01001266 ret = meson_sar_adc_calib(indio_dev);
1267 if (ret)
1268 dev_warn(&pdev->dev, "calibration failed\n");
1269
Martin Blumenstingl3adbf342017-01-22 19:17:13 +01001270 platform_set_drvdata(pdev, indio_dev);
1271
1272 ret = iio_device_register(indio_dev);
1273 if (ret)
1274 goto err_hw;
1275
1276 return 0;
1277
1278err_hw:
1279 meson_sar_adc_hw_disable(indio_dev);
1280err:
1281 return ret;
1282}
1283
1284static int meson_sar_adc_remove(struct platform_device *pdev)
1285{
1286 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
1287
1288 iio_device_unregister(indio_dev);
1289
1290 return meson_sar_adc_hw_disable(indio_dev);
1291}
1292
1293static int __maybe_unused meson_sar_adc_suspend(struct device *dev)
1294{
1295 struct iio_dev *indio_dev = dev_get_drvdata(dev);
1296
1297 return meson_sar_adc_hw_disable(indio_dev);
1298}
1299
1300static int __maybe_unused meson_sar_adc_resume(struct device *dev)
1301{
1302 struct iio_dev *indio_dev = dev_get_drvdata(dev);
1303
1304 return meson_sar_adc_hw_enable(indio_dev);
1305}
1306
1307static SIMPLE_DEV_PM_OPS(meson_sar_adc_pm_ops,
1308 meson_sar_adc_suspend, meson_sar_adc_resume);
1309
1310static struct platform_driver meson_sar_adc_driver = {
1311 .probe = meson_sar_adc_probe,
1312 .remove = meson_sar_adc_remove,
1313 .driver = {
1314 .name = "meson-saradc",
1315 .of_match_table = meson_sar_adc_of_match,
1316 .pm = &meson_sar_adc_pm_ops,
1317 },
1318};
1319
1320module_platform_driver(meson_sar_adc_driver);
1321
1322MODULE_AUTHOR("Martin Blumenstingl <martin.blumenstingl@googlemail.com>");
1323MODULE_DESCRIPTION("Amlogic Meson SAR ADC driver");
1324MODULE_LICENSE("GPL v2");