summaryrefslogtreecommitdiff
path: root/drivers/hwmon/lm95245.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/hwmon/lm95245.c')
-rw-r--r--drivers/hwmon/lm95245.c138
1 files changed, 53 insertions, 85 deletions
diff --git a/drivers/hwmon/lm95245.c b/drivers/hwmon/lm95245.c
index 29388fcf5f74..9ed300c6b5f7 100644
--- a/drivers/hwmon/lm95245.c
+++ b/drivers/hwmon/lm95245.c
@@ -13,7 +13,6 @@
#include <linux/hwmon.h>
#include <linux/i2c.h>
#include <linux/module.h>
-#include <linux/mutex.h>
#include <linux/regmap.h>
#include <linux/slab.h>
@@ -86,7 +85,6 @@ static const unsigned short normal_i2c[] = {
/* Client data (each client gets its own) */
struct lm95245_data {
struct regmap *regmap;
- struct mutex update_lock;
int interval; /* in msecs */
};
@@ -161,18 +159,18 @@ static int lm95245_read_temp(struct device *dev, u32 attr, int channel,
{
struct lm95245_data *data = dev_get_drvdata(dev);
struct regmap *regmap = data->regmap;
- int ret, regl, regh, regvall, regvalh;
+ unsigned int regs[2];
+ unsigned int regval;
+ u8 regvals[2];
+ int ret;
switch (attr) {
case hwmon_temp_input:
- regl = channel ? LM95245_REG_R_REMOTE_TEMPL_S :
- LM95245_REG_R_LOCAL_TEMPL_S;
- regh = channel ? LM95245_REG_R_REMOTE_TEMPH_S :
- LM95245_REG_R_LOCAL_TEMPH_S;
- ret = regmap_read(regmap, regl, &regvall);
- if (ret < 0)
- return ret;
- ret = regmap_read(regmap, regh, &regvalh);
+ regs[0] = channel ? LM95245_REG_R_REMOTE_TEMPL_S :
+ LM95245_REG_R_LOCAL_TEMPL_S;
+ regs[1] = channel ? LM95245_REG_R_REMOTE_TEMPH_S :
+ LM95245_REG_R_LOCAL_TEMPH_S;
+ ret = regmap_multi_reg_read(regmap, regs, regvals, 2);
if (ret < 0)
return ret;
/*
@@ -181,92 +179,77 @@ static int lm95245_read_temp(struct device *dev, u32 attr, int channel,
* Use signed calculation for remote if signed bit is set
* or if reported temperature is below signed limit.
*/
- if (!channel || (regvalh & 0x80) || regvalh < 0x7f) {
- *val = temp_from_reg_signed(regvalh, regvall);
+ if (!channel || (regvals[1] & 0x80) || regvals[1] < 0x7f) {
+ *val = temp_from_reg_signed(regvals[1], regvals[0]);
return 0;
}
- ret = regmap_read(regmap, LM95245_REG_R_REMOTE_TEMPL_U,
- &regvall);
- if (ret < 0)
- return ret;
- ret = regmap_read(regmap, LM95245_REG_R_REMOTE_TEMPH_U,
- &regvalh);
- if (ret < 0)
+ ret = regmap_bulk_read(regmap, LM95245_REG_R_REMOTE_TEMPH_U, regvals, 2);
+ if (ret)
return ret;
- *val = temp_from_reg_unsigned(regvalh, regvall);
+ *val = temp_from_reg_unsigned(regvals[0], regvals[1]);
return 0;
case hwmon_temp_max:
ret = regmap_read(regmap, LM95245_REG_RW_REMOTE_OS_LIMIT,
- &regvalh);
+ &regval);
if (ret < 0)
return ret;
- *val = regvalh * 1000;
+ *val = regval * 1000;
return 0;
case hwmon_temp_crit:
- regh = channel ? LM95245_REG_RW_REMOTE_TCRIT_LIMIT :
- LM95245_REG_RW_LOCAL_OS_TCRIT_LIMIT;
- ret = regmap_read(regmap, regh, &regvalh);
+ regs[0] = channel ? LM95245_REG_RW_REMOTE_TCRIT_LIMIT :
+ LM95245_REG_RW_LOCAL_OS_TCRIT_LIMIT;
+ ret = regmap_read(regmap, regs[0], &regval);
if (ret < 0)
return ret;
- *val = regvalh * 1000;
+ *val = regval * 1000;
return 0;
case hwmon_temp_max_hyst:
- ret = regmap_read(regmap, LM95245_REG_RW_REMOTE_OS_LIMIT,
- &regvalh);
+ regs[0] = LM95245_REG_RW_REMOTE_OS_LIMIT;
+ regs[1] = LM95245_REG_RW_COMMON_HYSTERESIS;
+ ret = regmap_multi_reg_read(regmap, regs, regvals, 2);
if (ret < 0)
return ret;
- ret = regmap_read(regmap, LM95245_REG_RW_COMMON_HYSTERESIS,
- &regvall);
- if (ret < 0)
- return ret;
- *val = (regvalh - regvall) * 1000;
+ *val = (regvals[0] - regvals[1]) * 1000;
return 0;
case hwmon_temp_crit_hyst:
- regh = channel ? LM95245_REG_RW_REMOTE_TCRIT_LIMIT :
- LM95245_REG_RW_LOCAL_OS_TCRIT_LIMIT;
- ret = regmap_read(regmap, regh, &regvalh);
- if (ret < 0)
- return ret;
- ret = regmap_read(regmap, LM95245_REG_RW_COMMON_HYSTERESIS,
- &regvall);
+ regs[0] = channel ? LM95245_REG_RW_REMOTE_TCRIT_LIMIT :
+ LM95245_REG_RW_LOCAL_OS_TCRIT_LIMIT;
+ regs[1] = LM95245_REG_RW_COMMON_HYSTERESIS;
+
+ ret = regmap_multi_reg_read(regmap, regs, regvals, 2);
if (ret < 0)
return ret;
- *val = (regvalh - regvall) * 1000;
+ *val = (regvals[0] - regvals[1]) * 1000;
return 0;
case hwmon_temp_type:
- ret = regmap_read(regmap, LM95245_REG_RW_CONFIG2, &regvalh);
+ ret = regmap_read(regmap, LM95245_REG_RW_CONFIG2, &regval);
if (ret < 0)
return ret;
- *val = (regvalh & CFG2_REMOTE_TT) ? 1 : 2;
+ *val = (regval & CFG2_REMOTE_TT) ? 1 : 2;
return 0;
case hwmon_temp_offset:
- ret = regmap_read(regmap, LM95245_REG_RW_REMOTE_OFFL,
- &regvall);
- if (ret < 0)
- return ret;
- ret = regmap_read(regmap, LM95245_REG_RW_REMOTE_OFFH,
- &regvalh);
+ ret = regmap_bulk_read(regmap, LM95245_REG_RW_REMOTE_OFFH, regvals, 2);
if (ret < 0)
return ret;
- *val = temp_from_reg_signed(regvalh, regvall);
+ *val = temp_from_reg_signed(regvals[0], regvals[1]);
return 0;
case hwmon_temp_max_alarm:
- ret = regmap_read(regmap, LM95245_REG_R_STATUS1, &regvalh);
+ ret = regmap_read(regmap, LM95245_REG_R_STATUS1, &regval);
if (ret < 0)
return ret;
- *val = !!(regvalh & STATUS1_ROS);
+ *val = !!(regval & STATUS1_ROS);
return 0;
case hwmon_temp_crit_alarm:
- ret = regmap_read(regmap, LM95245_REG_R_STATUS1, &regvalh);
+ ret = regmap_read(regmap, LM95245_REG_R_STATUS1, &regval);
if (ret < 0)
return ret;
- *val = !!(regvalh & (channel ? STATUS1_RTCRIT : STATUS1_LOC));
+ *val = !!(regval & (channel ? STATUS1_RTCRIT : STATUS1_LOC));
return 0;
case hwmon_temp_fault:
- ret = regmap_read(regmap, LM95245_REG_R_STATUS1, &regvalh);
+ ret = regmap_read(regmap, LM95245_REG_R_STATUS1, &regval);
if (ret < 0)
return ret;
- *val = !!(regvalh & STATUS1_DIODE_FAULT);
+ *val = !!(regval & STATUS1_DIODE_FAULT);
return 0;
default:
return -EOPNOTSUPP;
@@ -279,6 +262,7 @@ static int lm95245_write_temp(struct device *dev, u32 attr, int channel,
struct lm95245_data *data = dev_get_drvdata(dev);
struct regmap *regmap = data->regmap;
unsigned int regval;
+ u8 regvals[2];
int ret, reg;
switch (attr) {
@@ -293,34 +277,24 @@ static int lm95245_write_temp(struct device *dev, u32 attr, int channel,
ret = regmap_write(regmap, reg, val);
return ret;
case hwmon_temp_crit_hyst:
- mutex_lock(&data->update_lock);
ret = regmap_read(regmap, LM95245_REG_RW_LOCAL_OS_TCRIT_LIMIT,
&regval);
- if (ret < 0) {
- mutex_unlock(&data->update_lock);
+ if (ret < 0)
return ret;
- }
/* Clamp to reasonable range to prevent overflow */
val = clamp_val(val, -1000000, 1000000);
val = regval - val / 1000;
val = clamp_val(val, 0, 31);
ret = regmap_write(regmap, LM95245_REG_RW_COMMON_HYSTERESIS,
val);
- mutex_unlock(&data->update_lock);
return ret;
case hwmon_temp_offset:
val = clamp_val(val, -128000, 127875);
val = val * 256 / 1000;
- mutex_lock(&data->update_lock);
- ret = regmap_write(regmap, LM95245_REG_RW_REMOTE_OFFL,
- val & 0xe0);
- if (ret < 0) {
- mutex_unlock(&data->update_lock);
- return ret;
- }
- ret = regmap_write(regmap, LM95245_REG_RW_REMOTE_OFFH,
- (val >> 8) & 0xff);
- mutex_unlock(&data->update_lock);
+ regvals[0] = val >> 8;
+ regvals[1] = val & 0xe0;
+
+ ret = regmap_bulk_write(regmap, LM95245_REG_RW_REMOTE_OFFH, regvals, 2);
return ret;
case hwmon_temp_type:
if (val != 1 && val != 2)
@@ -352,14 +326,10 @@ static int lm95245_write_chip(struct device *dev, u32 attr, int channel,
long val)
{
struct lm95245_data *data = dev_get_drvdata(dev);
- int ret;
switch (attr) {
case hwmon_chip_update_interval:
- mutex_lock(&data->update_lock);
- ret = lm95245_set_conversion_rate(data, val);
- mutex_unlock(&data->update_lock);
- return ret;
+ return lm95245_set_conversion_rate(data, val);
default:
return -EOPNOTSUPP;
}
@@ -461,7 +431,7 @@ static int lm95245_detect(struct i2c_client *new_client,
return -ENODEV;
}
- strlcpy(info->type, name, I2C_NAME_SIZE);
+ strscpy(info->type, name, I2C_NAME_SIZE);
return 0;
}
@@ -518,12 +488,12 @@ static const struct regmap_config lm95245_regmap_config = {
.val_bits = 8,
.writeable_reg = lm95245_is_writeable_reg,
.volatile_reg = lm95245_is_volatile_reg,
- .cache_type = REGCACHE_RBTREE,
+ .cache_type = REGCACHE_MAPLE,
.use_single_read = true,
.use_single_write = true,
};
-static const struct hwmon_channel_info *lm95245_info[] = {
+static const struct hwmon_channel_info * const lm95245_info[] = {
HWMON_CHANNEL_INFO(chip,
HWMON_C_UPDATE_INTERVAL),
HWMON_CHANNEL_INFO(temp,
@@ -562,8 +532,6 @@ static int lm95245_probe(struct i2c_client *client)
if (IS_ERR(data->regmap))
return PTR_ERR(data->regmap);
- mutex_init(&data->update_lock);
-
/* Initialize the LM95245 chip */
ret = lm95245_init_client(data);
if (ret < 0)
@@ -578,8 +546,8 @@ static int lm95245_probe(struct i2c_client *client)
/* Driver data (common to all clients) */
static const struct i2c_device_id lm95245_id[] = {
- { "lm95235", 0 },
- { "lm95245", 0 },
+ { "lm95235" },
+ { "lm95245" },
{ }
};
MODULE_DEVICE_TABLE(i2c, lm95245_id);
@@ -597,7 +565,7 @@ static struct i2c_driver lm95245_driver = {
.name = "lm95245",
.of_match_table = of_match_ptr(lm95245_of_match),
},
- .probe_new = lm95245_probe,
+ .probe = lm95245_probe,
.id_table = lm95245_id,
.detect = lm95245_detect,
.address_list = normal_i2c,