aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAlvaro Gamez Machado <alvaro.gamez@hazent.com>2018-06-08 06:23:39 -0400
committerDavid S. Miller <davem@davemloft.net>2018-06-10 15:38:03 -0400
commitb718e8c8f4f5920aaddc2e52d5e32f494c91129c (patch)
treef7147d1b843d1f8219bba61bb006f3e0da6f6fec
parent6d8c50dcb029872b298eea68cc6209c866fd3e14 (diff)
net: phy: dp83822: use BMCR_ANENABLE instead of BMSR_ANEGCAPABLE for DP83620
DP83620 register set is compatible with the DP83848, but it also supports 100base-FX. When the hardware is configured such as that fiber mode is enabled, autonegotiation is not possible. The chip, however, doesn't expose this information via BMSR_ANEGCAPABLE. Instead, this bit is always set high, even if the particular hardware configuration makes it so that auto negotiation is not possible [1]. Under these circumstances, the phy subsystem keeps trying for autonegotiation to happen, without success. Hereby, we inspect BMCR_ANENABLE bit after genphy_config_init, which on reset is set to 0 when auto negotiation is disabled, and so we use this value instead of BMSR_ANEGCAPABLE. [1] https://e2e.ti.com/support/interface/ethernet/f/903/p/697165/2571170 Signed-off-by: Alvaro Gamez Machado <alvaro.gamez@hazent.com> Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r--drivers/net/phy/dp83848.c35
1 files changed, 29 insertions, 6 deletions
diff --git a/drivers/net/phy/dp83848.c b/drivers/net/phy/dp83848.c
index cd09c3af2117..6e8e42361fd5 100644
--- a/drivers/net/phy/dp83848.c
+++ b/drivers/net/phy/dp83848.c
@@ -74,6 +74,25 @@ static int dp83848_config_intr(struct phy_device *phydev)
74 return phy_write(phydev, DP83848_MICR, control); 74 return phy_write(phydev, DP83848_MICR, control);
75} 75}
76 76
77static int dp83848_config_init(struct phy_device *phydev)
78{
79 int err;
80 int val;
81
82 err = genphy_config_init(phydev);
83 if (err < 0)
84 return err;
85
86 /* DP83620 always reports Auto Negotiation Ability on BMSR. Instead,
87 * we check initial value of BMCR Auto negotiation enable bit
88 */
89 val = phy_read(phydev, MII_BMCR);
90 if (!(val & BMCR_ANENABLE))
91 phydev->autoneg = AUTONEG_DISABLE;
92
93 return 0;
94}
95
77static struct mdio_device_id __maybe_unused dp83848_tbl[] = { 96static struct mdio_device_id __maybe_unused dp83848_tbl[] = {
78 { TI_DP83848C_PHY_ID, 0xfffffff0 }, 97 { TI_DP83848C_PHY_ID, 0xfffffff0 },
79 { NS_DP83848C_PHY_ID, 0xfffffff0 }, 98 { NS_DP83848C_PHY_ID, 0xfffffff0 },
@@ -83,7 +102,7 @@ static struct mdio_device_id __maybe_unused dp83848_tbl[] = {
83}; 102};
84MODULE_DEVICE_TABLE(mdio, dp83848_tbl); 103MODULE_DEVICE_TABLE(mdio, dp83848_tbl);
85 104
86#define DP83848_PHY_DRIVER(_id, _name) \ 105#define DP83848_PHY_DRIVER(_id, _name, _config_init) \
87 { \ 106 { \
88 .phy_id = _id, \ 107 .phy_id = _id, \
89 .phy_id_mask = 0xfffffff0, \ 108 .phy_id_mask = 0xfffffff0, \
@@ -92,7 +111,7 @@ MODULE_DEVICE_TABLE(mdio, dp83848_tbl);
92 .flags = PHY_HAS_INTERRUPT, \ 111 .flags = PHY_HAS_INTERRUPT, \
93 \ 112 \
94 .soft_reset = genphy_soft_reset, \ 113 .soft_reset = genphy_soft_reset, \
95 .config_init = genphy_config_init, \ 114 .config_init = _config_init, \
96 .suspend = genphy_suspend, \ 115 .suspend = genphy_suspend, \
97 .resume = genphy_resume, \ 116 .resume = genphy_resume, \
98 \ 117 \
@@ -102,10 +121,14 @@ MODULE_DEVICE_TABLE(mdio, dp83848_tbl);
102 } 121 }
103 122
104static struct phy_driver dp83848_driver[] = { 123static struct phy_driver dp83848_driver[] = {
105 DP83848_PHY_DRIVER(TI_DP83848C_PHY_ID, "TI DP83848C 10/100 Mbps PHY"), 124 DP83848_PHY_DRIVER(TI_DP83848C_PHY_ID, "TI DP83848C 10/100 Mbps PHY",
106 DP83848_PHY_DRIVER(NS_DP83848C_PHY_ID, "NS DP83848C 10/100 Mbps PHY"), 125 genphy_config_init),
107 DP83848_PHY_DRIVER(TI_DP83620_PHY_ID, "TI DP83620 10/100 Mbps PHY"), 126 DP83848_PHY_DRIVER(NS_DP83848C_PHY_ID, "NS DP83848C 10/100 Mbps PHY",
108 DP83848_PHY_DRIVER(TLK10X_PHY_ID, "TI TLK10X 10/100 Mbps PHY"), 127 genphy_config_init),
128 DP83848_PHY_DRIVER(TI_DP83620_PHY_ID, "TI DP83620 10/100 Mbps PHY",
129 dp83848_config_init),
130 DP83848_PHY_DRIVER(TLK10X_PHY_ID, "TI TLK10X 10/100 Mbps PHY",
131 genphy_config_init),
109}; 132};
110module_phy_driver(dp83848_driver); 133module_phy_driver(dp83848_driver);
111 134