/* Copyright 2008 - 2016 Freescale Semiconductor, Inc.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *     * Redistributions of source code must retain the above copyright
 *	 notice, this list of conditions and the following disclaimer.
 *     * Redistributions in binary form must reproduce the above copyright
 *	 notice, this list of conditions and the following disclaimer in the
 *	 documentation and/or other materials provided with the distribution.
 *     * Neither the name of Freescale Semiconductor nor the
 *	 names of its contributors may be used to endorse or promote products
 *	 derived from this software without specific prior written permission.
 *
 * ALTERNATIVELY, this software may be distributed under the terms of the
 * GNU General Public License ("GPL") as published by the Free Software
 * Foundation, either version 2 of that License or (at your option) any
 * later version.
 *
 * THIS SOFTWARE IS PROVIDED BY Freescale Semiconductor ``AS IS'' AND ANY
 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 * DISCLAIMED. IN NO EVENT SHALL Freescale Semiconductor BE LIABLE FOR ANY
 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#include "bman_priv.h"

#define IRQNAME		"BMan portal %d"
#define MAX_IRQNAME	16	/* big enough for "BMan portal %d" */

/* Portal register assists */

/* Cache-inhibited register offsets */
#define BM_REG_RCR_PI_CINH	0x0000
#define BM_REG_RCR_CI_CINH	0x0004
#define BM_REG_RCR_ITR		0x0008
#define BM_REG_CFG		0x0100
#define BM_REG_SCN(n)		(0x0200 + ((n) << 2))
#define BM_REG_ISR		0x0e00
#define BM_REG_IER		0x0e04
#define BM_REG_ISDR		0x0e08
#define BM_REG_IIR		0x0e0c

/* Cache-enabled register offsets */
#define BM_CL_CR		0x0000
#define BM_CL_RR0		0x0100
#define BM_CL_RR1		0x0140
#define BM_CL_RCR		0x1000
#define BM_CL_RCR_PI_CENA	0x3000
#define BM_CL_RCR_CI_CENA	0x3100

/*
 * Portal modes.
 *   Enum types;
 *     pmode == production mode
 *     cmode == consumption mode,
 *   Enum values use 3 letter codes. First letter matches the portal mode,
 *   remaining two letters indicate;
 *     ci == cache-inhibited portal register
 *     ce == cache-enabled portal register
 *     vb == in-band valid-bit (cache-enabled)
 */
enum bm_rcr_pmode {		/* matches BCSP_CFG::RPM */
	bm_rcr_pci = 0,		/* PI index, cache-inhibited */
	bm_rcr_pce = 1,		/* PI index, cache-enabled */
	bm_rcr_pvb = 2		/* valid-bit */
};
enum bm_rcr_cmode {		/* s/w-only */
	bm_rcr_cci,		/* CI index, cache-inhibited */
	bm_rcr_cce		/* CI index, cache-enabled */
};


/* --- Portal structures --- */

#define BM_RCR_SIZE		8

/* Release Command */
struct bm_rcr_entry {
	union {
		struct {
			u8 _ncw_verb; /* writes to this are non-coherent */
			u8 bpid; /* used with BM_RCR_VERB_CMD_BPID_SINGLE */
			u8 __reserved1[62];
		};
		struct bm_buffer bufs[8];
	};
};
#define BM_RCR_VERB_VBIT		0x80
#define BM_RCR_VERB_CMD_MASK		0x70	/* one of two values; */
#define BM_RCR_VERB_CMD_BPID_SINGLE	0x20
#define BM_RCR_VERB_CMD_BPID_MULTI	0x30
#define BM_RCR_VERB_BUFCOUNT_MASK	0x0f	/* values 1..8 */

struct bm_rcr {
	struct bm_rcr_entry *ring, *cursor;
	u8 ci, available, ithresh, vbit;
#ifdef CONFIG_FSL_DPAA_CHECKING
	u32 busy;
	enum bm_rcr_pmode pmode;
	enum bm_rcr_cmode cmode;
#endif
};

