aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTrond Myklebust <Trond.Myklebust@netapp.com>2005-10-18 17:20:21 -0400
committerTrond Myklebust <Trond.Myklebust@netapp.com>2005-10-18 17:20:21 -0400
commit550f57470c6506f5ef3c708335dea6bd48bf3dc4 (patch)
treebe34cc170cce1e103baec1976f7903528eb4ff4d
parentb8e5c4c2978fa666287525a9de2fa648a7581262 (diff)
NFSv4: Ensure that we recover from the OPEN + OPEN_CONFIRM BAD_STATEID race
If the server is in the unconfirmed OPEN state for a given open owner and receives a second OPEN for the same open owner, it will cancel the state of the first request and set up an OPEN_CONFIRM for the second. This can cause a race that is discussed in rfc3530 on page 181. The following patch allows the client to recover by retrying the original open request. Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
-rw-r--r--fs/nfs/nfs4proc.c10
1 files changed, 10 insertions, 0 deletions
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c
index a8be9af610ac..ff378126ccd7 100644
--- a/fs/nfs/nfs4proc.c
+++ b/fs/nfs/nfs4proc.c
@@ -785,6 +785,16 @@ static struct nfs4_state *nfs4_do_open(struct inode *dir, struct dentry *dentry,
785 exception.retry = 1; 785 exception.retry = 1;
786 continue; 786 continue;
787 } 787 }
788 /*
789 * BAD_STATEID on OPEN means that the server cancelled our
790 * state before it received the OPEN_CONFIRM.
791 * Recover by retrying the request as per the discussion
792 * on Page 181 of RFC3530.
793 */
794 if (status == -NFS4ERR_BAD_STATEID) {
795 exception.retry = 1;
796 continue;
797 }
788 res = ERR_PTR(nfs4_handle_exception(NFS_SERVER(dir), 798 res = ERR_PTR(nfs4_handle_exception(NFS_SERVER(dir),
789 status, &exception)); 799 status, &exception));
790 } while (exception.retry); 800 } while (exception.retry);