aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorMichael Chan <mchan@broadcom.com>2012-07-29 15:15:43 -0400
committerDavid S. Miller <davem@davemloft.net>2012-07-30 02:18:31 -0400
commit091f0ea30074bc43f9250961b3247af713024bc6 (patch)
tree6811dce54854469457b3c5e20d150f160de0c4ba /drivers
parent10ce95d6ef36c65df7dcd3b8fcf86913f8b298bd (diff)
tg3: Add New 5719 Read DMA workaround
After Power-on-reset, the 5719's TX DMA length registers may contain uninitialized values and cause TX DMA to stall. Check for invalid values and set a register bit to flush the TX channels. The bit needs to be turned off after the DMA channels have been flushed. Signed-off-by: Michael Chan <mchan@broadcom.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/net/ethernet/broadcom/tg3.c23
-rw-r--r--drivers/net/ethernet/broadcom/tg3.h7
2 files changed, 29 insertions, 1 deletions
diff --git a/drivers/net/ethernet/broadcom/tg3.c b/drivers/net/ethernet/broadcom/tg3.c
index f0434dfbda9c..50045ed1e8c0 100644
--- a/drivers/net/ethernet/broadcom/tg3.c
+++ b/drivers/net/ethernet/broadcom/tg3.c
@@ -9276,6 +9276,19 @@ static int tg3_reset_hw(struct tg3 *tp, int reset_phy)
9276 tw32_f(RDMAC_MODE, rdmac_mode); 9276 tw32_f(RDMAC_MODE, rdmac_mode);
9277 udelay(40); 9277 udelay(40);
9278 9278
9279 if (GET_ASIC_REV(tp->pci_chip_rev_id) == ASIC_REV_5719) {
9280 for (i = 0; i < TG3_NUM_RDMA_CHANNELS; i++) {
9281 if (tr32(TG3_RDMA_LENGTH + (i << 2)) > TG3_MAX_MTU(tp))
9282 break;
9283 }
9284 if (i < TG3_NUM_RDMA_CHANNELS) {
9285 val = tr32(TG3_LSO_RD_DMA_CRPTEN_CTRL);
9286 val |= TG3_LSO_RD_DMA_TX_LENGTH_WA;
9287 tw32(TG3_LSO_RD_DMA_CRPTEN_CTRL, val);
9288 tg3_flag_set(tp, 5719_RDMA_BUG);
9289 }
9290 }
9291
9279 tw32(RCVDCC_MODE, RCVDCC_MODE_ENABLE | RCVDCC_MODE_ATTN_ENABLE); 9292 tw32(RCVDCC_MODE, RCVDCC_MODE_ENABLE | RCVDCC_MODE_ATTN_ENABLE);
9280 if (!tg3_flag(tp, 5705_PLUS)) 9293 if (!tg3_flag(tp, 5705_PLUS))
9281 tw32(MBFREE_MODE, MBFREE_MODE_ENABLE); 9294 tw32(MBFREE_MODE, MBFREE_MODE_ENABLE);
@@ -9635,6 +9648,16 @@ static void tg3_periodic_fetch_stats(struct tg3 *tp)
9635 TG3_STAT_ADD32(&sp->tx_ucast_packets, MAC_TX_STATS_UCAST); 9648 TG3_STAT_ADD32(&sp->tx_ucast_packets, MAC_TX_STATS_UCAST);
9636 TG3_STAT_ADD32(&sp->tx_mcast_packets, MAC_TX_STATS_MCAST); 9649 TG3_STAT_ADD32(&sp->tx_mcast_packets, MAC_TX_STATS_MCAST);
9637 TG3_STAT_ADD32(&sp->tx_bcast_packets, MAC_TX_STATS_BCAST); 9650 TG3_STAT_ADD32(&sp->tx_bcast_packets, MAC_TX_STATS_BCAST);
9651 if (unlikely(tg3_flag(tp, 5719_RDMA_BUG) &&
9652 (sp->tx_ucast_packets.low + sp->tx_mcast_packets.low +
9653 sp->tx_bcast_packets.low) > TG3_NUM_RDMA_CHANNELS)) {
9654 u32 val;
9655
9656 val = tr32(TG3_LSO_RD_DMA_CRPTEN_CTRL);
9657 val &= ~TG3_LSO_RD_DMA_TX_LENGTH_WA;
9658 tw32(TG3_LSO_RD_DMA_CRPTEN_CTRL, val);
9659 tg3_flag_clear(tp, 5719_RDMA_BUG);
9660 }
9638 9661
9639 TG3_STAT_ADD32(&sp->rx_octets, MAC_RX_STATS_OCTETS); 9662 TG3_STAT_ADD32(&sp->rx_octets, MAC_RX_STATS_OCTETS);
9640 TG3_STAT_ADD32(&sp->rx_fragments, MAC_RX_STATS_FRAGMENTS); 9663 TG3_STAT_ADD32(&sp->rx_fragments, MAC_RX_STATS_FRAGMENTS);
diff --git a/drivers/net/ethernet/broadcom/tg3.h b/drivers/net/ethernet/broadcom/tg3.h
index 6fb45a500032..6d52cb286826 100644
--- a/drivers/net/ethernet/broadcom/tg3.h
+++ b/drivers/net/ethernet/broadcom/tg3.h
@@ -1376,7 +1376,11 @@
1376#define TG3_LSO_RD_DMA_CRPTEN_CTRL 0x00004910 1376#define TG3_LSO_RD_DMA_CRPTEN_CTRL 0x00004910
1377#define TG3_LSO_RD_DMA_CRPTEN_CTRL_BLEN_BD_4K 0x00030000 1377#define TG3_LSO_RD_DMA_CRPTEN_CTRL_BLEN_BD_4K 0x00030000
1378#define TG3_LSO_RD_DMA_CRPTEN_CTRL_BLEN_LSO_4K 0x000c0000 1378#define TG3_LSO_RD_DMA_CRPTEN_CTRL_BLEN_LSO_4K 0x000c0000
1379/* 0x4914 --> 0x4c00 unused */ 1379#define TG3_LSO_RD_DMA_TX_LENGTH_WA 0x02000000
1380/* 0x4914 --> 0x4be0 unused */
1381
1382#define TG3_NUM_RDMA_CHANNELS 4
1383#define TG3_RDMA_LENGTH 0x00004be0
1380 1384
1381/* Write DMA control registers */ 1385/* Write DMA control registers */
1382#define WDMAC_MODE 0x00004c00 1386#define WDMAC_MODE 0x00004c00
@@ -2959,6 +2963,7 @@ enum TG3_FLAGS {
2959 TG3_FLAG_L1PLLPD_EN, 2963 TG3_FLAG_L1PLLPD_EN,
2960 TG3_FLAG_APE_HAS_NCSI, 2964 TG3_FLAG_APE_HAS_NCSI,
2961 TG3_FLAG_4K_FIFO_LIMIT, 2965 TG3_FLAG_4K_FIFO_LIMIT,
2966 TG3_FLAG_5719_RDMA_BUG,
2962 TG3_FLAG_RESET_TASK_PENDING, 2967 TG3_FLAG_RESET_TASK_PENDING,
2963 TG3_FLAG_5705_PLUS, 2968 TG3_FLAG_5705_PLUS,
2964 TG3_FLAG_IS_5788, 2969 TG3_FLAG_IS_5788,