aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/phy
diff options
context:
space:
mode:
authorKirill Kapranov <kapranoff@inbox.ru>2013-03-26 21:16:13 -0400
committerDavid S. Miller <davem@davemloft.net>2013-03-27 13:10:43 -0400
commita33e6112d9b0c1ab4fb55bb538832ec789200a10 (patch)
tree7e48c42eb61c180e3c508b576e1776f927c91243 /drivers/net/phy
parent1b5ab0def4f6e42e8b8097c3b11d2e8d96baafec (diff)
phy: Elimination the forced speed reduction algorithm.
In case of fixed speed set up for a NIC (e.g. ethtool -s eth0 autoneg off speed 100 duplex full) with an ethernet cable plugged off, the mentioned algorithm slows down a NIC speed, so further cable hook-up leads to nonoperable link state. Signed-off-by: Kirill Kapranov <kapranoff@inbox.ru> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/phy')
-rw-r--r--drivers/net/phy/phy.c50
1 files changed, 1 insertions, 49 deletions
diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 298b4c201733..c14f14741b3f 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -463,33 +463,6 @@ void phy_stop_machine(struct phy_device *phydev)
463} 463}
464 464
465/** 465/**
466 * phy_force_reduction - reduce PHY speed/duplex settings by one step
467 * @phydev: target phy_device struct
468 *
469 * Description: Reduces the speed/duplex settings by one notch,
470 * in this order--
471 * 1000/FULL, 1000/HALF, 100/FULL, 100/HALF, 10/FULL, 10/HALF.
472 * The function bottoms out at 10/HALF.
473 */
474static void phy_force_reduction(struct phy_device *phydev)
475{
476 int idx;
477
478 idx = phy_find_setting(phydev->speed, phydev->duplex);
479
480 idx++;
481
482 idx = phy_find_valid(idx, phydev->supported);
483
484 phydev->speed = settings[idx].speed;
485 phydev->duplex = settings[idx].duplex;
486
487 pr_info("Trying %d/%s\n",
488 phydev->speed, DUPLEX_FULL == phydev->duplex ? "FULL" : "HALF");
489}
490
491
492/**
493 * phy_error - enter HALTED state for this PHY device 466 * phy_error - enter HALTED state for this PHY device
494 * @phydev: target phy_device struct 467 * @phydev: target phy_device struct
495 * 468 *
@@ -818,30 +791,11 @@ void phy_state_machine(struct work_struct *work)
818 phydev->adjust_link(phydev->attached_dev); 791 phydev->adjust_link(phydev->attached_dev);
819 792
820 } else if (0 == phydev->link_timeout--) { 793 } else if (0 == phydev->link_timeout--) {
821 int idx;
822
823 needs_aneg = 1; 794 needs_aneg = 1;
824 /* If we have the magic_aneg bit, 795 /* If we have the magic_aneg bit,
825 * we try again */ 796 * we try again */
826 if (phydev->drv->flags & PHY_HAS_MAGICANEG) 797 if (phydev->drv->flags & PHY_HAS_MAGICANEG)
827 break; 798 break;
828
829 /* The timer expired, and we still
830 * don't have a setting, so we try
831 * forcing it until we find one that
832 * works, starting from the fastest speed,
833 * and working our way down */
834 idx = phy_find_valid(0, phydev->supported);
835
836 phydev->speed = settings[idx].speed;
837 phydev->duplex = settings[idx].duplex;
838
839 phydev->autoneg = AUTONEG_DISABLE;
840
841 pr_info("Trying %d/%s\n",
842 phydev->speed,
843 DUPLEX_FULL == phydev->duplex ?
844 "FULL" : "HALF");
845 } 799 }
846 break; 800 break;
847 case PHY_NOLINK: 801 case PHY_NOLINK:
@@ -866,10 +820,8 @@ void phy_state_machine(struct work_struct *work)
866 phydev->state = PHY_RUNNING; 820 phydev->state = PHY_RUNNING;
867 netif_carrier_on(phydev->attached_dev); 821 netif_carrier_on(phydev->attached_dev);
868 } else { 822 } else {
869 if (0 == phydev->link_timeout--) { 823 if (0 == phydev->link_timeout--)
870 phy_force_reduction(phydev);
871 needs_aneg = 1; 824 needs_aneg = 1;
872 }
873 } 825 }
874 826
875 phydev->adjust_link(phydev->attached_dev); 827 phydev->adjust_link(phydev->attached_dev);