Module Name: src Committed By: msaitoh Date: Wed Jun 18 09:34:27 UTC 2014
Modified Files: src/sys/dist/ipf/netinet [netbsd-6-1]: ip_fil_netbsd.c src/sys/net [netbsd-6-1]: if_ethersubr.c if_loop.c if_vlan.c src/sys/netinet [netbsd-6-1]: if_arp.c ip_carp.c src/sys/netinet6 [netbsd-6-1]: ip6_flow.c nd6.c src/sys/rump/librump/rumpkern [netbsd-6-1]: klock.c Log Message: Pull up following revision(s) (requested by bouyer in ticket #1067): sys/dist/ipf/netinet/ip_fil_netbsd.c 1.9 via patch sys/net/if_ethersubr.c 1.197 via patch sys/net/if_loop.c 1.77 via patch sys/net/if_vlan.c 1.70 via patch sys/netinet/if_arp.c 1.158 sys/netinet/ip_carp.c 1.54 via patch sys/netinet6/ip6_flow.c 1.23 via patch sys/netinet6/nd6.c 1.150 via patch sys/rump/librump/rumpkern/klock.c 1.4 Make sure *(if_output)() is called with KERNEL_LOCK held to avoid mbuf leak. See http://mail-index.netbsd.org/tech-net/2014/04/09/msg004511.html for details. For netinet6, the problem report, fix and test were done by njoly@ on current-users@ To generate a diff of this commit: cvs rdiff -u -r1.61.2.1 -r1.61.2.1.2.1 \ src/sys/dist/ipf/netinet/ip_fil_netbsd.c cvs rdiff -u -r1.188.8.3 -r1.188.8.3.2.1 src/sys/net/if_ethersubr.c cvs rdiff -u -r1.75 -r1.75.18.1 src/sys/net/if_loop.c cvs rdiff -u -r1.69 -r1.69.22.1 src/sys/net/if_vlan.c cvs rdiff -u -r1.154 -r1.154.16.1 src/sys/netinet/if_arp.c cvs rdiff -u -r1.47.4.1 -r1.47.4.1.6.1 src/sys/netinet/ip_carp.c cvs rdiff -u -r1.19.2.1 -r1.19.2.1.2.1 src/sys/netinet6/ip6_flow.c cvs rdiff -u -r1.141.8.2 -r1.141.8.3 src/sys/netinet6/nd6.c cvs rdiff -u -r1.3 -r1.3.20.1 src/sys/rump/librump/rumpkern/klock.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/dist/ipf/netinet/ip_fil_netbsd.c diff -u src/sys/dist/ipf/netinet/ip_fil_netbsd.c:1.61.2.1 src/sys/dist/ipf/netinet/ip_fil_netbsd.c:1.61.2.1.2.1 --- src/sys/dist/ipf/netinet/ip_fil_netbsd.c:1.61.2.1 Fri Feb 8 19:54:45 2013 +++ src/sys/dist/ipf/netinet/ip_fil_netbsd.c Wed Jun 18 09:34:26 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: ip_fil_netbsd.c,v 1.61.2.1 2013/02/08 19:54:45 riz Exp $ */ +/* $NetBSD: ip_fil_netbsd.c,v 1.61.2.1.2.1 2014/06/18 09:34:26 msaitoh Exp $ */ /* * Copyright (C) 1993-2003 by Darren Reed. @@ -8,7 +8,7 @@ #if !defined(lint) #if defined(__NetBSD__) #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: ip_fil_netbsd.c,v 1.61.2.1 2013/02/08 19:54:45 riz Exp $"); +__KERNEL_RCSID(0, "$NetBSD: ip_fil_netbsd.c,v 1.61.2.1.2.1 2014/06/18 09:34:26 msaitoh Exp $"); #else static const char sccsid[] = "@(#)ip_fil.c 2.41 6/5/96 (C) 1993-2000 Darren Reed"; static const char rcsid[] = "@(#)Id: ip_fil_netbsd.c,v 2.55.2.67 2009/12/19 05:41:08 darrenr Exp"; @@ -1377,11 +1377,13 @@ fr_fastroute(mb_t *m0, mb_t **mpp, fr_in if (!ip->ip_sum) ip->ip_sum = in_cksum(m, hlen); # endif /* M_CSUM_IPv4 */ + KERNEL_LOCK(1, NULL); # if __NetBSD_Version__ >= 499001100 error = (*ifp->if_output)(ifp, m, dst, rt); # else error = (*ifp->if_output)(ifp, m, (struct sockaddr *)dst, rt); # endif + KERNEL_UNLOCK_ONE(NULL); if (i) { ip->ip_len = ntohs(ip->ip_len); ip->ip_off = ntohs(ip->ip_off); @@ -1471,6 +1473,7 @@ sendorfree: for (m = m0; m; m = m0) { m0 = m->m_act; m->m_act = 0; + KERNEL_LOCK(1, NULL); # if __NetBSD_Version__ >= 499001100 if (error == 0) error = (*ifp->if_output)(ifp, m, dst, rt); @@ -1483,6 +1486,7 @@ sendorfree: else FREE_MB_T(m); # endif + KERNEL_UNLOCK_ONE(NULL); } } done: Index: src/sys/net/if_ethersubr.c diff -u src/sys/net/if_ethersubr.c:1.188.8.3 src/sys/net/if_ethersubr.c:1.188.8.3.2.1 --- src/sys/net/if_ethersubr.c:1.188.8.3 Wed Oct 31 16:07:46 2012 +++ src/sys/net/if_ethersubr.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: if_ethersubr.c,v 1.188.8.3 2012/10/31 16:07:46 riz Exp $ */ +/* $NetBSD: if_ethersubr.c,v 1.188.8.3.2.1 2014/06/18 09:34:27 msaitoh Exp $ */ /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. @@ -61,7 +61,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: if_ethersubr.c,v 1.188.8.3 2012/10/31 16:07:46 riz Exp $"); +__KERNEL_RCSID(0, "$NetBSD: if_ethersubr.c,v 1.188.8.3.2.1 2014/06/18 09:34:27 msaitoh Exp $"); #include "opt_inet.h" #include "opt_atalk.h" @@ -222,6 +222,8 @@ ether_output(struct ifnet * const ifp0, struct at_ifaddr *aa; #endif /* NETATALK */ + KASSERT(KERNEL_LOCKED_P()); + #ifdef MBUFTRACE m_claimm(m, ifp->if_mowner); #endif Index: src/sys/net/if_loop.c diff -u src/sys/net/if_loop.c:1.75 src/sys/net/if_loop.c:1.75.18.1 --- src/sys/net/if_loop.c:1.75 Mon Jun 20 09:43:27 2011 +++ src/sys/net/if_loop.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: if_loop.c,v 1.75 2011/06/20 09:43:27 kefren Exp $ */ +/* $NetBSD: if_loop.c,v 1.75.18.1 2014/06/18 09:34:27 msaitoh Exp $ */ /* * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. @@ -65,7 +65,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: if_loop.c,v 1.75 2011/06/20 09:43:27 kefren Exp $"); +__KERNEL_RCSID(0, "$NetBSD: if_loop.c,v 1.75.18.1 2014/06/18 09:34:27 msaitoh Exp $"); #include "opt_inet.h" #include "opt_atalk.h" @@ -222,6 +222,8 @@ looutput(struct ifnet *ifp, struct mbuf int csum_flags; MCLAIM(m, ifp->if_mowner); + KASSERT(KERNEL_LOCKED_P()); + if ((m->m_flags & M_PKTHDR) == 0) panic("looutput: no header mbuf"); if (ifp->if_flags & IFF_LOOPBACK) Index: src/sys/net/if_vlan.c diff -u src/sys/net/if_vlan.c:1.69 src/sys/net/if_vlan.c:1.69.22.1 --- src/sys/net/if_vlan.c:1.69 Wed Oct 19 22:07:09 2011 +++ src/sys/net/if_vlan.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: if_vlan.c,v 1.69 2011/10/19 22:07:09 dyoung Exp $ */ +/* $NetBSD: if_vlan.c,v 1.69.22.1 2014/06/18 09:34:27 msaitoh Exp $ */ /*- * Copyright (c) 2000, 2001 The NetBSD Foundation, Inc. @@ -78,7 +78,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: if_vlan.c,v 1.69 2011/10/19 22:07:09 dyoung Exp $"); +__KERNEL_RCSID(0, "$NetBSD: if_vlan.c,v 1.69.22.1 2014/06/18 09:34:27 msaitoh Exp $"); #include "opt_inet.h" @@ -681,6 +681,8 @@ vlan_start(struct ifnet *ifp) int error; ALTQ_DECL(struct altq_pktattr pktattr;) + KASSERT(KERNEL_LOCKED_P()); + ifp->if_flags |= IFF_OACTIVE; for (;;) { Index: src/sys/netinet/if_arp.c diff -u src/sys/netinet/if_arp.c:1.154 src/sys/netinet/if_arp.c:1.154.16.1 --- src/sys/netinet/if_arp.c:1.154 Mon Jan 2 22:17:11 2012 +++ src/sys/netinet/if_arp.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: if_arp.c,v 1.154 2012/01/02 22:17:11 liamjfoy Exp $ */ +/* $NetBSD: if_arp.c,v 1.154.16.1 2014/06/18 09:34:27 msaitoh Exp $ */ /*- * Copyright (c) 1998, 2000, 2008 The NetBSD Foundation, Inc. @@ -68,7 +68,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: if_arp.c,v 1.154 2012/01/02 22:17:11 liamjfoy Exp $"); +__KERNEL_RCSID(0, "$NetBSD: if_arp.c,v 1.154.16.1 2014/06/18 09:34:27 msaitoh Exp $"); #include "opt_ddb.h" #include "opt_inet.h" @@ -1480,8 +1480,10 @@ revarprequest(struct ifnet *ifp) sa.sa_family = AF_ARP; sa.sa_len = 2; m->m_flags |= M_BCAST; - (*ifp->if_output)(ifp, m, &sa, NULL); + KERNEL_LOCK(1, NULL); + (*ifp->if_output)(ifp, m, &sa, NULL); + KERNEL_UNLOCK_ONE(NULL); } /* Index: src/sys/netinet/ip_carp.c diff -u src/sys/netinet/ip_carp.c:1.47.4.1 src/sys/netinet/ip_carp.c:1.47.4.1.6.1 --- src/sys/netinet/ip_carp.c:1.47.4.1 Mon Apr 2 18:25:35 2012 +++ src/sys/netinet/ip_carp.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: ip_carp.c,v 1.47.4.1 2012/04/02 18:25:35 riz Exp $ */ +/* $NetBSD: ip_carp.c,v 1.47.4.1.6.1 2014/06/18 09:34:27 msaitoh Exp $ */ /* $OpenBSD: ip_carp.c,v 1.113 2005/11/04 08:11:54 mcbride Exp $ */ /* @@ -30,7 +30,7 @@ #include "opt_inet.h" #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: ip_carp.c,v 1.47.4.1 2012/04/02 18:25:35 riz Exp $"); +__KERNEL_RCSID(0, "$NetBSD: ip_carp.c,v 1.47.4.1.6.1 2014/06/18 09:34:27 msaitoh Exp $"); /* * TODO: @@ -347,6 +347,7 @@ carp_setroute(struct carp_softc *sc, int struct ifaddr *ifa; int s; + KERNEL_LOCK(1, NULL); s = splsoftnet(); IFADDR_FOREACH(ifa, &sc->sc_if) { switch (ifa->ifa_addr->sa_family) { @@ -444,6 +445,7 @@ carp_setroute(struct carp_softc *sc, int } } splx(s); + KERNEL_UNLOCK_ONE(NULL); } /* @@ -844,6 +846,7 @@ carpdetach(struct carp_softc *sc) carp_setrun(sc, 0); carp_multicast_cleanup(sc); + KERNEL_LOCK(1, NULL); s = splnet(); if (sc->sc_carpdev != NULL) { /* XXX linkstatehook removal */ @@ -857,6 +860,7 @@ carpdetach(struct carp_softc *sc) } sc->sc_carpdev = NULL; splx(s); + KERNEL_UNLOCK_ONE(NULL); } /* Detach an interface from the carp. */ @@ -923,6 +927,7 @@ carp_send_ad(void *v) struct ifaddr *ifa; struct sockaddr sa; + KERNEL_LOCK(1, NULL); s = splsoftnet(); advbase = advskew = 0; /* Sssssh compiler */ @@ -1123,6 +1128,7 @@ carp_send_ad(void *v) retry_later: splx(s); + KERNEL_UNLOCK_ONE(NULL); if (advbase != 255 || advskew != 255) callout_schedule(&sc->sc_ad_tmo, tvtohz(&tv)); } @@ -1137,8 +1143,10 @@ carp_send_arp(struct carp_softc *sc) { struct ifaddr *ifa; struct in_addr *in; - int s = splsoftnet(); + int s; + KERNEL_LOCK(1, NULL); + s = splsoftnet(); IFADDR_FOREACH(ifa, &sc->sc_if) { if (ifa->ifa_addr->sa_family != AF_INET) @@ -1148,6 +1156,7 @@ carp_send_arp(struct carp_softc *sc) arprequest(sc->sc_carpdev, in, in, CLLADDR(sc->sc_if.if_sadl)); } splx(s); + KERNEL_UNLOCK_ONE(NULL); } #ifdef INET6 @@ -1157,7 +1166,10 @@ carp_send_na(struct carp_softc *sc) struct ifaddr *ifa; struct in6_addr *in6; static struct in6_addr mcast = IN6ADDR_LINKLOCAL_ALLNODES_INIT; - int s = splsoftnet(); + int s; + + KERNEL_LOCK(1, NULL); + s = splsoftnet(); IFADDR_FOREACH(ifa, &sc->sc_if) { @@ -1169,6 +1181,7 @@ carp_send_na(struct carp_softc *sc) ND_NA_FLAG_OVERRIDE, 1, NULL); } splx(s); + KERNEL_UNLOCK_ONE(NULL); } #endif /* INET6 */ @@ -1573,10 +1586,12 @@ carp_set_ifp(struct carp_softc *sc, stru if (sc->sc_naddrs || sc->sc_naddrs6) sc->sc_if.if_flags |= IFF_UP; carp_set_enaddr(sc); + KERNEL_LOCK(1, NULL); s = splnet(); /* XXX linkstatehooks establish */ carp_carpdev_state(ifp); splx(s); + KERNEL_UNLOCK_ONE(NULL); } else { carpdetach(sc); sc->sc_if.if_flags &= ~(IFF_UP|IFF_RUNNING); @@ -2035,6 +2050,7 @@ carp_output(struct ifnet *ifp, struct mb struct rtentry *rt) { struct carp_softc *sc = ((struct carp_softc *)ifp->if_softc); + KASSERT(KERNEL_LOCKED_P()); if (sc->sc_carpdev != NULL && sc->sc_state == MASTER) { return (sc->sc_carpdev->if_output(ifp, m, sa, rt)); Index: src/sys/netinet6/ip6_flow.c diff -u src/sys/netinet6/ip6_flow.c:1.19.2.1 src/sys/netinet6/ip6_flow.c:1.19.2.1.2.1 --- src/sys/netinet6/ip6_flow.c:1.19.2.1 Wed Oct 31 16:07:46 2012 +++ src/sys/netinet6/ip6_flow.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: ip6_flow.c,v 1.19.2.1 2012/10/31 16:07:46 riz Exp $ */ +/* $NetBSD: ip6_flow.c,v 1.19.2.1.2.1 2014/06/18 09:34:27 msaitoh Exp $ */ /*- * Copyright (c) 2007 The NetBSD Foundation, Inc. @@ -38,7 +38,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: ip6_flow.c,v 1.19.2.1 2012/10/31 16:07:46 riz Exp $"); +__KERNEL_RCSID(0, "$NetBSD: ip6_flow.c,v 1.19.2.1.2.1 2014/06/18 09:34:27 msaitoh Exp $"); #include <sys/param.h> #include <sys/systm.h> @@ -303,13 +303,14 @@ ip6flow_fastforward(struct mbuf **mp) ip6f->ip6f_uses++; + KERNEL_LOCK(1, NULL); /* Send on its way - straight to the interface output routine. */ if ((error = (*rt->rt_ifp->if_output)(rt->rt_ifp, m, dst, rt)) != 0) { ip6f->ip6f_dropped++; } else { ip6f->ip6f_forwarded++; } - + KERNEL_UNLOCK_ONE(NULL); return 1; } Index: src/sys/netinet6/nd6.c diff -u src/sys/netinet6/nd6.c:1.141.8.2 src/sys/netinet6/nd6.c:1.141.8.3 --- src/sys/netinet6/nd6.c:1.141.8.2 Tue Dec 17 20:47:49 2013 +++ src/sys/netinet6/nd6.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: nd6.c,v 1.141.8.2 2013/12/17 20:47:49 bouyer Exp $ */ +/* $NetBSD: nd6.c,v 1.141.8.3 2014/06/18 09:34:27 msaitoh Exp $ */ /* $KAME: nd6.c,v 1.279 2002/06/08 11:16:51 itojun Exp $ */ /* @@ -31,7 +31,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: nd6.c,v 1.141.8.2 2013/12/17 20:47:49 bouyer Exp $"); +__KERNEL_RCSID(0, "$NetBSD: nd6.c,v 1.141.8.3 2014/06/18 09:34:27 msaitoh Exp $"); #include "opt_ipsec.h" @@ -2177,9 +2177,13 @@ nd6_output(struct ifnet *ifp, struct ifn /* clean ipsec history once it goes out of the node */ ipsec_delaux(m); #endif + KERNEL_LOCK(1, NULL); if ((ifp->if_flags & IFF_LOOPBACK) != 0) - return (*ifp->if_output)(origifp, m, sin6tocsa(dst), rt); - return (*ifp->if_output)(ifp, m, sin6tocsa(dst), rt); + error = (*ifp->if_output)(origifp, m, sin6tocsa(dst), rt); + else + error = (*ifp->if_output)(ifp, m, sin6tocsa(dst), rt); + KERNEL_UNLOCK_ONE(NULL); + return error; bad: if (m != NULL) Index: src/sys/rump/librump/rumpkern/klock.c diff -u src/sys/rump/librump/rumpkern/klock.c:1.3 src/sys/rump/librump/rumpkern/klock.c:1.3.20.1 --- src/sys/rump/librump/rumpkern/klock.c:1.3 Wed Dec 1 14:59:38 2010 +++ src/sys/rump/librump/rumpkern/klock.c Wed Jun 18 09:34:27 2014 @@ -1,4 +1,4 @@ -/* $NetBSD: klock.c,v 1.3 2010/12/01 14:59:38 pooka Exp $ */ +/* $NetBSD: klock.c,v 1.3.20.1 2014/06/18 09:34:27 msaitoh Exp $ */ /* * Copyright (c) 2007-2010 Antti Kantee. All Rights Reserved. @@ -29,7 +29,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: klock.c,v 1.3 2010/12/01 14:59:38 pooka Exp $"); +__KERNEL_RCSID(0, "$NetBSD: klock.c,v 1.3.20.1 2014/06/18 09:34:27 msaitoh Exp $"); #include <sys/param.h> #include <sys/systm.h> @@ -117,6 +117,13 @@ _kernel_unlock(int nlocks, int *countp) } } +bool +_kernel_locked_p(void) +{ + + return giantowner == curlwp; +} + void rump_user_unschedule(int nlocks, int *countp, void *interlock) {