/* MC (Management Command) command */
struct bm_mc_command {
	u8 _ncw_verb; /* writes to this are non-coherent */
	u8 bpid; /* used by acquire command */
	u8 __reserved[62];
};
#define BM_MCC_VERB_VBIT		0x80
#define BM_MCC_VERB_CMD_MASK		0x70	/* where the verb contains; */
#define BM_MCC_VERB_CMD_ACQUIRE		0x10
#define BM_MCC_VERB_CMD_QUERY		0x40
#define BM_MCC_VERB_ACQUIRE_BUFCOUNT	0x0f	/* values 1..8 go here */

/* MC result, Acquire and Query Response */
union bm_mc_result {
	struct {
		u8 verb;
		u8 bpid;
		u8 __reserved[62];
	};
	struct bm_buffer bufs[8];
};
#define BM_MCR_VERB_VBIT		0x80
#define BM_MCR_VERB_CMD_MASK		BM_MCC_VERB_CMD_MASK
#define BM_MCR_VERB_CMD_ACQUIRE		BM_MCC_VERB_CMD_ACQUIRE
#define BM_MCR_VERB_CMD_QUERY		BM_MCC_VERB_CMD_QUERY
#define BM_MCR_VERB_CMD_ERR_INVALID	0x60
#define BM_MCR_VERB_CMD_ERR_ECC		0x70
#define BM_MCR_VERB_ACQUIRE_BUFCOUNT	BM_MCC_VERB_ACQUIRE_BUFCOUNT /* 0..8 */
#define BM_MCR_TIMEOUT			10000 /* us */

struct bm_mc {
	struct bm_mc_command *cr;
	union bm_mc_result *rr;
	u8 rridx, vbit;
#ifdef CONFIG_FSL_DPAA_CHECKING
	enum {
		/* Can only be _mc_start()ed */
		mc_idle,
		/* Can only be _mc_commit()ed or _mc_abort()ed */
		mc_user,
		/* Can only be _mc_retry()ed */
		mc_hw
	} state;
#endif
};

struct bm_addr {
	void __iomem *ce;	/* cache-enabled */
	void __iomem *ci;	/* cache-inhibited */
};

struct bm_portal {
	struct bm_addr addr;
	struct bm_rcr rcr;
	struct bm_mc mc;
} ____cacheline_aligned;

/* Cache-inhibited register access. */
static inline u32 bm_in(struct bm_portal *p, u32 offset)
{
	return __raw_readl(p->addr.ci + offset);
}

static inline void bm_out(struct bm_portal *p, u32 offset, u32 val)
{
	__raw_writel(val, p->addr.ci + offset);
}

/* Cache Enabled Portal Access */
static inline void bm_cl_invalidate(struct bm_portal *p, u32 offset)
{
	dpaa_invalidate(p->addr.ce + offset);
}

static inline void bm_cl_touch_ro(struct bm_portal *p, u32 offset)
{
	dpaa_touch_ro(p->addr.ce + offset);
}

static inline u32 bm_ce_in(struct bm_portal *p, u32 offset)
{
	return __raw_readl(p->addr.ce + offset);
}

struct bman_portal {
	struct bm_portal p;
	/* interrupt sources processed by portal_isr(), configurable */
	unsigned long irq_sources;
	/* probing time config params for cpu-affine portals */
	const struct bm_portal_config *config;
	char irqname[MAX_IRQNAME];
};

static cpumask_t affine_mask;
static DEFINE_SPINLOCK(affine_mask_lock);
static DEFINE_PER_CPU(struct bman_portal, bman_affine_portal);

static inline struct bman_portal *get_affine_portal(void)
{
	return &get_cpu_var(bman_affine_portal);
}

static inline void put_affine_portal(void)
{
	put_cpu_var(bman_affine_portal);
}

/*
 * This object type refers to a pool, it isn't *the* pool. There may be
 * more than one such object per BMan buffer pool, eg. if different users of the
 * pool are operating via different portals.
 */
