aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/thermal
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/thermal')
-rw-r--r--drivers/thermal/cpu_cooling.c360
-rw-r--r--drivers/thermal/db8500_cpufreq_cooling.c20
-rw-r--r--drivers/thermal/imx_thermal.c17
-rw-r--r--drivers/thermal/int340x_thermal/Makefile1
-rw-r--r--drivers/thermal/int340x_thermal/acpi_thermal_rel.c24
-rw-r--r--drivers/thermal/int340x_thermal/int3400_thermal.c1
-rw-r--r--drivers/thermal/int340x_thermal/int3402_thermal.c1
-rw-r--r--drivers/thermal/int340x_thermal/int3403_thermal.c4
-rw-r--r--drivers/thermal/int340x_thermal/processor_thermal_device.c311
-rw-r--r--drivers/thermal/intel_powerclamp.c1
-rw-r--r--drivers/thermal/of-thermal.c2
-rw-r--r--drivers/thermal/rcar_thermal.c17
-rw-r--r--drivers/thermal/rockchip_thermal.c1
-rw-r--r--drivers/thermal/samsung/Kconfig2
-rw-r--r--drivers/thermal/samsung/exynos_thermal_common.c12
-rw-r--r--drivers/thermal/samsung/exynos_tmu.c5
-rw-r--r--drivers/thermal/thermal_core.c6
-rw-r--r--drivers/thermal/thermal_core.h4
-rw-r--r--drivers/thermal/ti-soc-thermal/ti-thermal-common.c17
19 files changed, 514 insertions, 292 deletions
diff --git a/drivers/thermal/cpu_cooling.c b/drivers/thermal/cpu_cooling.c
index ad09e51ffae4..f65f0d109fc8 100644
--- a/drivers/thermal/cpu_cooling.c
+++ b/drivers/thermal/cpu_cooling.c
@@ -4,6 +4,8 @@
4 * Copyright (C) 2012 Samsung Electronics Co., Ltd(http://www.samsung.com) 4 * Copyright (C) 2012 Samsung Electronics Co., Ltd(http://www.samsung.com)
5 * Copyright (C) 2012 Amit Daniel <amit.kachhap@linaro.org> 5 * Copyright (C) 2012 Amit Daniel <amit.kachhap@linaro.org>
6 * 6 *
7 * Copyright (C) 2014 Viresh Kumar <viresh.kumar@linaro.org>
8 *
7 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 9 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
8 * This program is free software; you can redistribute it and/or modify 10 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by 11 * it under the terms of the GNU General Public License as published by
@@ -28,6 +30,20 @@
28#include <linux/cpu.h> 30#include <linux/cpu.h>
29#include <linux/cpu_cooling.h> 31#include <linux/cpu_cooling.h>
30 32
33/*
34 * Cooling state <-> CPUFreq frequency
35 *
36 * Cooling states are translated to frequencies throughout this driver and this
37 * is the relation between them.
38 *
39 * Highest cooling state corresponds to lowest possible frequency.
40 *
41 * i.e.
42 * level 0 --> 1st Max Freq
43 * level 1 --> 2nd Max Freq
44 * ...
45 */
46
31/** 47/**
32 * struct cpufreq_cooling_device - data for cooling device with cpufreq 48 * struct cpufreq_cooling_device - data for cooling device with cpufreq
33 * @id: unique integer value corresponding to each cpufreq_cooling_device 49 * @id: unique integer value corresponding to each cpufreq_cooling_device
@@ -38,25 +54,27 @@
38 * cooling devices. 54 * cooling devices.
39 * @cpufreq_val: integer value representing the absolute value of the clipped 55 * @cpufreq_val: integer value representing the absolute value of the clipped
40 * frequency. 56 * frequency.
57 * @max_level: maximum cooling level. One less than total number of valid
58 * cpufreq frequencies.
41 * @allowed_cpus: all the cpus involved for this cpufreq_cooling_device. 59 * @allowed_cpus: all the cpus involved for this cpufreq_cooling_device.
60 * @node: list_head to link all cpufreq_cooling_device together.
42 * 61 *
43 * This structure is required for keeping information of each 62 * This structure is required for keeping information of each registered
44 * cpufreq_cooling_device registered. In order to prevent corruption of this a 63 * cpufreq_cooling_device.
45 * mutex lock cooling_cpufreq_lock is used.
46 */ 64 */
47struct cpufreq_cooling_device { 65struct cpufreq_cooling_device {
48 int id; 66 int id;
49 struct thermal_cooling_device *cool_dev; 67 struct thermal_cooling_device *cool_dev;
50 unsigned int cpufreq_state; 68 unsigned int cpufreq_state;
51 unsigned int cpufreq_val; 69 unsigned int cpufreq_val;
70 unsigned int max_level;
71 unsigned int *freq_table; /* In descending order */
52 struct cpumask allowed_cpus; 72 struct cpumask allowed_cpus;
53 struct list_head node; 73 struct list_head node;
54}; 74};
55static DEFINE_IDR(cpufreq_idr); 75static DEFINE_IDR(cpufreq_idr);
56static DEFINE_MUTEX(cooling_cpufreq_lock); 76static DEFINE_MUTEX(cooling_cpufreq_lock);
57 77
58static unsigned int cpufreq_dev_count;
59
60static LIST_HEAD(cpufreq_dev_list); 78static LIST_HEAD(cpufreq_dev_list);
61 79
62/** 80/**
@@ -98,120 +116,30 @@ static void release_idr(struct idr *idr, int id)
98/* Below code defines functions to be used for cpufreq as cooling device */ 116/* Below code defines functions to be used for cpufreq as cooling device */
99 117
100/** 118/**
101 * is_cpufreq_valid - function to check frequency transitioning capability. 119 * get_level: Find the level for a particular frequency
102 * @cpu: cpu for which check is needed. 120 * @cpufreq_dev: cpufreq_dev for which the property is required
121 * @freq: Frequency
103 * 122 *
104 * This function will check the current state of the system if 123 * Return: level on success, THERMAL_CSTATE_INVALID on error.
105 * it is capable of changing the frequency for a given @cpu.
106 *
107 * Return: 0 if the system is not currently capable of changing
108 * the frequency of given cpu. !0 in case the frequency is changeable.
109 */ 124 */
110static int is_cpufreq_valid(int cpu) 125static unsigned long get_level(struct cpufreq_cooling_device *cpufreq_dev,
126 unsigned int freq)
111{ 127{
112 struct cpufreq_policy policy; 128 unsigned long level;
113
114 return !cpufreq_get_policy(&policy, cpu);
115}
116
117enum cpufreq_cooling_property {
118 GET_LEVEL,
119 GET_FREQ,
120 GET_MAXL,
121};
122
123/**
124 * get_property - fetch a property of interest for a give cpu.
125 * @cpu: cpu for which the property is required
126 * @input: query parameter
127 * @output: query return
128 * @property: type of query (frequency, level, max level)
129 *
130 * This is the common function to
131 * 1. get maximum cpu cooling states
132 * 2. translate frequency to cooling state
133 * 3. translate cooling state to frequency
134 * Note that the code may be not in good shape
135 * but it is written in this way in order to:
136 * a) reduce duplicate code as most of the code can be shared.
137 * b) make sure the logic is consistent when translating between
138 * cooling states and frequencies.
139 *
140 * Return: 0 on success, -EINVAL when invalid parameters are passed.
141 */
142static int get_property(unsigned int cpu, unsigned long input,
143 unsigned int *output,
144 enum cpufreq_cooling_property property)
145{
146 int i;
147 unsigned long max_level = 0, level = 0;
148 unsigned int freq = CPUFREQ_ENTRY_INVALID;
149 int descend = -1;
150 struct cpufreq_frequency_table *pos, *table =
151 cpufreq_frequency_get_table(cpu);
152
153 if (!output)
154 return -EINVAL;
155
156 if (!table)
157 return -EINVAL;
158
159 cpufreq_for_each_valid_entry(pos, table) {
160 /* ignore duplicate entry */
161 if (freq == pos->frequency)
162 continue;
163
164 /* get the frequency order */
165 if (freq != CPUFREQ_ENTRY_INVALID && descend == -1)
166 descend = freq > pos->frequency;
167
168 freq = pos->frequency;
169 max_level++;
170 }
171
172 /* No valid cpu frequency entry */
173 if (max_level == 0)
174 return -EINVAL;
175 129
176 /* max_level is an index, not a counter */ 130 for (level = 0; level <= cpufreq_dev->max_level; level++) {
177 max_level--; 131 if (freq == cpufreq_dev->freq_table[level])
132 return level;
178 133
179 /* get max level */ 134 if (freq > cpufreq_dev->freq_table[level])
180 if (property == GET_MAXL) { 135 break;
181 *output = (unsigned int)max_level;
182 return 0;
183 } 136 }
184 137
185 if (property == GET_FREQ) 138 return THERMAL_CSTATE_INVALID;
186 level = descend ? input : (max_level - input);
187
188 i = 0;
189 cpufreq_for_each_valid_entry(pos, table) {
190 /* ignore duplicate entry */
191 if (freq == pos->frequency)
192 continue;
193
194 /* now we have a valid frequency entry */
195 freq = pos->frequency;
196
197 if (property == GET_LEVEL && (unsigned int)input == freq) {
198 /* get level by frequency */
199 *output = descend ? i : (max_level - i);
200 return 0;
201 }
202 if (property == GET_FREQ && level == i) {
203 /* get frequency by level */
204 *output = freq;
205 return 0;
206 }
207 i++;
208 }
209
210 return -EINVAL;
211} 139}
212 140
213/** 141/**
214 * cpufreq_cooling_get_level - for a give cpu, return the cooling level. 142 * cpufreq_cooling_get_level - for a given cpu, return the cooling level.
215 * @cpu: cpu for which the level is required 143 * @cpu: cpu for which the level is required
216 * @freq: the frequency of interest 144 * @freq: the frequency of interest
217 * 145 *
@@ -223,77 +151,21 @@ static int get_property(unsigned int cpu, unsigned long input,
223 */ 151 */
224unsigned long cpufreq_cooling_get_level(unsigned int cpu, unsigned int freq) 152unsigned long cpufreq_cooling_get_level(unsigned int cpu, unsigned int freq)
225{ 153{
226 unsigned int val; 154 struct cpufreq_cooling_device *cpufreq_dev;
227
228 if (get_property(cpu, (unsigned long)freq, &val, GET_LEVEL))
229 return THERMAL_CSTATE_INVALID;
230
231 return (unsigned long)val;
232}
233EXPORT_SYMBOL_GPL(cpufreq_cooling_get_level);
234
235/**
236 * get_cpu_frequency - get the absolute value of frequency from level.
237 * @cpu: cpu for which frequency is fetched.
238 * @level: cooling level
239 *
240 * This function matches cooling level with frequency. Based on a cooling level
241 * of frequency, equals cooling state of cpu cooling device, it will return
242 * the corresponding frequency.
243 * e.g level=0 --> 1st MAX FREQ, level=1 ---> 2nd MAX FREQ, .... etc
244 *
245 * Return: 0 on error, the corresponding frequency otherwise.
246 */
247static unsigned int get_cpu_frequency(unsigned int cpu, unsigned long level)
248{
249 int ret = 0;
250 unsigned int freq;
251
252 ret = get_property(cpu, level, &freq, GET_FREQ);
253 if (ret)
254 return 0;
255
256 return freq;
257}
258
259/**
260 * cpufreq_apply_cooling - function to apply frequency clipping.
261 * @cpufreq_device: cpufreq_cooling_device pointer containing frequency
262 * clipping data.
263 * @cooling_state: value of the cooling state.
264 *
265 * Function used to make sure the cpufreq layer is aware of current thermal
266 * limits. The limits are applied by updating the cpufreq policy.
267 *
268 * Return: 0 on success, an error code otherwise (-EINVAL in case wrong
269 * cooling state).
270 */
271static int cpufreq_apply_cooling(struct cpufreq_cooling_device *cpufreq_device,
272 unsigned long cooling_state)
273{
274 unsigned int cpuid, clip_freq;
275 struct cpumask *mask = &cpufreq_device->allowed_cpus;
276 unsigned int cpu = cpumask_any(mask);
277
278
279 /* Check if the old cooling action is same as new cooling action */
280 if (cpufreq_device->cpufreq_state == cooling_state)
281 return 0;
282
283 clip_freq = get_cpu_frequency(cpu, cooling_state);
284 if (!clip_freq)
285 return -EINVAL;
286
287 cpufreq_device->cpufreq_state = cooling_state;
288 cpufreq_device->cpufreq_val = clip_freq;
289 155
290 for_each_cpu(cpuid, mask) { 156 mutex_lock(&cooling_cpufreq_lock);
291 if (is_cpufreq_valid(cpuid)) 157 list_for_each_entry(cpufreq_dev, &cpufreq_dev_list, node) {
292 cpufreq_update_policy(cpuid); 158 if (cpumask_test_cpu(cpu, &cpufreq_dev->allowed_cpus)) {
159 mutex_unlock(&cooling_cpufreq_lock);
160 return get_level(cpufreq_dev, freq);
161 }
293 } 162 }
163 mutex_unlock(&cooling_cpufreq_lock);
294 164
295 return 0; 165 pr_err("%s: cpu:%d not part of any cooling device\n", __func__, cpu);
166 return THERMAL_CSTATE_INVALID;
296} 167}
168EXPORT_SYMBOL_GPL(cpufreq_cooling_get_level);
297 169
298/** 170/**
299 * cpufreq_thermal_notifier - notifier callback for cpufreq policy change. 171 * cpufreq_thermal_notifier - notifier callback for cpufreq policy change.
@@ -323,11 +195,6 @@ static int cpufreq_thermal_notifier(struct notifier_block *nb,
323 &cpufreq_dev->allowed_cpus)) 195 &cpufreq_dev->allowed_cpus))
324 continue; 196 continue;
325 197
326 if (!cpufreq_dev->cpufreq_val)
327 cpufreq_dev->cpufreq_val = get_cpu_frequency(
328 cpumask_any(&cpufreq_dev->allowed_cpus),
329 cpufreq_dev->cpufreq_state);
330
331 max_freq = cpufreq_dev->cpufreq_val; 198 max_freq = cpufreq_dev->cpufreq_val;
332 199
333 if (policy->max != max_freq) 200 if (policy->max != max_freq)
@@ -354,19 +221,9 @@ static int cpufreq_get_max_state(struct thermal_cooling_device *cdev,
354 unsigned long *state) 221 unsigned long *state)
355{ 222{
356 struct cpufreq_cooling_device *cpufreq_device = cdev->devdata; 223 struct cpufreq_cooling_device *cpufreq_device = cdev->devdata;
357 struct cpumask *mask = &cpufreq_device->allowed_cpus;
358 unsigned int cpu;
359 unsigned int count = 0;
360 int ret;
361
362 cpu = cpumask_any(mask);
363
364 ret = get_property(cpu, 0, &count, GET_MAXL);
365 224
366 if (count > 0) 225 *state = cpufreq_device->max_level;
367 *state = count; 226 return 0;
368
369 return ret;
370} 227}
371 228
372/** 229/**
@@ -403,8 +260,24 @@ static int cpufreq_set_cur_state(struct thermal_cooling_device *cdev,
403 unsigned long state) 260 unsigned long state)
404{ 261{
405 struct cpufreq_cooling_device *cpufreq_device = cdev->devdata; 262 struct cpufreq_cooling_device *cpufreq_device = cdev->devdata;
263 unsigned int cpu = cpumask_any(&cpufreq_device->allowed_cpus);
264 unsigned int clip_freq;
265
266 /* Request state should be less than max_level */
267 if (WARN_ON(state > cpufreq_device->max_level))
268 return -EINVAL;
269
270 /* Check if the old cooling action is same as new cooling action */
271 if (cpufreq_device->cpufreq_state == state)
272 return 0;
406 273
407 return cpufreq_apply_cooling(cpufreq_device, state); 274 clip_freq = cpufreq_device->freq_table[state];
275 cpufreq_device->cpufreq_state = state;
276 cpufreq_device->cpufreq_val = clip_freq;
277
278 cpufreq_update_policy(cpu);
279
280 return 0;
408} 281}
409 282
410/* Bind cpufreq callbacks to thermal cooling device ops */ 283/* Bind cpufreq callbacks to thermal cooling device ops */
@@ -419,10 +292,25 @@ static struct notifier_block thermal_cpufreq_notifier_block = {
419 .notifier_call = cpufreq_thermal_notifier, 292 .notifier_call = cpufreq_thermal_notifier,
420}; 293};
421 294
295static unsigned int find_next_max(struct cpufreq_frequency_table *table,
296 unsigned int prev_max)
297{
298 struct cpufreq_frequency_table *pos;
299 unsigned int max = 0;
300
301 cpufreq_for_each_valid_entry(pos, table) {
302 if (pos->frequency > max && pos->frequency < prev_max)
303 max = pos->frequency;
304 }
305
306 return max;
307}
308
422/** 309/**
423 * __cpufreq_cooling_register - helper function to create cpufreq cooling device 310 * __cpufreq_cooling_register - helper function to create cpufreq cooling device
424 * @np: a valid struct device_node to the cooling device device tree node 311 * @np: a valid struct device_node to the cooling device device tree node
425 * @clip_cpus: cpumask of cpus where the frequency constraints will happen. 312 * @clip_cpus: cpumask of cpus where the frequency constraints will happen.
313 * Normally this should be same as cpufreq policy->related_cpus.
426 * 314 *
427 * This interface function registers the cpufreq cooling device with the name 315 * This interface function registers the cpufreq cooling device with the name
428 * "thermal-cpufreq-%x". This api can support multiple instances of cpufreq 316 * "thermal-cpufreq-%x". This api can support multiple instances of cpufreq
@@ -437,37 +325,42 @@ __cpufreq_cooling_register(struct device_node *np,
437 const struct cpumask *clip_cpus) 325 const struct cpumask *clip_cpus)
438{ 326{
439 struct thermal_cooling_device *cool_dev; 327 struct thermal_cooling_device *cool_dev;
440 struct cpufreq_cooling_device *cpufreq_dev = NULL; 328 struct cpufreq_cooling_device *cpufreq_dev;
441 unsigned int min = 0, max = 0;
442 char dev_name[THERMAL_NAME_LENGTH]; 329 char dev_name[THERMAL_NAME_LENGTH];
443 int ret = 0, i; 330 struct cpufreq_frequency_table *pos, *table;
444 struct cpufreq_policy policy; 331 unsigned int freq, i;
332 int ret;
445 333
446 /* Verify that all the clip cpus have same freq_min, freq_max limit */ 334 table = cpufreq_frequency_get_table(cpumask_first(clip_cpus));
447 for_each_cpu(i, clip_cpus) { 335 if (!table) {
448 /* continue if cpufreq policy not found and not return error */ 336 pr_debug("%s: CPUFreq table not found\n", __func__);
449 if (!cpufreq_get_policy(&policy, i)) 337 return ERR_PTR(-EPROBE_DEFER);
450 continue;
451 if (min == 0 && max == 0) {
452 min = policy.cpuinfo.min_freq;
453 max = policy.cpuinfo.max_freq;
454 } else {
455 if (min != policy.cpuinfo.min_freq ||
456 max != policy.cpuinfo.max_freq)
457 return ERR_PTR(-EINVAL);
458 }
459 } 338 }
460 cpufreq_dev = kzalloc(sizeof(struct cpufreq_cooling_device), 339
461 GFP_KERNEL); 340 cpufreq_dev = kzalloc(sizeof(*cpufreq_dev), GFP_KERNEL);
462 if (!cpufreq_dev) 341 if (!cpufreq_dev)
463 return ERR_PTR(-ENOMEM); 342 return ERR_PTR(-ENOMEM);
464 343
344 /* Find max levels */
345 cpufreq_for_each_valid_entry(pos, table)
346 cpufreq_dev->max_level++;
347
348 cpufreq_dev->freq_table = kmalloc(sizeof(*cpufreq_dev->freq_table) *
349 cpufreq_dev->max_level, GFP_KERNEL);
350 if (!cpufreq_dev->freq_table) {
351 cool_dev = ERR_PTR(-ENOMEM);
352 goto free_cdev;
353 }
354
355 /* max_level is an index, not a counter */
356 cpufreq_dev->max_level--;
357
465 cpumask_copy(&cpufreq_dev->allowed_cpus, clip_cpus); 358 cpumask_copy(&cpufreq_dev->allowed_cpus, clip_cpus);
466 359
467 ret = get_idr(&cpufreq_idr, &cpufreq_dev->id); 360 ret = get_idr(&cpufreq_idr, &cpufreq_dev->id);
468 if (ret) { 361 if (ret) {
469 kfree(cpufreq_dev); 362 cool_dev = ERR_PTR(ret);
470 return ERR_PTR(-EINVAL); 363 goto free_table;
471 } 364 }
472 365
473 snprintf(dev_name, sizeof(dev_name), "thermal-cpufreq-%d", 366 snprintf(dev_name, sizeof(dev_name), "thermal-cpufreq-%d",
@@ -475,25 +368,44 @@ __cpufreq_cooling_register(struct device_node *np,
475 368
476 cool_dev = thermal_of_cooling_device_register(np, dev_name, cpufreq_dev, 369 cool_dev = thermal_of_cooling_device_register(np, dev_name, cpufreq_dev,
477 &cpufreq_cooling_ops); 370 &cpufreq_cooling_ops);
478 if (IS_ERR(cool_dev)) { 371 if (IS_ERR(cool_dev))
479 release_idr(&cpufreq_idr, cpufreq_dev->id); 372 goto remove_idr;
480 kfree(cpufreq_dev); 373
481 return cool_dev; 374 /* Fill freq-table in descending order of frequencies */
375 for (i = 0, freq = -1; i <= cpufreq_dev->max_level; i++) {
376 freq = find_next_max(table, freq);
377 cpufreq_dev->freq_table[i] = freq;
378
379 /* Warn for duplicate entries */
380 if (!freq)
381 pr_warn("%s: table has duplicate entries\n", __func__);
382 else
383 pr_debug("%s: freq:%u KHz\n", __func__, freq);
482 } 384 }
385
386 cpufreq_dev->cpufreq_val = cpufreq_dev->freq_table[0];
483 cpufreq_dev->cool_dev = cool_dev; 387 cpufreq_dev->cool_dev = cool_dev;
484 cpufreq_dev->cpufreq_state = 0; 388
485 mutex_lock(&cooling_cpufreq_lock); 389 mutex_lock(&cooling_cpufreq_lock);
486 390
487 /* Register the notifier for first cpufreq cooling device */ 391 /* Register the notifier for first cpufreq cooling device */
488 if (cpufreq_dev_count == 0) 392 if (list_empty(&cpufreq_dev_list))
489 cpufreq_register_notifier(&thermal_cpufreq_notifier_block, 393 cpufreq_register_notifier(&thermal_cpufreq_notifier_block,
490 CPUFREQ_POLICY_NOTIFIER); 394 CPUFREQ_POLICY_NOTIFIER);
491 cpufreq_dev_count++;
492 list_add(&cpufreq_dev->node, &cpufreq_dev_list); 395 list_add(&cpufreq_dev->node, &cpufreq_dev_list);
493 396
494 mutex_unlock(&cooling_cpufreq_lock); 397 mutex_unlock(&cooling_cpufreq_lock);
495 398
496 return cool_dev; 399 return cool_dev;
400
401remove_idr:
402 release_idr(&cpufreq_idr, cpufreq_dev->id);
403free_table:
404 kfree(cpufreq_dev->freq_table);
405free_cdev:
406 kfree(cpufreq_dev);
407
408 return cool_dev;
497} 409}
498 410
499/** 411/**
@@ -554,16 +466,16 @@ void cpufreq_cooling_unregister(struct thermal_cooling_device *cdev)
554 cpufreq_dev = cdev->devdata; 466 cpufreq_dev = cdev->devdata;
555 mutex_lock(&cooling_cpufreq_lock); 467 mutex_lock(&cooling_cpufreq_lock);
556 list_del(&cpufreq_dev->node); 468 list_del(&cpufreq_dev->node);
557 cpufreq_dev_count--;
558 469
559 /* Unregister the notifier for the last cpufreq cooling device */ 470 /* Unregister the notifier for the last cpufreq cooling device */
560 if (cpufreq_dev_count == 0) 471 if (list_empty(&cpufreq_dev_list))
561 cpufreq_unregister_notifier(&thermal_cpufreq_notifier_block, 472 cpufreq_unregister_notifier(&thermal_cpufreq_notifier_block,
562 CPUFREQ_POLICY_NOTIFIER); 473 CPUFREQ_POLICY_NOTIFIER);
563 mutex_unlock(&cooling_cpufreq_lock); 474 mutex_unlock(&cooling_cpufreq_lock);
564 475
565 thermal_cooling_device_unregister(cpufreq_dev->cool_dev); 476 thermal_cooling_device_unregister(cpufreq_dev->cool_dev);
566 release_idr(&cpufreq_idr, cpufreq_dev->id); 477 release_idr(&cpufreq_idr, cpufreq_dev->id);
478 kfree(cpufreq_dev->freq_table);
567 kfree(cpufreq_dev); 479 kfree(cpufreq_dev);
568} 480}
569EXPORT_SYMBOL_GPL(cpufreq_cooling_unregister); 481EXPORT_SYMBOL_GPL(cpufreq_cooling_unregister);
diff --git a/drivers/thermal/db8500_cpufreq_cooling.c b/drivers/thermal/db8500_cpufreq_cooling.c
index 000d53e934a0..607b62c7e611 100644
--- a/drivers/thermal/db8500_cpufreq_cooling.c
+++ b/drivers/thermal/db8500_cpufreq_cooling.c
@@ -18,7 +18,6 @@
18 */ 18 */
19 19
20#include <linux/cpu_cooling.h> 20#include <linux/cpu_cooling.h>
21#include <linux/cpufreq.h>
22#include <linux/err.h> 21#include <linux/err.h>
23#include <linux/module.h> 22#include <linux/module.h>
24#include <linux/of.h> 23#include <linux/of.h>
@@ -28,18 +27,17 @@
28static int db8500_cpufreq_cooling_probe(struct platform_device *pdev) 27static int db8500_cpufreq_cooling_probe(struct platform_device *pdev)
29{ 28{
30 struct thermal_cooling_device *cdev; 29 struct thermal_cooling_device *cdev;
31 struct cpumask mask_val;
32
33 /* make sure cpufreq driver has been initialized */
34 if (!cpufreq_frequency_get_table(0))
35 return -EPROBE_DEFER;
36
37 cpumask_set_cpu(0, &mask_val);
38 cdev = cpufreq_cooling_register(&mask_val);
39 30
31 cdev = cpufreq_cooling_register(cpu_present_mask);
40 if (IS_ERR(cdev)) { 32 if (IS_ERR(cdev)) {
41 dev_err(&pdev->dev, "Failed to register cooling device\n"); 33 int ret = PTR_ERR(cdev);
42 return PTR_ERR(cdev); 34
35 if (ret != -EPROBE_DEFER)
36 dev_err(&pdev->dev,
37 "Failed to register cooling device %d\n",
38 ret);
39
40 return ret;
43 } 41 }
44 42
45 platform_set_drvdata(pdev, cdev); 43 platform_set_drvdata(pdev, cdev);
diff --git a/drivers/thermal/imx_thermal.c b/drivers/thermal/imx_thermal.c
index 88b32f942dcf..2ccbc0788353 100644
--- a/drivers/thermal/imx_thermal.c
+++ b/drivers/thermal/imx_thermal.c
@@ -9,7 +9,6 @@
9 9
10#include <linux/clk.h> 10#include <linux/clk.h>
11#include <linux/cpu_cooling.h> 11#include <linux/cpu_cooling.h>
12#include <linux/cpufreq.h>
13#include <linux/delay.h> 12#include <linux/delay.h>
14#include <linux/device.h> 13#include <linux/device.h>
15#include <linux/init.h> 14#include <linux/init.h>
@@ -454,15 +453,10 @@ static int imx_thermal_probe(struct platform_device *pdev)
454 const struct of_device_id *of_id = 453 const struct of_device_id *of_id =
455 of_match_device(of_imx_thermal_match, &pdev->dev); 454 of_match_device(of_imx_thermal_match, &pdev->dev);
456 struct imx_thermal_data *data; 455 struct imx_thermal_data *data;
457 struct cpumask clip_cpus;
458 struct regmap *map; 456 struct regmap *map;
459 int measure_freq; 457 int measure_freq;
460 int ret; 458 int ret;
461 459
462 if (!cpufreq_get_current_driver()) {
463 dev_dbg(&pdev->dev, "no cpufreq driver!");
464 return -EPROBE_DEFER;
465 }
466 data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); 460 data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
467 if (!data) 461 if (!data)
468 return -ENOMEM; 462 return -ENOMEM;
@@ -516,12 +510,13 @@ static int imx_thermal_probe(struct platform_device *pdev)
516 regmap_write(map, MISC0 + REG_SET, MISC0_REFTOP_SELBIASOFF); 510 regmap_write(map, MISC0 + REG_SET, MISC0_REFTOP_SELBIASOFF);
517 regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_POWER_DOWN); 511 regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_POWER_DOWN);
518 512
519 cpumask_set_cpu(0, &clip_cpus); 513 data->cdev = cpufreq_cooling_register(cpu_present_mask);
520 data->cdev = cpufreq_cooling_register(&clip_cpus);
521 if (IS_ERR(data->cdev)) { 514 if (IS_ERR(data->cdev)) {
522 ret = PTR_ERR(data->cdev); 515 ret = PTR_ERR(data->cdev);
523 dev_err(&pdev->dev, 516 if (ret != -EPROBE_DEFER)
524 "failed to register cpufreq cooling device: %d\n", ret); 517 dev_err(&pdev->dev,
518 "failed to register cpufreq cooling device: %d\n",
519 ret);
525 return ret; 520 return ret;
526 } 521 }
527 522
@@ -613,6 +608,7 @@ static int imx_thermal_suspend(struct device *dev)
613 regmap_write(map, TEMPSENSE0 + REG_CLR, TEMPSENSE0_MEASURE_TEMP); 608 regmap_write(map, TEMPSENSE0 + REG_CLR, TEMPSENSE0_MEASURE_TEMP);
614 regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_POWER_DOWN); 609 regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_POWER_DOWN);
615 data->mode = THERMAL_DEVICE_DISABLED; 610 data->mode = THERMAL_DEVICE_DISABLED;
611 clk_disable_unprepare(data->thermal_clk);
616 612
617 return 0; 613 return 0;
618} 614}
@@ -622,6 +618,7 @@ static int imx_thermal_resume(struct device *dev)
622 struct imx_thermal_data *data = dev_get_drvdata(dev); 618 struct imx_thermal_data *data = dev_get_drvdata(dev);
623 struct regmap *map = data->tempmon; 619 struct regmap *map = data->tempmon;
624 620
621 clk_prepare_enable(data->thermal_clk);
625 /* Enabled thermal sensor after resume */ 622 /* Enabled thermal sensor after resume */
626 regmap_write(map, TEMPSENSE0 + REG_CLR, TEMPSENSE0_POWER_DOWN); 623 regmap_write(map, TEMPSENSE0 + REG_CLR, TEMPSENSE0_POWER_DOWN);
627 regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_MEASURE_TEMP); 624 regmap_write(map, TEMPSENSE0 + REG_SET, TEMPSENSE0_MEASURE_TEMP);
diff --git a/drivers/thermal/int340x_thermal/Makefile b/drivers/thermal/int340x_thermal/Makefile
index ffe40bffaf1a..d4413698a85f 100644
--- a/drivers/thermal/int340x_thermal/Makefile
+++ b/drivers/thermal/int340x_thermal/Makefile
@@ -1,4 +1,5 @@
1obj-$(CONFIG_INT340X_THERMAL) += int3400_thermal.o 1obj-$(CONFIG_INT340X_THERMAL) += int3400_thermal.o
2obj-$(CONFIG_INT340X_THERMAL) += int3402_thermal.o 2obj-$(CONFIG_INT340X_THERMAL) += int3402_thermal.o
3obj-$(CONFIG_INT340X_THERMAL) += int3403_thermal.o 3obj-$(CONFIG_INT340X_THERMAL) += int3403_thermal.o
4obj-$(CONFIG_INT340X_THERMAL) += processor_thermal_device.o
4obj-$(CONFIG_ACPI_THERMAL_REL) += acpi_thermal_rel.o 5obj-$(CONFIG_ACPI_THERMAL_REL) += acpi_thermal_rel.o
diff --git a/drivers/thermal/int340x_thermal/acpi_thermal_rel.c b/drivers/thermal/int340x_thermal/acpi_thermal_rel.c
index e4e61b3fb11e..2c2ec7666eb1 100644
--- a/drivers/thermal/int340x_thermal/acpi_thermal_rel.c
+++ b/drivers/thermal/int340x_thermal/acpi_thermal_rel.c
@@ -82,7 +82,7 @@ int acpi_parse_trt(acpi_handle handle, int *trt_count, struct trt **trtp,
82 struct acpi_buffer trt_format = { sizeof("RRNNNNNN"), "RRNNNNNN" }; 82 struct acpi_buffer trt_format = { sizeof("RRNNNNNN"), "RRNNNNNN" };
83 83
84 if (!acpi_has_method(handle, "_TRT")) 84 if (!acpi_has_method(handle, "_TRT"))
85 return 0; 85 return -ENODEV;
86 86
87 status = acpi_evaluate_object(handle, "_TRT", NULL, &buffer); 87 status = acpi_evaluate_object(handle, "_TRT", NULL, &buffer);
88 if (ACPI_FAILURE(status)) 88 if (ACPI_FAILURE(status))
@@ -119,15 +119,11 @@ int acpi_parse_trt(acpi_handle handle, int *trt_count, struct trt **trtp,
119 continue; 119 continue;
120 120
121 result = acpi_bus_get_device(trt->source, &adev); 121 result = acpi_bus_get_device(trt->source, &adev);
122 if (!result) 122 if (result)
123 acpi_create_platform_device(adev);
124 else
125 pr_warn("Failed to get source ACPI device\n"); 123 pr_warn("Failed to get source ACPI device\n");
126 124
127 result = acpi_bus_get_device(trt->target, &adev); 125 result = acpi_bus_get_device(trt->target, &adev);
128 if (!result) 126 if (result)
129 acpi_create_platform_device(adev);
130 else
131 pr_warn("Failed to get target ACPI device\n"); 127 pr_warn("Failed to get target ACPI device\n");
132 } 128 }
133 129
@@ -167,7 +163,7 @@ int acpi_parse_art(acpi_handle handle, int *art_count, struct art **artp,
167 sizeof("RRNNNNNNNNNNN"), "RRNNNNNNNNNNN" }; 163 sizeof("RRNNNNNNNNNNN"), "RRNNNNNNNNNNN" };
168 164
169 if (!acpi_has_method(handle, "_ART")) 165 if (!acpi_has_method(handle, "_ART"))
170 return 0; 166 return -ENODEV;
171 167
172 status = acpi_evaluate_object(handle, "_ART", NULL, &buffer); 168 status = acpi_evaluate_object(handle, "_ART", NULL, &buffer);
173 if (ACPI_FAILURE(status)) 169 if (ACPI_FAILURE(status))
@@ -206,16 +202,12 @@ int acpi_parse_art(acpi_handle handle, int *art_count, struct art **artp,
206 202
207 if (art->source) { 203 if (art->source) {
208 result = acpi_bus_get_device(art->source, &adev); 204 result = acpi_bus_get_device(art->source, &adev);
209 if (!result) 205 if (result)
210 acpi_create_platform_device(adev);
211 else
212 pr_warn("Failed to get source ACPI device\n"); 206 pr_warn("Failed to get source ACPI device\n");
213 } 207 }
214 if (art->target) { 208 if (art->target) {
215 result = acpi_bus_get_device(art->target, &adev); 209 result = acpi_bus_get_device(art->target, &adev);
216 if (!result) 210 if (result)
217 acpi_create_platform_device(adev);
218 else
219 pr_warn("Failed to get source ACPI device\n"); 211 pr_warn("Failed to get source ACPI device\n");
220 } 212 }
221 } 213 }
@@ -321,8 +313,8 @@ static long acpi_thermal_rel_ioctl(struct file *f, unsigned int cmd,
321 unsigned long length = 0; 313 unsigned long length = 0;
322 int count = 0; 314 int count = 0;
323 char __user *arg = (void __user *)__arg; 315 char __user *arg = (void __user *)__arg;
324 struct trt *trts; 316 struct trt *trts = NULL;
325 struct art *arts; 317 struct art *arts = NULL;
326 318
327 switch (cmd) { 319 switch (cmd) {
328 case ACPI_THERMAL_GET_TRT_COUNT: 320 case ACPI_THERMAL_GET_TRT_COUNT:
diff --git a/drivers/thermal/int340x_thermal/int3400_thermal.c b/drivers/thermal/int340x_thermal/int3400_thermal.c
index dcb306ea14a4..65a98a97df07 100644
--- a/drivers/thermal/int340x_thermal/int3400_thermal.c
+++ b/drivers/thermal/int340x_thermal/int3400_thermal.c
@@ -335,7 +335,6 @@ static struct platform_driver int3400_thermal_driver = {
335 .remove = int3400_thermal_remove, 335 .remove = int3400_thermal_remove,
336 .driver = { 336 .driver = {
337 .name = "int3400 thermal", 337 .name = "int3400 thermal",
338 .owner = THIS_MODULE,
339 .acpi_match_table = ACPI_PTR(int3400_thermal_match), 338 .acpi_match_table = ACPI_PTR(int3400_thermal_match),
340 }, 339 },
341}; 340};
diff --git a/drivers/thermal/int340x_thermal/int3402_thermal.c b/drivers/thermal/int340x_thermal/int3402_thermal.c
index a5d08c14ba24..c5cbc3af3a05 100644
--- a/drivers/thermal/int340x_thermal/int3402_thermal.c
+++ b/drivers/thermal/int340x_thermal/int3402_thermal.c
@@ -231,7 +231,6 @@ static struct platform_driver int3402_thermal_driver = {
231 .remove = int3402_thermal_remove, 231 .remove = int3402_thermal_remove,
232 .driver = { 232 .driver = {
233 .name = "int3402 thermal", 233 .name = "int3402 thermal",
234 .owner = THIS_MODULE,
235 .acpi_match_table = int3402_thermal_match, 234 .acpi_match_table = int3402_thermal_match,
236 }, 235 },
237}; 236};
diff --git a/drivers/thermal/int340x_thermal/int3403_thermal.c b/drivers/thermal/int340x_thermal/int3403_thermal.c
index 1bfa6a69e77a..0faf500d8a77 100644
--- a/drivers/thermal/int340x_thermal/int3403_thermal.c
+++ b/drivers/thermal/int340x_thermal/int3403_thermal.c
@@ -301,6 +301,8 @@ static int int3403_sensor_remove(struct int3403_priv *priv)
301{ 301{
302 struct int3403_sensor *obj = priv->priv; 302 struct int3403_sensor *obj = priv->priv;
303 303
304 acpi_remove_notify_handler(priv->adev->handle,
305 ACPI_DEVICE_NOTIFY, int3403_notify);
304 thermal_zone_device_unregister(obj->tzone); 306 thermal_zone_device_unregister(obj->tzone);
305 return 0; 307 return 0;
306} 308}
@@ -369,6 +371,7 @@ static int int3403_cdev_add(struct int3403_priv *priv)
369 p = buf.pointer; 371 p = buf.pointer;
370 if (!p || (p->type != ACPI_TYPE_PACKAGE)) { 372 if (!p || (p->type != ACPI_TYPE_PACKAGE)) {
371 printk(KERN_WARNING "Invalid PPSS data\n"); 373 printk(KERN_WARNING "Invalid PPSS data\n");
374 kfree(buf.pointer);
372 return -EFAULT; 375 return -EFAULT;
373 } 376 }
374 377
@@ -381,6 +384,7 @@ static int int3403_cdev_add(struct int3403_priv *priv)
381 384
382 priv->priv = obj; 385 priv->priv = obj;
383 386
387 kfree(buf.pointer);
384 /* TODO: add ACPI notification support */ 388 /* TODO: add ACPI notification support */
385 389
386 return result; 390 return result;
diff --git a/drivers/thermal/int340x_thermal/processor_thermal_device.c b/drivers/thermal/int340x_thermal/processor_thermal_device.c
new file mode 100644
index 000000000000..0fe5dbbea968
--- /dev/null
+++ b/drivers/thermal/int340x_thermal/processor_thermal_device.c
@@ -0,0 +1,311 @@
1/*
2 * processor_thermal_device.c
3 * Copyright (c) 2014, Intel Corporation.
4 *
5 * This program is free software; you can redistribute it and/or modify it
6 * under the terms and conditions of the GNU General Public License,
7 * version 2, as published by the Free Software Foundation.
8 *
9 * This program is distributed in the hope it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12 * more details.
13 *
14 */
15#include <linux/kernel.h>
16#include <linux/module.h>
17#include <linux/init.h>
18#include <linux/pci.h>
19#include <linux/platform_device.h>
20#include <linux/acpi.h>
21
22/* Broadwell-U/HSB thermal reporting device */
23#define PCI_DEVICE_ID_PROC_BDW_THERMAL 0x1603
24#define PCI_DEVICE_ID_PROC_HSB_THERMAL 0x0A03
25
26/* Braswell thermal reporting device */
27#define PCI_DEVICE_ID_PROC_BSW_THERMAL 0x22DC
28
29struct power_config {
30 u32 index;
31 u32 min_uw;
32 u32 max_uw;
33 u32 tmin_us;
34 u32 tmax_us;
35 u32 step_uw;
36};
37
38struct proc_thermal_device {
39 struct device *dev;
40 struct acpi_device *adev;
41 struct power_config power_limits[2];
42};
43
44enum proc_thermal_emum_mode_type {
45 PROC_THERMAL_NONE,
46 PROC_THERMAL_PCI,
47 PROC_THERMAL_PLATFORM_DEV
48};
49
50/*
51 * We can have only one type of enumeration, PCI or Platform,
52 * not both. So we don't need instance specific data.
53 */
54static enum proc_thermal_emum_mode_type proc_thermal_emum_mode =
55 PROC_THERMAL_NONE;
56
57#define POWER_LIMIT_SHOW(index, suffix) \
58static ssize_t power_limit_##index##_##suffix##_show(struct device *dev, \
59 struct device_attribute *attr, \
60 char *buf) \
61{ \
62 struct pci_dev *pci_dev; \
63 struct platform_device *pdev; \
64 struct proc_thermal_device *proc_dev; \
65\
66 if (proc_thermal_emum_mode == PROC_THERMAL_PLATFORM_DEV) { \
67 pdev = to_platform_device(dev); \
68 proc_dev = platform_get_drvdata(pdev); \
69 } else { \
70 pci_dev = to_pci_dev(dev); \
71 proc_dev = pci_get_drvdata(pci_dev); \
72 } \
73 return sprintf(buf, "%lu\n",\
74 (unsigned long)proc_dev->power_limits[index].suffix * 1000); \
75}
76
77POWER_LIMIT_SHOW(0, min_uw)
78POWER_LIMIT_SHOW(0, max_uw)
79POWER_LIMIT_SHOW(0, step_uw)
80POWER_LIMIT_SHOW(0, tmin_us)
81POWER_LIMIT_SHOW(0, tmax_us)
82
83POWER_LIMIT_SHOW(1, min_uw)
84POWER_LIMIT_SHOW(1, max_uw)
85POWER_LIMIT_SHOW(1, step_uw)
86POWER_LIMIT_SHOW(1, tmin_us)
87POWER_LIMIT_SHOW(1, tmax_us)
88
89static DEVICE_ATTR_RO(power_limit_0_min_uw);
90static DEVICE_ATTR_RO(power_limit_0_max_uw);
91static DEVICE_ATTR_RO(power_limit_0_step_uw);
92static DEVICE_ATTR_RO(power_limit_0_tmin_us);
93static DEVICE_ATTR_RO(power_limit_0_tmax_us);
94
95static DEVICE_ATTR_RO(power_limit_1_min_uw);
96static DEVICE_ATTR_RO(power_limit_1_max_uw);
97static DEVICE_ATTR_RO(power_limit_1_step_uw);
98static DEVICE_ATTR_RO(power_limit_1_tmin_us);
99static DEVICE_ATTR_RO(power_limit_1_tmax_us);
100
101static struct attribute *power_limit_attrs[] = {
102 &dev_attr_power_limit_0_min_uw.attr,
103 &dev_attr_power_limit_1_min_uw.attr,
104 &dev_attr_power_limit_0_max_uw.attr,
105 &dev_attr_power_limit_1_max_uw.attr,
106 &dev_attr_power_limit_0_step_uw.attr,
107 &dev_attr_power_limit_1_step_uw.attr,
108 &dev_attr_power_limit_0_tmin_us.attr,
109 &dev_attr_power_limit_1_tmin_us.attr,
110 &dev_attr_power_limit_0_tmax_us.attr,
111 &dev_attr_power_limit_1_tmax_us.attr,
112 NULL
113};
114
115static struct attribute_group power_limit_attribute_group = {
116 .attrs = power_limit_attrs,
117 .name = "power_limits"
118};
119
120static int proc_thermal_add(struct device *dev,
121 struct proc_thermal_device **priv)
122{
123 struct proc_thermal_device *proc_priv;
124 struct acpi_device *adev;
125 acpi_status status;
126 struct acpi_buffer buf = { ACPI_ALLOCATE_BUFFER, NULL };
127 union acpi_object *elements, *ppcc;
128 union acpi_object *p;
129 int i;
130 int ret;
131
132 adev = ACPI_COMPANION(dev);
133 if (!adev)
134 return -ENODEV;
135
136 status = acpi_evaluate_object(adev->handle, "PPCC", NULL, &buf);
137 if (ACPI_FAILURE(status))
138 return -ENODEV;
139
140 p = buf.pointer;
141 if (!p || (p->type != ACPI_TYPE_PACKAGE)) {
142 dev_err(dev, "Invalid PPCC data\n");
143 ret = -EFAULT;
144 goto free_buffer;
145 }
146 if (!p->package.count) {
147 dev_err(dev, "Invalid PPCC package size\n");
148 ret = -EFAULT;
149 goto free_buffer;
150 }
151
152 proc_priv = devm_kzalloc(dev, sizeof(*proc_priv), GFP_KERNEL);
153 if (!proc_priv) {
154 ret = -ENOMEM;
155 goto free_buffer;
156 }
157
158 proc_priv->dev = dev;
159 proc_priv->adev = adev;
160
161 for (i = 0; i < min((int)p->package.count - 1, 2); ++i) {
162 elements = &(p->package.elements[i+1]);
163 if (elements->type != ACPI_TYPE_PACKAGE ||
164 elements->package.count != 6) {
165 ret = -EFAULT;
166 goto free_buffer;
167 }
168 ppcc = elements->package.elements;
169 proc_priv->power_limits[i].index = ppcc[0].integer.value;
170 proc_priv->power_limits[i].min_uw = ppcc[1].integer.value;
171 proc_priv->power_limits[i].max_uw = ppcc[2].integer.value;
172 proc_priv->power_limits[i].tmin_us = ppcc[3].integer.value;
173 proc_priv->power_limits[i].tmax_us = ppcc[4].integer.value;
174 proc_priv->power_limits[i].step_uw = ppcc[5].integer.value;
175 }
176
177 *priv = proc_priv;
178
179 ret = sysfs_create_group(&dev->kobj,
180 &power_limit_attribute_group);
181
182free_buffer:
183 kfree(buf.pointer);
184
185 return ret;
186}
187
188void proc_thermal_remove(struct proc_thermal_device *proc_priv)
189{
190 sysfs_remove_group(&proc_priv->dev->kobj,
191 &power_limit_attribute_group);
192}
193
194static int int3401_add(struct platform_device *pdev)
195{
196 struct proc_thermal_device *proc_priv;
197 int ret;
198
199 if (proc_thermal_emum_mode == PROC_THERMAL_PCI) {
200 dev_err(&pdev->dev, "error: enumerated as PCI dev\n");
201 return -ENODEV;
202 }
203
204 ret = proc_thermal_add(&pdev->dev, &proc_priv);
205 if (ret)
206 return ret;
207
208 platform_set_drvdata(pdev, proc_priv);
209 proc_thermal_emum_mode = PROC_THERMAL_PLATFORM_DEV;
210
211 return 0;
212}
213
214static int int3401_remove(struct platform_device *pdev)
215{
216 proc_thermal_remove(platform_get_drvdata(pdev));
217
218 return 0;
219}
220
221static int proc_thermal_pci_probe(struct pci_dev *pdev,
222 const struct pci_device_id *unused)
223{
224 struct proc_thermal_device *proc_priv;
225 int ret;
226
227 if (proc_thermal_emum_mode == PROC_THERMAL_PLATFORM_DEV) {
228 dev_err(&pdev->dev, "error: enumerated as platform dev\n");
229 return -ENODEV;
230 }
231
232 ret = pci_enable_device(pdev);
233 if (ret < 0) {
234 dev_err(&pdev->dev, "error: could not enable device\n");
235 return ret;
236 }
237
238 ret = proc_thermal_add(&pdev->dev, &proc_priv);
239 if (ret) {
240 pci_disable_device(pdev);
241 return ret;
242 }
243
244 pci_set_drvdata(pdev, proc_priv);
245 proc_thermal_emum_mode = PROC_THERMAL_PCI;
246
247 return 0;
248}
249
250static void proc_thermal_pci_remove(struct pci_dev *pdev)
251{
252 proc_thermal_remove(pci_get_drvdata(pdev));
253 pci_disable_device(pdev);
254}
255
256static const struct pci_device_id proc_thermal_pci_ids[] = {
257 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_PROC_BDW_THERMAL)},
258 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_PROC_HSB_THERMAL)},
259 { PCI_DEVICE(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_PROC_BSW_THERMAL)},
260 { 0, },
261};
262
263MODULE_DEVICE_TABLE(pci, proc_thermal_pci_ids);
264
265static struct pci_driver proc_thermal_pci_driver = {
266 .name = "proc_thermal",
267 .probe = proc_thermal_pci_probe,
268 .remove = proc_thermal_pci_remove,
269 .id_table = proc_thermal_pci_ids,
270};
271
272static const struct acpi_device_id int3401_device_ids[] = {
273 {"INT3401", 0},
274 {"", 0},
275};
276MODULE_DEVICE_TABLE(acpi, int3401_device_ids);
277
278static struct platform_driver int3401_driver = {
279 .probe = int3401_add,
280 .remove = int3401_remove,
281 .driver = {
282 .name = "int3401 thermal",
283 .acpi_match_table = int3401_device_ids,
284 },
285};
286
287static int __init proc_thermal_init(void)
288{
289 int ret;
290
291 ret = platform_driver_register(&int3401_driver);
292 if (ret)
293 return ret;
294
295 ret = pci_register_driver(&proc_thermal_pci_driver);
296
297 return ret;
298}
299
300static void __exit proc_thermal_exit(void)
301{
302 platform_driver_unregister(&int3401_driver);
303 pci_unregister_driver(&proc_thermal_pci_driver);
304}
305
306module_init(proc_thermal_init);
307module_exit(proc_thermal_exit);
308
309MODULE_AUTHOR("Srinivas Pandruvada <srinivas.pandruvada@linux.intel.com>");
310MODULE_DESCRIPTION("Processor Thermal Reporting Device Driver");
311MODULE_LICENSE("GPL v2");
diff --git a/drivers/thermal/intel_powerclamp.c b/drivers/thermal/intel_powerclamp.c
index e98b4249187c..6ceebd659dd4 100644
--- a/drivers/thermal/intel_powerclamp.c
+++ b/drivers/thermal/intel_powerclamp.c
@@ -688,6 +688,7 @@ static const struct x86_cpu_id intel_powerclamp_ids[] = {
688 { X86_VENDOR_INTEL, 6, 0x45}, 688 { X86_VENDOR_INTEL, 6, 0x45},
689 { X86_VENDOR_INTEL, 6, 0x46}, 689 { X86_VENDOR_INTEL, 6, 0x46},
690 { X86_VENDOR_INTEL, 6, 0x4c}, 690 { X86_VENDOR_INTEL, 6, 0x4c},
691 { X86_VENDOR_INTEL, 6, 0x56},
691 {} 692 {}
692}; 693};
693MODULE_DEVICE_TABLE(x86cpu, intel_powerclamp_ids); 694MODULE_DEVICE_TABLE(x86cpu, intel_powerclamp_ids);
diff --git a/drivers/thermal/of-thermal.c b/drivers/thermal/of-thermal.c
index e145b66df444..d717f3dab6f1 100644
--- a/drivers/thermal/of-thermal.c
+++ b/drivers/thermal/of-thermal.c
@@ -149,7 +149,7 @@ EXPORT_SYMBOL_GPL(of_thermal_is_trip_valid);
149 * 149 *
150 * Return: pointer to trip points table, NULL otherwise 150 * Return: pointer to trip points table, NULL otherwise
151 */ 151 */
152const struct thermal_trip * const 152const struct thermal_trip *
153of_thermal_get_trip_points(struct thermal_zone_device *tz) 153of_thermal_get_trip_points(struct thermal_zone_device *tz)
154{ 154{
155 struct __thermal_zone *data = tz->devdata; 155 struct __thermal_zone *data = tz->devdata;
diff --git a/drivers/thermal/rcar_thermal.c b/drivers/thermal/rcar_thermal.c
index 8803e693fe68..2580a4872f90 100644
--- a/drivers/thermal/rcar_thermal.c
+++ b/drivers/thermal/rcar_thermal.c
@@ -63,7 +63,7 @@ struct rcar_thermal_priv {
63 struct mutex lock; 63 struct mutex lock;
64 struct list_head list; 64 struct list_head list;
65 int id; 65 int id;
66 int ctemp; 66 u32 ctemp;
67}; 67};
68 68
69#define rcar_thermal_for_each_priv(pos, common) \ 69#define rcar_thermal_for_each_priv(pos, common) \
@@ -145,7 +145,7 @@ static int rcar_thermal_update_temp(struct rcar_thermal_priv *priv)
145{ 145{
146 struct device *dev = rcar_priv_to_dev(priv); 146 struct device *dev = rcar_priv_to_dev(priv);
147 int i; 147 int i;
148 int ctemp, old, new; 148 u32 ctemp, old, new;
149 int ret = -EINVAL; 149 int ret = -EINVAL;
150 150
151 mutex_lock(&priv->lock); 151 mutex_lock(&priv->lock);
@@ -372,6 +372,7 @@ static int rcar_thermal_probe(struct platform_device *pdev)
372 int i; 372 int i;
373 int ret = -ENODEV; 373 int ret = -ENODEV;
374 int idle = IDLE_INTERVAL; 374 int idle = IDLE_INTERVAL;
375 u32 enr_bits = 0;
375 376
376 common = devm_kzalloc(dev, sizeof(*common), GFP_KERNEL); 377 common = devm_kzalloc(dev, sizeof(*common), GFP_KERNEL);
377 if (!common) 378 if (!common)
@@ -390,7 +391,7 @@ static int rcar_thermal_probe(struct platform_device *pdev)
390 391
391 /* 392 /*
392 * platform has IRQ support. 393 * platform has IRQ support.
393 * Then, drier use common register 394 * Then, driver uses common registers
394 */ 395 */
395 396
396 ret = devm_request_irq(dev, irq->start, rcar_thermal_irq, 0, 397 ret = devm_request_irq(dev, irq->start, rcar_thermal_irq, 0,
@@ -408,9 +409,6 @@ static int rcar_thermal_probe(struct platform_device *pdev)
408 if (IS_ERR(common->base)) 409 if (IS_ERR(common->base))
409 return PTR_ERR(common->base); 410 return PTR_ERR(common->base);
410 411
411 /* enable temperature comparation */
412 rcar_thermal_common_write(common, ENR, 0x00030303);
413
414 idle = 0; /* polling delay is not needed */ 412 idle = 0; /* polling delay is not needed */
415 } 413 }
416 414
@@ -452,8 +450,15 @@ static int rcar_thermal_probe(struct platform_device *pdev)
452 rcar_thermal_irq_enable(priv); 450 rcar_thermal_irq_enable(priv);
453 451
454 list_move_tail(&priv->list, &common->head); 452 list_move_tail(&priv->list, &common->head);
453
454 /* update ENR bits */
455 enr_bits |= 3 << (i * 8);
455 } 456 }
456 457
458 /* enable temperature comparation */
459 if (irq)
460 rcar_thermal_common_write(common, ENR, enr_bits);
461
457 platform_set_drvdata(pdev, common); 462 platform_set_drvdata(pdev, common);
458 463
459 dev_info(dev, "%d sensor probed\n", i); 464 dev_info(dev, "%d sensor probed\n", i);
diff --git a/drivers/thermal/rockchip_thermal.c b/drivers/thermal/rockchip_thermal.c
index 1bcddfc60e91..9c6ce548e363 100644
--- a/drivers/thermal/rockchip_thermal.c
+++ b/drivers/thermal/rockchip_thermal.c
@@ -677,7 +677,6 @@ static SIMPLE_DEV_PM_OPS(rockchip_thermal_pm_ops,
677static struct platform_driver rockchip_thermal_driver = { 677static struct platform_driver rockchip_thermal_driver = {
678 .driver = { 678 .driver = {
679 .name = "rockchip-thermal", 679 .name = "rockchip-thermal",
680 .owner = THIS_MODULE,
681 .pm = &rockchip_thermal_pm_ops, 680 .pm = &rockchip_thermal_pm_ops,
682 .of_match_table = of_rockchip_thermal_match, 681 .of_match_table = of_rockchip_thermal_match,
683 }, 682 },
diff --git a/drivers/thermal/samsung/Kconfig b/drivers/thermal/samsung/Kconfig
index f760389a204c..c43306ecc0ab 100644
--- a/drivers/thermal/samsung/Kconfig
+++ b/drivers/thermal/samsung/Kconfig
@@ -1,6 +1,6 @@
1config EXYNOS_THERMAL 1config EXYNOS_THERMAL
2 tristate "Exynos thermal management unit driver" 2 tristate "Exynos thermal management unit driver"
3 depends on ARCH_HAS_BANDGAP && OF 3 depends on OF
4 help 4 help
5 If you say yes here you get support for the TMU (Thermal Management 5 If you say yes here you get support for the TMU (Thermal Management
6 Unit) driver for SAMSUNG EXYNOS series of SoCs. This driver initialises 6 Unit) driver for SAMSUNG EXYNOS series of SoCs. This driver initialises
diff --git a/drivers/thermal/samsung/exynos_thermal_common.c b/drivers/thermal/samsung/exynos_thermal_common.c
index b6be572704a4..6dc3815cc73f 100644
--- a/drivers/thermal/samsung/exynos_thermal_common.c
+++ b/drivers/thermal/samsung/exynos_thermal_common.c
@@ -347,7 +347,6 @@ void exynos_report_trigger(struct thermal_sensor_conf *conf)
347int exynos_register_thermal(struct thermal_sensor_conf *sensor_conf) 347int exynos_register_thermal(struct thermal_sensor_conf *sensor_conf)
348{ 348{
349 int ret; 349 int ret;
350 struct cpumask mask_val;
351 struct exynos_thermal_zone *th_zone; 350 struct exynos_thermal_zone *th_zone;
352 351
353 if (!sensor_conf || !sensor_conf->read_temperature) { 352 if (!sensor_conf || !sensor_conf->read_temperature) {
@@ -367,13 +366,14 @@ int exynos_register_thermal(struct thermal_sensor_conf *sensor_conf)
367 * sensor 366 * sensor
368 */ 367 */
369 if (sensor_conf->cooling_data.freq_clip_count > 0) { 368 if (sensor_conf->cooling_data.freq_clip_count > 0) {
370 cpumask_set_cpu(0, &mask_val);
371 th_zone->cool_dev[th_zone->cool_dev_size] = 369 th_zone->cool_dev[th_zone->cool_dev_size] =
372 cpufreq_cooling_register(&mask_val); 370 cpufreq_cooling_register(cpu_present_mask);
373 if (IS_ERR(th_zone->cool_dev[th_zone->cool_dev_size])) { 371 if (IS_ERR(th_zone->cool_dev[th_zone->cool_dev_size])) {
374 dev_err(sensor_conf->dev, 372 ret = PTR_ERR(th_zone->cool_dev[th_zone->cool_dev_size]);
375 "Failed to register cpufreq cooling device\n"); 373 if (ret != -EPROBE_DEFER)
376 ret = -EINVAL; 374 dev_err(sensor_conf->dev,
375 "Failed to register cpufreq cooling device: %d\n",
376 ret);
377 goto err_unregister; 377 goto err_unregister;
378 } 378 }
379 th_zone->cool_dev_size++; 379 th_zone->cool_dev_size++;
diff --git a/drivers/thermal/samsung/exynos_tmu.c b/drivers/thermal/samsung/exynos_tmu.c
index d44d91d681d4..d2f1e62a4232 100644
--- a/drivers/thermal/samsung/exynos_tmu.c
+++ b/drivers/thermal/samsung/exynos_tmu.c
@@ -927,7 +927,10 @@ static int exynos_tmu_probe(struct platform_device *pdev)
927 /* Register the sensor with thermal management interface */ 927 /* Register the sensor with thermal management interface */
928 ret = exynos_register_thermal(sensor_conf); 928 ret = exynos_register_thermal(sensor_conf);
929 if (ret) { 929 if (ret) {
930 dev_err(&pdev->dev, "Failed to register thermal interface\n"); 930 if (ret != -EPROBE_DEFER)
931 dev_err(&pdev->dev,
932 "Failed to register thermal interface: %d\n",
933 ret);
931 goto err_clk; 934 goto err_clk;
932 } 935 }
933 data->reg_conf = sensor_conf; 936 data->reg_conf = sensor_conf;
diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c
index 84fdf0792e27..87e0b0782023 100644
--- a/drivers/thermal/thermal_core.c
+++ b/drivers/thermal/thermal_core.c
@@ -930,7 +930,7 @@ int thermal_zone_bind_cooling_device(struct thermal_zone_device *tz,
930 struct thermal_zone_device *pos1; 930 struct thermal_zone_device *pos1;
931 struct thermal_cooling_device *pos2; 931 struct thermal_cooling_device *pos2;
932 unsigned long max_state; 932 unsigned long max_state;
933 int result; 933 int result, ret;
934 934
935 if (trip >= tz->trips || (trip < 0 && trip != THERMAL_TRIPS_NONE)) 935 if (trip >= tz->trips || (trip < 0 && trip != THERMAL_TRIPS_NONE))
936 return -EINVAL; 936 return -EINVAL;
@@ -947,7 +947,9 @@ int thermal_zone_bind_cooling_device(struct thermal_zone_device *tz,
947 if (tz != pos1 || cdev != pos2) 947 if (tz != pos1 || cdev != pos2)
948 return -EINVAL; 948 return -EINVAL;
949 949
950 cdev->ops->get_max_state(cdev, &max_state); 950 ret = cdev->ops->get_max_state(cdev, &max_state);
951 if (ret)
952 return ret;
951 953
952 /* lower default 0, upper default max_state */ 954 /* lower default 0, upper default max_state */
953 lower = lower == THERMAL_NO_LIMIT ? 0 : lower; 955 lower = lower == THERMAL_NO_LIMIT ? 0 : lower;
diff --git a/drivers/thermal/thermal_core.h b/drivers/thermal/thermal_core.h
index 9083e7520623..0531c752fbbb 100644
--- a/drivers/thermal/thermal_core.h
+++ b/drivers/thermal/thermal_core.h
@@ -91,7 +91,7 @@ int of_parse_thermal_zones(void);
91void of_thermal_destroy_zones(void); 91void of_thermal_destroy_zones(void);
92int of_thermal_get_ntrips(struct thermal_zone_device *); 92int of_thermal_get_ntrips(struct thermal_zone_device *);
93bool of_thermal_is_trip_valid(struct thermal_zone_device *, int); 93bool of_thermal_is_trip_valid(struct thermal_zone_device *, int);
94const struct thermal_trip * const 94const struct thermal_trip *
95of_thermal_get_trip_points(struct thermal_zone_device *); 95of_thermal_get_trip_points(struct thermal_zone_device *);
96#else 96#else
97static inline int of_parse_thermal_zones(void) { return 0; } 97static inline int of_parse_thermal_zones(void) { return 0; }
@@ -105,7 +105,7 @@ static inline bool of_thermal_is_trip_valid(struct thermal_zone_device *tz,
105{ 105{
106 return 0; 106 return 0;
107} 107}
108static inline const struct thermal_trip * const 108static inline const struct thermal_trip *
109of_thermal_get_trip_points(struct thermal_zone_device *tz) 109of_thermal_get_trip_points(struct thermal_zone_device *tz)
110{ 110{
111 return NULL; 111 return NULL;
diff --git a/drivers/thermal/ti-soc-thermal/ti-thermal-common.c b/drivers/thermal/ti-soc-thermal/ti-thermal-common.c
index 5fd03865e396..3fb054a10f6a 100644
--- a/drivers/thermal/ti-soc-thermal/ti-thermal-common.c
+++ b/drivers/thermal/ti-soc-thermal/ti-thermal-common.c
@@ -28,7 +28,6 @@
28#include <linux/kernel.h> 28#include <linux/kernel.h>
29#include <linux/workqueue.h> 29#include <linux/workqueue.h>
30#include <linux/thermal.h> 30#include <linux/thermal.h>
31#include <linux/cpufreq.h>
32#include <linux/cpumask.h> 31#include <linux/cpumask.h>
33#include <linux/cpu_cooling.h> 32#include <linux/cpu_cooling.h>
34#include <linux/of.h> 33#include <linux/of.h>
@@ -407,17 +406,17 @@ int ti_thermal_register_cpu_cooling(struct ti_bandgap *bgp, int id)
407 if (!data) 406 if (!data)
408 return -EINVAL; 407 return -EINVAL;
409 408
410 if (!cpufreq_get_current_driver()) {
411 dev_dbg(bgp->dev, "no cpufreq driver yet\n");
412 return -EPROBE_DEFER;
413 }
414
415 /* Register cooling device */ 409 /* Register cooling device */
416 data->cool_dev = cpufreq_cooling_register(cpu_present_mask); 410 data->cool_dev = cpufreq_cooling_register(cpu_present_mask);
417 if (IS_ERR(data->cool_dev)) { 411 if (IS_ERR(data->cool_dev)) {
418 dev_err(bgp->dev, 412 int ret = PTR_ERR(data->cool_dev);
419 "Failed to register cpufreq cooling device\n"); 413
420 return PTR_ERR(data->cool_dev); 414 if (ret != -EPROBE_DEFER)
415 dev_err(bgp->dev,
416 "Failed to register cpu cooling device %d\n",
417 ret);
418
419 return ret;
421 } 420 }
422 ti_bandgap_set_sensor_data(bgp, id, data); 421 ti_bandgap_set_sensor_data(bgp, id, data);
423 422