[PATCH] ddr: marvell: a38x: Perform DDR training sequence again for 2nd boot

- DDR Training sequence happens very fast. The speedup in boot time is negligible by skipping the training sequence during 2nd boot or after. So remove the check and skip. - This change improves the robustness of DDR training. If u-boot crashed during DDR training, the training could be left in a limbo state, where the BootROM has recorded that it is already in a 2nd boot. The training must be repeated in this scenario to get out of this limbo state, but due to the check it cannot be performed.
Signed-off-by: Tony Dinh mibodhi@gmail.com ---
drivers/ddr/marvell/a38x/mv_ddr_plat.c | 7 ------- 1 file changed, 7 deletions(-)
diff --git a/drivers/ddr/marvell/a38x/mv_ddr_plat.c b/drivers/ddr/marvell/a38x/mv_ddr_plat.c index 6e7949ac72..8ec9fb0874 100644 --- a/drivers/ddr/marvell/a38x/mv_ddr_plat.c +++ b/drivers/ddr/marvell/a38x/mv_ddr_plat.c @@ -1363,13 +1363,6 @@ int mv_ddr_pre_training_soc_config(const char *ddr_type) DRAM_RESET_MASK_MASKED << DRAM_RESET_MASK_OFFS); }
- /* Check if DRAM is already initialized */ - if (reg_read(REG_BOOTROM_ROUTINE_ADDR) & - (1 << REG_BOOTROM_ROUTINE_DRAM_INIT_OFFS)) { - printf("%s Training Sequence - 2nd boot - Skip\n", ddr_type); - return MV_OK; - } - /* Fix read ready phases for all SOC in reg 0x15c8 */ reg_val = reg_read(TRAINING_DBG_3_REG);

Hi Pali,
Could you review this patch?
Thanks, Tony
On Sun, Apr 2, 2023 at 9:42 PM Tony Dinh mibodhi@gmail.com wrote:
- DDR Training sequence happens very fast. The speedup in boot time is
negligible by skipping the training sequence during 2nd boot or after. So remove the check and skip.
- This change improves the robustness of DDR training. If u-boot crashed
during DDR training, the training could be left in a limbo state, where the BootROM has recorded that it is already in a 2nd boot. The training must be repeated in this scenario to get out of this limbo state, but due to the check it cannot be performed.
Signed-off-by: Tony Dinh mibodhi@gmail.com
drivers/ddr/marvell/a38x/mv_ddr_plat.c | 7 ------- 1 file changed, 7 deletions(-)
diff --git a/drivers/ddr/marvell/a38x/mv_ddr_plat.c b/drivers/ddr/marvell/a38x/mv_ddr_plat.c index 6e7949ac72..8ec9fb0874 100644 --- a/drivers/ddr/marvell/a38x/mv_ddr_plat.c +++ b/drivers/ddr/marvell/a38x/mv_ddr_plat.c @@ -1363,13 +1363,6 @@ int mv_ddr_pre_training_soc_config(const char *ddr_type) DRAM_RESET_MASK_MASKED << DRAM_RESET_MASK_OFFS); }
/* Check if DRAM is already initialized */
if (reg_read(REG_BOOTROM_ROUTINE_ADDR) &
(1 << REG_BOOTROM_ROUTINE_DRAM_INIT_OFFS)) {
printf("%s Training Sequence - 2nd boot - Skip\n", ddr_type);
return MV_OK;
}
/* Fix read ready phases for all SOC in reg 0x15c8 */ reg_val = reg_read(TRAINING_DBG_3_REG);
-- 2.30.2

