aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Documentation/feature-removal-schedule.txt9
-rw-r--r--Documentation/hwmon/f71805f105
-rw-r--r--Documentation/hwmon/it872
-rw-r--r--Documentation/hwmon/sysfs-interface18
-rw-r--r--Documentation/i2c/busses/i2c-sis96x (renamed from Documentation/i2c/busses/i2c-sis69x)4
-rw-r--r--MAINTAINERS6
-rw-r--r--drivers/hwmon/Kconfig10
-rw-r--r--drivers/hwmon/Makefile1
-rw-r--r--drivers/hwmon/f71805f.c908
-rw-r--r--drivers/hwmon/it87.c8
-rw-r--r--drivers/hwmon/lm77.c8
-rw-r--r--drivers/hwmon/w83792d.c31
-rw-r--r--drivers/i2c/algos/i2c-algo-sibyte.c2
-rw-r--r--drivers/i2c/busses/Kconfig1
-rw-r--r--drivers/i2c/busses/i2c-i801.c2
-rw-r--r--drivers/i2c/busses/i2c-parport-light.c9
-rw-r--r--drivers/i2c/busses/i2c-parport.c7
-rw-r--r--drivers/i2c/busses/i2c-pxa.c2
-rw-r--r--drivers/i2c/i2c-core.c15
-rw-r--r--include/linux/i2c.h3
20 files changed, 1111 insertions, 40 deletions
diff --git a/Documentation/feature-removal-schedule.txt b/Documentation/feature-removal-schedule.txt
index 4d4897c8ef96..b730d765b525 100644
--- a/Documentation/feature-removal-schedule.txt
+++ b/Documentation/feature-removal-schedule.txt
@@ -162,3 +162,12 @@ What: pci_module_init(driver)
162When: January 2007 162When: January 2007
163Why: Is replaced by pci_register_driver(pci_driver). 163Why: Is replaced by pci_register_driver(pci_driver).
164Who: Richard Knutsson <ricknu-0@student.ltu.se> and Greg Kroah-Hartman <gregkh@suse.de> 164Who: Richard Knutsson <ricknu-0@student.ltu.se> and Greg Kroah-Hartman <gregkh@suse.de>
165
166---------------------------
167
168What: I2C interface of the it87 driver
169When: January 2007
170Why: The ISA interface is faster and should be always available. The I2C
171 probing is also known to cause trouble in at least one case (see
172 bug #5889.)
173Who: Jean Delvare <khali@linux-fr.org>
diff --git a/Documentation/hwmon/f71805f b/Documentation/hwmon/f71805f
new file mode 100644
index 000000000000..28c5b7d1eb90
--- /dev/null
+++ b/Documentation/hwmon/f71805f
@@ -0,0 +1,105 @@
1Kernel driver f71805f
2=====================
3
4Supported chips:
5 * Fintek F71805F/FG
6 Prefix: 'f71805f'
7 Addresses scanned: none, address read from Super I/O config space
8 Datasheet: Provided by Fintek on request
9
10Author: Jean Delvare <khali@linux-fr.org>
11
12Thanks to Denis Kieft from Barracuda Networks for the donation of a
13test system (custom Jetway K8M8MS motherboard, with CPU and RAM) and
14for providing initial documentation.
15
16Thanks to Kris Chen from Fintek for answering technical questions and
17providing additional documentation.
18
19Thanks to Chris Lin from Jetway for providing wiring schematics and
20anwsering technical questions.
21
22
23Description
24-----------
25
26The Fintek F71805F/FG Super I/O chip includes complete hardware monitoring
27capabilities. It can monitor up to 9 voltages (counting its own power
28source), 3 fans and 3 temperature sensors.
29
30This chip also has fan controlling features, using either DC or PWM, in
31three different modes (one manual, two automatic). The driver doesn't
32support these features yet.
33
34The driver assumes that no more than one chip is present, which seems
35reasonable.
36
37
38Voltage Monitoring
39------------------
40
41Voltages are sampled by an 8-bit ADC with a LSB of 8 mV. The supported
42range is thus from 0 to 2.040 V. Voltage values outside of this range
43need external resistors. An exception is in0, which is used to monitor
44the chip's own power source (+3.3V), and is divided internally by a
45factor 2.
46
47The two LSB of the voltage limit registers are not used (always 0), so
48you can only set the limits in steps of 32 mV (before scaling).
49
50The wirings and resistor values suggested by Fintek are as follow:
51
52 pin expected
53 name use R1 R2 divider raw val.
54
55in0 VCC VCC3.3V int. int. 2.00 1.65 V
56in1 VIN1 VTT1.2V 10K - 1.00 1.20 V
57in2 VIN2 VRAM 100K 100K 2.00 ~1.25 V (1)
58in3 VIN3 VCHIPSET 47K 100K 1.47 2.24 V (2)
59in4 VIN4 VCC5V 200K 47K 5.25 0.95 V
60in5 VIN5 +12V 200K 20K 11.00 1.05 V
61in6 VIN6 VCC1.5V 10K - 1.00 1.50 V
62in7 VIN7 VCORE 10K - 1.00 ~1.40 V (1)
63in8 VIN8 VSB5V 200K 47K 1.00 0.95 V
64
65(1) Depends on your hardware setup.
66(2) Obviously not correct, swapping R1 and R2 would make more sense.
67
68These values can be used as hints at best, as motherboard manufacturers
69are free to use a completely different setup. As a matter of fact, the
70Jetway K8M8MS uses a significantly different setup. You will have to
71find out documentation about your own motherboard, and edit sensors.conf
72accordingly.
73
74Each voltage measured has associated low and high limits, each of which
75triggers an alarm when crossed.
76
77
78Fan Monitoring
79--------------
80
81Fan rotation speeds are reported as 12-bit values from a gated clock
82signal. Speeds down to 366 RPM can be measured. There is no theoretical
83high limit, but values over 6000 RPM seem to cause problem. The effective
84resolution is much lower than you would expect, the step between different
85register values being 10 rather than 1.
86
87The chip assumes 2 pulse-per-revolution fans.
88
89An alarm is triggered if the rotation speed drops below a programmable
90limit or is too low to be measured.
91
92
93Temperature Monitoring
94----------------------
95
96Temperatures are reported in degrees Celsius. Each temperature measured
97has a high limit, those crossing triggers an alarm. There is an associated
98hysteresis value, below which the temperature has to drop before the
99alarm is cleared.
100
101All temperature channels are external, there is no embedded temperature
102sensor. Each channel can be used for connecting either a thermal diode
103or a thermistor. The driver reports the currently selected mode, but
104doesn't allow changing it. In theory, the BIOS should have configured
105everything properly.
diff --git a/Documentation/hwmon/it87 b/Documentation/hwmon/it87
index 7f42e441c645..9555be1ed999 100644
--- a/Documentation/hwmon/it87
+++ b/Documentation/hwmon/it87
@@ -9,7 +9,7 @@ Supported chips:
9 http://www.ite.com.tw/ 9 http://www.ite.com.tw/
10 * IT8712F 10 * IT8712F
11 Prefix: 'it8712' 11 Prefix: 'it8712'
12 Addresses scanned: I2C 0x28 - 0x2f 12 Addresses scanned: I2C 0x2d
13 from Super I/O config space (8 I/O ports) 13 from Super I/O config space (8 I/O ports)
14 Datasheet: Publicly available at the ITE website 14 Datasheet: Publicly available at the ITE website
15 http://www.ite.com.tw/ 15 http://www.ite.com.tw/
diff --git a/Documentation/hwmon/sysfs-interface b/Documentation/hwmon/sysfs-interface
index 764cdc5480e7..a0d0ab24288e 100644
--- a/Documentation/hwmon/sysfs-interface
+++ b/Documentation/hwmon/sysfs-interface
@@ -179,11 +179,12 @@ temp[1-*]_auto_point[1-*]_temp_hyst
179**************** 179****************
180 180
181temp[1-3]_type Sensor type selection. 181temp[1-3]_type Sensor type selection.
182 Integers 1, 2, 3 or thermistor Beta value (3435) 182 Integers 1 to 4 or thermistor Beta value (typically 3435)
183 Read/Write. 183 Read/Write.
184 1: PII/Celeron Diode 184 1: PII/Celeron Diode
185 2: 3904 transistor 185 2: 3904 transistor
186 3: thermal diode 186 3: thermal diode
187 4: thermistor (default/unknown Beta)
187 Not all types are supported by all chips 188 Not all types are supported by all chips
188 189
189temp[1-4]_max Temperature max value. 190temp[1-4]_max Temperature max value.
@@ -261,6 +262,21 @@ alarms Alarm bitmask.
261 of individual bits. 262 of individual bits.
262 Bits are defined in kernel/include/sensors.h. 263 Bits are defined in kernel/include/sensors.h.
263 264
265alarms_in Alarm bitmask relative to in (voltage) channels
266 Read only
267 A '1' bit means an alarm, LSB corresponds to in0 and so on
268 Prefered to 'alarms' for newer chips
269
270alarms_fan Alarm bitmask relative to fan channels
271 Read only
272 A '1' bit means an alarm, LSB corresponds to fan1 and so on
273 Prefered to 'alarms' for newer chips
274
275alarms_temp Alarm bitmask relative to temp (temperature) channels
276 Read only
277 A '1' bit means an alarm, LSB corresponds to temp1 and so on
278 Prefered to 'alarms' for newer chips
279
264beep_enable Beep/interrupt enable 280beep_enable Beep/interrupt enable
265 0 to disable. 281 0 to disable.
266 1 to enable. 282 1 to enable.
diff --git a/Documentation/i2c/busses/i2c-sis69x b/Documentation/i2c/busses/i2c-sis96x
index b88953dfd580..00a009b977e9 100644
--- a/Documentation/i2c/busses/i2c-sis69x
+++ b/Documentation/i2c/busses/i2c-sis96x
@@ -7,7 +7,7 @@ Supported adapters:
7 Any combination of these host bridges: 7 Any combination of these host bridges:
8 645, 645DX (aka 646), 648, 650, 651, 655, 735, 745, 746 8 645, 645DX (aka 646), 648, 650, 651, 655, 735, 745, 746
9 and these south bridges: 9 and these south bridges:
10 961, 962, 963(L) 10 961, 962, 963(L)
11 11
12Author: Mark M. Hoffman <mhoffman@lightlink.com> 12Author: Mark M. Hoffman <mhoffman@lightlink.com>
13 13
@@ -29,7 +29,7 @@ The command "lspci" as root should produce something like these lines:
29 29
30or perhaps this... 30or perhaps this...
31 31
3200:00.0 Host bridge: Silicon Integrated Systems [SiS]: Unknown device 0645 3200:00.0 Host bridge: Silicon Integrated Systems [SiS]: Unknown device 0645
3300:02.0 ISA bridge: Silicon Integrated Systems [SiS]: Unknown device 0961 3300:02.0 ISA bridge: Silicon Integrated Systems [SiS]: Unknown device 0961
3400:02.1 SMBus: Silicon Integrated Systems [SiS]: Unknown device 0016 3400:02.1 SMBus: Silicon Integrated Systems [SiS]: Unknown device 0016
35 35
diff --git a/MAINTAINERS b/MAINTAINERS
index a05aefdea602..b22db521cec1 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -931,6 +931,12 @@ M: sct@redhat.com, akpm@osdl.org, adilger@clusterfs.com
931L: ext3-users@redhat.com 931L: ext3-users@redhat.com
932S: Maintained 932S: Maintained
933 933
934F71805F HARDWARE MONITORING DRIVER
935P: Jean Delvare
936M: khali@linux-fr.org
937L: lm-sensors@lm-sensors.org
938S: Maintained
939
934FARSYNC SYNCHRONOUS DRIVER 940FARSYNC SYNCHRONOUS DRIVER
935P: Kevin Curtis 941P: Kevin Curtis
936M: kevin.curtis@farsite.co.uk 942M: kevin.curtis@farsite.co.uk
diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig
index c58295914365..7230d4e08196 100644
--- a/drivers/hwmon/Kconfig
+++ b/drivers/hwmon/Kconfig
@@ -113,6 +113,16 @@ config SENSORS_DS1621
113 This driver can also be built as a module. If so, the module 113 This driver can also be built as a module. If so, the module
114 will be called ds1621. 114 will be called ds1621.
115 115
116config SENSORS_F71805F
117 tristate "Fintek F71805F/FG"
118 depends on HWMON && EXPERIMENTAL
119 help
120 If you say yes here you get support for hardware monitoring
121 features of the Fintek F71805F/FG chips.
122
123 This driver can also be built as a module. If so, the module
124 will be called f71805f.
125
116config SENSORS_FSCHER 126config SENSORS_FSCHER
117 tristate "FSC Hermes" 127 tristate "FSC Hermes"
118 depends on HWMON && I2C && EXPERIMENTAL 128 depends on HWMON && I2C && EXPERIMENTAL
diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile
index 06d4a1d14105..fbdb8d911a72 100644
--- a/drivers/hwmon/Makefile
+++ b/drivers/hwmon/Makefile
@@ -18,6 +18,7 @@ obj-$(CONFIG_SENSORS_ADM1031) += adm1031.o
18obj-$(CONFIG_SENSORS_ADM9240) += adm9240.o 18obj-$(CONFIG_SENSORS_ADM9240) += adm9240.o
19obj-$(CONFIG_SENSORS_ATXP1) += atxp1.o 19obj-$(CONFIG_SENSORS_ATXP1) += atxp1.o
20obj-$(CONFIG_SENSORS_DS1621) += ds1621.o 20obj-$(CONFIG_SENSORS_DS1621) += ds1621.o
21obj-$(CONFIG_SENSORS_F71805F) += f71805f.o
21obj-$(CONFIG_SENSORS_FSCHER) += fscher.o 22obj-$(CONFIG_SENSORS_FSCHER) += fscher.o
22obj-$(CONFIG_SENSORS_FSCPOS) += fscpos.o 23obj-$(CONFIG_SENSORS_FSCPOS) += fscpos.o
23obj-$(CONFIG_SENSORS_GL518SM) += gl518sm.o 24obj-$(CONFIG_SENSORS_GL518SM) += gl518sm.o
diff --git a/drivers/hwmon/f71805f.c b/drivers/hwmon/f71805f.c
new file mode 100644
index 000000000000..e029e0a94ecc
--- /dev/null
+++ b/drivers/hwmon/f71805f.c
@@ -0,0 +1,908 @@
1/*
2 * f71805f.c - driver for the Fintek F71805F/FG Super-I/O chip integrated
3 * hardware monitoring features
4 * Copyright (C) 2005 Jean Delvare <khali@linux-fr.org>
5 *
6 * The F71805F/FG is a LPC Super-I/O chip made by Fintek. It integrates
7 * complete hardware monitoring features: voltage, fan and temperature
8 * sensors, and manual and automatic fan speed control.
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
14 *
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
19 *
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 */
24
25#include <linux/module.h>
26#include <linux/init.h>
27#include <linux/slab.h>
28#include <linux/jiffies.h>
29#include <linux/platform_device.h>
30#include <linux/hwmon.h>
31#include <linux/hwmon-sysfs.h>
32#include <linux/err.h>
33#include <asm/io.h>
34
35static struct platform_device *pdev;
36
37#define DRVNAME "f71805f"
38
39/*
40 * Super-I/O constants and functions
41 */
42
43#define F71805F_LD_HWM 0x04
44
45#define SIO_REG_LDSEL 0x07 /* Logical device select */
46#define SIO_REG_DEVID 0x20 /* Device ID (2 bytes) */
47#define SIO_REG_DEVREV 0x22 /* Device revision */
48#define SIO_REG_MANID 0x23 /* Fintek ID (2 bytes) */
49#define SIO_REG_ENABLE 0x30 /* Logical device enable */
50#define SIO_REG_ADDR 0x60 /* Logical device address (2 bytes) */
51
52#define SIO_FINTEK_ID 0x1934
53#define SIO_F71805F_ID 0x0406
54
55static inline int
56superio_inb(int base, int reg)
57{
58 outb(reg, base);
59 return inb(base + 1);
60}
61
62static int
63superio_inw(int base, int reg)
64{
65 int val;
66 outb(reg++, base);
67 val = inb(base + 1) << 8;
68 outb(reg, base);
69 val |= inb(base + 1);
70 return val;
71}
72
73static inline void
74superio_select(int base, int ld)
75{
76 outb(SIO_REG_LDSEL, base);
77 outb(ld, base + 1);
78}
79
80static inline void
81superio_enter(int base)
82{
83 outb(0x87, base);
84 outb(0x87, base);
85}
86
87static inline void
88superio_exit(int base)
89{
90 outb(0xaa, base);
91}
92
93/*
94 * ISA constants
95 */
96
97#define REGION_LENGTH 2
98#define ADDR_REG_OFFSET 0
99#define DATA_REG_OFFSET 1
100
101static struct resource f71805f_resource __initdata = {
102 .flags = IORESOURCE_IO,
103};
104
105/*
106 * Registers
107 */
108
109/* in nr from 0 to 8 (8-bit values) */
110#define F71805F_REG_IN(nr) (0x10 + (nr))
111#define F71805F_REG_IN_HIGH(nr) (0x40 + 2 * (nr))
112#define F71805F_REG_IN_LOW(nr) (0x41 + 2 * (nr))
113/* fan nr from 0 to 2 (12-bit values, two registers) */
114#define F71805F_REG_FAN(nr) (0x20 + 2 * (nr))
115#define F71805F_REG_FAN_LOW(nr) (0x28 + 2 * (nr))
116#define F71805F_REG_FAN_CTRL(nr) (0x60 + 16 * (nr))
117/* temp nr from 0 to 2 (8-bit values) */
118#define F71805F_REG_TEMP(nr) (0x1B + (nr))
119#define F71805F_REG_TEMP_HIGH(nr) (0x54 + 2 * (nr))
120#define F71805F_REG_TEMP_HYST(nr) (0x55 + 2 * (nr))
121#define F71805F_REG_TEMP_MODE 0x01
122
123#define F71805F_REG_START 0x00
124/* status nr from 0 to 2 */
125#define F71805F_REG_STATUS(nr) (0x36 + (nr))
126
127/*
128 * Data structures and manipulation thereof
129 */
130
131struct f71805f_data {
132 unsigned short addr;
133 const char *name;
134 struct semaphore lock;
135 struct class_device *class_dev;
136
137 struct semaphore update_lock;
138 char valid; /* !=0 if following fields are valid */
139 unsigned long last_updated; /* In jiffies */
140 unsigned long last_limits; /* In jiffies */
141
142 /* Register values */
143 u8 in[9];
144 u8 in_high[9];
145 u8 in_low[9];
146 u16 fan[3];
147 u16 fan_low[3];
148 u8 fan_enabled; /* Read once at init time */
149 u8 temp[3];
150 u8 temp_high[3];
151 u8 temp_hyst[3];
152 u8 temp_mode;
153 u8 alarms[3];
154};
155
156static inline long in_from_reg(u8 reg)
157{
158 return (reg * 8);
159}
160
161/* The 2 least significant bits are not used */
162static inline u8 in_to_reg(long val)
163{
164 if (val <= 0)
165 return 0;
166 if (val >= 2016)
167 return 0xfc;
168 return (((val + 16) / 32) << 2);
169}
170
171/* in0 is downscaled by a factor 2 internally */
172static inline long in0_from_reg(u8 reg)
173{
174 return (reg * 16);
175}
176
177static inline u8 in0_to_reg(long val)
178{
179 if (val <= 0)
180 return 0;
181 if (val >= 4032)
182 return 0xfc;
183 return (((val + 32) / 64) << 2);
184}
185
186/* The 4 most significant bits are not used */
187static inline long fan_from_reg(u16 reg)
188{
189 reg &= 0xfff;
190 if (!reg || reg == 0xfff)
191 return 0;
192 return (1500000 / reg);
193}
194
195static inline u16 fan_to_reg(long rpm)
196{
197 /* If the low limit is set below what the chip can measure,
198 store the largest possible 12-bit value in the registers,
199 so that no alarm will ever trigger. */
200 if (rpm < 367)
201 return 0xfff;
202 return (1500000 / rpm);
203}
204
205static inline long temp_from_reg(u8 reg)
206{
207 return (reg * 1000);
208}
209
210static inline u8 temp_to_reg(long val)
211{
212 if (val < 0)
213 val = 0;
214 else if (val > 1000 * 0xff)
215 val = 0xff;
216 return ((val + 500) / 1000);
217}
218
219/*
220 * Device I/O access
221 */
222
223static u8 f71805f_read8(struct f71805f_data *data, u8 reg)
224{
225 u8 val;
226
227 down(&data->lock);
228 outb(reg, data->addr + ADDR_REG_OFFSET);
229 val = inb(data->addr + DATA_REG_OFFSET);
230 up(&data->lock);
231
232 return val;
233}
234
235static void f71805f_write8(struct f71805f_data *data, u8 reg, u8 val)
236{
237 down(&data->lock);
238 outb(reg, data->addr + ADDR_REG_OFFSET);
239 outb(val, data->addr + DATA_REG_OFFSET);
240 up(&data->lock);
241}
242
243/* It is important to read the MSB first, because doing so latches the
244 value of the LSB, so we are sure both bytes belong to the same value. */
245static u16 f71805f_read16(struct f71805f_data *data, u8 reg)
246{
247 u16 val;
248
249 down(&data->lock);
250 outb(reg, data->addr + ADDR_REG_OFFSET);
251 val = inb(data->addr + DATA_REG_OFFSET) << 8;
252 outb(++reg, data->addr + ADDR_REG_OFFSET);
253 val |= inb(data->addr + DATA_REG_OFFSET);
254 up(&data->lock);
255
256 return val;
257}
258
259static void f71805f_write16(struct f71805f_data *data, u8 reg, u16 val)
260{
261 down(&data->lock);
262 outb(reg, data->addr + ADDR_REG_OFFSET);
263 outb(val >> 8, data->addr + DATA_REG_OFFSET);
264 outb(++reg, data->addr + ADDR_REG_OFFSET);
265 outb(val & 0xff, data->addr + DATA_REG_OFFSET);
266 up(&data->lock);
267}
268
269static struct f71805f_data *f71805f_update_device(struct device *dev)
270{
271 struct f71805f_data *data = dev_get_drvdata(dev);
272 int nr;
273
274 down(&data->update_lock);
275
276 /* Limit registers cache is refreshed after 60 seconds */
277 if (time_after(jiffies, data->last_updated + 60 * HZ)
278 || !data->valid) {
279 for (nr = 0; nr < 9; nr++) {
280 data->in_high[nr] = f71805f_read8(data,
281 F71805F_REG_IN_HIGH(nr));
282 data->in_low[nr] = f71805f_read8(data,
283 F71805F_REG_IN_LOW(nr));
284 }
285 for (nr = 0; nr < 3; nr++) {
286 if (data->fan_enabled & (1 << nr))
287 data->fan_low[nr] = f71805f_read16(data,
288 F71805F_REG_FAN_LOW(nr));
289 }
290 for (nr = 0; nr < 3; nr++) {
291 data->temp_high[nr] = f71805f_read8(data,
292 F71805F_REG_TEMP_HIGH(nr));
293 data->temp_hyst[nr] = f71805f_read8(data,
294 F71805F_REG_TEMP_HYST(nr));
295 }
296 data->temp_mode = f71805f_read8(data, F71805F_REG_TEMP_MODE);
297
298 data->last_limits = jiffies;
299 }
300
301 /* Measurement registers cache is refreshed after 1 second */
302 if (time_after(jiffies, data->last_updated + HZ)
303 || !data->valid) {
304 for (nr = 0; nr < 9; nr++) {
305 data->in[nr] = f71805f_read8(data,
306 F71805F_REG_IN(nr));
307 }
308 for (nr = 0; nr < 3; nr++) {
309 if (data->fan_enabled & (1 << nr))
310 data->fan[nr] = f71805f_read16(data,
311 F71805F_REG_FAN(nr));
312 }
313 for (nr = 0; nr < 3; nr++) {
314 data->temp[nr] = f71805f_read8(data,
315 F71805F_REG_TEMP(nr));
316 }
317 for (nr = 0; nr < 3; nr++) {
318 data->alarms[nr] = f71805f_read8(data,
319 F71805F_REG_STATUS(nr));
320 }
321
322 data->last_updated = jiffies;
323 data->valid = 1;
324 }
325
326 up(&data->update_lock);
327
328 return data;
329}
330
331/*
332 * Sysfs interface
333 */
334
335static ssize_t show_in0(struct device *dev, struct device_attribute *devattr,
336 char *buf)
337{
338 struct f71805f_data *data = f71805f_update_device(dev);
339
340 return sprintf(buf, "%ld\n", in0_from_reg(data->in[0]));
341}
342
343static ssize_t show_in0_max(struct device *dev, struct device_attribute
344 *devattr, char *buf)
345{
346 struct f71805f_data *data = f71805f_update_device(dev);
347
348 return sprintf(buf, "%ld\n", in0_from_reg(data->in_high[0]));
349}
350
351static ssize_t show_in0_min(struct device *dev, struct device_attribute
352 *devattr, char *buf)
353{
354 struct f71805f_data *data = f71805f_update_device(dev);
355
356 return sprintf(buf, "%ld\n", in0_from_reg(data->in_low[0]));
357}
358
359static ssize_t set_in0_max(struct device *dev, struct device_attribute
360 *devattr, const char *buf, size_t count)
361{
362 struct f71805f_data *data = dev_get_drvdata(dev);
363 long val = simple_strtol(buf, NULL, 10);
364
365 down(&data->update_lock);
366 data->in_high[0] = in0_to_reg(val);
367 f71805f_write8(data, F71805F_REG_IN_HIGH(0), data->in_high[0]);
368 up(&data->update_lock);
369
370 return count;
371}
372
373static ssize_t set_in0_min(struct device *dev, struct device_attribute
374 *devattr, const char *buf, size_t count)
375{
376 struct f71805f_data *data = dev_get_drvdata(dev);
377 long val = simple_strtol(buf, NULL, 10);
378
379 down(&data->update_lock);
380 data->in_low[0] = in0_to_reg(val);
381 f71805f_write8(data, F71805F_REG_IN_LOW(0), data->in_low[0]);
382 up(&data->update_lock);
383
384 return count;
385}
386
387static DEVICE_ATTR(in0_input, S_IRUGO, show_in0, NULL);
388static DEVICE_ATTR(in0_max, S_IRUGO| S_IWUSR, show_in0_max, set_in0_max);
389static DEVICE_ATTR(in0_min, S_IRUGO| S_IWUSR, show_in0_min, set_in0_min);
390
391static ssize_t show_in(struct device *dev, struct device_attribute *devattr,
392 char *buf)
393{
394 struct f71805f_data *data = f71805f_update_device(dev);
395 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
396 int nr = attr->index;
397
398 return sprintf(buf, "%ld\n", in_from_reg(data->in[nr]));
399}
400
401static ssize_t show_in_max(struct device *dev, struct device_attribute
402 *devattr, char *buf)
403{
404 struct f71805f_data *data = f71805f_update_device(dev);
405 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
406 int nr = attr->index;
407
408 return sprintf(buf, "%ld\n", in_from_reg(data->in_high[nr]));
409}
410
411static ssize_t show_in_min(struct device *dev, struct device_attribute
412 *devattr, char *buf)
413{
414 struct f71805f_data *data = f71805f_update_device(dev);
415 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
416 int nr = attr->index;
417
418 return sprintf(buf, "%ld\n", in_from_reg(data->in_low[nr]));
419}
420
421static ssize_t set_in_max(struct device *dev, struct device_attribute
422 *devattr, const char *buf, size_t count)
423{
424 struct f71805f_data *data = dev_get_drvdata(dev);
425 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
426 int nr = attr->index;
427 long val = simple_strtol(buf, NULL, 10);
428
429 down(&data->update_lock);
430 data->in_high[nr] = in_to_reg(val);
431 f71805f_write8(data, F71805F_REG_IN_HIGH(nr), data->in_high[nr]);
432 up(&data->update_lock);
433
434 return count;
435}
436
437static ssize_t set_in_min(struct device *dev, struct device_attribute
438 *devattr, const char *buf, size_t count)
439{
440 struct f71805f_data *data = dev_get_drvdata(dev);
441 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
442 int nr = attr->index;
443 long val = simple_strtol(buf, NULL, 10);
444
445 down(&data->update_lock);
446 data->in_low[nr] = in_to_reg(val);
447 f71805f_write8(data, F71805F_REG_IN_LOW(nr), data->in_low[nr]);
448 up(&data->update_lock);
449
450 return count;
451}
452
453#define sysfs_in(offset) \
454static SENSOR_DEVICE_ATTR(in##offset##_input, S_IRUGO, \
455 show_in, NULL, offset); \
456static SENSOR_DEVICE_ATTR(in##offset##_max, S_IRUGO | S_IWUSR, \
457 show_in_max, set_in_max, offset); \
458static SENSOR_DEVICE_ATTR(in##offset##_min, S_IRUGO | S_IWUSR, \
459 show_in_min, set_in_min, offset)
460
461sysfs_in(1);
462sysfs_in(2);
463sysfs_in(3);
464sysfs_in(4);
465sysfs_in(5);
466sysfs_in(6);
467sysfs_in(7);
468sysfs_in(8);
469
470static ssize_t show_fan(struct device *dev, struct device_attribute *devattr,
471 char *buf)
472{
473 struct f71805f_data *data = f71805f_update_device(dev);
474 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
475 int nr = attr->index;
476
477 return sprintf(buf, "%ld\n", fan_from_reg(data->fan[nr]));
478}
479
480static ssize_t show_fan_min(struct device *dev, struct device_attribute
481 *devattr, char *buf)
482{
483 struct f71805f_data *data = f71805f_update_device(dev);
484 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
485 int nr = attr->index;
486
487 return sprintf(buf, "%ld\n", fan_from_reg(data->fan_low[nr]));
488}
489
490static ssize_t set_fan_min(struct device *dev, struct device_attribute
491 *devattr, const char *buf, size_t count)
492{
493 struct f71805f_data *data = dev_get_drvdata(dev);
494 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
495 int nr = attr->index;
496 long val = simple_strtol(buf, NULL, 10);
497
498 down(&data->update_lock);
499 data->fan_low[nr] = fan_to_reg(val);
500 f71805f_write16(data, F71805F_REG_FAN_LOW(nr), data->fan_low[nr]);
501 up(&data->update_lock);
502
503 return count;
504}
505
506#define sysfs_fan(offset) \
507static SENSOR_DEVICE_ATTR(fan##offset##_input, S_IRUGO, \
508 show_fan, NULL, offset - 1); \
509static SENSOR_DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \
510 show_fan_min, set_fan_min, offset - 1)
511
512sysfs_fan(1);
513sysfs_fan(2);
514sysfs_fan(3);
515
516static ssize_t show_temp(struct device *dev, struct device_attribute *devattr,
517 char *buf)
518{
519 struct f71805f_data *data = f71805f_update_device(dev);
520 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
521 int nr = attr->index;
522
523 return sprintf(buf, "%ld\n", temp_from_reg(data->temp[nr]));
524}
525
526static ssize_t show_temp_max(struct device *dev, struct device_attribute
527 *devattr, char *buf)
528{
529 struct f71805f_data *data = f71805f_update_device(dev);
530 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
531 int nr = attr->index;
532
533 return sprintf(buf, "%ld\n", temp_from_reg(data->temp_high[nr]));
534}
535
536static ssize_t show_temp_hyst(struct device *dev, struct device_attribute
537 *devattr, char *buf)
538{
539 struct f71805f_data *data = f71805f_update_device(dev);
540 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
541 int nr = attr->index;
542
543 return sprintf(buf, "%ld\n", temp_from_reg(data->temp_hyst[nr]));
544}
545
546static ssize_t show_temp_type(struct device *dev, struct device_attribute
547 *devattr, char *buf)
548{
549 struct f71805f_data *data = f71805f_update_device(dev);
550 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
551 int nr = attr->index;
552
553 /* 3 is diode, 4 is thermistor */
554 return sprintf(buf, "%u\n", (data->temp_mode & (1 << nr)) ? 3 : 4);
555}
556
557static ssize_t set_temp_max(struct device *dev, struct device_attribute
558 *devattr, const char *buf, size_t count)
559{
560 struct f71805f_data *data = dev_get_drvdata(dev);
561 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
562 int nr = attr->index;
563 long val = simple_strtol(buf, NULL, 10);
564
565 down(&data->update_lock);
566 data->temp_high[nr] = temp_to_reg(val);
567 f71805f_write8(data, F71805F_REG_TEMP_HIGH(nr), data->temp_high[nr]);
568 up(&data->update_lock);
569
570 return count;
571}
572
573static ssize_t set_temp_hyst(struct device *dev, struct device_attribute
574 *devattr, const char *buf, size_t count)
575{
576 struct f71805f_data *data = dev_get_drvdata(dev);
577 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
578 int nr = attr->index;
579 long val = simple_strtol(buf, NULL, 10);
580
581 down(&data->update_lock);
582 data->temp_hyst[nr] = temp_to_reg(val);
583 f71805f_write8(data, F71805F_REG_TEMP_HYST(nr), data->temp_hyst[nr]);
584 up(&data->update_lock);
585
586 return count;
587}
588
589#define sysfs_temp(offset) \
590static SENSOR_DEVICE_ATTR(temp##offset##_input, S_IRUGO, \
591 show_temp, NULL, offset - 1); \
592static SENSOR_DEVICE_ATTR(temp##offset##_max, S_IRUGO | S_IWUSR, \
593 show_temp_max, set_temp_max, offset - 1); \
594static SENSOR_DEVICE_ATTR(temp##offset##_max_hyst, S_IRUGO | S_IWUSR, \
595 show_temp_hyst, set_temp_hyst, offset - 1); \
596static SENSOR_DEVICE_ATTR(temp##offset##_type, S_IRUGO, \
597 show_temp_type, NULL, offset - 1)
598
599sysfs_temp(1);
600sysfs_temp(2);
601sysfs_temp(3);
602
603static ssize_t show_alarms_in(struct device *dev, struct device_attribute
604 *devattr, char *buf)
605{
606 struct f71805f_data *data = f71805f_update_device(dev);
607
608 return sprintf(buf, "%d\n", data->alarms[0] |
609 ((data->alarms[1] & 0x01) << 8));
610}
611
612static ssize_t show_alarms_fan(struct device *dev, struct device_attribute
613 *devattr, char *buf)
614{
615 struct f71805f_data *data = f71805f_update_device(dev);
616
617 return sprintf(buf, "%d\n", data->alarms[2] & 0x07);
618}
619
620static ssize_t show_alarms_temp(struct device *dev, struct device_attribute
621 *devattr, char *buf)
622{
623 struct f71805f_data *data = f71805f_update_device(dev);
624
625 return sprintf(buf, "%d\n", (data->alarms[1] >> 3) & 0x07);
626}
627
628static DEVICE_ATTR(alarms_in, S_IRUGO, show_alarms_in, NULL);
629static DEVICE_ATTR(alarms_fan, S_IRUGO, show_alarms_fan, NULL);
630static DEVICE_ATTR(alarms_temp, S_IRUGO, show_alarms_temp, NULL);
631
632static ssize_t show_name(struct device *dev, struct device_attribute
633 *devattr, char *buf)
634{
635 struct f71805f_data *data = dev_get_drvdata(dev);
636
637 return sprintf(buf, "%s\n", data->name);
638}
639
640static DEVICE_ATTR(name, S_IRUGO, show_name, NULL);
641
642/*
643 * Device registration and initialization
644 */
645
646static void __devinit f71805f_init_device(struct f71805f_data *data)
647{
648 u8 reg;
649 int i;
650
651 reg = f71805f_read8(data, F71805F_REG_START);
652 if ((reg & 0x41) != 0x01) {
653 printk(KERN_DEBUG DRVNAME ": Starting monitoring "
654 "operations\n");
655 f71805f_write8(data, F71805F_REG_START, (reg | 0x01) & ~0x40);
656 }
657
658 /* Fan monitoring can be disabled. If it is, we won't be polling
659 the register values, and won't create the related sysfs files. */
660 for (i = 0; i < 3; i++) {
661 reg = f71805f_read8(data, F71805F_REG_FAN_CTRL(i));
662 if (!(reg & 0x80))
663 data->fan_enabled |= (1 << i);
664 }
665}
666
667static int __devinit f71805f_probe(struct platform_device *pdev)
668{
669 struct f71805f_data *data;
670 struct resource *res;
671 int err;
672
673 if (!(data = kzalloc(sizeof(struct f71805f_data), GFP_KERNEL))) {
674 err = -ENOMEM;
675 printk(KERN_ERR DRVNAME ": Out of memory\n");
676 goto exit;
677 }
678
679 res = platform_get_resource(pdev, IORESOURCE_IO, 0);
680 data->addr = res->start;
681 init_MUTEX(&data->lock);
682 data->name = "f71805f";
683 init_MUTEX(&data->update_lock);
684
685 platform_set_drvdata(pdev, data);
686
687 data->class_dev = hwmon_device_register(&pdev->dev);
688 if (IS_ERR(data->class_dev)) {
689 err = PTR_ERR(data->class_dev);
690 dev_err(&pdev->dev, "Class registration failed (%d)\n", err);
691 goto exit_free;
692 }
693
694 /* Initialize the F71805F chip */
695 f71805f_init_device(data);
696
697 /* Register sysfs interface files */
698 device_create_file(&pdev->dev, &dev_attr_in0_input);
699 device_create_file(&pdev->dev, &dev_attr_in0_max);
700 device_create_file(&pdev->dev, &dev_attr_in0_min);
701 device_create_file(&pdev->dev, &sensor_dev_attr_in1_input.dev_attr);
702 device_create_file(&pdev->dev, &sensor_dev_attr_in2_input.dev_attr);
703 device_create_file(&pdev->dev, &sensor_dev_attr_in3_input.dev_attr);
704 device_create_file(&pdev->dev, &sensor_dev_attr_in4_input.dev_attr);
705 device_create_file(&pdev->dev, &sensor_dev_attr_in5_input.dev_attr);
706 device_create_file(&pdev->dev, &sensor_dev_attr_in6_input.dev_attr);
707 device_create_file(&pdev->dev, &sensor_dev_attr_in7_input.dev_attr);
708 device_create_file(&pdev->dev, &sensor_dev_attr_in8_input.dev_attr);
709 device_create_file(&pdev->dev, &sensor_dev_attr_in1_max.dev_attr);
710 device_create_file(&pdev->dev, &sensor_dev_attr_in2_max.dev_attr);
711 device_create_file(&pdev->dev, &sensor_dev_attr_in3_max.dev_attr);
712 device_create_file(&pdev->dev, &sensor_dev_attr_in4_max.dev_attr);
713 device_create_file(&pdev->dev, &sensor_dev_attr_in5_max.dev_attr);
714 device_create_file(&pdev->dev, &sensor_dev_attr_in6_max.dev_attr);
715 device_create_file(&pdev->dev, &sensor_dev_attr_in7_max.dev_attr);
716 device_create_file(&pdev->dev, &sensor_dev_attr_in8_max.dev_attr);
717 device_create_file(&pdev->dev, &sensor_dev_attr_in1_min.dev_attr);
718 device_create_file(&pdev->dev, &sensor_dev_attr_in2_min.dev_attr);
719 device_create_file(&pdev->dev, &sensor_dev_attr_in3_min.dev_attr);
720 device_create_file(&pdev->dev, &sensor_dev_attr_in4_min.dev_attr);
721 device_create_file(&pdev->dev, &sensor_dev_attr_in5_min.dev_attr);
722 device_create_file(&pdev->dev, &sensor_dev_attr_in6_min.dev_attr);
723 device_create_file(&pdev->dev, &sensor_dev_attr_in7_min.dev_attr);
724 device_create_file(&pdev->dev, &sensor_dev_attr_in8_min.dev_attr);
725 if (data->fan_enabled & (1 << 0)) {
726 device_create_file(&pdev->dev,
727 &sensor_dev_attr_fan1_input.dev_attr);
728 device_create_file(&pdev->dev,
729 &sensor_dev_attr_fan1_min.dev_attr);
730 }
731 if (data->fan_enabled & (1 << 1)) {
732 device_create_file(&pdev->dev,
733 &sensor_dev_attr_fan2_input.dev_attr);
734 device_create_file(&pdev->dev,
735 &sensor_dev_attr_fan2_min.dev_attr);
736 }
737 if (data->fan_enabled & (1 << 2)) {
738 device_create_file(&pdev->dev,
739 &sensor_dev_attr_fan3_input.dev_attr);
740 device_create_file(&pdev->dev,
741 &sensor_dev_attr_fan3_min.dev_attr);
742 }
743 device_create_file(&pdev->dev,
744 &sensor_dev_attr_temp1_input.dev_attr);
745 device_create_file(&pdev->dev,
746 &sensor_dev_attr_temp2_input.dev_attr);
747 device_create_file(&pdev->dev,
748 &sensor_dev_attr_temp3_input.dev_attr);
749 device_create_file(&pdev->dev, &sensor_dev_attr_temp1_max.dev_attr);
750 device_create_file(&pdev->dev, &sensor_dev_attr_temp2_max.dev_attr);
751 device_create_file(&pdev->dev, &sensor_dev_attr_temp3_max.dev_attr);
752 device_create_file(&pdev->dev,
753 &sensor_dev_attr_temp1_max_hyst.dev_attr);
754 device_create_file(&pdev->dev,
755 &sensor_dev_attr_temp2_max_hyst.dev_attr);
756 device_create_file(&pdev->dev,
757 &sensor_dev_attr_temp3_max_hyst.dev_attr);
758 device_create_file(&pdev->dev, &sensor_dev_attr_temp1_type.dev_attr);
759 device_create_file(&pdev->dev, &sensor_dev_attr_temp2_type.dev_attr);
760 device_create_file(&pdev->dev, &sensor_dev_attr_temp3_type.dev_attr);
761 device_create_file(&pdev->dev, &dev_attr_alarms_in);
762 device_create_file(&pdev->dev, &dev_attr_alarms_fan);
763 device_create_file(&pdev->dev, &dev_attr_alarms_temp);
764 device_create_file(&pdev->dev, &dev_attr_name);
765
766 return 0;
767
768exit_free:
769 kfree(data);
770exit:
771 return err;
772}
773
774static int __devexit f71805f_remove(struct platform_device *pdev)
775{
776 struct f71805f_data *data = platform_get_drvdata(pdev);
777
778 platform_set_drvdata(pdev, NULL);
779 hwmon_device_unregister(data->class_dev);
780 kfree(data);
781
782 return 0;
783}
784
785static struct platform_driver f71805f_driver = {
786 .driver = {
787 .owner = THIS_MODULE,
788 .name = DRVNAME,
789 },
790 .probe = f71805f_probe,
791 .remove = __devexit_p(f71805f_remove),
792};
793
794static int __init f71805f_device_add(unsigned short address)
795{
796 int err;
797
798 pdev = platform_device_alloc(DRVNAME, address);
799 if (!pdev) {
800 err = -ENOMEM;
801 printk(KERN_ERR DRVNAME ": Device allocation failed\n");
802 goto exit;
803 }
804
805 f71805f_resource.start = address;
806 f71805f_resource.end = address + REGION_LENGTH - 1;
807 f71805f_resource.name = pdev->name;
808 err = platform_device_add_resources(pdev, &f71805f_resource, 1);
809 if (err) {
810 printk(KERN_ERR DRVNAME ": Device resource addition failed "
811 "(%d)\n", err);
812 goto exit_device_put;
813 }
814
815 err = platform_device_add(pdev);
816 if (err) {
817 printk(KERN_ERR DRVNAME ": Device addition failed (%d)\n",
818 err);
819 goto exit_device_put;
820 }
821
822 return 0;
823
824exit_device_put:
825 platform_device_put(pdev);
826exit:
827 return err;
828}
829
830static int __init f71805f_find(int sioaddr, unsigned short *address)
831{
832 int err = -ENODEV;
833 u16 devid;
834
835 superio_enter(sioaddr);
836
837 devid = superio_inw(sioaddr, SIO_REG_MANID);
838 if (devid != SIO_FINTEK_ID)
839 goto exit;
840
841 devid = superio_inw(sioaddr, SIO_REG_DEVID);
842 if (devid != SIO_F71805F_ID) {
843 printk(KERN_INFO DRVNAME ": Unsupported Fintek device, "
844 "skipping\n");
845 goto exit;
846 }
847
848 superio_select(sioaddr, F71805F_LD_HWM);
849 if (!(superio_inb(sioaddr, SIO_REG_ENABLE) & 0x01)) {
850 printk(KERN_WARNING DRVNAME ": Device not activated, "
851 "skipping\n");
852 goto exit;
853 }
854
855 *address = superio_inw(sioaddr, SIO_REG_ADDR);
856 if (*address == 0) {
857 printk(KERN_WARNING DRVNAME ": Base address not set, "
858 "skipping\n");
859 goto exit;
860 }
861
862 err = 0;
863 printk(KERN_INFO DRVNAME ": Found F71805F chip at %#x, revision %u\n",
864 *address, superio_inb(sioaddr, SIO_REG_DEVREV));
865
866exit:
867 superio_exit(sioaddr);
868 return err;
869}
870
871static int __init f71805f_init(void)
872{
873 int err;
874 unsigned short address;
875
876 if (f71805f_find(0x2e, &address)
877 && f71805f_find(0x4e, &address))
878 return -ENODEV;
879
880 err = platform_driver_register(&f71805f_driver);
881 if (err)
882 goto exit;
883
884 /* Sets global pdev as a side effect */
885 err = f71805f_device_add(address);
886 if (err)
887 goto exit_driver;
888
889 return 0;
890
891exit_driver:
892 platform_driver_unregister(&f71805f_driver);
893exit:
894 return err;
895}
896
897static void __exit f71805f_exit(void)
898{
899 platform_device_unregister(pdev);
900 platform_driver_unregister(&f71805f_driver);
901}
902
903MODULE_AUTHOR("Jean Delvare <khali@linux-fr>");
904MODULE_LICENSE("GPL");
905MODULE_DESCRIPTION("F71805F hardware monitoring driver");
906
907module_init(f71805f_init);
908module_exit(f71805f_exit);
diff --git a/drivers/hwmon/it87.c b/drivers/hwmon/it87.c
index 0da7c9c508c3..e87d52c59940 100644
--- a/drivers/hwmon/it87.c
+++ b/drivers/hwmon/it87.c
@@ -45,8 +45,7 @@
45 45
46 46
47/* Addresses to scan */ 47/* Addresses to scan */
48static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 48static unsigned short normal_i2c[] = { 0x2d, I2C_CLIENT_END };
49 0x2e, 0x2f, I2C_CLIENT_END };
50static unsigned short isa_address; 49static unsigned short isa_address;
51 50
52/* Insmod parameters */ 51/* Insmod parameters */
@@ -830,6 +829,11 @@ static int it87_detect(struct i2c_adapter *adapter, int address, int kind)
830 if ((err = i2c_attach_client(new_client))) 829 if ((err = i2c_attach_client(new_client)))
831 goto ERROR2; 830 goto ERROR2;
832 831
832 if (!is_isa)
833 dev_info(&new_client->dev, "The I2C interface to IT87xxF "
834 "hardware monitoring chips is deprecated. Please "
835 "report if you still rely on it.\n");
836
833 /* Check PWM configuration */ 837 /* Check PWM configuration */
834 enable_pwm_interface = it87_check_pwm(new_client); 838 enable_pwm_interface = it87_check_pwm(new_client);
835 839
diff --git a/drivers/hwmon/lm77.c b/drivers/hwmon/lm77.c
index a2f420d01fb7..df9e02aaa70a 100644
--- a/drivers/hwmon/lm77.c
+++ b/drivers/hwmon/lm77.c
@@ -87,15 +87,15 @@ static struct i2c_driver lm77_driver = {
87 87
88/* In the temperature registers, the low 3 bits are not part of the 88/* In the temperature registers, the low 3 bits are not part of the
89 temperature values; they are the status bits. */ 89 temperature values; they are the status bits. */
90static inline u16 LM77_TEMP_TO_REG(int temp) 90static inline s16 LM77_TEMP_TO_REG(int temp)
91{ 91{
92 int ntemp = SENSORS_LIMIT(temp, LM77_TEMP_MIN, LM77_TEMP_MAX); 92 int ntemp = SENSORS_LIMIT(temp, LM77_TEMP_MIN, LM77_TEMP_MAX);
93 return (u16)((ntemp / 500) * 8); 93 return (ntemp / 500) * 8;
94} 94}
95 95
96static inline int LM77_TEMP_FROM_REG(u16 reg) 96static inline int LM77_TEMP_FROM_REG(s16 reg)
97{ 97{
98 return ((int)reg / 8) * 500; 98 return (reg / 8) * 500;
99} 99}
100 100
101/* sysfs stuff */ 101/* sysfs stuff */
diff --git a/drivers/hwmon/w83792d.c b/drivers/hwmon/w83792d.c
index b176bf0c4c7b..a2f6bb676235 100644
--- a/drivers/hwmon/w83792d.c
+++ b/drivers/hwmon/w83792d.c
@@ -303,10 +303,6 @@ struct w83792d_data {
303static int w83792d_attach_adapter(struct i2c_adapter *adapter); 303static int w83792d_attach_adapter(struct i2c_adapter *adapter);
304static int w83792d_detect(struct i2c_adapter *adapter, int address, int kind); 304static int w83792d_detect(struct i2c_adapter *adapter, int address, int kind);
305static int w83792d_detach_client(struct i2c_client *client); 305static int w83792d_detach_client(struct i2c_client *client);
306
307static int w83792d_read_value(struct i2c_client *client, u8 register);
308static int w83792d_write_value(struct i2c_client *client, u8 register,
309 u8 value);
310static struct w83792d_data *w83792d_update_device(struct device *dev); 306static struct w83792d_data *w83792d_update_device(struct device *dev);
311 307
312#ifdef DEBUG 308#ifdef DEBUG
@@ -329,6 +325,20 @@ static inline long in_count_from_reg(int nr, struct w83792d_data *data)
329 return ((data->in[nr] << 2) | ((data->low_bits >> (2 * nr)) & 0x03)); 325 return ((data->in[nr] << 2) | ((data->low_bits >> (2 * nr)) & 0x03));
330} 326}
331 327
328/* The SMBus locks itself. The Winbond W83792D chip has a bank register,
329 but the driver only accesses registers in bank 0, so we don't have
330 to switch banks and lock access between switches. */
331static inline int w83792d_read_value(struct i2c_client *client, u8 reg)
332{
333 return i2c_smbus_read_byte_data(client, reg);
334}
335
336static inline int
337w83792d_write_value(struct i2c_client *client, u8 reg, u8 value)
338{
339 return i2c_smbus_write_byte_data(client, reg, value);
340}
341
332/* following are the sysfs callback functions */ 342/* following are the sysfs callback functions */
333static ssize_t show_in(struct device *dev, struct device_attribute *attr, 343static ssize_t show_in(struct device *dev, struct device_attribute *attr,
334 char *buf) 344 char *buf)
@@ -1386,19 +1396,6 @@ w83792d_detach_client(struct i2c_client *client)
1386 return 0; 1396 return 0;
1387} 1397}
1388 1398
1389/* The SMBus locks itself. The Winbond W83792D chip has a bank register,
1390 but the driver only accesses registers in bank 0, so we don't have
1391 to switch banks and lock access between switches. */
1392static int w83792d_read_value(struct i2c_client *client, u8 reg)
1393{
1394 return i2c_smbus_read_byte_data(client, reg);
1395}
1396
1397static int w83792d_write_value(struct i2c_client *client, u8 reg, u8 value)
1398{
1399 return i2c_smbus_write_byte_data(client, reg, value);
1400}
1401
1402static void 1399static void
1403w83792d_init_client(struct i2c_client *client) 1400w83792d_init_client(struct i2c_client *client)
1404{ 1401{
diff --git a/drivers/i2c/algos/i2c-algo-sibyte.c b/drivers/i2c/algos/i2c-algo-sibyte.c
index 938848ae162d..3df3f09995c2 100644
--- a/drivers/i2c/algos/i2c-algo-sibyte.c
+++ b/drivers/i2c/algos/i2c-algo-sibyte.c
@@ -202,7 +202,7 @@ EXPORT_SYMBOL(i2c_sibyte_del_bus);
202#ifdef MODULE 202#ifdef MODULE
203MODULE_AUTHOR("Kip Walker, Broadcom Corp."); 203MODULE_AUTHOR("Kip Walker, Broadcom Corp.");
204MODULE_DESCRIPTION("SiByte I2C-Bus algorithm"); 204MODULE_DESCRIPTION("SiByte I2C-Bus algorithm");
205MODULE_PARM(bit_scan, "i"); 205module_param(bit_scan, int, 0);
206MODULE_PARM_DESC(bit_scan, "Scan for active chips on the bus"); 206MODULE_PARM_DESC(bit_scan, "Scan for active chips on the bus");
207MODULE_LICENSE("GPL"); 207MODULE_LICENSE("GPL");
208 208
diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig
index 08d5b8fed2dc..ff92735c7c85 100644
--- a/drivers/i2c/busses/Kconfig
+++ b/drivers/i2c/busses/Kconfig
@@ -124,6 +124,7 @@ config I2C_I801
124 ICH6 124 ICH6
125 ICH7 125 ICH7
126 ESB2 126 ESB2
127 ICH8
127 128
128 This driver can also be built as a module. If so, the module 129 This driver can also be built as a module. If so, the module
129 will be called i2c-i801. 130 will be called i2c-i801.
diff --git a/drivers/i2c/busses/i2c-i801.c b/drivers/i2c/busses/i2c-i801.c
index 1c752ddc10e2..8e0f3158215f 100644
--- a/drivers/i2c/busses/i2c-i801.c
+++ b/drivers/i2c/busses/i2c-i801.c
@@ -32,6 +32,7 @@
32 ICH6 266A 32 ICH6 266A
33 ICH7 27DA 33 ICH7 27DA
34 ESB2 269B 34 ESB2 269B
35 ICH8 283E
35 This driver supports several versions of Intel's I/O Controller Hubs (ICH). 36 This driver supports several versions of Intel's I/O Controller Hubs (ICH).
36 For SMBus support, they are similar to the PIIX4 and are part 37 For SMBus support, they are similar to the PIIX4 and are part
37 of Intel's '810' and other chipsets. 38 of Intel's '810' and other chipsets.
@@ -527,6 +528,7 @@ static struct pci_device_id i801_ids[] = {
527 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ICH6_16) }, 528 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ICH6_16) },
528 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ICH7_17) }, 529 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ICH7_17) },
529 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ESB2_17) }, 530 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ESB2_17) },
531 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_ICH8_5) },
530 { 0, } 532 { 0, }
531}; 533};
532 534
diff --git a/drivers/i2c/busses/i2c-parport-light.c b/drivers/i2c/busses/i2c-parport-light.c
index 3e5eba9fcacb..c63025a4c861 100644
--- a/drivers/i2c/busses/i2c-parport-light.c
+++ b/drivers/i2c/busses/i2c-parport-light.c
@@ -121,14 +121,11 @@ static struct i2c_adapter parport_adapter = {
121 121
122static int __init i2c_parport_init(void) 122static int __init i2c_parport_init(void)
123{ 123{
124 int type_count; 124 if (type < 0 || type >= ARRAY_SIZE(adapter_parm)) {
125
126 type_count = sizeof(adapter_parm)/sizeof(struct adapter_parm);
127 if (type < 0 || type >= type_count) {
128 printk(KERN_WARNING "i2c-parport: invalid type (%d)\n", type); 125 printk(KERN_WARNING "i2c-parport: invalid type (%d)\n", type);
129 type = 0; 126 type = 0;
130 } 127 }
131 128
132 if (base == 0) { 129 if (base == 0) {
133 printk(KERN_INFO "i2c-parport: using default base 0x%x\n", DEFAULT_BASE); 130 printk(KERN_INFO "i2c-parport: using default base 0x%x\n", DEFAULT_BASE);
134 base = DEFAULT_BASE; 131 base = DEFAULT_BASE;
@@ -152,7 +149,7 @@ static int __init i2c_parport_init(void)
152 release_region(base, 3); 149 release_region(base, 3);
153 return -ENODEV; 150 return -ENODEV;
154 } 151 }
155 152
156 return 0; 153 return 0;
157} 154}
158 155
diff --git a/drivers/i2c/busses/i2c-parport.c b/drivers/i2c/busses/i2c-parport.c
index 2854d858fc9b..7e2e8cd1c14a 100644
--- a/drivers/i2c/busses/i2c-parport.c
+++ b/drivers/i2c/busses/i2c-parport.c
@@ -241,14 +241,11 @@ static struct parport_driver i2c_parport_driver = {
241 241
242static int __init i2c_parport_init(void) 242static int __init i2c_parport_init(void)
243{ 243{
244 int type_count; 244 if (type < 0 || type >= ARRAY_SIZE(adapter_parm)) {
245
246 type_count = sizeof(adapter_parm)/sizeof(struct adapter_parm);
247 if (type < 0 || type >= type_count) {
248 printk(KERN_WARNING "i2c-parport: invalid type (%d)\n", type); 245 printk(KERN_WARNING "i2c-parport: invalid type (%d)\n", type);
249 type = 0; 246 type = 0;
250 } 247 }
251 248
252 return parport_register_driver(&i2c_parport_driver); 249 return parport_register_driver(&i2c_parport_driver);
253} 250}
254 251
diff --git a/drivers/i2c/busses/i2c-pxa.c b/drivers/i2c/busses/i2c-pxa.c
index 86e2234faf80..7579f4b256a8 100644
--- a/drivers/i2c/busses/i2c-pxa.c
+++ b/drivers/i2c/busses/i2c-pxa.c
@@ -861,7 +861,7 @@ static irqreturn_t i2c_pxa_handler(int this_irq, void *dev_id, struct pt_regs *r
861 decode_ISR(isr); 861 decode_ISR(isr);
862 } 862 }
863 863
864 if (i2c->irqlogidx < sizeof(i2c->isrlog)/sizeof(u32)) 864 if (i2c->irqlogidx < ARRAY_SIZE(i2c->isrlog))
865 i2c->isrlog[i2c->irqlogidx++] = isr; 865 i2c->isrlog[i2c->irqlogidx++] = isr;
866 866
867 show_state(i2c); 867 show_state(i2c);
diff --git a/drivers/i2c/i2c-core.c b/drivers/i2c/i2c-core.c
index 0ce58b506046..1a2c9ab5d9e3 100644
--- a/drivers/i2c/i2c-core.c
+++ b/drivers/i2c/i2c-core.c
@@ -946,6 +946,20 @@ s32 i2c_smbus_read_i2c_block_data(struct i2c_client *client, u8 command, u8 *val
946 } 946 }
947} 947}
948 948
949s32 i2c_smbus_write_i2c_block_data(struct i2c_client *client, u8 command,
950 u8 length, u8 *values)
951{
952 union i2c_smbus_data data;
953
954 if (length > I2C_SMBUS_BLOCK_MAX)
955 length = I2C_SMBUS_BLOCK_MAX;
956 data.block[0] = length;
957 memcpy(data.block + 1, values, length);
958 return i2c_smbus_xfer(client->adapter, client->addr, client->flags,
959 I2C_SMBUS_WRITE, command,
960 I2C_SMBUS_I2C_BLOCK_DATA, &data);
961}
962
949/* Simulate a SMBus command using the i2c protocol 963/* Simulate a SMBus command using the i2c protocol
950 No checking of parameters is done! */ 964 No checking of parameters is done! */
951static s32 i2c_smbus_xfer_emulated(struct i2c_adapter * adapter, u16 addr, 965static s32 i2c_smbus_xfer_emulated(struct i2c_adapter * adapter, u16 addr,
@@ -1150,6 +1164,7 @@ EXPORT_SYMBOL(i2c_smbus_read_word_data);
1150EXPORT_SYMBOL(i2c_smbus_write_word_data); 1164EXPORT_SYMBOL(i2c_smbus_write_word_data);
1151EXPORT_SYMBOL(i2c_smbus_write_block_data); 1165EXPORT_SYMBOL(i2c_smbus_write_block_data);
1152EXPORT_SYMBOL(i2c_smbus_read_i2c_block_data); 1166EXPORT_SYMBOL(i2c_smbus_read_i2c_block_data);
1167EXPORT_SYMBOL(i2c_smbus_write_i2c_block_data);
1153 1168
1154MODULE_AUTHOR("Simon G. Vogl <simon@tk.uni-linz.ac.at>"); 1169MODULE_AUTHOR("Simon G. Vogl <simon@tk.uni-linz.ac.at>");
1155MODULE_DESCRIPTION("I2C-Bus main module"); 1170MODULE_DESCRIPTION("I2C-Bus main module");
diff --git a/include/linux/i2c.h b/include/linux/i2c.h
index 7863a59bd598..63f1d63cc1d8 100644
--- a/include/linux/i2c.h
+++ b/include/linux/i2c.h
@@ -100,6 +100,9 @@ extern s32 i2c_smbus_write_block_data(struct i2c_client * client,
100/* Returns the number of read bytes */ 100/* Returns the number of read bytes */
101extern s32 i2c_smbus_read_i2c_block_data(struct i2c_client * client, 101extern s32 i2c_smbus_read_i2c_block_data(struct i2c_client * client,
102 u8 command, u8 *values); 102 u8 command, u8 *values);
103extern s32 i2c_smbus_write_i2c_block_data(struct i2c_client * client,
104 u8 command, u8 length,
105 u8 *values);
103 106
104/* 107/*
105 * A driver is capable of handling one or more physical devices present on 108 * A driver is capable of handling one or more physical devices present on