root/drivers/staging/iio/meter/ade7854-i2c.c

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

DEFINITIONS

This source file includes following definitions.
  1. ade7854_i2c_write_reg
  2. ade7854_i2c_read_reg
  3. ade7854_i2c_probe

   1 // SPDX-License-Identifier: GPL-2.0+
   2 /*
   3  * ADE7854/58/68/78 Polyphase Multifunction Energy Metering IC Driver (I2C Bus)
   4  *
   5  * Copyright 2010 Analog Devices Inc.
   6  */
   7 
   8 #include <linux/device.h>
   9 #include <linux/kernel.h>
  10 #include <linux/i2c.h>
  11 #include <linux/slab.h>
  12 #include <linux/module.h>
  13 
  14 #include <linux/iio/iio.h>
  15 #include "ade7854.h"
  16 
  17 static int ade7854_i2c_write_reg(struct device *dev,
  18                                  u16 reg_address,
  19                                  u32 val,
  20                                  int bits)
  21 {
  22         int ret;
  23         int count;
  24         struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  25         struct ade7854_state *st = iio_priv(indio_dev);
  26 
  27         mutex_lock(&st->buf_lock);
  28         st->tx[0] = (reg_address >> 8) & 0xFF;
  29         st->tx[1] = reg_address & 0xFF;
  30 
  31         switch (bits) {
  32         case 8:
  33                 st->tx[2] = val & 0xFF;
  34                 count = 3;
  35                 break;
  36         case 16:
  37                 st->tx[2] = (val >> 8) & 0xFF;
  38                 st->tx[3] = val & 0xFF;
  39                 count = 4;
  40                 break;
  41         case 24:
  42                 st->tx[2] = (val >> 16) & 0xFF;
  43                 st->tx[3] = (val >> 8) & 0xFF;
  44                 st->tx[4] = val & 0xFF;
  45                 count = 5;
  46                 break;
  47         case 32:
  48                 st->tx[2] = (val >> 24) & 0xFF;
  49                 st->tx[3] = (val >> 16) & 0xFF;
  50                 st->tx[4] = (val >> 8) & 0xFF;
  51                 st->tx[5] = val & 0xFF;
  52                 count = 6;
  53                 break;
  54         default:
  55                 ret = -EINVAL;
  56                 goto unlock;
  57         }
  58 
  59         ret = i2c_master_send(st->i2c, st->tx, count);
  60 
  61 unlock:
  62         mutex_unlock(&st->buf_lock);
  63 
  64         return ret < 0 ? ret : 0;
  65 }
  66 
  67 static int ade7854_i2c_read_reg(struct device *dev,
  68                                 u16 reg_address,
  69                                 u32 *val,
  70                                 int bits)
  71 {
  72         struct iio_dev *indio_dev = dev_to_iio_dev(dev);
  73         struct ade7854_state *st = iio_priv(indio_dev);
  74         int ret;
  75 
  76         mutex_lock(&st->buf_lock);
  77         st->tx[0] = (reg_address >> 8) & 0xFF;
  78         st->tx[1] = reg_address & 0xFF;
  79 
  80         ret = i2c_master_send(st->i2c, st->tx, 2);
  81         if (ret < 0)
  82                 goto unlock;
  83 
  84         ret = i2c_master_recv(st->i2c, st->rx, bits);
  85         if (ret < 0)
  86                 goto unlock;
  87 
  88         switch (bits) {
  89         case 8:
  90                 *val = st->rx[0];
  91                 break;
  92         case 16:
  93                 *val = (st->rx[0] << 8) | st->rx[1];
  94                 break;
  95         case 24:
  96                 *val = (st->rx[0] << 16) | (st->rx[1] << 8) | st->rx[2];
  97                 break;
  98         case 32:
  99                 *val = (st->rx[0] << 24) | (st->rx[1] << 16) |
 100                         (st->rx[2] << 8) | st->rx[3];
 101                 break;
 102         default:
 103                 ret = -EINVAL;
 104                 goto unlock;
 105         }
 106 
 107 unlock:
 108         mutex_unlock(&st->buf_lock);
 109         return ret;
 110 }
 111 
 112 static int ade7854_i2c_probe(struct i2c_client *client,
 113                              const struct i2c_device_id *id)
 114 {
 115         struct ade7854_state *st;
 116         struct iio_dev *indio_dev;
 117 
 118         indio_dev = devm_iio_device_alloc(&client->dev, sizeof(*st));
 119         if (!indio_dev)
 120                 return -ENOMEM;
 121         st = iio_priv(indio_dev);
 122         i2c_set_clientdata(client, indio_dev);
 123         st->read_reg = ade7854_i2c_read_reg;
 124         st->write_reg = ade7854_i2c_write_reg;
 125         st->i2c = client;
 126         st->irq = client->irq;
 127 
 128         return ade7854_probe(indio_dev, &client->dev);
 129 }
 130 
 131 static const struct i2c_device_id ade7854_id[] = {
 132         { "ade7854", 0 },
 133         { "ade7858", 0 },
 134         { "ade7868", 0 },
 135         { "ade7878", 0 },
 136         { }
 137 };
 138 MODULE_DEVICE_TABLE(i2c, ade7854_id);
 139 
 140 static struct i2c_driver ade7854_i2c_driver = {
 141         .driver = {
 142                 .name = "ade7854",
 143         },
 144         .probe    = ade7854_i2c_probe,
 145         .id_table = ade7854_id,
 146 };
 147 module_i2c_driver(ade7854_i2c_driver);
 148 
 149 MODULE_AUTHOR("Barry Song <21cnbao@gmail.com>");
 150 MODULE_DESCRIPTION("Analog Devices ADE7854/58/68/78 Polyphase Multifunction Energy Metering IC I2C Driver");
 151 MODULE_LICENSE("GPL v2");

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