diff options
author | Brad Smith <brad@cvs.openbsd.org> | 2006-11-06 03:52:38 +0000 |
---|---|---|
committer | Brad Smith <brad@cvs.openbsd.org> | 2006-11-06 03:52:38 +0000 |
commit | 251ab214435f554736da79414b1a27f6fc5595ed (patch) | |
tree | 5a0c2537994add981b012ff0cacf65a8279b98c5 /sys/dev/pci/if_em.c | |
parent | eb74a369c8f72096ee10551e85932d5f795565ef (diff) |
Sync up to Intel's latest FreeBSD em driver (6.2.9). Adds support
for a few newer Intel PCIe boards, some code removal and cleaning
and a few bug fixes.
From: Jack Vogel@Intel
Tested by mk@ wilfried@ brad@ dlg@, Marc Winiger, Gabriel Kihlman,
Jason Dixon, Johan Mson Lindman, and a few other end users.
Tested with 82543, 82544, 82540, 82545, 82541, 82547, 82546 and 82573.
Diffstat (limited to 'sys/dev/pci/if_em.c')
-rw-r--r-- | sys/dev/pci/if_em.c | 83 |
1 files changed, 44 insertions, 39 deletions
diff --git a/sys/dev/pci/if_em.c b/sys/dev/pci/if_em.c index d6dfc7082bb..30b8946e5bf 100644 --- a/sys/dev/pci/if_em.c +++ b/sys/dev/pci/if_em.c @@ -31,7 +31,7 @@ POSSIBILITY OF SUCH DAMAGE. ***************************************************************************/ -/* $OpenBSD: if_em.c,v 1.152 2006/11/03 06:39:10 brad Exp $ */ +/* $OpenBSD: if_em.c,v 1.153 2006/11/06 03:52:37 brad Exp $ */ /* $FreeBSD: if_em.c,v 1.46 2004/09/29 18:28:28 mlaier Exp $ */ #include <dev/pci/if_em.h> @@ -45,7 +45,7 @@ int em_display_debug_stats = 0; * Driver version *********************************************************************/ -char em_driver_version[] = "6.1.4"; +char em_driver_version[] = "6.2.9"; /********************************************************************* * PCI Device ID Table @@ -97,6 +97,7 @@ const struct pci_matchid em_devices[] = { { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_82571EB_COPPER }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_82571EB_FIBER }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_82571EB_QUAD_CPR }, + { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_82571EB_QUAD_CPR_LP }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_82571EB_SERDES }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_82572EI_COPPER }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_82572EI_FIBER }, @@ -113,6 +114,8 @@ const struct pci_matchid em_devices[] = { { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_ICH8_IGP_AMT }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_ICH8_IGP_C }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_ICH8_IFE }, + { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_ICH8_IFE_G }, + { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_ICH8_IFE_GT }, { PCI_VENDOR_INTEL, PCI_PRODUCT_INTEL_ICH8_IGP_M } }; @@ -553,6 +556,12 @@ em_ioctl(struct ifnet *ifp, u_long command, caddr_t data) } break; case SIOCSIFMEDIA: + /* Check SOL/IDER usage */ + if (em_check_phy_reset_block(&sc->hw)) { + printf("%s: Media change is blocked due to SOL/IDER session.\n", + sc->sc_dv.dv_xname); + break; + } case SIOCGIFMEDIA: IOCTL_DEBUGOUT("ioctl rcv'd: SIOCxIFMEDIA (Get/Set Interface Media)"); error = ifmedia_ioctl(ifp, ifr, &sc->media, command); @@ -638,7 +647,8 @@ em_init(void *arg) } IFQ_SET_MAXLEN(&ifp->if_snd, sc->num_tx_desc - 1); - /* Packet Buffer Allocation (PBA) + /* + * Packet Buffer Allocation (PBA) * Writing PBA sets the receive portion of the buffer * the remainder is used for the transmit buffer. * @@ -659,9 +669,10 @@ em_init(void *arg) sc->tx_head_addr = pba << EM_TX_HEAD_ADDR_SHIFT; sc->tx_fifo_size = (E1000_PBA_40K - pba) << EM_PBA_BYTES_SHIFT; break; - case em_80003es2lan: /* 80003es2lan: Total Packet Buffer is 48K */ - case em_82571: /* 82571: Total Packet Buffer is 48K */ - case em_82572: /* 82572: Total Packet Buffer is 48K */ + /* Total Packet Buffer on these is 48k */ + case em_82571: + case em_82572: + case em_80003es2lan: pba = E1000_PBA_32K; /* 32K for Rx, 16K for Tx */ break; case em_82573: /* 82573: Total Packet Buffer is 32K */ @@ -1277,8 +1288,6 @@ em_local_timer(void *arg) splx(s); } -#define SPEED_MODE_BIT (1<<21) /* On PCI-E MACs only */ - void em_update_link_status(struct em_softc *sc) { @@ -1294,6 +1303,7 @@ em_update_link_status(struct em_softc *sc) ((sc->hw.mac_type == em_82571) || (sc->hw.mac_type == em_82572))) { int tarc0; + tarc0 = E1000_READ_REG(&sc->hw, TARC0); tarc0 |= SPEED_MODE_BIT; E1000_WRITE_REG(&sc->hw, TARC0, tarc0); @@ -1526,7 +1536,8 @@ em_hardware_init(struct em_softc *sc) (sc->hw.mac_type == em_82571 || sc->hw.mac_type == em_82572)) { uint16_t phy_tmp = 0; - /* speed up time to link by disabling smart power down */ + + /* Speed up time to link by disabling smart power down */ em_read_phy_reg(&sc->hw, IGP02E1000_PHY_POWER_MGMT, &phy_tmp); phy_tmp &= ~IGP02E1000_PM_SPD; em_write_phy_reg(&sc->hw, IGP02E1000_PHY_POWER_MGMT, phy_tmp); @@ -1538,11 +1549,12 @@ em_hardware_init(struct em_softc *sc) * - High water mark should allow for at least two frames to be * received after sending an XOFF. * - Low water mark works best when it is very near the high water mark. - * This allows the receiver to restart by sending XON when it has drained - * a bit. Here we use an arbitary value of 1500 which will restart after - * one full frame is pulled from the buffer. There could be several smaller - * frames in the buffer and if so they will not trigger the XON until their - * total number reduces the buffer by 1500. + * This allows the receiver to restart by sending XON when it has + * drained a bit. Here we use an arbitary value of 1500 which will + * restart after one full frame is pulled from the buffer. There + * could be several smaller frames in the buffer and if so they will + * not trigger the XON until their total number reduces the buffer + * by 1500. * - The pause time is fairly large at 1000 x 512ns = 512 usec. */ rx_buffer_size = ((E1000_READ_REG(&sc->hw, PBA) & 0xffff) << 10 ); @@ -1555,7 +1567,7 @@ em_hardware_init(struct em_softc *sc) else sc->hw.fc_pause_time = 0x1000; sc->hw.fc_send_xon = TRUE; - sc->hw.fc = em_fc_full; + sc->hw.fc = E1000_FC_FULL; if (em_init_hw(&sc->hw) < 0) { printf("%s: Hardware Initialization Failed", @@ -1578,6 +1590,7 @@ em_setup_interface(struct em_softc *sc) { struct ifnet *ifp; u_char fiber_type = IFM_1000_SX; + INIT_DEBUGOUT("em_setup_interface: begin"); ifp = &sc->interface_data.ac_if; @@ -1835,8 +1848,7 @@ em_setup_transmit_structures(struct em_softc *sc) void em_initialize_transmit_unit(struct em_softc *sc) { - u_int32_t reg_tctl, reg_tarc; - u_int32_t reg_tipg = 0; + u_int32_t reg_tctl, reg_tipg = 0; u_int64_t bus_addr; INIT_DEBUGOUT("em_initialize_transmit_unit: begin"); @@ -1883,24 +1895,6 @@ em_initialize_transmit_unit(struct em_softc *sc) if (sc->hw.mac_type >= em_82540) E1000_WRITE_REG(&sc->hw, TADV, sc->tx_abs_int_delay); - /* Do adapter specific tweaks before we enable the transmitter */ - if (sc->hw.mac_type == em_82571 || sc->hw.mac_type == em_82572) { - reg_tarc = E1000_READ_REG(&sc->hw, TARC0); - reg_tarc |= (1 << 25); - E1000_WRITE_REG(&sc->hw, TARC0, reg_tarc); - reg_tarc = E1000_READ_REG(&sc->hw, TARC1); - reg_tarc |= (1 << 25); - reg_tarc &= ~(1 << 28); - E1000_WRITE_REG(&sc->hw, TARC1, reg_tarc); - } else if (sc->hw.mac_type == em_80003es2lan) { - reg_tarc = E1000_READ_REG(&sc->hw, TARC0); - reg_tarc |= 1; - E1000_WRITE_REG(&sc->hw, TARC0, reg_tarc); - reg_tarc = E1000_READ_REG(&sc->hw, TARC1); - reg_tarc |= 1; - E1000_WRITE_REG(&sc->hw, TARC1, reg_tarc); - } - /* Program the Transmit Control Register */ reg_tctl = E1000_TCTL_PSP | E1000_TCTL_EN | (E1000_COLLISION_THRESHOLD << E1000_CT_SHIFT); @@ -2289,10 +2283,6 @@ em_initialize_receive_unit(struct em_softc *sc) E1000_WRITE_REG(&sc->hw, RDBAH, (u_int32_t)(bus_addr >> 32)); E1000_WRITE_REG(&sc->hw, RDBAL, (u_int32_t)bus_addr); - /* Setup the HW Rx Head and Tail Descriptor Pointers */ - E1000_WRITE_REG(&sc->hw, RDT, sc->num_rx_desc - 1); - E1000_WRITE_REG(&sc->hw, RDH, 0); - /* Setup the Receive Control Register */ reg_rctl = E1000_RCTL_EN | E1000_RCTL_BAM | E1000_RCTL_LBM_NO | E1000_RCTL_RDMTS_HALF | @@ -2329,6 +2319,10 @@ em_initialize_receive_unit(struct em_softc *sc) /* Enable Receives */ E1000_WRITE_REG(&sc->hw, RCTL, reg_rctl); + + /* Setup the HW Rx Head and Tail Descriptor Pointers */ + E1000_WRITE_REG(&sc->hw, RDH, 0); + E1000_WRITE_REG(&sc->hw, RDT, sc->num_rx_desc - 1); } /********************************************************************* @@ -2701,6 +2695,16 @@ em_pci_clear_mwi(struct em_hw *hw) (hw->pci_cmd_word & ~CMD_MEM_WRT_INVALIDATE)); } +/* + * We may eventually really do this, but its unnecessary + * for now so we just return unsupported. + */ +int32_t +em_read_pcie_cap_reg(struct em_hw *hw, uint32_t reg, uint16_t *value) +{ + return (0); +} + /********************************************************************* * 82544 Coexistence issue workaround. * There are 2 issues. @@ -2895,6 +2899,7 @@ em_print_hw_stats(struct em_softc *sc) (long long)sc->stats.algnerrc); printf("%s: Carrier extension errors = %lld\n", unit, (long long)sc->stats.cexterr); + printf("%s: RX overruns = %ld\n", unit, sc->rx_overruns); printf("%s: watchdog timeouts = %ld\n", unit, |