diff options
Diffstat (limited to 'drivers/hwmon')
39 files changed, 3222 insertions, 1026 deletions
diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig index 140d5f851a5b..138dc50270e3 100644 --- a/drivers/hwmon/Kconfig +++ b/drivers/hwmon/Kconfig | |||
@@ -12,12 +12,20 @@ config HWMON | |||
12 | of a system. Most modern motherboards include such a device. It | 12 | of a system. Most modern motherboards include such a device. It |
13 | can include temperature sensors, voltage sensors, fan speed | 13 | can include temperature sensors, voltage sensors, fan speed |
14 | sensors and various additional features such as the ability to | 14 | sensors and various additional features such as the ability to |
15 | control the speed of the fans. | 15 | control the speed of the fans. If you want this support you |
16 | should say Y here and also to the specific driver(s) for your | ||
17 | sensors chip(s) below. | ||
18 | |||
19 | This support can also be built as a module. If so, the module | ||
20 | will be called hwmon. | ||
21 | |||
22 | config HWMON_VID | ||
23 | tristate | ||
24 | default n | ||
16 | 25 | ||
17 | config SENSORS_ADM1021 | 26 | config SENSORS_ADM1021 |
18 | tristate "Analog Devices ADM1021 and compatibles" | 27 | tristate "Analog Devices ADM1021 and compatibles" |
19 | depends on HWMON && I2C | 28 | depends on HWMON && I2C |
20 | select I2C_SENSOR | ||
21 | help | 29 | help |
22 | If you say yes here you get support for Analog Devices ADM1021 | 30 | If you say yes here you get support for Analog Devices ADM1021 |
23 | and ADM1023 sensor chips and clones: Maxim MAX1617 and MAX1617A, | 31 | and ADM1023 sensor chips and clones: Maxim MAX1617 and MAX1617A, |
@@ -30,7 +38,7 @@ config SENSORS_ADM1021 | |||
30 | config SENSORS_ADM1025 | 38 | config SENSORS_ADM1025 |
31 | tristate "Analog Devices ADM1025 and compatibles" | 39 | tristate "Analog Devices ADM1025 and compatibles" |
32 | depends on HWMON && I2C && EXPERIMENTAL | 40 | depends on HWMON && I2C && EXPERIMENTAL |
33 | select I2C_SENSOR | 41 | select HWMON_VID |
34 | help | 42 | help |
35 | If you say yes here you get support for Analog Devices ADM1025 | 43 | If you say yes here you get support for Analog Devices ADM1025 |
36 | and Philips NE1619 sensor chips. | 44 | and Philips NE1619 sensor chips. |
@@ -41,7 +49,7 @@ config SENSORS_ADM1025 | |||
41 | config SENSORS_ADM1026 | 49 | config SENSORS_ADM1026 |
42 | tristate "Analog Devices ADM1026 and compatibles" | 50 | tristate "Analog Devices ADM1026 and compatibles" |
43 | depends on HWMON && I2C && EXPERIMENTAL | 51 | depends on HWMON && I2C && EXPERIMENTAL |
44 | select I2C_SENSOR | 52 | select HWMON_VID |
45 | help | 53 | help |
46 | If you say yes here you get support for Analog Devices ADM1026 | 54 | If you say yes here you get support for Analog Devices ADM1026 |
47 | sensor chip. | 55 | sensor chip. |
@@ -52,7 +60,6 @@ config SENSORS_ADM1026 | |||
52 | config SENSORS_ADM1031 | 60 | config SENSORS_ADM1031 |
53 | tristate "Analog Devices ADM1031 and compatibles" | 61 | tristate "Analog Devices ADM1031 and compatibles" |
54 | depends on HWMON && I2C && EXPERIMENTAL | 62 | depends on HWMON && I2C && EXPERIMENTAL |
55 | select I2C_SENSOR | ||
56 | help | 63 | help |
57 | If you say yes here you get support for Analog Devices ADM1031 | 64 | If you say yes here you get support for Analog Devices ADM1031 |
58 | and ADM1030 sensor chips. | 65 | and ADM1030 sensor chips. |
@@ -63,7 +70,7 @@ config SENSORS_ADM1031 | |||
63 | config SENSORS_ADM9240 | 70 | config SENSORS_ADM9240 |
64 | tristate "Analog Devices ADM9240 and compatibles" | 71 | tristate "Analog Devices ADM9240 and compatibles" |
65 | depends on HWMON && I2C && EXPERIMENTAL | 72 | depends on HWMON && I2C && EXPERIMENTAL |
66 | select I2C_SENSOR | 73 | select HWMON_VID |
67 | help | 74 | help |
68 | If you say yes here you get support for Analog Devices ADM9240, | 75 | If you say yes here you get support for Analog Devices ADM9240, |
69 | Dallas DS1780, National Semiconductor LM81 sensor chips. | 76 | Dallas DS1780, National Semiconductor LM81 sensor chips. |
@@ -74,7 +81,7 @@ config SENSORS_ADM9240 | |||
74 | config SENSORS_ASB100 | 81 | config SENSORS_ASB100 |
75 | tristate "Asus ASB100 Bach" | 82 | tristate "Asus ASB100 Bach" |
76 | depends on HWMON && I2C && EXPERIMENTAL | 83 | depends on HWMON && I2C && EXPERIMENTAL |
77 | select I2C_SENSOR | 84 | select HWMON_VID |
78 | help | 85 | help |
79 | If you say yes here you get support for the ASB100 Bach sensor | 86 | If you say yes here you get support for the ASB100 Bach sensor |
80 | chip found on some Asus mainboards. | 87 | chip found on some Asus mainboards. |
@@ -85,7 +92,7 @@ config SENSORS_ASB100 | |||
85 | config SENSORS_ATXP1 | 92 | config SENSORS_ATXP1 |
86 | tristate "Attansic ATXP1 VID controller" | 93 | tristate "Attansic ATXP1 VID controller" |
87 | depends on HWMON && I2C && EXPERIMENTAL | 94 | depends on HWMON && I2C && EXPERIMENTAL |
88 | select I2C_SENSOR | 95 | select HWMON_VID |
89 | help | 96 | help |
90 | If you say yes here you get support for the Attansic ATXP1 VID | 97 | If you say yes here you get support for the Attansic ATXP1 VID |
91 | controller. | 98 | controller. |
@@ -99,7 +106,6 @@ config SENSORS_ATXP1 | |||
99 | config SENSORS_DS1621 | 106 | config SENSORS_DS1621 |
100 | tristate "Dallas Semiconductor DS1621 and DS1625" | 107 | tristate "Dallas Semiconductor DS1621 and DS1625" |
101 | depends on HWMON && I2C && EXPERIMENTAL | 108 | depends on HWMON && I2C && EXPERIMENTAL |
102 | select I2C_SENSOR | ||
103 | help | 109 | help |
104 | If you say yes here you get support for Dallas Semiconductor | 110 | If you say yes here you get support for Dallas Semiconductor |
105 | DS1621 and DS1625 sensor chips. | 111 | DS1621 and DS1625 sensor chips. |
@@ -110,7 +116,6 @@ config SENSORS_DS1621 | |||
110 | config SENSORS_FSCHER | 116 | config SENSORS_FSCHER |
111 | tristate "FSC Hermes" | 117 | tristate "FSC Hermes" |
112 | depends on HWMON && I2C && EXPERIMENTAL | 118 | depends on HWMON && I2C && EXPERIMENTAL |
113 | select I2C_SENSOR | ||
114 | help | 119 | help |
115 | If you say yes here you get support for Fujitsu Siemens | 120 | If you say yes here you get support for Fujitsu Siemens |
116 | Computers Hermes sensor chips. | 121 | Computers Hermes sensor chips. |
@@ -121,7 +126,6 @@ config SENSORS_FSCHER | |||
121 | config SENSORS_FSCPOS | 126 | config SENSORS_FSCPOS |
122 | tristate "FSC Poseidon" | 127 | tristate "FSC Poseidon" |
123 | depends on HWMON && I2C && EXPERIMENTAL | 128 | depends on HWMON && I2C && EXPERIMENTAL |
124 | select I2C_SENSOR | ||
125 | help | 129 | help |
126 | If you say yes here you get support for Fujitsu Siemens | 130 | If you say yes here you get support for Fujitsu Siemens |
127 | Computers Poseidon sensor chips. | 131 | Computers Poseidon sensor chips. |
@@ -132,7 +136,6 @@ config SENSORS_FSCPOS | |||
132 | config SENSORS_GL518SM | 136 | config SENSORS_GL518SM |
133 | tristate "Genesys Logic GL518SM" | 137 | tristate "Genesys Logic GL518SM" |
134 | depends on HWMON && I2C | 138 | depends on HWMON && I2C |
135 | select I2C_SENSOR | ||
136 | help | 139 | help |
137 | If you say yes here you get support for Genesys Logic GL518SM | 140 | If you say yes here you get support for Genesys Logic GL518SM |
138 | sensor chips. | 141 | sensor chips. |
@@ -143,7 +146,7 @@ config SENSORS_GL518SM | |||
143 | config SENSORS_GL520SM | 146 | config SENSORS_GL520SM |
144 | tristate "Genesys Logic GL520SM" | 147 | tristate "Genesys Logic GL520SM" |
145 | depends on HWMON && I2C && EXPERIMENTAL | 148 | depends on HWMON && I2C && EXPERIMENTAL |
146 | select I2C_SENSOR | 149 | select HWMON_VID |
147 | help | 150 | help |
148 | If you say yes here you get support for Genesys Logic GL520SM | 151 | If you say yes here you get support for Genesys Logic GL520SM |
149 | sensor chips. | 152 | sensor chips. |
@@ -154,7 +157,8 @@ config SENSORS_GL520SM | |||
154 | config SENSORS_IT87 | 157 | config SENSORS_IT87 |
155 | tristate "ITE IT87xx and compatibles" | 158 | tristate "ITE IT87xx and compatibles" |
156 | depends on HWMON && I2C | 159 | depends on HWMON && I2C |
157 | select I2C_SENSOR | 160 | select I2C_ISA |
161 | select HWMON_VID | ||
158 | help | 162 | help |
159 | If you say yes here you get support for ITE IT87xx sensor chips | 163 | If you say yes here you get support for ITE IT87xx sensor chips |
160 | and clones: SiS960. | 164 | and clones: SiS960. |
@@ -165,7 +169,6 @@ config SENSORS_IT87 | |||
165 | config SENSORS_LM63 | 169 | config SENSORS_LM63 |
166 | tristate "National Semiconductor LM63" | 170 | tristate "National Semiconductor LM63" |
167 | depends on HWMON && I2C && EXPERIMENTAL | 171 | depends on HWMON && I2C && EXPERIMENTAL |
168 | select I2C_SENSOR | ||
169 | help | 172 | help |
170 | If you say yes here you get support for the National Semiconductor | 173 | If you say yes here you get support for the National Semiconductor |
171 | LM63 remote diode digital temperature sensor with integrated fan | 174 | LM63 remote diode digital temperature sensor with integrated fan |
@@ -178,7 +181,6 @@ config SENSORS_LM63 | |||
178 | config SENSORS_LM75 | 181 | config SENSORS_LM75 |
179 | tristate "National Semiconductor LM75 and compatibles" | 182 | tristate "National Semiconductor LM75 and compatibles" |
180 | depends on HWMON && I2C | 183 | depends on HWMON && I2C |
181 | select I2C_SENSOR | ||
182 | help | 184 | help |
183 | If you say yes here you get support for National Semiconductor LM75 | 185 | If you say yes here you get support for National Semiconductor LM75 |
184 | sensor chips and clones: Dallas Semiconductor DS75 and DS1775 (in | 186 | sensor chips and clones: Dallas Semiconductor DS75 and DS1775 (in |
@@ -194,7 +196,6 @@ config SENSORS_LM75 | |||
194 | config SENSORS_LM77 | 196 | config SENSORS_LM77 |
195 | tristate "National Semiconductor LM77" | 197 | tristate "National Semiconductor LM77" |
196 | depends on HWMON && I2C && EXPERIMENTAL | 198 | depends on HWMON && I2C && EXPERIMENTAL |
197 | select I2C_SENSOR | ||
198 | help | 199 | help |
199 | If you say yes here you get support for National Semiconductor LM77 | 200 | If you say yes here you get support for National Semiconductor LM77 |
200 | sensor chips. | 201 | sensor chips. |
@@ -205,7 +206,8 @@ config SENSORS_LM77 | |||
205 | config SENSORS_LM78 | 206 | config SENSORS_LM78 |
206 | tristate "National Semiconductor LM78 and compatibles" | 207 | tristate "National Semiconductor LM78 and compatibles" |
207 | depends on HWMON && I2C && EXPERIMENTAL | 208 | depends on HWMON && I2C && EXPERIMENTAL |
208 | select I2C_SENSOR | 209 | select I2C_ISA |
210 | select HWMON_VID | ||
209 | help | 211 | help |
210 | If you say yes here you get support for National Semiconductor LM78, | 212 | If you say yes here you get support for National Semiconductor LM78, |
211 | LM78-J and LM79. | 213 | LM78-J and LM79. |
@@ -216,7 +218,6 @@ config SENSORS_LM78 | |||
216 | config SENSORS_LM80 | 218 | config SENSORS_LM80 |
217 | tristate "National Semiconductor LM80" | 219 | tristate "National Semiconductor LM80" |
218 | depends on HWMON && I2C && EXPERIMENTAL | 220 | depends on HWMON && I2C && EXPERIMENTAL |
219 | select I2C_SENSOR | ||
220 | help | 221 | help |
221 | If you say yes here you get support for National Semiconductor | 222 | If you say yes here you get support for National Semiconductor |
222 | LM80 sensor chips. | 223 | LM80 sensor chips. |
@@ -227,7 +228,6 @@ config SENSORS_LM80 | |||
227 | config SENSORS_LM83 | 228 | config SENSORS_LM83 |
228 | tristate "National Semiconductor LM83" | 229 | tristate "National Semiconductor LM83" |
229 | depends on HWMON && I2C | 230 | depends on HWMON && I2C |
230 | select I2C_SENSOR | ||
231 | help | 231 | help |
232 | If you say yes here you get support for National Semiconductor | 232 | If you say yes here you get support for National Semiconductor |
233 | LM83 sensor chips. | 233 | LM83 sensor chips. |
@@ -238,7 +238,7 @@ config SENSORS_LM83 | |||
238 | config SENSORS_LM85 | 238 | config SENSORS_LM85 |
239 | tristate "National Semiconductor LM85 and compatibles" | 239 | tristate "National Semiconductor LM85 and compatibles" |
240 | depends on HWMON && I2C && EXPERIMENTAL | 240 | depends on HWMON && I2C && EXPERIMENTAL |
241 | select I2C_SENSOR | 241 | select HWMON_VID |
242 | help | 242 | help |
243 | If you say yes here you get support for National Semiconductor LM85 | 243 | If you say yes here you get support for National Semiconductor LM85 |
244 | sensor chips and clones: ADT7463, EMC6D100, EMC6D102 and ADM1027. | 244 | sensor chips and clones: ADT7463, EMC6D100, EMC6D102 and ADM1027. |
@@ -249,7 +249,7 @@ config SENSORS_LM85 | |||
249 | config SENSORS_LM87 | 249 | config SENSORS_LM87 |
250 | tristate "National Semiconductor LM87" | 250 | tristate "National Semiconductor LM87" |
251 | depends on HWMON && I2C && EXPERIMENTAL | 251 | depends on HWMON && I2C && EXPERIMENTAL |
252 | select I2C_SENSOR | 252 | select HWMON_VID |
253 | help | 253 | help |
254 | If you say yes here you get support for National Semiconductor LM87 | 254 | If you say yes here you get support for National Semiconductor LM87 |
255 | sensor chips. | 255 | sensor chips. |
@@ -260,7 +260,6 @@ config SENSORS_LM87 | |||
260 | config SENSORS_LM90 | 260 | config SENSORS_LM90 |
261 | tristate "National Semiconductor LM90 and compatibles" | 261 | tristate "National Semiconductor LM90 and compatibles" |
262 | depends on HWMON && I2C | 262 | depends on HWMON && I2C |
263 | select I2C_SENSOR | ||
264 | help | 263 | help |
265 | If you say yes here you get support for National Semiconductor LM90, | 264 | If you say yes here you get support for National Semiconductor LM90, |
266 | LM86, LM89 and LM99, Analog Devices ADM1032 and Maxim MAX6657 and | 265 | LM86, LM89 and LM99, Analog Devices ADM1032 and Maxim MAX6657 and |
@@ -275,7 +274,6 @@ config SENSORS_LM90 | |||
275 | config SENSORS_LM92 | 274 | config SENSORS_LM92 |
276 | tristate "National Semiconductor LM92 and compatibles" | 275 | tristate "National Semiconductor LM92 and compatibles" |
277 | depends on HWMON && I2C && EXPERIMENTAL | 276 | depends on HWMON && I2C && EXPERIMENTAL |
278 | select I2C_SENSOR | ||
279 | help | 277 | help |
280 | If you say yes here you get support for National Semiconductor LM92 | 278 | If you say yes here you get support for National Semiconductor LM92 |
281 | and Maxim MAX6635 sensor chips. | 279 | and Maxim MAX6635 sensor chips. |
@@ -286,7 +284,6 @@ config SENSORS_LM92 | |||
286 | config SENSORS_MAX1619 | 284 | config SENSORS_MAX1619 |
287 | tristate "Maxim MAX1619 sensor chip" | 285 | tristate "Maxim MAX1619 sensor chip" |
288 | depends on HWMON && I2C && EXPERIMENTAL | 286 | depends on HWMON && I2C && EXPERIMENTAL |
289 | select I2C_SENSOR | ||
290 | help | 287 | help |
291 | If you say yes here you get support for MAX1619 sensor chip. | 288 | If you say yes here you get support for MAX1619 sensor chip. |
292 | 289 | ||
@@ -296,8 +293,8 @@ config SENSORS_MAX1619 | |||
296 | config SENSORS_PC87360 | 293 | config SENSORS_PC87360 |
297 | tristate "National Semiconductor PC87360 family" | 294 | tristate "National Semiconductor PC87360 family" |
298 | depends on HWMON && I2C && EXPERIMENTAL | 295 | depends on HWMON && I2C && EXPERIMENTAL |
299 | select I2C_SENSOR | ||
300 | select I2C_ISA | 296 | select I2C_ISA |
297 | select HWMON_VID | ||
301 | help | 298 | help |
302 | If you say yes here you get access to the hardware monitoring | 299 | If you say yes here you get access to the hardware monitoring |
303 | functions of the National Semiconductor PC8736x Super-I/O chips. | 300 | functions of the National Semiconductor PC8736x Super-I/O chips. |
@@ -311,7 +308,6 @@ config SENSORS_PC87360 | |||
311 | config SENSORS_SIS5595 | 308 | config SENSORS_SIS5595 |
312 | tristate "Silicon Integrated Systems Corp. SiS5595" | 309 | tristate "Silicon Integrated Systems Corp. SiS5595" |
313 | depends on HWMON && I2C && PCI && EXPERIMENTAL | 310 | depends on HWMON && I2C && PCI && EXPERIMENTAL |
314 | select I2C_SENSOR | ||
315 | select I2C_ISA | 311 | select I2C_ISA |
316 | help | 312 | help |
317 | If you say yes here you get support for the integrated sensors in | 313 | If you say yes here you get support for the integrated sensors in |
@@ -323,7 +319,6 @@ config SENSORS_SIS5595 | |||
323 | config SENSORS_SMSC47M1 | 319 | config SENSORS_SMSC47M1 |
324 | tristate "SMSC LPC47M10x and compatibles" | 320 | tristate "SMSC LPC47M10x and compatibles" |
325 | depends on HWMON && I2C && EXPERIMENTAL | 321 | depends on HWMON && I2C && EXPERIMENTAL |
326 | select I2C_SENSOR | ||
327 | select I2C_ISA | 322 | select I2C_ISA |
328 | help | 323 | help |
329 | If you say yes here you get support for the integrated fan | 324 | If you say yes here you get support for the integrated fan |
@@ -336,7 +331,6 @@ config SENSORS_SMSC47M1 | |||
336 | config SENSORS_SMSC47B397 | 331 | config SENSORS_SMSC47B397 |
337 | tristate "SMSC LPC47B397-NC" | 332 | tristate "SMSC LPC47B397-NC" |
338 | depends on HWMON && I2C && EXPERIMENTAL | 333 | depends on HWMON && I2C && EXPERIMENTAL |
339 | select I2C_SENSOR | ||
340 | select I2C_ISA | 334 | select I2C_ISA |
341 | help | 335 | help |
342 | If you say yes here you get support for the SMSC LPC47B397-NC | 336 | If you say yes here you get support for the SMSC LPC47B397-NC |
@@ -348,7 +342,6 @@ config SENSORS_SMSC47B397 | |||
348 | config SENSORS_VIA686A | 342 | config SENSORS_VIA686A |
349 | tristate "VIA686A" | 343 | tristate "VIA686A" |
350 | depends on HWMON && I2C && PCI | 344 | depends on HWMON && I2C && PCI |
351 | select I2C_SENSOR | ||
352 | select I2C_ISA | 345 | select I2C_ISA |
353 | help | 346 | help |
354 | If you say yes here you get support for the integrated sensors in | 347 | If you say yes here you get support for the integrated sensors in |
@@ -360,7 +353,8 @@ config SENSORS_VIA686A | |||
360 | config SENSORS_W83781D | 353 | config SENSORS_W83781D |
361 | tristate "Winbond W83781D, W83782D, W83783S, W83627HF, Asus AS99127F" | 354 | tristate "Winbond W83781D, W83782D, W83783S, W83627HF, Asus AS99127F" |
362 | depends on HWMON && I2C | 355 | depends on HWMON && I2C |
363 | select I2C_SENSOR | 356 | select I2C_ISA |
357 | select HWMON_VID | ||
364 | help | 358 | help |
365 | If you say yes here you get support for the Winbond W8378x series | 359 | If you say yes here you get support for the Winbond W8378x series |
366 | of sensor chips: the W83781D, W83782D, W83783S and W83627HF, | 360 | of sensor chips: the W83781D, W83782D, W83783S and W83627HF, |
@@ -369,10 +363,18 @@ config SENSORS_W83781D | |||
369 | This driver can also be built as a module. If so, the module | 363 | This driver can also be built as a module. If so, the module |
370 | will be called w83781d. | 364 | will be called w83781d. |
371 | 365 | ||
366 | config SENSORS_W83792D | ||
367 | tristate "Winbond W83792D" | ||
368 | depends on HWMON && I2C && EXPERIMENTAL | ||
369 | help | ||
370 | If you say yes here you get support for the Winbond W83792D chip. | ||
371 | |||
372 | This driver can also be built as a module. If so, the module | ||
373 | will be called w83792d. | ||
374 | |||
372 | config SENSORS_W83L785TS | 375 | config SENSORS_W83L785TS |
373 | tristate "Winbond W83L785TS-S" | 376 | tristate "Winbond W83L785TS-S" |
374 | depends on HWMON && I2C && EXPERIMENTAL | 377 | depends on HWMON && I2C && EXPERIMENTAL |
375 | select I2C_SENSOR | ||
376 | help | 378 | help |
377 | If you say yes here you get support for the Winbond W83L785TS-S | 379 | If you say yes here you get support for the Winbond W83L785TS-S |
378 | sensor chip, which is used on the Asus A7N8X, among other | 380 | sensor chip, which is used on the Asus A7N8X, among other |
@@ -384,8 +386,8 @@ config SENSORS_W83L785TS | |||
384 | config SENSORS_W83627HF | 386 | config SENSORS_W83627HF |
385 | tristate "Winbond W83627HF, W83627THF, W83637HF, W83697HF" | 387 | tristate "Winbond W83627HF, W83627THF, W83637HF, W83697HF" |
386 | depends on HWMON && I2C && EXPERIMENTAL | 388 | depends on HWMON && I2C && EXPERIMENTAL |
387 | select I2C_SENSOR | ||
388 | select I2C_ISA | 389 | select I2C_ISA |
390 | select HWMON_VID | ||
389 | help | 391 | help |
390 | If you say yes here you get support for the Winbond W836X7 series | 392 | If you say yes here you get support for the Winbond W836X7 series |
391 | of sensor chips: the W83627HF, W83627THF, W83637HF, and the W83697HF | 393 | of sensor chips: the W83627HF, W83627THF, W83637HF, and the W83697HF |
@@ -396,7 +398,6 @@ config SENSORS_W83627HF | |||
396 | config SENSORS_W83627EHF | 398 | config SENSORS_W83627EHF |
397 | tristate "Winbond W83627EHF" | 399 | tristate "Winbond W83627EHF" |
398 | depends on HWMON && I2C && EXPERIMENTAL | 400 | depends on HWMON && I2C && EXPERIMENTAL |
399 | select I2C_SENSOR | ||
400 | select I2C_ISA | 401 | select I2C_ISA |
401 | help | 402 | help |
402 | If you say yes here you get preliminary support for the hardware | 403 | If you say yes here you get preliminary support for the hardware |
@@ -404,6 +405,9 @@ config SENSORS_W83627EHF | |||
404 | Only fan and temperature inputs are supported at the moment, while | 405 | Only fan and temperature inputs are supported at the moment, while |
405 | the chip does much more than that. | 406 | the chip does much more than that. |
406 | 407 | ||
408 | This driver also supports the W83627EHG, which is the lead-free | ||
409 | version of the W83627EHF. | ||
410 | |||
407 | This driver can also be built as a module. If so, the module | 411 | This driver can also be built as a module. If so, the module |
408 | will be called w83627ehf. | 412 | will be called w83627ehf. |
409 | 413 | ||
diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile index 2781403a0236..381f1bf04cc5 100644 --- a/drivers/hwmon/Makefile +++ b/drivers/hwmon/Makefile | |||
@@ -2,9 +2,13 @@ | |||
2 | # Makefile for sensor chip drivers. | 2 | # Makefile for sensor chip drivers. |
3 | # | 3 | # |
4 | 4 | ||
5 | obj-$(CONFIG_HWMON) += hwmon.o | ||
6 | obj-$(CONFIG_HWMON_VID) += hwmon-vid.o | ||
7 | |||
5 | # asb100, then w83781d go first, as they can override other drivers' addresses. | 8 | # asb100, then w83781d go first, as they can override other drivers' addresses. |
6 | obj-$(CONFIG_SENSORS_ASB100) += asb100.o | 9 | obj-$(CONFIG_SENSORS_ASB100) += asb100.o |
7 | obj-$(CONFIG_SENSORS_W83627HF) += w83627hf.o | 10 | obj-$(CONFIG_SENSORS_W83627HF) += w83627hf.o |
11 | obj-$(CONFIG_SENSORS_W83792D) += w83792d.o | ||
8 | obj-$(CONFIG_SENSORS_W83781D) += w83781d.o | 12 | obj-$(CONFIG_SENSORS_W83781D) += w83781d.o |
9 | 13 | ||
10 | obj-$(CONFIG_SENSORS_ADM1021) += adm1021.o | 14 | obj-$(CONFIG_SENSORS_ADM1021) += adm1021.o |
diff --git a/drivers/hwmon/adm1021.c b/drivers/hwmon/adm1021.c index d2c774c32f45..e928cdb041cb 100644 --- a/drivers/hwmon/adm1021.c +++ b/drivers/hwmon/adm1021.c | |||
@@ -24,7 +24,8 @@ | |||
24 | #include <linux/slab.h> | 24 | #include <linux/slab.h> |
25 | #include <linux/jiffies.h> | 25 | #include <linux/jiffies.h> |
26 | #include <linux/i2c.h> | 26 | #include <linux/i2c.h> |
27 | #include <linux/i2c-sensor.h> | 27 | #include <linux/hwmon.h> |
28 | #include <linux/err.h> | ||
28 | 29 | ||
29 | 30 | ||
30 | /* Addresses to scan */ | 31 | /* Addresses to scan */ |
@@ -32,10 +33,9 @@ static unsigned short normal_i2c[] = { 0x18, 0x19, 0x1a, | |||
32 | 0x29, 0x2a, 0x2b, | 33 | 0x29, 0x2a, 0x2b, |
33 | 0x4c, 0x4d, 0x4e, | 34 | 0x4c, 0x4d, 0x4e, |
34 | I2C_CLIENT_END }; | 35 | I2C_CLIENT_END }; |
35 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
36 | 36 | ||
37 | /* Insmod parameters */ | 37 | /* Insmod parameters */ |
38 | SENSORS_INSMOD_8(adm1021, adm1023, max1617, max1617a, thmc10, lm84, gl523sm, mc1066); | 38 | I2C_CLIENT_INSMOD_8(adm1021, adm1023, max1617, max1617a, thmc10, lm84, gl523sm, mc1066); |
39 | 39 | ||
40 | /* adm1021 constants specified below */ | 40 | /* adm1021 constants specified below */ |
41 | 41 | ||
@@ -89,6 +89,7 @@ clearing it. Weird, ey? --Phil */ | |||
89 | /* Each client has this additional data */ | 89 | /* Each client has this additional data */ |
90 | struct adm1021_data { | 90 | struct adm1021_data { |
91 | struct i2c_client client; | 91 | struct i2c_client client; |
92 | struct class_device *class_dev; | ||
92 | enum chips type; | 93 | enum chips type; |
93 | 94 | ||
94 | struct semaphore update_lock; | 95 | struct semaphore update_lock; |
@@ -185,7 +186,7 @@ static int adm1021_attach_adapter(struct i2c_adapter *adapter) | |||
185 | { | 186 | { |
186 | if (!(adapter->class & I2C_CLASS_HWMON)) | 187 | if (!(adapter->class & I2C_CLASS_HWMON)) |
187 | return 0; | 188 | return 0; |
188 | return i2c_detect(adapter, &addr_data, adm1021_detect); | 189 | return i2c_probe(adapter, &addr_data, adm1021_detect); |
189 | } | 190 | } |
190 | 191 | ||
191 | static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind) | 192 | static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind) |
@@ -196,15 +197,6 @@ static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind) | |||
196 | int err = 0; | 197 | int err = 0; |
197 | const char *type_name = ""; | 198 | const char *type_name = ""; |
198 | 199 | ||
199 | /* Make sure we aren't probing the ISA bus!! This is just a safety check | ||
200 | at this moment; i2c_detect really won't call us. */ | ||
201 | #ifdef DEBUG | ||
202 | if (i2c_is_isa_adapter(adapter)) { | ||
203 | dev_dbg(&adapter->dev, "adm1021_detect called for an ISA bus adapter?!?\n"); | ||
204 | return 0; | ||
205 | } | ||
206 | #endif | ||
207 | |||
208 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) | 200 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) |
209 | goto error0; | 201 | goto error0; |
210 | 202 | ||
@@ -295,6 +287,12 @@ static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind) | |||
295 | adm1021_init_client(new_client); | 287 | adm1021_init_client(new_client); |
296 | 288 | ||
297 | /* Register sysfs hooks */ | 289 | /* Register sysfs hooks */ |
290 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
291 | if (IS_ERR(data->class_dev)) { | ||
292 | err = PTR_ERR(data->class_dev); | ||
293 | goto error2; | ||
294 | } | ||
295 | |||
298 | device_create_file(&new_client->dev, &dev_attr_temp1_max); | 296 | device_create_file(&new_client->dev, &dev_attr_temp1_max); |
299 | device_create_file(&new_client->dev, &dev_attr_temp1_min); | 297 | device_create_file(&new_client->dev, &dev_attr_temp1_min); |
300 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 298 | device_create_file(&new_client->dev, &dev_attr_temp1_input); |
@@ -305,6 +303,8 @@ static int adm1021_detect(struct i2c_adapter *adapter, int address, int kind) | |||
305 | 303 | ||
306 | return 0; | 304 | return 0; |
307 | 305 | ||
306 | error2: | ||
307 | i2c_detach_client(new_client); | ||
308 | error1: | 308 | error1: |
309 | kfree(data); | 309 | kfree(data); |
310 | error0: | 310 | error0: |
@@ -322,14 +322,15 @@ static void adm1021_init_client(struct i2c_client *client) | |||
322 | 322 | ||
323 | static int adm1021_detach_client(struct i2c_client *client) | 323 | static int adm1021_detach_client(struct i2c_client *client) |
324 | { | 324 | { |
325 | struct adm1021_data *data = i2c_get_clientdata(client); | ||
325 | int err; | 326 | int err; |
326 | 327 | ||
327 | if ((err = i2c_detach_client(client))) { | 328 | hwmon_device_unregister(data->class_dev); |
328 | dev_err(&client->dev, "Client deregistration failed, client not detached.\n"); | 329 | |
330 | if ((err = i2c_detach_client(client))) | ||
329 | return err; | 331 | return err; |
330 | } | ||
331 | 332 | ||
332 | kfree(i2c_get_clientdata(client)); | 333 | kfree(data); |
333 | return 0; | 334 | return 0; |
334 | } | 335 | } |
335 | 336 | ||
diff --git a/drivers/hwmon/adm1025.c b/drivers/hwmon/adm1025.c index e452d0daf906..526b7ff179eb 100644 --- a/drivers/hwmon/adm1025.c +++ b/drivers/hwmon/adm1025.c | |||
@@ -50,8 +50,9 @@ | |||
50 | #include <linux/slab.h> | 50 | #include <linux/slab.h> |
51 | #include <linux/jiffies.h> | 51 | #include <linux/jiffies.h> |
52 | #include <linux/i2c.h> | 52 | #include <linux/i2c.h> |
53 | #include <linux/i2c-sensor.h> | 53 | #include <linux/hwmon.h> |
54 | #include <linux/i2c-vid.h> | 54 | #include <linux/hwmon-vid.h> |
55 | #include <linux/err.h> | ||
55 | 56 | ||
56 | /* | 57 | /* |
57 | * Addresses to scan | 58 | * Addresses to scan |
@@ -60,13 +61,12 @@ | |||
60 | */ | 61 | */ |
61 | 62 | ||
62 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; | 63 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; |
63 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
64 | 64 | ||
65 | /* | 65 | /* |
66 | * Insmod parameters | 66 | * Insmod parameters |
67 | */ | 67 | */ |
68 | 68 | ||
69 | SENSORS_INSMOD_2(adm1025, ne1619); | 69 | I2C_CLIENT_INSMOD_2(adm1025, ne1619); |
70 | 70 | ||
71 | /* | 71 | /* |
72 | * The ADM1025 registers | 72 | * The ADM1025 registers |
@@ -132,6 +132,7 @@ static struct i2c_driver adm1025_driver = { | |||
132 | 132 | ||
133 | struct adm1025_data { | 133 | struct adm1025_data { |
134 | struct i2c_client client; | 134 | struct i2c_client client; |
135 | struct class_device *class_dev; | ||
135 | struct semaphore update_lock; | 136 | struct semaphore update_lock; |
136 | char valid; /* zero until following fields are valid */ | 137 | char valid; /* zero until following fields are valid */ |
137 | unsigned long last_updated; /* in jiffies */ | 138 | unsigned long last_updated; /* in jiffies */ |
@@ -312,7 +313,7 @@ static int adm1025_attach_adapter(struct i2c_adapter *adapter) | |||
312 | { | 313 | { |
313 | if (!(adapter->class & I2C_CLASS_HWMON)) | 314 | if (!(adapter->class & I2C_CLASS_HWMON)) |
314 | return 0; | 315 | return 0; |
315 | return i2c_detect(adapter, &addr_data, adm1025_detect); | 316 | return i2c_probe(adapter, &addr_data, adm1025_detect); |
316 | } | 317 | } |
317 | 318 | ||
318 | /* | 319 | /* |
@@ -416,6 +417,12 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | |||
416 | adm1025_init_client(new_client); | 417 | adm1025_init_client(new_client); |
417 | 418 | ||
418 | /* Register sysfs hooks */ | 419 | /* Register sysfs hooks */ |
420 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
421 | if (IS_ERR(data->class_dev)) { | ||
422 | err = PTR_ERR(data->class_dev); | ||
423 | goto exit_detach; | ||
424 | } | ||
425 | |||
419 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 426 | device_create_file(&new_client->dev, &dev_attr_in0_input); |
420 | device_create_file(&new_client->dev, &dev_attr_in1_input); | 427 | device_create_file(&new_client->dev, &dev_attr_in1_input); |
421 | device_create_file(&new_client->dev, &dev_attr_in2_input); | 428 | device_create_file(&new_client->dev, &dev_attr_in2_input); |
@@ -452,6 +459,8 @@ static int adm1025_detect(struct i2c_adapter *adapter, int address, int kind) | |||
452 | 459 | ||
453 | return 0; | 460 | return 0; |
454 | 461 | ||
462 | exit_detach: | ||
463 | i2c_detach_client(new_client); | ||
455 | exit_free: | 464 | exit_free: |
456 | kfree(data); | 465 | kfree(data); |
457 | exit: | 466 | exit: |
@@ -464,7 +473,7 @@ static void adm1025_init_client(struct i2c_client *client) | |||
464 | struct adm1025_data *data = i2c_get_clientdata(client); | 473 | struct adm1025_data *data = i2c_get_clientdata(client); |
465 | int i; | 474 | int i; |
466 | 475 | ||
467 | data->vrm = i2c_which_vrm(); | 476 | data->vrm = vid_which_vrm(); |
468 | 477 | ||
469 | /* | 478 | /* |
470 | * Set high limits | 479 | * Set high limits |
@@ -502,15 +511,15 @@ static void adm1025_init_client(struct i2c_client *client) | |||
502 | 511 | ||
503 | static int adm1025_detach_client(struct i2c_client *client) | 512 | static int adm1025_detach_client(struct i2c_client *client) |
504 | { | 513 | { |
514 | struct adm1025_data *data = i2c_get_clientdata(client); | ||
505 | int err; | 515 | int err; |
506 | 516 | ||
507 | if ((err = i2c_detach_client(client))) { | 517 | hwmon_device_unregister(data->class_dev); |
508 | dev_err(&client->dev, "Client deregistration failed, " | 518 | |
509 | "client not detached.\n"); | 519 | if ((err = i2c_detach_client(client))) |
510 | return err; | 520 | return err; |
511 | } | ||
512 | 521 | ||
513 | kfree(i2c_get_clientdata(client)); | 522 | kfree(data); |
514 | return 0; | 523 | return 0; |
515 | } | 524 | } |
516 | 525 | ||
diff --git a/drivers/hwmon/adm1026.c b/drivers/hwmon/adm1026.c index c8a7f47911f9..625158110fd4 100644 --- a/drivers/hwmon/adm1026.c +++ b/drivers/hwmon/adm1026.c | |||
@@ -28,16 +28,16 @@ | |||
28 | #include <linux/slab.h> | 28 | #include <linux/slab.h> |
29 | #include <linux/jiffies.h> | 29 | #include <linux/jiffies.h> |
30 | #include <linux/i2c.h> | 30 | #include <linux/i2c.h> |
31 | #include <linux/i2c-sensor.h> | 31 | #include <linux/hwmon.h> |
32 | #include <linux/i2c-vid.h> | ||
33 | #include <linux/hwmon-sysfs.h> | 32 | #include <linux/hwmon-sysfs.h> |
33 | #include <linux/hwmon-vid.h> | ||
34 | #include <linux/err.h> | ||
34 | 35 | ||
35 | /* Addresses to scan */ | 36 | /* Addresses to scan */ |
36 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; | 37 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; |
37 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
38 | 38 | ||
39 | /* Insmod parameters */ | 39 | /* Insmod parameters */ |
40 | SENSORS_INSMOD_1(adm1026); | 40 | I2C_CLIENT_INSMOD_1(adm1026); |
41 | 41 | ||
42 | static int gpio_input[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, | 42 | static int gpio_input[17] = { -1, -1, -1, -1, -1, -1, -1, -1, -1, |
43 | -1, -1, -1, -1, -1, -1, -1, -1 }; | 43 | -1, -1, -1, -1, -1, -1, -1, -1 }; |
@@ -259,6 +259,7 @@ struct pwm_data { | |||
259 | 259 | ||
260 | struct adm1026_data { | 260 | struct adm1026_data { |
261 | struct i2c_client client; | 261 | struct i2c_client client; |
262 | struct class_device *class_dev; | ||
262 | struct semaphore lock; | 263 | struct semaphore lock; |
263 | enum chips type; | 264 | enum chips type; |
264 | 265 | ||
@@ -319,13 +320,15 @@ int adm1026_attach_adapter(struct i2c_adapter *adapter) | |||
319 | if (!(adapter->class & I2C_CLASS_HWMON)) { | 320 | if (!(adapter->class & I2C_CLASS_HWMON)) { |
320 | return 0; | 321 | return 0; |
321 | } | 322 | } |
322 | return i2c_detect(adapter, &addr_data, adm1026_detect); | 323 | return i2c_probe(adapter, &addr_data, adm1026_detect); |
323 | } | 324 | } |
324 | 325 | ||
325 | int adm1026_detach_client(struct i2c_client *client) | 326 | int adm1026_detach_client(struct i2c_client *client) |
326 | { | 327 | { |
328 | struct adm1026_data *data = i2c_get_clientdata(client); | ||
329 | hwmon_device_unregister(data->class_dev); | ||
327 | i2c_detach_client(client); | 330 | i2c_detach_client(client); |
328 | kfree(i2c_get_clientdata(client)); | 331 | kfree(data); |
329 | return 0; | 332 | return 0; |
330 | } | 333 | } |
331 | 334 | ||
@@ -1549,12 +1552,18 @@ int adm1026_detect(struct i2c_adapter *adapter, int address, | |||
1549 | goto exitfree; | 1552 | goto exitfree; |
1550 | 1553 | ||
1551 | /* Set the VRM version */ | 1554 | /* Set the VRM version */ |
1552 | data->vrm = i2c_which_vrm(); | 1555 | data->vrm = vid_which_vrm(); |
1553 | 1556 | ||
1554 | /* Initialize the ADM1026 chip */ | 1557 | /* Initialize the ADM1026 chip */ |
1555 | adm1026_init_client(new_client); | 1558 | adm1026_init_client(new_client); |
1556 | 1559 | ||
1557 | /* Register sysfs hooks */ | 1560 | /* Register sysfs hooks */ |
1561 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
1562 | if (IS_ERR(data->class_dev)) { | ||
1563 | err = PTR_ERR(data->class_dev); | ||
1564 | goto exitdetach; | ||
1565 | } | ||
1566 | |||
1558 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_input.dev_attr); | 1567 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_input.dev_attr); |
1559 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_max.dev_attr); | 1568 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_max.dev_attr); |
1560 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_min.dev_attr); | 1569 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_min.dev_attr); |
@@ -1690,6 +1699,8 @@ int adm1026_detect(struct i2c_adapter *adapter, int address, | |||
1690 | return 0; | 1699 | return 0; |
1691 | 1700 | ||
1692 | /* Error out and cleanup code */ | 1701 | /* Error out and cleanup code */ |
1702 | exitdetach: | ||
1703 | i2c_detach_client(new_client); | ||
1693 | exitfree: | 1704 | exitfree: |
1694 | kfree(data); | 1705 | kfree(data); |
1695 | exit: | 1706 | exit: |
diff --git a/drivers/hwmon/adm1031.c b/drivers/hwmon/adm1031.c index 936250957270..58338ed7c8a1 100644 --- a/drivers/hwmon/adm1031.c +++ b/drivers/hwmon/adm1031.c | |||
@@ -26,7 +26,8 @@ | |||
26 | #include <linux/slab.h> | 26 | #include <linux/slab.h> |
27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
28 | #include <linux/i2c.h> | 28 | #include <linux/i2c.h> |
29 | #include <linux/i2c-sensor.h> | 29 | #include <linux/hwmon.h> |
30 | #include <linux/err.h> | ||
30 | 31 | ||
31 | /* Following macros takes channel parameter starting from 0 to 2 */ | 32 | /* Following macros takes channel parameter starting from 0 to 2 */ |
32 | #define ADM1031_REG_FAN_SPEED(nr) (0x08 + (nr)) | 33 | #define ADM1031_REG_FAN_SPEED(nr) (0x08 + (nr)) |
@@ -59,16 +60,16 @@ | |||
59 | 60 | ||
60 | /* Addresses to scan */ | 61 | /* Addresses to scan */ |
61 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; | 62 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; |
62 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
63 | 63 | ||
64 | /* Insmod parameters */ | 64 | /* Insmod parameters */ |
65 | SENSORS_INSMOD_2(adm1030, adm1031); | 65 | I2C_CLIENT_INSMOD_2(adm1030, adm1031); |
66 | 66 | ||
67 | typedef u8 auto_chan_table_t[8][2]; | 67 | typedef u8 auto_chan_table_t[8][2]; |
68 | 68 | ||
69 | /* Each client has this additional data */ | 69 | /* Each client has this additional data */ |
70 | struct adm1031_data { | 70 | struct adm1031_data { |
71 | struct i2c_client client; | 71 | struct i2c_client client; |
72 | struct class_device *class_dev; | ||
72 | struct semaphore update_lock; | 73 | struct semaphore update_lock; |
73 | int chip_type; | 74 | int chip_type; |
74 | char valid; /* !=0 if following fields are valid */ | 75 | char valid; /* !=0 if following fields are valid */ |
@@ -725,10 +726,10 @@ static int adm1031_attach_adapter(struct i2c_adapter *adapter) | |||
725 | { | 726 | { |
726 | if (!(adapter->class & I2C_CLASS_HWMON)) | 727 | if (!(adapter->class & I2C_CLASS_HWMON)) |
727 | return 0; | 728 | return 0; |
728 | return i2c_detect(adapter, &addr_data, adm1031_detect); | 729 | return i2c_probe(adapter, &addr_data, adm1031_detect); |
729 | } | 730 | } |
730 | 731 | ||
731 | /* This function is called by i2c_detect */ | 732 | /* This function is called by i2c_probe */ |
732 | static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) | 733 | static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) |
733 | { | 734 | { |
734 | struct i2c_client *new_client; | 735 | struct i2c_client *new_client; |
@@ -788,6 +789,12 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) | |||
788 | adm1031_init_client(new_client); | 789 | adm1031_init_client(new_client); |
789 | 790 | ||
790 | /* Register sysfs hooks */ | 791 | /* Register sysfs hooks */ |
792 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
793 | if (IS_ERR(data->class_dev)) { | ||
794 | err = PTR_ERR(data->class_dev); | ||
795 | goto exit_detach; | ||
796 | } | ||
797 | |||
791 | device_create_file(&new_client->dev, &dev_attr_fan1_input); | 798 | device_create_file(&new_client->dev, &dev_attr_fan1_input); |
792 | device_create_file(&new_client->dev, &dev_attr_fan1_div); | 799 | device_create_file(&new_client->dev, &dev_attr_fan1_div); |
793 | device_create_file(&new_client->dev, &dev_attr_fan1_min); | 800 | device_create_file(&new_client->dev, &dev_attr_fan1_min); |
@@ -833,6 +840,8 @@ static int adm1031_detect(struct i2c_adapter *adapter, int address, int kind) | |||
833 | 840 | ||
834 | return 0; | 841 | return 0; |
835 | 842 | ||
843 | exit_detach: | ||
844 | i2c_detach_client(new_client); | ||
836 | exit_free: | 845 | exit_free: |
837 | kfree(data); | 846 | kfree(data); |
838 | exit: | 847 | exit: |
@@ -841,11 +850,14 @@ exit: | |||
841 | 850 | ||
842 | static int adm1031_detach_client(struct i2c_client *client) | 851 | static int adm1031_detach_client(struct i2c_client *client) |
843 | { | 852 | { |
853 | struct adm1031_data *data = i2c_get_clientdata(client); | ||
844 | int ret; | 854 | int ret; |
855 | |||
856 | hwmon_device_unregister(data->class_dev); | ||
845 | if ((ret = i2c_detach_client(client)) != 0) { | 857 | if ((ret = i2c_detach_client(client)) != 0) { |
846 | return ret; | 858 | return ret; |
847 | } | 859 | } |
848 | kfree(i2c_get_clientdata(client)); | 860 | kfree(data); |
849 | return 0; | 861 | return 0; |
850 | } | 862 | } |
851 | 863 | ||
diff --git a/drivers/hwmon/adm9240.c b/drivers/hwmon/adm9240.c index ce2a6eb93f6e..bc7faef162f7 100644 --- a/drivers/hwmon/adm9240.c +++ b/drivers/hwmon/adm9240.c | |||
@@ -45,17 +45,16 @@ | |||
45 | #include <linux/module.h> | 45 | #include <linux/module.h> |
46 | #include <linux/slab.h> | 46 | #include <linux/slab.h> |
47 | #include <linux/i2c.h> | 47 | #include <linux/i2c.h> |
48 | #include <linux/i2c-sensor.h> | 48 | #include <linux/hwmon.h> |
49 | #include <linux/i2c-vid.h> | 49 | #include <linux/hwmon-vid.h> |
50 | #include <linux/err.h> | ||
50 | 51 | ||
51 | /* Addresses to scan */ | 52 | /* Addresses to scan */ |
52 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, 0x2f, | 53 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, 0x2f, |
53 | I2C_CLIENT_END }; | 54 | I2C_CLIENT_END }; |
54 | 55 | ||
55 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
56 | |||
57 | /* Insmod parameters */ | 56 | /* Insmod parameters */ |
58 | SENSORS_INSMOD_3(adm9240, ds1780, lm81); | 57 | I2C_CLIENT_INSMOD_3(adm9240, ds1780, lm81); |
59 | 58 | ||
60 | /* ADM9240 registers */ | 59 | /* ADM9240 registers */ |
61 | #define ADM9240_REG_MAN_ID 0x3e | 60 | #define ADM9240_REG_MAN_ID 0x3e |
@@ -150,6 +149,7 @@ static struct i2c_driver adm9240_driver = { | |||
150 | struct adm9240_data { | 149 | struct adm9240_data { |
151 | enum chips type; | 150 | enum chips type; |
152 | struct i2c_client client; | 151 | struct i2c_client client; |
152 | struct class_device *class_dev; | ||
153 | struct semaphore update_lock; | 153 | struct semaphore update_lock; |
154 | char valid; | 154 | char valid; |
155 | unsigned long last_updated_measure; | 155 | unsigned long last_updated_measure; |
@@ -582,6 +582,12 @@ static int adm9240_detect(struct i2c_adapter *adapter, int address, int kind) | |||
582 | adm9240_init_client(new_client); | 582 | adm9240_init_client(new_client); |
583 | 583 | ||
584 | /* populate sysfs filesystem */ | 584 | /* populate sysfs filesystem */ |
585 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
586 | if (IS_ERR(data->class_dev)) { | ||
587 | err = PTR_ERR(data->class_dev); | ||
588 | goto exit_detach; | ||
589 | } | ||
590 | |||
585 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 591 | device_create_file(&new_client->dev, &dev_attr_in0_input); |
586 | device_create_file(&new_client->dev, &dev_attr_in0_min); | 592 | device_create_file(&new_client->dev, &dev_attr_in0_min); |
587 | device_create_file(&new_client->dev, &dev_attr_in0_max); | 593 | device_create_file(&new_client->dev, &dev_attr_in0_max); |
@@ -615,6 +621,9 @@ static int adm9240_detect(struct i2c_adapter *adapter, int address, int kind) | |||
615 | device_create_file(&new_client->dev, &dev_attr_cpu0_vid); | 621 | device_create_file(&new_client->dev, &dev_attr_cpu0_vid); |
616 | 622 | ||
617 | return 0; | 623 | return 0; |
624 | |||
625 | exit_detach: | ||
626 | i2c_detach_client(new_client); | ||
618 | exit_free: | 627 | exit_free: |
619 | kfree(data); | 628 | kfree(data); |
620 | exit: | 629 | exit: |
@@ -625,20 +634,20 @@ static int adm9240_attach_adapter(struct i2c_adapter *adapter) | |||
625 | { | 634 | { |
626 | if (!(adapter->class & I2C_CLASS_HWMON)) | 635 | if (!(adapter->class & I2C_CLASS_HWMON)) |
627 | return 0; | 636 | return 0; |
628 | return i2c_detect(adapter, &addr_data, adm9240_detect); | 637 | return i2c_probe(adapter, &addr_data, adm9240_detect); |
629 | } | 638 | } |
630 | 639 | ||
631 | static int adm9240_detach_client(struct i2c_client *client) | 640 | static int adm9240_detach_client(struct i2c_client *client) |
632 | { | 641 | { |
642 | struct adm9240_data *data = i2c_get_clientdata(client); | ||
633 | int err; | 643 | int err; |
634 | 644 | ||
635 | if ((err = i2c_detach_client(client))) { | 645 | hwmon_device_unregister(data->class_dev); |
636 | dev_err(&client->dev, "Client deregistration failed, " | 646 | |
637 | "client not detached.\n"); | 647 | if ((err = i2c_detach_client(client))) |
638 | return err; | 648 | return err; |
639 | } | ||
640 | 649 | ||
641 | kfree(i2c_get_clientdata(client)); | 650 | kfree(data); |
642 | return 0; | 651 | return 0; |
643 | } | 652 | } |
644 | 653 | ||
@@ -648,7 +657,7 @@ static void adm9240_init_client(struct i2c_client *client) | |||
648 | u8 conf = adm9240_read_value(client, ADM9240_REG_CONFIG); | 657 | u8 conf = adm9240_read_value(client, ADM9240_REG_CONFIG); |
649 | u8 mode = adm9240_read_value(client, ADM9240_REG_TEMP_CONF) & 3; | 658 | u8 mode = adm9240_read_value(client, ADM9240_REG_TEMP_CONF) & 3; |
650 | 659 | ||
651 | data->vrm = i2c_which_vrm(); /* need this to report vid as mV */ | 660 | data->vrm = vid_which_vrm(); /* need this to report vid as mV */ |
652 | 661 | ||
653 | dev_info(&client->dev, "Using VRM: %d.%d\n", data->vrm / 10, | 662 | dev_info(&client->dev, "Using VRM: %d.%d\n", data->vrm / 10, |
654 | data->vrm % 10); | 663 | data->vrm % 10); |
diff --git a/drivers/hwmon/asb100.c b/drivers/hwmon/asb100.c index 70d996d6fe0a..8e34855a6274 100644 --- a/drivers/hwmon/asb100.c +++ b/drivers/hwmon/asb100.c | |||
@@ -39,8 +39,9 @@ | |||
39 | #include <linux/module.h> | 39 | #include <linux/module.h> |
40 | #include <linux/slab.h> | 40 | #include <linux/slab.h> |
41 | #include <linux/i2c.h> | 41 | #include <linux/i2c.h> |
42 | #include <linux/i2c-sensor.h> | 42 | #include <linux/hwmon.h> |
43 | #include <linux/i2c-vid.h> | 43 | #include <linux/hwmon-vid.h> |
44 | #include <linux/err.h> | ||
44 | #include <linux/init.h> | 45 | #include <linux/init.h> |
45 | #include <linux/jiffies.h> | 46 | #include <linux/jiffies.h> |
46 | #include "lm75.h" | 47 | #include "lm75.h" |
@@ -54,11 +55,8 @@ | |||
54 | /* I2C addresses to scan */ | 55 | /* I2C addresses to scan */ |
55 | static unsigned short normal_i2c[] = { 0x2d, I2C_CLIENT_END }; | 56 | static unsigned short normal_i2c[] = { 0x2d, I2C_CLIENT_END }; |
56 | 57 | ||
57 | /* ISA addresses to scan (none) */ | ||
58 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
59 | |||
60 | /* Insmod parameters */ | 58 | /* Insmod parameters */ |
61 | SENSORS_INSMOD_1(asb100); | 59 | I2C_CLIENT_INSMOD_1(asb100); |
62 | I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: " | 60 | I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: " |
63 | "{bus, clientaddr, subclientaddr1, subclientaddr2}"); | 61 | "{bus, clientaddr, subclientaddr1, subclientaddr2}"); |
64 | 62 | ||
@@ -183,6 +181,7 @@ static u8 DIV_TO_REG(long val) | |||
183 | dynamically allocated, at the same time the client itself is allocated. */ | 181 | dynamically allocated, at the same time the client itself is allocated. */ |
184 | struct asb100_data { | 182 | struct asb100_data { |
185 | struct i2c_client client; | 183 | struct i2c_client client; |
184 | struct class_device *class_dev; | ||
186 | struct semaphore lock; | 185 | struct semaphore lock; |
187 | enum chips type; | 186 | enum chips type; |
188 | 187 | ||
@@ -621,7 +620,7 @@ static int asb100_attach_adapter(struct i2c_adapter *adapter) | |||
621 | { | 620 | { |
622 | if (!(adapter->class & I2C_CLASS_HWMON)) | 621 | if (!(adapter->class & I2C_CLASS_HWMON)) |
623 | return 0; | 622 | return 0; |
624 | return i2c_detect(adapter, &addr_data, asb100_detect); | 623 | return i2c_probe(adapter, &addr_data, asb100_detect); |
625 | } | 624 | } |
626 | 625 | ||
627 | static int asb100_detect_subclients(struct i2c_adapter *adapter, int address, | 626 | static int asb100_detect_subclients(struct i2c_adapter *adapter, int address, |
@@ -714,14 +713,6 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
714 | struct i2c_client *new_client; | 713 | struct i2c_client *new_client; |
715 | struct asb100_data *data; | 714 | struct asb100_data *data; |
716 | 715 | ||
717 | /* asb100 is SMBus only */ | ||
718 | if (i2c_is_isa_adapter(adapter)) { | ||
719 | pr_debug("asb100.o: detect failed, " | ||
720 | "cannot attach to legacy adapter!\n"); | ||
721 | err = -ENODEV; | ||
722 | goto ERROR0; | ||
723 | } | ||
724 | |||
725 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) { | 716 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) { |
726 | pr_debug("asb100.o: detect failed, " | 717 | pr_debug("asb100.o: detect failed, " |
727 | "smbus byte data not supported!\n"); | 718 | "smbus byte data not supported!\n"); |
@@ -821,6 +812,12 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
821 | data->fan_min[2] = asb100_read_value(new_client, ASB100_REG_FAN_MIN(2)); | 812 | data->fan_min[2] = asb100_read_value(new_client, ASB100_REG_FAN_MIN(2)); |
822 | 813 | ||
823 | /* Register sysfs hooks */ | 814 | /* Register sysfs hooks */ |
815 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
816 | if (IS_ERR(data->class_dev)) { | ||
817 | err = PTR_ERR(data->class_dev); | ||
818 | goto ERROR3; | ||
819 | } | ||
820 | |||
824 | device_create_file_in(new_client, 0); | 821 | device_create_file_in(new_client, 0); |
825 | device_create_file_in(new_client, 1); | 822 | device_create_file_in(new_client, 1); |
826 | device_create_file_in(new_client, 2); | 823 | device_create_file_in(new_client, 2); |
@@ -847,6 +844,11 @@ static int asb100_detect(struct i2c_adapter *adapter, int address, int kind) | |||
847 | 844 | ||
848 | return 0; | 845 | return 0; |
849 | 846 | ||
847 | ERROR3: | ||
848 | i2c_detach_client(data->lm75[1]); | ||
849 | i2c_detach_client(data->lm75[0]); | ||
850 | kfree(data->lm75[1]); | ||
851 | kfree(data->lm75[0]); | ||
850 | ERROR2: | 852 | ERROR2: |
851 | i2c_detach_client(new_client); | 853 | i2c_detach_client(new_client); |
852 | ERROR1: | 854 | ERROR1: |
@@ -857,21 +859,23 @@ ERROR0: | |||
857 | 859 | ||
858 | static int asb100_detach_client(struct i2c_client *client) | 860 | static int asb100_detach_client(struct i2c_client *client) |
859 | { | 861 | { |
862 | struct asb100_data *data = i2c_get_clientdata(client); | ||
860 | int err; | 863 | int err; |
861 | 864 | ||
862 | if ((err = i2c_detach_client(client))) { | 865 | /* main client */ |
863 | dev_err(&client->dev, "client deregistration failed; " | 866 | if (data) |
864 | "client not detached.\n"); | 867 | hwmon_device_unregister(data->class_dev); |
868 | |||
869 | if ((err = i2c_detach_client(client))) | ||
865 | return err; | 870 | return err; |
866 | } | ||
867 | 871 | ||
868 | if (i2c_get_clientdata(client)==NULL) { | 872 | /* main client */ |
869 | /* subclients */ | 873 | if (data) |
874 | kfree(data); | ||
875 | |||
876 | /* subclient */ | ||
877 | else | ||
870 | kfree(client); | 878 | kfree(client); |
871 | } else { | ||
872 | /* main client */ | ||
873 | kfree(i2c_get_clientdata(client)); | ||
874 | } | ||
875 | 879 | ||
876 | return 0; | 880 | return 0; |
877 | } | 881 | } |
@@ -969,7 +973,7 @@ static void asb100_init_client(struct i2c_client *client) | |||
969 | 973 | ||
970 | vid = asb100_read_value(client, ASB100_REG_VID_FANDIV) & 0x0f; | 974 | vid = asb100_read_value(client, ASB100_REG_VID_FANDIV) & 0x0f; |
971 | vid |= (asb100_read_value(client, ASB100_REG_CHIPID) & 0x01) << 4; | 975 | vid |= (asb100_read_value(client, ASB100_REG_CHIPID) & 0x01) << 4; |
972 | data->vrm = i2c_which_vrm(); | 976 | data->vrm = vid_which_vrm(); |
973 | vid = vid_from_reg(vid, data->vrm); | 977 | vid = vid_from_reg(vid, data->vrm); |
974 | 978 | ||
975 | /* Start monitoring */ | 979 | /* Start monitoring */ |
diff --git a/drivers/hwmon/atxp1.c b/drivers/hwmon/atxp1.c index fca3fc1cef72..deb4d34c9539 100644 --- a/drivers/hwmon/atxp1.c +++ b/drivers/hwmon/atxp1.c | |||
@@ -23,8 +23,9 @@ | |||
23 | #include <linux/module.h> | 23 | #include <linux/module.h> |
24 | #include <linux/jiffies.h> | 24 | #include <linux/jiffies.h> |
25 | #include <linux/i2c.h> | 25 | #include <linux/i2c.h> |
26 | #include <linux/i2c-sensor.h> | 26 | #include <linux/hwmon.h> |
27 | #include <linux/i2c-vid.h> | 27 | #include <linux/hwmon-vid.h> |
28 | #include <linux/err.h> | ||
28 | 29 | ||
29 | MODULE_LICENSE("GPL"); | 30 | MODULE_LICENSE("GPL"); |
30 | MODULE_DESCRIPTION("System voltages control via Attansic ATXP1"); | 31 | MODULE_DESCRIPTION("System voltages control via Attansic ATXP1"); |
@@ -40,9 +41,8 @@ MODULE_AUTHOR("Sebastian Witt <se.witt@gmx.net>"); | |||
40 | #define ATXP1_GPIO1MASK 0x0f | 41 | #define ATXP1_GPIO1MASK 0x0f |
41 | 42 | ||
42 | static unsigned short normal_i2c[] = { 0x37, 0x4e, I2C_CLIENT_END }; | 43 | static unsigned short normal_i2c[] = { 0x37, 0x4e, I2C_CLIENT_END }; |
43 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
44 | 44 | ||
45 | SENSORS_INSMOD_1(atxp1); | 45 | I2C_CLIENT_INSMOD_1(atxp1); |
46 | 46 | ||
47 | static int atxp1_attach_adapter(struct i2c_adapter * adapter); | 47 | static int atxp1_attach_adapter(struct i2c_adapter * adapter); |
48 | static int atxp1_detach_client(struct i2c_client * client); | 48 | static int atxp1_detach_client(struct i2c_client * client); |
@@ -59,6 +59,7 @@ static struct i2c_driver atxp1_driver = { | |||
59 | 59 | ||
60 | struct atxp1_data { | 60 | struct atxp1_data { |
61 | struct i2c_client client; | 61 | struct i2c_client client; |
62 | struct class_device *class_dev; | ||
62 | struct semaphore update_lock; | 63 | struct semaphore update_lock; |
63 | unsigned long last_updated; | 64 | unsigned long last_updated; |
64 | u8 valid; | 65 | u8 valid; |
@@ -252,7 +253,7 @@ static DEVICE_ATTR(gpio2, S_IRUGO | S_IWUSR, atxp1_showgpio2, atxp1_storegpio2); | |||
252 | 253 | ||
253 | static int atxp1_attach_adapter(struct i2c_adapter *adapter) | 254 | static int atxp1_attach_adapter(struct i2c_adapter *adapter) |
254 | { | 255 | { |
255 | return i2c_detect(adapter, &addr_data, &atxp1_detect); | 256 | return i2c_probe(adapter, &addr_data, &atxp1_detect); |
256 | }; | 257 | }; |
257 | 258 | ||
258 | static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind) | 259 | static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind) |
@@ -295,7 +296,7 @@ static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind) | |||
295 | } | 296 | } |
296 | 297 | ||
297 | /* Get VRM */ | 298 | /* Get VRM */ |
298 | data->vrm = i2c_which_vrm(); | 299 | data->vrm = vid_which_vrm(); |
299 | 300 | ||
300 | if ((data->vrm != 90) && (data->vrm != 91)) { | 301 | if ((data->vrm != 90) && (data->vrm != 91)) { |
301 | dev_err(&new_client->dev, "Not supporting VRM %d.%d\n", | 302 | dev_err(&new_client->dev, "Not supporting VRM %d.%d\n", |
@@ -317,6 +318,12 @@ static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind) | |||
317 | goto exit_free; | 318 | goto exit_free; |
318 | } | 319 | } |
319 | 320 | ||
321 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
322 | if (IS_ERR(data->class_dev)) { | ||
323 | err = PTR_ERR(data->class_dev); | ||
324 | goto exit_detach; | ||
325 | } | ||
326 | |||
320 | device_create_file(&new_client->dev, &dev_attr_gpio1); | 327 | device_create_file(&new_client->dev, &dev_attr_gpio1); |
321 | device_create_file(&new_client->dev, &dev_attr_gpio2); | 328 | device_create_file(&new_client->dev, &dev_attr_gpio2); |
322 | device_create_file(&new_client->dev, &dev_attr_cpu0_vid); | 329 | device_create_file(&new_client->dev, &dev_attr_cpu0_vid); |
@@ -326,6 +333,8 @@ static int atxp1_detect(struct i2c_adapter *adapter, int address, int kind) | |||
326 | 333 | ||
327 | return 0; | 334 | return 0; |
328 | 335 | ||
336 | exit_detach: | ||
337 | i2c_detach_client(new_client); | ||
329 | exit_free: | 338 | exit_free: |
330 | kfree(data); | 339 | kfree(data); |
331 | exit: | 340 | exit: |
@@ -334,14 +343,17 @@ exit: | |||
334 | 343 | ||
335 | static int atxp1_detach_client(struct i2c_client * client) | 344 | static int atxp1_detach_client(struct i2c_client * client) |
336 | { | 345 | { |
346 | struct atxp1_data * data = i2c_get_clientdata(client); | ||
337 | int err; | 347 | int err; |
338 | 348 | ||
349 | hwmon_device_unregister(data->class_dev); | ||
350 | |||
339 | err = i2c_detach_client(client); | 351 | err = i2c_detach_client(client); |
340 | 352 | ||
341 | if (err) | 353 | if (err) |
342 | dev_err(&client->dev, "Failed to detach client.\n"); | 354 | dev_err(&client->dev, "Failed to detach client.\n"); |
343 | else | 355 | else |
344 | kfree(i2c_get_clientdata(client)); | 356 | kfree(data); |
345 | 357 | ||
346 | return err; | 358 | return err; |
347 | }; | 359 | }; |
diff --git a/drivers/hwmon/ds1621.c b/drivers/hwmon/ds1621.c index 5360d58804f6..b0199e063d0e 100644 --- a/drivers/hwmon/ds1621.c +++ b/drivers/hwmon/ds1621.c | |||
@@ -26,16 +26,16 @@ | |||
26 | #include <linux/slab.h> | 26 | #include <linux/slab.h> |
27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
28 | #include <linux/i2c.h> | 28 | #include <linux/i2c.h> |
29 | #include <linux/i2c-sensor.h> | 29 | #include <linux/hwmon.h> |
30 | #include <linux/err.h> | ||
30 | #include "lm75.h" | 31 | #include "lm75.h" |
31 | 32 | ||
32 | /* Addresses to scan */ | 33 | /* Addresses to scan */ |
33 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c, | 34 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c, |
34 | 0x4d, 0x4e, 0x4f, I2C_CLIENT_END }; | 35 | 0x4d, 0x4e, 0x4f, I2C_CLIENT_END }; |
35 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
36 | 36 | ||
37 | /* Insmod parameters */ | 37 | /* Insmod parameters */ |
38 | SENSORS_INSMOD_1(ds1621); | 38 | I2C_CLIENT_INSMOD_1(ds1621); |
39 | static int polarity = -1; | 39 | static int polarity = -1; |
40 | module_param(polarity, int, 0); | 40 | module_param(polarity, int, 0); |
41 | MODULE_PARM_DESC(polarity, "Output's polarity: 0 = active high, 1 = active low"); | 41 | MODULE_PARM_DESC(polarity, "Output's polarity: 0 = active high, 1 = active low"); |
@@ -71,6 +71,7 @@ MODULE_PARM_DESC(polarity, "Output's polarity: 0 = active high, 1 = active low") | |||
71 | /* Each client has this additional data */ | 71 | /* Each client has this additional data */ |
72 | struct ds1621_data { | 72 | struct ds1621_data { |
73 | struct i2c_client client; | 73 | struct i2c_client client; |
74 | struct class_device *class_dev; | ||
74 | struct semaphore update_lock; | 75 | struct semaphore update_lock; |
75 | char valid; /* !=0 if following fields are valid */ | 76 | char valid; /* !=0 if following fields are valid */ |
76 | unsigned long last_updated; /* In jiffies */ | 77 | unsigned long last_updated; /* In jiffies */ |
@@ -179,10 +180,10 @@ static DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, show_temp_max, set_temp_max); | |||
179 | 180 | ||
180 | static int ds1621_attach_adapter(struct i2c_adapter *adapter) | 181 | static int ds1621_attach_adapter(struct i2c_adapter *adapter) |
181 | { | 182 | { |
182 | return i2c_detect(adapter, &addr_data, ds1621_detect); | 183 | return i2c_probe(adapter, &addr_data, ds1621_detect); |
183 | } | 184 | } |
184 | 185 | ||
185 | /* This function is called by i2c_detect */ | 186 | /* This function is called by i2c_probe */ |
186 | int ds1621_detect(struct i2c_adapter *adapter, int address, | 187 | int ds1621_detect(struct i2c_adapter *adapter, int address, |
187 | int kind) | 188 | int kind) |
188 | { | 189 | { |
@@ -250,6 +251,12 @@ int ds1621_detect(struct i2c_adapter *adapter, int address, | |||
250 | ds1621_init_client(new_client); | 251 | ds1621_init_client(new_client); |
251 | 252 | ||
252 | /* Register sysfs hooks */ | 253 | /* Register sysfs hooks */ |
254 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
255 | if (IS_ERR(data->class_dev)) { | ||
256 | err = PTR_ERR(data->class_dev); | ||
257 | goto exit_detach; | ||
258 | } | ||
259 | |||
253 | device_create_file(&new_client->dev, &dev_attr_alarms); | 260 | device_create_file(&new_client->dev, &dev_attr_alarms); |
254 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 261 | device_create_file(&new_client->dev, &dev_attr_temp1_input); |
255 | device_create_file(&new_client->dev, &dev_attr_temp1_min); | 262 | device_create_file(&new_client->dev, &dev_attr_temp1_min); |
@@ -259,6 +266,8 @@ int ds1621_detect(struct i2c_adapter *adapter, int address, | |||
259 | 266 | ||
260 | /* OK, this is not exactly good programming practice, usually. But it is | 267 | /* OK, this is not exactly good programming practice, usually. But it is |
261 | very code-efficient in this case. */ | 268 | very code-efficient in this case. */ |
269 | exit_detach: | ||
270 | i2c_detach_client(new_client); | ||
262 | exit_free: | 271 | exit_free: |
263 | kfree(data); | 272 | kfree(data); |
264 | exit: | 273 | exit: |
@@ -267,15 +276,15 @@ int ds1621_detect(struct i2c_adapter *adapter, int address, | |||
267 | 276 | ||
268 | static int ds1621_detach_client(struct i2c_client *client) | 277 | static int ds1621_detach_client(struct i2c_client *client) |
269 | { | 278 | { |
279 | struct ds1621_data *data = i2c_get_clientdata(client); | ||
270 | int err; | 280 | int err; |
271 | 281 | ||
272 | if ((err = i2c_detach_client(client))) { | 282 | hwmon_device_unregister(data->class_dev); |
273 | dev_err(&client->dev, "Client deregistration failed, " | 283 | |
274 | "client not detached.\n"); | 284 | if ((err = i2c_detach_client(client))) |
275 | return err; | 285 | return err; |
276 | } | ||
277 | 286 | ||
278 | kfree(i2c_get_clientdata(client)); | 287 | kfree(data); |
279 | 288 | ||
280 | return 0; | 289 | return 0; |
281 | } | 290 | } |
diff --git a/drivers/hwmon/fscher.c b/drivers/hwmon/fscher.c index da411741c2c5..eef6061d786b 100644 --- a/drivers/hwmon/fscher.c +++ b/drivers/hwmon/fscher.c | |||
@@ -31,20 +31,20 @@ | |||
31 | #include <linux/slab.h> | 31 | #include <linux/slab.h> |
32 | #include <linux/jiffies.h> | 32 | #include <linux/jiffies.h> |
33 | #include <linux/i2c.h> | 33 | #include <linux/i2c.h> |
34 | #include <linux/i2c-sensor.h> | 34 | #include <linux/hwmon.h> |
35 | #include <linux/err.h> | ||
35 | 36 | ||
36 | /* | 37 | /* |
37 | * Addresses to scan | 38 | * Addresses to scan |
38 | */ | 39 | */ |
39 | 40 | ||
40 | static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END }; | 41 | static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END }; |
41 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
42 | 42 | ||
43 | /* | 43 | /* |
44 | * Insmod parameters | 44 | * Insmod parameters |
45 | */ | 45 | */ |
46 | 46 | ||
47 | SENSORS_INSMOD_1(fscher); | 47 | I2C_CLIENT_INSMOD_1(fscher); |
48 | 48 | ||
49 | /* | 49 | /* |
50 | * The FSCHER registers | 50 | * The FSCHER registers |
@@ -132,6 +132,7 @@ static struct i2c_driver fscher_driver = { | |||
132 | 132 | ||
133 | struct fscher_data { | 133 | struct fscher_data { |
134 | struct i2c_client client; | 134 | struct i2c_client client; |
135 | struct class_device *class_dev; | ||
135 | struct semaphore update_lock; | 136 | struct semaphore update_lock; |
136 | char valid; /* zero until following fields are valid */ | 137 | char valid; /* zero until following fields are valid */ |
137 | unsigned long last_updated; /* in jiffies */ | 138 | unsigned long last_updated; /* in jiffies */ |
@@ -287,7 +288,7 @@ static int fscher_attach_adapter(struct i2c_adapter *adapter) | |||
287 | { | 288 | { |
288 | if (!(adapter->class & I2C_CLASS_HWMON)) | 289 | if (!(adapter->class & I2C_CLASS_HWMON)) |
289 | return 0; | 290 | return 0; |
290 | return i2c_detect(adapter, &addr_data, fscher_detect); | 291 | return i2c_probe(adapter, &addr_data, fscher_detect); |
291 | } | 292 | } |
292 | 293 | ||
293 | static int fscher_detect(struct i2c_adapter *adapter, int address, int kind) | 294 | static int fscher_detect(struct i2c_adapter *adapter, int address, int kind) |
@@ -341,6 +342,12 @@ static int fscher_detect(struct i2c_adapter *adapter, int address, int kind) | |||
341 | fscher_init_client(new_client); | 342 | fscher_init_client(new_client); |
342 | 343 | ||
343 | /* Register sysfs hooks */ | 344 | /* Register sysfs hooks */ |
345 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
346 | if (IS_ERR(data->class_dev)) { | ||
347 | err = PTR_ERR(data->class_dev); | ||
348 | goto exit_detach; | ||
349 | } | ||
350 | |||
344 | device_create_file_revision(new_client); | 351 | device_create_file_revision(new_client); |
345 | device_create_file_alarms(new_client); | 352 | device_create_file_alarms(new_client); |
346 | device_create_file_control(new_client); | 353 | device_create_file_control(new_client); |
@@ -360,6 +367,8 @@ static int fscher_detect(struct i2c_adapter *adapter, int address, int kind) | |||
360 | 367 | ||
361 | return 0; | 368 | return 0; |
362 | 369 | ||
370 | exit_detach: | ||
371 | i2c_detach_client(new_client); | ||
363 | exit_free: | 372 | exit_free: |
364 | kfree(data); | 373 | kfree(data); |
365 | exit: | 374 | exit: |
@@ -368,15 +377,15 @@ exit: | |||
368 | 377 | ||
369 | static int fscher_detach_client(struct i2c_client *client) | 378 | static int fscher_detach_client(struct i2c_client *client) |
370 | { | 379 | { |
380 | struct fscher_data *data = i2c_get_clientdata(client); | ||
371 | int err; | 381 | int err; |
372 | 382 | ||
373 | if ((err = i2c_detach_client(client))) { | 383 | hwmon_device_unregister(data->class_dev); |
374 | dev_err(&client->dev, "Client deregistration failed, " | 384 | |
375 | "client not detached.\n"); | 385 | if ((err = i2c_detach_client(client))) |
376 | return err; | 386 | return err; |
377 | } | ||
378 | 387 | ||
379 | kfree(i2c_get_clientdata(client)); | 388 | kfree(data); |
380 | return 0; | 389 | return 0; |
381 | } | 390 | } |
382 | 391 | ||
diff --git a/drivers/hwmon/fscpos.c b/drivers/hwmon/fscpos.c index 301ae98bd0ad..5fc77a5fed07 100644 --- a/drivers/hwmon/fscpos.c +++ b/drivers/hwmon/fscpos.c | |||
@@ -34,19 +34,19 @@ | |||
34 | #include <linux/slab.h> | 34 | #include <linux/slab.h> |
35 | #include <linux/jiffies.h> | 35 | #include <linux/jiffies.h> |
36 | #include <linux/i2c.h> | 36 | #include <linux/i2c.h> |
37 | #include <linux/i2c-sensor.h> | ||
38 | #include <linux/init.h> | 37 | #include <linux/init.h> |
38 | #include <linux/hwmon.h> | ||
39 | #include <linux/err.h> | ||
39 | 40 | ||
40 | /* | 41 | /* |
41 | * Addresses to scan | 42 | * Addresses to scan |
42 | */ | 43 | */ |
43 | static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END }; | 44 | static unsigned short normal_i2c[] = { 0x73, I2C_CLIENT_END }; |
44 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
45 | 45 | ||
46 | /* | 46 | /* |
47 | * Insmod parameters | 47 | * Insmod parameters |
48 | */ | 48 | */ |
49 | SENSORS_INSMOD_1(fscpos); | 49 | I2C_CLIENT_INSMOD_1(fscpos); |
50 | 50 | ||
51 | /* | 51 | /* |
52 | * The FSCPOS registers | 52 | * The FSCPOS registers |
@@ -113,6 +113,7 @@ static struct i2c_driver fscpos_driver = { | |||
113 | */ | 113 | */ |
114 | struct fscpos_data { | 114 | struct fscpos_data { |
115 | struct i2c_client client; | 115 | struct i2c_client client; |
116 | struct class_device *class_dev; | ||
116 | struct semaphore update_lock; | 117 | struct semaphore update_lock; |
117 | char valid; /* 0 until following fields are valid */ | 118 | char valid; /* 0 until following fields are valid */ |
118 | unsigned long last_updated; /* In jiffies */ | 119 | unsigned long last_updated; /* In jiffies */ |
@@ -434,7 +435,7 @@ static int fscpos_attach_adapter(struct i2c_adapter *adapter) | |||
434 | { | 435 | { |
435 | if (!(adapter->class & I2C_CLASS_HWMON)) | 436 | if (!(adapter->class & I2C_CLASS_HWMON)) |
436 | return 0; | 437 | return 0; |
437 | return i2c_detect(adapter, &addr_data, fscpos_detect); | 438 | return i2c_probe(adapter, &addr_data, fscpos_detect); |
438 | } | 439 | } |
439 | 440 | ||
440 | int fscpos_detect(struct i2c_adapter *adapter, int address, int kind) | 441 | int fscpos_detect(struct i2c_adapter *adapter, int address, int kind) |
@@ -496,6 +497,12 @@ int fscpos_detect(struct i2c_adapter *adapter, int address, int kind) | |||
496 | dev_info(&new_client->dev, "Found fscpos chip, rev %u\n", data->revision); | 497 | dev_info(&new_client->dev, "Found fscpos chip, rev %u\n", data->revision); |
497 | 498 | ||
498 | /* Register sysfs hooks */ | 499 | /* Register sysfs hooks */ |
500 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
501 | if (IS_ERR(data->class_dev)) { | ||
502 | err = PTR_ERR(data->class_dev); | ||
503 | goto exit_detach; | ||
504 | } | ||
505 | |||
499 | device_create_file(&new_client->dev, &dev_attr_event); | 506 | device_create_file(&new_client->dev, &dev_attr_event); |
500 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 507 | device_create_file(&new_client->dev, &dev_attr_in0_input); |
501 | device_create_file(&new_client->dev, &dev_attr_in1_input); | 508 | device_create_file(&new_client->dev, &dev_attr_in1_input); |
@@ -526,6 +533,8 @@ int fscpos_detect(struct i2c_adapter *adapter, int address, int kind) | |||
526 | 533 | ||
527 | return 0; | 534 | return 0; |
528 | 535 | ||
536 | exit_detach: | ||
537 | i2c_detach_client(new_client); | ||
529 | exit_free: | 538 | exit_free: |
530 | kfree(data); | 539 | kfree(data); |
531 | exit: | 540 | exit: |
@@ -534,14 +543,14 @@ exit: | |||
534 | 543 | ||
535 | static int fscpos_detach_client(struct i2c_client *client) | 544 | static int fscpos_detach_client(struct i2c_client *client) |
536 | { | 545 | { |
546 | struct fscpos_data *data = i2c_get_clientdata(client); | ||
537 | int err; | 547 | int err; |
538 | 548 | ||
539 | if ((err = i2c_detach_client(client))) { | 549 | hwmon_device_unregister(data->class_dev); |
540 | dev_err(&client->dev, "Client deregistration failed, client" | 550 | |
541 | " not detached.\n"); | 551 | if ((err = i2c_detach_client(client))) |
542 | return err; | 552 | return err; |
543 | } | 553 | kfree(data); |
544 | kfree(i2c_get_clientdata(client)); | ||
545 | return 0; | 554 | return 0; |
546 | } | 555 | } |
547 | 556 | ||
diff --git a/drivers/hwmon/gl518sm.c b/drivers/hwmon/gl518sm.c index 6bedf729dcf5..256b9323c84b 100644 --- a/drivers/hwmon/gl518sm.c +++ b/drivers/hwmon/gl518sm.c | |||
@@ -41,14 +41,14 @@ | |||
41 | #include <linux/slab.h> | 41 | #include <linux/slab.h> |
42 | #include <linux/jiffies.h> | 42 | #include <linux/jiffies.h> |
43 | #include <linux/i2c.h> | 43 | #include <linux/i2c.h> |
44 | #include <linux/i2c-sensor.h> | 44 | #include <linux/hwmon.h> |
45 | #include <linux/err.h> | ||
45 | 46 | ||
46 | /* Addresses to scan */ | 47 | /* Addresses to scan */ |
47 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, I2C_CLIENT_END }; | 48 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, I2C_CLIENT_END }; |
48 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
49 | 49 | ||
50 | /* Insmod parameters */ | 50 | /* Insmod parameters */ |
51 | SENSORS_INSMOD_2(gl518sm_r00, gl518sm_r80); | 51 | I2C_CLIENT_INSMOD_2(gl518sm_r00, gl518sm_r80); |
52 | 52 | ||
53 | /* Many GL518 constants specified below */ | 53 | /* Many GL518 constants specified below */ |
54 | 54 | ||
@@ -117,6 +117,7 @@ static inline u8 FAN_TO_REG(long rpm, int div) | |||
117 | /* Each client has this additional data */ | 117 | /* Each client has this additional data */ |
118 | struct gl518_data { | 118 | struct gl518_data { |
119 | struct i2c_client client; | 119 | struct i2c_client client; |
120 | struct class_device *class_dev; | ||
120 | enum chips type; | 121 | enum chips type; |
121 | 122 | ||
122 | struct semaphore update_lock; | 123 | struct semaphore update_lock; |
@@ -346,7 +347,7 @@ static int gl518_attach_adapter(struct i2c_adapter *adapter) | |||
346 | { | 347 | { |
347 | if (!(adapter->class & I2C_CLASS_HWMON)) | 348 | if (!(adapter->class & I2C_CLASS_HWMON)) |
348 | return 0; | 349 | return 0; |
349 | return i2c_detect(adapter, &addr_data, gl518_detect); | 350 | return i2c_probe(adapter, &addr_data, gl518_detect); |
350 | } | 351 | } |
351 | 352 | ||
352 | static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) | 353 | static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) |
@@ -419,6 +420,12 @@ static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) | |||
419 | gl518_init_client((struct i2c_client *) new_client); | 420 | gl518_init_client((struct i2c_client *) new_client); |
420 | 421 | ||
421 | /* Register sysfs hooks */ | 422 | /* Register sysfs hooks */ |
423 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
424 | if (IS_ERR(data->class_dev)) { | ||
425 | err = PTR_ERR(data->class_dev); | ||
426 | goto exit_detach; | ||
427 | } | ||
428 | |||
422 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 429 | device_create_file(&new_client->dev, &dev_attr_in0_input); |
423 | device_create_file(&new_client->dev, &dev_attr_in1_input); | 430 | device_create_file(&new_client->dev, &dev_attr_in1_input); |
424 | device_create_file(&new_client->dev, &dev_attr_in2_input); | 431 | device_create_file(&new_client->dev, &dev_attr_in2_input); |
@@ -450,6 +457,8 @@ static int gl518_detect(struct i2c_adapter *adapter, int address, int kind) | |||
450 | /* OK, this is not exactly good programming practice, usually. But it is | 457 | /* OK, this is not exactly good programming practice, usually. But it is |
451 | very code-efficient in this case. */ | 458 | very code-efficient in this case. */ |
452 | 459 | ||
460 | exit_detach: | ||
461 | i2c_detach_client(new_client); | ||
453 | exit_free: | 462 | exit_free: |
454 | kfree(data); | 463 | kfree(data); |
455 | exit: | 464 | exit: |
@@ -477,16 +486,15 @@ static void gl518_init_client(struct i2c_client *client) | |||
477 | 486 | ||
478 | static int gl518_detach_client(struct i2c_client *client) | 487 | static int gl518_detach_client(struct i2c_client *client) |
479 | { | 488 | { |
489 | struct gl518_data *data = i2c_get_clientdata(client); | ||
480 | int err; | 490 | int err; |
481 | 491 | ||
482 | if ((err = i2c_detach_client(client))) { | 492 | hwmon_device_unregister(data->class_dev); |
483 | dev_err(&client->dev, "Client deregistration failed, " | ||
484 | "client not detached.\n"); | ||
485 | return err; | ||
486 | } | ||
487 | 493 | ||
488 | kfree(i2c_get_clientdata(client)); | 494 | if ((err = i2c_detach_client(client))) |
495 | return err; | ||
489 | 496 | ||
497 | kfree(data); | ||
490 | return 0; | 498 | return 0; |
491 | } | 499 | } |
492 | 500 | ||
diff --git a/drivers/hwmon/gl520sm.c b/drivers/hwmon/gl520sm.c index 80ae8d30c2af..12fd757066fc 100644 --- a/drivers/hwmon/gl520sm.c +++ b/drivers/hwmon/gl520sm.c | |||
@@ -26,8 +26,9 @@ | |||
26 | #include <linux/slab.h> | 26 | #include <linux/slab.h> |
27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
28 | #include <linux/i2c.h> | 28 | #include <linux/i2c.h> |
29 | #include <linux/i2c-sensor.h> | 29 | #include <linux/hwmon.h> |
30 | #include <linux/i2c-vid.h> | 30 | #include <linux/hwmon-vid.h> |
31 | #include <linux/err.h> | ||
31 | 32 | ||
32 | /* Type of the extra sensor */ | 33 | /* Type of the extra sensor */ |
33 | static unsigned short extra_sensor_type; | 34 | static unsigned short extra_sensor_type; |
@@ -36,10 +37,9 @@ MODULE_PARM_DESC(extra_sensor_type, "Type of extra sensor (0=autodetect, 1=tempe | |||
36 | 37 | ||
37 | /* Addresses to scan */ | 38 | /* Addresses to scan */ |
38 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, I2C_CLIENT_END }; | 39 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, I2C_CLIENT_END }; |
39 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
40 | 40 | ||
41 | /* Insmod parameters */ | 41 | /* Insmod parameters */ |
42 | SENSORS_INSMOD_1(gl520sm); | 42 | I2C_CLIENT_INSMOD_1(gl520sm); |
43 | 43 | ||
44 | /* Many GL520 constants specified below | 44 | /* Many GL520 constants specified below |
45 | One of the inputs can be configured as either temp or voltage. | 45 | One of the inputs can be configured as either temp or voltage. |
@@ -120,6 +120,7 @@ static struct i2c_driver gl520_driver = { | |||
120 | /* Client data */ | 120 | /* Client data */ |
121 | struct gl520_data { | 121 | struct gl520_data { |
122 | struct i2c_client client; | 122 | struct i2c_client client; |
123 | struct class_device *class_dev; | ||
123 | struct semaphore update_lock; | 124 | struct semaphore update_lock; |
124 | char valid; /* zero until the following fields are valid */ | 125 | char valid; /* zero until the following fields are valid */ |
125 | unsigned long last_updated; /* in jiffies */ | 126 | unsigned long last_updated; /* in jiffies */ |
@@ -518,7 +519,7 @@ static int gl520_attach_adapter(struct i2c_adapter *adapter) | |||
518 | { | 519 | { |
519 | if (!(adapter->class & I2C_CLASS_HWMON)) | 520 | if (!(adapter->class & I2C_CLASS_HWMON)) |
520 | return 0; | 521 | return 0; |
521 | return i2c_detect(adapter, &addr_data, gl520_detect); | 522 | return i2c_probe(adapter, &addr_data, gl520_detect); |
522 | } | 523 | } |
523 | 524 | ||
524 | static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) | 525 | static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) |
@@ -571,6 +572,12 @@ static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) | |||
571 | gl520_init_client(new_client); | 572 | gl520_init_client(new_client); |
572 | 573 | ||
573 | /* Register sysfs hooks */ | 574 | /* Register sysfs hooks */ |
575 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
576 | if (IS_ERR(data->class_dev)) { | ||
577 | err = PTR_ERR(data->class_dev); | ||
578 | goto exit_detach; | ||
579 | } | ||
580 | |||
574 | device_create_file_vid(new_client, 0); | 581 | device_create_file_vid(new_client, 0); |
575 | 582 | ||
576 | device_create_file_in(new_client, 0); | 583 | device_create_file_in(new_client, 0); |
@@ -592,6 +599,8 @@ static int gl520_detect(struct i2c_adapter *adapter, int address, int kind) | |||
592 | 599 | ||
593 | return 0; | 600 | return 0; |
594 | 601 | ||
602 | exit_detach: | ||
603 | i2c_detach_client(new_client); | ||
595 | exit_free: | 604 | exit_free: |
596 | kfree(data); | 605 | kfree(data); |
597 | exit: | 606 | exit: |
@@ -608,7 +617,7 @@ static void gl520_init_client(struct i2c_client *client) | |||
608 | conf = oldconf = gl520_read_value(client, GL520_REG_CONF); | 617 | conf = oldconf = gl520_read_value(client, GL520_REG_CONF); |
609 | 618 | ||
610 | data->alarm_mask = 0xff; | 619 | data->alarm_mask = 0xff; |
611 | data->vrm = i2c_which_vrm(); | 620 | data->vrm = vid_which_vrm(); |
612 | 621 | ||
613 | if (extra_sensor_type == 1) | 622 | if (extra_sensor_type == 1) |
614 | conf &= ~0x10; | 623 | conf &= ~0x10; |
@@ -639,15 +648,15 @@ static void gl520_init_client(struct i2c_client *client) | |||
639 | 648 | ||
640 | static int gl520_detach_client(struct i2c_client *client) | 649 | static int gl520_detach_client(struct i2c_client *client) |
641 | { | 650 | { |
651 | struct gl520_data *data = i2c_get_clientdata(client); | ||
642 | int err; | 652 | int err; |
643 | 653 | ||
644 | if ((err = i2c_detach_client(client))) { | 654 | hwmon_device_unregister(data->class_dev); |
645 | dev_err(&client->dev, "Client deregistration failed, " | 655 | |
646 | "client not detached.\n"); | 656 | if ((err = i2c_detach_client(client))) |
647 | return err; | 657 | return err; |
648 | } | ||
649 | 658 | ||
650 | kfree(i2c_get_clientdata(client)); | 659 | kfree(data); |
651 | return 0; | 660 | return 0; |
652 | } | 661 | } |
653 | 662 | ||
diff --git a/drivers/hwmon/hwmon-vid.c b/drivers/hwmon/hwmon-vid.c new file mode 100644 index 000000000000..312769ad4dab --- /dev/null +++ b/drivers/hwmon/hwmon-vid.c | |||
@@ -0,0 +1,189 @@ | |||
1 | /* | ||
2 | hwmon-vid.c - VID/VRM/VRD voltage conversions | ||
3 | |||
4 | Copyright (c) 2004 Rudolf Marek <r.marek@sh.cvut.cz> | ||
5 | |||
6 | Partly imported from i2c-vid.h of the lm_sensors project | ||
7 | Copyright (c) 2002 Mark D. Studebaker <mdsxyz123@yahoo.com> | ||
8 | With assistance from Trent Piepho <xyzzy@speakeasy.org> | ||
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/config.h> | ||
26 | #include <linux/module.h> | ||
27 | #include <linux/kernel.h> | ||
28 | #include <linux/hwmon-vid.h> | ||
29 | |||
30 | /* | ||
31 | Common code for decoding VID pins. | ||
32 | |||
33 | References: | ||
34 | |||
35 | For VRM 8.4 to 9.1, "VRM x.y DC-DC Converter Design Guidelines", | ||
36 | available at http://developer.intel.com/. | ||
37 | |||
38 | For VRD 10.0 and up, "VRD x.y Design Guide", | ||
39 | available at http://developer.intel.com/. | ||
40 | |||
41 | AMD Opteron processors don't follow the Intel specifications. | ||
42 | I'm going to "make up" 2.4 as the spec number for the Opterons. | ||
43 | No good reason just a mnemonic for the 24x Opteron processor | ||
44 | series. | ||
45 | |||
46 | Opteron VID encoding is: | ||
47 | 00000 = 1.550 V | ||
48 | 00001 = 1.525 V | ||
49 | . . . . | ||
50 | 11110 = 0.800 V | ||
51 | 11111 = 0.000 V (off) | ||
52 | */ | ||
53 | |||
54 | /* vrm is the VRM/VRD document version multiplied by 10. | ||
55 | val is the 4-, 5- or 6-bit VID code. | ||
56 | Returned value is in mV to avoid floating point in the kernel. */ | ||
57 | int vid_from_reg(int val, int vrm) | ||
58 | { | ||
59 | int vid; | ||
60 | |||
61 | switch(vrm) { | ||
62 | |||
63 | case 0: | ||
64 | return 0; | ||
65 | |||
66 | case 100: /* VRD 10.0 */ | ||
67 | if((val & 0x1f) == 0x1f) | ||
68 | return 0; | ||
69 | if((val & 0x1f) <= 0x09 || val == 0x0a) | ||
70 | vid = 10875 - (val & 0x1f) * 250; | ||
71 | else | ||
72 | vid = 18625 - (val & 0x1f) * 250; | ||
73 | if(val & 0x20) | ||
74 | vid -= 125; | ||
75 | vid /= 10; /* only return 3 dec. places for now */ | ||
76 | return vid; | ||
77 | |||
78 | case 24: /* Opteron processor */ | ||
79 | return(val == 0x1f ? 0 : 1550 - val * 25); | ||
80 | |||
81 | case 91: /* VRM 9.1 */ | ||
82 | case 90: /* VRM 9.0 */ | ||
83 | return(val == 0x1f ? 0 : | ||
84 | 1850 - val * 25); | ||
85 | |||
86 | case 85: /* VRM 8.5 */ | ||
87 | return((val & 0x10 ? 25 : 0) + | ||
88 | ((val & 0x0f) > 0x04 ? 2050 : 1250) - | ||
89 | ((val & 0x0f) * 50)); | ||
90 | |||
91 | case 84: /* VRM 8.4 */ | ||
92 | val &= 0x0f; | ||
93 | /* fall through */ | ||
94 | default: /* VRM 8.2 */ | ||
95 | return(val == 0x1f ? 0 : | ||
96 | val & 0x10 ? 5100 - (val) * 100 : | ||
97 | 2050 - (val) * 50); | ||
98 | } | ||
99 | } | ||
100 | |||
101 | |||
102 | /* | ||
103 | After this point is the code to automatically determine which | ||
104 | VRM/VRD specification should be used depending on the CPU. | ||
105 | */ | ||
106 | |||
107 | struct vrm_model { | ||
108 | u8 vendor; | ||
109 | u8 eff_family; | ||
110 | u8 eff_model; | ||
111 | int vrm_type; | ||
112 | }; | ||
113 | |||
114 | #define ANY 0xFF | ||
115 | |||
116 | #ifdef CONFIG_X86 | ||
117 | |||
118 | static struct vrm_model vrm_models[] = { | ||
119 | {X86_VENDOR_AMD, 0x6, ANY, 90}, /* Athlon Duron etc */ | ||
120 | {X86_VENDOR_AMD, 0xF, ANY, 24}, /* Athlon 64, Opteron */ | ||
121 | {X86_VENDOR_INTEL, 0x6, 0x9, 85}, /* 0.13um too */ | ||
122 | {X86_VENDOR_INTEL, 0x6, 0xB, 85}, /* Tualatin */ | ||
123 | {X86_VENDOR_INTEL, 0x6, ANY, 82}, /* any P6 */ | ||
124 | {X86_VENDOR_INTEL, 0x7, ANY, 0}, /* Itanium */ | ||
125 | {X86_VENDOR_INTEL, 0xF, 0x0, 90}, /* P4 */ | ||
126 | {X86_VENDOR_INTEL, 0xF, 0x1, 90}, /* P4 Willamette */ | ||
127 | {X86_VENDOR_INTEL, 0xF, 0x2, 90}, /* P4 Northwood */ | ||
128 | {X86_VENDOR_INTEL, 0xF, 0x3, 100}, /* P4 Prescott */ | ||
129 | {X86_VENDOR_INTEL, 0xF, 0x4, 100}, /* P4 Prescott */ | ||
130 | {X86_VENDOR_INTEL, 0x10,ANY, 0}, /* Itanium 2 */ | ||
131 | {X86_VENDOR_UNKNOWN, ANY, ANY, 0} /* stop here */ | ||
132 | }; | ||
133 | |||
134 | static int find_vrm(u8 eff_family, u8 eff_model, u8 vendor) | ||
135 | { | ||
136 | int i = 0; | ||
137 | |||
138 | while (vrm_models[i].vendor!=X86_VENDOR_UNKNOWN) { | ||
139 | if (vrm_models[i].vendor==vendor) | ||
140 | if ((vrm_models[i].eff_family==eff_family) | ||
141 | && ((vrm_models[i].eff_model==eff_model) || | ||
142 | (vrm_models[i].eff_model==ANY))) | ||
143 | return vrm_models[i].vrm_type; | ||
144 | i++; | ||
145 | } | ||
146 | |||
147 | return 0; | ||
148 | } | ||
149 | |||
150 | int vid_which_vrm(void) | ||
151 | { | ||
152 | struct cpuinfo_x86 *c = cpu_data; | ||
153 | u32 eax; | ||
154 | u8 eff_family, eff_model; | ||
155 | int vrm_ret; | ||
156 | |||
157 | if (c->x86 < 6) /* Any CPU with family lower than 6 */ | ||
158 | return 0; /* doesn't have VID and/or CPUID */ | ||
159 | |||
160 | eax = cpuid_eax(1); | ||
161 | eff_family = ((eax & 0x00000F00)>>8); | ||
162 | eff_model = ((eax & 0x000000F0)>>4); | ||
163 | if (eff_family == 0xF) { /* use extended model & family */ | ||
164 | eff_family += ((eax & 0x00F00000)>>20); | ||
165 | eff_model += ((eax & 0x000F0000)>>16)<<4; | ||
166 | } | ||
167 | vrm_ret = find_vrm(eff_family,eff_model,c->x86_vendor); | ||
168 | if (vrm_ret == 0) | ||
169 | printk(KERN_INFO "hwmon-vid: Unknown VRM version of your " | ||
170 | "x86 CPU\n"); | ||
171 | return vrm_ret; | ||
172 | } | ||
173 | |||
174 | /* and now something completely different for the non-x86 world */ | ||
175 | #else | ||
176 | int vid_which_vrm(void) | ||
177 | { | ||
178 | printk(KERN_INFO "hwmon-vid: Unknown VRM version of your CPU\n"); | ||
179 | return 0; | ||
180 | } | ||
181 | #endif | ||
182 | |||
183 | EXPORT_SYMBOL(vid_from_reg); | ||
184 | EXPORT_SYMBOL(vid_which_vrm); | ||
185 | |||
186 | MODULE_AUTHOR("Rudolf Marek <r.marek@sh.cvut.cz>"); | ||
187 | |||
188 | MODULE_DESCRIPTION("hwmon-vid driver"); | ||
189 | MODULE_LICENSE("GPL"); | ||
diff --git a/drivers/hwmon/hwmon.c b/drivers/hwmon/hwmon.c new file mode 100644 index 000000000000..9b41c9bd805f --- /dev/null +++ b/drivers/hwmon/hwmon.c | |||
@@ -0,0 +1,98 @@ | |||
1 | /* | ||
2 | hwmon.c - part of lm_sensors, Linux kernel modules for hardware monitoring | ||
3 | |||
4 | This file defines the sysfs class "hwmon", for use by sensors drivers. | ||
5 | |||
6 | Copyright (C) 2005 Mark M. Hoffman <mhoffman@lightlink.com> | ||
7 | |||
8 | This program is free software; you can redistribute it and/or modify | ||
9 | it under the terms of the GNU General Public License as published by | ||
10 | the Free Software Foundation; version 2 of the License. | ||
11 | */ | ||
12 | |||
13 | #include <linux/module.h> | ||
14 | #include <linux/device.h> | ||
15 | #include <linux/err.h> | ||
16 | #include <linux/kdev_t.h> | ||
17 | #include <linux/idr.h> | ||
18 | #include <linux/hwmon.h> | ||
19 | |||
20 | #define HWMON_ID_PREFIX "hwmon" | ||
21 | #define HWMON_ID_FORMAT HWMON_ID_PREFIX "%d" | ||
22 | |||
23 | static struct class *hwmon_class; | ||
24 | |||
25 | static DEFINE_IDR(hwmon_idr); | ||
26 | |||
27 | /** | ||
28 | * hwmon_device_register - register w/ hwmon sysfs class | ||
29 | * @dev: the device to register | ||
30 | * | ||
31 | * hwmon_device_unregister() must be called when the class device is no | ||
32 | * longer needed. | ||
33 | * | ||
34 | * Returns the pointer to the new struct class device. | ||
35 | */ | ||
36 | struct class_device *hwmon_device_register(struct device *dev) | ||
37 | { | ||
38 | struct class_device *cdev; | ||
39 | int id; | ||
40 | |||
41 | if (idr_pre_get(&hwmon_idr, GFP_KERNEL) == 0) | ||
42 | return ERR_PTR(-ENOMEM); | ||
43 | |||
44 | if (idr_get_new(&hwmon_idr, NULL, &id) < 0) | ||
45 | return ERR_PTR(-ENOMEM); | ||
46 | |||
47 | id = id & MAX_ID_MASK; | ||
48 | cdev = class_device_create(hwmon_class, MKDEV(0,0), dev, | ||
49 | HWMON_ID_FORMAT, id); | ||
50 | |||
51 | if (IS_ERR(cdev)) | ||
52 | idr_remove(&hwmon_idr, id); | ||
53 | |||
54 | return cdev; | ||
55 | } | ||
56 | |||
57 | /** | ||
58 | * hwmon_device_unregister - removes the previously registered class device | ||
59 | * | ||
60 | * @cdev: the class device to destroy | ||
61 | */ | ||
62 | void hwmon_device_unregister(struct class_device *cdev) | ||
63 | { | ||
64 | int id; | ||
65 | |||
66 | if (sscanf(cdev->class_id, HWMON_ID_FORMAT, &id) == 1) { | ||
67 | class_device_unregister(cdev); | ||
68 | idr_remove(&hwmon_idr, id); | ||
69 | } else | ||
70 | dev_dbg(cdev->dev, | ||
71 | "hwmon_device_unregister() failed: bad class ID!\n"); | ||
72 | } | ||
73 | |||
74 | static int __init hwmon_init(void) | ||
75 | { | ||
76 | hwmon_class = class_create(THIS_MODULE, "hwmon"); | ||
77 | if (IS_ERR(hwmon_class)) { | ||
78 | printk(KERN_ERR "hwmon.c: couldn't create sysfs class\n"); | ||
79 | return PTR_ERR(hwmon_class); | ||
80 | } | ||
81 | return 0; | ||
82 | } | ||
83 | |||
84 | static void __exit hwmon_exit(void) | ||
85 | { | ||
86 | class_destroy(hwmon_class); | ||
87 | } | ||
88 | |||
89 | module_init(hwmon_init); | ||
90 | module_exit(hwmon_exit); | ||
91 | |||
92 | EXPORT_SYMBOL_GPL(hwmon_device_register); | ||
93 | EXPORT_SYMBOL_GPL(hwmon_device_unregister); | ||
94 | |||
95 | MODULE_AUTHOR("Mark M. Hoffman <mhoffman@lightlink.com>"); | ||
96 | MODULE_DESCRIPTION("hardware monitoring sysfs/class support"); | ||
97 | MODULE_LICENSE("GPL"); | ||
98 | |||
diff --git a/drivers/hwmon/it87.c b/drivers/hwmon/it87.c index db20c9e47393..53cc2b6d6385 100644 --- a/drivers/hwmon/it87.c +++ b/drivers/hwmon/it87.c | |||
@@ -36,19 +36,21 @@ | |||
36 | #include <linux/slab.h> | 36 | #include <linux/slab.h> |
37 | #include <linux/jiffies.h> | 37 | #include <linux/jiffies.h> |
38 | #include <linux/i2c.h> | 38 | #include <linux/i2c.h> |
39 | #include <linux/i2c-sensor.h> | 39 | #include <linux/i2c-isa.h> |
40 | #include <linux/i2c-vid.h> | 40 | #include <linux/hwmon.h> |
41 | #include <linux/hwmon-sysfs.h> | 41 | #include <linux/hwmon-sysfs.h> |
42 | #include <linux/hwmon-vid.h> | ||
43 | #include <linux/err.h> | ||
42 | #include <asm/io.h> | 44 | #include <asm/io.h> |
43 | 45 | ||
44 | 46 | ||
45 | /* Addresses to scan */ | 47 | /* Addresses to scan */ |
46 | static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, | 48 | static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, |
47 | 0x2e, 0x2f, I2C_CLIENT_END }; | 49 | 0x2e, 0x2f, I2C_CLIENT_END }; |
48 | static unsigned int normal_isa[] = { 0x0290, I2C_CLIENT_ISA_END }; | 50 | static unsigned short isa_address = 0x290; |
49 | 51 | ||
50 | /* Insmod parameters */ | 52 | /* Insmod parameters */ |
51 | SENSORS_INSMOD_2(it87, it8712); | 53 | I2C_CLIENT_INSMOD_2(it87, it8712); |
52 | 54 | ||
53 | #define REG 0x2e /* The register to read/write */ | 55 | #define REG 0x2e /* The register to read/write */ |
54 | #define DEV 0x07 /* Register: Logical device select */ | 56 | #define DEV 0x07 /* Register: Logical device select */ |
@@ -192,6 +194,7 @@ static int DIV_TO_REG(int val) | |||
192 | allocated. */ | 194 | allocated. */ |
193 | struct it87_data { | 195 | struct it87_data { |
194 | struct i2c_client client; | 196 | struct i2c_client client; |
197 | struct class_device *class_dev; | ||
195 | struct semaphore lock; | 198 | struct semaphore lock; |
196 | enum chips type; | 199 | enum chips type; |
197 | 200 | ||
@@ -218,7 +221,7 @@ struct it87_data { | |||
218 | 221 | ||
219 | 222 | ||
220 | static int it87_attach_adapter(struct i2c_adapter *adapter); | 223 | static int it87_attach_adapter(struct i2c_adapter *adapter); |
221 | static int it87_find(int *address); | 224 | static int it87_isa_attach_adapter(struct i2c_adapter *adapter); |
222 | static int it87_detect(struct i2c_adapter *adapter, int address, int kind); | 225 | static int it87_detect(struct i2c_adapter *adapter, int address, int kind); |
223 | static int it87_detach_client(struct i2c_client *client); | 226 | static int it87_detach_client(struct i2c_client *client); |
224 | 227 | ||
@@ -239,6 +242,14 @@ static struct i2c_driver it87_driver = { | |||
239 | .detach_client = it87_detach_client, | 242 | .detach_client = it87_detach_client, |
240 | }; | 243 | }; |
241 | 244 | ||
245 | static struct i2c_driver it87_isa_driver = { | ||
246 | .owner = THIS_MODULE, | ||
247 | .name = "it87-isa", | ||
248 | .attach_adapter = it87_isa_attach_adapter, | ||
249 | .detach_client = it87_detach_client, | ||
250 | }; | ||
251 | |||
252 | |||
242 | static ssize_t show_in(struct device *dev, struct device_attribute *attr, | 253 | static ssize_t show_in(struct device *dev, struct device_attribute *attr, |
243 | char *buf) | 254 | char *buf) |
244 | { | 255 | { |
@@ -686,11 +697,16 @@ static int it87_attach_adapter(struct i2c_adapter *adapter) | |||
686 | { | 697 | { |
687 | if (!(adapter->class & I2C_CLASS_HWMON)) | 698 | if (!(adapter->class & I2C_CLASS_HWMON)) |
688 | return 0; | 699 | return 0; |
689 | return i2c_detect(adapter, &addr_data, it87_detect); | 700 | return i2c_probe(adapter, &addr_data, it87_detect); |
690 | } | 701 | } |
691 | 702 | ||
692 | /* SuperIO detection - will change normal_isa[0] if a chip is found */ | 703 | static int it87_isa_attach_adapter(struct i2c_adapter *adapter) |
693 | static int it87_find(int *address) | 704 | { |
705 | return it87_detect(adapter, isa_address, -1); | ||
706 | } | ||
707 | |||
708 | /* SuperIO detection - will change isa_address if a chip is found */ | ||
709 | static int __init it87_find(int *address) | ||
694 | { | 710 | { |
695 | int err = -ENODEV; | 711 | int err = -ENODEV; |
696 | 712 | ||
@@ -721,7 +737,7 @@ exit: | |||
721 | return err; | 737 | return err; |
722 | } | 738 | } |
723 | 739 | ||
724 | /* This function is called by i2c_detect */ | 740 | /* This function is called by i2c_probe */ |
725 | int it87_detect(struct i2c_adapter *adapter, int address, int kind) | 741 | int it87_detect(struct i2c_adapter *adapter, int address, int kind) |
726 | { | 742 | { |
727 | int i; | 743 | int i; |
@@ -738,7 +754,7 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
738 | 754 | ||
739 | /* Reserve the ISA region */ | 755 | /* Reserve the ISA region */ |
740 | if (is_isa) | 756 | if (is_isa) |
741 | if (!request_region(address, IT87_EXTENT, it87_driver.name)) | 757 | if (!request_region(address, IT87_EXTENT, it87_isa_driver.name)) |
742 | goto ERROR0; | 758 | goto ERROR0; |
743 | 759 | ||
744 | /* Probe whether there is anything available on this address. Already | 760 | /* Probe whether there is anything available on this address. Already |
@@ -784,7 +800,7 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
784 | i2c_set_clientdata(new_client, data); | 800 | i2c_set_clientdata(new_client, data); |
785 | new_client->addr = address; | 801 | new_client->addr = address; |
786 | new_client->adapter = adapter; | 802 | new_client->adapter = adapter; |
787 | new_client->driver = &it87_driver; | 803 | new_client->driver = is_isa ? &it87_isa_driver : &it87_driver; |
788 | new_client->flags = 0; | 804 | new_client->flags = 0; |
789 | 805 | ||
790 | /* Now, we do the remaining detection. */ | 806 | /* Now, we do the remaining detection. */ |
@@ -840,6 +856,12 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
840 | it87_init_client(new_client, data); | 856 | it87_init_client(new_client, data); |
841 | 857 | ||
842 | /* Register sysfs hooks */ | 858 | /* Register sysfs hooks */ |
859 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
860 | if (IS_ERR(data->class_dev)) { | ||
861 | err = PTR_ERR(data->class_dev); | ||
862 | goto ERROR3; | ||
863 | } | ||
864 | |||
843 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_input.dev_attr); | 865 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_input.dev_attr); |
844 | device_create_file(&new_client->dev, &sensor_dev_attr_in1_input.dev_attr); | 866 | device_create_file(&new_client->dev, &sensor_dev_attr_in1_input.dev_attr); |
845 | device_create_file(&new_client->dev, &sensor_dev_attr_in2_input.dev_attr); | 867 | device_create_file(&new_client->dev, &sensor_dev_attr_in2_input.dev_attr); |
@@ -897,13 +919,15 @@ int it87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
897 | } | 919 | } |
898 | 920 | ||
899 | if (data->type == it8712) { | 921 | if (data->type == it8712) { |
900 | data->vrm = i2c_which_vrm(); | 922 | data->vrm = vid_which_vrm(); |
901 | device_create_file_vrm(new_client); | 923 | device_create_file_vrm(new_client); |
902 | device_create_file_vid(new_client); | 924 | device_create_file_vid(new_client); |
903 | } | 925 | } |
904 | 926 | ||
905 | return 0; | 927 | return 0; |
906 | 928 | ||
929 | ERROR3: | ||
930 | i2c_detach_client(new_client); | ||
907 | ERROR2: | 931 | ERROR2: |
908 | kfree(data); | 932 | kfree(data); |
909 | ERROR1: | 933 | ERROR1: |
@@ -915,17 +939,17 @@ ERROR0: | |||
915 | 939 | ||
916 | static int it87_detach_client(struct i2c_client *client) | 940 | static int it87_detach_client(struct i2c_client *client) |
917 | { | 941 | { |
942 | struct it87_data *data = i2c_get_clientdata(client); | ||
918 | int err; | 943 | int err; |
919 | 944 | ||
920 | if ((err = i2c_detach_client(client))) { | 945 | hwmon_device_unregister(data->class_dev); |
921 | dev_err(&client->dev, | 946 | |
922 | "Client deregistration failed, client not detached.\n"); | 947 | if ((err = i2c_detach_client(client))) |
923 | return err; | 948 | return err; |
924 | } | ||
925 | 949 | ||
926 | if(i2c_is_isa_client(client)) | 950 | if(i2c_is_isa_client(client)) |
927 | release_region(client->addr, IT87_EXTENT); | 951 | release_region(client->addr, IT87_EXTENT); |
928 | kfree(i2c_get_clientdata(client)); | 952 | kfree(data); |
929 | 953 | ||
930 | return 0; | 954 | return 0; |
931 | } | 955 | } |
@@ -1158,16 +1182,28 @@ static struct it87_data *it87_update_device(struct device *dev) | |||
1158 | 1182 | ||
1159 | static int __init sm_it87_init(void) | 1183 | static int __init sm_it87_init(void) |
1160 | { | 1184 | { |
1161 | int addr; | 1185 | int addr, res; |
1162 | 1186 | ||
1163 | if (!it87_find(&addr)) { | 1187 | if (!it87_find(&addr)) { |
1164 | normal_isa[0] = addr; | 1188 | isa_address = addr; |
1189 | } | ||
1190 | |||
1191 | res = i2c_add_driver(&it87_driver); | ||
1192 | if (res) | ||
1193 | return res; | ||
1194 | |||
1195 | res = i2c_isa_add_driver(&it87_isa_driver); | ||
1196 | if (res) { | ||
1197 | i2c_del_driver(&it87_driver); | ||
1198 | return res; | ||
1165 | } | 1199 | } |
1166 | return i2c_add_driver(&it87_driver); | 1200 | |
1201 | return 0; | ||
1167 | } | 1202 | } |
1168 | 1203 | ||
1169 | static void __exit sm_it87_exit(void) | 1204 | static void __exit sm_it87_exit(void) |
1170 | { | 1205 | { |
1206 | i2c_isa_del_driver(&it87_isa_driver); | ||
1171 | i2c_del_driver(&it87_driver); | 1207 | i2c_del_driver(&it87_driver); |
1172 | } | 1208 | } |
1173 | 1209 | ||
diff --git a/drivers/hwmon/lm63.c b/drivers/hwmon/lm63.c index 7c6f9ea5a254..be5c7095ecbb 100644 --- a/drivers/hwmon/lm63.c +++ b/drivers/hwmon/lm63.c | |||
@@ -42,8 +42,9 @@ | |||
42 | #include <linux/slab.h> | 42 | #include <linux/slab.h> |
43 | #include <linux/jiffies.h> | 43 | #include <linux/jiffies.h> |
44 | #include <linux/i2c.h> | 44 | #include <linux/i2c.h> |
45 | #include <linux/i2c-sensor.h> | ||
46 | #include <linux/hwmon-sysfs.h> | 45 | #include <linux/hwmon-sysfs.h> |
46 | #include <linux/hwmon.h> | ||
47 | #include <linux/err.h> | ||
47 | 48 | ||
48 | /* | 49 | /* |
49 | * Addresses to scan | 50 | * Addresses to scan |
@@ -51,13 +52,12 @@ | |||
51 | */ | 52 | */ |
52 | 53 | ||
53 | static unsigned short normal_i2c[] = { 0x4c, I2C_CLIENT_END }; | 54 | static unsigned short normal_i2c[] = { 0x4c, I2C_CLIENT_END }; |
54 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
55 | 55 | ||
56 | /* | 56 | /* |
57 | * Insmod parameters | 57 | * Insmod parameters |
58 | */ | 58 | */ |
59 | 59 | ||
60 | SENSORS_INSMOD_1(lm63); | 60 | I2C_CLIENT_INSMOD_1(lm63); |
61 | 61 | ||
62 | /* | 62 | /* |
63 | * The LM63 registers | 63 | * The LM63 registers |
@@ -152,6 +152,7 @@ static struct i2c_driver lm63_driver = { | |||
152 | 152 | ||
153 | struct lm63_data { | 153 | struct lm63_data { |
154 | struct i2c_client client; | 154 | struct i2c_client client; |
155 | struct class_device *class_dev; | ||
155 | struct semaphore update_lock; | 156 | struct semaphore update_lock; |
156 | char valid; /* zero until following fields are valid */ | 157 | char valid; /* zero until following fields are valid */ |
157 | unsigned long last_updated; /* in jiffies */ | 158 | unsigned long last_updated; /* in jiffies */ |
@@ -358,7 +359,7 @@ static int lm63_attach_adapter(struct i2c_adapter *adapter) | |||
358 | { | 359 | { |
359 | if (!(adapter->class & I2C_CLASS_HWMON)) | 360 | if (!(adapter->class & I2C_CLASS_HWMON)) |
360 | return 0; | 361 | return 0; |
361 | return i2c_detect(adapter, &addr_data, lm63_detect); | 362 | return i2c_probe(adapter, &addr_data, lm63_detect); |
362 | } | 363 | } |
363 | 364 | ||
364 | /* | 365 | /* |
@@ -437,6 +438,12 @@ static int lm63_detect(struct i2c_adapter *adapter, int address, int kind) | |||
437 | lm63_init_client(new_client); | 438 | lm63_init_client(new_client); |
438 | 439 | ||
439 | /* Register sysfs hooks */ | 440 | /* Register sysfs hooks */ |
441 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
442 | if (IS_ERR(data->class_dev)) { | ||
443 | err = PTR_ERR(data->class_dev); | ||
444 | goto exit_detach; | ||
445 | } | ||
446 | |||
440 | if (data->config & 0x04) { /* tachometer enabled */ | 447 | if (data->config & 0x04) { /* tachometer enabled */ |
441 | device_create_file(&new_client->dev, | 448 | device_create_file(&new_client->dev, |
442 | &sensor_dev_attr_fan1_input.dev_attr); | 449 | &sensor_dev_attr_fan1_input.dev_attr); |
@@ -462,6 +469,8 @@ static int lm63_detect(struct i2c_adapter *adapter, int address, int kind) | |||
462 | 469 | ||
463 | return 0; | 470 | return 0; |
464 | 471 | ||
472 | exit_detach: | ||
473 | i2c_detach_client(new_client); | ||
465 | exit_free: | 474 | exit_free: |
466 | kfree(data); | 475 | kfree(data); |
467 | exit: | 476 | exit: |
@@ -505,15 +514,15 @@ static void lm63_init_client(struct i2c_client *client) | |||
505 | 514 | ||
506 | static int lm63_detach_client(struct i2c_client *client) | 515 | static int lm63_detach_client(struct i2c_client *client) |
507 | { | 516 | { |
517 | struct lm63_data *data = i2c_get_clientdata(client); | ||
508 | int err; | 518 | int err; |
509 | 519 | ||
510 | if ((err = i2c_detach_client(client))) { | 520 | hwmon_device_unregister(data->class_dev); |
511 | dev_err(&client->dev, "Client deregistration failed, " | 521 | |
512 | "client not detached\n"); | 522 | if ((err = i2c_detach_client(client))) |
513 | return err; | 523 | return err; |
514 | } | ||
515 | 524 | ||
516 | kfree(i2c_get_clientdata(client)); | 525 | kfree(data); |
517 | return 0; | 526 | return 0; |
518 | } | 527 | } |
519 | 528 | ||
diff --git a/drivers/hwmon/lm75.c b/drivers/hwmon/lm75.c index 5be164ed278e..9a3ebdf583f4 100644 --- a/drivers/hwmon/lm75.c +++ b/drivers/hwmon/lm75.c | |||
@@ -23,17 +23,17 @@ | |||
23 | #include <linux/slab.h> | 23 | #include <linux/slab.h> |
24 | #include <linux/jiffies.h> | 24 | #include <linux/jiffies.h> |
25 | #include <linux/i2c.h> | 25 | #include <linux/i2c.h> |
26 | #include <linux/i2c-sensor.h> | 26 | #include <linux/hwmon.h> |
27 | #include <linux/err.h> | ||
27 | #include "lm75.h" | 28 | #include "lm75.h" |
28 | 29 | ||
29 | 30 | ||
30 | /* Addresses to scan */ | 31 | /* Addresses to scan */ |
31 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c, | 32 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, 0x4c, |
32 | 0x4d, 0x4e, 0x4f, I2C_CLIENT_END }; | 33 | 0x4d, 0x4e, 0x4f, I2C_CLIENT_END }; |
33 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
34 | 34 | ||
35 | /* Insmod parameters */ | 35 | /* Insmod parameters */ |
36 | SENSORS_INSMOD_1(lm75); | 36 | I2C_CLIENT_INSMOD_1(lm75); |
37 | 37 | ||
38 | /* Many LM75 constants specified below */ | 38 | /* Many LM75 constants specified below */ |
39 | 39 | ||
@@ -46,6 +46,7 @@ SENSORS_INSMOD_1(lm75); | |||
46 | /* Each client has this additional data */ | 46 | /* Each client has this additional data */ |
47 | struct lm75_data { | 47 | struct lm75_data { |
48 | struct i2c_client client; | 48 | struct i2c_client client; |
49 | struct class_device *class_dev; | ||
49 | struct semaphore update_lock; | 50 | struct semaphore update_lock; |
50 | char valid; /* !=0 if following fields are valid */ | 51 | char valid; /* !=0 if following fields are valid */ |
51 | unsigned long last_updated; /* In jiffies */ | 52 | unsigned long last_updated; /* In jiffies */ |
@@ -107,10 +108,10 @@ static int lm75_attach_adapter(struct i2c_adapter *adapter) | |||
107 | { | 108 | { |
108 | if (!(adapter->class & I2C_CLASS_HWMON)) | 109 | if (!(adapter->class & I2C_CLASS_HWMON)) |
109 | return 0; | 110 | return 0; |
110 | return i2c_detect(adapter, &addr_data, lm75_detect); | 111 | return i2c_probe(adapter, &addr_data, lm75_detect); |
111 | } | 112 | } |
112 | 113 | ||
113 | /* This function is called by i2c_detect */ | 114 | /* This function is called by i2c_probe */ |
114 | static int lm75_detect(struct i2c_adapter *adapter, int address, int kind) | 115 | static int lm75_detect(struct i2c_adapter *adapter, int address, int kind) |
115 | { | 116 | { |
116 | int i; | 117 | int i; |
@@ -119,16 +120,6 @@ static int lm75_detect(struct i2c_adapter *adapter, int address, int kind) | |||
119 | int err = 0; | 120 | int err = 0; |
120 | const char *name = ""; | 121 | const char *name = ""; |
121 | 122 | ||
122 | /* Make sure we aren't probing the ISA bus!! This is just a safety check | ||
123 | at this moment; i2c_detect really won't call us. */ | ||
124 | #ifdef DEBUG | ||
125 | if (i2c_is_isa_adapter(adapter)) { | ||
126 | dev_dbg(&adapter->dev, | ||
127 | "lm75_detect called for an ISA bus adapter?!?\n"); | ||
128 | goto exit; | ||
129 | } | ||
130 | #endif | ||
131 | |||
132 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA | | 123 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA | |
133 | I2C_FUNC_SMBUS_WORD_DATA)) | 124 | I2C_FUNC_SMBUS_WORD_DATA)) |
134 | goto exit; | 125 | goto exit; |
@@ -208,12 +199,20 @@ static int lm75_detect(struct i2c_adapter *adapter, int address, int kind) | |||
208 | lm75_init_client(new_client); | 199 | lm75_init_client(new_client); |
209 | 200 | ||
210 | /* Register sysfs hooks */ | 201 | /* Register sysfs hooks */ |
202 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
203 | if (IS_ERR(data->class_dev)) { | ||
204 | err = PTR_ERR(data->class_dev); | ||
205 | goto exit_detach; | ||
206 | } | ||
207 | |||
211 | device_create_file(&new_client->dev, &dev_attr_temp1_max); | 208 | device_create_file(&new_client->dev, &dev_attr_temp1_max); |
212 | device_create_file(&new_client->dev, &dev_attr_temp1_max_hyst); | 209 | device_create_file(&new_client->dev, &dev_attr_temp1_max_hyst); |
213 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 210 | device_create_file(&new_client->dev, &dev_attr_temp1_input); |
214 | 211 | ||
215 | return 0; | 212 | return 0; |
216 | 213 | ||
214 | exit_detach: | ||
215 | i2c_detach_client(new_client); | ||
217 | exit_free: | 216 | exit_free: |
218 | kfree(data); | 217 | kfree(data); |
219 | exit: | 218 | exit: |
@@ -222,8 +221,10 @@ exit: | |||
222 | 221 | ||
223 | static int lm75_detach_client(struct i2c_client *client) | 222 | static int lm75_detach_client(struct i2c_client *client) |
224 | { | 223 | { |
224 | struct lm75_data *data = i2c_get_clientdata(client); | ||
225 | hwmon_device_unregister(data->class_dev); | ||
225 | i2c_detach_client(client); | 226 | i2c_detach_client(client); |
226 | kfree(i2c_get_clientdata(client)); | 227 | kfree(data); |
227 | return 0; | 228 | return 0; |
228 | } | 229 | } |
229 | 230 | ||
@@ -251,8 +252,12 @@ static int lm75_write_value(struct i2c_client *client, u8 reg, u16 value) | |||
251 | 252 | ||
252 | static void lm75_init_client(struct i2c_client *client) | 253 | static void lm75_init_client(struct i2c_client *client) |
253 | { | 254 | { |
254 | /* Initialize the LM75 chip */ | 255 | int reg; |
255 | lm75_write_value(client, LM75_REG_CONF, 0); | 256 | |
257 | /* Enable if in shutdown mode */ | ||
258 | reg = lm75_read_value(client, LM75_REG_CONF); | ||
259 | if (reg >= 0 && (reg & 0x01)) | ||
260 | lm75_write_value(client, LM75_REG_CONF, reg & 0xfe); | ||
256 | } | 261 | } |
257 | 262 | ||
258 | static struct lm75_data *lm75_update_device(struct device *dev) | 263 | static struct lm75_data *lm75_update_device(struct device *dev) |
diff --git a/drivers/hwmon/lm75.h b/drivers/hwmon/lm75.h index 63e3f2fb4c21..af7dc650ee15 100644 --- a/drivers/hwmon/lm75.h +++ b/drivers/hwmon/lm75.h | |||
@@ -25,7 +25,7 @@ | |||
25 | which contains this code, we don't worry about the wasted space. | 25 | which contains this code, we don't worry about the wasted space. |
26 | */ | 26 | */ |
27 | 27 | ||
28 | #include <linux/i2c-sensor.h> | 28 | #include <linux/hwmon.h> |
29 | 29 | ||
30 | /* straight from the datasheet */ | 30 | /* straight from the datasheet */ |
31 | #define LM75_TEMP_MIN (-55000) | 31 | #define LM75_TEMP_MIN (-55000) |
diff --git a/drivers/hwmon/lm77.c b/drivers/hwmon/lm77.c index b98f44952997..866eab96a6f6 100644 --- a/drivers/hwmon/lm77.c +++ b/drivers/hwmon/lm77.c | |||
@@ -30,15 +30,14 @@ | |||
30 | #include <linux/slab.h> | 30 | #include <linux/slab.h> |
31 | #include <linux/jiffies.h> | 31 | #include <linux/jiffies.h> |
32 | #include <linux/i2c.h> | 32 | #include <linux/i2c.h> |
33 | #include <linux/i2c-sensor.h> | 33 | #include <linux/hwmon.h> |
34 | 34 | #include <linux/err.h> | |
35 | 35 | ||
36 | /* Addresses to scan */ | 36 | /* Addresses to scan */ |
37 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, I2C_CLIENT_END }; | 37 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, I2C_CLIENT_END }; |
38 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
39 | 38 | ||
40 | /* Insmod parameters */ | 39 | /* Insmod parameters */ |
41 | SENSORS_INSMOD_1(lm77); | 40 | I2C_CLIENT_INSMOD_1(lm77); |
42 | 41 | ||
43 | /* The LM77 registers */ | 42 | /* The LM77 registers */ |
44 | #define LM77_REG_TEMP 0x00 | 43 | #define LM77_REG_TEMP 0x00 |
@@ -51,6 +50,7 @@ SENSORS_INSMOD_1(lm77); | |||
51 | /* Each client has this additional data */ | 50 | /* Each client has this additional data */ |
52 | struct lm77_data { | 51 | struct lm77_data { |
53 | struct i2c_client client; | 52 | struct i2c_client client; |
53 | struct class_device *class_dev; | ||
54 | struct semaphore update_lock; | 54 | struct semaphore update_lock; |
55 | char valid; | 55 | char valid; |
56 | unsigned long last_updated; /* In jiffies */ | 56 | unsigned long last_updated; /* In jiffies */ |
@@ -208,10 +208,10 @@ static int lm77_attach_adapter(struct i2c_adapter *adapter) | |||
208 | { | 208 | { |
209 | if (!(adapter->class & I2C_CLASS_HWMON)) | 209 | if (!(adapter->class & I2C_CLASS_HWMON)) |
210 | return 0; | 210 | return 0; |
211 | return i2c_detect(adapter, &addr_data, lm77_detect); | 211 | return i2c_probe(adapter, &addr_data, lm77_detect); |
212 | } | 212 | } |
213 | 213 | ||
214 | /* This function is called by i2c_detect */ | 214 | /* This function is called by i2c_probe */ |
215 | static int lm77_detect(struct i2c_adapter *adapter, int address, int kind) | 215 | static int lm77_detect(struct i2c_adapter *adapter, int address, int kind) |
216 | { | 216 | { |
217 | struct i2c_client *new_client; | 217 | struct i2c_client *new_client; |
@@ -317,6 +317,12 @@ static int lm77_detect(struct i2c_adapter *adapter, int address, int kind) | |||
317 | lm77_init_client(new_client); | 317 | lm77_init_client(new_client); |
318 | 318 | ||
319 | /* Register sysfs hooks */ | 319 | /* Register sysfs hooks */ |
320 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
321 | if (IS_ERR(data->class_dev)) { | ||
322 | err = PTR_ERR(data->class_dev); | ||
323 | goto exit_detach; | ||
324 | } | ||
325 | |||
320 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 326 | device_create_file(&new_client->dev, &dev_attr_temp1_input); |
321 | device_create_file(&new_client->dev, &dev_attr_temp1_crit); | 327 | device_create_file(&new_client->dev, &dev_attr_temp1_crit); |
322 | device_create_file(&new_client->dev, &dev_attr_temp1_min); | 328 | device_create_file(&new_client->dev, &dev_attr_temp1_min); |
@@ -327,6 +333,8 @@ static int lm77_detect(struct i2c_adapter *adapter, int address, int kind) | |||
327 | device_create_file(&new_client->dev, &dev_attr_alarms); | 333 | device_create_file(&new_client->dev, &dev_attr_alarms); |
328 | return 0; | 334 | return 0; |
329 | 335 | ||
336 | exit_detach: | ||
337 | i2c_detach_client(new_client); | ||
330 | exit_free: | 338 | exit_free: |
331 | kfree(data); | 339 | kfree(data); |
332 | exit: | 340 | exit: |
@@ -335,8 +343,10 @@ exit: | |||
335 | 343 | ||
336 | static int lm77_detach_client(struct i2c_client *client) | 344 | static int lm77_detach_client(struct i2c_client *client) |
337 | { | 345 | { |
346 | struct lm77_data *data = i2c_get_clientdata(client); | ||
347 | hwmon_device_unregister(data->class_dev); | ||
338 | i2c_detach_client(client); | 348 | i2c_detach_client(client); |
339 | kfree(i2c_get_clientdata(client)); | 349 | kfree(data); |
340 | return 0; | 350 | return 0; |
341 | } | 351 | } |
342 | 352 | ||
diff --git a/drivers/hwmon/lm78.c b/drivers/hwmon/lm78.c index 29241469dcba..f6730dc3573b 100644 --- a/drivers/hwmon/lm78.c +++ b/drivers/hwmon/lm78.c | |||
@@ -23,7 +23,10 @@ | |||
23 | #include <linux/slab.h> | 23 | #include <linux/slab.h> |
24 | #include <linux/jiffies.h> | 24 | #include <linux/jiffies.h> |
25 | #include <linux/i2c.h> | 25 | #include <linux/i2c.h> |
26 | #include <linux/i2c-sensor.h> | 26 | #include <linux/i2c-isa.h> |
27 | #include <linux/hwmon.h> | ||
28 | #include <linux/hwmon-vid.h> | ||
29 | #include <linux/err.h> | ||
27 | #include <asm/io.h> | 30 | #include <asm/io.h> |
28 | 31 | ||
29 | /* Addresses to scan */ | 32 | /* Addresses to scan */ |
@@ -31,10 +34,10 @@ static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24, | |||
31 | 0x25, 0x26, 0x27, 0x28, 0x29, | 34 | 0x25, 0x26, 0x27, 0x28, 0x29, |
32 | 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, | 35 | 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, |
33 | 0x2f, I2C_CLIENT_END }; | 36 | 0x2f, I2C_CLIENT_END }; |
34 | static unsigned int normal_isa[] = { 0x0290, I2C_CLIENT_ISA_END }; | 37 | static unsigned short isa_address = 0x290; |
35 | 38 | ||
36 | /* Insmod parameters */ | 39 | /* Insmod parameters */ |
37 | SENSORS_INSMOD_3(lm78, lm78j, lm79); | 40 | I2C_CLIENT_INSMOD_2(lm78, lm79); |
38 | 41 | ||
39 | /* Many LM78 constants specified below */ | 42 | /* Many LM78 constants specified below */ |
40 | 43 | ||
@@ -104,13 +107,6 @@ static inline int TEMP_FROM_REG(s8 val) | |||
104 | return val * 1000; | 107 | return val * 1000; |
105 | } | 108 | } |
106 | 109 | ||
107 | /* VID: mV | ||
108 | REG: (see doc/vid) */ | ||
109 | static inline int VID_FROM_REG(u8 val) | ||
110 | { | ||
111 | return val==0x1f ? 0 : val>=0x10 ? 5100-val*100 : 2050-val*50; | ||
112 | } | ||
113 | |||
114 | #define DIV_FROM_REG(val) (1 << (val)) | 110 | #define DIV_FROM_REG(val) (1 << (val)) |
115 | 111 | ||
116 | /* There are some complications in a module like this. First off, LM78 chips | 112 | /* There are some complications in a module like this. First off, LM78 chips |
@@ -134,6 +130,7 @@ static inline int VID_FROM_REG(u8 val) | |||
134 | allocated. */ | 130 | allocated. */ |
135 | struct lm78_data { | 131 | struct lm78_data { |
136 | struct i2c_client client; | 132 | struct i2c_client client; |
133 | struct class_device *class_dev; | ||
137 | struct semaphore lock; | 134 | struct semaphore lock; |
138 | enum chips type; | 135 | enum chips type; |
139 | 136 | ||
@@ -156,6 +153,7 @@ struct lm78_data { | |||
156 | 153 | ||
157 | 154 | ||
158 | static int lm78_attach_adapter(struct i2c_adapter *adapter); | 155 | static int lm78_attach_adapter(struct i2c_adapter *adapter); |
156 | static int lm78_isa_attach_adapter(struct i2c_adapter *adapter); | ||
159 | static int lm78_detect(struct i2c_adapter *adapter, int address, int kind); | 157 | static int lm78_detect(struct i2c_adapter *adapter, int address, int kind); |
160 | static int lm78_detach_client(struct i2c_client *client); | 158 | static int lm78_detach_client(struct i2c_client *client); |
161 | 159 | ||
@@ -174,6 +172,14 @@ static struct i2c_driver lm78_driver = { | |||
174 | .detach_client = lm78_detach_client, | 172 | .detach_client = lm78_detach_client, |
175 | }; | 173 | }; |
176 | 174 | ||
175 | static struct i2c_driver lm78_isa_driver = { | ||
176 | .owner = THIS_MODULE, | ||
177 | .name = "lm78-isa", | ||
178 | .attach_adapter = lm78_isa_attach_adapter, | ||
179 | .detach_client = lm78_detach_client, | ||
180 | }; | ||
181 | |||
182 | |||
177 | /* 7 Voltages */ | 183 | /* 7 Voltages */ |
178 | static ssize_t show_in(struct device *dev, char *buf, int nr) | 184 | static ssize_t show_in(struct device *dev, char *buf, int nr) |
179 | { | 185 | { |
@@ -445,7 +451,7 @@ static DEVICE_ATTR(fan3_div, S_IRUGO, show_fan_3_div, NULL); | |||
445 | static ssize_t show_vid(struct device *dev, struct device_attribute *attr, char *buf) | 451 | static ssize_t show_vid(struct device *dev, struct device_attribute *attr, char *buf) |
446 | { | 452 | { |
447 | struct lm78_data *data = lm78_update_device(dev); | 453 | struct lm78_data *data = lm78_update_device(dev); |
448 | return sprintf(buf, "%d\n", VID_FROM_REG(data->vid)); | 454 | return sprintf(buf, "%d\n", vid_from_reg(82, data->vid)); |
449 | } | 455 | } |
450 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid, NULL); | 456 | static DEVICE_ATTR(cpu0_vid, S_IRUGO, show_vid, NULL); |
451 | 457 | ||
@@ -465,10 +471,15 @@ static int lm78_attach_adapter(struct i2c_adapter *adapter) | |||
465 | { | 471 | { |
466 | if (!(adapter->class & I2C_CLASS_HWMON)) | 472 | if (!(adapter->class & I2C_CLASS_HWMON)) |
467 | return 0; | 473 | return 0; |
468 | return i2c_detect(adapter, &addr_data, lm78_detect); | 474 | return i2c_probe(adapter, &addr_data, lm78_detect); |
475 | } | ||
476 | |||
477 | static int lm78_isa_attach_adapter(struct i2c_adapter *adapter) | ||
478 | { | ||
479 | return lm78_detect(adapter, isa_address, -1); | ||
469 | } | 480 | } |
470 | 481 | ||
471 | /* This function is called by i2c_detect */ | 482 | /* This function is called by i2c_probe */ |
472 | int lm78_detect(struct i2c_adapter *adapter, int address, int kind) | 483 | int lm78_detect(struct i2c_adapter *adapter, int address, int kind) |
473 | { | 484 | { |
474 | int i, err; | 485 | int i, err; |
@@ -485,7 +496,8 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind) | |||
485 | 496 | ||
486 | /* Reserve the ISA region */ | 497 | /* Reserve the ISA region */ |
487 | if (is_isa) | 498 | if (is_isa) |
488 | if (!request_region(address, LM78_EXTENT, lm78_driver.name)) { | 499 | if (!request_region(address, LM78_EXTENT, |
500 | lm78_isa_driver.name)) { | ||
489 | err = -EBUSY; | 501 | err = -EBUSY; |
490 | goto ERROR0; | 502 | goto ERROR0; |
491 | } | 503 | } |
@@ -540,7 +552,7 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind) | |||
540 | i2c_set_clientdata(new_client, data); | 552 | i2c_set_clientdata(new_client, data); |
541 | new_client->addr = address; | 553 | new_client->addr = address; |
542 | new_client->adapter = adapter; | 554 | new_client->adapter = adapter; |
543 | new_client->driver = &lm78_driver; | 555 | new_client->driver = is_isa ? &lm78_isa_driver : &lm78_driver; |
544 | new_client->flags = 0; | 556 | new_client->flags = 0; |
545 | 557 | ||
546 | /* Now, we do the remaining detection. */ | 558 | /* Now, we do the remaining detection. */ |
@@ -559,10 +571,9 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind) | |||
559 | /* Determine the chip type. */ | 571 | /* Determine the chip type. */ |
560 | if (kind <= 0) { | 572 | if (kind <= 0) { |
561 | i = lm78_read_value(new_client, LM78_REG_CHIPID); | 573 | i = lm78_read_value(new_client, LM78_REG_CHIPID); |
562 | if (i == 0x00 || i == 0x20) | 574 | if (i == 0x00 || i == 0x20 /* LM78 */ |
575 | || i == 0x40) /* LM78-J */ | ||
563 | kind = lm78; | 576 | kind = lm78; |
564 | else if (i == 0x40) | ||
565 | kind = lm78j; | ||
566 | else if ((i & 0xfe) == 0xc0) | 577 | else if ((i & 0xfe) == 0xc0) |
567 | kind = lm79; | 578 | kind = lm79; |
568 | else { | 579 | else { |
@@ -578,8 +589,6 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind) | |||
578 | 589 | ||
579 | if (kind == lm78) { | 590 | if (kind == lm78) { |
580 | client_name = "lm78"; | 591 | client_name = "lm78"; |
581 | } else if (kind == lm78j) { | ||
582 | client_name = "lm78-j"; | ||
583 | } else if (kind == lm79) { | 592 | } else if (kind == lm79) { |
584 | client_name = "lm79"; | 593 | client_name = "lm79"; |
585 | } | 594 | } |
@@ -605,6 +614,12 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind) | |||
605 | } | 614 | } |
606 | 615 | ||
607 | /* Register sysfs hooks */ | 616 | /* Register sysfs hooks */ |
617 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
618 | if (IS_ERR(data->class_dev)) { | ||
619 | err = PTR_ERR(data->class_dev); | ||
620 | goto ERROR3; | ||
621 | } | ||
622 | |||
608 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 623 | device_create_file(&new_client->dev, &dev_attr_in0_input); |
609 | device_create_file(&new_client->dev, &dev_attr_in0_min); | 624 | device_create_file(&new_client->dev, &dev_attr_in0_min); |
610 | device_create_file(&new_client->dev, &dev_attr_in0_max); | 625 | device_create_file(&new_client->dev, &dev_attr_in0_max); |
@@ -643,6 +658,8 @@ int lm78_detect(struct i2c_adapter *adapter, int address, int kind) | |||
643 | 658 | ||
644 | return 0; | 659 | return 0; |
645 | 660 | ||
661 | ERROR3: | ||
662 | i2c_detach_client(new_client); | ||
646 | ERROR2: | 663 | ERROR2: |
647 | kfree(data); | 664 | kfree(data); |
648 | ERROR1: | 665 | ERROR1: |
@@ -654,18 +671,18 @@ ERROR0: | |||
654 | 671 | ||
655 | static int lm78_detach_client(struct i2c_client *client) | 672 | static int lm78_detach_client(struct i2c_client *client) |
656 | { | 673 | { |
674 | struct lm78_data *data = i2c_get_clientdata(client); | ||
657 | int err; | 675 | int err; |
658 | 676 | ||
659 | if ((err = i2c_detach_client(client))) { | 677 | hwmon_device_unregister(data->class_dev); |
660 | dev_err(&client->dev, | 678 | |
661 | "Client deregistration failed, client not detached.\n"); | 679 | if ((err = i2c_detach_client(client))) |
662 | return err; | 680 | return err; |
663 | } | ||
664 | 681 | ||
665 | if(i2c_is_isa_client(client)) | 682 | if(i2c_is_isa_client(client)) |
666 | release_region(client->addr, LM78_EXTENT); | 683 | release_region(client->addr, LM78_EXTENT); |
667 | 684 | ||
668 | kfree(i2c_get_clientdata(client)); | 685 | kfree(data); |
669 | 686 | ||
670 | return 0; | 687 | return 0; |
671 | } | 688 | } |
@@ -777,18 +794,31 @@ static struct lm78_data *lm78_update_device(struct device *dev) | |||
777 | 794 | ||
778 | static int __init sm_lm78_init(void) | 795 | static int __init sm_lm78_init(void) |
779 | { | 796 | { |
780 | return i2c_add_driver(&lm78_driver); | 797 | int res; |
798 | |||
799 | res = i2c_add_driver(&lm78_driver); | ||
800 | if (res) | ||
801 | return res; | ||
802 | |||
803 | res = i2c_isa_add_driver(&lm78_isa_driver); | ||
804 | if (res) { | ||
805 | i2c_del_driver(&lm78_driver); | ||
806 | return res; | ||
807 | } | ||
808 | |||
809 | return 0; | ||
781 | } | 810 | } |
782 | 811 | ||
783 | static void __exit sm_lm78_exit(void) | 812 | static void __exit sm_lm78_exit(void) |
784 | { | 813 | { |
814 | i2c_isa_del_driver(&lm78_isa_driver); | ||
785 | i2c_del_driver(&lm78_driver); | 815 | i2c_del_driver(&lm78_driver); |
786 | } | 816 | } |
787 | 817 | ||
788 | 818 | ||
789 | 819 | ||
790 | MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>"); | 820 | MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>"); |
791 | MODULE_DESCRIPTION("LM78, LM78-J and LM79 driver"); | 821 | MODULE_DESCRIPTION("LM78/LM79 driver"); |
792 | MODULE_LICENSE("GPL"); | 822 | MODULE_LICENSE("GPL"); |
793 | 823 | ||
794 | module_init(sm_lm78_init); | 824 | module_init(sm_lm78_init); |
diff --git a/drivers/hwmon/lm80.c b/drivers/hwmon/lm80.c index 8100595feb44..83af8b3a0cac 100644 --- a/drivers/hwmon/lm80.c +++ b/drivers/hwmon/lm80.c | |||
@@ -26,15 +26,15 @@ | |||
26 | #include <linux/slab.h> | 26 | #include <linux/slab.h> |
27 | #include <linux/jiffies.h> | 27 | #include <linux/jiffies.h> |
28 | #include <linux/i2c.h> | 28 | #include <linux/i2c.h> |
29 | #include <linux/i2c-sensor.h> | 29 | #include <linux/hwmon.h> |
30 | #include <linux/err.h> | ||
30 | 31 | ||
31 | /* Addresses to scan */ | 32 | /* Addresses to scan */ |
32 | static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, | 33 | static unsigned short normal_i2c[] = { 0x28, 0x29, 0x2a, 0x2b, 0x2c, |
33 | 0x2d, 0x2e, 0x2f, I2C_CLIENT_END }; | 34 | 0x2d, 0x2e, 0x2f, I2C_CLIENT_END }; |
34 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
35 | 35 | ||
36 | /* Insmod parameters */ | 36 | /* Insmod parameters */ |
37 | SENSORS_INSMOD_1(lm80); | 37 | I2C_CLIENT_INSMOD_1(lm80); |
38 | 38 | ||
39 | /* Many LM80 constants specified below */ | 39 | /* Many LM80 constants specified below */ |
40 | 40 | ||
@@ -107,6 +107,7 @@ static inline long TEMP_FROM_REG(u16 temp) | |||
107 | 107 | ||
108 | struct lm80_data { | 108 | struct lm80_data { |
109 | struct i2c_client client; | 109 | struct i2c_client client; |
110 | struct class_device *class_dev; | ||
110 | struct semaphore update_lock; | 111 | struct semaphore update_lock; |
111 | char valid; /* !=0 if following fields are valid */ | 112 | char valid; /* !=0 if following fields are valid */ |
112 | unsigned long last_updated; /* In jiffies */ | 113 | unsigned long last_updated; /* In jiffies */ |
@@ -389,7 +390,7 @@ static int lm80_attach_adapter(struct i2c_adapter *adapter) | |||
389 | { | 390 | { |
390 | if (!(adapter->class & I2C_CLASS_HWMON)) | 391 | if (!(adapter->class & I2C_CLASS_HWMON)) |
391 | return 0; | 392 | return 0; |
392 | return i2c_detect(adapter, &addr_data, lm80_detect); | 393 | return i2c_probe(adapter, &addr_data, lm80_detect); |
393 | } | 394 | } |
394 | 395 | ||
395 | int lm80_detect(struct i2c_adapter *adapter, int address, int kind) | 396 | int lm80_detect(struct i2c_adapter *adapter, int address, int kind) |
@@ -451,6 +452,12 @@ int lm80_detect(struct i2c_adapter *adapter, int address, int kind) | |||
451 | data->fan_min[1] = lm80_read_value(new_client, LM80_REG_FAN_MIN(2)); | 452 | data->fan_min[1] = lm80_read_value(new_client, LM80_REG_FAN_MIN(2)); |
452 | 453 | ||
453 | /* Register sysfs hooks */ | 454 | /* Register sysfs hooks */ |
455 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
456 | if (IS_ERR(data->class_dev)) { | ||
457 | err = PTR_ERR(data->class_dev); | ||
458 | goto error_detach; | ||
459 | } | ||
460 | |||
454 | device_create_file(&new_client->dev, &dev_attr_in0_min); | 461 | device_create_file(&new_client->dev, &dev_attr_in0_min); |
455 | device_create_file(&new_client->dev, &dev_attr_in1_min); | 462 | device_create_file(&new_client->dev, &dev_attr_in1_min); |
456 | device_create_file(&new_client->dev, &dev_attr_in2_min); | 463 | device_create_file(&new_client->dev, &dev_attr_in2_min); |
@@ -487,6 +494,8 @@ int lm80_detect(struct i2c_adapter *adapter, int address, int kind) | |||
487 | 494 | ||
488 | return 0; | 495 | return 0; |
489 | 496 | ||
497 | error_detach: | ||
498 | i2c_detach_client(new_client); | ||
490 | error_free: | 499 | error_free: |
491 | kfree(data); | 500 | kfree(data); |
492 | exit: | 501 | exit: |
@@ -495,15 +504,15 @@ exit: | |||
495 | 504 | ||
496 | static int lm80_detach_client(struct i2c_client *client) | 505 | static int lm80_detach_client(struct i2c_client *client) |
497 | { | 506 | { |
507 | struct lm80_data *data = i2c_get_clientdata(client); | ||
498 | int err; | 508 | int err; |
499 | 509 | ||
500 | if ((err = i2c_detach_client(client))) { | 510 | hwmon_device_unregister(data->class_dev); |
501 | dev_err(&client->dev, "Client deregistration failed, " | 511 | |
502 | "client not detached.\n"); | 512 | if ((err = i2c_detach_client(client))) |
503 | return err; | 513 | return err; |
504 | } | ||
505 | 514 | ||
506 | kfree(i2c_get_clientdata(client)); | 515 | kfree(data); |
507 | return 0; | 516 | return 0; |
508 | } | 517 | } |
509 | 518 | ||
diff --git a/drivers/hwmon/lm83.c b/drivers/hwmon/lm83.c index a49008b444c8..d74b2c20c719 100644 --- a/drivers/hwmon/lm83.c +++ b/drivers/hwmon/lm83.c | |||
@@ -32,8 +32,9 @@ | |||
32 | #include <linux/slab.h> | 32 | #include <linux/slab.h> |
33 | #include <linux/jiffies.h> | 33 | #include <linux/jiffies.h> |
34 | #include <linux/i2c.h> | 34 | #include <linux/i2c.h> |
35 | #include <linux/i2c-sensor.h> | ||
36 | #include <linux/hwmon-sysfs.h> | 35 | #include <linux/hwmon-sysfs.h> |
36 | #include <linux/hwmon.h> | ||
37 | #include <linux/err.h> | ||
37 | 38 | ||
38 | /* | 39 | /* |
39 | * Addresses to scan | 40 | * Addresses to scan |
@@ -45,13 +46,12 @@ static unsigned short normal_i2c[] = { 0x18, 0x19, 0x1a, | |||
45 | 0x29, 0x2a, 0x2b, | 46 | 0x29, 0x2a, 0x2b, |
46 | 0x4c, 0x4d, 0x4e, | 47 | 0x4c, 0x4d, 0x4e, |
47 | I2C_CLIENT_END }; | 48 | I2C_CLIENT_END }; |
48 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
49 | 49 | ||
50 | /* | 50 | /* |
51 | * Insmod parameters | 51 | * Insmod parameters |
52 | */ | 52 | */ |
53 | 53 | ||
54 | SENSORS_INSMOD_1(lm83); | 54 | I2C_CLIENT_INSMOD_1(lm83); |
55 | 55 | ||
56 | /* | 56 | /* |
57 | * The LM83 registers | 57 | * The LM83 registers |
@@ -138,6 +138,7 @@ static struct i2c_driver lm83_driver = { | |||
138 | 138 | ||
139 | struct lm83_data { | 139 | struct lm83_data { |
140 | struct i2c_client client; | 140 | struct i2c_client client; |
141 | struct class_device *class_dev; | ||
141 | struct semaphore update_lock; | 142 | struct semaphore update_lock; |
142 | char valid; /* zero until following fields are valid */ | 143 | char valid; /* zero until following fields are valid */ |
143 | unsigned long last_updated; /* in jiffies */ | 144 | unsigned long last_updated; /* in jiffies */ |
@@ -212,7 +213,7 @@ static int lm83_attach_adapter(struct i2c_adapter *adapter) | |||
212 | { | 213 | { |
213 | if (!(adapter->class & I2C_CLASS_HWMON)) | 214 | if (!(adapter->class & I2C_CLASS_HWMON)) |
214 | return 0; | 215 | return 0; |
215 | return i2c_detect(adapter, &addr_data, lm83_detect); | 216 | return i2c_probe(adapter, &addr_data, lm83_detect); |
216 | } | 217 | } |
217 | 218 | ||
218 | /* | 219 | /* |
@@ -312,6 +313,12 @@ static int lm83_detect(struct i2c_adapter *adapter, int address, int kind) | |||
312 | */ | 313 | */ |
313 | 314 | ||
314 | /* Register sysfs hooks */ | 315 | /* Register sysfs hooks */ |
316 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
317 | if (IS_ERR(data->class_dev)) { | ||
318 | err = PTR_ERR(data->class_dev); | ||
319 | goto exit_detach; | ||
320 | } | ||
321 | |||
315 | device_create_file(&new_client->dev, | 322 | device_create_file(&new_client->dev, |
316 | &sensor_dev_attr_temp1_input.dev_attr); | 323 | &sensor_dev_attr_temp1_input.dev_attr); |
317 | device_create_file(&new_client->dev, | 324 | device_create_file(&new_client->dev, |
@@ -340,6 +347,8 @@ static int lm83_detect(struct i2c_adapter *adapter, int address, int kind) | |||
340 | 347 | ||
341 | return 0; | 348 | return 0; |
342 | 349 | ||
350 | exit_detach: | ||
351 | i2c_detach_client(new_client); | ||
343 | exit_free: | 352 | exit_free: |
344 | kfree(data); | 353 | kfree(data); |
345 | exit: | 354 | exit: |
@@ -348,15 +357,15 @@ exit: | |||
348 | 357 | ||
349 | static int lm83_detach_client(struct i2c_client *client) | 358 | static int lm83_detach_client(struct i2c_client *client) |
350 | { | 359 | { |
360 | struct lm83_data *data = i2c_get_clientdata(client); | ||
351 | int err; | 361 | int err; |
352 | 362 | ||
353 | if ((err = i2c_detach_client(client))) { | 363 | hwmon_device_unregister(data->class_dev); |
354 | dev_err(&client->dev, | 364 | |
355 | "Client deregistration failed, client not detached.\n"); | 365 | if ((err = i2c_detach_client(client))) |
356 | return err; | 366 | return err; |
357 | } | ||
358 | 367 | ||
359 | kfree(i2c_get_clientdata(client)); | 368 | kfree(data); |
360 | return 0; | 369 | return 0; |
361 | } | 370 | } |
362 | 371 | ||
diff --git a/drivers/hwmon/lm85.c b/drivers/hwmon/lm85.c index b4d7fd418264..ab214df9624b 100644 --- a/drivers/hwmon/lm85.c +++ b/drivers/hwmon/lm85.c | |||
@@ -28,15 +28,15 @@ | |||
28 | #include <linux/slab.h> | 28 | #include <linux/slab.h> |
29 | #include <linux/jiffies.h> | 29 | #include <linux/jiffies.h> |
30 | #include <linux/i2c.h> | 30 | #include <linux/i2c.h> |
31 | #include <linux/i2c-sensor.h> | 31 | #include <linux/hwmon.h> |
32 | #include <linux/i2c-vid.h> | 32 | #include <linux/hwmon-vid.h> |
33 | #include <linux/err.h> | ||
33 | 34 | ||
34 | /* Addresses to scan */ | 35 | /* Addresses to scan */ |
35 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; | 36 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; |
36 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
37 | 37 | ||
38 | /* Insmod parameters */ | 38 | /* Insmod parameters */ |
39 | SENSORS_INSMOD_6(lm85b, lm85c, adm1027, adt7463, emc6d100, emc6d102); | 39 | I2C_CLIENT_INSMOD_6(lm85b, lm85c, adm1027, adt7463, emc6d100, emc6d102); |
40 | 40 | ||
41 | /* The LM85 registers */ | 41 | /* The LM85 registers */ |
42 | 42 | ||
@@ -281,15 +281,6 @@ static int ZONE_TO_REG( int zone ) | |||
281 | #define PPR_TO_REG(val,fan) (SENSORS_LIMIT((val)-1,0,3)<<(fan *2)) | 281 | #define PPR_TO_REG(val,fan) (SENSORS_LIMIT((val)-1,0,3)<<(fan *2)) |
282 | #define PPR_FROM_REG(val,fan) ((((val)>>(fan * 2))&0x03)+1) | 282 | #define PPR_FROM_REG(val,fan) ((((val)>>(fan * 2))&0x03)+1) |
283 | 283 | ||
284 | /* i2c-vid.h defines vid_from_reg() */ | ||
285 | #define VID_FROM_REG(val,vrm) (vid_from_reg((val),(vrm))) | ||
286 | |||
287 | /* Unlike some other drivers we DO NOT set initial limits. Use | ||
288 | * the config file to set limits. Some users have reported | ||
289 | * motherboards shutting down when we set limits in a previous | ||
290 | * version of the driver. | ||
291 | */ | ||
292 | |||
293 | /* Chip sampling rates | 284 | /* Chip sampling rates |
294 | * | 285 | * |
295 | * Some sensors are not updated more frequently than once per second | 286 | * Some sensors are not updated more frequently than once per second |
@@ -339,6 +330,7 @@ struct lm85_autofan { | |||
339 | 330 | ||
340 | struct lm85_data { | 331 | struct lm85_data { |
341 | struct i2c_client client; | 332 | struct i2c_client client; |
333 | struct class_device *class_dev; | ||
342 | struct semaphore lock; | 334 | struct semaphore lock; |
343 | enum chips type; | 335 | enum chips type; |
344 | 336 | ||
@@ -1019,7 +1011,7 @@ int lm85_attach_adapter(struct i2c_adapter *adapter) | |||
1019 | { | 1011 | { |
1020 | if (!(adapter->class & I2C_CLASS_HWMON)) | 1012 | if (!(adapter->class & I2C_CLASS_HWMON)) |
1021 | return 0; | 1013 | return 0; |
1022 | return i2c_detect(adapter, &addr_data, lm85_detect); | 1014 | return i2c_probe(adapter, &addr_data, lm85_detect); |
1023 | } | 1015 | } |
1024 | 1016 | ||
1025 | int lm85_detect(struct i2c_adapter *adapter, int address, | 1017 | int lm85_detect(struct i2c_adapter *adapter, int address, |
@@ -1031,11 +1023,6 @@ int lm85_detect(struct i2c_adapter *adapter, int address, | |||
1031 | int err = 0; | 1023 | int err = 0; |
1032 | const char *type_name = ""; | 1024 | const char *type_name = ""; |
1033 | 1025 | ||
1034 | if (i2c_is_isa_adapter(adapter)) { | ||
1035 | /* This chip has no ISA interface */ | ||
1036 | goto ERROR0 ; | ||
1037 | }; | ||
1038 | |||
1039 | if (!i2c_check_functionality(adapter, | 1026 | if (!i2c_check_functionality(adapter, |
1040 | I2C_FUNC_SMBUS_BYTE_DATA)) { | 1027 | I2C_FUNC_SMBUS_BYTE_DATA)) { |
1041 | /* We need to be able to do byte I/O */ | 1028 | /* We need to be able to do byte I/O */ |
@@ -1160,12 +1147,18 @@ int lm85_detect(struct i2c_adapter *adapter, int address, | |||
1160 | goto ERROR1; | 1147 | goto ERROR1; |
1161 | 1148 | ||
1162 | /* Set the VRM version */ | 1149 | /* Set the VRM version */ |
1163 | data->vrm = i2c_which_vrm(); | 1150 | data->vrm = vid_which_vrm(); |
1164 | 1151 | ||
1165 | /* Initialize the LM85 chip */ | 1152 | /* Initialize the LM85 chip */ |
1166 | lm85_init_client(new_client); | 1153 | lm85_init_client(new_client); |
1167 | 1154 | ||
1168 | /* Register sysfs hooks */ | 1155 | /* Register sysfs hooks */ |
1156 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
1157 | if (IS_ERR(data->class_dev)) { | ||
1158 | err = PTR_ERR(data->class_dev); | ||
1159 | goto ERROR2; | ||
1160 | } | ||
1161 | |||
1169 | device_create_file(&new_client->dev, &dev_attr_fan1_input); | 1162 | device_create_file(&new_client->dev, &dev_attr_fan1_input); |
1170 | device_create_file(&new_client->dev, &dev_attr_fan2_input); | 1163 | device_create_file(&new_client->dev, &dev_attr_fan2_input); |
1171 | device_create_file(&new_client->dev, &dev_attr_fan3_input); | 1164 | device_create_file(&new_client->dev, &dev_attr_fan3_input); |
@@ -1235,6 +1228,8 @@ int lm85_detect(struct i2c_adapter *adapter, int address, | |||
1235 | return 0; | 1228 | return 0; |
1236 | 1229 | ||
1237 | /* Error out and cleanup code */ | 1230 | /* Error out and cleanup code */ |
1231 | ERROR2: | ||
1232 | i2c_detach_client(new_client); | ||
1238 | ERROR1: | 1233 | ERROR1: |
1239 | kfree(data); | 1234 | kfree(data); |
1240 | ERROR0: | 1235 | ERROR0: |
@@ -1243,8 +1238,10 @@ int lm85_detect(struct i2c_adapter *adapter, int address, | |||
1243 | 1238 | ||
1244 | int lm85_detach_client(struct i2c_client *client) | 1239 | int lm85_detach_client(struct i2c_client *client) |
1245 | { | 1240 | { |
1241 | struct lm85_data *data = i2c_get_clientdata(client); | ||
1242 | hwmon_device_unregister(data->class_dev); | ||
1246 | i2c_detach_client(client); | 1243 | i2c_detach_client(client); |
1247 | kfree(i2c_get_clientdata(client)); | 1244 | kfree(data); |
1248 | return 0; | 1245 | return 0; |
1249 | } | 1246 | } |
1250 | 1247 | ||
diff --git a/drivers/hwmon/lm87.c b/drivers/hwmon/lm87.c index 1921ed1af182..dca996de4c33 100644 --- a/drivers/hwmon/lm87.c +++ b/drivers/hwmon/lm87.c | |||
@@ -57,8 +57,9 @@ | |||
57 | #include <linux/slab.h> | 57 | #include <linux/slab.h> |
58 | #include <linux/jiffies.h> | 58 | #include <linux/jiffies.h> |
59 | #include <linux/i2c.h> | 59 | #include <linux/i2c.h> |
60 | #include <linux/i2c-sensor.h> | 60 | #include <linux/hwmon.h> |
61 | #include <linux/i2c-vid.h> | 61 | #include <linux/hwmon-vid.h> |
62 | #include <linux/err.h> | ||
62 | 63 | ||
63 | /* | 64 | /* |
64 | * Addresses to scan | 65 | * Addresses to scan |
@@ -66,13 +67,12 @@ | |||
66 | */ | 67 | */ |
67 | 68 | ||
68 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; | 69 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, I2C_CLIENT_END }; |
69 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
70 | 70 | ||
71 | /* | 71 | /* |
72 | * Insmod parameters | 72 | * Insmod parameters |
73 | */ | 73 | */ |
74 | 74 | ||
75 | SENSORS_INSMOD_1(lm87); | 75 | I2C_CLIENT_INSMOD_1(lm87); |
76 | 76 | ||
77 | /* | 77 | /* |
78 | * The LM87 registers | 78 | * The LM87 registers |
@@ -175,6 +175,7 @@ static struct i2c_driver lm87_driver = { | |||
175 | 175 | ||
176 | struct lm87_data { | 176 | struct lm87_data { |
177 | struct i2c_client client; | 177 | struct i2c_client client; |
178 | struct class_device *class_dev; | ||
178 | struct semaphore update_lock; | 179 | struct semaphore update_lock; |
179 | char valid; /* zero until following fields are valid */ | 180 | char valid; /* zero until following fields are valid */ |
180 | unsigned long last_updated; /* In jiffies */ | 181 | unsigned long last_updated; /* In jiffies */ |
@@ -537,7 +538,7 @@ static int lm87_attach_adapter(struct i2c_adapter *adapter) | |||
537 | { | 538 | { |
538 | if (!(adapter->class & I2C_CLASS_HWMON)) | 539 | if (!(adapter->class & I2C_CLASS_HWMON)) |
539 | return 0; | 540 | return 0; |
540 | return i2c_detect(adapter, &addr_data, lm87_detect); | 541 | return i2c_probe(adapter, &addr_data, lm87_detect); |
541 | } | 542 | } |
542 | 543 | ||
543 | /* | 544 | /* |
@@ -608,6 +609,12 @@ static int lm87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
608 | data->in_scale[7] = 1875; | 609 | data->in_scale[7] = 1875; |
609 | 610 | ||
610 | /* Register sysfs hooks */ | 611 | /* Register sysfs hooks */ |
612 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
613 | if (IS_ERR(data->class_dev)) { | ||
614 | err = PTR_ERR(data->class_dev); | ||
615 | goto exit_detach; | ||
616 | } | ||
617 | |||
611 | device_create_file(&new_client->dev, &dev_attr_in1_input); | 618 | device_create_file(&new_client->dev, &dev_attr_in1_input); |
612 | device_create_file(&new_client->dev, &dev_attr_in1_min); | 619 | device_create_file(&new_client->dev, &dev_attr_in1_min); |
613 | device_create_file(&new_client->dev, &dev_attr_in1_max); | 620 | device_create_file(&new_client->dev, &dev_attr_in1_max); |
@@ -673,6 +680,8 @@ static int lm87_detect(struct i2c_adapter *adapter, int address, int kind) | |||
673 | 680 | ||
674 | return 0; | 681 | return 0; |
675 | 682 | ||
683 | exit_detach: | ||
684 | i2c_detach_client(new_client); | ||
676 | exit_free: | 685 | exit_free: |
677 | kfree(data); | 686 | kfree(data); |
678 | exit: | 687 | exit: |
@@ -685,7 +694,7 @@ static void lm87_init_client(struct i2c_client *client) | |||
685 | u8 config; | 694 | u8 config; |
686 | 695 | ||
687 | data->channel = lm87_read_value(client, LM87_REG_CHANNEL_MODE); | 696 | data->channel = lm87_read_value(client, LM87_REG_CHANNEL_MODE); |
688 | data->vrm = i2c_which_vrm(); | 697 | data->vrm = vid_which_vrm(); |
689 | 698 | ||
690 | config = lm87_read_value(client, LM87_REG_CONFIG); | 699 | config = lm87_read_value(client, LM87_REG_CONFIG); |
691 | if (!(config & 0x01)) { | 700 | if (!(config & 0x01)) { |
@@ -719,15 +728,15 @@ static void lm87_init_client(struct i2c_client *client) | |||
719 | 728 | ||
720 | static int lm87_detach_client(struct i2c_client *client) | 729 | static int lm87_detach_client(struct i2c_client *client) |
721 | { | 730 | { |
731 | struct lm87_data *data = i2c_get_clientdata(client); | ||
722 | int err; | 732 | int err; |
723 | 733 | ||
724 | if ((err = i2c_detach_client(client))) { | 734 | hwmon_device_unregister(data->class_dev); |
725 | dev_err(&client->dev, "Client deregistration failed, " | 735 | |
726 | "client not detached.\n"); | 736 | if ((err = i2c_detach_client(client))) |
727 | return err; | 737 | return err; |
728 | } | ||
729 | 738 | ||
730 | kfree(i2c_get_clientdata(client)); | 739 | kfree(data); |
731 | return 0; | 740 | return 0; |
732 | } | 741 | } |
733 | 742 | ||
diff --git a/drivers/hwmon/lm90.c b/drivers/hwmon/lm90.c index a67dcadf7cb0..14de05fcd431 100644 --- a/drivers/hwmon/lm90.c +++ b/drivers/hwmon/lm90.c | |||
@@ -75,8 +75,9 @@ | |||
75 | #include <linux/slab.h> | 75 | #include <linux/slab.h> |
76 | #include <linux/jiffies.h> | 76 | #include <linux/jiffies.h> |
77 | #include <linux/i2c.h> | 77 | #include <linux/i2c.h> |
78 | #include <linux/i2c-sensor.h> | ||
79 | #include <linux/hwmon-sysfs.h> | 78 | #include <linux/hwmon-sysfs.h> |
79 | #include <linux/hwmon.h> | ||
80 | #include <linux/err.h> | ||
80 | 81 | ||
81 | /* | 82 | /* |
82 | * Addresses to scan | 83 | * Addresses to scan |
@@ -89,13 +90,12 @@ | |||
89 | */ | 90 | */ |
90 | 91 | ||
91 | static unsigned short normal_i2c[] = { 0x4c, 0x4d, I2C_CLIENT_END }; | 92 | static unsigned short normal_i2c[] = { 0x4c, 0x4d, I2C_CLIENT_END }; |
92 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
93 | 93 | ||
94 | /* | 94 | /* |
95 | * Insmod parameters | 95 | * Insmod parameters |
96 | */ | 96 | */ |
97 | 97 | ||
98 | SENSORS_INSMOD_6(lm90, adm1032, lm99, lm86, max6657, adt7461); | 98 | I2C_CLIENT_INSMOD_6(lm90, adm1032, lm99, lm86, max6657, adt7461); |
99 | 99 | ||
100 | /* | 100 | /* |
101 | * The LM90 registers | 101 | * The LM90 registers |
@@ -200,6 +200,7 @@ static struct i2c_driver lm90_driver = { | |||
200 | 200 | ||
201 | struct lm90_data { | 201 | struct lm90_data { |
202 | struct i2c_client client; | 202 | struct i2c_client client; |
203 | struct class_device *class_dev; | ||
203 | struct semaphore update_lock; | 204 | struct semaphore update_lock; |
204 | char valid; /* zero until following fields are valid */ | 205 | char valid; /* zero until following fields are valid */ |
205 | unsigned long last_updated; /* in jiffies */ | 206 | unsigned long last_updated; /* in jiffies */ |
@@ -352,7 +353,7 @@ static int lm90_attach_adapter(struct i2c_adapter *adapter) | |||
352 | { | 353 | { |
353 | if (!(adapter->class & I2C_CLASS_HWMON)) | 354 | if (!(adapter->class & I2C_CLASS_HWMON)) |
354 | return 0; | 355 | return 0; |
355 | return i2c_detect(adapter, &addr_data, lm90_detect); | 356 | return i2c_probe(adapter, &addr_data, lm90_detect); |
356 | } | 357 | } |
357 | 358 | ||
358 | /* | 359 | /* |
@@ -500,6 +501,12 @@ static int lm90_detect(struct i2c_adapter *adapter, int address, int kind) | |||
500 | lm90_init_client(new_client); | 501 | lm90_init_client(new_client); |
501 | 502 | ||
502 | /* Register sysfs hooks */ | 503 | /* Register sysfs hooks */ |
504 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
505 | if (IS_ERR(data->class_dev)) { | ||
506 | err = PTR_ERR(data->class_dev); | ||
507 | goto exit_detach; | ||
508 | } | ||
509 | |||
503 | device_create_file(&new_client->dev, | 510 | device_create_file(&new_client->dev, |
504 | &sensor_dev_attr_temp1_input.dev_attr); | 511 | &sensor_dev_attr_temp1_input.dev_attr); |
505 | device_create_file(&new_client->dev, | 512 | device_create_file(&new_client->dev, |
@@ -524,6 +531,8 @@ static int lm90_detect(struct i2c_adapter *adapter, int address, int kind) | |||
524 | 531 | ||
525 | return 0; | 532 | return 0; |
526 | 533 | ||
534 | exit_detach: | ||
535 | i2c_detach_client(new_client); | ||
527 | exit_free: | 536 | exit_free: |
528 | kfree(data); | 537 | kfree(data); |
529 | exit: | 538 | exit: |
@@ -547,15 +556,15 @@ static void lm90_init_client(struct i2c_client *client) | |||
547 | 556 | ||
548 | static int lm90_detach_client(struct i2c_client *client) | 557 | static int lm90_detach_client(struct i2c_client *client) |
549 | { | 558 | { |
559 | struct lm90_data *data = i2c_get_clientdata(client); | ||
550 | int err; | 560 | int err; |
551 | 561 | ||
552 | if ((err = i2c_detach_client(client))) { | 562 | hwmon_device_unregister(data->class_dev); |
553 | dev_err(&client->dev, "Client deregistration failed, " | 563 | |
554 | "client not detached.\n"); | 564 | if ((err = i2c_detach_client(client))) |
555 | return err; | 565 | return err; |
556 | } | ||
557 | 566 | ||
558 | kfree(i2c_get_clientdata(client)); | 567 | kfree(data); |
559 | return 0; | 568 | return 0; |
560 | } | 569 | } |
561 | 570 | ||
diff --git a/drivers/hwmon/lm92.c b/drivers/hwmon/lm92.c index 215c8e40ffdd..647b7c7cd575 100644 --- a/drivers/hwmon/lm92.c +++ b/drivers/hwmon/lm92.c | |||
@@ -44,17 +44,16 @@ | |||
44 | #include <linux/init.h> | 44 | #include <linux/init.h> |
45 | #include <linux/slab.h> | 45 | #include <linux/slab.h> |
46 | #include <linux/i2c.h> | 46 | #include <linux/i2c.h> |
47 | #include <linux/i2c-sensor.h> | 47 | #include <linux/hwmon.h> |
48 | 48 | #include <linux/err.h> | |
49 | 49 | ||
50 | /* The LM92 and MAX6635 have 2 two-state pins for address selection, | 50 | /* The LM92 and MAX6635 have 2 two-state pins for address selection, |
51 | resulting in 4 possible addresses. */ | 51 | resulting in 4 possible addresses. */ |
52 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, | 52 | static unsigned short normal_i2c[] = { 0x48, 0x49, 0x4a, 0x4b, |
53 | I2C_CLIENT_END }; | 53 | I2C_CLIENT_END }; |
54 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
55 | 54 | ||
56 | /* Insmod parameters */ | 55 | /* Insmod parameters */ |
57 | SENSORS_INSMOD_1(lm92); | 56 | I2C_CLIENT_INSMOD_1(lm92); |
58 | 57 | ||
59 | /* The LM92 registers */ | 58 | /* The LM92 registers */ |
60 | #define LM92_REG_CONFIG 0x01 /* 8-bit, RW */ | 59 | #define LM92_REG_CONFIG 0x01 /* 8-bit, RW */ |
@@ -96,6 +95,7 @@ static struct i2c_driver lm92_driver; | |||
96 | /* Client data (each client gets its own) */ | 95 | /* Client data (each client gets its own) */ |
97 | struct lm92_data { | 96 | struct lm92_data { |
98 | struct i2c_client client; | 97 | struct i2c_client client; |
98 | struct class_device *class_dev; | ||
99 | struct semaphore update_lock; | 99 | struct semaphore update_lock; |
100 | char valid; /* zero until following fields are valid */ | 100 | char valid; /* zero until following fields are valid */ |
101 | unsigned long last_updated; /* in jiffies */ | 101 | unsigned long last_updated; /* in jiffies */ |
@@ -359,6 +359,12 @@ static int lm92_detect(struct i2c_adapter *adapter, int address, int kind) | |||
359 | lm92_init_client(new_client); | 359 | lm92_init_client(new_client); |
360 | 360 | ||
361 | /* Register sysfs hooks */ | 361 | /* Register sysfs hooks */ |
362 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
363 | if (IS_ERR(data->class_dev)) { | ||
364 | err = PTR_ERR(data->class_dev); | ||
365 | goto exit_detach; | ||
366 | } | ||
367 | |||
362 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 368 | device_create_file(&new_client->dev, &dev_attr_temp1_input); |
363 | device_create_file(&new_client->dev, &dev_attr_temp1_crit); | 369 | device_create_file(&new_client->dev, &dev_attr_temp1_crit); |
364 | device_create_file(&new_client->dev, &dev_attr_temp1_crit_hyst); | 370 | device_create_file(&new_client->dev, &dev_attr_temp1_crit_hyst); |
@@ -370,6 +376,8 @@ static int lm92_detect(struct i2c_adapter *adapter, int address, int kind) | |||
370 | 376 | ||
371 | return 0; | 377 | return 0; |
372 | 378 | ||
379 | exit_detach: | ||
380 | i2c_detach_client(new_client); | ||
373 | exit_free: | 381 | exit_free: |
374 | kfree(data); | 382 | kfree(data); |
375 | exit: | 383 | exit: |
@@ -380,20 +388,20 @@ static int lm92_attach_adapter(struct i2c_adapter *adapter) | |||
380 | { | 388 | { |
381 | if (!(adapter->class & I2C_CLASS_HWMON)) | 389 | if (!(adapter->class & I2C_CLASS_HWMON)) |
382 | return 0; | 390 | return 0; |
383 | return i2c_detect(adapter, &addr_data, lm92_detect); | 391 | return i2c_probe(adapter, &addr_data, lm92_detect); |
384 | } | 392 | } |
385 | 393 | ||
386 | static int lm92_detach_client(struct i2c_client *client) | 394 | static int lm92_detach_client(struct i2c_client *client) |
387 | { | 395 | { |
396 | struct lm92_data *data = i2c_get_clientdata(client); | ||
388 | int err; | 397 | int err; |
389 | 398 | ||
390 | if ((err = i2c_detach_client(client))) { | 399 | hwmon_device_unregister(data->class_dev); |
391 | dev_err(&client->dev, "Client deregistration failed, " | 400 | |
392 | "client not detached.\n"); | 401 | if ((err = i2c_detach_client(client))) |
393 | return err; | 402 | return err; |
394 | } | ||
395 | 403 | ||
396 | kfree(i2c_get_clientdata(client)); | 404 | kfree(data); |
397 | return 0; | 405 | return 0; |
398 | } | 406 | } |
399 | 407 | ||
diff --git a/drivers/hwmon/max1619.c b/drivers/hwmon/max1619.c index 3c159f1d49ee..16bf71f3a04d 100644 --- a/drivers/hwmon/max1619.c +++ b/drivers/hwmon/max1619.c | |||
@@ -31,20 +31,19 @@ | |||
31 | #include <linux/slab.h> | 31 | #include <linux/slab.h> |
32 | #include <linux/jiffies.h> | 32 | #include <linux/jiffies.h> |
33 | #include <linux/i2c.h> | 33 | #include <linux/i2c.h> |
34 | #include <linux/i2c-sensor.h> | 34 | #include <linux/hwmon.h> |
35 | 35 | #include <linux/err.h> | |
36 | 36 | ||
37 | static unsigned short normal_i2c[] = { 0x18, 0x19, 0x1a, | 37 | static unsigned short normal_i2c[] = { 0x18, 0x19, 0x1a, |
38 | 0x29, 0x2a, 0x2b, | 38 | 0x29, 0x2a, 0x2b, |
39 | 0x4c, 0x4d, 0x4e, | 39 | 0x4c, 0x4d, 0x4e, |
40 | I2C_CLIENT_END }; | 40 | I2C_CLIENT_END }; |
41 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
42 | 41 | ||
43 | /* | 42 | /* |
44 | * Insmod parameters | 43 | * Insmod parameters |
45 | */ | 44 | */ |
46 | 45 | ||
47 | SENSORS_INSMOD_1(max1619); | 46 | I2C_CLIENT_INSMOD_1(max1619); |
48 | 47 | ||
49 | /* | 48 | /* |
50 | * The MAX1619 registers | 49 | * The MAX1619 registers |
@@ -104,6 +103,7 @@ static struct i2c_driver max1619_driver = { | |||
104 | 103 | ||
105 | struct max1619_data { | 104 | struct max1619_data { |
106 | struct i2c_client client; | 105 | struct i2c_client client; |
106 | struct class_device *class_dev; | ||
107 | struct semaphore update_lock; | 107 | struct semaphore update_lock; |
108 | char valid; /* zero until following fields are valid */ | 108 | char valid; /* zero until following fields are valid */ |
109 | unsigned long last_updated; /* in jiffies */ | 109 | unsigned long last_updated; /* in jiffies */ |
@@ -179,7 +179,7 @@ static int max1619_attach_adapter(struct i2c_adapter *adapter) | |||
179 | { | 179 | { |
180 | if (!(adapter->class & I2C_CLASS_HWMON)) | 180 | if (!(adapter->class & I2C_CLASS_HWMON)) |
181 | return 0; | 181 | return 0; |
182 | return i2c_detect(adapter, &addr_data, max1619_detect); | 182 | return i2c_probe(adapter, &addr_data, max1619_detect); |
183 | } | 183 | } |
184 | 184 | ||
185 | /* | 185 | /* |
@@ -275,6 +275,12 @@ static int max1619_detect(struct i2c_adapter *adapter, int address, int kind) | |||
275 | max1619_init_client(new_client); | 275 | max1619_init_client(new_client); |
276 | 276 | ||
277 | /* Register sysfs hooks */ | 277 | /* Register sysfs hooks */ |
278 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
279 | if (IS_ERR(data->class_dev)) { | ||
280 | err = PTR_ERR(data->class_dev); | ||
281 | goto exit_detach; | ||
282 | } | ||
283 | |||
278 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 284 | device_create_file(&new_client->dev, &dev_attr_temp1_input); |
279 | device_create_file(&new_client->dev, &dev_attr_temp2_input); | 285 | device_create_file(&new_client->dev, &dev_attr_temp2_input); |
280 | device_create_file(&new_client->dev, &dev_attr_temp2_min); | 286 | device_create_file(&new_client->dev, &dev_attr_temp2_min); |
@@ -285,6 +291,8 @@ static int max1619_detect(struct i2c_adapter *adapter, int address, int kind) | |||
285 | 291 | ||
286 | return 0; | 292 | return 0; |
287 | 293 | ||
294 | exit_detach: | ||
295 | i2c_detach_client(new_client); | ||
288 | exit_free: | 296 | exit_free: |
289 | kfree(data); | 297 | kfree(data); |
290 | exit: | 298 | exit: |
@@ -308,15 +316,15 @@ static void max1619_init_client(struct i2c_client *client) | |||
308 | 316 | ||
309 | static int max1619_detach_client(struct i2c_client *client) | 317 | static int max1619_detach_client(struct i2c_client *client) |
310 | { | 318 | { |
319 | struct max1619_data *data = i2c_get_clientdata(client); | ||
311 | int err; | 320 | int err; |
312 | 321 | ||
313 | if ((err = i2c_detach_client(client))) { | 322 | hwmon_device_unregister(data->class_dev); |
314 | dev_err(&client->dev, "Client deregistration failed, " | 323 | |
315 | "client not detached.\n"); | 324 | if ((err = i2c_detach_client(client))) |
316 | return err; | 325 | return err; |
317 | } | ||
318 | 326 | ||
319 | kfree(i2c_get_clientdata(client)); | 327 | kfree(data); |
320 | return 0; | 328 | return 0; |
321 | } | 329 | } |
322 | 330 | ||
diff --git a/drivers/hwmon/pc87360.c b/drivers/hwmon/pc87360.c index fa4032d53b79..cf2a35799c7c 100644 --- a/drivers/hwmon/pc87360.c +++ b/drivers/hwmon/pc87360.c | |||
@@ -38,23 +38,19 @@ | |||
38 | #include <linux/slab.h> | 38 | #include <linux/slab.h> |
39 | #include <linux/jiffies.h> | 39 | #include <linux/jiffies.h> |
40 | #include <linux/i2c.h> | 40 | #include <linux/i2c.h> |
41 | #include <linux/i2c-sensor.h> | 41 | #include <linux/i2c-isa.h> |
42 | #include <linux/i2c-vid.h> | 42 | #include <linux/hwmon.h> |
43 | #include <linux/hwmon-sysfs.h> | ||
44 | #include <linux/hwmon-vid.h> | ||
45 | #include <linux/err.h> | ||
43 | #include <asm/io.h> | 46 | #include <asm/io.h> |
44 | 47 | ||
45 | static unsigned short normal_i2c[] = { I2C_CLIENT_END }; | ||
46 | static unsigned int normal_isa[] = { 0, I2C_CLIENT_ISA_END }; | ||
47 | static struct i2c_force_data forces[] = {{ NULL }}; | ||
48 | static u8 devid; | 48 | static u8 devid; |
49 | static unsigned int extra_isa[3]; | 49 | static unsigned short address; |
50 | static unsigned short extra_isa[3]; | ||
50 | static u8 confreg[4]; | 51 | static u8 confreg[4]; |
51 | 52 | ||
52 | enum chips { any_chip, pc87360, pc87363, pc87364, pc87365, pc87366 }; | 53 | enum chips { any_chip, pc87360, pc87363, pc87364, pc87365, pc87366 }; |
53 | static struct i2c_address_data addr_data = { | ||
54 | .normal_i2c = normal_i2c, | ||
55 | .normal_isa = normal_isa, | ||
56 | .forces = forces, | ||
57 | }; | ||
58 | 54 | ||
59 | static int init = 1; | 55 | static int init = 1; |
60 | module_param(init, int, 0); | 56 | module_param(init, int, 0); |
@@ -186,6 +182,7 @@ static inline u8 PWM_TO_REG(int val, int inv) | |||
186 | 182 | ||
187 | struct pc87360_data { | 183 | struct pc87360_data { |
188 | struct i2c_client client; | 184 | struct i2c_client client; |
185 | struct class_device *class_dev; | ||
189 | struct semaphore lock; | 186 | struct semaphore lock; |
190 | struct semaphore update_lock; | 187 | struct semaphore update_lock; |
191 | char valid; /* !=0 if following fields are valid */ | 188 | char valid; /* !=0 if following fields are valid */ |
@@ -224,8 +221,7 @@ struct pc87360_data { | |||
224 | * Functions declaration | 221 | * Functions declaration |
225 | */ | 222 | */ |
226 | 223 | ||
227 | static int pc87360_attach_adapter(struct i2c_adapter *adapter); | 224 | static int pc87360_detect(struct i2c_adapter *adapter); |
228 | static int pc87360_detect(struct i2c_adapter *adapter, int address, int kind); | ||
229 | static int pc87360_detach_client(struct i2c_client *client); | 225 | static int pc87360_detach_client(struct i2c_client *client); |
230 | 226 | ||
231 | static int pc87360_read_value(struct pc87360_data *data, u8 ldi, u8 bank, | 227 | static int pc87360_read_value(struct pc87360_data *data, u8 ldi, u8 bank, |
@@ -242,8 +238,7 @@ static struct pc87360_data *pc87360_update_device(struct device *dev); | |||
242 | static struct i2c_driver pc87360_driver = { | 238 | static struct i2c_driver pc87360_driver = { |
243 | .owner = THIS_MODULE, | 239 | .owner = THIS_MODULE, |
244 | .name = "pc87360", | 240 | .name = "pc87360", |
245 | .flags = I2C_DF_NOTIFY, | 241 | .attach_adapter = pc87360_detect, |
246 | .attach_adapter = pc87360_attach_adapter, | ||
247 | .detach_client = pc87360_detach_client, | 242 | .detach_client = pc87360_detach_client, |
248 | }; | 243 | }; |
249 | 244 | ||
@@ -251,168 +246,178 @@ static struct i2c_driver pc87360_driver = { | |||
251 | * Sysfs stuff | 246 | * Sysfs stuff |
252 | */ | 247 | */ |
253 | 248 | ||
254 | static ssize_t set_fan_min(struct device *dev, const char *buf, | 249 | static ssize_t show_fan_input(struct device *dev, struct device_attribute *devattr, char *buf) |
255 | size_t count, int nr) | 250 | { |
251 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
252 | struct pc87360_data *data = pc87360_update_device(dev); | ||
253 | return sprintf(buf, "%u\n", FAN_FROM_REG(data->fan[attr->index], | ||
254 | FAN_DIV_FROM_REG(data->fan_status[attr->index]))); | ||
255 | } | ||
256 | static ssize_t show_fan_min(struct device *dev, struct device_attribute *devattr, char *buf) | ||
257 | { | ||
258 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
259 | struct pc87360_data *data = pc87360_update_device(dev); | ||
260 | return sprintf(buf, "%u\n", FAN_FROM_REG(data->fan_min[attr->index], | ||
261 | FAN_DIV_FROM_REG(data->fan_status[attr->index]))); | ||
262 | } | ||
263 | static ssize_t show_fan_div(struct device *dev, struct device_attribute *devattr, char *buf) | ||
264 | { | ||
265 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
266 | struct pc87360_data *data = pc87360_update_device(dev); | ||
267 | return sprintf(buf, "%u\n", | ||
268 | FAN_DIV_FROM_REG(data->fan_status[attr->index])); | ||
269 | } | ||
270 | static ssize_t show_fan_status(struct device *dev, struct device_attribute *devattr, char *buf) | ||
256 | { | 271 | { |
272 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
273 | struct pc87360_data *data = pc87360_update_device(dev); | ||
274 | return sprintf(buf, "%u\n", | ||
275 | FAN_STATUS_FROM_REG(data->fan_status[attr->index])); | ||
276 | } | ||
277 | static ssize_t set_fan_min(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
278 | size_t count) | ||
279 | { | ||
280 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
257 | struct i2c_client *client = to_i2c_client(dev); | 281 | struct i2c_client *client = to_i2c_client(dev); |
258 | struct pc87360_data *data = i2c_get_clientdata(client); | 282 | struct pc87360_data *data = i2c_get_clientdata(client); |
259 | long fan_min = simple_strtol(buf, NULL, 10); | 283 | long fan_min = simple_strtol(buf, NULL, 10); |
260 | 284 | ||
261 | down(&data->update_lock); | 285 | down(&data->update_lock); |
262 | fan_min = FAN_TO_REG(fan_min, FAN_DIV_FROM_REG(data->fan_status[nr])); | 286 | fan_min = FAN_TO_REG(fan_min, FAN_DIV_FROM_REG(data->fan_status[attr->index])); |
263 | 287 | ||
264 | /* If it wouldn't fit, change clock divisor */ | 288 | /* If it wouldn't fit, change clock divisor */ |
265 | while (fan_min > 255 | 289 | while (fan_min > 255 |
266 | && (data->fan_status[nr] & 0x60) != 0x60) { | 290 | && (data->fan_status[attr->index] & 0x60) != 0x60) { |
267 | fan_min >>= 1; | 291 | fan_min >>= 1; |
268 | data->fan[nr] >>= 1; | 292 | data->fan[attr->index] >>= 1; |
269 | data->fan_status[nr] += 0x20; | 293 | data->fan_status[attr->index] += 0x20; |
270 | } | 294 | } |
271 | data->fan_min[nr] = fan_min > 255 ? 255 : fan_min; | 295 | data->fan_min[attr->index] = fan_min > 255 ? 255 : fan_min; |
272 | pc87360_write_value(data, LD_FAN, NO_BANK, PC87360_REG_FAN_MIN(nr), | 296 | pc87360_write_value(data, LD_FAN, NO_BANK, PC87360_REG_FAN_MIN(attr->index), |
273 | data->fan_min[nr]); | 297 | data->fan_min[attr->index]); |
274 | 298 | ||
275 | /* Write new divider, preserve alarm bits */ | 299 | /* Write new divider, preserve alarm bits */ |
276 | pc87360_write_value(data, LD_FAN, NO_BANK, PC87360_REG_FAN_STATUS(nr), | 300 | pc87360_write_value(data, LD_FAN, NO_BANK, PC87360_REG_FAN_STATUS(attr->index), |
277 | data->fan_status[nr] & 0xF9); | 301 | data->fan_status[attr->index] & 0xF9); |
278 | up(&data->update_lock); | 302 | up(&data->update_lock); |
279 | 303 | ||
280 | return count; | 304 | return count; |
281 | } | 305 | } |
282 | 306 | ||
283 | #define show_and_set_fan(offset) \ | 307 | #define show_and_set_fan(offset) \ |
284 | static ssize_t show_fan##offset##_input(struct device *dev, struct device_attribute *attr, char *buf) \ | 308 | static SENSOR_DEVICE_ATTR(fan##offset##_input, S_IRUGO, \ |
285 | { \ | 309 | show_fan_input, NULL, offset-1); \ |
286 | struct pc87360_data *data = pc87360_update_device(dev); \ | 310 | static SENSOR_DEVICE_ATTR(fan##offset##_min, S_IWUSR | S_IRUGO, \ |
287 | return sprintf(buf, "%u\n", FAN_FROM_REG(data->fan[offset-1], \ | 311 | show_fan_min, set_fan_min, offset-1); \ |
288 | FAN_DIV_FROM_REG(data->fan_status[offset-1]))); \ | 312 | static SENSOR_DEVICE_ATTR(fan##offset##_div, S_IRUGO, \ |
289 | } \ | 313 | show_fan_div, NULL, offset-1); \ |
290 | static ssize_t show_fan##offset##_min(struct device *dev, struct device_attribute *attr, char *buf) \ | 314 | static SENSOR_DEVICE_ATTR(fan##offset##_status, S_IRUGO, \ |
291 | { \ | 315 | show_fan_status, NULL, offset-1); |
292 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
293 | return sprintf(buf, "%u\n", FAN_FROM_REG(data->fan_min[offset-1], \ | ||
294 | FAN_DIV_FROM_REG(data->fan_status[offset-1]))); \ | ||
295 | } \ | ||
296 | static ssize_t show_fan##offset##_div(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
297 | { \ | ||
298 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
299 | return sprintf(buf, "%u\n", \ | ||
300 | FAN_DIV_FROM_REG(data->fan_status[offset-1])); \ | ||
301 | } \ | ||
302 | static ssize_t show_fan##offset##_status(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
303 | { \ | ||
304 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
305 | return sprintf(buf, "%u\n", \ | ||
306 | FAN_STATUS_FROM_REG(data->fan_status[offset-1])); \ | ||
307 | } \ | ||
308 | static ssize_t set_fan##offset##_min(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
309 | size_t count) \ | ||
310 | { \ | ||
311 | return set_fan_min(dev, buf, count, offset-1); \ | ||
312 | } \ | ||
313 | static DEVICE_ATTR(fan##offset##_input, S_IRUGO, \ | ||
314 | show_fan##offset##_input, NULL); \ | ||
315 | static DEVICE_ATTR(fan##offset##_min, S_IWUSR | S_IRUGO, \ | ||
316 | show_fan##offset##_min, set_fan##offset##_min); \ | ||
317 | static DEVICE_ATTR(fan##offset##_div, S_IRUGO, \ | ||
318 | show_fan##offset##_div, NULL); \ | ||
319 | static DEVICE_ATTR(fan##offset##_status, S_IRUGO, \ | ||
320 | show_fan##offset##_status, NULL); | ||
321 | show_and_set_fan(1) | 316 | show_and_set_fan(1) |
322 | show_and_set_fan(2) | 317 | show_and_set_fan(2) |
323 | show_and_set_fan(3) | 318 | show_and_set_fan(3) |
324 | 319 | ||
320 | static ssize_t show_pwm(struct device *dev, struct device_attribute *devattr, char *buf) | ||
321 | { | ||
322 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
323 | struct pc87360_data *data = pc87360_update_device(dev); | ||
324 | return sprintf(buf, "%u\n", | ||
325 | PWM_FROM_REG(data->pwm[attr->index], | ||
326 | FAN_CONFIG_INVERT(data->fan_conf, | ||
327 | attr->index))); | ||
328 | } | ||
329 | static ssize_t set_pwm(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
330 | size_t count) | ||
331 | { | ||
332 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
333 | struct i2c_client *client = to_i2c_client(dev); | ||
334 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
335 | long val = simple_strtol(buf, NULL, 10); | ||
336 | |||
337 | down(&data->update_lock); | ||
338 | data->pwm[attr->index] = PWM_TO_REG(val, | ||
339 | FAN_CONFIG_INVERT(data->fan_conf, attr->index)); | ||
340 | pc87360_write_value(data, LD_FAN, NO_BANK, PC87360_REG_PWM(attr->index), | ||
341 | data->pwm[attr->index]); | ||
342 | up(&data->update_lock); | ||
343 | return count; | ||
344 | } | ||
345 | |||
325 | #define show_and_set_pwm(offset) \ | 346 | #define show_and_set_pwm(offset) \ |
326 | static ssize_t show_pwm##offset(struct device *dev, struct device_attribute *attr, char *buf) \ | 347 | static SENSOR_DEVICE_ATTR(pwm##offset, S_IWUSR | S_IRUGO, \ |
327 | { \ | 348 | show_pwm, set_pwm, offset-1); |
328 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
329 | return sprintf(buf, "%u\n", \ | ||
330 | PWM_FROM_REG(data->pwm[offset-1], \ | ||
331 | FAN_CONFIG_INVERT(data->fan_conf, \ | ||
332 | offset-1))); \ | ||
333 | } \ | ||
334 | static ssize_t set_pwm##offset(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
335 | size_t count) \ | ||
336 | { \ | ||
337 | struct i2c_client *client = to_i2c_client(dev); \ | ||
338 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
339 | long val = simple_strtol(buf, NULL, 10); \ | ||
340 | \ | ||
341 | down(&data->update_lock); \ | ||
342 | data->pwm[offset-1] = PWM_TO_REG(val, \ | ||
343 | FAN_CONFIG_INVERT(data->fan_conf, offset-1)); \ | ||
344 | pc87360_write_value(data, LD_FAN, NO_BANK, PC87360_REG_PWM(offset-1), \ | ||
345 | data->pwm[offset-1]); \ | ||
346 | up(&data->update_lock); \ | ||
347 | return count; \ | ||
348 | } \ | ||
349 | static DEVICE_ATTR(pwm##offset, S_IWUSR | S_IRUGO, \ | ||
350 | show_pwm##offset, set_pwm##offset); | ||
351 | show_and_set_pwm(1) | 349 | show_and_set_pwm(1) |
352 | show_and_set_pwm(2) | 350 | show_and_set_pwm(2) |
353 | show_and_set_pwm(3) | 351 | show_and_set_pwm(3) |
354 | 352 | ||
353 | static ssize_t show_in_input(struct device *dev, struct device_attribute *devattr, char *buf) | ||
354 | { | ||
355 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
356 | struct pc87360_data *data = pc87360_update_device(dev); | ||
357 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in[attr->index], | ||
358 | data->in_vref)); | ||
359 | } | ||
360 | static ssize_t show_in_min(struct device *dev, struct device_attribute *devattr, char *buf) | ||
361 | { | ||
362 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
363 | struct pc87360_data *data = pc87360_update_device(dev); | ||
364 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_min[attr->index], | ||
365 | data->in_vref)); | ||
366 | } | ||
367 | static ssize_t show_in_max(struct device *dev, struct device_attribute *devattr, char *buf) | ||
368 | { | ||
369 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
370 | struct pc87360_data *data = pc87360_update_device(dev); | ||
371 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_max[attr->index], | ||
372 | data->in_vref)); | ||
373 | } | ||
374 | static ssize_t show_in_status(struct device *dev, struct device_attribute *devattr, char *buf) | ||
375 | { | ||
376 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
377 | struct pc87360_data *data = pc87360_update_device(dev); | ||
378 | return sprintf(buf, "%u\n", data->in_status[attr->index]); | ||
379 | } | ||
380 | static ssize_t set_in_min(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
381 | size_t count) | ||
382 | { | ||
383 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
384 | struct i2c_client *client = to_i2c_client(dev); | ||
385 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
386 | long val = simple_strtol(buf, NULL, 10); | ||
387 | |||
388 | down(&data->update_lock); | ||
389 | data->in_min[attr->index] = IN_TO_REG(val, data->in_vref); | ||
390 | pc87360_write_value(data, LD_IN, attr->index, PC87365_REG_IN_MIN, | ||
391 | data->in_min[attr->index]); | ||
392 | up(&data->update_lock); | ||
393 | return count; | ||
394 | } | ||
395 | static ssize_t set_in_max(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
396 | size_t count) | ||
397 | { | ||
398 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
399 | struct i2c_client *client = to_i2c_client(dev); | ||
400 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
401 | long val = simple_strtol(buf, NULL, 10); | ||
402 | |||
403 | down(&data->update_lock); | ||
404 | data->in_max[attr->index] = IN_TO_REG(val, | ||
405 | data->in_vref); | ||
406 | pc87360_write_value(data, LD_IN, attr->index, PC87365_REG_IN_MAX, | ||
407 | data->in_max[attr->index]); | ||
408 | up(&data->update_lock); | ||
409 | return count; | ||
410 | } | ||
411 | |||
355 | #define show_and_set_in(offset) \ | 412 | #define show_and_set_in(offset) \ |
356 | static ssize_t show_in##offset##_input(struct device *dev, struct device_attribute *attr, char *buf) \ | 413 | static SENSOR_DEVICE_ATTR(in##offset##_input, S_IRUGO, \ |
357 | { \ | 414 | show_in_input, NULL, offset); \ |
358 | struct pc87360_data *data = pc87360_update_device(dev); \ | 415 | static SENSOR_DEVICE_ATTR(in##offset##_min, S_IWUSR | S_IRUGO, \ |
359 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in[offset], \ | 416 | show_in_min, set_in_min, offset); \ |
360 | data->in_vref)); \ | 417 | static SENSOR_DEVICE_ATTR(in##offset##_max, S_IWUSR | S_IRUGO, \ |
361 | } \ | 418 | show_in_max, set_in_max, offset); \ |
362 | static ssize_t show_in##offset##_min(struct device *dev, struct device_attribute *attr, char *buf) \ | 419 | static SENSOR_DEVICE_ATTR(in##offset##_status, S_IRUGO, \ |
363 | { \ | 420 | show_in_status, NULL, offset); |
364 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
365 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_min[offset], \ | ||
366 | data->in_vref)); \ | ||
367 | } \ | ||
368 | static ssize_t show_in##offset##_max(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
369 | { \ | ||
370 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
371 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_max[offset], \ | ||
372 | data->in_vref)); \ | ||
373 | } \ | ||
374 | static ssize_t show_in##offset##_status(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
375 | { \ | ||
376 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
377 | return sprintf(buf, "%u\n", data->in_status[offset]); \ | ||
378 | } \ | ||
379 | static ssize_t set_in##offset##_min(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
380 | size_t count) \ | ||
381 | { \ | ||
382 | struct i2c_client *client = to_i2c_client(dev); \ | ||
383 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
384 | long val = simple_strtol(buf, NULL, 10); \ | ||
385 | \ | ||
386 | down(&data->update_lock); \ | ||
387 | data->in_min[offset] = IN_TO_REG(val, data->in_vref); \ | ||
388 | pc87360_write_value(data, LD_IN, offset, PC87365_REG_IN_MIN, \ | ||
389 | data->in_min[offset]); \ | ||
390 | up(&data->update_lock); \ | ||
391 | return count; \ | ||
392 | } \ | ||
393 | static ssize_t set_in##offset##_max(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
394 | size_t count) \ | ||
395 | { \ | ||
396 | struct i2c_client *client = to_i2c_client(dev); \ | ||
397 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
398 | long val = simple_strtol(buf, NULL, 10); \ | ||
399 | \ | ||
400 | down(&data->update_lock); \ | ||
401 | data->in_max[offset] = IN_TO_REG(val, \ | ||
402 | data->in_vref); \ | ||
403 | pc87360_write_value(data, LD_IN, offset, PC87365_REG_IN_MAX, \ | ||
404 | data->in_max[offset]); \ | ||
405 | up(&data->update_lock); \ | ||
406 | return count; \ | ||
407 | } \ | ||
408 | static DEVICE_ATTR(in##offset##_input, S_IRUGO, \ | ||
409 | show_in##offset##_input, NULL); \ | ||
410 | static DEVICE_ATTR(in##offset##_min, S_IWUSR | S_IRUGO, \ | ||
411 | show_in##offset##_min, set_in##offset##_min); \ | ||
412 | static DEVICE_ATTR(in##offset##_max, S_IWUSR | S_IRUGO, \ | ||
413 | show_in##offset##_max, set_in##offset##_max); \ | ||
414 | static DEVICE_ATTR(in##offset##_status, S_IRUGO, \ | ||
415 | show_in##offset##_status, NULL); | ||
416 | show_and_set_in(0) | 421 | show_and_set_in(0) |
417 | show_and_set_in(1) | 422 | show_and_set_in(1) |
418 | show_and_set_in(2) | 423 | show_and_set_in(2) |
@@ -425,88 +430,97 @@ show_and_set_in(8) | |||
425 | show_and_set_in(9) | 430 | show_and_set_in(9) |
426 | show_and_set_in(10) | 431 | show_and_set_in(10) |
427 | 432 | ||
433 | static ssize_t show_therm_input(struct device *dev, struct device_attribute *devattr, char *buf) | ||
434 | { | ||
435 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
436 | struct pc87360_data *data = pc87360_update_device(dev); | ||
437 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in[attr->index], | ||
438 | data->in_vref)); | ||
439 | } | ||
440 | static ssize_t show_therm_min(struct device *dev, struct device_attribute *devattr, char *buf) | ||
441 | { | ||
442 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
443 | struct pc87360_data *data = pc87360_update_device(dev); | ||
444 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_min[attr->index], | ||
445 | data->in_vref)); | ||
446 | } | ||
447 | static ssize_t show_therm_max(struct device *dev, struct device_attribute *devattr, char *buf) | ||
448 | { | ||
449 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
450 | struct pc87360_data *data = pc87360_update_device(dev); | ||
451 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_max[attr->index], | ||
452 | data->in_vref)); | ||
453 | } | ||
454 | static ssize_t show_therm_crit(struct device *dev, struct device_attribute *devattr, char *buf) | ||
455 | { | ||
456 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
457 | struct pc87360_data *data = pc87360_update_device(dev); | ||
458 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_crit[attr->index-11], | ||
459 | data->in_vref)); | ||
460 | } | ||
461 | static ssize_t show_therm_status(struct device *dev, struct device_attribute *devattr, char *buf) | ||
462 | { | ||
463 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
464 | struct pc87360_data *data = pc87360_update_device(dev); | ||
465 | return sprintf(buf, "%u\n", data->in_status[attr->index]); | ||
466 | } | ||
467 | static ssize_t set_therm_min(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
468 | size_t count) | ||
469 | { | ||
470 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
471 | struct i2c_client *client = to_i2c_client(dev); | ||
472 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
473 | long val = simple_strtol(buf, NULL, 10); | ||
474 | |||
475 | down(&data->update_lock); | ||
476 | data->in_min[attr->index] = IN_TO_REG(val, data->in_vref); | ||
477 | pc87360_write_value(data, LD_IN, attr->index, PC87365_REG_TEMP_MIN, | ||
478 | data->in_min[attr->index]); | ||
479 | up(&data->update_lock); | ||
480 | return count; | ||
481 | } | ||
482 | static ssize_t set_therm_max(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
483 | size_t count) | ||
484 | { | ||
485 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
486 | struct i2c_client *client = to_i2c_client(dev); | ||
487 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
488 | long val = simple_strtol(buf, NULL, 10); | ||
489 | |||
490 | down(&data->update_lock); | ||
491 | data->in_max[attr->index] = IN_TO_REG(val, data->in_vref); | ||
492 | pc87360_write_value(data, LD_IN, attr->index, PC87365_REG_TEMP_MAX, | ||
493 | data->in_max[attr->index]); | ||
494 | up(&data->update_lock); | ||
495 | return count; | ||
496 | } | ||
497 | static ssize_t set_therm_crit(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
498 | size_t count) | ||
499 | { | ||
500 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
501 | struct i2c_client *client = to_i2c_client(dev); | ||
502 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
503 | long val = simple_strtol(buf, NULL, 10); | ||
504 | |||
505 | down(&data->update_lock); | ||
506 | data->in_crit[attr->index-11] = IN_TO_REG(val, data->in_vref); | ||
507 | pc87360_write_value(data, LD_IN, attr->index, PC87365_REG_TEMP_CRIT, | ||
508 | data->in_crit[attr->index-11]); | ||
509 | up(&data->update_lock); | ||
510 | return count; | ||
511 | } | ||
512 | |||
428 | #define show_and_set_therm(offset) \ | 513 | #define show_and_set_therm(offset) \ |
429 | static ssize_t show_temp##offset##_input(struct device *dev, struct device_attribute *attr, char *buf) \ | 514 | static SENSOR_DEVICE_ATTR(temp##offset##_input, S_IRUGO, \ |
430 | { \ | 515 | show_therm_input, NULL, 11+offset-4); \ |
431 | struct pc87360_data *data = pc87360_update_device(dev); \ | 516 | static SENSOR_DEVICE_ATTR(temp##offset##_min, S_IWUSR | S_IRUGO, \ |
432 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in[offset+7], \ | 517 | show_therm_min, set_therm_min, 11+offset-4); \ |
433 | data->in_vref)); \ | 518 | static SENSOR_DEVICE_ATTR(temp##offset##_max, S_IWUSR | S_IRUGO, \ |
434 | } \ | 519 | show_therm_max, set_therm_max, 11+offset-4); \ |
435 | static ssize_t show_temp##offset##_min(struct device *dev, struct device_attribute *attr, char *buf) \ | 520 | static SENSOR_DEVICE_ATTR(temp##offset##_crit, S_IWUSR | S_IRUGO, \ |
436 | { \ | 521 | show_therm_crit, set_therm_crit, 11+offset-4); \ |
437 | struct pc87360_data *data = pc87360_update_device(dev); \ | 522 | static SENSOR_DEVICE_ATTR(temp##offset##_status, S_IRUGO, \ |
438 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_min[offset+7], \ | 523 | show_therm_status, NULL, 11+offset-4); |
439 | data->in_vref)); \ | ||
440 | } \ | ||
441 | static ssize_t show_temp##offset##_max(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
442 | { \ | ||
443 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
444 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_max[offset+7], \ | ||
445 | data->in_vref)); \ | ||
446 | } \ | ||
447 | static ssize_t show_temp##offset##_crit(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
448 | { \ | ||
449 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
450 | return sprintf(buf, "%u\n", IN_FROM_REG(data->in_crit[offset-4], \ | ||
451 | data->in_vref)); \ | ||
452 | } \ | ||
453 | static ssize_t show_temp##offset##_status(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
454 | { \ | ||
455 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
456 | return sprintf(buf, "%u\n", data->in_status[offset+7]); \ | ||
457 | } \ | ||
458 | static ssize_t set_temp##offset##_min(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
459 | size_t count) \ | ||
460 | { \ | ||
461 | struct i2c_client *client = to_i2c_client(dev); \ | ||
462 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
463 | long val = simple_strtol(buf, NULL, 10); \ | ||
464 | \ | ||
465 | down(&data->update_lock); \ | ||
466 | data->in_min[offset+7] = IN_TO_REG(val, data->in_vref); \ | ||
467 | pc87360_write_value(data, LD_IN, offset+7, PC87365_REG_TEMP_MIN, \ | ||
468 | data->in_min[offset+7]); \ | ||
469 | up(&data->update_lock); \ | ||
470 | return count; \ | ||
471 | } \ | ||
472 | static ssize_t set_temp##offset##_max(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
473 | size_t count) \ | ||
474 | { \ | ||
475 | struct i2c_client *client = to_i2c_client(dev); \ | ||
476 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
477 | long val = simple_strtol(buf, NULL, 10); \ | ||
478 | \ | ||
479 | down(&data->update_lock); \ | ||
480 | data->in_max[offset+7] = IN_TO_REG(val, data->in_vref); \ | ||
481 | pc87360_write_value(data, LD_IN, offset+7, PC87365_REG_TEMP_MAX, \ | ||
482 | data->in_max[offset+7]); \ | ||
483 | up(&data->update_lock); \ | ||
484 | return count; \ | ||
485 | } \ | ||
486 | static ssize_t set_temp##offset##_crit(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
487 | size_t count) \ | ||
488 | { \ | ||
489 | struct i2c_client *client = to_i2c_client(dev); \ | ||
490 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
491 | long val = simple_strtol(buf, NULL, 10); \ | ||
492 | \ | ||
493 | down(&data->update_lock); \ | ||
494 | data->in_crit[offset-4] = IN_TO_REG(val, data->in_vref); \ | ||
495 | pc87360_write_value(data, LD_IN, offset+7, PC87365_REG_TEMP_CRIT, \ | ||
496 | data->in_crit[offset-4]); \ | ||
497 | up(&data->update_lock); \ | ||
498 | return count; \ | ||
499 | } \ | ||
500 | static DEVICE_ATTR(temp##offset##_input, S_IRUGO, \ | ||
501 | show_temp##offset##_input, NULL); \ | ||
502 | static DEVICE_ATTR(temp##offset##_min, S_IWUSR | S_IRUGO, \ | ||
503 | show_temp##offset##_min, set_temp##offset##_min); \ | ||
504 | static DEVICE_ATTR(temp##offset##_max, S_IWUSR | S_IRUGO, \ | ||
505 | show_temp##offset##_max, set_temp##offset##_max); \ | ||
506 | static DEVICE_ATTR(temp##offset##_crit, S_IWUSR | S_IRUGO, \ | ||
507 | show_temp##offset##_crit, set_temp##offset##_crit); \ | ||
508 | static DEVICE_ATTR(temp##offset##_status, S_IRUGO, \ | ||
509 | show_temp##offset##_status, NULL); | ||
510 | show_and_set_therm(4) | 524 | show_and_set_therm(4) |
511 | show_and_set_therm(5) | 525 | show_and_set_therm(5) |
512 | show_and_set_therm(6) | 526 | show_and_set_therm(6) |
@@ -539,84 +553,93 @@ static ssize_t show_in_alarms(struct device *dev, struct device_attribute *attr, | |||
539 | } | 553 | } |
540 | static DEVICE_ATTR(alarms_in, S_IRUGO, show_in_alarms, NULL); | 554 | static DEVICE_ATTR(alarms_in, S_IRUGO, show_in_alarms, NULL); |
541 | 555 | ||
556 | static ssize_t show_temp_input(struct device *dev, struct device_attribute *devattr, char *buf) | ||
557 | { | ||
558 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
559 | struct pc87360_data *data = pc87360_update_device(dev); | ||
560 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp[attr->index])); | ||
561 | } | ||
562 | static ssize_t show_temp_min(struct device *dev, struct device_attribute *devattr, char *buf) | ||
563 | { | ||
564 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
565 | struct pc87360_data *data = pc87360_update_device(dev); | ||
566 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_min[attr->index])); | ||
567 | } | ||
568 | static ssize_t show_temp_max(struct device *dev, struct device_attribute *devattr, char *buf) | ||
569 | { | ||
570 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
571 | struct pc87360_data *data = pc87360_update_device(dev); | ||
572 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[attr->index])); | ||
573 | } | ||
574 | static ssize_t show_temp_crit(struct device *dev, struct device_attribute *devattr, char *buf) | ||
575 | { | ||
576 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
577 | struct pc87360_data *data = pc87360_update_device(dev); | ||
578 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_crit[attr->index])); | ||
579 | } | ||
580 | static ssize_t show_temp_status(struct device *dev, struct device_attribute *devattr, char *buf) | ||
581 | { | ||
582 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
583 | struct pc87360_data *data = pc87360_update_device(dev); | ||
584 | return sprintf(buf, "%d\n", data->temp_status[attr->index]); | ||
585 | } | ||
586 | static ssize_t set_temp_min(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
587 | size_t count) | ||
588 | { | ||
589 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
590 | struct i2c_client *client = to_i2c_client(dev); | ||
591 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
592 | long val = simple_strtol(buf, NULL, 10); | ||
593 | |||
594 | down(&data->update_lock); | ||
595 | data->temp_min[attr->index] = TEMP_TO_REG(val); | ||
596 | pc87360_write_value(data, LD_TEMP, attr->index, PC87365_REG_TEMP_MIN, | ||
597 | data->temp_min[attr->index]); | ||
598 | up(&data->update_lock); | ||
599 | return count; | ||
600 | } | ||
601 | static ssize_t set_temp_max(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
602 | size_t count) | ||
603 | { | ||
604 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
605 | struct i2c_client *client = to_i2c_client(dev); | ||
606 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
607 | long val = simple_strtol(buf, NULL, 10); | ||
608 | |||
609 | down(&data->update_lock); | ||
610 | data->temp_max[attr->index] = TEMP_TO_REG(val); | ||
611 | pc87360_write_value(data, LD_TEMP, attr->index, PC87365_REG_TEMP_MAX, | ||
612 | data->temp_max[attr->index]); | ||
613 | up(&data->update_lock); | ||
614 | return count; | ||
615 | } | ||
616 | static ssize_t set_temp_crit(struct device *dev, struct device_attribute *devattr, const char *buf, | ||
617 | size_t count) | ||
618 | { | ||
619 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
620 | struct i2c_client *client = to_i2c_client(dev); | ||
621 | struct pc87360_data *data = i2c_get_clientdata(client); | ||
622 | long val = simple_strtol(buf, NULL, 10); | ||
623 | |||
624 | down(&data->update_lock); | ||
625 | data->temp_crit[attr->index] = TEMP_TO_REG(val); | ||
626 | pc87360_write_value(data, LD_TEMP, attr->index, PC87365_REG_TEMP_CRIT, | ||
627 | data->temp_crit[attr->index]); | ||
628 | up(&data->update_lock); | ||
629 | return count; | ||
630 | } | ||
631 | |||
542 | #define show_and_set_temp(offset) \ | 632 | #define show_and_set_temp(offset) \ |
543 | static ssize_t show_temp##offset##_input(struct device *dev, struct device_attribute *attr, char *buf) \ | 633 | static SENSOR_DEVICE_ATTR(temp##offset##_input, S_IRUGO, \ |
544 | { \ | 634 | show_temp_input, NULL, offset-1); \ |
545 | struct pc87360_data *data = pc87360_update_device(dev); \ | 635 | static SENSOR_DEVICE_ATTR(temp##offset##_min, S_IWUSR | S_IRUGO, \ |
546 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp[offset-1])); \ | 636 | show_temp_min, set_temp_min, offset-1); \ |
547 | } \ | 637 | static SENSOR_DEVICE_ATTR(temp##offset##_max, S_IWUSR | S_IRUGO, \ |
548 | static ssize_t show_temp##offset##_min(struct device *dev, struct device_attribute *attr, char *buf) \ | 638 | show_temp_max, set_temp_max, offset-1); \ |
549 | { \ | 639 | static SENSOR_DEVICE_ATTR(temp##offset##_crit, S_IWUSR | S_IRUGO, \ |
550 | struct pc87360_data *data = pc87360_update_device(dev); \ | 640 | show_temp_crit, set_temp_crit, offset-1); \ |
551 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_min[offset-1])); \ | 641 | static SENSOR_DEVICE_ATTR(temp##offset##_status, S_IRUGO, \ |
552 | } \ | 642 | show_temp_status, NULL, offset-1); |
553 | static ssize_t show_temp##offset##_max(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
554 | { \ | ||
555 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
556 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_max[offset-1])); \ | ||
557 | }\ | ||
558 | static ssize_t show_temp##offset##_crit(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
559 | { \ | ||
560 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
561 | return sprintf(buf, "%d\n", TEMP_FROM_REG(data->temp_crit[offset-1])); \ | ||
562 | }\ | ||
563 | static ssize_t show_temp##offset##_status(struct device *dev, struct device_attribute *attr, char *buf) \ | ||
564 | { \ | ||
565 | struct pc87360_data *data = pc87360_update_device(dev); \ | ||
566 | return sprintf(buf, "%d\n", data->temp_status[offset-1]); \ | ||
567 | }\ | ||
568 | static ssize_t set_temp##offset##_min(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
569 | size_t count) \ | ||
570 | { \ | ||
571 | struct i2c_client *client = to_i2c_client(dev); \ | ||
572 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
573 | long val = simple_strtol(buf, NULL, 10); \ | ||
574 | \ | ||
575 | down(&data->update_lock); \ | ||
576 | data->temp_min[offset-1] = TEMP_TO_REG(val); \ | ||
577 | pc87360_write_value(data, LD_TEMP, offset-1, PC87365_REG_TEMP_MIN, \ | ||
578 | data->temp_min[offset-1]); \ | ||
579 | up(&data->update_lock); \ | ||
580 | return count; \ | ||
581 | } \ | ||
582 | static ssize_t set_temp##offset##_max(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
583 | size_t count) \ | ||
584 | { \ | ||
585 | struct i2c_client *client = to_i2c_client(dev); \ | ||
586 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
587 | long val = simple_strtol(buf, NULL, 10); \ | ||
588 | \ | ||
589 | down(&data->update_lock); \ | ||
590 | data->temp_max[offset-1] = TEMP_TO_REG(val); \ | ||
591 | pc87360_write_value(data, LD_TEMP, offset-1, PC87365_REG_TEMP_MAX, \ | ||
592 | data->temp_max[offset-1]); \ | ||
593 | up(&data->update_lock); \ | ||
594 | return count; \ | ||
595 | } \ | ||
596 | static ssize_t set_temp##offset##_crit(struct device *dev, struct device_attribute *attr, const char *buf, \ | ||
597 | size_t count) \ | ||
598 | { \ | ||
599 | struct i2c_client *client = to_i2c_client(dev); \ | ||
600 | struct pc87360_data *data = i2c_get_clientdata(client); \ | ||
601 | long val = simple_strtol(buf, NULL, 10); \ | ||
602 | \ | ||
603 | down(&data->update_lock); \ | ||
604 | data->temp_crit[offset-1] = TEMP_TO_REG(val); \ | ||
605 | pc87360_write_value(data, LD_TEMP, offset-1, PC87365_REG_TEMP_CRIT, \ | ||
606 | data->temp_crit[offset-1]); \ | ||
607 | up(&data->update_lock); \ | ||
608 | return count; \ | ||
609 | } \ | ||
610 | static DEVICE_ATTR(temp##offset##_input, S_IRUGO, \ | ||
611 | show_temp##offset##_input, NULL); \ | ||
612 | static DEVICE_ATTR(temp##offset##_min, S_IWUSR | S_IRUGO, \ | ||
613 | show_temp##offset##_min, set_temp##offset##_min); \ | ||
614 | static DEVICE_ATTR(temp##offset##_max, S_IWUSR | S_IRUGO, \ | ||
615 | show_temp##offset##_max, set_temp##offset##_max); \ | ||
616 | static DEVICE_ATTR(temp##offset##_crit, S_IWUSR | S_IRUGO, \ | ||
617 | show_temp##offset##_crit, set_temp##offset##_crit); \ | ||
618 | static DEVICE_ATTR(temp##offset##_status, S_IRUGO, \ | ||
619 | show_temp##offset##_status, NULL); | ||
620 | show_and_set_temp(1) | 643 | show_and_set_temp(1) |
621 | show_and_set_temp(2) | 644 | show_and_set_temp(2) |
622 | show_and_set_temp(3) | 645 | show_and_set_temp(3) |
@@ -632,12 +655,7 @@ static DEVICE_ATTR(alarms_temp, S_IRUGO, show_temp_alarms, NULL); | |||
632 | * Device detection, registration and update | 655 | * Device detection, registration and update |
633 | */ | 656 | */ |
634 | 657 | ||
635 | static int pc87360_attach_adapter(struct i2c_adapter *adapter) | 658 | static int __init pc87360_find(int sioaddr, u8 *devid, unsigned short *addresses) |
636 | { | ||
637 | return i2c_detect(adapter, &addr_data, pc87360_detect); | ||
638 | } | ||
639 | |||
640 | static int pc87360_find(int sioaddr, u8 *devid, int *address) | ||
641 | { | 659 | { |
642 | u16 val; | 660 | u16 val; |
643 | int i; | 661 | int i; |
@@ -683,7 +701,7 @@ static int pc87360_find(int sioaddr, u8 *devid, int *address) | |||
683 | continue; | 701 | continue; |
684 | } | 702 | } |
685 | 703 | ||
686 | address[i] = val; | 704 | addresses[i] = val; |
687 | 705 | ||
688 | if (i==0) { /* Fans */ | 706 | if (i==0) { /* Fans */ |
689 | confreg[0] = superio_inb(sioaddr, 0xF0); | 707 | confreg[0] = superio_inb(sioaddr, 0xF0); |
@@ -727,9 +745,7 @@ static int pc87360_find(int sioaddr, u8 *devid, int *address) | |||
727 | return 0; | 745 | return 0; |
728 | } | 746 | } |
729 | 747 | ||
730 | /* We don't really care about the address. | 748 | static int pc87360_detect(struct i2c_adapter *adapter) |
731 | Read from extra_isa instead. */ | ||
732 | int pc87360_detect(struct i2c_adapter *adapter, int address, int kind) | ||
733 | { | 749 | { |
734 | int i; | 750 | int i; |
735 | struct i2c_client *new_client; | 751 | struct i2c_client *new_client; |
@@ -738,9 +754,6 @@ int pc87360_detect(struct i2c_adapter *adapter, int address, int kind) | |||
738 | const char *name = "pc87360"; | 754 | const char *name = "pc87360"; |
739 | int use_thermistors = 0; | 755 | int use_thermistors = 0; |
740 | 756 | ||
741 | if (!i2c_is_isa_adapter(adapter)) | ||
742 | return -ENODEV; | ||
743 | |||
744 | if (!(data = kmalloc(sizeof(struct pc87360_data), GFP_KERNEL))) | 757 | if (!(data = kmalloc(sizeof(struct pc87360_data), GFP_KERNEL))) |
745 | return -ENOMEM; | 758 | return -ENOMEM; |
746 | memset(data, 0x00, sizeof(struct pc87360_data)); | 759 | memset(data, 0x00, sizeof(struct pc87360_data)); |
@@ -838,51 +851,57 @@ int pc87360_detect(struct i2c_adapter *adapter, int address, int kind) | |||
838 | } | 851 | } |
839 | 852 | ||
840 | /* Register sysfs hooks */ | 853 | /* Register sysfs hooks */ |
854 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
855 | if (IS_ERR(data->class_dev)) { | ||
856 | err = PTR_ERR(data->class_dev); | ||
857 | goto ERROR3; | ||
858 | } | ||
859 | |||
841 | if (data->innr) { | 860 | if (data->innr) { |
842 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 861 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_input.dev_attr); |
843 | device_create_file(&new_client->dev, &dev_attr_in1_input); | 862 | device_create_file(&new_client->dev, &sensor_dev_attr_in1_input.dev_attr); |
844 | device_create_file(&new_client->dev, &dev_attr_in2_input); | 863 | device_create_file(&new_client->dev, &sensor_dev_attr_in2_input.dev_attr); |
845 | device_create_file(&new_client->dev, &dev_attr_in3_input); | 864 | device_create_file(&new_client->dev, &sensor_dev_attr_in3_input.dev_attr); |
846 | device_create_file(&new_client->dev, &dev_attr_in4_input); | 865 | device_create_file(&new_client->dev, &sensor_dev_attr_in4_input.dev_attr); |
847 | device_create_file(&new_client->dev, &dev_attr_in5_input); | 866 | device_create_file(&new_client->dev, &sensor_dev_attr_in5_input.dev_attr); |
848 | device_create_file(&new_client->dev, &dev_attr_in6_input); | 867 | device_create_file(&new_client->dev, &sensor_dev_attr_in6_input.dev_attr); |
849 | device_create_file(&new_client->dev, &dev_attr_in7_input); | 868 | device_create_file(&new_client->dev, &sensor_dev_attr_in7_input.dev_attr); |
850 | device_create_file(&new_client->dev, &dev_attr_in8_input); | 869 | device_create_file(&new_client->dev, &sensor_dev_attr_in8_input.dev_attr); |
851 | device_create_file(&new_client->dev, &dev_attr_in9_input); | 870 | device_create_file(&new_client->dev, &sensor_dev_attr_in9_input.dev_attr); |
852 | device_create_file(&new_client->dev, &dev_attr_in10_input); | 871 | device_create_file(&new_client->dev, &sensor_dev_attr_in10_input.dev_attr); |
853 | device_create_file(&new_client->dev, &dev_attr_in0_min); | 872 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_min.dev_attr); |
854 | device_create_file(&new_client->dev, &dev_attr_in1_min); | 873 | device_create_file(&new_client->dev, &sensor_dev_attr_in1_min.dev_attr); |
855 | device_create_file(&new_client->dev, &dev_attr_in2_min); | 874 | device_create_file(&new_client->dev, &sensor_dev_attr_in2_min.dev_attr); |
856 | device_create_file(&new_client->dev, &dev_attr_in3_min); | 875 | device_create_file(&new_client->dev, &sensor_dev_attr_in3_min.dev_attr); |
857 | device_create_file(&new_client->dev, &dev_attr_in4_min); | 876 | device_create_file(&new_client->dev, &sensor_dev_attr_in4_min.dev_attr); |
858 | device_create_file(&new_client->dev, &dev_attr_in5_min); | 877 | device_create_file(&new_client->dev, &sensor_dev_attr_in5_min.dev_attr); |
859 | device_create_file(&new_client->dev, &dev_attr_in6_min); | 878 | device_create_file(&new_client->dev, &sensor_dev_attr_in6_min.dev_attr); |
860 | device_create_file(&new_client->dev, &dev_attr_in7_min); | 879 | device_create_file(&new_client->dev, &sensor_dev_attr_in7_min.dev_attr); |
861 | device_create_file(&new_client->dev, &dev_attr_in8_min); | 880 | device_create_file(&new_client->dev, &sensor_dev_attr_in8_min.dev_attr); |
862 | device_create_file(&new_client->dev, &dev_attr_in9_min); | 881 | device_create_file(&new_client->dev, &sensor_dev_attr_in9_min.dev_attr); |
863 | device_create_file(&new_client->dev, &dev_attr_in10_min); | 882 | device_create_file(&new_client->dev, &sensor_dev_attr_in10_min.dev_attr); |
864 | device_create_file(&new_client->dev, &dev_attr_in0_max); | 883 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_max.dev_attr); |
865 | device_create_file(&new_client->dev, &dev_attr_in1_max); | 884 | device_create_file(&new_client->dev, &sensor_dev_attr_in1_max.dev_attr); |
866 | device_create_file(&new_client->dev, &dev_attr_in2_max); | 885 | device_create_file(&new_client->dev, &sensor_dev_attr_in2_max.dev_attr); |
867 | device_create_file(&new_client->dev, &dev_attr_in3_max); | 886 | device_create_file(&new_client->dev, &sensor_dev_attr_in3_max.dev_attr); |
868 | device_create_file(&new_client->dev, &dev_attr_in4_max); | 887 | device_create_file(&new_client->dev, &sensor_dev_attr_in4_max.dev_attr); |
869 | device_create_file(&new_client->dev, &dev_attr_in5_max); | 888 | device_create_file(&new_client->dev, &sensor_dev_attr_in5_max.dev_attr); |
870 | device_create_file(&new_client->dev, &dev_attr_in6_max); | 889 | device_create_file(&new_client->dev, &sensor_dev_attr_in6_max.dev_attr); |
871 | device_create_file(&new_client->dev, &dev_attr_in7_max); | 890 | device_create_file(&new_client->dev, &sensor_dev_attr_in7_max.dev_attr); |
872 | device_create_file(&new_client->dev, &dev_attr_in8_max); | 891 | device_create_file(&new_client->dev, &sensor_dev_attr_in8_max.dev_attr); |
873 | device_create_file(&new_client->dev, &dev_attr_in9_max); | 892 | device_create_file(&new_client->dev, &sensor_dev_attr_in9_max.dev_attr); |
874 | device_create_file(&new_client->dev, &dev_attr_in10_max); | 893 | device_create_file(&new_client->dev, &sensor_dev_attr_in10_max.dev_attr); |
875 | device_create_file(&new_client->dev, &dev_attr_in0_status); | 894 | device_create_file(&new_client->dev, &sensor_dev_attr_in0_status.dev_attr); |
876 | device_create_file(&new_client->dev, &dev_attr_in1_status); | 895 | device_create_file(&new_client->dev, &sensor_dev_attr_in1_status.dev_attr); |
877 | device_create_file(&new_client->dev, &dev_attr_in2_status); | 896 | device_create_file(&new_client->dev, &sensor_dev_attr_in2_status.dev_attr); |
878 | device_create_file(&new_client->dev, &dev_attr_in3_status); | 897 | device_create_file(&new_client->dev, &sensor_dev_attr_in3_status.dev_attr); |
879 | device_create_file(&new_client->dev, &dev_attr_in4_status); | 898 | device_create_file(&new_client->dev, &sensor_dev_attr_in4_status.dev_attr); |
880 | device_create_file(&new_client->dev, &dev_attr_in5_status); | 899 | device_create_file(&new_client->dev, &sensor_dev_attr_in5_status.dev_attr); |
881 | device_create_file(&new_client->dev, &dev_attr_in6_status); | 900 | device_create_file(&new_client->dev, &sensor_dev_attr_in6_status.dev_attr); |
882 | device_create_file(&new_client->dev, &dev_attr_in7_status); | 901 | device_create_file(&new_client->dev, &sensor_dev_attr_in7_status.dev_attr); |
883 | device_create_file(&new_client->dev, &dev_attr_in8_status); | 902 | device_create_file(&new_client->dev, &sensor_dev_attr_in8_status.dev_attr); |
884 | device_create_file(&new_client->dev, &dev_attr_in9_status); | 903 | device_create_file(&new_client->dev, &sensor_dev_attr_in9_status.dev_attr); |
885 | device_create_file(&new_client->dev, &dev_attr_in10_status); | 904 | device_create_file(&new_client->dev, &sensor_dev_attr_in10_status.dev_attr); |
886 | 905 | ||
887 | device_create_file(&new_client->dev, &dev_attr_cpu0_vid); | 906 | device_create_file(&new_client->dev, &dev_attr_cpu0_vid); |
888 | device_create_file(&new_client->dev, &dev_attr_vrm); | 907 | device_create_file(&new_client->dev, &dev_attr_vrm); |
@@ -890,90 +909,92 @@ int pc87360_detect(struct i2c_adapter *adapter, int address, int kind) | |||
890 | } | 909 | } |
891 | 910 | ||
892 | if (data->tempnr) { | 911 | if (data->tempnr) { |
893 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 912 | device_create_file(&new_client->dev, &sensor_dev_attr_temp1_input.dev_attr); |
894 | device_create_file(&new_client->dev, &dev_attr_temp2_input); | 913 | device_create_file(&new_client->dev, &sensor_dev_attr_temp2_input.dev_attr); |
895 | device_create_file(&new_client->dev, &dev_attr_temp1_min); | 914 | device_create_file(&new_client->dev, &sensor_dev_attr_temp1_min.dev_attr); |
896 | device_create_file(&new_client->dev, &dev_attr_temp2_min); | 915 | device_create_file(&new_client->dev, &sensor_dev_attr_temp2_min.dev_attr); |
897 | device_create_file(&new_client->dev, &dev_attr_temp1_max); | 916 | device_create_file(&new_client->dev, &sensor_dev_attr_temp1_max.dev_attr); |
898 | device_create_file(&new_client->dev, &dev_attr_temp2_max); | 917 | device_create_file(&new_client->dev, &sensor_dev_attr_temp2_max.dev_attr); |
899 | device_create_file(&new_client->dev, &dev_attr_temp1_crit); | 918 | device_create_file(&new_client->dev, &sensor_dev_attr_temp1_crit.dev_attr); |
900 | device_create_file(&new_client->dev, &dev_attr_temp2_crit); | 919 | device_create_file(&new_client->dev, &sensor_dev_attr_temp2_crit.dev_attr); |
901 | device_create_file(&new_client->dev, &dev_attr_temp1_status); | 920 | device_create_file(&new_client->dev, &sensor_dev_attr_temp1_status.dev_attr); |
902 | device_create_file(&new_client->dev, &dev_attr_temp2_status); | 921 | device_create_file(&new_client->dev, &sensor_dev_attr_temp2_status.dev_attr); |
903 | 922 | ||
904 | device_create_file(&new_client->dev, &dev_attr_alarms_temp); | 923 | device_create_file(&new_client->dev, &dev_attr_alarms_temp); |
905 | } | 924 | } |
906 | if (data->tempnr == 3) { | 925 | if (data->tempnr == 3) { |
907 | device_create_file(&new_client->dev, &dev_attr_temp3_input); | 926 | device_create_file(&new_client->dev, &sensor_dev_attr_temp3_input.dev_attr); |
908 | device_create_file(&new_client->dev, &dev_attr_temp3_min); | 927 | device_create_file(&new_client->dev, &sensor_dev_attr_temp3_min.dev_attr); |
909 | device_create_file(&new_client->dev, &dev_attr_temp3_max); | 928 | device_create_file(&new_client->dev, &sensor_dev_attr_temp3_max.dev_attr); |
910 | device_create_file(&new_client->dev, &dev_attr_temp3_crit); | 929 | device_create_file(&new_client->dev, &sensor_dev_attr_temp3_crit.dev_attr); |
911 | device_create_file(&new_client->dev, &dev_attr_temp3_status); | 930 | device_create_file(&new_client->dev, &sensor_dev_attr_temp3_status.dev_attr); |
912 | } | 931 | } |
913 | if (data->innr == 14) { | 932 | if (data->innr == 14) { |
914 | device_create_file(&new_client->dev, &dev_attr_temp4_input); | 933 | device_create_file(&new_client->dev, &sensor_dev_attr_temp4_input.dev_attr); |
915 | device_create_file(&new_client->dev, &dev_attr_temp5_input); | 934 | device_create_file(&new_client->dev, &sensor_dev_attr_temp5_input.dev_attr); |
916 | device_create_file(&new_client->dev, &dev_attr_temp6_input); | 935 | device_create_file(&new_client->dev, &sensor_dev_attr_temp6_input.dev_attr); |
917 | device_create_file(&new_client->dev, &dev_attr_temp4_min); | 936 | device_create_file(&new_client->dev, &sensor_dev_attr_temp4_min.dev_attr); |
918 | device_create_file(&new_client->dev, &dev_attr_temp5_min); | 937 | device_create_file(&new_client->dev, &sensor_dev_attr_temp5_min.dev_attr); |
919 | device_create_file(&new_client->dev, &dev_attr_temp6_min); | 938 | device_create_file(&new_client->dev, &sensor_dev_attr_temp6_min.dev_attr); |
920 | device_create_file(&new_client->dev, &dev_attr_temp4_max); | 939 | device_create_file(&new_client->dev, &sensor_dev_attr_temp4_max.dev_attr); |
921 | device_create_file(&new_client->dev, &dev_attr_temp5_max); | 940 | device_create_file(&new_client->dev, &sensor_dev_attr_temp5_max.dev_attr); |
922 | device_create_file(&new_client->dev, &dev_attr_temp6_max); | 941 | device_create_file(&new_client->dev, &sensor_dev_attr_temp6_max.dev_attr); |
923 | device_create_file(&new_client->dev, &dev_attr_temp4_crit); | 942 | device_create_file(&new_client->dev, &sensor_dev_attr_temp4_crit.dev_attr); |
924 | device_create_file(&new_client->dev, &dev_attr_temp5_crit); | 943 | device_create_file(&new_client->dev, &sensor_dev_attr_temp5_crit.dev_attr); |
925 | device_create_file(&new_client->dev, &dev_attr_temp6_crit); | 944 | device_create_file(&new_client->dev, &sensor_dev_attr_temp6_crit.dev_attr); |
926 | device_create_file(&new_client->dev, &dev_attr_temp4_status); | 945 | device_create_file(&new_client->dev, &sensor_dev_attr_temp4_status.dev_attr); |
927 | device_create_file(&new_client->dev, &dev_attr_temp5_status); | 946 | device_create_file(&new_client->dev, &sensor_dev_attr_temp5_status.dev_attr); |
928 | device_create_file(&new_client->dev, &dev_attr_temp6_status); | 947 | device_create_file(&new_client->dev, &sensor_dev_attr_temp6_status.dev_attr); |
929 | } | 948 | } |
930 | 949 | ||
931 | if (data->fannr) { | 950 | if (data->fannr) { |
932 | if (FAN_CONFIG_MONITOR(data->fan_conf, 0)) { | 951 | if (FAN_CONFIG_MONITOR(data->fan_conf, 0)) { |
933 | device_create_file(&new_client->dev, | 952 | device_create_file(&new_client->dev, |
934 | &dev_attr_fan1_input); | 953 | &sensor_dev_attr_fan1_input.dev_attr); |
935 | device_create_file(&new_client->dev, | 954 | device_create_file(&new_client->dev, |
936 | &dev_attr_fan1_min); | 955 | &sensor_dev_attr_fan1_min.dev_attr); |
937 | device_create_file(&new_client->dev, | 956 | device_create_file(&new_client->dev, |
938 | &dev_attr_fan1_div); | 957 | &sensor_dev_attr_fan1_div.dev_attr); |
939 | device_create_file(&new_client->dev, | 958 | device_create_file(&new_client->dev, |
940 | &dev_attr_fan1_status); | 959 | &sensor_dev_attr_fan1_status.dev_attr); |
941 | } | 960 | } |
942 | 961 | ||
943 | if (FAN_CONFIG_MONITOR(data->fan_conf, 1)) { | 962 | if (FAN_CONFIG_MONITOR(data->fan_conf, 1)) { |
944 | device_create_file(&new_client->dev, | 963 | device_create_file(&new_client->dev, |
945 | &dev_attr_fan2_input); | 964 | &sensor_dev_attr_fan2_input.dev_attr); |
946 | device_create_file(&new_client->dev, | 965 | device_create_file(&new_client->dev, |
947 | &dev_attr_fan2_min); | 966 | &sensor_dev_attr_fan2_min.dev_attr); |
948 | device_create_file(&new_client->dev, | 967 | device_create_file(&new_client->dev, |
949 | &dev_attr_fan2_div); | 968 | &sensor_dev_attr_fan2_div.dev_attr); |
950 | device_create_file(&new_client->dev, | 969 | device_create_file(&new_client->dev, |
951 | &dev_attr_fan2_status); | 970 | &sensor_dev_attr_fan2_status.dev_attr); |
952 | } | 971 | } |
953 | 972 | ||
954 | if (FAN_CONFIG_CONTROL(data->fan_conf, 0)) | 973 | if (FAN_CONFIG_CONTROL(data->fan_conf, 0)) |
955 | device_create_file(&new_client->dev, &dev_attr_pwm1); | 974 | device_create_file(&new_client->dev, &sensor_dev_attr_pwm1.dev_attr); |
956 | if (FAN_CONFIG_CONTROL(data->fan_conf, 1)) | 975 | if (FAN_CONFIG_CONTROL(data->fan_conf, 1)) |
957 | device_create_file(&new_client->dev, &dev_attr_pwm2); | 976 | device_create_file(&new_client->dev, &sensor_dev_attr_pwm2.dev_attr); |
958 | } | 977 | } |
959 | if (data->fannr == 3) { | 978 | if (data->fannr == 3) { |
960 | if (FAN_CONFIG_MONITOR(data->fan_conf, 2)) { | 979 | if (FAN_CONFIG_MONITOR(data->fan_conf, 2)) { |
961 | device_create_file(&new_client->dev, | 980 | device_create_file(&new_client->dev, |
962 | &dev_attr_fan3_input); | 981 | &sensor_dev_attr_fan3_input.dev_attr); |
963 | device_create_file(&new_client->dev, | 982 | device_create_file(&new_client->dev, |
964 | &dev_attr_fan3_min); | 983 | &sensor_dev_attr_fan3_min.dev_attr); |
965 | device_create_file(&new_client->dev, | 984 | device_create_file(&new_client->dev, |
966 | &dev_attr_fan3_div); | 985 | &sensor_dev_attr_fan3_div.dev_attr); |
967 | device_create_file(&new_client->dev, | 986 | device_create_file(&new_client->dev, |
968 | &dev_attr_fan3_status); | 987 | &sensor_dev_attr_fan3_status.dev_attr); |
969 | } | 988 | } |
970 | 989 | ||
971 | if (FAN_CONFIG_CONTROL(data->fan_conf, 2)) | 990 | if (FAN_CONFIG_CONTROL(data->fan_conf, 2)) |
972 | device_create_file(&new_client->dev, &dev_attr_pwm3); | 991 | device_create_file(&new_client->dev, &sensor_dev_attr_pwm3.dev_attr); |
973 | } | 992 | } |
974 | 993 | ||
975 | return 0; | 994 | return 0; |
976 | 995 | ||
996 | ERROR3: | ||
997 | i2c_detach_client(new_client); | ||
977 | ERROR2: | 998 | ERROR2: |
978 | for (i = 0; i < 3; i++) { | 999 | for (i = 0; i < 3; i++) { |
979 | if (data->address[i]) { | 1000 | if (data->address[i]) { |
@@ -990,11 +1011,10 @@ static int pc87360_detach_client(struct i2c_client *client) | |||
990 | struct pc87360_data *data = i2c_get_clientdata(client); | 1011 | struct pc87360_data *data = i2c_get_clientdata(client); |
991 | int i; | 1012 | int i; |
992 | 1013 | ||
993 | if ((i = i2c_detach_client(client))) { | 1014 | hwmon_device_unregister(data->class_dev); |
994 | dev_err(&client->dev, "Client deregistration failed, " | 1015 | |
995 | "client not detached.\n"); | 1016 | if ((i = i2c_detach_client(client))) |
996 | return i; | 1017 | return i; |
997 | } | ||
998 | 1018 | ||
999 | for (i = 0; i < 3; i++) { | 1019 | for (i = 0; i < 3; i++) { |
1000 | if (data->address[i]) { | 1020 | if (data->address[i]) { |
@@ -1320,23 +1340,23 @@ static int __init pc87360_init(void) | |||
1320 | /* Arbitrarily pick one of the addresses */ | 1340 | /* Arbitrarily pick one of the addresses */ |
1321 | for (i = 0; i < 3; i++) { | 1341 | for (i = 0; i < 3; i++) { |
1322 | if (extra_isa[i] != 0x0000) { | 1342 | if (extra_isa[i] != 0x0000) { |
1323 | normal_isa[0] = extra_isa[i]; | 1343 | address = extra_isa[i]; |
1324 | break; | 1344 | break; |
1325 | } | 1345 | } |
1326 | } | 1346 | } |
1327 | 1347 | ||
1328 | if (normal_isa[0] == 0x0000) { | 1348 | if (address == 0x0000) { |
1329 | printk(KERN_WARNING "pc87360: No active logical device, " | 1349 | printk(KERN_WARNING "pc87360: No active logical device, " |
1330 | "module not inserted.\n"); | 1350 | "module not inserted.\n"); |
1331 | return -ENODEV; | 1351 | return -ENODEV; |
1332 | } | 1352 | } |
1333 | 1353 | ||
1334 | return i2c_add_driver(&pc87360_driver); | 1354 | return i2c_isa_add_driver(&pc87360_driver); |
1335 | } | 1355 | } |
1336 | 1356 | ||
1337 | static void __exit pc87360_exit(void) | 1357 | static void __exit pc87360_exit(void) |
1338 | { | 1358 | { |
1339 | i2c_del_driver(&pc87360_driver); | 1359 | i2c_isa_del_driver(&pc87360_driver); |
1340 | } | 1360 | } |
1341 | 1361 | ||
1342 | 1362 | ||
diff --git a/drivers/hwmon/sis5595.c b/drivers/hwmon/sis5595.c index 6bbfc8fb4f13..8610bce08244 100644 --- a/drivers/hwmon/sis5595.c +++ b/drivers/hwmon/sis5595.c | |||
@@ -55,7 +55,9 @@ | |||
55 | #include <linux/ioport.h> | 55 | #include <linux/ioport.h> |
56 | #include <linux/pci.h> | 56 | #include <linux/pci.h> |
57 | #include <linux/i2c.h> | 57 | #include <linux/i2c.h> |
58 | #include <linux/i2c-sensor.h> | 58 | #include <linux/i2c-isa.h> |
59 | #include <linux/hwmon.h> | ||
60 | #include <linux/err.h> | ||
59 | #include <linux/init.h> | 61 | #include <linux/init.h> |
60 | #include <linux/jiffies.h> | 62 | #include <linux/jiffies.h> |
61 | #include <asm/io.h> | 63 | #include <asm/io.h> |
@@ -68,14 +70,10 @@ module_param(force_addr, ushort, 0); | |||
68 | MODULE_PARM_DESC(force_addr, | 70 | MODULE_PARM_DESC(force_addr, |
69 | "Initialize the base address of the sensors"); | 71 | "Initialize the base address of the sensors"); |
70 | 72 | ||
71 | /* Addresses to scan. | 73 | /* Device address |
72 | Note that we can't determine the ISA address until we have initialized | 74 | Note that we can't determine the ISA address until we have initialized |
73 | our module */ | 75 | our module */ |
74 | static unsigned short normal_i2c[] = { I2C_CLIENT_END }; | 76 | static unsigned short address; |
75 | static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END }; | ||
76 | |||
77 | /* Insmod parameters */ | ||
78 | SENSORS_INSMOD_1(sis5595); | ||
79 | 77 | ||
80 | /* Many SIS5595 constants specified below */ | 78 | /* Many SIS5595 constants specified below */ |
81 | 79 | ||
@@ -168,6 +166,7 @@ static inline u8 DIV_TO_REG(int val) | |||
168 | allocated. */ | 166 | allocated. */ |
169 | struct sis5595_data { | 167 | struct sis5595_data { |
170 | struct i2c_client client; | 168 | struct i2c_client client; |
169 | struct class_device *class_dev; | ||
171 | struct semaphore lock; | 170 | struct semaphore lock; |
172 | 171 | ||
173 | struct semaphore update_lock; | 172 | struct semaphore update_lock; |
@@ -190,8 +189,7 @@ struct sis5595_data { | |||
190 | 189 | ||
191 | static struct pci_dev *s_bridge; /* pointer to the (only) sis5595 */ | 190 | static struct pci_dev *s_bridge; /* pointer to the (only) sis5595 */ |
192 | 191 | ||
193 | static int sis5595_attach_adapter(struct i2c_adapter *adapter); | 192 | static int sis5595_detect(struct i2c_adapter *adapter); |
194 | static int sis5595_detect(struct i2c_adapter *adapter, int address, int kind); | ||
195 | static int sis5595_detach_client(struct i2c_client *client); | 193 | static int sis5595_detach_client(struct i2c_client *client); |
196 | 194 | ||
197 | static int sis5595_read_value(struct i2c_client *client, u8 register); | 195 | static int sis5595_read_value(struct i2c_client *client, u8 register); |
@@ -202,9 +200,7 @@ static void sis5595_init_client(struct i2c_client *client); | |||
202 | static struct i2c_driver sis5595_driver = { | 200 | static struct i2c_driver sis5595_driver = { |
203 | .owner = THIS_MODULE, | 201 | .owner = THIS_MODULE, |
204 | .name = "sis5595", | 202 | .name = "sis5595", |
205 | .id = I2C_DRIVERID_SIS5595, | 203 | .attach_adapter = sis5595_detect, |
206 | .flags = I2C_DF_NOTIFY, | ||
207 | .attach_adapter = sis5595_attach_adapter, | ||
208 | .detach_client = sis5595_detach_client, | 204 | .detach_client = sis5595_detach_client, |
209 | }; | 205 | }; |
210 | 206 | ||
@@ -476,14 +472,7 @@ static ssize_t show_alarms(struct device *dev, struct device_attribute *attr, ch | |||
476 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | 472 | static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); |
477 | 473 | ||
478 | /* This is called when the module is loaded */ | 474 | /* This is called when the module is loaded */ |
479 | static int sis5595_attach_adapter(struct i2c_adapter *adapter) | 475 | static int sis5595_detect(struct i2c_adapter *adapter) |
480 | { | ||
481 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
482 | return 0; | ||
483 | return i2c_detect(adapter, &addr_data, sis5595_detect); | ||
484 | } | ||
485 | |||
486 | int sis5595_detect(struct i2c_adapter *adapter, int address, int kind) | ||
487 | { | 476 | { |
488 | int err = 0; | 477 | int err = 0; |
489 | int i; | 478 | int i; |
@@ -492,10 +481,6 @@ int sis5595_detect(struct i2c_adapter *adapter, int address, int kind) | |||
492 | char val; | 481 | char val; |
493 | u16 a; | 482 | u16 a; |
494 | 483 | ||
495 | /* Make sure we are probing the ISA bus!! */ | ||
496 | if (!i2c_is_isa_adapter(adapter)) | ||
497 | goto exit; | ||
498 | |||
499 | if (force_addr) | 484 | if (force_addr) |
500 | address = force_addr & ~(SIS5595_EXTENT - 1); | 485 | address = force_addr & ~(SIS5595_EXTENT - 1); |
501 | /* Reserve the ISA region */ | 486 | /* Reserve the ISA region */ |
@@ -578,6 +563,12 @@ int sis5595_detect(struct i2c_adapter *adapter, int address, int kind) | |||
578 | } | 563 | } |
579 | 564 | ||
580 | /* Register sysfs hooks */ | 565 | /* Register sysfs hooks */ |
566 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
567 | if (IS_ERR(data->class_dev)) { | ||
568 | err = PTR_ERR(data->class_dev); | ||
569 | goto exit_detach; | ||
570 | } | ||
571 | |||
581 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 572 | device_create_file(&new_client->dev, &dev_attr_in0_input); |
582 | device_create_file(&new_client->dev, &dev_attr_in0_min); | 573 | device_create_file(&new_client->dev, &dev_attr_in0_min); |
583 | device_create_file(&new_client->dev, &dev_attr_in0_max); | 574 | device_create_file(&new_client->dev, &dev_attr_in0_max); |
@@ -608,7 +599,9 @@ int sis5595_detect(struct i2c_adapter *adapter, int address, int kind) | |||
608 | device_create_file(&new_client->dev, &dev_attr_temp1_max_hyst); | 599 | device_create_file(&new_client->dev, &dev_attr_temp1_max_hyst); |
609 | } | 600 | } |
610 | return 0; | 601 | return 0; |
611 | 602 | ||
603 | exit_detach: | ||
604 | i2c_detach_client(new_client); | ||
612 | exit_free: | 605 | exit_free: |
613 | kfree(data); | 606 | kfree(data); |
614 | exit_release: | 607 | exit_release: |
@@ -619,18 +612,17 @@ exit: | |||
619 | 612 | ||
620 | static int sis5595_detach_client(struct i2c_client *client) | 613 | static int sis5595_detach_client(struct i2c_client *client) |
621 | { | 614 | { |
615 | struct sis5595_data *data = i2c_get_clientdata(client); | ||
622 | int err; | 616 | int err; |
623 | 617 | ||
624 | if ((err = i2c_detach_client(client))) { | 618 | hwmon_device_unregister(data->class_dev); |
625 | dev_err(&client->dev, | 619 | |
626 | "Client deregistration failed, client not detached.\n"); | 620 | if ((err = i2c_detach_client(client))) |
627 | return err; | 621 | return err; |
628 | } | ||
629 | 622 | ||
630 | if (i2c_is_isa_client(client)) | 623 | release_region(client->addr, SIS5595_EXTENT); |
631 | release_region(client->addr, SIS5595_EXTENT); | ||
632 | 624 | ||
633 | kfree(i2c_get_clientdata(client)); | 625 | kfree(data); |
634 | 626 | ||
635 | return 0; | 627 | return 0; |
636 | } | 628 | } |
@@ -745,7 +737,6 @@ static int __devinit sis5595_pci_probe(struct pci_dev *dev, | |||
745 | { | 737 | { |
746 | u16 val; | 738 | u16 val; |
747 | int *i; | 739 | int *i; |
748 | int addr = 0; | ||
749 | 740 | ||
750 | for (i = blacklist; *i != 0; i++) { | 741 | for (i = blacklist; *i != 0; i++) { |
751 | struct pci_dev *dev; | 742 | struct pci_dev *dev; |
@@ -761,22 +752,19 @@ static int __devinit sis5595_pci_probe(struct pci_dev *dev, | |||
761 | pci_read_config_word(dev, SIS5595_BASE_REG, &val)) | 752 | pci_read_config_word(dev, SIS5595_BASE_REG, &val)) |
762 | return -ENODEV; | 753 | return -ENODEV; |
763 | 754 | ||
764 | addr = val & ~(SIS5595_EXTENT - 1); | 755 | address = val & ~(SIS5595_EXTENT - 1); |
765 | if (addr == 0 && force_addr == 0) { | 756 | if (address == 0 && force_addr == 0) { |
766 | dev_err(&dev->dev, "Base address not set - upgrade BIOS or use force_addr=0xaddr\n"); | 757 | dev_err(&dev->dev, "Base address not set - upgrade BIOS or use force_addr=0xaddr\n"); |
767 | return -ENODEV; | 758 | return -ENODEV; |
768 | } | 759 | } |
769 | if (force_addr) | ||
770 | addr = force_addr; /* so detect will get called */ | ||
771 | 760 | ||
772 | if (!addr) { | 761 | if (!address) { |
773 | dev_err(&dev->dev,"No SiS 5595 sensors found.\n"); | 762 | dev_err(&dev->dev,"No SiS 5595 sensors found.\n"); |
774 | return -ENODEV; | 763 | return -ENODEV; |
775 | } | 764 | } |
776 | normal_isa[0] = addr; | ||
777 | 765 | ||
778 | s_bridge = pci_dev_get(dev); | 766 | s_bridge = pci_dev_get(dev); |
779 | if (i2c_add_driver(&sis5595_driver)) { | 767 | if (i2c_isa_add_driver(&sis5595_driver)) { |
780 | pci_dev_put(s_bridge); | 768 | pci_dev_put(s_bridge); |
781 | s_bridge = NULL; | 769 | s_bridge = NULL; |
782 | } | 770 | } |
@@ -803,7 +791,7 @@ static void __exit sm_sis5595_exit(void) | |||
803 | { | 791 | { |
804 | pci_unregister_driver(&sis5595_pci_driver); | 792 | pci_unregister_driver(&sis5595_pci_driver); |
805 | if (s_bridge != NULL) { | 793 | if (s_bridge != NULL) { |
806 | i2c_del_driver(&sis5595_driver); | 794 | i2c_isa_del_driver(&sis5595_driver); |
807 | pci_dev_put(s_bridge); | 795 | pci_dev_put(s_bridge); |
808 | s_bridge = NULL; | 796 | s_bridge = NULL; |
809 | } | 797 | } |
diff --git a/drivers/hwmon/smsc47b397.c b/drivers/hwmon/smsc47b397.c index fdeeb3ab6f2f..7fe71576dea4 100644 --- a/drivers/hwmon/smsc47b397.c +++ b/drivers/hwmon/smsc47b397.c | |||
@@ -31,23 +31,14 @@ | |||
31 | #include <linux/ioport.h> | 31 | #include <linux/ioport.h> |
32 | #include <linux/jiffies.h> | 32 | #include <linux/jiffies.h> |
33 | #include <linux/i2c.h> | 33 | #include <linux/i2c.h> |
34 | #include <linux/i2c-sensor.h> | 34 | #include <linux/i2c-isa.h> |
35 | #include <linux/hwmon.h> | ||
36 | #include <linux/err.h> | ||
35 | #include <linux/init.h> | 37 | #include <linux/init.h> |
36 | #include <asm/io.h> | 38 | #include <asm/io.h> |
37 | 39 | ||
38 | static unsigned short normal_i2c[] = { I2C_CLIENT_END }; | ||
39 | /* Address is autodetected, there is no default value */ | 40 | /* Address is autodetected, there is no default value */ |
40 | static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END }; | 41 | static unsigned short address; |
41 | static struct i2c_force_data forces[] = {{NULL}}; | ||
42 | |||
43 | enum chips { any_chip, smsc47b397 }; | ||
44 | static struct i2c_address_data addr_data = { | ||
45 | .normal_i2c = normal_i2c, | ||
46 | .normal_isa = normal_isa, | ||
47 | .probe = normal_i2c, /* cheat */ | ||
48 | .ignore = normal_i2c, /* cheat */ | ||
49 | .forces = forces, | ||
50 | }; | ||
51 | 42 | ||
52 | /* Super-I/0 registers and commands */ | 43 | /* Super-I/0 registers and commands */ |
53 | 44 | ||
@@ -100,6 +91,7 @@ static u8 smsc47b397_reg_temp[] = {0x25, 0x26, 0x27, 0x80}; | |||
100 | 91 | ||
101 | struct smsc47b397_data { | 92 | struct smsc47b397_data { |
102 | struct i2c_client client; | 93 | struct i2c_client client; |
94 | struct class_device *class_dev; | ||
103 | struct semaphore lock; | 95 | struct semaphore lock; |
104 | 96 | ||
105 | struct semaphore update_lock; | 97 | struct semaphore update_lock; |
@@ -215,52 +207,40 @@ sysfs_fan(4); | |||
215 | #define device_create_file_fan(client, num) \ | 207 | #define device_create_file_fan(client, num) \ |
216 | device_create_file(&client->dev, &dev_attr_fan##num##_input) | 208 | device_create_file(&client->dev, &dev_attr_fan##num##_input) |
217 | 209 | ||
218 | static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind); | ||
219 | |||
220 | static int smsc47b397_attach_adapter(struct i2c_adapter *adapter) | ||
221 | { | ||
222 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
223 | return 0; | ||
224 | return i2c_detect(adapter, &addr_data, smsc47b397_detect); | ||
225 | } | ||
226 | |||
227 | static int smsc47b397_detach_client(struct i2c_client *client) | 210 | static int smsc47b397_detach_client(struct i2c_client *client) |
228 | { | 211 | { |
212 | struct smsc47b397_data *data = i2c_get_clientdata(client); | ||
229 | int err; | 213 | int err; |
230 | 214 | ||
231 | if ((err = i2c_detach_client(client))) { | 215 | hwmon_device_unregister(data->class_dev); |
232 | dev_err(&client->dev, "Client deregistration failed, " | 216 | |
233 | "client not detached.\n"); | 217 | if ((err = i2c_detach_client(client))) |
234 | return err; | 218 | return err; |
235 | } | ||
236 | 219 | ||
237 | release_region(client->addr, SMSC_EXTENT); | 220 | release_region(client->addr, SMSC_EXTENT); |
238 | kfree(i2c_get_clientdata(client)); | 221 | kfree(data); |
239 | 222 | ||
240 | return 0; | 223 | return 0; |
241 | } | 224 | } |
242 | 225 | ||
226 | static int smsc47b397_detect(struct i2c_adapter *adapter); | ||
227 | |||
243 | static struct i2c_driver smsc47b397_driver = { | 228 | static struct i2c_driver smsc47b397_driver = { |
244 | .owner = THIS_MODULE, | 229 | .owner = THIS_MODULE, |
245 | .name = "smsc47b397", | 230 | .name = "smsc47b397", |
246 | .id = I2C_DRIVERID_SMSC47B397, | 231 | .attach_adapter = smsc47b397_detect, |
247 | .flags = I2C_DF_NOTIFY, | ||
248 | .attach_adapter = smsc47b397_attach_adapter, | ||
249 | .detach_client = smsc47b397_detach_client, | 232 | .detach_client = smsc47b397_detach_client, |
250 | }; | 233 | }; |
251 | 234 | ||
252 | static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind) | 235 | static int smsc47b397_detect(struct i2c_adapter *adapter) |
253 | { | 236 | { |
254 | struct i2c_client *new_client; | 237 | struct i2c_client *new_client; |
255 | struct smsc47b397_data *data; | 238 | struct smsc47b397_data *data; |
256 | int err = 0; | 239 | int err = 0; |
257 | 240 | ||
258 | if (!i2c_is_isa_adapter(adapter)) { | 241 | if (!request_region(address, SMSC_EXTENT, smsc47b397_driver.name)) { |
259 | return 0; | 242 | dev_err(&adapter->dev, "Region 0x%x already in use!\n", |
260 | } | 243 | address); |
261 | |||
262 | if (!request_region(addr, SMSC_EXTENT, smsc47b397_driver.name)) { | ||
263 | dev_err(&adapter->dev, "Region 0x%x already in use!\n", addr); | ||
264 | return -EBUSY; | 244 | return -EBUSY; |
265 | } | 245 | } |
266 | 246 | ||
@@ -272,7 +252,7 @@ static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind) | |||
272 | 252 | ||
273 | new_client = &data->client; | 253 | new_client = &data->client; |
274 | i2c_set_clientdata(new_client, data); | 254 | i2c_set_clientdata(new_client, data); |
275 | new_client->addr = addr; | 255 | new_client->addr = address; |
276 | init_MUTEX(&data->lock); | 256 | init_MUTEX(&data->lock); |
277 | new_client->adapter = adapter; | 257 | new_client->adapter = adapter; |
278 | new_client->driver = &smsc47b397_driver; | 258 | new_client->driver = &smsc47b397_driver; |
@@ -285,6 +265,12 @@ static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind) | |||
285 | if ((err = i2c_attach_client(new_client))) | 265 | if ((err = i2c_attach_client(new_client))) |
286 | goto error_free; | 266 | goto error_free; |
287 | 267 | ||
268 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
269 | if (IS_ERR(data->class_dev)) { | ||
270 | err = PTR_ERR(data->class_dev); | ||
271 | goto error_detach; | ||
272 | } | ||
273 | |||
288 | device_create_file_temp(new_client, 1); | 274 | device_create_file_temp(new_client, 1); |
289 | device_create_file_temp(new_client, 2); | 275 | device_create_file_temp(new_client, 2); |
290 | device_create_file_temp(new_client, 3); | 276 | device_create_file_temp(new_client, 3); |
@@ -297,14 +283,16 @@ static int smsc47b397_detect(struct i2c_adapter *adapter, int addr, int kind) | |||
297 | 283 | ||
298 | return 0; | 284 | return 0; |
299 | 285 | ||
286 | error_detach: | ||
287 | i2c_detach_client(new_client); | ||
300 | error_free: | 288 | error_free: |
301 | kfree(data); | 289 | kfree(data); |
302 | error_release: | 290 | error_release: |
303 | release_region(addr, SMSC_EXTENT); | 291 | release_region(address, SMSC_EXTENT); |
304 | return err; | 292 | return err; |
305 | } | 293 | } |
306 | 294 | ||
307 | static int __init smsc47b397_find(unsigned int *addr) | 295 | static int __init smsc47b397_find(unsigned short *addr) |
308 | { | 296 | { |
309 | u8 id, rev; | 297 | u8 id, rev; |
310 | 298 | ||
@@ -333,15 +321,15 @@ static int __init smsc47b397_init(void) | |||
333 | { | 321 | { |
334 | int ret; | 322 | int ret; |
335 | 323 | ||
336 | if ((ret = smsc47b397_find(normal_isa))) | 324 | if ((ret = smsc47b397_find(&address))) |
337 | return ret; | 325 | return ret; |
338 | 326 | ||
339 | return i2c_add_driver(&smsc47b397_driver); | 327 | return i2c_isa_add_driver(&smsc47b397_driver); |
340 | } | 328 | } |
341 | 329 | ||
342 | static void __exit smsc47b397_exit(void) | 330 | static void __exit smsc47b397_exit(void) |
343 | { | 331 | { |
344 | i2c_del_driver(&smsc47b397_driver); | 332 | i2c_isa_del_driver(&smsc47b397_driver); |
345 | } | 333 | } |
346 | 334 | ||
347 | MODULE_AUTHOR("Mark M. Hoffman <mhoffman@lightlink.com>"); | 335 | MODULE_AUTHOR("Mark M. Hoffman <mhoffman@lightlink.com>"); |
diff --git a/drivers/hwmon/smsc47m1.c b/drivers/hwmon/smsc47m1.c index 7166ad0b2fda..7e699a8ede26 100644 --- a/drivers/hwmon/smsc47m1.c +++ b/drivers/hwmon/smsc47m1.c | |||
@@ -30,21 +30,14 @@ | |||
30 | #include <linux/ioport.h> | 30 | #include <linux/ioport.h> |
31 | #include <linux/jiffies.h> | 31 | #include <linux/jiffies.h> |
32 | #include <linux/i2c.h> | 32 | #include <linux/i2c.h> |
33 | #include <linux/i2c-sensor.h> | 33 | #include <linux/i2c-isa.h> |
34 | #include <linux/hwmon.h> | ||
35 | #include <linux/err.h> | ||
34 | #include <linux/init.h> | 36 | #include <linux/init.h> |
35 | #include <asm/io.h> | 37 | #include <asm/io.h> |
36 | 38 | ||
37 | static unsigned short normal_i2c[] = { I2C_CLIENT_END }; | ||
38 | /* Address is autodetected, there is no default value */ | 39 | /* Address is autodetected, there is no default value */ |
39 | static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END }; | 40 | static unsigned short address; |
40 | static struct i2c_force_data forces[] = {{NULL}}; | ||
41 | |||
42 | enum chips { any_chip, smsc47m1 }; | ||
43 | static struct i2c_address_data addr_data = { | ||
44 | .normal_i2c = normal_i2c, | ||
45 | .normal_isa = normal_isa, | ||
46 | .forces = forces, | ||
47 | }; | ||
48 | 41 | ||
49 | /* Super-I/0 registers and commands */ | 42 | /* Super-I/0 registers and commands */ |
50 | 43 | ||
@@ -108,6 +101,7 @@ superio_exit(void) | |||
108 | 101 | ||
109 | struct smsc47m1_data { | 102 | struct smsc47m1_data { |
110 | struct i2c_client client; | 103 | struct i2c_client client; |
104 | struct class_device *class_dev; | ||
111 | struct semaphore lock; | 105 | struct semaphore lock; |
112 | 106 | ||
113 | struct semaphore update_lock; | 107 | struct semaphore update_lock; |
@@ -121,9 +115,7 @@ struct smsc47m1_data { | |||
121 | }; | 115 | }; |
122 | 116 | ||
123 | 117 | ||
124 | static int smsc47m1_attach_adapter(struct i2c_adapter *adapter); | 118 | static int smsc47m1_detect(struct i2c_adapter *adapter); |
125 | static int smsc47m1_find(int *address); | ||
126 | static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind); | ||
127 | static int smsc47m1_detach_client(struct i2c_client *client); | 119 | static int smsc47m1_detach_client(struct i2c_client *client); |
128 | 120 | ||
129 | static int smsc47m1_read_value(struct i2c_client *client, u8 reg); | 121 | static int smsc47m1_read_value(struct i2c_client *client, u8 reg); |
@@ -136,9 +128,7 @@ static struct smsc47m1_data *smsc47m1_update_device(struct device *dev, | |||
136 | static struct i2c_driver smsc47m1_driver = { | 128 | static struct i2c_driver smsc47m1_driver = { |
137 | .owner = THIS_MODULE, | 129 | .owner = THIS_MODULE, |
138 | .name = "smsc47m1", | 130 | .name = "smsc47m1", |
139 | .id = I2C_DRIVERID_SMSC47M1, | 131 | .attach_adapter = smsc47m1_detect, |
140 | .flags = I2C_DF_NOTIFY, | ||
141 | .attach_adapter = smsc47m1_attach_adapter, | ||
142 | .detach_client = smsc47m1_detach_client, | 132 | .detach_client = smsc47m1_detach_client, |
143 | }; | 133 | }; |
144 | 134 | ||
@@ -354,14 +344,7 @@ fan_present(2); | |||
354 | 344 | ||
355 | static DEVICE_ATTR(alarms, S_IRUGO, get_alarms, NULL); | 345 | static DEVICE_ATTR(alarms, S_IRUGO, get_alarms, NULL); |
356 | 346 | ||
357 | static int smsc47m1_attach_adapter(struct i2c_adapter *adapter) | 347 | static int __init smsc47m1_find(unsigned short *addr) |
358 | { | ||
359 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
360 | return 0; | ||
361 | return i2c_detect(adapter, &addr_data, smsc47m1_detect); | ||
362 | } | ||
363 | |||
364 | static int smsc47m1_find(int *address) | ||
365 | { | 348 | { |
366 | u8 val; | 349 | u8 val; |
367 | 350 | ||
@@ -388,10 +371,10 @@ static int smsc47m1_find(int *address) | |||
388 | } | 371 | } |
389 | 372 | ||
390 | superio_select(); | 373 | superio_select(); |
391 | *address = (superio_inb(SUPERIO_REG_BASE) << 8) | 374 | *addr = (superio_inb(SUPERIO_REG_BASE) << 8) |
392 | | superio_inb(SUPERIO_REG_BASE + 1); | 375 | | superio_inb(SUPERIO_REG_BASE + 1); |
393 | val = superio_inb(SUPERIO_REG_ACT); | 376 | val = superio_inb(SUPERIO_REG_ACT); |
394 | if (*address == 0 || (val & 0x01) == 0) { | 377 | if (*addr == 0 || (val & 0x01) == 0) { |
395 | printk(KERN_INFO "smsc47m1: Device is disabled, will not use\n"); | 378 | printk(KERN_INFO "smsc47m1: Device is disabled, will not use\n"); |
396 | superio_exit(); | 379 | superio_exit(); |
397 | return -ENODEV; | 380 | return -ENODEV; |
@@ -401,17 +384,13 @@ static int smsc47m1_find(int *address) | |||
401 | return 0; | 384 | return 0; |
402 | } | 385 | } |
403 | 386 | ||
404 | static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind) | 387 | static int smsc47m1_detect(struct i2c_adapter *adapter) |
405 | { | 388 | { |
406 | struct i2c_client *new_client; | 389 | struct i2c_client *new_client; |
407 | struct smsc47m1_data *data; | 390 | struct smsc47m1_data *data; |
408 | int err = 0; | 391 | int err = 0; |
409 | int fan1, fan2, pwm1, pwm2; | 392 | int fan1, fan2, pwm1, pwm2; |
410 | 393 | ||
411 | if (!i2c_is_isa_adapter(adapter)) { | ||
412 | return 0; | ||
413 | } | ||
414 | |||
415 | if (!request_region(address, SMSC_EXTENT, smsc47m1_driver.name)) { | 394 | if (!request_region(address, SMSC_EXTENT, smsc47m1_driver.name)) { |
416 | dev_err(&adapter->dev, "Region 0x%x already in use!\n", address); | 395 | dev_err(&adapter->dev, "Region 0x%x already in use!\n", address); |
417 | return -EBUSY; | 396 | return -EBUSY; |
@@ -461,6 +440,13 @@ static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind) | |||
461 | function. */ | 440 | function. */ |
462 | smsc47m1_update_device(&new_client->dev, 1); | 441 | smsc47m1_update_device(&new_client->dev, 1); |
463 | 442 | ||
443 | /* Register sysfs hooks */ | ||
444 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
445 | if (IS_ERR(data->class_dev)) { | ||
446 | err = PTR_ERR(data->class_dev); | ||
447 | goto error_detach; | ||
448 | } | ||
449 | |||
464 | if (fan1) { | 450 | if (fan1) { |
465 | device_create_file(&new_client->dev, &dev_attr_fan1_input); | 451 | device_create_file(&new_client->dev, &dev_attr_fan1_input); |
466 | device_create_file(&new_client->dev, &dev_attr_fan1_min); | 452 | device_create_file(&new_client->dev, &dev_attr_fan1_min); |
@@ -494,6 +480,8 @@ static int smsc47m1_detect(struct i2c_adapter *adapter, int address, int kind) | |||
494 | 480 | ||
495 | return 0; | 481 | return 0; |
496 | 482 | ||
483 | error_detach: | ||
484 | i2c_detach_client(new_client); | ||
497 | error_free: | 485 | error_free: |
498 | kfree(data); | 486 | kfree(data); |
499 | error_release: | 487 | error_release: |
@@ -503,16 +491,16 @@ error_release: | |||
503 | 491 | ||
504 | static int smsc47m1_detach_client(struct i2c_client *client) | 492 | static int smsc47m1_detach_client(struct i2c_client *client) |
505 | { | 493 | { |
494 | struct smsc47m1_data *data = i2c_get_clientdata(client); | ||
506 | int err; | 495 | int err; |
507 | 496 | ||
508 | if ((err = i2c_detach_client(client))) { | 497 | hwmon_device_unregister(data->class_dev); |
509 | dev_err(&client->dev, "Client deregistration failed, " | 498 | |
510 | "client not detached.\n"); | 499 | if ((err = i2c_detach_client(client))) |
511 | return err; | 500 | return err; |
512 | } | ||
513 | 501 | ||
514 | release_region(client->addr, SMSC_EXTENT); | 502 | release_region(client->addr, SMSC_EXTENT); |
515 | kfree(i2c_get_clientdata(client)); | 503 | kfree(data); |
516 | 504 | ||
517 | return 0; | 505 | return 0; |
518 | } | 506 | } |
@@ -573,16 +561,16 @@ static struct smsc47m1_data *smsc47m1_update_device(struct device *dev, | |||
573 | 561 | ||
574 | static int __init sm_smsc47m1_init(void) | 562 | static int __init sm_smsc47m1_init(void) |
575 | { | 563 | { |
576 | if (smsc47m1_find(normal_isa)) { | 564 | if (smsc47m1_find(&address)) { |
577 | return -ENODEV; | 565 | return -ENODEV; |
578 | } | 566 | } |
579 | 567 | ||
580 | return i2c_add_driver(&smsc47m1_driver); | 568 | return i2c_isa_add_driver(&smsc47m1_driver); |
581 | } | 569 | } |
582 | 570 | ||
583 | static void __exit sm_smsc47m1_exit(void) | 571 | static void __exit sm_smsc47m1_exit(void) |
584 | { | 572 | { |
585 | i2c_del_driver(&smsc47m1_driver); | 573 | i2c_isa_del_driver(&smsc47m1_driver); |
586 | } | 574 | } |
587 | 575 | ||
588 | MODULE_AUTHOR("Mark D. Studebaker <mdsxyz123@yahoo.com>"); | 576 | MODULE_AUTHOR("Mark D. Studebaker <mdsxyz123@yahoo.com>"); |
diff --git a/drivers/hwmon/via686a.c b/drivers/hwmon/via686a.c index 164d47948390..eb84997627c8 100644 --- a/drivers/hwmon/via686a.c +++ b/drivers/hwmon/via686a.c | |||
@@ -35,7 +35,9 @@ | |||
35 | #include <linux/pci.h> | 35 | #include <linux/pci.h> |
36 | #include <linux/jiffies.h> | 36 | #include <linux/jiffies.h> |
37 | #include <linux/i2c.h> | 37 | #include <linux/i2c.h> |
38 | #include <linux/i2c-sensor.h> | 38 | #include <linux/i2c-isa.h> |
39 | #include <linux/hwmon.h> | ||
40 | #include <linux/err.h> | ||
39 | #include <linux/init.h> | 41 | #include <linux/init.h> |
40 | #include <asm/io.h> | 42 | #include <asm/io.h> |
41 | 43 | ||
@@ -47,14 +49,10 @@ module_param(force_addr, ushort, 0); | |||
47 | MODULE_PARM_DESC(force_addr, | 49 | MODULE_PARM_DESC(force_addr, |
48 | "Initialize the base address of the sensors"); | 50 | "Initialize the base address of the sensors"); |
49 | 51 | ||
50 | /* Addresses to scan. | 52 | /* Device address |
51 | Note that we can't determine the ISA address until we have initialized | 53 | Note that we can't determine the ISA address until we have initialized |
52 | our module */ | 54 | our module */ |
53 | static unsigned short normal_i2c[] = { I2C_CLIENT_END }; | 55 | static unsigned short address; |
54 | static unsigned int normal_isa[] = { 0x0000, I2C_CLIENT_ISA_END }; | ||
55 | |||
56 | /* Insmod parameters */ | ||
57 | SENSORS_INSMOD_1(via686a); | ||
58 | 56 | ||
59 | /* | 57 | /* |
60 | The Via 686a southbridge has a LM78-like chip integrated on the same IC. | 58 | The Via 686a southbridge has a LM78-like chip integrated on the same IC. |
@@ -297,6 +295,7 @@ static inline long TEMP_FROM_REG10(u16 val) | |||
297 | via686a client is allocated. */ | 295 | via686a client is allocated. */ |
298 | struct via686a_data { | 296 | struct via686a_data { |
299 | struct i2c_client client; | 297 | struct i2c_client client; |
298 | struct class_device *class_dev; | ||
300 | struct semaphore update_lock; | 299 | struct semaphore update_lock; |
301 | char valid; /* !=0 if following fields are valid */ | 300 | char valid; /* !=0 if following fields are valid */ |
302 | unsigned long last_updated; /* In jiffies */ | 301 | unsigned long last_updated; /* In jiffies */ |
@@ -315,8 +314,7 @@ struct via686a_data { | |||
315 | 314 | ||
316 | static struct pci_dev *s_bridge; /* pointer to the (only) via686a */ | 315 | static struct pci_dev *s_bridge; /* pointer to the (only) via686a */ |
317 | 316 | ||
318 | static int via686a_attach_adapter(struct i2c_adapter *adapter); | 317 | static int via686a_detect(struct i2c_adapter *adapter); |
319 | static int via686a_detect(struct i2c_adapter *adapter, int address, int kind); | ||
320 | static int via686a_detach_client(struct i2c_client *client); | 318 | static int via686a_detach_client(struct i2c_client *client); |
321 | 319 | ||
322 | static inline int via686a_read_value(struct i2c_client *client, u8 reg) | 320 | static inline int via686a_read_value(struct i2c_client *client, u8 reg) |
@@ -576,22 +574,13 @@ static DEVICE_ATTR(alarms, S_IRUGO, show_alarms, NULL); | |||
576 | static struct i2c_driver via686a_driver = { | 574 | static struct i2c_driver via686a_driver = { |
577 | .owner = THIS_MODULE, | 575 | .owner = THIS_MODULE, |
578 | .name = "via686a", | 576 | .name = "via686a", |
579 | .id = I2C_DRIVERID_VIA686A, | 577 | .attach_adapter = via686a_detect, |
580 | .flags = I2C_DF_NOTIFY, | ||
581 | .attach_adapter = via686a_attach_adapter, | ||
582 | .detach_client = via686a_detach_client, | 578 | .detach_client = via686a_detach_client, |
583 | }; | 579 | }; |
584 | 580 | ||
585 | 581 | ||
586 | /* This is called when the module is loaded */ | 582 | /* This is called when the module is loaded */ |
587 | static int via686a_attach_adapter(struct i2c_adapter *adapter) | 583 | static int via686a_detect(struct i2c_adapter *adapter) |
588 | { | ||
589 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
590 | return 0; | ||
591 | return i2c_detect(adapter, &addr_data, via686a_detect); | ||
592 | } | ||
593 | |||
594 | static int via686a_detect(struct i2c_adapter *adapter, int address, int kind) | ||
595 | { | 584 | { |
596 | struct i2c_client *new_client; | 585 | struct i2c_client *new_client; |
597 | struct via686a_data *data; | 586 | struct via686a_data *data; |
@@ -599,13 +588,6 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind) | |||
599 | const char client_name[] = "via686a"; | 588 | const char client_name[] = "via686a"; |
600 | u16 val; | 589 | u16 val; |
601 | 590 | ||
602 | /* Make sure we are probing the ISA bus!! */ | ||
603 | if (!i2c_is_isa_adapter(adapter)) { | ||
604 | dev_err(&adapter->dev, | ||
605 | "via686a_detect called for an I2C bus adapter?!?\n"); | ||
606 | return 0; | ||
607 | } | ||
608 | |||
609 | /* 8231 requires multiple of 256, we enforce that on 686 as well */ | 591 | /* 8231 requires multiple of 256, we enforce that on 686 as well */ |
610 | if (force_addr) | 592 | if (force_addr) |
611 | address = force_addr & 0xFF00; | 593 | address = force_addr & 0xFF00; |
@@ -637,7 +619,7 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind) | |||
637 | 619 | ||
638 | if (!(data = kmalloc(sizeof(struct via686a_data), GFP_KERNEL))) { | 620 | if (!(data = kmalloc(sizeof(struct via686a_data), GFP_KERNEL))) { |
639 | err = -ENOMEM; | 621 | err = -ENOMEM; |
640 | goto ERROR0; | 622 | goto exit_release; |
641 | } | 623 | } |
642 | memset(data, 0, sizeof(struct via686a_data)); | 624 | memset(data, 0, sizeof(struct via686a_data)); |
643 | 625 | ||
@@ -655,12 +637,18 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind) | |||
655 | init_MUTEX(&data->update_lock); | 637 | init_MUTEX(&data->update_lock); |
656 | /* Tell the I2C layer a new client has arrived */ | 638 | /* Tell the I2C layer a new client has arrived */ |
657 | if ((err = i2c_attach_client(new_client))) | 639 | if ((err = i2c_attach_client(new_client))) |
658 | goto ERROR3; | 640 | goto exit_free; |
659 | 641 | ||
660 | /* Initialize the VIA686A chip */ | 642 | /* Initialize the VIA686A chip */ |
661 | via686a_init_client(new_client); | 643 | via686a_init_client(new_client); |
662 | 644 | ||
663 | /* Register sysfs hooks */ | 645 | /* Register sysfs hooks */ |
646 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
647 | if (IS_ERR(data->class_dev)) { | ||
648 | err = PTR_ERR(data->class_dev); | ||
649 | goto exit_detach; | ||
650 | } | ||
651 | |||
664 | device_create_file(&new_client->dev, &dev_attr_in0_input); | 652 | device_create_file(&new_client->dev, &dev_attr_in0_input); |
665 | device_create_file(&new_client->dev, &dev_attr_in1_input); | 653 | device_create_file(&new_client->dev, &dev_attr_in1_input); |
666 | device_create_file(&new_client->dev, &dev_attr_in2_input); | 654 | device_create_file(&new_client->dev, &dev_attr_in2_input); |
@@ -695,25 +683,27 @@ static int via686a_detect(struct i2c_adapter *adapter, int address, int kind) | |||
695 | 683 | ||
696 | return 0; | 684 | return 0; |
697 | 685 | ||
698 | ERROR3: | 686 | exit_detach: |
687 | i2c_detach_client(new_client); | ||
688 | exit_free: | ||
699 | kfree(data); | 689 | kfree(data); |
700 | ERROR0: | 690 | exit_release: |
701 | release_region(address, VIA686A_EXTENT); | 691 | release_region(address, VIA686A_EXTENT); |
702 | return err; | 692 | return err; |
703 | } | 693 | } |
704 | 694 | ||
705 | static int via686a_detach_client(struct i2c_client *client) | 695 | static int via686a_detach_client(struct i2c_client *client) |
706 | { | 696 | { |
697 | struct via686a_data *data = i2c_get_clientdata(client); | ||
707 | int err; | 698 | int err; |
708 | 699 | ||
709 | if ((err = i2c_detach_client(client))) { | 700 | hwmon_device_unregister(data->class_dev); |
710 | dev_err(&client->dev, | 701 | |
711 | "Client deregistration failed, client not detached.\n"); | 702 | if ((err = i2c_detach_client(client))) |
712 | return err; | 703 | return err; |
713 | } | ||
714 | 704 | ||
715 | release_region(client->addr, VIA686A_EXTENT); | 705 | release_region(client->addr, VIA686A_EXTENT); |
716 | kfree(i2c_get_clientdata(client)); | 706 | kfree(data); |
717 | 707 | ||
718 | return 0; | 708 | return 0; |
719 | } | 709 | } |
@@ -810,29 +800,25 @@ static int __devinit via686a_pci_probe(struct pci_dev *dev, | |||
810 | const struct pci_device_id *id) | 800 | const struct pci_device_id *id) |
811 | { | 801 | { |
812 | u16 val; | 802 | u16 val; |
813 | int addr = 0; | ||
814 | 803 | ||
815 | if (PCIBIOS_SUCCESSFUL != | 804 | if (PCIBIOS_SUCCESSFUL != |
816 | pci_read_config_word(dev, VIA686A_BASE_REG, &val)) | 805 | pci_read_config_word(dev, VIA686A_BASE_REG, &val)) |
817 | return -ENODEV; | 806 | return -ENODEV; |
818 | 807 | ||
819 | addr = val & ~(VIA686A_EXTENT - 1); | 808 | address = val & ~(VIA686A_EXTENT - 1); |
820 | if (addr == 0 && force_addr == 0) { | 809 | if (address == 0 && force_addr == 0) { |
821 | dev_err(&dev->dev, "base address not set - upgrade BIOS " | 810 | dev_err(&dev->dev, "base address not set - upgrade BIOS " |
822 | "or use force_addr=0xaddr\n"); | 811 | "or use force_addr=0xaddr\n"); |
823 | return -ENODEV; | 812 | return -ENODEV; |
824 | } | 813 | } |
825 | if (force_addr) | ||
826 | addr = force_addr; /* so detect will get called */ | ||
827 | 814 | ||
828 | if (!addr) { | 815 | if (!address) { |
829 | dev_err(&dev->dev, "No Via 686A sensors found.\n"); | 816 | dev_err(&dev->dev, "No Via 686A sensors found.\n"); |
830 | return -ENODEV; | 817 | return -ENODEV; |
831 | } | 818 | } |
832 | normal_isa[0] = addr; | ||
833 | 819 | ||
834 | s_bridge = pci_dev_get(dev); | 820 | s_bridge = pci_dev_get(dev); |
835 | if (i2c_add_driver(&via686a_driver)) { | 821 | if (i2c_isa_add_driver(&via686a_driver)) { |
836 | pci_dev_put(s_bridge); | 822 | pci_dev_put(s_bridge); |
837 | s_bridge = NULL; | 823 | s_bridge = NULL; |
838 | } | 824 | } |
@@ -859,7 +845,7 @@ static void __exit sm_via686a_exit(void) | |||
859 | { | 845 | { |
860 | pci_unregister_driver(&via686a_pci_driver); | 846 | pci_unregister_driver(&via686a_pci_driver); |
861 | if (s_bridge != NULL) { | 847 | if (s_bridge != NULL) { |
862 | i2c_del_driver(&via686a_driver); | 848 | i2c_isa_del_driver(&via686a_driver); |
863 | pci_dev_put(s_bridge); | 849 | pci_dev_put(s_bridge); |
864 | s_bridge = NULL; | 850 | s_bridge = NULL; |
865 | } | 851 | } |
diff --git a/drivers/hwmon/w83627ehf.c b/drivers/hwmon/w83627ehf.c index 8a40b6976e1a..b60efe8f8b26 100644 --- a/drivers/hwmon/w83627ehf.c +++ b/drivers/hwmon/w83627ehf.c | |||
@@ -9,6 +9,9 @@ | |||
9 | Thanks to Leon Moonen, Steve Cliffe and Grant Coady for their help | 9 | Thanks to Leon Moonen, Steve Cliffe and Grant Coady for their help |
10 | in testing and debugging this driver. | 10 | in testing and debugging this driver. |
11 | 11 | ||
12 | This driver also supports the W83627EHG, which is the lead-free | ||
13 | version of the W83627EHF. | ||
14 | |||
12 | This program is free software; you can redistribute it and/or modify | 15 | This program is free software; you can redistribute it and/or modify |
13 | it under the terms of the GNU General Public License as published by | 16 | it under the terms of the GNU General Public License as published by |
14 | the Free Software Foundation; either version 2 of the License, or | 17 | the Free Software Foundation; either version 2 of the License, or |
@@ -37,17 +40,14 @@ | |||
37 | #include <linux/init.h> | 40 | #include <linux/init.h> |
38 | #include <linux/slab.h> | 41 | #include <linux/slab.h> |
39 | #include <linux/i2c.h> | 42 | #include <linux/i2c.h> |
40 | #include <linux/i2c-sensor.h> | 43 | #include <linux/i2c-isa.h> |
44 | #include <linux/hwmon.h> | ||
45 | #include <linux/err.h> | ||
41 | #include <asm/io.h> | 46 | #include <asm/io.h> |
42 | #include "lm75.h" | 47 | #include "lm75.h" |
43 | 48 | ||
44 | /* Addresses to scan | 49 | /* The actual ISA address is read from Super-I/O configuration space */ |
45 | The actual ISA address is read from Super-I/O configuration space */ | 50 | static unsigned short address; |
46 | static unsigned short normal_i2c[] = { I2C_CLIENT_END }; | ||
47 | static unsigned int normal_isa[] = { 0, I2C_CLIENT_ISA_END }; | ||
48 | |||
49 | /* Insmod parameters */ | ||
50 | SENSORS_INSMOD_1(w83627ehf); | ||
51 | 51 | ||
52 | /* | 52 | /* |
53 | * Super-I/O constants and functions | 53 | * Super-I/O constants and functions |
@@ -174,6 +174,7 @@ temp1_to_reg(int temp) | |||
174 | 174 | ||
175 | struct w83627ehf_data { | 175 | struct w83627ehf_data { |
176 | struct i2c_client client; | 176 | struct i2c_client client; |
177 | struct class_device *class_dev; | ||
177 | struct semaphore lock; | 178 | struct semaphore lock; |
178 | 179 | ||
179 | struct semaphore update_lock; | 180 | struct semaphore update_lock; |
@@ -666,15 +667,12 @@ static void w83627ehf_init_client(struct i2c_client *client) | |||
666 | } | 667 | } |
667 | } | 668 | } |
668 | 669 | ||
669 | static int w83627ehf_detect(struct i2c_adapter *adapter, int address, int kind) | 670 | static int w83627ehf_detect(struct i2c_adapter *adapter) |
670 | { | 671 | { |
671 | struct i2c_client *client; | 672 | struct i2c_client *client; |
672 | struct w83627ehf_data *data; | 673 | struct w83627ehf_data *data; |
673 | int i, err = 0; | 674 | int i, err = 0; |
674 | 675 | ||
675 | if (!i2c_is_isa_adapter(adapter)) | ||
676 | return 0; | ||
677 | |||
678 | if (!request_region(address, REGION_LENGTH, w83627ehf_driver.name)) { | 676 | if (!request_region(address, REGION_LENGTH, w83627ehf_driver.name)) { |
679 | err = -EBUSY; | 677 | err = -EBUSY; |
680 | goto exit; | 678 | goto exit; |
@@ -720,6 +718,12 @@ static int w83627ehf_detect(struct i2c_adapter *adapter, int address, int kind) | |||
720 | data->has_fan |= (1 << 4); | 718 | data->has_fan |= (1 << 4); |
721 | 719 | ||
722 | /* Register sysfs hooks */ | 720 | /* Register sysfs hooks */ |
721 | data->class_dev = hwmon_device_register(&client->dev); | ||
722 | if (IS_ERR(data->class_dev)) { | ||
723 | err = PTR_ERR(data->class_dev); | ||
724 | goto exit_detach; | ||
725 | } | ||
726 | |||
723 | device_create_file(&client->dev, &dev_attr_fan1_input); | 727 | device_create_file(&client->dev, &dev_attr_fan1_input); |
724 | device_create_file(&client->dev, &dev_attr_fan1_min); | 728 | device_create_file(&client->dev, &dev_attr_fan1_min); |
725 | device_create_file(&client->dev, &dev_attr_fan1_div); | 729 | device_create_file(&client->dev, &dev_attr_fan1_div); |
@@ -753,6 +757,8 @@ static int w83627ehf_detect(struct i2c_adapter *adapter, int address, int kind) | |||
753 | 757 | ||
754 | return 0; | 758 | return 0; |
755 | 759 | ||
760 | exit_detach: | ||
761 | i2c_detach_client(client); | ||
756 | exit_free: | 762 | exit_free: |
757 | kfree(data); | 763 | kfree(data); |
758 | exit_release: | 764 | exit_release: |
@@ -761,24 +767,17 @@ exit: | |||
761 | return err; | 767 | return err; |
762 | } | 768 | } |
763 | 769 | ||
764 | static int w83627ehf_attach_adapter(struct i2c_adapter *adapter) | ||
765 | { | ||
766 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
767 | return 0; | ||
768 | return i2c_detect(adapter, &addr_data, w83627ehf_detect); | ||
769 | } | ||
770 | |||
771 | static int w83627ehf_detach_client(struct i2c_client *client) | 770 | static int w83627ehf_detach_client(struct i2c_client *client) |
772 | { | 771 | { |
772 | struct w83627ehf_data *data = i2c_get_clientdata(client); | ||
773 | int err; | 773 | int err; |
774 | 774 | ||
775 | if ((err = i2c_detach_client(client))) { | 775 | hwmon_device_unregister(data->class_dev); |
776 | dev_err(&client->dev, "Client deregistration failed, " | 776 | |
777 | "client not detached.\n"); | 777 | if ((err = i2c_detach_client(client))) |
778 | return err; | 778 | return err; |
779 | } | ||
780 | release_region(client->addr, REGION_LENGTH); | 779 | release_region(client->addr, REGION_LENGTH); |
781 | kfree(i2c_get_clientdata(client)); | 780 | kfree(data); |
782 | 781 | ||
783 | return 0; | 782 | return 0; |
784 | } | 783 | } |
@@ -786,12 +785,11 @@ static int w83627ehf_detach_client(struct i2c_client *client) | |||
786 | static struct i2c_driver w83627ehf_driver = { | 785 | static struct i2c_driver w83627ehf_driver = { |
787 | .owner = THIS_MODULE, | 786 | .owner = THIS_MODULE, |
788 | .name = "w83627ehf", | 787 | .name = "w83627ehf", |
789 | .flags = I2C_DF_NOTIFY, | 788 | .attach_adapter = w83627ehf_detect, |
790 | .attach_adapter = w83627ehf_attach_adapter, | ||
791 | .detach_client = w83627ehf_detach_client, | 789 | .detach_client = w83627ehf_detach_client, |
792 | }; | 790 | }; |
793 | 791 | ||
794 | static int __init w83627ehf_find(int sioaddr, int *address) | 792 | static int __init w83627ehf_find(int sioaddr, unsigned short *addr) |
795 | { | 793 | { |
796 | u16 val; | 794 | u16 val; |
797 | 795 | ||
@@ -809,8 +807,8 @@ static int __init w83627ehf_find(int sioaddr, int *address) | |||
809 | superio_select(W83627EHF_LD_HWM); | 807 | superio_select(W83627EHF_LD_HWM); |
810 | val = (superio_inb(SIO_REG_ADDR) << 8) | 808 | val = (superio_inb(SIO_REG_ADDR) << 8) |
811 | | superio_inb(SIO_REG_ADDR + 1); | 809 | | superio_inb(SIO_REG_ADDR + 1); |
812 | *address = val & ~(REGION_LENGTH - 1); | 810 | *addr = val & ~(REGION_LENGTH - 1); |
813 | if (*address == 0) { | 811 | if (*addr == 0) { |
814 | superio_exit(); | 812 | superio_exit(); |
815 | return -ENODEV; | 813 | return -ENODEV; |
816 | } | 814 | } |
@@ -826,16 +824,16 @@ static int __init w83627ehf_find(int sioaddr, int *address) | |||
826 | 824 | ||
827 | static int __init sensors_w83627ehf_init(void) | 825 | static int __init sensors_w83627ehf_init(void) |
828 | { | 826 | { |
829 | if (w83627ehf_find(0x2e, &normal_isa[0]) | 827 | if (w83627ehf_find(0x2e, &address) |
830 | && w83627ehf_find(0x4e, &normal_isa[0])) | 828 | && w83627ehf_find(0x4e, &address)) |
831 | return -ENODEV; | 829 | return -ENODEV; |
832 | 830 | ||
833 | return i2c_add_driver(&w83627ehf_driver); | 831 | return i2c_isa_add_driver(&w83627ehf_driver); |
834 | } | 832 | } |
835 | 833 | ||
836 | static void __exit sensors_w83627ehf_exit(void) | 834 | static void __exit sensors_w83627ehf_exit(void) |
837 | { | 835 | { |
838 | i2c_del_driver(&w83627ehf_driver); | 836 | i2c_isa_del_driver(&w83627ehf_driver); |
839 | } | 837 | } |
840 | 838 | ||
841 | MODULE_AUTHOR("Jean Delvare <khali@linux-fr.org>"); | 839 | MODULE_AUTHOR("Jean Delvare <khali@linux-fr.org>"); |
diff --git a/drivers/hwmon/w83627hf.c b/drivers/hwmon/w83627hf.c index bd87a42e068a..02bd5c0239a2 100644 --- a/drivers/hwmon/w83627hf.c +++ b/drivers/hwmon/w83627hf.c | |||
@@ -42,8 +42,10 @@ | |||
42 | #include <linux/slab.h> | 42 | #include <linux/slab.h> |
43 | #include <linux/jiffies.h> | 43 | #include <linux/jiffies.h> |
44 | #include <linux/i2c.h> | 44 | #include <linux/i2c.h> |
45 | #include <linux/i2c-sensor.h> | 45 | #include <linux/i2c-isa.h> |
46 | #include <linux/i2c-vid.h> | 46 | #include <linux/hwmon.h> |
47 | #include <linux/hwmon-vid.h> | ||
48 | #include <linux/err.h> | ||
47 | #include <asm/io.h> | 49 | #include <asm/io.h> |
48 | #include "lm75.h" | 50 | #include "lm75.h" |
49 | 51 | ||
@@ -56,12 +58,11 @@ module_param(force_i2c, byte, 0); | |||
56 | MODULE_PARM_DESC(force_i2c, | 58 | MODULE_PARM_DESC(force_i2c, |
57 | "Initialize the i2c address of the sensors"); | 59 | "Initialize the i2c address of the sensors"); |
58 | 60 | ||
59 | /* Addresses to scan */ | 61 | /* The actual ISA address is read from Super-I/O configuration space */ |
60 | static unsigned short normal_i2c[] = { I2C_CLIENT_END }; | 62 | static unsigned short address; |
61 | static unsigned int normal_isa[] = { 0, I2C_CLIENT_ISA_END }; | ||
62 | 63 | ||
63 | /* Insmod parameters */ | 64 | /* Insmod parameters */ |
64 | SENSORS_INSMOD_4(w83627hf, w83627thf, w83697hf, w83637hf); | 65 | enum chips { any_chip, w83627hf, w83627thf, w83697hf, w83637hf }; |
65 | 66 | ||
66 | static int init = 1; | 67 | static int init = 1; |
67 | module_param(init, bool, 0); | 68 | module_param(init, bool, 0); |
@@ -277,6 +278,7 @@ static inline u8 DIV_TO_REG(long val) | |||
277 | dynamically allocated, at the same time when a new client is allocated. */ | 278 | dynamically allocated, at the same time when a new client is allocated. */ |
278 | struct w83627hf_data { | 279 | struct w83627hf_data { |
279 | struct i2c_client client; | 280 | struct i2c_client client; |
281 | struct class_device *class_dev; | ||
280 | struct semaphore lock; | 282 | struct semaphore lock; |
281 | enum chips type; | 283 | enum chips type; |
282 | 284 | ||
@@ -314,9 +316,7 @@ struct w83627hf_data { | |||
314 | }; | 316 | }; |
315 | 317 | ||
316 | 318 | ||
317 | static int w83627hf_attach_adapter(struct i2c_adapter *adapter); | 319 | static int w83627hf_detect(struct i2c_adapter *adapter); |
318 | static int w83627hf_detect(struct i2c_adapter *adapter, int address, | ||
319 | int kind); | ||
320 | static int w83627hf_detach_client(struct i2c_client *client); | 320 | static int w83627hf_detach_client(struct i2c_client *client); |
321 | 321 | ||
322 | static int w83627hf_read_value(struct i2c_client *client, u16 register); | 322 | static int w83627hf_read_value(struct i2c_client *client, u16 register); |
@@ -328,9 +328,7 @@ static void w83627hf_init_client(struct i2c_client *client); | |||
328 | static struct i2c_driver w83627hf_driver = { | 328 | static struct i2c_driver w83627hf_driver = { |
329 | .owner = THIS_MODULE, | 329 | .owner = THIS_MODULE, |
330 | .name = "w83627hf", | 330 | .name = "w83627hf", |
331 | .id = I2C_DRIVERID_W83627HF, | 331 | .attach_adapter = w83627hf_detect, |
332 | .flags = I2C_DF_NOTIFY, | ||
333 | .attach_adapter = w83627hf_attach_adapter, | ||
334 | .detach_client = w83627hf_detach_client, | 332 | .detach_client = w83627hf_detach_client, |
335 | }; | 333 | }; |
336 | 334 | ||
@@ -959,16 +957,7 @@ device_create_file(&client->dev, &dev_attr_temp##offset##_type); \ | |||
959 | } while (0) | 957 | } while (0) |
960 | 958 | ||
961 | 959 | ||
962 | /* This function is called when: | 960 | static int __init w83627hf_find(int sioaddr, unsigned short *addr) |
963 | * w83627hf_driver is inserted (when this module is loaded), for each | ||
964 | available adapter | ||
965 | * when a new adapter is inserted (and w83627hf_driver is still present) */ | ||
966 | static int w83627hf_attach_adapter(struct i2c_adapter *adapter) | ||
967 | { | ||
968 | return i2c_detect(adapter, &addr_data, w83627hf_detect); | ||
969 | } | ||
970 | |||
971 | static int w83627hf_find(int sioaddr, int *address) | ||
972 | { | 961 | { |
973 | u16 val; | 962 | u16 val; |
974 | 963 | ||
@@ -988,32 +977,24 @@ static int w83627hf_find(int sioaddr, int *address) | |||
988 | superio_select(W83627HF_LD_HWM); | 977 | superio_select(W83627HF_LD_HWM); |
989 | val = (superio_inb(WINB_BASE_REG) << 8) | | 978 | val = (superio_inb(WINB_BASE_REG) << 8) | |
990 | superio_inb(WINB_BASE_REG + 1); | 979 | superio_inb(WINB_BASE_REG + 1); |
991 | *address = val & ~(WINB_EXTENT - 1); | 980 | *addr = val & ~(WINB_EXTENT - 1); |
992 | if (*address == 0 && force_addr == 0) { | 981 | if (*addr == 0 && force_addr == 0) { |
993 | superio_exit(); | 982 | superio_exit(); |
994 | return -ENODEV; | 983 | return -ENODEV; |
995 | } | 984 | } |
996 | if (force_addr) | ||
997 | *address = force_addr; /* so detect will get called */ | ||
998 | 985 | ||
999 | superio_exit(); | 986 | superio_exit(); |
1000 | return 0; | 987 | return 0; |
1001 | } | 988 | } |
1002 | 989 | ||
1003 | int w83627hf_detect(struct i2c_adapter *adapter, int address, | 990 | static int w83627hf_detect(struct i2c_adapter *adapter) |
1004 | int kind) | ||
1005 | { | 991 | { |
1006 | int val; | 992 | int val, kind; |
1007 | struct i2c_client *new_client; | 993 | struct i2c_client *new_client; |
1008 | struct w83627hf_data *data; | 994 | struct w83627hf_data *data; |
1009 | int err = 0; | 995 | int err = 0; |
1010 | const char *client_name = ""; | 996 | const char *client_name = ""; |
1011 | 997 | ||
1012 | if (!i2c_is_isa_adapter(adapter)) { | ||
1013 | err = -ENODEV; | ||
1014 | goto ERROR0; | ||
1015 | } | ||
1016 | |||
1017 | if(force_addr) | 998 | if(force_addr) |
1018 | address = force_addr & ~(WINB_EXTENT - 1); | 999 | address = force_addr & ~(WINB_EXTENT - 1); |
1019 | 1000 | ||
@@ -1102,6 +1083,12 @@ int w83627hf_detect(struct i2c_adapter *adapter, int address, | |||
1102 | data->fan_min[2] = w83627hf_read_value(new_client, W83781D_REG_FAN_MIN(3)); | 1083 | data->fan_min[2] = w83627hf_read_value(new_client, W83781D_REG_FAN_MIN(3)); |
1103 | 1084 | ||
1104 | /* Register sysfs hooks */ | 1085 | /* Register sysfs hooks */ |
1086 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
1087 | if (IS_ERR(data->class_dev)) { | ||
1088 | err = PTR_ERR(data->class_dev); | ||
1089 | goto ERROR3; | ||
1090 | } | ||
1091 | |||
1105 | device_create_file_in(new_client, 0); | 1092 | device_create_file_in(new_client, 0); |
1106 | if (kind != w83697hf) | 1093 | if (kind != w83697hf) |
1107 | device_create_file_in(new_client, 1); | 1094 | device_create_file_in(new_client, 1); |
@@ -1152,6 +1139,8 @@ int w83627hf_detect(struct i2c_adapter *adapter, int address, | |||
1152 | 1139 | ||
1153 | return 0; | 1140 | return 0; |
1154 | 1141 | ||
1142 | ERROR3: | ||
1143 | i2c_detach_client(new_client); | ||
1155 | ERROR2: | 1144 | ERROR2: |
1156 | kfree(data); | 1145 | kfree(data); |
1157 | ERROR1: | 1146 | ERROR1: |
@@ -1162,16 +1151,16 @@ int w83627hf_detect(struct i2c_adapter *adapter, int address, | |||
1162 | 1151 | ||
1163 | static int w83627hf_detach_client(struct i2c_client *client) | 1152 | static int w83627hf_detach_client(struct i2c_client *client) |
1164 | { | 1153 | { |
1154 | struct w83627hf_data *data = i2c_get_clientdata(client); | ||
1165 | int err; | 1155 | int err; |
1166 | 1156 | ||
1167 | if ((err = i2c_detach_client(client))) { | 1157 | hwmon_device_unregister(data->class_dev); |
1168 | dev_err(&client->dev, | 1158 | |
1169 | "Client deregistration failed, client not detached.\n"); | 1159 | if ((err = i2c_detach_client(client))) |
1170 | return err; | 1160 | return err; |
1171 | } | ||
1172 | 1161 | ||
1173 | release_region(client->addr, WINB_EXTENT); | 1162 | release_region(client->addr, WINB_EXTENT); |
1174 | kfree(i2c_get_clientdata(client)); | 1163 | kfree(data); |
1175 | 1164 | ||
1176 | return 0; | 1165 | return 0; |
1177 | } | 1166 | } |
@@ -1327,7 +1316,7 @@ static void w83627hf_init_client(struct i2c_client *client) | |||
1327 | data->vrm = (data->vrm_ovt & 0x01) ? 90 : 82; | 1316 | data->vrm = (data->vrm_ovt & 0x01) ? 90 : 82; |
1328 | } else { | 1317 | } else { |
1329 | /* Convert VID to voltage based on default VRM */ | 1318 | /* Convert VID to voltage based on default VRM */ |
1330 | data->vrm = i2c_which_vrm(); | 1319 | data->vrm = vid_which_vrm(); |
1331 | } | 1320 | } |
1332 | 1321 | ||
1333 | tmp = w83627hf_read_value(client, W83781D_REG_SCFG1); | 1322 | tmp = w83627hf_read_value(client, W83781D_REG_SCFG1); |
@@ -1485,20 +1474,17 @@ static struct w83627hf_data *w83627hf_update_device(struct device *dev) | |||
1485 | 1474 | ||
1486 | static int __init sensors_w83627hf_init(void) | 1475 | static int __init sensors_w83627hf_init(void) |
1487 | { | 1476 | { |
1488 | int addr; | 1477 | if (w83627hf_find(0x2e, &address) |
1489 | 1478 | && w83627hf_find(0x4e, &address)) { | |
1490 | if (w83627hf_find(0x2e, &addr) | ||
1491 | && w83627hf_find(0x4e, &addr)) { | ||
1492 | return -ENODEV; | 1479 | return -ENODEV; |
1493 | } | 1480 | } |
1494 | normal_isa[0] = addr; | ||
1495 | 1481 | ||
1496 | return i2c_add_driver(&w83627hf_driver); | 1482 | return i2c_isa_add_driver(&w83627hf_driver); |
1497 | } | 1483 | } |
1498 | 1484 | ||
1499 | static void __exit sensors_w83627hf_exit(void) | 1485 | static void __exit sensors_w83627hf_exit(void) |
1500 | { | 1486 | { |
1501 | i2c_del_driver(&w83627hf_driver); | 1487 | i2c_isa_del_driver(&w83627hf_driver); |
1502 | } | 1488 | } |
1503 | 1489 | ||
1504 | MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>, " | 1490 | MODULE_AUTHOR("Frodo Looijaard <frodol@dds.nl>, " |
diff --git a/drivers/hwmon/w83781d.c b/drivers/hwmon/w83781d.c index 0bb131ce09eb..4c43337ca780 100644 --- a/drivers/hwmon/w83781d.c +++ b/drivers/hwmon/w83781d.c | |||
@@ -38,8 +38,10 @@ | |||
38 | #include <linux/slab.h> | 38 | #include <linux/slab.h> |
39 | #include <linux/jiffies.h> | 39 | #include <linux/jiffies.h> |
40 | #include <linux/i2c.h> | 40 | #include <linux/i2c.h> |
41 | #include <linux/i2c-sensor.h> | 41 | #include <linux/i2c-isa.h> |
42 | #include <linux/i2c-vid.h> | 42 | #include <linux/hwmon.h> |
43 | #include <linux/hwmon-vid.h> | ||
44 | #include <linux/err.h> | ||
43 | #include <asm/io.h> | 45 | #include <asm/io.h> |
44 | #include "lm75.h" | 46 | #include "lm75.h" |
45 | 47 | ||
@@ -47,10 +49,10 @@ | |||
47 | static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, | 49 | static unsigned short normal_i2c[] = { 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, |
48 | 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, | 50 | 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, |
49 | 0x2c, 0x2d, 0x2e, 0x2f, I2C_CLIENT_END }; | 51 | 0x2c, 0x2d, 0x2e, 0x2f, I2C_CLIENT_END }; |
50 | static unsigned int normal_isa[] = { 0x0290, I2C_CLIENT_ISA_END }; | 52 | static unsigned short isa_address = 0x290; |
51 | 53 | ||
52 | /* Insmod parameters */ | 54 | /* Insmod parameters */ |
53 | SENSORS_INSMOD_5(w83781d, w83782d, w83783s, w83627hf, as99127f); | 55 | I2C_CLIENT_INSMOD_5(w83781d, w83782d, w83783s, w83627hf, as99127f); |
54 | I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: " | 56 | I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: " |
55 | "{bus, clientaddr, subclientaddr1, subclientaddr2}"); | 57 | "{bus, clientaddr, subclientaddr1, subclientaddr2}"); |
56 | 58 | ||
@@ -218,6 +220,7 @@ DIV_TO_REG(long val, enum chips type) | |||
218 | allocated. */ | 220 | allocated. */ |
219 | struct w83781d_data { | 221 | struct w83781d_data { |
220 | struct i2c_client client; | 222 | struct i2c_client client; |
223 | struct class_device *class_dev; | ||
221 | struct semaphore lock; | 224 | struct semaphore lock; |
222 | enum chips type; | 225 | enum chips type; |
223 | 226 | ||
@@ -255,6 +258,7 @@ struct w83781d_data { | |||
255 | }; | 258 | }; |
256 | 259 | ||
257 | static int w83781d_attach_adapter(struct i2c_adapter *adapter); | 260 | static int w83781d_attach_adapter(struct i2c_adapter *adapter); |
261 | static int w83781d_isa_attach_adapter(struct i2c_adapter *adapter); | ||
258 | static int w83781d_detect(struct i2c_adapter *adapter, int address, int kind); | 262 | static int w83781d_detect(struct i2c_adapter *adapter, int address, int kind); |
259 | static int w83781d_detach_client(struct i2c_client *client); | 263 | static int w83781d_detach_client(struct i2c_client *client); |
260 | 264 | ||
@@ -273,6 +277,14 @@ static struct i2c_driver w83781d_driver = { | |||
273 | .detach_client = w83781d_detach_client, | 277 | .detach_client = w83781d_detach_client, |
274 | }; | 278 | }; |
275 | 279 | ||
280 | static struct i2c_driver w83781d_isa_driver = { | ||
281 | .owner = THIS_MODULE, | ||
282 | .name = "w83781d-isa", | ||
283 | .attach_adapter = w83781d_isa_attach_adapter, | ||
284 | .detach_client = w83781d_detach_client, | ||
285 | }; | ||
286 | |||
287 | |||
276 | /* following are the sysfs callback functions */ | 288 | /* following are the sysfs callback functions */ |
277 | #define show_in_reg(reg) \ | 289 | #define show_in_reg(reg) \ |
278 | static ssize_t show_##reg (struct device *dev, char *buf, int nr) \ | 290 | static ssize_t show_##reg (struct device *dev, char *buf, int nr) \ |
@@ -856,7 +868,13 @@ w83781d_attach_adapter(struct i2c_adapter *adapter) | |||
856 | { | 868 | { |
857 | if (!(adapter->class & I2C_CLASS_HWMON)) | 869 | if (!(adapter->class & I2C_CLASS_HWMON)) |
858 | return 0; | 870 | return 0; |
859 | return i2c_detect(adapter, &addr_data, w83781d_detect); | 871 | return i2c_probe(adapter, &addr_data, w83781d_detect); |
872 | } | ||
873 | |||
874 | static int | ||
875 | w83781d_isa_attach_adapter(struct i2c_adapter *adapter) | ||
876 | { | ||
877 | return w83781d_detect(adapter, isa_address, -1); | ||
860 | } | 878 | } |
861 | 879 | ||
862 | /* Assumes that adapter is of I2C, not ISA variety. | 880 | /* Assumes that adapter is of I2C, not ISA variety. |
@@ -961,10 +979,10 @@ w83781d_detect_subclients(struct i2c_adapter *adapter, int address, int kind, | |||
961 | ERROR_SC_3: | 979 | ERROR_SC_3: |
962 | i2c_detach_client(data->lm75[0]); | 980 | i2c_detach_client(data->lm75[0]); |
963 | ERROR_SC_2: | 981 | ERROR_SC_2: |
964 | if (NULL != data->lm75[1]) | 982 | if (data->lm75[1]) |
965 | kfree(data->lm75[1]); | 983 | kfree(data->lm75[1]); |
966 | ERROR_SC_1: | 984 | ERROR_SC_1: |
967 | if (NULL != data->lm75[0]) | 985 | if (data->lm75[0]) |
968 | kfree(data->lm75[0]); | 986 | kfree(data->lm75[0]); |
969 | ERROR_SC_0: | 987 | ERROR_SC_0: |
970 | return err; | 988 | return err; |
@@ -999,7 +1017,7 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind) | |||
999 | 1017 | ||
1000 | if (is_isa) | 1018 | if (is_isa) |
1001 | if (!request_region(address, W83781D_EXTENT, | 1019 | if (!request_region(address, W83781D_EXTENT, |
1002 | w83781d_driver.name)) { | 1020 | w83781d_isa_driver.name)) { |
1003 | dev_dbg(&adapter->dev, "Request of region " | 1021 | dev_dbg(&adapter->dev, "Request of region " |
1004 | "0x%x-0x%x for w83781d failed\n", address, | 1022 | "0x%x-0x%x for w83781d failed\n", address, |
1005 | address + W83781D_EXTENT - 1); | 1023 | address + W83781D_EXTENT - 1); |
@@ -1057,7 +1075,7 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind) | |||
1057 | new_client->addr = address; | 1075 | new_client->addr = address; |
1058 | init_MUTEX(&data->lock); | 1076 | init_MUTEX(&data->lock); |
1059 | new_client->adapter = adapter; | 1077 | new_client->adapter = adapter; |
1060 | new_client->driver = &w83781d_driver; | 1078 | new_client->driver = is_isa ? &w83781d_isa_driver : &w83781d_driver; |
1061 | new_client->flags = 0; | 1079 | new_client->flags = 0; |
1062 | 1080 | ||
1063 | /* Now, we do the remaining detection. */ | 1081 | /* Now, we do the remaining detection. */ |
@@ -1189,6 +1207,12 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind) | |||
1189 | data->pwmenable[i] = 1; | 1207 | data->pwmenable[i] = 1; |
1190 | 1208 | ||
1191 | /* Register sysfs hooks */ | 1209 | /* Register sysfs hooks */ |
1210 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
1211 | if (IS_ERR(data->class_dev)) { | ||
1212 | err = PTR_ERR(data->class_dev); | ||
1213 | goto ERROR4; | ||
1214 | } | ||
1215 | |||
1192 | device_create_file_in(new_client, 0); | 1216 | device_create_file_in(new_client, 0); |
1193 | if (kind != w83783s) | 1217 | if (kind != w83783s) |
1194 | device_create_file_in(new_client, 1); | 1218 | device_create_file_in(new_client, 1); |
@@ -1241,6 +1265,15 @@ w83781d_detect(struct i2c_adapter *adapter, int address, int kind) | |||
1241 | 1265 | ||
1242 | return 0; | 1266 | return 0; |
1243 | 1267 | ||
1268 | ERROR4: | ||
1269 | if (data->lm75[1]) { | ||
1270 | i2c_detach_client(data->lm75[1]); | ||
1271 | kfree(data->lm75[1]); | ||
1272 | } | ||
1273 | if (data->lm75[0]) { | ||
1274 | i2c_detach_client(data->lm75[0]); | ||
1275 | kfree(data->lm75[0]); | ||
1276 | } | ||
1244 | ERROR3: | 1277 | ERROR3: |
1245 | i2c_detach_client(new_client); | 1278 | i2c_detach_client(new_client); |
1246 | ERROR2: | 1279 | ERROR2: |
@@ -1255,24 +1288,26 @@ ERROR0: | |||
1255 | static int | 1288 | static int |
1256 | w83781d_detach_client(struct i2c_client *client) | 1289 | w83781d_detach_client(struct i2c_client *client) |
1257 | { | 1290 | { |
1291 | struct w83781d_data *data = i2c_get_clientdata(client); | ||
1258 | int err; | 1292 | int err; |
1259 | 1293 | ||
1294 | /* main client */ | ||
1295 | if (data) | ||
1296 | hwmon_device_unregister(data->class_dev); | ||
1297 | |||
1260 | if (i2c_is_isa_client(client)) | 1298 | if (i2c_is_isa_client(client)) |
1261 | release_region(client->addr, W83781D_EXTENT); | 1299 | release_region(client->addr, W83781D_EXTENT); |
1262 | 1300 | ||
1263 | if ((err = i2c_detach_client(client))) { | 1301 | if ((err = i2c_detach_client(client))) |
1264 | dev_err(&client->dev, | ||
1265 | "Client deregistration failed, client not detached.\n"); | ||
1266 | return err; | 1302 | return err; |
1267 | } | ||
1268 | 1303 | ||
1269 | if (i2c_get_clientdata(client)==NULL) { | 1304 | /* main client */ |
1270 | /* subclients */ | 1305 | if (data) |
1306 | kfree(data); | ||
1307 | |||
1308 | /* subclient */ | ||
1309 | else | ||
1271 | kfree(client); | 1310 | kfree(client); |
1272 | } else { | ||
1273 | /* main client */ | ||
1274 | kfree(i2c_get_clientdata(client)); | ||
1275 | } | ||
1276 | 1311 | ||
1277 | return 0; | 1312 | return 0; |
1278 | } | 1313 | } |
@@ -1443,7 +1478,7 @@ w83781d_init_client(struct i2c_client *client) | |||
1443 | w83781d_write_value(client, W83781D_REG_BEEP_INTS2, 0); | 1478 | w83781d_write_value(client, W83781D_REG_BEEP_INTS2, 0); |
1444 | } | 1479 | } |
1445 | 1480 | ||
1446 | data->vrm = i2c_which_vrm(); | 1481 | data->vrm = vid_which_vrm(); |
1447 | 1482 | ||
1448 | if ((type != w83781d) && (type != as99127f)) { | 1483 | if ((type != w83781d) && (type != as99127f)) { |
1449 | tmp = w83781d_read_value(client, W83781D_REG_SCFG1); | 1484 | tmp = w83781d_read_value(client, W83781D_REG_SCFG1); |
@@ -1613,12 +1648,25 @@ static struct w83781d_data *w83781d_update_device(struct device *dev) | |||
1613 | static int __init | 1648 | static int __init |
1614 | sensors_w83781d_init(void) | 1649 | sensors_w83781d_init(void) |
1615 | { | 1650 | { |
1616 | return i2c_add_driver(&w83781d_driver); | 1651 | int res; |
1652 | |||
1653 | res = i2c_add_driver(&w83781d_driver); | ||
1654 | if (res) | ||
1655 | return res; | ||
1656 | |||
1657 | res = i2c_isa_add_driver(&w83781d_isa_driver); | ||
1658 | if (res) { | ||
1659 | i2c_del_driver(&w83781d_driver); | ||
1660 | return res; | ||
1661 | } | ||
1662 | |||
1663 | return 0; | ||
1617 | } | 1664 | } |
1618 | 1665 | ||
1619 | static void __exit | 1666 | static void __exit |
1620 | sensors_w83781d_exit(void) | 1667 | sensors_w83781d_exit(void) |
1621 | { | 1668 | { |
1669 | i2c_isa_del_driver(&w83781d_isa_driver); | ||
1622 | i2c_del_driver(&w83781d_driver); | 1670 | i2c_del_driver(&w83781d_driver); |
1623 | } | 1671 | } |
1624 | 1672 | ||
diff --git a/drivers/hwmon/w83792d.c b/drivers/hwmon/w83792d.c new file mode 100644 index 000000000000..ba0c28015f6a --- /dev/null +++ b/drivers/hwmon/w83792d.c | |||
@@ -0,0 +1,1649 @@ | |||
1 | /* | ||
2 | w83792d.c - Part of lm_sensors, Linux kernel modules for hardware | ||
3 | monitoring | ||
4 | Copyright (C) 2004, 2005 Winbond Electronics Corp. | ||
5 | Chunhao Huang <DZShen@Winbond.com.tw>, | ||
6 | Rudolf Marek <r.marek@sh.cvut.cz> | ||
7 | |||
8 | This program is free software; you can redistribute it and/or modify | ||
9 | it under the terms of the GNU General Public License as published by | ||
10 | the Free Software Foundation; either version 2 of the License, or | ||
11 | (at your option) any later version. | ||
12 | |||
13 | This program is distributed in the hope that it will be useful, | ||
14 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
16 | GNU General Public License for more details. | ||
17 | |||
18 | You should have received a copy of the GNU General Public License | ||
19 | along with this program; if not, write to the Free Software | ||
20 | Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
21 | |||
22 | Note: | ||
23 | 1. This driver is only for 2.6 kernel, 2.4 kernel need a different driver. | ||
24 | 2. This driver is only for Winbond W83792D C version device, there | ||
25 | are also some motherboards with B version W83792D device. The | ||
26 | calculation method to in6-in7(measured value, limits) is a little | ||
27 | different between C and B version. C or B version can be identified | ||
28 | by CR[0x49h]. | ||
29 | */ | ||
30 | |||
31 | /* | ||
32 | Supports following chips: | ||
33 | |||
34 | Chip #vin #fanin #pwm #temp wchipid vendid i2c ISA | ||
35 | w83792d 9 7 7 3 0x7a 0x5ca3 yes no | ||
36 | */ | ||
37 | |||
38 | #include <linux/config.h> | ||
39 | #include <linux/module.h> | ||
40 | #include <linux/init.h> | ||
41 | #include <linux/slab.h> | ||
42 | #include <linux/i2c.h> | ||
43 | #include <linux/hwmon.h> | ||
44 | #include <linux/hwmon-sysfs.h> | ||
45 | #include <linux/err.h> | ||
46 | |||
47 | /* Addresses to scan */ | ||
48 | static unsigned short normal_i2c[] = { 0x2c, 0x2d, 0x2e, 0x2f, I2C_CLIENT_END }; | ||
49 | |||
50 | /* Insmod parameters */ | ||
51 | I2C_CLIENT_INSMOD_1(w83792d); | ||
52 | I2C_CLIENT_MODULE_PARM(force_subclients, "List of subclient addresses: " | ||
53 | "{bus, clientaddr, subclientaddr1, subclientaddr2}"); | ||
54 | |||
55 | static int init; | ||
56 | module_param(init, bool, 0); | ||
57 | MODULE_PARM_DESC(init, "Set to one to force chip initialization"); | ||
58 | |||
59 | /* The W83792D registers */ | ||
60 | static const u8 W83792D_REG_IN[9] = { | ||
61 | 0x20, /* Vcore A in DataSheet */ | ||
62 | 0x21, /* Vcore B in DataSheet */ | ||
63 | 0x22, /* VIN0 in DataSheet */ | ||
64 | 0x23, /* VIN1 in DataSheet */ | ||
65 | 0x24, /* VIN2 in DataSheet */ | ||
66 | 0x25, /* VIN3 in DataSheet */ | ||
67 | 0x26, /* 5VCC in DataSheet */ | ||
68 | 0xB0, /* 5VSB in DataSheet */ | ||
69 | 0xB1 /* VBAT in DataSheet */ | ||
70 | }; | ||
71 | #define W83792D_REG_LOW_BITS1 0x3E /* Low Bits I in DataSheet */ | ||
72 | #define W83792D_REG_LOW_BITS2 0x3F /* Low Bits II in DataSheet */ | ||
73 | static const u8 W83792D_REG_IN_MAX[9] = { | ||
74 | 0x2B, /* Vcore A High Limit in DataSheet */ | ||
75 | 0x2D, /* Vcore B High Limit in DataSheet */ | ||
76 | 0x2F, /* VIN0 High Limit in DataSheet */ | ||
77 | 0x31, /* VIN1 High Limit in DataSheet */ | ||
78 | 0x33, /* VIN2 High Limit in DataSheet */ | ||
79 | 0x35, /* VIN3 High Limit in DataSheet */ | ||
80 | 0x37, /* 5VCC High Limit in DataSheet */ | ||
81 | 0xB4, /* 5VSB High Limit in DataSheet */ | ||
82 | 0xB6 /* VBAT High Limit in DataSheet */ | ||
83 | }; | ||
84 | static const u8 W83792D_REG_IN_MIN[9] = { | ||
85 | 0x2C, /* Vcore A Low Limit in DataSheet */ | ||
86 | 0x2E, /* Vcore B Low Limit in DataSheet */ | ||
87 | 0x30, /* VIN0 Low Limit in DataSheet */ | ||
88 | 0x32, /* VIN1 Low Limit in DataSheet */ | ||
89 | 0x34, /* VIN2 Low Limit in DataSheet */ | ||
90 | 0x36, /* VIN3 Low Limit in DataSheet */ | ||
91 | 0x38, /* 5VCC Low Limit in DataSheet */ | ||
92 | 0xB5, /* 5VSB Low Limit in DataSheet */ | ||
93 | 0xB7 /* VBAT Low Limit in DataSheet */ | ||
94 | }; | ||
95 | static const u8 W83792D_REG_FAN[7] = { | ||
96 | 0x28, /* FAN 1 Count in DataSheet */ | ||
97 | 0x29, /* FAN 2 Count in DataSheet */ | ||
98 | 0x2A, /* FAN 3 Count in DataSheet */ | ||
99 | 0xB8, /* FAN 4 Count in DataSheet */ | ||
100 | 0xB9, /* FAN 5 Count in DataSheet */ | ||
101 | 0xBA, /* FAN 6 Count in DataSheet */ | ||
102 | 0xBE /* FAN 7 Count in DataSheet */ | ||
103 | }; | ||
104 | static const u8 W83792D_REG_FAN_MIN[7] = { | ||
105 | 0x3B, /* FAN 1 Count Low Limit in DataSheet */ | ||
106 | 0x3C, /* FAN 2 Count Low Limit in DataSheet */ | ||
107 | 0x3D, /* FAN 3 Count Low Limit in DataSheet */ | ||
108 | 0xBB, /* FAN 4 Count Low Limit in DataSheet */ | ||
109 | 0xBC, /* FAN 5 Count Low Limit in DataSheet */ | ||
110 | 0xBD, /* FAN 6 Count Low Limit in DataSheet */ | ||
111 | 0xBF /* FAN 7 Count Low Limit in DataSheet */ | ||
112 | }; | ||
113 | #define W83792D_REG_FAN_CFG 0x84 /* FAN Configuration in DataSheet */ | ||
114 | static const u8 W83792D_REG_FAN_DIV[4] = { | ||
115 | 0x47, /* contains FAN2 and FAN1 Divisor */ | ||
116 | 0x5B, /* contains FAN4 and FAN3 Divisor */ | ||
117 | 0x5C, /* contains FAN6 and FAN5 Divisor */ | ||
118 | 0x9E /* contains FAN7 Divisor. */ | ||
119 | }; | ||
120 | static const u8 W83792D_REG_PWM[7] = { | ||
121 | 0x81, /* FAN 1 Duty Cycle, be used to control */ | ||
122 | 0x83, /* FAN 2 Duty Cycle, be used to control */ | ||
123 | 0x94, /* FAN 3 Duty Cycle, be used to control */ | ||
124 | 0xA3, /* FAN 4 Duty Cycle, be used to control */ | ||
125 | 0xA4, /* FAN 5 Duty Cycle, be used to control */ | ||
126 | 0xA5, /* FAN 6 Duty Cycle, be used to control */ | ||
127 | 0xA6 /* FAN 7 Duty Cycle, be used to control */ | ||
128 | }; | ||
129 | #define W83792D_REG_BANK 0x4E | ||
130 | #define W83792D_REG_TEMP2_CONFIG 0xC2 | ||
131 | #define W83792D_REG_TEMP3_CONFIG 0xCA | ||
132 | |||
133 | static const u8 W83792D_REG_TEMP1[3] = { | ||
134 | 0x27, /* TEMP 1 in DataSheet */ | ||
135 | 0x39, /* TEMP 1 Over in DataSheet */ | ||
136 | 0x3A, /* TEMP 1 Hyst in DataSheet */ | ||
137 | }; | ||
138 | |||
139 | static const u8 W83792D_REG_TEMP_ADD[2][6] = { | ||
140 | { 0xC0, /* TEMP 2 in DataSheet */ | ||
141 | 0xC1, /* TEMP 2(0.5 deg) in DataSheet */ | ||
142 | 0xC5, /* TEMP 2 Over High part in DataSheet */ | ||
143 | 0xC6, /* TEMP 2 Over Low part in DataSheet */ | ||
144 | 0xC3, /* TEMP 2 Thyst High part in DataSheet */ | ||
145 | 0xC4 }, /* TEMP 2 Thyst Low part in DataSheet */ | ||
146 | { 0xC8, /* TEMP 3 in DataSheet */ | ||
147 | 0xC9, /* TEMP 3(0.5 deg) in DataSheet */ | ||
148 | 0xCD, /* TEMP 3 Over High part in DataSheet */ | ||
149 | 0xCE, /* TEMP 3 Over Low part in DataSheet */ | ||
150 | 0xCB, /* TEMP 3 Thyst High part in DataSheet */ | ||
151 | 0xCC } /* TEMP 3 Thyst Low part in DataSheet */ | ||
152 | }; | ||
153 | |||
154 | static const u8 W83792D_REG_THERMAL[3] = { | ||
155 | 0x85, /* SmartFanI: Fan1 target value */ | ||
156 | 0x86, /* SmartFanI: Fan2 target value */ | ||
157 | 0x96 /* SmartFanI: Fan3 target value */ | ||
158 | }; | ||
159 | |||
160 | static const u8 W83792D_REG_TOLERANCE[3] = { | ||
161 | 0x87, /* (bit3-0)SmartFan Fan1 tolerance */ | ||
162 | 0x87, /* (bit7-4)SmartFan Fan2 tolerance */ | ||
163 | 0x97 /* (bit3-0)SmartFan Fan3 tolerance */ | ||
164 | }; | ||
165 | |||
166 | static const u8 W83792D_REG_POINTS[3][4] = { | ||
167 | { 0x85, /* SmartFanII: Fan1 temp point 1 */ | ||
168 | 0xE3, /* SmartFanII: Fan1 temp point 2 */ | ||
169 | 0xE4, /* SmartFanII: Fan1 temp point 3 */ | ||
170 | 0xE5 }, /* SmartFanII: Fan1 temp point 4 */ | ||
171 | { 0x86, /* SmartFanII: Fan2 temp point 1 */ | ||
172 | 0xE6, /* SmartFanII: Fan2 temp point 2 */ | ||
173 | 0xE7, /* SmartFanII: Fan2 temp point 3 */ | ||
174 | 0xE8 }, /* SmartFanII: Fan2 temp point 4 */ | ||
175 | { 0x96, /* SmartFanII: Fan3 temp point 1 */ | ||
176 | 0xE9, /* SmartFanII: Fan3 temp point 2 */ | ||
177 | 0xEA, /* SmartFanII: Fan3 temp point 3 */ | ||
178 | 0xEB } /* SmartFanII: Fan3 temp point 4 */ | ||
179 | }; | ||
180 | |||
181 | static const u8 W83792D_REG_LEVELS[3][4] = { | ||
182 | { 0x88, /* (bit3-0) SmartFanII: Fan1 Non-Stop */ | ||
183 | 0x88, /* (bit7-4) SmartFanII: Fan1 Level 1 */ | ||
184 | 0xE0, /* (bit7-4) SmartFanII: Fan1 Level 2 */ | ||
185 | 0xE0 }, /* (bit3-0) SmartFanII: Fan1 Level 3 */ | ||
186 | { 0x89, /* (bit3-0) SmartFanII: Fan2 Non-Stop */ | ||
187 | 0x89, /* (bit7-4) SmartFanII: Fan2 Level 1 */ | ||
188 | 0xE1, /* (bit7-4) SmartFanII: Fan2 Level 2 */ | ||
189 | 0xE1 }, /* (bit3-0) SmartFanII: Fan2 Level 3 */ | ||
190 | { 0x98, /* (bit3-0) SmartFanII: Fan3 Non-Stop */ | ||
191 | 0x98, /* (bit7-4) SmartFanII: Fan3 Level 1 */ | ||
192 | 0xE2, /* (bit7-4) SmartFanII: Fan3 Level 2 */ | ||
193 | 0xE2 } /* (bit3-0) SmartFanII: Fan3 Level 3 */ | ||
194 | }; | ||
195 | |||
196 | #define W83792D_REG_CONFIG 0x40 | ||
197 | #define W83792D_REG_VID_FANDIV 0x47 | ||
198 | #define W83792D_REG_CHIPID 0x49 | ||
199 | #define W83792D_REG_WCHIPID 0x58 | ||
200 | #define W83792D_REG_CHIPMAN 0x4F | ||
201 | #define W83792D_REG_PIN 0x4B | ||
202 | #define W83792D_REG_I2C_SUBADDR 0x4A | ||
203 | |||
204 | #define W83792D_REG_ALARM1 0xA9 /* realtime status register1 */ | ||
205 | #define W83792D_REG_ALARM2 0xAA /* realtime status register2 */ | ||
206 | #define W83792D_REG_ALARM3 0xAB /* realtime status register3 */ | ||
207 | #define W83792D_REG_CHASSIS 0x42 /* Bit 5: Case Open status bit */ | ||
208 | #define W83792D_REG_CHASSIS_CLR 0x44 /* Bit 7: Case Open CLR_CHS/Reset bit */ | ||
209 | |||
210 | /* control in0/in1 's limit modifiability */ | ||
211 | #define W83792D_REG_VID_IN_B 0x17 | ||
212 | |||
213 | #define W83792D_REG_VBAT 0x5D | ||
214 | #define W83792D_REG_I2C_ADDR 0x48 | ||
215 | |||
216 | /* Conversions. Rounding and limit checking is only done on the TO_REG | ||
217 | variants. Note that you should be a bit careful with which arguments | ||
218 | these macros are called: arguments may be evaluated more than once. | ||
219 | Fixing this is just not worth it. */ | ||
220 | #define IN_FROM_REG(nr,val) (((nr)<=1)?(val*2): \ | ||
221 | ((((nr)==6)||((nr)==7))?(val*6):(val*4))) | ||
222 | #define IN_TO_REG(nr,val) (((nr)<=1)?(val/2): \ | ||
223 | ((((nr)==6)||((nr)==7))?(val/6):(val/4))) | ||
224 | |||
225 | static inline u8 | ||
226 | FAN_TO_REG(long rpm, int div) | ||
227 | { | ||
228 | if (rpm == 0) | ||
229 | return 255; | ||
230 | rpm = SENSORS_LIMIT(rpm, 1, 1000000); | ||
231 | return SENSORS_LIMIT((1350000 + rpm * div / 2) / (rpm * div), 1, 254); | ||
232 | } | ||
233 | |||
234 | #define FAN_FROM_REG(val,div) ((val) == 0 ? -1 : \ | ||
235 | ((val) == 255 ? 0 : \ | ||
236 | 1350000 / ((val) * (div)))) | ||
237 | |||
238 | /* for temp1 */ | ||
239 | #define TEMP1_TO_REG(val) (SENSORS_LIMIT(((val) < 0 ? (val)+0x100*1000 \ | ||
240 | : (val)) / 1000, 0, 0xff)) | ||
241 | #define TEMP1_FROM_REG(val) (((val) & 0x80 ? (val)-0x100 : (val)) * 1000) | ||
242 | /* for temp2 and temp3, because they need addtional resolution */ | ||
243 | #define TEMP_ADD_FROM_REG(val1, val2) \ | ||
244 | ((((val1) & 0x80 ? (val1)-0x100 \ | ||
245 | : (val1)) * 1000) + ((val2 & 0x80) ? 500 : 0)) | ||
246 | #define TEMP_ADD_TO_REG_HIGH(val) \ | ||
247 | (SENSORS_LIMIT(((val) < 0 ? (val)+0x100*1000 \ | ||
248 | : (val)) / 1000, 0, 0xff)) | ||
249 | #define TEMP_ADD_TO_REG_LOW(val) ((val%1000) ? 0x80 : 0x00) | ||
250 | |||
251 | #define PWM_FROM_REG(val) (val) | ||
252 | #define PWM_TO_REG(val) (SENSORS_LIMIT((val),0,255)) | ||
253 | #define DIV_FROM_REG(val) (1 << (val)) | ||
254 | |||
255 | static inline u8 | ||
256 | DIV_TO_REG(long val) | ||
257 | { | ||
258 | int i; | ||
259 | val = SENSORS_LIMIT(val, 1, 128) >> 1; | ||
260 | for (i = 0; i < 6; i++) { | ||
261 | if (val == 0) | ||
262 | break; | ||
263 | val >>= 1; | ||
264 | } | ||
265 | return ((u8) i); | ||
266 | } | ||
267 | |||
268 | struct w83792d_data { | ||
269 | struct i2c_client client; | ||
270 | struct class_device *class_dev; | ||
271 | struct semaphore lock; | ||
272 | enum chips type; | ||
273 | |||
274 | struct semaphore update_lock; | ||
275 | char valid; /* !=0 if following fields are valid */ | ||
276 | unsigned long last_updated; /* In jiffies */ | ||
277 | |||
278 | /* array of 2 pointers to subclients */ | ||
279 | struct i2c_client *lm75[2]; | ||
280 | |||
281 | u8 in[9]; /* Register value */ | ||
282 | u8 in_max[9]; /* Register value */ | ||
283 | u8 in_min[9]; /* Register value */ | ||
284 | u8 low_bits[2]; /* Additional resolution to voltage in0-6 */ | ||
285 | u8 fan[7]; /* Register value */ | ||
286 | u8 fan_min[7]; /* Register value */ | ||
287 | u8 temp1[3]; /* current, over, thyst */ | ||
288 | u8 temp_add[2][6]; /* Register value */ | ||
289 | u8 fan_div[7]; /* Register encoding, shifted right */ | ||
290 | u8 pwm[7]; /* We only consider the first 3 set of pwm, | ||
291 | although 792 chip has 7 set of pwm. */ | ||
292 | u8 pwmenable[3]; | ||
293 | u8 pwm_mode[7]; /* indicates PWM or DC mode: 1->PWM; 0->DC */ | ||
294 | u32 alarms; /* realtime status register encoding,combined */ | ||
295 | u8 chassis; /* Chassis status */ | ||
296 | u8 chassis_clear; /* CLR_CHS, clear chassis intrusion detection */ | ||
297 | u8 thermal_cruise[3]; /* Smart FanI: Fan1,2,3 target value */ | ||
298 | u8 tolerance[3]; /* Fan1,2,3 tolerance(Smart Fan I/II) */ | ||
299 | u8 sf2_points[3][4]; /* Smart FanII: Fan1,2,3 temperature points */ | ||
300 | u8 sf2_levels[3][4]; /* Smart FanII: Fan1,2,3 duty cycle levels */ | ||
301 | }; | ||
302 | |||
303 | static int w83792d_attach_adapter(struct i2c_adapter *adapter); | ||
304 | static int w83792d_detect(struct i2c_adapter *adapter, int address, int kind); | ||
305 | static int w83792d_detach_client(struct i2c_client *client); | ||
306 | |||
307 | static int w83792d_read_value(struct i2c_client *client, u8 register); | ||
308 | static int w83792d_write_value(struct i2c_client *client, u8 register, | ||
309 | u8 value); | ||
310 | static struct w83792d_data *w83792d_update_device(struct device *dev); | ||
311 | |||
312 | #ifdef DEBUG | ||
313 | static void w83792d_print_debug(struct w83792d_data *data, struct device *dev); | ||
314 | #endif | ||
315 | |||
316 | static void w83792d_init_client(struct i2c_client *client); | ||
317 | |||
318 | static struct i2c_driver w83792d_driver = { | ||
319 | .owner = THIS_MODULE, | ||
320 | .name = "w83792d", | ||
321 | .flags = I2C_DF_NOTIFY, | ||
322 | .attach_adapter = w83792d_attach_adapter, | ||
323 | .detach_client = w83792d_detach_client, | ||
324 | }; | ||
325 | |||
326 | static long in_count_from_reg(int nr, struct w83792d_data *data) | ||
327 | { | ||
328 | u16 vol_count = data->in[nr]; | ||
329 | u16 low_bits = 0; | ||
330 | vol_count = (vol_count << 2); | ||
331 | switch (nr) | ||
332 | { | ||
333 | case 0: /* vin0 */ | ||
334 | low_bits = (data->low_bits[0]) & 0x03; | ||
335 | break; | ||
336 | case 1: /* vin1 */ | ||
337 | low_bits = ((data->low_bits[0]) & 0x0c) >> 2; | ||
338 | break; | ||
339 | case 2: /* vin2 */ | ||
340 | low_bits = ((data->low_bits[0]) & 0x30) >> 4; | ||
341 | break; | ||
342 | case 3: /* vin3 */ | ||
343 | low_bits = ((data->low_bits[0]) & 0xc0) >> 6; | ||
344 | break; | ||
345 | case 4: /* vin4 */ | ||
346 | low_bits = (data->low_bits[1]) & 0x03; | ||
347 | break; | ||
348 | case 5: /* vin5 */ | ||
349 | low_bits = ((data->low_bits[1]) & 0x0c) >> 2; | ||
350 | break; | ||
351 | case 6: /* vin6 */ | ||
352 | low_bits = ((data->low_bits[1]) & 0x30) >> 4; | ||
353 | default: | ||
354 | break; | ||
355 | } | ||
356 | vol_count = vol_count | low_bits; | ||
357 | return vol_count; | ||
358 | } | ||
359 | |||
360 | /* following are the sysfs callback functions */ | ||
361 | static ssize_t show_in(struct device *dev, struct device_attribute *attr, | ||
362 | char *buf) | ||
363 | { | ||
364 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
365 | int nr = sensor_attr->index; | ||
366 | struct w83792d_data *data = w83792d_update_device(dev); | ||
367 | return sprintf(buf,"%ld\n", IN_FROM_REG(nr,(in_count_from_reg(nr, data)))); | ||
368 | } | ||
369 | |||
370 | #define show_in_reg(reg) \ | ||
371 | static ssize_t show_##reg(struct device *dev, struct device_attribute *attr, \ | ||
372 | char *buf) \ | ||
373 | { \ | ||
374 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); \ | ||
375 | int nr = sensor_attr->index; \ | ||
376 | struct w83792d_data *data = w83792d_update_device(dev); \ | ||
377 | return sprintf(buf,"%ld\n", (long)(IN_FROM_REG(nr, (data->reg[nr])*4))); \ | ||
378 | } | ||
379 | |||
380 | show_in_reg(in_min); | ||
381 | show_in_reg(in_max); | ||
382 | |||
383 | #define store_in_reg(REG, reg) \ | ||
384 | static ssize_t store_in_##reg (struct device *dev, \ | ||
385 | struct device_attribute *attr, \ | ||
386 | const char *buf, size_t count) \ | ||
387 | { \ | ||
388 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); \ | ||
389 | int nr = sensor_attr->index; \ | ||
390 | struct i2c_client *client = to_i2c_client(dev); \ | ||
391 | struct w83792d_data *data = i2c_get_clientdata(client); \ | ||
392 | u32 val; \ | ||
393 | \ | ||
394 | val = simple_strtoul(buf, NULL, 10); \ | ||
395 | data->in_##reg[nr] = SENSORS_LIMIT(IN_TO_REG(nr, val)/4, 0, 255); \ | ||
396 | w83792d_write_value(client, W83792D_REG_IN_##REG[nr], data->in_##reg[nr]); \ | ||
397 | \ | ||
398 | return count; \ | ||
399 | } | ||
400 | store_in_reg(MIN, min); | ||
401 | store_in_reg(MAX, max); | ||
402 | |||
403 | #define sysfs_in_reg(offset) \ | ||
404 | static SENSOR_DEVICE_ATTR(in##offset##_input, S_IRUGO, show_in, \ | ||
405 | NULL, offset); \ | ||
406 | static SENSOR_DEVICE_ATTR(in##offset##_min, S_IRUGO | S_IWUSR, \ | ||
407 | show_in_min, store_in_min, offset); \ | ||
408 | static SENSOR_DEVICE_ATTR(in##offset##_max, S_IRUGO | S_IWUSR, \ | ||
409 | show_in_max, store_in_max, offset); | ||
410 | |||
411 | sysfs_in_reg(0); | ||
412 | sysfs_in_reg(1); | ||
413 | sysfs_in_reg(2); | ||
414 | sysfs_in_reg(3); | ||
415 | sysfs_in_reg(4); | ||
416 | sysfs_in_reg(5); | ||
417 | sysfs_in_reg(6); | ||
418 | sysfs_in_reg(7); | ||
419 | sysfs_in_reg(8); | ||
420 | |||
421 | #define device_create_file_in(client, offset) \ | ||
422 | do { \ | ||
423 | device_create_file(&client->dev, &sensor_dev_attr_in##offset##_input.dev_attr); \ | ||
424 | device_create_file(&client->dev, &sensor_dev_attr_in##offset##_max.dev_attr); \ | ||
425 | device_create_file(&client->dev, &sensor_dev_attr_in##offset##_min.dev_attr); \ | ||
426 | } while (0) | ||
427 | |||
428 | #define show_fan_reg(reg) \ | ||
429 | static ssize_t show_##reg (struct device *dev, struct device_attribute *attr, \ | ||
430 | char *buf) \ | ||
431 | { \ | ||
432 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); \ | ||
433 | int nr = sensor_attr->index - 1; \ | ||
434 | struct w83792d_data *data = w83792d_update_device(dev); \ | ||
435 | return sprintf(buf,"%d\n", \ | ||
436 | FAN_FROM_REG(data->reg[nr], DIV_FROM_REG(data->fan_div[nr]))); \ | ||
437 | } | ||
438 | |||
439 | show_fan_reg(fan); | ||
440 | show_fan_reg(fan_min); | ||
441 | |||
442 | static ssize_t | ||
443 | store_fan_min(struct device *dev, struct device_attribute *attr, | ||
444 | const char *buf, size_t count) | ||
445 | { | ||
446 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
447 | int nr = sensor_attr->index - 1; | ||
448 | struct i2c_client *client = to_i2c_client(dev); | ||
449 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
450 | u32 val; | ||
451 | |||
452 | val = simple_strtoul(buf, NULL, 10); | ||
453 | data->fan_min[nr] = FAN_TO_REG(val, DIV_FROM_REG(data->fan_div[nr])); | ||
454 | w83792d_write_value(client, W83792D_REG_FAN_MIN[nr], | ||
455 | data->fan_min[nr]); | ||
456 | |||
457 | return count; | ||
458 | } | ||
459 | |||
460 | static ssize_t | ||
461 | show_fan_div(struct device *dev, struct device_attribute *attr, | ||
462 | char *buf) | ||
463 | { | ||
464 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
465 | int nr = sensor_attr->index; | ||
466 | struct w83792d_data *data = w83792d_update_device(dev); | ||
467 | return sprintf(buf, "%u\n", DIV_FROM_REG(data->fan_div[nr - 1])); | ||
468 | } | ||
469 | |||
470 | /* Note: we save and restore the fan minimum here, because its value is | ||
471 | determined in part by the fan divisor. This follows the principle of | ||
472 | least suprise; the user doesn't expect the fan minimum to change just | ||
473 | because the divisor changed. */ | ||
474 | static ssize_t | ||
475 | store_fan_div(struct device *dev, struct device_attribute *attr, | ||
476 | const char *buf, size_t count) | ||
477 | { | ||
478 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
479 | int nr = sensor_attr->index - 1; | ||
480 | struct i2c_client *client = to_i2c_client(dev); | ||
481 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
482 | unsigned long min; | ||
483 | /*u8 reg;*/ | ||
484 | u8 fan_div_reg = 0; | ||
485 | u8 tmp_fan_div; | ||
486 | |||
487 | /* Save fan_min */ | ||
488 | min = FAN_FROM_REG(data->fan_min[nr], | ||
489 | DIV_FROM_REG(data->fan_div[nr])); | ||
490 | |||
491 | data->fan_div[nr] = DIV_TO_REG(simple_strtoul(buf, NULL, 10)); | ||
492 | |||
493 | fan_div_reg = w83792d_read_value(client, W83792D_REG_FAN_DIV[nr >> 1]); | ||
494 | fan_div_reg &= (nr & 0x01) ? 0x8f : 0xf8; | ||
495 | tmp_fan_div = (nr & 0x01) ? (((data->fan_div[nr]) << 4) & 0x70) | ||
496 | : ((data->fan_div[nr]) & 0x07); | ||
497 | w83792d_write_value(client, W83792D_REG_FAN_DIV[nr >> 1], | ||
498 | fan_div_reg | tmp_fan_div); | ||
499 | |||
500 | /* Restore fan_min */ | ||
501 | data->fan_min[nr] = FAN_TO_REG(min, DIV_FROM_REG(data->fan_div[nr])); | ||
502 | w83792d_write_value(client, W83792D_REG_FAN_MIN[nr], data->fan_min[nr]); | ||
503 | |||
504 | return count; | ||
505 | } | ||
506 | |||
507 | #define sysfs_fan(offset) \ | ||
508 | static SENSOR_DEVICE_ATTR(fan##offset##_input, S_IRUGO, show_fan, NULL, \ | ||
509 | offset); \ | ||
510 | static SENSOR_DEVICE_ATTR(fan##offset##_div, S_IRUGO | S_IWUSR, \ | ||
511 | show_fan_div, store_fan_div, offset); \ | ||
512 | static SENSOR_DEVICE_ATTR(fan##offset##_min, S_IRUGO | S_IWUSR, \ | ||
513 | show_fan_min, store_fan_min, offset); | ||
514 | |||
515 | sysfs_fan(1); | ||
516 | sysfs_fan(2); | ||
517 | sysfs_fan(3); | ||
518 | sysfs_fan(4); | ||
519 | sysfs_fan(5); | ||
520 | sysfs_fan(6); | ||
521 | sysfs_fan(7); | ||
522 | |||
523 | #define device_create_file_fan(client, offset) \ | ||
524 | do { \ | ||
525 | device_create_file(&client->dev, &sensor_dev_attr_fan##offset##_input.dev_attr); \ | ||
526 | device_create_file(&client->dev, &sensor_dev_attr_fan##offset##_div.dev_attr); \ | ||
527 | device_create_file(&client->dev, &sensor_dev_attr_fan##offset##_min.dev_attr); \ | ||
528 | } while (0) | ||
529 | |||
530 | |||
531 | /* read/write the temperature1, includes measured value and limits */ | ||
532 | |||
533 | static ssize_t show_temp1(struct device *dev, struct device_attribute *attr, | ||
534 | char *buf) | ||
535 | { | ||
536 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
537 | int nr = sensor_attr->index; | ||
538 | struct w83792d_data *data = w83792d_update_device(dev); | ||
539 | return sprintf(buf, "%d\n", TEMP1_FROM_REG(data->temp1[nr])); | ||
540 | } | ||
541 | |||
542 | static ssize_t store_temp1(struct device *dev, struct device_attribute *attr, | ||
543 | const char *buf, size_t count) | ||
544 | { | ||
545 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
546 | int nr = sensor_attr->index; | ||
547 | struct i2c_client *client = to_i2c_client(dev); | ||
548 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
549 | s32 val; | ||
550 | |||
551 | val = simple_strtol(buf, NULL, 10); | ||
552 | |||
553 | data->temp1[nr] = TEMP1_TO_REG(val); | ||
554 | w83792d_write_value(client, W83792D_REG_TEMP1[nr], | ||
555 | data->temp1[nr]); | ||
556 | |||
557 | return count; | ||
558 | } | ||
559 | |||
560 | |||
561 | static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, show_temp1, NULL, 0); | ||
562 | static SENSOR_DEVICE_ATTR(temp1_max, S_IRUGO | S_IWUSR, show_temp1, | ||
563 | store_temp1, 1); | ||
564 | static SENSOR_DEVICE_ATTR(temp1_max_hyst, S_IRUGO | S_IWUSR, show_temp1, | ||
565 | store_temp1, 2); | ||
566 | |||
567 | #define device_create_file_temp1(client) \ | ||
568 | do { \ | ||
569 | device_create_file(&client->dev, &sensor_dev_attr_temp1_input.dev_attr); \ | ||
570 | device_create_file(&client->dev, &sensor_dev_attr_temp1_max.dev_attr); \ | ||
571 | device_create_file(&client->dev, &sensor_dev_attr_temp1_max_hyst.dev_attr); \ | ||
572 | } while (0) | ||
573 | |||
574 | |||
575 | /* read/write the temperature2-3, includes measured value and limits */ | ||
576 | |||
577 | static ssize_t show_temp23(struct device *dev, struct device_attribute *attr, | ||
578 | char *buf) | ||
579 | { | ||
580 | struct sensor_device_attribute_2 *sensor_attr = to_sensor_dev_attr_2(attr); | ||
581 | int nr = sensor_attr->nr; | ||
582 | int index = sensor_attr->index; | ||
583 | struct w83792d_data *data = w83792d_update_device(dev); | ||
584 | return sprintf(buf,"%ld\n", | ||
585 | (long)TEMP_ADD_FROM_REG(data->temp_add[nr][index], | ||
586 | data->temp_add[nr][index+1])); | ||
587 | } | ||
588 | |||
589 | static ssize_t store_temp23(struct device *dev, struct device_attribute *attr, | ||
590 | const char *buf, size_t count) | ||
591 | { | ||
592 | struct sensor_device_attribute_2 *sensor_attr = to_sensor_dev_attr_2(attr); | ||
593 | int nr = sensor_attr->nr; | ||
594 | int index = sensor_attr->index; | ||
595 | struct i2c_client *client = to_i2c_client(dev); | ||
596 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
597 | s32 val; | ||
598 | |||
599 | val = simple_strtol(buf, NULL, 10); | ||
600 | |||
601 | data->temp_add[nr][index] = TEMP_ADD_TO_REG_HIGH(val); | ||
602 | data->temp_add[nr][index+1] = TEMP_ADD_TO_REG_LOW(val); | ||
603 | w83792d_write_value(client, W83792D_REG_TEMP_ADD[nr][index], | ||
604 | data->temp_add[nr][index]); | ||
605 | w83792d_write_value(client, W83792D_REG_TEMP_ADD[nr][index+1], | ||
606 | data->temp_add[nr][index+1]); | ||
607 | |||
608 | return count; | ||
609 | } | ||
610 | |||
611 | #define sysfs_temp23(name,idx) \ | ||
612 | static SENSOR_DEVICE_ATTR_2(name##_input, S_IRUGO, show_temp23, NULL, \ | ||
613 | idx, 0); \ | ||
614 | static SENSOR_DEVICE_ATTR_2(name##_max, S_IRUGO | S_IWUSR, \ | ||
615 | show_temp23, store_temp23, idx, 2); \ | ||
616 | static SENSOR_DEVICE_ATTR_2(name##_max_hyst, S_IRUGO | S_IWUSR, \ | ||
617 | show_temp23, store_temp23, idx, 4); | ||
618 | |||
619 | sysfs_temp23(temp2,0) | ||
620 | sysfs_temp23(temp3,1) | ||
621 | |||
622 | #define device_create_file_temp_add(client, offset) \ | ||
623 | do { \ | ||
624 | device_create_file(&client->dev, &sensor_dev_attr_temp##offset##_input.dev_attr); \ | ||
625 | device_create_file(&client->dev, &sensor_dev_attr_temp##offset##_max.dev_attr); \ | ||
626 | device_create_file(&client->dev, \ | ||
627 | &sensor_dev_attr_temp##offset##_max_hyst.dev_attr); \ | ||
628 | } while (0) | ||
629 | |||
630 | |||
631 | /* get reatime status of all sensors items: voltage, temp, fan */ | ||
632 | static ssize_t | ||
633 | show_alarms_reg(struct device *dev, struct device_attribute *attr, char *buf) | ||
634 | { | ||
635 | struct w83792d_data *data = w83792d_update_device(dev); | ||
636 | return sprintf(buf, "%d\n", data->alarms); | ||
637 | } | ||
638 | |||
639 | static | ||
640 | DEVICE_ATTR(alarms, S_IRUGO, show_alarms_reg, NULL); | ||
641 | #define device_create_file_alarms(client) \ | ||
642 | device_create_file(&client->dev, &dev_attr_alarms); | ||
643 | |||
644 | |||
645 | |||
646 | static ssize_t | ||
647 | show_pwm(struct device *dev, struct device_attribute *attr, | ||
648 | char *buf) | ||
649 | { | ||
650 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
651 | int nr = sensor_attr->index; | ||
652 | struct w83792d_data *data = w83792d_update_device(dev); | ||
653 | return sprintf(buf, "%ld\n", (long) PWM_FROM_REG(data->pwm[nr-1])); | ||
654 | } | ||
655 | |||
656 | static ssize_t | ||
657 | show_pwmenable(struct device *dev, struct device_attribute *attr, | ||
658 | char *buf) | ||
659 | { | ||
660 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
661 | int nr = sensor_attr->index - 1; | ||
662 | struct w83792d_data *data = w83792d_update_device(dev); | ||
663 | long pwm_enable_tmp = 1; | ||
664 | |||
665 | switch (data->pwmenable[nr]) { | ||
666 | case 0: | ||
667 | pwm_enable_tmp = 1; /* manual mode */ | ||
668 | break; | ||
669 | case 1: | ||
670 | pwm_enable_tmp = 3; /*thermal cruise/Smart Fan I */ | ||
671 | break; | ||
672 | case 2: | ||
673 | pwm_enable_tmp = 2; /* Smart Fan II */ | ||
674 | break; | ||
675 | } | ||
676 | |||
677 | return sprintf(buf, "%ld\n", pwm_enable_tmp); | ||
678 | } | ||
679 | |||
680 | static ssize_t | ||
681 | store_pwm(struct device *dev, struct device_attribute *attr, | ||
682 | const char *buf, size_t count) | ||
683 | { | ||
684 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
685 | int nr = sensor_attr->index - 1; | ||
686 | struct i2c_client *client = to_i2c_client(dev); | ||
687 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
688 | u32 val; | ||
689 | |||
690 | val = simple_strtoul(buf, NULL, 10); | ||
691 | data->pwm[nr] = PWM_TO_REG(val); | ||
692 | w83792d_write_value(client, W83792D_REG_PWM[nr], data->pwm[nr]); | ||
693 | |||
694 | return count; | ||
695 | } | ||
696 | |||
697 | static ssize_t | ||
698 | store_pwmenable(struct device *dev, struct device_attribute *attr, | ||
699 | const char *buf, size_t count) | ||
700 | { | ||
701 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
702 | int nr = sensor_attr->index - 1; | ||
703 | struct i2c_client *client = to_i2c_client(dev); | ||
704 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
705 | u32 val; | ||
706 | u8 fan_cfg_tmp, cfg1_tmp, cfg2_tmp, cfg3_tmp, cfg4_tmp; | ||
707 | |||
708 | val = simple_strtoul(buf, NULL, 10); | ||
709 | switch (val) { | ||
710 | case 1: | ||
711 | data->pwmenable[nr] = 0; /* manual mode */ | ||
712 | break; | ||
713 | case 2: | ||
714 | data->pwmenable[nr] = 2; /* Smart Fan II */ | ||
715 | break; | ||
716 | case 3: | ||
717 | data->pwmenable[nr] = 1; /* thermal cruise/Smart Fan I */ | ||
718 | break; | ||
719 | default: | ||
720 | return -EINVAL; | ||
721 | } | ||
722 | cfg1_tmp = data->pwmenable[0]; | ||
723 | cfg2_tmp = (data->pwmenable[1]) << 2; | ||
724 | cfg3_tmp = (data->pwmenable[2]) << 4; | ||
725 | cfg4_tmp = w83792d_read_value(client,W83792D_REG_FAN_CFG) & 0xc0; | ||
726 | fan_cfg_tmp = ((cfg4_tmp | cfg3_tmp) | cfg2_tmp) | cfg1_tmp; | ||
727 | w83792d_write_value(client, W83792D_REG_FAN_CFG, fan_cfg_tmp); | ||
728 | |||
729 | return count; | ||
730 | } | ||
731 | |||
732 | #define sysfs_pwm(offset) \ | ||
733 | static SENSOR_DEVICE_ATTR(pwm##offset, S_IRUGO | S_IWUSR, \ | ||
734 | show_pwm, store_pwm, offset); \ | ||
735 | static SENSOR_DEVICE_ATTR(pwm##offset##_enable, S_IRUGO | S_IWUSR, \ | ||
736 | show_pwmenable, store_pwmenable, offset); \ | ||
737 | |||
738 | sysfs_pwm(1); | ||
739 | sysfs_pwm(2); | ||
740 | sysfs_pwm(3); | ||
741 | |||
742 | |||
743 | #define device_create_file_pwm(client, offset) \ | ||
744 | do { \ | ||
745 | device_create_file(&client->dev, &sensor_dev_attr_pwm##offset.dev_attr); \ | ||
746 | } while (0) | ||
747 | |||
748 | #define device_create_file_pwmenable(client, offset) \ | ||
749 | do { \ | ||
750 | device_create_file(&client->dev, &sensor_dev_attr_pwm##offset##_enable.dev_attr); \ | ||
751 | } while (0) | ||
752 | |||
753 | |||
754 | static ssize_t | ||
755 | show_pwm_mode(struct device *dev, struct device_attribute *attr, | ||
756 | char *buf) | ||
757 | { | ||
758 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
759 | int nr = sensor_attr->index; | ||
760 | struct w83792d_data *data = w83792d_update_device(dev); | ||
761 | return sprintf(buf, "%d\n", data->pwm_mode[nr-1]); | ||
762 | } | ||
763 | |||
764 | static ssize_t | ||
765 | store_pwm_mode(struct device *dev, struct device_attribute *attr, | ||
766 | const char *buf, size_t count) | ||
767 | { | ||
768 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
769 | int nr = sensor_attr->index - 1; | ||
770 | struct i2c_client *client = to_i2c_client(dev); | ||
771 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
772 | u32 val; | ||
773 | u8 pwm_mode_mask = 0; | ||
774 | |||
775 | val = simple_strtoul(buf, NULL, 10); | ||
776 | data->pwm_mode[nr] = SENSORS_LIMIT(val, 0, 1); | ||
777 | pwm_mode_mask = w83792d_read_value(client, | ||
778 | W83792D_REG_PWM[nr]) & 0x7f; | ||
779 | w83792d_write_value(client, W83792D_REG_PWM[nr], | ||
780 | ((data->pwm_mode[nr]) << 7) | pwm_mode_mask); | ||
781 | |||
782 | return count; | ||
783 | } | ||
784 | |||
785 | #define sysfs_pwm_mode(offset) \ | ||
786 | static SENSOR_DEVICE_ATTR(pwm##offset##_mode, S_IRUGO | S_IWUSR, \ | ||
787 | show_pwm_mode, store_pwm_mode, offset); | ||
788 | |||
789 | sysfs_pwm_mode(1); | ||
790 | sysfs_pwm_mode(2); | ||
791 | sysfs_pwm_mode(3); | ||
792 | |||
793 | #define device_create_file_pwm_mode(client, offset) \ | ||
794 | do { \ | ||
795 | device_create_file(&client->dev, &sensor_dev_attr_pwm##offset##_mode.dev_attr); \ | ||
796 | } while (0) | ||
797 | |||
798 | |||
799 | static ssize_t | ||
800 | show_regs_chassis(struct device *dev, struct device_attribute *attr, | ||
801 | char *buf) | ||
802 | { | ||
803 | struct w83792d_data *data = w83792d_update_device(dev); | ||
804 | return sprintf(buf, "%d\n", data->chassis); | ||
805 | } | ||
806 | |||
807 | static DEVICE_ATTR(chassis, S_IRUGO, show_regs_chassis, NULL); | ||
808 | |||
809 | #define device_create_file_chassis(client) \ | ||
810 | do { \ | ||
811 | device_create_file(&client->dev, &dev_attr_chassis); \ | ||
812 | } while (0) | ||
813 | |||
814 | |||
815 | static ssize_t | ||
816 | show_chassis_clear(struct device *dev, struct device_attribute *attr, char *buf) | ||
817 | { | ||
818 | struct w83792d_data *data = w83792d_update_device(dev); | ||
819 | return sprintf(buf, "%d\n", data->chassis_clear); | ||
820 | } | ||
821 | |||
822 | static ssize_t | ||
823 | store_chassis_clear(struct device *dev, struct device_attribute *attr, | ||
824 | const char *buf, size_t count) | ||
825 | { | ||
826 | struct i2c_client *client = to_i2c_client(dev); | ||
827 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
828 | u32 val; | ||
829 | u8 temp1 = 0, temp2 = 0; | ||
830 | |||
831 | val = simple_strtoul(buf, NULL, 10); | ||
832 | |||
833 | data->chassis_clear = SENSORS_LIMIT(val, 0 ,1); | ||
834 | temp1 = ((data->chassis_clear) << 7) & 0x80; | ||
835 | temp2 = w83792d_read_value(client, | ||
836 | W83792D_REG_CHASSIS_CLR) & 0x7f; | ||
837 | w83792d_write_value(client, W83792D_REG_CHASSIS_CLR, temp1 | temp2); | ||
838 | |||
839 | return count; | ||
840 | } | ||
841 | |||
842 | static DEVICE_ATTR(chassis_clear, S_IRUGO | S_IWUSR, | ||
843 | show_chassis_clear, store_chassis_clear); | ||
844 | |||
845 | #define device_create_file_chassis_clear(client) \ | ||
846 | do { \ | ||
847 | device_create_file(&client->dev, &dev_attr_chassis_clear); \ | ||
848 | } while (0) | ||
849 | |||
850 | |||
851 | |||
852 | /* For Smart Fan I / Thermal Cruise */ | ||
853 | static ssize_t | ||
854 | show_thermal_cruise(struct device *dev, struct device_attribute *attr, | ||
855 | char *buf) | ||
856 | { | ||
857 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
858 | int nr = sensor_attr->index; | ||
859 | struct w83792d_data *data = w83792d_update_device(dev); | ||
860 | return sprintf(buf, "%ld\n", (long)data->thermal_cruise[nr-1]); | ||
861 | } | ||
862 | |||
863 | static ssize_t | ||
864 | store_thermal_cruise(struct device *dev, struct device_attribute *attr, | ||
865 | const char *buf, size_t count) | ||
866 | { | ||
867 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
868 | int nr = sensor_attr->index - 1; | ||
869 | struct i2c_client *client = to_i2c_client(dev); | ||
870 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
871 | u32 val; | ||
872 | u8 target_tmp=0, target_mask=0; | ||
873 | |||
874 | val = simple_strtoul(buf, NULL, 10); | ||
875 | target_tmp = val; | ||
876 | target_tmp = target_tmp & 0x7f; | ||
877 | target_mask = w83792d_read_value(client, W83792D_REG_THERMAL[nr]) & 0x80; | ||
878 | data->thermal_cruise[nr] = SENSORS_LIMIT(target_tmp, 0, 255); | ||
879 | w83792d_write_value(client, W83792D_REG_THERMAL[nr], | ||
880 | (data->thermal_cruise[nr]) | target_mask); | ||
881 | |||
882 | return count; | ||
883 | } | ||
884 | |||
885 | #define sysfs_thermal_cruise(offset) \ | ||
886 | static SENSOR_DEVICE_ATTR(thermal_cruise##offset, S_IRUGO | S_IWUSR, \ | ||
887 | show_thermal_cruise, store_thermal_cruise, offset); | ||
888 | |||
889 | sysfs_thermal_cruise(1); | ||
890 | sysfs_thermal_cruise(2); | ||
891 | sysfs_thermal_cruise(3); | ||
892 | |||
893 | #define device_create_file_thermal_cruise(client, offset) \ | ||
894 | do { \ | ||
895 | device_create_file(&client->dev, \ | ||
896 | &sensor_dev_attr_thermal_cruise##offset.dev_attr); \ | ||
897 | } while (0) | ||
898 | |||
899 | |||
900 | /* For Smart Fan I/Thermal Cruise and Smart Fan II */ | ||
901 | static ssize_t | ||
902 | show_tolerance(struct device *dev, struct device_attribute *attr, | ||
903 | char *buf) | ||
904 | { | ||
905 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
906 | int nr = sensor_attr->index; | ||
907 | struct w83792d_data *data = w83792d_update_device(dev); | ||
908 | return sprintf(buf, "%ld\n", (long)data->tolerance[nr-1]); | ||
909 | } | ||
910 | |||
911 | static ssize_t | ||
912 | store_tolerance(struct device *dev, struct device_attribute *attr, | ||
913 | const char *buf, size_t count) | ||
914 | { | ||
915 | struct sensor_device_attribute *sensor_attr = to_sensor_dev_attr(attr); | ||
916 | int nr = sensor_attr->index - 1; | ||
917 | struct i2c_client *client = to_i2c_client(dev); | ||
918 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
919 | u32 val; | ||
920 | u8 tol_tmp, tol_mask; | ||
921 | |||
922 | val = simple_strtoul(buf, NULL, 10); | ||
923 | tol_mask = w83792d_read_value(client, | ||
924 | W83792D_REG_TOLERANCE[nr]) & ((nr == 1) ? 0x0f : 0xf0); | ||
925 | tol_tmp = SENSORS_LIMIT(val, 0, 15); | ||
926 | tol_tmp &= 0x0f; | ||
927 | data->tolerance[nr] = tol_tmp; | ||
928 | if (nr == 1) { | ||
929 | tol_tmp <<= 4; | ||
930 | } | ||
931 | w83792d_write_value(client, W83792D_REG_TOLERANCE[nr], | ||
932 | tol_mask | tol_tmp); | ||
933 | |||
934 | return count; | ||
935 | } | ||
936 | |||
937 | #define sysfs_tolerance(offset) \ | ||
938 | static SENSOR_DEVICE_ATTR(tolerance##offset, S_IRUGO | S_IWUSR, \ | ||
939 | show_tolerance, store_tolerance, offset); | ||
940 | |||
941 | sysfs_tolerance(1); | ||
942 | sysfs_tolerance(2); | ||
943 | sysfs_tolerance(3); | ||
944 | |||
945 | #define device_create_file_tolerance(client, offset) \ | ||
946 | do { \ | ||
947 | device_create_file(&client->dev, &sensor_dev_attr_tolerance##offset.dev_attr); \ | ||
948 | } while (0) | ||
949 | |||
950 | |||
951 | /* For Smart Fan II */ | ||
952 | static ssize_t | ||
953 | show_sf2_point(struct device *dev, struct device_attribute *attr, | ||
954 | char *buf) | ||
955 | { | ||
956 | struct sensor_device_attribute_2 *sensor_attr = to_sensor_dev_attr_2(attr); | ||
957 | int nr = sensor_attr->nr; | ||
958 | int index = sensor_attr->index; | ||
959 | struct w83792d_data *data = w83792d_update_device(dev); | ||
960 | return sprintf(buf, "%ld\n", (long)data->sf2_points[index-1][nr-1]); | ||
961 | } | ||
962 | |||
963 | static ssize_t | ||
964 | store_sf2_point(struct device *dev, struct device_attribute *attr, | ||
965 | const char *buf, size_t count) | ||
966 | { | ||
967 | struct sensor_device_attribute_2 *sensor_attr = to_sensor_dev_attr_2(attr); | ||
968 | int nr = sensor_attr->nr - 1; | ||
969 | int index = sensor_attr->index - 1; | ||
970 | struct i2c_client *client = to_i2c_client(dev); | ||
971 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
972 | u32 val; | ||
973 | u8 mask_tmp = 0; | ||
974 | |||
975 | val = simple_strtoul(buf, NULL, 10); | ||
976 | data->sf2_points[index][nr] = SENSORS_LIMIT(val, 0, 127); | ||
977 | mask_tmp = w83792d_read_value(client, | ||
978 | W83792D_REG_POINTS[index][nr]) & 0x80; | ||
979 | w83792d_write_value(client, W83792D_REG_POINTS[index][nr], | ||
980 | mask_tmp|data->sf2_points[index][nr]); | ||
981 | |||
982 | return count; | ||
983 | } | ||
984 | |||
985 | #define sysfs_sf2_point(offset, index) \ | ||
986 | static SENSOR_DEVICE_ATTR_2(sf2_point##offset##_fan##index, S_IRUGO | S_IWUSR, \ | ||
987 | show_sf2_point, store_sf2_point, offset, index); | ||
988 | |||
989 | sysfs_sf2_point(1, 1); /* Fan1 */ | ||
990 | sysfs_sf2_point(2, 1); /* Fan1 */ | ||
991 | sysfs_sf2_point(3, 1); /* Fan1 */ | ||
992 | sysfs_sf2_point(4, 1); /* Fan1 */ | ||
993 | sysfs_sf2_point(1, 2); /* Fan2 */ | ||
994 | sysfs_sf2_point(2, 2); /* Fan2 */ | ||
995 | sysfs_sf2_point(3, 2); /* Fan2 */ | ||
996 | sysfs_sf2_point(4, 2); /* Fan2 */ | ||
997 | sysfs_sf2_point(1, 3); /* Fan3 */ | ||
998 | sysfs_sf2_point(2, 3); /* Fan3 */ | ||
999 | sysfs_sf2_point(3, 3); /* Fan3 */ | ||
1000 | sysfs_sf2_point(4, 3); /* Fan3 */ | ||
1001 | |||
1002 | #define device_create_file_sf2_point(client, offset, index) \ | ||
1003 | do { \ | ||
1004 | device_create_file(&client->dev, \ | ||
1005 | &sensor_dev_attr_sf2_point##offset##_fan##index.dev_attr); \ | ||
1006 | } while (0) | ||
1007 | |||
1008 | |||
1009 | static ssize_t | ||
1010 | show_sf2_level(struct device *dev, struct device_attribute *attr, | ||
1011 | char *buf) | ||
1012 | { | ||
1013 | struct sensor_device_attribute_2 *sensor_attr = to_sensor_dev_attr_2(attr); | ||
1014 | int nr = sensor_attr->nr; | ||
1015 | int index = sensor_attr->index; | ||
1016 | struct w83792d_data *data = w83792d_update_device(dev); | ||
1017 | return sprintf(buf, "%d\n", | ||
1018 | (((data->sf2_levels[index-1][nr]) * 100) / 15)); | ||
1019 | } | ||
1020 | |||
1021 | static ssize_t | ||
1022 | store_sf2_level(struct device *dev, struct device_attribute *attr, | ||
1023 | const char *buf, size_t count) | ||
1024 | { | ||
1025 | struct sensor_device_attribute_2 *sensor_attr = to_sensor_dev_attr_2(attr); | ||
1026 | int nr = sensor_attr->nr; | ||
1027 | int index = sensor_attr->index - 1; | ||
1028 | struct i2c_client *client = to_i2c_client(dev); | ||
1029 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
1030 | u32 val; | ||
1031 | u8 mask_tmp=0, level_tmp=0; | ||
1032 | |||
1033 | val = simple_strtoul(buf, NULL, 10); | ||
1034 | data->sf2_levels[index][nr] = SENSORS_LIMIT((val * 15) / 100, 0, 15); | ||
1035 | mask_tmp = w83792d_read_value(client, W83792D_REG_LEVELS[index][nr]) | ||
1036 | & ((nr==3) ? 0xf0 : 0x0f); | ||
1037 | if (nr==3) { | ||
1038 | level_tmp = data->sf2_levels[index][nr]; | ||
1039 | } else { | ||
1040 | level_tmp = data->sf2_levels[index][nr] << 4; | ||
1041 | } | ||
1042 | w83792d_write_value(client, W83792D_REG_LEVELS[index][nr], level_tmp | mask_tmp); | ||
1043 | |||
1044 | return count; | ||
1045 | } | ||
1046 | |||
1047 | #define sysfs_sf2_level(offset, index) \ | ||
1048 | static SENSOR_DEVICE_ATTR_2(sf2_level##offset##_fan##index, S_IRUGO | S_IWUSR, \ | ||
1049 | show_sf2_level, store_sf2_level, offset, index); | ||
1050 | |||
1051 | sysfs_sf2_level(1, 1); /* Fan1 */ | ||
1052 | sysfs_sf2_level(2, 1); /* Fan1 */ | ||
1053 | sysfs_sf2_level(3, 1); /* Fan1 */ | ||
1054 | sysfs_sf2_level(1, 2); /* Fan2 */ | ||
1055 | sysfs_sf2_level(2, 2); /* Fan2 */ | ||
1056 | sysfs_sf2_level(3, 2); /* Fan2 */ | ||
1057 | sysfs_sf2_level(1, 3); /* Fan3 */ | ||
1058 | sysfs_sf2_level(2, 3); /* Fan3 */ | ||
1059 | sysfs_sf2_level(3, 3); /* Fan3 */ | ||
1060 | |||
1061 | #define device_create_file_sf2_level(client, offset, index) \ | ||
1062 | do { \ | ||
1063 | device_create_file(&client->dev, \ | ||
1064 | &sensor_dev_attr_sf2_level##offset##_fan##index.dev_attr); \ | ||
1065 | } while (0) | ||
1066 | |||
1067 | |||
1068 | /* This function is called when: | ||
1069 | * w83792d_driver is inserted (when this module is loaded), for each | ||
1070 | available adapter | ||
1071 | * when a new adapter is inserted (and w83792d_driver is still present) */ | ||
1072 | static int | ||
1073 | w83792d_attach_adapter(struct i2c_adapter *adapter) | ||
1074 | { | ||
1075 | if (!(adapter->class & I2C_CLASS_HWMON)) | ||
1076 | return 0; | ||
1077 | return i2c_probe(adapter, &addr_data, w83792d_detect); | ||
1078 | } | ||
1079 | |||
1080 | |||
1081 | static int | ||
1082 | w83792d_create_subclient(struct i2c_adapter *adapter, | ||
1083 | struct i2c_client *new_client, int addr, | ||
1084 | struct i2c_client **sub_cli) | ||
1085 | { | ||
1086 | int err; | ||
1087 | struct i2c_client *sub_client; | ||
1088 | |||
1089 | (*sub_cli) = sub_client = kmalloc(sizeof(struct i2c_client), GFP_KERNEL); | ||
1090 | if (!(sub_client)) { | ||
1091 | return -ENOMEM; | ||
1092 | } | ||
1093 | memset(sub_client, 0x00, sizeof(struct i2c_client)); | ||
1094 | sub_client->addr = 0x48 + addr; | ||
1095 | i2c_set_clientdata(sub_client, NULL); | ||
1096 | sub_client->adapter = adapter; | ||
1097 | sub_client->driver = &w83792d_driver; | ||
1098 | sub_client->flags = 0; | ||
1099 | strlcpy(sub_client->name, "w83792d subclient", I2C_NAME_SIZE); | ||
1100 | if ((err = i2c_attach_client(sub_client))) { | ||
1101 | dev_err(&new_client->dev, "subclient registration " | ||
1102 | "at address 0x%x failed\n", sub_client->addr); | ||
1103 | kfree(sub_client); | ||
1104 | return err; | ||
1105 | } | ||
1106 | return 0; | ||
1107 | } | ||
1108 | |||
1109 | |||
1110 | static int | ||
1111 | w83792d_detect_subclients(struct i2c_adapter *adapter, int address, int kind, | ||
1112 | struct i2c_client *new_client) | ||
1113 | { | ||
1114 | int i, id, err; | ||
1115 | u8 val; | ||
1116 | struct w83792d_data *data = i2c_get_clientdata(new_client); | ||
1117 | |||
1118 | id = i2c_adapter_id(adapter); | ||
1119 | if (force_subclients[0] == id && force_subclients[1] == address) { | ||
1120 | for (i = 2; i <= 3; i++) { | ||
1121 | if (force_subclients[i] < 0x48 || | ||
1122 | force_subclients[i] > 0x4f) { | ||
1123 | dev_err(&new_client->dev, "invalid subclient " | ||
1124 | "address %d; must be 0x48-0x4f\n", | ||
1125 | force_subclients[i]); | ||
1126 | err = -ENODEV; | ||
1127 | goto ERROR_SC_0; | ||
1128 | } | ||
1129 | } | ||
1130 | w83792d_write_value(new_client, W83792D_REG_I2C_SUBADDR, | ||
1131 | (force_subclients[2] & 0x07) | | ||
1132 | ((force_subclients[3] & 0x07) << 4)); | ||
1133 | } | ||
1134 | |||
1135 | val = w83792d_read_value(new_client, W83792D_REG_I2C_SUBADDR); | ||
1136 | if (!(val & 0x08)) { | ||
1137 | err = w83792d_create_subclient(adapter, new_client, val & 0x7, | ||
1138 | &data->lm75[0]); | ||
1139 | if (err < 0) | ||
1140 | goto ERROR_SC_0; | ||
1141 | } | ||
1142 | if (!(val & 0x80)) { | ||
1143 | if ((data->lm75[0] != NULL) && | ||
1144 | ((val & 0x7) == ((val >> 4) & 0x7))) { | ||
1145 | dev_err(&new_client->dev, "duplicate addresses 0x%x, " | ||
1146 | "use force_subclient\n", data->lm75[0]->addr); | ||
1147 | err = -ENODEV; | ||
1148 | goto ERROR_SC_1; | ||
1149 | } | ||
1150 | err = w83792d_create_subclient(adapter, new_client, | ||
1151 | (val >> 4) & 0x7, &data->lm75[1]); | ||
1152 | if (err < 0) | ||
1153 | goto ERROR_SC_1; | ||
1154 | } | ||
1155 | |||
1156 | return 0; | ||
1157 | |||
1158 | /* Undo inits in case of errors */ | ||
1159 | |||
1160 | ERROR_SC_1: | ||
1161 | if (data->lm75[0] != NULL) { | ||
1162 | i2c_detach_client(data->lm75[0]); | ||
1163 | kfree(data->lm75[0]); | ||
1164 | } | ||
1165 | ERROR_SC_0: | ||
1166 | return err; | ||
1167 | } | ||
1168 | |||
1169 | |||
1170 | static int | ||
1171 | w83792d_detect(struct i2c_adapter *adapter, int address, int kind) | ||
1172 | { | ||
1173 | int i = 0, val1 = 0, val2; | ||
1174 | struct i2c_client *new_client; | ||
1175 | struct w83792d_data *data; | ||
1176 | int err = 0; | ||
1177 | const char *client_name = ""; | ||
1178 | |||
1179 | if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA)) { | ||
1180 | goto ERROR0; | ||
1181 | } | ||
1182 | |||
1183 | /* OK. For now, we presume we have a valid client. We now create the | ||
1184 | client structure, even though we cannot fill it completely yet. | ||
1185 | But it allows us to access w83792d_{read,write}_value. */ | ||
1186 | |||
1187 | if (!(data = kmalloc(sizeof(struct w83792d_data), GFP_KERNEL))) { | ||
1188 | err = -ENOMEM; | ||
1189 | goto ERROR0; | ||
1190 | } | ||
1191 | memset(data, 0, sizeof(struct w83792d_data)); | ||
1192 | |||
1193 | new_client = &data->client; | ||
1194 | i2c_set_clientdata(new_client, data); | ||
1195 | new_client->addr = address; | ||
1196 | init_MUTEX(&data->lock); | ||
1197 | new_client->adapter = adapter; | ||
1198 | new_client->driver = &w83792d_driver; | ||
1199 | new_client->flags = 0; | ||
1200 | |||
1201 | /* Now, we do the remaining detection. */ | ||
1202 | |||
1203 | /* The w83792d may be stuck in some other bank than bank 0. This may | ||
1204 | make reading other information impossible. Specify a force=... or | ||
1205 | force_*=... parameter, and the Winbond will be reset to the right | ||
1206 | bank. */ | ||
1207 | if (kind < 0) { | ||
1208 | if (w83792d_read_value(new_client, W83792D_REG_CONFIG) & 0x80) { | ||
1209 | dev_warn(&new_client->dev, "Detection failed at step " | ||
1210 | "3\n"); | ||
1211 | goto ERROR1; | ||
1212 | } | ||
1213 | val1 = w83792d_read_value(new_client, W83792D_REG_BANK); | ||
1214 | val2 = w83792d_read_value(new_client, W83792D_REG_CHIPMAN); | ||
1215 | /* Check for Winbond ID if in bank 0 */ | ||
1216 | if (!(val1 & 0x07)) { /* is Bank0 */ | ||
1217 | if (((!(val1 & 0x80)) && (val2 != 0xa3)) || | ||
1218 | ((val1 & 0x80) && (val2 != 0x5c))) { | ||
1219 | goto ERROR1; | ||
1220 | } | ||
1221 | } | ||
1222 | /* If Winbond chip, address of chip and W83792D_REG_I2C_ADDR | ||
1223 | should match */ | ||
1224 | if (w83792d_read_value(new_client, | ||
1225 | W83792D_REG_I2C_ADDR) != address) { | ||
1226 | dev_warn(&new_client->dev, "Detection failed " | ||
1227 | "at step 5\n"); | ||
1228 | goto ERROR1; | ||
1229 | } | ||
1230 | } | ||
1231 | |||
1232 | /* We have either had a force parameter, or we have already detected the | ||
1233 | Winbond. Put it now into bank 0 and Vendor ID High Byte */ | ||
1234 | w83792d_write_value(new_client, | ||
1235 | W83792D_REG_BANK, | ||
1236 | (w83792d_read_value(new_client, | ||
1237 | W83792D_REG_BANK) & 0x78) | 0x80); | ||
1238 | |||
1239 | /* Determine the chip type. */ | ||
1240 | if (kind <= 0) { | ||
1241 | /* get vendor ID */ | ||
1242 | val2 = w83792d_read_value(new_client, W83792D_REG_CHIPMAN); | ||
1243 | if (val2 != 0x5c) { /* the vendor is NOT Winbond */ | ||
1244 | goto ERROR1; | ||
1245 | } | ||
1246 | val1 = w83792d_read_value(new_client, W83792D_REG_WCHIPID); | ||
1247 | if (val1 == 0x7a && address >= 0x2c) { | ||
1248 | kind = w83792d; | ||
1249 | } else { | ||
1250 | if (kind == 0) | ||
1251 | dev_warn(&new_client->dev, | ||
1252 | "w83792d: Ignoring 'force' parameter for" | ||
1253 | " unknown chip at adapter %d, address" | ||
1254 | " 0x%02x\n", i2c_adapter_id(adapter), | ||
1255 | address); | ||
1256 | goto ERROR1; | ||
1257 | } | ||
1258 | } | ||
1259 | |||
1260 | if (kind == w83792d) { | ||
1261 | client_name = "w83792d"; | ||
1262 | } else { | ||
1263 | dev_err(&new_client->dev, "w83792d: Internal error: unknown" | ||
1264 | " kind (%d)?!?", kind); | ||
1265 | goto ERROR1; | ||
1266 | } | ||
1267 | |||
1268 | /* Fill in the remaining client fields and put into the global list */ | ||
1269 | strlcpy(new_client->name, client_name, I2C_NAME_SIZE); | ||
1270 | data->type = kind; | ||
1271 | |||
1272 | data->valid = 0; | ||
1273 | init_MUTEX(&data->update_lock); | ||
1274 | |||
1275 | /* Tell the I2C layer a new client has arrived */ | ||
1276 | if ((err = i2c_attach_client(new_client))) | ||
1277 | goto ERROR1; | ||
1278 | |||
1279 | if ((err = w83792d_detect_subclients(adapter, address, | ||
1280 | kind, new_client))) | ||
1281 | goto ERROR2; | ||
1282 | |||
1283 | /* Initialize the chip */ | ||
1284 | w83792d_init_client(new_client); | ||
1285 | |||
1286 | /* A few vars need to be filled upon startup */ | ||
1287 | for (i = 1; i <= 7; i++) { | ||
1288 | data->fan_min[i - 1] = w83792d_read_value(new_client, | ||
1289 | W83792D_REG_FAN_MIN[i]); | ||
1290 | } | ||
1291 | |||
1292 | /* Register sysfs hooks */ | ||
1293 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
1294 | if (IS_ERR(data->class_dev)) { | ||
1295 | err = PTR_ERR(data->class_dev); | ||
1296 | goto ERROR3; | ||
1297 | } | ||
1298 | device_create_file_in(new_client, 0); | ||
1299 | device_create_file_in(new_client, 1); | ||
1300 | device_create_file_in(new_client, 2); | ||
1301 | device_create_file_in(new_client, 3); | ||
1302 | device_create_file_in(new_client, 4); | ||
1303 | device_create_file_in(new_client, 5); | ||
1304 | device_create_file_in(new_client, 6); | ||
1305 | device_create_file_in(new_client, 7); | ||
1306 | device_create_file_in(new_client, 8); | ||
1307 | |||
1308 | device_create_file_fan(new_client, 1); | ||
1309 | device_create_file_fan(new_client, 2); | ||
1310 | device_create_file_fan(new_client, 3); | ||
1311 | device_create_file_fan(new_client, 4); | ||
1312 | device_create_file_fan(new_client, 5); | ||
1313 | device_create_file_fan(new_client, 6); | ||
1314 | device_create_file_fan(new_client, 7); | ||
1315 | |||
1316 | device_create_file_temp1(new_client); /* Temp1 */ | ||
1317 | device_create_file_temp_add(new_client, 2); /* Temp2 */ | ||
1318 | device_create_file_temp_add(new_client, 3); /* Temp3 */ | ||
1319 | |||
1320 | device_create_file_alarms(new_client); | ||
1321 | |||
1322 | device_create_file_pwm(new_client, 1); | ||
1323 | device_create_file_pwm(new_client, 2); | ||
1324 | device_create_file_pwm(new_client, 3); | ||
1325 | |||
1326 | device_create_file_pwmenable(new_client, 1); | ||
1327 | device_create_file_pwmenable(new_client, 2); | ||
1328 | device_create_file_pwmenable(new_client, 3); | ||
1329 | |||
1330 | device_create_file_pwm_mode(new_client, 1); | ||
1331 | device_create_file_pwm_mode(new_client, 2); | ||
1332 | device_create_file_pwm_mode(new_client, 3); | ||
1333 | |||
1334 | device_create_file_chassis(new_client); | ||
1335 | device_create_file_chassis_clear(new_client); | ||
1336 | |||
1337 | device_create_file_thermal_cruise(new_client, 1); | ||
1338 | device_create_file_thermal_cruise(new_client, 2); | ||
1339 | device_create_file_thermal_cruise(new_client, 3); | ||
1340 | |||
1341 | device_create_file_tolerance(new_client, 1); | ||
1342 | device_create_file_tolerance(new_client, 2); | ||
1343 | device_create_file_tolerance(new_client, 3); | ||
1344 | |||
1345 | device_create_file_sf2_point(new_client, 1, 1); /* Fan1 */ | ||
1346 | device_create_file_sf2_point(new_client, 2, 1); /* Fan1 */ | ||
1347 | device_create_file_sf2_point(new_client, 3, 1); /* Fan1 */ | ||
1348 | device_create_file_sf2_point(new_client, 4, 1); /* Fan1 */ | ||
1349 | device_create_file_sf2_point(new_client, 1, 2); /* Fan2 */ | ||
1350 | device_create_file_sf2_point(new_client, 2, 2); /* Fan2 */ | ||
1351 | device_create_file_sf2_point(new_client, 3, 2); /* Fan2 */ | ||
1352 | device_create_file_sf2_point(new_client, 4, 2); /* Fan2 */ | ||
1353 | device_create_file_sf2_point(new_client, 1, 3); /* Fan3 */ | ||
1354 | device_create_file_sf2_point(new_client, 2, 3); /* Fan3 */ | ||
1355 | device_create_file_sf2_point(new_client, 3, 3); /* Fan3 */ | ||
1356 | device_create_file_sf2_point(new_client, 4, 3); /* Fan3 */ | ||
1357 | |||
1358 | device_create_file_sf2_level(new_client, 1, 1); /* Fan1 */ | ||
1359 | device_create_file_sf2_level(new_client, 2, 1); /* Fan1 */ | ||
1360 | device_create_file_sf2_level(new_client, 3, 1); /* Fan1 */ | ||
1361 | device_create_file_sf2_level(new_client, 1, 2); /* Fan2 */ | ||
1362 | device_create_file_sf2_level(new_client, 2, 2); /* Fan2 */ | ||
1363 | device_create_file_sf2_level(new_client, 3, 2); /* Fan2 */ | ||
1364 | device_create_file_sf2_level(new_client, 1, 3); /* Fan3 */ | ||
1365 | device_create_file_sf2_level(new_client, 2, 3); /* Fan3 */ | ||
1366 | device_create_file_sf2_level(new_client, 3, 3); /* Fan3 */ | ||
1367 | |||
1368 | return 0; | ||
1369 | |||
1370 | ERROR3: | ||
1371 | if (data->lm75[0] != NULL) { | ||
1372 | i2c_detach_client(data->lm75[0]); | ||
1373 | kfree(data->lm75[0]); | ||
1374 | } | ||
1375 | if (data->lm75[1] != NULL) { | ||
1376 | i2c_detach_client(data->lm75[1]); | ||
1377 | kfree(data->lm75[1]); | ||
1378 | } | ||
1379 | ERROR2: | ||
1380 | i2c_detach_client(new_client); | ||
1381 | ERROR1: | ||
1382 | kfree(data); | ||
1383 | ERROR0: | ||
1384 | return err; | ||
1385 | } | ||
1386 | |||
1387 | static int | ||
1388 | w83792d_detach_client(struct i2c_client *client) | ||
1389 | { | ||
1390 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
1391 | int err; | ||
1392 | |||
1393 | /* main client */ | ||
1394 | if (data) | ||
1395 | hwmon_device_unregister(data->class_dev); | ||
1396 | |||
1397 | if ((err = i2c_detach_client(client))) | ||
1398 | return err; | ||
1399 | |||
1400 | /* main client */ | ||
1401 | if (data) | ||
1402 | kfree(data); | ||
1403 | /* subclient */ | ||
1404 | else | ||
1405 | kfree(client); | ||
1406 | |||
1407 | return 0; | ||
1408 | } | ||
1409 | |||
1410 | /* The SMBus locks itself, usually, but nothing may access the Winbond between | ||
1411 | bank switches. ISA access must always be locked explicitly! | ||
1412 | We ignore the W83792D BUSY flag at this moment - it could lead to deadlocks, | ||
1413 | would slow down the W83792D access and should not be necessary. | ||
1414 | There are some ugly typecasts here, but the good news is - they should | ||
1415 | nowhere else be necessary! */ | ||
1416 | static int | ||
1417 | w83792d_read_value(struct i2c_client *client, u8 reg) | ||
1418 | { | ||
1419 | int res=0; | ||
1420 | res = i2c_smbus_read_byte_data(client, reg); | ||
1421 | |||
1422 | return res; | ||
1423 | } | ||
1424 | |||
1425 | static int | ||
1426 | w83792d_write_value(struct i2c_client *client, u8 reg, u8 value) | ||
1427 | { | ||
1428 | i2c_smbus_write_byte_data(client, reg, value); | ||
1429 | return 0; | ||
1430 | } | ||
1431 | |||
1432 | /* Called when we have found a new W83792D. It should set limits, etc. */ | ||
1433 | static void | ||
1434 | w83792d_init_client(struct i2c_client *client) | ||
1435 | { | ||
1436 | u8 temp2_cfg, temp3_cfg, vid_in_b; | ||
1437 | |||
1438 | if (init) { | ||
1439 | w83792d_write_value(client, W83792D_REG_CONFIG, 0x80); | ||
1440 | } | ||
1441 | /* Clear the bit6 of W83792D_REG_VID_IN_B(set it into 0): | ||
1442 | W83792D_REG_VID_IN_B bit6 = 0: the high/low limit of | ||
1443 | vin0/vin1 can be modified by user; | ||
1444 | W83792D_REG_VID_IN_B bit6 = 1: the high/low limit of | ||
1445 | vin0/vin1 auto-updated, can NOT be modified by user. */ | ||
1446 | vid_in_b = w83792d_read_value(client, W83792D_REG_VID_IN_B); | ||
1447 | w83792d_write_value(client, W83792D_REG_VID_IN_B, | ||
1448 | vid_in_b & 0xbf); | ||
1449 | |||
1450 | temp2_cfg = w83792d_read_value(client, W83792D_REG_TEMP2_CONFIG); | ||
1451 | temp3_cfg = w83792d_read_value(client, W83792D_REG_TEMP3_CONFIG); | ||
1452 | w83792d_write_value(client, W83792D_REG_TEMP2_CONFIG, | ||
1453 | temp2_cfg & 0xe6); | ||
1454 | w83792d_write_value(client, W83792D_REG_TEMP3_CONFIG, | ||
1455 | temp3_cfg & 0xe6); | ||
1456 | |||
1457 | /* Start monitoring */ | ||
1458 | w83792d_write_value(client, W83792D_REG_CONFIG, | ||
1459 | (w83792d_read_value(client, | ||
1460 | W83792D_REG_CONFIG) & 0xf7) | ||
1461 | | 0x01); | ||
1462 | } | ||
1463 | |||
1464 | static struct w83792d_data *w83792d_update_device(struct device *dev) | ||
1465 | { | ||
1466 | struct i2c_client *client = to_i2c_client(dev); | ||
1467 | struct w83792d_data *data = i2c_get_clientdata(client); | ||
1468 | int i, j; | ||
1469 | u8 reg_array_tmp[4], pwm_array_tmp[7], reg_tmp; | ||
1470 | |||
1471 | down(&data->update_lock); | ||
1472 | |||
1473 | if (time_after | ||
1474 | (jiffies - data->last_updated, (unsigned long) (HZ * 3)) | ||
1475 | || time_before(jiffies, data->last_updated) || !data->valid) { | ||
1476 | dev_dbg(dev, "Starting device update\n"); | ||
1477 | |||
1478 | /* Update the voltages measured value and limits */ | ||
1479 | for (i = 0; i < 9; i++) { | ||
1480 | data->in[i] = w83792d_read_value(client, | ||
1481 | W83792D_REG_IN[i]); | ||
1482 | data->in_max[i] = w83792d_read_value(client, | ||
1483 | W83792D_REG_IN_MAX[i]); | ||
1484 | data->in_min[i] = w83792d_read_value(client, | ||
1485 | W83792D_REG_IN_MIN[i]); | ||
1486 | } | ||
1487 | data->low_bits[0] = w83792d_read_value(client, | ||
1488 | W83792D_REG_LOW_BITS1); | ||
1489 | data->low_bits[1] = w83792d_read_value(client, | ||
1490 | W83792D_REG_LOW_BITS2); | ||
1491 | for (i = 0; i < 7; i++) { | ||
1492 | /* Update the Fan measured value and limits */ | ||
1493 | data->fan[i] = w83792d_read_value(client, | ||
1494 | W83792D_REG_FAN[i]); | ||
1495 | data->fan_min[i] = w83792d_read_value(client, | ||
1496 | W83792D_REG_FAN_MIN[i]); | ||
1497 | /* Update the PWM/DC Value and PWM/DC flag */ | ||
1498 | pwm_array_tmp[i] = w83792d_read_value(client, | ||
1499 | W83792D_REG_PWM[i]); | ||
1500 | data->pwm[i] = pwm_array_tmp[i] & 0x0f; | ||
1501 | data->pwm_mode[i] = (pwm_array_tmp[i] >> 7) & 0x01; | ||
1502 | } | ||
1503 | |||
1504 | reg_tmp = w83792d_read_value(client, W83792D_REG_FAN_CFG); | ||
1505 | data->pwmenable[0] = reg_tmp & 0x03; | ||
1506 | data->pwmenable[1] = (reg_tmp>>2) & 0x03; | ||
1507 | data->pwmenable[2] = (reg_tmp>>4) & 0x03; | ||
1508 | |||
1509 | for (i = 0; i < 3; i++) { | ||
1510 | data->temp1[i] = w83792d_read_value(client, | ||
1511 | W83792D_REG_TEMP1[i]); | ||
1512 | } | ||
1513 | for (i = 0; i < 2; i++) { | ||
1514 | for (j = 0; j < 6; j++) { | ||
1515 | data->temp_add[i][j] = w83792d_read_value( | ||
1516 | client,W83792D_REG_TEMP_ADD[i][j]); | ||
1517 | } | ||
1518 | } | ||
1519 | |||
1520 | /* Update the Fan Divisor */ | ||
1521 | for (i = 0; i < 4; i++) { | ||
1522 | reg_array_tmp[i] = w83792d_read_value(client, | ||
1523 | W83792D_REG_FAN_DIV[i]); | ||
1524 | } | ||
1525 | data->fan_div[0] = reg_array_tmp[0] & 0x07; | ||
1526 | data->fan_div[1] = (reg_array_tmp[0] >> 4) & 0x07; | ||
1527 | data->fan_div[2] = reg_array_tmp[1] & 0x07; | ||
1528 | data->fan_div[3] = (reg_array_tmp[1] >> 4) & 0x07; | ||
1529 | data->fan_div[4] = reg_array_tmp[2] & 0x07; | ||
1530 | data->fan_div[5] = (reg_array_tmp[2] >> 4) & 0x07; | ||
1531 | data->fan_div[6] = reg_array_tmp[3] & 0x07; | ||
1532 | |||
1533 | /* Update the realtime status */ | ||
1534 | data->alarms = w83792d_read_value(client, W83792D_REG_ALARM1) + | ||
1535 | (w83792d_read_value(client, W83792D_REG_ALARM2) << 8) + | ||
1536 | (w83792d_read_value(client, W83792D_REG_ALARM3) << 16); | ||
1537 | |||
1538 | /* Update CaseOpen status and it's CLR_CHS. */ | ||
1539 | data->chassis = (w83792d_read_value(client, | ||
1540 | W83792D_REG_CHASSIS) >> 5) & 0x01; | ||
1541 | data->chassis_clear = (w83792d_read_value(client, | ||
1542 | W83792D_REG_CHASSIS_CLR) >> 7) & 0x01; | ||
1543 | |||
1544 | /* Update Thermal Cruise/Smart Fan I target value */ | ||
1545 | for (i = 0; i < 3; i++) { | ||
1546 | data->thermal_cruise[i] = | ||
1547 | w83792d_read_value(client, | ||
1548 | W83792D_REG_THERMAL[i]) & 0x7f; | ||
1549 | } | ||
1550 | |||
1551 | /* Update Smart Fan I/II tolerance */ | ||
1552 | reg_tmp = w83792d_read_value(client, W83792D_REG_TOLERANCE[0]); | ||
1553 | data->tolerance[0] = reg_tmp & 0x0f; | ||
1554 | data->tolerance[1] = (reg_tmp >> 4) & 0x0f; | ||
1555 | data->tolerance[2] = w83792d_read_value(client, | ||
1556 | W83792D_REG_TOLERANCE[2]) & 0x0f; | ||
1557 | |||
1558 | /* Update Smart Fan II temperature points */ | ||
1559 | for (i = 0; i < 3; i++) { | ||
1560 | for (j = 0; j < 4; j++) { | ||
1561 | data->sf2_points[i][j] = w83792d_read_value( | ||
1562 | client,W83792D_REG_POINTS[i][j]) & 0x7f; | ||
1563 | } | ||
1564 | } | ||
1565 | |||
1566 | /* Update Smart Fan II duty cycle levels */ | ||
1567 | for (i = 0; i < 3; i++) { | ||
1568 | reg_tmp = w83792d_read_value(client, | ||
1569 | W83792D_REG_LEVELS[i][0]); | ||
1570 | data->sf2_levels[i][0] = reg_tmp & 0x0f; | ||
1571 | data->sf2_levels[i][1] = (reg_tmp >> 4) & 0x0f; | ||
1572 | reg_tmp = w83792d_read_value(client, | ||
1573 | W83792D_REG_LEVELS[i][2]); | ||
1574 | data->sf2_levels[i][2] = (reg_tmp >> 4) & 0x0f; | ||
1575 | data->sf2_levels[i][3] = reg_tmp & 0x0f; | ||
1576 | } | ||
1577 | |||
1578 | data->last_updated = jiffies; | ||
1579 | data->valid = 1; | ||
1580 | } | ||
1581 | |||
1582 | up(&data->update_lock); | ||
1583 | |||
1584 | #ifdef DEBUG | ||
1585 | w83792d_print_debug(data, dev); | ||
1586 | #endif | ||
1587 | |||
1588 | return data; | ||
1589 | } | ||
1590 | |||
1591 | #ifdef DEBUG | ||
1592 | static void w83792d_print_debug(struct w83792d_data *data, struct device *dev) | ||
1593 | { | ||
1594 | int i=0, j=0; | ||
1595 | dev_dbg(dev, "==========The following is the debug message...========\n"); | ||
1596 | dev_dbg(dev, "9 set of Voltages: =====>\n"); | ||
1597 | for (i=0; i<9; i++) { | ||
1598 | dev_dbg(dev, "vin[%d] is: 0x%x\n", i, data->in[i]); | ||
1599 | dev_dbg(dev, "vin[%d] max is: 0x%x\n", i, data->in_max[i]); | ||
1600 | dev_dbg(dev, "vin[%d] min is: 0x%x\n", i, data->in_min[i]); | ||
1601 | } | ||
1602 | dev_dbg(dev, "Low Bit1 is: 0x%x\n", data->low_bits[0]); | ||
1603 | dev_dbg(dev, "Low Bit2 is: 0x%x\n", data->low_bits[1]); | ||
1604 | dev_dbg(dev, "7 set of Fan Counts and Duty Cycles: =====>\n"); | ||
1605 | for (i=0; i<7; i++) { | ||
1606 | dev_dbg(dev, "fan[%d] is: 0x%x\n", i, data->fan[i]); | ||
1607 | dev_dbg(dev, "fan[%d] min is: 0x%x\n", i, data->fan_min[i]); | ||
1608 | dev_dbg(dev, "pwm[%d] is: 0x%x\n", i, data->pwm[i]); | ||
1609 | dev_dbg(dev, "pwm_mode[%d] is: 0x%x\n", i, data->pwm_mode[i]); | ||
1610 | } | ||
1611 | dev_dbg(dev, "3 set of Temperatures: =====>\n"); | ||
1612 | for (i=0; i<3; i++) { | ||
1613 | dev_dbg(dev, "temp1[%d] is: 0x%x\n", i, data->temp1[i]); | ||
1614 | } | ||
1615 | |||
1616 | for (i=0; i<2; i++) { | ||
1617 | for (j=0; j<6; j++) { | ||
1618 | dev_dbg(dev, "temp_add[%d][%d] is: 0x%x\n", i, j, | ||
1619 | data->temp_add[i][j]); | ||
1620 | } | ||
1621 | } | ||
1622 | |||
1623 | for (i=0; i<7; i++) { | ||
1624 | dev_dbg(dev, "fan_div[%d] is: 0x%x\n", i, data->fan_div[i]); | ||
1625 | } | ||
1626 | dev_dbg(dev, "==========End of the debug message...==================\n"); | ||
1627 | dev_dbg(dev, "\n"); | ||
1628 | } | ||
1629 | #endif | ||
1630 | |||
1631 | static int __init | ||
1632 | sensors_w83792d_init(void) | ||
1633 | { | ||
1634 | return i2c_add_driver(&w83792d_driver); | ||
1635 | } | ||
1636 | |||
1637 | static void __exit | ||
1638 | sensors_w83792d_exit(void) | ||
1639 | { | ||
1640 | i2c_del_driver(&w83792d_driver); | ||
1641 | } | ||
1642 | |||
1643 | MODULE_AUTHOR("Chunhao Huang @ Winbond <DZShen@Winbond.com.tw>"); | ||
1644 | MODULE_DESCRIPTION("W83792AD/D driver for linux-2.6"); | ||
1645 | MODULE_LICENSE("GPL"); | ||
1646 | |||
1647 | module_init(sensors_w83792d_init); | ||
1648 | module_exit(sensors_w83792d_exit); | ||
1649 | |||
diff --git a/drivers/hwmon/w83l785ts.c b/drivers/hwmon/w83l785ts.c index 4469d52aba4c..133e34ab1d0a 100644 --- a/drivers/hwmon/w83l785ts.c +++ b/drivers/hwmon/w83l785ts.c | |||
@@ -36,7 +36,8 @@ | |||
36 | #include <linux/slab.h> | 36 | #include <linux/slab.h> |
37 | #include <linux/jiffies.h> | 37 | #include <linux/jiffies.h> |
38 | #include <linux/i2c.h> | 38 | #include <linux/i2c.h> |
39 | #include <linux/i2c-sensor.h> | 39 | #include <linux/hwmon.h> |
40 | #include <linux/err.h> | ||
40 | 41 | ||
41 | /* How many retries on register read error */ | 42 | /* How many retries on register read error */ |
42 | #define MAX_RETRIES 5 | 43 | #define MAX_RETRIES 5 |
@@ -47,13 +48,12 @@ | |||
47 | */ | 48 | */ |
48 | 49 | ||
49 | static unsigned short normal_i2c[] = { 0x2e, I2C_CLIENT_END }; | 50 | static unsigned short normal_i2c[] = { 0x2e, I2C_CLIENT_END }; |
50 | static unsigned int normal_isa[] = { I2C_CLIENT_ISA_END }; | ||
51 | 51 | ||
52 | /* | 52 | /* |
53 | * Insmod parameters | 53 | * Insmod parameters |
54 | */ | 54 | */ |
55 | 55 | ||
56 | SENSORS_INSMOD_1(w83l785ts); | 56 | I2C_CLIENT_INSMOD_1(w83l785ts); |
57 | 57 | ||
58 | /* | 58 | /* |
59 | * The W83L785TS-S registers | 59 | * The W83L785TS-S registers |
@@ -105,6 +105,7 @@ static struct i2c_driver w83l785ts_driver = { | |||
105 | 105 | ||
106 | struct w83l785ts_data { | 106 | struct w83l785ts_data { |
107 | struct i2c_client client; | 107 | struct i2c_client client; |
108 | struct class_device *class_dev; | ||
108 | struct semaphore update_lock; | 109 | struct semaphore update_lock; |
109 | char valid; /* zero until following fields are valid */ | 110 | char valid; /* zero until following fields are valid */ |
110 | unsigned long last_updated; /* in jiffies */ | 111 | unsigned long last_updated; /* in jiffies */ |
@@ -140,7 +141,7 @@ static int w83l785ts_attach_adapter(struct i2c_adapter *adapter) | |||
140 | { | 141 | { |
141 | if (!(adapter->class & I2C_CLASS_HWMON)) | 142 | if (!(adapter->class & I2C_CLASS_HWMON)) |
142 | return 0; | 143 | return 0; |
143 | return i2c_detect(adapter, &addr_data, w83l785ts_detect); | 144 | return i2c_probe(adapter, &addr_data, w83l785ts_detect); |
144 | } | 145 | } |
145 | 146 | ||
146 | /* | 147 | /* |
@@ -239,11 +240,19 @@ static int w83l785ts_detect(struct i2c_adapter *adapter, int address, int kind) | |||
239 | */ | 240 | */ |
240 | 241 | ||
241 | /* Register sysfs hooks */ | 242 | /* Register sysfs hooks */ |
243 | data->class_dev = hwmon_device_register(&new_client->dev); | ||
244 | if (IS_ERR(data->class_dev)) { | ||
245 | err = PTR_ERR(data->class_dev); | ||
246 | goto exit_detach; | ||
247 | } | ||
248 | |||
242 | device_create_file(&new_client->dev, &dev_attr_temp1_input); | 249 | device_create_file(&new_client->dev, &dev_attr_temp1_input); |
243 | device_create_file(&new_client->dev, &dev_attr_temp1_max); | 250 | device_create_file(&new_client->dev, &dev_attr_temp1_max); |
244 | 251 | ||
245 | return 0; | 252 | return 0; |
246 | 253 | ||
254 | exit_detach: | ||
255 | i2c_detach_client(new_client); | ||
247 | exit_free: | 256 | exit_free: |
248 | kfree(data); | 257 | kfree(data); |
249 | exit: | 258 | exit: |
@@ -252,15 +261,15 @@ exit: | |||
252 | 261 | ||
253 | static int w83l785ts_detach_client(struct i2c_client *client) | 262 | static int w83l785ts_detach_client(struct i2c_client *client) |
254 | { | 263 | { |
264 | struct w83l785ts_data *data = i2c_get_clientdata(client); | ||
255 | int err; | 265 | int err; |
256 | 266 | ||
257 | if ((err = i2c_detach_client(client))) { | 267 | hwmon_device_unregister(data->class_dev); |
258 | dev_err(&client->dev, "Client deregistration failed, " | 268 | |
259 | "client not detached.\n"); | 269 | if ((err = i2c_detach_client(client))) |
260 | return err; | 270 | return err; |
261 | } | ||
262 | 271 | ||
263 | kfree(i2c_get_clientdata(client)); | 272 | kfree(data); |
264 | return 0; | 273 | return 0; |
265 | } | 274 | } |
266 | 275 | ||