blob: 030212104fe6dfc6b9cbcafff6d3e7331593cea9 [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/*
2 * linux/drivers/cpufreq/cpufreq.c
3 *
4 * Copyright (C) 2001 Russell King
5 * (C) 2002 - 2003 Dominik Brodowski <linux@brodo.de>
Viresh Kumarbb176f72013-06-19 14:19:33 +05306 * (C) 2013 Viresh Kumar <viresh.kumar@linaro.org>
Linus Torvalds1da177e2005-04-16 15:20:36 -07007 *
Ashok Rajc32b6b82005-10-30 14:59:54 -08008 * Oct 2005 - Ashok Raj <ashok.raj@intel.com>
Dave Jones32ee8c32006-02-28 00:43:23 -05009 * Added handling for CPU hotplug
Dave Jones8ff69732006-03-05 03:37:23 -050010 * Feb 2006 - Jacob Shin <jacob.shin@amd.com>
11 * Fix handling for CPU hotplug -- affected CPUs
Ashok Rajc32b6b82005-10-30 14:59:54 -080012 *
Linus Torvalds1da177e2005-04-16 15:20:36 -070013 * This program is free software; you can redistribute it and/or modify
14 * it under the terms of the GNU General Public License version 2 as
15 * published by the Free Software Foundation.
Linus Torvalds1da177e2005-04-16 15:20:36 -070016 */
17
Viresh Kumardb701152012-10-23 01:29:03 +020018#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
19
Viresh Kumar5ff0a262013-08-06 22:53:03 +053020#include <linux/cpu.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070021#include <linux/cpufreq.h>
22#include <linux/delay.h>
Linus Torvalds1da177e2005-04-16 15:20:36 -070023#include <linux/device.h>
Viresh Kumar5ff0a262013-08-06 22:53:03 +053024#include <linux/init.h>
25#include <linux/kernel_stat.h>
26#include <linux/module.h>
akpm@osdl.org3fc54d32006-01-13 15:54:22 -080027#include <linux/mutex.h>
Viresh Kumar5ff0a262013-08-06 22:53:03 +053028#include <linux/slab.h>
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +010029#include <linux/syscore_ops.h>
Viresh Kumar5ff0a262013-08-06 22:53:03 +053030#include <linux/tick.h>
Thomas Renninger6f4f2722010-04-20 13:17:36 +020031#include <trace/events/power.h>
32
Linus Torvalds1da177e2005-04-16 15:20:36 -070033/**
Dave Jonescd878472006-08-11 17:59:28 -040034 * The "cpufreq driver" - the arch- or hardware-dependent low
Linus Torvalds1da177e2005-04-16 15:20:36 -070035 * level driver of CPUFreq support, and its spinlock. This lock
36 * also protects the cpufreq_cpu_data array.
37 */
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +020038static struct cpufreq_driver *cpufreq_driver;
Mike Travis7a6aedf2008-03-25 15:06:53 -070039static DEFINE_PER_CPU(struct cpufreq_policy *, cpufreq_cpu_data);
Srivatsa S. Bhat84148092013-07-30 04:25:10 +053040static DEFINE_PER_CPU(struct cpufreq_policy *, cpufreq_cpu_data_fallback);
Viresh Kumarbb176f72013-06-19 14:19:33 +053041static DEFINE_RWLOCK(cpufreq_driver_lock);
42static DEFINE_MUTEX(cpufreq_governor_lock);
Lukasz Majewskic88a1f82013-08-06 22:53:08 +053043static LIST_HEAD(cpufreq_policy_list);
Viresh Kumarbb176f72013-06-19 14:19:33 +053044
Thomas Renninger084f3492007-07-09 11:35:28 -070045#ifdef CONFIG_HOTPLUG_CPU
46/* This one keeps track of the previously set governor of a removed CPU */
Dmitry Monakhove77b89f2009-10-05 00:38:55 +040047static DEFINE_PER_CPU(char[CPUFREQ_NAME_LEN], cpufreq_cpu_governor);
Thomas Renninger084f3492007-07-09 11:35:28 -070048#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -070049
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080050/*
51 * cpu_policy_rwsem is a per CPU reader-writer semaphore designed to cure
52 * all cpufreq/hotplug/workqueue/etc related lock issues.
53 *
54 * The rules for this semaphore:
55 * - Any routine that wants to read from the policy structure will
56 * do a down_read on this semaphore.
57 * - Any routine that will write to the policy structure and/or may take away
58 * the policy altogether (eg. CPU hotplug), will hold this lock in write
59 * mode before doing so.
60 *
61 * Additional rules:
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080062 * - Governor routines that can be called in cpufreq hotplug path should not
63 * take this sem as top level hotplug notifier handler takes this.
Mathieu Desnoyers395913d2009-06-08 13:17:31 -040064 * - Lock should not be held across
65 * __cpufreq_governor(data, CPUFREQ_GOV_STOP);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080066 */
Tejun Heof1625062009-10-29 22:34:13 +090067static DEFINE_PER_CPU(int, cpufreq_policy_cpu);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080068static DEFINE_PER_CPU(struct rw_semaphore, cpu_policy_rwsem);
69
70#define lock_policy_rwsem(mode, cpu) \
Viresh Kumarfa1d8af2013-02-07 15:38:42 +053071static int lock_policy_rwsem_##mode(int cpu) \
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080072{ \
Tejun Heof1625062009-10-29 22:34:13 +090073 int policy_cpu = per_cpu(cpufreq_policy_cpu, cpu); \
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080074 BUG_ON(policy_cpu == -1); \
75 down_##mode(&per_cpu(cpu_policy_rwsem, policy_cpu)); \
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080076 \
77 return 0; \
78}
79
80lock_policy_rwsem(read, cpu);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080081lock_policy_rwsem(write, cpu);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080082
Viresh Kumarfa1d8af2013-02-07 15:38:42 +053083#define unlock_policy_rwsem(mode, cpu) \
84static void unlock_policy_rwsem_##mode(int cpu) \
85{ \
86 int policy_cpu = per_cpu(cpufreq_policy_cpu, cpu); \
87 BUG_ON(policy_cpu == -1); \
88 up_##mode(&per_cpu(cpu_policy_rwsem, policy_cpu)); \
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080089}
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080090
Viresh Kumarfa1d8af2013-02-07 15:38:42 +053091unlock_policy_rwsem(read, cpu);
92unlock_policy_rwsem(write, cpu);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -080093
Viresh Kumar6eed9402013-08-06 22:53:11 +053094/*
95 * rwsem to guarantee that cpufreq driver module doesn't unload during critical
96 * sections
97 */
98static DECLARE_RWSEM(cpufreq_rwsem);
99
Linus Torvalds1da177e2005-04-16 15:20:36 -0700100/* internal prototypes */
Dave Jones29464f22009-01-18 01:37:11 -0500101static int __cpufreq_governor(struct cpufreq_policy *policy,
102 unsigned int event);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800103static unsigned int __cpufreq_get(unsigned int cpu);
David Howells65f27f32006-11-22 14:55:48 +0000104static void handle_update(struct work_struct *work);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700105
106/**
Dave Jones32ee8c32006-02-28 00:43:23 -0500107 * Two notifier lists: the "policy" list is involved in the
108 * validation process for a new CPU frequency policy; the
Linus Torvalds1da177e2005-04-16 15:20:36 -0700109 * "transition" list for kernel code that needs to handle
110 * changes to devices when the CPU clock speed changes.
111 * The mutex locks both lists.
112 */
Alan Sterne041c682006-03-27 01:16:30 -0800113static BLOCKING_NOTIFIER_HEAD(cpufreq_policy_notifier_list);
Alan Sternb4dfdbb2006-10-04 02:17:06 -0700114static struct srcu_notifier_head cpufreq_transition_notifier_list;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700115
Cesar Eduardo Barros74212ca2008-02-16 08:41:24 -0200116static bool init_cpufreq_transition_notifier_list_called;
Alan Sternb4dfdbb2006-10-04 02:17:06 -0700117static int __init init_cpufreq_transition_notifier_list(void)
118{
119 srcu_init_notifier_head(&cpufreq_transition_notifier_list);
Cesar Eduardo Barros74212ca2008-02-16 08:41:24 -0200120 init_cpufreq_transition_notifier_list_called = true;
Alan Sternb4dfdbb2006-10-04 02:17:06 -0700121 return 0;
122}
Linus Torvaldsb3438f82006-11-20 11:47:18 -0800123pure_initcall(init_cpufreq_transition_notifier_list);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700124
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -0400125static int off __read_mostly;
Viresh Kumarda584452012-10-26 00:51:32 +0200126static int cpufreq_disabled(void)
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -0400127{
128 return off;
129}
130void disable_cpufreq(void)
131{
132 off = 1;
133}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700134static LIST_HEAD(cpufreq_governor_list);
Dave Jones29464f22009-01-18 01:37:11 -0500135static DEFINE_MUTEX(cpufreq_governor_mutex);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700136
Viresh Kumar4d5dcc42013-03-27 15:58:58 +0000137bool have_governor_per_policy(void)
138{
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200139 return cpufreq_driver->have_governor_per_policy;
Viresh Kumar4d5dcc42013-03-27 15:58:58 +0000140}
Viresh Kumar3f869d62013-05-16 05:09:56 +0000141EXPORT_SYMBOL_GPL(have_governor_per_policy);
Viresh Kumar4d5dcc42013-03-27 15:58:58 +0000142
Viresh Kumar944e9a02013-05-16 05:09:57 +0000143struct kobject *get_governor_parent_kobj(struct cpufreq_policy *policy)
144{
145 if (have_governor_per_policy())
146 return &policy->kobj;
147 else
148 return cpufreq_global_kobject;
149}
150EXPORT_SYMBOL_GPL(get_governor_parent_kobj);
151
Viresh Kumar72a4ce32013-05-17 11:26:32 +0000152static inline u64 get_cpu_idle_time_jiffy(unsigned int cpu, u64 *wall)
153{
154 u64 idle_time;
155 u64 cur_wall_time;
156 u64 busy_time;
157
158 cur_wall_time = jiffies64_to_cputime64(get_jiffies_64());
159
160 busy_time = kcpustat_cpu(cpu).cpustat[CPUTIME_USER];
161 busy_time += kcpustat_cpu(cpu).cpustat[CPUTIME_SYSTEM];
162 busy_time += kcpustat_cpu(cpu).cpustat[CPUTIME_IRQ];
163 busy_time += kcpustat_cpu(cpu).cpustat[CPUTIME_SOFTIRQ];
164 busy_time += kcpustat_cpu(cpu).cpustat[CPUTIME_STEAL];
165 busy_time += kcpustat_cpu(cpu).cpustat[CPUTIME_NICE];
166
167 idle_time = cur_wall_time - busy_time;
168 if (wall)
169 *wall = cputime_to_usecs(cur_wall_time);
170
171 return cputime_to_usecs(idle_time);
172}
173
174u64 get_cpu_idle_time(unsigned int cpu, u64 *wall, int io_busy)
175{
176 u64 idle_time = get_cpu_idle_time_us(cpu, io_busy ? wall : NULL);
177
178 if (idle_time == -1ULL)
179 return get_cpu_idle_time_jiffy(cpu, wall);
180 else if (!io_busy)
181 idle_time += get_cpu_iowait_time_us(cpu, wall);
182
183 return idle_time;
184}
185EXPORT_SYMBOL_GPL(get_cpu_idle_time);
186
Viresh Kumar6eed9402013-08-06 22:53:11 +0530187struct cpufreq_policy *cpufreq_cpu_get(unsigned int cpu)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700188{
Viresh Kumar6eed9402013-08-06 22:53:11 +0530189 struct cpufreq_policy *policy = NULL;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700190 unsigned long flags;
191
Viresh Kumar6eed9402013-08-06 22:53:11 +0530192 if (cpufreq_disabled() || (cpu >= nr_cpu_ids))
193 return NULL;
194
195 if (!down_read_trylock(&cpufreq_rwsem))
196 return NULL;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700197
198 /* get the cpufreq driver */
Nathan Zimmer0d1857a2013-02-22 16:24:34 +0000199 read_lock_irqsave(&cpufreq_driver_lock, flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700200
Viresh Kumar6eed9402013-08-06 22:53:11 +0530201 if (cpufreq_driver) {
202 /* get the CPU */
203 policy = per_cpu(cpufreq_cpu_data, cpu);
204 if (policy)
205 kobject_get(&policy->kobj);
206 }
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200207
Viresh Kumar6eed9402013-08-06 22:53:11 +0530208 read_unlock_irqrestore(&cpufreq_driver_lock, flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700209
Viresh Kumar3a3e9e02013-08-06 22:53:05 +0530210 if (!policy)
Viresh Kumar6eed9402013-08-06 22:53:11 +0530211 up_read(&cpufreq_rwsem);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700212
Viresh Kumar3a3e9e02013-08-06 22:53:05 +0530213 return policy;
Stephen Boyda9144432012-07-20 18:14:38 +0000214}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700215EXPORT_SYMBOL_GPL(cpufreq_cpu_get);
216
Viresh Kumar3a3e9e02013-08-06 22:53:05 +0530217void cpufreq_cpu_put(struct cpufreq_policy *policy)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700218{
Dirk Brandewied5aaffa2013-01-17 16:22:21 +0000219 if (cpufreq_disabled())
220 return;
221
Viresh Kumar6eed9402013-08-06 22:53:11 +0530222 kobject_put(&policy->kobj);
223 up_read(&cpufreq_rwsem);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700224}
225EXPORT_SYMBOL_GPL(cpufreq_cpu_put);
226
Linus Torvalds1da177e2005-04-16 15:20:36 -0700227/*********************************************************************
Linus Torvalds1da177e2005-04-16 15:20:36 -0700228 * EXTERNALLY AFFECTING FREQUENCY CHANGES *
229 *********************************************************************/
230
231/**
232 * adjust_jiffies - adjust the system "loops_per_jiffy"
233 *
234 * This function alters the system "loops_per_jiffy" for the clock
235 * speed change. Note that loops_per_jiffy cannot be updated on SMP
Dave Jones32ee8c32006-02-28 00:43:23 -0500236 * systems as each CPU might be scaled differently. So, use the arch
Linus Torvalds1da177e2005-04-16 15:20:36 -0700237 * per-CPU loops_per_jiffy value wherever possible.
238 */
239#ifndef CONFIG_SMP
240static unsigned long l_p_j_ref;
Viresh Kumarbb176f72013-06-19 14:19:33 +0530241static unsigned int l_p_j_ref_freq;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700242
Arjan van de Ven858119e2006-01-14 13:20:43 -0800243static void adjust_jiffies(unsigned long val, struct cpufreq_freqs *ci)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700244{
245 if (ci->flags & CPUFREQ_CONST_LOOPS)
246 return;
247
248 if (!l_p_j_ref_freq) {
249 l_p_j_ref = loops_per_jiffy;
250 l_p_j_ref_freq = ci->old;
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200251 pr_debug("saving %lu as reference value for loops_per_jiffy; "
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530252 "freq is %u kHz\n", l_p_j_ref, l_p_j_ref_freq);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700253 }
Viresh Kumarbb176f72013-06-19 14:19:33 +0530254 if ((val == CPUFREQ_POSTCHANGE && ci->old != ci->new) ||
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -0700255 (val == CPUFREQ_RESUMECHANGE || val == CPUFREQ_SUSPENDCHANGE)) {
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530256 loops_per_jiffy = cpufreq_scale(l_p_j_ref, l_p_j_ref_freq,
257 ci->new);
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200258 pr_debug("scaling loops_per_jiffy to %lu "
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530259 "for frequency %u kHz\n", loops_per_jiffy, ci->new);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700260 }
261}
262#else
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530263static inline void adjust_jiffies(unsigned long val, struct cpufreq_freqs *ci)
264{
265 return;
266}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700267#endif
268
Viresh Kumar0956df9c2013-06-19 14:19:34 +0530269static void __cpufreq_notify_transition(struct cpufreq_policy *policy,
Viresh Kumarb43a7ff2013-03-24 11:56:43 +0530270 struct cpufreq_freqs *freqs, unsigned int state)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700271{
272 BUG_ON(irqs_disabled());
273
Dirk Brandewied5aaffa2013-01-17 16:22:21 +0000274 if (cpufreq_disabled())
275 return;
276
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200277 freqs->flags = cpufreq_driver->flags;
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200278 pr_debug("notification %u of frequency transition to %u kHz\n",
Dave Jonese4472cb2006-01-31 15:53:55 -0800279 state, freqs->new);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700280
Linus Torvalds1da177e2005-04-16 15:20:36 -0700281 switch (state) {
Dave Jonese4472cb2006-01-31 15:53:55 -0800282
Linus Torvalds1da177e2005-04-16 15:20:36 -0700283 case CPUFREQ_PRECHANGE:
Viresh Kumar266c13d2013-07-02 16:36:28 +0530284 if (WARN(policy->transition_ongoing ==
285 cpumask_weight(policy->cpus),
Viresh Kumar7c30ed52013-06-19 10:16:55 +0530286 "In middle of another frequency transition\n"))
287 return;
288
Viresh Kumar266c13d2013-07-02 16:36:28 +0530289 policy->transition_ongoing++;
Viresh Kumar7c30ed52013-06-19 10:16:55 +0530290
Dave Jones32ee8c32006-02-28 00:43:23 -0500291 /* detect if the driver reported a value as "old frequency"
Dave Jonese4472cb2006-01-31 15:53:55 -0800292 * which is not equal to what the cpufreq core thinks is
293 * "old frequency".
Linus Torvalds1da177e2005-04-16 15:20:36 -0700294 */
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200295 if (!(cpufreq_driver->flags & CPUFREQ_CONST_LOOPS)) {
Dave Jonese4472cb2006-01-31 15:53:55 -0800296 if ((policy) && (policy->cpu == freqs->cpu) &&
297 (policy->cur) && (policy->cur != freqs->old)) {
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200298 pr_debug("Warning: CPU frequency is"
Dave Jonese4472cb2006-01-31 15:53:55 -0800299 " %u, cpufreq assumed %u kHz.\n",
300 freqs->old, policy->cur);
301 freqs->old = policy->cur;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700302 }
303 }
Alan Sternb4dfdbb2006-10-04 02:17:06 -0700304 srcu_notifier_call_chain(&cpufreq_transition_notifier_list,
Alan Sterne041c682006-03-27 01:16:30 -0800305 CPUFREQ_PRECHANGE, freqs);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700306 adjust_jiffies(CPUFREQ_PRECHANGE, freqs);
307 break;
Dave Jonese4472cb2006-01-31 15:53:55 -0800308
Linus Torvalds1da177e2005-04-16 15:20:36 -0700309 case CPUFREQ_POSTCHANGE:
Viresh Kumar7c30ed52013-06-19 10:16:55 +0530310 if (WARN(!policy->transition_ongoing,
311 "No frequency transition in progress\n"))
312 return;
313
Viresh Kumar266c13d2013-07-02 16:36:28 +0530314 policy->transition_ongoing--;
Viresh Kumar7c30ed52013-06-19 10:16:55 +0530315
Linus Torvalds1da177e2005-04-16 15:20:36 -0700316 adjust_jiffies(CPUFREQ_POSTCHANGE, freqs);
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200317 pr_debug("FREQ: %lu - CPU: %lu", (unsigned long)freqs->new,
Thomas Renninger6f4f2722010-04-20 13:17:36 +0200318 (unsigned long)freqs->cpu);
Thomas Renninger25e41932011-01-03 17:50:44 +0100319 trace_cpu_frequency(freqs->new, freqs->cpu);
Alan Sternb4dfdbb2006-10-04 02:17:06 -0700320 srcu_notifier_call_chain(&cpufreq_transition_notifier_list,
Alan Sterne041c682006-03-27 01:16:30 -0800321 CPUFREQ_POSTCHANGE, freqs);
Dave Jonese4472cb2006-01-31 15:53:55 -0800322 if (likely(policy) && likely(policy->cpu == freqs->cpu))
323 policy->cur = freqs->new;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700324 break;
325 }
Linus Torvalds1da177e2005-04-16 15:20:36 -0700326}
Viresh Kumarbb176f72013-06-19 14:19:33 +0530327
Viresh Kumarb43a7ff2013-03-24 11:56:43 +0530328/**
329 * cpufreq_notify_transition - call notifier chain and adjust_jiffies
330 * on frequency transition.
331 *
332 * This function calls the transition notifiers and the "adjust_jiffies"
333 * function. It is called twice on all CPU frequency changes that have
334 * external effects.
335 */
336void cpufreq_notify_transition(struct cpufreq_policy *policy,
337 struct cpufreq_freqs *freqs, unsigned int state)
338{
339 for_each_cpu(freqs->cpu, policy->cpus)
340 __cpufreq_notify_transition(policy, freqs, state);
341}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700342EXPORT_SYMBOL_GPL(cpufreq_notify_transition);
343
344
Linus Torvalds1da177e2005-04-16 15:20:36 -0700345/*********************************************************************
346 * SYSFS INTERFACE *
347 *********************************************************************/
348
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700349static struct cpufreq_governor *__find_governor(const char *str_governor)
350{
351 struct cpufreq_governor *t;
352
353 list_for_each_entry(t, &cpufreq_governor_list, governor_list)
Dave Jones29464f22009-01-18 01:37:11 -0500354 if (!strnicmp(str_governor, t->name, CPUFREQ_NAME_LEN))
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700355 return t;
356
357 return NULL;
358}
359
Linus Torvalds1da177e2005-04-16 15:20:36 -0700360/**
361 * cpufreq_parse_governor - parse a governor string
362 */
Dave Jones905d77c2008-03-05 14:28:32 -0500363static int cpufreq_parse_governor(char *str_governor, unsigned int *policy,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700364 struct cpufreq_governor **governor)
365{
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700366 int err = -EINVAL;
367
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200368 if (!cpufreq_driver)
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700369 goto out;
370
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200371 if (cpufreq_driver->setpolicy) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700372 if (!strnicmp(str_governor, "performance", CPUFREQ_NAME_LEN)) {
373 *policy = CPUFREQ_POLICY_PERFORMANCE;
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700374 err = 0;
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530375 } else if (!strnicmp(str_governor, "powersave",
376 CPUFREQ_NAME_LEN)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700377 *policy = CPUFREQ_POLICY_POWERSAVE;
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700378 err = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700379 }
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200380 } else if (cpufreq_driver->target) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700381 struct cpufreq_governor *t;
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700382
akpm@osdl.org3fc54d32006-01-13 15:54:22 -0800383 mutex_lock(&cpufreq_governor_mutex);
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700384
385 t = __find_governor(str_governor);
386
Jeremy Fitzhardingeea714972006-07-06 12:32:01 -0700387 if (t == NULL) {
Kees Cook1a8e1462011-05-04 08:38:56 -0700388 int ret;
Jeremy Fitzhardingeea714972006-07-06 12:32:01 -0700389
Kees Cook1a8e1462011-05-04 08:38:56 -0700390 mutex_unlock(&cpufreq_governor_mutex);
391 ret = request_module("cpufreq_%s", str_governor);
392 mutex_lock(&cpufreq_governor_mutex);
Jeremy Fitzhardingeea714972006-07-06 12:32:01 -0700393
Kees Cook1a8e1462011-05-04 08:38:56 -0700394 if (ret == 0)
395 t = __find_governor(str_governor);
Jeremy Fitzhardingeea714972006-07-06 12:32:01 -0700396 }
397
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700398 if (t != NULL) {
399 *governor = t;
400 err = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700401 }
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700402
akpm@osdl.org3fc54d32006-01-13 15:54:22 -0800403 mutex_unlock(&cpufreq_governor_mutex);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700404 }
Dave Jones29464f22009-01-18 01:37:11 -0500405out:
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -0700406 return err;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700407}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700408
Linus Torvalds1da177e2005-04-16 15:20:36 -0700409/**
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530410 * cpufreq_per_cpu_attr_read() / show_##file_name() -
411 * print out cpufreq information
Linus Torvalds1da177e2005-04-16 15:20:36 -0700412 *
413 * Write out information from cpufreq_driver->policy[cpu]; object must be
414 * "unsigned int".
415 */
416
Dave Jones32ee8c32006-02-28 00:43:23 -0500417#define show_one(file_name, object) \
418static ssize_t show_##file_name \
Dave Jones905d77c2008-03-05 14:28:32 -0500419(struct cpufreq_policy *policy, char *buf) \
Dave Jones32ee8c32006-02-28 00:43:23 -0500420{ \
Dave Jones29464f22009-01-18 01:37:11 -0500421 return sprintf(buf, "%u\n", policy->object); \
Linus Torvalds1da177e2005-04-16 15:20:36 -0700422}
423
424show_one(cpuinfo_min_freq, cpuinfo.min_freq);
425show_one(cpuinfo_max_freq, cpuinfo.max_freq);
Thomas Renningered129782009-02-04 01:17:41 +0100426show_one(cpuinfo_transition_latency, cpuinfo.transition_latency);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700427show_one(scaling_min_freq, min);
428show_one(scaling_max_freq, max);
429show_one(scaling_cur_freq, cur);
430
Viresh Kumar3a3e9e02013-08-06 22:53:05 +0530431static int __cpufreq_set_policy(struct cpufreq_policy *policy,
432 struct cpufreq_policy *new_policy);
Thomas Renninger7970e082006-04-13 15:14:04 +0200433
Linus Torvalds1da177e2005-04-16 15:20:36 -0700434/**
435 * cpufreq_per_cpu_attr_write() / store_##file_name() - sysfs write access
436 */
437#define store_one(file_name, object) \
438static ssize_t store_##file_name \
Dave Jones905d77c2008-03-05 14:28:32 -0500439(struct cpufreq_policy *policy, const char *buf, size_t count) \
Linus Torvalds1da177e2005-04-16 15:20:36 -0700440{ \
Jingoo Hanf55c9c22012-10-31 05:49:13 +0000441 unsigned int ret; \
Linus Torvalds1da177e2005-04-16 15:20:36 -0700442 struct cpufreq_policy new_policy; \
443 \
444 ret = cpufreq_get_policy(&new_policy, policy->cpu); \
445 if (ret) \
446 return -EINVAL; \
447 \
Dave Jones29464f22009-01-18 01:37:11 -0500448 ret = sscanf(buf, "%u", &new_policy.object); \
Linus Torvalds1da177e2005-04-16 15:20:36 -0700449 if (ret != 1) \
450 return -EINVAL; \
451 \
Thomas Renninger7970e082006-04-13 15:14:04 +0200452 ret = __cpufreq_set_policy(policy, &new_policy); \
453 policy->user_policy.object = policy->object; \
Linus Torvalds1da177e2005-04-16 15:20:36 -0700454 \
455 return ret ? ret : count; \
456}
457
Dave Jones29464f22009-01-18 01:37:11 -0500458store_one(scaling_min_freq, min);
459store_one(scaling_max_freq, max);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700460
461/**
462 * show_cpuinfo_cur_freq - current CPU frequency as detected by hardware
463 */
Dave Jones905d77c2008-03-05 14:28:32 -0500464static ssize_t show_cpuinfo_cur_freq(struct cpufreq_policy *policy,
465 char *buf)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700466{
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800467 unsigned int cur_freq = __cpufreq_get(policy->cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700468 if (!cur_freq)
469 return sprintf(buf, "<unknown>");
470 return sprintf(buf, "%u\n", cur_freq);
471}
472
Linus Torvalds1da177e2005-04-16 15:20:36 -0700473/**
474 * show_scaling_governor - show the current policy for the specified CPU
475 */
Dave Jones905d77c2008-03-05 14:28:32 -0500476static ssize_t show_scaling_governor(struct cpufreq_policy *policy, char *buf)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700477{
Dave Jones29464f22009-01-18 01:37:11 -0500478 if (policy->policy == CPUFREQ_POLICY_POWERSAVE)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700479 return sprintf(buf, "powersave\n");
480 else if (policy->policy == CPUFREQ_POLICY_PERFORMANCE)
481 return sprintf(buf, "performance\n");
482 else if (policy->governor)
viresh kumar4b972f02012-10-23 01:23:43 +0200483 return scnprintf(buf, CPUFREQ_NAME_PLEN, "%s\n",
Dave Jones29464f22009-01-18 01:37:11 -0500484 policy->governor->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700485 return -EINVAL;
486}
487
Linus Torvalds1da177e2005-04-16 15:20:36 -0700488/**
489 * store_scaling_governor - store policy for the specified CPU
490 */
Dave Jones905d77c2008-03-05 14:28:32 -0500491static ssize_t store_scaling_governor(struct cpufreq_policy *policy,
492 const char *buf, size_t count)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700493{
Jingoo Hanf55c9c22012-10-31 05:49:13 +0000494 unsigned int ret;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700495 char str_governor[16];
496 struct cpufreq_policy new_policy;
497
498 ret = cpufreq_get_policy(&new_policy, policy->cpu);
499 if (ret)
500 return ret;
501
Dave Jones29464f22009-01-18 01:37:11 -0500502 ret = sscanf(buf, "%15s", str_governor);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700503 if (ret != 1)
504 return -EINVAL;
505
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530506 if (cpufreq_parse_governor(str_governor, &new_policy.policy,
507 &new_policy.governor))
Linus Torvalds1da177e2005-04-16 15:20:36 -0700508 return -EINVAL;
509
Viresh Kumarbb176f72013-06-19 14:19:33 +0530510 /*
511 * Do not use cpufreq_set_policy here or the user_policy.max
512 * will be wrongly overridden
513 */
Thomas Renninger7970e082006-04-13 15:14:04 +0200514 ret = __cpufreq_set_policy(policy, &new_policy);
515
516 policy->user_policy.policy = policy->policy;
517 policy->user_policy.governor = policy->governor;
Thomas Renninger7970e082006-04-13 15:14:04 +0200518
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530519 if (ret)
520 return ret;
521 else
522 return count;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700523}
524
525/**
526 * show_scaling_driver - show the cpufreq driver currently loaded
527 */
Dave Jones905d77c2008-03-05 14:28:32 -0500528static ssize_t show_scaling_driver(struct cpufreq_policy *policy, char *buf)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700529{
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200530 return scnprintf(buf, CPUFREQ_NAME_PLEN, "%s\n", cpufreq_driver->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700531}
532
533/**
534 * show_scaling_available_governors - show the available CPUfreq governors
535 */
Dave Jones905d77c2008-03-05 14:28:32 -0500536static ssize_t show_scaling_available_governors(struct cpufreq_policy *policy,
537 char *buf)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700538{
539 ssize_t i = 0;
540 struct cpufreq_governor *t;
541
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200542 if (!cpufreq_driver->target) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700543 i += sprintf(buf, "performance powersave");
544 goto out;
545 }
546
547 list_for_each_entry(t, &cpufreq_governor_list, governor_list) {
Dave Jones29464f22009-01-18 01:37:11 -0500548 if (i >= (ssize_t) ((PAGE_SIZE / sizeof(char))
549 - (CPUFREQ_NAME_LEN + 2)))
Linus Torvalds1da177e2005-04-16 15:20:36 -0700550 goto out;
viresh kumar4b972f02012-10-23 01:23:43 +0200551 i += scnprintf(&buf[i], CPUFREQ_NAME_PLEN, "%s ", t->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700552 }
Dave Jones7d5e3502006-02-02 17:03:42 -0500553out:
Linus Torvalds1da177e2005-04-16 15:20:36 -0700554 i += sprintf(&buf[i], "\n");
555 return i;
556}
Darrick J. Wonge8628dd2008-04-18 13:31:12 -0700557
Lan Tianyuf4fd3792013-06-27 15:08:54 +0800558ssize_t cpufreq_show_cpus(const struct cpumask *mask, char *buf)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700559{
560 ssize_t i = 0;
561 unsigned int cpu;
562
Rusty Russell835481d2009-01-04 05:18:06 -0800563 for_each_cpu(cpu, mask) {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700564 if (i)
565 i += scnprintf(&buf[i], (PAGE_SIZE - i - 2), " ");
566 i += scnprintf(&buf[i], (PAGE_SIZE - i - 2), "%u", cpu);
567 if (i >= (PAGE_SIZE - 5))
Dave Jones29464f22009-01-18 01:37:11 -0500568 break;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700569 }
570 i += sprintf(&buf[i], "\n");
571 return i;
572}
Lan Tianyuf4fd3792013-06-27 15:08:54 +0800573EXPORT_SYMBOL_GPL(cpufreq_show_cpus);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700574
Darrick J. Wonge8628dd2008-04-18 13:31:12 -0700575/**
576 * show_related_cpus - show the CPUs affected by each transition even if
577 * hw coordination is in use
578 */
579static ssize_t show_related_cpus(struct cpufreq_policy *policy, char *buf)
580{
Lan Tianyuf4fd3792013-06-27 15:08:54 +0800581 return cpufreq_show_cpus(policy->related_cpus, buf);
Darrick J. Wonge8628dd2008-04-18 13:31:12 -0700582}
583
584/**
585 * show_affected_cpus - show the CPUs affected by each transition
586 */
587static ssize_t show_affected_cpus(struct cpufreq_policy *policy, char *buf)
588{
Lan Tianyuf4fd3792013-06-27 15:08:54 +0800589 return cpufreq_show_cpus(policy->cpus, buf);
Darrick J. Wonge8628dd2008-04-18 13:31:12 -0700590}
591
Venki Pallipadi9e769882007-10-26 10:18:21 -0700592static ssize_t store_scaling_setspeed(struct cpufreq_policy *policy,
Dave Jones905d77c2008-03-05 14:28:32 -0500593 const char *buf, size_t count)
Venki Pallipadi9e769882007-10-26 10:18:21 -0700594{
595 unsigned int freq = 0;
596 unsigned int ret;
597
CHIKAMA masaki879000f2008-06-05 22:46:33 -0700598 if (!policy->governor || !policy->governor->store_setspeed)
Venki Pallipadi9e769882007-10-26 10:18:21 -0700599 return -EINVAL;
600
601 ret = sscanf(buf, "%u", &freq);
602 if (ret != 1)
603 return -EINVAL;
604
605 policy->governor->store_setspeed(policy, freq);
606
607 return count;
608}
609
610static ssize_t show_scaling_setspeed(struct cpufreq_policy *policy, char *buf)
611{
CHIKAMA masaki879000f2008-06-05 22:46:33 -0700612 if (!policy->governor || !policy->governor->show_setspeed)
Venki Pallipadi9e769882007-10-26 10:18:21 -0700613 return sprintf(buf, "<unsupported>\n");
614
615 return policy->governor->show_setspeed(policy, buf);
616}
Linus Torvalds1da177e2005-04-16 15:20:36 -0700617
Thomas Renningere2f74f32009-11-19 12:31:01 +0100618/**
viresh kumar8bf1ac722012-10-23 01:23:33 +0200619 * show_bios_limit - show the current cpufreq HW/BIOS limitation
Thomas Renningere2f74f32009-11-19 12:31:01 +0100620 */
621static ssize_t show_bios_limit(struct cpufreq_policy *policy, char *buf)
622{
623 unsigned int limit;
624 int ret;
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200625 if (cpufreq_driver->bios_limit) {
626 ret = cpufreq_driver->bios_limit(policy->cpu, &limit);
Thomas Renningere2f74f32009-11-19 12:31:01 +0100627 if (!ret)
628 return sprintf(buf, "%u\n", limit);
629 }
630 return sprintf(buf, "%u\n", policy->cpuinfo.max_freq);
631}
632
Borislav Petkov6dad2a22010-03-31 21:56:46 +0200633cpufreq_freq_attr_ro_perm(cpuinfo_cur_freq, 0400);
634cpufreq_freq_attr_ro(cpuinfo_min_freq);
635cpufreq_freq_attr_ro(cpuinfo_max_freq);
636cpufreq_freq_attr_ro(cpuinfo_transition_latency);
637cpufreq_freq_attr_ro(scaling_available_governors);
638cpufreq_freq_attr_ro(scaling_driver);
639cpufreq_freq_attr_ro(scaling_cur_freq);
640cpufreq_freq_attr_ro(bios_limit);
641cpufreq_freq_attr_ro(related_cpus);
642cpufreq_freq_attr_ro(affected_cpus);
643cpufreq_freq_attr_rw(scaling_min_freq);
644cpufreq_freq_attr_rw(scaling_max_freq);
645cpufreq_freq_attr_rw(scaling_governor);
646cpufreq_freq_attr_rw(scaling_setspeed);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700647
Dave Jones905d77c2008-03-05 14:28:32 -0500648static struct attribute *default_attrs[] = {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700649 &cpuinfo_min_freq.attr,
650 &cpuinfo_max_freq.attr,
Thomas Renningered129782009-02-04 01:17:41 +0100651 &cpuinfo_transition_latency.attr,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700652 &scaling_min_freq.attr,
653 &scaling_max_freq.attr,
654 &affected_cpus.attr,
Darrick J. Wonge8628dd2008-04-18 13:31:12 -0700655 &related_cpus.attr,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700656 &scaling_governor.attr,
657 &scaling_driver.attr,
658 &scaling_available_governors.attr,
Venki Pallipadi9e769882007-10-26 10:18:21 -0700659 &scaling_setspeed.attr,
Linus Torvalds1da177e2005-04-16 15:20:36 -0700660 NULL
661};
662
Dave Jones29464f22009-01-18 01:37:11 -0500663#define to_policy(k) container_of(k, struct cpufreq_policy, kobj)
664#define to_attr(a) container_of(a, struct freq_attr, attr)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700665
Dave Jones29464f22009-01-18 01:37:11 -0500666static ssize_t show(struct kobject *kobj, struct attribute *attr, char *buf)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700667{
Dave Jones905d77c2008-03-05 14:28:32 -0500668 struct cpufreq_policy *policy = to_policy(kobj);
669 struct freq_attr *fattr = to_attr(attr);
Dave Jones0db4a8a2008-03-05 14:20:57 -0500670 ssize_t ret = -EINVAL;
Viresh Kumar6eed9402013-08-06 22:53:11 +0530671
672 if (!down_read_trylock(&cpufreq_rwsem))
673 goto exit;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800674
675 if (lock_policy_rwsem_read(policy->cpu) < 0)
Viresh Kumar6eed9402013-08-06 22:53:11 +0530676 goto up_read;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800677
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530678 if (fattr->show)
679 ret = fattr->show(policy, buf);
680 else
681 ret = -EIO;
682
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800683 unlock_policy_rwsem_read(policy->cpu);
Viresh Kumar6eed9402013-08-06 22:53:11 +0530684
685up_read:
686 up_read(&cpufreq_rwsem);
687exit:
Linus Torvalds1da177e2005-04-16 15:20:36 -0700688 return ret;
689}
690
Dave Jones905d77c2008-03-05 14:28:32 -0500691static ssize_t store(struct kobject *kobj, struct attribute *attr,
692 const char *buf, size_t count)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700693{
Dave Jones905d77c2008-03-05 14:28:32 -0500694 struct cpufreq_policy *policy = to_policy(kobj);
695 struct freq_attr *fattr = to_attr(attr);
Dave Jonesa07530b2008-03-05 14:22:25 -0500696 ssize_t ret = -EINVAL;
Viresh Kumar6eed9402013-08-06 22:53:11 +0530697
698 if (!down_read_trylock(&cpufreq_rwsem))
699 goto exit;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800700
701 if (lock_policy_rwsem_write(policy->cpu) < 0)
Viresh Kumar6eed9402013-08-06 22:53:11 +0530702 goto up_read;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800703
Gautham R Shenoye08f5f52006-10-26 16:20:58 +0530704 if (fattr->store)
705 ret = fattr->store(policy, buf, count);
706 else
707 ret = -EIO;
708
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -0800709 unlock_policy_rwsem_write(policy->cpu);
Viresh Kumar6eed9402013-08-06 22:53:11 +0530710
711up_read:
712 up_read(&cpufreq_rwsem);
713exit:
Linus Torvalds1da177e2005-04-16 15:20:36 -0700714 return ret;
715}
716
Dave Jones905d77c2008-03-05 14:28:32 -0500717static void cpufreq_sysfs_release(struct kobject *kobj)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700718{
Dave Jones905d77c2008-03-05 14:28:32 -0500719 struct cpufreq_policy *policy = to_policy(kobj);
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200720 pr_debug("last reference is dropped\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -0700721 complete(&policy->kobj_unregister);
722}
723
Emese Revfy52cf25d2010-01-19 02:58:23 +0100724static const struct sysfs_ops sysfs_ops = {
Linus Torvalds1da177e2005-04-16 15:20:36 -0700725 .show = show,
726 .store = store,
727};
728
729static struct kobj_type ktype_cpufreq = {
730 .sysfs_ops = &sysfs_ops,
731 .default_attrs = default_attrs,
732 .release = cpufreq_sysfs_release,
733};
734
Viresh Kumar2361be22013-05-17 16:09:09 +0530735struct kobject *cpufreq_global_kobject;
736EXPORT_SYMBOL(cpufreq_global_kobject);
737
738static int cpufreq_global_kobject_usage;
739
740int cpufreq_get_global_kobject(void)
741{
742 if (!cpufreq_global_kobject_usage++)
743 return kobject_add(cpufreq_global_kobject,
744 &cpu_subsys.dev_root->kobj, "%s", "cpufreq");
745
746 return 0;
747}
748EXPORT_SYMBOL(cpufreq_get_global_kobject);
749
750void cpufreq_put_global_kobject(void)
751{
752 if (!--cpufreq_global_kobject_usage)
753 kobject_del(cpufreq_global_kobject);
754}
755EXPORT_SYMBOL(cpufreq_put_global_kobject);
756
757int cpufreq_sysfs_create_file(const struct attribute *attr)
758{
759 int ret = cpufreq_get_global_kobject();
760
761 if (!ret) {
762 ret = sysfs_create_file(cpufreq_global_kobject, attr);
763 if (ret)
764 cpufreq_put_global_kobject();
765 }
766
767 return ret;
768}
769EXPORT_SYMBOL(cpufreq_sysfs_create_file);
770
771void cpufreq_sysfs_remove_file(const struct attribute *attr)
772{
773 sysfs_remove_file(cpufreq_global_kobject, attr);
774 cpufreq_put_global_kobject();
775}
776EXPORT_SYMBOL(cpufreq_sysfs_remove_file);
777
Dave Jones19d6f7e2009-07-08 17:35:39 -0400778/* symlink affected CPUs */
Viresh Kumar308b60e2013-07-31 14:35:14 +0200779static int cpufreq_add_dev_symlink(struct cpufreq_policy *policy)
Dave Jones19d6f7e2009-07-08 17:35:39 -0400780{
781 unsigned int j;
782 int ret = 0;
783
784 for_each_cpu(j, policy->cpus) {
Kay Sievers8a25a2f2011-12-21 14:29:42 -0800785 struct device *cpu_dev;
Dave Jones19d6f7e2009-07-08 17:35:39 -0400786
Viresh Kumar308b60e2013-07-31 14:35:14 +0200787 if (j == policy->cpu)
Dave Jones19d6f7e2009-07-08 17:35:39 -0400788 continue;
Dave Jones19d6f7e2009-07-08 17:35:39 -0400789
Viresh Kumare8fdde12013-07-31 14:31:33 +0200790 pr_debug("Adding link for CPU: %u\n", j);
Kay Sievers8a25a2f2011-12-21 14:29:42 -0800791 cpu_dev = get_cpu_device(j);
792 ret = sysfs_create_link(&cpu_dev->kobj, &policy->kobj,
Dave Jones19d6f7e2009-07-08 17:35:39 -0400793 "cpufreq");
Rafael J. Wysocki71c34612013-08-04 01:19:34 +0200794 if (ret)
795 break;
Dave Jones19d6f7e2009-07-08 17:35:39 -0400796 }
797 return ret;
798}
799
Viresh Kumar308b60e2013-07-31 14:35:14 +0200800static int cpufreq_add_dev_interface(struct cpufreq_policy *policy,
Kay Sievers8a25a2f2011-12-21 14:29:42 -0800801 struct device *dev)
Dave Jones909a6942009-07-08 18:05:42 -0400802{
803 struct freq_attr **drv_attr;
Dave Jones909a6942009-07-08 18:05:42 -0400804 int ret = 0;
Dave Jones909a6942009-07-08 18:05:42 -0400805
806 /* prepare interface data */
807 ret = kobject_init_and_add(&policy->kobj, &ktype_cpufreq,
Kay Sievers8a25a2f2011-12-21 14:29:42 -0800808 &dev->kobj, "cpufreq");
Dave Jones909a6942009-07-08 18:05:42 -0400809 if (ret)
810 return ret;
811
812 /* set up files for this cpu device */
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200813 drv_attr = cpufreq_driver->attr;
Dave Jones909a6942009-07-08 18:05:42 -0400814 while ((drv_attr) && (*drv_attr)) {
815 ret = sysfs_create_file(&policy->kobj, &((*drv_attr)->attr));
816 if (ret)
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200817 goto err_out_kobj_put;
Dave Jones909a6942009-07-08 18:05:42 -0400818 drv_attr++;
819 }
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200820 if (cpufreq_driver->get) {
Dave Jones909a6942009-07-08 18:05:42 -0400821 ret = sysfs_create_file(&policy->kobj, &cpuinfo_cur_freq.attr);
822 if (ret)
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200823 goto err_out_kobj_put;
Dave Jones909a6942009-07-08 18:05:42 -0400824 }
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200825 if (cpufreq_driver->target) {
Dave Jones909a6942009-07-08 18:05:42 -0400826 ret = sysfs_create_file(&policy->kobj, &scaling_cur_freq.attr);
827 if (ret)
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200828 goto err_out_kobj_put;
Dave Jones909a6942009-07-08 18:05:42 -0400829 }
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200830 if (cpufreq_driver->bios_limit) {
Thomas Renningere2f74f32009-11-19 12:31:01 +0100831 ret = sysfs_create_file(&policy->kobj, &bios_limit.attr);
832 if (ret)
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200833 goto err_out_kobj_put;
Thomas Renningere2f74f32009-11-19 12:31:01 +0100834 }
Dave Jones909a6942009-07-08 18:05:42 -0400835
Viresh Kumar308b60e2013-07-31 14:35:14 +0200836 ret = cpufreq_add_dev_symlink(policy);
Dave Jonesecf7e462009-07-08 18:48:47 -0400837 if (ret)
838 goto err_out_kobj_put;
839
Srivatsa S. Bhate18f1682013-07-30 04:24:23 +0530840 return ret;
841
842err_out_kobj_put:
843 kobject_put(&policy->kobj);
844 wait_for_completion(&policy->kobj_unregister);
845 return ret;
846}
847
848static void cpufreq_init_policy(struct cpufreq_policy *policy)
849{
850 struct cpufreq_policy new_policy;
851 int ret = 0;
852
Viresh Kumard5b73cd2013-08-06 22:53:06 +0530853 memcpy(&new_policy, policy, sizeof(*policy));
Dave Jonesecf7e462009-07-08 18:48:47 -0400854 /* assure that the starting sequence is run in __cpufreq_set_policy */
855 policy->governor = NULL;
856
857 /* set default policy */
858 ret = __cpufreq_set_policy(policy, &new_policy);
859 policy->user_policy.policy = policy->policy;
860 policy->user_policy.governor = policy->governor;
861
862 if (ret) {
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200863 pr_debug("setting policy failed\n");
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200864 if (cpufreq_driver->exit)
865 cpufreq_driver->exit(policy);
Dave Jonesecf7e462009-07-08 18:48:47 -0400866 }
Dave Jones909a6942009-07-08 18:05:42 -0400867}
868
Viresh Kumarfcf80582013-01-29 14:39:08 +0000869#ifdef CONFIG_HOTPLUG_CPU
Viresh Kumard8d3b472013-08-04 01:20:07 +0200870static int cpufreq_add_policy_cpu(struct cpufreq_policy *policy,
871 unsigned int cpu, struct device *dev,
872 bool frozen)
Viresh Kumarfcf80582013-01-29 14:39:08 +0000873{
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +0200874 int ret = 0, has_target = !!cpufreq_driver->target;
Viresh Kumarfcf80582013-01-29 14:39:08 +0000875 unsigned long flags;
876
Viresh Kumar3de9bde2013-08-06 22:53:13 +0530877 if (has_target) {
878 ret = __cpufreq_governor(policy, CPUFREQ_GOV_STOP);
879 if (ret) {
880 pr_err("%s: Failed to stop governor\n", __func__);
881 return ret;
882 }
883 }
Viresh Kumarfcf80582013-01-29 14:39:08 +0000884
Viresh Kumard8d3b472013-08-04 01:20:07 +0200885 lock_policy_rwsem_write(policy->cpu);
Viresh Kumar2eaa3e22013-02-07 10:55:00 +0530886
Nathan Zimmer0d1857a2013-02-22 16:24:34 +0000887 write_lock_irqsave(&cpufreq_driver_lock, flags);
Viresh Kumar2eaa3e22013-02-07 10:55:00 +0530888
Viresh Kumarfcf80582013-01-29 14:39:08 +0000889 cpumask_set_cpu(cpu, policy->cpus);
Viresh Kumar2eaa3e22013-02-07 10:55:00 +0530890 per_cpu(cpufreq_policy_cpu, cpu) = policy->cpu;
Viresh Kumarfcf80582013-01-29 14:39:08 +0000891 per_cpu(cpufreq_cpu_data, cpu) = policy;
Nathan Zimmer0d1857a2013-02-22 16:24:34 +0000892 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
Viresh Kumarfcf80582013-01-29 14:39:08 +0000893
Viresh Kumard8d3b472013-08-04 01:20:07 +0200894 unlock_policy_rwsem_write(policy->cpu);
Viresh Kumar2eaa3e22013-02-07 10:55:00 +0530895
Viresh Kumar820c6ca2013-04-22 00:48:03 +0200896 if (has_target) {
Viresh Kumar3de9bde2013-08-06 22:53:13 +0530897 if ((ret = __cpufreq_governor(policy, CPUFREQ_GOV_START)) ||
898 (ret = __cpufreq_governor(policy, CPUFREQ_GOV_LIMITS))) {
899 pr_err("%s: Failed to start governor\n", __func__);
900 return ret;
901 }
Viresh Kumar820c6ca2013-04-22 00:48:03 +0200902 }
Viresh Kumarfcf80582013-01-29 14:39:08 +0000903
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +0530904 /* Don't touch sysfs links during light-weight init */
Rafael J. Wysocki71c34612013-08-04 01:19:34 +0200905 if (!frozen)
906 ret = sysfs_create_link(&dev->kobj, &policy->kobj, "cpufreq");
Viresh Kumarfcf80582013-01-29 14:39:08 +0000907
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +0530908 return ret;
Viresh Kumarfcf80582013-01-29 14:39:08 +0000909}
910#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -0700911
Srivatsa S. Bhat84148092013-07-30 04:25:10 +0530912static struct cpufreq_policy *cpufreq_policy_restore(unsigned int cpu)
913{
914 struct cpufreq_policy *policy;
915 unsigned long flags;
916
917 write_lock_irqsave(&cpufreq_driver_lock, flags);
918
919 policy = per_cpu(cpufreq_cpu_data_fallback, cpu);
920
921 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
922
923 return policy;
924}
925
Srivatsa S. Bhate9698cc2013-07-30 04:24:11 +0530926static struct cpufreq_policy *cpufreq_policy_alloc(void)
927{
928 struct cpufreq_policy *policy;
929
930 policy = kzalloc(sizeof(*policy), GFP_KERNEL);
931 if (!policy)
932 return NULL;
933
934 if (!alloc_cpumask_var(&policy->cpus, GFP_KERNEL))
935 goto err_free_policy;
936
937 if (!zalloc_cpumask_var(&policy->related_cpus, GFP_KERNEL))
938 goto err_free_cpumask;
939
Lukasz Majewskic88a1f82013-08-06 22:53:08 +0530940 INIT_LIST_HEAD(&policy->policy_list);
Srivatsa S. Bhate9698cc2013-07-30 04:24:11 +0530941 return policy;
942
943err_free_cpumask:
944 free_cpumask_var(policy->cpus);
945err_free_policy:
946 kfree(policy);
947
948 return NULL;
949}
950
951static void cpufreq_policy_free(struct cpufreq_policy *policy)
952{
953 free_cpumask_var(policy->related_cpus);
954 free_cpumask_var(policy->cpus);
955 kfree(policy);
956}
957
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +0530958static int __cpufreq_add_dev(struct device *dev, struct subsys_interface *sif,
959 bool frozen)
Linus Torvalds1da177e2005-04-16 15:20:36 -0700960{
Viresh Kumarfcf80582013-01-29 14:39:08 +0000961 unsigned int j, cpu = dev->id;
Viresh Kumar65922462013-02-07 10:56:03 +0530962 int ret = -ENOMEM;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700963 struct cpufreq_policy *policy;
Linus Torvalds1da177e2005-04-16 15:20:36 -0700964 unsigned long flags;
Prarit Bhargava90e41ba2009-11-12 09:18:46 -0500965#ifdef CONFIG_HOTPLUG_CPU
Viresh Kumarfcf80582013-01-29 14:39:08 +0000966 struct cpufreq_governor *gov;
Rafael J. Wysocki878f6e02013-08-18 15:35:59 +0200967 int sibling;
Prarit Bhargava90e41ba2009-11-12 09:18:46 -0500968#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -0700969
Ashok Rajc32b6b82005-10-30 14:59:54 -0800970 if (cpu_is_offline(cpu))
971 return 0;
972
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +0200973 pr_debug("adding CPU %u\n", cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700974
975#ifdef CONFIG_SMP
976 /* check whether a different CPU already registered this
977 * CPU because it is in the same boat. */
978 policy = cpufreq_cpu_get(cpu);
979 if (unlikely(policy)) {
Dave Jones8ff69732006-03-05 03:37:23 -0500980 cpufreq_cpu_put(policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -0700981 return 0;
982 }
Viresh Kumarfcf80582013-01-29 14:39:08 +0000983
Viresh Kumar6eed9402013-08-06 22:53:11 +0530984 if (!down_read_trylock(&cpufreq_rwsem))
985 return 0;
986
Viresh Kumarfcf80582013-01-29 14:39:08 +0000987#ifdef CONFIG_HOTPLUG_CPU
988 /* Check if this cpu was hot-unplugged earlier and has siblings */
Nathan Zimmer0d1857a2013-02-22 16:24:34 +0000989 read_lock_irqsave(&cpufreq_driver_lock, flags);
Rafael J. Wysocki878f6e02013-08-18 15:35:59 +0200990 for_each_online_cpu(sibling) {
991 struct cpufreq_policy *cp = per_cpu(cpufreq_cpu_data, sibling);
992 if (cp && cpumask_test_cpu(cpu, cp->related_cpus)) {
Nathan Zimmer0d1857a2013-02-22 16:24:34 +0000993 read_unlock_irqrestore(&cpufreq_driver_lock, flags);
Rafael J. Wysocki878f6e02013-08-18 15:35:59 +0200994 ret = cpufreq_add_policy_cpu(cp, cpu, dev, frozen);
Viresh Kumar6eed9402013-08-06 22:53:11 +0530995 up_read(&cpufreq_rwsem);
996 return ret;
Viresh Kumar2eaa3e22013-02-07 10:55:00 +0530997 }
Viresh Kumarfcf80582013-01-29 14:39:08 +0000998 }
Nathan Zimmer0d1857a2013-02-22 16:24:34 +0000999 read_unlock_irqrestore(&cpufreq_driver_lock, flags);
Viresh Kumarfcf80582013-01-29 14:39:08 +00001000#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -07001001#endif
1002
Srivatsa S. Bhat84148092013-07-30 04:25:10 +05301003 if (frozen)
1004 /* Restore the saved policy when doing light-weight init */
1005 policy = cpufreq_policy_restore(cpu);
1006 else
1007 policy = cpufreq_policy_alloc();
1008
Dave Jones059019a2009-07-08 16:30:03 -04001009 if (!policy)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001010 goto nomem_out;
Dave Jones059019a2009-07-08 16:30:03 -04001011
Linus Torvalds1da177e2005-04-16 15:20:36 -07001012 policy->cpu = cpu;
Viresh Kumar65922462013-02-07 10:56:03 +05301013 policy->governor = CPUFREQ_DEFAULT_GOVERNOR;
Rusty Russell835481d2009-01-04 05:18:06 -08001014 cpumask_copy(policy->cpus, cpumask_of(cpu));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001015
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001016 /* Initially set CPU itself as the policy_cpu */
Tejun Heof1625062009-10-29 22:34:13 +09001017 per_cpu(cpufreq_policy_cpu, cpu) = cpu;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001018
Linus Torvalds1da177e2005-04-16 15:20:36 -07001019 init_completion(&policy->kobj_unregister);
David Howells65f27f32006-11-22 14:55:48 +00001020 INIT_WORK(&policy->update, handle_update);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001021
1022 /* call driver. From then on the cpufreq must be able
1023 * to accept all calls to ->verify and ->setpolicy for this CPU
1024 */
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001025 ret = cpufreq_driver->init(policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001026 if (ret) {
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001027 pr_debug("initialization failed\n");
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301028 goto err_set_policy_cpu;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001029 }
Viresh Kumar643ae6e2013-01-12 05:14:38 +00001030
Viresh Kumarfcf80582013-01-29 14:39:08 +00001031 /* related cpus should atleast have policy->cpus */
1032 cpumask_or(policy->related_cpus, policy->related_cpus, policy->cpus);
1033
Viresh Kumar643ae6e2013-01-12 05:14:38 +00001034 /*
1035 * affected cpus must always be the one, which are online. We aren't
1036 * managing offline cpus here.
1037 */
1038 cpumask_and(policy->cpus, policy->cpus, cpu_online_mask);
1039
Mike Chan187d9f42008-12-04 12:19:17 -08001040 policy->user_policy.min = policy->min;
1041 policy->user_policy.max = policy->max;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001042
Thomas Renningera1531ac2008-07-29 22:32:58 -07001043 blocking_notifier_call_chain(&cpufreq_policy_notifier_list,
1044 CPUFREQ_START, policy);
1045
Viresh Kumarfcf80582013-01-29 14:39:08 +00001046#ifdef CONFIG_HOTPLUG_CPU
1047 gov = __find_governor(per_cpu(cpufreq_cpu_governor, cpu));
1048 if (gov) {
1049 policy->governor = gov;
1050 pr_debug("Restoring governor %s for cpu %d\n",
1051 policy->governor->name, cpu);
Thomas Renninger4bfa0422009-07-24 15:25:03 +02001052 }
Viresh Kumarfcf80582013-01-29 14:39:08 +00001053#endif
Linus Torvalds1da177e2005-04-16 15:20:36 -07001054
Srivatsa S. Bhate18f1682013-07-30 04:24:23 +05301055 write_lock_irqsave(&cpufreq_driver_lock, flags);
1056 for_each_cpu(j, policy->cpus) {
1057 per_cpu(cpufreq_cpu_data, j) = policy;
1058 per_cpu(cpufreq_policy_cpu, j) = policy->cpu;
1059 }
1060 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
1061
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301062 if (!frozen) {
Viresh Kumar308b60e2013-07-31 14:35:14 +02001063 ret = cpufreq_add_dev_interface(policy, dev);
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301064 if (ret)
1065 goto err_out_unregister;
1066 }
Dave Jones8ff69732006-03-05 03:37:23 -05001067
Viresh Kumar9515f4d2013-08-20 12:08:23 +05301068 write_lock_irqsave(&cpufreq_driver_lock, flags);
1069 list_add(&policy->policy_list, &cpufreq_policy_list);
1070 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
1071
Srivatsa S. Bhate18f1682013-07-30 04:24:23 +05301072 cpufreq_init_policy(policy);
1073
Greg Kroah-Hartman038c5b32007-12-17 15:54:39 -04001074 kobject_uevent(&policy->kobj, KOBJ_ADD);
Viresh Kumar6eed9402013-08-06 22:53:11 +05301075 up_read(&cpufreq_rwsem);
1076
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001077 pr_debug("initialization complete\n");
Dave Jones87c32272006-03-29 01:48:37 -05001078
Linus Torvalds1da177e2005-04-16 15:20:36 -07001079 return 0;
1080
Linus Torvalds1da177e2005-04-16 15:20:36 -07001081err_out_unregister:
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00001082 write_lock_irqsave(&cpufreq_driver_lock, flags);
Srivatsa S. Bhate18f1682013-07-30 04:24:23 +05301083 for_each_cpu(j, policy->cpus) {
Mike Travis7a6aedf2008-03-25 15:06:53 -07001084 per_cpu(cpufreq_cpu_data, j) = NULL;
Srivatsa S. Bhate18f1682013-07-30 04:24:23 +05301085 if (j != cpu)
1086 per_cpu(cpufreq_policy_cpu, j) = -1;
1087 }
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00001088 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001089
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301090err_set_policy_cpu:
1091 per_cpu(cpufreq_policy_cpu, cpu) = -1;
Srivatsa S. Bhate9698cc2013-07-30 04:24:11 +05301092 cpufreq_policy_free(policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001093nomem_out:
Viresh Kumar6eed9402013-08-06 22:53:11 +05301094 up_read(&cpufreq_rwsem);
1095
Linus Torvalds1da177e2005-04-16 15:20:36 -07001096 return ret;
1097}
1098
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301099/**
1100 * cpufreq_add_dev - add a CPU device
1101 *
1102 * Adds the cpufreq interface for a CPU device.
1103 *
1104 * The Oracle says: try running cpufreq registration/unregistration concurrently
1105 * with with cpu hotplugging and all hell will break loose. Tried to clean this
1106 * mess up, but more thorough testing is needed. - Mathieu
1107 */
1108static int cpufreq_add_dev(struct device *dev, struct subsys_interface *sif)
1109{
1110 return __cpufreq_add_dev(dev, sif, false);
1111}
1112
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001113static void update_policy_cpu(struct cpufreq_policy *policy, unsigned int cpu)
1114{
1115 int j;
1116
1117 policy->last_cpu = policy->cpu;
1118 policy->cpu = cpu;
1119
Viresh Kumar3361b7b2013-02-04 11:38:51 +00001120 for_each_cpu(j, policy->cpus)
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001121 per_cpu(cpufreq_policy_cpu, j) = cpu;
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001122
1123#ifdef CONFIG_CPU_FREQ_TABLE
1124 cpufreq_frequency_table_update_policy_cpu(policy);
1125#endif
1126 blocking_notifier_call_chain(&cpufreq_policy_notifier_list,
1127 CPUFREQ_UPDATE_POLICY_CPU, policy);
1128}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001129
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301130static int cpufreq_nominate_new_policy_cpu(struct cpufreq_policy *policy,
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301131 unsigned int old_cpu, bool frozen)
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301132{
1133 struct device *cpu_dev;
1134 unsigned long flags;
1135 int ret;
1136
1137 /* first sibling now owns the new sysfs dir */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301138 cpu_dev = get_cpu_device(cpumask_first(policy->cpus));
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301139
1140 /* Don't touch sysfs files during light-weight tear-down */
1141 if (frozen)
1142 return cpu_dev->id;
1143
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301144 sysfs_remove_link(&cpu_dev->kobj, "cpufreq");
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301145 ret = kobject_move(&policy->kobj, &cpu_dev->kobj);
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301146 if (ret) {
1147 pr_err("%s: Failed to move kobj: %d", __func__, ret);
1148
1149 WARN_ON(lock_policy_rwsem_write(old_cpu));
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301150 cpumask_set_cpu(old_cpu, policy->cpus);
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301151
1152 write_lock_irqsave(&cpufreq_driver_lock, flags);
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301153 per_cpu(cpufreq_cpu_data, old_cpu) = policy;
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301154 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
1155
1156 unlock_policy_rwsem_write(old_cpu);
1157
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301158 ret = sysfs_create_link(&cpu_dev->kobj, &policy->kobj,
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301159 "cpufreq");
1160
1161 return -EINVAL;
1162 }
1163
1164 return cpu_dev->id;
1165}
1166
Linus Torvalds1da177e2005-04-16 15:20:36 -07001167/**
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001168 * __cpufreq_remove_dev - remove a CPU device
Linus Torvalds1da177e2005-04-16 15:20:36 -07001169 *
1170 * Removes the cpufreq interface for a CPU device.
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001171 * Caller should already have policy_rwsem in write mode for this CPU.
1172 * This routine frees the rwsem before returning.
Linus Torvalds1da177e2005-04-16 15:20:36 -07001173 */
Viresh Kumarbb176f72013-06-19 14:19:33 +05301174static int __cpufreq_remove_dev(struct device *dev,
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301175 struct subsys_interface *sif, bool frozen)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001176{
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301177 unsigned int cpu = dev->id, cpus;
Viresh Kumar3de9bde2013-08-06 22:53:13 +05301178 int new_cpu, ret;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001179 unsigned long flags;
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301180 struct cpufreq_policy *policy;
Amerigo Wang499bca92010-03-04 03:23:46 -05001181 struct kobject *kobj;
1182 struct completion *cmp;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001183
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001184 pr_debug("%s: unregistering CPU %u\n", __func__, cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001185
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00001186 write_lock_irqsave(&cpufreq_driver_lock, flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001187
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301188 policy = per_cpu(cpufreq_cpu_data, cpu);
Mike Travis7a6aedf2008-03-25 15:06:53 -07001189 per_cpu(cpufreq_cpu_data, cpu) = NULL;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001190
Srivatsa S. Bhat84148092013-07-30 04:25:10 +05301191 /* Save the policy somewhere when doing a light-weight tear-down */
1192 if (frozen)
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301193 per_cpu(cpufreq_cpu_data_fallback, cpu) = policy;
Srivatsa S. Bhat84148092013-07-30 04:25:10 +05301194
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00001195 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001196
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301197 if (!policy) {
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001198 pr_debug("%s: No cpu_data found\n", __func__);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001199 return -EINVAL;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001200 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001201
Viresh Kumar3de9bde2013-08-06 22:53:13 +05301202 if (cpufreq_driver->target) {
1203 ret = __cpufreq_governor(policy, CPUFREQ_GOV_STOP);
1204 if (ret) {
1205 pr_err("%s: Failed to stop governor\n", __func__);
1206 return ret;
1207 }
1208 }
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001209
Jacob Shin27ecddc2011-04-27 13:32:11 -05001210#ifdef CONFIG_HOTPLUG_CPU
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001211 if (!cpufreq_driver->setpolicy)
Dirk Brandewiefa69e332013-02-06 09:02:11 -08001212 strncpy(per_cpu(cpufreq_cpu_governor, cpu),
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301213 policy->governor->name, CPUFREQ_NAME_LEN);
Jacob Shin27ecddc2011-04-27 13:32:11 -05001214#endif
1215
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301216 WARN_ON(lock_policy_rwsem_write(cpu));
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301217 cpus = cpumask_weight(policy->cpus);
Viresh Kumare4969eb2013-04-11 08:04:53 +00001218
1219 if (cpus > 1)
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301220 cpumask_clear_cpu(cpu, policy->cpus);
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301221 unlock_policy_rwsem_write(cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001222
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301223 if (cpu != policy->cpu && !frozen) {
Viresh Kumar73bf0fc2013-02-05 22:21:14 +01001224 sysfs_remove_link(&dev->kobj, "cpufreq");
1225 } else if (cpus > 1) {
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301226
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301227 new_cpu = cpufreq_nominate_new_policy_cpu(policy, cpu, frozen);
Srivatsa S. Bhatf9ba6802013-07-30 04:24:36 +05301228 if (new_cpu >= 0) {
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301229 WARN_ON(lock_policy_rwsem_write(cpu));
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301230 update_policy_cpu(policy, new_cpu);
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301231 unlock_policy_rwsem_write(cpu);
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301232
1233 if (!frozen) {
1234 pr_debug("%s: policy Kobject moved to cpu: %d "
1235 "from: %d\n",__func__, new_cpu, cpu);
1236 }
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001237 }
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001238 }
Venki Pallipadiec282972007-03-26 12:03:19 -07001239
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001240 /* If cpu is last user of policy, free policy */
1241 if (cpus == 1) {
Viresh Kumar3de9bde2013-08-06 22:53:13 +05301242 if (cpufreq_driver->target) {
1243 ret = __cpufreq_governor(policy,
1244 CPUFREQ_GOV_POLICY_EXIT);
1245 if (ret) {
1246 pr_err("%s: Failed to exit governor\n",
1247 __func__);
1248 return ret;
1249 }
Viresh Kumaredab2fb2013-08-20 12:08:22 +05301250 }
Rafael J. Wysocki2a998592013-07-30 00:32:00 +02001251
Srivatsa S. Bhat84148092013-07-30 04:25:10 +05301252 if (!frozen) {
1253 lock_policy_rwsem_read(cpu);
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301254 kobj = &policy->kobj;
1255 cmp = &policy->kobj_unregister;
Srivatsa S. Bhat84148092013-07-30 04:25:10 +05301256 unlock_policy_rwsem_read(cpu);
1257 kobject_put(kobj);
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001258
Srivatsa S. Bhat84148092013-07-30 04:25:10 +05301259 /*
1260 * We need to make sure that the underlying kobj is
1261 * actually not referenced anymore by anybody before we
1262 * proceed with unloading.
1263 */
1264 pr_debug("waiting for dropping of refcount\n");
1265 wait_for_completion(cmp);
1266 pr_debug("wait complete\n");
1267 }
1268
1269 /*
1270 * Perform the ->exit() even during light-weight tear-down,
1271 * since this is a core component, and is essential for the
1272 * subsequent light-weight ->init() to succeed.
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001273 */
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001274 if (cpufreq_driver->exit)
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301275 cpufreq_driver->exit(policy);
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001276
Viresh Kumar9515f4d2013-08-20 12:08:23 +05301277 /* Remove policy from list of active policies */
1278 write_lock_irqsave(&cpufreq_driver_lock, flags);
1279 list_del(&policy->policy_list);
1280 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
1281
Srivatsa S. Bhat84148092013-07-30 04:25:10 +05301282 if (!frozen)
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301283 cpufreq_policy_free(policy);
Rafael J. Wysocki2a998592013-07-30 00:32:00 +02001284 } else {
Rafael J. Wysocki2a998592013-07-30 00:32:00 +02001285 if (cpufreq_driver->target) {
Viresh Kumar3de9bde2013-08-06 22:53:13 +05301286 if ((ret = __cpufreq_governor(policy, CPUFREQ_GOV_START)) ||
1287 (ret = __cpufreq_governor(policy, CPUFREQ_GOV_LIMITS))) {
1288 pr_err("%s: Failed to start governor\n",
1289 __func__);
1290 return ret;
1291 }
Rafael J. Wysocki2a998592013-07-30 00:32:00 +02001292 }
Viresh Kumarb8eed8a2013-01-14 13:23:03 +00001293 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001294
Viresh Kumar2eaa3e22013-02-07 10:55:00 +05301295 per_cpu(cpufreq_policy_cpu, cpu) = -1;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001296 return 0;
1297}
1298
Kay Sievers8a25a2f2011-12-21 14:29:42 -08001299static int cpufreq_remove_dev(struct device *dev, struct subsys_interface *sif)
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001300{
Kay Sievers8a25a2f2011-12-21 14:29:42 -08001301 unsigned int cpu = dev->id;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001302 int retval;
Venki Pallipadiec282972007-03-26 12:03:19 -07001303
1304 if (cpu_is_offline(cpu))
1305 return 0;
1306
Srivatsa S. Bhata82fab22013-07-30 04:24:49 +05301307 retval = __cpufreq_remove_dev(dev, sif, false);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001308 return retval;
1309}
1310
David Howells65f27f32006-11-22 14:55:48 +00001311static void handle_update(struct work_struct *work)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001312{
David Howells65f27f32006-11-22 14:55:48 +00001313 struct cpufreq_policy *policy =
1314 container_of(work, struct cpufreq_policy, update);
1315 unsigned int cpu = policy->cpu;
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001316 pr_debug("handle_update for cpu %u called\n", cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001317 cpufreq_update_policy(cpu);
1318}
1319
1320/**
Viresh Kumarbb176f72013-06-19 14:19:33 +05301321 * cpufreq_out_of_sync - If actual and saved CPU frequency differs, we're
1322 * in deep trouble.
Linus Torvalds1da177e2005-04-16 15:20:36 -07001323 * @cpu: cpu number
1324 * @old_freq: CPU frequency the kernel thinks the CPU runs at
1325 * @new_freq: CPU frequency the CPU actually runs at
1326 *
Dave Jones29464f22009-01-18 01:37:11 -05001327 * We adjust to current frequency first, and need to clean up later.
1328 * So either call to cpufreq_update_policy() or schedule handle_update()).
Linus Torvalds1da177e2005-04-16 15:20:36 -07001329 */
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301330static void cpufreq_out_of_sync(unsigned int cpu, unsigned int old_freq,
1331 unsigned int new_freq)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001332{
Viresh Kumarb43a7ff2013-03-24 11:56:43 +05301333 struct cpufreq_policy *policy;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001334 struct cpufreq_freqs freqs;
Viresh Kumarb43a7ff2013-03-24 11:56:43 +05301335 unsigned long flags;
1336
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001337 pr_debug("Warning: CPU frequency out of sync: cpufreq and timing "
Linus Torvalds1da177e2005-04-16 15:20:36 -07001338 "core thinks of %u, is %u kHz.\n", old_freq, new_freq);
1339
Linus Torvalds1da177e2005-04-16 15:20:36 -07001340 freqs.old = old_freq;
1341 freqs.new = new_freq;
Viresh Kumarb43a7ff2013-03-24 11:56:43 +05301342
1343 read_lock_irqsave(&cpufreq_driver_lock, flags);
1344 policy = per_cpu(cpufreq_cpu_data, cpu);
1345 read_unlock_irqrestore(&cpufreq_driver_lock, flags);
1346
1347 cpufreq_notify_transition(policy, &freqs, CPUFREQ_PRECHANGE);
1348 cpufreq_notify_transition(policy, &freqs, CPUFREQ_POSTCHANGE);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001349}
1350
Dave Jones32ee8c32006-02-28 00:43:23 -05001351/**
Dhaval Giani4ab70df2006-12-13 14:49:15 +05301352 * cpufreq_quick_get - get the CPU frequency (in kHz) from policy->cur
Venkatesh Pallipadi95235ca2005-12-02 10:43:20 -08001353 * @cpu: CPU number
1354 *
1355 * This is the last known freq, without actually getting it from the driver.
1356 * Return value will be same as what is shown in scaling_cur_freq in sysfs.
1357 */
1358unsigned int cpufreq_quick_get(unsigned int cpu)
1359{
Dirk Brandewie9e21ba82013-02-06 09:02:08 -08001360 struct cpufreq_policy *policy;
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301361 unsigned int ret_freq = 0;
Venkatesh Pallipadi95235ca2005-12-02 10:43:20 -08001362
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001363 if (cpufreq_driver && cpufreq_driver->setpolicy && cpufreq_driver->get)
1364 return cpufreq_driver->get(cpu);
Dirk Brandewie9e21ba82013-02-06 09:02:08 -08001365
1366 policy = cpufreq_cpu_get(cpu);
Venkatesh Pallipadi95235ca2005-12-02 10:43:20 -08001367 if (policy) {
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301368 ret_freq = policy->cur;
Venkatesh Pallipadi95235ca2005-12-02 10:43:20 -08001369 cpufreq_cpu_put(policy);
1370 }
1371
Dave Jones4d34a672008-02-07 16:33:49 -05001372 return ret_freq;
Venkatesh Pallipadi95235ca2005-12-02 10:43:20 -08001373}
1374EXPORT_SYMBOL(cpufreq_quick_get);
1375
Jesse Barnes3d737102011-06-28 10:59:12 -07001376/**
1377 * cpufreq_quick_get_max - get the max reported CPU frequency for this CPU
1378 * @cpu: CPU number
1379 *
1380 * Just return the max possible frequency for a given CPU.
1381 */
1382unsigned int cpufreq_quick_get_max(unsigned int cpu)
1383{
1384 struct cpufreq_policy *policy = cpufreq_cpu_get(cpu);
1385 unsigned int ret_freq = 0;
1386
1387 if (policy) {
1388 ret_freq = policy->max;
1389 cpufreq_cpu_put(policy);
1390 }
1391
1392 return ret_freq;
1393}
1394EXPORT_SYMBOL(cpufreq_quick_get_max);
1395
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001396static unsigned int __cpufreq_get(unsigned int cpu)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001397{
Mike Travis7a6aedf2008-03-25 15:06:53 -07001398 struct cpufreq_policy *policy = per_cpu(cpufreq_cpu_data, cpu);
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301399 unsigned int ret_freq = 0;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001400
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001401 if (!cpufreq_driver->get)
Dave Jones4d34a672008-02-07 16:33:49 -05001402 return ret_freq;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001403
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001404 ret_freq = cpufreq_driver->get(cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001405
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301406 if (ret_freq && policy->cur &&
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001407 !(cpufreq_driver->flags & CPUFREQ_CONST_LOOPS)) {
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301408 /* verify no discrepancy between actual and
1409 saved value exists */
1410 if (unlikely(ret_freq != policy->cur)) {
1411 cpufreq_out_of_sync(cpu, policy->cur, ret_freq);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001412 schedule_work(&policy->update);
1413 }
1414 }
1415
Dave Jones4d34a672008-02-07 16:33:49 -05001416 return ret_freq;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001417}
Linus Torvalds1da177e2005-04-16 15:20:36 -07001418
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001419/**
1420 * cpufreq_get - get the current CPU frequency (in kHz)
1421 * @cpu: CPU number
1422 *
1423 * Get the CPU current (static) CPU frequency
1424 */
1425unsigned int cpufreq_get(unsigned int cpu)
1426{
1427 unsigned int ret_freq = 0;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001428
Viresh Kumar6eed9402013-08-06 22:53:11 +05301429 if (!down_read_trylock(&cpufreq_rwsem))
1430 return 0;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001431
1432 if (unlikely(lock_policy_rwsem_read(cpu)))
1433 goto out_policy;
1434
1435 ret_freq = __cpufreq_get(cpu);
1436
1437 unlock_policy_rwsem_read(cpu);
1438
1439out_policy:
Viresh Kumar6eed9402013-08-06 22:53:11 +05301440 up_read(&cpufreq_rwsem);
1441
Dave Jones4d34a672008-02-07 16:33:49 -05001442 return ret_freq;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001443}
1444EXPORT_SYMBOL(cpufreq_get);
1445
Kay Sievers8a25a2f2011-12-21 14:29:42 -08001446static struct subsys_interface cpufreq_interface = {
1447 .name = "cpufreq",
1448 .subsys = &cpu_subsys,
1449 .add_dev = cpufreq_add_dev,
1450 .remove_dev = cpufreq_remove_dev,
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001451};
1452
Linus Torvalds1da177e2005-04-16 15:20:36 -07001453/**
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001454 * cpufreq_bp_suspend - Prepare the boot CPU for system suspend.
1455 *
1456 * This function is only executed for the boot processor. The other CPUs
1457 * have been put offline by means of CPU hotplug.
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001458 */
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001459static int cpufreq_bp_suspend(void)
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001460{
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301461 int ret = 0;
Dave Jones4bc5d342009-08-04 14:03:25 -04001462
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001463 int cpu = smp_processor_id();
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301464 struct cpufreq_policy *policy;
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001465
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001466 pr_debug("suspending cpu %u\n", cpu);
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001467
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001468 /* If there's no policy for the boot CPU, we have nothing to do. */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301469 policy = cpufreq_cpu_get(cpu);
1470 if (!policy)
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001471 return 0;
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001472
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001473 if (cpufreq_driver->suspend) {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301474 ret = cpufreq_driver->suspend(policy);
Dominik Brodowskice6c3992009-08-07 22:58:51 +02001475 if (ret)
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001476 printk(KERN_ERR "cpufreq: suspend failed in ->suspend "
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301477 "step on CPU %u\n", policy->cpu);
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001478 }
1479
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301480 cpufreq_cpu_put(policy);
Dave Jonesc9060492008-02-07 16:32:18 -05001481 return ret;
Benjamin Herrenschmidt42d4dc32005-04-29 07:40:12 -07001482}
1483
1484/**
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001485 * cpufreq_bp_resume - Restore proper frequency handling of the boot CPU.
Linus Torvalds1da177e2005-04-16 15:20:36 -07001486 *
1487 * 1.) resume CPUfreq hardware support (cpufreq_driver->resume())
Dominik Brodowskice6c3992009-08-07 22:58:51 +02001488 * 2.) schedule call cpufreq_update_policy() ASAP as interrupts are
1489 * restored. It will verify that the current freq is in sync with
1490 * what we believe it to be. This is a bit later than when it
1491 * should be, but nonethteless it's better than calling
1492 * cpufreq_driver->get() here which might re-enable interrupts...
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001493 *
1494 * This function is only executed for the boot CPU. The other CPUs have not
1495 * been turned on yet.
Linus Torvalds1da177e2005-04-16 15:20:36 -07001496 */
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001497static void cpufreq_bp_resume(void)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001498{
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301499 int ret = 0;
Dave Jones4bc5d342009-08-04 14:03:25 -04001500
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001501 int cpu = smp_processor_id();
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301502 struct cpufreq_policy *policy;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001503
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001504 pr_debug("resuming cpu %u\n", cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001505
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001506 /* If there's no policy for the boot CPU, we have nothing to do. */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301507 policy = cpufreq_cpu_get(cpu);
1508 if (!policy)
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001509 return;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001510
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001511 if (cpufreq_driver->resume) {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301512 ret = cpufreq_driver->resume(policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001513 if (ret) {
1514 printk(KERN_ERR "cpufreq: resume failed in ->resume "
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301515 "step on CPU %u\n", policy->cpu);
Dave Jonesc9060492008-02-07 16:32:18 -05001516 goto fail;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001517 }
1518 }
1519
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301520 schedule_work(&policy->update);
Dominik Brodowskice6c3992009-08-07 22:58:51 +02001521
Dave Jonesc9060492008-02-07 16:32:18 -05001522fail:
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301523 cpufreq_cpu_put(policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001524}
1525
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01001526static struct syscore_ops cpufreq_syscore_ops = {
1527 .suspend = cpufreq_bp_suspend,
1528 .resume = cpufreq_bp_resume,
Linus Torvalds1da177e2005-04-16 15:20:36 -07001529};
1530
Borislav Petkov9d950462013-01-20 10:24:28 +00001531/**
1532 * cpufreq_get_current_driver - return current driver's name
1533 *
1534 * Return the name string of the currently loaded cpufreq driver
1535 * or NULL, if none.
1536 */
1537const char *cpufreq_get_current_driver(void)
1538{
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001539 if (cpufreq_driver)
1540 return cpufreq_driver->name;
1541
1542 return NULL;
Borislav Petkov9d950462013-01-20 10:24:28 +00001543}
1544EXPORT_SYMBOL_GPL(cpufreq_get_current_driver);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001545
1546/*********************************************************************
1547 * NOTIFIER LISTS INTERFACE *
1548 *********************************************************************/
1549
1550/**
1551 * cpufreq_register_notifier - register a driver with cpufreq
1552 * @nb: notifier function to register
1553 * @list: CPUFREQ_TRANSITION_NOTIFIER or CPUFREQ_POLICY_NOTIFIER
1554 *
Dave Jones32ee8c32006-02-28 00:43:23 -05001555 * Add a driver to one of two lists: either a list of drivers that
Linus Torvalds1da177e2005-04-16 15:20:36 -07001556 * are notified about clock rate changes (once before and once after
1557 * the transition), or a list of drivers that are notified about
1558 * changes in cpufreq policy.
1559 *
1560 * This function may sleep, and has the same return conditions as
Alan Sterne041c682006-03-27 01:16:30 -08001561 * blocking_notifier_chain_register.
Linus Torvalds1da177e2005-04-16 15:20:36 -07001562 */
1563int cpufreq_register_notifier(struct notifier_block *nb, unsigned int list)
1564{
1565 int ret;
1566
Dirk Brandewied5aaffa2013-01-17 16:22:21 +00001567 if (cpufreq_disabled())
1568 return -EINVAL;
1569
Cesar Eduardo Barros74212ca2008-02-16 08:41:24 -02001570 WARN_ON(!init_cpufreq_transition_notifier_list_called);
1571
Linus Torvalds1da177e2005-04-16 15:20:36 -07001572 switch (list) {
1573 case CPUFREQ_TRANSITION_NOTIFIER:
Alan Sternb4dfdbb2006-10-04 02:17:06 -07001574 ret = srcu_notifier_chain_register(
Alan Sterne041c682006-03-27 01:16:30 -08001575 &cpufreq_transition_notifier_list, nb);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001576 break;
1577 case CPUFREQ_POLICY_NOTIFIER:
Alan Sterne041c682006-03-27 01:16:30 -08001578 ret = blocking_notifier_chain_register(
1579 &cpufreq_policy_notifier_list, nb);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001580 break;
1581 default:
1582 ret = -EINVAL;
1583 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001584
1585 return ret;
1586}
1587EXPORT_SYMBOL(cpufreq_register_notifier);
1588
Linus Torvalds1da177e2005-04-16 15:20:36 -07001589/**
1590 * cpufreq_unregister_notifier - unregister a driver with cpufreq
1591 * @nb: notifier block to be unregistered
Viresh Kumarbb176f72013-06-19 14:19:33 +05301592 * @list: CPUFREQ_TRANSITION_NOTIFIER or CPUFREQ_POLICY_NOTIFIER
Linus Torvalds1da177e2005-04-16 15:20:36 -07001593 *
1594 * Remove a driver from the CPU frequency notifier list.
1595 *
1596 * This function may sleep, and has the same return conditions as
Alan Sterne041c682006-03-27 01:16:30 -08001597 * blocking_notifier_chain_unregister.
Linus Torvalds1da177e2005-04-16 15:20:36 -07001598 */
1599int cpufreq_unregister_notifier(struct notifier_block *nb, unsigned int list)
1600{
1601 int ret;
1602
Dirk Brandewied5aaffa2013-01-17 16:22:21 +00001603 if (cpufreq_disabled())
1604 return -EINVAL;
1605
Linus Torvalds1da177e2005-04-16 15:20:36 -07001606 switch (list) {
1607 case CPUFREQ_TRANSITION_NOTIFIER:
Alan Sternb4dfdbb2006-10-04 02:17:06 -07001608 ret = srcu_notifier_chain_unregister(
Alan Sterne041c682006-03-27 01:16:30 -08001609 &cpufreq_transition_notifier_list, nb);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001610 break;
1611 case CPUFREQ_POLICY_NOTIFIER:
Alan Sterne041c682006-03-27 01:16:30 -08001612 ret = blocking_notifier_chain_unregister(
1613 &cpufreq_policy_notifier_list, nb);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001614 break;
1615 default:
1616 ret = -EINVAL;
1617 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001618
1619 return ret;
1620}
1621EXPORT_SYMBOL(cpufreq_unregister_notifier);
1622
1623
1624/*********************************************************************
1625 * GOVERNORS *
1626 *********************************************************************/
1627
Linus Torvalds1da177e2005-04-16 15:20:36 -07001628int __cpufreq_driver_target(struct cpufreq_policy *policy,
1629 unsigned int target_freq,
1630 unsigned int relation)
1631{
1632 int retval = -EINVAL;
Viresh Kumar72499242012-10-31 01:28:21 +01001633 unsigned int old_target_freq = target_freq;
Ashok Rajc32b6b82005-10-30 14:59:54 -08001634
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -04001635 if (cpufreq_disabled())
1636 return -ENODEV;
Viresh Kumar7c30ed52013-06-19 10:16:55 +05301637 if (policy->transition_ongoing)
1638 return -EBUSY;
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -04001639
Viresh Kumar72499242012-10-31 01:28:21 +01001640 /* Make sure that target_freq is within supported range */
1641 if (target_freq > policy->max)
1642 target_freq = policy->max;
1643 if (target_freq < policy->min)
1644 target_freq = policy->min;
1645
1646 pr_debug("target for CPU %u: %u kHz, relation %u, requested %u kHz\n",
1647 policy->cpu, target_freq, relation, old_target_freq);
Viresh Kumar5a1c0222012-10-31 01:28:15 +01001648
1649 if (target_freq == policy->cur)
1650 return 0;
1651
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001652 if (cpufreq_driver->target)
1653 retval = cpufreq_driver->target(policy, target_freq, relation);
Ashok Raj90d45d12005-11-08 21:34:24 -08001654
Linus Torvalds1da177e2005-04-16 15:20:36 -07001655 return retval;
1656}
1657EXPORT_SYMBOL_GPL(__cpufreq_driver_target);
1658
Linus Torvalds1da177e2005-04-16 15:20:36 -07001659int cpufreq_driver_target(struct cpufreq_policy *policy,
1660 unsigned int target_freq,
1661 unsigned int relation)
1662{
Julia Lawallf1829e42008-07-25 22:44:53 +02001663 int ret = -EINVAL;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001664
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001665 if (unlikely(lock_policy_rwsem_write(policy->cpu)))
Julia Lawallf1829e42008-07-25 22:44:53 +02001666 goto fail;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001667
1668 ret = __cpufreq_driver_target(policy, target_freq, relation);
1669
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001670 unlock_policy_rwsem_write(policy->cpu);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001671
Julia Lawallf1829e42008-07-25 22:44:53 +02001672fail:
Linus Torvalds1da177e2005-04-16 15:20:36 -07001673 return ret;
1674}
1675EXPORT_SYMBOL_GPL(cpufreq_driver_target);
1676
Arjan van de Ven153d7f32006-07-26 15:40:07 +02001677/*
Arjan van de Ven153d7f32006-07-26 15:40:07 +02001678 * when "event" is CPUFREQ_GOV_LIMITS
1679 */
Linus Torvalds1da177e2005-04-16 15:20:36 -07001680
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301681static int __cpufreq_governor(struct cpufreq_policy *policy,
1682 unsigned int event)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001683{
Dave Jonescc993ca2005-07-28 09:43:56 -07001684 int ret;
Thomas Renninger6afde102007-10-02 13:28:13 -07001685
1686 /* Only must be defined when default governor is known to have latency
1687 restrictions, like e.g. conservative or ondemand.
1688 That this is the case is already ensured in Kconfig
1689 */
1690#ifdef CONFIG_CPU_FREQ_GOV_PERFORMANCE
1691 struct cpufreq_governor *gov = &cpufreq_gov_performance;
1692#else
1693 struct cpufreq_governor *gov = NULL;
1694#endif
Thomas Renninger1c256242007-10-02 13:28:12 -07001695
1696 if (policy->governor->max_transition_latency &&
1697 policy->cpuinfo.transition_latency >
1698 policy->governor->max_transition_latency) {
Thomas Renninger6afde102007-10-02 13:28:13 -07001699 if (!gov)
1700 return -EINVAL;
1701 else {
1702 printk(KERN_WARNING "%s governor failed, too long"
1703 " transition latency of HW, fallback"
1704 " to %s governor\n",
1705 policy->governor->name,
1706 gov->name);
1707 policy->governor = gov;
1708 }
Thomas Renninger1c256242007-10-02 13:28:12 -07001709 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001710
Viresh Kumarfe492f32013-08-06 22:53:10 +05301711 if (event == CPUFREQ_GOV_POLICY_INIT)
1712 if (!try_module_get(policy->governor->owner))
1713 return -EINVAL;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001714
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001715 pr_debug("__cpufreq_governor for CPU %u, event %u\n",
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301716 policy->cpu, event);
Xiaoguang Chen95731eb2013-06-19 15:00:07 +08001717
1718 mutex_lock(&cpufreq_governor_lock);
1719 if ((!policy->governor_enabled && (event == CPUFREQ_GOV_STOP)) ||
1720 (policy->governor_enabled && (event == CPUFREQ_GOV_START))) {
1721 mutex_unlock(&cpufreq_governor_lock);
Viresh Kumarfe492f32013-08-06 22:53:10 +05301722 if (event == CPUFREQ_GOV_POLICY_INIT)
1723 module_put(policy->governor->owner);
Xiaoguang Chen95731eb2013-06-19 15:00:07 +08001724 return -EBUSY;
1725 }
1726
1727 if (event == CPUFREQ_GOV_STOP)
1728 policy->governor_enabled = false;
1729 else if (event == CPUFREQ_GOV_START)
1730 policy->governor_enabled = true;
1731
1732 mutex_unlock(&cpufreq_governor_lock);
1733
Linus Torvalds1da177e2005-04-16 15:20:36 -07001734 ret = policy->governor->governor(policy, event);
1735
Viresh Kumar4d5dcc42013-03-27 15:58:58 +00001736 if (!ret) {
1737 if (event == CPUFREQ_GOV_POLICY_INIT)
1738 policy->governor->initialized++;
1739 else if (event == CPUFREQ_GOV_POLICY_EXIT)
1740 policy->governor->initialized--;
Xiaoguang Chen95731eb2013-06-19 15:00:07 +08001741 } else {
1742 /* Restore original values */
1743 mutex_lock(&cpufreq_governor_lock);
1744 if (event == CPUFREQ_GOV_STOP)
1745 policy->governor_enabled = true;
1746 else if (event == CPUFREQ_GOV_START)
1747 policy->governor_enabled = false;
1748 mutex_unlock(&cpufreq_governor_lock);
Viresh Kumar4d5dcc42013-03-27 15:58:58 +00001749 }
Viresh Kumarb3940582013-02-01 05:42:58 +00001750
Viresh Kumarfe492f32013-08-06 22:53:10 +05301751 if (((event == CPUFREQ_GOV_POLICY_INIT) && ret) ||
1752 ((event == CPUFREQ_GOV_POLICY_EXIT) && !ret))
Linus Torvalds1da177e2005-04-16 15:20:36 -07001753 module_put(policy->governor->owner);
1754
1755 return ret;
1756}
1757
Linus Torvalds1da177e2005-04-16 15:20:36 -07001758int cpufreq_register_governor(struct cpufreq_governor *governor)
1759{
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -07001760 int err;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001761
1762 if (!governor)
1763 return -EINVAL;
1764
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -04001765 if (cpufreq_disabled())
1766 return -ENODEV;
1767
akpm@osdl.org3fc54d32006-01-13 15:54:22 -08001768 mutex_lock(&cpufreq_governor_mutex);
Dave Jones32ee8c32006-02-28 00:43:23 -05001769
Viresh Kumarb3940582013-02-01 05:42:58 +00001770 governor->initialized = 0;
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -07001771 err = -EBUSY;
1772 if (__find_governor(governor->name) == NULL) {
1773 err = 0;
1774 list_add(&governor->governor_list, &cpufreq_governor_list);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001775 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001776
Dave Jones32ee8c32006-02-28 00:43:23 -05001777 mutex_unlock(&cpufreq_governor_mutex);
Jeremy Fitzhardinge3bcb09a2006-07-06 12:30:26 -07001778 return err;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001779}
1780EXPORT_SYMBOL_GPL(cpufreq_register_governor);
1781
Linus Torvalds1da177e2005-04-16 15:20:36 -07001782void cpufreq_unregister_governor(struct cpufreq_governor *governor)
1783{
Prarit Bhargava90e41ba2009-11-12 09:18:46 -05001784#ifdef CONFIG_HOTPLUG_CPU
1785 int cpu;
1786#endif
1787
Linus Torvalds1da177e2005-04-16 15:20:36 -07001788 if (!governor)
1789 return;
1790
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -04001791 if (cpufreq_disabled())
1792 return;
1793
Prarit Bhargava90e41ba2009-11-12 09:18:46 -05001794#ifdef CONFIG_HOTPLUG_CPU
1795 for_each_present_cpu(cpu) {
1796 if (cpu_online(cpu))
1797 continue;
1798 if (!strcmp(per_cpu(cpufreq_cpu_governor, cpu), governor->name))
1799 strcpy(per_cpu(cpufreq_cpu_governor, cpu), "\0");
1800 }
1801#endif
1802
akpm@osdl.org3fc54d32006-01-13 15:54:22 -08001803 mutex_lock(&cpufreq_governor_mutex);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001804 list_del(&governor->governor_list);
akpm@osdl.org3fc54d32006-01-13 15:54:22 -08001805 mutex_unlock(&cpufreq_governor_mutex);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001806 return;
1807}
1808EXPORT_SYMBOL_GPL(cpufreq_unregister_governor);
1809
1810
Linus Torvalds1da177e2005-04-16 15:20:36 -07001811/*********************************************************************
1812 * POLICY INTERFACE *
1813 *********************************************************************/
1814
1815/**
1816 * cpufreq_get_policy - get the current cpufreq_policy
Dave Jones29464f22009-01-18 01:37:11 -05001817 * @policy: struct cpufreq_policy into which the current cpufreq_policy
1818 * is written
Linus Torvalds1da177e2005-04-16 15:20:36 -07001819 *
1820 * Reads the current cpufreq policy.
1821 */
1822int cpufreq_get_policy(struct cpufreq_policy *policy, unsigned int cpu)
1823{
1824 struct cpufreq_policy *cpu_policy;
1825 if (!policy)
1826 return -EINVAL;
1827
1828 cpu_policy = cpufreq_cpu_get(cpu);
1829 if (!cpu_policy)
1830 return -EINVAL;
1831
Viresh Kumard5b73cd2013-08-06 22:53:06 +05301832 memcpy(policy, cpu_policy, sizeof(*policy));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001833
1834 cpufreq_cpu_put(cpu_policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001835 return 0;
1836}
1837EXPORT_SYMBOL(cpufreq_get_policy);
1838
Arjan van de Ven153d7f32006-07-26 15:40:07 +02001839/*
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301840 * data : current policy.
1841 * policy : policy to be set.
Arjan van de Ven153d7f32006-07-26 15:40:07 +02001842 */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301843static int __cpufreq_set_policy(struct cpufreq_policy *policy,
1844 struct cpufreq_policy *new_policy)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001845{
Viresh Kumar7bd353a2013-03-27 15:58:57 +00001846 int ret = 0, failed = 1;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001847
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301848 pr_debug("setting new policy for CPU %u: %u - %u kHz\n", new_policy->cpu,
1849 new_policy->min, new_policy->max);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001850
Viresh Kumard5b73cd2013-08-06 22:53:06 +05301851 memcpy(&new_policy->cpuinfo, &policy->cpuinfo, sizeof(policy->cpuinfo));
Linus Torvalds1da177e2005-04-16 15:20:36 -07001852
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301853 if (new_policy->min > policy->max || new_policy->max < policy->min) {
Mattia Dongili9c9a43e2006-07-05 23:12:20 +02001854 ret = -EINVAL;
1855 goto error_out;
1856 }
1857
Linus Torvalds1da177e2005-04-16 15:20:36 -07001858 /* verify the cpu speed can be set within this limit */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301859 ret = cpufreq_driver->verify(new_policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001860 if (ret)
1861 goto error_out;
1862
Linus Torvalds1da177e2005-04-16 15:20:36 -07001863 /* adjust if necessary - all reasons */
Alan Sterne041c682006-03-27 01:16:30 -08001864 blocking_notifier_call_chain(&cpufreq_policy_notifier_list,
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301865 CPUFREQ_ADJUST, new_policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001866
1867 /* adjust if necessary - hardware incompatibility*/
Alan Sterne041c682006-03-27 01:16:30 -08001868 blocking_notifier_call_chain(&cpufreq_policy_notifier_list,
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301869 CPUFREQ_INCOMPATIBLE, new_policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001870
Viresh Kumarbb176f72013-06-19 14:19:33 +05301871 /*
1872 * verify the cpu speed can be set within this limit, which might be
1873 * different to the first one
1874 */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301875 ret = cpufreq_driver->verify(new_policy);
Alan Sterne041c682006-03-27 01:16:30 -08001876 if (ret)
Linus Torvalds1da177e2005-04-16 15:20:36 -07001877 goto error_out;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001878
1879 /* notification of the new policy */
Alan Sterne041c682006-03-27 01:16:30 -08001880 blocking_notifier_call_chain(&cpufreq_policy_notifier_list,
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301881 CPUFREQ_NOTIFY, new_policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001882
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301883 policy->min = new_policy->min;
1884 policy->max = new_policy->max;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001885
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001886 pr_debug("new min and max freqs are %u - %u kHz\n",
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301887 policy->min, policy->max);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001888
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001889 if (cpufreq_driver->setpolicy) {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301890 policy->policy = new_policy->policy;
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001891 pr_debug("setting range\n");
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301892 ret = cpufreq_driver->setpolicy(new_policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001893 } else {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301894 if (new_policy->governor != policy->governor) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001895 /* save old, working values */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301896 struct cpufreq_governor *old_gov = policy->governor;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001897
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001898 pr_debug("governor switch\n");
Linus Torvalds1da177e2005-04-16 15:20:36 -07001899
1900 /* end old governor */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301901 if (policy->governor) {
1902 __cpufreq_governor(policy, CPUFREQ_GOV_STOP);
1903 unlock_policy_rwsem_write(new_policy->cpu);
1904 __cpufreq_governor(policy,
Viresh Kumar7bd353a2013-03-27 15:58:57 +00001905 CPUFREQ_GOV_POLICY_EXIT);
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301906 lock_policy_rwsem_write(new_policy->cpu);
Viresh Kumar7bd353a2013-03-27 15:58:57 +00001907 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001908
1909 /* start new governor */
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301910 policy->governor = new_policy->governor;
1911 if (!__cpufreq_governor(policy, CPUFREQ_GOV_POLICY_INIT)) {
1912 if (!__cpufreq_governor(policy, CPUFREQ_GOV_START)) {
Viresh Kumar7bd353a2013-03-27 15:58:57 +00001913 failed = 0;
Viresh Kumar955ef482013-05-16 05:09:58 +00001914 } else {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301915 unlock_policy_rwsem_write(new_policy->cpu);
1916 __cpufreq_governor(policy,
Viresh Kumar7bd353a2013-03-27 15:58:57 +00001917 CPUFREQ_GOV_POLICY_EXIT);
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301918 lock_policy_rwsem_write(new_policy->cpu);
Viresh Kumar955ef482013-05-16 05:09:58 +00001919 }
Viresh Kumar7bd353a2013-03-27 15:58:57 +00001920 }
1921
1922 if (failed) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07001923 /* new governor failed, so re-start old one */
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001924 pr_debug("starting governor %s failed\n",
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301925 policy->governor->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001926 if (old_gov) {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301927 policy->governor = old_gov;
1928 __cpufreq_governor(policy,
Viresh Kumar7bd353a2013-03-27 15:58:57 +00001929 CPUFREQ_GOV_POLICY_INIT);
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301930 __cpufreq_governor(policy,
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05301931 CPUFREQ_GOV_START);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001932 }
1933 ret = -EINVAL;
1934 goto error_out;
1935 }
1936 /* might be a policy change, too, so fall through */
1937 }
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001938 pr_debug("governor: change or update limits\n");
Viresh Kumar3de9bde2013-08-06 22:53:13 +05301939 ret = __cpufreq_governor(policy, CPUFREQ_GOV_LIMITS);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001940 }
1941
Dave Jones7d5e3502006-02-02 17:03:42 -05001942error_out:
Linus Torvalds1da177e2005-04-16 15:20:36 -07001943 return ret;
1944}
1945
1946/**
Linus Torvalds1da177e2005-04-16 15:20:36 -07001947 * cpufreq_update_policy - re-evaluate an existing cpufreq policy
1948 * @cpu: CPU which shall be re-evaluated
1949 *
Lucas De Marchi25985ed2011-03-30 22:57:33 -03001950 * Useful for policy notifiers which have different necessities
Linus Torvalds1da177e2005-04-16 15:20:36 -07001951 * at different times.
1952 */
1953int cpufreq_update_policy(unsigned int cpu)
1954{
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301955 struct cpufreq_policy *policy = cpufreq_cpu_get(cpu);
1956 struct cpufreq_policy new_policy;
Julia Lawallf1829e42008-07-25 22:44:53 +02001957 int ret;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001958
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301959 if (!policy) {
Julia Lawallf1829e42008-07-25 22:44:53 +02001960 ret = -ENODEV;
1961 goto no_policy;
1962 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001963
Julia Lawallf1829e42008-07-25 22:44:53 +02001964 if (unlikely(lock_policy_rwsem_write(cpu))) {
1965 ret = -EINVAL;
1966 goto fail;
1967 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07001968
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001969 pr_debug("updating policy for CPU %u\n", cpu);
Viresh Kumard5b73cd2013-08-06 22:53:06 +05301970 memcpy(&new_policy, policy, sizeof(*policy));
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301971 new_policy.min = policy->user_policy.min;
1972 new_policy.max = policy->user_policy.max;
1973 new_policy.policy = policy->user_policy.policy;
1974 new_policy.governor = policy->user_policy.governor;
Linus Torvalds1da177e2005-04-16 15:20:36 -07001975
Viresh Kumarbb176f72013-06-19 14:19:33 +05301976 /*
1977 * BIOS might change freq behind our back
1978 * -> ask driver for current freq and notify governors about a change
1979 */
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02001980 if (cpufreq_driver->get) {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301981 new_policy.cur = cpufreq_driver->get(cpu);
1982 if (!policy->cur) {
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02001983 pr_debug("Driver did not initialize current freq");
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301984 policy->cur = new_policy.cur;
Thomas Renningera85f7bd2006-02-01 11:36:04 +01001985 } else {
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301986 if (policy->cur != new_policy.cur && cpufreq_driver->target)
1987 cpufreq_out_of_sync(cpu, policy->cur,
1988 new_policy.cur);
Thomas Renningera85f7bd2006-02-01 11:36:04 +01001989 }
Thomas Renninger0961dd02006-01-26 18:46:33 +01001990 }
1991
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301992 ret = __cpufreq_set_policy(policy, &new_policy);
Linus Torvalds1da177e2005-04-16 15:20:36 -07001993
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08001994 unlock_policy_rwsem_write(cpu);
1995
Julia Lawallf1829e42008-07-25 22:44:53 +02001996fail:
Viresh Kumar3a3e9e02013-08-06 22:53:05 +05301997 cpufreq_cpu_put(policy);
Julia Lawallf1829e42008-07-25 22:44:53 +02001998no_policy:
Linus Torvalds1da177e2005-04-16 15:20:36 -07001999 return ret;
2000}
2001EXPORT_SYMBOL(cpufreq_update_policy);
2002
Paul Gortmaker27609842013-06-19 13:54:04 -04002003static int cpufreq_cpu_callback(struct notifier_block *nfb,
Ashok Rajc32b6b82005-10-30 14:59:54 -08002004 unsigned long action, void *hcpu)
2005{
2006 unsigned int cpu = (unsigned long)hcpu;
Kay Sievers8a25a2f2011-12-21 14:29:42 -08002007 struct device *dev;
Srivatsa S. Bhat5302c3f2013-07-30 04:25:25 +05302008 bool frozen = false;
Ashok Rajc32b6b82005-10-30 14:59:54 -08002009
Kay Sievers8a25a2f2011-12-21 14:29:42 -08002010 dev = get_cpu_device(cpu);
2011 if (dev) {
Srivatsa S. Bhat5302c3f2013-07-30 04:25:25 +05302012
2013 if (action & CPU_TASKS_FROZEN)
2014 frozen = true;
2015
2016 switch (action & ~CPU_TASKS_FROZEN) {
Ashok Rajc32b6b82005-10-30 14:59:54 -08002017 case CPU_ONLINE:
Srivatsa S. Bhat5302c3f2013-07-30 04:25:25 +05302018 __cpufreq_add_dev(dev, NULL, frozen);
Srivatsa S. Bhat23d328992013-07-30 04:23:56 +05302019 cpufreq_update_policy(cpu);
Ashok Rajc32b6b82005-10-30 14:59:54 -08002020 break;
Srivatsa S. Bhat5302c3f2013-07-30 04:25:25 +05302021
Ashok Rajc32b6b82005-10-30 14:59:54 -08002022 case CPU_DOWN_PREPARE:
Srivatsa S. Bhat5302c3f2013-07-30 04:25:25 +05302023 __cpufreq_remove_dev(dev, NULL, frozen);
Ashok Rajc32b6b82005-10-30 14:59:54 -08002024 break;
Srivatsa S. Bhat5302c3f2013-07-30 04:25:25 +05302025
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08002026 case CPU_DOWN_FAILED:
Srivatsa S. Bhat5302c3f2013-07-30 04:25:25 +05302027 __cpufreq_add_dev(dev, NULL, frozen);
Ashok Rajc32b6b82005-10-30 14:59:54 -08002028 break;
2029 }
2030 }
2031 return NOTIFY_OK;
2032}
2033
Neal Buckendahl9c36f742010-06-22 22:02:44 -05002034static struct notifier_block __refdata cpufreq_cpu_notifier = {
Viresh Kumarbb176f72013-06-19 14:19:33 +05302035 .notifier_call = cpufreq_cpu_callback,
Ashok Rajc32b6b82005-10-30 14:59:54 -08002036};
Linus Torvalds1da177e2005-04-16 15:20:36 -07002037
2038/*********************************************************************
2039 * REGISTER / UNREGISTER CPUFREQ DRIVER *
2040 *********************************************************************/
2041
2042/**
2043 * cpufreq_register_driver - register a CPU Frequency driver
2044 * @driver_data: A struct cpufreq_driver containing the values#
2045 * submitted by the CPU Frequency driver.
2046 *
Viresh Kumarbb176f72013-06-19 14:19:33 +05302047 * Registers a CPU Frequency driver to this core code. This code
Linus Torvalds1da177e2005-04-16 15:20:36 -07002048 * returns zero on success, -EBUSY when another driver got here first
Dave Jones32ee8c32006-02-28 00:43:23 -05002049 * (and isn't unregistered in the meantime).
Linus Torvalds1da177e2005-04-16 15:20:36 -07002050 *
2051 */
Linus Torvalds221dee22007-02-26 14:55:48 -08002052int cpufreq_register_driver(struct cpufreq_driver *driver_data)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002053{
2054 unsigned long flags;
2055 int ret;
2056
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -04002057 if (cpufreq_disabled())
2058 return -ENODEV;
2059
Linus Torvalds1da177e2005-04-16 15:20:36 -07002060 if (!driver_data || !driver_data->verify || !driver_data->init ||
2061 ((!driver_data->setpolicy) && (!driver_data->target)))
2062 return -EINVAL;
2063
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02002064 pr_debug("trying to register driver %s\n", driver_data->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002065
2066 if (driver_data->setpolicy)
2067 driver_data->flags |= CPUFREQ_CONST_LOOPS;
2068
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00002069 write_lock_irqsave(&cpufreq_driver_lock, flags);
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02002070 if (cpufreq_driver) {
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00002071 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002072 return -EBUSY;
2073 }
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02002074 cpufreq_driver = driver_data;
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00002075 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002076
Kay Sievers8a25a2f2011-12-21 14:29:42 -08002077 ret = subsys_interface_register(&cpufreq_interface);
Jiri Slaby8f5bc2a2011-03-01 17:41:10 +01002078 if (ret)
2079 goto err_null_driver;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002080
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02002081 if (!(cpufreq_driver->flags & CPUFREQ_STICKY)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002082 int i;
2083 ret = -ENODEV;
2084
2085 /* check for at least one working CPU */
Mike Travis7a6aedf2008-03-25 15:06:53 -07002086 for (i = 0; i < nr_cpu_ids; i++)
2087 if (cpu_possible(i) && per_cpu(cpufreq_cpu_data, i)) {
Linus Torvalds1da177e2005-04-16 15:20:36 -07002088 ret = 0;
Mike Travis7a6aedf2008-03-25 15:06:53 -07002089 break;
2090 }
Linus Torvalds1da177e2005-04-16 15:20:36 -07002091
2092 /* if all ->init() calls failed, unregister */
2093 if (ret) {
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02002094 pr_debug("no CPU initialized for driver %s\n",
Gautham R Shenoye08f5f52006-10-26 16:20:58 +05302095 driver_data->name);
Kay Sievers8a25a2f2011-12-21 14:29:42 -08002096 goto err_if_unreg;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002097 }
2098 }
2099
Jiri Slaby8f5bc2a2011-03-01 17:41:10 +01002100 register_hotcpu_notifier(&cpufreq_cpu_notifier);
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02002101 pr_debug("driver %s up and running\n", driver_data->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002102
Jiri Slaby8f5bc2a2011-03-01 17:41:10 +01002103 return 0;
Kay Sievers8a25a2f2011-12-21 14:29:42 -08002104err_if_unreg:
2105 subsys_interface_unregister(&cpufreq_interface);
Jiri Slaby8f5bc2a2011-03-01 17:41:10 +01002106err_null_driver:
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00002107 write_lock_irqsave(&cpufreq_driver_lock, flags);
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02002108 cpufreq_driver = NULL;
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00002109 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
Dave Jones4d34a672008-02-07 16:33:49 -05002110 return ret;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002111}
2112EXPORT_SYMBOL_GPL(cpufreq_register_driver);
2113
Linus Torvalds1da177e2005-04-16 15:20:36 -07002114/**
2115 * cpufreq_unregister_driver - unregister the current CPUFreq driver
2116 *
Viresh Kumarbb176f72013-06-19 14:19:33 +05302117 * Unregister the current CPUFreq driver. Only call this if you have
Linus Torvalds1da177e2005-04-16 15:20:36 -07002118 * the right to do so, i.e. if you have succeeded in initialising before!
2119 * Returns zero if successful, and -EINVAL if the cpufreq_driver is
2120 * currently not initialised.
2121 */
Linus Torvalds221dee22007-02-26 14:55:48 -08002122int cpufreq_unregister_driver(struct cpufreq_driver *driver)
Linus Torvalds1da177e2005-04-16 15:20:36 -07002123{
2124 unsigned long flags;
2125
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02002126 if (!cpufreq_driver || (driver != cpufreq_driver))
Linus Torvalds1da177e2005-04-16 15:20:36 -07002127 return -EINVAL;
Linus Torvalds1da177e2005-04-16 15:20:36 -07002128
Dominik Brodowski2d06d8c2011-03-27 15:04:46 +02002129 pr_debug("unregistering driver %s\n", driver->name);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002130
Kay Sievers8a25a2f2011-12-21 14:29:42 -08002131 subsys_interface_unregister(&cpufreq_interface);
Chandra Seetharaman65edc682006-06-27 02:54:08 -07002132 unregister_hotcpu_notifier(&cpufreq_cpu_notifier);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002133
Viresh Kumar6eed9402013-08-06 22:53:11 +05302134 down_write(&cpufreq_rwsem);
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00002135 write_lock_irqsave(&cpufreq_driver_lock, flags);
Viresh Kumar6eed9402013-08-06 22:53:11 +05302136
Rafael J. Wysocki1c3d85d2013-04-29 00:08:16 +02002137 cpufreq_driver = NULL;
Viresh Kumar6eed9402013-08-06 22:53:11 +05302138
Nathan Zimmer0d1857a2013-02-22 16:24:34 +00002139 write_unlock_irqrestore(&cpufreq_driver_lock, flags);
Viresh Kumar6eed9402013-08-06 22:53:11 +05302140 up_write(&cpufreq_rwsem);
Linus Torvalds1da177e2005-04-16 15:20:36 -07002141
2142 return 0;
2143}
2144EXPORT_SYMBOL_GPL(cpufreq_unregister_driver);
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08002145
2146static int __init cpufreq_core_init(void)
2147{
2148 int cpu;
2149
Konrad Rzeszutek Wilka7b422c2012-03-13 19:18:39 -04002150 if (cpufreq_disabled())
2151 return -ENODEV;
2152
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08002153 for_each_possible_cpu(cpu) {
Tejun Heof1625062009-10-29 22:34:13 +09002154 per_cpu(cpufreq_policy_cpu, cpu) = -1;
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08002155 init_rwsem(&per_cpu(cpu_policy_rwsem, cpu));
2156 }
Thomas Renninger8aa84ad2009-07-24 15:25:05 +02002157
Viresh Kumar2361be22013-05-17 16:09:09 +05302158 cpufreq_global_kobject = kobject_create();
Thomas Renninger8aa84ad2009-07-24 15:25:05 +02002159 BUG_ON(!cpufreq_global_kobject);
Rafael J. Wysockie00e56d2011-03-23 22:16:32 +01002160 register_syscore_ops(&cpufreq_syscore_ops);
Thomas Renninger8aa84ad2009-07-24 15:25:05 +02002161
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08002162 return 0;
2163}
Venkatesh Pallipadi5a01f2e2007-02-05 16:12:44 -08002164core_initcall(cpufreq_core_init);