From 362f2f8647cfa53e36bf910b42ad084674ade9dc Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Tue, 10 Sep 2013 13:49:00 +0100 Subject: iio: sensors-core: st: Allow full-scale to be an optional feature Some chips either don't support it or fail to provide adequate documentation, so sometimes it's impossible to enable the feature even if it is supported. Signed-off-by: Lee Jones Acked-by: Denis Ciocca Signed-off-by: Jonathan Cameron --- drivers/iio/pressure/st_pressure_core.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index ceebd3c2789..16cfbc53076 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -226,8 +226,10 @@ int st_press_common_probe(struct iio_dev *indio_dev, indio_dev->channels = pdata->sensor->ch; indio_dev->num_channels = ARRAY_SIZE(st_press_channels); - pdata->current_fullscale = (struct st_sensor_fullscale_avl *) - &pdata->sensor->fs.fs_avl[0]; + if (pdata->sensor->fs.addr != 0) + pdata->current_fullscale = (struct st_sensor_fullscale_avl *) + &pdata->sensor->fs.fs_avl[0]; + pdata->odr = pdata->sensor->odr.odr_avl[0].hz; if (!plat_data) -- cgit v1.2.3-70-g09d2 From 302fbd50ef31a93aee67061ed4594dceb94b0783 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Tue, 10 Sep 2013 13:49:00 +0100 Subject: iio: pressure-core: st: Describe LPS331AP defines by name They're currently named *_1_*, for 'Sensor 1', but the code will be much more readable if we use the naming convention *_LPS331AP_* instead. Signed-off-by: Lee Jones Signed-off-by: Jonathan Cameron --- drivers/iio/pressure/st_pressure_core.c | 94 ++++++++++++++++----------------- 1 file changed, 46 insertions(+), 48 deletions(-) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index 16cfbc53076..541340b874f 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -36,94 +36,92 @@ ST_PRESS_LSB_PER_CELSIUS) #define ST_PRESS_NUMBER_DATA_CHANNELS 1 -/* DEFAULT VALUE FOR SENSORS */ -#define ST_PRESS_DEFAULT_OUT_XL_ADDR 0x28 -#define ST_TEMP_DEFAULT_OUT_L_ADDR 0x2b - /* FULLSCALE */ #define ST_PRESS_FS_AVL_1260MB 1260 -/* CUSTOM VALUES FOR SENSOR 1 */ -#define ST_PRESS_1_WAI_EXP 0xbb -#define ST_PRESS_1_ODR_ADDR 0x20 -#define ST_PRESS_1_ODR_MASK 0x70 -#define ST_PRESS_1_ODR_AVL_1HZ_VAL 0x01 -#define ST_PRESS_1_ODR_AVL_7HZ_VAL 0x05 -#define ST_PRESS_1_ODR_AVL_13HZ_VAL 0x06 -#define ST_PRESS_1_ODR_AVL_25HZ_VAL 0x07 -#define ST_PRESS_1_PW_ADDR 0x20 -#define ST_PRESS_1_PW_MASK 0x80 -#define ST_PRESS_1_FS_ADDR 0x23 -#define ST_PRESS_1_FS_MASK 0x30 -#define ST_PRESS_1_FS_AVL_1260_VAL 0x00 -#define ST_PRESS_1_FS_AVL_1260_GAIN ST_PRESS_KPASCAL_NANO_SCALE -#define ST_PRESS_1_FS_AVL_TEMP_GAIN ST_PRESS_CELSIUS_NANO_SCALE -#define ST_PRESS_1_BDU_ADDR 0x20 -#define ST_PRESS_1_BDU_MASK 0x04 -#define ST_PRESS_1_DRDY_IRQ_ADDR 0x22 -#define ST_PRESS_1_DRDY_IRQ_INT1_MASK 0x04 -#define ST_PRESS_1_DRDY_IRQ_INT2_MASK 0x20 -#define ST_PRESS_1_MULTIREAD_BIT true -#define ST_PRESS_1_TEMP_OFFSET 42500 +/* CUSTOM VALUES FOR LPS331AP SENSOR */ +#define ST_PRESS_LPS331AP_WAI_EXP 0xbb +#define ST_PRESS_LPS331AP_ODR_ADDR 0x20 +#define ST_PRESS_LPS331AP_ODR_MASK 0x70 +#define ST_PRESS_LPS331AP_ODR_AVL_1HZ_VAL 0x01 +#define ST_PRESS_LPS331AP_ODR_AVL_7HZ_VAL 0x05 +#define ST_PRESS_LPS331AP_ODR_AVL_13HZ_VAL 0x06 +#define ST_PRESS_LPS331AP_ODR_AVL_25HZ_VAL 0x07 +#define ST_PRESS_LPS331AP_PW_ADDR 0x20 +#define ST_PRESS_LPS331AP_PW_MASK 0x80 +#define ST_PRESS_LPS331AP_FS_ADDR 0x23 +#define ST_PRESS_LPS331AP_FS_MASK 0x30 +#define ST_PRESS_LPS331AP_FS_AVL_1260_VAL 0x00 +#define ST_PRESS_LPS331AP_FS_AVL_1260_GAIN ST_PRESS_KPASCAL_NANO_SCALE +#define ST_PRESS_LPS331AP_FS_AVL_TEMP_GAIN ST_PRESS_CELSIUS_NANO_SCALE +#define ST_PRESS_LPS331AP_BDU_ADDR 0x20 +#define ST_PRESS_LPS331AP_BDU_MASK 0x04 +#define ST_PRESS_LPS331AP_DRDY_IRQ_ADDR 0x22 +#define ST_PRESS_LPS331AP_DRDY_IRQ_INT1_MASK 0x04 +#define ST_PRESS_LPS331AP_DRDY_IRQ_INT2_MASK 0x20 +#define ST_PRESS_LPS331AP_MULTIREAD_BIT true +#define ST_PRESS_LPS331AP_TEMP_OFFSET 42500 +#define ST_PRESS_LPS331AP_OUT_XL_ADDR 0x28 +#define ST_TEMP_LPS331AP_OUT_L_ADDR 0x2b static const struct iio_chan_spec st_press_channels[] = { ST_SENSORS_LSM_CHANNELS(IIO_PRESSURE, BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE), ST_SENSORS_SCAN_X, 0, IIO_NO_MOD, 'u', IIO_LE, 24, 24, - ST_PRESS_DEFAULT_OUT_XL_ADDR), + ST_PRESS_LPS331AP_OUT_XL_ADDR), ST_SENSORS_LSM_CHANNELS(IIO_TEMP, BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE) | BIT(IIO_CHAN_INFO_OFFSET), -1, 0, IIO_NO_MOD, 's', IIO_LE, 16, 16, - ST_TEMP_DEFAULT_OUT_L_ADDR), + ST_TEMP_LPS331AP_OUT_L_ADDR), IIO_CHAN_SOFT_TIMESTAMP(1) }; static const struct st_sensors st_press_sensors[] = { { - .wai = ST_PRESS_1_WAI_EXP, + .wai = ST_PRESS_LPS331AP_WAI_EXP, .sensors_supported = { [0] = LPS331AP_PRESS_DEV_NAME, }, .ch = (struct iio_chan_spec *)st_press_channels, .odr = { - .addr = ST_PRESS_1_ODR_ADDR, - .mask = ST_PRESS_1_ODR_MASK, + .addr = ST_PRESS_LPS331AP_ODR_ADDR, + .mask = ST_PRESS_LPS331AP_ODR_MASK, .odr_avl = { - { 1, ST_PRESS_1_ODR_AVL_1HZ_VAL, }, - { 7, ST_PRESS_1_ODR_AVL_7HZ_VAL, }, - { 13, ST_PRESS_1_ODR_AVL_13HZ_VAL, }, - { 25, ST_PRESS_1_ODR_AVL_25HZ_VAL, }, + { 1, ST_PRESS_LPS331AP_ODR_AVL_1HZ_VAL, }, + { 7, ST_PRESS_LPS331AP_ODR_AVL_7HZ_VAL, }, + { 13, ST_PRESS_LPS331AP_ODR_AVL_13HZ_VAL, }, + { 25, ST_PRESS_LPS331AP_ODR_AVL_25HZ_VAL, }, }, }, .pw = { - .addr = ST_PRESS_1_PW_ADDR, - .mask = ST_PRESS_1_PW_MASK, + .addr = ST_PRESS_LPS331AP_PW_ADDR, + .mask = ST_PRESS_LPS331AP_PW_MASK, .value_on = ST_SENSORS_DEFAULT_POWER_ON_VALUE, .value_off = ST_SENSORS_DEFAULT_POWER_OFF_VALUE, }, .fs = { - .addr = ST_PRESS_1_FS_ADDR, - .mask = ST_PRESS_1_FS_MASK, + .addr = ST_PRESS_LPS331AP_FS_ADDR, + .mask = ST_PRESS_LPS331AP_FS_MASK, .fs_avl = { [0] = { .num = ST_PRESS_FS_AVL_1260MB, - .value = ST_PRESS_1_FS_AVL_1260_VAL, - .gain = ST_PRESS_1_FS_AVL_1260_GAIN, - .gain2 = ST_PRESS_1_FS_AVL_TEMP_GAIN, + .value = ST_PRESS_LPS331AP_FS_AVL_1260_VAL, + .gain = ST_PRESS_LPS331AP_FS_AVL_1260_GAIN, + .gain2 = ST_PRESS_LPS331AP_FS_AVL_TEMP_GAIN, }, }, }, .bdu = { - .addr = ST_PRESS_1_BDU_ADDR, - .mask = ST_PRESS_1_BDU_MASK, + .addr = ST_PRESS_LPS331AP_BDU_ADDR, + .mask = ST_PRESS_LPS331AP_BDU_MASK, }, .drdy_irq = { - .addr = ST_PRESS_1_DRDY_IRQ_ADDR, - .mask_int1 = ST_PRESS_1_DRDY_IRQ_INT1_MASK, - .mask_int2 = ST_PRESS_1_DRDY_IRQ_INT2_MASK, + .addr = ST_PRESS_LPS331AP_DRDY_IRQ_ADDR, + .mask_int1 = ST_PRESS_LPS331AP_DRDY_IRQ_INT1_MASK, + .mask_int2 = ST_PRESS_LPS331AP_DRDY_IRQ_INT2_MASK, }, - .multi_read_bit = ST_PRESS_1_MULTIREAD_BIT, + .multi_read_bit = ST_PRESS_LPS331AP_MULTIREAD_BIT, .bootime = 2, }, }; -- cgit v1.2.3-70-g09d2 From 2f5effcbd097a37690c86b80a3c242dd8338d59c Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Tue, 10 Sep 2013 13:49:00 +0100 Subject: iio: pressure-core: st: Expand and rename LPS331AP's channel descriptor Due to the MACRO used, the task of reading, understanding and maintaining the LPS331AP's channel descriptor is substantially difficult. This patch is based on the view that it's better to have easy to read, maintainable code than to save a few lines here and there. For that reason we're expanding the array so initialisation is completed in full. Signed-off-by: Lee Jones Signed-off-by: Jonathan Cameron --- drivers/iio/pressure/st_pressure_core.c | 45 +++++++++++++++++++++++++-------- 1 file changed, 34 insertions(+), 11 deletions(-) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index 541340b874f..506b02d27b0 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -64,16 +64,39 @@ #define ST_PRESS_LPS331AP_OUT_XL_ADDR 0x28 #define ST_TEMP_LPS331AP_OUT_L_ADDR 0x2b -static const struct iio_chan_spec st_press_channels[] = { - ST_SENSORS_LSM_CHANNELS(IIO_PRESSURE, +static const struct iio_chan_spec st_press_lps331ap_channels[] = { + { + .type = IIO_PRESSURE, + .channel2 = IIO_NO_MOD, + .address = ST_PRESS_LPS331AP_OUT_XL_ADDR, + .scan_index = ST_SENSORS_SCAN_X, + .scan_type = { + .sign = 'u', + .realbits = 24, + .storagebits = 24, + .endianness = IIO_LE, + }, + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE), - ST_SENSORS_SCAN_X, 0, IIO_NO_MOD, 'u', IIO_LE, 24, 24, - ST_PRESS_LPS331AP_OUT_XL_ADDR), - ST_SENSORS_LSM_CHANNELS(IIO_TEMP, - BIT(IIO_CHAN_INFO_RAW) | BIT(IIO_CHAN_INFO_SCALE) | - BIT(IIO_CHAN_INFO_OFFSET), - -1, 0, IIO_NO_MOD, 's', IIO_LE, 16, 16, - ST_TEMP_LPS331AP_OUT_L_ADDR), + .modified = 0, + }, + { + .type = IIO_TEMP, + .channel2 = IIO_NO_MOD, + .address = ST_TEMP_LPS331AP_OUT_L_ADDR, + .scan_index = -1, + .scan_type = { + .sign = 'u', + .realbits = 16, + .storagebits = 16, + .endianness = IIO_LE, + }, + .info_mask_separate = + BIT(IIO_CHAN_INFO_RAW) | + BIT(IIO_CHAN_INFO_SCALE) | + BIT(IIO_CHAN_INFO_OFFSET), + .modified = 0, + }, IIO_CHAN_SOFT_TIMESTAMP(1) }; @@ -83,7 +106,7 @@ static const struct st_sensors st_press_sensors[] = { .sensors_supported = { [0] = LPS331AP_PRESS_DEV_NAME, }, - .ch = (struct iio_chan_spec *)st_press_channels, + .ch = (struct iio_chan_spec *)st_press_lps331ap_channels, .odr = { .addr = ST_PRESS_LPS331AP_ODR_ADDR, .mask = ST_PRESS_LPS331AP_ODR_MASK, @@ -222,7 +245,7 @@ int st_press_common_probe(struct iio_dev *indio_dev, pdata->num_data_channels = ST_PRESS_NUMBER_DATA_CHANNELS; pdata->multiread_bit = pdata->sensor->multi_read_bit; indio_dev->channels = pdata->sensor->ch; - indio_dev->num_channels = ARRAY_SIZE(st_press_channels); + indio_dev->num_channels = ARRAY_SIZE(st_press_lps331ap_channels); if (pdata->sensor->fs.addr != 0) pdata->current_fullscale = (struct st_sensor_fullscale_avl *) -- cgit v1.2.3-70-g09d2 From ea01f2c18a22a2a8385909d64662afc92da6b13f Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Tue, 10 Sep 2013 13:49:00 +0100 Subject: iio: pressure-core: st: Allow for number of channels to vary At the moment the number of channels specified is dictated by the first sensor supported by the driver. As we add support for more sensors this is likely to vary. Instead of using the ARRAY_SIZE() of the LPS331AP's channel specifier we'll use a new adaptable 'struct st_sensors' element instead. Signed-off-by: Lee Jones Acked-by: Denis Ciocca Signed-off-by: Jonathan Cameron --- drivers/iio/pressure/st_pressure_core.c | 3 ++- include/linux/iio/common/st_sensors.h | 1 + 2 files changed, 3 insertions(+), 1 deletion(-) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index 506b02d27b0..93bff9ba05d 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -107,6 +107,7 @@ static const struct st_sensors st_press_sensors[] = { [0] = LPS331AP_PRESS_DEV_NAME, }, .ch = (struct iio_chan_spec *)st_press_lps331ap_channels, + .num_ch = ARRAY_SIZE(st_press_lps331ap_channels), .odr = { .addr = ST_PRESS_LPS331AP_ODR_ADDR, .mask = ST_PRESS_LPS331AP_ODR_MASK, @@ -245,7 +246,7 @@ int st_press_common_probe(struct iio_dev *indio_dev, pdata->num_data_channels = ST_PRESS_NUMBER_DATA_CHANNELS; pdata->multiread_bit = pdata->sensor->multi_read_bit; indio_dev->channels = pdata->sensor->ch; - indio_dev->num_channels = ARRAY_SIZE(st_press_lps331ap_channels); + indio_dev->num_channels = pdata->sensor->num_ch; if (pdata->sensor->fs.addr != 0) pdata->current_fullscale = (struct st_sensor_fullscale_avl *) diff --git a/include/linux/iio/common/st_sensors.h b/include/linux/iio/common/st_sensors.h index e51f65480ea..e732fda6c8e 100644 --- a/include/linux/iio/common/st_sensors.h +++ b/include/linux/iio/common/st_sensors.h @@ -184,6 +184,7 @@ struct st_sensors { u8 wai; char sensors_supported[ST_SENSORS_MAX_4WAI][ST_SENSORS_MAX_NAME]; struct iio_chan_spec *ch; + int num_ch; struct st_sensor_odr odr; struct st_sensor_power pw; struct st_sensor_axis enable_axis; -- cgit v1.2.3-70-g09d2 From 38d1c6a9116bd9642ebcb027ac66305590aa8488 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Mon, 16 Sep 2013 17:02:00 +0100 Subject: iio: sensors-core: st: Support sensors which don't have a Data Ready pin Not all ST's sensors support data ready, so let's make the declaration of one conditional. Signed-off-by: Lee Jones Signed-off-by: Jonathan Cameron --- drivers/iio/common/st_sensors/st_sensors_core.c | 33 ++++++++++++++++--------- drivers/iio/pressure/st_pressure_core.c | 3 ++- 2 files changed, 24 insertions(+), 12 deletions(-) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/common/st_sensors/st_sensors_core.c b/drivers/iio/common/st_sensors/st_sensors_core.c index 793136aff39..d21b611d875 100644 --- a/drivers/iio/common/st_sensors/st_sensors_core.c +++ b/drivers/iio/common/st_sensors/st_sensors_core.c @@ -198,21 +198,17 @@ int st_sensors_set_axis_enable(struct iio_dev *indio_dev, u8 axis_enable) } EXPORT_SYMBOL(st_sensors_set_axis_enable); -int st_sensors_init_sensor(struct iio_dev *indio_dev, - struct st_sensors_platform_data *pdata) +static int st_sensors_set_drdy_int_pin(struct iio_dev *indio_dev, + struct st_sensors_platform_data *pdata) { - int err; struct st_sensor_data *sdata = iio_priv(indio_dev); - mutex_init(&sdata->tb.buf_lock); - switch (pdata->drdy_int_pin) { case 1: if (sdata->sensor->drdy_irq.mask_int1 == 0) { dev_err(&indio_dev->dev, "DRDY on INT1 not available.\n"); - err = -EINVAL; - goto init_error; + return -EINVAL; } sdata->drdy_int_pin = 1; break; @@ -220,17 +216,29 @@ int st_sensors_init_sensor(struct iio_dev *indio_dev, if (sdata->sensor->drdy_irq.mask_int2 == 0) { dev_err(&indio_dev->dev, "DRDY on INT2 not available.\n"); - err = -EINVAL; - goto init_error; + return -EINVAL; } sdata->drdy_int_pin = 2; break; default: dev_err(&indio_dev->dev, "DRDY on pdata not valid.\n"); - err = -EINVAL; - goto init_error; + return -EINVAL; } + return 0; +} + +int st_sensors_init_sensor(struct iio_dev *indio_dev, + struct st_sensors_platform_data *pdata) +{ + struct st_sensor_data *sdata = iio_priv(indio_dev); + int err = 0; + + mutex_init(&sdata->tb.buf_lock); + + if (pdata) + err = st_sensors_set_drdy_int_pin(indio_dev, pdata); + err = st_sensors_set_enable(indio_dev, false); if (err < 0) goto init_error; @@ -266,6 +274,9 @@ int st_sensors_set_dataready_irq(struct iio_dev *indio_dev, bool enable) u8 drdy_mask; struct st_sensor_data *sdata = iio_priv(indio_dev); + if (!sdata->sensor->drdy_irq.addr) + return 0; + /* Enable/Disable the interrupt generator 1. */ if (sdata->sensor->drdy_irq.ig1.en_addr > 0) { err = st_sensors_write_data_with_mask(indio_dev, diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index 93bff9ba05d..3abada26c3c 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -254,7 +254,8 @@ int st_press_common_probe(struct iio_dev *indio_dev, pdata->odr = pdata->sensor->odr.odr_avl[0].hz; - if (!plat_data) + /* Some devices don't support a data ready pin. */ + if (!plat_data && pdata->sensor->drdy_irq.addr) plat_data = (struct st_sensors_platform_data *)&default_press_pdata; -- cgit v1.2.3-70-g09d2 From a6cc5b250c88930c47a0a231107844b69f086428 Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Mon, 16 Sep 2013 17:02:00 +0100 Subject: iio: pressure-core: st: Clean-up probe() function This patch contains some pretty basic clean-ups in probe() pertaining to the simplification of error handling and a couple of readability adaptions. Signed-off-by: Lee Jones Signed-off-by: Jonathan Cameron --- drivers/iio/pressure/st_pressure_core.c | 28 +++++++++++++++------------- 1 file changed, 15 insertions(+), 13 deletions(-) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index 3abada26c3c..453995310d4 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -232,21 +232,23 @@ static const struct iio_trigger_ops st_press_trigger_ops = { int st_press_common_probe(struct iio_dev *indio_dev, struct st_sensors_platform_data *plat_data) { - int err; struct st_sensor_data *pdata = iio_priv(indio_dev); + int irq = pdata->get_irq_data_ready(indio_dev); + int err; indio_dev->modes = INDIO_DIRECT_MODE; indio_dev->info = &press_info; err = st_sensors_check_device_support(indio_dev, - ARRAY_SIZE(st_press_sensors), st_press_sensors); + ARRAY_SIZE(st_press_sensors), + st_press_sensors); if (err < 0) - goto st_press_common_probe_error; + return err; pdata->num_data_channels = ST_PRESS_NUMBER_DATA_CHANNELS; - pdata->multiread_bit = pdata->sensor->multi_read_bit; - indio_dev->channels = pdata->sensor->ch; - indio_dev->num_channels = pdata->sensor->num_ch; + pdata->multiread_bit = pdata->sensor->multi_read_bit; + indio_dev->channels = pdata->sensor->ch; + indio_dev->num_channels = pdata->sensor->num_ch; if (pdata->sensor->fs.addr != 0) pdata->current_fullscale = (struct st_sensor_fullscale_avl *) @@ -261,15 +263,15 @@ int st_press_common_probe(struct iio_dev *indio_dev, err = st_sensors_init_sensor(indio_dev, plat_data); if (err < 0) - goto st_press_common_probe_error; + return err; - if (pdata->get_irq_data_ready(indio_dev) > 0) { + if (irq > 0) { err = st_press_allocate_ring(indio_dev); if (err < 0) - goto st_press_common_probe_error; + return err; err = st_sensors_allocate_trigger(indio_dev, - ST_PRESS_TRIGGER_OPS); + ST_PRESS_TRIGGER_OPS); if (err < 0) goto st_press_probe_trigger_error; } @@ -281,12 +283,12 @@ int st_press_common_probe(struct iio_dev *indio_dev, return err; st_press_device_register_error: - if (pdata->get_irq_data_ready(indio_dev) > 0) + if (irq > 0) st_sensors_deallocate_trigger(indio_dev); st_press_probe_trigger_error: - if (pdata->get_irq_data_ready(indio_dev) > 0) + if (irq > 0) st_press_deallocate_ring(indio_dev); -st_press_common_probe_error: + return err; } EXPORT_SYMBOL(st_press_common_probe); -- cgit v1.2.3-70-g09d2 From 7885a8ce6800ec37147902b316cd73790865dc1d Mon Sep 17 00:00:00 2001 From: Lee Jones Date: Mon, 16 Sep 2013 17:02:00 +0100 Subject: iio: pressure: st: Add support for new LPS001WP pressure sensor Here we use existing practices to introduce support for another pressure/temperature sensor, the LPS001WP. Signed-off-by: Lee Jones Signed-off-by: Jonathan Cameron --- drivers/iio/pressure/st_pressure.h | 1 + drivers/iio/pressure/st_pressure_core.c | 84 +++++++++++++++++++++++++++++++++ drivers/iio/pressure/st_pressure_i2c.c | 1 + 3 files changed, 86 insertions(+) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/pressure/st_pressure.h b/drivers/iio/pressure/st_pressure.h index b0b630688da..049c21acf1f 100644 --- a/drivers/iio/pressure/st_pressure.h +++ b/drivers/iio/pressure/st_pressure.h @@ -14,6 +14,7 @@ #include #include +#define LPS001WP_PRESS_DEV_NAME "lps001wp" #define LPS331AP_PRESS_DEV_NAME "lps331ap" /** diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index 453995310d4..e8795420957 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -64,6 +64,21 @@ #define ST_PRESS_LPS331AP_OUT_XL_ADDR 0x28 #define ST_TEMP_LPS331AP_OUT_L_ADDR 0x2b +/* CUSTOM VALUES FOR LPS001WP SENSOR */ +#define ST_PRESS_LPS001WP_WAI_EXP 0xba +#define ST_PRESS_LPS001WP_ODR_ADDR 0x20 +#define ST_PRESS_LPS001WP_ODR_MASK 0x30 +#define ST_PRESS_LPS001WP_ODR_AVL_1HZ_VAL 0x01 +#define ST_PRESS_LPS001WP_ODR_AVL_7HZ_VAL 0x02 +#define ST_PRESS_LPS001WP_ODR_AVL_13HZ_VAL 0x03 +#define ST_PRESS_LPS001WP_PW_ADDR 0x20 +#define ST_PRESS_LPS001WP_PW_MASK 0x40 +#define ST_PRESS_LPS001WP_BDU_ADDR 0x20 +#define ST_PRESS_LPS001WP_BDU_MASK 0x04 +#define ST_PRESS_LPS001WP_MULTIREAD_BIT true +#define ST_PRESS_LPS001WP_OUT_L_ADDR 0x28 +#define ST_TEMP_LPS001WP_OUT_L_ADDR 0x2a + static const struct iio_chan_spec st_press_lps331ap_channels[] = { { .type = IIO_PRESSURE, @@ -100,6 +115,40 @@ static const struct iio_chan_spec st_press_lps331ap_channels[] = { IIO_CHAN_SOFT_TIMESTAMP(1) }; +static const struct iio_chan_spec st_press_lps001wp_channels[] = { + { + .type = IIO_PRESSURE, + .channel2 = IIO_NO_MOD, + .address = ST_PRESS_LPS001WP_OUT_L_ADDR, + .scan_index = ST_SENSORS_SCAN_X, + .scan_type = { + .sign = 'u', + .realbits = 16, + .storagebits = 16, + .endianness = IIO_LE, + }, + .info_mask_separate = BIT(IIO_CHAN_INFO_RAW), + .modified = 0, + }, + { + .type = IIO_TEMP, + .channel2 = IIO_NO_MOD, + .address = ST_TEMP_LPS001WP_OUT_L_ADDR, + .scan_index = -1, + .scan_type = { + .sign = 'u', + .realbits = 16, + .storagebits = 16, + .endianness = IIO_LE, + }, + .info_mask_separate = + BIT(IIO_CHAN_INFO_RAW) | + BIT(IIO_CHAN_INFO_OFFSET), + .modified = 0, + }, + IIO_CHAN_SOFT_TIMESTAMP(1) +}; + static const struct st_sensors st_press_sensors[] = { { .wai = ST_PRESS_LPS331AP_WAI_EXP, @@ -148,6 +197,41 @@ static const struct st_sensors st_press_sensors[] = { .multi_read_bit = ST_PRESS_LPS331AP_MULTIREAD_BIT, .bootime = 2, }, + { + .wai = ST_PRESS_LPS001WP_WAI_EXP, + .sensors_supported = { + [0] = LPS001WP_PRESS_DEV_NAME, + }, + .ch = (struct iio_chan_spec *)st_press_lps001wp_channels, + .num_ch = ARRAY_SIZE(st_press_lps001wp_channels), + .odr = { + .addr = ST_PRESS_LPS001WP_ODR_ADDR, + .mask = ST_PRESS_LPS001WP_ODR_MASK, + .odr_avl = { + { 1, ST_PRESS_LPS001WP_ODR_AVL_1HZ_VAL, }, + { 7, ST_PRESS_LPS001WP_ODR_AVL_7HZ_VAL, }, + { 13, ST_PRESS_LPS001WP_ODR_AVL_13HZ_VAL, }, + }, + }, + .pw = { + .addr = ST_PRESS_LPS001WP_PW_ADDR, + .mask = ST_PRESS_LPS001WP_PW_MASK, + .value_on = ST_SENSORS_DEFAULT_POWER_ON_VALUE, + .value_off = ST_SENSORS_DEFAULT_POWER_OFF_VALUE, + }, + .fs = { + .addr = 0, + }, + .bdu = { + .addr = ST_PRESS_LPS001WP_BDU_ADDR, + .mask = ST_PRESS_LPS001WP_BDU_MASK, + }, + .drdy_irq = { + .addr = 0, + }, + .multi_read_bit = ST_PRESS_LPS001WP_MULTIREAD_BIT, + .bootime = 2, + }, }; static int st_press_read_raw(struct iio_dev *indio_dev, diff --git a/drivers/iio/pressure/st_pressure_i2c.c b/drivers/iio/pressure/st_pressure_i2c.c index 08aac5e6251..51eab7fcb19 100644 --- a/drivers/iio/pressure/st_pressure_i2c.c +++ b/drivers/iio/pressure/st_pressure_i2c.c @@ -49,6 +49,7 @@ static int st_press_i2c_remove(struct i2c_client *client) } static const struct i2c_device_id st_press_id_table[] = { + { LPS001WP_PRESS_DEV_NAME }, { LPS331AP_PRESS_DEV_NAME }, {}, }; -- cgit v1.2.3-70-g09d2 From 7a137c9c40784e7be0a44182ed6ebc5ea22d5ac1 Mon Sep 17 00:00:00 2001 From: Denis CIOCCA Date: Wed, 18 Sep 2013 10:00:00 +0100 Subject: iio:press: Register buffer also without specific trigger This patch fix buffer registration that allows to use generic IIO trigger. Signed-off-by: Denis Ciocca Signed-off-by: Jonathan Cameron --- drivers/iio/pressure/st_pressure_core.c | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) (limited to 'drivers/iio/pressure') diff --git a/drivers/iio/pressure/st_pressure_core.c b/drivers/iio/pressure/st_pressure_core.c index e8795420957..2da411b6925 100644 --- a/drivers/iio/pressure/st_pressure_core.c +++ b/drivers/iio/pressure/st_pressure_core.c @@ -349,11 +349,11 @@ int st_press_common_probe(struct iio_dev *indio_dev, if (err < 0) return err; - if (irq > 0) { - err = st_press_allocate_ring(indio_dev); - if (err < 0) - return err; + err = st_press_allocate_ring(indio_dev); + if (err < 0) + return err; + if (irq > 0) { err = st_sensors_allocate_trigger(indio_dev, ST_PRESS_TRIGGER_OPS); if (err < 0) @@ -370,8 +370,7 @@ st_press_device_register_error: if (irq > 0) st_sensors_deallocate_trigger(indio_dev); st_press_probe_trigger_error: - if (irq > 0) - st_press_deallocate_ring(indio_dev); + st_press_deallocate_ring(indio_dev); return err; } @@ -382,10 +381,10 @@ void st_press_common_remove(struct iio_dev *indio_dev) struct st_sensor_data *pdata = iio_priv(indio_dev); iio_device_unregister(indio_dev); - if (pdata->get_irq_data_ready(indio_dev) > 0) { + if (pdata->get_irq_data_ready(indio_dev) > 0) st_sensors_deallocate_trigger(indio_dev); - st_press_deallocate_ring(indio_dev); - } + + st_press_deallocate_ring(indio_dev); } EXPORT_SYMBOL(st_press_common_remove); -- cgit v1.2.3-70-g09d2