2 * Copyright 2010 Red Hat Inc.
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
26 #include <linux/acpi.h>
28 #include <linux/power_supply.h>
29 #include <linux/hwmon.h>
30 #include <linux/hwmon-sysfs.h>
34 #include "nouveau_drm.h"
35 #include "nouveau_hwmon.h"
37 #if defined(CONFIG_HWMON) || (defined(MODULE) && defined(CONFIG_HWMON_MODULE))
39 nouveau_hwmon_show_temp(struct device
*d
, struct device_attribute
*a
, char *buf
)
41 struct drm_device
*dev
= dev_get_drvdata(d
);
42 struct nouveau_drm
*drm
= nouveau_drm(dev
);
43 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
44 int temp
= therm
->temp_get(therm
);
49 return snprintf(buf
, PAGE_SIZE
, "%d\n", temp
* 1000);
51 static SENSOR_DEVICE_ATTR(temp1_input
, S_IRUGO
, nouveau_hwmon_show_temp
,
55 nouveau_hwmon_show_temp1_auto_point1_pwm(struct device
*d
,
56 struct device_attribute
*a
, char *buf
)
58 return snprintf(buf
, PAGE_SIZE
, "%d\n", 100);
60 static SENSOR_DEVICE_ATTR(temp1_auto_point1_pwm
, S_IRUGO
,
61 nouveau_hwmon_show_temp1_auto_point1_pwm
, NULL
, 0);
64 nouveau_hwmon_temp1_auto_point1_temp(struct device
*d
,
65 struct device_attribute
*a
, char *buf
)
67 struct drm_device
*dev
= dev_get_drvdata(d
);
68 struct nouveau_drm
*drm
= nouveau_drm(dev
);
69 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
71 return snprintf(buf
, PAGE_SIZE
, "%d\n",
72 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_FAN_BOOST
) * 1000);
75 nouveau_hwmon_set_temp1_auto_point1_temp(struct device
*d
,
76 struct device_attribute
*a
,
77 const char *buf
, size_t count
)
79 struct drm_device
*dev
= dev_get_drvdata(d
);
80 struct nouveau_drm
*drm
= nouveau_drm(dev
);
81 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
84 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
87 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_FAN_BOOST
,
92 static SENSOR_DEVICE_ATTR(temp1_auto_point1_temp
, S_IRUGO
| S_IWUSR
,
93 nouveau_hwmon_temp1_auto_point1_temp
,
94 nouveau_hwmon_set_temp1_auto_point1_temp
, 0);
97 nouveau_hwmon_temp1_auto_point1_temp_hyst(struct device
*d
,
98 struct device_attribute
*a
, char *buf
)
100 struct drm_device
*dev
= dev_get_drvdata(d
);
101 struct nouveau_drm
*drm
= nouveau_drm(dev
);
102 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
104 return snprintf(buf
, PAGE_SIZE
, "%d\n",
105 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_FAN_BOOST_HYST
) * 1000);
108 nouveau_hwmon_set_temp1_auto_point1_temp_hyst(struct device
*d
,
109 struct device_attribute
*a
,
110 const char *buf
, size_t count
)
112 struct drm_device
*dev
= dev_get_drvdata(d
);
113 struct nouveau_drm
*drm
= nouveau_drm(dev
);
114 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
117 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
120 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_FAN_BOOST_HYST
,
125 static SENSOR_DEVICE_ATTR(temp1_auto_point1_temp_hyst
, S_IRUGO
| S_IWUSR
,
126 nouveau_hwmon_temp1_auto_point1_temp_hyst
,
127 nouveau_hwmon_set_temp1_auto_point1_temp_hyst
, 0);
130 nouveau_hwmon_max_temp(struct device
*d
, struct device_attribute
*a
, char *buf
)
132 struct drm_device
*dev
= dev_get_drvdata(d
);
133 struct nouveau_drm
*drm
= nouveau_drm(dev
);
134 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
136 return snprintf(buf
, PAGE_SIZE
, "%d\n",
137 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_DOWN_CLK
) * 1000);
140 nouveau_hwmon_set_max_temp(struct device
*d
, struct device_attribute
*a
,
141 const char *buf
, size_t count
)
143 struct drm_device
*dev
= dev_get_drvdata(d
);
144 struct nouveau_drm
*drm
= nouveau_drm(dev
);
145 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
148 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
151 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_DOWN_CLK
, value
/ 1000);
155 static SENSOR_DEVICE_ATTR(temp1_max
, S_IRUGO
| S_IWUSR
, nouveau_hwmon_max_temp
,
156 nouveau_hwmon_set_max_temp
,
160 nouveau_hwmon_max_temp_hyst(struct device
*d
, struct device_attribute
*a
,
163 struct drm_device
*dev
= dev_get_drvdata(d
);
164 struct nouveau_drm
*drm
= nouveau_drm(dev
);
165 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
167 return snprintf(buf
, PAGE_SIZE
, "%d\n",
168 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_DOWN_CLK_HYST
) * 1000);
171 nouveau_hwmon_set_max_temp_hyst(struct device
*d
, struct device_attribute
*a
,
172 const char *buf
, size_t count
)
174 struct drm_device
*dev
= dev_get_drvdata(d
);
175 struct nouveau_drm
*drm
= nouveau_drm(dev
);
176 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
179 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
182 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_DOWN_CLK_HYST
,
187 static SENSOR_DEVICE_ATTR(temp1_max_hyst
, S_IRUGO
| S_IWUSR
,
188 nouveau_hwmon_max_temp_hyst
,
189 nouveau_hwmon_set_max_temp_hyst
, 0);
192 nouveau_hwmon_critical_temp(struct device
*d
, struct device_attribute
*a
,
195 struct drm_device
*dev
= dev_get_drvdata(d
);
196 struct nouveau_drm
*drm
= nouveau_drm(dev
);
197 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
199 return snprintf(buf
, PAGE_SIZE
, "%d\n",
200 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_CRITICAL
) * 1000);
203 nouveau_hwmon_set_critical_temp(struct device
*d
, struct device_attribute
*a
,
207 struct drm_device
*dev
= dev_get_drvdata(d
);
208 struct nouveau_drm
*drm
= nouveau_drm(dev
);
209 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
212 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
215 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_CRITICAL
, value
/ 1000);
219 static SENSOR_DEVICE_ATTR(temp1_crit
, S_IRUGO
| S_IWUSR
,
220 nouveau_hwmon_critical_temp
,
221 nouveau_hwmon_set_critical_temp
,
225 nouveau_hwmon_critical_temp_hyst(struct device
*d
, struct device_attribute
*a
,
228 struct drm_device
*dev
= dev_get_drvdata(d
);
229 struct nouveau_drm
*drm
= nouveau_drm(dev
);
230 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
232 return snprintf(buf
, PAGE_SIZE
, "%d\n",
233 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_CRITICAL_HYST
) * 1000);
236 nouveau_hwmon_set_critical_temp_hyst(struct device
*d
,
237 struct device_attribute
*a
,
241 struct drm_device
*dev
= dev_get_drvdata(d
);
242 struct nouveau_drm
*drm
= nouveau_drm(dev
);
243 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
246 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
249 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_CRITICAL_HYST
,
254 static SENSOR_DEVICE_ATTR(temp1_crit_hyst
, S_IRUGO
| S_IWUSR
,
255 nouveau_hwmon_critical_temp_hyst
,
256 nouveau_hwmon_set_critical_temp_hyst
, 0);
258 nouveau_hwmon_emergency_temp(struct device
*d
, struct device_attribute
*a
,
261 struct drm_device
*dev
= dev_get_drvdata(d
);
262 struct nouveau_drm
*drm
= nouveau_drm(dev
);
263 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
265 return snprintf(buf
, PAGE_SIZE
, "%d\n",
266 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_SHUTDOWN
) * 1000);
269 nouveau_hwmon_set_emergency_temp(struct device
*d
, struct device_attribute
*a
,
273 struct drm_device
*dev
= dev_get_drvdata(d
);
274 struct nouveau_drm
*drm
= nouveau_drm(dev
);
275 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
278 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
281 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_SHUTDOWN
, value
/ 1000);
285 static SENSOR_DEVICE_ATTR(temp1_emergency
, S_IRUGO
| S_IWUSR
,
286 nouveau_hwmon_emergency_temp
,
287 nouveau_hwmon_set_emergency_temp
,
291 nouveau_hwmon_emergency_temp_hyst(struct device
*d
, struct device_attribute
*a
,
294 struct drm_device
*dev
= dev_get_drvdata(d
);
295 struct nouveau_drm
*drm
= nouveau_drm(dev
);
296 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
298 return snprintf(buf
, PAGE_SIZE
, "%d\n",
299 therm
->attr_get(therm
, NVKM_THERM_ATTR_THRS_SHUTDOWN_HYST
) * 1000);
302 nouveau_hwmon_set_emergency_temp_hyst(struct device
*d
,
303 struct device_attribute
*a
,
307 struct drm_device
*dev
= dev_get_drvdata(d
);
308 struct nouveau_drm
*drm
= nouveau_drm(dev
);
309 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
312 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
315 therm
->attr_set(therm
, NVKM_THERM_ATTR_THRS_SHUTDOWN_HYST
,
320 static SENSOR_DEVICE_ATTR(temp1_emergency_hyst
, S_IRUGO
| S_IWUSR
,
321 nouveau_hwmon_emergency_temp_hyst
,
322 nouveau_hwmon_set_emergency_temp_hyst
,
325 static ssize_t
nouveau_hwmon_show_name(struct device
*dev
,
326 struct device_attribute
*attr
,
329 return sprintf(buf
, "nouveau\n");
331 static SENSOR_DEVICE_ATTR(name
, S_IRUGO
, nouveau_hwmon_show_name
, NULL
, 0);
333 static ssize_t
nouveau_hwmon_show_update_rate(struct device
*dev
,
334 struct device_attribute
*attr
,
337 return sprintf(buf
, "1000\n");
339 static SENSOR_DEVICE_ATTR(update_rate
, S_IRUGO
,
340 nouveau_hwmon_show_update_rate
,
344 nouveau_hwmon_show_fan1_input(struct device
*d
, struct device_attribute
*attr
,
347 struct drm_device
*dev
= dev_get_drvdata(d
);
348 struct nouveau_drm
*drm
= nouveau_drm(dev
);
349 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
351 return snprintf(buf
, PAGE_SIZE
, "%d\n", therm
->fan_sense(therm
));
353 static SENSOR_DEVICE_ATTR(fan1_input
, S_IRUGO
, nouveau_hwmon_show_fan1_input
,
357 nouveau_hwmon_get_pwm1_enable(struct device
*d
,
358 struct device_attribute
*a
, char *buf
)
360 struct drm_device
*dev
= dev_get_drvdata(d
);
361 struct nouveau_drm
*drm
= nouveau_drm(dev
);
362 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
365 ret
= therm
->attr_get(therm
, NVKM_THERM_ATTR_FAN_MODE
);
369 return sprintf(buf
, "%i\n", ret
);
373 nouveau_hwmon_set_pwm1_enable(struct device
*d
, struct device_attribute
*a
,
374 const char *buf
, size_t count
)
376 struct drm_device
*dev
= dev_get_drvdata(d
);
377 struct nouveau_drm
*drm
= nouveau_drm(dev
);
378 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
382 ret
= kstrtol(buf
, 10, &value
);
386 ret
= therm
->attr_set(therm
, NVKM_THERM_ATTR_FAN_MODE
, value
);
392 static SENSOR_DEVICE_ATTR(pwm1_enable
, S_IRUGO
| S_IWUSR
,
393 nouveau_hwmon_get_pwm1_enable
,
394 nouveau_hwmon_set_pwm1_enable
, 0);
397 nouveau_hwmon_get_pwm1(struct device
*d
, struct device_attribute
*a
, char *buf
)
399 struct drm_device
*dev
= dev_get_drvdata(d
);
400 struct nouveau_drm
*drm
= nouveau_drm(dev
);
401 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
404 ret
= therm
->fan_get(therm
);
408 return sprintf(buf
, "%i\n", ret
);
412 nouveau_hwmon_set_pwm1(struct device
*d
, struct device_attribute
*a
,
413 const char *buf
, size_t count
)
415 struct drm_device
*dev
= dev_get_drvdata(d
);
416 struct nouveau_drm
*drm
= nouveau_drm(dev
);
417 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
421 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
424 ret
= therm
->fan_set(therm
, value
);
431 static SENSOR_DEVICE_ATTR(pwm1
, S_IRUGO
| S_IWUSR
,
432 nouveau_hwmon_get_pwm1
,
433 nouveau_hwmon_set_pwm1
, 0);
436 nouveau_hwmon_get_pwm1_min(struct device
*d
,
437 struct device_attribute
*a
, char *buf
)
439 struct drm_device
*dev
= dev_get_drvdata(d
);
440 struct nouveau_drm
*drm
= nouveau_drm(dev
);
441 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
444 ret
= therm
->attr_get(therm
, NVKM_THERM_ATTR_FAN_MIN_DUTY
);
448 return sprintf(buf
, "%i\n", ret
);
452 nouveau_hwmon_set_pwm1_min(struct device
*d
, struct device_attribute
*a
,
453 const char *buf
, size_t count
)
455 struct drm_device
*dev
= dev_get_drvdata(d
);
456 struct nouveau_drm
*drm
= nouveau_drm(dev
);
457 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
461 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
464 ret
= therm
->attr_set(therm
, NVKM_THERM_ATTR_FAN_MIN_DUTY
, value
);
471 static SENSOR_DEVICE_ATTR(pwm1_min
, S_IRUGO
| S_IWUSR
,
472 nouveau_hwmon_get_pwm1_min
,
473 nouveau_hwmon_set_pwm1_min
, 0);
476 nouveau_hwmon_get_pwm1_max(struct device
*d
,
477 struct device_attribute
*a
, char *buf
)
479 struct drm_device
*dev
= dev_get_drvdata(d
);
480 struct nouveau_drm
*drm
= nouveau_drm(dev
);
481 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
484 ret
= therm
->attr_get(therm
, NVKM_THERM_ATTR_FAN_MAX_DUTY
);
488 return sprintf(buf
, "%i\n", ret
);
492 nouveau_hwmon_set_pwm1_max(struct device
*d
, struct device_attribute
*a
,
493 const char *buf
, size_t count
)
495 struct drm_device
*dev
= dev_get_drvdata(d
);
496 struct nouveau_drm
*drm
= nouveau_drm(dev
);
497 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
501 if (kstrtol(buf
, 10, &value
) == -EINVAL
)
504 ret
= therm
->attr_set(therm
, NVKM_THERM_ATTR_FAN_MAX_DUTY
, value
);
511 static SENSOR_DEVICE_ATTR(pwm1_max
, S_IRUGO
| S_IWUSR
,
512 nouveau_hwmon_get_pwm1_max
,
513 nouveau_hwmon_set_pwm1_max
, 0);
515 static struct attribute
*hwmon_default_attributes
[] = {
516 &sensor_dev_attr_name
.dev_attr
.attr
,
517 &sensor_dev_attr_update_rate
.dev_attr
.attr
,
520 static struct attribute
*hwmon_temp_attributes
[] = {
521 &sensor_dev_attr_temp1_input
.dev_attr
.attr
,
522 &sensor_dev_attr_temp1_auto_point1_pwm
.dev_attr
.attr
,
523 &sensor_dev_attr_temp1_auto_point1_temp
.dev_attr
.attr
,
524 &sensor_dev_attr_temp1_auto_point1_temp_hyst
.dev_attr
.attr
,
525 &sensor_dev_attr_temp1_max
.dev_attr
.attr
,
526 &sensor_dev_attr_temp1_max_hyst
.dev_attr
.attr
,
527 &sensor_dev_attr_temp1_crit
.dev_attr
.attr
,
528 &sensor_dev_attr_temp1_crit_hyst
.dev_attr
.attr
,
529 &sensor_dev_attr_temp1_emergency
.dev_attr
.attr
,
530 &sensor_dev_attr_temp1_emergency_hyst
.dev_attr
.attr
,
533 static struct attribute
*hwmon_fan_rpm_attributes
[] = {
534 &sensor_dev_attr_fan1_input
.dev_attr
.attr
,
537 static struct attribute
*hwmon_pwm_fan_attributes
[] = {
538 &sensor_dev_attr_pwm1_enable
.dev_attr
.attr
,
539 &sensor_dev_attr_pwm1
.dev_attr
.attr
,
540 &sensor_dev_attr_pwm1_min
.dev_attr
.attr
,
541 &sensor_dev_attr_pwm1_max
.dev_attr
.attr
,
545 static const struct attribute_group hwmon_default_attrgroup
= {
546 .attrs
= hwmon_default_attributes
,
548 static const struct attribute_group hwmon_temp_attrgroup
= {
549 .attrs
= hwmon_temp_attributes
,
551 static const struct attribute_group hwmon_fan_rpm_attrgroup
= {
552 .attrs
= hwmon_fan_rpm_attributes
,
554 static const struct attribute_group hwmon_pwm_fan_attrgroup
= {
555 .attrs
= hwmon_pwm_fan_attributes
,
560 nouveau_hwmon_init(struct drm_device
*dev
)
562 #if defined(CONFIG_HWMON) || (defined(MODULE) && defined(CONFIG_HWMON_MODULE))
563 struct nouveau_drm
*drm
= nouveau_drm(dev
);
564 struct nvkm_therm
*therm
= nvxx_therm(&drm
->device
);
565 struct nouveau_hwmon
*hwmon
;
566 struct device
*hwmon_dev
;
569 hwmon
= drm
->hwmon
= kzalloc(sizeof(*hwmon
), GFP_KERNEL
);
574 if (!therm
|| !therm
->temp_get
|| !therm
->attr_get
|| !therm
->attr_set
)
577 hwmon_dev
= hwmon_device_register(&dev
->pdev
->dev
);
578 if (IS_ERR(hwmon_dev
)) {
579 ret
= PTR_ERR(hwmon_dev
);
580 NV_ERROR(drm
, "Unable to register hwmon device: %d\n", ret
);
583 dev_set_drvdata(hwmon_dev
, dev
);
585 /* set the default attributes */
586 ret
= sysfs_create_group(&hwmon_dev
->kobj
, &hwmon_default_attrgroup
);
590 /* if the card has a working thermal sensor */
591 if (therm
->temp_get(therm
) >= 0) {
592 ret
= sysfs_create_group(&hwmon_dev
->kobj
, &hwmon_temp_attrgroup
);
597 /* if the card has a pwm fan */
598 /*XXX: incorrect, need better detection for this, some boards have
599 * the gpio entries for pwm fan control even when there's no
600 * actual fan connected to it... therm table? */
601 if (therm
->fan_get
&& therm
->fan_get(therm
) >= 0) {
602 ret
= sysfs_create_group(&hwmon_dev
->kobj
,
603 &hwmon_pwm_fan_attrgroup
);
608 /* if the card can read the fan rpm */
609 if (therm
->fan_sense(therm
) >= 0) {
610 ret
= sysfs_create_group(&hwmon_dev
->kobj
,
611 &hwmon_fan_rpm_attrgroup
);
616 hwmon
->hwmon
= hwmon_dev
;
621 NV_ERROR(drm
, "Unable to create some hwmon sysfs files: %d\n", ret
);
622 hwmon_device_unregister(hwmon_dev
);
631 nouveau_hwmon_fini(struct drm_device
*dev
)
633 #if defined(CONFIG_HWMON) || (defined(MODULE) && defined(CONFIG_HWMON_MODULE))
634 struct nouveau_hwmon
*hwmon
= nouveau_hwmon(dev
);
637 sysfs_remove_group(&hwmon
->hwmon
->kobj
, &hwmon_default_attrgroup
);
638 sysfs_remove_group(&hwmon
->hwmon
->kobj
, &hwmon_temp_attrgroup
);
639 sysfs_remove_group(&hwmon
->hwmon
->kobj
, &hwmon_pwm_fan_attrgroup
);
640 sysfs_remove_group(&hwmon
->hwmon
->kobj
, &hwmon_fan_rpm_attrgroup
);
642 hwmon_device_unregister(hwmon
->hwmon
);
645 nouveau_drm(dev
)->hwmon
= NULL
;