From mboxrd@z Thu Jan  1 00:00:00 1970
Return-Path: <dev-bounces@dpdk.org>
Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124])
	by inbox.dpdk.org (Postfix) with ESMTP id B242643C3E;
	Sun,  3 Mar 2024 18:39:12 +0100 (CET)
Received: from mails.dpdk.org (localhost [127.0.0.1])
	by mails.dpdk.org (Postfix) with ESMTP id 9F27D43648;
	Sun,  3 Mar 2024 18:38:56 +0100 (CET)
Received: from mx0b-0016f401.pphosted.com (mx0b-0016f401.pphosted.com
 [67.231.156.173])
 by mails.dpdk.org (Postfix) with ESMTP id A9D2D43648
 for <dev@dpdk.org>; Sun,  3 Mar 2024 18:38:54 +0100 (CET)
Received: from pps.filterd (m0045851.ppops.net [127.0.0.1])
 by mx0b-0016f401.pphosted.com (8.17.1.24/8.17.1.24) with ESMTP id
 423EvbQq031413 for <dev@dpdk.org>; Sun, 3 Mar 2024 09:38:54 -0800
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=
 from:to:cc:subject:date:message-id:in-reply-to:references
 :mime-version:content-type; s=pfpt0220; bh=mjo/CH41g3xjrevHVO85T
 CO8YCf+5c6QU7Bahr9HAmA=; b=NvjTIxrvQBYRHFMkJQLZI7yQLPvwapclCTiuR
 sAuf2cuRPm0itKl72jUGvspb7mmy3qSsnr6BaLo2dTAHmacLNvDtQZX+L/d2Jf2S
 97FRnHz2M2EUABmebhgtLpmbqqBOxQ8J/EmQtJVA9tXrob/3qF4QlMoJO2iltfhU
 ShXKgI51YB/IZwYoC3BYr4V+E0LaFbVIEXY4suuXU32ydgHFi2v+kw4pzdiHq7sX
 SOFMrFpaiPV/uwzu1g4e/uOZduMX8UeTs9255WSEUXI/bS6f1Hf2Xn/KJ4FEH+Tx
 ZExzZsEvBB1m7kc1iqxobZkm812xPzf1R94Tbzo1JPgwxaHfg==
Received: from dc5-exch05.marvell.com ([199.233.59.128])
 by mx0b-0016f401.pphosted.com (PPS) with ESMTPS id 3wm4gmjjkb-1
 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT)
 for <dev@dpdk.org>; Sun, 03 Mar 2024 09:38:53 -0800 (PST)
Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH05.marvell.com
 (10.69.176.209) with Microsoft SMTP Server (version=TLS1_2,
 cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384) id 15.2.1258.12; Sun, 3 Mar
 2024 09:38:52 -0800
Received: from DC5-EXCH05.marvell.com (10.69.176.209) by
 DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id
 15.0.1497.48; Sun, 3 Mar 2024 09:38:49 -0800
Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH05.marvell.com
 (10.69.176.209) with Microsoft SMTP Server id 15.2.1258.12 via Frontend
 Transport; Sun, 3 Mar 2024 09:38:49 -0800
Received: from localhost.localdomain (unknown [10.29.52.211])
 by maili.marvell.com (Postfix) with ESMTP id 9CDAE3F718E;
 Sun,  3 Mar 2024 09:38:47 -0800 (PST)
From: Harman Kalra <hkalra@marvell.com>
To: Nithin Dabilpuram <ndabilpuram@marvell.com>, Kiran Kumar K
 <kirankumark@marvell.com>, Sunil Kumar Kori <skori@marvell.com>, Satha Rao
 <skoteshwar@marvell.com>, Harman Kalra <hkalra@marvell.com>
CC: <dev@dpdk.org>
Subject: [PATCH v6 04/23] net/cnxk: eswitch devargs parsing
Date: Sun, 3 Mar 2024 23:08:14 +0530
Message-ID: <20240303173833.100039-5-hkalra@marvell.com>
X-Mailer: git-send-email 2.18.0
In-Reply-To: <20240303173833.100039-1-hkalra@marvell.com>
References: <20230811163419.165790-1-hkalra@marvell.com>
 <20240303173833.100039-1-hkalra@marvell.com>
