summaryrefslogtreecommitdiff
path: root/drivers/iio/chemical/ccs811.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/iio/chemical/ccs811.c')
-rw-r--r--drivers/iio/chemical/ccs811.c83
1 files changed, 42 insertions, 41 deletions
diff --git a/drivers/iio/chemical/ccs811.c b/drivers/iio/chemical/ccs811.c
index 451fb65dbe60..998c9239c4c7 100644
--- a/drivers/iio/chemical/ccs811.c
+++ b/drivers/iio/chemical/ccs811.c
@@ -15,6 +15,7 @@
* 4. Read error register and put the information in logs
*/
+#include <linux/cleanup.h>
#include <linux/delay.h>
#include <linux/gpio/consumer.h>
#include <linux/i2c.h>
@@ -214,6 +215,40 @@ static int ccs811_get_measurement(struct ccs811_data *data)
return ret;
}
+static int ccs811_read_info_raw(struct ccs811_data *data,
+ struct iio_chan_spec const *chan,
+ int *val, int mask)
+{
+ int ret;
+
+ guard(mutex)(&data->lock);
+ ret = ccs811_get_measurement(data);
+ if (ret < 0)
+ return ret;
+
+ switch (chan->type) {
+ case IIO_VOLTAGE:
+ *val = be16_to_cpu(data->buffer.raw_data) & CCS811_VOLTAGE_MASK;
+ return IIO_VAL_INT;
+ case IIO_CURRENT:
+ *val = be16_to_cpu(data->buffer.raw_data) >> 10;
+ return IIO_VAL_INT;
+ case IIO_CONCENTRATION:
+ switch (chan->channel2) {
+ case IIO_MOD_CO2:
+ *val = be16_to_cpu(data->buffer.co2);
+ return IIO_VAL_INT;
+ case IIO_MOD_VOC:
+ *val = be16_to_cpu(data->buffer.voc);
+ return IIO_VAL_INT;
+ default:
+ return -EINVAL;
+ }
+ default:
+ return -EINVAL;
+ }
+}
+
static int ccs811_read_raw(struct iio_dev *indio_dev,
struct iio_chan_spec const *chan,
int *val, int *val2, long mask)
@@ -223,46 +258,12 @@ static int ccs811_read_raw(struct iio_dev *indio_dev,
switch (mask) {
case IIO_CHAN_INFO_RAW:
- ret = iio_device_claim_direct_mode(indio_dev);
- if (ret)
- return ret;
- mutex_lock(&data->lock);
- ret = ccs811_get_measurement(data);
- if (ret < 0) {
- mutex_unlock(&data->lock);
- iio_device_release_direct_mode(indio_dev);
- return ret;
- }
+ if (!iio_device_claim_direct(indio_dev))
+ return -EBUSY;
- switch (chan->type) {
- case IIO_VOLTAGE:
- *val = be16_to_cpu(data->buffer.raw_data) &
- CCS811_VOLTAGE_MASK;
- ret = IIO_VAL_INT;
- break;
- case IIO_CURRENT:
- *val = be16_to_cpu(data->buffer.raw_data) >> 10;
- ret = IIO_VAL_INT;
- break;
- case IIO_CONCENTRATION:
- switch (chan->channel2) {
- case IIO_MOD_CO2:
- *val = be16_to_cpu(data->buffer.co2);
- ret = IIO_VAL_INT;
- break;
- case IIO_MOD_VOC:
- *val = be16_to_cpu(data->buffer.voc);
- ret = IIO_VAL_INT;
- break;
- default:
- ret = -EINVAL;
- }
- break;
- default:
- ret = -EINVAL;
- }
- mutex_unlock(&data->lock);
- iio_device_release_direct_mode(indio_dev);
+ ret = ccs811_read_info_raw(data, chan, val, mask);
+
+ iio_device_release_direct(indio_dev);
return ret;
@@ -342,8 +343,8 @@ static irqreturn_t ccs811_trigger_handler(int irq, void *p)
goto err;
}
- iio_push_to_buffers_with_timestamp(indio_dev, &data->scan,
- iio_get_time_ns(indio_dev));
+ iio_push_to_buffers_with_ts(indio_dev, &data->scan, sizeof(data->scan),
+ iio_get_time_ns(indio_dev));
err:
iio_trigger_notify_done(indio_dev->trig);