// SPDX-License-Identifier: GPL-2.0-only
/******************************************************************************
*******************************************************************************
**
**  Copyright (C) 2005-2010 Red Hat, Inc.  All rights reserved.
**
**
*******************************************************************************
******************************************************************************/

/* Central locking logic has four stages:

   dlm_lock()
   dlm_unlock()

   request_lock(ls, lkb)
   convert_lock(ls, lkb)
   unlock_lock(ls, lkb)
   cancel_lock(ls, lkb)

   _request_lock(r, lkb)
   _convert_lock(r, lkb)
   _unlock_lock(r, lkb)
   _cancel_lock(r, lkb)

   do_request(r, lkb)
   do_convert(r, lkb)
   do_unlock(r, lkb)
   do_cancel(r, lkb)

   Stage 1 (lock, unlock) is mainly about checking input args and
   splitting into one of the four main operations:

       dlm_lock          = request_lock
       dlm_lock+CONVERT  = convert_lock
       dlm_unlock        = unlock_lock
       dlm_unlock+CANCEL = cancel_lock

   Stage 2, xxxx_lock(), just finds and locks the relevant rsb which is
   provided to the next stage.

   Stage 3, _xxxx_lock(), determines if the operation is local or remote.
   When remote, it calls send_xxxx(), when local it calls do_xxxx().

   Stage 4, do_xxxx(), is the guts of the operation.  It manipulates the
   given rsb and lkb and queues callbacks.

   For remote operations, send_xxxx() results in the corresponding do_xxxx()
   function being executed on the remote node.  The connecting send/receive
   calls on local (L) and remote (R) nodes:

   L: send_xxxx()              ->  R: receive_xxxx()
                                   R: do_xxxx()
   L: receive_xxxx_reply()     <-  R: send_xxxx_reply()
*/
#include <trace/events/dlm.h>

#include <linux/types.h>
#include <linux/rbtree.h>
#include <linux/slab.h>
#include "dlm_internal.h"
#include <linux/dlm_device.h>
#include "memory.h"
#include "midcomms.h"
#include "requestqueue.h"
#include "util.h"
#include "dir.h"
#include "member.h"
#include "lockspace.h"
#include "ast.h"
#include "lock.h"
#include "rcom.h"
#include "recover.h"
#include "lvb_table.h"
#include "user.h"
#include "config.h"

static int send_request(struct dlm_rsb *r, struct dlm_lkb *lkb);
static int send_convert(struct dlm_rsb *r, struct dlm_lkb *lkb);
static int send_unlock(struct dlm_rsb *r, struct dlm_lkb *lkb);
static int send_cancel(struct dlm_rsb *r, struct dlm_lkb *lkb);
static int send_grant(struct dlm_rsb *r, struct dlm_lkb *lkb);
static int send_bast(struct dlm_rsb *r, struct dlm_lkb *lkb, int mode);
static int send_lookup(struct dlm_rsb *r, struct dlm_lkb *lkb);
static int send_remove(struct dlm_rsb *r);
static int _request_lock(struct dlm_rsb *r, struct dlm_lkb *lkb);
static int _cancel_lock(struct dlm_rsb *r, struct dlm_lkb *lkb);
static void __receive_convert_reply(struct dlm_rsb *r, struct dlm_lkb *lkb,
				    const struct dlm_message *ms, bool local);
static int receive_extralen(const struct dlm_message *ms);
static void do_purge(struct dlm_ls *ls, int nodeid, int pid);
static void deactivate_rsb(struct kref *kref);

/*
 * Lock compatibilty matrix - thanks Steve
 * UN = Unlocked state. Not really a state, used as a flag
 * PD = Padding. Used to make the matrix a nice power of two in size
 * Other states are the same as the VMS DLM.
 * Usage: matrix[grmode+1][rqmode+1]  (although m[rq+1][gr+1] is the same)
 */

static const int __dlm_compat_matrix[8][8] = {
      /* UN NL CR CW PR PW EX PD */
        {1, 1, 1, 1, 1, 1, 1, 0},       /* UN */
        {1, 1, 1, 1, 1, 1, 1, 0},       /* NL */
        {1, 1, 1, 1, 1, 1, 0, 0},       /* CR */
        {1, 1, 1, 1, 0, 0, 0, 0},       /* CW */
        {1, 1, 1, 0, 1, 0, 0, 0},       /* PR */
        {1, 1, 1, 0, 0, 0, 0, 0},       /* PW */
        {1, 1, 0, 0, 0, 0, 0, 0},       /* EX */
        {0, 0, 0, 0, 0, 0, 0, 0}        /* PD */
};

/*
 * This defines the direction of transfer of LVB data.
 * Granted mode is the row; requested mode is the column.
 * Usage: matrix[grmode+1][rqmode+1]
 * 1 = LVB is returned to the caller
 * 0 = LVB is written to the resource
 * -1 = nothing happens to the LVB
 */

const int dlm_lvb_operations[8][8] = {
        /* UN   NL  CR  CW  PR  PW  EX  PD*/
        {  -1,  1,  1,  1,  1,  1,  1, -1 }, /* UN */
        {  -1,  1,  1,  1,  1,  1,  1,  0 }, /* NL */
        {  -1, -1,  1,  1,  1,  1,  1,  0 }, /* CR */
        {  -1, -1, -1,  1,  1,  1,  1,  0 }, /* CW */
        {  -1, -1, -1, -1,  1,  1,  1,  0 }, /* PR */
        {  -1,  0,  0,  0,  0,  0,  1,  0 }, /* PW */
        {  -1,  0,  0,  0,  0,  0,  0,  0 }, /* EX */
        {  -1,  0,  0,  0,  0,  0,  0,  0 }  /* PD */
};

#define modes_compat(gr, rq) \
	__dlm_compat_matrix[(gr)->lkb_grmode + 1][(rq)->lkb_rqmode + 1]

int dlm_modes_compat(int mode1, int mode2)
{
	return __dlm_compat_matrix[mode1 + 1][mode2 + 1];
}

/*
 * Compatibility matrix for conversions with QUECVT set.
 * Granted mode is the row; requested mode is the column.
 * Usage: matrix[grmode+1][rqmode+1]
 */

static const int __quecvt_compat_matrix[8][8] = {
      /* UN NL CR CW PR PW EX PD */
        {0, 0, 0, 0, 0, 0, 0, 0},       /* UN */
        {0, 0, 1, 1, 1, 1, 1, 0},       /* NL */
        {0, 0, 0, 1, 1, 1, 1, 0},       /* CR */
        {0, 0, 0, 0, 1, 1, 1, 0},       /* CW */
        {0, 0, 0, 1, 0, 1, 1, 0},       /* PR */
        {0, 0, 0, 0, 0, 0, 1, 0},       /* PW */
        {0, 0, 0, 0, 0, 0, 0, 0},       /* EX */
        {0, 0, 0, 0, 0, 0, 0, 0}        /* PD */
};

void dlm_print_lkb(struct dlm_lkb *lkb)
{
	printk(KERN_ERR "lkb: nodeid %d id %x remid %x exflags %x flags %x "
	       "sts %d rq %d gr %d wait_type %d wait_nodeid %d seq %llu\n",
	       lkb->lkb_nodeid, lkb->lkb_id, lkb->lkb_remid, lkb->lkb_exflags,
	       dlm_iflags_val(lkb), lkb->lkb_status, lkb->lkb_rqmode,
	       lkb->lkb_grmode, lkb->lkb_wait_type, lkb->lkb_wait_nodeid,
	       (unsigned long long)lkb->lkb_recover_seq);
}

static void dlm_print_rsb(struct dlm_rsb *r)
{
	printk(KERN_ERR "rsb: nodeid %d master %d dir %d flags %lx first %x "
	       "rlc %d name %s\n",
	       r->res_nodeid, r->res_master_nodeid, r->res_dir_nodeid,
	       r->res_flags, r->res_first_lkid, r->res_recover_locks_count,
	       r->res_name);
}

void dlm_dump_rsb(struct dlm_rsb *r)
{
	struct dlm_lkb *lkb;

	dlm_print_rsb(r);

	printk(KERN_ERR "rsb: root_list empty %d recover_list empty %d\n",
	       list_empty(&r->res_root_list), list_empty(&r->res_recover_list));
	printk(KERN_ERR "rsb lookup list\n");
	list_for_each_entry(lkb, &r->res_lookup, lkb_rsb_lookup)
		dlm_print_lkb(lkb);
	printk(KERN_ERR "rsb grant queue:\n");
	list_for_each_entry(lkb, &r->res_grantqueue, lkb_statequeue)
		dlm_print_lkb(lkb);
	printk(KERN_ERR "rsb convert queue:\n");
	list_for_each_entry(lkb, &r->res_convertqueue, lkb_statequeue)
		dlm_print_lkb(lkb);
	printk(KERN_ERR "rsb wait queue:\n");
	list_for_each_entry(lkb, &r->res_waitqueue, lkb_statequeue)
		dlm_print_lkb(lkb);
}

/* Threads cannot use the lockspace while it's being recovered */

void dlm_lock_recovery(struct dlm_ls *ls)
{
	down_read(&ls->ls_in_recovery);
}

void dlm_unlock_recovery(struct dlm_ls *ls)
{
	up_read(&ls->ls_in_recovery);
}

int dlm_lock_recovery_try(struct dlm_ls *ls)
{
	return down_read_trylock(&ls->ls_in_recovery);
}

static inline int can_be_queued(struct dlm_lkb *lkb)
{
	return !(lkb->lkb_exflags & DLM_LKF_NOQUEUE);
}

static inline int force_blocking_asts(struct dlm_lkb *lkb)
{
	return (lkb->lkb_exflags & DLM_LKF_NOQUEUEBAST);
}

static inline int is_demoted(struct dlm_lkb *lkb)
{
	return test_bit(DLM_SBF_DEMOTED_BIT, &lkb->lkb_sbflags);
}

static inline int is_altmode(struct dlm_lkb *lkb)
{
	return test_bit(DLM_SBF_ALTMODE_BIT, &lkb->lkb_sbflags);
}

static inline int is_granted(struct dlm_lkb *lkb)
{
	return (lkb->lkb_status == DLM_LKSTS_GRANTED);
}

static inline int is_remote(struct dlm_rsb *r)
{
	DLM_ASSERT(r->res_nodeid >= 0, dlm_print_rsb(r););
	return !!r->res_nodeid;
}

static inline int is_process_copy(struct dlm_lkb *lkb)
{
	return lkb->lkb_nodeid &&
	       !test_bit(DLM_IFL_MSTCPY_BIT, &lkb->lkb_iflags);
}

static inline int is_master_copy(struct dlm_lkb *lkb)
{
	return test_bit(DLM_IFL_MSTCPY_BIT, &lkb->lkb_iflags);
}

static inline int middle_conversion(struct dlm_lkb *lkb)
{
	if ((lkb->lkb_grmode==DLM_LOCK_PR && lkb->lkb_rqmode==DLM_LOCK_CW) ||
	    (lkb->lkb_rqmode==DLM_LOCK_PR && lkb->lkb_grmode==DLM_LOCK_CW))
		return 1;
	return 0;
}

static inline int down_conversion(struct dlm_lkb *lkb)
{
	return (!middle_conversion(lkb) && lkb->lkb_rqmode < lkb->lkb_grmode);
}

static inline int is_overlap_unlock(struct dlm_lkb *lkb)
{
	return test_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags);
}

static inline int is_overlap_cancel(struct dlm_lkb *lkb)
{
	return test_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags);
}

static inline int is_overlap(struct dlm_lkb *lkb)
{
	return test_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags) ||
	       test_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags);
}

static void queue_cast(struct dlm_rsb *r, struct dlm_lkb *lkb, int rv)
{
	if (is_master_copy(lkb))
		return;

	DLM_ASSERT(lkb->lkb_lksb, dlm_print_lkb(lkb););

	if (rv == -DLM_ECANCEL &&
	    test_and_clear_bit(DLM_IFL_DEADLOCK_CANCEL_BIT, &lkb->lkb_iflags))
		rv = -EDEADLK;

	dlm_add_cb(lkb, DLM_CB_CAST, lkb->lkb_grmode, rv, dlm_sbflags_val(lkb));
}

static inline void queue_cast_overlap(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	queue_cast(r, lkb,
		   is_overlap_unlock(lkb) ? -DLM_EUNLOCK : -DLM_ECANCEL);
}

static void queue_bast(struct dlm_rsb *r, struct dlm_lkb *lkb, int rqmode)
{
	if (is_master_copy(lkb)) {
		send_bast(r, lkb, rqmode);
	} else {
		dlm_add_cb(lkb, DLM_CB_BAST, rqmode, 0, 0);
	}
}

/*
 * Basic operations on rsb's and lkb's
 */

static inline unsigned long rsb_toss_jiffies(void)
{
	return jiffies + (READ_ONCE(dlm_config.ci_toss_secs) * HZ);
}

/* This is only called to add a reference when the code already holds
   a valid reference to the rsb, so there's no need for locking. */

static inline void hold_rsb(struct dlm_rsb *r)
{
	/* inactive rsbs are not ref counted */
	WARN_ON(rsb_flag(r, RSB_INACTIVE));
	kref_get(&r->res_ref);
}

void dlm_hold_rsb(struct dlm_rsb *r)
{
	hold_rsb(r);
}

/* TODO move this to lib/refcount.c */
static __must_check bool
dlm_refcount_dec_and_write_lock_bh(refcount_t *r, rwlock_t *lock)
__cond_acquires(lock)
{
	if (refcount_dec_not_one(r))
		return false;

	write_lock_bh(lock);
	if (!refcount_dec_and_test(r)) {
		write_unlock_bh(lock);
		return false;
	}

	return true;
}

/* TODO move this to include/linux/kref.h */
static inline int dlm_kref_put_write_lock_bh(struct kref *kref,
					     void (*release)(struct kref *kref),
					     rwlock_t *lock)
{
	if (dlm_refcount_dec_and_write_lock_bh(&kref->refcount, lock)) {
		release(kref);
		return 1;
	}

	return 0;
}

static void put_rsb(struct dlm_rsb *r)
{
	struct dlm_ls *ls = r->res_ls;
	int rv;

	rv = dlm_kref_put_write_lock_bh(&r->res_ref, deactivate_rsb,
					&ls->ls_rsbtbl_lock);
	if (rv)
		write_unlock_bh(&ls->ls_rsbtbl_lock);
}

void dlm_put_rsb(struct dlm_rsb *r)
{
	put_rsb(r);
}

/* connected with timer_delete_sync() in dlm_ls_stop() to stop
 * new timers when recovery is triggered and don't run them
 * again until a resume_scan_timer() tries it again.
 */
static void enable_scan_timer(struct dlm_ls *ls, unsigned long jiffies)
{
	if (!dlm_locking_stopped(ls))
		mod_timer(&ls->ls_scan_timer, jiffies);
}

/* This function tries to resume the timer callback if a rsb
 * is on the scan list and no timer is pending. It might that
 * the first entry is on currently executed as timer callback
 * but we don't care if a timer queued up again and does
 * nothing. Should be a rare case.
 */
void resume_scan_timer(struct dlm_ls *ls)
{
	struct dlm_rsb *r;

	spin_lock_bh(&ls->ls_scan_lock);
	r = list_first_entry_or_null(&ls->ls_scan_list, struct dlm_rsb,
				     res_scan_list);
	if (r && !timer_pending(&ls->ls_scan_timer))
		enable_scan_timer(ls, r->res_toss_time);
	spin_unlock_bh(&ls->ls_scan_lock);
}

/* ls_rsbtbl_lock must be held */

static void del_scan(struct dlm_ls *ls, struct dlm_rsb *r)
{
	struct dlm_rsb *first;

	/* active rsbs should never be on the scan list */
	WARN_ON(!rsb_flag(r, RSB_INACTIVE));

	spin_lock_bh(&ls->ls_scan_lock);
	r->res_toss_time = 0;

	/* if the rsb is not queued do nothing */
	if (list_empty(&r->res_scan_list))
		goto out;

	/* get the first element before delete */
	first = list_first_entry(&ls->ls_scan_list, struct dlm_rsb,
				 res_scan_list);
	list_del_init(&r->res_scan_list);
	/* check if the first element was the rsb we deleted */
	if (first == r) {
		/* try to get the new first element, if the list
		 * is empty now try to delete the timer, if we are
		 * too late we don't care.
		 *
		 * if the list isn't empty and a new first element got
		 * in place, set the new timer expire time.
		 */
		first = list_first_entry_or_null(&ls->ls_scan_list, struct dlm_rsb,
						 res_scan_list);
		if (!first)
			timer_delete(&ls->ls_scan_timer);
		else
			enable_scan_timer(ls, first->res_toss_time);
	}

out:
	spin_unlock_bh(&ls->ls_scan_lock);
}

static void add_scan(struct dlm_ls *ls, struct dlm_rsb *r)
{
	int our_nodeid = dlm_our_nodeid();
	struct dlm_rsb *first;

	/* A dir record for a remote master rsb should never be on the scan list. */
	WARN_ON(!dlm_no_directory(ls) &&
		(r->res_master_nodeid != our_nodeid) &&
		(dlm_dir_nodeid(r) == our_nodeid));

	/* An active rsb should never be on the scan list. */
	WARN_ON(!rsb_flag(r, RSB_INACTIVE));

	/* An rsb should not already be on the scan list. */
	WARN_ON(!list_empty(&r->res_scan_list));

	spin_lock_bh(&ls->ls_scan_lock);
	/* set the new rsb absolute expire time in the rsb */
	r->res_toss_time = rsb_toss_jiffies();
	if (list_empty(&ls->ls_scan_list)) {
		/* if the queue is empty add the element and it's
		 * our new expire time
		 */
		list_add_tail(&r->res_scan_list, &ls->ls_scan_list);
		enable_scan_timer(ls, r->res_toss_time);
	} else {
		/* try to get the maybe new first element and then add
		 * to this rsb with the oldest expire time to the end
		 * of the queue. If the list was empty before this
		 * rsb expire time is our next expiration if it wasn't
		 * the now new first elemet is our new expiration time
		 */
		first = list_first_entry_or_null(&ls->ls_scan_list, struct dlm_rsb,
						 res_scan_list);
		list_add_tail(&r->res_scan_list, &ls->ls_scan_list);
		if (!first)
			enable_scan_timer(ls, r->res_toss_time);
		else
			enable_scan_timer(ls, first->res_toss_time);
	}
	spin_unlock_bh(&ls->ls_scan_lock);
}

/* if we hit contention we do in 250 ms a retry to trylock.
 * if there is any other mod_timer in between we don't care
 * about that it expires earlier again this is only for the
 * unlikely case nothing happened in this time.
 */
#define DLM_TOSS_TIMER_RETRY	(jiffies + msecs_to_jiffies(250))

/* Called by lockspace scan_timer to free unused rsb's. */

void dlm_rsb_scan(struct timer_list *timer)
{
	struct dlm_ls *ls = timer_container_of(ls, timer, ls_scan_timer);
	int our_nodeid = dlm_our_nodeid();
	struct dlm_rsb *r;
	int rv;

	while (1) {
		/* interrupting point to leave iteration when
		 * recovery waits for timer_delete_sync(), recovery
		 * will take care to delete everything in scan list.
		 */
		if (dlm_locking_stopped(ls))
			break;

		rv = spin_trylock(&ls->ls_scan_lock);
		if (!rv) {
			/* rearm again try timer */
			enable_scan_timer(ls, DLM_TOSS_TIMER_RETRY);
			break;
		}

		r = list_first_entry_or_null(&ls->ls_scan_list, struct dlm_rsb,
					     res_scan_list);
		if (!r) {
			/* the next add_scan will enable the timer again */
			spin_unlock(&ls->ls_scan_lock);
			break;
		}

		/*
		 * If the first rsb is not yet expired, then stop because the
		 * list is sorted with nearest expiration first.
		 */
		if (time_before(jiffies, r->res_toss_time)) {
			/* rearm with the next rsb to expire in the future */
			enable_scan_timer(ls, r->res_toss_time);
			spin_unlock(&ls->ls_scan_lock);
			break;
		}

		/* in find_rsb_dir/nodir there is a reverse order of this
		 * lock, however this is only a trylock if we hit some
		 * possible contention we try it again.
		 */
		rv = write_trylock(&ls->ls_rsbtbl_lock);
		if (!rv) {
			spin_unlock(&ls->ls_scan_lock);
			/* rearm again try timer */
			enable_scan_timer(ls, DLM_TOSS_TIMER_RETRY);
			break;
		}

		list_del(&r->res_slow_list);
		rhashtable_remove_fast(&ls->ls_rsbtbl, &r->res_node,
				       dlm_rhash_rsb_params);
		rsb_clear_flag(r, RSB_HASHED);

		/* ls_rsbtbl_lock is not needed when calling send_remove() */
		write_unlock(&ls->ls_rsbtbl_lock);

		list_del_init(&r->res_scan_list);
		spin_unlock(&ls->ls_scan_lock);

		/* An rsb that is a dir record for a remote master rsb
		 * cannot be removed, and should not have a timer enabled.
		 */
		WARN_ON(!dlm_no_directory(ls) &&
			(r->res_master_nodeid != our_nodeid) &&
			(dlm_dir_nodeid(r) == our_nodeid));

		/* We're the master of this rsb but we're not
		 * the directory record, so we need to tell the
		 * dir node to remove the dir record
		 */
		if (!dlm_no_directory(ls) &&
		    (r->res_master_nodeid == our_nodeid) &&
		    (dlm_dir_nodeid(r) != our_nodeid))
			send_remove(r);

		free_inactive_rsb(r);
	}
}

/* If ls->ls_new_rsb is empty, return -EAGAIN, so the caller can
   unlock any spinlocks, go back and call pre_rsb_struct again.
   Otherwise, take an rsb off the list and return it. */

static int get_rsb_struct(struct dlm_ls *ls, const void *name, int len,
			  struct dlm_rsb **r_ret)
{
	struct dlm_rsb *r;

	r = dlm_allocate_rsb();
	if (!r)
		return -ENOMEM;

	r->res_ls = ls;
	r->res_length = len;
	memcpy(r->res_name, name, len);
	spin_lock_init(&r->res_lock);

	INIT_LIST_HEAD(&r->res_lookup);
	INIT_LIST_HEAD(&r->res_grantqueue);
	INIT_LIST_HEAD(&r->res_convertqueue);
	INIT_LIST_HEAD(&r->res_waitqueue);
	INIT_LIST_HEAD(&r->res_root_list);
	INIT_LIST_HEAD(&r->res_scan_list);
	INIT_LIST_HEAD(&r->res_recover_list);
	INIT_LIST_HEAD(&r->res_masters_list);

	*r_ret = r;
	return 0;
}

int dlm_search_rsb_tree(struct rhashtable *rhash, const void *name, int len,
			struct dlm_rsb **r_ret)
{
	char key[DLM_RESNAME_MAXLEN] = {};

	memcpy(key, name, len);
	*r_ret = rhashtable_lookup_fast(rhash, &key, dlm_rhash_rsb_params);
	if (*r_ret)
		return 0;

	return -EBADR;
}

static int rsb_insert(struct dlm_rsb *rsb, struct rhashtable *rhash)
{
	int rv;

	rv = rhashtable_insert_fast(rhash, &rsb->res_node,
				    dlm_rhash_rsb_params);
	if (!rv)
		rsb_set_flag(rsb, RSB_HASHED);

	return rv;
}

/*
 * Find rsb in rsbtbl and potentially create/add one
 *
 * Delaying the release of rsb's has a similar benefit to applications keeping
 * NL locks on an rsb, but without the guarantee that the cached master value
 * will still be valid when the rsb is reused.  Apps aren't always smart enough
 * to keep NL locks on an rsb that they may lock again shortly; this can lead
 * to excessive master lookups and removals if we don't delay the release.
 *
 * Searching for an rsb means looking through both the normal list and toss
 * list.  When found on the toss list the rsb is moved to the normal list with
 * ref count of 1; when found on normal list the ref count is incremented.
 *
 * rsb's on the keep list are being used locally and refcounted.
 * rsb's on the toss list are not being used locally, and are not refcounted.
 *
 * The toss list rsb's were either
 * - previously used locally but not any more (were on keep list, then
 *   moved to toss list when last refcount dropped)
 * - created and put on toss list as a directory record for a lookup
 *   (we are the dir node for the res, but are not using the res right now,
 *   but some other node is)
 *
 * The purpose of find_rsb() is to return a refcounted rsb for local use.
 * So, if the given rsb is on the toss list, it is moved to the keep list
 * before being returned.
 *
 * deactivate_rsb() happens when all local usage of the rsb is done, i.e. no
 * more refcounts exist, so the rsb is moved from the keep list to the
 * toss list.
 *
 * rsb's on both keep and toss lists are used for doing a name to master
 * lookups.  rsb's that are in use locally (and being refcounted) are on
 * the keep list, rsb's that are not in use locally (not refcounted) and
 * only exist for name/master lookups are on the toss list.
 *
 * rsb's on the toss list who's dir_nodeid is not local can have stale
 * name/master mappings.  So, remote requests on such rsb's can potentially
 * return with an error, which means the mapping is stale and needs to
 * be updated with a new lookup.  (The idea behind MASTER UNCERTAIN and
 * first_lkid is to keep only a single outstanding request on an rsb
 * while that rsb has a potentially stale master.)
 */

