@@ -98,7 +98,7 @@ static int net_assign_generic(struct net *net, unsigned int id, void *data)
9898 }
9999
100100 ng = net_alloc_generic ();
101- if (ng == NULL )
101+ if (! ng )
102102 return - ENOMEM ;
103103
104104 /*
@@ -148,13 +148,6 @@ static int ops_init(const struct pernet_operations *ops, struct net *net)
148148 return err ;
149149}
150150
151- static void ops_free (const struct pernet_operations * ops , struct net * net )
152- {
153- if (ops -> id && ops -> size ) {
154- kfree (net_generic (net , * ops -> id ));
155- }
156- }
157-
158151static void ops_pre_exit_list (const struct pernet_operations * ops ,
159152 struct list_head * net_exit_list )
160153{
@@ -184,7 +177,7 @@ static void ops_free_list(const struct pernet_operations *ops,
184177 struct net * net ;
185178 if (ops -> size && ops -> id ) {
186179 list_for_each_entry (net , net_exit_list , exit_list )
187- ops_free ( ops , net );
180+ kfree ( net_generic ( net , * ops -> id ) );
188181 }
189182}
190183
@@ -433,15 +426,18 @@ static struct net *net_alloc(void)
433426
434427static void net_free (struct net * net )
435428{
436- kfree (rcu_access_pointer (net -> gen ));
437- kmem_cache_free (net_cachep , net );
429+ if (refcount_dec_and_test (& net -> passive )) {
430+ kfree (rcu_access_pointer (net -> gen ));
431+ kmem_cache_free (net_cachep , net );
432+ }
438433}
439434
440435void net_drop_ns (void * p )
441436{
442- struct net * ns = p ;
443- if (ns && refcount_dec_and_test (& ns -> passive ))
444- net_free (ns );
437+ struct net * net = (struct net * )p ;
438+
439+ if (net )
440+ net_free (net );
445441}
446442
447443struct net * copy_net_ns (unsigned long flags ,
@@ -479,7 +475,7 @@ struct net *copy_net_ns(unsigned long flags,
479475put_userns :
480476 key_remove_domain (net -> key_domain );
481477 put_user_ns (user_ns );
482- net_drop_ns (net );
478+ net_free (net );
483479dec_ucounts :
484480 dec_net_namespaces (ucounts );
485481 return ERR_PTR (rv );
@@ -611,7 +607,7 @@ static void cleanup_net(struct work_struct *work)
611607 dec_net_namespaces (net -> ucounts );
612608 key_remove_domain (net -> key_domain );
613609 put_user_ns (net -> user_ns );
614- net_drop_ns (net );
610+ net_free (net );
615611 }
616612}
617613
@@ -1120,6 +1116,14 @@ static int __init net_ns_init(void)
11201116
11211117pure_initcall (net_ns_init );
11221118
1119+ static void free_exit_list (struct pernet_operations * ops , struct list_head * net_exit_list )
1120+ {
1121+ ops_pre_exit_list (ops , net_exit_list );
1122+ synchronize_rcu ();
1123+ ops_exit_list (ops , net_exit_list );
1124+ ops_free_list (ops , net_exit_list );
1125+ }
1126+
11231127#ifdef CONFIG_NET_NS
11241128static int __register_pernet_operations (struct list_head * list ,
11251129 struct pernet_operations * ops )
@@ -1145,10 +1149,7 @@ static int __register_pernet_operations(struct list_head *list,
11451149out_undo :
11461150 /* If I have an error cleanup all namespaces I initialized */
11471151 list_del (& ops -> list );
1148- ops_pre_exit_list (ops , & net_exit_list );
1149- synchronize_rcu ();
1150- ops_exit_list (ops , & net_exit_list );
1151- ops_free_list (ops , & net_exit_list );
1152+ free_exit_list (ops , & net_exit_list );
11521153 return error ;
11531154}
11541155
@@ -1161,10 +1162,8 @@ static void __unregister_pernet_operations(struct pernet_operations *ops)
11611162 /* See comment in __register_pernet_operations() */
11621163 for_each_net (net )
11631164 list_add_tail (& net -> exit_list , & net_exit_list );
1164- ops_pre_exit_list (ops , & net_exit_list );
1165- synchronize_rcu ();
1166- ops_exit_list (ops , & net_exit_list );
1167- ops_free_list (ops , & net_exit_list );
1165+
1166+ free_exit_list (ops , & net_exit_list );
11681167}
11691168
11701169#else
@@ -1187,10 +1186,7 @@ static void __unregister_pernet_operations(struct pernet_operations *ops)
11871186 } else {
11881187 LIST_HEAD (net_exit_list );
11891188 list_add (& init_net .exit_list , & net_exit_list );
1190- ops_pre_exit_list (ops , & net_exit_list );
1191- synchronize_rcu ();
1192- ops_exit_list (ops , & net_exit_list );
1193- ops_free_list (ops , & net_exit_list );
1189+ free_exit_list (ops , & net_exit_list );
11941190 }
11951191}
11961192
0 commit comments