/*
 * GPL HEADER START
 *
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 only,
 * as published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * General Public License version 2 for more details (a copy is included
 * in the LICENSE file that accompanied this code).
 *
 * You should have received a copy of the GNU General Public License
 * version 2 along with this program; if not, write to the
 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
 * Boston, MA 021110-1307, USA
 *
 * GPL HEADER END
 */
/*
 * Copyright (c) 2012, Intel Corporation.
 */
/*
 * This file is part of Lustre, http://www.lustre.org/
 * Lustre is a trademark of Sun Microsystems, Inc.
 *
 * lnet/lnet/lib-ptl.c
 *
 * portal & match routines
 *
 * Author: liang@whamcloud.com
 */

#define DEBUG_SUBSYSTEM S_LNET

#include "../../include/linux/lnet/lib-lnet.h"

/* NB: add /proc interfaces in upcoming patches */
int portal_rotor = LNET_PTL_ROTOR_HASH_RT;
module_param(portal_rotor, int, 0644);
MODULE_PARM_DESC(portal_rotor, "redirect PUTs to different cpu-partitions");

static int
lnet_ptl_match_type(unsigned int index, lnet_process_id_t match_id,
		    __u64 mbits, __u64 ignore_bits)
{
	struct lnet_portal *ptl = the_lnet.ln_portals[index];
	int unique;

	unique = ignore_bits == 0 &&
		 match_id.nid != LNET_NID_ANY &&
		 match_id.pid != LNET_PID_ANY;

	LASSERT(!lnet_ptl_is_unique(ptl) || !lnet_ptl_is_wildcard(ptl));

	/* prefer to check w/o any lock */
	if (likely(lnet_ptl_is_unique(ptl) || lnet_ptl_is_wildcard(ptl)))
		goto match;

	/* unset, new portal */
	lnet_ptl_lock(ptl);
	/* check again with lock */
	if (unlikely(lnet_ptl_is_unique(ptl) || lnet_ptl_is_wildcard(ptl))) {
		lnet_ptl_unlock(ptl);
		goto match;
	}

	/* still not set */
	if (unique)
		lnet_ptl_setopt(ptl, LNET_PTL_MATCH_UNIQUE);
	else
		lnet_ptl_setopt(ptl, LNET_PTL_MATCH_WILDCARD);

	lnet_ptl_unlock(ptl);

	return 1;

 match:
	if ((lnet_ptl_is_unique(ptl) && !unique) ||
	    (lnet_ptl_is_wildcard(ptl) && unique))
		return 0;
	return 1;
}

static void
lnet_ptl_enable_mt(struct lnet_portal *ptl, int cpt)
{
	struct lnet_match_table	*mtable = ptl->ptl_mtables[cpt];
	int i;

	/* with hold of both lnet_res_lock(cpt) and lnet_ptl_lock */
	LASSERT(lnet_ptl_is_wildcard(ptl));

	mtable->mt_enabled = 1;

	ptl->ptl_mt_maps[ptl->ptl_mt_nmaps] = cpt;
	for (i = ptl->ptl_mt_nmaps - 1; i >= 0; i--) {
		LASSERT(ptl->ptl_mt_maps[i] != cpt);
		if (ptl->ptl_mt_maps[i] < cpt)
			break;

		/* swap to order */
		ptl->ptl_mt_maps[i + 1] = ptl->ptl_mt_maps[i];
		ptl->ptl_mt_maps[i] = cpt;
	}

	ptl->ptl_mt_nmaps++;
}

static void
lnet_ptl_disable_mt(struct lnet_portal *ptl, int cpt)
{
	struct lnet_match_table	*mtable = ptl->ptl_mtables[cpt];
	int i;

	/* with hold of both lnet_res_lock(cpt) and lnet_ptl_lock */
	LASSERT(lnet_ptl_is_wildcard(ptl));

	if (LNET_CPT_NUMBER == 1)
		return; /* never disable the only match-table */

	mtable->mt_enabled = 0;

	LASSERT(ptl->ptl_mt_nmaps > 0 &&
		ptl->ptl_mt_nmaps <= LNET_CPT_NUMBER);

	/* remove it from mt_maps */
	ptl->ptl_mt_nmaps--;
	for (i = 0; i < ptl->ptl_mt_nmaps; i++) {
		if (ptl->ptl_mt_maps[i] >= cpt) /* overwrite it */
			ptl->ptl_mt_maps[i] = ptl->ptl_mt_maps[i + 1];
	}
}

