summaryrefslogtreecommitdiffstats
path: root/drivers/i2c
diff options
context:
space:
mode:
authorWolfram Sang <wsa+renesas@sang-engineering.com>2018-07-10 23:42:17 +0200
committerWolfram Sang <wsa@the-dreams.de>2018-07-17 10:42:48 +0200
commit0b71026c69caa10261218528326721828d29a481 (patch)
treeeb0d0bd98fb7b59026a82e1dea675d18375d2246 /drivers/i2c
parentffc59c496bf8498657321c59433f55bbcf2d9c38 (diff)
downloadlinux-0b71026c69caa10261218528326721828d29a481.tar.gz
linux-0b71026c69caa10261218528326721828d29a481.tar.bz2
linux-0b71026c69caa10261218528326721828d29a481.zip
i2c: recovery: refactor recovery function
After exiting the while loop, we checked if recovery was successful and sent a STOP to the clients. Meanwhile however, we send a STOP after every pulse, so it is not needed after the loop. If we move the check for a free bus to the end of the while loop, we can shorten and simplify the logic. It is still ensured that at least one STOP will be sent to the wire even if SDA was not stuck low. Signed-off-by: Wolfram Sang <wsa+renesas@sang-engineering.com> Reviewed-by: Peter Rosin <peda@axentia.se> Signed-off-by: Wolfram Sang <wsa@the-dreams.de>
Diffstat (limited to 'drivers/i2c')
-rw-r--r--drivers/i2c/i2c-core-base.c24
1 files changed, 6 insertions, 18 deletions
diff --git a/drivers/i2c/i2c-core-base.c b/drivers/i2c/i2c-core-base.c
index 871a9731894f..c7995efd58ea 100644
--- a/drivers/i2c/i2c-core-base.c
+++ b/drivers/i2c/i2c-core-base.c
@@ -191,9 +191,6 @@ int i2c_generic_scl_recovery(struct i2c_adapter *adap)
ret = -EBUSY;
break;
}
- /* Break if SDA is high */
- if (bri->get_sda && bri->get_sda(adap))
- break;
}
val = !val;
@@ -209,22 +206,13 @@ int i2c_generic_scl_recovery(struct i2c_adapter *adap)
if (bri->set_sda)
bri->set_sda(adap, val);
ndelay(RECOVERY_NDELAY / 2);
- }
-
- /* check if recovery actually succeeded */
- if (bri->get_sda && !bri->get_sda(adap))
- ret = -EBUSY;
- /* If all went well, send STOP for a sane bus state. */
- if (ret == 0 && bri->set_sda) {
- bri->set_scl(adap, 0);
- ndelay(RECOVERY_NDELAY / 2);
- bri->set_sda(adap, 0);
- ndelay(RECOVERY_NDELAY / 2);
- bri->set_scl(adap, 1);
- ndelay(RECOVERY_NDELAY / 2);
- bri->set_sda(adap, 1);
- ndelay(RECOVERY_NDELAY / 2);
+ /* Break if SDA is high */
+ if (val && bri->get_sda) {
+ ret = bri->get_sda(adap) ? 0 : -EBUSY;
+ if (ret == 0)
+ break;
+ }
}
if (bri->unprepare_recovery)