Do not use the interface pointer after if_put(). Rename ipip_input_gif()
authorbluhm <bluhm@openbsd.org>
Tue, 20 Jun 2017 11:12:13 +0000 (11:12 +0000)
committerbluhm <bluhm@openbsd.org>
Tue, 20 Jun 2017 11:12:13 +0000 (11:12 +0000)
to ipip_input_if() and always pass the ifp.  Only dump the packet
to bpf if we are called with a gif(4) interface.
OK mpi@

sys/net/if_gif.c
sys/netinet/ip_ipip.c
sys/netinet/ip_ipip.h

index 051cbcf..3b46296 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: if_gif.c,v 1.97 2017/06/19 17:58:49 bluhm Exp $       */
+/*     $OpenBSD: if_gif.c,v 1.98 2017/06/20 11:12:13 bluhm Exp $       */
 /*     $KAME: if_gif.c,v 1.43 2001/02/20 08:51:07 itojun Exp $ */
 
 /*
@@ -751,7 +751,7 @@ in_gif_input(struct mbuf **mp, int *offp, int proto, int af)
                gifp->if_ipackets++;
                gifp->if_ibytes += m->m_pkthdr.len;
                /* We have a configured GIF */
-               return ipip_input_gif(mp, offp, proto, af, gifp);
+               return ipip_input_if(mp, offp, proto, af, gifp);
        }
 
 inject:
@@ -876,7 +876,7 @@ int in6_gif_input(struct mbuf **mp, int *offp, int proto, int af)
                m->m_pkthdr.ph_ifidx = gifp->if_index;
                gifp->if_ipackets++;
                gifp->if_ibytes += m->m_pkthdr.len;
-               return ipip_input_gif(mp, offp, proto, af, gifp);
+               return ipip_input_if(mp, offp, proto, af, gifp);
        }
 
 inject:
index 214d4c3..a7de325 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: ip_ipip.c,v 1.84 2017/06/19 17:58:49 bluhm Exp $ */
+/*     $OpenBSD: ip_ipip.c,v 1.85 2017/06/20 11:12:13 bluhm Exp $ */
 /*
  * The authors of this code are John Ioannidis (ji@tla.org),
  * Angelos D. Keromytis (kermit@csd.uch.gr) and
@@ -39,6 +39,8 @@
  * IP-inside-IP processing
  */
 
+#include "bpfilter.h"
+#include "gif.h"
 #include "pf.h"
 
 #include <sys/param.h>
@@ -48,6 +50,7 @@
 #include <sys/sysctl.h>
 
 #include <net/if.h>
+#include <net/if_types.h>
 #include <net/if_var.h>
 #include <net/route.h>
 #include <net/netisr.h>
@@ -64,8 +67,6 @@
 #include <netinet/ip_mroute.h>
 #endif
 
-#include "bpfilter.h"
-
 #if NPF > 0
 #include <net/pfvar.h>
 #endif
@@ -91,11 +92,13 @@ ipip_init(void)
 }
 
 /*
- * Really only a wrapper for ipip_input_gif(), for use with pr_input.
+ * Really only a wrapper for ipip_input_if(), for use with pr_input.
  */
 int
-ipip_input(struct mbuf **mp, int *offp, int proto, int af)
+ipip_input(struct mbuf **mp, int *offp, int nxt, int af)
 {
+       struct ifnet *ifp;
+
        /* If we do not accept IP-in-IP explicitly, drop.  */
        if (!ipip_allow && ((*mp)->m_flags & (M_AUTH|M_CONF)) == 0) {
                DPRINTF(("%s: dropped due to policy\n", __func__));
@@ -104,7 +107,15 @@ ipip_input(struct mbuf **mp, int *offp, int proto, int af)
                return IPPROTO_DONE;
        }
 
-       return ipip_input_gif(mp, offp, proto, af, NULL);
+       ifp = if_get((*mp)->m_pkthdr.ph_ifidx);
+       if (ifp == NULL) {
+               m_freemp(mp);
+               return IPPROTO_DONE;
+       }
+       nxt = ipip_input_if(mp, offp, nxt, af, ifp);
+       if_put(ifp);
+
+       return nxt;
 }
 
 /*
@@ -116,12 +127,11 @@ ipip_input(struct mbuf **mp, int *offp, int proto, int af)
  */
 
 int
