diff options
60 files changed, 3689 insertions, 1731 deletions
diff --git a/Documentation/hwmon/ads7828 b/Documentation/hwmon/ads7828 new file mode 100644 index 000000000000..75bc4beaf447 --- /dev/null +++ b/Documentation/hwmon/ads7828 | |||
| @@ -0,0 +1,36 @@ | |||
| 1 | Kernel driver ads7828 | ||
| 2 | ===================== | ||
| 3 | |||
| 4 | Supported chips: | ||
| 5 | * Texas Instruments/Burr-Brown ADS7828 | ||
| 6 | Prefix: 'ads7828' | ||
| 7 | Addresses scanned: I2C 0x48, 0x49, 0x4a, 0x4b | ||
| 8 | Datasheet: Publicly available at the Texas Instruments website : | ||
| 9 | http://focus.ti.com/lit/ds/symlink/ads7828.pdf | ||
| 10 | |||
| 11 | Authors: | ||
| 12 | Steve Hardy <steve@linuxrealtime.co.uk> | ||
| 13 | |||
| 14 | Module Parameters | ||
| 15 | ----------------- | ||
| 16 | |||
| 17 | * se_input: bool (default Y) | ||
| 18 | Single ended operation - set to N for differential mode | ||
| 19 | * int_vref: bool (default Y) | ||
| 20 | Operate with the internal 2.5V reference - set to N for external reference | ||
| 21 | * vref_mv: int (default 2500) | ||
| 22 | If using an external reference, set this to the reference voltage in mV | ||
| 23 | |||
| 24 | Description | ||
| 25 | ----------- | ||
| 26 | |||
| 27 | This driver implements support for the Texas Instruments ADS7828. | ||
| 28 | |||
| 29 | This device is a 12-bit 8-channel A-D converter. | ||
| 30 | |||
| 31 | It can operate in single ended mode (8 +ve inputs) or in differential mode, | ||
| 32 | where 4 differential pairs can be measured. | ||
| 33 | |||
| 34 | The chip also has the facility to use an external voltage reference. This | ||
| 35 | may be required if your hardware supplies the ADS7828 from a 5V supply, see | ||
| 36 | the datasheet for more details. | ||
diff --git a/Documentation/hwmon/it87 b/Documentation/hwmon/it87 index 5b704a40256b..f4ce1fdbeff6 100644 --- a/Documentation/hwmon/it87 +++ b/Documentation/hwmon/it87 | |||
| @@ -30,7 +30,7 @@ Supported chips: | |||
| 30 | Datasheet: No longer be available | 30 | Datasheet: No longer be available |
| 31 | 31 | ||
| 32 | Authors: | 32 | Authors: |
| 33 | Christophe Gauthron <chrisg@0-in.com> | 33 | Christophe Gauthron |
| 34 | Jean Delvare <khali@linux-fr.org> | 34 | Jean Delvare <khali@linux-fr.org> |
| 35 | 35 | ||
| 36 | 36 | ||
diff --git a/Documentation/hwmon/lm78 b/Documentation/hwmon/lm78 index dfc318a60fd4..60932e26abaa 100644 --- a/Documentation/hwmon/lm78 +++ b/Documentation/hwmon/lm78 | |||
| @@ -4,12 +4,12 @@ Kernel driver lm78 | |||
| 4 | Supported chips: | 4 | Supported chips: |
| 5 | * National Semiconductor LM78 / LM78-J | 5 | * National Semiconductor LM78 / LM78-J |
| 6 | Prefix: 'lm78' | 6 | Prefix: 'lm78' |
| 7 | Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports) | 7 | Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) |
| 8 | Datasheet: Publicly available at the National Semiconductor website | 8 | Datasheet: Publicly available at the National Semiconductor website |
| 9 | http://www.national.com/ | 9 | http://www.national.com/ |
| 10 | * National Semiconductor LM79 | 10 | * National Semiconductor LM79 |
| 11 | Prefix: 'lm79' | 11 | Prefix: 'lm79' |
| 12 | Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports) | 12 | Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) |
| 13 | Datasheet: Publicly available at the National Semiconductor website | 13 | Datasheet: Publicly available at the National Semiconductor website |
| 14 | http://www.national.com/ | 14 | http://www.national.com/ |
| 15 | 15 | ||
diff --git a/Documentation/hwmon/lm87 b/Documentation/hwmon/lm87 index c952c57f0e11..ec27aa1b94cb 100644 --- a/Documentation/hwmon/lm87 +++ b/Documentation/hwmon/lm87 | |||
| @@ -4,8 +4,12 @@ Kernel driver lm87 | |||
| 4 | Supported chips: | 4 | Supported chips: |
| 5 | * National Semiconductor LM87 | 5 | * National Semiconductor LM87 |
| 6 | Prefix: 'lm87' | 6 | Prefix: 'lm87' |
| 7 | Addresses scanned: I2C 0x2c - 0x2f | 7 | Addresses scanned: I2C 0x2c - 0x2e |
| 8 | Datasheet: http://www.national.com/pf/LM/LM87.html | 8 | Datasheet: http://www.national.com/pf/LM/LM87.html |
| 9 | * Analog Devices ADM1024 | ||
| 10 | Prefix: 'adm1024' | ||
| 11 | Addresses scanned: I2C 0x2c - 0x2e | ||
| 12 | Datasheet: http://www.analog.com/en/prod/0,2877,ADM1024,00.html | ||
| 9 | 13 | ||
| 10 | Authors: | 14 | Authors: |
| 11 | Frodo Looijaard <frodol@dds.nl>, | 15 | Frodo Looijaard <frodol@dds.nl>, |
| @@ -19,11 +23,12 @@ Authors: | |||
| 19 | Description | 23 | Description |
| 20 | ----------- | 24 | ----------- |
| 21 | 25 | ||
| 22 | This driver implements support for the National Semiconductor LM87. | 26 | This driver implements support for the National Semiconductor LM87 |
| 27 | and the Analog Devices ADM1024. | ||
| 23 | 28 | ||
| 24 | The LM87 implements up to three temperature sensors, up to two fan | 29 | The LM87 implements up to three temperature sensors, up to two fan |
| 25 | rotation speed sensors, up to seven voltage sensors, alarms, and some | 30 | rotation speed sensors, up to seven voltage sensors, alarms, and some |
| 26 | miscellaneous stuff. | 31 | miscellaneous stuff. The ADM1024 is fully compatible. |
| 27 | 32 | ||
| 28 | Temperatures are measured in degrees Celsius. Each input has a high | 33 | Temperatures are measured in degrees Celsius. Each input has a high |
| 29 | and low alarm settings. A high limit produces an alarm when the value | 34 | and low alarm settings. A high limit produces an alarm when the value |
diff --git a/Documentation/hwmon/userspace-tools b/Documentation/hwmon/userspace-tools index 19900a8fe679..9865aeedc58f 100644 --- a/Documentation/hwmon/userspace-tools +++ b/Documentation/hwmon/userspace-tools | |||
| @@ -14,7 +14,7 @@ Lm-sensors | |||
| 14 | 14 | ||
| 15 | Core set of utilities that will allow you to obtain health information, | 15 | Core set of utilities that will allow you to obtain health information, |
| 16 | setup monitoring limits etc. You can get them on their homepage | 16 | setup monitoring limits etc. You can get them on their homepage |
| 17 | http://www.lm-sensors.nu/ or as a package from your Linux distribution. | 17 | http://www.lm-sensors.org/ or as a package from your Linux distribution. |
| 18 | 18 | ||
| 19 | If from website: | 19 | If from website: |
| 20 | Get lm-sensors from project web site. Please note, you need only userspace | 20 | Get lm-sensors from project web site. Please note, you need only userspace |
diff --git a/Documentation/hwmon/w83627ehf b/Documentation/hwmon/w83627ehf index ccc2bcb61068..d6e1ae30fa6e 100644 --- a/Documentation/hwmon/w83627ehf +++ b/Documentation/hwmon/w83627ehf | |||
| @@ -23,8 +23,9 @@ W83627DHG super I/O chips. We will refer to them collectively as Winbond chips. | |||
| 23 | 23 | ||
| 24 | The chips implement three temperature sensors, five fan rotation | 24 | The chips implement three temperature sensors, five fan rotation |
| 25 | speed sensors, ten analog voltage sensors (only nine for the 627DHG), one | 25 | speed sensors, ten analog voltage sensors (only nine for the 627DHG), one |
| 26 | VID (6 pins), alarms with beep warnings (control unimplemented), and | 26 | VID (6 pins for the 627EHF/EHG, 8 pins for the 627DHG), alarms with beep |
| 27 | some automatic fan regulation strategies (plus manual fan control mode). | 27 | warnings (control unimplemented), and some automatic fan regulation |
| 28 | strategies (plus manual fan control mode). | ||
| 28 | 29 | ||
| 29 | Temperatures are measured in degrees Celsius and measurement resolution is 1 | 30 | Temperatures are measured in degrees Celsius and measurement resolution is 1 |
| 30 | degC for temp1 and 0.5 degC for temp2 and temp3. An alarm is triggered when | 31 | degC for temp1 and 0.5 degC for temp2 and temp3. An alarm is triggered when |
diff --git a/Documentation/hwmon/w83627hf b/Documentation/hwmon/w83627hf index 792231921241..880a59f53da9 100644 --- a/Documentation/hwmon/w83627hf +++ b/Documentation/hwmon/w83627hf | |||
| @@ -73,5 +73,4 @@ doesn't help, you may just ignore the bogus VID reading with no harm done. | |||
| 73 | 73 | ||
| 74 | For further information on this driver see the w83781d driver documentation. | 74 | For further information on this driver see the w83781d driver documentation. |
| 75 | 75 | ||
| 76 | [1] http://www2.lm-sensors.nu/~lm78/cvs/browse.cgi/lm_sensors2/doc/vid | 76 | [1] http://www.lm-sensors.org/browser/lm-sensors/trunk/doc/vid |
| 77 | |||
diff --git a/Documentation/hwmon/w83781d b/Documentation/hwmon/w83781d index b1e9f80098ee..6f800a0283e9 100644 --- a/Documentation/hwmon/w83781d +++ b/Documentation/hwmon/w83781d | |||
| @@ -4,20 +4,16 @@ Kernel driver w83781d | |||
| 4 | Supported chips: | 4 | Supported chips: |
| 5 | * Winbond W83781D | 5 | * Winbond W83781D |
| 6 | Prefix: 'w83781d' | 6 | Prefix: 'w83781d' |
| 7 | Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports) | 7 | Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) |
| 8 | Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83781d.pdf | 8 | Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83781d.pdf |
| 9 | * Winbond W83782D | 9 | * Winbond W83782D |
| 10 | Prefix: 'w83782d' | 10 | Prefix: 'w83782d' |
| 11 | Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports) | 11 | Addresses scanned: I2C 0x28 - 0x2f, ISA 0x290 (8 I/O ports) |
| 12 | Datasheet: http://www.winbond.com/PDF/sheet/w83782d.pdf | 12 | Datasheet: http://www.winbond.com/PDF/sheet/w83782d.pdf |
| 13 | * Winbond W83783S | 13 | * Winbond W83783S |
| 14 | Prefix: 'w83783s' | 14 | Prefix: 'w83783s' |
| 15 | Addresses scanned: I2C 0x2d | 15 | Addresses scanned: I2C 0x2d |
| 16 | Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83783s.pdf | 16 | Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/w83783s.pdf |
| 17 | * Winbond W83627HF | ||
| 18 | Prefix: 'w83627hf' | ||
| 19 | Addresses scanned: I2C 0x20 - 0x2f, ISA 0x290 (8 I/O ports) | ||
| 20 | Datasheet: http://www.winbond.com/PDF/sheet/w83627hf.pdf | ||
| 21 | * Asus AS99127F | 17 | * Asus AS99127F |
| 22 | Prefix: 'as99127f' | 18 | Prefix: 'as99127f' |
| 23 | Addresses scanned: I2C 0x28 - 0x2f | 19 | Addresses scanned: I2C 0x28 - 0x2f |
| @@ -50,20 +46,18 @@ force_subclients=bus,caddr,saddr,saddr | |||
| 50 | Description | 46 | Description |
| 51 | ----------- | 47 | ----------- |
| 52 | 48 | ||
| 53 | This driver implements support for the Winbond W83781D, W83782D, W83783S, | 49 | This driver implements support for the Winbond W83781D, W83782D, W83783S |
| 54 | W83627HF chips, and the Asus AS99127F chips. We will refer to them | 50 | chips, and the Asus AS99127F chips. We will refer to them collectively as |
| 55 | collectively as W8378* chips. | 51 | W8378* chips. |
| 56 | 52 | ||
| 57 | There is quite some difference between these chips, but they are similar | 53 | There is quite some difference between these chips, but they are similar |
| 58 | enough that it was sensible to put them together in one driver. | 54 | enough that it was sensible to put them together in one driver. |
| 59 | The W83627HF chip is assumed to be identical to the ISA W83782D. | ||
| 60 | The Asus chips are similar to an I2C-only W83782D. | 55 | The Asus chips are similar to an I2C-only W83782D. |
| 61 | 56 | ||
| 62 | Chip #vin #fanin #pwm #temp wchipid vendid i2c ISA | 57 | Chip #vin #fanin #pwm #temp wchipid vendid i2c ISA |
| 63 | as99127f 7 3 0 3 0x31 0x12c3 yes no | 58 | as99127f 7 3 0 3 0x31 0x12c3 yes no |
| 64 | as99127f rev.2 (type_name = as99127f) 0x31 0x5ca3 yes no | 59 | as99127f rev.2 (type_name = as99127f) 0x31 0x5ca3 yes no |
| 65 | w83781d 7 3 0 3 0x10-1 0x5ca3 yes yes | 60 | w83781d 7 3 0 3 0x10-1 0x5ca3 yes yes |
| 66 | w83627hf 9 3 2 3 0x21 0x5ca3 yes yes(LPC) | ||
| 67 | w83782d 9 3 2-4 3 0x30 0x5ca3 yes yes | 61 | w83782d 9 3 2-4 3 0x30 0x5ca3 yes yes |
| 68 | w83783s 5-6 3 2 1-2 0x40 0x5ca3 yes no | 62 | w83783s 5-6 3 2 1-2 0x40 0x5ca3 yes no |
| 69 | 63 | ||
| @@ -143,9 +137,9 @@ Individual alarm and beep bits: | |||
| 143 | 0x000400: in6 | 137 | 0x000400: in6 |
| 144 | 0x000800: fan3 | 138 | 0x000800: fan3 |
| 145 | 0x001000: chassis | 139 | 0x001000: chassis |
| 146 | 0x002000: temp3 (W83782D and W83627HF only) | 140 | 0x002000: temp3 (W83782D only) |
| 147 | 0x010000: in7 (W83782D and W83627HF only) | 141 | 0x010000: in7 (W83782D only) |
| 148 | 0x020000: in8 (W83782D and W83627HF only) | 142 | 0x020000: in8 (W83782D only) |
| 149 | 143 | ||
| 150 | If an alarm triggers, it will remain triggered until the hardware register | 144 | If an alarm triggers, it will remain triggered until the hardware register |
| 151 | is read at least once. This means that the cause for the alarm may | 145 | is read at least once. This means that the cause for the alarm may |
diff --git a/Documentation/hwmon/w83l786ng b/Documentation/hwmon/w83l786ng new file mode 100644 index 000000000000..d8f55d7fff10 --- /dev/null +++ b/Documentation/hwmon/w83l786ng | |||
| @@ -0,0 +1,54 @@ | |||
| 1 | Kernel driver w83l786ng | ||
| 2 | ===================== | ||
| 3 | |||
| 4 | Supported chips: | ||
| 5 | * Winbond W83L786NG/W83L786NR | ||
| 6 | Prefix: 'w83l786ng' | ||
| 7 | Addresses scanned: I2C 0x2e - 0x2f | ||
| 8 | Datasheet: http://www.winbond-usa.com/products/winbond_products/pdfs/PCIC/W83L786NRNG09.pdf | ||
| 9 | |||
| 10 | Author: Kevin Lo <kevlo@kevlo.org> | ||
| 11 | |||
| 12 | |||
| 13 | Module Parameters | ||
| 14 | ----------------- | ||
| 15 | |||
| 16 | * reset boolean | ||
| 17 | (default 0) | ||
| 18 | Use 'reset=1' to reset the chip (via index 0x40, bit 7). The default | ||
| 19 | behavior is no chip reset to preserve BIOS settings | ||
| 20 | |||
| 21 | |||
| 22 | Description | ||
| 23 | ----------- | ||
| 24 | |||
| 25 | This driver implements support for Winbond W83L786NG/W83L786NR chips. | ||
| 26 | |||
| 27 | The driver implements two temperature sensors, two fan rotation speed | ||
| 28 | sensors, and three voltage sensors. | ||
| 29 | |||
| 30 | Temperatures are measured in degrees Celsius and measurement resolution is 1 | ||
| 31 | degC for temp1 and temp2. | ||
| 32 | |||
| 33 | Fan rotation speeds are reported in RPM (rotations per minute). Fan readings | ||
| 34 | readings can be divided by a programmable divider (1, 2, 4, 8, 16, 32, 64 | ||
| 35 | or 128 for fan 1/2) to give the readings more range or accuracy. | ||
| 36 | |||
| 37 | Voltage sensors (also known as IN sensors) report their values in millivolts. | ||
| 38 | An alarm is triggered if the voltage has crossed a programmable minimum | ||
| 39 | or maximum limit. | ||
| 40 | |||
| 41 | /sys files | ||
| 42 | ---------- | ||
| 43 | |||
| 44 | pwm[1-2] - this file stores PWM duty cycle or DC value (fan speed) in range: | ||
| 45 | 0 (stop) to 255 (full) | ||
| 46 | pwm[1-2]_enable - this file controls mode of fan/temperature control: | ||
| 47 | * 0 Manual Mode | ||
| 48 | * 1 Thermal Cruise | ||
| 49 | * 2 Smart Fan II | ||
| 50 | * 4 FAN_SET | ||
| 51 | pwm[1-2]_mode - Select PWM of DC mode | ||
| 52 | * 0 DC | ||
| 53 | * 1 PWM | ||
| 54 | tolerance[1-2] - Value in degrees of Celsius (degC) for +- T | ||
diff --git a/Documentation/i2c/busses/i2c-piix4 b/Documentation/i2c/busses/i2c-piix4 index cf6b6cb02aa1..ef1efa79b1df 100644 --- a/Documentation/i2c/busses/i2c-piix4 +++ b/Documentation/i2c/busses/i2c-piix4 | |||
| @@ -95,4 +95,4 @@ of all affected systems, so the only safe solution was to prevent access to | |||
| 95 | the SMBus on all IBM systems (detected using DMI data.) | 95 | the SMBus on all IBM systems (detected using DMI data.) |
| 96 | 96 | ||
| 97 | For additional information, read: | 97 | For additional information, read: |
| 98 | http://www2.lm-sensors.nu/~lm78/cvs/lm_sensors2/README.thinkpad | 98 | http://www.lm-sensors.org/browser/lm-sensors/trunk/README.thinkpad |
diff --git a/drivers/firmware/dmi_scan.c b/drivers/firmware/dmi_scan.c index e0bade732376..1412d7bcdbd1 100644 --- a/drivers/firmware/dmi_scan.c +++ b/drivers/firmware/dmi_scan.c | |||
| @@ -43,18 +43,12 @@ static char * __init dmi_string(const struct dmi_header *dm, u8 s) | |||
| 43 | * We have to be cautious here. We have seen BIOSes with DMI pointers | 43 | * We have to be cautious here. We have seen BIOSes with DMI pointers |
| 44 | * pointing to completely the wrong place for example | 44 | * pointing to completely the wrong place for example |
| 45 | */ | 45 | */ |
| 46 | static int __init dmi_table(u32 base, int len, int num, | 46 | static void dmi_table(u8 *buf, int len, int num, |
| 47 | void (*decode)(const struct dmi_header *)) | 47 | void (*decode)(const struct dmi_header *)) |
| 48 | { | 48 | { |
| 49 | u8 *buf, *data; | 49 | u8 *data = buf; |
| 50 | int i = 0; | 50 | int i = 0; |
| 51 | 51 | ||
| 52 | buf = dmi_ioremap(base, len); | ||
| 53 | if (buf == NULL) | ||
| 54 | return -1; | ||
| 55 | |||
| 56 | data = buf; | ||
| 57 | |||
| 58 | /* | 52 | /* |
| 59 | * Stop when we see all the items the table claimed to have | 53 | * Stop when we see all the items the table claimed to have |
| 60 | * OR we run off the end of the table (also happens) | 54 | * OR we run off the end of the table (also happens) |
| @@ -75,7 +69,23 @@ static int __init dmi_table(u32 base, int len, int num, | |||
| 75 | data += 2; | 69 | data += 2; |
| 76 | i++; | 70 | i++; |
| 77 | } | 71 | } |
| 78 | dmi_iounmap(buf, len); | 72 | } |
| 73 | |||
| 74 | static u32 dmi_base; | ||
| 75 | static u16 dmi_len; | ||
| 76 | static u16 dmi_num; | ||
| 77 | |||
| 78 | static int __init dmi_walk_early(void (*decode)(const struct dmi_header *)) | ||
| 79 | { | ||
| 80 | u8 *buf; | ||
| 81 | |||
| 82 | buf = dmi_ioremap(dmi_base, dmi_len); | ||
| 83 | if (buf == NULL) | ||
| 84 | return -1; | ||
| 85 | |||
| 86 | dmi_table(buf, dmi_len, dmi_num, decode); | ||
| 87 | |||
| 88 | dmi_iounmap(buf, dmi_len); | ||
| 79 | return 0; | 89 | return 0; |
| 80 | } | 90 | } |
| 81 | 91 | ||
| @@ -291,9 +301,9 @@ static int __init dmi_present(const char __iomem *p) | |||
| 291 | 301 | ||
| 292 | memcpy_fromio(buf, p, 15); | 302 | memcpy_fromio(buf, p, 15); |
| 293 | if ((memcmp(buf, "_DMI_", 5) == 0) && dmi_checksum(buf)) { | 303 | if ((memcmp(buf, "_DMI_", 5) == 0) && dmi_checksum(buf)) { |
| 294 | u16 num = (buf[13] << 8) | buf[12]; | 304 | dmi_num = (buf[13] << 8) | buf[12]; |
| 295 | u16 len = (buf[7] << 8) | buf[6]; | 305 | dmi_len = (buf[7] << 8) | buf[6]; |
| 296 | u32 base = (buf[11] << 24) | (buf[10] << 16) | | 306 | dmi_base = (buf[11] << 24) | (buf[10] << 16) | |
| 297 | (buf[9] << 8) | buf[8]; | 307 | (buf[9] << 8) | buf[8]; |
| 298 | 308 | ||
| 299 | /* | 309 | /* |
| @@ -305,7 +315,7 @@ static int __init dmi_present(const char __iomem *p) | |||
| 305 | buf[14] >> 4, buf[14] & 0xF); | 315 | buf[14] >> 4, buf[14] & 0xF); |
| 306 | else | 316 | else |
| 307 | printk(KERN_INFO "DMI present.\n"); | 317 | printk(KERN_INFO "DMI present.\n"); |
| 308 | if (dmi_table(base,len, num, dmi_decode) == 0) | 318 | if (dmi_walk_early(dmi_decode) == 0) |
| 309 | return 0; | 319 | return 0; |
| 310 | } | 320 | } |
| 311 | return 1; | 321 | return 1; |
| @@ -489,3 +499,27 @@ int dmi_get_year(int field) | |||
| 489 | 499 | ||
| 490 | return year; | 500 | return year; |
| 491 | } | 501 | } |
| 502 | |||
| 503 | /** | ||
| 504 | * dmi_walk - Walk the DMI table and get called back for every record | ||
| 505 | * @decode: Callback function | ||
| 506 | * | ||
| 507 | * Returns -1 when the DMI table can't be reached, 0 on success. | ||
| 508 | */ | ||
| 509 | int dmi_walk(void (*decode)(const struct dmi_header *)) | ||
| 510 | { | ||
| 511 | u8 *buf; | ||
| 512 | |||
| 513 | if (!dmi_available) | ||
| 514 | return -1; | ||
| 515 | |||
| 516 | buf = ioremap(dmi_base, dmi_len); | ||
| 517 | if (buf == NULL) | ||
| 518 | return -1; | ||
| 519 | |||
| 520 | dmi_table(buf, dmi_len, dmi_num, decode); | ||
| 521 | |||
| 522 | iounmap(buf); | ||
| 523 | return 0; | ||
| 524 | } | ||
| 525 | EXPORT_SYMBOL_GPL(dmi_walk); | ||
diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig index a0445bea9f75..410ffe4e9d80 100644 --- a/drivers/hwmon/Kconfig +++ b/drivers/hwmon/Kconfig | |||
| @@ -433,12 +433,12 @@ config SENSORS_LM85 | |||
| 433 | will be called lm85. | 433 | will be called lm85. |
| 434 | 434 | ||
| 435 | config SENSORS_LM87 | 435 | config SENSORS_LM87 |
| 436 | tristate "National Semiconductor LM87" | 436 | tristate "National Semiconductor LM87 and compatibles" |
| 437 | depends on I2C | 437 | depends on I2C |
| 438 | select HWMON_VID | 438 | select HWMON_VID |
| 439 | help | 439 | help |
| 440 | If you say yes here you get support for National Semiconductor LM87 | 440 | If you say yes here you get support for National Semiconductor LM87 |
| 441 | sensor chips. | 441 | and Analog Devices ADM1024 sensor chips. |
| 442 | 442 | ||
| 443 | This driver can also be built as a module. If so, the module | 443 | This driver can also be built as a module. If so, the module |
| 444 | will be called lm87. | 444 | will be called lm87. |
| @@ -588,6 +588,16 @@ config SENSORS_SMSC47B397 | |||
| 588 | This driver can also be built as a module. If so, the module | 588 | This driver can also be built as a module. If so, the module |
| 589 | will be called smsc47b397. | 589 | will be called smsc47b397. |
| 590 | 590 | ||
| 591 | config SENSORS_ADS7828 | ||
| 592 | tristate "Texas Instruments ADS7828" | ||
| 593 | depends on I2C | ||
| 594 | help | ||
| 595 | If you say yes here you get support for Texas Instruments ADS7828 | ||
| 596 | 12-bit 8-channel ADC device. | ||
| 597 | |||
| 598 | This driver can also be built as a module. If so, the module | ||
| 599 | will be called ads7828. | ||
| 600 | |||
| 591 | config SENSORS_THMC50 | 601 | config SENSORS_THMC50 |
| 592 | tristate "Texas Instruments THMC50 / Analog Devices ADM1022" | 602 | tristate "Texas Instruments THMC50 / Analog Devices ADM1022" |
| 593 | depends on I2C && EXPERIMENTAL | 603 | depends on I2C && EXPERIMENTAL |
| @@ -631,13 +641,13 @@ config SENSORS_VT8231 | |||
| 631 | will be called vt8231. | 641 | will be called vt8231. |
| 632 | 642 | ||
| 633 | config SENSORS_W83781D | 643 | config SENSORS_W83781D |
| 634 | tristate "Winbond W83781D, W83782D, W83783S, W83627HF, Asus AS99127F" | 644 | tristate "Winbond W83781D, W83782D, W83783S, Asus AS99127F" |
| 635 | depends on I2C | 645 | depends on I2C |
| 636 | select HWMON_VID | 646 | select HWMON_VID |
| 637 | help | 647 | help |
| 638 | If you say yes here you get support for the Winbond W8378x series | 648 | If you say yes here you get support for the Winbond W8378x series |
| 639 | of sensor chips: the W83781D, W83782D, W83783S and W83627HF, | 649 | of sensor chips: the W83781D, W83782D and W83783S, and the similar |
| 640 | and the similar Asus AS99127F. | 650 | Asus AS99127F. |
| 641 | 651 | ||
| 642 | This driver can also be built as a module. If so, the module | 652 | This driver can also be built as a module. If so, the module |
| 643 | will be called w83781d. | 653 | will be called w83781d. |
| @@ -683,6 +693,16 @@ config SENSORS_W83L785TS | |||
| 683 | This driver can also be built as a module. If so, the module | 693 | This driver can also be built as a module. If so, the module |
| 684 | will be called w83l785ts. | 694 | will be called w83l785ts. |
| 685 | 695 | ||
| 696 | config SENSORS_W83L786NG | ||
| 697 | tristate "Winbond W83L786NG, W83L786NR" | ||
| 698 | depends on I2C && EXPERIMENTAL | ||
| 699 | help | ||
| 700 | If you say yes here you get support for the Winbond W83L786NG | ||
| 701 | and W83L786NR sensor chips. | ||
| 702 | |||
| 703 | This driver can also be built as a module. If so, the module | ||
| 704 | will be called w83l786ng. | ||
| 705 | |||
| 686 | config SENSORS_W83627HF | 706 | config SENSORS_W83627HF |
| 687 | tristate "Winbond W83627HF, W83627THF, W83637HF, W83687THF, W83697HF" | 707 | tristate "Winbond W83627HF, W83627THF, W83637HF, W83687THF, W83697HF" |
| 688 | select HWMON_VID | 708 | select HWMON_VID |
diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile index 55595f6e1aa6..824161337f1c 100644 --- a/drivers/hwmon/Makefile +++ b/drivers/hwmon/Makefile | |||
| @@ -22,6 +22,7 @@ obj-$(CONFIG_SENSORS_ADM1026) += adm1026.o | |||
| 22 | obj-$(CONFIG_SENSORS_ADM1029) += adm1029.o | 22 | obj-$(CONFIG_SENSORS_ADM1029) += adm1029.o |
| 23 | obj-$(CONFIG_SENSORS_ADM1031) += adm1031.o | 23 | obj-$(CONFIG_SENSORS_ADM1031) += adm1031.o |
| 24 | obj-$(CONFIG_SENSORS_ADM9240) += adm9240.o | 24 | obj-$(CONFIG_SENSORS_ADM9240) += adm9240.o |
| 25 | obj-$(CONFIG_SENSORS_ADS7828) += ads7828.o | ||
| 25 | obj-$(CONFIG_SENSORS_ADT7470) += adt7470.o | 26 | obj-$(CONFIG_SENSORS_ADT7470) += adt7470.o |
| 26 | obj-$(CONFIG_SENSORS_APPLESMC) += applesmc.o | 27 | obj-$(CONFIG_SENSORS_APPLESMC) += applesmc.o |
| 27 | obj-$(CONFIG_SENSORS_AMS) += ams/ | 28 | obj-$(CONFIG_SENSORS_AMS) += ams/ |
| @@ -68,6 +69,7 @@ obj-$(CONFIG_SENSORS_VT1211) += vt1211.o | |||
| 68 | obj-$(CONFIG_SENSORS_VT8231) += vt8231.o | 69 | obj-$(CONFIG_SENSORS_VT8231) += vt8231.o |
| 69 | obj-$(CONFIG_SENSORS_W83627EHF) += w83627ehf.o | 70 | obj-$(CONFIG_SENSORS_W83627EHF) += w83627ehf.o |
| 70 | obj-$(CONFIG_SENSORS_W83L785TS) += w83l785ts.o | 71 | obj-$(CONFIG_SENSORS_W83L785TS) += w83l785ts.o |
| 72 | obj-$(CONFIG_SENSORS_W83L786NG) += w83l786ng.o | ||
| 71 | 73 | ||
| 72 | ifeq ($(CONFIG_HWMON_DEBUG_CHIP),y) | 74 | ifeq ($(CONFIG_HWMON_DEBUG_CHIP),y) |
| 73 | EXTRA_CFLAGS += -DDEBUG | 75 | EXTRA_CFLAGS += -DDEBUG |
diff --git a/drivers/hwmon/abituguru3.c b/drivers/hwmon/abituguru3.c index d9f04ce90327..ed33fddc4dee 100644 --- a/drivers/hwmon/abituguru3.c +++ b/drivers/hwmon/abituguru3.c | |||
| @@ -528,6 +528,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
| 528 | { "AUX1 Fan", 33, 2, 60, 1, 0 }, | 528 | { "AUX1 Fan", 33, 2, 60, 1, 0 }, |
| 529 | { "AUX2 Fan", 35, 2, 60, 1, 0 }, | 529 | { "AUX2 Fan", 35, 2, 60, 1, 0 }, |
| 530 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, | 530 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, |
| 531 | { "AUX4 Fan", 37, 2, 60, 1, 0 }, | ||
| 531 | { NULL, 0, 0, 0, 0, 0 } } | 532 | { NULL, 0, 0, 0, 0, 0 } } |
| 532 | }, | 533 | }, |
| 533 | { 0x001B, "unknown", { | 534 | { 0x001B, "unknown", { |
diff --git a/drivers/hwmon/adm1021.c b/drivers/hwmon/adm1021.c index ebdc6d7db231..b96be772e498 100644 --- a/drivers/hwmon/adm1021.c +++ b/drivers/hwmon/adm1021.c | |||
| @@ -115,7 +115,6 @@ static struct i2c_driver adm1021_driver = { | |||
| 115 | .driver = { | 115 | .driver = { |
| 116 | .name = "adm1021", | 116 | .name = "adm1021", |
| 117 | }, | 117 | }, |
| 118 | .id = I2C_DRIVERID_ADM1021, | ||
| 119 | .attach_adapter = adm1021_attach_adapter, | 118 | .attach_adapter = adm1021_attach_adapter, |
| 120 | .detach_client = adm1021_detach_client, | 119 | .detach_client = adm1021_detach_client, |
| 121 | }; | 120 | }; |
diff --git a/drivers/hwmon/adm1025.c b/drivers/hwmon/adm1025.c index 041ecb0bdf48..e96c3725203d 100644 --- a/drivers/hwmon/adm1025.c +++ b/drivers/hwmon/adm1025.c | |||
| @@ -51,6 +51,7 @@ | |||
| 51 | #include <linux/jiffies.h> | 51 | #include <linux/jiffies.h> |
| 52 | #include <linux/i2c.h> | 52 | #include <linux/i2c.h> |
| 53 | #include <linux/hwmon.h> | 53 | #include <linux/hwmon.h> |
| 54 | #include <linux/hwmon-sysfs.h> | ||
| 54 | #include <linux/hwmon-vid.h> | 55 | #include <linux/hwmon-vid.h> |
| 55 | #include <linux/err.h> | 56 | #include <linux/err.h> |
| 56 | #include <linux/mutex.h> | 57 | #include <linux/mutex.h> |
| @@ -74,7 +75,7 @@ I2C_CLIENT_INSMOD_2(adm1025, ne1619); | |||
| 74 | */ | 75 | */ |
| 75 | 76 | ||
| 76 | #define ADM1025_REG_MAN_ID 0x3E | 77 | #define ADM1025_REG_MAN_ID 0x3E |
| 77 | #define ADM1025_REG_CHIP_ID 0x3F | 78 | #define ADM1025_REG_CHIP_ID 0x3F |
| 78 | #define ADM1025_REG_CONFIG 0x40 | 79 | #define ADM1025_REG_CONFIG 0x40 |
| 79 | #define ADM1025_REG_STATUS1 0x41 | 80 | #define ADM1025_REG_STATUS1 0x41 |
| 80 | #define ADM1025_REG_STATUS2 0x42 | 81 | #define ADM1025_REG_STATUS2 0x42 |
| @@ -92,7 +93,7 @@ I2C_CLIENT_INSMOD_2(adm1025, ne1619); | |||
| 92 | * The ADM1025 uses signed 8-bit values for temperatures. | 93 | * The ADM1025 uses signed 8-bit values for temperatures. |
| 93 | */ | 94 | */ |
| 94 | 95 | ||
| 95 | static int in_scale[6] = { 2500, 2250, 3300, 5000, 12000, 3300 }; | 96 | static const int in_scale[6] = { 2500, 2250, 3300, 5000, 12000, 3300 }; |
| 96 | 97 | ||
| 97 | #define IN_FROM_REG(reg,scale) (((reg) * (scale) + 96) / 192) | 98 | #define IN_FROM_REG(reg,scale) (((reg) * (scale) + 96) / 192) |
| 98 | #define IN_TO_REG(val,scale) ((val) <= 0 ? 0 : \ | 99 | #define IN_TO_REG(val,scale) ((val) <= 0 ? 0 : \ |
| @@ -122,7 +123,6 @@ static struct i2c_driver adm1025_driver = { | |||
| 122 | .driver = { | 123 | .driver = { |
| 123 | .name = "adm1025", | 124 | .name = "adm1025", |
| 124 | }, | 125 | }, |
| 125 | .id = I2C_DRIVERID_ADM1025, | ||
| 126 | .attach_adapter = adm1025_attach_adapter, | 126 | .attach_adapter = adm1025_attach_adapter, |
| 127 | .detach_client = adm1025_detach_client, | 127 | .detach_client = adm1025_detach_client, |
| 128 | }; | 128 | }; |
| @@ -153,86 +153,96 @@ struct adm1025_data { | |||
| 153 | * Sysfs stuff | 153 | * Sysfs stuff |
| 154 | */ | 154 | */ |
| 155 | 155 | ||
| 156 | #define show_in(offset) \ | 156 | static ssize_t |
| 157 | static ssize_t show_in##offset(struct device *dev, struct device_attribute *attr, char *buf) \ | 157 | show_in(struct device *dev, struct device_attribute *attr, char *buf) |
| 158 | { \ | 158 | { |
| 159 | struct adm1025_data *data = adm1025_update_device(dev); \ | 159 | int index = to_sensor_dev_attr(attr)->index; |
| 160 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in[offset], \ | 160 | struct adm1025_data *data = adm1025_update_device(dev); |
| 161 | in_scale[offset])); \ | 161 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in[index], |
| 162 | } \ | 162 | in_scale[index])); |
| 163 | static ssize_t show_in##offset##_min(struct device *dev, struct device_attribute *attr, char *buf) \ | 163 | } |
| 164 | { \ | 164 | |
| 165 | struct adm1025_data *data = adm1025_update_device(dev); \ | 165 | static ssize_t |
| 166 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_min[offset], \ | 166 | show_in_min(struct device *dev, struct device_attribute *attr, char *buf) |
| 167 | in_scale[offset])); \ | 167 | { |
| 168 | } \ | 168 | int index = to_sensor_dev_attr(attr)->index; |
| 169 | static ssize_t show_in##offset##_max(struct device *dev, struct device_attribute *attr, char *buf) \ | 169 | struct adm1025_data *data = adm1025_update_device(dev); |
| 170 | { \ | 170 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_min[index], |
| 171 | struct adm1025_data *data = adm1025_update_device(dev); \ | 171 | in_scale[index])); |
| 172 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_max[offset], \ | 172 | } |
| 173 | in_scale[offset])); \ | 173 | |
| 174 | } \ | 174 | static ssize_t |
| 175 | static DEVICE_ATTR(in##offset##_input, S_IRUGO, show_in##offset, NULL); | 175 | show_in_max(struct device *dev, struct device_attribute *attr, char *buf) |
| 176 | show_in(0); | 176 | { |
| 177 | show_in(1); | 177 | int index = to_sensor_dev_attr(attr)->index; |
| 178 | show_in(2); | 178 | struct adm1025_data *data = adm1025_update_device(dev); |
| 179 | show_in(3); | 179 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_max[index], |
| 180 | show_in(4); | 180 | in_scale[index])); |
| 181 | show_in(5); | 181 | } |
| 182 | 182 | ||
| 183 | #define show_temp(offset) \ | 183 | static ssize_t |
| 184 | static ssize_t show_temp##offset(struct device *dev, struct device_attribute *attr, char *buf) \ | 184 | show_temp(struct device *dev, struct device_attribute *attr, char *buf) |
| 185 | { \ | 185 | { |
| 186 | struct adm1025_data *data = adm1025_update_device(dev); \ | 186 | int index = to_sensor_dev_attr(attr)->index; |
| 187 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp[offset-1])); \ | 187 | struct adm1025_data *data = adm1025_update_device(dev); |
| 188 | } \ | 188 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp[index])); |
| 189 | static ssize_t show_temp##offset##_min(struct device *dev, struct device_attribute *attr, char *buf) \ | 189 | } |
| 190 | { \ | 190 | |
| 191 | struct adm1025_data *data = adm1025_update_device(dev); \ | 191 | static ssize_t |
| 192 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_min[offset-1])); \ | 192 | show_temp_min(struct device *dev, struct device_attribute *attr, char *buf) |
| 193 | } \ | 193 | { |
| 194 | static ssize_t show_temp##offset##_max(struct device *dev, struct device_attribute *attr, char *buf) \ | 194 | int index = to_sensor_dev_attr(attr)->index; |
| 195 | { \ | 195 | struct adm1025_data *data = adm1025_update_device(dev); |
| 196 | struct adm1025_data *data = adm1025_update_device(dev); \ | 196 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_min[index])); |
| 197 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[offset-1])); \ | 197 | } |
| 198 | }\ | 198 | |
| 199 | static DEVICE_ATTR(temp##offset##_input, S_IRUGO, show_temp##offset, NULL); | 199 | static ssize_t |
| 200 | show_temp(1); | 200 | show_temp_max(struct device *dev, struct device_attribute *attr, char *buf) |
| 201 | show_temp(2); | 201 | { |
| 202 | int index = to_sensor_dev_attr(attr)->index; | ||
| 203 | struct adm1025_data *data = adm1025_update_device(dev); | ||
| 204 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[index])); | ||
| 205 | } | ||
| 206 | |||
| 207 | static ssize_t set_in_min(struct device *dev, struct device_attribute *attr, | ||
| 208 | const char *buf, size_t count) | ||
| 209 | { | ||
| 210 | int index = to_sensor_dev_attr(attr)->index; | ||
| 211 | struct i2c_client *client = to_i2c_client(dev); | ||
| 212 | struct adm1025_data *data = i2c_get_clientdata(client); | ||
| 213 | long val = simple_strtol(buf, NULL, 10); | ||
| 214 | |||
| 215 | mutex_lock(&data->update_lock); | ||
| 216 | data->in_min[index] = IN_TO_REG(val, in_scale[index]); | ||
| 217 | i2c_smbus_write_byte_data(client, ADM1025_REG_IN_MIN(index), | ||
| 218 | data->in_min[index]); | ||
| 219 | mutex_unlock(&data->update_lock); | ||
| 220 | return count; | ||
| 221 | } | ||
| 222 | |||
| 223 | static ssize_t set_in_max(struct device *dev, struct device_attribute *attr, | ||
| 224 | const char *buf, size_t count) | ||
| 225 | { | ||
| 226 | int index = to_sensor_dev_attr(attr)->index; | ||
| 227 | struct i2c_client *client = to_i2c_client(dev); | ||
| 228 | struct adm1025_data *data = i2c_get_clientdata(client); | ||
| 229 | long val = simple_strtol(buf, NULL, 10); | ||
| 230 | |||
| 231 | mutex_lock(&data->update_lock); | ||
| 232 | data->in_max[index] = IN_TO_REG(val, in_scale[index]); | ||
| 233 | i2c_smbus_write_byte_data(client, ADM1025_REG_IN_MAX(index), | ||
| 234 | data->in_max[index]); | ||
| 235 | mutex_unlock(&data->update_lock); | ||
| 236 | return count; | ||
| 237 | } | ||
| 202 | 238 | ||
| 203 | #define set_in(offset) \ | 239 | #define set_in(offset) \ |
| 204 | static ssize_t set_in##offset##_min(struct device *dev, struct device_attribute *attr, const char *buf, \ | 240 | static SENSOR_DEVICE_ATTR(in##offset##_input, S_IRUGO, \ |
| 205 | size_t count) \ | 241 | show_in, NULL, offset); \ |
| 206 | { \ | 242 | static SENSOR_DEVICE_ATTR(in##offset##_min, S_IWUSR | S_IRUGO, \ |
| 207 | struct i2c_client *client = to_i2c_client(dev); \ | 243 | show_in_min, set_in_min, offset); \ |
| 208 | struct adm1025_data *data = i2c_get_clientdata(client); \ | 244 | static SENSOR_DEVICE_ATTR(in##offset##_max, S_IWUSR | S_IRUGO, \ |
| 209 | long val = simple_strtol(buf, NULL, 10); \ | 245 | show_in_max, set_in_max, offset) |
| 210 | \ | ||
| 211 | mutex_lock(&data->update_lock); \ | ||
| 212 | data->in_min[offset] = IN_TO_REG(val, in_scale[offset]); \ | ||
| 213 | i2c_smbus_write_byte_data(client, ADM1025_REG_IN_MIN(offset), \ | ||
| 214 | data->in_min[offset]); \ | ||
| 215 | mutex_unlock(&data->update_lock); \ | ||
| 216 | return count; \ | ||
| 217 | } \ | ||
| 218 | static ssize_t set_in##offset##_max(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
| 219 | size_t count) \ | ||
| 220 | { \ | ||
| 221 | struct i2c_client *client = to_i2c_client(dev); \ | ||
| 222 | struct adm1025_data *data = i2c_get_clientdata(client); \ | ||
| 223 | long val = simple_strtol(buf, NULL, 10); \ | ||
| 224 | \ | ||
| 225 | mutex_lock(&data->update_lock); \ | ||
| 226 | data->in_max[offset] = IN_TO_REG(val, in_scale[offset]); \ | ||
| 227 | i2c_smbus_write_byte_data(client, ADM1025_REG_IN_MAX(offset), \ | ||
| 228 | data->in_max[offset]); \ | ||
| 229 | mutex_unlock(&data->update_lock); \ | ||
| 230 | return count; \ | ||
| 231 | } \ | ||
| 232 | static DEVICE_ATTR(in##offset##_min, S_IWUSR | S_IRUGO, \ | ||
| 233 | show_in##offset##_min, set_in##offset##_min); \ | ||
| 234 | static DEVICE_ATTR(in##offset##_max, S_IWUSR | S_IRUGO, \ | ||
| 235 | show_in##offset##_max, set_in##offset##_max); | ||
| 236 | set_in(0); | 246 | set_in(0); |
| 237 | set_in(1); | 247 | set_in(1); |
| 238 | set_in(2); | 248 | set_in(2); |
| @@ -240,65 +250,91 @@ set_in(3); | |||
| 240 | set_in(4); | 250 | set_in(4); |
| 241 | set_in(5); | 251 | set_in(5); |
| 242 | 252 | ||
| 253 | static ssize_t set_temp_min(struct device *dev, struct device_attribute *attr, | ||
| 254 | const char *buf, size_t count) | ||
| 255 | { | ||
| 256 | int index = to_sensor_dev_attr(attr)->index; | ||
| 257 | struct i2c_client *client = to_i2c_client(dev); | ||
| 258 | struct adm1025_data *data = i2c_get_clientdata(client); | ||
| 259 | long val = simple_strtol(buf, NULL, 10); | ||
| 260 | |||
| 261 | mutex_lock(&data->update_lock); | ||
| 262 | data->temp_min[index] = TEMP_TO_REG(val); | ||
| 263 | i2c_smbus_write_byte_data(client, ADM1025_REG_TEMP_LOW(index), | ||
| 264 | data->temp_min[index]); | ||
| 265 | mutex_unlock(&data->update_lock); | ||
| 266 | return count; | ||
| 267 | } | ||
| 268 | |||
| 269 | static ssize_t set_temp_max(struct device *dev, struct device_attribute *attr, | ||
| 270 | const char *buf, size_t count) | ||
| 271 | { | ||
| 272 | int index = to_sensor_dev_attr(attr)->index; | ||
| 273 | struct i2c_client *client = to_i2c_client(dev); | ||
| 274 | struct adm1025_data *data = i2c_get_clientdata(client); | ||
| 275 | long val = simple_strtol(buf, NULL, 10); | ||
| 276 | |||
| 277 | mutex_lock(&data->update_lock); | ||
| 278 | data->temp_max[index] = TEMP_TO_REG(val); | ||
| 279 | i2c_smbus_write_byte_data(client, ADM1025_REG_TEMP_HIGH(index), | ||
| 280 | data->temp_max[index]); | ||
| 281 | mutex_unlock(&data->update_lock); | ||
| 282 | return count; | ||
| 283 | } | ||
| 284 | |||
| 243 | #define set_temp(offset) \ | 285 | #define set_temp(offset) \ |
| 244 | static ssize_t set_temp##offset##_min(struct device *dev, struct device_attribute *attr, const char *buf, \ | 286 | static SENSOR_DEVICE_ATTR(temp##offset##_input, S_IRUGO, \ |
| 245 | size_t count) \ | 287 | show_temp, NULL, offset - 1); \ |
| 246 | { \ | 288 | static SENSOR_DEVICE_ATTR(temp##offset##_min, S_IWUSR | S_IRUGO, \ |
| 247 | struct i2c_client *client = to_i2c_client(dev); \ | 289 | show_temp_min, set_temp_min, offset - 1); \ |
| 248 | struct adm1025_data *data = i2c_get_clientdata(client); \ | 290 | static SENSOR_DEVICE_ATTR(temp##offset##_max, S_IWUSR | S_IRUGO, \ |
| 249 | long val = simple_strtol(buf, NULL, 10); \ | 291 | show_temp_max, set_temp_max, offset - 1) |
| 250 | \ | ||
| 251 | mutex_lock(&data->update_lock); \ | ||
| 252 | data->temp_min[offset-1] = TEMP_TO_REG(val); \ | ||
| 253 | i2c_smbus_write_byte_data(client, ADM1025_REG_TEMP_LOW(offset-1), \ | ||
| 254 | data->temp_min[offset-1]); \ | ||
| 255 | mutex_unlock(&data->update_lock); \ | ||
| 256 | return count; \ | ||
| 257 | } \ | ||
| 258 | static ssize_t set_temp##offset##_max(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
| 259 | size_t count) \ | ||
| 260 | { \ | ||
| 261 | struct i2c_client *client = to_i2c_client(dev); \ | ||
| 262 | struct adm1025_data *data = i2c_get_clientdata(client); \ | ||
| 263 | long val = simple_strtol(buf, NULL, 10); \ | ||
| 264 | \ | ||
| 265 | mutex_lock(&data->update_lock); \ | ||
| 266 | data->temp_max[offset-1] = TEMP_TO_REG(val); \ | ||
| 267 | i2c_smbus_write_byte_data(client, ADM1025_REG_TEMP_HIGH(offset-1), \ | ||
| 268 | data->temp_max[offset-1]); \ | ||
| 269 | mutex_unlock(&data->update_lock); \ | ||
| 270 | return count; \ | ||
| 271 | } \ | ||
| 272 | static DEVICE_ATTR(temp##offset##_min, S_IWUSR | S_IRUGO, \ | ||
| 273 | show_temp##offset##_min, set_temp##offset##_min); \ | ||
| 274 | static DEVICE_ATTR(temp##offset##_max, S_IWUSR | S_IRUGO, \ | ||
| 275 | show_temp##offset##_max, set_temp##offset##_max); | ||
| 276 | set_temp(1); | 292 | set_temp(1); |
| 277 | set_temp(2); | 293 | set_temp(2); |
| 278 | 294 | ||
| 279 | static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, char *buf) | 295 | static ssize_t |
| 296 | show_alarms(struct device *dev, struct device_attribute *attr, char *buf) | ||
| 280 | { | 297 | { |
| 281 | struct adm1025_data *data = adm1025_update_device(dev); | 298 | struct adm1025_data *data = adm1025_update_device(dev); |
| 282 | return sprintf(buf, "%u\n", data->alarms); | 299 | return sprintf(buf, "%u\n", data->alarms); |
| 283 | } | 300 | } |
| 284 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | 301 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); |
| 285 | 302 | ||
| 286 | static ssize_t show_vid(struct device *dev, struct device_attribute *attr, char *buf) | 303 | static ssize_t |
| 304 | show_alarm(struct device *dev, struct device_attribute *attr, char *buf) | ||
| 305 | { | ||
| 306 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 307 | struct adm1025_data *data = adm1025_update_device(dev); | ||
| 308 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); | ||
| 309 | } | ||
| 310 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 311 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 312 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 313 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 314 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 315 | static SENSOR_DEVICE_ATTR(in5_alarm, S_IRUGO, show_alarm, NULL, 9); | ||
| 316 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, 5); | ||
| 317 | static SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 318 | static SENSOR_DEVICE_ATTR(temp1_fault, S_IRUGO, show_alarm, NULL, 14); | ||
| 319 | |||
| 320 | static ssize_t | ||
| 321 | show_vid(struct device *dev, struct device_attribute *attr, char *buf) | ||
| 287 | { | 322 | { |
| 288 | struct adm1025_data *data = adm1025_update_device(dev); | 323 | struct adm1025_data *data = adm1025_update_device(dev); |
| 289 | return sprintf(buf, "%u\n", vid_from_reg(data->vid, data->vrm)); | 324 | return sprintf(buf, "%u\n", vid_from_reg(data->vid, data->vrm)); |
| 290 | } | 325 | } |
| 291 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid, NULL); | 326 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid, NULL); |
| 292 | 327 | ||
| 293 | static ssize_t show_vrm(struct device *dev, struct device_attribute *attr, char *buf) | 328 | static ssize_t |
| 329 | show_vrm(struct device *dev, struct device_attribute *attr, char *buf) | ||
| 294 | { | 330 | { |
| 295 | struct adm1025_data *data = dev_get_drvdata(dev); | 331 | struct adm1025_data *data = dev_get_drvdata(dev); |
| 296 | return sprintf(buf, "%u\n", data->vrm); | 332 | return sprintf(buf, "%u\n", data->vrm); |
| 297 | } | 333 | } |
| 298 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 334 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, |
| 335 | const char *buf, size_t count) | ||
| 299 | { | 336 | { |
| 300 | struct i2c_client *client = to_i2c_client(dev); | 337 | struct adm1025_data *data = dev_get_drvdata(dev); |
| 301 | struct adm1025_data *data = i2c_get_clientdata(client); | ||
| 302 | data->vrm = simple_strtoul(buf, NULL, 10); | 338 | data->vrm = simple_strtoul(buf, NULL, 10); |
| 303 | return count; | 339 | return count; |
| 304 | } | 340 | } |
| @@ -316,27 +352,35 @@ static int adm1025_attach_adapter(struct i2c_adapter *adapter) | |||
| 316 | } | 352 | } |
| 317 | 353 | ||
| 318 | static struct attribute *adm1025_attributes[] = { | 354 | static struct attribute *adm1025_attributes[] = { |
| 319 | &dev_attr_in0_input.attr, | 355 | &sensor_dev_attr_in0_input.dev_attr.attr, |
| 320 | &dev_attr_in1_input.attr, | 356 | &sensor_dev_attr_in1_input.dev_attr.attr, |
| 321 | &dev_attr_in2_input.attr, | 357 | &sensor_dev_attr_in2_input.dev_attr.attr, |
| 322 | &dev_attr_in3_input.attr, | 358 | &sensor_dev_attr_in3_input.dev_attr.attr, |
| 323 | &dev_attr_in5_input.attr, | 359 | &sensor_dev_attr_in5_input.dev_attr.attr, |
| 324 | &dev_attr_in0_min.attr, | 360 | &sensor_dev_attr_in0_min.dev_attr.attr, |
| 325 | &dev_attr_in1_min.attr, | 361 | &sensor_dev_attr_in1_min.dev_attr.attr, |
| 326 | &dev_attr_in2_min.attr, | 362 | &sensor_dev_attr_in2_min.dev_attr.attr, |
| 327 | &dev_attr_in3_min.attr, | 363 | &sensor_dev_attr_in3_min.dev_attr.attr, |
| 328 | &dev_attr_in5_min.attr, | 364 | &sensor_dev_attr_in5_min.dev_attr.attr, |
| 329 | &dev_attr_in0_max.attr, | 365 | &sensor_dev_attr_in0_max.dev_attr.attr, |
| 330 | &dev_attr_in1_max.attr, | 366 | &sensor_dev_attr_in1_max.dev_attr.attr, |
| 331 | &dev_attr_in2_max.attr, | 367 | &sensor_dev_attr_in2_max.dev_attr.attr, |
| 332 | &dev_attr_in3_max.attr, | 368 | &sensor_dev_attr_in3_max.dev_attr.attr, |
| 333 | &dev_attr_in5_max.attr, | 369 | &sensor_dev_attr_in5_max.dev_attr.attr, |
| 334 | &dev_attr_temp1_input.attr, | 370 | &sensor_dev_attr_in0_alarm.dev_attr.attr, |
| 335 | &dev_attr_temp2_input.attr, | 371 | &sensor_dev_attr_in1_alarm.dev_attr.attr, |
| 336 | &dev_attr_temp1_min.attr, | 372 | &sensor_dev_attr_in2_alarm.dev_attr.attr, |
| 337 | &dev_attr_temp2_min.attr, | 373 | &sensor_dev_attr_in3_alarm.dev_attr.attr, |
| 338 | &dev_attr_temp1_max.attr, | 374 | &sensor_dev_attr_in5_alarm.dev_attr.attr, |
| 339 | &dev_attr_temp2_max.attr, | 375 | &sensor_dev_attr_temp1_input.dev_attr.attr, |
| 376 | &sensor_dev_attr_temp2_input.dev_attr.attr, | ||
| 377 | &sensor_dev_attr_temp1_min.dev_attr.attr, | ||
| 378 | &sensor_dev_attr_temp2_min.dev_attr.attr, | ||
| 379 | &sensor_dev_attr_temp1_max.dev_attr.attr, | ||
| 380 | &sensor_dev_attr_temp2_max.dev_attr.attr, | ||
| 381 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 382 | &sensor_dev_attr_temp2_alarm.dev_attr.attr, | ||
| 383 | &sensor_dev_attr_temp1_fault.dev_attr.attr, | ||
| 340 | &dev_attr_alarms.attr, | 384 | &dev_attr_alarms.attr, |
| 341 | &dev_attr_cpu0_vid.attr, | 385 | &dev_attr_cpu0_vid.attr, |
| 342 | &dev_attr_vrm.attr, | 386 | &dev_attr_vrm.attr, |
| @@ -347,15 +391,16 @@ static const struct attribute_group adm1025_group = { | |||
| 347 | .attrs = adm1025_attributes, | 391 | .attrs = adm1025_attributes, |
| 348 | }; | 392 | }; |
| 349 | 393 | ||
| 350 | static struct attribute *adm1025_attributes_opt[] = { | 394 | static struct attribute *adm1025_attributes_in4[] = { |
| 351 | &dev_attr_in4_input.attr, | 395 | &sensor_dev_attr_in4_input.dev_attr.attr, |
| 352 | &dev_attr_in4_min.attr, | 396 | &sensor_dev_attr_in4_min.dev_attr.attr, |
| 353 | &dev_attr_in4_max.attr, | 397 | &sensor_dev_attr_in4_max.dev_attr.attr, |
| 398 | &sensor_dev_attr_in4_alarm.dev_attr.attr, | ||
| 354 | NULL | 399 | NULL |
| 355 | }; | 400 | }; |
| 356 | 401 | ||
| 357 | static const struct attribute_group adm1025_group_opt = { | 402 | static const struct attribute_group adm1025_group_in4 = { |
| 358 | .attrs = adm1025_attributes_opt, | 403 | .attrs = adm1025_attributes_in4, |
| 359 | }; | 404 | }; |
| 360 | 405 | ||
| 361 | /* | 406 | /* |
| @@ -364,7 +409,7 @@ static const struct attribute_group adm1025_group_opt = { | |||
| 364 | */ | 409 | */ |
| 365 | static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | 410 | static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) |
| 366 | { | 411 | { |
| 367 | struct i2c_client *new_client; | 412 | struct i2c_client *client; |
| 368 | struct adm1025_data *data; | 413 | struct adm1025_data *data; |
| 369 | int err = 0; | 414 | int err = 0; |
| 370 | const char *name = ""; | 415 | const char *name = ""; |
| @@ -378,14 +423,11 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 378 | goto exit; | 423 | goto exit; |
| 379 | } | 424 | } |
| 380 | 425 | ||
| 381 | /* The common I2C client data is placed right before the | 426 | client = &data->client; |
| 382 | ADM1025-specific data. */ | 427 | i2c_set_clientdata(client, data); |
| 383 | new_client = &data->client; | 428 | client->addr = address; |
| 384 | i2c_set_clientdata(new_client, data); | 429 | client->adapter = adapter; |
| 385 | new_client->addr = address; | 430 | client->driver = &adm1025_driver; |
| 386 | new_client->adapter = adapter; | ||
| 387 | new_client->driver = &adm1025_driver; | ||
| 388 | new_client->flags = 0; | ||
| 389 | 431 | ||
| 390 | /* | 432 | /* |
| 391 | * Now we do the remaining detection. A negative kind means that | 433 | * Now we do the remaining detection. A negative kind means that |
| @@ -397,12 +439,12 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 397 | * requested, so both the detection and the identification steps | 439 | * requested, so both the detection and the identification steps |
| 398 | * are skipped. | 440 | * are skipped. |
| 399 | */ | 441 | */ |
| 400 | config = i2c_smbus_read_byte_data(new_client, ADM1025_REG_CONFIG); | 442 | config = i2c_smbus_read_byte_data(client, ADM1025_REG_CONFIG); |
| 401 | if (kind < 0) { /* detection */ | 443 | if (kind < 0) { /* detection */ |
| 402 | if ((config & 0x80) != 0x00 | 444 | if ((config & 0x80) != 0x00 |
| 403 | || (i2c_smbus_read_byte_data(new_client, | 445 | || (i2c_smbus_read_byte_data(client, |
| 404 | ADM1025_REG_STATUS1) & 0xC0) != 0x00 | 446 | ADM1025_REG_STATUS1) & 0xC0) != 0x00 |
| 405 | || (i2c_smbus_read_byte_data(new_client, | 447 | || (i2c_smbus_read_byte_data(client, |
| 406 | ADM1025_REG_STATUS2) & 0xBC) != 0x00) { | 448 | ADM1025_REG_STATUS2) & 0xBC) != 0x00) { |
| 407 | dev_dbg(&adapter->dev, | 449 | dev_dbg(&adapter->dev, |
| 408 | "ADM1025 detection failed at 0x%02x.\n", | 450 | "ADM1025 detection failed at 0x%02x.\n", |
| @@ -414,11 +456,9 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 414 | if (kind <= 0) { /* identification */ | 456 | if (kind <= 0) { /* identification */ |
| 415 | u8 man_id, chip_id; | 457 | u8 man_id, chip_id; |
| 416 | 458 | ||
| 417 | man_id = i2c_smbus_read_byte_data(new_client, | 459 | man_id = i2c_smbus_read_byte_data(client, ADM1025_REG_MAN_ID); |
| 418 | ADM1025_REG_MAN_ID); | 460 | chip_id = i2c_smbus_read_byte_data(client, ADM1025_REG_CHIP_ID); |
| 419 | chip_id = i2c_smbus_read_byte_data(new_client, | 461 | |
| 420 | ADM1025_REG_CHIP_ID); | ||
| 421 | |||
| 422 | if (man_id == 0x41) { /* Analog Devices */ | 462 | if (man_id == 0x41) { /* Analog Devices */ |
| 423 | if ((chip_id & 0xF0) == 0x20) { /* ADM1025/ADM1025A */ | 463 | if ((chip_id & 0xF0) == 0x20) { /* ADM1025/ADM1025A */ |
| 424 | kind = adm1025; | 464 | kind = adm1025; |
| @@ -446,33 +486,28 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 446 | } | 486 | } |
| 447 | 487 | ||
| 448 | /* We can fill in the remaining client fields */ | 488 | /* We can fill in the remaining client fields */ |
| 449 | strlcpy(new_client->name, name, I2C_NAME_SIZE); | 489 | strlcpy(client->name, name, I2C_NAME_SIZE); |
| 450 | data->valid = 0; | ||
| 451 | mutex_init(&data->update_lock); | 490 | mutex_init(&data->update_lock); |
| 452 | 491 | ||
| 453 | /* Tell the I2C layer a new client has arrived */ | 492 | /* Tell the I2C layer a new client has arrived */ |
| 454 | if ((err = i2c_attach_client(new_client))) | 493 | if ((err = i2c_attach_client(client))) |
| 455 | goto exit_free; | 494 | goto exit_free; |
| 456 | 495 | ||
| 457 | /* Initialize the ADM1025 chip */ | 496 | /* Initialize the ADM1025 chip */ |
| 458 | adm1025_init_client(new_client); | 497 | adm1025_init_client(client); |
| 459 | 498 | ||
| 460 | /* Register sysfs hooks */ | 499 | /* Register sysfs hooks */ |
| 461 | if ((err = sysfs_create_group(&new_client->dev.kobj, &adm1025_group))) | 500 | if ((err = sysfs_create_group(&client->dev.kobj, &adm1025_group))) |
| 462 | goto exit_detach; | 501 | goto exit_detach; |
| 463 | 502 | ||
| 464 | /* Pin 11 is either in4 (+12V) or VID4 */ | 503 | /* Pin 11 is either in4 (+12V) or VID4 */ |
| 465 | if (!(config & 0x20)) { | 504 | if (!(config & 0x20)) { |
| 466 | if ((err = device_create_file(&new_client->dev, | 505 | if ((err = sysfs_create_group(&client->dev.kobj, |
| 467 | &dev_attr_in4_input)) | 506 | &adm1025_group_in4))) |
| 468 | || (err = device_create_file(&new_client->dev, | ||
| 469 | &dev_attr_in4_min)) | ||
| 470 | || (err = device_create_file(&new_client->dev, | ||
| 471 | &dev_attr_in4_max))) | ||
| 472 | goto exit_remove; | 507 | goto exit_remove; |
| 473 | } | 508 | } |
| 474 | 509 | ||
| 475 | data->hwmon_dev = hwmon_device_register(&new_client->dev); | 510 | data->hwmon_dev = hwmon_device_register(&client->dev); |
| 476 | if (IS_ERR(data->hwmon_dev)) { | 511 | if (IS_ERR(data->hwmon_dev)) { |
| 477 | err = PTR_ERR(data->hwmon_dev); | 512 | err = PTR_ERR(data->hwmon_dev); |
| 478 | goto exit_remove; | 513 | goto exit_remove; |
| @@ -481,10 +516,10 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 481 | return 0; | 516 | return 0; |
| 482 | 517 | ||
| 483 | exit_remove: | 518 | exit_remove: |
| 484 | sysfs_remove_group(&new_client->dev.kobj, &adm1025_group); | 519 | sysfs_remove_group(&client->dev.kobj, &adm1025_group); |
| 485 | sysfs_remove_group(&new_client->dev.kobj, &adm1025_group_opt); | 520 | sysfs_remove_group(&client->dev.kobj, &adm1025_group_in4); |
| 486 | exit_detach: | 521 | exit_detach: |
| 487 | i2c_detach_client(new_client); | 522 | i2c_detach_client(client); |
| 488 | exit_free: | 523 | exit_free: |
| 489 | kfree(data); | 524 | kfree(data); |
| 490 | exit: | 525 | exit: |
| @@ -540,7 +575,7 @@ static int adm1025_detach_client(struct i2c_client *client) | |||
| 540 | 575 | ||
| 541 | hwmon_device_unregister(data->hwmon_dev); | 576 | hwmon_device_unregister(data->hwmon_dev); |
| 542 | sysfs_remove_group(&client->dev.kobj, &adm1025_group); | 577 | sysfs_remove_group(&client->dev.kobj, &adm1025_group); |
| 543 | sysfs_remove_group(&client->dev.kobj, &adm1025_group_opt); | 578 | sysfs_remove_group(&client->dev.kobj, &adm1025_group_in4); |
| 544 | 579 | ||
| 545 | if ((err = i2c_detach_client(client))) | 580 | if ((err = i2c_detach_client(client))) |
| 546 | return err; | 581 | return err; |
diff --git a/drivers/hwmon/adm1026.c b/drivers/hwmon/adm1026.c index 3e63c1486770..8002f68240c4 100644 --- a/drivers/hwmon/adm1026.c +++ b/drivers/hwmon/adm1026.c | |||
| @@ -40,8 +40,8 @@ static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; | |||
| 40 | /* Insmod parameters */ | 40 | /* Insmod parameters */ |
| 41 | I2C_CLIENT_INSMOD_1(adm1026); | 41 | I2C_CLIENT_INSMOD_1(adm1026); |
| 42 | 42 | ||
| 43 | static int gpio_input[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, | 43 | static int gpio_input[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, |
| 44 | -1, -1, -1, -1, -1, -1, -1, -1 }; | 44 | -1, -1, -1, -1, -1, -1, -1, -1 }; |
| 45 | static int gpio_output[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, | 45 | static int gpio_output[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, |
| 46 | -1, -1, -1, -1, -1, -1, -1, -1 }; | 46 | -1, -1, -1, -1, -1, -1, -1, -1 }; |
| 47 | static int gpio_inverted[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, | 47 | static int gpio_inverted[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, |
| @@ -49,46 +49,49 @@ static int gpio_inverted[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, | |||
| 49 | static int gpio_normal[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, | 49 | static int gpio_normal[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, |
| 50 | -1, -1, -1, -1, -1, -1, -1, -1 }; | 50 | -1, -1, -1, -1, -1, -1, -1, -1 }; |
| 51 | static int gpio_fan[8] = { -1, -1, -1, -1, -1, -1, -1, -1 }; | 51 | static int gpio_fan[8] = { -1, -1, -1, -1, -1, -1, -1, -1 }; |
| 52 | module_param_array(gpio_input,int,NULL,0); | 52 | module_param_array(gpio_input, int, NULL, 0); |
| 53 | MODULE_PARM_DESC(gpio_input,"List of GPIO pins (0-16) to program as inputs"); | 53 | MODULE_PARM_DESC(gpio_input, "List of GPIO pins (0-16) to program as inputs"); |
| 54 | module_param_array(gpio_output,int,NULL,0); | 54 | module_param_array(gpio_output, int, NULL, 0); |
| 55 | MODULE_PARM_DESC(gpio_output,"List of GPIO pins (0-16) to program as " | 55 | MODULE_PARM_DESC(gpio_output, "List of GPIO pins (0-16) to program as " |
| 56 | "outputs"); | 56 | "outputs"); |
| 57 | module_param_array(gpio_inverted,int,NULL,0); | 57 | module_param_array(gpio_inverted, int, NULL, 0); |
| 58 | MODULE_PARM_DESC(gpio_inverted,"List of GPIO pins (0-16) to program as " | 58 | MODULE_PARM_DESC(gpio_inverted, "List of GPIO pins (0-16) to program as " |
| 59 | "inverted"); | 59 | "inverted"); |
| 60 | module_param_array(gpio_normal,int,NULL,0); | 60 | module_param_array(gpio_normal, int, NULL, 0); |
| 61 | MODULE_PARM_DESC(gpio_normal,"List of GPIO pins (0-16) to program as " | 61 | MODULE_PARM_DESC(gpio_normal, "List of GPIO pins (0-16) to program as " |
| 62 | "normal/non-inverted"); | 62 | "normal/non-inverted"); |
| 63 | module_param_array(gpio_fan,int,NULL,0); | 63 | module_param_array(gpio_fan, int, NULL, 0); |
| 64 | MODULE_PARM_DESC(gpio_fan,"List of GPIO pins (0-7) to program as fan tachs"); | 64 | MODULE_PARM_DESC(gpio_fan, "List of GPIO pins (0-7) to program as fan tachs"); |
| 65 | 65 | ||
| 66 | /* Many ADM1026 constants specified below */ | 66 | /* Many ADM1026 constants specified below */ |
| 67 | 67 | ||
| 68 | /* The ADM1026 registers */ | 68 | /* The ADM1026 registers */ |
| 69 | #define ADM1026_REG_CONFIG1 0x00 | 69 | #define ADM1026_REG_CONFIG1 0x00 |
| 70 | #define CFG1_MONITOR 0x01 | 70 | #define CFG1_MONITOR 0x01 |
| 71 | #define CFG1_INT_ENABLE 0x02 | 71 | #define CFG1_INT_ENABLE 0x02 |
| 72 | #define CFG1_INT_CLEAR 0x04 | 72 | #define CFG1_INT_CLEAR 0x04 |
| 73 | #define CFG1_AIN8_9 0x08 | 73 | #define CFG1_AIN8_9 0x08 |
| 74 | #define CFG1_THERM_HOT 0x10 | 74 | #define CFG1_THERM_HOT 0x10 |
| 75 | #define CFG1_DAC_AFC 0x20 | 75 | #define CFG1_DAC_AFC 0x20 |
| 76 | #define CFG1_PWM_AFC 0x40 | 76 | #define CFG1_PWM_AFC 0x40 |
| 77 | #define CFG1_RESET 0x80 | 77 | #define CFG1_RESET 0x80 |
| 78 | #define ADM1026_REG_CONFIG2 0x01 | 78 | |
| 79 | #define ADM1026_REG_CONFIG2 0x01 | ||
| 79 | /* CONFIG2 controls FAN0/GPIO0 through FAN7/GPIO7 */ | 80 | /* CONFIG2 controls FAN0/GPIO0 through FAN7/GPIO7 */ |
| 80 | #define ADM1026_REG_CONFIG3 0x07 | 81 | |
| 81 | #define CFG3_GPIO16_ENABLE 0x01 | 82 | #define ADM1026_REG_CONFIG3 0x07 |
| 82 | #define CFG3_CI_CLEAR 0x02 | 83 | #define CFG3_GPIO16_ENABLE 0x01 |
| 83 | #define CFG3_VREF_250 0x04 | 84 | #define CFG3_CI_CLEAR 0x02 |
| 84 | #define CFG3_GPIO16_DIR 0x40 | 85 | #define CFG3_VREF_250 0x04 |
| 85 | #define CFG3_GPIO16_POL 0x80 | 86 | #define CFG3_GPIO16_DIR 0x40 |
| 86 | #define ADM1026_REG_E2CONFIG 0x13 | 87 | #define CFG3_GPIO16_POL 0x80 |
| 87 | #define E2CFG_READ 0x01 | 88 | |
| 88 | #define E2CFG_WRITE 0x02 | 89 | #define ADM1026_REG_E2CONFIG 0x13 |
| 89 | #define E2CFG_ERASE 0x04 | 90 | #define E2CFG_READ 0x01 |
| 90 | #define E2CFG_ROM 0x08 | 91 | #define E2CFG_WRITE 0x02 |
| 91 | #define E2CFG_CLK_EXT 0x80 | 92 | #define E2CFG_ERASE 0x04 |
| 93 | #define E2CFG_ROM 0x08 | ||
| 94 | #define E2CFG_CLK_EXT 0x80 | ||
| 92 | 95 | ||
| 93 | /* There are 10 general analog inputs and 7 dedicated inputs | 96 | /* There are 10 general analog inputs and 7 dedicated inputs |
| 94 | * They are: | 97 | * They are: |
| @@ -129,48 +132,48 @@ static u16 ADM1026_REG_TEMP_TMIN[] = { 0x10, 0x11, 0x12 }; | |||
| 129 | static u16 ADM1026_REG_TEMP_THERM[] = { 0x0d, 0x0e, 0x0f }; | 132 | static u16 ADM1026_REG_TEMP_THERM[] = { 0x0d, 0x0e, 0x0f }; |
| 130 | static u16 ADM1026_REG_TEMP_OFFSET[] = { 0x1e, 0x6e, 0x6f }; | 133 | static u16 ADM1026_REG_TEMP_OFFSET[] = { 0x1e, 0x6e, 0x6f }; |
| 131 | 134 | ||
| 132 | #define ADM1026_REG_FAN(nr) (0x38 + (nr)) | 135 | #define ADM1026_REG_FAN(nr) (0x38 + (nr)) |
| 133 | #define ADM1026_REG_FAN_MIN(nr) (0x60 + (nr)) | 136 | #define ADM1026_REG_FAN_MIN(nr) (0x60 + (nr)) |
| 134 | #define ADM1026_REG_FAN_DIV_0_3 0x02 | 137 | #define ADM1026_REG_FAN_DIV_0_3 0x02 |
| 135 | #define ADM1026_REG_FAN_DIV_4_7 0x03 | 138 | #define ADM1026_REG_FAN_DIV_4_7 0x03 |
| 136 | 139 | ||
| 137 | #define ADM1026_REG_DAC 0x04 | 140 | #define ADM1026_REG_DAC 0x04 |
| 138 | #define ADM1026_REG_PWM 0x05 | 141 | #define ADM1026_REG_PWM 0x05 |
| 139 | 142 | ||
| 140 | #define ADM1026_REG_GPIO_CFG_0_3 0x08 | 143 | #define ADM1026_REG_GPIO_CFG_0_3 0x08 |
| 141 | #define ADM1026_REG_GPIO_CFG_4_7 0x09 | 144 | #define ADM1026_REG_GPIO_CFG_4_7 0x09 |
| 142 | #define ADM1026_REG_GPIO_CFG_8_11 0x0a | 145 | #define ADM1026_REG_GPIO_CFG_8_11 0x0a |
| 143 | #define ADM1026_REG_GPIO_CFG_12_15 0x0b | 146 | #define ADM1026_REG_GPIO_CFG_12_15 0x0b |
| 144 | /* CFG_16 in REG_CFG3 */ | 147 | /* CFG_16 in REG_CFG3 */ |
| 145 | #define ADM1026_REG_GPIO_STATUS_0_7 0x24 | 148 | #define ADM1026_REG_GPIO_STATUS_0_7 0x24 |
| 146 | #define ADM1026_REG_GPIO_STATUS_8_15 0x25 | 149 | #define ADM1026_REG_GPIO_STATUS_8_15 0x25 |
| 147 | /* STATUS_16 in REG_STATUS4 */ | 150 | /* STATUS_16 in REG_STATUS4 */ |
| 148 | #define ADM1026_REG_GPIO_MASK_0_7 0x1c | 151 | #define ADM1026_REG_GPIO_MASK_0_7 0x1c |
| 149 | #define ADM1026_REG_GPIO_MASK_8_15 0x1d | 152 | #define ADM1026_REG_GPIO_MASK_8_15 0x1d |
| 150 | /* MASK_16 in REG_MASK4 */ | 153 | /* MASK_16 in REG_MASK4 */ |
| 151 | 154 | ||
| 152 | #define ADM1026_REG_COMPANY 0x16 | 155 | #define ADM1026_REG_COMPANY 0x16 |
| 153 | #define ADM1026_REG_VERSTEP 0x17 | 156 | #define ADM1026_REG_VERSTEP 0x17 |
| 154 | /* These are the recognized values for the above regs */ | 157 | /* These are the recognized values for the above regs */ |
| 155 | #define ADM1026_COMPANY_ANALOG_DEV 0x41 | 158 | #define ADM1026_COMPANY_ANALOG_DEV 0x41 |
| 156 | #define ADM1026_VERSTEP_GENERIC 0x40 | 159 | #define ADM1026_VERSTEP_GENERIC 0x40 |
| 157 | #define ADM1026_VERSTEP_ADM1026 0x44 | 160 | #define ADM1026_VERSTEP_ADM1026 0x44 |
| 158 | 161 | ||
| 159 | #define ADM1026_REG_MASK1 0x18 | 162 | #define ADM1026_REG_MASK1 0x18 |
| 160 | #define ADM1026_REG_MASK2 0x19 | 163 | #define ADM1026_REG_MASK2 0x19 |
| 161 | #define ADM1026_REG_MASK3 0x1a | 164 | #define ADM1026_REG_MASK3 0x1a |
| 162 | #define ADM1026_REG_MASK4 0x1b | 165 | #define ADM1026_REG_MASK4 0x1b |
| 163 | 166 | ||
| 164 | #define ADM1026_REG_STATUS1 0x20 | 167 | #define ADM1026_REG_STATUS1 0x20 |
| 165 | #define ADM1026_REG_STATUS2 0x21 | 168 | #define ADM1026_REG_STATUS2 0x21 |
| 166 | #define ADM1026_REG_STATUS3 0x22 | 169 | #define ADM1026_REG_STATUS3 0x22 |
| 167 | #define ADM1026_REG_STATUS4 0x23 | 170 | #define ADM1026_REG_STATUS4 0x23 |
| 168 | 171 | ||
| 169 | #define ADM1026_FAN_ACTIVATION_TEMP_HYST -6 | 172 | #define ADM1026_FAN_ACTIVATION_TEMP_HYST -6 |
| 170 | #define ADM1026_FAN_CONTROL_TEMP_RANGE 20 | 173 | #define ADM1026_FAN_CONTROL_TEMP_RANGE 20 |
| 171 | #define ADM1026_PWM_MAX 255 | 174 | #define ADM1026_PWM_MAX 255 |
| 172 | 175 | ||
| 173 | /* Conversions. Rounding and limit checking is only done on the TO_REG | 176 | /* Conversions. Rounding and limit checking is only done on the TO_REG |
| 174 | * variants. Note that you should be a bit careful with which arguments | 177 | * variants. Note that you should be a bit careful with which arguments |
| 175 | * these macros are called: arguments may be evaluated more than once. | 178 | * these macros are called: arguments may be evaluated more than once. |
| 176 | */ | 179 | */ |
| @@ -186,52 +189,49 @@ static u16 ADM1026_REG_TEMP_OFFSET[] = { 0x1e, 0x6e, 0x6f }; | |||
| 186 | * The values in this table are based on Table II, page 15 of the | 189 | * The values in this table are based on Table II, page 15 of the |
| 187 | * datasheet. | 190 | * datasheet. |
| 188 | */ | 191 | */ |
| 189 | static int adm1026_scaling[] = { /* .001 Volts */ | 192 | static int adm1026_scaling[] = { /* .001 Volts */ |
| 190 | 2250, 2250, 2250, 2250, 2250, 2250, | 193 | 2250, 2250, 2250, 2250, 2250, 2250, |
| 191 | 1875, 1875, 1875, 1875, 3000, 3330, | 194 | 1875, 1875, 1875, 1875, 3000, 3330, |
| 192 | 3330, 4995, 2250, 12000, 13875 | 195 | 3330, 4995, 2250, 12000, 13875 |
| 193 | }; | 196 | }; |
| 194 | #define NEG12_OFFSET 16000 | 197 | #define NEG12_OFFSET 16000 |
| 195 | #define SCALE(val,from,to) (((val)*(to) + ((from)/2))/(from)) | 198 | #define SCALE(val, from, to) (((val)*(to) + ((from)/2))/(from)) |
| 196 | #define INS_TO_REG(n,val) (SENSORS_LIMIT(SCALE(val,adm1026_scaling[n],192),\ | 199 | #define INS_TO_REG(n, val) (SENSORS_LIMIT(SCALE(val, adm1026_scaling[n], 192),\ |
| 197 | 0,255)) | 200 | 0, 255)) |
| 198 | #define INS_FROM_REG(n,val) (SCALE(val,192,adm1026_scaling[n])) | 201 | #define INS_FROM_REG(n, val) (SCALE(val, 192, adm1026_scaling[n])) |
| 199 | 202 | ||
| 200 | /* FAN speed is measured using 22.5kHz clock and counts for 2 pulses | 203 | /* FAN speed is measured using 22.5kHz clock and counts for 2 pulses |
| 201 | * and we assume a 2 pulse-per-rev fan tach signal | 204 | * and we assume a 2 pulse-per-rev fan tach signal |
| 202 | * 22500 kHz * 60 (sec/min) * 2 (pulse) / 2 (pulse/rev) == 1350000 | 205 | * 22500 kHz * 60 (sec/min) * 2 (pulse) / 2 (pulse/rev) == 1350000 |
| 203 | */ | 206 | */ |
| 204 | #define FAN_TO_REG(val,div) ((val)<=0 ? 0xff : SENSORS_LIMIT(1350000/((val)*\ | 207 | #define FAN_TO_REG(val, div) ((val) <= 0 ? 0xff : \ |
| 205 | (div)),1,254)) | 208 | SENSORS_LIMIT(1350000/((val)*(div)), 1, 254)) |
| 206 | #define FAN_FROM_REG(val,div) ((val)==0?-1:(val)==0xff ? 0 : 1350000/((val)*\ | 209 | #define FAN_FROM_REG(val, div) ((val) == 0 ? -1:(val) == 0xff ? 0 : \ |
| 207 | (div))) | 210 | 1350000/((val)*(div))) |
| 208 | #define DIV_FROM_REG(val) (1<<(val)) | 211 | #define DIV_FROM_REG(val) (1<<(val)) |
| 209 | #define DIV_TO_REG(val) ((val)>=8 ? 3 : (val)>=4 ? 2 : (val)>=2 ? 1 : 0) | 212 | #define DIV_TO_REG(val) ((val) >= 8 ? 3 : (val) >= 4 ? 2 : (val) >= 2 ? 1 : 0) |
| 210 | 213 | ||
| 211 | /* Temperature is reported in 1 degC increments */ | 214 | /* Temperature is reported in 1 degC increments */ |
| 212 | #define TEMP_TO_REG(val) (SENSORS_LIMIT(((val)+((val)<0 ? -500 : 500))/1000,\ | 215 | #define TEMP_TO_REG(val) (SENSORS_LIMIT(((val)+((val)<0 ? -500 : 500))/1000,\ |
| 213 | -127,127)) | 216 | -127, 127)) |
| 214 | #define TEMP_FROM_REG(val) ((val) * 1000) | 217 | #define TEMP_FROM_REG(val) ((val) * 1000) |
| 215 | #define OFFSET_TO_REG(val) (SENSORS_LIMIT(((val)+((val)<0 ? -500 : 500))/1000,\ | 218 | #define OFFSET_TO_REG(val) (SENSORS_LIMIT(((val)+((val)<0 ? -500 : 500))/1000,\ |
| 216 | -127,127)) | 219 | -127, 127)) |
| 217 | #define OFFSET_FROM_REG(val) ((val) * 1000) | 220 | #define OFFSET_FROM_REG(val) ((val) * 1000) |
| 218 | 221 | ||
| 219 | #define PWM_TO_REG(val) (SENSORS_LIMIT(val,0,255)) | 222 | #define PWM_TO_REG(val) (SENSORS_LIMIT(val, 0, 255)) |
| 220 | #define PWM_FROM_REG(val) (val) | 223 | #define PWM_FROM_REG(val) (val) |
| 221 | 224 | ||
| 222 | #define PWM_MIN_TO_REG(val) ((val) & 0xf0) | 225 | #define PWM_MIN_TO_REG(val) ((val) & 0xf0) |
| 223 | #define PWM_MIN_FROM_REG(val) (((val) & 0xf0) + ((val) >> 4)) | 226 | #define PWM_MIN_FROM_REG(val) (((val) & 0xf0) + ((val) >> 4)) |
| 224 | 227 | ||
| 225 | /* Analog output is a voltage, and scaled to millivolts. The datasheet | 228 | /* Analog output is a voltage, and scaled to millivolts. The datasheet |
| 226 | * indicates that the DAC could be used to drive the fans, but in our | 229 | * indicates that the DAC could be used to drive the fans, but in our |
| 227 | * example board (Arima HDAMA) it isn't connected to the fans at all. | 230 | * example board (Arima HDAMA) it isn't connected to the fans at all. |
| 228 | */ | 231 | */ |
| 229 | #define DAC_TO_REG(val) (SENSORS_LIMIT(((((val)*255)+500)/2500),0,255)) | 232 | #define DAC_TO_REG(val) (SENSORS_LIMIT(((((val)*255)+500)/2500), 0, 255)) |
| 230 | #define DAC_FROM_REG(val) (((val)*2500)/255) | 233 | #define DAC_FROM_REG(val) (((val)*2500)/255) |
| 231 | 234 | ||
| 232 | /* Typically used with systems using a v9.1 VRM spec ? */ | ||
| 233 | #define ADM1026_INIT_VRM 91 | ||
| 234 | |||
| 235 | /* Chip sampling rates | 235 | /* Chip sampling rates |
| 236 | * | 236 | * |
| 237 | * Some sensors are not updated more frequently than once per second | 237 | * Some sensors are not updated more frequently than once per second |
| @@ -243,8 +243,8 @@ static int adm1026_scaling[] = { /* .001 Volts */ | |||
| 243 | * So, we keep the config data up to date in the cache | 243 | * So, we keep the config data up to date in the cache |
| 244 | * when it is written and only sample it once every 5 *minutes* | 244 | * when it is written and only sample it once every 5 *minutes* |
| 245 | */ | 245 | */ |
| 246 | #define ADM1026_DATA_INTERVAL (1 * HZ) | 246 | #define ADM1026_DATA_INTERVAL (1 * HZ) |
| 247 | #define ADM1026_CONFIG_INTERVAL (5 * 60 * HZ) | 247 | #define ADM1026_CONFIG_INTERVAL (5 * 60 * HZ) |
| 248 | 248 | ||
| 249 | /* We allow for multiple chips in a single system. | 249 | /* We allow for multiple chips in a single system. |
| 250 | * | 250 | * |
| @@ -261,37 +261,36 @@ struct pwm_data { | |||
| 261 | struct adm1026_data { | 261 | struct adm1026_data { |
| 262 | struct i2c_client client; | 262 | struct i2c_client client; |
| 263 | struct device *hwmon_dev; | 263 | struct device *hwmon_dev; |
| 264 | enum chips type; | ||
| 265 | 264 | ||
| 266 | struct mutex update_lock; | 265 | struct mutex update_lock; |
| 267 | int valid; /* !=0 if following fields are valid */ | 266 | int valid; /* !=0 if following fields are valid */ |
| 268 | unsigned long last_reading; /* In jiffies */ | 267 | unsigned long last_reading; /* In jiffies */ |
| 269 | unsigned long last_config; /* In jiffies */ | 268 | unsigned long last_config; /* In jiffies */ |
| 270 | 269 | ||
| 271 | u8 in[17]; /* Register value */ | 270 | u8 in[17]; /* Register value */ |
| 272 | u8 in_max[17]; /* Register value */ | 271 | u8 in_max[17]; /* Register value */ |
| 273 | u8 in_min[17]; /* Register value */ | 272 | u8 in_min[17]; /* Register value */ |
| 274 | s8 temp[3]; /* Register value */ | 273 | s8 temp[3]; /* Register value */ |
| 275 | s8 temp_min[3]; /* Register value */ | 274 | s8 temp_min[3]; /* Register value */ |
| 276 | s8 temp_max[3]; /* Register value */ | 275 | s8 temp_max[3]; /* Register value */ |
| 277 | s8 temp_tmin[3]; /* Register value */ | 276 | s8 temp_tmin[3]; /* Register value */ |
| 278 | s8 temp_crit[3]; /* Register value */ | 277 | s8 temp_crit[3]; /* Register value */ |
| 279 | s8 temp_offset[3]; /* Register value */ | 278 | s8 temp_offset[3]; /* Register value */ |
| 280 | u8 fan[8]; /* Register value */ | 279 | u8 fan[8]; /* Register value */ |
| 281 | u8 fan_min[8]; /* Register value */ | 280 | u8 fan_min[8]; /* Register value */ |
| 282 | u8 fan_div[8]; /* Decoded value */ | 281 | u8 fan_div[8]; /* Decoded value */ |
| 283 | struct pwm_data pwm1; /* Pwm control values */ | 282 | struct pwm_data pwm1; /* Pwm control values */ |
| 284 | int vid; /* Decoded value */ | 283 | int vid; /* Decoded value */ |
| 285 | u8 vrm; /* VRM version */ | 284 | u8 vrm; /* VRM version */ |
| 286 | u8 analog_out; /* Register value (DAC) */ | 285 | u8 analog_out; /* Register value (DAC) */ |
| 287 | long alarms; /* Register encoding, combined */ | 286 | long alarms; /* Register encoding, combined */ |
| 288 | long alarm_mask; /* Register encoding, combined */ | 287 | long alarm_mask; /* Register encoding, combined */ |
| 289 | long gpio; /* Register encoding, combined */ | 288 | long gpio; /* Register encoding, combined */ |
| 290 | long gpio_mask; /* Register encoding, combined */ | 289 | long gpio_mask; /* Register encoding, combined */ |
| 291 | u8 gpio_config[17]; /* Decoded value */ | 290 | u8 gpio_config[17]; /* Decoded value */ |
| 292 | u8 config1; /* Register value */ | 291 | u8 config1; /* Register value */ |
| 293 | u8 config2; /* Register value */ | 292 | u8 config2; /* Register value */ |
| 294 | u8 config3; /* Register value */ | 293 | u8 config3; /* Register value */ |
| 295 | }; | 294 | }; |
| 296 | 295 | ||
| 297 | static int adm1026_attach_adapter(struct i2c_adapter *adapter); | 296 | static int adm1026_attach_adapter(struct i2c_adapter *adapter); |
| @@ -301,7 +300,7 @@ static int adm1026_detach_client(struct i2c_client *client); | |||
| 301 | static int adm1026_read_value(struct i2c_client *client, u8 reg); | 300 | static int adm1026_read_value(struct i2c_client *client, u8 reg); |
| 302 | static int adm1026_write_value(struct i2c_client *client, u8 reg, int value); | 301 | static int adm1026_write_value(struct i2c_client *client, u8 reg, int value); |
| 303 | static void adm1026_print_gpio(struct i2c_client *client); | 302 | static void adm1026_print_gpio(struct i2c_client *client); |
| 304 | static void adm1026_fixup_gpio(struct i2c_client *client); | 303 | static void adm1026_fixup_gpio(struct i2c_client *client); |
| 305 | static struct adm1026_data *adm1026_update_device(struct device *dev); | 304 | static struct adm1026_data *adm1026_update_device(struct device *dev); |
| 306 | static void adm1026_init_client(struct i2c_client *client); | 305 | static void adm1026_init_client(struct i2c_client *client); |
| 307 | 306 | ||
| @@ -311,7 +310,7 @@ static struct i2c_driver adm1026_driver = { | |||
| 311 | .name = "adm1026", | 310 | .name = "adm1026", |
| 312 | }, | 311 | }, |
| 313 | .attach_adapter = adm1026_attach_adapter, | 312 | .attach_adapter = adm1026_attach_adapter, |
| 314 | .detach_client = adm1026_detach_client, | 313 | .detach_client = adm1026_detach_client, |
| 315 | }; | 314 | }; |
| 316 | 315 | ||
| 317 | static int adm1026_attach_adapter(struct i2c_adapter *adapter) | 316 | static int adm1026_attach_adapter(struct i2c_adapter *adapter) |
| @@ -355,7 +354,7 @@ static void adm1026_init_client(struct i2c_client *client) | |||
| 355 | int value, i; | 354 | int value, i; |
| 356 | struct adm1026_data *data = i2c_get_clientdata(client); | 355 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 357 | 356 | ||
| 358 | dev_dbg(&client->dev, "Initializing device\n"); | 357 | dev_dbg(&client->dev, "Initializing device\n"); |
| 359 | /* Read chip config */ | 358 | /* Read chip config */ |
| 360 | data->config1 = adm1026_read_value(client, ADM1026_REG_CONFIG1); | 359 | data->config1 = adm1026_read_value(client, ADM1026_REG_CONFIG1); |
| 361 | data->config2 = adm1026_read_value(client, ADM1026_REG_CONFIG2); | 360 | data->config2 = adm1026_read_value(client, ADM1026_REG_CONFIG2); |
| @@ -384,7 +383,6 @@ static void adm1026_init_client(struct i2c_client *client) | |||
| 384 | "and temp limits enabled.\n"); | 383 | "and temp limits enabled.\n"); |
| 385 | } | 384 | } |
| 386 | 385 | ||
| 387 | value = data->config3; | ||
| 388 | if (data->config3 & CFG3_GPIO16_ENABLE) { | 386 | if (data->config3 & CFG3_GPIO16_ENABLE) { |
| 389 | dev_dbg(&client->dev, "GPIO16 enabled. THERM " | 387 | dev_dbg(&client->dev, "GPIO16 enabled. THERM " |
| 390 | "pin disabled.\n"); | 388 | "pin disabled.\n"); |
| @@ -426,10 +424,10 @@ static void adm1026_init_client(struct i2c_client *client) | |||
| 426 | * configured, we don't want to mess with them. | 424 | * configured, we don't want to mess with them. |
| 427 | * If they weren't, the default is 100% PWM, no | 425 | * If they weren't, the default is 100% PWM, no |
| 428 | * control and will suffice until 'sensors -s' | 426 | * control and will suffice until 'sensors -s' |
| 429 | * can be run by the user. We DO set the default | 427 | * can be run by the user. We DO set the default |
| 430 | * value for pwm1.auto_pwm_min to its maximum | 428 | * value for pwm1.auto_pwm_min to its maximum |
| 431 | * so that enabling automatic pwm fan control | 429 | * so that enabling automatic pwm fan control |
| 432 | * without first setting a value for pwm1.auto_pwm_min | 430 | * without first setting a value for pwm1.auto_pwm_min |
| 433 | * will not result in potentially dangerous fan speed decrease. | 431 | * will not result in potentially dangerous fan speed decrease. |
| 434 | */ | 432 | */ |
| 435 | data->pwm1.auto_pwm_min=255; | 433 | data->pwm1.auto_pwm_min=255; |
| @@ -453,7 +451,7 @@ static void adm1026_init_client(struct i2c_client *client) | |||
| 453 | static void adm1026_print_gpio(struct i2c_client *client) | 451 | static void adm1026_print_gpio(struct i2c_client *client) |
| 454 | { | 452 | { |
| 455 | struct adm1026_data *data = i2c_get_clientdata(client); | 453 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 456 | int i; | 454 | int i; |
| 457 | 455 | ||
| 458 | dev_dbg(&client->dev, "GPIO config is:"); | 456 | dev_dbg(&client->dev, "GPIO config is:"); |
| 459 | for (i = 0;i <= 7;++i) { | 457 | for (i = 0;i <= 7;++i) { |
| @@ -477,7 +475,7 @@ static void adm1026_print_gpio(struct i2c_client *client) | |||
| 477 | data->gpio_config[16] & 0x02 ? "" : "!", | 475 | data->gpio_config[16] & 0x02 ? "" : "!", |
| 478 | data->gpio_config[16] & 0x01 ? "OUT" : "IN"); | 476 | data->gpio_config[16] & 0x01 ? "OUT" : "IN"); |
| 479 | } else { | 477 | } else { |
| 480 | /* GPIO16 is THERM */ | 478 | /* GPIO16 is THERM */ |
| 481 | dev_dbg(&client->dev, "\tTHERM\n"); | 479 | dev_dbg(&client->dev, "\tTHERM\n"); |
| 482 | } | 480 | } |
| 483 | } | 481 | } |
| @@ -485,8 +483,8 @@ static void adm1026_print_gpio(struct i2c_client *client) | |||
| 485 | static void adm1026_fixup_gpio(struct i2c_client *client) | 483 | static void adm1026_fixup_gpio(struct i2c_client *client) |
| 486 | { | 484 | { |
| 487 | struct adm1026_data *data = i2c_get_clientdata(client); | 485 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 488 | int i; | 486 | int i; |
| 489 | int value; | 487 | int value; |
| 490 | 488 | ||
| 491 | /* Make the changes requested. */ | 489 | /* Make the changes requested. */ |
| 492 | /* We may need to unlock/stop monitoring or soft-reset the | 490 | /* We may need to unlock/stop monitoring or soft-reset the |
| @@ -516,14 +514,14 @@ static void adm1026_fixup_gpio(struct i2c_client *client) | |||
| 516 | } | 514 | } |
| 517 | } | 515 | } |
| 518 | 516 | ||
| 519 | /* Inverted */ | 517 | /* Inverted */ |
| 520 | for (i = 0;i <= 16;++i) { | 518 | for (i = 0;i <= 16;++i) { |
| 521 | if (gpio_inverted[i] >= 0 && gpio_inverted[i] <= 16) { | 519 | if (gpio_inverted[i] >= 0 && gpio_inverted[i] <= 16) { |
| 522 | data->gpio_config[gpio_inverted[i]] &= ~ 0x02; | 520 | data->gpio_config[gpio_inverted[i]] &= ~ 0x02; |
| 523 | } | 521 | } |
| 524 | } | 522 | } |
| 525 | 523 | ||
| 526 | /* Normal overrides inverted */ | 524 | /* Normal overrides inverted */ |
| 527 | for (i = 0;i <= 16;++i) { | 525 | for (i = 0;i <= 16;++i) { |
| 528 | if (gpio_normal[i] >= 0 && gpio_normal[i] <= 16) { | 526 | if (gpio_normal[i] >= 0 && gpio_normal[i] <= 16) { |
| 529 | data->gpio_config[gpio_normal[i]] |= 0x02; | 527 | data->gpio_config[gpio_normal[i]] |= 0x02; |
| @@ -569,7 +567,7 @@ static struct adm1026_data *adm1026_update_device(struct device *dev) | |||
| 569 | if (!data->valid | 567 | if (!data->valid |
| 570 | || time_after(jiffies, data->last_reading + ADM1026_DATA_INTERVAL)) { | 568 | || time_after(jiffies, data->last_reading + ADM1026_DATA_INTERVAL)) { |
| 571 | /* Things that change quickly */ | 569 | /* Things that change quickly */ |
| 572 | dev_dbg(&client->dev,"Reading sensor values\n"); | 570 | dev_dbg(&client->dev, "Reading sensor values\n"); |
| 573 | for (i = 0;i <= 16;++i) { | 571 | for (i = 0;i <= 16;++i) { |
| 574 | data->in[i] = | 572 | data->in[i] = |
| 575 | adm1026_read_value(client, ADM1026_REG_IN[i]); | 573 | adm1026_read_value(client, ADM1026_REG_IN[i]); |
| @@ -582,18 +580,18 @@ static struct adm1026_data *adm1026_update_device(struct device *dev) | |||
| 582 | 580 | ||
| 583 | for (i = 0;i <= 2;++i) { | 581 | for (i = 0;i <= 2;++i) { |
| 584 | /* NOTE: temp[] is s8 and we assume 2's complement | 582 | /* NOTE: temp[] is s8 and we assume 2's complement |
| 585 | * "conversion" in the assignment */ | 583 | * "conversion" in the assignment */ |
| 586 | data->temp[i] = | 584 | data->temp[i] = |
| 587 | adm1026_read_value(client, ADM1026_REG_TEMP[i]); | 585 | adm1026_read_value(client, ADM1026_REG_TEMP[i]); |
| 588 | } | 586 | } |
| 589 | 587 | ||
| 590 | data->pwm1.pwm = adm1026_read_value(client, | 588 | data->pwm1.pwm = adm1026_read_value(client, |
| 591 | ADM1026_REG_PWM); | 589 | ADM1026_REG_PWM); |
| 592 | data->analog_out = adm1026_read_value(client, | 590 | data->analog_out = adm1026_read_value(client, |
| 593 | ADM1026_REG_DAC); | 591 | ADM1026_REG_DAC); |
| 594 | /* GPIO16 is MSbit of alarms, move it to gpio */ | 592 | /* GPIO16 is MSbit of alarms, move it to gpio */ |
| 595 | alarms = adm1026_read_value(client, ADM1026_REG_STATUS4); | 593 | alarms = adm1026_read_value(client, ADM1026_REG_STATUS4); |
| 596 | gpio = alarms & 0x80 ? 0x0100 : 0; /* GPIO16 */ | 594 | gpio = alarms & 0x80 ? 0x0100 : 0; /* GPIO16 */ |
| 597 | alarms &= 0x7f; | 595 | alarms &= 0x7f; |
| 598 | alarms <<= 8; | 596 | alarms <<= 8; |
| 599 | alarms |= adm1026_read_value(client, ADM1026_REG_STATUS3); | 597 | alarms |= adm1026_read_value(client, ADM1026_REG_STATUS3); |
| @@ -604,24 +602,24 @@ static struct adm1026_data *adm1026_update_device(struct device *dev) | |||
| 604 | data->alarms = alarms; | 602 | data->alarms = alarms; |
| 605 | 603 | ||
| 606 | /* Read the GPIO values */ | 604 | /* Read the GPIO values */ |
| 607 | gpio |= adm1026_read_value(client, | 605 | gpio |= adm1026_read_value(client, |
| 608 | ADM1026_REG_GPIO_STATUS_8_15); | 606 | ADM1026_REG_GPIO_STATUS_8_15); |
| 609 | gpio <<= 8; | 607 | gpio <<= 8; |
| 610 | gpio |= adm1026_read_value(client, | 608 | gpio |= adm1026_read_value(client, |
| 611 | ADM1026_REG_GPIO_STATUS_0_7); | 609 | ADM1026_REG_GPIO_STATUS_0_7); |
| 612 | data->gpio = gpio; | 610 | data->gpio = gpio; |
| 613 | 611 | ||
| 614 | data->last_reading = jiffies; | 612 | data->last_reading = jiffies; |
| 615 | }; /* last_reading */ | 613 | }; /* last_reading */ |
| 616 | 614 | ||
| 617 | if (!data->valid || | 615 | if (!data->valid || |
| 618 | time_after(jiffies, data->last_config + ADM1026_CONFIG_INTERVAL)) { | 616 | time_after(jiffies, data->last_config + ADM1026_CONFIG_INTERVAL)) { |
| 619 | /* Things that don't change often */ | 617 | /* Things that don't change often */ |
| 620 | dev_dbg(&client->dev, "Reading config values\n"); | 618 | dev_dbg(&client->dev, "Reading config values\n"); |
| 621 | for (i = 0;i <= 16;++i) { | 619 | for (i = 0;i <= 16;++i) { |
| 622 | data->in_min[i] = adm1026_read_value(client, | 620 | data->in_min[i] = adm1026_read_value(client, |
| 623 | ADM1026_REG_IN_MIN[i]); | 621 | ADM1026_REG_IN_MIN[i]); |
| 624 | data->in_max[i] = adm1026_read_value(client, | 622 | data->in_max[i] = adm1026_read_value(client, |
| 625 | ADM1026_REG_IN_MAX[i]); | 623 | ADM1026_REG_IN_MAX[i]); |
| 626 | } | 624 | } |
| 627 | 625 | ||
| @@ -629,32 +627,32 @@ static struct adm1026_data *adm1026_update_device(struct device *dev) | |||
| 629 | | (adm1026_read_value(client, ADM1026_REG_FAN_DIV_4_7) | 627 | | (adm1026_read_value(client, ADM1026_REG_FAN_DIV_4_7) |
| 630 | << 8); | 628 | << 8); |
| 631 | for (i = 0;i <= 7;++i) { | 629 | for (i = 0;i <= 7;++i) { |
| 632 | data->fan_min[i] = adm1026_read_value(client, | 630 | data->fan_min[i] = adm1026_read_value(client, |
| 633 | ADM1026_REG_FAN_MIN(i)); | 631 | ADM1026_REG_FAN_MIN(i)); |
| 634 | data->fan_div[i] = DIV_FROM_REG(value & 0x03); | 632 | data->fan_div[i] = DIV_FROM_REG(value & 0x03); |
| 635 | value >>= 2; | 633 | value >>= 2; |
| 636 | } | 634 | } |
| 637 | 635 | ||
| 638 | for (i = 0; i <= 2; ++i) { | 636 | for (i = 0; i <= 2; ++i) { |
| 639 | /* NOTE: temp_xxx[] are s8 and we assume 2's | 637 | /* NOTE: temp_xxx[] are s8 and we assume 2's |
| 640 | * complement "conversion" in the assignment | 638 | * complement "conversion" in the assignment |
| 641 | */ | 639 | */ |
| 642 | data->temp_min[i] = adm1026_read_value(client, | 640 | data->temp_min[i] = adm1026_read_value(client, |
| 643 | ADM1026_REG_TEMP_MIN[i]); | 641 | ADM1026_REG_TEMP_MIN[i]); |
| 644 | data->temp_max[i] = adm1026_read_value(client, | 642 | data->temp_max[i] = adm1026_read_value(client, |
| 645 | ADM1026_REG_TEMP_MAX[i]); | 643 | ADM1026_REG_TEMP_MAX[i]); |
| 646 | data->temp_tmin[i] = adm1026_read_value(client, | 644 | data->temp_tmin[i] = adm1026_read_value(client, |
| 647 | ADM1026_REG_TEMP_TMIN[i]); | 645 | ADM1026_REG_TEMP_TMIN[i]); |
| 648 | data->temp_crit[i] = adm1026_read_value(client, | 646 | data->temp_crit[i] = adm1026_read_value(client, |
| 649 | ADM1026_REG_TEMP_THERM[i]); | 647 | ADM1026_REG_TEMP_THERM[i]); |
| 650 | data->temp_offset[i] = adm1026_read_value(client, | 648 | data->temp_offset[i] = adm1026_read_value(client, |
| 651 | ADM1026_REG_TEMP_OFFSET[i]); | 649 | ADM1026_REG_TEMP_OFFSET[i]); |
| 652 | } | 650 | } |
| 653 | 651 | ||
| 654 | /* Read the STATUS/alarm masks */ | 652 | /* Read the STATUS/alarm masks */ |
| 655 | alarms = adm1026_read_value(client, ADM1026_REG_MASK4); | 653 | alarms = adm1026_read_value(client, ADM1026_REG_MASK4); |
| 656 | gpio = alarms & 0x80 ? 0x0100 : 0; /* GPIO16 */ | 654 | gpio = alarms & 0x80 ? 0x0100 : 0; /* GPIO16 */ |
| 657 | alarms = (alarms & 0x7f) << 8; | 655 | alarms = (alarms & 0x7f) << 8; |
| 658 | alarms |= adm1026_read_value(client, ADM1026_REG_MASK3); | 656 | alarms |= adm1026_read_value(client, ADM1026_REG_MASK3); |
| 659 | alarms <<= 8; | 657 | alarms <<= 8; |
| 660 | alarms |= adm1026_read_value(client, ADM1026_REG_MASK2); | 658 | alarms |= adm1026_read_value(client, ADM1026_REG_MASK2); |
| @@ -663,24 +661,24 @@ static struct adm1026_data *adm1026_update_device(struct device *dev) | |||
| 663 | data->alarm_mask = alarms; | 661 | data->alarm_mask = alarms; |
| 664 | 662 | ||
| 665 | /* Read the GPIO values */ | 663 | /* Read the GPIO values */ |
| 666 | gpio |= adm1026_read_value(client, | 664 | gpio |= adm1026_read_value(client, |
| 667 | ADM1026_REG_GPIO_MASK_8_15); | 665 | ADM1026_REG_GPIO_MASK_8_15); |
| 668 | gpio <<= 8; | 666 | gpio <<= 8; |
| 669 | gpio |= adm1026_read_value(client, ADM1026_REG_GPIO_MASK_0_7); | 667 | gpio |= adm1026_read_value(client, ADM1026_REG_GPIO_MASK_0_7); |
| 670 | data->gpio_mask = gpio; | 668 | data->gpio_mask = gpio; |
| 671 | 669 | ||
| 672 | /* Read various values from CONFIG1 */ | 670 | /* Read various values from CONFIG1 */ |
| 673 | data->config1 = adm1026_read_value(client, | 671 | data->config1 = adm1026_read_value(client, |
| 674 | ADM1026_REG_CONFIG1); | 672 | ADM1026_REG_CONFIG1); |
| 675 | if (data->config1 & CFG1_PWM_AFC) { | 673 | if (data->config1 & CFG1_PWM_AFC) { |
| 676 | data->pwm1.enable = 2; | 674 | data->pwm1.enable = 2; |
| 677 | data->pwm1.auto_pwm_min = | 675 | data->pwm1.auto_pwm_min = |
| 678 | PWM_MIN_FROM_REG(data->pwm1.pwm); | 676 | PWM_MIN_FROM_REG(data->pwm1.pwm); |
| 679 | } | 677 | } |
| 680 | /* Read the GPIO config */ | 678 | /* Read the GPIO config */ |
| 681 | data->config2 = adm1026_read_value(client, | 679 | data->config2 = adm1026_read_value(client, |
| 682 | ADM1026_REG_CONFIG2); | 680 | ADM1026_REG_CONFIG2); |
| 683 | data->config3 = adm1026_read_value(client, | 681 | data->config3 = adm1026_read_value(client, |
| 684 | ADM1026_REG_CONFIG3); | 682 | ADM1026_REG_CONFIG3); |
| 685 | data->gpio_config[16] = (data->config3 >> 6) & 0x03; | 683 | data->gpio_config[16] = (data->config3 >> 6) & 0x03; |
| 686 | 684 | ||
| @@ -695,7 +693,7 @@ static struct adm1026_data *adm1026_update_device(struct device *dev) | |||
| 695 | } | 693 | } |
| 696 | 694 | ||
| 697 | data->last_config = jiffies; | 695 | data->last_config = jiffies; |
| 698 | }; /* last_config */ | 696 | }; /* last_config */ |
| 699 | 697 | ||
| 700 | dev_dbg(&client->dev, "Setting VID from GPIO11-15.\n"); | 698 | dev_dbg(&client->dev, "Setting VID from GPIO11-15.\n"); |
| 701 | data->vid = (data->gpio >> 11) & 0x1f; | 699 | data->vid = (data->gpio >> 11) & 0x1f; |
| @@ -710,15 +708,15 @@ static ssize_t show_in(struct device *dev, struct device_attribute *attr, | |||
| 710 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 708 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 711 | int nr = sensor_attr->index; | 709 | int nr = sensor_attr->index; |
| 712 | struct adm1026_data *data = adm1026_update_device(dev); | 710 | struct adm1026_data *data = adm1026_update_device(dev); |
| 713 | return sprintf(buf,"%d\n", INS_FROM_REG(nr, data->in[nr])); | 711 | return sprintf(buf, "%d\n", INS_FROM_REG(nr, data->in[nr])); |
| 714 | } | 712 | } |
| 715 | static ssize_t show_in_min(struct device *dev, struct device_attribute *attr, | 713 | static ssize_t show_in_min(struct device *dev, struct device_attribute *attr, |
| 716 | char *buf) | 714 | char *buf) |
| 717 | { | 715 | { |
| 718 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 716 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 719 | int nr = sensor_attr->index; | 717 | int nr = sensor_attr->index; |
| 720 | struct adm1026_data *data = adm1026_update_device(dev); | 718 | struct adm1026_data *data = adm1026_update_device(dev); |
| 721 | return sprintf(buf,"%d\n", INS_FROM_REG(nr, data->in_min[nr])); | 719 | return sprintf(buf, "%d\n", INS_FROM_REG(nr, data->in_min[nr])); |
| 722 | } | 720 | } |
| 723 | static ssize_t set_in_min(struct device *dev, struct device_attribute *attr, | 721 | static ssize_t set_in_min(struct device *dev, struct device_attribute *attr, |
| 724 | const char *buf, size_t count) | 722 | const char *buf, size_t count) |
| @@ -733,7 +731,7 @@ static ssize_t set_in_min(struct device *dev, struct device_attribute *attr, | |||
| 733 | data->in_min[nr] = INS_TO_REG(nr, val); | 731 | data->in_min[nr] = INS_TO_REG(nr, val); |
| 734 | adm1026_write_value(client, ADM1026_REG_IN_MIN[nr], data->in_min[nr]); | 732 | adm1026_write_value(client, ADM1026_REG_IN_MIN[nr], data->in_min[nr]); |
| 735 | mutex_unlock(&data->update_lock); | 733 | mutex_unlock(&data->update_lock); |
| 736 | return count; | 734 | return count; |
| 737 | } | 735 | } |
| 738 | static ssize_t show_in_max(struct device *dev, struct device_attribute *attr, | 736 | static ssize_t show_in_max(struct device *dev, struct device_attribute *attr, |
| 739 | char *buf) | 737 | char *buf) |
| @@ -741,7 +739,7 @@ static ssize_t show_in_max(struct device *dev, struct device_attribute *attr, | |||
| 741 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 739 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 742 | int nr = sensor_attr->index; | 740 | int nr = sensor_attr->index; |
| 743 | struct adm1026_data *data = adm1026_update_device(dev); | 741 | struct adm1026_data *data = adm1026_update_device(dev); |
| 744 | return sprintf(buf,"%d\n", INS_FROM_REG(nr, data->in_max[nr])); | 742 | return sprintf(buf, "%d\n", INS_FROM_REG(nr, data->in_max[nr])); |
| 745 | } | 743 | } |
| 746 | static ssize_t set_in_max(struct device *dev, struct device_attribute *attr, | 744 | static ssize_t set_in_max(struct device *dev, struct device_attribute *attr, |
| 747 | const char *buf, size_t count) | 745 | const char *buf, size_t count) |
| @@ -788,13 +786,13 @@ in_reg(15); | |||
| 788 | static ssize_t show_in16(struct device *dev, struct device_attribute *attr, char *buf) | 786 | static ssize_t show_in16(struct device *dev, struct device_attribute *attr, char *buf) |
| 789 | { | 787 | { |
| 790 | struct adm1026_data *data = adm1026_update_device(dev); | 788 | struct adm1026_data *data = adm1026_update_device(dev); |
| 791 | return sprintf(buf,"%d\n", INS_FROM_REG(16, data->in[16]) - | 789 | return sprintf(buf, "%d\n", INS_FROM_REG(16, data->in[16]) - |
| 792 | NEG12_OFFSET); | 790 | NEG12_OFFSET); |
| 793 | } | 791 | } |
| 794 | static ssize_t show_in16_min(struct device *dev, struct device_attribute *attr, char *buf) | 792 | static ssize_t show_in16_min(struct device *dev, struct device_attribute *attr, char *buf) |
| 795 | { | 793 | { |
| 796 | struct adm1026_data *data = adm1026_update_device(dev); | 794 | struct adm1026_data *data = adm1026_update_device(dev); |
| 797 | return sprintf(buf,"%d\n", INS_FROM_REG(16, data->in_min[16]) | 795 | return sprintf(buf, "%d\n", INS_FROM_REG(16, data->in_min[16]) |
| 798 | - NEG12_OFFSET); | 796 | - NEG12_OFFSET); |
| 799 | } | 797 | } |
| 800 | static ssize_t set_in16_min(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 798 | static ssize_t set_in16_min(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) |
| @@ -807,12 +805,12 @@ static ssize_t set_in16_min(struct device *dev, struct device_attribute *attr, c | |||
| 807 | data->in_min[16] = INS_TO_REG(16, val + NEG12_OFFSET); | 805 | data->in_min[16] = INS_TO_REG(16, val + NEG12_OFFSET); |
| 808 | adm1026_write_value(client, ADM1026_REG_IN_MIN[16], data->in_min[16]); | 806 | adm1026_write_value(client, ADM1026_REG_IN_MIN[16], data->in_min[16]); |
| 809 | mutex_unlock(&data->update_lock); | 807 | mutex_unlock(&data->update_lock); |
| 810 | return count; | 808 | return count; |
| 811 | } | 809 | } |
| 812 | static ssize_t show_in16_max(struct device *dev, struct device_attribute *attr, char *buf) | 810 | static ssize_t show_in16_max(struct device *dev, struct device_attribute *attr, char *buf) |
| 813 | { | 811 | { |
| 814 | struct adm1026_data *data = adm1026_update_device(dev); | 812 | struct adm1026_data *data = adm1026_update_device(dev); |
| 815 | return sprintf(buf,"%d\n", INS_FROM_REG(16, data->in_max[16]) | 813 | return sprintf(buf, "%d\n", INS_FROM_REG(16, data->in_max[16]) |
| 816 | - NEG12_OFFSET); | 814 | - NEG12_OFFSET); |
| 817 | } | 815 | } |
| 818 | static ssize_t set_in16_max(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 816 | static ssize_t set_in16_max(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) |
| @@ -843,7 +841,7 @@ static ssize_t show_fan(struct device *dev, struct device_attribute *attr, | |||
| 843 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 841 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 844 | int nr = sensor_attr->index; | 842 | int nr = sensor_attr->index; |
| 845 | struct adm1026_data *data = adm1026_update_device(dev); | 843 | struct adm1026_data *data = adm1026_update_device(dev); |
| 846 | return sprintf(buf,"%d\n", FAN_FROM_REG(data->fan[nr], | 844 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan[nr], |
| 847 | data->fan_div[nr])); | 845 | data->fan_div[nr])); |
| 848 | } | 846 | } |
| 849 | static ssize_t show_fan_min(struct device *dev, struct device_attribute *attr, | 847 | static ssize_t show_fan_min(struct device *dev, struct device_attribute *attr, |
| @@ -852,7 +850,7 @@ static ssize_t show_fan_min(struct device *dev, struct device_attribute *attr, | |||
| 852 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 850 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 853 | int nr = sensor_attr->index; | 851 | int nr = sensor_attr->index; |
| 854 | struct adm1026_data *data = adm1026_update_device(dev); | 852 | struct adm1026_data *data = adm1026_update_device(dev); |
| 855 | return sprintf(buf,"%d\n", FAN_FROM_REG(data->fan_min[nr], | 853 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_min[nr], |
| 856 | data->fan_div[nr])); | 854 | data->fan_div[nr])); |
| 857 | } | 855 | } |
| 858 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, | 856 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, |
| @@ -872,10 +870,10 @@ static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, | |||
| 872 | return count; | 870 | return count; |
| 873 | } | 871 | } |
| 874 | 872 | ||
| 875 | #define fan_offset(offset) \ | 873 | #define fan_offset(offset) \ |
| 876 | static SENSOR_DEVICE_ATTR(fan##offset##_input, S_IRUGO, show_fan, NULL, \ | 874 | static SENSOR_DEVICE_ATTR(fan##offset##_input, S_IRUGO, show_fan, NULL, \ |
| 877 | offset - 1); \ | 875 | offset - 1); \ |
| 878 | static SENSOR_DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \ | 876 | static SENSOR_DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \ |
| 879 | show_fan_min, set_fan_min, offset - 1); | 877 | show_fan_min, set_fan_min, offset - 1); |
| 880 | 878 | ||
| 881 | fan_offset(1); | 879 | fan_offset(1); |
| @@ -892,8 +890,8 @@ static void fixup_fan_min(struct device *dev, int fan, int old_div) | |||
| 892 | { | 890 | { |
| 893 | struct i2c_client *client = to_i2c_client(dev); | 891 | struct i2c_client *client = to_i2c_client(dev); |
| 894 | struct adm1026_data *data = i2c_get_clientdata(client); | 892 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 895 | int new_min; | 893 | int new_min; |
| 896 | int new_div = data->fan_div[fan]; | 894 | int new_div = data->fan_div[fan]; |
| 897 | 895 | ||
| 898 | /* 0 and 0xff are special. Don't adjust them */ | 896 | /* 0 and 0xff are special. Don't adjust them */ |
| 899 | if (data->fan_min[fan] == 0 || data->fan_min[fan] == 0xff) { | 897 | if (data->fan_min[fan] == 0 || data->fan_min[fan] == 0xff) { |
| @@ -913,7 +911,7 @@ static ssize_t show_fan_div(struct device *dev, struct device_attribute *attr, | |||
| 913 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 911 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 914 | int nr = sensor_attr->index; | 912 | int nr = sensor_attr->index; |
| 915 | struct adm1026_data *data = adm1026_update_device(dev); | 913 | struct adm1026_data *data = adm1026_update_device(dev); |
| 916 | return sprintf(buf,"%d\n", data->fan_div[nr]); | 914 | return sprintf(buf, "%d\n", data->fan_div[nr]); |
| 917 | } | 915 | } |
| 918 | static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, | 916 | static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, |
| 919 | const char *buf, size_t count) | 917 | const char *buf, size_t count) |
| @@ -922,10 +920,10 @@ static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, | |||
| 922 | int nr = sensor_attr->index; | 920 | int nr = sensor_attr->index; |
| 923 | struct i2c_client *client = to_i2c_client(dev); | 921 | struct i2c_client *client = to_i2c_client(dev); |
| 924 | struct adm1026_data *data = i2c_get_clientdata(client); | 922 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 925 | int val,orig_div,new_div,shift; | 923 | int val, orig_div, new_div, shift; |
| 926 | 924 | ||
| 927 | val = simple_strtol(buf, NULL, 10); | 925 | val = simple_strtol(buf, NULL, 10); |
| 928 | new_div = DIV_TO_REG(val); | 926 | new_div = DIV_TO_REG(val); |
| 929 | if (new_div == 0) { | 927 | if (new_div == 0) { |
| 930 | return -EINVAL; | 928 | return -EINVAL; |
| 931 | } | 929 | } |
| @@ -946,14 +944,14 @@ static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, | |||
| 946 | } | 944 | } |
| 947 | 945 | ||
| 948 | if (data->fan_div[nr] != orig_div) { | 946 | if (data->fan_div[nr] != orig_div) { |
| 949 | fixup_fan_min(dev,nr,orig_div); | 947 | fixup_fan_min(dev, nr, orig_div); |
| 950 | } | 948 | } |
| 951 | mutex_unlock(&data->update_lock); | 949 | mutex_unlock(&data->update_lock); |
| 952 | return count; | 950 | return count; |
| 953 | } | 951 | } |
| 954 | 952 | ||
| 955 | #define fan_offset_div(offset) \ | 953 | #define fan_offset_div(offset) \ |
| 956 | static SENSOR_DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \ | 954 | static SENSOR_DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \ |
| 957 | show_fan_div, set_fan_div, offset - 1); | 955 | show_fan_div, set_fan_div, offset - 1); |
| 958 | 956 | ||
| 959 | fan_offset_div(1); | 957 | fan_offset_div(1); |
| @@ -972,7 +970,7 @@ static ssize_t show_temp(struct device *dev, struct device_attribute *attr, | |||
| 972 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 970 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 973 | int nr = sensor_attr->index; | 971 | int nr = sensor_attr->index; |
| 974 | struct adm1026_data *data = adm1026_update_device(dev); | 972 | struct adm1026_data *data = adm1026_update_device(dev); |
| 975 | return sprintf(buf,"%d\n", TEMP_FROM_REG(data->temp[nr])); | 973 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp[nr])); |
| 976 | } | 974 | } |
| 977 | static ssize_t show_temp_min(struct device *dev, struct device_attribute *attr, | 975 | static ssize_t show_temp_min(struct device *dev, struct device_attribute *attr, |
| 978 | char *buf) | 976 | char *buf) |
| @@ -980,7 +978,7 @@ static ssize_t show_temp_min(struct device *dev, struct device_attribute *attr, | |||
| 980 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 978 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 981 | int nr = sensor_attr->index; | 979 | int nr = sensor_attr->index; |
| 982 | struct adm1026_data *data = adm1026_update_device(dev); | 980 | struct adm1026_data *data = adm1026_update_device(dev); |
| 983 | return sprintf(buf,"%d\n", TEMP_FROM_REG(data->temp_min[nr])); | 981 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_min[nr])); |
| 984 | } | 982 | } |
| 985 | static ssize_t set_temp_min(struct device *dev, struct device_attribute *attr, | 983 | static ssize_t set_temp_min(struct device *dev, struct device_attribute *attr, |
| 986 | const char *buf, size_t count) | 984 | const char *buf, size_t count) |
| @@ -1004,7 +1002,7 @@ static ssize_t show_temp_max(struct device *dev, struct device_attribute *attr, | |||
| 1004 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 1002 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 1005 | int nr = sensor_attr->index; | 1003 | int nr = sensor_attr->index; |
| 1006 | struct adm1026_data *data = adm1026_update_device(dev); | 1004 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1007 | return sprintf(buf,"%d\n", TEMP_FROM_REG(data->temp_max[nr])); | 1005 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[nr])); |
| 1008 | } | 1006 | } |
| 1009 | static ssize_t set_temp_max(struct device *dev, struct device_attribute *attr, | 1007 | static ssize_t set_temp_max(struct device *dev, struct device_attribute *attr, |
| 1010 | const char *buf, size_t count) | 1008 | const char *buf, size_t count) |
| @@ -1024,7 +1022,7 @@ static ssize_t set_temp_max(struct device *dev, struct device_attribute *attr, | |||
| 1024 | } | 1022 | } |
| 1025 | 1023 | ||
| 1026 | #define temp_reg(offset) \ | 1024 | #define temp_reg(offset) \ |
| 1027 | static SENSOR_DEVICE_ATTR(temp##offset##_input, S_IRUGO, show_temp, \ | 1025 | static SENSOR_DEVICE_ATTR(temp##offset##_input, S_IRUGO, show_temp, \ |
| 1028 | NULL, offset - 1); \ | 1026 | NULL, offset - 1); \ |
| 1029 | static SENSOR_DEVICE_ATTR(temp##offset##_min, S_IRUGO | S_IWUSR, \ | 1027 | static SENSOR_DEVICE_ATTR(temp##offset##_min, S_IRUGO | S_IWUSR, \ |
| 1030 | show_temp_min, set_temp_min, offset - 1); \ | 1028 | show_temp_min, set_temp_min, offset - 1); \ |
| @@ -1042,7 +1040,7 @@ static ssize_t show_temp_offset(struct device *dev, | |||
| 1042 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 1040 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 1043 | int nr = sensor_attr->index; | 1041 | int nr = sensor_attr->index; |
| 1044 | struct adm1026_data *data = adm1026_update_device(dev); | 1042 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1045 | return sprintf(buf,"%d\n", TEMP_FROM_REG(data->temp_offset[nr])); | 1043 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_offset[nr])); |
| 1046 | } | 1044 | } |
| 1047 | static ssize_t set_temp_offset(struct device *dev, | 1045 | static ssize_t set_temp_offset(struct device *dev, |
| 1048 | struct device_attribute *attr, const char *buf, | 1046 | struct device_attribute *attr, const char *buf, |
| @@ -1076,7 +1074,7 @@ static ssize_t show_temp_auto_point1_temp_hyst(struct device *dev, | |||
| 1076 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 1074 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 1077 | int nr = sensor_attr->index; | 1075 | int nr = sensor_attr->index; |
| 1078 | struct adm1026_data *data = adm1026_update_device(dev); | 1076 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1079 | return sprintf(buf,"%d\n", TEMP_FROM_REG( | 1077 | return sprintf(buf, "%d\n", TEMP_FROM_REG( |
| 1080 | ADM1026_FAN_ACTIVATION_TEMP_HYST + data->temp_tmin[nr])); | 1078 | ADM1026_FAN_ACTIVATION_TEMP_HYST + data->temp_tmin[nr])); |
| 1081 | } | 1079 | } |
| 1082 | static ssize_t show_temp_auto_point2_temp(struct device *dev, | 1080 | static ssize_t show_temp_auto_point2_temp(struct device *dev, |
| @@ -1085,7 +1083,7 @@ static ssize_t show_temp_auto_point2_temp(struct device *dev, | |||
| 1085 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 1083 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 1086 | int nr = sensor_attr->index; | 1084 | int nr = sensor_attr->index; |
| 1087 | struct adm1026_data *data = adm1026_update_device(dev); | 1085 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1088 | return sprintf(buf,"%d\n", TEMP_FROM_REG(data->temp_tmin[nr] + | 1086 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_tmin[nr] + |
| 1089 | ADM1026_FAN_CONTROL_TEMP_RANGE)); | 1087 | ADM1026_FAN_CONTROL_TEMP_RANGE)); |
| 1090 | } | 1088 | } |
| 1091 | static ssize_t show_temp_auto_point1_temp(struct device *dev, | 1089 | static ssize_t show_temp_auto_point1_temp(struct device *dev, |
| @@ -1094,7 +1092,7 @@ static ssize_t show_temp_auto_point1_temp(struct device *dev, | |||
| 1094 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 1092 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 1095 | int nr = sensor_attr->index; | 1093 | int nr = sensor_attr->index; |
| 1096 | struct adm1026_data *data = adm1026_update_device(dev); | 1094 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1097 | return sprintf(buf,"%d\n", TEMP_FROM_REG(data->temp_tmin[nr])); | 1095 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_tmin[nr])); |
| 1098 | } | 1096 | } |
| 1099 | static ssize_t set_temp_auto_point1_temp(struct device *dev, | 1097 | static ssize_t set_temp_auto_point1_temp(struct device *dev, |
| 1100 | struct device_attribute *attr, const char *buf, size_t count) | 1098 | struct device_attribute *attr, const char *buf, size_t count) |
| @@ -1113,13 +1111,13 @@ static ssize_t set_temp_auto_point1_temp(struct device *dev, | |||
| 1113 | return count; | 1111 | return count; |
| 1114 | } | 1112 | } |
| 1115 | 1113 | ||
| 1116 | #define temp_auto_point(offset) \ | 1114 | #define temp_auto_point(offset) \ |
| 1117 | static SENSOR_DEVICE_ATTR(temp##offset##_auto_point1_temp, S_IRUGO | S_IWUSR, \ | 1115 | static SENSOR_DEVICE_ATTR(temp##offset##_auto_point1_temp, \ |
| 1118 | show_temp_auto_point1_temp, set_temp_auto_point1_temp, \ | 1116 | S_IRUGO | S_IWUSR, show_temp_auto_point1_temp, \ |
| 1119 | offset - 1); \ | 1117 | set_temp_auto_point1_temp, offset - 1); \ |
| 1120 | static SENSOR_DEVICE_ATTR(temp##offset##_auto_point1_temp_hyst, S_IRUGO, \ | 1118 | static SENSOR_DEVICE_ATTR(temp##offset##_auto_point1_temp_hyst, S_IRUGO,\ |
| 1121 | show_temp_auto_point1_temp_hyst, NULL, offset - 1); \ | 1119 | show_temp_auto_point1_temp_hyst, NULL, offset - 1); \ |
| 1122 | static SENSOR_DEVICE_ATTR(temp##offset##_auto_point2_temp, S_IRUGO, \ | 1120 | static SENSOR_DEVICE_ATTR(temp##offset##_auto_point2_temp, S_IRUGO, \ |
| 1123 | show_temp_auto_point2_temp, NULL, offset - 1); | 1121 | show_temp_auto_point2_temp, NULL, offset - 1); |
| 1124 | 1122 | ||
| 1125 | temp_auto_point(1); | 1123 | temp_auto_point(1); |
| @@ -1130,7 +1128,7 @@ static ssize_t show_temp_crit_enable(struct device *dev, | |||
| 1130 | struct device_attribute *attr, char *buf) | 1128 | struct device_attribute *attr, char *buf) |
| 1131 | { | 1129 | { |
| 1132 | struct adm1026_data *data = adm1026_update_device(dev); | 1130 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1133 | return sprintf(buf,"%d\n", (data->config1 & CFG1_THERM_HOT) >> 4); | 1131 | return sprintf(buf, "%d\n", (data->config1 & CFG1_THERM_HOT) >> 4); |
| 1134 | } | 1132 | } |
| 1135 | static ssize_t set_temp_crit_enable(struct device *dev, | 1133 | static ssize_t set_temp_crit_enable(struct device *dev, |
| 1136 | struct device_attribute *attr, const char *buf, size_t count) | 1134 | struct device_attribute *attr, const char *buf, size_t count) |
| @@ -1142,7 +1140,7 @@ static ssize_t set_temp_crit_enable(struct device *dev, | |||
| 1142 | if ((val == 1) || (val==0)) { | 1140 | if ((val == 1) || (val==0)) { |
| 1143 | mutex_lock(&data->update_lock); | 1141 | mutex_lock(&data->update_lock); |
| 1144 | data->config1 = (data->config1 & ~CFG1_THERM_HOT) | (val << 4); | 1142 | data->config1 = (data->config1 & ~CFG1_THERM_HOT) | (val << 4); |
| 1145 | adm1026_write_value(client, ADM1026_REG_CONFIG1, | 1143 | adm1026_write_value(client, ADM1026_REG_CONFIG1, |
| 1146 | data->config1); | 1144 | data->config1); |
| 1147 | mutex_unlock(&data->update_lock); | 1145 | mutex_unlock(&data->update_lock); |
| 1148 | } | 1146 | } |
| @@ -1163,7 +1161,7 @@ static ssize_t show_temp_crit(struct device *dev, | |||
| 1163 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | 1161 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); |
| 1164 | int nr = sensor_attr->index; | 1162 | int nr = sensor_attr->index; |
| 1165 | struct adm1026_data *data = adm1026_update_device(dev); | 1163 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1166 | return sprintf(buf,"%d\n", TEMP_FROM_REG(data->temp_crit[nr])); | 1164 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_crit[nr])); |
| 1167 | } | 1165 | } |
| 1168 | static ssize_t set_temp_crit(struct device *dev, struct device_attribute *attr, | 1166 | static ssize_t set_temp_crit(struct device *dev, struct device_attribute *attr, |
| 1169 | const char *buf, size_t count) | 1167 | const char *buf, size_t count) |
| @@ -1193,7 +1191,7 @@ temp_crit_reg(3); | |||
| 1193 | static ssize_t show_analog_out_reg(struct device *dev, struct device_attribute *attr, char *buf) | 1191 | static ssize_t show_analog_out_reg(struct device *dev, struct device_attribute *attr, char *buf) |
| 1194 | { | 1192 | { |
| 1195 | struct adm1026_data *data = adm1026_update_device(dev); | 1193 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1196 | return sprintf(buf,"%d\n", DAC_FROM_REG(data->analog_out)); | 1194 | return sprintf(buf, "%d\n", DAC_FROM_REG(data->analog_out)); |
| 1197 | } | 1195 | } |
| 1198 | static ssize_t set_analog_out_reg(struct device *dev, struct device_attribute *attr, const char *buf, | 1196 | static ssize_t set_analog_out_reg(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1199 | size_t count) | 1197 | size_t count) |
| @@ -1209,26 +1207,25 @@ static ssize_t set_analog_out_reg(struct device *dev, struct device_attribute *a | |||
| 1209 | return count; | 1207 | return count; |
| 1210 | } | 1208 | } |
| 1211 | 1209 | ||
| 1212 | static DEVICE_ATTR(analog_out, S_IRUGO | S_IWUSR, show_analog_out_reg, | 1210 | static DEVICE_ATTR(analog_out, S_IRUGO | S_IWUSR, show_analog_out_reg, |
| 1213 | set_analog_out_reg); | 1211 | set_analog_out_reg); |
| 1214 | 1212 | ||
| 1215 | static ssize_t show_vid_reg(struct device *dev, struct device_attribute *attr, char *buf) | 1213 | static ssize_t show_vid_reg(struct device *dev, struct device_attribute *attr, char *buf) |
| 1216 | { | 1214 | { |
| 1217 | struct adm1026_data *data = adm1026_update_device(dev); | 1215 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1218 | return sprintf(buf,"%d\n", vid_from_reg(data->vid & 0x3f, data->vrm)); | 1216 | return sprintf(buf, "%d\n", vid_from_reg(data->vid & 0x3f, data->vrm)); |
| 1219 | } | 1217 | } |
| 1220 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid_reg, NULL); | 1218 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid_reg, NULL); |
| 1221 | 1219 | ||
| 1222 | static ssize_t show_vrm_reg(struct device *dev, struct device_attribute *attr, char *buf) | 1220 | static ssize_t show_vrm_reg(struct device *dev, struct device_attribute *attr, char *buf) |
| 1223 | { | 1221 | { |
| 1224 | struct adm1026_data *data = dev_get_drvdata(dev); | 1222 | struct adm1026_data *data = dev_get_drvdata(dev); |
| 1225 | return sprintf(buf,"%d\n", data->vrm); | 1223 | return sprintf(buf, "%d\n", data->vrm); |
| 1226 | } | 1224 | } |
| 1227 | static ssize_t store_vrm_reg(struct device *dev, struct device_attribute *attr, const char *buf, | 1225 | static ssize_t store_vrm_reg(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1228 | size_t count) | 1226 | size_t count) |
| 1229 | { | 1227 | { |
| 1230 | struct i2c_client *client = to_i2c_client(dev); | 1228 | struct adm1026_data *data = dev_get_drvdata(dev); |
| 1231 | struct adm1026_data *data = i2c_get_clientdata(client); | ||
| 1232 | 1229 | ||
| 1233 | data->vrm = simple_strtol(buf, NULL, 10); | 1230 | data->vrm = simple_strtol(buf, NULL, 10); |
| 1234 | return count; | 1231 | return count; |
| @@ -1239,15 +1236,52 @@ static DEVICE_ATTR(vrm, S_IRUGO | S_IWUSR, show_vrm_reg, store_vrm_reg); | |||
| 1239 | static ssize_t show_alarms_reg(struct device *dev, struct device_attribute *attr, char *buf) | 1236 | static ssize_t show_alarms_reg(struct device *dev, struct device_attribute *attr, char *buf) |
| 1240 | { | 1237 | { |
| 1241 | struct adm1026_data *data = adm1026_update_device(dev); | 1238 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1242 | return sprintf(buf, "%ld\n", (long) (data->alarms)); | 1239 | return sprintf(buf, "%ld\n", data->alarms); |
| 1243 | } | 1240 | } |
| 1244 | 1241 | ||
| 1245 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms_reg, NULL); | 1242 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms_reg, NULL); |
| 1246 | 1243 | ||
| 1244 | static ssize_t show_alarm(struct device *dev, struct device_attribute *attr, | ||
| 1245 | char *buf) | ||
| 1246 | { | ||
| 1247 | struct adm1026_data *data = adm1026_update_device(dev); | ||
| 1248 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 1249 | return sprintf(buf, "%ld\n", (data->alarms >> bitnr) & 1); | ||
| 1250 | } | ||
| 1251 | |||
| 1252 | static SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 1253 | static SENSOR_DEVICE_ATTR(temp3_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 1254 | static SENSOR_DEVICE_ATTR(in9_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 1255 | static SENSOR_DEVICE_ATTR(in11_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 1256 | static SENSOR_DEVICE_ATTR(in12_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 1257 | static SENSOR_DEVICE_ATTR(in13_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 1258 | static SENSOR_DEVICE_ATTR(in14_alarm, S_IRUGO, show_alarm, NULL, 5); | ||
| 1259 | static SENSOR_DEVICE_ATTR(in15_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 1260 | static SENSOR_DEVICE_ATTR(in16_alarm, S_IRUGO, show_alarm, NULL, 7); | ||
| 1261 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 1262 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 9); | ||
| 1263 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 10); | ||
| 1264 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 11); | ||
| 1265 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL, 12); | ||
| 1266 | static SENSOR_DEVICE_ATTR(in5_alarm, S_IRUGO, show_alarm, NULL, 13); | ||
| 1267 | static SENSOR_DEVICE_ATTR(in6_alarm, S_IRUGO, show_alarm, NULL, 14); | ||
| 1268 | static SENSOR_DEVICE_ATTR(in7_alarm, S_IRUGO, show_alarm, NULL, 15); | ||
| 1269 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 16); | ||
| 1270 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 17); | ||
| 1271 | static SENSOR_DEVICE_ATTR(fan3_alarm, S_IRUGO, show_alarm, NULL, 18); | ||
| 1272 | static SENSOR_DEVICE_ATTR(fan4_alarm, S_IRUGO, show_alarm, NULL, 19); | ||
| 1273 | static SENSOR_DEVICE_ATTR(fan5_alarm, S_IRUGO, show_alarm, NULL, 20); | ||
| 1274 | static SENSOR_DEVICE_ATTR(fan6_alarm, S_IRUGO, show_alarm, NULL, 21); | ||
| 1275 | static SENSOR_DEVICE_ATTR(fan7_alarm, S_IRUGO, show_alarm, NULL, 22); | ||
| 1276 | static SENSOR_DEVICE_ATTR(fan8_alarm, S_IRUGO, show_alarm, NULL, 23); | ||
| 1277 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, 24); | ||
| 1278 | static SENSOR_DEVICE_ATTR(in10_alarm, S_IRUGO, show_alarm, NULL, 25); | ||
| 1279 | static SENSOR_DEVICE_ATTR(in8_alarm, S_IRUGO, show_alarm, NULL, 26); | ||
| 1280 | |||
| 1247 | static ssize_t show_alarm_mask(struct device *dev, struct device_attribute *attr, char *buf) | 1281 | static ssize_t show_alarm_mask(struct device *dev, struct device_attribute *attr, char *buf) |
| 1248 | { | 1282 | { |
| 1249 | struct adm1026_data *data = adm1026_update_device(dev); | 1283 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1250 | return sprintf(buf,"%ld\n", data->alarm_mask); | 1284 | return sprintf(buf, "%ld\n", data->alarm_mask); |
| 1251 | } | 1285 | } |
| 1252 | static ssize_t set_alarm_mask(struct device *dev, struct device_attribute *attr, const char *buf, | 1286 | static ssize_t set_alarm_mask(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1253 | size_t count) | 1287 | size_t count) |
| @@ -1283,7 +1317,7 @@ static DEVICE_ATTR(alarm_mask, S_IRUGO | S_IWUSR, show_alarm_mask, | |||
| 1283 | static ssize_t show_gpio(struct device *dev, struct device_attribute *attr, char *buf) | 1317 | static ssize_t show_gpio(struct device *dev, struct device_attribute *attr, char *buf) |
| 1284 | { | 1318 | { |
| 1285 | struct adm1026_data *data = adm1026_update_device(dev); | 1319 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1286 | return sprintf(buf,"%ld\n", data->gpio); | 1320 | return sprintf(buf, "%ld\n", data->gpio); |
| 1287 | } | 1321 | } |
| 1288 | static ssize_t set_gpio(struct device *dev, struct device_attribute *attr, const char *buf, | 1322 | static ssize_t set_gpio(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1289 | size_t count) | 1323 | size_t count) |
| @@ -1291,16 +1325,16 @@ static ssize_t set_gpio(struct device *dev, struct device_attribute *attr, const | |||
| 1291 | struct i2c_client *client = to_i2c_client(dev); | 1325 | struct i2c_client *client = to_i2c_client(dev); |
| 1292 | struct adm1026_data *data = i2c_get_clientdata(client); | 1326 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 1293 | int val = simple_strtol(buf, NULL, 10); | 1327 | int val = simple_strtol(buf, NULL, 10); |
| 1294 | long gpio; | 1328 | long gpio; |
| 1295 | 1329 | ||
| 1296 | mutex_lock(&data->update_lock); | 1330 | mutex_lock(&data->update_lock); |
| 1297 | data->gpio = val & 0x1ffff; | 1331 | data->gpio = val & 0x1ffff; |
| 1298 | gpio = data->gpio; | 1332 | gpio = data->gpio; |
| 1299 | adm1026_write_value(client, ADM1026_REG_GPIO_STATUS_0_7,gpio & 0xff); | 1333 | adm1026_write_value(client, ADM1026_REG_GPIO_STATUS_0_7, gpio & 0xff); |
| 1300 | gpio >>= 8; | 1334 | gpio >>= 8; |
| 1301 | adm1026_write_value(client, ADM1026_REG_GPIO_STATUS_8_15,gpio & 0xff); | 1335 | adm1026_write_value(client, ADM1026_REG_GPIO_STATUS_8_15, gpio & 0xff); |
| 1302 | gpio = ((gpio >> 1) & 0x80) | (data->alarms >> 24 & 0x7f); | 1336 | gpio = ((gpio >> 1) & 0x80) | (data->alarms >> 24 & 0x7f); |
| 1303 | adm1026_write_value(client, ADM1026_REG_STATUS4,gpio & 0xff); | 1337 | adm1026_write_value(client, ADM1026_REG_STATUS4, gpio & 0xff); |
| 1304 | mutex_unlock(&data->update_lock); | 1338 | mutex_unlock(&data->update_lock); |
| 1305 | return count; | 1339 | return count; |
| 1306 | } | 1340 | } |
| @@ -1311,7 +1345,7 @@ static DEVICE_ATTR(gpio, S_IRUGO | S_IWUSR, show_gpio, set_gpio); | |||
| 1311 | static ssize_t show_gpio_mask(struct device *dev, struct device_attribute *attr, char *buf) | 1345 | static ssize_t show_gpio_mask(struct device *dev, struct device_attribute *attr, char *buf) |
| 1312 | { | 1346 | { |
| 1313 | struct adm1026_data *data = adm1026_update_device(dev); | 1347 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1314 | return sprintf(buf,"%ld\n", data->gpio_mask); | 1348 | return sprintf(buf, "%ld\n", data->gpio_mask); |
| 1315 | } | 1349 | } |
| 1316 | static ssize_t set_gpio_mask(struct device *dev, struct device_attribute *attr, const char *buf, | 1350 | static ssize_t set_gpio_mask(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1317 | size_t count) | 1351 | size_t count) |
| @@ -1319,16 +1353,16 @@ static ssize_t set_gpio_mask(struct device *dev, struct device_attribute *attr, | |||
| 1319 | struct i2c_client *client = to_i2c_client(dev); | 1353 | struct i2c_client *client = to_i2c_client(dev); |
| 1320 | struct adm1026_data *data = i2c_get_clientdata(client); | 1354 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 1321 | int val = simple_strtol(buf, NULL, 10); | 1355 | int val = simple_strtol(buf, NULL, 10); |
| 1322 | long mask; | 1356 | long mask; |
| 1323 | 1357 | ||
| 1324 | mutex_lock(&data->update_lock); | 1358 | mutex_lock(&data->update_lock); |
| 1325 | data->gpio_mask = val & 0x1ffff; | 1359 | data->gpio_mask = val & 0x1ffff; |
| 1326 | mask = data->gpio_mask; | 1360 | mask = data->gpio_mask; |
| 1327 | adm1026_write_value(client, ADM1026_REG_GPIO_MASK_0_7,mask & 0xff); | 1361 | adm1026_write_value(client, ADM1026_REG_GPIO_MASK_0_7, mask & 0xff); |
| 1328 | mask >>= 8; | 1362 | mask >>= 8; |
| 1329 | adm1026_write_value(client, ADM1026_REG_GPIO_MASK_8_15,mask & 0xff); | 1363 | adm1026_write_value(client, ADM1026_REG_GPIO_MASK_8_15, mask & 0xff); |
| 1330 | mask = ((mask >> 1) & 0x80) | (data->alarm_mask >> 24 & 0x7f); | 1364 | mask = ((mask >> 1) & 0x80) | (data->alarm_mask >> 24 & 0x7f); |
| 1331 | adm1026_write_value(client, ADM1026_REG_MASK1,mask & 0xff); | 1365 | adm1026_write_value(client, ADM1026_REG_MASK1, mask & 0xff); |
| 1332 | mutex_unlock(&data->update_lock); | 1366 | mutex_unlock(&data->update_lock); |
| 1333 | return count; | 1367 | return count; |
| 1334 | } | 1368 | } |
| @@ -1338,7 +1372,7 @@ static DEVICE_ATTR(gpio_mask, S_IRUGO | S_IWUSR, show_gpio_mask, set_gpio_mask); | |||
| 1338 | static ssize_t show_pwm_reg(struct device *dev, struct device_attribute *attr, char *buf) | 1372 | static ssize_t show_pwm_reg(struct device *dev, struct device_attribute *attr, char *buf) |
| 1339 | { | 1373 | { |
| 1340 | struct adm1026_data *data = adm1026_update_device(dev); | 1374 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1341 | return sprintf(buf,"%d\n", PWM_FROM_REG(data->pwm1.pwm)); | 1375 | return sprintf(buf, "%d\n", PWM_FROM_REG(data->pwm1.pwm)); |
| 1342 | } | 1376 | } |
| 1343 | static ssize_t set_pwm_reg(struct device *dev, struct device_attribute *attr, const char *buf, | 1377 | static ssize_t set_pwm_reg(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1344 | size_t count) | 1378 | size_t count) |
| @@ -1359,7 +1393,7 @@ static ssize_t set_pwm_reg(struct device *dev, struct device_attribute *attr, co | |||
| 1359 | static ssize_t show_auto_pwm_min(struct device *dev, struct device_attribute *attr, char *buf) | 1393 | static ssize_t show_auto_pwm_min(struct device *dev, struct device_attribute *attr, char *buf) |
| 1360 | { | 1394 | { |
| 1361 | struct adm1026_data *data = adm1026_update_device(dev); | 1395 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1362 | return sprintf(buf,"%d\n", data->pwm1.auto_pwm_min); | 1396 | return sprintf(buf, "%d\n", data->pwm1.auto_pwm_min); |
| 1363 | } | 1397 | } |
| 1364 | static ssize_t set_auto_pwm_min(struct device *dev, struct device_attribute *attr, const char *buf, | 1398 | static ssize_t set_auto_pwm_min(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1365 | size_t count) | 1399 | size_t count) |
| @@ -1369,10 +1403,10 @@ static ssize_t set_auto_pwm_min(struct device *dev, struct device_attribute *att | |||
| 1369 | int val = simple_strtol(buf, NULL, 10); | 1403 | int val = simple_strtol(buf, NULL, 10); |
| 1370 | 1404 | ||
| 1371 | mutex_lock(&data->update_lock); | 1405 | mutex_lock(&data->update_lock); |
| 1372 | data->pwm1.auto_pwm_min = SENSORS_LIMIT(val,0,255); | 1406 | data->pwm1.auto_pwm_min = SENSORS_LIMIT(val, 0, 255); |
| 1373 | if (data->pwm1.enable == 2) { /* apply immediately */ | 1407 | if (data->pwm1.enable == 2) { /* apply immediately */ |
| 1374 | data->pwm1.pwm = PWM_TO_REG((data->pwm1.pwm & 0x0f) | | 1408 | data->pwm1.pwm = PWM_TO_REG((data->pwm1.pwm & 0x0f) | |
| 1375 | PWM_MIN_TO_REG(data->pwm1.auto_pwm_min)); | 1409 | PWM_MIN_TO_REG(data->pwm1.auto_pwm_min)); |
| 1376 | adm1026_write_value(client, ADM1026_REG_PWM, data->pwm1.pwm); | 1410 | adm1026_write_value(client, ADM1026_REG_PWM, data->pwm1.pwm); |
| 1377 | } | 1411 | } |
| 1378 | mutex_unlock(&data->update_lock); | 1412 | mutex_unlock(&data->update_lock); |
| @@ -1380,12 +1414,12 @@ static ssize_t set_auto_pwm_min(struct device *dev, struct device_attribute *att | |||
| 1380 | } | 1414 | } |
| 1381 | static ssize_t show_auto_pwm_max(struct device *dev, struct device_attribute *attr, char *buf) | 1415 | static ssize_t show_auto_pwm_max(struct device *dev, struct device_attribute *attr, char *buf) |
| 1382 | { | 1416 | { |
| 1383 | return sprintf(buf,"%d\n", ADM1026_PWM_MAX); | 1417 | return sprintf(buf, "%d\n", ADM1026_PWM_MAX); |
| 1384 | } | 1418 | } |
| 1385 | static ssize_t show_pwm_enable(struct device *dev, struct device_attribute *attr, char *buf) | 1419 | static ssize_t show_pwm_enable(struct device *dev, struct device_attribute *attr, char *buf) |
| 1386 | { | 1420 | { |
| 1387 | struct adm1026_data *data = adm1026_update_device(dev); | 1421 | struct adm1026_data *data = adm1026_update_device(dev); |
| 1388 | return sprintf(buf,"%d\n", data->pwm1.enable); | 1422 | return sprintf(buf, "%d\n", data->pwm1.enable); |
| 1389 | } | 1423 | } |
| 1390 | static ssize_t set_pwm_enable(struct device *dev, struct device_attribute *attr, const char *buf, | 1424 | static ssize_t set_pwm_enable(struct device *dev, struct device_attribute *attr, const char *buf, |
| 1391 | size_t count) | 1425 | size_t count) |
| @@ -1393,7 +1427,7 @@ static ssize_t set_pwm_enable(struct device *dev, struct device_attribute *attr, | |||
| 1393 | struct i2c_client *client = to_i2c_client(dev); | 1427 | struct i2c_client *client = to_i2c_client(dev); |
| 1394 | struct adm1026_data *data = i2c_get_clientdata(client); | 1428 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 1395 | int val = simple_strtol(buf, NULL, 10); | 1429 | int val = simple_strtol(buf, NULL, 10); |
| 1396 | int old_enable; | 1430 | int old_enable; |
| 1397 | 1431 | ||
| 1398 | if ((val >= 0) && (val < 3)) { | 1432 | if ((val >= 0) && (val < 3)) { |
| 1399 | mutex_lock(&data->update_lock); | 1433 | mutex_lock(&data->update_lock); |
| @@ -1403,15 +1437,15 @@ static ssize_t set_pwm_enable(struct device *dev, struct device_attribute *attr, | |||
| 1403 | | ((val == 2) ? CFG1_PWM_AFC : 0); | 1437 | | ((val == 2) ? CFG1_PWM_AFC : 0); |
| 1404 | adm1026_write_value(client, ADM1026_REG_CONFIG1, | 1438 | adm1026_write_value(client, ADM1026_REG_CONFIG1, |
| 1405 | data->config1); | 1439 | data->config1); |
| 1406 | if (val == 2) { /* apply pwm1_auto_pwm_min to pwm1 */ | 1440 | if (val == 2) { /* apply pwm1_auto_pwm_min to pwm1 */ |
| 1407 | data->pwm1.pwm = PWM_TO_REG((data->pwm1.pwm & 0x0f) | | 1441 | data->pwm1.pwm = PWM_TO_REG((data->pwm1.pwm & 0x0f) | |
| 1408 | PWM_MIN_TO_REG(data->pwm1.auto_pwm_min)); | 1442 | PWM_MIN_TO_REG(data->pwm1.auto_pwm_min)); |
| 1409 | adm1026_write_value(client, ADM1026_REG_PWM, | 1443 | adm1026_write_value(client, ADM1026_REG_PWM, |
| 1410 | data->pwm1.pwm); | 1444 | data->pwm1.pwm); |
| 1411 | } else if (!((old_enable == 1) && (val == 1))) { | 1445 | } else if (!((old_enable == 1) && (val == 1))) { |
| 1412 | /* set pwm to safe value */ | 1446 | /* set pwm to safe value */ |
| 1413 | data->pwm1.pwm = 255; | 1447 | data->pwm1.pwm = 255; |
| 1414 | adm1026_write_value(client, ADM1026_REG_PWM, | 1448 | adm1026_write_value(client, ADM1026_REG_PWM, |
| 1415 | data->pwm1.pwm); | 1449 | data->pwm1.pwm); |
| 1416 | } | 1450 | } |
| 1417 | mutex_unlock(&data->update_lock); | 1451 | mutex_unlock(&data->update_lock); |
| @@ -1420,20 +1454,20 @@ static ssize_t set_pwm_enable(struct device *dev, struct device_attribute *attr, | |||
| 1420 | } | 1454 | } |
| 1421 | 1455 | ||
| 1422 | /* enable PWM fan control */ | 1456 | /* enable PWM fan control */ |
| 1423 | static DEVICE_ATTR(pwm1, S_IRUGO | S_IWUSR, show_pwm_reg, set_pwm_reg); | 1457 | static DEVICE_ATTR(pwm1, S_IRUGO | S_IWUSR, show_pwm_reg, set_pwm_reg); |
| 1424 | static DEVICE_ATTR(pwm2, S_IRUGO | S_IWUSR, show_pwm_reg, set_pwm_reg); | 1458 | static DEVICE_ATTR(pwm2, S_IRUGO | S_IWUSR, show_pwm_reg, set_pwm_reg); |
| 1425 | static DEVICE_ATTR(pwm3, S_IRUGO | S_IWUSR, show_pwm_reg, set_pwm_reg); | 1459 | static DEVICE_ATTR(pwm3, S_IRUGO | S_IWUSR, show_pwm_reg, set_pwm_reg); |
| 1426 | static DEVICE_ATTR(pwm1_enable, S_IRUGO | S_IWUSR, show_pwm_enable, | 1460 | static DEVICE_ATTR(pwm1_enable, S_IRUGO | S_IWUSR, show_pwm_enable, |
| 1427 | set_pwm_enable); | 1461 | set_pwm_enable); |
| 1428 | static DEVICE_ATTR(pwm2_enable, S_IRUGO | S_IWUSR, show_pwm_enable, | 1462 | static DEVICE_ATTR(pwm2_enable, S_IRUGO | S_IWUSR, show_pwm_enable, |
| 1429 | set_pwm_enable); | 1463 | set_pwm_enable); |
| 1430 | static DEVICE_ATTR(pwm3_enable, S_IRUGO | S_IWUSR, show_pwm_enable, | 1464 | static DEVICE_ATTR(pwm3_enable, S_IRUGO | S_IWUSR, show_pwm_enable, |
| 1431 | set_pwm_enable); | 1465 | set_pwm_enable); |
| 1432 | static DEVICE_ATTR(temp1_auto_point1_pwm, S_IRUGO | S_IWUSR, | 1466 | static DEVICE_ATTR(temp1_auto_point1_pwm, S_IRUGO | S_IWUSR, |
| 1433 | show_auto_pwm_min, set_auto_pwm_min); | 1467 | show_auto_pwm_min, set_auto_pwm_min); |
| 1434 | static DEVICE_ATTR(temp2_auto_point1_pwm, S_IRUGO | S_IWUSR, | 1468 | static DEVICE_ATTR(temp2_auto_point1_pwm, S_IRUGO | S_IWUSR, |
| 1435 | show_auto_pwm_min, set_auto_pwm_min); | 1469 | show_auto_pwm_min, set_auto_pwm_min); |
| 1436 | static DEVICE_ATTR(temp3_auto_point1_pwm, S_IRUGO | S_IWUSR, | 1470 | static DEVICE_ATTR(temp3_auto_point1_pwm, S_IRUGO | S_IWUSR, |
| 1437 | show_auto_pwm_min, set_auto_pwm_min); | 1471 | show_auto_pwm_min, set_auto_pwm_min); |
| 1438 | 1472 | ||
| 1439 | static DEVICE_ATTR(temp1_auto_point2_pwm, S_IRUGO, show_auto_pwm_max, NULL); | 1473 | static DEVICE_ATTR(temp1_auto_point2_pwm, S_IRUGO, show_auto_pwm_max, NULL); |
| @@ -1444,105 +1478,115 @@ static struct attribute *adm1026_attributes[] = { | |||
| 1444 | &sensor_dev_attr_in0_input.dev_attr.attr, | 1478 | &sensor_dev_attr_in0_input.dev_attr.attr, |
| 1445 | &sensor_dev_attr_in0_max.dev_attr.attr, | 1479 | &sensor_dev_attr_in0_max.dev_attr.attr, |
| 1446 | &sensor_dev_attr_in0_min.dev_attr.attr, | 1480 | &sensor_dev_attr_in0_min.dev_attr.attr, |
| 1481 | &sensor_dev_attr_in0_alarm.dev_attr.attr, | ||
| 1447 | &sensor_dev_attr_in1_input.dev_attr.attr, | 1482 | &sensor_dev_attr_in1_input.dev_attr.attr, |
| 1448 | &sensor_dev_attr_in1_max.dev_attr.attr, | 1483 | &sensor_dev_attr_in1_max.dev_attr.attr, |
| 1449 | &sensor_dev_attr_in1_min.dev_attr.attr, | 1484 | &sensor_dev_attr_in1_min.dev_attr.attr, |
| 1485 | &sensor_dev_attr_in1_alarm.dev_attr.attr, | ||
| 1450 | &sensor_dev_attr_in2_input.dev_attr.attr, | 1486 | &sensor_dev_attr_in2_input.dev_attr.attr, |
| 1451 | &sensor_dev_attr_in2_max.dev_attr.attr, | 1487 | &sensor_dev_attr_in2_max.dev_attr.attr, |
| 1452 | &sensor_dev_attr_in2_min.dev_attr.attr, | 1488 | &sensor_dev_attr_in2_min.dev_attr.attr, |
| 1489 | &sensor_dev_attr_in2_alarm.dev_attr.attr, | ||
| 1453 | &sensor_dev_attr_in3_input.dev_attr.attr, | 1490 | &sensor_dev_attr_in3_input.dev_attr.attr, |
| 1454 | &sensor_dev_attr_in3_max.dev_attr.attr, | 1491 | &sensor_dev_attr_in3_max.dev_attr.attr, |
| 1455 | &sensor_dev_attr_in3_min.dev_attr.attr, | 1492 | &sensor_dev_attr_in3_min.dev_attr.attr, |
| 1493 | &sensor_dev_attr_in3_alarm.dev_attr.attr, | ||
| 1456 | &sensor_dev_attr_in4_input.dev_attr.attr, | 1494 | &sensor_dev_attr_in4_input.dev_attr.attr, |
| 1457 | &sensor_dev_attr_in4_max.dev_attr.attr, | 1495 | &sensor_dev_attr_in4_max.dev_attr.attr, |
| 1458 | &sensor_dev_attr_in4_min.dev_attr.attr, | 1496 | &sensor_dev_attr_in4_min.dev_attr.attr, |
| 1497 | &sensor_dev_attr_in4_alarm.dev_attr.attr, | ||
| 1459 | &sensor_dev_attr_in5_input.dev_attr.attr, | 1498 | &sensor_dev_attr_in5_input.dev_attr.attr, |
| 1460 | &sensor_dev_attr_in5_max.dev_attr.attr, | 1499 | &sensor_dev_attr_in5_max.dev_attr.attr, |
| 1461 | &sensor_dev_attr_in5_min.dev_attr.attr, | 1500 | &sensor_dev_attr_in5_min.dev_attr.attr, |
| 1501 | &sensor_dev_attr_in5_alarm.dev_attr.attr, | ||
| 1462 | &sensor_dev_attr_in6_input.dev_attr.attr, | 1502 | &sensor_dev_attr_in6_input.dev_attr.attr, |
| 1463 | &sensor_dev_attr_in6_max.dev_attr.attr, | 1503 | &sensor_dev_attr_in6_max.dev_attr.attr, |
| 1464 | &sensor_dev_attr_in6_min.dev_attr.attr, | 1504 | &sensor_dev_attr_in6_min.dev_attr.attr, |
| 1505 | &sensor_dev_attr_in6_alarm.dev_attr.attr, | ||
| 1465 | &sensor_dev_attr_in7_input.dev_attr.attr, | 1506 | &sensor_dev_attr_in7_input.dev_attr.attr, |
| 1466 | &sensor_dev_attr_in7_max.dev_attr.attr, | 1507 | &sensor_dev_attr_in7_max.dev_attr.attr, |
| 1467 | &sensor_dev_attr_in7_min.dev_attr.attr, | 1508 | &sensor_dev_attr_in7_min.dev_attr.attr, |
| 1468 | &sensor_dev_attr_in8_input.dev_attr.attr, | 1509 | &sensor_dev_attr_in7_alarm.dev_attr.attr, |
| 1469 | &sensor_dev_attr_in8_max.dev_attr.attr, | ||
| 1470 | &sensor_dev_attr_in8_min.dev_attr.attr, | ||
| 1471 | &sensor_dev_attr_in9_input.dev_attr.attr, | ||
| 1472 | &sensor_dev_attr_in9_max.dev_attr.attr, | ||
| 1473 | &sensor_dev_attr_in9_min.dev_attr.attr, | ||
| 1474 | &sensor_dev_attr_in10_input.dev_attr.attr, | 1510 | &sensor_dev_attr_in10_input.dev_attr.attr, |
| 1475 | &sensor_dev_attr_in10_max.dev_attr.attr, | 1511 | &sensor_dev_attr_in10_max.dev_attr.attr, |
| 1476 | &sensor_dev_attr_in10_min.dev_attr.attr, | 1512 | &sensor_dev_attr_in10_min.dev_attr.attr, |
| 1513 | &sensor_dev_attr_in10_alarm.dev_attr.attr, | ||
| 1477 | &sensor_dev_attr_in11_input.dev_attr.attr, | 1514 | &sensor_dev_attr_in11_input.dev_attr.attr, |
| 1478 | &sensor_dev_attr_in11_max.dev_attr.attr, | 1515 | &sensor_dev_attr_in11_max.dev_attr.attr, |
| 1479 | &sensor_dev_attr_in11_min.dev_attr.attr, | 1516 | &sensor_dev_attr_in11_min.dev_attr.attr, |
| 1517 | &sensor_dev_attr_in11_alarm.dev_attr.attr, | ||
| 1480 | &sensor_dev_attr_in12_input.dev_attr.attr, | 1518 | &sensor_dev_attr_in12_input.dev_attr.attr, |
| 1481 | &sensor_dev_attr_in12_max.dev_attr.attr, | 1519 | &sensor_dev_attr_in12_max.dev_attr.attr, |
| 1482 | &sensor_dev_attr_in12_min.dev_attr.attr, | 1520 | &sensor_dev_attr_in12_min.dev_attr.attr, |
| 1521 | &sensor_dev_attr_in12_alarm.dev_attr.attr, | ||
| 1483 | &sensor_dev_attr_in13_input.dev_attr.attr, | 1522 | &sensor_dev_attr_in13_input.dev_attr.attr, |
| 1484 | &sensor_dev_attr_in13_max.dev_attr.attr, | 1523 | &sensor_dev_attr_in13_max.dev_attr.attr, |
| 1485 | &sensor_dev_attr_in13_min.dev_attr.attr, | 1524 | &sensor_dev_attr_in13_min.dev_attr.attr, |
| 1525 | &sensor_dev_attr_in13_alarm.dev_attr.attr, | ||
| 1486 | &sensor_dev_attr_in14_input.dev_attr.attr, | 1526 | &sensor_dev_attr_in14_input.dev_attr.attr, |
| 1487 | &sensor_dev_attr_in14_max.dev_attr.attr, | 1527 | &sensor_dev_attr_in14_max.dev_attr.attr, |
| 1488 | &sensor_dev_attr_in14_min.dev_attr.attr, | 1528 | &sensor_dev_attr_in14_min.dev_attr.attr, |
| 1529 | &sensor_dev_attr_in14_alarm.dev_attr.attr, | ||
| 1489 | &sensor_dev_attr_in15_input.dev_attr.attr, | 1530 | &sensor_dev_attr_in15_input.dev_attr.attr, |
| 1490 | &sensor_dev_attr_in15_max.dev_attr.attr, | 1531 | &sensor_dev_attr_in15_max.dev_attr.attr, |
| 1491 | &sensor_dev_attr_in15_min.dev_attr.attr, | 1532 | &sensor_dev_attr_in15_min.dev_attr.attr, |
| 1533 | &sensor_dev_attr_in15_alarm.dev_attr.attr, | ||
| 1492 | &sensor_dev_attr_in16_input.dev_attr.attr, | 1534 | &sensor_dev_attr_in16_input.dev_attr.attr, |
| 1493 | &sensor_dev_attr_in16_max.dev_attr.attr, | 1535 | &sensor_dev_attr_in16_max.dev_attr.attr, |
| 1494 | &sensor_dev_attr_in16_min.dev_attr.attr, | 1536 | &sensor_dev_attr_in16_min.dev_attr.attr, |
| 1537 | &sensor_dev_attr_in16_alarm.dev_attr.attr, | ||
| 1495 | &sensor_dev_attr_fan1_input.dev_attr.attr, | 1538 | &sensor_dev_attr_fan1_input.dev_attr.attr, |
| 1496 | &sensor_dev_attr_fan1_div.dev_attr.attr, | 1539 | &sensor_dev_attr_fan1_div.dev_attr.attr, |
| 1497 | &sensor_dev_attr_fan1_min.dev_attr.attr, | 1540 | &sensor_dev_attr_fan1_min.dev_attr.attr, |
| 1541 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 1498 | &sensor_dev_attr_fan2_input.dev_attr.attr, | 1542 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 1499 | &sensor_dev_attr_fan2_div.dev_attr.attr, | 1543 | &sensor_dev_attr_fan2_div.dev_attr.attr, |
| 1500 | &sensor_dev_attr_fan2_min.dev_attr.attr, | 1544 | &sensor_dev_attr_fan2_min.dev_attr.attr, |
| 1545 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | ||
| 1501 | &sensor_dev_attr_fan3_input.dev_attr.attr, | 1546 | &sensor_dev_attr_fan3_input.dev_attr.attr, |
| 1502 | &sensor_dev_attr_fan3_div.dev_attr.attr, | 1547 | &sensor_dev_attr_fan3_div.dev_attr.attr, |
| 1503 | &sensor_dev_attr_fan3_min.dev_attr.attr, | 1548 | &sensor_dev_attr_fan3_min.dev_attr.attr, |
| 1549 | &sensor_dev_attr_fan3_alarm.dev_attr.attr, | ||
| 1504 | &sensor_dev_attr_fan4_input.dev_attr.attr, | 1550 | &sensor_dev_attr_fan4_input.dev_attr.attr, |
| 1505 | &sensor_dev_attr_fan4_div.dev_attr.attr, | 1551 | &sensor_dev_attr_fan4_div.dev_attr.attr, |
| 1506 | &sensor_dev_attr_fan4_min.dev_attr.attr, | 1552 | &sensor_dev_attr_fan4_min.dev_attr.attr, |
| 1553 | &sensor_dev_attr_fan4_alarm.dev_attr.attr, | ||
| 1507 | &sensor_dev_attr_fan5_input.dev_attr.attr, | 1554 | &sensor_dev_attr_fan5_input.dev_attr.attr, |
| 1508 | &sensor_dev_attr_fan5_div.dev_attr.attr, | 1555 | &sensor_dev_attr_fan5_div.dev_attr.attr, |
| 1509 | &sensor_dev_attr_fan5_min.dev_attr.attr, | 1556 | &sensor_dev_attr_fan5_min.dev_attr.attr, |
| 1557 | &sensor_dev_attr_fan5_alarm.dev_attr.attr, | ||
| 1510 | &sensor_dev_attr_fan6_input.dev_attr.attr, | 1558 | &sensor_dev_attr_fan6_input.dev_attr.attr, |
| 1511 | &sensor_dev_attr_fan6_div.dev_attr.attr, | 1559 | &sensor_dev_attr_fan6_div.dev_attr.attr, |
| 1512 | &sensor_dev_attr_fan6_min.dev_attr.attr, | 1560 | &sensor_dev_attr_fan6_min.dev_attr.attr, |
| 1561 | &sensor_dev_attr_fan6_alarm.dev_attr.attr, | ||
| 1513 | &sensor_dev_attr_fan7_input.dev_attr.attr, | 1562 | &sensor_dev_attr_fan7_input.dev_attr.attr, |
| 1514 | &sensor_dev_attr_fan7_div.dev_attr.attr, | 1563 | &sensor_dev_attr_fan7_div.dev_attr.attr, |
| 1515 | &sensor_dev_attr_fan7_min.dev_attr.attr, | 1564 | &sensor_dev_attr_fan7_min.dev_attr.attr, |
| 1565 | &sensor_dev_attr_fan7_alarm.dev_attr.attr, | ||
| 1516 | &sensor_dev_attr_fan8_input.dev_attr.attr, | 1566 | &sensor_dev_attr_fan8_input.dev_attr.attr, |
| 1517 | &sensor_dev_attr_fan8_div.dev_attr.attr, | 1567 | &sensor_dev_attr_fan8_div.dev_attr.attr, |
| 1518 | &sensor_dev_attr_fan8_min.dev_attr.attr, | 1568 | &sensor_dev_attr_fan8_min.dev_attr.attr, |
| 1569 | &sensor_dev_attr_fan8_alarm.dev_attr.attr, | ||
| 1519 | &sensor_dev_attr_temp1_input.dev_attr.attr, | 1570 | &sensor_dev_attr_temp1_input.dev_attr.attr, |
| 1520 | &sensor_dev_attr_temp1_max.dev_attr.attr, | 1571 | &sensor_dev_attr_temp1_max.dev_attr.attr, |
| 1521 | &sensor_dev_attr_temp1_min.dev_attr.attr, | 1572 | &sensor_dev_attr_temp1_min.dev_attr.attr, |
| 1573 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 1522 | &sensor_dev_attr_temp2_input.dev_attr.attr, | 1574 | &sensor_dev_attr_temp2_input.dev_attr.attr, |
| 1523 | &sensor_dev_attr_temp2_max.dev_attr.attr, | 1575 | &sensor_dev_attr_temp2_max.dev_attr.attr, |
| 1524 | &sensor_dev_attr_temp2_min.dev_attr.attr, | 1576 | &sensor_dev_attr_temp2_min.dev_attr.attr, |
| 1525 | &sensor_dev_attr_temp3_input.dev_attr.attr, | 1577 | &sensor_dev_attr_temp2_alarm.dev_attr.attr, |
| 1526 | &sensor_dev_attr_temp3_max.dev_attr.attr, | ||
| 1527 | &sensor_dev_attr_temp3_min.dev_attr.attr, | ||
| 1528 | &sensor_dev_attr_temp1_offset.dev_attr.attr, | 1578 | &sensor_dev_attr_temp1_offset.dev_attr.attr, |
| 1529 | &sensor_dev_attr_temp2_offset.dev_attr.attr, | 1579 | &sensor_dev_attr_temp2_offset.dev_attr.attr, |
| 1530 | &sensor_dev_attr_temp3_offset.dev_attr.attr, | ||
| 1531 | &sensor_dev_attr_temp1_auto_point1_temp.dev_attr.attr, | 1580 | &sensor_dev_attr_temp1_auto_point1_temp.dev_attr.attr, |
| 1532 | &sensor_dev_attr_temp2_auto_point1_temp.dev_attr.attr, | 1581 | &sensor_dev_attr_temp2_auto_point1_temp.dev_attr.attr, |
| 1533 | &sensor_dev_attr_temp3_auto_point1_temp.dev_attr.attr, | ||
| 1534 | &sensor_dev_attr_temp1_auto_point1_temp_hyst.dev_attr.attr, | 1582 | &sensor_dev_attr_temp1_auto_point1_temp_hyst.dev_attr.attr, |
| 1535 | &sensor_dev_attr_temp2_auto_point1_temp_hyst.dev_attr.attr, | 1583 | &sensor_dev_attr_temp2_auto_point1_temp_hyst.dev_attr.attr, |
| 1536 | &sensor_dev_attr_temp3_auto_point1_temp_hyst.dev_attr.attr, | ||
| 1537 | &sensor_dev_attr_temp1_auto_point2_temp.dev_attr.attr, | 1584 | &sensor_dev_attr_temp1_auto_point2_temp.dev_attr.attr, |
| 1538 | &sensor_dev_attr_temp2_auto_point2_temp.dev_attr.attr, | 1585 | &sensor_dev_attr_temp2_auto_point2_temp.dev_attr.attr, |
| 1539 | &sensor_dev_attr_temp3_auto_point2_temp.dev_attr.attr, | ||
| 1540 | &sensor_dev_attr_temp1_crit.dev_attr.attr, | 1586 | &sensor_dev_attr_temp1_crit.dev_attr.attr, |
| 1541 | &sensor_dev_attr_temp2_crit.dev_attr.attr, | 1587 | &sensor_dev_attr_temp2_crit.dev_attr.attr, |
| 1542 | &sensor_dev_attr_temp3_crit.dev_attr.attr, | ||
| 1543 | &dev_attr_temp1_crit_enable.attr, | 1588 | &dev_attr_temp1_crit_enable.attr, |
| 1544 | &dev_attr_temp2_crit_enable.attr, | 1589 | &dev_attr_temp2_crit_enable.attr, |
| 1545 | &dev_attr_temp3_crit_enable.attr, | ||
| 1546 | &dev_attr_cpu0_vid.attr, | 1590 | &dev_attr_cpu0_vid.attr, |
| 1547 | &dev_attr_vrm.attr, | 1591 | &dev_attr_vrm.attr, |
| 1548 | &dev_attr_alarms.attr, | 1592 | &dev_attr_alarms.attr, |
| @@ -1557,10 +1601,8 @@ static struct attribute *adm1026_attributes[] = { | |||
| 1557 | &dev_attr_pwm3_enable.attr, | 1601 | &dev_attr_pwm3_enable.attr, |
| 1558 | &dev_attr_temp1_auto_point1_pwm.attr, | 1602 | &dev_attr_temp1_auto_point1_pwm.attr, |
| 1559 | &dev_attr_temp2_auto_point1_pwm.attr, | 1603 | &dev_attr_temp2_auto_point1_pwm.attr, |
| 1560 | &dev_attr_temp3_auto_point1_pwm.attr, | ||
| 1561 | &dev_attr_temp1_auto_point2_pwm.attr, | 1604 | &dev_attr_temp1_auto_point2_pwm.attr, |
| 1562 | &dev_attr_temp2_auto_point2_pwm.attr, | 1605 | &dev_attr_temp2_auto_point2_pwm.attr, |
| 1563 | &dev_attr_temp3_auto_point2_pwm.attr, | ||
| 1564 | &dev_attr_analog_out.attr, | 1606 | &dev_attr_analog_out.attr, |
| 1565 | NULL | 1607 | NULL |
| 1566 | }; | 1608 | }; |
| @@ -1569,11 +1611,45 @@ static const struct attribute_group adm1026_group = { | |||
| 1569 | .attrs = adm1026_attributes, | 1611 | .attrs = adm1026_attributes, |
| 1570 | }; | 1612 | }; |
| 1571 | 1613 | ||
| 1614 | static struct attribute *adm1026_attributes_temp3[] = { | ||
| 1615 | &sensor_dev_attr_temp3_input.dev_attr.attr, | ||
| 1616 | &sensor_dev_attr_temp3_max.dev_attr.attr, | ||
| 1617 | &sensor_dev_attr_temp3_min.dev_attr.attr, | ||
| 1618 | &sensor_dev_attr_temp3_alarm.dev_attr.attr, | ||
| 1619 | &sensor_dev_attr_temp3_offset.dev_attr.attr, | ||
| 1620 | &sensor_dev_attr_temp3_auto_point1_temp.dev_attr.attr, | ||
| 1621 | &sensor_dev_attr_temp3_auto_point1_temp_hyst.dev_attr.attr, | ||
| 1622 | &sensor_dev_attr_temp3_auto_point2_temp.dev_attr.attr, | ||
| 1623 | &sensor_dev_attr_temp3_crit.dev_attr.attr, | ||
| 1624 | &dev_attr_temp3_crit_enable.attr, | ||
| 1625 | &dev_attr_temp3_auto_point1_pwm.attr, | ||
| 1626 | &dev_attr_temp3_auto_point2_pwm.attr, | ||
| 1627 | }; | ||
| 1628 | |||
| 1629 | static const struct attribute_group adm1026_group_temp3 = { | ||
| 1630 | .attrs = adm1026_attributes_temp3, | ||
| 1631 | }; | ||
| 1632 | |||
| 1633 | static struct attribute *adm1026_attributes_in8_9[] = { | ||
| 1634 | &sensor_dev_attr_in8_input.dev_attr.attr, | ||
| 1635 | &sensor_dev_attr_in8_max.dev_attr.attr, | ||
| 1636 | &sensor_dev_attr_in8_min.dev_attr.attr, | ||
| 1637 | &sensor_dev_attr_in8_alarm.dev_attr.attr, | ||
| 1638 | &sensor_dev_attr_in9_input.dev_attr.attr, | ||
| 1639 | &sensor_dev_attr_in9_max.dev_attr.attr, | ||
| 1640 | &sensor_dev_attr_in9_min.dev_attr.attr, | ||
| 1641 | &sensor_dev_attr_in9_alarm.dev_attr.attr, | ||
| 1642 | }; | ||
| 1643 | |||
| 1644 | static const struct attribute_group adm1026_group_in8_9 = { | ||
| 1645 | .attrs = adm1026_attributes_in8_9, | ||
| 1646 | }; | ||
| 1647 | |||
| 1572 | static int adm1026_detect(struct i2c_adapter *adapter, int address, | 1648 | static int adm1026_detect(struct i2c_adapter *adapter, int address, |
| 1573 | int kind) | 1649 | int kind) |
| 1574 | { | 1650 | { |
| 1575 | int company, verstep; | 1651 | int company, verstep; |
| 1576 | struct i2c_client *new_client; | 1652 | struct i2c_client *client; |
| 1577 | struct adm1026_data *data; | 1653 | struct adm1026_data *data; |
| 1578 | int err = 0; | 1654 | int err = 0; |
| 1579 | const char *type_name = ""; | 1655 | const char *type_name = ""; |
| @@ -1592,26 +1668,25 @@ static int adm1026_detect(struct i2c_adapter *adapter, int address, | |||
| 1592 | goto exit; | 1668 | goto exit; |
| 1593 | } | 1669 | } |
| 1594 | 1670 | ||
| 1595 | new_client = &data->client; | 1671 | client = &data->client; |
| 1596 | i2c_set_clientdata(new_client, data); | 1672 | i2c_set_clientdata(client, data); |
| 1597 | new_client->addr = address; | 1673 | client->addr = address; |
| 1598 | new_client->adapter = adapter; | 1674 | client->adapter = adapter; |
| 1599 | new_client->driver = &adm1026_driver; | 1675 | client->driver = &adm1026_driver; |
| 1600 | new_client->flags = 0; | ||
| 1601 | 1676 | ||
| 1602 | /* Now, we do the remaining detection. */ | 1677 | /* Now, we do the remaining detection. */ |
| 1603 | 1678 | ||
| 1604 | company = adm1026_read_value(new_client, ADM1026_REG_COMPANY); | 1679 | company = adm1026_read_value(client, ADM1026_REG_COMPANY); |
| 1605 | verstep = adm1026_read_value(new_client, ADM1026_REG_VERSTEP); | 1680 | verstep = adm1026_read_value(client, ADM1026_REG_VERSTEP); |
| 1606 | 1681 | ||
| 1607 | dev_dbg(&new_client->dev, "Detecting device at %d,0x%02x with" | 1682 | dev_dbg(&client->dev, "Detecting device at %d,0x%02x with" |
| 1608 | " COMPANY: 0x%02x and VERSTEP: 0x%02x\n", | 1683 | " COMPANY: 0x%02x and VERSTEP: 0x%02x\n", |
| 1609 | i2c_adapter_id(new_client->adapter), new_client->addr, | 1684 | i2c_adapter_id(client->adapter), client->addr, |
| 1610 | company, verstep); | 1685 | company, verstep); |
| 1611 | 1686 | ||
| 1612 | /* If auto-detecting, Determine the chip type. */ | 1687 | /* If auto-detecting, Determine the chip type. */ |
| 1613 | if (kind <= 0) { | 1688 | if (kind <= 0) { |
| 1614 | dev_dbg(&new_client->dev, "Autodetecting device at %d,0x%02x " | 1689 | dev_dbg(&client->dev, "Autodetecting device at %d,0x%02x " |
| 1615 | "...\n", i2c_adapter_id(adapter), address); | 1690 | "...\n", i2c_adapter_id(adapter), address); |
| 1616 | if (company == ADM1026_COMPANY_ANALOG_DEV | 1691 | if (company == ADM1026_COMPANY_ANALOG_DEV |
| 1617 | && verstep == ADM1026_VERSTEP_ADM1026) { | 1692 | && verstep == ADM1026_VERSTEP_ADM1026) { |
| @@ -1627,16 +1702,15 @@ static int adm1026_detect(struct i2c_adapter *adapter, int address, | |||
| 1627 | verstep); | 1702 | verstep); |
| 1628 | kind = any_chip; | 1703 | kind = any_chip; |
| 1629 | } else { | 1704 | } else { |
| 1630 | dev_dbg(&new_client->dev, ": Autodetection " | 1705 | dev_dbg(&client->dev, ": Autodetection " |
| 1631 | "failed\n"); | 1706 | "failed\n"); |
| 1632 | /* Not an ADM1026 ... */ | 1707 | /* Not an ADM1026 ... */ |
| 1633 | if (kind == 0) { /* User used force=x,y */ | 1708 | if (kind == 0) { /* User used force=x,y */ |
| 1634 | dev_err(&adapter->dev, "Generic ADM1026 not " | 1709 | dev_err(&adapter->dev, "Generic ADM1026 not " |
| 1635 | "found at %d,0x%02x. Try " | 1710 | "found at %d,0x%02x. Try " |
| 1636 | "force_adm1026.\n", | 1711 | "force_adm1026.\n", |
| 1637 | i2c_adapter_id(adapter), address); | 1712 | i2c_adapter_id(adapter), address); |
| 1638 | } | 1713 | } |
| 1639 | err = 0; | ||
| 1640 | goto exitfree; | 1714 | goto exitfree; |
| 1641 | } | 1715 | } |
| 1642 | } | 1716 | } |
| @@ -1655,28 +1729,34 @@ static int adm1026_detect(struct i2c_adapter *adapter, int address, | |||
| 1655 | err = -EFAULT; | 1729 | err = -EFAULT; |
| 1656 | goto exitfree; | 1730 | goto exitfree; |
| 1657 | } | 1731 | } |
| 1658 | strlcpy(new_client->name, type_name, I2C_NAME_SIZE); | 1732 | strlcpy(client->name, type_name, I2C_NAME_SIZE); |
| 1659 | 1733 | ||
| 1660 | /* Fill in the remaining client fields */ | 1734 | /* Fill in the remaining client fields */ |
| 1661 | data->type = kind; | ||
| 1662 | data->valid = 0; | ||
| 1663 | mutex_init(&data->update_lock); | 1735 | mutex_init(&data->update_lock); |
| 1664 | 1736 | ||
| 1665 | /* Tell the I2C layer a new client has arrived */ | 1737 | /* Tell the I2C layer a new client has arrived */ |
| 1666 | if ((err = i2c_attach_client(new_client))) | 1738 | if ((err = i2c_attach_client(client))) |
| 1667 | goto exitfree; | 1739 | goto exitfree; |
| 1668 | 1740 | ||
| 1669 | /* Set the VRM version */ | 1741 | /* Set the VRM version */ |
| 1670 | data->vrm = vid_which_vrm(); | 1742 | data->vrm = vid_which_vrm(); |
| 1671 | 1743 | ||
| 1672 | /* Initialize the ADM1026 chip */ | 1744 | /* Initialize the ADM1026 chip */ |
| 1673 | adm1026_init_client(new_client); | 1745 | adm1026_init_client(client); |
| 1674 | 1746 | ||
| 1675 | /* Register sysfs hooks */ | 1747 | /* Register sysfs hooks */ |
| 1676 | if ((err = sysfs_create_group(&new_client->dev.kobj, &adm1026_group))) | 1748 | if ((err = sysfs_create_group(&client->dev.kobj, &adm1026_group))) |
| 1677 | goto exitdetach; | 1749 | goto exitdetach; |
| 1750 | if (data->config1 & CFG1_AIN8_9) | ||
| 1751 | err = sysfs_create_group(&client->dev.kobj, | ||
| 1752 | &adm1026_group_in8_9); | ||
| 1753 | else | ||
| 1754 | err = sysfs_create_group(&client->dev.kobj, | ||
| 1755 | &adm1026_group_temp3); | ||
| 1756 | if (err) | ||
| 1757 | goto exitremove; | ||
| 1678 | 1758 | ||
| 1679 | data->hwmon_dev = hwmon_device_register(&new_client->dev); | 1759 | data->hwmon_dev = hwmon_device_register(&client->dev); |
| 1680 | if (IS_ERR(data->hwmon_dev)) { | 1760 | if (IS_ERR(data->hwmon_dev)) { |
| 1681 | err = PTR_ERR(data->hwmon_dev); | 1761 | err = PTR_ERR(data->hwmon_dev); |
| 1682 | goto exitremove; | 1762 | goto exitremove; |
| @@ -1686,9 +1766,13 @@ static int adm1026_detect(struct i2c_adapter *adapter, int address, | |||
| 1686 | 1766 | ||
| 1687 | /* Error out and cleanup code */ | 1767 | /* Error out and cleanup code */ |
| 1688 | exitremove: | 1768 | exitremove: |
| 1689 | sysfs_remove_group(&new_client->dev.kobj, &adm1026_group); | 1769 | sysfs_remove_group(&client->dev.kobj, &adm1026_group); |
| 1770 | if (data->config1 & CFG1_AIN8_9) | ||
| 1771 | sysfs_remove_group(&client->dev.kobj, &adm1026_group_in8_9); | ||
| 1772 | else | ||
| 1773 | sysfs_remove_group(&client->dev.kobj, &adm1026_group_temp3); | ||
| 1690 | exitdetach: | 1774 | exitdetach: |
| 1691 | i2c_detach_client(new_client); | 1775 | i2c_detach_client(client); |
| 1692 | exitfree: | 1776 | exitfree: |
| 1693 | kfree(data); | 1777 | kfree(data); |
| 1694 | exit: | 1778 | exit: |
| @@ -1700,6 +1784,10 @@ static int adm1026_detach_client(struct i2c_client *client) | |||
| 1700 | struct adm1026_data *data = i2c_get_clientdata(client); | 1784 | struct adm1026_data *data = i2c_get_clientdata(client); |
| 1701 | hwmon_device_unregister(data->hwmon_dev); | 1785 | hwmon_device_unregister(data->hwmon_dev); |
| 1702 | sysfs_remove_group(&client->dev.kobj, &adm1026_group); | 1786 | sysfs_remove_group(&client->dev.kobj, &adm1026_group); |
| 1787 | if (data->config1 & CFG1_AIN8_9) | ||
| 1788 | sysfs_remove_group(&client->dev.kobj, &adm1026_group_in8_9); | ||
| 1789 | else | ||
| 1790 | sysfs_remove_group(&client->dev.kobj, &adm1026_group_temp3); | ||
| 1703 | i2c_detach_client(client); | 1791 | i2c_detach_client(client); |
| 1704 | kfree(data); | 1792 | kfree(data); |
| 1705 | return 0; | 1793 | return 0; |
| @@ -1710,14 +1798,14 @@ static int __init sm_adm1026_init(void) | |||
| 1710 | return i2c_add_driver(&adm1026_driver); | 1798 | return i2c_add_driver(&adm1026_driver); |
| 1711 | } | 1799 | } |
| 1712 | 1800 | ||
| 1713 | static void __exit sm_adm1026_exit(void) | 1801 | static void __exit sm_adm1026_exit(void) |
| 1714 | { | 1802 | { |
| 1715 | i2c_del_driver(&adm1026_driver); | 1803 | i2c_del_driver(&adm1026_driver); |
| 1716 | } | 1804 | } |
| 1717 | 1805 | ||
| 1718 | MODULE_LICENSE("GPL"); | 1806 | MODULE_LICENSE("GPL"); |
| 1719 | MODULE_AUTHOR("Philip Pokorny <ppokorny@penguincomputing.com>, " | 1807 | MODULE_AUTHOR("Philip Pokorny <ppokorny@penguincomputing.com>, " |
| 1720 | "Justin Thiessen <jthiessen@penguincomputing.com>"); | 1808 | "Justin Thiessen <jthiessen@penguincomputing.com>"); |
| 1721 | MODULE_DESCRIPTION("ADM1026 driver"); | 1809 | MODULE_DESCRIPTION("ADM1026 driver"); |
| 1722 | 1810 | ||
| 1723 | module_init(sm_adm1026_init); | 1811 | module_init(sm_adm1026_init); |
diff --git a/drivers/hwmon/adm1031.c b/drivers/hwmon/adm1031.c index 37cfc101da5e..5aaad3636c98 100644 --- a/drivers/hwmon/adm1031.c +++ b/drivers/hwmon/adm1031.c | |||
| @@ -5,7 +5,7 @@ | |||
| 5 | Supports adm1030 / adm1031 | 5 | Supports adm1030 / adm1031 |
| 6 | Copyright (C) 2004 Alexandre d'Alton <alex@alexdalton.org> | 6 | Copyright (C) 2004 Alexandre d'Alton <alex@alexdalton.org> |
| 7 | Reworked by Jean Delvare <khali@linux-fr.org> | 7 | Reworked by Jean Delvare <khali@linux-fr.org> |
| 8 | 8 | ||
| 9 | This program is free software; you can redistribute it and/or modify | 9 | This program is free software; you can redistribute it and/or modify |
| 10 | it under the terms of the GNU General Public License as published by | 10 | it under the terms of the GNU General Public License as published by |
| 11 | the Free Software Foundation; either version 2 of the License, or | 11 | the Free Software Foundation; either version 2 of the License, or |
| @@ -27,27 +27,28 @@ | |||
| 27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
| 28 | #include <linux/i2c.h> | 28 | #include <linux/i2c.h> |
| 29 | #include <linux/hwmon.h> | 29 | #include <linux/hwmon.h> |
| 30 | #include <linux/hwmon-sysfs.h> | ||
| 30 | #include <linux/err.h> | 31 | #include <linux/err.h> |
| 31 | #include <linux/mutex.h> | 32 | #include <linux/mutex.h> |
| 32 | 33 | ||
| 33 | /* Following macros takes channel parameter starting from 0 to 2 */ | 34 | /* Following macros takes channel parameter starting from 0 to 2 */ |
| 34 | #define ADM1031_REG_FAN_SPEED(nr) (0x08 + (nr)) | 35 | #define ADM1031_REG_FAN_SPEED(nr) (0x08 + (nr)) |
| 35 | #define ADM1031_REG_FAN_DIV(nr) (0x20 + (nr)) | 36 | #define ADM1031_REG_FAN_DIV(nr) (0x20 + (nr)) |
| 36 | #define ADM1031_REG_PWM (0x22) | 37 | #define ADM1031_REG_PWM (0x22) |
| 37 | #define ADM1031_REG_FAN_MIN(nr) (0x10 + (nr)) | 38 | #define ADM1031_REG_FAN_MIN(nr) (0x10 + (nr)) |
| 38 | 39 | ||
| 39 | #define ADM1031_REG_TEMP_MAX(nr) (0x14 + 4*(nr)) | 40 | #define ADM1031_REG_TEMP_MAX(nr) (0x14 + 4 * (nr)) |
| 40 | #define ADM1031_REG_TEMP_MIN(nr) (0x15 + 4*(nr)) | 41 | #define ADM1031_REG_TEMP_MIN(nr) (0x15 + 4 * (nr)) |
| 41 | #define ADM1031_REG_TEMP_CRIT(nr) (0x16 + 4*(nr)) | 42 | #define ADM1031_REG_TEMP_CRIT(nr) (0x16 + 4 * (nr)) |
| 42 | 43 | ||
| 43 | #define ADM1031_REG_TEMP(nr) (0xa + (nr)) | 44 | #define ADM1031_REG_TEMP(nr) (0x0a + (nr)) |
| 44 | #define ADM1031_REG_AUTO_TEMP(nr) (0x24 + (nr)) | 45 | #define ADM1031_REG_AUTO_TEMP(nr) (0x24 + (nr)) |
| 45 | 46 | ||
| 46 | #define ADM1031_REG_STATUS(nr) (0x2 + (nr)) | 47 | #define ADM1031_REG_STATUS(nr) (0x2 + (nr)) |
| 47 | 48 | ||
| 48 | #define ADM1031_REG_CONF1 0x0 | 49 | #define ADM1031_REG_CONF1 0x00 |
| 49 | #define ADM1031_REG_CONF2 0x1 | 50 | #define ADM1031_REG_CONF2 0x01 |
| 50 | #define ADM1031_REG_EXT_TEMP 0x6 | 51 | #define ADM1031_REG_EXT_TEMP 0x06 |
| 51 | 52 | ||
| 52 | #define ADM1031_CONF1_MONITOR_ENABLE 0x01 /* Monitoring enable */ | 53 | #define ADM1031_CONF1_MONITOR_ENABLE 0x01 /* Monitoring enable */ |
| 53 | #define ADM1031_CONF1_PWM_INVERT 0x08 /* PWM Invert */ | 54 | #define ADM1031_CONF1_PWM_INVERT 0x08 /* PWM Invert */ |
| @@ -78,7 +79,7 @@ struct adm1031_data { | |||
| 78 | /* The chan_select_table contains the possible configurations for | 79 | /* The chan_select_table contains the possible configurations for |
| 79 | * auto fan control. | 80 | * auto fan control. |
| 80 | */ | 81 | */ |
| 81 | auto_chan_table_t *chan_select_table; | 82 | const auto_chan_table_t *chan_select_table; |
| 82 | u16 alarm; | 83 | u16 alarm; |
| 83 | u8 conf1; | 84 | u8 conf1; |
| 84 | u8 conf2; | 85 | u8 conf2; |
| @@ -181,25 +182,25 @@ static int AUTO_TEMP_MAX_TO_REG(int val, int reg, int pwm) | |||
| 181 | #define GET_FAN_AUTO_BITFIELD(data, idx) \ | 182 | #define GET_FAN_AUTO_BITFIELD(data, idx) \ |
| 182 | (*(data)->chan_select_table)[FAN_CHAN_FROM_REG((data)->conf1)][idx%2] | 183 | (*(data)->chan_select_table)[FAN_CHAN_FROM_REG((data)->conf1)][idx%2] |
| 183 | 184 | ||
| 184 | /* The tables below contains the possible values for the auto fan | 185 | /* The tables below contains the possible values for the auto fan |
| 185 | * control bitfields. the index in the table is the register value. | 186 | * control bitfields. the index in the table is the register value. |
| 186 | * MSb is the auto fan control enable bit, so the four first entries | 187 | * MSb is the auto fan control enable bit, so the four first entries |
| 187 | * in the table disables auto fan control when both bitfields are zero. | 188 | * in the table disables auto fan control when both bitfields are zero. |
| 188 | */ | 189 | */ |
| 189 | static auto_chan_table_t auto_channel_select_table_adm1031 = { | 190 | static const auto_chan_table_t auto_channel_select_table_adm1031 = { |
| 190 | {0, 0}, {0, 0}, {0, 0}, {0, 0}, | 191 | { 0, 0 }, { 0, 0 }, { 0, 0 }, { 0, 0 }, |
| 191 | {2 /*0b010 */ , 4 /*0b100 */ }, | 192 | { 2 /* 0b010 */ , 4 /* 0b100 */ }, |
| 192 | {2 /*0b010 */ , 2 /*0b010 */ }, | 193 | { 2 /* 0b010 */ , 2 /* 0b010 */ }, |
| 193 | {4 /*0b100 */ , 4 /*0b100 */ }, | 194 | { 4 /* 0b100 */ , 4 /* 0b100 */ }, |
| 194 | {7 /*0b111 */ , 7 /*0b111 */ }, | 195 | { 7 /* 0b111 */ , 7 /* 0b111 */ }, |
| 195 | }; | 196 | }; |
| 196 | 197 | ||
| 197 | static auto_chan_table_t auto_channel_select_table_adm1030 = { | 198 | static const auto_chan_table_t auto_channel_select_table_adm1030 = { |
| 198 | {0, 0}, {0, 0}, {0, 0}, {0, 0}, | 199 | { 0, 0 }, { 0, 0 }, { 0, 0 }, { 0, 0 }, |
| 199 | {2 /*0b10 */ , 0}, | 200 | { 2 /* 0b10 */ , 0 }, |
| 200 | {0xff /*invalid */ , 0}, | 201 | { 0xff /* invalid */ , 0 }, |
| 201 | {0xff /*invalid */ , 0}, | 202 | { 0xff /* invalid */ , 0 }, |
| 202 | {3 /*0b11 */ , 0}, | 203 | { 3 /* 0b11 */ , 0 }, |
| 203 | }; | 204 | }; |
| 204 | 205 | ||
| 205 | /* That function checks if a bitfield is valid and returns the other bitfield | 206 | /* That function checks if a bitfield is valid and returns the other bitfield |
| @@ -228,8 +229,8 @@ get_fan_auto_nearest(struct adm1031_data *data, | |||
| 228 | break; | 229 | break; |
| 229 | } else if (val == (*data->chan_select_table)[i][chan] && | 230 | } else if (val == (*data->chan_select_table)[i][chan] && |
| 230 | first_match == -1) { | 231 | first_match == -1) { |
| 231 | /* Save the first match in case of an exact match has not been | 232 | /* Save the first match in case of an exact match has |
| 232 | * found | 233 | * not been found |
| 233 | */ | 234 | */ |
| 234 | first_match = i; | 235 | first_match = i; |
| 235 | } | 236 | } |
| @@ -245,17 +246,21 @@ get_fan_auto_nearest(struct adm1031_data *data, | |||
| 245 | return 0; | 246 | return 0; |
| 246 | } | 247 | } |
| 247 | 248 | ||
| 248 | static ssize_t show_fan_auto_channel(struct device *dev, char *buf, int nr) | 249 | static ssize_t show_fan_auto_channel(struct device *dev, |
| 250 | struct device_attribute *attr, char *buf) | ||
| 249 | { | 251 | { |
| 252 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 250 | struct adm1031_data *data = adm1031_update_device(dev); | 253 | struct adm1031_data *data = adm1031_update_device(dev); |
| 251 | return sprintf(buf, "%d\n", GET_FAN_AUTO_BITFIELD(data, nr)); | 254 | return sprintf(buf, "%d\n", GET_FAN_AUTO_BITFIELD(data, nr)); |
| 252 | } | 255 | } |
| 253 | 256 | ||
| 254 | static ssize_t | 257 | static ssize_t |
| 255 | set_fan_auto_channel(struct device *dev, const char *buf, size_t count, int nr) | 258 | set_fan_auto_channel(struct device *dev, struct device_attribute *attr, |
| 259 | const char *buf, size_t count) | ||
| 256 | { | 260 | { |
| 257 | struct i2c_client *client = to_i2c_client(dev); | 261 | struct i2c_client *client = to_i2c_client(dev); |
| 258 | struct adm1031_data *data = i2c_get_clientdata(client); | 262 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 263 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 259 | int val = simple_strtol(buf, NULL, 10); | 264 | int val = simple_strtol(buf, NULL, 10); |
| 260 | u8 reg; | 265 | u8 reg; |
| 261 | int ret; | 266 | int ret; |
| @@ -264,16 +269,17 @@ set_fan_auto_channel(struct device *dev, const char *buf, size_t count, int nr) | |||
| 264 | old_fan_mode = data->conf1; | 269 | old_fan_mode = data->conf1; |
| 265 | 270 | ||
| 266 | mutex_lock(&data->update_lock); | 271 | mutex_lock(&data->update_lock); |
| 267 | 272 | ||
| 268 | if ((ret = get_fan_auto_nearest(data, nr, val, data->conf1, ®))) { | 273 | if ((ret = get_fan_auto_nearest(data, nr, val, data->conf1, ®))) { |
| 269 | mutex_unlock(&data->update_lock); | 274 | mutex_unlock(&data->update_lock); |
| 270 | return ret; | 275 | return ret; |
| 271 | } | 276 | } |
| 272 | if (((data->conf1 = FAN_CHAN_TO_REG(reg, data->conf1)) & ADM1031_CONF1_AUTO_MODE) ^ | 277 | data->conf1 = FAN_CHAN_TO_REG(reg, data->conf1); |
| 278 | if ((data->conf1 & ADM1031_CONF1_AUTO_MODE) ^ | ||
| 273 | (old_fan_mode & ADM1031_CONF1_AUTO_MODE)) { | 279 | (old_fan_mode & ADM1031_CONF1_AUTO_MODE)) { |
| 274 | if (data->conf1 & ADM1031_CONF1_AUTO_MODE){ | 280 | if (data->conf1 & ADM1031_CONF1_AUTO_MODE){ |
| 275 | /* Switch to Auto Fan Mode | 281 | /* Switch to Auto Fan Mode |
| 276 | * Save PWM registers | 282 | * Save PWM registers |
| 277 | * Set PWM registers to 33% Both */ | 283 | * Set PWM registers to 33% Both */ |
| 278 | data->old_pwm[0] = data->pwm[0]; | 284 | data->old_pwm[0] = data->pwm[0]; |
| 279 | data->old_pwm[1] = data->pwm[1]; | 285 | data->old_pwm[1] = data->pwm[1]; |
| @@ -283,7 +289,7 @@ set_fan_auto_channel(struct device *dev, const char *buf, size_t count, int nr) | |||
| 283 | data->pwm[0] = data->old_pwm[0]; | 289 | data->pwm[0] = data->old_pwm[0]; |
| 284 | data->pwm[1] = data->old_pwm[1]; | 290 | data->pwm[1] = data->old_pwm[1]; |
| 285 | /* Restore PWM registers */ | 291 | /* Restore PWM registers */ |
| 286 | adm1031_write_value(client, ADM1031_REG_PWM, | 292 | adm1031_write_value(client, ADM1031_REG_PWM, |
| 287 | data->pwm[0] | (data->pwm[1] << 4)); | 293 | data->pwm[0] | (data->pwm[1] << 4)); |
| 288 | } | 294 | } |
| 289 | } | 295 | } |
| @@ -293,41 +299,35 @@ set_fan_auto_channel(struct device *dev, const char *buf, size_t count, int nr) | |||
| 293 | return count; | 299 | return count; |
| 294 | } | 300 | } |
| 295 | 301 | ||
| 296 | #define fan_auto_channel_offset(offset) \ | 302 | static SENSOR_DEVICE_ATTR(auto_fan1_channel, S_IRUGO | S_IWUSR, |
| 297 | static ssize_t show_fan_auto_channel_##offset (struct device *dev, struct device_attribute *attr, char *buf) \ | 303 | show_fan_auto_channel, set_fan_auto_channel, 0); |
| 298 | { \ | 304 | static SENSOR_DEVICE_ATTR(auto_fan2_channel, S_IRUGO | S_IWUSR, |
| 299 | return show_fan_auto_channel(dev, buf, offset - 1); \ | 305 | show_fan_auto_channel, set_fan_auto_channel, 1); |
| 300 | } \ | ||
| 301 | static ssize_t set_fan_auto_channel_##offset (struct device *dev, struct device_attribute *attr, \ | ||
| 302 | const char *buf, size_t count) \ | ||
| 303 | { \ | ||
| 304 | return set_fan_auto_channel(dev, buf, count, offset - 1); \ | ||
| 305 | } \ | ||
| 306 | static DEVICE_ATTR(auto_fan##offset##_channel, S_IRUGO | S_IWUSR, \ | ||
| 307 | show_fan_auto_channel_##offset, \ | ||
| 308 | set_fan_auto_channel_##offset) | ||
| 309 | |||
| 310 | fan_auto_channel_offset(1); | ||
| 311 | fan_auto_channel_offset(2); | ||
| 312 | 306 | ||
| 313 | /* Auto Temps */ | 307 | /* Auto Temps */ |
| 314 | static ssize_t show_auto_temp_off(struct device *dev, char *buf, int nr) | 308 | static ssize_t show_auto_temp_off(struct device *dev, |
| 309 | struct device_attribute *attr, char *buf) | ||
| 315 | { | 310 | { |
| 311 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 316 | struct adm1031_data *data = adm1031_update_device(dev); | 312 | struct adm1031_data *data = adm1031_update_device(dev); |
| 317 | return sprintf(buf, "%d\n", | 313 | return sprintf(buf, "%d\n", |
| 318 | AUTO_TEMP_OFF_FROM_REG(data->auto_temp[nr])); | 314 | AUTO_TEMP_OFF_FROM_REG(data->auto_temp[nr])); |
| 319 | } | 315 | } |
| 320 | static ssize_t show_auto_temp_min(struct device *dev, char *buf, int nr) | 316 | static ssize_t show_auto_temp_min(struct device *dev, |
| 317 | struct device_attribute *attr, char *buf) | ||
| 321 | { | 318 | { |
| 319 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 322 | struct adm1031_data *data = adm1031_update_device(dev); | 320 | struct adm1031_data *data = adm1031_update_device(dev); |
| 323 | return sprintf(buf, "%d\n", | 321 | return sprintf(buf, "%d\n", |
| 324 | AUTO_TEMP_MIN_FROM_REG(data->auto_temp[nr])); | 322 | AUTO_TEMP_MIN_FROM_REG(data->auto_temp[nr])); |
| 325 | } | 323 | } |
| 326 | static ssize_t | 324 | static ssize_t |
| 327 | set_auto_temp_min(struct device *dev, const char *buf, size_t count, int nr) | 325 | set_auto_temp_min(struct device *dev, struct device_attribute *attr, |
| 326 | const char *buf, size_t count) | ||
| 328 | { | 327 | { |
| 329 | struct i2c_client *client = to_i2c_client(dev); | 328 | struct i2c_client *client = to_i2c_client(dev); |
| 330 | struct adm1031_data *data = i2c_get_clientdata(client); | 329 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 330 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 331 | int val = simple_strtol(buf, NULL, 10); | 331 | int val = simple_strtol(buf, NULL, 10); |
| 332 | 332 | ||
| 333 | mutex_lock(&data->update_lock); | 333 | mutex_lock(&data->update_lock); |
| @@ -337,17 +337,21 @@ set_auto_temp_min(struct device *dev, const char *buf, size_t count, int nr) | |||
| 337 | mutex_unlock(&data->update_lock); | 337 | mutex_unlock(&data->update_lock); |
| 338 | return count; | 338 | return count; |
| 339 | } | 339 | } |
| 340 | static ssize_t show_auto_temp_max(struct device *dev, char *buf, int nr) | 340 | static ssize_t show_auto_temp_max(struct device *dev, |
| 341 | struct device_attribute *attr, char *buf) | ||
| 341 | { | 342 | { |
| 343 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 342 | struct adm1031_data *data = adm1031_update_device(dev); | 344 | struct adm1031_data *data = adm1031_update_device(dev); |
| 343 | return sprintf(buf, "%d\n", | 345 | return sprintf(buf, "%d\n", |
| 344 | AUTO_TEMP_MAX_FROM_REG(data->auto_temp[nr])); | 346 | AUTO_TEMP_MAX_FROM_REG(data->auto_temp[nr])); |
| 345 | } | 347 | } |
| 346 | static ssize_t | 348 | static ssize_t |
| 347 | set_auto_temp_max(struct device *dev, const char *buf, size_t count, int nr) | 349 | set_auto_temp_max(struct device *dev, struct device_attribute *attr, |
| 350 | const char *buf, size_t count) | ||
| 348 | { | 351 | { |
| 349 | struct i2c_client *client = to_i2c_client(dev); | 352 | struct i2c_client *client = to_i2c_client(dev); |
| 350 | struct adm1031_data *data = i2c_get_clientdata(client); | 353 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 354 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 351 | int val = simple_strtol(buf, NULL, 10); | 355 | int val = simple_strtol(buf, NULL, 10); |
| 352 | 356 | ||
| 353 | mutex_lock(&data->update_lock); | 357 | mutex_lock(&data->update_lock); |
| @@ -358,56 +362,37 @@ set_auto_temp_max(struct device *dev, const char *buf, size_t count, int nr) | |||
| 358 | return count; | 362 | return count; |
| 359 | } | 363 | } |
| 360 | 364 | ||
| 361 | #define auto_temp_reg(offset) \ | 365 | #define auto_temp_reg(offset) \ |
| 362 | static ssize_t show_auto_temp_##offset##_off (struct device *dev, struct device_attribute *attr, char *buf) \ | 366 | static SENSOR_DEVICE_ATTR(auto_temp##offset##_off, S_IRUGO, \ |
| 363 | { \ | 367 | show_auto_temp_off, NULL, offset - 1); \ |
| 364 | return show_auto_temp_off(dev, buf, offset - 1); \ | 368 | static SENSOR_DEVICE_ATTR(auto_temp##offset##_min, S_IRUGO | S_IWUSR, \ |
| 365 | } \ | 369 | show_auto_temp_min, set_auto_temp_min, offset - 1); \ |
| 366 | static ssize_t show_auto_temp_##offset##_min (struct device *dev, struct device_attribute *attr, char *buf) \ | 370 | static SENSOR_DEVICE_ATTR(auto_temp##offset##_max, S_IRUGO | S_IWUSR, \ |
| 367 | { \ | 371 | show_auto_temp_max, set_auto_temp_max, offset - 1) |
| 368 | return show_auto_temp_min(dev, buf, offset - 1); \ | ||
| 369 | } \ | ||
| 370 | static ssize_t show_auto_temp_##offset##_max (struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 371 | { \ | ||
| 372 | return show_auto_temp_max(dev, buf, offset - 1); \ | ||
| 373 | } \ | ||
| 374 | static ssize_t set_auto_temp_##offset##_min (struct device *dev, struct device_attribute *attr, \ | ||
| 375 | const char *buf, size_t count) \ | ||
| 376 | { \ | ||
| 377 | return set_auto_temp_min(dev, buf, count, offset - 1); \ | ||
| 378 | } \ | ||
| 379 | static ssize_t set_auto_temp_##offset##_max (struct device *dev, struct device_attribute *attr, \ | ||
| 380 | const char *buf, size_t count) \ | ||
| 381 | { \ | ||
| 382 | return set_auto_temp_max(dev, buf, count, offset - 1); \ | ||
| 383 | } \ | ||
| 384 | static DEVICE_ATTR(auto_temp##offset##_off, S_IRUGO, \ | ||
| 385 | show_auto_temp_##offset##_off, NULL); \ | ||
| 386 | static DEVICE_ATTR(auto_temp##offset##_min, S_IRUGO | S_IWUSR, \ | ||
| 387 | show_auto_temp_##offset##_min, set_auto_temp_##offset##_min);\ | ||
| 388 | static DEVICE_ATTR(auto_temp##offset##_max, S_IRUGO | S_IWUSR, \ | ||
| 389 | show_auto_temp_##offset##_max, set_auto_temp_##offset##_max) | ||
| 390 | 372 | ||
| 391 | auto_temp_reg(1); | 373 | auto_temp_reg(1); |
| 392 | auto_temp_reg(2); | 374 | auto_temp_reg(2); |
| 393 | auto_temp_reg(3); | 375 | auto_temp_reg(3); |
| 394 | 376 | ||
| 395 | /* pwm */ | 377 | /* pwm */ |
| 396 | static ssize_t show_pwm(struct device *dev, char *buf, int nr) | 378 | static ssize_t show_pwm(struct device *dev, |
| 379 | struct device_attribute *attr, char *buf) | ||
| 397 | { | 380 | { |
| 381 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 398 | struct adm1031_data *data = adm1031_update_device(dev); | 382 | struct adm1031_data *data = adm1031_update_device(dev); |
| 399 | return sprintf(buf, "%d\n", PWM_FROM_REG(data->pwm[nr])); | 383 | return sprintf(buf, "%d\n", PWM_FROM_REG(data->pwm[nr])); |
| 400 | } | 384 | } |
| 401 | static ssize_t | 385 | static ssize_t set_pwm(struct device *dev, struct device_attribute *attr, |
| 402 | set_pwm(struct device *dev, const char *buf, size_t count, int nr) | 386 | const char *buf, size_t count) |
| 403 | { | 387 | { |
| 404 | struct i2c_client *client = to_i2c_client(dev); | 388 | struct i2c_client *client = to_i2c_client(dev); |
| 405 | struct adm1031_data *data = i2c_get_clientdata(client); | 389 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 390 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 406 | int val = simple_strtol(buf, NULL, 10); | 391 | int val = simple_strtol(buf, NULL, 10); |
| 407 | int reg; | 392 | int reg; |
| 408 | 393 | ||
| 409 | mutex_lock(&data->update_lock); | 394 | mutex_lock(&data->update_lock); |
| 410 | if ((data->conf1 & ADM1031_CONF1_AUTO_MODE) && | 395 | if ((data->conf1 & ADM1031_CONF1_AUTO_MODE) && |
| 411 | (((val>>4) & 0xf) != 5)) { | 396 | (((val>>4) & 0xf) != 5)) { |
| 412 | /* In automatic mode, the only PWM accepted is 33% */ | 397 | /* In automatic mode, the only PWM accepted is 33% */ |
| 413 | mutex_unlock(&data->update_lock); | 398 | mutex_unlock(&data->update_lock); |
| @@ -422,21 +407,12 @@ set_pwm(struct device *dev, const char *buf, size_t count, int nr) | |||
| 422 | return count; | 407 | return count; |
| 423 | } | 408 | } |
| 424 | 409 | ||
| 425 | #define pwm_reg(offset) \ | 410 | static SENSOR_DEVICE_ATTR(pwm1, S_IRUGO | S_IWUSR, show_pwm, set_pwm, 0); |
| 426 | static ssize_t show_pwm_##offset (struct device *dev, struct device_attribute *attr, char *buf) \ | 411 | static SENSOR_DEVICE_ATTR(pwm2, S_IRUGO | S_IWUSR, show_pwm, set_pwm, 1); |
| 427 | { \ | 412 | static SENSOR_DEVICE_ATTR(auto_fan1_min_pwm, S_IRUGO | S_IWUSR, |
| 428 | return show_pwm(dev, buf, offset - 1); \ | 413 | show_pwm, set_pwm, 0); |
| 429 | } \ | 414 | static SENSOR_DEVICE_ATTR(auto_fan2_min_pwm, S_IRUGO | S_IWUSR, |
| 430 | static ssize_t set_pwm_##offset (struct device *dev, struct device_attribute *attr, \ | 415 | show_pwm, set_pwm, 1); |
| 431 | const char *buf, size_t count) \ | ||
| 432 | { \ | ||
| 433 | return set_pwm(dev, buf, count, offset - 1); \ | ||
| 434 | } \ | ||
| 435 | static DEVICE_ATTR(pwm##offset, S_IRUGO | S_IWUSR, \ | ||
| 436 | show_pwm_##offset, set_pwm_##offset) | ||
| 437 | |||
| 438 | pwm_reg(1); | ||
| 439 | pwm_reg(2); | ||
| 440 | 416 | ||
| 441 | /* Fans */ | 417 | /* Fans */ |
| 442 | 418 | ||
| @@ -471,7 +447,7 @@ static int trust_fan_readings(struct adm1031_data *data, int chan) | |||
| 471 | AUTO_TEMP_MIN_FROM_REG_DEG(data->auto_temp[0]) | 447 | AUTO_TEMP_MIN_FROM_REG_DEG(data->auto_temp[0]) |
| 472 | || data->temp[1] >= | 448 | || data->temp[1] >= |
| 473 | AUTO_TEMP_MIN_FROM_REG_DEG(data->auto_temp[1]) | 449 | AUTO_TEMP_MIN_FROM_REG_DEG(data->auto_temp[1]) |
| 474 | || (data->chip_type == adm1031 | 450 | || (data->chip_type == adm1031 |
| 475 | && data->temp[2] >= | 451 | && data->temp[2] >= |
| 476 | AUTO_TEMP_MIN_FROM_REG_DEG(data->auto_temp[2])); | 452 | AUTO_TEMP_MIN_FROM_REG_DEG(data->auto_temp[2])); |
| 477 | break; | 453 | break; |
| @@ -483,8 +459,10 @@ static int trust_fan_readings(struct adm1031_data *data, int chan) | |||
| 483 | } | 459 | } |
| 484 | 460 | ||
| 485 | 461 | ||
| 486 | static ssize_t show_fan(struct device *dev, char *buf, int nr) | 462 | static ssize_t show_fan(struct device *dev, |
| 463 | struct device_attribute *attr, char *buf) | ||
| 487 | { | 464 | { |
| 465 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 488 | struct adm1031_data *data = adm1031_update_device(dev); | 466 | struct adm1031_data *data = adm1031_update_device(dev); |
| 489 | int value; | 467 | int value; |
| 490 | 468 | ||
| @@ -493,28 +471,33 @@ static ssize_t show_fan(struct device *dev, char *buf, int nr) | |||
| 493 | return sprintf(buf, "%d\n", value); | 471 | return sprintf(buf, "%d\n", value); |
| 494 | } | 472 | } |
| 495 | 473 | ||
| 496 | static ssize_t show_fan_div(struct device *dev, char *buf, int nr) | 474 | static ssize_t show_fan_div(struct device *dev, |
| 475 | struct device_attribute *attr, char *buf) | ||
| 497 | { | 476 | { |
| 477 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 498 | struct adm1031_data *data = adm1031_update_device(dev); | 478 | struct adm1031_data *data = adm1031_update_device(dev); |
| 499 | return sprintf(buf, "%d\n", FAN_DIV_FROM_REG(data->fan_div[nr])); | 479 | return sprintf(buf, "%d\n", FAN_DIV_FROM_REG(data->fan_div[nr])); |
| 500 | } | 480 | } |
| 501 | static ssize_t show_fan_min(struct device *dev, char *buf, int nr) | 481 | static ssize_t show_fan_min(struct device *dev, |
| 482 | struct device_attribute *attr, char *buf) | ||
| 502 | { | 483 | { |
| 484 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 503 | struct adm1031_data *data = adm1031_update_device(dev); | 485 | struct adm1031_data *data = adm1031_update_device(dev); |
| 504 | return sprintf(buf, "%d\n", | 486 | return sprintf(buf, "%d\n", |
| 505 | FAN_FROM_REG(data->fan_min[nr], | 487 | FAN_FROM_REG(data->fan_min[nr], |
| 506 | FAN_DIV_FROM_REG(data->fan_div[nr]))); | 488 | FAN_DIV_FROM_REG(data->fan_div[nr]))); |
| 507 | } | 489 | } |
| 508 | static ssize_t | 490 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, |
| 509 | set_fan_min(struct device *dev, const char *buf, size_t count, int nr) | 491 | const char *buf, size_t count) |
| 510 | { | 492 | { |
| 511 | struct i2c_client *client = to_i2c_client(dev); | 493 | struct i2c_client *client = to_i2c_client(dev); |
| 512 | struct adm1031_data *data = i2c_get_clientdata(client); | 494 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 495 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 513 | int val = simple_strtol(buf, NULL, 10); | 496 | int val = simple_strtol(buf, NULL, 10); |
| 514 | 497 | ||
| 515 | mutex_lock(&data->update_lock); | 498 | mutex_lock(&data->update_lock); |
| 516 | if (val) { | 499 | if (val) { |
| 517 | data->fan_min[nr] = | 500 | data->fan_min[nr] = |
| 518 | FAN_TO_REG(val, FAN_DIV_FROM_REG(data->fan_div[nr])); | 501 | FAN_TO_REG(val, FAN_DIV_FROM_REG(data->fan_div[nr])); |
| 519 | } else { | 502 | } else { |
| 520 | data->fan_min[nr] = 0xff; | 503 | data->fan_min[nr] = 0xff; |
| @@ -523,11 +506,12 @@ set_fan_min(struct device *dev, const char *buf, size_t count, int nr) | |||
| 523 | mutex_unlock(&data->update_lock); | 506 | mutex_unlock(&data->update_lock); |
| 524 | return count; | 507 | return count; |
| 525 | } | 508 | } |
| 526 | static ssize_t | 509 | static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, |
| 527 | set_fan_div(struct device *dev, const char *buf, size_t count, int nr) | 510 | const char *buf, size_t count) |
| 528 | { | 511 | { |
| 529 | struct i2c_client *client = to_i2c_client(dev); | 512 | struct i2c_client *client = to_i2c_client(dev); |
| 530 | struct adm1031_data *data = i2c_get_clientdata(client); | 513 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 514 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 531 | int val = simple_strtol(buf, NULL, 10); | 515 | int val = simple_strtol(buf, NULL, 10); |
| 532 | u8 tmp; | 516 | u8 tmp; |
| 533 | int old_div; | 517 | int old_div; |
| @@ -535,68 +519,53 @@ set_fan_div(struct device *dev, const char *buf, size_t count, int nr) | |||
| 535 | 519 | ||
| 536 | tmp = val == 8 ? 0xc0 : | 520 | tmp = val == 8 ? 0xc0 : |
| 537 | val == 4 ? 0x80 : | 521 | val == 4 ? 0x80 : |
| 538 | val == 2 ? 0x40 : | 522 | val == 2 ? 0x40 : |
| 539 | val == 1 ? 0x00 : | 523 | val == 1 ? 0x00 : |
| 540 | 0xff; | 524 | 0xff; |
| 541 | if (tmp == 0xff) | 525 | if (tmp == 0xff) |
| 542 | return -EINVAL; | 526 | return -EINVAL; |
| 543 | 527 | ||
| 544 | mutex_lock(&data->update_lock); | 528 | mutex_lock(&data->update_lock); |
| 529 | /* Get fresh readings */ | ||
| 530 | data->fan_div[nr] = adm1031_read_value(client, | ||
| 531 | ADM1031_REG_FAN_DIV(nr)); | ||
| 532 | data->fan_min[nr] = adm1031_read_value(client, | ||
| 533 | ADM1031_REG_FAN_MIN(nr)); | ||
| 534 | |||
| 535 | /* Write the new clock divider and fan min */ | ||
| 545 | old_div = FAN_DIV_FROM_REG(data->fan_div[nr]); | 536 | old_div = FAN_DIV_FROM_REG(data->fan_div[nr]); |
| 546 | data->fan_div[nr] = (tmp & 0xC0) | (0x3f & data->fan_div[nr]); | 537 | data->fan_div[nr] = tmp | (0x3f & data->fan_div[nr]); |
| 547 | new_min = data->fan_min[nr] * old_div / | 538 | new_min = data->fan_min[nr] * old_div / val; |
| 548 | FAN_DIV_FROM_REG(data->fan_div[nr]); | ||
| 549 | data->fan_min[nr] = new_min > 0xff ? 0xff : new_min; | 539 | data->fan_min[nr] = new_min > 0xff ? 0xff : new_min; |
| 550 | data->fan[nr] = data->fan[nr] * old_div / | ||
| 551 | FAN_DIV_FROM_REG(data->fan_div[nr]); | ||
| 552 | 540 | ||
| 553 | adm1031_write_value(client, ADM1031_REG_FAN_DIV(nr), | 541 | adm1031_write_value(client, ADM1031_REG_FAN_DIV(nr), |
| 554 | data->fan_div[nr]); | 542 | data->fan_div[nr]); |
| 555 | adm1031_write_value(client, ADM1031_REG_FAN_MIN(nr), | 543 | adm1031_write_value(client, ADM1031_REG_FAN_MIN(nr), |
| 556 | data->fan_min[nr]); | 544 | data->fan_min[nr]); |
| 545 | |||
| 546 | /* Invalidate the cache: fan speed is no longer valid */ | ||
| 547 | data->valid = 0; | ||
| 557 | mutex_unlock(&data->update_lock); | 548 | mutex_unlock(&data->update_lock); |
| 558 | return count; | 549 | return count; |
| 559 | } | 550 | } |
| 560 | 551 | ||
| 561 | #define fan_offset(offset) \ | 552 | #define fan_offset(offset) \ |
| 562 | static ssize_t show_fan_##offset (struct device *dev, struct device_attribute *attr, char *buf) \ | 553 | static SENSOR_DEVICE_ATTR(fan##offset##_input, S_IRUGO, \ |
| 563 | { \ | 554 | show_fan, NULL, offset - 1); \ |
| 564 | return show_fan(dev, buf, offset - 1); \ | 555 | static SENSOR_DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \ |
| 565 | } \ | 556 | show_fan_min, set_fan_min, offset - 1); \ |
| 566 | static ssize_t show_fan_##offset##_min (struct device *dev, struct device_attribute *attr, char *buf) \ | 557 | static SENSOR_DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \ |
| 567 | { \ | 558 | show_fan_div, set_fan_div, offset - 1) |
| 568 | return show_fan_min(dev, buf, offset - 1); \ | ||
| 569 | } \ | ||
| 570 | static ssize_t show_fan_##offset##_div (struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 571 | { \ | ||
| 572 | return show_fan_div(dev, buf, offset - 1); \ | ||
| 573 | } \ | ||
| 574 | static ssize_t set_fan_##offset##_min (struct device *dev, struct device_attribute *attr, \ | ||
| 575 | const char *buf, size_t count) \ | ||
| 576 | { \ | ||
| 577 | return set_fan_min(dev, buf, count, offset - 1); \ | ||
| 578 | } \ | ||
| 579 | static ssize_t set_fan_##offset##_div (struct device *dev, struct device_attribute *attr, \ | ||
| 580 | const char *buf, size_t count) \ | ||
| 581 | { \ | ||
| 582 | return set_fan_div(dev, buf, count, offset - 1); \ | ||
| 583 | } \ | ||
| 584 | static DEVICE_ATTR(fan##offset##_input, S_IRUGO, show_fan_##offset, \ | ||
| 585 | NULL); \ | ||
| 586 | static DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \ | ||
| 587 | show_fan_##offset##_min, set_fan_##offset##_min); \ | ||
| 588 | static DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \ | ||
| 589 | show_fan_##offset##_div, set_fan_##offset##_div); \ | ||
| 590 | static DEVICE_ATTR(auto_fan##offset##_min_pwm, S_IRUGO | S_IWUSR, \ | ||
| 591 | show_pwm_##offset, set_pwm_##offset) | ||
| 592 | 559 | ||
| 593 | fan_offset(1); | 560 | fan_offset(1); |
| 594 | fan_offset(2); | 561 | fan_offset(2); |
| 595 | 562 | ||
| 596 | 563 | ||
| 597 | /* Temps */ | 564 | /* Temps */ |
| 598 | static ssize_t show_temp(struct device *dev, char *buf, int nr) | 565 | static ssize_t show_temp(struct device *dev, |
| 566 | struct device_attribute *attr, char *buf) | ||
| 599 | { | 567 | { |
| 568 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 600 | struct adm1031_data *data = adm1031_update_device(dev); | 569 | struct adm1031_data *data = adm1031_update_device(dev); |
| 601 | int ext; | 570 | int ext; |
| 602 | ext = nr == 0 ? | 571 | ext = nr == 0 ? |
| @@ -604,26 +573,33 @@ static ssize_t show_temp(struct device *dev, char *buf, int nr) | |||
| 604 | (((data->ext_temp[nr] >> ((nr - 1) * 3)) & 7)); | 573 | (((data->ext_temp[nr] >> ((nr - 1) * 3)) & 7)); |
| 605 | return sprintf(buf, "%d\n", TEMP_FROM_REG_EXT(data->temp[nr], ext)); | 574 | return sprintf(buf, "%d\n", TEMP_FROM_REG_EXT(data->temp[nr], ext)); |
| 606 | } | 575 | } |
| 607 | static ssize_t show_temp_min(struct device *dev, char *buf, int nr) | 576 | static ssize_t show_temp_min(struct device *dev, |
| 577 | struct device_attribute *attr, char *buf) | ||
| 608 | { | 578 | { |
| 579 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 609 | struct adm1031_data *data = adm1031_update_device(dev); | 580 | struct adm1031_data *data = adm1031_update_device(dev); |
| 610 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_min[nr])); | 581 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_min[nr])); |
| 611 | } | 582 | } |
| 612 | static ssize_t show_temp_max(struct device *dev, char *buf, int nr) | 583 | static ssize_t show_temp_max(struct device *dev, |
| 584 | struct device_attribute *attr, char *buf) | ||
| 613 | { | 585 | { |
| 586 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 614 | struct adm1031_data *data = adm1031_update_device(dev); | 587 | struct adm1031_data *data = adm1031_update_device(dev); |
| 615 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[nr])); | 588 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[nr])); |
| 616 | } | 589 | } |
| 617 | static ssize_t show_temp_crit(struct device *dev, char *buf, int nr) | 590 | static ssize_t show_temp_crit(struct device *dev, |
| 591 | struct device_attribute *attr, char *buf) | ||
| 618 | { | 592 | { |
| 593 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 619 | struct adm1031_data *data = adm1031_update_device(dev); | 594 | struct adm1031_data *data = adm1031_update_device(dev); |
| 620 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_crit[nr])); | 595 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_crit[nr])); |
| 621 | } | 596 | } |
| 622 | static ssize_t | 597 | static ssize_t set_temp_min(struct device *dev, struct device_attribute *attr, |
| 623 | set_temp_min(struct device *dev, const char *buf, size_t count, int nr) | 598 | const char *buf, size_t count) |
| 624 | { | 599 | { |
| 625 | struct i2c_client *client = to_i2c_client(dev); | 600 | struct i2c_client *client = to_i2c_client(dev); |
| 626 | struct adm1031_data *data = i2c_get_clientdata(client); | 601 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 602 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 627 | int val; | 603 | int val; |
| 628 | 604 | ||
| 629 | val = simple_strtol(buf, NULL, 10); | 605 | val = simple_strtol(buf, NULL, 10); |
| @@ -635,11 +611,12 @@ set_temp_min(struct device *dev, const char *buf, size_t count, int nr) | |||
| 635 | mutex_unlock(&data->update_lock); | 611 | mutex_unlock(&data->update_lock); |
| 636 | return count; | 612 | return count; |
| 637 | } | 613 | } |
| 638 | static ssize_t | 614 | static ssize_t set_temp_max(struct device *dev, struct device_attribute *attr, |
| 639 | set_temp_max(struct device *dev, const char *buf, size_t count, int nr) | 615 | const char *buf, size_t count) |
| 640 | { | 616 | { |
| 641 | struct i2c_client *client = to_i2c_client(dev); | 617 | struct i2c_client *client = to_i2c_client(dev); |
| 642 | struct adm1031_data *data = i2c_get_clientdata(client); | 618 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 619 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 643 | int val; | 620 | int val; |
| 644 | 621 | ||
| 645 | val = simple_strtol(buf, NULL, 10); | 622 | val = simple_strtol(buf, NULL, 10); |
| @@ -651,11 +628,12 @@ set_temp_max(struct device *dev, const char *buf, size_t count, int nr) | |||
| 651 | mutex_unlock(&data->update_lock); | 628 | mutex_unlock(&data->update_lock); |
| 652 | return count; | 629 | return count; |
| 653 | } | 630 | } |
| 654 | static ssize_t | 631 | static ssize_t set_temp_crit(struct device *dev, struct device_attribute *attr, |
| 655 | set_temp_crit(struct device *dev, const char *buf, size_t count, int nr) | 632 | const char *buf, size_t count) |
| 656 | { | 633 | { |
| 657 | struct i2c_client *client = to_i2c_client(dev); | 634 | struct i2c_client *client = to_i2c_client(dev); |
| 658 | struct adm1031_data *data = i2c_get_clientdata(client); | 635 | struct adm1031_data *data = i2c_get_clientdata(client); |
| 636 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 659 | int val; | 637 | int val; |
| 660 | 638 | ||
| 661 | val = simple_strtol(buf, NULL, 10); | 639 | val = simple_strtol(buf, NULL, 10); |
| @@ -668,46 +646,15 @@ set_temp_crit(struct device *dev, const char *buf, size_t count, int nr) | |||
| 668 | return count; | 646 | return count; |
| 669 | } | 647 | } |
| 670 | 648 | ||
| 671 | #define temp_reg(offset) \ | 649 | #define temp_reg(offset) \ |
| 672 | static ssize_t show_temp_##offset (struct device *dev, struct device_attribute *attr, char *buf) \ | 650 | static SENSOR_DEVICE_ATTR(temp##offset##_input, S_IRUGO, \ |
| 673 | { \ | 651 | show_temp, NULL, offset - 1); \ |
| 674 | return show_temp(dev, buf, offset - 1); \ | 652 | static SENSOR_DEVICE_ATTR(temp##offset##_min, S_IRUGO | S_IWUSR, \ |
| 675 | } \ | 653 | show_temp_min, set_temp_min, offset - 1); \ |
| 676 | static ssize_t show_temp_##offset##_min (struct device *dev, struct device_attribute *attr, char *buf) \ | 654 | static SENSOR_DEVICE_ATTR(temp##offset##_max, S_IRUGO | S_IWUSR, \ |
| 677 | { \ | 655 | show_temp_max, set_temp_max, offset - 1); \ |
| 678 | return show_temp_min(dev, buf, offset - 1); \ | 656 | static SENSOR_DEVICE_ATTR(temp##offset##_crit, S_IRUGO | S_IWUSR, \ |
| 679 | } \ | 657 | show_temp_crit, set_temp_crit, offset - 1) |
| 680 | static ssize_t show_temp_##offset##_max (struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 681 | { \ | ||
| 682 | return show_temp_max(dev, buf, offset - 1); \ | ||
| 683 | } \ | ||
| 684 | static ssize_t show_temp_##offset##_crit (struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 685 | { \ | ||
| 686 | return show_temp_crit(dev, buf, offset - 1); \ | ||
| 687 | } \ | ||
| 688 | static ssize_t set_temp_##offset##_min (struct device *dev, struct device_attribute *attr, \ | ||
| 689 | const char *buf, size_t count) \ | ||
| 690 | { \ | ||
| 691 | return set_temp_min(dev, buf, count, offset - 1); \ | ||
| 692 | } \ | ||
| 693 | static ssize_t set_temp_##offset##_max (struct device *dev, struct device_attribute *attr, \ | ||
| 694 | const char *buf, size_t count) \ | ||
| 695 | { \ | ||
| 696 | return set_temp_max(dev, buf, count, offset - 1); \ | ||
| 697 | } \ | ||
| 698 | static ssize_t set_temp_##offset##_crit (struct device *dev, struct device_attribute *attr, \ | ||
| 699 | const char *buf, size_t count) \ | ||
| 700 | { \ | ||
| 701 | return set_temp_crit(dev, buf, count, offset - 1); \ | ||
| 702 | } \ | ||
| 703 | static DEVICE_ATTR(temp##offset##_input, S_IRUGO, show_temp_##offset, \ | ||
| 704 | NULL); \ | ||
| 705 | static DEVICE_ATTR(temp##offset##_min, S_IRUGO | S_IWUSR, \ | ||
| 706 | show_temp_##offset##_min, set_temp_##offset##_min); \ | ||
| 707 | static DEVICE_ATTR(temp##offset##_max, S_IRUGO | S_IWUSR, \ | ||
| 708 | show_temp_##offset##_max, set_temp_##offset##_max); \ | ||
| 709 | static DEVICE_ATTR(temp##offset##_crit, S_IRUGO | S_IWUSR, \ | ||
| 710 | show_temp_##offset##_crit, set_temp_##offset##_crit) | ||
| 711 | 658 | ||
| 712 | temp_reg(1); | 659 | temp_reg(1); |
| 713 | temp_reg(2); | 660 | temp_reg(2); |
| @@ -722,6 +669,29 @@ static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, ch | |||
| 722 | 669 | ||
| 723 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | 670 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); |
| 724 | 671 | ||
| 672 | static ssize_t show_alarm(struct device *dev, | ||
| 673 | struct device_attribute *attr, char *buf) | ||
| 674 | { | ||
| 675 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 676 | struct adm1031_data *data = adm1031_update_device(dev); | ||
| 677 | return sprintf(buf, "%d\n", (data->alarm >> bitnr) & 1); | ||
| 678 | } | ||
| 679 | |||
| 680 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 681 | static SENSOR_DEVICE_ATTR(fan1_fault, S_IRUGO, show_alarm, NULL, 1); | ||
| 682 | static SENSOR_DEVICE_ATTR(temp2_max_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 683 | static SENSOR_DEVICE_ATTR(temp2_min_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 684 | static SENSOR_DEVICE_ATTR(temp2_crit_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 685 | static SENSOR_DEVICE_ATTR(temp2_fault, S_IRUGO, show_alarm, NULL, 5); | ||
| 686 | static SENSOR_DEVICE_ATTR(temp1_max_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 687 | static SENSOR_DEVICE_ATTR(temp1_min_alarm, S_IRUGO, show_alarm, NULL, 7); | ||
| 688 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 689 | static SENSOR_DEVICE_ATTR(fan2_fault, S_IRUGO, show_alarm, NULL, 9); | ||
| 690 | static SENSOR_DEVICE_ATTR(temp3_max_alarm, S_IRUGO, show_alarm, NULL, 10); | ||
| 691 | static SENSOR_DEVICE_ATTR(temp3_min_alarm, S_IRUGO, show_alarm, NULL, 11); | ||
| 692 | static SENSOR_DEVICE_ATTR(temp3_crit_alarm, S_IRUGO, show_alarm, NULL, 12); | ||
| 693 | static SENSOR_DEVICE_ATTR(temp3_fault, S_IRUGO, show_alarm, NULL, 13); | ||
| 694 | static SENSOR_DEVICE_ATTR(temp1_crit_alarm, S_IRUGO, show_alarm, NULL, 14); | ||
| 725 | 695 | ||
| 726 | static int adm1031_attach_adapter(struct i2c_adapter *adapter) | 696 | static int adm1031_attach_adapter(struct i2c_adapter *adapter) |
| 727 | { | 697 | { |
| @@ -731,29 +701,38 @@ static int adm1031_attach_adapter(struct i2c_adapter *adapter) | |||
| 731 | } | 701 | } |
| 732 | 702 | ||
| 733 | static struct attribute *adm1031_attributes[] = { | 703 | static struct attribute *adm1031_attributes[] = { |
| 734 | &dev_attr_fan1_input.attr, | 704 | &sensor_dev_attr_fan1_input.dev_attr.attr, |
| 735 | &dev_attr_fan1_div.attr, | 705 | &sensor_dev_attr_fan1_div.dev_attr.attr, |
| 736 | &dev_attr_fan1_min.attr, | 706 | &sensor_dev_attr_fan1_min.dev_attr.attr, |
| 737 | &dev_attr_pwm1.attr, | 707 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, |
| 738 | &dev_attr_auto_fan1_channel.attr, | 708 | &sensor_dev_attr_fan1_fault.dev_attr.attr, |
| 739 | &dev_attr_temp1_input.attr, | 709 | &sensor_dev_attr_pwm1.dev_attr.attr, |
| 740 | &dev_attr_temp1_min.attr, | 710 | &sensor_dev_attr_auto_fan1_channel.dev_attr.attr, |
| 741 | &dev_attr_temp1_max.attr, | 711 | &sensor_dev_attr_temp1_input.dev_attr.attr, |
| 742 | &dev_attr_temp1_crit.attr, | 712 | &sensor_dev_attr_temp1_min.dev_attr.attr, |
| 743 | &dev_attr_temp2_input.attr, | 713 | &sensor_dev_attr_temp1_min_alarm.dev_attr.attr, |
| 744 | &dev_attr_temp2_min.attr, | 714 | &sensor_dev_attr_temp1_max.dev_attr.attr, |
| 745 | &dev_attr_temp2_max.attr, | 715 | &sensor_dev_attr_temp1_max_alarm.dev_attr.attr, |
| 746 | &dev_attr_temp2_crit.attr, | 716 | &sensor_dev_attr_temp1_crit.dev_attr.attr, |
| 747 | 717 | &sensor_dev_attr_temp1_crit_alarm.dev_attr.attr, | |
| 748 | &dev_attr_auto_temp1_off.attr, | 718 | &sensor_dev_attr_temp2_input.dev_attr.attr, |
| 749 | &dev_attr_auto_temp1_min.attr, | 719 | &sensor_dev_attr_temp2_min.dev_attr.attr, |
| 750 | &dev_attr_auto_temp1_max.attr, | 720 | &sensor_dev_attr_temp2_min_alarm.dev_attr.attr, |
| 751 | 721 | &sensor_dev_attr_temp2_max.dev_attr.attr, | |
| 752 | &dev_attr_auto_temp2_off.attr, | 722 | &sensor_dev_attr_temp2_max_alarm.dev_attr.attr, |
| 753 | &dev_attr_auto_temp2_min.attr, | 723 | &sensor_dev_attr_temp2_crit.dev_attr.attr, |
| 754 | &dev_attr_auto_temp2_max.attr, | 724 | &sensor_dev_attr_temp2_crit_alarm.dev_attr.attr, |
| 755 | 725 | &sensor_dev_attr_temp2_fault.dev_attr.attr, | |
| 756 | &dev_attr_auto_fan1_min_pwm.attr, | 726 | |
| 727 | &sensor_dev_attr_auto_temp1_off.dev_attr.attr, | ||
| 728 | &sensor_dev_attr_auto_temp1_min.dev_attr.attr, | ||
| 729 | &sensor_dev_attr_auto_temp1_max.dev_attr.attr, | ||
| 730 | |||
| 731 | &sensor_dev_attr_auto_temp2_off.dev_attr.attr, | ||
| 732 | &sensor_dev_attr_auto_temp2_min.dev_attr.attr, | ||
| 733 | &sensor_dev_attr_auto_temp2_max.dev_attr.attr, | ||
| 734 | |||
| 735 | &sensor_dev_attr_auto_fan1_min_pwm.dev_attr.attr, | ||
| 757 | 736 | ||
| 758 | &dev_attr_alarms.attr, | 737 | &dev_attr_alarms.attr, |
| 759 | 738 | ||
| @@ -765,19 +744,25 @@ static const struct attribute_group adm1031_group = { | |||
| 765 | }; | 744 | }; |
| 766 | 745 | ||
| 767 | static struct attribute *adm1031_attributes_opt[] = { | 746 | static struct attribute *adm1031_attributes_opt[] = { |
| 768 | &dev_attr_fan2_input.attr, | 747 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 769 | &dev_attr_fan2_div.attr, | 748 | &sensor_dev_attr_fan2_div.dev_attr.attr, |
| 770 | &dev_attr_fan2_min.attr, | 749 | &sensor_dev_attr_fan2_min.dev_attr.attr, |
| 771 | &dev_attr_pwm2.attr, | 750 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, |
| 772 | &dev_attr_auto_fan2_channel.attr, | 751 | &sensor_dev_attr_fan2_fault.dev_attr.attr, |
| 773 | &dev_attr_temp3_input.attr, | 752 | &sensor_dev_attr_pwm2.dev_attr.attr, |
| 774 | &dev_attr_temp3_min.attr, | 753 | &sensor_dev_attr_auto_fan2_channel.dev_attr.attr, |
| 775 | &dev_attr_temp3_max.attr, | 754 | &sensor_dev_attr_temp3_input.dev_attr.attr, |
| 776 | &dev_attr_temp3_crit.attr, | 755 | &sensor_dev_attr_temp3_min.dev_attr.attr, |
| 777 | &dev_attr_auto_temp3_off.attr, | 756 | &sensor_dev_attr_temp3_min_alarm.dev_attr.attr, |
| 778 | &dev_attr_auto_temp3_min.attr, | 757 | &sensor_dev_attr_temp3_max.dev_attr.attr, |
| 779 | &dev_attr_auto_temp3_max.attr, | 758 | &sensor_dev_attr_temp3_max_alarm.dev_attr.attr, |
| 780 | &dev_attr_auto_fan2_min_pwm.attr, | 759 | &sensor_dev_attr_temp3_crit.dev_attr.attr, |
| 760 | &sensor_dev_attr_temp3_crit_alarm.dev_attr.attr, | ||
| 761 | &sensor_dev_attr_temp3_fault.dev_attr.attr, | ||
| 762 | &sensor_dev_attr_auto_temp3_off.dev_attr.attr, | ||
| 763 | &sensor_dev_attr_auto_temp3_min.dev_attr.attr, | ||
| 764 | &sensor_dev_attr_auto_temp3_max.dev_attr.attr, | ||
| 765 | &sensor_dev_attr_auto_fan2_min_pwm.dev_attr.attr, | ||
| 781 | NULL | 766 | NULL |
| 782 | }; | 767 | }; |
| 783 | 768 | ||
| @@ -788,7 +773,7 @@ static const struct attribute_group adm1031_group_opt = { | |||
| 788 | /* This function is called by i2c_probe */ | 773 | /* This function is called by i2c_probe */ |
| 789 | static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) | 774 | static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) |
| 790 | { | 775 | { |
| 791 | struct i2c_client *new_client; | 776 | struct i2c_client *client; |
| 792 | struct adm1031_data *data; | 777 | struct adm1031_data *data; |
| 793 | int err = 0; | 778 | int err = 0; |
| 794 | const char *name = ""; | 779 | const char *name = ""; |
| @@ -801,17 +786,16 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 801 | goto exit; | 786 | goto exit; |
| 802 | } | 787 | } |
| 803 | 788 | ||
| 804 | new_client = &data->client; | 789 | client = &data->client; |
| 805 | i2c_set_clientdata(new_client, data); | 790 | i2c_set_clientdata(client, data); |
| 806 | new_client->addr = address; | 791 | client->addr = address; |
| 807 | new_client->adapter = adapter; | 792 | client->adapter = adapter; |
| 808 | new_client->driver = &adm1031_driver; | 793 | client->driver = &adm1031_driver; |
| 809 | new_client->flags = 0; | ||
| 810 | 794 | ||
| 811 | if (kind < 0) { | 795 | if (kind < 0) { |
| 812 | int id, co; | 796 | int id, co; |
| 813 | id = i2c_smbus_read_byte_data(new_client, 0x3d); | 797 | id = i2c_smbus_read_byte_data(client, 0x3d); |
| 814 | co = i2c_smbus_read_byte_data(new_client, 0x3e); | 798 | co = i2c_smbus_read_byte_data(client, 0x3e); |
| 815 | 799 | ||
| 816 | if (!((id == 0x31 || id == 0x30) && co == 0x41)) | 800 | if (!((id == 0x31 || id == 0x30) && co == 0x41)) |
| 817 | goto exit_free; | 801 | goto exit_free; |
| @@ -832,28 +816,27 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 832 | } | 816 | } |
| 833 | data->chip_type = kind; | 817 | data->chip_type = kind; |
| 834 | 818 | ||
| 835 | strlcpy(new_client->name, name, I2C_NAME_SIZE); | 819 | strlcpy(client->name, name, I2C_NAME_SIZE); |
| 836 | data->valid = 0; | ||
| 837 | mutex_init(&data->update_lock); | 820 | mutex_init(&data->update_lock); |
| 838 | 821 | ||
| 839 | /* Tell the I2C layer a new client has arrived */ | 822 | /* Tell the I2C layer a new client has arrived */ |
| 840 | if ((err = i2c_attach_client(new_client))) | 823 | if ((err = i2c_attach_client(client))) |
| 841 | goto exit_free; | 824 | goto exit_free; |
| 842 | 825 | ||
| 843 | /* Initialize the ADM1031 chip */ | 826 | /* Initialize the ADM1031 chip */ |
| 844 | adm1031_init_client(new_client); | 827 | adm1031_init_client(client); |
| 845 | 828 | ||
| 846 | /* Register sysfs hooks */ | 829 | /* Register sysfs hooks */ |
| 847 | if ((err = sysfs_create_group(&new_client->dev.kobj, &adm1031_group))) | 830 | if ((err = sysfs_create_group(&client->dev.kobj, &adm1031_group))) |
| 848 | goto exit_detach; | 831 | goto exit_detach; |
| 849 | 832 | ||
| 850 | if (kind == adm1031) { | 833 | if (kind == adm1031) { |
| 851 | if ((err = sysfs_create_group(&new_client->dev.kobj, | 834 | if ((err = sysfs_create_group(&client->dev.kobj, |
| 852 | &adm1031_group_opt))) | 835 | &adm1031_group_opt))) |
| 853 | goto exit_remove; | 836 | goto exit_remove; |
| 854 | } | 837 | } |
| 855 | 838 | ||
| 856 | data->hwmon_dev = hwmon_device_register(&new_client->dev); | 839 | data->hwmon_dev = hwmon_device_register(&client->dev); |
| 857 | if (IS_ERR(data->hwmon_dev)) { | 840 | if (IS_ERR(data->hwmon_dev)) { |
| 858 | err = PTR_ERR(data->hwmon_dev); | 841 | err = PTR_ERR(data->hwmon_dev); |
| 859 | goto exit_remove; | 842 | goto exit_remove; |
| @@ -862,10 +845,10 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 862 | return 0; | 845 | return 0; |
| 863 | 846 | ||
| 864 | exit_remove: | 847 | exit_remove: |
| 865 | sysfs_remove_group(&new_client->dev.kobj, &adm1031_group); | 848 | sysfs_remove_group(&client->dev.kobj, &adm1031_group); |
| 866 | sysfs_remove_group(&new_client->dev.kobj, &adm1031_group_opt); | 849 | sysfs_remove_group(&client->dev.kobj, &adm1031_group_opt); |
| 867 | exit_detach: | 850 | exit_detach: |
| 868 | i2c_detach_client(new_client); | 851 | i2c_detach_client(client); |
| 869 | exit_free: | 852 | exit_free: |
| 870 | kfree(data); | 853 | kfree(data); |
| 871 | exit: | 854 | exit: |
| @@ -897,7 +880,7 @@ static void adm1031_init_client(struct i2c_client *client) | |||
| 897 | if (data->chip_type == adm1031) { | 880 | if (data->chip_type == adm1031) { |
| 898 | mask |= (ADM1031_CONF2_PWM2_ENABLE | | 881 | mask |= (ADM1031_CONF2_PWM2_ENABLE | |
| 899 | ADM1031_CONF2_TACH2_ENABLE); | 882 | ADM1031_CONF2_TACH2_ENABLE); |
| 900 | } | 883 | } |
| 901 | /* Initialize the ADM1031 chip (enables fan speed reading ) */ | 884 | /* Initialize the ADM1031 chip (enables fan speed reading ) */ |
| 902 | read_val = adm1031_read_value(client, ADM1031_REG_CONF2); | 885 | read_val = adm1031_read_value(client, ADM1031_REG_CONF2); |
| 903 | if ((read_val | mask) != read_val) { | 886 | if ((read_val | mask) != read_val) { |
| @@ -976,7 +959,7 @@ static struct adm1031_data *adm1031_update_device(struct device *dev) | |||
| 976 | if (data->chip_type == adm1030) { | 959 | if (data->chip_type == adm1030) { |
| 977 | data->alarm &= 0xc0ff; | 960 | data->alarm &= 0xc0ff; |
| 978 | } | 961 | } |
| 979 | 962 | ||
| 980 | for (chan=0; chan<(data->chip_type == adm1030 ? 1 : 2); chan++) { | 963 | for (chan=0; chan<(data->chip_type == adm1030 ? 1 : 2); chan++) { |
| 981 | data->fan_div[chan] = | 964 | data->fan_div[chan] = |
| 982 | adm1031_read_value(client, ADM1031_REG_FAN_DIV(chan)); | 965 | adm1031_read_value(client, ADM1031_REG_FAN_DIV(chan)); |
| @@ -985,7 +968,7 @@ static struct adm1031_data *adm1031_update_device(struct device *dev) | |||
| 985 | data->fan[chan] = | 968 | data->fan[chan] = |
| 986 | adm1031_read_value(client, ADM1031_REG_FAN_SPEED(chan)); | 969 | adm1031_read_value(client, ADM1031_REG_FAN_SPEED(chan)); |
| 987 | data->pwm[chan] = | 970 | data->pwm[chan] = |
| 988 | 0xf & (adm1031_read_value(client, ADM1031_REG_PWM) >> | 971 | 0xf & (adm1031_read_value(client, ADM1031_REG_PWM) >> |
| 989 | (4*chan)); | 972 | (4*chan)); |
| 990 | } | 973 | } |
| 991 | data->last_updated = jiffies; | 974 | data->last_updated = jiffies; |
diff --git a/drivers/hwmon/adm9240.c b/drivers/hwmon/adm9240.c index c17d0b6b3283..7671d2bf7800 100644 --- a/drivers/hwmon/adm9240.c +++ b/drivers/hwmon/adm9240.c | |||
| @@ -141,7 +141,6 @@ static struct i2c_driver adm9240_driver = { | |||
| 141 | .driver = { | 141 | .driver = { |
| 142 | .name = "adm9240", | 142 | .name = "adm9240", |
| 143 | }, | 143 | }, |
| 144 | .id = I2C_DRIVERID_ADM9240, | ||
| 145 | .attach_adapter = adm9240_attach_adapter, | 144 | .attach_adapter = adm9240_attach_adapter, |
| 146 | .detach_client = adm9240_detach_client, | 145 | .detach_client = adm9240_detach_client, |
| 147 | }; | 146 | }; |
| @@ -415,6 +414,23 @@ static ssize_t show_alarms(struct device *dev, | |||
| 415 | } | 414 | } |
| 416 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | 415 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); |
| 417 | 416 | ||
| 417 | static ssize_t show_alarm(struct device *dev, | ||
| 418 | struct device_attribute *attr, char *buf) | ||
| 419 | { | ||
| 420 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 421 | struct adm9240_data *data = adm9240_update_device(dev); | ||
| 422 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); | ||
| 423 | } | ||
| 424 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 425 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 426 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 427 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 428 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 429 | static SENSOR_DEVICE_ATTR(in5_alarm, S_IRUGO, show_alarm, NULL, 9); | ||
| 430 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 431 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 432 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 7); | ||
| 433 | |||
| 418 | /* vid */ | 434 | /* vid */ |
| 419 | static ssize_t show_vid(struct device *dev, | 435 | static ssize_t show_vid(struct device *dev, |
| 420 | struct device_attribute *attr, char *buf) | 436 | struct device_attribute *attr, char *buf) |
| @@ -469,30 +485,39 @@ static struct attribute *adm9240_attributes[] = { | |||
| 469 | &sensor_dev_attr_in0_input.dev_attr.attr, | 485 | &sensor_dev_attr_in0_input.dev_attr.attr, |
| 470 | &sensor_dev_attr_in0_min.dev_attr.attr, | 486 | &sensor_dev_attr_in0_min.dev_attr.attr, |
| 471 | &sensor_dev_attr_in0_max.dev_attr.attr, | 487 | &sensor_dev_attr_in0_max.dev_attr.attr, |
| 488 | &sensor_dev_attr_in0_alarm.dev_attr.attr, | ||
| 472 | &sensor_dev_attr_in1_input.dev_attr.attr, | 489 | &sensor_dev_attr_in1_input.dev_attr.attr, |
| 473 | &sensor_dev_attr_in1_min.dev_attr.attr, | 490 | &sensor_dev_attr_in1_min.dev_attr.attr, |
| 474 | &sensor_dev_attr_in1_max.dev_attr.attr, | 491 | &sensor_dev_attr_in1_max.dev_attr.attr, |
| 492 | &sensor_dev_attr_in1_alarm.dev_attr.attr, | ||
| 475 | &sensor_dev_attr_in2_input.dev_attr.attr, | 493 | &sensor_dev_attr_in2_input.dev_attr.attr, |
| 476 | &sensor_dev_attr_in2_min.dev_attr.attr, | 494 | &sensor_dev_attr_in2_min.dev_attr.attr, |
| 477 | &sensor_dev_attr_in2_max.dev_attr.attr, | 495 | &sensor_dev_attr_in2_max.dev_attr.attr, |
| 496 | &sensor_dev_attr_in2_alarm.dev_attr.attr, | ||
| 478 | &sensor_dev_attr_in3_input.dev_attr.attr, | 497 | &sensor_dev_attr_in3_input.dev_attr.attr, |
| 479 | &sensor_dev_attr_in3_min.dev_attr.attr, | 498 | &sensor_dev_attr_in3_min.dev_attr.attr, |
| 480 | &sensor_dev_attr_in3_max.dev_attr.attr, | 499 | &sensor_dev_attr_in3_max.dev_attr.attr, |
| 500 | &sensor_dev_attr_in3_alarm.dev_attr.attr, | ||
| 481 | &sensor_dev_attr_in4_input.dev_attr.attr, | 501 | &sensor_dev_attr_in4_input.dev_attr.attr, |
| 482 | &sensor_dev_attr_in4_min.dev_attr.attr, | 502 | &sensor_dev_attr_in4_min.dev_attr.attr, |
| 483 | &sensor_dev_attr_in4_max.dev_attr.attr, | 503 | &sensor_dev_attr_in4_max.dev_attr.attr, |
| 504 | &sensor_dev_attr_in4_alarm.dev_attr.attr, | ||
| 484 | &sensor_dev_attr_in5_input.dev_attr.attr, | 505 | &sensor_dev_attr_in5_input.dev_attr.attr, |
| 485 | &sensor_dev_attr_in5_min.dev_attr.attr, | 506 | &sensor_dev_attr_in5_min.dev_attr.attr, |
| 486 | &sensor_dev_attr_in5_max.dev_attr.attr, | 507 | &sensor_dev_attr_in5_max.dev_attr.attr, |
| 508 | &sensor_dev_attr_in5_alarm.dev_attr.attr, | ||
| 487 | &dev_attr_temp1_input.attr, | 509 | &dev_attr_temp1_input.attr, |
| 488 | &sensor_dev_attr_temp1_max.dev_attr.attr, | 510 | &sensor_dev_attr_temp1_max.dev_attr.attr, |
| 489 | &sensor_dev_attr_temp1_max_hyst.dev_attr.attr, | 511 | &sensor_dev_attr_temp1_max_hyst.dev_attr.attr, |
| 512 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 490 | &sensor_dev_attr_fan1_input.dev_attr.attr, | 513 | &sensor_dev_attr_fan1_input.dev_attr.attr, |
| 491 | &sensor_dev_attr_fan1_div.dev_attr.attr, | 514 | &sensor_dev_attr_fan1_div.dev_attr.attr, |
| 492 | &sensor_dev_attr_fan1_min.dev_attr.attr, | 515 | &sensor_dev_attr_fan1_min.dev_attr.attr, |
| 516 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 493 | &sensor_dev_attr_fan2_input.dev_attr.attr, | 517 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 494 | &sensor_dev_attr_fan2_div.dev_attr.attr, | 518 | &sensor_dev_attr_fan2_div.dev_attr.attr, |
| 495 | &sensor_dev_attr_fan2_min.dev_attr.attr, | 519 | &sensor_dev_attr_fan2_min.dev_attr.attr, |
| 520 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | ||
| 496 | &dev_attr_alarms.attr, | 521 | &dev_attr_alarms.attr, |
| 497 | &dev_attr_aout_output.attr, | 522 | &dev_attr_aout_output.attr, |
| 498 | &dev_attr_chassis_clear.attr, | 523 | &dev_attr_chassis_clear.attr, |
diff --git a/drivers/hwmon/ads7828.c b/drivers/hwmon/ads7828.c new file mode 100644 index 000000000000..6b8a73ef404c --- /dev/null +++ b/drivers/hwmon/ads7828.c | |||
| @@ -0,0 +1,297 @@ | |||
| 1 | /* | ||
| 2 | ads7828.c - lm_sensors driver for ads7828 12-bit 8-channel ADC | ||
| 3 | (C) 2007 EADS Astrium | ||
| 4 | |||
| 5 | This driver is based on the lm75 and other lm_sensors/hwmon drivers | ||
| 6 | |||
| 7 | Written by Steve Hardy <steve@linuxrealtime.co.uk> | ||
| 8 | |||
| 9 | Datasheet available at: http://focus.ti.com/lit/ds/symlink/ads7828.pdf | ||
| 10 | |||
| 11 | This program is free software; you can redistribute it and/or modify | ||
| 12 | it under the terms of the GNU General Public License as published by | ||
| 13 | the Free Software Foundation; either version 2 of the License, or | ||
| 14 | (at your option) any later version. | ||
| 15 | |||
| 16 | This program is distributed in the hope that it will be useful, | ||
| 17 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 18 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 19 | GNU General Public License for more details. | ||
| 20 | |||
| 21 | You should have received a copy of the GNU General Public License | ||
| 22 | along with this program; if not, write to the Free Software | ||
| 23 | Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
| 24 | */ | ||
| 25 | |||
| 26 | #include <linux/module.h> | ||
| 27 | #include <linux/init.h> | ||
| 28 | #include <linux/slab.h> | ||
| 29 | #include <linux/jiffies.h> | ||
| 30 | #include <linux/i2c.h> | ||
| 31 | #include <linux/hwmon.h> | ||
| 32 | #include <linux/hwmon-sysfs.h> | ||
| 33 | #include <linux/err.h> | ||
| 34 | #include <linux/mutex.h> | ||
| 35 | |||
| 36 | /* The ADS7828 registers */ | ||
| 37 | #define ADS7828_NCH 8 /* 8 channels of 12-bit A-D supported */ | ||
| 38 | #define ADS7828_CMD_SD_SE 0x80 /* Single ended inputs */ | ||
| 39 | #define ADS7828_CMD_SD_DIFF 0x00 /* Differential inputs */ | ||
| 40 | #define ADS7828_CMD_PD0 0x0 /* Power Down between A-D conversions */ | ||
| 41 | #define ADS7828_CMD_PD1 0x04 /* Internal ref OFF && A-D ON */ | ||
| 42 | #define ADS7828_CMD_PD2 0x08 /* Internal ref ON && A-D OFF */ | ||
| 43 | #define ADS7828_CMD_PD3 0x0C /* Internal ref ON && A-D ON */ | ||
| 44 | #define ADS7828_INT_VREF_MV 2500 /* Internal vref is 2.5V, 2500mV */ | ||
| 45 | |||
| 46 | /* Addresses to scan */ | ||
| 47 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, | ||
| 48 | I2C_CLIENT_END }; | ||
| 49 | |||
| 50 | /* Insmod parameters */ | ||
| 51 | I2C_CLIENT_INSMOD_1(ads7828); | ||
| 52 | |||
| 53 | /* Other module parameters */ | ||
| 54 | static int se_input = 1; /* Default is SE, 0 == diff */ | ||
| 55 | static int int_vref = 1; /* Default is internal ref ON */ | ||
| 56 | static int vref_mv = ADS7828_INT_VREF_MV; /* set if vref != 2.5V */ | ||
| 57 | module_param(se_input, bool, S_IRUGO); | ||
| 58 | module_param(int_vref, bool, S_IRUGO); | ||
| 59 | module_param(vref_mv, int, S_IRUGO); | ||
| 60 | |||
| 61 | /* Global Variables */ | ||
| 62 | static u8 ads7828_cmd_byte; /* cmd byte without channel bits */ | ||
| 63 | static unsigned int ads7828_lsb_resol; /* resolution of the ADC sample lsb */ | ||
| 64 | |||
| 65 | /* Each client has this additional data */ | ||
| 66 | struct ads7828_data { | ||
| 67 | struct i2c_client client; | ||
| 68 | struct device *hwmon_dev; | ||
| 69 | struct mutex update_lock; /* mutex protect updates */ | ||
| 70 | char valid; /* !=0 if following fields are valid */ | ||
| 71 | unsigned long last_updated; /* In jiffies */ | ||
| 72 | u16 adc_input[ADS7828_NCH]; /* ADS7828_NCH 12-bit samples */ | ||
| 73 | }; | ||
| 74 | |||
| 75 | /* Function declaration - necessary due to function dependencies */ | ||
| 76 | static int ads7828_detect(struct i2c_adapter *adapter, int address, int kind); | ||
| 77 | |||
| 78 | /* The ADS7828 returns the 12-bit sample in two bytes, | ||
| 79 | these are read as a word then byte-swapped */ | ||
| 80 | static u16 ads7828_read_value(struct i2c_client *client, u8 reg) | ||
| 81 | { | ||
| 82 | return swab16(i2c_smbus_read_word_data(client, reg)); | ||
| 83 | } | ||
| 84 | |||
| 85 | static inline u8 channel_cmd_byte(int ch) | ||
| 86 | { | ||
| 87 | /* cmd byte C2,C1,C0 - see datasheet */ | ||
| 88 | u8 cmd = (((ch>>1) | (ch&0x01)<<2)<<4); | ||
| 89 | cmd |= ads7828_cmd_byte; | ||
| 90 | return cmd; | ||
| 91 | } | ||
| 92 | |||
| 93 | /* Update data for the device (all 8 channels) */ | ||
| 94 | static struct ads7828_data *ads7828_update_device(struct device *dev) | ||
| 95 | { | ||
| 96 | struct i2c_client *client = to_i2c_client(dev); | ||
| 97 | struct ads7828_data *data = i2c_get_clientdata(client); | ||
| 98 | |||
| 99 | mutex_lock(&data->update_lock); | ||
| 100 | |||
| 101 | if (time_after(jiffies, data->last_updated + HZ + HZ / 2) | ||
| 102 | || !data->valid) { | ||
| 103 | unsigned int ch; | ||
| 104 | dev_dbg(&client->dev, "Starting ads7828 update\n"); | ||
| 105 | |||
| 106 | for (ch = 0; ch < ADS7828_NCH; ch++) { | ||
| 107 | u8 cmd = channel_cmd_byte(ch); | ||
| 108 | data->adc_input[ch] = ads7828_read_value(client, cmd); | ||
| 109 | } | ||
| 110 | data->last_updated = jiffies; | ||
| 111 | data->valid = 1; | ||
| 112 | } | ||
| 113 | |||
| 114 | mutex_unlock(&data->update_lock); | ||
| 115 | |||
| 116 | return data; | ||
| 117 | } | ||
| 118 | |||
| 119 | /* sysfs callback function */ | ||
| 120 | static ssize_t show_in(struct device *dev, struct device_attribute *da, | ||
| 121 | char *buf) | ||
| 122 | { | ||
| 123 | struct sensor_device_attribute *attr = to_sensor_dev_attr(da); | ||
| 124 | struct ads7828_data *data = ads7828_update_device(dev); | ||
| 125 | /* Print value (in mV as specified in sysfs-interface documentation) */ | ||
| 126 | return sprintf(buf, "%d\n", (data->adc_input[attr->index] * | ||
| 127 | ads7828_lsb_resol)/1000); | ||
| 128 | } | ||
| 129 | |||
| 130 | #define in_reg(offset)\ | ||
| 131 | static SENSOR_DEVICE_ATTR(in##offset##_input, S_IRUGO, show_in,\ | ||
| 132 | NULL, offset) | ||
| 133 | |||
| 134 | in_reg(0); | ||
| 135 | in_reg(1); | ||
| 136 | in_reg(2); | ||
| 137 | in_reg(3); | ||
| 138 | in_reg(4); | ||
| 139 | in_reg(5); | ||
| 140 | in_reg(6); | ||
| 141 | in_reg(7); | ||
| 142 | |||
| 143 | static struct attribute *ads7828_attributes[] = { | ||
| 144 | &sensor_dev_attr_in0_input.dev_attr.attr, | ||
| 145 | &sensor_dev_attr_in1_input.dev_attr.attr, | ||
| 146 | &sensor_dev_attr_in2_input.dev_attr.attr, | ||
| 147 | &sensor_dev_attr_in3_input.dev_attr.attr, | ||
| 148 | &sensor_dev_attr_in4_input.dev_attr.attr, | ||
| 149 | &sensor_dev_attr_in5_input.dev_attr.attr, | ||
| 150 | &sensor_dev_attr_in6_input.dev_attr.attr, | ||
| 151 | &sensor_dev_attr_in7_input.dev_attr.attr, | ||
| 152 | NULL | ||
| 153 | }; | ||
| 154 | |||
| 155 | static const struct attribute_group ads7828_group = { | ||
| 156 | .attrs = ads7828_attributes, | ||
| 157 | }; | ||
| 158 | |||
| 159 | static int ads7828_attach_adapter(struct i2c_adapter *adapter) | ||
| 160 | { | ||
| 161 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
| 162 | return 0; | ||
| 163 | return i2c_probe(adapter, &addr_data, ads7828_detect); | ||
| 164 | } | ||
| 165 | |||
| 166 | static int ads7828_detach_client(struct i2c_client *client) | ||
| 167 | { | ||
| 168 | struct ads7828_data *data = i2c_get_clientdata(client); | ||
| 169 | hwmon_device_unregister(data->hwmon_dev); | ||
| 170 | sysfs_remove_group(&client->dev.kobj, &ads7828_group); | ||
| 171 | i2c_detach_client(client); | ||
| 172 | kfree(i2c_get_clientdata(client)); | ||
| 173 | return 0; | ||
| 174 | } | ||
| 175 | |||
| 176 | /* This is the driver that will be inserted */ | ||
| 177 | static struct i2c_driver ads7828_driver = { | ||
| 178 | .driver = { | ||
| 179 | .name = "ads7828", | ||
| 180 | }, | ||
| 181 | .attach_adapter = ads7828_attach_adapter, | ||
| 182 | .detach_client = ads7828_detach_client, | ||
| 183 | }; | ||
| 184 | |||
| 185 | /* This function is called by i2c_probe */ | ||
| 186 | static int ads7828_detect(struct i2c_adapter *adapter, int address, int kind) | ||
| 187 | { | ||
| 188 | struct i2c_client *client; | ||
| 189 | struct ads7828_data *data; | ||
| 190 | int err = 0; | ||
| 191 | const char *name = ""; | ||
| 192 | |||
| 193 | /* Check we have a valid client */ | ||
| 194 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_READ_WORD_DATA)) | ||
| 195 | goto exit; | ||
| 196 | |||
| 197 | /* OK. For now, we presume we have a valid client. We now create the | ||
| 198 | client structure, even though we cannot fill it completely yet. | ||
| 199 | But it allows us to access ads7828_read_value. */ | ||
| 200 | data = kzalloc(sizeof(struct ads7828_data), GFP_KERNEL); | ||
| 201 | if (!data) { | ||
| 202 | err = -ENOMEM; | ||
| 203 | goto exit; | ||
| 204 | } | ||
| 205 | |||
| 206 | client = &data->client; | ||
| 207 | i2c_set_clientdata(client, data); | ||
| 208 | client->addr = address; | ||
| 209 | client->adapter = adapter; | ||
| 210 | client->driver = &ads7828_driver; | ||
| 211 | |||
| 212 | /* Now, we do the remaining detection. There is no identification | ||
| 213 | dedicated register so attempt to sanity check using knowledge of | ||
| 214 | the chip | ||
| 215 | - Read from the 8 channel addresses | ||
| 216 | - Check the top 4 bits of each result are not set (12 data bits) | ||
| 217 | */ | ||
| 218 | if (kind < 0) { | ||
| 219 | int ch; | ||
| 220 | for (ch = 0; ch < ADS7828_NCH; ch++) { | ||
| 221 | u16 in_data; | ||
| 222 | u8 cmd = channel_cmd_byte(ch); | ||
| 223 | in_data = ads7828_read_value(client, cmd); | ||
| 224 | if (in_data & 0xF000) { | ||
| 225 | printk(KERN_DEBUG | ||
| 226 | "%s : Doesn't look like an ads7828 device\n", | ||
| 227 | __FUNCTION__); | ||
| 228 | goto exit_free; | ||
| 229 | } | ||
| 230 | } | ||
| 231 | } | ||
| 232 | |||
| 233 | /* Determine the chip type - only one kind supported! */ | ||
| 234 | if (kind <= 0) | ||
| 235 | kind = ads7828; | ||
| 236 | |||
| 237 | if (kind == ads7828) | ||
| 238 | name = "ads7828"; | ||
| 239 | |||
| 240 | /* Fill in the remaining client fields, put it into the global list */ | ||
| 241 | strlcpy(client->name, name, I2C_NAME_SIZE); | ||
| 242 | |||
| 243 | mutex_init(&data->update_lock); | ||
| 244 | |||
| 245 | /* Tell the I2C layer a new client has arrived */ | ||
| 246 | err = i2c_attach_client(client); | ||
| 247 | if (err) | ||
| 248 | goto exit_free; | ||
| 249 | |||
| 250 | /* Register sysfs hooks */ | ||
| 251 | err = sysfs_create_group(&client->dev.kobj, &ads7828_group); | ||
| 252 | if (err) | ||
| 253 | goto exit_detach; | ||
| 254 | |||
| 255 | data->hwmon_dev = hwmon_device_register(&client->dev); | ||
| 256 | if (IS_ERR(data->hwmon_dev)) { | ||
| 257 | err = PTR_ERR(data->hwmon_dev); | ||
| 258 | goto exit_remove; | ||
| 259 | } | ||
| 260 | |||
| 261 | return 0; | ||
| 262 | |||
| 263 | exit_remove: | ||
| 264 | sysfs_remove_group(&client->dev.kobj, &ads7828_group); | ||
| 265 | exit_detach: | ||
| 266 | i2c_detach_client(client); | ||
| 267 | exit_free: | ||
| 268 | kfree(data); | ||
| 269 | exit: | ||
| 270 | return err; | ||
| 271 | } | ||
| 272 | |||
| 273 | static int __init sensors_ads7828_init(void) | ||
| 274 | { | ||
| 275 | /* Initialize the command byte according to module parameters */ | ||
| 276 | ads7828_cmd_byte = se_input ? | ||
| 277 | ADS7828_CMD_SD_SE : ADS7828_CMD_SD_DIFF; | ||
| 278 | ads7828_cmd_byte |= int_vref ? | ||
| 279 | ADS7828_CMD_PD3 : ADS7828_CMD_PD1; | ||
| 280 | |||
| 281 | /* Calculate the LSB resolution */ | ||
| 282 | ads7828_lsb_resol = (vref_mv*1000)/4096; | ||
| 283 | |||
| 284 | return i2c_add_driver(&ads7828_driver); | ||
| 285 | } | ||
| 286 | |||
| 287 | static void __exit sensors_ads7828_exit(void) | ||
| 288 | { | ||
| 289 | i2c_del_driver(&ads7828_driver); | ||
| 290 | } | ||
| 291 | |||
| 292 | MODULE_AUTHOR("Steve Hardy <steve@linuxrealtime.co.uk>"); | ||
| 293 | MODULE_DESCRIPTION("ADS7828 driver"); | ||
| 294 | MODULE_LICENSE("GPL"); | ||
| 295 | |||
| 296 | module_init(sensors_ads7828_init); | ||
| 297 | module_exit(sensors_ads7828_exit); | ||
diff --git a/drivers/hwmon/adt7470.c b/drivers/hwmon/adt7470.c index 9810aaa0489d..747693ab2ff1 100644 --- a/drivers/hwmon/adt7470.c +++ b/drivers/hwmon/adt7470.c | |||
| @@ -48,7 +48,22 @@ I2C_CLIENT_INSMOD_1(adt7470); | |||
| 48 | #define ADT7470_REG_CFG 0x40 | 48 | #define ADT7470_REG_CFG 0x40 |
| 49 | #define ADT7470_FSPD_MASK 0x04 | 49 | #define ADT7470_FSPD_MASK 0x04 |
| 50 | #define ADT7470_REG_ALARM1 0x41 | 50 | #define ADT7470_REG_ALARM1 0x41 |
| 51 | #define ADT7470_R1T_ALARM 0x01 | ||
| 52 | #define ADT7470_R2T_ALARM 0x02 | ||
| 53 | #define ADT7470_R3T_ALARM 0x04 | ||
| 54 | #define ADT7470_R4T_ALARM 0x08 | ||
| 55 | #define ADT7470_R5T_ALARM 0x10 | ||
| 56 | #define ADT7470_R6T_ALARM 0x20 | ||
| 57 | #define ADT7470_R7T_ALARM 0x40 | ||
| 58 | #define ADT7470_OOL_ALARM 0x80 | ||
| 51 | #define ADT7470_REG_ALARM2 0x42 | 59 | #define ADT7470_REG_ALARM2 0x42 |
| 60 | #define ADT7470_R8T_ALARM 0x01 | ||
| 61 | #define ADT7470_R9T_ALARM 0x02 | ||
| 62 | #define ADT7470_R10T_ALARM 0x04 | ||
| 63 | #define ADT7470_FAN1_ALARM 0x10 | ||
| 64 | #define ADT7470_FAN2_ALARM 0x20 | ||
| 65 | #define ADT7470_FAN3_ALARM 0x40 | ||
| 66 | #define ADT7470_FAN4_ALARM 0x80 | ||
| 52 | #define ADT7470_REG_TEMP_LIMITS_BASE_ADDR 0x44 | 67 | #define ADT7470_REG_TEMP_LIMITS_BASE_ADDR 0x44 |
| 53 | #define ADT7470_REG_TEMP_LIMITS_MAX_ADDR 0x57 | 68 | #define ADT7470_REG_TEMP_LIMITS_MAX_ADDR 0x57 |
| 54 | #define ADT7470_REG_FAN_MIN_BASE_ADDR 0x58 | 69 | #define ADT7470_REG_FAN_MIN_BASE_ADDR 0x58 |
| @@ -97,6 +112,8 @@ I2C_CLIENT_INSMOD_1(adt7470); | |||
| 97 | #define ADT7470_REG_PWM_AUTO_TEMP(x) (ADT7470_REG_PWM_AUTO_TEMP_BASE_ADDR + \ | 112 | #define ADT7470_REG_PWM_AUTO_TEMP(x) (ADT7470_REG_PWM_AUTO_TEMP_BASE_ADDR + \ |
| 98 | ((x) / 2)) | 113 | ((x) / 2)) |
| 99 | 114 | ||
| 115 | #define ALARM2(x) ((x) << 8) | ||
| 116 | |||
| 100 | #define ADT7470_VENDOR 0x41 | 117 | #define ADT7470_VENDOR 0x41 |
| 101 | #define ADT7470_DEVICE 0x70 | 118 | #define ADT7470_DEVICE 0x70 |
| 102 | /* datasheet only mentions a revision 2 */ | 119 | /* datasheet only mentions a revision 2 */ |
| @@ -114,8 +131,6 @@ I2C_CLIENT_INSMOD_1(adt7470); | |||
| 114 | /* sleep 1s while gathering temperature data */ | 131 | /* sleep 1s while gathering temperature data */ |
| 115 | #define TEMP_COLLECTION_TIME 1000 | 132 | #define TEMP_COLLECTION_TIME 1000 |
| 116 | 133 | ||
| 117 | #define power_of_2(x) (((x) & ((x) - 1)) == 0) | ||
| 118 | |||
| 119 | /* datasheet says to divide this number by the fan reading to get fan rpm */ | 134 | /* datasheet says to divide this number by the fan reading to get fan rpm */ |
| 120 | #define FAN_PERIOD_TO_RPM(x) ((90000 * 60) / (x)) | 135 | #define FAN_PERIOD_TO_RPM(x) ((90000 * 60) / (x)) |
| 121 | #define FAN_RPM_TO_PERIOD FAN_PERIOD_TO_RPM | 136 | #define FAN_RPM_TO_PERIOD FAN_PERIOD_TO_RPM |
| @@ -138,7 +153,8 @@ struct adt7470_data { | |||
| 138 | u16 fan[ADT7470_FAN_COUNT]; | 153 | u16 fan[ADT7470_FAN_COUNT]; |
| 139 | u16 fan_min[ADT7470_FAN_COUNT]; | 154 | u16 fan_min[ADT7470_FAN_COUNT]; |
| 140 | u16 fan_max[ADT7470_FAN_COUNT]; | 155 | u16 fan_max[ADT7470_FAN_COUNT]; |
| 141 | u16 alarms, alarms_mask; | 156 | u16 alarm; |
| 157 | u16 alarms_mask; | ||
| 142 | u8 force_pwm_max; | 158 | u8 force_pwm_max; |
| 143 | u8 pwm[ADT7470_PWM_COUNT]; | 159 | u8 pwm[ADT7470_PWM_COUNT]; |
| 144 | u8 pwm_max[ADT7470_PWM_COUNT]; | 160 | u8 pwm_max[ADT7470_PWM_COUNT]; |
| @@ -262,7 +278,10 @@ static struct adt7470_data *adt7470_update_device(struct device *dev) | |||
| 262 | else | 278 | else |
| 263 | data->force_pwm_max = 0; | 279 | data->force_pwm_max = 0; |
| 264 | 280 | ||
| 265 | data->alarms = adt7470_read_word_data(client, ADT7470_REG_ALARM1); | 281 | data->alarm = i2c_smbus_read_byte_data(client, ADT7470_REG_ALARM1); |
| 282 | if (data->alarm & ADT7470_OOL_ALARM) | ||
| 283 | data->alarm |= ALARM2(i2c_smbus_read_byte_data(client, | ||
| 284 | ADT7470_REG_ALARM2)); | ||
| 266 | data->alarms_mask = adt7470_read_word_data(client, | 285 | data->alarms_mask = adt7470_read_word_data(client, |
| 267 | ADT7470_REG_ALARM1_MASK); | 286 | ADT7470_REG_ALARM1_MASK); |
| 268 | 287 | ||
| @@ -370,17 +389,13 @@ static ssize_t show_temp(struct device *dev, struct device_attribute *devattr, | |||
| 370 | return sprintf(buf, "%d\n", 1000 * data->temp[attr->index]); | 389 | return sprintf(buf, "%d\n", 1000 * data->temp[attr->index]); |
| 371 | } | 390 | } |
| 372 | 391 | ||
| 373 | static ssize_t show_alarms(struct device *dev, | 392 | static ssize_t show_alarm_mask(struct device *dev, |
| 374 | struct device_attribute *devattr, | 393 | struct device_attribute *devattr, |
| 375 | char *buf) | 394 | char *buf) |
| 376 | { | 395 | { |
| 377 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
| 378 | struct adt7470_data *data = adt7470_update_device(dev); | 396 | struct adt7470_data *data = adt7470_update_device(dev); |
| 379 | 397 | ||
| 380 | if (attr->index) | 398 | return sprintf(buf, "%x\n", data->alarms_mask); |
| 381 | return sprintf(buf, "%x\n", data->alarms); | ||
| 382 | else | ||
| 383 | return sprintf(buf, "%x\n", data->alarms_mask); | ||
| 384 | } | 399 | } |
| 385 | 400 | ||
| 386 | static ssize_t show_fan_max(struct device *dev, | 401 | static ssize_t show_fan_max(struct device *dev, |
| @@ -677,7 +692,7 @@ static int cvt_auto_temp(int input) | |||
| 677 | { | 692 | { |
| 678 | if (input == ADT7470_PWM_ALL_TEMPS) | 693 | if (input == ADT7470_PWM_ALL_TEMPS) |
| 679 | return 0; | 694 | return 0; |
| 680 | if (input < 1 || !power_of_2(input)) | 695 | if (input < 1 || !is_power_of_2(input)) |
| 681 | return -EINVAL; | 696 | return -EINVAL; |
| 682 | return ilog2(input) + 1; | 697 | return ilog2(input) + 1; |
| 683 | } | 698 | } |
| @@ -715,8 +730,20 @@ static ssize_t set_pwm_auto_temp(struct device *dev, | |||
| 715 | return count; | 730 | return count; |
| 716 | } | 731 | } |
| 717 | 732 | ||
| 718 | static SENSOR_DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL, 0); | 733 | static ssize_t show_alarm(struct device *dev, |
| 719 | static SENSOR_DEVICE_ATTR(alarm_mask, S_IRUGO, show_alarms, NULL, 1); | 734 | struct device_attribute *devattr, |
| 735 | char *buf) | ||
| 736 | { | ||
| 737 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
| 738 | struct adt7470_data *data = adt7470_update_device(dev); | ||
| 739 | |||
| 740 | if (data->alarm & attr->index) | ||
| 741 | return sprintf(buf, "1\n"); | ||
| 742 | else | ||
| 743 | return sprintf(buf, "0\n"); | ||
| 744 | } | ||
| 745 | |||
| 746 | static DEVICE_ATTR(alarm_mask, S_IRUGO, show_alarm_mask, NULL); | ||
| 720 | 747 | ||
| 721 | static SENSOR_DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, show_temp_max, | 748 | static SENSOR_DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, show_temp_max, |
| 722 | set_temp_max, 0); | 749 | set_temp_max, 0); |
| @@ -771,6 +798,27 @@ static SENSOR_DEVICE_ATTR(temp8_input, S_IRUGO, show_temp, NULL, 7); | |||
| 771 | static SENSOR_DEVICE_ATTR(temp9_input, S_IRUGO, show_temp, NULL, 8); | 798 | static SENSOR_DEVICE_ATTR(temp9_input, S_IRUGO, show_temp, NULL, 8); |
| 772 | static SENSOR_DEVICE_ATTR(temp10_input, S_IRUGO, show_temp, NULL, 9); | 799 | static SENSOR_DEVICE_ATTR(temp10_input, S_IRUGO, show_temp, NULL, 9); |
| 773 | 800 | ||
| 801 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, | ||
| 802 | ADT7470_R1T_ALARM); | ||
| 803 | static SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, show_alarm, NULL, | ||
| 804 | ADT7470_R2T_ALARM); | ||
| 805 | static SENSOR_DEVICE_ATTR(temp3_alarm, S_IRUGO, show_alarm, NULL, | ||
| 806 | ADT7470_R3T_ALARM); | ||
| 807 | static SENSOR_DEVICE_ATTR(temp4_alarm, S_IRUGO, show_alarm, NULL, | ||
| 808 | ADT7470_R4T_ALARM); | ||
| 809 | static SENSOR_DEVICE_ATTR(temp5_alarm, S_IRUGO, show_alarm, NULL, | ||
| 810 | ADT7470_R5T_ALARM); | ||
| 811 | static SENSOR_DEVICE_ATTR(temp6_alarm, S_IRUGO, show_alarm, NULL, | ||
| 812 | ADT7470_R6T_ALARM); | ||
| 813 | static SENSOR_DEVICE_ATTR(temp7_alarm, S_IRUGO, show_alarm, NULL, | ||
| 814 | ADT7470_R7T_ALARM); | ||
| 815 | static SENSOR_DEVICE_ATTR(temp8_alarm, S_IRUGO, show_alarm, NULL, | ||
| 816 | ALARM2(ADT7470_R8T_ALARM)); | ||
| 817 | static SENSOR_DEVICE_ATTR(temp9_alarm, S_IRUGO, show_alarm, NULL, | ||
| 818 | ALARM2(ADT7470_R9T_ALARM)); | ||
| 819 | static SENSOR_DEVICE_ATTR(temp10_alarm, S_IRUGO, show_alarm, NULL, | ||
| 820 | ALARM2(ADT7470_R10T_ALARM)); | ||
| 821 | |||
| 774 | static SENSOR_DEVICE_ATTR(fan1_max, S_IWUSR | S_IRUGO, show_fan_max, | 822 | static SENSOR_DEVICE_ATTR(fan1_max, S_IWUSR | S_IRUGO, show_fan_max, |
| 775 | set_fan_max, 0); | 823 | set_fan_max, 0); |
| 776 | static SENSOR_DEVICE_ATTR(fan2_max, S_IWUSR | S_IRUGO, show_fan_max, | 824 | static SENSOR_DEVICE_ATTR(fan2_max, S_IWUSR | S_IRUGO, show_fan_max, |
| @@ -794,6 +842,15 @@ static SENSOR_DEVICE_ATTR(fan2_input, S_IRUGO, show_fan, NULL, 1); | |||
| 794 | static SENSOR_DEVICE_ATTR(fan3_input, S_IRUGO, show_fan, NULL, 2); | 842 | static SENSOR_DEVICE_ATTR(fan3_input, S_IRUGO, show_fan, NULL, 2); |
| 795 | static SENSOR_DEVICE_ATTR(fan4_input, S_IRUGO, show_fan, NULL, 3); | 843 | static SENSOR_DEVICE_ATTR(fan4_input, S_IRUGO, show_fan, NULL, 3); |
| 796 | 844 | ||
| 845 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, | ||
| 846 | ALARM2(ADT7470_FAN1_ALARM)); | ||
| 847 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, | ||
| 848 | ALARM2(ADT7470_FAN2_ALARM)); | ||
| 849 | static SENSOR_DEVICE_ATTR(fan3_alarm, S_IRUGO, show_alarm, NULL, | ||
| 850 | ALARM2(ADT7470_FAN3_ALARM)); | ||
| 851 | static SENSOR_DEVICE_ATTR(fan4_alarm, S_IRUGO, show_alarm, NULL, | ||
| 852 | ALARM2(ADT7470_FAN4_ALARM)); | ||
| 853 | |||
| 797 | static SENSOR_DEVICE_ATTR(force_pwm_max, S_IWUSR | S_IRUGO, | 854 | static SENSOR_DEVICE_ATTR(force_pwm_max, S_IWUSR | S_IRUGO, |
| 798 | show_force_pwm_max, set_force_pwm_max, 0); | 855 | show_force_pwm_max, set_force_pwm_max, 0); |
| 799 | 856 | ||
| @@ -858,8 +915,7 @@ static SENSOR_DEVICE_ATTR(pwm4_auto_channels_temp, S_IWUSR | S_IRUGO, | |||
| 858 | 915 | ||
| 859 | static struct attribute *adt7470_attr[] = | 916 | static struct attribute *adt7470_attr[] = |
| 860 | { | 917 | { |
| 861 | &sensor_dev_attr_alarms.dev_attr.attr, | 918 | &dev_attr_alarm_mask.attr, |
| 862 | &sensor_dev_attr_alarm_mask.dev_attr.attr, | ||
| 863 | &sensor_dev_attr_temp1_max.dev_attr.attr, | 919 | &sensor_dev_attr_temp1_max.dev_attr.attr, |
| 864 | &sensor_dev_attr_temp2_max.dev_attr.attr, | 920 | &sensor_dev_attr_temp2_max.dev_attr.attr, |
| 865 | &sensor_dev_attr_temp3_max.dev_attr.attr, | 921 | &sensor_dev_attr_temp3_max.dev_attr.attr, |
| @@ -890,6 +946,16 @@ static struct attribute *adt7470_attr[] = | |||
| 890 | &sensor_dev_attr_temp8_input.dev_attr.attr, | 946 | &sensor_dev_attr_temp8_input.dev_attr.attr, |
| 891 | &sensor_dev_attr_temp9_input.dev_attr.attr, | 947 | &sensor_dev_attr_temp9_input.dev_attr.attr, |
| 892 | &sensor_dev_attr_temp10_input.dev_attr.attr, | 948 | &sensor_dev_attr_temp10_input.dev_attr.attr, |
| 949 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 950 | &sensor_dev_attr_temp2_alarm.dev_attr.attr, | ||
| 951 | &sensor_dev_attr_temp3_alarm.dev_attr.attr, | ||
| 952 | &sensor_dev_attr_temp4_alarm.dev_attr.attr, | ||
| 953 | &sensor_dev_attr_temp5_alarm.dev_attr.attr, | ||
| 954 | &sensor_dev_attr_temp6_alarm.dev_attr.attr, | ||
| 955 | &sensor_dev_attr_temp7_alarm.dev_attr.attr, | ||
| 956 | &sensor_dev_attr_temp8_alarm.dev_attr.attr, | ||
| 957 | &sensor_dev_attr_temp9_alarm.dev_attr.attr, | ||
| 958 | &sensor_dev_attr_temp10_alarm.dev_attr.attr, | ||
| 893 | &sensor_dev_attr_fan1_max.dev_attr.attr, | 959 | &sensor_dev_attr_fan1_max.dev_attr.attr, |
| 894 | &sensor_dev_attr_fan2_max.dev_attr.attr, | 960 | &sensor_dev_attr_fan2_max.dev_attr.attr, |
| 895 | &sensor_dev_attr_fan3_max.dev_attr.attr, | 961 | &sensor_dev_attr_fan3_max.dev_attr.attr, |
| @@ -902,6 +968,10 @@ static struct attribute *adt7470_attr[] = | |||
| 902 | &sensor_dev_attr_fan2_input.dev_attr.attr, | 968 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 903 | &sensor_dev_attr_fan3_input.dev_attr.attr, | 969 | &sensor_dev_attr_fan3_input.dev_attr.attr, |
| 904 | &sensor_dev_attr_fan4_input.dev_attr.attr, | 970 | &sensor_dev_attr_fan4_input.dev_attr.attr, |
| 971 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 972 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | ||
| 973 | &sensor_dev_attr_fan3_alarm.dev_attr.attr, | ||
| 974 | &sensor_dev_attr_fan4_alarm.dev_attr.attr, | ||
| 905 | &sensor_dev_attr_force_pwm_max.dev_attr.attr, | 975 | &sensor_dev_attr_force_pwm_max.dev_attr.attr, |
| 906 | &sensor_dev_attr_pwm1.dev_attr.attr, | 976 | &sensor_dev_attr_pwm1.dev_attr.attr, |
| 907 | &sensor_dev_attr_pwm2.dev_attr.attr, | 977 | &sensor_dev_attr_pwm2.dev_attr.attr, |
diff --git a/drivers/hwmon/asb100.c b/drivers/hwmon/asb100.c index 9460dba4cf74..950cea8d1d65 100644 --- a/drivers/hwmon/asb100.c +++ b/drivers/hwmon/asb100.c | |||
| @@ -40,6 +40,7 @@ | |||
| 40 | #include <linux/slab.h> | 40 | #include <linux/slab.h> |
| 41 | #include <linux/i2c.h> | 41 | #include <linux/i2c.h> |
| 42 | #include <linux/hwmon.h> | 42 | #include <linux/hwmon.h> |
| 43 | #include <linux/hwmon-sysfs.h> | ||
| 43 | #include <linux/hwmon-vid.h> | 44 | #include <linux/hwmon-vid.h> |
| 44 | #include <linux/err.h> | 45 | #include <linux/err.h> |
| 45 | #include <linux/init.h> | 46 | #include <linux/init.h> |
| @@ -47,12 +48,6 @@ | |||
| 47 | #include <linux/mutex.h> | 48 | #include <linux/mutex.h> |
| 48 | #include "lm75.h" | 49 | #include "lm75.h" |
| 49 | 50 | ||
| 50 | /* | ||
| 51 | HISTORY: | ||
| 52 | 2003-12-29 1.0.0 Ported from lm_sensors project for kernel 2.6 | ||
| 53 | */ | ||
| 54 | #define ASB100_VERSION "1.0.0" | ||
| 55 | |||
| 56 | /* I2C addresses to scan */ | 51 | /* I2C addresses to scan */ |
| 57 | static unsigned short normal_i2c[] = { 0x2d, I2C_CLIENT_END }; | 52 | static unsigned short normal_i2c[] = { 0x2d, I2C_CLIENT_END }; |
| 58 | 53 | ||
| @@ -221,15 +216,16 @@ static struct i2c_driver asb100_driver = { | |||
| 221 | .driver = { | 216 | .driver = { |
| 222 | .name = "asb100", | 217 | .name = "asb100", |
| 223 | }, | 218 | }, |
| 224 | .id = I2C_DRIVERID_ASB100, | ||
| 225 | .attach_adapter = asb100_attach_adapter, | 219 | .attach_adapter = asb100_attach_adapter, |
| 226 | .detach_client = asb100_detach_client, | 220 | .detach_client = asb100_detach_client, |
| 227 | }; | 221 | }; |
| 228 | 222 | ||
| 229 | /* 7 Voltages */ | 223 | /* 7 Voltages */ |
| 230 | #define show_in_reg(reg) \ | 224 | #define show_in_reg(reg) \ |
| 231 | static ssize_t show_##reg (struct device *dev, char *buf, int nr) \ | 225 | static ssize_t show_##reg(struct device *dev, struct device_attribute *attr, \ |
| 226 | char *buf) \ | ||
| 232 | { \ | 227 | { \ |
| 228 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 233 | struct asb100_data *data = asb100_update_device(dev); \ | 229 | struct asb100_data *data = asb100_update_device(dev); \ |
| 234 | return sprintf(buf, "%d\n", IN_FROM_REG(data->reg[nr])); \ | 230 | return sprintf(buf, "%d\n", IN_FROM_REG(data->reg[nr])); \ |
| 235 | } | 231 | } |
| @@ -239,9 +235,10 @@ show_in_reg(in_min) | |||
| 239 | show_in_reg(in_max) | 235 | show_in_reg(in_max) |
| 240 | 236 | ||
| 241 | #define set_in_reg(REG, reg) \ | 237 | #define set_in_reg(REG, reg) \ |
| 242 | static ssize_t set_in_##reg(struct device *dev, const char *buf, \ | 238 | static ssize_t set_in_##reg(struct device *dev, struct device_attribute *attr, \ |
| 243 | size_t count, int nr) \ | 239 | const char *buf, size_t count) \ |
| 244 | { \ | 240 | { \ |
| 241 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 245 | struct i2c_client *client = to_i2c_client(dev); \ | 242 | struct i2c_client *client = to_i2c_client(dev); \ |
| 246 | struct asb100_data *data = i2c_get_clientdata(client); \ | 243 | struct asb100_data *data = i2c_get_clientdata(client); \ |
| 247 | unsigned long val = simple_strtoul(buf, NULL, 10); \ | 244 | unsigned long val = simple_strtoul(buf, NULL, 10); \ |
| @@ -258,37 +255,12 @@ set_in_reg(MIN, min) | |||
| 258 | set_in_reg(MAX, max) | 255 | set_in_reg(MAX, max) |
| 259 | 256 | ||
| 260 | #define sysfs_in(offset) \ | 257 | #define sysfs_in(offset) \ |
| 261 | static ssize_t \ | 258 | static SENSOR_DEVICE_ATTR(in##offset##_input, S_IRUGO, \ |
| 262 | show_in##offset (struct device *dev, struct device_attribute *attr, char *buf) \ | 259 | show_in, NULL, offset); \ |
| 263 | { \ | 260 | static SENSOR_DEVICE_ATTR(in##offset##_min, S_IRUGO | S_IWUSR, \ |
| 264 | return show_in(dev, buf, offset); \ | 261 | show_in_min, set_in_min, offset); \ |
| 265 | } \ | 262 | static SENSOR_DEVICE_ATTR(in##offset##_max, S_IRUGO | S_IWUSR, \ |
| 266 | static DEVICE_ATTR(in##offset##_input, S_IRUGO, \ | 263 | show_in_max, set_in_max, offset) |
| 267 | show_in##offset, NULL); \ | ||
| 268 | static ssize_t \ | ||
| 269 | show_in##offset##_min (struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 270 | { \ | ||
| 271 | return show_in_min(dev, buf, offset); \ | ||
| 272 | } \ | ||
| 273 | static ssize_t \ | ||
| 274 | show_in##offset##_max (struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 275 | { \ | ||
| 276 | return show_in_max(dev, buf, offset); \ | ||
| 277 | } \ | ||
| 278 | static ssize_t set_in##offset##_min (struct device *dev, struct device_attribute *attr, \ | ||
| 279 | const char *buf, size_t count) \ | ||
| 280 | { \ | ||
| 281 | return set_in_min(dev, buf, count, offset); \ | ||
| 282 | } \ | ||
| 283 | static ssize_t set_in##offset##_max (struct device *dev, struct device_attribute *attr, \ | ||
| 284 | const char *buf, size_t count) \ | ||
| 285 | { \ | ||
| 286 | return set_in_max(dev, buf, count, offset); \ | ||
| 287 | } \ | ||
| 288 | static DEVICE_ATTR(in##offset##_min, S_IRUGO | S_IWUSR, \ | ||
| 289 | show_in##offset##_min, set_in##offset##_min); \ | ||
| 290 | static DEVICE_ATTR(in##offset##_max, S_IRUGO | S_IWUSR, \ | ||
| 291 | show_in##offset##_max, set_in##offset##_max); | ||
| 292 | 264 | ||
| 293 | sysfs_in(0); | 265 | sysfs_in(0); |
| 294 | sysfs_in(1); | 266 | sysfs_in(1); |
| @@ -299,29 +271,36 @@ sysfs_in(5); | |||
| 299 | sysfs_in(6); | 271 | sysfs_in(6); |
| 300 | 272 | ||
| 301 | /* 3 Fans */ | 273 | /* 3 Fans */ |
| 302 | static ssize_t show_fan(struct device *dev, char *buf, int nr) | 274 | static ssize_t show_fan(struct device *dev, struct device_attribute *attr, |
| 275 | char *buf) | ||
| 303 | { | 276 | { |
| 277 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 304 | struct asb100_data *data = asb100_update_device(dev); | 278 | struct asb100_data *data = asb100_update_device(dev); |
| 305 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan[nr], | 279 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan[nr], |
| 306 | DIV_FROM_REG(data->fan_div[nr]))); | 280 | DIV_FROM_REG(data->fan_div[nr]))); |
| 307 | } | 281 | } |
| 308 | 282 | ||
| 309 | static ssize_t show_fan_min(struct device *dev, char *buf, int nr) | 283 | static ssize_t show_fan_min(struct device *dev, struct device_attribute *attr, |
| 284 | char *buf) | ||
| 310 | { | 285 | { |
| 286 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 311 | struct asb100_data *data = asb100_update_device(dev); | 287 | struct asb100_data *data = asb100_update_device(dev); |
| 312 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_min[nr], | 288 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_min[nr], |
| 313 | DIV_FROM_REG(data->fan_div[nr]))); | 289 | DIV_FROM_REG(data->fan_div[nr]))); |
| 314 | } | 290 | } |
| 315 | 291 | ||
| 316 | static ssize_t show_fan_div(struct device *dev, char *buf, int nr) | 292 | static ssize_t show_fan_div(struct device *dev, struct device_attribute *attr, |
| 293 | char *buf) | ||
| 317 | { | 294 | { |
| 295 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 318 | struct asb100_data *data = asb100_update_device(dev); | 296 | struct asb100_data *data = asb100_update_device(dev); |
| 319 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->fan_div[nr])); | 297 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->fan_div[nr])); |
| 320 | } | 298 | } |
| 321 | 299 | ||
| 322 | static ssize_t set_fan_min(struct device *dev, const char *buf, | 300 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, |
| 323 | size_t count, int nr) | 301 | const char *buf, size_t count) |
| 324 | { | 302 | { |
| 303 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 325 | struct i2c_client *client = to_i2c_client(dev); | 304 | struct i2c_client *client = to_i2c_client(dev); |
| 326 | struct asb100_data *data = i2c_get_clientdata(client); | 305 | struct asb100_data *data = i2c_get_clientdata(client); |
| 327 | u32 val = simple_strtoul(buf, NULL, 10); | 306 | u32 val = simple_strtoul(buf, NULL, 10); |
| @@ -337,22 +316,23 @@ static ssize_t set_fan_min(struct device *dev, const char *buf, | |||
| 337 | determined in part by the fan divisor. This follows the principle of | 316 | determined in part by the fan divisor. This follows the principle of |
| 338 | least surprise; the user doesn't expect the fan minimum to change just | 317 | least surprise; the user doesn't expect the fan minimum to change just |
| 339 | because the divisor changed. */ | 318 | because the divisor changed. */ |
| 340 | static ssize_t set_fan_div(struct device *dev, const char *buf, | 319 | static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, |
| 341 | size_t count, int nr) | 320 | const char *buf, size_t count) |
| 342 | { | 321 | { |
| 322 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 343 | struct i2c_client *client = to_i2c_client(dev); | 323 | struct i2c_client *client = to_i2c_client(dev); |
| 344 | struct asb100_data *data = i2c_get_clientdata(client); | 324 | struct asb100_data *data = i2c_get_clientdata(client); |
| 345 | unsigned long min; | 325 | unsigned long min; |
| 346 | unsigned long val = simple_strtoul(buf, NULL, 10); | 326 | unsigned long val = simple_strtoul(buf, NULL, 10); |
| 347 | int reg; | 327 | int reg; |
| 348 | 328 | ||
| 349 | mutex_lock(&data->update_lock); | 329 | mutex_lock(&data->update_lock); |
| 350 | 330 | ||
| 351 | min = FAN_FROM_REG(data->fan_min[nr], | 331 | min = FAN_FROM_REG(data->fan_min[nr], |
| 352 | DIV_FROM_REG(data->fan_div[nr])); | 332 | DIV_FROM_REG(data->fan_div[nr])); |
| 353 | data->fan_div[nr] = DIV_TO_REG(val); | 333 | data->fan_div[nr] = DIV_TO_REG(val); |
| 354 | 334 | ||
| 355 | switch(nr) { | 335 | switch (nr) { |
| 356 | case 0: /* fan 1 */ | 336 | case 0: /* fan 1 */ |
| 357 | reg = asb100_read_value(client, ASB100_REG_VID_FANDIV); | 337 | reg = asb100_read_value(client, ASB100_REG_VID_FANDIV); |
| 358 | reg = (reg & 0xcf) | (data->fan_div[0] << 4); | 338 | reg = (reg & 0xcf) | (data->fan_div[0] << 4); |
| @@ -382,34 +362,12 @@ static ssize_t set_fan_div(struct device *dev, const char *buf, | |||
| 382 | } | 362 | } |
| 383 | 363 | ||
| 384 | #define sysfs_fan(offset) \ | 364 | #define sysfs_fan(offset) \ |
| 385 | static ssize_t show_fan##offset(struct device *dev, struct device_attribute *attr, char *buf) \ | 365 | static SENSOR_DEVICE_ATTR(fan##offset##_input, S_IRUGO, \ |
| 386 | { \ | 366 | show_fan, NULL, offset - 1); \ |
| 387 | return show_fan(dev, buf, offset - 1); \ | 367 | static SENSOR_DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \ |
| 388 | } \ | 368 | show_fan_min, set_fan_min, offset - 1); \ |
| 389 | static ssize_t show_fan##offset##_min(struct device *dev, struct device_attribute *attr, char *buf) \ | 369 | static SENSOR_DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \ |
| 390 | { \ | 370 | show_fan_div, set_fan_div, offset - 1) |
| 391 | return show_fan_min(dev, buf, offset - 1); \ | ||
| 392 | } \ | ||
| 393 | static ssize_t show_fan##offset##_div(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 394 | { \ | ||
| 395 | return show_fan_div(dev, buf, offset - 1); \ | ||
| 396 | } \ | ||
| 397 | static ssize_t set_fan##offset##_min(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
| 398 | size_t count) \ | ||
| 399 | { \ | ||
| 400 | return set_fan_min(dev, buf, count, offset - 1); \ | ||
| 401 | } \ | ||
| 402 | static ssize_t set_fan##offset##_div(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
| 403 | size_t count) \ | ||
| 404 | { \ | ||
| 405 | return set_fan_div(dev, buf, count, offset - 1); \ | ||
| 406 | } \ | ||
| 407 | static DEVICE_ATTR(fan##offset##_input, S_IRUGO, \ | ||
| 408 | show_fan##offset, NULL); \ | ||
| 409 | static DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \ | ||
| 410 | show_fan##offset##_min, set_fan##offset##_min); \ | ||
| 411 | static DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \ | ||
| 412 | show_fan##offset##_div, set_fan##offset##_div); | ||
| 413 | 371 | ||
| 414 | sysfs_fan(1); | 372 | sysfs_fan(1); |
| 415 | sysfs_fan(2); | 373 | sysfs_fan(2); |
| @@ -430,10 +388,12 @@ static int sprintf_temp_from_reg(u16 reg, char *buf, int nr) | |||
| 430 | } | 388 | } |
| 431 | return ret; | 389 | return ret; |
| 432 | } | 390 | } |
| 433 | 391 | ||
| 434 | #define show_temp_reg(reg) \ | 392 | #define show_temp_reg(reg) \ |
| 435 | static ssize_t show_##reg(struct device *dev, char *buf, int nr) \ | 393 | static ssize_t show_##reg(struct device *dev, struct device_attribute *attr, \ |
| 394 | char *buf) \ | ||
| 436 | { \ | 395 | { \ |
| 396 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 437 | struct asb100_data *data = asb100_update_device(dev); \ | 397 | struct asb100_data *data = asb100_update_device(dev); \ |
| 438 | return sprintf_temp_from_reg(data->reg[nr], buf, nr); \ | 398 | return sprintf_temp_from_reg(data->reg[nr], buf, nr); \ |
| 439 | } | 399 | } |
| @@ -443,9 +403,10 @@ show_temp_reg(temp_max); | |||
| 443 | show_temp_reg(temp_hyst); | 403 | show_temp_reg(temp_hyst); |
| 444 | 404 | ||
| 445 | #define set_temp_reg(REG, reg) \ | 405 | #define set_temp_reg(REG, reg) \ |
| 446 | static ssize_t set_##reg(struct device *dev, const char *buf, \ | 406 | static ssize_t set_##reg(struct device *dev, struct device_attribute *attr, \ |
| 447 | size_t count, int nr) \ | 407 | const char *buf, size_t count) \ |
| 448 | { \ | 408 | { \ |
| 409 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 449 | struct i2c_client *client = to_i2c_client(dev); \ | 410 | struct i2c_client *client = to_i2c_client(dev); \ |
| 450 | struct asb100_data *data = i2c_get_clientdata(client); \ | 411 | struct asb100_data *data = i2c_get_clientdata(client); \ |
| 451 | long val = simple_strtol(buf, NULL, 10); \ | 412 | long val = simple_strtol(buf, NULL, 10); \ |
| @@ -469,33 +430,12 @@ set_temp_reg(MAX, temp_max); | |||
| 469 | set_temp_reg(HYST, temp_hyst); | 430 | set_temp_reg(HYST, temp_hyst); |
| 470 | 431 | ||
| 471 | #define sysfs_temp(num) \ | 432 | #define sysfs_temp(num) \ |
| 472 | static ssize_t show_temp##num(struct device *dev, struct device_attribute *attr, char *buf) \ | 433 | static SENSOR_DEVICE_ATTR(temp##num##_input, S_IRUGO, \ |
| 473 | { \ | 434 | show_temp, NULL, num - 1); \ |
| 474 | return show_temp(dev, buf, num-1); \ | 435 | static SENSOR_DEVICE_ATTR(temp##num##_max, S_IRUGO | S_IWUSR, \ |
| 475 | } \ | 436 | show_temp_max, set_temp_max, num - 1); \ |
| 476 | static DEVICE_ATTR(temp##num##_input, S_IRUGO, show_temp##num, NULL); \ | 437 | static SENSOR_DEVICE_ATTR(temp##num##_max_hyst, S_IRUGO | S_IWUSR, \ |
| 477 | static ssize_t show_temp_max##num(struct device *dev, struct device_attribute *attr, char *buf) \ | 438 | show_temp_hyst, set_temp_hyst, num - 1) |
| 478 | { \ | ||
| 479 | return show_temp_max(dev, buf, num-1); \ | ||
| 480 | } \ | ||
| 481 | static ssize_t set_temp_max##num(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
| 482 | size_t count) \ | ||
| 483 | { \ | ||
| 484 | return set_temp_max(dev, buf, count, num-1); \ | ||
| 485 | } \ | ||
| 486 | static DEVICE_ATTR(temp##num##_max, S_IRUGO | S_IWUSR, \ | ||
| 487 | show_temp_max##num, set_temp_max##num); \ | ||
| 488 | static ssize_t show_temp_hyst##num(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 489 | { \ | ||
| 490 | return show_temp_hyst(dev, buf, num-1); \ | ||
| 491 | } \ | ||
| 492 | static ssize_t set_temp_hyst##num(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
| 493 | size_t count) \ | ||
| 494 | { \ | ||
| 495 | return set_temp_hyst(dev, buf, count, num-1); \ | ||
| 496 | } \ | ||
| 497 | static DEVICE_ATTR(temp##num##_max_hyst, S_IRUGO | S_IWUSR, \ | ||
| 498 | show_temp_hyst##num, set_temp_hyst##num); | ||
| 499 | 439 | ||
| 500 | sysfs_temp(1); | 440 | sysfs_temp(1); |
| 501 | sysfs_temp(2); | 441 | sysfs_temp(2); |
| @@ -503,7 +443,8 @@ sysfs_temp(3); | |||
| 503 | sysfs_temp(4); | 443 | sysfs_temp(4); |
| 504 | 444 | ||
| 505 | /* VID */ | 445 | /* VID */ |
| 506 | static ssize_t show_vid(struct device *dev, struct device_attribute *attr, char *buf) | 446 | static ssize_t show_vid(struct device *dev, struct device_attribute *attr, |
| 447 | char *buf) | ||
| 507 | { | 448 | { |
| 508 | struct asb100_data *data = asb100_update_device(dev); | 449 | struct asb100_data *data = asb100_update_device(dev); |
| 509 | return sprintf(buf, "%d\n", vid_from_reg(data->vid, data->vrm)); | 450 | return sprintf(buf, "%d\n", vid_from_reg(data->vid, data->vrm)); |
| @@ -512,25 +453,26 @@ static ssize_t show_vid(struct device *dev, struct device_attribute *attr, char | |||
| 512 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid, NULL); | 453 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid, NULL); |
| 513 | 454 | ||
| 514 | /* VRM */ | 455 | /* VRM */ |
| 515 | static ssize_t show_vrm(struct device *dev, struct device_attribute *attr, char *buf) | 456 | static ssize_t show_vrm(struct device *dev, struct device_attribute *attr, |
| 457 | char *buf) | ||
| 516 | { | 458 | { |
| 517 | struct asb100_data *data = dev_get_drvdata(dev); | 459 | struct asb100_data *data = dev_get_drvdata(dev); |
| 518 | return sprintf(buf, "%d\n", data->vrm); | 460 | return sprintf(buf, "%d\n", data->vrm); |
| 519 | } | 461 | } |
| 520 | 462 | ||
| 521 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 463 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, |
| 464 | const char *buf, size_t count) | ||
| 522 | { | 465 | { |
| 523 | struct i2c_client *client = to_i2c_client(dev); | 466 | struct asb100_data *data = dev_get_drvdata(dev); |
| 524 | struct asb100_data *data = i2c_get_clientdata(client); | 467 | data->vrm = simple_strtoul(buf, NULL, 10); |
| 525 | unsigned long val = simple_strtoul(buf, NULL, 10); | ||
| 526 | data->vrm = val; | ||
| 527 | return count; | 468 | return count; |
| 528 | } | 469 | } |
| 529 | 470 | ||
| 530 | /* Alarms */ | 471 | /* Alarms */ |
| 531 | static DEVICE_ATTR(vrm, S_IRUGO | S_IWUSR, show_vrm, set_vrm); | 472 | static DEVICE_ATTR(vrm, S_IRUGO | S_IWUSR, show_vrm, set_vrm); |
| 532 | 473 | ||
| 533 | static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, char *buf) | 474 | static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, |
| 475 | char *buf) | ||
| 534 | { | 476 | { |
| 535 | struct asb100_data *data = asb100_update_device(dev); | 477 | struct asb100_data *data = asb100_update_device(dev); |
| 536 | return sprintf(buf, "%u\n", data->alarms); | 478 | return sprintf(buf, "%u\n", data->alarms); |
| @@ -538,14 +480,35 @@ static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, ch | |||
| 538 | 480 | ||
| 539 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | 481 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); |
| 540 | 482 | ||
| 483 | static ssize_t show_alarm(struct device *dev, struct device_attribute *attr, | ||
| 484 | char *buf) | ||
| 485 | { | ||
| 486 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 487 | struct asb100_data *data = asb100_update_device(dev); | ||
| 488 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); | ||
| 489 | } | ||
| 490 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 491 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 492 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 493 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 494 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 495 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 496 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 7); | ||
| 497 | static SENSOR_DEVICE_ATTR(fan3_alarm, S_IRUGO, show_alarm, NULL, 11); | ||
| 498 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 499 | static SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, show_alarm, NULL, 5); | ||
| 500 | static SENSOR_DEVICE_ATTR(temp3_alarm, S_IRUGO, show_alarm, NULL, 13); | ||
| 501 | |||
| 541 | /* 1 PWM */ | 502 | /* 1 PWM */ |
| 542 | static ssize_t show_pwm1(struct device *dev, struct device_attribute *attr, char *buf) | 503 | static ssize_t show_pwm1(struct device *dev, struct device_attribute *attr, |
| 504 | char *buf) | ||
| 543 | { | 505 | { |
| 544 | struct asb100_data *data = asb100_update_device(dev); | 506 | struct asb100_data *data = asb100_update_device(dev); |
| 545 | return sprintf(buf, "%d\n", ASB100_PWM_FROM_REG(data->pwm & 0x0f)); | 507 | return sprintf(buf, "%d\n", ASB100_PWM_FROM_REG(data->pwm & 0x0f)); |
| 546 | } | 508 | } |
| 547 | 509 | ||
| 548 | static ssize_t set_pwm1(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 510 | static ssize_t set_pwm1(struct device *dev, struct device_attribute *attr, |
| 511 | const char *buf, size_t count) | ||
| 549 | { | 512 | { |
| 550 | struct i2c_client *client = to_i2c_client(dev); | 513 | struct i2c_client *client = to_i2c_client(dev); |
| 551 | struct asb100_data *data = i2c_get_clientdata(client); | 514 | struct asb100_data *data = i2c_get_clientdata(client); |
| @@ -559,14 +522,15 @@ static ssize_t set_pwm1(struct device *dev, struct device_attribute *attr, const | |||
| 559 | return count; | 522 | return count; |
| 560 | } | 523 | } |
| 561 | 524 | ||
| 562 | static ssize_t show_pwm_enable1(struct device *dev, struct device_attribute *attr, char *buf) | 525 | static ssize_t show_pwm_enable1(struct device *dev, |
| 526 | struct device_attribute *attr, char *buf) | ||
| 563 | { | 527 | { |
| 564 | struct asb100_data *data = asb100_update_device(dev); | 528 | struct asb100_data *data = asb100_update_device(dev); |
| 565 | return sprintf(buf, "%d\n", (data->pwm & 0x80) ? 1 : 0); | 529 | return sprintf(buf, "%d\n", (data->pwm & 0x80) ? 1 : 0); |
| 566 | } | 530 | } |
| 567 | 531 | ||
| 568 | static ssize_t set_pwm_enable1(struct device *dev, struct device_attribute *attr, const char *buf, | 532 | static ssize_t set_pwm_enable1(struct device *dev, |
| 569 | size_t count) | 533 | struct device_attribute *attr, const char *buf, size_t count) |
| 570 | { | 534 | { |
| 571 | struct i2c_client *client = to_i2c_client(dev); | 535 | struct i2c_client *client = to_i2c_client(dev); |
| 572 | struct asb100_data *data = i2c_get_clientdata(client); | 536 | struct asb100_data *data = i2c_get_clientdata(client); |
| @@ -585,50 +549,62 @@ static DEVICE_ATTR(pwm1_enable, S_IRUGO | S_IWUSR, | |||
| 585 | show_pwm_enable1, set_pwm_enable1); | 549 | show_pwm_enable1, set_pwm_enable1); |
| 586 | 550 | ||
| 587 | static struct attribute *asb100_attributes[] = { | 551 | static struct attribute *asb100_attributes[] = { |
| 588 | &dev_attr_in0_input.attr, | 552 | &sensor_dev_attr_in0_input.dev_attr.attr, |
| 589 | &dev_attr_in0_min.attr, | 553 | &sensor_dev_attr_in0_min.dev_attr.attr, |
| 590 | &dev_attr_in0_max.attr, | 554 | &sensor_dev_attr_in0_max.dev_attr.attr, |
| 591 | &dev_attr_in1_input.attr, | 555 | &sensor_dev_attr_in1_input.dev_attr.attr, |
| 592 | &dev_attr_in1_min.attr, | 556 | &sensor_dev_attr_in1_min.dev_attr.attr, |
| 593 | &dev_attr_in1_max.attr, | 557 | &sensor_dev_attr_in1_max.dev_attr.attr, |
| 594 | &dev_attr_in2_input.attr, | 558 | &sensor_dev_attr_in2_input.dev_attr.attr, |
| 595 | &dev_attr_in2_min.attr, | 559 | &sensor_dev_attr_in2_min.dev_attr.attr, |
| 596 | &dev_attr_in2_max.attr, | 560 | &sensor_dev_attr_in2_max.dev_attr.attr, |
| 597 | &dev_attr_in3_input.attr, | 561 | &sensor_dev_attr_in3_input.dev_attr.attr, |
| 598 | &dev_attr_in3_min.attr, | 562 | &sensor_dev_attr_in3_min.dev_attr.attr, |
| 599 | &dev_attr_in3_max.attr, | 563 | &sensor_dev_attr_in3_max.dev_attr.attr, |
| 600 | &dev_attr_in4_input.attr, | 564 | &sensor_dev_attr_in4_input.dev_attr.attr, |
| 601 | &dev_attr_in4_min.attr, | 565 | &sensor_dev_attr_in4_min.dev_attr.attr, |
| 602 | &dev_attr_in4_max.attr, | 566 | &sensor_dev_attr_in4_max.dev_attr.attr, |
| 603 | &dev_attr_in5_input.attr, | 567 | &sensor_dev_attr_in5_input.dev_attr.attr, |
| 604 | &dev_attr_in5_min.attr, | 568 | &sensor_dev_attr_in5_min.dev_attr.attr, |
| 605 | &dev_attr_in5_max.attr, | 569 | &sensor_dev_attr_in5_max.dev_attr.attr, |
| 606 | &dev_attr_in6_input.attr, | 570 | &sensor_dev_attr_in6_input.dev_attr.attr, |
| 607 | &dev_attr_in6_min.attr, | 571 | &sensor_dev_attr_in6_min.dev_attr.attr, |
| 608 | &dev_attr_in6_max.attr, | 572 | &sensor_dev_attr_in6_max.dev_attr.attr, |
| 609 | 573 | ||
| 610 | &dev_attr_fan1_input.attr, | 574 | &sensor_dev_attr_fan1_input.dev_attr.attr, |
| 611 | &dev_attr_fan1_min.attr, | 575 | &sensor_dev_attr_fan1_min.dev_attr.attr, |
| 612 | &dev_attr_fan1_div.attr, | 576 | &sensor_dev_attr_fan1_div.dev_attr.attr, |
| 613 | &dev_attr_fan2_input.attr, | 577 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 614 | &dev_attr_fan2_min.attr, | 578 | &sensor_dev_attr_fan2_min.dev_attr.attr, |
| 615 | &dev_attr_fan2_div.attr, | 579 | &sensor_dev_attr_fan2_div.dev_attr.attr, |
| 616 | &dev_attr_fan3_input.attr, | 580 | &sensor_dev_attr_fan3_input.dev_attr.attr, |
| 617 | &dev_attr_fan3_min.attr, | 581 | &sensor_dev_attr_fan3_min.dev_attr.attr, |
| 618 | &dev_attr_fan3_div.attr, | 582 | &sensor_dev_attr_fan3_div.dev_attr.attr, |
| 619 | 583 | ||
| 620 | &dev_attr_temp1_input.attr, | 584 | &sensor_dev_attr_temp1_input.dev_attr.attr, |
| 621 | &dev_attr_temp1_max.attr, | 585 | &sensor_dev_attr_temp1_max.dev_attr.attr, |
| 622 | &dev_attr_temp1_max_hyst.attr, | 586 | &sensor_dev_attr_temp1_max_hyst.dev_attr.attr, |
| 623 | &dev_attr_temp2_input.attr, | 587 | &sensor_dev_attr_temp2_input.dev_attr.attr, |
| 624 | &dev_attr_temp2_max.attr, | 588 | &sensor_dev_attr_temp2_max.dev_attr.attr, |
| 625 | &dev_attr_temp2_max_hyst.attr, | 589 | &sensor_dev_attr_temp2_max_hyst.dev_attr.attr, |
| 626 | &dev_attr_temp3_input.attr, | 590 | &sensor_dev_attr_temp3_input.dev_attr.attr, |
| 627 | &dev_attr_temp3_max.attr, | 591 | &sensor_dev_attr_temp3_max.dev_attr.attr, |
| 628 | &dev_attr_temp3_max_hyst.attr, | 592 | &sensor_dev_attr_temp3_max_hyst.dev_attr.attr, |
| 629 | &dev_attr_temp4_input.attr, | 593 | &sensor_dev_attr_temp4_input.dev_attr.attr, |
| 630 | &dev_attr_temp4_max.attr, | 594 | &sensor_dev_attr_temp4_max.dev_attr.attr, |
| 631 | &dev_attr_temp4_max_hyst.attr, | 595 | &sensor_dev_attr_temp4_max_hyst.dev_attr.attr, |
| 596 | |||
| 597 | &sensor_dev_attr_in0_alarm.dev_attr.attr, | ||
| 598 | &sensor_dev_attr_in1_alarm.dev_attr.attr, | ||
| 599 | &sensor_dev_attr_in2_alarm.dev_attr.attr, | ||
| 600 | &sensor_dev_attr_in3_alarm.dev_attr.attr, | ||
| 601 | &sensor_dev_attr_in4_alarm.dev_attr.attr, | ||
| 602 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 603 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | ||
| 604 | &sensor_dev_attr_fan3_alarm.dev_attr.attr, | ||
| 605 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 606 | &sensor_dev_attr_temp2_alarm.dev_attr.attr, | ||
| 607 | &sensor_dev_attr_temp3_alarm.dev_attr.attr, | ||
| 632 | 608 | ||
| 633 | &dev_attr_cpu0_vid.attr, | 609 | &dev_attr_cpu0_vid.attr, |
| 634 | &dev_attr_vrm.attr, | 610 | &dev_attr_vrm.attr, |
| @@ -656,10 +632,10 @@ static int asb100_attach_adapter(struct i2c_adapter *adapter) | |||
| 656 | } | 632 | } |
| 657 | 633 | ||
| 658 | static int asb100_detect_subclients(struct i2c_adapter *adapter, int address, | 634 | static int asb100_detect_subclients(struct i2c_adapter *adapter, int address, |
| 659 | int kind, struct i2c_client *new_client) | 635 | int kind, struct i2c_client *client) |
| 660 | { | 636 | { |
| 661 | int i, id, err; | 637 | int i, id, err; |
| 662 | struct asb100_data *data = i2c_get_clientdata(new_client); | 638 | struct asb100_data *data = i2c_get_clientdata(client); |
| 663 | 639 | ||
| 664 | data->lm75[0] = kzalloc(sizeof(struct i2c_client), GFP_KERNEL); | 640 | data->lm75[0] = kzalloc(sizeof(struct i2c_client), GFP_KERNEL); |
| 665 | if (!(data->lm75[0])) { | 641 | if (!(data->lm75[0])) { |
| @@ -679,26 +655,26 @@ static int asb100_detect_subclients(struct i2c_adapter *adapter, int address, | |||
| 679 | for (i = 2; i <= 3; i++) { | 655 | for (i = 2; i <= 3; i++) { |
| 680 | if (force_subclients[i] < 0x48 || | 656 | if (force_subclients[i] < 0x48 || |
| 681 | force_subclients[i] > 0x4f) { | 657 | force_subclients[i] > 0x4f) { |
| 682 | dev_err(&new_client->dev, "invalid subclient " | 658 | dev_err(&client->dev, "invalid subclient " |
| 683 | "address %d; must be 0x48-0x4f\n", | 659 | "address %d; must be 0x48-0x4f\n", |
| 684 | force_subclients[i]); | 660 | force_subclients[i]); |
| 685 | err = -ENODEV; | 661 | err = -ENODEV; |
| 686 | goto ERROR_SC_2; | 662 | goto ERROR_SC_2; |
| 687 | } | 663 | } |
| 688 | } | 664 | } |
| 689 | asb100_write_value(new_client, ASB100_REG_I2C_SUBADDR, | 665 | asb100_write_value(client, ASB100_REG_I2C_SUBADDR, |
| 690 | (force_subclients[2] & 0x07) | | 666 | (force_subclients[2] & 0x07) | |
| 691 | ((force_subclients[3] & 0x07) <<4)); | 667 | ((force_subclients[3] & 0x07) << 4)); |
| 692 | data->lm75[0]->addr = force_subclients[2]; | 668 | data->lm75[0]->addr = force_subclients[2]; |
| 693 | data->lm75[1]->addr = force_subclients[3]; | 669 | data->lm75[1]->addr = force_subclients[3]; |
| 694 | } else { | 670 | } else { |
| 695 | int val = asb100_read_value(new_client, ASB100_REG_I2C_SUBADDR); | 671 | int val = asb100_read_value(client, ASB100_REG_I2C_SUBADDR); |
| 696 | data->lm75[0]->addr = 0x48 + (val & 0x07); | 672 | data->lm75[0]->addr = 0x48 + (val & 0x07); |
| 697 | data->lm75[1]->addr = 0x48 + ((val >> 4) & 0x07); | 673 | data->lm75[1]->addr = 0x48 + ((val >> 4) & 0x07); |
| 698 | } | 674 | } |
| 699 | 675 | ||
| 700 | if(data->lm75[0]->addr == data->lm75[1]->addr) { | 676 | if (data->lm75[0]->addr == data->lm75[1]->addr) { |
| 701 | dev_err(&new_client->dev, "duplicate addresses 0x%x " | 677 | dev_err(&client->dev, "duplicate addresses 0x%x " |
| 702 | "for subclients\n", data->lm75[0]->addr); | 678 | "for subclients\n", data->lm75[0]->addr); |
| 703 | err = -ENODEV; | 679 | err = -ENODEV; |
| 704 | goto ERROR_SC_2; | 680 | goto ERROR_SC_2; |
| @@ -708,18 +684,17 @@ static int asb100_detect_subclients(struct i2c_adapter *adapter, int address, | |||
| 708 | i2c_set_clientdata(data->lm75[i], NULL); | 684 | i2c_set_clientdata(data->lm75[i], NULL); |
| 709 | data->lm75[i]->adapter = adapter; | 685 | data->lm75[i]->adapter = adapter; |
| 710 | data->lm75[i]->driver = &asb100_driver; | 686 | data->lm75[i]->driver = &asb100_driver; |
| 711 | data->lm75[i]->flags = 0; | ||
| 712 | strlcpy(data->lm75[i]->name, "asb100 subclient", I2C_NAME_SIZE); | 687 | strlcpy(data->lm75[i]->name, "asb100 subclient", I2C_NAME_SIZE); |
| 713 | } | 688 | } |
| 714 | 689 | ||
| 715 | if ((err = i2c_attach_client(data->lm75[0]))) { | 690 | if ((err = i2c_attach_client(data->lm75[0]))) { |
| 716 | dev_err(&new_client->dev, "subclient %d registration " | 691 | dev_err(&client->dev, "subclient %d registration " |
| 717 | "at address 0x%x failed.\n", i, data->lm75[0]->addr); | 692 | "at address 0x%x failed.\n", i, data->lm75[0]->addr); |
| 718 | goto ERROR_SC_2; | 693 | goto ERROR_SC_2; |
| 719 | } | 694 | } |
| 720 | 695 | ||
| 721 | if ((err = i2c_attach_client(data->lm75[1]))) { | 696 | if ((err = i2c_attach_client(data->lm75[1]))) { |
| 722 | dev_err(&new_client->dev, "subclient %d registration " | 697 | dev_err(&client->dev, "subclient %d registration " |
| 723 | "at address 0x%x failed.\n", i, data->lm75[1]->addr); | 698 | "at address 0x%x failed.\n", i, data->lm75[1]->addr); |
| 724 | goto ERROR_SC_3; | 699 | goto ERROR_SC_3; |
| 725 | } | 700 | } |
| @@ -740,7 +715,7 @@ ERROR_SC_0: | |||
| 740 | static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | 715 | static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) |
| 741 | { | 716 | { |
| 742 | int err; | 717 | int err; |
| 743 | struct i2c_client *new_client; | 718 | struct i2c_client *client; |
| 744 | struct asb100_data *data; | 719 | struct asb100_data *data; |
| 745 | 720 | ||
| 746 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) { | 721 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) { |
| @@ -760,13 +735,12 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 760 | goto ERROR0; | 735 | goto ERROR0; |
| 761 | } | 736 | } |
| 762 | 737 | ||
| 763 | new_client = &data->client; | 738 | client = &data->client; |
| 764 | mutex_init(&data->lock); | 739 | mutex_init(&data->lock); |
| 765 | i2c_set_clientdata(new_client, data); | 740 | i2c_set_clientdata(client, data); |
| 766 | new_client->addr = address; | 741 | client->addr = address; |
| 767 | new_client->adapter = adapter; | 742 | client->adapter = adapter; |
| 768 | new_client->driver = &asb100_driver; | 743 | client->driver = &asb100_driver; |
| 769 | new_client->flags = 0; | ||
| 770 | 744 | ||
| 771 | /* Now, we do the remaining detection. */ | 745 | /* Now, we do the remaining detection. */ |
| 772 | 746 | ||
| @@ -776,15 +750,15 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 776 | bank. */ | 750 | bank. */ |
| 777 | if (kind < 0) { | 751 | if (kind < 0) { |
| 778 | 752 | ||
| 779 | int val1 = asb100_read_value(new_client, ASB100_REG_BANK); | 753 | int val1 = asb100_read_value(client, ASB100_REG_BANK); |
| 780 | int val2 = asb100_read_value(new_client, ASB100_REG_CHIPMAN); | 754 | int val2 = asb100_read_value(client, ASB100_REG_CHIPMAN); |
| 781 | 755 | ||
| 782 | /* If we're in bank 0 */ | 756 | /* If we're in bank 0 */ |
| 783 | if ( (!(val1 & 0x07)) && | 757 | if ((!(val1 & 0x07)) && |
| 784 | /* Check for ASB100 ID (low byte) */ | 758 | /* Check for ASB100 ID (low byte) */ |
| 785 | ( ((!(val1 & 0x80)) && (val2 != 0x94)) || | 759 | (((!(val1 & 0x80)) && (val2 != 0x94)) || |
| 786 | /* Check for ASB100 ID (high byte ) */ | 760 | /* Check for ASB100 ID (high byte ) */ |
| 787 | ((val1 & 0x80) && (val2 != 0x06)) ) ) { | 761 | ((val1 & 0x80) && (val2 != 0x06)))) { |
| 788 | pr_debug("asb100.o: detect failed, " | 762 | pr_debug("asb100.o: detect failed, " |
| 789 | "bad chip id 0x%02x!\n", val2); | 763 | "bad chip id 0x%02x!\n", val2); |
| 790 | err = -ENODEV; | 764 | err = -ENODEV; |
| @@ -795,19 +769,19 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 795 | 769 | ||
| 796 | /* We have either had a force parameter, or we have already detected | 770 | /* We have either had a force parameter, or we have already detected |
| 797 | Winbond. Put it now into bank 0 and Vendor ID High Byte */ | 771 | Winbond. Put it now into bank 0 and Vendor ID High Byte */ |
| 798 | asb100_write_value(new_client, ASB100_REG_BANK, | 772 | asb100_write_value(client, ASB100_REG_BANK, |
| 799 | (asb100_read_value(new_client, ASB100_REG_BANK) & 0x78) | 0x80); | 773 | (asb100_read_value(client, ASB100_REG_BANK) & 0x78) | 0x80); |
| 800 | 774 | ||
| 801 | /* Determine the chip type. */ | 775 | /* Determine the chip type. */ |
| 802 | if (kind <= 0) { | 776 | if (kind <= 0) { |
| 803 | int val1 = asb100_read_value(new_client, ASB100_REG_WCHIPID); | 777 | int val1 = asb100_read_value(client, ASB100_REG_WCHIPID); |
| 804 | int val2 = asb100_read_value(new_client, ASB100_REG_CHIPMAN); | 778 | int val2 = asb100_read_value(client, ASB100_REG_CHIPMAN); |
| 805 | 779 | ||
| 806 | if ((val1 == 0x31) && (val2 == 0x06)) | 780 | if ((val1 == 0x31) && (val2 == 0x06)) |
| 807 | kind = asb100; | 781 | kind = asb100; |
| 808 | else { | 782 | else { |
| 809 | if (kind == 0) | 783 | if (kind == 0) |
| 810 | dev_warn(&new_client->dev, "ignoring " | 784 | dev_warn(&client->dev, "ignoring " |
| 811 | "'force' parameter for unknown chip " | 785 | "'force' parameter for unknown chip " |
| 812 | "at adapter %d, address 0x%02x.\n", | 786 | "at adapter %d, address 0x%02x.\n", |
| 813 | i2c_adapter_id(adapter), address); | 787 | i2c_adapter_id(adapter), address); |
| @@ -817,34 +791,32 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 817 | } | 791 | } |
| 818 | 792 | ||
| 819 | /* Fill in remaining client fields and put it into the global list */ | 793 | /* Fill in remaining client fields and put it into the global list */ |
| 820 | strlcpy(new_client->name, "asb100", I2C_NAME_SIZE); | 794 | strlcpy(client->name, "asb100", I2C_NAME_SIZE); |
| 821 | data->type = kind; | 795 | data->type = kind; |
| 822 | |||
| 823 | data->valid = 0; | ||
| 824 | mutex_init(&data->update_lock); | 796 | mutex_init(&data->update_lock); |
| 825 | 797 | ||
| 826 | /* Tell the I2C layer a new client has arrived */ | 798 | /* Tell the I2C layer a new client has arrived */ |
| 827 | if ((err = i2c_attach_client(new_client))) | 799 | if ((err = i2c_attach_client(client))) |
| 828 | goto ERROR1; | 800 | goto ERROR1; |
| 829 | 801 | ||
| 830 | /* Attach secondary lm75 clients */ | 802 | /* Attach secondary lm75 clients */ |
| 831 | if ((err = asb100_detect_subclients(adapter, address, kind, | 803 | if ((err = asb100_detect_subclients(adapter, address, kind, |
| 832 | new_client))) | 804 | client))) |
| 833 | goto ERROR2; | 805 | goto ERROR2; |
| 834 | 806 | ||
| 835 | /* Initialize the chip */ | 807 | /* Initialize the chip */ |
| 836 | asb100_init_client(new_client); | 808 | asb100_init_client(client); |
| 837 | 809 | ||
| 838 | /* A few vars need to be filled upon startup */ | 810 | /* A few vars need to be filled upon startup */ |
| 839 | data->fan_min[0] = asb100_read_value(new_client, ASB100_REG_FAN_MIN(0)); | 811 | data->fan_min[0] = asb100_read_value(client, ASB100_REG_FAN_MIN(0)); |
| 840 | data->fan_min[1] = asb100_read_value(new_client, ASB100_REG_FAN_MIN(1)); | 812 | data->fan_min[1] = asb100_read_value(client, ASB100_REG_FAN_MIN(1)); |
| 841 | data->fan_min[2] = asb100_read_value(new_client, ASB100_REG_FAN_MIN(2)); | 813 | data->fan_min[2] = asb100_read_value(client, ASB100_REG_FAN_MIN(2)); |
| 842 | 814 | ||
| 843 | /* Register sysfs hooks */ | 815 | /* Register sysfs hooks */ |
| 844 | if ((err = sysfs_create_group(&new_client->dev.kobj, &asb100_group))) | 816 | if ((err = sysfs_create_group(&client->dev.kobj, &asb100_group))) |
| 845 | goto ERROR3; | 817 | goto ERROR3; |
| 846 | 818 | ||
| 847 | data->hwmon_dev = hwmon_device_register(&new_client->dev); | 819 | data->hwmon_dev = hwmon_device_register(&client->dev); |
| 848 | if (IS_ERR(data->hwmon_dev)) { | 820 | if (IS_ERR(data->hwmon_dev)) { |
| 849 | err = PTR_ERR(data->hwmon_dev); | 821 | err = PTR_ERR(data->hwmon_dev); |
| 850 | goto ERROR4; | 822 | goto ERROR4; |
| @@ -853,14 +825,14 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 853 | return 0; | 825 | return 0; |
| 854 | 826 | ||
| 855 | ERROR4: | 827 | ERROR4: |
| 856 | sysfs_remove_group(&new_client->dev.kobj, &asb100_group); | 828 | sysfs_remove_group(&client->dev.kobj, &asb100_group); |
| 857 | ERROR3: | 829 | ERROR3: |
| 858 | i2c_detach_client(data->lm75[1]); | 830 | i2c_detach_client(data->lm75[1]); |
| 859 | i2c_detach_client(data->lm75[0]); | 831 | i2c_detach_client(data->lm75[0]); |
| 860 | kfree(data->lm75[1]); | 832 | kfree(data->lm75[1]); |
| 861 | kfree(data->lm75[0]); | 833 | kfree(data->lm75[0]); |
| 862 | ERROR2: | 834 | ERROR2: |
| 863 | i2c_detach_client(new_client); | 835 | i2c_detach_client(client); |
| 864 | ERROR1: | 836 | ERROR1: |
| 865 | kfree(data); | 837 | kfree(data); |
| 866 | ERROR0: | 838 | ERROR0: |
| @@ -916,17 +888,17 @@ static int asb100_read_value(struct i2c_client *client, u16 reg) | |||
| 916 | /* convert from ISA to LM75 I2C addresses */ | 888 | /* convert from ISA to LM75 I2C addresses */ |
| 917 | switch (reg & 0xff) { | 889 | switch (reg & 0xff) { |
| 918 | case 0x50: /* TEMP */ | 890 | case 0x50: /* TEMP */ |
| 919 | res = swab16(i2c_smbus_read_word_data (cl, 0)); | 891 | res = swab16(i2c_smbus_read_word_data(cl, 0)); |
| 920 | break; | 892 | break; |
| 921 | case 0x52: /* CONFIG */ | 893 | case 0x52: /* CONFIG */ |
| 922 | res = i2c_smbus_read_byte_data(cl, 1); | 894 | res = i2c_smbus_read_byte_data(cl, 1); |
| 923 | break; | 895 | break; |
| 924 | case 0x53: /* HYST */ | 896 | case 0x53: /* HYST */ |
| 925 | res = swab16(i2c_smbus_read_word_data (cl, 2)); | 897 | res = swab16(i2c_smbus_read_word_data(cl, 2)); |
| 926 | break; | 898 | break; |
| 927 | case 0x55: /* MAX */ | 899 | case 0x55: /* MAX */ |
| 928 | default: | 900 | default: |
| 929 | res = swab16(i2c_smbus_read_word_data (cl, 3)); | 901 | res = swab16(i2c_smbus_read_word_data(cl, 3)); |
| 930 | break; | 902 | break; |
| 931 | } | 903 | } |
| 932 | } | 904 | } |
| @@ -989,7 +961,7 @@ static void asb100_init_client(struct i2c_client *client) | |||
| 989 | vid = vid_from_reg(vid, data->vrm); | 961 | vid = vid_from_reg(vid, data->vrm); |
| 990 | 962 | ||
| 991 | /* Start monitoring */ | 963 | /* Start monitoring */ |
| 992 | asb100_write_value(client, ASB100_REG_CONFIG, | 964 | asb100_write_value(client, ASB100_REG_CONFIG, |
| 993 | (asb100_read_value(client, ASB100_REG_CONFIG) & 0xf7) | 0x01); | 965 | (asb100_read_value(client, ASB100_REG_CONFIG) & 0xf7) | 0x01); |
| 994 | } | 966 | } |
| 995 | 967 | ||
| @@ -1078,4 +1050,3 @@ MODULE_LICENSE("GPL"); | |||
| 1078 | 1050 | ||
| 1079 | module_init(asb100_init); | 1051 | module_init(asb100_init); |
| 1080 | module_exit(asb100_exit); | 1052 | module_exit(asb100_exit); |
| 1081 | |||
diff --git a/drivers/hwmon/dme1737.c b/drivers/hwmon/dme1737.c index a878c98e252e..ddddd9f34c19 100644 --- a/drivers/hwmon/dme1737.c +++ b/drivers/hwmon/dme1737.c | |||
| @@ -44,6 +44,10 @@ static int force_start; | |||
| 44 | module_param(force_start, bool, 0); | 44 | module_param(force_start, bool, 0); |
| 45 | MODULE_PARM_DESC(force_start, "Force the chip to start monitoring inputs"); | 45 | MODULE_PARM_DESC(force_start, "Force the chip to start monitoring inputs"); |
| 46 | 46 | ||
| 47 | static unsigned short force_id; | ||
| 48 | module_param(force_id, ushort, 0); | ||
| 49 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 50 | |||
| 47 | /* Addresses to scan */ | 51 | /* Addresses to scan */ |
| 48 | static unsigned short normal_i2c[] = {0x2c, 0x2d, 0x2e, I2C_CLIENT_END}; | 52 | static unsigned short normal_i2c[] = {0x2c, 0x2d, 0x2e, I2C_CLIENT_END}; |
| 49 | 53 | ||
| @@ -279,14 +283,21 @@ static inline int TEMP_HYST_TO_REG(int val, int ix, int reg) | |||
| 279 | /* Fan input RPM */ | 283 | /* Fan input RPM */ |
| 280 | static inline int FAN_FROM_REG(int reg, int tpc) | 284 | static inline int FAN_FROM_REG(int reg, int tpc) |
| 281 | { | 285 | { |
| 282 | return (reg == 0 || reg == 0xffff) ? 0 : | 286 | if (tpc) { |
| 283 | (tpc == 0) ? 90000 * 60 / reg : tpc * reg; | 287 | return tpc * reg; |
| 288 | } else { | ||
| 289 | return (reg == 0 || reg == 0xffff) ? 0 : 90000 * 60 / reg; | ||
| 290 | } | ||
| 284 | } | 291 | } |
| 285 | 292 | ||
| 286 | static inline int FAN_TO_REG(int val, int tpc) | 293 | static inline int FAN_TO_REG(int val, int tpc) |
| 287 | { | 294 | { |
| 288 | return SENSORS_LIMIT((tpc == 0) ? 90000 * 60 / val : val / tpc, | 295 | if (tpc) { |
| 289 | 0, 0xffff); | 296 | return SENSORS_LIMIT(val / tpc, 0, 0xffff); |
| 297 | } else { | ||
| 298 | return (val <= 0) ? 0xffff : | ||
| 299 | SENSORS_LIMIT(90000 * 60 / val, 0, 0xfffe); | ||
| 300 | } | ||
| 290 | } | 301 | } |
| 291 | 302 | ||
| 292 | /* Fan TPC (tach pulse count) | 303 | /* Fan TPC (tach pulse count) |
| @@ -2019,7 +2030,7 @@ static int dme1737_i2c_get_features(int sio_cip, struct dme1737_data *data) | |||
| 2019 | 2030 | ||
| 2020 | /* Check device ID | 2031 | /* Check device ID |
| 2021 | * The DME1737 can return either 0x78 or 0x77 as its device ID. */ | 2032 | * The DME1737 can return either 0x78 or 0x77 as its device ID. */ |
| 2022 | reg = dme1737_sio_inb(sio_cip, 0x20); | 2033 | reg = force_id ? force_id : dme1737_sio_inb(sio_cip, 0x20); |
| 2023 | if (!(reg == 0x77 || reg == 0x78)) { | 2034 | if (!(reg == 0x77 || reg == 0x78)) { |
| 2024 | err = -ENODEV; | 2035 | err = -ENODEV; |
| 2025 | goto exit; | 2036 | goto exit; |
| @@ -2191,7 +2202,7 @@ static int __init dme1737_isa_detect(int sio_cip, unsigned short *addr) | |||
| 2191 | /* Check device ID | 2202 | /* Check device ID |
| 2192 | * We currently know about SCH3112 (0x7c), SCH3114 (0x7d), and | 2203 | * We currently know about SCH3112 (0x7c), SCH3114 (0x7d), and |
| 2193 | * SCH3116 (0x7f). */ | 2204 | * SCH3116 (0x7f). */ |
| 2194 | reg = dme1737_sio_inb(sio_cip, 0x20); | 2205 | reg = force_id ? force_id : dme1737_sio_inb(sio_cip, 0x20); |
| 2195 | if (!(reg == 0x7c || reg == 0x7d || reg == 0x7f)) { | 2206 | if (!(reg == 0x7c || reg == 0x7d || reg == 0x7f)) { |
| 2196 | err = -ENODEV; | 2207 | err = -ENODEV; |
| 2197 | goto exit; | 2208 | goto exit; |
diff --git a/drivers/hwmon/ds1621.c b/drivers/hwmon/ds1621.c index b7bd000b130f..3f5163de13c1 100644 --- a/drivers/hwmon/ds1621.c +++ b/drivers/hwmon/ds1621.c | |||
| @@ -94,7 +94,6 @@ static struct i2c_driver ds1621_driver = { | |||
| 94 | .driver = { | 94 | .driver = { |
| 95 | .name = "ds1621", | 95 | .name = "ds1621", |
| 96 | }, | 96 | }, |
| 97 | .id = I2C_DRIVERID_DS1621, | ||
| 98 | .attach_adapter = ds1621_attach_adapter, | 97 | .attach_adapter = ds1621_attach_adapter, |
| 99 | .detach_client = ds1621_detach_client, | 98 | .detach_client = ds1621_detach_client, |
| 100 | }; | 99 | }; |
diff --git a/drivers/hwmon/f71805f.c b/drivers/hwmon/f71805f.c index 5d9d5cc816a2..7a14a2dbb752 100644 --- a/drivers/hwmon/f71805f.c +++ b/drivers/hwmon/f71805f.c | |||
| @@ -41,6 +41,10 @@ | |||
| 41 | #include <linux/ioport.h> | 41 | #include <linux/ioport.h> |
| 42 | #include <asm/io.h> | 42 | #include <asm/io.h> |
| 43 | 43 | ||
| 44 | static unsigned short force_id; | ||
| 45 | module_param(force_id, ushort, 0); | ||
| 46 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 47 | |||
| 44 | static struct platform_device *pdev; | 48 | static struct platform_device *pdev; |
| 45 | 49 | ||
| 46 | #define DRVNAME "f71805f" | 50 | #define DRVNAME "f71805f" |
| @@ -1497,7 +1501,7 @@ static int __init f71805f_find(int sioaddr, unsigned short *address, | |||
| 1497 | if (devid != SIO_FINTEK_ID) | 1501 | if (devid != SIO_FINTEK_ID) |
| 1498 | goto exit; | 1502 | goto exit; |
| 1499 | 1503 | ||
| 1500 | devid = superio_inw(sioaddr, SIO_REG_DEVID); | 1504 | devid = force_id ? force_id : superio_inw(sioaddr, SIO_REG_DEVID); |
| 1501 | switch (devid) { | 1505 | switch (devid) { |
| 1502 | case SIO_F71805F_ID: | 1506 | case SIO_F71805F_ID: |
| 1503 | sio_data->kind = f71805f; | 1507 | sio_data->kind = f71805f; |
diff --git a/drivers/hwmon/f71882fg.c b/drivers/hwmon/f71882fg.c index 6db74434a02e..cbeb4984b5c7 100644 --- a/drivers/hwmon/f71882fg.c +++ b/drivers/hwmon/f71882fg.c | |||
| @@ -74,6 +74,10 @@ | |||
| 74 | 74 | ||
| 75 | #define FAN_MIN_DETECT 366 /* Lowest detectable fanspeed */ | 75 | #define FAN_MIN_DETECT 366 /* Lowest detectable fanspeed */ |
| 76 | 76 | ||
| 77 | static unsigned short force_id; | ||
| 78 | module_param(force_id, ushort, 0); | ||
| 79 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 80 | |||
| 77 | static struct platform_device *f71882fg_pdev = NULL; | 81 | static struct platform_device *f71882fg_pdev = NULL; |
| 78 | 82 | ||
| 79 | /* Super-I/O Function prototypes */ | 83 | /* Super-I/O Function prototypes */ |
| @@ -843,7 +847,7 @@ static int __init f71882fg_find(int sioaddr, unsigned short *address) | |||
| 843 | goto exit; | 847 | goto exit; |
| 844 | } | 848 | } |
| 845 | 849 | ||
| 846 | devid = superio_inw(sioaddr, SIO_REG_DEVID); | 850 | devid = force_id ? force_id : superio_inw(sioaddr, SIO_REG_DEVID); |
| 847 | if (devid != SIO_F71882_ID) { | 851 | if (devid != SIO_F71882_ID) { |
| 848 | printk(KERN_INFO DRVNAME ": Unsupported Fintek device\n"); | 852 | printk(KERN_INFO DRVNAME ": Unsupported Fintek device\n"); |
| 849 | goto exit; | 853 | goto exit; |
diff --git a/drivers/hwmon/fscher.c b/drivers/hwmon/fscher.c index e67c36953b2d..721c70177b17 100644 --- a/drivers/hwmon/fscher.c +++ b/drivers/hwmon/fscher.c | |||
| @@ -123,7 +123,6 @@ static struct i2c_driver fscher_driver = { | |||
| 123 | .driver = { | 123 | .driver = { |
| 124 | .name = "fscher", | 124 | .name = "fscher", |
| 125 | }, | 125 | }, |
| 126 | .id = I2C_DRIVERID_FSCHER, | ||
| 127 | .attach_adapter = fscher_attach_adapter, | 126 | .attach_adapter = fscher_attach_adapter, |
| 128 | .detach_client = fscher_detach_client, | 127 | .detach_client = fscher_detach_client, |
| 129 | }; | 128 | }; |
diff --git a/drivers/hwmon/fschmd.c b/drivers/hwmon/fschmd.c index 63a4df0580db..b7c9eef0f928 100644 --- a/drivers/hwmon/fschmd.c +++ b/drivers/hwmon/fschmd.c | |||
| @@ -41,6 +41,7 @@ | |||
| 41 | #include <linux/err.h> | 41 | #include <linux/err.h> |
| 42 | #include <linux/mutex.h> | 42 | #include <linux/mutex.h> |
| 43 | #include <linux/sysfs.h> | 43 | #include <linux/sysfs.h> |
| 44 | #include <linux/dmi.h> | ||
| 44 | 45 | ||
| 45 | /* Addresses to scan */ | 46 | /* Addresses to scan */ |
| 46 | static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END }; | 47 | static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END }; |
| @@ -133,7 +134,7 @@ static const u8 FSCHMD_REG_TEMP_STATE[5][5] = { | |||
| 133 | { 0x71, 0x81, 0x91 }, /* her */ | 134 | { 0x71, 0x81, 0x91 }, /* her */ |
| 134 | { 0x71, 0xd1, 0x81, 0x91 }, /* scy */ | 135 | { 0x71, 0xd1, 0x81, 0x91 }, /* scy */ |
| 135 | { 0x71, 0x81, 0x91 }, /* hrc */ | 136 | { 0x71, 0x81, 0x91 }, /* hrc */ |
| 136 | { 0x71, 0x81, 0x91, 0xd1, 0xe1 }, /*Â hmd */ | 137 | { 0x71, 0x81, 0x91, 0xd1, 0xe1 }, /* hmd */ |
| 137 | }; | 138 | }; |
| 138 | 139 | ||
| 139 | /* temperature high limit registers, FSC does not document these. Proven to be | 140 | /* temperature high limit registers, FSC does not document these. Proven to be |
| @@ -146,7 +147,7 @@ static const u8 FSCHMD_REG_TEMP_LIMIT[5][5] = { | |||
| 146 | { 0x76, 0x86, 0x96 }, /* her */ | 147 | { 0x76, 0x86, 0x96 }, /* her */ |
| 147 | { 0x76, 0xd6, 0x86, 0x96 }, /* scy */ | 148 | { 0x76, 0xd6, 0x86, 0x96 }, /* scy */ |
| 148 | { 0x76, 0x86, 0x96 }, /* hrc */ | 149 | { 0x76, 0x86, 0x96 }, /* hrc */ |
| 149 | { 0x76, 0x86, 0x96, 0xd6, 0xe6 }, /*Â hmd */ | 150 | { 0x76, 0x86, 0x96, 0xd6, 0xe6 }, /* hmd */ |
| 150 | }; | 151 | }; |
| 151 | 152 | ||
| 152 | /* These were found through experimenting with an fscher, currently they are | 153 | /* These were found through experimenting with an fscher, currently they are |
| @@ -210,6 +211,13 @@ struct fschmd_data { | |||
| 210 | u8 fan_ripple[6]; /* divider for rps */ | 211 | u8 fan_ripple[6]; /* divider for rps */ |
| 211 | }; | 212 | }; |
| 212 | 213 | ||
| 214 | /* Global variables to hold information read from special DMI tables, which are | ||
| 215 | available on FSC machines with an fscher or later chip. */ | ||
| 216 | static int dmi_mult[3] = { 490, 200, 100 }; | ||
| 217 | static int dmi_offset[3] = { 0, 0, 0 }; | ||
| 218 | static int dmi_vref = -1; | ||
| 219 | |||
| 220 | |||
| 213 | /* | 221 | /* |
| 214 | * Sysfs attr show / store functions | 222 | * Sysfs attr show / store functions |
| 215 | */ | 223 | */ |
| @@ -221,8 +229,13 @@ static ssize_t show_in_value(struct device *dev, | |||
| 221 | int index = to_sensor_dev_attr(devattr)->index; | 229 | int index = to_sensor_dev_attr(devattr)->index; |
| 222 | struct fschmd_data *data = fschmd_update_device(dev); | 230 | struct fschmd_data *data = fschmd_update_device(dev); |
| 223 | 231 | ||
| 224 | return sprintf(buf, "%d\n", (data->volt[index] * | 232 | /* fscher / fschrc - 1 as data->kind is an array index, not a chips */ |
| 225 | max_reading[index] + 128) / 255); | 233 | if (data->kind == (fscher - 1) || data->kind >= (fschrc - 1)) |
| 234 | return sprintf(buf, "%d\n", (data->volt[index] * dmi_vref * | ||
| 235 | dmi_mult[index]) / 255 + dmi_offset[index]); | ||
| 236 | else | ||
| 237 | return sprintf(buf, "%d\n", (data->volt[index] * | ||
| 238 | max_reading[index] + 128) / 255); | ||
| 226 | } | 239 | } |
| 227 | 240 | ||
| 228 | 241 | ||
| @@ -525,6 +538,68 @@ static struct sensor_device_attribute fschmd_fan_attr[] = { | |||
| 525 | * Real code | 538 | * Real code |
| 526 | */ | 539 | */ |
| 527 | 540 | ||
| 541 | /* DMI decode routine to read voltage scaling factors from special DMI tables, | ||
| 542 | which are available on FSC machines with an fscher or later chip. */ | ||
| 543 | static void fschmd_dmi_decode(const struct dmi_header *header) | ||
| 544 | { | ||
| 545 | int i, mult[3] = { 0 }, offset[3] = { 0 }, vref = 0, found = 0; | ||
| 546 | |||
| 547 | /* dmi code ugliness, we get passed the address of the contents of | ||
| 548 | a complete DMI record, but in the form of a dmi_header pointer, in | ||
| 549 | reality this address holds header->length bytes of which the header | ||
| 550 | are the first 4 bytes */ | ||
| 551 | u8 *dmi_data = (u8 *)header; | ||
| 552 | |||
| 553 | /* We are looking for OEM-specific type 185 */ | ||
| 554 | if (header->type != 185) | ||
| 555 | return; | ||
| 556 | |||
| 557 | /* we are looking for what Siemens calls "subtype" 19, the subtype | ||
| 558 | is stored in byte 5 of the dmi block */ | ||
| 559 | if (header->length < 5 || dmi_data[4] != 19) | ||
| 560 | return; | ||
| 561 | |||
| 562 | /* After the subtype comes 1 unknown byte and then blocks of 5 bytes, | ||
| 563 | consisting of what Siemens calls an "Entity" number, followed by | ||
| 564 | 2 16-bit words in LSB first order */ | ||
| 565 | for (i = 6; (i + 4) < header->length; i += 5) { | ||
| 566 | /* entity 1 - 3: voltage multiplier and offset */ | ||
| 567 | if (dmi_data[i] >= 1 && dmi_data[i] <= 3) { | ||
| 568 | /* Our in sensors order and the DMI order differ */ | ||
| 569 | const int shuffle[3] = { 1, 0, 2 }; | ||
| 570 | int in = shuffle[dmi_data[i] - 1]; | ||
| 571 | |||
| 572 | /* Check for twice the same entity */ | ||
| 573 | if (found & (1 << in)) | ||
| 574 | return; | ||
| 575 | |||
| 576 | mult[in] = dmi_data[i + 1] | (dmi_data[i + 2] << 8); | ||
| 577 | offset[in] = dmi_data[i + 3] | (dmi_data[i + 4] << 8); | ||
| 578 | |||
| 579 | found |= 1 << in; | ||
| 580 | } | ||
| 581 | |||
| 582 | /* entity 7: reference voltage */ | ||
| 583 | if (dmi_data[i] == 7) { | ||
| 584 | /* Check for twice the same entity */ | ||
| 585 | if (found & 0x08) | ||
| 586 | return; | ||
| 587 | |||
| 588 | vref = dmi_data[i + 1] | (dmi_data[i + 2] << 8); | ||
| 589 | |||
| 590 | found |= 0x08; | ||
| 591 | } | ||
| 592 | } | ||
| 593 | |||
| 594 | if (found == 0x0F) { | ||
| 595 | for (i = 0; i < 3; i++) { | ||
| 596 | dmi_mult[i] = mult[i] * 10; | ||
| 597 | dmi_offset[i] = offset[i] * 10; | ||
| 598 | } | ||
| 599 | dmi_vref = vref; | ||
| 600 | } | ||
| 601 | } | ||
| 602 | |||
| 528 | static int fschmd_detect(struct i2c_adapter *adapter, int address, int kind) | 603 | static int fschmd_detect(struct i2c_adapter *adapter, int address, int kind) |
| 529 | { | 604 | { |
| 530 | struct i2c_client *client; | 605 | struct i2c_client *client; |
| @@ -586,6 +661,17 @@ static int fschmd_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 586 | data->temp_max[2] = 50 + 128; | 661 | data->temp_max[2] = 50 + 128; |
| 587 | } | 662 | } |
| 588 | 663 | ||
| 664 | /* Read the special DMI table for fscher and newer chips */ | ||
| 665 | if (kind == fscher || kind >= fschrc) { | ||
| 666 | dmi_walk(fschmd_dmi_decode); | ||
| 667 | if (dmi_vref == -1) { | ||
| 668 | printk(KERN_WARNING FSCHMD_NAME | ||
| 669 | ": Couldn't get voltage scaling factors from " | ||
| 670 | "BIOS DMI table, using builtin defaults\n"); | ||
| 671 | dmi_vref = 33; | ||
| 672 | } | ||
| 673 | } | ||
| 674 | |||
| 589 | /* i2c kind goes from 1-5, we want from 0-4 to address arrays */ | 675 | /* i2c kind goes from 1-5, we want from 0-4 to address arrays */ |
| 590 | data->kind = kind - 1; | 676 | data->kind = kind - 1; |
| 591 | strlcpy(client->name, client_names[data->kind], I2C_NAME_SIZE); | 677 | strlcpy(client->name, client_names[data->kind], I2C_NAME_SIZE); |
diff --git a/drivers/hwmon/fscpos.c b/drivers/hwmon/fscpos.c index 92c9703d0ac0..2f1075323a1e 100644 --- a/drivers/hwmon/fscpos.c +++ b/drivers/hwmon/fscpos.c | |||
| @@ -105,7 +105,6 @@ static struct i2c_driver fscpos_driver = { | |||
| 105 | .driver = { | 105 | .driver = { |
| 106 | .name = "fscpos", | 106 | .name = "fscpos", |
| 107 | }, | 107 | }, |
| 108 | .id = I2C_DRIVERID_FSCPOS, | ||
| 109 | .attach_adapter = fscpos_attach_adapter, | 108 | .attach_adapter = fscpos_attach_adapter, |
| 110 | .detach_client = fscpos_detach_client, | 109 | .detach_client = fscpos_detach_client, |
| 111 | }; | 110 | }; |
diff --git a/drivers/hwmon/gl518sm.c b/drivers/hwmon/gl518sm.c index bb58d9866a37..3b1ac48fce23 100644 --- a/drivers/hwmon/gl518sm.c +++ b/drivers/hwmon/gl518sm.c | |||
| @@ -30,10 +30,6 @@ | |||
| 30 | * We did not keep that part of the original driver in the Linux 2.6 | 30 | * We did not keep that part of the original driver in the Linux 2.6 |
| 31 | * version, since it was making the driver significantly more complex | 31 | * version, since it was making the driver significantly more complex |
| 32 | * with no real benefit. | 32 | * with no real benefit. |
| 33 | * | ||
| 34 | * History: | ||
| 35 | * 2004-01-28 Original port. (Hong-Gunn Chew) | ||
| 36 | * 2004-01-31 Code review and approval. (Jean Delvare) | ||
| 37 | */ | 33 | */ |
| 38 | 34 | ||
| 39 | #include <linux/module.h> | 35 | #include <linux/module.h> |
| @@ -42,6 +38,7 @@ | |||
| 42 | #include <linux/jiffies.h> | 38 | #include <linux/jiffies.h> |
| 43 | #include <linux/i2c.h> | 39 | #include <linux/i2c.h> |
| 44 | #include <linux/hwmon.h> | 40 | #include <linux/hwmon.h> |
| 41 | #include <linux/hwmon-sysfs.h> | ||
| 45 | #include <linux/err.h> | 42 | #include <linux/err.h> |
| 46 | #include <linux/mutex.h> | 43 | #include <linux/mutex.h> |
| 47 | #include <linux/sysfs.h> | 44 | #include <linux/sysfs.h> |
| @@ -99,10 +96,10 @@ static inline u8 FAN_TO_REG(long rpm, int div) | |||
| 99 | long rpmdiv; | 96 | long rpmdiv; |
| 100 | if (rpm == 0) | 97 | if (rpm == 0) |
| 101 | return 0; | 98 | return 0; |
| 102 | rpmdiv = SENSORS_LIMIT(rpm, 1, 1920000) * div; | 99 | rpmdiv = SENSORS_LIMIT(rpm, 1, 960000) * div; |
| 103 | return SENSORS_LIMIT((960000 + rpmdiv / 2) / rpmdiv, 1, 255); | 100 | return SENSORS_LIMIT((480000 + rpmdiv / 2) / rpmdiv, 1, 255); |
| 104 | } | 101 | } |
| 105 | #define FAN_FROM_REG(val,div) ((val)==0 ? 0 : (960000/((val)*(div)))) | 102 | #define FAN_FROM_REG(val,div) ((val)==0 ? 0 : (480000/((val)*(div)))) |
| 106 | 103 | ||
| 107 | #define IN_TO_REG(val) (SENSORS_LIMIT((((val)+9)/19),0,255)) | 104 | #define IN_TO_REG(val) (SENSORS_LIMIT((((val)+9)/19),0,255)) |
| 108 | #define IN_FROM_REG(val) ((val)*19) | 105 | #define IN_FROM_REG(val) ((val)*19) |
| @@ -110,7 +107,6 @@ static inline u8 FAN_TO_REG(long rpm, int div) | |||
| 110 | #define VDD_TO_REG(val) (SENSORS_LIMIT((((val)*4+47)/95),0,255)) | 107 | #define VDD_TO_REG(val) (SENSORS_LIMIT((((val)*4+47)/95),0,255)) |
| 111 | #define VDD_FROM_REG(val) (((val)*95+2)/4) | 108 | #define VDD_FROM_REG(val) (((val)*95+2)/4) |
| 112 | 109 | ||
| 113 | #define DIV_TO_REG(val) ((val)==4?2:(val)==2?1:(val)==1?0:3) | ||
| 114 | #define DIV_FROM_REG(val) (1 << (val)) | 110 | #define DIV_FROM_REG(val) (1 << (val)) |
| 115 | 111 | ||
| 116 | #define BEEP_MASK_TO_REG(val) ((val) & 0x7f & data->alarm_mask) | 112 | #define BEEP_MASK_TO_REG(val) ((val) & 0x7f & data->alarm_mask) |
| @@ -129,7 +125,6 @@ struct gl518_data { | |||
| 129 | u8 voltage_in[4]; /* Register values; [0] = VDD */ | 125 | u8 voltage_in[4]; /* Register values; [0] = VDD */ |
| 130 | u8 voltage_min[4]; /* Register values; [0] = VDD */ | 126 | u8 voltage_min[4]; /* Register values; [0] = VDD */ |
| 131 | u8 voltage_max[4]; /* Register values; [0] = VDD */ | 127 | u8 voltage_max[4]; /* Register values; [0] = VDD */ |
| 132 | u8 iter_voltage_in[4]; /* Register values; [0] = VDD */ | ||
| 133 | u8 fan_in[2]; | 128 | u8 fan_in[2]; |
| 134 | u8 fan_min[2]; | 129 | u8 fan_min[2]; |
| 135 | u8 fan_div[2]; /* Register encoding, shifted right */ | 130 | u8 fan_div[2]; /* Register encoding, shifted right */ |
| @@ -138,7 +133,7 @@ struct gl518_data { | |||
| 138 | u8 temp_max; /* Register values */ | 133 | u8 temp_max; /* Register values */ |
| 139 | u8 temp_hyst; /* Register values */ | 134 | u8 temp_hyst; /* Register values */ |
| 140 | u8 alarms; /* Register value */ | 135 | u8 alarms; /* Register value */ |
| 141 | u8 alarm_mask; /* Register value */ | 136 | u8 alarm_mask; |
| 142 | u8 beep_mask; /* Register value */ | 137 | u8 beep_mask; /* Register value */ |
| 143 | u8 beep_enable; /* Boolean */ | 138 | u8 beep_enable; /* Boolean */ |
| 144 | }; | 139 | }; |
| @@ -156,7 +151,6 @@ static struct i2c_driver gl518_driver = { | |||
| 156 | .driver = { | 151 | .driver = { |
| 157 | .name = "gl518sm", | 152 | .name = "gl518sm", |
| 158 | }, | 153 | }, |
| 159 | .id = I2C_DRIVERID_GL518, | ||
| 160 | .attach_adapter = gl518_attach_adapter, | 154 | .attach_adapter = gl518_attach_adapter, |
| 161 | .detach_client = gl518_detach_client, | 155 | .detach_client = gl518_detach_client, |
| 162 | }; | 156 | }; |
| @@ -172,24 +166,10 @@ static ssize_t show_##suffix(struct device *dev, struct device_attribute *attr, | |||
| 172 | return sprintf(buf, "%d\n", type##_FROM_REG(data->value)); \ | 166 | return sprintf(buf, "%d\n", type##_FROM_REG(data->value)); \ |
| 173 | } | 167 | } |
| 174 | 168 | ||
| 175 | #define show_fan(suffix, value, index) \ | ||
| 176 | static ssize_t show_##suffix(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 177 | { \ | ||
| 178 | struct gl518_data *data = gl518_update_device(dev); \ | ||
| 179 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->value[index], \ | ||
| 180 | DIV_FROM_REG(data->fan_div[index]))); \ | ||
| 181 | } | ||
| 182 | |||
| 183 | show(TEMP, temp_input1, temp_in); | 169 | show(TEMP, temp_input1, temp_in); |
| 184 | show(TEMP, temp_max1, temp_max); | 170 | show(TEMP, temp_max1, temp_max); |
| 185 | show(TEMP, temp_hyst1, temp_hyst); | 171 | show(TEMP, temp_hyst1, temp_hyst); |
| 186 | show(BOOL, fan_auto1, fan_auto1); | 172 | show(BOOL, fan_auto1, fan_auto1); |
| 187 | show_fan(fan_input1, fan_in, 0); | ||
| 188 | show_fan(fan_input2, fan_in, 1); | ||
| 189 | show_fan(fan_min1, fan_min, 0); | ||
| 190 | show_fan(fan_min2, fan_min, 1); | ||
| 191 | show(DIV, fan_div1, fan_div[0]); | ||
| 192 | show(DIV, fan_div2, fan_div[1]); | ||
| 193 | show(VDD, in_input0, voltage_in[0]); | 173 | show(VDD, in_input0, voltage_in[0]); |
| 194 | show(IN, in_input1, voltage_in[1]); | 174 | show(IN, in_input1, voltage_in[1]); |
| 195 | show(IN, in_input2, voltage_in[2]); | 175 | show(IN, in_input2, voltage_in[2]); |
| @@ -206,6 +186,32 @@ show(RAW, alarms, alarms); | |||
| 206 | show(BOOL, beep_enable, beep_enable); | 186 | show(BOOL, beep_enable, beep_enable); |
| 207 | show(BEEP_MASK, beep_mask, beep_mask); | 187 | show(BEEP_MASK, beep_mask, beep_mask); |
| 208 | 188 | ||
| 189 | static ssize_t show_fan_input(struct device *dev, | ||
| 190 | struct device_attribute *attr, char *buf) | ||
| 191 | { | ||
| 192 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 193 | struct gl518_data *data = gl518_update_device(dev); | ||
| 194 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_in[nr], | ||
| 195 | DIV_FROM_REG(data->fan_div[nr]))); | ||
| 196 | } | ||
| 197 | |||
| 198 | static ssize_t show_fan_min(struct device *dev, | ||
| 199 | struct device_attribute *attr, char *buf) | ||
| 200 | { | ||
| 201 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 202 | struct gl518_data *data = gl518_update_device(dev); | ||
| 203 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_min[nr], | ||
| 204 | DIV_FROM_REG(data->fan_div[nr]))); | ||
| 205 | } | ||
| 206 | |||
| 207 | static ssize_t show_fan_div(struct device *dev, | ||
| 208 | struct device_attribute *attr, char *buf) | ||
| 209 | { | ||
| 210 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 211 | struct gl518_data *data = gl518_update_device(dev); | ||
| 212 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->fan_div[nr])); | ||
| 213 | } | ||
| 214 | |||
| 209 | #define set(type, suffix, value, reg) \ | 215 | #define set(type, suffix, value, reg) \ |
| 210 | static ssize_t set_##suffix(struct device *dev, struct device_attribute *attr, const char *buf, \ | 216 | static ssize_t set_##suffix(struct device *dev, struct device_attribute *attr, const char *buf, \ |
| 211 | size_t count) \ | 217 | size_t count) \ |
| @@ -247,8 +253,6 @@ static ssize_t set_##suffix(struct device *dev, struct device_attribute *attr, c | |||
| 247 | set(TEMP, temp_max1, temp_max, GL518_REG_TEMP_MAX); | 253 | set(TEMP, temp_max1, temp_max, GL518_REG_TEMP_MAX); |
| 248 | set(TEMP, temp_hyst1, temp_hyst, GL518_REG_TEMP_HYST); | 254 | set(TEMP, temp_hyst1, temp_hyst, GL518_REG_TEMP_HYST); |
| 249 | set_bits(BOOL, fan_auto1, fan_auto1, GL518_REG_MISC, 0x08, 3); | 255 | set_bits(BOOL, fan_auto1, fan_auto1, GL518_REG_MISC, 0x08, 3); |
| 250 | set_bits(DIV, fan_div1, fan_div[0], GL518_REG_MISC, 0xc0, 6); | ||
| 251 | set_bits(DIV, fan_div2, fan_div[1], GL518_REG_MISC, 0x30, 4); | ||
| 252 | set_low(VDD, in_min0, voltage_min[0], GL518_REG_VDD_LIMIT); | 256 | set_low(VDD, in_min0, voltage_min[0], GL518_REG_VDD_LIMIT); |
| 253 | set_low(IN, in_min1, voltage_min[1], GL518_REG_VIN1_LIMIT); | 257 | set_low(IN, in_min1, voltage_min[1], GL518_REG_VIN1_LIMIT); |
| 254 | set_low(IN, in_min2, voltage_min[2], GL518_REG_VIN2_LIMIT); | 258 | set_low(IN, in_min2, voltage_min[2], GL518_REG_VIN2_LIMIT); |
| @@ -260,25 +264,27 @@ set_high(IN, in_max3, voltage_max[3], GL518_REG_VIN3_LIMIT); | |||
| 260 | set_bits(BOOL, beep_enable, beep_enable, GL518_REG_CONF, 0x04, 2); | 264 | set_bits(BOOL, beep_enable, beep_enable, GL518_REG_CONF, 0x04, 2); |
| 261 | set(BEEP_MASK, beep_mask, beep_mask, GL518_REG_ALARM); | 265 | set(BEEP_MASK, beep_mask, beep_mask, GL518_REG_ALARM); |
| 262 | 266 | ||
| 263 | static ssize_t set_fan_min1(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 267 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, |
| 268 | const char *buf, size_t count) | ||
| 264 | { | 269 | { |
| 265 | struct i2c_client *client = to_i2c_client(dev); | 270 | struct i2c_client *client = to_i2c_client(dev); |
| 266 | struct gl518_data *data = i2c_get_clientdata(client); | 271 | struct gl518_data *data = i2c_get_clientdata(client); |
| 272 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 267 | int regvalue; | 273 | int regvalue; |
| 268 | unsigned long val = simple_strtoul(buf, NULL, 10); | 274 | unsigned long val = simple_strtoul(buf, NULL, 10); |
| 269 | 275 | ||
| 270 | mutex_lock(&data->update_lock); | 276 | mutex_lock(&data->update_lock); |
| 271 | regvalue = gl518_read_value(client, GL518_REG_FAN_LIMIT); | 277 | regvalue = gl518_read_value(client, GL518_REG_FAN_LIMIT); |
| 272 | data->fan_min[0] = FAN_TO_REG(val, | 278 | data->fan_min[nr] = FAN_TO_REG(val, DIV_FROM_REG(data->fan_div[nr])); |
| 273 | DIV_FROM_REG(data->fan_div[0])); | 279 | regvalue = (regvalue & (0xff << (8 * nr))) |
| 274 | regvalue = (regvalue & 0x00ff) | (data->fan_min[0] << 8); | 280 | | (data->fan_min[nr] << (8 * (1 - nr))); |
| 275 | gl518_write_value(client, GL518_REG_FAN_LIMIT, regvalue); | 281 | gl518_write_value(client, GL518_REG_FAN_LIMIT, regvalue); |
| 276 | 282 | ||
| 277 | data->beep_mask = gl518_read_value(client, GL518_REG_ALARM); | 283 | data->beep_mask = gl518_read_value(client, GL518_REG_ALARM); |
| 278 | if (data->fan_min[0] == 0) | 284 | if (data->fan_min[nr] == 0) |
| 279 | data->alarm_mask &= ~0x20; | 285 | data->alarm_mask &= ~(0x20 << nr); |
| 280 | else | 286 | else |
| 281 | data->alarm_mask |= 0x20; | 287 | data->alarm_mask |= (0x20 << nr); |
| 282 | data->beep_mask &= data->alarm_mask; | 288 | data->beep_mask &= data->alarm_mask; |
| 283 | gl518_write_value(client, GL518_REG_ALARM, data->beep_mask); | 289 | gl518_write_value(client, GL518_REG_ALARM, data->beep_mask); |
| 284 | 290 | ||
| @@ -286,28 +292,32 @@ static ssize_t set_fan_min1(struct device *dev, struct device_attribute *attr, c | |||
| 286 | return count; | 292 | return count; |
| 287 | } | 293 | } |
| 288 | 294 | ||
| 289 | static ssize_t set_fan_min2(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 295 | static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, |
| 296 | const char *buf, size_t count) | ||
| 290 | { | 297 | { |
| 291 | struct i2c_client *client = to_i2c_client(dev); | 298 | struct i2c_client *client = to_i2c_client(dev); |
| 292 | struct gl518_data *data = i2c_get_clientdata(client); | 299 | struct gl518_data *data = i2c_get_clientdata(client); |
| 300 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 293 | int regvalue; | 301 | int regvalue; |
| 294 | unsigned long val = simple_strtoul(buf, NULL, 10); | 302 | unsigned long val = simple_strtoul(buf, NULL, 10); |
| 295 | 303 | ||
| 296 | mutex_lock(&data->update_lock); | 304 | switch (val) { |
| 297 | regvalue = gl518_read_value(client, GL518_REG_FAN_LIMIT); | 305 | case 1: val = 0; break; |
| 298 | data->fan_min[1] = FAN_TO_REG(val, | 306 | case 2: val = 1; break; |
| 299 | DIV_FROM_REG(data->fan_div[1])); | 307 | case 4: val = 2; break; |
| 300 | regvalue = (regvalue & 0xff00) | data->fan_min[1]; | 308 | case 8: val = 3; break; |
| 301 | gl518_write_value(client, GL518_REG_FAN_LIMIT, regvalue); | 309 | default: |
| 302 | 310 | dev_err(dev, "Invalid fan clock divider %lu, choose one " | |
| 303 | data->beep_mask = gl518_read_value(client, GL518_REG_ALARM); | 311 | "of 1, 2, 4 or 8\n", val); |
| 304 | if (data->fan_min[1] == 0) | 312 | return -EINVAL; |
| 305 | data->alarm_mask &= ~0x40; | 313 | } |
| 306 | else | ||
| 307 | data->alarm_mask |= 0x40; | ||
| 308 | data->beep_mask &= data->alarm_mask; | ||
| 309 | gl518_write_value(client, GL518_REG_ALARM, data->beep_mask); | ||
| 310 | 314 | ||
| 315 | mutex_lock(&data->update_lock); | ||
| 316 | regvalue = gl518_read_value(client, GL518_REG_MISC); | ||
| 317 | data->fan_div[nr] = val; | ||
| 318 | regvalue = (regvalue & ~(0xc0 >> (2 * nr))) | ||
| 319 | | (data->fan_div[nr] << (6 - 2 * nr)); | ||
| 320 | gl518_write_value(client, GL518_REG_MISC, regvalue); | ||
| 311 | mutex_unlock(&data->update_lock); | 321 | mutex_unlock(&data->update_lock); |
| 312 | return count; | 322 | return count; |
| 313 | } | 323 | } |
| @@ -317,12 +327,16 @@ static DEVICE_ATTR(temp1_max, S_IWUSR|S_IRUGO, show_temp_max1, set_temp_max1); | |||
| 317 | static DEVICE_ATTR(temp1_max_hyst, S_IWUSR|S_IRUGO, | 327 | static DEVICE_ATTR(temp1_max_hyst, S_IWUSR|S_IRUGO, |
| 318 | show_temp_hyst1, set_temp_hyst1); | 328 | show_temp_hyst1, set_temp_hyst1); |
| 319 | static DEVICE_ATTR(fan1_auto, S_IWUSR|S_IRUGO, show_fan_auto1, set_fan_auto1); | 329 | static DEVICE_ATTR(fan1_auto, S_IWUSR|S_IRUGO, show_fan_auto1, set_fan_auto1); |
| 320 | static DEVICE_ATTR(fan1_input, S_IRUGO, show_fan_input1, NULL); | 330 | static SENSOR_DEVICE_ATTR(fan1_input, S_IRUGO, show_fan_input, NULL, 0); |
| 321 | static DEVICE_ATTR(fan2_input, S_IRUGO, show_fan_input2, NULL); | 331 | static SENSOR_DEVICE_ATTR(fan2_input, S_IRUGO, show_fan_input, NULL, 1); |
| 322 | static DEVICE_ATTR(fan1_min, S_IWUSR|S_IRUGO, show_fan_min1, set_fan_min1); | 332 | static SENSOR_DEVICE_ATTR(fan1_min, S_IWUSR|S_IRUGO, |
| 323 | static DEVICE_ATTR(fan2_min, S_IWUSR|S_IRUGO, show_fan_min2, set_fan_min2); | 333 | show_fan_min, set_fan_min, 0); |
| 324 | static DEVICE_ATTR(fan1_div, S_IWUSR|S_IRUGO, show_fan_div1, set_fan_div1); | 334 | static SENSOR_DEVICE_ATTR(fan2_min, S_IWUSR|S_IRUGO, |
| 325 | static DEVICE_ATTR(fan2_div, S_IWUSR|S_IRUGO, show_fan_div2, set_fan_div2); | 335 | show_fan_min, set_fan_min, 1); |
| 336 | static SENSOR_DEVICE_ATTR(fan1_div, S_IWUSR|S_IRUGO, | ||
| 337 | show_fan_div, set_fan_div, 0); | ||
| 338 | static SENSOR_DEVICE_ATTR(fan2_div, S_IWUSR|S_IRUGO, | ||
| 339 | show_fan_div, set_fan_div, 1); | ||
| 326 | static DEVICE_ATTR(in0_input, S_IRUGO, show_in_input0, NULL); | 340 | static DEVICE_ATTR(in0_input, S_IRUGO, show_in_input0, NULL); |
| 327 | static DEVICE_ATTR(in1_input, S_IRUGO, show_in_input1, NULL); | 341 | static DEVICE_ATTR(in1_input, S_IRUGO, show_in_input1, NULL); |
| 328 | static DEVICE_ATTR(in2_input, S_IRUGO, show_in_input2, NULL); | 342 | static DEVICE_ATTR(in2_input, S_IRUGO, show_in_input2, NULL); |
| @@ -341,10 +355,62 @@ static DEVICE_ATTR(beep_enable, S_IWUSR|S_IRUGO, | |||
| 341 | static DEVICE_ATTR(beep_mask, S_IWUSR|S_IRUGO, | 355 | static DEVICE_ATTR(beep_mask, S_IWUSR|S_IRUGO, |
| 342 | show_beep_mask, set_beep_mask); | 356 | show_beep_mask, set_beep_mask); |
| 343 | 357 | ||
| 358 | static ssize_t show_alarm(struct device *dev, struct device_attribute *attr, | ||
| 359 | char *buf) | ||
| 360 | { | ||
| 361 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 362 | struct gl518_data *data = gl518_update_device(dev); | ||
| 363 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); | ||
| 364 | } | ||
| 365 | |||
| 366 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 367 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 368 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 369 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 370 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 371 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 5); | ||
| 372 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 373 | |||
| 374 | static ssize_t show_beep(struct device *dev, struct device_attribute *attr, | ||
| 375 | char *buf) | ||
| 376 | { | ||
| 377 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 378 | struct gl518_data *data = gl518_update_device(dev); | ||
| 379 | return sprintf(buf, "%u\n", (data->beep_mask >> bitnr) & 1); | ||
| 380 | } | ||
| 381 | |||
| 382 | static ssize_t set_beep(struct device *dev, struct device_attribute *attr, | ||
| 383 | const char *buf, size_t count) | ||
| 384 | { | ||
| 385 | struct i2c_client *client = to_i2c_client(dev); | ||
| 386 | struct gl518_data *data = i2c_get_clientdata(client); | ||
| 387 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 388 | unsigned long bit; | ||
| 389 | |||
| 390 | bit = simple_strtoul(buf, NULL, 10); | ||
| 391 | if (bit & ~1) | ||
| 392 | return -EINVAL; | ||
| 393 | |||
| 394 | mutex_lock(&data->update_lock); | ||
| 395 | data->beep_mask = gl518_read_value(client, GL518_REG_ALARM); | ||
| 396 | if (bit) | ||
| 397 | data->beep_mask |= (1 << bitnr); | ||
| 398 | else | ||
| 399 | data->beep_mask &= ~(1 << bitnr); | ||
| 400 | gl518_write_value(client, GL518_REG_ALARM, data->beep_mask); | ||
| 401 | mutex_unlock(&data->update_lock); | ||
| 402 | return count; | ||
| 403 | } | ||
| 404 | |||
| 405 | static SENSOR_DEVICE_ATTR(in0_beep, S_IRUGO|S_IWUSR, show_beep, set_beep, 0); | ||
| 406 | static SENSOR_DEVICE_ATTR(in1_beep, S_IRUGO|S_IWUSR, show_beep, set_beep, 1); | ||
| 407 | static SENSOR_DEVICE_ATTR(in2_beep, S_IRUGO|S_IWUSR, show_beep, set_beep, 2); | ||
| 408 | static SENSOR_DEVICE_ATTR(in3_beep, S_IRUGO|S_IWUSR, show_beep, set_beep, 3); | ||
| 409 | static SENSOR_DEVICE_ATTR(temp1_beep, S_IRUGO|S_IWUSR, show_beep, set_beep, 4); | ||
| 410 | static SENSOR_DEVICE_ATTR(fan1_beep, S_IRUGO|S_IWUSR, show_beep, set_beep, 5); | ||
| 411 | static SENSOR_DEVICE_ATTR(fan2_beep, S_IRUGO|S_IWUSR, show_beep, set_beep, 6); | ||
| 412 | |||
| 344 | static struct attribute *gl518_attributes[] = { | 413 | static struct attribute *gl518_attributes[] = { |
| 345 | &dev_attr_in0_input.attr, | ||
| 346 | &dev_attr_in1_input.attr, | ||
| 347 | &dev_attr_in2_input.attr, | ||
| 348 | &dev_attr_in3_input.attr, | 414 | &dev_attr_in3_input.attr, |
| 349 | &dev_attr_in0_min.attr, | 415 | &dev_attr_in0_min.attr, |
| 350 | &dev_attr_in1_min.attr, | 416 | &dev_attr_in1_min.attr, |
| @@ -354,18 +420,32 @@ static struct attribute *gl518_attributes[] = { | |||
| 354 | &dev_attr_in1_max.attr, | 420 | &dev_attr_in1_max.attr, |
| 355 | &dev_attr_in2_max.attr, | 421 | &dev_attr_in2_max.attr, |
| 356 | &dev_attr_in3_max.attr, | 422 | &dev_attr_in3_max.attr, |
| 423 | &sensor_dev_attr_in0_alarm.dev_attr.attr, | ||
| 424 | &sensor_dev_attr_in1_alarm.dev_attr.attr, | ||
| 425 | &sensor_dev_attr_in2_alarm.dev_attr.attr, | ||
| 426 | &sensor_dev_attr_in3_alarm.dev_attr.attr, | ||
| 427 | &sensor_dev_attr_in0_beep.dev_attr.attr, | ||
| 428 | &sensor_dev_attr_in1_beep.dev_attr.attr, | ||
| 429 | &sensor_dev_attr_in2_beep.dev_attr.attr, | ||
| 430 | &sensor_dev_attr_in3_beep.dev_attr.attr, | ||
| 357 | 431 | ||
| 358 | &dev_attr_fan1_auto.attr, | 432 | &dev_attr_fan1_auto.attr, |
| 359 | &dev_attr_fan1_input.attr, | 433 | &sensor_dev_attr_fan1_input.dev_attr.attr, |
| 360 | &dev_attr_fan2_input.attr, | 434 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 361 | &dev_attr_fan1_min.attr, | 435 | &sensor_dev_attr_fan1_min.dev_attr.attr, |
| 362 | &dev_attr_fan2_min.attr, | 436 | &sensor_dev_attr_fan2_min.dev_attr.attr, |
| 363 | &dev_attr_fan1_div.attr, | 437 | &sensor_dev_attr_fan1_div.dev_attr.attr, |
| 364 | &dev_attr_fan2_div.attr, | 438 | &sensor_dev_attr_fan2_div.dev_attr.attr, |
| 439 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 440 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | ||
| 441 | &sensor_dev_attr_fan1_beep.dev_attr.attr, | ||
| 442 | &sensor_dev_attr_fan2_beep.dev_attr.attr, | ||
| 365 | 443 | ||
| 366 | &dev_attr_temp1_input.attr, | 444 | &dev_attr_temp1_input.attr, |
| 367 | &dev_attr_temp1_max.attr, | 445 | &dev_attr_temp1_max.attr, |
| 368 | &dev_attr_temp1_max_hyst.attr, | 446 | &dev_attr_temp1_max_hyst.attr, |
| 447 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 448 | &sensor_dev_attr_temp1_beep.dev_attr.attr, | ||
| 369 | 449 | ||
| 370 | &dev_attr_alarms.attr, | 450 | &dev_attr_alarms.attr, |
| 371 | &dev_attr_beep_enable.attr, | 451 | &dev_attr_beep_enable.attr, |
| @@ -377,6 +457,17 @@ static const struct attribute_group gl518_group = { | |||
| 377 | .attrs = gl518_attributes, | 457 | .attrs = gl518_attributes, |
| 378 | }; | 458 | }; |
| 379 | 459 | ||
| 460 | static struct attribute *gl518_attributes_r80[] = { | ||
| 461 | &dev_attr_in0_input.attr, | ||
| 462 | &dev_attr_in1_input.attr, | ||
| 463 | &dev_attr_in2_input.attr, | ||
| 464 | NULL | ||
| 465 | }; | ||
| 466 | |||
| 467 | static const struct attribute_group gl518_group_r80 = { | ||
| 468 | .attrs = gl518_attributes_r80, | ||
| 469 | }; | ||
| 470 | |||
| 380 | /* | 471 | /* |
| 381 | * Real code | 472 | * Real code |
| 382 | */ | 473 | */ |
| @@ -391,7 +482,7 @@ static int gl518_attach_adapter(struct i2c_adapter *adapter) | |||
| 391 | static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) | 482 | static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) |
| 392 | { | 483 | { |
| 393 | int i; | 484 | int i; |
| 394 | struct i2c_client *new_client; | 485 | struct i2c_client *client; |
| 395 | struct gl518_data *data; | 486 | struct gl518_data *data; |
| 396 | int err = 0; | 487 | int err = 0; |
| 397 | 488 | ||
| @@ -408,25 +499,24 @@ static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 408 | goto exit; | 499 | goto exit; |
| 409 | } | 500 | } |
| 410 | 501 | ||
| 411 | new_client = &data->client; | 502 | client = &data->client; |
| 412 | i2c_set_clientdata(new_client, data); | 503 | i2c_set_clientdata(client, data); |
| 413 | 504 | ||
| 414 | new_client->addr = address; | 505 | client->addr = address; |
| 415 | new_client->adapter = adapter; | 506 | client->adapter = adapter; |
| 416 | new_client->driver = &gl518_driver; | 507 | client->driver = &gl518_driver; |
| 417 | new_client->flags = 0; | ||
| 418 | 508 | ||
| 419 | /* Now, we do the remaining detection. */ | 509 | /* Now, we do the remaining detection. */ |
| 420 | 510 | ||
| 421 | if (kind < 0) { | 511 | if (kind < 0) { |
| 422 | if ((gl518_read_value(new_client, GL518_REG_CHIP_ID) != 0x80) | 512 | if ((gl518_read_value(client, GL518_REG_CHIP_ID) != 0x80) |
| 423 | || (gl518_read_value(new_client, GL518_REG_CONF) & 0x80)) | 513 | || (gl518_read_value(client, GL518_REG_CONF) & 0x80)) |
| 424 | goto exit_free; | 514 | goto exit_free; |
| 425 | } | 515 | } |
| 426 | 516 | ||
| 427 | /* Determine the chip type. */ | 517 | /* Determine the chip type. */ |
| 428 | if (kind <= 0) { | 518 | if (kind <= 0) { |
| 429 | i = gl518_read_value(new_client, GL518_REG_REVISION); | 519 | i = gl518_read_value(client, GL518_REG_REVISION); |
| 430 | if (i == 0x00) { | 520 | if (i == 0x00) { |
| 431 | kind = gl518sm_r00; | 521 | kind = gl518sm_r00; |
| 432 | } else if (i == 0x80) { | 522 | } else if (i == 0x80) { |
| @@ -442,25 +532,27 @@ static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 442 | } | 532 | } |
| 443 | 533 | ||
| 444 | /* Fill in the remaining client fields */ | 534 | /* Fill in the remaining client fields */ |
| 445 | strlcpy(new_client->name, "gl518sm", I2C_NAME_SIZE); | 535 | strlcpy(client->name, "gl518sm", I2C_NAME_SIZE); |
| 446 | data->type = kind; | 536 | data->type = kind; |
| 447 | data->valid = 0; | ||
| 448 | mutex_init(&data->update_lock); | 537 | mutex_init(&data->update_lock); |
| 449 | 538 | ||
| 450 | /* Tell the I2C layer a new client has arrived */ | 539 | /* Tell the I2C layer a new client has arrived */ |
| 451 | if ((err = i2c_attach_client(new_client))) | 540 | if ((err = i2c_attach_client(client))) |
| 452 | goto exit_free; | 541 | goto exit_free; |
| 453 | 542 | ||
| 454 | /* Initialize the GL518SM chip */ | 543 | /* Initialize the GL518SM chip */ |
| 455 | data->alarm_mask = 0xff; | 544 | data->alarm_mask = 0xff; |
| 456 | data->voltage_in[0]=data->voltage_in[1]=data->voltage_in[2]=0; | 545 | gl518_init_client(client); |
| 457 | gl518_init_client((struct i2c_client *) new_client); | ||
| 458 | 546 | ||
| 459 | /* Register sysfs hooks */ | 547 | /* Register sysfs hooks */ |
| 460 | if ((err = sysfs_create_group(&new_client->dev.kobj, &gl518_group))) | 548 | if ((err = sysfs_create_group(&client->dev.kobj, &gl518_group))) |
| 461 | goto exit_detach; | 549 | goto exit_detach; |
| 550 | if (data->type == gl518sm_r80) | ||
| 551 | if ((err = sysfs_create_group(&client->dev.kobj, | ||
| 552 | &gl518_group_r80))) | ||
| 553 | goto exit_remove_files; | ||
| 462 | 554 | ||
| 463 | data->hwmon_dev = hwmon_device_register(&new_client->dev); | 555 | data->hwmon_dev = hwmon_device_register(&client->dev); |
| 464 | if (IS_ERR(data->hwmon_dev)) { | 556 | if (IS_ERR(data->hwmon_dev)) { |
| 465 | err = PTR_ERR(data->hwmon_dev); | 557 | err = PTR_ERR(data->hwmon_dev); |
| 466 | goto exit_remove_files; | 558 | goto exit_remove_files; |
| @@ -469,9 +561,11 @@ static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 469 | return 0; | 561 | return 0; |
| 470 | 562 | ||
| 471 | exit_remove_files: | 563 | exit_remove_files: |
| 472 | sysfs_remove_group(&new_client->dev.kobj, &gl518_group); | 564 | sysfs_remove_group(&client->dev.kobj, &gl518_group); |
| 565 | if (data->type == gl518sm_r80) | ||
| 566 | sysfs_remove_group(&client->dev.kobj, &gl518_group_r80); | ||
| 473 | exit_detach: | 567 | exit_detach: |
| 474 | i2c_detach_client(new_client); | 568 | i2c_detach_client(client); |
| 475 | exit_free: | 569 | exit_free: |
| 476 | kfree(data); | 570 | kfree(data); |
| 477 | exit: | 571 | exit: |
| @@ -504,6 +598,8 @@ static int gl518_detach_client(struct i2c_client *client) | |||
| 504 | 598 | ||
| 505 | hwmon_device_unregister(data->hwmon_dev); | 599 | hwmon_device_unregister(data->hwmon_dev); |
| 506 | sysfs_remove_group(&client->dev.kobj, &gl518_group); | 600 | sysfs_remove_group(&client->dev.kobj, &gl518_group); |
| 601 | if (data->type == gl518sm_r80) | ||
| 602 | sysfs_remove_group(&client->dev.kobj, &gl518_group_r80); | ||
| 507 | 603 | ||
| 508 | if ((err = i2c_detach_client(client))) | 604 | if ((err = i2c_detach_client(client))) |
| 509 | return err; | 605 | return err; |
| @@ -512,9 +608,9 @@ static int gl518_detach_client(struct i2c_client *client) | |||
| 512 | return 0; | 608 | return 0; |
| 513 | } | 609 | } |
| 514 | 610 | ||
| 515 | /* Registers 0x07 to 0x0c are word-sized, others are byte-sized | 611 | /* Registers 0x07 to 0x0c are word-sized, others are byte-sized |
| 516 | GL518 uses a high-byte first convention, which is exactly opposite to | 612 | GL518 uses a high-byte first convention, which is exactly opposite to |
| 517 | the usual practice. */ | 613 | the SMBus standard. */ |
| 518 | static int gl518_read_value(struct i2c_client *client, u8 reg) | 614 | static int gl518_read_value(struct i2c_client *client, u8 reg) |
| 519 | { | 615 | { |
| 520 | if ((reg >= 0x07) && (reg <= 0x0c)) | 616 | if ((reg >= 0x07) && (reg <= 0x0c)) |
| @@ -523,9 +619,6 @@ static int gl518_read_value(struct i2c_client *client, u8 reg) | |||
| 523 | return i2c_smbus_read_byte_data(client, reg); | 619 | return i2c_smbus_read_byte_data(client, reg); |
| 524 | } | 620 | } |
| 525 | 621 | ||
| 526 | /* Registers 0x07 to 0x0c are word-sized, others are byte-sized | ||
| 527 | GL518 uses a high-byte first convention, which is exactly opposite to | ||
| 528 | the usual practice. */ | ||
| 529 | static int gl518_write_value(struct i2c_client *client, u8 reg, u16 value) | 622 | static int gl518_write_value(struct i2c_client *client, u8 reg, u16 value) |
| 530 | { | 623 | { |
| 531 | if ((reg >= 0x07) && (reg <= 0x0c)) | 624 | if ((reg >= 0x07) && (reg <= 0x0c)) |
diff --git a/drivers/hwmon/gl520sm.c b/drivers/hwmon/gl520sm.c index 2d39d8fc2389..03ecdc334764 100644 --- a/drivers/hwmon/gl520sm.c +++ b/drivers/hwmon/gl520sm.c | |||
| @@ -27,6 +27,7 @@ | |||
| 27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
| 28 | #include <linux/i2c.h> | 28 | #include <linux/i2c.h> |
| 29 | #include <linux/hwmon.h> | 29 | #include <linux/hwmon.h> |
| 30 | #include <linux/hwmon-sysfs.h> | ||
| 30 | #include <linux/hwmon-vid.h> | 31 | #include <linux/hwmon-vid.h> |
| 31 | #include <linux/err.h> | 32 | #include <linux/err.h> |
| 32 | #include <linux/mutex.h> | 33 | #include <linux/mutex.h> |
| @@ -43,9 +44,9 @@ static unsigned short normal_i2c[] = { 0x2c, 0x2d, I2C_CLIENT_END }; | |||
| 43 | /* Insmod parameters */ | 44 | /* Insmod parameters */ |
| 44 | I2C_CLIENT_INSMOD_1(gl520sm); | 45 | I2C_CLIENT_INSMOD_1(gl520sm); |
| 45 | 46 | ||
| 46 | /* Many GL520 constants specified below | 47 | /* Many GL520 constants specified below |
| 47 | One of the inputs can be configured as either temp or voltage. | 48 | One of the inputs can be configured as either temp or voltage. |
| 48 | That's why _TEMP2 and _IN4 access the same register | 49 | That's why _TEMP2 and _IN4 access the same register |
| 49 | */ | 50 | */ |
| 50 | 51 | ||
| 51 | /* The GL520 registers */ | 52 | /* The GL520 registers */ |
| @@ -56,37 +57,14 @@ That's why _TEMP2 and _IN4 access the same register | |||
| 56 | 57 | ||
| 57 | #define GL520_REG_VID_INPUT 0x02 | 58 | #define GL520_REG_VID_INPUT 0x02 |
| 58 | 59 | ||
| 59 | #define GL520_REG_IN0_INPUT 0x15 | 60 | static const u8 GL520_REG_IN_INPUT[] = { 0x15, 0x14, 0x13, 0x0d, 0x0e }; |
| 60 | #define GL520_REG_IN0_LIMIT 0x0c | 61 | static const u8 GL520_REG_IN_LIMIT[] = { 0x0c, 0x09, 0x0a, 0x0b }; |
| 61 | #define GL520_REG_IN0_MIN GL520_REG_IN0_LIMIT | 62 | static const u8 GL520_REG_IN_MIN[] = { 0x0c, 0x09, 0x0a, 0x0b, 0x18 }; |
| 62 | #define GL520_REG_IN0_MAX GL520_REG_IN0_LIMIT | 63 | static const u8 GL520_REG_IN_MAX[] = { 0x0c, 0x09, 0x0a, 0x0b, 0x17 }; |
| 63 | 64 | ||
| 64 | #define GL520_REG_IN1_INPUT 0x14 | 65 | static const u8 GL520_REG_TEMP_INPUT[] = { 0x04, 0x0e }; |
| 65 | #define GL520_REG_IN1_LIMIT 0x09 | 66 | static const u8 GL520_REG_TEMP_MAX[] = { 0x05, 0x17 }; |
| 66 | #define GL520_REG_IN1_MIN GL520_REG_IN1_LIMIT | 67 | static const u8 GL520_REG_TEMP_MAX_HYST[] = { 0x06, 0x18 }; |
| 67 | #define GL520_REG_IN1_MAX GL520_REG_IN1_LIMIT | ||
| 68 | |||
| 69 | #define GL520_REG_IN2_INPUT 0x13 | ||
| 70 | #define GL520_REG_IN2_LIMIT 0x0a | ||
| 71 | #define GL520_REG_IN2_MIN GL520_REG_IN2_LIMIT | ||
| 72 | #define GL520_REG_IN2_MAX GL520_REG_IN2_LIMIT | ||
| 73 | |||
| 74 | #define GL520_REG_IN3_INPUT 0x0d | ||
| 75 | #define GL520_REG_IN3_LIMIT 0x0b | ||
| 76 | #define GL520_REG_IN3_MIN GL520_REG_IN3_LIMIT | ||
| 77 | #define GL520_REG_IN3_MAX GL520_REG_IN3_LIMIT | ||
| 78 | |||
| 79 | #define GL520_REG_IN4_INPUT 0x0e | ||
| 80 | #define GL520_REG_IN4_MAX 0x17 | ||
| 81 | #define GL520_REG_IN4_MIN 0x18 | ||
| 82 | |||
| 83 | #define GL520_REG_TEMP1_INPUT 0x04 | ||
| 84 | #define GL520_REG_TEMP1_MAX 0x05 | ||
| 85 | #define GL520_REG_TEMP1_MAX_HYST 0x06 | ||
| 86 | |||
| 87 | #define GL520_REG_TEMP2_INPUT 0x0e | ||
| 88 | #define GL520_REG_TEMP2_MAX 0x17 | ||
| 89 | #define GL520_REG_TEMP2_MAX_HYST 0x18 | ||
| 90 | 68 | ||
| 91 | #define GL520_REG_FAN_INPUT 0x07 | 69 | #define GL520_REG_FAN_INPUT 0x07 |
| 92 | #define GL520_REG_FAN_MIN 0x08 | 70 | #define GL520_REG_FAN_MIN 0x08 |
| @@ -114,7 +92,6 @@ static struct i2c_driver gl520_driver = { | |||
| 114 | .driver = { | 92 | .driver = { |
| 115 | .name = "gl520sm", | 93 | .name = "gl520sm", |
| 116 | }, | 94 | }, |
| 117 | .id = I2C_DRIVERID_GL520, | ||
| 118 | .attach_adapter = gl520_attach_adapter, | 95 | .attach_adapter = gl520_attach_adapter, |
| 119 | .detach_client = gl520_detach_client, | 96 | .detach_client = gl520_detach_client, |
| 120 | }; | 97 | }; |
| @@ -150,93 +127,13 @@ struct gl520_data { | |||
| 150 | * Sysfs stuff | 127 | * Sysfs stuff |
| 151 | */ | 128 | */ |
| 152 | 129 | ||
| 153 | #define sysfs_r(type, n, item, reg) \ | 130 | static ssize_t get_cpu_vid(struct device *dev, struct device_attribute *attr, |
| 154 | static ssize_t get_##type##item (struct gl520_data *, char *, int); \ | 131 | char *buf) |
| 155 | static ssize_t get_##type##n##item (struct device *, struct device_attribute *attr, char *); \ | ||
| 156 | static ssize_t get_##type##n##item (struct device *dev, struct device_attribute *attr, char *buf) \ | ||
| 157 | { \ | ||
| 158 | struct gl520_data *data = gl520_update_device(dev); \ | ||
| 159 | return get_##type##item(data, buf, (n)); \ | ||
| 160 | } | ||
| 161 | |||
| 162 | #define sysfs_w(type, n, item, reg) \ | ||
| 163 | static ssize_t set_##type##item (struct i2c_client *, struct gl520_data *, const char *, size_t, int, int); \ | ||
| 164 | static ssize_t set_##type##n##item (struct device *, struct device_attribute *attr, const char *, size_t); \ | ||
| 165 | static ssize_t set_##type##n##item (struct device *dev, struct device_attribute *attr, const char *buf, size_t count) \ | ||
| 166 | { \ | ||
| 167 | struct i2c_client *client = to_i2c_client(dev); \ | ||
| 168 | struct gl520_data *data = i2c_get_clientdata(client); \ | ||
| 169 | return set_##type##item(client, data, buf, count, (n), reg); \ | ||
| 170 | } | ||
| 171 | |||
| 172 | #define sysfs_rw_n(type, n, item, reg) \ | ||
| 173 | sysfs_r(type, n, item, reg) \ | ||
| 174 | sysfs_w(type, n, item, reg) \ | ||
| 175 | static DEVICE_ATTR(type##n##item, S_IRUGO | S_IWUSR, get_##type##n##item, set_##type##n##item); | ||
| 176 | |||
| 177 | #define sysfs_ro_n(type, n, item, reg) \ | ||
| 178 | sysfs_r(type, n, item, reg) \ | ||
| 179 | static DEVICE_ATTR(type##n##item, S_IRUGO, get_##type##n##item, NULL); | ||
| 180 | |||
| 181 | #define sysfs_rw(type, item, reg) \ | ||
| 182 | sysfs_r(type, 0, item, reg) \ | ||
| 183 | sysfs_w(type, 0, item, reg) \ | ||
| 184 | static DEVICE_ATTR(type##item, S_IRUGO | S_IWUSR, get_##type##0##item, set_##type##0##item); | ||
| 185 | |||
| 186 | #define sysfs_ro(type, item, reg) \ | ||
| 187 | sysfs_r(type, 0, item, reg) \ | ||
| 188 | static DEVICE_ATTR(type##item, S_IRUGO, get_##type##0##item, NULL); | ||
| 189 | |||
| 190 | |||
| 191 | #define sysfs_vid(n) \ | ||
| 192 | sysfs_ro_n(cpu, n, _vid, GL520_REG_VID_INPUT) | ||
| 193 | |||
| 194 | #define sysfs_in(n) \ | ||
| 195 | sysfs_ro_n(in, n, _input, GL520_REG_IN##n##INPUT) \ | ||
| 196 | sysfs_rw_n(in, n, _min, GL520_REG_IN##n##_MIN) \ | ||
| 197 | sysfs_rw_n(in, n, _max, GL520_REG_IN##n##_MAX) \ | ||
| 198 | |||
| 199 | #define sysfs_fan(n) \ | ||
| 200 | sysfs_ro_n(fan, n, _input, GL520_REG_FAN_INPUT) \ | ||
| 201 | sysfs_rw_n(fan, n, _min, GL520_REG_FAN_MIN) \ | ||
| 202 | sysfs_rw_n(fan, n, _div, GL520_REG_FAN_DIV) | ||
| 203 | |||
| 204 | #define sysfs_fan_off(n) \ | ||
| 205 | sysfs_rw_n(fan, n, _off, GL520_REG_FAN_OFF) \ | ||
| 206 | |||
| 207 | #define sysfs_temp(n) \ | ||
| 208 | sysfs_ro_n(temp, n, _input, GL520_REG_TEMP##n##_INPUT) \ | ||
| 209 | sysfs_rw_n(temp, n, _max, GL520_REG_TEMP##n##_MAX) \ | ||
| 210 | sysfs_rw_n(temp, n, _max_hyst, GL520_REG_TEMP##n##_MAX_HYST) | ||
| 211 | |||
| 212 | #define sysfs_alarms() \ | ||
| 213 | sysfs_ro(alarms, , GL520_REG_ALARMS) \ | ||
| 214 | sysfs_rw(beep_enable, , GL520_REG_BEEP_ENABLE) \ | ||
| 215 | sysfs_rw(beep_mask, , GL520_REG_BEEP_MASK) | ||
| 216 | |||
| 217 | |||
| 218 | sysfs_vid(0) | ||
| 219 | |||
| 220 | sysfs_in(0) | ||
| 221 | sysfs_in(1) | ||
| 222 | sysfs_in(2) | ||
| 223 | sysfs_in(3) | ||
| 224 | sysfs_in(4) | ||
| 225 | |||
| 226 | sysfs_fan(1) | ||
| 227 | sysfs_fan(2) | ||
| 228 | sysfs_fan_off(1) | ||
| 229 | |||
| 230 | sysfs_temp(1) | ||
| 231 | sysfs_temp(2) | ||
| 232 | |||
| 233 | sysfs_alarms() | ||
| 234 | |||
| 235 | |||
| 236 | static ssize_t get_cpu_vid(struct gl520_data *data, char *buf, int n) | ||
| 237 | { | 132 | { |
| 133 | struct gl520_data *data = gl520_update_device(dev); | ||
| 238 | return sprintf(buf, "%u\n", vid_from_reg(data->vid, data->vrm)); | 134 | return sprintf(buf, "%u\n", vid_from_reg(data->vid, data->vrm)); |
| 239 | } | 135 | } |
| 136 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, get_cpu_vid, NULL); | ||
| 240 | 137 | ||
| 241 | #define VDD_FROM_REG(val) (((val)*95+2)/4) | 138 | #define VDD_FROM_REG(val) (((val)*95+2)/4) |
| 242 | #define VDD_TO_REG(val) (SENSORS_LIMIT((((val)*4+47)/95),0,255)) | 139 | #define VDD_TO_REG(val) (SENSORS_LIMIT((((val)*4+47)/95),0,255)) |
| @@ -244,8 +141,11 @@ static ssize_t get_cpu_vid(struct gl520_data *data, char *buf, int n) | |||
| 244 | #define IN_FROM_REG(val) ((val)*19) | 141 | #define IN_FROM_REG(val) ((val)*19) |
| 245 | #define IN_TO_REG(val) (SENSORS_LIMIT((((val)+9)/19),0,255)) | 142 | #define IN_TO_REG(val) (SENSORS_LIMIT((((val)+9)/19),0,255)) |
| 246 | 143 | ||
| 247 | static ssize_t get_in_input(struct gl520_data *data, char *buf, int n) | 144 | static ssize_t get_in_input(struct device *dev, struct device_attribute *attr, |
| 145 | char *buf) | ||
| 248 | { | 146 | { |
| 147 | int n = to_sensor_dev_attr(attr)->index; | ||
| 148 | struct gl520_data *data = gl520_update_device(dev); | ||
| 249 | u8 r = data->in_input[n]; | 149 | u8 r = data->in_input[n]; |
| 250 | 150 | ||
| 251 | if (n == 0) | 151 | if (n == 0) |
| @@ -254,8 +154,11 @@ static ssize_t get_in_input(struct gl520_data *data, char *buf, int n) | |||
| 254 | return sprintf(buf, "%d\n", IN_FROM_REG(r)); | 154 | return sprintf(buf, "%d\n", IN_FROM_REG(r)); |
| 255 | } | 155 | } |
| 256 | 156 | ||
| 257 | static ssize_t get_in_min(struct gl520_data *data, char *buf, int n) | 157 | static ssize_t get_in_min(struct device *dev, struct device_attribute *attr, |
| 158 | char *buf) | ||
| 258 | { | 159 | { |
| 160 | int n = to_sensor_dev_attr(attr)->index; | ||
| 161 | struct gl520_data *data = gl520_update_device(dev); | ||
| 259 | u8 r = data->in_min[n]; | 162 | u8 r = data->in_min[n]; |
| 260 | 163 | ||
| 261 | if (n == 0) | 164 | if (n == 0) |
| @@ -264,8 +167,11 @@ static ssize_t get_in_min(struct gl520_data *data, char *buf, int n) | |||
| 264 | return sprintf(buf, "%d\n", IN_FROM_REG(r)); | 167 | return sprintf(buf, "%d\n", IN_FROM_REG(r)); |
| 265 | } | 168 | } |
| 266 | 169 | ||
| 267 | static ssize_t get_in_max(struct gl520_data *data, char *buf, int n) | 170 | static ssize_t get_in_max(struct device *dev, struct device_attribute *attr, |
| 171 | char *buf) | ||
| 268 | { | 172 | { |
| 173 | int n = to_sensor_dev_attr(attr)->index; | ||
| 174 | struct gl520_data *data = gl520_update_device(dev); | ||
| 269 | u8 r = data->in_max[n]; | 175 | u8 r = data->in_max[n]; |
| 270 | 176 | ||
| 271 | if (n == 0) | 177 | if (n == 0) |
| @@ -274,8 +180,12 @@ static ssize_t get_in_max(struct gl520_data *data, char *buf, int n) | |||
| 274 | return sprintf(buf, "%d\n", IN_FROM_REG(r)); | 180 | return sprintf(buf, "%d\n", IN_FROM_REG(r)); |
| 275 | } | 181 | } |
| 276 | 182 | ||
| 277 | static ssize_t set_in_min(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 183 | static ssize_t set_in_min(struct device *dev, struct device_attribute *attr, |
| 184 | const char *buf, size_t count) | ||
| 278 | { | 185 | { |
| 186 | struct i2c_client *client = to_i2c_client(dev); | ||
| 187 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 188 | int n = to_sensor_dev_attr(attr)->index; | ||
| 279 | long v = simple_strtol(buf, NULL, 10); | 189 | long v = simple_strtol(buf, NULL, 10); |
| 280 | u8 r; | 190 | u8 r; |
| 281 | 191 | ||
| @@ -289,16 +199,22 @@ static ssize_t set_in_min(struct i2c_client *client, struct gl520_data *data, co | |||
| 289 | data->in_min[n] = r; | 199 | data->in_min[n] = r; |
| 290 | 200 | ||
| 291 | if (n < 4) | 201 | if (n < 4) |
| 292 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0xff) | r); | 202 | gl520_write_value(client, GL520_REG_IN_MIN[n], |
| 203 | (gl520_read_value(client, GL520_REG_IN_MIN[n]) | ||
| 204 | & ~0xff) | r); | ||
| 293 | else | 205 | else |
| 294 | gl520_write_value(client, reg, r); | 206 | gl520_write_value(client, GL520_REG_IN_MIN[n], r); |
| 295 | 207 | ||
| 296 | mutex_unlock(&data->update_lock); | 208 | mutex_unlock(&data->update_lock); |
| 297 | return count; | 209 | return count; |
| 298 | } | 210 | } |
| 299 | 211 | ||
| 300 | static ssize_t set_in_max(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 212 | static ssize_t set_in_max(struct device *dev, struct device_attribute *attr, |
| 213 | const char *buf, size_t count) | ||
| 301 | { | 214 | { |
| 215 | struct i2c_client *client = to_i2c_client(dev); | ||
| 216 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 217 | int n = to_sensor_dev_attr(attr)->index; | ||
| 302 | long v = simple_strtol(buf, NULL, 10); | 218 | long v = simple_strtol(buf, NULL, 10); |
| 303 | u8 r; | 219 | u8 r; |
| 304 | 220 | ||
| @@ -312,57 +228,109 @@ static ssize_t set_in_max(struct i2c_client *client, struct gl520_data *data, co | |||
| 312 | data->in_max[n] = r; | 228 | data->in_max[n] = r; |
| 313 | 229 | ||
| 314 | if (n < 4) | 230 | if (n < 4) |
| 315 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0xff00) | (r << 8)); | 231 | gl520_write_value(client, GL520_REG_IN_MAX[n], |
| 232 | (gl520_read_value(client, GL520_REG_IN_MAX[n]) | ||
| 233 | & ~0xff00) | (r << 8)); | ||
| 316 | else | 234 | else |
| 317 | gl520_write_value(client, reg, r); | 235 | gl520_write_value(client, GL520_REG_IN_MAX[n], r); |
| 318 | 236 | ||
| 319 | mutex_unlock(&data->update_lock); | 237 | mutex_unlock(&data->update_lock); |
| 320 | return count; | 238 | return count; |
| 321 | } | 239 | } |
| 322 | 240 | ||
| 241 | static SENSOR_DEVICE_ATTR(in0_input, S_IRUGO, get_in_input, NULL, 0); | ||
| 242 | static SENSOR_DEVICE_ATTR(in1_input, S_IRUGO, get_in_input, NULL, 1); | ||
| 243 | static SENSOR_DEVICE_ATTR(in2_input, S_IRUGO, get_in_input, NULL, 2); | ||
| 244 | static SENSOR_DEVICE_ATTR(in3_input, S_IRUGO, get_in_input, NULL, 3); | ||
| 245 | static SENSOR_DEVICE_ATTR(in4_input, S_IRUGO, get_in_input, NULL, 4); | ||
| 246 | static SENSOR_DEVICE_ATTR(in0_min, S_IRUGO | S_IWUSR, | ||
| 247 | get_in_min, set_in_min, 0); | ||
| 248 | static SENSOR_DEVICE_ATTR(in1_min, S_IRUGO | S_IWUSR, | ||
| 249 | get_in_min, set_in_min, 1); | ||
| 250 | static SENSOR_DEVICE_ATTR(in2_min, S_IRUGO | S_IWUSR, | ||
| 251 | get_in_min, set_in_min, 2); | ||
| 252 | static SENSOR_DEVICE_ATTR(in3_min, S_IRUGO | S_IWUSR, | ||
| 253 | get_in_min, set_in_min, 3); | ||
| 254 | static SENSOR_DEVICE_ATTR(in4_min, S_IRUGO | S_IWUSR, | ||
| 255 | get_in_min, set_in_min, 4); | ||
| 256 | static SENSOR_DEVICE_ATTR(in0_max, S_IRUGO | S_IWUSR, | ||
| 257 | get_in_max, set_in_max, 0); | ||
| 258 | static SENSOR_DEVICE_ATTR(in1_max, S_IRUGO | S_IWUSR, | ||
| 259 | get_in_max, set_in_max, 1); | ||
| 260 | static SENSOR_DEVICE_ATTR(in2_max, S_IRUGO | S_IWUSR, | ||
| 261 | get_in_max, set_in_max, 2); | ||
| 262 | static SENSOR_DEVICE_ATTR(in3_max, S_IRUGO | S_IWUSR, | ||
| 263 | get_in_max, set_in_max, 3); | ||
| 264 | static SENSOR_DEVICE_ATTR(in4_max, S_IRUGO | S_IWUSR, | ||
| 265 | get_in_max, set_in_max, 4); | ||
| 266 | |||
| 323 | #define DIV_FROM_REG(val) (1 << (val)) | 267 | #define DIV_FROM_REG(val) (1 << (val)) |
| 324 | #define FAN_FROM_REG(val,div) ((val)==0 ? 0 : (480000/((val) << (div)))) | 268 | #define FAN_FROM_REG(val,div) ((val)==0 ? 0 : (480000/((val) << (div)))) |
| 325 | #define FAN_TO_REG(val,div) ((val)<=0?0:SENSORS_LIMIT((480000 + ((val) << ((div)-1))) / ((val) << (div)), 1, 255)); | 269 | #define FAN_TO_REG(val,div) ((val)<=0?0:SENSORS_LIMIT((480000 + ((val) << ((div)-1))) / ((val) << (div)), 1, 255)); |
| 326 | 270 | ||
| 327 | static ssize_t get_fan_input(struct gl520_data *data, char *buf, int n) | 271 | static ssize_t get_fan_input(struct device *dev, struct device_attribute *attr, |
| 272 | char *buf) | ||
| 328 | { | 273 | { |
| 329 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_input[n - 1], data->fan_div[n - 1])); | 274 | int n = to_sensor_dev_attr(attr)->index; |
| 275 | struct gl520_data *data = gl520_update_device(dev); | ||
| 276 | |||
| 277 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_input[n], | ||
| 278 | data->fan_div[n])); | ||
| 330 | } | 279 | } |
| 331 | 280 | ||
| 332 | static ssize_t get_fan_min(struct gl520_data *data, char *buf, int n) | 281 | static ssize_t get_fan_min(struct device *dev, struct device_attribute *attr, |
| 282 | char *buf) | ||
| 333 | { | 283 | { |
| 334 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_min[n - 1], data->fan_div[n - 1])); | 284 | int n = to_sensor_dev_attr(attr)->index; |
| 285 | struct gl520_data *data = gl520_update_device(dev); | ||
| 286 | |||
| 287 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->fan_min[n], | ||
| 288 | data->fan_div[n])); | ||
| 335 | } | 289 | } |
| 336 | 290 | ||
| 337 | static ssize_t get_fan_div(struct gl520_data *data, char *buf, int n) | 291 | static ssize_t get_fan_div(struct device *dev, struct device_attribute *attr, |
| 292 | char *buf) | ||
| 338 | { | 293 | { |
| 339 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->fan_div[n - 1])); | 294 | int n = to_sensor_dev_attr(attr)->index; |
| 295 | struct gl520_data *data = gl520_update_device(dev); | ||
| 296 | |||
| 297 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->fan_div[n])); | ||
| 340 | } | 298 | } |
| 341 | 299 | ||
| 342 | static ssize_t get_fan_off(struct gl520_data *data, char *buf, int n) | 300 | static ssize_t get_fan_off(struct device *dev, struct device_attribute *attr, |
| 301 | char *buf) | ||
| 343 | { | 302 | { |
| 303 | struct gl520_data *data = gl520_update_device(dev); | ||
| 344 | return sprintf(buf, "%d\n", data->fan_off); | 304 | return sprintf(buf, "%d\n", data->fan_off); |
| 345 | } | 305 | } |
| 346 | 306 | ||
| 347 | static ssize_t set_fan_min(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 307 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, |
| 308 | const char *buf, size_t count) | ||
| 348 | { | 309 | { |
| 310 | struct i2c_client *client = to_i2c_client(dev); | ||
| 311 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 312 | int n = to_sensor_dev_attr(attr)->index; | ||
| 349 | unsigned long v = simple_strtoul(buf, NULL, 10); | 313 | unsigned long v = simple_strtoul(buf, NULL, 10); |
| 350 | u8 r; | 314 | u8 r; |
| 351 | 315 | ||
| 352 | mutex_lock(&data->update_lock); | 316 | mutex_lock(&data->update_lock); |
| 353 | r = FAN_TO_REG(v, data->fan_div[n - 1]); | 317 | r = FAN_TO_REG(v, data->fan_div[n]); |
| 354 | data->fan_min[n - 1] = r; | 318 | data->fan_min[n] = r; |
| 355 | 319 | ||
| 356 | if (n == 1) | 320 | if (n == 0) |
| 357 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0xff00) | (r << 8)); | 321 | gl520_write_value(client, GL520_REG_FAN_MIN, |
| 322 | (gl520_read_value(client, GL520_REG_FAN_MIN) | ||
| 323 | & ~0xff00) | (r << 8)); | ||
| 358 | else | 324 | else |
| 359 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0xff) | r); | 325 | gl520_write_value(client, GL520_REG_FAN_MIN, |
| 326 | (gl520_read_value(client, GL520_REG_FAN_MIN) | ||
| 327 | & ~0xff) | r); | ||
| 360 | 328 | ||
| 361 | data->beep_mask = gl520_read_value(client, GL520_REG_BEEP_MASK); | 329 | data->beep_mask = gl520_read_value(client, GL520_REG_BEEP_MASK); |
| 362 | if (data->fan_min[n - 1] == 0) | 330 | if (data->fan_min[n] == 0) |
| 363 | data->alarm_mask &= (n == 1) ? ~0x20 : ~0x40; | 331 | data->alarm_mask &= (n == 0) ? ~0x20 : ~0x40; |
| 364 | else | 332 | else |
| 365 | data->alarm_mask |= (n == 1) ? 0x20 : 0x40; | 333 | data->alarm_mask |= (n == 0) ? 0x20 : 0x40; |
| 366 | data->beep_mask &= data->alarm_mask; | 334 | data->beep_mask &= data->alarm_mask; |
| 367 | gl520_write_value(client, GL520_REG_BEEP_MASK, data->beep_mask); | 335 | gl520_write_value(client, GL520_REG_BEEP_MASK, data->beep_mask); |
| 368 | 336 | ||
| @@ -370,8 +338,12 @@ static ssize_t set_fan_min(struct i2c_client *client, struct gl520_data *data, c | |||
| 370 | return count; | 338 | return count; |
| 371 | } | 339 | } |
| 372 | 340 | ||
| 373 | static ssize_t set_fan_div(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 341 | static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, |
| 342 | const char *buf, size_t count) | ||
| 374 | { | 343 | { |
| 344 | struct i2c_client *client = to_i2c_client(dev); | ||
| 345 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 346 | int n = to_sensor_dev_attr(attr)->index; | ||
| 375 | unsigned long v = simple_strtoul(buf, NULL, 10); | 347 | unsigned long v = simple_strtoul(buf, NULL, 10); |
| 376 | u8 r; | 348 | u8 r; |
| 377 | 349 | ||
| @@ -386,133 +358,282 @@ static ssize_t set_fan_div(struct i2c_client *client, struct gl520_data *data, c | |||
| 386 | } | 358 | } |
| 387 | 359 | ||
| 388 | mutex_lock(&data->update_lock); | 360 | mutex_lock(&data->update_lock); |
| 389 | data->fan_div[n - 1] = r; | 361 | data->fan_div[n] = r; |
| 390 | 362 | ||
| 391 | if (n == 1) | 363 | if (n == 0) |
| 392 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0xc0) | (r << 6)); | 364 | gl520_write_value(client, GL520_REG_FAN_DIV, |
| 365 | (gl520_read_value(client, GL520_REG_FAN_DIV) | ||
| 366 | & ~0xc0) | (r << 6)); | ||
| 393 | else | 367 | else |
| 394 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0x30) | (r << 4)); | 368 | gl520_write_value(client, GL520_REG_FAN_DIV, |
| 369 | (gl520_read_value(client, GL520_REG_FAN_DIV) | ||
| 370 | & ~0x30) | (r << 4)); | ||
| 395 | 371 | ||
| 396 | mutex_unlock(&data->update_lock); | 372 | mutex_unlock(&data->update_lock); |
| 397 | return count; | 373 | return count; |
| 398 | } | 374 | } |
| 399 | 375 | ||
| 400 | static ssize_t set_fan_off(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 376 | static ssize_t set_fan_off(struct device *dev, struct device_attribute *attr, |
| 377 | const char *buf, size_t count) | ||
| 401 | { | 378 | { |
| 379 | struct i2c_client *client = to_i2c_client(dev); | ||
| 380 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 402 | u8 r = simple_strtoul(buf, NULL, 10)?1:0; | 381 | u8 r = simple_strtoul(buf, NULL, 10)?1:0; |
| 403 | 382 | ||
| 404 | mutex_lock(&data->update_lock); | 383 | mutex_lock(&data->update_lock); |
| 405 | data->fan_off = r; | 384 | data->fan_off = r; |
| 406 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0x0c) | (r << 2)); | 385 | gl520_write_value(client, GL520_REG_FAN_OFF, |
| 386 | (gl520_read_value(client, GL520_REG_FAN_OFF) | ||
| 387 | & ~0x0c) | (r << 2)); | ||
| 407 | mutex_unlock(&data->update_lock); | 388 | mutex_unlock(&data->update_lock); |
| 408 | return count; | 389 | return count; |
| 409 | } | 390 | } |
| 410 | 391 | ||
| 392 | static SENSOR_DEVICE_ATTR(fan1_input, S_IRUGO, get_fan_input, NULL, 0); | ||
| 393 | static SENSOR_DEVICE_ATTR(fan2_input, S_IRUGO, get_fan_input, NULL, 1); | ||
| 394 | static SENSOR_DEVICE_ATTR(fan1_min, S_IRUGO | S_IWUSR, | ||
| 395 | get_fan_min, set_fan_min, 0); | ||
| 396 | static SENSOR_DEVICE_ATTR(fan2_min, S_IRUGO | S_IWUSR, | ||
| 397 | get_fan_min, set_fan_min, 1); | ||
| 398 | static SENSOR_DEVICE_ATTR(fan1_div, S_IRUGO | S_IWUSR, | ||
| 399 | get_fan_div, set_fan_div, 0); | ||
| 400 | static SENSOR_DEVICE_ATTR(fan2_div, S_IRUGO | S_IWUSR, | ||
| 401 | get_fan_div, set_fan_div, 1); | ||
| 402 | static DEVICE_ATTR(fan1_off, S_IRUGO | S_IWUSR, | ||
| 403 | get_fan_off, set_fan_off); | ||
| 404 | |||
| 411 | #define TEMP_FROM_REG(val) (((val) - 130) * 1000) | 405 | #define TEMP_FROM_REG(val) (((val) - 130) * 1000) |
| 412 | #define TEMP_TO_REG(val) (SENSORS_LIMIT(((((val)<0?(val)-500:(val)+500) / 1000)+130),0,255)) | 406 | #define TEMP_TO_REG(val) (SENSORS_LIMIT(((((val)<0?(val)-500:(val)+500) / 1000)+130),0,255)) |
| 413 | 407 | ||
| 414 | static ssize_t get_temp_input(struct gl520_data *data, char *buf, int n) | 408 | static ssize_t get_temp_input(struct device *dev, struct device_attribute *attr, |
| 409 | char *buf) | ||
| 415 | { | 410 | { |
| 416 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_input[n - 1])); | 411 | int n = to_sensor_dev_attr(attr)->index; |
| 412 | struct gl520_data *data = gl520_update_device(dev); | ||
| 413 | |||
| 414 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_input[n])); | ||
| 417 | } | 415 | } |
| 418 | 416 | ||
| 419 | static ssize_t get_temp_max(struct gl520_data *data, char *buf, int n) | 417 | static ssize_t get_temp_max(struct device *dev, struct device_attribute *attr, |
| 418 | char *buf) | ||
| 420 | { | 419 | { |
| 421 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[n - 1])); | 420 | int n = to_sensor_dev_attr(attr)->index; |
| 421 | struct gl520_data *data = gl520_update_device(dev); | ||
| 422 | |||
| 423 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[n])); | ||
| 422 | } | 424 | } |
| 423 | 425 | ||
| 424 | static ssize_t get_temp_max_hyst(struct gl520_data *data, char *buf, int n) | 426 | static ssize_t get_temp_max_hyst(struct device *dev, struct device_attribute |
| 427 | *attr, char *buf) | ||
| 425 | { | 428 | { |
| 426 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max_hyst[n - 1])); | 429 | int n = to_sensor_dev_attr(attr)->index; |
| 430 | struct gl520_data *data = gl520_update_device(dev); | ||
| 431 | |||
| 432 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max_hyst[n])); | ||
| 427 | } | 433 | } |
| 428 | 434 | ||
| 429 | static ssize_t set_temp_max(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 435 | static ssize_t set_temp_max(struct device *dev, struct device_attribute *attr, |
| 436 | const char *buf, size_t count) | ||
| 430 | { | 437 | { |
| 438 | struct i2c_client *client = to_i2c_client(dev); | ||
| 439 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 440 | int n = to_sensor_dev_attr(attr)->index; | ||
| 431 | long v = simple_strtol(buf, NULL, 10); | 441 | long v = simple_strtol(buf, NULL, 10); |
| 432 | 442 | ||
| 433 | mutex_lock(&data->update_lock); | 443 | mutex_lock(&data->update_lock); |
| 434 | data->temp_max[n - 1] = TEMP_TO_REG(v); | 444 | data->temp_max[n] = TEMP_TO_REG(v); |
| 435 | gl520_write_value(client, reg, data->temp_max[n - 1]); | 445 | gl520_write_value(client, GL520_REG_TEMP_MAX[n], data->temp_max[n]); |
| 436 | mutex_unlock(&data->update_lock); | 446 | mutex_unlock(&data->update_lock); |
| 437 | return count; | 447 | return count; |
| 438 | } | 448 | } |
| 439 | 449 | ||
| 440 | static ssize_t set_temp_max_hyst(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 450 | static ssize_t set_temp_max_hyst(struct device *dev, struct device_attribute |
| 451 | *attr, const char *buf, size_t count) | ||
| 441 | { | 452 | { |
| 453 | struct i2c_client *client = to_i2c_client(dev); | ||
| 454 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 455 | int n = to_sensor_dev_attr(attr)->index; | ||
| 442 | long v = simple_strtol(buf, NULL, 10); | 456 | long v = simple_strtol(buf, NULL, 10); |
| 443 | 457 | ||
| 444 | mutex_lock(&data->update_lock); | 458 | mutex_lock(&data->update_lock); |
| 445 | data->temp_max_hyst[n - 1] = TEMP_TO_REG(v); | 459 | data->temp_max_hyst[n] = TEMP_TO_REG(v); |
| 446 | gl520_write_value(client, reg, data->temp_max_hyst[n - 1]); | 460 | gl520_write_value(client, GL520_REG_TEMP_MAX_HYST[n], |
| 461 | data->temp_max_hyst[n]); | ||
| 447 | mutex_unlock(&data->update_lock); | 462 | mutex_unlock(&data->update_lock); |
| 448 | return count; | 463 | return count; |
| 449 | } | 464 | } |
| 450 | 465 | ||
| 451 | static ssize_t get_alarms(struct gl520_data *data, char *buf, int n) | 466 | static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, get_temp_input, NULL, 0); |
| 467 | static SENSOR_DEVICE_ATTR(temp2_input, S_IRUGO, get_temp_input, NULL, 1); | ||
| 468 | static SENSOR_DEVICE_ATTR(temp1_max, S_IRUGO | S_IWUSR, | ||
| 469 | get_temp_max, set_temp_max, 0); | ||
| 470 | static SENSOR_DEVICE_ATTR(temp2_max, S_IRUGO | S_IWUSR, | ||
| 471 | get_temp_max, set_temp_max, 1); | ||
| 472 | static SENSOR_DEVICE_ATTR(temp1_max_hyst, S_IRUGO | S_IWUSR, | ||
| 473 | get_temp_max_hyst, set_temp_max_hyst, 0); | ||
| 474 | static SENSOR_DEVICE_ATTR(temp2_max_hyst, S_IRUGO | S_IWUSR, | ||
| 475 | get_temp_max_hyst, set_temp_max_hyst, 1); | ||
| 476 | |||
| 477 | static ssize_t get_alarms(struct device *dev, struct device_attribute *attr, | ||
| 478 | char *buf) | ||
| 452 | { | 479 | { |
| 480 | struct gl520_data *data = gl520_update_device(dev); | ||
| 453 | return sprintf(buf, "%d\n", data->alarms); | 481 | return sprintf(buf, "%d\n", data->alarms); |
| 454 | } | 482 | } |
| 455 | 483 | ||
| 456 | static ssize_t get_beep_enable(struct gl520_data *data, char *buf, int n) | 484 | static ssize_t get_beep_enable(struct device *dev, struct device_attribute |
| 485 | *attr, char *buf) | ||
| 457 | { | 486 | { |
| 487 | struct gl520_data *data = gl520_update_device(dev); | ||
| 458 | return sprintf(buf, "%d\n", data->beep_enable); | 488 | return sprintf(buf, "%d\n", data->beep_enable); |
| 459 | } | 489 | } |
| 460 | 490 | ||
| 461 | static ssize_t get_beep_mask(struct gl520_data *data, char *buf, int n) | 491 | static ssize_t get_beep_mask(struct device *dev, struct device_attribute *attr, |
| 492 | char *buf) | ||
| 462 | { | 493 | { |
| 494 | struct gl520_data *data = gl520_update_device(dev); | ||
| 463 | return sprintf(buf, "%d\n", data->beep_mask); | 495 | return sprintf(buf, "%d\n", data->beep_mask); |
| 464 | } | 496 | } |
| 465 | 497 | ||
| 466 | static ssize_t set_beep_enable(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 498 | static ssize_t set_beep_enable(struct device *dev, struct device_attribute |
| 499 | *attr, const char *buf, size_t count) | ||
| 467 | { | 500 | { |
| 501 | struct i2c_client *client = to_i2c_client(dev); | ||
| 502 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 468 | u8 r = simple_strtoul(buf, NULL, 10)?0:1; | 503 | u8 r = simple_strtoul(buf, NULL, 10)?0:1; |
| 469 | 504 | ||
| 470 | mutex_lock(&data->update_lock); | 505 | mutex_lock(&data->update_lock); |
| 471 | data->beep_enable = !r; | 506 | data->beep_enable = !r; |
| 472 | gl520_write_value(client, reg, (gl520_read_value(client, reg) & ~0x04) | (r << 2)); | 507 | gl520_write_value(client, GL520_REG_BEEP_ENABLE, |
| 508 | (gl520_read_value(client, GL520_REG_BEEP_ENABLE) | ||
| 509 | & ~0x04) | (r << 2)); | ||
| 473 | mutex_unlock(&data->update_lock); | 510 | mutex_unlock(&data->update_lock); |
| 474 | return count; | 511 | return count; |
| 475 | } | 512 | } |
| 476 | 513 | ||
| 477 | static ssize_t set_beep_mask(struct i2c_client *client, struct gl520_data *data, const char *buf, size_t count, int n, int reg) | 514 | static ssize_t set_beep_mask(struct device *dev, struct device_attribute *attr, |
| 515 | const char *buf, size_t count) | ||
| 478 | { | 516 | { |
| 517 | struct i2c_client *client = to_i2c_client(dev); | ||
| 518 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 479 | u8 r = simple_strtoul(buf, NULL, 10); | 519 | u8 r = simple_strtoul(buf, NULL, 10); |
| 480 | 520 | ||
| 481 | mutex_lock(&data->update_lock); | 521 | mutex_lock(&data->update_lock); |
| 482 | r &= data->alarm_mask; | 522 | r &= data->alarm_mask; |
| 483 | data->beep_mask = r; | 523 | data->beep_mask = r; |
| 484 | gl520_write_value(client, reg, r); | 524 | gl520_write_value(client, GL520_REG_BEEP_MASK, r); |
| 525 | mutex_unlock(&data->update_lock); | ||
| 526 | return count; | ||
| 527 | } | ||
| 528 | |||
| 529 | static DEVICE_ATTR(alarms, S_IRUGO, get_alarms, NULL); | ||
| 530 | static DEVICE_ATTR(beep_enable, S_IRUGO | S_IWUSR, | ||
| 531 | get_beep_enable, set_beep_enable); | ||
| 532 | static DEVICE_ATTR(beep_mask, S_IRUGO | S_IWUSR, | ||
| 533 | get_beep_mask, set_beep_mask); | ||
| 534 | |||
| 535 | static ssize_t get_alarm(struct device *dev, struct device_attribute *attr, | ||
| 536 | char *buf) | ||
| 537 | { | ||
| 538 | int bit_nr = to_sensor_dev_attr(attr)->index; | ||
| 539 | struct gl520_data *data = gl520_update_device(dev); | ||
| 540 | |||
| 541 | return sprintf(buf, "%d\n", (data->alarms >> bit_nr) & 1); | ||
| 542 | } | ||
| 543 | |||
| 544 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, get_alarm, NULL, 0); | ||
| 545 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, get_alarm, NULL, 1); | ||
| 546 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, get_alarm, NULL, 2); | ||
| 547 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, get_alarm, NULL, 3); | ||
| 548 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, get_alarm, NULL, 4); | ||
| 549 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, get_alarm, NULL, 5); | ||
| 550 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, get_alarm, NULL, 6); | ||
| 551 | static SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, get_alarm, NULL, 7); | ||
| 552 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, get_alarm, NULL, 7); | ||
| 553 | |||
| 554 | static ssize_t get_beep(struct device *dev, struct device_attribute *attr, | ||
| 555 | char *buf) | ||
| 556 | { | ||
| 557 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 558 | struct gl520_data *data = gl520_update_device(dev); | ||
| 559 | |||
| 560 | return sprintf(buf, "%d\n", (data->beep_mask >> bitnr) & 1); | ||
| 561 | } | ||
| 562 | |||
| 563 | static ssize_t set_beep(struct device *dev, struct device_attribute *attr, | ||
| 564 | const char *buf, size_t count) | ||
| 565 | { | ||
| 566 | struct i2c_client *client = to_i2c_client(dev); | ||
| 567 | struct gl520_data *data = i2c_get_clientdata(client); | ||
| 568 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 569 | unsigned long bit; | ||
| 570 | |||
| 571 | bit = simple_strtoul(buf, NULL, 10); | ||
| 572 | if (bit & ~1) | ||
| 573 | return -EINVAL; | ||
| 574 | |||
| 575 | mutex_lock(&data->update_lock); | ||
| 576 | data->beep_mask = gl520_read_value(client, GL520_REG_BEEP_MASK); | ||
| 577 | if (bit) | ||
| 578 | data->beep_mask |= (1 << bitnr); | ||
| 579 | else | ||
| 580 | data->beep_mask &= ~(1 << bitnr); | ||
| 581 | gl520_write_value(client, GL520_REG_BEEP_MASK, data->beep_mask); | ||
| 485 | mutex_unlock(&data->update_lock); | 582 | mutex_unlock(&data->update_lock); |
| 486 | return count; | 583 | return count; |
| 487 | } | 584 | } |
| 488 | 585 | ||
| 586 | static SENSOR_DEVICE_ATTR(in0_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 0); | ||
| 587 | static SENSOR_DEVICE_ATTR(in1_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 1); | ||
| 588 | static SENSOR_DEVICE_ATTR(in2_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 2); | ||
| 589 | static SENSOR_DEVICE_ATTR(in3_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 3); | ||
| 590 | static SENSOR_DEVICE_ATTR(temp1_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 4); | ||
| 591 | static SENSOR_DEVICE_ATTR(fan1_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 5); | ||
| 592 | static SENSOR_DEVICE_ATTR(fan2_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 6); | ||
| 593 | static SENSOR_DEVICE_ATTR(temp2_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 7); | ||
| 594 | static SENSOR_DEVICE_ATTR(in4_beep, S_IRUGO | S_IWUSR, get_beep, set_beep, 7); | ||
| 595 | |||
| 489 | static struct attribute *gl520_attributes[] = { | 596 | static struct attribute *gl520_attributes[] = { |
| 490 | &dev_attr_cpu0_vid.attr, | 597 | &dev_attr_cpu0_vid.attr, |
| 491 | 598 | ||
| 492 | &dev_attr_in0_input.attr, | 599 | &sensor_dev_attr_in0_input.dev_attr.attr, |
| 493 | &dev_attr_in0_min.attr, | 600 | &sensor_dev_attr_in0_min.dev_attr.attr, |
| 494 | &dev_attr_in0_max.attr, | 601 | &sensor_dev_attr_in0_max.dev_attr.attr, |
| 495 | &dev_attr_in1_input.attr, | 602 | &sensor_dev_attr_in0_alarm.dev_attr.attr, |
| 496 | &dev_attr_in1_min.attr, | 603 | &sensor_dev_attr_in0_beep.dev_attr.attr, |
| 497 | &dev_attr_in1_max.attr, | 604 | &sensor_dev_attr_in1_input.dev_attr.attr, |
| 498 | &dev_attr_in2_input.attr, | 605 | &sensor_dev_attr_in1_min.dev_attr.attr, |
| 499 | &dev_attr_in2_min.attr, | 606 | &sensor_dev_attr_in1_max.dev_attr.attr, |
| 500 | &dev_attr_in2_max.attr, | 607 | &sensor_dev_attr_in1_alarm.dev_attr.attr, |
| 501 | &dev_attr_in3_input.attr, | 608 | &sensor_dev_attr_in1_beep.dev_attr.attr, |
| 502 | &dev_attr_in3_min.attr, | 609 | &sensor_dev_attr_in2_input.dev_attr.attr, |
| 503 | &dev_attr_in3_max.attr, | 610 | &sensor_dev_attr_in2_min.dev_attr.attr, |
| 504 | 611 | &sensor_dev_attr_in2_max.dev_attr.attr, | |
| 505 | &dev_attr_fan1_input.attr, | 612 | &sensor_dev_attr_in2_alarm.dev_attr.attr, |
| 506 | &dev_attr_fan1_min.attr, | 613 | &sensor_dev_attr_in2_beep.dev_attr.attr, |
| 507 | &dev_attr_fan1_div.attr, | 614 | &sensor_dev_attr_in3_input.dev_attr.attr, |
| 615 | &sensor_dev_attr_in3_min.dev_attr.attr, | ||
| 616 | &sensor_dev_attr_in3_max.dev_attr.attr, | ||
| 617 | &sensor_dev_attr_in3_alarm.dev_attr.attr, | ||
| 618 | &sensor_dev_attr_in3_beep.dev_attr.attr, | ||
| 619 | |||
| 620 | &sensor_dev_attr_fan1_input.dev_attr.attr, | ||
| 621 | &sensor_dev_attr_fan1_min.dev_attr.attr, | ||
| 622 | &sensor_dev_attr_fan1_div.dev_attr.attr, | ||
| 623 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 624 | &sensor_dev_attr_fan1_beep.dev_attr.attr, | ||
| 508 | &dev_attr_fan1_off.attr, | 625 | &dev_attr_fan1_off.attr, |
| 509 | &dev_attr_fan2_input.attr, | 626 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 510 | &dev_attr_fan2_min.attr, | 627 | &sensor_dev_attr_fan2_min.dev_attr.attr, |
| 511 | &dev_attr_fan2_div.attr, | 628 | &sensor_dev_attr_fan2_div.dev_attr.attr, |
| 512 | 629 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | |
| 513 | &dev_attr_temp1_input.attr, | 630 | &sensor_dev_attr_fan2_beep.dev_attr.attr, |
| 514 | &dev_attr_temp1_max.attr, | 631 | |
| 515 | &dev_attr_temp1_max_hyst.attr, | 632 | &sensor_dev_attr_temp1_input.dev_attr.attr, |
| 633 | &sensor_dev_attr_temp1_max.dev_attr.attr, | ||
| 634 | &sensor_dev_attr_temp1_max_hyst.dev_attr.attr, | ||
| 635 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 636 | &sensor_dev_attr_temp1_beep.dev_attr.attr, | ||
| 516 | 637 | ||
| 517 | &dev_attr_alarms.attr, | 638 | &dev_attr_alarms.attr, |
| 518 | &dev_attr_beep_enable.attr, | 639 | &dev_attr_beep_enable.attr, |
| @@ -525,13 +646,17 @@ static const struct attribute_group gl520_group = { | |||
| 525 | }; | 646 | }; |
| 526 | 647 | ||
| 527 | static struct attribute *gl520_attributes_opt[] = { | 648 | static struct attribute *gl520_attributes_opt[] = { |
| 528 | &dev_attr_in4_input.attr, | 649 | &sensor_dev_attr_in4_input.dev_attr.attr, |
| 529 | &dev_attr_in4_min.attr, | 650 | &sensor_dev_attr_in4_min.dev_attr.attr, |
| 530 | &dev_attr_in4_max.attr, | 651 | &sensor_dev_attr_in4_max.dev_attr.attr, |
| 531 | 652 | &sensor_dev_attr_in4_alarm.dev_attr.attr, | |
| 532 | &dev_attr_temp2_input.attr, | 653 | &sensor_dev_attr_in4_beep.dev_attr.attr, |
| 533 | &dev_attr_temp2_max.attr, | 654 | |
| 534 | &dev_attr_temp2_max_hyst.attr, | 655 | &sensor_dev_attr_temp2_input.dev_attr.attr, |
| 656 | &sensor_dev_attr_temp2_max.dev_attr.attr, | ||
| 657 | &sensor_dev_attr_temp2_max_hyst.dev_attr.attr, | ||
| 658 | &sensor_dev_attr_temp2_alarm.dev_attr.attr, | ||
| 659 | &sensor_dev_attr_temp2_beep.dev_attr.attr, | ||
| 535 | NULL | 660 | NULL |
| 536 | }; | 661 | }; |
| 537 | 662 | ||
| @@ -553,7 +678,7 @@ static int gl520_attach_adapter(struct i2c_adapter *adapter) | |||
| 553 | 678 | ||
| 554 | static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) | 679 | static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) |
| 555 | { | 680 | { |
| 556 | struct i2c_client *new_client; | 681 | struct i2c_client *client; |
| 557 | struct gl520_data *data; | 682 | struct gl520_data *data; |
| 558 | int err = 0; | 683 | int err = 0; |
| 559 | 684 | ||
| @@ -570,59 +695,65 @@ static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 570 | goto exit; | 695 | goto exit; |
| 571 | } | 696 | } |
| 572 | 697 | ||
| 573 | new_client = &data->client; | 698 | client = &data->client; |
| 574 | i2c_set_clientdata(new_client, data); | 699 | i2c_set_clientdata(client, data); |
| 575 | new_client->addr = address; | 700 | client->addr = address; |
| 576 | new_client->adapter = adapter; | 701 | client->adapter = adapter; |
| 577 | new_client->driver = &gl520_driver; | 702 | client->driver = &gl520_driver; |
| 578 | new_client->flags = 0; | ||
| 579 | 703 | ||
| 580 | /* Determine the chip type. */ | 704 | /* Determine the chip type. */ |
| 581 | if (kind < 0) { | 705 | if (kind < 0) { |
| 582 | if ((gl520_read_value(new_client, GL520_REG_CHIP_ID) != 0x20) || | 706 | if ((gl520_read_value(client, GL520_REG_CHIP_ID) != 0x20) || |
| 583 | ((gl520_read_value(new_client, GL520_REG_REVISION) & 0x7f) != 0x00) || | 707 | ((gl520_read_value(client, GL520_REG_REVISION) & 0x7f) != 0x00) || |
| 584 | ((gl520_read_value(new_client, GL520_REG_CONF) & 0x80) != 0x00)) { | 708 | ((gl520_read_value(client, GL520_REG_CONF) & 0x80) != 0x00)) { |
| 585 | dev_dbg(&new_client->dev, "Unknown chip type, skipping\n"); | 709 | dev_dbg(&client->dev, "Unknown chip type, skipping\n"); |
| 586 | goto exit_free; | 710 | goto exit_free; |
| 587 | } | 711 | } |
| 588 | } | 712 | } |
| 589 | 713 | ||
| 590 | /* Fill in the remaining client fields */ | 714 | /* Fill in the remaining client fields */ |
| 591 | strlcpy(new_client->name, "gl520sm", I2C_NAME_SIZE); | 715 | strlcpy(client->name, "gl520sm", I2C_NAME_SIZE); |
| 592 | data->valid = 0; | ||
| 593 | mutex_init(&data->update_lock); | 716 | mutex_init(&data->update_lock); |
| 594 | 717 | ||
| 595 | /* Tell the I2C layer a new client has arrived */ | 718 | /* Tell the I2C layer a new client has arrived */ |
| 596 | if ((err = i2c_attach_client(new_client))) | 719 | if ((err = i2c_attach_client(client))) |
| 597 | goto exit_free; | 720 | goto exit_free; |
| 598 | 721 | ||
| 599 | /* Initialize the GL520SM chip */ | 722 | /* Initialize the GL520SM chip */ |
| 600 | gl520_init_client(new_client); | 723 | gl520_init_client(client); |
| 601 | 724 | ||
| 602 | /* Register sysfs hooks */ | 725 | /* Register sysfs hooks */ |
| 603 | if ((err = sysfs_create_group(&new_client->dev.kobj, &gl520_group))) | 726 | if ((err = sysfs_create_group(&client->dev.kobj, &gl520_group))) |
| 604 | goto exit_detach; | 727 | goto exit_detach; |
| 605 | 728 | ||
| 606 | if (data->two_temps) { | 729 | if (data->two_temps) { |
| 607 | if ((err = device_create_file(&new_client->dev, | 730 | if ((err = device_create_file(&client->dev, |
| 608 | &dev_attr_temp2_input)) | 731 | &sensor_dev_attr_temp2_input.dev_attr)) |
| 609 | || (err = device_create_file(&new_client->dev, | 732 | || (err = device_create_file(&client->dev, |
| 610 | &dev_attr_temp2_max)) | 733 | &sensor_dev_attr_temp2_max.dev_attr)) |
| 611 | || (err = device_create_file(&new_client->dev, | 734 | || (err = device_create_file(&client->dev, |
| 612 | &dev_attr_temp2_max_hyst))) | 735 | &sensor_dev_attr_temp2_max_hyst.dev_attr)) |
| 736 | || (err = device_create_file(&client->dev, | ||
| 737 | &sensor_dev_attr_temp2_alarm.dev_attr)) | ||
| 738 | || (err = device_create_file(&client->dev, | ||
| 739 | &sensor_dev_attr_temp2_beep.dev_attr))) | ||
| 613 | goto exit_remove_files; | 740 | goto exit_remove_files; |
| 614 | } else { | 741 | } else { |
| 615 | if ((err = device_create_file(&new_client->dev, | 742 | if ((err = device_create_file(&client->dev, |
| 616 | &dev_attr_in4_input)) | 743 | &sensor_dev_attr_in4_input.dev_attr)) |
| 617 | || (err = device_create_file(&new_client->dev, | 744 | || (err = device_create_file(&client->dev, |
| 618 | &dev_attr_in4_min)) | 745 | &sensor_dev_attr_in4_min.dev_attr)) |
| 619 | || (err = device_create_file(&new_client->dev, | 746 | || (err = device_create_file(&client->dev, |
| 620 | &dev_attr_in4_max))) | 747 | &sensor_dev_attr_in4_max.dev_attr)) |
| 748 | || (err = device_create_file(&client->dev, | ||
| 749 | &sensor_dev_attr_in4_alarm.dev_attr)) | ||
| 750 | || (err = device_create_file(&client->dev, | ||
| 751 | &sensor_dev_attr_in4_beep.dev_attr))) | ||
| 621 | goto exit_remove_files; | 752 | goto exit_remove_files; |
| 622 | } | 753 | } |
| 623 | 754 | ||
| 624 | 755 | ||
| 625 | data->hwmon_dev = hwmon_device_register(&new_client->dev); | 756 | data->hwmon_dev = hwmon_device_register(&client->dev); |
| 626 | if (IS_ERR(data->hwmon_dev)) { | 757 | if (IS_ERR(data->hwmon_dev)) { |
| 627 | err = PTR_ERR(data->hwmon_dev); | 758 | err = PTR_ERR(data->hwmon_dev); |
| 628 | goto exit_remove_files; | 759 | goto exit_remove_files; |
| @@ -631,10 +762,10 @@ static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 631 | return 0; | 762 | return 0; |
| 632 | 763 | ||
| 633 | exit_remove_files: | 764 | exit_remove_files: |
| 634 | sysfs_remove_group(&new_client->dev.kobj, &gl520_group); | 765 | sysfs_remove_group(&client->dev.kobj, &gl520_group); |
| 635 | sysfs_remove_group(&new_client->dev.kobj, &gl520_group_opt); | 766 | sysfs_remove_group(&client->dev.kobj, &gl520_group_opt); |
| 636 | exit_detach: | 767 | exit_detach: |
| 637 | i2c_detach_client(new_client); | 768 | i2c_detach_client(client); |
| 638 | exit_free: | 769 | exit_free: |
| 639 | kfree(data); | 770 | kfree(data); |
| 640 | exit: | 771 | exit: |
| @@ -697,7 +828,7 @@ static int gl520_detach_client(struct i2c_client *client) | |||
| 697 | } | 828 | } |
| 698 | 829 | ||
| 699 | 830 | ||
| 700 | /* Registers 0x07 to 0x0c are word-sized, others are byte-sized | 831 | /* Registers 0x07 to 0x0c are word-sized, others are byte-sized |
| 701 | GL520 uses a high-byte first convention */ | 832 | GL520 uses a high-byte first convention */ |
| 702 | static int gl520_read_value(struct i2c_client *client, u8 reg) | 833 | static int gl520_read_value(struct i2c_client *client, u8 reg) |
| 703 | { | 834 | { |
| @@ -720,7 +851,7 @@ static struct gl520_data *gl520_update_device(struct device *dev) | |||
| 720 | { | 851 | { |
| 721 | struct i2c_client *client = to_i2c_client(dev); | 852 | struct i2c_client *client = to_i2c_client(dev); |
| 722 | struct gl520_data *data = i2c_get_clientdata(client); | 853 | struct gl520_data *data = i2c_get_clientdata(client); |
| 723 | int val; | 854 | int val, i; |
| 724 | 855 | ||
| 725 | mutex_lock(&data->update_lock); | 856 | mutex_lock(&data->update_lock); |
| 726 | 857 | ||
| @@ -732,18 +863,13 @@ static struct gl520_data *gl520_update_device(struct device *dev) | |||
| 732 | data->beep_mask = gl520_read_value(client, GL520_REG_BEEP_MASK); | 863 | data->beep_mask = gl520_read_value(client, GL520_REG_BEEP_MASK); |
| 733 | data->vid = gl520_read_value(client, GL520_REG_VID_INPUT) & 0x1f; | 864 | data->vid = gl520_read_value(client, GL520_REG_VID_INPUT) & 0x1f; |
| 734 | 865 | ||
| 735 | val = gl520_read_value(client, GL520_REG_IN0_LIMIT); | 866 | for (i = 0; i < 4; i++) { |
| 736 | data->in_min[0] = val & 0xff; | 867 | data->in_input[i] = gl520_read_value(client, |
| 737 | data->in_max[0] = (val >> 8) & 0xff; | 868 | GL520_REG_IN_INPUT[i]); |
| 738 | val = gl520_read_value(client, GL520_REG_IN1_LIMIT); | 869 | val = gl520_read_value(client, GL520_REG_IN_LIMIT[i]); |
| 739 | data->in_min[1] = val & 0xff; | 870 | data->in_min[i] = val & 0xff; |
| 740 | data->in_max[1] = (val >> 8) & 0xff; | 871 | data->in_max[i] = (val >> 8) & 0xff; |
| 741 | val = gl520_read_value(client, GL520_REG_IN2_LIMIT); | 872 | } |
| 742 | data->in_min[2] = val & 0xff; | ||
| 743 | data->in_max[2] = (val >> 8) & 0xff; | ||
| 744 | val = gl520_read_value(client, GL520_REG_IN3_LIMIT); | ||
| 745 | data->in_min[3] = val & 0xff; | ||
| 746 | data->in_max[3] = (val >> 8) & 0xff; | ||
| 747 | 873 | ||
| 748 | val = gl520_read_value(client, GL520_REG_FAN_INPUT); | 874 | val = gl520_read_value(client, GL520_REG_FAN_INPUT); |
| 749 | data->fan_input[0] = (val >> 8) & 0xff; | 875 | data->fan_input[0] = (val >> 8) & 0xff; |
| @@ -753,9 +879,12 @@ static struct gl520_data *gl520_update_device(struct device *dev) | |||
| 753 | data->fan_min[0] = (val >> 8) & 0xff; | 879 | data->fan_min[0] = (val >> 8) & 0xff; |
| 754 | data->fan_min[1] = val & 0xff; | 880 | data->fan_min[1] = val & 0xff; |
| 755 | 881 | ||
| 756 | data->temp_input[0] = gl520_read_value(client, GL520_REG_TEMP1_INPUT); | 882 | data->temp_input[0] = gl520_read_value(client, |
| 757 | data->temp_max[0] = gl520_read_value(client, GL520_REG_TEMP1_MAX); | 883 | GL520_REG_TEMP_INPUT[0]); |
| 758 | data->temp_max_hyst[0] = gl520_read_value(client, GL520_REG_TEMP1_MAX_HYST); | 884 | data->temp_max[0] = gl520_read_value(client, |
| 885 | GL520_REG_TEMP_MAX[0]); | ||
| 886 | data->temp_max_hyst[0] = gl520_read_value(client, | ||
| 887 | GL520_REG_TEMP_MAX_HYST[0]); | ||
| 759 | 888 | ||
| 760 | val = gl520_read_value(client, GL520_REG_FAN_DIV); | 889 | val = gl520_read_value(client, GL520_REG_FAN_DIV); |
| 761 | data->fan_div[0] = (val >> 6) & 0x03; | 890 | data->fan_div[0] = (val >> 6) & 0x03; |
| @@ -767,20 +896,21 @@ static struct gl520_data *gl520_update_device(struct device *dev) | |||
| 767 | val = gl520_read_value(client, GL520_REG_CONF); | 896 | val = gl520_read_value(client, GL520_REG_CONF); |
| 768 | data->beep_enable = !((val >> 2) & 1); | 897 | data->beep_enable = !((val >> 2) & 1); |
| 769 | 898 | ||
| 770 | data->in_input[0] = gl520_read_value(client, GL520_REG_IN0_INPUT); | ||
| 771 | data->in_input[1] = gl520_read_value(client, GL520_REG_IN1_INPUT); | ||
| 772 | data->in_input[2] = gl520_read_value(client, GL520_REG_IN2_INPUT); | ||
| 773 | data->in_input[3] = gl520_read_value(client, GL520_REG_IN3_INPUT); | ||
| 774 | |||
| 775 | /* Temp1 and Vin4 are the same input */ | 899 | /* Temp1 and Vin4 are the same input */ |
| 776 | if (data->two_temps) { | 900 | if (data->two_temps) { |
| 777 | data->temp_input[1] = gl520_read_value(client, GL520_REG_TEMP2_INPUT); | 901 | data->temp_input[1] = gl520_read_value(client, |
| 778 | data->temp_max[1] = gl520_read_value(client, GL520_REG_TEMP2_MAX); | 902 | GL520_REG_TEMP_INPUT[1]); |
| 779 | data->temp_max_hyst[1] = gl520_read_value(client, GL520_REG_TEMP2_MAX_HYST); | 903 | data->temp_max[1] = gl520_read_value(client, |
| 904 | GL520_REG_TEMP_MAX[1]); | ||
| 905 | data->temp_max_hyst[1] = gl520_read_value(client, | ||
| 906 | GL520_REG_TEMP_MAX_HYST[1]); | ||
| 780 | } else { | 907 | } else { |
| 781 | data->in_input[4] = gl520_read_value(client, GL520_REG_IN4_INPUT); | 908 | data->in_input[4] = gl520_read_value(client, |
| 782 | data->in_min[4] = gl520_read_value(client, GL520_REG_IN4_MIN); | 909 | GL520_REG_IN_INPUT[4]); |
| 783 | data->in_max[4] = gl520_read_value(client, GL520_REG_IN4_MAX); | 910 | data->in_min[4] = gl520_read_value(client, |
| 911 | GL520_REG_IN_MIN[4]); | ||
| 912 | data->in_max[4] = gl520_read_value(client, | ||
| 913 | GL520_REG_IN_MAX[4]); | ||
| 784 | } | 914 | } |
| 785 | 915 | ||
| 786 | data->last_updated = jiffies; | 916 | data->last_updated = jiffies; |
diff --git a/drivers/hwmon/it87.c b/drivers/hwmon/it87.c index ad6c8a319903..e12c132ff83a 100644 --- a/drivers/hwmon/it87.c +++ b/drivers/hwmon/it87.c | |||
| @@ -17,8 +17,8 @@ | |||
| 17 | IT8726F Super I/O chip w/LPC interface | 17 | IT8726F Super I/O chip w/LPC interface |
| 18 | Sis950 A clone of the IT8705F | 18 | Sis950 A clone of the IT8705F |
| 19 | 19 | ||
| 20 | Copyright (C) 2001 Chris Gauthron <chrisg@0-in.com> | 20 | Copyright (C) 2001 Chris Gauthron |
| 21 | Copyright (C) 2005-2006 Jean Delvare <khali@linux-fr.org> | 21 | Copyright (C) 2005-2007 Jean Delvare <khali@linux-fr.org> |
| 22 | 22 | ||
| 23 | This program is free software; you can redistribute it and/or modify | 23 | This program is free software; you can redistribute it and/or modify |
| 24 | it under the terms of the GNU General Public License as published by | 24 | it under the terms of the GNU General Public License as published by |
| @@ -52,6 +52,10 @@ | |||
| 52 | 52 | ||
| 53 | enum chips { it87, it8712, it8716, it8718 }; | 53 | enum chips { it87, it8712, it8716, it8718 }; |
| 54 | 54 | ||
| 55 | static unsigned short force_id; | ||
| 56 | module_param(force_id, ushort, 0); | ||
| 57 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 58 | |||
| 55 | static struct platform_device *pdev; | 59 | static struct platform_device *pdev; |
| 56 | 60 | ||
| 57 | #define REG 0x2e /* The register to read/write */ | 61 | #define REG 0x2e /* The register to read/write */ |
| @@ -776,6 +780,30 @@ static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, ch | |||
| 776 | } | 780 | } |
| 777 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | 781 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); |
| 778 | 782 | ||
| 783 | static ssize_t show_alarm(struct device *dev, struct device_attribute *attr, | ||
| 784 | char *buf) | ||
| 785 | { | ||
| 786 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 787 | struct it87_data *data = it87_update_device(dev); | ||
| 788 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); | ||
| 789 | } | ||
| 790 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 791 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 9); | ||
| 792 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 10); | ||
| 793 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 11); | ||
| 794 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL, 12); | ||
| 795 | static SENSOR_DEVICE_ATTR(in5_alarm, S_IRUGO, show_alarm, NULL, 13); | ||
| 796 | static SENSOR_DEVICE_ATTR(in6_alarm, S_IRUGO, show_alarm, NULL, 14); | ||
| 797 | static SENSOR_DEVICE_ATTR(in7_alarm, S_IRUGO, show_alarm, NULL, 15); | ||
| 798 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 799 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 800 | static SENSOR_DEVICE_ATTR(fan3_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 801 | static SENSOR_DEVICE_ATTR(fan4_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 802 | static SENSOR_DEVICE_ATTR(fan5_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 803 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, 16); | ||
| 804 | static SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, show_alarm, NULL, 17); | ||
| 805 | static SENSOR_DEVICE_ATTR(temp3_alarm, S_IRUGO, show_alarm, NULL, 18); | ||
| 806 | |||
| 779 | static ssize_t | 807 | static ssize_t |
| 780 | show_vrm_reg(struct device *dev, struct device_attribute *attr, char *buf) | 808 | show_vrm_reg(struct device *dev, struct device_attribute *attr, char *buf) |
| 781 | { | 809 | { |
| @@ -837,6 +865,14 @@ static struct attribute *it87_attributes[] = { | |||
| 837 | &sensor_dev_attr_in5_max.dev_attr.attr, | 865 | &sensor_dev_attr_in5_max.dev_attr.attr, |
| 838 | &sensor_dev_attr_in6_max.dev_attr.attr, | 866 | &sensor_dev_attr_in6_max.dev_attr.attr, |
| 839 | &sensor_dev_attr_in7_max.dev_attr.attr, | 867 | &sensor_dev_attr_in7_max.dev_attr.attr, |
| 868 | &sensor_dev_attr_in0_alarm.dev_attr.attr, | ||
| 869 | &sensor_dev_attr_in1_alarm.dev_attr.attr, | ||
| 870 | &sensor_dev_attr_in2_alarm.dev_attr.attr, | ||
| 871 | &sensor_dev_attr_in3_alarm.dev_attr.attr, | ||
| 872 | &sensor_dev_attr_in4_alarm.dev_attr.attr, | ||
| 873 | &sensor_dev_attr_in5_alarm.dev_attr.attr, | ||
| 874 | &sensor_dev_attr_in6_alarm.dev_attr.attr, | ||
| 875 | &sensor_dev_attr_in7_alarm.dev_attr.attr, | ||
| 840 | 876 | ||
| 841 | &sensor_dev_attr_temp1_input.dev_attr.attr, | 877 | &sensor_dev_attr_temp1_input.dev_attr.attr, |
| 842 | &sensor_dev_attr_temp2_input.dev_attr.attr, | 878 | &sensor_dev_attr_temp2_input.dev_attr.attr, |
| @@ -850,6 +886,9 @@ static struct attribute *it87_attributes[] = { | |||
| 850 | &sensor_dev_attr_temp1_type.dev_attr.attr, | 886 | &sensor_dev_attr_temp1_type.dev_attr.attr, |
| 851 | &sensor_dev_attr_temp2_type.dev_attr.attr, | 887 | &sensor_dev_attr_temp2_type.dev_attr.attr, |
| 852 | &sensor_dev_attr_temp3_type.dev_attr.attr, | 888 | &sensor_dev_attr_temp3_type.dev_attr.attr, |
| 889 | &sensor_dev_attr_temp1_alarm.dev_attr.attr, | ||
| 890 | &sensor_dev_attr_temp2_alarm.dev_attr.attr, | ||
| 891 | &sensor_dev_attr_temp3_alarm.dev_attr.attr, | ||
| 853 | 892 | ||
| 854 | &dev_attr_alarms.attr, | 893 | &dev_attr_alarms.attr, |
| 855 | &dev_attr_name.attr, | 894 | &dev_attr_name.attr, |
| @@ -882,12 +921,21 @@ static struct attribute *it87_attributes_opt[] = { | |||
| 882 | &sensor_dev_attr_fan3_min.dev_attr.attr, | 921 | &sensor_dev_attr_fan3_min.dev_attr.attr, |
| 883 | &sensor_dev_attr_fan3_div.dev_attr.attr, | 922 | &sensor_dev_attr_fan3_div.dev_attr.attr, |
| 884 | 923 | ||
| 924 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 925 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | ||
| 926 | &sensor_dev_attr_fan3_alarm.dev_attr.attr, | ||
| 927 | &sensor_dev_attr_fan4_alarm.dev_attr.attr, | ||
| 928 | &sensor_dev_attr_fan5_alarm.dev_attr.attr, | ||
| 929 | |||
| 885 | &sensor_dev_attr_pwm1_enable.dev_attr.attr, | 930 | &sensor_dev_attr_pwm1_enable.dev_attr.attr, |
| 886 | &sensor_dev_attr_pwm2_enable.dev_attr.attr, | 931 | &sensor_dev_attr_pwm2_enable.dev_attr.attr, |
| 887 | &sensor_dev_attr_pwm3_enable.dev_attr.attr, | 932 | &sensor_dev_attr_pwm3_enable.dev_attr.attr, |
| 888 | &sensor_dev_attr_pwm1.dev_attr.attr, | 933 | &sensor_dev_attr_pwm1.dev_attr.attr, |
| 889 | &sensor_dev_attr_pwm2.dev_attr.attr, | 934 | &sensor_dev_attr_pwm2.dev_attr.attr, |
| 890 | &sensor_dev_attr_pwm3.dev_attr.attr, | 935 | &sensor_dev_attr_pwm3.dev_attr.attr, |
| 936 | &dev_attr_pwm1_freq.attr, | ||
| 937 | &dev_attr_pwm2_freq.attr, | ||
| 938 | &dev_attr_pwm3_freq.attr, | ||
| 891 | 939 | ||
| 892 | &dev_attr_vrm.attr, | 940 | &dev_attr_vrm.attr, |
| 893 | &dev_attr_cpu0_vid.attr, | 941 | &dev_attr_cpu0_vid.attr, |
| @@ -906,7 +954,7 @@ static int __init it87_find(unsigned short *address, | |||
| 906 | u16 chip_type; | 954 | u16 chip_type; |
| 907 | 955 | ||
| 908 | superio_enter(); | 956 | superio_enter(); |
| 909 | chip_type = superio_inw(DEVID); | 957 | chip_type = force_id ? force_id : superio_inw(DEVID); |
| 910 | 958 | ||
| 911 | switch (chip_type) { | 959 | switch (chip_type) { |
| 912 | case IT8705F_DEVID: | 960 | case IT8705F_DEVID: |
| @@ -1027,35 +1075,45 @@ static int __devinit it87_probe(struct platform_device *pdev) | |||
| 1027 | if ((err = device_create_file(dev, | 1075 | if ((err = device_create_file(dev, |
| 1028 | &sensor_dev_attr_fan1_input16.dev_attr)) | 1076 | &sensor_dev_attr_fan1_input16.dev_attr)) |
| 1029 | || (err = device_create_file(dev, | 1077 | || (err = device_create_file(dev, |
| 1030 | &sensor_dev_attr_fan1_min16.dev_attr))) | 1078 | &sensor_dev_attr_fan1_min16.dev_attr)) |
| 1079 | || (err = device_create_file(dev, | ||
| 1080 | &sensor_dev_attr_fan1_alarm.dev_attr))) | ||
| 1031 | goto ERROR4; | 1081 | goto ERROR4; |
| 1032 | } | 1082 | } |
| 1033 | if (data->has_fan & (1 << 1)) { | 1083 | if (data->has_fan & (1 << 1)) { |
| 1034 | if ((err = device_create_file(dev, | 1084 | if ((err = device_create_file(dev, |
| 1035 | &sensor_dev_attr_fan2_input16.dev_attr)) | 1085 | &sensor_dev_attr_fan2_input16.dev_attr)) |
| 1036 | || (err = device_create_file(dev, | 1086 | || (err = device_create_file(dev, |
| 1037 | &sensor_dev_attr_fan2_min16.dev_attr))) | 1087 | &sensor_dev_attr_fan2_min16.dev_attr)) |
| 1088 | || (err = device_create_file(dev, | ||
| 1089 | &sensor_dev_attr_fan2_alarm.dev_attr))) | ||
| 1038 | goto ERROR4; | 1090 | goto ERROR4; |
| 1039 | } | 1091 | } |
| 1040 | if (data->has_fan & (1 << 2)) { | 1092 | if (data->has_fan & (1 << 2)) { |
| 1041 | if ((err = device_create_file(dev, | 1093 | if ((err = device_create_file(dev, |
| 1042 | &sensor_dev_attr_fan3_input16.dev_attr)) | 1094 | &sensor_dev_attr_fan3_input16.dev_attr)) |
| 1043 | || (err = device_create_file(dev, | 1095 | || (err = device_create_file(dev, |
| 1044 | &sensor_dev_attr_fan3_min16.dev_attr))) | 1096 | &sensor_dev_attr_fan3_min16.dev_attr)) |
| 1097 | || (err = device_create_file(dev, | ||
| 1098 | &sensor_dev_attr_fan3_alarm.dev_attr))) | ||
| 1045 | goto ERROR4; | 1099 | goto ERROR4; |
| 1046 | } | 1100 | } |
| 1047 | if (data->has_fan & (1 << 3)) { | 1101 | if (data->has_fan & (1 << 3)) { |
| 1048 | if ((err = device_create_file(dev, | 1102 | if ((err = device_create_file(dev, |
| 1049 | &sensor_dev_attr_fan4_input16.dev_attr)) | 1103 | &sensor_dev_attr_fan4_input16.dev_attr)) |
| 1050 | || (err = device_create_file(dev, | 1104 | || (err = device_create_file(dev, |
| 1051 | &sensor_dev_attr_fan4_min16.dev_attr))) | 1105 | &sensor_dev_attr_fan4_min16.dev_attr)) |
| 1106 | || (err = device_create_file(dev, | ||
| 1107 | &sensor_dev_attr_fan4_alarm.dev_attr))) | ||
| 1052 | goto ERROR4; | 1108 | goto ERROR4; |
| 1053 | } | 1109 | } |
| 1054 | if (data->has_fan & (1 << 4)) { | 1110 | if (data->has_fan & (1 << 4)) { |
| 1055 | if ((err = device_create_file(dev, | 1111 | if ((err = device_create_file(dev, |
| 1056 | &sensor_dev_attr_fan5_input16.dev_attr)) | 1112 | &sensor_dev_attr_fan5_input16.dev_attr)) |
| 1057 | || (err = device_create_file(dev, | 1113 | || (err = device_create_file(dev, |
| 1058 | &sensor_dev_attr_fan5_min16.dev_attr))) | 1114 | &sensor_dev_attr_fan5_min16.dev_attr)) |
| 1115 | || (err = device_create_file(dev, | ||
| 1116 | &sensor_dev_attr_fan5_alarm.dev_attr))) | ||
| 1059 | goto ERROR4; | 1117 | goto ERROR4; |
| 1060 | } | 1118 | } |
| 1061 | } else { | 1119 | } else { |
| @@ -1066,7 +1124,9 @@ static int __devinit it87_probe(struct platform_device *pdev) | |||
| 1066 | || (err = device_create_file(dev, | 1124 | || (err = device_create_file(dev, |
| 1067 | &sensor_dev_attr_fan1_min.dev_attr)) | 1125 | &sensor_dev_attr_fan1_min.dev_attr)) |
| 1068 | || (err = device_create_file(dev, | 1126 | || (err = device_create_file(dev, |
| 1069 | &sensor_dev_attr_fan1_div.dev_attr))) | 1127 | &sensor_dev_attr_fan1_div.dev_attr)) |
| 1128 | || (err = device_create_file(dev, | ||
| 1129 | &sensor_dev_attr_fan1_alarm.dev_attr))) | ||
| 1070 | goto ERROR4; | 1130 | goto ERROR4; |
| 1071 | } | 1131 | } |
| 1072 | if (data->has_fan & (1 << 1)) { | 1132 | if (data->has_fan & (1 << 1)) { |
| @@ -1075,7 +1135,9 @@ static int __devinit it87_probe(struct platform_device *pdev) | |||
| 1075 | || (err = device_create_file(dev, | 1135 | || (err = device_create_file(dev, |
| 1076 | &sensor_dev_attr_fan2_min.dev_attr)) | 1136 | &sensor_dev_attr_fan2_min.dev_attr)) |
| 1077 | || (err = device_create_file(dev, | 1137 | || (err = device_create_file(dev, |
| 1078 | &sensor_dev_attr_fan2_div.dev_attr))) | 1138 | &sensor_dev_attr_fan2_div.dev_attr)) |
| 1139 | || (err = device_create_file(dev, | ||
| 1140 | &sensor_dev_attr_fan2_alarm.dev_attr))) | ||
| 1079 | goto ERROR4; | 1141 | goto ERROR4; |
| 1080 | } | 1142 | } |
| 1081 | if (data->has_fan & (1 << 2)) { | 1143 | if (data->has_fan & (1 << 2)) { |
| @@ -1084,7 +1146,9 @@ static int __devinit it87_probe(struct platform_device *pdev) | |||
| 1084 | || (err = device_create_file(dev, | 1146 | || (err = device_create_file(dev, |
| 1085 | &sensor_dev_attr_fan3_min.dev_attr)) | 1147 | &sensor_dev_attr_fan3_min.dev_attr)) |
| 1086 | || (err = device_create_file(dev, | 1148 | || (err = device_create_file(dev, |
| 1087 | &sensor_dev_attr_fan3_div.dev_attr))) | 1149 | &sensor_dev_attr_fan3_div.dev_attr)) |
| 1150 | || (err = device_create_file(dev, | ||
| 1151 | &sensor_dev_attr_fan3_alarm.dev_attr))) | ||
| 1088 | goto ERROR4; | 1152 | goto ERROR4; |
| 1089 | } | 1153 | } |
| 1090 | } | 1154 | } |
| @@ -1488,7 +1552,7 @@ static void __exit sm_it87_exit(void) | |||
| 1488 | } | 1552 | } |
| 1489 | 1553 | ||
| 1490 | 1554 | ||
| 1491 | MODULE_AUTHOR("Chris Gauthron <chrisg@0-in.com>, " | 1555 | MODULE_AUTHOR("Chris Gauthron, " |
| 1492 | "Jean Delvare <khali@linux-fr.org>"); | 1556 | "Jean Delvare <khali@linux-fr.org>"); |
| 1493 | MODULE_DESCRIPTION("IT8705F/8712F/8716F/8718F/8726F, SiS950 driver"); | 1557 | MODULE_DESCRIPTION("IT8705F/8712F/8716F/8718F/8726F, SiS950 driver"); |
| 1494 | module_param(update_vbat, bool, 0); | 1558 | module_param(update_vbat, bool, 0); |
diff --git a/drivers/hwmon/lm75.c b/drivers/hwmon/lm75.c index 37a8cc032ffa..e5c35a355a57 100644 --- a/drivers/hwmon/lm75.c +++ b/drivers/hwmon/lm75.c | |||
| @@ -74,7 +74,6 @@ static struct i2c_driver lm75_driver = { | |||
| 74 | .driver = { | 74 | .driver = { |
| 75 | .name = "lm75", | 75 | .name = "lm75", |
| 76 | }, | 76 | }, |
| 77 | .id = I2C_DRIVERID_LM75, | ||
| 78 | .attach_adapter = lm75_attach_adapter, | 77 | .attach_adapter = lm75_attach_adapter, |
| 79 | .detach_client = lm75_detach_client, | 78 | .detach_client = lm75_detach_client, |
| 80 | }; | 79 | }; |
diff --git a/drivers/hwmon/lm77.c b/drivers/hwmon/lm77.c index cee5c2e8cfad..459b70ad6bee 100644 --- a/drivers/hwmon/lm77.c +++ b/drivers/hwmon/lm77.c | |||
| @@ -31,6 +31,7 @@ | |||
| 31 | #include <linux/jiffies.h> | 31 | #include <linux/jiffies.h> |
| 32 | #include <linux/i2c.h> | 32 | #include <linux/i2c.h> |
| 33 | #include <linux/hwmon.h> | 33 | #include <linux/hwmon.h> |
| 34 | #include <linux/hwmon-sysfs.h> | ||
| 34 | #include <linux/err.h> | 35 | #include <linux/err.h> |
| 35 | #include <linux/mutex.h> | 36 | #include <linux/mutex.h> |
| 36 | 37 | ||
| @@ -113,7 +114,6 @@ show(temp_input); | |||
| 113 | show(temp_crit); | 114 | show(temp_crit); |
| 114 | show(temp_min); | 115 | show(temp_min); |
| 115 | show(temp_max); | 116 | show(temp_max); |
| 116 | show(alarms); | ||
| 117 | 117 | ||
| 118 | /* read routines for hysteresis values */ | 118 | /* read routines for hysteresis values */ |
| 119 | static ssize_t show_temp_crit_hyst(struct device *dev, struct device_attribute *attr, char *buf) | 119 | static ssize_t show_temp_crit_hyst(struct device *dev, struct device_attribute *attr, char *buf) |
| @@ -186,6 +186,14 @@ static ssize_t set_temp_crit(struct device *dev, struct device_attribute *attr, | |||
| 186 | return count; | 186 | return count; |
| 187 | } | 187 | } |
| 188 | 188 | ||
| 189 | static ssize_t show_alarm(struct device *dev, struct device_attribute *attr, | ||
| 190 | char *buf) | ||
| 191 | { | ||
| 192 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 193 | struct lm77_data *data = lm77_update_device(dev); | ||
| 194 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); | ||
| 195 | } | ||
| 196 | |||
| 189 | static DEVICE_ATTR(temp1_input, S_IRUGO, | 197 | static DEVICE_ATTR(temp1_input, S_IRUGO, |
| 190 | show_temp_input, NULL); | 198 | show_temp_input, NULL); |
| 191 | static DEVICE_ATTR(temp1_crit, S_IWUSR | S_IRUGO, | 199 | static DEVICE_ATTR(temp1_crit, S_IWUSR | S_IRUGO, |
| @@ -202,8 +210,9 @@ static DEVICE_ATTR(temp1_min_hyst, S_IRUGO, | |||
| 202 | static DEVICE_ATTR(temp1_max_hyst, S_IRUGO, | 210 | static DEVICE_ATTR(temp1_max_hyst, S_IRUGO, |
| 203 | show_temp_max_hyst, NULL); | 211 | show_temp_max_hyst, NULL); |
| 204 | 212 | ||
| 205 | static DEVICE_ATTR(alarms, S_IRUGO, | 213 | static SENSOR_DEVICE_ATTR(temp1_crit_alarm, S_IRUGO, show_alarm, NULL, 2); |
| 206 | show_alarms, NULL); | 214 | static SENSOR_DEVICE_ATTR(temp1_min_alarm, S_IRUGO, show_alarm, NULL, 0); |
| 215 | static SENSOR_DEVICE_ATTR(temp1_max_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 207 | 216 | ||
| 208 | static int lm77_attach_adapter(struct i2c_adapter *adapter) | 217 | static int lm77_attach_adapter(struct i2c_adapter *adapter) |
| 209 | { | 218 | { |
| @@ -220,8 +229,9 @@ static struct attribute *lm77_attributes[] = { | |||
| 220 | &dev_attr_temp1_crit_hyst.attr, | 229 | &dev_attr_temp1_crit_hyst.attr, |
| 221 | &dev_attr_temp1_min_hyst.attr, | 230 | &dev_attr_temp1_min_hyst.attr, |
| 222 | &dev_attr_temp1_max_hyst.attr, | 231 | &dev_attr_temp1_max_hyst.attr, |
| 223 | &dev_attr_alarms.attr, | 232 | &sensor_dev_attr_temp1_crit_alarm.dev_attr.attr, |
| 224 | 233 | &sensor_dev_attr_temp1_min_alarm.dev_attr.attr, | |
| 234 | &sensor_dev_attr_temp1_max_alarm.dev_attr.attr, | ||
| 225 | NULL | 235 | NULL |
| 226 | }; | 236 | }; |
| 227 | 237 | ||
diff --git a/drivers/hwmon/lm78.c b/drivers/hwmon/lm78.c index 3f7055ee679f..0a9eb1f6f4e4 100644 --- a/drivers/hwmon/lm78.c +++ b/drivers/hwmon/lm78.c | |||
| @@ -37,10 +37,8 @@ | |||
| 37 | static struct platform_device *pdev; | 37 | static struct platform_device *pdev; |
| 38 | 38 | ||
| 39 | /* Addresses to scan */ | 39 | /* Addresses to scan */ |
| 40 | static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24, | 40 | static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, |
| 41 | 0x25, 0x26, 0x27, 0x28, 0x29, | 41 | 0x2e, 0x2f, I2C_CLIENT_END }; |
| 42 | 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, | ||
| 43 | 0x2f, I2C_CLIENT_END }; | ||
| 44 | static unsigned short isa_address = 0x290; | 42 | static unsigned short isa_address = 0x290; |
| 45 | 43 | ||
| 46 | /* Insmod parameters */ | 44 | /* Insmod parameters */ |
| @@ -170,7 +168,6 @@ static struct i2c_driver lm78_driver = { | |||
| 170 | .driver = { | 168 | .driver = { |
| 171 | .name = "lm78", | 169 | .name = "lm78", |
| 172 | }, | 170 | }, |
| 173 | .id = I2C_DRIVERID_LM78, | ||
| 174 | .attach_adapter = lm78_attach_adapter, | 171 | .attach_adapter = lm78_attach_adapter, |
| 175 | .detach_client = lm78_detach_client, | 172 | .detach_client = lm78_detach_client, |
| 176 | }; | 173 | }; |
diff --git a/drivers/hwmon/lm80.c b/drivers/hwmon/lm80.c index 063cdba00a88..a2ca055f3922 100644 --- a/drivers/hwmon/lm80.c +++ b/drivers/hwmon/lm80.c | |||
| @@ -27,6 +27,7 @@ | |||
| 27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
| 28 | #include <linux/i2c.h> | 28 | #include <linux/i2c.h> |
| 29 | #include <linux/hwmon.h> | 29 | #include <linux/hwmon.h> |
| 30 | #include <linux/hwmon-sysfs.h> | ||
| 30 | #include <linux/err.h> | 31 | #include <linux/err.h> |
| 31 | #include <linux/mutex.h> | 32 | #include <linux/mutex.h> |
| 32 | 33 | ||
| @@ -127,7 +128,7 @@ struct lm80_data { | |||
| 127 | u16 alarms; /* Register encoding, combined */ | 128 | u16 alarms; /* Register encoding, combined */ |
| 128 | }; | 129 | }; |
| 129 | 130 | ||
| 130 | /* | 131 | /* |
| 131 | * Functions declaration | 132 | * Functions declaration |
| 132 | */ | 133 | */ |
| 133 | 134 | ||
| @@ -147,7 +148,6 @@ static struct i2c_driver lm80_driver = { | |||
| 147 | .driver = { | 148 | .driver = { |
| 148 | .name = "lm80", | 149 | .name = "lm80", |
| 149 | }, | 150 | }, |
| 150 | .id = I2C_DRIVERID_LM80, | ||
| 151 | .attach_adapter = lm80_attach_adapter, | 151 | .attach_adapter = lm80_attach_adapter, |
| 152 | .detach_client = lm80_detach_client, | 152 | .detach_client = lm80_detach_client, |
| 153 | }; | 153 | }; |
| @@ -159,105 +159,74 @@ static struct i2c_driver lm80_driver = { | |||
| 159 | #define show_in(suffix, value) \ | 159 | #define show_in(suffix, value) \ |
| 160 | static ssize_t show_in_##suffix(struct device *dev, struct device_attribute *attr, char *buf) \ | 160 | static ssize_t show_in_##suffix(struct device *dev, struct device_attribute *attr, char *buf) \ |
| 161 | { \ | 161 | { \ |
| 162 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 162 | struct lm80_data *data = lm80_update_device(dev); \ | 163 | struct lm80_data *data = lm80_update_device(dev); \ |
| 163 | return sprintf(buf, "%d\n", IN_FROM_REG(data->value)); \ | 164 | return sprintf(buf, "%d\n", IN_FROM_REG(data->value[nr])); \ |
| 164 | } | 165 | } |
| 165 | show_in(min0, in_min[0]); | 166 | show_in(min, in_min) |
| 166 | show_in(min1, in_min[1]); | 167 | show_in(max, in_max) |
| 167 | show_in(min2, in_min[2]); | 168 | show_in(input, in) |
| 168 | show_in(min3, in_min[3]); | ||
| 169 | show_in(min4, in_min[4]); | ||
| 170 | show_in(min5, in_min[5]); | ||
| 171 | show_in(min6, in_min[6]); | ||
| 172 | show_in(max0, in_max[0]); | ||
| 173 | show_in(max1, in_max[1]); | ||
| 174 | show_in(max2, in_max[2]); | ||
| 175 | show_in(max3, in_max[3]); | ||
| 176 | show_in(max4, in_max[4]); | ||
| 177 | show_in(max5, in_max[5]); | ||
| 178 | show_in(max6, in_max[6]); | ||
| 179 | show_in(input0, in[0]); | ||
| 180 | show_in(input1, in[1]); | ||
| 181 | show_in(input2, in[2]); | ||
| 182 | show_in(input3, in[3]); | ||
| 183 | show_in(input4, in[4]); | ||
| 184 | show_in(input5, in[5]); | ||
| 185 | show_in(input6, in[6]); | ||
| 186 | 169 | ||
| 187 | #define set_in(suffix, value, reg) \ | 170 | #define set_in(suffix, value, reg) \ |
| 188 | static ssize_t set_in_##suffix(struct device *dev, struct device_attribute *attr, const char *buf, \ | 171 | static ssize_t set_in_##suffix(struct device *dev, struct device_attribute *attr, const char *buf, \ |
| 189 | size_t count) \ | 172 | size_t count) \ |
| 190 | { \ | 173 | { \ |
| 174 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 191 | struct i2c_client *client = to_i2c_client(dev); \ | 175 | struct i2c_client *client = to_i2c_client(dev); \ |
| 192 | struct lm80_data *data = i2c_get_clientdata(client); \ | 176 | struct lm80_data *data = i2c_get_clientdata(client); \ |
| 193 | long val = simple_strtol(buf, NULL, 10); \ | 177 | long val = simple_strtol(buf, NULL, 10); \ |
| 194 | \ | 178 | \ |
| 195 | mutex_lock(&data->update_lock);\ | 179 | mutex_lock(&data->update_lock);\ |
| 196 | data->value = IN_TO_REG(val); \ | 180 | data->value[nr] = IN_TO_REG(val); \ |
| 197 | lm80_write_value(client, reg, data->value); \ | 181 | lm80_write_value(client, reg(nr), data->value[nr]); \ |
| 198 | mutex_unlock(&data->update_lock);\ | 182 | mutex_unlock(&data->update_lock);\ |
| 199 | return count; \ | 183 | return count; \ |
| 200 | } | 184 | } |
| 201 | set_in(min0, in_min[0], LM80_REG_IN_MIN(0)); | 185 | set_in(min, in_min, LM80_REG_IN_MIN) |
| 202 | set_in(min1, in_min[1], LM80_REG_IN_MIN(1)); | 186 | set_in(max, in_max, LM80_REG_IN_MAX) |
| 203 | set_in(min2, in_min[2], LM80_REG_IN_MIN(2)); | 187 | |
| 204 | set_in(min3, in_min[3], LM80_REG_IN_MIN(3)); | 188 | #define show_fan(suffix, value) \ |
| 205 | set_in(min4, in_min[4], LM80_REG_IN_MIN(4)); | ||
| 206 | set_in(min5, in_min[5], LM80_REG_IN_MIN(5)); | ||
| 207 | set_in(min6, in_min[6], LM80_REG_IN_MIN(6)); | ||
| 208 | set_in(max0, in_max[0], LM80_REG_IN_MAX(0)); | ||
| 209 | set_in(max1, in_max[1], LM80_REG_IN_MAX(1)); | ||
| 210 | set_in(max2, in_max[2], LM80_REG_IN_MAX(2)); | ||
| 211 | set_in(max3, in_max[3], LM80_REG_IN_MAX(3)); | ||
| 212 | set_in(max4, in_max[4], LM80_REG_IN_MAX(4)); | ||
| 213 | set_in(max5, in_max[5], LM80_REG_IN_MAX(5)); | ||
| 214 | set_in(max6, in_max[6], LM80_REG_IN_MAX(6)); | ||
| 215 | |||
| 216 | #define show_fan(suffix, value, div) \ | ||
| 217 | static ssize_t show_fan_##suffix(struct device *dev, struct device_attribute *attr, char *buf) \ | 189 | static ssize_t show_fan_##suffix(struct device *dev, struct device_attribute *attr, char *buf) \ |
| 218 | { \ | 190 | { \ |
| 191 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 219 | struct lm80_data *data = lm80_update_device(dev); \ | 192 | struct lm80_data *data = lm80_update_device(dev); \ |
| 220 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->value, \ | 193 | return sprintf(buf, "%d\n", FAN_FROM_REG(data->value[nr], \ |
| 221 | DIV_FROM_REG(data->div))); \ | 194 | DIV_FROM_REG(data->fan_div[nr]))); \ |
| 222 | } | 195 | } |
| 223 | show_fan(min1, fan_min[0], fan_div[0]); | 196 | show_fan(min, fan_min) |
| 224 | show_fan(min2, fan_min[1], fan_div[1]); | 197 | show_fan(input, fan) |
| 225 | show_fan(input1, fan[0], fan_div[0]); | ||
| 226 | show_fan(input2, fan[1], fan_div[1]); | ||
| 227 | 198 | ||
| 228 | #define show_fan_div(suffix, value) \ | 199 | static ssize_t show_fan_div(struct device *dev, struct device_attribute *attr, |
| 229 | static ssize_t show_fan_div##suffix(struct device *dev, struct device_attribute *attr, char *buf) \ | 200 | char *buf) |
| 230 | { \ | 201 | { |
| 231 | struct lm80_data *data = lm80_update_device(dev); \ | 202 | int nr = to_sensor_dev_attr(attr)->index; |
| 232 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->value)); \ | 203 | struct lm80_data *data = lm80_update_device(dev); |
| 204 | return sprintf(buf, "%d\n", DIV_FROM_REG(data->fan_div[nr])); | ||
| 233 | } | 205 | } |
| 234 | show_fan_div(1, fan_div[0]); | ||
| 235 | show_fan_div(2, fan_div[1]); | ||
| 236 | 206 | ||
| 237 | #define set_fan(suffix, value, reg, div) \ | 207 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *attr, |
| 238 | static ssize_t set_fan_##suffix(struct device *dev, struct device_attribute *attr, const char *buf, \ | 208 | const char *buf, size_t count) |
| 239 | size_t count) \ | 209 | { |
| 240 | { \ | 210 | int nr = to_sensor_dev_attr(attr)->index; |
| 241 | struct i2c_client *client = to_i2c_client(dev); \ | 211 | struct i2c_client *client = to_i2c_client(dev); |
| 242 | struct lm80_data *data = i2c_get_clientdata(client); \ | 212 | struct lm80_data *data = i2c_get_clientdata(client); |
| 243 | long val = simple_strtoul(buf, NULL, 10); \ | 213 | long val = simple_strtoul(buf, NULL, 10); |
| 244 | \ | 214 | |
| 245 | mutex_lock(&data->update_lock);\ | 215 | mutex_lock(&data->update_lock); |
| 246 | data->value = FAN_TO_REG(val, DIV_FROM_REG(data->div)); \ | 216 | data->fan_min[nr] = FAN_TO_REG(val, DIV_FROM_REG(data->fan_div[nr])); |
| 247 | lm80_write_value(client, reg, data->value); \ | 217 | lm80_write_value(client, LM80_REG_FAN_MIN(nr + 1), data->fan_min[nr]); |
| 248 | mutex_unlock(&data->update_lock);\ | 218 | mutex_unlock(&data->update_lock); |
| 249 | return count; \ | 219 | return count; |
| 250 | } | 220 | } |
| 251 | set_fan(min1, fan_min[0], LM80_REG_FAN_MIN(1), fan_div[0]); | ||
| 252 | set_fan(min2, fan_min[1], LM80_REG_FAN_MIN(2), fan_div[1]); | ||
| 253 | 221 | ||
| 254 | /* Note: we save and restore the fan minimum here, because its value is | 222 | /* Note: we save and restore the fan minimum here, because its value is |
| 255 | determined in part by the fan divisor. This follows the principle of | 223 | determined in part by the fan divisor. This follows the principle of |
| 256 | least surprise; the user doesn't expect the fan minimum to change just | 224 | least surprise; the user doesn't expect the fan minimum to change just |
| 257 | because the divisor changed. */ | 225 | because the divisor changed. */ |
| 258 | static ssize_t set_fan_div(struct device *dev, const char *buf, | 226 | static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, |
| 259 | size_t count, int nr) | 227 | const char *buf, size_t count) |
| 260 | { | 228 | { |
| 229 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 261 | struct i2c_client *client = to_i2c_client(dev); | 230 | struct i2c_client *client = to_i2c_client(dev); |
| 262 | struct lm80_data *data = i2c_get_clientdata(client); | 231 | struct lm80_data *data = i2c_get_clientdata(client); |
| 263 | unsigned long min, val = simple_strtoul(buf, NULL, 10); | 232 | unsigned long min, val = simple_strtoul(buf, NULL, 10); |
| @@ -292,15 +261,6 @@ static ssize_t set_fan_div(struct device *dev, const char *buf, | |||
| 292 | return count; | 261 | return count; |
| 293 | } | 262 | } |
| 294 | 263 | ||
| 295 | #define set_fan_div(number) \ | ||
| 296 | static ssize_t set_fan_div##number(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
| 297 | size_t count) \ | ||
| 298 | { \ | ||
| 299 | return set_fan_div(dev, buf, count, number - 1); \ | ||
| 300 | } | ||
| 301 | set_fan_div(1); | ||
| 302 | set_fan_div(2); | ||
| 303 | |||
| 304 | static ssize_t show_temp_input1(struct device *dev, struct device_attribute *attr, char *buf) | 264 | static ssize_t show_temp_input1(struct device *dev, struct device_attribute *attr, char *buf) |
| 305 | { | 265 | { |
| 306 | struct lm80_data *data = lm80_update_device(dev); | 266 | struct lm80_data *data = lm80_update_device(dev); |
| @@ -337,41 +297,66 @@ set_temp(hot_hyst, temp_hot_hyst, LM80_REG_TEMP_HOT_HYST); | |||
| 337 | set_temp(os_max, temp_os_max, LM80_REG_TEMP_OS_MAX); | 297 | set_temp(os_max, temp_os_max, LM80_REG_TEMP_OS_MAX); |
| 338 | set_temp(os_hyst, temp_os_hyst, LM80_REG_TEMP_OS_HYST); | 298 | set_temp(os_hyst, temp_os_hyst, LM80_REG_TEMP_OS_HYST); |
| 339 | 299 | ||
| 340 | static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, char *buf) | 300 | static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, |
| 301 | char *buf) | ||
| 341 | { | 302 | { |
| 342 | struct lm80_data *data = lm80_update_device(dev); | 303 | struct lm80_data *data = lm80_update_device(dev); |
| 343 | return sprintf(buf, "%u\n", data->alarms); | 304 | return sprintf(buf, "%u\n", data->alarms); |
| 344 | } | 305 | } |
| 345 | 306 | ||
| 346 | static DEVICE_ATTR(in0_min, S_IWUSR | S_IRUGO, show_in_min0, set_in_min0); | 307 | static ssize_t show_alarm(struct device *dev, struct device_attribute *attr, |
| 347 | static DEVICE_ATTR(in1_min, S_IWUSR | S_IRUGO, show_in_min1, set_in_min1); | 308 | char *buf) |
| 348 | static DEVICE_ATTR(in2_min, S_IWUSR | S_IRUGO, show_in_min2, set_in_min2); | 309 | { |
| 349 | static DEVICE_ATTR(in3_min, S_IWUSR | S_IRUGO, show_in_min3, set_in_min3); | 310 | int bitnr = to_sensor_dev_attr(attr)->index; |
| 350 | static DEVICE_ATTR(in4_min, S_IWUSR | S_IRUGO, show_in_min4, set_in_min4); | 311 | struct lm80_data *data = lm80_update_device(dev); |
| 351 | static DEVICE_ATTR(in5_min, S_IWUSR | S_IRUGO, show_in_min5, set_in_min5); | 312 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); |
| 352 | static DEVICE_ATTR(in6_min, S_IWUSR | S_IRUGO, show_in_min6, set_in_min6); | 313 | } |
| 353 | static DEVICE_ATTR(in0_max, S_IWUSR | S_IRUGO, show_in_max0, set_in_max0); | 314 | |
| 354 | static DEVICE_ATTR(in1_max, S_IWUSR | S_IRUGO, show_in_max1, set_in_max1); | 315 | static SENSOR_DEVICE_ATTR(in0_min, S_IWUSR | S_IRUGO, |
| 355 | static DEVICE_ATTR(in2_max, S_IWUSR | S_IRUGO, show_in_max2, set_in_max2); | 316 | show_in_min, set_in_min, 0); |
| 356 | static DEVICE_ATTR(in3_max, S_IWUSR | S_IRUGO, show_in_max3, set_in_max3); | 317 | static SENSOR_DEVICE_ATTR(in1_min, S_IWUSR | S_IRUGO, |
| 357 | static DEVICE_ATTR(in4_max, S_IWUSR | S_IRUGO, show_in_max4, set_in_max4); | 318 | show_in_min, set_in_min, 1); |
| 358 | static DEVICE_ATTR(in5_max, S_IWUSR | S_IRUGO, show_in_max5, set_in_max5); | 319 | static SENSOR_DEVICE_ATTR(in2_min, S_IWUSR | S_IRUGO, |
| 359 | static DEVICE_ATTR(in6_max, S_IWUSR | S_IRUGO, show_in_max6, set_in_max6); | 320 | show_in_min, set_in_min, 2); |
| 360 | static DEVICE_ATTR(in0_input, S_IRUGO, show_in_input0, NULL); | 321 | static SENSOR_DEVICE_ATTR(in3_min, S_IWUSR | S_IRUGO, |
| 361 | static DEVICE_ATTR(in1_input, S_IRUGO, show_in_input1, NULL); | 322 | show_in_min, set_in_min, 3); |
| 362 | static DEVICE_ATTR(in2_input, S_IRUGO, show_in_input2, NULL); | 323 | static SENSOR_DEVICE_ATTR(in4_min, S_IWUSR | S_IRUGO, |
| 363 | static DEVICE_ATTR(in3_input, S_IRUGO, show_in_input3, NULL); | 324 | show_in_min, set_in_min, 4); |
| 364 | static DEVICE_ATTR(in4_input, S_IRUGO, show_in_input4, NULL); | 325 | static SENSOR_DEVICE_ATTR(in5_min, S_IWUSR | S_IRUGO, |
| 365 | static DEVICE_ATTR(in5_input, S_IRUGO, show_in_input5, NULL); | 326 | show_in_min, set_in_min, 5); |
| 366 | static DEVICE_ATTR(in6_input, S_IRUGO, show_in_input6, NULL); | 327 | static SENSOR_DEVICE_ATTR(in6_min, S_IWUSR | S_IRUGO, |
| 367 | static DEVICE_ATTR(fan1_min, S_IWUSR | S_IRUGO, show_fan_min1, | 328 | show_in_min, set_in_min, 6); |
| 368 | set_fan_min1); | 329 | static SENSOR_DEVICE_ATTR(in0_max, S_IWUSR | S_IRUGO, |
| 369 | static DEVICE_ATTR(fan2_min, S_IWUSR | S_IRUGO, show_fan_min2, | 330 | show_in_max, set_in_max, 0); |
| 370 | set_fan_min2); | 331 | static SENSOR_DEVICE_ATTR(in1_max, S_IWUSR | S_IRUGO, |
| 371 | static DEVICE_ATTR(fan1_input, S_IRUGO, show_fan_input1, NULL); | 332 | show_in_max, set_in_max, 1); |
| 372 | static DEVICE_ATTR(fan2_input, S_IRUGO, show_fan_input2, NULL); | 333 | static SENSOR_DEVICE_ATTR(in2_max, S_IWUSR | S_IRUGO, |
| 373 | static DEVICE_ATTR(fan1_div, S_IWUSR | S_IRUGO, show_fan_div1, set_fan_div1); | 334 | show_in_max, set_in_max, 2); |
| 374 | static DEVICE_ATTR(fan2_div, S_IWUSR | S_IRUGO, show_fan_div2, set_fan_div2); | 335 | static SENSOR_DEVICE_ATTR(in3_max, S_IWUSR | S_IRUGO, |
| 336 | show_in_max, set_in_max, 3); | ||
| 337 | static SENSOR_DEVICE_ATTR(in4_max, S_IWUSR | S_IRUGO, | ||
| 338 | show_in_max, set_in_max, 4); | ||
| 339 | static SENSOR_DEVICE_ATTR(in5_max, S_IWUSR | S_IRUGO, | ||
| 340 | show_in_max, set_in_max, 5); | ||
| 341 | static SENSOR_DEVICE_ATTR(in6_max, S_IWUSR | S_IRUGO, | ||
| 342 | show_in_max, set_in_max, 6); | ||
| 343 | static SENSOR_DEVICE_ATTR(in0_input, S_IRUGO, show_in_input, NULL, 0); | ||
| 344 | static SENSOR_DEVICE_ATTR(in1_input, S_IRUGO, show_in_input, NULL, 1); | ||
| 345 | static SENSOR_DEVICE_ATTR(in2_input, S_IRUGO, show_in_input, NULL, 2); | ||
| 346 | static SENSOR_DEVICE_ATTR(in3_input, S_IRUGO, show_in_input, NULL, 3); | ||
| 347 | static SENSOR_DEVICE_ATTR(in4_input, S_IRUGO, show_in_input, NULL, 4); | ||
| 348 | static SENSOR_DEVICE_ATTR(in5_input, S_IRUGO, show_in_input, NULL, 5); | ||
| 349 | static SENSOR_DEVICE_ATTR(in6_input, S_IRUGO, show_in_input, NULL, 6); | ||
| 350 | static SENSOR_DEVICE_ATTR(fan1_min, S_IWUSR | S_IRUGO, | ||
| 351 | show_fan_min, set_fan_min, 0); | ||
| 352 | static SENSOR_DEVICE_ATTR(fan2_min, S_IWUSR | S_IRUGO, | ||
| 353 | show_fan_min, set_fan_min, 1); | ||
| 354 | static SENSOR_DEVICE_ATTR(fan1_input, S_IRUGO, show_fan_input, NULL, 0); | ||
| 355 | static SENSOR_DEVICE_ATTR(fan2_input, S_IRUGO, show_fan_input, NULL, 1); | ||
| 356 | static SENSOR_DEVICE_ATTR(fan1_div, S_IWUSR | S_IRUGO, | ||
| 357 | show_fan_div, set_fan_div, 0); | ||
| 358 | static SENSOR_DEVICE_ATTR(fan2_div, S_IWUSR | S_IRUGO, | ||
| 359 | show_fan_div, set_fan_div, 1); | ||
| 375 | static DEVICE_ATTR(temp1_input, S_IRUGO, show_temp_input1, NULL); | 360 | static DEVICE_ATTR(temp1_input, S_IRUGO, show_temp_input1, NULL); |
| 376 | static DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, show_temp_hot_max, | 361 | static DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, show_temp_hot_max, |
| 377 | set_temp_hot_max); | 362 | set_temp_hot_max); |
| @@ -382,6 +367,17 @@ static DEVICE_ATTR(temp1_crit, S_IWUSR | S_IRUGO, show_temp_os_max, | |||
| 382 | static DEVICE_ATTR(temp1_crit_hyst, S_IWUSR | S_IRUGO, show_temp_os_hyst, | 367 | static DEVICE_ATTR(temp1_crit_hyst, S_IWUSR | S_IRUGO, show_temp_os_hyst, |
| 383 | set_temp_os_hyst); | 368 | set_temp_os_hyst); |
| 384 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | 369 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); |
| 370 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 0); | ||
| 371 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 1); | ||
| 372 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 373 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 374 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 375 | static SENSOR_DEVICE_ATTR(in5_alarm, S_IRUGO, show_alarm, NULL, 5); | ||
| 376 | static SENSOR_DEVICE_ATTR(in6_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 377 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 10); | ||
| 378 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 11); | ||
| 379 | static SENSOR_DEVICE_ATTR(temp1_max_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 380 | static SENSOR_DEVICE_ATTR(temp1_crit_alarm, S_IRUGO, show_alarm, NULL, 13); | ||
| 385 | 381 | ||
| 386 | /* | 382 | /* |
| 387 | * Real code | 383 | * Real code |
| @@ -395,40 +391,50 @@ static int lm80_attach_adapter(struct i2c_adapter *adapter) | |||
| 395 | } | 391 | } |
| 396 | 392 | ||
| 397 | static struct attribute *lm80_attributes[] = { | 393 | static struct attribute *lm80_attributes[] = { |
| 398 | &dev_attr_in0_min.attr, | 394 | &sensor_dev_attr_in0_min.dev_attr.attr, |
| 399 | &dev_attr_in1_min.attr, | 395 | &sensor_dev_attr_in1_min.dev_attr.attr, |
| 400 | &dev_attr_in2_min.attr, | 396 | &sensor_dev_attr_in2_min.dev_attr.attr, |
| 401 | &dev_attr_in3_min.attr, | 397 | &sensor_dev_attr_in3_min.dev_attr.attr, |
| 402 | &dev_attr_in4_min.attr, | 398 | &sensor_dev_attr_in4_min.dev_attr.attr, |
| 403 | &dev_attr_in5_min.attr, | 399 | &sensor_dev_attr_in5_min.dev_attr.attr, |
| 404 | &dev_attr_in6_min.attr, | 400 | &sensor_dev_attr_in6_min.dev_attr.attr, |
| 405 | &dev_attr_in0_max.attr, | 401 | &sensor_dev_attr_in0_max.dev_attr.attr, |
| 406 | &dev_attr_in1_max.attr, | 402 | &sensor_dev_attr_in1_max.dev_attr.attr, |
| 407 | &dev_attr_in2_max.attr, | 403 | &sensor_dev_attr_in2_max.dev_attr.attr, |
| 408 | &dev_attr_in3_max.attr, | 404 | &sensor_dev_attr_in3_max.dev_attr.attr, |
| 409 | &dev_attr_in4_max.attr, | 405 | &sensor_dev_attr_in4_max.dev_attr.attr, |
| 410 | &dev_attr_in5_max.attr, | 406 | &sensor_dev_attr_in5_max.dev_attr.attr, |
| 411 | &dev_attr_in6_max.attr, | 407 | &sensor_dev_attr_in6_max.dev_attr.attr, |
| 412 | &dev_attr_in0_input.attr, | 408 | &sensor_dev_attr_in0_input.dev_attr.attr, |
| 413 | &dev_attr_in1_input.attr, | 409 | &sensor_dev_attr_in1_input.dev_attr.attr, |
| 414 | &dev_attr_in2_input.attr, | 410 | &sensor_dev_attr_in2_input.dev_attr.attr, |
| 415 | &dev_attr_in3_input.attr, | 411 | &sensor_dev_attr_in3_input.dev_attr.attr, |
| 416 | &dev_attr_in4_input.attr, | 412 | &sensor_dev_attr_in4_input.dev_attr.attr, |
| 417 | &dev_attr_in5_input.attr, | 413 | &sensor_dev_attr_in5_input.dev_attr.attr, |
| 418 | &dev_attr_in6_input.attr, | 414 | &sensor_dev_attr_in6_input.dev_attr.attr, |
| 419 | &dev_attr_fan1_min.attr, | 415 | &sensor_dev_attr_fan1_min.dev_attr.attr, |
| 420 | &dev_attr_fan2_min.attr, | 416 | &sensor_dev_attr_fan2_min.dev_attr.attr, |
| 421 | &dev_attr_fan1_input.attr, | 417 | &sensor_dev_attr_fan1_input.dev_attr.attr, |
| 422 | &dev_attr_fan2_input.attr, | 418 | &sensor_dev_attr_fan2_input.dev_attr.attr, |
| 423 | &dev_attr_fan1_div.attr, | 419 | &sensor_dev_attr_fan1_div.dev_attr.attr, |
| 424 | &dev_attr_fan2_div.attr, | 420 | &sensor_dev_attr_fan2_div.dev_attr.attr, |
| 425 | &dev_attr_temp1_input.attr, | 421 | &dev_attr_temp1_input.attr, |
| 426 | &dev_attr_temp1_max.attr, | 422 | &dev_attr_temp1_max.attr, |
| 427 | &dev_attr_temp1_max_hyst.attr, | 423 | &dev_attr_temp1_max_hyst.attr, |
| 428 | &dev_attr_temp1_crit.attr, | 424 | &dev_attr_temp1_crit.attr, |
| 429 | &dev_attr_temp1_crit_hyst.attr, | 425 | &dev_attr_temp1_crit_hyst.attr, |
| 430 | &dev_attr_alarms.attr, | 426 | &dev_attr_alarms.attr, |
| 431 | 427 | &sensor_dev_attr_in0_alarm.dev_attr.attr, | |
| 428 | &sensor_dev_attr_in1_alarm.dev_attr.attr, | ||
| 429 | &sensor_dev_attr_in2_alarm.dev_attr.attr, | ||
| 430 | &sensor_dev_attr_in3_alarm.dev_attr.attr, | ||
| 431 | &sensor_dev_attr_in4_alarm.dev_attr.attr, | ||
| 432 | &sensor_dev_attr_in5_alarm.dev_attr.attr, | ||
| 433 | &sensor_dev_attr_in6_alarm.dev_attr.attr, | ||
| 434 | &sensor_dev_attr_fan1_alarm.dev_attr.attr, | ||
| 435 | &sensor_dev_attr_fan2_alarm.dev_attr.attr, | ||
| 436 | &sensor_dev_attr_temp1_max_alarm.dev_attr.attr, | ||
| 437 | &sensor_dev_attr_temp1_crit_alarm.dev_attr.attr, | ||
| 432 | NULL | 438 | NULL |
| 433 | }; | 439 | }; |
| 434 | 440 | ||
| @@ -439,7 +445,7 @@ static const struct attribute_group lm80_group = { | |||
| 439 | static int lm80_detect(struct i2c_adapter *adapter, int address, int kind) | 445 | static int lm80_detect(struct i2c_adapter *adapter, int address, int kind) |
| 440 | { | 446 | { |
| 441 | int i, cur; | 447 | int i, cur; |
| 442 | struct i2c_client *new_client; | 448 | struct i2c_client *client; |
| 443 | struct lm80_data *data; | 449 | struct lm80_data *data; |
| 444 | int err = 0; | 450 | int err = 0; |
| 445 | const char *name; | 451 | const char *name; |
| @@ -455,21 +461,20 @@ static int lm80_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 455 | goto exit; | 461 | goto exit; |
| 456 | } | 462 | } |
| 457 | 463 | ||
| 458 | new_client = &data->client; | 464 | client = &data->client; |
| 459 | i2c_set_clientdata(new_client, data); | 465 | i2c_set_clientdata(client, data); |
| 460 | new_client->addr = address; | 466 | client->addr = address; |
| 461 | new_client->adapter = adapter; | 467 | client->adapter = adapter; |
| 462 | new_client->driver = &lm80_driver; | 468 | client->driver = &lm80_driver; |
| 463 | new_client->flags = 0; | ||
| 464 | 469 | ||
| 465 | /* Now, we do the remaining detection. It is lousy. */ | 470 | /* Now, we do the remaining detection. It is lousy. */ |
| 466 | if (lm80_read_value(new_client, LM80_REG_ALARM2) & 0xc0) | 471 | if (lm80_read_value(client, LM80_REG_ALARM2) & 0xc0) |
| 467 | goto error_free; | 472 | goto error_free; |
| 468 | for (i = 0x2a; i <= 0x3d; i++) { | 473 | for (i = 0x2a; i <= 0x3d; i++) { |
| 469 | cur = i2c_smbus_read_byte_data(new_client, i); | 474 | cur = i2c_smbus_read_byte_data(client, i); |
| 470 | if ((i2c_smbus_read_byte_data(new_client, i + 0x40) != cur) | 475 | if ((i2c_smbus_read_byte_data(client, i + 0x40) != cur) |
| 471 | || (i2c_smbus_read_byte_data(new_client, i + 0x80) != cur) | 476 | || (i2c_smbus_read_byte_data(client, i + 0x80) != cur) |
| 472 | || (i2c_smbus_read_byte_data(new_client, i + 0xc0) != cur)) | 477 | || (i2c_smbus_read_byte_data(client, i + 0xc0) != cur)) |
| 473 | goto error_free; | 478 | goto error_free; |
| 474 | } | 479 | } |
| 475 | 480 | ||
| @@ -477,27 +482,26 @@ static int lm80_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 477 | kind = lm80; | 482 | kind = lm80; |
| 478 | name = "lm80"; | 483 | name = "lm80"; |
| 479 | 484 | ||
| 480 | /* Fill in the remaining client fields and put it into the global list */ | 485 | /* Fill in the remaining client fields */ |
| 481 | strlcpy(new_client->name, name, I2C_NAME_SIZE); | 486 | strlcpy(client->name, name, I2C_NAME_SIZE); |
| 482 | data->valid = 0; | ||
| 483 | mutex_init(&data->update_lock); | 487 | mutex_init(&data->update_lock); |
| 484 | 488 | ||
| 485 | /* Tell the I2C layer a new client has arrived */ | 489 | /* Tell the I2C layer a new client has arrived */ |
| 486 | if ((err = i2c_attach_client(new_client))) | 490 | if ((err = i2c_attach_client(client))) |
| 487 | goto error_free; | 491 | goto error_free; |
| 488 | 492 | ||
| 489 | /* Initialize the LM80 chip */ | 493 | /* Initialize the LM80 chip */ |
| 490 | lm80_init_client(new_client); | 494 | lm80_init_client(client); |
| 491 | 495 | ||
| 492 | /* A few vars need to be filled upon startup */ | 496 | /* A few vars need to be filled upon startup */ |
| 493 | data->fan_min[0] = lm80_read_value(new_client, LM80_REG_FAN_MIN(1)); | 497 | data->fan_min[0] = lm80_read_value(client, LM80_REG_FAN_MIN(1)); |
| 494 | data->fan_min[1] = lm80_read_value(new_client, LM80_REG_FAN_MIN(2)); | 498 | data->fan_min[1] = lm80_read_value(client, LM80_REG_FAN_MIN(2)); |
| 495 | 499 | ||
| 496 | /* Register sysfs hooks */ | 500 | /* Register sysfs hooks */ |
| 497 | if ((err = sysfs_create_group(&new_client->dev.kobj, &lm80_group))) | 501 | if ((err = sysfs_create_group(&client->dev.kobj, &lm80_group))) |
| 498 | goto error_detach; | 502 | goto error_detach; |
| 499 | 503 | ||
| 500 | data->hwmon_dev = hwmon_device_register(&new_client->dev); | 504 | data->hwmon_dev = hwmon_device_register(&client->dev); |
| 501 | if (IS_ERR(data->hwmon_dev)) { | 505 | if (IS_ERR(data->hwmon_dev)) { |
| 502 | err = PTR_ERR(data->hwmon_dev); | 506 | err = PTR_ERR(data->hwmon_dev); |
| 503 | goto error_remove; | 507 | goto error_remove; |
| @@ -506,9 +510,9 @@ static int lm80_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 506 | return 0; | 510 | return 0; |
| 507 | 511 | ||
| 508 | error_remove: | 512 | error_remove: |
| 509 | sysfs_remove_group(&new_client->dev.kobj, &lm80_group); | 513 | sysfs_remove_group(&client->dev.kobj, &lm80_group); |
| 510 | error_detach: | 514 | error_detach: |
| 511 | i2c_detach_client(new_client); | 515 | i2c_detach_client(client); |
| 512 | error_free: | 516 | error_free: |
| 513 | kfree(data); | 517 | kfree(data); |
| 514 | exit: | 518 | exit: |
diff --git a/drivers/hwmon/lm83.c b/drivers/hwmon/lm83.c index 0336b4572a61..6e8903a6e902 100644 --- a/drivers/hwmon/lm83.c +++ b/drivers/hwmon/lm83.c | |||
| @@ -133,7 +133,6 @@ static struct i2c_driver lm83_driver = { | |||
| 133 | .driver = { | 133 | .driver = { |
| 134 | .name = "lm83", | 134 | .name = "lm83", |
| 135 | }, | 135 | }, |
| 136 | .id = I2C_DRIVERID_LM83, | ||
| 137 | .attach_adapter = lm83_attach_adapter, | 136 | .attach_adapter = lm83_attach_adapter, |
| 138 | .detach_client = lm83_detach_client, | 137 | .detach_client = lm83_detach_client, |
| 139 | }; | 138 | }; |
diff --git a/drivers/hwmon/lm85.c b/drivers/hwmon/lm85.c index a02480be65f2..4bb0f291a6b8 100644 --- a/drivers/hwmon/lm85.c +++ b/drivers/hwmon/lm85.c | |||
| @@ -367,7 +367,6 @@ static struct i2c_driver lm85_driver = { | |||
| 367 | .driver = { | 367 | .driver = { |
| 368 | .name = "lm85", | 368 | .name = "lm85", |
| 369 | }, | 369 | }, |
| 370 | .id = I2C_DRIVERID_LM85, | ||
| 371 | .attach_adapter = lm85_attach_adapter, | 370 | .attach_adapter = lm85_attach_adapter, |
| 372 | .detach_client = lm85_detach_client, | 371 | .detach_client = lm85_detach_client, |
| 373 | }; | 372 | }; |
| @@ -444,12 +443,8 @@ static ssize_t show_vrm_reg(struct device *dev, struct device_attribute *attr, c | |||
| 444 | 443 | ||
| 445 | static ssize_t store_vrm_reg(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 444 | static ssize_t store_vrm_reg(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) |
| 446 | { | 445 | { |
| 447 | struct i2c_client *client = to_i2c_client(dev); | 446 | struct lm85_data *data = dev_get_drvdata(dev); |
| 448 | struct lm85_data *data = i2c_get_clientdata(client); | 447 | data->vrm = simple_strtoul(buf, NULL, 10); |
| 449 | u32 val; | ||
| 450 | |||
| 451 | val = simple_strtoul(buf, NULL, 10); | ||
| 452 | data->vrm = val; | ||
| 453 | return count; | 448 | return count; |
| 454 | } | 449 | } |
| 455 | 450 | ||
| @@ -519,17 +514,64 @@ static ssize_t show_pwm_enable(struct device *dev, struct device_attribute | |||
| 519 | { | 514 | { |
| 520 | int nr = to_sensor_dev_attr(attr)->index; | 515 | int nr = to_sensor_dev_attr(attr)->index; |
| 521 | struct lm85_data *data = lm85_update_device(dev); | 516 | struct lm85_data *data = lm85_update_device(dev); |
| 522 | int pwm_zone; | 517 | int pwm_zone, enable; |
| 523 | 518 | ||
| 524 | pwm_zone = ZONE_FROM_REG(data->autofan[nr].config); | 519 | pwm_zone = ZONE_FROM_REG(data->autofan[nr].config); |
| 525 | return sprintf(buf,"%d\n", (pwm_zone != 0 && pwm_zone != -1) ); | 520 | switch (pwm_zone) { |
| 521 | case -1: /* PWM is always at 100% */ | ||
| 522 | enable = 0; | ||
| 523 | break; | ||
| 524 | case 0: /* PWM is always at 0% */ | ||
| 525 | case -2: /* PWM responds to manual control */ | ||
| 526 | enable = 1; | ||
| 527 | break; | ||
| 528 | default: /* PWM in automatic mode */ | ||
| 529 | enable = 2; | ||
| 530 | } | ||
| 531 | return sprintf(buf, "%d\n", enable); | ||
| 532 | } | ||
| 533 | |||
| 534 | static ssize_t set_pwm_enable(struct device *dev, struct device_attribute | ||
| 535 | *attr, const char *buf, size_t count) | ||
| 536 | { | ||
| 537 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 538 | struct i2c_client *client = to_i2c_client(dev); | ||
| 539 | struct lm85_data *data = i2c_get_clientdata(client); | ||
| 540 | long val = simple_strtol(buf, NULL, 10); | ||
| 541 | u8 config; | ||
| 542 | |||
| 543 | switch (val) { | ||
| 544 | case 0: | ||
| 545 | config = 3; | ||
| 546 | break; | ||
| 547 | case 1: | ||
| 548 | config = 7; | ||
| 549 | break; | ||
| 550 | case 2: | ||
| 551 | /* Here we have to choose arbitrarily one of the 5 possible | ||
| 552 | configurations; I go for the safest */ | ||
| 553 | config = 6; | ||
| 554 | break; | ||
| 555 | default: | ||
| 556 | return -EINVAL; | ||
| 557 | } | ||
| 558 | |||
| 559 | mutex_lock(&data->update_lock); | ||
| 560 | data->autofan[nr].config = lm85_read_value(client, | ||
| 561 | LM85_REG_AFAN_CONFIG(nr)); | ||
| 562 | data->autofan[nr].config = (data->autofan[nr].config & ~0xe0) | ||
| 563 | | (config << 5); | ||
| 564 | lm85_write_value(client, LM85_REG_AFAN_CONFIG(nr), | ||
| 565 | data->autofan[nr].config); | ||
| 566 | mutex_unlock(&data->update_lock); | ||
| 567 | return count; | ||
| 526 | } | 568 | } |
| 527 | 569 | ||
| 528 | #define show_pwm_reg(offset) \ | 570 | #define show_pwm_reg(offset) \ |
| 529 | static SENSOR_DEVICE_ATTR(pwm##offset, S_IRUGO | S_IWUSR, \ | 571 | static SENSOR_DEVICE_ATTR(pwm##offset, S_IRUGO | S_IWUSR, \ |
| 530 | show_pwm, set_pwm, offset - 1); \ | 572 | show_pwm, set_pwm, offset - 1); \ |
| 531 | static SENSOR_DEVICE_ATTR(pwm##offset##_enable, S_IRUGO, \ | 573 | static SENSOR_DEVICE_ATTR(pwm##offset##_enable, S_IRUGO | S_IWUSR, \ |
| 532 | show_pwm_enable, NULL, offset - 1) | 574 | show_pwm_enable, set_pwm_enable, offset - 1) |
| 533 | 575 | ||
| 534 | show_pwm_reg(1); | 576 | show_pwm_reg(1); |
| 535 | show_pwm_reg(2); | 577 | show_pwm_reg(2); |
diff --git a/drivers/hwmon/lm87.c b/drivers/hwmon/lm87.c index 28cdff0c556b..8ee07c5c97a1 100644 --- a/drivers/hwmon/lm87.c +++ b/drivers/hwmon/lm87.c | |||
| @@ -5,7 +5,7 @@ | |||
| 5 | * Philip Edelbrock <phil@netroedge.com> | 5 | * Philip Edelbrock <phil@netroedge.com> |
| 6 | * Stephen Rousset <stephen.rousset@rocketlogix.com> | 6 | * Stephen Rousset <stephen.rousset@rocketlogix.com> |
| 7 | * Dan Eaton <dan.eaton@rocketlogix.com> | 7 | * Dan Eaton <dan.eaton@rocketlogix.com> |
| 8 | * Copyright (C) 2004 Jean Delvare <khali@linux-fr.org> | 8 | * Copyright (C) 2004,2007 Jean Delvare <khali@linux-fr.org> |
| 9 | * | 9 | * |
| 10 | * Original port to Linux 2.6 by Jeff Oliver. | 10 | * Original port to Linux 2.6 by Jeff Oliver. |
| 11 | * | 11 | * |
| @@ -37,6 +37,11 @@ | |||
| 37 | * instead. The LM87 is the only hardware monitoring chipset I know of | 37 | * instead. The LM87 is the only hardware monitoring chipset I know of |
| 38 | * which uses amplitude modulation. Be careful when using this feature. | 38 | * which uses amplitude modulation. Be careful when using this feature. |
| 39 | * | 39 | * |
| 40 | * This driver also supports the ADM1024, a sensor chip made by Analog | ||
| 41 | * Devices. That chip is fully compatible with the LM87. Complete | ||
| 42 | * datasheet can be obtained from Analog's website at: | ||
| 43 | * http://www.analog.com/en/prod/0,2877,ADM1024,00.html | ||
| 44 | * | ||
| 40 | * This program is free software; you can redistribute it and/or modify | 45 | * This program is free software; you can redistribute it and/or modify |
| 41 | * it under the terms of the GNU General Public License as published by | 46 | * it under the terms of the GNU General Public License as published by |
| 42 | * the Free Software Foundation; either version 2 of the License, or | 47 | * the Free Software Foundation; either version 2 of the License, or |
| @@ -74,7 +79,7 @@ static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; | |||
| 74 | * Insmod parameters | 79 | * Insmod parameters |
| 75 | */ | 80 | */ |
| 76 | 81 | ||
| 77 | I2C_CLIENT_INSMOD_1(lm87); | 82 | I2C_CLIENT_INSMOD_2(lm87, adm1024); |
| 78 | 83 | ||
| 79 | /* | 84 | /* |
| 80 | * The LM87 registers | 85 | * The LM87 registers |
| @@ -166,7 +171,6 @@ static struct i2c_driver lm87_driver = { | |||
| 166 | .driver = { | 171 | .driver = { |
| 167 | .name = "lm87", | 172 | .name = "lm87", |
| 168 | }, | 173 | }, |
| 169 | .id = I2C_DRIVERID_LM87, | ||
| 170 | .attach_adapter = lm87_attach_adapter, | 174 | .attach_adapter = lm87_attach_adapter, |
| 171 | .detach_client = lm87_detach_client, | 175 | .detach_client = lm87_detach_client, |
| 172 | }; | 176 | }; |
| @@ -506,8 +510,7 @@ static ssize_t show_vrm(struct device *dev, struct device_attribute *attr, char | |||
| 506 | } | 510 | } |
| 507 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) | 511 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, const char *buf, size_t count) |
| 508 | { | 512 | { |
| 509 | struct i2c_client *client = to_i2c_client(dev); | 513 | struct lm87_data *data = dev_get_drvdata(dev); |
| 510 | struct lm87_data *data = i2c_get_clientdata(client); | ||
| 511 | data->vrm = simple_strtoul(buf, NULL, 10); | 514 | data->vrm = simple_strtoul(buf, NULL, 10); |
| 512 | return count; | 515 | return count; |
| 513 | } | 516 | } |
| @@ -662,6 +665,7 @@ static int lm87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 662 | struct i2c_client *new_client; | 665 | struct i2c_client *new_client; |
| 663 | struct lm87_data *data; | 666 | struct lm87_data *data; |
| 664 | int err = 0; | 667 | int err = 0; |
| 668 | static const char *names[] = { "lm87", "adm1024" }; | ||
| 665 | 669 | ||
| 666 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) | 670 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) |
| 667 | goto exit; | 671 | goto exit; |
| @@ -686,11 +690,18 @@ static int lm87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 686 | 690 | ||
| 687 | /* Now, we do the remaining detection. */ | 691 | /* Now, we do the remaining detection. */ |
| 688 | if (kind < 0) { | 692 | if (kind < 0) { |
| 693 | u8 cid = lm87_read_value(new_client, LM87_REG_COMPANY_ID); | ||
| 689 | u8 rev = lm87_read_value(new_client, LM87_REG_REVISION); | 694 | u8 rev = lm87_read_value(new_client, LM87_REG_REVISION); |
| 690 | 695 | ||
| 691 | if (rev < 0x01 || rev > 0x08 | 696 | if (cid == 0x02 /* National Semiconductor */ |
| 692 | || (lm87_read_value(new_client, LM87_REG_CONFIG) & 0x80) | 697 | && (rev >= 0x01 && rev <= 0x08)) |
| 693 | || lm87_read_value(new_client, LM87_REG_COMPANY_ID) != 0x02) { | 698 | kind = lm87; |
| 699 | else if (cid == 0x41 /* Analog Devices */ | ||
| 700 | && (rev & 0xf0) == 0x10) | ||
| 701 | kind = adm1024; | ||
| 702 | |||
| 703 | if (kind < 0 | ||
| 704 | || (lm87_read_value(new_client, LM87_REG_CONFIG) & 0x80)) { | ||
| 694 | dev_dbg(&adapter->dev, | 705 | dev_dbg(&adapter->dev, |
| 695 | "LM87 detection failed at 0x%02x.\n", | 706 | "LM87 detection failed at 0x%02x.\n", |
| 696 | address); | 707 | address); |
| @@ -699,7 +710,7 @@ static int lm87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 699 | } | 710 | } |
| 700 | 711 | ||
| 701 | /* We can fill in the remaining client fields */ | 712 | /* We can fill in the remaining client fields */ |
| 702 | strlcpy(new_client->name, "lm87", I2C_NAME_SIZE); | 713 | strlcpy(new_client->name, names[kind - 1], I2C_NAME_SIZE); |
| 703 | data->valid = 0; | 714 | data->valid = 0; |
| 704 | mutex_init(&data->update_lock); | 715 | mutex_init(&data->update_lock); |
| 705 | 716 | ||
diff --git a/drivers/hwmon/lm90.c b/drivers/hwmon/lm90.c index 960df9fa75af..f7ec95bedbf6 100644 --- a/drivers/hwmon/lm90.c +++ b/drivers/hwmon/lm90.c | |||
| @@ -204,7 +204,6 @@ static struct i2c_driver lm90_driver = { | |||
| 204 | .driver = { | 204 | .driver = { |
| 205 | .name = "lm90", | 205 | .name = "lm90", |
| 206 | }, | 206 | }, |
| 207 | .id = I2C_DRIVERID_LM90, | ||
| 208 | .attach_adapter = lm90_attach_adapter, | 207 | .attach_adapter = lm90_attach_adapter, |
| 209 | .detach_client = lm90_detach_client, | 208 | .detach_client = lm90_detach_client, |
| 210 | }; | 209 | }; |
| @@ -531,24 +530,24 @@ static int lm90_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 531 | kind = lm90; | 530 | kind = lm90; |
| 532 | 531 | ||
| 533 | if (kind < 0) { /* detection and identification */ | 532 | if (kind < 0) { /* detection and identification */ |
| 534 | u8 man_id, chip_id, reg_config1, reg_convrate; | 533 | int man_id, chip_id, reg_config1, reg_convrate; |
| 535 | 534 | ||
| 536 | if (lm90_read_reg(new_client, LM90_REG_R_MAN_ID, | 535 | if ((man_id = i2c_smbus_read_byte_data(new_client, |
| 537 | &man_id) < 0 | 536 | LM90_REG_R_MAN_ID)) < 0 |
| 538 | || lm90_read_reg(new_client, LM90_REG_R_CHIP_ID, | 537 | || (chip_id = i2c_smbus_read_byte_data(new_client, |
| 539 | &chip_id) < 0 | 538 | LM90_REG_R_CHIP_ID)) < 0 |
| 540 | || lm90_read_reg(new_client, LM90_REG_R_CONFIG1, | 539 | || (reg_config1 = i2c_smbus_read_byte_data(new_client, |
| 541 | ®_config1) < 0 | 540 | LM90_REG_R_CONFIG1)) < 0 |
| 542 | || lm90_read_reg(new_client, LM90_REG_R_CONVRATE, | 541 | || (reg_convrate = i2c_smbus_read_byte_data(new_client, |
| 543 | ®_convrate) < 0) | 542 | LM90_REG_R_CONVRATE)) < 0) |
| 544 | goto exit_free; | 543 | goto exit_free; |
| 545 | 544 | ||
| 546 | if ((address == 0x4C || address == 0x4D) | 545 | if ((address == 0x4C || address == 0x4D) |
| 547 | && man_id == 0x01) { /* National Semiconductor */ | 546 | && man_id == 0x01) { /* National Semiconductor */ |
| 548 | u8 reg_config2; | 547 | int reg_config2; |
| 549 | 548 | ||
| 550 | if (lm90_read_reg(new_client, LM90_REG_R_CONFIG2, | 549 | if ((reg_config2 = i2c_smbus_read_byte_data(new_client, |
| 551 | ®_config2) < 0) | 550 | LM90_REG_R_CONFIG2)) < 0) |
| 552 | goto exit_free; | 551 | goto exit_free; |
| 553 | 552 | ||
| 554 | if ((reg_config1 & 0x2A) == 0x00 | 553 | if ((reg_config1 & 0x2A) == 0x00 |
diff --git a/drivers/hwmon/lm92.c b/drivers/hwmon/lm92.c index 61d1bd1d5b6e..af5c77d568fe 100644 --- a/drivers/hwmon/lm92.c +++ b/drivers/hwmon/lm92.c | |||
| @@ -428,7 +428,6 @@ static struct i2c_driver lm92_driver = { | |||
| 428 | .driver = { | 428 | .driver = { |
| 429 | .name = "lm92", | 429 | .name = "lm92", |
| 430 | }, | 430 | }, |
| 431 | .id = I2C_DRIVERID_LM92, | ||
| 432 | .attach_adapter = lm92_attach_adapter, | 431 | .attach_adapter = lm92_attach_adapter, |
| 433 | .detach_client = lm92_detach_client, | 432 | .detach_client = lm92_detach_client, |
| 434 | }; | 433 | }; |
diff --git a/drivers/hwmon/pc87360.c b/drivers/hwmon/pc87360.c index 9d660133d517..9b462bb13fa3 100644 --- a/drivers/hwmon/pc87360.c +++ b/drivers/hwmon/pc87360.c | |||
| @@ -59,6 +59,10 @@ MODULE_PARM_DESC(init, | |||
| 59 | " 2: Forcibly enable all voltage and temperature channels, except in9\n" | 59 | " 2: Forcibly enable all voltage and temperature channels, except in9\n" |
| 60 | " 3: Forcibly enable all voltage and temperature channels, including in9"); | 60 | " 3: Forcibly enable all voltage and temperature channels, including in9"); |
| 61 | 61 | ||
| 62 | static unsigned short force_id; | ||
| 63 | module_param(force_id, ushort, 0); | ||
| 64 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 65 | |||
| 62 | /* | 66 | /* |
| 63 | * Super-I/O registers and operations | 67 | * Super-I/O registers and operations |
| 64 | */ | 68 | */ |
| @@ -826,7 +830,7 @@ static int __init pc87360_find(int sioaddr, u8 *devid, unsigned short *addresses | |||
| 826 | /* No superio_enter */ | 830 | /* No superio_enter */ |
| 827 | 831 | ||
| 828 | /* Identify device */ | 832 | /* Identify device */ |
| 829 | val = superio_inb(sioaddr, DEVID); | 833 | val = force_id ? force_id : superio_inb(sioaddr, DEVID); |
| 830 | switch (val) { | 834 | switch (val) { |
| 831 | case 0xE1: /* PC87360 */ | 835 | case 0xE1: /* PC87360 */ |
| 832 | case 0xE8: /* PC87363 */ | 836 | case 0xE8: /* PC87363 */ |
diff --git a/drivers/hwmon/pc87427.c b/drivers/hwmon/pc87427.c index d40509ad6ae6..7265f22ae5cd 100644 --- a/drivers/hwmon/pc87427.c +++ b/drivers/hwmon/pc87427.c | |||
| @@ -34,6 +34,10 @@ | |||
| 34 | #include <linux/ioport.h> | 34 | #include <linux/ioport.h> |
| 35 | #include <asm/io.h> | 35 | #include <asm/io.h> |
| 36 | 36 | ||
| 37 | static unsigned short force_id; | ||
| 38 | module_param(force_id, ushort, 0); | ||
| 39 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 40 | |||
| 37 | static struct platform_device *pdev; | 41 | static struct platform_device *pdev; |
| 38 | 42 | ||
| 39 | #define DRVNAME "pc87427" | 43 | #define DRVNAME "pc87427" |
| @@ -555,7 +559,7 @@ static int __init pc87427_find(int sioaddr, unsigned short *address) | |||
| 555 | int i, err = 0; | 559 | int i, err = 0; |
| 556 | 560 | ||
| 557 | /* Identify device */ | 561 | /* Identify device */ |
| 558 | val = superio_inb(sioaddr, SIOREG_DEVID); | 562 | val = force_id ? force_id : superio_inb(sioaddr, SIOREG_DEVID); |
| 559 | if (val != 0xf2) { /* PC87427 */ | 563 | if (val != 0xf2) { /* PC87427 */ |
| 560 | err = -ENODEV; | 564 | err = -ENODEV; |
| 561 | goto exit; | 565 | goto exit; |
diff --git a/drivers/hwmon/smsc47b397.c b/drivers/hwmon/smsc47b397.c index 0b57d2ea2cf7..f61d8f4185b2 100644 --- a/drivers/hwmon/smsc47b397.c +++ b/drivers/hwmon/smsc47b397.c | |||
| @@ -38,6 +38,10 @@ | |||
| 38 | #include <linux/mutex.h> | 38 | #include <linux/mutex.h> |
| 39 | #include <asm/io.h> | 39 | #include <asm/io.h> |
| 40 | 40 | ||
| 41 | static unsigned short force_id; | ||
| 42 | module_param(force_id, ushort, 0); | ||
| 43 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 44 | |||
| 41 | static struct platform_device *pdev; | 45 | static struct platform_device *pdev; |
| 42 | 46 | ||
| 43 | #define DRVNAME "smsc47b397" | 47 | #define DRVNAME "smsc47b397" |
| @@ -333,7 +337,7 @@ static int __init smsc47b397_find(unsigned short *addr) | |||
| 333 | u8 id, rev; | 337 | u8 id, rev; |
| 334 | 338 | ||
| 335 | superio_enter(); | 339 | superio_enter(); |
| 336 | id = superio_inb(SUPERIO_REG_DEVID); | 340 | id = force_id ? force_id : superio_inb(SUPERIO_REG_DEVID); |
| 337 | 341 | ||
| 338 | if ((id != 0x6f) && (id != 0x81) && (id != 0x85)) { | 342 | if ((id != 0x6f) && (id != 0x81) && (id != 0x85)) { |
| 339 | superio_exit(); | 343 | superio_exit(); |
diff --git a/drivers/hwmon/smsc47m1.c b/drivers/hwmon/smsc47m1.c index a10a380868e2..0d7f0c4d06bb 100644 --- a/drivers/hwmon/smsc47m1.c +++ b/drivers/hwmon/smsc47m1.c | |||
| @@ -39,6 +39,10 @@ | |||
| 39 | #include <linux/sysfs.h> | 39 | #include <linux/sysfs.h> |
| 40 | #include <asm/io.h> | 40 | #include <asm/io.h> |
| 41 | 41 | ||
| 42 | static unsigned short force_id; | ||
| 43 | module_param(force_id, ushort, 0); | ||
| 44 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 45 | |||
| 42 | static struct platform_device *pdev; | 46 | static struct platform_device *pdev; |
| 43 | 47 | ||
| 44 | #define DRVNAME "smsc47m1" | 48 | #define DRVNAME "smsc47m1" |
| @@ -399,7 +403,7 @@ static int __init smsc47m1_find(unsigned short *addr, | |||
| 399 | u8 val; | 403 | u8 val; |
| 400 | 404 | ||
| 401 | superio_enter(); | 405 | superio_enter(); |
| 402 | val = superio_inb(SUPERIO_REG_DEVID); | 406 | val = force_id ? force_id : superio_inb(SUPERIO_REG_DEVID); |
| 403 | 407 | ||
| 404 | /* | 408 | /* |
| 405 | * SMSC LPC47M10x/LPC47M112/LPC47M13x (device id 0x59), LPC47M14x | 409 | * SMSC LPC47M10x/LPC47M112/LPC47M13x (device id 0x59), LPC47M14x |
diff --git a/drivers/hwmon/smsc47m192.c b/drivers/hwmon/smsc47m192.c index b87552652588..8b0c188e60f6 100644 --- a/drivers/hwmon/smsc47m192.c +++ b/drivers/hwmon/smsc47m192.c | |||
| @@ -341,8 +341,7 @@ static ssize_t show_vrm(struct device *dev, struct device_attribute *attr, | |||
| 341 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, | 341 | static ssize_t set_vrm(struct device *dev, struct device_attribute *attr, |
| 342 | const char *buf, size_t count) | 342 | const char *buf, size_t count) |
| 343 | { | 343 | { |
| 344 | struct i2c_client *client = to_i2c_client(dev); | 344 | struct smsc47m192_data *data = dev_get_drvdata(dev); |
| 345 | struct smsc47m192_data *data = i2c_get_clientdata(client); | ||
| 346 | data->vrm = simple_strtoul(buf, NULL, 10); | 345 | data->vrm = simple_strtoul(buf, NULL, 10); |
| 347 | return count; | 346 | return count; |
| 348 | } | 347 | } |
diff --git a/drivers/hwmon/vt1211.c b/drivers/hwmon/vt1211.c index 7dfcc8dd316d..12b43590fa53 100644 --- a/drivers/hwmon/vt1211.c +++ b/drivers/hwmon/vt1211.c | |||
| @@ -42,6 +42,10 @@ static int int_mode = -1; | |||
| 42 | module_param(int_mode, int, 0); | 42 | module_param(int_mode, int, 0); |
| 43 | MODULE_PARM_DESC(int_mode, "Force the temperature interrupt mode"); | 43 | MODULE_PARM_DESC(int_mode, "Force the temperature interrupt mode"); |
| 44 | 44 | ||
| 45 | static unsigned short force_id; | ||
| 46 | module_param(force_id, ushort, 0); | ||
| 47 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 48 | |||
| 45 | static struct platform_device *pdev; | 49 | static struct platform_device *pdev; |
| 46 | 50 | ||
| 47 | #define DRVNAME "vt1211" | 51 | #define DRVNAME "vt1211" |
| @@ -1280,10 +1284,12 @@ EXIT: | |||
| 1280 | static int __init vt1211_find(int sio_cip, unsigned short *address) | 1284 | static int __init vt1211_find(int sio_cip, unsigned short *address) |
| 1281 | { | 1285 | { |
| 1282 | int err = -ENODEV; | 1286 | int err = -ENODEV; |
| 1287 | int devid; | ||
| 1283 | 1288 | ||
| 1284 | superio_enter(sio_cip); | 1289 | superio_enter(sio_cip); |
| 1285 | 1290 | ||
| 1286 | if (superio_inb(sio_cip, SIO_VT1211_DEVID) != SIO_VT1211_ID) { | 1291 | devid = force_id ? force_id : superio_inb(sio_cip, SIO_VT1211_DEVID); |
| 1292 | if (devid != SIO_VT1211_ID) { | ||
| 1287 | goto EXIT; | 1293 | goto EXIT; |
| 1288 | } | 1294 | } |
| 1289 | 1295 | ||
diff --git a/drivers/hwmon/vt8231.c b/drivers/hwmon/vt8231.c index 2196a84603f5..f87661775fe0 100644 --- a/drivers/hwmon/vt8231.c +++ b/drivers/hwmon/vt8231.c | |||
| @@ -504,7 +504,7 @@ static ssize_t set_fan_div(struct device *dev, struct device_attribute *attr, | |||
| 504 | case 4: data->fan_div[nr] = 2; break; | 504 | case 4: data->fan_div[nr] = 2; break; |
| 505 | case 8: data->fan_div[nr] = 3; break; | 505 | case 8: data->fan_div[nr] = 3; break; |
| 506 | default: | 506 | default: |
| 507 | dev_err(dev, "fan_div value %ld not supported." | 507 | dev_err(dev, "fan_div value %ld not supported. " |
| 508 | "Choose one of 1, 2, 4 or 8!\n", val); | 508 | "Choose one of 1, 2, 4 or 8!\n", val); |
| 509 | mutex_unlock(&data->update_lock); | 509 | mutex_unlock(&data->update_lock); |
| 510 | return -EINVAL; | 510 | return -EINVAL; |
diff --git a/drivers/hwmon/w83627ehf.c b/drivers/hwmon/w83627ehf.c index d5aa25ce5dbd..075164dd65a7 100644 --- a/drivers/hwmon/w83627ehf.c +++ b/drivers/hwmon/w83627ehf.c | |||
| @@ -59,6 +59,10 @@ static const char * w83627ehf_device_names[] = { | |||
| 59 | "w83627dhg", | 59 | "w83627dhg", |
| 60 | }; | 60 | }; |
| 61 | 61 | ||
| 62 | static unsigned short force_id; | ||
| 63 | module_param(force_id, ushort, 0); | ||
| 64 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 65 | |||
| 62 | #define DRVNAME "w83627ehf" | 66 | #define DRVNAME "w83627ehf" |
| 63 | 67 | ||
| 64 | /* | 68 | /* |
| @@ -1198,8 +1202,7 @@ static void w83627ehf_device_remove_files(struct device *dev) | |||
| 1198 | device_remove_file(dev, &sda_temp[i].dev_attr); | 1202 | device_remove_file(dev, &sda_temp[i].dev_attr); |
| 1199 | 1203 | ||
| 1200 | device_remove_file(dev, &dev_attr_name); | 1204 | device_remove_file(dev, &dev_attr_name); |
| 1201 | if (data->vid != 0x3f) | 1205 | device_remove_file(dev, &dev_attr_cpu0_vid); |
| 1202 | device_remove_file(dev, &dev_attr_cpu0_vid); | ||
| 1203 | } | 1206 | } |
| 1204 | 1207 | ||
| 1205 | /* Get the monitoring functions started */ | 1208 | /* Get the monitoring functions started */ |
| @@ -1299,11 +1302,16 @@ static int __devinit w83627ehf_probe(struct platform_device *pdev) | |||
| 1299 | } | 1302 | } |
| 1300 | } | 1303 | } |
| 1301 | 1304 | ||
| 1302 | data->vid = superio_inb(sio_data->sioreg, SIO_REG_VID_DATA) & 0x3f; | 1305 | data->vid = superio_inb(sio_data->sioreg, SIO_REG_VID_DATA); |
| 1306 | if (sio_data->kind == w83627ehf) /* 6 VID pins only */ | ||
| 1307 | data->vid &= 0x3f; | ||
| 1308 | |||
| 1309 | err = device_create_file(dev, &dev_attr_cpu0_vid); | ||
| 1310 | if (err) | ||
| 1311 | goto exit_release; | ||
| 1303 | } else { | 1312 | } else { |
| 1304 | dev_info(dev, "VID pins in output mode, CPU VID not " | 1313 | dev_info(dev, "VID pins in output mode, CPU VID not " |
| 1305 | "available\n"); | 1314 | "available\n"); |
| 1306 | data->vid = 0x3f; | ||
| 1307 | } | 1315 | } |
| 1308 | 1316 | ||
| 1309 | /* fan4 and fan5 share some pins with the GPIO and serial flash */ | 1317 | /* fan4 and fan5 share some pins with the GPIO and serial flash */ |
| @@ -1386,12 +1394,6 @@ static int __devinit w83627ehf_probe(struct platform_device *pdev) | |||
| 1386 | if (err) | 1394 | if (err) |
| 1387 | goto exit_remove; | 1395 | goto exit_remove; |
| 1388 | 1396 | ||
| 1389 | if (data->vid != 0x3f) { | ||
| 1390 | err = device_create_file(dev, &dev_attr_cpu0_vid); | ||
| 1391 | if (err) | ||
| 1392 | goto exit_remove; | ||
| 1393 | } | ||
| 1394 | |||
| 1395 | data->hwmon_dev = hwmon_device_register(dev); | 1397 | data->hwmon_dev = hwmon_device_register(dev); |
| 1396 | if (IS_ERR(data->hwmon_dev)) { | 1398 | if (IS_ERR(data->hwmon_dev)) { |
| 1397 | err = PTR_ERR(data->hwmon_dev); | 1399 | err = PTR_ERR(data->hwmon_dev); |
| @@ -1445,8 +1447,11 @@ static int __init w83627ehf_find(int sioaddr, unsigned short *addr, | |||
| 1445 | 1447 | ||
| 1446 | superio_enter(sioaddr); | 1448 | superio_enter(sioaddr); |
| 1447 | 1449 | ||
| 1448 | val = (superio_inb(sioaddr, SIO_REG_DEVID) << 8) | 1450 | if (force_id) |
| 1449 | | superio_inb(sioaddr, SIO_REG_DEVID + 1); | 1451 | val = force_id; |
| 1452 | else | ||
| 1453 | val = (superio_inb(sioaddr, SIO_REG_DEVID) << 8) | ||
| 1454 | | superio_inb(sioaddr, SIO_REG_DEVID + 1); | ||
| 1450 | switch (val & SIO_ID_MASK) { | 1455 | switch (val & SIO_ID_MASK) { |
| 1451 | case SIO_W83627EHF_ID: | 1456 | case SIO_W83627EHF_ID: |
| 1452 | sio_data->kind = w83627ehf; | 1457 | sio_data->kind = w83627ehf; |
diff --git a/drivers/hwmon/w83627hf.c b/drivers/hwmon/w83627hf.c index 879d0a6544cc..9564fb069957 100644 --- a/drivers/hwmon/w83627hf.c +++ b/drivers/hwmon/w83627hf.c | |||
| @@ -75,6 +75,10 @@ static int init = 1; | |||
| 75 | module_param(init, bool, 0); | 75 | module_param(init, bool, 0); |
| 76 | MODULE_PARM_DESC(init, "Set to zero to bypass chip initialization"); | 76 | MODULE_PARM_DESC(init, "Set to zero to bypass chip initialization"); |
| 77 | 77 | ||
| 78 | static unsigned short force_id; | ||
| 79 | module_param(force_id, ushort, 0); | ||
| 80 | MODULE_PARM_DESC(force_id, "Override the detected device ID"); | ||
| 81 | |||
| 78 | /* modified from kernel/include/traps.c */ | 82 | /* modified from kernel/include/traps.c */ |
| 79 | static int REG; /* The register to read/write */ | 83 | static int REG; /* The register to read/write */ |
| 80 | #define DEV 0x07 /* Register: Logical device select */ | 84 | #define DEV 0x07 /* Register: Logical device select */ |
| @@ -319,10 +323,8 @@ static inline u8 pwm_freq_to_reg(unsigned long val) | |||
| 319 | return (0x80 | (180000UL / (val << 8))); | 323 | return (0x80 | (180000UL / (val << 8))); |
| 320 | } | 324 | } |
| 321 | 325 | ||
| 322 | #define BEEP_MASK_FROM_REG(val) (val) | 326 | #define BEEP_MASK_FROM_REG(val) ((val) & 0xff7fff) |
| 323 | #define BEEP_MASK_TO_REG(val) ((val) & 0xffffff) | 327 | #define BEEP_MASK_TO_REG(val) ((val) & 0xff7fff) |
| 324 | #define BEEP_ENABLE_TO_REG(val) ((val)?1:0) | ||
| 325 | #define BEEP_ENABLE_FROM_REG(val) ((val)?1:0) | ||
| 326 | 328 | ||
| 327 | #define DIV_FROM_REG(val) (1 << (val)) | 329 | #define DIV_FROM_REG(val) (1 << (val)) |
| 328 | 330 | ||
| @@ -363,7 +365,6 @@ struct w83627hf_data { | |||
| 363 | u8 vid; /* Register encoding, combined */ | 365 | u8 vid; /* Register encoding, combined */ |
| 364 | u32 alarms; /* Register encoding, combined */ | 366 | u32 alarms; /* Register encoding, combined */ |
| 365 | u32 beep_mask; /* Register encoding, combined */ | 367 | u32 beep_mask; /* Register encoding, combined */ |
| 366 | u8 beep_enable; /* Boolean */ | ||
| 367 | u8 pwm[3]; /* Register value */ | 368 | u8 pwm[3]; /* Register value */ |
| 368 | u8 pwm_freq[3]; /* Register value */ | 369 | u8 pwm_freq[3]; /* Register value */ |
| 369 | u16 sens[3]; /* 1 = pentium diode; 2 = 3904 diode; | 370 | u16 sens[3]; /* 1 = pentium diode; 2 = 3904 diode; |
| @@ -713,65 +714,151 @@ show_alarms_reg(struct device *dev, struct device_attribute *attr, char *buf) | |||
| 713 | } | 714 | } |
| 714 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms_reg, NULL); | 715 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms_reg, NULL); |
| 715 | 716 | ||
| 716 | #define show_beep_reg(REG, reg) \ | 717 | static ssize_t |
| 717 | static ssize_t show_beep_##reg (struct device *dev, struct device_attribute *attr, char *buf) \ | 718 | show_alarm(struct device *dev, struct device_attribute *attr, char *buf) |
| 718 | { \ | 719 | { |
| 719 | struct w83627hf_data *data = w83627hf_update_device(dev); \ | 720 | struct w83627hf_data *data = w83627hf_update_device(dev); |
| 720 | return sprintf(buf,"%ld\n", \ | 721 | int bitnr = to_sensor_dev_attr(attr)->index; |
| 721 | (long)BEEP_##REG##_FROM_REG(data->beep_##reg)); \ | 722 | return sprintf(buf, "%u\n", (data->alarms >> bitnr) & 1); |
| 722 | } | 723 | } |
| 723 | show_beep_reg(ENABLE, enable) | 724 | static SENSOR_DEVICE_ATTR(in0_alarm, S_IRUGO, show_alarm, NULL, 0); |
| 724 | show_beep_reg(MASK, mask) | 725 | static SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL, 1); |
| 726 | static SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL, 2); | ||
| 727 | static SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL, 3); | ||
| 728 | static SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL, 8); | ||
| 729 | static SENSOR_DEVICE_ATTR(in5_alarm, S_IRUGO, show_alarm, NULL, 9); | ||
| 730 | static SENSOR_DEVICE_ATTR(in6_alarm, S_IRUGO, show_alarm, NULL, 10); | ||
| 731 | static SENSOR_DEVICE_ATTR(in7_alarm, S_IRUGO, show_alarm, NULL, 16); | ||
| 732 | static SENSOR_DEVICE_ATTR(in8_alarm, S_IRUGO, show_alarm, NULL, 17); | ||
| 733 | static SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL, 6); | ||
| 734 | static SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL, 7); | ||
| 735 | static SENSOR_DEVICE_ATTR(fan3_alarm, S_IRUGO, show_alarm, NULL, 11); | ||
| 736 | static SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL, 4); | ||
| 737 | static SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, show_alarm, NULL, 5); | ||
| 738 | static SENSOR_DEVICE_ATTR(temp3_alarm, S_IRUGO, show_alarm, NULL, 13); | ||
| 725 | 739 | ||
| 726 | #define BEEP_ENABLE 0 /* Store beep_enable */ | 740 | static ssize_t |
| 727 | #define BEEP_MASK 1 /* Store beep_mask */ | 741 | show_beep_mask(struct device *dev, struct device_attribute *attr, char *buf) |
| 742 | { | ||
| 743 | struct w83627hf_data *data = w83627hf_update_device(dev); | ||
| 744 | return sprintf(buf, "%ld\n", | ||
| 745 | (long)BEEP_MASK_FROM_REG(data->beep_mask)); | ||
| 746 | } | ||
| 728 | 747 | ||
| 729 | static ssize_t | 748 | static ssize_t |
| 730 | store_beep_reg(struct device *dev, const char *buf, size_t count, | 749 | store_beep_mask(struct device *dev, struct device_attribute *attr, |
| 731 | int update_mask) | 750 | const char *buf, size_t count) |
| 732 | { | 751 | { |
| 733 | struct w83627hf_data *data = dev_get_drvdata(dev); | 752 | struct w83627hf_data *data = dev_get_drvdata(dev); |
| 734 | u32 val, val2; | 753 | unsigned long val; |
| 735 | 754 | ||
| 736 | val = simple_strtoul(buf, NULL, 10); | 755 | val = simple_strtoul(buf, NULL, 10); |
| 737 | 756 | ||
| 738 | mutex_lock(&data->update_lock); | 757 | mutex_lock(&data->update_lock); |
| 739 | 758 | ||
| 740 | if (update_mask == BEEP_MASK) { /* We are storing beep_mask */ | 759 | /* preserve beep enable */ |
| 741 | data->beep_mask = BEEP_MASK_TO_REG(val); | 760 | data->beep_mask = (data->beep_mask & 0x8000) |
| 742 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS1, | 761 | | BEEP_MASK_TO_REG(val); |
| 743 | data->beep_mask & 0xff); | 762 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS1, |
| 744 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS3, | 763 | data->beep_mask & 0xff); |
| 745 | ((data->beep_mask) >> 16) & 0xff); | 764 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS3, |
| 746 | val2 = (data->beep_mask >> 8) & 0x7f; | 765 | ((data->beep_mask) >> 16) & 0xff); |
| 747 | } else { /* We are storing beep_enable */ | ||
| 748 | val2 = | ||
| 749 | w83627hf_read_value(data, W83781D_REG_BEEP_INTS2) & 0x7f; | ||
| 750 | data->beep_enable = BEEP_ENABLE_TO_REG(val); | ||
| 751 | } | ||
| 752 | |||
| 753 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS2, | 766 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS2, |
| 754 | val2 | data->beep_enable << 7); | 767 | (data->beep_mask >> 8) & 0xff); |
| 755 | 768 | ||
| 756 | mutex_unlock(&data->update_lock); | 769 | mutex_unlock(&data->update_lock); |
| 757 | return count; | 770 | return count; |
| 758 | } | 771 | } |
| 759 | 772 | ||
| 760 | #define sysfs_beep(REG, reg) \ | 773 | static DEVICE_ATTR(beep_mask, S_IRUGO | S_IWUSR, |
| 761 | static ssize_t show_regs_beep_##reg (struct device *dev, struct device_attribute *attr, char *buf) \ | 774 | show_beep_mask, store_beep_mask); |
| 762 | { \ | 775 | |
| 763 | return show_beep_##reg(dev, attr, buf); \ | 776 | static ssize_t |
| 764 | } \ | 777 | show_beep(struct device *dev, struct device_attribute *attr, char *buf) |
| 765 | static ssize_t \ | 778 | { |
| 766 | store_regs_beep_##reg (struct device *dev, struct device_attribute *attr, const char *buf, size_t count) \ | 779 | struct w83627hf_data *data = w83627hf_update_device(dev); |
| 767 | { \ | 780 | int bitnr = to_sensor_dev_attr(attr)->index; |
| 768 | return store_beep_reg(dev, buf, count, BEEP_##REG); \ | 781 | return sprintf(buf, "%u\n", (data->beep_mask >> bitnr) & 1); |
| 769 | } \ | 782 | } |
| 770 | static DEVICE_ATTR(beep_##reg, S_IRUGO | S_IWUSR, \ | 783 | |
| 771 | show_regs_beep_##reg, store_regs_beep_##reg); | 784 | static ssize_t |
| 785 | store_beep(struct device *dev, struct device_attribute *attr, | ||
| 786 | const char *buf, size_t count) | ||
| 787 | { | ||
| 788 | struct w83627hf_data *data = dev_get_drvdata(dev); | ||
| 789 | int bitnr = to_sensor_dev_attr(attr)->index; | ||
| 790 | unsigned long bit; | ||
| 791 | u8 reg; | ||
| 792 | |||
| 793 | bit = simple_strtoul(buf, NULL, 10); | ||
| 794 | if (bit & ~1) | ||
| 795 | return -EINVAL; | ||
| 796 | |||
| 797 | mutex_lock(&data->update_lock); | ||
| 798 | if (bit) | ||
| 799 | data->beep_mask |= (1 << bitnr); | ||
| 800 | else | ||
| 801 | data->beep_mask &= ~(1 << bitnr); | ||
| 802 | |||
| 803 | if (bitnr < 8) { | ||
| 804 | reg = w83627hf_read_value(data, W83781D_REG_BEEP_INTS1); | ||
| 805 | if (bit) | ||
| 806 | reg |= (1 << bitnr); | ||
| 807 | else | ||
| 808 | reg &= ~(1 << bitnr); | ||
| 809 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS1, reg); | ||
| 810 | } else if (bitnr < 16) { | ||
| 811 | reg = w83627hf_read_value(data, W83781D_REG_BEEP_INTS2); | ||
| 812 | if (bit) | ||
| 813 | reg |= (1 << (bitnr - 8)); | ||
| 814 | else | ||
| 815 | reg &= ~(1 << (bitnr - 8)); | ||
| 816 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS2, reg); | ||
| 817 | } else { | ||
| 818 | reg = w83627hf_read_value(data, W83781D_REG_BEEP_INTS3); | ||
| 819 | if (bit) | ||
| 820 | reg |= (1 << (bitnr - 16)); | ||
| 821 | else | ||
| 822 | reg &= ~(1 << (bitnr - 16)); | ||
| 823 | w83627hf_write_value(data, W83781D_REG_BEEP_INTS3, reg); | ||
| 824 | } | ||
| 825 | mutex_unlock(&data->update_lock); | ||
| 826 | |||
| 827 | return count; | ||
| 828 | } | ||
| 772 | 829 | ||
| 773 | sysfs_beep(ENABLE, enable); | 830 | static SENSOR_DEVICE_ATTR(in0_beep, S_IRUGO | S_IWUSR, |
| 774 | sysfs_beep(MASK, mask); | 831 | show_beep, store_beep, 0); |
| 832 | static SENSOR_DEVICE_ATTR(in1_beep, S_IRUGO | S_IWUSR, | ||
| 833 | show_beep, store_beep, 1); | ||
| 834 | static SENSOR_DEVICE_ATTR(in2_beep, S_IRUGO | S_IWUSR, | ||
| 835 | show_beep, store_beep, 2); | ||
| 836 | static SENSOR_DEVICE_ATTR(in3_beep, S_IRUGO | S_IWUSR, | ||
| 837 | show_beep, store_beep, 3); | ||
| 838 | static SENSOR_DEVICE_ATTR(in4_beep, S_IRUGO | S_IWUSR, | ||
| 839 | show_beep, store_beep, 8); | ||
| 840 | static SENSOR_DEVICE_ATTR(in5_beep, S_IRUGO | S_IWUSR, | ||
| 841 | show_beep, store_beep, 9); | ||
| 842 | static SENSOR_DEVICE_ATTR(in6_beep, S_IRUGO | S_IWUSR, | ||
| 843 | show_beep, store_beep, 10); | ||
| 844 | static SENSOR_DEVICE_ATTR(in7_beep, S_IRUGO | S_IWUSR, | ||
| 845 | show_beep, store_beep, 16); | ||
| 846 | static SENSOR_DEVICE_ATTR(in8_beep, S_IRUGO | S_IWUSR, | ||
| 847 | show_beep, store_beep, 17); | ||
| 848 | static SENSOR_DEVICE_ATTR(fan1_beep, S_IRUGO | S_IWUSR, | ||
| 849 | show_beep, store_beep, 6); | ||
| 850 | static SENSOR_DEVICE_ATTR(fan2_beep, S_IRUGO | S_IWUSR, | ||
| 851 | show_beep, store_beep, 7); | ||
| 852 | static SENSOR_DEVICE_ATTR(fan3_beep, S_IRUGO | S_IWUSR, | ||
| 853 | show_beep, store_beep, 11); | ||
| 854 | static SENSOR_DEVICE_ATTR(temp1_beep, S_IRUGO | S_IWUSR, | ||
| 855 | show_beep, store_beep, 4); | ||
| 856 | static SENSOR_DEVICE_ATTR(temp2_beep, S_IRUGO | S_IWUSR, | ||
| 857 | show_beep, store_beep, 5); | ||
| 858 | static SENSOR_DEVICE_ATTR(temp3_beep, S_IRUGO | S_IWUSR, | ||
| 859 | show_beep, store_beep, 13); | ||
| 860 | static SENSOR_DEVICE_ATTR(beep_enable, S_IRUGO | S_IWUSR, | ||
| 861 | show_beep, store_beep, 15); | ||
| 775 | 862 | ||
| 776 | static ssize_t | 863 | static ssize_t |
| 777 | show_fan_div(struct device *dev, struct device_attribute *devattr, char *buf) | 864 | show_fan_div(struct device *dev, struct device_attribute *devattr, char *buf) |
| @@ -1014,7 +1101,7 @@ static int __init w83627hf_find(int sioaddr, unsigned short *addr, | |||
| 1014 | VAL = sioaddr + 1; | 1101 | VAL = sioaddr + 1; |
| 1015 | 1102 | ||
| 1016 | superio_enter(); | 1103 | superio_enter(); |
| 1017 | val= superio_inb(DEVID); | 1104 | val = force_id ? force_id : superio_inb(DEVID); |
| 1018 | switch (val) { | 1105 | switch (val) { |
| 1019 | case W627_DEVID: | 1106 | case W627_DEVID: |
| 1020 | sio_data->type = w83627hf; | 1107 | sio_data->type = w83627hf; |
| @@ -1073,23 +1160,31 @@ static int __init w83627hf_find(int sioaddr, unsigned short *addr, | |||
| 1073 | #define VIN_UNIT_ATTRS(_X_) \ | 1160 | #define VIN_UNIT_ATTRS(_X_) \ |
| 1074 | &sensor_dev_attr_in##_X_##_input.dev_attr.attr, \ | 1161 | &sensor_dev_attr_in##_X_##_input.dev_attr.attr, \ |
| 1075 | &sensor_dev_attr_in##_X_##_min.dev_attr.attr, \ | 1162 | &sensor_dev_attr_in##_X_##_min.dev_attr.attr, \ |
| 1076 | &sensor_dev_attr_in##_X_##_max.dev_attr.attr | 1163 | &sensor_dev_attr_in##_X_##_max.dev_attr.attr, \ |
| 1164 | &sensor_dev_attr_in##_X_##_alarm.dev_attr.attr, \ | ||
| 1165 | &sensor_dev_attr_in##_X_##_beep.dev_attr.attr | ||
| 1077 | 1166 | ||
| 1078 | #define FAN_UNIT_ATTRS(_X_) \ | 1167 | #define FAN_UNIT_ATTRS(_X_) \ |
| 1079 | &sensor_dev_attr_fan##_X_##_input.dev_attr.attr, \ | 1168 | &sensor_dev_attr_fan##_X_##_input.dev_attr.attr, \ |
| 1080 | &sensor_dev_attr_fan##_X_##_min.dev_attr.attr, \ | 1169 | &sensor_dev_attr_fan##_X_##_min.dev_attr.attr, \ |
| 1081 | &sensor_dev_attr_fan##_X_##_div.dev_attr.attr | 1170 | &sensor_dev_attr_fan##_X_##_div.dev_attr.attr, \ |
| 1171 | &sensor_dev_attr_fan##_X_##_alarm.dev_attr.attr, \ | ||
| 1172 | &sensor_dev_attr_fan##_X_##_beep.dev_attr.attr | ||
| 1082 | 1173 | ||
| 1083 | #define TEMP_UNIT_ATTRS(_X_) \ | 1174 | #define TEMP_UNIT_ATTRS(_X_) \ |
| 1084 | &sensor_dev_attr_temp##_X_##_input.dev_attr.attr, \ | 1175 | &sensor_dev_attr_temp##_X_##_input.dev_attr.attr, \ |
| 1085 | &sensor_dev_attr_temp##_X_##_max.dev_attr.attr, \ | 1176 | &sensor_dev_attr_temp##_X_##_max.dev_attr.attr, \ |
| 1086 | &sensor_dev_attr_temp##_X_##_max_hyst.dev_attr.attr, \ | 1177 | &sensor_dev_attr_temp##_X_##_max_hyst.dev_attr.attr, \ |
| 1087 | &sensor_dev_attr_temp##_X_##_type.dev_attr.attr | 1178 | &sensor_dev_attr_temp##_X_##_type.dev_attr.attr, \ |
| 1179 | &sensor_dev_attr_temp##_X_##_alarm.dev_attr.attr, \ | ||
| 1180 | &sensor_dev_attr_temp##_X_##_beep.dev_attr.attr | ||
| 1088 | 1181 | ||
| 1089 | static struct attribute *w83627hf_attributes[] = { | 1182 | static struct attribute *w83627hf_attributes[] = { |
| 1090 | &dev_attr_in0_input.attr, | 1183 | &dev_attr_in0_input.attr, |
| 1091 | &dev_attr_in0_min.attr, | 1184 | &dev_attr_in0_min.attr, |
| 1092 | &dev_attr_in0_max.attr, | 1185 | &dev_attr_in0_max.attr, |
| 1186 | &sensor_dev_attr_in0_alarm.dev_attr.attr, | ||
| 1187 | &sensor_dev_attr_in0_beep.dev_attr.attr, | ||
| 1093 | VIN_UNIT_ATTRS(2), | 1188 | VIN_UNIT_ATTRS(2), |
| 1094 | VIN_UNIT_ATTRS(3), | 1189 | VIN_UNIT_ATTRS(3), |
| 1095 | VIN_UNIT_ATTRS(4), | 1190 | VIN_UNIT_ATTRS(4), |
| @@ -1103,7 +1198,7 @@ static struct attribute *w83627hf_attributes[] = { | |||
| 1103 | TEMP_UNIT_ATTRS(2), | 1198 | TEMP_UNIT_ATTRS(2), |
| 1104 | 1199 | ||
| 1105 | &dev_attr_alarms.attr, | 1200 | &dev_attr_alarms.attr, |
| 1106 | &dev_attr_beep_enable.attr, | 1201 | &sensor_dev_attr_beep_enable.dev_attr.attr, |
| 1107 | &dev_attr_beep_mask.attr, | 1202 | &dev_attr_beep_mask.attr, |
| 1108 | 1203 | ||
| 1109 | &sensor_dev_attr_pwm1.dev_attr.attr, | 1204 | &sensor_dev_attr_pwm1.dev_attr.attr, |
| @@ -1193,12 +1288,20 @@ static int __devinit w83627hf_probe(struct platform_device *pdev) | |||
| 1193 | || (err = device_create_file(dev, | 1288 | || (err = device_create_file(dev, |
| 1194 | &sensor_dev_attr_in5_max.dev_attr)) | 1289 | &sensor_dev_attr_in5_max.dev_attr)) |
| 1195 | || (err = device_create_file(dev, | 1290 | || (err = device_create_file(dev, |
| 1291 | &sensor_dev_attr_in5_alarm.dev_attr)) | ||
| 1292 | || (err = device_create_file(dev, | ||
| 1293 | &sensor_dev_attr_in5_beep.dev_attr)) | ||
| 1294 | || (err = device_create_file(dev, | ||
| 1196 | &sensor_dev_attr_in6_input.dev_attr)) | 1295 | &sensor_dev_attr_in6_input.dev_attr)) |
| 1197 | || (err = device_create_file(dev, | 1296 | || (err = device_create_file(dev, |
| 1198 | &sensor_dev_attr_in6_min.dev_attr)) | 1297 | &sensor_dev_attr_in6_min.dev_attr)) |
| 1199 | || (err = device_create_file(dev, | 1298 | || (err = device_create_file(dev, |
| 1200 | &sensor_dev_attr_in6_max.dev_attr)) | 1299 | &sensor_dev_attr_in6_max.dev_attr)) |
| 1201 | || (err = device_create_file(dev, | 1300 | || (err = device_create_file(dev, |
| 1301 | &sensor_dev_attr_in6_alarm.dev_attr)) | ||
| 1302 | || (err = device_create_file(dev, | ||
| 1303 | &sensor_dev_attr_in6_beep.dev_attr)) | ||
| 1304 | || (err = device_create_file(dev, | ||
| 1202 | &sensor_dev_attr_pwm1_freq.dev_attr)) | 1305 | &sensor_dev_attr_pwm1_freq.dev_attr)) |
| 1203 | || (err = device_create_file(dev, | 1306 | || (err = device_create_file(dev, |
| 1204 | &sensor_dev_attr_pwm2_freq.dev_attr))) | 1307 | &sensor_dev_attr_pwm2_freq.dev_attr))) |
| @@ -1212,18 +1315,30 @@ static int __devinit w83627hf_probe(struct platform_device *pdev) | |||
| 1212 | || (err = device_create_file(dev, | 1315 | || (err = device_create_file(dev, |
| 1213 | &sensor_dev_attr_in1_max.dev_attr)) | 1316 | &sensor_dev_attr_in1_max.dev_attr)) |
| 1214 | || (err = device_create_file(dev, | 1317 | || (err = device_create_file(dev, |
| 1318 | &sensor_dev_attr_in1_alarm.dev_attr)) | ||
| 1319 | || (err = device_create_file(dev, | ||
| 1320 | &sensor_dev_attr_in1_beep.dev_attr)) | ||
| 1321 | || (err = device_create_file(dev, | ||
| 1215 | &sensor_dev_attr_fan3_input.dev_attr)) | 1322 | &sensor_dev_attr_fan3_input.dev_attr)) |
| 1216 | || (err = device_create_file(dev, | 1323 | || (err = device_create_file(dev, |
| 1217 | &sensor_dev_attr_fan3_min.dev_attr)) | 1324 | &sensor_dev_attr_fan3_min.dev_attr)) |
| 1218 | || (err = device_create_file(dev, | 1325 | || (err = device_create_file(dev, |
| 1219 | &sensor_dev_attr_fan3_div.dev_attr)) | 1326 | &sensor_dev_attr_fan3_div.dev_attr)) |
| 1220 | || (err = device_create_file(dev, | 1327 | || (err = device_create_file(dev, |
| 1328 | &sensor_dev_attr_fan3_alarm.dev_attr)) | ||
| 1329 | || (err = device_create_file(dev, | ||
| 1330 | &sensor_dev_attr_fan3_beep.dev_attr)) | ||
| 1331 | || (err = device_create_file(dev, | ||
| 1221 | &sensor_dev_attr_temp3_input.dev_attr)) | 1332 | &sensor_dev_attr_temp3_input.dev_attr)) |
| 1222 | || (err = device_create_file(dev, | 1333 | || (err = device_create_file(dev, |
| 1223 | &sensor_dev_attr_temp3_max.dev_attr)) | 1334 | &sensor_dev_attr_temp3_max.dev_attr)) |
| 1224 | || (err = device_create_file(dev, | 1335 | || (err = device_create_file(dev, |
| 1225 | &sensor_dev_attr_temp3_max_hyst.dev_attr)) | 1336 | &sensor_dev_attr_temp3_max_hyst.dev_attr)) |
| 1226 | || (err = device_create_file(dev, | 1337 | || (err = device_create_file(dev, |
| 1338 | &sensor_dev_attr_temp3_alarm.dev_attr)) | ||
| 1339 | || (err = device_create_file(dev, | ||
| 1340 | &sensor_dev_attr_temp3_beep.dev_attr)) | ||
| 1341 | || (err = device_create_file(dev, | ||
| 1227 | &sensor_dev_attr_temp3_type.dev_attr))) | 1342 | &sensor_dev_attr_temp3_type.dev_attr))) |
| 1228 | goto ERROR4; | 1343 | goto ERROR4; |
| 1229 | 1344 | ||
| @@ -1511,6 +1626,11 @@ static void __devinit w83627hf_init_device(struct platform_device *pdev) | |||
| 1511 | (w83627hf_read_value(data, | 1626 | (w83627hf_read_value(data, |
| 1512 | W83781D_REG_CONFIG) & 0xf7) | 1627 | W83781D_REG_CONFIG) & 0xf7) |
| 1513 | | 0x01); | 1628 | | 0x01); |
| 1629 | |||
| 1630 | /* Enable VBAT monitoring if needed */ | ||
| 1631 | tmp = w83627hf_read_value(data, W83781D_REG_VBAT); | ||
| 1632 | if (!(tmp & 0x01)) | ||
| 1633 | w83627hf_write_value(data, W83781D_REG_VBAT, tmp | 0x01); | ||
| 1514 | } | 1634 | } |
| 1515 | 1635 | ||
| 1516 | static void w83627hf_update_fan_div(struct w83627hf_data *data) | 1636 | static void w83627hf_update_fan_div(struct w83627hf_data *data) |
| @@ -1603,8 +1723,7 @@ static struct w83627hf_data *w83627hf_update_device(struct device *dev) | |||
| 1603 | (w83627hf_read_value(data, W83781D_REG_ALARM2) << 8) | | 1723 | (w83627hf_read_value(data, W83781D_REG_ALARM2) << 8) | |
| 1604 | (w83627hf_read_value(data, W83781D_REG_ALARM3) << 16); | 1724 | (w83627hf_read_value(data, W83781D_REG_ALARM3) << 16); |
| 1605 | i = w83627hf_read_value(data, W83781D_REG_BEEP_INTS2); | 1725 | i = w83627hf_read_value(data, W83781D_REG_BEEP_INTS2); |
| 1606 | data->beep_enable = i >> 7; | 1726 | data->beep_mask = (i << 8) | |
| 1607 | data->beep_mask = ((i & 0x7f) << 8) | | ||
| 1608 | w83627hf_read_value(data, W83781D_REG_BEEP_INTS1) | | 1727 | w83627hf_read_value(data, W83781D_REG_BEEP_INTS1) | |
| 1609 | w83627hf_read_value(data, W83781D_REG_BEEP_INTS3) << 16; | 1728 | w83627hf_read_value(data, W83781D_REG_BEEP_INTS3) << 16; |
| 1610 | data->last_updated = jiffies; | 1729 | data->last_updated = jiffies; |
diff --git a/drivers/hwmon/w83781d.c b/drivers/hwmon/w83781d.c index e0fa7520400d..7421f6ea53e1 100644 --- a/drivers/hwmon/w83781d.c +++ b/drivers/hwmon/w83781d.c | |||
| @@ -28,7 +28,6 @@ | |||
| 28 | as99127f 7 3 0 3 0x31 0x12c3 yes no | 28 | as99127f 7 3 0 3 0x31 0x12c3 yes no |
| 29 | as99127f rev.2 (type_name = as99127f) 0x31 0x5ca3 yes no | 29 | as99127f rev.2 (type_name = as99127f) 0x31 0x5ca3 yes no |
| 30 | w83781d 7 3 0 3 0x10-1 0x5ca3 yes yes | 30 | w83781d 7 3 0 3 0x10-1 0x5ca3 yes yes |
| 31 | w83627hf 9 3 2 3 0x21 0x5ca3 yes yes(LPC) | ||
| 32 | w83782d 9 3 2-4 3 0x30 0x5ca3 yes yes | 31 | w83782d 9 3 2-4 3 0x30 0x5ca3 yes yes |
| 33 | w83783s 5-6 3 2 1-2 0x40 0x5ca3 yes no | 32 | w83783s 5-6 3 2 1-2 0x40 0x5ca3 yes no |
| 34 | 33 | ||
| @@ -54,13 +53,12 @@ | |||
| 54 | static struct platform_device *pdev; | 53 | static struct platform_device *pdev; |
| 55 | 54 | ||
| 56 | /* Addresses to scan */ | 55 | /* Addresses to scan */ |
| 57 | static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, | 56 | static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, |
| 58 | 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, | 57 | 0x2e, 0x2f, I2C_CLIENT_END }; |
| 59 | 0x2c, 0x2d, 0x2e, 0x2f, I2C_CLIENT_END }; | ||
| 60 | static unsigned short isa_address = 0x290; | 58 | static unsigned short isa_address = 0x290; |
| 61 | 59 | ||
| 62 | /* Insmod parameters */ | 60 | /* Insmod parameters */ |
| 63 | I2C_CLIENT_INSMOD_5(w83781d, w83782d, w83783s, w83627hf, as99127f); | 61 | I2C_CLIENT_INSMOD_4(w83781d, w83782d, w83783s, as99127f); |
| 64 | I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: " | 62 | I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: " |
| 65 | "{bus, clientaddr, subclientaddr1, subclientaddr2}"); | 63 | "{bus, clientaddr, subclientaddr1, subclientaddr2}"); |
| 66 | 64 | ||
| @@ -114,7 +112,7 @@ MODULE_PARM_DESC(init, "Set to zero to bypass chip initialization"); | |||
| 114 | #define W83781D_REG_ALARM1 0x41 | 112 | #define W83781D_REG_ALARM1 0x41 |
| 115 | #define W83781D_REG_ALARM2 0x42 | 113 | #define W83781D_REG_ALARM2 0x42 |
| 116 | 114 | ||
| 117 | /* Real-time status (W83782D, W83783S, W83627HF) */ | 115 | /* Real-time status (W83782D, W83783S) */ |
| 118 | #define W83782D_REG_ALARM1 0x459 | 116 | #define W83782D_REG_ALARM1 0x459 |
| 119 | #define W83782D_REG_ALARM2 0x45A | 117 | #define W83782D_REG_ALARM2 0x45A |
| 120 | #define W83782D_REG_ALARM3 0x45B | 118 | #define W83782D_REG_ALARM3 0x45B |
| @@ -153,10 +151,6 @@ static const u8 BIT_SCFG2[] = { 0x10, 0x20, 0x40 }; | |||
| 153 | 151 | ||
| 154 | #define W83781D_DEFAULT_BETA 3435 | 152 | #define W83781D_DEFAULT_BETA 3435 |
| 155 | 153 | ||
| 156 | /* RT Table registers */ | ||
| 157 | #define W83781D_REG_RT_IDX 0x50 | ||
| 158 | #define W83781D_REG_RT_VAL 0x51 | ||
| 159 | |||
| 160 | /* Conversions */ | 154 | /* Conversions */ |
| 161 | #define IN_TO_REG(val) SENSORS_LIMIT(((val) + 8) / 16, 0, 255) | 155 | #define IN_TO_REG(val) SENSORS_LIMIT(((val) + 8) / 16, 0, 255) |
| 162 | #define IN_FROM_REG(val) ((val) * 16) | 156 | #define IN_FROM_REG(val) ((val) * 16) |
| @@ -271,7 +265,6 @@ static struct i2c_driver w83781d_driver = { | |||
| 271 | .driver = { | 265 | .driver = { |
| 272 | .name = "w83781d", | 266 | .name = "w83781d", |
| 273 | }, | 267 | }, |
| 274 | .id = I2C_DRIVERID_W83781D, | ||
| 275 | .attach_adapter = w83781d_attach_adapter, | 268 | .attach_adapter = w83781d_attach_adapter, |
| 276 | .detach_client = w83781d_detach_client, | 269 | .detach_client = w83781d_detach_client, |
| 277 | }; | 270 | }; |
| @@ -696,7 +689,7 @@ store_fan_div(struct device *dev, struct device_attribute *da, | |||
| 696 | unsigned long val = simple_strtoul(buf, NULL, 10); | 689 | unsigned long val = simple_strtoul(buf, NULL, 10); |
| 697 | 690 | ||
| 698 | mutex_lock(&data->update_lock); | 691 | mutex_lock(&data->update_lock); |
| 699 | 692 | ||
| 700 | /* Save fan_min */ | 693 | /* Save fan_min */ |
| 701 | min = FAN_FROM_REG(data->fan_min[nr], | 694 | min = FAN_FROM_REG(data->fan_min[nr], |
| 702 | DIV_FROM_REG(data->fan_div[nr])); | 695 | DIV_FROM_REG(data->fan_div[nr])); |
| @@ -963,8 +956,6 @@ w83781d_detect_subclients(struct i2c_adapter *adapter, int address, int kind, | |||
| 963 | client_name = "w83782d subclient"; | 956 | client_name = "w83782d subclient"; |
| 964 | else if (kind == w83783s) | 957 | else if (kind == w83783s) |
| 965 | client_name = "w83783s subclient"; | 958 | client_name = "w83783s subclient"; |
| 966 | else if (kind == w83627hf) | ||
| 967 | client_name = "w83627hf subclient"; | ||
| 968 | else if (kind == as99127f) | 959 | else if (kind == as99127f) |
| 969 | client_name = "as99127f subclient"; | 960 | client_name = "as99127f subclient"; |
| 970 | 961 | ||
| @@ -1004,7 +995,7 @@ ERROR_SC_0: | |||
| 1004 | #define IN_UNIT_ATTRS(X) \ | 995 | #define IN_UNIT_ATTRS(X) \ |
| 1005 | &sensor_dev_attr_in##X##_input.dev_attr.attr, \ | 996 | &sensor_dev_attr_in##X##_input.dev_attr.attr, \ |
| 1006 | &sensor_dev_attr_in##X##_min.dev_attr.attr, \ | 997 | &sensor_dev_attr_in##X##_min.dev_attr.attr, \ |
| 1007 | &sensor_dev_attr_in##X##_max.dev_attr.attr, \ | 998 | &sensor_dev_attr_in##X##_max.dev_attr.attr, \ |
| 1008 | &sensor_dev_attr_in##X##_alarm.dev_attr.attr, \ | 999 | &sensor_dev_attr_in##X##_alarm.dev_attr.attr, \ |
| 1009 | &sensor_dev_attr_in##X##_beep.dev_attr.attr | 1000 | &sensor_dev_attr_in##X##_beep.dev_attr.attr |
| 1010 | 1001 | ||
| @@ -1268,9 +1259,7 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 1268 | kind = w83782d; | 1259 | kind = w83782d; |
| 1269 | else if (val1 == 0x40 && vendid == winbond && address == 0x2d) | 1260 | else if (val1 == 0x40 && vendid == winbond && address == 0x2d) |
| 1270 | kind = w83783s; | 1261 | kind = w83783s; |
| 1271 | else if (val1 == 0x21 && vendid == winbond) | 1262 | else if (val1 == 0x31) |
| 1272 | kind = w83627hf; | ||
| 1273 | else if (val1 == 0x31 && address >= 0x28) | ||
| 1274 | kind = as99127f; | 1263 | kind = as99127f; |
| 1275 | else { | 1264 | else { |
| 1276 | if (kind == 0) | 1265 | if (kind == 0) |
| @@ -1288,8 +1277,6 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind) | |||
| 1288 | client_name = "w83782d"; | 1277 | client_name = "w83782d"; |
| 1289 | } else if (kind == w83783s) { | 1278 | } else if (kind == w83783s) { |
| 1290 | client_name = "w83783s"; | 1279 | client_name = "w83783s"; |
| 1291 | } else if (kind == w83627hf) { | ||
| 1292 | client_name = "w83627hf"; | ||
| 1293 | } else if (kind == as99127f) { | 1280 | } else if (kind == as99127f) { |
| 1294 | client_name = "as99127f"; | 1281 | client_name = "as99127f"; |
| 1295 | } | 1282 | } |
| @@ -1396,10 +1383,6 @@ w83781d_isa_probe(struct platform_device *pdev) | |||
| 1396 | 1383 | ||
| 1397 | reg = w83781d_read_value(data, W83781D_REG_WCHIPID); | 1384 | reg = w83781d_read_value(data, W83781D_REG_WCHIPID); |
| 1398 | switch (reg) { | 1385 | switch (reg) { |
| 1399 | case 0x21: | ||
| 1400 | data->type = w83627hf; | ||
| 1401 | name = "w83627hf"; | ||
| 1402 | break; | ||
| 1403 | case 0x30: | 1386 | case 0x30: |
| 1404 | data->type = w83782d; | 1387 | data->type = w83782d; |
| 1405 | name = "w83782d"; | 1388 | name = "w83782d"; |
| @@ -1453,9 +1436,9 @@ w83781d_isa_remove(struct platform_device *pdev) | |||
| 1453 | } | 1436 | } |
| 1454 | 1437 | ||
| 1455 | /* The SMBus locks itself, usually, but nothing may access the Winbond between | 1438 | /* The SMBus locks itself, usually, but nothing may access the Winbond between |
| 1456 | bank switches. ISA access must always be locked explicitly! | 1439 | bank switches. ISA access must always be locked explicitly! |
| 1457 | We ignore the W83781D BUSY flag at this moment - it could lead to deadlocks, | 1440 | We ignore the W83781D BUSY flag at this moment - it could lead to deadlocks, |
| 1458 | would slow down the W83781D access and should not be necessary. | 1441 | would slow down the W83781D access and should not be necessary. |
| 1459 | There are some ugly typecasts here, but the good news is - they should | 1442 | There are some ugly typecasts here, but the good news is - they should |
| 1460 | nowhere else be necessary! */ | 1443 | nowhere else be necessary! */ |
| 1461 | static int | 1444 | static int |
| @@ -1599,11 +1582,6 @@ w83781d_init_device(struct device *dev) | |||
| 1599 | int type = data->type; | 1582 | int type = data->type; |
| 1600 | u8 tmp; | 1583 | u8 tmp; |
| 1601 | 1584 | ||
| 1602 | if (type == w83627hf) | ||
| 1603 | dev_info(dev, "The W83627HF chip is better supported by the " | ||
| 1604 | "w83627hf driver, support will be dropped from the " | ||
| 1605 | "w83781d driver soon\n"); | ||
| 1606 | |||
| 1607 | if (reset && type != as99127f) { /* this resets registers we don't have | 1585 | if (reset && type != as99127f) { /* this resets registers we don't have |
| 1608 | documentation for on the as99127f */ | 1586 | documentation for on the as99127f */ |
| 1609 | /* Resetting the chip has been the default for a long time, | 1587 | /* Resetting the chip has been the default for a long time, |
| @@ -1717,8 +1695,7 @@ static struct w83781d_data *w83781d_update_device(struct device *dev) | |||
| 1717 | w83781d_read_value(data, W83781D_REG_IN_MIN(i)); | 1695 | w83781d_read_value(data, W83781D_REG_IN_MIN(i)); |
| 1718 | data->in_max[i] = | 1696 | data->in_max[i] = |
| 1719 | w83781d_read_value(data, W83781D_REG_IN_MAX(i)); | 1697 | w83781d_read_value(data, W83781D_REG_IN_MAX(i)); |
| 1720 | if ((data->type != w83782d) | 1698 | if ((data->type != w83782d) && (i == 6)) |
| 1721 | && (data->type != w83627hf) && (i == 6)) | ||
| 1722 | break; | 1699 | break; |
| 1723 | } | 1700 | } |
| 1724 | for (i = 0; i < 3; i++) { | 1701 | for (i = 0; i < 3; i++) { |
| @@ -1776,7 +1753,7 @@ static struct w83781d_data *w83781d_update_device(struct device *dev) | |||
| 1776 | data->fan_div[1] |= (i >> 4) & 0x04; | 1753 | data->fan_div[1] |= (i >> 4) & 0x04; |
| 1777 | data->fan_div[2] |= (i >> 5) & 0x04; | 1754 | data->fan_div[2] |= (i >> 5) & 0x04; |
| 1778 | } | 1755 | } |
| 1779 | if ((data->type == w83782d) || (data->type == w83627hf)) { | 1756 | if (data->type == w83782d) { |
| 1780 | data->alarms = w83781d_read_value(data, | 1757 | data->alarms = w83781d_read_value(data, |
| 1781 | W83782D_REG_ALARM1) | 1758 | W83782D_REG_ALARM1) |
| 1782 | | (w83781d_read_value(data, | 1759 | | (w83781d_read_value(data, |
| @@ -1886,13 +1863,11 @@ w83781d_isa_found(unsigned short address) | |||
| 1886 | outb_p(W83781D_REG_WCHIPID, address + W83781D_ADDR_REG_OFFSET); | 1863 | outb_p(W83781D_REG_WCHIPID, address + W83781D_ADDR_REG_OFFSET); |
| 1887 | val = inb_p(address + W83781D_DATA_REG_OFFSET); | 1864 | val = inb_p(address + W83781D_DATA_REG_OFFSET); |
| 1888 | if ((val & 0xfe) == 0x10 /* W83781D */ | 1865 | if ((val & 0xfe) == 0x10 /* W83781D */ |
| 1889 | || val == 0x30 /* W83782D */ | 1866 | || val == 0x30) /* W83782D */ |
| 1890 | || val == 0x21) /* W83627HF */ | ||
| 1891 | found = 1; | 1867 | found = 1; |
| 1892 | 1868 | ||
| 1893 | if (found) | 1869 | if (found) |
| 1894 | pr_info("w83781d: Found a %s chip at %#x\n", | 1870 | pr_info("w83781d: Found a %s chip at %#x\n", |
| 1895 | val == 0x21 ? "W83627HF" : | ||
| 1896 | val == 0x30 ? "W83782D" : "W83781D", (int)address); | 1871 | val == 0x30 ? "W83782D" : "W83781D", (int)address); |
| 1897 | 1872 | ||
| 1898 | release: | 1873 | release: |
diff --git a/drivers/hwmon/w83791d.c b/drivers/hwmon/w83791d.c index a9c01a6f0057..85bd21ee3298 100644 --- a/drivers/hwmon/w83791d.c +++ b/drivers/hwmon/w83791d.c | |||
| @@ -840,14 +840,12 @@ static ssize_t store_vrm_reg(struct device *dev, | |||
| 840 | struct device_attribute *attr, | 840 | struct device_attribute *attr, |
| 841 | const char *buf, size_t count) | 841 | const char *buf, size_t count) |
| 842 | { | 842 | { |
| 843 | struct i2c_client *client = to_i2c_client(dev); | 843 | struct w83791d_data *data = dev_get_drvdata(dev); |
| 844 | struct w83791d_data *data = i2c_get_clientdata(client); | ||
| 845 | unsigned long val = simple_strtoul(buf, NULL, 10); | ||
| 846 | 844 | ||
| 847 | /* No lock needed as vrm is internal to the driver | 845 | /* No lock needed as vrm is internal to the driver |
| 848 | (not read from a chip register) and so is not | 846 | (not read from a chip register) and so is not |
| 849 | updated in w83791d_update_device() */ | 847 | updated in w83791d_update_device() */ |
| 850 | data->vrm = val; | 848 | data->vrm = simple_strtoul(buf, NULL, 10); |
| 851 | 849 | ||
| 852 | return count; | 850 | return count; |
| 853 | } | 851 | } |
diff --git a/drivers/hwmon/w83793.c b/drivers/hwmon/w83793.c index 48599e1cc554..3ba1d6b33473 100644 --- a/drivers/hwmon/w83793.c +++ b/drivers/hwmon/w83793.c | |||
| @@ -131,6 +131,7 @@ static u8 scale_in_add[] = { 0, 0, 0, 0, 0, 0, 0, 150, 150, 0 }; | |||
| 131 | #define PWM_DUTY 0 | 131 | #define PWM_DUTY 0 |
| 132 | #define PWM_START 1 | 132 | #define PWM_START 1 |
| 133 | #define PWM_NONSTOP 2 | 133 | #define PWM_NONSTOP 2 |
| 134 | #define PWM_STOP_TIME 3 | ||
| 134 | #define W83793_REG_PWM(index, nr) (((nr) == 0 ? 0xb3 : \ | 135 | #define W83793_REG_PWM(index, nr) (((nr) == 0 ? 0xb3 : \ |
| 135 | (nr) == 1 ? 0x220 : 0x218) + (index)) | 136 | (nr) == 1 ? 0x220 : 0x218) + (index)) |
| 136 | 137 | ||
| @@ -242,9 +243,7 @@ static struct i2c_driver w83793_driver = { | |||
| 242 | static ssize_t | 243 | static ssize_t |
| 243 | show_vrm(struct device *dev, struct device_attribute *attr, char *buf) | 244 | show_vrm(struct device *dev, struct device_attribute *attr, char *buf) |
| 244 | { | 245 | { |
| 245 | struct i2c_client *client = to_i2c_client(dev); | 246 | struct w83793_data *data = dev_get_drvdata(dev); |
| 246 | struct w83793_data *data = i2c_get_clientdata(client); | ||
| 247 | |||
| 248 | return sprintf(buf, "%d\n", data->vrm); | 247 | return sprintf(buf, "%d\n", data->vrm); |
| 249 | } | 248 | } |
| 250 | 249 | ||
| @@ -263,9 +262,7 @@ static ssize_t | |||
| 263 | store_vrm(struct device *dev, struct device_attribute *attr, | 262 | store_vrm(struct device *dev, struct device_attribute *attr, |
| 264 | const char *buf, size_t count) | 263 | const char *buf, size_t count) |
| 265 | { | 264 | { |
| 266 | struct i2c_client *client = to_i2c_client(dev); | 265 | struct w83793_data *data = dev_get_drvdata(dev); |
| 267 | struct w83793_data *data = i2c_get_clientdata(client); | ||
| 268 | |||
| 269 | data->vrm = simple_strtoul(buf, NULL, 10); | 266 | data->vrm = simple_strtoul(buf, NULL, 10); |
| 270 | return count; | 267 | return count; |
| 271 | } | 268 | } |
| @@ -407,10 +404,6 @@ store_fan_min(struct device *dev, struct device_attribute *attr, | |||
| 407 | return count; | 404 | return count; |
| 408 | } | 405 | } |
| 409 | 406 | ||
| 410 | #define PWM_DUTY 0 | ||
| 411 | #define PWM_START 1 | ||
| 412 | #define PWM_NONSTOP 2 | ||
| 413 | #define PWM_STOP_TIME 3 | ||
| 414 | static ssize_t | 407 | static ssize_t |
| 415 | show_pwm(struct device *dev, struct device_attribute *attr, char *buf) | 408 | show_pwm(struct device *dev, struct device_attribute *attr, char *buf) |
| 416 | { | 409 | { |
diff --git a/drivers/hwmon/w83l785ts.c b/drivers/hwmon/w83l785ts.c index b5db354e2f19..1d6259d29e74 100644 --- a/drivers/hwmon/w83l785ts.c +++ b/drivers/hwmon/w83l785ts.c | |||
| @@ -96,7 +96,6 @@ static struct i2c_driver w83l785ts_driver = { | |||
| 96 | .driver = { | 96 | .driver = { |
| 97 | .name = "w83l785ts", | 97 | .name = "w83l785ts", |
| 98 | }, | 98 | }, |
| 99 | .id = I2C_DRIVERID_W83L785TS, | ||
| 100 | .attach_adapter = w83l785ts_attach_adapter, | 99 | .attach_adapter = w83l785ts_attach_adapter, |
| 101 | .detach_client = w83l785ts_detach_client, | 100 | .detach_client = w83l785ts_detach_client, |
| 102 | }; | 101 | }; |
diff --git a/drivers/hwmon/w83l786ng.c b/drivers/hwmon/w83l786ng.c new file mode 100644 index 000000000000..1dbee4fa23ad --- /dev/null +++ b/drivers/hwmon/w83l786ng.c | |||
| @@ -0,0 +1,821 @@ | |||
| 1 | /* | ||
| 2 | w83l786ng.c - Linux kernel driver for hardware monitoring | ||
| 3 | Copyright (c) 2007 Kevin Lo <kevlo@kevlo.org> | ||
| 4 | |||
| 5 | This program is free software; you can redistribute it and/or modify | ||
| 6 | it under the terms of the GNU General Public License as published by | ||
| 7 | the Free Software Foundation - version 2. | ||
| 8 | |||
| 9 | This program is distributed in the hope that it will be useful, | ||
| 10 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
| 11 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
| 12 | GNU General Public License for more details. | ||
| 13 | |||
| 14 | You should have received a copy of the GNU General Public License | ||
| 15 | along with this program; if not, write to the Free Software | ||
| 16 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA | ||
| 17 | 02110-1301 USA. | ||
| 18 | */ | ||
| 19 | |||
| 20 | /* | ||
| 21 | Supports following chips: | ||
| 22 | |||
| 23 | Chip #vin #fanin #pwm #temp wchipid vendid i2c ISA | ||
| 24 | w83l786ng 3 2 2 2 0x7b 0x5ca3 yes no | ||
| 25 | */ | ||
| 26 | |||
| 27 | #include <linux/module.h> | ||
| 28 | #include <linux/init.h> | ||
| 29 | #include <linux/slab.h> | ||
| 30 | #include <linux/i2c.h> | ||
| 31 | #include <linux/hwmon.h> | ||
| 32 | #include <linux/hwmon-vid.h> | ||
| 33 | #include <linux/hwmon-sysfs.h> | ||
| 34 | #include <linux/err.h> | ||
| 35 | #include <linux/mutex.h> | ||
| 36 | |||
| 37 | /* Addresses to scan */ | ||
| 38 | static unsigned short normal_i2c[] = { 0x2e, 0x2f, I2C_CLIENT_END }; | ||
| 39 | |||
| 40 | /* Insmod parameters */ | ||
| 41 | I2C_CLIENT_INSMOD_1(w83l786ng); | ||
| 42 | |||
| 43 | static int reset; | ||
| 44 | module_param(reset, bool, 0); | ||
| 45 | MODULE_PARM_DESC(reset, "Set to 1 to reset chip, not recommended"); | ||
| 46 | |||
| 47 | #define W83L786NG_REG_IN_MIN(nr) (0x2C + (nr) * 2) | ||
| 48 | #define W83L786NG_REG_IN_MAX(nr) (0x2B + (nr) * 2) | ||
| 49 | #define W83L786NG_REG_IN(nr) ((nr) + 0x20) | ||
| 50 | |||
| 51 | #define W83L786NG_REG_FAN(nr) ((nr) + 0x28) | ||
| 52 | #define W83L786NG_REG_FAN_MIN(nr) ((nr) + 0x3B) | ||
| 53 | |||
| 54 | #define W83L786NG_REG_CONFIG 0x40 | ||
| 55 | #define W83L786NG_REG_ALARM1 0x41 | ||
| 56 | #define W83L786NG_REG_ALARM2 0x42 | ||
| 57 | #define W83L786NG_REG_GPIO_EN 0x47 | ||
| 58 | #define W83L786NG_REG_MAN_ID2 0x4C | ||
| 59 | #define W83L786NG_REG_MAN_ID1 0x4D | ||
| 60 | #define W83L786NG_REG_CHIP_ID 0x4E | ||
| 61 | |||
| 62 | #define W83L786NG_REG_DIODE 0x53 | ||
| 63 | #define W83L786NG_REG_FAN_DIV 0x54 | ||
| 64 | #define W83L786NG_REG_FAN_CFG 0x80 | ||
| 65 | |||
| 66 | #define W83L786NG_REG_TOLERANCE 0x8D | ||
| 67 | |||
| 68 | static const u8 W83L786NG_REG_TEMP[2][3] = { | ||
| 69 | { 0x25, /* TEMP 0 in DataSheet */ | ||
| 70 | 0x35, /* TEMP 0 Over in DataSheet */ | ||
| 71 | 0x36 }, /* TEMP 0 Hyst in DataSheet */ | ||
| 72 | { 0x26, /* TEMP 1 in DataSheet */ | ||
| 73 | 0x37, /* TEMP 1 Over in DataSheet */ | ||
| 74 | 0x38 } /* TEMP 1 Hyst in DataSheet */ | ||
| 75 | }; | ||
| 76 | |||
| 77 | static const u8 W83L786NG_PWM_MODE_SHIFT[] = {6, 7}; | ||
| 78 | static const u8 W83L786NG_PWM_ENABLE_SHIFT[] = {2, 4}; | ||
| 79 | |||
| 80 | /* FAN Duty Cycle, be used to control */ | ||
| 81 | static const u8 W83L786NG_REG_PWM[] = {0x81, 0x87}; | ||
| 82 | |||
| 83 | |||
| 84 | static inline u8 | ||
| 85 | FAN_TO_REG(long rpm, int div) | ||
| 86 | { | ||
| 87 | if (rpm == 0) | ||
| 88 | return 255; | ||
| 89 | rpm = SENSORS_LIMIT(rpm, 1, 1000000); | ||
| 90 | return SENSORS_LIMIT((1350000 + rpm * div / 2) / (rpm * div), 1, 254); | ||
| 91 | } | ||
| 92 | |||
| 93 | #define FAN_FROM_REG(val,div) ((val) == 0 ? -1 : \ | ||
| 94 | ((val) == 255 ? 0 : \ | ||
| 95 | 1350000 / ((val) * (div)))) | ||
| 96 | |||
| 97 | /* for temp */ | ||
| 98 | #define TEMP_TO_REG(val) (SENSORS_LIMIT(((val) < 0 ? (val)+0x100*1000 \ | ||
| 99 | : (val)) / 1000, 0, 0xff)) | ||
| 100 | #define TEMP_FROM_REG(val) (((val) & 0x80 ? (val)-0x100 : (val)) * 1000) | ||
| 101 | |||
| 102 | /* The analog voltage inputs have 8mV LSB. Since the sysfs output is | ||
| 103 | in mV as would be measured on the chip input pin, need to just | ||
| 104 | multiply/divide by 8 to translate from/to register values. */ | ||
| 105 | #define IN_TO_REG(val) (SENSORS_LIMIT((((val) + 4) / 8), 0, 255)) | ||
| 106 | #define IN_FROM_REG(val) ((val) * 8) | ||
| 107 | |||
| 108 | #define DIV_FROM_REG(val) (1 << (val)) | ||
| 109 | |||
| 110 | static inline u8 | ||
| 111 | DIV_TO_REG(long val) | ||
| 112 | { | ||
| 113 | int i; | ||
| 114 | val = SENSORS_LIMIT(val, 1, 128) >> 1; | ||
| 115 | for (i = 0; i < 7; i++) { | ||
| 116 | if (val == 0) | ||
| 117 | break; | ||
| 118 | val >>= 1; | ||
| 119 | } | ||
| 120 | return ((u8) i); | ||
| 121 | } | ||
| 122 | |||
| 123 | struct w83l786ng_data { | ||
| 124 | struct i2c_client client; | ||
| 125 | struct device *hwmon_dev; | ||
| 126 | struct mutex update_lock; | ||
| 127 | char valid; /* !=0 if following fields are valid */ | ||
| 128 | unsigned long last_updated; /* In jiffies */ | ||
| 129 | unsigned long last_nonvolatile; /* In jiffies, last time we update the | ||
| 130 | nonvolatile registers */ | ||
| 131 | |||
| 132 | u8 in[3]; | ||
| 133 | u8 in_max[3]; | ||
| 134 | u8 in_min[3]; | ||
| 135 | u8 fan[2]; | ||
| 136 | u8 fan_div[2]; | ||
| 137 | u8 fan_min[2]; | ||
| 138 | u8 temp_type[2]; | ||
| 139 | u8 temp[2][3]; | ||
| 140 | u8 pwm[2]; | ||
| 141 | u8 pwm_mode[2]; /* 0->DC variable voltage | ||
| 142 | 1->PWM variable duty cycle */ | ||
| 143 | |||
| 144 | u8 pwm_enable[2]; /* 1->manual | ||
| 145 | 2->thermal cruise (also called SmartFan I) */ | ||
| 146 | u8 tolerance[2]; | ||
| 147 | }; | ||
| 148 | |||
| 149 | static int w83l786ng_attach_adapter(struct i2c_adapter *adapter); | ||
| 150 | static int w83l786ng_detect(struct i2c_adapter *adapter, int address, int kind); | ||
| 151 | static int w83l786ng_detach_client(struct i2c_client *client); | ||
| 152 | static void w83l786ng_init_client(struct i2c_client *client); | ||
| 153 | static struct w83l786ng_data *w83l786ng_update_device(struct device *dev); | ||
| 154 | |||
| 155 | static struct i2c_driver w83l786ng_driver = { | ||
| 156 | .driver = { | ||
| 157 | .name = "w83l786ng", | ||
| 158 | }, | ||
| 159 | .attach_adapter = w83l786ng_attach_adapter, | ||
| 160 | .detach_client = w83l786ng_detach_client, | ||
| 161 | }; | ||
| 162 | |||
| 163 | static u8 | ||
| 164 | w83l786ng_read_value(struct i2c_client *client, u8 reg) | ||
| 165 | { | ||
| 166 | return i2c_smbus_read_byte_data(client, reg); | ||
| 167 | } | ||
| 168 | |||
| 169 | static int | ||
| 170 | w83l786ng_write_value(struct i2c_client *client, u8 reg, u8 value) | ||
| 171 | { | ||
| 172 | return i2c_smbus_write_byte_data(client, reg, value); | ||
| 173 | } | ||
| 174 | |||
| 175 | /* following are the sysfs callback functions */ | ||
| 176 | #define show_in_reg(reg) \ | ||
| 177 | static ssize_t \ | ||
| 178 | show_##reg(struct device *dev, struct device_attribute *attr, \ | ||
| 179 | char *buf) \ | ||
| 180 | { \ | ||
| 181 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 182 | struct w83l786ng_data *data = w83l786ng_update_device(dev); \ | ||
| 183 | return sprintf(buf,"%d\n", IN_FROM_REG(data->reg[nr])); \ | ||
| 184 | } | ||
| 185 | |||
| 186 | show_in_reg(in) | ||
| 187 | show_in_reg(in_min) | ||
| 188 | show_in_reg(in_max) | ||
| 189 | |||
| 190 | #define store_in_reg(REG, reg) \ | ||
| 191 | static ssize_t \ | ||
| 192 | store_in_##reg (struct device *dev, struct device_attribute *attr, \ | ||
| 193 | const char *buf, size_t count) \ | ||
| 194 | { \ | ||
| 195 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 196 | struct i2c_client *client = to_i2c_client(dev); \ | ||
| 197 | struct w83l786ng_data *data = i2c_get_clientdata(client); \ | ||
| 198 | unsigned long val = simple_strtoul(buf, NULL, 10); \ | ||
| 199 | mutex_lock(&data->update_lock); \ | ||
| 200 | data->in_##reg[nr] = IN_TO_REG(val); \ | ||
| 201 | w83l786ng_write_value(client, W83L786NG_REG_IN_##REG(nr), \ | ||
| 202 | data->in_##reg[nr]); \ | ||
| 203 | mutex_unlock(&data->update_lock); \ | ||
| 204 | return count; \ | ||
| 205 | } | ||
| 206 | |||
| 207 | store_in_reg(MIN, min) | ||
| 208 | store_in_reg(MAX, max) | ||
| 209 | |||
| 210 | static struct sensor_device_attribute sda_in_input[] = { | ||
| 211 | SENSOR_ATTR(in0_input, S_IRUGO, show_in, NULL, 0), | ||
| 212 | SENSOR_ATTR(in1_input, S_IRUGO, show_in, NULL, 1), | ||
| 213 | SENSOR_ATTR(in2_input, S_IRUGO, show_in, NULL, 2), | ||
| 214 | }; | ||
| 215 | |||
| 216 | static struct sensor_device_attribute sda_in_min[] = { | ||
| 217 | SENSOR_ATTR(in0_min, S_IWUSR | S_IRUGO, show_in_min, store_in_min, 0), | ||
| 218 | SENSOR_ATTR(in1_min, S_IWUSR | S_IRUGO, show_in_min, store_in_min, 1), | ||
| 219 | SENSOR_ATTR(in2_min, S_IWUSR | S_IRUGO, show_in_min, store_in_min, 2), | ||
| 220 | }; | ||
| 221 | |||
| 222 | static struct sensor_device_attribute sda_in_max[] = { | ||
| 223 | SENSOR_ATTR(in0_max, S_IWUSR | S_IRUGO, show_in_max, store_in_max, 0), | ||
| 224 | SENSOR_ATTR(in1_max, S_IWUSR | S_IRUGO, show_in_max, store_in_max, 1), | ||
| 225 | SENSOR_ATTR(in2_max, S_IWUSR | S_IRUGO, show_in_max, store_in_max, 2), | ||
| 226 | }; | ||
| 227 | |||
| 228 | #define show_fan_reg(reg) \ | ||
| 229 | static ssize_t show_##reg(struct device *dev, struct device_attribute *attr, \ | ||
| 230 | char *buf) \ | ||
| 231 | { \ | ||
| 232 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 233 | struct w83l786ng_data *data = w83l786ng_update_device(dev); \ | ||
| 234 | return sprintf(buf,"%d\n", \ | ||
| 235 | FAN_FROM_REG(data->fan[nr], DIV_FROM_REG(data->fan_div[nr]))); \ | ||
| 236 | } | ||
| 237 | |||
| 238 | show_fan_reg(fan); | ||
| 239 | show_fan_reg(fan_min); | ||
| 240 | |||
| 241 | static ssize_t | ||
| 242 | store_fan_min(struct device *dev, struct device_attribute *attr, | ||
| 243 | const char *buf, size_t count) | ||
| 244 | { | ||
| 245 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 246 | struct i2c_client *client = to_i2c_client(dev); | ||
| 247 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 248 | u32 val; | ||
| 249 | |||
| 250 | val = simple_strtoul(buf, NULL, 10); | ||
| 251 | mutex_lock(&data->update_lock); | ||
| 252 | data->fan_min[nr] = FAN_TO_REG(val, DIV_FROM_REG(data->fan_div[nr])); | ||
| 253 | w83l786ng_write_value(client, W83L786NG_REG_FAN_MIN(nr), | ||
| 254 | data->fan_min[nr]); | ||
| 255 | mutex_unlock(&data->update_lock); | ||
| 256 | |||
| 257 | return count; | ||
| 258 | } | ||
| 259 | |||
| 260 | static ssize_t | ||
| 261 | show_fan_div(struct device *dev, struct device_attribute *attr, | ||
| 262 | char *buf) | ||
| 263 | { | ||
| 264 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 265 | struct w83l786ng_data *data = w83l786ng_update_device(dev); | ||
| 266 | return sprintf(buf, "%u\n", DIV_FROM_REG(data->fan_div[nr])); | ||
| 267 | } | ||
| 268 | |||
| 269 | /* Note: we save and restore the fan minimum here, because its value is | ||
| 270 | determined in part by the fan divisor. This follows the principle of | ||
| 271 | least surprise; the user doesn't expect the fan minimum to change just | ||
| 272 | because the divisor changed. */ | ||
| 273 | static ssize_t | ||
| 274 | store_fan_div(struct device *dev, struct device_attribute *attr, | ||
| 275 | const char *buf, size_t count) | ||
| 276 | { | ||
| 277 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 278 | struct i2c_client *client = to_i2c_client(dev); | ||
| 279 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 280 | |||
| 281 | unsigned long min; | ||
| 282 | u8 tmp_fan_div; | ||
| 283 | u8 fan_div_reg; | ||
| 284 | u8 keep_mask = 0; | ||
| 285 | u8 new_shift = 0; | ||
| 286 | |||
| 287 | /* Save fan_min */ | ||
| 288 | mutex_lock(&data->update_lock); | ||
| 289 | min = FAN_FROM_REG(data->fan_min[nr], DIV_FROM_REG(data->fan_div[nr])); | ||
| 290 | |||
| 291 | data->fan_div[nr] = DIV_TO_REG(simple_strtoul(buf, NULL, 10)); | ||
| 292 | |||
| 293 | switch (nr) { | ||
| 294 | case 0: | ||
| 295 | keep_mask = 0xf8; | ||
| 296 | new_shift = 0; | ||
| 297 | break; | ||
| 298 | case 1: | ||
| 299 | keep_mask = 0x8f; | ||
| 300 | new_shift = 4; | ||
| 301 | break; | ||
| 302 | } | ||
| 303 | |||
| 304 | fan_div_reg = w83l786ng_read_value(client, W83L786NG_REG_FAN_DIV) | ||
| 305 | & keep_mask; | ||
| 306 | |||
| 307 | tmp_fan_div = (data->fan_div[nr] << new_shift) & ~keep_mask; | ||
| 308 | |||
| 309 | w83l786ng_write_value(client, W83L786NG_REG_FAN_DIV, | ||
| 310 | fan_div_reg | tmp_fan_div); | ||
| 311 | |||
| 312 | /* Restore fan_min */ | ||
| 313 | data->fan_min[nr] = FAN_TO_REG(min, DIV_FROM_REG(data->fan_div[nr])); | ||
| 314 | w83l786ng_write_value(client, W83L786NG_REG_FAN_MIN(nr), | ||
| 315 | data->fan_min[nr]); | ||
| 316 | mutex_unlock(&data->update_lock); | ||
| 317 | |||
| 318 | return count; | ||
| 319 | } | ||
| 320 | |||
| 321 | static struct sensor_device_attribute sda_fan_input[] = { | ||
| 322 | SENSOR_ATTR(fan1_input, S_IRUGO, show_fan, NULL, 0), | ||
| 323 | SENSOR_ATTR(fan2_input, S_IRUGO, show_fan, NULL, 1), | ||
| 324 | }; | ||
| 325 | |||
| 326 | static struct sensor_device_attribute sda_fan_min[] = { | ||
| 327 | SENSOR_ATTR(fan1_min, S_IWUSR | S_IRUGO, show_fan_min, | ||
| 328 | store_fan_min, 0), | ||
| 329 | SENSOR_ATTR(fan2_min, S_IWUSR | S_IRUGO, show_fan_min, | ||
| 330 | store_fan_min, 1), | ||
| 331 | }; | ||
| 332 | |||
| 333 | static struct sensor_device_attribute sda_fan_div[] = { | ||
| 334 | SENSOR_ATTR(fan1_div, S_IWUSR | S_IRUGO, show_fan_div, | ||
| 335 | store_fan_div, 0), | ||
| 336 | SENSOR_ATTR(fan2_div, S_IWUSR | S_IRUGO, show_fan_div, | ||
| 337 | store_fan_div, 1), | ||
| 338 | }; | ||
| 339 | |||
| 340 | |||
| 341 | /* read/write the temperature, includes measured value and limits */ | ||
| 342 | |||
| 343 | static ssize_t | ||
| 344 | show_temp(struct device *dev, struct device_attribute *attr, char *buf) | ||
| 345 | { | ||
| 346 | struct sensor_device_attribute_2 *sensor_attr = | ||
| 347 | to_sensor_dev_attr_2(attr); | ||
| 348 | int nr = sensor_attr->nr; | ||
| 349 | int index = sensor_attr->index; | ||
| 350 | struct w83l786ng_data *data = w83l786ng_update_device(dev); | ||
| 351 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp[nr][index])); | ||
| 352 | } | ||
| 353 | |||
| 354 | static ssize_t | ||
| 355 | store_temp(struct device *dev, struct device_attribute *attr, | ||
| 356 | const char *buf, size_t count) | ||
| 357 | { | ||
| 358 | struct sensor_device_attribute_2 *sensor_attr = | ||
| 359 | to_sensor_dev_attr_2(attr); | ||
| 360 | int nr = sensor_attr->nr; | ||
| 361 | int index = sensor_attr->index; | ||
| 362 | struct i2c_client *client = to_i2c_client(dev); | ||
| 363 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 364 | s32 val; | ||
| 365 | |||
| 366 | val = simple_strtol(buf, NULL, 10); | ||
| 367 | mutex_lock(&data->update_lock); | ||
| 368 | data->temp[nr][index] = TEMP_TO_REG(val); | ||
| 369 | w83l786ng_write_value(client, W83L786NG_REG_TEMP[nr][index], | ||
| 370 | data->temp[nr][index]); | ||
| 371 | mutex_unlock(&data->update_lock); | ||
| 372 | |||
| 373 | return count; | ||
| 374 | } | ||
| 375 | |||
| 376 | static struct sensor_device_attribute_2 sda_temp_input[] = { | ||
| 377 | SENSOR_ATTR_2(temp1_input, S_IRUGO, show_temp, NULL, 0, 0), | ||
| 378 | SENSOR_ATTR_2(temp2_input, S_IRUGO, show_temp, NULL, 1, 0), | ||
| 379 | }; | ||
| 380 | |||
| 381 | static struct sensor_device_attribute_2 sda_temp_max[] = { | ||
| 382 | SENSOR_ATTR_2(temp1_max, S_IRUGO | S_IWUSR, | ||
| 383 | show_temp, store_temp, 0, 1), | ||
| 384 | SENSOR_ATTR_2(temp2_max, S_IRUGO | S_IWUSR, | ||
| 385 | show_temp, store_temp, 1, 1), | ||
| 386 | }; | ||
| 387 | |||
| 388 | static struct sensor_device_attribute_2 sda_temp_max_hyst[] = { | ||
| 389 | SENSOR_ATTR_2(temp1_max_hyst, S_IRUGO | S_IWUSR, | ||
| 390 | show_temp, store_temp, 0, 2), | ||
| 391 | SENSOR_ATTR_2(temp2_max_hyst, S_IRUGO | S_IWUSR, | ||
| 392 | show_temp, store_temp, 1, 2), | ||
| 393 | }; | ||
| 394 | |||
| 395 | #define show_pwm_reg(reg) \ | ||
| 396 | static ssize_t show_##reg (struct device *dev, struct device_attribute *attr, \ | ||
| 397 | char *buf) \ | ||
| 398 | { \ | ||
| 399 | struct w83l786ng_data *data = w83l786ng_update_device(dev); \ | ||
| 400 | int nr = to_sensor_dev_attr(attr)->index; \ | ||
| 401 | return sprintf(buf, "%d\n", data->reg[nr]); \ | ||
| 402 | } | ||
| 403 | |||
| 404 | show_pwm_reg(pwm_mode) | ||
| 405 | show_pwm_reg(pwm_enable) | ||
| 406 | show_pwm_reg(pwm) | ||
| 407 | |||
| 408 | static ssize_t | ||
| 409 | store_pwm_mode(struct device *dev, struct device_attribute *attr, | ||
| 410 | const char *buf, size_t count) | ||
| 411 | { | ||
| 412 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 413 | struct i2c_client *client = to_i2c_client(dev); | ||
| 414 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 415 | u32 val = simple_strtoul(buf, NULL, 10); | ||
| 416 | u8 reg; | ||
| 417 | |||
| 418 | if (val > 1) | ||
| 419 | return -EINVAL; | ||
| 420 | mutex_lock(&data->update_lock); | ||
| 421 | data->pwm_mode[nr] = val; | ||
| 422 | reg = w83l786ng_read_value(client, W83L786NG_REG_FAN_CFG); | ||
| 423 | reg &= ~(1 << W83L786NG_PWM_MODE_SHIFT[nr]); | ||
| 424 | if (!val) | ||
| 425 | reg |= 1 << W83L786NG_PWM_MODE_SHIFT[nr]; | ||
| 426 | w83l786ng_write_value(client, W83L786NG_REG_FAN_CFG, reg); | ||
| 427 | mutex_unlock(&data->update_lock); | ||
| 428 | return count; | ||
| 429 | } | ||
| 430 | |||
| 431 | static ssize_t | ||
| 432 | store_pwm(struct device *dev, struct device_attribute *attr, | ||
| 433 | const char *buf, size_t count) | ||
| 434 | { | ||
| 435 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 436 | struct i2c_client *client = to_i2c_client(dev); | ||
| 437 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 438 | u32 val = SENSORS_LIMIT(simple_strtoul(buf, NULL, 10), 0, 255); | ||
| 439 | |||
| 440 | mutex_lock(&data->update_lock); | ||
| 441 | data->pwm[nr] = val; | ||
| 442 | w83l786ng_write_value(client, W83L786NG_REG_PWM[nr], val); | ||
| 443 | mutex_unlock(&data->update_lock); | ||
| 444 | return count; | ||
| 445 | } | ||
| 446 | |||
| 447 | static ssize_t | ||
| 448 | store_pwm_enable(struct device *dev, struct device_attribute *attr, | ||
| 449 | const char *buf, size_t count) | ||
| 450 | { | ||
| 451 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 452 | struct i2c_client *client = to_i2c_client(dev); | ||
| 453 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 454 | u32 val = simple_strtoul(buf, NULL, 10); | ||
| 455 | |||
| 456 | u8 reg; | ||
| 457 | |||
| 458 | if (!val || (val > 2)) /* only modes 1 and 2 are supported */ | ||
| 459 | return -EINVAL; | ||
| 460 | |||
| 461 | mutex_lock(&data->update_lock); | ||
| 462 | reg = w83l786ng_read_value(client, W83L786NG_REG_FAN_CFG); | ||
| 463 | data->pwm_enable[nr] = val; | ||
| 464 | reg &= ~(0x02 << W83L786NG_PWM_ENABLE_SHIFT[nr]); | ||
| 465 | reg |= (val - 1) << W83L786NG_PWM_ENABLE_SHIFT[nr]; | ||
| 466 | w83l786ng_write_value(client, W83L786NG_REG_FAN_CFG, reg); | ||
| 467 | mutex_unlock(&data->update_lock); | ||
| 468 | return count; | ||
| 469 | } | ||
| 470 | |||
| 471 | static struct sensor_device_attribute sda_pwm[] = { | ||
| 472 | SENSOR_ATTR(pwm1, S_IWUSR | S_IRUGO, show_pwm, store_pwm, 0), | ||
| 473 | SENSOR_ATTR(pwm2, S_IWUSR | S_IRUGO, show_pwm, store_pwm, 1), | ||
| 474 | }; | ||
| 475 | |||
| 476 | static struct sensor_device_attribute sda_pwm_mode[] = { | ||
| 477 | SENSOR_ATTR(pwm1_mode, S_IWUSR | S_IRUGO, show_pwm_mode, | ||
| 478 | store_pwm_mode, 0), | ||
| 479 | SENSOR_ATTR(pwm2_mode, S_IWUSR | S_IRUGO, show_pwm_mode, | ||
| 480 | store_pwm_mode, 1), | ||
| 481 | }; | ||
| 482 | |||
| 483 | static struct sensor_device_attribute sda_pwm_enable[] = { | ||
| 484 | SENSOR_ATTR(pwm1_enable, S_IWUSR | S_IRUGO, show_pwm_enable, | ||
| 485 | store_pwm_enable, 0), | ||
| 486 | SENSOR_ATTR(pwm2_enable, S_IWUSR | S_IRUGO, show_pwm_enable, | ||
| 487 | store_pwm_enable, 1), | ||
| 488 | }; | ||
| 489 | |||
| 490 | /* For Smart Fan I/Thermal Cruise and Smart Fan II */ | ||
| 491 | static ssize_t | ||
| 492 | show_tolerance(struct device *dev, struct device_attribute *attr, char *buf) | ||
| 493 | { | ||
| 494 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 495 | struct w83l786ng_data *data = w83l786ng_update_device(dev); | ||
| 496 | return sprintf(buf, "%ld\n", (long)data->tolerance[nr]); | ||
| 497 | } | ||
| 498 | |||
| 499 | static ssize_t | ||
| 500 | store_tolerance(struct device *dev, struct device_attribute *attr, | ||
| 501 | const char *buf, size_t count) | ||
| 502 | { | ||
| 503 | int nr = to_sensor_dev_attr(attr)->index; | ||
| 504 | struct i2c_client *client = to_i2c_client(dev); | ||
| 505 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 506 | u32 val; | ||
| 507 | u8 tol_tmp, tol_mask; | ||
| 508 | |||
| 509 | val = simple_strtoul(buf, NULL, 10); | ||
| 510 | |||
| 511 | mutex_lock(&data->update_lock); | ||
| 512 | tol_mask = w83l786ng_read_value(client, | ||
| 513 | W83L786NG_REG_TOLERANCE) & ((nr == 1) ? 0x0f : 0xf0); | ||
| 514 | tol_tmp = SENSORS_LIMIT(val, 0, 15); | ||
| 515 | tol_tmp &= 0x0f; | ||
| 516 | data->tolerance[nr] = tol_tmp; | ||
| 517 | if (nr == 1) { | ||
| 518 | tol_tmp <<= 4; | ||
| 519 | } | ||
| 520 | |||
| 521 | w83l786ng_write_value(client, W83L786NG_REG_TOLERANCE, | ||
| 522 | tol_mask | tol_tmp); | ||
| 523 | mutex_unlock(&data->update_lock); | ||
| 524 | return count; | ||
| 525 | } | ||
| 526 | |||
| 527 | static struct sensor_device_attribute sda_tolerance[] = { | ||
| 528 | SENSOR_ATTR(pwm1_tolerance, S_IWUSR | S_IRUGO, | ||
| 529 | show_tolerance, store_tolerance, 0), | ||
| 530 | SENSOR_ATTR(pwm2_tolerance, S_IWUSR | S_IRUGO, | ||
| 531 | show_tolerance, store_tolerance, 1), | ||
| 532 | }; | ||
| 533 | |||
| 534 | |||
| 535 | #define IN_UNIT_ATTRS(X) \ | ||
| 536 | &sda_in_input[X].dev_attr.attr, \ | ||
| 537 | &sda_in_min[X].dev_attr.attr, \ | ||
| 538 | &sda_in_max[X].dev_attr.attr | ||
| 539 | |||
| 540 | #define FAN_UNIT_ATTRS(X) \ | ||
| 541 | &sda_fan_input[X].dev_attr.attr, \ | ||
| 542 | &sda_fan_min[X].dev_attr.attr, \ | ||
| 543 | &sda_fan_div[X].dev_attr.attr | ||
| 544 | |||
| 545 | #define TEMP_UNIT_ATTRS(X) \ | ||
| 546 | &sda_temp_input[X].dev_attr.attr, \ | ||
| 547 | &sda_temp_max[X].dev_attr.attr, \ | ||
| 548 | &sda_temp_max_hyst[X].dev_attr.attr | ||
| 549 | |||
| 550 | #define PWM_UNIT_ATTRS(X) \ | ||
| 551 | &sda_pwm[X].dev_attr.attr, \ | ||
| 552 | &sda_pwm_mode[X].dev_attr.attr, \ | ||
| 553 | &sda_pwm_enable[X].dev_attr.attr | ||
| 554 | |||
| 555 | #define TOLERANCE_UNIT_ATTRS(X) \ | ||
| 556 | &sda_tolerance[X].dev_attr.attr | ||
| 557 | |||
| 558 | static struct attribute *w83l786ng_attributes[] = { | ||
| 559 | IN_UNIT_ATTRS(0), | ||
| 560 | IN_UNIT_ATTRS(1), | ||
| 561 | IN_UNIT_ATTRS(2), | ||
| 562 | FAN_UNIT_ATTRS(0), | ||
| 563 | FAN_UNIT_ATTRS(1), | ||
| 564 | TEMP_UNIT_ATTRS(0), | ||
| 565 | TEMP_UNIT_ATTRS(1), | ||
| 566 | PWM_UNIT_ATTRS(0), | ||
| 567 | PWM_UNIT_ATTRS(1), | ||
| 568 | TOLERANCE_UNIT_ATTRS(0), | ||
| 569 | TOLERANCE_UNIT_ATTRS(1), | ||
| 570 | NULL | ||
| 571 | }; | ||
| 572 | |||
| 573 | static const struct attribute_group w83l786ng_group = { | ||
| 574 | .attrs = w83l786ng_attributes, | ||
| 575 | }; | ||
| 576 | |||
| 577 | static int | ||
| 578 | w83l786ng_attach_adapter(struct i2c_adapter *adapter) | ||
| 579 | { | ||
| 580 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
| 581 | return 0; | ||
| 582 | return i2c_probe(adapter, &addr_data, w83l786ng_detect); | ||
| 583 | } | ||
| 584 | |||
| 585 | static int | ||
| 586 | w83l786ng_detect(struct i2c_adapter *adapter, int address, int kind) | ||
| 587 | { | ||
| 588 | struct i2c_client *client; | ||
| 589 | struct device *dev; | ||
| 590 | struct w83l786ng_data *data; | ||
| 591 | int i, err = 0; | ||
| 592 | u8 reg_tmp; | ||
| 593 | |||
| 594 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) { | ||
| 595 | goto exit; | ||
| 596 | } | ||
| 597 | |||
| 598 | /* OK. For now, we presume we have a valid client. We now create the | ||
| 599 | client structure, even though we cannot fill it completely yet. | ||
| 600 | But it allows us to access w83l786ng_{read,write}_value. */ | ||
| 601 | |||
| 602 | if (!(data = kzalloc(sizeof(struct w83l786ng_data), GFP_KERNEL))) { | ||
| 603 | err = -ENOMEM; | ||
| 604 | goto exit; | ||
| 605 | } | ||
| 606 | |||
| 607 | client = &data->client; | ||
| 608 | dev = &client->dev; | ||
| 609 | i2c_set_clientdata(client, data); | ||
| 610 | client->addr = address; | ||
| 611 | client->adapter = adapter; | ||
| 612 | client->driver = &w83l786ng_driver; | ||
| 613 | |||
| 614 | /* | ||
| 615 | * Now we do the remaining detection. A negative kind means that | ||
| 616 | * the driver was loaded with no force parameter (default), so we | ||
| 617 | * must both detect and identify the chip (actually there is only | ||
| 618 | * one possible kind of chip for now, W83L786NG). A zero kind means | ||
| 619 | * that the driver was loaded with the force parameter, the detection | ||
| 620 | * step shall be skipped. A positive kind means that the driver | ||
| 621 | * was loaded with the force parameter and a given kind of chip is | ||
| 622 | * requested, so both the detection and the identification steps | ||
| 623 | * are skipped. | ||
| 624 | */ | ||
| 625 | if (kind < 0) { /* detection */ | ||
| 626 | if (((w83l786ng_read_value(client, | ||
| 627 | W83L786NG_REG_CONFIG) & 0x80) != 0x00)) { | ||
| 628 | dev_dbg(&adapter->dev, | ||
| 629 | "W83L786NG detection failed at 0x%02x.\n", | ||
| 630 | address); | ||
| 631 | goto exit_free; | ||
| 632 | } | ||
| 633 | } | ||
| 634 | |||
| 635 | if (kind <= 0) { /* identification */ | ||
| 636 | u16 man_id; | ||
| 637 | u8 chip_id; | ||
| 638 | |||
| 639 | man_id = (w83l786ng_read_value(client, | ||
| 640 | W83L786NG_REG_MAN_ID1) << 8) + | ||
| 641 | w83l786ng_read_value(client, W83L786NG_REG_MAN_ID2); | ||
| 642 | chip_id = w83l786ng_read_value(client, W83L786NG_REG_CHIP_ID); | ||
| 643 | |||
| 644 | if (man_id == 0x5CA3) { /* Winbond */ | ||
| 645 | if (chip_id == 0x80) { /* W83L786NG */ | ||
| 646 | kind = w83l786ng; | ||
| 647 | } | ||
| 648 | } | ||
| 649 | |||
| 650 | if (kind <= 0) { /* identification failed */ | ||
| 651 | dev_info(&adapter->dev, | ||
| 652 | "Unsupported chip (man_id=0x%04X, " | ||
| 653 | "chip_id=0x%02X).\n", man_id, chip_id); | ||
| 654 | goto exit_free; | ||
| 655 | } | ||
| 656 | } | ||
| 657 | |||
| 658 | /* Fill in the remaining client fields and put into the global list */ | ||
| 659 | strlcpy(client->name, "w83l786ng", I2C_NAME_SIZE); | ||
| 660 | mutex_init(&data->update_lock); | ||
| 661 | |||
| 662 | /* Tell the I2C layer a new client has arrived */ | ||
| 663 | if ((err = i2c_attach_client(client))) | ||
| 664 | goto exit_free; | ||
| 665 | |||
| 666 | /* Initialize the chip */ | ||
| 667 | w83l786ng_init_client(client); | ||
| 668 | |||
| 669 | /* A few vars need to be filled upon startup */ | ||
| 670 | for (i = 0; i < 2; i++) { | ||
| 671 | data->fan_min[i] = w83l786ng_read_value(client, | ||
| 672 | W83L786NG_REG_FAN_MIN(i)); | ||
| 673 | } | ||
| 674 | |||
| 675 | /* Update the fan divisor */ | ||
| 676 | reg_tmp = w83l786ng_read_value(client, W83L786NG_REG_FAN_DIV); | ||
| 677 | data->fan_div[0] = reg_tmp & 0x07; | ||
| 678 | data->fan_div[1] = (reg_tmp >> 4) & 0x07; | ||
| 679 | |||
| 680 | /* Register sysfs hooks */ | ||
| 681 | if ((err = sysfs_create_group(&client->dev.kobj, &w83l786ng_group))) | ||
| 682 | goto exit_remove; | ||
| 683 | |||
| 684 | data->hwmon_dev = hwmon_device_register(dev); | ||
| 685 | if (IS_ERR(data->hwmon_dev)) { | ||
| 686 | err = PTR_ERR(data->hwmon_dev); | ||
| 687 | goto exit_remove; | ||
| 688 | } | ||
| 689 | |||
| 690 | return 0; | ||
| 691 | |||
| 692 | /* Unregister sysfs hooks */ | ||
| 693 | |||
| 694 | exit_remove: | ||
| 695 | sysfs_remove_group(&client->dev.kobj, &w83l786ng_group); | ||
| 696 | i2c_detach_client(client); | ||
| 697 | exit_free: | ||
| 698 | kfree(data); | ||
| 699 | exit: | ||
| 700 | return err; | ||
| 701 | } | ||
| 702 | |||
| 703 | static int | ||
| 704 | w83l786ng_detach_client(struct i2c_client *client) | ||
| 705 | { | ||
| 706 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 707 | int err; | ||
| 708 | |||
| 709 | hwmon_device_unregister(data->hwmon_dev); | ||
| 710 | sysfs_remove_group(&client->dev.kobj, &w83l786ng_group); | ||
| 711 | |||
| 712 | if ((err = i2c_detach_client(client))) | ||
| 713 | return err; | ||
| 714 | |||
| 715 | kfree(data); | ||
| 716 | |||
| 717 | return 0; | ||
| 718 | } | ||
| 719 | |||
| 720 | static void | ||
| 721 | w83l786ng_init_client(struct i2c_client *client) | ||
| 722 | { | ||
| 723 | u8 tmp; | ||
| 724 | |||
| 725 | if (reset) | ||
| 726 | w83l786ng_write_value(client, W83L786NG_REG_CONFIG, 0x80); | ||
| 727 | |||
| 728 | /* Start monitoring */ | ||
| 729 | tmp = w83l786ng_read_value(client, W83L786NG_REG_CONFIG); | ||
| 730 | if (!(tmp & 0x01)) | ||
| 731 | w83l786ng_write_value(client, W83L786NG_REG_CONFIG, tmp | 0x01); | ||
| 732 | } | ||
| 733 | |||
| 734 | static struct w83l786ng_data *w83l786ng_update_device(struct device *dev) | ||
| 735 | { | ||
| 736 | struct i2c_client *client = to_i2c_client(dev); | ||
| 737 | struct w83l786ng_data *data = i2c_get_clientdata(client); | ||
| 738 | int i, j; | ||
| 739 | u8 reg_tmp, pwmcfg; | ||
| 740 | |||
| 741 | mutex_lock(&data->update_lock); | ||
| 742 | if (time_after(jiffies, data->last_updated + HZ + HZ / 2) | ||
| 743 | || !data->valid) { | ||
| 744 | dev_dbg(&client->dev, "Updating w83l786ng data.\n"); | ||
| 745 | |||
| 746 | /* Update the voltages measured value and limits */ | ||
| 747 | for (i = 0; i < 3; i++) { | ||
| 748 | data->in[i] = w83l786ng_read_value(client, | ||
| 749 | W83L786NG_REG_IN(i)); | ||
| 750 | data->in_min[i] = w83l786ng_read_value(client, | ||
| 751 | W83L786NG_REG_IN_MIN(i)); | ||
| 752 | data->in_max[i] = w83l786ng_read_value(client, | ||
| 753 | W83L786NG_REG_IN_MAX(i)); | ||
| 754 | } | ||
| 755 | |||
| 756 | /* Update the fan counts and limits */ | ||
| 757 | for (i = 0; i < 2; i++) { | ||
| 758 | data->fan[i] = w83l786ng_read_value(client, | ||
| 759 | W83L786NG_REG_FAN(i)); | ||
| 760 | data->fan_min[i] = w83l786ng_read_value(client, | ||
| 761 | W83L786NG_REG_FAN_MIN(i)); | ||
| 762 | } | ||
| 763 | |||
| 764 | /* Update the fan divisor */ | ||
| 765 | reg_tmp = w83l786ng_read_value(client, W83L786NG_REG_FAN_DIV); | ||
| 766 | data->fan_div[0] = reg_tmp & 0x07; | ||
| 767 | data->fan_div[1] = (reg_tmp >> 4) & 0x07; | ||
| 768 | |||
| 769 | pwmcfg = w83l786ng_read_value(client, W83L786NG_REG_FAN_CFG); | ||
| 770 | for (i = 0; i < 2; i++) { | ||
| 771 | data->pwm_mode[i] = | ||
| 772 | ((pwmcfg >> W83L786NG_PWM_MODE_SHIFT[i]) & 1) | ||
| 773 | ? 0 : 1; | ||
| 774 | data->pwm_enable[i] = | ||
| 775 | ((pwmcfg >> W83L786NG_PWM_ENABLE_SHIFT[i]) & 2) + 1; | ||
| 776 | data->pwm[i] = w83l786ng_read_value(client, | ||
| 777 | W83L786NG_REG_PWM[i]); | ||
| 778 | } | ||
| 779 | |||
| 780 | |||
| 781 | /* Update the temperature sensors */ | ||
| 782 | for (i = 0; i < 2; i++) { | ||
| 783 | for (j = 0; j < 3; j++) { | ||
| 784 | data->temp[i][j] = w83l786ng_read_value(client, | ||
| 785 | W83L786NG_REG_TEMP[i][j]); | ||
| 786 | } | ||
| 787 | } | ||
| 788 | |||
| 789 | /* Update Smart Fan I/II tolerance */ | ||
| 790 | reg_tmp = w83l786ng_read_value(client, W83L786NG_REG_TOLERANCE); | ||
| 791 | data->tolerance[0] = reg_tmp & 0x0f; | ||
| 792 | data->tolerance[1] = (reg_tmp >> 4) & 0x0f; | ||
| 793 | |||
| 794 | data->last_updated = jiffies; | ||
| 795 | data->valid = 1; | ||
| 796 | |||
| 797 | } | ||
| 798 | |||
| 799 | mutex_unlock(&data->update_lock); | ||
| 800 | |||
| 801 | return data; | ||
| 802 | } | ||
| 803 | |||
| 804 | static int __init | ||
| 805 | sensors_w83l786ng_init(void) | ||
| 806 | { | ||
| 807 | return i2c_add_driver(&w83l786ng_driver); | ||
| 808 | } | ||
| 809 | |||
| 810 | static void __exit | ||
| 811 | sensors_w83l786ng_exit(void) | ||
| 812 | { | ||
| 813 | i2c_del_driver(&w83l786ng_driver); | ||
| 814 | } | ||
| 815 | |||
| 816 | MODULE_AUTHOR("Kevin Lo"); | ||
| 817 | MODULE_DESCRIPTION("w83l786ng driver"); | ||
| 818 | MODULE_LICENSE("GPL"); | ||
| 819 | |||
| 820 | module_init(sensors_w83l786ng_init); | ||
| 821 | module_exit(sensors_w83l786ng_exit); | ||
diff --git a/drivers/i2c/chips/eeprom.c b/drivers/i2c/chips/eeprom.c index fde297b21ad7..7dee001e5133 100644 --- a/drivers/i2c/chips/eeprom.c +++ b/drivers/i2c/chips/eeprom.c | |||
| @@ -71,7 +71,6 @@ static struct i2c_driver eeprom_driver = { | |||
| 71 | .driver = { | 71 | .driver = { |
| 72 | .name = "eeprom", | 72 | .name = "eeprom", |
| 73 | }, | 73 | }, |
| 74 | .id = I2C_DRIVERID_EEPROM, | ||
| 75 | .attach_adapter = eeprom_attach_adapter, | 74 | .attach_adapter = eeprom_attach_adapter, |
| 76 | .detach_client = eeprom_detach_client, | 75 | .detach_client = eeprom_detach_client, |
| 77 | }; | 76 | }; |
diff --git a/drivers/i2c/chips/pcf8574.c b/drivers/i2c/chips/pcf8574.c index b3b830ccf209..e5b31329b56e 100644 --- a/drivers/i2c/chips/pcf8574.c +++ b/drivers/i2c/chips/pcf8574.c | |||
| @@ -67,7 +67,6 @@ static struct i2c_driver pcf8574_driver = { | |||
| 67 | .driver = { | 67 | .driver = { |
| 68 | .name = "pcf8574", | 68 | .name = "pcf8574", |
| 69 | }, | 69 | }, |
| 70 | .id = I2C_DRIVERID_PCF8574, | ||
| 71 | .attach_adapter = pcf8574_attach_adapter, | 70 | .attach_adapter = pcf8574_attach_adapter, |
| 72 | .detach_client = pcf8574_detach_client, | 71 | .detach_client = pcf8574_detach_client, |
| 73 | }; | 72 | }; |
diff --git a/drivers/i2c/chips/pcf8591.c b/drivers/i2c/chips/pcf8591.c index 865f4409c06b..66c7c3bb9429 100644 --- a/drivers/i2c/chips/pcf8591.c +++ b/drivers/i2c/chips/pcf8591.c | |||
| @@ -92,7 +92,6 @@ static struct i2c_driver pcf8591_driver = { | |||
| 92 | .driver = { | 92 | .driver = { |
| 93 | .name = "pcf8591", | 93 | .name = "pcf8591", |
| 94 | }, | 94 | }, |
| 95 | .id = I2C_DRIVERID_PCF8591, | ||
| 96 | .attach_adapter = pcf8591_attach_adapter, | 95 | .attach_adapter = pcf8591_attach_adapter, |
| 97 | .detach_client = pcf8591_detach_client, | 96 | .detach_client = pcf8591_detach_client, |
| 98 | }; | 97 | }; |
diff --git a/include/linux/dmi.h b/include/linux/dmi.h index b1251b2af568..bbc9992ec374 100644 --- a/include/linux/dmi.h +++ b/include/linux/dmi.h | |||
| @@ -79,6 +79,7 @@ extern void dmi_scan_machine(void); | |||
| 79 | extern int dmi_get_year(int field); | 79 | extern int dmi_get_year(int field); |
| 80 | extern int dmi_name_in_vendors(const char *str); | 80 | extern int dmi_name_in_vendors(const char *str); |
| 81 | extern int dmi_available; | 81 | extern int dmi_available; |
| 82 | extern int dmi_walk(void (*decode)(const struct dmi_header *)); | ||
| 82 | 83 | ||
| 83 | #else | 84 | #else |
| 84 | 85 | ||
| @@ -89,6 +90,8 @@ static inline const struct dmi_device * dmi_find_device(int type, const char *na | |||
| 89 | static inline int dmi_get_year(int year) { return 0; } | 90 | static inline int dmi_get_year(int year) { return 0; } |
| 90 | static inline int dmi_name_in_vendors(const char *s) { return 0; } | 91 | static inline int dmi_name_in_vendors(const char *s) { return 0; } |
| 91 | #define dmi_available 0 | 92 | #define dmi_available 0 |
| 93 | static inline int dmi_walk(void (*decode)(const struct dmi_header *)) | ||
| 94 | { return -1; } | ||
| 92 | 95 | ||
| 93 | #endif | 96 | #endif |
| 94 | 97 | ||
diff --git a/include/linux/i2c-id.h b/include/linux/i2c-id.h index f922b060158b..b979112f74e0 100644 --- a/include/linux/i2c-id.h +++ b/include/linux/i2c-id.h | |||
| @@ -96,42 +96,6 @@ | |||
| 96 | 96 | ||
| 97 | #define I2C_DRIVERID_I2CDEV 900 | 97 | #define I2C_DRIVERID_I2CDEV 900 |
| 98 | 98 | ||
| 99 | /* IDs -- Use DRIVERIDs 1000-1999 for sensors. | ||
| 100 | These were originally in sensors.h in the lm_sensors package */ | ||
| 101 | #define I2C_DRIVERID_LM78 1002 | ||
| 102 | #define I2C_DRIVERID_LM75 1003 | ||
| 103 | #define I2C_DRIVERID_GL518 1004 | ||
| 104 | #define I2C_DRIVERID_EEPROM 1005 | ||
| 105 | #define I2C_DRIVERID_W83781D 1006 | ||
| 106 | #define I2C_DRIVERID_LM80 1007 | ||
| 107 | #define I2C_DRIVERID_ADM1021 1008 | ||
| 108 | #define I2C_DRIVERID_ADM9240 1009 | ||
| 109 | #define I2C_DRIVERID_LTC1710 1010 | ||
| 110 | #define I2C_DRIVERID_BT869 1013 | ||
| 111 | #define I2C_DRIVERID_MAXILIFE 1014 | ||
| 112 | #define I2C_DRIVERID_MATORB 1015 | ||
| 113 | #define I2C_DRIVERID_GL520 1016 | ||
| 114 | #define I2C_DRIVERID_THMC50 1017 | ||
| 115 | #define I2C_DRIVERID_ADM1025 1020 | ||
| 116 | #define I2C_DRIVERID_LM87 1021 | ||
| 117 | #define I2C_DRIVERID_PCF8574 1022 | ||
| 118 | #define I2C_DRIVERID_MTP008 1023 | ||
| 119 | #define I2C_DRIVERID_DS1621 1024 | ||
| 120 | #define I2C_DRIVERID_ADM1024 1025 | ||
| 121 | #define I2C_DRIVERID_CH700X 1027 /* single driver for CH7003-7009 digital pc to tv encoders */ | ||
| 122 | #define I2C_DRIVERID_FSCPOS 1028 | ||
| 123 | #define I2C_DRIVERID_FSCSCY 1029 | ||
| 124 | #define I2C_DRIVERID_PCF8591 1030 | ||
| 125 | #define I2C_DRIVERID_LM92 1033 | ||
| 126 | #define I2C_DRIVERID_SMARTBATT 1035 | ||
| 127 | #define I2C_DRIVERID_BMCSENSORS 1036 | ||
| 128 | #define I2C_DRIVERID_FS451 1037 | ||
| 129 | #define I2C_DRIVERID_LM85 1039 | ||
| 130 | #define I2C_DRIVERID_LM83 1040 | ||
| 131 | #define I2C_DRIVERID_LM90 1042 | ||
| 132 | #define I2C_DRIVERID_ASB100 1043 | ||
| 133 | #define I2C_DRIVERID_FSCHER 1046 | ||
| 134 | #define I2C_DRIVERID_W83L785TS 1047 | ||
| 135 | #define I2C_DRIVERID_OV7670 1048 /* Omnivision 7670 camera */ | 99 | #define I2C_DRIVERID_OV7670 1048 /* Omnivision 7670 camera */ |
| 136 | 100 | ||
| 137 | /* | 101 | /* |
