From ef3a700d5b1b4af97d51f4328843dcd9b5919044 Mon Sep 17 00:00:00 2001 From: Casey Bodley Date: Wed, 22 Feb 2012 11:44:57 -0800 Subject: [PATCH] recovery: always send RECLAIM_COMPLETE on client recovery client was previously only sending RECLAIM_COMPLETE during grace period. the spec mandates that RECLAIM_COMPLETE be sent before any non-reclaim locking operations, regardless of grace period. when recovery code detects a NFS4ERR_NO_GRACE error, send RECLAIM_COMPLETE immediately before attempting any out-of-grace recovery Signed-off-by: Casey Bodley --- daemon/recovery.c | 60 ++++++++++++++++++++++++++--------------------- 1 file changed, 33 insertions(+), 27 deletions(-) diff --git a/daemon/recovery.c b/daemon/recovery.c index f145dcb..ddd9e27 100644 --- a/daemon/recovery.c +++ b/daemon/recovery.c @@ -236,19 +236,22 @@ static int recover_open( if (status == NFS4_OK) /* use existing delegation */ goto out; - if (*grace) + if (*grace) { status = recover_open_grace(session, &open->parent, &open->file, &open->owner, open->share_access, open->share_deny, &stateid, &delegation); - else - status = NFS4ERR_NO_GRACE; - - if (status == NFS4ERR_NO_GRACE) { - *grace = FALSE; + if (status == NFS4ERR_NO_GRACE) { + *grace = FALSE; + /* send RECLAIM_COMPLETE before any out-of-grace recovery */ + nfs41_reclaim_complete(session); + } + } + if (!*grace) { status = recover_open_no_grace(session, &open->parent, &open->file, &open->owner, open->share_access, open->share_deny, &stateid, &delegation); } + if (status) goto out; @@ -304,15 +307,17 @@ static int recover_locks( if (lock->delegated) continue; - if (*grace) + if (*grace) { status = nfs41_lock(session, &open->file, &open->owner, lock->exclusive ? WRITE_LT : READ_LT, lock->offset, lock->length, TRUE, FALSE, &stateid); - else - status = NFS4ERR_NO_GRACE; - - if (status == NFS4ERR_NO_GRACE) { - *grace = FALSE; + if (status == NFS4ERR_NO_GRACE) { + *grace = FALSE; + /* send RECLAIM_COMPLETE before any out-of-grace recovery */ + nfs41_reclaim_complete(session); + } + } + if (!*grace) { /* attempt out-of-grace recovery with a normal LOCK */ status = nfs41_lock(session, &open->file, &open->owner, lock->exclusive ? WRITE_LT : READ_LT, lock->offset, @@ -361,11 +366,13 @@ static int recover_delegation_want( status = nfs41_want_delegation(session, &deleg->file, &claim, want_flags, FALSE, &delegation); - } else - status = NFS4ERR_NO_GRACE; - - if (status == NFS4ERR_NO_GRACE) { - *grace = FALSE; + if (status == NFS4ERR_NO_GRACE) { + *grace = FALSE; + /* send RECLAIM_COMPLETE before any out-of-grace recovery */ + nfs41_reclaim_complete(session); + } + } + if (!*grace) { /* attempt out-of-grace recovery with with CLAIM_DELEG_PREV_FH */ claim.claim = CLAIM_DELEG_PREV_FH; @@ -418,14 +425,16 @@ static int recover_delegation_open( memcpy(owner.owner + sizeof(time_t), deleg, sizeof(deleg)); owner.owner_len = sizeof(time_t) + sizeof(deleg); - if (*grace) + if (*grace) { status = recover_open_grace(session, &deleg->parent, &deleg->file, &owner, access, deny, &stateid.stateid, &delegation); - else - status = NFS4ERR_NO_GRACE; - - if (status == NFS4ERR_NO_GRACE) { - *grace = FALSE; + if (status == NFS4ERR_NO_GRACE) { + *grace = FALSE; + /* send RECLAIM_COMPLETE before any out-of-grace recovery */ + nfs41_reclaim_complete(session); + } + } + if (!*grace) { status = recover_open_no_grace(session, &deleg->parent, &deleg->file, &owner, access, deny, &stateid.stateid, &delegation); } @@ -535,10 +544,7 @@ unlock: if (grace && status != NFS4ERR_BADSESSION) { /* send reclaim_complete, but don't fail on errors */ - status = nfs41_reclaim_complete(session); - if (status && status == NFS4ERR_NOTSUPP) - eprintf("nfs41_reclaim_complete() failed with %s\n", - nfs_error_string(status)); + nfs41_reclaim_complete(session); } return status; }