xref: /dpdk/drivers/mempool/octeontx/octeontx_fpavf.c (revision e77506397fc8005c5129e22e9e2d15d5876790fd)
1aaf4363eSJerin Jacob /* SPDX-License-Identifier: BSD-3-Clause
2aaf4363eSJerin Jacob  * Copyright(c) 2017 Cavium, Inc
38700239fSSantosh Shukla  */
41c842786SSantosh Shukla 
51c842786SSantosh Shukla #include <stdlib.h>
61c842786SSantosh Shukla #include <string.h>
71c842786SSantosh Shukla #include <stdbool.h>
81c842786SSantosh Shukla #include <stdio.h>
91c842786SSantosh Shukla #include <unistd.h>
101c842786SSantosh Shukla #include <fcntl.h>
111c842786SSantosh Shukla #include <errno.h>
121c842786SSantosh Shukla #include <sys/mman.h>
131c842786SSantosh Shukla 
141c842786SSantosh Shukla #include <rte_atomic.h>
151c842786SSantosh Shukla #include <rte_eal.h>
161f37cb2bSDavid Marchand #include <bus_pci_driver.h>
171c842786SSantosh Shukla #include <rte_errno.h>
181c842786SSantosh Shukla #include <rte_memory.h>
191c842786SSantosh Shukla #include <rte_malloc.h>
201c842786SSantosh Shukla #include <rte_spinlock.h>
2102fd6c74SSantosh Shukla #include <rte_mbuf.h>
221c842786SSantosh Shukla 
2389ee1e94SSantosh Shukla #include "octeontx_mbox.h"
241c842786SSantosh Shukla #include "octeontx_fpavf.h"
251c842786SSantosh Shukla 
2602fd6c74SSantosh Shukla /* FPA Mbox Message */
2702fd6c74SSantosh Shukla #define IDENTIFY		0x0
2802fd6c74SSantosh Shukla 
2902fd6c74SSantosh Shukla #define FPA_CONFIGSET		0x1
3002fd6c74SSantosh Shukla #define FPA_CONFIGGET		0x2
3102fd6c74SSantosh Shukla #define FPA_START_COUNT		0x3
3202fd6c74SSantosh Shukla #define FPA_STOP_COUNT		0x4
3302fd6c74SSantosh Shukla #define FPA_ATTACHAURA		0x5
3402fd6c74SSantosh Shukla #define FPA_DETACHAURA		0x6
3502fd6c74SSantosh Shukla #define FPA_SETAURALVL		0x7
3602fd6c74SSantosh Shukla #define FPA_GETAURALVL		0x8
3702fd6c74SSantosh Shukla 
3802fd6c74SSantosh Shukla #define FPA_COPROC		0x1
3902fd6c74SSantosh Shukla 
4002fd6c74SSantosh Shukla /* fpa mbox struct */
4102fd6c74SSantosh Shukla struct octeontx_mbox_fpa_cfg {
4202fd6c74SSantosh Shukla 	int		aid;
4302fd6c74SSantosh Shukla 	uint64_t	pool_cfg;
4402fd6c74SSantosh Shukla 	uint64_t	pool_stack_base;
4502fd6c74SSantosh Shukla 	uint64_t	pool_stack_end;
4602fd6c74SSantosh Shukla 	uint64_t	aura_cfg;
4702fd6c74SSantosh Shukla };
4802fd6c74SSantosh Shukla 
49*e7750639SAndre Muezerie struct __rte_packed_begin gen_req {
5002fd6c74SSantosh Shukla 	uint32_t	value;
51*e7750639SAndre Muezerie } __rte_packed_end;
5202fd6c74SSantosh Shukla 
53*e7750639SAndre Muezerie struct __rte_packed_begin idn_req {
5402fd6c74SSantosh Shukla 	uint8_t	domain_id;
55*e7750639SAndre Muezerie } __rte_packed_end;
5602fd6c74SSantosh Shukla 
57*e7750639SAndre Muezerie struct __rte_packed_begin gen_resp {
5802fd6c74SSantosh Shukla 	uint16_t	domain_id;
5902fd6c74SSantosh Shukla 	uint16_t	vfid;
60*e7750639SAndre Muezerie } __rte_packed_end;
6102fd6c74SSantosh Shukla 
62*e7750639SAndre Muezerie struct __rte_packed_begin dcfg_resp {
6302fd6c74SSantosh Shukla 	uint8_t	sso_count;
6402fd6c74SSantosh Shukla 	uint8_t	ssow_count;
6502fd6c74SSantosh Shukla 	uint8_t	fpa_count;
6602fd6c74SSantosh Shukla 	uint8_t	pko_count;
6702fd6c74SSantosh Shukla 	uint8_t	tim_count;
6802fd6c74SSantosh Shukla 	uint8_t	net_port_count;
6902fd6c74SSantosh Shukla 	uint8_t	virt_port_count;
70*e7750639SAndre Muezerie } __rte_packed_end;
7102fd6c74SSantosh Shukla 
7202fd6c74SSantosh Shukla #define FPA_MAX_POOL	32
7302fd6c74SSantosh Shukla #define FPA_PF_PAGE_SZ	4096
7402fd6c74SSantosh Shukla 
7502fd6c74SSantosh Shukla #define FPA_LN_SIZE	128
7602fd6c74SSantosh Shukla #define FPA_ROUND_UP(x, size) \
7702fd6c74SSantosh Shukla 	((((unsigned long)(x)) + size-1) & (~(size-1)))
7802fd6c74SSantosh Shukla #define FPA_OBJSZ_2_CACHE_LINE(sz)	(((sz) + RTE_CACHE_LINE_MASK) >> 7)
7902fd6c74SSantosh Shukla #define FPA_CACHE_LINE_2_OBJSZ(sz)	((sz) << 7)
8002fd6c74SSantosh Shukla 
8102fd6c74SSantosh Shukla #define POOL_ENA			(0x1 << 0)
8202fd6c74SSantosh Shukla #define POOL_DIS			(0x0 << 0)
8302fd6c74SSantosh Shukla #define POOL_SET_NAT_ALIGN		(0x1 << 1)
8402fd6c74SSantosh Shukla #define POOL_DIS_NAT_ALIGN		(0x0 << 1)
8502fd6c74SSantosh Shukla #define POOL_STYPE(x)			(((x) & 0x1) << 2)
8602fd6c74SSantosh Shukla #define POOL_LTYPE(x)			(((x) & 0x3) << 3)
8702fd6c74SSantosh Shukla #define POOL_BUF_OFFSET(x)		(((x) & 0x7fffULL) << 16)
8802fd6c74SSantosh Shukla #define POOL_BUF_SIZE(x)		(((x) & 0x7ffULL) << 32)
8902fd6c74SSantosh Shukla 
901c842786SSantosh Shukla struct fpavf_res {
911c842786SSantosh Shukla 	void		*pool_stack_base;
921c842786SSantosh Shukla 	void		*bar0;
931c842786SSantosh Shukla 	uint64_t	stack_ln_ptr;
941c842786SSantosh Shukla 	uint16_t	domain_id;
951c842786SSantosh Shukla 	uint16_t	vf_id;	/* gpool_id */
961c842786SSantosh Shukla 	uint16_t	sz128;	/* Block size in cache lines */
971c842786SSantosh Shukla 	bool		is_inuse;
981c842786SSantosh Shukla };
991c842786SSantosh Shukla 
1001c842786SSantosh Shukla struct octeontx_fpadev {
1011c842786SSantosh Shukla 	rte_spinlock_t lock;
1021c842786SSantosh Shukla 	uint8_t	total_gpool_cnt;
1031c842786SSantosh Shukla 	struct fpavf_res pool[FPA_VF_MAX];
1041c842786SSantosh Shukla };
1051c842786SSantosh Shukla 
1061c842786SSantosh Shukla static struct octeontx_fpadev fpadev;
1071c842786SSantosh Shukla 
1089c99878aSJerin Jacob RTE_LOG_REGISTER(octeontx_logtype_fpavf, pmd.mempool.octeontx, NOTICE);
1097d6321deSPavan Nikhilesh 
11002fd6c74SSantosh Shukla /* lock is taken by caller */
11102fd6c74SSantosh Shukla static int
11202fd6c74SSantosh Shukla octeontx_fpa_gpool_alloc(unsigned int object_size)
11302fd6c74SSantosh Shukla {
1149bc692f8SPavan Nikhilesh 	uint16_t global_domain = octeontx_get_global_domain();
11502fd6c74SSantosh Shukla 	struct fpavf_res *res = NULL;
11602fd6c74SSantosh Shukla 	unsigned int sz128;
1179bc692f8SPavan Nikhilesh 	int i;
11802fd6c74SSantosh Shukla 
11902fd6c74SSantosh Shukla 	sz128 = FPA_OBJSZ_2_CACHE_LINE(object_size);
12002fd6c74SSantosh Shukla 
1219bc692f8SPavan Nikhilesh 	for (i = 0; i < FPA_VF_MAX; i++) {
12202fd6c74SSantosh Shukla 
12302fd6c74SSantosh Shukla 		/* Skip VF that is not mapped Or _inuse */
1249bc692f8SPavan Nikhilesh 		if ((fpadev.pool[i].bar0 == NULL) ||
1259bc692f8SPavan Nikhilesh 		    (fpadev.pool[i].is_inuse == true) ||
1269bc692f8SPavan Nikhilesh 		    (fpadev.pool[i].domain_id != global_domain))
12702fd6c74SSantosh Shukla 			continue;
12802fd6c74SSantosh Shukla 
1299bc692f8SPavan Nikhilesh 		res = &fpadev.pool[i];
13002fd6c74SSantosh Shukla 
13102fd6c74SSantosh Shukla 		RTE_ASSERT(res->domain_id != (uint16_t)~0);
13202fd6c74SSantosh Shukla 		RTE_ASSERT(res->vf_id != (uint16_t)~0);
13302fd6c74SSantosh Shukla 		RTE_ASSERT(res->stack_ln_ptr != 0);
13402fd6c74SSantosh Shukla 
13502fd6c74SSantosh Shukla 		if (res->sz128 == 0) {
13602fd6c74SSantosh Shukla 			res->sz128 = sz128;
137f665790aSDavid Marchand 			fpavf_log_dbg("gpool %d blk_sz %d", res->vf_id,
1389bc692f8SPavan Nikhilesh 				      sz128);
13902fd6c74SSantosh Shukla 
1409bc692f8SPavan Nikhilesh 			return res->vf_id;
14102fd6c74SSantosh Shukla 		}
14202fd6c74SSantosh Shukla 	}
14302fd6c74SSantosh Shukla 
14402fd6c74SSantosh Shukla 	return -ENOSPC;
14502fd6c74SSantosh Shukla }
14602fd6c74SSantosh Shukla 
1479bc692f8SPavan Nikhilesh static __rte_always_inline struct fpavf_res *
1489bc692f8SPavan Nikhilesh octeontx_get_fpavf(uint16_t gpool)
1499bc692f8SPavan Nikhilesh {
1509bc692f8SPavan Nikhilesh 	uint16_t global_domain = octeontx_get_global_domain();
1519bc692f8SPavan Nikhilesh 	int i;
1529bc692f8SPavan Nikhilesh 
1539bc692f8SPavan Nikhilesh 	for (i = 0; i < FPA_VF_MAX; i++) {
1549bc692f8SPavan Nikhilesh 		if (fpadev.pool[i].domain_id != global_domain)
1559bc692f8SPavan Nikhilesh 			continue;
1569bc692f8SPavan Nikhilesh 		if (fpadev.pool[i].vf_id != gpool)
1579bc692f8SPavan Nikhilesh 			continue;
1589bc692f8SPavan Nikhilesh 
1599bc692f8SPavan Nikhilesh 		return &fpadev.pool[i];
1609bc692f8SPavan Nikhilesh 	}
1619bc692f8SPavan Nikhilesh 
1629bc692f8SPavan Nikhilesh 	return NULL;
1639bc692f8SPavan Nikhilesh }
1649bc692f8SPavan Nikhilesh 
16502fd6c74SSantosh Shukla /* lock is taken by caller */
16602fd6c74SSantosh Shukla static __rte_always_inline uintptr_t
16702fd6c74SSantosh Shukla octeontx_fpa_gpool2handle(uint16_t gpool)
16802fd6c74SSantosh Shukla {
16902fd6c74SSantosh Shukla 	struct fpavf_res *res = NULL;
17002fd6c74SSantosh Shukla 
17102fd6c74SSantosh Shukla 	RTE_ASSERT(gpool < FPA_VF_MAX);
1729bc692f8SPavan Nikhilesh 	res = octeontx_get_fpavf(gpool);
1739bc692f8SPavan Nikhilesh 	if (res == NULL)
1749bc692f8SPavan Nikhilesh 		return 0;
17502fd6c74SSantosh Shukla 
17602fd6c74SSantosh Shukla 	return (uintptr_t)res->bar0 | gpool;
17702fd6c74SSantosh Shukla }
17802fd6c74SSantosh Shukla 
17902fd6c74SSantosh Shukla static __rte_always_inline bool
18002fd6c74SSantosh Shukla octeontx_fpa_handle_valid(uintptr_t handle)
18102fd6c74SSantosh Shukla {
18202fd6c74SSantosh Shukla 	struct fpavf_res *res = NULL;
18302fd6c74SSantosh Shukla 	uint8_t gpool;
18402fd6c74SSantosh Shukla 	int i;
18502fd6c74SSantosh Shukla 	bool ret = false;
18602fd6c74SSantosh Shukla 
18702fd6c74SSantosh Shukla 	if (unlikely(!handle))
18802fd6c74SSantosh Shukla 		return ret;
18902fd6c74SSantosh Shukla 
19002fd6c74SSantosh Shukla 	/* get the gpool */
19102fd6c74SSantosh Shukla 	gpool = octeontx_fpa_bufpool_gpool(handle);
19202fd6c74SSantosh Shukla 
19302fd6c74SSantosh Shukla 	/* get the bar address */
19402fd6c74SSantosh Shukla 	handle &= ~(uint64_t)FPA_GPOOL_MASK;
19502fd6c74SSantosh Shukla 	for (i = 0; i < FPA_VF_MAX; i++) {
19602fd6c74SSantosh Shukla 		if ((uintptr_t)fpadev.pool[i].bar0 != handle)
19702fd6c74SSantosh Shukla 			continue;
19802fd6c74SSantosh Shukla 
19902fd6c74SSantosh Shukla 		/* validate gpool */
2009bc692f8SPavan Nikhilesh 		if (gpool != fpadev.pool[i].vf_id)
20102fd6c74SSantosh Shukla 			return false;
20202fd6c74SSantosh Shukla 
20302fd6c74SSantosh Shukla 		res = &fpadev.pool[i];
20402fd6c74SSantosh Shukla 
20502fd6c74SSantosh Shukla 		if (res->sz128 == 0 || res->domain_id == (uint16_t)~0 ||
20602fd6c74SSantosh Shukla 		    res->stack_ln_ptr == 0)
20702fd6c74SSantosh Shukla 			ret = false;
20802fd6c74SSantosh Shukla 		else
20902fd6c74SSantosh Shukla 			ret = true;
21002fd6c74SSantosh Shukla 		break;
21102fd6c74SSantosh Shukla 	}
21202fd6c74SSantosh Shukla 
21302fd6c74SSantosh Shukla 	return ret;
21402fd6c74SSantosh Shukla }
21502fd6c74SSantosh Shukla 
21602fd6c74SSantosh Shukla static int
21702fd6c74SSantosh Shukla octeontx_fpapf_pool_setup(unsigned int gpool, unsigned int buf_size,
21802fd6c74SSantosh Shukla 			  signed short buf_offset, unsigned int max_buf_count)
21902fd6c74SSantosh Shukla {
22002fd6c74SSantosh Shukla 	void *memptr = NULL;
221efd785f9SThomas Monjalon 	rte_iova_t phys_addr;
22202fd6c74SSantosh Shukla 	unsigned int memsz;
22302fd6c74SSantosh Shukla 	struct fpavf_res *fpa = NULL;
22402fd6c74SSantosh Shukla 	uint64_t reg;
22502fd6c74SSantosh Shukla 	struct octeontx_mbox_hdr hdr;
22602fd6c74SSantosh Shukla 	struct dcfg_resp resp;
22702fd6c74SSantosh Shukla 	struct octeontx_mbox_fpa_cfg cfg;
22802fd6c74SSantosh Shukla 	int ret = -1;
22902fd6c74SSantosh Shukla 
2309bc692f8SPavan Nikhilesh 	fpa = octeontx_get_fpavf(gpool);
2319bc692f8SPavan Nikhilesh 	if (fpa == NULL)
2329bc692f8SPavan Nikhilesh 		return -EINVAL;
2339bc692f8SPavan Nikhilesh 
23402fd6c74SSantosh Shukla 	memsz = FPA_ROUND_UP(max_buf_count / fpa->stack_ln_ptr, FPA_LN_SIZE) *
23502fd6c74SSantosh Shukla 			FPA_LN_SIZE;
23602fd6c74SSantosh Shukla 
23702fd6c74SSantosh Shukla 	/* Round-up to page size */
23802fd6c74SSantosh Shukla 	memsz = (memsz + FPA_PF_PAGE_SZ - 1) & ~(uintptr_t)(FPA_PF_PAGE_SZ-1);
23902fd6c74SSantosh Shukla 	memptr = rte_malloc(NULL, memsz, RTE_CACHE_LINE_SIZE);
24002fd6c74SSantosh Shukla 	if (memptr == NULL) {
24102fd6c74SSantosh Shukla 		ret = -ENOMEM;
24202fd6c74SSantosh Shukla 		goto err;
24302fd6c74SSantosh Shukla 	}
24402fd6c74SSantosh Shukla 
24502fd6c74SSantosh Shukla 	/* Configure stack */
24602fd6c74SSantosh Shukla 	fpa->pool_stack_base = memptr;
24787cf4c6cSThomas Monjalon 	phys_addr = rte_malloc_virt2iova(memptr);
24802fd6c74SSantosh Shukla 
24902fd6c74SSantosh Shukla 	buf_size /= FPA_LN_SIZE;
25002fd6c74SSantosh Shukla 
25102fd6c74SSantosh Shukla 	/* POOL setup */
25202fd6c74SSantosh Shukla 	hdr.coproc = FPA_COPROC;
25302fd6c74SSantosh Shukla 	hdr.msg = FPA_CONFIGSET;
25402fd6c74SSantosh Shukla 	hdr.vfid = fpa->vf_id;
25502fd6c74SSantosh Shukla 	hdr.res_code = 0;
25602fd6c74SSantosh Shukla 
25702fd6c74SSantosh Shukla 	buf_offset /= FPA_LN_SIZE;
25802fd6c74SSantosh Shukla 	reg = POOL_BUF_SIZE(buf_size) | POOL_BUF_OFFSET(buf_offset) |
25902fd6c74SSantosh Shukla 		POOL_LTYPE(0x2) | POOL_STYPE(0) | POOL_SET_NAT_ALIGN |
26002fd6c74SSantosh Shukla 		POOL_ENA;
26102fd6c74SSantosh Shukla 
262e1712291SPavan Nikhilesh 	cfg.aid = 0;
26302fd6c74SSantosh Shukla 	cfg.pool_cfg = reg;
26402fd6c74SSantosh Shukla 	cfg.pool_stack_base = phys_addr;
26502fd6c74SSantosh Shukla 	cfg.pool_stack_end = phys_addr + memsz;
26602fd6c74SSantosh Shukla 	cfg.aura_cfg = (1 << 9);
26702fd6c74SSantosh Shukla 
268d8dd3165SPavan Nikhilesh 	ret = octeontx_mbox_send(&hdr, &cfg,
26902fd6c74SSantosh Shukla 					sizeof(struct octeontx_mbox_fpa_cfg),
27002fd6c74SSantosh Shukla 					&resp, sizeof(resp));
27102fd6c74SSantosh Shukla 	if (ret < 0) {
27202fd6c74SSantosh Shukla 		ret = -EACCES;
27302fd6c74SSantosh Shukla 		goto err;
27402fd6c74SSantosh Shukla 	}
27502fd6c74SSantosh Shukla 
276f665790aSDavid Marchand 	fpavf_log_dbg(" vfid %d gpool %d aid %d pool_cfg 0x%x pool_stack_base %" PRIx64 " pool_stack_end %" PRIx64" aura_cfg %" PRIx64,
27702fd6c74SSantosh Shukla 		      fpa->vf_id, gpool, cfg.aid, (unsigned int)cfg.pool_cfg,
27802fd6c74SSantosh Shukla 		      cfg.pool_stack_base, cfg.pool_stack_end, cfg.aura_cfg);
27902fd6c74SSantosh Shukla 
28002fd6c74SSantosh Shukla 	/* Now pool is in_use */
28102fd6c74SSantosh Shukla 	fpa->is_inuse = true;
28202fd6c74SSantosh Shukla 
28302fd6c74SSantosh Shukla err:
28402fd6c74SSantosh Shukla 	if (ret < 0)
28502fd6c74SSantosh Shukla 		rte_free(memptr);
28602fd6c74SSantosh Shukla 
28702fd6c74SSantosh Shukla 	return ret;
28802fd6c74SSantosh Shukla }
28902fd6c74SSantosh Shukla 
29002fd6c74SSantosh Shukla static int
29102fd6c74SSantosh Shukla octeontx_fpapf_pool_destroy(unsigned int gpool_index)
29202fd6c74SSantosh Shukla {
29302fd6c74SSantosh Shukla 	struct octeontx_mbox_hdr hdr;
29402fd6c74SSantosh Shukla 	struct dcfg_resp resp;
29502fd6c74SSantosh Shukla 	struct octeontx_mbox_fpa_cfg cfg;
29602fd6c74SSantosh Shukla 	struct fpavf_res *fpa = NULL;
29702fd6c74SSantosh Shukla 	int ret = -1;
29802fd6c74SSantosh Shukla 
2999bc692f8SPavan Nikhilesh 	fpa = octeontx_get_fpavf(gpool_index);
3004f2c3c7bSKrzysztof Kanas 	if (fpa == NULL)
3014f2c3c7bSKrzysztof Kanas 		return -EINVAL;
30202fd6c74SSantosh Shukla 
30302fd6c74SSantosh Shukla 	hdr.coproc = FPA_COPROC;
30402fd6c74SSantosh Shukla 	hdr.msg = FPA_CONFIGSET;
30502fd6c74SSantosh Shukla 	hdr.vfid = fpa->vf_id;
30602fd6c74SSantosh Shukla 	hdr.res_code = 0;
30702fd6c74SSantosh Shukla 
30802fd6c74SSantosh Shukla 	/* reset and free the pool */
30902fd6c74SSantosh Shukla 	cfg.aid = 0;
31002fd6c74SSantosh Shukla 	cfg.pool_cfg = 0;
31102fd6c74SSantosh Shukla 	cfg.pool_stack_base = 0;
31202fd6c74SSantosh Shukla 	cfg.pool_stack_end = 0;
31302fd6c74SSantosh Shukla 	cfg.aura_cfg = 0;
31402fd6c74SSantosh Shukla 
315d8dd3165SPavan Nikhilesh 	ret = octeontx_mbox_send(&hdr, &cfg,
31602fd6c74SSantosh Shukla 					sizeof(struct octeontx_mbox_fpa_cfg),
31702fd6c74SSantosh Shukla 					&resp, sizeof(resp));
31802fd6c74SSantosh Shukla 	if (ret < 0) {
31902fd6c74SSantosh Shukla 		ret = -EACCES;
32002fd6c74SSantosh Shukla 		goto err;
32102fd6c74SSantosh Shukla 	}
32202fd6c74SSantosh Shukla 
32302fd6c74SSantosh Shukla 	ret = 0;
32402fd6c74SSantosh Shukla err:
32502fd6c74SSantosh Shukla 	/* anycase free pool stack memory */
32602fd6c74SSantosh Shukla 	rte_free(fpa->pool_stack_base);
32702fd6c74SSantosh Shukla 	fpa->pool_stack_base = NULL;
32802fd6c74SSantosh Shukla 	return ret;
32902fd6c74SSantosh Shukla }
33002fd6c74SSantosh Shukla 
33102fd6c74SSantosh Shukla static int
33202fd6c74SSantosh Shukla octeontx_fpapf_aura_attach(unsigned int gpool_index)
33302fd6c74SSantosh Shukla {
33402fd6c74SSantosh Shukla 	struct octeontx_mbox_hdr hdr;
33502fd6c74SSantosh Shukla 	struct dcfg_resp resp;
33602fd6c74SSantosh Shukla 	struct octeontx_mbox_fpa_cfg cfg;
33702fd6c74SSantosh Shukla 	int ret = 0;
33802fd6c74SSantosh Shukla 
33902fd6c74SSantosh Shukla 	if (gpool_index >= FPA_MAX_POOL) {
34002fd6c74SSantosh Shukla 		ret = -EINVAL;
34102fd6c74SSantosh Shukla 		goto err;
34202fd6c74SSantosh Shukla 	}
34302fd6c74SSantosh Shukla 	hdr.coproc = FPA_COPROC;
34402fd6c74SSantosh Shukla 	hdr.msg = FPA_ATTACHAURA;
34502fd6c74SSantosh Shukla 	hdr.vfid = gpool_index;
34602fd6c74SSantosh Shukla 	hdr.res_code = 0;
34702fd6c74SSantosh Shukla 	memset(&cfg, 0x0, sizeof(struct octeontx_mbox_fpa_cfg));
348e1712291SPavan Nikhilesh 	cfg.aid = 0;
34902fd6c74SSantosh Shukla 
350d8dd3165SPavan Nikhilesh 	ret = octeontx_mbox_send(&hdr, &cfg,
35102fd6c74SSantosh Shukla 					sizeof(struct octeontx_mbox_fpa_cfg),
35202fd6c74SSantosh Shukla 					&resp, sizeof(resp));
35302fd6c74SSantosh Shukla 	if (ret < 0) {
354f665790aSDavid Marchand 		fpavf_log_err("Could not attach fpa aura %d to pool %d. Err=%d. FuncErr=%d",
355179c7e89SPavan Nikhilesh 			      FPA_AURA_IDX(gpool_index), gpool_index, ret,
356179c7e89SPavan Nikhilesh 			      hdr.res_code);
35702fd6c74SSantosh Shukla 		ret = -EACCES;
35802fd6c74SSantosh Shukla 		goto err;
35902fd6c74SSantosh Shukla 	}
36002fd6c74SSantosh Shukla err:
36102fd6c74SSantosh Shukla 	return ret;
36202fd6c74SSantosh Shukla }
36302fd6c74SSantosh Shukla 
36402fd6c74SSantosh Shukla static int
36502fd6c74SSantosh Shukla octeontx_fpapf_aura_detach(unsigned int gpool_index)
36602fd6c74SSantosh Shukla {
36702fd6c74SSantosh Shukla 	struct octeontx_mbox_fpa_cfg cfg = {0};
36802fd6c74SSantosh Shukla 	struct octeontx_mbox_hdr hdr = {0};
36902fd6c74SSantosh Shukla 	int ret = 0;
37002fd6c74SSantosh Shukla 
37102fd6c74SSantosh Shukla 	if (gpool_index >= FPA_MAX_POOL) {
37202fd6c74SSantosh Shukla 		ret = -EINVAL;
37302fd6c74SSantosh Shukla 		goto err;
37402fd6c74SSantosh Shukla 	}
37502fd6c74SSantosh Shukla 
376e1712291SPavan Nikhilesh 	cfg.aid = 0;
37702fd6c74SSantosh Shukla 	hdr.coproc = FPA_COPROC;
37802fd6c74SSantosh Shukla 	hdr.msg = FPA_DETACHAURA;
37902fd6c74SSantosh Shukla 	hdr.vfid = gpool_index;
380d8dd3165SPavan Nikhilesh 	ret = octeontx_mbox_send(&hdr, &cfg, sizeof(cfg), NULL, 0);
38102fd6c74SSantosh Shukla 	if (ret < 0) {
382f665790aSDavid Marchand 		fpavf_log_err("Couldn't detach FPA aura %d Err=%d FuncErr=%d",
383179c7e89SPavan Nikhilesh 			      FPA_AURA_IDX(gpool_index), ret,
384179c7e89SPavan Nikhilesh 			      hdr.res_code);
38502fd6c74SSantosh Shukla 		ret = -EINVAL;
38602fd6c74SSantosh Shukla 	}
38702fd6c74SSantosh Shukla 
38802fd6c74SSantosh Shukla err:
38902fd6c74SSantosh Shukla 	return ret;
39002fd6c74SSantosh Shukla }
39102fd6c74SSantosh Shukla 
392f477a469SPavan Nikhilesh int
393f477a469SPavan Nikhilesh octeontx_fpavf_pool_set_range(uintptr_t handle, unsigned long memsz,
39402fd6c74SSantosh Shukla 			  void *memva, uint16_t gpool)
39502fd6c74SSantosh Shukla {
39602fd6c74SSantosh Shukla 	uint64_t va_end;
39702fd6c74SSantosh Shukla 
39802fd6c74SSantosh Shukla 	if (unlikely(!handle))
39902fd6c74SSantosh Shukla 		return -ENODEV;
40002fd6c74SSantosh Shukla 
40102fd6c74SSantosh Shukla 	va_end = (uintptr_t)memva + memsz;
40202fd6c74SSantosh Shukla 	va_end &= ~RTE_CACHE_LINE_MASK;
40302fd6c74SSantosh Shukla 
40402fd6c74SSantosh Shukla 	/* VHPOOL setup */
40502fd6c74SSantosh Shukla 	fpavf_write64((uintptr_t)memva,
40602fd6c74SSantosh Shukla 			 (void *)((uintptr_t)handle +
40702fd6c74SSantosh Shukla 			 FPA_VF_VHPOOL_START_ADDR(gpool)));
40802fd6c74SSantosh Shukla 	fpavf_write64(va_end,
40902fd6c74SSantosh Shukla 			 (void *)((uintptr_t)handle +
41002fd6c74SSantosh Shukla 			 FPA_VF_VHPOOL_END_ADDR(gpool)));
41102fd6c74SSantosh Shukla 	return 0;
41202fd6c74SSantosh Shukla }
41302fd6c74SSantosh Shukla 
41402fd6c74SSantosh Shukla static int
41502fd6c74SSantosh Shukla octeontx_fpapf_start_count(uint16_t gpool_index)
41602fd6c74SSantosh Shukla {
41702fd6c74SSantosh Shukla 	int ret = 0;
41802fd6c74SSantosh Shukla 	struct octeontx_mbox_hdr hdr = {0};
41902fd6c74SSantosh Shukla 
42002fd6c74SSantosh Shukla 	if (gpool_index >= FPA_MAX_POOL) {
42102fd6c74SSantosh Shukla 		ret = -EINVAL;
42202fd6c74SSantosh Shukla 		goto err;
42302fd6c74SSantosh Shukla 	}
42402fd6c74SSantosh Shukla 
42502fd6c74SSantosh Shukla 	hdr.coproc = FPA_COPROC;
42602fd6c74SSantosh Shukla 	hdr.msg = FPA_START_COUNT;
42702fd6c74SSantosh Shukla 	hdr.vfid = gpool_index;
428d8dd3165SPavan Nikhilesh 	ret = octeontx_mbox_send(&hdr, NULL, 0, NULL, 0);
42902fd6c74SSantosh Shukla 	if (ret < 0) {
430f665790aSDavid Marchand 		fpavf_log_err("Could not start buffer counting for FPA pool %d. Err=%d. FuncErr=%d",
43102fd6c74SSantosh Shukla 			      gpool_index, ret, hdr.res_code);
43202fd6c74SSantosh Shukla 		ret = -EINVAL;
43302fd6c74SSantosh Shukla 		goto err;
43402fd6c74SSantosh Shukla 	}
43502fd6c74SSantosh Shukla 
43602fd6c74SSantosh Shukla err:
43702fd6c74SSantosh Shukla 	return ret;
43802fd6c74SSantosh Shukla }
43902fd6c74SSantosh Shukla 
44002fd6c74SSantosh Shukla static __rte_always_inline int
44102fd6c74SSantosh Shukla octeontx_fpavf_free(unsigned int gpool)
44202fd6c74SSantosh Shukla {
4439bc692f8SPavan Nikhilesh 	struct fpavf_res *res = octeontx_get_fpavf(gpool);
44402fd6c74SSantosh Shukla 	int ret = 0;
44502fd6c74SSantosh Shukla 
44602fd6c74SSantosh Shukla 	if (gpool >= FPA_MAX_POOL) {
44702fd6c74SSantosh Shukla 		ret = -EINVAL;
44802fd6c74SSantosh Shukla 		goto err;
44902fd6c74SSantosh Shukla 	}
45002fd6c74SSantosh Shukla 
45102fd6c74SSantosh Shukla 	/* Pool is free */
4529bc692f8SPavan Nikhilesh 	if (res != NULL)
4539bc692f8SPavan Nikhilesh 		res->is_inuse = false;
45402fd6c74SSantosh Shukla 
45502fd6c74SSantosh Shukla err:
45602fd6c74SSantosh Shukla 	return ret;
45702fd6c74SSantosh Shukla }
45802fd6c74SSantosh Shukla 
45902fd6c74SSantosh Shukla static __rte_always_inline int
46002fd6c74SSantosh Shukla octeontx_gpool_free(uint16_t gpool)
46102fd6c74SSantosh Shukla {
4629bc692f8SPavan Nikhilesh 	struct fpavf_res *res = octeontx_get_fpavf(gpool);
4639bc692f8SPavan Nikhilesh 
4649bc692f8SPavan Nikhilesh 	if (res && res->sz128 != 0) {
4659bc692f8SPavan Nikhilesh 		res->sz128 = 0;
46602fd6c74SSantosh Shukla 		return 0;
46702fd6c74SSantosh Shukla 	}
46802fd6c74SSantosh Shukla 	return -EINVAL;
46902fd6c74SSantosh Shukla }
47002fd6c74SSantosh Shukla 
47102fd6c74SSantosh Shukla /*
47202fd6c74SSantosh Shukla  * Return buffer size for a given pool
47302fd6c74SSantosh Shukla  */
47402fd6c74SSantosh Shukla int
47502fd6c74SSantosh Shukla octeontx_fpa_bufpool_block_size(uintptr_t handle)
47602fd6c74SSantosh Shukla {
47702fd6c74SSantosh Shukla 	struct fpavf_res *res = NULL;
47802fd6c74SSantosh Shukla 	uint8_t gpool;
47902fd6c74SSantosh Shukla 
48002fd6c74SSantosh Shukla 	if (unlikely(!octeontx_fpa_handle_valid(handle)))
48102fd6c74SSantosh Shukla 		return -EINVAL;
48202fd6c74SSantosh Shukla 
48302fd6c74SSantosh Shukla 	/* get the gpool */
48402fd6c74SSantosh Shukla 	gpool = octeontx_fpa_bufpool_gpool(handle);
4859bc692f8SPavan Nikhilesh 	res = octeontx_get_fpavf(gpool);
4869bc692f8SPavan Nikhilesh 	return res ? FPA_CACHE_LINE_2_OBJSZ(res->sz128) : 0;
48702fd6c74SSantosh Shukla }
48802fd6c74SSantosh Shukla 
489e48de68dSSantosh Shukla int
490e48de68dSSantosh Shukla octeontx_fpa_bufpool_free_count(uintptr_t handle)
491e48de68dSSantosh Shukla {
492e48de68dSSantosh Shukla 	uint64_t cnt, limit, avail;
493e48de68dSSantosh Shukla 	uint8_t gpool;
494179c7e89SPavan Nikhilesh 	uint16_t gaura;
495e48de68dSSantosh Shukla 	uintptr_t pool_bar;
496e48de68dSSantosh Shukla 
497e48de68dSSantosh Shukla 	if (unlikely(!octeontx_fpa_handle_valid(handle)))
498e48de68dSSantosh Shukla 		return -EINVAL;
499e48de68dSSantosh Shukla 
500e48de68dSSantosh Shukla 	/* get the gpool */
501e48de68dSSantosh Shukla 	gpool = octeontx_fpa_bufpool_gpool(handle);
502179c7e89SPavan Nikhilesh 	/* get the aura */
503179c7e89SPavan Nikhilesh 	gaura = octeontx_fpa_bufpool_gaura(handle);
504e48de68dSSantosh Shukla 
505e48de68dSSantosh Shukla 	/* Get pool bar address from handle */
506e48de68dSSantosh Shukla 	pool_bar = handle & ~(uint64_t)FPA_GPOOL_MASK;
507e48de68dSSantosh Shukla 
508e48de68dSSantosh Shukla 	cnt = fpavf_read64((void *)((uintptr_t)pool_bar +
509179c7e89SPavan Nikhilesh 				FPA_VF_VHAURA_CNT(gaura)));
510e48de68dSSantosh Shukla 	limit = fpavf_read64((void *)((uintptr_t)pool_bar +
511179c7e89SPavan Nikhilesh 				FPA_VF_VHAURA_CNT_LIMIT(gaura)));
512e48de68dSSantosh Shukla 
513e48de68dSSantosh Shukla 	avail = fpavf_read64((void *)((uintptr_t)pool_bar +
514e48de68dSSantosh Shukla 				FPA_VF_VHPOOL_AVAILABLE(gpool)));
515e48de68dSSantosh Shukla 
516e48de68dSSantosh Shukla 	return RTE_MIN(avail, (limit - cnt));
517e48de68dSSantosh Shukla }
518e48de68dSSantosh Shukla 
51902fd6c74SSantosh Shukla uintptr_t
52002fd6c74SSantosh Shukla octeontx_fpa_bufpool_create(unsigned int object_size, unsigned int object_count,
521f477a469SPavan Nikhilesh 				unsigned int buf_offset, int node_id)
52202fd6c74SSantosh Shukla {
52302fd6c74SSantosh Shukla 	unsigned int gpool;
524179c7e89SPavan Nikhilesh 	unsigned int gaura;
52502fd6c74SSantosh Shukla 	uintptr_t gpool_handle;
52602fd6c74SSantosh Shukla 	uintptr_t pool_bar;
52702fd6c74SSantosh Shukla 	int res;
52802fd6c74SSantosh Shukla 
52902fd6c74SSantosh Shukla 	RTE_SET_USED(node_id);
53050aa486cSJerin Jacob 	RTE_BUILD_BUG_ON(sizeof(struct rte_mbuf) > OCTEONTX_FPAVF_BUF_OFFSET);
53102fd6c74SSantosh Shukla 
532b4134b2dSPavan Nikhilesh 	octeontx_mbox_init();
53302fd6c74SSantosh Shukla 	object_size = RTE_CACHE_LINE_ROUNDUP(object_size);
53402fd6c74SSantosh Shukla 	if (object_size > FPA_MAX_OBJ_SIZE) {
53502fd6c74SSantosh Shukla 		errno = EINVAL;
53602fd6c74SSantosh Shukla 		goto error_end;
53702fd6c74SSantosh Shukla 	}
53802fd6c74SSantosh Shukla 
53902fd6c74SSantosh Shukla 	rte_spinlock_lock(&fpadev.lock);
54002fd6c74SSantosh Shukla 	res = octeontx_fpa_gpool_alloc(object_size);
54102fd6c74SSantosh Shukla 
54202fd6c74SSantosh Shukla 	/* Bail if failed */
54302fd6c74SSantosh Shukla 	if (unlikely(res < 0)) {
54402fd6c74SSantosh Shukla 		errno = res;
54502fd6c74SSantosh Shukla 		goto error_unlock;
54602fd6c74SSantosh Shukla 	}
54702fd6c74SSantosh Shukla 
54802fd6c74SSantosh Shukla 	/* get fpavf */
54902fd6c74SSantosh Shukla 	gpool = res;
55002fd6c74SSantosh Shukla 
55102fd6c74SSantosh Shukla 	/* get pool handle */
55202fd6c74SSantosh Shukla 	gpool_handle = octeontx_fpa_gpool2handle(gpool);
55302fd6c74SSantosh Shukla 	if (!octeontx_fpa_handle_valid(gpool_handle)) {
55402fd6c74SSantosh Shukla 		errno = ENOSPC;
55502fd6c74SSantosh Shukla 		goto error_gpool_free;
55602fd6c74SSantosh Shukla 	}
55702fd6c74SSantosh Shukla 
55802fd6c74SSantosh Shukla 	/* Get pool bar address from handle */
55902fd6c74SSantosh Shukla 	pool_bar = gpool_handle & ~(uint64_t)FPA_GPOOL_MASK;
56002fd6c74SSantosh Shukla 
56102fd6c74SSantosh Shukla 	res = octeontx_fpapf_pool_setup(gpool, object_size, buf_offset,
56202fd6c74SSantosh Shukla 					object_count);
56302fd6c74SSantosh Shukla 	if (res < 0) {
56402fd6c74SSantosh Shukla 		errno = res;
56502fd6c74SSantosh Shukla 		goto error_gpool_free;
56602fd6c74SSantosh Shukla 	}
56702fd6c74SSantosh Shukla 
56802fd6c74SSantosh Shukla 	/* populate AURA fields */
56902fd6c74SSantosh Shukla 	res = octeontx_fpapf_aura_attach(gpool);
57002fd6c74SSantosh Shukla 	if (res < 0) {
57102fd6c74SSantosh Shukla 		errno = res;
57202fd6c74SSantosh Shukla 		goto error_pool_destroy;
57302fd6c74SSantosh Shukla 	}
57402fd6c74SSantosh Shukla 
575179c7e89SPavan Nikhilesh 	gaura = FPA_AURA_IDX(gpool);
576179c7e89SPavan Nikhilesh 
57702fd6c74SSantosh Shukla 	/* Release lock */
57802fd6c74SSantosh Shukla 	rte_spinlock_unlock(&fpadev.lock);
57902fd6c74SSantosh Shukla 
58002fd6c74SSantosh Shukla 	/* populate AURA registers */
58102fd6c74SSantosh Shukla 	fpavf_write64(object_count, (void *)((uintptr_t)pool_bar +
582179c7e89SPavan Nikhilesh 			 FPA_VF_VHAURA_CNT(gaura)));
58302fd6c74SSantosh Shukla 	fpavf_write64(object_count, (void *)((uintptr_t)pool_bar +
584179c7e89SPavan Nikhilesh 			 FPA_VF_VHAURA_CNT_LIMIT(gaura)));
58502fd6c74SSantosh Shukla 	fpavf_write64(object_count + 1, (void *)((uintptr_t)pool_bar +
586179c7e89SPavan Nikhilesh 			 FPA_VF_VHAURA_CNT_THRESHOLD(gaura)));
58702fd6c74SSantosh Shukla 
58802fd6c74SSantosh Shukla 	octeontx_fpapf_start_count(gpool);
58902fd6c74SSantosh Shukla 
59002fd6c74SSantosh Shukla 	return gpool_handle;
59102fd6c74SSantosh Shukla 
59202fd6c74SSantosh Shukla error_pool_destroy:
59302fd6c74SSantosh Shukla 	octeontx_fpavf_free(gpool);
59402fd6c74SSantosh Shukla 	octeontx_fpapf_pool_destroy(gpool);
59502fd6c74SSantosh Shukla error_gpool_free:
59602fd6c74SSantosh Shukla 	octeontx_gpool_free(gpool);
59702fd6c74SSantosh Shukla error_unlock:
59802fd6c74SSantosh Shukla 	rte_spinlock_unlock(&fpadev.lock);
59902fd6c74SSantosh Shukla error_end:
60002fd6c74SSantosh Shukla 	return (uintptr_t)NULL;
60102fd6c74SSantosh Shukla }
60202fd6c74SSantosh Shukla 
603806714f1SSantosh Shukla /*
604806714f1SSantosh Shukla  * Destroy a buffer pool.
605806714f1SSantosh Shukla  */
606806714f1SSantosh Shukla int
607806714f1SSantosh Shukla octeontx_fpa_bufpool_destroy(uintptr_t handle, int node_id)
608806714f1SSantosh Shukla {
609806714f1SSantosh Shukla 	void **node, **curr, *head = NULL;
610806714f1SSantosh Shukla 	uint64_t sz;
611806714f1SSantosh Shukla 	uint64_t cnt, avail;
612806714f1SSantosh Shukla 	uint8_t gpool;
613179c7e89SPavan Nikhilesh 	uint16_t gaura;
614806714f1SSantosh Shukla 	uintptr_t pool_bar;
615806714f1SSantosh Shukla 	int ret;
616806714f1SSantosh Shukla 
617806714f1SSantosh Shukla 	RTE_SET_USED(node_id);
618806714f1SSantosh Shukla 
619806714f1SSantosh Shukla 	/* Wait for all outstanding writes to be committed */
620806714f1SSantosh Shukla 	rte_smp_wmb();
621806714f1SSantosh Shukla 
622806714f1SSantosh Shukla 	if (unlikely(!octeontx_fpa_handle_valid(handle)))
623806714f1SSantosh Shukla 		return -EINVAL;
624806714f1SSantosh Shukla 
625806714f1SSantosh Shukla 	/* get the pool */
626806714f1SSantosh Shukla 	gpool = octeontx_fpa_bufpool_gpool(handle);
627179c7e89SPavan Nikhilesh 	/* get the aura */
628179c7e89SPavan Nikhilesh 	gaura = octeontx_fpa_bufpool_gaura(handle);
629806714f1SSantosh Shukla 
630806714f1SSantosh Shukla 	/* Get pool bar address from handle */
631806714f1SSantosh Shukla 	pool_bar = handle & ~(uint64_t)FPA_GPOOL_MASK;
632806714f1SSantosh Shukla 
633806714f1SSantosh Shukla 	 /* Check for no outstanding buffers */
634806714f1SSantosh Shukla 	cnt = fpavf_read64((void *)((uintptr_t)pool_bar +
635179c7e89SPavan Nikhilesh 					FPA_VF_VHAURA_CNT(gaura)));
636806714f1SSantosh Shukla 	if (cnt) {
637f665790aSDavid Marchand 		fpavf_log_dbg("buffer exist in pool cnt %" PRId64, cnt);
638806714f1SSantosh Shukla 		return -EBUSY;
639806714f1SSantosh Shukla 	}
640806714f1SSantosh Shukla 
641806714f1SSantosh Shukla 	rte_spinlock_lock(&fpadev.lock);
642806714f1SSantosh Shukla 
643806714f1SSantosh Shukla 	avail = fpavf_read64((void *)((uintptr_t)pool_bar +
644806714f1SSantosh Shukla 				FPA_VF_VHPOOL_AVAILABLE(gpool)));
645806714f1SSantosh Shukla 
646806714f1SSantosh Shukla 	/* Prepare to empty the entire POOL */
647806714f1SSantosh Shukla 	fpavf_write64(avail, (void *)((uintptr_t)pool_bar +
648179c7e89SPavan Nikhilesh 			 FPA_VF_VHAURA_CNT_LIMIT(gaura)));
649806714f1SSantosh Shukla 	fpavf_write64(avail + 1, (void *)((uintptr_t)pool_bar +
650179c7e89SPavan Nikhilesh 			 FPA_VF_VHAURA_CNT_THRESHOLD(gaura)));
651806714f1SSantosh Shukla 
652806714f1SSantosh Shukla 	/* Empty the pool */
653806714f1SSantosh Shukla 	/* Invalidate the POOL */
654806714f1SSantosh Shukla 	octeontx_gpool_free(gpool);
655806714f1SSantosh Shukla 
656806714f1SSantosh Shukla 	/* Process all buffers in the pool */
657806714f1SSantosh Shukla 	while (avail--) {
658806714f1SSantosh Shukla 
659806714f1SSantosh Shukla 		/* Yank a buffer from the pool */
660806714f1SSantosh Shukla 		node = (void *)(uintptr_t)
661806714f1SSantosh Shukla 			fpavf_read64((void *)
662179c7e89SPavan Nikhilesh 				    (pool_bar + FPA_VF_VHAURA_OP_ALLOC(gaura)));
663806714f1SSantosh Shukla 
664806714f1SSantosh Shukla 		if (node == NULL) {
665f665790aSDavid Marchand 			fpavf_log_err("GAURA[%u] missing %" PRIx64 " buf",
666179c7e89SPavan Nikhilesh 				      gaura, avail);
667806714f1SSantosh Shukla 			break;
668806714f1SSantosh Shukla 		}
669806714f1SSantosh Shukla 
6707be78d02SJosh Soref 		/* Insert it into an ordered linked list */
671806714f1SSantosh Shukla 		for (curr = &head; curr[0] != NULL; curr = curr[0]) {
672806714f1SSantosh Shukla 			if ((uintptr_t)node <= (uintptr_t)curr[0])
673806714f1SSantosh Shukla 				break;
674806714f1SSantosh Shukla 		}
675806714f1SSantosh Shukla 		node[0] = curr[0];
676806714f1SSantosh Shukla 		curr[0] = node;
677806714f1SSantosh Shukla 	}
678806714f1SSantosh Shukla 
679806714f1SSantosh Shukla 	/* Verify the linked list to be a perfect series */
680806714f1SSantosh Shukla 	sz = octeontx_fpa_bufpool_block_size(handle) << 7;
681806714f1SSantosh Shukla 	for (curr = head; curr != NULL && curr[0] != NULL;
682806714f1SSantosh Shukla 		curr = curr[0]) {
683806714f1SSantosh Shukla 		if (curr == curr[0] ||
684806714f1SSantosh Shukla 			((uintptr_t)curr != ((uintptr_t)curr[0] - sz))) {
685f665790aSDavid Marchand 			fpavf_log_err("POOL# %u buf sequence err (%p vs. %p)",
686806714f1SSantosh Shukla 				      gpool, curr, curr[0]);
687806714f1SSantosh Shukla 		}
688806714f1SSantosh Shukla 	}
689806714f1SSantosh Shukla 
690806714f1SSantosh Shukla 	/* Disable pool operation */
691806714f1SSantosh Shukla 	fpavf_write64(~0ul, (void *)((uintptr_t)pool_bar +
692806714f1SSantosh Shukla 			 FPA_VF_VHPOOL_START_ADDR(gpool)));
693806714f1SSantosh Shukla 	fpavf_write64(~0ul, (void *)((uintptr_t)pool_bar +
694806714f1SSantosh Shukla 			FPA_VF_VHPOOL_END_ADDR(gpool)));
695806714f1SSantosh Shukla 
696806714f1SSantosh Shukla 	(void)octeontx_fpapf_pool_destroy(gpool);
697806714f1SSantosh Shukla 
698806714f1SSantosh Shukla 	/* Deactivate the AURA */
699806714f1SSantosh Shukla 	fpavf_write64(0, (void *)((uintptr_t)pool_bar +
700179c7e89SPavan Nikhilesh 			FPA_VF_VHAURA_CNT_LIMIT(gaura)));
701806714f1SSantosh Shukla 	fpavf_write64(0, (void *)((uintptr_t)pool_bar +
702179c7e89SPavan Nikhilesh 			FPA_VF_VHAURA_CNT_THRESHOLD(gaura)));
703806714f1SSantosh Shukla 
704806714f1SSantosh Shukla 	ret = octeontx_fpapf_aura_detach(gpool);
705806714f1SSantosh Shukla 	if (ret) {
706f665790aSDavid Marchand 		fpavf_log_err("Failed to detach gaura %u. error code=%d",
707806714f1SSantosh Shukla 			      gpool, ret);
708806714f1SSantosh Shukla 	}
709806714f1SSantosh Shukla 
710806714f1SSantosh Shukla 	/* Free VF */
711806714f1SSantosh Shukla 	(void)octeontx_fpavf_free(gpool);
712806714f1SSantosh Shukla 
713806714f1SSantosh Shukla 	rte_spinlock_unlock(&fpadev.lock);
714806714f1SSantosh Shukla 	return 0;
715806714f1SSantosh Shukla }
716806714f1SSantosh Shukla 
7171c842786SSantosh Shukla static void
7181c842786SSantosh Shukla octeontx_fpavf_setup(void)
7191c842786SSantosh Shukla {
7201c842786SSantosh Shukla 	uint8_t i;
7211c842786SSantosh Shukla 	static bool init_once;
7221c842786SSantosh Shukla 
7231c842786SSantosh Shukla 	if (!init_once) {
7241c842786SSantosh Shukla 		rte_spinlock_init(&fpadev.lock);
7251c842786SSantosh Shukla 		fpadev.total_gpool_cnt = 0;
7261c842786SSantosh Shukla 
7271c842786SSantosh Shukla 		for (i = 0; i < FPA_VF_MAX; i++) {
7281c842786SSantosh Shukla 
7291c842786SSantosh Shukla 			fpadev.pool[i].domain_id = ~0;
7301c842786SSantosh Shukla 			fpadev.pool[i].stack_ln_ptr = 0;
7311c842786SSantosh Shukla 			fpadev.pool[i].sz128 = 0;
7321c842786SSantosh Shukla 			fpadev.pool[i].bar0 = NULL;
7331c842786SSantosh Shukla 			fpadev.pool[i].pool_stack_base = NULL;
7341c842786SSantosh Shukla 			fpadev.pool[i].is_inuse = false;
7351c842786SSantosh Shukla 		}
7361c842786SSantosh Shukla 		init_once = 1;
7371c842786SSantosh Shukla 	}
7381c842786SSantosh Shukla }
7391c842786SSantosh Shukla 
7401c842786SSantosh Shukla static int
7411c842786SSantosh Shukla octeontx_fpavf_identify(void *bar0)
7421c842786SSantosh Shukla {
7431c842786SSantosh Shukla 	uint64_t val;
7441c842786SSantosh Shukla 	uint16_t domain_id;
7451c842786SSantosh Shukla 	uint16_t vf_id;
7461c842786SSantosh Shukla 	uint64_t stack_ln_ptr;
7479bc692f8SPavan Nikhilesh 	static uint16_t vf_idx;
7481c842786SSantosh Shukla 
7491c842786SSantosh Shukla 	val = fpavf_read64((void *)((uintptr_t)bar0 +
7501c842786SSantosh Shukla 				FPA_VF_VHAURA_CNT_THRESHOLD(0)));
7511c842786SSantosh Shukla 
7521c842786SSantosh Shukla 	domain_id = (val >> 8) & 0xffff;
7531c842786SSantosh Shukla 	vf_id = (val >> 24) & 0xffff;
7541c842786SSantosh Shukla 
7551c842786SSantosh Shukla 	stack_ln_ptr = fpavf_read64((void *)((uintptr_t)bar0 +
7561c842786SSantosh Shukla 					FPA_VF_VHPOOL_THRESHOLD(0)));
7579bc692f8SPavan Nikhilesh 	if (vf_idx >= FPA_VF_MAX) {
758f665790aSDavid Marchand 		fpavf_log_err("vf_id(%d) greater than max vf (32)", vf_id);
7599bc692f8SPavan Nikhilesh 		return -E2BIG;
7601c842786SSantosh Shukla 	}
7611c842786SSantosh Shukla 
7629bc692f8SPavan Nikhilesh 	fpadev.pool[vf_idx].domain_id = domain_id;
7639bc692f8SPavan Nikhilesh 	fpadev.pool[vf_idx].vf_id = vf_id;
7649bc692f8SPavan Nikhilesh 	fpadev.pool[vf_idx].bar0 = bar0;
7659bc692f8SPavan Nikhilesh 	fpadev.pool[vf_idx].stack_ln_ptr = stack_ln_ptr;
7661c842786SSantosh Shukla 
7671c842786SSantosh Shukla 	/* SUCCESS */
7689bc692f8SPavan Nikhilesh 	return vf_idx++;
7691c842786SSantosh Shukla }
7701c842786SSantosh Shukla 
7711c842786SSantosh Shukla /* FPAVF pcie device aka mempool probe */
7721c842786SSantosh Shukla static int
7731c842786SSantosh Shukla fpavf_probe(struct rte_pci_driver *pci_drv, struct rte_pci_device *pci_dev)
7741c842786SSantosh Shukla {
7751c842786SSantosh Shukla 	uint8_t *idreg;
7761c842786SSantosh Shukla 	int res;
777ca5aeab3SPablo de Lara 	struct fpavf_res *fpa = NULL;
7781c842786SSantosh Shukla 
7791c842786SSantosh Shukla 	RTE_SET_USED(pci_drv);
7801c842786SSantosh Shukla 	RTE_SET_USED(fpa);
7811c842786SSantosh Shukla 
7821c842786SSantosh Shukla 	/* For secondary processes, the primary has done all the work */
7831c842786SSantosh Shukla 	if (rte_eal_process_type() != RTE_PROC_PRIMARY)
7841c842786SSantosh Shukla 		return 0;
7851c842786SSantosh Shukla 
7861c842786SSantosh Shukla 	if (pci_dev->mem_resource[0].addr == NULL) {
7871c842786SSantosh Shukla 		fpavf_log_err("Empty bars %p ", pci_dev->mem_resource[0].addr);
7881c842786SSantosh Shukla 		return -ENODEV;
7891c842786SSantosh Shukla 	}
7901c842786SSantosh Shukla 	idreg = pci_dev->mem_resource[0].addr;
7911c842786SSantosh Shukla 
7921c842786SSantosh Shukla 	octeontx_fpavf_setup();
7931c842786SSantosh Shukla 
7941c842786SSantosh Shukla 	res = octeontx_fpavf_identify(idreg);
7951c842786SSantosh Shukla 	if (res < 0)
7961c842786SSantosh Shukla 		return -1;
7971c842786SSantosh Shukla 
7981c842786SSantosh Shukla 	fpa = &fpadev.pool[res];
7991c842786SSantosh Shukla 	fpadev.total_gpool_cnt++;
8001c842786SSantosh Shukla 	rte_wmb();
8011c842786SSantosh Shukla 
8021c842786SSantosh Shukla 	fpavf_log_dbg("total_fpavfs %d bar0 %p domain %d vf %d stk_ln_ptr 0x%x",
8031c842786SSantosh Shukla 		       fpadev.total_gpool_cnt, fpa->bar0, fpa->domain_id,
8041c842786SSantosh Shukla 		       fpa->vf_id, (unsigned int)fpa->stack_ln_ptr);
8051c842786SSantosh Shukla 
8061c842786SSantosh Shukla 	return 0;
8071c842786SSantosh Shukla }
8081c842786SSantosh Shukla 
8091c842786SSantosh Shukla static const struct rte_pci_id pci_fpavf_map[] = {
8101c842786SSantosh Shukla 	{
8111c842786SSantosh Shukla 		RTE_PCI_DEVICE(PCI_VENDOR_ID_CAVIUM,
8121c842786SSantosh Shukla 				PCI_DEVICE_ID_OCTEONTX_FPA_VF)
8131c842786SSantosh Shukla 	},
8141c842786SSantosh Shukla 	{
8151c842786SSantosh Shukla 		.vendor_id = 0,
8161c842786SSantosh Shukla 	},
8171c842786SSantosh Shukla };
8181c842786SSantosh Shukla 
8191c842786SSantosh Shukla static struct rte_pci_driver pci_fpavf = {
8201c842786SSantosh Shukla 	.id_table = pci_fpavf_map,
821d622cad8SJerin Jacob 	.drv_flags = RTE_PCI_DRV_NEED_MAPPING | RTE_PCI_DRV_NEED_IOVA_AS_VA,
8221c842786SSantosh Shukla 	.probe = fpavf_probe,
8231c842786SSantosh Shukla };
8241c842786SSantosh Shukla 
8251c842786SSantosh Shukla RTE_PMD_REGISTER_PCI(octeontx_fpavf, pci_fpavf);
826