Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys add API to manipulate ifa->ia_hash and ia_hash_pslist_en...
details: https://anonhg.NetBSD.org/src/rev/a806ec2ae049
branches: trunk
changeset: 349316:a806ec2ae049
user: knakahara <knakahara%NetBSD.org@localhost>
date: Tue Dec 06 07:01:47 2016 +0000
description:
add API to manipulate ifa->ia_hash and ia_hash_pslist_entry, and fix ia_hash_pslist_entry race by using them.
in_ifaddr_lock is required before writing ifa->ia_hash and
ia_hash_pslist_entry to serialize writer processings.
reviewed by ozaki-r@n.o.
diffstat:
sys/net/if_spppsubr.c | 28 +++------------
sys/netinet/in.c | 92 ++++++++++++++++++++++++++++++--------------------
sys/netinet/in_var.h | 4 +-
3 files changed, 64 insertions(+), 60 deletions(-)
diffs (237 lines):
diff -r 57073d934a49 -r a806ec2ae049 sys/net/if_spppsubr.c
--- a/sys/net/if_spppsubr.c Tue Dec 06 06:41:14 2016 +0000
+++ b/sys/net/if_spppsubr.c Tue Dec 06 07:01:47 2016 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: if_spppsubr.c,v 1.161 2016/12/01 02:30:54 knakahara Exp $ */
+/* $NetBSD: if_spppsubr.c,v 1.162 2016/12/06 07:01:47 knakahara Exp $ */
/*
* Synchronous PPP/Cisco link level subroutines.
@@ -41,7 +41,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: if_spppsubr.c,v 1.161 2016/12/01 02:30:54 knakahara Exp $");
+__KERNEL_RCSID(0, "$NetBSD: if_spppsubr.c,v 1.162 2016/12/06 07:01:47 knakahara Exp $");
#if defined(_KERNEL_OPT)
#include "opt_inet.h"
@@ -4921,19 +4921,11 @@
sp->ipcp.saved_hisaddr = dest->sin_addr.s_addr;
}
- LIST_REMOVE(ifatoia(ifa), ia_hash);
- IN_ADDRHASH_WRITER_REMOVE(ifatoia(ifa));
-#ifdef NET_MPSAFE
- pserialize_perform(in_ifaddrhash_psz);
-#endif
- IN_ADDRHASH_ENTRY_DESTROY(ifatoia(ifa));
+ in_addrhash_remove(ifatoia(ifa));
error = in_ifinit(ifp, ifatoia(ifa), &new_sin, &new_dst, 0);
- IN_ADDRHASH_ENTRY_INIT(ifatoia(ifa));
- LIST_INSERT_HEAD(&IN_IFADDR_HASH(ifatoia(ifa)->ia_addr.sin_addr.s_addr),
- ifatoia(ifa), ia_hash);
- IN_ADDRHASH_WRITER_INSERT_HEAD(ifatoia(ifa));
+ in_addrhash_insert(ifatoia(ifa));
if (debug && error)
{
@@ -5012,19 +5004,11 @@
if (sp->ipcp.flags & IPCP_HISADDR_DYN)
new_dst.sin_addr.s_addr = sp->ipcp.saved_hisaddr;
- LIST_REMOVE(ifatoia(ifa), ia_hash);
- IN_ADDRHASH_WRITER_REMOVE(ifatoia(ifa));
-#ifdef NET_MPSAFE
- pserialize_perform(in_ifaddrhash_psz);
-#endif
- IN_ADDRHASH_ENTRY_DESTROY(ifatoia(ifa));
+ in_addrhash_remove(ifatoia(ifa));
error = in_ifinit(ifp, ifatoia(ifa), &new_sin, &new_dst, 0);
- IN_ADDRHASH_ENTRY_INIT(ifatoia(ifa));
- LIST_INSERT_HEAD(&IN_IFADDR_HASH(ifatoia(ifa)->ia_addr.sin_addr.s_addr),
- ifatoia(ifa), ia_hash);
- IN_ADDRHASH_WRITER_INSERT_HEAD(ifatoia(ifa));
+ in_addrhash_insert(ifatoia(ifa));
if (debug && error)
{
diff -r 57073d934a49 -r a806ec2ae049 sys/netinet/in.c
--- a/sys/netinet/in.c Tue Dec 06 06:41:14 2016 +0000
+++ b/sys/netinet/in.c Tue Dec 06 07:01:47 2016 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: in.c,v 1.188 2016/11/18 10:38:55 knakahara Exp $ */
+/* $NetBSD: in.c,v 1.189 2016/12/06 07:01:47 knakahara Exp $ */
/*
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
@@ -91,7 +91,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: in.c,v 1.188 2016/11/18 10:38:55 knakahara Exp $");
+__KERNEL_RCSID(0, "$NetBSD: in.c,v 1.189 2016/12/06 07:01:47 knakahara Exp $");
#include "arp.h"
@@ -149,6 +149,9 @@
static int in_lifaddr_ioctl(struct socket *, u_long, void *,
struct ifnet *);
+static void in_addrhash_insert_locked(struct in_ifaddr *);
+static void in_addrhash_remove_locked(struct in_ifaddr *);
+
static int in_addprefix(struct in_ifaddr *, int);
static void in_scrubaddr(struct in_ifaddr *);
static int in_scrubprefix(struct in_ifaddr *);
@@ -598,14 +601,7 @@
case SIOCSIFADDR:
if (!newifaddr) {
- mutex_enter(&in_ifaddr_lock);
- LIST_REMOVE(ia, ia_hash);
- IN_ADDRHASH_WRITER_REMOVE(ia);
- mutex_exit(&in_ifaddr_lock);
-#ifdef NET_MPSAFE
- pserialize_perform(in_ifaddrhash_psz);
-#endif
- IN_ADDRHASH_ENTRY_DESTROY(ia);
+ in_addrhash_remove(ia);
need_reinsert = true;
}
error = in_ifinit(ifp, ia, satocsin(ifreq_getaddr(cmd, ifr)),
@@ -619,14 +615,7 @@
ia->ia_sockmask = *satocsin(ifreq_getaddr(cmd, ifr));
ia->ia_subnetmask = ia->ia_sockmask.sin_addr.s_addr;
if (!newifaddr) {
- mutex_enter(&in_ifaddr_lock);
- LIST_REMOVE(ia, ia_hash);
- IN_ADDRHASH_WRITER_REMOVE(ia);
- mutex_exit(&in_ifaddr_lock);
-#ifdef NET_MPSAFE
- pserialize_perform(in_ifaddrhash_psz);
-#endif
- IN_ADDRHASH_ENTRY_DESTROY(ia);
+ in_addrhash_remove(ia);
need_reinsert = true;
}
error = in_ifinit(ifp, ia, NULL, NULL, 0);
@@ -649,14 +638,7 @@
if (ifra->ifra_addr.sin_family == AF_INET &&
(hostIsNew || maskIsNew)) {
if (!newifaddr) {
- mutex_enter(&in_ifaddr_lock);
- LIST_REMOVE(ia, ia_hash);
- IN_ADDRHASH_WRITER_REMOVE(ia);
- mutex_exit(&in_ifaddr_lock);
-#ifdef NET_MPSAFE
- pserialize_perform(in_ifaddrhash_psz);
-#endif
- IN_ADDRHASH_ENTRY_DESTROY(ia);
+ in_addrhash_remove(ia);
need_reinsert = true;
}
error = in_ifinit(ifp, ia, &ifra->ifra_addr,
@@ -715,17 +697,10 @@
mutex_enter(&in_ifaddr_lock);
TAILQ_INSERT_TAIL(&in_ifaddrhead, ia, ia_list);
IN_ADDRLIST_WRITER_INSERT_TAIL(ia);
- LIST_INSERT_HEAD(&IN_IFADDR_HASH(ia->ia_addr.sin_addr.s_addr),
- ia, ia_hash);
- IN_ADDRHASH_WRITER_INSERT_HEAD(ia);
+ in_addrhash_insert_locked(ia);
mutex_exit(&in_ifaddr_lock);
} else if (need_reinsert) {
- mutex_enter(&in_ifaddr_lock);
- LIST_INSERT_HEAD(&IN_IFADDR_HASH(ia->ia_addr.sin_addr.s_addr),
- ia, ia_hash);
- IN_ADDRHASH_ENTRY_INIT(ia);
- IN_ADDRHASH_WRITER_INSERT_HEAD(ia);
- mutex_exit(&in_ifaddr_lock);
+ in_addrhash_insert(ia);
}
if (error == 0) {
@@ -851,8 +826,7 @@
in_scrubaddr(ia);
mutex_enter(&in_ifaddr_lock);
- LIST_REMOVE(ia, ia_hash);
- IN_ADDRHASH_WRITER_REMOVE(ia);
+ in_addrhash_remove_locked(ia);
TAILQ_REMOVE(&in_ifaddrhead, ia, ia_list);
IN_ADDRLIST_WRITER_REMOVE(ia);
ifa_remove(ifp, &ia->ia_ifa);
@@ -867,6 +841,50 @@
in_setmaxmtu();
}
+static void
+in_addrhash_insert_locked(struct in_ifaddr *ia)
+{
+
+ KASSERT(mutex_owned(&in_ifaddr_lock));
+
+ LIST_INSERT_HEAD(&IN_IFADDR_HASH(ia->ia_addr.sin_addr.s_addr), ia,
+ ia_hash);
+ IN_ADDRHASH_ENTRY_INIT(ia);
+ IN_ADDRHASH_WRITER_INSERT_HEAD(ia);
+}
+
+void
+in_addrhash_insert(struct in_ifaddr *ia)
+{
+
+ mutex_enter(&in_ifaddr_lock);
+ in_addrhash_insert_locked(ia);
+ mutex_exit(&in_ifaddr_lock);
+}
+
+static void
+in_addrhash_remove_locked(struct in_ifaddr *ia)
+{
+
+ KASSERT(mutex_owned(&in_ifaddr_lock));
+
+ LIST_REMOVE(ia, ia_hash);
+ IN_ADDRHASH_WRITER_REMOVE(ia);
+}
+
+void
+in_addrhash_remove(struct in_ifaddr *ia)
+{
+
+ mutex_enter(&in_ifaddr_lock);
+ in_addrhash_remove_locked(ia);
+ mutex_exit(&in_ifaddr_lock);
+#ifdef NET_MPSAFE
+ pserialize_perform(in_ifaddrhash_psz);
+#endif
+ IN_ADDRHASH_ENTRY_DESTROY(ia);
+}
+
void
in_purgeif(struct ifnet *ifp) /* MUST be called at splsoftnet() */
{
diff -r 57073d934a49 -r a806ec2ae049 sys/netinet/in_var.h
--- a/sys/netinet/in_var.h Tue Dec 06 06:41:14 2016 +0000
+++ b/sys/netinet/in_var.h Tue Dec 06 07:01:47 2016 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: in_var.h,v 1.89 2016/11/18 10:38:55 knakahara Exp $ */
+/* $NetBSD: in_var.h,v 1.90 2016/12/06 07:01:47 knakahara Exp $ */
/*-
* Copyright (c) 1998 The NetBSD Foundation, Inc.
@@ -420,6 +420,8 @@
int in_control(struct socket *, u_long, void *, struct ifnet *);
void in_purgeaddr(struct ifaddr *);
void in_purgeif(struct ifnet *);
+void in_addrhash_insert(struct in_ifaddr *);
+void in_addrhash_remove(struct in_ifaddr *);
int ipflow_fastforward(struct mbuf *);
struct ipid_state;
Home |
Main Index |
Thread Index |
Old Index