static int find_rsb_dir(struct dlm_ls *ls, const void *name, int len,
			uint32_t hash, int dir_nodeid, int from_nodeid,
			unsigned int flags, struct dlm_rsb **r_ret)
{
	struct dlm_rsb *r = NULL;
	int our_nodeid = dlm_our_nodeid();
	int from_local = 0;
	int from_other = 0;
	int from_dir = 0;
	int create = 0;
	int error;

	if (flags & R_RECEIVE_REQUEST) {
		if (from_nodeid == dir_nodeid)
			from_dir = 1;
		else
			from_other = 1;
	} else if (flags & R_REQUEST) {
		from_local = 1;
	}

	/*
	 * flags & R_RECEIVE_RECOVER is from dlm_recover_master_copy, so
	 * from_nodeid has sent us a lock in dlm_recover_locks, believing
	 * we're the new master.  Our local recovery may not have set
	 * res_master_nodeid to our_nodeid yet, so allow either.  Don't
	 * create the rsb; dlm_recover_process_copy() will handle EBADR
	 * by resending.
	 *
	 * If someone sends us a request, we are the dir node, and we do
	 * not find the rsb anywhere, then recreate it.  This happens if
	 * someone sends us a request after we have removed/freed an rsb.
	 * (They sent a request instead of lookup because they are using
	 * an rsb taken from their scan list.)
	 */

	if (from_local || from_dir ||
	    (from_other && (dir_nodeid == our_nodeid))) {
		create = 1;
	}

 retry:
	error = dlm_search_rsb_tree(&ls->ls_rsbtbl, name, len, &r);
	if (error)
		goto do_new;

	/* check if the rsb is active under read lock - likely path */
	read_lock_bh(&ls->ls_rsbtbl_lock);
	if (!rsb_flag(r, RSB_HASHED)) {
		read_unlock_bh(&ls->ls_rsbtbl_lock);
		error = -EBADR;
		goto do_new;
	}
	
	/*
	 * rsb is active, so we can't check master_nodeid without lock_rsb.
	 */

	if (rsb_flag(r, RSB_INACTIVE)) {
		read_unlock_bh(&ls->ls_rsbtbl_lock);
		goto do_inactive;
	}

	kref_get(&r->res_ref);
	read_unlock_bh(&ls->ls_rsbtbl_lock);
	goto out;


 do_inactive:
	write_lock_bh(&ls->ls_rsbtbl_lock);

	/*
	 * The expectation here is that the rsb will have HASHED and
	 * INACTIVE flags set, and that the rsb can be moved from
	 * inactive back to active again.  However, between releasing
	 * the read lock and acquiring the write lock, this rsb could
	 * have been removed from rsbtbl, and had HASHED cleared, to
	 * be freed.  To deal with this case, we would normally need
	 * to repeat dlm_search_rsb_tree while holding the write lock,
	 * but rcu allows us to simply check the HASHED flag, because
	 * the rcu read lock means the rsb will not be freed yet.
	 * If the HASHED flag is not set, then the rsb is being freed,
	 * so we add a new rsb struct.  If the HASHED flag is set,
	 * and INACTIVE is not set, it means another thread has
	 * made the rsb active, as we're expecting to do here, and
	 * we just repeat the lookup (this will be very unlikely.)
	 */
	if (rsb_flag(r, RSB_HASHED)) {
		if (!rsb_flag(r, RSB_INACTIVE)) {
			write_unlock_bh(&ls->ls_rsbtbl_lock);
			goto retry;
		}
	} else {
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		error = -EBADR;
		goto do_new;
	}

	/*
	 * rsb found inactive (master_nodeid may be out of date unless
	 * we are the dir_nodeid or were the master)  No other thread
	 * is using this rsb because it's inactive, so we can
	 * look at or update res_master_nodeid without lock_rsb.
	 */

	if ((r->res_master_nodeid != our_nodeid) && from_other) {
		/* our rsb was not master, and another node (not the dir node)
		   has sent us a request */
		log_debug(ls, "find_rsb inactive from_other %d master %d dir %d %s",
			  from_nodeid, r->res_master_nodeid, dir_nodeid,
			  r->res_name);
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		error = -ENOTBLK;
		goto out;
	}

	if ((r->res_master_nodeid != our_nodeid) && from_dir) {
		/* don't think this should ever happen */
		log_error(ls, "find_rsb inactive from_dir %d master %d",
			  from_nodeid, r->res_master_nodeid);
		dlm_print_rsb(r);
		/* fix it and go on */
		r->res_master_nodeid = our_nodeid;
		r->res_nodeid = 0;
		rsb_clear_flag(r, RSB_MASTER_UNCERTAIN);
		r->res_first_lkid = 0;
	}

	if (from_local && (r->res_master_nodeid != our_nodeid)) {
		/* Because we have held no locks on this rsb,
		   res_master_nodeid could have become stale. */
		rsb_set_flag(r, RSB_MASTER_UNCERTAIN);
		r->res_first_lkid = 0;
	}

	/* we always deactivate scan timer for the rsb, when
	 * we move it out of the inactive state as rsb state
	 * can be changed and scan timers are only for inactive
	 * rsbs.
	 */
	del_scan(ls, r);
	list_move(&r->res_slow_list, &ls->ls_slow_active);
	rsb_clear_flag(r, RSB_INACTIVE);
	kref_init(&r->res_ref); /* ref is now used in active state */
	write_unlock_bh(&ls->ls_rsbtbl_lock);

	goto out;


 do_new:
	/*
	 * rsb not found
	 */

	if (error == -EBADR && !create)
		goto out;

	error = get_rsb_struct(ls, name, len, &r);
	if (WARN_ON_ONCE(error))
		goto out;

	r->res_hash = hash;
	r->res_dir_nodeid = dir_nodeid;
	kref_init(&r->res_ref);

	if (from_dir) {
		/* want to see how often this happens */
		log_debug(ls, "find_rsb new from_dir %d recreate %s",
			  from_nodeid, r->res_name);
		r->res_master_nodeid = our_nodeid;
		r->res_nodeid = 0;
		goto out_add;
	}

	if (from_other && (dir_nodeid != our_nodeid)) {
		/* should never happen */
		log_error(ls, "find_rsb new from_other %d dir %d our %d %s",
			  from_nodeid, dir_nodeid, our_nodeid, r->res_name);
		dlm_free_rsb(r);
		r = NULL;
		error = -ENOTBLK;
		goto out;
	}

	if (from_other) {
		log_debug(ls, "find_rsb new from_other %d dir %d %s",
			  from_nodeid, dir_nodeid, r->res_name);
	}

	if (dir_nodeid == our_nodeid) {
		/* When we are the dir nodeid, we can set the master
		   node immediately */
		r->res_master_nodeid = our_nodeid;
		r->res_nodeid = 0;
	} else {
		/* set_master will send_lookup to dir_nodeid */
		r->res_master_nodeid = 0;
		r->res_nodeid = -1;
	}

 out_add:

	write_lock_bh(&ls->ls_rsbtbl_lock);
	error = rsb_insert(r, &ls->ls_rsbtbl);
	if (error == -EEXIST) {
		/* somebody else was faster and it seems the
		 * rsb exists now, we do a whole relookup
		 */
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		dlm_free_rsb(r);
		goto retry;
	} else if (!error) {
		list_add(&r->res_slow_list, &ls->ls_slow_active);
	}
	write_unlock_bh(&ls->ls_rsbtbl_lock);
 out:
	*r_ret = r;
	return error;
}

/* During recovery, other nodes can send us new MSTCPY locks (from
   dlm_recover_locks) before we've made ourself master (in
   dlm_recover_masters). */

static int find_rsb_nodir(struct dlm_ls *ls, const void *name, int len,
			  uint32_t hash, int dir_nodeid, int from_nodeid,
			  unsigned int flags, struct dlm_rsb **r_ret)
{
	struct dlm_rsb *r = NULL;
	int our_nodeid = dlm_our_nodeid();
	int recover = (flags & R_RECEIVE_RECOVER);
	int error;

 retry:
	error = dlm_search_rsb_tree(&ls->ls_rsbtbl, name, len, &r);
	if (error)
		goto do_new;

	/* check if the rsb is in active state under read lock - likely path */
	read_lock_bh(&ls->ls_rsbtbl_lock);
	if (!rsb_flag(r, RSB_HASHED)) {
		read_unlock_bh(&ls->ls_rsbtbl_lock);
		goto do_new;
	}

	if (rsb_flag(r, RSB_INACTIVE)) {
		read_unlock_bh(&ls->ls_rsbtbl_lock);
		goto do_inactive;
	}

	/*
	 * rsb is active, so we can't check master_nodeid without lock_rsb.
	 */

	kref_get(&r->res_ref);
	read_unlock_bh(&ls->ls_rsbtbl_lock);

	goto out;


 do_inactive:
	write_lock_bh(&ls->ls_rsbtbl_lock);

	/* See comment in find_rsb_dir. */
	if (rsb_flag(r, RSB_HASHED)) {
		if (!rsb_flag(r, RSB_INACTIVE)) {
			write_unlock_bh(&ls->ls_rsbtbl_lock);
			goto retry;
		}
	} else {
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		goto do_new;
	}


	/*
	 * rsb found inactive. No other thread is using this rsb because
	 * it's inactive, so we can look at or update res_master_nodeid
	 * without lock_rsb.
	 */

	if (!recover && (r->res_master_nodeid != our_nodeid) && from_nodeid) {
		/* our rsb is not master, and another node has sent us a
		   request; this should never happen */
		log_error(ls, "find_rsb inactive from_nodeid %d master %d dir %d",
			  from_nodeid, r->res_master_nodeid, dir_nodeid);
		dlm_print_rsb(r);
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		error = -ENOTBLK;
		goto out;
	}

	if (!recover && (r->res_master_nodeid != our_nodeid) &&
	    (dir_nodeid == our_nodeid)) {
		/* our rsb is not master, and we are dir; may as well fix it;
		   this should never happen */
		log_error(ls, "find_rsb inactive our %d master %d dir %d",
			  our_nodeid, r->res_master_nodeid, dir_nodeid);
		dlm_print_rsb(r);
		r->res_master_nodeid = our_nodeid;
		r->res_nodeid = 0;
	}

	del_scan(ls, r);
	list_move(&r->res_slow_list, &ls->ls_slow_active);
	rsb_clear_flag(r, RSB_INACTIVE);
	kref_init(&r->res_ref);
	write_unlock_bh(&ls->ls_rsbtbl_lock);

	goto out;


 do_new:
	/*
	 * rsb not found
	 */

	error = get_rsb_struct(ls, name, len, &r);
	if (WARN_ON_ONCE(error))
		goto out;

	r->res_hash = hash;
	r->res_dir_nodeid = dir_nodeid;
	r->res_master_nodeid = dir_nodeid;
	r->res_nodeid = (dir_nodeid == our_nodeid) ? 0 : dir_nodeid;
	kref_init(&r->res_ref);

	write_lock_bh(&ls->ls_rsbtbl_lock);
	error = rsb_insert(r, &ls->ls_rsbtbl);
	if (error == -EEXIST) {
		/* somebody else was faster and it seems the
		 * rsb exists now, we do a whole relookup
		 */
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		dlm_free_rsb(r);
		goto retry;
	} else if (!error) {
		list_add(&r->res_slow_list, &ls->ls_slow_active);
	}
	write_unlock_bh(&ls->ls_rsbtbl_lock);

 out:
	*r_ret = r;
	return error;
}

/*
 * rsb rcu usage
 *
 * While rcu read lock is held, the rsb cannot be freed,
 * which allows a lookup optimization.
 *
 * Two threads are accessing the same rsb concurrently,
 * the first (A) is trying to use the rsb, the second (B)
 * is trying to free the rsb.
 *
 * thread A                 thread B
 * (trying to use rsb)      (trying to free rsb)
 *
 * A1. rcu read lock
 * A2. rsbtbl read lock
 * A3. look up rsb in rsbtbl
 * A4. rsbtbl read unlock
 *                          B1. rsbtbl write lock
 *                          B2. look up rsb in rsbtbl
 *                          B3. remove rsb from rsbtbl
 *                          B4. clear rsb HASHED flag
 *                          B5. rsbtbl write unlock
 *                          B6. begin freeing rsb using rcu...
 *
 * (rsb is inactive, so try to make it active again)
 * A5. read rsb HASHED flag (safe because rsb is not freed yet)
 * A6. the rsb HASHED flag is not set, which it means the rsb
 *     is being removed from rsbtbl and freed, so don't use it.
 * A7. rcu read unlock
 *
 *                          B7. ...finish freeing rsb using rcu
 * A8. create a new rsb
 *
 * Without the rcu optimization, steps A5-8 would need to do
 * an extra rsbtbl lookup:
 * A5. rsbtbl write lock
 * A6. look up rsb in rsbtbl, not found
 * A7. rsbtbl write unlock
 * A8. create a new rsb
 */

static int find_rsb(struct dlm_ls *ls, const void *name, int len,
		    int from_nodeid, unsigned int flags,
		    struct dlm_rsb **r_ret)
{
	int dir_nodeid;
	uint32_t hash;
	int rv;

	if (len > DLM_RESNAME_MAXLEN)
		return -EINVAL;

	hash = jhash(name, len, 0);
	dir_nodeid = dlm_hash2nodeid(ls, hash);

	rcu_read_lock();
	if (dlm_no_directory(ls))
		rv = find_rsb_nodir(ls, name, len, hash, dir_nodeid,
				      from_nodeid, flags, r_ret);
	else
		rv = find_rsb_dir(ls, name, len, hash, dir_nodeid,
				    from_nodeid, flags, r_ret);
	rcu_read_unlock();
	return rv;
}

/* we have received a request and found that res_master_nodeid != our_nodeid,
   so we need to return an error or make ourself the master */

static int validate_master_nodeid(struct dlm_ls *ls, struct dlm_rsb *r,
				  int from_nodeid)
{
	if (dlm_no_directory(ls)) {
		log_error(ls, "find_rsb keep from_nodeid %d master %d dir %d",
			  from_nodeid, r->res_master_nodeid,
			  r->res_dir_nodeid);
		dlm_print_rsb(r);
		return -ENOTBLK;
	}

	if (from_nodeid != r->res_dir_nodeid) {
		/* our rsb is not master, and another node (not the dir node)
	   	   has sent us a request.  this is much more common when our
	   	   master_nodeid is zero, so limit debug to non-zero.  */

		if (r->res_master_nodeid) {
			log_debug(ls, "validate master from_other %d master %d "
				  "dir %d first %x %s", from_nodeid,
				  r->res_master_nodeid, r->res_dir_nodeid,
				  r->res_first_lkid, r->res_name);
		}
		return -ENOTBLK;
	} else {
		/* our rsb is not master, but the dir nodeid has sent us a
	   	   request; this could happen with master 0 / res_nodeid -1 */

		if (r->res_master_nodeid) {
			log_error(ls, "validate master from_dir %d master %d "
				  "first %x %s",
				  from_nodeid, r->res_master_nodeid,
				  r->res_first_lkid, r->res_name);
		}

		r->res_master_nodeid = dlm_our_nodeid();
		r->res_nodeid = 0;
		return 0;
	}
}

static void __dlm_master_lookup(struct dlm_ls *ls, struct dlm_rsb *r, int our_nodeid,
				int from_nodeid, bool is_inactive, unsigned int flags,
				int *r_nodeid, int *result)
{
	int fix_master = (flags & DLM_LU_RECOVER_MASTER);
	int from_master = (flags & DLM_LU_RECOVER_DIR);

	if (r->res_dir_nodeid != our_nodeid) {
		/* should not happen, but may as well fix it and carry on */
		log_error(ls, "%s res_dir %d our %d %s", __func__,
			  r->res_dir_nodeid, our_nodeid, r->res_name);
		r->res_dir_nodeid = our_nodeid;
	}

	if (fix_master && r->res_master_nodeid && dlm_is_removed(ls, r->res_master_nodeid)) {
		/* Recovery uses this function to set a new master when
		 * the previous master failed.  Setting NEW_MASTER will
		 * force dlm_recover_masters to call recover_master on this
		 * rsb even though the res_nodeid is no longer removed.
		 */

		r->res_master_nodeid = from_nodeid;
		r->res_nodeid = from_nodeid;
		rsb_set_flag(r, RSB_NEW_MASTER);

		if (is_inactive) {
			/* I don't think we should ever find it inactive. */
			log_error(ls, "%s fix_master inactive", __func__);
			dlm_dump_rsb(r);
		}
	}

	if (from_master && (r->res_master_nodeid != from_nodeid)) {
		/* this will happen if from_nodeid became master during
		 * a previous recovery cycle, and we aborted the previous
		 * cycle before recovering this master value
		 */

		log_limit(ls, "%s from_master %d master_nodeid %d res_nodeid %d first %x %s",
			  __func__, from_nodeid, r->res_master_nodeid,
			  r->res_nodeid, r->res_first_lkid, r->res_name);

		if (r->res_master_nodeid == our_nodeid) {
			log_error(ls, "from_master %d our_master", from_nodeid);
			dlm_dump_rsb(r);
			goto ret_assign;
		}

		r->res_master_nodeid = from_nodeid;
		r->res_nodeid = from_nodeid;
		rsb_set_flag(r, RSB_NEW_MASTER);
	}

	if (!r->res_master_nodeid) {
		/* this will happen if recovery happens while we're looking
		 * up the master for this rsb
		 */

		log_debug(ls, "%s master 0 to %d first %x %s", __func__,
			  from_nodeid, r->res_first_lkid, r->res_name);
		r->res_master_nodeid = from_nodeid;
		r->res_nodeid = from_nodeid;
	}

	if (!from_master && !fix_master &&
	    (r->res_master_nodeid == from_nodeid)) {
		/* this can happen when the master sends remove, the dir node
		 * finds the rsb on the active list and ignores the remove,
		 * and the former master sends a lookup
		 */

		log_limit(ls, "%s from master %d flags %x first %x %s",
			  __func__, from_nodeid, flags, r->res_first_lkid,
			  r->res_name);
	}

 ret_assign:
	*r_nodeid = r->res_master_nodeid;
	if (result)
		*result = DLM_LU_MATCH;
}

/*
 * We're the dir node for this res and another node wants to know the
 * master nodeid.  During normal operation (non recovery) this is only
 * called from receive_lookup(); master lookups when the local node is
 * the dir node are done by find_rsb().
 *
 * normal operation, we are the dir node for a resource
 * . _request_lock
 * . set_master
 * . send_lookup
 * . receive_lookup
 * . dlm_master_lookup flags 0
 *
 * recover directory, we are rebuilding dir for all resources
 * . dlm_recover_directory
 * . dlm_rcom_names
 *   remote node sends back the rsb names it is master of and we are dir of
 * . dlm_master_lookup RECOVER_DIR (fix_master 0, from_master 1)
 *   we either create new rsb setting remote node as master, or find existing
 *   rsb and set master to be the remote node.
 *
 * recover masters, we are finding the new master for resources
 * . dlm_recover_masters
 * . recover_master
 * . dlm_send_rcom_lookup
 * . receive_rcom_lookup
 * . dlm_master_lookup RECOVER_MASTER (fix_master 1, from_master 0)
 */

static int _dlm_master_lookup(struct dlm_ls *ls, int from_nodeid, const char *name,
			      int len, unsigned int flags, int *r_nodeid, int *result)
{
	struct dlm_rsb *r = NULL;
	uint32_t hash;
	int our_nodeid = dlm_our_nodeid();
	int dir_nodeid, error;

	if (len > DLM_RESNAME_MAXLEN)
		return -EINVAL;

	if (from_nodeid == our_nodeid) {
		log_error(ls, "dlm_master_lookup from our_nodeid %d flags %x",
			  our_nodeid, flags);
		return -EINVAL;
	}

	hash = jhash(name, len, 0);
	dir_nodeid = dlm_hash2nodeid(ls, hash);
	if (dir_nodeid != our_nodeid) {
		log_error(ls, "dlm_master_lookup from %d dir %d our %d h %x %d",
			  from_nodeid, dir_nodeid, our_nodeid, hash,
			  ls->ls_num_nodes);
		*r_nodeid = -1;
		return -EINVAL;
	}

 retry:
	error = dlm_search_rsb_tree(&ls->ls_rsbtbl, name, len, &r);
	if (error)
		goto not_found;

	/* check if the rsb is active under read lock - likely path */
	read_lock_bh(&ls->ls_rsbtbl_lock);
	if (!rsb_flag(r, RSB_HASHED)) {
		read_unlock_bh(&ls->ls_rsbtbl_lock);
		goto not_found;
	}

	if (rsb_flag(r, RSB_INACTIVE)) {
		read_unlock_bh(&ls->ls_rsbtbl_lock);
		goto do_inactive;
	}

	/* because the rsb is active, we need to lock_rsb before
	 * checking/changing re_master_nodeid
	 */

	hold_rsb(r);
	read_unlock_bh(&ls->ls_rsbtbl_lock);
	lock_rsb(r);

	__dlm_master_lookup(ls, r, our_nodeid, from_nodeid, false,
			    flags, r_nodeid, result);

	/* the rsb was active */
	unlock_rsb(r);
	put_rsb(r);

	return 0;

 do_inactive:
	/* unlikely path - check if still part of ls_rsbtbl */
	write_lock_bh(&ls->ls_rsbtbl_lock);

	/* see comment in find_rsb_dir */
	if (rsb_flag(r, RSB_HASHED)) {
		if (!rsb_flag(r, RSB_INACTIVE)) {
			write_unlock_bh(&ls->ls_rsbtbl_lock);
			/* something as changed, very unlikely but
			 * try again
			 */
			goto retry;
		}
	} else {
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		goto not_found;
	}

	/* because the rsb is inactive, it's not refcounted and lock_rsb
	   is not used, but is protected by the rsbtbl lock */

	__dlm_master_lookup(ls, r, our_nodeid, from_nodeid, true, flags,
			    r_nodeid, result);

	/* A dir record rsb should never be on scan list.
	 * Except when we are the dir and master node.
	 * This function should only be called by the dir
	 * node.
	 */
	WARN_ON(!list_empty(&r->res_scan_list) &&
		r->res_master_nodeid != our_nodeid);

	write_unlock_bh(&ls->ls_rsbtbl_lock);

	return 0;

 not_found:
	error = get_rsb_struct(ls, name, len, &r);
	if (WARN_ON_ONCE(error))
		goto out;

	r->res_hash = hash;
	r->res_dir_nodeid = our_nodeid;
	r->res_master_nodeid = from_nodeid;
	r->res_nodeid = from_nodeid;
	rsb_set_flag(r, RSB_INACTIVE);

	write_lock_bh(&ls->ls_rsbtbl_lock);
	error = rsb_insert(r, &ls->ls_rsbtbl);
	if (error == -EEXIST) {
		/* somebody else was faster and it seems the
		 * rsb exists now, we do a whole relookup
		 */
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		dlm_free_rsb(r);
		goto retry;
	} else if (error) {
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		/* should never happen */
		dlm_free_rsb(r);
		goto retry;
	}

	list_add(&r->res_slow_list, &ls->ls_slow_inactive);
	write_unlock_bh(&ls->ls_rsbtbl_lock);

	if (result)
		*result = DLM_LU_ADD;
	*r_nodeid = from_nodeid;
 out:
	return error;
}

int dlm_master_lookup(struct dlm_ls *ls, int from_nodeid, const char *name,
		      int len, unsigned int flags, int *r_nodeid, int *result)
{
	int rv;
	rcu_read_lock();
	rv = _dlm_master_lookup(ls, from_nodeid, name, len, flags, r_nodeid, result);
	rcu_read_unlock();
	return rv;
}

static void dlm_dump_rsb_hash(struct dlm_ls *ls, uint32_t hash)
{
	struct dlm_rsb *r;

	read_lock_bh(&ls->ls_rsbtbl_lock);
	list_for_each_entry(r, &ls->ls_slow_active, res_slow_list) {
		if (r->res_hash == hash)
			dlm_dump_rsb(r);
	}
	read_unlock_bh(&ls->ls_rsbtbl_lock);
}

void dlm_dump_rsb_name(struct dlm_ls *ls, const char *name, int len)
{
	struct dlm_rsb *r = NULL;
	int error;

	rcu_read_lock();
	error = dlm_search_rsb_tree(&ls->ls_rsbtbl, name, len, &r);
	if (!error)
		goto out;

	dlm_dump_rsb(r);
 out:
	rcu_read_unlock();
}

static void deactivate_rsb(struct kref *kref)
{
	struct dlm_rsb *r = container_of(kref, struct dlm_rsb, res_ref);
	struct dlm_ls *ls = r->res_ls;
	int our_nodeid = dlm_our_nodeid();

	DLM_ASSERT(list_empty(&r->res_root_list), dlm_print_rsb(r););
	rsb_set_flag(r, RSB_INACTIVE);
	list_move(&r->res_slow_list, &ls->ls_slow_inactive);

	/*
	 * When the rsb becomes unused, there are two possibilities:
	 * 1. Leave the inactive rsb in place (don't remove it).
	 * 2. Add it to the scan list to be removed.
	 *
	 * 1 is done when the rsb is acting as the dir record
	 * for a remotely mastered rsb.  The rsb must be left
	 * in place as an inactive rsb to act as the dir record.
	 *
	 * 2 is done when a) the rsb is not the master and not the
	 * dir record, b) when the rsb is both the master and the
	 * dir record, c) when the rsb is master but not dir record.
	 *
	 * (If no directory is used, the rsb can always be removed.)
	 */
	if (dlm_no_directory(ls) ||
	    (r->res_master_nodeid == our_nodeid ||
	     dlm_dir_nodeid(r) != our_nodeid))
		add_scan(ls, r);

	if (r->res_lvbptr) {
		dlm_free_lvb(r->res_lvbptr);
		r->res_lvbptr = NULL;
	}
}

void free_inactive_rsb(struct dlm_rsb *r)
{
	WARN_ON_ONCE(!rsb_flag(r, RSB_INACTIVE));

	DLM_ASSERT(list_empty(&r->res_lookup), dlm_dump_rsb(r););
	DLM_ASSERT(list_empty(&r->res_grantqueue), dlm_dump_rsb(r););
	DLM_ASSERT(list_empty(&r->res_convertqueue), dlm_dump_rsb(r););
	DLM_ASSERT(list_empty(&r->res_waitqueue), dlm_dump_rsb(r););
	DLM_ASSERT(list_empty(&r->res_root_list), dlm_dump_rsb(r););
	DLM_ASSERT(list_empty(&r->res_scan_list), dlm_dump_rsb(r););
	DLM_ASSERT(list_empty(&r->res_recover_list), dlm_dump_rsb(r););
	DLM_ASSERT(list_empty(&r->res_masters_list), dlm_dump_rsb(r););

	dlm_free_rsb(r);
}

