diff options
author | David S. Miller <davem@davemloft.net> | 2014-12-11 21:00:13 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2014-12-11 21:00:13 -0500 |
commit | c11a9009ae6a8c42a8cd69d885601e1aa6fbea04 (patch) | |
tree | 2298b1c69843267ef079f7d7486caf1f3e433c79 | |
parent | 70e71ca0af244f48a5dcf56dc435243792e3a495 (diff) | |
parent | 9697f1cde9901c00298fd1313b4aaf96f287bf7a (diff) |
Merge branch 'dsa'
Florian Fainelli says:
====================
net: dsa: two small bug fixes
Here are two small fixes for the DSA slave interface creation code:
- first patch fixes a null pointer de-reference with an invalid PHY
device pointer while calling phy_connect_direct()
- second path propagates the dsa_slave_phy_setup() error code down to
its caller: dsa_slave_create
====================
Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r-- | net/dsa/slave.c | 16 |
1 files changed, 13 insertions, 3 deletions
diff --git a/net/dsa/slave.c b/net/dsa/slave.c index 528380a3e296..515569ffde8a 100644 --- a/net/dsa/slave.c +++ b/net/dsa/slave.c | |||
@@ -512,7 +512,7 @@ static int dsa_slave_fixed_link_update(struct net_device *dev, | |||
512 | } | 512 | } |
513 | 513 | ||
514 | /* slave device setup *******************************************************/ | 514 | /* slave device setup *******************************************************/ |
515 | static void dsa_slave_phy_setup(struct dsa_slave_priv *p, | 515 | static int dsa_slave_phy_setup(struct dsa_slave_priv *p, |
516 | struct net_device *slave_dev) | 516 | struct net_device *slave_dev) |
517 | { | 517 | { |
518 | struct dsa_switch *ds = p->parent; | 518 | struct dsa_switch *ds = p->parent; |
@@ -533,7 +533,7 @@ static void dsa_slave_phy_setup(struct dsa_slave_priv *p, | |||
533 | ret = of_phy_register_fixed_link(port_dn); | 533 | ret = of_phy_register_fixed_link(port_dn); |
534 | if (ret) { | 534 | if (ret) { |
535 | netdev_err(slave_dev, "failed to register fixed PHY\n"); | 535 | netdev_err(slave_dev, "failed to register fixed PHY\n"); |
536 | return; | 536 | return ret; |
537 | } | 537 | } |
538 | phy_is_fixed = true; | 538 | phy_is_fixed = true; |
539 | phy_dn = port_dn; | 539 | phy_dn = port_dn; |
@@ -555,12 +555,17 @@ static void dsa_slave_phy_setup(struct dsa_slave_priv *p, | |||
555 | */ | 555 | */ |
556 | if (!p->phy) { | 556 | if (!p->phy) { |
557 | p->phy = ds->slave_mii_bus->phy_map[p->port]; | 557 | p->phy = ds->slave_mii_bus->phy_map[p->port]; |
558 | if (!p->phy) | ||
559 | return -ENODEV; | ||
560 | |||
558 | phy_connect_direct(slave_dev, p->phy, dsa_slave_adjust_link, | 561 | phy_connect_direct(slave_dev, p->phy, dsa_slave_adjust_link, |
559 | p->phy_interface); | 562 | p->phy_interface); |
560 | } else { | 563 | } else { |
561 | netdev_info(slave_dev, "attached PHY at address %d [%s]\n", | 564 | netdev_info(slave_dev, "attached PHY at address %d [%s]\n", |
562 | p->phy->addr, p->phy->drv->name); | 565 | p->phy->addr, p->phy->drv->name); |
563 | } | 566 | } |
567 | |||
568 | return 0; | ||
564 | } | 569 | } |
565 | 570 | ||
566 | int dsa_slave_suspend(struct net_device *slave_dev) | 571 | int dsa_slave_suspend(struct net_device *slave_dev) |
@@ -653,12 +658,17 @@ dsa_slave_create(struct dsa_switch *ds, struct device *parent, | |||
653 | p->old_link = -1; | 658 | p->old_link = -1; |
654 | p->old_duplex = -1; | 659 | p->old_duplex = -1; |
655 | 660 | ||
656 | dsa_slave_phy_setup(p, slave_dev); | 661 | ret = dsa_slave_phy_setup(p, slave_dev); |
662 | if (ret) { | ||
663 | free_netdev(slave_dev); | ||
664 | return NULL; | ||
665 | } | ||
657 | 666 | ||
658 | ret = register_netdev(slave_dev); | 667 | ret = register_netdev(slave_dev); |
659 | if (ret) { | 668 | if (ret) { |
660 | netdev_err(master, "error %d registering interface %s\n", | 669 | netdev_err(master, "error %d registering interface %s\n", |
661 | ret, slave_dev->name); | 670 | ret, slave_dev->name); |
671 | phy_disconnect(p->phy); | ||
662 | free_netdev(slave_dev); | 672 | free_netdev(slave_dev); |
663 | return NULL; | 673 | return NULL; |
664 | } | 674 | } |