Message ID | 20220420075924.14546-5-shubhrajyoti.datta@xilinx.com |
---|---|
State | Accepted |
Headers | show |
Series | i2c: xiic: misc fixes | expand |
On 4/20/22 09:59, Shubhrajyoti Datta wrote: > From: Raviteja Narayanam <raviteja.narayanam@xilinx.com> > > When a group of messages are sent from user space as a set, if > the last message has less than Tx FIFO DEPTH number of bytes > to transfer, Tx half empty interrupt is triggered continuously > from the hardware. It is due to Bus not busy interrupt coming > along with Tx half empty and tx empty. > > Hence, service the Tx interrupts before Bus not busy interrupt > to update the i2c message status correctly. > > Signed-off-by: Raviteja Narayanam <raviteja.narayanam@xilinx.com> > Signed-off-by: Shubhrajyoti Datta <shubhrajyoti.datta@xilinx.com> > --- > drivers/i2c/busses/i2c-xiic.c | 38 ++++++++++++++++++----------------- > 1 file changed, 20 insertions(+), 18 deletions(-) > > diff --git a/drivers/i2c/busses/i2c-xiic.c b/drivers/i2c/busses/i2c-xiic.c > index eb4d34e7c0fe..953f7cffe0d8 100644 > --- a/drivers/i2c/busses/i2c-xiic.c > +++ b/drivers/i2c/busses/i2c-xiic.c > @@ -468,24 +468,6 @@ static irqreturn_t xiic_process(int irq, void *dev_id) > } > } > } > - if (pend & XIIC_INTR_BNB_MASK) { > - /* IIC bus has transitioned to not busy */ > - clr |= XIIC_INTR_BNB_MASK; > - > - /* The bus is not busy, disable BusNotBusy interrupt */ > - xiic_irq_dis(i2c, XIIC_INTR_BNB_MASK); > - > - if (!i2c->tx_msg) > - goto out; > - > - wakeup_req = 1; > - > - if (i2c->nmsgs == 1 && !i2c->rx_msg && > - xiic_tx_space(i2c) == 0) > - wakeup_code = STATE_DONE; > - else > - wakeup_code = STATE_ERROR; > - } > if (pend & (XIIC_INTR_TX_EMPTY_MASK | XIIC_INTR_TX_HALF_MASK)) { > /* Transmit register/FIFO is empty or ½ empty */ > > @@ -522,6 +504,26 @@ static irqreturn_t xiic_process(int irq, void *dev_id) > */ > xiic_irq_dis(i2c, XIIC_INTR_TX_HALF_MASK); > } > + > + if (pend & XIIC_INTR_BNB_MASK) { > + /* IIC bus has transitioned to not busy */ > + clr |= XIIC_INTR_BNB_MASK; > + > + /* The bus is not busy, disable BusNotBusy interrupt */ > + xiic_irq_dis(i2c, XIIC_INTR_BNB_MASK); > + > + if (!i2c->tx_msg) > + goto out; > + > + wakeup_req = 1; > + > + if (i2c->nmsgs == 1 && !i2c->rx_msg && > + xiic_tx_space(i2c) == 0) > + wakeup_code = STATE_DONE; > + else > + wakeup_code = STATE_ERROR; > + } > + > out: > dev_dbg(i2c->adap.dev.parent, "%s clr: 0x%x\n", __func__, clr); > Acked-by: Michal Simek <michal.simek@xilinx.com> Thanks, Michal
On Wed, Apr 20, 2022 at 01:29:24PM +0530, Shubhrajyoti Datta wrote: > From: Raviteja Narayanam <raviteja.narayanam@xilinx.com> > > When a group of messages are sent from user space as a set, if > the last message has less than Tx FIFO DEPTH number of bytes > to transfer, Tx half empty interrupt is triggered continuously > from the hardware. It is due to Bus not busy interrupt coming > along with Tx half empty and tx empty. > > Hence, service the Tx interrupts before Bus not busy interrupt > to update the i2c message status correctly. > > Signed-off-by: Raviteja Narayanam <raviteja.narayanam@xilinx.com> > Signed-off-by: Shubhrajyoti Datta <shubhrajyoti.datta@xilinx.com> Applied to for-next, thanks!
diff --git a/drivers/i2c/busses/i2c-xiic.c b/drivers/i2c/busses/i2c-xiic.c index eb4d34e7c0fe..953f7cffe0d8 100644 --- a/drivers/i2c/busses/i2c-xiic.c +++ b/drivers/i2c/busses/i2c-xiic.c @@ -468,24 +468,6 @@ static irqreturn_t xiic_process(int irq, void *dev_id) } } } - if (pend & XIIC_INTR_BNB_MASK) { - /* IIC bus has transitioned to not busy */ - clr |= XIIC_INTR_BNB_MASK; - - /* The bus is not busy, disable BusNotBusy interrupt */ - xiic_irq_dis(i2c, XIIC_INTR_BNB_MASK); - - if (!i2c->tx_msg) - goto out; - - wakeup_req = 1; - - if (i2c->nmsgs == 1 && !i2c->rx_msg && - xiic_tx_space(i2c) == 0) - wakeup_code = STATE_DONE; - else - wakeup_code = STATE_ERROR; - } if (pend & (XIIC_INTR_TX_EMPTY_MASK | XIIC_INTR_TX_HALF_MASK)) { /* Transmit register/FIFO is empty or ½ empty */ @@ -522,6 +504,26 @@ static irqreturn_t xiic_process(int irq, void *dev_id) */ xiic_irq_dis(i2c, XIIC_INTR_TX_HALF_MASK); } + + if (pend & XIIC_INTR_BNB_MASK) { + /* IIC bus has transitioned to not busy */ + clr |= XIIC_INTR_BNB_MASK; + + /* The bus is not busy, disable BusNotBusy interrupt */ + xiic_irq_dis(i2c, XIIC_INTR_BNB_MASK); + + if (!i2c->tx_msg) + goto out; + + wakeup_req = 1; + + if (i2c->nmsgs == 1 && !i2c->rx_msg && + xiic_tx_space(i2c) == 0) + wakeup_code = STATE_DONE; + else + wakeup_code = STATE_ERROR; + } + out: dev_dbg(i2c->adap.dev.parent, "%s clr: 0x%x\n", __func__, clr);