Skip site navigation (1)Skip section navigation (2)
Date:      Tue, 9 Oct 2012 19:41:28 +0400
From:      Gleb Smirnoff <glebius@FreeBSD.org>
To:        net@FreeBSD.org
Subject:   [CFT/Review] net byte order for AF_INET
Message-ID:  <20121009154128.GU34622@FreeBSD.org>

next in thread | raw e-mail | index | archive | help

--Ycz6tD7Th1CMF4v7
Content-Type: text/plain; charset=koi8-r
Content-Disposition: inline

  Hello,

  this is a patch that switches entire IPv4 stack to network
byte order. That means, that at any layer any module should
expect IP header in network byte order. Any host byte order
values can be stored in local variables only and are never stored
into a packet itself.

  The new code brings clarity, since a developer doesn't need to
know which byte order should he/she switch a packet to when
passing it to a particular function in stack. Also, any new
function introduced should expect net byte order for a packet
supplied.

  The patch has been tested by me on amd64 and ray@ on mips.
TCP, UDP, ICMP, fragment reassembly and basic packet filtering
works okay.

More testing is desired, especially on boxes using some extensions
as packet filters with policy routing, running gre(4), ipsec(4),
divert(4), gif(4), multicast routing, stf(4), ng_ipfw(4), SCTP, etc.

Code reviewing also appreciated.

-- 
Totus tuus, Glebius.

--Ycz6tD7Th1CMF4v7
Content-Type: text/x-diff; charset=koi8-r
Content-Disposition: attachment; filename="IPv4.net-byte-order.diff"

Index: sys/netinet/tcp_input.c
===================================================================
--- sys/netinet/tcp_input.c	(revision 241370)
+++ sys/netinet/tcp_input.c	(working copy)
@@ -645,21 +645,19 @@
 		ip = mtod(m, struct ip *);
 		ipov = (struct ipovly *)ip;
 		th = (struct tcphdr *)((caddr_t)ip + off0);
-		tlen = ip->ip_len;
+		tlen = ntohs(ip->ip_len);
 
 		if (m->m_pkthdr.csum_flags & CSUM_DATA_VALID) {
 			if (m->m_pkthdr.csum_flags & CSUM_PSEUDO_HDR)
 				th->th_sum = m->m_pkthdr.csum_data;
 			else
 				th->th_sum = in_pseudo(ip->ip_src.s_addr,
-						ip->ip_dst.s_addr,
-						htonl(m->m_pkthdr.csum_data +
-							ip->ip_len +
-							IPPROTO_TCP));
+				    ip->ip_dst.s_addr,
+				    htonl(m->m_pkthdr.csum_data + tlen +
+				    IPPROTO_TCP));
 			th->th_sum ^= 0xffff;
 #ifdef TCPDEBUG
-			ipov->ih_len = (u_short)tlen;
-			ipov->ih_len = htons(ipov->ih_len);
+			ipov->ih_len = ip->ip_len;
 #endif
 		} else {
 			/*
@@ -667,8 +665,7 @@
 			 */
 			len = sizeof (struct ip) + tlen;
 			bzero(ipov->ih_x1, sizeof(ipov->ih_x1));
-			ipov->ih_len = (u_short)tlen;
-			ipov->ih_len = htons(ipov->ih_len);
+			ipov->ih_len = ip->ip_len;
 			th->th_sum = in_cksum(m, len);
 		}
 		if (th->th_sum) {
Index: sys/netinet/in.h
===================================================================
--- sys/netinet/in.h	(revision 241370)
+++ sys/netinet/in.h	(working copy)
@@ -741,33 +741,6 @@
 #define	satosin(sa)	((struct sockaddr_in *)(sa))
 #define	sintosa(sin)	((struct sockaddr *)(sin))
 #define	ifatoia(ifa)	((struct in_ifaddr *)(ifa))
-
-/*
- * Historically, BSD keeps ip_len and ip_off in host format
- * when doing layer 3 processing, and this often requires
- * to translate the format back and forth.
- * To make the process explicit, we define a couple of macros
- * that also take into account the fact that at some point
- * we may want to keep those fields always in net format.
- */
-
-#if (BYTE_ORDER == BIG_ENDIAN) || defined(HAVE_NET_IPLEN)
-#define SET_NET_IPLEN(p)	do {} while (0)
-#define SET_HOST_IPLEN(p)	do {} while (0)
-#else
-#define SET_NET_IPLEN(p)	do {		\
-	struct ip *h_ip = (p);			\
-	h_ip->ip_len = htons(h_ip->ip_len);	\
-	h_ip->ip_off = htons(h_ip->ip_off);	\
-	} while (0)
-
-#define SET_HOST_IPLEN(p)	do {		\
-	struct ip *h_ip = (p);			\
-	h_ip->ip_len = ntohs(h_ip->ip_len);	\
-	h_ip->ip_off = ntohs(h_ip->ip_off);	\
-	} while (0)
-#endif /* !HAVE_NET_IPLEN */
-
 #endif /* _KERNEL */
 
 /* INET6 stuff */
Index: sys/netinet/tcp_subr.c
===================================================================
--- sys/netinet/tcp_subr.c	(revision 241370)
+++ sys/netinet/tcp_subr.c	(working copy)
@@ -584,10 +584,10 @@
 #ifdef INET
 	{
 		tlen += sizeof (struct tcpiphdr);
-		ip->ip_len = tlen;
+		ip->ip_len = htons(tlen);
 		ip->ip_ttl = V_ip_defttl;
 		if (V_path_mtu_discovery)
-			ip->ip_off |= IP_DF;
+			ip->ip_off |= htons(IP_DF);
 	}
 #endif
 	m->m_len = tlen;
@@ -1398,12 +1398,11 @@
 					    /*
 					     * If no alternative MTU was
 					     * proposed, try the next smaller
-					     * one.  ip->ip_len has already
-					     * been swapped in icmp_input().
+					     * one.
 					     */
 					    if (!mtu)
-						mtu = ip_next_mtu(ip->ip_len,
-						 1);
+						mtu = ip_next_mtu(
+						 ntohs(ip->ip_len), 1);
 					    if (mtu < V_tcp_minmss
 						 + sizeof(struct tcpiphdr))
 						mtu = V_tcp_minmss
Index: sys/netinet/tcp_debug.c
===================================================================
--- sys/netinet/tcp_debug.c	(revision 241370)
+++ sys/netinet/tcp_debug.c	(working copy)
@@ -175,11 +175,10 @@
 #ifdef INET6
 		    isipv6 ? ntohs(((struct ip6_hdr *)ipgen)->ip6_plen) :
 #endif
-		    ((struct ip *)ipgen)->ip_len;
+		    ntohs(((struct ip *)ipgen)->ip_len);
 		if (act == TA_OUTPUT) {
 			seq = ntohl(seq);
 			ack = ntohl(ack);
-			len = ntohs((u_short)len);
 		}
 		if (act == TA_OUTPUT)
 			len -= sizeof (struct tcphdr);
