static int fec_reset_phy(struct platform_device *pdev)
{
- int err, phy_reset;
- bool active_high = false;
+ int err;
int msec = 1, phy_post_delay = 0;
struct device_node *np = pdev->dev.of_node;
+ struct net_device *ndev = platform_get_drvdata(pdev);
+ struct fec_enet_private *fep = netdev_priv(ndev);
if (!np)
return 0;
if (!err && msec > 1000)
msec = 1;
- phy_reset = of_get_named_gpio(np, "phy-reset-gpios", 0);
- if (phy_reset == -EPROBE_DEFER)
- return phy_reset;
- else if (!gpio_is_valid(phy_reset))
+ fep->phy_reset_gpio = of_get_named_gpio(np, "phy-reset-gpios", 0);
+ if (fep->phy_reset_gpio == -EPROBE_DEFER)
+ return fep->phy_reset_gpio;
+ else if (!gpio_is_valid(fep->phy_reset_gpio)) {
+ fep->phy_reset_gpio = -1;
return 0;
+ }
err = of_property_read_u32(np, "phy-reset-post-delay", &phy_post_delay);
/* valid reset duration should be less than 1s */
if (!err && phy_post_delay > 1000)
return -EINVAL;
- active_high = of_property_read_bool(np, "phy-reset-active-high");
+ fep->active_high = of_property_read_bool(np, "phy-reset-active-high");
- err = devm_gpio_request_one(&pdev->dev, phy_reset,
- active_high ? GPIOF_OUT_INIT_HIGH : GPIOF_OUT_INIT_LOW,
+ err = devm_gpio_request_one(&pdev->dev, fep->phy_reset_gpio,
+ fep->active_high ? GPIOF_OUT_INIT_HIGH : GPIOF_OUT_INIT_LOW,
"phy-reset");
if (err) {
dev_err(&pdev->dev, "failed to get phy-reset-gpios: %d\n", err);
return err;
}
+ fep->phy_reset_in_suspend = of_property_read_bool(np,
+ "phy-reset-in-suspend");
+
if (msec > 20)
msleep(msec);
else
usleep_range(msec * 1000, msec * 1000 + 1000);
- gpio_set_value_cansleep(phy_reset, !active_high);
+ gpio_set_value_cansleep(fep->phy_reset_gpio, !fep->active_high);
if (!phy_post_delay)
return 0;
fec_stop(ndev);
if (!(fep->wol_flag & FEC_WOL_FLAG_ENABLE)) {
fec_irqs_disable(ndev);
+ if (fep->phy_reset_in_suspend)
+ gpio_set_value_cansleep(fep->phy_reset_gpio, fep->active_high);
pinctrl_pm_select_sleep_state(&fep->pdev->dev);
} else {
disable_irq(fep->wake_irq);
if (ret < 0)
return ret;
} else if (fep->mii_bus_share && !ndev->phydev) {
+ if (fep->phy_reset_in_suspend)
+ gpio_set_value_cansleep(fep->phy_reset_gpio, fep->active_high);
pinctrl_pm_select_sleep_state(&fep->pdev->dev);
}
rtnl_unlock();
writel(val, fep->hwp + FEC_ECNTRL);
fep->wol_flag &= ~FEC_WOL_FLAG_SLEEP_ON;
} else {
+ if (fep->phy_reset_in_suspend)
+ gpio_set_value_cansleep(fep->phy_reset_gpio, !fep->active_high);
pinctrl_pm_select_default_state(&fep->pdev->dev);
}
fec_restart(ndev);
napi_enable(&fep->napi);
phy_start(ndev->phydev);
} else if (fep->mii_bus_share && !ndev->phydev) {
+ if (fep->phy_reset_in_suspend)
+ gpio_set_value_cansleep(fep->phy_reset_gpio, !fep->active_high);
pinctrl_pm_select_default_state(&fep->pdev->dev);
/* And then recovery mii bus */
ret = fec_restore_mii_bus(ndev);