Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 7485d26b authored by Laurent Pinchart's avatar Laurent Pinchart Committed by Kumar Gala
Browse files

cpm_uart: Modem control lines support



This patch replaces the get_mctrl/set_mctrl stubs with modem control line
read/write access through the GPIO lib.

Available modem control lines are described in the device tree using GPIO
bindings. The driver expect a GPIO pin for each of the CTS, RTS, DCD, DSR,
DTR and RI signals. Unused control lines can be left out.

Signed-off-by: default avatarLaurent Pinchart <laurentp@cse-semaphore.com>
Signed-off-by: default avatarKumar Gala <galak@kernel.crashing.org>
parent dc2380ec
Loading
Loading
Loading
Loading
+11 −0
Original line number Diff line number Diff line
@@ -7,6 +7,15 @@ Currently defined compatibles:
- fsl,cpm2-scc-uart
- fsl,qe-uart

Modem control lines connected to GPIO controllers are listed in the gpios
property as described in booting-without-of.txt, section IX.1 in the following
order:

CTS, RTS, DCD, DSR, DTR, and RI.

The gpios property is optional and can be left out when control lines are
not used.

Example:

	serial@11a00 {
@@ -18,4 +27,6 @@ Example:
		interrupt-parent = <&PIC>;
		fsl,cpm-brg = <1>;
		fsl,cpm-command = <00800000>;
		gpios = <&gpio_c 15 0
			 &gpio_d 29 0>;
	};
+10 −0
Original line number Diff line number Diff line
@@ -50,6 +50,15 @@

#define SCC_WAIT_CLOSING 100

#define GPIO_CTS	0
#define GPIO_RTS	1
#define GPIO_DCD	2
#define GPIO_DSR	3
#define GPIO_DTR	4
#define GPIO_RI		5

#define NUM_GPIOS	(GPIO_RI+1)

struct uart_cpm_port {
	struct uart_port	port;
	u16			rx_nrfifos;
@@ -82,6 +91,7 @@ struct uart_cpm_port {
	int			wait_closing;
	/* value to combine with opcode to form cpm command */
	u32			command;
	int			gpios[NUM_GPIOS];
};

extern int cpm_uart_nr;
+37 −3
Original line number Diff line number Diff line
@@ -43,6 +43,8 @@
#include <linux/dma-mapping.h>
#include <linux/fs_uart_pd.h>
#include <linux/of_platform.h>
#include <linux/gpio.h>
#include <linux/of_gpio.h>

#include <asm/io.h>
#include <asm/irq.h>
@@ -96,13 +98,41 @@ static unsigned int cpm_uart_tx_empty(struct uart_port *port)

static void cpm_uart_set_mctrl(struct uart_port *port, unsigned int mctrl)
{
	/* Whee. Do nothing. */
	struct uart_cpm_port *pinfo = (struct uart_cpm_port *)port;

	if (pinfo->gpios[GPIO_RTS] >= 0)
		gpio_set_value(pinfo->gpios[GPIO_RTS], !(mctrl & TIOCM_RTS));

	if (pinfo->gpios[GPIO_DTR] >= 0)
		gpio_set_value(pinfo->gpios[GPIO_DTR], !(mctrl & TIOCM_DTR));
}

static unsigned int cpm_uart_get_mctrl(struct uart_port *port)
{
	/* Whee. Do nothing. */
	return TIOCM_CAR | TIOCM_DSR | TIOCM_CTS;
	struct uart_cpm_port *pinfo = (struct uart_cpm_port *)port;
	unsigned int mctrl = TIOCM_CTS | TIOCM_DSR | TIOCM_CAR;

	if (pinfo->gpios[GPIO_CTS] >= 0) {
		if (gpio_get_value(pinfo->gpios[GPIO_CTS]))
			mctrl &= ~TIOCM_CTS;
	}

	if (pinfo->gpios[GPIO_DSR] >= 0) {
		if (gpio_get_value(pinfo->gpios[GPIO_DSR]))
			mctrl &= ~TIOCM_DSR;
	}

	if (pinfo->gpios[GPIO_DCD] >= 0) {
		if (gpio_get_value(pinfo->gpios[GPIO_DCD]))
			mctrl &= ~TIOCM_CAR;
	}

	if (pinfo->gpios[GPIO_RI] >= 0) {
		if (!gpio_get_value(pinfo->gpios[GPIO_RI]))
			mctrl |= TIOCM_RNG;
	}

	return mctrl;
}

/*
@@ -991,6 +1021,7 @@ static int cpm_uart_init_port(struct device_node *np,
	void __iomem *mem, *pram;
	int len;
	int ret;
	int i;

	data = of_get_property(np, "fsl,cpm-brg", &len);
	if (!data || len != 4) {
@@ -1050,6 +1081,9 @@ static int cpm_uart_init_port(struct device_node *np,
		goto out_pram;
	}

	for (i = 0; i < NUM_GPIOS; i++)
		pinfo->gpios[i] = of_get_gpio(np, i);

	return cpm_uart_request_port(&pinfo->port);

out_pram: