SUNRPC: Cache cred of process creating the rpc_client
authorTrond Myklebust <trondmy@gmail.com>
Wed, 24 Apr 2019 21:46:42 +0000 (17:46 -0400)
committerAnna Schumaker <Anna.Schumaker@Netapp.com>
Fri, 26 Apr 2019 20:00:48 +0000 (16:00 -0400)
When converting kuids to AUTH_UNIX creds, etc we will want to use the
same user namespace as the process that created the rpc client.

Signed-off-by: Trond Myklebust <trond.myklebust@hammerspace.com>
Signed-off-by: Anna Schumaker <Anna.Schumaker@Netapp.com>
fs/lockd/host.c
fs/lockd/mon.c
fs/nfs/client.c
fs/nfs/mount_clnt.c
fs/nfsd/nfs4callback.c
include/linux/sunrpc/clnt.h
net/sunrpc/clnt.c
net/sunrpc/rpcb_clnt.c

index f0b5c98..d460811 100644 (file)
@@ -458,6 +458,7 @@ nlm_bind_host(struct nlm_host *host)
                        .authflavor     = RPC_AUTH_UNIX,
                        .flags          = (RPC_CLNT_CREATE_NOPING |
                                           RPC_CLNT_CREATE_AUTOBIND),
+                       .cred           = current_cred(),
                };
 
                /*
index 654594e..1eabd91 100644 (file)
@@ -82,6 +82,7 @@ static struct rpc_clnt *nsm_create(struct net *net, const char *nodename)
                .version                = NSM_VERSION,
                .authflavor             = RPC_AUTH_NULL,
                .flags                  = RPC_CLNT_CREATE_NOPING,
+               .cred                   = current_cred(),
        };
 
        return rpc_create(&args);
index f74638c..a843cf3 100644 (file)
@@ -500,6 +500,7 @@ int nfs_create_rpc_client(struct nfs_client *clp,
                .program        = &nfs_program,
                .version        = clp->rpc_ops->version,
                .authflavor     = flavor,
+               .cred           = current_cred(),
        };
 
        if (test_bit(NFS_CS_DISCRTRY, &clp->cl_flags))
index d979ff4..cb7c10e 100644 (file)
@@ -163,6 +163,7 @@ int nfs_mount(struct nfs_mount_request *info)
                .program        = &mnt_program,
                .version        = info->version,
                .authflavor     = RPC_AUTH_UNIX,
+               .cred           = current_cred(),
        };
        struct rpc_clnt         *mnt_clnt;
        int                     status;
@@ -249,6 +250,7 @@ void nfs_umount(const struct nfs_mount_request *info)
                .version        = info->version,
                .authflavor     = RPC_AUTH_UNIX,
                .flags          = RPC_CLNT_CREATE_NOPING,
+               .cred           = current_cred(),
        };
        struct rpc_message msg  = {
                .rpc_argp       = info->dirpath,
index f7494be..3a10399 100644 (file)
@@ -868,6 +868,7 @@ static int setup_callback_client(struct nfs4_client *clp, struct nfs4_cb_conn *c
                .program        = &cb_program,
                .version        = 1,
                .flags          = (RPC_CLNT_CREATE_NOPING | RPC_CLNT_CREATE_QUIET),
+               .cred           = current_cred(),
        };
        struct rpc_clnt *client;
        const struct cred *cred;
index 943762a..6e80731 100644 (file)
@@ -72,6 +72,7 @@ struct rpc_clnt {
        struct dentry           *cl_debugfs;    /* debugfs directory */
 #endif
        struct rpc_xprt_iter    cl_xpi;
+       const struct cred       *cl_cred;
 };
 
 /*
@@ -126,6 +127,7 @@ struct rpc_create_args {
        unsigned long           flags;
        char                    *client_name;
        struct svc_xprt         *bc_xprt;       /* NFSv4.1 backchannel */
