Skip to content

Commit

Permalink
serial: sh-sci: Fix up SCFCR handling.
Browse files Browse the repository at this point in the history
Presently there are a few places that make assumptions about the
existence of SCFCR, which doesn't hold true for several port types. While
generally harmless, this does lead to bogus reads/writes in both the
termios/runtime PM cases that are better off simply never being made in
the first place.

While we're at it, also get rid of a straggling PORT_SCI check that
infers all non-SCI ports contain SCFCR. This doesn't presently have any
impact, but as we're now able to test for the existence of registers
without defering to the port type we future proof for additional port
types.

Signed-off-by: Paul Mundt <lethal@linux-sh.org>
  • Loading branch information
Paul Mundt committed Nov 24, 2011
1 parent a9098b3 commit 0979e0e
Showing 1 changed file with 28 additions and 5 deletions.
33 changes: 28 additions & 5 deletions drivers/tty/serial/sh-sci.c
Original file line number Diff line number Diff line change
Expand Up @@ -1652,6 +1652,7 @@ static unsigned int sci_scbrr_calc(unsigned int algo_id, unsigned int bps,

static void sci_reset(struct uart_port *port)
{
struct plat_sci_reg *reg;
unsigned int status;

do {
Expand All @@ -1660,17 +1661,18 @@ static void sci_reset(struct uart_port *port)

sci_out(port, SCSCR, 0x00); /* TE=0, RE=0, CKE1=0 */

if (port->type != PORT_SCI)
reg = sci_getreg(port, SCFCR);
if (reg->size)
sci_out(port, SCFCR, SCFCR_RFRST | SCFCR_TFRST);
}

static void sci_set_termios(struct uart_port *port, struct ktermios *termios,
struct ktermios *old)
{
struct sci_port *s = to_sci_port(port);
struct plat_sci_reg *reg;
unsigned int baud, smr_val, max_baud;
int t = -1;
u16 scfcr = 0;

/*
* earlyprintk comes here early on with port->uartclk set to zero.
Expand Down Expand Up @@ -1720,7 +1722,18 @@ static void sci_set_termios(struct uart_port *port, struct ktermios *termios,
}

sci_init_pins(port, termios->c_cflag);
sci_out(port, SCFCR, scfcr | ((termios->c_cflag & CRTSCTS) ? SCFCR_MCE : 0));

reg = sci_getreg(port, SCFCR);
if (reg->size) {
unsigned short ctrl;

ctrl = sci_in(port, SCFCR);
if (termios->c_cflag & CRTSCTS)
ctrl |= SCFCR_MCE;
else
ctrl &= ~SCFCR_MCE;
sci_out(port, SCFCR, ctrl);
}

sci_out(port, SCSCR, s->cfg->scscr);

Expand Down Expand Up @@ -2113,9 +2126,16 @@ static int sci_runtime_suspend(struct device *dev)
struct uart_port *port = &sci_port->port;

if (uart_console(port)) {
struct plat_sci_reg *reg;

sci_port->saved_smr = sci_in(port, SCSMR);
sci_port->saved_brr = sci_in(port, SCBRR);
sci_port->saved_fcr = sci_in(port, SCFCR);

reg = sci_getreg(port, SCFCR);
if (reg->size)
sci_port->saved_fcr = sci_in(port, SCFCR);
else
sci_port->saved_fcr = 0;
}
return 0;
}
Expand All @@ -2129,7 +2149,10 @@ static int sci_runtime_resume(struct device *dev)
sci_reset(port);
sci_out(port, SCSMR, sci_port->saved_smr);
sci_out(port, SCBRR, sci_port->saved_brr);
sci_out(port, SCFCR, sci_port->saved_fcr);

if (sci_port->saved_fcr)
sci_out(port, SCFCR, sci_port->saved_fcr);

sci_out(port, SCSCR, sci_port->cfg->scscr);
}
return 0;
Expand Down

0 comments on commit 0979e0e

Please sign in to comment.