root/drivers/iio/dac/m62332.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. m62332_set_value
  2. m62332_read_raw
  3. m62332_write_raw
  4. m62332_suspend
  5. m62332_resume
  6. m62332_probe
  7. m62332_remove

   1 // SPDX-License-Identifier: GPL-2.0-or-later
   2 /*
   3  *  m62332.c - Support for Mitsubishi m62332 DAC
   4  *
   5  *  Copyright (c) 2014 Dmitry Eremin-Solenikov
   6  *
   7  *  Based on max517 driver:
   8  *  Copyright (C) 2010, 2011 Roland Stigge <stigge@antcom.de>
   9  */
  10 
  11 #include <linux/module.h>
  12 #include <linux/slab.h>
  13 #include <linux/i2c.h>
  14 #include <linux/err.h>
  15 
  16 #include <linux/iio/iio.h>
  17 #include <linux/iio/driver.h>
  18 
  19 #include <linux/regulator/consumer.h>
  20 
  21 #define M62332_CHANNELS 2
  22 
  23 struct m62332_data {
  24         struct i2c_client       *client;
  25         struct regulator        *vcc;
  26         struct mutex            mutex;
  27         u8                      raw[M62332_CHANNELS];
  28 #ifdef CONFIG_PM_SLEEP
  29         u8                      save[M62332_CHANNELS];
  30 #endif
  31 };
  32 
  33 static int m62332_set_value(struct iio_dev *indio_dev, u8 val, int channel)
  34 {
  35         struct m62332_data *data = iio_priv(indio_dev);
  36         struct i2c_client *client = data->client;
  37         u8 outbuf[2];
  38         int res;
  39 
  40         if (val == data->raw[channel])
  41                 return 0;
  42 
  43         outbuf[0] = channel;
  44         outbuf[1] = val;
  45 
  46         mutex_lock(&data->mutex);
  47 
  48         if (val) {
  49                 res = regulator_enable(data->vcc);
  50                 if (res)
  51                         goto out;
  52         }
  53 
  54         res = i2c_master_send(client, outbuf, ARRAY_SIZE(outbuf));
  55         if (res >= 0 && res != ARRAY_SIZE(outbuf))
  56                 res = -EIO;
  57         if (res < 0)
  58                 goto out;
  59 
  60         data->raw[channel] = val;
  61 
  62         if (!val)
  63                 regulator_disable(data->vcc);
  64 
  65         mutex_unlock(&data->mutex);
  66 
  67         return 0;
  68 
  69 out:
  70         mutex_unlock(&data->mutex);
  71 
  72         return res;
  73 }
  74 
  75 static int m62332_read_raw(struct iio_dev *indio_dev,
  76                            struct iio_chan_spec const *chan,
  77                            int *val,
  78                            int *val2,
  79                            long mask)
  80 {
  81         struct m62332_data *data = iio_priv(indio_dev);
  82         int ret;
  83 
  84         switch (mask) {
  85         case IIO_CHAN_INFO_SCALE:
  86                 /* Corresponds to Vref / 2^(bits) */
  87                 ret = regulator_get_voltage(data->vcc);
  88                 if (ret < 0)
  89                         return ret;
  90 
  91                 *val = ret / 1000; /* mV */
  92                 *val2 = 8;
  93 
  94                 return IIO_VAL_FRACTIONAL_LOG2;
  95         case IIO_CHAN_INFO_RAW:
  96                 *val = data->raw[chan->channel];
  97 
  98                 return IIO_VAL_INT;
  99         case IIO_CHAN_INFO_OFFSET:
 100                 *val = 1;
 101 
 102                 return IIO_VAL_INT;
 103         default:
 104                 break;
 105         }
 106 
 107         return -EINVAL;
 108 }
 109 
 110 static int m62332_write_raw(struct iio_dev *indio_dev,
 111                             struct iio_chan_spec const *chan, int val, int val2,
 112                             long mask)
 113 {
 114         switch (mask) {
 115         case IIO_CHAN_INFO_RAW:
 116                 if (val < 0 || val > 255)
 117                         return -EINVAL;
 118 
 119                 return m62332_set_value(indio_dev, val, chan->channel);
 120         default:
 121                 break;
 122         }
 123 
 124         return -EINVAL;
 125 }
 126 
 127 #ifdef CONFIG_PM_SLEEP
 128 static int m62332_suspend(struct device *dev)
 129 {
 130         struct i2c_client *client = to_i2c_client(dev);
 131         struct iio_dev *indio_dev = i2c_get_clientdata(client);
 132         struct m62332_data *data = iio_priv(indio_dev);
 133         int ret;
 134 
 135         data->save[0] = data->raw[0];
 136         data->save[1] = data->raw[1];
 137 
 138         ret = m62332_set_value(indio_dev, 0, 0);
 139         if (ret < 0)
 140                 return ret;
 141 
 142         return m62332_set_value(indio_dev, 0, 1);
 143 }
 144 
 145 static int m62332_resume(struct device *dev)
 146 {
 147         struct i2c_client *client = to_i2c_client(dev);
 148         struct iio_dev *indio_dev = i2c_get_clientdata(client);
 149         struct m62332_data *data = iio_priv(indio_dev);
 150         int ret;
 151 
 152         ret = m62332_set_value(indio_dev, data->save[0], 0);
 153         if (ret < 0)
 154                 return ret;
 155 
 156         return m62332_set_value(indio_dev, data->save[1], 1);
 157 }
 158 
 159 static SIMPLE_DEV_PM_OPS(m62332_pm_ops, m62332_suspend, m62332_resume);
 160 #define M62332_PM_OPS (&m62332_pm_ops)
 161 #else
 162 #define M62332_PM_OPS NULL
 163 #endif
 164 
 165 static const struct iio_info m62332_info = {
 166         .read_raw = m62332_read_raw,
 167         .write_raw = m62332_write_raw,
 168 };
 169 
 170 #define M62332_CHANNEL(chan) {                                  \
 171         .type = IIO_VOLTAGE,                                    \
 172         .indexed = 1,                                           \
 173         .output = 1,                                            \
 174         .channel = (chan),                                      \
 175         .datasheet_name = "CH" #chan,                           \
 176         .info_mask_separate = BIT(IIO_CHAN_INFO_RAW),           \
 177         .info_mask_shared_by_type = BIT(IIO_CHAN_INFO_SCALE) |  \
 178                                     BIT(IIO_CHAN_INFO_OFFSET),  \
 179 }
 180 
 181 static const struct iio_chan_spec m62332_channels[M62332_CHANNELS] = {
 182         M62332_CHANNEL(0),
 183         M62332_CHANNEL(1)
 184 };
 185 
 186 static int m62332_probe(struct i2c_client *client,
 187                         const struct i2c_device_id *id)
 188 {
 189         struct m62332_data *data;
 190         struct iio_dev *indio_dev;
 191         int ret;
 192 
 193         indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*data));
 194         if (!indio_dev)
 195                 return -ENOMEM;
 196 
 197         data = iio_priv(indio_dev);
 198         i2c_set_clientdata(client, indio_dev);
 199         data->client = client;
 200 
 201         mutex_init(&data->mutex);
 202 
 203         data->vcc = devm_regulator_get(&client->dev, "VCC");
 204         if (IS_ERR(data->vcc))
 205                 return PTR_ERR(data->vcc);
 206 
 207         /* establish that the iio_dev is a child of the i2c device */
 208         indio_dev->dev.parent = &client->dev;
 209 
 210         indio_dev->num_channels = ARRAY_SIZE(m62332_channels);
 211         indio_dev->channels = m62332_channels;
 212         indio_dev->modes = INDIO_DIRECT_MODE;
 213         indio_dev->info = &m62332_info;
 214 
 215         ret = iio_map_array_register(indio_dev, client->dev.platform_data);
 216         if (ret < 0)
 217                 return ret;
 218 
 219         ret = iio_device_register(indio_dev);
 220         if (ret < 0)
 221                 goto err;
 222 
 223         return 0;
 224 
 225 err:
 226         iio_map_array_unregister(indio_dev);
 227 
 228         return ret;
 229 }
 230 
 231 static int m62332_remove(struct i2c_client *client)
 232 {
 233         struct iio_dev *indio_dev = i2c_get_clientdata(client);
 234 
 235         iio_device_unregister(indio_dev);
 236         iio_map_array_unregister(indio_dev);
 237         m62332_set_value(indio_dev, 0, 0);
 238         m62332_set_value(indio_dev, 0, 1);
 239 
 240         return 0;
 241 }
 242 
 243 static const struct i2c_device_id m62332_id[] = {
 244         { "m62332", },
 245         { }
 246 };
 247 MODULE_DEVICE_TABLE(i2c, m62332_id);
 248 
 249 static struct i2c_driver m62332_driver = {
 250         .driver = {
 251                 .name   = "m62332",
 252                 .pm     = M62332_PM_OPS,
 253         },
 254         .probe          = m62332_probe,
 255         .remove         = m62332_remove,
 256         .id_table       = m62332_id,
 257 };
 258 module_i2c_driver(m62332_driver);
 259 
 260 MODULE_AUTHOR("Dmitry Eremin-Solenikov");
 261 MODULE_DESCRIPTION("M62332 8-bit DAC");
 262 MODULE_LICENSE("GPL v2");

/* [<][>][^][v][top][bottom][index][help] */