mirror of
https://github.com/torvalds/linux.git
synced 2026-08-01 03:59:40 +02:00
net: stmmac: mdio: provide stmmac_mdio_wait()
All the readl_poll_timeout()s follow the same pattern - test a register for a bit being clear every 100us, and timeout after 10ms returning -EBUSY. Wrap this up into a function to avoid duplicating this. This slightly changes the return value for stmmac_mdio_write() if the second readl_poll_timeout() fails - rather than returning -ETIMEDOUT we return -EBUSY matching the stmmac_mdio_read() behaviour. Signed-off-by: Russell King (Oracle) <rmk+kernel@armlinux.org.uk> Reviewed-by: Andrew Lunn <andrew@lunn.ch> Tested-by: Mohd Ayaan Anwar <quic_mohdayaa@quicinc.com> Link: https://patch.msgid.link/E1uu8nx-00000001voa-0tJ0@rmk-PC.armlinux.org.uk Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
parent
16e03235d5
commit
9eb633ad1d
|
|
@ -45,6 +45,16 @@
|
|||
#define MII_XGMAC_PA_SHIFT 16
|
||||
#define MII_XGMAC_DA_SHIFT 21
|
||||
|
||||
static int stmmac_mdio_wait(void __iomem *reg, u32 mask)
|
||||
{
|
||||
u32 v;
|
||||
|
||||
if (readl_poll_timeout(reg, v, !(v & mask), 100, 10000))
|
||||
return -EBUSY;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void stmmac_xgmac2_c45_format(struct stmmac_priv *priv, int phyaddr,
|
||||
int devad, int phyreg, u32 *hw_addr)
|
||||
{
|
||||
|
|
@ -83,7 +93,6 @@ static int stmmac_xgmac2_mdio_read(struct stmmac_priv *priv, u32 addr,
|
|||
{
|
||||
unsigned int mii_address = priv->hw->mii.addr;
|
||||
unsigned int mii_data = priv->hw->mii.data;
|
||||
u32 tmp;
|
||||
int ret;
|
||||
|
||||
ret = pm_runtime_resume_and_get(priv->device);
|
||||
|
|
@ -91,33 +100,27 @@ static int stmmac_xgmac2_mdio_read(struct stmmac_priv *priv, u32 addr,
|
|||
return ret;
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,
|
||||
!(tmp & MII_XGMAC_BUSY), 100, 10000)) {
|
||||
ret = -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_data, MII_XGMAC_BUSY);
|
||||
if (ret)
|
||||
goto err_disable_clks;
|
||||
}
|
||||
|
||||
value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)
|
||||
& priv->hw->mii.clk_csr_mask;
|
||||
value |= MII_XGMAC_READ;
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,
|
||||
!(tmp & MII_XGMAC_BUSY), 100, 10000)) {
|
||||
ret = -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_data, MII_XGMAC_BUSY);
|
||||
if (ret)
|
||||
goto err_disable_clks;
|
||||
}
|
||||
|
||||
/* Set the MII address register to read */
|
||||
writel(addr, priv->ioaddr + mii_address);
|
||||
writel(value, priv->ioaddr + mii_data);
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,
|
||||
!(tmp & MII_XGMAC_BUSY), 100, 10000)) {
|
||||
ret = -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_data, MII_XGMAC_BUSY);
|
||||
if (ret)
|
||||
goto err_disable_clks;
|
||||
}
|
||||
|
||||
/* Read the data from the MII data register */
|
||||
ret = (int)readl(priv->ioaddr + mii_data) & GENMASK(15, 0);
|
||||
|
|
@ -160,7 +163,6 @@ static int stmmac_xgmac2_mdio_write(struct stmmac_priv *priv, u32 addr,
|
|||
{
|
||||
unsigned int mii_address = priv->hw->mii.addr;
|
||||
unsigned int mii_data = priv->hw->mii.data;
|
||||
u32 tmp;
|
||||
int ret;
|
||||
|
||||
ret = pm_runtime_resume_and_get(priv->device);
|
||||
|
|
@ -168,11 +170,9 @@ static int stmmac_xgmac2_mdio_write(struct stmmac_priv *priv, u32 addr,
|
|||
return ret;
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,
|
||||
!(tmp & MII_XGMAC_BUSY), 100, 10000)) {
|
||||
ret = -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_data, MII_XGMAC_BUSY);
|
||||
if (ret)
|
||||
goto err_disable_clks;
|
||||
}
|
||||
|
||||
value |= (priv->clk_csr << priv->hw->mii.clk_csr_shift)
|
||||
& priv->hw->mii.clk_csr_mask;
|
||||
|
|
@ -180,19 +180,16 @@ static int stmmac_xgmac2_mdio_write(struct stmmac_priv *priv, u32 addr,
|
|||
value |= MII_XGMAC_WRITE;
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_data, tmp,
|
||||
!(tmp & MII_XGMAC_BUSY), 100, 10000)) {
|
||||
ret = -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_data, MII_XGMAC_BUSY);
|
||||
if (ret)
|
||||
goto err_disable_clks;
|
||||
}
|
||||
|
||||
/* Set the MII address register to write */
|
||||
writel(addr, priv->ioaddr + mii_address);
|
||||
writel(value, priv->ioaddr + mii_data);
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
ret = readl_poll_timeout(priv->ioaddr + mii_data, tmp,
|
||||
!(tmp & MII_XGMAC_BUSY), 100, 10000);
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_data, MII_XGMAC_BUSY);
|
||||
|
||||
err_disable_clks:
|
||||
pm_runtime_put(priv->device);
|
||||
|
|
@ -253,18 +250,18 @@ static int stmmac_mdio_read(struct stmmac_priv *priv, int data, u32 value)
|
|||
{
|
||||
unsigned int mii_address = priv->hw->mii.addr;
|
||||
unsigned int mii_data = priv->hw->mii.data;
|
||||
u32 v;
|
||||
int ret;
|
||||
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_address, v, !(v & MII_BUSY),
|
||||
100, 10000))
|
||||
return -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_address, MII_BUSY);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
writel(data, priv->ioaddr + mii_data);
|
||||
writel(value, priv->ioaddr + mii_address);
|
||||
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_address, v, !(v & MII_BUSY),
|
||||
100, 10000))
|
||||
return -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_address, MII_BUSY);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Read the data from the MII data register */
|
||||
return readl(priv->ioaddr + mii_data) & MII_DATA_MASK;
|
||||
|
|
@ -340,20 +337,19 @@ static int stmmac_mdio_write(struct stmmac_priv *priv, int data, u32 value)
|
|||
{
|
||||
unsigned int mii_address = priv->hw->mii.addr;
|
||||
unsigned int mii_data = priv->hw->mii.data;
|
||||
u32 v;
|
||||
int ret;
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
if (readl_poll_timeout(priv->ioaddr + mii_address, v, !(v & MII_BUSY),
|
||||
100, 10000))
|
||||
return -EBUSY;
|
||||
ret = stmmac_mdio_wait(priv->ioaddr + mii_address, MII_BUSY);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
/* Set the MII address register to write */
|
||||
writel(data, priv->ioaddr + mii_data);
|
||||
writel(value, priv->ioaddr + mii_address);
|
||||
|
||||
/* Wait until any existing MII operation is complete */
|
||||
return readl_poll_timeout(priv->ioaddr + mii_address, v,
|
||||
!(v & MII_BUSY), 100, 10000);
|
||||
return stmmac_mdio_wait(priv->ioaddr + mii_address, MII_BUSY);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user