diff options
Diffstat (limited to 'fs/nfs')
-rw-r--r-- | fs/nfs/nfs4proc.c | 41 |
1 files changed, 37 insertions, 4 deletions
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index 122b9340e6ef..e1212914bc03 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c | |||
@@ -7483,7 +7483,8 @@ out: | |||
7483 | */ | 7483 | */ |
7484 | static int | 7484 | static int |
7485 | _nfs41_proc_secinfo_no_name(struct nfs_server *server, struct nfs_fh *fhandle, | 7485 | _nfs41_proc_secinfo_no_name(struct nfs_server *server, struct nfs_fh *fhandle, |
7486 | struct nfs_fsinfo *info, struct nfs4_secinfo_flavors *flavors) | 7486 | struct nfs_fsinfo *info, |
7487 | struct nfs4_secinfo_flavors *flavors, bool use_integrity) | ||
7487 | { | 7488 | { |
7488 | struct nfs41_secinfo_no_name_args args = { | 7489 | struct nfs41_secinfo_no_name_args args = { |
7489 | .style = SECINFO_STYLE_CURRENT_FH, | 7490 | .style = SECINFO_STYLE_CURRENT_FH, |
@@ -7496,8 +7497,23 @@ _nfs41_proc_secinfo_no_name(struct nfs_server *server, struct nfs_fh *fhandle, | |||
7496 | .rpc_argp = &args, | 7497 | .rpc_argp = &args, |
7497 | .rpc_resp = &res, | 7498 | .rpc_resp = &res, |
7498 | }; | 7499 | }; |
7499 | return nfs4_call_sync(server->nfs_client->cl_rpcclient, server, &msg, | 7500 | struct rpc_clnt *clnt = server->client; |
7500 | &args.seq_args, &res.seq_res, 0); | 7501 | int status; |
7502 | |||
7503 | if (use_integrity) { | ||
7504 | clnt = server->nfs_client->cl_rpcclient; | ||
7505 | msg.rpc_cred = nfs4_get_clid_cred(server->nfs_client); | ||
7506 | } | ||
7507 | |||
7508 | dprintk("--> %s\n", __func__); | ||
7509 | status = nfs4_call_sync(clnt, server, &msg, &args.seq_args, | ||
7510 | &res.seq_res, 0); | ||
7511 | dprintk("<-- %s status=%d\n", __func__, status); | ||
7512 | |||
7513 | if (msg.rpc_cred) | ||
7514 | put_rpccred(msg.rpc_cred); | ||
7515 | |||
7516 | return status; | ||
7501 | } | 7517 | } |
7502 | 7518 | ||
7503 | static int | 7519 | static int |
@@ -7507,7 +7523,24 @@ nfs41_proc_secinfo_no_name(struct nfs_server *server, struct nfs_fh *fhandle, | |||
7507 | struct nfs4_exception exception = { }; | 7523 | struct nfs4_exception exception = { }; |
7508 | int err; | 7524 | int err; |
7509 | do { | 7525 | do { |
7510 | err = _nfs41_proc_secinfo_no_name(server, fhandle, info, flavors); | 7526 | /* first try using integrity protection */ |
7527 | err = -NFS4ERR_WRONGSEC; | ||
7528 | |||
7529 | /* try to use integrity protection with machine cred */ | ||
7530 | if (_nfs4_is_integrity_protected(server->nfs_client)) | ||
7531 | err = _nfs41_proc_secinfo_no_name(server, fhandle, info, | ||
7532 | flavors, true); | ||
7533 | |||
7534 | /* | ||
7535 | * if unable to use integrity protection, or SECINFO with | ||
7536 | * integrity protection returns NFS4ERR_WRONGSEC (which is | ||
7537 | * disallowed by spec, but exists in deployed servers) use | ||
7538 | * the current filesystem's rpc_client and the user cred. | ||
7539 | */ | ||
7540 | if (err == -NFS4ERR_WRONGSEC) | ||
7541 | err = _nfs41_proc_secinfo_no_name(server, fhandle, info, | ||
7542 | flavors, false); | ||
7543 | |||
7511 | switch (err) { | 7544 | switch (err) { |
7512 | case 0: | 7545 | case 0: |
7513 | case -NFS4ERR_WRONGSEC: | 7546 | case -NFS4ERR_WRONGSEC: |