via686a.c (dca3a783400a18e2bf4503b1d4a85c4d0ca1a7e4) via686a.c (088ce2ac9ebac5c74faf4d39083627875fa6f0f0)
1/*
2 * via686a.c - Part of lm_sensors, Linux kernel modules
3 * for hardware monitoring
4 *
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>

--- 111 unchanged lines hidden (view full) ---

120 * voltagefactor[4]=6.3/2628; (2628/6.30=417.14) // +12V
121 * in[i]=(data[i+2]*25.0+133)*voltagefactor[i];
122 * That is:
123 * volts = (25*regVal+133)*factor
124 * regVal = (volts/factor-133)/25
125 * (These conversions were contributed by Jonathan Teh Soon Yew
126 * <j.teh@iname.com>)
127 */
1/*
2 * via686a.c - Part of lm_sensors, Linux kernel modules
3 * for hardware monitoring
4 *
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>

--- 111 unchanged lines hidden (view full) ---

120 * voltagefactor[4]=6.3/2628; (2628/6.30=417.14) // +12V
121 * in[i]=(data[i+2]*25.0+133)*voltagefactor[i];
122 * That is:
123 * volts = (25*regVal+133)*factor
124 * regVal = (volts/factor-133)/25
125 * (These conversions were contributed by Jonathan Teh Soon Yew
126 * <j.teh@iname.com>)
127 */
128static inline u8 IN_TO_REG(long val, int inNum)
128static inline u8 IN_TO_REG(long val, int in_num)
129{
130 /*
131 * To avoid floating point, we multiply constants by 10 (100 for +12V).
132 * Rounding is done (120500 is actually 133000 - 12500).
133 * Remember that val is expressed in 0.001V/bit, which is why we divide
134 * by an additional 10000 (100000 for +12V): 1000 for val and 10 (100)
135 * for the constants.
136 */
129{
130 /*
131 * To avoid floating point, we multiply constants by 10 (100 for +12V).
132 * Rounding is done (120500 is actually 133000 - 12500).
133 * Remember that val is expressed in 0.001V/bit, which is why we divide
134 * by an additional 10000 (100000 for +12V): 1000 for val and 10 (100)
135 * for the constants.
136 */
137 if (inNum <= 1)
137 if (in_num <= 1)
138 return (u8) clamp_val((val * 21024 - 1205000) / 250000, 0, 255);
138 return (u8) clamp_val((val * 21024 - 1205000) / 250000, 0, 255);
139 else if (inNum == 2)
139 else if (in_num == 2)
140 return (u8) clamp_val((val * 15737 - 1205000) / 250000, 0, 255);
140 return (u8) clamp_val((val * 15737 - 1205000) / 250000, 0, 255);
141 else if (inNum == 3)
141 else if (in_num == 3)
142 return (u8) clamp_val((val * 10108 - 1205000) / 250000, 0, 255);
143 else
144 return (u8) clamp_val((val * 41714 - 12050000) / 2500000, 0,
145 255);
146}
147
142 return (u8) clamp_val((val * 10108 - 1205000) / 250000, 0, 255);
143 else
144 return (u8) clamp_val((val * 41714 - 12050000) / 2500000, 0,
145 255);
146}
147
148static inline long IN_FROM_REG(u8 val, int inNum)
148static inline long IN_FROM_REG(u8 val, int in_num)
149{
150 /*
151 * To avoid floating point, we multiply constants by 10 (100 for +12V).
152 * We also multiply them by 1000 because we want 0.001V/bit for the
153 * output value. Rounding is done.
154 */
149{
150 /*
151 * To avoid floating point, we multiply constants by 10 (100 for +12V).
152 * We also multiply them by 1000 because we want 0.001V/bit for the
153 * output value. Rounding is done.
154 */
155 if (inNum <= 1)
155 if (in_num <= 1)
156 return (long) ((250000 * val + 1330000 + 21024 / 2) / 21024);
156 return (long) ((250000 * val + 1330000 + 21024 / 2) / 21024);
157 else if (inNum == 2)
157 else if (in_num == 2)
158 return (long) ((250000 * val + 1330000 + 15737 / 2) / 15737);
158 return (long) ((250000 * val + 1330000 + 15737 / 2) / 15737);
159 else if (inNum == 3)
159 else if (in_num == 3)
160 return (long) ((250000 * val + 1330000 + 10108 / 2) / 10108);
161 else
162 return (long) ((2500000 * val + 13300000 + 41714 / 2) / 41714);
163}
164
165/********* FAN RPM CONVERSIONS ********/
166/*
167 * Higher register values = slower fans (the fan's strobe gates a counter).

--- 37 unchanged lines hidden (view full) ---

205 * look-up table stuff. The unofficial data (see below) have effectively
206 * 7-bit resolution (they are rounded to the nearest degree). I'm assuming
207 * that the transfer function of the device is monotonic and smooth, so a
208 * smooth function fit to the data will allow us to get better precision.
209 * I used the 5th-order poly fit described above and solved for
210 * VIA register values 0-255. I *10 before rounding, so we get tenth-degree
211 * precision. (I could have done all 1024 values for our 10-bit readings,
212 * but the function is very linear in the useful range (0-80 deg C), so
160 return (long) ((250000 * val + 1330000 + 10108 / 2) / 10108);
161 else
162 return (long) ((2500000 * val + 13300000 + 41714 / 2) / 41714);
163}
164
165/********* FAN RPM CONVERSIONS ********/
166/*
167 * Higher register values = slower fans (the fan's strobe gates a counter).

--- 37 unchanged lines hidden (view full) ---

205 * look-up table stuff. The unofficial data (see below) have effectively
206 * 7-bit resolution (they are rounded to the nearest degree). I'm assuming
207 * that the transfer function of the device is monotonic and smooth, so a
208 * smooth function fit to the data will allow us to get better precision.
209 * I used the 5th-order poly fit described above and solved for
210 * VIA register values 0-255. I *10 before rounding, so we get tenth-degree
211 * precision. (I could have done all 1024 values for our 10-bit readings,
212 * but the function is very linear in the useful range (0-80 deg C), so
213 * we'll just use linear interpolation for 10-bit readings.) So, tempLUT
213 * we'll just use linear interpolation for 10-bit readings.) So, temp_lut
214 * is the temp at via register values 0-255:
215 */
214 * is the temp at via register values 0-255:
215 */
216static const s16 tempLUT[] = {
216static const s16 temp_lut[] = {
217 -709, -688, -667, -646, -627, -607, -589, -570, -553, -536, -519,
218 -503, -487, -471, -456, -442, -428, -414, -400, -387, -375,
219 -362, -350, -339, -327, -316, -305, -295, -285, -275, -265,
220 -255, -246, -237, -229, -220, -212, -204, -196, -188, -180,
221 -173, -166, -159, -152, -145, -139, -132, -126, -120, -114,
222 -108, -102, -96, -91, -85, -80, -74, -69, -64, -59, -54, -49,
223 -44, -39, -34, -29, -25, -20, -15, -11, -6, -2, 3, 7, 12, 16,
224 20, 25, 29, 33, 37, 42, 46, 50, 54, 59, 63, 67, 71, 75, 79, 84,

--- 31 unchanged lines hidden (view full) ---

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)
262 * Note that n=161:
263 */
217 -709, -688, -667, -646, -627, -607, -589, -570, -553, -536, -519,
218 -503, -487, -471, -456, -442, -428, -414, -400, -387, -375,
219 -362, -350, -339, -327, -316, -305, -295, -285, -275, -265,
220 -255, -246, -237, -229, -220, -212, -204, -196, -188, -180,
221 -173, -166, -159, -152, -145, -139, -132, -126, -120, -114,
222 -108, -102, -96, -91, -85, -80, -74, -69, -64, -59, -54, -49,
223 -44, -39, -34, -29, -25, -20, -15, -11, -6, -2, 3, 7, 12, 16,
224 20, 25, 29, 33, 37, 42, 46, 50, 54, 59, 63, 67, 71, 75, 79, 84,

--- 31 unchanged lines hidden (view full) ---

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)
262 * Note that n=161:
263 */
264static const u8 viaLUT[] = {
264static const u8 via_lut[] = {
265 12, 12, 13, 14, 14, 15, 16, 16, 17, 18, 18, 19, 20, 20, 21, 22, 23,
266 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 35, 36, 37, 39, 40,
267 41, 43, 45, 46, 48, 49, 51, 53, 55, 57, 59, 60, 62, 64, 66,
268 69, 71, 73, 75, 77, 79, 82, 84, 86, 88, 91, 93, 95, 98, 100,
269 103, 105, 107, 110, 112, 115, 117, 119, 122, 124, 126, 129,
270 131, 134, 136, 138, 140, 143, 145, 147, 150, 152, 154, 156,
271 158, 160, 162, 164, 166, 168, 170, 172, 174, 176, 178, 180,
272 182, 183, 185, 187, 188, 190, 192, 193, 195, 196, 198, 199,

--- 6 unchanged lines hidden (view full) ---

279
280/*
281 * Converting temps to (8-bit) hyst and over registers
282 * No interpolation here.
283 * The +50 is because the temps start at -50
284 */
285static inline u8 TEMP_TO_REG(long val)
286{
265 12, 12, 13, 14, 14, 15, 16, 16, 17, 18, 18, 19, 20, 20, 21, 22, 23,
266 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 35, 36, 37, 39, 40,
267 41, 43, 45, 46, 48, 49, 51, 53, 55, 57, 59, 60, 62, 64, 66,
268 69, 71, 73, 75, 77, 79, 82, 84, 86, 88, 91, 93, 95, 98, 100,
269 103, 105, 107, 110, 112, 115, 117, 119, 122, 124, 126, 129,
270 131, 134, 136, 138, 140, 143, 145, 147, 150, 152, 154, 156,
271 158, 160, 162, 164, 166, 168, 170, 172, 174, 176, 178, 180,
272 182, 183, 185, 187, 188, 190, 192, 193, 195, 196, 198, 199,

--- 6 unchanged lines hidden (view full) ---

279
280/*
281 * Converting temps to (8-bit) hyst and over registers
282 * No interpolation here.
283 * The +50 is because the temps start at -50
284 */
285static inline u8 TEMP_TO_REG(long val)
286{
287 return viaLUT[val <= -50000 ? 0 : val >= 110000 ? 160 :
287 return via_lut[val <= -50000 ? 0 : val >= 110000 ? 160 :
288 (val < 0 ? val - 500 : val + 500) / 1000 + 50];
289}
290
291/* for 8-bit temperature hyst and over registers */
288 (val < 0 ? val - 500 : val + 500) / 1000 + 50];
289}
290
291/* for 8-bit temperature hyst and over registers */
292#define TEMP_FROM_REG(val) ((long)tempLUT[val] * 100)
292#define TEMP_FROM_REG(val) ((long)temp_lut[val] * 100)
293
294/* for 10-bit temperature readings */
295static inline long TEMP_FROM_REG10(u16 val)
296{
293
294/* for 10-bit temperature readings */
295static inline long TEMP_FROM_REG10(u16 val)
296{
297 u16 eightBits = val >> 2;
298 u16 twoBits = val & 3;
297 u16 eight_bits = val >> 2;
298 u16 two_bits = val & 3;
299
300 /* no interpolation for these */
299
300 /* no interpolation for these */
301 if (twoBits == 0 || eightBits == 255)
302 return TEMP_FROM_REG(eightBits);
301 if (two_bits == 0 || eight_bits == 255)
302 return TEMP_FROM_REG(eight_bits);
303
304 /* do some linear interpolation */
303
304 /* do some linear interpolation */
305 return (tempLUT[eightBits] * (4 - twoBits) +
306 tempLUT[eightBits + 1] * twoBits) * 25;
305 return (temp_lut[eight_bits] * (4 - two_bits) +
306 temp_lut[eight_bits + 1] * two_bits) * 25;
307}
308
309#define DIV_FROM_REG(val) (1 << (val))
310#define DIV_TO_REG(val) ((val) == 8 ? 3 : (val) == 4 ? 2 : (val) == 1 ? 0 : 1)
311
312/*
313 * For each registered chip, we need to keep some data in memory.
314 * The structure is dynamically allocated.

--- 650 unchanged lines hidden ---
307}
308
309#define DIV_FROM_REG(val) (1 << (val))
310#define DIV_TO_REG(val) ((val) == 8 ? 3 : (val) == 4 ? 2 : (val) == 1 ? 0 : 1)
311
312/*
313 * For each registered chip, we need to keep some data in memory.
314 * The structure is dynamically allocated.

--- 650 unchanged lines hidden ---