Search
SailfishOS Open Build Service
>
Projects
>
home:sledge
:
beagle
>
kernel-adaptation-dm3730
> 0023-fixed-DSP-clock-frequency.patch
Log In
Username
Password
Cancel
Overview
Repositories
Revisions
Requests
Users
Advanced
Attributes
Meta
File 0023-fixed-DSP-clock-frequency.patch of Package kernel-adaptation-dm3730
From fe1d8980b8cc5c2add3190af3d0d43db32d157bd Mon Sep 17 00:00:00 2001 From: MediStream-Devel-VM <info@berlinux-solutions.de> Date: Mon, 18 Mar 2013 10:32:08 +0100 Subject: [PATCH] -fixed DSP clock frequency --- drivers/cpufreq/omap-cpufreq.c | 112 +++++++++++++++++++++++++++++++++++---- 1 files changed, 100 insertions(+), 12 deletions(-) diff --git a/drivers/cpufreq/omap-cpufreq.c b/drivers/cpufreq/omap-cpufreq.c index 17fa04d..ad7f7d9 100644 --- a/drivers/cpufreq/omap-cpufreq.c +++ b/drivers/cpufreq/omap-cpufreq.c @@ -50,11 +50,11 @@ static DEFINE_PER_CPU(struct lpj_info, lpj_ref); static struct lpj_info global_lpj_ref; #endif -static struct cpufreq_frequency_table *freq_table; +static struct cpufreq_frequency_table *freq_table, *iva_freq_table; static atomic_t freq_table_users = ATOMIC_INIT(0); -static struct clk *mpu_clk; -static char *mpu_clk_name; -static struct device *mpu_dev; +static struct clk *mpu_clk, *iva_clk; +static char *mpu_clk_name, *iva_clk_name; +static struct device *mpu_dev, *iva_dev; static struct regulator *mpu_reg; static int omap_verify_speed(struct cpufreq_policy *policy) @@ -79,7 +79,7 @@ static int omap_target(struct cpufreq_policy *policy, unsigned int target_freq, unsigned int relation) { - unsigned int i; + unsigned int i, opp_index; int r, ret = 0; struct cpufreq_freqs freqs; struct opp *opp; @@ -92,13 +92,13 @@ static int omap_target(struct cpufreq_policy *policy, } ret = cpufreq_frequency_table_target(policy, freq_table, target_freq, - relation, &i); + relation, &opp_index); if (ret) { dev_dbg(mpu_dev, "%s: cpu%d: no freq match for %d(ret=%d)\n", __func__, policy->cpu, target_freq, ret); return ret; } - freqs.new = freq_table[i].frequency; + freqs.new = freq_table[opp_index].frequency; if (!freqs.new) { dev_err(mpu_dev, "%s: cpu%d: no match for freq %d\n", __func__, policy->cpu, target_freq); @@ -161,6 +161,18 @@ static int omap_target(struct cpufreq_policy *policy, } freqs.new = omap_getspeed(policy->cpu); + + if (!ret && iva_freq_table && iva_clk) { + const unsigned long iva_rate = + iva_freq_table[opp_index].frequency*1000; + dev_warn(mpu_dev, "set IVA rate to: %d\n", iva_rate); + ret = clk_set_rate(iva_clk, iva_rate); + if (ret) { + pr_err("%s: failed to set %s rate %lu[%d]\n", + __func__, iva_clk->name, iva_rate, ret); + } + } + #ifdef CONFIG_SMP /* * Note that loops_per_jiffy is not updated on SMP systems in @@ -199,8 +211,70 @@ done: static inline void freq_table_free(void) { - if (atomic_dec_and_test(&freq_table_users)) + if (atomic_dec_and_test(&freq_table_users)) { opp_free_cpufreq_table(mpu_dev, &freq_table); + opp_free_cpufreq_table(iva_dev, &iva_freq_table); + } +} + +static inline void clk_free(void) +{ + if (mpu_clk) { + clk_put(mpu_clk); + mpu_clk = NULL; + } + if (iva_clk) { + clk_put(iva_clk); + iva_clk = NULL; + } +} + +static int __cpuinit omap_iva_init(struct cpufreq_policy *policy) +{ + int result; + unsigned long iva_rate; + unsigned int opp_index, mpu_freq = omap_getspeed(policy->cpu); + + if (!iva_clk_name) { + pr_info("%s: iva unavailable\n", __func__); + return 0; + } + iva_dev = omap_device_get_by_hwmod_name("iva"); + if (!iva_dev) { + pr_err("%s: unable to get the iva device\n", __func__); + return -EINVAL; + } + iva_clk = clk_get(NULL, iva_clk_name); + if (IS_ERR(iva_clk)) { + dev_err(iva_dev, "%s: cpu%d: %s clock unavailable\n", + __func__, policy->cpu, iva_clk_name); + return PTR_ERR(iva_clk); + } + result = opp_init_cpufreq_table(iva_dev, &iva_freq_table); + if (result) { + dev_err(iva_dev, "%s: cpu%d: failed creating freq table[%d]\n", + __func__, policy->cpu, result); + return result; + } + + result = cpufreq_frequency_table_target(policy, freq_table, mpu_freq, + CPUFREQ_RELATION_L, &opp_index); + if (result) { + dev_err(mpu_dev, "%s: cpu%d: no freq match for %u[%d]\n", + __func__, policy->cpu, mpu_freq, result); + return result; + } + iva_rate = iva_freq_table[opp_index].frequency*1000; + dev_err(mpu_dev, "set IVA rate to: %d\n", iva_rate); + result = clk_set_rate(iva_clk, iva_rate); + if (result) { + pr_err("%s: cpu%d: failed to set %s rate %lu[%d]\n", + __func__, policy->cpu, iva_clk->name, iva_rate, + result); + return result; + } + + return 0; } static int __cpuinit omap_cpu_init(struct cpufreq_policy *policy) @@ -218,8 +292,20 @@ static int __cpuinit omap_cpu_init(struct cpufreq_policy *policy) policy->cur = policy->min = policy->max = omap_getspeed(policy->cpu); - if (atomic_inc_return(&freq_table_users) == 1) + if (atomic_inc_return(&freq_table_users) == 1) { result = opp_init_cpufreq_table(mpu_dev, &freq_table); + if (result) { + dev_err(mpu_dev, "%s: cpu%d: failed creating freq table[%d]\n", + __func__, policy->cpu, result); + goto fail_ck; + } + result = omap_iva_init(policy); + if (result) { + pr_err("%s: cpu%d: failed to initialize iva[%d]\n", + __func__, policy->cpu, result); + goto fail_table; + } + } if (result) { dev_err(mpu_dev, "%s: cpu%d: failed creating freq table[%d]\n", @@ -257,14 +343,14 @@ static int __cpuinit omap_cpu_init(struct cpufreq_policy *policy) fail_table: freq_table_free(); fail_ck: - clk_put(mpu_clk); + clk_free(); return result; } static int omap_cpu_exit(struct cpufreq_policy *policy) { freq_table_free(); - clk_put(mpu_clk); + clk_free(); return 0; } @@ -288,8 +374,10 @@ static int __init omap_cpufreq_init(void) { if (cpu_is_omap24xx()) mpu_clk_name = "virt_prcm_set"; - else if (cpu_is_omap34xx()) + else if (cpu_is_omap34xx()) { mpu_clk_name = "dpll1_ck"; + iva_clk_name = "dpll2_ck"; + } else if (cpu_is_omap44xx()) mpu_clk_name = "dpll_mpu_ck"; -- 1.7.5.4