aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/sky2.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/sky2.c')
-rw-r--r--drivers/net/sky2.c136
1 files changed, 103 insertions, 33 deletions
diff --git a/drivers/net/sky2.c b/drivers/net/sky2.c
index 060951a8022b..d0e5875628e9 100644
--- a/drivers/net/sky2.c
+++ b/drivers/net/sky2.c
@@ -118,12 +118,15 @@ static const struct pci_device_id sky2_id_table[] = {
118 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4351) }, /* 88E8036 */ 118 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4351) }, /* 88E8036 */
119 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4352) }, /* 88E8038 */ 119 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4352) }, /* 88E8038 */
120 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4353) }, /* 88E8039 */ 120 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4353) }, /* 88E8039 */
121 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4354) }, /* 88E8040 */
121 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4356) }, /* 88EC033 */ 122 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4356) }, /* 88EC033 */
123 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x435A) }, /* 88E8048 */
122 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4360) }, /* 88E8052 */ 124 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4360) }, /* 88E8052 */
123 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4361) }, /* 88E8050 */ 125 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4361) }, /* 88E8050 */
124 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4362) }, /* 88E8053 */ 126 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4362) }, /* 88E8053 */
125 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4363) }, /* 88E8055 */ 127 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4363) }, /* 88E8055 */
126 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4364) }, /* 88E8056 */ 128 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4364) }, /* 88E8056 */
129 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4365) }, /* 88E8070 */
127 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4366) }, /* 88EC036 */ 130 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4366) }, /* 88EC036 */
128 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4367) }, /* 88EC032 */ 131 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4367) }, /* 88EC032 */
129 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4368) }, /* 88EC034 */ 132 { PCI_DEVICE(PCI_VENDOR_ID_MARVELL, 0x4368) }, /* 88EC034 */
@@ -147,6 +150,7 @@ static const char *yukon2_name[] = {
147 "Extreme", /* 0xb5 */ 150 "Extreme", /* 0xb5 */
148 "EC", /* 0xb6 */ 151 "EC", /* 0xb6 */
149 "FE", /* 0xb7 */ 152 "FE", /* 0xb7 */
153 "FE+", /* 0xb8 */
150}; 154};
151 155
152static void sky2_set_multicast(struct net_device *dev); 156static void sky2_set_multicast(struct net_device *dev);
@@ -331,7 +335,7 @@ static void sky2_phy_init(struct sky2_hw *hw, unsigned port)
331 335
332 ctrl = gm_phy_read(hw, port, PHY_MARV_PHY_CTRL); 336 ctrl = gm_phy_read(hw, port, PHY_MARV_PHY_CTRL);
333 if (sky2_is_copper(hw)) { 337 if (sky2_is_copper(hw)) {
334 if (hw->chip_id == CHIP_ID_YUKON_FE) { 338 if (!(hw->flags & SKY2_HW_GIGABIT)) {
335 /* enable automatic crossover */ 339 /* enable automatic crossover */
336 ctrl |= PHY_M_PC_MDI_XMODE(PHY_M_PC_ENA_AUTO) >> 1; 340 ctrl |= PHY_M_PC_MDI_XMODE(PHY_M_PC_ENA_AUTO) >> 1;
337 } else { 341 } else {
@@ -450,7 +454,7 @@ static void sky2_phy_init(struct sky2_hw *hw, unsigned port)
450 454
451 gma_write16(hw, port, GM_GP_CTRL, reg); 455 gma_write16(hw, port, GM_GP_CTRL, reg);
452 456
453 if (hw->chip_id != CHIP_ID_YUKON_FE) 457 if (hw->flags & SKY2_HW_GIGABIT)
454 gm_phy_write(hw, port, PHY_MARV_1000T_CTRL, ct1000); 458 gm_phy_write(hw, port, PHY_MARV_1000T_CTRL, ct1000);
455 459
456 gm_phy_write(hw, port, PHY_MARV_AUNE_ADV, adv); 460 gm_phy_write(hw, port, PHY_MARV_AUNE_ADV, adv);
@@ -474,6 +478,23 @@ static void sky2_phy_init(struct sky2_hw *hw, unsigned port)
474 gm_phy_write(hw, port, PHY_MARV_FE_LED_PAR, ctrl); 478 gm_phy_write(hw, port, PHY_MARV_FE_LED_PAR, ctrl);
475 break; 479 break;
476 480
481 case CHIP_ID_YUKON_FE_P:
482 /* Enable Link Partner Next Page */
483 ctrl = gm_phy_read(hw, port, PHY_MARV_PHY_CTRL);
484 ctrl |= PHY_M_PC_ENA_LIP_NP;
485
486 /* disable Energy Detect and enable scrambler */
487 ctrl &= ~(PHY_M_PC_ENA_ENE_DT | PHY_M_PC_DIS_SCRAMB);
488 gm_phy_write(hw, port, PHY_MARV_PHY_CTRL, ctrl);
489
490 /* set LED2 -> ACT, LED1 -> LINK, LED0 -> SPEED */
491 ctrl = PHY_M_FELP_LED2_CTRL(LED_PAR_CTRL_ACT_BL) |
492 PHY_M_FELP_LED1_CTRL(LED_PAR_CTRL_LINK) |
493 PHY_M_FELP_LED0_CTRL(LED_PAR_CTRL_SPEED);
494
495 gm_phy_write(hw, port, PHY_MARV_FE_LED_PAR, ctrl);
496 break;
497
477 case CHIP_ID_YUKON_XL: 498 case CHIP_ID_YUKON_XL:
478 pg = gm_phy_read(hw, port, PHY_MARV_EXT_ADR); 499 pg = gm_phy_read(hw, port, PHY_MARV_EXT_ADR);
479 500
@@ -543,7 +564,13 @@ static void sky2_phy_init(struct sky2_hw *hw, unsigned port)
543 564
544 /* set page register to 0 */ 565 /* set page register to 0 */
545 gm_phy_write(hw, port, PHY_MARV_EXT_ADR, 0); 566 gm_phy_write(hw, port, PHY_MARV_EXT_ADR, 0);
567 } else if (hw->chip_id == CHIP_ID_YUKON_FE_P &&
568 hw->chip_rev == CHIP_REV_YU_FE2_A0) {
569 /* apply workaround for integrated resistors calibration */
570 gm_phy_write(hw, port, PHY_MARV_PAGE_ADDR, 17);
571 gm_phy_write(hw, port, PHY_MARV_PAGE_DATA, 0x3f60);
546 } else if (hw->chip_id != CHIP_ID_YUKON_EX) { 572 } else if (hw->chip_id != CHIP_ID_YUKON_EX) {
573 /* no effect on Yukon-XL */
547 gm_phy_write(hw, port, PHY_MARV_LED_CTRL, ledctrl); 574 gm_phy_write(hw, port, PHY_MARV_LED_CTRL, ledctrl);
548 575
549 if (sky2->autoneg == AUTONEG_DISABLE || sky2->speed == SPEED_100) { 576 if (sky2->autoneg == AUTONEG_DISABLE || sky2->speed == SPEED_100) {
@@ -664,25 +691,25 @@ static void sky2_wol_init(struct sky2_port *sky2)
664 691
665static void sky2_set_tx_stfwd(struct sky2_hw *hw, unsigned port) 692static void sky2_set_tx_stfwd(struct sky2_hw *hw, unsigned port)
666{ 693{
667 if (hw->chip_id == CHIP_ID_YUKON_EX && hw->chip_rev != CHIP_REV_YU_EX_A0) { 694 struct net_device *dev = hw->dev[port];
695
696 if (dev->mtu <= ETH_DATA_LEN)
668 sky2_write32(hw, SK_REG(port, TX_GMF_CTRL_T), 697 sky2_write32(hw, SK_REG(port, TX_GMF_CTRL_T),
669 TX_STFW_ENA | 698 TX_JUMBO_DIS | TX_STFW_ENA);
670 (hw->dev[port]->mtu > ETH_DATA_LEN) ? TX_JUMBO_ENA : TX_JUMBO_DIS); 699
671 } else { 700 else if (hw->chip_id != CHIP_ID_YUKON_EC_U)
672 if (hw->dev[port]->mtu > ETH_DATA_LEN) { 701 sky2_write32(hw, SK_REG(port, TX_GMF_CTRL_T),
673 /* set Tx GMAC FIFO Almost Empty Threshold */ 702 TX_STFW_ENA | TX_JUMBO_ENA);
674 sky2_write32(hw, SK_REG(port, TX_GMF_AE_THR), 703 else {
675 (ECU_JUMBO_WM << 16) | ECU_AE_THR); 704 /* set Tx GMAC FIFO Almost Empty Threshold */
705 sky2_write32(hw, SK_REG(port, TX_GMF_AE_THR),
706 (ECU_JUMBO_WM << 16) | ECU_AE_THR);
676 707
677 sky2_write32(hw, SK_REG(port, TX_GMF_CTRL_T), 708 sky2_write32(hw, SK_REG(port, TX_GMF_CTRL_T),
678 TX_JUMBO_ENA | TX_STFW_DIS); 709 TX_JUMBO_ENA | TX_STFW_DIS);
679 710
680 /* Can't do offload because of lack of store/forward */ 711 /* Can't do offload because of lack of store/forward */
681 hw->dev[port]->features &= ~(NETIF_F_TSO | NETIF_F_SG 712 dev->features &= ~(NETIF_F_TSO | NETIF_F_SG | NETIF_F_ALL_CSUM);
682 | NETIF_F_ALL_CSUM);
683 } else
684 sky2_write32(hw, SK_REG(port, TX_GMF_CTRL_T),
685 TX_JUMBO_DIS | TX_STFW_ENA);
686 } 713 }
687} 714}
688 715
@@ -768,7 +795,8 @@ static void sky2_mac_init(struct sky2_hw *hw, unsigned port)
768 /* Configure Rx MAC FIFO */ 795 /* Configure Rx MAC FIFO */
769 sky2_write8(hw, SK_REG(port, RX_GMF_CTRL_T), GMF_RST_CLR); 796 sky2_write8(hw, SK_REG(port, RX_GMF_CTRL_T), GMF_RST_CLR);
770 rx_reg = GMF_OPER_ON | GMF_RX_F_FL_ON; 797 rx_reg = GMF_OPER_ON | GMF_RX_F_FL_ON;
771 if (hw->chip_id == CHIP_ID_YUKON_EX) 798 if (hw->chip_id == CHIP_ID_YUKON_EX ||
799 hw->chip_id == CHIP_ID_YUKON_FE_P)
772 rx_reg |= GMF_RX_OVER_ON; 800 rx_reg |= GMF_RX_OVER_ON;
773 801
774 sky2_write32(hw, SK_REG(port, RX_GMF_CTRL_T), rx_reg); 802 sky2_write32(hw, SK_REG(port, RX_GMF_CTRL_T), rx_reg);
@@ -777,7 +805,12 @@ static void sky2_mac_init(struct sky2_hw *hw, unsigned port)
777 sky2_write16(hw, SK_REG(port, RX_GMF_FL_MSK), GMR_FS_ANY_ERR); 805 sky2_write16(hw, SK_REG(port, RX_GMF_FL_MSK), GMR_FS_ANY_ERR);
778 806
779 /* Set threshold to 0xa (64 bytes) + 1 to workaround pause bug */ 807 /* Set threshold to 0xa (64 bytes) + 1 to workaround pause bug */
780 sky2_write16(hw, SK_REG(port, RX_GMF_FL_THR), RX_GMF_FL_THR_DEF+1); 808 reg = RX_GMF_FL_THR_DEF + 1;
809 /* Another magic mystery workaround from sk98lin */
810 if (hw->chip_id == CHIP_ID_YUKON_FE_P &&
811 hw->chip_rev == CHIP_REV_YU_FE2_A0)
812 reg = 0x178;
813 sky2_write16(hw, SK_REG(port, RX_GMF_FL_THR), reg);
781 814
782 /* Configure Tx MAC FIFO */ 815 /* Configure Tx MAC FIFO */
783 sky2_write8(hw, SK_REG(port, TX_GMF_CTRL_T), GMF_RST_CLR); 816 sky2_write8(hw, SK_REG(port, TX_GMF_CTRL_T), GMF_RST_CLR);
@@ -1704,8 +1737,12 @@ static u16 sky2_phy_speed(const struct sky2_hw *hw, u16 aux)
1704 if (hw->flags & SKY2_HW_FIBRE_PHY) 1737 if (hw->flags & SKY2_HW_FIBRE_PHY)
1705 return SPEED_1000; 1738 return SPEED_1000;
1706 1739
1707 if (hw->chip_id == CHIP_ID_YUKON_FE) 1740 if (!(hw->flags & SKY2_HW_GIGABIT)) {
1708 return (aux & PHY_M_PS_SPEED_100) ? SPEED_100 : SPEED_10; 1741 if (aux & PHY_M_PS_SPEED_100)
1742 return SPEED_100;
1743 else
1744 return SPEED_10;
1745 }
1709 1746
1710 switch (aux & PHY_M_PS_SPEED_MSK) { 1747 switch (aux & PHY_M_PS_SPEED_MSK) {
1711 case PHY_M_PS_SPEED_1000: 1748 case PHY_M_PS_SPEED_1000:
@@ -1949,7 +1986,9 @@ static int sky2_change_mtu(struct net_device *dev, int new_mtu)
1949 if (new_mtu < ETH_ZLEN || new_mtu > ETH_JUMBO_MTU) 1986 if (new_mtu < ETH_ZLEN || new_mtu > ETH_JUMBO_MTU)
1950 return -EINVAL; 1987 return -EINVAL;
1951 1988
1952 if (new_mtu > ETH_DATA_LEN && hw->chip_id == CHIP_ID_YUKON_FE) 1989 if (new_mtu > ETH_DATA_LEN &&
1990 (hw->chip_id == CHIP_ID_YUKON_FE ||
1991 hw->chip_id == CHIP_ID_YUKON_FE_P))
1953 return -EINVAL; 1992 return -EINVAL;
1954 1993
1955 if (!netif_running(dev)) { 1994 if (!netif_running(dev)) {
@@ -1966,7 +2005,7 @@ static int sky2_change_mtu(struct net_device *dev, int new_mtu)
1966 2005
1967 synchronize_irq(hw->pdev->irq); 2006 synchronize_irq(hw->pdev->irq);
1968 2007
1969 if (hw->chip_id == CHIP_ID_YUKON_EC_U || hw->chip_id == CHIP_ID_YUKON_EX) 2008 if (!(hw->flags & SKY2_HW_RAMBUFFER))
1970 sky2_set_tx_stfwd(hw, port); 2009 sky2_set_tx_stfwd(hw, port);
1971 2010
1972 ctl = gma_read16(hw, port, GM_GP_CTRL); 2011 ctl = gma_read16(hw, port, GM_GP_CTRL);
@@ -2205,7 +2244,7 @@ static int sky2_status_intr(struct sky2_hw *hw, int to_do)
2205 } 2244 }
2206 2245
2207 /* This chip reports checksum status differently */ 2246 /* This chip reports checksum status differently */
2208 if (hw->chip_id == CHIP_ID_YUKON_EX) { 2247 if (hw->flags & SKY2_HW_NEW_LE) {
2209 if (sky2->rx_csum && 2248 if (sky2->rx_csum &&
2210 (le->css & (CSS_ISIPV4 | CSS_ISIPV6)) && 2249 (le->css & (CSS_ISIPV4 | CSS_ISIPV6)) &&
2211 (le->css & CSS_TCPUDPCSOK)) 2250 (le->css & CSS_TCPUDPCSOK))
@@ -2246,8 +2285,14 @@ static int sky2_status_intr(struct sky2_hw *hw, int to_do)
2246 if (!sky2->rx_csum) 2285 if (!sky2->rx_csum)
2247 break; 2286 break;
2248 2287
2249 if (hw->chip_id == CHIP_ID_YUKON_EX) 2288 /* If this happens then driver assuming wrong format */
2289 if (unlikely(hw->flags & SKY2_HW_NEW_LE)) {
2290 if (net_ratelimit())
2291 printk(KERN_NOTICE "%s: unexpected"
2292 " checksum status\n",
2293 dev->name);
2250 break; 2294 break;
2295 }
2251 2296
2252 /* Both checksum counters are programmed to start at 2297 /* Both checksum counters are programmed to start at
2253 * the same offset, so unless there is a problem they 2298 * the same offset, so unless there is a problem they
@@ -2549,17 +2594,25 @@ static void sky2_netpoll(struct net_device *dev)
2549#endif 2594#endif
2550 2595
2551/* Chip internal frequency for clock calculations */ 2596/* Chip internal frequency for clock calculations */
2552static inline u32 sky2_mhz(const struct sky2_hw *hw) 2597static u32 sky2_mhz(const struct sky2_hw *hw)
2553{ 2598{
2554 switch (hw->chip_id) { 2599 switch (hw->chip_id) {
2555 case CHIP_ID_YUKON_EC: 2600 case CHIP_ID_YUKON_EC:
2556 case CHIP_ID_YUKON_EC_U: 2601 case CHIP_ID_YUKON_EC_U:
2557 case CHIP_ID_YUKON_EX: 2602 case CHIP_ID_YUKON_EX:
2558 return 125; /* 125 Mhz */ 2603 return 125;
2604
2559 case CHIP_ID_YUKON_FE: 2605 case CHIP_ID_YUKON_FE:
2560 return 100; /* 100 Mhz */ 2606 return 100;
2561 default: /* YUKON_XL */ 2607
2562 return 156; /* 156 Mhz */ 2608 case CHIP_ID_YUKON_FE_P:
2609 return 50;
2610
2611 case CHIP_ID_YUKON_XL:
2612 return 156;
2613
2614 default:
2615 BUG();
2563 } 2616 }
2564} 2617}
2565 2618
@@ -2623,6 +2676,12 @@ static int __devinit sky2_init(struct sky2_hw *hw)
2623 hw->flags = SKY2_HW_RAMBUFFER; 2676 hw->flags = SKY2_HW_RAMBUFFER;
2624 break; 2677 break;
2625 2678
2679 case CHIP_ID_YUKON_FE_P:
2680 hw->flags = SKY2_HW_NEWER_PHY
2681 | SKY2_HW_NEW_LE
2682 | SKY2_HW_AUTO_TX_SUM
2683 | SKY2_HW_ADV_POWER_CTL;
2684 break;
2626 default: 2685 default:
2627 dev_err(&hw->pdev->dev, "unsupported chip type 0x%x\n", 2686 dev_err(&hw->pdev->dev, "unsupported chip type 0x%x\n",
2628 hw->chip_id); 2687 hw->chip_id);
@@ -2827,7 +2886,9 @@ static int sky2_set_wol(struct net_device *dev, struct ethtool_wolinfo *wol)
2827 2886
2828 sky2->wol = wol->wolopts; 2887 sky2->wol = wol->wolopts;
2829 2888
2830 if (hw->chip_id == CHIP_ID_YUKON_EC_U || hw->chip_id == CHIP_ID_YUKON_EX) 2889 if (hw->chip_id == CHIP_ID_YUKON_EC_U ||
2890 hw->chip_id == CHIP_ID_YUKON_EX ||
2891 hw->chip_id == CHIP_ID_YUKON_FE_P)
2831 sky2_write32(hw, B0_CTST, sky2->wol 2892 sky2_write32(hw, B0_CTST, sky2->wol
2832 ? Y2_HW_WOL_ON : Y2_HW_WOL_OFF); 2893 ? Y2_HW_WOL_ON : Y2_HW_WOL_OFF);
2833 2894
@@ -3820,6 +3881,13 @@ static __devinit struct net_device *sky2_init_netdev(struct sky2_hw *hw,
3820 sky2->hw = hw; 3881 sky2->hw = hw;
3821 sky2->msg_enable = netif_msg_init(debug, default_msg); 3882 sky2->msg_enable = netif_msg_init(debug, default_msg);
3822 3883
3884 /* This chip has hardware problems that generates
3885 * bogus PHY receive status so by default shut up the message.
3886 */
3887 if (hw->chip_id == CHIP_ID_YUKON_FE_P &&
3888 hw->chip_rev == CHIP_REV_YU_FE2_A0)
3889 sky2->msg_enable &= ~NETIF_MSG_RX_ERR;
3890
3823 /* Auto speed and flow control */ 3891 /* Auto speed and flow control */
3824 sky2->autoneg = AUTONEG_ENABLE; 3892 sky2->autoneg = AUTONEG_ENABLE;
3825 sky2->flow_mode = FC_BOTH; 3893 sky2->flow_mode = FC_BOTH;
@@ -4189,7 +4257,9 @@ static int sky2_resume(struct pci_dev *pdev)
4189 pci_enable_wake(pdev, PCI_D0, 0); 4257 pci_enable_wake(pdev, PCI_D0, 0);
4190 4258
4191 /* Re-enable all clocks */ 4259 /* Re-enable all clocks */
4192 if (hw->chip_id == CHIP_ID_YUKON_EX || hw->chip_id == CHIP_ID_YUKON_EC_U) 4260 if (hw->chip_id == CHIP_ID_YUKON_EX ||
4261 hw->chip_id == CHIP_ID_YUKON_EC_U ||
4262 hw->chip_id == CHIP_ID_YUKON_FE_P)
4193 sky2_pci_write32(hw, PCI_DEV_REG3, 0); 4263 sky2_pci_write32(hw, PCI_DEV_REG3, 0);
4194 4264
4195 sky2_reset(hw); 4265 sky2_reset(hw);