diff options
Diffstat (limited to 'recipes-kernel/linux/linux-ti33x-psp-3.2/3.2.16/0041-serial-PL011-clear-pending-interrupts.patch')
-rw-r--r-- | recipes-kernel/linux/linux-ti33x-psp-3.2/3.2.16/0041-serial-PL011-clear-pending-interrupts.patch | 82 |
1 files changed, 82 insertions, 0 deletions
diff --git a/recipes-kernel/linux/linux-ti33x-psp-3.2/3.2.16/0041-serial-PL011-clear-pending-interrupts.patch b/recipes-kernel/linux/linux-ti33x-psp-3.2/3.2.16/0041-serial-PL011-clear-pending-interrupts.patch new file mode 100644 index 00000000..3b17d2c7 --- /dev/null +++ b/recipes-kernel/linux/linux-ti33x-psp-3.2/3.2.16/0041-serial-PL011-clear-pending-interrupts.patch @@ -0,0 +1,82 @@ +From 83b1f68d0e0fdc6993be1ebf4ef51a439b71180f Mon Sep 17 00:00:00 2001 +From: Linus Walleij <linus.walleij@linaro.org> +Date: Tue, 13 Mar 2012 13:27:23 +0100 +Subject: [PATCH 41/68] serial: PL011: clear pending interrupts + +commit 9b96fbacda34079dea0638ee1e92c56286f6114a upstream. + +Chanho Min reported that when the boot loader transfers +control to the kernel, there may be pending interrupts +causing the UART to lock up in an eternal loop trying to +pick tokens from the FIFO (since the RX interrupt flag +indicates there are tokens) while in practice there are +no tokens - in fact there is only a pending IRQ flag. + +This patch address the issue with a combination of two +patches suggested by Russell King that clears and mask +all interrupts at probe() and clears any pending error +and RX interrupts at port startup time. + +We suspect the spurious interrupts are a side-effect of +switching the UART from FIFO to non-FIFO mode. + +Cc: Shreshtha Kumar Sahu <shreshthakumar.sahu@stericsson.com> +Reported-by: Chanho Min <chanho0207@gmail.com> +Suggested-by: Russell King <linux@arm.linux.org.uk> +Signed-off-by: Linus Walleij <linus.walleij@linaro.org> +Reviewed-by: Jong-Sung Kim <neidhard.kim@lge.com> +Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> +--- + drivers/tty/serial/amba-pl011.c | 15 +++++++++++---- + 1 file changed, 11 insertions(+), 4 deletions(-) + +diff --git a/drivers/tty/serial/amba-pl011.c b/drivers/tty/serial/amba-pl011.c +index 8e00926..dddc3f2 100644 +--- a/drivers/tty/serial/amba-pl011.c ++++ b/drivers/tty/serial/amba-pl011.c +@@ -1380,6 +1380,10 @@ static int pl011_startup(struct uart_port *port) + + uap->port.uartclk = clk_get_rate(uap->clk); + ++ /* Clear pending error and receive interrupts */ ++ writew(UART011_OEIS | UART011_BEIS | UART011_PEIS | UART011_FEIS | ++ UART011_RTIS | UART011_RXIS, uap->port.membase + UART011_ICR); ++ + /* + * Allocate the IRQ + */ +@@ -1414,10 +1418,6 @@ static int pl011_startup(struct uart_port *port) + cr = UART01x_CR_UARTEN | UART011_CR_RXE | UART011_CR_TXE; + writew(cr, uap->port.membase + UART011_CR); + +- /* Clear pending error interrupts */ +- writew(UART011_OEIS | UART011_BEIS | UART011_PEIS | UART011_FEIS, +- uap->port.membase + UART011_ICR); +- + /* + * initialise the old status of the modem signals + */ +@@ -1432,6 +1432,9 @@ static int pl011_startup(struct uart_port *port) + * as well. + */ + spin_lock_irq(&uap->port.lock); ++ /* Clear out any spuriously appearing RX interrupts */ ++ writew(UART011_RTIS | UART011_RXIS, ++ uap->port.membase + UART011_ICR); + uap->im = UART011_RTIM; + if (!pl011_dma_rx_running(uap)) + uap->im |= UART011_RXIM; +@@ -1916,6 +1919,10 @@ static int pl011_probe(struct amba_device *dev, const struct amba_id *id) + goto unmap; + } + ++ /* Ensure interrupts from this UART are masked and cleared */ ++ writew(0, uap->port.membase + UART011_IMSC); ++ writew(0xffff, uap->port.membase + UART011_ICR); ++ + uap->vendor = vendor; + uap->lcrh_rx = vendor->lcrh_rx; + uap->lcrh_tx = vendor->lcrh_tx; +-- +1.7.10 + |