From 421496cffbe5189e312e9066d12be20294e00a37 Mon Sep 17 00:00:00 2001 From: sephe Date: Tue, 14 Aug 2007 13:30:35 +0000 Subject: [PATCH] Add a new csum flag to tell IP defragmenter that csum_data does _not_ contain a valid IP fragment payload checksum. This flag is only intented to be used by IP defragmenter. Currently only bce(4), bge(4) and ti(4) provide valid IP fragment payload checksum. Turn on the new csum flag for the rest of the drivers, which support hardware TCP/UDP checksum offload but hard-wire csum_data to 0xffff, to avoid bypassing verification of defragmented payload's checksum. Discussed-with: dillon@, hsu@ Approved-by: dillon@ --- sys/dev/netif/em/if_em.c | 5 +++-- sys/dev/netif/gx/if_gx.c | 5 +++-- sys/dev/netif/lge/if_lge.c | 5 +++-- sys/dev/netif/ndis/if_ndis.c | 5 +++-- sys/dev/netif/nfe/if_nfe.c | 5 +++-- sys/dev/netif/nge/if_nge.c | 5 +++-- sys/dev/netif/re/if_re.c | 5 +++-- sys/dev/netif/stge/if_stge.c | 6 ++++-- sys/dev/netif/txp/if_txp.c | 5 +++-- sys/dev/netif/vge/if_vge.c | 5 +++-- sys/dev/netif/xl/if_xl.c | 5 +++-- sys/netinet/ip_input.c | 12 +++++++++++- sys/sys/mbuf.h | 6 +++++- 13 files changed, 50 insertions(+), 24 deletions(-) diff --git a/sys/dev/netif/em/if_em.c b/sys/dev/netif/em/if_em.c index 5a9588f0cf..c85f29c40b 100644 --- a/sys/dev/netif/em/if_em.c +++ b/sys/dev/netif/em/if_em.c @@ -64,7 +64,7 @@ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * $DragonFly: src/sys/dev/netif/em/if_em.c,v 1.59 2007/05/14 12:31:41 sephe Exp $ + * $DragonFly: src/sys/dev/netif/em/if_em.c,v 1.60 2007/08/14 13:30:35 sephe Exp $ * $FreeBSD$ */ /* @@ -3145,7 +3145,8 @@ em_receive_checksum(struct adapter *adapter, /* Did it pass? */ if (!(rx_desc->errors & E1000_RXD_ERR_TCPE)) { mp->m_pkthdr.csum_flags |= - (CSUM_DATA_VALID | CSUM_PSEUDO_HDR); + (CSUM_DATA_VALID | CSUM_PSEUDO_HDR | + CSUM_FRAG_NOT_CHECKED); mp->m_pkthdr.csum_data = htons(0xffff); } } diff --git a/sys/dev/netif/gx/if_gx.c b/sys/dev/netif/gx/if_gx.c index c8f40dcfeb..4e015095be 100644 --- a/sys/dev/netif/gx/if_gx.c +++ b/sys/dev/netif/gx/if_gx.c @@ -27,7 +27,7 @@ * SUCH DAMAGE. * * $FreeBSD: src/sys/dev/gx/if_gx.c,v 1.2.2.3 2001/12/14 19:51:39 jlemon Exp $ - * $DragonFly: src/sys/dev/netif/gx/if_gx.c,v 1.27 2007/03/26 12:13:58 sephe Exp $ + * $DragonFly: src/sys/dev/netif/gx/if_gx.c,v 1.28 2007/08/14 13:30:35 sephe Exp $ */ #include @@ -1257,7 +1257,8 @@ gx_rxeof(struct gx_softc *gx) #endif if ((staterr & TCP_CSMASK) == GX_RXSTAT_HAS_TCP_CSUM) { m->m_pkthdr.csum_flags |= - CSUM_DATA_VALID | CSUM_PSEUDO_HDR; + CSUM_DATA_VALID | CSUM_PSEUDO_HDR | + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } } diff --git a/sys/dev/netif/lge/if_lge.c b/sys/dev/netif/lge/if_lge.c index 11da586503..c273f892a5 100644 --- a/sys/dev/netif/lge/if_lge.c +++ b/sys/dev/netif/lge/if_lge.c @@ -31,7 +31,7 @@ * THE POSSIBILITY OF SUCH DAMAGE. * * $FreeBSD: src/sys/dev/lge/if_lge.c,v 1.5.2.2 2001/12/14 19:49:23 jlemon Exp $ - * $DragonFly: src/sys/dev/netif/lge/if_lge.c,v 1.38 2006/12/22 23:26:20 swildner Exp $ + * $DragonFly: src/sys/dev/netif/lge/if_lge.c,v 1.39 2007/08/14 13:30:35 sephe Exp $ */ /* @@ -912,7 +912,8 @@ lge_rxeof(struct lge_softc *sc, int cnt) (rxsts & LGE_RXSTS_ISUDP && !(rxsts & LGE_RXSTS_UDPCSUMERR))) { m->m_pkthdr.csum_flags |= - CSUM_DATA_VALID|CSUM_PSEUDO_HDR; + CSUM_DATA_VALID|CSUM_PSEUDO_HDR| + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } diff --git a/sys/dev/netif/ndis/if_ndis.c b/sys/dev/netif/ndis/if_ndis.c index 44cb3fe69e..6bc953c357 100644 --- a/sys/dev/netif/ndis/if_ndis.c +++ b/sys/dev/netif/ndis/if_ndis.c @@ -30,7 +30,7 @@ * THE POSSIBILITY OF SUCH DAMAGE. * * $FreeBSD: src/sys/dev/if_ndis/if_ndis.c,v 1.65 2004/07/07 17:46:30 wpaul Exp $ - * $DragonFly: src/sys/dev/netif/ndis/if_ndis.c,v 1.20 2007/01/03 14:12:52 swildner Exp $ + * $DragonFly: src/sys/dev/netif/ndis/if_ndis.c,v 1.21 2007/08/14 13:30:35 sephe Exp $ */ #include @@ -845,7 +845,8 @@ ndis_rxeof(ndis_handle adapter, ndis_packet **packets, uint32_t pktcnt) (NDIS_RXCSUM_TCP_PASSED | NDIS_RXCSUM_UDP_PASSED)) { m0->m_pkthdr.csum_flags |= - CSUM_DATA_VALID|CSUM_PSEUDO_HDR; + CSUM_DATA_VALID|CSUM_PSEUDO_HDR| + CSUM_FRAG_NOT_CHECKED; m0->m_pkthdr.csum_data = 0xFFFF; } } diff --git a/sys/dev/netif/nfe/if_nfe.c b/sys/dev/netif/nfe/if_nfe.c index 54f385eddf..24a9098ae1 100644 --- a/sys/dev/netif/nfe/if_nfe.c +++ b/sys/dev/netif/nfe/if_nfe.c @@ -1,5 +1,5 @@ /* $OpenBSD: if_nfe.c,v 1.63 2006/06/17 18:00:43 brad Exp $ */ -/* $DragonFly: src/sys/dev/netif/nfe/if_nfe.c,v 1.15 2007/08/10 15:29:25 sephe Exp $ */ +/* $DragonFly: src/sys/dev/netif/nfe/if_nfe.c,v 1.16 2007/08/14 13:30:35 sephe Exp $ */ /* * Copyright (c) 2006 The DragonFly Project. All rights reserved. @@ -894,7 +894,8 @@ nfe_rxeof(struct nfe_softc *sc) if (flags & (NFE_RX_UDP_CSUMOK_V2 | NFE_RX_TCP_CSUMOK_V2)) { m->m_pkthdr.csum_flags |= CSUM_DATA_VALID | - CSUM_PSEUDO_HDR; + CSUM_PSEUDO_HDR | + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } } diff --git a/sys/dev/netif/nge/if_nge.c b/sys/dev/netif/nge/if_nge.c index 1c778ddb15..fb733cc746 100644 --- a/sys/dev/netif/nge/if_nge.c +++ b/sys/dev/netif/nge/if_nge.c @@ -31,7 +31,7 @@ * THE POSSIBILITY OF SUCH DAMAGE. * * $FreeBSD: src/sys/dev/nge/if_nge.c,v 1.13.2.13 2003/02/05 22:03:57 mbr Exp $ - * $DragonFly: src/sys/dev/netif/nge/if_nge.c,v 1.42 2007/03/26 12:13:58 sephe Exp $ + * $DragonFly: src/sys/dev/netif/nge/if_nge.c,v 1.43 2007/08/14 13:30:35 sephe Exp $ */ /* @@ -1274,7 +1274,8 @@ nge_rxeof(struct nge_softc *sc) (extsts & NGE_RXEXTSTS_UDPPKT && (extsts & NGE_RXEXTSTS_UDPCSUMERR) == 0)) { m->m_pkthdr.csum_flags |= - CSUM_DATA_VALID|CSUM_PSEUDO_HDR; + CSUM_DATA_VALID|CSUM_PSEUDO_HDR| + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } diff --git a/sys/dev/netif/re/if_re.c b/sys/dev/netif/re/if_re.c index 64c3411a6d..6bdb91d676 100644 --- a/sys/dev/netif/re/if_re.c +++ b/sys/dev/netif/re/if_re.c @@ -33,7 +33,7 @@ * THE POSSIBILITY OF SUCH DAMAGE. * * $FreeBSD: src/sys/dev/re/if_re.c,v 1.25 2004/06/09 14:34:01 naddy Exp $ - * $DragonFly: src/sys/dev/netif/re/if_re.c,v 1.35 2007/08/12 11:51:26 sephe Exp $ + * $DragonFly: src/sys/dev/netif/re/if_re.c,v 1.36 2007/08/14 13:30:35 sephe Exp $ */ /* @@ -1591,7 +1591,8 @@ re_rxeof(struct re_softc *sc) (RE_UDPPKT(rxstat) && (rxstat & RE_RDESC_STAT_UDPSUMBAD)) == 0) { m->m_pkthdr.csum_flags |= - CSUM_DATA_VALID|CSUM_PSEUDO_HDR; + CSUM_DATA_VALID|CSUM_PSEUDO_HDR| + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } } diff --git a/sys/dev/netif/stge/if_stge.c b/sys/dev/netif/stge/if_stge.c index 3abde193a8..5fcd1d2687 100644 --- a/sys/dev/netif/stge/if_stge.c +++ b/sys/dev/netif/stge/if_stge.c @@ -1,6 +1,6 @@ /* $NetBSD: if_stge.c,v 1.32 2005/12/11 12:22:49 christos Exp $ */ /* $FreeBSD: src/sys/dev/stge/if_stge.c,v 1.2 2006/08/12 01:21:36 yongari Exp $ */ -/* $DragonFly: src/sys/dev/netif/stge/if_stge.c,v 1.1 2006/11/16 13:43:55 sephe Exp $ */ +/* $DragonFly: src/sys/dev/netif/stge/if_stge.c,v 1.2 2007/08/14 13:30:35 sephe Exp $ */ /*- * Copyright (c) 2001 The NetBSD Foundation, Inc. @@ -1783,7 +1783,9 @@ stge_rxeof(struct stge_softc *sc, int count) ((status & RFD_UDPDetected) != 0 && (status & RFD_UDPError) == 0)) { m->m_pkthdr.csum_flags |= - (CSUM_DATA_VALID | CSUM_PSEUDO_HDR); + (CSUM_DATA_VALID | + CSUM_PSEUDO_HDR | + CSUM_FRAG_NOT_CHECKED); m->m_pkthdr.csum_data = 0xffff; } } diff --git a/sys/dev/netif/txp/if_txp.c b/sys/dev/netif/txp/if_txp.c index 7f82f6a38b..fe3e3357cb 100644 --- a/sys/dev/netif/txp/if_txp.c +++ b/sys/dev/netif/txp/if_txp.c @@ -1,6 +1,6 @@ /* $OpenBSD: if_txp.c,v 1.48 2001/06/27 06:34:50 kjc Exp $ */ /* $FreeBSD: src/sys/dev/txp/if_txp.c,v 1.4.2.4 2001/12/14 19:50:43 jlemon Exp $ */ -/* $DragonFly: src/sys/dev/netif/txp/if_txp.c,v 1.42 2007/03/26 12:13:58 sephe Exp $ */ +/* $DragonFly: src/sys/dev/netif/txp/if_txp.c,v 1.43 2007/08/14 13:30:35 sephe Exp $ */ /* * Copyright (c) 2001 @@ -717,7 +717,8 @@ txp_rx_reclaim(struct txp_softc *sc, struct txp_rx_ring *r) if ((rxd->rx_stat & RX_STAT_TCPCKSUMGOOD) || (rxd->rx_stat & RX_STAT_UDPCKSUMGOOD)) { m->m_pkthdr.csum_flags |= - CSUM_DATA_VALID|CSUM_PSEUDO_HDR; + CSUM_DATA_VALID|CSUM_PSEUDO_HDR| + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } diff --git a/sys/dev/netif/vge/if_vge.c b/sys/dev/netif/vge/if_vge.c index b95079d63f..a8a8661bd8 100644 --- a/sys/dev/netif/vge/if_vge.c +++ b/sys/dev/netif/vge/if_vge.c @@ -30,7 +30,7 @@ * THE POSSIBILITY OF SUCH DAMAGE. * * $FreeBSD: src/sys/dev/vge/if_vge.c,v 1.24 2006/02/14 12:44:56 glebius Exp $ - * $DragonFly: src/sys/dev/netif/vge/if_vge.c,v 1.4 2007/03/24 08:42:42 sephe Exp $ + * $DragonFly: src/sys/dev/netif/vge/if_vge.c,v 1.5 2007/08/14 13:30:35 sephe Exp $ */ /* @@ -1375,7 +1375,8 @@ vge_rxeof(struct vge_softc *sc, int count) if (rxctl & (VGE_RDCTL_TCPPKT|VGE_RDCTL_UDPPKT) && rxctl & VGE_RDCTL_PROTOCSUMOK) { m->m_pkthdr.csum_flags |= - CSUM_DATA_VALID|CSUM_PSEUDO_HDR; + CSUM_DATA_VALID|CSUM_PSEUDO_HDR| + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } } diff --git a/sys/dev/netif/xl/if_xl.c b/sys/dev/netif/xl/if_xl.c index 5c48d68552..af68415487 100644 --- a/sys/dev/netif/xl/if_xl.c +++ b/sys/dev/netif/xl/if_xl.c @@ -30,7 +30,7 @@ * THE POSSIBILITY OF SUCH DAMAGE. * * $FreeBSD: src/sys/pci/if_xl.c,v 1.72.2.28 2003/10/08 06:01:57 murray Exp $ - * $DragonFly: src/sys/dev/netif/xl/if_xl.c,v 1.48 2007/05/19 06:21:43 sephe Exp $ + * $DragonFly: src/sys/dev/netif/xl/if_xl.c,v 1.49 2007/08/14 13:30:35 sephe Exp $ */ /* @@ -2122,7 +2122,8 @@ again: (rxstat & XL_RXSTAT_UDPCKOK && !(rxstat & XL_RXSTAT_UDPCKERR))) { m->m_pkthdr.csum_flags |= - CSUM_DATA_VALID|CSUM_PSEUDO_HDR; + CSUM_DATA_VALID|CSUM_PSEUDO_HDR| + CSUM_FRAG_NOT_CHECKED; m->m_pkthdr.csum_data = 0xffff; } } diff --git a/sys/netinet/ip_input.c b/sys/netinet/ip_input.c index a3af94f380..709cbea7f9 100644 --- a/sys/netinet/ip_input.c +++ b/sys/netinet/ip_input.c @@ -65,7 +65,7 @@ * * @(#)ip_input.c 8.2 (Berkeley) 1/4/94 * $FreeBSD: src/sys/netinet/ip_input.c,v 1.130.2.52 2003/03/07 07:01:28 silby Exp $ - * $DragonFly: src/sys/netinet/ip_input.c,v 1.69 2007/08/11 18:57:34 dillon Exp $ + * $DragonFly: src/sys/netinet/ip_input.c,v 1.70 2007/08/14 13:30:35 sephe Exp $ */ #define _IP_VHL @@ -1130,6 +1130,16 @@ ip_reass(struct mbuf *m, struct ipq *fp, struct ipq *where, #endif /* + * If the hardware has not done csum over this fragment + * then csum_data is not valid at all. + */ + if ((m->m_pkthdr.csum_flags & (CSUM_FRAG_NOT_CHECKED | CSUM_DATA_VALID)) + == (CSUM_FRAG_NOT_CHECKED | CSUM_DATA_VALID)) { + m->m_pkthdr.csum_data = 0; + m->m_pkthdr.csum_flags &= ~(CSUM_DATA_VALID | CSUM_PSEUDO_HDR); + } + + /* * Presence of header sizes in mbufs * would confuse code below. */ diff --git a/sys/sys/mbuf.h b/sys/sys/mbuf.h index bbc5307368..ce78569d30 100644 --- a/sys/sys/mbuf.h +++ b/sys/sys/mbuf.h @@ -34,7 +34,7 @@ * * @(#)mbuf.h 8.5 (Berkeley) 2/19/95 * $FreeBSD: src/sys/sys/mbuf.h,v 1.44.2.17 2003/04/15 06:15:02 silby Exp $ - * $DragonFly: src/sys/sys/mbuf.h,v 1.39 2007/08/11 23:11:23 josepht Exp $ + * $DragonFly: src/sys/sys/mbuf.h,v 1.40 2007/08/14 13:30:35 sephe Exp $ */ #ifndef _SYS_MBUF_H_ @@ -220,6 +220,10 @@ struct mbuf { #define CSUM_IP_VALID 0x0200 /* ... the csum is valid */ #define CSUM_DATA_VALID 0x0400 /* csum_data field is valid */ #define CSUM_PSEUDO_HDR 0x0800 /* csum_data has pseudo hdr */ +#define CSUM_FRAG_NOT_CHECKED 0x1000 /* did _not_ csum fragment + * NB: This flag is only used + * by IP defragmenter. + */ #define CSUM_DELAY_DATA (CSUM_TCP | CSUM_UDP) #define CSUM_DELAY_IP (CSUM_IP) /* XXX add ipv6 here too? */ -- 2.11.4.GIT