Lines Matching +full:opp +full:- +full:suspend
1 // SPDX-License-Identifier: GPL-2.0-only
25 #include "cpufreq-dt.h"
44 if (cpumask_test_cpu(cpu, priv->cpus)) in cpufreq_dt_find_data()
53 struct private_data *priv = policy->driver_data; in set_target()
54 unsigned long freq = policy->freq_table[index].frequency; in set_target()
56 return dev_pm_opp_set_rate(priv->cpu_dev, freq * 1000); in set_target()
60 * An earlier version of opp-v1 bindings used to name the regulator
61 * "cpu0-supply", we still need to handle that for backwards compatibility.
65 struct device_node *np __free(device_node) = of_node_get(dev->of_node); in find_supply_name()
66 int cpu = dev->id; in find_supply_name()
73 if (!cpu && of_property_present(np, "cpu0-supply")) in find_supply_name()
76 if (of_property_present(np, "cpu-supply")) in find_supply_name()
91 priv = cpufreq_dt_find_data(policy->cpu); in cpufreq_init()
93 pr_err("failed to find data for cpu%d\n", policy->cpu); in cpufreq_init()
94 return -ENODEV; in cpufreq_init()
96 cpu_dev = priv->cpu_dev; in cpufreq_init()
109 cpumask_copy(policy->cpus, priv->cpus); in cpufreq_init()
110 policy->driver_data = priv; in cpufreq_init()
111 policy->clk = cpu_clk; in cpufreq_init()
112 policy->freq_table = priv->freq_table; in cpufreq_init()
113 policy->suspend_freq = dev_pm_opp_get_suspend_opp_freq(cpu_dev) / 1000; in cpufreq_init()
114 policy->cpuinfo.transition_latency = transition_latency; in cpufreq_init()
115 policy->dvfs_possible_from_any_cpu = true; in cpufreq_init()
122 /* We did light-weight tear down earlier, nothing to do here */ in cpufreq_online()
129 * Preserve policy->driver_data and don't free resources on light-weight in cpufreq_offline()
137 clk_put(policy->clk); in cpufreq_exit()
151 .name = "cpufreq-dt",
153 .suspend = cpufreq_generic_suspend,
170 return -EPROBE_DEFER; in dt_cpufreq_early_init()
174 return -ENOMEM; in dt_cpufreq_early_init()
176 if (!zalloc_cpumask_var(&priv->cpus, GFP_KERNEL)) in dt_cpufreq_early_init()
177 return -ENOMEM; in dt_cpufreq_early_init()
179 cpumask_set_cpu(cpu, priv->cpus); in dt_cpufreq_early_init()
180 priv->cpu_dev = cpu_dev; in dt_cpufreq_early_init()
183 * OPP layer will be taking care of regulators now, but it needs to know in dt_cpufreq_early_init()
188 priv->opp_token = dev_pm_opp_set_regulators(cpu_dev, reg_name); in dt_cpufreq_early_init()
189 if (priv->opp_token < 0) { in dt_cpufreq_early_init()
190 ret = dev_err_probe(cpu_dev, priv->opp_token, in dt_cpufreq_early_init()
196 /* Get OPP-sharing information from "operating-points-v2" bindings */ in dt_cpufreq_early_init()
197 ret = dev_pm_opp_of_get_sharing_cpus(cpu_dev, priv->cpus); in dt_cpufreq_early_init()
199 if (ret != -ENOENT) in dt_cpufreq_early_init()
203 * operating-points-v2 not supported, fallback to all CPUs share in dt_cpufreq_early_init()
204 * OPP for backward compatibility if the platform hasn't set in dt_cpufreq_early_init()
207 if (dev_pm_opp_get_sharing_cpus(cpu_dev, priv->cpus)) in dt_cpufreq_early_init()
212 * Initialize OPP tables for all priv->cpus. They will be shared by in dt_cpufreq_early_init()
213 * all CPUs which have marked their CPUs shared with OPP bindings. in dt_cpufreq_early_init()
215 * For platforms not using operating-points-v2 bindings, we do this in dt_cpufreq_early_init()
216 * before updating priv->cpus. Otherwise, we will end up creating in dt_cpufreq_early_init()
220 * it is -EPROBE_DEFER. in dt_cpufreq_early_init()
222 ret = dev_pm_opp_of_cpumask_add_table(priv->cpus); in dt_cpufreq_early_init()
224 priv->have_static_opps = true; in dt_cpufreq_early_init()
225 } else if (ret == -EPROBE_DEFER) { in dt_cpufreq_early_init()
230 * The OPP table must be initialized, statically or dynamically, by this in dt_cpufreq_early_init()
235 dev_err(cpu_dev, "OPP table can't be empty\n"); in dt_cpufreq_early_init()
236 ret = -ENODEV; in dt_cpufreq_early_init()
241 cpumask_setall(priv->cpus); in dt_cpufreq_early_init()
242 ret = dev_pm_opp_set_sharing_cpus(cpu_dev, priv->cpus); in dt_cpufreq_early_init()
248 ret = dev_pm_opp_init_cpufreq_table(cpu_dev, &priv->freq_table); in dt_cpufreq_early_init()
254 list_add(&priv->node, &priv_list); in dt_cpufreq_early_init()
258 if (priv->have_static_opps) in dt_cpufreq_early_init()
259 dev_pm_opp_of_cpumask_remove_table(priv->cpus); in dt_cpufreq_early_init()
260 dev_pm_opp_put_regulators(priv->opp_token); in dt_cpufreq_early_init()
262 free_cpumask_var(priv->cpus); in dt_cpufreq_early_init()
271 dev_pm_opp_free_cpufreq_table(priv->cpu_dev, &priv->freq_table); in dt_cpufreq_release()
272 if (priv->have_static_opps) in dt_cpufreq_release()
273 dev_pm_opp_of_cpumask_remove_table(priv->cpus); in dt_cpufreq_release()
274 dev_pm_opp_put_regulators(priv->opp_token); in dt_cpufreq_release()
275 free_cpumask_var(priv->cpus); in dt_cpufreq_release()
276 list_del(&priv->node); in dt_cpufreq_release()
282 struct cpufreq_dt_platform_data *data = dev_get_platdata(&pdev->dev); in dt_cpufreq_probe()
285 /* Request resources early so we can return in case of -EPROBE_DEFER */ in dt_cpufreq_probe()
287 ret = dt_cpufreq_early_init(&pdev->dev, cpu); in dt_cpufreq_probe()
293 if (data->have_governor_per_policy) in dt_cpufreq_probe()
296 dt_cpufreq_driver.resume = data->resume; in dt_cpufreq_probe()
297 if (data->suspend) in dt_cpufreq_probe()
298 dt_cpufreq_driver.suspend = data->suspend; in dt_cpufreq_probe()
299 if (data->get_intermediate) { in dt_cpufreq_probe()
300 dt_cpufreq_driver.target_intermediate = data->target_intermediate; in dt_cpufreq_probe()
301 dt_cpufreq_driver.get_intermediate = data->get_intermediate; in dt_cpufreq_probe()
307 dev_err(&pdev->dev, "failed register driver: %d\n", ret); in dt_cpufreq_probe()
325 .name = "cpufreq-dt",
336 cpufreq_dt_devinfo.name = "cpufreq-dt"; in cpufreq_dt_pdev_register()
343 MODULE_ALIAS("platform:cpufreq-dt");