Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 20 Apr 2017 09:05:53 +0000 (UTC)
From:      Kristof Provost <kp@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r317186 - in head/sys: netinet6 netpfil/pf
Message-ID:  <201704200905.v3K95rRT097206@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: kp
Date: Thu Apr 20 09:05:53 2017
New Revision: 317186
URL: https://svnweb.freebsd.org/changeset/base/317186

Log:
  pf: Fix possible incorrect IPv6 fragmentation
  
  When forwarding pf tracks the size of the largest fragment in a fragmented
  packet, and refragments based on this size.
  It failed to ensure that this size was a multiple of 8 (as is required for all
  but the last fragment), so it could end up generating incorrect fragments.
  
  For example, if we received an 8 byte and 12 byte fragment pf would emit a first
  fragment with 12 bytes of payload and the final fragment would claim to be at
  offset 8 (not 12).
  
  We now assert that the fragment size is a multiple of 8 in ip6_fragment(), so
  other users won't make the same mistake.
  
  Reported by:	Antonios Atlasis <aatlasis at secfu net>
  MFC after:	3 days

Modified:
  head/sys/netinet6/ip6_output.c
  head/sys/netpfil/pf/pf_norm.c

Modified: head/sys/netinet6/ip6_output.c
==============================================================================
--- head/sys/netinet6/ip6_output.c	Thu Apr 20 09:01:31 2017	(r317185)
+++ head/sys/netinet6/ip6_output.c	Thu Apr 20 09:05:53 2017	(r317186)
@@ -226,6 +226,8 @@ ip6_fragment(struct ifnet *ifp, struct m
 	int error;
 	int tlen = m0->m_pkthdr.len;
 
+	KASSERT(( mtu % 8 == 0), ("Fragment length must be a multiple of 8"));
+
 	m = m0;
 	ip6 = mtod(m, struct ip6_hdr *);
 	mnext = &m->m_nextpkt;

Modified: head/sys/netpfil/pf/pf_norm.c
==============================================================================
--- head/sys/netpfil/pf/pf_norm.c	Thu Apr 20 09:01:31 2017	(r317185)
+++ head/sys/netpfil/pf/pf_norm.c	Thu Apr 20 09:05:53 2017	(r317186)
@@ -762,6 +762,10 @@ pf_refragment6(struct ifnet *ifp, struct
 		hdr->ip6_nxt = IPPROTO_FRAGMENT;
 	}
 
+	/* The MTU must be a multiple of 8 bytes, or we risk doing the
+	 * fragmentation wrong. */
+	maxlen = maxlen & ~7;
+
 	/*
 	 * Maxlen may be less than 8 if there was only a single
 	 * fragment.  As it was fragmented before, add a fragment



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