static int
lnet_try_match_md(lnet_libmd_t *md,
		  struct lnet_match_info *info, struct lnet_msg *msg)
{
	/* ALWAYS called holding the lnet_res_lock, and can't lnet_res_unlock;
	 * lnet_match_blocked_msg() relies on this to avoid races */
	unsigned int offset;
	unsigned int mlength;
	lnet_me_t *me = md->md_me;

	/* MD exhausted */
	if (lnet_md_exhausted(md))
		return LNET_MATCHMD_NONE | LNET_MATCHMD_EXHAUSTED;

	/* mismatched MD op */
	if ((md->md_options & info->mi_opc) == 0)
		return LNET_MATCHMD_NONE;

	/* mismatched ME nid/pid? */
	if (me->me_match_id.nid != LNET_NID_ANY &&
	    me->me_match_id.nid != info->mi_id.nid)
		return LNET_MATCHMD_NONE;

	if (me->me_match_id.pid != LNET_PID_ANY &&
	    me->me_match_id.pid != info->mi_id.pid)
		return LNET_MATCHMD_NONE;

	/* mismatched ME matchbits? */
	if (((me->me_match_bits ^ info->mi_mbits) & ~me->me_ignore_bits) != 0)
		return LNET_MATCHMD_NONE;

	/* Hurrah! This _is_ a match; check it out... */

	if ((md->md_options & LNET_MD_MANAGE_REMOTE) == 0)
		offset = md->md_offset;
	else
		offset = info->mi_roffset;

	if ((md->md_options & LNET_MD_MAX_SIZE) != 0) {
		mlength = md->md_max_size;
		LASSERT(md->md_offset + mlength <= md->md_length);
	} else {
		mlength = md->md_length - offset;
	}

	if (info->mi_rlength <= mlength) {	/* fits in allowed space */
		mlength = info->mi_rlength;
	} else if ((md->md_options & LNET_MD_TRUNCATE) == 0) {
		/* this packet _really_ is too big */
		CERROR("Matching packet from %s, match %llu length %d too big: %d left, %d allowed\n",
		       libcfs_id2str(info->mi_id), info->mi_mbits,
		       info->mi_rlength, md->md_length - offset, mlength);

		return LNET_MATCHMD_DROP;
	}

	/* Commit to this ME/MD */
	CDEBUG(D_NET, "Incoming %s index %x from %s of length %d/%d into md %#llx [%d] + %d\n",
	       (info->mi_opc == LNET_MD_OP_PUT) ? "put" : "get",
	       info->mi_portal, libcfs_id2str(info->mi_id), mlength,
	       info->mi_rlength, md->md_lh.lh_cookie, md->md_niov, offset);

	lnet_msg_attach_md(msg, md, offset, mlength);
	md->md_offset = offset + mlength;

	if (!lnet_md_exhausted(md))
		return LNET_MATCHMD_OK;

	/* Auto-unlink NOW, so the ME gets unlinked if required.
	 * We bumped md->md_refcount above so the MD just gets flagged
	 * for unlink when it is finalized. */
	if ((md->md_flags & LNET_MD_FLAG_AUTO_UNLINK) != 0)
		lnet_md_unlink(md);

	return LNET_MATCHMD_OK | LNET_MATCHMD_EXHAUSTED;
}

static struct lnet_match_table *
lnet_match2mt(struct lnet_portal *ptl, lnet_process_id_t id, __u64 mbits)
{
	if (LNET_CPT_NUMBER == 1)
		return ptl->ptl_mtables[0]; /* the only one */

	/* if it's a unique portal, return match-table hashed by NID */
	return lnet_ptl_is_unique(ptl) ?
	       ptl->ptl_mtables[lnet_cpt_of_nid(id.nid)] : NULL;
}

