Message ID | 20231031144252.2112593-2-m.szyprowski@samsung.com |
---|---|
State | Superseded |
Headers | show |
Series | [v3,1/3] i2c: s3c24xx: fix read transfers in polling mode | expand |
Hi Marek, On Tue, Oct 31, 2023 at 03:42:50PM +0100, Marek Szyprowski wrote: > To properly handle read transfers in polling mode, no waiting for the ACK > state is needed as it will never come. Just wait a bit to ensure start > state is on the bus and continue processing next bytes. > > Fixes: 117053f77a5a ("i2c: s3c2410: Add polling mode support") > Signed-off-by: Marek Szyprowski <m.szyprowski@samsung.com> > Reviewed-by: Chanho Park <chanho61.park@samsung.com> > --- > drivers/i2c/busses/i2c-s3c2410.c | 9 +++++++-- > 1 file changed, 7 insertions(+), 2 deletions(-) > > diff --git a/drivers/i2c/busses/i2c-s3c2410.c b/drivers/i2c/busses/i2c-s3c2410.c > index c56886af724e..bcc6afe2ccb5 100644 > --- a/drivers/i2c/busses/i2c-s3c2410.c > +++ b/drivers/i2c/busses/i2c-s3c2410.c > @@ -216,8 +216,13 @@ static bool is_ack(struct s3c24xx_i2c *i2c) > int tries; > > for (tries = 50; tries; --tries) { > - if (readl(i2c->regs + S3C2410_IICCON) > - & S3C2410_IICCON_IRQPEND) { > + unsigned long tmp = readl(i2c->regs + S3C2410_IICCON); > + > + if (!(tmp & S3C2410_IICCON_ACKEN)) { > + usleep_range(100, 200); > + return true; even though there are some obscure points here, I trust you have got here by doing some proper testing and, knowing you, I guess it was a thorough testing. I'm going to ack it, however, I think this driver needs some proper cleanup. I have all the hardware, fortunately, I just need to find some time to do it. Reviewed-by: Andi Shyti <andi.shyti@kernel.org> I will appreciate if you also add a comment on how you managed to get the 100-200 us sleeping range. Andi > + } > + if (tmp & S3C2410_IICCON_IRQPEND) { > if (!(readl(i2c->regs + S3C2410_IICSTAT) > & S3C2410_IICSTAT_LASTBIT)) > return true; > -- > 2.34.1 >
diff --git a/drivers/i2c/busses/i2c-s3c2410.c b/drivers/i2c/busses/i2c-s3c2410.c index c56886af724e..bcc6afe2ccb5 100644 --- a/drivers/i2c/busses/i2c-s3c2410.c +++ b/drivers/i2c/busses/i2c-s3c2410.c @@ -216,8 +216,13 @@ static bool is_ack(struct s3c24xx_i2c *i2c) int tries; for (tries = 50; tries; --tries) { - if (readl(i2c->regs + S3C2410_IICCON) - & S3C2410_IICCON_IRQPEND) { + unsigned long tmp = readl(i2c->regs + S3C2410_IICCON); + + if (!(tmp & S3C2410_IICCON_ACKEN)) { + usleep_range(100, 200); + return true; + } + if (tmp & S3C2410_IICCON_IRQPEND) { if (!(readl(i2c->regs + S3C2410_IICSTAT) & S3C2410_IICSTAT_LASTBIT)) return true;