summaryrefslogtreecommitdiffstats
path: root/drivers/i2c/algos
diff options
context:
space:
mode:
authorRoel Kluin <roel.kluin@gmail.com>2009-03-28 21:34:42 +0100
committerJean Delvare <khali@linux-fr.org>2009-03-28 21:34:42 +0100
commit94d78e180c0323422854bc1718e657ac2d0cac1b (patch)
tree7db1c35614e593f80ee17c10915dda76d2ee2836 /drivers/i2c/algos
parent0c168ceb9e1898a7f2895e80ce9915835b083bd3 (diff)
i2c-algo-pcf: Handle timeout correctly
With a postfix decrement these timeouts reach -1 rather than 0, but after the loop it is tested whether they have become 0. As pointed out by Jean Delvare, the msg_num should be tested before the timeout. With the current order, you could exit with a timeout error while all the messages were successfully transferred. Signed-off-by: Roel Kluin <roel.kluin@gmail.com> Signed-off-by: Jean Delvare <khali@linux-fr.org> Acked-by: Eric Brower <ebrower@gmail.com>
Diffstat (limited to 'drivers/i2c/algos')
-rw-r--r--drivers/i2c/algos/i2c-algo-pcf.c18
1 files changed, 10 insertions, 8 deletions
diff --git a/drivers/i2c/algos/i2c-algo-pcf.c b/drivers/i2c/algos/i2c-algo-pcf.c
index 5906986d013..65a769f3ae7 100644
--- a/drivers/i2c/algos/i2c-algo-pcf.c
+++ b/drivers/i2c/algos/i2c-algo-pcf.c
@@ -115,15 +115,17 @@ static int wait_for_bb(struct i2c_algo_pcf_data *adap)
status = get_pcf(adap, 1);
- while (timeout-- && !(status & I2C_PCF_BB)) {
+ while (!(status & I2C_PCF_BB) && --timeout) {
udelay(100); /* wait for 100 us */
status = get_pcf(adap, 1);
}
- if (timeout <= 0)
+ if (timeout == 0) {
printk(KERN_ERR "Timeout waiting for Bus Busy\n");
+ return -ETIMEDOUT;
+ }
- return timeout <= 0;
+ return 0;
}
static int wait_for_pin(struct i2c_algo_pcf_data *adap, int *status)
@@ -133,7 +135,7 @@ static int wait_for_pin(struct i2c_algo_pcf_data *adap, int *status)
*status = get_pcf(adap, 1);
- while (timeout-- && (*status & I2C_PCF_PIN)) {
+ while ((*status & I2C_PCF_PIN) && --timeout) {
adap->waitforpin(adap->data);
*status = get_pcf(adap, 1);
}
@@ -142,10 +144,10 @@ static int wait_for_pin(struct i2c_algo_pcf_data *adap, int *status)
return -EINTR;
}
- if (timeout <= 0)
- return -1;
- else
- return 0;
+ if (timeout == 0)
+ return -ETIMEDOUT;
+
+ return 0;
}
/*