提交 87515772 编写于 作者: P Peter Hurley 提交者: Greg Kroah-Hartman

earlycon: 8250: Fix command line regression

Restore undocumented behavior of kernel command line parameters of
the forms:
    console=uart[8250],io|mmio|mmio32,<addr>[,options]
    console=uart[8250],<addr>[,options]
where 'options' have not been specified; in this case, the hardware
is assumed to be initialized.

Fixes: c7cef0a8 ("console: Add extensible console matching")
Reported-by: NYinghai Lu <yinghai@kernel.org>
Signed-off-by: NPeter Hurley <peter@hurleysoftware.com>
Signed-off-by: NGreg Kroah-Hartman <gregkh@linuxfoundation.org>
上级 99492c39
...@@ -3412,9 +3412,23 @@ static void univ8250_console_write(struct console *co, const char *s, ...@@ -3412,9 +3412,23 @@ static void univ8250_console_write(struct console *co, const char *s,
serial8250_console_write(up, s, count); serial8250_console_write(up, s, count);
} }
static int serial8250_console_setup(struct uart_8250_port *up, char *options) static unsigned int probe_baud(struct uart_port *port)
{
unsigned char lcr, dll, dlm;
unsigned int quot;
lcr = serial_port_in(port, UART_LCR);
serial_port_out(port, UART_LCR, lcr | UART_LCR_DLAB);
dll = serial_port_in(port, UART_DLL);
dlm = serial_port_in(port, UART_DLM);
serial_port_out(port, UART_LCR, lcr);
quot = (dlm << 8) | dll;
return (port->uartclk / 16) / quot;
}
static int serial8250_console_setup(struct uart_port *port, char *options, bool probe)
{ {
struct uart_port *port = &up->port;
int baud = 9600; int baud = 9600;
int bits = 8; int bits = 8;
int parity = 'n'; int parity = 'n';
...@@ -3425,13 +3439,15 @@ static int serial8250_console_setup(struct uart_8250_port *up, char *options) ...@@ -3425,13 +3439,15 @@ static int serial8250_console_setup(struct uart_8250_port *up, char *options)
if (options) if (options)
uart_parse_options(options, &baud, &parity, &bits, &flow); uart_parse_options(options, &baud, &parity, &bits, &flow);
else if (probe)
baud = probe_baud(port);
return uart_set_options(port, port->cons, baud, parity, bits, flow); return uart_set_options(port, port->cons, baud, parity, bits, flow);
} }
static int univ8250_console_setup(struct console *co, char *options) static int univ8250_console_setup(struct console *co, char *options)
{ {
struct uart_8250_port *up; struct uart_port *port;
/* /*
* Check whether an invalid uart number has been specified, and * Check whether an invalid uart number has been specified, and
...@@ -3440,11 +3456,11 @@ static int univ8250_console_setup(struct console *co, char *options) ...@@ -3440,11 +3456,11 @@ static int univ8250_console_setup(struct console *co, char *options)
*/ */
if (co->index >= nr_uarts) if (co->index >= nr_uarts)
co->index = 0; co->index = 0;
up = &serial8250_ports[co->index]; port = &serial8250_ports[co->index].port;
/* link port to console */ /* link port to console */
up->port.cons = co; port->cons = co;
return serial8250_console_setup(up, options); return serial8250_console_setup(port, options, false);
} }
/** /**
...@@ -3491,7 +3507,8 @@ static int univ8250_console_match(struct console *co, char *name, int idx, ...@@ -3491,7 +3507,8 @@ static int univ8250_console_match(struct console *co, char *name, int idx,
continue; continue;
co->index = i; co->index = i;
return univ8250_console_setup(co, options); port->cons = co;
return serial8250_console_setup(port, options, true);
} }
return -ENODEV; return -ENODEV;
......
...@@ -105,21 +105,6 @@ static void __init early_serial8250_write(struct console *console, ...@@ -105,21 +105,6 @@ static void __init early_serial8250_write(struct console *console,
serial8250_early_out(port, UART_IER, ier); serial8250_early_out(port, UART_IER, ier);
} }
static unsigned int __init probe_baud(struct uart_port *port)
{
unsigned char lcr, dll, dlm;
unsigned int quot;
lcr = serial8250_early_in(port, UART_LCR);
serial8250_early_out(port, UART_LCR, lcr | UART_LCR_DLAB);
dll = serial8250_early_in(port, UART_DLL);
dlm = serial8250_early_in(port, UART_DLM);
serial8250_early_out(port, UART_LCR, lcr);
quot = (dlm << 8) | dll;
return (port->uartclk / 16) / quot;
}
static void __init init_port(struct earlycon_device *device) static void __init init_port(struct earlycon_device *device)
{ {
struct uart_port *port = &device->port; struct uart_port *port = &device->port;
...@@ -151,10 +136,6 @@ static int __init early_serial8250_setup(struct earlycon_device *device, ...@@ -151,10 +136,6 @@ static int __init early_serial8250_setup(struct earlycon_device *device,
struct uart_port *port = &device->port; struct uart_port *port = &device->port;
unsigned int ier; unsigned int ier;
device->baud = probe_baud(&device->port);
snprintf(device->options, sizeof(device->options), "%u",
device->baud);
/* assume the device was initialized, only mask interrupts */ /* assume the device was initialized, only mask interrupts */
ier = serial8250_early_in(port, UART_IER); ier = serial8250_early_in(port, UART_IER);
serial8250_early_out(port, UART_IER, ier & UART_IER_UUE); serial8250_early_out(port, UART_IER, ier & UART_IER_UUE);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册