2022-06-06 10:26:23

by Ilpo Järvinen

[permalink] [raw]
Subject: [PATCH 01/36] serial: Add uart_rs485_config()

A few serial drivers make a call to rs485_config() themselves (all
these seem to relate to init). Convert them all to use a common helper
which makes it easy to make adjustments on tasks related to it as
serial_rs485 struct sanitization is going to be added.

In pci_fintek_setup() (in 8250_pci.c), the rs485_config() call was made
with NULL, however, it can be changed to pass uart_port's rs485 struct.
No other callers should pass NULL into rs485_config() so the NULL check
can now be eliminated.

Signed-off-by: Ilpo Järvinen <[email protected]>
---
drivers/tty/serial/8250/8250_pci.c | 6 ++----
drivers/tty/serial/8250/8250_port.c | 2 +-
drivers/tty/serial/fsl_lpuart.c | 2 +-
drivers/tty/serial/imx.c | 2 +-
drivers/tty/serial/serial_core.c | 6 ++++++
include/linux/serial_core.h | 1 +
6 files changed, 12 insertions(+), 7 deletions(-)

diff --git a/drivers/tty/serial/8250/8250_pci.c b/drivers/tty/serial/8250/8250_pci.c
index a17619db7939..fb0a49e39072 100644
--- a/drivers/tty/serial/8250/8250_pci.c
+++ b/drivers/tty/serial/8250/8250_pci.c
@@ -1562,9 +1562,7 @@ static int pci_fintek_rs485_config(struct uart_port *port,

pci_read_config_byte(pci_dev, 0x40 + 8 * *index + 7, &setting);

- if (!rs485)
- rs485 = &port->rs485;
- else if (rs485->flags & SER_RS485_ENABLED)
+ if (rs485->flags & SER_RS485_ENABLED)
memset(rs485->padding, 0, sizeof(rs485->padding));
else
memset(rs485, 0, sizeof(*rs485));
@@ -1689,7 +1687,7 @@ static int pci_fintek_init(struct pci_dev *dev)
* pciserial_resume_ports()
*/
port = serial8250_get_port(priv->line[i]);
- pci_fintek_rs485_config(&port->port, NULL);
+ uart_rs485_config(&port->port);
} else {
/* First init without port data
* force init to RS232 Mode
diff --git a/drivers/tty/serial/8250/8250_port.c b/drivers/tty/serial/8250/8250_port.c
index 78b6dedc43e6..d7384ab364d2 100644
--- a/drivers/tty/serial/8250/8250_port.c
+++ b/drivers/tty/serial/8250/8250_port.c
@@ -3199,7 +3199,7 @@ static void serial8250_config_port(struct uart_port *port, int flags)
autoconfig(up);

if (port->rs485.flags & SER_RS485_ENABLED)
- port->rs485_config(port, &port->rs485);
+ uart_rs485_config(port);

/* if access method is AU, it is a 16550 with a quirk */
if (port->type == PORT_16550A && port->iotype == UPIO_AU)
diff --git a/drivers/tty/serial/fsl_lpuart.c b/drivers/tty/serial/fsl_lpuart.c
index 0d6e62f6bb07..509a7912fa9d 100644
--- a/drivers/tty/serial/fsl_lpuart.c
+++ b/drivers/tty/serial/fsl_lpuart.c
@@ -2724,7 +2724,7 @@ static int lpuart_probe(struct platform_device *pdev)
sport->port.rs485.delay_rts_after_send)
dev_err(&pdev->dev, "driver doesn't support RTS delays\n");

- sport->port.rs485_config(&sport->port, &sport->port.rs485);
+ uart_rs485_config(&sport->port);

ret = devm_request_irq(&pdev->dev, sport->port.irq, handler, 0,
DRIVER_NAME, sport);
diff --git a/drivers/tty/serial/imx.c b/drivers/tty/serial/imx.c
index 7d2094dc5a59..9ce09b81ac9b 100644
--- a/drivers/tty/serial/imx.c
+++ b/drivers/tty/serial/imx.c
@@ -2338,7 +2338,7 @@ static int imx_uart_probe(struct platform_device *pdev)
dev_err(&pdev->dev,
"low-active RTS not possible when receiver is off, enabling receiver\n");

- imx_uart_rs485_config(&sport->port, &sport->port.rs485);
+ uart_rs485_config(&sport->port);

/* Disable interrupts before requesting them */
ucr1 = imx_uart_readl(sport, UCR1);
diff --git a/drivers/tty/serial/serial_core.c b/drivers/tty/serial/serial_core.c
index 9a85b41caa0a..8466181db4e9 100644
--- a/drivers/tty/serial/serial_core.c
+++ b/drivers/tty/serial/serial_core.c
@@ -1276,6 +1276,12 @@ static int uart_get_icount(struct tty_struct *tty,
return 0;
}

+int uart_rs485_config(struct uart_port *port)
+{
+ return port->rs485_config(port, &port->rs485);
+}
+EXPORT_SYMBOL_GPL(uart_rs485_config);
+
static int uart_get_rs485_config(struct uart_port *port,
struct serial_rs485 __user *rs485)
{
diff --git a/include/linux/serial_core.h b/include/linux/serial_core.h
index cbd5070bc87f..d3ebb4db2d80 100644
--- a/include/linux/serial_core.h
+++ b/include/linux/serial_core.h
@@ -592,4 +592,5 @@ static inline int uart_handle_break(struct uart_port *port)
!((cflag) & CLOCAL))

int uart_get_rs485_mode(struct uart_port *port);
+int uart_rs485_config(struct uart_port *port);
#endif /* LINUX_SERIAL_CORE_H */
--
2.30.2


2022-06-25 20:42:42

by Lukas Wunner

[permalink] [raw]
Subject: Re: [PATCH 01/36] serial: Add uart_rs485_config()

On Mon, Jun 06, 2022 at 01:03:58PM +0300, Ilpo J?rvinen wrote:
> A few serial drivers make a call to rs485_config() themselves (all
> these seem to relate to init). Convert them all to use a common helper
> which makes it easy to make adjustments on tasks related to it as
> serial_rs485 struct sanitization is going to be added.
[...]
--- a/drivers/tty/serial/serial_core.c
> +++ b/drivers/tty/serial/serial_core.c
> @@ -1276,6 +1276,12 @@ static int uart_get_icount(struct tty_struct *tty,
> return 0;
> }
>
> +int uart_rs485_config(struct uart_port *port)
> +{
> + return port->rs485_config(port, &port->rs485);
> +}
> +EXPORT_SYMBOL_GPL(uart_rs485_config);

Why doesn't this helper acquire the port spinlock, unlike
uart_set_rs485_config()? Is this safe? Do all callers hold the lock?
Do we need an assertion to verify the lock is held?

Thanks,

Lukas

2022-06-26 12:47:58

by Lino Sanfilippo

[permalink] [raw]
Subject: Re: [PATCH 01/36] serial: Add uart_rs485_config()

On 25.06.22 at 22:19, Lukas Wunner wrote:

>
> Why doesn't this helper acquire the port spinlock, unlike
> uart_set_rs485_config()? Is this safe? Do all callers hold the lock?
> Do we need an assertion to verify the lock is held?
>

AFAIU the callers are using this only during initialization, so there is nothing else
at this time that accesses the serial_rs485 struct and thus no need for locking.

Regards,
Lino