0001
0002
0003
0004
0005
0006
0007
0008 #include <linux/completion.h>
0009 #include <linux/interrupt.h>
0010 #include <linux/io.h>
0011 #include <linux/module.h>
0012 #include <linux/mod_devicetable.h>
0013 #include <linux/platform_device.h>
0014 #include <linux/pm_runtime.h>
0015 #include <linux/property.h>
0016 #include <linux/regmap.h>
0017 #include <linux/thermal.h>
0018
0019 #include <linux/iio/iio.h>
0020 #include <linux/iio/driver.h>
0021 #include <linux/iio/machine.h>
0022 #include <linux/mfd/axp20x.h>
0023
0024 #define AXP20X_ADC_EN1_MASK GENMASK(7, 0)
0025
0026 #define AXP20X_ADC_EN2_MASK (GENMASK(3, 2) | BIT(7))
0027 #define AXP22X_ADC_EN1_MASK (GENMASK(7, 5) | BIT(0))
0028
0029 #define AXP20X_GPIO10_IN_RANGE_GPIO0 BIT(0)
0030 #define AXP20X_GPIO10_IN_RANGE_GPIO1 BIT(1)
0031 #define AXP20X_GPIO10_IN_RANGE_GPIO0_VAL(x) ((x) & BIT(0))
0032 #define AXP20X_GPIO10_IN_RANGE_GPIO1_VAL(x) (((x) & BIT(0)) << 1)
0033
0034 #define AXP20X_ADC_RATE_MASK GENMASK(7, 6)
0035 #define AXP813_V_I_ADC_RATE_MASK GENMASK(5, 4)
0036 #define AXP813_ADC_RATE_MASK (AXP20X_ADC_RATE_MASK | AXP813_V_I_ADC_RATE_MASK)
0037 #define AXP20X_ADC_RATE_HZ(x) ((ilog2((x) / 25) << 6) & AXP20X_ADC_RATE_MASK)
0038 #define AXP22X_ADC_RATE_HZ(x) ((ilog2((x) / 100) << 6) & AXP20X_ADC_RATE_MASK)
0039 #define AXP813_TS_GPIO0_ADC_RATE_HZ(x) AXP20X_ADC_RATE_HZ(x)
0040 #define AXP813_V_I_ADC_RATE_HZ(x) ((ilog2((x) / 100) << 4) & AXP813_V_I_ADC_RATE_MASK)
0041 #define AXP813_ADC_RATE_HZ(x) (AXP20X_ADC_RATE_HZ(x) | AXP813_V_I_ADC_RATE_HZ(x))
0042
0043 #define AXP20X_ADC_CHANNEL(_channel, _name, _type, _reg) \
0044 { \
0045 .type = _type, \
0046 .indexed = 1, \
0047 .channel = _channel, \
0048 .address = _reg, \
0049 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | \
0050 BIT(IIO_CHAN_INFO_SCALE), \
0051 .datasheet_name = _name, \
0052 }
0053
0054 #define AXP20X_ADC_CHANNEL_OFFSET(_channel, _name, _type, _reg) \
0055 { \
0056 .type = _type, \
0057 .indexed = 1, \
0058 .channel = _channel, \
0059 .address = _reg, \
0060 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | \
0061 BIT(IIO_CHAN_INFO_SCALE) |\
0062 BIT(IIO_CHAN_INFO_OFFSET),\
0063 .datasheet_name = _name, \
0064 }
0065
0066 struct axp_data;
0067
0068 struct axp20x_adc_iio {
0069 struct regmap *regmap;
0070 const struct axp_data *data;
0071 };
0072
0073 enum axp20x_adc_channel_v {
0074 AXP20X_ACIN_V = 0,
0075 AXP20X_VBUS_V,
0076 AXP20X_TS_IN,
0077 AXP20X_GPIO0_V,
0078 AXP20X_GPIO1_V,
0079 AXP20X_IPSOUT_V,
0080 AXP20X_BATT_V,
0081 };
0082
0083 enum axp20x_adc_channel_i {
0084 AXP20X_ACIN_I = 0,
0085 AXP20X_VBUS_I,
0086 AXP20X_BATT_CHRG_I,
0087 AXP20X_BATT_DISCHRG_I,
0088 };
0089
0090 enum axp22x_adc_channel_v {
0091 AXP22X_TS_IN = 0,
0092 AXP22X_BATT_V,
0093 };
0094
0095 enum axp22x_adc_channel_i {
0096 AXP22X_BATT_CHRG_I = 1,
0097 AXP22X_BATT_DISCHRG_I,
0098 };
0099
0100 enum axp813_adc_channel_v {
0101 AXP813_TS_IN = 0,
0102 AXP813_GPIO0_V,
0103 AXP813_BATT_V,
0104 };
0105
0106 static struct iio_map axp20x_maps[] = {
0107 {
0108 .consumer_dev_name = "axp20x-usb-power-supply",
0109 .consumer_channel = "vbus_v",
0110 .adc_channel_label = "vbus_v",
0111 }, {
0112 .consumer_dev_name = "axp20x-usb-power-supply",
0113 .consumer_channel = "vbus_i",
0114 .adc_channel_label = "vbus_i",
0115 }, {
0116 .consumer_dev_name = "axp20x-ac-power-supply",
0117 .consumer_channel = "acin_v",
0118 .adc_channel_label = "acin_v",
0119 }, {
0120 .consumer_dev_name = "axp20x-ac-power-supply",
0121 .consumer_channel = "acin_i",
0122 .adc_channel_label = "acin_i",
0123 }, {
0124 .consumer_dev_name = "axp20x-battery-power-supply",
0125 .consumer_channel = "batt_v",
0126 .adc_channel_label = "batt_v",
0127 }, {
0128 .consumer_dev_name = "axp20x-battery-power-supply",
0129 .consumer_channel = "batt_chrg_i",
0130 .adc_channel_label = "batt_chrg_i",
0131 }, {
0132 .consumer_dev_name = "axp20x-battery-power-supply",
0133 .consumer_channel = "batt_dischrg_i",
0134 .adc_channel_label = "batt_dischrg_i",
0135 }, { }
0136 };
0137
0138 static struct iio_map axp22x_maps[] = {
0139 {
0140 .consumer_dev_name = "axp20x-battery-power-supply",
0141 .consumer_channel = "batt_v",
0142 .adc_channel_label = "batt_v",
0143 }, {
0144 .consumer_dev_name = "axp20x-battery-power-supply",
0145 .consumer_channel = "batt_chrg_i",
0146 .adc_channel_label = "batt_chrg_i",
0147 }, {
0148 .consumer_dev_name = "axp20x-battery-power-supply",
0149 .consumer_channel = "batt_dischrg_i",
0150 .adc_channel_label = "batt_dischrg_i",
0151 }, { }
0152 };
0153
0154
0155
0156
0157
0158
0159
0160 static const struct iio_chan_spec axp20x_adc_channels[] = {
0161 AXP20X_ADC_CHANNEL(AXP20X_ACIN_V, "acin_v", IIO_VOLTAGE,
0162 AXP20X_ACIN_V_ADC_H),
0163 AXP20X_ADC_CHANNEL(AXP20X_ACIN_I, "acin_i", IIO_CURRENT,
0164 AXP20X_ACIN_I_ADC_H),
0165 AXP20X_ADC_CHANNEL(AXP20X_VBUS_V, "vbus_v", IIO_VOLTAGE,
0166 AXP20X_VBUS_V_ADC_H),
0167 AXP20X_ADC_CHANNEL(AXP20X_VBUS_I, "vbus_i", IIO_CURRENT,
0168 AXP20X_VBUS_I_ADC_H),
0169 {
0170 .type = IIO_TEMP,
0171 .address = AXP20X_TEMP_ADC_H,
0172 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
0173 BIT(IIO_CHAN_INFO_SCALE) |
0174 BIT(IIO_CHAN_INFO_OFFSET),
0175 .datasheet_name = "pmic_temp",
0176 },
0177 AXP20X_ADC_CHANNEL_OFFSET(AXP20X_GPIO0_V, "gpio0_v", IIO_VOLTAGE,
0178 AXP20X_GPIO0_V_ADC_H),
0179 AXP20X_ADC_CHANNEL_OFFSET(AXP20X_GPIO1_V, "gpio1_v", IIO_VOLTAGE,
0180 AXP20X_GPIO1_V_ADC_H),
0181 AXP20X_ADC_CHANNEL(AXP20X_IPSOUT_V, "ipsout_v", IIO_VOLTAGE,
0182 AXP20X_IPSOUT_V_HIGH_H),
0183 AXP20X_ADC_CHANNEL(AXP20X_BATT_V, "batt_v", IIO_VOLTAGE,
0184 AXP20X_BATT_V_H),
0185 AXP20X_ADC_CHANNEL(AXP20X_BATT_CHRG_I, "batt_chrg_i", IIO_CURRENT,
0186 AXP20X_BATT_CHRG_I_H),
0187 AXP20X_ADC_CHANNEL(AXP20X_BATT_DISCHRG_I, "batt_dischrg_i", IIO_CURRENT,
0188 AXP20X_BATT_DISCHRG_I_H),
0189 AXP20X_ADC_CHANNEL(AXP20X_TS_IN, "ts_v", IIO_VOLTAGE,
0190 AXP20X_TS_IN_H),
0191 };
0192
0193 static const struct iio_chan_spec axp22x_adc_channels[] = {
0194 {
0195 .type = IIO_TEMP,
0196 .address = AXP22X_PMIC_TEMP_H,
0197 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
0198 BIT(IIO_CHAN_INFO_SCALE) |
0199 BIT(IIO_CHAN_INFO_OFFSET),
0200 .datasheet_name = "pmic_temp",
0201 },
0202 AXP20X_ADC_CHANNEL(AXP22X_BATT_V, "batt_v", IIO_VOLTAGE,
0203 AXP20X_BATT_V_H),
0204 AXP20X_ADC_CHANNEL(AXP22X_BATT_CHRG_I, "batt_chrg_i", IIO_CURRENT,
0205 AXP20X_BATT_CHRG_I_H),
0206 AXP20X_ADC_CHANNEL(AXP22X_BATT_DISCHRG_I, "batt_dischrg_i", IIO_CURRENT,
0207 AXP20X_BATT_DISCHRG_I_H),
0208 AXP20X_ADC_CHANNEL(AXP22X_TS_IN, "ts_v", IIO_VOLTAGE,
0209 AXP22X_TS_ADC_H),
0210 };
0211
0212 static const struct iio_chan_spec axp813_adc_channels[] = {
0213 {
0214 .type = IIO_TEMP,
0215 .address = AXP22X_PMIC_TEMP_H,
0216 .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
0217 BIT(IIO_CHAN_INFO_SCALE) |
0218 BIT(IIO_CHAN_INFO_OFFSET),
0219 .datasheet_name = "pmic_temp",
0220 },
0221 AXP20X_ADC_CHANNEL(AXP813_GPIO0_V, "gpio0_v", IIO_VOLTAGE,
0222 AXP288_GP_ADC_H),
0223 AXP20X_ADC_CHANNEL(AXP813_BATT_V, "batt_v", IIO_VOLTAGE,
0224 AXP20X_BATT_V_H),
0225 AXP20X_ADC_CHANNEL(AXP22X_BATT_CHRG_I, "batt_chrg_i", IIO_CURRENT,
0226 AXP20X_BATT_CHRG_I_H),
0227 AXP20X_ADC_CHANNEL(AXP22X_BATT_DISCHRG_I, "batt_dischrg_i", IIO_CURRENT,
0228 AXP20X_BATT_DISCHRG_I_H),
0229 AXP20X_ADC_CHANNEL(AXP813_TS_IN, "ts_v", IIO_VOLTAGE,
0230 AXP288_TS_ADC_H),
0231 };
0232
0233 static int axp20x_adc_raw(struct iio_dev *indio_dev,
0234 struct iio_chan_spec const *chan, int *val)
0235 {
0236 struct axp20x_adc_iio *info = iio_priv(indio_dev);
0237 int size = 12;
0238
0239
0240
0241
0242
0243
0244 if (chan->type == IIO_CURRENT && chan->channel == AXP20X_BATT_DISCHRG_I)
0245 size = 13;
0246 else
0247 size = 12;
0248
0249 *val = axp20x_read_variable_width(info->regmap, chan->address, size);
0250 if (*val < 0)
0251 return *val;
0252
0253 return IIO_VAL_INT;
0254 }
0255
0256 static int axp22x_adc_raw(struct iio_dev *indio_dev,
0257 struct iio_chan_spec const *chan, int *val)
0258 {
0259 struct axp20x_adc_iio *info = iio_priv(indio_dev);
0260
0261 *val = axp20x_read_variable_width(info->regmap, chan->address, 12);
0262 if (*val < 0)
0263 return *val;
0264
0265 return IIO_VAL_INT;
0266 }
0267
0268 static int axp813_adc_raw(struct iio_dev *indio_dev,
0269 struct iio_chan_spec const *chan, int *val)
0270 {
0271 struct axp20x_adc_iio *info = iio_priv(indio_dev);
0272
0273 *val = axp20x_read_variable_width(info->regmap, chan->address, 12);
0274 if (*val < 0)
0275 return *val;
0276
0277 return IIO_VAL_INT;
0278 }
0279
0280 static int axp20x_adc_scale_voltage(int channel, int *val, int *val2)
0281 {
0282 switch (channel) {
0283 case AXP20X_ACIN_V:
0284 case AXP20X_VBUS_V:
0285 *val = 1;
0286 *val2 = 700000;
0287 return IIO_VAL_INT_PLUS_MICRO;
0288
0289 case AXP20X_GPIO0_V:
0290 case AXP20X_GPIO1_V:
0291 *val = 0;
0292 *val2 = 500000;
0293 return IIO_VAL_INT_PLUS_MICRO;
0294
0295 case AXP20X_BATT_V:
0296 *val = 1;
0297 *val2 = 100000;
0298 return IIO_VAL_INT_PLUS_MICRO;
0299
0300 case AXP20X_IPSOUT_V:
0301 *val = 1;
0302 *val2 = 400000;
0303 return IIO_VAL_INT_PLUS_MICRO;
0304
0305 case AXP20X_TS_IN:
0306
0307 *val = 0;
0308 *val2 = 800000;
0309 return IIO_VAL_INT_PLUS_MICRO;
0310
0311 default:
0312 return -EINVAL;
0313 }
0314 }
0315
0316 static int axp22x_adc_scale_voltage(int channel, int *val, int *val2)
0317 {
0318 switch (channel) {
0319 case AXP22X_BATT_V:
0320
0321 *val = 1;
0322 *val2 = 100000;
0323 return IIO_VAL_INT_PLUS_MICRO;
0324
0325 case AXP22X_TS_IN:
0326
0327 *val = 0;
0328 *val2 = 800000;
0329 return IIO_VAL_INT_PLUS_MICRO;
0330
0331 default:
0332 return -EINVAL;
0333 }
0334 }
0335 static int axp813_adc_scale_voltage(int channel, int *val, int *val2)
0336 {
0337 switch (channel) {
0338 case AXP813_GPIO0_V:
0339 *val = 0;
0340 *val2 = 800000;
0341 return IIO_VAL_INT_PLUS_MICRO;
0342
0343 case AXP813_BATT_V:
0344 *val = 1;
0345 *val2 = 100000;
0346 return IIO_VAL_INT_PLUS_MICRO;
0347
0348 case AXP813_TS_IN:
0349
0350 *val = 0;
0351 *val2 = 800000;
0352 return IIO_VAL_INT_PLUS_MICRO;
0353
0354 default:
0355 return -EINVAL;
0356 }
0357 }
0358
0359 static int axp20x_adc_scale_current(int channel, int *val, int *val2)
0360 {
0361 switch (channel) {
0362 case AXP20X_ACIN_I:
0363 *val = 0;
0364 *val2 = 625000;
0365 return IIO_VAL_INT_PLUS_MICRO;
0366
0367 case AXP20X_VBUS_I:
0368 *val = 0;
0369 *val2 = 375000;
0370 return IIO_VAL_INT_PLUS_MICRO;
0371
0372 case AXP20X_BATT_DISCHRG_I:
0373 case AXP20X_BATT_CHRG_I:
0374 *val = 0;
0375 *val2 = 500000;
0376 return IIO_VAL_INT_PLUS_MICRO;
0377
0378 default:
0379 return -EINVAL;
0380 }
0381 }
0382
0383 static int axp20x_adc_scale(struct iio_chan_spec const *chan, int *val,
0384 int *val2)
0385 {
0386 switch (chan->type) {
0387 case IIO_VOLTAGE:
0388 return axp20x_adc_scale_voltage(chan->channel, val, val2);
0389
0390 case IIO_CURRENT:
0391 return axp20x_adc_scale_current(chan->channel, val, val2);
0392
0393 case IIO_TEMP:
0394 *val = 100;
0395 return IIO_VAL_INT;
0396
0397 default:
0398 return -EINVAL;
0399 }
0400 }
0401
0402 static int axp22x_adc_scale(struct iio_chan_spec const *chan, int *val,
0403 int *val2)
0404 {
0405 switch (chan->type) {
0406 case IIO_VOLTAGE:
0407 return axp22x_adc_scale_voltage(chan->channel, val, val2);
0408
0409 case IIO_CURRENT:
0410 *val = 1;
0411 return IIO_VAL_INT;
0412
0413 case IIO_TEMP:
0414 *val = 100;
0415 return IIO_VAL_INT;
0416
0417 default:
0418 return -EINVAL;
0419 }
0420 }
0421
0422 static int axp813_adc_scale(struct iio_chan_spec const *chan, int *val,
0423 int *val2)
0424 {
0425 switch (chan->type) {
0426 case IIO_VOLTAGE:
0427 return axp813_adc_scale_voltage(chan->channel, val, val2);
0428
0429 case IIO_CURRENT:
0430 *val = 1;
0431 return IIO_VAL_INT;
0432
0433 case IIO_TEMP:
0434 *val = 100;
0435 return IIO_VAL_INT;
0436
0437 default:
0438 return -EINVAL;
0439 }
0440 }
0441
0442 static int axp20x_adc_offset_voltage(struct iio_dev *indio_dev, int channel,
0443 int *val)
0444 {
0445 struct axp20x_adc_iio *info = iio_priv(indio_dev);
0446 int ret;
0447
0448 ret = regmap_read(info->regmap, AXP20X_GPIO10_IN_RANGE, val);
0449 if (ret < 0)
0450 return ret;
0451
0452 switch (channel) {
0453 case AXP20X_GPIO0_V:
0454 *val &= AXP20X_GPIO10_IN_RANGE_GPIO0;
0455 break;
0456
0457 case AXP20X_GPIO1_V:
0458 *val &= AXP20X_GPIO10_IN_RANGE_GPIO1;
0459 break;
0460
0461 default:
0462 return -EINVAL;
0463 }
0464
0465 *val = *val ? 700000 : 0;
0466
0467 return IIO_VAL_INT;
0468 }
0469
0470 static int axp20x_adc_offset(struct iio_dev *indio_dev,
0471 struct iio_chan_spec const *chan, int *val)
0472 {
0473 switch (chan->type) {
0474 case IIO_VOLTAGE:
0475 return axp20x_adc_offset_voltage(indio_dev, chan->channel, val);
0476
0477 case IIO_TEMP:
0478 *val = -1447;
0479 return IIO_VAL_INT;
0480
0481 default:
0482 return -EINVAL;
0483 }
0484 }
0485
0486 static int axp20x_read_raw(struct iio_dev *indio_dev,
0487 struct iio_chan_spec const *chan, int *val,
0488 int *val2, long mask)
0489 {
0490 switch (mask) {
0491 case IIO_CHAN_INFO_OFFSET:
0492 return axp20x_adc_offset(indio_dev, chan, val);
0493
0494 case IIO_CHAN_INFO_SCALE:
0495 return axp20x_adc_scale(chan, val, val2);
0496
0497 case IIO_CHAN_INFO_RAW:
0498 return axp20x_adc_raw(indio_dev, chan, val);
0499
0500 default:
0501 return -EINVAL;
0502 }
0503 }
0504
0505 static int axp22x_read_raw(struct iio_dev *indio_dev,
0506 struct iio_chan_spec const *chan, int *val,
0507 int *val2, long mask)
0508 {
0509 switch (mask) {
0510 case IIO_CHAN_INFO_OFFSET:
0511
0512 *val = -2677;
0513 return IIO_VAL_INT;
0514
0515 case IIO_CHAN_INFO_SCALE:
0516 return axp22x_adc_scale(chan, val, val2);
0517
0518 case IIO_CHAN_INFO_RAW:
0519 return axp22x_adc_raw(indio_dev, chan, val);
0520
0521 default:
0522 return -EINVAL;
0523 }
0524 }
0525
0526 static int axp813_read_raw(struct iio_dev *indio_dev,
0527 struct iio_chan_spec const *chan, int *val,
0528 int *val2, long mask)
0529 {
0530 switch (mask) {
0531 case IIO_CHAN_INFO_OFFSET:
0532 *val = -2667;
0533 return IIO_VAL_INT;
0534
0535 case IIO_CHAN_INFO_SCALE:
0536 return axp813_adc_scale(chan, val, val2);
0537
0538 case IIO_CHAN_INFO_RAW:
0539 return axp813_adc_raw(indio_dev, chan, val);
0540
0541 default:
0542 return -EINVAL;
0543 }
0544 }
0545
0546 static int axp20x_write_raw(struct iio_dev *indio_dev,
0547 struct iio_chan_spec const *chan, int val, int val2,
0548 long mask)
0549 {
0550 struct axp20x_adc_iio *info = iio_priv(indio_dev);
0551 unsigned int reg, regval;
0552
0553
0554
0555
0556
0557 if (mask != IIO_CHAN_INFO_OFFSET)
0558 return -EINVAL;
0559
0560 if (val != 0 && val != 700000)
0561 return -EINVAL;
0562
0563 val = val ? 1 : 0;
0564
0565 switch (chan->channel) {
0566 case AXP20X_GPIO0_V:
0567 reg = AXP20X_GPIO10_IN_RANGE_GPIO0;
0568 regval = AXP20X_GPIO10_IN_RANGE_GPIO0_VAL(val);
0569 break;
0570
0571 case AXP20X_GPIO1_V:
0572 reg = AXP20X_GPIO10_IN_RANGE_GPIO1;
0573 regval = AXP20X_GPIO10_IN_RANGE_GPIO1_VAL(val);
0574 break;
0575
0576 default:
0577 return -EINVAL;
0578 }
0579
0580 return regmap_update_bits(info->regmap, AXP20X_GPIO10_IN_RANGE, reg,
0581 regval);
0582 }
0583
0584 static const struct iio_info axp20x_adc_iio_info = {
0585 .read_raw = axp20x_read_raw,
0586 .write_raw = axp20x_write_raw,
0587 };
0588
0589 static const struct iio_info axp22x_adc_iio_info = {
0590 .read_raw = axp22x_read_raw,
0591 };
0592
0593 static const struct iio_info axp813_adc_iio_info = {
0594 .read_raw = axp813_read_raw,
0595 };
0596
0597 static int axp20x_adc_rate(struct axp20x_adc_iio *info, int rate)
0598 {
0599 return regmap_update_bits(info->regmap, AXP20X_ADC_RATE,
0600 AXP20X_ADC_RATE_MASK,
0601 AXP20X_ADC_RATE_HZ(rate));
0602 }
0603
0604 static int axp22x_adc_rate(struct axp20x_adc_iio *info, int rate)
0605 {
0606 return regmap_update_bits(info->regmap, AXP20X_ADC_RATE,
0607 AXP20X_ADC_RATE_MASK,
0608 AXP22X_ADC_RATE_HZ(rate));
0609 }
0610
0611 static int axp813_adc_rate(struct axp20x_adc_iio *info, int rate)
0612 {
0613 return regmap_update_bits(info->regmap, AXP813_ADC_RATE,
0614 AXP813_ADC_RATE_MASK,
0615 AXP813_ADC_RATE_HZ(rate));
0616 }
0617
0618 struct axp_data {
0619 const struct iio_info *iio_info;
0620 int num_channels;
0621 struct iio_chan_spec const *channels;
0622 unsigned long adc_en1_mask;
0623 int (*adc_rate)(struct axp20x_adc_iio *info,
0624 int rate);
0625 bool adc_en2;
0626 struct iio_map *maps;
0627 };
0628
0629 static const struct axp_data axp20x_data = {
0630 .iio_info = &axp20x_adc_iio_info,
0631 .num_channels = ARRAY_SIZE(axp20x_adc_channels),
0632 .channels = axp20x_adc_channels,
0633 .adc_en1_mask = AXP20X_ADC_EN1_MASK,
0634 .adc_rate = axp20x_adc_rate,
0635 .adc_en2 = true,
0636 .maps = axp20x_maps,
0637 };
0638
0639 static const struct axp_data axp22x_data = {
0640 .iio_info = &axp22x_adc_iio_info,
0641 .num_channels = ARRAY_SIZE(axp22x_adc_channels),
0642 .channels = axp22x_adc_channels,
0643 .adc_en1_mask = AXP22X_ADC_EN1_MASK,
0644 .adc_rate = axp22x_adc_rate,
0645 .adc_en2 = false,
0646 .maps = axp22x_maps,
0647 };
0648
0649 static const struct axp_data axp813_data = {
0650 .iio_info = &axp813_adc_iio_info,
0651 .num_channels = ARRAY_SIZE(axp813_adc_channels),
0652 .channels = axp813_adc_channels,
0653 .adc_en1_mask = AXP22X_ADC_EN1_MASK,
0654 .adc_rate = axp813_adc_rate,
0655 .adc_en2 = false,
0656 .maps = axp22x_maps,
0657 };
0658
0659 static const struct of_device_id axp20x_adc_of_match[] = {
0660 { .compatible = "x-powers,axp209-adc", .data = (void *)&axp20x_data, },
0661 { .compatible = "x-powers,axp221-adc", .data = (void *)&axp22x_data, },
0662 { .compatible = "x-powers,axp813-adc", .data = (void *)&axp813_data, },
0663 { }
0664 };
0665 MODULE_DEVICE_TABLE(of, axp20x_adc_of_match);
0666
0667 static const struct platform_device_id axp20x_adc_id_match[] = {
0668 { .name = "axp20x-adc", .driver_data = (kernel_ulong_t)&axp20x_data, },
0669 { .name = "axp22x-adc", .driver_data = (kernel_ulong_t)&axp22x_data, },
0670 { .name = "axp813-adc", .driver_data = (kernel_ulong_t)&axp813_data, },
0671 { },
0672 };
0673 MODULE_DEVICE_TABLE(platform, axp20x_adc_id_match);
0674
0675 static int axp20x_probe(struct platform_device *pdev)
0676 {
0677 struct axp20x_adc_iio *info;
0678 struct iio_dev *indio_dev;
0679 struct axp20x_dev *axp20x_dev;
0680 int ret;
0681
0682 axp20x_dev = dev_get_drvdata(pdev->dev.parent);
0683
0684 indio_dev = devm_iio_device_alloc(&pdev->dev, sizeof(*info));
0685 if (!indio_dev)
0686 return -ENOMEM;
0687
0688 info = iio_priv(indio_dev);
0689 platform_set_drvdata(pdev, indio_dev);
0690
0691 info->regmap = axp20x_dev->regmap;
0692 indio_dev->modes = INDIO_DIRECT_MODE;
0693
0694 if (!dev_fwnode(&pdev->dev)) {
0695 const struct platform_device_id *id;
0696
0697 id = platform_get_device_id(pdev);
0698 info->data = (const struct axp_data *)id->driver_data;
0699 } else {
0700 struct device *dev = &pdev->dev;
0701
0702 info->data = device_get_match_data(dev);
0703 }
0704
0705 indio_dev->name = platform_get_device_id(pdev)->name;
0706 indio_dev->info = info->data->iio_info;
0707 indio_dev->num_channels = info->data->num_channels;
0708 indio_dev->channels = info->data->channels;
0709
0710
0711 regmap_write(info->regmap, AXP20X_ADC_EN1, info->data->adc_en1_mask);
0712
0713 if (info->data->adc_en2)
0714
0715 regmap_update_bits(info->regmap, AXP20X_ADC_EN2,
0716 AXP20X_ADC_EN2_MASK, AXP20X_ADC_EN2_MASK);
0717
0718
0719 info->data->adc_rate(info, 100);
0720
0721 ret = iio_map_array_register(indio_dev, info->data->maps);
0722 if (ret < 0) {
0723 dev_err(&pdev->dev, "failed to register IIO maps: %d\n", ret);
0724 goto fail_map;
0725 }
0726
0727 ret = iio_device_register(indio_dev);
0728 if (ret < 0) {
0729 dev_err(&pdev->dev, "could not register the device\n");
0730 goto fail_register;
0731 }
0732
0733 return 0;
0734
0735 fail_register:
0736 iio_map_array_unregister(indio_dev);
0737
0738 fail_map:
0739 regmap_write(info->regmap, AXP20X_ADC_EN1, 0);
0740
0741 if (info->data->adc_en2)
0742 regmap_write(info->regmap, AXP20X_ADC_EN2, 0);
0743
0744 return ret;
0745 }
0746
0747 static int axp20x_remove(struct platform_device *pdev)
0748 {
0749 struct iio_dev *indio_dev = platform_get_drvdata(pdev);
0750 struct axp20x_adc_iio *info = iio_priv(indio_dev);
0751
0752 iio_device_unregister(indio_dev);
0753 iio_map_array_unregister(indio_dev);
0754
0755 regmap_write(info->regmap, AXP20X_ADC_EN1, 0);
0756
0757 if (info->data->adc_en2)
0758 regmap_write(info->regmap, AXP20X_ADC_EN2, 0);
0759
0760 return 0;
0761 }
0762
0763 static struct platform_driver axp20x_adc_driver = {
0764 .driver = {
0765 .name = "axp20x-adc",
0766 .of_match_table = axp20x_adc_of_match,
0767 },
0768 .id_table = axp20x_adc_id_match,
0769 .probe = axp20x_probe,
0770 .remove = axp20x_remove,
0771 };
0772
0773 module_platform_driver(axp20x_adc_driver);
0774
0775 MODULE_DESCRIPTION("ADC driver for AXP20X and AXP22X PMICs");
0776 MODULE_AUTHOR("Quentin Schulz <quentin.schulz@free-electrons.com>");
0777 MODULE_LICENSE("GPL");