struct lnet_match_table *
lnet_mt_of_attach(unsigned int index, lnet_process_id_t id,
		  __u64 mbits, __u64 ignore_bits, lnet_ins_pos_t pos)
{
	struct lnet_portal *ptl;
	struct lnet_match_table	*mtable;

	/* NB: called w/o lock */
	LASSERT(index < the_lnet.ln_nportals);

	if (!lnet_ptl_match_type(index, id, mbits, ignore_bits))
		return NULL;

	ptl = the_lnet.ln_portals[index];

	mtable = lnet_match2mt(ptl, id, mbits);
	if (mtable != NULL) /* unique portal or only one match-table */
		return mtable;

	/* it's a wildcard portal */
	switch (pos) {
	default:
		return NULL;
	case LNET_INS_BEFORE:
	case LNET_INS_AFTER:
		/* posted by no affinity thread, always hash to specific
		 * match-table to avoid buffer stealing which is heavy */
		return ptl->ptl_mtables[ptl->ptl_index % LNET_CPT_NUMBER];
	case LNET_INS_LOCAL:
		/* posted by cpu-affinity thread */
		return ptl->ptl_mtables[lnet_cpt_current()];
	}
}

static struct lnet_match_table *
lnet_mt_of_match(struct lnet_match_info *info, struct lnet_msg *msg)
{
	struct lnet_match_table	*mtable;
	struct lnet_portal *ptl;
	unsigned int nmaps;
	unsigned int rotor;
	unsigned int cpt;
	bool routed;

	/* NB: called w/o lock */
	LASSERT(info->mi_portal < the_lnet.ln_nportals);
	ptl = the_lnet.ln_portals[info->mi_portal];

	LASSERT(lnet_ptl_is_wildcard(ptl) || lnet_ptl_is_unique(ptl));

	mtable = lnet_match2mt(ptl, info->mi_id, info->mi_mbits);
	if (mtable != NULL)
		return mtable;

	/* it's a wildcard portal */
	routed = LNET_NIDNET(msg->msg_hdr.src_nid) !=
		 LNET_NIDNET(msg->msg_hdr.dest_nid);

	if (portal_rotor == LNET_PTL_ROTOR_OFF ||
	    (portal_rotor != LNET_PTL_ROTOR_ON && !routed)) {
		cpt = lnet_cpt_current();
		if (ptl->ptl_mtables[cpt]->mt_enabled)
			return ptl->ptl_mtables[cpt];
	}

	rotor = ptl->ptl_rotor++; /* get round-robin factor */
	if (portal_rotor == LNET_PTL_ROTOR_HASH_RT && routed)
		cpt = lnet_cpt_of_nid(msg->msg_hdr.src_nid);
	else
		cpt = rotor % LNET_CPT_NUMBER;

	if (!ptl->ptl_mtables[cpt]->mt_enabled) {
		/* is there any active entry for this portal? */
		nmaps = ptl->ptl_mt_nmaps;
		/* map to an active mtable to avoid heavy "stealing" */
		if (nmaps != 0) {
			/* NB: there is possibility that ptl_mt_maps is being
			 * changed because we are not under protection of
			 * lnet_ptl_lock, but it shouldn't hurt anything */
			cpt = ptl->ptl_mt_maps[rotor % nmaps];
		}
	}

	return ptl->ptl_mtables[cpt];
}

static int
lnet_mt_test_exhausted(struct lnet_match_table *mtable, int pos)
{
	__u64 *bmap;
	int i;

	if (!lnet_ptl_is_wildcard(the_lnet.ln_portals[mtable->mt_portal]))
		return 0;

	if (pos < 0) { /* check all bits */
		for (i = 0; i < LNET_MT_EXHAUSTED_BMAP; i++) {
			if (mtable->mt_exhausted[i] != (__u64)(-1))
				return 0;
		}
		return 1;
	}

	LASSERT(pos <= LNET_MT_HASH_IGNORE);
	/* mtable::mt_mhash[pos] is marked as exhausted or not */
	bmap = &mtable->mt_exhausted[pos >> LNET_MT_BITS_U64];
	pos &= (1 << LNET_MT_BITS_U64) - 1;

	return ((*bmap) & (1ULL << pos)) != 0;
}