struct bman_pool {
	/* index of the buffer pool to encapsulate (0-63) */
	u32 bpid;
	/* Used for hash-table admin when using depletion notifications. */
	struct bman_portal *portal;
	struct bman_pool *next;
};

static u32 poll_portal_slow(struct bman_portal *p, u32 is);

static irqreturn_t portal_isr(int irq, void *ptr)
{
	struct bman_portal *p = ptr;
	struct bm_portal *portal = &p->p;
	u32 clear = p->irq_sources;
	u32 is = bm_in(portal, BM_REG_ISR) & p->irq_sources;

	if (unlikely(!is))
		return IRQ_NONE;

	clear |= poll_portal_slow(p, is);
	bm_out(portal, BM_REG_ISR, clear);
	return IRQ_HANDLED;
}

/* --- RCR API --- */

#define RCR_SHIFT	ilog2(sizeof(struct bm_rcr_entry))
#define RCR_CARRY	(uintptr_t)(BM_RCR_SIZE << RCR_SHIFT)

/* Bit-wise logic to wrap a ring pointer by clearing the "carry bit" */
static struct bm_rcr_entry *rcr_carryclear(struct bm_rcr_entry *p)
{
	uintptr_t addr = (uintptr_t)p;

	addr &= ~RCR_CARRY;

	return (struct bm_rcr_entry *)addr;
}

#ifdef CONFIG_FSL_DPAA_CHECKING
/* Bit-wise logic to convert a ring pointer to a ring index */
static int rcr_ptr2idx(struct bm_rcr_entry *e)
{
	return ((uintptr_t)e >> RCR_SHIFT) & (BM_RCR_SIZE - 1);
}
#endif

/* Increment the 'cursor' ring pointer, taking 'vbit' into account */
static inline void rcr_inc(struct bm_rcr *rcr)
{
	/* increment to the next RCR pointer and handle overflow and 'vbit' */
	struct bm_rcr_entry *partial = rcr->cursor + 1;

	rcr->cursor = rcr_carryclear(partial);
	if (partial != rcr->cursor)
		rcr->vbit ^= BM_RCR_VERB_VBIT;
}

static int bm_rcr_get_avail(struct bm_portal *portal)
{
	struct bm_rcr *rcr = &portal->rcr;

	return rcr->available;
}

static int bm_rcr_get_fill(struct bm_portal *portal)
{
	struct bm_rcr *rcr = &portal->rcr;

	return BM_RCR_SIZE - 1 - rcr->available;
}

static void bm_rcr_set_ithresh(struct bm_portal *portal, u8 ithresh)
{
	struct bm_rcr *rcr = &portal->rcr;

	rcr->ithresh = ithresh;
	bm_out(portal, BM_REG_RCR_ITR, ithresh);
}

static void bm_rcr_cce_prefetch(struct bm_portal *portal)
{
	__maybe_unused struct bm_rcr *rcr = &portal->rcr;

	DPAA_ASSERT(rcr->cmode == bm_rcr_cce);
	bm_cl_touch_ro(portal, BM_CL_RCR_CI_CENA);
}

static u8 bm_rcr_cce_update(struct bm_portal *portal)
{
	struct bm_rcr *rcr = &portal->rcr;
	u8 diff, old_ci = rcr->ci;

	DPAA_ASSERT(rcr->cmode == bm_rcr_cce);
	rcr->ci = bm_ce_in(portal, BM_CL_RCR_CI_CENA) & (BM_RCR_SIZE - 1);
	bm_cl_invalidate(portal, BM_CL_RCR_CI_CENA);
	diff = dpaa_cyc_diff(BM_RCR_SIZE, old_ci, rcr->ci);
	rcr->available += diff;
	return diff;
}

