diff options
Diffstat (limited to 'drivers/net/tg3.c')
-rw-r--r-- | drivers/net/tg3.c | 37 |
1 files changed, 31 insertions, 6 deletions
diff --git a/drivers/net/tg3.c b/drivers/net/tg3.c index 81f4aedf534c..ef2f1fdd6f64 100644 --- a/drivers/net/tg3.c +++ b/drivers/net/tg3.c | |||
@@ -5806,6 +5806,13 @@ static int tg3_reset_hw(struct tg3 *tp) | |||
5806 | } | 5806 | } |
5807 | memset(tp->hw_status, 0, TG3_HW_STATUS_SIZE); | 5807 | memset(tp->hw_status, 0, TG3_HW_STATUS_SIZE); |
5808 | 5808 | ||
5809 | if (tp->tg3_flags2 & TG3_FLG2_MII_SERDES) { | ||
5810 | tp->tg3_flags2 &= ~TG3_FLG2_PARALLEL_DETECT; | ||
5811 | /* reset to prevent losing 1st rx packet intermittently */ | ||
5812 | tw32_f(MAC_RX_MODE, RX_MODE_RESET); | ||
5813 | udelay(10); | ||
5814 | } | ||
5815 | |||
5809 | tp->mac_mode = MAC_MODE_TXSTAT_ENABLE | MAC_MODE_RXSTAT_ENABLE | | 5816 | tp->mac_mode = MAC_MODE_TXSTAT_ENABLE | MAC_MODE_RXSTAT_ENABLE | |
5810 | MAC_MODE_TDE_ENABLE | MAC_MODE_RDE_ENABLE | MAC_MODE_FHDE_ENABLE; | 5817 | MAC_MODE_TDE_ENABLE | MAC_MODE_RDE_ENABLE | MAC_MODE_FHDE_ENABLE; |
5811 | tw32_f(MAC_MODE, tp->mac_mode | MAC_MODE_RXSTAT_CLEAR | MAC_MODE_TXSTAT_CLEAR); | 5818 | tw32_f(MAC_MODE, tp->mac_mode | MAC_MODE_RXSTAT_CLEAR | MAC_MODE_TXSTAT_CLEAR); |
@@ -5937,7 +5944,7 @@ static int tg3_reset_hw(struct tg3 *tp) | |||
5937 | tw32(MAC_LED_CTRL, tp->led_ctrl); | 5944 | tw32(MAC_LED_CTRL, tp->led_ctrl); |
5938 | 5945 | ||
5939 | tw32(MAC_MI_STAT, MAC_MI_STAT_LNKSTAT_ATTN_ENAB); | 5946 | tw32(MAC_MI_STAT, MAC_MI_STAT_LNKSTAT_ATTN_ENAB); |
5940 | if (tp->tg3_flags2 & TG3_FLG2_ANY_SERDES) { | 5947 | if (tp->tg3_flags2 & TG3_FLG2_PHY_SERDES) { |
5941 | tw32_f(MAC_RX_MODE, RX_MODE_RESET); | 5948 | tw32_f(MAC_RX_MODE, RX_MODE_RESET); |
5942 | udelay(10); | 5949 | udelay(10); |
5943 | } | 5950 | } |
@@ -7360,12 +7367,17 @@ static int tg3_nway_reset(struct net_device *dev) | |||
7360 | if (!netif_running(dev)) | 7367 | if (!netif_running(dev)) |
7361 | return -EAGAIN; | 7368 | return -EAGAIN; |
7362 | 7369 | ||
7370 | if (tp->tg3_flags2 & TG3_FLG2_PHY_SERDES) | ||
7371 | return -EINVAL; | ||
7372 | |||
7363 | spin_lock_bh(&tp->lock); | 7373 | spin_lock_bh(&tp->lock); |
7364 | r = -EINVAL; | 7374 | r = -EINVAL; |
7365 | tg3_readphy(tp, MII_BMCR, &bmcr); | 7375 | tg3_readphy(tp, MII_BMCR, &bmcr); |
7366 | if (!tg3_readphy(tp, MII_BMCR, &bmcr) && | 7376 | if (!tg3_readphy(tp, MII_BMCR, &bmcr) && |
7367 | (bmcr & BMCR_ANENABLE)) { | 7377 | ((bmcr & BMCR_ANENABLE) || |
7368 | tg3_writephy(tp, MII_BMCR, bmcr | BMCR_ANRESTART); | 7378 | (tp->tg3_flags2 & TG3_FLG2_PARALLEL_DETECT))) { |
7379 | tg3_writephy(tp, MII_BMCR, bmcr | BMCR_ANRESTART | | ||
7380 | BMCR_ANENABLE); | ||
7369 | r = 0; | 7381 | r = 0; |
7370 | } | 7382 | } |
7371 | spin_unlock_bh(&tp->lock); | 7383 | spin_unlock_bh(&tp->lock); |
@@ -7927,19 +7939,32 @@ static int tg3_run_loopback(struct tg3 *tp, int loopback_mode) | |||
7927 | struct tg3_rx_buffer_desc *desc; | 7939 | struct tg3_rx_buffer_desc *desc; |
7928 | 7940 | ||
7929 | if (loopback_mode == TG3_MAC_LOOPBACK) { | 7941 | if (loopback_mode == TG3_MAC_LOOPBACK) { |
7942 | /* HW errata - mac loopback fails in some cases on 5780. | ||
7943 | * Normal traffic and PHY loopback are not affected by | ||
7944 | * errata. | ||
7945 | */ | ||
7946 | if (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5780) | ||
7947 | return 0; | ||
7948 | |||
7930 | mac_mode = (tp->mac_mode & ~MAC_MODE_PORT_MODE_MASK) | | 7949 | mac_mode = (tp->mac_mode & ~MAC_MODE_PORT_MODE_MASK) | |
7931 | MAC_MODE_PORT_INT_LPBACK | MAC_MODE_LINK_POLARITY | | 7950 | MAC_MODE_PORT_INT_LPBACK | MAC_MODE_LINK_POLARITY | |
7932 | MAC_MODE_PORT_MODE_GMII; | 7951 | MAC_MODE_PORT_MODE_GMII; |
7933 | tw32(MAC_MODE, mac_mode); | 7952 | tw32(MAC_MODE, mac_mode); |
7934 | } else if (loopback_mode == TG3_PHY_LOOPBACK) { | 7953 | } else if (loopback_mode == TG3_PHY_LOOPBACK) { |
7954 | tg3_writephy(tp, MII_BMCR, BMCR_LOOPBACK | BMCR_FULLDPLX | | ||
7955 | BMCR_SPEED1000); | ||
7956 | udelay(40); | ||
7957 | /* reset to prevent losing 1st rx packet intermittently */ | ||
7958 | if (tp->tg3_flags2 & TG3_FLG2_MII_SERDES) { | ||
7959 | tw32_f(MAC_RX_MODE, RX_MODE_RESET); | ||
7960 | udelay(10); | ||
7961 | tw32_f(MAC_RX_MODE, tp->rx_mode); | ||
7962 | } | ||
7935 | mac_mode = (tp->mac_mode & ~MAC_MODE_PORT_MODE_MASK) | | 7963 | mac_mode = (tp->mac_mode & ~MAC_MODE_PORT_MODE_MASK) | |
7936 | MAC_MODE_LINK_POLARITY | MAC_MODE_PORT_MODE_GMII; | 7964 | MAC_MODE_LINK_POLARITY | MAC_MODE_PORT_MODE_GMII; |
7937 | if ((tp->phy_id & PHY_ID_MASK) == PHY_ID_BCM5401) | 7965 | if ((tp->phy_id & PHY_ID_MASK) == PHY_ID_BCM5401) |
7938 | mac_mode &= ~MAC_MODE_LINK_POLARITY; | 7966 | mac_mode &= ~MAC_MODE_LINK_POLARITY; |
7939 | tw32(MAC_MODE, mac_mode); | 7967 | tw32(MAC_MODE, mac_mode); |
7940 | |||
7941 | tg3_writephy(tp, MII_BMCR, BMCR_LOOPBACK | BMCR_FULLDPLX | | ||
7942 | BMCR_SPEED1000); | ||
7943 | } | 7968 | } |
7944 | else | 7969 | else |
7945 | return -EINVAL; | 7970 | return -EINVAL; |