static void
lnet_mt_set_exhausted(struct lnet_match_table *mtable, int pos, int exhausted)
{
	__u64 *bmap;

	LASSERT(lnet_ptl_is_wildcard(the_lnet.ln_portals[mtable->mt_portal]));
	LASSERT(pos <= LNET_MT_HASH_IGNORE);

	/* set mtable::mt_mhash[pos] as exhausted/non-exhausted */
	bmap = &mtable->mt_exhausted[pos >> LNET_MT_BITS_U64];
	pos &= (1 << LNET_MT_BITS_U64) - 1;

	if (!exhausted)
		*bmap &= ~(1ULL << pos);
	else
		*bmap |= 1ULL << pos;
}

struct list_head *
lnet_mt_match_head(struct lnet_match_table *mtable,
		   lnet_process_id_t id, __u64 mbits)
{
	struct lnet_portal *ptl = the_lnet.ln_portals[mtable->mt_portal];

	if (lnet_ptl_is_wildcard(ptl)) {
		return &mtable->mt_mhash[mbits & LNET_MT_HASH_MASK];
	} else {
		unsigned long hash = mbits + id.nid + id.pid;

		LASSERT(lnet_ptl_is_unique(ptl));
		hash = hash_long(hash, LNET_MT_HASH_BITS);
		return &mtable->mt_mhash[hash];
	}
}

int
lnet_mt_match_md(struct lnet_match_table *mtable,
		 struct lnet_match_info *info, struct lnet_msg *msg)
{
	struct list_head *head;
	lnet_me_t *me;
	lnet_me_t *tmp;
	int exhausted = 0;
	int rc;

	/* any ME with ignore bits? */
	if (!list_empty(&mtable->mt_mhash[LNET_MT_HASH_IGNORE]))
		head = &mtable->mt_mhash[LNET_MT_HASH_IGNORE];
	else
		head = lnet_mt_match_head(mtable, info->mi_id, info->mi_mbits);
 again:
	/* NB: only wildcard portal needs to return LNET_MATCHMD_EXHAUSTED */
	if (lnet_ptl_is_wildcard(the_lnet.ln_portals[mtable->mt_portal]))
		exhausted = LNET_MATCHMD_EXHAUSTED;

	list_for_each_entry_safe(me, tmp, head, me_list) {
		/* ME attached but MD not attached yet */
		if (me->me_md == NULL)
			continue;

		LASSERT(me == me->me_md->md_me);

		rc = lnet_try_match_md(me->me_md, info, msg);
		if ((rc & LNET_MATCHMD_EXHAUSTED) == 0)
			exhausted = 0; /* mlist is not empty */

		if ((rc & LNET_MATCHMD_FINISH) != 0) {
			/* don't return EXHAUSTED bit because we don't know
			 * whether the mlist is empty or not */
			return rc & ~LNET_MATCHMD_EXHAUSTED;
		}
	}

	if (exhausted == LNET_MATCHMD_EXHAUSTED) { /* @head is exhausted */
		lnet_mt_set_exhausted(mtable, head - mtable->mt_mhash, 1);
		if (!lnet_mt_test_exhausted(mtable, -1))
			exhausted = 0;
	}

	if (exhausted == 0 && head == &mtable->mt_mhash[LNET_MT_HASH_IGNORE]) {
		head = lnet_mt_match_head(mtable, info->mi_id, info->mi_mbits);
		goto again; /* re-check MEs w/o ignore-bits */
	}

	if (info->mi_opc == LNET_MD_OP_GET ||
	    !lnet_ptl_is_lazy(the_lnet.ln_portals[info->mi_portal]))
		return exhausted | LNET_MATCHMD_DROP;

	return exhausted | LNET_MATCHMD_NONE;
}

static int
lnet_ptl_match_early(struct lnet_portal *ptl, struct lnet_msg *msg)
{
	int rc;

	/* message arrived before any buffer posting on this portal,
	 * simply delay or drop this message */
	if (likely(lnet_ptl_is_wildcard(ptl) || lnet_ptl_is_unique(ptl)))
		return 0;

	lnet_ptl_lock(ptl);
	/* check it again with hold of lock */
	if (lnet_ptl_is_wildcard(ptl) || lnet_ptl_is_unique(ptl)) {
		lnet_ptl_unlock(ptl);
		return 0;
	}

	if (lnet_ptl_is_lazy(ptl)) {
		if (msg->msg_rx_ready_delay) {
			msg->msg_rx_delayed = 1;
			list_add_tail(&msg->msg_list,
					  &ptl->ptl_msg_delayed);
		}
		rc = LNET_MATCHMD_NONE;
	} else {
		rc = LNET_MATCHMD_DROP;
	}

	lnet_ptl_unlock(ptl);
	return rc;
}