/* Attaching/detaching lkb's from rsb's is for rsb reference counting.
   The rsb must exist as long as any lkb's for it do. */

static void attach_lkb(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	hold_rsb(r);
	lkb->lkb_resource = r;
}

static void detach_lkb(struct dlm_lkb *lkb)
{
	if (lkb->lkb_resource) {
		put_rsb(lkb->lkb_resource);
		lkb->lkb_resource = NULL;
	}
}

static int _create_lkb(struct dlm_ls *ls, struct dlm_lkb **lkb_ret,
		       unsigned long start, unsigned long end)
{
	struct xa_limit limit;
	struct dlm_lkb *lkb;
	int rv;

	limit.max = end;
	limit.min = start;

	lkb = dlm_allocate_lkb();
	if (!lkb)
		return -ENOMEM;

	lkb->lkb_last_bast_cb_mode = DLM_LOCK_IV;
	lkb->lkb_last_cast_cb_mode = DLM_LOCK_IV;
	lkb->lkb_last_cb_mode = DLM_LOCK_IV;
	lkb->lkb_nodeid = -1;
	lkb->lkb_grmode = DLM_LOCK_IV;
	kref_init(&lkb->lkb_ref);
	INIT_LIST_HEAD(&lkb->lkb_ownqueue);
	INIT_LIST_HEAD(&lkb->lkb_rsb_lookup);

	write_lock_bh(&ls->ls_lkbxa_lock);
	rv = xa_alloc(&ls->ls_lkbxa, &lkb->lkb_id, lkb, limit, GFP_ATOMIC);
	write_unlock_bh(&ls->ls_lkbxa_lock);

	if (rv < 0) {
		log_error(ls, "create_lkb xa error %d", rv);
		dlm_free_lkb(lkb);
		return rv;
	}

	*lkb_ret = lkb;
	return 0;
}

static int create_lkb(struct dlm_ls *ls, struct dlm_lkb **lkb_ret)
{
	return _create_lkb(ls, lkb_ret, 1, ULONG_MAX);
}

static int find_lkb(struct dlm_ls *ls, uint32_t lkid, struct dlm_lkb **lkb_ret)
{
	struct dlm_lkb *lkb;

	rcu_read_lock();
	lkb = xa_load(&ls->ls_lkbxa, lkid);
	if (lkb) {
		/* check if lkb is still part of lkbxa under lkbxa_lock as
		 * the lkb_ref is tight to the lkbxa data structure, see
		 * __put_lkb().
		 */
		read_lock_bh(&ls->ls_lkbxa_lock);
		if (kref_read(&lkb->lkb_ref))
			kref_get(&lkb->lkb_ref);
		else
			lkb = NULL;
		read_unlock_bh(&ls->ls_lkbxa_lock);
	}
	rcu_read_unlock();

	*lkb_ret = lkb;
	return lkb ? 0 : -ENOENT;
}

static void kill_lkb(struct kref *kref)
{
	struct dlm_lkb *lkb = container_of(kref, struct dlm_lkb, lkb_ref);

	/* All work is done after the return from kref_put() so we
	   can release the write_lock before the detach_lkb */

	DLM_ASSERT(!lkb->lkb_status, dlm_print_lkb(lkb););
}

/* __put_lkb() is used when an lkb may not have an rsb attached to
   it so we need to provide the lockspace explicitly */

static int __put_lkb(struct dlm_ls *ls, struct dlm_lkb *lkb)
{
	uint32_t lkid = lkb->lkb_id;
	int rv;

	rv = dlm_kref_put_write_lock_bh(&lkb->lkb_ref, kill_lkb,
					&ls->ls_lkbxa_lock);
	if (rv) {
		xa_erase(&ls->ls_lkbxa, lkid);
		write_unlock_bh(&ls->ls_lkbxa_lock);

		detach_lkb(lkb);

		/* for local/process lkbs, lvbptr points to caller's lksb */
		if (lkb->lkb_lvbptr && is_master_copy(lkb))
			dlm_free_lvb(lkb->lkb_lvbptr);
		dlm_free_lkb(lkb);
	}

	return rv;
}

int dlm_put_lkb(struct dlm_lkb *lkb)
{
	struct dlm_ls *ls;

	DLM_ASSERT(lkb->lkb_resource, dlm_print_lkb(lkb););
	DLM_ASSERT(lkb->lkb_resource->res_ls, dlm_print_lkb(lkb););

	ls = lkb->lkb_resource->res_ls;
	return __put_lkb(ls, lkb);
}

/* This is only called to add a reference when the code already holds
   a valid reference to the lkb, so there's no need for locking. */

static inline void hold_lkb(struct dlm_lkb *lkb)
{
	kref_get(&lkb->lkb_ref);
}

static void unhold_lkb_assert(struct kref *kref)
{
	struct dlm_lkb *lkb = container_of(kref, struct dlm_lkb, lkb_ref);

	DLM_ASSERT(false, dlm_print_lkb(lkb););
}

/* This is called when we need to remove a reference and are certain
   it's not the last ref.  e.g. del_lkb is always called between a
   find_lkb/put_lkb and is always the inverse of a previous add_lkb.
   put_lkb would work fine, but would involve unnecessary locking */

static inline void unhold_lkb(struct dlm_lkb *lkb)
{
	kref_put(&lkb->lkb_ref, unhold_lkb_assert);
}

static void lkb_add_ordered(struct list_head *new, struct list_head *head,
			    int mode)
{
	struct dlm_lkb *lkb = NULL, *iter;

	list_for_each_entry(iter, head, lkb_statequeue)
		if (iter->lkb_rqmode < mode) {
			lkb = iter;
			list_add_tail(new, &iter->lkb_statequeue);
			break;
		}

	if (!lkb)
		list_add_tail(new, head);
}

/* add/remove lkb to rsb's grant/convert/wait queue */

static void add_lkb(struct dlm_rsb *r, struct dlm_lkb *lkb, int status)
{
	kref_get(&lkb->lkb_ref);

	DLM_ASSERT(!lkb->lkb_status, dlm_print_lkb(lkb););

	lkb->lkb_timestamp = ktime_get();

	lkb->lkb_status = status;

	switch (status) {
	case DLM_LKSTS_WAITING:
		if (lkb->lkb_exflags & DLM_LKF_HEADQUE)
			list_add(&lkb->lkb_statequeue, &r->res_waitqueue);
		else
			list_add_tail(&lkb->lkb_statequeue, &r->res_waitqueue);
		break;
	case DLM_LKSTS_GRANTED:
		/* convention says granted locks kept in order of grmode */
		lkb_add_ordered(&lkb->lkb_statequeue, &r->res_grantqueue,
				lkb->lkb_grmode);
		break;
	case DLM_LKSTS_CONVERT:
		if (lkb->lkb_exflags & DLM_LKF_HEADQUE)
			list_add(&lkb->lkb_statequeue, &r->res_convertqueue);
		else
			list_add_tail(&lkb->lkb_statequeue,
				      &r->res_convertqueue);
		break;
	default:
		DLM_ASSERT(0, dlm_print_lkb(lkb); printk("sts=%d\n", status););
	}
}

static void del_lkb(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	lkb->lkb_status = 0;
	list_del(&lkb->lkb_statequeue);
	unhold_lkb(lkb);
}

static void move_lkb(struct dlm_rsb *r, struct dlm_lkb *lkb, int sts)
{
	del_lkb(r, lkb);
	add_lkb(r, lkb, sts);
}

static int msg_reply_type(int mstype)
{
	switch (mstype) {
	case DLM_MSG_REQUEST:
		return DLM_MSG_REQUEST_REPLY;
	case DLM_MSG_CONVERT:
		return DLM_MSG_CONVERT_REPLY;
	case DLM_MSG_UNLOCK:
		return DLM_MSG_UNLOCK_REPLY;
	case DLM_MSG_CANCEL:
		return DLM_MSG_CANCEL_REPLY;
	case DLM_MSG_LOOKUP:
		return DLM_MSG_LOOKUP_REPLY;
	}
	return -1;
}

/* add/remove lkb from global waiters list of lkb's waiting for
   a reply from a remote node */

static void add_to_waiters(struct dlm_lkb *lkb, int mstype, int to_nodeid)
{
	struct dlm_ls *ls = lkb->lkb_resource->res_ls;

	spin_lock_bh(&ls->ls_waiters_lock);
	if (lkb->lkb_wait_type || is_overlap_cancel(lkb)) {
		switch (mstype) {
		case DLM_MSG_UNLOCK:
			set_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags);
			break;
		case DLM_MSG_CANCEL:
			set_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags);
			break;
		default:
			/* should never happen as validate_lock_args() checks
			 * on lkb_wait_type and validate_unlock_args() only
			 * creates UNLOCK or CANCEL messages.
			 */
			WARN_ON_ONCE(1);
			goto out;
		}
		lkb->lkb_wait_count++;
		hold_lkb(lkb);

		log_debug(ls, "addwait %x cur %d overlap %d count %d f %x",
			  lkb->lkb_id, lkb->lkb_wait_type, mstype,
			  lkb->lkb_wait_count, dlm_iflags_val(lkb));
		goto out;
	}

	DLM_ASSERT(!lkb->lkb_wait_count,
		   dlm_print_lkb(lkb);
		   printk("wait_count %d\n", lkb->lkb_wait_count););

	lkb->lkb_wait_count++;
	lkb->lkb_wait_type = mstype;
	lkb->lkb_wait_nodeid = to_nodeid; /* for debugging */
	hold_lkb(lkb);
	list_add(&lkb->lkb_wait_reply, &ls->ls_waiters);
 out:
	spin_unlock_bh(&ls->ls_waiters_lock);
}

/* We clear the RESEND flag because we might be taking an lkb off the waiters
   list as part of process_requestqueue (e.g. a lookup that has an optimized
   request reply on the requestqueue) between dlm_recover_waiters_pre() which
   set RESEND and dlm_recover_waiters_post() */

static int _remove_from_waiters(struct dlm_lkb *lkb, int mstype,
				const struct dlm_message *ms)
{
	struct dlm_ls *ls = lkb->lkb_resource->res_ls;
	int overlap_done = 0;

	if (mstype == DLM_MSG_UNLOCK_REPLY &&
	    test_and_clear_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags)) {
		log_debug(ls, "remwait %x unlock_reply overlap", lkb->lkb_id);
		overlap_done = 1;
		goto out_del;
	}

	if (mstype == DLM_MSG_CANCEL_REPLY &&
	    test_and_clear_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags)) {
		log_debug(ls, "remwait %x cancel_reply overlap", lkb->lkb_id);
		overlap_done = 1;
		goto out_del;
	}

	/* Cancel state was preemptively cleared by a successful convert,
	   see next comment, nothing to do. */

	if ((mstype == DLM_MSG_CANCEL_REPLY) &&
	    (lkb->lkb_wait_type != DLM_MSG_CANCEL)) {
		log_debug(ls, "remwait %x cancel_reply wait_type %d",
			  lkb->lkb_id, lkb->lkb_wait_type);
		return -1;
	}

	/* Remove for the convert reply, and premptively remove for the
	   cancel reply.  A convert has been granted while there's still
	   an outstanding cancel on it (the cancel is moot and the result
	   in the cancel reply should be 0).  We preempt the cancel reply
	   because the app gets the convert result and then can follow up
	   with another op, like convert.  This subsequent op would see the
	   lingering state of the cancel and fail with -EBUSY. */

	if ((mstype == DLM_MSG_CONVERT_REPLY) &&
	    (lkb->lkb_wait_type == DLM_MSG_CONVERT) && ms && !ms->m_result &&
	    test_and_clear_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags)) {
		log_debug(ls, "remwait %x convert_reply zap overlap_cancel",
			  lkb->lkb_id);
		lkb->lkb_wait_type = 0;
		lkb->lkb_wait_count--;
		unhold_lkb(lkb);
		goto out_del;
	}

	/* N.B. type of reply may not always correspond to type of original
	   msg due to lookup->request optimization, verify others? */

	if (lkb->lkb_wait_type) {
		lkb->lkb_wait_type = 0;
		goto out_del;
	}

	log_error(ls, "remwait error %x remote %d %x msg %d flags %x no wait",
		  lkb->lkb_id, ms ? le32_to_cpu(ms->m_header.h_nodeid) : 0,
		  lkb->lkb_remid, mstype, dlm_iflags_val(lkb));
	return -1;

 out_del:
	/* the force-unlock/cancel has completed and we haven't recvd a reply
	   to the op that was in progress prior to the unlock/cancel; we
	   give up on any reply to the earlier op.  FIXME: not sure when/how
	   this would happen */

	if (overlap_done && lkb->lkb_wait_type) {
		log_error(ls, "remwait error %x reply %d wait_type %d overlap",
			  lkb->lkb_id, mstype, lkb->lkb_wait_type);
		lkb->lkb_wait_count--;
		unhold_lkb(lkb);
		lkb->lkb_wait_type = 0;
	}

	DLM_ASSERT(lkb->lkb_wait_count, dlm_print_lkb(lkb););

	clear_bit(DLM_IFL_RESEND_BIT, &lkb->lkb_iflags);
	lkb->lkb_wait_count--;
	if (!lkb->lkb_wait_count)
		list_del_init(&lkb->lkb_wait_reply);
	unhold_lkb(lkb);
	return 0;
}

static int remove_from_waiters(struct dlm_lkb *lkb, int mstype)
{
	struct dlm_ls *ls = lkb->lkb_resource->res_ls;
	int error;

	spin_lock_bh(&ls->ls_waiters_lock);
	error = _remove_from_waiters(lkb, mstype, NULL);
	spin_unlock_bh(&ls->ls_waiters_lock);
	return error;
}

/* Handles situations where we might be processing a "fake" or "local" reply in
 * the recovery context which stops any locking activity. Only debugfs might
 * change the lockspace waiters but they will held the recovery lock to ensure
 * remove_from_waiters_ms() in local case will be the only user manipulating the
 * lockspace waiters in recovery context.
 */

static int remove_from_waiters_ms(struct dlm_lkb *lkb,
				  const struct dlm_message *ms, bool local)
{
	struct dlm_ls *ls = lkb->lkb_resource->res_ls;
	int error;

	if (!local)
		spin_lock_bh(&ls->ls_waiters_lock);
	else
		WARN_ON_ONCE(!rwsem_is_locked(&ls->ls_in_recovery) ||
			     !dlm_locking_stopped(ls));
	error = _remove_from_waiters(lkb, le32_to_cpu(ms->m_type), ms);
	if (!local)
		spin_unlock_bh(&ls->ls_waiters_lock);
	return error;
}

/* lkb is master or local copy */

static void set_lvb_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int b, len = r->res_ls->ls_lvblen;

	/* b=1 lvb returned to caller
	   b=0 lvb written to rsb or invalidated
	   b=-1 do nothing */

	b =  dlm_lvb_operations[lkb->lkb_grmode + 1][lkb->lkb_rqmode + 1];

	if (b == 1) {
		if (!lkb->lkb_lvbptr)
			return;

		if (!(lkb->lkb_exflags & DLM_LKF_VALBLK))
			return;

		if (!r->res_lvbptr)
			return;

		memcpy(lkb->lkb_lvbptr, r->res_lvbptr, len);
		lkb->lkb_lvbseq = r->res_lvbseq;

	} else if (b == 0) {
		if (lkb->lkb_exflags & DLM_LKF_IVVALBLK) {
			rsb_set_flag(r, RSB_VALNOTVALID);
			return;
		}

		if (!lkb->lkb_lvbptr)
			return;

		if (!(lkb->lkb_exflags & DLM_LKF_VALBLK))
			return;

		if (!r->res_lvbptr)
			r->res_lvbptr = dlm_allocate_lvb(r->res_ls);

		if (!r->res_lvbptr)
			return;

		memcpy(r->res_lvbptr, lkb->lkb_lvbptr, len);
		r->res_lvbseq++;
		lkb->lkb_lvbseq = r->res_lvbseq;
		rsb_clear_flag(r, RSB_VALNOTVALID);
	}

	if (rsb_flag(r, RSB_VALNOTVALID))
		set_bit(DLM_SBF_VALNOTVALID_BIT, &lkb->lkb_sbflags);
}

static void set_lvb_unlock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	if (lkb->lkb_grmode < DLM_LOCK_PW)
		return;

	if (lkb->lkb_exflags & DLM_LKF_IVVALBLK) {
		rsb_set_flag(r, RSB_VALNOTVALID);
		return;
	}

	if (!lkb->lkb_lvbptr)
		return;

	if (!(lkb->lkb_exflags & DLM_LKF_VALBLK))
		return;

	if (!r->res_lvbptr)
		r->res_lvbptr = dlm_allocate_lvb(r->res_ls);

	if (!r->res_lvbptr)
		return;

	memcpy(r->res_lvbptr, lkb->lkb_lvbptr, r->res_ls->ls_lvblen);
	r->res_lvbseq++;
	rsb_clear_flag(r, RSB_VALNOTVALID);
}

/* lkb is process copy (pc) */

static void set_lvb_lock_pc(struct dlm_rsb *r, struct dlm_lkb *lkb,
			    const struct dlm_message *ms)
{
	int b;

	if (!lkb->lkb_lvbptr)
		return;

	if (!(lkb->lkb_exflags & DLM_LKF_VALBLK))
		return;

	b = dlm_lvb_operations[lkb->lkb_grmode + 1][lkb->lkb_rqmode + 1];
	if (b == 1) {
		int len = receive_extralen(ms);
		if (len > r->res_ls->ls_lvblen)
			len = r->res_ls->ls_lvblen;
		memcpy(lkb->lkb_lvbptr, ms->m_extra, len);
		lkb->lkb_lvbseq = le32_to_cpu(ms->m_lvbseq);
	}
}

/* Manipulate lkb's on rsb's convert/granted/waiting queues
   remove_lock -- used for unlock, removes lkb from granted
   revert_lock -- used for cancel, moves lkb from convert to granted
   grant_lock  -- used for request and convert, adds lkb to granted or
                  moves lkb from convert or waiting to granted

   Each of these is used for master or local copy lkb's.  There is
   also a _pc() variation used to make the corresponding change on
   a process copy (pc) lkb. */

static void _remove_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	del_lkb(r, lkb);
	lkb->lkb_grmode = DLM_LOCK_IV;
	/* this unhold undoes the original ref from create_lkb()
	   so this leads to the lkb being freed */
	unhold_lkb(lkb);
}

static void remove_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	set_lvb_unlock(r, lkb);
	_remove_lock(r, lkb);
}

static void remove_lock_pc(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	_remove_lock(r, lkb);
}

/* returns: 0 did nothing
	    1 moved lock to granted
	   -1 removed lock */

static int revert_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int rv = 0;

	lkb->lkb_rqmode = DLM_LOCK_IV;

	switch (lkb->lkb_status) {
	case DLM_LKSTS_GRANTED:
		break;
	case DLM_LKSTS_CONVERT:
		move_lkb(r, lkb, DLM_LKSTS_GRANTED);
		rv = 1;
		break;
	case DLM_LKSTS_WAITING:
		del_lkb(r, lkb);
		lkb->lkb_grmode = DLM_LOCK_IV;
		/* this unhold undoes the original ref from create_lkb()
		   so this leads to the lkb being freed */
		unhold_lkb(lkb);
		rv = -1;
		break;
	default:
		log_print("invalid status for revert %d", lkb->lkb_status);
	}
	return rv;
}

static int revert_lock_pc(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	return revert_lock(r, lkb);
}

static void _grant_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	if (lkb->lkb_grmode != lkb->lkb_rqmode) {
		lkb->lkb_grmode = lkb->lkb_rqmode;
		if (lkb->lkb_status)
			move_lkb(r, lkb, DLM_LKSTS_GRANTED);
		else
			add_lkb(r, lkb, DLM_LKSTS_GRANTED);
	}

	lkb->lkb_rqmode = DLM_LOCK_IV;
	lkb->lkb_highbast = 0;
}

static void grant_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	set_lvb_lock(r, lkb);
	_grant_lock(r, lkb);
}

static void grant_lock_pc(struct dlm_rsb *r, struct dlm_lkb *lkb,
			  const struct dlm_message *ms)
{
	set_lvb_lock_pc(r, lkb, ms);
	_grant_lock(r, lkb);
}

/* called by grant_pending_locks() which means an async grant message must
   be sent to the requesting node in addition to granting the lock if the
   lkb belongs to a remote node. */

static void grant_lock_pending(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	grant_lock(r, lkb);
	if (is_master_copy(lkb))
		send_grant(r, lkb);
	else
		queue_cast(r, lkb, 0);
}

/* The special CONVDEADLK, ALTPR and ALTCW flags allow the master to
   change the granted/requested modes.  We're munging things accordingly in
   the process copy.
   CONVDEADLK: our grmode may have been forced down to NL to resolve a
   conversion deadlock
   ALTPR/ALTCW: our rqmode may have been changed to PR or CW to become
   compatible with other granted locks */

static void munge_demoted(struct dlm_lkb *lkb)
{
	if (lkb->lkb_rqmode == DLM_LOCK_IV || lkb->lkb_grmode == DLM_LOCK_IV) {
		log_print("munge_demoted %x invalid modes gr %d rq %d",
			  lkb->lkb_id, lkb->lkb_grmode, lkb->lkb_rqmode);
		return;
	}

	lkb->lkb_grmode = DLM_LOCK_NL;
}

static void munge_altmode(struct dlm_lkb *lkb, const struct dlm_message *ms)
{
	if (ms->m_type != cpu_to_le32(DLM_MSG_REQUEST_REPLY) &&
	    ms->m_type != cpu_to_le32(DLM_MSG_GRANT)) {
		log_print("munge_altmode %x invalid reply type %d",
			  lkb->lkb_id, le32_to_cpu(ms->m_type));
		return;
	}

	if (lkb->lkb_exflags & DLM_LKF_ALTPR)
		lkb->lkb_rqmode = DLM_LOCK_PR;
	else if (lkb->lkb_exflags & DLM_LKF_ALTCW)
		lkb->lkb_rqmode = DLM_LOCK_CW;
	else {
		log_print("munge_altmode invalid exflags %x", lkb->lkb_exflags);
		dlm_print_lkb(lkb);
	}
}

static inline int first_in_list(struct dlm_lkb *lkb, struct list_head *head)
{
	struct dlm_lkb *first = list_entry(head->next, struct dlm_lkb,
					   lkb_statequeue);
	if (lkb->lkb_id == first->lkb_id)
		return 1;

	return 0;
}

/* Check if the given lkb conflicts with another lkb on the queue. */

static int queue_conflict(struct list_head *head, struct dlm_lkb *lkb)
{
	struct dlm_lkb *this;

	list_for_each_entry(this, head, lkb_statequeue) {
		if (this == lkb)
			continue;
		if (!modes_compat(this, lkb))
			return 1;
	}
	return 0;
}

/*
 * "A conversion deadlock arises with a pair of lock requests in the converting
 * queue for one resource.  The granted mode of each lock blocks the requested
 * mode of the other lock."
 *
 * Part 2: if the granted mode of lkb is preventing an earlier lkb in the
 * convert queue from being granted, then deadlk/demote lkb.
 *
 * Example:
 * Granted Queue: empty
 * Convert Queue: NL->EX (first lock)
 *                PR->EX (second lock)
 *
 * The first lock can't be granted because of the granted mode of the second
 * lock and the second lock can't be granted because it's not first in the
 * list.  We either cancel lkb's conversion (PR->EX) and return EDEADLK, or we
 * demote the granted mode of lkb (from PR to NL) if it has the CONVDEADLK
 * flag set and return DEMOTED in the lksb flags.
 *
 * Originally, this function detected conv-deadlk in a more limited scope:
 * - if !modes_compat(lkb1, lkb2) && !modes_compat(lkb2, lkb1), or
 * - if lkb1 was the first entry in the queue (not just earlier), and was
 *   blocked by the granted mode of lkb2, and there was nothing on the
 *   granted queue preventing lkb1 from being granted immediately, i.e.
 *   lkb2 was the only thing preventing lkb1 from being granted.
 *
 * That second condition meant we'd only say there was conv-deadlk if
 * resolving it (by demotion) would lead to the first lock on the convert
 * queue being granted right away.  It allowed conversion deadlocks to exist
 * between locks on the convert queue while they couldn't be granted anyway.
 *
 * Now, we detect and take action on conversion deadlocks immediately when
 * they're created, even if they may not be immediately consequential.  If
 * lkb1 exists anywhere in the convert queue and lkb2 comes in with a granted
 * mode that would prevent lkb1's conversion from being granted, we do a
 * deadlk/demote on lkb2 right away and don't let it onto the convert queue.
 * I think this means that the lkb_is_ahead condition below should always
 * be zero, i.e. there will never be conv-deadlk between two locks that are
 * both already on the convert queue.
 */

static int conversion_deadlock_detect(struct dlm_rsb *r, struct dlm_lkb *lkb2)
{
	struct dlm_lkb *lkb1;
	int lkb_is_ahead = 0;

	list_for_each_entry(lkb1, &r->res_convertqueue, lkb_statequeue) {
		if (lkb1 == lkb2) {
			lkb_is_ahead = 1;
			continue;
		}

		if (!lkb_is_ahead) {
			if (!modes_compat(lkb2, lkb1))
				return 1;
		} else {
			if (!modes_compat(lkb2, lkb1) &&
			    !modes_compat(lkb1, lkb2))
				return 1;
		}
	}
	return 0;
}

/*
 * Return 1 if the lock can be granted, 0 otherwise.
 * Also detect and resolve conversion deadlocks.
 *
 * lkb is the lock to be granted
 *
 * now is 1 if the function is being called in the context of the
 * immediate request, it is 0 if called later, after the lock has been
 * queued.
 *
 * recover is 1 if dlm_recover_grant() is trying to grant conversions
 * after recovery.
 *
 * References are from chapter 6 of "VAXcluster Principles" by Roy Davis
 */

