diff options
Diffstat (limited to 'freebsd/sys/dev/re/if_re.c')
-rw-r--r-- | freebsd/sys/dev/re/if_re.c | 114 |
1 files changed, 68 insertions, 46 deletions
diff --git a/freebsd/sys/dev/re/if_re.c b/freebsd/sys/dev/re/if_re.c index b574f9a2..554af66a 100644 --- a/freebsd/sys/dev/re/if_re.c +++ b/freebsd/sys/dev/re/if_re.c @@ -129,6 +129,7 @@ __FBSDID("$FreeBSD$"); #include <sys/taskqueue.h> #include <net/if.h> +#include <net/if_var.h> #include <net/if_arp.h> #include <net/ethernet.h> #include <net/if_dl.h> @@ -149,7 +150,7 @@ __FBSDID("$FreeBSD$"); #include <dev/pci/pcireg.h> #include <dev/pci/pcivar.h> -#include <pci/if_rlreg.h> +#include <dev/rl/if_rlreg.h> MODULE_DEPEND(re, pci, 1, 1, 1); MODULE_DEPEND(re, ether, 1, 1, 1); @@ -239,6 +240,7 @@ static const struct rl_hwrev re_hwrevs[] = { { RL_HWREV_8168F, RL_8169, "8168F/8111F", RL_JUMBO_MTU_9K}, { RL_HWREV_8168G, RL_8169, "8168G/8111G", RL_JUMBO_MTU_9K}, { RL_HWREV_8168GU, RL_8169, "8168GU/8111GU", RL_JUMBO_MTU_9K}, + { RL_HWREV_8168H, RL_8169, "8168H/8111H", RL_JUMBO_MTU_9K}, { RL_HWREV_8411, RL_8169, "8411", RL_JUMBO_MTU_9K}, { RL_HWREV_8411B, RL_8169, "8411B", RL_JUMBO_MTU_9K}, { 0, 0, NULL, 0 } @@ -305,6 +307,7 @@ static void re_set_linkspeed (struct rl_softc *); #ifdef DEV_NETMAP /* see ixgbe.c for details */ #include <dev/netmap/if_re_netmap.h> +MODULE_DEPEND(re, netmap, 1, 1, 1); #endif /* !DEV_NETMAP */ #ifdef RE_DIAG @@ -635,9 +638,8 @@ re_miibus_statchg(device_t dev) } } /* - * RealTek controllers does not provide any interface to - * Tx/Rx MACs for resolved speed, duplex and flow-control - * parameters. + * RealTek controllers do not provide any interface to the RX/TX + * MACs for resolved speed, duplex and flow-control parameters. */ } @@ -659,7 +661,7 @@ re_set_rxmode(struct rl_softc *sc) rxfilt = RL_RXCFG_CONFIG | RL_RXCFG_RX_INDIV | RL_RXCFG_RX_BROAD; if ((sc->rl_flags & RL_FLAG_EARLYOFF) != 0) rxfilt |= RL_RXCFG_EARLYOFF; - else if ((sc->rl_flags & RL_FLAG_EARLYOFFV2) != 0) + else if ((sc->rl_flags & RL_FLAG_8168G_PLUS) != 0) rxfilt |= RL_RXCFG_EARLYOFFV2; if (ifp->if_flags & (IFF_ALLMULTI | IFF_PROMISC)) { @@ -953,7 +955,7 @@ re_probe(device_t dev) } t = re_devs; - for (i = 0; i < sizeof(re_devs) / sizeof(re_devs[0]); i++, t++) { + for (i = 0; i < nitems(re_devs); i++, t++) { if (vendor == t->rl_vid && devid == t->rl_did) { device_set_desc(dev, t->rl_name); return (BUS_PROBE_DEFAULT); @@ -1206,11 +1208,10 @@ re_attach(device_t dev) struct rl_softc *sc; struct ifnet *ifp; const struct rl_hwrev *hw_rev; + int capmask, error = 0, hwrev, i, msic, msixc, + phy, reg, rid; u_int32_t cap, ctl; - int hwrev; u_int16_t devid, re_did = 0; - int error = 0, i, phy, rid; - int msic, msixc, reg; uint8_t cfg; sc = device_get_softc(dev); @@ -1338,7 +1339,7 @@ re_attach(device_t dev) SYS_RES_IRQ, &rid, RF_ACTIVE); if (sc->rl_irq[i] == NULL) { device_printf(dev, - "couldn't llocate IRQ resources for " + "couldn't allocate IRQ resources for " "message %d\n", rid); error = ENXIO; goto fail; @@ -1364,8 +1365,8 @@ re_attach(device_t dev) if ((cap & PCIEM_LINK_CAP_ASPM) != 0) { ctl = pci_read_config(dev, sc->rl_expcap + PCIER_LINK_CTL, 2); - if ((ctl & 0x0003) != 0) { - ctl &= ~0x0003; + if ((ctl & PCIEM_LINK_CTL_ASPMC) != 0) { + ctl &= ~PCIEM_LINK_CTL_ASPMC; pci_write_config(dev, sc->rl_expcap + PCIER_LINK_CTL, ctl, 2); device_printf(dev, "ASPM disabled\n"); @@ -1490,11 +1491,12 @@ re_attach(device_t dev) RL_FLAG_DESCV2 | RL_FLAG_MACSTAT | RL_FLAG_CMDSTOP | RL_FLAG_AUTOPAD | RL_FLAG_JUMBOV2 | RL_FLAG_CMDSTOP_WAIT_TXQ | RL_FLAG_WOL_MANLINK | - RL_FLAG_EARLYOFFV2 | RL_FLAG_RXDV_GATED; + RL_FLAG_8168G_PLUS; break; case RL_HWREV_8168GU: + case RL_HWREV_8168H: if (pci_get_device(dev) == RT_DEVICEID_8101E) { - /* RTL8106EUS */ + /* RTL8106E(US), RTL8107E */ sc->rl_flags |= RL_FLAG_FASTETHER; } else sc->rl_flags |= RL_FLAG_JUMBOV2 | RL_FLAG_WOL_MANLINK; @@ -1502,7 +1504,7 @@ re_attach(device_t dev) sc->rl_flags |= RL_FLAG_PHYWAKE | RL_FLAG_PAR | RL_FLAG_DESCV2 | RL_FLAG_MACSTAT | RL_FLAG_CMDSTOP | RL_FLAG_AUTOPAD | RL_FLAG_CMDSTOP_WAIT_TXQ | - RL_FLAG_EARLYOFFV2 | RL_FLAG_RXDV_GATED; + RL_FLAG_8168G_PLUS; break; case RL_HWREV_8169_8110SB: case RL_HWREV_8169_8110SBL: @@ -1652,8 +1654,11 @@ re_attach(device_t dev) phy = RE_PHYAD_INTERNAL; if (sc->rl_type == RL_8169) phy = 1; + capmask = BMSR_DEFCAPMASK; + if ((sc->rl_flags & RL_FLAG_FASTETHER) != 0) + capmask &= ~BMSR_EXTSTAT; error = mii_attach(dev, &sc->rl_miibus, ifp, re_ifmedia_upd, - re_ifmedia_sts, BMSR_DEFCAPMASK, phy, MII_OFFSET_ANY, MIIF_DOPAUSE); + re_ifmedia_sts, capmask, phy, MII_OFFSET_ANY, MIIF_DOPAUSE); if (error != 0) { device_printf(dev, "attaching PHYs failed\n"); goto fail; @@ -1676,7 +1681,7 @@ re_attach(device_t dev) /* * Don't enable TSO by default. It is known to generate * corrupted TCP segments(bad TCP options) under certain - * circumtances. + * circumstances. */ ifp->if_hwassist &= ~CSUM_TSO; ifp->if_capenable &= ~(IFCAP_TSO4 | IFCAP_VLAN_HWTSO); @@ -1688,18 +1693,18 @@ re_attach(device_t dev) * Must appear after the call to ether_ifattach() because * ether_ifattach() sets ifi_hdrlen to the default value. */ - ifp->if_data.ifi_hdrlen = sizeof(struct ether_vlan_header); + ifp->if_hdrlen = sizeof(struct ether_vlan_header); #ifdef DEV_NETMAP re_netmap_attach(sc); #endif /* DEV_NETMAP */ + #ifdef RE_DIAG /* * Perform hardware diagnostic on the original RTL8169. * Some 32-bit cards were incorrectly wired and would * malfunction if plugged into a 64-bit slot. */ - if (hwrev == RL_HWREV_8169) { error = re_diag(sc); if (error) { @@ -1731,7 +1736,6 @@ re_attach(device_t dev) } fail: - if (error) re_detach(dev); @@ -1825,10 +1829,10 @@ re_detach(device_t dev) /* Unload and free the RX DMA ring memory and map */ if (sc->rl_ldata.rl_rx_list_tag) { - if (sc->rl_ldata.rl_rx_list_map) + if (sc->rl_ldata.rl_rx_list_addr) bus_dmamap_unload(sc->rl_ldata.rl_rx_list_tag, sc->rl_ldata.rl_rx_list_map); - if (sc->rl_ldata.rl_rx_list_map && sc->rl_ldata.rl_rx_list) + if (sc->rl_ldata.rl_rx_list) bus_dmamem_free(sc->rl_ldata.rl_rx_list_tag, sc->rl_ldata.rl_rx_list, sc->rl_ldata.rl_rx_list_map); @@ -1838,10 +1842,10 @@ re_detach(device_t dev) /* Unload and free the TX DMA ring memory and map */ if (sc->rl_ldata.rl_tx_list_tag) { - if (sc->rl_ldata.rl_tx_list_map) + if (sc->rl_ldata.rl_tx_list_addr) bus_dmamap_unload(sc->rl_ldata.rl_tx_list_tag, sc->rl_ldata.rl_tx_list_map); - if (sc->rl_ldata.rl_tx_list_map && sc->rl_ldata.rl_tx_list) + if (sc->rl_ldata.rl_tx_list) bus_dmamem_free(sc->rl_ldata.rl_tx_list_tag, sc->rl_ldata.rl_tx_list, sc->rl_ldata.rl_tx_list_map); @@ -1883,10 +1887,10 @@ re_detach(device_t dev) /* Unload and free the stats buffer and map */ if (sc->rl_ldata.rl_stag) { - if (sc->rl_ldata.rl_smap) + if (sc->rl_ldata.rl_stats_addr) bus_dmamap_unload(sc->rl_ldata.rl_stag, sc->rl_ldata.rl_smap); - if (sc->rl_ldata.rl_smap && sc->rl_ldata.rl_stats) + if (sc->rl_ldata.rl_stats) bus_dmamem_free(sc->rl_ldata.rl_stag, sc->rl_ldata.rl_stats, sc->rl_ldata.rl_smap); bus_dma_tag_destroy(sc->rl_ldata.rl_stag); @@ -2248,7 +2252,7 @@ re_rxeof(struct rl_softc *sc, int *rx_npktsp) (rxstat & RL_RDESC_STAT_ERRS) == RL_RDESC_STAT_GIANT) rxerr = 0; if (rxerr != 0) { - ifp->if_ierrors++; + if_inc_counter(ifp, IFCOUNTER_IERRORS, 1); /* * If this is part of a multi-fragment packet, * discard all the pieces. @@ -2271,7 +2275,7 @@ re_rxeof(struct rl_softc *sc, int *rx_npktsp) else rxerr = re_newbuf(sc, i); if (rxerr != 0) { - ifp->if_iqdrops++; + if_inc_counter(ifp, IFCOUNTER_IQDROPS, 1); if (sc->rl_head != NULL) { m_freem(sc->rl_head); sc->rl_head = sc->rl_tail = NULL; @@ -2313,7 +2317,7 @@ re_rxeof(struct rl_softc *sc, int *rx_npktsp) #ifdef RE_FIXUP_RX re_fixup_rx(m); #endif - ifp->if_ipackets++; + if_inc_counter(ifp, IFCOUNTER_IPACKETS, 1); m->m_pkthdr.rcvif = ifp; /* Do RX checksumming if enabled */ @@ -2432,11 +2436,11 @@ re_txeof(struct rl_softc *sc) txd->tx_m = NULL; if (txstat & (RL_TDESC_STAT_EXCESSCOL| RL_TDESC_STAT_COLCNT)) - ifp->if_collisions++; + if_inc_counter(ifp, IFCOUNTER_COLLISIONS, 1); if (txstat & RL_TDESC_STAT_TXERRSUM) - ifp->if_oerrors++; + if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); else - ifp->if_opackets++; + if_inc_counter(ifp, IFCOUNTER_OPACKETS, 1); } sc->rl_ldata.rl_tx_free++; ifp->if_drv_flags &= ~IFF_DRV_OACTIVE; @@ -2551,7 +2555,7 @@ re_intr(void *arg) return (FILTER_STRAY); CSR_WRITE_2(sc, RL_IMR, 0); - taskqueue_enqueue_fast(taskqueue_fast, &sc->rl_inttask); + taskqueue_enqueue(taskqueue_fast, &sc->rl_inttask); return (FILTER_HANDLED); } @@ -2619,7 +2623,7 @@ re_int_task(void *arg, int npending) RL_UNLOCK(sc); if ((CSR_READ_2(sc, RL_ISR) & RL_INTRS_CPLUS) || rval) { - taskqueue_enqueue_fast(taskqueue_fast, &sc->rl_inttask); + taskqueue_enqueue(taskqueue_fast, &sc->rl_inttask); return; } @@ -2827,7 +2831,7 @@ re_encap(struct rl_softc *sc, struct mbuf **m_head) /* * Unconditionally enable IP checksum if TCP or UDP * checksum is required. Otherwise, TCP/UDP checksum - * does't make effects. + * doesn't make effects. */ if (((*m_head)->m_pkthdr.csum_flags & RE_CSUM_FEATURES) != 0) { if ((sc->rl_flags & RL_FLAG_DESCV2) == 0) { @@ -2937,6 +2941,7 @@ re_start_locked(struct ifnet *ifp) return; } #endif /* DEV_NETMAP */ + if ((ifp->if_drv_flags & (IFF_DRV_RUNNING | IFF_DRV_OACTIVE)) != IFF_DRV_RUNNING || (sc->rl_flags & RL_FLAG_LINK) == 0) return; @@ -3192,14 +3197,18 @@ re_init_locked(struct rl_softc *sc) CSR_WRITE_4(sc, RL_TXLIST_ADDR_LO, RL_ADDR_LO(sc->rl_ldata.rl_tx_list_addr)); - if ((sc->rl_flags & RL_FLAG_RXDV_GATED) != 0) + if ((sc->rl_flags & RL_FLAG_8168G_PLUS) != 0) { + /* Disable RXDV gate. */ CSR_WRITE_4(sc, RL_MISC, CSR_READ_4(sc, RL_MISC) & ~0x00080000); + } /* - * Enable transmit and receive. + * Enable transmit and receive for pre-RTL8168G controllers. + * RX/TX MACs should be enabled before RX/TX configuration. */ - CSR_WRITE_1(sc, RL_COMMAND, RL_CMD_TX_ENB|RL_CMD_RX_ENB); + if ((sc->rl_flags & RL_FLAG_8168G_PLUS) == 0) + CSR_WRITE_1(sc, RL_COMMAND, RL_CMD_TX_ENB | RL_CMD_RX_ENB); /* * Set the initial TX configuration. @@ -3227,6 +3236,13 @@ re_init_locked(struct rl_softc *sc) CSR_WRITE_2(sc, RL_INTRMOD, 0x5100); } + /* + * Enable transmit and receive for RTL8168G and later controllers. + * RX/TX MACs should be enabled after RX/TX configuration. + */ + if ((sc->rl_flags & RL_FLAG_8168G_PLUS) != 0) + CSR_WRITE_1(sc, RL_COMMAND, RL_CMD_TX_ENB | RL_CMD_RX_ENB); + #ifdef DEVICE_POLLING /* * Disable interrupts if we are polling. @@ -3250,10 +3266,6 @@ re_init_locked(struct rl_softc *sc) /* Start RX/TX process. */ CSR_WRITE_4(sc, RL_MISSEDPKT, 0); -#ifdef notdef - /* Enable receiver and transmitter. */ - CSR_WRITE_1(sc, RL_COMMAND, RL_CMD_TX_ENB|RL_CMD_RX_ENB); -#endif /* * Initialize the timer interrupt register so that @@ -3294,7 +3306,7 @@ re_init_locked(struct rl_softc *sc) if ((sc->rl_flags & RL_FLAG_JUMBOV2) != 0) { /* * For controllers that use new jumbo frame scheme, - * set maximum size of jumbo frame depedning on + * set maximum size of jumbo frame depending on * controller revisions. */ if (ifp->if_mtu > RL_MTU) @@ -3546,7 +3558,7 @@ re_watchdog(struct rl_softc *sc) } if_printf(ifp, "watchdog timeout\n"); - ifp->if_oerrors++; + if_inc_counter(ifp, IFCOUNTER_OERRORS, 1); re_rxeof(sc, NULL); ifp->if_drv_flags &= ~IFF_DRV_RUNNING; @@ -3585,6 +3597,12 @@ re_stop(struct rl_softc *sc) ~(RL_RXCFG_RX_ALLPHYS | RL_RXCFG_RX_INDIV | RL_RXCFG_RX_MULTI | RL_RXCFG_RX_BROAD)); + if ((sc->rl_flags & RL_FLAG_8168G_PLUS) != 0) { + /* Enable RXDV gate. */ + CSR_WRITE_4(sc, RL_MISC, CSR_READ_4(sc, RL_MISC) | + 0x00080000); + } + if ((sc->rl_flags & RL_FLAG_WAIT_TXPOLL) != 0) { for (i = RL_TIMEOUT; i > 0; i--) { if ((CSR_READ_1(sc, sc->rl_txstart) & @@ -3836,6 +3854,11 @@ re_setwol(struct rl_softc *sc) CSR_READ_1(sc, RL_GPIO) & ~0x01); } if ((ifp->if_capenable & IFCAP_WOL) != 0) { + if ((sc->rl_flags & RL_FLAG_8168G_PLUS) != 0) { + /* Disable RXDV gate. */ + CSR_WRITE_4(sc, RL_MISC, CSR_READ_4(sc, RL_MISC) & + ~0x00080000); + } re_set_rxmode(sc); if ((sc->rl_flags & RL_FLAG_WOL_MANLINK) != 0) re_set_linkspeed(sc); @@ -3948,7 +3971,6 @@ re_add_sysctls(struct rl_softc *sc) sc->rl_int_rx_mod = RL_TIMER_DEFAULT; } } - } static int @@ -3990,7 +4012,7 @@ re_sysctl_stats(SYSCTL_HANDLER_ARGS) RL_UNLOCK(sc); if (i == 0) { device_printf(sc->rl_dev, - "DUMP statistics request timedout\n"); + "DUMP statistics request timed out\n"); return (ETIMEDOUT); } done: |