Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/dev/i2c Read the Tos limit from the chip, instead of ass...



details:   https://anonhg.NetBSD.org/src/rev/d7a27ceff859
branches:  trunk
changeset: 342618:d7a27ceff859
user:      jdc <jdc%NetBSD.org@localhost>
date:      Fri Jan 01 20:13:50 2016 +0000

description:
Read the Tos limit from the chip, instead of assuming 80'C, in case
firmware has altered it.  Make the *decode functions return temperatures
in either uK or C for envsys and sysctl, respectively.

diffstat:

 sys/dev/i2c/lm75.c |  74 ++++++++++++++++++++++++++++++-----------------------
 1 files changed, 42 insertions(+), 32 deletions(-)

diffs (192 lines):

diff -r 73ea1e843af9 -r d7a27ceff859 sys/dev/i2c/lm75.c
--- a/sys/dev/i2c/lm75.c        Fri Jan 01 19:46:48 2016 +0000
+++ b/sys/dev/i2c/lm75.c        Fri Jan 01 20:13:50 2016 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: lm75.c,v 1.26 2015/09/27 13:02:21 phx Exp $    */
+/*     $NetBSD: lm75.c,v 1.27 2016/01/01 20:13:50 jdc Exp $    */
 
 /*
  * Copyright (c) 2003 Wasabi Systems, Inc.
@@ -36,7 +36,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: lm75.c,v 1.26 2015/09/27 13:02:21 phx Exp $");
+__KERNEL_RCSID(0, "$NetBSD: lm75.c,v 1.27 2016/01/01 20:13:50 jdc Exp $");
 
 #include <sys/param.h>
 #include <sys/systm.h>
@@ -58,7 +58,7 @@
        envsys_data_t sc_sensor;
        int sc_tmax;
 
-       uint32_t (*sc_lmtemp_decode)(const uint8_t *);
+       uint32_t (*sc_lmtemp_decode)(const uint8_t *, int);
 };
 
 static int  lmtemp_match(device_t, cfdata_t, void *);
@@ -71,9 +71,11 @@
 
 static int     lmtemp_config_write(struct lmtemp_softc *, uint8_t);
 static int     lmtemp_temp_write(struct lmtemp_softc *, int, uint16_t);
-static uint32_t lmtemp_decode_lm75(const uint8_t *);
-static uint32_t lmtemp_decode_ds75(const uint8_t *);
-static uint32_t lmtemp_decode_lm77(const uint8_t *);
+static int     lmtemp_temp_read(struct lmtemp_softc *, uint8_t, uint32_t *,
+                               int);
+static uint32_t lmtemp_decode_lm75(const uint8_t *, int);
+static uint32_t lmtemp_decode_ds75(const uint8_t *, int);
+static uint32_t lmtemp_decode_lm77(const uint8_t *, int);
 
 static void    lmtemp_setup_sysctl(struct lmtemp_softc *);
 static int     sysctl_lm75_temp(SYSCTLFN_ARGS);
@@ -97,7 +99,7 @@
        const char *lmtemp_name;
        int lmtemp_addrmask;
        int lmtemp_addr;
-       uint32_t (*lmtemp_decode)(const uint8_t *);
+       uint32_t (*lmtemp_decode)(const uint8_t *, int);
 } lmtemptbl[] = {
        { lmtemp_lm75,  "LM75",
            LM75_ADDRMASK,      LM75_ADDR,      lmtemp_decode_lm75 },
@@ -177,16 +179,21 @@
                        lmtemptbl[i].lmtemp_name);
        }
 
-       /*
-        * according to the LM75 data sheet 80C is the default, so leave it
-        * there to avoid unexpected behaviour
-        */
-       sc->sc_tmax = 80;
+       sc->sc_lmtemp_decode = lmtemptbl[i].lmtemp_decode;
+
+       iic_acquire_bus(sc->sc_tag, I2C_F_POLL);
+
+       /* Read temperature limit and remember initial value. */
+       if (lmtemp_temp_read(sc, LM75_REG_TOS_SET_POINT, &sc->sc_tmax, 1)
+           != 0) {
+               iic_release_bus(sc->sc_tag, I2C_F_POLL);
+               return;
+       }
+
        if (i == lmtemp_lm75)
                lmtemp_setup_sysctl(sc);
 
        /* Set the configuration of the LM75 to defaults. */