static int _can_be_granted(struct dlm_rsb *r, struct dlm_lkb *lkb, int now,
			   int recover)
{
	int8_t conv = (lkb->lkb_grmode != DLM_LOCK_IV);

	/*
	 * 6-10: Version 5.4 introduced an option to address the phenomenon of
	 * a new request for a NL mode lock being blocked.
	 *
	 * 6-11: If the optional EXPEDITE flag is used with the new NL mode
	 * request, then it would be granted.  In essence, the use of this flag
	 * tells the Lock Manager to expedite theis request by not considering
	 * what may be in the CONVERTING or WAITING queues...  As of this
	 * writing, the EXPEDITE flag can be used only with new requests for NL
	 * mode locks.  This flag is not valid for conversion requests.
	 *
	 * A shortcut.  Earlier checks return an error if EXPEDITE is used in a
	 * conversion or used with a non-NL requested mode.  We also know an
	 * EXPEDITE request is always granted immediately, so now must always
	 * be 1.  The full condition to grant an expedite request: (now &&
	 * !conv && lkb->rqmode == DLM_LOCK_NL && (flags & EXPEDITE)) can
	 * therefore be shortened to just checking the flag.
	 */

	if (lkb->lkb_exflags & DLM_LKF_EXPEDITE)
		return 1;

	/*
	 * A shortcut. Without this, !queue_conflict(grantqueue, lkb) would be
	 * added to the remaining conditions.
	 */

	if (queue_conflict(&r->res_grantqueue, lkb))
		return 0;

	/*
	 * 6-3: By default, a conversion request is immediately granted if the
	 * requested mode is compatible with the modes of all other granted
	 * locks
	 */

	if (queue_conflict(&r->res_convertqueue, lkb))
		return 0;

	/*
	 * The RECOVER_GRANT flag means dlm_recover_grant() is granting
	 * locks for a recovered rsb, on which lkb's have been rebuilt.
	 * The lkb's may have been rebuilt on the queues in a different
	 * order than they were in on the previous master.  So, granting
	 * queued conversions in order after recovery doesn't make sense
	 * since the order hasn't been preserved anyway.  The new order
	 * could also have created a new "in place" conversion deadlock.
	 * (e.g. old, failed master held granted EX, with PR->EX, NL->EX.
	 * After recovery, there would be no granted locks, and possibly
	 * NL->EX, PR->EX, an in-place conversion deadlock.)  So, after
	 * recovery, grant conversions without considering order.
	 */

	if (conv && recover)
		return 1;

	/*
	 * 6-5: But the default algorithm for deciding whether to grant or
	 * queue conversion requests does not by itself guarantee that such
	 * requests are serviced on a "first come first serve" basis.  This, in
	 * turn, can lead to a phenomenon known as "indefinate postponement".
	 *
	 * 6-7: This issue is dealt with by using the optional QUECVT flag with
	 * the system service employed to request a lock conversion.  This flag
	 * forces certain conversion requests to be queued, even if they are
	 * compatible with the granted modes of other locks on the same
	 * resource.  Thus, the use of this flag results in conversion requests
	 * being ordered on a "first come first servce" basis.
	 *
	 * DCT: This condition is all about new conversions being able to occur
	 * "in place" while the lock remains on the granted queue (assuming
	 * nothing else conflicts.)  IOW if QUECVT isn't set, a conversion
	 * doesn't _have_ to go onto the convert queue where it's processed in
	 * order.  The "now" variable is necessary to distinguish converts
	 * being received and processed for the first time now, because once a
	 * convert is moved to the conversion queue the condition below applies
	 * requiring fifo granting.
	 */

	if (now && conv && !(lkb->lkb_exflags & DLM_LKF_QUECVT))
		return 1;

	/*
	 * Even if the convert is compat with all granted locks,
	 * QUECVT forces it behind other locks on the convert queue.
	 */

	if (now && conv && (lkb->lkb_exflags & DLM_LKF_QUECVT)) {
		if (list_empty(&r->res_convertqueue))
			return 1;
		else
			return 0;
	}

	/*
	 * The NOORDER flag is set to avoid the standard vms rules on grant
	 * order.
	 */

	if (lkb->lkb_exflags & DLM_LKF_NOORDER)
		return 1;

	/*
	 * 6-3: Once in that queue [CONVERTING], a conversion request cannot be
	 * granted until all other conversion requests ahead of it are granted
	 * and/or canceled.
	 */

	if (!now && conv && first_in_list(lkb, &r->res_convertqueue))
		return 1;

	/*
	 * 6-4: By default, a new request is immediately granted only if all
	 * three of the following conditions are satisfied when the request is
	 * issued:
	 * - The queue of ungranted conversion requests for the resource is
	 *   empty.
	 * - The queue of ungranted new requests for the resource is empty.
	 * - The mode of the new request is compatible with the most
	 *   restrictive mode of all granted locks on the resource.
	 */

	if (now && !conv && list_empty(&r->res_convertqueue) &&
	    list_empty(&r->res_waitqueue))
		return 1;

	/*
	 * 6-4: Once a lock request is in the queue of ungranted new requests,
	 * it cannot be granted until the queue of ungranted conversion
	 * requests is empty, all ungranted new requests ahead of it are
	 * granted and/or canceled, and it is compatible with the granted mode
	 * of the most restrictive lock granted on the resource.
	 */

	if (!now && !conv && list_empty(&r->res_convertqueue) &&
	    first_in_list(lkb, &r->res_waitqueue))
		return 1;

	return 0;
}

static int can_be_granted(struct dlm_rsb *r, struct dlm_lkb *lkb, int now,
			  int recover, int *err)
{
	int rv;
	int8_t alt = 0, rqmode = lkb->lkb_rqmode;
	int8_t is_convert = (lkb->lkb_grmode != DLM_LOCK_IV);

	if (err)
		*err = 0;

	rv = _can_be_granted(r, lkb, now, recover);
	if (rv)
		goto out;

	/*
	 * The CONVDEADLK flag is non-standard and tells the dlm to resolve
	 * conversion deadlocks by demoting grmode to NL, otherwise the dlm
	 * cancels one of the locks.
	 */

	if (is_convert && can_be_queued(lkb) &&
	    conversion_deadlock_detect(r, lkb)) {
		if (lkb->lkb_exflags & DLM_LKF_CONVDEADLK) {
			lkb->lkb_grmode = DLM_LOCK_NL;
			set_bit(DLM_SBF_DEMOTED_BIT, &lkb->lkb_sbflags);
		} else if (err) {
			*err = -EDEADLK;
		} else {
			log_print("can_be_granted deadlock %x now %d",
				  lkb->lkb_id, now);
			dlm_dump_rsb(r);
		}
		goto out;
	}

	/*
	 * The ALTPR and ALTCW flags are non-standard and tell the dlm to try
	 * to grant a request in a mode other than the normal rqmode.  It's a
	 * simple way to provide a big optimization to applications that can
	 * use them.
	 */

	if (rqmode != DLM_LOCK_PR && (lkb->lkb_exflags & DLM_LKF_ALTPR))
		alt = DLM_LOCK_PR;
	else if (rqmode != DLM_LOCK_CW && (lkb->lkb_exflags & DLM_LKF_ALTCW))
		alt = DLM_LOCK_CW;

	if (alt) {
		lkb->lkb_rqmode = alt;
		rv = _can_be_granted(r, lkb, now, 0);
		if (rv)
			set_bit(DLM_SBF_ALTMODE_BIT, &lkb->lkb_sbflags);
		else
			lkb->lkb_rqmode = rqmode;
	}
 out:
	return rv;
}

/* Returns the highest requested mode of all blocked conversions; sets
   cw if there's a blocked conversion to DLM_LOCK_CW. */

static int grant_pending_convert(struct dlm_rsb *r, int high, int *cw,
				 unsigned int *count)
{
	struct dlm_lkb *lkb, *s;
	int recover = rsb_flag(r, RSB_RECOVER_GRANT);
	int hi, demoted, quit, grant_restart, demote_restart;
	int deadlk;

	quit = 0;
 restart:
	grant_restart = 0;
	demote_restart = 0;
	hi = DLM_LOCK_IV;

	list_for_each_entry_safe(lkb, s, &r->res_convertqueue, lkb_statequeue) {
		demoted = is_demoted(lkb);
		deadlk = 0;

		if (can_be_granted(r, lkb, 0, recover, &deadlk)) {
			grant_lock_pending(r, lkb);
			grant_restart = 1;
			if (count)
				(*count)++;
			continue;
		}

		if (!demoted && is_demoted(lkb)) {
			log_print("WARN: pending demoted %x node %d %s",
				  lkb->lkb_id, lkb->lkb_nodeid, r->res_name);
			demote_restart = 1;
			continue;
		}

		if (deadlk) {
			/*
			 * If DLM_LKB_NODLKWT flag is set and conversion
			 * deadlock is detected, we request blocking AST and
			 * down (or cancel) conversion.
			 */
			if (lkb->lkb_exflags & DLM_LKF_NODLCKWT) {
				if (lkb->lkb_highbast < lkb->lkb_rqmode) {
					queue_bast(r, lkb, lkb->lkb_rqmode);
					lkb->lkb_highbast = lkb->lkb_rqmode;
				}
			} else {
				log_print("WARN: pending deadlock %x node %d %s",
					  lkb->lkb_id, lkb->lkb_nodeid,
					  r->res_name);
				dlm_dump_rsb(r);
			}
			continue;
		}

		hi = max_t(int, lkb->lkb_rqmode, hi);

		if (cw && lkb->lkb_rqmode == DLM_LOCK_CW)
			*cw = 1;
	}

	if (grant_restart)
		goto restart;
	if (demote_restart && !quit) {
		quit = 1;
		goto restart;
	}

	return max_t(int, high, hi);
}

static int grant_pending_wait(struct dlm_rsb *r, int high, int *cw,
			      unsigned int *count)
{
	struct dlm_lkb *lkb, *s;

	list_for_each_entry_safe(lkb, s, &r->res_waitqueue, lkb_statequeue) {
		if (can_be_granted(r, lkb, 0, 0, NULL)) {
			grant_lock_pending(r, lkb);
			if (count)
				(*count)++;
		} else {
			high = max_t(int, lkb->lkb_rqmode, high);
			if (lkb->lkb_rqmode == DLM_LOCK_CW)
				*cw = 1;
		}
	}

	return high;
}

/* cw of 1 means there's a lock with a rqmode of DLM_LOCK_CW that's blocked
   on either the convert or waiting queue.
   high is the largest rqmode of all locks blocked on the convert or
   waiting queue. */

static int lock_requires_bast(struct dlm_lkb *gr, int high, int cw)
{
	if (gr->lkb_grmode == DLM_LOCK_PR && cw) {
		if (gr->lkb_highbast < DLM_LOCK_EX)
			return 1;
		return 0;
	}

	if (gr->lkb_highbast < high &&
	    !__dlm_compat_matrix[gr->lkb_grmode+1][high+1])
		return 1;
	return 0;
}

static void grant_pending_locks(struct dlm_rsb *r, unsigned int *count)
{
	struct dlm_lkb *lkb, *s;
	int high = DLM_LOCK_IV;
	int cw = 0;

	if (!is_master(r)) {
		log_print("grant_pending_locks r nodeid %d", r->res_nodeid);
		dlm_dump_rsb(r);
		return;
	}

	high = grant_pending_convert(r, high, &cw, count);
	high = grant_pending_wait(r, high, &cw, count);

	if (high == DLM_LOCK_IV)
		return;

	/*
	 * If there are locks left on the wait/convert queue then send blocking
	 * ASTs to granted locks based on the largest requested mode (high)
	 * found above.
	 */

	list_for_each_entry_safe(lkb, s, &r->res_grantqueue, lkb_statequeue) {
		if (lkb->lkb_bastfn && lock_requires_bast(lkb, high, cw)) {
			if (cw && high == DLM_LOCK_PR &&
			    lkb->lkb_grmode == DLM_LOCK_PR)
				queue_bast(r, lkb, DLM_LOCK_CW);
			else
				queue_bast(r, lkb, high);
			lkb->lkb_highbast = high;
		}
	}
}

static int modes_require_bast(struct dlm_lkb *gr, struct dlm_lkb *rq)
{
	if ((gr->lkb_grmode == DLM_LOCK_PR && rq->lkb_rqmode == DLM_LOCK_CW) ||
	    (gr->lkb_grmode == DLM_LOCK_CW && rq->lkb_rqmode == DLM_LOCK_PR)) {
		if (gr->lkb_highbast < DLM_LOCK_EX)
			return 1;
		return 0;
	}

	if (gr->lkb_highbast < rq->lkb_rqmode && !modes_compat(gr, rq))
		return 1;
	return 0;
}

static void send_bast_queue(struct dlm_rsb *r, struct list_head *head,
			    struct dlm_lkb *lkb)
{
	struct dlm_lkb *gr;

	list_for_each_entry(gr, head, lkb_statequeue) {
		/* skip self when sending basts to convertqueue */
		if (gr == lkb)
			continue;
		if (gr->lkb_bastfn && modes_require_bast(gr, lkb)) {
			queue_bast(r, gr, lkb->lkb_rqmode);
			gr->lkb_highbast = lkb->lkb_rqmode;
		}
	}
}

static void send_blocking_asts(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	send_bast_queue(r, &r->res_grantqueue, lkb);
}

static void send_blocking_asts_all(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	send_bast_queue(r, &r->res_grantqueue, lkb);
	send_bast_queue(r, &r->res_convertqueue, lkb);
}

/* set_master(r, lkb) -- set the master nodeid of a resource

   The purpose of this function is to set the nodeid field in the given
   lkb using the nodeid field in the given rsb.  If the rsb's nodeid is
   known, it can just be copied to the lkb and the function will return
   0.  If the rsb's nodeid is _not_ known, it needs to be looked up
   before it can be copied to the lkb.

   When the rsb nodeid is being looked up remotely, the initial lkb
   causing the lookup is kept on the ls_waiters list waiting for the
   lookup reply.  Other lkb's waiting for the same rsb lookup are kept
   on the rsb's res_lookup list until the master is verified.

   Return values:
   0: nodeid is set in rsb/lkb and the caller should go ahead and use it
   1: the rsb master is not available and the lkb has been placed on
      a wait queue
*/

static int set_master(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int our_nodeid = dlm_our_nodeid();

	if (rsb_flag(r, RSB_MASTER_UNCERTAIN)) {
		rsb_clear_flag(r, RSB_MASTER_UNCERTAIN);
		r->res_first_lkid = lkb->lkb_id;
		lkb->lkb_nodeid = r->res_nodeid;
		return 0;
	}

	if (r->res_first_lkid && r->res_first_lkid != lkb->lkb_id) {
		list_add_tail(&lkb->lkb_rsb_lookup, &r->res_lookup);
		return 1;
	}

	if (r->res_master_nodeid == our_nodeid) {
		lkb->lkb_nodeid = 0;
		return 0;
	}

	if (r->res_master_nodeid) {
		lkb->lkb_nodeid = r->res_master_nodeid;
		return 0;
	}

	if (dlm_dir_nodeid(r) == our_nodeid) {
		/* This is a somewhat unusual case; find_rsb will usually
		   have set res_master_nodeid when dir nodeid is local, but
		   there are cases where we become the dir node after we've
		   past find_rsb and go through _request_lock again.
		   confirm_master() or process_lookup_list() needs to be
		   called after this. */
		log_debug(r->res_ls, "set_master %x self master %d dir %d %s",
			  lkb->lkb_id, r->res_master_nodeid, r->res_dir_nodeid,
			  r->res_name);
		r->res_master_nodeid = our_nodeid;
		r->res_nodeid = 0;
		lkb->lkb_nodeid = 0;
		return 0;
	}

	r->res_first_lkid = lkb->lkb_id;
	send_lookup(r, lkb);
	return 1;
}

static void process_lookup_list(struct dlm_rsb *r)
{
	struct dlm_lkb *lkb, *safe;

	list_for_each_entry_safe(lkb, safe, &r->res_lookup, lkb_rsb_lookup) {
		list_del_init(&lkb->lkb_rsb_lookup);
		_request_lock(r, lkb);
	}
}

/* confirm_master -- confirm (or deny) an rsb's master nodeid */

static void confirm_master(struct dlm_rsb *r, int error)
{
	struct dlm_lkb *lkb;

	if (!r->res_first_lkid)
		return;

	switch (error) {
	case 0:
	case -EINPROGRESS:
		r->res_first_lkid = 0;
		process_lookup_list(r);
		break;

	case -EAGAIN:
	case -EBADR:
	case -ENOTBLK:
		/* the remote request failed and won't be retried (it was
		   a NOQUEUE, or has been canceled/unlocked); make a waiting
		   lkb the first_lkid */

		r->res_first_lkid = 0;

		if (!list_empty(&r->res_lookup)) {
			lkb = list_entry(r->res_lookup.next, struct dlm_lkb,
					 lkb_rsb_lookup);
			list_del_init(&lkb->lkb_rsb_lookup);
			r->res_first_lkid = lkb->lkb_id;
			_request_lock(r, lkb);
		}
		break;

	default:
		log_error(r->res_ls, "confirm_master unknown error %d", error);
	}
}

static int set_lock_args(int mode, struct dlm_lksb *lksb, uint32_t flags,
			 int namelen, void (*ast)(void *astparam),
			 void *astparam,
			 void (*bast)(void *astparam, int mode),
			 struct dlm_args *args)
{
	int rv = -EINVAL;

	/* check for invalid arg usage */

	if (mode < 0 || mode > DLM_LOCK_EX)
		goto out;

	if (!(flags & DLM_LKF_CONVERT) && (namelen > DLM_RESNAME_MAXLEN))
		goto out;

	if (flags & DLM_LKF_CANCEL)
		goto out;

	if (flags & DLM_LKF_QUECVT && !(flags & DLM_LKF_CONVERT))
		goto out;

	if (flags & DLM_LKF_CONVDEADLK && !(flags & DLM_LKF_CONVERT))
		goto out;

	if (flags & DLM_LKF_CONVDEADLK && flags & DLM_LKF_NOQUEUE)
		goto out;

	if (flags & DLM_LKF_EXPEDITE && flags & DLM_LKF_CONVERT)
		goto out;

	if (flags & DLM_LKF_EXPEDITE && flags & DLM_LKF_QUECVT)
		goto out;

	if (flags & DLM_LKF_EXPEDITE && flags & DLM_LKF_NOQUEUE)
		goto out;

	if (flags & DLM_LKF_EXPEDITE && mode != DLM_LOCK_NL)
		goto out;

	if (!ast || !lksb)
		goto out;

	if (flags & DLM_LKF_VALBLK && !lksb->sb_lvbptr)
		goto out;

	if (flags & DLM_LKF_CONVERT && !lksb->sb_lkid)
		goto out;

	/* these args will be copied to the lkb in validate_lock_args,
	   it cannot be done now because when converting locks, fields in
	   an active lkb cannot be modified before locking the rsb */

	args->flags = flags;
	args->astfn = ast;
	args->astparam = astparam;
	args->bastfn = bast;
	args->mode = mode;
	args->lksb = lksb;
	rv = 0;
 out:
	return rv;
}

static int set_unlock_args(uint32_t flags, void *astarg, struct dlm_args *args)
{
	if (flags & ~(DLM_LKF_CANCEL | DLM_LKF_VALBLK | DLM_LKF_IVVALBLK |
 		      DLM_LKF_FORCEUNLOCK))
		return -EINVAL;

	if (flags & DLM_LKF_CANCEL && flags & DLM_LKF_FORCEUNLOCK)
		return -EINVAL;

	args->flags = flags;
	args->astparam = astarg;
	return 0;
}

static int validate_lock_args(struct dlm_ls *ls, struct dlm_lkb *lkb,
			      struct dlm_args *args)
{
	int rv = -EBUSY;

	if (args->flags & DLM_LKF_CONVERT) {
		if (lkb->lkb_status != DLM_LKSTS_GRANTED)
			goto out;

		/* lock not allowed if there's any op in progress */
		if (lkb->lkb_wait_type || lkb->lkb_wait_count)
			goto out;

		if (is_overlap(lkb))
			goto out;

		rv = -EINVAL;
		if (test_bit(DLM_IFL_MSTCPY_BIT, &lkb->lkb_iflags))
			goto out;

		if (args->flags & DLM_LKF_QUECVT &&
		    !__quecvt_compat_matrix[lkb->lkb_grmode+1][args->mode+1])
			goto out;
	}

	lkb->lkb_exflags = args->flags;
	dlm_set_sbflags_val(lkb, 0);
	lkb->lkb_astfn = args->astfn;
	lkb->lkb_astparam = args->astparam;
	lkb->lkb_bastfn = args->bastfn;
	lkb->lkb_rqmode = args->mode;
	lkb->lkb_lksb = args->lksb;
	lkb->lkb_lvbptr = args->lksb->sb_lvbptr;
	lkb->lkb_ownpid = (int) current->pid;
	rv = 0;
 out:
	switch (rv) {
	case 0:
		break;
	case -EINVAL:
		/* annoy the user because dlm usage is wrong */
		WARN_ON(1);
		log_error(ls, "%s %d %x %x %x %d %d", __func__,
			  rv, lkb->lkb_id, dlm_iflags_val(lkb), args->flags,
			  lkb->lkb_status, lkb->lkb_wait_type);
		break;
	default:
		log_debug(ls, "%s %d %x %x %x %d %d", __func__,
			  rv, lkb->lkb_id, dlm_iflags_val(lkb), args->flags,
			  lkb->lkb_status, lkb->lkb_wait_type);
		break;
	}

	return rv;
}

/* when dlm_unlock() sees -EBUSY with CANCEL/FORCEUNLOCK it returns 0
   for success */

/* note: it's valid for lkb_nodeid/res_nodeid to be -1 when we get here
   because there may be a lookup in progress and it's valid to do
   cancel/unlockf on it */

static int validate_unlock_args(struct dlm_lkb *lkb, struct dlm_args *args)
{
	struct dlm_ls *ls = lkb->lkb_resource->res_ls;
	int rv = -EBUSY;

	/* normal unlock not allowed if there's any op in progress */
	if (!(args->flags & (DLM_LKF_CANCEL | DLM_LKF_FORCEUNLOCK)) &&
	    (lkb->lkb_wait_type || lkb->lkb_wait_count))
		goto out;

	/* an lkb may be waiting for an rsb lookup to complete where the
	   lookup was initiated by another lock */

	if (!list_empty(&lkb->lkb_rsb_lookup)) {
		if (args->flags & (DLM_LKF_CANCEL | DLM_LKF_FORCEUNLOCK)) {
			log_debug(ls, "unlock on rsb_lookup %x", lkb->lkb_id);
			list_del_init(&lkb->lkb_rsb_lookup);
			queue_cast(lkb->lkb_resource, lkb,
				   args->flags & DLM_LKF_CANCEL ?
				   -DLM_ECANCEL : -DLM_EUNLOCK);
			unhold_lkb(lkb); /* undoes create_lkb() */
		}
		/* caller changes -EBUSY to 0 for CANCEL and FORCEUNLOCK */
		goto out;
	}

	rv = -EINVAL;
	if (test_bit(DLM_IFL_MSTCPY_BIT, &lkb->lkb_iflags)) {
		log_error(ls, "unlock on MSTCPY %x", lkb->lkb_id);
		dlm_print_lkb(lkb);
		goto out;
	}

	/* an lkb may still exist even though the lock is EOL'ed due to a
	 * cancel, unlock or failed noqueue request; an app can't use these
	 * locks; return same error as if the lkid had not been found at all
	 */

	if (test_bit(DLM_IFL_ENDOFLIFE_BIT, &lkb->lkb_iflags)) {
		log_debug(ls, "unlock on ENDOFLIFE %x", lkb->lkb_id);
		rv = -ENOENT;
		goto out;
	}

	if (is_overlap_unlock(lkb))
		goto out;

	/* cancel not allowed with another cancel/unlock in progress */

	if (args->flags & DLM_LKF_CANCEL) {
		if (lkb->lkb_exflags & DLM_LKF_CANCEL)
			goto out;

		if (is_overlap_cancel(lkb))
			goto out;

		if (test_bit(DLM_IFL_RESEND_BIT, &lkb->lkb_iflags)) {
			set_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags);
			rv = -EBUSY;
			goto out;
		}

		/* there's nothing to cancel */
		if (lkb->lkb_status == DLM_LKSTS_GRANTED &&
		    !lkb->lkb_wait_type) {
			rv = -EBUSY;
			goto out;
		}

		switch (lkb->lkb_wait_type) {
		case DLM_MSG_LOOKUP:
		case DLM_MSG_REQUEST:
			set_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags);
			rv = -EBUSY;
			goto out;
		case DLM_MSG_UNLOCK:
		case DLM_MSG_CANCEL:
			goto out;
		}
		/* add_to_waiters() will set OVERLAP_CANCEL */
		goto out_ok;
	}

	/* do we need to allow a force-unlock if there's a normal unlock
	   already in progress?  in what conditions could the normal unlock
	   fail such that we'd want to send a force-unlock to be sure? */

	if (args->flags & DLM_LKF_FORCEUNLOCK) {
		if (lkb->lkb_exflags & DLM_LKF_FORCEUNLOCK)
			goto out;

		if (test_bit(DLM_IFL_RESEND_BIT, &lkb->lkb_iflags)) {
			set_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags);
			rv = -EBUSY;
			goto out;
		}

		switch (lkb->lkb_wait_type) {
		case DLM_MSG_LOOKUP:
		case DLM_MSG_REQUEST:
			set_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags);
			rv = -EBUSY;
			goto out;
		case DLM_MSG_UNLOCK:
			goto out;
		}
		/* add_to_waiters() will set OVERLAP_UNLOCK */
	}

 out_ok:
	/* an overlapping op shouldn't blow away exflags from other op */
	lkb->lkb_exflags |= args->flags;
	dlm_set_sbflags_val(lkb, 0);
	lkb->lkb_astparam = args->astparam;
	rv = 0;
 out:
	switch (rv) {
	case 0:
		break;
	case -EINVAL:
		/* annoy the user because dlm usage is wrong */
		WARN_ON(1);
		log_error(ls, "%s %d %x %x %x %x %d %s", __func__, rv,
			  lkb->lkb_id, dlm_iflags_val(lkb), lkb->lkb_exflags,
			  args->flags, lkb->lkb_wait_type,
			  lkb->lkb_resource->res_name);
		break;
	default:
		log_debug(ls, "%s %d %x %x %x %x %d %s", __func__, rv,
			  lkb->lkb_id, dlm_iflags_val(lkb), lkb->lkb_exflags,
			  args->flags, lkb->lkb_wait_type,
			  lkb->lkb_resource->res_name);
		break;
	}

	return rv;
}

