Commit 597fe310 authored by Shinya Kuribayashi's avatar Shinya Kuribayashi Committed by Ben Dooks

i2c-designware: Skip RX_FULL and TX_EMPTY bits on tx abort errors

Suppose TX_ABRT occurs in the middle of processing i2c_msg msgs[], and
a STOP condition has already been generated on the bus.  In this case,
subsequent i2c_dw_xfer_msg() might initiate a new and unnecessary I2C
transaction, which we'd have to avoid.

Furthermore, anytime TX_ABRT is set, the contents of tx/rx buffers are
flushed, so we don't have to process RX_FULL and TX_EMPTY.

Disable interrupts, and skip them.
Signed-off-by: default avatarShinya Kuribayashi <shinya.kuribayashi@necel.com>
Signed-off-by: default avatarBen Dooks <ben-linux@fluff.org>
parent 8f588e40
...@@ -621,6 +621,13 @@ static irqreturn_t i2c_dw_isr(int this_irq, void *dev_id) ...@@ -621,6 +621,13 @@ static irqreturn_t i2c_dw_isr(int this_irq, void *dev_id)
if (stat & DW_IC_INTR_TX_ABRT) { if (stat & DW_IC_INTR_TX_ABRT) {
dev->cmd_err |= DW_IC_ERR_TX_ABRT; dev->cmd_err |= DW_IC_ERR_TX_ABRT;
dev->status = STATUS_IDLE; dev->status = STATUS_IDLE;
/*
* Anytime TX_ABRT is set, the contents of the tx/rx
* buffers are flushed. Make sure to skip them.
*/
writel(0, dev->base + DW_IC_INTR_MASK);
goto tx_aborted;
} }
if (stat & DW_IC_INTR_RX_FULL) if (stat & DW_IC_INTR_RX_FULL)
...@@ -635,6 +642,7 @@ static irqreturn_t i2c_dw_isr(int this_irq, void *dev_id) ...@@ -635,6 +642,7 @@ static irqreturn_t i2c_dw_isr(int this_irq, void *dev_id)
* the current transmit status. * the current transmit status.
*/ */
tx_aborted:
if ((stat & (DW_IC_INTR_TX_ABRT | DW_IC_INTR_STOP_DET)) || dev->msg_err) if ((stat & (DW_IC_INTR_TX_ABRT | DW_IC_INTR_STOP_DET)) || dev->msg_err)
complete(&dev->cmd_complete); complete(&dev->cmd_complete);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment