]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/blobdiff - releases/4.14.111/tty-serial-atmel-add-is_half_duplex-helper.patch
Linux 4.14.111
[thirdparty/kernel/stable-queue.git] / releases / 4.14.111 / tty-serial-atmel-add-is_half_duplex-helper.patch
diff --git a/releases/4.14.111/tty-serial-atmel-add-is_half_duplex-helper.patch b/releases/4.14.111/tty-serial-atmel-add-is_half_duplex-helper.patch
new file mode 100644 (file)
index 0000000..1da0f2c
--- /dev/null
@@ -0,0 +1,80 @@
+From f3040983132bf3477acd45d2452a906e67c2fec9 Mon Sep 17 00:00:00 2001
+From: Razvan Stefanescu <razvan.stefanescu@microchip.com>
+Date: Tue, 19 Mar 2019 15:20:34 +0200
+Subject: tty/serial: atmel: Add is_half_duplex helper
+
+From: Razvan Stefanescu <razvan.stefanescu@microchip.com>
+
+commit f3040983132bf3477acd45d2452a906e67c2fec9 upstream.
+
+Use a helper function to check that a port needs to use half duplex
+communication, replacing several occurrences of multi-line bit checking.
+
+Fixes: b389f173aaa1 ("tty/serial: atmel: RS485 half duplex w/DMA: enable RX after TX is done")
+Cc: stable <stable@vger.kernel.org>
+Signed-off-by: Razvan Stefanescu <razvan.stefanescu@microchip.com>
+Acked-by: Richard Genoud <richard.genoud@gmail.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+
+---
+ drivers/tty/serial/atmel_serial.c |   19 +++++++++++--------
+ 1 file changed, 11 insertions(+), 8 deletions(-)
+
+--- a/drivers/tty/serial/atmel_serial.c
++++ b/drivers/tty/serial/atmel_serial.c
+@@ -238,6 +238,12 @@ static inline void atmel_uart_write_char
+       __raw_writeb(value, port->membase + ATMEL_US_THR);
+ }
++static inline int atmel_uart_is_half_duplex(struct uart_port *port)
++{
++      return (port->rs485.flags & SER_RS485_ENABLED) &&
++              !(port->rs485.flags & SER_RS485_RX_DURING_TX);
++}
++
+ #ifdef CONFIG_SERIAL_ATMEL_PDC
+ static bool atmel_use_pdc_rx(struct uart_port *port)
+ {
+@@ -489,9 +495,9 @@ static void atmel_stop_tx(struct uart_po
+       /* Disable interrupts */
+       atmel_uart_writel(port, ATMEL_US_IDR, atmel_port->tx_done_mask);
+-      if ((port->rs485.flags & SER_RS485_ENABLED) &&
+-          !(port->rs485.flags & SER_RS485_RX_DURING_TX))
++      if (atmel_uart_is_half_duplex(port))
+               atmel_start_rx(port);
++
+ }
+ /*
+@@ -508,8 +514,7 @@ static void atmel_start_tx(struct uart_p
+               return;
+       if (atmel_use_pdc_tx(port) || atmel_use_dma_tx(port))
+-              if ((port->rs485.flags & SER_RS485_ENABLED) &&
+-                  !(port->rs485.flags & SER_RS485_RX_DURING_TX))
++              if (atmel_uart_is_half_duplex(port))
+                       atmel_stop_rx(port);
+       if (atmel_use_pdc_tx(port))
+@@ -806,8 +811,7 @@ static void atmel_complete_tx_dma(void *
+        */
+       if (!uart_circ_empty(xmit))
+               atmel_tasklet_schedule(atmel_port, &atmel_port->tasklet_tx);
+-      else if ((port->rs485.flags & SER_RS485_ENABLED) &&
+-               !(port->rs485.flags & SER_RS485_RX_DURING_TX)) {
++      else if (atmel_uart_is_half_duplex(port)) {
+               /* DMA done, stop TX, start RX for RS485 */
+               atmel_start_rx(port);
+       }
+@@ -1383,8 +1387,7 @@ static void atmel_tx_pdc(struct uart_por
+               atmel_uart_writel(port, ATMEL_US_IER,
+                                 atmel_port->tx_done_mask);
+       } else {
+-              if ((port->rs485.flags & SER_RS485_ENABLED) &&
+-                  !(port->rs485.flags & SER_RS485_RX_DURING_TX)) {
++              if (atmel_uart_is_half_duplex(port)) {
+                       /* DMA done, stop TX, start RX for RS485 */
+                       atmel_start_rx(port);
+               }