/*
 * Four stage 4 varieties:
 * do_request(), do_convert(), do_unlock(), do_cancel()
 * These are called on the master node for the given lock and
 * from the central locking logic.
 */

static int do_request(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error = 0;

	if (can_be_granted(r, lkb, 1, 0, NULL)) {
		grant_lock(r, lkb);
		queue_cast(r, lkb, 0);
		goto out;
	}

	if (can_be_queued(lkb)) {
		error = -EINPROGRESS;
		add_lkb(r, lkb, DLM_LKSTS_WAITING);
		goto out;
	}

	error = -EAGAIN;
	queue_cast(r, lkb, -EAGAIN);
 out:
	return error;
}

static void do_request_effects(struct dlm_rsb *r, struct dlm_lkb *lkb,
			       int error)
{
	switch (error) {
	case -EAGAIN:
		if (force_blocking_asts(lkb))
			send_blocking_asts_all(r, lkb);
		break;
	case -EINPROGRESS:
		send_blocking_asts(r, lkb);
		break;
	}
}

static int do_convert(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error = 0;
	int deadlk = 0;

	/* changing an existing lock may allow others to be granted */

	if (can_be_granted(r, lkb, 1, 0, &deadlk)) {
		grant_lock(r, lkb);
		queue_cast(r, lkb, 0);
		goto out;
	}

	/* can_be_granted() detected that this lock would block in a conversion
	   deadlock, so we leave it on the granted queue and return EDEADLK in
	   the ast for the convert. */

	if (deadlk && !(lkb->lkb_exflags & DLM_LKF_NODLCKWT)) {
		/* it's left on the granted queue */
		revert_lock(r, lkb);
		queue_cast(r, lkb, -EDEADLK);
		error = -EDEADLK;
		goto out;
	}

	/* is_demoted() means the can_be_granted() above set the grmode
	   to NL, and left us on the granted queue.  This auto-demotion
	   (due to CONVDEADLK) might mean other locks, and/or this lock, are
	   now grantable.  We have to try to grant other converting locks
	   before we try again to grant this one. */

	if (is_demoted(lkb)) {
		grant_pending_convert(r, DLM_LOCK_IV, NULL, NULL);
		if (_can_be_granted(r, lkb, 1, 0)) {
			grant_lock(r, lkb);
			queue_cast(r, lkb, 0);
			goto out;
		}
		/* else fall through and move to convert queue */
	}

	if (can_be_queued(lkb)) {
		error = -EINPROGRESS;
		del_lkb(r, lkb);
		add_lkb(r, lkb, DLM_LKSTS_CONVERT);
		goto out;
	}

	error = -EAGAIN;
	queue_cast(r, lkb, -EAGAIN);
 out:
	return error;
}

static void do_convert_effects(struct dlm_rsb *r, struct dlm_lkb *lkb,
			       int error)
{
	switch (error) {
	case 0:
		grant_pending_locks(r, NULL);
		/* grant_pending_locks also sends basts */
		break;
	case -EAGAIN:
		if (force_blocking_asts(lkb))
			send_blocking_asts_all(r, lkb);
		break;
	case -EINPROGRESS:
		send_blocking_asts(r, lkb);
		break;
	}
}

static int do_unlock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	remove_lock(r, lkb);
	queue_cast(r, lkb, -DLM_EUNLOCK);
	return -DLM_EUNLOCK;
}

static void do_unlock_effects(struct dlm_rsb *r, struct dlm_lkb *lkb,
			      int error)
{
	grant_pending_locks(r, NULL);
}

/* returns: 0 did nothing, -DLM_ECANCEL canceled lock */

static int do_cancel(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error;

	error = revert_lock(r, lkb);
	if (error) {
		queue_cast(r, lkb, -DLM_ECANCEL);
		return -DLM_ECANCEL;
	}
	return 0;
}

static void do_cancel_effects(struct dlm_rsb *r, struct dlm_lkb *lkb,
			      int error)
{
	if (error)
		grant_pending_locks(r, NULL);
}

/*
 * Four stage 3 varieties:
 * _request_lock(), _convert_lock(), _unlock_lock(), _cancel_lock()
 */

/* add a new lkb to a possibly new rsb, called by requesting process */

static int _request_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error;

	/* set_master: sets lkb nodeid from r */

	error = set_master(r, lkb);
	if (error < 0)
		goto out;
	if (error) {
		error = 0;
		goto out;
	}

	if (is_remote(r)) {
		/* receive_request() calls do_request() on remote node */
		error = send_request(r, lkb);
	} else {
		error = do_request(r, lkb);
		/* for remote locks the request_reply is sent
		   between do_request and do_request_effects */
		do_request_effects(r, lkb, error);
	}
 out:
	return error;
}

/* change some property of an existing lkb, e.g. mode */

static int _convert_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error;

	if (is_remote(r)) {
		/* receive_convert() calls do_convert() on remote node */
		error = send_convert(r, lkb);
	} else {
		error = do_convert(r, lkb);
		/* for remote locks the convert_reply is sent
		   between do_convert and do_convert_effects */
		do_convert_effects(r, lkb, error);
	}

	return error;
}

/* remove an existing lkb from the granted queue */

static int _unlock_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error;

	if (is_remote(r)) {
		/* receive_unlock() calls do_unlock() on remote node */
		error = send_unlock(r, lkb);
	} else {
		error = do_unlock(r, lkb);
		/* for remote locks the unlock_reply is sent
		   between do_unlock and do_unlock_effects */
		do_unlock_effects(r, lkb, error);
	}

	return error;
}

/* remove an existing lkb from the convert or wait queue */

static int _cancel_lock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error;

	if (is_remote(r)) {
		/* receive_cancel() calls do_cancel() on remote node */
		error = send_cancel(r, lkb);
	} else {
		error = do_cancel(r, lkb);
		/* for remote locks the cancel_reply is sent
		   between do_cancel and do_cancel_effects */
		do_cancel_effects(r, lkb, error);
	}

	return error;
}

/*
 * Four stage 2 varieties:
 * request_lock(), convert_lock(), unlock_lock(), cancel_lock()
 */

static int request_lock(struct dlm_ls *ls, struct dlm_lkb *lkb,
			const void *name, int len,
			struct dlm_args *args)
{
	struct dlm_rsb *r;
	int error;

	error = validate_lock_args(ls, lkb, args);
	if (error)
		return error;

	error = find_rsb(ls, name, len, 0, R_REQUEST, &r);
	if (error)
		return error;

	lock_rsb(r);

	attach_lkb(r, lkb);
	lkb->lkb_lksb->sb_lkid = lkb->lkb_id;

	error = _request_lock(r, lkb);

	unlock_rsb(r);
	put_rsb(r);
	return error;
}

static int convert_lock(struct dlm_ls *ls, struct dlm_lkb *lkb,
			struct dlm_args *args)
{
	struct dlm_rsb *r;
	int error;

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_lock_args(ls, lkb, args);
	if (error)
		goto out;

	error = _convert_lock(r, lkb);
 out:
	unlock_rsb(r);
	put_rsb(r);
	return error;
}

static int unlock_lock(struct dlm_ls *ls, struct dlm_lkb *lkb,
		       struct dlm_args *args)
{
	struct dlm_rsb *r;
	int error;

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_unlock_args(lkb, args);
	if (error)
		goto out;

	error = _unlock_lock(r, lkb);
 out:
	unlock_rsb(r);
	put_rsb(r);
	return error;
}

static int cancel_lock(struct dlm_ls *ls, struct dlm_lkb *lkb,
		       struct dlm_args *args)
{
	struct dlm_rsb *r;
	int error;

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_unlock_args(lkb, args);
	if (error)
		goto out;

	error = _cancel_lock(r, lkb);
 out:
	unlock_rsb(r);
	put_rsb(r);
	return error;
}

/*
 * Two stage 1 varieties:  dlm_lock() and dlm_unlock()
 */

int dlm_lock(dlm_lockspace_t *lockspace,
	     int mode,
	     struct dlm_lksb *lksb,
	     uint32_t flags,
	     const void *name,
	     unsigned int namelen,
	     uint32_t parent_lkid,
	     void (*ast) (void *astarg),
	     void *astarg,
	     void (*bast) (void *astarg, int mode))
{
	struct dlm_ls *ls;
	struct dlm_lkb *lkb;
	struct dlm_args args;
	int error, convert = flags & DLM_LKF_CONVERT;

	ls = dlm_find_lockspace_local(lockspace);
	if (!ls)
		return -EINVAL;

	dlm_lock_recovery(ls);

	if (convert)
		error = find_lkb(ls, lksb->sb_lkid, &lkb);
	else
		error = create_lkb(ls, &lkb);

	if (error)
		goto out;

	trace_dlm_lock_start(ls, lkb, name, namelen, mode, flags);

	error = set_lock_args(mode, lksb, flags, namelen, ast, astarg, bast,
			      &args);
	if (error)
		goto out_put;

	if (convert)
		error = convert_lock(ls, lkb, &args);
	else
		error = request_lock(ls, lkb, name, namelen, &args);

	if (error == -EINPROGRESS)
		error = 0;
 out_put:
	trace_dlm_lock_end(ls, lkb, name, namelen, mode, flags, error, true);

	if (convert || error)
		__put_lkb(ls, lkb);
	if (error == -EAGAIN || error == -EDEADLK)
		error = 0;
 out:
	dlm_unlock_recovery(ls);
	dlm_put_lockspace(ls);
	return error;
}

int dlm_unlock(dlm_lockspace_t *lockspace,
	       uint32_t lkid,
	       uint32_t flags,
	       struct dlm_lksb *lksb,
	       void *astarg)
{
	struct dlm_ls *ls;
	struct dlm_lkb *lkb;
	struct dlm_args args;
	int error;

	ls = dlm_find_lockspace_local(lockspace);
	if (!ls)
		return -EINVAL;

	dlm_lock_recovery(ls);

	error = find_lkb(ls, lkid, &lkb);
	if (error)
		goto out;

	trace_dlm_unlock_start(ls, lkb, flags);

	error = set_unlock_args(flags, astarg, &args);
	if (error)
		goto out_put;

	if (flags & DLM_LKF_CANCEL)
		error = cancel_lock(ls, lkb, &args);
	else
		error = unlock_lock(ls, lkb, &args);

	if (error == -DLM_EUNLOCK || error == -DLM_ECANCEL)
		error = 0;
	if (error == -EBUSY && (flags & (DLM_LKF_CANCEL | DLM_LKF_FORCEUNLOCK)))
		error = 0;
 out_put:
	trace_dlm_unlock_end(ls, lkb, flags, error);

	dlm_put_lkb(lkb);
 out:
	dlm_unlock_recovery(ls);
	dlm_put_lockspace(ls);
	return error;
}

/*
 * send/receive routines for remote operations and replies
 *
 * send_args
 * send_common
 * send_request			receive_request
 * send_convert			receive_convert
 * send_unlock			receive_unlock
 * send_cancel			receive_cancel
 * send_grant			receive_grant
 * send_bast			receive_bast
 * send_lookup			receive_lookup
 * send_remove			receive_remove
 *
 * 				send_common_reply
 * receive_request_reply	send_request_reply
 * receive_convert_reply	send_convert_reply
 * receive_unlock_reply		send_unlock_reply
 * receive_cancel_reply		send_cancel_reply
 * receive_lookup_reply		send_lookup_reply
 */

static int _create_message(struct dlm_ls *ls, int mb_len,
			   int to_nodeid, int mstype,
			   struct dlm_message **ms_ret,
			   struct dlm_mhandle **mh_ret)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	char *mb;

	/* get_buffer gives us a message handle (mh) that we need to
	   pass into midcomms_commit and a message buffer (mb) that we
	   write our data into */

	mh = dlm_midcomms_get_mhandle(to_nodeid, mb_len, &mb);
	if (!mh)
		return -ENOBUFS;

	ms = (struct dlm_message *) mb;

	ms->m_header.h_version = cpu_to_le32(DLM_HEADER_MAJOR | DLM_HEADER_MINOR);
	ms->m_header.u.h_lockspace = cpu_to_le32(ls->ls_global_id);
	ms->m_header.h_nodeid = cpu_to_le32(dlm_our_nodeid());
	ms->m_header.h_length = cpu_to_le16(mb_len);
	ms->m_header.h_cmd = DLM_MSG;

	ms->m_type = cpu_to_le32(mstype);

	*mh_ret = mh;
	*ms_ret = ms;
	return 0;
}

static int create_message(struct dlm_rsb *r, struct dlm_lkb *lkb,
			  int to_nodeid, int mstype,
			  struct dlm_message **ms_ret,
			  struct dlm_mhandle **mh_ret)
{
	int mb_len = sizeof(struct dlm_message);

	switch (mstype) {
	case DLM_MSG_REQUEST:
	case DLM_MSG_LOOKUP:
	case DLM_MSG_REMOVE:
		mb_len += r->res_length;
		break;
	case DLM_MSG_CONVERT:
	case DLM_MSG_UNLOCK:
	case DLM_MSG_REQUEST_REPLY:
	case DLM_MSG_CONVERT_REPLY:
	case DLM_MSG_GRANT:
		if (lkb && lkb->lkb_lvbptr && (lkb->lkb_exflags & DLM_LKF_VALBLK))
			mb_len += r->res_ls->ls_lvblen;
		break;
	}

	return _create_message(r->res_ls, mb_len, to_nodeid, mstype,
			       ms_ret, mh_ret);
}

/* further lowcomms enhancements or alternate implementations may make
   the return value from this function useful at some point */

static int send_message(struct dlm_mhandle *mh, struct dlm_message *ms,
			const void *name, int namelen)
{
	dlm_midcomms_commit_mhandle(mh, name, namelen);
	return 0;
}

static void send_args(struct dlm_rsb *r, struct dlm_lkb *lkb,
		      struct dlm_message *ms)
{
	ms->m_nodeid   = cpu_to_le32(lkb->lkb_nodeid);
	ms->m_pid      = cpu_to_le32(lkb->lkb_ownpid);
	ms->m_lkid     = cpu_to_le32(lkb->lkb_id);
	ms->m_remid    = cpu_to_le32(lkb->lkb_remid);
	ms->m_exflags  = cpu_to_le32(lkb->lkb_exflags);
	ms->m_sbflags  = cpu_to_le32(dlm_sbflags_val(lkb));
	ms->m_flags    = cpu_to_le32(dlm_dflags_val(lkb));
	ms->m_lvbseq   = cpu_to_le32(lkb->lkb_lvbseq);
	ms->m_status   = cpu_to_le32(lkb->lkb_status);
	ms->m_grmode   = cpu_to_le32(lkb->lkb_grmode);
	ms->m_rqmode   = cpu_to_le32(lkb->lkb_rqmode);
	ms->m_hash     = cpu_to_le32(r->res_hash);

	/* m_result and m_bastmode are set from function args,
	   not from lkb fields */

	if (lkb->lkb_bastfn)
		ms->m_asts |= cpu_to_le32(DLM_CB_BAST);
	if (lkb->lkb_astfn)
		ms->m_asts |= cpu_to_le32(DLM_CB_CAST);

	/* compare with switch in create_message; send_remove() doesn't
	   use send_args() */

	switch (ms->m_type) {
	case cpu_to_le32(DLM_MSG_REQUEST):
	case cpu_to_le32(DLM_MSG_LOOKUP):
		memcpy(ms->m_extra, r->res_name, r->res_length);
		break;
	case cpu_to_le32(DLM_MSG_CONVERT):
	case cpu_to_le32(DLM_MSG_UNLOCK):
	case cpu_to_le32(DLM_MSG_REQUEST_REPLY):
	case cpu_to_le32(DLM_MSG_CONVERT_REPLY):
	case cpu_to_le32(DLM_MSG_GRANT):
		if (!lkb->lkb_lvbptr || !(lkb->lkb_exflags & DLM_LKF_VALBLK))
			break;
		memcpy(ms->m_extra, lkb->lkb_lvbptr, r->res_ls->ls_lvblen);
		break;
	}
}

static int send_common(struct dlm_rsb *r, struct dlm_lkb *lkb, int mstype)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int to_nodeid, error;

	to_nodeid = r->res_nodeid;

	add_to_waiters(lkb, mstype, to_nodeid);
	error = create_message(r, lkb, to_nodeid, mstype, &ms, &mh);
	if (error)
		goto fail;

	send_args(r, lkb, ms);

	error = send_message(mh, ms, r->res_name, r->res_length);
	if (error)
		goto fail;
	return 0;

 fail:
	remove_from_waiters(lkb, msg_reply_type(mstype));
	return error;
}

static int send_request(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	return send_common(r, lkb, DLM_MSG_REQUEST);
}

static int send_convert(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	int error;

	error = send_common(r, lkb, DLM_MSG_CONVERT);

	/* down conversions go without a reply from the master */
	if (!error && down_conversion(lkb)) {
		remove_from_waiters(lkb, DLM_MSG_CONVERT_REPLY);
		r->res_ls->ls_local_ms.m_type = cpu_to_le32(DLM_MSG_CONVERT_REPLY);
		r->res_ls->ls_local_ms.m_result = 0;
		__receive_convert_reply(r, lkb, &r->res_ls->ls_local_ms, true);
	}

	return error;
}

/* FIXME: if this lkb is the only lock we hold on the rsb, then set
   MASTER_UNCERTAIN to force the next request on the rsb to confirm
   that the master is still correct. */

static int send_unlock(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	return send_common(r, lkb, DLM_MSG_UNLOCK);
}

static int send_cancel(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	return send_common(r, lkb, DLM_MSG_CANCEL);
}

static int send_grant(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int to_nodeid, error;

	to_nodeid = lkb->lkb_nodeid;

	error = create_message(r, lkb, to_nodeid, DLM_MSG_GRANT, &ms, &mh);
	if (error)
		goto out;

	send_args(r, lkb, ms);

	ms->m_result = 0;

	error = send_message(mh, ms, r->res_name, r->res_length);
 out:
	return error;
}

static int send_bast(struct dlm_rsb *r, struct dlm_lkb *lkb, int mode)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int to_nodeid, error;

	to_nodeid = lkb->lkb_nodeid;

	error = create_message(r, NULL, to_nodeid, DLM_MSG_BAST, &ms, &mh);
	if (error)
		goto out;

	send_args(r, lkb, ms);

	ms->m_bastmode = cpu_to_le32(mode);

	error = send_message(mh, ms, r->res_name, r->res_length);
 out:
	return error;
}

static int send_lookup(struct dlm_rsb *r, struct dlm_lkb *lkb)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int to_nodeid, error;

	to_nodeid = dlm_dir_nodeid(r);

	add_to_waiters(lkb, DLM_MSG_LOOKUP, to_nodeid);
	error = create_message(r, NULL, to_nodeid, DLM_MSG_LOOKUP, &ms, &mh);
	if (error)
		goto fail;

	send_args(r, lkb, ms);

	error = send_message(mh, ms, r->res_name, r->res_length);
	if (error)
		goto fail;
	return 0;

 fail:
	remove_from_waiters(lkb, DLM_MSG_LOOKUP_REPLY);
	return error;
}

static int send_remove(struct dlm_rsb *r)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int to_nodeid, error;

	to_nodeid = dlm_dir_nodeid(r);

	error = create_message(r, NULL, to_nodeid, DLM_MSG_REMOVE, &ms, &mh);
	if (error)
		goto out;

	memcpy(ms->m_extra, r->res_name, r->res_length);
	ms->m_hash = cpu_to_le32(r->res_hash);

	error = send_message(mh, ms, r->res_name, r->res_length);
 out:
	return error;
}

static int send_common_reply(struct dlm_rsb *r, struct dlm_lkb *lkb,
			     int mstype, int rv)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int to_nodeid, error;

	to_nodeid = lkb->lkb_nodeid;

	error = create_message(r, lkb, to_nodeid, mstype, &ms, &mh);
	if (error)
		goto out;

	send_args(r, lkb, ms);

	ms->m_result = cpu_to_le32(to_dlm_errno(rv));

	error = send_message(mh, ms, r->res_name, r->res_length);
 out:
	return error;
}

static int send_request_reply(struct dlm_rsb *r, struct dlm_lkb *lkb, int rv)
{
	return send_common_reply(r, lkb, DLM_MSG_REQUEST_REPLY, rv);
}

static int send_convert_reply(struct dlm_rsb *r, struct dlm_lkb *lkb, int rv)
{
	return send_common_reply(r, lkb, DLM_MSG_CONVERT_REPLY, rv);
}

static int send_unlock_reply(struct dlm_rsb *r, struct dlm_lkb *lkb, int rv)
{
	return send_common_reply(r, lkb, DLM_MSG_UNLOCK_REPLY, rv);
}

static int send_cancel_reply(struct dlm_rsb *r, struct dlm_lkb *lkb, int rv)
{
	return send_common_reply(r, lkb, DLM_MSG_CANCEL_REPLY, rv);
}

static int send_lookup_reply(struct dlm_ls *ls,
			     const struct dlm_message *ms_in, int ret_nodeid,
			     int rv)
{
	struct dlm_rsb *r = &ls->ls_local_rsb;
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int error, nodeid = le32_to_cpu(ms_in->m_header.h_nodeid);

	error = create_message(r, NULL, nodeid, DLM_MSG_LOOKUP_REPLY, &ms, &mh);
	if (error)
		goto out;

	ms->m_lkid = ms_in->m_lkid;
	ms->m_result = cpu_to_le32(to_dlm_errno(rv));
	ms->m_nodeid = cpu_to_le32(ret_nodeid);

	error = send_message(mh, ms, ms_in->m_extra, receive_extralen(ms_in));
 out:
	return error;
}

/* which args we save from a received message depends heavily on the type
   of message, unlike the send side where we can safely send everything about
   the lkb for any type of message */

static void receive_flags(struct dlm_lkb *lkb, const struct dlm_message *ms)
{
	lkb->lkb_exflags = le32_to_cpu(ms->m_exflags);
	dlm_set_sbflags_val(lkb, le32_to_cpu(ms->m_sbflags));
	dlm_set_dflags_val(lkb, le32_to_cpu(ms->m_flags));
}

static void receive_flags_reply(struct dlm_lkb *lkb,
				const struct dlm_message *ms,
				bool local)
{
	if (local)
		return;

	dlm_set_sbflags_val(lkb, le32_to_cpu(ms->m_sbflags));
	dlm_set_dflags_val(lkb, le32_to_cpu(ms->m_flags));
}

static int receive_extralen(const struct dlm_message *ms)
{
	return (le16_to_cpu(ms->m_header.h_length) -
		sizeof(struct dlm_message));
}

static int receive_lvb(struct dlm_ls *ls, struct dlm_lkb *lkb,
		       const struct dlm_message *ms)
{
	int len;

	if (lkb->lkb_exflags & DLM_LKF_VALBLK) {
		if (!lkb->lkb_lvbptr)
			lkb->lkb_lvbptr = dlm_allocate_lvb(ls);
		if (!lkb->lkb_lvbptr)
			return -ENOMEM;
		len = receive_extralen(ms);
		if (len > ls->ls_lvblen)
			len = ls->ls_lvblen;
		memcpy(lkb->lkb_lvbptr, ms->m_extra, len);
	}
	return 0;
}

static void fake_bastfn(void *astparam, int mode)
{
	log_print("fake_bastfn should not be called");
}

static void fake_astfn(void *astparam)
{
	log_print("fake_astfn should not be called");
}

static int receive_request_args(struct dlm_ls *ls, struct dlm_lkb *lkb,
				const struct dlm_message *ms)
{
	lkb->lkb_nodeid = le32_to_cpu(ms->m_header.h_nodeid);
	lkb->lkb_ownpid = le32_to_cpu(ms->m_pid);
	lkb->lkb_remid = le32_to_cpu(ms->m_lkid);
	lkb->lkb_grmode = DLM_LOCK_IV;
	lkb->lkb_rqmode = le32_to_cpu(ms->m_rqmode);

	lkb->lkb_bastfn = (ms->m_asts & cpu_to_le32(DLM_CB_BAST)) ? &fake_bastfn : NULL;
	lkb->lkb_astfn = (ms->m_asts & cpu_to_le32(DLM_CB_CAST)) ? &fake_astfn : NULL;

	if (lkb->lkb_exflags & DLM_LKF_VALBLK) {
		/* lkb was just created so there won't be an lvb yet */
		lkb->lkb_lvbptr = dlm_allocate_lvb(ls);
		if (!lkb->lkb_lvbptr)
			return -ENOMEM;
	}

	return 0;
}

static int receive_convert_args(struct dlm_ls *ls, struct dlm_lkb *lkb,
				const struct dlm_message *ms)
{
	if (lkb->lkb_status != DLM_LKSTS_GRANTED)
		return -EBUSY;

	if (receive_lvb(ls, lkb, ms))
		return -ENOMEM;

	lkb->lkb_rqmode = le32_to_cpu(ms->m_rqmode);
	lkb->lkb_lvbseq = le32_to_cpu(ms->m_lvbseq);

	return 0;
}

