netdev.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH net-next v2 0/9] net: phy: consolidate PHY reset
@ 2013-12-06 21:01 Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 1/9] net: phy: report link partner features through ethtool Florian Fainelli
                   ` (9 more replies)
  0 siblings, 10 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

This patchset consolidates the PHY reset through the MII BMCR
register by using a central place were this is done.

This patchset resumes the work Kyle Moffett started here:
https://lkml.org/lkml/2011/10/20/301

Note that at this point, drivers doing funky things after issuing
a PHY reset using phy_init_hw() will still suffer from PHY state
machine problems, this will be taken care of later on.

Florian Fainelli (9):
  net: phy: report link partner features through ethtool
  net: phy: use phy_init_hw instead of open-coding it
  net: greth: use phy_read_status()
  net: bfin_mac: do not reset PHY after phy_start()
  net: phy: consolidate PHY reset in phy_init_hw()
  net: mv643xx_eth: use phy_init_hw to reset PHY
  net: pxa168_eth: use phy_init_hw for PHY reset
  net: tc35815: use phy_init_hw for PHY reset
  net: sh_eth: do not issue a wild PHY reset through BMCR

 Documentation/networking/phy.txt           |  3 +-
 drivers/net/ethernet/adi/bfin_mac.c        |  1 -
 drivers/net/ethernet/aeroflex/greth.c      |  2 +-
 drivers/net/ethernet/marvell/mv643xx_eth.c | 21 +---------
 drivers/net/ethernet/marvell/pxa168_eth.c  | 20 +---------
 drivers/net/ethernet/renesas/sh_eth.c      |  5 ++-
 drivers/net/ethernet/toshiba/tc35815.c     | 15 ++------
 drivers/net/phy/phy.c                      | 11 +++---
 drivers/net/phy/phy_device.c               | 62 +++++++++++++++++++++++++++++-
 include/linux/phy.h                        |  5 ++-
 10 files changed, 82 insertions(+), 63 deletions(-)

-- 
1.8.3.2

^ permalink raw reply	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 1/9] net: phy: report link partner features through ethtool
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 2/9] net: phy: use phy_init_hw instead of open-coding it Florian Fainelli
                   ` (8 subsequent siblings)
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

The PHY library already reads the MII_STAT1000 and MII_LPA registers in
genphy_read_status(), so extend it to also populate the PHY device link
partner advertised features such that we can feed this back into ethtool
when asked for it in phy_ethtool_gset().

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
 drivers/net/phy/phy.c        | 1 +
 drivers/net/phy/phy_device.c | 6 ++++++
 include/linux/phy.h          | 5 +++--
 3 files changed, 10 insertions(+), 2 deletions(-)

diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 36c6994..05cb8fe 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -289,6 +289,7 @@ int phy_ethtool_gset(struct phy_device *phydev, struct ethtool_cmd *cmd)
 	cmd->supported = phydev->supported;
 
 	cmd->advertising = phydev->advertising;
+	cmd->lp_advertising = phydev->lp_advertising;
 
 	ethtool_cmd_speed_set(cmd, phydev->speed);
 	cmd->duplex = phydev->duplex;
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
index d6447b3..6db3659 100644
--- a/drivers/net/phy/phy_device.c
+++ b/drivers/net/phy/phy_device.c
@@ -839,6 +839,8 @@ int genphy_read_status(struct phy_device *phydev)
 	if (err)
 		return err;
 
