aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2018-07-13 18:34:29 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2018-07-13 18:34:29 -0400
commit2db39a2f491a48ec740e0214a7dd584eefc2137d (patch)
tree02bb3727ae2442d0146558cfd02b231783b767d1
parent3951dbf232e8500bef27f77437fd5d04b67cc6d1 (diff)
parentabe41184abac487264a4904bfcff2d5500dccce6 (diff)
Merge branch 'i2c/for-current' of git://git.kernel.org/pub/scm/linux/kernel/git/wsa/linux
Pull i2c fixes from Wolfram Sang: - I2C core bugfix regarding bus recovery - driver bugfix for the tegra driver - typo correction * 'i2c/for-current' of git://git.kernel.org/pub/scm/linux/kernel/git/wsa/linux: i2c: recovery: if possible send STOP with recovery pulses i2c: tegra: Fix NACK error handling i2c: stu300: use non-archaic spelling of failes
-rw-r--r--drivers/i2c/busses/i2c-stu300.c2
-rw-r--r--drivers/i2c/busses/i2c-tegra.c17
-rw-r--r--drivers/i2c/i2c-core-base.c11
3 files changed, 19 insertions, 11 deletions
diff --git a/drivers/i2c/busses/i2c-stu300.c b/drivers/i2c/busses/i2c-stu300.c
index e866c481bfc3..fce52bdab2b7 100644
--- a/drivers/i2c/busses/i2c-stu300.c
+++ b/drivers/i2c/busses/i2c-stu300.c
@@ -127,7 +127,7 @@ enum stu300_error {
127 127
128/* 128/*
129 * The number of address send athemps tried before giving up. 129 * The number of address send athemps tried before giving up.
130 * If the first one failes it seems like 5 to 8 attempts are required. 130 * If the first one fails it seems like 5 to 8 attempts are required.
131 */ 131 */
132#define NUM_ADDR_RESEND_ATTEMPTS 12 132#define NUM_ADDR_RESEND_ATTEMPTS 12
133 133
diff --git a/drivers/i2c/busses/i2c-tegra.c b/drivers/i2c/busses/i2c-tegra.c
index 5fccd1f1bca8..797def5319f1 100644
--- a/drivers/i2c/busses/i2c-tegra.c
+++ b/drivers/i2c/busses/i2c-tegra.c
@@ -545,6 +545,14 @@ static int tegra_i2c_disable_packet_mode(struct tegra_i2c_dev *i2c_dev)
545{ 545{
546 u32 cnfg; 546 u32 cnfg;
547 547
548 /*
549 * NACK interrupt is generated before the I2C controller generates
550 * the STOP condition on the bus. So wait for 2 clock periods
551 * before disabling the controller so that the STOP condition has
552 * been delivered properly.
553 */
554 udelay(DIV_ROUND_UP(2 * 1000000, i2c_dev->bus_clk_rate));
555
548 cnfg = i2c_readl(i2c_dev, I2C_CNFG); 556 cnfg = i2c_readl(i2c_dev, I2C_CNFG);
549 if (cnfg & I2C_CNFG_PACKET_MODE_EN) 557 if (cnfg & I2C_CNFG_PACKET_MODE_EN)
550 i2c_writel(i2c_dev, cnfg & ~I2C_CNFG_PACKET_MODE_EN, I2C_CNFG); 558 i2c_writel(i2c_dev, cnfg & ~I2C_CNFG_PACKET_MODE_EN, I2C_CNFG);
@@ -706,15 +714,6 @@ static int tegra_i2c_xfer_msg(struct tegra_i2c_dev *i2c_dev,
706 if (likely(i2c_dev->msg_err == I2C_ERR_NONE)) 714 if (likely(i2c_dev->msg_err == I2C_ERR_NONE))
707 return 0; 715 return 0;
708 716
709 /*
710 * NACK interrupt is generated before the I2C controller generates
711 * the STOP condition on the bus. So wait for 2 clock periods
712 * before resetting the controller so that the STOP condition has
713 * been delivered properly.
714 */
715 if (i2c_dev->msg_err == I2C_ERR_NO_ACK)
716 udelay(DIV_ROUND_UP(2 * 1000000, i2c_dev->bus_clk_rate));
717
718 tegra_i2c_init(i2c_dev); 717 tegra_i2c_init(i2c_dev);
719 if (i2c_dev->msg_err == I2C_ERR_NO_ACK) { 718 if (i2c_dev->msg_err == I2C_ERR_NO_ACK) {
720 if (msg->flags & I2C_M_IGNORE_NAK) 719 if (msg->flags & I2C_M_IGNORE_NAK)
diff --git a/drivers/i2c/i2c-core-base.c b/drivers/i2c/i2c-core-base.c
index 31d16ada6e7d..301285c54603 100644
--- a/drivers/i2c/i2c-core-base.c
+++ b/drivers/i2c/i2c-core-base.c
@@ -198,7 +198,16 @@ int i2c_generic_scl_recovery(struct i2c_adapter *adap)
198 198
199 val = !val; 199 val = !val;
200 bri->set_scl(adap, val); 200 bri->set_scl(adap, val);
201 ndelay(RECOVERY_NDELAY); 201
202 /*
203 * If we can set SDA, we will always create STOP here to ensure
204 * the additional pulses will do no harm. This is achieved by
205 * letting SDA follow SCL half a cycle later.
206 */
207 ndelay(RECOVERY_NDELAY / 2);
208 if (bri->set_sda)
209 bri->set_sda(adap, val);
210 ndelay(RECOVERY_NDELAY / 2);
202 } 211 }
203 212
204 /* check if recovery actually succeeded */ 213 /* check if recovery actually succeeded */