linux/drivers/iio/humidity/hdc100x.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2/*
   3 * hdc100x.c - Support for the TI HDC100x temperature + humidity sensors
   4 *
   5 * Copyright (C) 2015, 2018
   6 * Author: Matt Ranostay <matt.ranostay@konsulko.com>
   7 *
   8 * Datasheets:
   9 * http://www.ti.com/product/HDC1000/datasheet
  10 * http://www.ti.com/product/HDC1008/datasheet
  11 * http://www.ti.com/product/HDC1010/datasheet
  12 * http://www.ti.com/product/HDC1050/datasheet
  13 * http://www.ti.com/product/HDC1080/datasheet
  14 */
  15
  16#include <linux/delay.h>
  17#include <linux/module.h>
  18#include <linux/init.h>
  19#include <linux/i2c.h>
  20
  21#include <linux/iio/iio.h>
  22#include <linux/iio/sysfs.h>
  23#include <linux/iio/buffer.h>
  24#include <linux/iio/trigger_consumer.h>
  25#include <linux/iio/triggered_buffer.h>
  26
  27#define HDC100X_REG_TEMP                        0x00
  28#define HDC100X_REG_HUMIDITY                    0x01
  29
  30#define HDC100X_REG_CONFIG                      0x02
  31#define HDC100X_REG_CONFIG_ACQ_MODE             BIT(12)
  32#define HDC100X_REG_CONFIG_HEATER_EN            BIT(13)
  33
  34struct hdc100x_data {
  35        struct i2c_client *client;
  36        struct mutex lock;
  37        u16 config;
  38
  39        /* integration time of the sensor */
  40        int adc_int_us[2];
  41};
  42
  43/* integration time in us */
  44static const int hdc100x_int_time[][3] = {
  45        { 6350, 3650, 0 },      /* IIO_TEMP channel*/
  46        { 6500, 3850, 2500 },   /* IIO_HUMIDITYRELATIVE channel */
  47};
  48
  49/* HDC100X_REG_CONFIG shift and mask values */
  50static const struct {
  51        int shift;
  52        int mask;
  53} hdc100x_resolution_shift[2] = {
  54        { /* IIO_TEMP channel */
  55                .shift = 10,
  56                .mask = 1
  57        },
  58        { /* IIO_HUMIDITYRELATIVE channel */
  59                .shift = 8,
  60                .mask = 3,
  61        },
  62};
  63
  64static IIO_CONST_ATTR(temp_integration_time_available,
  65                "0.00365 0.00635");
  66
  67static IIO_CONST_ATTR(humidityrelative_integration_time_available,
  68                "0.0025 0.00385 0.0065");
  69
  70static IIO_CONST_ATTR(out_current_heater_raw_available,
  71                "0 1");
  72
  73static struct attribute *hdc100x_attributes[] = {
  74        &iio_const_attr_temp_integration_time_available.dev_attr.attr,
  75        &iio_const_attr_humidityrelative_integration_time_available.dev_attr.attr,
  76        &iio_const_attr_out_current_heater_raw_available.dev_attr.attr,
  77        NULL
  78};
  79
  80static const struct attribute_group hdc100x_attribute_group = {
  81        .attrs = hdc100x_attributes,
  82};
  83
  84static const struct iio_chan_spec hdc100x_channels[] = {
  85        {
  86                .type = IIO_TEMP,
  87                .address = HDC100X_REG_TEMP,
  88                .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
  89                        BIT(IIO_CHAN_INFO_SCALE) |
  90                        BIT(IIO_CHAN_INFO_INT_TIME) |
  91                        BIT(IIO_CHAN_INFO_OFFSET),
  92                .scan_index = 0,
  93                .scan_type = {
  94                        .sign = 's',
  95                        .realbits = 16,
  96                        .storagebits = 16,
  97                        .endianness = IIO_BE,
  98                },
  99        },
 100        {
 101                .type = IIO_HUMIDITYRELATIVE,
 102                .address = HDC100X_REG_HUMIDITY,
 103                .info_mask_separate = BIT(IIO_CHAN_INFO_RAW) |
 104                        BIT(IIO_CHAN_INFO_SCALE) |
 105                        BIT(IIO_CHAN_INFO_INT_TIME),
 106                .scan_index = 1,
 107                .scan_type = {
 108                        .sign = 'u',
 109                        .realbits = 16,
 110                        .storagebits = 16,
 111                        .endianness = IIO_BE,
 112                },
 113        },
 114        {
 115                .type = IIO_CURRENT,
 116                .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),
 117                .extend_name = "heater",
 118                .output = 1,
 119                .scan_index = -1,
 120        },
 121        IIO_CHAN_SOFT_TIMESTAMP(2),
 122};
 123
 124static const unsigned long hdc100x_scan_masks[] = {0x3, 0};
 125
 126static int hdc100x_update_config(struct hdc100x_data *data, int mask, int val)
 127{
 128        int tmp = (~mask & data->config) | val;
 129        int ret;
 130
 131        ret = i2c_smbus_write_word_swapped(data->client,
 132                                                HDC100X_REG_CONFIG, tmp);
 133        if (!ret)
 134                data->config = tmp;
 135
 136        return ret;
 137}
 138
 139static int hdc100x_set_it_time(struct hdc100x_data *data, int chan, int val2)
 140{
 141        int shift = hdc100x_resolution_shift[chan].shift;
 142        int ret = -EINVAL;
 143        int i;
 144
 145        for (i = 0; i < ARRAY_SIZE(hdc100x_int_time[chan]); i++) {
 146                if (val2 && val2 == hdc100x_int_time[chan][i]) {
 147                        ret = hdc100x_update_config(data,
 148                                hdc100x_resolution_shift[chan].mask << shift,
 149                                i << shift);
 150                        if (!ret)
 151                                data->adc_int_us[chan] = val2;
 152                        break;
 153                }
 154        }
 155
 156        return ret;
 157}
 158
 159static int hdc100x_get_measurement(struct hdc100x_data *data,
 160                                   struct iio_chan_spec const *chan)
 161{
 162        struct i2c_client *client = data->client;
 163        int delay = data->adc_int_us[chan->address];
 164        int ret;
 165        __be16 val;
 166
 167        /* start measurement */
 168        ret = i2c_smbus_write_byte(client, chan->address);
 169        if (ret < 0) {
 170                dev_err(&client->dev, "cannot start measurement");
 171                return ret;
 172        }
 173
 174        /* wait for integration time to pass */
 175        usleep_range(delay, delay + 1000);
 176
 177        /* read measurement */
 178        ret = i2c_master_recv(data->client, (char *)&val, sizeof(val));
 179        if (ret < 0) {
 180                dev_err(&client->dev, "cannot read sensor data\n");
 181                return ret;
 182        }
 183        return be16_to_cpu(val);
 184}
 185
 186static int hdc100x_get_heater_status(struct hdc100x_data *data)
 187{
 188        return !!(data->config & HDC100X_REG_CONFIG_HEATER_EN);
 189}
 190
 191static int hdc100x_read_raw(struct iio_dev *indio_dev,
 192                            struct iio_chan_spec const *chan, int *val,
 193                            int *val2, long mask)
 194{
 195        struct hdc100x_data *data = iio_priv(indio_dev);
 196
 197        switch (mask) {
 198        case IIO_CHAN_INFO_RAW: {
 199                int ret;
 200
 201                mutex_lock(&data->lock);
 202                if (chan->type == IIO_CURRENT) {
 203                        *val = hdc100x_get_heater_status(data);
 204                        ret = IIO_VAL_INT;
 205                } else {
 206                        ret = iio_device_claim_direct_mode(indio_dev);
 207                        if (ret) {
 208                                mutex_unlock(&data->lock);
 209                                return ret;
 210                        }
 211
 212                        ret = hdc100x_get_measurement(data, chan);
 213                        iio_device_release_direct_mode(indio_dev);
 214                        if (ret >= 0) {
 215                                *val = ret;
 216                                ret = IIO_VAL_INT;
 217                        }
 218                }
 219                mutex_unlock(&data->lock);
 220                return ret;
 221        }
 222        case IIO_CHAN_INFO_INT_TIME:
 223                *val = 0;
 224                *val2 = data->adc_int_us[chan->address];
 225                return IIO_VAL_INT_PLUS_MICRO;
 226        case IIO_CHAN_INFO_SCALE:
 227                if (chan->type == IIO_TEMP) {
 228                        *val = 165000;
 229                        *val2 = 65536;
 230                        return IIO_VAL_FRACTIONAL;
 231                } else {
 232                        *val = 100000;
 233                        *val2 = 65536;
 234                        return IIO_VAL_FRACTIONAL;
 235                }
 236                break;
 237        case IIO_CHAN_INFO_OFFSET:
 238                *val = -15887;
 239                *val2 = 515151;
 240                return IIO_VAL_INT_PLUS_MICRO;
 241        default:
 242                return -EINVAL;
 243        }
 244}
 245
 246static int hdc100x_write_raw(struct iio_dev *indio_dev,
 247                             struct iio_chan_spec const *chan,
 248                             int val, int val2, long mask)
 249{
 250        struct hdc100x_data *data = iio_priv(indio_dev);
 251        int ret = -EINVAL;
 252
 253        switch (mask) {
 254        case IIO_CHAN_INFO_INT_TIME:
 255                if (val != 0)
 256                        return -EINVAL;
 257
 258                mutex_lock(&data->lock);
 259                ret = hdc100x_set_it_time(data, chan->address, val2);
 260                mutex_unlock(&data->lock);
 261                return ret;
 262        case IIO_CHAN_INFO_RAW:
 263                if (chan->type != IIO_CURRENT || val2 != 0)
 264                        return -EINVAL;
 265
 266                mutex_lock(&data->lock);
 267                ret = hdc100x_update_config(data, HDC100X_REG_CONFIG_HEATER_EN,
 268                                        val ? HDC100X_REG_CONFIG_HEATER_EN : 0);
 269                mutex_unlock(&data->lock);
 270                return ret;
 271        default:
 272                return -EINVAL;
 273        }
 274}
 275
 276static int hdc100x_buffer_postenable(struct iio_dev *indio_dev)
 277{
 278        struct hdc100x_data *data = iio_priv(indio_dev);
 279        int ret;
 280
 281        ret = iio_triggered_buffer_postenable(indio_dev);
 282        if (ret)
 283                return ret;
 284
 285        /* Buffer is enabled. First set ACQ Mode, then attach poll func */
 286        mutex_lock(&data->lock);
 287        ret = hdc100x_update_config(data, HDC100X_REG_CONFIG_ACQ_MODE,
 288                                    HDC100X_REG_CONFIG_ACQ_MODE);
 289        mutex_unlock(&data->lock);
 290        if (ret)
 291                iio_triggered_buffer_predisable(indio_dev);
 292
 293        return ret;
 294}
 295
 296static int hdc100x_buffer_predisable(struct iio_dev *indio_dev)
 297{
 298        struct hdc100x_data *data = iio_priv(indio_dev);
 299        int ret, ret2;
 300
 301        mutex_lock(&data->lock);
 302        ret = hdc100x_update_config(data, HDC100X_REG_CONFIG_ACQ_MODE, 0);
 303        mutex_unlock(&data->lock);
 304
 305        ret2 = iio_triggered_buffer_predisable(indio_dev);
 306        if (ret == 0)
 307                ret = ret2;
 308
 309        return ret;
 310}
 311
 312static const struct iio_buffer_setup_ops hdc_buffer_setup_ops = {
 313        .postenable  = hdc100x_buffer_postenable,
 314        .predisable  = hdc100x_buffer_predisable,
 315};
 316
 317static irqreturn_t hdc100x_trigger_handler(int irq, void *p)
 318{
 319        struct iio_poll_func *pf = p;
 320        struct iio_dev *indio_dev = pf->indio_dev;
 321        struct hdc100x_data *data = iio_priv(indio_dev);
 322        struct i2c_client *client = data->client;
 323        int delay = data->adc_int_us[0] + data->adc_int_us[1];
 324        int ret;
 325        s16 buf[8];  /* 2x s16 + padding + 8 byte timestamp */
 326
 327        /* dual read starts at temp register */
 328        mutex_lock(&data->lock);
 329        ret = i2c_smbus_write_byte(client, HDC100X_REG_TEMP);
 330        if (ret < 0) {
 331                dev_err(&client->dev, "cannot start measurement\n");
 332                goto err;
 333        }
 334        usleep_range(delay, delay + 1000);
 335
 336        ret = i2c_master_recv(client, (u8 *)buf, 4);
 337        if (ret < 0) {
 338                dev_err(&client->dev, "cannot read sensor data\n");
 339                goto err;
 340        }
 341
 342        iio_push_to_buffers_with_timestamp(indio_dev, buf,
 343                                           iio_get_time_ns(indio_dev));
 344err:
 345        mutex_unlock(&data->lock);
 346        iio_trigger_notify_done(indio_dev->trig);
 347
 348        return IRQ_HANDLED;
 349}
 350
 351static const struct iio_info hdc100x_info = {
 352        .read_raw = hdc100x_read_raw,
 353        .write_raw = hdc100x_write_raw,
 354        .attrs = &hdc100x_attribute_group,
 355};
 356
 357static int hdc100x_probe(struct i2c_client *client,
 358                         const struct i2c_device_id *id)
 359{
 360        struct iio_dev *indio_dev;
 361        struct hdc100x_data *data;
 362        int ret;
 363
 364        if (!i2c_check_functionality(client->adapter, I2C_FUNC_SMBUS_WORD_DATA |
 365                                     I2C_FUNC_SMBUS_BYTE | I2C_FUNC_I2C))
 366                return -EOPNOTSUPP;
 367
 368        indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*data));
 369        if (!indio_dev)
 370                return -ENOMEM;
 371
 372        data = iio_priv(indio_dev);
 373        i2c_set_clientdata(client, indio_dev);
 374        data->client = client;
 375        mutex_init(&data->lock);
 376
 377        indio_dev->dev.parent = &client->dev;
 378        indio_dev->name = dev_name(&client->dev);
 379        indio_dev->modes = INDIO_DIRECT_MODE;
 380        indio_dev->info = &hdc100x_info;
 381
 382        indio_dev->channels = hdc100x_channels;
 383        indio_dev->num_channels = ARRAY_SIZE(hdc100x_channels);
 384        indio_dev->available_scan_masks = hdc100x_scan_masks;
 385
 386        /* be sure we are in a known state */
 387        hdc100x_set_it_time(data, 0, hdc100x_int_time[0][0]);
 388        hdc100x_set_it_time(data, 1, hdc100x_int_time[1][0]);
 389        hdc100x_update_config(data, HDC100X_REG_CONFIG_ACQ_MODE, 0);
 390
 391        ret = devm_iio_triggered_buffer_setup(&client->dev,
 392                                         indio_dev, NULL,
 393                                         hdc100x_trigger_handler,
 394                                         &hdc_buffer_setup_ops);
 395        if (ret < 0) {
 396                dev_err(&client->dev, "iio triggered buffer setup failed\n");
 397                return ret;
 398        }
 399
 400        return devm_iio_device_register(&client->dev, indio_dev);
 401}
 402
 403static const struct i2c_device_id hdc100x_id[] = {
 404        { "hdc100x", 0 },
 405        { "hdc1000", 0 },
 406        { "hdc1008", 0 },
 407        { "hdc1010", 0 },
 408        { "hdc1050", 0 },
 409        { "hdc1080", 0 },
 410        { }
 411};
 412MODULE_DEVICE_TABLE(i2c, hdc100x_id);
 413
 414static const struct of_device_id hdc100x_dt_ids[] = {
 415        { .compatible = "ti,hdc1000" },
 416        { .compatible = "ti,hdc1008" },
 417        { .compatible = "ti,hdc1010" },
 418        { .compatible = "ti,hdc1050" },
 419        { .compatible = "ti,hdc1080" },
 420        { }
 421};
 422MODULE_DEVICE_TABLE(of, hdc100x_dt_ids);
 423
 424static struct i2c_driver hdc100x_driver = {
 425        .driver = {
 426                .name   = "hdc100x",
 427                .of_match_table = of_match_ptr(hdc100x_dt_ids),
 428        },
 429        .probe = hdc100x_probe,
 430        .id_table = hdc100x_id,
 431};
 432module_i2c_driver(hdc100x_driver);
 433
 434MODULE_AUTHOR("Matt Ranostay <matt.ranostay@konsulko.com>");
 435MODULE_DESCRIPTION("TI HDC100x humidity and temperature sensor driver");
 436MODULE_LICENSE("GPL");
 437