From dd56b638951936cda945ba5641cc44927a5f1c6d Mon Sep 17 00:00:00 2001 From: Geert Uytterhoeven Date: Sun, 26 Oct 2008 17:04:38 +0100 Subject: [PATCH 1/7] hwmon: (w83781d) Fix linking when built-in When w83781d is built-in, the final links fails with the following vague error message: `.exit.text' referenced in section `.init.text' of drivers/built-in.o: defined in discarded section `.exit.text' of drivers/built-in.o w83781d_isa_unregister() cannot be marked __exit, as it's also called from sensors_w83781d_init(), which is marked __init. Signed-off-by: Geert Uytterhoeven Cc: Wolfgang Grandegger Signed-off-by: Jean Delvare --- drivers/hwmon/w83781d.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/drivers/hwmon/w83781d.c b/drivers/hwmon/w83781d.c index d4d1b859d4f..fc12bd412e3 100644 --- a/drivers/hwmon/w83781d.c +++ b/drivers/hwmon/w83781d.c @@ -1968,7 +1968,7 @@ exit: return res; } -static void __exit +static void w83781d_isa_unregister(void) { if (pdev) { @@ -2017,7 +2017,7 @@ w83781d_isa_register(void) return 0; } -static void __exit +static void w83781d_isa_unregister(void) { } From 1b871826b3dfcdcd78140d17c00e452eec6c12a4 Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Sun, 26 Oct 2008 17:04:39 +0100 Subject: [PATCH 2/7] hwmon-vid: Add support for AMD family 10h CPUs The AMD family 10h CPUs use the same VID decoding table as the family 0Fh CPUs. Signed-off-by: Jean Delvare Cc: Rudolf Marek --- drivers/hwmon/hwmon-vid.c | 1 + 1 file changed, 1 insertion(+) diff --git a/drivers/hwmon/hwmon-vid.c b/drivers/hwmon/hwmon-vid.c index c54eff92be4..bfc296145bb 100644 --- a/drivers/hwmon/hwmon-vid.c +++ b/drivers/hwmon/hwmon-vid.c @@ -180,6 +180,7 @@ static struct vrm_model vrm_models[] = { {X86_VENDOR_AMD, 0x6, ANY, ANY, 90}, /* Athlon Duron etc */ {X86_VENDOR_AMD, 0xF, 0x3F, ANY, 24}, /* Athlon 64, Opteron */ {X86_VENDOR_AMD, 0xF, ANY, ANY, 25}, /* NPT family 0Fh */ + {X86_VENDOR_AMD, 0x10, ANY, ANY, 25}, /* NPT family 10h */ {X86_VENDOR_INTEL, 0x6, 0x9, ANY, 13}, /* Pentium M (130 nm) */ {X86_VENDOR_INTEL, 0x6, 0xB, ANY, 85}, /* Tualatin */ {X86_VENDOR_INTEL, 0x6, 0xD, ANY, 13}, /* Pentium M (90 nm) */ From ec38fa2b35f13e7fa1d676a5bc997d0df1b02574 Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Sun, 26 Oct 2008 17:04:39 +0100 Subject: [PATCH 3/7] hwmon: (lm90) Fix handling of hysteresis value There are several problems in the way the hysteresis value is handled by the lm90 driver: * In show_temphyst(), specific handling of the MAX6646 is missing, so the hysteresis is reported incorrectly if the critical temperature is over 127 degrees C. * In set_temphyst(), the new hysteresis register value is written to the chip but data->temp_hyst isn't updated accordingly, so there is a short period of time (up to 2 seconds) where the old hystereris value will be returned while the new one is already active. * In set_temphyst(), the critical temperature which is used as a base to compute the value of the hysteresis register lacks device-specific handling. As a result, the value of the hysteresis register might be incorrect for the ADT7461 and MAX6646 chips. Fix these 3 bugs. Signed-off-by: Jean Delvare Cc: Ben Hutchings Cc: Nate Case --- drivers/hwmon/lm90.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/drivers/hwmon/lm90.c b/drivers/hwmon/lm90.c index 3edeebc0b83..6242e72a82c 100644 --- a/drivers/hwmon/lm90.c +++ b/drivers/hwmon/lm90.c @@ -461,6 +461,8 @@ static ssize_t show_temphyst(struct device *dev, struct device_attribute *devatt if (data->kind == adt7461) temp = temp_from_u8_adt7461(data, data->temp8[attr->index]); + else if (data->kind == max6646) + temp = temp_from_u8(data->temp8[attr->index]); else temp = temp_from_s8(data->temp8[attr->index]); @@ -473,12 +475,19 @@ static ssize_t set_temphyst(struct device *dev, struct device_attribute *dummy, struct i2c_client *client = to_i2c_client(dev); struct lm90_data *data = i2c_get_clientdata(client); long val = simple_strtol(buf, NULL, 10); - long hyst; + int temp; mutex_lock(&data->update_lock); - hyst = temp_from_s8(data->temp8[2]) - val; + if (data->kind == adt7461) + temp = temp_from_u8_adt7461(data, data->temp8[2]); + else if (data->kind == max6646) + temp = temp_from_u8(data->temp8[2]); + else + temp = temp_from_s8(data->temp8[2]); + + data->temp_hyst = hyst_to_reg(temp - val); i2c_smbus_write_byte_data(client, LM90_REG_W_TCRIT_HYST, - hyst_to_reg(hyst)); + data->temp_hyst); mutex_unlock(&data->update_lock); return count; } From 97ae60bb38279e1941c738b1037a57e6b14efeaf Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Sun, 26 Oct 2008 17:04:39 +0100 Subject: [PATCH 4/7] hwmon: (lm90) Add support for the LM99 16 degree offset The LM99 differs from the LM86, LM89 and LM90 in that it reports remote temperatures (temp2) 16 degrees lower than they really are. So far we have been cheating and handled this in userspace but it really should be handled by the driver directly. Signed-off-by: Jean Delvare Cc: Matthew Garrett --- Documentation/hwmon/lm90 | 2 +- drivers/hwmon/lm90.c | 37 +++++++++++++++++++++++++++++++++---- 2 files changed, 34 insertions(+), 5 deletions(-) diff --git a/Documentation/hwmon/lm90 b/Documentation/hwmon/lm90 index e0d5206d1de..0e841171023 100644 --- a/Documentation/hwmon/lm90 +++ b/Documentation/hwmon/lm90 @@ -8,7 +8,7 @@ Supported chips: Datasheet: Publicly available at the National Semiconductor website http://www.national.com/pf/LM/LM90.html * National Semiconductor LM89 - Prefix: 'lm99' + Prefix: 'lm89' (no auto-detection) Addresses scanned: I2C 0x4c and 0x4d Datasheet: Publicly available at the National Semiconductor website http://www.national.com/mpf/LM/LM89.html diff --git a/drivers/hwmon/lm90.c b/drivers/hwmon/lm90.c index 6242e72a82c..96a70186672 100644 --- a/drivers/hwmon/lm90.c +++ b/drivers/hwmon/lm90.c @@ -12,9 +12,9 @@ * made by National Semiconductor. Both have an increased remote * temperature measurement accuracy (1 degree), and the LM99 * additionally shifts remote temperatures (measured and limits) by 16 - * degrees, which allows for higher temperatures measurement. The - * driver doesn't handle it since it can be done easily in user-space. + * degrees, which allows for higher temperatures measurement. * Note that there is no way to differentiate between both chips. + * When device is auto-detected, the driver will assume an LM99. * * This driver also supports the LM86, another sensor chip made by * National Semiconductor. It is exactly similar to the LM90 except it @@ -169,8 +169,8 @@ static const struct i2c_device_id lm90_id[] = { { "adt7461", adt7461 }, { "lm90", lm90 }, { "lm86", lm86 }, - { "lm89", lm99 }, - { "lm99", lm99 }, /* Missing temperature offset */ + { "lm89", lm86 }, + { "lm99", lm99 }, { "max6646", max6646 }, { "max6647", max6646 }, { "max6649", max6646 }, @@ -366,6 +366,10 @@ static ssize_t show_temp8(struct device *dev, struct device_attribute *devattr, else temp = temp_from_s8(data->temp8[attr->index]); + /* +16 degrees offset for temp2 for the LM99 */ + if (data->kind == lm99 && attr->index == 3) + temp += 16000; + return sprintf(buf, "%d\n", temp); } @@ -385,6 +389,10 @@ static ssize_t set_temp8(struct device *dev, struct device_attribute *devattr, long val = simple_strtol(buf, NULL, 10); int nr = attr->index; + /* +16 degrees offset for temp2 for the LM99 */ + if (data->kind == lm99 && attr->index == 3) + val -= 16000; + mutex_lock(&data->update_lock); if (data->kind == adt7461) data->temp8[nr] = temp_to_u8_adt7461(data, val); @@ -411,6 +419,10 @@ static ssize_t show_temp11(struct device *dev, struct device_attribute *devattr, else temp = temp_from_s16(data->temp11[attr->index]); + /* +16 degrees offset for temp2 for the LM99 */ + if (data->kind == lm99 && attr->index <= 2) + temp += 16000; + return sprintf(buf, "%d\n", temp); } @@ -432,6 +444,10 @@ static ssize_t set_temp11(struct device *dev, struct device_attribute *devattr, long val = simple_strtol(buf, NULL, 10); int nr = attr->index; + /* +16 degrees offset for temp2 for the LM99 */ + if (data->kind == lm99 && attr->index <= 2) + val -= 16000; + mutex_lock(&data->update_lock); if (data->kind == adt7461) data->temp11[nr] = temp_to_u16_adt7461(data, val); @@ -466,6 +482,10 @@ static ssize_t show_temphyst(struct device *dev, struct device_attribute *devatt else temp = temp_from_s8(data->temp8[attr->index]); + /* +16 degrees offset for temp2 for the LM99 */ + if (data->kind == lm99 && attr->index == 3) + temp += 16000; + return sprintf(buf, "%d\n", temp - temp_from_s8(data->temp_hyst)); } @@ -691,6 +711,15 @@ static int lm90_detect(struct i2c_client *new_client, int kind, } else if ((chip_id & 0xF0) == 0x30) { /* LM89/LM99 */ kind = lm99; + dev_info(&adapter->dev, + "Assuming LM99 chip at " + "0x%02x\n", address); + dev_info(&adapter->dev, + "If it is an LM89, pass " + "force_lm86=%d,0x%02x when " + "loading the lm90 driver\n", + i2c_adapter_id(adapter), + address); } else if (address == 0x4C && (chip_id & 0xF0) == 0x10) { /* LM86 */ From be821b78af9de886571e3565515a59f966d66f42 Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Sun, 26 Oct 2008 17:04:40 +0100 Subject: [PATCH 5/7] hwmon: (adt7473) Fix voltage conversion routines Fix voltage conversion routines. Based on an earlier patch from Paulius Zaleckas. According to the datasheet voltage is scaled with resistors and value 192 is nominal voltage. 0 is 0V. Signed-off-by: Jean Delvare Cc: Paulius Zaleckas Cc: Darrick J. Wong --- drivers/hwmon/adt7473.c | 29 +++++++++-------------------- 1 file changed, 9 insertions(+), 20 deletions(-) diff --git a/drivers/hwmon/adt7473.c b/drivers/hwmon/adt7473.c index 3a0b6313647..b9a8ea30c99 100644 --- a/drivers/hwmon/adt7473.c +++ b/drivers/hwmon/adt7473.c @@ -319,35 +319,24 @@ out: } /* - * On this chip, voltages are given as a count of steps between a minimum - * and maximum voltage, not a direct voltage. + * Conversions */ -static const int volt_convert_table[][2] = { - {2997, 3}, - {4395, 4}, + +/* IN are scaled acording to built-in resistors */ +static const int adt7473_scaling[] = { /* .001 Volts */ + 2250, 3300 }; +#define SCALE(val, from, to) (((val) * (to) + ((from) / 2)) / (from)) static int decode_volt(int volt_index, u8 raw) { - int cmax = volt_convert_table[volt_index][0]; - int cmin = volt_convert_table[volt_index][1]; - return ((raw * (cmax - cmin)) / 255) + cmin; + return SCALE(raw, 192, adt7473_scaling[volt_index]); } static u8 encode_volt(int volt_index, int cooked) { - int cmax = volt_convert_table[volt_index][0]; - int cmin = volt_convert_table[volt_index][1]; - u8 x; - - if (cooked > cmax) - cooked = cmax; - else if (cooked < cmin) - cooked = cmin; - - x = ((cooked - cmin) * 255) / (cmax - cmin); - - return x; + int raw = SCALE(cooked, adt7473_scaling[volt_index], 192); + return SENSORS_LIMIT(raw, 0, 255); } static ssize_t show_volt_min(struct device *dev, From 4777e4e6b8540ee4226876a737833d03bbc55394 Mon Sep 17 00:00:00 2001 From: Alistair John Strachan Date: Sun, 26 Oct 2008 17:04:40 +0100 Subject: [PATCH 6/7] hwmon: (abituguru3) Cosmetic whitespace fixes As the probable result of zealous copy/pasting, many supported boards contain sensor names with trailing whitespace. Though this is not a huge problem, it is inconsistent with other sensor names, and with other similar hwmon drivers. Additionally, the DMI nag message added in 2.6.27 was missing a space between two sentence fragments -- might as well clean that up too. Doesn't alter any kernel text, just data. Signed-off-by: Alistair John Strachan Reported-by: Justin Piszcz Acked-by: Hans de Goede Signed-off-by: Jean Delvare --- drivers/hwmon/abituguru3.c | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/drivers/hwmon/abituguru3.c b/drivers/hwmon/abituguru3.c index d9e7a49d6cb..c28cd6ca372 100644 --- a/drivers/hwmon/abituguru3.c +++ b/drivers/hwmon/abituguru3.c @@ -178,7 +178,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM", 26, 1, 1, 1, 0 }, { "CPU Fan", 32, 2, 60, 1, 0 }, { "NB Fan", 33, 2, 60, 1, 0 }, @@ -200,7 +200,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM1", 26, 1, 1, 1, 0 }, { "PWM2", 27, 1, 1, 1, 0 }, { "PWM3", 28, 1, 1, 1, 0 }, @@ -229,7 +229,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM", 26, 1, 1, 1, 0 }, { "CPU Fan", 32, 2, 60, 1, 0 }, { "NB Fan", 33, 2, 60, 1, 0 }, @@ -250,7 +250,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM", 26, 1, 1, 1, 0 }, { "CPU Fan", 32, 2, 60, 1, 0 }, { "NB Fan", 33, 2, 60, 1, 0 }, @@ -342,7 +342,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM1", 26, 1, 1, 1, 0 }, { "PWM2", 27, 1, 1, 1, 0 }, { "PWM3", 28, 1, 1, 1, 0 }, @@ -371,7 +371,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM", 26, 1, 1, 1, 0 }, { "CPU Fan", 32, 2, 60, 1, 0 }, { "NB Fan", 33, 2, 60, 1, 0 }, @@ -416,7 +416,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM1", 26, 1, 1, 1, 0 }, { "PWM2", 27, 1, 1, 1, 0 }, { "PWM3", 28, 1, 1, 1, 0 }, @@ -446,7 +446,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "ATX +3.3V", 10, 0, 20, 1, 0 }, { "ATX 5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 26, 1, 1, 1, 0 }, + { "System", 26, 1, 1, 1, 0 }, { "PWM", 27, 1, 1, 1, 0 }, { "CPU FAN", 32, 2, 60, 1, 0 }, { "SYS FAN", 34, 2, 60, 1, 0 }, @@ -469,7 +469,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM Phase1", 26, 1, 1, 1, 0 }, { "PWM Phase2", 27, 1, 1, 1, 0 }, { "PWM Phase3", 28, 1, 1, 1, 0 }, @@ -487,7 +487,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "DDR2", 13, 0, 20, 1, 0 }, { "DDR2 VTT", 14, 0, 10, 1, 0 }, { "CPU VTT", 3, 0, 20, 1, 0 }, - { "NB 1.2V ", 4, 0, 10, 1, 0 }, + { "NB 1.2V", 4, 0, 10, 1, 0 }, { "SB 1.5V", 6, 0, 10, 1, 0 }, { "HyperTransport", 5, 0, 10, 1, 0 }, { "ATX +12V (24-Pin)", 12, 0, 60, 1, 0 }, @@ -496,7 +496,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "ATX +3.3V", 10, 0, 20, 1, 0 }, { "ATX 5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, { "PWM Phase1", 26, 1, 1, 1, 0 }, { "PWM Phase2", 27, 1, 1, 1, 0 }, { "PWM Phase3", 28, 1, 1, 1, 0 }, @@ -523,8 +523,8 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "+3.3V", 10, 0, 20, 1, 0 }, { "5VSB", 11, 0, 30, 1, 0 }, { "CPU", 24, 1, 1, 1, 0 }, - { "System ", 25, 1, 1, 1, 0 }, - { "PWM ", 26, 1, 1, 1, 0 }, + { "System", 25, 1, 1, 1, 0 }, + { "PWM", 26, 1, 1, 1, 0 }, { "PWM Phase2", 27, 1, 1, 1, 0 }, { "PWM Phase3", 28, 1, 1, 1, 0 }, { "PWM Phase4", 29, 1, 1, 1, 0 }, @@ -947,7 +947,7 @@ static int __devinit abituguru3_probe(struct platform_device *pdev) if (!abituguru3_motherboards[i].dmi_name) { printk(KERN_WARNING ABIT_UGURU3_NAME ": this motherboard was " "not detected using DMI. Please send the output of " - "\"dmidecode\" to the abituguru3 maintainer" + "\"dmidecode\" to the abituguru3 maintainer " "(see MAINTAINERS)\n"); } #endif From c02d65694debbc82dc48453a9fd52efb036c7258 Mon Sep 17 00:00:00 2001 From: Alistair John Strachan Date: Sun, 26 Oct 2008 17:04:40 +0100 Subject: [PATCH 7/7] hwmon: (abituguru3) enable DMI probing feature on AW9D-MAX Switch the AW9D-MAX over from port probing to the preferred DMI probe method. Signed-off-by: Alistair John Strachan Tested-by: Justin Piszcz Acked-by: Hans de Goede Signed-off-by: Jean Delvare --- drivers/hwmon/abituguru3.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/hwmon/abituguru3.c b/drivers/hwmon/abituguru3.c index c28cd6ca372..70bb854086d 100644 --- a/drivers/hwmon/abituguru3.c +++ b/drivers/hwmon/abituguru3.c @@ -402,7 +402,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { { "AUX3 Fan", 36, 2, 60, 1, 0 }, { NULL, 0, 0, 0, 0, 0 } } }, - { 0x0016, NULL /* AW9D-MAX, need DMI string */, { + { 0x0016, "AW9D-MAX (Intel i975-ICH7)", { { "CPU Core", 0, 0, 10, 1, 0 }, { "DDR2", 1, 0, 20, 1, 0 }, { "DDR2 VTT", 2, 0, 10, 1, 0 },