aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorHans de Goede <hdegoede@redhat.com>2009-12-09 14:36:01 -0500
committerJean Delvare <khali@linux-fr.org>2009-12-09 14:36:01 -0500
commit7669896f499e1bce5cfb38f2685ff583ecdb24dd (patch)
treeac73a6c61327d36518ebbe9625620de974fa878e /drivers
parentfc16c56e694d361388bae701894fd719dbc0f7eb (diff)
hwmon: (f71882fg) Add support for the f71889fg (version 2)
This adds support for the Fintek f71889fg to the f71882fg driver, many thanks to Gerd v. Egidy for providing (remote) access to a machine which such an ic. Note that this bit of the patch: - val = SENSORS_LIMIT(val, 0, 255); + + if (data->type == f71889fg) + val = SENSORS_LIMIT(val, -128, 127); + else + val = SENSORS_LIMIT(val, 0, 127); Changes behaviour for already supported models, the new behaviour is correct as the already supported models have bit 7 of the involved registers fixed at 0, so the previous behaviour which allowed setting temp zone limits > 127 was not correct. Signed-off-by: Hans de Goede <hdegoede@redhat.com> Signed-off-by: Jean Delvare <khali@linux-fr.org>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/hwmon/Kconfig6
-rw-r--r--drivers/hwmon/f71882fg.c86
2 files changed, 71 insertions, 21 deletions
diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig
index dd6939370f75..edf8febb5bc4 100644
--- a/drivers/hwmon/Kconfig
+++ b/drivers/hwmon/Kconfig
@@ -305,12 +305,12 @@ config SENSORS_F71805F
305 will be called f71805f. 305 will be called f71805f.
306 306
307config SENSORS_F71882FG 307config SENSORS_F71882FG
308 tristate "Fintek F71858FG, F71862FG, F71882FG and F8000" 308 tristate "Fintek F71858FG, F71862FG, F71882FG, F71889FG and F8000"
309 depends on EXPERIMENTAL 309 depends on EXPERIMENTAL
310 help 310 help
311 If you say yes here you get support for hardware monitoring 311 If you say yes here you get support for hardware monitoring
312 features of the Fintek F71858FG, F71862FG/71863FG, F71882FG/F71883FG 312 features of the Fintek F71858FG, F71862FG/71863FG, F71882FG/F71883FG,
313 and F8000 Super-I/O chips. 313 F71889FG and F8000 Super-I/O chips.
314 314
315 This driver can also be built as a module. If so, the module 315 This driver can also be built as a module. If so, the module
316 will be called f71882fg. 316 will be called f71882fg.
diff --git a/drivers/hwmon/f71882fg.c b/drivers/hwmon/f71882fg.c
index 3a695f06905e..a95fa4256caa 100644
--- a/drivers/hwmon/f71882fg.c
+++ b/drivers/hwmon/f71882fg.c
@@ -48,6 +48,7 @@
48#define SIO_F71858_ID 0x0507 /* Chipset ID */ 48#define SIO_F71858_ID 0x0507 /* Chipset ID */
49#define SIO_F71862_ID 0x0601 /* Chipset ID */ 49#define SIO_F71862_ID 0x0601 /* Chipset ID */
50#define SIO_F71882_ID 0x0541 /* Chipset ID */ 50#define SIO_F71882_ID 0x0541 /* Chipset ID */
51#define SIO_F71889_ID 0x0723 /* Chipset ID */
51#define SIO_F8000_ID 0x0581 /* Chipset ID */ 52#define SIO_F8000_ID 0x0581 /* Chipset ID */
52 53
53#define REGION_LENGTH 8 54#define REGION_LENGTH 8
@@ -95,12 +96,13 @@ static unsigned short force_id;
95module_param(force_id, ushort, 0); 96module_param(force_id, ushort, 0);
96MODULE_PARM_DESC(force_id, "Override the detected device ID"); 97MODULE_PARM_DESC(force_id, "Override the detected device ID");
97 98
98enum chips { f71858fg, f71862fg, f71882fg, f8000 }; 99enum chips { f71858fg, f71862fg, f71882fg, f71889fg, f8000 };
99 100
100static const char *f71882fg_names[] = { 101static const char *f71882fg_names[] = {
101 "f71858fg", 102 "f71858fg",
102 "f71862fg", 103 "f71862fg",
103 "f71882fg", 104 "f71882fg",
105 "f71889fg",
104 "f8000", 106 "f8000",
105}; 107};
106 108
@@ -155,7 +157,7 @@ struct f71882fg_data {
155 u8 pwm_auto_point_hyst[2]; 157 u8 pwm_auto_point_hyst[2];
156 u8 pwm_auto_point_mapping[4]; 158 u8 pwm_auto_point_mapping[4];
157 u8 pwm_auto_point_pwm[4][5]; 159 u8 pwm_auto_point_pwm[4][5];
158 u8 pwm_auto_point_temp[4][4]; 160 s8 pwm_auto_point_temp[4][4];
159}; 161};
160 162
161/* Sysfs in */ 163/* Sysfs in */
@@ -945,7 +947,7 @@ static struct f71882fg_data *f71882fg_update_device(struct device *dev)
945 /* Update once every 60 seconds */ 947 /* Update once every 60 seconds */
946 if ( time_after(jiffies, data->last_limits + 60 * HZ ) || 948 if ( time_after(jiffies, data->last_limits + 60 * HZ ) ||
947 !data->valid) { 949 !data->valid) {
948 if (data->type == f71882fg) { 950 if (data->type == f71882fg || data->type == f71889fg) {
949 data->in1_max = 951 data->in1_max =
950 f71882fg_read8(data, F71882FG_REG_IN1_HIGH); 952 f71882fg_read8(data, F71882FG_REG_IN1_HIGH);
951 data->in_beep = 953 data->in_beep =
@@ -967,7 +969,8 @@ static struct f71882fg_data *f71882fg_update_device(struct device *dev)
967 F71882FG_REG_TEMP_HYST(1)); 969 F71882FG_REG_TEMP_HYST(1));
968 } 970 }
969 971
970 if (data->type == f71862fg || data->type == f71882fg) { 972 if (data->type == f71862fg || data->type == f71882fg ||
973 data->type == f71889fg) {
971 data->fan_beep = f71882fg_read8(data, 974 data->fan_beep = f71882fg_read8(data,
972 F71882FG_REG_FAN_BEEP); 975 F71882FG_REG_FAN_BEEP);
973 data->temp_beep = f71882fg_read8(data, 976 data->temp_beep = f71882fg_read8(data,
@@ -977,15 +980,33 @@ static struct f71882fg_data *f71882fg_update_device(struct device *dev)
977 data->temp_type[2] = (reg & 0x04) ? 2 : 4; 980 data->temp_type[2] = (reg & 0x04) ? 2 : 4;
978 data->temp_type[3] = (reg & 0x08) ? 2 : 4; 981 data->temp_type[3] = (reg & 0x08) ? 2 : 4;
979 } 982 }
980 reg2 = f71882fg_read8(data, F71882FG_REG_PECI); 983 /* Determine temp index 1 sensor type */
981 if ((reg2 & 0x03) == 0x01) 984 if (data->type == f71889fg) {
982 data->temp_type[1] = 6 /* PECI */; 985 reg2 = f71882fg_read8(data, F71882FG_REG_START);
983 else if ((reg2 & 0x03) == 0x02) 986 switch ((reg2 & 0x60) >> 5) {
984 data->temp_type[1] = 5 /* AMDSI */; 987 case 0x00: /* BJT / Thermistor */
985 else if (data->type == f71862fg || data->type == f71882fg) 988 data->temp_type[1] = (reg & 0x02) ? 2 : 4;
986 data->temp_type[1] = (reg & 0x02) ? 2 : 4; 989 break;
987 else 990 case 0x01: /* AMDSI */
988 data->temp_type[1] = 2; /* Only supports BJT */ 991 data->temp_type[1] = 5;
992 break;
993 case 0x02: /* PECI */
994 case 0x03: /* Ibex Peak ?? Report as PECI for now */
995 data->temp_type[1] = 6;
996 break;
997 }
998 } else {
999 reg2 = f71882fg_read8(data, F71882FG_REG_PECI);
1000 if ((reg2 & 0x03) == 0x01)
1001 data->temp_type[1] = 6; /* PECI */
1002 else if ((reg2 & 0x03) == 0x02)
1003 data->temp_type[1] = 5; /* AMDSI */
1004 else if (data->type == f71862fg ||
1005 data->type == f71882fg)
1006 data->temp_type[1] = (reg & 0x02) ? 2 : 4;
1007 else /* f71858fg and f8000 only support BJT */
1008 data->temp_type[1] = 2;
1009 }
989 1010
990 data->pwm_enable = f71882fg_read8(data, 1011 data->pwm_enable = f71882fg_read8(data,
991 F71882FG_REG_PWM_ENABLE); 1012 F71882FG_REG_PWM_ENABLE);
@@ -1062,7 +1083,7 @@ static struct f71882fg_data *f71882fg_update_device(struct device *dev)
1062 if (data->type == f8000) 1083 if (data->type == f8000)
1063 data->fan[3] = f71882fg_read16(data, 1084 data->fan[3] = f71882fg_read16(data,
1064 F71882FG_REG_FAN(3)); 1085 F71882FG_REG_FAN(3));
1065 if (data->type == f71882fg) 1086 if (data->type == f71882fg || data->type == f71889fg)
1066 data->in_status = f71882fg_read8(data, 1087 data->in_status = f71882fg_read8(data,
1067 F71882FG_REG_IN_STATUS); 1088 F71882FG_REG_IN_STATUS);
1068 for (nr = 0; nr < nr_ins; nr++) 1089 for (nr = 0; nr < nr_ins; nr++)
@@ -1780,7 +1801,11 @@ static ssize_t store_pwm_auto_point_temp(struct device *dev,
1780 int pwm = to_sensor_dev_attr_2(devattr)->index; 1801 int pwm = to_sensor_dev_attr_2(devattr)->index;
1781 int point = to_sensor_dev_attr_2(devattr)->nr; 1802 int point = to_sensor_dev_attr_2(devattr)->nr;
1782 long val = simple_strtol(buf, NULL, 10) / 1000; 1803 long val = simple_strtol(buf, NULL, 10) / 1000;
1783 val = SENSORS_LIMIT(val, 0, 255); 1804
1805 if (data->type == f71889fg)
1806 val = SENSORS_LIMIT(val, -128, 127);
1807 else
1808 val = SENSORS_LIMIT(val, 0, 127);
1784 1809
1785 mutex_lock(&data->update_lock); 1810 mutex_lock(&data->update_lock);
1786 f71882fg_write8(data, F71882FG_REG_POINT_TEMP(pwm, point), val); 1811 f71882fg_write8(data, F71882FG_REG_POINT_TEMP(pwm, point), val);
@@ -1871,6 +1896,7 @@ static int __devinit f71882fg_probe(struct platform_device *pdev)
1871 ARRAY_SIZE(f71858fg_in_temp_attr)); 1896 ARRAY_SIZE(f71858fg_in_temp_attr));
1872 break; 1897 break;
1873 case f71882fg: 1898 case f71882fg:
1899 case f71889fg:
1874 err = f71882fg_create_sysfs_files(pdev, 1900 err = f71882fg_create_sysfs_files(pdev,
1875 fxxxx_in1_alarm_attr, 1901 fxxxx_in1_alarm_attr,
1876 ARRAY_SIZE(fxxxx_in1_alarm_attr)); 1902 ARRAY_SIZE(fxxxx_in1_alarm_attr));
@@ -1908,6 +1934,7 @@ static int __devinit f71882fg_probe(struct platform_device *pdev)
1908 err = (data->pwm_enable & 0x15) != 0x15; 1934 err = (data->pwm_enable & 0x15) != 0x15;
1909 break; 1935 break;
1910 case f71882fg: 1936 case f71882fg:
1937 case f71889fg:
1911 err = 0; 1938 err = 0;
1912 break; 1939 break;
1913 case f8000: 1940 case f8000:
@@ -1927,7 +1954,8 @@ static int __devinit f71882fg_probe(struct platform_device *pdev)
1927 if (err) 1954 if (err)
1928 goto exit_unregister_sysfs; 1955 goto exit_unregister_sysfs;
1929 1956
1930 if (data->type == f71862fg || data->type == f71882fg) { 1957 if (data->type == f71862fg || data->type == f71882fg ||
1958 data->type == f71889fg) {
1931 err = f71882fg_create_sysfs_files(pdev, 1959 err = f71882fg_create_sysfs_files(pdev,
1932 fxxxx_fan_beep_attr, nr_fans); 1960 fxxxx_fan_beep_attr, nr_fans);
1933 if (err) 1961 if (err)
@@ -1950,6 +1978,22 @@ static int __devinit f71882fg_probe(struct platform_device *pdev)
1950 f8000_auto_pwm_attr, 1978 f8000_auto_pwm_attr,
1951 ARRAY_SIZE(f8000_auto_pwm_attr)); 1979 ARRAY_SIZE(f8000_auto_pwm_attr));
1952 break; 1980 break;
1981 case f71889fg:
1982 for (i = 0; i < nr_fans; i++) {
1983 data->pwm_auto_point_mapping[i] =
1984 f71882fg_read8(data,
1985 F71882FG_REG_POINT_MAPPING(i));
1986 if (data->pwm_auto_point_mapping[i] & 0x80)
1987 break;
1988 }
1989 if (i != nr_fans) {
1990 dev_warn(&pdev->dev,
1991 "Auto pwm controlled by raw digital "
1992 "data, disabling pwm auto_point "
1993 "sysfs attributes\n");
1994 break;
1995 }
1996 /* fall through */
1953 default: /* f71858fg / f71882fg */ 1997 default: /* f71858fg / f71882fg */
1954 err = f71882fg_create_sysfs_files(pdev, 1998 err = f71882fg_create_sysfs_files(pdev,
1955 &fxxxx_auto_pwm_attr[0][0], 1999 &fxxxx_auto_pwm_attr[0][0],
@@ -2006,6 +2050,7 @@ static int f71882fg_remove(struct platform_device *pdev)
2006 ARRAY_SIZE(f71858fg_in_temp_attr)); 2050 ARRAY_SIZE(f71858fg_in_temp_attr));
2007 break; 2051 break;
2008 case f71882fg: 2052 case f71882fg:
2053 case f71889fg:
2009 f71882fg_remove_sysfs_files(pdev, 2054 f71882fg_remove_sysfs_files(pdev,
2010 fxxxx_in1_alarm_attr, 2055 fxxxx_in1_alarm_attr,
2011 ARRAY_SIZE(fxxxx_in1_alarm_attr)); 2056 ARRAY_SIZE(fxxxx_in1_alarm_attr));
@@ -2027,7 +2072,8 @@ static int f71882fg_remove(struct platform_device *pdev)
2027 f71882fg_remove_sysfs_files(pdev, &fxxxx_fan_attr[0][0], 2072 f71882fg_remove_sysfs_files(pdev, &fxxxx_fan_attr[0][0],
2028 ARRAY_SIZE(fxxxx_fan_attr[0]) * nr_fans); 2073 ARRAY_SIZE(fxxxx_fan_attr[0]) * nr_fans);
2029 2074
2030 if (data->type == f71862fg || data->type == f71882fg) 2075 if (data->type == f71862fg || data->type == f71882fg ||
2076 data->type == f71889fg)
2031 f71882fg_remove_sysfs_files(pdev, 2077 f71882fg_remove_sysfs_files(pdev,
2032 fxxxx_fan_beep_attr, nr_fans); 2078 fxxxx_fan_beep_attr, nr_fans);
2033 2079
@@ -2082,11 +2128,15 @@ static int __init f71882fg_find(int sioaddr, unsigned short *address,
2082 case SIO_F71882_ID: 2128 case SIO_F71882_ID:
2083 sio_data->type = f71882fg; 2129 sio_data->type = f71882fg;
2084 break; 2130 break;
2131 case SIO_F71889_ID:
2132 sio_data->type = f71889fg;
2133 break;
2085 case SIO_F8000_ID: 2134 case SIO_F8000_ID:
2086 sio_data->type = f8000; 2135 sio_data->type = f8000;
2087 break; 2136 break;
2088 default: 2137 default:
2089 printk(KERN_INFO DRVNAME ": Unsupported Fintek device\n"); 2138 printk(KERN_INFO DRVNAME ": Unsupported Fintek device: %04x\n",
2139 (unsigned int)devid);
2090 goto exit; 2140 goto exit;
2091 } 2141 }
2092 2142