hwmon: (f71882fg) Add support for the F81865F
[linux-2.6/linux-acpi-2.6/ibm-acpi-2.6.git] / drivers / hwmon / f71882fg.c
blobaa8cf5d5c22e5377562e27b8304cef17677018e5
1 /***************************************************************************
2 * Copyright (C) 2006 by Hans Edgington <hans@edgington.nl> *
3 * Copyright (C) 2007-2011 Hans de Goede <hdegoede@redhat.com> *
4 * *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
9 * *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
14 * *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
21 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
23 #include <linux/module.h>
24 #include <linux/init.h>
25 #include <linux/slab.h>
26 #include <linux/jiffies.h>
27 #include <linux/platform_device.h>
28 #include <linux/hwmon.h>
29 #include <linux/hwmon-sysfs.h>
30 #include <linux/err.h>
31 #include <linux/mutex.h>
32 #include <linux/io.h>
33 #include <linux/acpi.h>
35 #define DRVNAME "f71882fg"
37 #define SIO_F71858FG_LD_HWM 0x02 /* Hardware monitor logical device */
38 #define SIO_F71882FG_LD_HWM 0x04 /* Hardware monitor logical device */
39 #define SIO_UNLOCK_KEY 0x87 /* Key to enable Super-I/O */
40 #define SIO_LOCK_KEY 0xAA /* Key to disable Super-I/O */
42 #define SIO_REG_LDSEL 0x07 /* Logical device select */
43 #define SIO_REG_DEVID 0x20 /* Device ID (2 bytes) */
44 #define SIO_REG_DEVREV 0x22 /* Device revision */
45 #define SIO_REG_MANID 0x23 /* Fintek ID (2 bytes) */
46 #define SIO_REG_ENABLE 0x30 /* Logical device enable */
47 #define SIO_REG_ADDR 0x60 /* Logical device address (2 bytes) */
49 #define SIO_FINTEK_ID 0x1934 /* Manufacturers ID */
50 #define SIO_F71808E_ID 0x0901 /* Chipset ID */
51 #define SIO_F71858_ID 0x0507 /* Chipset ID */
52 #define SIO_F71862_ID 0x0601 /* Chipset ID */
53 #define SIO_F71869_ID 0x0814 /* Chipset ID */
54 #define SIO_F71882_ID 0x0541 /* Chipset ID */
55 #define SIO_F71889_ID 0x0723 /* Chipset ID */
56 #define SIO_F71889E_ID 0x0909 /* Chipset ID */
57 #define SIO_F8000_ID 0x0581 /* Chipset ID */
58 #define SIO_F81865_ID 0x0704 /* Chipset ID */
60 #define REGION_LENGTH 8
61 #define ADDR_REG_OFFSET 5
62 #define DATA_REG_OFFSET 6
64 #define F71882FG_REG_IN_STATUS 0x12 /* f7188x only */
65 #define F71882FG_REG_IN_BEEP 0x13 /* f7188x only */
66 #define F71882FG_REG_IN(nr) (0x20 + (nr))
67 #define F71882FG_REG_IN1_HIGH 0x32 /* f7188x only */
69 #define F71882FG_REG_FAN(nr) (0xA0 + (16 * (nr)))
70 #define F71882FG_REG_FAN_TARGET(nr) (0xA2 + (16 * (nr)))
71 #define F71882FG_REG_FAN_FULL_SPEED(nr) (0xA4 + (16 * (nr)))
72 #define F71882FG_REG_FAN_STATUS 0x92
73 #define F71882FG_REG_FAN_BEEP 0x93
75 #define F71882FG_REG_TEMP(nr) (0x70 + 2 * (nr))
76 #define F71882FG_REG_TEMP_OVT(nr) (0x80 + 2 * (nr))
77 #define F71882FG_REG_TEMP_HIGH(nr) (0x81 + 2 * (nr))
78 #define F71882FG_REG_TEMP_STATUS 0x62
79 #define F71882FG_REG_TEMP_BEEP 0x63
80 #define F71882FG_REG_TEMP_CONFIG 0x69
81 #define F71882FG_REG_TEMP_HYST(nr) (0x6C + (nr))
82 #define F71882FG_REG_TEMP_TYPE 0x6B
83 #define F71882FG_REG_TEMP_DIODE_OPEN 0x6F
85 #define F71882FG_REG_PWM(nr) (0xA3 + (16 * (nr)))
86 #define F71882FG_REG_PWM_TYPE 0x94
87 #define F71882FG_REG_PWM_ENABLE 0x96
89 #define F71882FG_REG_FAN_HYST(nr) (0x98 + (nr))
91 #define F71882FG_REG_FAN_FAULT_T 0x9F
92 #define F71882FG_FAN_NEG_TEMP_EN 0x20
93 #define F71882FG_FAN_PROG_SEL 0x80
95 #define F71882FG_REG_POINT_PWM(pwm, point) (0xAA + (point) + (16 * (pwm)))
96 #define F71882FG_REG_POINT_TEMP(pwm, point) (0xA6 + (point) + (16 * (pwm)))
97 #define F71882FG_REG_POINT_MAPPING(nr) (0xAF + 16 * (nr))
99 #define F71882FG_REG_START 0x01
101 #define F71882FG_MAX_INS 9
103 #define FAN_MIN_DETECT 366 /* Lowest detectable fanspeed */
105 static unsigned short force_id;
106 module_param(force_id, ushort, 0);
107 MODULE_PARM_DESC(force_id, "Override the detected device ID");
109 enum chips { f71808e, f71858fg, f71862fg, f71869, f71882fg, f71889fg,
110 f71889ed, f8000, f81865f };
112 static const char *f71882fg_names[] = {
113 "f71808e",
114 "f71858fg",
115 "f71862fg",
116 "f71869", /* Both f71869f and f71869e, reg. compatible and same id */
117 "f71882fg",
118 "f71889fg", /* f81801u too, same id */
119 "f71889ed",
120 "f8000",
121 "f81865f",
124 static const char f71882fg_has_in[][F71882FG_MAX_INS] = {
125 [f71808e] = { 1, 1, 1, 1, 1, 1, 0, 1, 1 },
126 [f71858fg] = { 1, 1, 1, 0, 0, 0, 0, 0, 0 },
127 [f71862fg] = { 1, 1, 1, 1, 1, 1, 1, 1, 1 },
128 [f71869] = { 1, 1, 1, 1, 1, 1, 1, 1, 1 },
129 [f71882fg] = { 1, 1, 1, 1, 1, 1, 1, 1, 1 },
130 [f71889fg] = { 1, 1, 1, 1, 1, 1, 1, 1, 1 },
131 [f71889ed] = { 1, 1, 1, 1, 1, 1, 1, 1, 1 },
132 [f8000] = { 1, 1, 1, 0, 0, 0, 0, 0, 0 },
133 [f81865f] = { 1, 1, 1, 1, 1, 1, 1, 0, 0 },
136 static const char f71882fg_has_in1_alarm[] = {
137 [f71808e] = 0,
138 [f71858fg] = 0,
139 [f71862fg] = 0,
140 [f71869] = 0,
141 [f71882fg] = 1,
142 [f71889fg] = 1,
143 [f71889ed] = 1,
144 [f8000] = 0,
145 [f81865f] = 1,
148 static const char f71882fg_has_beep[] = {
149 [f71808e] = 0,
150 [f71858fg] = 0,
151 [f71862fg] = 1,
152 [f71869] = 1,
153 [f71882fg] = 1,
154 [f71889fg] = 1,
155 [f71889ed] = 1,
156 [f8000] = 0,
157 [f81865f] = 1,
160 static const char f71882fg_nr_fans[] = {
161 [f71808e] = 3,
162 [f71858fg] = 3,
163 [f71862fg] = 3,
164 [f71869] = 3,
165 [f71882fg] = 4,
166 [f71889fg] = 3,
167 [f71889ed] = 3,
168 [f8000] = 3,
169 [f81865f] = 2,
172 static const char f71882fg_nr_temps[] = {
173 [f71808e] = 2,
174 [f71858fg] = 3,
175 [f71862fg] = 3,
176 [f71869] = 3,
177 [f71882fg] = 3,
178 [f71889fg] = 3,
179 [f71889ed] = 3,
180 [f8000] = 3,
181 [f81865f] = 2,
184 static struct platform_device *f71882fg_pdev;
186 /* Super-I/O Function prototypes */
187 static inline int superio_inb(int base, int reg);
188 static inline int superio_inw(int base, int reg);
189 static inline int superio_enter(int base);
190 static inline void superio_select(int base, int ld);
191 static inline void superio_exit(int base);
193 struct f71882fg_sio_data {
194 enum chips type;
197 struct f71882fg_data {
198 unsigned short addr;
199 enum chips type;
200 struct device *hwmon_dev;
202 struct mutex update_lock;
203 int temp_start; /* temp numbering start (0 or 1) */
204 char valid; /* !=0 if following fields are valid */
205 char auto_point_temp_signed;
206 unsigned long last_updated; /* In jiffies */
207 unsigned long last_limits; /* In jiffies */
209 /* Register Values */
210 u8 in[F71882FG_MAX_INS];
211 u8 in1_max;
212 u8 in_status;
213 u8 in_beep;
214 u16 fan[4];
215 u16 fan_target[4];
216 u16 fan_full_speed[4];
217 u8 fan_status;
218 u8 fan_beep;
219 /* Note: all models have max 3 temperature channels, but on some
220 they are addressed as 0-2 and on others as 1-3, so for coding
221 convenience we reserve space for 4 channels */
222 u16 temp[4];
223 u8 temp_ovt[4];
224 u8 temp_high[4];
225 u8 temp_hyst[2]; /* 2 hysts stored per reg */
226 u8 temp_type[4];
227 u8 temp_status;
228 u8 temp_beep;
229 u8 temp_diode_open;
230 u8 temp_config;
231 u8 pwm[4];
232 u8 pwm_enable;
233 u8 pwm_auto_point_hyst[2];
234 u8 pwm_auto_point_mapping[4];
235 u8 pwm_auto_point_pwm[4][5];
236 s8 pwm_auto_point_temp[4][4];
239 /* Sysfs in */
240 static ssize_t show_in(struct device *dev, struct device_attribute *devattr,
241 char *buf);
242 static ssize_t show_in_max(struct device *dev, struct device_attribute
243 *devattr, char *buf);
244 static ssize_t store_in_max(struct device *dev, struct device_attribute
245 *devattr, const char *buf, size_t count);
246 static ssize_t show_in_beep(struct device *dev, struct device_attribute
247 *devattr, char *buf);
248 static ssize_t store_in_beep(struct device *dev, struct device_attribute
249 *devattr, const char *buf, size_t count);
250 static ssize_t show_in_alarm(struct device *dev, struct device_attribute
251 *devattr, char *buf);
252 /* Sysfs Fan */
253 static ssize_t show_fan(struct device *dev, struct device_attribute *devattr,
254 char *buf);
255 static ssize_t show_fan_full_speed(struct device *dev,
256 struct device_attribute *devattr, char *buf);
257 static ssize_t store_fan_full_speed(struct device *dev,
258 struct device_attribute *devattr, const char *buf, size_t count);
259 static ssize_t show_fan_beep(struct device *dev, struct device_attribute
260 *devattr, char *buf);
261 static ssize_t store_fan_beep(struct device *dev, struct device_attribute
262 *devattr, const char *buf, size_t count);
263 static ssize_t show_fan_alarm(struct device *dev, struct device_attribute
264 *devattr, char *buf);
265 /* Sysfs Temp */
266 static ssize_t show_temp(struct device *dev, struct device_attribute
267 *devattr, char *buf);
268 static ssize_t show_temp_max(struct device *dev, struct device_attribute
269 *devattr, char *buf);
270 static ssize_t store_temp_max(struct device *dev, struct device_attribute
271 *devattr, const char *buf, size_t count);
272 static ssize_t show_temp_max_hyst(struct device *dev, struct device_attribute
273 *devattr, char *buf);
274 static ssize_t store_temp_max_hyst(struct device *dev, struct device_attribute
275 *devattr, const char *buf, size_t count);
276 static ssize_t show_temp_crit(struct device *dev, struct device_attribute
277 *devattr, char *buf);
278 static ssize_t store_temp_crit(struct device *dev, struct device_attribute
279 *devattr, const char *buf, size_t count);
280 static ssize_t show_temp_crit_hyst(struct device *dev, struct device_attribute
281 *devattr, char *buf);
282 static ssize_t show_temp_type(struct device *dev, struct device_attribute
283 *devattr, char *buf);
284 static ssize_t show_temp_beep(struct device *dev, struct device_attribute
285 *devattr, char *buf);
286 static ssize_t store_temp_beep(struct device *dev, struct device_attribute
287 *devattr, const char *buf, size_t count);
288 static ssize_t show_temp_alarm(struct device *dev, struct device_attribute
289 *devattr, char *buf);
290 static ssize_t show_temp_fault(struct device *dev, struct device_attribute
291 *devattr, char *buf);
292 /* PWM and Auto point control */
293 static ssize_t show_pwm(struct device *dev, struct device_attribute *devattr,
294 char *buf);
295 static ssize_t store_pwm(struct device *dev, struct device_attribute *devattr,
296 const char *buf, size_t count);
297 static ssize_t show_pwm_enable(struct device *dev,
298 struct device_attribute *devattr, char *buf);
299 static ssize_t store_pwm_enable(struct device *dev,
300 struct device_attribute *devattr, const char *buf, size_t count);
301 static ssize_t show_pwm_interpolate(struct device *dev,
302 struct device_attribute *devattr, char *buf);
303 static ssize_t store_pwm_interpolate(struct device *dev,
304 struct device_attribute *devattr, const char *buf, size_t count);
305 static ssize_t show_pwm_auto_point_channel(struct device *dev,
306 struct device_attribute *devattr, char *buf);
307 static ssize_t store_pwm_auto_point_channel(struct device *dev,
308 struct device_attribute *devattr, const char *buf, size_t count);
309 static ssize_t show_pwm_auto_point_temp_hyst(struct device *dev,
310 struct device_attribute *devattr, char *buf);
311 static ssize_t store_pwm_auto_point_temp_hyst(struct device *dev,
312 struct device_attribute *devattr, const char *buf, size_t count);
313 static ssize_t show_pwm_auto_point_pwm(struct device *dev,
314 struct device_attribute *devattr, char *buf);
315 static ssize_t store_pwm_auto_point_pwm(struct device *dev,
316 struct device_attribute *devattr, const char *buf, size_t count);
317 static ssize_t show_pwm_auto_point_temp(struct device *dev,
318 struct device_attribute *devattr, char *buf);
319 static ssize_t store_pwm_auto_point_temp(struct device *dev,
320 struct device_attribute *devattr, const char *buf, size_t count);
321 /* Sysfs misc */
322 static ssize_t show_name(struct device *dev, struct device_attribute *devattr,
323 char *buf);
325 static int __devinit f71882fg_probe(struct platform_device * pdev);
326 static int f71882fg_remove(struct platform_device *pdev);
328 static struct platform_driver f71882fg_driver = {
329 .driver = {
330 .owner = THIS_MODULE,
331 .name = DRVNAME,
333 .probe = f71882fg_probe,
334 .remove = f71882fg_remove,
337 static DEVICE_ATTR(name, S_IRUGO, show_name, NULL);
339 /* Temp attr for the f71858fg, the f71858fg is special as it has its
340 temperature indexes start at 0 (the others start at 1) */
341 static struct sensor_device_attribute_2 f71858fg_temp_attr[] = {
342 SENSOR_ATTR_2(temp1_input, S_IRUGO, show_temp, NULL, 0, 0),
343 SENSOR_ATTR_2(temp1_max, S_IRUGO|S_IWUSR, show_temp_max,
344 store_temp_max, 0, 0),
345 SENSOR_ATTR_2(temp1_max_hyst, S_IRUGO|S_IWUSR, show_temp_max_hyst,
346 store_temp_max_hyst, 0, 0),
347 SENSOR_ATTR_2(temp1_max_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 0),
348 SENSOR_ATTR_2(temp1_crit, S_IRUGO|S_IWUSR, show_temp_crit,
349 store_temp_crit, 0, 0),
350 SENSOR_ATTR_2(temp1_crit_hyst, S_IRUGO, show_temp_crit_hyst, NULL,
351 0, 0),
352 SENSOR_ATTR_2(temp1_crit_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 4),
353 SENSOR_ATTR_2(temp1_fault, S_IRUGO, show_temp_fault, NULL, 0, 0),
354 SENSOR_ATTR_2(temp2_input, S_IRUGO, show_temp, NULL, 0, 1),
355 SENSOR_ATTR_2(temp2_max, S_IRUGO|S_IWUSR, show_temp_max,
356 store_temp_max, 0, 1),
357 SENSOR_ATTR_2(temp2_max_hyst, S_IRUGO|S_IWUSR, show_temp_max_hyst,
358 store_temp_max_hyst, 0, 1),
359 SENSOR_ATTR_2(temp2_max_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 1),
360 SENSOR_ATTR_2(temp2_crit, S_IRUGO|S_IWUSR, show_temp_crit,
361 store_temp_crit, 0, 1),
362 SENSOR_ATTR_2(temp2_crit_hyst, S_IRUGO, show_temp_crit_hyst, NULL,
363 0, 1),
364 SENSOR_ATTR_2(temp2_crit_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 5),
365 SENSOR_ATTR_2(temp2_fault, S_IRUGO, show_temp_fault, NULL, 0, 1),
366 SENSOR_ATTR_2(temp3_input, S_IRUGO, show_temp, NULL, 0, 2),
367 SENSOR_ATTR_2(temp3_max, S_IRUGO|S_IWUSR, show_temp_max,
368 store_temp_max, 0, 2),
369 SENSOR_ATTR_2(temp3_max_hyst, S_IRUGO|S_IWUSR, show_temp_max_hyst,
370 store_temp_max_hyst, 0, 2),
371 SENSOR_ATTR_2(temp3_max_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 2),
372 SENSOR_ATTR_2(temp3_crit, S_IRUGO|S_IWUSR, show_temp_crit,
373 store_temp_crit, 0, 2),
374 SENSOR_ATTR_2(temp3_crit_hyst, S_IRUGO, show_temp_crit_hyst, NULL,
375 0, 2),
376 SENSOR_ATTR_2(temp3_crit_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 6),
377 SENSOR_ATTR_2(temp3_fault, S_IRUGO, show_temp_fault, NULL, 0, 2),
380 /* Temp attr for the standard models */
381 static struct sensor_device_attribute_2 fxxxx_temp_attr[3][9] = { {
382 SENSOR_ATTR_2(temp1_input, S_IRUGO, show_temp, NULL, 0, 1),
383 SENSOR_ATTR_2(temp1_max, S_IRUGO|S_IWUSR, show_temp_max,
384 store_temp_max, 0, 1),
385 SENSOR_ATTR_2(temp1_max_hyst, S_IRUGO|S_IWUSR, show_temp_max_hyst,
386 store_temp_max_hyst, 0, 1),
387 /* Should really be temp1_max_alarm, but older versions did not handle
388 the max and crit alarms separately and lm_sensors v2 depends on the
389 presence of temp#_alarm files. The same goes for temp2/3 _alarm. */
390 SENSOR_ATTR_2(temp1_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 1),
391 SENSOR_ATTR_2(temp1_crit, S_IRUGO|S_IWUSR, show_temp_crit,
392 store_temp_crit, 0, 1),
393 SENSOR_ATTR_2(temp1_crit_hyst, S_IRUGO, show_temp_crit_hyst, NULL,
394 0, 1),
395 SENSOR_ATTR_2(temp1_crit_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 5),
396 SENSOR_ATTR_2(temp1_type, S_IRUGO, show_temp_type, NULL, 0, 1),
397 SENSOR_ATTR_2(temp1_fault, S_IRUGO, show_temp_fault, NULL, 0, 1),
398 }, {
399 SENSOR_ATTR_2(temp2_input, S_IRUGO, show_temp, NULL, 0, 2),
400 SENSOR_ATTR_2(temp2_max, S_IRUGO|S_IWUSR, show_temp_max,
401 store_temp_max, 0, 2),
402 SENSOR_ATTR_2(temp2_max_hyst, S_IRUGO|S_IWUSR, show_temp_max_hyst,
403 store_temp_max_hyst, 0, 2),
404 /* Should be temp2_max_alarm, see temp1_alarm note */
405 SENSOR_ATTR_2(temp2_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 2),
406 SENSOR_ATTR_2(temp2_crit, S_IRUGO|S_IWUSR, show_temp_crit,
407 store_temp_crit, 0, 2),
408 SENSOR_ATTR_2(temp2_crit_hyst, S_IRUGO, show_temp_crit_hyst, NULL,
409 0, 2),
410 SENSOR_ATTR_2(temp2_crit_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 6),
411 SENSOR_ATTR_2(temp2_type, S_IRUGO, show_temp_type, NULL, 0, 2),
412 SENSOR_ATTR_2(temp2_fault, S_IRUGO, show_temp_fault, NULL, 0, 2),
413 }, {
414 SENSOR_ATTR_2(temp3_input, S_IRUGO, show_temp, NULL, 0, 3),
415 SENSOR_ATTR_2(temp3_max, S_IRUGO|S_IWUSR, show_temp_max,
416 store_temp_max, 0, 3),
417 SENSOR_ATTR_2(temp3_max_hyst, S_IRUGO|S_IWUSR, show_temp_max_hyst,
418 store_temp_max_hyst, 0, 3),
419 /* Should be temp3_max_alarm, see temp1_alarm note */
420 SENSOR_ATTR_2(temp3_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 3),
421 SENSOR_ATTR_2(temp3_crit, S_IRUGO|S_IWUSR, show_temp_crit,
422 store_temp_crit, 0, 3),
423 SENSOR_ATTR_2(temp3_crit_hyst, S_IRUGO, show_temp_crit_hyst, NULL,
424 0, 3),
425 SENSOR_ATTR_2(temp3_crit_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 7),
426 SENSOR_ATTR_2(temp3_type, S_IRUGO, show_temp_type, NULL, 0, 3),
427 SENSOR_ATTR_2(temp3_fault, S_IRUGO, show_temp_fault, NULL, 0, 3),
428 } };
430 /* Temp attr for models which can beep on temp alarm */
431 static struct sensor_device_attribute_2 fxxxx_temp_beep_attr[3][2] = { {
432 SENSOR_ATTR_2(temp1_max_beep, S_IRUGO|S_IWUSR, show_temp_beep,
433 store_temp_beep, 0, 1),
434 SENSOR_ATTR_2(temp1_crit_beep, S_IRUGO|S_IWUSR, show_temp_beep,
435 store_temp_beep, 0, 5),
436 }, {
437 SENSOR_ATTR_2(temp2_max_beep, S_IRUGO|S_IWUSR, show_temp_beep,
438 store_temp_beep, 0, 2),
439 SENSOR_ATTR_2(temp2_crit_beep, S_IRUGO|S_IWUSR, show_temp_beep,
440 store_temp_beep, 0, 6),
441 }, {
442 SENSOR_ATTR_2(temp3_max_beep, S_IRUGO|S_IWUSR, show_temp_beep,
443 store_temp_beep, 0, 3),
444 SENSOR_ATTR_2(temp3_crit_beep, S_IRUGO|S_IWUSR, show_temp_beep,
445 store_temp_beep, 0, 7),
446 } };
448 /* Temp attr for the f8000
449 Note on the f8000 temp_ovt (crit) is used as max, and temp_high (max)
450 is used as hysteresis value to clear alarms
451 Also like the f71858fg its temperature indexes start at 0
453 static struct sensor_device_attribute_2 f8000_temp_attr[] = {
454 SENSOR_ATTR_2(temp1_input, S_IRUGO, show_temp, NULL, 0, 0),
455 SENSOR_ATTR_2(temp1_max, S_IRUGO|S_IWUSR, show_temp_crit,
456 store_temp_crit, 0, 0),
457 SENSOR_ATTR_2(temp1_max_hyst, S_IRUGO|S_IWUSR, show_temp_max,
458 store_temp_max, 0, 0),
459 SENSOR_ATTR_2(temp1_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 4),
460 SENSOR_ATTR_2(temp1_fault, S_IRUGO, show_temp_fault, NULL, 0, 0),
461 SENSOR_ATTR_2(temp2_input, S_IRUGO, show_temp, NULL, 0, 1),
462 SENSOR_ATTR_2(temp2_max, S_IRUGO|S_IWUSR, show_temp_crit,
463 store_temp_crit, 0, 1),
464 SENSOR_ATTR_2(temp2_max_hyst, S_IRUGO|S_IWUSR, show_temp_max,
465 store_temp_max, 0, 1),
466 SENSOR_ATTR_2(temp2_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 5),
467 SENSOR_ATTR_2(temp2_fault, S_IRUGO, show_temp_fault, NULL, 0, 1),
468 SENSOR_ATTR_2(temp3_input, S_IRUGO, show_temp, NULL, 0, 2),
469 SENSOR_ATTR_2(temp3_max, S_IRUGO|S_IWUSR, show_temp_crit,
470 store_temp_crit, 0, 2),
471 SENSOR_ATTR_2(temp3_max_hyst, S_IRUGO|S_IWUSR, show_temp_max,
472 store_temp_max, 0, 2),
473 SENSOR_ATTR_2(temp3_alarm, S_IRUGO, show_temp_alarm, NULL, 0, 6),
474 SENSOR_ATTR_2(temp3_fault, S_IRUGO, show_temp_fault, NULL, 0, 2),
477 /* in attr for all models */
478 static struct sensor_device_attribute_2 fxxxx_in_attr[] = {
479 SENSOR_ATTR_2(in0_input, S_IRUGO, show_in, NULL, 0, 0),
480 SENSOR_ATTR_2(in1_input, S_IRUGO, show_in, NULL, 0, 1),
481 SENSOR_ATTR_2(in2_input, S_IRUGO, show_in, NULL, 0, 2),
482 SENSOR_ATTR_2(in3_input, S_IRUGO, show_in, NULL, 0, 3),
483 SENSOR_ATTR_2(in4_input, S_IRUGO, show_in, NULL, 0, 4),
484 SENSOR_ATTR_2(in5_input, S_IRUGO, show_in, NULL, 0, 5),
485 SENSOR_ATTR_2(in6_input, S_IRUGO, show_in, NULL, 0, 6),
486 SENSOR_ATTR_2(in7_input, S_IRUGO, show_in, NULL, 0, 7),
487 SENSOR_ATTR_2(in8_input, S_IRUGO, show_in, NULL, 0, 8),
490 /* For models with in1 alarm capability */
491 static struct sensor_device_attribute_2 fxxxx_in1_alarm_attr[] = {
492 SENSOR_ATTR_2(in1_max, S_IRUGO|S_IWUSR, show_in_max, store_in_max,
493 0, 1),
494 SENSOR_ATTR_2(in1_beep, S_IRUGO|S_IWUSR, show_in_beep, store_in_beep,
495 0, 1),
496 SENSOR_ATTR_2(in1_alarm, S_IRUGO, show_in_alarm, NULL, 0, 1),
499 /* Fan / PWM attr common to all models */
500 static struct sensor_device_attribute_2 fxxxx_fan_attr[4][6] = { {
501 SENSOR_ATTR_2(fan1_input, S_IRUGO, show_fan, NULL, 0, 0),
502 SENSOR_ATTR_2(fan1_full_speed, S_IRUGO|S_IWUSR,
503 show_fan_full_speed,
504 store_fan_full_speed, 0, 0),
505 SENSOR_ATTR_2(fan1_alarm, S_IRUGO, show_fan_alarm, NULL, 0, 0),
506 SENSOR_ATTR_2(pwm1, S_IRUGO|S_IWUSR, show_pwm, store_pwm, 0, 0),
507 SENSOR_ATTR_2(pwm1_enable, S_IRUGO|S_IWUSR, show_pwm_enable,
508 store_pwm_enable, 0, 0),
509 SENSOR_ATTR_2(pwm1_interpolate, S_IRUGO|S_IWUSR,
510 show_pwm_interpolate, store_pwm_interpolate, 0, 0),
511 }, {
512 SENSOR_ATTR_2(fan2_input, S_IRUGO, show_fan, NULL, 0, 1),
513 SENSOR_ATTR_2(fan2_full_speed, S_IRUGO|S_IWUSR,
514 show_fan_full_speed,
515 store_fan_full_speed, 0, 1),
516 SENSOR_ATTR_2(fan2_alarm, S_IRUGO, show_fan_alarm, NULL, 0, 1),
517 SENSOR_ATTR_2(pwm2, S_IRUGO|S_IWUSR, show_pwm, store_pwm, 0, 1),
518 SENSOR_ATTR_2(pwm2_enable, S_IRUGO|S_IWUSR, show_pwm_enable,
519 store_pwm_enable, 0, 1),
520 SENSOR_ATTR_2(pwm2_interpolate, S_IRUGO|S_IWUSR,
521 show_pwm_interpolate, store_pwm_interpolate, 0, 1),
522 }, {
523 SENSOR_ATTR_2(fan3_input, S_IRUGO, show_fan, NULL, 0, 2),
524 SENSOR_ATTR_2(fan3_full_speed, S_IRUGO|S_IWUSR,
525 show_fan_full_speed,
526 store_fan_full_speed, 0, 2),
527 SENSOR_ATTR_2(fan3_alarm, S_IRUGO, show_fan_alarm, NULL, 0, 2),
528 SENSOR_ATTR_2(pwm3, S_IRUGO|S_IWUSR, show_pwm, store_pwm, 0, 2),
529 SENSOR_ATTR_2(pwm3_enable, S_IRUGO|S_IWUSR, show_pwm_enable,
530 store_pwm_enable, 0, 2),
531 SENSOR_ATTR_2(pwm3_interpolate, S_IRUGO|S_IWUSR,
532 show_pwm_interpolate, store_pwm_interpolate, 0, 2),
533 }, {
534 SENSOR_ATTR_2(fan4_input, S_IRUGO, show_fan, NULL, 0, 3),
535 SENSOR_ATTR_2(fan4_full_speed, S_IRUGO|S_IWUSR,
536 show_fan_full_speed,
537 store_fan_full_speed, 0, 3),
538 SENSOR_ATTR_2(fan4_alarm, S_IRUGO, show_fan_alarm, NULL, 0, 3),
539 SENSOR_ATTR_2(pwm4, S_IRUGO|S_IWUSR, show_pwm, store_pwm, 0, 3),
540 SENSOR_ATTR_2(pwm4_enable, S_IRUGO|S_IWUSR, show_pwm_enable,
541 store_pwm_enable, 0, 3),
542 SENSOR_ATTR_2(pwm4_interpolate, S_IRUGO|S_IWUSR,
543 show_pwm_interpolate, store_pwm_interpolate, 0, 3),
544 } };
546 /* Attr for models which can beep on Fan alarm */
547 static struct sensor_device_attribute_2 fxxxx_fan_beep_attr[] = {
548 SENSOR_ATTR_2(fan1_beep, S_IRUGO|S_IWUSR, show_fan_beep,
549 store_fan_beep, 0, 0),
550 SENSOR_ATTR_2(fan2_beep, S_IRUGO|S_IWUSR, show_fan_beep,
551 store_fan_beep, 0, 1),
552 SENSOR_ATTR_2(fan3_beep, S_IRUGO|S_IWUSR, show_fan_beep,
553 store_fan_beep, 0, 2),
554 SENSOR_ATTR_2(fan4_beep, S_IRUGO|S_IWUSR, show_fan_beep,
555 store_fan_beep, 0, 3),
558 /* PWM attr for the f71862fg, fewer pwms and fewer zones per pwm than the
559 standard models */
560 static struct sensor_device_attribute_2 f71862fg_auto_pwm_attr[] = {
561 SENSOR_ATTR_2(pwm1_auto_channels_temp, S_IRUGO|S_IWUSR,
562 show_pwm_auto_point_channel,
563 store_pwm_auto_point_channel, 0, 0),
564 SENSOR_ATTR_2(pwm1_auto_point1_pwm, S_IRUGO|S_IWUSR,
565 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
566 1, 0),
567 SENSOR_ATTR_2(pwm1_auto_point2_pwm, S_IRUGO|S_IWUSR,
568 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
569 4, 0),
570 SENSOR_ATTR_2(pwm1_auto_point1_temp, S_IRUGO|S_IWUSR,
571 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
572 0, 0),
573 SENSOR_ATTR_2(pwm1_auto_point2_temp, S_IRUGO|S_IWUSR,
574 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
575 3, 0),
576 SENSOR_ATTR_2(pwm1_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
577 show_pwm_auto_point_temp_hyst,
578 store_pwm_auto_point_temp_hyst,
579 0, 0),
580 SENSOR_ATTR_2(pwm1_auto_point2_temp_hyst, S_IRUGO,
581 show_pwm_auto_point_temp_hyst, NULL, 3, 0),
583 SENSOR_ATTR_2(pwm2_auto_channels_temp, S_IRUGO|S_IWUSR,
584 show_pwm_auto_point_channel,
585 store_pwm_auto_point_channel, 0, 1),
586 SENSOR_ATTR_2(pwm2_auto_point1_pwm, S_IRUGO|S_IWUSR,
587 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
588 1, 1),
589 SENSOR_ATTR_2(pwm2_auto_point2_pwm, S_IRUGO|S_IWUSR,
590 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
591 4, 1),
592 SENSOR_ATTR_2(pwm2_auto_point1_temp, S_IRUGO|S_IWUSR,
593 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
594 0, 1),
595 SENSOR_ATTR_2(pwm2_auto_point2_temp, S_IRUGO|S_IWUSR,
596 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
597 3, 1),
598 SENSOR_ATTR_2(pwm2_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
599 show_pwm_auto_point_temp_hyst,
600 store_pwm_auto_point_temp_hyst,
601 0, 1),
602 SENSOR_ATTR_2(pwm2_auto_point2_temp_hyst, S_IRUGO,
603 show_pwm_auto_point_temp_hyst, NULL, 3, 1),
605 SENSOR_ATTR_2(pwm3_auto_channels_temp, S_IRUGO|S_IWUSR,
606 show_pwm_auto_point_channel,
607 store_pwm_auto_point_channel, 0, 2),
608 SENSOR_ATTR_2(pwm3_auto_point1_pwm, S_IRUGO|S_IWUSR,
609 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
610 1, 2),
611 SENSOR_ATTR_2(pwm3_auto_point2_pwm, S_IRUGO|S_IWUSR,
612 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
613 4, 2),
614 SENSOR_ATTR_2(pwm3_auto_point1_temp, S_IRUGO|S_IWUSR,
615 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
616 0, 2),
617 SENSOR_ATTR_2(pwm3_auto_point2_temp, S_IRUGO|S_IWUSR,
618 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
619 3, 2),
620 SENSOR_ATTR_2(pwm3_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
621 show_pwm_auto_point_temp_hyst,
622 store_pwm_auto_point_temp_hyst,
623 0, 2),
624 SENSOR_ATTR_2(pwm3_auto_point2_temp_hyst, S_IRUGO,
625 show_pwm_auto_point_temp_hyst, NULL, 3, 2),
628 /* PWM attr for the f71808e/f71869, almost identical to the f71862fg, but the
629 pwm setting when the temperature is above the pwmX_auto_point1_temp can be
630 programmed instead of being hardcoded to 0xff */
631 static struct sensor_device_attribute_2 f71869_auto_pwm_attr[] = {
632 SENSOR_ATTR_2(pwm1_auto_channels_temp, S_IRUGO|S_IWUSR,
633 show_pwm_auto_point_channel,
634 store_pwm_auto_point_channel, 0, 0),
635 SENSOR_ATTR_2(pwm1_auto_point1_pwm, S_IRUGO|S_IWUSR,
636 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
637 0, 0),
638 SENSOR_ATTR_2(pwm1_auto_point2_pwm, S_IRUGO|S_IWUSR,
639 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
640 1, 0),
641 SENSOR_ATTR_2(pwm1_auto_point3_pwm, S_IRUGO|S_IWUSR,
642 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
643 4, 0),
644 SENSOR_ATTR_2(pwm1_auto_point1_temp, S_IRUGO|S_IWUSR,
645 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
646 0, 0),
647 SENSOR_ATTR_2(pwm1_auto_point2_temp, S_IRUGO|S_IWUSR,
648 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
649 3, 0),
650 SENSOR_ATTR_2(pwm1_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
651 show_pwm_auto_point_temp_hyst,
652 store_pwm_auto_point_temp_hyst,
653 0, 0),
654 SENSOR_ATTR_2(pwm1_auto_point2_temp_hyst, S_IRUGO,
655 show_pwm_auto_point_temp_hyst, NULL, 3, 0),
657 SENSOR_ATTR_2(pwm2_auto_channels_temp, S_IRUGO|S_IWUSR,
658 show_pwm_auto_point_channel,
659 store_pwm_auto_point_channel, 0, 1),
660 SENSOR_ATTR_2(pwm2_auto_point1_pwm, S_IRUGO|S_IWUSR,
661 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
662 0, 1),
663 SENSOR_ATTR_2(pwm2_auto_point2_pwm, S_IRUGO|S_IWUSR,
664 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
665 1, 1),
666 SENSOR_ATTR_2(pwm2_auto_point3_pwm, S_IRUGO|S_IWUSR,
667 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
668 4, 1),
669 SENSOR_ATTR_2(pwm2_auto_point1_temp, S_IRUGO|S_IWUSR,
670 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
671 0, 1),
672 SENSOR_ATTR_2(pwm2_auto_point2_temp, S_IRUGO|S_IWUSR,
673 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
674 3, 1),
675 SENSOR_ATTR_2(pwm2_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
676 show_pwm_auto_point_temp_hyst,
677 store_pwm_auto_point_temp_hyst,
678 0, 1),
679 SENSOR_ATTR_2(pwm2_auto_point2_temp_hyst, S_IRUGO,
680 show_pwm_auto_point_temp_hyst, NULL, 3, 1),
682 SENSOR_ATTR_2(pwm3_auto_channels_temp, S_IRUGO|S_IWUSR,
683 show_pwm_auto_point_channel,
684 store_pwm_auto_point_channel, 0, 2),
685 SENSOR_ATTR_2(pwm3_auto_point1_pwm, S_IRUGO|S_IWUSR,
686 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
687 0, 2),
688 SENSOR_ATTR_2(pwm3_auto_point2_pwm, S_IRUGO|S_IWUSR,
689 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
690 1, 2),
691 SENSOR_ATTR_2(pwm3_auto_point3_pwm, S_IRUGO|S_IWUSR,
692 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
693 4, 2),
694 SENSOR_ATTR_2(pwm3_auto_point1_temp, S_IRUGO|S_IWUSR,
695 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
696 0, 2),
697 SENSOR_ATTR_2(pwm3_auto_point2_temp, S_IRUGO|S_IWUSR,
698 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
699 3, 2),
700 SENSOR_ATTR_2(pwm3_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
701 show_pwm_auto_point_temp_hyst,
702 store_pwm_auto_point_temp_hyst,
703 0, 2),
704 SENSOR_ATTR_2(pwm3_auto_point2_temp_hyst, S_IRUGO,
705 show_pwm_auto_point_temp_hyst, NULL, 3, 2),
708 /* PWM attr for the standard models */
709 static struct sensor_device_attribute_2 fxxxx_auto_pwm_attr[4][14] = { {
710 SENSOR_ATTR_2(pwm1_auto_channels_temp, S_IRUGO|S_IWUSR,
711 show_pwm_auto_point_channel,
712 store_pwm_auto_point_channel, 0, 0),
713 SENSOR_ATTR_2(pwm1_auto_point1_pwm, S_IRUGO|S_IWUSR,
714 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
715 0, 0),
716 SENSOR_ATTR_2(pwm1_auto_point2_pwm, S_IRUGO|S_IWUSR,
717 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
718 1, 0),
719 SENSOR_ATTR_2(pwm1_auto_point3_pwm, S_IRUGO|S_IWUSR,
720 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
721 2, 0),
722 SENSOR_ATTR_2(pwm1_auto_point4_pwm, S_IRUGO|S_IWUSR,
723 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
724 3, 0),
725 SENSOR_ATTR_2(pwm1_auto_point5_pwm, S_IRUGO|S_IWUSR,
726 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
727 4, 0),
728 SENSOR_ATTR_2(pwm1_auto_point1_temp, S_IRUGO|S_IWUSR,
729 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
730 0, 0),
731 SENSOR_ATTR_2(pwm1_auto_point2_temp, S_IRUGO|S_IWUSR,
732 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
733 1, 0),
734 SENSOR_ATTR_2(pwm1_auto_point3_temp, S_IRUGO|S_IWUSR,
735 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
736 2, 0),
737 SENSOR_ATTR_2(pwm1_auto_point4_temp, S_IRUGO|S_IWUSR,
738 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
739 3, 0),
740 SENSOR_ATTR_2(pwm1_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
741 show_pwm_auto_point_temp_hyst,
742 store_pwm_auto_point_temp_hyst,
743 0, 0),
744 SENSOR_ATTR_2(pwm1_auto_point2_temp_hyst, S_IRUGO,
745 show_pwm_auto_point_temp_hyst, NULL, 1, 0),
746 SENSOR_ATTR_2(pwm1_auto_point3_temp_hyst, S_IRUGO,
747 show_pwm_auto_point_temp_hyst, NULL, 2, 0),
748 SENSOR_ATTR_2(pwm1_auto_point4_temp_hyst, S_IRUGO,
749 show_pwm_auto_point_temp_hyst, NULL, 3, 0),
750 }, {
751 SENSOR_ATTR_2(pwm2_auto_channels_temp, S_IRUGO|S_IWUSR,
752 show_pwm_auto_point_channel,
753 store_pwm_auto_point_channel, 0, 1),
754 SENSOR_ATTR_2(pwm2_auto_point1_pwm, S_IRUGO|S_IWUSR,
755 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
756 0, 1),
757 SENSOR_ATTR_2(pwm2_auto_point2_pwm, S_IRUGO|S_IWUSR,
758 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
759 1, 1),
760 SENSOR_ATTR_2(pwm2_auto_point3_pwm, S_IRUGO|S_IWUSR,
761 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
762 2, 1),
763 SENSOR_ATTR_2(pwm2_auto_point4_pwm, S_IRUGO|S_IWUSR,
764 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
765 3, 1),
766 SENSOR_ATTR_2(pwm2_auto_point5_pwm, S_IRUGO|S_IWUSR,
767 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
768 4, 1),
769 SENSOR_ATTR_2(pwm2_auto_point1_temp, S_IRUGO|S_IWUSR,
770 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
771 0, 1),
772 SENSOR_ATTR_2(pwm2_auto_point2_temp, S_IRUGO|S_IWUSR,
773 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
774 1, 1),
775 SENSOR_ATTR_2(pwm2_auto_point3_temp, S_IRUGO|S_IWUSR,
776 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
777 2, 1),
778 SENSOR_ATTR_2(pwm2_auto_point4_temp, S_IRUGO|S_IWUSR,
779 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
780 3, 1),
781 SENSOR_ATTR_2(pwm2_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
782 show_pwm_auto_point_temp_hyst,
783 store_pwm_auto_point_temp_hyst,
784 0, 1),
785 SENSOR_ATTR_2(pwm2_auto_point2_temp_hyst, S_IRUGO,
786 show_pwm_auto_point_temp_hyst, NULL, 1, 1),
787 SENSOR_ATTR_2(pwm2_auto_point3_temp_hyst, S_IRUGO,
788 show_pwm_auto_point_temp_hyst, NULL, 2, 1),
789 SENSOR_ATTR_2(pwm2_auto_point4_temp_hyst, S_IRUGO,
790 show_pwm_auto_point_temp_hyst, NULL, 3, 1),
791 }, {
792 SENSOR_ATTR_2(pwm3_auto_channels_temp, S_IRUGO|S_IWUSR,
793 show_pwm_auto_point_channel,
794 store_pwm_auto_point_channel, 0, 2),
795 SENSOR_ATTR_2(pwm3_auto_point1_pwm, S_IRUGO|S_IWUSR,
796 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
797 0, 2),
798 SENSOR_ATTR_2(pwm3_auto_point2_pwm, S_IRUGO|S_IWUSR,
799 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
800 1, 2),
801 SENSOR_ATTR_2(pwm3_auto_point3_pwm, S_IRUGO|S_IWUSR,
802 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
803 2, 2),
804 SENSOR_ATTR_2(pwm3_auto_point4_pwm, S_IRUGO|S_IWUSR,
805 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
806 3, 2),
807 SENSOR_ATTR_2(pwm3_auto_point5_pwm, S_IRUGO|S_IWUSR,
808 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
809 4, 2),
810 SENSOR_ATTR_2(pwm3_auto_point1_temp, S_IRUGO|S_IWUSR,
811 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
812 0, 2),
813 SENSOR_ATTR_2(pwm3_auto_point2_temp, S_IRUGO|S_IWUSR,
814 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
815 1, 2),
816 SENSOR_ATTR_2(pwm3_auto_point3_temp, S_IRUGO|S_IWUSR,
817 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
818 2, 2),
819 SENSOR_ATTR_2(pwm3_auto_point4_temp, S_IRUGO|S_IWUSR,
820 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
821 3, 2),
822 SENSOR_ATTR_2(pwm3_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
823 show_pwm_auto_point_temp_hyst,
824 store_pwm_auto_point_temp_hyst,
825 0, 2),
826 SENSOR_ATTR_2(pwm3_auto_point2_temp_hyst, S_IRUGO,
827 show_pwm_auto_point_temp_hyst, NULL, 1, 2),
828 SENSOR_ATTR_2(pwm3_auto_point3_temp_hyst, S_IRUGO,
829 show_pwm_auto_point_temp_hyst, NULL, 2, 2),
830 SENSOR_ATTR_2(pwm3_auto_point4_temp_hyst, S_IRUGO,
831 show_pwm_auto_point_temp_hyst, NULL, 3, 2),
832 }, {
833 SENSOR_ATTR_2(pwm4_auto_channels_temp, S_IRUGO|S_IWUSR,
834 show_pwm_auto_point_channel,
835 store_pwm_auto_point_channel, 0, 3),
836 SENSOR_ATTR_2(pwm4_auto_point1_pwm, S_IRUGO|S_IWUSR,
837 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
838 0, 3),
839 SENSOR_ATTR_2(pwm4_auto_point2_pwm, S_IRUGO|S_IWUSR,
840 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
841 1, 3),
842 SENSOR_ATTR_2(pwm4_auto_point3_pwm, S_IRUGO|S_IWUSR,
843 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
844 2, 3),
845 SENSOR_ATTR_2(pwm4_auto_point4_pwm, S_IRUGO|S_IWUSR,
846 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
847 3, 3),
848 SENSOR_ATTR_2(pwm4_auto_point5_pwm, S_IRUGO|S_IWUSR,
849 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
850 4, 3),
851 SENSOR_ATTR_2(pwm4_auto_point1_temp, S_IRUGO|S_IWUSR,
852 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
853 0, 3),
854 SENSOR_ATTR_2(pwm4_auto_point2_temp, S_IRUGO|S_IWUSR,
855 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
856 1, 3),
857 SENSOR_ATTR_2(pwm4_auto_point3_temp, S_IRUGO|S_IWUSR,
858 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
859 2, 3),
860 SENSOR_ATTR_2(pwm4_auto_point4_temp, S_IRUGO|S_IWUSR,
861 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
862 3, 3),
863 SENSOR_ATTR_2(pwm4_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
864 show_pwm_auto_point_temp_hyst,
865 store_pwm_auto_point_temp_hyst,
866 0, 3),
867 SENSOR_ATTR_2(pwm4_auto_point2_temp_hyst, S_IRUGO,
868 show_pwm_auto_point_temp_hyst, NULL, 1, 3),
869 SENSOR_ATTR_2(pwm4_auto_point3_temp_hyst, S_IRUGO,
870 show_pwm_auto_point_temp_hyst, NULL, 2, 3),
871 SENSOR_ATTR_2(pwm4_auto_point4_temp_hyst, S_IRUGO,
872 show_pwm_auto_point_temp_hyst, NULL, 3, 3),
873 } };
875 /* Fan attr specific to the f8000 (4th fan input can only measure speed) */
876 static struct sensor_device_attribute_2 f8000_fan_attr[] = {
877 SENSOR_ATTR_2(fan4_input, S_IRUGO, show_fan, NULL, 0, 3),
880 /* PWM attr for the f8000, zones mapped to temp instead of to pwm!
881 Also the register block at offset A0 maps to TEMP1 (so our temp2, as the
882 F8000 starts counting temps at 0), B0 maps the TEMP2 and C0 maps to TEMP0 */
883 static struct sensor_device_attribute_2 f8000_auto_pwm_attr[] = {
884 SENSOR_ATTR_2(pwm1_auto_channels_temp, S_IRUGO|S_IWUSR,
885 show_pwm_auto_point_channel,
886 store_pwm_auto_point_channel, 0, 0),
887 SENSOR_ATTR_2(temp1_auto_point1_pwm, S_IRUGO|S_IWUSR,
888 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
889 0, 2),
890 SENSOR_ATTR_2(temp1_auto_point2_pwm, S_IRUGO|S_IWUSR,
891 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
892 1, 2),
893 SENSOR_ATTR_2(temp1_auto_point3_pwm, S_IRUGO|S_IWUSR,
894 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
895 2, 2),
896 SENSOR_ATTR_2(temp1_auto_point4_pwm, S_IRUGO|S_IWUSR,
897 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
898 3, 2),
899 SENSOR_ATTR_2(temp1_auto_point5_pwm, S_IRUGO|S_IWUSR,
900 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
901 4, 2),
902 SENSOR_ATTR_2(temp1_auto_point1_temp, S_IRUGO|S_IWUSR,
903 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
904 0, 2),
905 SENSOR_ATTR_2(temp1_auto_point2_temp, S_IRUGO|S_IWUSR,
906 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
907 1, 2),
908 SENSOR_ATTR_2(temp1_auto_point3_temp, S_IRUGO|S_IWUSR,
909 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
910 2, 2),
911 SENSOR_ATTR_2(temp1_auto_point4_temp, S_IRUGO|S_IWUSR,
912 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
913 3, 2),
914 SENSOR_ATTR_2(temp1_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
915 show_pwm_auto_point_temp_hyst,
916 store_pwm_auto_point_temp_hyst,
917 0, 2),
918 SENSOR_ATTR_2(temp1_auto_point2_temp_hyst, S_IRUGO,
919 show_pwm_auto_point_temp_hyst, NULL, 1, 2),
920 SENSOR_ATTR_2(temp1_auto_point3_temp_hyst, S_IRUGO,
921 show_pwm_auto_point_temp_hyst, NULL, 2, 2),
922 SENSOR_ATTR_2(temp1_auto_point4_temp_hyst, S_IRUGO,
923 show_pwm_auto_point_temp_hyst, NULL, 3, 2),
925 SENSOR_ATTR_2(pwm2_auto_channels_temp, S_IRUGO|S_IWUSR,
926 show_pwm_auto_point_channel,
927 store_pwm_auto_point_channel, 0, 1),
928 SENSOR_ATTR_2(temp2_auto_point1_pwm, S_IRUGO|S_IWUSR,
929 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
930 0, 0),
931 SENSOR_ATTR_2(temp2_auto_point2_pwm, S_IRUGO|S_IWUSR,
932 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
933 1, 0),
934 SENSOR_ATTR_2(temp2_auto_point3_pwm, S_IRUGO|S_IWUSR,
935 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
936 2, 0),
937 SENSOR_ATTR_2(temp2_auto_point4_pwm, S_IRUGO|S_IWUSR,
938 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
939 3, 0),
940 SENSOR_ATTR_2(temp2_auto_point5_pwm, S_IRUGO|S_IWUSR,
941 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
942 4, 0),
943 SENSOR_ATTR_2(temp2_auto_point1_temp, S_IRUGO|S_IWUSR,
944 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
945 0, 0),
946 SENSOR_ATTR_2(temp2_auto_point2_temp, S_IRUGO|S_IWUSR,
947 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
948 1, 0),
949 SENSOR_ATTR_2(temp2_auto_point3_temp, S_IRUGO|S_IWUSR,
950 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
951 2, 0),
952 SENSOR_ATTR_2(temp2_auto_point4_temp, S_IRUGO|S_IWUSR,
953 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
954 3, 0),
955 SENSOR_ATTR_2(temp2_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
956 show_pwm_auto_point_temp_hyst,
957 store_pwm_auto_point_temp_hyst,
958 0, 0),
959 SENSOR_ATTR_2(temp2_auto_point2_temp_hyst, S_IRUGO,
960 show_pwm_auto_point_temp_hyst, NULL, 1, 0),
961 SENSOR_ATTR_2(temp2_auto_point3_temp_hyst, S_IRUGO,
962 show_pwm_auto_point_temp_hyst, NULL, 2, 0),
963 SENSOR_ATTR_2(temp2_auto_point4_temp_hyst, S_IRUGO,
964 show_pwm_auto_point_temp_hyst, NULL, 3, 0),
966 SENSOR_ATTR_2(pwm3_auto_channels_temp, S_IRUGO|S_IWUSR,
967 show_pwm_auto_point_channel,
968 store_pwm_auto_point_channel, 0, 2),
969 SENSOR_ATTR_2(temp3_auto_point1_pwm, S_IRUGO|S_IWUSR,
970 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
971 0, 1),
972 SENSOR_ATTR_2(temp3_auto_point2_pwm, S_IRUGO|S_IWUSR,
973 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
974 1, 1),
975 SENSOR_ATTR_2(temp3_auto_point3_pwm, S_IRUGO|S_IWUSR,
976 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
977 2, 1),
978 SENSOR_ATTR_2(temp3_auto_point4_pwm, S_IRUGO|S_IWUSR,
979 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
980 3, 1),
981 SENSOR_ATTR_2(temp3_auto_point5_pwm, S_IRUGO|S_IWUSR,
982 show_pwm_auto_point_pwm, store_pwm_auto_point_pwm,
983 4, 1),
984 SENSOR_ATTR_2(temp3_auto_point1_temp, S_IRUGO|S_IWUSR,
985 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
986 0, 1),
987 SENSOR_ATTR_2(temp3_auto_point2_temp, S_IRUGO|S_IWUSR,
988 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
989 1, 1),
990 SENSOR_ATTR_2(temp3_auto_point3_temp, S_IRUGO|S_IWUSR,
991 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
992 2, 1),
993 SENSOR_ATTR_2(temp3_auto_point4_temp, S_IRUGO|S_IWUSR,
994 show_pwm_auto_point_temp, store_pwm_auto_point_temp,
995 3, 1),
996 SENSOR_ATTR_2(temp3_auto_point1_temp_hyst, S_IRUGO|S_IWUSR,
997 show_pwm_auto_point_temp_hyst,
998 store_pwm_auto_point_temp_hyst,
999 0, 1),
1000 SENSOR_ATTR_2(temp3_auto_point2_temp_hyst, S_IRUGO,
1001 show_pwm_auto_point_temp_hyst, NULL, 1, 1),
1002 SENSOR_ATTR_2(temp3_auto_point3_temp_hyst, S_IRUGO,
1003 show_pwm_auto_point_temp_hyst, NULL, 2, 1),
1004 SENSOR_ATTR_2(temp3_auto_point4_temp_hyst, S_IRUGO,
1005 show_pwm_auto_point_temp_hyst, NULL, 3, 1),
1008 /* Super I/O functions */
1009 static inline int superio_inb(int base, int reg)
1011 outb(reg, base);
1012 return inb(base + 1);
1015 static int superio_inw(int base, int reg)
1017 int val;
1018 val = superio_inb(base, reg) << 8;
1019 val |= superio_inb(base, reg + 1);
1020 return val;
1023 static inline int superio_enter(int base)
1025 /* Don't step on other drivers' I/O space by accident */
1026 if (!request_muxed_region(base, 2, DRVNAME)) {
1027 pr_err("I/O address 0x%04x already in use\n", base);
1028 return -EBUSY;
1031 /* according to the datasheet the key must be send twice! */
1032 outb(SIO_UNLOCK_KEY, base);
1033 outb(SIO_UNLOCK_KEY, base);
1035 return 0;
1038 static inline void superio_select(int base, int ld)
1040 outb(SIO_REG_LDSEL, base);
1041 outb(ld, base + 1);
1044 static inline void superio_exit(int base)
1046 outb(SIO_LOCK_KEY, base);
1047 release_region(base, 2);
1050 static inline int fan_from_reg(u16 reg)
1052 return reg ? (1500000 / reg) : 0;
1055 static inline u16 fan_to_reg(int fan)
1057 return fan ? (1500000 / fan) : 0;
1060 static u8 f71882fg_read8(struct f71882fg_data *data, u8 reg)
1062 u8 val;
1064 outb(reg, data->addr + ADDR_REG_OFFSET);
1065 val = inb(data->addr + DATA_REG_OFFSET);
1067 return val;
1070 static u16 f71882fg_read16(struct f71882fg_data *data, u8 reg)
1072 u16 val;
1074 val = f71882fg_read8(data, reg) << 8;
1075 val |= f71882fg_read8(data, reg + 1);
1077 return val;
1080 static void f71882fg_write8(struct f71882fg_data *data, u8 reg, u8 val)
1082 outb(reg, data->addr + ADDR_REG_OFFSET);
1083 outb(val, data->addr + DATA_REG_OFFSET);
1086 static void f71882fg_write16(struct f71882fg_data *data, u8 reg, u16 val)
1088 f71882fg_write8(data, reg, val >> 8);
1089 f71882fg_write8(data, reg + 1, val & 0xff);
1092 static u16 f71882fg_read_temp(struct f71882fg_data *data, int nr)
1094 if (data->type == f71858fg)
1095 return f71882fg_read16(data, F71882FG_REG_TEMP(nr));
1096 else
1097 return f71882fg_read8(data, F71882FG_REG_TEMP(nr));
1100 static struct f71882fg_data *f71882fg_update_device(struct device *dev)
1102 struct f71882fg_data *data = dev_get_drvdata(dev);
1103 int nr_fans = f71882fg_nr_fans[data->type];
1104 int nr_temps = f71882fg_nr_temps[data->type];
1105 int nr, reg, point;
1107 mutex_lock(&data->update_lock);
1109 /* Update once every 60 seconds */
1110 if (time_after(jiffies, data->last_limits + 60 * HZ) ||
1111 !data->valid) {
1112 if (f71882fg_has_in1_alarm[data->type]) {
1113 data->in1_max =
1114 f71882fg_read8(data, F71882FG_REG_IN1_HIGH);
1115 data->in_beep =
1116 f71882fg_read8(data, F71882FG_REG_IN_BEEP);
1119 /* Get High & boundary temps*/
1120 for (nr = data->temp_start; nr < nr_temps + data->temp_start;
1121 nr++) {
1122 data->temp_ovt[nr] = f71882fg_read8(data,
1123 F71882FG_REG_TEMP_OVT(nr));
1124 data->temp_high[nr] = f71882fg_read8(data,
1125 F71882FG_REG_TEMP_HIGH(nr));
1128 if (data->type != f8000) {
1129 data->temp_hyst[0] = f71882fg_read8(data,
1130 F71882FG_REG_TEMP_HYST(0));
1131 data->temp_hyst[1] = f71882fg_read8(data,
1132 F71882FG_REG_TEMP_HYST(1));
1134 /* All but the f71858fg / f8000 have this register */
1135 if ((data->type != f71858fg) && (data->type != f8000)) {
1136 reg = f71882fg_read8(data, F71882FG_REG_TEMP_TYPE);
1137 data->temp_type[1] = (reg & 0x02) ? 2 : 4;
1138 data->temp_type[2] = (reg & 0x04) ? 2 : 4;
1139 data->temp_type[3] = (reg & 0x08) ? 2 : 4;
1142 if (f71882fg_has_beep[data->type]) {
1143 data->fan_beep = f71882fg_read8(data,
1144 F71882FG_REG_FAN_BEEP);
1145 data->temp_beep = f71882fg_read8(data,
1146 F71882FG_REG_TEMP_BEEP);
1149 data->pwm_enable = f71882fg_read8(data,
1150 F71882FG_REG_PWM_ENABLE);
1151 data->pwm_auto_point_hyst[0] =
1152 f71882fg_read8(data, F71882FG_REG_FAN_HYST(0));
1153 data->pwm_auto_point_hyst[1] =
1154 f71882fg_read8(data, F71882FG_REG_FAN_HYST(1));
1156 for (nr = 0; nr < nr_fans; nr++) {
1157 data->pwm_auto_point_mapping[nr] =
1158 f71882fg_read8(data,
1159 F71882FG_REG_POINT_MAPPING(nr));
1161 switch (data->type) {
1162 default:
1163 for (point = 0; point < 5; point++) {
1164 data->pwm_auto_point_pwm[nr][point] =
1165 f71882fg_read8(data,
1166 F71882FG_REG_POINT_PWM
1167 (nr, point));
1169 for (point = 0; point < 4; point++) {
1170 data->pwm_auto_point_temp[nr][point] =
1171 f71882fg_read8(data,
1172 F71882FG_REG_POINT_TEMP
1173 (nr, point));
1175 break;
1176 case f71808e:
1177 case f71869:
1178 data->pwm_auto_point_pwm[nr][0] =
1179 f71882fg_read8(data,
1180 F71882FG_REG_POINT_PWM(nr, 0));
1181 /* Fall through */
1182 case f71862fg:
1183 data->pwm_auto_point_pwm[nr][1] =
1184 f71882fg_read8(data,
1185 F71882FG_REG_POINT_PWM
1186 (nr, 1));
1187 data->pwm_auto_point_pwm[nr][4] =
1188 f71882fg_read8(data,
1189 F71882FG_REG_POINT_PWM
1190 (nr, 4));
1191 data->pwm_auto_point_temp[nr][0] =
1192 f71882fg_read8(data,
1193 F71882FG_REG_POINT_TEMP
1194 (nr, 0));
1195 data->pwm_auto_point_temp[nr][3] =
1196 f71882fg_read8(data,
1197 F71882FG_REG_POINT_TEMP
1198 (nr, 3));
1199 break;
1202 data->last_limits = jiffies;
1205 /* Update every second */
1206 if (time_after(jiffies, data->last_updated + HZ) || !data->valid) {
1207 data->temp_status = f71882fg_read8(data,
1208 F71882FG_REG_TEMP_STATUS);
1209 data->temp_diode_open = f71882fg_read8(data,
1210 F71882FG_REG_TEMP_DIODE_OPEN);
1211 for (nr = data->temp_start; nr < nr_temps + data->temp_start;
1212 nr++)
1213 data->temp[nr] = f71882fg_read_temp(data, nr);
1215 data->fan_status = f71882fg_read8(data,
1216 F71882FG_REG_FAN_STATUS);
1217 for (nr = 0; nr < nr_fans; nr++) {
1218 data->fan[nr] = f71882fg_read16(data,
1219 F71882FG_REG_FAN(nr));
1220 data->fan_target[nr] =
1221 f71882fg_read16(data, F71882FG_REG_FAN_TARGET(nr));
1222 data->fan_full_speed[nr] =
1223 f71882fg_read16(data,
1224 F71882FG_REG_FAN_FULL_SPEED(nr));
1225 data->pwm[nr] =
1226 f71882fg_read8(data, F71882FG_REG_PWM(nr));
1228 /* The f8000 can monitor 1 more fan, but has no pwm for it */
1229 if (data->type == f8000)
1230 data->fan[3] = f71882fg_read16(data,
1231 F71882FG_REG_FAN(3));
1233 if (f71882fg_has_in1_alarm[data->type])
1234 data->in_status = f71882fg_read8(data,
1235 F71882FG_REG_IN_STATUS);
1236 for (nr = 0; nr < F71882FG_MAX_INS; nr++)
1237 if (f71882fg_has_in[data->type][nr])
1238 data->in[nr] = f71882fg_read8(data,
1239 F71882FG_REG_IN(nr));
1241 data->last_updated = jiffies;
1242 data->valid = 1;
1245 mutex_unlock(&data->update_lock);
1247 return data;
1250 /* Sysfs Interface */
1251 static ssize_t show_fan(struct device *dev, struct device_attribute *devattr,
1252 char *buf)
1254 struct f71882fg_data *data = f71882fg_update_device(dev);
1255 int nr = to_sensor_dev_attr_2(devattr)->index;
1256 int speed = fan_from_reg(data->fan[nr]);
1258 if (speed == FAN_MIN_DETECT)
1259 speed = 0;
1261 return sprintf(buf, "%d\n", speed);
1264 static ssize_t show_fan_full_speed(struct device *dev,
1265 struct device_attribute *devattr, char *buf)
1267 struct f71882fg_data *data = f71882fg_update_device(dev);
1268 int nr = to_sensor_dev_attr_2(devattr)->index;
1269 int speed = fan_from_reg(data->fan_full_speed[nr]);
1270 return sprintf(buf, "%d\n", speed);
1273 static ssize_t store_fan_full_speed(struct device *dev,
1274 struct device_attribute *devattr,
1275 const char *buf, size_t count)
1277 struct f71882fg_data *data = dev_get_drvdata(dev);
1278 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1279 long val;
1281 err = strict_strtol(buf, 10, &val);
1282 if (err)
1283 return err;
1285 val = SENSORS_LIMIT(val, 23, 1500000);
1286 val = fan_to_reg(val);
1288 mutex_lock(&data->update_lock);
1289 f71882fg_write16(data, F71882FG_REG_FAN_FULL_SPEED(nr), val);
1290 data->fan_full_speed[nr] = val;
1291 mutex_unlock(&data->update_lock);
1293 return count;
1296 static ssize_t show_fan_beep(struct device *dev, struct device_attribute
1297 *devattr, char *buf)
1299 struct f71882fg_data *data = f71882fg_update_device(dev);
1300 int nr = to_sensor_dev_attr_2(devattr)->index;
1302 if (data->fan_beep & (1 << nr))
1303 return sprintf(buf, "1\n");
1304 else
1305 return sprintf(buf, "0\n");
1308 static ssize_t store_fan_beep(struct device *dev, struct device_attribute
1309 *devattr, const char *buf, size_t count)
1311 struct f71882fg_data *data = dev_get_drvdata(dev);
1312 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1313 unsigned long val;
1315 err = strict_strtoul(buf, 10, &val);
1316 if (err)
1317 return err;
1319 mutex_lock(&data->update_lock);
1320 data->fan_beep = f71882fg_read8(data, F71882FG_REG_FAN_BEEP);
1321 if (val)
1322 data->fan_beep |= 1 << nr;
1323 else
1324 data->fan_beep &= ~(1 << nr);
1326 f71882fg_write8(data, F71882FG_REG_FAN_BEEP, data->fan_beep);
1327 mutex_unlock(&data->update_lock);
1329 return count;
1332 static ssize_t show_fan_alarm(struct device *dev, struct device_attribute
1333 *devattr, char *buf)
1335 struct f71882fg_data *data = f71882fg_update_device(dev);
1336 int nr = to_sensor_dev_attr_2(devattr)->index;
1338 if (data->fan_status & (1 << nr))
1339 return sprintf(buf, "1\n");
1340 else
1341 return sprintf(buf, "0\n");
1344 static ssize_t show_in(struct device *dev, struct device_attribute *devattr,
1345 char *buf)
1347 struct f71882fg_data *data = f71882fg_update_device(dev);
1348 int nr = to_sensor_dev_attr_2(devattr)->index;
1350 return sprintf(buf, "%d\n", data->in[nr] * 8);
1353 static ssize_t show_in_max(struct device *dev, struct device_attribute
1354 *devattr, char *buf)
1356 struct f71882fg_data *data = f71882fg_update_device(dev);
1358 return sprintf(buf, "%d\n", data->in1_max * 8);
1361 static ssize_t store_in_max(struct device *dev, struct device_attribute
1362 *devattr, const char *buf, size_t count)
1364 struct f71882fg_data *data = dev_get_drvdata(dev);
1365 int err;
1366 long val;
1368 err = strict_strtol(buf, 10, &val);
1369 if (err)
1370 return err;
1372 val /= 8;
1373 val = SENSORS_LIMIT(val, 0, 255);
1375 mutex_lock(&data->update_lock);
1376 f71882fg_write8(data, F71882FG_REG_IN1_HIGH, val);
1377 data->in1_max = val;
1378 mutex_unlock(&data->update_lock);
1380 return count;
1383 static ssize_t show_in_beep(struct device *dev, struct device_attribute
1384 *devattr, char *buf)
1386 struct f71882fg_data *data = f71882fg_update_device(dev);
1387 int nr = to_sensor_dev_attr_2(devattr)->index;
1389 if (data->in_beep & (1 << nr))
1390 return sprintf(buf, "1\n");
1391 else
1392 return sprintf(buf, "0\n");
1395 static ssize_t store_in_beep(struct device *dev, struct device_attribute
1396 *devattr, const char *buf, size_t count)
1398 struct f71882fg_data *data = dev_get_drvdata(dev);
1399 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1400 unsigned long val;
1402 err = strict_strtoul(buf, 10, &val);
1403 if (err)
1404 return err;
1406 mutex_lock(&data->update_lock);
1407 data->in_beep = f71882fg_read8(data, F71882FG_REG_IN_BEEP);
1408 if (val)
1409 data->in_beep |= 1 << nr;
1410 else
1411 data->in_beep &= ~(1 << nr);
1413 f71882fg_write8(data, F71882FG_REG_IN_BEEP, data->in_beep);
1414 mutex_unlock(&data->update_lock);
1416 return count;
1419 static ssize_t show_in_alarm(struct device *dev, struct device_attribute
1420 *devattr, char *buf)
1422 struct f71882fg_data *data = f71882fg_update_device(dev);
1423 int nr = to_sensor_dev_attr_2(devattr)->index;
1425 if (data->in_status & (1 << nr))
1426 return sprintf(buf, "1\n");
1427 else
1428 return sprintf(buf, "0\n");
1431 static ssize_t show_temp(struct device *dev, struct device_attribute *devattr,
1432 char *buf)
1434 struct f71882fg_data *data = f71882fg_update_device(dev);
1435 int nr = to_sensor_dev_attr_2(devattr)->index;
1436 int sign, temp;
1438 if (data->type == f71858fg) {
1439 /* TEMP_TABLE_SEL 1 or 3 ? */
1440 if (data->temp_config & 1) {
1441 sign = data->temp[nr] & 0x0001;
1442 temp = (data->temp[nr] >> 5) & 0x7ff;
1443 } else {
1444 sign = data->temp[nr] & 0x8000;
1445 temp = (data->temp[nr] >> 5) & 0x3ff;
1447 temp *= 125;
1448 if (sign)
1449 temp -= 128000;
1450 } else
1451 temp = data->temp[nr] * 1000;
1453 return sprintf(buf, "%d\n", temp);
1456 static ssize_t show_temp_max(struct device *dev, struct device_attribute
1457 *devattr, char *buf)
1459 struct f71882fg_data *data = f71882fg_update_device(dev);
1460 int nr = to_sensor_dev_attr_2(devattr)->index;
1462 return sprintf(buf, "%d\n", data->temp_high[nr] * 1000);
1465 static ssize_t store_temp_max(struct device *dev, struct device_attribute
1466 *devattr, const char *buf, size_t count)
1468 struct f71882fg_data *data = dev_get_drvdata(dev);
1469 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1470 long val;
1472 err = strict_strtol(buf, 10, &val);
1473 if (err)
1474 return err;
1476 val /= 1000;
1477 val = SENSORS_LIMIT(val, 0, 255);
1479 mutex_lock(&data->update_lock);
1480 f71882fg_write8(data, F71882FG_REG_TEMP_HIGH(nr), val);
1481 data->temp_high[nr] = val;
1482 mutex_unlock(&data->update_lock);
1484 return count;
1487 static ssize_t show_temp_max_hyst(struct device *dev, struct device_attribute
1488 *devattr, char *buf)
1490 struct f71882fg_data *data = f71882fg_update_device(dev);
1491 int nr = to_sensor_dev_attr_2(devattr)->index;
1492 int temp_max_hyst;
1494 mutex_lock(&data->update_lock);
1495 if (nr & 1)
1496 temp_max_hyst = data->temp_hyst[nr / 2] >> 4;
1497 else
1498 temp_max_hyst = data->temp_hyst[nr / 2] & 0x0f;
1499 temp_max_hyst = (data->temp_high[nr] - temp_max_hyst) * 1000;
1500 mutex_unlock(&data->update_lock);
1502 return sprintf(buf, "%d\n", temp_max_hyst);
1505 static ssize_t store_temp_max_hyst(struct device *dev, struct device_attribute
1506 *devattr, const char *buf, size_t count)
1508 struct f71882fg_data *data = dev_get_drvdata(dev);
1509 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1510 ssize_t ret = count;
1511 u8 reg;
1512 long val;
1514 err = strict_strtol(buf, 10, &val);
1515 if (err)
1516 return err;
1518 val /= 1000;
1520 mutex_lock(&data->update_lock);
1522 /* convert abs to relative and check */
1523 data->temp_high[nr] = f71882fg_read8(data, F71882FG_REG_TEMP_HIGH(nr));
1524 val = SENSORS_LIMIT(val, data->temp_high[nr] - 15,
1525 data->temp_high[nr]);
1526 val = data->temp_high[nr] - val;
1528 /* convert value to register contents */
1529 reg = f71882fg_read8(data, F71882FG_REG_TEMP_HYST(nr / 2));
1530 if (nr & 1)
1531 reg = (reg & 0x0f) | (val << 4);
1532 else
1533 reg = (reg & 0xf0) | val;
1534 f71882fg_write8(data, F71882FG_REG_TEMP_HYST(nr / 2), reg);
1535 data->temp_hyst[nr / 2] = reg;
1537 mutex_unlock(&data->update_lock);
1538 return ret;
1541 static ssize_t show_temp_crit(struct device *dev, struct device_attribute
1542 *devattr, char *buf)
1544 struct f71882fg_data *data = f71882fg_update_device(dev);
1545 int nr = to_sensor_dev_attr_2(devattr)->index;
1547 return sprintf(buf, "%d\n", data->temp_ovt[nr] * 1000);
1550 static ssize_t store_temp_crit(struct device *dev, struct device_attribute
1551 *devattr, const char *buf, size_t count)
1553 struct f71882fg_data *data = dev_get_drvdata(dev);
1554 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1555 long val;
1557 err = strict_strtol(buf, 10, &val);
1558 if (err)
1559 return err;
1561 val /= 1000;
1562 val = SENSORS_LIMIT(val, 0, 255);
1564 mutex_lock(&data->update_lock);
1565 f71882fg_write8(data, F71882FG_REG_TEMP_OVT(nr), val);
1566 data->temp_ovt[nr] = val;
1567 mutex_unlock(&data->update_lock);
1569 return count;
1572 static ssize_t show_temp_crit_hyst(struct device *dev, struct device_attribute
1573 *devattr, char *buf)
1575 struct f71882fg_data *data = f71882fg_update_device(dev);
1576 int nr = to_sensor_dev_attr_2(devattr)->index;
1577 int temp_crit_hyst;
1579 mutex_lock(&data->update_lock);
1580 if (nr & 1)
1581 temp_crit_hyst = data->temp_hyst[nr / 2] >> 4;
1582 else
1583 temp_crit_hyst = data->temp_hyst[nr / 2] & 0x0f;
1584 temp_crit_hyst = (data->temp_ovt[nr] - temp_crit_hyst) * 1000;
1585 mutex_unlock(&data->update_lock);
1587 return sprintf(buf, "%d\n", temp_crit_hyst);
1590 static ssize_t show_temp_type(struct device *dev, struct device_attribute
1591 *devattr, char *buf)
1593 struct f71882fg_data *data = f71882fg_update_device(dev);
1594 int nr = to_sensor_dev_attr_2(devattr)->index;
1596 return sprintf(buf, "%d\n", data->temp_type[nr]);
1599 static ssize_t show_temp_beep(struct device *dev, struct device_attribute
1600 *devattr, char *buf)
1602 struct f71882fg_data *data = f71882fg_update_device(dev);
1603 int nr = to_sensor_dev_attr_2(devattr)->index;
1605 if (data->temp_beep & (1 << nr))
1606 return sprintf(buf, "1\n");
1607 else
1608 return sprintf(buf, "0\n");
1611 static ssize_t store_temp_beep(struct device *dev, struct device_attribute
1612 *devattr, const char *buf, size_t count)
1614 struct f71882fg_data *data = dev_get_drvdata(dev);
1615 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1616 unsigned long val;
1618 err = strict_strtoul(buf, 10, &val);
1619 if (err)
1620 return err;
1622 mutex_lock(&data->update_lock);
1623 data->temp_beep = f71882fg_read8(data, F71882FG_REG_TEMP_BEEP);
1624 if (val)
1625 data->temp_beep |= 1 << nr;
1626 else
1627 data->temp_beep &= ~(1 << nr);
1629 f71882fg_write8(data, F71882FG_REG_TEMP_BEEP, data->temp_beep);
1630 mutex_unlock(&data->update_lock);
1632 return count;
1635 static ssize_t show_temp_alarm(struct device *dev, struct device_attribute
1636 *devattr, char *buf)
1638 struct f71882fg_data *data = f71882fg_update_device(dev);
1639 int nr = to_sensor_dev_attr_2(devattr)->index;
1641 if (data->temp_status & (1 << nr))
1642 return sprintf(buf, "1\n");
1643 else
1644 return sprintf(buf, "0\n");
1647 static ssize_t show_temp_fault(struct device *dev, struct device_attribute
1648 *devattr, char *buf)
1650 struct f71882fg_data *data = f71882fg_update_device(dev);
1651 int nr = to_sensor_dev_attr_2(devattr)->index;
1653 if (data->temp_diode_open & (1 << nr))
1654 return sprintf(buf, "1\n");
1655 else
1656 return sprintf(buf, "0\n");
1659 static ssize_t show_pwm(struct device *dev,
1660 struct device_attribute *devattr, char *buf)
1662 struct f71882fg_data *data = f71882fg_update_device(dev);
1663 int val, nr = to_sensor_dev_attr_2(devattr)->index;
1664 mutex_lock(&data->update_lock);
1665 if (data->pwm_enable & (1 << (2 * nr)))
1666 /* PWM mode */
1667 val = data->pwm[nr];
1668 else {
1669 /* RPM mode */
1670 val = 255 * fan_from_reg(data->fan_target[nr])
1671 / fan_from_reg(data->fan_full_speed[nr]);
1673 mutex_unlock(&data->update_lock);
1674 return sprintf(buf, "%d\n", val);
1677 static ssize_t store_pwm(struct device *dev,
1678 struct device_attribute *devattr, const char *buf,
1679 size_t count)
1681 struct f71882fg_data *data = dev_get_drvdata(dev);
1682 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1683 long val;
1685 err = strict_strtol(buf, 10, &val);
1686 if (err)
1687 return err;
1689 val = SENSORS_LIMIT(val, 0, 255);
1691 mutex_lock(&data->update_lock);
1692 data->pwm_enable = f71882fg_read8(data, F71882FG_REG_PWM_ENABLE);
1693 if ((data->type == f8000 && ((data->pwm_enable >> 2 * nr) & 3) != 2) ||
1694 (data->type != f8000 && !((data->pwm_enable >> 2 * nr) & 2))) {
1695 count = -EROFS;
1696 goto leave;
1698 if (data->pwm_enable & (1 << (2 * nr))) {
1699 /* PWM mode */
1700 f71882fg_write8(data, F71882FG_REG_PWM(nr), val);
1701 data->pwm[nr] = val;
1702 } else {
1703 /* RPM mode */
1704 int target, full_speed;
1705 full_speed = f71882fg_read16(data,
1706 F71882FG_REG_FAN_FULL_SPEED(nr));
1707 target = fan_to_reg(val * fan_from_reg(full_speed) / 255);
1708 f71882fg_write16(data, F71882FG_REG_FAN_TARGET(nr), target);
1709 data->fan_target[nr] = target;
1710 data->fan_full_speed[nr] = full_speed;
1712 leave:
1713 mutex_unlock(&data->update_lock);
1715 return count;
1718 static ssize_t show_pwm_enable(struct device *dev,
1719 struct device_attribute *devattr, char *buf)
1721 int result = 0;
1722 struct f71882fg_data *data = f71882fg_update_device(dev);
1723 int nr = to_sensor_dev_attr_2(devattr)->index;
1725 switch ((data->pwm_enable >> 2 * nr) & 3) {
1726 case 0:
1727 case 1:
1728 result = 2; /* Normal auto mode */
1729 break;
1730 case 2:
1731 result = 1; /* Manual mode */
1732 break;
1733 case 3:
1734 if (data->type == f8000)
1735 result = 3; /* Thermostat mode */
1736 else
1737 result = 1; /* Manual mode */
1738 break;
1741 return sprintf(buf, "%d\n", result);
1744 static ssize_t store_pwm_enable(struct device *dev, struct device_attribute
1745 *devattr, const char *buf, size_t count)
1747 struct f71882fg_data *data = dev_get_drvdata(dev);
1748 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1749 long val;
1751 err = strict_strtol(buf, 10, &val);
1752 if (err)
1753 return err;
1755 /* Special case for F8000 pwm channel 3 which only does auto mode */
1756 if (data->type == f8000 && nr == 2 && val != 2)
1757 return -EINVAL;
1759 mutex_lock(&data->update_lock);
1760 data->pwm_enable = f71882fg_read8(data, F71882FG_REG_PWM_ENABLE);
1761 /* Special case for F8000 auto PWM mode / Thermostat mode */
1762 if (data->type == f8000 && ((data->pwm_enable >> 2 * nr) & 1)) {
1763 switch (val) {
1764 case 2:
1765 data->pwm_enable &= ~(2 << (2 * nr));
1766 break; /* Normal auto mode */
1767 case 3:
1768 data->pwm_enable |= 2 << (2 * nr);
1769 break; /* Thermostat mode */
1770 default:
1771 count = -EINVAL;
1772 goto leave;
1774 } else {
1775 switch (val) {
1776 case 1:
1777 /* The f71858fg does not support manual RPM mode */
1778 if (data->type == f71858fg &&
1779 ((data->pwm_enable >> (2 * nr)) & 1)) {
1780 count = -EINVAL;
1781 goto leave;
1783 data->pwm_enable |= 2 << (2 * nr);
1784 break; /* Manual */
1785 case 2:
1786 data->pwm_enable &= ~(2 << (2 * nr));
1787 break; /* Normal auto mode */
1788 default:
1789 count = -EINVAL;
1790 goto leave;
1793 f71882fg_write8(data, F71882FG_REG_PWM_ENABLE, data->pwm_enable);
1794 leave:
1795 mutex_unlock(&data->update_lock);
1797 return count;
1800 static ssize_t show_pwm_auto_point_pwm(struct device *dev,
1801 struct device_attribute *devattr,
1802 char *buf)
1804 int result;
1805 struct f71882fg_data *data = f71882fg_update_device(dev);
1806 int pwm = to_sensor_dev_attr_2(devattr)->index;
1807 int point = to_sensor_dev_attr_2(devattr)->nr;
1809 mutex_lock(&data->update_lock);
1810 if (data->pwm_enable & (1 << (2 * pwm))) {
1811 /* PWM mode */
1812 result = data->pwm_auto_point_pwm[pwm][point];
1813 } else {
1814 /* RPM mode */
1815 result = 32 * 255 / (32 + data->pwm_auto_point_pwm[pwm][point]);
1817 mutex_unlock(&data->update_lock);
1819 return sprintf(buf, "%d\n", result);
1822 static ssize_t store_pwm_auto_point_pwm(struct device *dev,
1823 struct device_attribute *devattr,
1824 const char *buf, size_t count)
1826 struct f71882fg_data *data = dev_get_drvdata(dev);
1827 int err, pwm = to_sensor_dev_attr_2(devattr)->index;
1828 int point = to_sensor_dev_attr_2(devattr)->nr;
1829 long val;
1831 err = strict_strtol(buf, 10, &val);
1832 if (err)
1833 return err;
1835 val = SENSORS_LIMIT(val, 0, 255);
1837 mutex_lock(&data->update_lock);
1838 data->pwm_enable = f71882fg_read8(data, F71882FG_REG_PWM_ENABLE);
1839 if (data->pwm_enable & (1 << (2 * pwm))) {
1840 /* PWM mode */
1841 } else {
1842 /* RPM mode */
1843 if (val < 29) /* Prevent negative numbers */
1844 val = 255;
1845 else
1846 val = (255 - val) * 32 / val;
1848 f71882fg_write8(data, F71882FG_REG_POINT_PWM(pwm, point), val);
1849 data->pwm_auto_point_pwm[pwm][point] = val;
1850 mutex_unlock(&data->update_lock);
1852 return count;
1855 static ssize_t show_pwm_auto_point_temp_hyst(struct device *dev,
1856 struct device_attribute *devattr,
1857 char *buf)
1859 int result = 0;
1860 struct f71882fg_data *data = f71882fg_update_device(dev);
1861 int nr = to_sensor_dev_attr_2(devattr)->index;
1862 int point = to_sensor_dev_attr_2(devattr)->nr;
1864 mutex_lock(&data->update_lock);
1865 if (nr & 1)
1866 result = data->pwm_auto_point_hyst[nr / 2] >> 4;
1867 else
1868 result = data->pwm_auto_point_hyst[nr / 2] & 0x0f;
1869 result = 1000 * (data->pwm_auto_point_temp[nr][point] - result);
1870 mutex_unlock(&data->update_lock);
1872 return sprintf(buf, "%d\n", result);
1875 static ssize_t store_pwm_auto_point_temp_hyst(struct device *dev,
1876 struct device_attribute *devattr,
1877 const char *buf, size_t count)
1879 struct f71882fg_data *data = dev_get_drvdata(dev);
1880 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1881 int point = to_sensor_dev_attr_2(devattr)->nr;
1882 u8 reg;
1883 long val;
1885 err = strict_strtol(buf, 10, &val);
1886 if (err)
1887 return err;
1889 val /= 1000;
1891 mutex_lock(&data->update_lock);
1892 data->pwm_auto_point_temp[nr][point] =
1893 f71882fg_read8(data, F71882FG_REG_POINT_TEMP(nr, point));
1894 val = SENSORS_LIMIT(val, data->pwm_auto_point_temp[nr][point] - 15,
1895 data->pwm_auto_point_temp[nr][point]);
1896 val = data->pwm_auto_point_temp[nr][point] - val;
1898 reg = f71882fg_read8(data, F71882FG_REG_FAN_HYST(nr / 2));
1899 if (nr & 1)
1900 reg = (reg & 0x0f) | (val << 4);
1901 else
1902 reg = (reg & 0xf0) | val;
1904 f71882fg_write8(data, F71882FG_REG_FAN_HYST(nr / 2), reg);
1905 data->pwm_auto_point_hyst[nr / 2] = reg;
1906 mutex_unlock(&data->update_lock);
1908 return count;
1911 static ssize_t show_pwm_interpolate(struct device *dev,
1912 struct device_attribute *devattr, char *buf)
1914 int result;
1915 struct f71882fg_data *data = f71882fg_update_device(dev);
1916 int nr = to_sensor_dev_attr_2(devattr)->index;
1918 result = (data->pwm_auto_point_mapping[nr] >> 4) & 1;
1920 return sprintf(buf, "%d\n", result);
1923 static ssize_t store_pwm_interpolate(struct device *dev,
1924 struct device_attribute *devattr,
1925 const char *buf, size_t count)
1927 struct f71882fg_data *data = dev_get_drvdata(dev);
1928 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1929 unsigned long val;
1931 err = strict_strtoul(buf, 10, &val);
1932 if (err)
1933 return err;
1935 mutex_lock(&data->update_lock);
1936 data->pwm_auto_point_mapping[nr] =
1937 f71882fg_read8(data, F71882FG_REG_POINT_MAPPING(nr));
1938 if (val)
1939 val = data->pwm_auto_point_mapping[nr] | (1 << 4);
1940 else
1941 val = data->pwm_auto_point_mapping[nr] & (~(1 << 4));
1942 f71882fg_write8(data, F71882FG_REG_POINT_MAPPING(nr), val);
1943 data->pwm_auto_point_mapping[nr] = val;
1944 mutex_unlock(&data->update_lock);
1946 return count;
1949 static ssize_t show_pwm_auto_point_channel(struct device *dev,
1950 struct device_attribute *devattr,
1951 char *buf)
1953 int result;
1954 struct f71882fg_data *data = f71882fg_update_device(dev);
1955 int nr = to_sensor_dev_attr_2(devattr)->index;
1957 result = 1 << ((data->pwm_auto_point_mapping[nr] & 3) -
1958 data->temp_start);
1960 return sprintf(buf, "%d\n", result);
1963 static ssize_t store_pwm_auto_point_channel(struct device *dev,
1964 struct device_attribute *devattr,
1965 const char *buf, size_t count)
1967 struct f71882fg_data *data = dev_get_drvdata(dev);
1968 int err, nr = to_sensor_dev_attr_2(devattr)->index;
1969 long val;
1971 err = strict_strtol(buf, 10, &val);
1972 if (err)
1973 return err;
1975 switch (val) {
1976 case 1:
1977 val = 0;
1978 break;
1979 case 2:
1980 val = 1;
1981 break;
1982 case 4:
1983 val = 2;
1984 break;
1985 default:
1986 return -EINVAL;
1988 val += data->temp_start;
1989 mutex_lock(&data->update_lock);
1990 data->pwm_auto_point_mapping[nr] =
1991 f71882fg_read8(data, F71882FG_REG_POINT_MAPPING(nr));
1992 val = (data->pwm_auto_point_mapping[nr] & 0xfc) | val;
1993 f71882fg_write8(data, F71882FG_REG_POINT_MAPPING(nr), val);
1994 data->pwm_auto_point_mapping[nr] = val;
1995 mutex_unlock(&data->update_lock);
1997 return count;
2000 static ssize_t show_pwm_auto_point_temp(struct device *dev,
2001 struct device_attribute *devattr,
2002 char *buf)
2004 int result;
2005 struct f71882fg_data *data = f71882fg_update_device(dev);
2006 int pwm = to_sensor_dev_attr_2(devattr)->index;
2007 int point = to_sensor_dev_attr_2(devattr)->nr;
2009 result = data->pwm_auto_point_temp[pwm][point];
2010 return sprintf(buf, "%d\n", 1000 * result);
2013 static ssize_t store_pwm_auto_point_temp(struct device *dev,
2014 struct device_attribute *devattr,
2015 const char *buf, size_t count)
2017 struct f71882fg_data *data = dev_get_drvdata(dev);
2018 int err, pwm = to_sensor_dev_attr_2(devattr)->index;
2019 int point = to_sensor_dev_attr_2(devattr)->nr;
2020 long val;
2022 err = strict_strtol(buf, 10, &val);
2023 if (err)
2024 return err;
2026 val /= 1000;
2028 if (data->auto_point_temp_signed)
2029 val = SENSORS_LIMIT(val, -128, 127);
2030 else
2031 val = SENSORS_LIMIT(val, 0, 127);
2033 mutex_lock(&data->update_lock);
2034 f71882fg_write8(data, F71882FG_REG_POINT_TEMP(pwm, point), val);
2035 data->pwm_auto_point_temp[pwm][point] = val;
2036 mutex_unlock(&data->update_lock);
2038 return count;
2041 static ssize_t show_name(struct device *dev, struct device_attribute *devattr,
2042 char *buf)
2044 struct f71882fg_data *data = dev_get_drvdata(dev);
2045 return sprintf(buf, "%s\n", f71882fg_names[data->type]);
2048 static int __devinit f71882fg_create_sysfs_files(struct platform_device *pdev,
2049 struct sensor_device_attribute_2 *attr, int count)
2051 int err, i;
2053 for (i = 0; i < count; i++) {
2054 err = device_create_file(&pdev->dev, &attr[i].dev_attr);
2055 if (err)
2056 return err;
2058 return 0;
2061 static void f71882fg_remove_sysfs_files(struct platform_device *pdev,
2062 struct sensor_device_attribute_2 *attr, int count)
2064 int i;
2066 for (i = 0; i < count; i++)
2067 device_remove_file(&pdev->dev, &attr[i].dev_attr);
2070 static int __devinit f71882fg_probe(struct platform_device *pdev)
2072 struct f71882fg_data *data;
2073 struct f71882fg_sio_data *sio_data = pdev->dev.platform_data;
2074 int nr_fans = f71882fg_nr_fans[sio_data->type];
2075 int nr_temps = f71882fg_nr_temps[sio_data->type];
2076 int err, i;
2077 u8 start_reg, reg;
2079 data = kzalloc(sizeof(struct f71882fg_data), GFP_KERNEL);
2080 if (!data)
2081 return -ENOMEM;
2083 data->addr = platform_get_resource(pdev, IORESOURCE_IO, 0)->start;
2084 data->type = sio_data->type;
2085 data->temp_start =
2086 (data->type == f71858fg || data->type == f8000) ? 0 : 1;
2087 mutex_init(&data->update_lock);
2088 platform_set_drvdata(pdev, data);
2090 start_reg = f71882fg_read8(data, F71882FG_REG_START);
2091 if (start_reg & 0x04) {
2092 dev_warn(&pdev->dev, "Hardware monitor is powered down\n");
2093 err = -ENODEV;
2094 goto exit_free;
2096 if (!(start_reg & 0x03)) {
2097 dev_warn(&pdev->dev, "Hardware monitoring not activated\n");
2098 err = -ENODEV;
2099 goto exit_free;
2102 /* Register sysfs interface files */
2103 err = device_create_file(&pdev->dev, &dev_attr_name);
2104 if (err)
2105 goto exit_unregister_sysfs;
2107 if (start_reg & 0x01) {
2108 switch (data->type) {
2109 case f71858fg:
2110 data->temp_config =
2111 f71882fg_read8(data, F71882FG_REG_TEMP_CONFIG);
2112 if (data->temp_config & 0x10)
2113 /* The f71858fg temperature alarms behave as
2114 the f8000 alarms in this mode */
2115 err = f71882fg_create_sysfs_files(pdev,
2116 f8000_temp_attr,
2117 ARRAY_SIZE(f8000_temp_attr));
2118 else
2119 err = f71882fg_create_sysfs_files(pdev,
2120 f71858fg_temp_attr,
2121 ARRAY_SIZE(f71858fg_temp_attr));
2122 break;
2123 case f8000:
2124 err = f71882fg_create_sysfs_files(pdev,
2125 f8000_temp_attr,
2126 ARRAY_SIZE(f8000_temp_attr));
2127 break;
2128 default:
2129 err = f71882fg_create_sysfs_files(pdev,
2130 &fxxxx_temp_attr[0][0],
2131 ARRAY_SIZE(fxxxx_temp_attr[0]) * nr_temps);
2133 if (err)
2134 goto exit_unregister_sysfs;
2136 if (f71882fg_has_beep[data->type]) {
2137 err = f71882fg_create_sysfs_files(pdev,
2138 &fxxxx_temp_beep_attr[0][0],
2139 ARRAY_SIZE(fxxxx_temp_beep_attr[0])
2140 * nr_temps);
2141 if (err)
2142 goto exit_unregister_sysfs;
2145 for (i = 0; i < F71882FG_MAX_INS; i++) {
2146 if (f71882fg_has_in[data->type][i]) {
2147 err = device_create_file(&pdev->dev,
2148 &fxxxx_in_attr[i].dev_attr);
2149 if (err)
2150 goto exit_unregister_sysfs;
2153 if (f71882fg_has_in1_alarm[data->type]) {
2154 err = f71882fg_create_sysfs_files(pdev,
2155 fxxxx_in1_alarm_attr,
2156 ARRAY_SIZE(fxxxx_in1_alarm_attr));
2157 if (err)
2158 goto exit_unregister_sysfs;
2162 if (start_reg & 0x02) {
2163 switch (data->type) {
2164 case f71808e:
2165 case f71869:
2166 /* These always have signed auto point temps */
2167 data->auto_point_temp_signed = 1;
2168 /* Fall through to select correct fan/pwm reg bank! */
2169 case f71889fg:
2170 case f71889ed:
2171 reg = f71882fg_read8(data, F71882FG_REG_FAN_FAULT_T);
2172 if (reg & F71882FG_FAN_NEG_TEMP_EN)
2173 data->auto_point_temp_signed = 1;
2174 /* Ensure banked pwm registers point to right bank */
2175 reg &= ~F71882FG_FAN_PROG_SEL;
2176 f71882fg_write8(data, F71882FG_REG_FAN_FAULT_T, reg);
2177 break;
2178 default:
2179 break;
2182 data->pwm_enable =
2183 f71882fg_read8(data, F71882FG_REG_PWM_ENABLE);
2185 /* Sanity check the pwm settings */
2186 switch (data->type) {
2187 case f71858fg:
2188 err = 0;
2189 for (i = 0; i < nr_fans; i++)
2190 if (((data->pwm_enable >> (i * 2)) & 3) == 3)
2191 err = 1;
2192 break;
2193 case f71862fg:
2194 err = (data->pwm_enable & 0x15) != 0x15;
2195 break;
2196 case f8000:
2197 err = data->pwm_enable & 0x20;
2198 break;
2199 default:
2200 err = 0;
2201 break;
2203 if (err) {
2204 dev_err(&pdev->dev,
2205 "Invalid (reserved) pwm settings: 0x%02x\n",
2206 (unsigned int)data->pwm_enable);
2207 err = -ENODEV;
2208 goto exit_unregister_sysfs;
2211 err = f71882fg_create_sysfs_files(pdev, &fxxxx_fan_attr[0][0],
2212 ARRAY_SIZE(fxxxx_fan_attr[0]) * nr_fans);
2213 if (err)
2214 goto exit_unregister_sysfs;
2216 if (f71882fg_has_beep[data->type]) {
2217 err = f71882fg_create_sysfs_files(pdev,
2218 fxxxx_fan_beep_attr, nr_fans);
2219 if (err)
2220 goto exit_unregister_sysfs;
2223 switch (data->type) {
2224 case f71808e:
2225 case f71869:
2226 case f71889fg:
2227 case f71889ed:
2228 for (i = 0; i < nr_fans; i++) {
2229 data->pwm_auto_point_mapping[i] =
2230 f71882fg_read8(data,
2231 F71882FG_REG_POINT_MAPPING(i));
2232 if ((data->pwm_auto_point_mapping[i] & 0x80) ||
2233 (data->pwm_auto_point_mapping[i] & 3) == 0)
2234 break;
2236 if (i != nr_fans) {
2237 dev_warn(&pdev->dev,
2238 "Auto pwm controlled by raw digital "
2239 "data, disabling pwm auto_point "
2240 "sysfs attributes\n");
2241 goto no_pwm_auto_point;
2243 break;
2244 default:
2245 break;
2248 switch (data->type) {
2249 case f71862fg:
2250 err = f71882fg_create_sysfs_files(pdev,
2251 f71862fg_auto_pwm_attr,
2252 ARRAY_SIZE(f71862fg_auto_pwm_attr));
2253 break;
2254 case f71808e:
2255 case f71869:
2256 err = f71882fg_create_sysfs_files(pdev,
2257 f71869_auto_pwm_attr,
2258 ARRAY_SIZE(f71869_auto_pwm_attr));
2259 break;
2260 case f8000:
2261 err = f71882fg_create_sysfs_files(pdev,
2262 f8000_fan_attr,
2263 ARRAY_SIZE(f8000_fan_attr));
2264 if (err)
2265 goto exit_unregister_sysfs;
2266 err = f71882fg_create_sysfs_files(pdev,
2267 f8000_auto_pwm_attr,
2268 ARRAY_SIZE(f8000_auto_pwm_attr));
2269 break;
2270 default:
2271 err = f71882fg_create_sysfs_files(pdev,
2272 &fxxxx_auto_pwm_attr[0][0],
2273 ARRAY_SIZE(fxxxx_auto_pwm_attr[0]) * nr_fans);
2275 if (err)
2276 goto exit_unregister_sysfs;
2278 no_pwm_auto_point:
2279 for (i = 0; i < nr_fans; i++)
2280 dev_info(&pdev->dev, "Fan: %d is in %s mode\n", i + 1,
2281 (data->pwm_enable & (1 << 2 * i)) ?
2282 "duty-cycle" : "RPM");
2285 data->hwmon_dev = hwmon_device_register(&pdev->dev);
2286 if (IS_ERR(data->hwmon_dev)) {
2287 err = PTR_ERR(data->hwmon_dev);
2288 data->hwmon_dev = NULL;
2289 goto exit_unregister_sysfs;
2292 return 0;
2294 exit_unregister_sysfs:
2295 f71882fg_remove(pdev); /* Will unregister the sysfs files for us */
2296 return err; /* f71882fg_remove() also frees our data */
2297 exit_free:
2298 kfree(data);
2299 return err;
2302 static int f71882fg_remove(struct platform_device *pdev)
2304 struct f71882fg_data *data = platform_get_drvdata(pdev);
2305 int nr_fans = f71882fg_nr_fans[data->type];
2306 int nr_temps = f71882fg_nr_temps[data->type];
2307 int i;
2308 u8 start_reg = f71882fg_read8(data, F71882FG_REG_START);
2310 if (data->hwmon_dev)
2311 hwmon_device_unregister(data->hwmon_dev);
2313 device_remove_file(&pdev->dev, &dev_attr_name);
2315 if (start_reg & 0x01) {
2316 switch (data->type) {
2317 case f71858fg:
2318 if (data->temp_config & 0x10)
2319 f71882fg_remove_sysfs_files(pdev,
2320 f8000_temp_attr,
2321 ARRAY_SIZE(f8000_temp_attr));
2322 else
2323 f71882fg_remove_sysfs_files(pdev,
2324 f71858fg_temp_attr,
2325 ARRAY_SIZE(f71858fg_temp_attr));
2326 break;
2327 case f8000:
2328 f71882fg_remove_sysfs_files(pdev,
2329 f8000_temp_attr,
2330 ARRAY_SIZE(f8000_temp_attr));
2331 break;
2332 default:
2333 f71882fg_remove_sysfs_files(pdev,
2334 &fxxxx_temp_attr[0][0],
2335 ARRAY_SIZE(fxxxx_temp_attr[0]) * nr_temps);
2337 if (f71882fg_has_beep[data->type]) {
2338 f71882fg_remove_sysfs_files(pdev,
2339 &fxxxx_temp_beep_attr[0][0],
2340 ARRAY_SIZE(fxxxx_temp_beep_attr[0]) * nr_temps);
2343 for (i = 0; i < F71882FG_MAX_INS; i++) {
2344 if (f71882fg_has_in[data->type][i]) {
2345 device_remove_file(&pdev->dev,
2346 &fxxxx_in_attr[i].dev_attr);
2349 if (f71882fg_has_in1_alarm[data->type]) {
2350 f71882fg_remove_sysfs_files(pdev,
2351 fxxxx_in1_alarm_attr,
2352 ARRAY_SIZE(fxxxx_in1_alarm_attr));
2356 if (start_reg & 0x02) {
2357 f71882fg_remove_sysfs_files(pdev, &fxxxx_fan_attr[0][0],
2358 ARRAY_SIZE(fxxxx_fan_attr[0]) * nr_fans);
2360 if (f71882fg_has_beep[data->type]) {
2361 f71882fg_remove_sysfs_files(pdev,
2362 fxxxx_fan_beep_attr, nr_fans);
2365 switch (data->type) {
2366 case f71862fg:
2367 f71882fg_remove_sysfs_files(pdev,
2368 f71862fg_auto_pwm_attr,
2369 ARRAY_SIZE(f71862fg_auto_pwm_attr));
2370 break;
2371 case f71808e:
2372 case f71869:
2373 f71882fg_remove_sysfs_files(pdev,
2374 f71869_auto_pwm_attr,
2375 ARRAY_SIZE(f71869_auto_pwm_attr));
2376 break;
2377 case f8000:
2378 f71882fg_remove_sysfs_files(pdev,
2379 f8000_fan_attr,
2380 ARRAY_SIZE(f8000_fan_attr));
2381 f71882fg_remove_sysfs_files(pdev,
2382 f8000_auto_pwm_attr,
2383 ARRAY_SIZE(f8000_auto_pwm_attr));
2384 break;
2385 default:
2386 f71882fg_remove_sysfs_files(pdev,
2387 &fxxxx_auto_pwm_attr[0][0],
2388 ARRAY_SIZE(fxxxx_auto_pwm_attr[0]) * nr_fans);
2392 platform_set_drvdata(pdev, NULL);
2393 kfree(data);
2395 return 0;
2398 static int __init f71882fg_find(int sioaddr, unsigned short *address,
2399 struct f71882fg_sio_data *sio_data)
2401 u16 devid;
2402 int err = superio_enter(sioaddr);
2403 if (err)
2404 return err;
2406 devid = superio_inw(sioaddr, SIO_REG_MANID);
2407 if (devid != SIO_FINTEK_ID) {
2408 pr_debug("Not a Fintek device\n");
2409 err = -ENODEV;
2410 goto exit;
2413 devid = force_id ? force_id : superio_inw(sioaddr, SIO_REG_DEVID);
2414 switch (devid) {
2415 case SIO_F71808E_ID:
2416 sio_data->type = f71808e;
2417 break;
2418 case SIO_F71858_ID:
2419 sio_data->type = f71858fg;
2420 break;
2421 case SIO_F71862_ID:
2422 sio_data->type = f71862fg;
2423 break;
2424 case SIO_F71869_ID:
2425 sio_data->type = f71869;
2426 break;
2427 case SIO_F71882_ID:
2428 sio_data->type = f71882fg;
2429 break;
2430 case SIO_F71889_ID:
2431 sio_data->type = f71889fg;
2432 break;
2433 case SIO_F71889E_ID:
2434 sio_data->type = f71889ed;
2435 break;
2436 case SIO_F8000_ID:
2437 sio_data->type = f8000;
2438 break;
2439 case SIO_F81865_ID:
2440 sio_data->type = f81865f;
2441 break;
2442 default:
2443 pr_info("Unsupported Fintek device: %04x\n",
2444 (unsigned int)devid);
2445 err = -ENODEV;
2446 goto exit;
2449 if (sio_data->type == f71858fg)
2450 superio_select(sioaddr, SIO_F71858FG_LD_HWM);
2451 else
2452 superio_select(sioaddr, SIO_F71882FG_LD_HWM);
2454 if (!(superio_inb(sioaddr, SIO_REG_ENABLE) & 0x01)) {
2455 pr_warn("Device not activated\n");
2456 err = -ENODEV;
2457 goto exit;
2460 *address = superio_inw(sioaddr, SIO_REG_ADDR);
2461 if (*address == 0) {
2462 pr_warn("Base address not set\n");
2463 err = -ENODEV;
2464 goto exit;
2466 *address &= ~(REGION_LENGTH - 1); /* Ignore 3 LSB */
2468 err = 0;
2469 pr_info("Found %s chip at %#x, revision %d\n",
2470 f71882fg_names[sio_data->type], (unsigned int)*address,
2471 (int)superio_inb(sioaddr, SIO_REG_DEVREV));
2472 exit:
2473 superio_exit(sioaddr);
2474 return err;
2477 static int __init f71882fg_device_add(unsigned short address,
2478 const struct f71882fg_sio_data *sio_data)
2480 struct resource res = {
2481 .start = address,
2482 .end = address + REGION_LENGTH - 1,
2483 .flags = IORESOURCE_IO,
2485 int err;
2487 f71882fg_pdev = platform_device_alloc(DRVNAME, address);
2488 if (!f71882fg_pdev)
2489 return -ENOMEM;
2491 res.name = f71882fg_pdev->name;
2492 err = acpi_check_resource_conflict(&res);
2493 if (err)
2494 goto exit_device_put;
2496 err = platform_device_add_resources(f71882fg_pdev, &res, 1);
2497 if (err) {
2498 pr_err("Device resource addition failed\n");
2499 goto exit_device_put;
2502 err = platform_device_add_data(f71882fg_pdev, sio_data,
2503 sizeof(struct f71882fg_sio_data));
2504 if (err) {
2505 pr_err("Platform data allocation failed\n");
2506 goto exit_device_put;
2509 err = platform_device_add(f71882fg_pdev);
2510 if (err) {
2511 pr_err("Device addition failed\n");
2512 goto exit_device_put;
2515 return 0;
2517 exit_device_put:
2518 platform_device_put(f71882fg_pdev);
2520 return err;
2523 static int __init f71882fg_init(void)
2525 int err = -ENODEV;
2526 unsigned short address;
2527 struct f71882fg_sio_data sio_data;
2529 memset(&sio_data, 0, sizeof(sio_data));
2531 if (f71882fg_find(0x2e, &address, &sio_data) &&
2532 f71882fg_find(0x4e, &address, &sio_data))
2533 goto exit;
2535 err = platform_driver_register(&f71882fg_driver);
2536 if (err)
2537 goto exit;
2539 err = f71882fg_device_add(address, &sio_data);
2540 if (err)
2541 goto exit_driver;
2543 return 0;
2545 exit_driver:
2546 platform_driver_unregister(&f71882fg_driver);
2547 exit:
2548 return err;
2551 static void __exit f71882fg_exit(void)
2553 platform_device_unregister(f71882fg_pdev);
2554 platform_driver_unregister(&f71882fg_driver);
2557 MODULE_DESCRIPTION("F71882FG Hardware Monitoring Driver");
2558 MODULE_AUTHOR("Hans Edgington, Hans de Goede (hdegoede@redhat.com)");
2559 MODULE_LICENSE("GPL");
2561 module_init(f71882fg_init);
2562 module_exit(f71882fg_exit);