summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPatrick McHardy <kaber@trash.net>2007-03-14 16:39:07 -0700
committerDavid S. Miller <davem@sunset.davemloft.net>2007-04-25 22:25:43 -0700
commitc6a1e615d1ba942b9e783079d53f741e4a8e1c89 (patch)
tree230f3c78633b4066cc49af8b45c614d32d760e34
parent0661cca9c216322e77dca7f47df107c02ce4e70c (diff)
downloadlinux-c6a1e615d1ba942b9e783079d53f741e4a8e1c89.tar.bz2
[NETFILTER]: nf_conntrack: simplify l4 protocol array allocation
The retrying after an allocation failure is not necessary anymore since we're holding the mutex the entire time, for the same reason the double allocation race can't happen anymore. Signed-off-by: Patrick McHardy <kaber@trash.net> Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r--net/netfilter/nf_conntrack_proto.c37
1 files changed, 12 insertions, 25 deletions
diff --git a/net/netfilter/nf_conntrack_proto.c b/net/netfilter/nf_conntrack_proto.c
index 509725412d3b..e4aad2087f4d 100644
--- a/net/netfilter/nf_conntrack_proto.c
+++ b/net/netfilter/nf_conntrack_proto.c
@@ -281,47 +281,34 @@ int nf_conntrack_l4proto_register(struct nf_conntrack_l4proto *l4proto)
return -EBUSY;
mutex_lock(&nf_ct_proto_mutex);
-retry:
- if (nf_ct_protos[l4proto->l3proto]) {
- if (nf_ct_protos[l4proto->l3proto][l4proto->l4proto]
- != &nf_conntrack_l4proto_generic) {
- ret = -EBUSY;
- goto out_unlock;
- }
- } else {
+ if (!nf_ct_protos[l4proto->l3proto]) {
/* l3proto may be loaded latter. */
struct nf_conntrack_l4proto **proto_array;
int i;
- proto_array = (struct nf_conntrack_l4proto **)
- kmalloc(MAX_NF_CT_PROTO *
- sizeof(struct nf_conntrack_l4proto *),
- GFP_KERNEL);
+ proto_array = kmalloc(MAX_NF_CT_PROTO *
+ sizeof(struct nf_conntrack_l4proto *),
+ GFP_KERNEL);
if (proto_array == NULL) {
ret = -ENOMEM;
goto out_unlock;
}
+
for (i = 0; i < MAX_NF_CT_PROTO; i++)
proto_array[i] = &nf_conntrack_l4proto_generic;
-
- if (nf_ct_protos[l4proto->l3proto])
- /* bad timing, but no problem */
- kfree(proto_array);
- else
- nf_ct_protos[l4proto->l3proto] = proto_array;
-
- /*
- * Just once because array is never freed until unloading
- * nf_conntrack.ko
- */
- goto retry;
+ nf_ct_protos[l4proto->l3proto] = proto_array;
+ } else if (nf_ct_protos[l4proto->l3proto][l4proto->l4proto] !=
+ &nf_conntrack_l4proto_generic) {
+ ret = -EBUSY;
+ goto out_unlock;
}
ret = nf_ct_l4proto_register_sysctl(l4proto);
if (ret < 0)
goto out_unlock;
- rcu_assign_pointer(nf_ct_protos[l4proto->l3proto][l4proto->l4proto], l4proto);
+ rcu_assign_pointer(nf_ct_protos[l4proto->l3proto][l4proto->l4proto],
+ l4proto);
out_unlock:
mutex_unlock(&nf_ct_proto_mutex);