[U-Boot] [PATCH 1/2] arm: vf610: lpuart: fix status register handling

Stefan Agner stefan at agner.ch
Tue Aug 19 17:54:27 CEST 2014


The status register 1 (S1) is not writeable, hence we should not
write it. In order to clear the RDRF flag we only need to read
the data register.

Also, when stressing U-Boot a lot with serial input, an overflow can
occur which asserts the S1_OR flag (while not asserting the S1_RDRF
flag). To clear this flag we again just need to read the data
register, hence add this flag to the abort conditions for the while
loop.

Insert a compiler barrier to make sure reading the data register
gets executed after reading the status register.

Signed-off-by: Stefan Agner <stefan at agner.ch>
---
 drivers/serial/serial_lpuart.c | 9 +++------
 1 file changed, 3 insertions(+), 6 deletions(-)

diff --git a/drivers/serial/serial_lpuart.c b/drivers/serial/serial_lpuart.c
index da5f9a2..96173ca 100644
--- a/drivers/serial/serial_lpuart.c
+++ b/drivers/serial/serial_lpuart.c
@@ -14,6 +14,7 @@
 
 #define US1_TDRE        (1 << 7)
 #define US1_RDRF        (1 << 5)
+#define US1_OR          (1 << 3)
 #define UC2_TE          (1 << 3)
 #define UC2_RE          (1 << 2)
 
@@ -38,14 +39,10 @@ static void lpuart_serial_setbrg(void)
 
 static int lpuart_serial_getc(void)
 {
-	u8 status;
-
-	while (!(__raw_readb(&base->us1) & US1_RDRF))
+	while (!(__raw_readb(&base->us1) & (US1_RDRF | US1_OR)))
 		WATCHDOG_RESET();
 
-	status = __raw_readb(&base->us1);
-	status |= US1_RDRF;
-	__raw_writeb(status, &base->us1);
+	barrier();
 
 	return __raw_readb(&base->ud);
 }
-- 
2.0.4



More information about the U-Boot mailing list