hwmon: (tmp401) Add support of three advanced features
authorCamel Guo <camel.guo@axis.com>
Thu, 14 Apr 2022 07:58:23 +0000 (09:58 +0200)
committerGuenter Roeck <linux@roeck-us.net>
Fri, 20 May 2022 17:57:05 +0000 (10:57 -0700)
tmp401 driver supports TMP401, TMP411 and TMP43X temperature sensors.
According to their datasheet:
- all of them support extended temperature range feature;
- TMP411 and TPM43X support n-factor correction feature;
- TMP43X support beta compensation feature.

In order to support setting them during bootup, this commit reads
ti,extended-range-enable, ti,n-factor and ti,beta-compensation and set
the corresponding registers during probing.

Signed-off-by: Camel Guo <camel.guo@axis.com>
Link: https://lore.kernel.org/r/20220414075824.2634839-3-camel.guo@axis.com
Signed-off-by: Guenter Roeck <linux@roeck-us.net>
drivers/hwmon/tmp401.c

index 52c9e7d..63e53c8 100644 (file)
@@ -41,6 +41,8 @@ enum chips { tmp401, tmp411, tmp431, tmp432, tmp435 };
 #define TMP401_STATUS                          0x02
 #define TMP401_CONFIG                          0x03
 #define TMP401_CONVERSION_RATE                 0x04
+#define TMP4XX_N_FACTOR_REG                    0x18
+#define TMP43X_BETA_RANGE                      0x25
 #define TMP401_TEMP_CRIT_HYST                  0x21
 #define TMP401_MANUFACTURER_ID_REG             0xFE
 #define TMP401_DEVICE_ID_REG                   0xFF
@@ -543,6 +545,8 @@ static int tmp401_init_client(struct tmp401_data *data)
        struct regmap *regmap = data->regmap;
        u32 config, config_orig;
        int ret;
+       u32 val = 0;
+       s32 nfactor = 0;
 
        /* Set conversion rate to 2 Hz */
        ret = regmap_write(regmap, TMP401_CONVERSION_RATE, 5);
@@ -557,10 +561,48 @@ static int tmp401_init_client(struct tmp401_data *data)
        config_orig = config;
        config &= ~TMP401_CONFIG_SHUTDOWN;
 
+       if (of_property_read_bool(data->client->dev.of_node, "ti,extended-range-enable")) {
+               /* Enable measurement over extended temperature range */
+               config |= TMP401_CONFIG_RANGE;
+       }
+
        data->extended_range = !!(config & TMP401_CONFIG_RANGE);
 
-       if (config != config_orig)
+       if (config != config_orig) {
                ret = regmap_write(regmap, TMP401_CONFIG, config);
+               if (ret < 0)
+                       return ret;
+       }
+
+       ret = of_property_read_u32(data->client->dev.of_node, "ti,n-factor", &nfactor);
+       if (!ret) {
+               if (data->kind == tmp401) {
+                       dev_err(&data->client->dev, "ti,tmp401 does not support n-factor correction\n");
+                       return -EINVAL;
+               }
+               if (nfactor < -128 || nfactor > 127) {
+                       dev_err(&data->client->dev, "n-factor is invalid (%d)\n", nfactor);
+                       return -EINVAL;
+               }
+               ret = regmap_write(regmap, TMP4XX_N_FACTOR_REG, (unsigned int)nfactor);
+               if (ret < 0)
+                       return ret;
+       }
+
+       ret = of_property_read_u32(data->client->dev.of_node, "ti,beta-compensation", &val);
+       if (!ret) {
+               if (data->kind == tmp401 || data->kind == tmp411) {
+                       dev_err(&data->client->dev, "ti,tmp401 or ti,tmp411 does not support beta compensation\n");
+                       return -EINVAL;
+               }
+               if (val > 15) {
+                       dev_err(&data->client->dev, "beta-compensation is invalid (%u)\n", val);
+                       return -EINVAL;
+               }
+               ret = regmap_write(regmap, TMP43X_BETA_RANGE, val);
+               if (ret < 0)
+                       return ret;
+       }
 
        return ret;
 }