diff options
Diffstat (limited to 'net/dsa/slave.c')
-rw-r--r-- | net/dsa/slave.c | 19 |
1 files changed, 16 insertions, 3 deletions
diff --git a/net/dsa/slave.c b/net/dsa/slave.c index d0c7bce88743..68c9eea00518 100644 --- a/net/dsa/slave.c +++ b/net/dsa/slave.c | |||
@@ -1127,7 +1127,7 @@ static int dsa_slave_phy_setup(struct dsa_slave_priv *p, | |||
1127 | p->phy_interface = mode; | 1127 | p->phy_interface = mode; |
1128 | 1128 | ||
1129 | phy_dn = of_parse_phandle(port_dn, "phy-handle", 0); | 1129 | phy_dn = of_parse_phandle(port_dn, "phy-handle", 0); |
1130 | if (of_phy_is_fixed_link(port_dn)) { | 1130 | if (!phy_dn && of_phy_is_fixed_link(port_dn)) { |
1131 | /* In the case of a fixed PHY, the DT node associated | 1131 | /* In the case of a fixed PHY, the DT node associated |
1132 | * to the fixed PHY is the Port DT node | 1132 | * to the fixed PHY is the Port DT node |
1133 | */ | 1133 | */ |
@@ -1137,7 +1137,7 @@ static int dsa_slave_phy_setup(struct dsa_slave_priv *p, | |||
1137 | return ret; | 1137 | return ret; |
1138 | } | 1138 | } |
1139 | phy_is_fixed = true; | 1139 | phy_is_fixed = true; |
1140 | phy_dn = port_dn; | 1140 | phy_dn = of_node_get(port_dn); |
1141 | } | 1141 | } |
1142 | 1142 | ||
1143 | if (ds->ops->get_phy_flags) | 1143 | if (ds->ops->get_phy_flags) |
@@ -1156,6 +1156,7 @@ static int dsa_slave_phy_setup(struct dsa_slave_priv *p, | |||
1156 | ret = dsa_slave_phy_connect(p, slave_dev, phy_id); | 1156 | ret = dsa_slave_phy_connect(p, slave_dev, phy_id); |
1157 | if (ret) { | 1157 | if (ret) { |
1158 | netdev_err(slave_dev, "failed to connect to phy%d: %d\n", phy_id, ret); | 1158 | netdev_err(slave_dev, "failed to connect to phy%d: %d\n", phy_id, ret); |
1159 | of_node_put(phy_dn); | ||
1159 | return ret; | 1160 | return ret; |
1160 | } | 1161 | } |
1161 | } else { | 1162 | } else { |
@@ -1164,6 +1165,8 @@ static int dsa_slave_phy_setup(struct dsa_slave_priv *p, | |||
1164 | phy_flags, | 1165 | phy_flags, |
1165 | p->phy_interface); | 1166 | p->phy_interface); |
1166 | } | 1167 | } |
1168 | |||
1169 | of_node_put(phy_dn); | ||
1167 | } | 1170 | } |
1168 | 1171 | ||
1169 | if (p->phy && phy_is_fixed) | 1172 | if (p->phy && phy_is_fixed) |
@@ -1176,6 +1179,8 @@ static int dsa_slave_phy_setup(struct dsa_slave_priv *p, | |||
1176 | ret = dsa_slave_phy_connect(p, slave_dev, p->port); | 1179 | ret = dsa_slave_phy_connect(p, slave_dev, p->port); |
1177 | if (ret) { | 1180 | if (ret) { |
1178 | netdev_err(slave_dev, "failed to connect to port %d: %d\n", p->port, ret); | 1181 | netdev_err(slave_dev, "failed to connect to port %d: %d\n", p->port, ret); |
1182 | if (phy_is_fixed) | ||
1183 | of_phy_deregister_fixed_link(port_dn); | ||
1179 | return ret; | 1184 | return ret; |
1180 | } | 1185 | } |
1181 | } | 1186 | } |
@@ -1293,10 +1298,18 @@ int dsa_slave_create(struct dsa_switch *ds, struct device *parent, | |||
1293 | void dsa_slave_destroy(struct net_device *slave_dev) | 1298 | void dsa_slave_destroy(struct net_device *slave_dev) |
1294 | { | 1299 | { |
1295 | struct dsa_slave_priv *p = netdev_priv(slave_dev); | 1300 | struct dsa_slave_priv *p = netdev_priv(slave_dev); |
1301 | struct dsa_switch *ds = p->parent; | ||
1302 | struct device_node *port_dn; | ||
1303 | |||
1304 | port_dn = ds->ports[p->port].dn; | ||
1296 | 1305 | ||
1297 | netif_carrier_off(slave_dev); | 1306 | netif_carrier_off(slave_dev); |
1298 | if (p->phy) | 1307 | if (p->phy) { |
1299 | phy_disconnect(p->phy); | 1308 | phy_disconnect(p->phy); |
1309 | |||
1310 | if (of_phy_is_fixed_link(port_dn)) | ||
1311 | of_phy_deregister_fixed_link(port_dn); | ||
1312 | } | ||
1300 | unregister_netdev(slave_dev); | 1313 | unregister_netdev(slave_dev); |
1301 | free_netdev(slave_dev); | 1314 | free_netdev(slave_dev); |
1302 | } | 1315 | } |