+       const struct cred       *cred;
 };
 
 struct rpc_add_xprt_test {
index e933f11..369a264 100644 (file)
@@ -394,6 +394,7 @@ static struct rpc_clnt * rpc_new_client(const struct rpc_create_args *args,
        if (err)
                goto out_no_clid;
 
+       clnt->cl_cred     = get_cred(args->cred);
        clnt->cl_procinfo = version->procs;
        clnt->cl_maxproc  = version->nrprocs;
        clnt->cl_prog     = args->prognumber ? : program->number;
@@ -439,6 +440,7 @@ static struct rpc_clnt * rpc_new_client(const struct rpc_create_args *args,
 out_no_path:
        rpc_free_iostats(clnt->cl_metrics);
 out_no_stats:
+       put_cred(clnt->cl_cred);
        rpc_free_clid(clnt);
 out_no_clid:
        kfree(clnt);
@@ -631,6 +633,7 @@ static struct rpc_clnt *__rpc_clone_client(struct rpc_create_args *args,
        new->cl_discrtry = clnt->cl_discrtry;
        new->cl_chatty = clnt->cl_chatty;
        new->cl_principal = clnt->cl_principal;
+       new->cl_cred = get_cred(clnt->cl_cred);
        return new;
 
 out_err:
@@ -652,6 +655,7 @@ struct rpc_clnt *rpc_clone_client(struct rpc_clnt *clnt)
                .prognumber     = clnt->cl_prog,
                .version        = clnt->cl_vers,
                .authflavor     = clnt->cl_auth->au_flavor,
+               .cred           = clnt->cl_cred,
        };
        return __rpc_clone_client(&args, clnt);
 }
@@ -673,6 +677,7 @@ rpc_clone_client_set_auth(struct rpc_clnt *clnt, rpc_authflavor_t flavor)
                .prognumber     = clnt->cl_prog,
                .version        = clnt->cl_vers,
                .authflavor     = flavor,
+               .cred           = clnt->cl_cred,
        };
        return __rpc_clone_client(&args, clnt);
 }
@@ -880,6 +885,7 @@ rpc_free_client(struct rpc_clnt *clnt)
        xprt_put(rcu_dereference_raw(clnt->cl_xprt));
        xprt_iter_destroy(&clnt->cl_xpi);
        rpciod_down();
+       put_cred(clnt->cl_cred);
        rpc_free_clid(clnt);
        kfree(clnt);
        return parent;
@@ -944,6 +950,7 @@ struct rpc_clnt *rpc_bind_new_program(struct rpc_clnt *old,
                .prognumber     = program->number,
                .version        = vers,
                .authflavor     = old->cl_auth->au_flavor,
+               .cred           = old->cl_cred,
        };
        struct rpc_clnt *clnt;
        int err;
index 18b0cf2..2277b7c 100644 (file)
@@ -240,6 +240,7 @@ static int rpcb_create_local_unix(struct net *net)
                .program        = &rpcb_program,
                .version        = RPCBVERS_2,
                .authflavor     = RPC_AUTH_NULL,
+               .cred           = current_cred(),
                /*
                 * We turn off the idle timeout to prevent the kernel
                 * from automatically disconnecting the socket.
@@ -299,6 +300,7 @@ static int rpcb_create_local_net(struct net *net)
                .program        = &rpcb_program,
                .version        = RPCBVERS_2,
                .authflavor     = RPC_AUTH_UNIX,
+               .cred           = current_cred(),
                .flags          = RPC_CLNT_CREATE_NOPING,
        };
        struct rpc_clnt *clnt, *clnt4;
@@ -358,7 +360,8 @@ out:
 static struct rpc_clnt *rpcb_create(struct net *net, const char *nodename,
                                    const char *hostname,
                                    struct sockaddr *srvaddr, size_t salen,
-                                   int proto, u32 version)
+                                   int proto, u32 version,
+                                   const struct cred *cred)
 {
        struct rpc_create_args args = {
                .net            = net,
@@ -370,6 +373,7 @@ static struct rpc_clnt *rpcb_create(struct net *net, const char *nodename,
                .program        = &rpcb_program,
                .version        = version,
                .authflavor     = RPC_AUTH_UNIX,
+               .cred           = cred,
                .flags          = (RPC_CLNT_CREATE_NOPING |
                                        RPC_CLNT_CREATE_NONPRIVPORT),
        };
@@ -745,7 +749,8 @@ void rpcb_getport_async(struct rpc_task *task)
        rpcb_clnt = rpcb_create(xprt->xprt_net,
                                clnt->cl_nodename,
                                xprt->servername, sap, salen,
-                               xprt->prot, bind_version);
+                               xprt->prot, bind_version,
+                               clnt->cl_cred);
        if (IS_ERR(rpcb_clnt)) {
                status = PTR_ERR(rpcb_clnt);
                dprintk("RPC: %5u %s: rpcb_create failed, error %ld\n",