[PATCH v5 3/6] clk: rockchip: RK3288: add suspend and resume
Doug Anderson
dianders at chromium.org
Mon Oct 27 20:31:36 PDT 2014
Chris,
On Mon, Oct 27, 2014 at 8:15 PM, Chris Zhong <zyw at rock-chips.com> wrote:
>
> On 10/28/2014 01:27 AM, Doug Anderson wrote:
>
> Chris,
>
> On Mon, Oct 27, 2014 at 6:47 AM, Chris Zhong <zyw at rock-chips.com> wrote:
>
> save and restore some clks, which might be changed in suspend.
>
> Signed-off-by: Tony Xie <xxx at rock-chips.com>
> Signed-off-by: Chris Zhong <zyw at rock-chips.com>
>
> ---
>
> Changes in v5:
> - modify comments
>
> Changes in v4: None
> Changes in v3: None
> Changes in v2:
> - __raw_readl/__raw_writel replaced by readl_relaxed/writel_relaxed
>
> drivers/clk/rockchip/clk-rk3288.c | 60
> +++++++++++++++++++++++++++++++++++++
> 1 file changed, 60 insertions(+)
>
> diff --git a/drivers/clk/rockchip/clk-rk3288.c
> b/drivers/clk/rockchip/clk-rk3288.c
> index 2327829..94da06c 100644
> --- a/drivers/clk/rockchip/clk-rk3288.c
> +++ b/drivers/clk/rockchip/clk-rk3288.c
> @@ -16,6 +16,7 @@
> #include <linux/clk-provider.h>
> #include <linux/of.h>
> #include <linux/of_address.h>
> +#include <linux/syscore_ops.h>
> #include <dt-bindings/clock/rk3288-cru.h>
> #include "clk.h"
>
> @@ -762,6 +763,64 @@ static const char *rk3288_critical_clocks[] __initconst
> = {
> "hclk_peri",
> };
>
> +#ifdef CONFIG_PM_SLEEP
> +static void __iomem *rk3288_cru_base;
> +static const int rk3288_saved_cru_reg_ids[] = {
> + RK3288_MODE_CON,
> + RK3288_CLKSEL_CON(0),
> + RK3288_CLKSEL_CON(1),
> + RK3288_CLKSEL_CON(10),
> + RK3288_CLKSEL_CON(33),
> + RK3288_CLKSEL_CON(37),
> +};
>
> I still haven't had time to figure out exactly why these registers and
> not others...
>
> ...but I think that the code here looks reasonable and I have verified
> that saving at least some of these registers does matter. I'd vote to
> land these and if we have to add/remove registers later we can do it.
> Thus:
>
> Reviewed-by: Doug Anderson <dianders at chromium.org>
> Tested-by: Doug Anderson <dianders at chromium.org>
>
>
> These CLKSEL registers would be changed in maskrom. so we need save and
> restore them.
>
> code in maskrom :
> ...
> cruReg->CRU_CLKSEL_CON[0] = (0x9fff<<16)
> | (0x0<<15) // CORE select ARM PLL
> | (0x0<<8) // core div
> | (0x0<<4) // aclk_core_mp_div
> | (0x0); // aclk_core_m0_dive
> cruReg->CRU_CLKSEL_CON[1] = (0xf3ff<<16)
> | (1<<15) // bus_aclk_pll_sel= GPLL
> | (0x0<<12) // pd_bus_pclk_div
> | (0x0<<8) // pd_bus_hclk_div=1:1
> | (0x0<<3) // pd_bus_aclk_div
> | (0x0); // pd_bus_clk_div
> cruReg->CRU_CLKSEL_CON[10] = (((0x1<<15)|(0x3<<12)|(0x3<<8)|(0x1f))<<16)
> | (0x1<<15) // peri_pll_sel = GPLL
> | (0x0<<12) // aclk_periph:pclk_periph = 1:1
> | (0x0<<8) // aclk_periph:hclk_periph = 1:1
> | (0x0); // GPLL:aclk_periph = 1:1
> cruReg->CRU_CLKSEL_CON[33] = (((0x1f<<8)|(0x1f))<<16)
> | (0x0<<8) // alive_pclk
> | (0x0); // pmu_pclk
> cruReg->CRU_CLKSEL_CON[37] = (((0x1f<<9)|(0x1f<<4)|(0x7))<<16)
> | (0<<9) //pclk_core_dbg
> | (0x0<<4) // atclk_core
> | (0x0); // clk_l2ram
> ...
OK, now it makes sense! When I read:
+ * Cru will be reset in maskrom when system wake up from fastboot.
+ * The apll/cpll/gpll will be set into slow mode in maskrom.
+ * So save them before suspend, restore them after resume.
I thought that all of the CRU was being reset. ...but it's only some
registers. I guess I would have expected:
+ * Some CRU registers will be reset in maskrom when the system
+ * wakes up from fastboot.
+ * So save them before suspend, restore them after resume.
When you go into deep sleep do we need to save and restore more of the
registers? I think your current patch series can only want up from
the very lightest sleep mode, right?
More information about the Linux-rockchip
mailing list