diff options
author | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2014-11-05 14:42:48 -0500 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2014-11-05 14:42:48 -0500 |
commit | be61a0d78449f53519905640ac3a9f24c197cbaf (patch) | |
tree | 216a7655e2d6dc8f751214aa93a4863a27954a98 /drivers/iio | |
parent | 7be921a226dcbbbd8fb6f5d63bea4856b3a11624 (diff) | |
parent | 4e4cd14e7cbead5ca20465f4a7ce973d42434a2f (diff) |
Merge tag 'iio-for-3.19a' of git://git.kernel.org/pub/scm/linux/kernel/git/jic23/iio into staging-next
Jonathan writes:
First round of new drivers, features and cleanups for IIO in the 3.19 cycle.
New drivers / supported parts
* rockchip - rk3066-tsadc variant
* si7020 humidity and temperature sensor
* mcp320x - add mcp3001, mcp3002, mcp3004, mcp3008, mcp3201, mcp3202
* bmp280 pressure and temperature sensor
* Qualcomm SPMI PMIC current ADC driver
* Exynos_adc - support exynos7
New features
* vf610-adc - add temperature sensor support
* Documentation of current attributes, scaled pressure, offset and
scaled humidity, RGBC intensity gain factor and scale applied to
differential voltage channels.
* Bring iio_event_monitor up to date with newer modifiers.
* Add of_xlate function to allow for complex channel mappings from the
device tree.
* Add -g parameter to generic_buffer example to allow for devices with
directly fed (no trigger) buffers.
* Move exynos driver over to syscon for PMU register access.
Cleanups, fixes for new drivers
* lis3l02dq drop an unneeded else.
* st sensors - renam st_sensors to st_sensor_settings (for clarity)
* st sensors - drop an unused parameter from all the probe utility
functions.
* vf610 better error handling and tidy up.
* si7020 - cleanups following merge
* as3935 - drop some unnecessary semicolons.
* bmp280 - fix the pressure calculation.
Diffstat (limited to 'drivers/iio')
35 files changed, 1761 insertions, 232 deletions
diff --git a/drivers/iio/accel/st_accel.h b/drivers/iio/accel/st_accel.h index c3877630b2e4..fa9646034305 100644 --- a/drivers/iio/accel/st_accel.h +++ b/drivers/iio/accel/st_accel.h | |||
@@ -33,8 +33,7 @@ static const struct st_sensors_platform_data default_accel_pdata = { | |||
33 | .drdy_int_pin = 1, | 33 | .drdy_int_pin = 1, |
34 | }; | 34 | }; |
35 | 35 | ||
36 | int st_accel_common_probe(struct iio_dev *indio_dev, | 36 | int st_accel_common_probe(struct iio_dev *indio_dev); |
37 | struct st_sensors_platform_data *pdata); | ||
38 | void st_accel_common_remove(struct iio_dev *indio_dev); | 37 | void st_accel_common_remove(struct iio_dev *indio_dev); |
39 | 38 | ||
40 | #ifdef CONFIG_IIO_BUFFER | 39 | #ifdef CONFIG_IIO_BUFFER |
diff --git a/drivers/iio/accel/st_accel_core.c b/drivers/iio/accel/st_accel_core.c index 087864854c61..53f32629283a 100644 --- a/drivers/iio/accel/st_accel_core.c +++ b/drivers/iio/accel/st_accel_core.c | |||
@@ -161,7 +161,7 @@ static const struct iio_chan_spec st_accel_16bit_channels[] = { | |||
161 | IIO_CHAN_SOFT_TIMESTAMP(3) | 161 | IIO_CHAN_SOFT_TIMESTAMP(3) |
162 | }; | 162 | }; |
163 | 163 | ||
164 | static const struct st_sensors st_accel_sensors[] = { | 164 | static const struct st_sensor_settings st_accel_sensors_settings[] = { |
165 | { | 165 | { |
166 | .wai = ST_ACCEL_1_WAI_EXP, | 166 | .wai = ST_ACCEL_1_WAI_EXP, |
167 | .sensors_supported = { | 167 | .sensors_supported = { |
@@ -457,8 +457,7 @@ static const struct iio_trigger_ops st_accel_trigger_ops = { | |||
457 | #define ST_ACCEL_TRIGGER_OPS NULL | 457 | #define ST_ACCEL_TRIGGER_OPS NULL |
458 | #endif | 458 | #endif |
459 | 459 | ||
460 | int st_accel_common_probe(struct iio_dev *indio_dev, | 460 | int st_accel_common_probe(struct iio_dev *indio_dev) |
461 | struct st_sensors_platform_data *plat_data) | ||
462 | { | 461 | { |
463 | struct st_sensor_data *adata = iio_priv(indio_dev); | 462 | struct st_sensor_data *adata = iio_priv(indio_dev); |
464 | int irq = adata->get_irq_data_ready(indio_dev); | 463 | int irq = adata->get_irq_data_ready(indio_dev); |
@@ -470,24 +469,25 @@ int st_accel_common_probe(struct iio_dev *indio_dev, | |||
470 | st_sensors_power_enable(indio_dev); | 469 | st_sensors_power_enable(indio_dev); |
471 | 470 | ||
472 | err = st_sensors_check_device_support(indio_dev, | 471 | err = st_sensors_check_device_support(indio_dev, |
473 | ARRAY_SIZE(st_accel_sensors), st_accel_sensors); | 472 | ARRAY_SIZE(st_accel_sensors_settings), |
473 | st_accel_sensors_settings); | ||
474 | if (err < 0) | 474 | if (err < 0) |
475 | return err; | 475 | return err; |
476 | 476 | ||
477 | adata->num_data_channels = ST_ACCEL_NUMBER_DATA_CHANNELS; | 477 | adata->num_data_channels = ST_ACCEL_NUMBER_DATA_CHANNELS; |
478 | adata->multiread_bit = adata->sensor->multi_read_bit; | 478 | adata->multiread_bit = adata->sensor_settings->multi_read_bit; |
479 | indio_dev->channels = adata->sensor->ch; | 479 | indio_dev->channels = adata->sensor_settings->ch; |
480 | indio_dev->num_channels = ST_SENSORS_NUMBER_ALL_CHANNELS; | 480 | indio_dev->num_channels = ST_SENSORS_NUMBER_ALL_CHANNELS; |
481 | 481 | ||
482 | adata->current_fullscale = (struct st_sensor_fullscale_avl *) | 482 | adata->current_fullscale = (struct st_sensor_fullscale_avl *) |
483 | &adata->sensor->fs.fs_avl[0]; | 483 | &adata->sensor_settings->fs.fs_avl[0]; |
484 | adata->odr = adata->sensor->odr.odr_avl[0].hz; | 484 | adata->odr = adata->sensor_settings->odr.odr_avl[0].hz; |
485 | 485 | ||
486 | if (!plat_data) | 486 | if (!adata->dev->platform_data) |
487 | plat_data = | 487 | adata->dev->platform_data = |
488 | (struct st_sensors_platform_data *)&default_accel_pdata; | 488 | (struct st_sensors_platform_data *)&default_accel_pdata; |
489 | 489 | ||
490 | err = st_sensors_init_sensor(indio_dev, plat_data); | 490 | err = st_sensors_init_sensor(indio_dev, adata->dev->platform_data); |
491 | if (err < 0) | 491 | if (err < 0) |
492 | return err; | 492 | return err; |
493 | 493 | ||
diff --git a/drivers/iio/accel/st_accel_i2c.c b/drivers/iio/accel/st_accel_i2c.c index 7164aeff3ab1..c7246bdd30b9 100644 --- a/drivers/iio/accel/st_accel_i2c.c +++ b/drivers/iio/accel/st_accel_i2c.c | |||
@@ -79,12 +79,11 @@ static int st_accel_i2c_probe(struct i2c_client *client, | |||
79 | return -ENOMEM; | 79 | return -ENOMEM; |
80 | 80 | ||
81 | adata = iio_priv(indio_dev); | 81 | adata = iio_priv(indio_dev); |
82 | adata->dev = &client->dev; | ||
83 | st_sensors_of_i2c_probe(client, st_accel_of_match); | 82 | st_sensors_of_i2c_probe(client, st_accel_of_match); |
84 | 83 | ||
85 | st_sensors_i2c_configure(indio_dev, client, adata); | 84 | st_sensors_i2c_configure(indio_dev, client, adata); |
86 | 85 | ||
87 | err = st_accel_common_probe(indio_dev, client->dev.platform_data); | 86 | err = st_accel_common_probe(indio_dev); |
88 | if (err < 0) | 87 | if (err < 0) |
89 | return err; | 88 | return err; |
90 | 89 | ||
diff --git a/drivers/iio/accel/st_accel_spi.c b/drivers/iio/accel/st_accel_spi.c index 195639646e34..12ec29389e4b 100644 --- a/drivers/iio/accel/st_accel_spi.c +++ b/drivers/iio/accel/st_accel_spi.c | |||
@@ -29,11 +29,10 @@ static int st_accel_spi_probe(struct spi_device *spi) | |||
29 | return -ENOMEM; | 29 | return -ENOMEM; |
30 | 30 | ||
31 | adata = iio_priv(indio_dev); | 31 | adata = iio_priv(indio_dev); |
32 | adata->dev = &spi->dev; | ||
33 | 32 | ||
34 | st_sensors_spi_configure(indio_dev, spi, adata); | 33 | st_sensors_spi_configure(indio_dev, spi, adata); |
35 | 34 | ||
36 | err = st_accel_common_probe(indio_dev, spi->dev.platform_data); | 35 | err = st_accel_common_probe(indio_dev); |
37 | if (err < 0) | 36 | if (err < 0) |
38 | return err; | 37 | return err; |
39 | 38 | ||
diff --git a/drivers/iio/adc/Kconfig b/drivers/iio/adc/Kconfig index 88bdc8f612e2..d0924f3cfa25 100644 --- a/drivers/iio/adc/Kconfig +++ b/drivers/iio/adc/Kconfig | |||
@@ -206,6 +206,20 @@ config NAU7802 | |||
206 | To compile this driver as a module, choose M here: the | 206 | To compile this driver as a module, choose M here: the |
207 | module will be called nau7802. | 207 | module will be called nau7802. |
208 | 208 | ||
209 | config QCOM_SPMI_IADC | ||
210 | tristate "Qualcomm SPMI PMIC current ADC" | ||
211 | depends on SPMI | ||
212 | select REGMAP_SPMI | ||
213 | help | ||
214 | This is the IIO Current ADC driver for Qualcomm QPNP IADC Chip. | ||
215 | |||
216 | The driver supports single mode operation to read from one of two | ||
217 | channels (external or internal). Hardware have additional | ||
218 | channels internally used for gain and offset calibration. | ||
219 | |||
220 | To compile this driver as a module, choose M here: the module will | ||
221 | be called qcom-spmi-iadc. | ||
222 | |||
209 | config ROCKCHIP_SARADC | 223 | config ROCKCHIP_SARADC |
210 | tristate "Rockchip SARADC driver" | 224 | tristate "Rockchip SARADC driver" |
211 | depends on ARCH_ROCKCHIP || (ARM && COMPILE_TEST) | 225 | depends on ARCH_ROCKCHIP || (ARM && COMPILE_TEST) |
diff --git a/drivers/iio/adc/Makefile b/drivers/iio/adc/Makefile index cb88a6a23b8f..c06718b9d8ce 100644 --- a/drivers/iio/adc/Makefile +++ b/drivers/iio/adc/Makefile | |||
@@ -22,6 +22,7 @@ obj-$(CONFIG_MCP320X) += mcp320x.o | |||
22 | obj-$(CONFIG_MCP3422) += mcp3422.o | 22 | obj-$(CONFIG_MCP3422) += mcp3422.o |
23 | obj-$(CONFIG_MEN_Z188_ADC) += men_z188_adc.o | 23 | obj-$(CONFIG_MEN_Z188_ADC) += men_z188_adc.o |
24 | obj-$(CONFIG_NAU7802) += nau7802.o | 24 | obj-$(CONFIG_NAU7802) += nau7802.o |
25 | obj-$(CONFIG_QCOM_SPMI_IADC) += qcom-spmi-iadc.o | ||
25 | obj-$(CONFIG_ROCKCHIP_SARADC) += rockchip_saradc.o | 26 | obj-$(CONFIG_ROCKCHIP_SARADC) += rockchip_saradc.o |
26 | obj-$(CONFIG_TI_ADC081C) += ti-adc081c.o | 27 | obj-$(CONFIG_TI_ADC081C) += ti-adc081c.o |
27 | obj-$(CONFIG_TI_ADC128S052) += ti-adc128s052.o | 28 | obj-$(CONFIG_TI_ADC128S052) += ti-adc128s052.o |
diff --git a/drivers/iio/adc/exynos_adc.c b/drivers/iio/adc/exynos_adc.c index 43620fd4c66a..3a2dbb3b4926 100644 --- a/drivers/iio/adc/exynos_adc.c +++ b/drivers/iio/adc/exynos_adc.c | |||
@@ -39,6 +39,8 @@ | |||
39 | #include <linux/iio/iio.h> | 39 | #include <linux/iio/iio.h> |
40 | #include <linux/iio/machine.h> | 40 | #include <linux/iio/machine.h> |
41 | #include <linux/iio/driver.h> | 41 | #include <linux/iio/driver.h> |
42 | #include <linux/mfd/syscon.h> | ||
43 | #include <linux/regmap.h> | ||
42 | 44 | ||
43 | /* S3C/EXYNOS4412/5250 ADC_V1 registers definitions */ | 45 | /* S3C/EXYNOS4412/5250 ADC_V1 registers definitions */ |
44 | #define ADC_V1_CON(x) ((x) + 0x00) | 46 | #define ADC_V1_CON(x) ((x) + 0x00) |
@@ -90,11 +92,14 @@ | |||
90 | 92 | ||
91 | #define EXYNOS_ADC_TIMEOUT (msecs_to_jiffies(100)) | 93 | #define EXYNOS_ADC_TIMEOUT (msecs_to_jiffies(100)) |
92 | 94 | ||
95 | #define EXYNOS_ADCV1_PHY_OFFSET 0x0718 | ||
96 | #define EXYNOS_ADCV2_PHY_OFFSET 0x0720 | ||
97 | |||
93 | struct exynos_adc { | 98 | struct exynos_adc { |
94 | struct exynos_adc_data *data; | 99 | struct exynos_adc_data *data; |
95 | struct device *dev; | 100 | struct device *dev; |
96 | void __iomem *regs; | 101 | void __iomem *regs; |
97 | void __iomem *enable_reg; | 102 | struct regmap *pmu_map; |
98 | struct clk *clk; | 103 | struct clk *clk; |
99 | struct clk *sclk; | 104 | struct clk *sclk; |
100 | unsigned int irq; | 105 | unsigned int irq; |
@@ -110,6 +115,7 @@ struct exynos_adc_data { | |||
110 | int num_channels; | 115 | int num_channels; |
111 | bool needs_sclk; | 116 | bool needs_sclk; |
112 | bool needs_adc_phy; | 117 | bool needs_adc_phy; |
118 | int phy_offset; | ||
113 | u32 mask; | 119 | u32 mask; |
114 | 120 | ||
115 | void (*init_hw)(struct exynos_adc *info); | 121 | void (*init_hw)(struct exynos_adc *info); |
@@ -183,7 +189,7 @@ static void exynos_adc_v1_init_hw(struct exynos_adc *info) | |||
183 | u32 con1; | 189 | u32 con1; |
184 | 190 | ||
185 | if (info->data->needs_adc_phy) | 191 | if (info->data->needs_adc_phy) |
186 | writel(1, info->enable_reg); | 192 | regmap_write(info->pmu_map, info->data->phy_offset, 1); |
187 | 193 | ||
188 | /* set default prescaler values and Enable prescaler */ | 194 | /* set default prescaler values and Enable prescaler */ |
189 | con1 = ADC_V1_CON_PRSCLV(49) | ADC_V1_CON_PRSCEN; | 195 | con1 = ADC_V1_CON_PRSCLV(49) | ADC_V1_CON_PRSCEN; |
@@ -198,7 +204,7 @@ static void exynos_adc_v1_exit_hw(struct exynos_adc *info) | |||
198 | u32 con; | 204 | u32 con; |
199 | 205 | ||
200 | if (info->data->needs_adc_phy) | 206 | if (info->data->needs_adc_phy) |
201 | writel(0, info->enable_reg); | 207 | regmap_write(info->pmu_map, info->data->phy_offset, 0); |
202 | 208 | ||
203 | con = readl(ADC_V1_CON(info->regs)); | 209 | con = readl(ADC_V1_CON(info->regs)); |
204 | con |= ADC_V1_CON_STANDBY; | 210 | con |= ADC_V1_CON_STANDBY; |
@@ -225,6 +231,7 @@ static const struct exynos_adc_data exynos_adc_v1_data = { | |||
225 | .num_channels = MAX_ADC_V1_CHANNELS, | 231 | .num_channels = MAX_ADC_V1_CHANNELS, |
226 | .mask = ADC_DATX_MASK, /* 12 bit ADC resolution */ | 232 | .mask = ADC_DATX_MASK, /* 12 bit ADC resolution */ |
227 | .needs_adc_phy = true, | 233 | .needs_adc_phy = true, |
234 | .phy_offset = EXYNOS_ADCV1_PHY_OFFSET, | ||
228 | 235 | ||
229 | .init_hw = exynos_adc_v1_init_hw, | 236 | .init_hw = exynos_adc_v1_init_hw, |
230 | .exit_hw = exynos_adc_v1_exit_hw, | 237 | .exit_hw = exynos_adc_v1_exit_hw, |
@@ -314,7 +321,7 @@ static void exynos_adc_v2_init_hw(struct exynos_adc *info) | |||
314 | u32 con1, con2; | 321 | u32 con1, con2; |
315 | 322 | ||
316 | if (info->data->needs_adc_phy) | 323 | if (info->data->needs_adc_phy) |
317 | writel(1, info->enable_reg); | 324 | regmap_write(info->pmu_map, info->data->phy_offset, 1); |
318 | 325 | ||
319 | con1 = ADC_V2_CON1_SOFT_RESET; | 326 | con1 = ADC_V2_CON1_SOFT_RESET; |
320 | writel(con1, ADC_V2_CON1(info->regs)); | 327 | writel(con1, ADC_V2_CON1(info->regs)); |
@@ -332,7 +339,7 @@ static void exynos_adc_v2_exit_hw(struct exynos_adc *info) | |||
332 | u32 con; | 339 | u32 con; |
333 | 340 | ||
334 | if (info->data->needs_adc_phy) | 341 | if (info->data->needs_adc_phy) |
335 | writel(0, info->enable_reg); | 342 | regmap_write(info->pmu_map, info->data->phy_offset, 0); |
336 | 343 | ||
337 | con = readl(ADC_V2_CON1(info->regs)); | 344 | con = readl(ADC_V2_CON1(info->regs)); |
338 | con &= ~ADC_CON_EN_START; | 345 | con &= ~ADC_CON_EN_START; |
@@ -362,6 +369,7 @@ static const struct exynos_adc_data exynos_adc_v2_data = { | |||
362 | .num_channels = MAX_ADC_V2_CHANNELS, | 369 | .num_channels = MAX_ADC_V2_CHANNELS, |
363 | .mask = ADC_DATX_MASK, /* 12 bit ADC resolution */ | 370 | .mask = ADC_DATX_MASK, /* 12 bit ADC resolution */ |
364 | .needs_adc_phy = true, | 371 | .needs_adc_phy = true, |
372 | .phy_offset = EXYNOS_ADCV2_PHY_OFFSET, | ||
365 | 373 | ||
366 | .init_hw = exynos_adc_v2_init_hw, | 374 | .init_hw = exynos_adc_v2_init_hw, |
367 | .exit_hw = exynos_adc_v2_exit_hw, | 375 | .exit_hw = exynos_adc_v2_exit_hw, |
@@ -374,6 +382,7 @@ static const struct exynos_adc_data exynos3250_adc_data = { | |||
374 | .mask = ADC_DATX_MASK, /* 12 bit ADC resolution */ | 382 | .mask = ADC_DATX_MASK, /* 12 bit ADC resolution */ |
375 | .needs_sclk = true, | 383 | .needs_sclk = true, |
376 | .needs_adc_phy = true, | 384 | .needs_adc_phy = true, |
385 | .phy_offset = EXYNOS_ADCV1_PHY_OFFSET, | ||
377 | 386 | ||
378 | .init_hw = exynos_adc_v2_init_hw, | 387 | .init_hw = exynos_adc_v2_init_hw, |
379 | .exit_hw = exynos_adc_v2_exit_hw, | 388 | .exit_hw = exynos_adc_v2_exit_hw, |
@@ -381,6 +390,35 @@ static const struct exynos_adc_data exynos3250_adc_data = { | |||
381 | .start_conv = exynos_adc_v2_start_conv, | 390 | .start_conv = exynos_adc_v2_start_conv, |
382 | }; | 391 | }; |
383 | 392 | ||
393 | static void exynos_adc_exynos7_init_hw(struct exynos_adc *info) | ||
394 | { | ||
395 | u32 con1, con2; | ||
396 | |||
397 | if (info->data->needs_adc_phy) | ||
398 | regmap_write(info->pmu_map, info->data->phy_offset, 1); | ||
399 | |||
400 | con1 = ADC_V2_CON1_SOFT_RESET; | ||
401 | writel(con1, ADC_V2_CON1(info->regs)); | ||
402 | |||
403 | con2 = readl(ADC_V2_CON2(info->regs)); | ||
404 | con2 &= ~ADC_V2_CON2_C_TIME(7); | ||
405 | con2 |= ADC_V2_CON2_C_TIME(0); | ||
406 | writel(con2, ADC_V2_CON2(info->regs)); | ||
407 | |||
408 | /* Enable interrupts */ | ||
409 | writel(1, ADC_V2_INT_EN(info->regs)); | ||
410 | } | ||
411 | |||
412 | static const struct exynos_adc_data exynos7_adc_data = { | ||
413 | .num_channels = MAX_ADC_V1_CHANNELS, | ||
414 | .mask = ADC_DATX_MASK, /* 12 bit ADC resolution */ | ||
415 | |||
416 | .init_hw = exynos_adc_exynos7_init_hw, | ||
417 | .exit_hw = exynos_adc_v2_exit_hw, | ||
418 | .clear_irq = exynos_adc_v2_clear_irq, | ||
419 | .start_conv = exynos_adc_v2_start_conv, | ||
420 | }; | ||
421 | |||
384 | static const struct of_device_id exynos_adc_match[] = { | 422 | static const struct of_device_id exynos_adc_match[] = { |
385 | { | 423 | { |
386 | .compatible = "samsung,s3c2410-adc", | 424 | .compatible = "samsung,s3c2410-adc", |
@@ -406,6 +444,9 @@ static const struct of_device_id exynos_adc_match[] = { | |||
406 | }, { | 444 | }, { |
407 | .compatible = "samsung,exynos3250-adc", | 445 | .compatible = "samsung,exynos3250-adc", |
408 | .data = &exynos3250_adc_data, | 446 | .data = &exynos3250_adc_data, |
447 | }, { | ||
448 | .compatible = "samsung,exynos7-adc", | ||
449 | .data = &exynos7_adc_data, | ||
409 | }, | 450 | }, |
410 | {}, | 451 | {}, |
411 | }; | 452 | }; |
@@ -558,10 +599,13 @@ static int exynos_adc_probe(struct platform_device *pdev) | |||
558 | 599 | ||
559 | 600 | ||
560 | if (info->data->needs_adc_phy) { | 601 | if (info->data->needs_adc_phy) { |
561 | mem = platform_get_resource(pdev, IORESOURCE_MEM, 1); | 602 | info->pmu_map = syscon_regmap_lookup_by_phandle( |
562 | info->enable_reg = devm_ioremap_resource(&pdev->dev, mem); | 603 | pdev->dev.of_node, |
563 | if (IS_ERR(info->enable_reg)) | 604 | "samsung,syscon-phandle"); |
564 | return PTR_ERR(info->enable_reg); | 605 | if (IS_ERR(info->pmu_map)) { |
606 | dev_err(&pdev->dev, "syscon regmap lookup failed.\n"); | ||
607 | return PTR_ERR(info->pmu_map); | ||
608 | } | ||
565 | } | 609 | } |
566 | 610 | ||
567 | irq = platform_get_irq(pdev, 0); | 611 | irq = platform_get_irq(pdev, 0); |
diff --git a/drivers/iio/adc/mcp320x.c b/drivers/iio/adc/mcp320x.c index 28a086e48776..efbfd12a4bfd 100644 --- a/drivers/iio/adc/mcp320x.c +++ b/drivers/iio/adc/mcp320x.c | |||
@@ -1,9 +1,30 @@ | |||
1 | /* | 1 | /* |
2 | * Copyright (C) 2013 Oskar Andero <oskar.andero@gmail.com> | 2 | * Copyright (C) 2013 Oskar Andero <oskar.andero@gmail.com> |
3 | * Copyright (C) 2014 Rose Technology | ||
4 | * Allan Bendorff Jensen <abj@rosetechnology.dk> | ||
5 | * Soren Andersen <san@rosetechnology.dk> | ||
6 | * | ||
7 | * Driver for following ADC chips from Microchip Technology's: | ||
8 | * 10 Bit converter | ||
9 | * MCP3001 | ||
10 | * MCP3002 | ||
11 | * MCP3004 | ||
12 | * MCP3008 | ||
13 | * ------------ | ||
14 | * 12 bit converter | ||
15 | * MCP3201 | ||
16 | * MCP3202 | ||
17 | * MCP3204 | ||
18 | * MCP3208 | ||
19 | * ------------ | ||
3 | * | 20 | * |
4 | * Driver for Microchip Technology's MCP3204 and MCP3208 ADC chips. | ||
5 | * Datasheet can be found here: | 21 | * Datasheet can be found here: |
6 | * http://ww1.microchip.com/downloads/en/devicedoc/21298c.pdf | 22 | * http://ww1.microchip.com/downloads/en/DeviceDoc/21293C.pdf mcp3001 |
23 | * http://ww1.microchip.com/downloads/en/DeviceDoc/21294E.pdf mcp3002 | ||
24 | * http://ww1.microchip.com/downloads/en/DeviceDoc/21295d.pdf mcp3004/08 | ||
25 | * http://ww1.microchip.com/downloads/en/DeviceDoc/21290D.pdf mcp3201 | ||
26 | * http://ww1.microchip.com/downloads/en/DeviceDoc/21034D.pdf mcp3202 | ||
27 | * http://ww1.microchip.com/downloads/en/DeviceDoc/21298c.pdf mcp3204/08 | ||
7 | * | 28 | * |
8 | * This program is free software; you can redistribute it and/or modify | 29 | * This program is free software; you can redistribute it and/or modify |
9 | * it under the terms of the GNU General Public License version 2 as | 30 | * it under the terms of the GNU General Public License version 2 as |
@@ -11,19 +32,29 @@ | |||
11 | */ | 32 | */ |
12 | 33 | ||
13 | #include <linux/err.h> | 34 | #include <linux/err.h> |
35 | #include <linux/delay.h> | ||
14 | #include <linux/spi/spi.h> | 36 | #include <linux/spi/spi.h> |
15 | #include <linux/module.h> | 37 | #include <linux/module.h> |
16 | #include <linux/iio/iio.h> | 38 | #include <linux/iio/iio.h> |
17 | #include <linux/regulator/consumer.h> | 39 | #include <linux/regulator/consumer.h> |
18 | 40 | ||
19 | #define MCP_SINGLE_ENDED (1 << 3) | ||
20 | #define MCP_START_BIT (1 << 4) | ||
21 | |||
22 | enum { | 41 | enum { |
42 | mcp3001, | ||
43 | mcp3002, | ||
44 | mcp3004, | ||
45 | mcp3008, | ||
46 | mcp3201, | ||
47 | mcp3202, | ||
23 | mcp3204, | 48 | mcp3204, |
24 | mcp3208, | 49 | mcp3208, |
25 | }; | 50 | }; |
26 | 51 | ||
52 | struct mcp320x_chip_info { | ||
53 | const struct iio_chan_spec *channels; | ||
54 | unsigned int num_channels; | ||
55 | unsigned int resolution; | ||
56 | }; | ||
57 | |||
27 | struct mcp320x { | 58 | struct mcp320x { |
28 | struct spi_device *spi; | 59 | struct spi_device *spi; |
29 | struct spi_message msg; | 60 | struct spi_message msg; |
@@ -34,19 +65,69 @@ struct mcp320x { | |||
34 | 65 | ||
35 | struct regulator *reg; | 66 | struct regulator *reg; |
36 | struct mutex lock; | 67 | struct mutex lock; |
68 | const struct mcp320x_chip_info *chip_info; | ||
37 | }; | 69 | }; |
38 | 70 | ||
39 | static int mcp320x_adc_conversion(struct mcp320x *adc, u8 msg) | 71 | static int mcp320x_channel_to_tx_data(int device_index, |
72 | const unsigned int channel, bool differential) | ||
73 | { | ||
74 | int start_bit = 1; | ||
75 | |||
76 | switch (device_index) { | ||
77 | case mcp3001: | ||
78 | case mcp3201: | ||
79 | return 0; | ||
80 | case mcp3002: | ||
81 | case mcp3202: | ||
82 | return ((start_bit << 4) | (!differential << 3) | | ||
83 | (channel << 2)); | ||
84 | case mcp3004: | ||
85 | case mcp3204: | ||
86 | case mcp3008: | ||
87 | case mcp3208: | ||
88 | return ((start_bit << 6) | (!differential << 5) | | ||
89 | (channel << 2)); | ||
90 | default: | ||
91 | return -EINVAL; | ||
92 | } | ||
93 | } | ||
94 | |||
95 | static int mcp320x_adc_conversion(struct mcp320x *adc, u8 channel, | ||
96 | bool differential, int device_index) | ||
40 | { | 97 | { |
41 | int ret; | 98 | int ret; |
42 | 99 | ||
43 | adc->tx_buf = msg; | 100 | adc->rx_buf[0] = 0; |
44 | ret = spi_sync(adc->spi, &adc->msg); | 101 | adc->rx_buf[1] = 0; |
45 | if (ret < 0) | 102 | adc->tx_buf = mcp320x_channel_to_tx_data(device_index, |
46 | return ret; | 103 | channel, differential); |
104 | |||
105 | if (device_index != mcp3001 && device_index != mcp3201) { | ||
106 | ret = spi_sync(adc->spi, &adc->msg); | ||
107 | if (ret < 0) | ||
108 | return ret; | ||
109 | } else { | ||
110 | ret = spi_read(adc->spi, &adc->rx_buf, sizeof(adc->rx_buf)); | ||
111 | if (ret < 0) | ||
112 | return ret; | ||
113 | } | ||
47 | 114 | ||
48 | return ((adc->rx_buf[0] & 0x3f) << 6) | | 115 | switch (device_index) { |
49 | (adc->rx_buf[1] >> 2); | 116 | case mcp3001: |
117 | return (adc->rx_buf[0] << 5 | adc->rx_buf[1] >> 3); | ||
118 | case mcp3002: | ||
119 | case mcp3004: | ||
120 | case mcp3008: | ||
121 | return (adc->rx_buf[0] << 2 | adc->rx_buf[1] >> 6); | ||
122 | case mcp3201: | ||
123 | return (adc->rx_buf[0] << 7 | adc->rx_buf[1] >> 1); | ||
124 | case mcp3202: | ||
125 | case mcp3204: | ||
126 | case mcp3208: | ||
127 | return (adc->rx_buf[0] << 4 | adc->rx_buf[1] >> 4); | ||
128 | default: | ||
129 | return -EINVAL; | ||
130 | } | ||
50 | } | 131 | } |
51 | 132 | ||
52 | static int mcp320x_read_raw(struct iio_dev *indio_dev, | 133 | static int mcp320x_read_raw(struct iio_dev *indio_dev, |
@@ -55,18 +136,17 @@ static int mcp320x_read_raw(struct iio_dev *indio_dev, | |||
55 | { | 136 | { |
56 | struct mcp320x *adc = iio_priv(indio_dev); | 137 | struct mcp320x *adc = iio_priv(indio_dev); |
57 | int ret = -EINVAL; | 138 | int ret = -EINVAL; |
139 | int device_index = 0; | ||
58 | 140 | ||
59 | mutex_lock(&adc->lock); | 141 | mutex_lock(&adc->lock); |
60 | 142 | ||
143 | device_index = spi_get_device_id(adc->spi)->driver_data; | ||
144 | |||
61 | switch (mask) { | 145 | switch (mask) { |
62 | case IIO_CHAN_INFO_RAW: | 146 | case IIO_CHAN_INFO_RAW: |
63 | if (channel->differential) | 147 | ret = mcp320x_adc_conversion(adc, channel->address, |
64 | ret = mcp320x_adc_conversion(adc, | 148 | channel->differential, device_index); |
65 | MCP_START_BIT | channel->address); | 149 | |
66 | else | ||
67 | ret = mcp320x_adc_conversion(adc, | ||
68 | MCP_START_BIT | MCP_SINGLE_ENDED | | ||
69 | channel->address); | ||
70 | if (ret < 0) | 150 | if (ret < 0) |
71 | goto out; | 151 | goto out; |
72 | 152 | ||
@@ -75,18 +155,15 @@ static int mcp320x_read_raw(struct iio_dev *indio_dev, | |||
75 | break; | 155 | break; |
76 | 156 | ||
77 | case IIO_CHAN_INFO_SCALE: | 157 | case IIO_CHAN_INFO_SCALE: |
78 | /* Digital output code = (4096 * Vin) / Vref */ | ||
79 | ret = regulator_get_voltage(adc->reg); | 158 | ret = regulator_get_voltage(adc->reg); |
80 | if (ret < 0) | 159 | if (ret < 0) |
81 | goto out; | 160 | goto out; |
82 | 161 | ||
162 | /* convert regulator output voltage to mV */ | ||
83 | *val = ret / 1000; | 163 | *val = ret / 1000; |
84 | *val2 = 12; | 164 | *val2 = adc->chip_info->resolution; |
85 | ret = IIO_VAL_FRACTIONAL_LOG2; | 165 | ret = IIO_VAL_FRACTIONAL_LOG2; |
86 | break; | 166 | break; |
87 | |||
88 | default: | ||
89 | break; | ||
90 | } | 167 | } |
91 | 168 | ||
92 | out: | 169 | out: |
@@ -117,6 +194,16 @@ out: | |||
117 | .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) \ | 194 | .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) \ |
118 | } | 195 | } |
119 | 196 | ||
197 | static const struct iio_chan_spec mcp3201_channels[] = { | ||
198 | MCP320X_VOLTAGE_CHANNEL_DIFF(0), | ||
199 | }; | ||
200 | |||
201 | static const struct iio_chan_spec mcp3202_channels[] = { | ||
202 | MCP320X_VOLTAGE_CHANNEL(0), | ||
203 | MCP320X_VOLTAGE_CHANNEL(1), | ||
204 | MCP320X_VOLTAGE_CHANNEL_DIFF(0), | ||
205 | }; | ||
206 | |||
120 | static const struct iio_chan_spec mcp3204_channels[] = { | 207 | static const struct iio_chan_spec mcp3204_channels[] = { |
121 | MCP320X_VOLTAGE_CHANNEL(0), | 208 | MCP320X_VOLTAGE_CHANNEL(0), |
122 | MCP320X_VOLTAGE_CHANNEL(1), | 209 | MCP320X_VOLTAGE_CHANNEL(1), |
@@ -146,19 +233,46 @@ static const struct iio_info mcp320x_info = { | |||
146 | .driver_module = THIS_MODULE, | 233 | .driver_module = THIS_MODULE, |
147 | }; | 234 | }; |
148 | 235 | ||
149 | struct mcp3208_chip_info { | 236 | static const struct mcp320x_chip_info mcp320x_chip_infos[] = { |
150 | const struct iio_chan_spec *channels; | 237 | [mcp3001] = { |
151 | unsigned int num_channels; | 238 | .channels = mcp3201_channels, |
152 | }; | 239 | .num_channels = ARRAY_SIZE(mcp3201_channels), |
153 | 240 | .resolution = 10 | |
154 | static const struct mcp3208_chip_info mcp3208_chip_infos[] = { | 241 | }, |
242 | [mcp3002] = { | ||
243 | .channels = mcp3202_channels, | ||
244 | .num_channels = ARRAY_SIZE(mcp3202_channels), | ||
245 | .resolution = 10 | ||
246 | }, | ||
247 | [mcp3004] = { | ||
248 | .channels = mcp3204_channels, | ||
249 | .num_channels = ARRAY_SIZE(mcp3204_channels), | ||
250 | .resolution = 10 | ||
251 | }, | ||
252 | [mcp3008] = { | ||
253 | .channels = mcp3208_channels, | ||
254 | .num_channels = ARRAY_SIZE(mcp3208_channels), | ||
255 | .resolution = 10 | ||
256 | }, | ||
257 | [mcp3201] = { | ||
258 | .channels = mcp3201_channels, | ||
259 | .num_channels = ARRAY_SIZE(mcp3201_channels), | ||
260 | .resolution = 12 | ||
261 | }, | ||
262 | [mcp3202] = { | ||
263 | .channels = mcp3202_channels, | ||
264 | .num_channels = ARRAY_SIZE(mcp3202_channels), | ||
265 | .resolution = 12 | ||
266 | }, | ||
155 | [mcp3204] = { | 267 | [mcp3204] = { |
156 | .channels = mcp3204_channels, | 268 | .channels = mcp3204_channels, |
157 | .num_channels = ARRAY_SIZE(mcp3204_channels) | 269 | .num_channels = ARRAY_SIZE(mcp3204_channels), |
270 | .resolution = 12 | ||
158 | }, | 271 | }, |
159 | [mcp3208] = { | 272 | [mcp3208] = { |
160 | .channels = mcp3208_channels, | 273 | .channels = mcp3208_channels, |
161 | .num_channels = ARRAY_SIZE(mcp3208_channels) | 274 | .num_channels = ARRAY_SIZE(mcp3208_channels), |
275 | .resolution = 12 | ||
162 | }, | 276 | }, |
163 | }; | 277 | }; |
164 | 278 | ||
@@ -166,7 +280,7 @@ static int mcp320x_probe(struct spi_device *spi) | |||
166 | { | 280 | { |
167 | struct iio_dev *indio_dev; | 281 | struct iio_dev *indio_dev; |
168 | struct mcp320x *adc; | 282 | struct mcp320x *adc; |
169 | const struct mcp3208_chip_info *chip_info; | 283 | const struct mcp320x_chip_info *chip_info; |
170 | int ret; | 284 | int ret; |
171 | 285 | ||
172 | indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*adc)); | 286 | indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*adc)); |
@@ -181,7 +295,7 @@ static int mcp320x_probe(struct spi_device *spi) | |||
181 | indio_dev->modes = INDIO_DIRECT_MODE; | 295 | indio_dev->modes = INDIO_DIRECT_MODE; |
182 | indio_dev->info = &mcp320x_info; | 296 | indio_dev->info = &mcp320x_info; |
183 | 297 | ||
184 | chip_info = &mcp3208_chip_infos[spi_get_device_id(spi)->driver_data]; | 298 | chip_info = &mcp320x_chip_infos[spi_get_device_id(spi)->driver_data]; |
185 | indio_dev->channels = chip_info->channels; | 299 | indio_dev->channels = chip_info->channels; |
186 | indio_dev->num_channels = chip_info->num_channels; | 300 | indio_dev->num_channels = chip_info->num_channels; |
187 | 301 | ||
@@ -226,7 +340,45 @@ static int mcp320x_remove(struct spi_device *spi) | |||
226 | return 0; | 340 | return 0; |
227 | } | 341 | } |
228 | 342 | ||
343 | #if defined(CONFIG_OF) | ||
344 | static const struct of_device_id mcp320x_dt_ids[] = { | ||
345 | { | ||
346 | .compatible = "mcp3001", | ||
347 | .data = &mcp320x_chip_infos[mcp3001], | ||
348 | }, { | ||
349 | .compatible = "mcp3002", | ||
350 | .data = &mcp320x_chip_infos[mcp3002], | ||
351 | }, { | ||
352 | .compatible = "mcp3004", | ||
353 | .data = &mcp320x_chip_infos[mcp3004], | ||
354 | }, { | ||
355 | .compatible = "mcp3008", | ||
356 | .data = &mcp320x_chip_infos[mcp3008], | ||
357 | }, { | ||
358 | .compatible = "mcp3201", | ||
359 | .data = &mcp320x_chip_infos[mcp3201], | ||
360 | }, { | ||
361 | .compatible = "mcp3202", | ||
362 | .data = &mcp320x_chip_infos[mcp3202], | ||
363 | }, { | ||
364 | .compatible = "mcp3204", | ||
365 | .data = &mcp320x_chip_infos[mcp3204], | ||
366 | }, { | ||
367 | .compatible = "mcp3208", | ||
368 | .data = &mcp320x_chip_infos[mcp3208], | ||
369 | }, { | ||
370 | } | ||
371 | }; | ||
372 | MODULE_DEVICE_TABLE(of, mcp320x_dt_ids); | ||
373 | #endif | ||
374 | |||
229 | static const struct spi_device_id mcp320x_id[] = { | 375 | static const struct spi_device_id mcp320x_id[] = { |
376 | { "mcp3001", mcp3001 }, | ||
377 | { "mcp3002", mcp3002 }, | ||
378 | { "mcp3004", mcp3004 }, | ||
379 | { "mcp3008", mcp3008 }, | ||
380 | { "mcp3201", mcp3201 }, | ||
381 | { "mcp3202", mcp3202 }, | ||
230 | { "mcp3204", mcp3204 }, | 382 | { "mcp3204", mcp3204 }, |
231 | { "mcp3208", mcp3208 }, | 383 | { "mcp3208", mcp3208 }, |
232 | { } | 384 | { } |
@@ -245,5 +397,5 @@ static struct spi_driver mcp320x_driver = { | |||
245 | module_spi_driver(mcp320x_driver); | 397 | module_spi_driver(mcp320x_driver); |
246 | 398 | ||
247 | MODULE_AUTHOR("Oskar Andero <oskar.andero@gmail.com>"); | 399 | MODULE_AUTHOR("Oskar Andero <oskar.andero@gmail.com>"); |
248 | MODULE_DESCRIPTION("Microchip Technology MCP3204/08"); | 400 | MODULE_DESCRIPTION("Microchip Technology MCP3x01/02/04/08"); |
249 | MODULE_LICENSE("GPL v2"); | 401 | MODULE_LICENSE("GPL v2"); |
diff --git a/drivers/iio/adc/qcom-spmi-iadc.c b/drivers/iio/adc/qcom-spmi-iadc.c new file mode 100644 index 000000000000..b9666f2f5e51 --- /dev/null +++ b/drivers/iio/adc/qcom-spmi-iadc.c | |||
@@ -0,0 +1,595 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2012-2014, The Linux Foundation. All rights reserved. | ||
3 | * | ||
4 | * This program is free software; you can redistribute it and/or modify | ||
5 | * it under the terms of the GNU General Public License version 2 and | ||
6 | * only version 2 as published by the Free Software Foundation. | ||
7 | * | ||
8 | * This program is distributed in the hope that it will be useful, | ||
9 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
10 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
11 | * GNU General Public License for more details. | ||
12 | */ | ||
13 | |||
14 | #include <linux/bitops.h> | ||
15 | #include <linux/completion.h> | ||
16 | #include <linux/delay.h> | ||
17 | #include <linux/err.h> | ||
18 | #include <linux/iio/iio.h> | ||
19 | #include <linux/interrupt.h> | ||
20 | #include <linux/kernel.h> | ||
21 | #include <linux/mutex.h> | ||
22 | #include <linux/module.h> | ||
23 | #include <linux/of.h> | ||
24 | #include <linux/of_device.h> | ||
25 | #include <linux/platform_device.h> | ||
26 | #include <linux/regmap.h> | ||
27 | #include <linux/slab.h> | ||
28 | |||
29 | /* IADC register and bit definition */ | ||
30 | #define IADC_REVISION2 0x1 | ||
31 | #define IADC_REVISION2_SUPPORTED_IADC 1 | ||
32 | |||
33 | #define IADC_PERPH_TYPE 0x4 | ||
34 | #define IADC_PERPH_TYPE_ADC 8 | ||
35 | |||
36 | #define IADC_PERPH_SUBTYPE 0x5 | ||
37 | #define IADC_PERPH_SUBTYPE_IADC 3 | ||
38 | |||
39 | #define IADC_STATUS1 0x8 | ||
40 | #define IADC_STATUS1_OP_MODE 4 | ||
41 | #define IADC_STATUS1_REQ_STS BIT(1) | ||
42 | #define IADC_STATUS1_EOC BIT(0) | ||
43 | #define IADC_STATUS1_REQ_STS_EOC_MASK 0x3 | ||
44 | |||
45 | #define IADC_MODE_CTL 0x40 | ||
46 | #define IADC_OP_MODE_SHIFT 3 | ||
47 | #define IADC_OP_MODE_NORMAL 0 | ||
48 | #define IADC_TRIM_EN BIT(0) | ||
49 | |||
50 | #define IADC_EN_CTL1 0x46 | ||
51 | #define IADC_EN_CTL1_SET BIT(7) | ||
52 | |||
53 | #define IADC_CH_SEL_CTL 0x48 | ||
54 | |||
55 | #define IADC_DIG_PARAM 0x50 | ||
56 | #define IADC_DIG_DEC_RATIO_SEL_SHIFT 2 | ||
57 | |||
58 | #define IADC_HW_SETTLE_DELAY 0x51 | ||
59 | |||
60 | #define IADC_CONV_REQ 0x52 | ||
61 | #define IADC_CONV_REQ_SET BIT(7) | ||
62 | |||
63 | #define IADC_FAST_AVG_CTL 0x5a | ||
64 | #define IADC_FAST_AVG_EN 0x5b | ||
65 | #define IADC_FAST_AVG_EN_SET BIT(7) | ||
66 | |||
67 | #define IADC_PERH_RESET_CTL3 0xda | ||
68 | #define IADC_FOLLOW_WARM_RB BIT(2) | ||
69 | |||
70 | #define IADC_DATA 0x60 /* 16 bits */ | ||
71 | |||
72 | #define IADC_SEC_ACCESS 0xd0 | ||
73 | #define IADC_SEC_ACCESS_DATA 0xa5 | ||
74 | |||
75 | #define IADC_NOMINAL_RSENSE 0xf4 | ||
76 | #define IADC_NOMINAL_RSENSE_SIGN_MASK BIT(7) | ||
77 | |||
78 | #define IADC_REF_GAIN_MICRO_VOLTS 17857 | ||
79 | |||
80 | #define IADC_INT_RSENSE_DEVIATION 15625 /* nano Ohms per bit */ | ||
81 | |||
82 | #define IADC_INT_RSENSE_IDEAL_VALUE 10000 /* micro Ohms */ | ||
83 | #define IADC_INT_RSENSE_DEFAULT_VALUE 7800 /* micro Ohms */ | ||
84 | #define IADC_INT_RSENSE_DEFAULT_GF 9000 /* micro Ohms */ | ||
85 | #define IADC_INT_RSENSE_DEFAULT_SMIC 9700 /* micro Ohms */ | ||
86 | |||
87 | #define IADC_CONV_TIME_MIN_US 2000 | ||
88 | #define IADC_CONV_TIME_MAX_US 2100 | ||
89 | |||
90 | #define IADC_DEF_PRESCALING 0 /* 1:1 */ | ||
91 | #define IADC_DEF_DECIMATION 0 /* 512 */ | ||
92 | #define IADC_DEF_HW_SETTLE_TIME 0 /* 0 us */ | ||
93 | #define IADC_DEF_AVG_SAMPLES 0 /* 1 sample */ | ||
94 | |||
95 | /* IADC channel list */ | ||
96 | #define IADC_INT_RSENSE 0 | ||
97 | #define IADC_EXT_RSENSE 1 | ||
98 | #define IADC_GAIN_17P857MV 3 | ||
99 | #define IADC_EXT_OFFSET_CSP_CSN 5 | ||
100 | #define IADC_INT_OFFSET_CSP2_CSN2 6 | ||
101 | |||
102 | /** | ||
103 | * struct iadc_chip - IADC Current ADC device structure. | ||
104 | * @regmap: regmap for register read/write. | ||
105 | * @dev: This device pointer. | ||
106 | * @base: base offset for the ADC peripheral. | ||
107 | * @rsense: Values of the internal and external sense resister in micro Ohms. | ||
108 | * @poll_eoc: Poll for end of conversion instead of waiting for IRQ. | ||
109 | * @offset: Raw offset values for the internal and external channels. | ||
110 | * @gain: Raw gain of the channels. | ||
111 | * @lock: ADC lock for access to the peripheral. | ||
112 | * @complete: ADC notification after end of conversion interrupt is received. | ||
113 | */ | ||
114 | struct iadc_chip { | ||
115 | struct regmap *regmap; | ||
116 | struct device *dev; | ||
117 | u16 base; | ||
118 | bool poll_eoc; | ||
119 | u32 rsense[2]; | ||
120 | u16 offset[2]; | ||
121 | u16 gain; | ||
122 | struct mutex lock; | ||
123 | struct completion complete; | ||
124 | }; | ||
125 | |||
126 | static int iadc_read(struct iadc_chip *iadc, u16 offset, u8 *data) | ||
127 | { | ||
128 | unsigned int val; | ||
129 | int ret; | ||
130 | |||
131 | ret = regmap_read(iadc->regmap, iadc->base + offset, &val); | ||
132 | if (ret < 0) | ||
133 | return ret; | ||
134 | |||
135 | *data = val; | ||
136 | return 0; | ||
137 | } | ||
138 | |||
139 | static int iadc_write(struct iadc_chip *iadc, u16 offset, u8 data) | ||
140 | { | ||
141 | return regmap_write(iadc->regmap, iadc->base + offset, data); | ||
142 | } | ||
143 | |||
144 | static int iadc_reset(struct iadc_chip *iadc) | ||
145 | { | ||
146 | u8 data; | ||
147 | int ret; | ||
148 | |||
149 | ret = iadc_write(iadc, IADC_SEC_ACCESS, IADC_SEC_ACCESS_DATA); | ||
150 | if (ret < 0) | ||
151 | return ret; | ||
152 | |||
153 | ret = iadc_read(iadc, IADC_PERH_RESET_CTL3, &data); | ||
154 | if (ret < 0) | ||
155 | return ret; | ||
156 | |||
157 | ret = iadc_write(iadc, IADC_SEC_ACCESS, IADC_SEC_ACCESS_DATA); | ||
158 | if (ret < 0) | ||
159 | return ret; | ||
160 | |||
161 | data |= IADC_FOLLOW_WARM_RB; | ||
162 | |||
163 | return iadc_write(iadc, IADC_PERH_RESET_CTL3, data); | ||
164 | } | ||
165 | |||
166 | static int iadc_set_state(struct iadc_chip *iadc, bool state) | ||
167 | { | ||
168 | return iadc_write(iadc, IADC_EN_CTL1, state ? IADC_EN_CTL1_SET : 0); | ||
169 | } | ||
170 | |||
171 | static void iadc_status_show(struct iadc_chip *iadc) | ||
172 | { | ||
173 | u8 mode, sta1, chan, dig, en, req; | ||
174 | int ret; | ||
175 | |||
176 | ret = iadc_read(iadc, IADC_MODE_CTL, &mode); | ||
177 | if (ret < 0) | ||
178 | return; | ||
179 | |||
180 | ret = iadc_read(iadc, IADC_DIG_PARAM, &dig); | ||
181 | if (ret < 0) | ||
182 | return; | ||
183 | |||
184 | ret = iadc_read(iadc, IADC_CH_SEL_CTL, &chan); | ||
185 | if (ret < 0) | ||
186 | return; | ||
187 | |||
188 | ret = iadc_read(iadc, IADC_CONV_REQ, &req); | ||
189 | if (ret < 0) | ||
190 | return; | ||
191 | |||
192 | ret = iadc_read(iadc, IADC_STATUS1, &sta1); | ||
193 | if (ret < 0) | ||
194 | return; | ||
195 | |||
196 | ret = iadc_read(iadc, IADC_EN_CTL1, &en); | ||
197 | if (ret < 0) | ||
198 | return; | ||
199 | |||
200 | dev_err(iadc->dev, | ||
201 | "mode:%02x en:%02x chan:%02x dig:%02x req:%02x sta1:%02x\n", | ||
202 | mode, en, chan, dig, req, sta1); | ||
203 | } | ||
204 | |||
205 | static int iadc_configure(struct iadc_chip *iadc, int channel) | ||
206 | { | ||
207 | u8 decim, mode; | ||
208 | int ret; | ||
209 | |||
210 | /* Mode selection */ | ||
211 | mode = (IADC_OP_MODE_NORMAL << IADC_OP_MODE_SHIFT) | IADC_TRIM_EN; | ||
212 | ret = iadc_write(iadc, IADC_MODE_CTL, mode); | ||
213 | if (ret < 0) | ||
214 | return ret; | ||
215 | |||
216 | /* Channel selection */ | ||
217 | ret = iadc_write(iadc, IADC_CH_SEL_CTL, channel); | ||
218 | if (ret < 0) | ||
219 | return ret; | ||
220 | |||
221 | /* Digital parameter setup */ | ||
222 | decim = IADC_DEF_DECIMATION << IADC_DIG_DEC_RATIO_SEL_SHIFT; | ||
223 | ret = iadc_write(iadc, IADC_DIG_PARAM, decim); | ||
224 | if (ret < 0) | ||
225 | return ret; | ||
226 | |||
227 | /* HW settle time delay */ | ||
228 | ret = iadc_write(iadc, IADC_HW_SETTLE_DELAY, IADC_DEF_HW_SETTLE_TIME); | ||
229 | if (ret < 0) | ||
230 | return ret; | ||
231 | |||
232 | ret = iadc_write(iadc, IADC_FAST_AVG_CTL, IADC_DEF_AVG_SAMPLES); | ||
233 | if (ret < 0) | ||
234 | return ret; | ||
235 | |||
236 | if (IADC_DEF_AVG_SAMPLES) | ||
237 | ret = iadc_write(iadc, IADC_FAST_AVG_EN, IADC_FAST_AVG_EN_SET); | ||
238 | else | ||
239 | ret = iadc_write(iadc, IADC_FAST_AVG_EN, 0); | ||
240 | |||
241 | if (ret < 0) | ||
242 | return ret; | ||
243 | |||
244 | if (!iadc->poll_eoc) | ||
245 | reinit_completion(&iadc->complete); | ||
246 | |||
247 | ret = iadc_set_state(iadc, true); | ||
248 | if (ret < 0) | ||
249 | return ret; | ||
250 | |||
251 | /* Request conversion */ | ||
252 | return iadc_write(iadc, IADC_CONV_REQ, IADC_CONV_REQ_SET); | ||
253 | } | ||
254 | |||
255 | static int iadc_poll_wait_eoc(struct iadc_chip *iadc, unsigned int interval_us) | ||
256 | { | ||
257 | unsigned int count, retry; | ||
258 | int ret; | ||
259 | u8 sta1; | ||
260 | |||
261 | retry = interval_us / IADC_CONV_TIME_MIN_US; | ||
262 | |||
263 | for (count = 0; count < retry; count++) { | ||
264 | ret = iadc_read(iadc, IADC_STATUS1, &sta1); | ||
265 | if (ret < 0) | ||
266 | return ret; | ||
267 | |||
268 | sta1 &= IADC_STATUS1_REQ_STS_EOC_MASK; | ||
269 | if (sta1 == IADC_STATUS1_EOC) | ||
270 | return 0; | ||
271 | |||
272 | usleep_range(IADC_CONV_TIME_MIN_US, IADC_CONV_TIME_MAX_US); | ||
273 | } | ||
274 | |||
275 | iadc_status_show(iadc); | ||
276 | |||
277 | return -ETIMEDOUT; | ||
278 | } | ||
279 | |||
280 | static int iadc_read_result(struct iadc_chip *iadc, u16 *data) | ||
281 | { | ||
282 | return regmap_bulk_read(iadc->regmap, iadc->base + IADC_DATA, data, 2); | ||
283 | } | ||
284 | |||
285 | static int iadc_do_conversion(struct iadc_chip *iadc, int chan, u16 *data) | ||
286 | { | ||
287 | unsigned int wait; | ||
288 | int ret; | ||
289 | |||
290 | ret = iadc_configure(iadc, chan); | ||
291 | if (ret < 0) | ||
292 | goto exit; | ||
293 | |||
294 | wait = BIT(IADC_DEF_AVG_SAMPLES) * IADC_CONV_TIME_MIN_US * 2; | ||
295 | |||
296 | if (iadc->poll_eoc) { | ||
297 | ret = iadc_poll_wait_eoc(iadc, wait); | ||
298 | } else { | ||
299 | ret = wait_for_completion_timeout(&iadc->complete, wait); | ||
300 | if (!ret) | ||
301 | ret = -ETIMEDOUT; | ||
302 | else | ||
303 | /* double check conversion status */ | ||
304 | ret = iadc_poll_wait_eoc(iadc, IADC_CONV_TIME_MIN_US); | ||
305 | } | ||
306 | |||
307 | if (!ret) | ||
308 | ret = iadc_read_result(iadc, data); | ||
309 | exit: | ||
310 | iadc_set_state(iadc, false); | ||
311 | if (ret < 0) | ||
312 | dev_err(iadc->dev, "conversion failed\n"); | ||
313 | |||
314 | return ret; | ||
315 | } | ||
316 | |||
317 | static int iadc_read_raw(struct iio_dev *indio_dev, | ||
318 | struct iio_chan_spec const *chan, | ||
319 | int *val, int *val2, long mask) | ||
320 | { | ||
321 | struct iadc_chip *iadc = iio_priv(indio_dev); | ||
322 | s32 isense_ua, vsense_uv; | ||
323 | u16 adc_raw, vsense_raw; | ||
324 | int ret; | ||
325 | |||
326 | switch (mask) { | ||
327 | case IIO_CHAN_INFO_RAW: | ||
328 | mutex_lock(&iadc->lock); | ||
329 | ret = iadc_do_conversion(iadc, chan->channel, &adc_raw); | ||
330 | mutex_unlock(&iadc->lock); | ||
331 | if (ret < 0) | ||
332 | return ret; | ||
333 | |||
334 | vsense_raw = adc_raw - iadc->offset[chan->channel]; | ||
335 | |||
336 | vsense_uv = vsense_raw * IADC_REF_GAIN_MICRO_VOLTS; | ||
337 | vsense_uv /= (s32)iadc->gain - iadc->offset[chan->channel]; | ||
338 | |||
339 | isense_ua = vsense_uv / iadc->rsense[chan->channel]; | ||
340 | |||
341 | dev_dbg(iadc->dev, "off %d gain %d adc %d %duV I %duA\n", | ||
342 | iadc->offset[chan->channel], iadc->gain, | ||
343 | adc_raw, vsense_uv, isense_ua); | ||
344 | |||
345 | *val = isense_ua; | ||
346 | return IIO_VAL_INT; | ||
347 | case IIO_CHAN_INFO_SCALE: | ||
348 | *val = 0; | ||
349 | *val2 = 1000; | ||
350 | return IIO_VAL_INT_PLUS_MICRO; | ||
351 | } | ||
352 | |||
353 | return -EINVAL; | ||
354 | } | ||
355 | |||
356 | static const struct iio_info iadc_info = { | ||
357 | .read_raw = iadc_read_raw, | ||
358 | .driver_module = THIS_MODULE, | ||
359 | }; | ||
360 | |||
361 | static irqreturn_t iadc_isr(int irq, void *dev_id) | ||
362 | { | ||
363 | struct iadc_chip *iadc = dev_id; | ||
364 | |||
365 | complete(&iadc->complete); | ||
366 | |||
367 | return IRQ_HANDLED; | ||
368 | } | ||
369 | |||
370 | static int iadc_update_offset(struct iadc_chip *iadc) | ||
371 | { | ||
372 | int ret; | ||
373 | |||
374 | ret = iadc_do_conversion(iadc, IADC_GAIN_17P857MV, &iadc->gain); | ||
375 | if (ret < 0) | ||
376 | return ret; | ||
377 | |||
378 | ret = iadc_do_conversion(iadc, IADC_INT_OFFSET_CSP2_CSN2, | ||
379 | &iadc->offset[IADC_INT_RSENSE]); | ||
380 | if (ret < 0) | ||
381 | return ret; | ||
382 | |||
383 | if (iadc->gain == iadc->offset[IADC_INT_RSENSE]) { | ||
384 | dev_err(iadc->dev, "error: internal offset == gain %d\n", | ||
385 | iadc->gain); | ||
386 | return -EINVAL; | ||
387 | } | ||
388 | |||
389 | ret = iadc_do_conversion(iadc, IADC_EXT_OFFSET_CSP_CSN, | ||
390 | &iadc->offset[IADC_EXT_RSENSE]); | ||
391 | if (ret < 0) | ||
392 | return ret; | ||
393 | |||
394 | if (iadc->gain == iadc->offset[IADC_EXT_RSENSE]) { | ||
395 | dev_err(iadc->dev, "error: external offset == gain %d\n", | ||
396 | iadc->gain); | ||
397 | return -EINVAL; | ||
398 | } | ||
399 | |||
400 | return 0; | ||
401 | } | ||
402 | |||
403 | static int iadc_version_check(struct iadc_chip *iadc) | ||
404 | { | ||
405 | u8 val; | ||
406 | int ret; | ||
407 | |||
408 | ret = iadc_read(iadc, IADC_PERPH_TYPE, &val); | ||
409 | if (ret < 0) | ||
410 | return ret; | ||
411 | |||
412 | if (val < IADC_PERPH_TYPE_ADC) { | ||
413 | dev_err(iadc->dev, "%d is not ADC\n", val); | ||
414 | return -EINVAL; | ||
415 | } | ||
416 | |||
417 | ret = iadc_read(iadc, IADC_PERPH_SUBTYPE, &val); | ||
418 | if (ret < 0) | ||
419 | return ret; | ||
420 | |||
421 | if (val < IADC_PERPH_SUBTYPE_IADC) { | ||
422 | dev_err(iadc->dev, "%d is not IADC\n", val); | ||
423 | return -EINVAL; | ||
424 | } | ||
425 | |||
426 | ret = iadc_read(iadc, IADC_REVISION2, &val); | ||
427 | if (ret < 0) | ||
428 | return ret; | ||
429 | |||
430 | if (val < IADC_REVISION2_SUPPORTED_IADC) { | ||
431 | dev_err(iadc->dev, "revision %d not supported\n", val); | ||
432 | return -EINVAL; | ||
433 | } | ||
434 | |||
435 | return 0; | ||
436 | } | ||
437 | |||
438 | static int iadc_rsense_read(struct iadc_chip *iadc, struct device_node *node) | ||
439 | { | ||
440 | int ret, sign, int_sense; | ||
441 | u8 deviation; | ||
442 | |||
443 | ret = of_property_read_u32(node, "qcom,external-resistor-micro-ohms", | ||
444 | &iadc->rsense[IADC_EXT_RSENSE]); | ||
445 | if (ret < 0) | ||
446 | iadc->rsense[IADC_EXT_RSENSE] = IADC_INT_RSENSE_IDEAL_VALUE; | ||
447 | |||
448 | if (!iadc->rsense[IADC_EXT_RSENSE]) { | ||
449 | dev_err(iadc->dev, "external resistor can't be zero Ohms"); | ||
450 | return -EINVAL; | ||
451 | } | ||
452 | |||
453 | ret = iadc_read(iadc, IADC_NOMINAL_RSENSE, &deviation); | ||
454 | if (ret < 0) | ||
455 | return ret; | ||
456 | |||
457 | /* | ||
458 | * Deviation value stored is an offset from 10 mili Ohms, bit 7 is | ||
459 | * the sign, the remaining bits have an LSB of 15625 nano Ohms. | ||
460 | */ | ||
461 | sign = (deviation & IADC_NOMINAL_RSENSE_SIGN_MASK) ? -1 : 1; | ||
462 | |||
463 | deviation &= ~IADC_NOMINAL_RSENSE_SIGN_MASK; | ||
464 | |||
465 | /* Scale it to nono Ohms */ | ||
466 | int_sense = IADC_INT_RSENSE_IDEAL_VALUE * 1000; | ||
467 | int_sense += sign * deviation * IADC_INT_RSENSE_DEVIATION; | ||
468 | int_sense /= 1000; /* micro Ohms */ | ||
469 | |||
470 | iadc->rsense[IADC_INT_RSENSE] = int_sense; | ||
471 | return 0; | ||
472 | } | ||
473 | |||
474 | static const struct iio_chan_spec iadc_channels[] = { | ||
475 | { | ||
476 | .type = IIO_CURRENT, | ||
477 | .datasheet_name = "INTERNAL_RSENSE", | ||
478 | .channel = 0, | ||
479 | .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | | ||
480 | BIT(IIO_CHAN_INFO_SCALE), | ||
481 | .indexed = 1, | ||
482 | }, | ||
483 | { | ||
484 | .type = IIO_CURRENT, | ||
485 | .datasheet_name = "EXTERNAL_RSENSE", | ||
486 | .channel = 1, | ||
487 | .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | | ||
488 | BIT(IIO_CHAN_INFO_SCALE), | ||
489 | .indexed = 1, | ||
490 | }, | ||
491 | }; | ||
492 | |||
493 | static int iadc_probe(struct platform_device *pdev) | ||
494 | { | ||
495 | struct device_node *node = pdev->dev.of_node; | ||
496 | struct device *dev = &pdev->dev; | ||
497 | struct iio_dev *indio_dev; | ||
498 | struct iadc_chip *iadc; | ||
499 | int ret, irq_eoc; | ||
500 | u32 res; | ||
501 | |||
502 | indio_dev = devm_iio_device_alloc(dev, sizeof(*iadc)); | ||
503 | if (!indio_dev) | ||
504 | return -ENOMEM; | ||
505 | |||
506 | iadc = iio_priv(indio_dev); | ||
507 | iadc->dev = dev; | ||
508 | |||
509 | iadc->regmap = dev_get_regmap(dev->parent, NULL); | ||
510 | if (!iadc->regmap) | ||
511 | return -ENODEV; | ||
512 | |||
513 | init_completion(&iadc->complete); | ||
514 | mutex_init(&iadc->lock); | ||
515 | |||
516 | ret = of_property_read_u32(node, "reg", &res); | ||
517 | if (ret < 0) | ||
518 | return -ENODEV; | ||
519 | |||
520 | iadc->base = res; | ||
521 | |||
522 | ret = iadc_version_check(iadc); | ||
523 | if (ret < 0) | ||
524 | return -ENODEV; | ||
525 | |||
526 | ret = iadc_rsense_read(iadc, node); | ||
527 | if (ret < 0) | ||
528 | return -ENODEV; | ||
529 | |||
530 | dev_dbg(iadc->dev, "sense resistors %d and %d micro Ohm\n", | ||
531 | iadc->rsense[IADC_INT_RSENSE], | ||
532 | iadc->rsense[IADC_EXT_RSENSE]); | ||
533 | |||
534 | irq_eoc = platform_get_irq(pdev, 0); | ||
535 | if (irq_eoc == -EPROBE_DEFER) | ||
536 | return irq_eoc; | ||
537 | |||
538 | if (irq_eoc < 0) | ||
539 | iadc->poll_eoc = true; | ||
540 | |||
541 | ret = iadc_reset(iadc); | ||
542 | if (ret < 0) { | ||
543 | dev_err(dev, "reset failed\n"); | ||
544 | return ret; | ||
545 | } | ||
546 | |||
547 | if (!iadc->poll_eoc) { | ||
548 | ret = devm_request_irq(dev, irq_eoc, iadc_isr, 0, | ||
549 | "spmi-iadc", iadc); | ||
550 | if (!ret) | ||
551 | enable_irq_wake(irq_eoc); | ||
552 | else | ||
553 | return ret; | ||
554 | } else { | ||
555 | device_init_wakeup(iadc->dev, 1); | ||
556 | } | ||
557 | |||
558 | ret = iadc_update_offset(iadc); | ||
559 | if (ret < 0) { | ||
560 | dev_err(dev, "failed offset calibration\n"); | ||
561 | return ret; | ||
562 | } | ||
563 | |||
564 | indio_dev->dev.parent = dev; | ||
565 | indio_dev->dev.of_node = node; | ||
566 | indio_dev->name = pdev->name; | ||
567 | indio_dev->modes = INDIO_DIRECT_MODE; | ||
568 | indio_dev->info = &iadc_info; | ||
569 | indio_dev->channels = iadc_channels; | ||
570 | indio_dev->num_channels = ARRAY_SIZE(iadc_channels); | ||
571 | |||
572 | return devm_iio_device_register(dev, indio_dev); | ||
573 | } | ||
574 | |||
575 | static const struct of_device_id iadc_match_table[] = { | ||
576 | { .compatible = "qcom,spmi-iadc" }, | ||
577 | { } | ||
578 | }; | ||
579 | |||
580 | MODULE_DEVICE_TABLE(of, iadc_match_table); | ||
581 | |||
582 | static struct platform_driver iadc_driver = { | ||
583 | .driver = { | ||
584 | .name = "qcom-spmi-iadc", | ||
585 | .of_match_table = iadc_match_table, | ||
586 | }, | ||
587 | .probe = iadc_probe, | ||
588 | }; | ||
589 | |||
590 | module_platform_driver(iadc_driver); | ||
591 | |||
592 | MODULE_ALIAS("platform:qcom-spmi-iadc"); | ||
593 | MODULE_DESCRIPTION("Qualcomm SPMI PMIC current ADC driver"); | ||
594 | MODULE_LICENSE("GPL v2"); | ||
595 | MODULE_AUTHOR("Ivan T. Ivanov <iivanov@mm-sol.com>"); | ||
diff --git a/drivers/iio/adc/rockchip_saradc.c b/drivers/iio/adc/rockchip_saradc.c index e074a0b03f28..b546bc1a9c30 100644 --- a/drivers/iio/adc/rockchip_saradc.c +++ b/drivers/iio/adc/rockchip_saradc.c | |||
@@ -18,13 +18,13 @@ | |||
18 | #include <linux/interrupt.h> | 18 | #include <linux/interrupt.h> |
19 | #include <linux/io.h> | 19 | #include <linux/io.h> |
20 | #include <linux/of.h> | 20 | #include <linux/of.h> |
21 | #include <linux/of_device.h> | ||
21 | #include <linux/clk.h> | 22 | #include <linux/clk.h> |
22 | #include <linux/completion.h> | 23 | #include <linux/completion.h> |
23 | #include <linux/regulator/consumer.h> | 24 | #include <linux/regulator/consumer.h> |
24 | #include <linux/iio/iio.h> | 25 | #include <linux/iio/iio.h> |
25 | 26 | ||
26 | #define SARADC_DATA 0x00 | 27 | #define SARADC_DATA 0x00 |
27 | #define SARADC_DATA_MASK 0x3ff | ||
28 | 28 | ||
29 | #define SARADC_STAS 0x04 | 29 | #define SARADC_STAS 0x04 |
30 | #define SARADC_STAS_BUSY BIT(0) | 30 | #define SARADC_STAS_BUSY BIT(0) |
@@ -38,15 +38,22 @@ | |||
38 | #define SARADC_DLY_PU_SOC 0x0c | 38 | #define SARADC_DLY_PU_SOC 0x0c |
39 | #define SARADC_DLY_PU_SOC_MASK 0x3f | 39 | #define SARADC_DLY_PU_SOC_MASK 0x3f |
40 | 40 | ||
41 | #define SARADC_BITS 10 | ||
42 | #define SARADC_TIMEOUT msecs_to_jiffies(100) | 41 | #define SARADC_TIMEOUT msecs_to_jiffies(100) |
43 | 42 | ||
43 | struct rockchip_saradc_data { | ||
44 | int num_bits; | ||
45 | const struct iio_chan_spec *channels; | ||
46 | int num_channels; | ||
47 | unsigned long clk_rate; | ||
48 | }; | ||
49 | |||
44 | struct rockchip_saradc { | 50 | struct rockchip_saradc { |
45 | void __iomem *regs; | 51 | void __iomem *regs; |
46 | struct clk *pclk; | 52 | struct clk *pclk; |
47 | struct clk *clk; | 53 | struct clk *clk; |
48 | struct completion completion; | 54 | struct completion completion; |
49 | struct regulator *vref; | 55 | struct regulator *vref; |
56 | const struct rockchip_saradc_data *data; | ||
50 | u16 last_val; | 57 | u16 last_val; |
51 | }; | 58 | }; |
52 | 59 | ||
@@ -90,7 +97,7 @@ static int rockchip_saradc_read_raw(struct iio_dev *indio_dev, | |||
90 | } | 97 | } |
91 | 98 | ||
92 | *val = ret / 1000; | 99 | *val = ret / 1000; |
93 | *val2 = SARADC_BITS; | 100 | *val2 = info->data->num_bits; |
94 | return IIO_VAL_FRACTIONAL_LOG2; | 101 | return IIO_VAL_FRACTIONAL_LOG2; |
95 | default: | 102 | default: |
96 | return -EINVAL; | 103 | return -EINVAL; |
@@ -103,7 +110,7 @@ static irqreturn_t rockchip_saradc_isr(int irq, void *dev_id) | |||
103 | 110 | ||
104 | /* Read value */ | 111 | /* Read value */ |
105 | info->last_val = readl_relaxed(info->regs + SARADC_DATA); | 112 | info->last_val = readl_relaxed(info->regs + SARADC_DATA); |
106 | info->last_val &= SARADC_DATA_MASK; | 113 | info->last_val &= GENMASK(info->data->num_bits - 1, 0); |
107 | 114 | ||
108 | /* Clear irq & power down adc */ | 115 | /* Clear irq & power down adc */ |
109 | writel_relaxed(0, info->regs + SARADC_CTRL); | 116 | writel_relaxed(0, info->regs + SARADC_CTRL); |
@@ -133,12 +140,44 @@ static const struct iio_chan_spec rockchip_saradc_iio_channels[] = { | |||
133 | ADC_CHANNEL(2, "adc2"), | 140 | ADC_CHANNEL(2, "adc2"), |
134 | }; | 141 | }; |
135 | 142 | ||
143 | static const struct rockchip_saradc_data saradc_data = { | ||
144 | .num_bits = 10, | ||
145 | .channels = rockchip_saradc_iio_channels, | ||
146 | .num_channels = ARRAY_SIZE(rockchip_saradc_iio_channels), | ||
147 | .clk_rate = 1000000, | ||
148 | }; | ||
149 | |||
150 | static const struct iio_chan_spec rockchip_rk3066_tsadc_iio_channels[] = { | ||
151 | ADC_CHANNEL(0, "adc0"), | ||
152 | ADC_CHANNEL(1, "adc1"), | ||
153 | }; | ||
154 | |||
155 | static const struct rockchip_saradc_data rk3066_tsadc_data = { | ||
156 | .num_bits = 12, | ||
157 | .channels = rockchip_rk3066_tsadc_iio_channels, | ||
158 | .num_channels = ARRAY_SIZE(rockchip_rk3066_tsadc_iio_channels), | ||
159 | .clk_rate = 50000, | ||
160 | }; | ||
161 | |||
162 | static const struct of_device_id rockchip_saradc_match[] = { | ||
163 | { | ||
164 | .compatible = "rockchip,saradc", | ||
165 | .data = &saradc_data, | ||
166 | }, { | ||
167 | .compatible = "rockchip,rk3066-tsadc", | ||
168 | .data = &rk3066_tsadc_data, | ||
169 | }, | ||
170 | {}, | ||
171 | }; | ||
172 | MODULE_DEVICE_TABLE(of, rockchip_saradc_match); | ||
173 | |||
136 | static int rockchip_saradc_probe(struct platform_device *pdev) | 174 | static int rockchip_saradc_probe(struct platform_device *pdev) |
137 | { | 175 | { |
138 | struct rockchip_saradc *info = NULL; | 176 | struct rockchip_saradc *info = NULL; |
139 | struct device_node *np = pdev->dev.of_node; | 177 | struct device_node *np = pdev->dev.of_node; |
140 | struct iio_dev *indio_dev = NULL; | 178 | struct iio_dev *indio_dev = NULL; |
141 | struct resource *mem; | 179 | struct resource *mem; |
180 | const struct of_device_id *match; | ||
142 | int ret; | 181 | int ret; |
143 | int irq; | 182 | int irq; |
144 | 183 | ||
@@ -152,6 +191,9 @@ static int rockchip_saradc_probe(struct platform_device *pdev) | |||
152 | } | 191 | } |
153 | info = iio_priv(indio_dev); | 192 | info = iio_priv(indio_dev); |
154 | 193 | ||
194 | match = of_match_device(rockchip_saradc_match, &pdev->dev); | ||
195 | info->data = match->data; | ||
196 | |||
155 | mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 197 | mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
156 | info->regs = devm_ioremap_resource(&pdev->dev, mem); | 198 | info->regs = devm_ioremap_resource(&pdev->dev, mem); |
157 | if (IS_ERR(info->regs)) | 199 | if (IS_ERR(info->regs)) |
@@ -192,10 +234,10 @@ static int rockchip_saradc_probe(struct platform_device *pdev) | |||
192 | } | 234 | } |
193 | 235 | ||
194 | /* | 236 | /* |
195 | * Use a default of 1MHz for the converter clock. | 237 | * Use a default value for the converter clock. |
196 | * This may become user-configurable in the future. | 238 | * This may become user-configurable in the future. |
197 | */ | 239 | */ |
198 | ret = clk_set_rate(info->clk, 1000000); | 240 | ret = clk_set_rate(info->clk, info->data->clk_rate); |
199 | if (ret < 0) { | 241 | if (ret < 0) { |
200 | dev_err(&pdev->dev, "failed to set adc clk rate, %d\n", ret); | 242 | dev_err(&pdev->dev, "failed to set adc clk rate, %d\n", ret); |
201 | return ret; | 243 | return ret; |
@@ -227,8 +269,8 @@ static int rockchip_saradc_probe(struct platform_device *pdev) | |||
227 | indio_dev->info = &rockchip_saradc_iio_info; | 269 | indio_dev->info = &rockchip_saradc_iio_info; |
228 | indio_dev->modes = INDIO_DIRECT_MODE; | 270 | indio_dev->modes = INDIO_DIRECT_MODE; |
229 | 271 | ||
230 | indio_dev->channels = rockchip_saradc_iio_channels; | 272 | indio_dev->channels = info->data->channels; |
231 | indio_dev->num_channels = ARRAY_SIZE(rockchip_saradc_iio_channels); | 273 | indio_dev->num_channels = info->data->num_channels; |
232 | 274 | ||
233 | ret = iio_device_register(indio_dev); | 275 | ret = iio_device_register(indio_dev); |
234 | if (ret) | 276 | if (ret) |
@@ -296,12 +338,6 @@ static int rockchip_saradc_resume(struct device *dev) | |||
296 | static SIMPLE_DEV_PM_OPS(rockchip_saradc_pm_ops, | 338 | static SIMPLE_DEV_PM_OPS(rockchip_saradc_pm_ops, |
297 | rockchip_saradc_suspend, rockchip_saradc_resume); | 339 | rockchip_saradc_suspend, rockchip_saradc_resume); |
298 | 340 | ||
299 | static const struct of_device_id rockchip_saradc_match[] = { | ||
300 | { .compatible = "rockchip,saradc" }, | ||
301 | {}, | ||
302 | }; | ||
303 | MODULE_DEVICE_TABLE(of, rockchip_saradc_match); | ||
304 | |||
305 | static struct platform_driver rockchip_saradc_driver = { | 341 | static struct platform_driver rockchip_saradc_driver = { |
306 | .probe = rockchip_saradc_probe, | 342 | .probe = rockchip_saradc_probe, |
307 | .remove = rockchip_saradc_remove, | 343 | .remove = rockchip_saradc_remove, |
diff --git a/drivers/iio/adc/vf610_adc.c b/drivers/iio/adc/vf610_adc.c index 4a10ae97dbf2..8ec353c01d98 100644 --- a/drivers/iio/adc/vf610_adc.c +++ b/drivers/iio/adc/vf610_adc.c | |||
@@ -91,7 +91,7 @@ | |||
91 | #define VF610_ADC_CAL 0x80 | 91 | #define VF610_ADC_CAL 0x80 |
92 | 92 | ||
93 | /* Other field define */ | 93 | /* Other field define */ |
94 | #define VF610_ADC_ADCHC(x) ((x) & 0xF) | 94 | #define VF610_ADC_ADCHC(x) ((x) & 0x1F) |
95 | #define VF610_ADC_AIEN (0x1 << 7) | 95 | #define VF610_ADC_AIEN (0x1 << 7) |
96 | #define VF610_ADC_CONV_DISABLE 0x1F | 96 | #define VF610_ADC_CONV_DISABLE 0x1F |
97 | #define VF610_ADC_HS_COCO0 0x1 | 97 | #define VF610_ADC_HS_COCO0 0x1 |
@@ -153,6 +153,12 @@ struct vf610_adc { | |||
153 | BIT(IIO_CHAN_INFO_SAMP_FREQ), \ | 153 | BIT(IIO_CHAN_INFO_SAMP_FREQ), \ |
154 | } | 154 | } |
155 | 155 | ||
156 | #define VF610_ADC_TEMPERATURE_CHAN(_idx, _chan_type) { \ | ||
157 | .type = (_chan_type), \ | ||
158 | .channel = (_idx), \ | ||
159 | .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED), \ | ||
160 | } | ||
161 | |||
156 | static const struct iio_chan_spec vf610_adc_iio_channels[] = { | 162 | static const struct iio_chan_spec vf610_adc_iio_channels[] = { |
157 | VF610_ADC_CHAN(0, IIO_VOLTAGE), | 163 | VF610_ADC_CHAN(0, IIO_VOLTAGE), |
158 | VF610_ADC_CHAN(1, IIO_VOLTAGE), | 164 | VF610_ADC_CHAN(1, IIO_VOLTAGE), |
@@ -170,6 +176,7 @@ static const struct iio_chan_spec vf610_adc_iio_channels[] = { | |||
170 | VF610_ADC_CHAN(13, IIO_VOLTAGE), | 176 | VF610_ADC_CHAN(13, IIO_VOLTAGE), |
171 | VF610_ADC_CHAN(14, IIO_VOLTAGE), | 177 | VF610_ADC_CHAN(14, IIO_VOLTAGE), |
172 | VF610_ADC_CHAN(15, IIO_VOLTAGE), | 178 | VF610_ADC_CHAN(15, IIO_VOLTAGE), |
179 | VF610_ADC_TEMPERATURE_CHAN(26, IIO_TEMP), | ||
173 | /* sentinel */ | 180 | /* sentinel */ |
174 | }; | 181 | }; |
175 | 182 | ||
@@ -451,6 +458,7 @@ static int vf610_read_raw(struct iio_dev *indio_dev, | |||
451 | 458 | ||
452 | switch (mask) { | 459 | switch (mask) { |
453 | case IIO_CHAN_INFO_RAW: | 460 | case IIO_CHAN_INFO_RAW: |
461 | case IIO_CHAN_INFO_PROCESSED: | ||
454 | mutex_lock(&indio_dev->mlock); | 462 | mutex_lock(&indio_dev->mlock); |
455 | reinit_completion(&info->completion); | 463 | reinit_completion(&info->completion); |
456 | 464 | ||
@@ -468,7 +476,23 @@ static int vf610_read_raw(struct iio_dev *indio_dev, | |||
468 | return ret; | 476 | return ret; |
469 | } | 477 | } |
470 | 478 | ||
471 | *val = info->value; | 479 | switch (chan->type) { |
480 | case IIO_VOLTAGE: | ||
481 | *val = info->value; | ||
482 | break; | ||
483 | case IIO_TEMP: | ||
484 | /* | ||
485 | * Calculate in degree Celsius times 1000 | ||
486 | * Using sensor slope of 1.84 mV/°C and | ||
487 | * V at 25°C of 696 mV | ||
488 | */ | ||
489 | *val = 25000 - ((int)info->value - 864) * 1000000 / 1840; | ||
490 | break; | ||
491 | default: | ||
492 | mutex_unlock(&indio_dev->mlock); | ||
493 | return -EINVAL; | ||
494 | } | ||
495 | |||
472 | mutex_unlock(&indio_dev->mlock); | 496 | mutex_unlock(&indio_dev->mlock); |
473 | return IIO_VAL_INT; | 497 | return IIO_VAL_INT; |
474 | 498 | ||
@@ -569,9 +593,9 @@ static int vf610_adc_probe(struct platform_device *pdev) | |||
569 | return PTR_ERR(info->regs); | 593 | return PTR_ERR(info->regs); |
570 | 594 | ||
571 | irq = platform_get_irq(pdev, 0); | 595 | irq = platform_get_irq(pdev, 0); |
572 | if (irq <= 0) { | 596 | if (irq < 0) { |
573 | dev_err(&pdev->dev, "no irq resource?\n"); | 597 | dev_err(&pdev->dev, "no irq resource?\n"); |
574 | return -EINVAL; | 598 | return irq; |
575 | } | 599 | } |
576 | 600 | ||
577 | ret = devm_request_irq(info->dev, irq, | 601 | ret = devm_request_irq(info->dev, irq, |
@@ -586,8 +610,7 @@ static int vf610_adc_probe(struct platform_device *pdev) | |||
586 | if (IS_ERR(info->clk)) { | 610 | if (IS_ERR(info->clk)) { |
587 | dev_err(&pdev->dev, "failed getting clock, err = %ld\n", | 611 | dev_err(&pdev->dev, "failed getting clock, err = %ld\n", |
588 | PTR_ERR(info->clk)); | 612 | PTR_ERR(info->clk)); |
589 | ret = PTR_ERR(info->clk); | 613 | return PTR_ERR(info->clk); |
590 | return ret; | ||
591 | } | 614 | } |
592 | 615 | ||
593 | info->vref = devm_regulator_get(&pdev->dev, "vref"); | 616 | info->vref = devm_regulator_get(&pdev->dev, "vref"); |
@@ -681,17 +704,19 @@ static int vf610_adc_resume(struct device *dev) | |||
681 | 704 | ||
682 | ret = clk_prepare_enable(info->clk); | 705 | ret = clk_prepare_enable(info->clk); |
683 | if (ret) | 706 | if (ret) |
684 | return ret; | 707 | goto disable_reg; |
685 | 708 | ||
686 | vf610_adc_hw_init(info); | 709 | vf610_adc_hw_init(info); |
687 | 710 | ||
688 | return 0; | 711 | return 0; |
712 | |||
713 | disable_reg: | ||
714 | regulator_disable(info->vref); | ||
715 | return ret; | ||
689 | } | 716 | } |
690 | #endif | 717 | #endif |
691 | 718 | ||
692 | static SIMPLE_DEV_PM_OPS(vf610_adc_pm_ops, | 719 | static SIMPLE_DEV_PM_OPS(vf610_adc_pm_ops, vf610_adc_suspend, vf610_adc_resume); |
693 | vf610_adc_suspend, | ||
694 | vf610_adc_resume); | ||
695 | 720 | ||
696 | static struct platform_driver vf610_adc_driver = { | 721 | static struct platform_driver vf610_adc_driver = { |
697 | .probe = vf610_adc_probe, | 722 | .probe = vf610_adc_probe, |
diff --git a/drivers/iio/common/st_sensors/st_sensors_core.c b/drivers/iio/common/st_sensors/st_sensors_core.c index 24cfe4e044f9..edd13d2b4121 100644 --- a/drivers/iio/common/st_sensors/st_sensors_core.c +++ b/drivers/iio/common/st_sensors/st_sensors_core.c | |||
@@ -44,18 +44,18 @@ st_sensors_write_data_with_mask_error: | |||
44 | return err; | 44 | return err; |
45 | } | 45 | } |
46 | 46 | ||
47 | static int st_sensors_match_odr(struct st_sensors *sensor, | 47 | static int st_sensors_match_odr(struct st_sensor_settings *sensor_settings, |
48 | unsigned int odr, struct st_sensor_odr_avl *odr_out) | 48 | unsigned int odr, struct st_sensor_odr_avl *odr_out) |
49 | { | 49 | { |
50 | int i, ret = -EINVAL; | 50 | int i, ret = -EINVAL; |
51 | 51 | ||
52 | for (i = 0; i < ST_SENSORS_ODR_LIST_MAX; i++) { | 52 | for (i = 0; i < ST_SENSORS_ODR_LIST_MAX; i++) { |
53 | if (sensor->odr.odr_avl[i].hz == 0) | 53 | if (sensor_settings->odr.odr_avl[i].hz == 0) |
54 | goto st_sensors_match_odr_error; | 54 | goto st_sensors_match_odr_error; |
55 | 55 | ||
56 | if (sensor->odr.odr_avl[i].hz == odr) { | 56 | if (sensor_settings->odr.odr_avl[i].hz == odr) { |
57 | odr_out->hz = sensor->odr.odr_avl[i].hz; | 57 | odr_out->hz = sensor_settings->odr.odr_avl[i].hz; |
58 | odr_out->value = sensor->odr.odr_avl[i].value; | 58 | odr_out->value = sensor_settings->odr.odr_avl[i].value; |
59 | ret = 0; | 59 | ret = 0; |
60 | break; | 60 | break; |
61 | } | 61 | } |
@@ -71,23 +71,26 @@ int st_sensors_set_odr(struct iio_dev *indio_dev, unsigned int odr) | |||
71 | struct st_sensor_odr_avl odr_out = {0, 0}; | 71 | struct st_sensor_odr_avl odr_out = {0, 0}; |
72 | struct st_sensor_data *sdata = iio_priv(indio_dev); | 72 | struct st_sensor_data *sdata = iio_priv(indio_dev); |
73 | 73 | ||
74 | err = st_sensors_match_odr(sdata->sensor, odr, &odr_out); | 74 | err = st_sensors_match_odr(sdata->sensor_settings, odr, &odr_out); |
75 | if (err < 0) | 75 | if (err < 0) |
76 | goto st_sensors_match_odr_error; | 76 | goto st_sensors_match_odr_error; |
77 | 77 | ||
78 | if ((sdata->sensor->odr.addr == sdata->sensor->pw.addr) && | 78 | if ((sdata->sensor_settings->odr.addr == |
79 | (sdata->sensor->odr.mask == sdata->sensor->pw.mask)) { | 79 | sdata->sensor_settings->pw.addr) && |
80 | (sdata->sensor_settings->odr.mask == | ||
81 | sdata->sensor_settings->pw.mask)) { | ||
80 | if (sdata->enabled == true) { | 82 | if (sdata->enabled == true) { |
81 | err = st_sensors_write_data_with_mask(indio_dev, | 83 | err = st_sensors_write_data_with_mask(indio_dev, |
82 | sdata->sensor->odr.addr, | 84 | sdata->sensor_settings->odr.addr, |
83 | sdata->sensor->odr.mask, | 85 | sdata->sensor_settings->odr.mask, |
84 | odr_out.value); | 86 | odr_out.value); |
85 | } else { | 87 | } else { |
86 | err = 0; | 88 | err = 0; |
87 | } | 89 | } |
88 | } else { | 90 | } else { |
89 | err = st_sensors_write_data_with_mask(indio_dev, | 91 | err = st_sensors_write_data_with_mask(indio_dev, |
90 | sdata->sensor->odr.addr, sdata->sensor->odr.mask, | 92 | sdata->sensor_settings->odr.addr, |
93 | sdata->sensor_settings->odr.mask, | ||
91 | odr_out.value); | 94 | odr_out.value); |
92 | } | 95 | } |
93 | if (err >= 0) | 96 | if (err >= 0) |
@@ -98,16 +101,16 @@ st_sensors_match_odr_error: | |||
98 | } | 101 | } |
99 | EXPORT_SYMBOL(st_sensors_set_odr); | 102 | EXPORT_SYMBOL(st_sensors_set_odr); |
100 | 103 | ||
101 | static int st_sensors_match_fs(struct st_sensors *sensor, | 104 | static int st_sensors_match_fs(struct st_sensor_settings *sensor_settings, |
102 | unsigned int fs, int *index_fs_avl) | 105 | unsigned int fs, int *index_fs_avl) |
103 | { | 106 | { |
104 | int i, ret = -EINVAL; | 107 | int i, ret = -EINVAL; |
105 | 108 | ||
106 | for (i = 0; i < ST_SENSORS_FULLSCALE_AVL_MAX; i++) { | 109 | for (i = 0; i < ST_SENSORS_FULLSCALE_AVL_MAX; i++) { |
107 | if (sensor->fs.fs_avl[i].num == 0) | 110 | if (sensor_settings->fs.fs_avl[i].num == 0) |
108 | goto st_sensors_match_odr_error; | 111 | goto st_sensors_match_odr_error; |
109 | 112 | ||
110 | if (sensor->fs.fs_avl[i].num == fs) { | 113 | if (sensor_settings->fs.fs_avl[i].num == fs) { |
111 | *index_fs_avl = i; | 114 | *index_fs_avl = i; |
112 | ret = 0; | 115 | ret = 0; |
113 | break; | 116 | break; |
@@ -118,25 +121,24 @@ st_sensors_match_odr_error: | |||
118 | return ret; | 121 | return ret; |
119 | } | 122 | } |
120 | 123 | ||
121 | static int st_sensors_set_fullscale(struct iio_dev *indio_dev, | 124 | static int st_sensors_set_fullscale(struct iio_dev *indio_dev, unsigned int fs) |
122 | unsigned int fs) | ||
123 | { | 125 | { |
124 | int err, i = 0; | 126 | int err, i = 0; |
125 | struct st_sensor_data *sdata = iio_priv(indio_dev); | 127 | struct st_sensor_data *sdata = iio_priv(indio_dev); |
126 | 128 | ||
127 | err = st_sensors_match_fs(sdata->sensor, fs, &i); | 129 | err = st_sensors_match_fs(sdata->sensor_settings, fs, &i); |
128 | if (err < 0) | 130 | if (err < 0) |
129 | goto st_accel_set_fullscale_error; | 131 | goto st_accel_set_fullscale_error; |
130 | 132 | ||
131 | err = st_sensors_write_data_with_mask(indio_dev, | 133 | err = st_sensors_write_data_with_mask(indio_dev, |
132 | sdata->sensor->fs.addr, | 134 | sdata->sensor_settings->fs.addr, |
133 | sdata->sensor->fs.mask, | 135 | sdata->sensor_settings->fs.mask, |
134 | sdata->sensor->fs.fs_avl[i].value); | 136 | sdata->sensor_settings->fs.fs_avl[i].value); |
135 | if (err < 0) | 137 | if (err < 0) |
136 | goto st_accel_set_fullscale_error; | 138 | goto st_accel_set_fullscale_error; |
137 | 139 | ||
138 | sdata->current_fullscale = (struct st_sensor_fullscale_avl *) | 140 | sdata->current_fullscale = (struct st_sensor_fullscale_avl *) |
139 | &sdata->sensor->fs.fs_avl[i]; | 141 | &sdata->sensor_settings->fs.fs_avl[i]; |
140 | return err; | 142 | return err; |
141 | 143 | ||
142 | st_accel_set_fullscale_error: | 144 | st_accel_set_fullscale_error: |
@@ -153,10 +155,12 @@ int st_sensors_set_enable(struct iio_dev *indio_dev, bool enable) | |||
153 | struct st_sensor_data *sdata = iio_priv(indio_dev); | 155 | struct st_sensor_data *sdata = iio_priv(indio_dev); |
154 | 156 | ||
155 | if (enable) { | 157 | if (enable) { |
156 | tmp_value = sdata->sensor->pw.value_on; | 158 | tmp_value = sdata->sensor_settings->pw.value_on; |
157 | if ((sdata->sensor->odr.addr == sdata->sensor->pw.addr) && | 159 | if ((sdata->sensor_settings->odr.addr == |
158 | (sdata->sensor->odr.mask == sdata->sensor->pw.mask)) { | 160 | sdata->sensor_settings->pw.addr) && |
159 | err = st_sensors_match_odr(sdata->sensor, | 161 | (sdata->sensor_settings->odr.mask == |
162 | sdata->sensor_settings->pw.mask)) { | ||
163 | err = st_sensors_match_odr(sdata->sensor_settings, | ||
160 | sdata->odr, &odr_out); | 164 | sdata->odr, &odr_out); |
161 | if (err < 0) | 165 | if (err < 0) |
162 | goto set_enable_error; | 166 | goto set_enable_error; |
@@ -164,8 +168,8 @@ int st_sensors_set_enable(struct iio_dev *indio_dev, bool enable) | |||
164 | found = true; | 168 | found = true; |
165 | } | 169 | } |
166 | err = st_sensors_write_data_with_mask(indio_dev, | 170 | err = st_sensors_write_data_with_mask(indio_dev, |
167 | sdata->sensor->pw.addr, | 171 | sdata->sensor_settings->pw.addr, |
168 | sdata->sensor->pw.mask, tmp_value); | 172 | sdata->sensor_settings->pw.mask, tmp_value); |
169 | if (err < 0) | 173 | if (err < 0) |
170 | goto set_enable_error; | 174 | goto set_enable_error; |
171 | 175 | ||
@@ -175,9 +179,9 @@ int st_sensors_set_enable(struct iio_dev *indio_dev, bool enable) | |||
175 | sdata->odr = odr_out.hz; | 179 | sdata->odr = odr_out.hz; |
176 | } else { | 180 | } else { |
177 | err = st_sensors_write_data_with_mask(indio_dev, | 181 | err = st_sensors_write_data_with_mask(indio_dev, |
178 | sdata->sensor->pw.addr, | 182 | sdata->sensor_settings->pw.addr, |
179 | sdata->sensor->pw.mask, | 183 | sdata->sensor_settings->pw.mask, |
180 | sdata->sensor->pw.value_off); | 184 | sdata->sensor_settings->pw.value_off); |
181 | if (err < 0) | 185 | if (err < 0) |
182 | goto set_enable_error; | 186 | goto set_enable_error; |
183 | 187 | ||
@@ -194,8 +198,9 @@ int st_sensors_set_axis_enable(struct iio_dev *indio_dev, u8 axis_enable) | |||
194 | struct st_sensor_data *sdata = iio_priv(indio_dev); | 198 | struct st_sensor_data *sdata = iio_priv(indio_dev); |
195 | 199 | ||
196 | return st_sensors_write_data_with_mask(indio_dev, | 200 | return st_sensors_write_data_with_mask(indio_dev, |
197 | sdata->sensor->enable_axis.addr, | 201 | sdata->sensor_settings->enable_axis.addr, |
198 | sdata->sensor->enable_axis.mask, axis_enable); | 202 | sdata->sensor_settings->enable_axis.mask, |
203 | axis_enable); | ||
199 | } | 204 | } |
200 | EXPORT_SYMBOL(st_sensors_set_axis_enable); | 205 | EXPORT_SYMBOL(st_sensors_set_axis_enable); |
201 | 206 | ||
@@ -236,13 +241,13 @@ void st_sensors_power_disable(struct iio_dev *indio_dev) | |||
236 | EXPORT_SYMBOL(st_sensors_power_disable); | 241 | EXPORT_SYMBOL(st_sensors_power_disable); |
237 | 242 | ||
238 | static int st_sensors_set_drdy_int_pin(struct iio_dev *indio_dev, | 243 | static int st_sensors_set_drdy_int_pin(struct iio_dev *indio_dev, |
239 | struct st_sensors_platform_data *pdata) | 244 | struct st_sensors_platform_data *pdata) |
240 | { | 245 | { |
241 | struct st_sensor_data *sdata = iio_priv(indio_dev); | 246 | struct st_sensor_data *sdata = iio_priv(indio_dev); |
242 | 247 | ||
243 | switch (pdata->drdy_int_pin) { | 248 | switch (pdata->drdy_int_pin) { |
244 | case 1: | 249 | case 1: |
245 | if (sdata->sensor->drdy_irq.mask_int1 == 0) { | 250 | if (sdata->sensor_settings->drdy_irq.mask_int1 == 0) { |
246 | dev_err(&indio_dev->dev, | 251 | dev_err(&indio_dev->dev, |
247 | "DRDY on INT1 not available.\n"); | 252 | "DRDY on INT1 not available.\n"); |
248 | return -EINVAL; | 253 | return -EINVAL; |
@@ -250,7 +255,7 @@ static int st_sensors_set_drdy_int_pin(struct iio_dev *indio_dev, | |||
250 | sdata->drdy_int_pin = 1; | 255 | sdata->drdy_int_pin = 1; |
251 | break; | 256 | break; |
252 | case 2: | 257 | case 2: |
253 | if (sdata->sensor->drdy_irq.mask_int2 == 0) { | 258 | if (sdata->sensor_settings->drdy_irq.mask_int2 == 0) { |
254 | dev_err(&indio_dev->dev, | 259 | dev_err(&indio_dev->dev, |
255 | "DRDY on INT2 not available.\n"); | 260 | "DRDY on INT2 not available.\n"); |
256 | return -EINVAL; | 261 | return -EINVAL; |
@@ -318,7 +323,7 @@ int st_sensors_init_sensor(struct iio_dev *indio_dev, | |||
318 | 323 | ||
319 | if (sdata->current_fullscale) { | 324 | if (sdata->current_fullscale) { |
320 | err = st_sensors_set_fullscale(indio_dev, | 325 | err = st_sensors_set_fullscale(indio_dev, |
321 | sdata->current_fullscale->num); | 326 | sdata->current_fullscale->num); |
322 | if (err < 0) | 327 | if (err < 0) |
323 | return err; | 328 | return err; |
324 | } else | 329 | } else |
@@ -330,7 +335,8 @@ int st_sensors_init_sensor(struct iio_dev *indio_dev, | |||
330 | 335 | ||
331 | /* set BDU */ | 336 | /* set BDU */ |
332 | err = st_sensors_write_data_with_mask(indio_dev, | 337 | err = st_sensors_write_data_with_mask(indio_dev, |
333 | sdata->sensor->bdu.addr, sdata->sensor->bdu.mask, true); | 338 | sdata->sensor_settings->bdu.addr, |
339 | sdata->sensor_settings->bdu.mask, true); | ||
334 | if (err < 0) | 340 | if (err < 0) |
335 | return err; | 341 | return err; |
336 | 342 | ||
@@ -346,26 +352,28 @@ int st_sensors_set_dataready_irq(struct iio_dev *indio_dev, bool enable) | |||
346 | u8 drdy_mask; | 352 | u8 drdy_mask; |
347 | struct st_sensor_data *sdata = iio_priv(indio_dev); | 353 | struct st_sensor_data *sdata = iio_priv(indio_dev); |
348 | 354 | ||
349 | if (!sdata->sensor->drdy_irq.addr) | 355 | if (!sdata->sensor_settings->drdy_irq.addr) |
350 | return 0; | 356 | return 0; |
351 | 357 | ||
352 | /* Enable/Disable the interrupt generator 1. */ | 358 | /* Enable/Disable the interrupt generator 1. */ |
353 | if (sdata->sensor->drdy_irq.ig1.en_addr > 0) { | 359 | if (sdata->sensor_settings->drdy_irq.ig1.en_addr > 0) { |
354 | err = st_sensors_write_data_with_mask(indio_dev, | 360 | err = st_sensors_write_data_with_mask(indio_dev, |
355 | sdata->sensor->drdy_irq.ig1.en_addr, | 361 | sdata->sensor_settings->drdy_irq.ig1.en_addr, |
356 | sdata->sensor->drdy_irq.ig1.en_mask, (int)enable); | 362 | sdata->sensor_settings->drdy_irq.ig1.en_mask, |
363 | (int)enable); | ||
357 | if (err < 0) | 364 | if (err < 0) |
358 | goto st_accel_set_dataready_irq_error; | 365 | goto st_accel_set_dataready_irq_error; |
359 | } | 366 | } |
360 | 367 | ||
361 | if (sdata->drdy_int_pin == 1) | 368 | if (sdata->drdy_int_pin == 1) |
362 | drdy_mask = sdata->sensor->drdy_irq.mask_int1; | 369 | drdy_mask = sdata->sensor_settings->drdy_irq.mask_int1; |
363 | else | 370 | else |
364 | drdy_mask = sdata->sensor->drdy_irq.mask_int2; | 371 | drdy_mask = sdata->sensor_settings->drdy_irq.mask_int2; |
365 | 372 | ||
366 | /* Enable/Disable the interrupt generator for data ready. */ | 373 | /* Enable/Disable the interrupt generator for data ready. */ |
367 | err = st_sensors_write_data_with_mask(indio_dev, | 374 | err = st_sensors_write_data_with_mask(indio_dev, |
368 | sdata->sensor->drdy_irq.addr, drdy_mask, (int)enable); | 375 | sdata->sensor_settings->drdy_irq.addr, |
376 | drdy_mask, (int)enable); | ||
369 | 377 | ||
370 | st_accel_set_dataready_irq_error: | 378 | st_accel_set_dataready_irq_error: |
371 | return err; | 379 | return err; |
@@ -378,8 +386,8 @@ int st_sensors_set_fullscale_by_gain(struct iio_dev *indio_dev, int scale) | |||
378 | struct st_sensor_data *sdata = iio_priv(indio_dev); | 386 | struct st_sensor_data *sdata = iio_priv(indio_dev); |
379 | 387 | ||
380 | for (i = 0; i < ST_SENSORS_FULLSCALE_AVL_MAX; i++) { | 388 | for (i = 0; i < ST_SENSORS_FULLSCALE_AVL_MAX; i++) { |
381 | if ((sdata->sensor->fs.fs_avl[i].gain == scale) && | 389 | if ((sdata->sensor_settings->fs.fs_avl[i].gain == scale) && |
382 | (sdata->sensor->fs.fs_avl[i].gain != 0)) { | 390 | (sdata->sensor_settings->fs.fs_avl[i].gain != 0)) { |
383 | err = 0; | 391 | err = 0; |
384 | break; | 392 | break; |
385 | } | 393 | } |
@@ -388,7 +396,7 @@ int st_sensors_set_fullscale_by_gain(struct iio_dev *indio_dev, int scale) | |||
388 | goto st_sensors_match_scale_error; | 396 | goto st_sensors_match_scale_error; |
389 | 397 | ||
390 | err = st_sensors_set_fullscale(indio_dev, | 398 | err = st_sensors_set_fullscale(indio_dev, |
391 | sdata->sensor->fs.fs_avl[i].num); | 399 | sdata->sensor_settings->fs.fs_avl[i].num); |
392 | 400 | ||
393 | st_sensors_match_scale_error: | 401 | st_sensors_match_scale_error: |
394 | return err; | 402 | return err; |
@@ -439,7 +447,7 @@ int st_sensors_read_info_raw(struct iio_dev *indio_dev, | |||
439 | if (err < 0) | 447 | if (err < 0) |
440 | goto out; | 448 | goto out; |
441 | 449 | ||
442 | msleep((sdata->sensor->bootime * 1000) / sdata->odr); | 450 | msleep((sdata->sensor_settings->bootime * 1000) / sdata->odr); |
443 | err = st_sensors_read_axis_data(indio_dev, ch, val); | 451 | err = st_sensors_read_axis_data(indio_dev, ch, val); |
444 | if (err < 0) | 452 | if (err < 0) |
445 | goto out; | 453 | goto out; |
@@ -456,7 +464,8 @@ out: | |||
456 | EXPORT_SYMBOL(st_sensors_read_info_raw); | 464 | EXPORT_SYMBOL(st_sensors_read_info_raw); |
457 | 465 | ||
458 | int st_sensors_check_device_support(struct iio_dev *indio_dev, | 466 | int st_sensors_check_device_support(struct iio_dev *indio_dev, |
459 | int num_sensors_list, const struct st_sensors *sensors) | 467 | int num_sensors_list, |
468 | const struct st_sensor_settings *sensor_settings) | ||
460 | { | 469 | { |
461 | u8 wai; | 470 | u8 wai; |
462 | int i, n, err; | 471 | int i, n, err; |
@@ -470,23 +479,24 @@ int st_sensors_check_device_support(struct iio_dev *indio_dev, | |||
470 | } | 479 | } |
471 | 480 | ||
472 | for (i = 0; i < num_sensors_list; i++) { | 481 | for (i = 0; i < num_sensors_list; i++) { |
473 | if (sensors[i].wai == wai) | 482 | if (sensor_settings[i].wai == wai) |
474 | break; | 483 | break; |
475 | } | 484 | } |
476 | if (i == num_sensors_list) | 485 | if (i == num_sensors_list) |
477 | goto device_not_supported; | 486 | goto device_not_supported; |
478 | 487 | ||
479 | for (n = 0; n < ARRAY_SIZE(sensors[i].sensors_supported); n++) { | 488 | for (n = 0; n < ARRAY_SIZE(sensor_settings[i].sensors_supported); n++) { |
480 | if (strcmp(indio_dev->name, | 489 | if (strcmp(indio_dev->name, |
481 | &sensors[i].sensors_supported[n][0]) == 0) | 490 | &sensor_settings[i].sensors_supported[n][0]) == 0) |
482 | break; | 491 | break; |
483 | } | 492 | } |
484 | if (n == ARRAY_SIZE(sensors[i].sensors_supported)) { | 493 | if (n == ARRAY_SIZE(sensor_settings[i].sensors_supported)) { |
485 | dev_err(&indio_dev->dev, "device name and WhoAmI mismatch.\n"); | 494 | dev_err(&indio_dev->dev, "device name and WhoAmI mismatch.\n"); |
486 | goto sensor_name_mismatch; | 495 | goto sensor_name_mismatch; |
487 | } | 496 | } |
488 | 497 | ||
489 | sdata->sensor = (struct st_sensors *)&sensors[i]; | 498 | sdata->sensor_settings = |
499 | (struct st_sensor_settings *)&sensor_settings[i]; | ||
490 | 500 | ||
491 | return i; | 501 | return i; |
492 | 502 | ||
@@ -508,11 +518,11 @@ ssize_t st_sensors_sysfs_sampling_frequency_avail(struct device *dev, | |||
508 | 518 | ||
509 | mutex_lock(&indio_dev->mlock); | 519 | mutex_lock(&indio_dev->mlock); |
510 | for (i = 0; i < ST_SENSORS_ODR_LIST_MAX; i++) { | 520 | for (i = 0; i < ST_SENSORS_ODR_LIST_MAX; i++) { |
511 | if (sdata->sensor->odr.odr_avl[i].hz == 0) | 521 | if (sdata->sensor_settings->odr.odr_avl[i].hz == 0) |
512 | break; | 522 | break; |
513 | 523 | ||
514 | len += scnprintf(buf + len, PAGE_SIZE - len, "%d ", | 524 | len += scnprintf(buf + len, PAGE_SIZE - len, "%d ", |
515 | sdata->sensor->odr.odr_avl[i].hz); | 525 | sdata->sensor_settings->odr.odr_avl[i].hz); |
516 | } | 526 | } |
517 | mutex_unlock(&indio_dev->mlock); | 527 | mutex_unlock(&indio_dev->mlock); |
518 | buf[len - 1] = '\n'; | 528 | buf[len - 1] = '\n'; |
@@ -530,11 +540,11 @@ ssize_t st_sensors_sysfs_scale_avail(struct device *dev, | |||
530 | 540 | ||
531 | mutex_lock(&indio_dev->mlock); | 541 | mutex_lock(&indio_dev->mlock); |
532 | for (i = 0; i < ST_SENSORS_FULLSCALE_AVL_MAX; i++) { | 542 | for (i = 0; i < ST_SENSORS_FULLSCALE_AVL_MAX; i++) { |
533 | if (sdata->sensor->fs.fs_avl[i].num == 0) | 543 | if (sdata->sensor_settings->fs.fs_avl[i].num == 0) |
534 | break; | 544 | break; |
535 | 545 | ||
536 | len += scnprintf(buf + len, PAGE_SIZE - len, "0.%06u ", | 546 | len += scnprintf(buf + len, PAGE_SIZE - len, "0.%06u ", |
537 | sdata->sensor->fs.fs_avl[i].gain); | 547 | sdata->sensor_settings->fs.fs_avl[i].gain); |
538 | } | 548 | } |
539 | mutex_unlock(&indio_dev->mlock); | 549 | mutex_unlock(&indio_dev->mlock); |
540 | buf[len - 1] = '\n'; | 550 | buf[len - 1] = '\n'; |
diff --git a/drivers/iio/common/st_sensors/st_sensors_i2c.c b/drivers/iio/common/st_sensors/st_sensors_i2c.c index bb6f3085f57b..98cfee296d46 100644 --- a/drivers/iio/common/st_sensors/st_sensors_i2c.c +++ b/drivers/iio/common/st_sensors/st_sensors_i2c.c | |||
@@ -72,6 +72,7 @@ void st_sensors_i2c_configure(struct iio_dev *indio_dev, | |||
72 | indio_dev->dev.parent = &client->dev; | 72 | indio_dev->dev.parent = &client->dev; |
73 | indio_dev->name = client->name; | 73 | indio_dev->name = client->name; |
74 | 74 | ||
75 | sdata->dev = &client->dev; | ||
75 | sdata->tf = &st_sensors_tf_i2c; | 76 | sdata->tf = &st_sensors_tf_i2c; |
76 | sdata->get_irq_data_ready = st_sensors_i2c_get_irq; | 77 | sdata->get_irq_data_ready = st_sensors_i2c_get_irq; |
77 | } | 78 | } |
diff --git a/drivers/iio/common/st_sensors/st_sensors_spi.c b/drivers/iio/common/st_sensors/st_sensors_spi.c index 251baf6abc25..78a6a1ab3ece 100644 --- a/drivers/iio/common/st_sensors/st_sensors_spi.c +++ b/drivers/iio/common/st_sensors/st_sensors_spi.c | |||
@@ -111,6 +111,7 @@ void st_sensors_spi_configure(struct iio_dev *indio_dev, | |||
111 | indio_dev->dev.parent = &spi->dev; | 111 | indio_dev->dev.parent = &spi->dev; |
112 | indio_dev->name = spi->modalias; | 112 | indio_dev->name = spi->modalias; |
113 | 113 | ||
114 | sdata->dev = &spi->dev; | ||
114 | sdata->tf = &st_sensors_tf_spi; | 115 | sdata->tf = &st_sensors_tf_spi; |
115 | sdata->get_irq_data_ready = st_sensors_spi_get_irq; | 116 | sdata->get_irq_data_ready = st_sensors_spi_get_irq; |
116 | } | 117 | } |
diff --git a/drivers/iio/gyro/st_gyro.h b/drivers/iio/gyro/st_gyro.h index c197360c450b..5353d6328c54 100644 --- a/drivers/iio/gyro/st_gyro.h +++ b/drivers/iio/gyro/st_gyro.h | |||
@@ -30,8 +30,7 @@ static const struct st_sensors_platform_data gyro_pdata = { | |||
30 | .drdy_int_pin = 2, | 30 | .drdy_int_pin = 2, |
31 | }; | 31 | }; |
32 | 32 | ||
33 | int st_gyro_common_probe(struct iio_dev *indio_dev, | 33 | int st_gyro_common_probe(struct iio_dev *indio_dev); |
34 | struct st_sensors_platform_data *pdata); | ||
35 | void st_gyro_common_remove(struct iio_dev *indio_dev); | 34 | void st_gyro_common_remove(struct iio_dev *indio_dev); |
36 | 35 | ||
37 | #ifdef CONFIG_IIO_BUFFER | 36 | #ifdef CONFIG_IIO_BUFFER |
diff --git a/drivers/iio/gyro/st_gyro_core.c b/drivers/iio/gyro/st_gyro_core.c index f156fc6c5c6c..f07a2336f7dc 100644 --- a/drivers/iio/gyro/st_gyro_core.c +++ b/drivers/iio/gyro/st_gyro_core.c | |||
@@ -103,7 +103,7 @@ static const struct iio_chan_spec st_gyro_16bit_channels[] = { | |||
103 | IIO_CHAN_SOFT_TIMESTAMP(3) | 103 | IIO_CHAN_SOFT_TIMESTAMP(3) |
104 | }; | 104 | }; |
105 | 105 | ||
106 | static const struct st_sensors st_gyro_sensors[] = { | 106 | static const struct st_sensor_settings st_gyro_sensors_settings[] = { |
107 | { | 107 | { |
108 | .wai = ST_GYRO_1_WAI_EXP, | 108 | .wai = ST_GYRO_1_WAI_EXP, |
109 | .sensors_supported = { | 109 | .sensors_supported = { |
@@ -309,8 +309,7 @@ static const struct iio_trigger_ops st_gyro_trigger_ops = { | |||
309 | #define ST_GYRO_TRIGGER_OPS NULL | 309 | #define ST_GYRO_TRIGGER_OPS NULL |
310 | #endif | 310 | #endif |
311 | 311 | ||
312 | int st_gyro_common_probe(struct iio_dev *indio_dev, | 312 | int st_gyro_common_probe(struct iio_dev *indio_dev) |
313 | struct st_sensors_platform_data *pdata) | ||
314 | { | 313 | { |
315 | struct st_sensor_data *gdata = iio_priv(indio_dev); | 314 | struct st_sensor_data *gdata = iio_priv(indio_dev); |
316 | int irq = gdata->get_irq_data_ready(indio_dev); | 315 | int irq = gdata->get_irq_data_ready(indio_dev); |
@@ -322,20 +321,22 @@ int st_gyro_common_probe(struct iio_dev *indio_dev, | |||
322 | st_sensors_power_enable(indio_dev); | 321 | st_sensors_power_enable(indio_dev); |
323 | 322 | ||
324 | err = st_sensors_check_device_support(indio_dev, | 323 | err = st_sensors_check_device_support(indio_dev, |
325 | ARRAY_SIZE(st_gyro_sensors), st_gyro_sensors); | 324 | ARRAY_SIZE(st_gyro_sensors_settings), |
325 | st_gyro_sensors_settings); | ||
326 | if (err < 0) | 326 | if (err < 0) |
327 | return err; | 327 | return err; |
328 | 328 | ||
329 | gdata->num_data_channels = ST_GYRO_NUMBER_DATA_CHANNELS; | 329 | gdata->num_data_channels = ST_GYRO_NUMBER_DATA_CHANNELS; |
330 | gdata->multiread_bit = gdata->sensor->multi_read_bit; | 330 | gdata->multiread_bit = gdata->sensor_settings->multi_read_bit; |
331 | indio_dev->channels = gdata->sensor->ch; | 331 | indio_dev->channels = gdata->sensor_settings->ch; |
332 | indio_dev->num_channels = ST_SENSORS_NUMBER_ALL_CHANNELS; | 332 | indio_dev->num_channels = ST_SENSORS_NUMBER_ALL_CHANNELS; |
333 | 333 | ||
334 | gdata->current_fullscale = (struct st_sensor_fullscale_avl *) | 334 | gdata->current_fullscale = (struct st_sensor_fullscale_avl *) |
335 | &gdata->sensor->fs.fs_avl[0]; | 335 | &gdata->sensor_settings->fs.fs_avl[0]; |
336 | gdata->odr = gdata->sensor->odr.odr_avl[0].hz; | 336 | gdata->odr = gdata->sensor_settings->odr.odr_avl[0].hz; |
337 | 337 | ||
338 | err = st_sensors_init_sensor(indio_dev, pdata); | 338 | err = st_sensors_init_sensor(indio_dev, |
339 | (struct st_sensors_platform_data *)&gyro_pdata); | ||
339 | if (err < 0) | 340 | if (err < 0) |
340 | return err; | 341 | return err; |
341 | 342 | ||
diff --git a/drivers/iio/gyro/st_gyro_i2c.c b/drivers/iio/gyro/st_gyro_i2c.c index 8fa0ad2ef4ef..64480b16c689 100644 --- a/drivers/iio/gyro/st_gyro_i2c.c +++ b/drivers/iio/gyro/st_gyro_i2c.c | |||
@@ -67,13 +67,11 @@ static int st_gyro_i2c_probe(struct i2c_client *client, | |||
67 | return -ENOMEM; | 67 | return -ENOMEM; |
68 | 68 | ||
69 | gdata = iio_priv(indio_dev); | 69 | gdata = iio_priv(indio_dev); |
70 | gdata->dev = &client->dev; | ||
71 | st_sensors_of_i2c_probe(client, st_gyro_of_match); | 70 | st_sensors_of_i2c_probe(client, st_gyro_of_match); |
72 | 71 | ||
73 | st_sensors_i2c_configure(indio_dev, client, gdata); | 72 | st_sensors_i2c_configure(indio_dev, client, gdata); |
74 | 73 | ||
75 | err = st_gyro_common_probe(indio_dev, | 74 | err = st_gyro_common_probe(indio_dev); |
76 | (struct st_sensors_platform_data *)&gyro_pdata); | ||
77 | if (err < 0) | 75 | if (err < 0) |
78 | return err; | 76 | return err; |
79 | 77 | ||
diff --git a/drivers/iio/gyro/st_gyro_spi.c b/drivers/iio/gyro/st_gyro_spi.c index b4ad3be26687..e59bead6bc3c 100644 --- a/drivers/iio/gyro/st_gyro_spi.c +++ b/drivers/iio/gyro/st_gyro_spi.c | |||
@@ -29,12 +29,10 @@ static int st_gyro_spi_probe(struct spi_device *spi) | |||
29 | return -ENOMEM; | 29 | return -ENOMEM; |
30 | 30 | ||
31 | gdata = iio_priv(indio_dev); | 31 | gdata = iio_priv(indio_dev); |
32 | gdata->dev = &spi->dev; | ||
33 | 32 | ||
34 | st_sensors_spi_configure(indio_dev, spi, gdata); | 33 | st_sensors_spi_configure(indio_dev, spi, gdata); |
35 | 34 | ||
36 | err = st_gyro_common_probe(indio_dev, | 35 | err = st_gyro_common_probe(indio_dev); |
37 | (struct st_sensors_platform_data *)&gyro_pdata); | ||
38 | if (err < 0) | 36 | if (err < 0) |
39 | return err; | 37 | return err; |
40 | 38 | ||
diff --git a/drivers/iio/humidity/Kconfig b/drivers/iio/humidity/Kconfig index e116bd8dd0e4..4813b793b9f7 100644 --- a/drivers/iio/humidity/Kconfig +++ b/drivers/iio/humidity/Kconfig | |||
@@ -22,4 +22,14 @@ config SI7005 | |||
22 | To compile this driver as a module, choose M here: the module | 22 | To compile this driver as a module, choose M here: the module |
23 | will be called si7005. | 23 | will be called si7005. |
24 | 24 | ||
25 | config SI7020 | ||
26 | tristate "Si7013/20/21 Relative Humidity and Temperature Sensors" | ||
27 | depends on I2C | ||
28 | help | ||
29 | Say yes here to build support for the Silicon Labs Si7013/20/21 | ||
30 | Relative Humidity and Temperature Sensors. | ||
31 | |||
32 | To compile this driver as a module, choose M here: the module | ||
33 | will be called si7020. | ||
34 | |||
25 | endmenu | 35 | endmenu |
diff --git a/drivers/iio/humidity/Makefile b/drivers/iio/humidity/Makefile index e3f3d942e646..86e2d26e9f4d 100644 --- a/drivers/iio/humidity/Makefile +++ b/drivers/iio/humidity/Makefile | |||
@@ -4,3 +4,4 @@ | |||
4 | 4 | ||
5 | obj-$(CONFIG_DHT11) += dht11.o | 5 | obj-$(CONFIG_DHT11) += dht11.o |
6 | obj-$(CONFIG_SI7005) += si7005.o | 6 | obj-$(CONFIG_SI7005) += si7005.o |
7 | obj-$(CONFIG_SI7020) += si7020.o | ||
diff --git a/drivers/iio/humidity/si7020.c b/drivers/iio/humidity/si7020.c new file mode 100644 index 000000000000..b54164677b89 --- /dev/null +++ b/drivers/iio/humidity/si7020.c | |||
@@ -0,0 +1,161 @@ | |||
1 | /* | ||
2 | * si7020.c - Silicon Labs Si7013/20/21 Relative Humidity and Temp Sensors | ||
3 | * Copyright (c) 2013,2014 Uplogix, Inc. | ||
4 | * David Barksdale <dbarksdale@uplogix.com> | ||
5 | * | ||
6 | * This program is free software; you can redistribute it and/or modify it | ||
7 | * under the terms and conditions of the GNU General Public License, | ||
8 | * version 2, as published by the Free Software Foundation. | ||
9 | * | ||
10 | * This program is distributed in the hope that it will be useful, | ||
11 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
13 | * GNU General Public License for more details. | ||
14 | */ | ||
15 | |||
16 | /* | ||
17 | * The Silicon Labs Si7013/20/21 Relative Humidity and Temperature Sensors | ||
18 | * are i2c devices which have an identical programming interface for | ||
19 | * measuring relative humidity and temperature. The Si7013 has an additional | ||
20 | * temperature input which this driver does not support. | ||
21 | * | ||
22 | * Data Sheets: | ||
23 | * Si7013: http://www.silabs.com/Support%20Documents/TechnicalDocs/Si7013.pdf | ||
24 | * Si7020: http://www.silabs.com/Support%20Documents/TechnicalDocs/Si7020.pdf | ||
25 | * Si7021: http://www.silabs.com/Support%20Documents/TechnicalDocs/Si7021.pdf | ||
26 | */ | ||
27 | |||
28 | #include <linux/delay.h> | ||
29 | #include <linux/i2c.h> | ||
30 | #include <linux/module.h> | ||
31 | #include <linux/slab.h> | ||
32 | #include <linux/sysfs.h> | ||
33 | |||
34 | #include <linux/iio/iio.h> | ||
35 | #include <linux/iio/sysfs.h> | ||
36 | |||
37 | /* Measure Relative Humidity, Hold Master Mode */ | ||
38 | #define SI7020CMD_RH_HOLD 0xE5 | ||
39 | /* Measure Temperature, Hold Master Mode */ | ||
40 | #define SI7020CMD_TEMP_HOLD 0xE3 | ||
41 | /* Software Reset */ | ||
42 | #define SI7020CMD_RESET 0xFE | ||
43 | |||
44 | static int si7020_read_raw(struct iio_dev *indio_dev, | ||
45 | struct iio_chan_spec const *chan, int *val, | ||
46 | int *val2, long mask) | ||
47 | { | ||
48 | struct i2c_client *client = iio_priv(indio_dev); | ||
49 | int ret; | ||
50 | |||
51 | switch (mask) { | ||
52 | case IIO_CHAN_INFO_RAW: | ||
53 | ret = i2c_smbus_read_word_data(client, | ||
54 | chan->type == IIO_TEMP ? | ||
55 | SI7020CMD_TEMP_HOLD : | ||
56 | SI7020CMD_RH_HOLD); | ||
57 | if (ret < 0) | ||
58 | return ret; | ||
59 | *val = ret >> 2; | ||
60 | if (chan->type == IIO_HUMIDITYRELATIVE) | ||
61 | *val &= GENMASK(11, 0); | ||
62 | return IIO_VAL_INT; | ||
63 | case IIO_CHAN_INFO_SCALE: | ||
64 | if (chan->type == IIO_TEMP) | ||
65 | *val = 175720; /* = 175.72 * 1000 */ | ||
66 | else | ||
67 | *val = 125 * 1000; | ||
68 | *val2 = 65536 >> 2; | ||
69 | return IIO_VAL_FRACTIONAL; | ||
70 | case IIO_CHAN_INFO_OFFSET: | ||
71 | /* | ||
72 | * Since iio_convert_raw_to_processed_unlocked assumes offset | ||
73 | * is an integer we have to round these values and lose | ||
74 | * accuracy. | ||
75 | * Relative humidity will be 0.0032959% too high and | ||
76 | * temperature will be 0.00277344 degrees too high. | ||
77 | * This is no big deal because it's within the accuracy of the | ||
78 | * sensor. | ||
79 | */ | ||
80 | if (chan->type == IIO_TEMP) | ||
81 | *val = -4368; /* = -46.85 * (65536 >> 2) / 175.72 */ | ||
82 | else | ||
83 | *val = -786; /* = -6 * (65536 >> 2) / 125 */ | ||
84 | return IIO_VAL_INT; | ||
85 | default: | ||
86 | break; | ||
87 | } | ||
88 | |||
89 | return -EINVAL; | ||
90 | } | ||
91 | |||
92 | static const struct iio_chan_spec si7020_channels[] = { | ||
93 | { | ||
94 | .type = IIO_HUMIDITYRELATIVE, | ||
95 | .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | | ||
96 | BIT(IIO_CHAN_INFO_SCALE) | BIT(IIO_CHAN_INFO_OFFSET), | ||
97 | }, | ||
98 | { | ||
99 | .type = IIO_TEMP, | ||
100 | .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | | ||
101 | BIT(IIO_CHAN_INFO_SCALE) | BIT(IIO_CHAN_INFO_OFFSET), | ||
102 | } | ||
103 | }; | ||
104 | |||
105 | static const struct iio_info si7020_info = { | ||
106 | .read_raw = si7020_read_raw, | ||
107 | .driver_module = THIS_MODULE, | ||
108 | }; | ||
109 | |||
110 | static int si7020_probe(struct i2c_client *client, | ||
111 | const struct i2c_device_id *id) | ||
112 | { | ||
113 | struct iio_dev *indio_dev; | ||
114 | struct i2c_client **data; | ||
115 | int ret; | ||
116 | |||
117 | if (!i2c_check_functionality(client->adapter, | ||
118 | I2C_FUNC_SMBUS_WRITE_BYTE | | ||
119 | I2C_FUNC_SMBUS_READ_WORD_DATA)) | ||
120 | return -ENODEV; | ||
121 | |||
122 | /* Reset device, loads default settings. */ | ||
123 | ret = i2c_smbus_write_byte(client, SI7020CMD_RESET); | ||
124 | if (ret < 0) | ||
125 | return ret; | ||
126 | /* Wait the maximum power-up time after software reset. */ | ||
127 | msleep(15); | ||
128 | |||
129 | indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*client)); | ||
130 | if (!indio_dev) | ||
131 | return -ENOMEM; | ||
132 | |||
133 | data = iio_priv(indio_dev); | ||
134 | *data = client; | ||
135 | |||
136 | indio_dev->dev.parent = &client->dev; | ||
137 | indio_dev->name = dev_name(&client->dev); | ||
138 | indio_dev->modes = INDIO_DIRECT_MODE; | ||
139 | indio_dev->info = &si7020_info; | ||
140 | indio_dev->channels = si7020_channels; | ||
141 | indio_dev->num_channels = ARRAY_SIZE(si7020_channels); | ||
142 | |||
143 | return devm_iio_device_register(&client->dev, indio_dev); | ||
144 | } | ||
145 | |||
146 | static const struct i2c_device_id si7020_id[] = { | ||
147 | { "si7020", 0 }, | ||
148 | { } | ||
149 | }; | ||
150 | MODULE_DEVICE_TABLE(i2c, si7020_id); | ||
151 | |||
152 | static struct i2c_driver si7020_driver = { | ||
153 | .driver.name = "si7020", | ||
154 | .probe = si7020_probe, | ||
155 | .id_table = si7020_id, | ||
156 | }; | ||
157 | |||
158 | module_i2c_driver(si7020_driver); | ||
159 | MODULE_DESCRIPTION("Silicon Labs Si7013/20/21 Relative Humidity and Temperature Sensors"); | ||
160 | MODULE_AUTHOR("David Barksdale <dbarksdale@uplogix.com>"); | ||
161 | MODULE_LICENSE("GPL"); | ||
diff --git a/drivers/iio/inkern.c b/drivers/iio/inkern.c index f0846108d006..866fe904cba2 100644 --- a/drivers/iio/inkern.c +++ b/drivers/iio/inkern.c | |||
@@ -100,6 +100,28 @@ static int iio_dev_node_match(struct device *dev, void *data) | |||
100 | return dev->of_node == data && dev->type == &iio_device_type; | 100 | return dev->of_node == data && dev->type == &iio_device_type; |
101 | } | 101 | } |
102 | 102 | ||
103 | /** | ||
104 | * __of_iio_simple_xlate - translate iiospec to the IIO channel index | ||
105 | * @indio_dev: pointer to the iio_dev structure | ||
106 | * @iiospec: IIO specifier as found in the device tree | ||
107 | * | ||
108 | * This is simple translation function, suitable for the most 1:1 mapped | ||
109 | * channels in IIO chips. This function performs only one sanity check: | ||
110 | * whether IIO index is less than num_channels (that is specified in the | ||
111 | * iio_dev). | ||
112 | */ | ||
113 | static int __of_iio_simple_xlate(struct iio_dev *indio_dev, | ||
114 | const struct of_phandle_args *iiospec) | ||
115 | { | ||
116 | if (!iiospec->args_count) | ||
117 | return 0; | ||
118 | |||
119 | if (iiospec->args[0] >= indio_dev->num_channels) | ||
120 | return -EINVAL; | ||
121 | |||
122 | return iiospec->args[0]; | ||
123 | } | ||
124 | |||
103 | static int __of_iio_channel_get(struct iio_channel *channel, | 125 | static int __of_iio_channel_get(struct iio_channel *channel, |
104 | struct device_node *np, int index) | 126 | struct device_node *np, int index) |
105 | { | 127 | { |
@@ -122,18 +144,19 @@ static int __of_iio_channel_get(struct iio_channel *channel, | |||
122 | 144 | ||
123 | indio_dev = dev_to_iio_dev(idev); | 145 | indio_dev = dev_to_iio_dev(idev); |
124 | channel->indio_dev = indio_dev; | 146 | channel->indio_dev = indio_dev; |
125 | index = iiospec.args_count ? iiospec.args[0] : 0; | 147 | if (indio_dev->info->of_xlate) |
126 | if (index >= indio_dev->num_channels) { | 148 | index = indio_dev->info->of_xlate(indio_dev, &iiospec); |
127 | err = -EINVAL; | 149 | else |
150 | index = __of_iio_simple_xlate(indio_dev, &iiospec); | ||
151 | if (index < 0) | ||
128 | goto err_put; | 152 | goto err_put; |
129 | } | ||
130 | channel->channel = &indio_dev->channels[index]; | 153 | channel->channel = &indio_dev->channels[index]; |
131 | 154 | ||
132 | return 0; | 155 | return 0; |
133 | 156 | ||
134 | err_put: | 157 | err_put: |
135 | iio_device_put(indio_dev); | 158 | iio_device_put(indio_dev); |
136 | return err; | 159 | return index; |
137 | } | 160 | } |
138 | 161 | ||
139 | static struct iio_channel *of_iio_channel_get(struct device_node *np, int index) | 162 | static struct iio_channel *of_iio_channel_get(struct device_node *np, int index) |
diff --git a/drivers/iio/magnetometer/st_magn.h b/drivers/iio/magnetometer/st_magn.h index 694e33e0fb72..7e81d00ef0c3 100644 --- a/drivers/iio/magnetometer/st_magn.h +++ b/drivers/iio/magnetometer/st_magn.h | |||
@@ -18,8 +18,7 @@ | |||
18 | #define LSM303DLM_MAGN_DEV_NAME "lsm303dlm_magn" | 18 | #define LSM303DLM_MAGN_DEV_NAME "lsm303dlm_magn" |
19 | #define LIS3MDL_MAGN_DEV_NAME "lis3mdl" | 19 | #define LIS3MDL_MAGN_DEV_NAME "lis3mdl" |
20 | 20 | ||
21 | int st_magn_common_probe(struct iio_dev *indio_dev, | 21 | int st_magn_common_probe(struct iio_dev *indio_dev); |
22 | struct st_sensors_platform_data *pdata); | ||
23 | void st_magn_common_remove(struct iio_dev *indio_dev); | 22 | void st_magn_common_remove(struct iio_dev *indio_dev); |
24 | 23 | ||
25 | #ifdef CONFIG_IIO_BUFFER | 24 | #ifdef CONFIG_IIO_BUFFER |
diff --git a/drivers/iio/magnetometer/st_magn_core.c b/drivers/iio/magnetometer/st_magn_core.c index 68cae86dbd29..8ade473f99fe 100644 --- a/drivers/iio/magnetometer/st_magn_core.c +++ b/drivers/iio/magnetometer/st_magn_core.c | |||
@@ -149,7 +149,7 @@ static const struct iio_chan_spec st_magn_2_16bit_channels[] = { | |||
149 | IIO_CHAN_SOFT_TIMESTAMP(3) | 149 | IIO_CHAN_SOFT_TIMESTAMP(3) |
150 | }; | 150 | }; |
151 | 151 | ||
152 | static const struct st_sensors st_magn_sensors[] = { | 152 | static const struct st_sensor_settings st_magn_sensors_settings[] = { |
153 | { | 153 | { |
154 | .wai = ST_MAGN_1_WAI_EXP, | 154 | .wai = ST_MAGN_1_WAI_EXP, |
155 | .sensors_supported = { | 155 | .sensors_supported = { |
@@ -361,8 +361,7 @@ static const struct iio_info magn_info = { | |||
361 | .write_raw = &st_magn_write_raw, | 361 | .write_raw = &st_magn_write_raw, |
362 | }; | 362 | }; |
363 | 363 | ||
364 | int st_magn_common_probe(struct iio_dev *indio_dev, | 364 | int st_magn_common_probe(struct iio_dev *indio_dev) |
365 | struct st_sensors_platform_data *pdata) | ||
366 | { | 365 | { |
367 | struct st_sensor_data *mdata = iio_priv(indio_dev); | 366 | struct st_sensor_data *mdata = iio_priv(indio_dev); |
368 | int irq = mdata->get_irq_data_ready(indio_dev); | 367 | int irq = mdata->get_irq_data_ready(indio_dev); |
@@ -374,20 +373,21 @@ int st_magn_common_probe(struct iio_dev *indio_dev, | |||
374 | st_sensors_power_enable(indio_dev); | 373 | st_sensors_power_enable(indio_dev); |
375 | 374 | ||
376 | err = st_sensors_check_device_support(indio_dev, | 375 | err = st_sensors_check_device_support(indio_dev, |
377 | ARRAY_SIZE(st_magn_sensors), st_magn_sensors); | 376 | ARRAY_SIZE(st_magn_sensors_settings), |
377 | st_magn_sensors_settings); | ||
378 | if (err < 0) | 378 | if (err < 0) |
379 | return err; | 379 | return err; |
380 | 380 | ||
381 | mdata->num_data_channels = ST_MAGN_NUMBER_DATA_CHANNELS; | 381 | mdata->num_data_channels = ST_MAGN_NUMBER_DATA_CHANNELS; |
382 | mdata->multiread_bit = mdata->sensor->multi_read_bit; | 382 | mdata->multiread_bit = mdata->sensor_settings->multi_read_bit; |
383 | indio_dev->channels = mdata->sensor->ch; | 383 | indio_dev->channels = mdata->sensor_settings->ch; |
384 | indio_dev->num_channels = ST_SENSORS_NUMBER_ALL_CHANNELS; | 384 | indio_dev->num_channels = ST_SENSORS_NUMBER_ALL_CHANNELS; |
385 | 385 | ||
386 | mdata->current_fullscale = (struct st_sensor_fullscale_avl *) | 386 | mdata->current_fullscale = (struct st_sensor_fullscale_avl *) |
387 | &mdata->sensor->fs.fs_avl[0]; | 387 | &mdata->sensor_settings->fs.fs_avl[0]; |
388 | mdata->odr = mdata->sensor->odr.odr_avl[0].hz; | 388 | mdata->odr = mdata->sensor_settings->odr.odr_avl[0].hz; |
389 | 389 | ||
390 | err = st_sensors_init_sensor(indio_dev, pdata); | 390 | err = st_sensors_init_sensor(indio_dev, NULL); |
391 | if (err < 0) | 391 | if (err < 0) |
392 | return err; | 392 | return err; |
393 | 393 | ||
diff --git a/drivers/iio/magnetometer/st_magn_i2c.c b/drivers/iio/magnetometer/st_magn_i2c.c index 689250058442..92e5c15452a3 100644 --- a/drivers/iio/magnetometer/st_magn_i2c.c +++ b/drivers/iio/magnetometer/st_magn_i2c.c | |||
@@ -51,12 +51,11 @@ static int st_magn_i2c_probe(struct i2c_client *client, | |||
51 | return -ENOMEM; | 51 | return -ENOMEM; |
52 | 52 | ||
53 | mdata = iio_priv(indio_dev); | 53 | mdata = iio_priv(indio_dev); |
54 | mdata->dev = &client->dev; | ||
55 | st_sensors_of_i2c_probe(client, st_magn_of_match); | 54 | st_sensors_of_i2c_probe(client, st_magn_of_match); |
56 | 55 | ||
57 | st_sensors_i2c_configure(indio_dev, client, mdata); | 56 | st_sensors_i2c_configure(indio_dev, client, mdata); |
58 | 57 | ||
59 | err = st_magn_common_probe(indio_dev, NULL); | 58 | err = st_magn_common_probe(indio_dev); |
60 | if (err < 0) | 59 | if (err < 0) |
61 | return err; | 60 | return err; |
62 | 61 | ||
diff --git a/drivers/iio/magnetometer/st_magn_spi.c b/drivers/iio/magnetometer/st_magn_spi.c index a6143ea51dfc..7adacf160146 100644 --- a/drivers/iio/magnetometer/st_magn_spi.c +++ b/drivers/iio/magnetometer/st_magn_spi.c | |||
@@ -29,11 +29,10 @@ static int st_magn_spi_probe(struct spi_device *spi) | |||
29 | return -ENOMEM; | 29 | return -ENOMEM; |
30 | 30 | ||
31 | mdata = iio_priv(indio_dev); | 31 | mdata = iio_priv(indio_dev); |
32 | mdata->dev = &spi->dev; | ||
33 | 32 | ||
34 | st_sensors_spi_configure(indio_dev, spi, mdata); | 33 | st_sensors_spi_configure(indio_dev, spi, mdata); |
35 | 34 | ||
36 | err = st_magn_common_probe(indio_dev, NULL); | 35 | err = st_magn_common_probe(indio_dev); |
37 | if (err < 0) | 36 | if (err < 0) |
38 | return err; | 37 | return err; |
39 | 38 | ||
diff --git a/drivers/iio/pressure/Kconfig b/drivers/iio/pressure/Kconfig index 15afbc919521..a3be53792072 100644 --- a/drivers/iio/pressure/Kconfig +++ b/drivers/iio/pressure/Kconfig | |||
@@ -5,6 +5,17 @@ | |||
5 | 5 | ||
6 | menu "Pressure sensors" | 6 | menu "Pressure sensors" |
7 | 7 | ||
8 | config BMP280 | ||
9 | tristate "Bosch Sensortec BMP280 pressure sensor driver" | ||
10 | depends on I2C | ||
11 | select REGMAP_I2C | ||
12 | help | ||
13 | Say yes here to build support for Bosch Sensortec BMP280 | ||
14 | pressure and temperature sensor. | ||
15 | |||
16 | To compile this driver as a module, choose M here: the module | ||
17 | will be called bmp280. | ||
18 | |||
8 | config HID_SENSOR_PRESS | 19 | config HID_SENSOR_PRESS |
9 | depends on HID_SENSOR_HUB | 20 | depends on HID_SENSOR_HUB |
10 | select IIO_BUFFER | 21 | select IIO_BUFFER |
diff --git a/drivers/iio/pressure/Makefile b/drivers/iio/pressure/Makefile index 90a37e85cf21..88011f2ae00e 100644 --- a/drivers/iio/pressure/Makefile +++ b/drivers/iio/pressure/Makefile | |||
@@ -3,6 +3,7 @@ | |||
3 | # | 3 | # |
4 | 4 | ||
5 | # When adding new entries keep the list in alphabetical order | 5 | # When adding new entries keep the list in alphabetical order |
6 | obj-$(CONFIG_BMP280) += bmp280.o | ||
6 | obj-$(CONFIG_HID_SENSOR_PRESS) += hid-sensor-press.o | 7 | obj-$(CONFIG_HID_SENSOR_PRESS) += hid-sensor-press.o |
7 | obj-$(CONFIG_MPL115) += mpl115.o | 8 | obj-$(CONFIG_MPL115) += mpl115.o |
8 | obj-$(CONFIG_MPL3115) += mpl3115.o | 9 | obj-$(CONFIG_MPL3115) += mpl3115.o |
diff --git a/drivers/iio/pressure/bmp280.c b/drivers/iio/pressure/bmp280.c new file mode 100644 index 000000000000..75038dacfff1 --- /dev/null +++ b/drivers/iio/pressure/bmp280.c | |||
@@ -0,0 +1,455 @@ | |||
1 | /* | ||
2 | * Copyright (c) 2014 Intel Corporation | ||
3 | * | ||
4 | * Driver for Bosch Sensortec BMP280 digital pressure sensor. | ||
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 | */ | ||
11 | |||
12 | #define pr_fmt(fmt) "bmp280: " fmt | ||
13 | |||
14 | #include <linux/module.h> | ||
15 | #include <linux/i2c.h> | ||
16 | #include <linux/acpi.h> | ||
17 | #include <linux/regmap.h> | ||
18 | #include <linux/iio/iio.h> | ||
19 | #include <linux/iio/sysfs.h> | ||
20 | |||
21 | #define BMP280_REG_TEMP_XLSB 0xFC | ||
22 | #define BMP280_REG_TEMP_LSB 0xFB | ||
23 | #define BMP280_REG_TEMP_MSB 0xFA | ||
24 | #define BMP280_REG_PRESS_XLSB 0xF9 | ||
25 | #define BMP280_REG_PRESS_LSB 0xF8 | ||
26 | #define BMP280_REG_PRESS_MSB 0xF7 | ||
27 | |||
28 | #define BMP280_REG_CONFIG 0xF5 | ||
29 | #define BMP280_REG_CTRL_MEAS 0xF4 | ||
30 | #define BMP280_REG_STATUS 0xF3 | ||
31 | #define BMP280_REG_RESET 0xE0 | ||
32 | #define BMP280_REG_ID 0xD0 | ||
33 | |||
34 | #define BMP280_REG_COMP_TEMP_START 0x88 | ||
35 | #define BMP280_COMP_TEMP_REG_COUNT 6 | ||
36 | |||
37 | #define BMP280_REG_COMP_PRESS_START 0x8E | ||
38 | #define BMP280_COMP_PRESS_REG_COUNT 18 | ||
39 | |||
40 | #define BMP280_FILTER_MASK (BIT(4) | BIT(3) | BIT(2)) | ||
41 | #define BMP280_FILTER_OFF 0 | ||
42 | #define BMP280_FILTER_2X BIT(2) | ||
43 | #define BMP280_FILTER_4X BIT(3) | ||
44 | #define BMP280_FILTER_8X (BIT(3) | BIT(2)) | ||
45 | #define BMP280_FILTER_16X BIT(4) | ||
46 | |||
47 | #define BMP280_OSRS_TEMP_MASK (BIT(7) | BIT(6) | BIT(5)) | ||
48 | #define BMP280_OSRS_TEMP_SKIP 0 | ||
49 | #define BMP280_OSRS_TEMP_1X BIT(5) | ||
50 | #define BMP280_OSRS_TEMP_2X BIT(6) | ||
51 | #define BMP280_OSRS_TEMP_4X (BIT(6) | BIT(5)) | ||
52 | #define BMP280_OSRS_TEMP_8X BIT(7) | ||
53 | #define BMP280_OSRS_TEMP_16X (BIT(7) | BIT(5)) | ||
54 | |||
55 | #define BMP280_OSRS_PRESS_MASK (BIT(4) | BIT(3) | BIT(2)) | ||
56 | #define BMP280_OSRS_PRESS_SKIP 0 | ||
57 | #define BMP280_OSRS_PRESS_1X BIT(2) | ||
58 | #define BMP280_OSRS_PRESS_2X BIT(3) | ||
59 | #define BMP280_OSRS_PRESS_4X (BIT(3) | BIT(2)) | ||
60 | #define BMP280_OSRS_PRESS_8X BIT(4) | ||
61 | #define BMP280_OSRS_PRESS_16X (BIT(4) | BIT(2)) | ||
62 | |||
63 | #define BMP280_MODE_MASK (BIT(1) | BIT(0)) | ||
64 | #define BMP280_MODE_SLEEP 0 | ||
65 | #define BMP280_MODE_FORCED BIT(0) | ||
66 | #define BMP280_MODE_NORMAL (BIT(1) | BIT(0)) | ||
67 | |||
68 | #define BMP280_CHIP_ID 0x58 | ||
69 | #define BMP280_SOFT_RESET_VAL 0xB6 | ||
70 | |||
71 | struct bmp280_data { | ||
72 | struct i2c_client *client; | ||
73 | struct mutex lock; | ||
74 | struct regmap *regmap; | ||
75 | |||
76 | /* | ||
77 | * Carryover value from temperature conversion, used in pressure | ||
78 | * calculation. | ||
79 | */ | ||
80 | s32 t_fine; | ||
81 | }; | ||
82 | |||
83 | /* Compensation parameters. */ | ||
84 | struct bmp280_comp_temp { | ||
85 | u16 dig_t1; | ||
86 | s16 dig_t2, dig_t3; | ||
87 | }; | ||
88 | |||
89 | struct bmp280_comp_press { | ||
90 | u16 dig_p1; | ||
91 | s16 dig_p2, dig_p3, dig_p4, dig_p5, dig_p6, dig_p7, dig_p8, dig_p9; | ||
92 | }; | ||
93 | |||
94 | static const struct iio_chan_spec bmp280_channels[] = { | ||
95 | { | ||
96 | .type = IIO_PRESSURE, | ||
97 | .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED), | ||
98 | }, | ||
99 | { | ||
100 | .type = IIO_TEMP, | ||
101 | .info_mask_separate = BIT(IIO_CHAN_INFO_PROCESSED), | ||
102 | }, | ||
103 | }; | ||
104 | |||
105 | static bool bmp280_is_writeable_reg(struct device *dev, unsigned int reg) | ||
106 | { | ||
107 | switch (reg) { | ||
108 | case BMP280_REG_CONFIG: | ||
109 | case BMP280_REG_CTRL_MEAS: | ||
110 | case BMP280_REG_RESET: | ||
111 | return true; | ||
112 | default: | ||
113 | return false; | ||
114 | }; | ||
115 | } | ||
116 | |||
117 | static bool bmp280_is_volatile_reg(struct device *dev, unsigned int reg) | ||
118 | { | ||
119 | switch (reg) { | ||
120 | case BMP280_REG_TEMP_XLSB: | ||
121 | case BMP280_REG_TEMP_LSB: | ||
122 | case BMP280_REG_TEMP_MSB: | ||
123 | case BMP280_REG_PRESS_XLSB: | ||
124 | case BMP280_REG_PRESS_LSB: | ||
125 | case BMP280_REG_PRESS_MSB: | ||
126 | case BMP280_REG_STATUS: | ||
127 | return true; | ||
128 | default: | ||
129 | return false; | ||
130 | } | ||
131 | } | ||
132 | |||
133 | static const struct regmap_config bmp280_regmap_config = { | ||
134 | .reg_bits = 8, | ||
135 | .val_bits = 8, | ||
136 | |||
137 | .max_register = BMP280_REG_TEMP_XLSB, | ||
138 | .cache_type = REGCACHE_RBTREE, | ||
139 | |||
140 | .writeable_reg = bmp280_is_writeable_reg, | ||
141 | .volatile_reg = bmp280_is_volatile_reg, | ||
142 | }; | ||
143 | |||
144 | static int bmp280_read_compensation_temp(struct bmp280_data *data, | ||
145 | struct bmp280_comp_temp *comp) | ||
146 | { | ||
147 | int ret; | ||
148 | __le16 buf[BMP280_COMP_TEMP_REG_COUNT / 2]; | ||
149 | |||
150 | ret = regmap_bulk_read(data->regmap, BMP280_REG_COMP_TEMP_START, | ||
151 | buf, BMP280_COMP_TEMP_REG_COUNT); | ||
152 | if (ret < 0) { | ||
153 | dev_err(&data->client->dev, | ||
154 | "failed to read temperature calibration parameters\n"); | ||
155 | return ret; | ||
156 | } | ||
157 | |||
158 | comp->dig_t1 = (u16) le16_to_cpu(buf[0]); | ||
159 | comp->dig_t2 = (s16) le16_to_cpu(buf[1]); | ||
160 | comp->dig_t3 = (s16) le16_to_cpu(buf[2]); | ||
161 | |||
162 | return 0; | ||
163 | } | ||
164 | |||
165 | static int bmp280_read_compensation_press(struct bmp280_data *data, | ||
166 | struct bmp280_comp_press *comp) | ||
167 | { | ||
168 | int ret; | ||
169 | __le16 buf[BMP280_COMP_PRESS_REG_COUNT / 2]; | ||
170 | |||
171 | ret = regmap_bulk_read(data->regmap, BMP280_REG_COMP_PRESS_START, | ||
172 | buf, BMP280_COMP_PRESS_REG_COUNT); | ||
173 | if (ret < 0) { | ||
174 | dev_err(&data->client->dev, | ||
175 | "failed to read pressure calibration parameters\n"); | ||
176 | return ret; | ||
177 | } | ||
178 | |||
179 | comp->dig_p1 = (u16) le16_to_cpu(buf[0]); | ||
180 | comp->dig_p2 = (s16) le16_to_cpu(buf[1]); | ||
181 | comp->dig_p3 = (s16) le16_to_cpu(buf[2]); | ||
182 | comp->dig_p4 = (s16) le16_to_cpu(buf[3]); | ||
183 | comp->dig_p5 = (s16) le16_to_cpu(buf[4]); | ||
184 | comp->dig_p6 = (s16) le16_to_cpu(buf[5]); | ||
185 | comp->dig_p7 = (s16) le16_to_cpu(buf[6]); | ||
186 | comp->dig_p8 = (s16) le16_to_cpu(buf[7]); | ||
187 | comp->dig_p9 = (s16) le16_to_cpu(buf[8]); | ||
188 | |||
189 | return 0; | ||
190 | } | ||
191 | |||
192 | /* | ||
193 | * Returns temperature in DegC, resolution is 0.01 DegC. Output value of | ||
194 | * "5123" equals 51.23 DegC. t_fine carries fine temperature as global | ||
195 | * value. | ||
196 | * | ||
197 | * Taken from datasheet, Section 3.11.3, "Compensation formula". | ||
198 | */ | ||
199 | static s32 bmp280_compensate_temp(struct bmp280_data *data, | ||
200 | struct bmp280_comp_temp *comp, | ||
201 | s32 adc_temp) | ||
202 | { | ||
203 | s32 var1, var2, t; | ||
204 | |||
205 | var1 = (((adc_temp >> 3) - ((s32) comp->dig_t1 << 1)) * | ||
206 | ((s32) comp->dig_t2)) >> 11; | ||
207 | var2 = (((((adc_temp >> 4) - ((s32) comp->dig_t1)) * | ||
208 | ((adc_temp >> 4) - ((s32) comp->dig_t1))) >> 12) * | ||
209 | ((s32) comp->dig_t3)) >> 14; | ||
210 | |||
211 | data->t_fine = var1 + var2; | ||
212 | t = (data->t_fine * 5 + 128) >> 8; | ||
213 | |||
214 | return t; | ||
215 | } | ||
216 | |||
217 | /* | ||
218 | * Returns pressure in Pa as unsigned 32 bit integer in Q24.8 format (24 | ||
219 | * integer bits and 8 fractional bits). Output value of "24674867" | ||
220 | * represents 24674867/256 = 96386.2 Pa = 963.862 hPa | ||
221 | * | ||
222 | * Taken from datasheet, Section 3.11.3, "Compensation formula". | ||
223 | */ | ||
224 | static u32 bmp280_compensate_press(struct bmp280_data *data, | ||
225 | struct bmp280_comp_press *comp, | ||
226 | s32 adc_press) | ||
227 | { | ||
228 | s64 var1, var2, p; | ||
229 | |||
230 | var1 = ((s64) data->t_fine) - 128000; | ||
231 | var2 = var1 * var1 * (s64) comp->dig_p6; | ||
232 | var2 = var2 + ((var1 * (s64) comp->dig_p5) << 17); | ||
233 | var2 = var2 + (((s64) comp->dig_p4) << 35); | ||
234 | var1 = ((var1 * var1 * (s64) comp->dig_p3) >> 8) + | ||
235 | ((var1 * (s64) comp->dig_p2) << 12); | ||
236 | var1 = (((((s64) 1) << 47) + var1)) * ((s64) comp->dig_p1) >> 33; | ||
237 | |||
238 | if (var1 == 0) | ||
239 | return 0; | ||
240 | |||
241 | p = ((((s64) 1048576 - adc_press) << 31) - var2) * 3125; | ||
242 | p = div64_s64(p, var1); | ||
243 | var1 = (((s64) comp->dig_p9) * (p >> 13) * (p >> 13)) >> 25; | ||
244 | var2 = (((s64) comp->dig_p8) * p) >> 19; | ||
245 | p = ((p + var1 + var2) >> 8) + (((s64) comp->dig_p7) << 4); | ||
246 | |||
247 | return (u32) p; | ||
248 | } | ||
249 | |||
250 | static int bmp280_read_temp(struct bmp280_data *data, | ||
251 | int *val) | ||
252 | { | ||
253 | int ret; | ||
254 | __be32 tmp = 0; | ||
255 | s32 adc_temp, comp_temp; | ||
256 | struct bmp280_comp_temp comp; | ||
257 | |||
258 | ret = bmp280_read_compensation_temp(data, &comp); | ||
259 | if (ret < 0) | ||
260 | return ret; | ||
261 | |||
262 | ret = regmap_bulk_read(data->regmap, BMP280_REG_TEMP_MSB, | ||
263 | (u8 *) &tmp, 3); | ||
264 | if (ret < 0) { | ||
265 | dev_err(&data->client->dev, "failed to read temperature\n"); | ||
266 | return ret; | ||
267 | } | ||
268 | |||
269 | adc_temp = be32_to_cpu(tmp) >> 12; | ||
270 | comp_temp = bmp280_compensate_temp(data, &comp, adc_temp); | ||
271 | |||
272 | /* | ||
273 | * val might be NULL if we're called by the read_press routine, | ||
274 | * who only cares about the carry over t_fine value. | ||
275 | */ | ||
276 | if (val) { | ||
277 | *val = comp_temp * 10; | ||
278 | return IIO_VAL_INT; | ||
279 | } | ||
280 | |||
281 | return 0; | ||
282 | } | ||
283 | |||
284 | static int bmp280_read_press(struct bmp280_data *data, | ||
285 | int *val, int *val2) | ||
286 | { | ||
287 | int ret; | ||
288 | __be32 tmp = 0; | ||
289 | s32 adc_press; | ||
290 | u32 comp_press; | ||
291 | struct bmp280_comp_press comp; | ||
292 | |||
293 | ret = bmp280_read_compensation_press(data, &comp); | ||
294 | if (ret < 0) | ||
295 | return ret; | ||
296 | |||
297 | /* Read and compensate temperature so we get a reading of t_fine. */ | ||
298 | ret = bmp280_read_temp(data, NULL); | ||
299 | if (ret < 0) | ||
300 | return ret; | ||
301 | |||
302 | ret = regmap_bulk_read(data->regmap, BMP280_REG_PRESS_MSB, | ||
303 | (u8 *) &tmp, 3); | ||
304 | if (ret < 0) { | ||
305 | dev_err(&data->client->dev, "failed to read pressure\n"); | ||
306 | return ret; | ||
307 | } | ||
308 | |||
309 | adc_press = be32_to_cpu(tmp) >> 12; | ||
310 | comp_press = bmp280_compensate_press(data, &comp, adc_press); | ||
311 | |||
312 | *val = comp_press; | ||
313 | *val2 = 256000; | ||
314 | |||
315 | return IIO_VAL_FRACTIONAL; | ||
316 | } | ||
317 | |||
318 | static int bmp280_read_raw(struct iio_dev *indio_dev, | ||
319 | struct iio_chan_spec const *chan, | ||
320 | int *val, int *val2, long mask) | ||
321 | { | ||
322 | int ret; | ||
323 | struct bmp280_data *data = iio_priv(indio_dev); | ||
324 | |||
325 | mutex_lock(&data->lock); | ||
326 | |||
327 | switch (mask) { | ||
328 | case IIO_CHAN_INFO_PROCESSED: | ||
329 | switch (chan->type) { | ||
330 | case IIO_PRESSURE: | ||
331 | ret = bmp280_read_press(data, val, val2); | ||
332 | break; | ||
333 | case IIO_TEMP: | ||
334 | ret = bmp280_read_temp(data, val); | ||
335 | break; | ||
336 | default: | ||
337 | ret = -EINVAL; | ||
338 | break; | ||
339 | } | ||
340 | break; | ||
341 | default: | ||
342 | ret = -EINVAL; | ||
343 | break; | ||
344 | } | ||
345 | |||
346 | mutex_unlock(&data->lock); | ||
347 | |||
348 | return ret; | ||
349 | } | ||
350 | |||
351 | static const struct iio_info bmp280_info = { | ||
352 | .driver_module = THIS_MODULE, | ||
353 | .read_raw = &bmp280_read_raw, | ||
354 | }; | ||
355 | |||
356 | static int bmp280_chip_init(struct bmp280_data *data) | ||
357 | { | ||
358 | int ret; | ||
359 | |||
360 | ret = regmap_update_bits(data->regmap, BMP280_REG_CTRL_MEAS, | ||
361 | BMP280_OSRS_TEMP_MASK | | ||
362 | BMP280_OSRS_PRESS_MASK | | ||
363 | BMP280_MODE_MASK, | ||
364 | BMP280_OSRS_TEMP_2X | | ||
365 | BMP280_OSRS_PRESS_16X | | ||
366 | BMP280_MODE_NORMAL); | ||
367 | if (ret < 0) { | ||
368 | dev_err(&data->client->dev, | ||
369 | "failed to write config register\n"); | ||
370 | return ret; | ||
371 | } | ||
372 | |||
373 | ret = regmap_update_bits(data->regmap, BMP280_REG_CONFIG, | ||
374 | BMP280_FILTER_MASK, | ||
375 | BMP280_FILTER_4X); | ||
376 | if (ret < 0) { | ||
377 | dev_err(&data->client->dev, | ||
378 | "failed to write config register\n"); | ||
379 | return ret; | ||
380 | } | ||
381 | |||
382 | return ret; | ||
383 | } | ||
384 | |||
385 | static int bmp280_probe(struct i2c_client *client, | ||
386 | const struct i2c_device_id *id) | ||
387 | { | ||
388 | int ret; | ||
389 | struct iio_dev *indio_dev; | ||
390 | struct bmp280_data *data; | ||
391 | unsigned int chip_id; | ||
392 | |||
393 | indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*data)); | ||
394 | if (!indio_dev) | ||
395 | return -ENOMEM; | ||
396 | |||
397 | i2c_set_clientdata(client, indio_dev); | ||
398 | data = iio_priv(indio_dev); | ||
399 | mutex_init(&data->lock); | ||
400 | data->client = client; | ||
401 | |||
402 | indio_dev->dev.parent = &client->dev; | ||
403 | indio_dev->name = id->name; | ||
404 | indio_dev->channels = bmp280_channels; | ||
405 | indio_dev->num_channels = ARRAY_SIZE(bmp280_channels); | ||
406 | indio_dev->info = &bmp280_info; | ||
407 | indio_dev->modes = INDIO_DIRECT_MODE; | ||
408 | |||
409 | data->regmap = devm_regmap_init_i2c(client, &bmp280_regmap_config); | ||
410 | if (IS_ERR(data->regmap)) { | ||
411 | dev_err(&client->dev, "failed to allocate register map\n"); | ||
412 | return PTR_ERR(data->regmap); | ||
413 | } | ||
414 | |||
415 | ret = regmap_read(data->regmap, BMP280_REG_ID, &chip_id); | ||
416 | if (ret < 0) | ||
417 | return ret; | ||
418 | if (chip_id != BMP280_CHIP_ID) { | ||
419 | dev_err(&client->dev, "bad chip id. expected %x got %x\n", | ||
420 | BMP280_CHIP_ID, chip_id); | ||
421 | return -EINVAL; | ||
422 | } | ||
423 | |||
424 | ret = bmp280_chip_init(data); | ||
425 | if (ret < 0) | ||
426 | return ret; | ||
427 | |||
428 | return devm_iio_device_register(&client->dev, indio_dev); | ||
429 | } | ||
430 | |||
431 | static const struct acpi_device_id bmp280_acpi_match[] = { | ||
432 | {"BMP0280", 0}, | ||
433 | { }, | ||
434 | }; | ||
435 | MODULE_DEVICE_TABLE(acpi, bmp280_acpi_match); | ||
436 | |||
437 | static const struct i2c_device_id bmp280_id[] = { | ||
438 | {"bmp280", 0}, | ||
439 | { }, | ||
440 | }; | ||
441 | MODULE_DEVICE_TABLE(i2c, bmp280_id); | ||
442 | |||
443 | static struct i2c_driver bmp280_driver = { | ||
444 | .driver = { | ||
445 | .name = "bmp280", | ||
446 | .acpi_match_table = ACPI_PTR(bmp280_acpi_match), | ||
447 | }, | ||
448 | .probe = bmp280_probe, | ||
449 | .id_table = bmp280_id, | ||
450 | }; | ||
451 | module_i2c_driver(bmp280_driver); | ||
452 | |||
453 | MODULE_AUTHOR("Vlad Dogaru <vlad.dogaru@intel.com>"); | ||
454 | MODULE_DESCRIPTION("Driver for Bosch Sensortec BMP280 pressure and temperature sensor"); | ||
455 | MODULE_LICENSE("GPL v2"); | ||
diff --git a/drivers/iio/pressure/st_pressure.h b/drivers/iio/pressure/st_pressure.h index 242943c0c4e4..f5f41490060b 100644 --- a/drivers/iio/pressure/st_pressure.h +++ b/drivers/iio/pressure/st_pressure.h | |||
@@ -26,8 +26,7 @@ static const struct st_sensors_platform_data default_press_pdata = { | |||
26 | .drdy_int_pin = 1, | 26 | .drdy_int_pin = 1, |
27 | }; | 27 | }; |
28 | 28 | ||
29 | int st_press_common_probe(struct iio_dev *indio_dev, | 29 | int st_press_common_probe(struct iio_dev *indio_dev); |
30 | struct st_sensors_platform_data *pdata); | ||
31 | void st_press_common_remove(struct iio_dev *indio_dev); | 30 | void st_press_common_remove(struct iio_dev *indio_dev); |
32 | 31 | ||
33 | #ifdef CONFIG_IIO_BUFFER | 32 | #ifdef CONFIG_IIO_BUFFER |
diff --git a/drivers/iio/pressure/st_pressure_buffer.c b/drivers/iio/pressure/st_pressure_buffer.c index b37b1c9ac932..2ff53f222352 100644 --- a/drivers/iio/pressure/st_pressure_buffer.c +++ b/drivers/iio/pressure/st_pressure_buffer.c | |||
@@ -38,10 +38,10 @@ static int st_press_buffer_preenable(struct iio_dev *indio_dev) | |||
38 | static int st_press_buffer_postenable(struct iio_dev *indio_dev) | 38 | static int st_press_buffer_postenable(struct iio_dev *indio_dev) |
39 | { | 39 | { |
40 | int err; | 40 | int err; |
41 | struct st_sensor_data *pdata = iio_priv(indio_dev); | 41 | struct st_sensor_data *press_data = iio_priv(indio_dev); |
42 | 42 | ||
43 | pdata->buffer_data = kmalloc(indio_dev->scan_bytes, GFP_KERNEL); | 43 | press_data->buffer_data = kmalloc(indio_dev->scan_bytes, GFP_KERNEL); |
44 | if (pdata->buffer_data == NULL) { | 44 | if (press_data->buffer_data == NULL) { |
45 | err = -ENOMEM; | 45 | err = -ENOMEM; |
46 | goto allocate_memory_error; | 46 | goto allocate_memory_error; |
47 | } | 47 | } |
@@ -53,7 +53,7 @@ static int st_press_buffer_postenable(struct iio_dev *indio_dev) | |||
53 | return err; | 53 | return err; |
54 | 54 | ||
55 | st_press_buffer_postenable_error: | 55 | st_press_buffer_postenable_error: |
56 | kfree(pdata->buffer_data); | 56 | kfree(press_data->buffer_data); |
57 | allocate_memory_error: | 57 | allocate_memory_error: |
58 | return err; | 58 | return err; |
59 | } | 59 | } |
@@ -61,7 +61,7 @@ allocate_memory_error: | |||
61 | static int st_press_buffer_predisable(struct iio_dev *indio_dev) | 61 | static int st_press_buffer_predisable(struct iio_dev *indio_dev) |
62 | { | 62 | { |
63 | int err; | 63 | int err; |
64 | struct st_sensor_data *pdata = iio_priv(indio_dev); | 64 | struct st_sensor_data *press_data = iio_priv(indio_dev); |
65 | 65 | ||
66 | err = iio_triggered_buffer_predisable(indio_dev); | 66 | err = iio_triggered_buffer_predisable(indio_dev); |
67 | if (err < 0) | 67 | if (err < 0) |
@@ -70,7 +70,7 @@ static int st_press_buffer_predisable(struct iio_dev *indio_dev) | |||
70 | err = st_sensors_set_enable(indio_dev, false); | 70 | err = st_sensors_set_enable(indio_dev, false); |
71 | 71 | ||
72 | st_press_buffer_predisable_error: | 72 | st_press_buffer_predisable_error: |
73 | kfree(pdata->buffer_data); | 73 | kfree(press_data->buffer_data); |
74 | return err; | 74 | return err; |
75 | } | 75 | } |
76 | 76 | ||
diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index 473d914ef470..97baf40d424b 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c | |||
@@ -175,7 +175,7 @@ static const struct iio_chan_spec st_press_lps001wp_channels[] = { | |||
175 | IIO_CHAN_SOFT_TIMESTAMP(1) | 175 | IIO_CHAN_SOFT_TIMESTAMP(1) |
176 | }; | 176 | }; |
177 | 177 | ||
178 | static const struct st_sensors st_press_sensors[] = { | 178 | static const struct st_sensor_settings st_press_sensors_settings[] = { |
179 | { | 179 | { |
180 | .wai = ST_PRESS_LPS331AP_WAI_EXP, | 180 | .wai = ST_PRESS_LPS331AP_WAI_EXP, |
181 | .sensors_supported = { | 181 | .sensors_supported = { |
@@ -333,7 +333,7 @@ static int st_press_read_raw(struct iio_dev *indio_dev, | |||
333 | int *val2, long mask) | 333 | int *val2, long mask) |
334 | { | 334 | { |
335 | int err; | 335 | int err; |
336 | struct st_sensor_data *pdata = iio_priv(indio_dev); | 336 | struct st_sensor_data *press_data = iio_priv(indio_dev); |
337 | 337 | ||
338 | switch (mask) { | 338 | switch (mask) { |
339 | case IIO_CHAN_INFO_RAW: | 339 | case IIO_CHAN_INFO_RAW: |
@@ -347,10 +347,10 @@ static int st_press_read_raw(struct iio_dev *indio_dev, | |||
347 | 347 | ||
348 | switch (ch->type) { | 348 | switch (ch->type) { |
349 | case IIO_PRESSURE: | 349 | case IIO_PRESSURE: |
350 | *val2 = pdata->current_fullscale->gain; | 350 | *val2 = press_data->current_fullscale->gain; |
351 | break; | 351 | break; |
352 | case IIO_TEMP: | 352 | case IIO_TEMP: |
353 | *val2 = pdata->current_fullscale->gain2; | 353 | *val2 = press_data->current_fullscale->gain2; |
354 | break; | 354 | break; |
355 | default: | 355 | default: |
356 | err = -EINVAL; | 356 | err = -EINVAL; |
@@ -371,7 +371,7 @@ static int st_press_read_raw(struct iio_dev *indio_dev, | |||
371 | 371 | ||
372 | return IIO_VAL_FRACTIONAL; | 372 | return IIO_VAL_FRACTIONAL; |
373 | case IIO_CHAN_INFO_SAMP_FREQ: | 373 | case IIO_CHAN_INFO_SAMP_FREQ: |
374 | *val = pdata->odr; | 374 | *val = press_data->odr; |
375 | return IIO_VAL_INT; | 375 | return IIO_VAL_INT; |
376 | default: | 376 | default: |
377 | return -EINVAL; | 377 | return -EINVAL; |
@@ -409,11 +409,10 @@ static const struct iio_trigger_ops st_press_trigger_ops = { | |||
409 | #define ST_PRESS_TRIGGER_OPS NULL | 409 | #define ST_PRESS_TRIGGER_OPS NULL |
410 | #endif | 410 | #endif |
411 | 411 | ||
412 | int st_press_common_probe(struct iio_dev *indio_dev, | 412 | int st_press_common_probe(struct iio_dev *indio_dev) |
413 | struct st_sensors_platform_data *plat_data) | ||
414 | { | 413 | { |
415 | struct st_sensor_data *pdata = iio_priv(indio_dev); | 414 | struct st_sensor_data *press_data = iio_priv(indio_dev); |
416 | int irq = pdata->get_irq_data_ready(indio_dev); | 415 | int irq = press_data->get_irq_data_ready(indio_dev); |
417 | int err; | 416 | int err; |
418 | 417 | ||
419 | indio_dev->modes = INDIO_DIRECT_MODE; | 418 | indio_dev->modes = INDIO_DIRECT_MODE; |
@@ -422,28 +421,30 @@ int st_press_common_probe(struct iio_dev *indio_dev, | |||
422 | st_sensors_power_enable(indio_dev); | 421 | st_sensors_power_enable(indio_dev); |
423 | 422 | ||
424 | err = st_sensors_check_device_support(indio_dev, | 423 | err = st_sensors_check_device_support(indio_dev, |
425 | ARRAY_SIZE(st_press_sensors), | 424 | ARRAY_SIZE(st_press_sensors_settings), |
426 | st_press_sensors); | 425 | st_press_sensors_settings); |
427 | if (err < 0) | 426 | if (err < 0) |
428 | return err; | 427 | return err; |
429 | 428 | ||
430 | pdata->num_data_channels = ST_PRESS_NUMBER_DATA_CHANNELS; | 429 | press_data->num_data_channels = ST_PRESS_NUMBER_DATA_CHANNELS; |
431 | pdata->multiread_bit = pdata->sensor->multi_read_bit; | 430 | press_data->multiread_bit = press_data->sensor_settings->multi_read_bit; |
432 | indio_dev->channels = pdata->sensor->ch; | 431 | indio_dev->channels = press_data->sensor_settings->ch; |
433 | indio_dev->num_channels = pdata->sensor->num_ch; | 432 | indio_dev->num_channels = press_data->sensor_settings->num_ch; |
434 | 433 | ||
435 | if (pdata->sensor->fs.addr != 0) | 434 | if (press_data->sensor_settings->fs.addr != 0) |
436 | pdata->current_fullscale = (struct st_sensor_fullscale_avl *) | 435 | press_data->current_fullscale = |
437 | &pdata->sensor->fs.fs_avl[0]; | 436 | (struct st_sensor_fullscale_avl *) |
437 | &press_data->sensor_settings->fs.fs_avl[0]; | ||
438 | 438 | ||
439 | pdata->odr = pdata->sensor->odr.odr_avl[0].hz; | 439 | press_data->odr = press_data->sensor_settings->odr.odr_avl[0].hz; |
440 | 440 | ||
441 | /* Some devices don't support a data ready pin. */ | 441 | /* Some devices don't support a data ready pin. */ |
442 | if (!plat_data && pdata->sensor->drdy_irq.addr) | 442 | if (!press_data->dev->platform_data && |
443 | plat_data = | 443 | press_data->sensor_settings->drdy_irq.addr) |
444 | press_data->dev->platform_data = | ||
444 | (struct st_sensors_platform_data *)&default_press_pdata; | 445 | (struct st_sensors_platform_data *)&default_press_pdata; |
445 | 446 | ||
446 | err = st_sensors_init_sensor(indio_dev, plat_data); | 447 | err = st_sensors_init_sensor(indio_dev, press_data->dev->platform_data); |
447 | if (err < 0) | 448 | if (err < 0) |
448 | return err; | 449 | return err; |
449 | 450 | ||
@@ -479,12 +480,12 @@ EXPORT_SYMBOL(st_press_common_probe); | |||
479 | 480 | ||
480 | void st_press_common_remove(struct iio_dev *indio_dev) | 481 | void st_press_common_remove(struct iio_dev *indio_dev) |
481 | { | 482 | { |
482 | struct st_sensor_data *pdata = iio_priv(indio_dev); | 483 | struct st_sensor_data *press_data = iio_priv(indio_dev); |
483 | 484 | ||
484 | st_sensors_power_disable(indio_dev); | 485 | st_sensors_power_disable(indio_dev); |
485 | 486 | ||
486 | iio_device_unregister(indio_dev); | 487 | iio_device_unregister(indio_dev); |
487 | if (pdata->get_irq_data_ready(indio_dev) > 0) | 488 | if (press_data->get_irq_data_ready(indio_dev) > 0) |
488 | st_sensors_deallocate_trigger(indio_dev); | 489 | st_sensors_deallocate_trigger(indio_dev); |
489 | 490 | ||
490 | st_press_deallocate_ring(indio_dev); | 491 | st_press_deallocate_ring(indio_dev); |
diff --git a/drivers/iio/pressure/st_pressure_i2c.c b/drivers/iio/pressure/st_pressure_i2c.c index acaf165260bb..137788bba4a3 100644 --- a/drivers/iio/pressure/st_pressure_i2c.c +++ b/drivers/iio/pressure/st_pressure_i2c.c | |||
@@ -43,20 +43,19 @@ static int st_press_i2c_probe(struct i2c_client *client, | |||
43 | const struct i2c_device_id *id) | 43 | const struct i2c_device_id *id) |
44 | { | 44 | { |
45 | struct iio_dev *indio_dev; | 45 | struct iio_dev *indio_dev; |
46 | struct st_sensor_data *pdata; | 46 | struct st_sensor_data *press_data; |
47 | int err; | 47 | int err; |
48 | 48 | ||
49 | indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*pdata)); | 49 | indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*press_data)); |
50 | if (!indio_dev) | 50 | if (!indio_dev) |
51 | return -ENOMEM; | 51 | return -ENOMEM; |
52 | 52 | ||
53 | pdata = iio_priv(indio_dev); | 53 | press_data = iio_priv(indio_dev); |
54 | pdata->dev = &client->dev; | ||
55 | st_sensors_of_i2c_probe(client, st_press_of_match); | 54 | st_sensors_of_i2c_probe(client, st_press_of_match); |
56 | 55 | ||
57 | st_sensors_i2c_configure(indio_dev, client, pdata); | 56 | st_sensors_i2c_configure(indio_dev, client, press_data); |
58 | 57 | ||
59 | err = st_press_common_probe(indio_dev, client->dev.platform_data); | 58 | err = st_press_common_probe(indio_dev); |
60 | if (err < 0) | 59 | if (err < 0) |
61 | return err; | 60 | return err; |
62 | 61 | ||
diff --git a/drivers/iio/pressure/st_pressure_spi.c b/drivers/iio/pressure/st_pressure_spi.c index f45d430ec529..1ffa6d4d349c 100644 --- a/drivers/iio/pressure/st_pressure_spi.c +++ b/drivers/iio/pressure/st_pressure_spi.c | |||
@@ -21,19 +21,18 @@ | |||
21 | static int st_press_spi_probe(struct spi_device *spi) | 21 | static int st_press_spi_probe(struct spi_device *spi) |
22 | { | 22 | { |
23 | struct iio_dev *indio_dev; | 23 | struct iio_dev *indio_dev; |
24 | struct st_sensor_data *pdata; | 24 | struct st_sensor_data *press_data; |
25 | int err; | 25 | int err; |
26 | 26 | ||
27 | indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*pdata)); | 27 | indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*press_data)); |
28 | if (indio_dev == NULL) | 28 | if (indio_dev == NULL) |
29 | return -ENOMEM; | 29 | return -ENOMEM; |
30 | 30 | ||
31 | pdata = iio_priv(indio_dev); | 31 | press_data = iio_priv(indio_dev); |
32 | pdata->dev = &spi->dev; | ||
33 | 32 | ||
34 | st_sensors_spi_configure(indio_dev, spi, pdata); | 33 | st_sensors_spi_configure(indio_dev, spi, press_data); |
35 | 34 | ||
36 | err = st_press_common_probe(indio_dev, spi->dev.platform_data); | 35 | err = st_press_common_probe(indio_dev); |
37 | if (err < 0) | 36 | if (err < 0) |
38 | return err; | 37 | return err; |
39 | 38 | ||
diff --git a/drivers/iio/proximity/as3935.c b/drivers/iio/proximity/as3935.c index 5e780ef206f3..78244e6343f6 100644 --- a/drivers/iio/proximity/as3935.c +++ b/drivers/iio/proximity/as3935.c | |||
@@ -95,7 +95,7 @@ static int as3935_read(struct as3935_state *st, unsigned int reg, int *val) | |||
95 | *val = ret; | 95 | *val = ret; |
96 | 96 | ||
97 | return 0; | 97 | return 0; |
98 | }; | 98 | } |
99 | 99 | ||
100 | static int as3935_write(struct as3935_state *st, | 100 | static int as3935_write(struct as3935_state *st, |
101 | unsigned int reg, | 101 | unsigned int reg, |
@@ -107,7 +107,7 @@ static int as3935_write(struct as3935_state *st, | |||
107 | buf[1] = val; | 107 | buf[1] = val; |
108 | 108 | ||
109 | return spi_write(st->spi, buf, 2); | 109 | return spi_write(st->spi, buf, 2); |
110 | }; | 110 | } |
111 | 111 | ||
112 | static ssize_t as3935_sensor_sensitivity_show(struct device *dev, | 112 | static ssize_t as3935_sensor_sensitivity_show(struct device *dev, |
113 | struct device_attribute *attr, | 113 | struct device_attribute *attr, |
@@ -122,7 +122,7 @@ static ssize_t as3935_sensor_sensitivity_show(struct device *dev, | |||
122 | val = (val & AS3935_AFE_MASK) >> 1; | 122 | val = (val & AS3935_AFE_MASK) >> 1; |
123 | 123 | ||
124 | return sprintf(buf, "%d\n", val); | 124 | return sprintf(buf, "%d\n", val); |
125 | }; | 125 | } |
126 | 126 | ||
127 | static ssize_t as3935_sensor_sensitivity_store(struct device *dev, | 127 | static ssize_t as3935_sensor_sensitivity_store(struct device *dev, |
128 | struct device_attribute *attr, | 128 | struct device_attribute *attr, |
@@ -142,7 +142,7 @@ static ssize_t as3935_sensor_sensitivity_store(struct device *dev, | |||
142 | as3935_write(st, AS3935_AFE_GAIN, val << 1); | 142 | as3935_write(st, AS3935_AFE_GAIN, val << 1); |
143 | 143 | ||
144 | return len; | 144 | return len; |
145 | }; | 145 | } |
146 | 146 | ||
147 | static IIO_DEVICE_ATTR(sensor_sensitivity, S_IRUGO | S_IWUSR, | 147 | static IIO_DEVICE_ATTR(sensor_sensitivity, S_IRUGO | S_IWUSR, |
148 | as3935_sensor_sensitivity_show, as3935_sensor_sensitivity_store, 0); | 148 | as3935_sensor_sensitivity_show, as3935_sensor_sensitivity_store, 0); |
@@ -214,7 +214,7 @@ err_read: | |||
214 | iio_trigger_notify_done(indio_dev->trig); | 214 | iio_trigger_notify_done(indio_dev->trig); |
215 | 215 | ||
216 | return IRQ_HANDLED; | 216 | return IRQ_HANDLED; |
217 | }; | 217 | } |
218 | 218 | ||
219 | static const struct iio_trigger_ops iio_interrupt_trigger_ops = { | 219 | static const struct iio_trigger_ops iio_interrupt_trigger_ops = { |
220 | .owner = THIS_MODULE, | 220 | .owner = THIS_MODULE, |
@@ -238,7 +238,7 @@ static void as3935_event_work(struct work_struct *work) | |||
238 | dev_warn(&st->spi->dev, "noise level is too high"); | 238 | dev_warn(&st->spi->dev, "noise level is too high"); |
239 | break; | 239 | break; |
240 | } | 240 | } |
241 | }; | 241 | } |
242 | 242 | ||
243 | static irqreturn_t as3935_interrupt_handler(int irq, void *private) | 243 | static irqreturn_t as3935_interrupt_handler(int irq, void *private) |
244 | { | 244 | { |
@@ -417,7 +417,7 @@ unregister_trigger: | |||
417 | iio_trigger_unregister(st->trig); | 417 | iio_trigger_unregister(st->trig); |
418 | 418 | ||
419 | return ret; | 419 | return ret; |
420 | }; | 420 | } |
421 | 421 | ||
422 | static int as3935_remove(struct spi_device *spi) | 422 | static int as3935_remove(struct spi_device *spi) |
423 | { | 423 | { |
@@ -429,7 +429,7 @@ static int as3935_remove(struct spi_device *spi) | |||
429 | iio_trigger_unregister(st->trig); | 429 | iio_trigger_unregister(st->trig); |
430 | 430 | ||
431 | return 0; | 431 | return 0; |
432 | }; | 432 | } |
433 | 433 | ||
434 | static const struct spi_device_id as3935_id[] = { | 434 | static const struct spi_device_id as3935_id[] = { |
435 | {"as3935", 0}, | 435 | {"as3935", 0}, |