static inline struct bm_rcr_entry *bm_rcr_start(struct bm_portal *portal)
{
	struct bm_rcr *rcr = &portal->rcr;

	DPAA_ASSERT(!rcr->busy);
	if (!rcr->available)
		return NULL;
#ifdef CONFIG_FSL_DPAA_CHECKING
	rcr->busy = 1;
#endif
	dpaa_zero(rcr->cursor);
	return rcr->cursor;
}

static inline void bm_rcr_pvb_commit(struct bm_portal *portal, u8 myverb)
{
	struct bm_rcr *rcr = &portal->rcr;
	struct bm_rcr_entry *rcursor;

	DPAA_ASSERT(rcr->busy);
	DPAA_ASSERT(rcr->pmode == bm_rcr_pvb);
	DPAA_ASSERT(rcr->available >= 1);
	dma_wmb();
	rcursor = rcr->cursor;
	rcursor->_ncw_verb = myverb | rcr->vbit;
	dpaa_flush(rcursor);
	rcr_inc(rcr);
	rcr->available--;
#ifdef CONFIG_FSL_DPAA_CHECKING
	rcr->busy = 0;
#endif
}

static int bm_rcr_init(struct bm_portal *portal, enum bm_rcr_pmode pmode,
		       enum bm_rcr_cmode cmode)
{
	struct bm_rcr *rcr = &portal->rcr;
	u32 cfg;
	u8 pi;

	rcr->ring = portal->addr.ce + BM_CL_RCR;
	rcr->ci = bm_in(portal, BM_REG_RCR_CI_CINH) & (BM_RCR_SIZE - 1);
	pi = bm_in(portal, BM_REG_RCR_PI_CINH) & (BM_RCR_SIZE - 1);
	rcr->cursor = rcr->ring + pi;
	rcr->vbit = (bm_in(portal, BM_REG_RCR_PI_CINH) & BM_RCR_SIZE) ?
		BM_RCR_VERB_VBIT : 0;
	rcr->available = BM_RCR_SIZE - 1
		- dpaa_cyc_diff(BM_RCR_SIZE, rcr->ci, pi);
	rcr->ithresh = bm_in(portal, BM_REG_RCR_ITR);
#ifdef CONFIG_FSL_DPAA_CHECKING
	rcr->busy = 0;
	rcr->pmode = pmode;
	rcr->cmode = cmode;
#endif
	cfg = (bm_in(portal, BM_REG_CFG) & 0xffffffe0)
		| (pmode & 0x3); /* BCSP_CFG::RPM */
	bm_out(portal, BM_REG_CFG, cfg);
	return 0;
}

static void bm_rcr_finish(struct bm_portal *portal)
{
#ifdef CONFIG_FSL_DPAA_CHECKING
	struct bm_rcr *rcr = &portal->rcr;
	int i;

	DPAA_ASSERT(!rcr->busy);

	i = bm_in(portal, BM_REG_RCR_PI_CINH) & (BM_RCR_SIZE - 1);
	if (i != rcr_ptr2idx(rcr->cursor))
		pr_crit("losing uncommited RCR entries\n");

	i = bm_in(portal, BM_REG_RCR_CI_CINH) & (BM_RCR_SIZE - 1);
	if (i != rcr->ci)
		pr_crit("missing existing RCR completions\n");
	if (rcr->ci != rcr_ptr2idx(rcr->cursor))
		pr_crit("RCR destroyed unquiesced\n");
#endif
}

/* --- Management command API --- */
static int bm_mc_init(struct bm_portal *portal)
{
	struct bm_mc *mc = &portal->mc;

	mc->cr = portal->addr.ce + BM_CL_CR;
	mc->rr = portal->addr.ce + BM_CL_RR0;
	mc->rridx = (__raw_readb(&mc->cr->_ncw_verb) & BM_MCC_VERB_VBIT) ?
		    0 : 1;
	mc->vbit = mc->rridx ? BM_MCC_VERB_VBIT : 0;
#ifdef CONFIG_FSL_DPAA_CHECKING
	mc->state = mc_idle;
#endif
	return 0;
}

