Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 0f442aa2 authored by J. Bruce Fields's avatar J. Bruce Fields Committed by Linus Torvalds
Browse files

[PATCH] nfsd4: simplify process-open1 logic



nfsd4_process_open1 is very highly nested; flatten it out a bit.

Also, the preceding comment, which just outlines the logic, seems redundant.

Signed-off-by: default avatarJ. Bruce Fields <bfields@citi.umich.edu>
Signed-off-by: default avatarNeil Brown <neilb@suse.de>
Signed-off-by: default avatarAndrew Morton <akpm@osdl.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@osdl.org>
parent 375c5547
Loading
Loading
Loading
Loading
+35 −64
Original line number Diff line number Diff line
@@ -1429,90 +1429,61 @@ static struct lock_manager_operations nfsd_lease_mng_ops = {
};


/*
 * nfsd4_process_open1()
 * 	lookup stateowner.
 * 		found:
 * 			check confirmed 
 * 				confirmed:
 * 					check seqid
 * 				not confirmed:
 * 					delete owner
 * 					create new owner
 * 		notfound:
 * 			verify clientid
 * 			create new owner
 *
 * called with nfs4_lock_state() held.
 */
int
nfsd4_process_open1(struct nfsd4_open *open)
{
	int status;
	clientid_t *clientid = &open->op_clientid;
	struct nfs4_client *clp = NULL;
	unsigned int strhashval;
	struct nfs4_stateowner *sop = NULL;

	status = nfserr_inval;
	if (!check_name(open->op_owner))
		goto out;
		return nfserr_inval;

	if (STALE_CLIENTID(&open->op_clientid))
		return nfserr_stale_clientid;

	strhashval = ownerstr_hashval(clientid->cl_id, open->op_owner);
	sop = find_openstateowner_str(strhashval, open);
	if (sop) {
	open->op_stateowner = sop;
	if (!sop) {
		/* Make sure the client's lease hasn't expired. */
		clp = find_confirmed_client(clientid);
		if (clp == NULL)
			return nfserr_expired;
		goto renew;
	}
	if (!sop->so_confirmed) {
			/* Replace any unconfirmed stateowner without
			 * even checking for replays */
		/* Replace unconfirmed owners without checking for replay. */
		clp = sop->so_client;
		release_stateowner(sop);
		} else if (open->op_seqid == sop->so_seqid) {
			/* normal case */
		open->op_stateowner = NULL;
		goto renew;
		} else if (open->op_seqid == sop->so_seqid - 1) {
			/* replay */
	}
	if (open->op_seqid == sop->so_seqid - 1) {
		if (sop->so_replay.rp_buflen)
			return NFSERR_REPLAY_ME;
			else {
		/* The original OPEN failed so spectacularly
		 * that we don't even have replay data saved!
		 * Therefore, we have no choice but to continue
		 * processing this OPEN; presumably, we'll
		 * fail again for the same reason.
		 */
				dprintk("nfsd4_process_open1:"
					" replay with no replay cache\n");
		dprintk("nfsd4_process_open1: replay with no replay cache\n");
		goto renew;
	}
		} else {
			status = nfserr_bad_seqid;
			goto out;
		}
	} else {
		/* nfs4_stateowner not found.
		 * Verify clientid and instantiate new nfs4_stateowner.
		 * If verify fails this is presumably the result of the
		 * client's lease expiring.
		 */
		status = nfserr_expired;
		clp = find_confirmed_client(clientid);
		if (clp == NULL)
			goto out;
	}
	status = nfserr_resource;
	if (open->op_seqid != sop->so_seqid)
		return nfserr_bad_seqid;
renew:
	if (open->op_stateowner == NULL) {
		sop = alloc_init_open_stateowner(strhashval, clp, open);
		if (sop == NULL)
		goto out;
			return nfserr_resource;
		open->op_stateowner = sop;
renew:
	status = nfs_ok;
	}
	list_del_init(&sop->so_close_lru);
	renew_client(sop->so_client);
out:
	return status;
	return nfs_ok;
}

static inline int