.. | .. |
---|
| 1 | +// SPDX-License-Identifier: GPL-2.0 |
---|
1 | 2 | /* |
---|
2 | 3 | * adm1029.c - Part of lm_sensors, Linux kernel modules for hardware monitoring |
---|
3 | 4 | * |
---|
.. | .. |
---|
9 | 10 | * Very rare chip please let me know if you use it |
---|
10 | 11 | * |
---|
11 | 12 | * http://www.analog.com/UploadedFiles/Data_Sheets/ADM1029.pdf |
---|
12 | | - * |
---|
13 | | - * |
---|
14 | | - * This program is free software; you can redistribute it and/or modify |
---|
15 | | - * it under the terms of the GNU General Public License as published by |
---|
16 | | - * the Free Software Foundation version 2 of the License |
---|
17 | | - * |
---|
18 | | - * This program is distributed in the hope that it will be useful, |
---|
19 | | - * but WITHOUT ANY WARRANTY; without even the implied warranty of |
---|
20 | | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
---|
21 | | - * GNU General Public License for more details. |
---|
22 | | - * |
---|
23 | | - * You should have received a copy of the GNU General Public License |
---|
24 | | - * along with this program; if not, write to the Free Software |
---|
25 | | - * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. |
---|
26 | 13 | */ |
---|
27 | 14 | |
---|
28 | 15 | #include <linux/module.h> |
---|
.. | .. |
---|
111 | 98 | |
---|
112 | 99 | struct adm1029_data { |
---|
113 | 100 | struct i2c_client *client; |
---|
114 | | - struct mutex update_lock; |
---|
| 101 | + struct mutex update_lock; /* protect register access */ |
---|
115 | 102 | char valid; /* zero until following fields are valid */ |
---|
116 | 103 | unsigned long last_updated; /* in jiffies */ |
---|
117 | 104 | |
---|
.. | .. |
---|
134 | 121 | * Use the "cache" Luke, don't recheck values |
---|
135 | 122 | * if there are already checked not a long time later |
---|
136 | 123 | */ |
---|
137 | | - if (time_after(jiffies, data->last_updated + HZ * 2) |
---|
138 | | - || !data->valid) { |
---|
| 124 | + if (time_after(jiffies, data->last_updated + HZ * 2) || !data->valid) { |
---|
139 | 125 | int nr; |
---|
140 | 126 | |
---|
141 | 127 | dev_dbg(&client->dev, "Updating adm1029 data\n"); |
---|
.. | .. |
---|
170 | 156 | */ |
---|
171 | 157 | |
---|
172 | 158 | static ssize_t |
---|
173 | | -show_temp(struct device *dev, struct device_attribute *devattr, char *buf) |
---|
| 159 | +temp_show(struct device *dev, struct device_attribute *devattr, char *buf) |
---|
174 | 160 | { |
---|
175 | 161 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); |
---|
176 | 162 | struct adm1029_data *data = adm1029_update_device(dev); |
---|
| 163 | + |
---|
177 | 164 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp[attr->index])); |
---|
178 | 165 | } |
---|
179 | 166 | |
---|
180 | 167 | static ssize_t |
---|
181 | | -show_fan(struct device *dev, struct device_attribute *devattr, char *buf) |
---|
| 168 | +fan_show(struct device *dev, struct device_attribute *devattr, char *buf) |
---|
182 | 169 | { |
---|
183 | 170 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); |
---|
184 | 171 | struct adm1029_data *data = adm1029_update_device(dev); |
---|
185 | 172 | u16 val; |
---|
186 | | - if (data->fan[attr->index] == 0 |
---|
187 | | - || (data->fan_div[attr->index] & 0xC0) == 0 |
---|
188 | | - || data->fan[attr->index] == 255) { |
---|
| 173 | + |
---|
| 174 | + if (data->fan[attr->index] == 0 || |
---|
| 175 | + (data->fan_div[attr->index] & 0xC0) == 0 || |
---|
| 176 | + data->fan[attr->index] == 255) { |
---|
189 | 177 | return sprintf(buf, "0\n"); |
---|
190 | 178 | } |
---|
191 | 179 | |
---|
.. | .. |
---|
195 | 183 | } |
---|
196 | 184 | |
---|
197 | 185 | static ssize_t |
---|
198 | | -show_fan_div(struct device *dev, struct device_attribute *devattr, char *buf) |
---|
| 186 | +fan_div_show(struct device *dev, struct device_attribute *devattr, char *buf) |
---|
199 | 187 | { |
---|
200 | 188 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); |
---|
201 | 189 | struct adm1029_data *data = adm1029_update_device(dev); |
---|
| 190 | + |
---|
202 | 191 | if ((data->fan_div[attr->index] & 0xC0) == 0) |
---|
203 | 192 | return sprintf(buf, "0\n"); |
---|
204 | 193 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->fan_div[attr->index])); |
---|
205 | 194 | } |
---|
206 | 195 | |
---|
207 | | -static ssize_t set_fan_div(struct device *dev, |
---|
208 | | - struct device_attribute *devattr, const char *buf, size_t count) |
---|
| 196 | +static ssize_t fan_div_store(struct device *dev, |
---|
| 197 | + struct device_attribute *devattr, |
---|
| 198 | + const char *buf, size_t count) |
---|
209 | 199 | { |
---|
210 | 200 | struct adm1029_data *data = dev_get_drvdata(dev); |
---|
211 | 201 | struct i2c_client *client = data->client; |
---|
.. | .. |
---|
213 | 203 | u8 reg; |
---|
214 | 204 | long val; |
---|
215 | 205 | int ret = kstrtol(buf, 10, &val); |
---|
| 206 | + |
---|
216 | 207 | if (ret < 0) |
---|
217 | 208 | return ret; |
---|
218 | 209 | |
---|
.. | .. |
---|
253 | 244 | return count; |
---|
254 | 245 | } |
---|
255 | 246 | |
---|
256 | | -/* |
---|
257 | | - * Access rights on sysfs. S_IRUGO: Is Readable by User, Group and Others |
---|
258 | | - * S_IWUSR: Is Writable by User. |
---|
259 | | - */ |
---|
260 | | -static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, show_temp, NULL, 0); |
---|
261 | | -static SENSOR_DEVICE_ATTR(temp2_input, S_IRUGO, show_temp, NULL, 1); |
---|
262 | | -static SENSOR_DEVICE_ATTR(temp3_input, S_IRUGO, show_temp, NULL, 2); |
---|
| 247 | +/* Access rights on sysfs. */ |
---|
| 248 | +static SENSOR_DEVICE_ATTR_RO(temp1_input, temp, 0); |
---|
| 249 | +static SENSOR_DEVICE_ATTR_RO(temp2_input, temp, 1); |
---|
| 250 | +static SENSOR_DEVICE_ATTR_RO(temp3_input, temp, 2); |
---|
263 | 251 | |
---|
264 | | -static SENSOR_DEVICE_ATTR(temp1_max, S_IRUGO, show_temp, NULL, 3); |
---|
265 | | -static SENSOR_DEVICE_ATTR(temp2_max, S_IRUGO, show_temp, NULL, 4); |
---|
266 | | -static SENSOR_DEVICE_ATTR(temp3_max, S_IRUGO, show_temp, NULL, 5); |
---|
| 252 | +static SENSOR_DEVICE_ATTR_RO(temp1_max, temp, 3); |
---|
| 253 | +static SENSOR_DEVICE_ATTR_RO(temp2_max, temp, 4); |
---|
| 254 | +static SENSOR_DEVICE_ATTR_RO(temp3_max, temp, 5); |
---|
267 | 255 | |
---|
268 | | -static SENSOR_DEVICE_ATTR(temp1_min, S_IRUGO, show_temp, NULL, 6); |
---|
269 | | -static SENSOR_DEVICE_ATTR(temp2_min, S_IRUGO, show_temp, NULL, 7); |
---|
270 | | -static SENSOR_DEVICE_ATTR(temp3_min, S_IRUGO, show_temp, NULL, 8); |
---|
| 256 | +static SENSOR_DEVICE_ATTR_RO(temp1_min, temp, 6); |
---|
| 257 | +static SENSOR_DEVICE_ATTR_RO(temp2_min, temp, 7); |
---|
| 258 | +static SENSOR_DEVICE_ATTR_RO(temp3_min, temp, 8); |
---|
271 | 259 | |
---|
272 | | -static SENSOR_DEVICE_ATTR(fan1_input, S_IRUGO, show_fan, NULL, 0); |
---|
273 | | -static SENSOR_DEVICE_ATTR(fan2_input, S_IRUGO, show_fan, NULL, 1); |
---|
| 260 | +static SENSOR_DEVICE_ATTR_RO(fan1_input, fan, 0); |
---|
| 261 | +static SENSOR_DEVICE_ATTR_RO(fan2_input, fan, 1); |
---|
274 | 262 | |
---|
275 | | -static SENSOR_DEVICE_ATTR(fan1_min, S_IRUGO, show_fan, NULL, 2); |
---|
276 | | -static SENSOR_DEVICE_ATTR(fan2_min, S_IRUGO, show_fan, NULL, 3); |
---|
| 263 | +static SENSOR_DEVICE_ATTR_RO(fan1_min, fan, 2); |
---|
| 264 | +static SENSOR_DEVICE_ATTR_RO(fan2_min, fan, 3); |
---|
277 | 265 | |
---|
278 | | -static SENSOR_DEVICE_ATTR(fan1_div, S_IRUGO | S_IWUSR, |
---|
279 | | - show_fan_div, set_fan_div, 0); |
---|
280 | | -static SENSOR_DEVICE_ATTR(fan2_div, S_IRUGO | S_IWUSR, |
---|
281 | | - show_fan_div, set_fan_div, 1); |
---|
| 266 | +static SENSOR_DEVICE_ATTR_RW(fan1_div, fan_div, 0); |
---|
| 267 | +static SENSOR_DEVICE_ATTR_RW(fan2_div, fan_div, 1); |
---|
282 | 268 | |
---|
283 | 269 | static struct attribute *adm1029_attrs[] = { |
---|
284 | 270 | &sensor_dev_attr_temp1_input.dev_attr.attr, |
---|
.. | .. |
---|
327 | 313 | temp_devices_installed = i2c_smbus_read_byte_data(client, |
---|
328 | 314 | ADM1029_REG_TEMP_DEVICES_INSTALLED); |
---|
329 | 315 | nb_fan_support = i2c_smbus_read_byte_data(client, |
---|
330 | | - ADM1029_REG_NB_FAN_SUPPORT); |
---|
| 316 | + ADM1029_REG_NB_FAN_SUPPORT); |
---|
331 | 317 | /* 0x41 is Analog Devices */ |
---|
332 | | - if (man_id != 0x41 || (temp_devices_installed & 0xf9) != 0x01 |
---|
333 | | - || nb_fan_support != 0x03) |
---|
| 318 | + if (man_id != 0x41 || (temp_devices_installed & 0xf9) != 0x01 || |
---|
| 319 | + nb_fan_support != 0x03) |
---|
334 | 320 | return -ENODEV; |
---|
335 | 321 | |
---|
336 | 322 | if ((chip_id & 0xF0) != 0x00) { |
---|
.. | .. |
---|
366 | 352 | return 1; |
---|
367 | 353 | } |
---|
368 | 354 | |
---|
369 | | -static int adm1029_probe(struct i2c_client *client, |
---|
370 | | - const struct i2c_device_id *id) |
---|
| 355 | +static int adm1029_probe(struct i2c_client *client) |
---|
371 | 356 | { |
---|
372 | 357 | struct device *dev = &client->dev; |
---|
373 | 358 | struct adm1029_data *data; |
---|
.. | .. |
---|
404 | 389 | .driver = { |
---|
405 | 390 | .name = "adm1029", |
---|
406 | 391 | }, |
---|
407 | | - .probe = adm1029_probe, |
---|
| 392 | + .probe_new = adm1029_probe, |
---|
408 | 393 | .id_table = adm1029_id, |
---|
409 | 394 | .detect = adm1029_detect, |
---|
410 | 395 | .address_list = normal_i2c, |
---|