static int receive_unlock_args(struct dlm_ls *ls, struct dlm_lkb *lkb,
			       const struct dlm_message *ms)
{
	if (receive_lvb(ls, lkb, ms))
		return -ENOMEM;
	return 0;
}

/* We fill in the local-lkb fields with the info that send_xxxx_reply()
   uses to send a reply and that the remote end uses to process the reply. */

static void setup_local_lkb(struct dlm_ls *ls, const struct dlm_message *ms)
{
	struct dlm_lkb *lkb = &ls->ls_local_lkb;
	lkb->lkb_nodeid = le32_to_cpu(ms->m_header.h_nodeid);
	lkb->lkb_remid = le32_to_cpu(ms->m_lkid);
}

/* This is called after the rsb is locked so that we can safely inspect
   fields in the lkb. */

static int validate_message(struct dlm_lkb *lkb, const struct dlm_message *ms)
{
	int from = le32_to_cpu(ms->m_header.h_nodeid);
	int error = 0;

	/* currently mixing of user/kernel locks are not supported */
	if (ms->m_flags & cpu_to_le32(BIT(DLM_DFL_USER_BIT)) &&
	    !test_bit(DLM_DFL_USER_BIT, &lkb->lkb_dflags)) {
		log_error(lkb->lkb_resource->res_ls,
			  "got user dlm message for a kernel lock");
		error = -EINVAL;
		goto out;
	}

	switch (ms->m_type) {
	case cpu_to_le32(DLM_MSG_CONVERT):
	case cpu_to_le32(DLM_MSG_UNLOCK):
	case cpu_to_le32(DLM_MSG_CANCEL):
		if (!is_master_copy(lkb) || lkb->lkb_nodeid != from)
			error = -EINVAL;
		break;

	case cpu_to_le32(DLM_MSG_CONVERT_REPLY):
	case cpu_to_le32(DLM_MSG_UNLOCK_REPLY):
	case cpu_to_le32(DLM_MSG_CANCEL_REPLY):
	case cpu_to_le32(DLM_MSG_GRANT):
	case cpu_to_le32(DLM_MSG_BAST):
		if (!is_process_copy(lkb) || lkb->lkb_nodeid != from)
			error = -EINVAL;
		break;

	case cpu_to_le32(DLM_MSG_REQUEST_REPLY):
		if (!is_process_copy(lkb))
			error = -EINVAL;
		else if (lkb->lkb_nodeid != -1 && lkb->lkb_nodeid != from)
			error = -EINVAL;
		break;

	default:
		error = -EINVAL;
	}

out:
	if (error)
		log_error(lkb->lkb_resource->res_ls,
			  "ignore invalid message %d from %d %x %x %x %d",
			  le32_to_cpu(ms->m_type), from, lkb->lkb_id,
			  lkb->lkb_remid, dlm_iflags_val(lkb),
			  lkb->lkb_nodeid);
	return error;
}

static int receive_request(struct dlm_ls *ls, const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int from_nodeid;
	int error, namelen = 0;

	from_nodeid = le32_to_cpu(ms->m_header.h_nodeid);

	error = create_lkb(ls, &lkb);
	if (error)
		goto fail;

	receive_flags(lkb, ms);
	set_bit(DLM_IFL_MSTCPY_BIT, &lkb->lkb_iflags);
	error = receive_request_args(ls, lkb, ms);
	if (error) {
		__put_lkb(ls, lkb);
		goto fail;
	}

	/* The dir node is the authority on whether we are the master
	   for this rsb or not, so if the master sends us a request, we should
	   recreate the rsb if we've destroyed it.   This race happens when we
	   send a remove message to the dir node at the same time that the dir
	   node sends us a request for the rsb. */

	namelen = receive_extralen(ms);

	error = find_rsb(ls, ms->m_extra, namelen, from_nodeid,
			 R_RECEIVE_REQUEST, &r);
	if (error) {
		__put_lkb(ls, lkb);
		goto fail;
	}

	lock_rsb(r);

	if (r->res_master_nodeid != dlm_our_nodeid()) {
		error = validate_master_nodeid(ls, r, from_nodeid);
		if (error) {
			unlock_rsb(r);
			put_rsb(r);
			__put_lkb(ls, lkb);
			goto fail;
		}
	}

	attach_lkb(r, lkb);
	error = do_request(r, lkb);
	send_request_reply(r, lkb, error);
	do_request_effects(r, lkb, error);

	unlock_rsb(r);
	put_rsb(r);

	if (error == -EINPROGRESS)
		error = 0;
	if (error)
		dlm_put_lkb(lkb);
	return 0;

 fail:
	/* TODO: instead of returning ENOTBLK, add the lkb to res_lookup
	   and do this receive_request again from process_lookup_list once
	   we get the lookup reply.  This would avoid a many repeated
	   ENOTBLK request failures when the lookup reply designating us
	   as master is delayed. */

	if (error != -ENOTBLK) {
		log_limit(ls, "receive_request %x from %d %d",
			  le32_to_cpu(ms->m_lkid), from_nodeid, error);
	}

	setup_local_lkb(ls, ms);
	send_request_reply(&ls->ls_local_rsb, &ls->ls_local_lkb, error);
	return error;
}

static int receive_convert(struct dlm_ls *ls, const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error, reply = 1;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		goto fail;

	if (lkb->lkb_remid != le32_to_cpu(ms->m_lkid)) {
		log_error(ls, "receive_convert %x remid %x recover_seq %llu "
			  "remote %d %x", lkb->lkb_id, lkb->lkb_remid,
			  (unsigned long long)lkb->lkb_recover_seq,
			  le32_to_cpu(ms->m_header.h_nodeid),
			  le32_to_cpu(ms->m_lkid));
		error = -ENOENT;
		dlm_put_lkb(lkb);
		goto fail;
	}

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	receive_flags(lkb, ms);

	error = receive_convert_args(ls, lkb, ms);
	if (error) {
		send_convert_reply(r, lkb, error);
		goto out;
	}

	reply = !down_conversion(lkb);

	error = do_convert(r, lkb);
	if (reply)
		send_convert_reply(r, lkb, error);
	do_convert_effects(r, lkb, error);
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);
	return 0;

 fail:
	setup_local_lkb(ls, ms);
	send_convert_reply(&ls->ls_local_rsb, &ls->ls_local_lkb, error);
	return error;
}

static int receive_unlock(struct dlm_ls *ls, const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		goto fail;

	if (lkb->lkb_remid != le32_to_cpu(ms->m_lkid)) {
		log_error(ls, "receive_unlock %x remid %x remote %d %x",
			  lkb->lkb_id, lkb->lkb_remid,
			  le32_to_cpu(ms->m_header.h_nodeid),
			  le32_to_cpu(ms->m_lkid));
		error = -ENOENT;
		dlm_put_lkb(lkb);
		goto fail;
	}

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	receive_flags(lkb, ms);

	error = receive_unlock_args(ls, lkb, ms);
	if (error) {
		send_unlock_reply(r, lkb, error);
		goto out;
	}

	error = do_unlock(r, lkb);
	send_unlock_reply(r, lkb, error);
	do_unlock_effects(r, lkb, error);
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);
	return 0;

 fail:
	setup_local_lkb(ls, ms);
	send_unlock_reply(&ls->ls_local_rsb, &ls->ls_local_lkb, error);
	return error;
}

static int receive_cancel(struct dlm_ls *ls, const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		goto fail;

	receive_flags(lkb, ms);

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	error = do_cancel(r, lkb);
	send_cancel_reply(r, lkb, error);
	do_cancel_effects(r, lkb, error);
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);
	return 0;

 fail:
	setup_local_lkb(ls, ms);
	send_cancel_reply(&ls->ls_local_rsb, &ls->ls_local_lkb, error);
	return error;
}

static int receive_grant(struct dlm_ls *ls, const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		return error;

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	receive_flags_reply(lkb, ms, false);
	if (is_altmode(lkb))
		munge_altmode(lkb, ms);
	grant_lock_pc(r, lkb, ms);
	queue_cast(r, lkb, 0);
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);
	return 0;
}

static int receive_bast(struct dlm_ls *ls, const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		return error;

	r = lkb->lkb_resource;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	queue_bast(r, lkb, le32_to_cpu(ms->m_bastmode));
	lkb->lkb_highbast = le32_to_cpu(ms->m_bastmode);
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);
	return 0;
}

static void receive_lookup(struct dlm_ls *ls, const struct dlm_message *ms)
{
	int len, error, ret_nodeid, from_nodeid, our_nodeid;

	from_nodeid = le32_to_cpu(ms->m_header.h_nodeid);
	our_nodeid = dlm_our_nodeid();

	len = receive_extralen(ms);

	error = dlm_master_lookup(ls, from_nodeid, ms->m_extra, len, 0,
				  &ret_nodeid, NULL);

	/* Optimization: we're master so treat lookup as a request */
	if (!error && ret_nodeid == our_nodeid) {
		receive_request(ls, ms);
		return;
	}
	send_lookup_reply(ls, ms, ret_nodeid, error);
}

static void receive_remove(struct dlm_ls *ls, const struct dlm_message *ms)
{
	char name[DLM_RESNAME_MAXLEN+1];
	struct dlm_rsb *r;
	int rv, len, dir_nodeid, from_nodeid;

	from_nodeid = le32_to_cpu(ms->m_header.h_nodeid);

	len = receive_extralen(ms);

	if (len > DLM_RESNAME_MAXLEN) {
		log_error(ls, "receive_remove from %d bad len %d",
			  from_nodeid, len);
		return;
	}

	dir_nodeid = dlm_hash2nodeid(ls, le32_to_cpu(ms->m_hash));
	if (dir_nodeid != dlm_our_nodeid()) {
		log_error(ls, "receive_remove from %d bad nodeid %d",
			  from_nodeid, dir_nodeid);
		return;
	}

	/*
	 * Look for inactive rsb, if it's there, free it.
	 * If the rsb is active, it's being used, and we should ignore this
	 * message.  This is an expected race between the dir node sending a
	 * request to the master node at the same time as the master node sends
	 * a remove to the dir node.  The resolution to that race is for the
	 * dir node to ignore the remove message, and the master node to
	 * recreate the master rsb when it gets a request from the dir node for
	 * an rsb it doesn't have.
	 */

	memset(name, 0, sizeof(name));
	memcpy(name, ms->m_extra, len);

	rcu_read_lock();
	rv = dlm_search_rsb_tree(&ls->ls_rsbtbl, name, len, &r);
	if (rv) {
		rcu_read_unlock();
		/* should not happen */
		log_error(ls, "%s from %d not found %s", __func__,
			  from_nodeid, name);
		return;
	}

	write_lock_bh(&ls->ls_rsbtbl_lock);
	if (!rsb_flag(r, RSB_HASHED)) {
		rcu_read_unlock();
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		/* should not happen */
		log_error(ls, "%s from %d got removed during removal %s",
			  __func__, from_nodeid, name);
		return;
	}
	/* at this stage the rsb can only being freed here */
	rcu_read_unlock();

	if (!rsb_flag(r, RSB_INACTIVE)) {
		if (r->res_master_nodeid != from_nodeid) {
			/* should not happen */
			log_error(ls, "receive_remove on active rsb from %d master %d",
				  from_nodeid, r->res_master_nodeid);
			dlm_print_rsb(r);
			write_unlock_bh(&ls->ls_rsbtbl_lock);
			return;
		}

		/* Ignore the remove message, see race comment above. */

		log_debug(ls, "receive_remove from %d master %d first %x %s",
			  from_nodeid, r->res_master_nodeid, r->res_first_lkid,
			  name);
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		return;
	}

	if (r->res_master_nodeid != from_nodeid) {
		log_error(ls, "receive_remove inactive from %d master %d",
			  from_nodeid, r->res_master_nodeid);
		dlm_print_rsb(r);
		write_unlock_bh(&ls->ls_rsbtbl_lock);
		return;
	}

	list_del(&r->res_slow_list);
	rhashtable_remove_fast(&ls->ls_rsbtbl, &r->res_node,
			       dlm_rhash_rsb_params);
	rsb_clear_flag(r, RSB_HASHED);
	write_unlock_bh(&ls->ls_rsbtbl_lock);

	free_inactive_rsb(r);
}

static void receive_purge(struct dlm_ls *ls, const struct dlm_message *ms)
{
	do_purge(ls, le32_to_cpu(ms->m_nodeid), le32_to_cpu(ms->m_pid));
}

static int receive_request_reply(struct dlm_ls *ls,
				 const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error, mstype, result;
	int from_nodeid = le32_to_cpu(ms->m_header.h_nodeid);

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		return error;

	r = lkb->lkb_resource;
	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	mstype = lkb->lkb_wait_type;
	error = remove_from_waiters(lkb, DLM_MSG_REQUEST_REPLY);
	if (error) {
		log_error(ls, "receive_request_reply %x remote %d %x result %d",
			  lkb->lkb_id, from_nodeid, le32_to_cpu(ms->m_lkid),
			  from_dlm_errno(le32_to_cpu(ms->m_result)));
		dlm_dump_rsb(r);
		goto out;
	}

	/* Optimization: the dir node was also the master, so it took our
	   lookup as a request and sent request reply instead of lookup reply */
	if (mstype == DLM_MSG_LOOKUP) {
		r->res_master_nodeid = from_nodeid;
		r->res_nodeid = from_nodeid;
		lkb->lkb_nodeid = from_nodeid;
	}

	/* this is the value returned from do_request() on the master */
	result = from_dlm_errno(le32_to_cpu(ms->m_result));

	switch (result) {
	case -EAGAIN:
		/* request would block (be queued) on remote master */
		queue_cast(r, lkb, -EAGAIN);
		confirm_master(r, -EAGAIN);
		unhold_lkb(lkb); /* undoes create_lkb() */
		break;

	case -EINPROGRESS:
	case 0:
		/* request was queued or granted on remote master */
		receive_flags_reply(lkb, ms, false);
		lkb->lkb_remid = le32_to_cpu(ms->m_lkid);
		if (is_altmode(lkb))
			munge_altmode(lkb, ms);
		if (result) {
			add_lkb(r, lkb, DLM_LKSTS_WAITING);
		} else {
			grant_lock_pc(r, lkb, ms);
			queue_cast(r, lkb, 0);
		}
		confirm_master(r, result);
		break;

	case -EBADR:
	case -ENOTBLK:
		/* find_rsb failed to find rsb or rsb wasn't master */
		log_limit(ls, "receive_request_reply %x from %d %d "
			  "master %d dir %d first %x %s", lkb->lkb_id,
			  from_nodeid, result, r->res_master_nodeid,
			  r->res_dir_nodeid, r->res_first_lkid, r->res_name);

		if (r->res_dir_nodeid != dlm_our_nodeid() &&
		    r->res_master_nodeid != dlm_our_nodeid()) {
			/* cause _request_lock->set_master->send_lookup */
			r->res_master_nodeid = 0;
			r->res_nodeid = -1;
			lkb->lkb_nodeid = -1;
		}

		if (is_overlap(lkb)) {
			/* we'll ignore error in cancel/unlock reply */
			queue_cast_overlap(r, lkb);
			confirm_master(r, result);
			unhold_lkb(lkb); /* undoes create_lkb() */
		} else {
			_request_lock(r, lkb);

			if (r->res_master_nodeid == dlm_our_nodeid())
				confirm_master(r, 0);
		}
		break;

	default:
		log_error(ls, "receive_request_reply %x error %d",
			  lkb->lkb_id, result);
	}

	if ((result == 0 || result == -EINPROGRESS) &&
	    test_and_clear_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags)) {
		log_debug(ls, "receive_request_reply %x result %d unlock",
			  lkb->lkb_id, result);
		clear_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags);
		send_unlock(r, lkb);
	} else if ((result == -EINPROGRESS) &&
		   test_and_clear_bit(DLM_IFL_OVERLAP_CANCEL_BIT,
				      &lkb->lkb_iflags)) {
		log_debug(ls, "receive_request_reply %x cancel", lkb->lkb_id);
		clear_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags);
		send_cancel(r, lkb);
	} else {
		clear_bit(DLM_IFL_OVERLAP_CANCEL_BIT, &lkb->lkb_iflags);
		clear_bit(DLM_IFL_OVERLAP_UNLOCK_BIT, &lkb->lkb_iflags);
	}
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);
	return 0;
}

static void __receive_convert_reply(struct dlm_rsb *r, struct dlm_lkb *lkb,
				    const struct dlm_message *ms, bool local)
{
	/* this is the value returned from do_convert() on the master */
	switch (from_dlm_errno(le32_to_cpu(ms->m_result))) {
	case -EAGAIN:
		/* convert would block (be queued) on remote master */
		queue_cast(r, lkb, -EAGAIN);
		break;

	case -EDEADLK:
		receive_flags_reply(lkb, ms, local);
		revert_lock_pc(r, lkb);
		queue_cast(r, lkb, -EDEADLK);
		break;

	case -EINPROGRESS:
		/* convert was queued on remote master */
		receive_flags_reply(lkb, ms, local);
		if (is_demoted(lkb))
			munge_demoted(lkb);
		del_lkb(r, lkb);
		add_lkb(r, lkb, DLM_LKSTS_CONVERT);
		break;

	case 0:
		/* convert was granted on remote master */
		receive_flags_reply(lkb, ms, local);
		if (is_demoted(lkb))
			munge_demoted(lkb);
		grant_lock_pc(r, lkb, ms);
		queue_cast(r, lkb, 0);
		break;

	default:
		log_error(r->res_ls, "receive_convert_reply %x remote %d %x %d",
			  lkb->lkb_id, le32_to_cpu(ms->m_header.h_nodeid),
			  le32_to_cpu(ms->m_lkid),
			  from_dlm_errno(le32_to_cpu(ms->m_result)));
		dlm_print_rsb(r);
		dlm_print_lkb(lkb);
	}
}

static void _receive_convert_reply(struct dlm_lkb *lkb,
				   const struct dlm_message *ms, bool local)
{
	struct dlm_rsb *r = lkb->lkb_resource;
	int error;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	error = remove_from_waiters_ms(lkb, ms, local);
	if (error)
		goto out;

	__receive_convert_reply(r, lkb, ms, local);
 out:
	unlock_rsb(r);
	put_rsb(r);
}

static int receive_convert_reply(struct dlm_ls *ls,
				 const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	int error;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		return error;

	_receive_convert_reply(lkb, ms, false);
	dlm_put_lkb(lkb);
	return 0;
}

static void _receive_unlock_reply(struct dlm_lkb *lkb,
				  const struct dlm_message *ms, bool local)
{
	struct dlm_rsb *r = lkb->lkb_resource;
	int error;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	error = remove_from_waiters_ms(lkb, ms, local);
	if (error)
		goto out;

	/* this is the value returned from do_unlock() on the master */

	switch (from_dlm_errno(le32_to_cpu(ms->m_result))) {
	case -DLM_EUNLOCK:
		receive_flags_reply(lkb, ms, local);
		remove_lock_pc(r, lkb);
		queue_cast(r, lkb, -DLM_EUNLOCK);
		break;
	case -ENOENT:
		break;
	default:
		log_error(r->res_ls, "receive_unlock_reply %x error %d",
			  lkb->lkb_id, from_dlm_errno(le32_to_cpu(ms->m_result)));
	}
 out:
	unlock_rsb(r);
	put_rsb(r);
}

static int receive_unlock_reply(struct dlm_ls *ls,
				const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	int error;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		return error;

	_receive_unlock_reply(lkb, ms, false);
	dlm_put_lkb(lkb);
	return 0;
}

static void _receive_cancel_reply(struct dlm_lkb *lkb,
				  const struct dlm_message *ms, bool local)
{
	struct dlm_rsb *r = lkb->lkb_resource;
	int error;

	hold_rsb(r);
	lock_rsb(r);

	error = validate_message(lkb, ms);
	if (error)
		goto out;

	error = remove_from_waiters_ms(lkb, ms, local);
	if (error)
		goto out;

	/* this is the value returned from do_cancel() on the master */

	switch (from_dlm_errno(le32_to_cpu(ms->m_result))) {
	case -DLM_ECANCEL:
		receive_flags_reply(lkb, ms, local);
		revert_lock_pc(r, lkb);
		queue_cast(r, lkb, -DLM_ECANCEL);
		break;
	case 0:
		break;
	default:
		log_error(r->res_ls, "receive_cancel_reply %x error %d",
			  lkb->lkb_id,
			  from_dlm_errno(le32_to_cpu(ms->m_result)));
	}
 out:
	unlock_rsb(r);
	put_rsb(r);
}

static int receive_cancel_reply(struct dlm_ls *ls,
				const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	int error;

	error = find_lkb(ls, le32_to_cpu(ms->m_remid), &lkb);
	if (error)
		return error;

	_receive_cancel_reply(lkb, ms, false);
	dlm_put_lkb(lkb);
	return 0;
}

static void receive_lookup_reply(struct dlm_ls *ls,
				 const struct dlm_message *ms)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error, ret_nodeid;
	int do_lookup_list = 0;

	error = find_lkb(ls, le32_to_cpu(ms->m_lkid), &lkb);
	if (error) {
		log_error(ls, "%s no lkid %x", __func__,
			  le32_to_cpu(ms->m_lkid));
		return;
	}

	/* ms->m_result is the value returned by dlm_master_lookup on dir node
	   FIXME: will a non-zero error ever be returned? */

	r = lkb->lkb_resource;
	hold_rsb(r);
	lock_rsb(r);

	error = remove_from_waiters(lkb, DLM_MSG_LOOKUP_REPLY);
	if (error)
		goto out;

	ret_nodeid = le32_to_cpu(ms->m_nodeid);

	/* We sometimes receive a request from the dir node for this
	   rsb before we've received the dir node's loookup_reply for it.
	   The request from the dir node implies we're the master, so we set
	   ourself as master in receive_request_reply, and verify here that
	   we are indeed the master. */

	if (r->res_master_nodeid && (r->res_master_nodeid != ret_nodeid)) {
		/* This should never happen */
		log_error(ls, "receive_lookup_reply %x from %d ret %d "
			  "master %d dir %d our %d first %x %s",
			  lkb->lkb_id, le32_to_cpu(ms->m_header.h_nodeid),
			  ret_nodeid, r->res_master_nodeid, r->res_dir_nodeid,
			  dlm_our_nodeid(), r->res_first_lkid, r->res_name);
	}

	if (ret_nodeid == dlm_our_nodeid()) {
		r->res_master_nodeid = ret_nodeid;
		r->res_nodeid = 0;
		do_lookup_list = 1;
		r->res_first_lkid = 0;
	} else if (ret_nodeid == -1) {
		/* the remote node doesn't believe it's the dir node */
		log_error(ls, "receive_lookup_reply %x from %d bad ret_nodeid",
			  lkb->lkb_id, le32_to_cpu(ms->m_header.h_nodeid));
		r->res_master_nodeid = 0;
		r->res_nodeid = -1;
		lkb->lkb_nodeid = -1;
	} else {
		/* set_master() will set lkb_nodeid from r */
		r->res_master_nodeid = ret_nodeid;
		r->res_nodeid = ret_nodeid;
	}

	if (is_overlap(lkb)) {
		log_debug(ls, "receive_lookup_reply %x unlock %x",
			  lkb->lkb_id, dlm_iflags_val(lkb));
		queue_cast_overlap(r, lkb);
		unhold_lkb(lkb); /* undoes create_lkb() */
		goto out_list;
	}

	_request_lock(r, lkb);

 out_list:
	if (do_lookup_list)
		process_lookup_list(r);
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);
}

static void _receive_message(struct dlm_ls *ls, const struct dlm_message *ms,
			     uint32_t saved_seq)
{
	int error = 0, noent = 0;

	if (WARN_ON_ONCE(!dlm_is_member(ls, le32_to_cpu(ms->m_header.h_nodeid)))) {
		log_limit(ls, "receive %d from non-member %d %x %x %d",
			  le32_to_cpu(ms->m_type),
			  le32_to_cpu(ms->m_header.h_nodeid),
			  le32_to_cpu(ms->m_lkid), le32_to_cpu(ms->m_remid),
			  from_dlm_errno(le32_to_cpu(ms->m_result)));
		return;
	}

	switch (ms->m_type) {

	/* messages sent to a master node */

	case cpu_to_le32(DLM_MSG_REQUEST):
		error = receive_request(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_CONVERT):
		error = receive_convert(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_UNLOCK):
		error = receive_unlock(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_CANCEL):
		noent = 1;
		error = receive_cancel(ls, ms);
		break;

	/* messages sent from a master node (replies to above) */

	case cpu_to_le32(DLM_MSG_REQUEST_REPLY):
		error = receive_request_reply(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_CONVERT_REPLY):
		error = receive_convert_reply(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_UNLOCK_REPLY):
		error = receive_unlock_reply(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_CANCEL_REPLY):
		error = receive_cancel_reply(ls, ms);
		break;

	/* messages sent from a master node (only two types of async msg) */

	case cpu_to_le32(DLM_MSG_GRANT):
		noent = 1;
		error = receive_grant(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_BAST):
		noent = 1;
		error = receive_bast(ls, ms);
		break;

	/* messages sent to a dir node */

	case cpu_to_le32(DLM_MSG_LOOKUP):
		receive_lookup(ls, ms);
		break;

	case cpu_to_le32(DLM_MSG_REMOVE):
		receive_remove(ls, ms);
		break;

	/* messages sent from a dir node (remove has no reply) */

	case cpu_to_le32(DLM_MSG_LOOKUP_REPLY):
		receive_lookup_reply(ls, ms);
		break;

	/* other messages */

	case cpu_to_le32(DLM_MSG_PURGE):
		receive_purge(ls, ms);
		break;

	default:
		log_error(ls, "unknown message type %d",
			  le32_to_cpu(ms->m_type));
	}

	/*
	 * When checking for ENOENT, we're checking the result of
	 * find_lkb(m_remid):
	 *
	 * The lock id referenced in the message wasn't found.  This may
	 * happen in normal usage for the async messages and cancel, so
	 * only use log_debug for them.
	 *
	 * Some errors are expected and normal.
	 */

	if (error == -ENOENT && noent) {
		log_debug(ls, "receive %d no %x remote %d %x saved_seq %u",
			  le32_to_cpu(ms->m_type), le32_to_cpu(ms->m_remid),
			  le32_to_cpu(ms->m_header.h_nodeid),
			  le32_to_cpu(ms->m_lkid), saved_seq);
	} else if (error == -ENOENT) {
		log_error(ls, "receive %d no %x remote %d %x saved_seq %u",
			  le32_to_cpu(ms->m_type), le32_to_cpu(ms->m_remid),
			  le32_to_cpu(ms->m_header.h_nodeid),
			  le32_to_cpu(ms->m_lkid), saved_seq);

		if (ms->m_type == cpu_to_le32(DLM_MSG_CONVERT))
			dlm_dump_rsb_hash(ls, le32_to_cpu(ms->m_hash));
	}

	if (error == -EINVAL) {
		log_error(ls, "receive %d inval from %d lkid %x remid %x "
			  "saved_seq %u",
			  le32_to_cpu(ms->m_type),
			  le32_to_cpu(ms->m_header.h_nodeid),
			  le32_to_cpu(ms->m_lkid), le32_to_cpu(ms->m_remid),
			  saved_seq);
	}
}