Hi Tony,
On 4/3/23 06:42, Tony Dinh wrote:
- DDR Training sequence happens very fast. The speedup in boot time is
negligible by skipping the training sequence during 2nd boot or after. So remove the check and skip.
- This change improves the robustness of DDR training. If u-boot crashed
during DDR training, the training could be left in a limbo state, where the BootROM has recorded that it is already in a 2nd boot. The training must be repeated in this scenario to get out of this limbo state, but due to the check it cannot be performed.
Have you actually seen such cases with a crash in the first DDR config state? And did the board run the 2nd DDR config state successfully then? Just curious.
Other than this:
Reviewed-by: Stefan Roese sr@denx.de
Thanks, Stefan
Signed-off-by: Tony Dinh mibodhi@gmail.com
drivers/ddr/marvell/a38x/mv_ddr_plat.c | 7 ------- 1 file changed, 7 deletions(-)
diff --git a/drivers/ddr/marvell/a38x/mv_ddr_plat.c b/drivers/ddr/marvell/a38x/mv_ddr_plat.c index 6e7949ac72..8ec9fb0874 100644 --- a/drivers/ddr/marvell/a38x/mv_ddr_plat.c +++ b/drivers/ddr/marvell/a38x/mv_ddr_plat.c @@ -1363,13 +1363,6 @@ int mv_ddr_pre_training_soc_config(const char *ddr_type) DRAM_RESET_MASK_MASKED << DRAM_RESET_MASK_OFFS); }
- /* Check if DRAM is already initialized */
- if (reg_read(REG_BOOTROM_ROUTINE_ADDR) &
(1 << REG_BOOTROM_ROUTINE_DRAM_INIT_OFFS)) {
printf("%s Training Sequence - 2nd boot - Skip\n", ddr_type);
return MV_OK;
- }
- /* Fix read ready phases for all SOC in reg 0x15c8 */ reg_val = reg_read(TRAINING_DBG_3_REG);
Viele Grüße, Stefan Roese

Hi Stefan,
On Tue, Apr 11, 2023 at 1:36 AM Stefan Roese sr@denx.de wrote:
Hi Tony,
On 4/3/23 06:42, Tony Dinh wrote:
- DDR Training sequence happens very fast. The speedup in boot time is
negligible by skipping the training sequence during 2nd boot or after. So remove the check and skip.
- This change improves the robustness of DDR training. If u-boot crashed
during DDR training, the training could be left in a limbo state, where the BootROM has recorded that it is already in a 2nd boot. The training must be repeated in this scenario to get out of this limbo state, but due to the check it cannot be performed.
Have you actually seen such cases with a crash in the first DDR config state? And did the board run the 2nd DDR config state successfully then? Just curious.
I did have such a crash recently when I was testing the combination of LTO and Thumb configs on the Thecus N2350 board (Armada 385). And apparently it crashed during the DDR4 training in SPL. A power recycle always results in the board hung at the same place.
<BEGIN LOG> BootROM - 1.73 Booting from SPI flash
U-Boot SPL 2023.04-rc4-tld-1-00585-g4b635046b5-dirty (Mar 26 2023 - 13:33:35 -0700) High speed PHY - Version: 2.0 Detected Device ID 6820 board SerDes lanes topology details: | Lane # | Speed | Type | -------------------------------- | 0 | 0 | SGMII0 | | 1 | 3 | SATA0 | | 2 | 3 | SATA1 | | 4 | 5 | USB3 HOST0 | | 5 | 5 | USB3 HOST1 | -------------------------------- High speed PHY - Ended Successfully mv_ddr: 14.0.0 DDR4 Training Sequence - 2nd boot - Skip max poll IF #0 polling failed IF 0 DDR3 init_sequence - FAILED 0x1 max poll IF #0 polling failed IF 0 mv_ddr_is_training_done: timeout <END LOG>
So that led me to the DDR code that performs the check for 2nd boot. And forcing DDR training to run again (using kwboot) fixed the problem and the board can be booted normally again.
All the best, Tony
Other than this:
Reviewed-by: Stefan Roese sr@denx.de
Thanks, Stefan
Signed-off-by: Tony Dinh mibodhi@gmail.com
drivers/ddr/marvell/a38x/mv_ddr_plat.c | 7 ------- 1 file changed, 7 deletions(-)
diff --git a/drivers/ddr/marvell/a38x/mv_ddr_plat.c b/drivers/ddr/marvell/a38x/mv_ddr_plat.c index 6e7949ac72..8ec9fb0874 100644 --- a/drivers/ddr/marvell/a38x/mv_ddr_plat.c +++ b/drivers/ddr/marvell/a38x/mv_ddr_plat.c @@ -1363,13 +1363,6 @@ int mv_ddr_pre_training_soc_config(const char *ddr_type) DRAM_RESET_MASK_MASKED << DRAM_RESET_MASK_OFFS); }
/* Check if DRAM is already initialized */
if (reg_read(REG_BOOTROM_ROUTINE_ADDR) &
(1 << REG_BOOTROM_ROUTINE_DRAM_INIT_OFFS)) {
printf("%s Training Sequence - 2nd boot - Skip\n", ddr_type);
return MV_OK;
}
/* Fix read ready phases for all SOC in reg 0x15c8 */ reg_val = reg_read(TRAINING_DBG_3_REG);
Viele Grüße, Stefan Roese
-- DENX Software Engineering GmbH, Managing Director: Erika Unter HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany Phone: (+49)-8142-66989-51 Fax: (+49)-8142-66989-80 Email: sr@denx.de

