18d5d45fbSJean Delvare /* 2caaa0f36SShubhrajyoti D * lm75.c - Part of lm_sensors, Linux kernel modules for hardware 3caaa0f36SShubhrajyoti D * monitoring 4caaa0f36SShubhrajyoti D * Copyright (c) 1998, 1999 Frodo Looijaard <frodol@dds.nl> 5caaa0f36SShubhrajyoti D * 6caaa0f36SShubhrajyoti D * This program is free software; you can redistribute it and/or modify 7caaa0f36SShubhrajyoti D * it under the terms of the GNU General Public License as published by 8caaa0f36SShubhrajyoti D * the Free Software Foundation; either version 2 of the License, or 9caaa0f36SShubhrajyoti D * (at your option) any later version. 10caaa0f36SShubhrajyoti D * 11caaa0f36SShubhrajyoti D * This program is distributed in the hope that it will be useful, 12caaa0f36SShubhrajyoti D * but WITHOUT ANY WARRANTY; without even the implied warranty of 13caaa0f36SShubhrajyoti D * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14caaa0f36SShubhrajyoti D * GNU General Public License for more details. 15caaa0f36SShubhrajyoti D * 16caaa0f36SShubhrajyoti D * You should have received a copy of the GNU General Public License 17caaa0f36SShubhrajyoti D * along with this program; if not, write to the Free Software 18caaa0f36SShubhrajyoti D * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 198d5d45fbSJean Delvare */ 208d5d45fbSJean Delvare 218d5d45fbSJean Delvare #include <linux/module.h> 228d5d45fbSJean Delvare #include <linux/init.h> 238d5d45fbSJean Delvare #include <linux/slab.h> 248d5d45fbSJean Delvare #include <linux/jiffies.h> 258d5d45fbSJean Delvare #include <linux/i2c.h> 26943b0830SMark M. Hoffman #include <linux/hwmon.h> 279ca8e40cSJean Delvare #include <linux/hwmon-sysfs.h> 28943b0830SMark M. Hoffman #include <linux/err.h> 299a61bf63SIngo Molnar #include <linux/mutex.h> 3022e73183SEduardo Valentin #include <linux/of.h> 3122e73183SEduardo Valentin #include <linux/thermal.h> 328d5d45fbSJean Delvare #include "lm75.h" 338d5d45fbSJean Delvare 348d5d45fbSJean Delvare 3501a52397SDavid Brownell /* 3601a52397SDavid Brownell * This driver handles the LM75 and compatible digital temperature sensors. 3701a52397SDavid Brownell */ 3801a52397SDavid Brownell 399ebd3d82SDavid Brownell enum lm75_type { /* keep sorted in alphabetical order */ 40e96f9d89SMichael Hennerich adt75, 411f86df49SJean Delvare ds1775, 429ebd3d82SDavid Brownell ds75, 433fbc81e3SJean Delvare ds7505, 44c98d6c65SArnaud Ebalard g751, 451f86df49SJean Delvare lm75, 469ebd3d82SDavid Brownell lm75a, 479ebd3d82SDavid Brownell max6625, 489ebd3d82SDavid Brownell max6626, 499ebd3d82SDavid Brownell mcp980x, 509ebd3d82SDavid Brownell stds75, 519ebd3d82SDavid Brownell tcn75, 529ebd3d82SDavid Brownell tmp100, 539ebd3d82SDavid Brownell tmp101, 546d034059SShubhrajyoti Datta tmp105, 55c83959f8SFrans Klaver tmp112, 569ebd3d82SDavid Brownell tmp175, 579ebd3d82SDavid Brownell tmp275, 589ebd3d82SDavid Brownell tmp75, 599ebd3d82SDavid Brownell }; 609ebd3d82SDavid Brownell 618ff69eebSJean Delvare /* Addresses scanned */ 6225e9c86dSMark M. Hoffman static const unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c, 638d5d45fbSJean Delvare 0x4d, 0x4e, 0x4f, I2C_CLIENT_END }; 648d5d45fbSJean Delvare 658d5d45fbSJean Delvare 668d5d45fbSJean Delvare /* The LM75 registers */ 678d5d45fbSJean Delvare #define LM75_REG_CONF 0x01 689ca8e40cSJean Delvare static const u8 LM75_REG_TEMP[3] = { 699ca8e40cSJean Delvare 0x00, /* input */ 709ca8e40cSJean Delvare 0x03, /* max */ 719ca8e40cSJean Delvare 0x02, /* hyst */ 729ca8e40cSJean Delvare }; 738d5d45fbSJean Delvare 748d5d45fbSJean Delvare /* Each client has this additional data */ 758d5d45fbSJean Delvare struct lm75_data { 76d663ec49SGuenter Roeck struct i2c_client *client; 771beeffe4STony Jones struct device *hwmon_dev; 7822e73183SEduardo Valentin struct thermal_zone_device *tz; 799a61bf63SIngo Molnar struct mutex update_lock; 809ebd3d82SDavid Brownell u8 orig_conf; 8187d0621aSJean Delvare u8 resolution; /* In bits, between 9 and 12 */ 8287d0621aSJean Delvare u8 resolution_limits; 8301a52397SDavid Brownell char valid; /* !=0 if registers are valid */ 848d5d45fbSJean Delvare unsigned long last_updated; /* In jiffies */ 8587d0621aSJean Delvare unsigned long sample_time; /* In jiffies */ 8687d0621aSJean Delvare s16 temp[3]; /* Register values, 879ca8e40cSJean Delvare 0 = input 889ca8e40cSJean Delvare 1 = max 899ca8e40cSJean Delvare 2 = hyst */ 908d5d45fbSJean Delvare }; 918d5d45fbSJean Delvare 928d5d45fbSJean Delvare static int lm75_read_value(struct i2c_client *client, u8 reg); 938d5d45fbSJean Delvare static int lm75_write_value(struct i2c_client *client, u8 reg, u16 value); 948d5d45fbSJean Delvare static struct lm75_data *lm75_update_device(struct device *dev); 958d5d45fbSJean Delvare 968d5d45fbSJean Delvare 9701a52397SDavid Brownell /*-----------------------------------------------------------------------*/ 9801a52397SDavid Brownell 9922e73183SEduardo Valentin static inline long lm75_reg_to_mc(s16 temp, u8 resolution) 10022e73183SEduardo Valentin { 10122e73183SEduardo Valentin return ((temp >> (16 - resolution)) * 1000) >> (resolution - 8); 10222e73183SEduardo Valentin } 10322e73183SEduardo Valentin 10401a52397SDavid Brownell /* sysfs attributes for hwmon */ 1058d5d45fbSJean Delvare 10622e73183SEduardo Valentin static int lm75_read_temp(void *dev, long *temp) 10722e73183SEduardo Valentin { 10822e73183SEduardo Valentin struct lm75_data *data = lm75_update_device(dev); 10922e73183SEduardo Valentin 11022e73183SEduardo Valentin if (IS_ERR(data)) 11122e73183SEduardo Valentin return PTR_ERR(data); 11222e73183SEduardo Valentin 11322e73183SEduardo Valentin *temp = lm75_reg_to_mc(data->temp[0], data->resolution); 11422e73183SEduardo Valentin 11522e73183SEduardo Valentin return 0; 11622e73183SEduardo Valentin } 11722e73183SEduardo Valentin 1189ca8e40cSJean Delvare static ssize_t show_temp(struct device *dev, struct device_attribute *da, 1199ca8e40cSJean Delvare char *buf) 1209ca8e40cSJean Delvare { 1219ca8e40cSJean Delvare struct sensor_device_attribute *attr = to_sensor_dev_attr(da); 1229ca8e40cSJean Delvare struct lm75_data *data = lm75_update_device(dev); 1231f962f36SFrans Meulenbroeks 1241f962f36SFrans Meulenbroeks if (IS_ERR(data)) 1251f962f36SFrans Meulenbroeks return PTR_ERR(data); 1261f962f36SFrans Meulenbroeks 12722e73183SEduardo Valentin return sprintf(buf, "%ld\n", lm75_reg_to_mc(data->temp[attr->index], 12822e73183SEduardo Valentin data->resolution)); 1298d5d45fbSJean Delvare } 1308d5d45fbSJean Delvare 1319ca8e40cSJean Delvare static ssize_t set_temp(struct device *dev, struct device_attribute *da, 1329ca8e40cSJean Delvare const char *buf, size_t count) 1339ca8e40cSJean Delvare { 1349ca8e40cSJean Delvare struct sensor_device_attribute *attr = to_sensor_dev_attr(da); 135d663ec49SGuenter Roeck struct lm75_data *data = dev_get_drvdata(dev); 136d663ec49SGuenter Roeck struct i2c_client *client = data->client; 1379ca8e40cSJean Delvare int nr = attr->index; 138e3cd9528SShubhrajyoti D long temp; 139e3cd9528SShubhrajyoti D int error; 14087d0621aSJean Delvare u8 resolution; 141e3cd9528SShubhrajyoti D 14224edc0a7SFrans Meulenbroeks error = kstrtol(buf, 10, &temp); 143e3cd9528SShubhrajyoti D if (error) 144e3cd9528SShubhrajyoti D return error; 1459ca8e40cSJean Delvare 14687d0621aSJean Delvare /* 14787d0621aSJean Delvare * Resolution of limit registers is assumed to be the same as the 14887d0621aSJean Delvare * temperature input register resolution unless given explicitly. 14987d0621aSJean Delvare */ 15087d0621aSJean Delvare if (attr->index && data->resolution_limits) 15187d0621aSJean Delvare resolution = data->resolution_limits; 15287d0621aSJean Delvare else 15387d0621aSJean Delvare resolution = data->resolution; 15487d0621aSJean Delvare 1559ca8e40cSJean Delvare mutex_lock(&data->update_lock); 15687d0621aSJean Delvare temp = clamp_val(temp, LM75_TEMP_MIN, LM75_TEMP_MAX); 15787d0621aSJean Delvare data->temp[nr] = DIV_ROUND_CLOSEST(temp << (resolution - 8), 15887d0621aSJean Delvare 1000) << (16 - resolution); 1599ca8e40cSJean Delvare lm75_write_value(client, LM75_REG_TEMP[nr], data->temp[nr]); 1609ca8e40cSJean Delvare mutex_unlock(&data->update_lock); 1619ca8e40cSJean Delvare return count; 1628d5d45fbSJean Delvare } 1638d5d45fbSJean Delvare 1649ca8e40cSJean Delvare static SENSOR_DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, 1659ca8e40cSJean Delvare show_temp, set_temp, 1); 1669ca8e40cSJean Delvare static SENSOR_DEVICE_ATTR(temp1_max_hyst, S_IWUSR | S_IRUGO, 1679ca8e40cSJean Delvare show_temp, set_temp, 2); 1689ca8e40cSJean Delvare static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, show_temp, NULL, 0); 1698d5d45fbSJean Delvare 170d663ec49SGuenter Roeck static struct attribute *lm75_attrs[] = { 1719ca8e40cSJean Delvare &sensor_dev_attr_temp1_input.dev_attr.attr, 1729ca8e40cSJean Delvare &sensor_dev_attr_temp1_max.dev_attr.attr, 1739ca8e40cSJean Delvare &sensor_dev_attr_temp1_max_hyst.dev_attr.attr, 174c1685f61SMark M. Hoffman 175c1685f61SMark M. Hoffman NULL 176c1685f61SMark M. Hoffman }; 177d663ec49SGuenter Roeck ATTRIBUTE_GROUPS(lm75); 178c1685f61SMark M. Hoffman 1792251aef6SEduardo Valentin static const struct thermal_zone_of_device_ops lm75_of_thermal_ops = { 1802251aef6SEduardo Valentin .get_temp = lm75_read_temp, 1812251aef6SEduardo Valentin }; 1822251aef6SEduardo Valentin 18301a52397SDavid Brownell /*-----------------------------------------------------------------------*/ 18401a52397SDavid Brownell 1858ff69eebSJean Delvare /* device probe and removal */ 1869ebd3d82SDavid Brownell 1879ebd3d82SDavid Brownell static int 1889ebd3d82SDavid Brownell lm75_probe(struct i2c_client *client, const struct i2c_device_id *id) 1899ebd3d82SDavid Brownell { 190d663ec49SGuenter Roeck struct device *dev = &client->dev; 1919ebd3d82SDavid Brownell struct lm75_data *data; 1929ebd3d82SDavid Brownell int status; 1939ebd3d82SDavid Brownell u8 set_mask, clr_mask; 1949ebd3d82SDavid Brownell int new; 1950cd2c72dSJean Delvare enum lm75_type kind = id->driver_data; 1969ebd3d82SDavid Brownell 1979ebd3d82SDavid Brownell if (!i2c_check_functionality(client->adapter, 1989ebd3d82SDavid Brownell I2C_FUNC_SMBUS_BYTE_DATA | I2C_FUNC_SMBUS_WORD_DATA)) 1999ebd3d82SDavid Brownell return -EIO; 2009ebd3d82SDavid Brownell 201d663ec49SGuenter Roeck data = devm_kzalloc(dev, sizeof(struct lm75_data), GFP_KERNEL); 2029ebd3d82SDavid Brownell if (!data) 2039ebd3d82SDavid Brownell return -ENOMEM; 2049ebd3d82SDavid Brownell 205d663ec49SGuenter Roeck data->client = client; 2069ebd3d82SDavid Brownell i2c_set_clientdata(client, data); 2079ebd3d82SDavid Brownell mutex_init(&data->update_lock); 2089ebd3d82SDavid Brownell 2099ebd3d82SDavid Brownell /* Set to LM75 resolution (9 bits, 1/2 degree C) and range. 2109ebd3d82SDavid Brownell * Then tweak to be more precise when appropriate. 2119ebd3d82SDavid Brownell */ 2129ebd3d82SDavid Brownell set_mask = 0; 2138a5c5cc6SJean Delvare clr_mask = LM75_SHUTDOWN; /* continuous conversions */ 2148a5c5cc6SJean Delvare 2150cd2c72dSJean Delvare switch (kind) { 2168a5c5cc6SJean Delvare case adt75: 2178a5c5cc6SJean Delvare clr_mask |= 1 << 5; /* not one-shot mode */ 2180cd2c72dSJean Delvare data->resolution = 12; 2190cd2c72dSJean Delvare data->sample_time = HZ / 8; 2208a5c5cc6SJean Delvare break; 2218a5c5cc6SJean Delvare case ds1775: 2228a5c5cc6SJean Delvare case ds75: 2238a5c5cc6SJean Delvare case stds75: 2240cd2c72dSJean Delvare clr_mask |= 3 << 5; 2250cd2c72dSJean Delvare set_mask |= 2 << 5; /* 11-bit mode */ 2260cd2c72dSJean Delvare data->resolution = 11; 2270cd2c72dSJean Delvare data->sample_time = HZ; 2280cd2c72dSJean Delvare break; 2293fbc81e3SJean Delvare case ds7505: 2303fbc81e3SJean Delvare set_mask |= 3 << 5; /* 12-bit mode */ 2313fbc81e3SJean Delvare data->resolution = 12; 2323fbc81e3SJean Delvare data->sample_time = HZ / 4; 2333fbc81e3SJean Delvare break; 234c98d6c65SArnaud Ebalard case g751: 2350cd2c72dSJean Delvare case lm75: 2360cd2c72dSJean Delvare case lm75a: 2370cd2c72dSJean Delvare data->resolution = 9; 2380cd2c72dSJean Delvare data->sample_time = HZ / 2; 2390cd2c72dSJean Delvare break; 2400cd2c72dSJean Delvare case max6625: 2410cd2c72dSJean Delvare data->resolution = 9; 2420cd2c72dSJean Delvare data->sample_time = HZ / 4; 2430cd2c72dSJean Delvare break; 2440cd2c72dSJean Delvare case max6626: 2450cd2c72dSJean Delvare data->resolution = 12; 2460cd2c72dSJean Delvare data->resolution_limits = 9; 2470cd2c72dSJean Delvare data->sample_time = HZ / 4; 2480cd2c72dSJean Delvare break; 2490cd2c72dSJean Delvare case tcn75: 2500cd2c72dSJean Delvare data->resolution = 9; 2510cd2c72dSJean Delvare data->sample_time = HZ / 8; 2528a5c5cc6SJean Delvare break; 2538a5c5cc6SJean Delvare case mcp980x: 2540cd2c72dSJean Delvare data->resolution_limits = 9; 2550cd2c72dSJean Delvare /* fall through */ 2568a5c5cc6SJean Delvare case tmp100: 2578a5c5cc6SJean Delvare case tmp101: 2580cd2c72dSJean Delvare set_mask |= 3 << 5; /* 12-bit mode */ 2590cd2c72dSJean Delvare data->resolution = 12; 2600cd2c72dSJean Delvare data->sample_time = HZ; 2610cd2c72dSJean Delvare clr_mask |= 1 << 7; /* not one-shot mode */ 2620cd2c72dSJean Delvare break; 263c83959f8SFrans Klaver case tmp112: 264c83959f8SFrans Klaver set_mask |= 3 << 5; /* 12-bit mode */ 265c83959f8SFrans Klaver clr_mask |= 1 << 7; /* not one-shot mode */ 266c83959f8SFrans Klaver data->resolution = 12; 267c83959f8SFrans Klaver data->sample_time = HZ / 4; 268c83959f8SFrans Klaver break; 2698a5c5cc6SJean Delvare case tmp105: 2708a5c5cc6SJean Delvare case tmp175: 2718a5c5cc6SJean Delvare case tmp275: 2728a5c5cc6SJean Delvare case tmp75: 2730cd2c72dSJean Delvare set_mask |= 3 << 5; /* 12-bit mode */ 2748a5c5cc6SJean Delvare clr_mask |= 1 << 7; /* not one-shot mode */ 2750cd2c72dSJean Delvare data->resolution = 12; 2760cd2c72dSJean Delvare data->sample_time = HZ / 2; 2778a5c5cc6SJean Delvare break; 2788a5c5cc6SJean Delvare } 2799ebd3d82SDavid Brownell 2809ebd3d82SDavid Brownell /* configure as specified */ 2819ebd3d82SDavid Brownell status = lm75_read_value(client, LM75_REG_CONF); 2829ebd3d82SDavid Brownell if (status < 0) { 283d663ec49SGuenter Roeck dev_dbg(dev, "Can't read config? %d\n", status); 28413ac7a01SGuenter Roeck return status; 2859ebd3d82SDavid Brownell } 2869ebd3d82SDavid Brownell data->orig_conf = status; 2879ebd3d82SDavid Brownell new = status & ~clr_mask; 2889ebd3d82SDavid Brownell new |= set_mask; 2899ebd3d82SDavid Brownell if (status != new) 2909ebd3d82SDavid Brownell lm75_write_value(client, LM75_REG_CONF, new); 291d663ec49SGuenter Roeck dev_dbg(dev, "Config %02x\n", new); 2929ebd3d82SDavid Brownell 293d663ec49SGuenter Roeck data->hwmon_dev = hwmon_device_register_with_groups(dev, client->name, 294d663ec49SGuenter Roeck data, lm75_groups); 295d663ec49SGuenter Roeck if (IS_ERR(data->hwmon_dev)) 296d663ec49SGuenter Roeck return PTR_ERR(data->hwmon_dev); 2979ebd3d82SDavid Brownell 2982251aef6SEduardo Valentin data->tz = thermal_zone_of_sensor_register(data->hwmon_dev, 0, 299d663ec49SGuenter Roeck data->hwmon_dev, 3002251aef6SEduardo Valentin &lm75_of_thermal_ops); 30122e73183SEduardo Valentin if (IS_ERR(data->tz)) 30222e73183SEduardo Valentin data->tz = NULL; 30322e73183SEduardo Valentin 304d663ec49SGuenter Roeck dev_info(dev, "%s: sensor '%s'\n", 305739cf3a2SKay Sievers dev_name(data->hwmon_dev), client->name); 3069ebd3d82SDavid Brownell 3079ebd3d82SDavid Brownell return 0; 3089ebd3d82SDavid Brownell } 3099ebd3d82SDavid Brownell 3109ebd3d82SDavid Brownell static int lm75_remove(struct i2c_client *client) 3119ebd3d82SDavid Brownell { 3129ebd3d82SDavid Brownell struct lm75_data *data = i2c_get_clientdata(client); 3139ebd3d82SDavid Brownell 314d663ec49SGuenter Roeck thermal_zone_of_sensor_unregister(data->hwmon_dev, data->tz); 3159ebd3d82SDavid Brownell hwmon_device_unregister(data->hwmon_dev); 3169ebd3d82SDavid Brownell lm75_write_value(client, LM75_REG_CONF, data->orig_conf); 3179ebd3d82SDavid Brownell return 0; 3189ebd3d82SDavid Brownell } 3199ebd3d82SDavid Brownell 3209ebd3d82SDavid Brownell static const struct i2c_device_id lm75_ids[] = { 321e96f9d89SMichael Hennerich { "adt75", adt75, }, 3229ebd3d82SDavid Brownell { "ds1775", ds1775, }, 3239ebd3d82SDavid Brownell { "ds75", ds75, }, 3243fbc81e3SJean Delvare { "ds7505", ds7505, }, 325c98d6c65SArnaud Ebalard { "g751", g751, }, 3269ebd3d82SDavid Brownell { "lm75", lm75, }, 3279ebd3d82SDavid Brownell { "lm75a", lm75a, }, 3289ebd3d82SDavid Brownell { "max6625", max6625, }, 3299ebd3d82SDavid Brownell { "max6626", max6626, }, 3309ebd3d82SDavid Brownell { "mcp980x", mcp980x, }, 3319ebd3d82SDavid Brownell { "stds75", stds75, }, 3329ebd3d82SDavid Brownell { "tcn75", tcn75, }, 3339ebd3d82SDavid Brownell { "tmp100", tmp100, }, 3349ebd3d82SDavid Brownell { "tmp101", tmp101, }, 3356d034059SShubhrajyoti Datta { "tmp105", tmp105, }, 336c83959f8SFrans Klaver { "tmp112", tmp112, }, 3379ebd3d82SDavid Brownell { "tmp175", tmp175, }, 3389ebd3d82SDavid Brownell { "tmp275", tmp275, }, 3399ebd3d82SDavid Brownell { "tmp75", tmp75, }, 3409ebd3d82SDavid Brownell { /* LIST END */ } 3419ebd3d82SDavid Brownell }; 3429ebd3d82SDavid Brownell MODULE_DEVICE_TABLE(i2c, lm75_ids); 3439ebd3d82SDavid Brownell 34405e82fe4SLen Sorensen #define LM75A_ID 0xA1 34505e82fe4SLen Sorensen 3468ff69eebSJean Delvare /* Return 0 if detection is successful, -ENODEV otherwise */ 347310ec792SJean Delvare static int lm75_detect(struct i2c_client *new_client, 3488ff69eebSJean Delvare struct i2c_board_info *info) 3498d5d45fbSJean Delvare { 3508ff69eebSJean Delvare struct i2c_adapter *adapter = new_client->adapter; 3518d5d45fbSJean Delvare int i; 352e76f67b5SJean Delvare int conf, hyst, os; 35305e82fe4SLen Sorensen bool is_lm75a = 0; 3548d5d45fbSJean Delvare 3558d5d45fbSJean Delvare if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA | 3568d5d45fbSJean Delvare I2C_FUNC_SMBUS_WORD_DATA)) 3578ff69eebSJean Delvare return -ENODEV; 3588d5d45fbSJean Delvare 359426343efSJean Delvare /* 360426343efSJean Delvare * Now, we do the remaining detection. There is no identification- 361426343efSJean Delvare * dedicated register so we have to rely on several tricks: 362426343efSJean Delvare * unused bits, registers cycling over 8-address boundaries, 363426343efSJean Delvare * addresses 0x04-0x07 returning the last read value. 364426343efSJean Delvare * The cycling+unused addresses combination is not tested, 365426343efSJean Delvare * since it would significantly slow the detection down and would 366426343efSJean Delvare * hardly add any value. 367426343efSJean Delvare * 368426343efSJean Delvare * The National Semiconductor LM75A is different than earlier 369426343efSJean Delvare * LM75s. It has an ID byte of 0xaX (where X is the chip 370426343efSJean Delvare * revision, with 1 being the only revision in existence) in 371426343efSJean Delvare * register 7, and unused registers return 0xff rather than the 372426343efSJean Delvare * last read value. 373426343efSJean Delvare * 374426343efSJean Delvare * Note that this function only detects the original National 375426343efSJean Delvare * Semiconductor LM75 and the LM75A. Clones from other vendors 376426343efSJean Delvare * aren't detected, on purpose, because they are typically never 377426343efSJean Delvare * found on PC hardware. They are found on embedded designs where 378426343efSJean Delvare * they can be instantiated explicitly so detection is not needed. 379426343efSJean Delvare * The absence of identification registers on all these clones 380426343efSJean Delvare * would make their exhaustive detection very difficult and weak, 381426343efSJean Delvare * and odds are that the driver would bind to unsupported devices. 382426343efSJean Delvare */ 38305e82fe4SLen Sorensen 384e76f67b5SJean Delvare /* Unused bits */ 3858d5d45fbSJean Delvare conf = i2c_smbus_read_byte_data(new_client, 1); 386e76f67b5SJean Delvare if (conf & 0xe0) 387e76f67b5SJean Delvare return -ENODEV; 38805e82fe4SLen Sorensen 38905e82fe4SLen Sorensen /* First check for LM75A */ 39005e82fe4SLen Sorensen if (i2c_smbus_read_byte_data(new_client, 7) == LM75A_ID) { 39105e82fe4SLen Sorensen /* LM75A returns 0xff on unused registers so 39205e82fe4SLen Sorensen just to be sure we check for that too. */ 39305e82fe4SLen Sorensen if (i2c_smbus_read_byte_data(new_client, 4) != 0xff 39405e82fe4SLen Sorensen || i2c_smbus_read_byte_data(new_client, 5) != 0xff 39505e82fe4SLen Sorensen || i2c_smbus_read_byte_data(new_client, 6) != 0xff) 39605e82fe4SLen Sorensen return -ENODEV; 39705e82fe4SLen Sorensen is_lm75a = 1; 398e76f67b5SJean Delvare hyst = i2c_smbus_read_byte_data(new_client, 2); 399e76f67b5SJean Delvare os = i2c_smbus_read_byte_data(new_client, 3); 40005e82fe4SLen Sorensen } else { /* Traditional style LM75 detection */ 40105e82fe4SLen Sorensen /* Unused addresses */ 402e76f67b5SJean Delvare hyst = i2c_smbus_read_byte_data(new_client, 2); 403e76f67b5SJean Delvare if (i2c_smbus_read_byte_data(new_client, 4) != hyst 404e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, 5) != hyst 405e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, 6) != hyst 406e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, 7) != hyst) 4078ff69eebSJean Delvare return -ENODEV; 408e76f67b5SJean Delvare os = i2c_smbus_read_byte_data(new_client, 3); 409e76f67b5SJean Delvare if (i2c_smbus_read_byte_data(new_client, 4) != os 410e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, 5) != os 411e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, 6) != os 412e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, 7) != os) 4138ff69eebSJean Delvare return -ENODEV; 41405e82fe4SLen Sorensen } 4158d5d45fbSJean Delvare 4168d5d45fbSJean Delvare /* Addresses cycling */ 417e76f67b5SJean Delvare for (i = 8; i <= 248; i += 40) { 4188d5d45fbSJean Delvare if (i2c_smbus_read_byte_data(new_client, i + 1) != conf 419e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, i + 2) != hyst 420e76f67b5SJean Delvare || i2c_smbus_read_byte_data(new_client, i + 3) != os) 4218ff69eebSJean Delvare return -ENODEV; 42205e82fe4SLen Sorensen if (is_lm75a && i2c_smbus_read_byte_data(new_client, i + 7) 42305e82fe4SLen Sorensen != LM75A_ID) 42405e82fe4SLen Sorensen return -ENODEV; 4258d5d45fbSJean Delvare } 4268d5d45fbSJean Delvare 42705e82fe4SLen Sorensen strlcpy(info->type, is_lm75a ? "lm75a" : "lm75", I2C_NAME_SIZE); 4288d5d45fbSJean Delvare 4298d5d45fbSJean Delvare return 0; 4308d5d45fbSJean Delvare } 4318d5d45fbSJean Delvare 4329914518eSShubhrajyoti Datta #ifdef CONFIG_PM 4339914518eSShubhrajyoti Datta static int lm75_suspend(struct device *dev) 4349914518eSShubhrajyoti Datta { 4359914518eSShubhrajyoti Datta int status; 4369914518eSShubhrajyoti Datta struct i2c_client *client = to_i2c_client(dev); 4379914518eSShubhrajyoti Datta status = lm75_read_value(client, LM75_REG_CONF); 4389914518eSShubhrajyoti Datta if (status < 0) { 4399914518eSShubhrajyoti Datta dev_dbg(&client->dev, "Can't read config? %d\n", status); 4409914518eSShubhrajyoti Datta return status; 4419914518eSShubhrajyoti Datta } 4429914518eSShubhrajyoti Datta status = status | LM75_SHUTDOWN; 4439914518eSShubhrajyoti Datta lm75_write_value(client, LM75_REG_CONF, status); 4449914518eSShubhrajyoti Datta return 0; 4459914518eSShubhrajyoti Datta } 4469914518eSShubhrajyoti Datta 4479914518eSShubhrajyoti Datta static int lm75_resume(struct device *dev) 4489914518eSShubhrajyoti Datta { 4499914518eSShubhrajyoti Datta int status; 4509914518eSShubhrajyoti Datta struct i2c_client *client = to_i2c_client(dev); 4519914518eSShubhrajyoti Datta status = lm75_read_value(client, LM75_REG_CONF); 4529914518eSShubhrajyoti Datta if (status < 0) { 4539914518eSShubhrajyoti Datta dev_dbg(&client->dev, "Can't read config? %d\n", status); 4549914518eSShubhrajyoti Datta return status; 4559914518eSShubhrajyoti Datta } 4569914518eSShubhrajyoti Datta status = status & ~LM75_SHUTDOWN; 4579914518eSShubhrajyoti Datta lm75_write_value(client, LM75_REG_CONF, status); 4589914518eSShubhrajyoti Datta return 0; 4599914518eSShubhrajyoti Datta } 4609914518eSShubhrajyoti Datta 4619914518eSShubhrajyoti Datta static const struct dev_pm_ops lm75_dev_pm_ops = { 4629914518eSShubhrajyoti Datta .suspend = lm75_suspend, 4639914518eSShubhrajyoti Datta .resume = lm75_resume, 4649914518eSShubhrajyoti Datta }; 4659914518eSShubhrajyoti Datta #define LM75_DEV_PM_OPS (&lm75_dev_pm_ops) 4669914518eSShubhrajyoti Datta #else 4679914518eSShubhrajyoti Datta #define LM75_DEV_PM_OPS NULL 4689914518eSShubhrajyoti Datta #endif /* CONFIG_PM */ 4699914518eSShubhrajyoti Datta 4708ff69eebSJean Delvare static struct i2c_driver lm75_driver = { 4718ff69eebSJean Delvare .class = I2C_CLASS_HWMON, 47201a52397SDavid Brownell .driver = { 4738ff69eebSJean Delvare .name = "lm75", 4749914518eSShubhrajyoti Datta .pm = LM75_DEV_PM_OPS, 47501a52397SDavid Brownell }, 4768ff69eebSJean Delvare .probe = lm75_probe, 4778ff69eebSJean Delvare .remove = lm75_remove, 4788ff69eebSJean Delvare .id_table = lm75_ids, 4798ff69eebSJean Delvare .detect = lm75_detect, 480c3813d6aSJean Delvare .address_list = normal_i2c, 48101a52397SDavid Brownell }; 48201a52397SDavid Brownell 48301a52397SDavid Brownell /*-----------------------------------------------------------------------*/ 48401a52397SDavid Brownell 48501a52397SDavid Brownell /* register access */ 48601a52397SDavid Brownell 487caaa0f36SShubhrajyoti D /* 488caaa0f36SShubhrajyoti D * All registers are word-sized, except for the configuration register. 489caaa0f36SShubhrajyoti D * LM75 uses a high-byte first convention, which is exactly opposite to 490caaa0f36SShubhrajyoti D * the SMBus standard. 491caaa0f36SShubhrajyoti D */ 4928d5d45fbSJean Delvare static int lm75_read_value(struct i2c_client *client, u8 reg) 4938d5d45fbSJean Delvare { 4948d5d45fbSJean Delvare if (reg == LM75_REG_CONF) 4958d5d45fbSJean Delvare return i2c_smbus_read_byte_data(client, reg); 49690f4102cSJean Delvare else 49790f4102cSJean Delvare return i2c_smbus_read_word_swapped(client, reg); 4988d5d45fbSJean Delvare } 4998d5d45fbSJean Delvare 5008d5d45fbSJean Delvare static int lm75_write_value(struct i2c_client *client, u8 reg, u16 value) 5018d5d45fbSJean Delvare { 5028d5d45fbSJean Delvare if (reg == LM75_REG_CONF) 5038d5d45fbSJean Delvare return i2c_smbus_write_byte_data(client, reg, value); 5048d5d45fbSJean Delvare else 50590f4102cSJean Delvare return i2c_smbus_write_word_swapped(client, reg, value); 5068d5d45fbSJean Delvare } 5078d5d45fbSJean Delvare 5088d5d45fbSJean Delvare static struct lm75_data *lm75_update_device(struct device *dev) 5098d5d45fbSJean Delvare { 510d663ec49SGuenter Roeck struct lm75_data *data = dev_get_drvdata(dev); 511d663ec49SGuenter Roeck struct i2c_client *client = data->client; 5121f962f36SFrans Meulenbroeks struct lm75_data *ret = data; 5138d5d45fbSJean Delvare 5149a61bf63SIngo Molnar mutex_lock(&data->update_lock); 5158d5d45fbSJean Delvare 51687d0621aSJean Delvare if (time_after(jiffies, data->last_updated + data->sample_time) 5178d5d45fbSJean Delvare || !data->valid) { 5189ca8e40cSJean Delvare int i; 5198d5d45fbSJean Delvare dev_dbg(&client->dev, "Starting lm75 update\n"); 5208d5d45fbSJean Delvare 521bcccc3a2SDavid Brownell for (i = 0; i < ARRAY_SIZE(data->temp); i++) { 522bcccc3a2SDavid Brownell int status; 523bcccc3a2SDavid Brownell 524bcccc3a2SDavid Brownell status = lm75_read_value(client, LM75_REG_TEMP[i]); 5251f962f36SFrans Meulenbroeks if (unlikely(status < 0)) { 5261f962f36SFrans Meulenbroeks dev_dbg(dev, 5271f962f36SFrans Meulenbroeks "LM75: Failed to read value: reg %d, error %d\n", 528bcccc3a2SDavid Brownell LM75_REG_TEMP[i], status); 5291f962f36SFrans Meulenbroeks ret = ERR_PTR(status); 5301f962f36SFrans Meulenbroeks data->valid = 0; 5311f962f36SFrans Meulenbroeks goto abort; 5321f962f36SFrans Meulenbroeks } 533bcccc3a2SDavid Brownell data->temp[i] = status; 534bcccc3a2SDavid Brownell } 5358d5d45fbSJean Delvare data->last_updated = jiffies; 5368d5d45fbSJean Delvare data->valid = 1; 5378d5d45fbSJean Delvare } 5388d5d45fbSJean Delvare 5391f962f36SFrans Meulenbroeks abort: 5409a61bf63SIngo Molnar mutex_unlock(&data->update_lock); 5411f962f36SFrans Meulenbroeks return ret; 5428d5d45fbSJean Delvare } 5438d5d45fbSJean Delvare 544f0967eeaSAxel Lin module_i2c_driver(lm75_driver); 5458d5d45fbSJean Delvare 5468d5d45fbSJean Delvare MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>"); 5478d5d45fbSJean Delvare MODULE_DESCRIPTION("LM75 driver"); 5488d5d45fbSJean Delvare MODULE_LICENSE("GPL"); 549