- if (fifo_isfull(&hw->serial->rxfifo))
- hw->serial->status |= SERRF_RXFIFOOVERRUN;
- else
- fifo_push(&hw->serial->rxfifo, regs->DR);
+ /*
+ * Serial IRQ can happen for two reason: data ready (RDRF) or overrun (OR)
+ * If the data is ready, we need to fetch it from the data register or
+ * the interrupt will retrigger immediatly. In case of overrun, instead,
+ * the value of the data register is meaningless.
+ */
+ if (regs->SR & REG_SCI_SR_RDRF)
+ {
+ unsigned char data = regs->DR;
+
+ if (fifo_isfull(&hw->serial->rxfifo))
+ hw->serial->status |= SERRF_RXFIFOOVERRUN;
+ else
+ fifo_push(&hw->serial->rxfifo, data);
+ }