summaryrefslogtreecommitdiffstats
path: root/fs
diff options
context:
space:
mode:
authorTrond Myklebust <trond.myklebust@primarydata.com>2015-08-19 06:45:13 +0200
committerTrond Myklebust <trond.myklebust@primarydata.com>2015-08-19 06:45:13 +0200
commit3c13cb5b647ebe36fb79128bc8b917d2a3317b65 (patch)
tree04fdc0eb8041c2123c4e605d6a259ea8cca012b8 /fs
parentNFSv4.1/pnfs: Fix a close/delegreturn hang when return-on-close is set (diff)
downloadlinux-3c13cb5b647ebe36fb79128bc8b917d2a3317b65.tar.xz
linux-3c13cb5b647ebe36fb79128bc8b917d2a3317b65.zip
NFSv4.1/pnfs: Play safe w.r.t. close() races when return-on-close is set
If we have an OPEN_DOWNGRADE and CLOSE race with one another, we want to ensure that the layout is forgotten by the client, so that we start afresh with a new layoutget. Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com>
Diffstat (limited to 'fs')
-rw-r--r--fs/nfs/nfs4proc.c10
1 files changed, 5 insertions, 5 deletions
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c
index bda7837dfe6b..9e9f7816cf24 100644
--- a/fs/nfs/nfs4proc.c
+++ b/fs/nfs/nfs4proc.c
@@ -2661,7 +2661,7 @@ static void nfs4_close_done(struct rpc_task *task, void *data)
switch (task->tk_status) {
case 0:
res_stateid = &calldata->res.stateid;
- if (calldata->arg.fmode == 0 && calldata->roc)
+ if (calldata->roc)
pnfs_roc_set_barrier(state->inode,
calldata->roc_barrier);
renew_lease(server, calldata->timestamp);
@@ -2735,11 +2735,11 @@ static void nfs4_close_prepare(struct rpc_task *task, void *data)
goto out_no_action;
}
- if (calldata->arg.fmode == 0) {
+ if (calldata->arg.fmode == 0)
task->tk_msg.rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_CLOSE];
- if (calldata->roc)
- pnfs_roc_get_barrier(inode, &calldata->roc_barrier);
- }
+ if (calldata->roc)
+ pnfs_roc_get_barrier(inode, &calldata->roc_barrier);
+
calldata->arg.share_access =
nfs4_map_atomic_open_share(NFS_SERVER(inode),
calldata->arg.fmode, 0);