static int
lnet_ptl_match_delay(struct lnet_portal *ptl,
		     struct lnet_match_info *info, struct lnet_msg *msg)
{
	int first = ptl->ptl_mt_maps[0]; /* read w/o lock */
	int rc = 0;
	int i;

	/* steal buffer from other CPTs, and delay it if nothing to steal,
	 * this function is more expensive than a regular match, but we
	 * don't expect it can happen a lot */
	LASSERT(lnet_ptl_is_wildcard(ptl));

	for (i = 0; i < LNET_CPT_NUMBER; i++) {
		struct lnet_match_table *mtable;
		int cpt;

		cpt = (first + i) % LNET_CPT_NUMBER;
		mtable = ptl->ptl_mtables[cpt];
		if (i != 0 && i != LNET_CPT_NUMBER - 1 && !mtable->mt_enabled)
			continue;

		lnet_res_lock(cpt);
		lnet_ptl_lock(ptl);

		if (i == 0) { /* the first try, attach on stealing list */
			list_add_tail(&msg->msg_list,
					  &ptl->ptl_msg_stealing);
		}

		if (!list_empty(&msg->msg_list)) { /* on stealing list */
			rc = lnet_mt_match_md(mtable, info, msg);

			if ((rc & LNET_MATCHMD_EXHAUSTED) != 0 &&
			    mtable->mt_enabled)
				lnet_ptl_disable_mt(ptl, cpt);

			if ((rc & LNET_MATCHMD_FINISH) != 0)
				list_del_init(&msg->msg_list);

		} else {
			/* could be matched by lnet_ptl_attach_md()
			 * which is called by another thread */
			rc = msg->msg_md == NULL ?
			     LNET_MATCHMD_DROP : LNET_MATCHMD_OK;
		}

		if (!list_empty(&msg->msg_list) && /* not matched yet */
		    (i == LNET_CPT_NUMBER - 1 || /* the last CPT */
		     ptl->ptl_mt_nmaps == 0 ||   /* no active CPT */
		     (ptl->ptl_mt_nmaps == 1 &&  /* the only active CPT */
		      ptl->ptl_mt_maps[0] == cpt))) {
			/* nothing to steal, delay or drop */
			list_del_init(&msg->msg_list);

			if (lnet_ptl_is_lazy(ptl)) {
				msg->msg_rx_delayed = 1;
				list_add_tail(&msg->msg_list,
						  &ptl->ptl_msg_delayed);
				rc = LNET_MATCHMD_NONE;
			} else {
				rc = LNET_MATCHMD_DROP;
			}
		}

		lnet_ptl_unlock(ptl);
		lnet_res_unlock(cpt);

		if ((rc & LNET_MATCHMD_FINISH) != 0 || msg->msg_rx_delayed)
			break;
	}

	return rc;
}

