aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/cpufreq/cpufreq.c47
1 files changed, 28 insertions, 19 deletions
diff --git a/drivers/cpufreq/cpufreq.c b/drivers/cpufreq/cpufreq.c
index 7a511479ae29..6bbe5825765a 100644
--- a/drivers/cpufreq/cpufreq.c
+++ b/drivers/cpufreq/cpufreq.c
@@ -229,44 +229,53 @@ static inline void adjust_jiffies(unsigned long val, struct cpufreq_freqs *ci) {
229 229
230 230
231/** 231/**
232 * cpufreq_notify_transition - call notifier chain and adjust_jiffies on frequency transition 232 * cpufreq_notify_transition - call notifier chain and adjust_jiffies
233 * on frequency transition.
233 * 234 *
234 * This function calls the transition notifiers and the "adjust_jiffies" function. It is called 235 * This function calls the transition notifiers and the "adjust_jiffies"
235 * twice on all CPU frequency changes that have external effects. 236 * function. It is called twice on all CPU frequency changes that have
237 * external effects.
236 */ 238 */
237void cpufreq_notify_transition(struct cpufreq_freqs *freqs, unsigned int state) 239void cpufreq_notify_transition(struct cpufreq_freqs *freqs, unsigned int state)
238{ 240{
241 struct cpufreq_policy *policy;
242
239 BUG_ON(irqs_disabled()); 243 BUG_ON(irqs_disabled());
240 244
241 freqs->flags = cpufreq_driver->flags; 245 freqs->flags = cpufreq_driver->flags;
242 dprintk("notification %u of frequency transition to %u kHz\n", state, freqs->new); 246 dprintk("notification %u of frequency transition to %u kHz\n",
247 state, freqs->new);
243 248
244 down_read(&cpufreq_notifier_rwsem); 249 down_read(&cpufreq_notifier_rwsem);
250
251 policy = cpufreq_cpu_data[freqs->cpu];
245 switch (state) { 252 switch (state) {
253
246 case CPUFREQ_PRECHANGE: 254 case CPUFREQ_PRECHANGE:
247 /* detect if the driver reported a value as "old frequency" which 255 /* detect if the driver reported a value as "old frequency"
248 * is not equal to what the cpufreq core thinks is "old frequency". 256 * which is not equal to what the cpufreq core thinks is
257 * "old frequency".
249 */ 258 */
250 if (!(cpufreq_driver->flags & CPUFREQ_CONST_LOOPS)) { 259 if (!(cpufreq_driver->flags & CPUFREQ_CONST_LOOPS)) {
251 if ((likely(cpufreq_cpu_data[freqs->cpu])) && 260 if ((policy) && (policy->cpu == freqs->cpu) &&
252 (likely(cpufreq_cpu_data[freqs->cpu]->cpu == freqs->cpu)) && 261 (policy->cur) && (policy->cur != freqs->old)) {
253 (likely(cpufreq_cpu_data[freqs->cpu]->cur)) && 262 dprintk(KERN_WARNING "Warning: CPU frequency is"
254 (unlikely(freqs->old != cpufreq_cpu_data[freqs->cpu]->cur))) 263 " %u, cpufreq assumed %u kHz.\n",
255 { 264 freqs->old, policy->cur);
256 dprintk(KERN_WARNING "Warning: CPU frequency is %u, " 265 freqs->old = policy->cur;
257 "cpufreq assumed %u kHz.\n", freqs->old, cpufreq_cpu_data[freqs->cpu]->cur);
258 freqs->old = cpufreq_cpu_data[freqs->cpu]->cur;
259 } 266 }
260 } 267 }
261 notifier_call_chain(&cpufreq_transition_notifier_list, CPUFREQ_PRECHANGE, freqs); 268 notifier_call_chain(&cpufreq_transition_notifier_list,
269 CPUFREQ_PRECHANGE, freqs);
262 adjust_jiffies(CPUFREQ_PRECHANGE, freqs); 270 adjust_jiffies(CPUFREQ_PRECHANGE, freqs);
263 break; 271 break;
272
264 case CPUFREQ_POSTCHANGE: 273 case CPUFREQ_POSTCHANGE:
265 adjust_jiffies(CPUFREQ_POSTCHANGE, freqs); 274 adjust_jiffies(CPUFREQ_POSTCHANGE, freqs);
266 notifier_call_chain(&cpufreq_transition_notifier_list, CPUFREQ_POSTCHANGE, freqs); 275 notifier_call_chain(&cpufreq_transition_notifier_list,
267 if ((likely(cpufreq_cpu_data[freqs->cpu])) && 276 CPUFREQ_POSTCHANGE, freqs);
268 (likely(cpufreq_cpu_data[freqs->cpu]->cpu == freqs->cpu))) 277 if (likely(policy) && likely(policy->cpu == freqs->cpu))
269 cpufreq_cpu_data[freqs->cpu]->cur = freqs->new; 278 policy->cur = freqs->new;
270 break; 279 break;
271 } 280 }
272 up_read(&cpufreq_notifier_rwsem); 281 up_read(&cpufreq_notifier_rwsem);