aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJon Hunter <jonathanh@nvidia.com>2018-07-03 04:55:43 -0400
committerWolfram Sang <wsa@the-dreams.de>2018-07-09 18:20:47 -0400
commit54836e2d03e76d80aec3399368ffaf5b7caadd1b (patch)
tree8369a9e28bbf81801033ef079d3b89e56735088f
parentdbd39cf4249316c4089b8987f20850763ebbf43e (diff)
i2c: tegra: Fix NACK error handling
On Tegra30 Cardhu the PCA9546 I2C mux is not ACK'ing I2C commands on resume from suspend (which is caused by the reset signal for the I2C mux not being configured correctl). However, this NACK is causing the Tegra30 to hang on resuming from suspend which is not expected as we detect NACKs and handle them. The hang observed appears to occur when resetting the I2C controller to recover from the NACK. Commit 77821b4678f9 ("i2c: tegra: proper handling of error cases") added additional error handling for some error cases including NACK, however, it appears that this change conflicts with an early fix by commit f70893d08338 ("i2c: tegra: Add delay before resetting the controller after NACK"). After commit 77821b4678f9 was made we now disable 'packet mode' before the delay from commit f70893d08338 happens. Testing shows that moving the delay to before disabling 'packet mode' fixes the hang observed on Tegra30. The delay was added to give the I2C controller chance to send a stop condition and so it makes sense to move this to before we disable packet mode. Please note that packet mode is always enabled for Tegra. Fixes: 77821b4678f9 ("i2c: tegra: proper handling of error cases") Signed-off-by: Jon Hunter <jonathanh@nvidia.com> Acked-by: Thierry Reding <treding@nvidia.com> Signed-off-by: Wolfram Sang <wsa@the-dreams.de> Cc: stable@vger.kernel.org
-rw-r--r--drivers/i2c/busses/i2c-tegra.c17
1 files changed, 8 insertions, 9 deletions
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)