int
lnet_ptl_match_md(struct lnet_match_info *info, struct lnet_msg *msg)
{
	struct lnet_match_table	*mtable;
	struct lnet_portal *ptl;
	int rc;

	CDEBUG(D_NET, "Request from %s of length %d into portal %d MB=%#llx\n",
	       libcfs_id2str(info->mi_id), info->mi_rlength, info->mi_portal,
	       info->mi_mbits);

	if (info->mi_portal >= the_lnet.ln_nportals) {
		CERROR("Invalid portal %d not in [0-%d]\n",
		       info->mi_portal, the_lnet.ln_nportals);
		return LNET_MATCHMD_DROP;
	}

	ptl = the_lnet.ln_portals[info->mi_portal];
	rc = lnet_ptl_match_early(ptl, msg);
	if (rc != 0) /* matched or delayed early message */
		return rc;

	mtable = lnet_mt_of_match(info, msg);
	lnet_res_lock(mtable->mt_cpt);

	if (the_lnet.ln_shutdown) {
		rc = LNET_MATCHMD_DROP;
		goto out1;
	}

	rc = lnet_mt_match_md(mtable, info, msg);
	if ((rc & LNET_MATCHMD_EXHAUSTED) != 0 && mtable->mt_enabled) {
		lnet_ptl_lock(ptl);
		lnet_ptl_disable_mt(ptl, mtable->mt_cpt);
		lnet_ptl_unlock(ptl);
	}

	if ((rc & LNET_MATCHMD_FINISH) != 0)	/* matched or dropping */
		goto out1;

	if (!msg->msg_rx_ready_delay)
		goto out1;

	LASSERT(lnet_ptl_is_lazy(ptl));
	LASSERT(!msg->msg_rx_delayed);

	/* NB: we don't expect "delay" can happen a lot */
	if (lnet_ptl_is_unique(ptl) || LNET_CPT_NUMBER == 1) {
		lnet_ptl_lock(ptl);

		msg->msg_rx_delayed = 1;
		list_add_tail(&msg->msg_list, &ptl->ptl_msg_delayed);

		lnet_ptl_unlock(ptl);
		lnet_res_unlock(mtable->mt_cpt);

	} else  {
		lnet_res_unlock(mtable->mt_cpt);
		rc = lnet_ptl_match_delay(ptl, info, msg);
	}

	if (msg->msg_rx_delayed) {
		CDEBUG(D_NET,
		       "Delaying %s from %s ptl %d MB %#llx off %d len %d\n",
		       info->mi_opc == LNET_MD_OP_PUT ? "PUT" : "GET",
		       libcfs_id2str(info->mi_id), info->mi_portal,
		       info->mi_mbits, info->mi_roffset, info->mi_rlength);
	}
	goto out0;
 out1:
	lnet_res_unlock(mtable->mt_cpt);
 out0:
	/* EXHAUSTED bit is only meaningful for internal functions */
	return rc & ~LNET_MATCHMD_EXHAUSTED;
}

void
lnet_ptl_detach_md(lnet_me_t *me, lnet_libmd_t *md)
{
	LASSERT(me->me_md == md && md->md_me == me);

	me->me_md = NULL;
	md->md_me = NULL;
}

/* called with lnet_res_lock held */
void
lnet_ptl_attach_md(lnet_me_t *me, lnet_libmd_t *md,
		   struct list_head *matches, struct list_head *drops)
{
	struct lnet_portal *ptl = the_lnet.ln_portals[me->me_portal];
	struct lnet_match_table	*mtable;
	struct list_head *head;
	lnet_msg_t *tmp;
	lnet_msg_t *msg;
	int exhausted = 0;
	int cpt;

	LASSERT(md->md_refcount == 0); /* a brand new MD */

	me->me_md = md;
	md->md_me = me;

	cpt = lnet_cpt_of_cookie(md->md_lh.lh_cookie);
	mtable = ptl->ptl_mtables[cpt];

	if (list_empty(&ptl->ptl_msg_stealing) &&
	    list_empty(&ptl->ptl_msg_delayed) &&
	    !lnet_mt_test_exhausted(mtable, me->me_pos))
		return;

	lnet_ptl_lock(ptl);
	head = &ptl->ptl_msg_stealing;
 again:
	list_for_each_entry_safe(msg, tmp, head, msg_list) {
		struct lnet_match_info info;
		lnet_hdr_t *hdr;
		int rc;

		LASSERT(msg->msg_rx_delayed || head == &ptl->ptl_msg_stealing);

		hdr = &msg->msg_hdr;
		info.mi_id.nid  = hdr->src_nid;
		info.mi_id.pid  = hdr->src_pid;
		info.mi_opc     = LNET_MD_OP_PUT;
		info.mi_portal  = hdr->msg.put.ptl_index;
		info.mi_rlength = hdr->payload_length;
		info.mi_roffset = hdr->msg.put.offset;
		info.mi_mbits   = hdr->msg.put.match_bits;

		rc = lnet_try_match_md(md, &info, msg);

		exhausted = (rc & LNET_MATCHMD_EXHAUSTED) != 0;
		if ((rc & LNET_MATCHMD_NONE) != 0) {
			if (exhausted)
				break;
			continue;
		}

		/* Hurrah! This _is_ a match */
		LASSERT((rc & LNET_MATCHMD_FINISH) != 0);
		list_del_init(&msg->msg_list);

		if (head == &ptl->ptl_msg_stealing) {
			if (exhausted)
				break;
			/* stealing thread will handle the message */
			continue;
		}

		if ((rc & LNET_MATCHMD_OK) != 0) {
			list_add_tail(&msg->msg_list, matches);

			CDEBUG(D_NET, "Resuming delayed PUT from %s portal %d match %llu offset %d length %d.\n",
			       libcfs_id2str(info.mi_id),
			       info.mi_portal, info.mi_mbits,
			       info.mi_roffset, info.mi_rlength);
		} else {
			list_add_tail(&msg->msg_list, drops);
		}

		if (exhausted)
			break;
	}