+	phydev->lp_advertising = 0;
+
 	if (AUTONEG_ENABLE == phydev->autoneg) {
 		if (phydev->supported & (SUPPORTED_1000baseT_Half
 					| SUPPORTED_1000baseT_Full)) {
@@ -852,6 +854,8 @@ int genphy_read_status(struct phy_device *phydev)
 			if (adv < 0)
 				return adv;
 
+			phydev->lp_advertising =
+				mii_stat1000_to_ethtool_lpa_t(lpagb);
 			lpagb &= adv << 2;
 		}
 
@@ -860,6 +864,8 @@ int genphy_read_status(struct phy_device *phydev)
 		if (lpa < 0)
 			return lpa;
 
+		phydev->lp_advertising |= mii_lpa_to_ethtool_lpa_t(lpa);
+
 		adv = phy_read(phydev, MII_ADVERTISE);
 
 		if (adv < 0)
diff --git a/include/linux/phy.h b/include/linux/phy.h
index 7ff751a..90a666e 100644
--- a/include/linux/phy.h
+++ b/include/linux/phy.h
@@ -287,8 +287,8 @@ struct phy_c45_device_ids {
  * adjust_state: Callback for the enet driver to respond to
  * changes in the state machine.
  *
- * speed, duplex, pause, supported, advertising, and
- * autoneg are used like in mii_if_info
+ * speed, duplex, pause, supported, advertising, lp_advertising,
+ * and autoneg are used like in mii_if_info
  *
  * interrupts currently only supports enabled or disabled,
  * but could be changed in the future to support enabling
@@ -340,6 +340,7 @@ struct phy_device {
 	/* See mii.h for more info */
 	u32 supported;
 	u32 advertising;
+	u32 lp_advertising;
 
 	int autoneg;
 
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 2/9] net: phy: use phy_init_hw instead of open-coding it
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 1/9] net: phy: report link partner features through ethtool Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 3/9] net: greth: use phy_read_status() Florian Fainelli
                   ` (7 subsequent siblings)
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

Use phy_init_hw() instead of open-coding it in phy_mii_ioctl(), this
improves consistenty and makes sure that we will not duplicate the same
routine somewhere else.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
 drivers/net/phy/phy.c | 7 ++-----
 1 file changed, 2 insertions(+), 5 deletions(-)

diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 05cb8fe..5d7101b 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -361,11 +361,8 @@ int phy_mii_ioctl(struct phy_device *phydev,
 			      mii_data->reg_num, val);
 
 		if (mii_data->reg_num == MII_BMCR &&
-		    val & BMCR_RESET &&
-		    phydev->drv->config_init) {
-			phy_scan_fixups(phydev);
-			phydev->drv->config_init(phydev);
-		}
+		    val & BMCR_RESET)
+			phy_init_hw(phydev);
 		break;
 
 	case SIOCSHWTSTAMP:
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 3/9] net: greth: use phy_read_status()
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 1/9] net: phy: report link partner features through ethtool Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 2/9] net: phy: use phy_init_hw instead of open-coding it Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 4/9] net: bfin_mac: do not reset PHY after phy_start() Florian Fainelli
                   ` (6 subsequent siblings)
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

In case the greth driver is bound to anything but the Generic PHY
driver or the PHY has a special read_status callback implemented,
unexpected things will happen. Make sure we that we use
phy_read_status() which does the proper abstraction of calling the
driver specific read_status() callback for a given PHY.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
 drivers/net/ethernet/aeroflex/greth.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/net/ethernet/aeroflex/greth.c b/drivers/net/ethernet/aeroflex/greth.c
index e066945..b20cbf0 100644
--- a/drivers/net/ethernet/aeroflex/greth.c
+++ b/drivers/net/ethernet/aeroflex/greth.c
@@ -1361,7 +1361,7 @@ static int greth_mdio_init(struct greth_private *greth)
 		timeout = jiffies + 6*HZ;
 		while (!phy_aneg_done(greth->phy) && time_before(jiffies, timeout)) {
 		}
