From 0a38fd9326fde16597dc7eef274be46bdc8cdcee Mon Sep 17 00:00:00 2001 From: Ryan Case Date: Wed, 19 Dec 2018 12:33:53 -0800 Subject: tty: serial: qcom_geni_serial: Fix UART hang [ Upstream commit 663abb1a7a7ff8fea9ab0145463de7fcff823755 ] If a serial console write occured while a UART transmit command was waiting for a done signal then no further data would be sent until something new kicked the system into gear. If there is already data waiting in the circular buffer we must re-enable the tx watermark so we receive the expected interrupts. Signed-off-by: Ryan Case Reviewed-by: Evan Green Signed-off-by: Greg Kroah-Hartman Signed-off-by: Sasha Levin --- drivers/tty/serial/qcom_geni_serial.c | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'drivers') diff --git a/drivers/tty/serial/qcom_geni_serial.c b/drivers/tty/serial/qcom_geni_serial.c index b3f7d1a1e97f..2003dfcace5d 100644 --- a/drivers/tty/serial/qcom_geni_serial.c +++ b/drivers/tty/serial/qcom_geni_serial.c @@ -438,6 +438,7 @@ static void qcom_geni_serial_console_write(struct console *co, const char *s, bool locked = true; unsigned long flags; u32 geni_status; + u32 irq_en; WARN_ON(co->index < 0 || co->index >= GENI_UART_CONS_PORTS); @@ -472,6 +473,13 @@ static void qcom_geni_serial_console_write(struct console *co, const char *s, * has been sent, in which case we need to look for done first. */ qcom_geni_serial_poll_tx_done(uport); + + if (uart_circ_chars_pending(&uport->state->xmit)) { + irq_en = readl_relaxed(uport->membase + + SE_GENI_M_IRQ_EN); + writel_relaxed(irq_en | M_TX_FIFO_WATERMARK_EN, + uport->membase + SE_GENI_M_IRQ_EN); + } } __qcom_geni_serial_console_write(uport, s, count); -- cgit v1.2.3