Commit 5c25d954d37b7c18606d7ef99122424552b86ef2

Authored by Guenter Roeck
1 parent 1c65dc365e

hwmon: (nct6775) Add support for fanX_pulses sysfs attribute

Signed-off-by: Guenter Roeck <linux@roeck-us.net>

Showing 1 changed file with 64 additions and 0 deletions Side-by-side Diff

drivers/hwmon/nct6775.c
... ... @@ -205,6 +205,7 @@
205 205  
206 206 static const u16 NCT6775_REG_FAN[] = { 0x630, 0x632, 0x634, 0x636, 0x638 };
207 207 static const u16 NCT6775_REG_FAN_MIN[] = { 0x3b, 0x3c, 0x3d };
  208 +static const u16 NCT6775_REG_FAN_PULSES[] = { 0x641, 0x642, 0x643, 0x644, 0 };
208 209  
209 210 static const u16 NCT6775_REG_TEMP[] = {
210 211 0x27, 0x150, 0x250, 0x62b, 0x62c, 0x62d };
... ... @@ -264,6 +265,7 @@
264 265 12, 9 }; /* intrusion0, intrusion1 */
265 266  
266 267 static const u16 NCT6776_REG_FAN_MIN[] = { 0x63a, 0x63c, 0x63e, 0x640, 0x642 };
  268 +static const u16 NCT6776_REG_FAN_PULSES[] = { 0x644, 0x645, 0x646, 0, 0 };
267 269  
268 270 static const u16 NCT6776_REG_TEMP_CONFIG[ARRAY_SIZE(NCT6775_REG_TEMP)] = {
269 271 0x18, 0x152, 0x252, 0x628, 0x629, 0x62A };
... ... @@ -319,6 +321,8 @@
319 321 12, 9 }; /* intrusion0, intrusion1 */
320 322  
321 323 static const u16 NCT6779_REG_FAN[] = { 0x4b0, 0x4b2, 0x4b4, 0x4b6, 0x4b8 };
  324 +static const u16 NCT6779_REG_FAN_PULSES[] = {
  325 + 0x644, 0x645, 0x646, 0x647, 0x648 };
322 326  
323 327 static const u16 NCT6779_REG_TEMP[] = { 0x27, 0x150 };
324 328 static const u16 NCT6779_REG_TEMP_CONFIG[ARRAY_SIZE(NCT6779_REG_TEMP)] = {
... ... @@ -462,6 +466,7 @@
462 466  
463 467 const u16 *REG_FAN;
464 468 const u16 *REG_FAN_MIN;
  469 + const u16 *REG_FAN_PULSES;
465 470  
466 471 const u16 *REG_TEMP_SOURCE; /* temp register sources */
467 472 const u16 *REG_TEMP_OFFSET;
... ... @@ -481,6 +486,7 @@
481 486 u8 in[15][3]; /* [0]=in, [1]=in_max, [2]=in_min */
482 487 unsigned int rpm[5];
483 488 u16 fan_min[5];
  489 + u8 fan_pulses[5];
484 490 u8 fan_div[5];
485 491 u8 has_fan; /* some fan inputs can be disabled */
486 492 u8 has_fan_min; /* some fans don't have min register */
... ... @@ -802,6 +808,8 @@
802 808 if (data->has_fan_min & (1 << i))
803 809 data->fan_min[i] = nct6775_read_value(data,
804 810 data->REG_FAN_MIN[i]);
  811 + data->fan_pulses[i] =
  812 + nct6775_read_value(data, data->REG_FAN_PULSES[i]);
805 813  
806 814 nct6775_select_fan_div(dev, data, i, reg);
807 815 }
... ... @@ -1225,6 +1233,41 @@
1225 1233 return count;
1226 1234 }
1227 1235  
  1236 +static ssize_t
  1237 +show_fan_pulses(struct device *dev, struct device_attribute *attr, char *buf)
  1238 +{
  1239 + struct nct6775_data *data = nct6775_update_device(dev);
  1240 + struct sensor_device_attribute *sattr = to_sensor_dev_attr(attr);
  1241 + int p = data->fan_pulses[sattr->index];
  1242 +
  1243 + return sprintf(buf, "%d\n", p ? : 4);
  1244 +}
  1245 +
  1246 +static ssize_t
  1247 +store_fan_pulses(struct device *dev, struct device_attribute *attr,
  1248 + const char *buf, size_t count)
  1249 +{
  1250 + struct nct6775_data *data = dev_get_drvdata(dev);
  1251 + struct sensor_device_attribute *sattr = to_sensor_dev_attr(attr);
  1252 + int nr = sattr->index;
  1253 + unsigned long val;
  1254 + int err;
  1255 +
  1256 + err = kstrtoul(buf, 10, &val);
  1257 + if (err < 0)
  1258 + return err;
  1259 +
  1260 + if (val > 4)
  1261 + return -EINVAL;
  1262 +
  1263 + mutex_lock(&data->update_lock);
  1264 + data->fan_pulses[nr] = val & 3;
  1265 + nct6775_write_value(data, data->REG_FAN_PULSES[nr], val & 3);
  1266 + mutex_unlock(&data->update_lock);
  1267 +
  1268 + return count;
  1269 +}
  1270 +