-		genphy_read_status(greth->phy);
+		phy_read_status(greth->phy);
 		greth_link_change(greth->netdev);
 	}
 
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 4/9] net: bfin_mac: do not reset PHY after phy_start()
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
                   ` (2 preceding siblings ...)
  2013-12-06 21:01 ` [PATCH net-next v2 3/9] net: greth: use phy_read_status() Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 5/9] net: phy: consolidate PHY reset in phy_init_hw() Florian Fainelli
                   ` (5 subsequent siblings)
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

The PHY is already reset during driver probing, and this manual reset
after calling phy_start() will wipe out board-specific PHY fixups and
driver specific configuration initialization. Remove that explicit PHY
reset.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
 drivers/net/ethernet/adi/bfin_mac.c | 1 -
 1 file changed, 1 deletion(-)

diff --git a/drivers/net/ethernet/adi/bfin_mac.c b/drivers/net/ethernet/adi/bfin_mac.c
index 0d4f295..c0f68dc 100644
--- a/drivers/net/ethernet/adi/bfin_mac.c
+++ b/drivers/net/ethernet/adi/bfin_mac.c
@@ -1557,7 +1557,6 @@ static int bfin_mac_open(struct net_device *dev)
 		return ret;
 
 	phy_start(lp->phydev);
-	phy_write(lp->phydev, MII_BMCR, BMCR_RESET);
 	setup_system_regs(dev);
 	setup_mac_addr(dev->dev_addr);
 
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 5/9] net: phy: consolidate PHY reset in phy_init_hw()
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
                   ` (3 preceding siblings ...)
  2013-12-06 21:01 ` [PATCH net-next v2 4/9] net: bfin_mac: do not reset PHY after phy_start() Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 6/9] net: mv643xx_eth: use phy_init_hw to reset PHY Florian Fainelli
                   ` (4 subsequent siblings)
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

There are quite a lot of drivers touching a PHY device MII_BMCR
register to reset the PHY without taking care of:

1) ensuring that BMCR_RESET is cleared after a given timeout
2) the PHY state machine resuming to the proper state and re-applying
potentially changed settings such as auto-negotiation

Introduce phy_poll_reset() which will take care of polling the MII_BMCR
for the BMCR_RESET bit to be cleared after a given timeout or return a
timeout error code.

In order to make sure the PHY is in a correct state, phy_init_hw() first
issues a software reset through MII_BMCR and then applies any fixups.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
 Documentation/networking/phy.txt |  3 ++-
 drivers/net/phy/phy.c            |  5 ++--
 drivers/net/phy/phy_device.c     | 56 +++++++++++++++++++++++++++++++++++++++-
 3 files changed, 60 insertions(+), 4 deletions(-)

diff --git a/Documentation/networking/phy.txt b/Documentation/networking/phy.txt
index d5b1a39..ebf2707 100644
--- a/Documentation/networking/phy.txt
+++ b/Documentation/networking/phy.txt
@@ -255,7 +255,8 @@ Writing a PHY driver
 
    config_init: configures PHY into a sane state after a reset.
      For instance, a Davicom PHY requires descrambling disabled.
-   probe: Does any setup needed by the driver
+   probe: Allocate phy->priv, optionally refuse to bind.
+   PHY may not have been reset or had fixups run yet.
    suspend/resume: power management
    config_aneg: Changes the speed/duplex/negotiation settings
    read_status: Reads the current speed/duplex/negotiation settings
diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 5d7101b..e3dd691 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -318,6 +318,7 @@ int phy_mii_ioctl(struct phy_device *phydev,
 {
 	struct mii_ioctl_data *mii_data = if_mii(ifr);
 	u16 val = mii_data->val_in;
+	int ret = 0;
 
 	switch (cmd) {
 	case SIOCGMIIPHY:
@@ -362,7 +363,7 @@ int phy_mii_ioctl(struct phy_device *phydev,
 
 		if (mii_data->reg_num == MII_BMCR &&
 		    val & BMCR_RESET)
-			phy_init_hw(phydev);
+			ret = phy_init_hw(phydev);
 		break;
 
 	case SIOCSHWTSTAMP:
@@ -374,7 +375,7 @@ int phy_mii_ioctl(struct phy_device *phydev,
 		return -EOPNOTSUPP;
 	}
 
-	return 0;
+	return ret;
 }
 EXPORT_SYMBOL(phy_mii_ioctl);
 
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
index 6db3659..5a619f0 100644
--- a/drivers/net/phy/phy_device.c
+++ b/drivers/net/phy/phy_device.c
@@ -364,7 +364,11 @@ int phy_device_register(struct phy_device *phydev)
 	phydev->bus->phy_map[phydev->addr] = phydev;
 
 	/* Run all of the fixups for this PHY */
-	phy_scan_fixups(phydev);
+	err = phy_init_hw(phydev);
+	if (err) {
+		pr_err("PHY %d failed to initialize\n", phydev->addr);
+		goto out;
+	}
 
 	err = device_add(&phydev->dev);
 	if (err) {
@@ -497,6 +501,47 @@ void phy_disconnect(struct phy_device *phydev)
 }
 EXPORT_SYMBOL(phy_disconnect);
 
+/**
+ * phy_poll_reset - Safely wait until a PHY reset has properly completed
+ * @phydev: The PHY device to poll
+ *
+ * Description: According to IEEE 802.3, Section 2, Subsection 22.2.4.1.1, as
+ *   published in 2008, a PHY reset may take up to 0.5 seconds.  The MII BMCR
+ *   register must be polled until the BMCR_RESET bit clears.
+ *
+ *   Furthermore, any attempts to write to PHY registers may have no effect
+ *   or even generate MDIO bus errors until this is complete.
+ *
+ *   Some PHYs (such as the Marvell 88E1111) don't entirely conform to the
+ *   standard and do not fully reset after the BMCR_RESET bit is set, and may
+ *   even *REQUIRE* a soft-reset to properly restart autonegotiation.  In an
+ *   effort to support such broken PHYs, this function is separate from the
+ *   standard phy_init_hw() which will zero all the other bits in the BMCR
+ *   and reapply all driver-specific and board-specific fixups.
+ */
+static int phy_poll_reset(struct phy_device *phydev)
+{
+	/* Poll until the reset bit clears (50ms per retry == 0.6 sec) */
+	unsigned int retries = 12;
+	int ret;
+
+	do {
+		msleep(50);
+		ret = phy_read(phydev, MII_BMCR);
+		if (ret < 0)
+			return ret;
+	} while (ret & BMCR_RESET && --retries);
+	if (ret & BMCR_RESET)
+		return -ETIMEDOUT;
+
+	/*
+	 * Some chips (smsc911x) may still need up to another 1ms after the
+	 * BMCR_RESET bit is cleared before they are usable.
+	 */
+	msleep(1);
+	return 0;
+}
+
 int phy_init_hw(struct phy_device *phydev)
 {
 	int ret;
@@ -504,12 +549,21 @@ int phy_init_hw(struct phy_device *phydev)
 	if (!phydev->drv || !phydev->drv->config_init)
 		return 0;
 
+	ret = phy_write(phydev, MII_BMCR, BMCR_RESET);
+	if (ret < 0)
+		return ret;
+
+	ret = phy_poll_reset(phydev);
+	if (ret < 0)
+		return ret;
+
 	ret = phy_scan_fixups(phydev);
 	if (ret < 0)
 		return ret;
 
 	return phydev->drv->config_init(phydev);
 }
+EXPORT_SYMBOL(phy_init_hw);
 
 /**
  * phy_attach_direct - attach a network device to a given PHY device pointer
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 6/9] net: mv643xx_eth: use phy_init_hw to reset PHY
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
                   ` (4 preceding siblings ...)
  2013-12-06 21:01 ` [PATCH net-next v2 5/9] net: phy: consolidate PHY reset in phy_init_hw() Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-09 20:09   ` Sebastian Hesselbarth
  2013-12-06 21:01 ` [PATCH net-next v2 7/9] net: pxa168_eth: use phy_init_hw for PHY reset Florian Fainelli
                   ` (3 subsequent siblings)
  9 siblings, 1 reply; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

Instead of open-coding a PHY reset through the MII BMCR register, use
phy_init_hw() which does that for us and will also make sure that PHY
fixups are applied if required. We also remove a call to phy_reset()
due to the following sequence of calls in the driver:

phy_scan()
	-> phy_connect()
		-> phy_connect_direct()
			-> phy_attach_direct()
				-> phy_init_hw()

and we only have a call to phy_init() after phy_scan().

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
Changes since v2:
- improved commit message and explain why phy_reset() can go away
  entirely

 drivers/net/ethernet/marvell/mv643xx_eth.c | 21 +--------------------
 1 file changed, 1 insertion(+), 20 deletions(-)

diff --git a/drivers/net/ethernet/marvell/mv643xx_eth.c b/drivers/net/ethernet/marvell/mv643xx_eth.c
index fa90505..b3d9327 100644
--- a/drivers/net/ethernet/marvell/mv643xx_eth.c
+++ b/drivers/net/ethernet/marvell/mv643xx_eth.c
@@ -2066,23 +2066,6 @@ static inline void oom_timer_wrapper(unsigned long data)
 	napi_schedule(&mp->napi);
 }
 
-static void phy_reset(struct mv643xx_eth_private *mp)
-{
-	int data;
-
-	data = phy_read(mp->phy, MII_BMCR);
-	if (data < 0)
-		return;
-
-	data |= BMCR_RESET;
-	if (phy_write(mp->phy, MII_BMCR, data) < 0)
-		return;
-
-	do {
-		data = phy_read(mp->phy, MII_BMCR);
-	} while (data >= 0 && data & BMCR_RESET);
-}
-
 static void port_start(struct mv643xx_eth_private *mp)
 {
 	u32 pscr;
@@ -2095,7 +2078,7 @@ static void port_start(struct mv643xx_eth_private *mp)
 		struct ethtool_cmd cmd;
 
 		mv643xx_eth_get_settings(mp->dev, &cmd);
-		phy_reset(mp);
+		phy_init_hw(mp->phy);
 		mv643xx_eth_set_settings(mp->dev, &cmd);
 	}
 
@@ -2763,8 +2746,6 @@ static void phy_init(struct mv643xx_eth_private *mp, int speed, int duplex)
 {
 	struct phy_device *phy = mp->phy;
 
-	phy_reset(mp);
-
 	if (speed == 0) {
 		phy->autoneg = AUTONEG_ENABLE;
 		phy->speed = 0;
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 7/9] net: pxa168_eth: use phy_init_hw for PHY reset
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
                   ` (5 preceding siblings ...)
  2013-12-06 21:01 ` [PATCH net-next v2 6/9] net: mv643xx_eth: use phy_init_hw to reset PHY Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 8/9] net: tc35815: " Florian Fainelli
                   ` (2 subsequent siblings)
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

Instead of open-coding a PHY reset through the MII BMCR register, use
phy_init_hw() which does this for us and ensures that PHY device fixups
are also applied. We also remove a call to ethernet_phy_reset() which is
now unncessary since phy_attach() calls phy_attach_direct() which in
turns calls phy_init_hw().

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
Changes since v2:
- improve commit message and explain why ethernet_phy_reset() can go away
  entirely

 drivers/net/ethernet/marvell/pxa168_eth.c | 20 +-------------------
 1 file changed, 1 insertion(+), 19 deletions(-)

diff --git a/drivers/net/ethernet/marvell/pxa168_eth.c b/drivers/net/ethernet/marvell/pxa168_eth.c
index 2ad3241..452e81d 100644
--- a/drivers/net/ethernet/marvell/pxa168_eth.c
+++ b/drivers/net/ethernet/marvell/pxa168_eth.c
@@ -320,23 +320,6 @@ static void ethernet_phy_set_addr(struct pxa168_eth_private *pep, int phy_addr)
 	wrl(pep, PHY_ADDRESS, reg_data);
 }
 
-static void ethernet_phy_reset(struct pxa168_eth_private *pep)
-{
-	int data;
-
-	data = phy_read(pep->phy, MII_BMCR);
-	if (data < 0)
-		return;
-
-	data |= BMCR_RESET;
-	if (phy_write(pep->phy, MII_BMCR, data) < 0)
-		return;
-
-	do {
-		data = phy_read(pep->phy, MII_BMCR);
-	} while (data >= 0 && data & BMCR_RESET);
-}
-
 static void rxq_refill(struct net_device *dev)
 {
 	struct pxa168_eth_private *pep = netdev_priv(dev);
@@ -645,7 +628,7 @@ static void eth_port_start(struct net_device *dev)
 		struct ethtool_cmd cmd;
 
 		pxa168_get_settings(pep->dev, &cmd);
-		ethernet_phy_reset(pep);
+		phy_init_hw(pep->phy);
 		pxa168_set_settings(pep->dev, &cmd);
 	}
 
@@ -1382,7 +1365,6 @@ static struct phy_device *phy_scan(struct pxa168_eth_private *pep, int phy_addr)
 static void phy_init(struct pxa168_eth_private *pep, int speed, int duplex)
 {
 	struct phy_device *phy = pep->phy;
-	ethernet_phy_reset(pep);
 
 	phy_attach(pep->dev, dev_name(&phy->dev), PHY_INTERFACE_MODE_MII);
 
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 8/9] net: tc35815: use phy_init_hw for PHY reset
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
                   ` (6 preceding siblings ...)
  2013-12-06 21:01 ` [PATCH net-next v2 7/9] net: pxa168_eth: use phy_init_hw for PHY reset Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-06 21:01 ` [PATCH net-next v2 9/9] net: sh_eth: do not issue a wild PHY reset through BMCR Florian Fainelli
  2013-12-10  1:39 ` [PATCH net-next v2 0/9] net: phy: consolidate PHY reset David Miller
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

Instead of open-coding the PHY reset through MII BMCR, use phy_init_hw()
which does that for us and also makes sure that any PHY specific fixups
are applied.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
 drivers/net/ethernet/toshiba/tc35815.c | 15 ++++-----------
 1 file changed, 4 insertions(+), 11 deletions(-)

diff --git a/drivers/net/ethernet/toshiba/tc35815.c b/drivers/net/ethernet/toshiba/tc35815.c
index 1322546..f6b3212 100644
--- a/drivers/net/ethernet/toshiba/tc35815.c
+++ b/drivers/net/ethernet/toshiba/tc35815.c
@@ -1170,19 +1170,12 @@ static int tc35815_tx_full(struct net_device *dev)
 static void tc35815_restart(struct net_device *dev)
 {
 	struct tc35815_local *lp = netdev_priv(dev);
+	int ret;
 
 	if (lp->phy_dev) {
-		int timeout;
-
-		phy_write(lp->phy_dev, MII_BMCR, BMCR_RESET);
-		timeout = 100;
-		while (--timeout) {
-			if (!(phy_read(lp->phy_dev, MII_BMCR) & BMCR_RESET))
-				break;
-			udelay(1);
-		}
-		if (!timeout)
-			printk(KERN_ERR "%s: BMCR reset failed.\n", dev->name);
+		ret = phy_init_hw(lp->phy_dev);
+		if (ret)
+			printk(KERN_ERR "%s: PHY init failed.\n", dev->name);
 	}
 
 	spin_lock_bh(&lp->rx_lock);
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* [PATCH net-next v2 9/9] net: sh_eth: do not issue a wild PHY reset through BMCR
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
                   ` (7 preceding siblings ...)
  2013-12-06 21:01 ` [PATCH net-next v2 8/9] net: tc35815: " Florian Fainelli
@ 2013-12-06 21:01 ` Florian Fainelli
  2013-12-10  1:39 ` [PATCH net-next v2 0/9] net: phy: consolidate PHY reset David Miller
  9 siblings, 0 replies; 12+ messages in thread
From: Florian Fainelli @ 2013-12-06 21:01 UTC (permalink / raw)
  To: netdev
  Cc: davem, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle,
	Florian Fainelli

The sh_eth driver issues an uncontrolled PHY reset through the MII
register BMCR but fails to wait for the reset to complete, and will also
implicitely wipe out all possible PHY fixups applied. Use phy_init_hw()
which remedies both problems.

Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
---
 drivers/net/ethernet/renesas/sh_eth.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/drivers/net/ethernet/renesas/sh_eth.c b/drivers/net/ethernet/renesas/sh_eth.c
index d256ce1..6761dde 100644
--- a/drivers/net/ethernet/renesas/sh_eth.c
+++ b/drivers/net/ethernet/renesas/sh_eth.c
@@ -1704,7 +1704,10 @@ static int sh_eth_phy_start(struct net_device *ndev)
 		return ret;
 
 	/* reset phy - this also wakes it from PDOWN */
-	phy_write(mdp->phydev, MII_BMCR, BMCR_RESET);
+	ret = phy_init_hw(mdp->phydev);
+	if (ret)
+		return ret;
+
 	phy_start(mdp->phydev);
 
 	return 0;
-- 
1.8.3.2

^ permalink raw reply related	[flat|nested] 12+ messages in thread

* Re: [PATCH net-next v2 6/9] net: mv643xx_eth: use phy_init_hw to reset PHY
  2013-12-06 21:01 ` [PATCH net-next v2 6/9] net: mv643xx_eth: use phy_init_hw to reset PHY Florian Fainelli
@ 2013-12-09 20:09   ` Sebastian Hesselbarth
  0 siblings, 0 replies; 12+ messages in thread
From: Sebastian Hesselbarth @ 2013-12-09 20:09 UTC (permalink / raw)
  To: Florian Fainelli, netdev; +Cc: davem, sergei.shtylyov, afleming, kyle

On 12/06/2013 10:01 PM, Florian Fainelli wrote:
> Instead of open-coding a PHY reset through the MII BMCR register, use
> phy_init_hw() which does that for us and will also make sure that PHY
> fixups are applied if required. We also remove a call to phy_reset()
> due to the following sequence of calls in the driver:
>
> phy_scan()
> 	-> phy_connect()
> 		-> phy_connect_direct()
> 			-> phy_attach_direct()
> 				-> phy_init_hw()
>
> and we only have a call to phy_init() after phy_scan().
>
> Signed-off-by: Florian Fainelli <f.fainelli@gmail.com>
> ---
> Changes since v2:
> - improved commit message and explain why phy_reset() can go away
>    entirely

Series tested on mv643xx_eth with Marvell Dove SoC.

Tested-by: Sebastian Hesselbarth <sebastian.hesselbarth@gmail.com>

>   drivers/net/ethernet/marvell/mv643xx_eth.c | 21 +--------------------
>   1 file changed, 1 insertion(+), 20 deletions(-)

^ permalink raw reply	[flat|nested] 12+ messages in thread

* Re: [PATCH net-next v2 0/9] net: phy: consolidate PHY reset
  2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
                   ` (8 preceding siblings ...)
  2013-12-06 21:01 ` [PATCH net-next v2 9/9] net: sh_eth: do not issue a wild PHY reset through BMCR Florian Fainelli
@ 2013-12-10  1:39 ` David Miller
  9 siblings, 0 replies; 12+ messages in thread
From: David Miller @ 2013-12-10  1:39 UTC (permalink / raw)
  To: f.fainelli; +Cc: netdev, sebastian.hesselbarth, sergei.shtylyov, afleming, kyle

From: Florian Fainelli <f.fainelli@gmail.com>
Date: Fri, 6 Dec 2013 13:01:29 -0800

> This patchset consolidates the PHY reset through the MII BMCR
> register by using a central place were this is done.
> 
> This patchset resumes the work Kyle Moffett started here:
> https://lkml.org/lkml/2011/10/20/301
> 
> Note that at this point, drivers doing funky things after issuing
> a PHY reset using phy_init_hw() will still suffer from PHY state
> machine problems, this will be taken care of later on.

This looks fantastic, thanks for tackling this I know it isn't
easy.

Applied, thanks again!

^ permalink raw reply	[flat|nested] 12+ messages in thread

end of thread, other threads:[~2013-12-10  1:39 UTC | newest]

Thread overview: 12+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2013-12-06 21:01 [PATCH net-next v2 0/9] net: phy: consolidate PHY reset Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 1/9] net: phy: report link partner features through ethtool Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 2/9] net: phy: use phy_init_hw instead of open-coding it Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 3/9] net: greth: use phy_read_status() Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 4/9] net: bfin_mac: do not reset PHY after phy_start() Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 5/9] net: phy: consolidate PHY reset in phy_init_hw() Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 6/9] net: mv643xx_eth: use phy_init_hw to reset PHY Florian Fainelli
2013-12-09 20:09   ` Sebastian Hesselbarth
2013-12-06 21:01 ` [PATCH net-next v2 7/9] net: pxa168_eth: use phy_init_hw for PHY reset Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 8/9] net: tc35815: " Florian Fainelli
2013-12-06 21:01 ` [PATCH net-next v2 9/9] net: sh_eth: do not issue a wild PHY reset through BMCR Florian Fainelli
2013-12-10  1:39 ` [PATCH net-next v2 0/9] net: phy: consolidate PHY reset David Miller

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).