MIME-Version: 1.0
Content-Type: text/plain
X-Proofpoint-ORIG-GUID: 8jqMANhPrYHw4QGjiz3pNhbbsE8a3zHK
X-Proofpoint-GUID: 8jqMANhPrYHw4QGjiz3pNhbbsE8a3zHK
X-Proofpoint-Virus-Version: vendor=baseguard
 engine=ICAP:2.0.272,Aquarius:18.0.1011,Hydra:6.0.619,FMLib:17.11.176.26
 definitions=2024-03-03_08,2024-03-01_03,2023-05-22_02
X-BeenThere: dev@dpdk.org
X-Mailman-Version: 2.1.29
Precedence: list
List-Id: DPDK patches and discussions <dev.dpdk.org>
List-Unsubscribe: <https://mails.dpdk.org/options/dev>,
 <mailto:dev-request@dpdk.org?subject=unsubscribe>
List-Archive: <http://mails.dpdk.org/archives/dev/>
List-Post: <mailto:dev@dpdk.org>
List-Help: <mailto:dev-request@dpdk.org?subject=help>
List-Subscribe: <https://mails.dpdk.org/listinfo/dev>,
 <mailto:dev-request@dpdk.org?subject=subscribe>
Errors-To: dev-bounces@dpdk.org

Implementing the devargs parsing logic via which the representors
pattern is provided. These patterns define for which representies
representors shall be created.

Signed-off-by: Harman Kalra <hkalra@marvell.com>
---
 drivers/net/cnxk/cnxk_eswitch.c         |  88 +++++++++++++++++
 drivers/net/cnxk/cnxk_eswitch.h         |  52 ++++++++++
 drivers/net/cnxk/cnxk_eswitch_devargs.c | 124 ++++++++++++++++++++++++
 drivers/net/cnxk/meson.build            |   1 +
 4 files changed, 265 insertions(+)
 create mode 100644 drivers/net/cnxk/cnxk_eswitch_devargs.c

diff --git a/drivers/net/cnxk/cnxk_eswitch.c b/drivers/net/cnxk/cnxk_eswitch.c
index 810e7c9c25..687bb7d146 100644
--- a/drivers/net/cnxk/cnxk_eswitch.c
+++ b/drivers/net/cnxk/cnxk_eswitch.c
@@ -388,6 +388,7 @@ nix_lf_setup(struct cnxk_eswitch_dev *eswitch_dev)
 		plt_err("Failed to get rep cnt, rc=%d(%s)", rc, roc_error_msg_get(rc));
 		goto free_cqs;
 	}
+	eswitch_dev->repr_cnt.max_repr = eswitch_dev->nix.rep_cnt;
 
 	/* Allocating an NIX LF */
 	nb_rxq = CNXK_ESWITCH_MAX_RXQ;
@@ -525,11 +526,73 @@ eswitch_hw_rsrc_setup(struct cnxk_eswitch_dev *eswitch_dev, struct rte_pci_devic
 	return rc;
 }
 