1228 1271 static struct sensor_device_attribute sda_fan_input[] = {
1229 1272 SENSOR_ATTR(fan1_input, S_IRUGO, show_fan, NULL, 0),
1230 1273 SENSOR_ATTR(fan2_input, S_IRUGO, show_fan, NULL, 1),
... ... @@ -1254,6 +1297,19 @@
1254 1297 store_fan_min, 4),
1255 1298 };
1256 1299  
  1300 +static struct sensor_device_attribute sda_fan_pulses[] = {
  1301 + SENSOR_ATTR(fan1_pulses, S_IWUSR | S_IRUGO, show_fan_pulses,
  1302 + store_fan_pulses, 0),
  1303 + SENSOR_ATTR(fan2_pulses, S_IWUSR | S_IRUGO, show_fan_pulses,
  1304 + store_fan_pulses, 1),
  1305 + SENSOR_ATTR(fan3_pulses, S_IWUSR | S_IRUGO, show_fan_pulses,
  1306 + store_fan_pulses, 2),
  1307 + SENSOR_ATTR(fan4_pulses, S_IWUSR | S_IRUGO, show_fan_pulses,
  1308 + store_fan_pulses, 3),
  1309 + SENSOR_ATTR(fan5_pulses, S_IWUSR | S_IRUGO, show_fan_pulses,
  1310 + store_fan_pulses, 4),
  1311 +};
  1312 +
1257 1313 static struct sensor_device_attribute sda_fan_div[] = {
1258 1314 SENSOR_ATTR(fan1_div, S_IRUGO, show_fan_div, NULL, 0),
1259 1315 SENSOR_ATTR(fan2_div, S_IRUGO, show_fan_div, NULL, 1),
... ... @@ -1621,6 +1677,7 @@
1621 1677 device_remove_file(dev, &sda_fan_alarm[i].dev_attr);
1622 1678 device_remove_file(dev, &sda_fan_div[i].dev_attr);
1623 1679 device_remove_file(dev, &sda_fan_min[i].dev_attr);
  1680 + device_remove_file(dev, &sda_fan_pulses[i].dev_attr);
1624 1681 }
1625 1682 for (i = 0; i < NUM_TEMP; i++) {
1626 1683 if (!(data->have_temp & (1 << i)))
... ... @@ -1809,6 +1866,7 @@
1809 1866 data->REG_IN_MINMAX[1] = NCT6775_REG_IN_MAX;
1810 1867 data->REG_FAN = NCT6775_REG_FAN;
1811 1868 data->REG_FAN_MIN = NCT6775_REG_FAN_MIN;
  1869 + data->REG_FAN_PULSES = NCT6775_REG_FAN_PULSES;
1812 1870 data->REG_TEMP_OFFSET = NCT6775_REG_TEMP_OFFSET;
1813 1871 data->REG_TEMP_SOURCE = NCT6775_REG_TEMP_SOURCE;
1814 1872 data->REG_ALARM = NCT6775_REG_ALARM;
... ... @@ -1843,6 +1901,7 @@
1843 1901 data->REG_IN_MINMAX[1] = NCT6775_REG_IN_MAX;
1844 1902 data->REG_FAN = NCT6775_REG_FAN;
1845 1903 data->REG_FAN_MIN = NCT6776_REG_FAN_MIN;
  1904 + data->REG_FAN_PULSES = NCT6776_REG_FAN_PULSES;
1846 1905 data->REG_TEMP_OFFSET = NCT6775_REG_TEMP_OFFSET;
1847 1906 data->REG_TEMP_SOURCE = NCT6775_REG_TEMP_SOURCE;
1848 1907 data->REG_ALARM = NCT6775_REG_ALARM;
... ... @@ -1877,6 +1936,7 @@
1877 1936 data->REG_IN_MINMAX[1] = NCT6775_REG_IN_MAX;
1878 1937 data->REG_FAN = NCT6779_REG_FAN;
1879 1938 data->REG_FAN_MIN = NCT6776_REG_FAN_MIN;
  1939 + data->REG_FAN_PULSES = NCT6779_REG_FAN_PULSES;
1880 1940 data->REG_TEMP_OFFSET = NCT6779_REG_TEMP_OFFSET;
1881 1941 data->REG_TEMP_SOURCE = NCT6775_REG_TEMP_SOURCE;
1882 1942 data->REG_ALARM = NCT6779_REG_ALARM;
... ... @@ -2094,6 +2154,10 @@
2094 2154 if (err)
2095 2155 goto exit_remove;
2096 2156 }
  2157 + err = device_create_file(dev,
  2158 + &sda_fan_pulses[i].dev_attr);
  2159 + if (err)
  2160 + goto exit_remove;
2097 2161 }
2098 2162 }
2099 2163