diff options
author | Andrew Paprocki <andrew@ishiboo.com> | 2008-08-06 16:41:06 -0400 |
---|---|---|
committer | Jean Delvare <khali@mahadeva.delvare> | 2008-08-06 16:41:06 -0400 |
commit | 0475169c13e177e1af5a02f5e9f30fda13dc0b86 (patch) | |
tree | 9366e6e093ff39b037011a392c8f97140c3ccad9 | |
parent | 116d0486bdefc11f71e567cadf0c47f788b4dd06 (diff) |
hwmon: (it87) Support for 16-bit fan reading in it8712 >= rev 0x07
The it8712 chip supports 16-bit fan tachometers in revisions >= 0x07.
Revisions >= 0x08 dropped support for 8-bit fan divisor registers. The
patch enables 16-bit fan readings on all revisions >= 0x07 just like
the it8716 and it8718 chips.
Signed-off-by: Andrew Paprocki <andrew@ishiboo.com>
Signed-off-by: Jean Delvare <khali@linux-fr.org>
-rw-r--r-- | Documentation/hwmon/it87 | 9 | ||||
-rw-r--r-- | drivers/hwmon/it87.c | 32 |
2 files changed, 27 insertions, 14 deletions
diff --git a/Documentation/hwmon/it87 b/Documentation/hwmon/it87 index f4ce1fdbeff6..d931525f3f37 100644 --- a/Documentation/hwmon/it87 +++ b/Documentation/hwmon/it87 | |||
@@ -11,7 +11,9 @@ Supported chips: | |||
11 | Prefix: 'it8712' | 11 | Prefix: 'it8712' |
12 | Addresses scanned: from Super I/O config space (8 I/O ports) | 12 | Addresses scanned: from Super I/O config space (8 I/O ports) |
13 | Datasheet: Publicly available at the ITE website | 13 | Datasheet: Publicly available at the ITE website |
14 | http://www.ite.com.tw/ | 14 | http://www.ite.com.tw/product_info/file/pc/IT8712F_V0.9.1.pdf |
15 | http://www.ite.com.tw/product_info/file/pc/Errata%20V0.1%20for%20IT8712F%20V0.9.1.pdf | ||
16 | http://www.ite.com.tw/product_info/file/pc/IT8712F_V0.9.3.pdf | ||
15 | * IT8716F/IT8726F | 17 | * IT8716F/IT8726F |
16 | Prefix: 'it8716' | 18 | Prefix: 'it8716' |
17 | Addresses scanned: from Super I/O config space (8 I/O ports) | 19 | Addresses scanned: from Super I/O config space (8 I/O ports) |
@@ -90,14 +92,13 @@ upper VID bits share their pins with voltage inputs (in5 and in6) so you | |||
90 | can't have both on a given board. | 92 | can't have both on a given board. |
91 | 93 | ||
92 | The IT8716F, IT8718F and later IT8712F revisions have support for | 94 | The IT8716F, IT8718F and later IT8712F revisions have support for |
93 | 2 additional fans. They are supported by the driver for the IT8716F and | 95 | 2 additional fans. The additional fans are supported by the driver. |
94 | IT8718F but not for the IT8712F | ||
95 | 96 | ||
96 | The IT8716F and IT8718F, and late IT8712F and IT8705F also have optional | 97 | The IT8716F and IT8718F, and late IT8712F and IT8705F also have optional |
97 | 16-bit tachometer counters for fans 1 to 3. This is better (no more fan | 98 | 16-bit tachometer counters for fans 1 to 3. This is better (no more fan |
98 | clock divider mess) but not compatible with the older chips and | 99 | clock divider mess) but not compatible with the older chips and |
99 | revisions. For now, the driver only uses the 16-bit mode on the | 100 | revisions. For now, the driver only uses the 16-bit mode on the |
100 | IT8716F and IT8718F. | 101 | late IT8712F, IT8716F and IT8718F. |
101 | 102 | ||
102 | The IT8726F is just bit enhanced IT8716F with additional hardware | 103 | The IT8726F is just bit enhanced IT8716F with additional hardware |
103 | for AMD power sequencing. Therefore the chip will appear as IT8716F | 104 | for AMD power sequencing. Therefore the chip will appear as IT8716F |
diff --git a/drivers/hwmon/it87.c b/drivers/hwmon/it87.c index e12c132ff83a..2a365681f969 100644 --- a/drivers/hwmon/it87.c +++ b/drivers/hwmon/it87.c | |||
@@ -151,9 +151,9 @@ static int fix_pwm_polarity; | |||
151 | /* The IT8718F has the VID value in a different register, in Super-I/O | 151 | /* The IT8718F has the VID value in a different register, in Super-I/O |
152 | configuration space. */ | 152 | configuration space. */ |
153 | #define IT87_REG_VID 0x0a | 153 | #define IT87_REG_VID 0x0a |
154 | /* Warning: register 0x0b is used for something completely different in | 154 | /* The IT8705F and IT8712F earlier than revision 0x08 use register 0x0b |
155 | new chips/revisions. I suspect only 16-bit tachometer mode will work | 155 | for fan divisors. Later IT8712F revisions must use 16-bit tachometer |
156 | for these. */ | 156 | mode. */ |
157 | #define IT87_REG_FAN_DIV 0x0b | 157 | #define IT87_REG_FAN_DIV 0x0b |
158 | #define IT87_REG_FAN_16BIT 0x0c | 158 | #define IT87_REG_FAN_16BIT 0x0c |
159 | 159 | ||
@@ -234,6 +234,7 @@ static const unsigned int pwm_freq[8] = { | |||
234 | struct it87_sio_data { | 234 | struct it87_sio_data { |
235 | enum chips type; | 235 | enum chips type; |
236 | /* Values read from Super-I/O config space */ | 236 | /* Values read from Super-I/O config space */ |
237 | u8 revision; | ||
237 | u8 vid_value; | 238 | u8 vid_value; |
238 | }; | 239 | }; |
239 | 240 | ||
@@ -242,6 +243,7 @@ struct it87_sio_data { | |||
242 | struct it87_data { | 243 | struct it87_data { |
243 | struct device *hwmon_dev; | 244 | struct device *hwmon_dev; |
244 | enum chips type; | 245 | enum chips type; |
246 | u8 revision; | ||
245 | 247 | ||
246 | unsigned short addr; | 248 | unsigned short addr; |
247 | const char *name; | 249 | const char *name; |
@@ -268,6 +270,14 @@ struct it87_data { | |||
268 | u8 manual_pwm_ctl[3]; /* manual PWM value set by user */ | 270 | u8 manual_pwm_ctl[3]; /* manual PWM value set by user */ |
269 | }; | 271 | }; |
270 | 272 | ||
273 | static inline int has_16bit_fans(const struct it87_data *data) | ||
274 | { | ||
275 | /* IT8712F Datasheet 0.9.1, section 8.3.5 indicates 7h == Version I. | ||
276 | This is the first revision with 16bit tachometer support. */ | ||
277 | return (data->type == it8712 && data->revision >= 0x07) | ||
278 | || data->type == it8716 | ||
279 | || data->type == it8718; | ||
280 | } | ||
271 | 281 | ||
272 | static int it87_probe(struct platform_device *pdev); | 282 | static int it87_probe(struct platform_device *pdev); |
273 | static int __devexit it87_remove(struct platform_device *pdev); | 283 | static int __devexit it87_remove(struct platform_device *pdev); |
@@ -991,8 +1001,9 @@ static int __init it87_find(unsigned short *address, | |||
991 | } | 1001 | } |
992 | 1002 | ||
993 | err = 0; | 1003 | err = 0; |
1004 | sio_data->revision = superio_inb(DEVREV) & 0x0f; | ||
994 | pr_info("it87: Found IT%04xF chip at 0x%x, revision %d\n", | 1005 | pr_info("it87: Found IT%04xF chip at 0x%x, revision %d\n", |
995 | chip_type, *address, superio_inb(DEVREV) & 0x0f); | 1006 | chip_type, *address, sio_data->revision); |
996 | 1007 | ||
997 | /* Read GPIO config and VID value from LDN 7 (GPIO) */ | 1008 | /* Read GPIO config and VID value from LDN 7 (GPIO) */ |
998 | if (chip_type != IT8705F_DEVID) { | 1009 | if (chip_type != IT8705F_DEVID) { |
@@ -1045,6 +1056,7 @@ static int __devinit it87_probe(struct platform_device *pdev) | |||
1045 | 1056 | ||
1046 | data->addr = res->start; | 1057 | data->addr = res->start; |
1047 | data->type = sio_data->type; | 1058 | data->type = sio_data->type; |
1059 | data->revision = sio_data->revision; | ||
1048 | data->name = names[sio_data->type]; | 1060 | data->name = names[sio_data->type]; |
1049 | 1061 | ||
1050 | /* Now, we do the remaining detection. */ | 1062 | /* Now, we do the remaining detection. */ |
@@ -1069,7 +1081,7 @@ static int __devinit it87_probe(struct platform_device *pdev) | |||
1069 | goto ERROR2; | 1081 | goto ERROR2; |
1070 | 1082 | ||
1071 | /* Do not create fan files for disabled fans */ | 1083 | /* Do not create fan files for disabled fans */ |
1072 | if (data->type == it8716 || data->type == it8718) { | 1084 | if (has_16bit_fans(data)) { |
1073 | /* 16-bit tachometers */ | 1085 | /* 16-bit tachometers */ |
1074 | if (data->has_fan & (1 << 0)) { | 1086 | if (data->has_fan & (1 << 0)) { |
1075 | if ((err = device_create_file(dev, | 1087 | if ((err = device_create_file(dev, |
@@ -1350,7 +1362,7 @@ static void __devinit it87_init_device(struct platform_device *pdev) | |||
1350 | data->has_fan = (data->fan_main_ctrl >> 4) & 0x07; | 1362 | data->has_fan = (data->fan_main_ctrl >> 4) & 0x07; |
1351 | 1363 | ||
1352 | /* Set tachometers to 16-bit mode if needed */ | 1364 | /* Set tachometers to 16-bit mode if needed */ |
1353 | if (data->type == it8716 || data->type == it8718) { | 1365 | if (has_16bit_fans(data)) { |
1354 | tmp = it87_read_value(data, IT87_REG_FAN_16BIT); | 1366 | tmp = it87_read_value(data, IT87_REG_FAN_16BIT); |
1355 | if (~tmp & 0x07 & data->has_fan) { | 1367 | if (~tmp & 0x07 & data->has_fan) { |
1356 | dev_dbg(&pdev->dev, | 1368 | dev_dbg(&pdev->dev, |
@@ -1426,7 +1438,7 @@ static struct it87_data *it87_update_device(struct device *dev) | |||
1426 | data->fan[i] = it87_read_value(data, | 1438 | data->fan[i] = it87_read_value(data, |
1427 | IT87_REG_FAN[i]); | 1439 | IT87_REG_FAN[i]); |
1428 | /* Add high byte if in 16-bit mode */ | 1440 | /* Add high byte if in 16-bit mode */ |
1429 | if (data->type == it8716 || data->type == it8718) { | 1441 | if (has_16bit_fans(data)) { |
1430 | data->fan[i] |= it87_read_value(data, | 1442 | data->fan[i] |= it87_read_value(data, |
1431 | IT87_REG_FANX[i]) << 8; | 1443 | IT87_REG_FANX[i]) << 8; |
1432 | data->fan_min[i] |= it87_read_value(data, | 1444 | data->fan_min[i] |= it87_read_value(data, |
@@ -1443,8 +1455,7 @@ static struct it87_data *it87_update_device(struct device *dev) | |||
1443 | } | 1455 | } |
1444 | 1456 | ||
1445 | /* Newer chips don't have clock dividers */ | 1457 | /* Newer chips don't have clock dividers */ |
1446 | if ((data->has_fan & 0x07) && data->type != it8716 | 1458 | if ((data->has_fan & 0x07) && !has_16bit_fans(data)) { |
1447 | && data->type != it8718) { | ||
1448 | i = it87_read_value(data, IT87_REG_FAN_DIV); | 1459 | i = it87_read_value(data, IT87_REG_FAN_DIV); |
1449 | data->fan_div[0] = i & 0x07; | 1460 | data->fan_div[0] = i & 0x07; |
1450 | data->fan_div[1] = (i >> 3) & 0x07; | 1461 | data->fan_div[1] = (i >> 3) & 0x07; |
@@ -1460,7 +1471,8 @@ static struct it87_data *it87_update_device(struct device *dev) | |||
1460 | data->fan_ctl = it87_read_value(data, IT87_REG_FAN_CTL); | 1471 | data->fan_ctl = it87_read_value(data, IT87_REG_FAN_CTL); |
1461 | 1472 | ||
1462 | data->sensor = it87_read_value(data, IT87_REG_TEMP_ENABLE); | 1473 | data->sensor = it87_read_value(data, IT87_REG_TEMP_ENABLE); |
1463 | /* The 8705 does not have VID capability */ | 1474 | /* The 8705 does not have VID capability. |
1475 | The 8718 does not use IT87_REG_VID for the same purpose. */ | ||
1464 | if (data->type == it8712 || data->type == it8716) { | 1476 | if (data->type == it8712 || data->type == it8716) { |
1465 | data->vid = it87_read_value(data, IT87_REG_VID); | 1477 | data->vid = it87_read_value(data, IT87_REG_VID); |
1466 | /* The older IT8712F revisions had only 5 VID pins, | 1478 | /* The older IT8712F revisions had only 5 VID pins, |