2 * drivers/hwmon/applesmc.c - driver for Apple's SMC (accelerometer, temperature
3 * sensors, fan control, keyboard backlight control) used in Intel-based Apple
6 * Copyright (C) 2007 Nicolas Boichat <nicolas@boichat.ch>
8 * Based on hdaps.c driver:
9 * Copyright (C) 2005 Robert Love <rml@novell.com>
10 * Copyright (C) 2005 Jesper Juhl <jesper.juhl@gmail.com>
12 * Fan control based on smcFanControl:
13 * Copyright (C) 2006 Hendrik Holtmann <holtmann@mac.com>
15 * This program is free software; you can redistribute it and/or modify it
16 * under the terms of the GNU General Public License v2 as published by the
17 * Free Software Foundation.
19 * This program is distributed in the hope that it will be useful, but WITHOUT
20 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
24 * You should have received a copy of the GNU General Public License along with
25 * this program; if not, write to the Free Software Foundation, Inc.,
26 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
29 #include <linux/delay.h>
30 #include <linux/platform_device.h>
31 #include <linux/input-polldev.h>
32 #include <linux/kernel.h>
33 #include <linux/module.h>
34 #include <linux/timer.h>
35 #include <linux/dmi.h>
36 #include <linux/mutex.h>
37 #include <linux/hwmon-sysfs.h>
39 #include <linux/leds.h>
40 #include <linux/hwmon.h>
41 #include <linux/workqueue.h>
43 /* data port used by Apple SMC */
44 #define APPLESMC_DATA_PORT 0x300
45 /* command/status port used by Apple SMC */
46 #define APPLESMC_CMD_PORT 0x304
48 #define APPLESMC_NR_PORTS 32 /* 0x300-0x31f */
50 #define APPLESMC_MAX_DATA_LENGTH 32
52 #define APPLESMC_MIN_WAIT 0x0040
53 #define APPLESMC_MAX_WAIT 0x8000
55 #define APPLESMC_STATUS_MASK 0x0f
56 #define APPLESMC_READ_CMD 0x10
57 #define APPLESMC_WRITE_CMD 0x11
58 #define APPLESMC_GET_KEY_BY_INDEX_CMD 0x12
59 #define APPLESMC_GET_KEY_TYPE_CMD 0x13
61 #define KEY_COUNT_KEY "#KEY" /* r-o ui32 */
63 #define LIGHT_SENSOR_LEFT_KEY "ALV0" /* r-o {alv (6-10 bytes) */
64 #define LIGHT_SENSOR_RIGHT_KEY "ALV1" /* r-o {alv (6-10 bytes) */
65 #define BACKLIGHT_KEY "LKSB" /* w-o {lkb (2 bytes) */
67 #define CLAMSHELL_KEY "MSLD" /* r-o ui8 (unused) */
69 #define MOTION_SENSOR_X_KEY "MO_X" /* r-o sp78 (2 bytes) */
70 #define MOTION_SENSOR_Y_KEY "MO_Y" /* r-o sp78 (2 bytes) */
71 #define MOTION_SENSOR_Z_KEY "MO_Z" /* r-o sp78 (2 bytes) */
72 #define MOTION_SENSOR_KEY "MOCN" /* r/w ui16 */
74 #define FANS_COUNT "FNum" /* r-o ui8 */
75 #define FANS_MANUAL "FS! " /* r-w ui16 */
76 #define FAN_ACTUAL_SPEED "F0Ac" /* r-o fpe2 (2 bytes) */
77 #define FAN_MIN_SPEED "F0Mn" /* r-o fpe2 (2 bytes) */
78 #define FAN_MAX_SPEED "F0Mx" /* r-o fpe2 (2 bytes) */
79 #define FAN_SAFE_SPEED "F0Sf" /* r-o fpe2 (2 bytes) */
80 #define FAN_TARGET_SPEED "F0Tg" /* r-w fpe2 (2 bytes) */
81 #define FAN_POSITION "F0ID" /* r-o char[16] */
84 * Temperature sensors keys (sp78 - 2 bytes).
86 static const char* temperature_sensors_sets[][36] = {
87 /* Set 0: Macbook Pro */
88 { "TA0P", "TB0T", "TC0D", "TC0P", "TG0H", "TG0P", "TG0T", "Th0H",
89 "Th1H", "Tm0P", "Ts0P", "Ts1P", NULL },
90 /* Set 1: Macbook2 set */
91 { "TB0T", "TC0D", "TC0P", "TM0P", "TN0P", "TN1P", "TTF0", "Th0H",
92 "Th0S", "Th1H", NULL },
93 /* Set 2: Macbook set */
94 { "TB0T", "TC0D", "TC0P", "TM0P", "TN0P", "TN1P", "Th0H", "Th0S",
95 "Th1H", "Ts0P", NULL },
96 /* Set 3: Macmini set */
97 { "TC0D", "TC0P", NULL },
98 /* Set 4: Mac Pro (2 x Quad-Core) */
99 { "TA0P", "TCAG", "TCAH", "TCBG", "TCBH", "TC0C", "TC0D", "TC0P",
100 "TC1C", "TC1D", "TC2C", "TC2D", "TC3C", "TC3D", "THTG", "TH0P",
101 "TH1P", "TH2P", "TH3P", "TMAP", "TMAS", "TMBS", "TM0P", "TM0S",
102 "TM1P", "TM1S", "TM2P", "TM2S", "TM3S", "TM8P", "TM8S", "TM9P",
103 "TM9S", "TN0H", "TS0C", NULL },
105 { "TC0D", "TA0P", "TG0P", "TG0D", "TG0H", "TH0P", "Tm0P", "TO0P",
107 /* Set 6: Macbook3 set */
108 { "TB0T", "TC0D", "TC0P", "TM0P", "TN0P", "TTF0", "TW0P", "Th0H",
109 "Th0S", "Th1H", NULL },
110 /* Set 7: Macbook Air */
111 { "TB0T", "TB1S", "TB1T", "TB2S", "TB2T", "TC0D", "TC0P", "TCFP",
112 "TTF0", "TW0P", "Th0H", "Tp0P", "TpFP", "Ts0P", "Ts0S", NULL },
113 /* Set 8: Macbook Pro 4,1 (Penryn) */
114 { "TB0T", "TC0D", "TC0P", "TG0D", "TG0H", "TTF0", "TW0P", "Th0H",
115 "Th1H", "Th2H", "Tm0P", "Ts0P", NULL },
116 /* Set 9: Macbook Pro 3,1 (Santa Rosa) */
117 { "TALP", "TB0T", "TC0D", "TC0P", "TG0D", "TG0H", "TTF0", "TW0P",
118 "Th0H", "Th1H", "Th2H", "Tm0P", "Ts0P", NULL },
119 /* Set 10: iMac 5,1 */
120 { "TA0P", "TC0D", "TC0P", "TG0D", "TH0P", "TO0P", "Tm0P", NULL },
121 /* Set 11: Macbook 5,1 */
122 { "TB0T", "TB1T", "TB2T", "TB3T", "TC0D", "TC0P", "TN0D", "TN0P",
123 "TTF0", "Th0H", "Th1H", "ThFH", "Ts0P", "Ts0S", NULL },
124 /* Set 12: Macbook Pro 5,1 */
125 { "TB0T", "TB1T", "TB2T", "TB3T", "TC0D", "TC0F", "TC0P", "TG0D",
126 "TG0F", "TG0H", "TG0P", "TG0T", "TG1H", "TN0D", "TN0P", "TTF0",
127 "Th2H", "Tm0P", "Ts0P", "Ts0S", NULL },
130 /* List of keys used to read/write fan speeds */
131 static const char* fan_speed_keys[] = {
139 #define INIT_TIMEOUT_MSECS 5000 /* wait up to 5s for device init ... */
140 #define INIT_WAIT_MSECS 50 /* ... in 50ms increments */
142 #define APPLESMC_POLL_INTERVAL 50 /* msecs */
143 #define APPLESMC_INPUT_FUZZ 4 /* input event threshold */
144 #define APPLESMC_INPUT_FLAT 4
150 /* Structure to be passed to DMI_MATCH function */
151 struct dmi_match_data {
152 /* Indicates whether this computer has an accelerometer. */
154 /* Indicates whether this computer has light sensors and keyboard backlight. */
156 /* Indicates which temperature sensors set to use. */
160 static const int debug;
161 static struct platform_device *pdev;
164 static struct device *hwmon_dev;
165 static struct input_polled_dev *applesmc_idev;
167 /* Indicates whether this computer has an accelerometer. */
168 static unsigned int applesmc_accelerometer;
170 /* Indicates whether this computer has light sensors and keyboard backlight. */
171 static unsigned int applesmc_light;
173 /* Indicates which temperature sensors set to use. */
174 static unsigned int applesmc_temperature_set;
176 static DEFINE_MUTEX(applesmc_lock);
179 * Last index written to key_at_index sysfs file, and value to use for all other
180 * key_at_index_* sysfs files.
182 static unsigned int key_at_index;
184 static struct workqueue_struct *applesmc_led_wq;
187 * __wait_status - Wait up to 32ms for the status port to get a certain value
188 * (masked with 0x0f), returning zero if the value is obtained. Callers must
189 * hold applesmc_lock.
191 static int __wait_status(u8 val)
195 val = val & APPLESMC_STATUS_MASK;
197 for (us = APPLESMC_MIN_WAIT; us < APPLESMC_MAX_WAIT; us <<= 1) {
199 if ((inb(APPLESMC_CMD_PORT) & APPLESMC_STATUS_MASK) == val) {
202 "Waited %d us for status %x\n",
203 2 * us - APPLESMC_MIN_WAIT, val);
208 printk(KERN_WARNING "applesmc: wait status failed: %x != %x\n",
209 val, inb(APPLESMC_CMD_PORT));
215 * special treatment of command port - on newer macbooks, it seems necessary
216 * to resend the command byte before polling the status again. Callers must
217 * hold applesmc_lock.
219 static int send_command(u8 cmd)
222 for (us = APPLESMC_MIN_WAIT; us < APPLESMC_MAX_WAIT; us <<= 1) {
223 outb(cmd, APPLESMC_CMD_PORT);
225 if ((inb(APPLESMC_CMD_PORT) & APPLESMC_STATUS_MASK) == 0x0c)
228 printk(KERN_WARNING "applesmc: command failed: %x -> %x\n",
229 cmd, inb(APPLESMC_CMD_PORT));
234 * applesmc_read_key - reads len bytes from a given key, and put them in buffer.
235 * Returns zero on success or a negative error on failure. Callers must
236 * hold applesmc_lock.
238 static int applesmc_read_key(const char* key, u8* buffer, u8 len)
242 if (len > APPLESMC_MAX_DATA_LENGTH) {
243 printk(KERN_ERR "applesmc_read_key: cannot read more than "
244 "%d bytes\n", APPLESMC_MAX_DATA_LENGTH);
248 if (send_command(APPLESMC_READ_CMD))
251 for (i = 0; i < 4; i++) {
252 outb(key[i], APPLESMC_DATA_PORT);
253 if (__wait_status(0x04))
257 printk(KERN_DEBUG "<%s", key);
259 outb(len, APPLESMC_DATA_PORT);
261 printk(KERN_DEBUG ">%x", len);
263 for (i = 0; i < len; i++) {
264 if (__wait_status(0x05))
266 buffer[i] = inb(APPLESMC_DATA_PORT);
268 printk(KERN_DEBUG "<%x", buffer[i]);
271 printk(KERN_DEBUG "\n");
277 * applesmc_write_key - writes len bytes from buffer to a given key.
278 * Returns zero on success or a negative error on failure. Callers must
279 * hold applesmc_lock.
281 static int applesmc_write_key(const char* key, u8* buffer, u8 len)
285 if (len > APPLESMC_MAX_DATA_LENGTH) {
286 printk(KERN_ERR "applesmc_write_key: cannot write more than "
287 "%d bytes\n", APPLESMC_MAX_DATA_LENGTH);
291 if (send_command(APPLESMC_WRITE_CMD))
294 for (i = 0; i < 4; i++) {
295 outb(key[i], APPLESMC_DATA_PORT);
296 if (__wait_status(0x04))
300 outb(len, APPLESMC_DATA_PORT);
302 for (i = 0; i < len; i++) {
303 if (__wait_status(0x04))
305 outb(buffer[i], APPLESMC_DATA_PORT);
312 * applesmc_get_key_at_index - get key at index, and put the result in key
313 * (char[6]). Returns zero on success or a negative error on failure. Callers
314 * must hold applesmc_lock.
316 static int applesmc_get_key_at_index(int index, char* key)
320 readkey[0] = index >> 24;
321 readkey[1] = index >> 16;
322 readkey[2] = index >> 8;
325 if (send_command(APPLESMC_GET_KEY_BY_INDEX_CMD))
328 for (i = 0; i < 4; i++) {
329 outb(readkey[i], APPLESMC_DATA_PORT);
330 if (__wait_status(0x04))
334 outb(4, APPLESMC_DATA_PORT);
336 for (i = 0; i < 4; i++) {
337 if (__wait_status(0x05))
339 key[i] = inb(APPLESMC_DATA_PORT);
347 * applesmc_get_key_type - get key type, and put the result in type (char[6]).
348 * Returns zero on success or a negative error on failure. Callers must
349 * hold applesmc_lock.
351 static int applesmc_get_key_type(char* key, char* type)
355 if (send_command(APPLESMC_GET_KEY_TYPE_CMD))
358 for (i = 0; i < 4; i++) {
359 outb(key[i], APPLESMC_DATA_PORT);
360 if (__wait_status(0x04))
364 outb(6, APPLESMC_DATA_PORT);
366 for (i = 0; i < 6; i++) {
367 if (__wait_status(0x05))
369 type[i] = inb(APPLESMC_DATA_PORT);
377 * applesmc_read_motion_sensor - Read motion sensor (X, Y or Z). Callers must
378 * hold applesmc_lock.
380 static int applesmc_read_motion_sensor(int index, s16* value)
387 ret = applesmc_read_key(MOTION_SENSOR_X_KEY, buffer, 2);
390 ret = applesmc_read_key(MOTION_SENSOR_Y_KEY, buffer, 2);
393 ret = applesmc_read_key(MOTION_SENSOR_Z_KEY, buffer, 2);
399 *value = ((s16)buffer[0] << 8) | buffer[1];
405 * applesmc_device_init - initialize the accelerometer. Returns zero on success
406 * and negative error code on failure. Can sleep.
408 static int applesmc_device_init(void)
410 int total, ret = -ENXIO;
413 if (!applesmc_accelerometer)
416 mutex_lock(&applesmc_lock);
418 for (total = INIT_TIMEOUT_MSECS; total > 0; total -= INIT_WAIT_MSECS) {
420 printk(KERN_DEBUG "applesmc try %d\n", total);
421 if (!applesmc_read_key(MOTION_SENSOR_KEY, buffer, 2) &&
422 (buffer[0] != 0x00 || buffer[1] != 0x00)) {
423 if (total == INIT_TIMEOUT_MSECS) {
424 printk(KERN_DEBUG "applesmc: device has"
425 " already been initialized"
426 " (0x%02x, 0x%02x).\n",
427 buffer[0], buffer[1]);
429 printk(KERN_DEBUG "applesmc: device"
430 " successfully initialized"
431 " (0x%02x, 0x%02x).\n",
432 buffer[0], buffer[1]);
439 applesmc_write_key(MOTION_SENSOR_KEY, buffer, 2);
440 msleep(INIT_WAIT_MSECS);
443 printk(KERN_WARNING "applesmc: failed to init the device\n");
446 mutex_unlock(&applesmc_lock);
451 * applesmc_get_fan_count - get the number of fans. Callers must NOT hold
454 static int applesmc_get_fan_count(void)
459 mutex_lock(&applesmc_lock);
461 ret = applesmc_read_key(FANS_COUNT, buffer, 1);
463 mutex_unlock(&applesmc_lock);
470 /* Device model stuff */
471 static int applesmc_probe(struct platform_device *dev)
475 ret = applesmc_device_init();
479 printk(KERN_INFO "applesmc: device successfully initialized.\n");
483 static int applesmc_resume(struct platform_device *dev)
485 return applesmc_device_init();
488 static struct platform_driver applesmc_driver = {
489 .probe = applesmc_probe,
490 .resume = applesmc_resume,
493 .owner = THIS_MODULE,
498 * applesmc_calibrate - Set our "resting" values. Callers must
499 * hold applesmc_lock.
501 static void applesmc_calibrate(void)
503 applesmc_read_motion_sensor(SENSOR_X, &rest_x);
504 applesmc_read_motion_sensor(SENSOR_Y, &rest_y);
508 static void applesmc_idev_poll(struct input_polled_dev *dev)
510 struct input_dev *idev = dev->input;
513 mutex_lock(&applesmc_lock);
515 if (applesmc_read_motion_sensor(SENSOR_X, &x))
517 if (applesmc_read_motion_sensor(SENSOR_Y, &y))
521 input_report_abs(idev, ABS_X, x - rest_x);
522 input_report_abs(idev, ABS_Y, y - rest_y);
526 mutex_unlock(&applesmc_lock);
531 static ssize_t applesmc_name_show(struct device *dev,
532 struct device_attribute *attr, char *buf)
534 return snprintf(buf, PAGE_SIZE, "applesmc\n");
537 static ssize_t applesmc_position_show(struct device *dev,
538 struct device_attribute *attr, char *buf)
543 mutex_lock(&applesmc_lock);
545 ret = applesmc_read_motion_sensor(SENSOR_X, &x);
548 ret = applesmc_read_motion_sensor(SENSOR_Y, &y);
551 ret = applesmc_read_motion_sensor(SENSOR_Z, &z);
556 mutex_unlock(&applesmc_lock);
560 return snprintf(buf, PAGE_SIZE, "(%d,%d,%d)\n", x, y, z);
563 static ssize_t applesmc_light_show(struct device *dev,
564 struct device_attribute *attr, char *sysfsbuf)
566 static int data_length;
568 u8 left = 0, right = 0;
569 u8 buffer[10], query[6];
571 mutex_lock(&applesmc_lock);
574 ret = applesmc_get_key_type(LIGHT_SENSOR_LEFT_KEY, query);
577 data_length = clamp_val(query[0], 0, 10);
578 printk(KERN_INFO "applesmc: light sensor data length set to "
579 "%d\n", data_length);
582 ret = applesmc_read_key(LIGHT_SENSOR_LEFT_KEY, buffer, data_length);
586 ret = applesmc_read_key(LIGHT_SENSOR_RIGHT_KEY, buffer, data_length);
590 mutex_unlock(&applesmc_lock);
594 return snprintf(sysfsbuf, PAGE_SIZE, "(%d,%d)\n", left, right);
597 /* Displays degree Celsius * 1000 */
598 static ssize_t applesmc_show_temperature(struct device *dev,
599 struct device_attribute *devattr, char *sysfsbuf)
604 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
606 temperature_sensors_sets[applesmc_temperature_set][attr->index];
608 mutex_lock(&applesmc_lock);
610 ret = applesmc_read_key(key, buffer, 2);
611 temp = buffer[0]*1000;
612 temp += (buffer[1] >> 6) * 250;
614 mutex_unlock(&applesmc_lock);
619 return snprintf(sysfsbuf, PAGE_SIZE, "%u\n", temp);
622 static ssize_t applesmc_show_fan_speed(struct device *dev,
623 struct device_attribute *attr, char *sysfsbuf)
626 unsigned int speed = 0;
629 struct sensor_device_attribute_2 *sensor_attr =
630 to_sensor_dev_attr_2(attr);
632 newkey[0] = fan_speed_keys[sensor_attr->nr][0];
633 newkey[1] = '0' + sensor_attr->index;
634 newkey[2] = fan_speed_keys[sensor_attr->nr][2];
635 newkey[3] = fan_speed_keys[sensor_attr->nr][3];
638 mutex_lock(&applesmc_lock);
640 ret = applesmc_read_key(newkey, buffer, 2);
641 speed = ((buffer[0] << 8 | buffer[1]) >> 2);
643 mutex_unlock(&applesmc_lock);
647 return snprintf(sysfsbuf, PAGE_SIZE, "%u\n", speed);
650 static ssize_t applesmc_store_fan_speed(struct device *dev,
651 struct device_attribute *attr,
652 const char *sysfsbuf, size_t count)
658 struct sensor_device_attribute_2 *sensor_attr =
659 to_sensor_dev_attr_2(attr);
661 speed = simple_strtoul(sysfsbuf, NULL, 10);
663 if (speed > 0x4000) /* Bigger than a 14-bit value */
666 newkey[0] = fan_speed_keys[sensor_attr->nr][0];
667 newkey[1] = '0' + sensor_attr->index;
668 newkey[2] = fan_speed_keys[sensor_attr->nr][2];
669 newkey[3] = fan_speed_keys[sensor_attr->nr][3];
672 mutex_lock(&applesmc_lock);
674 buffer[0] = (speed >> 6) & 0xff;
675 buffer[1] = (speed << 2) & 0xff;
676 ret = applesmc_write_key(newkey, buffer, 2);
678 mutex_unlock(&applesmc_lock);
685 static ssize_t applesmc_show_fan_manual(struct device *dev,
686 struct device_attribute *devattr, char *sysfsbuf)
691 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
693 mutex_lock(&applesmc_lock);
695 ret = applesmc_read_key(FANS_MANUAL, buffer, 2);
696 manual = ((buffer[0] << 8 | buffer[1]) >> attr->index) & 0x01;
698 mutex_unlock(&applesmc_lock);
702 return snprintf(sysfsbuf, PAGE_SIZE, "%d\n", manual);
705 static ssize_t applesmc_store_fan_manual(struct device *dev,
706 struct device_attribute *devattr,
707 const char *sysfsbuf, size_t count)
713 struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
715 input = simple_strtoul(sysfsbuf, NULL, 10);
717 mutex_lock(&applesmc_lock);
719 ret = applesmc_read_key(FANS_MANUAL, buffer, 2);
720 val = (buffer[0] << 8 | buffer[1]);
725 val = val | (0x01 << attr->index);
727 val = val & ~(0x01 << attr->index);
729 buffer[0] = (val >> 8) & 0xFF;
730 buffer[1] = val & 0xFF;
732 ret = applesmc_write_key(FANS_MANUAL, buffer, 2);
735 mutex_unlock(&applesmc_lock);
742 static ssize_t applesmc_show_fan_position(struct device *dev,
743 struct device_attribute *attr, char *sysfsbuf)
748 struct sensor_device_attribute_2 *sensor_attr =
749 to_sensor_dev_attr_2(attr);
751 newkey[0] = FAN_POSITION[0];
752 newkey[1] = '0' + sensor_attr->index;
753 newkey[2] = FAN_POSITION[2];
754 newkey[3] = FAN_POSITION[3];
757 mutex_lock(&applesmc_lock);
759 ret = applesmc_read_key(newkey, buffer, 16);
762 mutex_unlock(&applesmc_lock);
766 return snprintf(sysfsbuf, PAGE_SIZE, "%s\n", buffer+4);
769 static ssize_t applesmc_calibrate_show(struct device *dev,
770 struct device_attribute *attr, char *sysfsbuf)
772 return snprintf(sysfsbuf, PAGE_SIZE, "(%d,%d)\n", rest_x, rest_y);
775 static ssize_t applesmc_calibrate_store(struct device *dev,
776 struct device_attribute *attr, const char *sysfsbuf, size_t count)
778 mutex_lock(&applesmc_lock);
779 applesmc_calibrate();
780 mutex_unlock(&applesmc_lock);
785 /* Store the next backlight value to be written by the work */
786 static unsigned int backlight_value;
788 static void applesmc_backlight_set(struct work_struct *work)
792 mutex_lock(&applesmc_lock);
793 buffer[0] = backlight_value;
795 applesmc_write_key(BACKLIGHT_KEY, buffer, 2);
796 mutex_unlock(&applesmc_lock);
798 static DECLARE_WORK(backlight_work, &applesmc_backlight_set);
800 static void applesmc_brightness_set(struct led_classdev *led_cdev,
801 enum led_brightness value)
805 backlight_value = value;
806 ret = queue_work(applesmc_led_wq, &backlight_work);
809 printk(KERN_DEBUG "applesmc: work was already on the queue.\n");
812 static ssize_t applesmc_key_count_show(struct device *dev,
813 struct device_attribute *attr, char *sysfsbuf)
819 mutex_lock(&applesmc_lock);
821 ret = applesmc_read_key(KEY_COUNT_KEY, buffer, 4);
822 count = ((u32)buffer[0]<<24) + ((u32)buffer[1]<<16) +
823 ((u32)buffer[2]<<8) + buffer[3];
825 mutex_unlock(&applesmc_lock);
829 return snprintf(sysfsbuf, PAGE_SIZE, "%d\n", count);
832 static ssize_t applesmc_key_at_index_read_show(struct device *dev,
833 struct device_attribute *attr, char *sysfsbuf)
839 mutex_lock(&applesmc_lock);
841 ret = applesmc_get_key_at_index(key_at_index, key);
843 if (ret || !key[0]) {
844 mutex_unlock(&applesmc_lock);
849 ret = applesmc_get_key_type(key, info);
852 mutex_unlock(&applesmc_lock);
858 * info[0] maximum value (APPLESMC_MAX_DATA_LENGTH) is much lower than
859 * PAGE_SIZE, so we don't need any checks before writing to sysfsbuf.
861 ret = applesmc_read_key(key, sysfsbuf, info[0]);
863 mutex_unlock(&applesmc_lock);
872 static ssize_t applesmc_key_at_index_data_length_show(struct device *dev,
873 struct device_attribute *attr, char *sysfsbuf)
879 mutex_lock(&applesmc_lock);
881 ret = applesmc_get_key_at_index(key_at_index, key);
883 if (ret || !key[0]) {
884 mutex_unlock(&applesmc_lock);
889 ret = applesmc_get_key_type(key, info);
891 mutex_unlock(&applesmc_lock);
894 return snprintf(sysfsbuf, PAGE_SIZE, "%d\n", info[0]);
899 static ssize_t applesmc_key_at_index_type_show(struct device *dev,
900 struct device_attribute *attr, char *sysfsbuf)
906 mutex_lock(&applesmc_lock);
908 ret = applesmc_get_key_at_index(key_at_index, key);
910 if (ret || !key[0]) {
911 mutex_unlock(&applesmc_lock);
916 ret = applesmc_get_key_type(key, info);
918 mutex_unlock(&applesmc_lock);
921 return snprintf(sysfsbuf, PAGE_SIZE, "%s\n", info+1);
926 static ssize_t applesmc_key_at_index_name_show(struct device *dev,
927 struct device_attribute *attr, char *sysfsbuf)
932 mutex_lock(&applesmc_lock);
934 ret = applesmc_get_key_at_index(key_at_index, key);
936 mutex_unlock(&applesmc_lock);
939 return snprintf(sysfsbuf, PAGE_SIZE, "%s\n", key);
944 static ssize_t applesmc_key_at_index_show(struct device *dev,
945 struct device_attribute *attr, char *sysfsbuf)
947 return snprintf(sysfsbuf, PAGE_SIZE, "%d\n", key_at_index);
950 static ssize_t applesmc_key_at_index_store(struct device *dev,
951 struct device_attribute *attr, const char *sysfsbuf, size_t count)
953 mutex_lock(&applesmc_lock);
955 key_at_index = simple_strtoul(sysfsbuf, NULL, 10);
957 mutex_unlock(&applesmc_lock);
962 static struct led_classdev applesmc_backlight = {
963 .name = "smc::kbd_backlight",
964 .default_trigger = "nand-disk",
965 .brightness_set = applesmc_brightness_set,
968 static DEVICE_ATTR(name, 0444, applesmc_name_show, NULL);
970 static DEVICE_ATTR(position, 0444, applesmc_position_show, NULL);
971 static DEVICE_ATTR(calibrate, 0644,
972 applesmc_calibrate_show, applesmc_calibrate_store);
974 static struct attribute *accelerometer_attributes[] = {
975 &dev_attr_position.attr,
976 &dev_attr_calibrate.attr,
980 static const struct attribute_group accelerometer_attributes_group =
981 { .attrs = accelerometer_attributes };
983 static DEVICE_ATTR(light, 0444, applesmc_light_show, NULL);
985 static DEVICE_ATTR(key_count, 0444, applesmc_key_count_show, NULL);
986 static DEVICE_ATTR(key_at_index, 0644,
987 applesmc_key_at_index_show, applesmc_key_at_index_store);
988 static DEVICE_ATTR(key_at_index_name, 0444,
989 applesmc_key_at_index_name_show, NULL);
990 static DEVICE_ATTR(key_at_index_type, 0444,
991 applesmc_key_at_index_type_show, NULL);
992 static DEVICE_ATTR(key_at_index_data_length, 0444,
993 applesmc_key_at_index_data_length_show, NULL);
994 static DEVICE_ATTR(key_at_index_data, 0444,
995 applesmc_key_at_index_read_show, NULL);
997 static struct attribute *key_enumeration_attributes[] = {
998 &dev_attr_key_count.attr,
999 &dev_attr_key_at_index.attr,
1000 &dev_attr_key_at_index_name.attr,
1001 &dev_attr_key_at_index_type.attr,
1002 &dev_attr_key_at_index_data_length.attr,
1003 &dev_attr_key_at_index_data.attr,
1007 static const struct attribute_group key_enumeration_group =
1008 { .attrs = key_enumeration_attributes };
1011 * Macro defining SENSOR_DEVICE_ATTR for a fan sysfs entries.
1012 * - show actual speed
1013 * - show/store minimum speed
1014 * - show maximum speed
1016 * - show/store target speed
1017 * - show/store manual mode
1019 #define sysfs_fan_speeds_offset(offset) \
1020 static SENSOR_DEVICE_ATTR_2(fan##offset##_input, S_IRUGO, \
1021 applesmc_show_fan_speed, NULL, 0, offset-1); \
1023 static SENSOR_DEVICE_ATTR_2(fan##offset##_min, S_IRUGO | S_IWUSR, \
1024 applesmc_show_fan_speed, applesmc_store_fan_speed, 1, offset-1); \
1026 static SENSOR_DEVICE_ATTR_2(fan##offset##_max, S_IRUGO, \
1027 applesmc_show_fan_speed, NULL, 2, offset-1); \
1029 static SENSOR_DEVICE_ATTR_2(fan##offset##_safe, S_IRUGO, \
1030 applesmc_show_fan_speed, NULL, 3, offset-1); \
1032 static SENSOR_DEVICE_ATTR_2(fan##offset##_output, S_IRUGO | S_IWUSR, \
1033 applesmc_show_fan_speed, applesmc_store_fan_speed, 4, offset-1); \
1035 static SENSOR_DEVICE_ATTR(fan##offset##_manual, S_IRUGO | S_IWUSR, \
1036 applesmc_show_fan_manual, applesmc_store_fan_manual, offset-1); \
1038 static SENSOR_DEVICE_ATTR(fan##offset##_label, S_IRUGO, \
1039 applesmc_show_fan_position, NULL, offset-1); \
1041 static struct attribute *fan##offset##_attributes[] = { \
1042 &sensor_dev_attr_fan##offset##_input.dev_attr.attr, \
1043 &sensor_dev_attr_fan##offset##_min.dev_attr.attr, \
1044 &sensor_dev_attr_fan##offset##_max.dev_attr.attr, \
1045 &sensor_dev_attr_fan##offset##_safe.dev_attr.attr, \
1046 &sensor_dev_attr_fan##offset##_output.dev_attr.attr, \
1047 &sensor_dev_attr_fan##offset##_manual.dev_attr.attr, \
1048 &sensor_dev_attr_fan##offset##_label.dev_attr.attr, \
1053 * Create the needed functions for each fan using the macro defined above
1054 * (4 fans are supported)
1056 sysfs_fan_speeds_offset(1);
1057 sysfs_fan_speeds_offset(2);
1058 sysfs_fan_speeds_offset(3);
1059 sysfs_fan_speeds_offset(4);
1061 static const struct attribute_group fan_attribute_groups[] = {
1062 { .attrs = fan1_attributes },
1063 { .attrs = fan2_attributes },
1064 { .attrs = fan3_attributes },
1065 { .attrs = fan4_attributes },
1069 * Temperature sensors sysfs entries.
1071 static SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO,
1072 applesmc_show_temperature, NULL, 0);
1073 static SENSOR_DEVICE_ATTR(temp2_input, S_IRUGO,
1074 applesmc_show_temperature, NULL, 1);
1075 static SENSOR_DEVICE_ATTR(temp3_input, S_IRUGO,
1076 applesmc_show_temperature, NULL, 2);
1077 static SENSOR_DEVICE_ATTR(temp4_input, S_IRUGO,
1078 applesmc_show_temperature, NULL, 3);
1079 static SENSOR_DEVICE_ATTR(temp5_input, S_IRUGO,
1080 applesmc_show_temperature, NULL, 4);
1081 static SENSOR_DEVICE_ATTR(temp6_input, S_IRUGO,
1082 applesmc_show_temperature, NULL, 5);
1083 static SENSOR_DEVICE_ATTR(temp7_input, S_IRUGO,
1084 applesmc_show_temperature, NULL, 6);
1085 static SENSOR_DEVICE_ATTR(temp8_input, S_IRUGO,
1086 applesmc_show_temperature, NULL, 7);
1087 static SENSOR_DEVICE_ATTR(temp9_input, S_IRUGO,
1088 applesmc_show_temperature, NULL, 8);
1089 static SENSOR_DEVICE_ATTR(temp10_input, S_IRUGO,
1090 applesmc_show_temperature, NULL, 9);
1091 static SENSOR_DEVICE_ATTR(temp11_input, S_IRUGO,
1092 applesmc_show_temperature, NULL, 10);
1093 static SENSOR_DEVICE_ATTR(temp12_input, S_IRUGO,
1094 applesmc_show_temperature, NULL, 11);
1095 static SENSOR_DEVICE_ATTR(temp13_input, S_IRUGO,
1096 applesmc_show_temperature, NULL, 12);
1097 static SENSOR_DEVICE_ATTR(temp14_input, S_IRUGO,
1098 applesmc_show_temperature, NULL, 13);
1099 static SENSOR_DEVICE_ATTR(temp15_input, S_IRUGO,
1100 applesmc_show_temperature, NULL, 14);
1101 static SENSOR_DEVICE_ATTR(temp16_input, S_IRUGO,
1102 applesmc_show_temperature, NULL, 15);
1103 static SENSOR_DEVICE_ATTR(temp17_input, S_IRUGO,
1104 applesmc_show_temperature, NULL, 16);
1105 static SENSOR_DEVICE_ATTR(temp18_input, S_IRUGO,
1106 applesmc_show_temperature, NULL, 17);
1107 static SENSOR_DEVICE_ATTR(temp19_input, S_IRUGO,
1108 applesmc_show_temperature, NULL, 18);
1109 static SENSOR_DEVICE_ATTR(temp20_input, S_IRUGO,
1110 applesmc_show_temperature, NULL, 19);
1111 static SENSOR_DEVICE_ATTR(temp21_input, S_IRUGO,
1112 applesmc_show_temperature, NULL, 20);
1113 static SENSOR_DEVICE_ATTR(temp22_input, S_IRUGO,
1114 applesmc_show_temperature, NULL, 21);
1115 static SENSOR_DEVICE_ATTR(temp23_input, S_IRUGO,
1116 applesmc_show_temperature, NULL, 22);
1117 static SENSOR_DEVICE_ATTR(temp24_input, S_IRUGO,
1118 applesmc_show_temperature, NULL, 23);
1119 static SENSOR_DEVICE_ATTR(temp25_input, S_IRUGO,
1120 applesmc_show_temperature, NULL, 24);
1121 static SENSOR_DEVICE_ATTR(temp26_input, S_IRUGO,
1122 applesmc_show_temperature, NULL, 25);
1123 static SENSOR_DEVICE_ATTR(temp27_input, S_IRUGO,
1124 applesmc_show_temperature, NULL, 26);
1125 static SENSOR_DEVICE_ATTR(temp28_input, S_IRUGO,
1126 applesmc_show_temperature, NULL, 27);
1127 static SENSOR_DEVICE_ATTR(temp29_input, S_IRUGO,
1128 applesmc_show_temperature, NULL, 28);
1129 static SENSOR_DEVICE_ATTR(temp30_input, S_IRUGO,
1130 applesmc_show_temperature, NULL, 29);
1131 static SENSOR_DEVICE_ATTR(temp31_input, S_IRUGO,
1132 applesmc_show_temperature, NULL, 30);
1133 static SENSOR_DEVICE_ATTR(temp32_input, S_IRUGO,
1134 applesmc_show_temperature, NULL, 31);
1135 static SENSOR_DEVICE_ATTR(temp33_input, S_IRUGO,
1136 applesmc_show_temperature, NULL, 32);
1137 static SENSOR_DEVICE_ATTR(temp34_input, S_IRUGO,
1138 applesmc_show_temperature, NULL, 33);
1139 static SENSOR_DEVICE_ATTR(temp35_input, S_IRUGO,
1140 applesmc_show_temperature, NULL, 34);
1142 static struct attribute *temperature_attributes[] = {
1143 &sensor_dev_attr_temp1_input.dev_attr.attr,
1144 &sensor_dev_attr_temp2_input.dev_attr.attr,
1145 &sensor_dev_attr_temp3_input.dev_attr.attr,
1146 &sensor_dev_attr_temp4_input.dev_attr.attr,
1147 &sensor_dev_attr_temp5_input.dev_attr.attr,
1148 &sensor_dev_attr_temp6_input.dev_attr.attr,
1149 &sensor_dev_attr_temp7_input.dev_attr.attr,
1150 &sensor_dev_attr_temp8_input.dev_attr.attr,
1151 &sensor_dev_attr_temp9_input.dev_attr.attr,
1152 &sensor_dev_attr_temp10_input.dev_attr.attr,
1153 &sensor_dev_attr_temp11_input.dev_attr.attr,
1154 &sensor_dev_attr_temp12_input.dev_attr.attr,
1155 &sensor_dev_attr_temp13_input.dev_attr.attr,
1156 &sensor_dev_attr_temp14_input.dev_attr.attr,
1157 &sensor_dev_attr_temp15_input.dev_attr.attr,
1158 &sensor_dev_attr_temp16_input.dev_attr.attr,
1159 &sensor_dev_attr_temp17_input.dev_attr.attr,
1160 &sensor_dev_attr_temp18_input.dev_attr.attr,
1161 &sensor_dev_attr_temp19_input.dev_attr.attr,
1162 &sensor_dev_attr_temp20_input.dev_attr.attr,
1163 &sensor_dev_attr_temp21_input.dev_attr.attr,
1164 &sensor_dev_attr_temp22_input.dev_attr.attr,
1165 &sensor_dev_attr_temp23_input.dev_attr.attr,
1166 &sensor_dev_attr_temp24_input.dev_attr.attr,
1167 &sensor_dev_attr_temp25_input.dev_attr.attr,
1168 &sensor_dev_attr_temp26_input.dev_attr.attr,
1169 &sensor_dev_attr_temp27_input.dev_attr.attr,
1170 &sensor_dev_attr_temp28_input.dev_attr.attr,
1171 &sensor_dev_attr_temp29_input.dev_attr.attr,
1172 &sensor_dev_attr_temp30_input.dev_attr.attr,
1173 &sensor_dev_attr_temp31_input.dev_attr.attr,
1174 &sensor_dev_attr_temp32_input.dev_attr.attr,
1175 &sensor_dev_attr_temp33_input.dev_attr.attr,
1176 &sensor_dev_attr_temp34_input.dev_attr.attr,
1177 &sensor_dev_attr_temp35_input.dev_attr.attr,
1181 static const struct attribute_group temperature_attributes_group =
1182 { .attrs = temperature_attributes };
1187 * applesmc_dmi_match - found a match. return one, short-circuiting the hunt.
1189 static int applesmc_dmi_match(const struct dmi_system_id *id)
1192 struct dmi_match_data* dmi_data = id->driver_data;
1193 printk(KERN_INFO "applesmc: %s detected:\n", id->ident);
1194 applesmc_accelerometer = dmi_data->accelerometer;
1195 printk(KERN_INFO "applesmc: - Model %s accelerometer\n",
1196 applesmc_accelerometer ? "with" : "without");
1197 applesmc_light = dmi_data->light;
1198 printk(KERN_INFO "applesmc: - Model %s light sensors and backlight\n",
1199 applesmc_light ? "with" : "without");
1201 applesmc_temperature_set = dmi_data->temperature_set;
1202 while (temperature_sensors_sets[applesmc_temperature_set][i] != NULL)
1204 printk(KERN_INFO "applesmc: - Model with %d temperature sensors\n", i);
1208 /* Create accelerometer ressources */
1209 static int applesmc_create_accelerometer(void)
1211 struct input_dev *idev;
1214 ret = sysfs_create_group(&pdev->dev.kobj,
1215 &accelerometer_attributes_group);
1219 applesmc_idev = input_allocate_polled_device();
1220 if (!applesmc_idev) {
1225 applesmc_idev->poll = applesmc_idev_poll;
1226 applesmc_idev->poll_interval = APPLESMC_POLL_INTERVAL;
1228 /* initial calibrate for the input device */
1229 applesmc_calibrate();
1231 /* initialize the input device */
1232 idev = applesmc_idev->input;
1233 idev->name = "applesmc";
1234 idev->id.bustype = BUS_HOST;
1235 idev->dev.parent = &pdev->dev;
1236 idev->evbit[0] = BIT_MASK(EV_ABS);
1237 input_set_abs_params(idev, ABS_X,
1238 -256, 256, APPLESMC_INPUT_FUZZ, APPLESMC_INPUT_FLAT);
1239 input_set_abs_params(idev, ABS_Y,
1240 -256, 256, APPLESMC_INPUT_FUZZ, APPLESMC_INPUT_FLAT);
1242 ret = input_register_polled_device(applesmc_idev);
1249 input_free_polled_device(applesmc_idev);
1252 sysfs_remove_group(&pdev->dev.kobj, &accelerometer_attributes_group);
1255 printk(KERN_WARNING "applesmc: driver init failed (ret=%d)!\n", ret);
1259 /* Release all ressources used by the accelerometer */
1260 static void applesmc_release_accelerometer(void)
1262 input_unregister_polled_device(applesmc_idev);
1263 input_free_polled_device(applesmc_idev);
1264 sysfs_remove_group(&pdev->dev.kobj, &accelerometer_attributes_group);
1267 static __initdata struct dmi_match_data applesmc_dmi_data[] = {
1268 /* MacBook Pro: accelerometer, backlight and temperature set 0 */
1269 { .accelerometer = 1, .light = 1, .temperature_set = 0 },
1270 /* MacBook2: accelerometer and temperature set 1 */
1271 { .accelerometer = 1, .light = 0, .temperature_set = 1 },
1272 /* MacBook: accelerometer and temperature set 2 */
1273 { .accelerometer = 1, .light = 0, .temperature_set = 2 },
1274 /* MacMini: temperature set 3 */
1275 { .accelerometer = 0, .light = 0, .temperature_set = 3 },
1276 /* MacPro: temperature set 4 */
1277 { .accelerometer = 0, .light = 0, .temperature_set = 4 },
1278 /* iMac: temperature set 5 */
1279 { .accelerometer = 0, .light = 0, .temperature_set = 5 },
1280 /* MacBook3: accelerometer and temperature set 6 */
1281 { .accelerometer = 1, .light = 0, .temperature_set = 6 },
1282 /* MacBook Air: accelerometer, backlight and temperature set 7 */
1283 { .accelerometer = 1, .light = 1, .temperature_set = 7 },
1284 /* MacBook Pro 4: accelerometer, backlight and temperature set 8 */
1285 { .accelerometer = 1, .light = 1, .temperature_set = 8 },
1286 /* MacBook Pro 3: accelerometer, backlight and temperature set 9 */
1287 { .accelerometer = 1, .light = 1, .temperature_set = 9 },
1288 /* iMac 5: light sensor only, temperature set 10 */
1289 { .accelerometer = 0, .light = 0, .temperature_set = 10 },
1290 /* MacBook 5: accelerometer, backlight and temperature set 11 */
1291 { .accelerometer = 1, .light = 1, .temperature_set = 11 },
1292 /* MacBook Pro 5: accelerometer, backlight and temperature set 12 */
1293 { .accelerometer = 1, .light = 1, .temperature_set = 12 },
1296 /* Note that DMI_MATCH(...,"MacBook") will match "MacBookPro1,1".
1297 * So we need to put "Apple MacBook Pro" before "Apple MacBook". */
1298 static __initdata struct dmi_system_id applesmc_whitelist[] = {
1299 { applesmc_dmi_match, "Apple MacBook Air", {
1300 DMI_MATCH(DMI_BOARD_VENDOR, "Apple"),
1301 DMI_MATCH(DMI_PRODUCT_NAME, "MacBookAir") },
1302 &applesmc_dmi_data[7]},
1303 { applesmc_dmi_match, "Apple MacBook Pro 5", {
1304 DMI_MATCH(DMI_BOARD_VENDOR, "Apple"),
1305 DMI_MATCH(DMI_PRODUCT_NAME, "MacBookPro5") },
1306 &applesmc_dmi_data[12]},
1307 { applesmc_dmi_match, "Apple MacBook Pro 4", {
1308 DMI_MATCH(DMI_BOARD_VENDOR, "Apple"),
1309 DMI_MATCH(DMI_PRODUCT_NAME, "MacBookPro4") },
1310 &applesmc_dmi_data[8]},
1311 { applesmc_dmi_match, "Apple MacBook Pro 3", {
1312 DMI_MATCH(DMI_BOARD_VENDOR, "Apple"),
1313 DMI_MATCH(DMI_PRODUCT_NAME, "MacBookPro3") },
1314 &applesmc_dmi_data[9]},
1315 { applesmc_dmi_match, "Apple MacBook Pro", {
1316 DMI_MATCH(DMI_BOARD_VENDOR,"Apple"),
1317 DMI_MATCH(DMI_PRODUCT_NAME,"MacBookPro") },
1318 &applesmc_dmi_data[0]},
1319 { applesmc_dmi_match, "Apple MacBook (v2)", {
1320 DMI_MATCH(DMI_BOARD_VENDOR,"Apple"),
1321 DMI_MATCH(DMI_PRODUCT_NAME,"MacBook2") },
1322 &applesmc_dmi_data[1]},
1323 { applesmc_dmi_match, "Apple MacBook (v3)", {
1324 DMI_MATCH(DMI_BOARD_VENDOR,"Apple"),
1325 DMI_MATCH(DMI_PRODUCT_NAME,"MacBook3") },
1326 &applesmc_dmi_data[6]},
1327 { applesmc_dmi_match, "Apple MacBook 5", {
1328 DMI_MATCH(DMI_BOARD_VENDOR, "Apple"),
1329 DMI_MATCH(DMI_PRODUCT_NAME, "MacBook5") },
1330 &applesmc_dmi_data[11]},
1331 { applesmc_dmi_match, "Apple MacBook", {
1332 DMI_MATCH(DMI_BOARD_VENDOR,"Apple"),
1333 DMI_MATCH(DMI_PRODUCT_NAME,"MacBook") },
1334 &applesmc_dmi_data[2]},
1335 { applesmc_dmi_match, "Apple Macmini", {
1336 DMI_MATCH(DMI_BOARD_VENDOR,"Apple"),
1337 DMI_MATCH(DMI_PRODUCT_NAME,"Macmini") },
1338 &applesmc_dmi_data[3]},
1339 { applesmc_dmi_match, "Apple MacPro2", {
1340 DMI_MATCH(DMI_BOARD_VENDOR,"Apple"),
1341 DMI_MATCH(DMI_PRODUCT_NAME,"MacPro2") },
1342 &applesmc_dmi_data[4]},
1343 { applesmc_dmi_match, "Apple iMac 5", {
1344 DMI_MATCH(DMI_BOARD_VENDOR, "Apple"),
1345 DMI_MATCH(DMI_PRODUCT_NAME, "iMac5") },
1346 &applesmc_dmi_data[10]},
1347 { applesmc_dmi_match, "Apple iMac", {
1348 DMI_MATCH(DMI_BOARD_VENDOR,"Apple"),
1349 DMI_MATCH(DMI_PRODUCT_NAME,"iMac") },
1350 &applesmc_dmi_data[5]},
1354 static int __init applesmc_init(void)
1360 if (!dmi_check_system(applesmc_whitelist)) {
1361 printk(KERN_WARNING "applesmc: supported laptop not found!\n");
1366 if (!request_region(APPLESMC_DATA_PORT, APPLESMC_NR_PORTS,
1372 ret = platform_driver_register(&applesmc_driver);
1376 pdev = platform_device_register_simple("applesmc", APPLESMC_DATA_PORT,
1379 ret = PTR_ERR(pdev);
1383 ret = sysfs_create_file(&pdev->dev.kobj, &dev_attr_name.attr);
1387 /* Create key enumeration sysfs files */
1388 ret = sysfs_create_group(&pdev->dev.kobj, &key_enumeration_group);
1392 /* create fan files */
1393 count = applesmc_get_fan_count();
1395 printk(KERN_ERR "applesmc: Cannot get the number of fans.\n");
1397 printk(KERN_INFO "applesmc: %d fans found.\n", count);
1401 printk(KERN_WARNING "applesmc: More than 4 fans found,"
1402 " but at most 4 fans are supported"
1403 " by the driver.\n");
1405 ret = sysfs_create_group(&pdev->dev.kobj,
1406 &fan_attribute_groups[3]);
1408 goto out_key_enumeration;
1410 ret = sysfs_create_group(&pdev->dev.kobj,
1411 &fan_attribute_groups[2]);
1413 goto out_key_enumeration;
1415 ret = sysfs_create_group(&pdev->dev.kobj,
1416 &fan_attribute_groups[1]);
1418 goto out_key_enumeration;
1420 ret = sysfs_create_group(&pdev->dev.kobj,
1421 &fan_attribute_groups[0]);
1430 temperature_sensors_sets[applesmc_temperature_set][i] != NULL;
1432 if (temperature_attributes[i] == NULL) {
1433 printk(KERN_ERR "applesmc: More temperature sensors "
1434 "in temperature_sensors_sets (at least %i)"
1435 "than available sysfs files in "
1436 "temperature_attributes (%i), please report "
1437 "this bug.\n", i, i-1);
1438 goto out_temperature;
1440 ret = sysfs_create_file(&pdev->dev.kobj,
1441 temperature_attributes[i]);
1443 goto out_temperature;
1446 if (applesmc_accelerometer) {
1447 ret = applesmc_create_accelerometer();
1449 goto out_temperature;
1452 if (applesmc_light) {
1453 /* Add light sensor file */
1454 ret = sysfs_create_file(&pdev->dev.kobj, &dev_attr_light.attr);
1456 goto out_accelerometer;
1458 /* Create the workqueue */
1459 applesmc_led_wq = create_singlethread_workqueue("applesmc-led");
1460 if (!applesmc_led_wq) {
1462 goto out_light_sysfs;
1465 /* register as a led device */
1466 ret = led_classdev_register(&pdev->dev, &applesmc_backlight);
1471 hwmon_dev = hwmon_device_register(&pdev->dev);
1472 if (IS_ERR(hwmon_dev)) {
1473 ret = PTR_ERR(hwmon_dev);
1474 goto out_light_ledclass;
1477 printk(KERN_INFO "applesmc: driver successfully loaded.\n");
1483 led_classdev_unregister(&applesmc_backlight);
1486 destroy_workqueue(applesmc_led_wq);
1489 sysfs_remove_file(&pdev->dev.kobj, &dev_attr_light.attr);
1491 if (applesmc_accelerometer)
1492 applesmc_release_accelerometer();
1494 sysfs_remove_group(&pdev->dev.kobj, &temperature_attributes_group);
1495 sysfs_remove_group(&pdev->dev.kobj, &fan_attribute_groups[0]);
1497 sysfs_remove_group(&pdev->dev.kobj, &fan_attribute_groups[1]);
1498 out_key_enumeration:
1499 sysfs_remove_group(&pdev->dev.kobj, &key_enumeration_group);
1501 sysfs_remove_file(&pdev->dev.kobj, &dev_attr_name.attr);
1503 platform_device_unregister(pdev);
1505 platform_driver_unregister(&applesmc_driver);
1507 release_region(APPLESMC_DATA_PORT, APPLESMC_NR_PORTS);
1509 printk(KERN_WARNING "applesmc: driver init failed (ret=%d)!\n", ret);
1513 static void __exit applesmc_exit(void)
1515 hwmon_device_unregister(hwmon_dev);
1516 if (applesmc_light) {
1517 led_classdev_unregister(&applesmc_backlight);
1518 destroy_workqueue(applesmc_led_wq);
1519 sysfs_remove_file(&pdev->dev.kobj, &dev_attr_light.attr);
1521 if (applesmc_accelerometer)
1522 applesmc_release_accelerometer();
1523 sysfs_remove_group(&pdev->dev.kobj, &temperature_attributes_group);
1524 sysfs_remove_group(&pdev->dev.kobj, &fan_attribute_groups[0]);
1525 sysfs_remove_group(&pdev->dev.kobj, &fan_attribute_groups[1]);
1526 sysfs_remove_group(&pdev->dev.kobj, &key_enumeration_group);
1527 sysfs_remove_file(&pdev->dev.kobj, &dev_attr_name.attr);
1528 platform_device_unregister(pdev);
1529 platform_driver_unregister(&applesmc_driver);
1530 release_region(APPLESMC_DATA_PORT, APPLESMC_NR_PORTS);
1532 printk(KERN_INFO "applesmc: driver unloaded.\n");
1535 module_init(applesmc_init);
1536 module_exit(applesmc_exit);
1538 MODULE_AUTHOR("Nicolas Boichat");
1539 MODULE_DESCRIPTION("Apple SMC");
1540 MODULE_LICENSE("GPL v2");