From owner-svn-src-head@FreeBSD.ORG Wed Jun 24 08:53:23 2009 Return-Path: Delivered-To: svn-src-head@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id 9D8711065673; Wed, 24 Jun 2009 08:53:23 +0000 (UTC) (envelope-from rwatson@FreeBSD.org) Received: from svn.freebsd.org (svn.freebsd.org [IPv6:2001:4f8:fff6::2c]) by mx1.freebsd.org (Postfix) with ESMTP id 8BD2D8FC20; Wed, 24 Jun 2009 08:53:23 +0000 (UTC) (envelope-from rwatson@FreeBSD.org) Received: from svn.freebsd.org (localhost [127.0.0.1]) by svn.freebsd.org (8.14.3/8.14.3) with ESMTP id n5O8rN7R006839; Wed, 24 Jun 2009 08:53:23 GMT (envelope-from rwatson@svn.freebsd.org) Received: (from rwatson@localhost) by svn.freebsd.org (8.14.3/8.14.3/Submit) id n5O8rNlN006837; Wed, 24 Jun 2009 08:53:23 GMT (envelope-from rwatson@svn.freebsd.org) Message-Id: <200906240853.n5O8rNlN006837@svn.freebsd.org> From: Robert Watson Date: Wed, 24 Jun 2009 08:53:23 +0000 (UTC) To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org X-SVN-Group: head MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Cc: Subject: svn commit: r194813 - head/sys/net X-BeenThere: svn-src-head@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: SVN commit messages for the src tree for head/-current List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Wed, 24 Jun 2009 08:53:24 -0000 Author: rwatson Date: Wed Jun 24 08:53:23 2009 New Revision: 194813 URL: http://svn.freebsd.org/changeset/base/194813 Log: Lock if_addrhead when iterating, and where necessary acquire and release ifadr references in if_sppp. MFC after: 6 weeks Modified: head/sys/net/if_spppsubr.c Modified: head/sys/net/if_spppsubr.c ============================================================================== --- head/sys/net/if_spppsubr.c Wed Jun 24 08:52:09 2009 (r194812) +++ head/sys/net/if_spppsubr.c Wed Jun 24 08:53:23 2009 (r194813) @@ -4905,6 +4905,7 @@ sppp_get_ip_addrs(struct sppp *sp, u_lon * aliases don't make any sense on a p2p link anyway. */ si = 0; + IF_ADDR_LOCK(ifp); TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) if (ifa->ifa_addr->sa_family == AF_INET) { si = (struct sockaddr_in *)ifa->ifa_addr; @@ -4923,6 +4924,7 @@ sppp_get_ip_addrs(struct sppp *sp, u_lon if (si && si->sin_addr.s_addr) ddst = si->sin_addr.s_addr; } + IF_ADDR_UNLOCK(ifp); if (dst) *dst = ntohl(ddst); if (src) *src = ntohl(ssrc); @@ -4946,23 +4948,24 @@ sppp_set_ip_addr(struct sppp *sp, u_long * aliases don't make any sense on a p2p link anyway. */ si = 0; - TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) - { - if (ifa->ifa_addr->sa_family == AF_INET) - { + IF_ADDR_LOCK(ifp); + TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) { + if (ifa->ifa_addr->sa_family == AF_INET) { si = (struct sockaddr_in *)ifa->ifa_addr; - if (si) + if (si != NULL) { + ifa_ref(ifa); break; + } } } + IF_ADDR_UNLOCK(ifp); - if (ifa && si) - { + if (ifa != NULL) { int error; + /* delete old route */ error = rtinit(ifa, (int)RTM_DELETE, RTF_HOST); - if(debug && error) - { + if (debug && error) { log(LOG_DEBUG, SPP_FMT "sppp_set_ip_addr: rtinit DEL failed, error=%d\n", SPP_ARGS(ifp), error); } @@ -4975,11 +4978,11 @@ sppp_set_ip_addr(struct sppp *sp, u_long /* add new route */ error = rtinit(ifa, (int)RTM_ADD, RTF_HOST); - if (debug && error) - { + if (debug && error) { log(LOG_DEBUG, SPP_FMT "sppp_set_ip_addr: rtinit ADD failed, error=%d", SPP_ARGS(ifp), error); } + ifa_free(ifa); } } #endif @@ -5004,7 +5007,8 @@ sppp_get_ip6_addrs(struct sppp *sp, stru * Pick the first link-local AF_INET6 address from the list, * aliases don't make any sense on a p2p link anyway. */ - si = 0; + si = NULL; + IF_ADDR_LOCK(ifp); TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) if (ifa->ifa_addr->sa_family == AF_INET6) { si = (struct sockaddr_in6 *)ifa->ifa_addr; @@ -5030,6 +5034,7 @@ sppp_get_ip6_addrs(struct sppp *sp, stru bcopy(&ddst, dst, sizeof(*dst)); if (src) bcopy(&ssrc, src, sizeof(*src)); + IF_ADDR_UNLOCK(ifp); } #ifdef IPV6CP_MYIFID_DYN @@ -5058,28 +5063,29 @@ sppp_set_ip6_addr(struct sppp *sp, const */ sin6 = NULL; - TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) - { - if (ifa->ifa_addr->sa_family == AF_INET6) - { + IF_ADDR_LOCK(ifp); + TAILQ_FOREACH(ifa, &ifp->if_addrhead, ifa_link) { + if (ifa->ifa_addr->sa_family == AF_INET6) { sin6 = (struct sockaddr_in6 *)ifa->ifa_addr; - if (sin6 && IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) + if (sin6 && IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { + ifa_ref(ifa); break; + } } } + IF_ADDR_UNLOCK(ifp); - if (ifa && sin6) - { + if (ifa != NULL) { int error; struct sockaddr_in6 new_sin6 = *sin6; bcopy(src, &new_sin6.sin6_addr, sizeof(new_sin6.sin6_addr)); error = in6_ifinit(ifp, ifatoia6(ifa), &new_sin6, 1); - if (debug && error) - { + if (debug && error) { log(LOG_DEBUG, SPP_FMT "sppp_set_ip6_addr: in6_ifinit " " failed, error=%d\n", SPP_ARGS(ifp), error); } + ifa_free(ifa); } } #endif