MMP3: QSEVEN adding qos and inactivity timer for GC port from Q7 BetaRC patch 5997 Signed-off-by: dipen <dpatel@marvell.com> Signed-off-by: frankf <frankf@marvell.com> (cherry picked from commit accc5f8da4cd6f5c8da6791f650635719ad6e128) Signed-off-by: Wen-chien Jesse Sung <jesse.sung@canonical.com>
diff --git a/arch/arm/mach-mmp/clock-mmp3.c b/arch/arm/mach-mmp/clock-mmp3.c index 67db843..14af35a 100644 --- a/arch/arm/mach-mmp/clock-mmp3.c +++ b/arch/arm/mach-mmp/clock-mmp3.c
@@ -30,6 +30,7 @@ #include <plat/devfreq.h> #include <linux/reboot.h> #include "common.h" +#include <linux/pm_qos_params.h> #define CORE_NUM 3 #define PMUA_CC APMU_REG(0x4) @@ -1153,6 +1154,15 @@ __raw_writel(tmp, clk->clk_rst);\ } +struct pm_qos_request_list gc_qos_ddrfreq_min; +static struct timer_list gc_idle_timer; +static bool gc_force_high_rate = false; +static void gc_set_constraint(unsigned long data) +{ + gc_force_high_rate = true; + pm_qos_update_request(&gc_qos_ddrfreq_min, PM_QOS_DEFAULT_VALUE); +} + static void gc_clk_init(struct clk *clk) { clk->rate = clk_get_rate(&mmp3_clk_pll1_clkoutp) / 2; @@ -1160,8 +1170,67 @@ clk->div = 2; clk->mul = 1; clk_reparent(clk, &mmp3_clk_pll1_clkoutp); + init_timer(&gc_idle_timer); + gc_idle_timer.function = gc_set_constraint; + gc_idle_timer.data = 1; + gc_idle_timer.expires = 1000 + jiffies; + gc_force_high_rate = true; + pm_qos_add_request(&gc_qos_ddrfreq_min, PM_QOS_DDR_DEVFREQ_MIN, + PM_QOS_DEFAULT_VALUE); } +static int gc_clk_setrate(struct clk *clk, unsigned long rate) +{ + unsigned long rate1 = rate; + if (gc_force_high_rate == true) + rate1 = 533333333; + + clk->mul = 1; + if (rate1 == clk_get_rate(&mmp3_clk_pll1)/8) { + clk->enable_val = PLL1D6; + clk->div = 8; + clk_reparent(clk, &mmp3_clk_pll1); + } else if (rate1 == clk_get_rate(&mmp3_clk_pll1)/4) { + clk->enable_val = PLL1D4; + clk->div = 4; + clk_reparent(clk, &mmp3_clk_pll1); + } else if (rate1 == clk_get_rate(&mmp3_clk_pll1_clkoutp)/3) { + clk->enable_val = PLL1D2; + clk->div = 3; + clk_reparent(clk, &mmp3_clk_pll1_clkoutp); + } else if (rate1 == clk_get_rate(&mmp3_clk_pll1)/2) { + clk->enable_val = PLL1D2; + clk->div = 2; + clk_reparent(clk, &mmp3_clk_pll1); + } else if (rate1 == clk_get_rate(&mmp3_clk_pll2_clkoutp)/2) { + clk->enable_val = PLL1D2; + clk->div = 2; + clk_reparent(clk, &mmp3_clk_pll2_clkoutp); + } else if (rate1 == clk_get_rate(&mmp3_clk_pll1_clkoutp)/2) { + clk->enable_val = PLL1D2; + clk->div = 2; + clk_reparent(clk, &mmp3_clk_pll1_clkoutp); + } else if (rate1 == clk_get_rate(&mmp3_clk_pll2)/2) { + clk->enable_val = PLL2D2; + clk->div = 2; + clk_reparent(clk, &mmp3_clk_pll2); + } else if (rate1 == clk_get_rate(&mmp3_clk_pll1)) { + clk->enable_val = PLL1D2; + clk->div = 1; + clk_reparent(clk, &mmp3_clk_pll1); + } else { + pr_err("%s: unexpected gc clock rate %ld\n", __func__, rate1); + BUG(); + } + + return 0; +} + + + + + + static int gc_clk_enable(struct clk *clk) { unsigned long gc_rate_cfg; @@ -1171,6 +1240,13 @@ * different gc clock rate. */ + pm_qos_update_request(&gc_qos_ddrfreq_min, DDR_CONSTRAINT_LVL1); + + if (gc_force_high_rate == true) + gc_clk_setrate(clk, 533333333); + del_timer(&gc_idle_timer); + gc_force_high_rate = false; + i = 0; while ((clk->inputs[i].input != clk->parent) && clk->inputs[i].input) i++; @@ -1195,6 +1271,13 @@ { GC_SET_BITS(0, GC2D_AXICLK_EN | GC3D_AXICLK_EN | GC2D3D_CLK_EN\ | GC2D_CLK_EN); + gc_idle_timer.expires = 1000 + jiffies; + add_timer(&gc_idle_timer); +/* ++ GC_SET_BITS(0,GC2D3D_CLK_EN | GC2D_CLK_EN); ++ GC_SET_BITS(0, GC2D_AXICLK_EN | GC3D_AXICLK_EN); +*/ + } static long gc_clk_round_rate(struct clk *clk, unsigned long rate) @@ -1217,6 +1300,8 @@ return clk_get_rate(&mmp3_clk_pll1); /* 800M */ } + +/* static int gc_clk_setrate(struct clk *clk, unsigned long rate) { clk->mul = 1; @@ -1259,6 +1344,7 @@ return 0; } +*/ int get_gcu_freqs_table(unsigned long *gcu_freqs_table, unsigned int *item_counts, unsigned int max_item_counts)