summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--drivers/serial/imx.c74
1 files changed, 33 insertions, 41 deletions
diff --git a/drivers/serial/imx.c b/drivers/serial/imx.c
index 06fa54c53fd..c637ae21912 100644
--- a/drivers/serial/imx.c
+++ b/drivers/serial/imx.c
@@ -354,66 +354,58 @@ static irqreturn_t imx_rxint(int irq, void *dev_id)
struct tty_struct *tty = sport->port.info->tty;
unsigned long flags, temp;
- rx = readl(sport->port.membase + URXD0);
spin_lock_irqsave(&sport->port.lock,flags);
- do {
+ while ((rx = readl(sport->port.membase + URXD0)) & URXD_CHARRDY) {
flg = TTY_NORMAL;
sport->port.icount.rx++;
temp = readl(sport->port.membase + USR2);
- if( temp & USR2_BRCD ) {
+ if (temp & USR2_BRCD) {
writel(temp | USR2_BRCD, sport->port.membase + USR2);
- if(uart_handle_break(&sport->port))
- goto ignore_char;
+ if (uart_handle_break(&sport->port))
+ continue;
}
if (uart_handle_sysrq_char
(&sport->port, (unsigned char)rx))
- goto ignore_char;
+ continue;
+
+ if (rx & (URXD_PRERR | URXD_OVRRUN | URXD_FRMERR) ) {
+ if (rx & URXD_PRERR)
+ sport->port.icount.parity++;
+ else if (rx & URXD_FRMERR)
+ sport->port.icount.frame++;
+ if (rx & URXD_OVRRUN)
+ sport->port.icount.overrun++;
+
+ if (rx & sport->port.ignore_status_mask) {
+ if (++ignored > 100)
+ goto out;
+ continue;
+ }
+
+ rx &= sport->port.read_status_mask;
+
+ if (rx & URXD_PRERR)
+ flg = TTY_PARITY;
+ else if (rx & URXD_FRMERR)
+ flg = TTY_FRAME;
+ if (rx & URXD_OVRRUN)
+ flg = TTY_OVERRUN;
- if( rx & (URXD_PRERR | URXD_OVRRUN | URXD_FRMERR) )
- goto handle_error;
+#ifdef SUPPORT_SYSRQ
+ sport->port.sysrq = 0;
+#endif
+ }
- error_return:
tty_insert_flip_char(tty, rx, flg);
-
- ignore_char:
- rx = readl(sport->port.membase + URXD0);
- } while(rx & URXD_CHARRDY);
+ }
out:
spin_unlock_irqrestore(&sport->port.lock,flags);
tty_flip_buffer_push(tty);
return IRQ_HANDLED;
-
-handle_error:
- if (rx & URXD_PRERR)
- sport->port.icount.parity++;
- else if (rx & URXD_FRMERR)
- sport->port.icount.frame++;
- if (rx & URXD_OVRRUN)
- sport->port.icount.overrun++;
-
- if (rx & sport->port.ignore_status_mask) {
- if (++ignored > 100)
- goto out;
- goto ignore_char;
- }
-
- rx &= sport->port.read_status_mask;
-
- if (rx & URXD_PRERR)
- flg = TTY_PARITY;
- else if (rx & URXD_FRMERR)
- flg = TTY_FRAME;
- if (rx & URXD_OVRRUN)
- flg = TTY_OVERRUN;
-
-#ifdef SUPPORT_SYSRQ
- sport->port.sysrq = 0;
-#endif
- goto error_return;
}
/*