static void bm_mc_finish(struct bm_portal *portal)
{
#ifdef CONFIG_FSL_DPAA_CHECKING
	struct bm_mc *mc = &portal->mc;

	DPAA_ASSERT(mc->state == mc_idle);
	if (mc->state != mc_idle)
		pr_crit("Losing incomplete MC command\n");
#endif
}

static inline struct bm_mc_command *bm_mc_start(struct bm_portal *portal)
{
	struct bm_mc *mc = &portal->mc;

	DPAA_ASSERT(mc->state == mc_idle);
#ifdef CONFIG_FSL_DPAA_CHECKING
	mc->state = mc_user;
#endif
	dpaa_zero(mc->cr);
	return mc->cr;
}

static inline void bm_mc_commit(struct bm_portal *portal, u8 myverb)
{
	struct bm_mc *mc = &portal->mc;
	union bm_mc_result *rr = mc->rr + mc->rridx;

	DPAA_ASSERT(mc->state == mc_user);
	dma_wmb();
	mc->cr->_ncw_verb = myverb | mc->vbit;
	dpaa_flush(mc->cr);
	dpaa_invalidate_touch_ro(rr);
#ifdef CONFIG_FSL_DPAA_CHECKING
	mc->state = mc_hw;
#endif
}

static inline union bm_mc_result *bm_mc_result(struct bm_portal *portal)
{
	struct bm_mc *mc = &portal->mc;
	union bm_mc_result *rr = mc->rr + mc->rridx;

	DPAA_ASSERT(mc->state == mc_hw);
	/*
	 * The inactive response register's verb byte always returns zero until
	 * its command is submitted and completed. This includes the valid-bit,
	 * in case you were wondering...
	 */
	if (!__raw_readb(&rr->verb)) {
		dpaa_invalidate_touch_ro(rr);
		return NULL;
	}
	mc->rridx ^= 1;
	mc->vbit ^= BM_MCC_VERB_VBIT;
#ifdef CONFIG_FSL_DPAA_CHECKING
	mc->state = mc_idle;
#endif
	return rr;
}

static inline int bm_mc_result_timeout(struct bm_portal *portal,
				       union bm_mc_result **mcr)
{
	int timeout = BM_MCR_TIMEOUT;

	do {
		*mcr = bm_mc_result(portal);
		if (*mcr)
			break;
		udelay(1);
	} while (--timeout);

	return timeout;
}

/* Disable all BSCN interrupts for the portal */
static void bm_isr_bscn_disable(struct bm_portal *portal)
{
	bm_out(portal, BM_REG_SCN(0), 0);
	bm_out(portal, BM_REG_SCN(1), 0);
}

static int bman_create_portal(struct bman_portal *portal,
			      const struct bm_portal_config *c)
{
	struct bm_portal *p;
	int ret;

	p = &portal->p;
	/*
	 * prep the low-level portal struct with the mapped addresses from the
	 * config, everything that follows depends on it and "config" is more
	 * for (de)reference...
	 */
	p->addr.ce = c->addr_virt[DPAA_PORTAL_CE];
	p->addr.ci = c->addr_virt[DPAA_PORTAL_CI];
	if (bm_rcr_init(p, bm_rcr_pvb, bm_rcr_cce)) {
		dev_err(c->dev, "RCR initialisation failed\n");
		goto fail_rcr;
	}
	if (bm_mc_init(p)) {
		dev_err(c->dev, "MC initialisation failed\n");
		goto fail_mc;
	}
	/*
	 * Default to all BPIDs disabled, we enable as required at
	 * run-time.
	 */
	bm_isr_bscn_disable(p);

	/* Write-to-clear any stale interrupt status bits */
	bm_out(p, BM_REG_ISDR, 0xffffffff);
	portal->irq_sources = 0;
	bm_out(p, BM_REG_IER, 0);
	bm_out(p, BM_REG_ISR, 0xffffffff);
	snprintf(portal->irqname, MAX_IRQNAME, IRQNAME, c->cpu);
	if (request_irq(c->irq, portal_isr, 0, portal->irqname,	portal)) {
		dev_err(c->dev, "request_irq() failed\n");
		goto fail_irq;
	}
	if (c->cpu != -1 && irq_can_set_affinity(c->irq) &&
	    irq_set_affinity(c->irq, cpumask_of(c->cpu))) {
		dev_err(c->dev, "irq_set_affinity() failed\n");
		goto fail_affinity;
	}

	/* Need RCR to be empty before continuing */
	ret = bm_rcr_get_fill(p);
	if (ret) {
		dev_err(c->dev, "RCR unclean\n");
		goto fail_rcr_empty;
	}
	/* Success */
	portal->config = c;

	bm_out(p, BM_REG_ISDR, 0);
	bm_out(p, BM_REG_IIR, 0);

	return 0;

fail_rcr_empty:
fail_affinity:
	free_irq(c->irq, portal);
fail_irq:
	bm_mc_finish(p);
fail_mc:
	bm_rcr_finish(p);
fail_rcr:
	return -EIO;
}