On 4/3/23 06:42, Tony Dinh wrote:
- DDR Training sequence happens very fast. The speedup in boot time is
negligible by skipping the training sequence during 2nd boot or after. So remove the check and skip.
- This change improves the robustness of DDR training. If u-boot crashed
during DDR training, the training could be left in a limbo state, where the BootROM has recorded that it is already in a 2nd boot. The training must be repeated in this scenario to get out of this limbo state, but due to the check it cannot be performed.
Signed-off-by: Tony Dinh mibodhi@gmail.com
Applied to u-boot-marvell/master
Thanks, Stefan
drivers/ddr/marvell/a38x/mv_ddr_plat.c | 7 ------- 1 file changed, 7 deletions(-)
diff --git a/drivers/ddr/marvell/a38x/mv_ddr_plat.c b/drivers/ddr/marvell/a38x/mv_ddr_plat.c index 6e7949ac72..8ec9fb0874 100644 --- a/drivers/ddr/marvell/a38x/mv_ddr_plat.c +++ b/drivers/ddr/marvell/a38x/mv_ddr_plat.c @@ -1363,13 +1363,6 @@ int mv_ddr_pre_training_soc_config(const char *ddr_type) DRAM_RESET_MASK_MASKED << DRAM_RESET_MASK_OFFS); }
- /* Check if DRAM is already initialized */
- if (reg_read(REG_BOOTROM_ROUTINE_ADDR) &
(1 << REG_BOOTROM_ROUTINE_DRAM_INIT_OFFS)) {
printf("%s Training Sequence - 2nd boot - Skip\n", ddr_type);
return MV_OK;
- }
- /* Fix read ready phases for all SOC in reg 0x15c8 */ reg_val = reg_read(TRAINING_DBG_3_REG);
Viele Grüße, Stefan Roese

Hi Pali,
I've created a pull request for this patch to the Marvell repo.
https://github.com/MarvellEmbeddedProcessors/mv-ddr-marvell/pull/41
Thanks, Tony
On Thu, Apr 13, 2023 at 11:06 PM Stefan Roese sr@denx.de wrote:
On 4/3/23 06:42, Tony Dinh wrote:
- DDR Training sequence happens very fast. The speedup in boot time is
negligible by skipping the training sequence during 2nd boot or after. So remove the check and skip.
- This change improves the robustness of DDR training. If u-boot crashed
during DDR training, the training could be left in a limbo state, where the BootROM has recorded that it is already in a 2nd boot. The training must be repeated in this scenario to get out of this limbo state, but due to the check it cannot be performed.
Signed-off-by: Tony Dinh mibodhi@gmail.com
Applied to u-boot-marvell/master
Thanks, Stefan
drivers/ddr/marvell/a38x/mv_ddr_plat.c | 7 ------- 1 file changed, 7 deletions(-)
diff --git a/drivers/ddr/marvell/a38x/mv_ddr_plat.c b/drivers/ddr/marvell/a38x/mv_ddr_plat.c index 6e7949ac72..8ec9fb0874 100644 --- a/drivers/ddr/marvell/a38x/mv_ddr_plat.c +++ b/drivers/ddr/marvell/a38x/mv_ddr_plat.c @@ -1363,13 +1363,6 @@ int mv_ddr_pre_training_soc_config(const char *ddr_type) DRAM_RESET_MASK_MASKED << DRAM_RESET_MASK_OFFS); }
/* Check if DRAM is already initialized */
if (reg_read(REG_BOOTROM_ROUTINE_ADDR) &
(1 << REG_BOOTROM_ROUTINE_DRAM_INIT_OFFS)) {
printf("%s Training Sequence - 2nd boot - Skip\n", ddr_type);
return MV_OK;
}
/* Fix read ready phases for all SOC in reg 0x15c8 */ reg_val = reg_read(TRAINING_DBG_3_REG);
Viele Grüße, Stefan Roese
-- DENX Software Engineering GmbH, Managing Director: Erika Unter HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany Phone: (+49)-8142-66989-51 Fax: (+49)-8142-66989-80 Email: sr@denx.de
participants (2)
-
Stefan Roese
-
Tony Dinh