|
@@ -271,30 +271,36 @@ static inline bool ktime_lt(const ktime_t cmp1, const ktime_t cmp2)
|
|
/**
|
|
/**
|
|
* pch_i2c_wait_for_bus_idle() - check the status of bus.
|
|
* pch_i2c_wait_for_bus_idle() - check the status of bus.
|
|
* @adap: Pointer to struct i2c_algo_pch_data.
|
|
* @adap: Pointer to struct i2c_algo_pch_data.
|
|
- * @timeout: waiting time counter (us).
|
|
|
|
|
|
+ * @timeout: waiting time counter (ms).
|
|
*/
|
|
*/
|
|
static s32 pch_i2c_wait_for_bus_idle(struct i2c_algo_pch_data *adap,
|
|
static s32 pch_i2c_wait_for_bus_idle(struct i2c_algo_pch_data *adap,
|
|
s32 timeout)
|
|
s32 timeout)
|
|
{
|
|
{
|
|
void __iomem *p = adap->pch_base_address;
|
|
void __iomem *p = adap->pch_base_address;
|
|
- ktime_t ns_val;
|
|
|
|
|
|
+ int schedule = 0;
|
|
|
|
+ unsigned long end = jiffies + msecs_to_jiffies(timeout);
|
|
|
|
+
|
|
|
|
+ while (ioread32(p + PCH_I2CSR) & I2CMBB_BIT) {
|
|
|
|
+ if (time_after(jiffies, end)) {
|
|
|
|
+ pch_dbg(adap, "I2CSR = %x\n", ioread32(p + PCH_I2CSR));
|
|
|
|
+ pch_err(adap, "%s: Timeout Error.return%d\n",
|
|
|
|
+ __func__, -ETIME);
|
|
|
|
+ pch_i2c_init(adap);
|
|
|
|
|
|
- if ((ioread32(p + PCH_I2CSR) & I2CMBB_BIT) == 0)
|
|
|
|
- return 0;
|
|
|
|
|
|
+ return -ETIME;
|
|
|
|
+ }
|
|
|
|
|
|
- /* MAX timeout value is timeout*1000*1000nsec */
|
|
|
|
- ns_val = ktime_add_ns(ktime_get(), timeout*1000*1000);
|
|
|
|
- do {
|
|
|
|
- msleep(20);
|
|
|
|
- if ((ioread32(p + PCH_I2CSR) & I2CMBB_BIT) == 0)
|
|
|
|
- return 0;
|
|
|
|
- } while (ktime_lt(ktime_get(), ns_val));
|
|
|
|
|
|
+ if (!schedule)
|
|
|
|
+ /* Retry after some usecs */
|
|
|
|
+ udelay(5);
|
|
|
|
+ else
|
|
|
|
+ /* Wait a bit more without consuming CPU */
|
|
|
|
+ usleep_range(20, 1000);
|
|
|
|
|
|
- pch_dbg(adap, "I2CSR = %x\n", ioread32(p + PCH_I2CSR));
|
|
|
|
- pch_err(adap, "%s: Timeout Error.return%d\n", __func__, -ETIME);
|
|
|
|
- pch_i2c_init(adap);
|
|
|
|
|
|
+ schedule = 1;
|
|
|
|
+ }
|
|
|
|
|
|
- return -ETIME;
|
|
|
|
|
|
+ return 0;
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|