struct bman_portal *bman_create_affine_portal(const struct bm_portal_config *c)
{
	struct bman_portal *portal;
	int err;

	portal = &per_cpu(bman_affine_portal, c->cpu);
	err = bman_create_portal(portal, c);
	if (err)
		return NULL;

	spin_lock(&affine_mask_lock);
	cpumask_set_cpu(c->cpu, &affine_mask);
	spin_unlock(&affine_mask_lock);

	return portal;
}

static u32 poll_portal_slow(struct bman_portal *p, u32 is)
{
	u32 ret = is;

	if (is & BM_PIRQ_RCRI) {
		bm_rcr_cce_update(&p->p);
		bm_rcr_set_ithresh(&p->p, 0);
		bm_out(&p->p, BM_REG_ISR, BM_PIRQ_RCRI);
		is &= ~BM_PIRQ_RCRI;
	}

	/* There should be no status register bits left undefined */
	DPAA_ASSERT(!is);
	return ret;
}

int bman_p_irqsource_add(struct bman_portal *p, u32 bits)
{
	unsigned long irqflags;

	local_irq_save(irqflags);
	set_bits(bits & BM_PIRQ_VISIBLE, &p->irq_sources);
	bm_out(&p->p, BM_REG_IER, p->irq_sources);
	local_irq_restore(irqflags);
	return 0;
}

static int bm_shutdown_pool(u32 bpid)
{
	struct bm_mc_command *bm_cmd;
	union bm_mc_result *bm_res;

	while (1) {
		struct bman_portal *p = get_affine_portal();
		/* Acquire buffers until empty */
		bm_cmd = bm_mc_start(&p->p);
		bm_cmd->bpid = bpid;
		bm_mc_commit(&p->p, BM_MCC_VERB_CMD_ACQUIRE | 1);
		if (!bm_mc_result_timeout(&p->p, &bm_res)) {
			put_affine_portal();
			pr_crit("BMan Acquire Command timedout\n");
			return -ETIMEDOUT;
		}
		if (!(bm_res->verb & BM_MCR_VERB_ACQUIRE_BUFCOUNT)) {
			put_affine_portal();
			/* Pool is empty */
			return 0;
		}
		put_affine_portal();
	}

	return 0;
}

struct gen_pool *bm_bpalloc;

static int bm_alloc_bpid_range(u32 *result, u32 count)
{
	unsigned long addr;

	addr = gen_pool_alloc(bm_bpalloc, count);
	if (!addr)
		return -ENOMEM;

	*result = addr & ~DPAA_GENALLOC_OFF;

	return 0;
}

static int bm_release_bpid(u32 bpid)
{
	int ret;

	ret = bm_shutdown_pool(bpid);
	if (ret) {
		pr_debug("BPID %d leaked\n", bpid);
		return ret;
	}

	gen_pool_free(bm_bpalloc, bpid | DPAA_GENALLOC_OFF, 1);
	return 0;
}

