diff mbox series

[4/9] ram: stm32mp1: tuning: add timeout for polling BISTGSR.BDDONE

Message ID 20200306111355.4.If03eb32f9863bed008f5367b47116f667bb85099@changeid
State Accepted
Commit f711d1f0804e01586b8f68af81cde6a15b58d427
Headers show
Series ram: stm32mp1: fixes | expand

Commit Message

Patrick Delaunay March 6, 2020, 10:14 a.m. UTC
Avoid to block the tuning procedure on BIST error (not finished
BIST procedure) by adding a 1000us timeout on the polling of
BISTGSR.BDDONE executed to detect the end of BIST.

The normal duration of the BIST test is around 5us.

This patch also cleanup comments.

Signed-off-by: Patrick Delaunay <patrick.delaunay at st.com>
---

 drivers/ram/stm32mp1/stm32mp1_tuning.c | 45 ++++++++++++++------------
 1 file changed, 25 insertions(+), 20 deletions(-)

Comments

Patrice CHOTARD March 18, 2020, 9:40 a.m. UTC | #1
On 3/6/20 11:14 AM, Patrick Delaunay wrote:
> Avoid to block the tuning procedure on BIST error (not finished
> BIST procedure) by adding a 1000us timeout on the polling of
> BISTGSR.BDDONE executed to detect the end of BIST.
>
> The normal duration of the BIST test is around 5us.
>
> This patch also cleanup comments.
>
> Signed-off-by: Patrick Delaunay <patrick.delaunay at st.com>
> ---
>
>  drivers/ram/stm32mp1/stm32mp1_tuning.c | 45 ++++++++++++++------------
>  1 file changed, 25 insertions(+), 20 deletions(-)
>
> diff --git a/drivers/ram/stm32mp1/stm32mp1_tuning.c b/drivers/ram/stm32mp1/stm32mp1_tuning.c
> index e3e6f0f79c..cab6cf087a 100644
> --- a/drivers/ram/stm32mp1/stm32mp1_tuning.c
> +++ b/drivers/ram/stm32mp1/stm32mp1_tuning.c
> @@ -8,6 +8,7 @@
>  #include <ram.h>
>  #include <reset.h>
>  #include <asm/io.h>
> +#include <linux/iopoll.h>
>  
>  #include "stm32mp1_ddr_regs.h"
>  #include "stm32mp1_ddr.h"
> @@ -246,6 +247,8 @@ static void BIST_test(struct stm32mp1_ddrphy *phy, u8 byte,
>  	bool result = true; /* BIST_SUCCESS */
>  	u32 cnt = 0;
>  	u32 error = 0;
> +	u32 val;
> +	int ret;
>  
>  	bist->test_result = true;
>  
> @@ -274,27 +277,29 @@ run:
>  			0x00000001);
>  	/* Write BISTRR.BINST = 3?b001; */
>  
> -	/* Wait for a number of CTL clocks before reading BIST register*/
> -	/* Wait 300 ctl_clk cycles;  ... IS it really needed?? */
> -	/* Perform BIST Instruction Stop*/
> -	/* Write BISTRR.BINST = 3?b010;*/
> -
> -	/* poll on BISTGSR.BDONE. If 0, wait.  ++TODO Add timeout */
> -	while (!(readl(&phy->bistgsr) & DDRPHYC_BISTGSR_BDDONE))
> -		;
> -
> -	/*Check if received correct number of words*/
> -	/* if (Read BISTWCSR.DXWCNT = Read BISTWCR.BWCNT) */
> -	if (((readl(&phy->bistwcsr)) >> DDRPHYC_BISTWCSR_DXWCNT_SHIFT) ==
> -	    readl(&phy->bistwcr)) {
> -		/*Determine if there is a data comparison error*/
> -		/* if (Read BISTGSR.BDXERR = 1?b0) */
> -		if (readl(&phy->bistgsr) & DDRPHYC_BISTGSR_BDXERR)
> -			result = false; /* BIST_FAIL; */
> -		else
> -			result = true; /* BIST_SUCCESS; */
> -	} else {
> +	/* poll on BISTGSR.BDONE and wait max 1000 us */
> +	ret = readl_poll_timeout(&phy->bistgsr, val,
> +				 val & DDRPHYC_BISTGSR_BDDONE, 1000);
> +
> +	if (ret < 0) {
> +		printf("warning: BIST timeout\n");
>  		result = false; /* BIST_FAIL; */
> +		/*Perform BIST Stop */
> +		clrsetbits_le32(&phy->bistrr, 0x00000007, 0x00000002);
> +	} else {
> +		/*Check if received correct number of words*/
> +		/* if (Read BISTWCSR.DXWCNT = Read BISTWCR.BWCNT) */
> +		if (((readl(&phy->bistwcsr)) >> DDRPHYC_BISTWCSR_DXWCNT_SHIFT)
> +		    == readl(&phy->bistwcr)) {
> +			/*Determine if there is a data comparison error*/
> +			/* if (Read BISTGSR.BDXERR = 1?b0) */
> +			if (readl(&phy->bistgsr) & DDRPHYC_BISTGSR_BDXERR)
> +				result = false; /* BIST_FAIL; */
> +			else
> +				result = true; /* BIST_SUCCESS; */
> +		} else {
> +			result = false; /* BIST_FAIL; */
> +		}
>  	}
>  
>  	/* loop while success */

Acked-by: Patrice Chotard <patrice.chotard at st.com>

Thanks

Patrice
Patrick Delaunay March 24, 2020, 8:49 a.m. UTC | #2
Hi,

> From: Patrick DELAUNAY <patrick.delaunay at st.com>
> Sent: vendredi 6 mars 2020 11:14
> 
> Avoid to block the tuning procedure on BIST error (not finished BIST procedure)
> by adding a 1000us timeout on the polling of BISTGSR.BDDONE executed to
> detect the end of BIST.
> 
> The normal duration of the BIST test is around 5us.
> 
> This patch also cleanup comments.
> 
> Signed-off-by: Patrick Delaunay <patrick.delaunay at st.com>
> ---

Applied to u-boot-stm/next, thanks!

Regards

Patrick
diff mbox series

Patch

diff --git a/drivers/ram/stm32mp1/stm32mp1_tuning.c b/drivers/ram/stm32mp1/stm32mp1_tuning.c
index e3e6f0f79c..cab6cf087a 100644
--- a/drivers/ram/stm32mp1/stm32mp1_tuning.c
+++ b/drivers/ram/stm32mp1/stm32mp1_tuning.c
@@ -8,6 +8,7 @@ 
 #include <ram.h>
 #include <reset.h>
 #include <asm/io.h>
+#include <linux/iopoll.h>
 
 #include "stm32mp1_ddr_regs.h"
 #include "stm32mp1_ddr.h"
@@ -246,6 +247,8 @@  static void BIST_test(struct stm32mp1_ddrphy *phy, u8 byte,
 	bool result = true; /* BIST_SUCCESS */
 	u32 cnt = 0;
 	u32 error = 0;
+	u32 val;
+	int ret;
 
 	bist->test_result = true;
 
@@ -274,27 +277,29 @@  run:
 			0x00000001);
 	/* Write BISTRR.BINST = 3?b001; */
 
-	/* Wait for a number of CTL clocks before reading BIST register*/
-	/* Wait 300 ctl_clk cycles;  ... IS it really needed?? */
-	/* Perform BIST Instruction Stop*/
-	/* Write BISTRR.BINST = 3?b010;*/
-
-	/* poll on BISTGSR.BDONE. If 0, wait.  ++TODO Add timeout */
-	while (!(readl(&phy->bistgsr) & DDRPHYC_BISTGSR_BDDONE))
-		;
-
-	/*Check if received correct number of words*/
-	/* if (Read BISTWCSR.DXWCNT = Read BISTWCR.BWCNT) */
-	if (((readl(&phy->bistwcsr)) >> DDRPHYC_BISTWCSR_DXWCNT_SHIFT) ==
-	    readl(&phy->bistwcr)) {
-		/*Determine if there is a data comparison error*/
-		/* if (Read BISTGSR.BDXERR = 1?b0) */
-		if (readl(&phy->bistgsr) & DDRPHYC_BISTGSR_BDXERR)
-			result = false; /* BIST_FAIL; */
-		else
-			result = true; /* BIST_SUCCESS; */
-	} else {
+	/* poll on BISTGSR.BDONE and wait max 1000 us */
+	ret = readl_poll_timeout(&phy->bistgsr, val,
+				 val & DDRPHYC_BISTGSR_BDDONE, 1000);
+
+	if (ret < 0) {
+		printf("warning: BIST timeout\n");
 		result = false; /* BIST_FAIL; */
+		/*Perform BIST Stop */
+		clrsetbits_le32(&phy->bistrr, 0x00000007, 0x00000002);
+	} else {
+		/*Check if received correct number of words*/
+		/* if (Read BISTWCSR.DXWCNT = Read BISTWCR.BWCNT) */
+		if (((readl(&phy->bistwcsr)) >> DDRPHYC_BISTWCSR_DXWCNT_SHIFT)
+		    == readl(&phy->bistwcr)) {
+			/*Determine if there is a data comparison error*/
+			/* if (Read BISTGSR.BDXERR = 1?b0) */
+			if (readl(&phy->bistgsr) & DDRPHYC_BISTGSR_BDXERR)
+				result = false; /* BIST_FAIL; */
+			else
+				result = true; /* BIST_SUCCESS; */
+		} else {
+			result = false; /* BIST_FAIL; */
+		}
 	}
 
 	/* loop while success */