Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 4b83626a authored by Mauro Carvalho Chehab's avatar Mauro Carvalho Chehab
Browse files

[media] em28xx: convert i2c wait completion logic to use jiffies



The I2C wait completion/timeout logic currently assumes that
msleep(5) will wait exaclty 5 ms. This is not true at all,
as it depends on CONFIG_HZ.

Convert it to use jiffies, in order to not wait for more time
than needed.

Signed-off-by: default avatarMauro Carvalho Chehab <m.chehab@samsung.com>
parent 5022a208
Loading
Loading
Loading
Loading
+31 −30
Original line number Original line Diff line number Diff line
@@ -26,6 +26,7 @@
#include <linux/kernel.h>
#include <linux/kernel.h>
#include <linux/usb.h>
#include <linux/usb.h>
#include <linux/i2c.h>
#include <linux/i2c.h>
#include <linux/jiffies.h>


#include "em28xx.h"
#include "em28xx.h"
#include "tuner-xc2028.h"
#include "tuner-xc2028.h"
@@ -48,8 +49,8 @@ MODULE_PARM_DESC(i2c_debug, "enable debug messages [i2c]");
 */
 */
static int em2800_i2c_send_bytes(struct em28xx *dev, u8 addr, u8 *buf, u16 len)
static int em2800_i2c_send_bytes(struct em28xx *dev, u8 addr, u8 *buf, u16 len)
{
{
	unsigned long timeout = jiffies + msecs_to_jiffies(EM2800_I2C_XFER_TIMEOUT);
	int ret;
	int ret;
	int write_timeout;
	u8 b2[6];
	u8 b2[6];


	if (len < 1 || len > 4)
	if (len < 1 || len > 4)
@@ -74,14 +75,14 @@ static int em2800_i2c_send_bytes(struct em28xx *dev, u8 addr, u8 *buf, u16 len)
		return (ret < 0) ? ret : -EIO;
		return (ret < 0) ? ret : -EIO;
	}
	}
	/* wait for completion */
	/* wait for completion */
	for (write_timeout = EM2800_I2C_XFER_TIMEOUT; write_timeout > 0;
	while (time_is_after_jiffies(timeout)) {
	     write_timeout -= 5) {
		ret = dev->em28xx_read_reg(dev, 0x05);
		ret = dev->em28xx_read_reg(dev, 0x05);
		if (ret == 0x80 + len - 1) {
		if (ret == 0x80 + len - 1)
			return len;
			return len;
		} else if (ret == 0x94 + len - 1) {
		if (ret == 0x94 + len - 1) {
			return -ENODEV;
			return -ENODEV;
		} else if (ret < 0) {
		}
		if (ret < 0) {
			em28xx_warn("failed to get i2c transfer status from bridge register (error=%i)\n",
			em28xx_warn("failed to get i2c transfer status from bridge register (error=%i)\n",
				    ret);
				    ret);
			return ret;
			return ret;
@@ -98,9 +99,9 @@ static int em2800_i2c_send_bytes(struct em28xx *dev, u8 addr, u8 *buf, u16 len)
 */
 */
static int em2800_i2c_recv_bytes(struct em28xx *dev, u8 addr, u8 *buf, u16 len)
static int em2800_i2c_recv_bytes(struct em28xx *dev, u8 addr, u8 *buf, u16 len)
{
{
	unsigned long timeout = jiffies + msecs_to_jiffies(EM2800_I2C_XFER_TIMEOUT);
	u8 buf2[4];
	u8 buf2[4];
	int ret;
	int ret;
	int read_timeout;
	int i;
	int i;


	if (len < 1 || len > 4)
	if (len < 1 || len > 4)
@@ -117,14 +118,14 @@ static int em2800_i2c_recv_bytes(struct em28xx *dev, u8 addr, u8 *buf, u16 len)
	}
	}


	/* wait for completion */
	/* wait for completion */
	for (read_timeout = EM2800_I2C_XFER_TIMEOUT; read_timeout > 0;
	while (time_is_after_jiffies(timeout)) {
	     read_timeout -= 5) {
		ret = dev->em28xx_read_reg(dev, 0x05);
		ret = dev->em28xx_read_reg(dev, 0x05);
		if (ret == 0x84 + len - 1) {
		if (ret == 0x84 + len - 1)
			break;
			break;
		} else if (ret == 0x94 + len - 1) {
		if (ret == 0x94 + len - 1) {
			return -ENODEV;
			return -ENODEV;
		} else if (ret < 0) {
		}
		if (ret < 0) {
			em28xx_warn("failed to get i2c transfer status from bridge register (error=%i)\n",
			em28xx_warn("failed to get i2c transfer status from bridge register (error=%i)\n",
				    ret);
				    ret);
			return ret;
			return ret;
@@ -168,7 +169,8 @@ static int em2800_i2c_check_for_device(struct em28xx *dev, u8 addr)
static int em28xx_i2c_send_bytes(struct em28xx *dev, u16 addr, u8 *buf,
static int em28xx_i2c_send_bytes(struct em28xx *dev, u16 addr, u8 *buf,
				 u16 len, int stop)
				 u16 len, int stop)
{
{
	int write_timeout, ret;
	unsigned long timeout = jiffies + msecs_to_jiffies(EM2800_I2C_XFER_TIMEOUT);
	int ret;


	if (len < 1 || len > 64)
	if (len < 1 || len > 64)
		return -EOPNOTSUPP;
		return -EOPNOTSUPP;
@@ -191,16 +193,16 @@ static int em28xx_i2c_send_bytes(struct em28xx *dev, u16 addr, u8 *buf,
		}
		}
	}
	}


	/* Check success of the i2c operation */
	/* wait for completion */
	for (write_timeout = EM2800_I2C_XFER_TIMEOUT; write_timeout > 0;
	while (time_is_after_jiffies(timeout)) {
	     write_timeout -= 5) {
		ret = dev->em28xx_read_reg(dev, 0x05);
		ret = dev->em28xx_read_reg(dev, 0x05);
		if (ret == 0) { /* success */
		if (ret == 0) /* success */
			return len;
			return len;
		} else if (ret == 0x10) {
		if (ret == 0x10) {
			return -ENODEV;
			return -ENODEV;
		} else if (ret < 0) {
		}
			em28xx_warn("failed to read i2c transfer status from bridge (error=%i)\n",
		if (ret < 0) {
			em28xx_warn("failed to get i2c transfer status from bridge register (error=%i)\n",
				    ret);
				    ret);
			return ret;
			return ret;
		}
		}
@@ -211,6 +213,7 @@ static int em28xx_i2c_send_bytes(struct em28xx *dev, u16 addr, u8 *buf,
		 * (even with high payload) ...
		 * (even with high payload) ...
		 */
		 */
	}
	}

	em28xx_warn("write to i2c device at 0x%x timed out\n", addr);
	em28xx_warn("write to i2c device at 0x%x timed out\n", addr);
	return -EIO;
	return -EIO;
}
}
@@ -248,21 +251,19 @@ static int em28xx_i2c_recv_bytes(struct em28xx *dev, u16 addr, u8 *buf, u16 len)


	/* Check success of the i2c operation */
	/* Check success of the i2c operation */
	ret = dev->em28xx_read_reg(dev, 0x05);
	ret = dev->em28xx_read_reg(dev, 0x05);
	if (ret == 0) /* success */
		return len;
	if (ret < 0) {
	if (ret < 0) {
		em28xx_warn("failed to read i2c transfer status from bridge (error=%i)\n",
		em28xx_warn("failed to get i2c transfer status from bridge register (error=%i)\n",
			    ret);
			    ret);
		return ret;
		return ret;
	}
	}
	if (ret > 0) {
	if (ret == 0x10)
		if (ret == 0x10) {
		return -ENODEV;
		return -ENODEV;
		} else {

	em28xx_warn("unknown i2c error (status=%i)\n", ret);
	em28xx_warn("unknown i2c error (status=%i)\n", ret);
	return -EIO;
	return -EIO;
}
}
	}
	return len;
}


/*
/*
 * em28xx_i2c_check_for_device()
 * em28xx_i2c_check_for_device()