/* If the lockspace is in recovery mode (locking stopped), then normal
   messages are saved on the requestqueue for processing after recovery is
   done.  When not in recovery mode, we wait for dlm_recoverd to drain saved
   messages off the requestqueue before we process new ones. This occurs right
   after recovery completes when we transition from saving all messages on
   requestqueue, to processing all the saved messages, to processing new
   messages as they arrive. */

static void dlm_receive_message(struct dlm_ls *ls, const struct dlm_message *ms,
				int nodeid)
{
try_again:
	read_lock_bh(&ls->ls_requestqueue_lock);
	if (test_bit(LSFL_RECV_MSG_BLOCKED, &ls->ls_flags)) {
		/* If we were a member of this lockspace, left, and rejoined,
		   other nodes may still be sending us messages from the
		   lockspace generation before we left. */
		if (WARN_ON_ONCE(!ls->ls_generation)) {
			read_unlock_bh(&ls->ls_requestqueue_lock);
			log_limit(ls, "receive %d from %d ignore old gen",
				  le32_to_cpu(ms->m_type), nodeid);
			return;
		}

		read_unlock_bh(&ls->ls_requestqueue_lock);
		write_lock_bh(&ls->ls_requestqueue_lock);
		/* recheck because we hold writelock now */
		if (!test_bit(LSFL_RECV_MSG_BLOCKED, &ls->ls_flags)) {
			write_unlock_bh(&ls->ls_requestqueue_lock);
			goto try_again;
		}

		dlm_add_requestqueue(ls, nodeid, ms);
		write_unlock_bh(&ls->ls_requestqueue_lock);
	} else {
		_receive_message(ls, ms, 0);
		read_unlock_bh(&ls->ls_requestqueue_lock);
	}
}

/* This is called by dlm_recoverd to process messages that were saved on
   the requestqueue. */

void dlm_receive_message_saved(struct dlm_ls *ls, const struct dlm_message *ms,
			       uint32_t saved_seq)
{
	_receive_message(ls, ms, saved_seq);
}

/* This is called by the midcomms layer when something is received for
   the lockspace.  It could be either a MSG (normal message sent as part of
   standard locking activity) or an RCOM (recovery message sent as part of
   lockspace recovery). */

void dlm_receive_buffer(const union dlm_packet *p, int nodeid)
{
	const struct dlm_header *hd = &p->header;
	struct dlm_ls *ls;
	int type = 0;

	switch (hd->h_cmd) {
	case DLM_MSG:
		type = le32_to_cpu(p->message.m_type);
		break;
	case DLM_RCOM:
		type = le32_to_cpu(p->rcom.rc_type);
		break;
	default:
		log_print("invalid h_cmd %d from %u", hd->h_cmd, nodeid);
		return;
	}

	if (le32_to_cpu(hd->h_nodeid) != nodeid) {
		log_print("invalid h_nodeid %d from %d lockspace %x",
			  le32_to_cpu(hd->h_nodeid), nodeid,
			  le32_to_cpu(hd->u.h_lockspace));
		return;
	}

	ls = dlm_find_lockspace_global(le32_to_cpu(hd->u.h_lockspace));
	if (!ls) {
		if (dlm_config.ci_log_debug) {
			printk_ratelimited(KERN_DEBUG "dlm: invalid lockspace "
				"%u from %d cmd %d type %d\n",
				le32_to_cpu(hd->u.h_lockspace), nodeid,
				hd->h_cmd, type);
		}

		if (hd->h_cmd == DLM_RCOM && type == DLM_RCOM_STATUS)
			dlm_send_ls_not_ready(nodeid, &p->rcom);
		return;
	}

	/* this rwsem allows dlm_ls_stop() to wait for all dlm_recv threads to
	   be inactive (in this ls) before transitioning to recovery mode */

	read_lock_bh(&ls->ls_recv_active);
	if (hd->h_cmd == DLM_MSG)
		dlm_receive_message(ls, &p->message, nodeid);
	else if (hd->h_cmd == DLM_RCOM)
		dlm_receive_rcom(ls, &p->rcom, nodeid);
	else
		log_error(ls, "invalid h_cmd %d from %d lockspace %x",
			  hd->h_cmd, nodeid, le32_to_cpu(hd->u.h_lockspace));
	read_unlock_bh(&ls->ls_recv_active);

	dlm_put_lockspace(ls);
}

static void recover_convert_waiter(struct dlm_ls *ls, struct dlm_lkb *lkb,
				   struct dlm_message *ms_local)
{
	if (middle_conversion(lkb)) {
		log_rinfo(ls, "%s %x middle convert in progress", __func__,
			 lkb->lkb_id);

		/* We sent this lock to the new master. The new master will
		 * tell us when it's granted.  We no longer need a reply, so
		 * use a fake reply to put the lkb into the right state.
		 */
		hold_lkb(lkb);
		memset(ms_local, 0, sizeof(struct dlm_message));
		ms_local->m_type = cpu_to_le32(DLM_MSG_CONVERT_REPLY);
		ms_local->m_result = cpu_to_le32(to_dlm_errno(-EINPROGRESS));
		ms_local->m_header.h_nodeid = cpu_to_le32(lkb->lkb_nodeid);
		_receive_convert_reply(lkb, ms_local, true);
		unhold_lkb(lkb);

	} else if (lkb->lkb_rqmode >= lkb->lkb_grmode) {
		set_bit(DLM_IFL_RESEND_BIT, &lkb->lkb_iflags);
	}

	/* lkb->lkb_rqmode < lkb->lkb_grmode shouldn't happen since down
	   conversions are async; there's no reply from the remote master */
}

/* A waiting lkb needs recovery if the master node has failed, or
   the master node is changing (only when no directory is used) */

static int waiter_needs_recovery(struct dlm_ls *ls, struct dlm_lkb *lkb,
				 int dir_nodeid)
{
	if (dlm_no_directory(ls))
		return 1;

	if (dlm_is_removed(ls, lkb->lkb_wait_nodeid))
		return 1;

	return 0;
}

/* Recovery for locks that are waiting for replies from nodes that are now
   gone.  We can just complete unlocks and cancels by faking a reply from the
   dead node.  Requests and up-conversions we flag to be resent after
   recovery.  Down-conversions can just be completed with a fake reply like
   unlocks.  Conversions between PR and CW need special attention. */

void dlm_recover_waiters_pre(struct dlm_ls *ls)
{
	struct dlm_lkb *lkb, *safe;
	struct dlm_message *ms_local;
	int wait_type, local_unlock_result, local_cancel_result;
	int dir_nodeid;

	ms_local = kmalloc(sizeof(*ms_local), GFP_KERNEL);
	if (!ms_local)
		return;

	list_for_each_entry_safe(lkb, safe, &ls->ls_waiters, lkb_wait_reply) {

		dir_nodeid = dlm_dir_nodeid(lkb->lkb_resource);

		/* exclude debug messages about unlocks because there can be so
		   many and they aren't very interesting */

		if (lkb->lkb_wait_type != DLM_MSG_UNLOCK) {
			log_debug(ls, "waiter %x remote %x msg %d r_nodeid %d "
				  "lkb_nodeid %d wait_nodeid %d dir_nodeid %d",
				  lkb->lkb_id,
				  lkb->lkb_remid,
				  lkb->lkb_wait_type,
				  lkb->lkb_resource->res_nodeid,
				  lkb->lkb_nodeid,
				  lkb->lkb_wait_nodeid,
				  dir_nodeid);
		}

		/* all outstanding lookups, regardless of destination  will be
		   resent after recovery is done */

		if (lkb->lkb_wait_type == DLM_MSG_LOOKUP) {
			set_bit(DLM_IFL_RESEND_BIT, &lkb->lkb_iflags);
			continue;
		}

		if (!waiter_needs_recovery(ls, lkb, dir_nodeid))
			continue;

		wait_type = lkb->lkb_wait_type;
		local_unlock_result = -DLM_EUNLOCK;
		local_cancel_result = -DLM_ECANCEL;

		/* Main reply may have been received leaving a zero wait_type,
		   but a reply for the overlapping op may not have been
		   received.  In that case we need to fake the appropriate
		   reply for the overlap op. */

		if (!wait_type) {
			if (is_overlap_cancel(lkb)) {
				wait_type = DLM_MSG_CANCEL;
				if (lkb->lkb_grmode == DLM_LOCK_IV)
					local_cancel_result = 0;
			}
			if (is_overlap_unlock(lkb)) {
				wait_type = DLM_MSG_UNLOCK;
				if (lkb->lkb_grmode == DLM_LOCK_IV)
					local_unlock_result = -ENOENT;
			}

			log_debug(ls, "rwpre overlap %x %x %d %d %d",
				  lkb->lkb_id, dlm_iflags_val(lkb), wait_type,
				  local_cancel_result, local_unlock_result);
		}

		switch (wait_type) {

		case DLM_MSG_REQUEST:
			set_bit(DLM_IFL_RESEND_BIT, &lkb->lkb_iflags);
			break;

		case DLM_MSG_CONVERT:
			recover_convert_waiter(ls, lkb, ms_local);
			break;

		case DLM_MSG_UNLOCK:
			hold_lkb(lkb);
			memset(ms_local, 0, sizeof(struct dlm_message));
			ms_local->m_type = cpu_to_le32(DLM_MSG_UNLOCK_REPLY);
			ms_local->m_result = cpu_to_le32(to_dlm_errno(local_unlock_result));
			ms_local->m_header.h_nodeid = cpu_to_le32(lkb->lkb_nodeid);
			_receive_unlock_reply(lkb, ms_local, true);
			dlm_put_lkb(lkb);
			break;

		case DLM_MSG_CANCEL:
			hold_lkb(lkb);
			memset(ms_local, 0, sizeof(struct dlm_message));
			ms_local->m_type = cpu_to_le32(DLM_MSG_CANCEL_REPLY);
			ms_local->m_result = cpu_to_le32(to_dlm_errno(local_cancel_result));
			ms_local->m_header.h_nodeid = cpu_to_le32(lkb->lkb_nodeid);
			_receive_cancel_reply(lkb, ms_local, true);
			dlm_put_lkb(lkb);
			break;

		default:
			log_error(ls, "invalid lkb wait_type %d %d",
				  lkb->lkb_wait_type, wait_type);
		}
		schedule();
	}
	kfree(ms_local);
}

static struct dlm_lkb *find_resend_waiter(struct dlm_ls *ls)
{
	struct dlm_lkb *lkb = NULL, *iter;

	spin_lock_bh(&ls->ls_waiters_lock);
	list_for_each_entry(iter, &ls->ls_waiters, lkb_wait_reply) {
		if (test_bit(DLM_IFL_RESEND_BIT, &iter->lkb_iflags)) {
			hold_lkb(iter);
			lkb = iter;
			break;
		}
	}
	spin_unlock_bh(&ls->ls_waiters_lock);

	return lkb;
}

/*
 * Forced state reset for locks that were in the middle of remote operations
 * when recovery happened (i.e. lkbs that were on the waiters list, waiting
 * for a reply from a remote operation.)  The lkbs remaining on the waiters
 * list need to be reevaluated; some may need resending to a different node
 * than previously, and some may now need local handling rather than remote.
 *
 * First, the lkb state for the voided remote operation is forcibly reset,
 * equivalent to what remove_from_waiters() would normally do:
 * . lkb removed from ls_waiters list
 * . lkb wait_type cleared
 * . lkb waiters_count cleared
 * . lkb ref count decremented for each waiters_count (almost always 1,
 *   but possibly 2 in case of cancel/unlock overlapping, which means
 *   two remote replies were being expected for the lkb.)
 *
 * Second, the lkb is reprocessed like an original operation would be,
 * by passing it to _request_lock or _convert_lock, which will either
 * process the lkb operation locally, or send it to a remote node again
 * and put the lkb back onto the waiters list.
 *
 * When reprocessing the lkb, we may find that it's flagged for an overlapping
 * force-unlock or cancel, either from before recovery began, or after recovery
 * finished.  If this is the case, the unlock/cancel is done directly, and the
 * original operation is not initiated again (no _request_lock/_convert_lock.)
 */

int dlm_recover_waiters_post(struct dlm_ls *ls)
{
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error = 0, mstype, err, oc, ou;

	while (1) {
		if (dlm_locking_stopped(ls)) {
			log_debug(ls, "recover_waiters_post aborted");
			error = -EINTR;
			break;
		}

		/* 
		 * Find an lkb from the waiters list that's been affected by
		 * recovery node changes, and needs to be reprocessed.  Does
		 * hold_lkb(), adding a refcount.
		 */
		lkb = find_resend_waiter(ls);
		if (!lkb)
			break;

		r = lkb->lkb_resource;
		hold_rsb(r);
		lock_rsb(r);

		/*
		 * If the lkb has been flagged for a force unlock or cancel,
		 * then the reprocessing below will be replaced by just doing
		 * the unlock/cancel directly.
		 */
		mstype = lkb->lkb_wait_type;
		oc = test_and_clear_bit(DLM_IFL_OVERLAP_CANCEL_BIT,
					&lkb->lkb_iflags);
		ou = test_and_clear_bit(DLM_IFL_OVERLAP_UNLOCK_BIT,
					&lkb->lkb_iflags);
		err = 0;

		log_debug(ls, "waiter %x remote %x msg %d r_nodeid %d "
			  "lkb_nodeid %d wait_nodeid %d dir_nodeid %d "
			  "overlap %d %d", lkb->lkb_id, lkb->lkb_remid, mstype,
			  r->res_nodeid, lkb->lkb_nodeid, lkb->lkb_wait_nodeid,
			  dlm_dir_nodeid(r), oc, ou);

		/*
		 * No reply to the pre-recovery operation will now be received,
		 * so a forced equivalent of remove_from_waiters() is needed to
		 * reset the waiters state that was in place before recovery.
		 */

		clear_bit(DLM_IFL_RESEND_BIT, &lkb->lkb_iflags);

		/* Forcibly clear wait_type */
		lkb->lkb_wait_type = 0;

		/*
		 * Forcibly reset wait_count and associated refcount.  The
		 * wait_count will almost always be 1, but in case of an
		 * overlapping unlock/cancel it could be 2: see where
		 * add_to_waiters() finds the lkb is already on the waiters
		 * list and does lkb_wait_count++; hold_lkb().
		 */
		while (lkb->lkb_wait_count) {
			lkb->lkb_wait_count--;
			unhold_lkb(lkb);
		}

		/* Forcibly remove from waiters list */
		spin_lock_bh(&ls->ls_waiters_lock);
		list_del_init(&lkb->lkb_wait_reply);
		spin_unlock_bh(&ls->ls_waiters_lock);

		/*
		 * The lkb is now clear of all prior waiters state and can be
		 * processed locally, or sent to remote node again, or directly
		 * cancelled/unlocked.
		 */

		if (oc || ou) {
			/* do an unlock or cancel instead of resending */
			switch (mstype) {
			case DLM_MSG_LOOKUP:
			case DLM_MSG_REQUEST:
				queue_cast(r, lkb, ou ? -DLM_EUNLOCK :
							-DLM_ECANCEL);
				unhold_lkb(lkb); /* undoes create_lkb() */
				break;
			case DLM_MSG_CONVERT:
				if (oc) {
					queue_cast(r, lkb, -DLM_ECANCEL);
				} else {
					lkb->lkb_exflags |= DLM_LKF_FORCEUNLOCK;
					_unlock_lock(r, lkb);
				}
				break;
			default:
				err = 1;
			}
		} else {
			switch (mstype) {
			case DLM_MSG_LOOKUP:
			case DLM_MSG_REQUEST:
				_request_lock(r, lkb);
				if (r->res_nodeid != -1 && is_master(r))
					confirm_master(r, 0);
				break;
			case DLM_MSG_CONVERT:
				_convert_lock(r, lkb);
				break;
			default:
				err = 1;
			}
		}

		if (err) {
			log_error(ls, "waiter %x msg %d r_nodeid %d "
				  "dir_nodeid %d overlap %d %d",
				  lkb->lkb_id, mstype, r->res_nodeid,
				  dlm_dir_nodeid(r), oc, ou);
		}
		unlock_rsb(r);
		put_rsb(r);
		dlm_put_lkb(lkb);
	}

	return error;
}

static void purge_mstcpy_list(struct dlm_ls *ls, struct dlm_rsb *r,
			      struct list_head *list)
{
	struct dlm_lkb *lkb, *safe;

	list_for_each_entry_safe(lkb, safe, list, lkb_statequeue) {
		if (!is_master_copy(lkb))
			continue;

		/* don't purge lkbs we've added in recover_master_copy for
		   the current recovery seq */

		if (lkb->lkb_recover_seq == ls->ls_recover_seq)
			continue;

		del_lkb(r, lkb);

		/* this put should free the lkb */
		if (!dlm_put_lkb(lkb))
			log_error(ls, "purged mstcpy lkb not released");
	}
}

void dlm_purge_mstcpy_locks(struct dlm_rsb *r)
{
	struct dlm_ls *ls = r->res_ls;

	purge_mstcpy_list(ls, r, &r->res_grantqueue);
	purge_mstcpy_list(ls, r, &r->res_convertqueue);
	purge_mstcpy_list(ls, r, &r->res_waitqueue);
}

static void purge_dead_list(struct dlm_ls *ls, struct dlm_rsb *r,
			    struct list_head *list,
			    int nodeid_gone, unsigned int *count)
{
	struct dlm_lkb *lkb, *safe;

	list_for_each_entry_safe(lkb, safe, list, lkb_statequeue) {
		if (!is_master_copy(lkb))
			continue;

		if ((lkb->lkb_nodeid == nodeid_gone) ||
		    dlm_is_removed(ls, lkb->lkb_nodeid)) {

			/* tell recover_lvb to invalidate the lvb
			   because a node holding EX/PW failed */
			if ((lkb->lkb_exflags & DLM_LKF_VALBLK) &&
			    (lkb->lkb_grmode >= DLM_LOCK_PW)) {
				rsb_set_flag(r, RSB_RECOVER_LVB_INVAL);
			}

			del_lkb(r, lkb);

			/* this put should free the lkb */
			if (!dlm_put_lkb(lkb))
				log_error(ls, "purged dead lkb not released");

			rsb_set_flag(r, RSB_RECOVER_GRANT);

			(*count)++;
		}
	}
}

/* Get rid of locks held by nodes that are gone. */

void dlm_recover_purge(struct dlm_ls *ls, const struct list_head *root_list)
{
	struct dlm_rsb *r;
	struct dlm_member *memb;
	int nodes_count = 0;
	int nodeid_gone = 0;
	unsigned int lkb_count = 0;

	/* cache one removed nodeid to optimize the common
	   case of a single node removed */

	list_for_each_entry(memb, &ls->ls_nodes_gone, list) {
		nodes_count++;
		nodeid_gone = memb->nodeid;
	}

	if (!nodes_count)
		return;

	list_for_each_entry(r, root_list, res_root_list) {
		lock_rsb(r);
		if (r->res_nodeid != -1 && is_master(r)) {
			purge_dead_list(ls, r, &r->res_grantqueue,
					nodeid_gone, &lkb_count);
			purge_dead_list(ls, r, &r->res_convertqueue,
					nodeid_gone, &lkb_count);
			purge_dead_list(ls, r, &r->res_waitqueue,
					nodeid_gone, &lkb_count);
		}
		unlock_rsb(r);

		cond_resched();
	}

	if (lkb_count)
		log_rinfo(ls, "dlm_recover_purge %u locks for %u nodes",
			  lkb_count, nodes_count);
}

static struct dlm_rsb *find_grant_rsb(struct dlm_ls *ls)
{
	struct dlm_rsb *r;

	read_lock_bh(&ls->ls_rsbtbl_lock);
	list_for_each_entry(r, &ls->ls_slow_active, res_slow_list) {
		if (!rsb_flag(r, RSB_RECOVER_GRANT))
			continue;
		if (!is_master(r)) {
			rsb_clear_flag(r, RSB_RECOVER_GRANT);
			continue;
		}
		hold_rsb(r);
		read_unlock_bh(&ls->ls_rsbtbl_lock);
		return r;
	}
	read_unlock_bh(&ls->ls_rsbtbl_lock);
	return NULL;
}

/*
 * Attempt to grant locks on resources that we are the master of.
 * Locks may have become grantable during recovery because locks
 * from departed nodes have been purged (or not rebuilt), allowing
 * previously blocked locks to now be granted.  The subset of rsb's
 * we are interested in are those with lkb's on either the convert or
 * waiting queues.
 *
 * Simplest would be to go through each master rsb and check for non-empty
 * convert or waiting queues, and attempt to grant on those rsbs.
 * Checking the queues requires lock_rsb, though, for which we'd need
 * to release the rsbtbl lock.  This would make iterating through all
 * rsb's very inefficient.  So, we rely on earlier recovery routines
 * to set RECOVER_GRANT on any rsb's that we should attempt to grant
 * locks for.
 */

void dlm_recover_grant(struct dlm_ls *ls)
{
	struct dlm_rsb *r;
	unsigned int count = 0;
	unsigned int rsb_count = 0;
	unsigned int lkb_count = 0;

	while (1) {
		r = find_grant_rsb(ls);
		if (!r)
			break;

		rsb_count++;
		count = 0;
		lock_rsb(r);
		/* the RECOVER_GRANT flag is checked in the grant path */
		grant_pending_locks(r, &count);
		rsb_clear_flag(r, RSB_RECOVER_GRANT);
		lkb_count += count;
		confirm_master(r, 0);
		unlock_rsb(r);
		put_rsb(r);
		cond_resched();
	}

	if (lkb_count)
		log_rinfo(ls, "dlm_recover_grant %u locks on %u resources",
			  lkb_count, rsb_count);
}

static struct dlm_lkb *search_remid_list(struct list_head *head, int nodeid,
					 uint32_t remid)
{
	struct dlm_lkb *lkb;

	list_for_each_entry(lkb, head, lkb_statequeue) {
		if (lkb->lkb_nodeid == nodeid && lkb->lkb_remid == remid)
			return lkb;
	}
	return NULL;
}

static struct dlm_lkb *search_remid(struct dlm_rsb *r, int nodeid,
				    uint32_t remid)
{
	struct dlm_lkb *lkb;

	lkb = search_remid_list(&r->res_grantqueue, nodeid, remid);
	if (lkb)
		return lkb;
	lkb = search_remid_list(&r->res_convertqueue, nodeid, remid);
	if (lkb)
		return lkb;
	lkb = search_remid_list(&r->res_waitqueue, nodeid, remid);
	if (lkb)
		return lkb;
	return NULL;
}

/* needs at least dlm_rcom + rcom_lock */
static int receive_rcom_lock_args(struct dlm_ls *ls, struct dlm_lkb *lkb,
				  struct dlm_rsb *r, const struct dlm_rcom *rc)
{
	struct rcom_lock *rl = (struct rcom_lock *) rc->rc_buf;

	lkb->lkb_nodeid = le32_to_cpu(rc->rc_header.h_nodeid);
	lkb->lkb_ownpid = le32_to_cpu(rl->rl_ownpid);
	lkb->lkb_remid = le32_to_cpu(rl->rl_lkid);
	lkb->lkb_exflags = le32_to_cpu(rl->rl_exflags);
	dlm_set_dflags_val(lkb, le32_to_cpu(rl->rl_flags));
	set_bit(DLM_IFL_MSTCPY_BIT, &lkb->lkb_iflags);
	lkb->lkb_lvbseq = le32_to_cpu(rl->rl_lvbseq);
	lkb->lkb_rqmode = rl->rl_rqmode;
	lkb->lkb_grmode = rl->rl_grmode;
	/* don't set lkb_status because add_lkb wants to itself */

	lkb->lkb_bastfn = (rl->rl_asts & DLM_CB_BAST) ? &fake_bastfn : NULL;
	lkb->lkb_astfn = (rl->rl_asts & DLM_CB_CAST) ? &fake_astfn : NULL;

	if (lkb->lkb_exflags & DLM_LKF_VALBLK) {
		int lvblen = le16_to_cpu(rc->rc_header.h_length) -
			sizeof(struct dlm_rcom) - sizeof(struct rcom_lock);
		if (lvblen > ls->ls_lvblen)
			return -EINVAL;
		lkb->lkb_lvbptr = dlm_allocate_lvb(ls);
		if (!lkb->lkb_lvbptr)
			return -ENOMEM;
		memcpy(lkb->lkb_lvbptr, rl->rl_lvb, lvblen);
	}

	/* Conversions between PR and CW (middle modes) need special handling.
	   The real granted mode of these converting locks cannot be determined
	   until all locks have been rebuilt on the rsb (recover_conversion) */

