linux/drivers/iio/adc/mcp320x.c
<<
>>
Prefs
   1/*
   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 * ------------
  20 *
  21 * Datasheet can be found here:
  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
  28 *
  29 * This program is free software; you can redistribute it and/or modify
  30 * it under the terms of the GNU General Public License version 2 as
  31 * published by the Free Software Foundation.
  32 */
  33
  34#include <linux/err.h>
  35#include <linux/delay.h>
  36#include <linux/spi/spi.h>
  37#include <linux/module.h>
  38#include <linux/iio/iio.h>
  39#include <linux/regulator/consumer.h>
  40
  41enum {
  42        mcp3001,
  43        mcp3002,
  44        mcp3004,
  45        mcp3008,
  46        mcp3201,
  47        mcp3202,
  48        mcp3204,
  49        mcp3208,
  50};
  51
  52struct mcp320x_chip_info {
  53        const struct iio_chan_spec *channels;
  54        unsigned int num_channels;
  55        unsigned int resolution;
  56};
  57
  58struct mcp320x {
  59        struct spi_device *spi;
  60        struct spi_message msg;
  61        struct spi_transfer transfer[2];
  62
  63        struct regulator *reg;
  64        struct mutex lock;
  65        const struct mcp320x_chip_info *chip_info;
  66
  67        u8 tx_buf ____cacheline_aligned;
  68        u8 rx_buf[2];
  69};
  70
  71static 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
  95static int mcp320x_adc_conversion(struct mcp320x *adc, u8 channel,
  96                                  bool differential, int device_index)
  97{
  98        int ret;
  99
 100        adc->rx_buf[0] = 0;
 101        adc->rx_buf[1] = 0;
 102        adc->tx_buf = mcp320x_channel_to_tx_data(device_index,
 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        }
 114
 115        switch (device_index) {
 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        }
 131}
 132
 133static int mcp320x_read_raw(struct iio_dev *indio_dev,
 134                            struct iio_chan_spec const *channel, int *val,
 135                            int *val2, long mask)
 136{
 137        struct mcp320x *adc = iio_priv(indio_dev);
 138        int ret = -EINVAL;
 139        int device_index = 0;
 140
 141        mutex_lock(&adc->lock);
 142
 143        device_index = spi_get_device_id(adc->spi)->driver_data;
 144
 145        switch (mask) {
 146        case IIO_CHAN_INFO_RAW:
 147                ret = mcp320x_adc_conversion(adc, channel->address,
 148                        channel->differential, device_index);
 149
 150                if (ret < 0)
 151                        goto out;
 152
 153                *val = ret;
 154                ret = IIO_VAL_INT;
 155                break;
 156
 157        case IIO_CHAN_INFO_SCALE:
 158                ret = regulator_get_voltage(adc->reg);
 159                if (ret < 0)
 160                        goto out;
 161
 162                /* convert regulator output voltage to mV */
 163                *val = ret / 1000;
 164                *val2 = adc->chip_info->resolution;
 165                ret = IIO_VAL_FRACTIONAL_LOG2;
 166                break;
 167        }
 168
 169out:
 170        mutex_unlock(&adc->lock);
 171
 172        return ret;
 173}
 174
 175#define MCP320X_VOLTAGE_CHANNEL(num)                            \
 176        {                                                       \
 177                .type = IIO_VOLTAGE,                            \
 178                .indexed = 1,                                   \
 179                .channel = (num),                               \
 180                .address = (num),                               \
 181                .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),   \
 182                .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) \
 183        }
 184
 185#define MCP320X_VOLTAGE_CHANNEL_DIFF(num)                       \
 186        {                                                       \
 187                .type = IIO_VOLTAGE,                            \
 188                .indexed = 1,                                   \
 189                .channel = (num * 2),                           \
 190                .channel2 = (num * 2 + 1),                      \
 191                .address = (num * 2),                           \
 192                .differential = 1,                              \
 193                .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),   \
 194                .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) \
 195        }
 196
 197static const struct iio_chan_spec mcp3201_channels[] = {
 198        MCP320X_VOLTAGE_CHANNEL_DIFF(0),
 199};
 200
 201static 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
 207static const struct iio_chan_spec mcp3204_channels[] = {
 208        MCP320X_VOLTAGE_CHANNEL(0),
 209        MCP320X_VOLTAGE_CHANNEL(1),
 210        MCP320X_VOLTAGE_CHANNEL(2),
 211        MCP320X_VOLTAGE_CHANNEL(3),
 212        MCP320X_VOLTAGE_CHANNEL_DIFF(0),
 213        MCP320X_VOLTAGE_CHANNEL_DIFF(1),
 214};
 215
 216static const struct iio_chan_spec mcp3208_channels[] = {
 217        MCP320X_VOLTAGE_CHANNEL(0),
 218        MCP320X_VOLTAGE_CHANNEL(1),
 219        MCP320X_VOLTAGE_CHANNEL(2),
 220        MCP320X_VOLTAGE_CHANNEL(3),
 221        MCP320X_VOLTAGE_CHANNEL(4),
 222        MCP320X_VOLTAGE_CHANNEL(5),
 223        MCP320X_VOLTAGE_CHANNEL(6),
 224        MCP320X_VOLTAGE_CHANNEL(7),
 225        MCP320X_VOLTAGE_CHANNEL_DIFF(0),
 226        MCP320X_VOLTAGE_CHANNEL_DIFF(1),
 227        MCP320X_VOLTAGE_CHANNEL_DIFF(2),
 228        MCP320X_VOLTAGE_CHANNEL_DIFF(3),
 229};
 230
 231static const struct iio_info mcp320x_info = {
 232        .read_raw = mcp320x_read_raw,
 233        .driver_module = THIS_MODULE,
 234};
 235
 236static const struct mcp320x_chip_info mcp320x_chip_infos[] = {
 237        [mcp3001] = {
 238                .channels = mcp3201_channels,
 239                .num_channels = ARRAY_SIZE(mcp3201_channels),
 240                .resolution = 10
 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        },
 267        [mcp3204] = {
 268                .channels = mcp3204_channels,
 269                .num_channels = ARRAY_SIZE(mcp3204_channels),
 270                .resolution = 12
 271        },
 272        [mcp3208] = {
 273                .channels = mcp3208_channels,
 274                .num_channels = ARRAY_SIZE(mcp3208_channels),
 275                .resolution = 12
 276        },
 277};
 278
 279static int mcp320x_probe(struct spi_device *spi)
 280{
 281        struct iio_dev *indio_dev;
 282        struct mcp320x *adc;
 283        const struct mcp320x_chip_info *chip_info;
 284        int ret;
 285
 286        indio_dev = devm_iio_device_alloc(&spi->dev, sizeof(*adc));
 287        if (!indio_dev)
 288                return -ENOMEM;
 289
 290        adc = iio_priv(indio_dev);
 291        adc->spi = spi;
 292
 293        indio_dev->dev.parent = &spi->dev;
 294        indio_dev->name = spi_get_device_id(spi)->name;
 295        indio_dev->modes = INDIO_DIRECT_MODE;
 296        indio_dev->info = &mcp320x_info;
 297
 298        chip_info = &mcp320x_chip_infos[spi_get_device_id(spi)->driver_data];
 299        indio_dev->channels = chip_info->channels;
 300        indio_dev->num_channels = chip_info->num_channels;
 301
 302        adc->chip_info = chip_info;
 303
 304        adc->transfer[0].tx_buf = &adc->tx_buf;
 305        adc->transfer[0].len = sizeof(adc->tx_buf);
 306        adc->transfer[1].rx_buf = adc->rx_buf;
 307        adc->transfer[1].len = sizeof(adc->rx_buf);
 308
 309        spi_message_init_with_transfers(&adc->msg, adc->transfer,
 310                                        ARRAY_SIZE(adc->transfer));
 311
 312        adc->reg = devm_regulator_get(&spi->dev, "vref");
 313        if (IS_ERR(adc->reg))
 314                return PTR_ERR(adc->reg);
 315
 316        ret = regulator_enable(adc->reg);
 317        if (ret < 0)
 318                return ret;
 319
 320        mutex_init(&adc->lock);
 321
 322        ret = iio_device_register(indio_dev);
 323        if (ret < 0)
 324                goto reg_disable;
 325
 326        return 0;
 327
 328reg_disable:
 329        regulator_disable(adc->reg);
 330
 331        return ret;
 332}
 333
 334static int mcp320x_remove(struct spi_device *spi)
 335{
 336        struct iio_dev *indio_dev = spi_get_drvdata(spi);
 337        struct mcp320x *adc = iio_priv(indio_dev);
 338
 339        iio_device_unregister(indio_dev);
 340        regulator_disable(adc->reg);
 341
 342        return 0;
 343}
 344
 345#if defined(CONFIG_OF)
 346static const struct of_device_id mcp320x_dt_ids[] = {
 347        {
 348                .compatible = "mcp3001",
 349                .data = &mcp320x_chip_infos[mcp3001],
 350        }, {
 351                .compatible = "mcp3002",
 352                .data = &mcp320x_chip_infos[mcp3002],
 353        }, {
 354                .compatible = "mcp3004",
 355                .data = &mcp320x_chip_infos[mcp3004],
 356        }, {
 357                .compatible = "mcp3008",
 358                .data = &mcp320x_chip_infos[mcp3008],
 359        }, {
 360                .compatible = "mcp3201",
 361                .data = &mcp320x_chip_infos[mcp3201],
 362        }, {
 363                .compatible = "mcp3202",
 364                .data = &mcp320x_chip_infos[mcp3202],
 365        }, {
 366                .compatible = "mcp3204",
 367                .data = &mcp320x_chip_infos[mcp3204],
 368        }, {
 369                .compatible = "mcp3208",
 370                .data = &mcp320x_chip_infos[mcp3208],
 371        }, {
 372        }
 373};
 374MODULE_DEVICE_TABLE(of, mcp320x_dt_ids);
 375#endif
 376
 377static const struct spi_device_id mcp320x_id[] = {
 378        { "mcp3001", mcp3001 },
 379        { "mcp3002", mcp3002 },
 380        { "mcp3004", mcp3004 },
 381        { "mcp3008", mcp3008 },
 382        { "mcp3201", mcp3201 },
 383        { "mcp3202", mcp3202 },
 384        { "mcp3204", mcp3204 },
 385        { "mcp3208", mcp3208 },
 386        { }
 387};
 388MODULE_DEVICE_TABLE(spi, mcp320x_id);
 389
 390static struct spi_driver mcp320x_driver = {
 391        .driver = {
 392                .name = "mcp320x",
 393                .owner = THIS_MODULE,
 394        },
 395        .probe = mcp320x_probe,
 396        .remove = mcp320x_remove,
 397        .id_table = mcp320x_id,
 398};
 399module_spi_driver(mcp320x_driver);
 400
 401MODULE_AUTHOR("Oskar Andero <oskar.andero@gmail.com>");
 402MODULE_DESCRIPTION("Microchip Technology MCP3x01/02/04/08");
 403MODULE_LICENSE("GPL v2");
 404