From a994b3deb00bf3177cdf9f92060baec4f640f466 Mon Sep 17 00:00:00 2001 From: Shengzhou Liu Date: Wed, 16 Dec 2015 16:45:41 +0800 Subject: [PATCH] driver/ddr/fsl: Add workaround for A009663 Erratum A-009663 workaround requires to set DDR_INTERVAL[BSTOPRE] to 0 before setting DDR_SDRAM_CFG[MEM_EN] and set DDR_INTERVAL[BSTOPRE] to the desired value after DDR initialization has completed. When DDR controller is configured to operate in auto-precharge mode(DDR_INTERVAL[BSTOPRE]=0), this workaround is not needed. Signed-off-by: Shengzhou Liu Reviewed-by: York Sun --- arch/arm/include/asm/arch-fsl-layerscape/config.h | 3 +++ arch/arm/include/asm/arch-ls102xa/config.h | 1 + arch/powerpc/cpu/mpc85xx/cmd_errata.c | 3 +++ arch/powerpc/include/asm/config_mpc85xx.h | 2 ++ drivers/ddr/fsl/fsl_ddr_gen4.c | 10 ++++++++++ include/fsl_ddr_sdram.h | 1 + 6 files changed, 20 insertions(+) diff --git a/arch/arm/include/asm/arch-fsl-layerscape/config.h b/arch/arm/include/asm/arch-fsl-layerscape/config.h index 83a207c308..f1b164fd6a 100644 --- a/arch/arm/include/asm/arch-fsl-layerscape/config.h +++ b/arch/arm/include/asm/arch-fsl-layerscape/config.h @@ -118,7 +118,9 @@ #define CONFIG_SYS_FSL_ERRATUM_A008585 #define CONFIG_SYS_FSL_ERRATUM_A008751 #define CONFIG_SYS_FSL_ERRATUM_A009635 +#define CONFIG_SYS_FSL_ERRATUM_A009663 #define CONFIG_SYS_FSL_ERRATUM_A009942 + #elif defined(CONFIG_LS1043A) #define CONFIG_MAX_CPUS 4 #define CONFIG_SYS_CACHELINE_SIZE 64 @@ -167,6 +169,7 @@ #define GICD_BASE 0x01401000 #define GICC_BASE 0x01402000 +#define CONFIG_SYS_FSL_ERRATUM_A009663 #define CONFIG_SYS_FSL_ERRATUM_A009929 #else #error SoC not defined diff --git a/arch/arm/include/asm/arch-ls102xa/config.h b/arch/arm/include/asm/arch-ls102xa/config.h index f066480c0c..424fe879dd 100644 --- a/arch/arm/include/asm/arch-ls102xa/config.h +++ b/arch/arm/include/asm/arch-ls102xa/config.h @@ -131,6 +131,7 @@ #define CONFIG_SYS_FSL_SEC_COMPAT 5 #define CONFIG_USB_MAX_CONTROLLER_COUNT 1 #define CONFIG_SYS_FSL_ERRATUM_A008378 +#define CONFIG_SYS_FSL_ERRATUM_A009663 #else #error SoC not defined #endif diff --git a/arch/powerpc/cpu/mpc85xx/cmd_errata.c b/arch/powerpc/cpu/mpc85xx/cmd_errata.c index a4935567f6..3b06ae42e4 100644 --- a/arch/powerpc/cpu/mpc85xx/cmd_errata.c +++ b/arch/powerpc/cpu/mpc85xx/cmd_errata.c @@ -326,6 +326,9 @@ static int do_errata(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) #if defined(CONFIG_SYS_FSL_B4860QDS_XFI_ERR) && defined(CONFIG_B4860QDS) puts("Work-around for Erratum XFI on B4860QDS enabled\n"); #endif +#ifdef CONFIG_SYS_FSL_ERRATUM_A009663 + puts("Work-around for Erratum A009663 enabled\n"); +#endif return 0; } diff --git a/arch/powerpc/include/asm/config_mpc85xx.h b/arch/powerpc/include/asm/config_mpc85xx.h index 674fac8828..eccc146dae 100644 --- a/arch/powerpc/include/asm/config_mpc85xx.h +++ b/arch/powerpc/include/asm/config_mpc85xx.h @@ -808,6 +808,7 @@ defined(CONFIG_PPC_T1020) || defined(CONFIG_PPC_T1022) #define QE_NUM_OF_SNUM 28 #define CONFIG_SYS_FSL_SFP_VER_3_0 #define CONFIG_SYS_FSL_ERRATUM_A008378 +#define CONFIG_SYS_FSL_ERRATUM_A009663 #elif defined(CONFIG_PPC_T1024) || defined(CONFIG_PPC_T1023) ||\ defined(CONFIG_PPC_T1014) || defined(CONFIG_PPC_T1013) @@ -856,6 +857,7 @@ defined(CONFIG_PPC_T1014) || defined(CONFIG_PPC_T1013) #define QE_NUM_OF_SNUM 28 #define CONFIG_SYS_FSL_SFP_VER_3_0 #define CONFIG_SYS_FSL_ERRATUM_A008378 +#define CONFIG_SYS_FSL_ERRATUM_A009663 #elif defined(CONFIG_PPC_T2080) || defined(CONFIG_PPC_T2081) #define CONFIG_E6500 diff --git a/drivers/ddr/fsl/fsl_ddr_gen4.c b/drivers/ddr/fsl/fsl_ddr_gen4.c index 0d9dd0bb46..6f76980d31 100644 --- a/drivers/ddr/fsl/fsl_ddr_gen4.c +++ b/drivers/ddr/fsl/fsl_ddr_gen4.c @@ -155,7 +155,12 @@ void fsl_ddr_set_memctl_regs(const fsl_ddr_cfg_regs_t *regs, ddr_out32(&ddr->sdram_mode_15, regs->ddr_sdram_mode_15); ddr_out32(&ddr->sdram_mode_16, regs->ddr_sdram_mode_16); ddr_out32(&ddr->sdram_md_cntl, regs->ddr_sdram_md_cntl); +#ifdef CONFIG_SYS_FSL_ERRATUM_A009663 + ddr_out32(&ddr->sdram_interval, + regs->ddr_sdram_interval & ~SDRAM_INTERVAL_BSTOPRE); +#else ddr_out32(&ddr->sdram_interval, regs->ddr_sdram_interval); +#endif ddr_out32(&ddr->sdram_data_init, regs->ddr_data_init); ddr_out32(&ddr->ddr_wrlvl_cntl, regs->ddr_wrlvl_cntl); #ifndef CONFIG_SYS_FSL_DDR_EMU @@ -397,6 +402,11 @@ step2: if (timeout <= 0) printf("Waiting for D_INIT timeout. Memory may not work.\n"); + +#ifdef CONFIG_SYS_FSL_ERRATUM_A009663 + ddr_out32(&ddr->sdram_interval, regs->ddr_sdram_interval); +#endif + #ifdef CONFIG_DEEP_SLEEP if (is_warm_boot()) { /* exit self-refresh */ diff --git a/include/fsl_ddr_sdram.h b/include/fsl_ddr_sdram.h index 9ea8b63779..3699c0408a 100644 --- a/include/fsl_ddr_sdram.h +++ b/include/fsl_ddr_sdram.h @@ -129,6 +129,7 @@ typedef struct ddr4_spd_eeprom_s generic_spd_eeprom_t; #define SDRAM_CFG2_ODT_ONLY_READ 2 #define SDRAM_CFG2_ODT_ALWAYS 3 +#define SDRAM_INTERVAL_BSTOPRE 0x3FFF #define TIMING_CFG_2_CPO_MASK 0x0F800000 #if defined(CONFIG_SYS_FSL_DDR_VER) && \ -- 2.39.5