aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/thermal/thermal_core.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/thermal/thermal_core.c')
-rw-r--r--drivers/thermal/thermal_core.c86
1 files changed, 79 insertions, 7 deletions
diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
index f1d511a9475b..338a88bf6662 100644
--- a/drivers/thermal/thermal_core.c
+++ b/drivers/thermal/thermal_core.c
@@ -34,6 +34,7 @@
34#include <linux/thermal.h> 34#include <linux/thermal.h>
35#include <linux/reboot.h> 35#include <linux/reboot.h>
36#include <linux/string.h> 36#include <linux/string.h>
37#include <linux/of.h>
37#include <net/netlink.h> 38#include <net/netlink.h>
38#include <net/genetlink.h> 39#include <net/genetlink.h>
39 40
@@ -403,7 +404,7 @@ int thermal_zone_get_temp(struct thermal_zone_device *tz, unsigned long *temp)
403 enum thermal_trip_type type; 404 enum thermal_trip_type type;
404#endif 405#endif
405 406
406 if (!tz || IS_ERR(tz)) 407 if (!tz || IS_ERR(tz) || !tz->ops->get_temp)
407 goto exit; 408 goto exit;
408 409
409 mutex_lock(&tz->lock); 410 mutex_lock(&tz->lock);
@@ -450,12 +451,18 @@ static void update_temperature(struct thermal_zone_device *tz)
450 tz->last_temperature = tz->temperature; 451 tz->last_temperature = tz->temperature;
451 tz->temperature = temp; 452 tz->temperature = temp;
452 mutex_unlock(&tz->lock); 453 mutex_unlock(&tz->lock);
454
455 dev_dbg(&tz->device, "last_temperature=%d, current_temperature=%d\n",
456 tz->last_temperature, tz->temperature);
453} 457}
454 458
455void thermal_zone_device_update(struct thermal_zone_device *tz) 459void thermal_zone_device_update(struct thermal_zone_device *tz)
456{ 460{
457 int count; 461 int count;
458 462
463 if (!tz->ops->get_temp)
464 return;
465
459 update_temperature(tz); 466 update_temperature(tz);
460 467
461 for (count = 0; count < tz->trips; count++) 468 for (count = 0; count < tz->trips; count++)
@@ -774,6 +781,9 @@ emul_temp_store(struct device *dev, struct device_attribute *attr,
774 ret = tz->ops->set_emul_temp(tz, temperature); 781 ret = tz->ops->set_emul_temp(tz, temperature);
775 } 782 }
776 783
784 if (!ret)
785 thermal_zone_device_update(tz);
786
777 return ret ? ret : count; 787 return ret ? ret : count;
778} 788}
779static DEVICE_ATTR(emul_temp, S_IWUSR, NULL, emul_temp_store); 789static DEVICE_ATTR(emul_temp, S_IWUSR, NULL, emul_temp_store);
@@ -1052,7 +1062,8 @@ static struct class thermal_class = {
1052}; 1062};
1053 1063
1054/** 1064/**
1055 * thermal_cooling_device_register() - register a new thermal cooling device 1065 * __thermal_cooling_device_register() - register a new thermal cooling device
1066 * @np: a pointer to a device tree node.
1056 * @type: the thermal cooling device type. 1067 * @type: the thermal cooling device type.
1057 * @devdata: device private data. 1068 * @devdata: device private data.
1058 * @ops: standard thermal cooling devices callbacks. 1069 * @ops: standard thermal cooling devices callbacks.
@@ -1060,13 +1071,16 @@ static struct class thermal_class = {
1060 * This interface function adds a new thermal cooling device (fan/processor/...) 1071 * This interface function adds a new thermal cooling device (fan/processor/...)
1061 * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself 1072 * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
1062 * to all the thermal zone devices registered at the same time. 1073 * to all the thermal zone devices registered at the same time.
1074 * It also gives the opportunity to link the cooling device to a device tree
1075 * node, so that it can be bound to a thermal zone created out of device tree.
1063 * 1076 *
1064 * Return: a pointer to the created struct thermal_cooling_device or an 1077 * Return: a pointer to the created struct thermal_cooling_device or an
1065 * ERR_PTR. Caller must check return value with IS_ERR*() helpers. 1078 * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
1066 */ 1079 */
1067struct thermal_cooling_device * 1080static struct thermal_cooling_device *
1068thermal_cooling_device_register(char *type, void *devdata, 1081__thermal_cooling_device_register(struct device_node *np,
1069 const struct thermal_cooling_device_ops *ops) 1082 char *type, void *devdata,
1083 const struct thermal_cooling_device_ops *ops)
1070{ 1084{
1071 struct thermal_cooling_device *cdev; 1085 struct thermal_cooling_device *cdev;
1072 int result; 1086 int result;
@@ -1091,6 +1105,7 @@ thermal_cooling_device_register(char *type, void *devdata,
1091 strlcpy(cdev->type, type ? : "", sizeof(cdev->type)); 1105 strlcpy(cdev->type, type ? : "", sizeof(cdev->type));
1092 mutex_init(&cdev->lock); 1106 mutex_init(&cdev->lock);
1093 INIT_LIST_HEAD(&cdev->thermal_instances); 1107 INIT_LIST_HEAD(&cdev->thermal_instances);
1108 cdev->np = np;
1094 cdev->ops = ops; 1109 cdev->ops = ops;
1095 cdev->updated = true; 1110 cdev->updated = true;
1096 cdev->device.class = &thermal_class; 1111 cdev->device.class = &thermal_class;
@@ -1133,9 +1148,53 @@ unregister:
1133 device_unregister(&cdev->device); 1148 device_unregister(&cdev->device);
1134 return ERR_PTR(result); 1149 return ERR_PTR(result);
1135} 1150}
1151
1152/**
1153 * thermal_cooling_device_register() - register a new thermal cooling device
1154 * @type: the thermal cooling device type.
1155 * @devdata: device private data.
1156 * @ops: standard thermal cooling devices callbacks.
1157 *
1158 * This interface function adds a new thermal cooling device (fan/processor/...)
1159 * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
1160 * to all the thermal zone devices registered at the same time.
1161 *
1162 * Return: a pointer to the created struct thermal_cooling_device or an
1163 * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
1164 */
1165struct thermal_cooling_device *
1166thermal_cooling_device_register(char *type, void *devdata,
1167 const struct thermal_cooling_device_ops *ops)
1168{
1169 return __thermal_cooling_device_register(NULL, type, devdata, ops);
1170}
1136EXPORT_SYMBOL_GPL(thermal_cooling_device_register); 1171EXPORT_SYMBOL_GPL(thermal_cooling_device_register);
1137 1172
1138/** 1173/**
1174 * thermal_of_cooling_device_register() - register an OF thermal cooling device
1175 * @np: a pointer to a device tree node.
1176 * @type: the thermal cooling device type.
1177 * @devdata: device private data.
1178 * @ops: standard thermal cooling devices callbacks.
1179 *
1180 * This function will register a cooling device with device tree node reference.
1181 * This interface function adds a new thermal cooling device (fan/processor/...)
1182 * to /sys/class/thermal/ folder as cooling_device[0-*]. It tries to bind itself
1183 * to all the thermal zone devices registered at the same time.
1184 *
1185 * Return: a pointer to the created struct thermal_cooling_device or an
1186 * ERR_PTR. Caller must check return value with IS_ERR*() helpers.
1187 */
1188struct thermal_cooling_device *
1189thermal_of_cooling_device_register(struct device_node *np,
1190 char *type, void *devdata,
1191 const struct thermal_cooling_device_ops *ops)
1192{
1193 return __thermal_cooling_device_register(np, type, devdata, ops);
1194}
1195EXPORT_SYMBOL_GPL(thermal_of_cooling_device_register);
1196
1197/**
1139 * thermal_cooling_device_unregister - removes the registered thermal cooling device 1198 * thermal_cooling_device_unregister - removes the registered thermal cooling device
1140 * @cdev: the thermal cooling device to remove. 1199 * @cdev: the thermal cooling device to remove.
1141 * 1200 *
@@ -1207,6 +1266,8 @@ void thermal_cdev_update(struct thermal_cooling_device *cdev)
1207 mutex_lock(&cdev->lock); 1266 mutex_lock(&cdev->lock);
1208 /* Make sure cdev enters the deepest cooling state */ 1267 /* Make sure cdev enters the deepest cooling state */
1209 list_for_each_entry(instance, &cdev->thermal_instances, cdev_node) { 1268 list_for_each_entry(instance, &cdev->thermal_instances, cdev_node) {
1269 dev_dbg(&cdev->device, "zone%d->target=%lu\n",
1270 instance->tz->id, instance->target);
1210 if (instance->target == THERMAL_NO_TARGET) 1271 if (instance->target == THERMAL_NO_TARGET)
1211 continue; 1272 continue;
1212 if (instance->target > target) 1273 if (instance->target > target)
@@ -1215,6 +1276,7 @@ void thermal_cdev_update(struct thermal_cooling_device *cdev)
1215 mutex_unlock(&cdev->lock); 1276 mutex_unlock(&cdev->lock);
1216 cdev->ops->set_cur_state(cdev, target); 1277 cdev->ops->set_cur_state(cdev, target);
1217 cdev->updated = true; 1278 cdev->updated = true;
1279 dev_dbg(&cdev->device, "set to state %lu\n", target);
1218} 1280}
1219EXPORT_SYMBOL(thermal_cdev_update); 1281EXPORT_SYMBOL(thermal_cdev_update);
1220 1282
@@ -1370,7 +1432,7 @@ static void remove_trip_attrs(struct thermal_zone_device *tz)
1370 */ 1432 */
1371struct thermal_zone_device *thermal_zone_device_register(const char *type, 1433struct thermal_zone_device *thermal_zone_device_register(const char *type,
1372 int trips, int mask, void *devdata, 1434 int trips, int mask, void *devdata,
1373 const struct thermal_zone_device_ops *ops, 1435 struct thermal_zone_device_ops *ops,
1374 const struct thermal_zone_params *tzp, 1436 const struct thermal_zone_params *tzp,
1375 int passive_delay, int polling_delay) 1437 int passive_delay, int polling_delay)
1376{ 1438{
@@ -1386,7 +1448,7 @@ struct thermal_zone_device *thermal_zone_device_register(const char *type,
1386 if (trips > THERMAL_MAX_TRIPS || trips < 0 || mask >> trips) 1448 if (trips > THERMAL_MAX_TRIPS || trips < 0 || mask >> trips)
1387 return ERR_PTR(-EINVAL); 1449 return ERR_PTR(-EINVAL);
1388 1450
1389 if (!ops || !ops->get_temp) 1451 if (!ops)
1390 return ERR_PTR(-EINVAL); 1452 return ERR_PTR(-EINVAL);
1391 1453
1392 if (trips > 0 && (!ops->get_trip_type || !ops->get_trip_temp)) 1454 if (trips > 0 && (!ops->get_trip_type || !ops->get_trip_temp))
@@ -1490,6 +1552,9 @@ struct thermal_zone_device *thermal_zone_device_register(const char *type,
1490 1552
1491 INIT_DELAYED_WORK(&(tz->poll_queue), thermal_zone_device_check); 1553 INIT_DELAYED_WORK(&(tz->poll_queue), thermal_zone_device_check);
1492 1554
1555 if (!tz->ops->get_temp)
1556 thermal_zone_device_set_polling(tz, 0);
1557
1493 thermal_zone_device_update(tz); 1558 thermal_zone_device_update(tz);
1494 1559
1495 if (!result) 1560 if (!result)
@@ -1740,8 +1805,14 @@ static int __init thermal_init(void)
1740 if (result) 1805 if (result)
1741 goto unregister_class; 1806 goto unregister_class;
1742 1807
1808 result = of_parse_thermal_zones();
1809 if (result)
1810 goto exit_netlink;
1811
1743 return 0; 1812 return 0;
1744 1813
1814exit_netlink:
1815 genetlink_exit();
1745unregister_governors: 1816unregister_governors:
1746 thermal_unregister_governors(); 1817 thermal_unregister_governors();
1747unregister_class: 1818unregister_class:
@@ -1757,6 +1828,7 @@ error:
1757 1828
1758static void __exit thermal_exit(void) 1829static void __exit thermal_exit(void)
1759{ 1830{
1831 of_thermal_destroy_zones();
1760 genetlink_exit(); 1832 genetlink_exit();
1761 class_unregister(&thermal_class); 1833 class_unregister(&thermal_class);
1762 thermal_unregister_governors(); 1834 thermal_unregister_governors();