diff options
Diffstat (limited to 'drivers/hwmon')
-rw-r--r-- | drivers/hwmon/Kconfig | 16 | ||||
-rw-r--r-- | drivers/hwmon/Makefile | 1 | ||||
-rw-r--r-- | drivers/hwmon/abituguru3.c | 134 | ||||
-rw-r--r-- | drivers/hwmon/adcxx.c | 329 | ||||
-rw-r--r-- | drivers/hwmon/applesmc.c | 20 | ||||
-rw-r--r-- | drivers/hwmon/coretemp.c | 5 | ||||
-rw-r--r-- | drivers/hwmon/hwmon-vid.c | 36 | ||||
-rw-r--r-- | drivers/hwmon/i5k_amb.c | 28 | ||||
-rw-r--r-- | drivers/hwmon/ibmaem.c | 27 | ||||
-rw-r--r-- | drivers/hwmon/w83791d.c | 3 |
10 files changed, 537 insertions, 62 deletions
diff --git a/drivers/hwmon/Kconfig b/drivers/hwmon/Kconfig index bf4ebfb86fa5..d402e8d813ce 100644 --- a/drivers/hwmon/Kconfig +++ b/drivers/hwmon/Kconfig | |||
@@ -77,6 +77,22 @@ config SENSORS_AD7418 | |||
77 | This driver can also be built as a module. If so, the module | 77 | This driver can also be built as a module. If so, the module |
78 | will be called ad7418. | 78 | will be called ad7418. |
79 | 79 | ||
80 | config SENSORS_ADCXX | ||
81 | tristate "National Semiconductor ADCxxxSxxx" | ||
82 | depends on SPI_MASTER && EXPERIMENTAL | ||
83 | help | ||
84 | If you say yes here you get support for the National Semiconductor | ||
85 | ADC<bb><c>S<sss> chip family, where | ||
86 | * bb is the resolution in number of bits (8, 10, 12) | ||
87 | * c is the number of channels (1, 2, 4, 8) | ||
88 | * sss is the maximum conversion speed (021 for 200 kSPS, 051 for 500 | ||
89 | kSPS and 101 for 1 MSPS) | ||
90 | |||
91 | Examples : ADC081S101, ADC124S501, ... | ||
92 | |||
93 | This driver can also be built as a module. If so, the module | ||
94 | will be called adcxx. | ||
95 | |||
80 | config SENSORS_ADM1021 | 96 | config SENSORS_ADM1021 |
81 | tristate "Analog Devices ADM1021 and compatibles" | 97 | tristate "Analog Devices ADM1021 and compatibles" |
82 | depends on I2C | 98 | depends on I2C |
diff --git a/drivers/hwmon/Makefile b/drivers/hwmon/Makefile index 7943e5cefb06..950134ab8426 100644 --- a/drivers/hwmon/Makefile +++ b/drivers/hwmon/Makefile | |||
@@ -17,6 +17,7 @@ obj-$(CONFIG_SENSORS_ABITUGURU) += abituguru.o | |||
17 | obj-$(CONFIG_SENSORS_ABITUGURU3)+= abituguru3.o | 17 | obj-$(CONFIG_SENSORS_ABITUGURU3)+= abituguru3.o |
18 | obj-$(CONFIG_SENSORS_AD7414) += ad7414.o | 18 | obj-$(CONFIG_SENSORS_AD7414) += ad7414.o |
19 | obj-$(CONFIG_SENSORS_AD7418) += ad7418.o | 19 | obj-$(CONFIG_SENSORS_AD7418) += ad7418.o |
20 | obj-$(CONFIG_SENSORS_ADCXX) += adcxx.o | ||
20 | obj-$(CONFIG_SENSORS_ADM1021) += adm1021.o | 21 | obj-$(CONFIG_SENSORS_ADM1021) += adm1021.o |
21 | obj-$(CONFIG_SENSORS_ADM1025) += adm1025.o | 22 | obj-$(CONFIG_SENSORS_ADM1025) += adm1025.o |
22 | obj-$(CONFIG_SENSORS_ADM1026) += adm1026.o | 23 | obj-$(CONFIG_SENSORS_ADM1026) += adm1026.o |
diff --git a/drivers/hwmon/abituguru3.c b/drivers/hwmon/abituguru3.c index f00f497b9ca9..d568c65c1370 100644 --- a/drivers/hwmon/abituguru3.c +++ b/drivers/hwmon/abituguru3.c | |||
@@ -1,5 +1,8 @@ | |||
1 | /* | 1 | /* |
2 | abituguru3.c Copyright (c) 2006 Hans de Goede <j.w.r.degoede@hhs.nl> | 2 | abituguru3.c |
3 | |||
4 | Copyright (c) 2006-2008 Hans de Goede <j.w.r.degoede@hhs.nl> | ||
5 | Copyright (c) 2008 Alistair John Strachan <alistair@devzero.co.uk> | ||
3 | 6 | ||
4 | This program is free software; you can redistribute it and/or modify | 7 | This program is free software; you can redistribute it and/or modify |
5 | it under the terms of the GNU General Public License as published by | 8 | it under the terms of the GNU General Public License as published by |
@@ -116,7 +119,7 @@ struct abituguru3_sensor_info { | |||
116 | 119 | ||
117 | struct abituguru3_motherboard_info { | 120 | struct abituguru3_motherboard_info { |
118 | u16 id; | 121 | u16 id; |
119 | const char *name; | 122 | const char *dmi_name; |
120 | /* + 1 -> end of sensors indicated by a sensor with name == NULL */ | 123 | /* + 1 -> end of sensors indicated by a sensor with name == NULL */ |
121 | struct abituguru3_sensor_info sensors[ABIT_UGURU3_MAX_NO_SENSORS + 1]; | 124 | struct abituguru3_sensor_info sensors[ABIT_UGURU3_MAX_NO_SENSORS + 1]; |
122 | }; | 125 | }; |
@@ -161,7 +164,7 @@ struct abituguru3_data { | |||
161 | 164 | ||
162 | /* Constants */ | 165 | /* Constants */ |
163 | static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | 166 | static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { |
164 | { 0x000C, "unknown", { | 167 | { 0x000C, NULL /* Unknown, need DMI string */, { |
165 | { "CPU Core", 0, 0, 10, 1, 0 }, | 168 | { "CPU Core", 0, 0, 10, 1, 0 }, |
166 | { "DDR", 1, 0, 10, 1, 0 }, | 169 | { "DDR", 1, 0, 10, 1, 0 }, |
167 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 170 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -183,7 +186,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
183 | { "AUX1 Fan", 35, 2, 60, 1, 0 }, | 186 | { "AUX1 Fan", 35, 2, 60, 1, 0 }, |
184 | { NULL, 0, 0, 0, 0, 0 } } | 187 | { NULL, 0, 0, 0, 0, 0 } } |
185 | }, | 188 | }, |
186 | { 0x000D, "Abit AW8", { | 189 | { 0x000D, NULL /* Abit AW8, need DMI string */, { |
187 | { "CPU Core", 0, 0, 10, 1, 0 }, | 190 | { "CPU Core", 0, 0, 10, 1, 0 }, |
188 | { "DDR", 1, 0, 10, 1, 0 }, | 191 | { "DDR", 1, 0, 10, 1, 0 }, |
189 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 192 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -212,7 +215,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
212 | { "AUX5 Fan", 39, 2, 60, 1, 0 }, | 215 | { "AUX5 Fan", 39, 2, 60, 1, 0 }, |
213 | { NULL, 0, 0, 0, 0, 0 } } | 216 | { NULL, 0, 0, 0, 0, 0 } } |
214 | }, | 217 | }, |
215 | { 0x000E, "AL-8", { | 218 | { 0x000E, NULL /* AL-8, need DMI string */, { |
216 | { "CPU Core", 0, 0, 10, 1, 0 }, | 219 | { "CPU Core", 0, 0, 10, 1, 0 }, |
217 | { "DDR", 1, 0, 10, 1, 0 }, | 220 | { "DDR", 1, 0, 10, 1, 0 }, |
218 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 221 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -233,7 +236,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
233 | { "SYS Fan", 34, 2, 60, 1, 0 }, | 236 | { "SYS Fan", 34, 2, 60, 1, 0 }, |
234 | { NULL, 0, 0, 0, 0, 0 } } | 237 | { NULL, 0, 0, 0, 0, 0 } } |
235 | }, | 238 | }, |
236 | { 0x000F, "unknown", { | 239 | { 0x000F, NULL /* Unknown, need DMI string */, { |
237 | { "CPU Core", 0, 0, 10, 1, 0 }, | 240 | { "CPU Core", 0, 0, 10, 1, 0 }, |
238 | { "DDR", 1, 0, 10, 1, 0 }, | 241 | { "DDR", 1, 0, 10, 1, 0 }, |
239 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 242 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -254,7 +257,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
254 | { "SYS Fan", 34, 2, 60, 1, 0 }, | 257 | { "SYS Fan", 34, 2, 60, 1, 0 }, |
255 | { NULL, 0, 0, 0, 0, 0 } } | 258 | { NULL, 0, 0, 0, 0, 0 } } |
256 | }, | 259 | }, |
257 | { 0x0010, "Abit NI8 SLI GR", { | 260 | { 0x0010, NULL /* Abit NI8 SLI GR, need DMI string */, { |
258 | { "CPU Core", 0, 0, 10, 1, 0 }, | 261 | { "CPU Core", 0, 0, 10, 1, 0 }, |
259 | { "DDR", 1, 0, 10, 1, 0 }, | 262 | { "DDR", 1, 0, 10, 1, 0 }, |
260 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 263 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -276,7 +279,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
276 | { "OTES1 Fan", 36, 2, 60, 1, 0 }, | 279 | { "OTES1 Fan", 36, 2, 60, 1, 0 }, |
277 | { NULL, 0, 0, 0, 0, 0 } } | 280 | { NULL, 0, 0, 0, 0, 0 } } |
278 | }, | 281 | }, |
279 | { 0x0011, "Abit AT8 32X", { | 282 | { 0x0011, NULL /* Abit AT8 32X, need DMI string */, { |
280 | { "CPU Core", 0, 0, 10, 1, 0 }, | 283 | { "CPU Core", 0, 0, 10, 1, 0 }, |
281 | { "DDR", 1, 0, 20, 1, 0 }, | 284 | { "DDR", 1, 0, 20, 1, 0 }, |
282 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 285 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -302,7 +305,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
302 | { "AUX2 Fan", 36, 2, 60, 1, 0 }, | 305 | { "AUX2 Fan", 36, 2, 60, 1, 0 }, |
303 | { NULL, 0, 0, 0, 0, 0 } } | 306 | { NULL, 0, 0, 0, 0, 0 } } |
304 | }, | 307 | }, |
305 | { 0x0012, "Abit AN8 32X", { | 308 | { 0x0012, NULL /* Abit AN8 32X, need DMI string */, { |
306 | { "CPU Core", 0, 0, 10, 1, 0 }, | 309 | { "CPU Core", 0, 0, 10, 1, 0 }, |
307 | { "DDR", 1, 0, 20, 1, 0 }, | 310 | { "DDR", 1, 0, 20, 1, 0 }, |
308 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 311 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -324,7 +327,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
324 | { "AUX1 Fan", 36, 2, 60, 1, 0 }, | 327 | { "AUX1 Fan", 36, 2, 60, 1, 0 }, |
325 | { NULL, 0, 0, 0, 0, 0 } } | 328 | { NULL, 0, 0, 0, 0, 0 } } |
326 | }, | 329 | }, |
327 | { 0x0013, "Abit AW8D", { | 330 | { 0x0013, NULL /* Abit AW8D, need DMI string */, { |
328 | { "CPU Core", 0, 0, 10, 1, 0 }, | 331 | { "CPU Core", 0, 0, 10, 1, 0 }, |
329 | { "DDR", 1, 0, 10, 1, 0 }, | 332 | { "DDR", 1, 0, 10, 1, 0 }, |
330 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 333 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -353,7 +356,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
353 | { "AUX5 Fan", 39, 2, 60, 1, 0 }, | 356 | { "AUX5 Fan", 39, 2, 60, 1, 0 }, |
354 | { NULL, 0, 0, 0, 0, 0 } } | 357 | { NULL, 0, 0, 0, 0, 0 } } |
355 | }, | 358 | }, |
356 | { 0x0014, "Abit AB9 Pro", { | 359 | { 0x0014, NULL /* Abit AB9 Pro, need DMI string */, { |
357 | { "CPU Core", 0, 0, 10, 1, 0 }, | 360 | { "CPU Core", 0, 0, 10, 1, 0 }, |
358 | { "DDR", 1, 0, 10, 1, 0 }, | 361 | { "DDR", 1, 0, 10, 1, 0 }, |
359 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 362 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -374,7 +377,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
374 | { "SYS Fan", 34, 2, 60, 1, 0 }, | 377 | { "SYS Fan", 34, 2, 60, 1, 0 }, |
375 | { NULL, 0, 0, 0, 0, 0 } } | 378 | { NULL, 0, 0, 0, 0, 0 } } |
376 | }, | 379 | }, |
377 | { 0x0015, "unknown", { | 380 | { 0x0015, NULL /* Unknown, need DMI string */, { |
378 | { "CPU Core", 0, 0, 10, 1, 0 }, | 381 | { "CPU Core", 0, 0, 10, 1, 0 }, |
379 | { "DDR", 1, 0, 20, 1, 0 }, | 382 | { "DDR", 1, 0, 20, 1, 0 }, |
380 | { "DDR VTT", 2, 0, 10, 1, 0 }, | 383 | { "DDR VTT", 2, 0, 10, 1, 0 }, |
@@ -398,7 +401,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
398 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, | 401 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, |
399 | { NULL, 0, 0, 0, 0, 0 } } | 402 | { NULL, 0, 0, 0, 0, 0 } } |
400 | }, | 403 | }, |
401 | { 0x0016, "AW9D-MAX", { | 404 | { 0x0016, NULL /* AW9D-MAX, need DMI string */, { |
402 | { "CPU Core", 0, 0, 10, 1, 0 }, | 405 | { "CPU Core", 0, 0, 10, 1, 0 }, |
403 | { "DDR2", 1, 0, 20, 1, 0 }, | 406 | { "DDR2", 1, 0, 20, 1, 0 }, |
404 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, | 407 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, |
@@ -426,7 +429,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
426 | { "OTES1 Fan", 38, 2, 60, 1, 0 }, | 429 | { "OTES1 Fan", 38, 2, 60, 1, 0 }, |
427 | { NULL, 0, 0, 0, 0, 0 } } | 430 | { NULL, 0, 0, 0, 0, 0 } } |
428 | }, | 431 | }, |
429 | { 0x0017, "unknown", { | 432 | { 0x0017, NULL /* Unknown, need DMI string */, { |
430 | { "CPU Core", 0, 0, 10, 1, 0 }, | 433 | { "CPU Core", 0, 0, 10, 1, 0 }, |
431 | { "DDR2", 1, 0, 20, 1, 0 }, | 434 | { "DDR2", 1, 0, 20, 1, 0 }, |
432 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, | 435 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, |
@@ -451,7 +454,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
451 | { "AUX3 FAN", 37, 2, 60, 1, 0 }, | 454 | { "AUX3 FAN", 37, 2, 60, 1, 0 }, |
452 | { NULL, 0, 0, 0, 0, 0 } } | 455 | { NULL, 0, 0, 0, 0, 0 } } |
453 | }, | 456 | }, |
454 | { 0x0018, "unknown", { | 457 | { 0x0018, NULL /* Unknown, need DMI string */, { |
455 | { "CPU Core", 0, 0, 10, 1, 0 }, | 458 | { "CPU Core", 0, 0, 10, 1, 0 }, |
456 | { "DDR2", 1, 0, 20, 1, 0 }, | 459 | { "DDR2", 1, 0, 20, 1, 0 }, |
457 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, | 460 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, |
@@ -478,7 +481,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
478 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, | 481 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, |
479 | { NULL, 0, 0, 0, 0, 0 } } | 482 | { NULL, 0, 0, 0, 0, 0 } } |
480 | }, | 483 | }, |
481 | { 0x0019, "unknown", { | 484 | { 0x0019, NULL /* Unknown, need DMI string */, { |
482 | { "CPU Core", 7, 0, 10, 1, 0 }, | 485 | { "CPU Core", 7, 0, 10, 1, 0 }, |
483 | { "DDR2", 13, 0, 20, 1, 0 }, | 486 | { "DDR2", 13, 0, 20, 1, 0 }, |
484 | { "DDR2 VTT", 14, 0, 10, 1, 0 }, | 487 | { "DDR2 VTT", 14, 0, 10, 1, 0 }, |
@@ -505,7 +508,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
505 | { "AUX3 FAN", 36, 2, 60, 1, 0 }, | 508 | { "AUX3 FAN", 36, 2, 60, 1, 0 }, |
506 | { NULL, 0, 0, 0, 0, 0 } } | 509 | { NULL, 0, 0, 0, 0, 0 } } |
507 | }, | 510 | }, |
508 | { 0x001A, "Abit IP35 Pro", { | 511 | { 0x001A, "IP35 Pro(Intel P35-ICH9R)", { |
509 | { "CPU Core", 0, 0, 10, 1, 0 }, | 512 | { "CPU Core", 0, 0, 10, 1, 0 }, |
510 | { "DDR2", 1, 0, 20, 1, 0 }, | 513 | { "DDR2", 1, 0, 20, 1, 0 }, |
511 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, | 514 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, |
@@ -533,7 +536,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
533 | { "AUX4 Fan", 37, 2, 60, 1, 0 }, | 536 | { "AUX4 Fan", 37, 2, 60, 1, 0 }, |
534 | { NULL, 0, 0, 0, 0, 0 } } | 537 | { NULL, 0, 0, 0, 0, 0 } } |
535 | }, | 538 | }, |
536 | { 0x001B, "unknown", { | 539 | { 0x001B, NULL /* Unknown, need DMI string */, { |
537 | { "CPU Core", 0, 0, 10, 1, 0 }, | 540 | { "CPU Core", 0, 0, 10, 1, 0 }, |
538 | { "DDR3", 1, 0, 20, 1, 0 }, | 541 | { "DDR3", 1, 0, 20, 1, 0 }, |
539 | { "DDR3 VTT", 2, 0, 10, 1, 0 }, | 542 | { "DDR3 VTT", 2, 0, 10, 1, 0 }, |
@@ -560,7 +563,7 @@ static const struct abituguru3_motherboard_info abituguru3_motherboards[] = { | |||
560 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, | 563 | { "AUX3 Fan", 36, 2, 60, 1, 0 }, |
561 | { NULL, 0, 0, 0, 0, 0 } } | 564 | { NULL, 0, 0, 0, 0, 0 } } |
562 | }, | 565 | }, |
563 | { 0x001C, "unknown", { | 566 | { 0x001C, NULL /* Unknown, need DMI string */, { |
564 | { "CPU Core", 0, 0, 10, 1, 0 }, | 567 | { "CPU Core", 0, 0, 10, 1, 0 }, |
565 | { "DDR2", 1, 0, 20, 1, 0 }, | 568 | { "DDR2", 1, 0, 20, 1, 0 }, |
566 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, | 569 | { "DDR2 VTT", 2, 0, 10, 1, 0 }, |
@@ -935,9 +938,18 @@ static int __devinit abituguru3_probe(struct platform_device *pdev) | |||
935 | goto abituguru3_probe_error; | 938 | goto abituguru3_probe_error; |
936 | } | 939 | } |
937 | data->sensors = abituguru3_motherboards[i].sensors; | 940 | data->sensors = abituguru3_motherboards[i].sensors; |
941 | |||
938 | printk(KERN_INFO ABIT_UGURU3_NAME ": found Abit uGuru3, motherboard " | 942 | printk(KERN_INFO ABIT_UGURU3_NAME ": found Abit uGuru3, motherboard " |
939 | "ID: %04X (%s)\n", (unsigned int)id, | 943 | "ID: %04X\n", (unsigned int)id); |
940 | abituguru3_motherboards[i].name); | 944 | |
945 | #ifdef CONFIG_DMI | ||
946 | if (!abituguru3_motherboards[i].dmi_name) { | ||
947 | printk(KERN_WARNING ABIT_UGURU3_NAME ": this motherboard was " | ||
948 | "not detected using DMI. Please send the output of " | ||
949 | "\"dmidecode\" to the abituguru3 maintainer" | ||
950 | "(see MAINTAINERS)\n"); | ||
951 | } | ||
952 | #endif | ||
941 | 953 | ||
942 | /* Fill the sysfs attr array */ | 954 | /* Fill the sysfs attr array */ |
943 | sysfs_attr_i = 0; | 955 | sysfs_attr_i = 0; |
@@ -1109,6 +1121,46 @@ static struct platform_driver abituguru3_driver = { | |||
1109 | .resume = abituguru3_resume | 1121 | .resume = abituguru3_resume |
1110 | }; | 1122 | }; |
1111 | 1123 | ||
1124 | #ifdef CONFIG_DMI | ||
1125 | |||
1126 | static int __init abituguru3_dmi_detect(void) | ||
1127 | { | ||
1128 | const char *board_vendor, *board_name; | ||
1129 | int i, err = (force) ? 1 : -ENODEV; | ||
1130 | |||
1131 | board_vendor = dmi_get_system_info(DMI_BOARD_VENDOR); | ||
1132 | if (!board_vendor || strcmp(board_vendor, "http://www.abit.com.tw/")) | ||
1133 | return err; | ||
1134 | |||
1135 | board_name = dmi_get_system_info(DMI_BOARD_NAME); | ||
1136 | if (!board_name) | ||
1137 | return err; | ||
1138 | |||
1139 | for (i = 0; abituguru3_motherboards[i].id; i++) { | ||
1140 | const char *dmi_name = abituguru3_motherboards[i].dmi_name; | ||
1141 | if (dmi_name && !strcmp(dmi_name, board_name)) | ||
1142 | break; | ||
1143 | } | ||
1144 | |||
1145 | if (!abituguru3_motherboards[i].id) | ||
1146 | return 1; | ||
1147 | |||
1148 | return 0; | ||
1149 | } | ||
1150 | |||
1151 | #else /* !CONFIG_DMI */ | ||
1152 | |||
1153 | static inline int abituguru3_dmi_detect(void) | ||
1154 | { | ||
1155 | return -ENODEV; | ||
1156 | } | ||
1157 | |||
1158 | #endif /* CONFIG_DMI */ | ||
1159 | |||
1160 | /* FIXME: Manual detection should die eventually; we need to collect stable | ||
1161 | * DMI model names first before we can rely entirely on CONFIG_DMI. | ||
1162 | */ | ||
1163 | |||
1112 | static int __init abituguru3_detect(void) | 1164 | static int __init abituguru3_detect(void) |
1113 | { | 1165 | { |
1114 | /* See if there is an uguru3 there. An idle uGuru3 will hold 0x00 or | 1166 | /* See if there is an uguru3 there. An idle uGuru3 will hold 0x00 or |
@@ -1119,7 +1171,7 @@ static int __init abituguru3_detect(void) | |||
1119 | if (((data_val == 0x00) || (data_val == 0x08)) && | 1171 | if (((data_val == 0x00) || (data_val == 0x08)) && |
1120 | ((cmd_val == 0xAC) || (cmd_val == 0x05) || | 1172 | ((cmd_val == 0xAC) || (cmd_val == 0x05) || |
1121 | (cmd_val == 0x55))) | 1173 | (cmd_val == 0x55))) |
1122 | return ABIT_UGURU3_BASE; | 1174 | return 0; |
1123 | 1175 | ||
1124 | ABIT_UGURU3_DEBUG("no Abit uGuru3 found, data = 0x%02X, cmd = " | 1176 | ABIT_UGURU3_DEBUG("no Abit uGuru3 found, data = 0x%02X, cmd = " |
1125 | "0x%02X\n", (unsigned int)data_val, (unsigned int)cmd_val); | 1177 | "0x%02X\n", (unsigned int)data_val, (unsigned int)cmd_val); |
@@ -1127,7 +1179,7 @@ static int __init abituguru3_detect(void) | |||
1127 | if (force) { | 1179 | if (force) { |
1128 | printk(KERN_INFO ABIT_UGURU3_NAME ": Assuming Abit uGuru3 is " | 1180 | printk(KERN_INFO ABIT_UGURU3_NAME ": Assuming Abit uGuru3 is " |
1129 | "present because of \"force\" parameter\n"); | 1181 | "present because of \"force\" parameter\n"); |
1130 | return ABIT_UGURU3_BASE; | 1182 | return 0; |
1131 | } | 1183 | } |
1132 | 1184 | ||
1133 | /* No uGuru3 found */ | 1185 | /* No uGuru3 found */ |
@@ -1138,27 +1190,29 @@ static struct platform_device *abituguru3_pdev; | |||
1138 | 1190 | ||
1139 | static int __init abituguru3_init(void) | 1191 | static int __init abituguru3_init(void) |
1140 | { | 1192 | { |
1141 | int address, err; | ||
1142 | struct resource res = { .flags = IORESOURCE_IO }; | 1193 | struct resource res = { .flags = IORESOURCE_IO }; |
1143 | 1194 | int err; | |
1144 | #ifdef CONFIG_DMI | 1195 | |
1145 | const char *board_vendor = dmi_get_system_info(DMI_BOARD_VENDOR); | 1196 | /* Attempt DMI detection first */ |
1146 | 1197 | err = abituguru3_dmi_detect(); | |
1147 | /* safety check, refuse to load on non Abit motherboards */ | 1198 | if (err < 0) |
1148 | if (!force && (!board_vendor || | 1199 | return err; |
1149 | strcmp(board_vendor, "http://www.abit.com.tw/"))) | 1200 | |
1150 | return -ENODEV; | 1201 | /* Fall back to manual detection if there was no exact |
1151 | #endif | 1202 | * board name match, or force was specified. |
1152 | 1203 | */ | |
1153 | address = abituguru3_detect(); | 1204 | if (err > 0) { |
1154 | if (address < 0) | 1205 | err = abituguru3_detect(); |
1155 | return address; | 1206 | if (err) |
1207 | return err; | ||
1208 | } | ||
1156 | 1209 | ||
1157 | err = platform_driver_register(&abituguru3_driver); | 1210 | err = platform_driver_register(&abituguru3_driver); |
1158 | if (err) | 1211 | if (err) |
1159 | goto exit; | 1212 | goto exit; |
1160 | 1213 | ||
1161 | abituguru3_pdev = platform_device_alloc(ABIT_UGURU3_NAME, address); | 1214 | abituguru3_pdev = platform_device_alloc(ABIT_UGURU3_NAME, |
1215 | ABIT_UGURU3_BASE); | ||
1162 | if (!abituguru3_pdev) { | 1216 | if (!abituguru3_pdev) { |
1163 | printk(KERN_ERR ABIT_UGURU3_NAME | 1217 | printk(KERN_ERR ABIT_UGURU3_NAME |
1164 | ": Device allocation failed\n"); | 1218 | ": Device allocation failed\n"); |
@@ -1166,8 +1220,8 @@ static int __init abituguru3_init(void) | |||
1166 | goto exit_driver_unregister; | 1220 | goto exit_driver_unregister; |
1167 | } | 1221 | } |
1168 | 1222 | ||
1169 | res.start = address; | 1223 | res.start = ABIT_UGURU3_BASE; |
1170 | res.end = address + ABIT_UGURU3_REGION_LENGTH - 1; | 1224 | res.end = ABIT_UGURU3_BASE + ABIT_UGURU3_REGION_LENGTH - 1; |
1171 | res.name = ABIT_UGURU3_NAME; | 1225 | res.name = ABIT_UGURU3_NAME; |
1172 | 1226 | ||
1173 | err = platform_device_add_resources(abituguru3_pdev, &res, 1); | 1227 | err = platform_device_add_resources(abituguru3_pdev, &res, 1); |
diff --git a/drivers/hwmon/adcxx.c b/drivers/hwmon/adcxx.c new file mode 100644 index 000000000000..242294db3db6 --- /dev/null +++ b/drivers/hwmon/adcxx.c | |||
@@ -0,0 +1,329 @@ | |||
1 | /* | ||
2 | * adcxx.c | ||
3 | * | ||
4 | * The adcxx4s is an AD converter family from National Semiconductor (NS). | ||
5 | * | ||
6 | * Copyright (c) 2008 Marc Pignat <marc.pignat@hevs.ch> | ||
7 | * | ||
8 | * The adcxx4s communicates with a host processor via an SPI/Microwire Bus | ||
9 | * interface. This driver supports the whole family of devices with name | ||
10 | * ADC<bb><c>S<sss>, where | ||
11 | * * bb is the resolution in number of bits (8, 10, 12) | ||
12 | * * c is the number of channels (1, 2, 4, 8) | ||
13 | * * sss is the maximum conversion speed (021 for 200 kSPS, 051 for 500 kSPS | ||
14 | * and 101 for 1 MSPS) | ||
15 | * | ||
16 | * Complete datasheets are available at National's website here: | ||
17 | * http://www.national.com/ds/DC/ADC<bb><c>S<sss>.pdf | ||
18 | * | ||
19 | * Handling of 8, 10 and 12 bits converters are the same, the | ||
20 | * unavailable bits are 0 :) | ||
21 | * | ||
22 | * This program is free software; you can redistribute it and/or modify | ||
23 | * it under the terms of the GNU General Public License as published by | ||
24 | * the Free Software Foundation; either version 2 of the License, or | ||
25 | * (at your option) any later version. | ||
26 | * | ||
27 | * This program is distributed in the hope that it will be useful, | ||
28 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
29 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
30 | * GNU General Public License for more details. | ||
31 | * | ||
32 | * You should have received a copy of the GNU General Public License | ||
33 | * along with this program; if not, write to the Free Software | ||
34 | * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
35 | */ | ||
36 | |||
37 | #include <linux/init.h> | ||
38 | #include <linux/module.h> | ||
39 | #include <linux/kernel.h> | ||
40 | #include <linux/device.h> | ||
41 | #include <linux/err.h> | ||
42 | #include <linux/sysfs.h> | ||
43 | #include <linux/hwmon.h> | ||
44 | #include <linux/hwmon-sysfs.h> | ||
45 | #include <linux/mutex.h> | ||
46 | #include <linux/spi/spi.h> | ||
47 | |||
48 | #define DRVNAME "adcxx" | ||
49 | |||
50 | struct adcxx { | ||
51 | struct device *hwmon_dev; | ||
52 | struct mutex lock; | ||
53 | u32 channels; | ||
54 | u32 reference; /* in millivolts */ | ||
55 | }; | ||
56 | |||
57 | /* sysfs hook function */ | ||
58 | static ssize_t adcxx_read(struct device *dev, | ||
59 | struct device_attribute *devattr, char *buf) | ||
60 | { | ||
61 | struct spi_device *spi = to_spi_device(dev); | ||
62 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
63 | struct adcxx *adc = dev_get_drvdata(&spi->dev); | ||
64 | u8 tx_buf[2] = { attr->index << 3 }; /* other bits are don't care */ | ||
65 | u8 rx_buf[2]; | ||
66 | int status; | ||
67 | int value; | ||
68 | |||
69 | if (mutex_lock_interruptible(&adc->lock)) | ||
70 | return -ERESTARTSYS; | ||
71 | |||
72 | status = spi_write_then_read(spi, tx_buf, sizeof(tx_buf), | ||
73 | rx_buf, sizeof(rx_buf)); | ||
74 | if (status < 0) { | ||
75 | dev_warn(dev, "spi_write_then_read failed with status %d\n", | ||
76 | status); | ||
77 | goto out; | ||
78 | } | ||
79 | |||
80 | value = (rx_buf[0] << 8) + rx_buf[1]; | ||
81 | dev_dbg(dev, "raw value = 0x%x\n", value); | ||
82 | |||
83 | value = value * adc->reference >> 12; | ||
84 | status = sprintf(buf, "%d\n", value); | ||
85 | out: | ||
86 | mutex_unlock(&adc->lock); | ||
87 | return status; | ||
88 | } | ||
89 | |||
90 | static ssize_t adcxx_show_min(struct device *dev, | ||
91 | struct device_attribute *devattr, char *buf) | ||
92 | { | ||
93 | /* The minimum reference is 0 for this chip family */ | ||
94 | return sprintf(buf, "0\n"); | ||
95 | } | ||
96 | |||
97 | static ssize_t adcxx_show_max(struct device *dev, | ||
98 | struct device_attribute *devattr, char *buf) | ||
99 | { | ||
100 | struct spi_device *spi = to_spi_device(dev); | ||
101 | struct adcxx *adc = dev_get_drvdata(&spi->dev); | ||
102 | u32 reference; | ||
103 | |||
104 | if (mutex_lock_interruptible(&adc->lock)) | ||
105 | return -ERESTARTSYS; | ||
106 | |||
107 | reference = adc->reference; | ||
108 | |||
109 | mutex_unlock(&adc->lock); | ||
110 | |||
111 | return sprintf(buf, "%d\n", reference); | ||
112 | } | ||
113 | |||
114 | static ssize_t adcxx_set_max(struct device *dev, | ||
115 | struct device_attribute *devattr, const char *buf, size_t count) | ||
116 | { | ||
117 | struct spi_device *spi = to_spi_device(dev); | ||
118 | struct adcxx *adc = dev_get_drvdata(&spi->dev); | ||
119 | unsigned long value; | ||
120 | |||
121 | if (strict_strtoul(buf, 10, &value)) | ||
122 | return -EINVAL; | ||
123 | |||
124 | if (mutex_lock_interruptible(&adc->lock)) | ||
125 | return -ERESTARTSYS; | ||
126 | |||
127 | adc->reference = value; | ||
128 | |||
129 | mutex_unlock(&adc->lock); | ||
130 | |||
131 | return count; | ||
132 | } | ||
133 | |||
134 | static ssize_t adcxx_show_name(struct device *dev, struct device_attribute | ||
135 | *devattr, char *buf) | ||
136 | { | ||
137 | struct spi_device *spi = to_spi_device(dev); | ||
138 | struct adcxx *adc = dev_get_drvdata(&spi->dev); | ||
139 | |||
140 | return sprintf(buf, "adcxx%ds\n", adc->channels); | ||
141 | } | ||
142 | |||
143 | static struct sensor_device_attribute ad_input[] = { | ||
144 | SENSOR_ATTR(name, S_IRUGO, adcxx_show_name, NULL, 0), | ||
145 | SENSOR_ATTR(in_min, S_IRUGO, adcxx_show_min, NULL, 0), | ||
146 | SENSOR_ATTR(in_max, S_IWUSR | S_IRUGO, adcxx_show_max, | ||
147 | adcxx_set_max, 0), | ||
148 | SENSOR_ATTR(in0_input, S_IRUGO, adcxx_read, NULL, 0), | ||
149 | SENSOR_ATTR(in1_input, S_IRUGO, adcxx_read, NULL, 1), | ||
150 | SENSOR_ATTR(in2_input, S_IRUGO, adcxx_read, NULL, 2), | ||
151 | SENSOR_ATTR(in3_input, S_IRUGO, adcxx_read, NULL, 3), | ||
152 | SENSOR_ATTR(in4_input, S_IRUGO, adcxx_read, NULL, 4), | ||
153 | SENSOR_ATTR(in5_input, S_IRUGO, adcxx_read, NULL, 5), | ||
154 | SENSOR_ATTR(in6_input, S_IRUGO, adcxx_read, NULL, 6), | ||
155 | SENSOR_ATTR(in7_input, S_IRUGO, adcxx_read, NULL, 7), | ||
156 | }; | ||
157 | |||
158 | /*----------------------------------------------------------------------*/ | ||
159 | |||
160 | static int __devinit adcxx_probe(struct spi_device *spi, int channels) | ||
161 | { | ||
162 | struct adcxx *adc; | ||
163 | int status; | ||
164 | int i; | ||
165 | |||
166 | adc = kzalloc(sizeof *adc, GFP_KERNEL); | ||
167 | if (!adc) | ||
168 | return -ENOMEM; | ||
169 | |||
170 | /* set a default value for the reference */ | ||
171 | adc->reference = 3300; | ||
172 | adc->channels = channels; | ||
173 | mutex_init(&adc->lock); | ||
174 | |||
175 | mutex_lock(&adc->lock); | ||
176 | |||
177 | dev_set_drvdata(&spi->dev, adc); | ||
178 | |||
179 | for (i = 0; i < 3 + adc->channels; i++) { | ||
180 | status = device_create_file(&spi->dev, &ad_input[i].dev_attr); | ||
181 | if (status) { | ||
182 | dev_err(&spi->dev, "device_create_file failed.\n"); | ||
183 | goto out_err; | ||
184 | } | ||
185 | } | ||
186 | |||
187 | adc->hwmon_dev = hwmon_device_register(&spi->dev); | ||
188 | if (IS_ERR(adc->hwmon_dev)) { | ||
189 | dev_err(&spi->dev, "hwmon_device_register failed.\n"); | ||
190 | status = PTR_ERR(adc->hwmon_dev); | ||
191 | goto out_err; | ||
192 | } | ||
193 | |||
194 | mutex_unlock(&adc->lock); | ||
195 | return 0; | ||
196 | |||
197 | out_err: | ||
198 | for (i--; i >= 0; i--) | ||
199 | device_remove_file(&spi->dev, &ad_input[i].dev_attr); | ||
200 | |||
201 | dev_set_drvdata(&spi->dev, NULL); | ||
202 | mutex_unlock(&adc->lock); | ||
203 | kfree(adc); | ||
204 | return status; | ||
205 | } | ||
206 | |||
207 | static int __devinit adcxx1s_probe(struct spi_device *spi) | ||
208 | { | ||
209 | return adcxx_probe(spi, 1); | ||
210 | } | ||
211 | |||
212 | static int __devinit adcxx2s_probe(struct spi_device *spi) | ||
213 | { | ||
214 | return adcxx_probe(spi, 2); | ||
215 | } | ||
216 | |||
217 | static int __devinit adcxx4s_probe(struct spi_device *spi) | ||
218 | { | ||
219 | return adcxx_probe(spi, 4); | ||
220 | } | ||
221 | |||
222 | static int __devinit adcxx8s_probe(struct spi_device *spi) | ||
223 | { | ||
224 | return adcxx_probe(spi, 8); | ||
225 | } | ||
226 | |||
227 | static int __devexit adcxx_remove(struct spi_device *spi) | ||
228 | { | ||
229 | struct adcxx *adc = dev_get_drvdata(&spi->dev); | ||
230 | int i; | ||
231 | |||
232 | mutex_lock(&adc->lock); | ||
233 | hwmon_device_unregister(adc->hwmon_dev); | ||
234 | for (i = 0; i < 3 + adc->channels; i++) | ||
235 | device_remove_file(&spi->dev, &ad_input[i].dev_attr); | ||
236 | |||
237 | dev_set_drvdata(&spi->dev, NULL); | ||
238 | mutex_unlock(&adc->lock); | ||
239 | kfree(adc); | ||
240 | |||
241 | return 0; | ||
242 | } | ||
243 | |||
244 | static struct spi_driver adcxx1s_driver = { | ||
245 | .driver = { | ||
246 | .name = "adcxx1s", | ||
247 | .owner = THIS_MODULE, | ||
248 | }, | ||
249 | .probe = adcxx1s_probe, | ||
250 | .remove = __devexit_p(adcxx_remove), | ||
251 | }; | ||
252 | |||
253 | static struct spi_driver adcxx2s_driver = { | ||
254 | .driver = { | ||
255 | .name = "adcxx2s", | ||
256 | .owner = THIS_MODULE, | ||
257 | }, | ||
258 | .probe = adcxx2s_probe, | ||
259 | .remove = __devexit_p(adcxx_remove), | ||
260 | }; | ||
261 | |||
262 | static struct spi_driver adcxx4s_driver = { | ||
263 | .driver = { | ||
264 | .name = "adcxx4s", | ||
265 | .owner = THIS_MODULE, | ||
266 | }, | ||
267 | .probe = adcxx4s_probe, | ||
268 | .remove = __devexit_p(adcxx_remove), | ||
269 | }; | ||
270 | |||
271 | static struct spi_driver adcxx8s_driver = { | ||
272 | .driver = { | ||
273 | .name = "adcxx8s", | ||
274 | .owner = THIS_MODULE, | ||
275 | }, | ||
276 | .probe = adcxx8s_probe, | ||
277 | .remove = __devexit_p(adcxx_remove), | ||
278 | }; | ||
279 | |||
280 | static int __init init_adcxx(void) | ||
281 | { | ||
282 | int status; | ||
283 | status = spi_register_driver(&adcxx1s_driver); | ||
284 | if (status) | ||
285 | goto reg_1_failed; | ||
286 | |||
287 | status = spi_register_driver(&adcxx2s_driver); | ||
288 | if (status) | ||
289 | goto reg_2_failed; | ||
290 | |||
291 | status = spi_register_driver(&adcxx4s_driver); | ||
292 | if (status) | ||
293 | goto reg_4_failed; | ||
294 | |||
295 | status = spi_register_driver(&adcxx8s_driver); | ||
296 | if (status) | ||
297 | goto reg_8_failed; | ||
298 | |||
299 | return status; | ||
300 | |||
301 | reg_8_failed: | ||
302 | spi_unregister_driver(&adcxx4s_driver); | ||
303 | reg_4_failed: | ||
304 | spi_unregister_driver(&adcxx2s_driver); | ||
305 | reg_2_failed: | ||
306 | spi_unregister_driver(&adcxx1s_driver); | ||
307 | reg_1_failed: | ||
308 | return status; | ||
309 | } | ||
310 | |||
311 | static void __exit exit_adcxx(void) | ||
312 | { | ||
313 | spi_unregister_driver(&adcxx1s_driver); | ||
314 | spi_unregister_driver(&adcxx2s_driver); | ||
315 | spi_unregister_driver(&adcxx4s_driver); | ||
316 | spi_unregister_driver(&adcxx8s_driver); | ||
317 | } | ||
318 | |||
319 | module_init(init_adcxx); | ||
320 | module_exit(exit_adcxx); | ||
321 | |||
322 | MODULE_AUTHOR("Marc Pignat"); | ||
323 | MODULE_DESCRIPTION("National Semiconductor adcxx8sxxx Linux driver"); | ||
324 | MODULE_LICENSE("GPL"); | ||
325 | |||
326 | MODULE_ALIAS("adcxx1s"); | ||
327 | MODULE_ALIAS("adcxx2s"); | ||
328 | MODULE_ALIAS("adcxx4s"); | ||
329 | MODULE_ALIAS("adcxx8s"); | ||
diff --git a/drivers/hwmon/applesmc.c b/drivers/hwmon/applesmc.c index aacc0c4b809c..b06b8e090a27 100644 --- a/drivers/hwmon/applesmc.c +++ b/drivers/hwmon/applesmc.c | |||
@@ -98,6 +98,12 @@ static const char* temperature_sensors_sets[][36] = { | |||
98 | "TH1P", "TH2P", "TH3P", "TMAP", "TMAS", "TMBS", "TM0P", "TM0S", | 98 | "TH1P", "TH2P", "TH3P", "TMAP", "TMAS", "TMBS", "TM0P", "TM0S", |
99 | "TM1P", "TM1S", "TM2P", "TM2S", "TM3S", "TM8P", "TM8S", "TM9P", | 99 | "TM1P", "TM1S", "TM2P", "TM2S", "TM3S", "TM8P", "TM8S", "TM9P", |
100 | "TM9S", "TN0H", "TS0C", NULL }, | 100 | "TM9S", "TN0H", "TS0C", NULL }, |
101 | /* Set 5: iMac */ | ||
102 | { "TC0D", "TA0P", "TG0P", "TG0D", "TG0H", "TH0P", "Tm0P", "TO0P", | ||
103 | "Tp0C", NULL }, | ||
104 | /* Set 6: Macbook3 set */ | ||
105 | { "TB0T", "TC0D", "TC0P", "TM0P", "TN0P", "TTF0", "TW0P", "Th0H", | ||
106 | "Th0S", "Th1H", NULL }, | ||
101 | }; | 107 | }; |
102 | 108 | ||
103 | /* List of keys used to read/write fan speeds */ | 109 | /* List of keys used to read/write fan speeds */ |
@@ -1223,6 +1229,10 @@ static __initdata struct dmi_match_data applesmc_dmi_data[] = { | |||
1223 | { .accelerometer = 0, .light = 0, .temperature_set = 3 }, | 1229 | { .accelerometer = 0, .light = 0, .temperature_set = 3 }, |
1224 | /* MacPro: temperature set 4 */ | 1230 | /* MacPro: temperature set 4 */ |
1225 | { .accelerometer = 0, .light = 0, .temperature_set = 4 }, | 1231 | { .accelerometer = 0, .light = 0, .temperature_set = 4 }, |
1232 | /* iMac: temperature set 5 */ | ||
1233 | { .accelerometer = 0, .light = 0, .temperature_set = 5 }, | ||
1234 | /* MacBook3: accelerometer and temperature set 6 */ | ||
1235 | { .accelerometer = 1, .light = 0, .temperature_set = 6 }, | ||
1226 | }; | 1236 | }; |
1227 | 1237 | ||
1228 | /* Note that DMI_MATCH(...,"MacBook") will match "MacBookPro1,1". | 1238 | /* Note that DMI_MATCH(...,"MacBook") will match "MacBookPro1,1". |
@@ -1232,10 +1242,14 @@ static __initdata struct dmi_system_id applesmc_whitelist[] = { | |||
1232 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), | 1242 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), |
1233 | DMI_MATCH(DMI_PRODUCT_NAME,"MacBookPro") }, | 1243 | DMI_MATCH(DMI_PRODUCT_NAME,"MacBookPro") }, |
1234 | (void*)&applesmc_dmi_data[0]}, | 1244 | (void*)&applesmc_dmi_data[0]}, |
1235 | { applesmc_dmi_match, "Apple MacBook", { | 1245 | { applesmc_dmi_match, "Apple MacBook (v2)", { |
1236 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), | 1246 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), |
1237 | DMI_MATCH(DMI_PRODUCT_NAME,"MacBook2") }, | 1247 | DMI_MATCH(DMI_PRODUCT_NAME,"MacBook2") }, |
1238 | (void*)&applesmc_dmi_data[1]}, | 1248 | (void*)&applesmc_dmi_data[1]}, |
1249 | { applesmc_dmi_match, "Apple MacBook (v3)", { | ||
1250 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), | ||
1251 | DMI_MATCH(DMI_PRODUCT_NAME,"MacBook3") }, | ||
1252 | (void*)&applesmc_dmi_data[6]}, | ||
1239 | { applesmc_dmi_match, "Apple MacBook", { | 1253 | { applesmc_dmi_match, "Apple MacBook", { |
1240 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), | 1254 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), |
1241 | DMI_MATCH(DMI_PRODUCT_NAME,"MacBook") }, | 1255 | DMI_MATCH(DMI_PRODUCT_NAME,"MacBook") }, |
@@ -1248,6 +1262,10 @@ static __initdata struct dmi_system_id applesmc_whitelist[] = { | |||
1248 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), | 1262 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), |
1249 | DMI_MATCH(DMI_PRODUCT_NAME,"MacPro2") }, | 1263 | DMI_MATCH(DMI_PRODUCT_NAME,"MacPro2") }, |
1250 | (void*)&applesmc_dmi_data[4]}, | 1264 | (void*)&applesmc_dmi_data[4]}, |
1265 | { applesmc_dmi_match, "Apple iMac", { | ||
1266 | DMI_MATCH(DMI_BOARD_VENDOR,"Apple"), | ||
1267 | DMI_MATCH(DMI_PRODUCT_NAME,"iMac") }, | ||
1268 | (void*)&applesmc_dmi_data[5]}, | ||
1251 | { .ident = NULL } | 1269 | { .ident = NULL } |
1252 | }; | 1270 | }; |
1253 | 1271 | ||
diff --git a/drivers/hwmon/coretemp.c b/drivers/hwmon/coretemp.c index 70239acecc8e..93c17223b527 100644 --- a/drivers/hwmon/coretemp.c +++ b/drivers/hwmon/coretemp.c | |||
@@ -413,10 +413,11 @@ static int __init coretemp_init(void) | |||
413 | for_each_online_cpu(i) { | 413 | for_each_online_cpu(i) { |
414 | struct cpuinfo_x86 *c = &cpu_data(i); | 414 | struct cpuinfo_x86 *c = &cpu_data(i); |
415 | 415 | ||
416 | /* check if family 6, models 0xe, 0xf, 0x16, 0x17 */ | 416 | /* check if family 6, models 0xe, 0xf, 0x16, 0x17, 0x1A */ |
417 | if ((c->cpuid_level < 0) || (c->x86 != 0x6) || | 417 | if ((c->cpuid_level < 0) || (c->x86 != 0x6) || |
418 | !((c->x86_model == 0xe) || (c->x86_model == 0xf) || | 418 | !((c->x86_model == 0xe) || (c->x86_model == 0xf) || |
419 | (c->x86_model == 0x16) || (c->x86_model == 0x17))) { | 419 | (c->x86_model == 0x16) || (c->x86_model == 0x17) || |
420 | (c->x86_model == 0x1A))) { | ||
420 | 421 | ||
421 | /* supported CPU not found, but report the unknown | 422 | /* supported CPU not found, but report the unknown |
422 | family 6 CPU */ | 423 | family 6 CPU */ |
diff --git a/drivers/hwmon/hwmon-vid.c b/drivers/hwmon/hwmon-vid.c index 7b0a32c4dcfb..c54eff92be4a 100644 --- a/drivers/hwmon/hwmon-vid.c +++ b/drivers/hwmon/hwmon-vid.c | |||
@@ -37,13 +37,21 @@ | |||
37 | * For VRD 10.0 and up, "VRD x.y Design Guide", | 37 | * For VRD 10.0 and up, "VRD x.y Design Guide", |
38 | * available at http://developer.intel.com/. | 38 | * available at http://developer.intel.com/. |
39 | * | 39 | * |
40 | * AMD NPT 0Fh (Athlon64 & Opteron), AMD Publication 32559, | 40 | * AMD Athlon 64 and AMD Opteron Processors, AMD Publication 26094, |
41 | * http://www.amd.com/us-en/assets/content_type/white_papers_and_tech_docs/26094.PDF | ||
42 | * Table 74. VID Code Voltages | ||
43 | * This corresponds to an arbitrary VRM code of 24 in the functions below. | ||
44 | * These CPU models (K8 revision <= E) have 5 VID pins. See also: | ||
45 | * Revision Guide for AMD Athlon 64 and AMD Opteron Processors, AMD Publication 25759, | ||
46 | * http://www.amd.com/us-en/assets/content_type/white_papers_and_tech_docs/25759.pdf | ||
47 | * | ||
48 | * AMD NPT Family 0Fh Processors, AMD Publication 32559, | ||
41 | * http://www.amd.com/us-en/assets/content_type/white_papers_and_tech_docs/32559.pdf | 49 | * http://www.amd.com/us-en/assets/content_type/white_papers_and_tech_docs/32559.pdf |
42 | * Table 71. VID Code Voltages | 50 | * Table 71. VID Code Voltages |
43 | * AMD Opteron processors don't follow the Intel specifications. | 51 | * This corresponds to an arbitrary VRM code of 25 in the functions below. |
44 | * I'm going to "make up" 2.4 as the spec number for the Opterons. | 52 | * These CPU models (K8 revision >= F) have 6 VID pins. See also: |
45 | * No good reason just a mnemonic for the 24x Opteron processor | 53 | * Revision Guide for AMD NPT Family 0Fh Processors, AMD Publication 33610, |
46 | * series. | 54 | * http://www.amd.com/us-en/assets/content_type/white_papers_and_tech_docs/33610.pdf |
47 | * | 55 | * |
48 | * The 17 specification is in fact Intel Mobile Voltage Positioning - | 56 | * The 17 specification is in fact Intel Mobile Voltage Positioning - |
49 | * (IMVP-II). You can find more information in the datasheet of Max1718 | 57 | * (IMVP-II). You can find more information in the datasheet of Max1718 |
@@ -95,7 +103,12 @@ int vid_from_reg(int val, u8 vrm) | |||
95 | return 0; | 103 | return 0; |
96 | return((1600000 - (val - 2) * 6250 + 500) / 1000); | 104 | return((1600000 - (val - 2) * 6250 + 500) / 1000); |
97 | 105 | ||
98 | case 24: /* AMD NPT 0Fh (Athlon64 & Opteron) */ | 106 | case 24: /* Athlon64 & Opteron */ |
107 | val &= 0x1f; | ||
108 | if (val == 0x1f) | ||
109 | return 0; | ||
110 | /* fall through */ | ||
111 | case 25: /* AMD NPT 0Fh */ | ||
99 | val &= 0x3f; | 112 | val &= 0x3f; |
100 | return (val < 32) ? 1550 - 25 * val | 113 | return (val < 32) ? 1550 - 25 * val |
101 | : 775 - (25 * (val - 31)) / 2; | 114 | : 775 - (25 * (val - 31)) / 2; |
@@ -157,11 +170,16 @@ struct vrm_model { | |||
157 | 170 | ||
158 | #ifdef CONFIG_X86 | 171 | #ifdef CONFIG_X86 |
159 | 172 | ||
160 | /* the stepping parameter is highest acceptable stepping for current line */ | 173 | /* |
174 | * The stepping parameter is highest acceptable stepping for current line. | ||
175 | * The model match must be exact for 4-bit values. For model values 0x10 | ||
176 | * and above (extended model), all models below the parameter will match. | ||
177 | */ | ||
161 | 178 | ||
162 | static struct vrm_model vrm_models[] = { | 179 | static struct vrm_model vrm_models[] = { |
163 | {X86_VENDOR_AMD, 0x6, ANY, ANY, 90}, /* Athlon Duron etc */ | 180 | {X86_VENDOR_AMD, 0x6, ANY, ANY, 90}, /* Athlon Duron etc */ |
164 | {X86_VENDOR_AMD, 0xF, ANY, ANY, 24}, /* Athlon 64, Opteron and above VRM 24 */ | 181 | {X86_VENDOR_AMD, 0xF, 0x3F, ANY, 24}, /* Athlon 64, Opteron */ |
182 | {X86_VENDOR_AMD, 0xF, ANY, ANY, 25}, /* NPT family 0Fh */ | ||
165 | {X86_VENDOR_INTEL, 0x6, 0x9, ANY, 13}, /* Pentium M (130 nm) */ | 183 | {X86_VENDOR_INTEL, 0x6, 0x9, ANY, 13}, /* Pentium M (130 nm) */ |
166 | {X86_VENDOR_INTEL, 0x6, 0xB, ANY, 85}, /* Tualatin */ | 184 | {X86_VENDOR_INTEL, 0x6, 0xB, ANY, 85}, /* Tualatin */ |
167 | {X86_VENDOR_INTEL, 0x6, 0xD, ANY, 13}, /* Pentium M (90 nm) */ | 185 | {X86_VENDOR_INTEL, 0x6, 0xD, ANY, 13}, /* Pentium M (90 nm) */ |
@@ -189,6 +207,8 @@ static u8 find_vrm(u8 eff_family, u8 eff_model, u8 eff_stepping, u8 vendor) | |||
189 | if (vrm_models[i].vendor==vendor) | 207 | if (vrm_models[i].vendor==vendor) |
190 | if ((vrm_models[i].eff_family==eff_family) | 208 | if ((vrm_models[i].eff_family==eff_family) |
191 | && ((vrm_models[i].eff_model==eff_model) || | 209 | && ((vrm_models[i].eff_model==eff_model) || |
210 | (vrm_models[i].eff_model >= 0x10 && | ||
211 | eff_model <= vrm_models[i].eff_model) || | ||
192 | (vrm_models[i].eff_model==ANY)) && | 212 | (vrm_models[i].eff_model==ANY)) && |
193 | (eff_stepping <= vrm_models[i].eff_stepping)) | 213 | (eff_stepping <= vrm_models[i].eff_stepping)) |
194 | return vrm_models[i].vrm_type; | 214 | return vrm_models[i].vrm_type; |
diff --git a/drivers/hwmon/i5k_amb.c b/drivers/hwmon/i5k_amb.c index f9e2ed621f7b..2ede9388096b 100644 --- a/drivers/hwmon/i5k_amb.c +++ b/drivers/hwmon/i5k_amb.c | |||
@@ -81,6 +81,8 @@ static unsigned long amb_reg_temp(unsigned int amb) | |||
81 | #define MAX_AMBS_PER_CHANNEL 16 | 81 | #define MAX_AMBS_PER_CHANNEL 16 |
82 | #define MAX_AMBS (MAX_MEM_CHANNELS * \ | 82 | #define MAX_AMBS (MAX_MEM_CHANNELS * \ |
83 | MAX_AMBS_PER_CHANNEL) | 83 | MAX_AMBS_PER_CHANNEL) |
84 | #define CHANNEL_SHIFT 4 | ||
85 | #define DIMM_MASK 0xF | ||
84 | /* | 86 | /* |
85 | * Ugly hack: For some reason the highest bit is set if there | 87 | * Ugly hack: For some reason the highest bit is set if there |
86 | * are _any_ DIMMs in the channel. Attempting to read from | 88 | * are _any_ DIMMs in the channel. Attempting to read from |
@@ -89,7 +91,7 @@ static unsigned long amb_reg_temp(unsigned int amb) | |||
89 | * might prevent us from seeing the 16th DIMM in the channel. | 91 | * might prevent us from seeing the 16th DIMM in the channel. |
90 | */ | 92 | */ |
91 | #define REAL_MAX_AMBS_PER_CHANNEL 15 | 93 | #define REAL_MAX_AMBS_PER_CHANNEL 15 |
92 | #define KNOBS_PER_AMB 5 | 94 | #define KNOBS_PER_AMB 6 |
93 | 95 | ||
94 | static unsigned long amb_num_from_reg(unsigned int byte_num, unsigned int bit) | 96 | static unsigned long amb_num_from_reg(unsigned int byte_num, unsigned int bit) |
95 | { | 97 | { |
@@ -238,6 +240,16 @@ static ssize_t show_amb_temp(struct device *dev, | |||
238 | 500 * amb_read_byte(data, amb_reg_temp(attr->index))); | 240 | 500 * amb_read_byte(data, amb_reg_temp(attr->index))); |
239 | } | 241 | } |
240 | 242 | ||
243 | static ssize_t show_label(struct device *dev, | ||
244 | struct device_attribute *devattr, | ||
245 | char *buf) | ||
246 | { | ||
247 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | ||
248 | |||
249 | return sprintf(buf, "Ch. %d DIMM %d\n", attr->index >> CHANNEL_SHIFT, | ||
250 | attr->index & DIMM_MASK); | ||
251 | } | ||
252 | |||
241 | static int __devinit i5k_amb_hwmon_init(struct platform_device *pdev) | 253 | static int __devinit i5k_amb_hwmon_init(struct platform_device *pdev) |
242 | { | 254 | { |
243 | int i, j, k, d = 0; | 255 | int i, j, k, d = 0; |
@@ -268,6 +280,20 @@ static int __devinit i5k_amb_hwmon_init(struct platform_device *pdev) | |||
268 | continue; | 280 | continue; |
269 | d++; | 281 | d++; |
270 | 282 | ||
283 | /* sysfs label */ | ||
284 | iattr = data->attrs + data->num_attrs; | ||
285 | snprintf(iattr->name, AMB_SYSFS_NAME_LEN, | ||
286 | "temp%d_label", d); | ||
287 | iattr->s_attr.dev_attr.attr.name = iattr->name; | ||
288 | iattr->s_attr.dev_attr.attr.mode = S_IRUGO; | ||
289 | iattr->s_attr.dev_attr.show = show_label; | ||
290 | iattr->s_attr.index = k; | ||
291 | res = device_create_file(&pdev->dev, | ||
292 | &iattr->s_attr.dev_attr); | ||
293 | if (res) | ||
294 | goto exit_remove; | ||
295 | data->num_attrs++; | ||
296 | |||
271 | /* Temperature sysfs knob */ | 297 | /* Temperature sysfs knob */ |
272 | iattr = data->attrs + data->num_attrs; | 298 | iattr = data->attrs + data->num_attrs; |
273 | snprintf(iattr->name, AMB_SYSFS_NAME_LEN, | 299 | snprintf(iattr->name, AMB_SYSFS_NAME_LEN, |
diff --git a/drivers/hwmon/ibmaem.c b/drivers/hwmon/ibmaem.c index c9416e657487..0f70dc204105 100644 --- a/drivers/hwmon/ibmaem.c +++ b/drivers/hwmon/ibmaem.c | |||
@@ -1,6 +1,6 @@ | |||
1 | /* | 1 | /* |
2 | * A hwmon driver for the IBM Active Energy Manager temperature/power sensors | 2 | * A hwmon driver for the IBM System Director Active Energy Manager (AEM) |
3 | * and capping functionality. | 3 | * temperature/power/energy sensors and capping functionality. |
4 | * Copyright (C) 2008 IBM | 4 | * Copyright (C) 2008 IBM |
5 | * | 5 | * |
6 | * Author: Darrick J. Wong <djwong@us.ibm.com> | 6 | * Author: Darrick J. Wong <djwong@us.ibm.com> |
@@ -463,12 +463,18 @@ static int aem_read_sensor(struct aem_data *data, u8 elt, u8 reg, | |||
463 | } | 463 | } |
464 | 464 | ||
465 | /* Update AEM energy registers */ | 465 | /* Update AEM energy registers */ |
466 | static void update_aem_energy_one(struct aem_data *data, int which) | ||
467 | { | ||
468 | aem_read_sensor(data, AEM_ENERGY_ELEMENT, which, | ||
469 | &data->energy[which], 8); | ||
470 | } | ||
471 | |||
466 | static void update_aem_energy(struct aem_data *data) | 472 | static void update_aem_energy(struct aem_data *data) |
467 | { | 473 | { |
468 | aem_read_sensor(data, AEM_ENERGY_ELEMENT, 0, &data->energy[0], 8); | 474 | update_aem_energy_one(data, 0); |
469 | if (data->ver_major < 2) | 475 | if (data->ver_major < 2) |
470 | return; | 476 | return; |
471 | aem_read_sensor(data, AEM_ENERGY_ELEMENT, 1, &data->energy[1], 8); | 477 | update_aem_energy_one(data, 1); |
472 | } | 478 | } |
473 | 479 | ||
474 | /* Update all AEM1 sensors */ | 480 | /* Update all AEM1 sensors */ |
@@ -676,7 +682,8 @@ static int aem_find_aem2(struct aem_ipmi_data *data, | |||
676 | return -ETIMEDOUT; | 682 | return -ETIMEDOUT; |
677 | 683 | ||
678 | if (data->rx_result || data->rx_msg_len != sizeof(*fi_resp) || | 684 | if (data->rx_result || data->rx_msg_len != sizeof(*fi_resp) || |
679 | memcmp(&fi_resp->id, &system_x_id, sizeof(system_x_id))) | 685 | memcmp(&fi_resp->id, &system_x_id, sizeof(system_x_id)) || |
686 | fi_resp->num_instances <= instance_num) | ||
680 | return -ENOENT; | 687 | return -ENOENT; |
681 | 688 | ||
682 | return 0; | 689 | return 0; |
@@ -849,7 +856,7 @@ static ssize_t aem_show_power(struct device *dev, | |||
849 | struct timespec b, a; | 856 | struct timespec b, a; |
850 | 857 | ||
851 | mutex_lock(&data->lock); | 858 | mutex_lock(&data->lock); |
852 | update_aem_energy(data); | 859 | update_aem_energy_one(data, attr->index); |
853 | getnstimeofday(&b); | 860 | getnstimeofday(&b); |
854 | before = data->energy[attr->index]; | 861 | before = data->energy[attr->index]; |
855 | 862 | ||
@@ -861,7 +868,7 @@ static ssize_t aem_show_power(struct device *dev, | |||
861 | return 0; | 868 | return 0; |
862 | } | 869 | } |
863 | 870 | ||
864 | update_aem_energy(data); | 871 | update_aem_energy_one(data, attr->index); |
865 | getnstimeofday(&a); | 872 | getnstimeofday(&a); |
866 | after = data->energy[attr->index]; | 873 | after = data->energy[attr->index]; |
867 | mutex_unlock(&data->lock); | 874 | mutex_unlock(&data->lock); |
@@ -880,7 +887,9 @@ static ssize_t aem_show_energy(struct device *dev, | |||
880 | { | 887 | { |
881 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); | 888 | struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr); |
882 | struct aem_data *a = dev_get_drvdata(dev); | 889 | struct aem_data *a = dev_get_drvdata(dev); |
883 | a->update(a); | 890 | mutex_lock(&a->lock); |
891 | update_aem_energy_one(a, attr->index); | ||
892 | mutex_unlock(&a->lock); | ||
884 | 893 | ||
885 | return sprintf(buf, "%llu\n", | 894 | return sprintf(buf, "%llu\n", |
886 | (unsigned long long)a->energy[attr->index] * 1000); | 895 | (unsigned long long)a->energy[attr->index] * 1000); |
@@ -1104,7 +1113,7 @@ static void __exit aem_exit(void) | |||
1104 | } | 1113 | } |
1105 | 1114 | ||
1106 | MODULE_AUTHOR("Darrick J. Wong <djwong@us.ibm.com>"); | 1115 | MODULE_AUTHOR("Darrick J. Wong <djwong@us.ibm.com>"); |
1107 | MODULE_DESCRIPTION("IBM Active Energy Manager power/temp sensor driver"); | 1116 | MODULE_DESCRIPTION("IBM AEM power/temp/energy sensor driver"); |
1108 | MODULE_LICENSE("GPL"); | 1117 | MODULE_LICENSE("GPL"); |
1109 | 1118 | ||
1110 | module_init(aem_init); | 1119 | module_init(aem_init); |
diff --git a/drivers/hwmon/w83791d.c b/drivers/hwmon/w83791d.c index daa7d121483b..de21142d106c 100644 --- a/drivers/hwmon/w83791d.c +++ b/drivers/hwmon/w83791d.c | |||
@@ -1055,9 +1055,10 @@ static int w83791d_probe(struct i2c_client *client, | |||
1055 | { | 1055 | { |
1056 | struct w83791d_data *data; | 1056 | struct w83791d_data *data; |
1057 | struct device *dev = &client->dev; | 1057 | struct device *dev = &client->dev; |
1058 | int i, val1, err; | 1058 | int i, err; |
1059 | 1059 | ||
1060 | #ifdef DEBUG | 1060 | #ifdef DEBUG |
1061 | int val1; | ||
1061 | val1 = w83791d_read(client, W83791D_REG_DID_VID4); | 1062 | val1 = w83791d_read(client, W83791D_REG_DID_VID4); |
1062 | dev_dbg(dev, "Device ID version: %d.%d (0x%02x)\n", | 1063 | dev_dbg(dev, "Device ID version: %d.%d (0x%02x)\n", |
1063 | (val1 >> 5) & 0x07, (val1 >> 1) & 0x0f, val1); | 1064 | (val1 >> 5) & 0x07, (val1 >> 1) & 0x0f, val1); |