	if (rl->rl_status == DLM_LKSTS_CONVERT && middle_conversion(lkb)) {
		/* We may need to adjust grmode depending on other granted locks. */
		log_limit(ls, "%s %x middle convert gr %d rq %d remote %d %x",
			  __func__, lkb->lkb_id, lkb->lkb_grmode,
			  lkb->lkb_rqmode, lkb->lkb_nodeid, lkb->lkb_remid);
		rsb_set_flag(r, RSB_RECOVER_CONVERT);
	}

	return 0;
}

/* This lkb may have been recovered in a previous aborted recovery so we need
   to check if the rsb already has an lkb with the given remote nodeid/lkid.
   If so we just send back a standard reply.  If not, we create a new lkb with
   the given values and send back our lkid.  We send back our lkid by sending
   back the rcom_lock struct we got but with the remid field filled in. */

/* needs at least dlm_rcom + rcom_lock */
int dlm_recover_master_copy(struct dlm_ls *ls, const struct dlm_rcom *rc,
			    __le32 *rl_remid, __le32 *rl_result)
{
	struct rcom_lock *rl = (struct rcom_lock *) rc->rc_buf;
	struct dlm_rsb *r;
	struct dlm_lkb *lkb;
	uint32_t remid = 0;
	int from_nodeid = le32_to_cpu(rc->rc_header.h_nodeid);
	int error;

	/* init rl_remid with rcom lock rl_remid */
	*rl_remid = rl->rl_remid;

	if (rl->rl_parent_lkid) {
		error = -EOPNOTSUPP;
		goto out;
	}

	remid = le32_to_cpu(rl->rl_lkid);

	/* In general we expect the rsb returned to be R_MASTER, but we don't
	   have to require it.  Recovery of masters on one node can overlap
	   recovery of locks on another node, so one node can send us MSTCPY
	   locks before we've made ourselves master of this rsb.  We can still
	   add new MSTCPY locks that we receive here without any harm; when
	   we make ourselves master, dlm_recover_masters() won't touch the
	   MSTCPY locks we've received early. */

	error = find_rsb(ls, rl->rl_name, le16_to_cpu(rl->rl_namelen),
			 from_nodeid, R_RECEIVE_RECOVER, &r);
	if (error)
		goto out;

	lock_rsb(r);

	if (dlm_no_directory(ls) && (dlm_dir_nodeid(r) != dlm_our_nodeid())) {
		log_error(ls, "dlm_recover_master_copy remote %d %x not dir",
			  from_nodeid, remid);
		error = -EBADR;
		goto out_unlock;
	}

	lkb = search_remid(r, from_nodeid, remid);
	if (lkb) {
		error = -EEXIST;
		goto out_remid;
	}

	error = create_lkb(ls, &lkb);
	if (error)
		goto out_unlock;

	error = receive_rcom_lock_args(ls, lkb, r, rc);
	if (error) {
		__put_lkb(ls, lkb);
		goto out_unlock;
	}

	attach_lkb(r, lkb);
	add_lkb(r, lkb, rl->rl_status);
	ls->ls_recover_locks_in++;

	if (!list_empty(&r->res_waitqueue) || !list_empty(&r->res_convertqueue))
		rsb_set_flag(r, RSB_RECOVER_GRANT);

 out_remid:
	/* this is the new value returned to the lock holder for
	   saving in its process-copy lkb */
	*rl_remid = cpu_to_le32(lkb->lkb_id);

	lkb->lkb_recover_seq = ls->ls_recover_seq;

 out_unlock:
	unlock_rsb(r);
	put_rsb(r);
 out:
	if (error && error != -EEXIST)
		log_rinfo(ls, "dlm_recover_master_copy remote %d %x error %d",
			  from_nodeid, remid, error);
	*rl_result = cpu_to_le32(error);
	return error;
}

/* needs at least dlm_rcom + rcom_lock */
int dlm_recover_process_copy(struct dlm_ls *ls, const struct dlm_rcom *rc,
			     uint64_t seq)
{
	struct rcom_lock *rl = (struct rcom_lock *) rc->rc_buf;
	struct dlm_rsb *r;
	struct dlm_lkb *lkb;
	uint32_t lkid, remid;
	int error, result;

	lkid = le32_to_cpu(rl->rl_lkid);
	remid = le32_to_cpu(rl->rl_remid);
	result = le32_to_cpu(rl->rl_result);

	error = find_lkb(ls, lkid, &lkb);
	if (error) {
		log_error(ls, "dlm_recover_process_copy no %x remote %d %x %d",
			  lkid, le32_to_cpu(rc->rc_header.h_nodeid), remid,
			  result);
		return error;
	}

	r = lkb->lkb_resource;
	hold_rsb(r);
	lock_rsb(r);

	if (!is_process_copy(lkb)) {
		log_error(ls, "dlm_recover_process_copy bad %x remote %d %x %d",
			  lkid, le32_to_cpu(rc->rc_header.h_nodeid), remid,
			  result);
		dlm_dump_rsb(r);
		unlock_rsb(r);
		put_rsb(r);
		dlm_put_lkb(lkb);
		return -EINVAL;
	}

	switch (result) {
	case -EBADR:
		/* There's a chance the new master received our lock before
		   dlm_recover_master_reply(), this wouldn't happen if we did
		   a barrier between recover_masters and recover_locks. */

		log_debug(ls, "dlm_recover_process_copy %x remote %d %x %d",
			  lkid, le32_to_cpu(rc->rc_header.h_nodeid), remid,
			  result);
	
		dlm_send_rcom_lock(r, lkb, seq);
		goto out;
	case -EEXIST:
	case 0:
		lkb->lkb_remid = remid;
		break;
	default:
		log_error(ls, "dlm_recover_process_copy %x remote %d %x %d unk",
			  lkid, le32_to_cpu(rc->rc_header.h_nodeid), remid,
			  result);
	}

	/* an ack for dlm_recover_locks() which waits for replies from
	   all the locks it sends to new masters */
	dlm_recovered_lock(r);
 out:
	unlock_rsb(r);
	put_rsb(r);
	dlm_put_lkb(lkb);

	return 0;
}

int dlm_user_request(struct dlm_ls *ls, struct dlm_user_args *ua,
		     int mode, uint32_t flags, void *name, unsigned int namelen)
{
	struct dlm_lkb *lkb;
	struct dlm_args args;
	bool do_put = true;
	int error;

	dlm_lock_recovery(ls);

	error = create_lkb(ls, &lkb);
	if (error) {
		kfree(ua);
		goto out;
	}

	trace_dlm_lock_start(ls, lkb, name, namelen, mode, flags);

	if (flags & DLM_LKF_VALBLK) {
		ua->lksb.sb_lvbptr = kzalloc(DLM_USER_LVB_LEN, GFP_NOFS);
		if (!ua->lksb.sb_lvbptr) {
			kfree(ua);
			error = -ENOMEM;
			goto out_put;
		}
	}
	error = set_lock_args(mode, &ua->lksb, flags, namelen, fake_astfn, ua,
			      fake_bastfn, &args);
	if (error) {
		kfree(ua->lksb.sb_lvbptr);
		ua->lksb.sb_lvbptr = NULL;
		kfree(ua);
		goto out_put;
	}

	/* After ua is attached to lkb it will be freed by dlm_free_lkb().
	   When DLM_DFL_USER_BIT is set, the dlm knows that this is a userspace
	   lock and that lkb_astparam is the dlm_user_args structure. */
	set_bit(DLM_DFL_USER_BIT, &lkb->lkb_dflags);
	error = request_lock(ls, lkb, name, namelen, &args);

	switch (error) {
	case 0:
		break;
	case -EINPROGRESS:
		error = 0;
		break;
	case -EAGAIN:
		error = 0;
		fallthrough;
	default:
		goto out_put;
	}

	/* add this new lkb to the per-process list of locks */
	spin_lock_bh(&ua->proc->locks_spin);
	hold_lkb(lkb);
	list_add_tail(&lkb->lkb_ownqueue, &ua->proc->locks);
	spin_unlock_bh(&ua->proc->locks_spin);
	do_put = false;
 out_put:
	trace_dlm_lock_end(ls, lkb, name, namelen, mode, flags, error, false);
	if (do_put)
		__put_lkb(ls, lkb);
 out:
	dlm_unlock_recovery(ls);
	return error;
}

int dlm_user_convert(struct dlm_ls *ls, struct dlm_user_args *ua_tmp,
		     int mode, uint32_t flags, uint32_t lkid, char *lvb_in)
{
	struct dlm_lkb *lkb;
	struct dlm_args args;
	struct dlm_user_args *ua;
	int error;

	dlm_lock_recovery(ls);

	error = find_lkb(ls, lkid, &lkb);
	if (error)
		goto out;

	trace_dlm_lock_start(ls, lkb, NULL, 0, mode, flags);

	/* user can change the params on its lock when it converts it, or
	   add an lvb that didn't exist before */

	ua = lkb->lkb_ua;

	if (flags & DLM_LKF_VALBLK && !ua->lksb.sb_lvbptr) {
		ua->lksb.sb_lvbptr = kzalloc(DLM_USER_LVB_LEN, GFP_NOFS);
		if (!ua->lksb.sb_lvbptr) {
			error = -ENOMEM;
			goto out_put;
		}
	}
	if (lvb_in && ua->lksb.sb_lvbptr)
		memcpy(ua->lksb.sb_lvbptr, lvb_in, DLM_USER_LVB_LEN);

	ua->xid = ua_tmp->xid;
	ua->castparam = ua_tmp->castparam;
	ua->castaddr = ua_tmp->castaddr;
	ua->bastparam = ua_tmp->bastparam;
	ua->bastaddr = ua_tmp->bastaddr;
	ua->user_lksb = ua_tmp->user_lksb;

	error = set_lock_args(mode, &ua->lksb, flags, 0, fake_astfn, ua,
			      fake_bastfn, &args);
	if (error)
		goto out_put;

	error = convert_lock(ls, lkb, &args);

	if (error == -EINPROGRESS || error == -EAGAIN || error == -EDEADLK)
		error = 0;
 out_put:
	trace_dlm_lock_end(ls, lkb, NULL, 0, mode, flags, error, false);
	dlm_put_lkb(lkb);
 out:
	dlm_unlock_recovery(ls);
	kfree(ua_tmp);
	return error;
}

/*
 * The caller asks for an orphan lock on a given resource with a given mode.
 * If a matching lock exists, it's moved to the owner's list of locks and
 * the lkid is returned.
 */

int dlm_user_adopt_orphan(struct dlm_ls *ls, struct dlm_user_args *ua_tmp,
		     int mode, uint32_t flags, void *name, unsigned int namelen,
		     uint32_t *lkid)
{
	struct dlm_lkb *lkb = NULL, *iter;
	struct dlm_user_args *ua;
	int found_other_mode = 0;
	int rv = 0;

	spin_lock_bh(&ls->ls_orphans_lock);
	list_for_each_entry(iter, &ls->ls_orphans, lkb_ownqueue) {
		if (iter->lkb_resource->res_length != namelen)
			continue;
		if (memcmp(iter->lkb_resource->res_name, name, namelen))
			continue;
		if (iter->lkb_grmode != mode) {
			found_other_mode = 1;
			continue;
		}

		lkb = iter;
		list_del_init(&iter->lkb_ownqueue);
		clear_bit(DLM_DFL_ORPHAN_BIT, &iter->lkb_dflags);
		*lkid = iter->lkb_id;
		break;
	}
	spin_unlock_bh(&ls->ls_orphans_lock);

	if (!lkb && found_other_mode) {
		rv = -EAGAIN;
		goto out;
	}

	if (!lkb) {
		rv = -ENOENT;
		goto out;
	}

	lkb->lkb_exflags = flags;
	lkb->lkb_ownpid = (int) current->pid;

	ua = lkb->lkb_ua;

	ua->proc = ua_tmp->proc;
	ua->xid = ua_tmp->xid;
	ua->castparam = ua_tmp->castparam;
	ua->castaddr = ua_tmp->castaddr;
	ua->bastparam = ua_tmp->bastparam;
	ua->bastaddr = ua_tmp->bastaddr;
	ua->user_lksb = ua_tmp->user_lksb;

	/*
	 * The lkb reference from the ls_orphans list was not
	 * removed above, and is now considered the reference
	 * for the proc locks list.
	 */

	spin_lock_bh(&ua->proc->locks_spin);
	list_add_tail(&lkb->lkb_ownqueue, &ua->proc->locks);
	spin_unlock_bh(&ua->proc->locks_spin);
 out:
	kfree(ua_tmp);
	return rv;
}

int dlm_user_unlock(struct dlm_ls *ls, struct dlm_user_args *ua_tmp,
		    uint32_t flags, uint32_t lkid, char *lvb_in)
{
	struct dlm_lkb *lkb;
	struct dlm_args args;
	struct dlm_user_args *ua;
	int error;

	dlm_lock_recovery(ls);

	error = find_lkb(ls, lkid, &lkb);
	if (error)
		goto out;

	trace_dlm_unlock_start(ls, lkb, flags);

	ua = lkb->lkb_ua;

	if (lvb_in && ua->lksb.sb_lvbptr)
		memcpy(ua->lksb.sb_lvbptr, lvb_in, DLM_USER_LVB_LEN);
	if (ua_tmp->castparam)
		ua->castparam = ua_tmp->castparam;
	ua->user_lksb = ua_tmp->user_lksb;

	error = set_unlock_args(flags, ua, &args);
	if (error)
		goto out_put;

	error = unlock_lock(ls, lkb, &args);

	if (error == -DLM_EUNLOCK)
		error = 0;
	/* from validate_unlock_args() */
	if (error == -EBUSY && (flags & DLM_LKF_FORCEUNLOCK))
		error = 0;
	if (error)
		goto out_put;

	spin_lock_bh(&ua->proc->locks_spin);
	/* dlm_user_add_cb() may have already taken lkb off the proc list */
	if (!list_empty(&lkb->lkb_ownqueue))
		list_move(&lkb->lkb_ownqueue, &ua->proc->unlocking);
	spin_unlock_bh(&ua->proc->locks_spin);
 out_put:
	trace_dlm_unlock_end(ls, lkb, flags, error);
	dlm_put_lkb(lkb);
 out:
	dlm_unlock_recovery(ls);
	kfree(ua_tmp);
	return error;
}

int dlm_user_cancel(struct dlm_ls *ls, struct dlm_user_args *ua_tmp,
		    uint32_t flags, uint32_t lkid)
{
	struct dlm_lkb *lkb;
	struct dlm_args args;
	struct dlm_user_args *ua;
	int error;

	dlm_lock_recovery(ls);

	error = find_lkb(ls, lkid, &lkb);
	if (error)
		goto out;

	trace_dlm_unlock_start(ls, lkb, flags);

	ua = lkb->lkb_ua;
	if (ua_tmp->castparam)
		ua->castparam = ua_tmp->castparam;
	ua->user_lksb = ua_tmp->user_lksb;

	error = set_unlock_args(flags, ua, &args);
	if (error)
		goto out_put;

	error = cancel_lock(ls, lkb, &args);

	if (error == -DLM_ECANCEL)
		error = 0;
	/* from validate_unlock_args() */
	if (error == -EBUSY)
		error = 0;
 out_put:
	trace_dlm_unlock_end(ls, lkb, flags, error);
	dlm_put_lkb(lkb);
 out:
	dlm_unlock_recovery(ls);
	kfree(ua_tmp);
	return error;
}

int dlm_user_deadlock(struct dlm_ls *ls, uint32_t flags, uint32_t lkid)
{
	struct dlm_lkb *lkb;
	struct dlm_args args;
	struct dlm_user_args *ua;
	struct dlm_rsb *r;
	int error;

	dlm_lock_recovery(ls);

	error = find_lkb(ls, lkid, &lkb);
	if (error)
		goto out;

	trace_dlm_unlock_start(ls, lkb, flags);

	ua = lkb->lkb_ua;

	error = set_unlock_args(flags, ua, &args);
	if (error)
		goto out_put;

	/* same as cancel_lock(), but set DEADLOCK_CANCEL after lock_rsb */

	r = lkb->lkb_resource;
	hold_rsb(r);
	lock_rsb(r);

	error = validate_unlock_args(lkb, &args);
	if (error)
		goto out_r;
	set_bit(DLM_IFL_DEADLOCK_CANCEL_BIT, &lkb->lkb_iflags);

	error = _cancel_lock(r, lkb);
 out_r:
	unlock_rsb(r);
	put_rsb(r);

	if (error == -DLM_ECANCEL)
		error = 0;
	/* from validate_unlock_args() */
	if (error == -EBUSY)
		error = 0;
 out_put:
	trace_dlm_unlock_end(ls, lkb, flags, error);
	dlm_put_lkb(lkb);
 out:
	dlm_unlock_recovery(ls);
	return error;
}

/* lkb's that are removed from the waiters list by revert are just left on the
   orphans list with the granted orphan locks, to be freed by purge */

static int orphan_proc_lock(struct dlm_ls *ls, struct dlm_lkb *lkb)
{
	struct dlm_args args;
	int error;

	hold_lkb(lkb); /* reference for the ls_orphans list */
	spin_lock_bh(&ls->ls_orphans_lock);
	list_add_tail(&lkb->lkb_ownqueue, &ls->ls_orphans);
	spin_unlock_bh(&ls->ls_orphans_lock);

	set_unlock_args(0, lkb->lkb_ua, &args);

	error = cancel_lock(ls, lkb, &args);
	if (error == -DLM_ECANCEL)
		error = 0;
	return error;
}

/* The FORCEUNLOCK flag allows the unlock to go ahead even if the lkb isn't
   granted.  Regardless of what rsb queue the lock is on, it's removed and
   freed.  The IVVALBLK flag causes the lvb on the resource to be invalidated
   if our lock is PW/EX (it's ignored if our granted mode is smaller.) */

static int unlock_proc_lock(struct dlm_ls *ls, struct dlm_lkb *lkb)
{
	struct dlm_args args;
	int error;

	set_unlock_args(DLM_LKF_FORCEUNLOCK | DLM_LKF_IVVALBLK,
			lkb->lkb_ua, &args);

	error = unlock_lock(ls, lkb, &args);
	if (error == -DLM_EUNLOCK)
		error = 0;
	return error;
}

/* We have to release clear_proc_locks mutex before calling unlock_proc_lock()
   (which does lock_rsb) due to deadlock with receiving a message that does
   lock_rsb followed by dlm_user_add_cb() */

static struct dlm_lkb *del_proc_lock(struct dlm_ls *ls,
				     struct dlm_user_proc *proc)
{
	struct dlm_lkb *lkb = NULL;

	spin_lock_bh(&ls->ls_clear_proc_locks);
	if (list_empty(&proc->locks))
		goto out;

	lkb = list_entry(proc->locks.next, struct dlm_lkb, lkb_ownqueue);
	list_del_init(&lkb->lkb_ownqueue);

	if (lkb->lkb_exflags & DLM_LKF_PERSISTENT)
		set_bit(DLM_DFL_ORPHAN_BIT, &lkb->lkb_dflags);
	else
		set_bit(DLM_IFL_DEAD_BIT, &lkb->lkb_iflags);
 out:
	spin_unlock_bh(&ls->ls_clear_proc_locks);
	return lkb;
}

/* The ls_clear_proc_locks mutex protects against dlm_user_add_cb() which
   1) references lkb->ua which we free here and 2) adds lkbs to proc->asts,
   which we clear here. */

/* proc CLOSING flag is set so no more device_reads should look at proc->asts
   list, and no more device_writes should add lkb's to proc->locks list; so we
   shouldn't need to take asts_spin or locks_spin here.  this assumes that
   device reads/writes/closes are serialized -- FIXME: we may need to serialize
   them ourself. */

void dlm_clear_proc_locks(struct dlm_ls *ls, struct dlm_user_proc *proc)
{
	struct dlm_callback *cb, *cb_safe;
	struct dlm_lkb *lkb, *safe;

	dlm_lock_recovery(ls);

	while (1) {
		lkb = del_proc_lock(ls, proc);
		if (!lkb)
			break;
		if (lkb->lkb_exflags & DLM_LKF_PERSISTENT)
			orphan_proc_lock(ls, lkb);
		else
			unlock_proc_lock(ls, lkb);

		/* this removes the reference for the proc->locks list
		   added by dlm_user_request, it may result in the lkb
		   being freed */

		dlm_put_lkb(lkb);
	}

	spin_lock_bh(&ls->ls_clear_proc_locks);

	/* in-progress unlocks */
	list_for_each_entry_safe(lkb, safe, &proc->unlocking, lkb_ownqueue) {
		list_del_init(&lkb->lkb_ownqueue);
		set_bit(DLM_IFL_DEAD_BIT, &lkb->lkb_iflags);
		dlm_put_lkb(lkb);
	}

	list_for_each_entry_safe(cb, cb_safe, &proc->asts, list) {
		list_del(&cb->list);
		dlm_free_cb(cb);
	}

	spin_unlock_bh(&ls->ls_clear_proc_locks);
	dlm_unlock_recovery(ls);
}

static void purge_proc_locks(struct dlm_ls *ls, struct dlm_user_proc *proc)
{
	struct dlm_callback *cb, *cb_safe;
	struct dlm_lkb *lkb, *safe;

	while (1) {
		lkb = NULL;
		spin_lock_bh(&proc->locks_spin);
		if (!list_empty(&proc->locks)) {
			lkb = list_entry(proc->locks.next, struct dlm_lkb,
					 lkb_ownqueue);
			list_del_init(&lkb->lkb_ownqueue);
		}
		spin_unlock_bh(&proc->locks_spin);

		if (!lkb)
			break;

		set_bit(DLM_IFL_DEAD_BIT, &lkb->lkb_iflags);
		unlock_proc_lock(ls, lkb);
		dlm_put_lkb(lkb); /* ref from proc->locks list */
	}

	spin_lock_bh(&proc->locks_spin);
	list_for_each_entry_safe(lkb, safe, &proc->unlocking, lkb_ownqueue) {
		list_del_init(&lkb->lkb_ownqueue);
		set_bit(DLM_IFL_DEAD_BIT, &lkb->lkb_iflags);
		dlm_put_lkb(lkb);
	}
	spin_unlock_bh(&proc->locks_spin);

	spin_lock_bh(&proc->asts_spin);
	list_for_each_entry_safe(cb, cb_safe, &proc->asts, list) {
		list_del(&cb->list);
		dlm_free_cb(cb);
	}
	spin_unlock_bh(&proc->asts_spin);
}

/* pid of 0 means purge all orphans */

static void do_purge(struct dlm_ls *ls, int nodeid, int pid)
{
	struct dlm_lkb *lkb, *safe;

	spin_lock_bh(&ls->ls_orphans_lock);
	list_for_each_entry_safe(lkb, safe, &ls->ls_orphans, lkb_ownqueue) {
		if (pid && lkb->lkb_ownpid != pid)
			continue;
		unlock_proc_lock(ls, lkb);
		list_del_init(&lkb->lkb_ownqueue);
		dlm_put_lkb(lkb);
	}
	spin_unlock_bh(&ls->ls_orphans_lock);
}

static int send_purge(struct dlm_ls *ls, int nodeid, int pid)
{
	struct dlm_message *ms;
	struct dlm_mhandle *mh;
	int error;

	error = _create_message(ls, sizeof(struct dlm_message), nodeid,
				DLM_MSG_PURGE, &ms, &mh);
	if (error)
		return error;
	ms->m_nodeid = cpu_to_le32(nodeid);
	ms->m_pid = cpu_to_le32(pid);

	return send_message(mh, ms, NULL, 0);
}

int dlm_user_purge(struct dlm_ls *ls, struct dlm_user_proc *proc,
		   int nodeid, int pid)
{
	int error = 0;

	if (nodeid && (nodeid != dlm_our_nodeid())) {
		error = send_purge(ls, nodeid, pid);
	} else {
		dlm_lock_recovery(ls);
		if (pid == current->pid)
			purge_proc_locks(ls, proc);
		else
			do_purge(ls, nodeid, pid);
		dlm_unlock_recovery(ls);
	}
	return error;
}

/* debug functionality */
int dlm_debug_add_lkb(struct dlm_ls *ls, uint32_t lkb_id, char *name, int len,
		      int lkb_nodeid, unsigned int lkb_dflags, int lkb_status)
{
	struct dlm_lksb *lksb;
	struct dlm_lkb *lkb;
	struct dlm_rsb *r;
	int error;

	/* we currently can't set a valid user lock */
	if (lkb_dflags & BIT(DLM_DFL_USER_BIT))
		return -EOPNOTSUPP;

	lksb = kzalloc(sizeof(*lksb), GFP_NOFS);
	if (!lksb)
		return -ENOMEM;

	error = _create_lkb(ls, &lkb, lkb_id, lkb_id + 1);
	if (error) {
		kfree(lksb);
		return error;
	}

	dlm_set_dflags_val(lkb, lkb_dflags);
	lkb->lkb_nodeid = lkb_nodeid;
	lkb->lkb_lksb = lksb;
	/* user specific pointer, just don't have it NULL for kernel locks */
	if (~lkb_dflags & BIT(DLM_DFL_USER_BIT))
		lkb->lkb_astparam = (void *)0xDEADBEEF;

	error = find_rsb(ls, name, len, 0, R_REQUEST, &r);
	if (error) {
		kfree(lksb);
		__put_lkb(ls, lkb);
		return error;
	}

	lock_rsb(r);
	attach_lkb(r, lkb);
	add_lkb(r, lkb, lkb_status);
	unlock_rsb(r);
	put_rsb(r);

	return 0;
}

int dlm_debug_add_lkb_to_waiters(struct dlm_ls *ls, uint32_t lkb_id,
				 int mstype, int to_nodeid)
{
	struct dlm_lkb *lkb;
	int error;

	error = find_lkb(ls, lkb_id, &lkb);
	if (error)
		return error;

	add_to_waiters(lkb, mstype, to_nodeid);
	dlm_put_lkb(lkb);
	return 0;
}

