can: mcp251x: Use readx_poll_timeout() helper
We may use special helper macro to poll IO till condition or timeout occurs. Signed-off-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com> Link: https://lore.kernel.org/r/20200217161038.25009-1-andriy.shevchenko@linux.intel.com Signed-off-by: Marc Kleine-Budde <mkl@pengutronix.de>
This commit is contained in:
parent
2d52dabbef
commit
74fa565b63
@ -32,6 +32,7 @@
|
||||
#include <linux/gpio/driver.h>
|
||||
#include <linux/interrupt.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/iopoll.h>
|
||||
#include <linux/kernel.h>
|
||||
#include <linux/module.h>
|
||||
#include <linux/netdevice.h>
|
||||
@ -376,6 +377,15 @@ static void mcp251x_write_bits(struct spi_device *spi, u8 reg,
|
||||
mcp251x_spi_trans(spi, 4);
|
||||
}
|
||||
|
||||
static u8 mcp251x_read_stat(struct spi_device *spi)
|
||||
{
|
||||
return mcp251x_read_reg(spi, CANSTAT) & CANCTRL_REQOP_MASK;
|
||||
}
|
||||
|
||||
#define mcp251x_read_stat_poll_timeout(addr, val, cond, delay_us, timeout_us) \
|
||||
readx_poll_timeout(mcp251x_read_stat, addr, val, cond, \
|
||||
delay_us, timeout_us)
|
||||
|
||||
#ifdef CONFIG_GPIOLIB
|
||||
enum {
|
||||
MCP251X_GPIO_TX0RTS = 0, /* inputs */
|
||||
@ -709,7 +719,8 @@ static void mcp251x_hw_sleep(struct spi_device *spi)
|
||||
/* May only be called when device is sleeping! */
|
||||
static int mcp251x_hw_wake(struct spi_device *spi)
|
||||
{
|
||||
unsigned long timeout;
|
||||
u8 value;
|
||||
int ret;
|
||||
|
||||
/* Force wakeup interrupt to wake device, but don't execute IST */
|
||||
disable_irq(spi->irq);
|
||||
@ -722,14 +733,12 @@ static int mcp251x_hw_wake(struct spi_device *spi)
|
||||
mcp251x_write_reg(spi, CANCTRL, CANCTRL_REQOP_CONF);
|
||||
|
||||
/* Wait for the device to enter config mode */
|
||||
timeout = jiffies + HZ;
|
||||
while ((mcp251x_read_reg(spi, CANSTAT) & CANCTRL_REQOP_MASK) !=
|
||||
CANCTRL_REQOP_CONF) {
|
||||
schedule();
|
||||
if (time_after(jiffies, timeout)) {
|
||||
dev_err(&spi->dev, "MCP251x didn't enter in config mode\n");
|
||||
return -EBUSY;
|
||||
}
|
||||
ret = mcp251x_read_stat_poll_timeout(spi, value, value == CANCTRL_REQOP_CONF,
|
||||
MCP251X_OST_DELAY_MS * 1000,
|
||||
USEC_PER_SEC);
|
||||
if (ret) {
|
||||
dev_err(&spi->dev, "MCP251x didn't enter in config mode\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Disable and clear pending interrupts */
|
||||
@ -784,7 +793,8 @@ static int mcp251x_do_set_mode(struct net_device *net, enum can_mode mode)
|
||||
static int mcp251x_set_normal_mode(struct spi_device *spi)
|
||||
{
|
||||
struct mcp251x_priv *priv = spi_get_drvdata(spi);
|
||||
unsigned long timeout;
|
||||
u8 value;
|
||||
int ret;
|
||||
|
||||
/* Enable interrupts */
|
||||
mcp251x_write_reg(spi, CANINTE,
|
||||
@ -802,13 +812,12 @@ static int mcp251x_set_normal_mode(struct spi_device *spi)
|
||||
mcp251x_write_reg(spi, CANCTRL, CANCTRL_REQOP_NORMAL);
|
||||
|
||||
/* Wait for the device to enter normal mode */
|
||||
timeout = jiffies + HZ;
|
||||
while (mcp251x_read_reg(spi, CANSTAT) & CANCTRL_REQOP_MASK) {
|
||||
schedule();
|
||||
if (time_after(jiffies, timeout)) {
|
||||
dev_err(&spi->dev, "MCP251x didn't enter in normal mode\n");
|
||||
return -EBUSY;
|
||||
}
|
||||
ret = mcp251x_read_stat_poll_timeout(spi, value, value == 0,
|
||||
MCP251X_OST_DELAY_MS * 1000,
|
||||
USEC_PER_SEC);
|
||||
if (ret) {
|
||||
dev_err(&spi->dev, "MCP251x didn't enter in normal mode\n");
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
priv->can.state = CAN_STATE_ERROR_ACTIVE;
|
||||
@ -852,7 +861,7 @@ static int mcp251x_setup(struct net_device *net, struct spi_device *spi)
|
||||
static int mcp251x_hw_reset(struct spi_device *spi)
|
||||
{
|
||||
struct mcp251x_priv *priv = spi_get_drvdata(spi);
|
||||
unsigned long timeout;
|
||||
u8 value;
|
||||
int ret;
|
||||
|
||||
/* Wait for oscillator startup timer after power up */
|
||||
@ -867,19 +876,12 @@ static int mcp251x_hw_reset(struct spi_device *spi)
|
||||
mdelay(MCP251X_OST_DELAY_MS);
|
||||
|
||||
/* Wait for reset to finish */
|
||||
timeout = jiffies + HZ;
|
||||
while ((mcp251x_read_reg(spi, CANSTAT) & CANCTRL_REQOP_MASK) !=
|
||||
CANCTRL_REQOP_CONF) {
|
||||
usleep_range(MCP251X_OST_DELAY_MS * 1000,
|
||||
MCP251X_OST_DELAY_MS * 1000 * 2);
|
||||
|
||||
if (time_after(jiffies, timeout)) {
|
||||
dev_err(&spi->dev,
|
||||
"MCP251x didn't enter in conf mode after reset\n");
|
||||
return -EBUSY;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
ret = mcp251x_read_stat_poll_timeout(spi, value, value == CANCTRL_REQOP_CONF,
|
||||
MCP251X_OST_DELAY_MS * 1000,
|
||||
USEC_PER_SEC);
|
||||
if (ret)
|
||||
dev_err(&spi->dev, "MCP251x didn't enter in conf mode after reset\n");
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int mcp251x_hw_probe(struct spi_device *spi)
|
||||
|
Loading…
x
Reference in New Issue
Block a user