+int
+cnxk_eswitch_representor_info_get(struct cnxk_eswitch_dev *eswitch_dev,
+				  struct rte_eth_representor_info *info)
+{
+	struct cnxk_eswitch_devargs *esw_da;
+	int rc = 0, n_entries, i, j = 0, k = 0;
+
+	for (i = 0; i < eswitch_dev->nb_esw_da; i++) {
+		for (j = 0; j < eswitch_dev->esw_da[i].nb_repr_ports; j++)
+			k++;
+	}
+	n_entries = k;
+
+	if (info == NULL)
+		goto out;
+
+	if ((uint32_t)n_entries > info->nb_ranges_alloc)
+		n_entries = info->nb_ranges_alloc;
+
+	k = 0;
+	info->controller = 0;
+	info->pf = 0;
+	for (i = 0; i < eswitch_dev->nb_esw_da; i++) {
+		esw_da = &eswitch_dev->esw_da[i];
+		info->ranges[k].type = esw_da->da.type;
+		switch (esw_da->da.type) {
+		case RTE_ETH_REPRESENTOR_PF:
+			info->ranges[k].controller = 0;
+			info->ranges[k].pf = esw_da->repr_hw_info[0].pfvf;
+			info->ranges[k].vf = 0;
+			info->ranges[k].id_base = info->ranges[i].pf;
+			info->ranges[k].id_end = info->ranges[i].pf;
+			snprintf(info->ranges[k].name, sizeof(info->ranges[k].name), "pf%d",
+				 info->ranges[k].pf);
+			k++;
+			break;
+		case RTE_ETH_REPRESENTOR_VF:
+			for (j = 0; j < esw_da->nb_repr_ports; j++) {
+				info->ranges[k].controller = 0;
+				info->ranges[k].pf = esw_da->da.ports[0];
+				info->ranges[k].vf = esw_da->repr_hw_info[j].pfvf;
+				info->ranges[k].id_base = esw_da->repr_hw_info[j].port_id;
+				info->ranges[k].id_end = esw_da->repr_hw_info[j].port_id;
+				snprintf(info->ranges[k].name, sizeof(info->ranges[k].name),
+					 "pf%dvf%d", info->ranges[k].pf, info->ranges[k].vf);
+				k++;
+			}
+			break;
+		default:
+			plt_err("Invalid type %d", esw_da->da.type);
+			rc = 0;
+			goto fail;
+		};
+	}
+	info->nb_ranges = k;
+fail:
+	return rc;
+out:
+	return n_entries;
+}
+
 static int
 cnxk_eswitch_dev_probe(struct rte_pci_driver *pci_drv, struct rte_pci_device *pci_dev)
 {
 	struct cnxk_eswitch_dev *eswitch_dev;
 	const struct rte_memzone *mz = NULL;
+	uint16_t num_reps;
 	int rc = -ENOMEM;
 
 	RTE_SET_USED(pci_drv);
@@ -562,12 +625,37 @@ cnxk_eswitch_dev_probe(struct rte_pci_driver *pci_drv, struct rte_pci_device *pc
 		}
 	}
 
+	if (pci_dev->device.devargs) {
+		rc = cnxk_eswitch_repr_devargs(pci_dev, eswitch_dev);
+		if (rc)
+			goto rsrc_cleanup;
+	}
+
+	if (eswitch_dev->repr_cnt.nb_repr_created > eswitch_dev->repr_cnt.max_repr) {
+		plt_err("Representors to be created %d can be greater than max allowed %d",
+			eswitch_dev->repr_cnt.nb_repr_created, eswitch_dev->repr_cnt.max_repr);
+		rc = -EINVAL;
+		goto rsrc_cleanup;
+	}
+
+	num_reps = eswitch_dev->repr_cnt.nb_repr_created;
+	if (!num_reps) {
+		plt_err("No representors enabled");
+		goto fail;
+	}
+
+	plt_esw_dbg("Max no of reps %d reps to be created %d Eswtch pfunc %x",
+		    eswitch_dev->repr_cnt.max_repr, eswitch_dev->repr_cnt.nb_repr_created,
+		    roc_nix_get_pf_func(&eswitch_dev->nix));
+
 	/* Spinlock for synchronization between representors traffic and control
 	 * messages
 	 */
 	rte_spinlock_init(&eswitch_dev->rep_lock);
 
 	return rc;
+rsrc_cleanup:
+	eswitch_hw_rsrc_cleanup(eswitch_dev, pci_dev);
 free_mem:
 	rte_memzone_free(mz);
 fail:
diff --git a/drivers/net/cnxk/cnxk_eswitch.h b/drivers/net/cnxk/cnxk_eswitch.h
index d1b4fa8761..6ff296399e 100644
--- a/drivers/net/cnxk/cnxk_eswitch.h
+++ b/drivers/net/cnxk/cnxk_eswitch.h
@@ -25,6 +25,47 @@
 #define CNXK_ESWITCH_QUEUE_STATE_STARTED    2
 #define CNXK_ESWITCH_QUEUE_STATE_STOPPED    3
 
