Add IPv4/TCP/UDP Tx checksum offloading support. It seems the
controller also has support for IP/TCP checksum offloading for Rx path. But I failed to find to way to enable Rx MAC to compute the checksum of received frames.
This commit is contained in:
parent
abd12fc6d6
commit
9955274c64
@ -80,6 +80,8 @@ MODULE_DEPEND(et, miibus, 1, 1, 1);
|
||||
static int msi_disable = 0;
|
||||
TUNABLE_INT("hw.et.msi_disable", &msi_disable);
|
||||
|
||||
#define ET_CSUM_FEATURES (CSUM_IP | CSUM_TCP | CSUM_UDP)
|
||||
|
||||
static int et_probe(device_t);
|
||||
static int et_attach(device_t);
|
||||
static int et_detach(device_t);
|
||||
@ -332,7 +334,7 @@ et_attach(device_t dev)
|
||||
ifp->if_ioctl = et_ioctl;
|
||||
ifp->if_start = et_start;
|
||||
ifp->if_mtu = ETHERMTU;
|
||||
ifp->if_capabilities = IFCAP_VLAN_MTU;
|
||||
ifp->if_capabilities = /*IFCAP_TXCSUM*/IFCAP_HWCSUM | IFCAP_VLAN_MTU;
|
||||
ifp->if_capenable = ifp->if_capabilities;
|
||||
IFQ_SET_MAXLEN(&ifp->if_snd, ET_TX_NDESC);
|
||||
IFQ_SET_READY(&ifp->if_snd);
|
||||
@ -1175,7 +1177,7 @@ et_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
|
||||
struct et_softc *sc = ifp->if_softc;
|
||||
struct mii_data *mii = device_get_softc(sc->sc_miibus);
|
||||
struct ifreq *ifr = (struct ifreq *)data;
|
||||
int error = 0, max_framelen;
|
||||
int error = 0, mask, max_framelen;
|
||||
|
||||
/* XXX LOCKSUSED */
|
||||
switch (cmd) {
|
||||
@ -1232,6 +1234,20 @@ et_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
|
||||
}
|
||||
break;
|
||||
|
||||
case SIOCSIFCAP:
|
||||
ET_LOCK(sc);
|
||||
mask = ifr->ifr_reqcap ^ ifp->if_capenable;
|
||||
if ((mask & IFCAP_TXCSUM) != 0 &&
|
||||
(IFCAP_TXCSUM & ifp->if_capabilities) != 0) {
|
||||
ifp->if_capenable ^= IFCAP_TXCSUM;
|
||||
if ((IFCAP_TXCSUM & ifp->if_capenable) != 0)
|
||||
ifp->if_hwassist |= ET_CSUM_FEATURES;
|
||||
else
|
||||
ifp->if_hwassist &= ~ET_CSUM_FEATURES;
|
||||
}
|
||||
ET_UNLOCK(sc);
|
||||
break;
|
||||
|
||||
default:
|
||||
error = ether_ioctl(ifp, cmd, data);
|
||||
break;
|
||||
@ -2026,7 +2042,7 @@ et_encap(struct et_softc *sc, struct mbuf **m0)
|
||||
struct et_txdesc *td;
|
||||
bus_dmamap_t map;
|
||||
int error, maxsegs, first_idx, last_idx, i;
|
||||
uint32_t tx_ready_pos, last_td_ctrl2;
|
||||
uint32_t csum_flags, tx_ready_pos, last_td_ctrl2;
|
||||
|
||||
maxsegs = ET_TX_NDESC - tbd->tbd_used;
|
||||
if (maxsegs > ET_NSEG_MAX)
|
||||
@ -2088,6 +2104,15 @@ et_encap(struct et_softc *sc, struct mbuf **m0)
|
||||
last_td_ctrl2 |= ET_TDCTRL2_INTR;
|
||||
}
|
||||
|
||||
csum_flags = 0;
|
||||
if ((m->m_pkthdr.csum_flags & ET_CSUM_FEATURES) != 0) {
|
||||
if ((m->m_pkthdr.csum_flags & CSUM_IP) != 0)
|
||||
csum_flags |= ET_TDCTRL2_CSUM_IP;
|
||||
if ((m->m_pkthdr.csum_flags & CSUM_UDP) != 0)
|
||||
csum_flags |= ET_TDCTRL2_CSUM_UDP;
|
||||
else if ((m->m_pkthdr.csum_flags & CSUM_TCP) != 0)
|
||||
csum_flags |= ET_TDCTRL2_CSUM_TCP;
|
||||
}
|
||||
last_idx = -1;
|
||||
for (i = 0; i < ctx.nsegs; ++i) {
|
||||
int idx;
|
||||
@ -2097,11 +2122,11 @@ et_encap(struct et_softc *sc, struct mbuf **m0)
|
||||
td->td_addr_hi = htole32(ET_ADDR_HI(segs[i].ds_addr));
|
||||
td->td_addr_lo = htole32(ET_ADDR_LO(segs[i].ds_addr));
|
||||
td->td_ctrl1 = htole32(segs[i].ds_len & ET_TDCTRL1_LEN_MASK);
|
||||
|
||||
if (i == ctx.nsegs - 1) { /* Last frag */
|
||||
td->td_ctrl2 = htole32(last_td_ctrl2);
|
||||
td->td_ctrl2 = htole32(last_td_ctrl2 | csum_flags);
|
||||
last_idx = idx;
|
||||
}
|
||||
} else
|
||||
td->td_ctrl2 = htole32(csum_flags);
|
||||
|
||||
MPASS(tx_ring->tr_ready_index < ET_TX_NDESC);
|
||||
if (++tx_ring->tr_ready_index == ET_TX_NDESC) {
|
||||
|
@ -111,6 +111,18 @@ struct et_txdesc {
|
||||
#define ET_TDCTRL2_LAST_FRAG 0x00000001
|
||||
#define ET_TDCTRL2_FIRST_FRAG 0x00000002
|
||||
#define ET_TDCTRL2_INTR 0x00000004
|
||||
#define ET_TDCTRL2_CTRL_WORD 0x00000008
|
||||
#define ET_TDCTRL2_HDX_BACKP 0x00000010
|
||||
#define ET_TDCTRL2_XMIT_PAUSE 0x00000020
|
||||
#define ET_TDCTRL2_FRAME_ERR 0x00000040
|
||||
#define ET_TDCTRL2_NO_CRC 0x00000080
|
||||
#define ET_TDCTRL2_MAC_OVRRD 0x00000100
|
||||
#define ET_TDCTRL2_PAD_PACKET 0x00000200
|
||||
#define ET_TDCTRL2_JUMBO_PACKET 0x00000400
|
||||
#define ET_TDCTRL2_INS_VLAN 0x00000800
|
||||
#define ET_TDCTRL2_CSUM_IP 0x00001000
|
||||
#define ET_TDCTRL2_CSUM_TCP 0x00002000
|
||||
#define ET_TDCTRL2_CSUM_UDP 0x00004000
|
||||
|
||||
struct et_rxdesc {
|
||||
uint32_t rd_addr_lo;
|
||||
|
Loading…
x
Reference in New Issue
Block a user