mirror of
https://xff.cz/git/u-boot/
synced 2025-09-01 16:52:14 +02:00
mpc85xx/t104x: Add deep sleep framework support
When T104x soc wakes up from deep sleep, control is passed to the primary core that starts executing uboot. After re-initialized some IP blocks, like DDRC, kernel will take responsibility to continue to restore environment it leaves before. Signed-off-by: Tang Yuantian <Yuantian.Tang@freescale.com> Reviewed-by: York Sun <yorksun@freescale.com>
This commit is contained in:
@@ -15,6 +15,7 @@
|
||||
#error Invalid setting for CONFIG_CHIP_SELECTS_PER_CTRL
|
||||
#endif
|
||||
|
||||
DECLARE_GLOBAL_DATA_PTR;
|
||||
|
||||
/*
|
||||
* regs has the to-be-set values for DDR controller registers
|
||||
@@ -43,6 +44,16 @@ void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs,
|
||||
u32 save1, save2;
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_DEEP_SLEEP
|
||||
const ccsr_gur_t *gur = (void __iomem *)(CONFIG_SYS_MPC85xx_GUTS_ADDR);
|
||||
bool sleep_flag = 0;
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_DEEP_SLEEP
|
||||
if (in_be32(&gur->scrtsr[0]) & (1 << 3))
|
||||
sleep_flag = 1;
|
||||
#endif
|
||||
|
||||
switch (ctrl_num) {
|
||||
case 0:
|
||||
ddr = (void *)CONFIG_SYS_FSL_DDR_ADDR;
|
||||
@@ -119,7 +130,13 @@ void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs,
|
||||
out_be32(&ddr->timing_cfg_0, regs->timing_cfg_0);
|
||||
out_be32(&ddr->timing_cfg_1, regs->timing_cfg_1);
|
||||
out_be32(&ddr->timing_cfg_2, regs->timing_cfg_2);
|
||||
out_be32(&ddr->sdram_cfg_2, regs->ddr_sdram_cfg_2);
|
||||
#ifdef CONFIG_DEEP_SLEEP
|
||||
if (sleep_flag)
|
||||
out_be32(&ddr->sdram_cfg_2,
|
||||
regs->ddr_sdram_cfg_2 & ~SDRAM_CFG2_D_INIT);
|
||||
else
|
||||
#endif
|
||||
out_be32(&ddr->sdram_cfg_2, regs->ddr_sdram_cfg_2);
|
||||
out_be32(&ddr->sdram_mode, regs->ddr_sdram_mode);
|
||||
out_be32(&ddr->sdram_mode_2, regs->ddr_sdram_mode_2);
|
||||
out_be32(&ddr->sdram_mode_3, regs->ddr_sdram_mode_3);
|
||||
@@ -132,8 +149,16 @@ void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs,
|
||||
out_be32(&ddr->sdram_interval, regs->ddr_sdram_interval);
|
||||
out_be32(&ddr->sdram_data_init, regs->ddr_data_init);
|
||||
out_be32(&ddr->sdram_clk_cntl, regs->ddr_sdram_clk_cntl);
|
||||
out_be32(&ddr->init_addr, regs->ddr_init_addr);
|
||||
out_be32(&ddr->init_ext_addr, regs->ddr_init_ext_addr);
|
||||
#ifdef CONFIG_DEEP_SLEEP
|
||||
if (sleep_flag) {
|
||||
out_be32(&ddr->init_addr, 0);
|
||||
out_be32(&ddr->init_ext_addr, (1 << 31));
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
out_be32(&ddr->init_addr, regs->ddr_init_addr);
|
||||
out_be32(&ddr->init_ext_addr, regs->ddr_init_ext_addr);
|
||||
}
|
||||
|
||||
out_be32(&ddr->timing_cfg_4, regs->timing_cfg_4);
|
||||
out_be32(&ddr->timing_cfg_5, regs->timing_cfg_5);
|
||||
@@ -374,8 +399,22 @@ step2:
|
||||
udelay(500);
|
||||
asm volatile("sync;isync");
|
||||
|
||||
#ifdef CONFIG_DEEP_SLEEP
|
||||
if (sleep_flag) {
|
||||
/* enter self-refresh */
|
||||
setbits_be32(&ddr->sdram_cfg_2, (1 << 31));
|
||||
/* do board specific memory setup */
|
||||
board_mem_sleep_setup();
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Let the controller go */
|
||||
temp_sdram_cfg = in_be32(&ddr->sdram_cfg) & ~SDRAM_CFG_BI;
|
||||
#ifdef CONFIG_DEEP_SLEEP
|
||||
if (sleep_flag)
|
||||
temp_sdram_cfg = (in_be32(&ddr->sdram_cfg) | SDRAM_CFG_BI);
|
||||
else
|
||||
#endif
|
||||
temp_sdram_cfg = (in_be32(&ddr->sdram_cfg) & ~SDRAM_CFG_BI);
|
||||
out_be32(&ddr->sdram_cfg, temp_sdram_cfg | SDRAM_CFG_MEM_EN);
|
||||
asm volatile("sync;isync");
|
||||
|
||||
@@ -526,4 +565,9 @@ step2:
|
||||
clrbits_be32(&ddr->sdram_cfg, 0x2);
|
||||
}
|
||||
#endif /* CONFIG_SYS_FSL_ERRATUM_DDR111_DDR134 */
|
||||
#ifdef CONFIG_DEEP_SLEEP
|
||||
if (sleep_flag)
|
||||
/* exit self-refresh */
|
||||
clrbits_be32(&ddr->sdram_cfg_2, (1 << 31));
|
||||
#endif
|
||||
}
|
||||
|
Reference in New Issue
Block a user