aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPali Rohár <pali.rohar@gmail.com>2016-06-17 18:54:48 -0400
committerGuenter Roeck <linux@roeck-us.net>2016-06-27 21:58:03 -0400
commit747bc8b063ae6b66447918280922253721cb1d9b (patch)
tree072e24eb7dae1f66fb4debc22433b0bdfe7dcb8a
parent68f86c75ca1eaf790907eb43c68f9f2996474116 (diff)
hwmon: (dell-smm) Detect fan with index=2
Some Dell machines (e.g. Dell Precision M3800) have two fans, first with index=0 and second with index=2. So export also attributes for third fan device with index=2. Reported-by: Tolga Cakir <cevelnet@gmail.com> Signed-off-by: Pali Rohár <pali.rohar@gmail.com> Tested-by: Tolga Cakir <cevelnet@gmail.com> Signed-off-by: Guenter Roeck <linux@roeck-us.net>
-rw-r--r--drivers/hwmon/dell-smm-hwmon.c24
1 files changed, 22 insertions, 2 deletions
diff --git a/drivers/hwmon/dell-smm-hwmon.c b/drivers/hwmon/dell-smm-hwmon.c
index 2ac87d553e22..571d4984d39c 100644
--- a/drivers/hwmon/dell-smm-hwmon.c
+++ b/drivers/hwmon/dell-smm-hwmon.c
@@ -81,6 +81,7 @@ static bool disallow_fan_type_call;
81#define I8K_HWMON_HAVE_TEMP4 (1 << 3) 81#define I8K_HWMON_HAVE_TEMP4 (1 << 3)
82#define I8K_HWMON_HAVE_FAN1 (1 << 4) 82#define I8K_HWMON_HAVE_FAN1 (1 << 4)
83#define I8K_HWMON_HAVE_FAN2 (1 << 5) 83#define I8K_HWMON_HAVE_FAN2 (1 << 5)
84#define I8K_HWMON_HAVE_FAN3 (1 << 6)
84 85
85MODULE_AUTHOR("Massimo Dal Zotto (dz@debian.org)"); 86MODULE_AUTHOR("Massimo Dal Zotto (dz@debian.org)");
86MODULE_AUTHOR("Pali Rohár <pali.rohar@gmail.com>"); 87MODULE_AUTHOR("Pali Rohár <pali.rohar@gmail.com>");
@@ -252,7 +253,7 @@ static int _i8k_get_fan_type(int fan)
252static int i8k_get_fan_type(int fan) 253static int i8k_get_fan_type(int fan)
253{ 254{
254 /* I8K_SMM_GET_FAN_TYPE SMM call is expensive, so cache values */ 255 /* I8K_SMM_GET_FAN_TYPE SMM call is expensive, so cache values */
255 static int types[2] = { INT_MIN, INT_MIN }; 256 static int types[3] = { INT_MIN, INT_MIN, INT_MIN };
256 257
257 if (types[fan] == INT_MIN) 258 if (types[fan] == INT_MIN)
258 types[fan] = _i8k_get_fan_type(fan); 259 types[fan] = _i8k_get_fan_type(fan);
@@ -719,6 +720,12 @@ static SENSOR_DEVICE_ATTR(fan2_label, S_IRUGO, i8k_hwmon_show_fan_label, NULL,
719 1); 720 1);
720static SENSOR_DEVICE_ATTR(pwm2, S_IRUGO | S_IWUSR, i8k_hwmon_show_pwm, 721static SENSOR_DEVICE_ATTR(pwm2, S_IRUGO | S_IWUSR, i8k_hwmon_show_pwm,
721 i8k_hwmon_set_pwm, 1); 722 i8k_hwmon_set_pwm, 1);
723static SENSOR_DEVICE_ATTR(fan3_input, S_IRUGO, i8k_hwmon_show_fan, NULL,
724 2);
725static SENSOR_DEVICE_ATTR(fan3_label, S_IRUGO, i8k_hwmon_show_fan_label, NULL,
726 2);
727static SENSOR_DEVICE_ATTR(pwm3, S_IRUGO | S_IWUSR, i8k_hwmon_show_pwm,
728 i8k_hwmon_set_pwm, 2);
722 729
723static struct attribute *i8k_attrs[] = { 730static struct attribute *i8k_attrs[] = {
724 &sensor_dev_attr_temp1_input.dev_attr.attr, /* 0 */ 731 &sensor_dev_attr_temp1_input.dev_attr.attr, /* 0 */
@@ -735,6 +742,9 @@ static struct attribute *i8k_attrs[] = {
735 &sensor_dev_attr_fan2_input.dev_attr.attr, /* 11 */ 742 &sensor_dev_attr_fan2_input.dev_attr.attr, /* 11 */
736 &sensor_dev_attr_fan2_label.dev_attr.attr, /* 12 */ 743 &sensor_dev_attr_fan2_label.dev_attr.attr, /* 12 */
737 &sensor_dev_attr_pwm2.dev_attr.attr, /* 13 */ 744 &sensor_dev_attr_pwm2.dev_attr.attr, /* 13 */
745 &sensor_dev_attr_fan3_input.dev_attr.attr, /* 14 */
746 &sensor_dev_attr_fan3_label.dev_attr.attr, /* 15 */
747 &sensor_dev_attr_pwm3.dev_attr.attr, /* 16 */
738 NULL 748 NULL
739}; 749};
740 750
@@ -742,7 +752,7 @@ static umode_t i8k_is_visible(struct kobject *kobj, struct attribute *attr,
742 int index) 752 int index)
743{ 753{
744 if (disallow_fan_type_call && 754 if (disallow_fan_type_call &&
745 (index == 9 || index == 12)) 755 (index == 9 || index == 12 || index == 15))
746 return 0; 756 return 0;
747 if (index >= 0 && index <= 1 && 757 if (index >= 0 && index <= 1 &&
748 !(i8k_hwmon_flags & I8K_HWMON_HAVE_TEMP1)) 758 !(i8k_hwmon_flags & I8K_HWMON_HAVE_TEMP1))
@@ -762,6 +772,9 @@ static umode_t i8k_is_visible(struct kobject *kobj, struct attribute *attr,
762 if (index >= 11 && index <= 13 && 772 if (index >= 11 && index <= 13 &&
763 !(i8k_hwmon_flags & I8K_HWMON_HAVE_FAN2)) 773 !(i8k_hwmon_flags & I8K_HWMON_HAVE_FAN2))
764 return 0; 774 return 0;
775 if (index >= 14 && index <= 16 &&
776 !(i8k_hwmon_flags & I8K_HWMON_HAVE_FAN3))
777 return 0;
765 778
766 return attr->mode; 779 return attr->mode;
767} 780}
@@ -807,6 +820,13 @@ static int __init i8k_init_hwmon(void)
807 if (err >= 0) 820 if (err >= 0)
808 i8k_hwmon_flags |= I8K_HWMON_HAVE_FAN2; 821 i8k_hwmon_flags |= I8K_HWMON_HAVE_FAN2;
809 822
823 /* Third fan attributes, if fan status or type is OK */
824 err = i8k_get_fan_status(2);
825 if (err < 0)
826 err = i8k_get_fan_type(2);
827 if (err >= 0)
828 i8k_hwmon_flags |= I8K_HWMON_HAVE_FAN3;
829
810 i8k_hwmon_dev = hwmon_device_register_with_groups(NULL, "dell_smm", 830 i8k_hwmon_dev = hwmon_device_register_with_groups(NULL, "dell_smm",
811 NULL, i8k_groups); 831 NULL, i8k_groups);
812 if (IS_ERR(i8k_hwmon_dev)) { 832 if (IS_ERR(i8k_hwmon_dev)) {