summaryrefslogtreecommitdiff
path: root/drivers/i2c
diff options
context:
space:
mode:
authorJae Hyun Yoo <jae.hyun.yoo@intel.com>2019-07-12 00:04:39 +0300
committerJae Hyun Yoo <jae.hyun.yoo@linux.intel.com>2021-11-05 10:22:08 +0300
commite5a672c1c0e433d986acbb21af8ebb7a92e51554 (patch)
treea4e669613af5aec13991748876a2c087e4d7e3df /drivers/i2c
parentba4c2f110fac5748ec409eff41f5c457e68826de (diff)
downloadlinux-e5a672c1c0e433d986acbb21af8ebb7a92e51554.tar.xz
i2c: aspeed: add SLAVE_ADDR_RECEIVED_PENDING interrupt handling
If a peer master sends messages too quickly before it processes previous slave DMA data handling, this indicator will be set. It's just a indicator and driver can't recover this case so just ignore it. Signed-off-by: Jae Hyun Yoo <jae.hyun.yoo@intel.com>
Diffstat (limited to 'drivers/i2c')
-rw-r--r--drivers/i2c/busses/i2c-aspeed.c13
1 files changed, 13 insertions, 0 deletions
diff --git a/drivers/i2c/busses/i2c-aspeed.c b/drivers/i2c/busses/i2c-aspeed.c
index f5a7a008270c..1354e2b04cdf 100644
--- a/drivers/i2c/busses/i2c-aspeed.c
+++ b/drivers/i2c/busses/i2c-aspeed.c
@@ -88,6 +88,7 @@
* status bits.
*/
#define ASPEED_I2CD_INTR_RECV_MASK 0xf000ffff
+#define ASPEED_I2CD_INTR_SLAVE_ADDR_RECEIVED_PENDING BIT(30)
#define ASPEED_I2CD_INTR_SLAVE_INACTIVE_TIMEOUT BIT(15)
#define ASPEED_I2CD_INTR_SDA_DL_TIMEOUT BIT(14)
#define ASPEED_I2CD_INTR_BUS_RECOVER_DONE BIT(13)
@@ -472,6 +473,18 @@ static u32 aspeed_i2c_slave_irq(struct aspeed_i2c_bus *bus, u32 irq_status)
dev_dbg(bus->dev, "slave irq status 0x%08x, cmd 0x%08x\n",
irq_status, command);
+ /*
+ * If a peer master sends messages too quickly before it processes
+ * previous slave DMA data handling, this indicator will be set. It's
+ * just a indicator and driver can't recover this case so just ignore
+ * it.
+ */
+ if (unlikely(irq_status &
+ ASPEED_I2CD_INTR_SLAVE_ADDR_RECEIVED_PENDING)) {
+ dev_dbg(bus->dev, "A slave addr match interrupt is pending.\n");
+ irq_handled |= ASPEED_I2CD_INTR_SLAVE_ADDR_RECEIVED_PENDING;
+ }
+
/* Slave was sent something. */
if (irq_status & ASPEED_I2CD_INTR_RX_DONE) {
aspeed_i2c_slave_handle_rx_done(bus, irq_status, &value);