[Devel,RHEL7,COMMIT] ve/net: Move net->ct.can_alloc check up to resolve_normal_ct()

Submitted by Konstantin Khorenko on Nov. 7, 2016, 8 a.m.

Details

Message ID 201611070800.uA7806fc028329@finist_cl7.x64_64.work.ct
State New
Series "ve/net: Move net->ct.can_alloc check up to resolve_normal_ct()"
Headers show

Commit Message

Konstantin Khorenko Nov. 7, 2016, 8 a.m.
The commit is pushed to "branch-rh7-3.10.0-493.vz7.25.x-ovz" and will appear at https://src.openvz.org/scm/ovz/vzkernel.git
after rh7-3.10.0-493.el7
------>
commit fedb9af7081fbf3f17c1950923e83bc1299cabee
Author: Kirill Tkhai <ktkhai@virtuozzo.com>
Date:   Mon Nov 7 12:00:06 2016 +0400

    ve/net: Move net->ct.can_alloc check up to resolve_normal_ct()
    
    Move it up on stack to break creation of a CT earlier.
    This avoids us to search in CT hashes and speeds work up.
    
    So, now nf_conntrack_alloc() creates a CT certanly,
    __nf_conntrack_alloc() doesn't return NULL and it does not
    need to be external.
    
    Signed-off-by: Kirill Tkhai <ktkhai@virtuozzo.com>
    Reviewed-by: Pavel Tikhomirov <ptikhomirov@virtuozzo.com>
    
    To be merged to commit 874e7b5c6eb9
    "net: Primitives to enable conntrack allocation"
    
    https://jira.sw.ru/browse/PSBM-54823
    
    Signed-off-by: Kirill Tkhai <ktkhai@virtuozzo.com>
---
 include/net/net_namespace.h       |  2 +-
 net/netfilter/nf_conntrack_core.c | 14 +++++++-------
 2 files changed, 8 insertions(+), 8 deletions(-)

Patch hide | download patch | download mbox

diff --git a/include/net/net_namespace.h b/include/net/net_namespace.h
index b998f7a..a68e7a1 100644
--- a/include/net/net_namespace.h
+++ b/include/net/net_namespace.h
@@ -318,7 +318,7 @@  static inline struct net *read_pnet(possible_net_t const *pnet)
 static inline void allow_conntrack_allocation(struct net *net)
 {
 	net->ct.can_alloc = true;
-	smp_wmb(); /* Pairs with rmb in __nf_conntrack_alloc() */
+	smp_wmb(); /* Pairs with rmb in resolve_normal_ct() */
 }
 #else
 static inline void allow_conntrack_allocation(struct net *net) { }
diff --git a/net/netfilter/nf_conntrack_core.c b/net/netfilter/nf_conntrack_core.c
index bf59ec5..2dc10d6 100644
--- a/net/netfilter/nf_conntrack_core.c
+++ b/net/netfilter/nf_conntrack_core.c
@@ -855,12 +855,6 @@  __nf_conntrack_alloc(struct net *net,
 	unsigned int ct_max = net->ct.max ? net->ct.max : init_net.ct.max;
 	struct nf_conn *ct;
 
-	if (!net->ct.can_alloc) {
-		/* No rules loaded */
-		return NULL;
-	}
-	smp_rmb(); /* Pairs with wmb in allow_conntrack_allocation() */
-
 	if (unlikely(!nf_conntrack_hash_rnd)) {
 		init_nf_conntrack_hash_rnd();
 		/* recompute the hash as nf_conntrack_hash_rnd is initialized */
@@ -977,7 +971,7 @@  init_conntrack(struct net *net, struct nf_conn *tmpl,
 	zone = nf_ct_zone_tmpl(tmpl, skb, &tmp);
 	ct = __nf_conntrack_alloc(net, zone, tuple, &repl_tuple, GFP_ATOMIC,
 				  hash);
-	if (IS_ERR_OR_NULL(ct))
+	if (IS_ERR(ct))
 		return (struct nf_conntrack_tuple_hash *)ct;
 
 	if (tmpl && nfct_synproxy(tmpl)) {
@@ -1083,6 +1077,12 @@  resolve_normal_ct(struct net *net, struct nf_conn *tmpl,
 	if (!net_ipt_permitted(net, VE_NF_CONNTRACK))
 		return NULL;
 
+	if (!net->ct.can_alloc) {
+		/* No rules loaded */
+		return NULL;
+	}
+	smp_rmb(); /* Pairs with wmb in allow_conntrack_allocation() */
+
 	if (!nf_ct_get_tuple(skb, skb_network_offset(skb),
 			     dataoff, l3num, protonum, &tuple, l3proto,
 			     l4proto)) {