Skip to content

Commit

Permalink
Merge branch 'bcmgenet-fix-aborted-suspend'
Browse files Browse the repository at this point in the history
Doug Berger says:

====================
net: bcmgenet: fix aborted suspend

It is not enough to return an error code from the driver suspend
routine. The driver must also restore the device functionality.

This commit corrects the issue introduced by commit 0db5509
("net: bcmgenet: return correct value 'ret' from bcmgenet_power_down")
by calling the driver resume function if the suspend function returns
an error.
====================

Signed-off-by: David S. Miller <davem@davemloft.net>
  • Loading branch information
David S. Miller committed Nov 18, 2018
2 parents 8a962c4 + c5a54bb commit 17bf169
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 30 deletions.
63 changes: 33 additions & 30 deletions drivers/net/ethernet/broadcom/genet/bcmgenet.c
Original file line number Diff line number Diff line change
Expand Up @@ -3612,36 +3612,6 @@ static int bcmgenet_remove(struct platform_device *pdev)
}

#ifdef CONFIG_PM_SLEEP
static int bcmgenet_suspend(struct device *d)
{
struct net_device *dev = dev_get_drvdata(d);
struct bcmgenet_priv *priv = netdev_priv(dev);
int ret = 0;

if (!netif_running(dev))
return 0;

netif_device_detach(dev);

bcmgenet_netif_stop(dev);

if (!device_may_wakeup(d))
phy_suspend(dev->phydev);

/* Prepare the device for Wake-on-LAN and switch to the slow clock */
if (device_may_wakeup(d) && priv->wolopts) {
ret = bcmgenet_power_down(priv, GENET_POWER_WOL_MAGIC);
clk_prepare_enable(priv->clk_wol);
} else if (priv->internal_phy) {
ret = bcmgenet_power_down(priv, GENET_POWER_PASSIVE);
}

/* Turn off the clocks */
clk_disable_unprepare(priv->clk);

return ret;
}

static int bcmgenet_resume(struct device *d)
{
struct net_device *dev = dev_get_drvdata(d);
Expand Down Expand Up @@ -3719,6 +3689,39 @@ static int bcmgenet_resume(struct device *d)
clk_disable_unprepare(priv->clk);
return ret;
}

static int bcmgenet_suspend(struct device *d)
{
struct net_device *dev = dev_get_drvdata(d);
struct bcmgenet_priv *priv = netdev_priv(dev);
int ret = 0;

if (!netif_running(dev))
return 0;

netif_device_detach(dev);

bcmgenet_netif_stop(dev);

if (!device_may_wakeup(d))
phy_suspend(dev->phydev);

/* Prepare the device for Wake-on-LAN and switch to the slow clock */
if (device_may_wakeup(d) && priv->wolopts) {
ret = bcmgenet_power_down(priv, GENET_POWER_WOL_MAGIC);
clk_prepare_enable(priv->clk_wol);
} else if (priv->internal_phy) {
ret = bcmgenet_power_down(priv, GENET_POWER_PASSIVE);
}

/* Turn off the clocks */
clk_disable_unprepare(priv->clk);

if (ret)
bcmgenet_resume(d);

return ret;
}
#endif /* CONFIG_PM_SLEEP */

static SIMPLE_DEV_PM_OPS(bcmgenet_pm_ops, bcmgenet_suspend, bcmgenet_resume);
Expand Down
6 changes: 6 additions & 0 deletions drivers/net/ethernet/broadcom/genet/bcmgenet_wol.c
Original file line number Diff line number Diff line change
Expand Up @@ -186,9 +186,15 @@ void bcmgenet_wol_power_up_cfg(struct bcmgenet_priv *priv,
}

reg = bcmgenet_umac_readl(priv, UMAC_MPD_CTRL);
if (!(reg & MPD_EN))
return; /* already powered up so skip the rest */
reg &= ~MPD_EN;
bcmgenet_umac_writel(priv, reg, UMAC_MPD_CTRL);

reg = bcmgenet_hfb_reg_readl(priv, HFB_CTRL);
reg &= ~(RBUF_HFB_EN | RBUF_ACPI_EN);
bcmgenet_hfb_reg_writel(priv, reg, HFB_CTRL);

/* Disable CRC Forward */
reg = bcmgenet_umac_readl(priv, UMAC_CMD);
reg &= ~CMD_CRC_FWD;
Expand Down

0 comments on commit 17bf169

Please sign in to comment.