+enum cnxk_esw_da_pattern_type {
+	CNXK_ESW_DA_TYPE_LIST = 0,
+	CNXK_ESW_DA_TYPE_PFVF,
+};
+
+struct cnxk_esw_repr_hw_info {
+	/* Representee pcifunc value */
+	uint16_t hw_func;
+	/* rep id in sync with kernel */
+	uint16_t rep_id;
+	/* pf or vf id */
+	uint16_t pfvf;
+	/* representor port id assigned to representee */
+	uint16_t port_id;
+};
+
+/* Structure representing per devarg information - this can be per representee
+ * or range of representee
+ */
+struct cnxk_eswitch_devargs {
+	/* Devargs populated */
+	struct rte_eth_devargs da;
+	/* HW info of representee */
+	struct cnxk_esw_repr_hw_info *repr_hw_info;
+	/* No of representor ports */
+	uint16_t nb_repr_ports;
+	/* Devargs pattern type */
+	enum cnxk_esw_da_pattern_type type;
+};
+
+struct cnxk_eswitch_repr_cnt {
+	/* Max possible representors */
+	uint16_t max_repr;
+	/* Representors to be created as per devargs passed */
+	uint16_t nb_repr_created;
+	/* Representors probed successfully */
+	uint16_t nb_repr_probed;
+	/* Representors started representing a representee */
+	uint16_t nb_repr_started;
+};
+
 struct cnxk_rep_info {
 	struct rte_eth_dev *rep_eth_dev;
 };
@@ -70,6 +111,14 @@ struct cnxk_eswitch_dev {
 	uint16_t rep_cnt;
 	uint8_t configured;
 
+	/* Eswitch Representors Devargs */
+	uint16_t nb_esw_da;
+	uint16_t last_probed;
+	struct cnxk_eswitch_devargs esw_da[RTE_MAX_ETHPORTS];
+
+	/* No of representors */
+	struct cnxk_eswitch_repr_cnt repr_cnt;
+
 	/* Port representor fields */
 	rte_spinlock_t rep_lock;
 	uint16_t switch_domain_id;
@@ -90,6 +139,9 @@ cnxk_eswitch_pmd_priv(void)
 }
 
 int cnxk_eswitch_nix_rsrc_start(struct cnxk_eswitch_dev *eswitch_dev);
+int cnxk_eswitch_repr_devargs(struct rte_pci_device *pci_dev, struct cnxk_eswitch_dev *eswitch_dev);
+int cnxk_eswitch_representor_info_get(struct cnxk_eswitch_dev *eswitch_dev,
+				      struct rte_eth_representor_info *info);
 int cnxk_eswitch_txq_setup(struct cnxk_eswitch_dev *eswitch_dev, uint16_t qid, uint16_t nb_desc,
 			   const struct rte_eth_txconf *tx_conf);
 int cnxk_eswitch_txq_release(struct cnxk_eswitch_dev *eswitch_dev, uint16_t qid);
