2 via686a.c - Part of lm_sensors, Linux kernel modules
3 for hardware monitoring
5 Copyright (c) 1998 - 2002 Frodo Looijaard <frodol@dds.nl>,
6 Kyösti Mälkki <kmalkki@cc.hut.fi>,
7 Mark Studebaker <mdsxyz123@yahoo.com>,
8 and Bob Dougherty <bobd@stanford.edu>
9 (Some conversion-factor data were contributed by Jonathan Teh Soon Yew
10 <j.teh@iname.com> and Alex van Kaam <darkside@chello.nl>.)
12 This program is free software; you can redistribute it and/or modify
13 it under the terms of the GNU General Public License as published by
14 the Free Software Foundation; either version 2 of the License, or
15 (at your option) any later version.
17 This program is distributed in the hope that it will be useful,
18 but WITHOUT ANY WARRANTY; without even the implied warranty of
19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 GNU General Public License for more details.
22 You should have received a copy of the GNU General Public License
23 along with this program; if not, write to the Free Software
24 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
28 Supports the Via VT82C686A, VT82C686B south bridges.
29 Reports all as a 686A.
30 Warning - only supports a single device.
33 #include <linux/config.h>
34 #include <linux/module.h>
35 #include <linux/slab.h>
36 #include <linux/pci.h>
37 #include <linux/delay.h>
38 #include <linux/i2c.h>
39 #include <linux/i2c-sensor.h>
40 #include <linux/init.h>
44 /* If force_addr is set to anything different from 0, we forcibly enable
45 the device at the given address. */
46 static int force_addr = 0;
47 MODULE_PARM(force_addr, "i");
48 MODULE_PARM_DESC(force_addr,
49 "Initialize the base address of the sensors");
52 Note that we can't determine the ISA address until we have initialized
54 static unsigned short normal_i2c[] = { I2C_CLIENT_END };
55 static unsigned short normal_i2c_range[] = { I2C_CLIENT_END };
56 static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END };
57 static unsigned int normal_isa_range[] = { I2C_CLIENT_ISA_END };
59 /* Insmod parameters */
60 SENSORS_INSMOD_1(via686a);
63 The Via 686a southbridge has a LM78-like chip integrated on the same IC.
64 This driver is a customized copy of lm78.c
67 /* Many VIA686A constants specified below */
69 /* Length of ISA address segment */
70 #define VIA686A_EXTENT 0x80
71 #define VIA686A_BASE_REG 0x70
72 #define VIA686A_ENABLE_REG 0x74
74 /* The VIA686A registers */
75 /* ins numbered 0-4 */
76 #define VIA686A_REG_IN_MAX(nr) (0x2b + ((nr) * 2))
77 #define VIA686A_REG_IN_MIN(nr) (0x2c + ((nr) * 2))
78 #define VIA686A_REG_IN(nr) (0x22 + (nr))
80 /* fans numbered 1-2 */
81 #define VIA686A_REG_FAN_MIN(nr) (0x3a + (nr))
82 #define VIA686A_REG_FAN(nr) (0x28 + (nr))
84 /* the following values are as speced by VIA: */
85 static const u8 regtemp[] = { 0x20, 0x21, 0x1f };
86 static const u8 regover[] = { 0x39, 0x3d, 0x1d };
87 static const u8 reghyst[] = { 0x3a, 0x3e, 0x1e };
89 /* temps numbered 1-3 */
90 #define VIA686A_REG_TEMP(nr) (regtemp[nr])
91 #define VIA686A_REG_TEMP_OVER(nr) (regover[nr])
92 #define VIA686A_REG_TEMP_HYST(nr) (reghyst[nr])
93 #define VIA686A_REG_TEMP_LOW1 0x4b // bits 7-6
94 #define VIA686A_REG_TEMP_LOW23 0x49 // 2 = bits 5-4, 3 = bits 7-6
96 #define VIA686A_REG_ALARM1 0x41
97 #define VIA686A_REG_ALARM2 0x42
98 #define VIA686A_REG_FANDIV 0x47
99 #define VIA686A_REG_CONFIG 0x40
100 /* The following register sets temp interrupt mode (bits 1-0 for temp1,
101 3-2 for temp2, 5-4 for temp3). Modes are:
102 00 interrupt stays as long as value is out-of-range
103 01 interrupt is cleared once register is read (default)
104 10 comparator mode- like 00, but ignores hysteresis
106 #define VIA686A_REG_TEMP_MODE 0x4b
107 /* We'll just assume that you want to set all 3 simultaneously: */
108 #define VIA686A_TEMP_MODE_MASK 0x3F
109 #define VIA686A_TEMP_MODE_CONTINUOUS (0x00)
111 /* Conversions. Rounding and limit checking is only done on the TO_REG
114 ********* VOLTAGE CONVERSIONS (Bob Dougherty) ********
115 From HWMon.cpp (Copyright 1998-2000 Jonathan Teh Soon Yew):
116 voltagefactor[0]=1.25/2628; (2628/1.25=2102.4) // Vccp
117 voltagefactor[1]=1.25/2628; (2628/1.25=2102.4) // +2.5V
118 voltagefactor[2]=1.67/2628; (2628/1.67=1573.7) // +3.3V
119 voltagefactor[3]=2.6/2628; (2628/2.60=1010.8) // +5V
120 voltagefactor[4]=6.3/2628; (2628/6.30=417.14) // +12V
121 in[i]=(data[i+2]*25.0+133)*voltagefactor[i];
123 volts = (25*regVal+133)*factor
124 regVal = (volts/factor-133)/25
125 (These conversions were contributed by Jonathan Teh Soon Yew
128 These get us close, but they don't completely agree with what my BIOS
129 says- they are all a bit low. But, it all we have to go on... */
130 static inline u8 IN_TO_REG(long val, int inNum)
132 /* to avoid floating point, we multiply everything by 100.
133 val is guaranteed to be positive, so we can achieve the effect of
134 rounding by (...*10+5)/10. Note that the *10 is hidden in the
135 /250 (which should really be /2500).
136 At the end, we need to /100 because we *100 everything and we need
137 to /10 because of the rounding thing, so we /1000. */
140 SENSORS_LIMIT(((val * 210240 - 13300) / 250 + 5) / 1000,
144 SENSORS_LIMIT(((val * 157370 - 13300) / 250 + 5) / 1000,
148 SENSORS_LIMIT(((val * 101080 - 13300) / 250 + 5) / 1000,
151 return (u8) SENSORS_LIMIT(((val * 41714 - 13300) / 250 + 5)
155 static inline long IN_FROM_REG(u8 val, int inNum)
157 /* to avoid floating point, we multiply everything by 100.
158 val is guaranteed to be positive, so we can achieve the effect of
159 rounding by adding 0.5. Or, to avoid fp math, we do (...*10+5)/10.
160 We need to scale with *100 anyway, so no need to /100 at the end. */
162 return (long) (((250000 * val + 13300) / 210240 * 10 + 5) /10);
164 return (long) (((250000 * val + 13300) / 157370 * 10 + 5) /10);
166 return (long) (((250000 * val + 13300) / 101080 * 10 + 5) /10);
168 return (long) (((250000 * val + 13300) / 41714 * 10 + 5) /10);
171 /********* FAN RPM CONVERSIONS ********/
172 /* Higher register values = slower fans (the fan's strobe gates a counter).
173 But this chip saturates back at 0, not at 255 like all the other chips.
175 static inline u8 FAN_TO_REG(long rpm, int div)
179 rpm = SENSORS_LIMIT(rpm, 1, 1000000);
180 return SENSORS_LIMIT((1350000 + rpm * div / 2) / (rpm * div), 1, 255);
183 #define FAN_FROM_REG(val,div) ((val)==0?0:(val)==255?0:1350000/((val)*(div)))
185 /******** TEMP CONVERSIONS (Bob Dougherty) *********/
186 /* linear fits from HWMon.cpp (Copyright 1998-2000 Jonathan Teh Soon Yew)
188 return double(temp)*0.427-32.08;
189 else if(temp>=169 && temp<=202)
190 return double(temp)*0.582-58.16;
192 return double(temp)*0.924-127.33;
194 A fifth-order polynomial fits the unofficial data (provided by Alex van
195 Kaam <darkside@chello.nl>) a bit better. It also give more reasonable
196 numbers on my machine (ie. they agree with what my BIOS tells me).
197 Here's the fifth-order fit to the 8-bit data:
198 temp = 1.625093e-10*val^5 - 1.001632e-07*val^4 + 2.457653e-05*val^3 -
199 2.967619e-03*val^2 + 2.175144e-01*val - 7.090067e+0.
201 (2000-10-25- RFD: thanks to Uwe Andersen <uandersen@mayah.com> for
202 finding my typos in this formula!)
204 Alas, none of the elegant function-fit solutions will work because we
205 aren't allowed to use floating point in the kernel and doing it with
206 integers doesn't rpovide enough precision. So we'll do boring old
207 look-up table stuff. The unofficial data (see below) have effectively
208 7-bit resolution (they are rounded to the nearest degree). I'm assuming
209 that the transfer function of the device is monotonic and smooth, so a
210 smooth function fit to the data will allow us to get better precision.
211 I used the 5th-order poly fit described above and solved for
212 VIA register values 0-255. I *10 before rounding, so we get tenth-degree
213 precision. (I could have done all 1024 values for our 10-bit readings,
214 but the function is very linear in the useful range (0-80 deg C), so
215 we'll just use linear interpolation for 10-bit readings.) So, tempLUT
216 is the temp at via register values 0-255: */
217 static const long tempLUT[] =
218 { -709, -688, -667, -646, -627, -607, -589, -570, -553, -536, -519,
219 -503, -487, -471, -456, -442, -428, -414, -400, -387, -375,
220 -362, -350, -339, -327, -316, -305, -295, -285, -275, -265,
221 -255, -246, -237, -229, -220, -212, -204, -196, -188, -180,
222 -173, -166, -159, -152, -145, -139, -132, -126, -120, -114,
223 -108, -102, -96, -91, -85, -80, -74, -69, -64, -59, -54, -49,
224 -44, -39, -34, -29, -25, -20, -15, -11, -6, -2, 3, 7, 12, 16,
225 20, 25, 29, 33, 37, 42, 46, 50, 54, 59, 63, 67, 71, 75, 79, 84,
226 88, 92, 96, 100, 104, 109, 113, 117, 121, 125, 130, 134, 138,
227 142, 146, 151, 155, 159, 163, 168, 172, 176, 181, 185, 189,
228 193, 198, 202, 206, 211, 215, 219, 224, 228, 232, 237, 241,
229 245, 250, 254, 259, 263, 267, 272, 276, 281, 285, 290, 294,
230 299, 303, 307, 312, 316, 321, 325, 330, 334, 339, 344, 348,
231 353, 357, 362, 366, 371, 376, 380, 385, 390, 395, 399, 404,
232 409, 414, 419, 423, 428, 433, 438, 443, 449, 454, 459, 464,
233 469, 475, 480, 486, 491, 497, 502, 508, 514, 520, 526, 532,
234 538, 544, 551, 557, 564, 571, 578, 584, 592, 599, 606, 614,
235 621, 629, 637, 645, 654, 662, 671, 680, 689, 698, 708, 718,
236 728, 738, 749, 759, 770, 782, 793, 805, 818, 830, 843, 856,
237 870, 883, 898, 912, 927, 943, 958, 975, 991, 1008, 1026, 1044,
238 1062, 1081, 1101, 1121, 1141, 1162, 1184, 1206, 1229, 1252,
239 1276, 1301, 1326, 1352, 1378, 1406, 1434, 1462
242 /* the original LUT values from Alex van Kaam <darkside@chello.nl>
243 (for via register values 12-240):
244 {-50,-49,-47,-45,-43,-41,-39,-38,-37,-35,-34,-33,-32,-31,
245 -30,-29,-28,-27,-26,-25,-24,-24,-23,-22,-21,-20,-20,-19,-18,-17,-17,-16,-15,
246 -15,-14,-14,-13,-12,-12,-11,-11,-10,-9,-9,-8,-8,-7,-7,-6,-6,-5,-5,-4,-4,-3,
247 -3,-2,-2,-1,-1,0,0,1,1,1,3,3,3,4,4,4,5,5,5,6,6,7,7,8,8,9,9,9,10,10,11,11,12,
248 12,12,13,13,13,14,14,15,15,16,16,16,17,17,18,18,19,19,20,20,21,21,21,22,22,
249 22,23,23,24,24,25,25,26,26,26,27,27,27,28,28,29,29,30,30,30,31,31,32,32,33,
250 33,34,34,35,35,35,36,36,37,37,38,38,39,39,40,40,41,41,42,42,43,43,44,44,45,
251 45,46,46,47,48,48,49,49,50,51,51,52,52,53,53,54,55,55,56,57,57,58,59,59,60,
252 61,62,62,63,64,65,66,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,83,84,
253 85,86,88,89,91,92,94,96,97,99,101,103,105,107,109,110};
256 Here's the reverse LUT. I got it by doing a 6-th order poly fit (needed
257 an extra term for a good fit to these inverse data!) and then
258 solving for each temp value from -50 to 110 (the useable range for
259 this chip). Here's the fit:
260 viaRegVal = -1.160370e-10*val^6 +3.193693e-08*val^5 - 1.464447e-06*val^4
261 - 2.525453e-04*val^3 + 1.424593e-02*val^2 + 2.148941e+00*val +7.275808e+01)
263 static const u8 viaLUT[] =
264 { 12, 12, 13, 14, 14, 15, 16, 16, 17, 18, 18, 19, 20, 20, 21, 22, 23,
265 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 35, 36, 37, 39, 40,
266 41, 43, 45, 46, 48, 49, 51, 53, 55, 57, 59, 60, 62, 64, 66,
267 69, 71, 73, 75, 77, 79, 82, 84, 86, 88, 91, 93, 95, 98, 100,
268 103, 105, 107, 110, 112, 115, 117, 119, 122, 124, 126, 129,
269 131, 134, 136, 138, 140, 143, 145, 147, 150, 152, 154, 156,
270 158, 160, 162, 164, 166, 168, 170, 172, 174, 176, 178, 180,
271 182, 183, 185, 187, 188, 190, 192, 193, 195, 196, 198, 199,
272 200, 202, 203, 205, 206, 207, 208, 209, 210, 211, 212, 213,
273 214, 215, 216, 217, 218, 219, 220, 221, 222, 222, 223, 224,
274 225, 226, 226, 227, 228, 228, 229, 230, 230, 231, 232, 232,
275 233, 233, 234, 235, 235, 236, 236, 237, 237, 238, 238, 239,
279 /* Converting temps to (8-bit) hyst and over registers
280 No interpolation here. Just check the limits and go.
281 The +5 effectively rounds off properly and the +50 is because
282 the temps start at -50 */
283 static inline u8 TEMP_TO_REG(long val)
286 SENSORS_LIMIT(viaLUT[((val <= -500) ? 0 : (val >= 1100) ? 160 :
287 ((val + 5) / 10 + 50))], 0, 255);
290 /* for 8-bit temperature hyst and over registers
291 The temp values are already *10, so we don't need to do that.
292 But we _will_ round these off to the nearest degree with (...*10+5)/10 */
293 #define TEMP_FROM_REG(val) ((tempLUT[(val)]*10+5)/10)
295 /* for 10-bit temperature readings
296 You might _think_ this is too long to inline, but's it's really only
298 static inline long TEMP_FROM_REG10(u16 val)
300 /* the temp values are already *10, so we don't need to do that. */
302 u16 eightBits = val >> 2;
303 u16 twoBits = val & 3;
305 /* handle the extremes first (they won't interpolate well! ;-) */
307 return (long) tempLUT[0];
309 return (long) tempLUT[255];
312 return (long) tempLUT[eightBits];
314 /* do some interpolation by multipying the lower and upper
315 bounds by 25, 50 or 75, then /100. */
316 temp = ((25 * (4 - twoBits)) * tempLUT[eightBits]
317 + (25 * twoBits) * tempLUT[eightBits + 1]);
318 /* increase the magnitude by 50 to achieve rounding. */
327 #define ALARMS_FROM_REG(val) (val)
329 #define DIV_FROM_REG(val) (1 << (val))
330 #define DIV_TO_REG(val) ((val)==8?3:(val)==4?2:(val)==1?0:1)
332 /* For the VIA686A, we need to keep some data in memory.
333 The structure is dynamically allocated, at the same time when a new
334 via686a client is allocated. */
335 struct via686a_data {
336 struct i2c_client client;
337 struct semaphore update_lock;
338 char valid; /* !=0 if following fields are valid */
339 unsigned long last_updated; /* In jiffies */
341 u8 in[5]; /* Register value */
342 u8 in_max[5]; /* Register value */
343 u8 in_min[5]; /* Register value */
344 u8 fan[2]; /* Register value */
345 u8 fan_min[2]; /* Register value */
346 u16 temp[3]; /* Register value 10 bit */
347 u8 temp_over[3]; /* Register value */
348 u8 temp_hyst[3]; /* Register value */
349 u8 fan_div[2]; /* Register encoding, shifted right */
350 u16 alarms; /* Register encoding, combined */
353 static struct pci_dev *s_bridge; /* pointer to the (only) via686a */
355 static int via686a_attach_adapter(struct i2c_adapter *adapter);
356 static int via686a_detect(struct i2c_adapter *adapter, int address, int kind);
357 static int via686a_detach_client(struct i2c_client *client);
359 static inline int via686a_read_value(struct i2c_client *client, u8 reg)
361 return (inb_p(client->addr + reg));
364 static inline void via686a_write_value(struct i2c_client *client, u8 reg,
367 outb_p(value, client->addr + reg);
370 static struct via686a_data *via686a_update_device(struct device *dev);
371 static void via686a_init_client(struct i2c_client *client);
373 /* following are the sysfs callback functions */
375 /* 7 voltage sensors */
376 static ssize_t show_in(struct device *dev, char *buf, int nr) {
377 struct via686a_data *data = via686a_update_device(dev);
378 return sprintf(buf, "%ld\n", IN_FROM_REG(data->in[nr], nr)*10 );
381 static ssize_t show_in_min(struct device *dev, char *buf, int nr) {
382 struct via686a_data *data = via686a_update_device(dev);
383 return sprintf(buf, "%ld\n", IN_FROM_REG(data->in_min[nr], nr)*10 );
386 static ssize_t show_in_max(struct device *dev, char *buf, int nr) {
387 struct via686a_data *data = via686a_update_device(dev);
388 return sprintf(buf, "%ld\n", IN_FROM_REG(data->in_max[nr], nr)*10 );
391 static ssize_t set_in_min(struct device *dev, const char *buf,
392 size_t count, int nr) {
393 struct i2c_client *client = to_i2c_client(dev);
394 struct via686a_data *data = i2c_get_clientdata(client);
395 unsigned long val = simple_strtoul(buf, NULL, 10)/10;
396 data->in_min[nr] = IN_TO_REG(val,nr);
397 via686a_write_value(client, VIA686A_REG_IN_MIN(nr),
401 static ssize_t set_in_max(struct device *dev, const char *buf,
402 size_t count, int nr) {
403 struct i2c_client *client = to_i2c_client(dev);
404 struct via686a_data *data = i2c_get_clientdata(client);
405 unsigned long val = simple_strtoul(buf, NULL, 10)/10;
406 data->in_max[nr] = IN_TO_REG(val,nr);
407 via686a_write_value(client, VIA686A_REG_IN_MAX(nr),
411 #define show_in_offset(offset) \
413 show_in##offset (struct device *dev, char *buf) \
415 return show_in(dev, buf, 0x##offset); \
418 show_in##offset##_min (struct device *dev, char *buf) \
420 return show_in_min(dev, buf, 0x##offset); \
423 show_in##offset##_max (struct device *dev, char *buf) \
425 return show_in_max(dev, buf, 0x##offset); \
427 static ssize_t set_in##offset##_min (struct device *dev, \
428 const char *buf, size_t count) \
430 return set_in_min(dev, buf, count, 0x##offset); \
432 static ssize_t set_in##offset##_max (struct device *dev, \
433 const char *buf, size_t count) \
435 return set_in_max(dev, buf, count, 0x##offset); \
437 static DEVICE_ATTR(in##offset##_input, S_IRUGO, show_in##offset, NULL) \
438 static DEVICE_ATTR(in##offset##_min, S_IRUGO | S_IWUSR, \
439 show_in##offset##_min, set_in##offset##_min) \
440 static DEVICE_ATTR(in##offset##_max, S_IRUGO | S_IWUSR, \
441 show_in##offset##_max, set_in##offset##_max)
450 static ssize_t show_temp(struct device *dev, char *buf, int nr) {
451 struct via686a_data *data = via686a_update_device(dev);
452 return sprintf(buf, "%ld\n", TEMP_FROM_REG10(data->temp[nr])*100 );
454 static ssize_t show_temp_over(struct device *dev, char *buf, int nr) {
455 struct via686a_data *data = via686a_update_device(dev);
456 return sprintf(buf, "%ld\n", TEMP_FROM_REG(data->temp_over[nr])*100);
458 static ssize_t show_temp_hyst(struct device *dev, char *buf, int nr) {
459 struct via686a_data *data = via686a_update_device(dev);
460 return sprintf(buf, "%ld\n", TEMP_FROM_REG(data->temp_hyst[nr])*100);
462 static ssize_t set_temp_over(struct device *dev, const char *buf,
463 size_t count, int nr) {
464 struct i2c_client *client = to_i2c_client(dev);
465 struct via686a_data *data = i2c_get_clientdata(client);
466 int val = simple_strtol(buf, NULL, 10)/100;
467 data->temp_over[nr] = TEMP_TO_REG(val);
468 via686a_write_value(client, VIA686A_REG_TEMP_OVER(nr), data->temp_over[nr]);
471 static ssize_t set_temp_hyst(struct device *dev, const char *buf,
472 size_t count, int nr) {
473 struct i2c_client *client = to_i2c_client(dev);
474 struct via686a_data *data = i2c_get_clientdata(client);
475 int val = simple_strtol(buf, NULL, 10)/100;
476 data->temp_hyst[nr] = TEMP_TO_REG(val);
477 via686a_write_value(client, VIA686A_REG_TEMP_HYST(nr), data->temp_hyst[nr]);
480 #define show_temp_offset(offset) \
481 static ssize_t show_temp_##offset (struct device *dev, char *buf) \
483 return show_temp(dev, buf, 0x##offset - 1); \
486 show_temp_##offset##_over (struct device *dev, char *buf) \
488 return show_temp_over(dev, buf, 0x##offset - 1); \
491 show_temp_##offset##_hyst (struct device *dev, char *buf) \
493 return show_temp_hyst(dev, buf, 0x##offset - 1); \
495 static ssize_t set_temp_##offset##_over (struct device *dev, \
496 const char *buf, size_t count) \
498 return set_temp_over(dev, buf, count, 0x##offset - 1); \
500 static ssize_t set_temp_##offset##_hyst (struct device *dev, \
501 const char *buf, size_t count) \
503 return set_temp_hyst(dev, buf, count, 0x##offset - 1); \
505 static DEVICE_ATTR(temp##offset##_input, S_IRUGO, show_temp_##offset, NULL) \
506 static DEVICE_ATTR(temp##offset##_max, S_IRUGO | S_IWUSR, \
507 show_temp_##offset##_over, set_temp_##offset##_over) \
508 static DEVICE_ATTR(temp##offset##_max_hyst, S_IRUGO | S_IWUSR, \
509 show_temp_##offset##_hyst, set_temp_##offset##_hyst)
516 static ssize_t show_fan(struct device *dev, char *buf, int nr) {
517 struct via686a_data *data = via686a_update_device(dev);
518 return sprintf(buf,"%d\n", FAN_FROM_REG(data->fan[nr],
519 DIV_FROM_REG(data->fan_div[nr])) );
521 static ssize_t show_fan_min(struct device *dev, char *buf, int nr) {
522 struct via686a_data *data = via686a_update_device(dev);
523 return sprintf(buf,"%d\n",
524 FAN_FROM_REG(data->fan_min[nr], DIV_FROM_REG(data->fan_div[nr])) );
526 static ssize_t show_fan_div(struct device *dev, char *buf, int nr) {
527 struct via686a_data *data = via686a_update_device(dev);
528 return sprintf(buf,"%d\n", DIV_FROM_REG(data->fan_div[nr]) );
530 static ssize_t set_fan_min(struct device *dev, const char *buf,
531 size_t count, int nr) {
532 struct i2c_client *client = to_i2c_client(dev);
533 struct via686a_data *data = i2c_get_clientdata(client);
534 int val = simple_strtol(buf, NULL, 10);
535 data->fan_min[nr] = FAN_TO_REG(val, DIV_FROM_REG(data->fan_div[nr]));
536 via686a_write_value(client, VIA686A_REG_FAN_MIN(nr+1), data->fan_min[nr]);
539 static ssize_t set_fan_div(struct device *dev, const char *buf,
540 size_t count, int nr) {
541 struct i2c_client *client = to_i2c_client(dev);
542 struct via686a_data *data = i2c_get_clientdata(client);
543 int val = simple_strtol(buf, NULL, 10);
544 int old = via686a_read_value(client, VIA686A_REG_FANDIV);
545 data->fan_div[nr] = DIV_TO_REG(val);
546 old = (old & 0x0f) | (data->fan_div[1] << 6) | (data->fan_div[0] << 4);
547 via686a_write_value(client, VIA686A_REG_FANDIV, old);
551 #define show_fan_offset(offset) \
552 static ssize_t show_fan_##offset (struct device *dev, char *buf) \
554 return show_fan(dev, buf, 0x##offset - 1); \
556 static ssize_t show_fan_##offset##_min (struct device *dev, char *buf) \
558 return show_fan_min(dev, buf, 0x##offset - 1); \
560 static ssize_t show_fan_##offset##_div (struct device *dev, char *buf) \
562 return show_fan_div(dev, buf, 0x##offset - 1); \
564 static ssize_t set_fan_##offset##_min (struct device *dev, \
565 const char *buf, size_t count) \
567 return set_fan_min(dev, buf, count, 0x##offset - 1); \
569 static ssize_t set_fan_##offset##_div (struct device *dev, \
570 const char *buf, size_t count) \
572 return set_fan_div(dev, buf, count, 0x##offset - 1); \
574 static DEVICE_ATTR(fan##offset##_input, S_IRUGO, show_fan_##offset, NULL) \
575 static DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \
576 show_fan_##offset##_min, set_fan_##offset##_min) \
577 static DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \
578 show_fan_##offset##_div, set_fan_##offset##_div)
584 static ssize_t show_alarms(struct device *dev, char *buf) {
585 struct via686a_data *data = via686a_update_device(dev);
586 return sprintf(buf,"%d\n", ALARMS_FROM_REG(data->alarms));
588 static DEVICE_ATTR(alarms, S_IRUGO | S_IWUSR, show_alarms, NULL);
590 /* The driver. I choose to use type i2c_driver, as at is identical to both
591 smbus_driver and isa_driver, and clients could be of either kind */
592 static struct i2c_driver via686a_driver = {
593 .owner = THIS_MODULE,
595 .id = I2C_DRIVERID_VIA686A,
596 .flags = I2C_DF_NOTIFY,
597 .attach_adapter = via686a_attach_adapter,
598 .detach_client = via686a_detach_client,
602 /* This is called when the module is loaded */
603 static int via686a_attach_adapter(struct i2c_adapter *adapter)
605 if (!(adapter->class & I2C_ADAP_CLASS_SMBUS))
607 return i2c_detect(adapter, &addr_data, via686a_detect);
610 static int via686a_detect(struct i2c_adapter *adapter, int address, int kind)
612 struct i2c_client *new_client;
613 struct via686a_data *data;
615 const char client_name[] = "via686a";
618 /* Make sure we are probing the ISA bus!! */
619 if (!i2c_is_isa_adapter(adapter)) {
620 dev_err(&adapter->dev,
621 "via686a_detect called for an I2C bus adapter?!?\n");
625 /* 8231 requires multiple of 256, we enforce that on 686 as well */
627 address = force_addr & 0xFF00;
630 dev_warn(&adapter->dev,"forcing ISA address 0x%04X\n", address);
631 if (PCIBIOS_SUCCESSFUL !=
632 pci_write_config_word(s_bridge, VIA686A_BASE_REG, address))
635 if (PCIBIOS_SUCCESSFUL !=
636 pci_read_config_word(s_bridge, VIA686A_ENABLE_REG, &val))
638 if (!(val & 0x0001)) {
639 dev_warn(&adapter->dev,"enabling sensors\n");
640 if (PCIBIOS_SUCCESSFUL !=
641 pci_write_config_word(s_bridge, VIA686A_ENABLE_REG,
646 /* Reserve the ISA region */
647 if (!request_region(address, VIA686A_EXTENT, "via686a-sensor")) {
648 dev_err(&adapter->dev,"region 0x%x already in use!\n",
653 if (!(data = kmalloc(sizeof(struct via686a_data), GFP_KERNEL))) {
657 memset(data, 0, sizeof(struct via686a_data));
659 new_client = &data->client;
660 i2c_set_clientdata(new_client, data);
661 new_client->addr = address;
662 new_client->adapter = adapter;
663 new_client->driver = &via686a_driver;
664 new_client->flags = 0;
665 new_client->dev.parent = &adapter->dev;
667 /* Fill in the remaining client fields and put into the global list */
668 snprintf(new_client->name, I2C_NAME_SIZE, client_name);
671 init_MUTEX(&data->update_lock);
672 /* Tell the I2C layer a new client has arrived */
673 if ((err = i2c_attach_client(new_client)))
676 /* Initialize the VIA686A chip */
677 via686a_init_client(new_client);
679 /* Register sysfs hooks */
680 device_create_file(&new_client->dev, &dev_attr_in0_input);
681 device_create_file(&new_client->dev, &dev_attr_in1_input);
682 device_create_file(&new_client->dev, &dev_attr_in2_input);
683 device_create_file(&new_client->dev, &dev_attr_in3_input);
684 device_create_file(&new_client->dev, &dev_attr_in4_input);
685 device_create_file(&new_client->dev, &dev_attr_in0_min);
686 device_create_file(&new_client->dev, &dev_attr_in1_min);
687 device_create_file(&new_client->dev, &dev_attr_in2_min);
688 device_create_file(&new_client->dev, &dev_attr_in3_min);
689 device_create_file(&new_client->dev, &dev_attr_in4_min);
690 device_create_file(&new_client->dev, &dev_attr_in0_max);
691 device_create_file(&new_client->dev, &dev_attr_in1_max);
692 device_create_file(&new_client->dev, &dev_attr_in2_max);
693 device_create_file(&new_client->dev, &dev_attr_in3_max);
694 device_create_file(&new_client->dev, &dev_attr_in4_max);
695 device_create_file(&new_client->dev, &dev_attr_temp1_input);
696 device_create_file(&new_client->dev, &dev_attr_temp2_input);
697 device_create_file(&new_client->dev, &dev_attr_temp3_input);
698 device_create_file(&new_client->dev, &dev_attr_temp1_max);
699 device_create_file(&new_client->dev, &dev_attr_temp2_max);
700 device_create_file(&new_client->dev, &dev_attr_temp3_max);
701 device_create_file(&new_client->dev, &dev_attr_temp1_max_hyst);
702 device_create_file(&new_client->dev, &dev_attr_temp2_max_hyst);
703 device_create_file(&new_client->dev, &dev_attr_temp3_max_hyst);
704 device_create_file(&new_client->dev, &dev_attr_fan1_input);
705 device_create_file(&new_client->dev, &dev_attr_fan2_input);
706 device_create_file(&new_client->dev, &dev_attr_fan1_min);
707 device_create_file(&new_client->dev, &dev_attr_fan2_min);
708 device_create_file(&new_client->dev, &dev_attr_fan1_div);
709 device_create_file(&new_client->dev, &dev_attr_fan2_div);
710 device_create_file(&new_client->dev, &dev_attr_alarms);
717 release_region(address, VIA686A_EXTENT);
721 static int via686a_detach_client(struct i2c_client *client)
725 if ((err = i2c_detach_client(client))) {
726 dev_err(&client->dev,
727 "Client deregistration failed, client not detached.\n");
731 release_region(client->addr, VIA686A_EXTENT);
732 kfree(i2c_get_clientdata(client));
737 /* Called when we have found a new VIA686A. Set limits, etc. */
738 static void via686a_init_client(struct i2c_client *client)
742 /* Start monitoring */
743 reg = via686a_read_value(client, VIA686A_REG_CONFIG);
744 via686a_write_value(client, VIA686A_REG_CONFIG, (reg|0x01)&0x7F);
746 /* Configure temp interrupt mode for continuous-interrupt operation */
747 via686a_write_value(client, VIA686A_REG_TEMP_MODE,
748 via686a_read_value(client, VIA686A_REG_TEMP_MODE) &
749 !(VIA686A_TEMP_MODE_MASK | VIA686A_TEMP_MODE_CONTINUOUS));
752 static struct via686a_data *via686a_update_device(struct device *dev)
754 struct i2c_client *client = to_i2c_client(dev);
755 struct via686a_data *data = i2c_get_clientdata(client);
758 down(&data->update_lock);
760 if ((jiffies - data->last_updated > HZ + HZ / 2) ||
761 (jiffies < data->last_updated) || !data->valid) {
763 for (i = 0; i <= 4; i++) {
765 via686a_read_value(client, VIA686A_REG_IN(i));
766 data->in_min[i] = via686a_read_value(client,
770 via686a_read_value(client, VIA686A_REG_IN_MAX(i));
772 for (i = 1; i <= 2; i++) {
774 via686a_read_value(client, VIA686A_REG_FAN(i));
775 data->fan_min[i - 1] = via686a_read_value(client,
776 VIA686A_REG_FAN_MIN(i));
778 for (i = 0; i <= 2; i++) {
779 data->temp[i] = via686a_read_value(client,
780 VIA686A_REG_TEMP(i)) << 2;
782 via686a_read_value(client,
783 VIA686A_REG_TEMP_OVER(i));
785 via686a_read_value(client,
786 VIA686A_REG_TEMP_HYST(i));
788 /* add in lower 2 bits
789 temp1 uses bits 7-6 of VIA686A_REG_TEMP_LOW1
790 temp2 uses bits 5-4 of VIA686A_REG_TEMP_LOW23
791 temp3 uses bits 7-6 of VIA686A_REG_TEMP_LOW23
793 data->temp[0] |= (via686a_read_value(client,
794 VIA686A_REG_TEMP_LOW1)
797 (via686a_read_value(client, VIA686A_REG_TEMP_LOW23) &
800 (via686a_read_value(client, VIA686A_REG_TEMP_LOW23) &
803 i = via686a_read_value(client, VIA686A_REG_FANDIV);
804 data->fan_div[0] = (i >> 4) & 0x03;
805 data->fan_div[1] = i >> 6;
807 via686a_read_value(client,
808 VIA686A_REG_ALARM1) |
809 (via686a_read_value(client, VIA686A_REG_ALARM2) << 8);
810 data->last_updated = jiffies;
814 up(&data->update_lock);
819 static struct pci_device_id via686a_pci_ids[] = {
821 .vendor = PCI_VENDOR_ID_VIA,
822 .device = PCI_DEVICE_ID_VIA_82C686_4,
823 .subvendor = PCI_ANY_ID,
824 .subdevice = PCI_ANY_ID,
829 static int __devinit via686a_pci_probe(struct pci_dev *dev,
830 const struct pci_device_id *id)
835 if (PCIBIOS_SUCCESSFUL !=
836 pci_read_config_word(dev, VIA686A_BASE_REG, &val))
839 addr = val & ~(VIA686A_EXTENT - 1);
840 if (addr == 0 && force_addr == 0) {
841 dev_err(&dev->dev,"base address not set - upgrade BIOS or use force_addr=0xaddr\n");
845 addr = force_addr; /* so detect will get called */
848 dev_err(&dev->dev,"No Via 686A sensors found.\n");
851 normal_isa[0] = addr;
853 return i2c_add_driver(&via686a_driver);
856 static void __devexit via686a_pci_remove(struct pci_dev *dev)
858 i2c_del_driver(&via686a_driver);
861 static struct pci_driver via686a_pci_driver = {
863 .id_table = via686a_pci_ids,
864 .probe = via686a_pci_probe,
865 .remove = __devexit_p(via686a_pci_remove),
868 static int __init sm_via686a_init(void)
870 return pci_module_init(&via686a_pci_driver);
873 static void __exit sm_via686a_exit(void)
875 pci_unregister_driver(&via686a_pci_driver);
878 MODULE_AUTHOR("Kyösti Mälkki <kmalkki@cc.hut.fi>, "
879 "Mark Studebaker <mdsxyz123@yahoo.com> "
880 "and Bob Dougherty <bobd@stanford.edu>");
881 MODULE_DESCRIPTION("VIA 686A Sensor device");
882 MODULE_LICENSE("GPL");
884 module_init(sm_via686a_init);
885 module_exit(sm_via686a_exit);