struct bman_pool *bman_new_pool(void)
{
	struct bman_pool *pool = NULL;
	u32 bpid;

	if (bm_alloc_bpid_range(&bpid, 1))
		return NULL;

	pool = kmalloc(sizeof(*pool), GFP_KERNEL);
	if (!pool)
		goto err;

	pool->bpid = bpid;

	return pool;
err:
	bm_release_bpid(bpid);
	kfree(pool);
	return NULL;
}
EXPORT_SYMBOL(bman_new_pool);

void bman_free_pool(struct bman_pool *pool)
{
	bm_release_bpid(pool->bpid);

	kfree(pool);
}
EXPORT_SYMBOL(bman_free_pool);

int bman_get_bpid(const struct bman_pool *pool)
{
	return pool->bpid;
}
EXPORT_SYMBOL(bman_get_bpid);

static void update_rcr_ci(struct bman_portal *p, int avail)
{
	if (avail)
		bm_rcr_cce_prefetch(&p->p);
	else
		bm_rcr_cce_update(&p->p);
}

int bman_release(struct bman_pool *pool, const struct bm_buffer *bufs, u8 num)
{
	struct bman_portal *p;
	struct bm_rcr_entry *r;
	unsigned long irqflags;
	int avail, timeout = 1000; /* 1ms */
	int i = num - 1;

	DPAA_ASSERT(num > 0 && num <= 8);

	do {
		p = get_affine_portal();
		local_irq_save(irqflags);
		avail = bm_rcr_get_avail(&p->p);
		if (avail < 2)
			update_rcr_ci(p, avail);
		r = bm_rcr_start(&p->p);
		local_irq_restore(irqflags);
		put_affine_portal();
		if (likely(r))
			break;

		udelay(1);
	} while (--timeout);

	if (unlikely(!timeout))
		return -ETIMEDOUT;

	p = get_affine_portal();
	local_irq_save(irqflags);
	/*
	 * we can copy all but the first entry, as this can trigger badness
	 * with the valid-bit
	 */
	bm_buffer_set64(r->bufs, bm_buffer_get64(bufs));
	bm_buffer_set_bpid(r->bufs, pool->bpid);
	if (i)
		memcpy(&r->bufs[1], &bufs[1], i * sizeof(bufs[0]));

	bm_rcr_pvb_commit(&p->p, BM_RCR_VERB_CMD_BPID_SINGLE |
			  (num & BM_RCR_VERB_BUFCOUNT_MASK));

	local_irq_restore(irqflags);
	put_affine_portal();
	return 0;
}
EXPORT_SYMBOL(bman_release);

int bman_acquire(struct bman_pool *pool, struct bm_buffer *bufs, u8 num)
{
	struct bman_portal *p = get_affine_portal();
	struct bm_mc_command *mcc;
	union bm_mc_result *mcr;
	int ret;

	DPAA_ASSERT(num > 0 && num <= 8);

	mcc = bm_mc_start(&p->p);
	mcc->bpid = pool->bpid;
	bm_mc_commit(&p->p, BM_MCC_VERB_CMD_ACQUIRE |
		     (num & BM_MCC_VERB_ACQUIRE_BUFCOUNT));
	if (!bm_mc_result_timeout(&p->p, &mcr)) {
		put_affine_portal();
		pr_crit("BMan Acquire Timeout\n");
		return -ETIMEDOUT;
	}
	ret = mcr->verb & BM_MCR_VERB_ACQUIRE_BUFCOUNT;
	if (bufs)
		memcpy(&bufs[0], &mcr->bufs[0], num * sizeof(bufs[0]));

	put_affine_portal();
	if (ret != num)
		ret = -ENOMEM;
	return ret;
}
EXPORT_SYMBOL(bman_acquire);

const struct bm_portal_config *
bman_get_bm_portal_config(const struct bman_portal *portal)
{
	return portal->config;
}