-       iic_acquire_bus(sc->sc_tag, I2C_F_POLL);
        if (lmtemp_config_write(sc, LM75_CONFIG_FAULT_QUEUE_4) != 0) {
                aprint_error_dev(self, "unable to write config register\n");
                iic_release_bus(sc->sc_tag, I2C_F_POLL);
@@ -206,8 +213,6 @@
                return;
        }
 
-       sc->sc_lmtemp_decode = lmtemptbl[i].lmtemp_decode;
-
        /* Hook into system monitor. */
        sc->sc_sme->sme_name = device_xname(self);
        sc->sc_sme->sme_cookie = sc;
@@ -245,7 +250,8 @@
 }
 
 static int
-lmtemp_temp_read(struct lmtemp_softc *sc, uint8_t which, uint32_t *valp)
+lmtemp_temp_read(struct lmtemp_softc *sc, uint8_t which, uint32_t *valp,
+    int degc)
 {
        int error;
        uint8_t cmdbuf[1];
@@ -258,7 +264,7 @@
        if (error)
                return error;
 
-       *valp = sc->sc_lmtemp_decode(buf);
+       *valp = sc->sc_lmtemp_decode(buf, degc);
        return 0;
 }
 
@@ -268,7 +274,7 @@
        uint32_t val;
        int error;
 
-       error = lmtemp_temp_read(sc, LM75_REG_TEMP, &val);
+       error = lmtemp_temp_read(sc, LM75_REG_TEMP, &val, 0);
        if (error) {
 #if 0
                aprint_error_dev(sc->sc_dev, "unable to read temperature, error = %d\n",
@@ -293,7 +299,7 @@
 }
 
 static uint32_t
-lmtemp_decode_lm75(const uint8_t *buf)
+lmtemp_decode_lm75(const uint8_t *buf, int degc)
 {
        int temp;
        uint32_t val;
@@ -305,14 +311,17 @@
        temp = (int8_t) buf[0];
        temp = (temp << 1) + ((buf[1] >> 7) & 0x1);
 
-       /* Temp is given in 1/2 deg. C, we convert to uK. */
-       val = temp * 500000 + 273150000;
+       /* Temp is given in 1/2 deg. C, we convert to C or uK. */
+       if (degc)
+               val = temp / 2;
+       else
+               val = temp * 500000 + 273150000;
 
        return val;
 }
 
 static uint32_t
-lmtemp_decode_ds75(const uint8_t *buf)
+lmtemp_decode_ds75(const uint8_t *buf, int degc)
 {
        int temp;
 
@@ -324,13 +333,16 @@
        temp = (temp << 4) | ((buf[1] >> 4) & 0xf);
 
        /*
-        * Conversion to uK is simple.
+        * Conversion to C or uK is simple.
         */
-       return (temp * 62500 + 273150000);
+       if (degc)
+               return temp / 16;
+       else
+               return (temp * 62500 + 273150000);
 }
 
 static uint32_t
-lmtemp_decode_lm77(const uint8_t *buf)
+lmtemp_decode_lm77(const uint8_t *buf, int degc)
 {
        int temp;
        uint32_t val;
@@ -343,8 +355,11 @@
        temp = (int8_t)buf[0];
        temp = (temp << 5) | ((buf[1] >> 3) & 0x1f);
 
-       /* Temp is given in 1/2 deg. C, we convert to uK. */
-       val = temp * 500000 + 273150000;
+       /* Temp is given in 1/2 deg. C, we convert to C or uK. */
+       if (degc)
+               val = temp / 2;
+       else
+               val = temp * 500000 + 273150000;
 
        return val;
 }
@@ -354,11 +369,6 @@
 {
        const struct sysctlnode *me = NULL, *node = NULL;
 
-       iic_acquire_bus(sc->sc_tag, I2C_F_POLL);
-       lmtemp_temp_write(sc, LM75_REG_THYST_SET_POINT, (sc->sc_tmax - 5) * 2);
-       lmtemp_temp_write(sc, LM75_REG_TOS_SET_POINT, sc->sc_tmax * 2);
-       iic_release_bus(sc->sc_tag, I2C_F_POLL);
-
        sysctl_createv(NULL, 0, NULL, &me,
            CTLFLAG_READWRITE,
            CTLTYPE_NODE, device_xname(sc->sc_dev), NULL,



Home | Main Index | Thread Index | Old Index