Index: sys/netinet/tcp_syncache.c
===================================================================
--- sys/netinet/tcp_syncache.c	(revision 241370)
+++ sys/netinet/tcp_syncache.c	(working copy)
@@ -1395,7 +1395,7 @@
 		ip = mtod(m, struct ip *);
 		ip->ip_v = IPVERSION;
 		ip->ip_hl = sizeof(struct ip) >> 2;
-		ip->ip_len = tlen;
+		ip->ip_len = htons(tlen);
 		ip->ip_id = 0;
 		ip->ip_off = 0;
 		ip->ip_sum = 0;
@@ -1413,7 +1413,7 @@
 		 *	2) the SCF_UNREACH flag has been set
 		 */
 		if (V_path_mtu_discovery && ((sc->sc_flags & SCF_UNREACH) == 0))
-		       ip->ip_off |= IP_DF;
+		       ip->ip_off |= htons(IP_DF);
 
 		th = (struct tcphdr *)(ip + 1);
 	}
@@ -1473,7 +1473,7 @@
 			ip6->ip6_plen = htons(ntohs(ip6->ip6_plen) + optlen);
 		else
 #endif
-			ip->ip_len += optlen;
+			ip->ip_len = htons(ntohs(ip->ip_len) + optlen);
 	} else
 		optlen = 0;
 
Index: sys/netinet/sctp_input.c
===================================================================
--- sys/netinet/sctp_input.c	(revision 241370)
+++ sys/netinet/sctp_input.c	(working copy)
@@ -6038,7 +6038,7 @@
 	dst.sin_len = sizeof(struct sockaddr_in);
 	dst.sin_port = sh->dest_port;
 	dst.sin_addr = ip->ip_dst;
