From: Mikko Perttunen mperttunen@nvidia.com
commit 27b7c6e096264cc7b91bb80a4f65f8c0a66f079f upstream.
Upon a communication error, the interrupt handler can call tegra_i2c_disable_packet_mode. This causes a sleeping poll to happen unless the current transaction was marked atomic. Fix this by making the poll happen atomically if we are in an IRQ.
This matches the behavior prior to the patch mentioned in the Fixes tag.
Fixes: ede2299f7101 ("i2c: tegra: Support atomic transfers") Cc: stable@vger.kernel.org Signed-off-by: Mikko Perttunen mperttunen@nvidia.com Reviewed-by: Dmitry Osipenko digetx@gmail.com Signed-off-by: Wolfram Sang wsa@kernel.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org
--- drivers/i2c/busses/i2c-tegra.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
--- a/drivers/i2c/busses/i2c-tegra.c +++ b/drivers/i2c/busses/i2c-tegra.c @@ -533,7 +533,7 @@ static int tegra_i2c_poll_register(struc void __iomem *addr = i2c_dev->base + tegra_i2c_reg_addr(i2c_dev, reg); u32 val;
- if (!i2c_dev->atomic_mode) + if (!i2c_dev->atomic_mode && !in_irq()) return readl_relaxed_poll_timeout(addr, val, !(val & mask), delay_us, timeout_us);