	if (!exhausted && head == &ptl->ptl_msg_stealing) {
		head = &ptl->ptl_msg_delayed;
		goto again;
	}

	if (lnet_ptl_is_wildcard(ptl) && !exhausted) {
		lnet_mt_set_exhausted(mtable, me->me_pos, 0);
		if (!mtable->mt_enabled)
			lnet_ptl_enable_mt(ptl, cpt);
	}

	lnet_ptl_unlock(ptl);
}

static void
lnet_ptl_cleanup(struct lnet_portal *ptl)
{
	struct lnet_match_table	*mtable;
	int i;

	if (ptl->ptl_mtables == NULL) /* uninitialized portal */
		return;

	LASSERT(list_empty(&ptl->ptl_msg_delayed));
	LASSERT(list_empty(&ptl->ptl_msg_stealing));
	cfs_percpt_for_each(mtable, i, ptl->ptl_mtables) {
		struct list_head *mhash;
		lnet_me_t *me;
		int j;

		if (mtable->mt_mhash == NULL) /* uninitialized match-table */
			continue;

		mhash = mtable->mt_mhash;
		/* cleanup ME */
		for (j = 0; j < LNET_MT_HASH_SIZE + 1; j++) {
			while (!list_empty(&mhash[j])) {
				me = list_entry(mhash[j].next,
						    lnet_me_t, me_list);
				CERROR("Active ME %p on exit\n", me);
				list_del(&me->me_list);
				lnet_me_free(me);
			}
		}
		/* the extra entry is for MEs with ignore bits */
		LIBCFS_FREE(mhash, sizeof(*mhash) * (LNET_MT_HASH_SIZE + 1));
	}

	cfs_percpt_free(ptl->ptl_mtables);
	ptl->ptl_mtables = NULL;
}

static int
lnet_ptl_setup(struct lnet_portal *ptl, int index)
{
	struct lnet_match_table	*mtable;
	struct list_head *mhash;
	int i;
	int j;

	ptl->ptl_mtables = cfs_percpt_alloc(lnet_cpt_table(),
					    sizeof(struct lnet_match_table));
	if (ptl->ptl_mtables == NULL) {
		CERROR("Failed to create match table for portal %d\n", index);
		return -ENOMEM;
	}

	ptl->ptl_index = index;
	INIT_LIST_HEAD(&ptl->ptl_msg_delayed);
	INIT_LIST_HEAD(&ptl->ptl_msg_stealing);
	spin_lock_init(&ptl->ptl_lock);
	cfs_percpt_for_each(mtable, i, ptl->ptl_mtables) {
		/* the extra entry is for MEs with ignore bits */
		LIBCFS_CPT_ALLOC(mhash, lnet_cpt_table(), i,
				 sizeof(*mhash) * (LNET_MT_HASH_SIZE + 1));
		if (mhash == NULL) {
			CERROR("Failed to create match hash for portal %d\n",
			       index);
			goto failed;
		}

		memset(&mtable->mt_exhausted[0], -1,
		       sizeof(mtable->mt_exhausted[0]) *
		       LNET_MT_EXHAUSTED_BMAP);
		mtable->mt_mhash = mhash;
		for (j = 0; j < LNET_MT_HASH_SIZE + 1; j++)
			INIT_LIST_HEAD(&mhash[j]);

		mtable->mt_portal = index;
		mtable->mt_cpt = i;
	}

	return 0;
 failed:
	lnet_ptl_cleanup(ptl);
	return -ENOMEM;
}

void
lnet_portals_destroy(void)
{
	int i;

	if (the_lnet.ln_portals == NULL)
		return;

	for (i = 0; i < the_lnet.ln_nportals; i++)
		lnet_ptl_cleanup(the_lnet.ln_portals[i]);

	cfs_array_free(the_lnet.ln_portals);
	the_lnet.ln_portals = NULL;
}