diff --git a/drivers/net/cnxk/cnxk_eswitch_devargs.c b/drivers/net/cnxk/cnxk_eswitch_devargs.c
new file mode 100644
index 0000000000..58383fb835
--- /dev/null
+++ b/drivers/net/cnxk/cnxk_eswitch_devargs.c
@@ -0,0 +1,124 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright(C) 2024 Marvell.
+ */
+
+#include <cnxk_eswitch.h>
+
+#define PF_SHIFT 10
+static inline int
+get_hw_func(uint16_t pf, uint16_t vf)
+{
+	return (pf << PF_SHIFT) | vf;
+}
+
+static int
+populate_repr_hw_info(struct cnxk_eswitch_dev *eswitch_dev, struct rte_eth_devargs *eth_da,
+		      uint16_t idx)
+{
+	struct cnxk_eswitch_devargs *esw_da = &eswitch_dev->esw_da[idx];
+	uint16_t nb_repr_ports, hw_func;
+	int rc, i, j;
+
+	if (eth_da->type == RTE_ETH_REPRESENTOR_NONE) {
+		plt_err("No representor type found");
+		return -EINVAL;
+	}
+
+	if (eth_da->type != RTE_ETH_REPRESENTOR_VF && eth_da->type != RTE_ETH_REPRESENTOR_PF &&
+	    eth_da->type != RTE_ETH_REPRESENTOR_SF) {
+		plt_err("unsupported representor type %d\n", eth_da->type);
+		return -ENOTSUP;
+	}
+
+	nb_repr_ports = (eth_da->type == RTE_ETH_REPRESENTOR_PF) ? eth_da->nb_ports :
+								   eth_da->nb_representor_ports;
+	esw_da->nb_repr_ports = nb_repr_ports;
+	/* If plain list is provided as representor pattern */
+	if (eth_da->nb_ports == 0)
+		return 0;
+
+	esw_da->repr_hw_info = plt_zmalloc(nb_repr_ports * sizeof(struct cnxk_esw_repr_hw_info), 0);
+	if (!esw_da->repr_hw_info) {
+		plt_err("Failed to allocate memory");
+		rc = -ENOMEM;
+		goto fail;
+	}
+
+	plt_esw_dbg("Representor param %d has %d pfvf", idx, nb_repr_ports);
+	/* Check if representor can be created for PFVF and populating HW func list */
+	for (i = 0; i < nb_repr_ports; i++) {
+		if (eth_da->type == RTE_ETH_REPRESENTOR_PF)
+			hw_func = get_hw_func(eth_da->ports[i], 0);
+		else
+			hw_func = get_hw_func(eth_da->ports[0], eth_da->representor_ports[i] + 1);
+
+		for (j = 0; j < eswitch_dev->repr_cnt.max_repr; j++) {
+			if (eswitch_dev->nix.rep_pfvf_map[j] == hw_func)
+				break;
+		}
+
+		/* HW func which doesn not match the map table received from AF, no
+		 * representor port is assigned.
+		 */
+		if (j == eswitch_dev->repr_cnt.max_repr) {
+			plt_err("Representor port can't be created for PF%dVF%d", eth_da->ports[0],
+				eth_da->representor_ports[i]);
+			rc = -EINVAL;
+			goto fail;
+		}
+
+		esw_da->repr_hw_info[i].hw_func = hw_func;
+		esw_da->repr_hw_info[i].rep_id = j;
+		esw_da->repr_hw_info[i].pfvf = (eth_da->type == RTE_ETH_REPRESENTOR_PF) ?
+						       eth_da->ports[0] :
+						       eth_da->representor_ports[i];
+		plt_esw_dbg("	HW func %x index %d type %d", hw_func, j, eth_da->type);
+	}
+
+	esw_da->type = CNXK_ESW_DA_TYPE_PFVF;
+
+	return 0;
+fail:
+	return rc;
+}
+
+int
+cnxk_eswitch_repr_devargs(struct rte_pci_device *pci_dev, struct cnxk_eswitch_dev *eswitch_dev)
+{
+	struct rte_devargs *devargs = pci_dev->device.devargs;
+	struct rte_eth_devargs eth_da[RTE_MAX_ETHPORTS];
+	int rc, i, j, count;
+
+	if (devargs == NULL) {
+		plt_err("No devargs passed");
+		rc = -EINVAL;
+		goto fail;
+	}
+
+	/* Parse devargs passed to ESW device */
+	rc = rte_eth_devargs_parse(devargs->args, eth_da, RTE_MAX_ETHPORTS);
+	if (rc < 0) {
+		plt_err("Failed to parse devargs, err %d", rc);
+		goto fail;
+	}
+
+	count = rc;
+	j = eswitch_dev->nb_esw_da;
+	for (i = 0; i < count; i++) {
+		rc = populate_repr_hw_info(eswitch_dev, &eth_da[i], j);
+		if (rc) {
+			plt_err("Failed to populate representer hw funcs, err %d", rc);
+			goto fail;
+		}
+
+		rte_memcpy(&eswitch_dev->esw_da[j].da, &eth_da[i], sizeof(struct rte_eth_devargs));
+		/* No of representor ports to be created */
+		eswitch_dev->repr_cnt.nb_repr_created += eswitch_dev->esw_da[j].nb_repr_ports;
+		j++;
+	}
+	eswitch_dev->nb_esw_da += count;
+
+	return 0;
+fail:
+	return rc;
+}
diff --git a/drivers/net/cnxk/meson.build b/drivers/net/cnxk/meson.build
index 012d098f80..ea7e363e89 100644
--- a/drivers/net/cnxk/meson.build
+++ b/drivers/net/cnxk/meson.build
@@ -29,6 +29,7 @@ sources = files(
         'cnxk_ethdev_telemetry.c',
         'cnxk_ethdev_sec_telemetry.c',
         'cnxk_eswitch.c',
+        'cnxk_eswitch_devargs.c',
         'cnxk_link.c',
         'cnxk_lookup.c',
         'cnxk_ptp.c',
-- 
2.18.0