Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

SUNRPC: service destruction in network namespace context

v2: Added comment to BUG_ON's in svc_destroy() to make code looks clearer.

This patch introduces network namespace filter for service destruction
function.
Nothing special here - just do exactly the same operations, but only for
tranports in passed networks namespace context.
BTW, BUG_ON() checks for empty service transports lists were returned into
svc_destroy() function. This is because of swithing generic svc_close_all() to
networks namespace dependable svc_close_net().

Signed-off-by: Stanislav Kinsbursky <skinsbursky@parallels.com>
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>

authored by

Stanislav Kinsbursky and committed by
Trond Myklebust
7b147f1f 3a22bf50

+29 -13
+1 -1
include/linux/sunrpc/svcsock.h
··· 34 34 /* 35 35 * Function prototypes. 36 36 */ 37 - void svc_close_all(struct svc_serv *); 37 + void svc_close_net(struct svc_serv *, struct net *); 38 38 int svc_recv(struct svc_rqst *, long); 39 39 int svc_send(struct svc_rqst *); 40 40 void svc_drop(struct svc_rqst *);
+11 -2
net/sunrpc/svc.c
··· 517 517 void 518 518 svc_destroy(struct svc_serv *serv) 519 519 { 520 + struct net *net = current->nsproxy->net_ns; 521 + 520 522 dprintk("svc: svc_destroy(%s, %d)\n", 521 523 serv->sv_program->pg_name, 522 524 serv->sv_nrthreads); ··· 541 539 * caller is using--nfsd_mutex in the case of nfsd). So it's 542 540 * safe to traverse those lists and shut everything down: 543 541 */ 544 - svc_close_all(serv); 542 + svc_close_net(serv, net); 543 + 544 + /* 545 + * The last user is gone and thus all sockets have to be destroyed to 546 + * the point. Check this. 547 + */ 548 + BUG_ON(!list_empty(&serv->sv_permsocks)); 549 + BUG_ON(!list_empty(&serv->sv_tempsocks)); 545 550 546 551 if (serv->sv_shutdown) 547 - serv->sv_shutdown(serv, current->nsproxy->net_ns); 552 + serv->sv_shutdown(serv, net); 548 553 549 554 cache_clean_deferred(serv); 550 555
+17 -10
net/sunrpc/svc_xprt.c
··· 922 922 } 923 923 EXPORT_SYMBOL_GPL(svc_close_xprt); 924 924 925 - static void svc_close_list(struct list_head *xprt_list) 925 + static void svc_close_list(struct list_head *xprt_list, struct net *net) 926 926 { 927 927 struct svc_xprt *xprt; 928 928 929 929 list_for_each_entry(xprt, xprt_list, xpt_list) { 930 + if (xprt->xpt_net != net) 931 + continue; 930 932 set_bit(XPT_CLOSE, &xprt->xpt_flags); 931 933 set_bit(XPT_BUSY, &xprt->xpt_flags); 932 934 } 933 935 } 934 936 935 - static void svc_clear_pools(struct svc_serv *serv) 937 + static void svc_clear_pools(struct svc_serv *serv, struct net *net) 936 938 { 937 939 struct svc_pool *pool; 938 940 struct svc_xprt *xprt; ··· 946 944 947 945 spin_lock_bh(&pool->sp_lock); 948 946 list_for_each_entry_safe(xprt, tmp, &pool->sp_sockets, xpt_ready) { 947 + if (xprt->xpt_net != net) 948 + continue; 949 949 list_del_init(&xprt->xpt_ready); 950 950 } 951 951 spin_unlock_bh(&pool->sp_lock); 952 952 } 953 953 } 954 954 955 - static void svc_clear_list(struct list_head *xprt_list) 955 + static void svc_clear_list(struct list_head *xprt_list, struct net *net) 956 956 { 957 957 struct svc_xprt *xprt; 958 958 struct svc_xprt *tmp; 959 959 960 960 list_for_each_entry_safe(xprt, tmp, xprt_list, xpt_list) { 961 + if (xprt->xpt_net != net) 962 + continue; 961 963 svc_delete_xprt(xprt); 962 964 } 963 - BUG_ON(!list_empty(xprt_list)); 965 + list_for_each_entry(xprt, xprt_list, xpt_list) 966 + BUG_ON(xprt->xpt_net == net); 964 967 } 965 968 966 - void svc_close_all(struct svc_serv *serv) 969 + void svc_close_net(struct svc_serv *serv, struct net *net) 967 970 { 968 - svc_close_list(&serv->sv_tempsocks); 969 - svc_close_list(&serv->sv_permsocks); 971 + svc_close_list(&serv->sv_tempsocks, net); 972 + svc_close_list(&serv->sv_permsocks, net); 970 973 971 - svc_clear_pools(serv); 974 + svc_clear_pools(serv, net); 972 975 /* 973 976 * At this point the sp_sockets lists will stay empty, since 974 977 * svc_enqueue will not add new entries without taking the 975 978 * sp_lock and checking XPT_BUSY. 976 979 */ 977 - svc_clear_list(&serv->sv_tempsocks); 978 - svc_clear_list(&serv->sv_permsocks); 980 + svc_clear_list(&serv->sv_tempsocks, net); 981 + svc_clear_list(&serv->sv_permsocks, net); 979 982 } 980 983 981 984 /*