int
lnet_portals_create(void)
{
	int size;
	int i;

	size = offsetof(struct lnet_portal, ptl_mt_maps[LNET_CPT_NUMBER]);

	the_lnet.ln_nportals = MAX_PORTALS;
	the_lnet.ln_portals = cfs_array_alloc(the_lnet.ln_nportals, size);
	if (the_lnet.ln_portals == NULL) {
		CERROR("Failed to allocate portals table\n");
		return -ENOMEM;
	}

	for (i = 0; i < the_lnet.ln_nportals; i++) {
		if (lnet_ptl_setup(the_lnet.ln_portals[i], i)) {
			lnet_portals_destroy();
			return -ENOMEM;
		}
	}

	return 0;
}

/**
 * Turn on the lazy portal attribute. Use with caution!
 *
 * This portal attribute only affects incoming PUT requests to the portal,
 * and is off by default. By default, if there's no matching MD for an
 * incoming PUT request, it is simply dropped. With the lazy attribute on,
 * such requests are queued indefinitely until either a matching MD is
 * posted to the portal or the lazy attribute is turned off.
 *
 * It would prevent dropped requests, however it should be regarded as the
 * last line of defense - i.e. users must keep a close watch on active
 * buffers on a lazy portal and once it becomes too low post more buffers as
 * soon as possible. This is because delayed requests usually have detrimental
 * effects on underlying network connections. A few delayed requests often
 * suffice to bring an underlying connection to a complete halt, due to flow
 * control mechanisms.
 *
 * There's also a DOS attack risk. If users don't post match-all MDs on a
 * lazy portal, a malicious peer can easily stop a service by sending some
 * PUT requests with match bits that won't match any MD. A routed server is
 * especially vulnerable since the connections to its neighbor routers are
 * shared among all clients.
 *
 * \param portal Index of the portal to enable the lazy attribute on.
 *
 * \retval 0       On success.
 * \retval -EINVAL If \a portal is not a valid index.
 */
int
LNetSetLazyPortal(int portal)
{
	struct lnet_portal *ptl;

	if (portal < 0 || portal >= the_lnet.ln_nportals)
		return -EINVAL;

	CDEBUG(D_NET, "Setting portal %d lazy\n", portal);
	ptl = the_lnet.ln_portals[portal];

	lnet_res_lock(LNET_LOCK_EX);
	lnet_ptl_lock(ptl);

	lnet_ptl_setopt(ptl, LNET_PTL_LAZY);

	lnet_ptl_unlock(ptl);
	lnet_res_unlock(LNET_LOCK_EX);

	return 0;
}
EXPORT_SYMBOL(LNetSetLazyPortal);

/**
 * Turn off the lazy portal attribute. Delayed requests on the portal,
 * if any, will be all dropped when this function returns.
 *
 * \param portal Index of the portal to disable the lazy attribute on.
 *
 * \retval 0       On success.
 * \retval -EINVAL If \a portal is not a valid index.
 */
int
LNetClearLazyPortal(int portal)
{
	struct lnet_portal *ptl;
	LIST_HEAD(zombies);

	if (portal < 0 || portal >= the_lnet.ln_nportals)
		return -EINVAL;

	ptl = the_lnet.ln_portals[portal];

	lnet_res_lock(LNET_LOCK_EX);
	lnet_ptl_lock(ptl);

	if (!lnet_ptl_is_lazy(ptl)) {
		lnet_ptl_unlock(ptl);
		lnet_res_unlock(LNET_LOCK_EX);
		return 0;
	}

	if (the_lnet.ln_shutdown)
		CWARN("Active lazy portal %d on exit\n", portal);
	else
		CDEBUG(D_NET, "clearing portal %d lazy\n", portal);

	/* grab all the blocked messages atomically */
	list_splice_init(&ptl->ptl_msg_delayed, &zombies);

	lnet_ptl_unsetopt(ptl, LNET_PTL_LAZY);

	lnet_ptl_unlock(ptl);
	lnet_res_unlock(LNET_LOCK_EX);

	lnet_drop_delayed_msg_list(&zombies, "Clearing lazy portal attr");

	return 0;
}
EXPORT_SYMBOL(LNetClearLazyPortal);
