From: Rafał Miłecki Date: Wed, 1 Feb 2017 19:53:15 +0000 (+0100) Subject: kernel: fix BCM54612E PHY support X-Git-Url: http://git.cdn.openwrt.org/?a=commitdiff_plain;h=0224e32cd0b1ac400f4d52b66d4839d90a328277;p=openwrt%2Fstaging%2Fwigyori.git kernel: fix BCM54612E PHY support This backports upstream commit 62e13097c46c ("net: phy: broadcom: rehook BCM54612E specific init") Signed-off-by: Rafał Miłecki --- diff --git a/target/linux/generic/patches-4.4/078-0004-net-phy-pick-Broadcom-drivers-updates-from-net-next-.patch b/target/linux/generic/patches-4.4/078-0004-net-phy-pick-Broadcom-drivers-updates-from-net-next-.patch index 87d6c50069..d050691841 100644 --- a/target/linux/generic/patches-4.4/078-0004-net-phy-pick-Broadcom-drivers-updates-from-net-next-.patch +++ b/target/linux/generic/patches-4.4/078-0004-net-phy-pick-Broadcom-drivers-updates-from-net-next-.patch @@ -1,6 +1,6 @@ --- a/drivers/net/phy/broadcom.c +++ b/drivers/net/phy/broadcom.c -@@ -30,6 +30,22 @@ MODULE_DESCRIPTION("Broadcom PHY driver" +@@ -30,6 +30,50 @@ MODULE_DESCRIPTION("Broadcom PHY driver" MODULE_AUTHOR("Maciej W. Rozycki"); MODULE_LICENSE("GPL"); @@ -19,11 +19,39 @@ + + return 0; +} ++ ++static int bcm54612e_config_init(struct phy_device *phydev) ++{ ++ /* Clear TX internal delay unless requested. */ ++ if ((phydev->interface != PHY_INTERFACE_MODE_RGMII_ID) && ++ (phydev->interface != PHY_INTERFACE_MODE_RGMII_TXID)) { ++ /* Disable TXD to GTXCLK clock delay (default set) */ ++ /* Bit 9 is the only field in shadow register 00011 */ ++ bcm_phy_write_shadow(phydev, 0x03, 0); ++ } ++ ++ /* Clear RX internal delay unless requested. */ ++ if ((phydev->interface != PHY_INTERFACE_MODE_RGMII_ID) && ++ (phydev->interface != PHY_INTERFACE_MODE_RGMII_RXID)) { ++ u16 reg; ++ ++ reg = bcm54xx_auxctl_read(phydev, ++ MII_BCM54XX_AUXCTL_SHDWSEL_MISC); ++ /* Disable RXD to RXC delay (default set) */ ++ reg &= ~MII_BCM54XX_AUXCTL_SHDWSEL_MISC_RGMII_SKEW_EN; ++ /* Clear shadow selector field */ ++ reg &= ~MII_BCM54XX_AUXCTL_SHDWSEL_MASK; ++ bcm54xx_auxctl_write(phydev, MII_BCM54XX_AUXCTL_SHDWSEL_MISC, ++ MII_BCM54XX_AUXCTL_MISC_WREN | reg); ++ } ++ ++ return 0; ++} + static int bcm54810_config(struct phy_device *phydev) { int rc, val; -@@ -230,7 +246,11 @@ static int bcm54xx_config_init(struct ph +@@ -230,7 +274,15 @@ static int bcm54xx_config_init(struct ph (phydev->dev_flags & PHY_BRCM_AUTO_PWRDWN_ENABLE)) bcm54xx_adjust_rxrefclk(phydev); @@ -32,11 +60,57 @@ + err = bcm54210e_config_init(phydev); + if (err) + return err; ++ } else if (BRCM_PHY_MODEL(phydev) == PHY_ID_BCM54612E) { ++ err = bcm54612e_config_init(phydev); ++ if (err) ++ return err; + } else if (BRCM_PHY_MODEL(phydev) == PHY_ID_BCM54810) { err = bcm54810_config(phydev); if (err) return err; -@@ -548,6 +568,19 @@ static struct phy_driver broadcom_driver +@@ -375,41 +427,6 @@ static int bcm5481_config_aneg(struct ph + return ret; + } + +-static int bcm54612e_config_aneg(struct phy_device *phydev) +-{ +- int ret; +- +- /* First, auto-negotiate. */ +- ret = genphy_config_aneg(phydev); +- +- /* Clear TX internal delay unless requested. */ +- if ((phydev->interface != PHY_INTERFACE_MODE_RGMII_ID) && +- (phydev->interface != PHY_INTERFACE_MODE_RGMII_TXID)) { +- /* Disable TXD to GTXCLK clock delay (default set) */ +- /* Bit 9 is the only field in shadow register 00011 */ +- bcm_phy_write_shadow(phydev, 0x03, 0); +- } +- +- /* Clear RX internal delay unless requested. */ +- if ((phydev->interface != PHY_INTERFACE_MODE_RGMII_ID) && +- (phydev->interface != PHY_INTERFACE_MODE_RGMII_RXID)) { +- u16 reg; +- +- /* Errata: reads require filling in the write selector field */ +- bcm54xx_auxctl_write(phydev, MII_BCM54XX_AUXCTL_SHDWSEL_MISC, +- MII_BCM54XX_AUXCTL_MISC_RDSEL_MISC); +- reg = phy_read(phydev, MII_BCM54XX_AUX_CTL); +- /* Disable RXD to RXC delay (default set) */ +- reg &= ~MII_BCM54XX_AUXCTL_MISC_RXD_RXC_SKEW; +- /* Clear shadow selector field */ +- reg &= ~MII_BCM54XX_AUXCTL_SHDWSEL_MASK; +- bcm54xx_auxctl_write(phydev, MII_BCM54XX_AUXCTL_SHDWSEL_MISC, +- MII_BCM54XX_AUXCTL_MISC_WREN | reg); +- } +- +- return ret; +-} +- + static int brcm_phy_setbits(struct phy_device *phydev, int reg, int set) + { + int val; +@@ -548,6 +565,19 @@ static struct phy_driver broadcom_driver .config_intr = bcm_phy_config_intr, .driver = { .owner = THIS_MODULE }, }, { @@ -56,7 +130,16 @@ .phy_id = PHY_ID_BCM5461, .phy_id_mask = 0xfffffff0, .name = "Broadcom BCM5461", -@@ -710,6 +743,7 @@ module_phy_driver(broadcom_drivers); +@@ -568,7 +598,7 @@ static struct phy_driver broadcom_driver + SUPPORTED_Pause | SUPPORTED_Asym_Pause, + .flags = PHY_HAS_MAGICANEG | PHY_HAS_INTERRUPT, + .config_init = bcm54xx_config_init, +- .config_aneg = bcm54612e_config_aneg, ++ .config_aneg = genphy_config_aneg, + .read_status = genphy_read_status, + .ack_interrupt = bcm_phy_ack_intr, + .config_intr = bcm_phy_config_intr, +@@ -710,6 +740,7 @@ module_phy_driver(broadcom_drivers); static struct mdio_device_id __maybe_unused broadcom_tbl[] = { { PHY_ID_BCM5411, 0xfffffff0 }, { PHY_ID_BCM5421, 0xfffffff0 },