0001
0002
0003
0004
0005
0006
0007
0008
0009 #include <linux/bsearch.h>
0010 #include <linux/delay.h>
0011 #include <linux/kernel.h>
0012 #include <linux/module.h>
0013 #include <linux/mod_devicetable.h>
0014 #include <linux/property.h>
0015 #include <linux/spi/spi.h>
0016 #include <linux/gpio/consumer.h>
0017
0018 #include <linux/iio/iio.h>
0019 #include <linux/iio/sysfs.h>
0020
0021
0022 #define AD5758_NOP 0x00
0023 #define AD5758_DAC_INPUT 0x01
0024 #define AD5758_DAC_OUTPUT 0x02
0025 #define AD5758_CLEAR_CODE 0x03
0026 #define AD5758_USER_GAIN 0x04
0027 #define AD5758_USER_OFFSET 0x05
0028 #define AD5758_DAC_CONFIG 0x06
0029 #define AD5758_SW_LDAC 0x07
0030 #define AD5758_KEY 0x08
0031 #define AD5758_GP_CONFIG1 0x09
0032 #define AD5758_GP_CONFIG2 0x0A
0033 #define AD5758_DCDC_CONFIG1 0x0B
0034 #define AD5758_DCDC_CONFIG2 0x0C
0035 #define AD5758_WDT_CONFIG 0x0F
0036 #define AD5758_DIGITAL_DIAG_CONFIG 0x10
0037 #define AD5758_ADC_CONFIG 0x11
0038 #define AD5758_FAULT_PIN_CONFIG 0x12
0039 #define AD5758_TWO_STAGE_READBACK_SELECT 0x13
0040 #define AD5758_DIGITAL_DIAG_RESULTS 0x14
0041 #define AD5758_ANALOG_DIAG_RESULTS 0x15
0042 #define AD5758_STATUS 0x16
0043 #define AD5758_CHIP_ID 0x17
0044 #define AD5758_FREQ_MONITOR 0x18
0045 #define AD5758_DEVICE_ID_0 0x19
0046 #define AD5758_DEVICE_ID_1 0x1A
0047 #define AD5758_DEVICE_ID_2 0x1B
0048 #define AD5758_DEVICE_ID_3 0x1C
0049
0050
0051 #define AD5758_DAC_CONFIG_RANGE_MSK GENMASK(3, 0)
0052 #define AD5758_DAC_CONFIG_RANGE_MODE(x) (((x) & 0xF) << 0)
0053 #define AD5758_DAC_CONFIG_INT_EN_MSK BIT(5)
0054 #define AD5758_DAC_CONFIG_INT_EN_MODE(x) (((x) & 0x1) << 5)
0055 #define AD5758_DAC_CONFIG_OUT_EN_MSK BIT(6)
0056 #define AD5758_DAC_CONFIG_OUT_EN_MODE(x) (((x) & 0x1) << 6)
0057 #define AD5758_DAC_CONFIG_SR_EN_MSK BIT(8)
0058 #define AD5758_DAC_CONFIG_SR_EN_MODE(x) (((x) & 0x1) << 8)
0059 #define AD5758_DAC_CONFIG_SR_CLOCK_MSK GENMASK(12, 9)
0060 #define AD5758_DAC_CONFIG_SR_CLOCK_MODE(x) (((x) & 0xF) << 9)
0061 #define AD5758_DAC_CONFIG_SR_STEP_MSK GENMASK(15, 13)
0062 #define AD5758_DAC_CONFIG_SR_STEP_MODE(x) (((x) & 0x7) << 13)
0063
0064
0065 #define AD5758_KEY_CODE_RESET_1 0x15FA
0066 #define AD5758_KEY_CODE_RESET_2 0xAF51
0067 #define AD5758_KEY_CODE_SINGLE_ADC_CONV 0x1ADC
0068 #define AD5758_KEY_CODE_RESET_WDT 0x0D06
0069 #define AD5758_KEY_CODE_CALIB_MEM_REFRESH 0xFCBA
0070
0071
0072 #define AD5758_DCDC_CONFIG1_DCDC_VPROG_MSK GENMASK(4, 0)
0073 #define AD5758_DCDC_CONFIG1_DCDC_VPROG_MODE(x) (((x) & 0x1F) << 0)
0074 #define AD5758_DCDC_CONFIG1_DCDC_MODE_MSK GENMASK(6, 5)
0075 #define AD5758_DCDC_CONFIG1_DCDC_MODE_MODE(x) (((x) & 0x3) << 5)
0076
0077
0078 #define AD5758_DCDC_CONFIG2_ILIMIT_MSK GENMASK(3, 1)
0079 #define AD5758_DCDC_CONFIG2_ILIMIT_MODE(x) (((x) & 0x7) << 1)
0080 #define AD5758_DCDC_CONFIG2_INTR_SAT_3WI_MSK BIT(11)
0081 #define AD5758_DCDC_CONFIG2_BUSY_3WI_MSK BIT(12)
0082
0083
0084 #define AD5758_CAL_MEM_UNREFRESHED_MSK BIT(15)
0085
0086
0087 #define AD5758_ADC_CONFIG_PPC_BUF_EN(x) (((x) & 0x1) << 11)
0088 #define AD5758_ADC_CONFIG_PPC_BUF_MSK BIT(11)
0089
0090 #define AD5758_WR_FLAG_MSK(x) (0x80 | ((x) & 0x1F))
0091
0092 #define AD5758_FULL_SCALE_MICRO 65535000000ULL
0093
0094 struct ad5758_range {
0095 int reg;
0096 int min;
0097 int max;
0098 };
0099
0100
0101
0102
0103
0104
0105
0106
0107
0108
0109
0110
0111
0112 struct ad5758_state {
0113 struct spi_device *spi;
0114 struct mutex lock;
0115 struct gpio_desc *gpio_reset;
0116 struct ad5758_range out_range;
0117 unsigned int dc_dc_mode;
0118 unsigned int dc_dc_ilim;
0119 unsigned int slew_time;
0120 bool pwr_down;
0121 __be32 d32[3];
0122 };
0123
0124
0125
0126
0127
0128
0129
0130
0131
0132
0133
0134
0135
0136
0137 enum ad5758_output_range {
0138 AD5758_RANGE_0V_5V,
0139 AD5758_RANGE_0V_10V,
0140 AD5758_RANGE_PLUSMINUS_5V,
0141 AD5758_RANGE_PLUSMINUS_10V,
0142 AD5758_RANGE_0mA_20mA = 8,
0143 AD5758_RANGE_0mA_24mA,
0144 AD5758_RANGE_4mA_24mA,
0145 AD5758_RANGE_PLUSMINUS_20mA,
0146 AD5758_RANGE_PLUSMINUS_24mA,
0147 AD5758_RANGE_MINUS_1mA_PLUS_22mA,
0148 };
0149
0150 enum ad5758_dc_dc_mode {
0151 AD5758_DCDC_MODE_POWER_OFF,
0152 AD5758_DCDC_MODE_DPC_CURRENT,
0153 AD5758_DCDC_MODE_DPC_VOLTAGE,
0154 AD5758_DCDC_MODE_PPC_CURRENT,
0155 };
0156
0157 static const struct ad5758_range ad5758_voltage_range[] = {
0158 { AD5758_RANGE_0V_5V, 0, 5000000 },
0159 { AD5758_RANGE_0V_10V, 0, 10000000 },
0160 { AD5758_RANGE_PLUSMINUS_5V, -5000000, 5000000 },
0161 { AD5758_RANGE_PLUSMINUS_10V, -10000000, 10000000 }
0162 };
0163
0164 static const struct ad5758_range ad5758_current_range[] = {
0165 { AD5758_RANGE_0mA_20mA, 0, 20000},
0166 { AD5758_RANGE_0mA_24mA, 0, 24000 },
0167 { AD5758_RANGE_4mA_24mA, 4, 24000 },
0168 { AD5758_RANGE_PLUSMINUS_20mA, -20000, 20000 },
0169 { AD5758_RANGE_PLUSMINUS_24mA, -24000, 24000 },
0170 { AD5758_RANGE_MINUS_1mA_PLUS_22mA, -1000, 22000 },
0171 };
0172
0173 static const int ad5758_sr_clk[16] = {
0174 240000, 200000, 150000, 128000, 64000, 32000, 16000, 8000, 4000, 2000,
0175 1000, 512, 256, 128, 64, 16
0176 };
0177
0178 static const int ad5758_sr_step[8] = {
0179 4, 12, 64, 120, 256, 500, 1820, 2048
0180 };
0181
0182 static const int ad5758_dc_dc_ilim[6] = {
0183 150000, 200000, 250000, 300000, 350000, 400000
0184 };
0185
0186 static int ad5758_spi_reg_read(struct ad5758_state *st, unsigned int addr)
0187 {
0188 struct spi_transfer t[] = {
0189 {
0190 .tx_buf = &st->d32[0],
0191 .len = 4,
0192 .cs_change = 1,
0193 }, {
0194 .tx_buf = &st->d32[1],
0195 .rx_buf = &st->d32[2],
0196 .len = 4,
0197 },
0198 };
0199 int ret;
0200
0201 st->d32[0] = cpu_to_be32(
0202 (AD5758_WR_FLAG_MSK(AD5758_TWO_STAGE_READBACK_SELECT) << 24) |
0203 (addr << 8));
0204 st->d32[1] = cpu_to_be32(AD5758_WR_FLAG_MSK(AD5758_NOP) << 24);
0205
0206 ret = spi_sync_transfer(st->spi, t, ARRAY_SIZE(t));
0207 if (ret < 0)
0208 return ret;
0209
0210 return (be32_to_cpu(st->d32[2]) >> 8) & 0xFFFF;
0211 }
0212
0213 static int ad5758_spi_reg_write(struct ad5758_state *st,
0214 unsigned int addr,
0215 unsigned int val)
0216 {
0217 st->d32[0] = cpu_to_be32((AD5758_WR_FLAG_MSK(addr) << 24) |
0218 ((val & 0xFFFF) << 8));
0219
0220 return spi_write(st->spi, &st->d32[0], sizeof(st->d32[0]));
0221 }
0222
0223 static int ad5758_spi_write_mask(struct ad5758_state *st,
0224 unsigned int addr,
0225 unsigned long int mask,
0226 unsigned int val)
0227 {
0228 int regval;
0229
0230 regval = ad5758_spi_reg_read(st, addr);
0231 if (regval < 0)
0232 return regval;
0233
0234 regval &= ~mask;
0235 regval |= val;
0236
0237 return ad5758_spi_reg_write(st, addr, regval);
0238 }
0239
0240 static int cmpfunc(const void *a, const void *b)
0241 {
0242 return *(int *)a - *(int *)b;
0243 }
0244
0245 static int ad5758_find_closest_match(const int *array,
0246 unsigned int size, int val)
0247 {
0248 int i;
0249
0250 for (i = 0; i < size; i++) {
0251 if (val <= array[i])
0252 return i;
0253 }
0254
0255 return size - 1;
0256 }
0257
0258 static int ad5758_wait_for_task_complete(struct ad5758_state *st,
0259 unsigned int reg,
0260 unsigned int mask)
0261 {
0262 unsigned int timeout;
0263 int ret;
0264
0265 timeout = 10;
0266 do {
0267 ret = ad5758_spi_reg_read(st, reg);
0268 if (ret < 0)
0269 return ret;
0270
0271 if (!(ret & mask))
0272 return 0;
0273
0274 usleep_range(100, 1000);
0275 } while (--timeout);
0276
0277 dev_err(&st->spi->dev,
0278 "Error reading bit 0x%x in 0x%x register\n", mask, reg);
0279
0280 return -EIO;
0281 }
0282
0283 static int ad5758_calib_mem_refresh(struct ad5758_state *st)
0284 {
0285 int ret;
0286
0287 ret = ad5758_spi_reg_write(st, AD5758_KEY,
0288 AD5758_KEY_CODE_CALIB_MEM_REFRESH);
0289 if (ret < 0) {
0290 dev_err(&st->spi->dev,
0291 "Failed to initiate a calibration memory refresh\n");
0292 return ret;
0293 }
0294
0295
0296 return ad5758_wait_for_task_complete(st, AD5758_DIGITAL_DIAG_RESULTS,
0297 AD5758_CAL_MEM_UNREFRESHED_MSK);
0298 }
0299
0300 static int ad5758_soft_reset(struct ad5758_state *st)
0301 {
0302 int ret;
0303
0304 ret = ad5758_spi_reg_write(st, AD5758_KEY, AD5758_KEY_CODE_RESET_1);
0305 if (ret < 0)
0306 return ret;
0307
0308 ret = ad5758_spi_reg_write(st, AD5758_KEY, AD5758_KEY_CODE_RESET_2);
0309
0310
0311 usleep_range(100, 1000);
0312
0313 return ret;
0314 }
0315
0316 static int ad5758_set_dc_dc_conv_mode(struct ad5758_state *st,
0317 enum ad5758_dc_dc_mode mode)
0318 {
0319 int ret;
0320
0321
0322
0323
0324
0325 if (mode == AD5758_DCDC_MODE_PPC_CURRENT) {
0326 ret = ad5758_spi_write_mask(st, AD5758_ADC_CONFIG,
0327 AD5758_ADC_CONFIG_PPC_BUF_MSK,
0328 AD5758_ADC_CONFIG_PPC_BUF_EN(1));
0329 if (ret < 0)
0330 return ret;
0331 }
0332
0333 ret = ad5758_spi_write_mask(st, AD5758_DCDC_CONFIG1,
0334 AD5758_DCDC_CONFIG1_DCDC_MODE_MSK,
0335 AD5758_DCDC_CONFIG1_DCDC_MODE_MODE(mode));
0336 if (ret < 0)
0337 return ret;
0338
0339
0340
0341
0342
0343 ret = ad5758_wait_for_task_complete(st, AD5758_DCDC_CONFIG2,
0344 AD5758_DCDC_CONFIG2_BUSY_3WI_MSK);
0345 if (ret < 0)
0346 return ret;
0347
0348 st->dc_dc_mode = mode;
0349
0350 return ret;
0351 }
0352
0353 static int ad5758_set_dc_dc_ilim(struct ad5758_state *st, unsigned int ilim)
0354 {
0355 int ret;
0356
0357 ret = ad5758_spi_write_mask(st, AD5758_DCDC_CONFIG2,
0358 AD5758_DCDC_CONFIG2_ILIMIT_MSK,
0359 AD5758_DCDC_CONFIG2_ILIMIT_MODE(ilim));
0360 if (ret < 0)
0361 return ret;
0362
0363
0364
0365
0366 return ad5758_wait_for_task_complete(st, AD5758_DCDC_CONFIG2,
0367 AD5758_DCDC_CONFIG2_BUSY_3WI_MSK);
0368 }
0369
0370 static int ad5758_slew_rate_set(struct ad5758_state *st,
0371 unsigned int sr_clk_idx,
0372 unsigned int sr_step_idx)
0373 {
0374 unsigned int mode;
0375 unsigned long int mask;
0376 int ret;
0377
0378 mask = AD5758_DAC_CONFIG_SR_EN_MSK |
0379 AD5758_DAC_CONFIG_SR_CLOCK_MSK |
0380 AD5758_DAC_CONFIG_SR_STEP_MSK;
0381 mode = AD5758_DAC_CONFIG_SR_EN_MODE(1) |
0382 AD5758_DAC_CONFIG_SR_STEP_MODE(sr_step_idx) |
0383 AD5758_DAC_CONFIG_SR_CLOCK_MODE(sr_clk_idx);
0384
0385 ret = ad5758_spi_write_mask(st, AD5758_DAC_CONFIG, mask, mode);
0386 if (ret < 0)
0387 return ret;
0388
0389
0390 return ad5758_wait_for_task_complete(st, AD5758_DIGITAL_DIAG_RESULTS,
0391 AD5758_CAL_MEM_UNREFRESHED_MSK);
0392 }
0393
0394 static int ad5758_slew_rate_config(struct ad5758_state *st)
0395 {
0396 unsigned int sr_clk_idx, sr_step_idx;
0397 int i, res;
0398 s64 diff_new, diff_old;
0399 u64 sr_step, calc_slew_time;
0400
0401 sr_clk_idx = 0;
0402 sr_step_idx = 0;
0403 diff_old = S64_MAX;
0404
0405
0406
0407
0408
0409
0410
0411 for (i = 0; i < ARRAY_SIZE(ad5758_sr_clk); i++) {
0412
0413
0414
0415
0416
0417 sr_step = AD5758_FULL_SCALE_MICRO;
0418 do_div(sr_step, ad5758_sr_clk[i]);
0419 do_div(sr_step, st->slew_time);
0420
0421
0422
0423
0424 res = ad5758_find_closest_match(ad5758_sr_step,
0425 ARRAY_SIZE(ad5758_sr_step),
0426 sr_step);
0427
0428 calc_slew_time = AD5758_FULL_SCALE_MICRO;
0429 do_div(calc_slew_time, ad5758_sr_step[res]);
0430 do_div(calc_slew_time, ad5758_sr_clk[i]);
0431
0432
0433
0434
0435
0436 diff_new = abs(st->slew_time - calc_slew_time);
0437 if (diff_new < diff_old) {
0438 diff_old = diff_new;
0439 sr_clk_idx = i;
0440 sr_step_idx = res;
0441 }
0442 }
0443
0444 return ad5758_slew_rate_set(st, sr_clk_idx, sr_step_idx);
0445 }
0446
0447 static int ad5758_set_out_range(struct ad5758_state *st, int range)
0448 {
0449 int ret;
0450
0451 ret = ad5758_spi_write_mask(st, AD5758_DAC_CONFIG,
0452 AD5758_DAC_CONFIG_RANGE_MSK,
0453 AD5758_DAC_CONFIG_RANGE_MODE(range));
0454 if (ret < 0)
0455 return ret;
0456
0457
0458 return ad5758_wait_for_task_complete(st, AD5758_DIGITAL_DIAG_RESULTS,
0459 AD5758_CAL_MEM_UNREFRESHED_MSK);
0460 }
0461
0462 static int ad5758_internal_buffers_en(struct ad5758_state *st, bool enable)
0463 {
0464 int ret;
0465
0466 ret = ad5758_spi_write_mask(st, AD5758_DAC_CONFIG,
0467 AD5758_DAC_CONFIG_INT_EN_MSK,
0468 AD5758_DAC_CONFIG_INT_EN_MODE(enable));
0469 if (ret < 0)
0470 return ret;
0471
0472
0473 return ad5758_wait_for_task_complete(st, AD5758_DIGITAL_DIAG_RESULTS,
0474 AD5758_CAL_MEM_UNREFRESHED_MSK);
0475 }
0476
0477 static int ad5758_reset(struct ad5758_state *st)
0478 {
0479 if (st->gpio_reset) {
0480 gpiod_set_value(st->gpio_reset, 0);
0481 usleep_range(100, 1000);
0482 gpiod_set_value(st->gpio_reset, 1);
0483 usleep_range(100, 1000);
0484
0485 return 0;
0486 } else {
0487
0488 return ad5758_soft_reset(st);
0489 }
0490 }
0491
0492 static int ad5758_reg_access(struct iio_dev *indio_dev,
0493 unsigned int reg,
0494 unsigned int writeval,
0495 unsigned int *readval)
0496 {
0497 struct ad5758_state *st = iio_priv(indio_dev);
0498 int ret;
0499
0500 mutex_lock(&st->lock);
0501 if (readval) {
0502 ret = ad5758_spi_reg_read(st, reg);
0503 if (ret < 0) {
0504 mutex_unlock(&st->lock);
0505 return ret;
0506 }
0507
0508 *readval = ret;
0509 ret = 0;
0510 } else {
0511 ret = ad5758_spi_reg_write(st, reg, writeval);
0512 }
0513 mutex_unlock(&st->lock);
0514
0515 return ret;
0516 }
0517
0518 static int ad5758_read_raw(struct iio_dev *indio_dev,
0519 struct iio_chan_spec const *chan,
0520 int *val, int *val2, long info)
0521 {
0522 struct ad5758_state *st = iio_priv(indio_dev);
0523 int max, min, ret;
0524
0525 switch (info) {
0526 case IIO_CHAN_INFO_RAW:
0527 mutex_lock(&st->lock);
0528 ret = ad5758_spi_reg_read(st, AD5758_DAC_INPUT);
0529 mutex_unlock(&st->lock);
0530 if (ret < 0)
0531 return ret;
0532
0533 *val = ret;
0534 return IIO_VAL_INT;
0535 case IIO_CHAN_INFO_SCALE:
0536 min = st->out_range.min;
0537 max = st->out_range.max;
0538 *val = (max - min) / 1000;
0539 *val2 = 16;
0540 return IIO_VAL_FRACTIONAL_LOG2;
0541 case IIO_CHAN_INFO_OFFSET:
0542 min = st->out_range.min;
0543 max = st->out_range.max;
0544 *val = ((min * (1 << 16)) / (max - min)) / 1000;
0545 return IIO_VAL_INT;
0546 default:
0547 return -EINVAL;
0548 }
0549 }
0550
0551 static int ad5758_write_raw(struct iio_dev *indio_dev,
0552 struct iio_chan_spec const *chan,
0553 int val, int val2, long info)
0554 {
0555 struct ad5758_state *st = iio_priv(indio_dev);
0556 int ret;
0557
0558 switch (info) {
0559 case IIO_CHAN_INFO_RAW:
0560 mutex_lock(&st->lock);
0561 ret = ad5758_spi_reg_write(st, AD5758_DAC_INPUT, val);
0562 mutex_unlock(&st->lock);
0563 return ret;
0564 default:
0565 return -EINVAL;
0566 }
0567 }
0568
0569 static ssize_t ad5758_read_powerdown(struct iio_dev *indio_dev,
0570 uintptr_t priv,
0571 const struct iio_chan_spec *chan,
0572 char *buf)
0573 {
0574 struct ad5758_state *st = iio_priv(indio_dev);
0575
0576 return sysfs_emit(buf, "%d\n", st->pwr_down);
0577 }
0578
0579 static ssize_t ad5758_write_powerdown(struct iio_dev *indio_dev,
0580 uintptr_t priv,
0581 struct iio_chan_spec const *chan,
0582 const char *buf, size_t len)
0583 {
0584 struct ad5758_state *st = iio_priv(indio_dev);
0585 bool pwr_down;
0586 unsigned int dac_config_mode, val;
0587 unsigned long int dac_config_msk;
0588 int ret;
0589
0590 ret = kstrtobool(buf, &pwr_down);
0591 if (ret)
0592 return ret;
0593
0594 mutex_lock(&st->lock);
0595 if (pwr_down)
0596 val = 0;
0597 else
0598 val = 1;
0599
0600 dac_config_mode = AD5758_DAC_CONFIG_OUT_EN_MODE(val) |
0601 AD5758_DAC_CONFIG_INT_EN_MODE(val);
0602 dac_config_msk = AD5758_DAC_CONFIG_OUT_EN_MSK |
0603 AD5758_DAC_CONFIG_INT_EN_MSK;
0604
0605 ret = ad5758_spi_write_mask(st, AD5758_DAC_CONFIG,
0606 dac_config_msk,
0607 dac_config_mode);
0608 if (ret < 0)
0609 goto err_unlock;
0610
0611 st->pwr_down = pwr_down;
0612
0613 err_unlock:
0614 mutex_unlock(&st->lock);
0615
0616 return ret ? ret : len;
0617 }
0618
0619 static const struct iio_info ad5758_info = {
0620 .read_raw = ad5758_read_raw,
0621 .write_raw = ad5758_write_raw,
0622 .debugfs_reg_access = &ad5758_reg_access,
0623 };
0624
0625 static const struct iio_chan_spec_ext_info ad5758_ext_info[] = {
0626 {
0627 .name = "powerdown",
0628 .read = ad5758_read_powerdown,
0629 .write = ad5758_write_powerdown,
0630 .shared = IIO_SHARED_BY_TYPE,
0631 },
0632 { }
0633 };
0634
0635 #define AD5758_DAC_CHAN(_chan_type) { \
0636 .type = (_chan_type), \
0637 .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_RAW) | \
0638 BIT(IIO_CHAN_INFO_SCALE) | \
0639 BIT(IIO_CHAN_INFO_OFFSET), \
0640 .indexed = 1, \
0641 .output = 1, \
0642 .ext_info = ad5758_ext_info, \
0643 }
0644
0645 static const struct iio_chan_spec ad5758_voltage_ch[] = {
0646 AD5758_DAC_CHAN(IIO_VOLTAGE)
0647 };
0648
0649 static const struct iio_chan_spec ad5758_current_ch[] = {
0650 AD5758_DAC_CHAN(IIO_CURRENT)
0651 };
0652
0653 static bool ad5758_is_valid_mode(enum ad5758_dc_dc_mode mode)
0654 {
0655 switch (mode) {
0656 case AD5758_DCDC_MODE_DPC_CURRENT:
0657 case AD5758_DCDC_MODE_DPC_VOLTAGE:
0658 case AD5758_DCDC_MODE_PPC_CURRENT:
0659 return true;
0660 default:
0661 return false;
0662 }
0663 }
0664
0665 static int ad5758_crc_disable(struct ad5758_state *st)
0666 {
0667 unsigned int mask;
0668
0669 mask = (AD5758_WR_FLAG_MSK(AD5758_DIGITAL_DIAG_CONFIG) << 24) | 0x5C3A;
0670 st->d32[0] = cpu_to_be32(mask);
0671
0672 return spi_write(st->spi, &st->d32[0], 4);
0673 }
0674
0675 static int ad5758_find_out_range(struct ad5758_state *st,
0676 const struct ad5758_range *range,
0677 unsigned int size,
0678 int min, int max)
0679 {
0680 int i;
0681
0682 for (i = 0; i < size; i++) {
0683 if ((min == range[i].min) && (max == range[i].max)) {
0684 st->out_range.reg = range[i].reg;
0685 st->out_range.min = range[i].min;
0686 st->out_range.max = range[i].max;
0687
0688 return 0;
0689 }
0690 }
0691
0692 return -EINVAL;
0693 }
0694
0695 static int ad5758_parse_dt(struct ad5758_state *st)
0696 {
0697 unsigned int tmp, tmparray[2], size;
0698 const struct ad5758_range *range;
0699 int *index, ret;
0700
0701 st->dc_dc_ilim = 0;
0702 ret = device_property_read_u32(&st->spi->dev,
0703 "adi,dc-dc-ilim-microamp", &tmp);
0704 if (ret) {
0705 dev_dbg(&st->spi->dev,
0706 "Missing \"dc-dc-ilim-microamp\" property\n");
0707 } else {
0708 index = bsearch(&tmp, ad5758_dc_dc_ilim,
0709 ARRAY_SIZE(ad5758_dc_dc_ilim),
0710 sizeof(int), cmpfunc);
0711 if (!index)
0712 dev_dbg(&st->spi->dev, "dc-dc-ilim out of range\n");
0713 else
0714 st->dc_dc_ilim = index - ad5758_dc_dc_ilim;
0715 }
0716
0717 ret = device_property_read_u32(&st->spi->dev, "adi,dc-dc-mode",
0718 &st->dc_dc_mode);
0719 if (ret) {
0720 dev_err(&st->spi->dev, "Missing \"dc-dc-mode\" property\n");
0721 return ret;
0722 }
0723
0724 if (!ad5758_is_valid_mode(st->dc_dc_mode))
0725 return -EINVAL;
0726
0727 if (st->dc_dc_mode == AD5758_DCDC_MODE_DPC_VOLTAGE) {
0728 ret = device_property_read_u32_array(&st->spi->dev,
0729 "adi,range-microvolt",
0730 tmparray, 2);
0731 if (ret) {
0732 dev_err(&st->spi->dev,
0733 "Missing \"range-microvolt\" property\n");
0734 return ret;
0735 }
0736 range = ad5758_voltage_range;
0737 size = ARRAY_SIZE(ad5758_voltage_range);
0738 } else {
0739 ret = device_property_read_u32_array(&st->spi->dev,
0740 "adi,range-microamp",
0741 tmparray, 2);
0742 if (ret) {
0743 dev_err(&st->spi->dev,
0744 "Missing \"range-microamp\" property\n");
0745 return ret;
0746 }
0747 range = ad5758_current_range;
0748 size = ARRAY_SIZE(ad5758_current_range);
0749 }
0750
0751 ret = ad5758_find_out_range(st, range, size, tmparray[0], tmparray[1]);
0752 if (ret) {
0753 dev_err(&st->spi->dev, "range invalid\n");
0754 return ret;
0755 }
0756
0757 ret = device_property_read_u32(&st->spi->dev, "adi,slew-time-us", &tmp);
0758 if (ret) {
0759 dev_dbg(&st->spi->dev, "Missing \"slew-time-us\" property\n");
0760 st->slew_time = 0;
0761 } else {
0762 st->slew_time = tmp;
0763 }
0764
0765 return 0;
0766 }
0767
0768 static int ad5758_init(struct ad5758_state *st)
0769 {
0770 int regval, ret;
0771
0772 st->gpio_reset = devm_gpiod_get_optional(&st->spi->dev, "reset",
0773 GPIOD_OUT_HIGH);
0774 if (IS_ERR(st->gpio_reset))
0775 return PTR_ERR(st->gpio_reset);
0776
0777
0778 ret = ad5758_crc_disable(st);
0779 if (ret < 0)
0780 return ret;
0781
0782
0783 ret = ad5758_reset(st);
0784 if (ret < 0)
0785 return ret;
0786
0787
0788 ret = ad5758_crc_disable(st);
0789 if (ret < 0)
0790 return ret;
0791
0792
0793 ret = ad5758_calib_mem_refresh(st);
0794 if (ret < 0)
0795 return ret;
0796
0797 regval = ad5758_spi_reg_read(st, AD5758_DIGITAL_DIAG_RESULTS);
0798 if (regval < 0)
0799 return regval;
0800
0801
0802 ret = ad5758_spi_reg_write(st, AD5758_DIGITAL_DIAG_RESULTS, regval);
0803 if (ret < 0)
0804 return ret;
0805
0806
0807 ret = ad5758_set_dc_dc_ilim(st, st->dc_dc_ilim);
0808 if (ret < 0)
0809 return ret;
0810
0811
0812 ret = ad5758_set_dc_dc_conv_mode(st, st->dc_dc_mode);
0813 if (ret < 0)
0814 return ret;
0815
0816
0817 ret = ad5758_set_out_range(st, st->out_range.reg);
0818 if (ret < 0)
0819 return ret;
0820
0821
0822 if (st->slew_time) {
0823 ret = ad5758_slew_rate_config(st);
0824 if (ret < 0)
0825 return ret;
0826 }
0827
0828
0829 ret = ad5758_internal_buffers_en(st, 1);
0830 if (ret < 0)
0831 return ret;
0832
0833
0834 return ad5758_spi_write_mask(st, AD5758_DAC_CONFIG,
0835 AD5758_DAC_CONFIG_OUT_EN_MSK,
0836 AD5758_DAC_CONFIG_OUT_EN_MODE(1));
0837 }
0838
0839 static int ad5758_probe(struct spi_device *spi)
0840 {
0841 struct ad5758_state *st;
0842 struct iio_dev *indio_dev;
0843 int ret;
0844
0845 indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*st));
0846 if (!indio_dev)
0847 return -ENOMEM;
0848
0849 st = iio_priv(indio_dev);
0850 spi_set_drvdata(spi, indio_dev);
0851
0852 st->spi = spi;
0853
0854 mutex_init(&st->lock);
0855
0856 indio_dev->name = spi_get_device_id(spi)->name;
0857 indio_dev->info = &ad5758_info;
0858 indio_dev->modes = INDIO_DIRECT_MODE;
0859 indio_dev->num_channels = 1;
0860
0861 ret = ad5758_parse_dt(st);
0862 if (ret < 0)
0863 return ret;
0864
0865 if (st->dc_dc_mode == AD5758_DCDC_MODE_DPC_VOLTAGE)
0866 indio_dev->channels = ad5758_voltage_ch;
0867 else
0868 indio_dev->channels = ad5758_current_ch;
0869
0870 ret = ad5758_init(st);
0871 if (ret < 0) {
0872 dev_err(&spi->dev, "AD5758 init failed\n");
0873 return ret;
0874 }
0875
0876 return devm_iio_device_register(&st->spi->dev, indio_dev);
0877 }
0878
0879 static const struct spi_device_id ad5758_id[] = {
0880 { "ad5758", 0 },
0881 {}
0882 };
0883 MODULE_DEVICE_TABLE(spi, ad5758_id);
0884
0885 static const struct of_device_id ad5758_of_match[] = {
0886 { .compatible = "adi,ad5758" },
0887 { },
0888 };
0889 MODULE_DEVICE_TABLE(of, ad5758_of_match);
0890
0891 static struct spi_driver ad5758_driver = {
0892 .driver = {
0893 .name = KBUILD_MODNAME,
0894 .of_match_table = ad5758_of_match,
0895 },
0896 .probe = ad5758_probe,
0897 .id_table = ad5758_id,
0898 };
0899
0900 module_spi_driver(ad5758_driver);
0901
0902 MODULE_AUTHOR("Stefan Popa <stefan.popa@analog.com>");
0903 MODULE_DESCRIPTION("Analog Devices AD5758 DAC");
0904 MODULE_LICENSE("GPL v2");