svn commit: r257323 - stable/9/sys/netgraph
Alexander V. Chernikov
melifaro at FreeBSD.org
Tue Oct 29 09:57:01 UTC 2013
Author: melifaro
Date: Tue Oct 29 09:57:00 2013
New Revision: 257323
URL: http://svnweb.freebsd.org/changeset/base/257323
Log:
Merge r256550.
Improve locking model used to protect netgraph topology:
use rwlocks instead of mutexes on node traversal.
Reviewed by: glebius
Tested by: Eugene Grosbein <egrosbein at rdtc.ru>
Sponsored by: Yandex LLC
Modified:
stable/9/sys/netgraph/ng_base.c
Directory Properties:
stable/9/sys/ (props changed)
Modified: stable/9/sys/netgraph/ng_base.c
==============================================================================
--- stable/9/sys/netgraph/ng_base.c Tue Oct 29 09:52:15 2013 (r257322)
+++ stable/9/sys/netgraph/ng_base.c Tue Oct 29 09:57:00 2013 (r257323)
@@ -74,7 +74,12 @@
MODULE_VERSION(netgraph, NG_ABI_VERSION);
/* Mutex to protect topology events. */
-static struct mtx ng_topo_mtx;
+static struct rwlock ng_topo_lock;
+#define TOPOLOGY_RLOCK() rw_rlock(&ng_topo_lock)
+#define TOPOLOGY_RUNLOCK() rw_runlock(&ng_topo_lock)
+#define TOPOLOGY_WLOCK() rw_wlock(&ng_topo_lock)
+#define TOPOLOGY_WUNLOCK() rw_wunlock(&ng_topo_lock)
+#define TOPOLOGY_NOTOWNED() rw_assert(&ng_topo_lock, RA_UNLOCKED)
#ifdef NETGRAPH_DEBUG
static struct mtx ng_nodelist_mtx; /* protects global node/hook lists */
@@ -1162,7 +1167,7 @@ ng_destroy_hook(hook_p hook)
* Protect divorce process with mutex, to avoid races on
* simultaneous disconnect.
*/
- mtx_lock(&ng_topo_mtx);
+ TOPOLOGY_WLOCK();
hook->hk_flags |= HK_INVALID;
@@ -1182,17 +1187,17 @@ ng_destroy_hook(hook_p hook)
* If it's already divorced from a node,
* just free it.
*/
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
} else {
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
ng_rmhook_self(peer); /* Send it a surprise */
}
NG_HOOK_UNREF(peer); /* account for peer link */
NG_HOOK_UNREF(hook); /* account for peer link */
} else
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
- mtx_assert(&ng_topo_mtx, MA_NOTOWNED);
+ TOPOLOGY_NOTOWNED();
/*
* Remove the hook from the node's list to avoid possible recursion
@@ -1233,9 +1238,9 @@ ng_bypass(hook_p hook1, hook_p hook2)
TRAP_ERROR();
return (EINVAL);
}
- mtx_lock(&ng_topo_mtx);
+ TOPOLOGY_WLOCK();
if (NG_HOOK_NOT_VALID(hook1) || NG_HOOK_NOT_VALID(hook2)) {
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
return (EINVAL);
}
hook1->hk_peer->hk_peer = hook2->hk_peer;
@@ -1243,7 +1248,7 @@ ng_bypass(hook_p hook1, hook_p hook2)
hook1->hk_peer = &ng_deadhook;
hook2->hk_peer = &ng_deadhook;
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
NG_HOOK_UNREF(hook1);
NG_HOOK_UNREF(hook2);
@@ -1440,15 +1445,15 @@ ng_con_part2(node_p node, item_p item, h
/*
* Acquire topo mutex to avoid race with ng_destroy_hook().
*/
- mtx_lock(&ng_topo_mtx);
+ TOPOLOGY_RLOCK();
peer = hook->hk_peer;
if (peer == &ng_deadhook) {
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_RUNLOCK();
printf("failed in ng_con_part2(B)\n");
ng_destroy_hook(hook);
ERROUT(ENOENT);
}
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_RUNLOCK();
if ((error = ng_send_fn2(peer->hk_node, peer, item, &ng_con_part3,
NULL, 0, NG_REUSE_ITEM))) {
@@ -1793,14 +1798,14 @@ ng_path2noderef(node_p here, const char
/* We have a segment, so look for a hook by that name */
hook = ng_findhook(node, segment);
- mtx_lock(&ng_topo_mtx);
+ TOPOLOGY_WLOCK();
/* Can't get there from here... */
if (hook == NULL || NG_HOOK_PEER(hook) == NULL ||
NG_HOOK_NOT_VALID(hook) ||
NG_HOOK_NOT_VALID(NG_HOOK_PEER(hook))) {
TRAP_ERROR();
NG_NODE_UNREF(node);
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
return (ENOENT);
}
@@ -1817,7 +1822,7 @@ ng_path2noderef(node_p here, const char
NG_NODE_UNREF(oldnode); /* XXX another race */
if (NG_NODE_NOT_VALID(node)) {
NG_NODE_UNREF(node); /* XXX more races */
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
TRAP_ERROR();
return (ENXIO);
}
@@ -1830,11 +1835,11 @@ ng_path2noderef(node_p here, const char
} else
*lasthook = NULL;
}
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
*destp = node;
return (0);
}
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_WUNLOCK();
}
}
@@ -3202,8 +3207,7 @@ ngb_mod_event(module_t mod, int event, v
rw_init(&ng_typelist_lock, "netgraph types");
rw_init(&ng_idhash_lock, "netgraph idhash");
rw_init(&ng_namehash_lock, "netgraph namehash");
- mtx_init(&ng_topo_mtx, "netgraph topology mutex", NULL,
- MTX_DEF);
+ rw_init(&ng_topo_lock, "netgraph topology mutex");
#ifdef NETGRAPH_DEBUG
mtx_init(&ng_nodelist_mtx, "netgraph nodelist mutex", NULL,
MTX_DEF);
@@ -3579,13 +3583,13 @@ ng_address_hook(node_p here, item_p item
* that the peer is still connected (even if invalid,) we know
* that the peer node is present, though maybe invalid.
*/
- mtx_lock(&ng_topo_mtx);
+ TOPOLOGY_RLOCK();
if ((hook == NULL) || NG_HOOK_NOT_VALID(hook) ||
NG_HOOK_NOT_VALID(peer = NG_HOOK_PEER(hook)) ||
NG_NODE_NOT_VALID(peernode = NG_PEER_NODE(hook))) {
NG_FREE_ITEM(item);
TRAP_ERROR();
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_RUNLOCK();
return (ENETDOWN);
}
@@ -3598,7 +3602,7 @@ ng_address_hook(node_p here, item_p item
NGI_SET_NODE(item, peernode);
SET_RETADDR(item, here, retaddr);
- mtx_unlock(&ng_topo_mtx);
+ TOPOLOGY_RUNLOCK();
return (0);
}
More information about the svn-src-stable-9
mailing list