aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/hwmon/it87.c48
1 files changed, 38 insertions, 10 deletions
diff --git a/drivers/hwmon/it87.c b/drivers/hwmon/it87.c
index 3827aa9aa11e..117d66fcded6 100644
--- a/drivers/hwmon/it87.c
+++ b/drivers/hwmon/it87.c
@@ -231,7 +231,8 @@ static const u8 IT87_REG_TEMP_OFFSET[] = { 0x56, 0x57, 0x59 };
231struct it87_devices { 231struct it87_devices {
232 const char *name; 232 const char *name;
233 u16 features; 233 u16 features;
234 u16 peci_mask; 234 u8 peci_mask;
235 u8 old_peci_mask;
235}; 236};
236 237
237#define FEAT_12MV_ADC (1 << 0) 238#define FEAT_12MV_ADC (1 << 0)
@@ -240,6 +241,7 @@ struct it87_devices {
240#define FEAT_16BIT_FANS (1 << 3) 241#define FEAT_16BIT_FANS (1 << 3)
241#define FEAT_TEMP_OFFSET (1 << 4) 242#define FEAT_TEMP_OFFSET (1 << 4)
242#define FEAT_TEMP_PECI (1 << 5) 243#define FEAT_TEMP_PECI (1 << 5)
244#define FEAT_TEMP_OLD_PECI (1 << 6)
243 245
244static const struct it87_devices it87_devices[] = { 246static const struct it87_devices it87_devices[] = {
245 [it87] = { 247 [it87] = {
@@ -256,17 +258,22 @@ static const struct it87_devices it87_devices[] = {
256 }, 258 },
257 [it8718] = { 259 [it8718] = {
258 .name = "it8718", 260 .name = "it8718",
259 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET, 261 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET
262 | FEAT_TEMP_OLD_PECI,
263 .old_peci_mask = 0x4,
260 }, 264 },
261 [it8720] = { 265 [it8720] = {
262 .name = "it8720", 266 .name = "it8720",
263 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET, 267 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET
268 | FEAT_TEMP_OLD_PECI,
269 .old_peci_mask = 0x4,
264 }, 270 },
265 [it8721] = { 271 [it8721] = {
266 .name = "it8721", 272 .name = "it8721",
267 .features = FEAT_NEWER_AUTOPWM | FEAT_12MV_ADC | FEAT_16BIT_FANS 273 .features = FEAT_NEWER_AUTOPWM | FEAT_12MV_ADC | FEAT_16BIT_FANS
268 | FEAT_TEMP_OFFSET | FEAT_TEMP_PECI, 274 | FEAT_TEMP_OFFSET | FEAT_TEMP_OLD_PECI | FEAT_TEMP_PECI,
269 .peci_mask = 0x05, 275 .peci_mask = 0x05,
276 .old_peci_mask = 0x02, /* Actually reports PCH */
270 }, 277 },
271 [it8728] = { 278 [it8728] = {
272 .name = "it8728", 279 .name = "it8728",
@@ -276,11 +283,15 @@ static const struct it87_devices it87_devices[] = {
276 }, 283 },
277 [it8782] = { 284 [it8782] = {
278 .name = "it8782", 285 .name = "it8782",
279 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET, 286 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET
287 | FEAT_TEMP_OLD_PECI,
288 .old_peci_mask = 0x4,
280 }, 289 },
281 [it8783] = { 290 [it8783] = {
282 .name = "it8783", 291 .name = "it8783",
283 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET, 292 .features = FEAT_16BIT_FANS | FEAT_TEMP_OFFSET
293 | FEAT_TEMP_OLD_PECI,
294 .old_peci_mask = 0x4,
284 }, 295 },
285}; 296};
286 297
@@ -291,6 +302,9 @@ static const struct it87_devices it87_devices[] = {
291#define has_temp_offset(data) ((data)->features & FEAT_TEMP_OFFSET) 302#define has_temp_offset(data) ((data)->features & FEAT_TEMP_OFFSET)
292#define has_temp_peci(data, nr) (((data)->features & FEAT_TEMP_PECI) && \ 303#define has_temp_peci(data, nr) (((data)->features & FEAT_TEMP_PECI) && \
293 ((data)->peci_mask & (1 << nr))) 304 ((data)->peci_mask & (1 << nr)))
305#define has_temp_old_peci(data, nr) \
306 (((data)->features & FEAT_TEMP_OLD_PECI) && \
307 ((data)->old_peci_mask & (1 << nr)))
294 308
295struct it87_sio_data { 309struct it87_sio_data {
296 enum chips type; 310 enum chips type;
@@ -315,7 +329,8 @@ struct it87_data {
315 struct device *hwmon_dev; 329 struct device *hwmon_dev;
316 enum chips type; 330 enum chips type;
317 u16 features; 331 u16 features;
318 u16 peci_mask; 332 u8 peci_mask;
333 u8 old_peci_mask;
319 334
320 unsigned short addr; 335 unsigned short addr;
321 const char *name; 336 const char *name;
@@ -329,7 +344,8 @@ struct it87_data {
329 u16 fan[5][2]; /* Register values, [nr][0]=fan, [1]=min */ 344 u16 fan[5][2]; /* Register values, [nr][0]=fan, [1]=min */
330 u8 has_temp; /* Bitfield, temp sensors enabled */ 345 u8 has_temp; /* Bitfield, temp sensors enabled */
331 s8 temp[3][4]; /* [nr][0]=temp, [1]=min, [2]=max, [3]=offset */ 346 s8 temp[3][4]; /* [nr][0]=temp, [1]=min, [2]=max, [3]=offset */
332 u8 sensor; /* Register value */ 347 u8 sensor; /* Register value (IT87_REG_TEMP_ENABLE) */
348 u8 extra; /* Register value (IT87_REG_TEMP_EXTRA) */
333 u8 fan_div[3]; /* Register encoding, shifted right */ 349 u8 fan_div[3]; /* Register encoding, shifted right */
334 u8 vid; /* Register encoding, combined */ 350 u8 vid; /* Register encoding, combined */
335 u8 vrm; 351 u8 vrm;
@@ -623,8 +639,10 @@ static ssize_t show_temp_type(struct device *dev, struct device_attribute *attr,
623 int nr = sensor_attr->index; 639 int nr = sensor_attr->index;
624 struct it87_data *data = it87_update_device(dev); 640 struct it87_data *data = it87_update_device(dev);
625 u8 reg = data->sensor; /* In case value is updated while used */ 641 u8 reg = data->sensor; /* In case value is updated while used */
642 u8 extra = data->extra;
626 643
627 if (has_temp_peci(data, nr) && (reg >> 6 == nr + 1)) 644 if ((has_temp_peci(data, nr) && (reg >> 6 == nr + 1))
645 || (has_temp_old_peci(data, nr) && (extra & 0x80)))
628 return sprintf(buf, "6\n"); /* Intel PECI */ 646 return sprintf(buf, "6\n"); /* Intel PECI */
629 if (reg & (1 << nr)) 647 if (reg & (1 << nr))
630 return sprintf(buf, "3\n"); /* thermal diode */ 648 return sprintf(buf, "3\n"); /* thermal diode */
@@ -641,7 +659,7 @@ static ssize_t set_temp_type(struct device *dev, struct device_attribute *attr,
641 659
642 struct it87_data *data = dev_get_drvdata(dev); 660 struct it87_data *data = dev_get_drvdata(dev);
643 long val; 661 long val;
644 u8 reg; 662 u8 reg, extra;
645 663
646 if (kstrtol(buf, 10, &val) < 0) 664 if (kstrtol(buf, 10, &val) < 0)
647 return -EINVAL; 665 return -EINVAL;
@@ -651,6 +669,9 @@ static ssize_t set_temp_type(struct device *dev, struct device_attribute *attr,
651 reg &= ~(8 << nr); 669 reg &= ~(8 << nr);
652 if (has_temp_peci(data, nr) && (reg >> 6 == nr + 1 || val == 6)) 670 if (has_temp_peci(data, nr) && (reg >> 6 == nr + 1 || val == 6))
653 reg &= 0x3f; 671 reg &= 0x3f;
672 extra = it87_read_value(data, IT87_REG_TEMP_EXTRA);
673 if (has_temp_old_peci(data, nr) && ((extra & 0x80) || val == 6))
674 extra &= 0x7f;
654 if (val == 2) { /* backwards compatibility */ 675 if (val == 2) { /* backwards compatibility */
655 dev_warn(dev, 676 dev_warn(dev,
656 "Sensor type 2 is deprecated, please use 4 instead\n"); 677 "Sensor type 2 is deprecated, please use 4 instead\n");
@@ -663,12 +684,17 @@ static ssize_t set_temp_type(struct device *dev, struct device_attribute *attr,
663 reg |= 8 << nr; 684 reg |= 8 << nr;
664 else if (has_temp_peci(data, nr) && val == 6) 685 else if (has_temp_peci(data, nr) && val == 6)
665 reg |= (nr + 1) << 6; 686 reg |= (nr + 1) << 6;
687 else if (has_temp_old_peci(data, nr) && val == 6)
688 extra |= 0x80;
666 else if (val != 0) 689 else if (val != 0)
667 return -EINVAL; 690 return -EINVAL;
668 691
669 mutex_lock(&data->update_lock); 692 mutex_lock(&data->update_lock);
670 data->sensor = reg; 693 data->sensor = reg;
694 data->extra = extra;
671 it87_write_value(data, IT87_REG_TEMP_ENABLE, data->sensor); 695 it87_write_value(data, IT87_REG_TEMP_ENABLE, data->sensor);
696 if (has_temp_old_peci(data, nr))
697 it87_write_value(data, IT87_REG_TEMP_EXTRA, data->extra);
672 data->valid = 0; /* Force cache refresh */ 698 data->valid = 0; /* Force cache refresh */
673 mutex_unlock(&data->update_lock); 699 mutex_unlock(&data->update_lock);
674 return count; 700 return count;
@@ -1980,6 +2006,7 @@ static int it87_probe(struct platform_device *pdev)
1980 data->type = sio_data->type; 2006 data->type = sio_data->type;
1981 data->features = it87_devices[sio_data->type].features; 2007 data->features = it87_devices[sio_data->type].features;
1982 data->peci_mask = it87_devices[sio_data->type].peci_mask; 2008 data->peci_mask = it87_devices[sio_data->type].peci_mask;
2009 data->old_peci_mask = it87_devices[sio_data->type].old_peci_mask;
1983 data->name = it87_devices[sio_data->type].name; 2010 data->name = it87_devices[sio_data->type].name;
1984 /* 2011 /*
1985 * IT8705F Datasheet 0.4.1, 3h == Version G. 2012 * IT8705F Datasheet 0.4.1, 3h == Version G.
@@ -2461,6 +2488,7 @@ static struct it87_data *it87_update_device(struct device *dev)
2461 it87_update_pwm_ctrl(data, i); 2488 it87_update_pwm_ctrl(data, i);
2462 2489
2463 data->sensor = it87_read_value(data, IT87_REG_TEMP_ENABLE); 2490 data->sensor = it87_read_value(data, IT87_REG_TEMP_ENABLE);
2491 data->extra = it87_read_value(data, IT87_REG_TEMP_EXTRA);
2464 /* 2492 /*
2465 * The IT8705F does not have VID capability. 2493 * The IT8705F does not have VID capability.
2466 * The IT8718F and later don't use IT87_REG_VID for the 2494 * The IT8718F and later don't use IT87_REG_VID for the