diff options
author | Henrik Rydberg <rydberg@euromail.se> | 2012-07-16 03:18:11 -0400 |
---|---|---|
committer | Guenter Roeck <linux@roeck-us.net> | 2012-07-22 00:48:45 -0400 |
commit | e30bca12573fbf54e2470723aadc047549d147ce (patch) | |
tree | fa5e6142841c7c2d7fc42ea29a8aa1a35ee3f94c /drivers/hwmon/applesmc.c | |
parent | b6e5122f09272cb30c2e1fc1d80a40bfa6e87757 (diff) |
hwmon: (applesmc) Ignore some temperature registers
Not all sensors in the T range are useful temperatures. This patch
creates a subset of sensors to be exported to userland, excluding the
unknown types.
Signed-off-by: Henrik Rydberg <rydberg@euromail.se>
Signed-off-by: Guenter Roeck <linux@roeck-us.net>
Diffstat (limited to 'drivers/hwmon/applesmc.c')
-rw-r--r-- | drivers/hwmon/applesmc.c | 75 |
1 files changed, 47 insertions, 28 deletions
diff --git a/drivers/hwmon/applesmc.c b/drivers/hwmon/applesmc.c index 75f87f125dac..4d937a18fadb 100644 --- a/drivers/hwmon/applesmc.c +++ b/drivers/hwmon/applesmc.c | |||
@@ -133,11 +133,13 @@ static struct applesmc_registers { | |||
133 | unsigned int temp_count; /* number of temperature registers */ | 133 | unsigned int temp_count; /* number of temperature registers */ |
134 | unsigned int temp_begin; /* temperature lower index bound */ | 134 | unsigned int temp_begin; /* temperature lower index bound */ |
135 | unsigned int temp_end; /* temperature upper index bound */ | 135 | unsigned int temp_end; /* temperature upper index bound */ |
136 | unsigned int index_count; /* size of temperature index array */ | ||
136 | int num_light_sensors; /* number of light sensors */ | 137 | int num_light_sensors; /* number of light sensors */ |
137 | bool has_accelerometer; /* has motion sensor */ | 138 | bool has_accelerometer; /* has motion sensor */ |
138 | bool has_key_backlight; /* has keyboard backlight */ | 139 | bool has_key_backlight; /* has keyboard backlight */ |
139 | bool init_complete; /* true when fully initialized */ | 140 | bool init_complete; /* true when fully initialized */ |
140 | struct applesmc_entry *cache; /* cached key entries */ | 141 | struct applesmc_entry *cache; /* cached key entries */ |
142 | const char **index; /* temperature key index */ | ||
141 | } smcreg = { | 143 | } smcreg = { |
142 | .mutex = __MUTEX_INITIALIZER(smcreg.mutex), | 144 | .mutex = __MUTEX_INITIALIZER(smcreg.mutex), |
143 | }; | 145 | }; |
@@ -469,6 +471,30 @@ static void applesmc_device_init(void) | |||
469 | pr_warn("failed to init the device\n"); | 471 | pr_warn("failed to init the device\n"); |
470 | } | 472 | } |
471 | 473 | ||
474 | static int applesmc_init_index(struct applesmc_registers *s) | ||
475 | { | ||
476 | const struct applesmc_entry *entry; | ||
477 | unsigned int i; | ||
478 | |||
479 | if (s->index) | ||
480 | return 0; | ||
481 | |||
482 | s->index = kcalloc(s->temp_count, sizeof(s->index[0]), GFP_KERNEL); | ||
483 | if (!s->index) | ||
484 | return -ENOMEM; | ||
485 | |||
486 | for (i = s->temp_begin; i < s->temp_end; i++) { | ||
487 | entry = applesmc_get_entry_by_index(i); | ||
488 | if (IS_ERR(entry)) | ||
489 | continue; | ||
490 | if (strcmp(entry->type, TEMP_SENSOR_TYPE)) | ||
491 | continue; | ||
492 | s->index[s->index_count++] = entry->key; | ||
493 | } | ||
494 | |||
495 | return 0; | ||
496 | } | ||
497 | |||
472 | /* | 498 | /* |
473 | * applesmc_init_smcreg_try - Try to initialize register cache. Idempotent. | 499 | * applesmc_init_smcreg_try - Try to initialize register cache. Idempotent. |
474 | */ | 500 | */ |
@@ -504,6 +530,10 @@ static int applesmc_init_smcreg_try(void) | |||
504 | return ret; | 530 | return ret; |
505 | s->temp_count = s->temp_end - s->temp_begin; | 531 | s->temp_count = s->temp_end - s->temp_begin; |
506 | 532 | ||
533 | ret = applesmc_init_index(s); | ||
534 | if (ret) | ||
535 | return ret; | ||
536 | |||
507 | ret = applesmc_has_key(LIGHT_SENSOR_LEFT_KEY, &left_light_sensor); | 537 | ret = applesmc_has_key(LIGHT_SENSOR_LEFT_KEY, &left_light_sensor); |
508 | if (ret) | 538 | if (ret) |
509 | return ret; | 539 | return ret; |
@@ -520,8 +550,8 @@ static int applesmc_init_smcreg_try(void) | |||
520 | s->num_light_sensors = left_light_sensor + right_light_sensor; | 550 | s->num_light_sensors = left_light_sensor + right_light_sensor; |
521 | s->init_complete = true; | 551 | s->init_complete = true; |
522 | 552 | ||
523 | pr_info("key=%d fan=%d temp=%d acc=%d lux=%d kbd=%d\n", | 553 | pr_info("key=%d fan=%d temp=%d index=%d acc=%d lux=%d kbd=%d\n", |
524 | s->key_count, s->fan_count, s->temp_count, | 554 | s->key_count, s->fan_count, s->temp_count, s->index_count, |
525 | s->has_accelerometer, | 555 | s->has_accelerometer, |
526 | s->num_light_sensors, | 556 | s->num_light_sensors, |
527 | s->has_key_backlight); | 557 | s->has_key_backlight); |
@@ -529,6 +559,15 @@ static int applesmc_init_smcreg_try(void) | |||
529 | return 0; | 559 | return 0; |
530 | } | 560 | } |
531 | 561 | ||
562 | static void applesmc_destroy_smcreg(void) | ||
563 | { | ||
564 | kfree(smcreg.index); | ||
565 | smcreg.index = NULL; | ||
566 | kfree(smcreg.cache); | ||
567 | smcreg.cache = NULL; | ||
568 | smcreg.init_complete = false; | ||
569 | } | ||
570 | |||
532 | /* | 571 | /* |
533 | * applesmc_init_smcreg - Initialize register cache. | 572 | * applesmc_init_smcreg - Initialize register cache. |
534 | * | 573 | * |
@@ -549,19 +588,11 @@ static int applesmc_init_smcreg(void) | |||
549 | msleep(INIT_WAIT_MSECS); | 588 | msleep(INIT_WAIT_MSECS); |
550 | } | 589 | } |
551 | 590 | ||
552 | kfree(smcreg.cache); | 591 | applesmc_destroy_smcreg(); |
553 | smcreg.cache = NULL; | ||
554 | 592 | ||
555 | return ret; | 593 | return ret; |
556 | } | 594 | } |
557 | 595 | ||
558 | static void applesmc_destroy_smcreg(void) | ||
559 | { | ||
560 | kfree(smcreg.cache); | ||
561 | smcreg.cache = NULL; | ||
562 | smcreg.init_complete = false; | ||
563 | } | ||
564 | |||
565 | /* Device model stuff */ | 596 | /* Device model stuff */ |
566 | static int applesmc_probe(struct platform_device *dev) | 597 | static int applesmc_probe(struct platform_device *dev) |
567 | { | 598 | { |
@@ -705,33 +736,21 @@ out: | |||
705 | static ssize_t applesmc_show_sensor_label(struct device *dev, | 736 | static ssize_t applesmc_show_sensor_label(struct device *dev, |
706 | struct device_attribute *devattr, char *sysfsbuf) | 737 | struct device_attribute *devattr, char *sysfsbuf) |
707 | { | 738 | { |
708 | int index = smcreg.temp_begin + to_index(devattr); | 739 | const char *key = smcreg.index[to_index(devattr)]; |
709 | const struct applesmc_entry *entry; | ||
710 | 740 | ||
711 | entry = applesmc_get_entry_by_index(index); | 741 | return snprintf(sysfsbuf, PAGE_SIZE, "%s\n", key); |
712 | if (IS_ERR(entry)) | ||
713 | return PTR_ERR(entry); | ||
714 | |||
715 | return snprintf(sysfsbuf, PAGE_SIZE, "%s\n", entry->key); | ||
716 | } | 742 | } |
717 | 743 | ||
718 | /* Displays degree Celsius * 1000 */ | 744 | /* Displays degree Celsius * 1000 */ |
719 | static ssize_t applesmc_show_temperature(struct device *dev, | 745 | static ssize_t applesmc_show_temperature(struct device *dev, |
720 | struct device_attribute *devattr, char *sysfsbuf) | 746 | struct device_attribute *devattr, char *sysfsbuf) |
721 | { | 747 | { |
722 | int index = smcreg.temp_begin + to_index(devattr); | 748 | const char *key = smcreg.index[to_index(devattr)]; |
723 | const struct applesmc_entry *entry; | ||
724 | int ret; | 749 | int ret; |
725 | s16 value; | 750 | s16 value; |
726 | int temp; | 751 | int temp; |
727 | 752 | ||
728 | entry = applesmc_get_entry_by_index(index); | 753 | ret = applesmc_read_s16(key, &value); |
729 | if (IS_ERR(entry)) | ||
730 | return PTR_ERR(entry); | ||
731 | if (strcmp(entry->type, TEMP_SENSOR_TYPE)) | ||
732 | return -EINVAL; | ||
733 | |||
734 | ret = applesmc_read_s16(entry->key, &value); | ||
735 | if (ret) | 754 | if (ret) |
736 | return ret; | 755 | return ret; |
737 | 756 | ||
@@ -1247,7 +1266,7 @@ static int __init applesmc_init(void) | |||
1247 | if (ret) | 1266 | if (ret) |
1248 | goto out_info; | 1267 | goto out_info; |
1249 | 1268 | ||
1250 | ret = applesmc_create_nodes(temp_group, smcreg.temp_count); | 1269 | ret = applesmc_create_nodes(temp_group, smcreg.index_count); |
1251 | if (ret) | 1270 | if (ret) |
1252 | goto out_fans; | 1271 | goto out_fans; |
1253 | 1272 | ||