diff options
| author | Stephen Hemminger <shemminger@linux-foundation.org> | 2007-09-19 18:36:44 -0400 |
|---|---|---|
| committer | Jeff Garzik <jeff@garzik.org> | 2007-09-20 15:23:00 -0400 |
| commit | ea76e63598eb312e5d33a782275be91038fc6df2 (patch) | |
| tree | 6d7ba4add8344afdc1046f248fce352e6d342444 | |
| parent | c99210b50fe741026d86fdcb5f3f5a0c00c503cc (diff) | |
sky2: reorganize chip revision features
This patch should cause no functional changes in driver behaviour.
There are (too) many revisions of the Yukon 2 chip now. Instead of
adding more conditionals based on chip revision; rerganize into a
set of feature flags so adding new versions is less problematic.
Signed-off-by: Stephen Hemminger <shemminger@linux-foundation.org>
Signed-off-by: Jeff Garzik <jeff@garzik.org>
| -rw-r--r-- | drivers/net/sky2.c | 135 | ||||
| -rw-r--r-- | drivers/net/sky2.h | 12 |
2 files changed, 90 insertions, 57 deletions
diff --git a/drivers/net/sky2.c b/drivers/net/sky2.c index 94552cc4c462..060951a8022b 100644 --- a/drivers/net/sky2.c +++ b/drivers/net/sky2.c | |||
| @@ -217,8 +217,7 @@ static void sky2_power_on(struct sky2_hw *hw) | |||
| 217 | else | 217 | else |
| 218 | sky2_write8(hw, B2_Y2_CLK_GATE, 0); | 218 | sky2_write8(hw, B2_Y2_CLK_GATE, 0); |
| 219 | 219 | ||
| 220 | if (hw->chip_id == CHIP_ID_YUKON_EC_U || | 220 | if (hw->flags & SKY2_HW_ADV_POWER_CTL) { |
| 221 | hw->chip_id == CHIP_ID_YUKON_EX) { | ||
| 222 | u32 reg; | 221 | u32 reg; |
| 223 | 222 | ||
| 224 | sky2_pci_write32(hw, PCI_DEV_REG3, 0); | 223 | sky2_pci_write32(hw, PCI_DEV_REG3, 0); |
| @@ -311,10 +310,8 @@ static void sky2_phy_init(struct sky2_hw *hw, unsigned port) | |||
| 311 | struct sky2_port *sky2 = netdev_priv(hw->dev[port]); | 310 | struct sky2_port *sky2 = netdev_priv(hw->dev[port]); |
| 312 | u16 ctrl, ct1000, adv, pg, ledctrl, ledover, reg; | 311 | u16 ctrl, ct1000, adv, pg, ledctrl, ledover, reg; |
| 313 | 312 | ||
| 314 | if (sky2->autoneg == AUTONEG_ENABLE | 313 | if (sky2->autoneg == AUTONEG_ENABLE && |
| 315 | && !(hw->chip_id == CHIP_ID_YUKON_XL | 314 | !(hw->flags & SKY2_HW_NEWER_PHY)) { |
| 316 | || hw->chip_id == CHIP_ID_YUKON_EC_U | ||
| 317 | || hw->chip_id == CHIP_ID_YUKON_EX)) { | ||
| 318 | u16 ectrl = gm_phy_read(hw, port, PHY_MARV_EXT_CTRL); | 315 | u16 ectrl = gm_phy_read(hw, port, PHY_MARV_EXT_CTRL); |
| 319 | 316 | ||
| 320 | ectrl &= ~(PHY_M_EC_M_DSC_MSK | PHY_M_EC_S_DSC_MSK | | 317 | ectrl &= ~(PHY_M_EC_M_DSC_MSK | PHY_M_EC_S_DSC_MSK | |
| @@ -346,9 +343,7 @@ static void sky2_phy_init(struct sky2_hw *hw, unsigned port) | |||
| 346 | 343 | ||
| 347 | /* downshift on PHY 88E1112 and 88E1149 is changed */ | 344 | /* downshift on PHY 88E1112 and 88E1149 is changed */ |
| 348 | if (sky2->autoneg == AUTONEG_ENABLE | 345 | if (sky2->autoneg == AUTONEG_ENABLE |
| 349 | && (hw->chip_id == CHIP_ID_YUKON_XL | 346 | && (hw->flags & SKY2_HW_NEWER_PHY)) { |
| 350 | || hw->chip_id == CHIP_ID_YUKON_EC_U | ||
| 351 | || hw->chip_id == CHIP_ID_YUKON_EX)) { | ||
| 352 | /* set downshift counter to 3x and enable downshift */ | 347 | /* set downshift counter to 3x and enable downshift */ |
| 353 | ctrl &= ~PHY_M_PC_DSC_MSK; | 348 | ctrl &= ~PHY_M_PC_DSC_MSK; |
| 354 | ctrl |= PHY_M_PC_DSC(2) | PHY_M_PC_DOWN_S_ENA; | 349 | ctrl |= PHY_M_PC_DSC(2) | PHY_M_PC_DOWN_S_ENA; |
| @@ -364,7 +359,7 @@ static void sky2_phy_init(struct sky2_hw *hw, unsigned port) | |||
| 364 | gm_phy_write(hw, port, PHY_MARV_PHY_CTRL, ctrl); | 359 | gm_phy_write(hw, port, PHY_MARV_PHY_CTRL, ctrl); |
| 365 | 360 | ||
| 366 | /* special setup for PHY 88E1112 Fiber */ | 361 | /* special setup for PHY 88E1112 Fiber */ |
| 367 | if (hw->chip_id == CHIP_ID_YUKON_XL && !sky2_is_copper(hw)) { | 362 | if (hw->chip_id == CHIP_ID_YUKON_XL && (hw->flags & SKY2_HW_FIBRE_PHY)) { |
| 368 | pg = gm_phy_read(hw, port, PHY_MARV_EXT_ADR); | 363 | pg = gm_phy_read(hw, port, PHY_MARV_EXT_ADR); |
| 369 | 364 | ||
| 370 | /* Fiber: select 1000BASE-X only mode MAC Specific Ctrl Reg. */ | 365 | /* Fiber: select 1000BASE-X only mode MAC Specific Ctrl Reg. */ |
| @@ -788,7 +783,7 @@ static void sky2_mac_init(struct sky2_hw *hw, unsigned port) | |||
| 788 | sky2_write8(hw, SK_REG(port, TX_GMF_CTRL_T), GMF_RST_CLR); | 783 | sky2_write8(hw, SK_REG(port, TX_GMF_CTRL_T), GMF_RST_CLR); |
| 789 | sky2_write16(hw, SK_REG(port, TX_GMF_CTRL_T), GMF_OPER_ON); | 784 | sky2_write16(hw, SK_REG(port, TX_GMF_CTRL_T), GMF_OPER_ON); |
| 790 | 785 | ||
| 791 | if (hw->chip_id == CHIP_ID_YUKON_EC_U || hw->chip_id == CHIP_ID_YUKON_EX) { | 786 | if (!(hw->flags & SKY2_HW_RAMBUFFER)) { |
| 792 | sky2_write8(hw, SK_REG(port, RX_GMF_LP_THR), 768/8); | 787 | sky2_write8(hw, SK_REG(port, RX_GMF_LP_THR), 768/8); |
| 793 | sky2_write8(hw, SK_REG(port, RX_GMF_UP_THR), 1024/8); | 788 | sky2_write8(hw, SK_REG(port, RX_GMF_UP_THR), 1024/8); |
| 794 | 789 | ||
| @@ -967,19 +962,15 @@ static void sky2_rx_unmap_skb(struct pci_dev *pdev, struct rx_ring_info *re) | |||
| 967 | */ | 962 | */ |
| 968 | static void rx_set_checksum(struct sky2_port *sky2) | 963 | static void rx_set_checksum(struct sky2_port *sky2) |
| 969 | { | 964 | { |
| 970 | struct sky2_rx_le *le; | 965 | struct sky2_rx_le *le = sky2_next_rx(sky2); |
| 971 | |||
| 972 | if (sky2->hw->chip_id != CHIP_ID_YUKON_EX) { | ||
| 973 | le = sky2_next_rx(sky2); | ||
| 974 | le->addr = cpu_to_le32((ETH_HLEN << 16) | ETH_HLEN); | ||
| 975 | le->ctrl = 0; | ||
| 976 | le->opcode = OP_TCPSTART | HW_OWNER; | ||
| 977 | 966 | ||
| 978 | sky2_write32(sky2->hw, | 967 | le->addr = cpu_to_le32((ETH_HLEN << 16) | ETH_HLEN); |
| 979 | Q_ADDR(rxqaddr[sky2->port], Q_CSR), | 968 | le->ctrl = 0; |
| 980 | sky2->rx_csum ? BMU_ENA_RX_CHKSUM : BMU_DIS_RX_CHKSUM); | 969 | le->opcode = OP_TCPSTART | HW_OWNER; |
| 981 | } | ||
| 982 | 970 | ||
| 971 | sky2_write32(sky2->hw, | ||
| 972 | Q_ADDR(rxqaddr[sky2->port], Q_CSR), | ||
| 973 | sky2->rx_csum ? BMU_ENA_RX_CHKSUM : BMU_DIS_RX_CHKSUM); | ||
| 983 | } | 974 | } |
| 984 | 975 | ||
| 985 | /* | 976 | /* |
| @@ -1175,7 +1166,8 @@ static int sky2_rx_start(struct sky2_port *sky2) | |||
| 1175 | 1166 | ||
| 1176 | sky2_prefetch_init(hw, rxq, sky2->rx_le_map, RX_LE_SIZE - 1); | 1167 | sky2_prefetch_init(hw, rxq, sky2->rx_le_map, RX_LE_SIZE - 1); |
| 1177 | 1168 | ||
| 1178 | rx_set_checksum(sky2); | 1169 | if (!(hw->flags & SKY2_HW_NEW_LE)) |
| 1170 | rx_set_checksum(sky2); | ||
| 1179 | 1171 | ||
| 1180 | /* Space needed for frame data + headers rounded up */ | 1172 | /* Space needed for frame data + headers rounded up */ |
| 1181 | size = roundup(sky2->netdev->mtu + ETH_HLEN + VLAN_HLEN, 8); | 1173 | size = roundup(sky2->netdev->mtu + ETH_HLEN + VLAN_HLEN, 8); |
| @@ -1246,7 +1238,7 @@ static int sky2_up(struct net_device *dev) | |||
| 1246 | struct sky2_port *sky2 = netdev_priv(dev); | 1238 | struct sky2_port *sky2 = netdev_priv(dev); |
| 1247 | struct sky2_hw *hw = sky2->hw; | 1239 | struct sky2_hw *hw = sky2->hw; |
| 1248 | unsigned port = sky2->port; | 1240 | unsigned port = sky2->port; |
| 1249 | u32 ramsize, imask; | 1241 | u32 imask; |
| 1250 | int cap, err = -ENOMEM; | 1242 | int cap, err = -ENOMEM; |
| 1251 | struct net_device *otherdev = hw->dev[sky2->port^1]; | 1243 | struct net_device *otherdev = hw->dev[sky2->port^1]; |
| 1252 | 1244 | ||
| @@ -1301,13 +1293,13 @@ static int sky2_up(struct net_device *dev) | |||
| 1301 | 1293 | ||
| 1302 | sky2_mac_init(hw, port); | 1294 | sky2_mac_init(hw, port); |
| 1303 | 1295 | ||
| 1304 | /* Register is number of 4K blocks on internal RAM buffer. */ | 1296 | if (hw->flags & SKY2_HW_RAMBUFFER) { |
| 1305 | ramsize = sky2_read8(hw, B2_E_0) * 4; | 1297 | /* Register is number of 4K blocks on internal RAM buffer. */ |
| 1306 | printk(KERN_INFO PFX "%s: ram buffer %dK\n", dev->name, ramsize); | 1298 | u32 ramsize = sky2_read8(hw, B2_E_0) * 4; |
| 1307 | |||
| 1308 | if (ramsize > 0) { | ||
| 1309 | u32 rxspace; | 1299 | u32 rxspace; |
| 1310 | 1300 | ||
| 1301 | printk(KERN_DEBUG PFX "%s: ram buffer %dK\n", dev->name, ramsize); | ||
| 1302 | |||
| 1311 | if (ramsize < 16) | 1303 | if (ramsize < 16) |
| 1312 | rxspace = ramsize / 2; | 1304 | rxspace = ramsize / 2; |
| 1313 | else | 1305 | else |
| @@ -1436,13 +1428,15 @@ static int sky2_xmit_frame(struct sk_buff *skb, struct net_device *dev) | |||
| 1436 | /* Check for TCP Segmentation Offload */ | 1428 | /* Check for TCP Segmentation Offload */ |
| 1437 | mss = skb_shinfo(skb)->gso_size; | 1429 | mss = skb_shinfo(skb)->gso_size; |
| 1438 | if (mss != 0) { | 1430 | if (mss != 0) { |
| 1439 | if (hw->chip_id != CHIP_ID_YUKON_EX) | 1431 | |
| 1432 | if (!(hw->flags & SKY2_HW_NEW_LE)) | ||
| 1440 | mss += ETH_HLEN + ip_hdrlen(skb) + tcp_hdrlen(skb); | 1433 | mss += ETH_HLEN + ip_hdrlen(skb) + tcp_hdrlen(skb); |
| 1441 | 1434 | ||
| 1442 | if (mss != sky2->tx_last_mss) { | 1435 | if (mss != sky2->tx_last_mss) { |
| 1443 | le = get_tx_le(sky2); | 1436 | le = get_tx_le(sky2); |
| 1444 | le->addr = cpu_to_le32(mss); | 1437 | le->addr = cpu_to_le32(mss); |
| 1445 | if (hw->chip_id == CHIP_ID_YUKON_EX) | 1438 | |
| 1439 | if (hw->flags & SKY2_HW_NEW_LE) | ||
| 1446 | le->opcode = OP_MSS | HW_OWNER; | 1440 | le->opcode = OP_MSS | HW_OWNER; |
| 1447 | else | 1441 | else |
| 1448 | le->opcode = OP_LRGLEN | HW_OWNER; | 1442 | le->opcode = OP_LRGLEN | HW_OWNER; |
| @@ -1468,8 +1462,7 @@ static int sky2_xmit_frame(struct sk_buff *skb, struct net_device *dev) | |||
| 1468 | /* Handle TCP checksum offload */ | 1462 | /* Handle TCP checksum offload */ |
| 1469 | if (skb->ip_summed == CHECKSUM_PARTIAL) { | 1463 | if (skb->ip_summed == CHECKSUM_PARTIAL) { |
| 1470 | /* On Yukon EX (some versions) encoding change. */ | 1464 | /* On Yukon EX (some versions) encoding change. */ |
| 1471 | if (hw->chip_id == CHIP_ID_YUKON_EX | 1465 | if (hw->flags & SKY2_HW_AUTO_TX_SUM) |
| 1472 | && hw->chip_rev != CHIP_REV_YU_EX_B0) | ||
| 1473 | ctrl |= CALSUM; /* auto checksum */ | 1466 | ctrl |= CALSUM; /* auto checksum */ |
| 1474 | else { | 1467 | else { |
| 1475 | const unsigned offset = skb_transport_offset(skb); | 1468 | const unsigned offset = skb_transport_offset(skb); |
| @@ -1708,7 +1701,7 @@ static int sky2_down(struct net_device *dev) | |||
| 1708 | 1701 | ||
| 1709 | static u16 sky2_phy_speed(const struct sky2_hw *hw, u16 aux) | 1702 | static u16 sky2_phy_speed(const struct sky2_hw *hw, u16 aux) |
| 1710 | { | 1703 | { |
| 1711 | if (!sky2_is_copper(hw)) | 1704 | if (hw->flags & SKY2_HW_FIBRE_PHY) |
| 1712 | return SPEED_1000; | 1705 | return SPEED_1000; |
| 1713 | 1706 | ||
| 1714 | if (hw->chip_id == CHIP_ID_YUKON_FE) | 1707 | if (hw->chip_id == CHIP_ID_YUKON_FE) |
| @@ -1753,9 +1746,7 @@ static void sky2_link_up(struct sky2_port *sky2) | |||
| 1753 | sky2_write8(hw, SK_REG(port, LNK_LED_REG), | 1746 | sky2_write8(hw, SK_REG(port, LNK_LED_REG), |
| 1754 | LINKLED_ON | LINKLED_BLINK_OFF | LINKLED_LINKSYNC_OFF); | 1747 | LINKLED_ON | LINKLED_BLINK_OFF | LINKLED_LINKSYNC_OFF); |
| 1755 | 1748 | ||
| 1756 | if (hw->chip_id == CHIP_ID_YUKON_XL | 1749 | if (hw->flags & SKY2_HW_NEWER_PHY) { |
| 1757 | || hw->chip_id == CHIP_ID_YUKON_EC_U | ||
| 1758 | || hw->chip_id == CHIP_ID_YUKON_EX) { | ||
| 1759 | u16 pg = gm_phy_read(hw, port, PHY_MARV_EXT_ADR); | 1750 | u16 pg = gm_phy_read(hw, port, PHY_MARV_EXT_ADR); |
| 1760 | u16 led = PHY_M_LEDC_LOS_CTRL(1); /* link active */ | 1751 | u16 led = PHY_M_LEDC_LOS_CTRL(1); /* link active */ |
| 1761 | 1752 | ||
| @@ -1847,7 +1838,7 @@ static int sky2_autoneg_done(struct sky2_port *sky2, u16 aux) | |||
| 1847 | /* Since the pause result bits seem to in different positions on | 1838 | /* Since the pause result bits seem to in different positions on |
| 1848 | * different chips. look at registers. | 1839 | * different chips. look at registers. |
| 1849 | */ | 1840 | */ |
| 1850 | if (!sky2_is_copper(hw)) { | 1841 | if (hw->flags & SKY2_HW_FIBRE_PHY) { |
| 1851 | /* Shift for bits in fiber PHY */ | 1842 | /* Shift for bits in fiber PHY */ |
| 1852 | advert &= ~(ADVERTISE_PAUSE_CAP|ADVERTISE_PAUSE_ASYM); | 1843 | advert &= ~(ADVERTISE_PAUSE_CAP|ADVERTISE_PAUSE_ASYM); |
| 1853 | lpa &= ~(LPA_PAUSE_CAP|LPA_PAUSE_ASYM); | 1844 | lpa &= ~(LPA_PAUSE_CAP|LPA_PAUSE_ASYM); |
| @@ -2593,23 +2584,56 @@ static int __devinit sky2_init(struct sky2_hw *hw) | |||
| 2593 | sky2_write8(hw, B0_CTST, CS_RST_CLR); | 2584 | sky2_write8(hw, B0_CTST, CS_RST_CLR); |
| 2594 | 2585 | ||
| 2595 | hw->chip_id = sky2_read8(hw, B2_CHIP_ID); | 2586 | hw->chip_id = sky2_read8(hw, B2_CHIP_ID); |
| 2596 | if (hw->chip_id < CHIP_ID_YUKON_XL || hw->chip_id > CHIP_ID_YUKON_FE) { | 2587 | hw->chip_rev = (sky2_read8(hw, B2_MAC_CFG) & CFG_CHIP_R_MSK) >> 4; |
| 2588 | |||
| 2589 | switch(hw->chip_id) { | ||
| 2590 | case CHIP_ID_YUKON_XL: | ||
| 2591 | hw->flags = SKY2_HW_GIGABIT | ||
| 2592 | | SKY2_HW_NEWER_PHY | ||
| 2593 | | SKY2_HW_RAMBUFFER; | ||
| 2594 | break; | ||
| 2595 | |||
| 2596 | case CHIP_ID_YUKON_EC_U: | ||
| 2597 | hw->flags = SKY2_HW_GIGABIT | ||
| 2598 | | SKY2_HW_NEWER_PHY | ||
| 2599 | | SKY2_HW_ADV_POWER_CTL; | ||
| 2600 | break; | ||
| 2601 | |||
| 2602 | case CHIP_ID_YUKON_EX: | ||
| 2603 | hw->flags = SKY2_HW_GIGABIT | ||
| 2604 | | SKY2_HW_NEWER_PHY | ||
| 2605 | | SKY2_HW_NEW_LE | ||
| 2606 | | SKY2_HW_ADV_POWER_CTL; | ||
| 2607 | |||
| 2608 | /* New transmit checksum */ | ||
| 2609 | if (hw->chip_rev != CHIP_REV_YU_EX_B0) | ||
| 2610 | hw->flags |= SKY2_HW_AUTO_TX_SUM; | ||
| 2611 | break; | ||
| 2612 | |||
| 2613 | case CHIP_ID_YUKON_EC: | ||
| 2614 | /* This rev is really old, and requires untested workarounds */ | ||
| 2615 | if (hw->chip_rev == CHIP_REV_YU_EC_A1) { | ||
| 2616 | dev_err(&hw->pdev->dev, "unsupported revision Yukon-EC rev A1\n"); | ||
| 2617 | return -EOPNOTSUPP; | ||
| 2618 | } | ||
| 2619 | hw->flags = SKY2_HW_GIGABIT | SKY2_HW_RAMBUFFER; | ||
| 2620 | break; | ||
| 2621 | |||
| 2622 | case CHIP_ID_YUKON_FE: | ||
| 2623 | hw->flags = SKY2_HW_RAMBUFFER; | ||
| 2624 | break; | ||
| 2625 | |||
| 2626 | default: | ||
| 2597 | dev_err(&hw->pdev->dev, "unsupported chip type 0x%x\n", | 2627 | dev_err(&hw->pdev->dev, "unsupported chip type 0x%x\n", |
| 2598 | hw->chip_id); | 2628 | hw->chip_id); |
| 2599 | return -EOPNOTSUPP; | 2629 | return -EOPNOTSUPP; |
| 2600 | } | 2630 | } |
| 2601 | 2631 | ||
| 2602 | hw->chip_rev = (sky2_read8(hw, B2_MAC_CFG) & CFG_CHIP_R_MSK) >> 4; | 2632 | hw->pmd_type = sky2_read8(hw, B2_PMD_TYP); |
| 2633 | if (hw->pmd_type == 'L' || hw->pmd_type == 'S' || hw->pmd_type == 'P') | ||
| 2634 | hw->flags |= SKY2_HW_FIBRE_PHY; | ||
| 2603 | 2635 | ||
| 2604 | /* This rev is really old, and requires untested workarounds */ | ||
| 2605 | if (hw->chip_id == CHIP_ID_YUKON_EC && hw->chip_rev == CHIP_REV_YU_EC_A1) { | ||
| 2606 | dev_err(&hw->pdev->dev, "unsupported revision Yukon-%s (0x%x) rev %d\n", | ||
| 2607 | yukon2_name[hw->chip_id - CHIP_ID_YUKON_XL], | ||
| 2608 | hw->chip_id, hw->chip_rev); | ||
| 2609 | return -EOPNOTSUPP; | ||
| 2610 | } | ||
| 2611 | 2636 | ||
| 2612 | hw->pmd_type = sky2_read8(hw, B2_PMD_TYP); | ||
| 2613 | hw->ports = 1; | 2637 | hw->ports = 1; |
| 2614 | t8 = sky2_read8(hw, B2_Y2_HW_RES); | 2638 | t8 = sky2_read8(hw, B2_Y2_HW_RES); |
| 2615 | if ((t8 & CFG_DUAL_MAC_MSK) == CFG_DUAL_MAC_MSK) { | 2639 | if ((t8 & CFG_DUAL_MAC_MSK) == CFG_DUAL_MAC_MSK) { |
| @@ -2821,7 +2845,7 @@ static u32 sky2_supported_modes(const struct sky2_hw *hw) | |||
| 2821 | | SUPPORTED_100baseT_Full | 2845 | | SUPPORTED_100baseT_Full |
| 2822 | | SUPPORTED_Autoneg | SUPPORTED_TP; | 2846 | | SUPPORTED_Autoneg | SUPPORTED_TP; |
| 2823 | 2847 | ||
| 2824 | if (hw->chip_id != CHIP_ID_YUKON_FE) | 2848 | if (hw->flags & SKY2_HW_GIGABIT) |
| 2825 | modes |= SUPPORTED_1000baseT_Half | 2849 | modes |= SUPPORTED_1000baseT_Half |
| 2826 | | SUPPORTED_1000baseT_Full; | 2850 | | SUPPORTED_1000baseT_Full; |
| 2827 | return modes; | 2851 | return modes; |
| @@ -3851,7 +3875,7 @@ static irqreturn_t __devinit sky2_test_intr(int irq, void *dev_id) | |||
| 3851 | return IRQ_NONE; | 3875 | return IRQ_NONE; |
| 3852 | 3876 | ||
| 3853 | if (status & Y2_IS_IRQ_SW) { | 3877 | if (status & Y2_IS_IRQ_SW) { |
| 3854 | hw->msi = 1; | 3878 | hw->flags |= SKY2_HW_USE_MSI; |
| 3855 | wake_up(&hw->msi_wait); | 3879 | wake_up(&hw->msi_wait); |
| 3856 | sky2_write8(hw, B0_CTST, CS_CL_SW_IRQ); | 3880 | sky2_write8(hw, B0_CTST, CS_CL_SW_IRQ); |
| 3857 | } | 3881 | } |
| @@ -3879,9 +3903,9 @@ static int __devinit sky2_test_msi(struct sky2_hw *hw) | |||
| 3879 | sky2_write8(hw, B0_CTST, CS_ST_SW_IRQ); | 3903 | sky2_write8(hw, B0_CTST, CS_ST_SW_IRQ); |
| 3880 | sky2_read8(hw, B0_CTST); | 3904 | sky2_read8(hw, B0_CTST); |
| 3881 | 3905 | ||
| 3882 | wait_event_timeout(hw->msi_wait, hw->msi, HZ/10); | 3906 | wait_event_timeout(hw->msi_wait, (hw->flags & SKY2_HW_USE_MSI), HZ/10); |
| 3883 | 3907 | ||
| 3884 | if (!hw->msi) { | 3908 | if (!(hw->flags & SKY2_HW_USE_MSI)) { |
| 3885 | /* MSI test failed, go back to INTx mode */ | 3909 | /* MSI test failed, go back to INTx mode */ |
| 3886 | dev_info(&pdev->dev, "No interrupt generated using MSI, " | 3910 | dev_info(&pdev->dev, "No interrupt generated using MSI, " |
| 3887 | "switching to INTx mode.\n"); | 3911 | "switching to INTx mode.\n"); |
| @@ -4014,7 +4038,8 @@ static int __devinit sky2_probe(struct pci_dev *pdev, | |||
| 4014 | goto err_out_free_netdev; | 4038 | goto err_out_free_netdev; |
| 4015 | } | 4039 | } |
| 4016 | 4040 | ||
| 4017 | err = request_irq(pdev->irq, sky2_intr, hw->msi ? 0 : IRQF_SHARED, | 4041 | err = request_irq(pdev->irq, sky2_intr, |
| 4042 | (hw->flags & SKY2_HW_USE_MSI) ? 0 : IRQF_SHARED, | ||
| 4018 | dev->name, hw); | 4043 | dev->name, hw); |
| 4019 | if (err) { | 4044 | if (err) { |
| 4020 | dev_err(&pdev->dev, "cannot assign irq %d\n", pdev->irq); | 4045 | dev_err(&pdev->dev, "cannot assign irq %d\n", pdev->irq); |
| @@ -4047,7 +4072,7 @@ static int __devinit sky2_probe(struct pci_dev *pdev, | |||
| 4047 | return 0; | 4072 | return 0; |
| 4048 | 4073 | ||
| 4049 | err_out_unregister: | 4074 | err_out_unregister: |
| 4050 | if (hw->msi) | 4075 | if (hw->flags & SKY2_HW_USE_MSI) |
| 4051 | pci_disable_msi(pdev); | 4076 | pci_disable_msi(pdev); |
| 4052 | unregister_netdev(dev); | 4077 | unregister_netdev(dev); |
| 4053 | err_out_free_netdev: | 4078 | err_out_free_netdev: |
| @@ -4096,7 +4121,7 @@ static void __devexit sky2_remove(struct pci_dev *pdev) | |||
| 4096 | sky2_read8(hw, B0_CTST); | 4121 | sky2_read8(hw, B0_CTST); |
| 4097 | 4122 | ||
| 4098 | free_irq(pdev->irq, hw); | 4123 | free_irq(pdev->irq, hw); |
| 4099 | if (hw->msi) | 4124 | if (hw->flags & SKY2_HW_USE_MSI) |
| 4100 | pci_disable_msi(pdev); | 4125 | pci_disable_msi(pdev); |
| 4101 | pci_free_consistent(pdev, STATUS_LE_BYTES, hw->st_le, hw->st_dma); | 4126 | pci_free_consistent(pdev, STATUS_LE_BYTES, hw->st_le, hw->st_dma); |
| 4102 | pci_release_regions(pdev); | 4127 | pci_release_regions(pdev); |
diff --git a/drivers/net/sky2.h b/drivers/net/sky2.h index 3baae48f8042..af303496f9e2 100644 --- a/drivers/net/sky2.h +++ b/drivers/net/sky2.h | |||
| @@ -2040,6 +2040,15 @@ struct sky2_hw { | |||
| 2040 | void __iomem *regs; | 2040 | void __iomem *regs; |
| 2041 | struct pci_dev *pdev; | 2041 | struct pci_dev *pdev; |
| 2042 | struct net_device *dev[2]; | 2042 | struct net_device *dev[2]; |
| 2043 | unsigned long flags; | ||
| 2044 | #define SKY2_HW_USE_MSI 0x00000001 | ||
| 2045 | #define SKY2_HW_FIBRE_PHY 0x00000002 | ||
| 2046 | #define SKY2_HW_GIGABIT 0x00000004 | ||
| 2047 | #define SKY2_HW_NEWER_PHY 0x00000008 | ||
| 2048 | #define SKY2_HW_RAMBUFFER 0x00000010 /* chip has RAM FIFO */ | ||
| 2049 | #define SKY2_HW_NEW_LE 0x00000020 /* new LSOv2 format */ | ||
| 2050 | #define SKY2_HW_AUTO_TX_SUM 0x00000040 /* new IP decode for Tx */ | ||
| 2051 | #define SKY2_HW_ADV_POWER_CTL 0x00000080 /* additional PHY power regs */ | ||
| 2043 | 2052 | ||
| 2044 | u8 chip_id; | 2053 | u8 chip_id; |
| 2045 | u8 chip_rev; | 2054 | u8 chip_rev; |
| @@ -2053,13 +2062,12 @@ struct sky2_hw { | |||
| 2053 | 2062 | ||
| 2054 | struct timer_list watchdog_timer; | 2063 | struct timer_list watchdog_timer; |
| 2055 | struct work_struct restart_work; | 2064 | struct work_struct restart_work; |
| 2056 | int msi; | ||
| 2057 | wait_queue_head_t msi_wait; | 2065 | wait_queue_head_t msi_wait; |
| 2058 | }; | 2066 | }; |
| 2059 | 2067 | ||
| 2060 | static inline int sky2_is_copper(const struct sky2_hw *hw) | 2068 | static inline int sky2_is_copper(const struct sky2_hw *hw) |
| 2061 | { | 2069 | { |
| 2062 | return !(hw->pmd_type == 'L' || hw->pmd_type == 'S' || hw->pmd_type == 'P'); | 2070 | return !(hw->flags & SKY2_HW_FIBRE_PHY); |
| 2063 | } | 2071 | } |
| 2064 | 2072 | ||
| 2065 | /* Register accessor for memory mapped device */ | 2073 | /* Register accessor for memory mapped device */ |
