linux/drivers/hwmon/tmp102.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-or-later
   2/* Texas Instruments TMP102 SMBus temperature sensor driver
   3 *
   4 * Copyright (C) 2010 Steven King <sfking@fdwdc.com>
   5 */
   6
   7#include <linux/delay.h>
   8#include <linux/module.h>
   9#include <linux/init.h>
  10#include <linux/slab.h>
  11#include <linux/i2c.h>
  12#include <linux/hwmon.h>
  13#include <linux/hwmon-sysfs.h>
  14#include <linux/err.h>
  15#include <linux/mutex.h>
  16#include <linux/device.h>
  17#include <linux/jiffies.h>
  18#include <linux/regmap.h>
  19#include <linux/of.h>
  20
  21#define DRIVER_NAME "tmp102"
  22
  23#define TMP102_TEMP_REG                 0x00
  24#define TMP102_CONF_REG                 0x01
  25/* note: these bit definitions are byte swapped */
  26#define         TMP102_CONF_SD          0x0100
  27#define         TMP102_CONF_TM          0x0200
  28#define         TMP102_CONF_POL         0x0400
  29#define         TMP102_CONF_F0          0x0800
  30#define         TMP102_CONF_F1          0x1000
  31#define         TMP102_CONF_R0          0x2000
  32#define         TMP102_CONF_R1          0x4000
  33#define         TMP102_CONF_OS          0x8000
  34#define         TMP102_CONF_EM          0x0010
  35#define         TMP102_CONF_AL          0x0020
  36#define         TMP102_CONF_CR0         0x0040
  37#define         TMP102_CONF_CR1         0x0080
  38#define TMP102_TLOW_REG                 0x02
  39#define TMP102_THIGH_REG                0x03
  40
  41#define TMP102_CONFREG_MASK     (TMP102_CONF_SD | TMP102_CONF_TM | \
  42                                 TMP102_CONF_POL | TMP102_CONF_F0 | \
  43                                 TMP102_CONF_F1 | TMP102_CONF_OS | \
  44                                 TMP102_CONF_EM | TMP102_CONF_AL | \
  45                                 TMP102_CONF_CR0 | TMP102_CONF_CR1)
  46
  47#define TMP102_CONFIG_CLEAR     (TMP102_CONF_SD | TMP102_CONF_OS | \
  48                                 TMP102_CONF_CR0)
  49#define TMP102_CONFIG_SET       (TMP102_CONF_TM | TMP102_CONF_EM | \
  50                                 TMP102_CONF_CR1)
  51
  52#define CONVERSION_TIME_MS              35      /* in milli-seconds */
  53
  54struct tmp102 {
  55        struct regmap *regmap;
  56        u16 config_orig;
  57        unsigned long ready_time;
  58};
  59
  60/* convert left adjusted 13-bit TMP102 register value to milliCelsius */
  61static inline int tmp102_reg_to_mC(s16 val)
  62{
  63        return ((val & ~0x01) * 1000) / 128;
  64}
  65
  66/* convert milliCelsius to left adjusted 13-bit TMP102 register value */
  67static inline u16 tmp102_mC_to_reg(int val)
  68{
  69        return (val * 128) / 1000;
  70}
  71
  72static int tmp102_read(struct device *dev, enum hwmon_sensor_types type,
  73                       u32 attr, int channel, long *temp)
  74{
  75        struct tmp102 *tmp102 = dev_get_drvdata(dev);
  76        unsigned int regval;
  77        int err, reg;
  78
  79        switch (attr) {
  80        case hwmon_temp_input:
  81                /* Is it too early to return a conversion ? */
  82                if (time_before(jiffies, tmp102->ready_time)) {
  83                        dev_dbg(dev, "%s: Conversion not ready yet..\n", __func__);
  84                        return -EAGAIN;
  85                }
  86                reg = TMP102_TEMP_REG;
  87                break;
  88        case hwmon_temp_max_hyst:
  89                reg = TMP102_TLOW_REG;
  90                break;
  91        case hwmon_temp_max:
  92                reg = TMP102_THIGH_REG;
  93                break;
  94        default:
  95                return -EOPNOTSUPP;
  96        }
  97
  98        err = regmap_read(tmp102->regmap, reg, &regval);
  99        if (err < 0)
 100                return err;
 101        *temp = tmp102_reg_to_mC(regval);
 102
 103        return 0;
 104}
 105
 106static int tmp102_write(struct device *dev, enum hwmon_sensor_types type,
 107                        u32 attr, int channel, long temp)
 108{
 109        struct tmp102 *tmp102 = dev_get_drvdata(dev);
 110        int reg;
 111
 112        switch (attr) {
 113        case hwmon_temp_max_hyst:
 114                reg = TMP102_TLOW_REG;
 115                break;
 116        case hwmon_temp_max:
 117                reg = TMP102_THIGH_REG;
 118                break;
 119        default:
 120                return -EOPNOTSUPP;
 121        }
 122
 123        temp = clamp_val(temp, -256000, 255000);
 124        return regmap_write(tmp102->regmap, reg, tmp102_mC_to_reg(temp));
 125}
 126
 127static umode_t tmp102_is_visible(const void *data, enum hwmon_sensor_types type,
 128                                 u32 attr, int channel)
 129{
 130        if (type != hwmon_temp)
 131                return 0;
 132
 133        switch (attr) {
 134        case hwmon_temp_input:
 135                return 0444;
 136        case hwmon_temp_max_hyst:
 137        case hwmon_temp_max:
 138                return 0644;
 139        default:
 140                return 0;
 141        }
 142}
 143
 144static const struct hwmon_channel_info *tmp102_info[] = {
 145        HWMON_CHANNEL_INFO(chip,
 146                           HWMON_C_REGISTER_TZ),
 147        HWMON_CHANNEL_INFO(temp,
 148                           HWMON_T_INPUT | HWMON_T_MAX | HWMON_T_MAX_HYST),
 149        NULL
 150};
 151
 152static const struct hwmon_ops tmp102_hwmon_ops = {
 153        .is_visible = tmp102_is_visible,
 154        .read = tmp102_read,
 155        .write = tmp102_write,
 156};
 157
 158static const struct hwmon_chip_info tmp102_chip_info = {
 159        .ops = &tmp102_hwmon_ops,
 160        .info = tmp102_info,
 161};
 162
 163static void tmp102_restore_config(void *data)
 164{
 165        struct tmp102 *tmp102 = data;
 166
 167        regmap_write(tmp102->regmap, TMP102_CONF_REG, tmp102->config_orig);
 168}
 169
 170static bool tmp102_is_writeable_reg(struct device *dev, unsigned int reg)
 171{
 172        return reg != TMP102_TEMP_REG;
 173}
 174
 175static bool tmp102_is_volatile_reg(struct device *dev, unsigned int reg)
 176{
 177        return reg == TMP102_TEMP_REG;
 178}
 179
 180static const struct regmap_config tmp102_regmap_config = {
 181        .reg_bits = 8,
 182        .val_bits = 16,
 183        .max_register = TMP102_THIGH_REG,
 184        .writeable_reg = tmp102_is_writeable_reg,
 185        .volatile_reg = tmp102_is_volatile_reg,
 186        .val_format_endian = REGMAP_ENDIAN_BIG,
 187        .cache_type = REGCACHE_RBTREE,
 188        .use_single_read = true,
 189        .use_single_write = true,
 190};
 191
 192static int tmp102_probe(struct i2c_client *client)
 193{
 194        struct device *dev = &client->dev;
 195        struct device *hwmon_dev;
 196        struct tmp102 *tmp102;
 197        unsigned int regval;
 198        int err;
 199
 200        if (!i2c_check_functionality(client->adapter,
 201                                     I2C_FUNC_SMBUS_WORD_DATA)) {
 202                dev_err(dev,
 203                        "adapter doesn't support SMBus word transactions\n");
 204                return -ENODEV;
 205        }
 206
 207        tmp102 = devm_kzalloc(dev, sizeof(*tmp102), GFP_KERNEL);
 208        if (!tmp102)
 209                return -ENOMEM;
 210
 211        i2c_set_clientdata(client, tmp102);
 212
 213        tmp102->regmap = devm_regmap_init_i2c(client, &tmp102_regmap_config);
 214        if (IS_ERR(tmp102->regmap))
 215                return PTR_ERR(tmp102->regmap);
 216
 217        err = regmap_read(tmp102->regmap, TMP102_CONF_REG, &regval);
 218        if (err < 0) {
 219                dev_err(dev, "error reading config register\n");
 220                return err;
 221        }
 222
 223        if ((regval & ~TMP102_CONFREG_MASK) !=
 224            (TMP102_CONF_R0 | TMP102_CONF_R1)) {
 225                dev_err(dev, "unexpected config register value\n");
 226                return -ENODEV;
 227        }
 228
 229        tmp102->config_orig = regval;
 230
 231        err = devm_add_action_or_reset(dev, tmp102_restore_config, tmp102);
 232        if (err)
 233                return err;
 234
 235        regval &= ~TMP102_CONFIG_CLEAR;
 236        regval |= TMP102_CONFIG_SET;
 237
 238        err = regmap_write(tmp102->regmap, TMP102_CONF_REG, regval);
 239        if (err < 0) {
 240                dev_err(dev, "error writing config register\n");
 241                return err;
 242        }
 243
 244        /*
 245         * Mark that we are not ready with data until the first
 246         * conversion is complete
 247         */
 248        tmp102->ready_time = jiffies + msecs_to_jiffies(CONVERSION_TIME_MS);
 249
 250        hwmon_dev = devm_hwmon_device_register_with_info(dev, client->name,
 251                                                         tmp102,
 252                                                         &tmp102_chip_info,
 253                                                         NULL);
 254        if (IS_ERR(hwmon_dev)) {
 255                dev_dbg(dev, "unable to register hwmon device\n");
 256                return PTR_ERR(hwmon_dev);
 257        }
 258        dev_info(dev, "initialized\n");
 259
 260        return 0;
 261}
 262
 263#ifdef CONFIG_PM_SLEEP
 264static int tmp102_suspend(struct device *dev)
 265{
 266        struct i2c_client *client = to_i2c_client(dev);
 267        struct tmp102 *tmp102 = i2c_get_clientdata(client);
 268
 269        return regmap_update_bits(tmp102->regmap, TMP102_CONF_REG,
 270                                  TMP102_CONF_SD, TMP102_CONF_SD);
 271}
 272
 273static int tmp102_resume(struct device *dev)
 274{
 275        struct i2c_client *client = to_i2c_client(dev);
 276        struct tmp102 *tmp102 = i2c_get_clientdata(client);
 277        int err;
 278
 279        err = regmap_update_bits(tmp102->regmap, TMP102_CONF_REG,
 280                                 TMP102_CONF_SD, 0);
 281
 282        tmp102->ready_time = jiffies + msecs_to_jiffies(CONVERSION_TIME_MS);
 283
 284        return err;
 285}
 286#endif /* CONFIG_PM */
 287
 288static SIMPLE_DEV_PM_OPS(tmp102_dev_pm_ops, tmp102_suspend, tmp102_resume);
 289
 290static const struct i2c_device_id tmp102_id[] = {
 291        { "tmp102", 0 },
 292        { }
 293};
 294MODULE_DEVICE_TABLE(i2c, tmp102_id);
 295
 296static const struct of_device_id __maybe_unused tmp102_of_match[] = {
 297        { .compatible = "ti,tmp102" },
 298        { },
 299};
 300MODULE_DEVICE_TABLE(of, tmp102_of_match);
 301
 302static struct i2c_driver tmp102_driver = {
 303        .driver.name    = DRIVER_NAME,
 304        .driver.of_match_table = of_match_ptr(tmp102_of_match),
 305        .driver.pm      = &tmp102_dev_pm_ops,
 306        .probe_new      = tmp102_probe,
 307        .id_table       = tmp102_id,
 308};
 309
 310module_i2c_driver(tmp102_driver);
 311
 312MODULE_AUTHOR("Steven King <sfking@fdwdc.com>");
 313MODULE_DESCRIPTION("Texas Instruments TMP102 temperature sensor driver");
 314MODULE_LICENSE("GPL");
 315