-ipip_input_gif(struct mbuf **mp, int *offp, int proto, int oaf,
-    struct ifnet *gifp)
+ipip_input_if(struct mbuf **mp, int *offp, int proto, int oaf,
+    struct ifnet *ifp)
 {
        struct mbuf *m = *mp;
        struct sockaddr_in *sin;
-       struct ifnet *ifp;
        struct ip *ip;
 #ifdef INET6
        struct sockaddr_in6 *sin6;
@@ -224,8 +234,7 @@ ipip_input_gif(struct mbuf **mp, int *offp, int proto, int oaf,
                hlen = ip->ip_hl << 2;
                if (m->m_pkthdr.len < hlen) {
                        ipipstat_inc(ipips_hdrops);
-                       m_freem(m);
-                       return IPPROTO_DONE;
+                       goto bad;
                }
                itos = ip->ip_tos;
                mode = m->m_flags & (M_AUTH|M_CONF) ?
@@ -258,14 +267,10 @@ ipip_input_gif(struct mbuf **mp, int *offp, int proto, int oaf,
        }
 
        /* Check for local address spoofing. */
-       ifp = if_get(m->m_pkthdr.ph_ifidx);
-       if (((ifp == NULL) || !(ifp->if_flags & IFF_LOOPBACK)) &&
-           ipip_allow != 2) {
+       if (!(ifp->if_flags & IFF_LOOPBACK) && ipip_allow != 2) {
                struct sockaddr_storage ss;
                struct rtentry *rt;
 
-               if_put(ifp);
-
                memset(&ss, 0, sizeof(ss));
 
                if (ip) {
@@ -288,16 +293,14 @@ ipip_input_gif(struct mbuf **mp, int *offp, int proto, int oaf,
                        goto bad;
                }
                rtfree(rt);
-       } else {
-               if_put(ifp);
        }
 
        /* Statistics */
        ipipstat_add(ipips_ibytes, m->m_pkthdr.len - hlen);
 
-#if NBPFILTER > 0
-       if (gifp && gifp->if_bpf)
-               bpf_mtap_af(gifp->if_bpf, iaf, m, BPF_DIRECTION_IN);
+#if NBPFILTER > 0 && NGIF > 0
+       if (ifp->if_type == IFT_GIF && ifp->if_bpf != NULL)
+               bpf_mtap_af(ifp->if_bpf, iaf, m, BPF_DIRECTION_IN);
 #endif
 #if NPF > 0
        pf_pkt_addr_changed(m);
index 2b8dc91..3ff6d1e 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: ip_ipip.h,v 1.9 2017/05/18 10:56:45 bluhm Exp $ */
+/*     $OpenBSD: ip_ipip.h,v 1.10 2017/06/20 11:12:13 bluhm Exp $ */
 /*
  * The authors of this code are John Ioannidis (ji@tla.org),
  * Angelos D. Keromytis (kermit@csd.uch.gr) and
@@ -106,7 +106,7 @@ ipipstat_add(enum ipipstat_counters c, uint64_t v)
 
 void   ipip_init(void);
 int    ipip_input(struct mbuf **, int *, int, int);
-int    ipip_input_gif(struct mbuf **, int *, int, int, struct ifnet *);
+int    ipip_input_if(struct mbuf **, int *, int, int, struct ifnet *);
 int    ipip_output(struct mbuf *, struct tdb *, struct mbuf **, int, int);
 int    ipip_sysctl(int *, u_int, void *, size_t *, void *, size_t);