Skip to content

Commit

Permalink
u-boot: Fix the SPI and eMMC hang issue
Browse files Browse the repository at this point in the history
Refer to 1 and 2, the root cause is the wrong data type of the timer
value.

Thanks [email protected] for the patches.

1. https://lists.denx.de/pipermail/u-boot/2024-December/574817.html
2. https://lists.denx.de/pipermail/u-boot/2024-December/574818.html

Signed-off-by: Baocheng Su <[email protected]>
  • Loading branch information
BaochengSu committed Dec 17, 2024
1 parent a8659b3 commit 1e9172a
Show file tree
Hide file tree
Showing 7 changed files with 126 additions and 88 deletions.

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Jan Kiszka <[email protected]>
Date: Mon, 30 Oct 2023 17:20:29 +0100
Subject: [PATCH] spi: cadence-quadspi: Fix error message on stuck busy state

We are not iterating CQSPI_REG_RETRY, we are waiting 'timeout' ms, since
day 1.

Signed-off-by: Jan Kiszka <[email protected]>
Reviewed-by: Stefan Roese <[email protected]>
Reviewed-by: Jagan Teki <[email protected]>
---
drivers/spi/cadence_qspi_apb.c | 3 +--
1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/drivers/spi/cadence_qspi_apb.c b/drivers/spi/cadence_qspi_apb.c
index 9ce2c0f254f3..d033184aa466 100644
--- a/drivers/spi/cadence_qspi_apb.c
+++ b/drivers/spi/cadence_qspi_apb.c
@@ -171,8 +171,7 @@ static unsigned int cadence_qspi_wait_idle(void *reg_base)
}

/* Timeout, still in busy mode. */
- printf("QSPI: QSPI is still busy after poll for %d times.\n",
- CQSPI_REG_RETRY);
+ printf("QSPI: QSPI is still busy after poll for %d ms.\n", timeout);
return 0;
}

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Ronald Wahl <[email protected]>
Date: Wed, 11 Dec 2024 21:51:04 +0100
Subject: [PATCH] spi: cadence-quadspi: fix potential malfunction after ~49
days uptime

The get_timer function returns an unsigned long which may be calculated
from the ARM system counter. This counter is reset only on a cold reset.
U-boot divides this counter down to a 1000 Hz counter that will cross
the 32bit barrier after a bit more than 49 days. Assigning the value to
an unsigned int will truncate it on 64bit systems.
Passing this truncated value back to the get_timer function will return
a very large value that is certainly larger than the timeout and so will
go down the error path and besides stopping U-Boot will lead to messages
like

"SPI: QSPI is still busy after poll for 5000 ms."

Signed-off-by: Ronald Wahl <[email protected]>
Cc: Vignesh R <[email protected]>
Cc: Pratyush Yadav <[email protected]>
---
drivers/spi/cadence_qspi_apb.c | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/drivers/spi/cadence_qspi_apb.c b/drivers/spi/cadence_qspi_apb.c
index d033184aa466..ecbd6f9d147d 100644
--- a/drivers/spi/cadence_qspi_apb.c
+++ b/drivers/spi/cadence_qspi_apb.c
@@ -152,9 +152,9 @@ static int cadence_qspi_set_protocol(struct cadence_spi_priv *priv,
/* Return 1 if idle, otherwise return 0 (busy). */
static unsigned int cadence_qspi_wait_idle(void *reg_base)
{
- unsigned int start, count = 0;
+ unsigned long start, count = 0;
/* timeout in unit of ms */
- unsigned int timeout = 5000;
+ unsigned long timeout = 5000;

start = get_timer(0);
for ( ; get_timer(start) < timeout ; ) {
@@ -171,7 +171,7 @@ static unsigned int cadence_qspi_wait_idle(void *reg_base)
}

/* Timeout, still in busy mode. */
- printf("QSPI: QSPI is still busy after poll for %d ms.\n", timeout);
+ printf("QSPI: QSPI is still busy after poll for %lu ms.\n", timeout);
return 0;
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001
From: Ronald Wahl <[email protected]>
Date: Wed, 11 Dec 2024 21:52:00 +0100
Subject: [PATCH] mmc: Fix potential timer value truncation

On 64bit systems the timer value might be truncated to a 32bit value
causing malfunctions. For example on ARM the timer might start from 0
again only after a cold reset. The 32bit overflow occurs after a bit
more than 49 days (1000 Hz counter) so booting after that time may lead
to a surprise because the board might become stuck requiring a cold
reset.

Signed-off-by: Ronald Wahl <[email protected]>
Cc: Peng Fan <[email protected]>
Cc: Jaehoon Chung <[email protected]>
---
drivers/mmc/mmc.c | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c
index 31cfda288587..2779302b843e 100644
--- a/drivers/mmc/mmc.c
+++ b/drivers/mmc/mmc.c
@@ -713,7 +713,7 @@ static int mmc_send_op_cond(struct mmc *mmc)
{
int err, i;
int timeout = 1000;
- uint start;
+ ulong start;

/* Some cards seem to need this */
mmc_go_idle(mmc);
@@ -808,7 +808,8 @@ int mmc_send_ext_csd(struct mmc *mmc, u8 *ext_csd)
static int __mmc_switch(struct mmc *mmc, u8 set, u8 index, u8 value,
bool send_status)
{
- unsigned int status, start;
+ ulong start;
+ unsigned int status;
struct mmc_cmd cmd;
int timeout_ms = DEFAULT_CMD6_TIMEOUT_MS;
bool is_part_switch = (set == EXT_CSD_CMD_SET_NORMAL) &&
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ Signed-off-by: Li Hua Qian <[email protected]>
1 file changed, 10 insertions(+), 2 deletions(-)

diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c
index dff0ff89a801..99a92f44bef4 100644
index 2779302b843e..7554730a0489 100644
--- a/drivers/mmc/mmc.c
+++ b/drivers/mmc/mmc.c
@@ -651,8 +651,16 @@ static int sd_send_op_cond(struct mmc *mmc, bool uhs_en)
Expand Down
7 changes: 4 additions & 3 deletions recipes-bsp/u-boot/u-boot-iot2050_2023.10.bb
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,10 @@ SRC_URI += " \
file://0009-dts-iot2050-Sync-kernel-dts-to-u-boot.patch \
file://0010-dts-iot2050-Support-new-IOT2050-SM-variant.patch \
file://0011-arm-dts-iot2050-Disable-lock-step-mode-for-all-iot20.patch \
file://0012-qspi-iot2050-Add-temporary-workaround-for-the-QSPI-i.patch \
file://0013-driver-iot2050-Add-a-temporary-workaround-for-the-eMMC.patch \
file://0014-driver-iot2050-Add-a-temporary-workaround-for-the-SD.patch \
file://0012-spi-cadence-quadspi-Fix-error-message-on-stuck-busy-.patch \
file://0013-spi-cadence-quadspi-fix-potential-malfunction-after-.patch \
file://0014-mmc-Fix-potential-timer-value-truncation.patch \
file://0015-driver-iot2050-Add-a-temporary-workaround-for-the-SD.patch \
"

SRC_URI[sha256sum] = "e00e6c6f014e046101739d08d06f328811cebcf5ae101348f409cbbd55ce6900"
Expand Down

0 comments on commit 1e9172a

Please sign in to comment.