-	length = ip->ip_len + iphlen;
+	length = ntohs(ip->ip_len) + iphlen;
 	/* Validate mbuf chain length with IP payload length. */
 	if (SCTP_HEADER_LEN(m) != length) {
 		SCTPDBG(SCTP_DEBUG_INPUT1,
Index: sys/netinet/udp_usrreq.c
===================================================================
--- sys/netinet/udp_usrreq.c	(revision 241370)
+++ sys/netinet/udp_usrreq.c	(working copy)
@@ -338,7 +338,7 @@
 	struct udphdr *uh;
 	struct ifnet *ifp;
 	struct inpcb *inp;
-	int len;
+	uint16_t len, ip_len;
 	struct ip save_ip;
 	struct sockaddr_in udp_in;
 #ifdef IPFIREWALL_FORWARD
@@ -392,13 +392,13 @@
 	 * reflect UDP length, drop.
 	 */
 	len = ntohs((u_short)uh->uh_ulen);
-	if (ip->ip_len != len) {
-		if (len > ip->ip_len || len < sizeof(struct udphdr)) {
+	ip_len = ntohs(ip->ip_len);
+	if (ip_len != len) {
+		if (len > ip_len || len < sizeof(struct udphdr)) {
 			UDPSTAT_INC(udps_badlen);
 			goto badunlocked;
 		}
-		m_adj(m, len - ip->ip_len);
-		/* ip->ip_len = len; */
+		m_adj(m, len - ip_len);
 	}
 
 	/*
@@ -601,7 +601,7 @@
 		if (badport_bandlim(BANDLIM_ICMP_UNREACH) < 0)
 			goto badunlocked;
 		*ip = save_ip;
-		ip->ip_len += iphlen;
+		ip->ip_len = htons(ip_len + iphlen);
 		icmp_error(m, ICMP_UNREACH, ICMP_UNREACH_PORT, 0, 0);
 		return;
 	}
@@ -1206,7 +1206,7 @@
 		struct ip *ip;
 
 		ip = (struct ip *)&ui->ui_i;
-		ip->ip_off |= IP_DF;
+		ip->ip_off |= htons(IP_DF);
 	}
 
 	ipflags = 0;
@@ -1233,7 +1233,7 @@
 		m->m_pkthdr.csum_data = offsetof(struct udphdr, uh_sum);
 	} else
 		ui->ui_sum = 0;
-	((struct ip *)ui)->ip_len = sizeof (struct udpiphdr) + len;
+	((struct ip *)ui)->ip_len = htons(sizeof(struct udpiphdr) + len);
 	((struct ip *)ui)->ip_ttl = inp->inp_ip_ttl;	/* XXX */
 	((struct ip *)ui)->ip_tos = tos;		/* XXX */
 	UDPSTAT_INC(udps_opackets);
@@ -1383,7 +1383,7 @@
 	m_adj(m, skip);
 
 	ip = mtod(m, struct ip *);
-	ip->ip_len -= skip;
+	ip->ip_len = htons(ntohs(ip->ip_len) - skip);
 	ip->ip_p = IPPROTO_ESP;
 
 	/*
Index: sys/netinet/ip_carp.c
===================================================================
--- sys/netinet/ip_carp.c	(revision 241370)
+++ sys/netinet/ip_carp.c	(working copy)
@@ -783,9 +783,9 @@
 		ip->ip_v = IPVERSION;
 		ip->ip_hl = sizeof(*ip) >> 2;
 		ip->ip_tos = IPTOS_LOWDELAY;
-		ip->ip_len = len;
+		ip->ip_len = htons(len);
 		ip->ip_id = ip_newid();
-		ip->ip_off = IP_DF;
+		ip->ip_off = htons(IP_DF);
 		ip->ip_ttl = CARP_DFLTTL;
 		ip->ip_p = IPPROTO_CARP;
 		ip->ip_sum = 0;
Index: sys/netinet/raw_ip.c
===================================================================
--- sys/netinet/raw_ip.c	(revision 241370)
+++ sys/netinet/raw_ip.c	(working copy)
@@ -292,6 +292,7 @@
 	 * not modify the packet except for some
 	 * byte order swaps.
 	 */
+	ip->ip_len = ntohs(ip->ip_len);
 	ip->ip_len += off;
 
 	hash = INP_PCBHASH_RAW(proto, ip->ip_src.s_addr,
@@ -449,11 +450,11 @@
 		ip = mtod(m, struct ip *);
 		ip->ip_tos = inp->inp_ip_tos;
 		if (inp->inp_flags & INP_DONTFRAG)
-			ip->ip_off = IP_DF;
+			ip->ip_off = htons(IP_DF);
 		else
 			ip->ip_off = 0;
 		ip->ip_p = inp->inp_ip_p;
-		ip->ip_len = m->m_pkthdr.len;
+		ip->ip_len = htons(m->m_pkthdr.len);
 		ip->ip_src = inp->inp_laddr;
 		if (jailed(inp->inp_cred)) {
 			/*
@@ -495,8 +496,8 @@
 		 * and don't allow packet length sizes that will crash.
 		 */
 		if (((ip->ip_hl != (sizeof (*ip) >> 2)) && inp->inp_options)
-		    || (ip->ip_len > m->m_pkthdr.len)
-		    || (ip->ip_len < (ip->ip_hl << 2))) {
+		    || (ntohs(ip->ip_len) > m->m_pkthdr.len)
+		    || (ntohs(ip->ip_len) < (ip->ip_hl << 2))) {
 			INP_RUNLOCK(inp);
 			m_freem(m);
 			return (EINVAL);
Index: sys/netinet/ip_divert.c
===================================================================
--- sys/netinet/ip_divert.c	(revision 241370)
+++ sys/netinet/ip_divert.c	(working copy)
@@ -386,10 +386,6 @@
 				INP_RUNLOCK(inp);
 				goto cantsend;
 			}
-
-			/* Convert fields to host order for ip_output() */
-			ip->ip_len = ntohs(ip->ip_len);
-			ip->ip_off = ntohs(ip->ip_off);
 			break;
 #ifdef INET6
 		case IPV6_VERSION >> 4:
Index: sys/netinet/sctp_usrreq.c
===================================================================
--- sys/netinet/sctp_usrreq.c	(revision 241370)
+++ sys/netinet/sctp_usrreq.c	(working copy)
@@ -180,7 +180,7 @@
 		SCTP_TCB_UNLOCK(stcb);
 		return;
 	}
-	totsz = ip->ip_len;
+	totsz = ntohs(ip->ip_len);
 
 	nxtsz = ntohs(icmph->icmp_nextmtu);
 	if (nxtsz == 0) {
Index: sys/netinet/ip_output.c
===================================================================
--- sys/netinet/ip_output.c	(revision 241370)
+++ sys/netinet/ip_output.c	(working copy)
@@ -102,7 +102,6 @@
 /*
  * IP output.  The packet in mbuf chain m contains a skeletal IP
  * header (with len, off, ttl, proto, tos, src, dst).
- * ip_len and ip_off are in host format.
  * The mbuf chain containing the packet will be freed.
  * The mbuf opt, if present, will not be freed.
  * If route ro is present and has ro_rt initialized, route lookup would be
@@ -175,6 +174,8 @@
 			hlen = len; /* ip->ip_hl is updated above */
 	}
 	ip = mtod(m, struct ip *);
+	ip_len = ntohs(ip->ip_len);
+	ip_off = ntohs(ip->ip_off);
 
 	/*
 	 * Fill in IP header.  If we are not allowing fragmentation,
@@ -442,7 +443,7 @@
 	 * packet or packet fragments, unless ALTQ is enabled on the given
 	 * interface in which case packetdrop should be done by queueing.
 	 */
-	n = ip->ip_len / mtu + 1; /* how many fragments ? */
+	n = ip_len / mtu + 1; /* how many fragments ? */
 	if (
 #ifdef ALTQ
 	    (!ALTQ_IS_ENABLED(&ifp->if_snd)) &&
@@ -469,7 +470,7 @@
 			goto bad;
 		}
 		/* don't allow broadcast messages to be fragmented */
-		if (ip->ip_len > mtu) {
+		if (ip_len > mtu) {
 			error = EMSGSIZE;
 			goto bad;
 		}
@@ -502,12 +503,6 @@
 	hlen = ip->ip_hl << 2;
 #endif /* IPSEC */
 
-	/*
-	 * To network byte order. pfil(9) hooks and ip_fragment() expect this.
-	 */
-	ip->ip_len = htons(ip->ip_len);
-	ip->ip_off = htons(ip->ip_off);
-
 	/* Jump over all PFIL processing if hooks are not active. */
 	if (!PFIL_HOOKED(&V_inet_pfil_hook))
 		goto passout;
@@ -544,8 +539,6 @@
 		} else {
 			if (ia != NULL)
 				ifa_free(&ia->ia_ifa);
-			ip->ip_len = ntohs(ip->ip_len);
-			ip->ip_off = ntohs(ip->ip_off);
 			goto again;	/* Redo the routing table lookup. */
 		}
 	}
@@ -579,16 +572,11 @@
 		m_tag_delete(m, fwd_tag);
 		if (ia != NULL)
 			ifa_free(&ia->ia_ifa);
-		ip->ip_len = ntohs(ip->ip_len);
-		ip->ip_off = ntohs(ip->ip_off);
 		goto again;
 	}
 #endif /* IPFIREWALL_FORWARD */
 
 passout:
-	ip_len = ntohs(ip->ip_len);
-	ip_off = ntohs(ip->ip_off);
-
 	/* 127/8 must not appear on wire - RFC1122. */
 	if ((ntohl(ip->ip_dst.s_addr) >> IN_CLASSA_NSHIFT) == IN_LOOPBACKNET ||
 	    (ntohl(ip->ip_src.s_addr) >> IN_CLASSA_NSHIFT) == IN_LOOPBACKNET) {
@@ -1295,8 +1283,6 @@
  * calls the output routine of the loopback "driver", but with an interface
  * pointer that might NOT be a loopback interface -- evil, but easier than
  * replicating that code here.
- *
- * IP header in host byte order.
  */
 static void
 ip_mloopback(struct ifnet *ifp, struct mbuf *m, struct sockaddr_in *dst,
@@ -1326,8 +1312,6 @@
 		 * than the interface's MTU.  Can this possibly matter?
 		 */
 		ip = mtod(copym, struct ip *);
-		ip->ip_len = htons(ip->ip_len);
-		ip->ip_off = htons(ip->ip_off);
 		ip->ip_sum = 0;
 		ip->ip_sum = in_cksum(copym, hlen);
 #if 1 /* XXX */
Index: sys/netinet/in_gif.c
===================================================================
--- sys/netinet/in_gif.c	(revision 241370)
+++ sys/netinet/in_gif.c	(working copy)
@@ -192,7 +192,7 @@
 	iphdr.ip_p = proto;
 	/* version will be set in ip_output() */
 	iphdr.ip_ttl = V_ip_gif_ttl;
-	iphdr.ip_len = m->m_pkthdr.len + sizeof(struct ip);
+	iphdr.ip_len = htons(m->m_pkthdr.len + sizeof(struct ip));
 	ip_ecn_ingress((ifp->if_flags & IFF_LINK1) ? ECN_ALLOWED : ECN_NOCARE,
 		       &iphdr.ip_tos, &tos);
 
Index: sys/netinet/ip_options.c
===================================================================
--- sys/netinet/ip_options.c	(revision 241370)
+++ sys/netinet/ip_options.c	(working copy)
@@ -494,7 +494,7 @@
 	unsigned optlen;
 
 	optlen = opt->m_len - sizeof(p->ipopt_dst);
-	if (optlen + ip->ip_len > IP_MAXPACKET) {
+	if (optlen + ntohs(ip->ip_len) > IP_MAXPACKET) {
 		*phlen = 0;
 		return (m);		/* XXX should fail */
 	}
@@ -527,7 +527,7 @@
 	*phlen = sizeof(struct ip) + optlen;
 	ip->ip_v = IPVERSION;
 	ip->ip_hl = *phlen >> 2;
-	ip->ip_len += optlen;
+	ip->ip_len = htons(ntohs(ip->ip_len) + optlen);
 	return (m);
 }
 
Index: sys/netinet/tcp_timewait.c
===================================================================
--- sys/netinet/tcp_timewait.c	(revision 241370)
+++ sys/netinet/tcp_timewait.c	(working copy)
@@ -593,9 +593,9 @@
 		m->m_pkthdr.csum_flags = CSUM_TCP;
 		th->th_sum = in_pseudo(ip->ip_src.s_addr, ip->ip_dst.s_addr,
 		    htons(sizeof(struct tcphdr) + optlen + IPPROTO_TCP));
-		ip->ip_len = m->m_pkthdr.len;
+		ip->ip_len = htons(m->m_pkthdr.len);
 		if (V_path_mtu_discovery)
-			ip->ip_off |= IP_DF;
+			ip->ip_off |= htons(IP_DF);
 		error = ip_output(m, inp->inp_options, NULL,
 		    ((tw->tw_so_options & SO_DONTROUTE) ? IP_ROUTETOIF : 0),
 		    NULL, inp);
Index: sys/netinet/tcp_output.c
===================================================================
--- sys/netinet/tcp_output.c	(revision 241370)
+++ sys/netinet/tcp_output.c	(working copy)
@@ -1239,7 +1239,7 @@
 	struct route ro;
 
 	bzero(&ro, sizeof(ro));
-	ip->ip_len = m->m_pkthdr.len;
+	ip->ip_len = htons(m->m_pkthdr.len);
 #ifdef INET6
 	if (tp->t_inpcb->inp_vflag & INP_IPV6PROTO)
 		ip->ip_ttl = in6_selecthlim(tp->t_inpcb, NULL);
@@ -1253,7 +1253,7 @@
 	 * NB: Don't set DF on small MTU/MSS to have a safe fallback.
 	 */
 	if (V_path_mtu_discovery && tp->t_maxopd > V_tcp_minmss)
-		ip->ip_off |= IP_DF;
+		ip->ip_off |= htons(IP_DF);
 
 	error = ip_output(m, tp->t_inpcb->inp_options, &ro,
 	    ((so->so_options & SO_DONTROUTE) ? IP_ROUTETOIF : 0), 0,
Index: sys/netinet/sctputil.c
===================================================================
--- sys/netinet/sctputil.c	(revision 241370)
+++ sys/netinet/sctputil.c	(working copy)
@@ -6821,7 +6821,7 @@
 	switch (iph->ip_v) {
 #ifdef INET
 	case IPVERSION:
-		iph->ip_len -= sizeof(struct udphdr);
+		iph->ip_len = ntohs(htons(iph->ip_len) - sizeof(struct udphdr));
 		sctp_input_with_port(m, off, port);
 		break;
 #endif
Index: sys/netinet/ip_input.c
===================================================================
--- sys/netinet/ip_input.c	(revision 241370)
+++ sys/netinet/ip_input.c	(working copy)
@@ -390,9 +390,8 @@
 		m->m_flags &= ~M_FASTFWD_OURS;
 		/* Set up some basics that will be used later. */
 		ip = mtod(m, struct ip *);
-		ip->ip_len = ntohs(ip->ip_len);
-		ip->ip_off = ntohs(ip->ip_off);
 		hlen = ip->ip_hl << 2;
+		ip_len = ntohs(ip->ip_len);
 		goto ours;
 	}
 
@@ -513,8 +512,6 @@
 #ifdef IPFIREWALL_FORWARD
 	if (m->m_flags & M_FASTFWD_OURS) {
 		m->m_flags &= ~M_FASTFWD_OURS;
-		ip->ip_len = ntohs(ip->ip_len);
-		ip->ip_off = ntohs(ip->ip_off);
 		goto ours;
 	}
 	if ((dchg = (m_tag_find(m, PACKET_TAG_IPFORWARD, NULL) != NULL)) != 0) {
@@ -523,20 +520,12 @@
 		 * packets originally destined to us to some other directly
 		 * connected host.
 		 */
-		ip->ip_len = ntohs(ip->ip_len);
-		ip->ip_off = ntohs(ip->ip_off);
 		ip_forward(m, dchg);
 		return;
 	}
 #endif /* IPFIREWALL_FORWARD */
 
 passin:
-	/*
-	 *  From now and up to output pfil(9) processing in ip_output()
-	 *  the header is in host byte order.
-	 */
-	ip->ip_len = ntohs(ip->ip_len);
-	ip->ip_off = ntohs(ip->ip_off);
 
 	/*
 	 * Process options and, if not destined for us,
@@ -732,20 +721,21 @@
 	 * Attempt reassembly; if it succeeds, proceed.
 	 * ip_reass() will return a different mbuf.
 	 */
-	if (ip->ip_off & (IP_MF | IP_OFFMASK)) {
+	if (ip->ip_off & htons(IP_MF | IP_OFFMASK)) {
 		m = ip_reass(m);
 		if (m == NULL)
 			return;
 		ip = mtod(m, struct ip *);
 		/* Get the header length of the reassembled packet */
 		hlen = ip->ip_hl << 2;
+		ip_len = ntohs(ip->ip_len);
 	}
 
 	/*
 	 * Further protocols expect the packet length to be w/o the
 	 * IP header.
 	 */
-	ip->ip_len -= hlen;
+	ip->ip_len = htons(ip_len - hlen);
 
 #ifdef IPSEC
 	/*
@@ -914,22 +904,21 @@
 	 * Adjust ip_len to not reflect header,
 	 * convert offset of this to bytes.
 	 */
-	ip->ip_len -= hlen;
-	if (ip->ip_off & IP_MF) {
+	ip->ip_len = htons(ntohs(ip->ip_len) - hlen);
+	if (ip->ip_off & htons(IP_MF)) {
 		/*
 		 * Make sure that fragments have a data length
 		 * that's a non-zero multiple of 8 bytes.
 		 */
-		if (ip->ip_len == 0 || (ip->ip_len & 0x7) != 0) {
+		if (ip->ip_len == 0 || (ip->ip_len & htons(0x7)) != 0) {
 			IPSTAT_INC(ips_toosmall); /* XXX */
 			goto dropfrag;
 		}
 		m->m_flags |= M_FRAG;
 	} else
 		m->m_flags &= ~M_FRAG;
-	ip->ip_off <<= 3;
+	ip->ip_off = htons(ntohs(ip->ip_off) << 3);
 
-
 	/*
 	 * Attempt reassembly; if it succeeds, proceed.
 	 * ip_reass() will return a different mbuf.
@@ -1000,7 +989,7 @@
 	 * Find a segment which begins after this one does.
 	 */
 	for (p = NULL, q = fp->ipq_frags; q; p = q, q = q->m_nextpkt)
-		if (GETIP(q)->ip_off > ip->ip_off)
+		if (ntohs(GETIP(q)->ip_off) > ntohs(ip->ip_off))
 			break;
 
 	/*
@@ -1013,14 +1002,15 @@
 	 * segment, then it's checksum is invalidated.
 	 */
 	if (p) {
-		i = GETIP(p)->ip_off + GETIP(p)->ip_len - ip->ip_off;
+		i = ntohs(GETIP(p)->ip_off) + ntohs(GETIP(p)->ip_len) -
+		    ntohs(ip->ip_off);
 		if (i > 0) {
-			if (i >= ip->ip_len)
+			if (i >= ntohs(ip->ip_len))
 				goto dropfrag;
 			m_adj(m, i);
 			m->m_pkthdr.csum_flags = 0;
-			ip->ip_off += i;
-			ip->ip_len -= i;
+			ip->ip_off = htons(ntohs(ip->ip_off) + i);
+			ip->ip_len = htons(ntohs(ip->ip_len) - i);
 		}
 		m->m_nextpkt = p->m_nextpkt;
 		p->m_nextpkt = m;
@@ -1033,12 +1023,13 @@
 	 * While we overlap succeeding segments trim them or,
 	 * if they are completely covered, dequeue them.
 	 */
-	for (; q != NULL && ip->ip_off + ip->ip_len > GETIP(q)->ip_off;
-	     q = nq) {
-		i = (ip->ip_off + ip->ip_len) - GETIP(q)->ip_off;
-		if (i < GETIP(q)->ip_len) {
-			GETIP(q)->ip_len -= i;
-			GETIP(q)->ip_off += i;
+	for (; q != NULL && ntohs(ip->ip_off) + ntohs(ip->ip_len) >
+	    ntohs(GETIP(q)->ip_off); q = nq) {
+		i = (ntohs(ip->ip_off) + ntohs(ip->ip_len)) -
+		    ntohs(GETIP(q)->ip_off);
+		if (i < ntohs(GETIP(q)->ip_len)) {
+			GETIP(q)->ip_len = htons(ntohs(GETIP(q)->ip_len) - i);
+			GETIP(q)->ip_off = htons(ntohs(GETIP(q)->ip_off) + i);
 			m_adj(q, i);
 			q->m_pkthdr.csum_flags = 0;
 			break;
@@ -1062,14 +1053,14 @@
 	 */
 	next = 0;
 	for (p = NULL, q = fp->ipq_frags; q; p = q, q = q->m_nextpkt) {
-		if (GETIP(q)->ip_off != next) {
+		if (ntohs(GETIP(q)->ip_off) != next) {
 			if (fp->ipq_nfrags > V_maxfragsperpacket) {
 				IPSTAT_ADD(ips_fragdropped, fp->ipq_nfrags);
 				ip_freef(head, fp);
 			}
 			goto done;
 		}
-		next += GETIP(q)->ip_len;
+		next += ntohs(GETIP(q)->ip_len);
 	}
 	/* Make sure the last packet didn't have the IP_MF flag */
 	if (p->m_flags & M_FRAG) {
@@ -1125,7 +1116,7 @@
 	 * packet;  dequeue and discard fragment reassembly header.
 	 * Make header visible.
 	 */
-	ip->ip_len = (ip->ip_hl << 2) + next;
+	ip->ip_len = htons((ip->ip_hl << 2) + next);
 	ip->ip_src = fp->ipq_src;
 	ip->ip_dst = fp->ipq_dst;
 	TAILQ_REMOVE(head, fp, ipq_list);
@@ -1365,8 +1356,6 @@
  *
  * The srcrt parameter indicates whether the packet is being forwarded
  * via a source route.
- *
- * IP header in host byte order.
  */
 void
 ip_forward(struct mbuf *m, int srcrt)
@@ -1436,7 +1425,7 @@
 		mcopy = NULL;
 	}
 	if (mcopy != NULL) {
-		mcopy->m_len = min(ip->ip_len, M_TRAILINGSPACE(mcopy));
+		mcopy->m_len = min(ntohs(ip->ip_len), M_TRAILINGSPACE(mcopy));
 		mcopy->m_pkthdr.len = mcopy->m_len;
 		m_copydata(m, 0, mcopy->m_len, mtod(mcopy, caddr_t));
 	}
@@ -1564,7 +1553,7 @@
 			if (ia != NULL)
 				mtu = ia->ia_ifp->if_mtu;
 			else
-				mtu = ip_next_mtu(ip->ip_len, 0);
+				mtu = ip_next_mtu(ntohs(ip->ip_len), 0);
 		}
 		IPSTAT_INC(ips_cantfrag);
 		break;
Index: sys/netinet/siftr.c
===================================================================
--- sys/netinet/siftr.c	(revision 241370)
+++ sys/netinet/siftr.c	(working copy)
@@ -952,7 +952,8 @@
 			 * the mbuf cluster "at" at offset "offset" bytes from
 			 * the beginning of the "at" mbuf's data pointer.
 			 */
-			th->th_sum = in_cksum_skip(*m, ip->ip_len, ip_hl);
+			th->th_sum = in_cksum_skip(*m, ntohs(ip->ip_len),
+			    ip_hl);
 		}
 
 		/*
Index: sys/netinet/ip_icmp.c
===================================================================
--- sys/netinet/ip_icmp.c	(revision 241370)
+++ sys/netinet/ip_icmp.c	(working copy)
@@ -200,7 +200,7 @@
 	 */
 	if (n->m_flags & M_DECRYPTED)
 		goto freeit;
-	if (oip->ip_off & ~(IP_MF|IP_DF))
+	if (oip->ip_off & htons(~(IP_MF|IP_DF)))
 		goto freeit;
 	if (n->m_flags & (M_BCAST|M_MCAST))
 		goto freeit;
@@ -234,16 +234,17 @@
 		tcphlen = th->th_off << 2;
 		if (tcphlen < sizeof(struct tcphdr))
 			goto freeit;
-		if (oip->ip_len < oiphlen + tcphlen)
+		if (ntohs(oip->ip_len) < oiphlen + tcphlen)
 			goto freeit;
 		if (oiphlen + tcphlen > n->m_len && n->m_next == NULL)
 			goto stdreply;
 		if (n->m_len < oiphlen + tcphlen && 
 		    ((n = m_pullup(n, oiphlen + tcphlen)) == NULL))
 			goto freeit;
-		icmpelen = max(tcphlen, min(V_icmp_quotelen, oip->ip_len - oiphlen));
+		icmpelen = max(tcphlen, min(V_icmp_quotelen,
+		    ntohs(oip->ip_len) - oiphlen));
 	} else
-stdreply:	icmpelen = max(8, min(V_icmp_quotelen, oip->ip_len - oiphlen));
+stdreply:	icmpelen = max(8, min(V_icmp_quotelen, ntohs(oip->ip_len) - oiphlen));
 
 	icmplen = min(oiphlen + icmpelen, nlen);
 	if (icmplen < sizeof(struct ip))
@@ -293,8 +294,6 @@
 	 */
 	m_copydata(n, 0, icmplen, (caddr_t)&icp->icmp_ip);
 	nip = &icp->icmp_ip;
-	nip->ip_len = htons(nip->ip_len);
-	nip->ip_off = htons(nip->ip_off);
 
 	/*
 	 * Set up ICMP message mbuf and copy old IP header (without options
@@ -309,7 +308,7 @@
 	m->m_pkthdr.rcvif = n->m_pkthdr.rcvif;
 	nip = mtod(m, struct ip *);
 	bcopy((caddr_t)oip, (caddr_t)nip, sizeof(struct ip));
-	nip->ip_len = m->m_len;
+	nip->ip_len = htons(m->m_len);
 	nip->ip_v = IPVERSION;
 	nip->ip_hl = 5;
 	nip->ip_p = IPPROTO_ICMP;
@@ -331,7 +330,7 @@
 	struct ip *ip = mtod(m, struct ip *);
 	struct sockaddr_in icmpsrc, icmpdst, icmpgw;
 	int hlen = off;
-	int icmplen = ip->ip_len;
+	int icmplen = ntohs(ip->ip_len);
 	int i, code;
 	void (*ctlfunc)(int, struct sockaddr *, void *);
 	int fibnum;
@@ -472,7 +471,6 @@
 			ICMPSTAT_INC(icps_badlen);
 			goto freeit;
 		}
-		icp->icmp_ip.ip_len = ntohs(icp->icmp_ip.ip_len);
 		/* Discard ICMP's in response to multicast packets */
 		if (IN_MULTICAST(ntohl(icp->icmp_ip.ip_dst.s_addr)))
 			goto badcode;
@@ -565,7 +563,8 @@
 		}
 		ifa_free(&ia->ia_ifa);
 reflect:
-		ip->ip_len += hlen;	/* since ip_input deducts this */
+		/* Since ip_input() deducts this. */
+		ip->ip_len = htons(ntohs(ip->ip_len) + hlen);
 		ICMPSTAT_INC(icps_reflect);
 		ICMPSTAT_INC(icps_outhist[icp->icmp_type]);
 		icmp_reflect(m);
@@ -835,7 +834,7 @@
 		 * Now strip out original options by copying rest of first
 		 * mbuf's data back, and adjust the IP length.
 		 */
-		ip->ip_len -= optlen;
+		ip->ip_len = htons(ntohs(ip->ip_len) - optlen);
 		ip->ip_v = IPVERSION;
 		ip->ip_hl = 5;
 		m->m_len -= optlen;
@@ -869,7 +868,7 @@
 	m->m_len -= hlen;
 	icp = mtod(m, struct icmp *);
 	icp->icmp_cksum = 0;
-	icp->icmp_cksum = in_cksum(m, ip->ip_len - hlen);
+	icp->icmp_cksum = in_cksum(m, ntohs(ip->ip_len) - hlen);
 	m->m_data -= hlen;
 	m->m_len += hlen;
 	m->m_pkthdr.rcvif = (struct ifnet *)0;
Index: sys/netinet/ip_gre.c
===================================================================
--- sys/netinet/ip_gre.c	(revision 241370)
+++ sys/netinet/ip_gre.c	(working copy)
@@ -274,12 +274,10 @@
 
 	/*
 	 * On FreeBSD, rip_input() supplies us with ip->ip_len
-	 * already converted into host byteorder and also decreases
-	 * it by the lengh of IP header, however, ip_input() expects
-	 * that this field is in the original format (network byteorder
-	 * and full size of IP packet), so that adjust accordingly.
+	 * decreased by the lengh of IP header, however, ip_input()
+	 * expects it to be full size of IP packet, so adjust accordingly.
 	 */
-	ip->ip_len = htons(ip->ip_len + sizeof(struct ip) - msiz);
+	ip->ip_len = htons(ntohs(ip->ip_len) + sizeof(struct ip) - msiz);
 
 	ip->ip_sum = 0;
 	ip->ip_sum = in_cksum(m, (ip->ip_hl << 2));
Index: sys/netinet/ip_ipsec.c
===================================================================
--- sys/netinet/ip_ipsec.c	(revision 241370)
+++ sys/netinet/ip_ipsec.c	(working copy)
@@ -264,7 +264,6 @@
 {
 #ifdef IPSEC
 	struct secpolicy *sp = NULL;
-	struct ip *ip = mtod(*m, struct ip *);
 	struct tdb_ident *tdbi;
 	struct m_tag *mtag;
 	int s;
@@ -332,9 +331,6 @@
 			}
 		}
 
-		ip->ip_len = htons(ip->ip_len);
-		ip->ip_off = htons(ip->ip_off);
-
 		/*
 		 * Do delayed checksums now because we send before
 		 * this is done in the normal processing path.
@@ -345,6 +341,8 @@
 		}
 #ifdef SCTP
 		if ((*m)->m_pkthdr.csum_flags & CSUM_SCTP) {
+			struct ip *ip = mtod(*m, struct ip *);
+
 			sctp_delayed_cksum(*m, (uint32_t)(ip->ip_hl << 2));
 			(*m)->m_pkthdr.csum_flags &= ~CSUM_SCTP;
 		}
@@ -359,8 +357,6 @@
 			 * IPsec processing and return without error.
 			 */
 			*error = 0;
-			ip->ip_len = ntohs(ip->ip_len);
-			ip->ip_off = ntohs(ip->ip_off);
 			goto done;
 		}
 		/*
Index: sys/netinet/ip_mroute.c
===================================================================
--- sys/netinet/ip_mroute.c	(revision 241370)
+++ sys/netinet/ip_mroute.c	(working copy)
@@ -1493,7 +1493,7 @@
 {
     struct ip  *ip = mtod(m, struct ip *);
     vifi_t vifi;
-    int plen = ip->ip_len;
+    int plen = ntohs(ip->ip_len);
 
     VIF_LOCK_ASSERT();
 
@@ -2376,10 +2376,7 @@
 
     /* Take care of delayed checksums */
     if (m->m_pkthdr.csum_flags & CSUM_DELAY_DATA) {
-	/* XXX: in_delayed_cksum() expects net byte order */
-	ip->ip_len = htons(ip->ip_len);
 	in_delayed_cksum(m);
-	ip->ip_len = ntohs(ip->ip_len);
 	m->m_pkthdr.csum_flags &= ~CSUM_DELAY_DATA;
     }
 
@@ -2401,10 +2398,8 @@
     /* Compute the MTU after the PIM Register encapsulation */
     mtu = 0xffff - sizeof(pim_encap_iphdr) - sizeof(pim_encap_pimhdr);
 
-    if (ip->ip_len <= mtu) {
+    if (ntohs(ip->ip_len) <= mtu) {
 	/* Turn the IP header into a valid one */
-	ip->ip_len = htons(ip->ip_len);
-	ip->ip_off = htons(ip->ip_off);
 	ip->ip_sum = 0;
 	ip->ip_sum = in_cksum(mb_copy, ip->ip_hl << 2);
     } else {
@@ -2509,7 +2504,8 @@
     ip_outer = mtod(mb_first, struct ip *);
     *ip_outer = pim_encap_iphdr;
     ip_outer->ip_id = ip_newid();
-    ip_outer->ip_len = len + sizeof(pim_encap_iphdr) + sizeof(pim_encap_pimhdr);
+    ip_outer->ip_len = htons(len + sizeof(pim_encap_iphdr) +
+	sizeof(pim_encap_pimhdr));
     ip_outer->ip_src = V_viftable[vifi].v_lcl_addr;
     ip_outer->ip_dst = rt->mfc_rp;
     /*
@@ -2517,8 +2513,8 @@
      * IP_DF bit.
      */
     ip_outer->ip_tos = ip->ip_tos;
-    if (ntohs(ip->ip_off) & IP_DF)
-	ip_outer->ip_off |= IP_DF;
+    if (ip->ip_off & htons(IP_DF))
+	ip_outer->ip_off |= htons(IP_DF);
     pimhdr = (struct pim_encap_pimhdr *)((caddr_t)ip_outer
 					 + sizeof(pim_encap_iphdr));
     *pimhdr = pim_encap_pimhdr;
@@ -2571,7 +2567,7 @@
     struct ip *ip = mtod(m, struct ip *);
     struct pim *pim;
     int minlen;
-    int datalen = ip->ip_len;
+    int datalen = ntohs(ip->ip_len);
     int ip_tos;
     int iphlen = off;
 
Index: sys/netinet/sctp_output.c
===================================================================
--- sys/netinet/sctp_output.c	(revision 241370)
+++ sys/netinet/sctp_output.c	(working copy)
@@ -3980,7 +3980,7 @@
 				tos_value |= sctp_get_ect(stcb);
 			}
 			if ((nofragment_flag) && (port == 0)) {
-				ip->ip_off = IP_DF;
+				ip->ip_off = htons(IP_DF);
 			} else
 				ip->ip_off = 0;
 
@@ -3988,7 +3988,7 @@
 			ip->ip_id = ip_newid();
 
 			ip->ip_ttl = inp->ip_inp.inp.inp_ip_ttl;
-			ip->ip_len = packet_length;
+			ip->ip_len = htons(packet_length);
 			ip->ip_tos = tos_value;
 			if (port) {
 				ip->ip_p = IPPROTO_UDP;
@@ -10991,7 +10991,7 @@
 				udp->uh_sum = 0;
 			}
 		}
-		ip->ip_len = len;
+		ip->ip_len = htons(len);
 		if (port) {
 #if defined(SCTP_WITH_NO_CSUM)
 			SCTP_STAT_INCR(sctps_sendnocrc);
Index: sys/netinet/igmp.c
===================================================================
--- sys/netinet/igmp.c	(revision 241370)
+++ sys/netinet/igmp.c	(working copy)
@@ -1442,7 +1442,7 @@
 
 	ip = mtod(m, struct ip *);
 	iphlen = off;
-	igmplen = ip->ip_len;
+	igmplen = ntohs(ip->ip_len);
 
 	/*
 	 * Validate lengths.
@@ -2225,7 +2225,7 @@
 
 	ip = mtod(m, struct ip *);
 	ip->ip_tos = 0;
-	ip->ip_len = sizeof(struct ip) + sizeof(struct igmp);
+	ip->ip_len = htons(sizeof(struct ip) + sizeof(struct igmp));
 	ip->ip_off = 0;
 	ip->ip_p = IPPROTO_IGMP;
 	ip->ip_src.s_addr = INADDR_ANY;
@@ -3522,8 +3522,8 @@
 
 	ip = mtod(m, struct ip *);
 	ip->ip_tos = IPTOS_PREC_INTERNETCONTROL;
-	ip->ip_len = hdrlen + igmpreclen;
-	ip->ip_off = IP_DF;
+	ip->ip_len = htons(hdrlen + igmpreclen);
+	ip->ip_off = htons(IP_DF);
 	ip->ip_p = IPPROTO_IGMP;
 	ip->ip_sum = 0;
 
Index: sys/netinet6/ip6_ipsec.c
===================================================================
--- sys/netinet6/ip6_ipsec.c	(revision 241370)
+++ sys/netinet6/ip6_ipsec.c	(working copy)
@@ -295,15 +295,9 @@
 		 */
 #ifdef INET
 		if ((*m)->m_pkthdr.csum_flags & CSUM_DELAY_DATA) {
-			struct ip *ip;
-
 			ipseclog((LOG_DEBUG,
 			    "%s: we do not support IPv4 over IPv6", __func__));
-			/* XXX: in_delayed_cksum() expects net byte order */
-			ip = mtod(*m, struct ip *);
-			ip->ip_len = htons(ip->ip_len);
 			in_delayed_cksum(*m);
-			ip->ip_len = ntohs(ip->ip_len);
 			(*m)->m_pkthdr.csum_flags &= ~CSUM_DELAY_DATA;
 		}
 #endif
Index: sys/netpfil/pf/pf.c
===================================================================
--- sys/netpfil/pf/pf.c	(revision 241370)
+++ sys/netpfil/pf/pf.c	(working copy)
@@ -2252,8 +2252,8 @@
 		h->ip_v = 4;
 		h->ip_hl = sizeof(*h) >> 2;
 		h->ip_tos = IPTOS_LOWDELAY;
-		h->ip_off = V_path_mtu_discovery ? IP_DF : 0;
-		h->ip_len = len;
+		h->ip_off = V_path_mtu_discovery ? htons(IP_DF) : 0;
+		h->ip_len = htons(len);
 		h->ip_ttl = ttl ? ttl : V_ip_defttl;
 		h->ip_sum = 0;
 
@@ -2316,17 +2316,8 @@
 	switch (af) {
 #ifdef INET
 	case AF_INET:
-	    {
-		struct ip *ip;
-
-		/* icmp_error() expects host byte ordering */
-		ip = mtod(m0, struct ip *);
-		NTOHS(ip->ip_len);
-		NTOHS(ip->ip_off);
-
 		pfse->pfse_type = PFSE_ICMP;
 		break;
-	    }
 #endif /* INET */
 #ifdef INET6
 	case AF_INET6:
Index: sys/netpfil/pf/if_pfsync.c
===================================================================
--- sys/netpfil/pf/if_pfsync.c	(revision 241370)
+++ sys/netpfil/pf/if_pfsync.c	(working copy)
@@ -1384,7 +1384,7 @@
 		ip->ip_hl = sizeof(sc->sc_template) >> 2;
 		ip->ip_tos = IPTOS_LOWDELAY;
 		/* len and id are set later. */
-		ip->ip_off = IP_DF;
+		ip->ip_off = htons(IP_DF);
 		ip->ip_ttl = PFSYNC_DFLTTL;
 		ip->ip_p = IPPROTO_PFSYNC;
 		ip->ip_src.s_addr = INADDR_ANY;
@@ -1522,7 +1522,7 @@
 	bcopy(&sc->sc_template, ip, sizeof(*ip));
 	offset = sizeof(*ip);
 
-	ip->ip_len = m->m_pkthdr.len;
+	ip->ip_len = htons(m->m_pkthdr.len);
 	ip->ip_id = htons(ip_randomid());
 
 	/* build the pfsync header */
Index: sys/netpfil/ipfw/ip_fw_dynamic.c
===================================================================
--- sys/netpfil/ipfw/ip_fw_dynamic.c	(revision 241370)
+++ sys/netpfil/ipfw/ip_fw_dynamic.c	(working copy)
@@ -1017,8 +1017,7 @@
 		h->ip_hl = sizeof(*h) >> 2;
 		h->ip_tos = IPTOS_LOWDELAY;
 		h->ip_off = 0;
-		/* ip_len must be in host format for ip_output */
-		h->ip_len = len;
+		h->ip_len = htons(len);
 		h->ip_ttl = V_ip_defttl;
 		h->ip_sum = 0;
 		break;
Index: sys/netpfil/ipfw/ip_fw_pfil.c
===================================================================
--- sys/netpfil/ipfw/ip_fw_pfil.c	(revision 241370)
+++ sys/netpfil/ipfw/ip_fw_pfil.c	(working copy)
@@ -431,7 +431,6 @@
 		int hlen;
 		struct mbuf *reass;
 
-		SET_HOST_IPLEN(ip); /* ip_reass wants host order */
 		reass = ip_reass(clone); /* Reassemble packet. */
 		if (reass == NULL)
 			return 0; /* not an error */
@@ -442,7 +441,6 @@
 		 */
 		ip = mtod(reass, struct ip *);
 		hlen = ip->ip_hl << 2;
-		SET_NET_IPLEN(ip);
 		ip->ip_sum = 0;
 		if (hlen == sizeof(struct ip))
 			ip->ip_sum = in_cksum_hdr(ip);
Index: sys/netpfil/ipfw/ip_dn_io.c
===================================================================
--- sys/netpfil/ipfw/ip_dn_io.c	(revision 241370)
+++ sys/netpfil/ipfw/ip_dn_io.c	(working copy)
@@ -658,13 +658,10 @@
 
 		switch (dst) {
 		case DIR_OUT:
-			SET_HOST_IPLEN(mtod(m, struct ip *));
 			ip_output(m, NULL, NULL, IP_FORWARDING, NULL, NULL);
 			break ;
 
 		case DIR_IN :
-			/* put header in network format for ip_input() */
-			//SET_NET_IPLEN(mtod(m, struct ip *));
 			netisr_dispatch(NETISR_IP, m);
 			break;
 
Index: sys/netpfil/ipfw/ip_fw2.c
===================================================================
--- sys/netpfil/ipfw/ip_fw2.c	(revision 241370)
+++ sys/netpfil/ipfw/ip_fw2.c	(working copy)
@@ -627,8 +627,6 @@
 		m_adj(m, args->L3offset);
 #endif
 	if (code != ICMP_REJECT_RST) { /* Send an ICMP unreach */
-		/* We need the IP header in host order for icmp_error(). */
-		SET_HOST_IPLEN(ip);
 		icmp_error(args->m, ICMP_UNREACH, code, 0L, 0);
 	} else if (args->f_id.proto == IPPROTO_TCP) {
 		struct tcphdr *const tcp =
@@ -2418,11 +2416,6 @@
 				/* if not fragmented, go to next rule */
 				if ((ip_off & (IP_MF | IP_OFFMASK)) == 0)
 				    break;
-				/* 
-				 * ip_reass() expects len & off in host
-				 * byte order.
-				 */
-				SET_HOST_IPLEN(ip);
 
 				args->m = m = ip_reass(m);
 
@@ -2436,7 +2429,6 @@
 
 				    ip = mtod(m, struct ip *);
 				    hlen = ip->ip_hl << 2;
-				    SET_NET_IPLEN(ip);
 				    ip->ip_sum = 0;
 				    if (hlen == sizeof(struct ip))
 					ip->ip_sum = in_cksum_hdr(ip);
Index: sys/netipsec/ipsec.c
===================================================================
--- sys/netipsec/ipsec.c	(revision 241370)
+++ sys/netipsec/ipsec.c	(working copy)
@@ -597,10 +597,9 @@
 	IPSEC_ASSERT(m != NULL, ("null mbuf"));
 	IPSEC_ASSERT(m->m_pkthdr.len >= sizeof(struct ip),("packet too short"));
 
-	/* NB: ip_input() flips it into host endian. XXX Need more checking. */
 	if (m->m_len >= sizeof (struct ip)) {
 		struct ip *ip = mtod(m, struct ip *);
-		if (ip->ip_off & (IP_MF | IP_OFFMASK))
+		if (ip->ip_off & htons(IP_MF | IP_OFFMASK))
 			goto done;
 #ifdef _IP_VHL
 		off = _IP_VHL_HL(ip->ip_vhl) << 2;
@@ -612,7 +611,7 @@
 		struct ip ih;
 
 		m_copydata(m, 0, sizeof (struct ip), (caddr_t) &ih);
-		if (ih.ip_off & (IP_MF | IP_OFFMASK))
+		if (ih.ip_off & htons(IP_MF | IP_OFFMASK))
 			goto done;
 #ifdef _IP_VHL
 		off = _IP_VHL_HL(ih.ip_vhl) << 2;
Index: sys/netgraph/ng_ipfw.c
===================================================================
--- sys/netgraph/ng_ipfw.c	(revision 241370)
+++ sys/netgraph/ng_ipfw.c	(working copy)
@@ -265,7 +265,6 @@
 		switch (ip->ip_v) {
 #ifdef INET
 		case IPVERSION:
-			SET_HOST_IPLEN(ip);
 			return (ip_output(m, NULL, NULL, IP_FORWARDING,
 			    NULL, NULL));
 #endif
Index: sys/net/if_stf.c
===================================================================
--- sys/net/if_stf.c	(revision 241370)
+++ sys/net/if_stf.c	(working copy)
@@ -523,7 +523,7 @@
 	bcopy(&in4, &ip->ip_dst, sizeof(ip->ip_dst));
 	ip->ip_p = IPPROTO_IPV6;
 	ip->ip_ttl = ip_stf_ttl;
-	ip->ip_len = m->m_pkthdr.len;	/*host order*/
+	ip->ip_len = htons(m->m_pkthdr.len);
 	if (ifp->if_flags & IFF_LINK1)
 		ip_ecn_ingress(ECN_ALLOWED, &ip->ip_tos, &tos);
 	else
Index: sys/net/if_gre.c
===================================================================
--- sys/net/if_gre.c	(revision 241370)
+++ sys/net/if_gre.c	(working copy)
@@ -356,7 +356,7 @@
 			 * RFC2004 specifies that fragmented diagrams shouldn't
 			 * be encapsulated.
 			 */
-			if (ip->ip_off & (IP_MF | IP_OFFMASK)) {
+			if (ip->ip_off & htons(IP_MF | IP_OFFMASK)) {
 				_IF_DROP(&ifp->if_snd);
 				m_freem(m);
 				error = EINVAL;    /* is there better errno? */
@@ -410,7 +410,7 @@
 			}
 			ip = mtod(m, struct ip *);
 			memcpy((caddr_t)(ip + 1), &mob_h, (unsigned)msiz);
-			ip->ip_len = ntohs(ip->ip_len) + msiz;
+			ip->ip_len = htons(ntohs(ip->ip_len) + msiz);
 		} else {  /* AF_INET */
 			_IF_DROP(&ifp->if_snd);
 			m_freem(m);

--Ycz6tD7Th1CMF4v7--



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20121009154128.GU34622>