diff options
author | Yixun Lan <dlan@gentoo.org> | 2017-09-06 21:52:39 +0800 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2017-09-18 18:31:48 +0200 |
commit | b86ac225037900963b1203344e5d129f5af6bbd2 (patch) | |
tree | 4c0e0ccf9cb5323dd631752d2bf2de5d2a880807 /drivers/tty/serial/meson_uart.c | |
parent | 2bd6bf03f4c1c59381d62c61d03f6cc3fe71f66e (diff) | |
download | linux-b86ac225037900963b1203344e5d129f5af6bbd2.tar.gz linux-b86ac225037900963b1203344e5d129f5af6bbd2.tar.bz2 linux-b86ac225037900963b1203344e5d129f5af6bbd2.zip |
serial: meson: add Magic SysRq support
This dirver try to implement the Magic SysRq support[1] for
Amlogic Inc's meson platfo
>From the hardware perspective, the UART IP can't detect the 'BREAK' command
clearly via the status register. Instead, we rely on the combination of
'FRAME_ERR bit && ch == 0', and it works fine.
[1] Documentation/admin-guide/sysrq.rst
Signed-off-by: Yixun Lan <dlan@gentoo.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/tty/serial/meson_uart.c')
-rw-r--r-- | drivers/tty/serial/meson_uart.c | 18 |
1 files changed, 16 insertions, 2 deletions
diff --git a/drivers/tty/serial/meson_uart.c b/drivers/tty/serial/meson_uart.c index 07c0f98be3ac..95d242a7dae1 100644 --- a/drivers/tty/serial/meson_uart.c +++ b/drivers/tty/serial/meson_uart.c @@ -14,6 +14,10 @@ * */ +#if defined(CONFIG_SERIAL_MESON_CONSOLE) && defined(CONFIG_MAGIC_SYSRQ) +#define SUPPORT_SYSRQ +#endif + #include <linux/clk.h> #include <linux/console.h> #include <linux/delay.h> @@ -183,12 +187,12 @@ static void meson_receive_chars(struct uart_port *port) { struct tty_port *tport = &port->state->port; char flag; - u32 status, ch, mode; + u32 ostatus, status, ch, mode; do { flag = TTY_NORMAL; port->icount.rx++; - status = readl(port->membase + AML_UART_STATUS); + ostatus = status = readl(port->membase + AML_UART_STATUS); if (status & AML_UART_ERR) { if (status & AML_UART_TX_FIFO_WERR) @@ -216,6 +220,16 @@ static void meson_receive_chars(struct uart_port *port) ch = readl(port->membase + AML_UART_RFIFO); ch &= 0xff; + if ((ostatus & AML_UART_FRAME_ERR) && (ch == 0)) { + port->icount.brk++; + flag = TTY_BREAK; + if (uart_handle_break(port)) + continue; + } + + if (uart_handle_sysrq_char(port, ch)) + continue; + if ((status & port->ignore_status_mask) == 0) tty_insert_flip_char(tport, ch, flag); |