lm93.c (dca3a783400a18e2bf4503b1d4a85c4d0ca1a7e4) lm93.c (088ce2ac9ebac5c74faf4d39083627875fa6f0f0)
1/*
2 * lm93.c - Part of lm_sensors, Linux kernel modules for hardware monitoring
3 *
4 * Author/Maintainer: Mark M. Hoffman <mhoffman@lightlink.com>
5 * Copyright (c) 2004 Utilitek Systems, Inc.
6 *
7 * derived in part from lm78.c:
8 * Copyright (c) 1998, 1999 Frodo Looijaard <frodol@dds.nl>

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

349 * static const unsigned long lm93_vin_val_nom[16] = {
350 * 927, 927, 927, 1200, 1500, 1500, 1200, 1200,
351 * 3300, 5000, 2500, 1969, 984, 984, 309, 3300,
352 * };
353 */
354
355static unsigned LM93_IN_FROM_REG(int nr, u8 reg)
356{
1/*
2 * lm93.c - Part of lm_sensors, Linux kernel modules for hardware monitoring
3 *
4 * Author/Maintainer: Mark M. Hoffman <mhoffman@lightlink.com>
5 * Copyright (c) 2004 Utilitek Systems, Inc.
6 *
7 * derived in part from lm78.c:
8 * Copyright (c) 1998, 1999 Frodo Looijaard <frodol@dds.nl>

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

349 * static const unsigned long lm93_vin_val_nom[16] = {
350 * 927, 927, 927, 1200, 1500, 1500, 1200, 1200,
351 * 3300, 5000, 2500, 1969, 984, 984, 309, 3300,
352 * };
353 */
354
355static unsigned LM93_IN_FROM_REG(int nr, u8 reg)
356{
357 const long uV_max = lm93_vin_val_max[nr] * 1000;
358 const long uV_min = lm93_vin_val_min[nr] * 1000;
357 const long uv_max = lm93_vin_val_max[nr] * 1000;
358 const long uv_min = lm93_vin_val_min[nr] * 1000;
359
359
360 const long slope = (uV_max - uV_min) /
360 const long slope = (uv_max - uv_min) /
361 (lm93_vin_reg_max[nr] - lm93_vin_reg_min[nr]);
361 (lm93_vin_reg_max[nr] - lm93_vin_reg_min[nr]);
362 const long intercept = uV_min - slope * lm93_vin_reg_min[nr];
362 const long intercept = uv_min - slope * lm93_vin_reg_min[nr];
363
364 return (slope * reg + intercept + 500) / 1000;
365}
366
367/*
368 * IN: mV, limits determined by channel nr
369 * REG: scaling determined by channel nr
370 */
371static u8 LM93_IN_TO_REG(int nr, unsigned val)
372{
373 /* range limit */
363
364 return (slope * reg + intercept + 500) / 1000;
365}
366
367/*
368 * IN: mV, limits determined by channel nr
369 * REG: scaling determined by channel nr
370 */
371static u8 LM93_IN_TO_REG(int nr, unsigned val)
372{
373 /* range limit */
374 const long mV = clamp_val(val,
374 const long mv = clamp_val(val,
375 lm93_vin_val_min[nr], lm93_vin_val_max[nr]);
376
377 /* try not to lose too much precision here */
375 lm93_vin_val_min[nr], lm93_vin_val_max[nr]);
376
377 /* try not to lose too much precision here */
378 const long uV = mV * 1000;
379 const long uV_max = lm93_vin_val_max[nr] * 1000;
380 const long uV_min = lm93_vin_val_min[nr] * 1000;
378 const long uv = mv * 1000;
379 const long uv_max = lm93_vin_val_max[nr] * 1000;
380 const long uv_min = lm93_vin_val_min[nr] * 1000;
381
382 /* convert */
381
382 /* convert */
383 const long slope = (uV_max - uV_min) /
383 const long slope = (uv_max - uv_min) /
384 (lm93_vin_reg_max[nr] - lm93_vin_reg_min[nr]);
384 (lm93_vin_reg_max[nr] - lm93_vin_reg_min[nr]);
385 const long intercept = uV_min - slope * lm93_vin_reg_min[nr];
385 const long intercept = uv_min - slope * lm93_vin_reg_min[nr];
386
386
387 u8 result = ((uV - intercept + (slope/2)) / slope);
387 u8 result = ((uv - intercept + (slope/2)) / slope);
388 result = clamp_val(result,
389 lm93_vin_reg_min[nr], lm93_vin_reg_max[nr]);
390 return result;
391}
392
393/* vid in mV, upper == 0 indicates low limit, otherwise upper limit */
394static unsigned LM93_IN_REL_FROM_REG(u8 reg, int upper, int vid)
395{
388 result = clamp_val(result,
389 lm93_vin_reg_min[nr], lm93_vin_reg_max[nr]);
390 return result;
391}
392
393/* vid in mV, upper == 0 indicates low limit, otherwise upper limit */
394static unsigned LM93_IN_REL_FROM_REG(u8 reg, int upper, int vid)
395{
396 const long uV_offset = upper ? (((reg >> 4 & 0x0f) + 1) * 12500) :
396 const long uv_offset = upper ? (((reg >> 4 & 0x0f) + 1) * 12500) :
397 (((reg >> 0 & 0x0f) + 1) * -25000);
397 (((reg >> 0 & 0x0f) + 1) * -25000);
398 const long uV_vid = vid * 1000;
399 return (uV_vid + uV_offset + 5000) / 10000;
398 const long uv_vid = vid * 1000;
399 return (uv_vid + uv_offset + 5000) / 10000;
400}
401
402#define LM93_IN_MIN_FROM_REG(reg, vid) LM93_IN_REL_FROM_REG((reg), 0, (vid))
403#define LM93_IN_MAX_FROM_REG(reg, vid) LM93_IN_REL_FROM_REG((reg), 1, (vid))
404
405/*
406 * vid in mV , upper == 0 indicates low limit, otherwise upper limit
407 * upper also determines which nibble of the register is returned
408 * (the other nibble will be 0x0)
409 */
410static u8 LM93_IN_REL_TO_REG(unsigned val, int upper, int vid)
411{
400}
401
402#define LM93_IN_MIN_FROM_REG(reg, vid) LM93_IN_REL_FROM_REG((reg), 0, (vid))
403#define LM93_IN_MAX_FROM_REG(reg, vid) LM93_IN_REL_FROM_REG((reg), 1, (vid))
404
405/*
406 * vid in mV , upper == 0 indicates low limit, otherwise upper limit
407 * upper also determines which nibble of the register is returned
408 * (the other nibble will be 0x0)
409 */
410static u8 LM93_IN_REL_TO_REG(unsigned val, int upper, int vid)
411{
412 long uV_offset = vid * 1000 - val * 10000;
412 long uv_offset = vid * 1000 - val * 10000;
413 if (upper) {
413 if (upper) {
414 uV_offset = clamp_val(uV_offset, 12500, 200000);
415 return (u8)((uV_offset / 12500 - 1) << 4);
414 uv_offset = clamp_val(uv_offset, 12500, 200000);
415 return (u8)((uv_offset / 12500 - 1) << 4);
416 } else {
416 } else {
417 uV_offset = clamp_val(uV_offset, -400000, -25000);
418 return (u8)((uV_offset / -25000 - 1) << 0);
417 uv_offset = clamp_val(uv_offset, -400000, -25000);
418 return (u8)((uv_offset / -25000 - 1) << 0);
419 }
420}
421
422/*
423 * TEMP: 1/1000 degrees C (-128C to +127C)
424 * REG: 1C/bit, two's complement
425 */
426static int LM93_TEMP_FROM_REG(u8 reg)

--- 2383 unchanged lines hidden ---
419 }
420}
421
422/*
423 * TEMP: 1/1000 degrees C (-128C to +127C)
424 * REG: 1C/bit, two's complement
425 */
426static int LM93_TEMP_FROM_REG(u8 reg)

--- 2383 unchanged lines hidden ---