From patchwork Mon Jan 15 15:57:15 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Harman Kalra X-Patchwork-Id: 135879 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 676FF438D2; Mon, 15 Jan 2024 16:57:45 +0100 (CET) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 44CBC4064E; Mon, 15 Jan 2024 16:57:45 +0100 (CET) Received: from mx0b-0016f401.pphosted.com (mx0b-0016f401.pphosted.com [67.231.156.173]) by mails.dpdk.org (Postfix) with ESMTP id 292FF402EB for ; Mon, 15 Jan 2024 16:57:43 +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 40F8l761023525; Mon, 15 Jan 2024 07:57:37 -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=Oxj9zYOmoUZr9MErOcvgJ 6dGD3eQoVFbUe11TzdKSyM=; b=Zr7QDpY4/ZHyISIEAV/HrGk6gqUofFcOsUWC1 GbzAEgdjgbKjEt1+5y+v7ysFz0d7AunsPF+RZaD+6MK+u3FWjpYwSdRTswiVBT5r 4EunY96EeReSW44XqRKwwBa4aefa5pUPPyu/Eei3RsdU/OTc8+usXq3yG6L00eeD GwzLcgLxQ4auZLK+hjFtHJkOfoS7o6QwtkFG10aq+iQuKdv20wqch7Vl0j7M1kD4 WfVseW/PlJatMwd+orrbeK4c6HpUxcwXsMDLi0GpRoaCbQ8kDkhbK/0hSJp7uTg4 Jx/EJTVvwUJmYkem6GOxcV9HG3kGMf0ITRPmx8sld9gXci1Aw== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0b-0016f401.pphosted.com (PPS) with ESMTPS id 3vn1gc19jx-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT); Mon, 15 Jan 2024 07:57:37 -0800 (PST) Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Mon, 15 Jan 2024 07:57:35 -0800 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Mon, 15 Jan 2024 07:57:35 -0800 Received: from localhost.localdomain (unknown [10.29.52.211]) by maili.marvell.com (Postfix) with ESMTP id 6D9F83F7065; Mon, 15 Jan 2024 07:57:29 -0800 (PST) From: Harman Kalra To: , Thomas Monjalon , Ferruh Yigit , Andrew Rybchenko , Ajit Khaparde , Somnath Kotur , John Daley , Hyong Youb Kim , Yuying Zhang , Beilei Xing , Qiming Yang , Qi Zhang , Wenjun Wu , Dariusz Sosnowski , Viacheslav Ovsiienko , "Ori Kam" , Suanming Mou , Matan Azrad , Chaoyong He CC: Harman Kalra Subject: [PATCH v2 1/1] ethdev: parsing multiple representor devargs string Date: Mon, 15 Jan 2024 21:27:15 +0530 Message-ID: <20240115155715.111154-2-hkalra@marvell.com> X-Mailer: git-send-email 2.18.0 In-Reply-To: <20240115155715.111154-1-hkalra@marvell.com> References: <20240111064432.193119-1-hkalra@marvell.com> <20240115155715.111154-1-hkalra@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: WINJA_Gd33sjGMxHHw3Z50sD_W1bJKw2 X-Proofpoint-GUID: WINJA_Gd33sjGMxHHw3Z50sD_W1bJKw2 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.272,Aquarius:18.0.997,Hydra:6.0.619,FMLib:17.11.176.26 definitions=2023-12-09_02,2023-12-07_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org Adding support for parsing multiple representor devargs strings passed to a PCI BDF. There may be scenario where port representors for various PFs or VFs under PFs are required and all these are representor ports shall be backed by single pci device. In such case port representors can be created using devargs string: ,representor=[pf[0-1],pf2vf[1,2-3],[4-5]] Signed-off-by: Harman Kalra --- doc/guides/prog_guide/poll_mode_drv.rst | 4 +- .../prog_guide/switch_representation.rst | 1 + drivers/net/bnxt/bnxt_ethdev.c | 4 +- drivers/net/enic/enic_ethdev.c | 4 +- drivers/net/i40e/i40e_ethdev.c | 4 +- drivers/net/ice/ice_dcf_ethdev.c | 4 +- drivers/net/ixgbe/ixgbe_ethdev.c | 4 +- drivers/net/mlx5/linux/mlx5_os.c | 8 +- .../net/nfp/flower/nfp_flower_representor.c | 4 +- drivers/net/sfc/sfc_ethdev.c | 4 +- lib/ethdev/ethdev_driver.c | 105 +++++++++++++++--- lib/ethdev/ethdev_driver.h | 9 +- 12 files changed, 119 insertions(+), 36 deletions(-) diff --git a/doc/guides/prog_guide/poll_mode_drv.rst b/doc/guides/prog_guide/poll_mode_drv.rst index c145a9066c..5008b41c60 100644 --- a/doc/guides/prog_guide/poll_mode_drv.rst +++ b/doc/guides/prog_guide/poll_mode_drv.rst @@ -376,7 +376,7 @@ parameters to those ports. * ``representor`` for a device which supports the creation of representor ports this argument allows user to specify which switch ports to enable port - representors for. Multiple representors in one device argument is invalid:: + representors for:: -a DBDF,representor=vf0 -a DBDF,representor=vf[0,4,6,9] @@ -389,6 +389,8 @@ parameters to those ports. -a DBDF,representor=pf1vf0 -a DBDF,representor=pf[0-1]sf[0-127] -a DBDF,representor=pf1 + -a DBDF,representor=[pf[0-1],pf2vf[0-2],pf3[3,5-8]] + (Multiple representors in one device argument can be represented as a list) Note: PMDs are not required to support the standard device arguments and users should consult the relevant PMD documentation to see support devargs. diff --git a/doc/guides/prog_guide/switch_representation.rst b/doc/guides/prog_guide/switch_representation.rst index 6fd7b98bdc..46e0ca85a5 100644 --- a/doc/guides/prog_guide/switch_representation.rst +++ b/doc/guides/prog_guide/switch_representation.rst @@ -77,6 +77,7 @@ thought as a software "patch panel" front-end for applications. -a pci:dbdf,representor=sf1 -a pci:dbdf,representor=sf[0-1023] -a pci:dbdf,representor=sf[0,2-1023] + -a pci:dbdf,representor=[pf[0-1],pf2vf[0-2],pf3[3,5]] - As virtual devices, they may be more limited than their physical counterparts, for instance by exposing only a subset of device diff --git a/drivers/net/bnxt/bnxt_ethdev.c b/drivers/net/bnxt/bnxt_ethdev.c index acf7e6e46e..5d4f599044 100644 --- a/drivers/net/bnxt/bnxt_ethdev.c +++ b/drivers/net/bnxt/bnxt_ethdev.c @@ -6383,8 +6383,8 @@ static int bnxt_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, if (pci_dev->device.devargs) { ret = rte_eth_devargs_parse(pci_dev->device.devargs->args, - ð_da); - if (ret) + ð_da, 1); + if (ret < 0) return ret; } diff --git a/drivers/net/enic/enic_ethdev.c b/drivers/net/enic/enic_ethdev.c index b04b6c9aa1..33d96ec07a 100644 --- a/drivers/net/enic/enic_ethdev.c +++ b/drivers/net/enic/enic_ethdev.c @@ -1317,8 +1317,8 @@ static int eth_enic_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, ENICPMD_FUNC_TRACE(); if (pci_dev->device.devargs) { retval = rte_eth_devargs_parse(pci_dev->device.devargs->args, - ð_da); - if (retval) + ð_da, 1); + if (retval < 0) return retval; } if (eth_da.nb_representor_ports > 0 && diff --git a/drivers/net/i40e/i40e_ethdev.c b/drivers/net/i40e/i40e_ethdev.c index 3ca226156b..4d21341382 100644 --- a/drivers/net/i40e/i40e_ethdev.c +++ b/drivers/net/i40e/i40e_ethdev.c @@ -646,8 +646,8 @@ eth_i40e_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, if (pci_dev->device.devargs) { retval = rte_eth_devargs_parse(pci_dev->device.devargs->args, - ð_da); - if (retval) + ð_da, 1); + if (retval < 0) return retval; } diff --git a/drivers/net/ice/ice_dcf_ethdev.c b/drivers/net/ice/ice_dcf_ethdev.c index 5d845bba31..0e991fe4b8 100644 --- a/drivers/net/ice/ice_dcf_ethdev.c +++ b/drivers/net/ice/ice_dcf_ethdev.c @@ -2041,8 +2041,8 @@ eth_ice_dcf_pci_probe(__rte_unused struct rte_pci_driver *pci_drv, if (!ice_devargs_check(pci_dev->device.devargs, ICE_DCF_DEVARG_CAP)) return 1; - ret = rte_eth_devargs_parse(pci_dev->device.devargs->args, ð_da); - if (ret) + ret = rte_eth_devargs_parse(pci_dev->device.devargs->args, ð_da, 1); + if (ret < 0) return ret; ret = rte_eth_dev_pci_generic_probe(pci_dev, diff --git a/drivers/net/ixgbe/ixgbe_ethdev.c b/drivers/net/ixgbe/ixgbe_ethdev.c index d6cf00317e..98e9b8a031 100644 --- a/drivers/net/ixgbe/ixgbe_ethdev.c +++ b/drivers/net/ixgbe/ixgbe_ethdev.c @@ -1765,8 +1765,8 @@ eth_ixgbe_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, if (pci_dev->device.devargs) { retval = rte_eth_devargs_parse(pci_dev->device.devargs->args, - ð_da); - if (retval) + ð_da, 1); + if (retval < 0) return retval; } else memset(ð_da, 0, sizeof(eth_da)); diff --git a/drivers/net/mlx5/linux/mlx5_os.c b/drivers/net/mlx5/linux/mlx5_os.c index ae82e1e5d8..17061126d5 100644 --- a/drivers/net/mlx5/linux/mlx5_os.c +++ b/drivers/net/mlx5/linux/mlx5_os.c @@ -2733,16 +2733,16 @@ mlx5_os_parse_eth_devargs(struct rte_device *dev, memset(eth_da, 0, sizeof(*eth_da)); /* Parse representor information first from class argument. */ if (dev->devargs->cls_str) - ret = rte_eth_devargs_parse(dev->devargs->cls_str, eth_da); - if (ret != 0) { + ret = rte_eth_devargs_parse(dev->devargs->cls_str, eth_da, 1); + if (ret < 0) { DRV_LOG(ERR, "failed to parse device arguments: %s", dev->devargs->cls_str); return -rte_errno; } if (eth_da->type == RTE_ETH_REPRESENTOR_NONE && dev->devargs->args) { /* Parse legacy device argument */ - ret = rte_eth_devargs_parse(dev->devargs->args, eth_da); - if (ret) { + ret = rte_eth_devargs_parse(dev->devargs->args, eth_da, 1); + if (ret < 0) { DRV_LOG(ERR, "failed to parse device arguments: %s", dev->devargs->args); return -rte_errno; diff --git a/drivers/net/nfp/flower/nfp_flower_representor.c b/drivers/net/nfp/flower/nfp_flower_representor.c index 5f7c1fa737..63fe37c8d7 100644 --- a/drivers/net/nfp/flower/nfp_flower_representor.c +++ b/drivers/net/nfp/flower/nfp_flower_representor.c @@ -792,8 +792,8 @@ nfp_flower_repr_create(struct nfp_app_fw_flower *app_fw_flower) /* Now parse PCI device args passed for representor info */ if (pci_dev->device.devargs != NULL) { - ret = rte_eth_devargs_parse(pci_dev->device.devargs->args, ð_da); - if (ret != 0) { + ret = rte_eth_devargs_parse(pci_dev->device.devargs->args, ð_da, 1); + if (ret < 0) { PMD_INIT_LOG(ERR, "devarg parse failed"); return -EINVAL; } diff --git a/drivers/net/sfc/sfc_ethdev.c b/drivers/net/sfc/sfc_ethdev.c index 6d57b2ba26..0bbcb80365 100644 --- a/drivers/net/sfc/sfc_ethdev.c +++ b/drivers/net/sfc/sfc_ethdev.c @@ -3305,8 +3305,8 @@ sfc_parse_rte_devargs(const char *args, struct rte_eth_devargs *devargs) int rc; if (args != NULL) { - rc = rte_eth_devargs_parse(args, ð_da); - if (rc != 0) { + rc = rte_eth_devargs_parse(args, ð_da, 1); + if (rc < 0) { SFC_GENERIC_LOG(ERR, "Failed to parse generic devargs '%s'", args); diff --git a/lib/ethdev/ethdev_driver.c b/lib/ethdev/ethdev_driver.c index bd917a15fc..208252f6c5 100644 --- a/lib/ethdev/ethdev_driver.c +++ b/lib/ethdev/ethdev_driver.c @@ -2,6 +2,7 @@ * Copyright(c) 2022 Intel Corporation */ +#include #include #include @@ -459,9 +460,23 @@ eth_dev_devargs_tokenise(struct rte_kvargs *arglist, const char *str_in) break; case 3: /* Parsing list */ - if (*letter == ']') - state = 2; - else if (*letter == '\0') + if (*letter == ']') { + /* Multiple representor case has ']' dual meaning, first end of + * individual pfvf list and other end of consolidated list of + * representors. + * Complete multiple representors list to be considered as one + * pair value. + */ + if ((strcmp("representor", pair->key) == 0) && + ((*(letter + 2) == 'p' && *(letter + 3) == 'f') || + (*(letter + 2) == 'v' && *(letter + 3) == 'f') || + (*(letter + 2) == 's' && *(letter + 3) == 'f') || + (*(letter + 2) == 'c' && isdigit(*(letter + 3))) || + (*(letter + 2) == '[' && isdigit(*(letter + 3))))) + state = 3; + else + state = 2; + } else if (*letter == '\0') return -EINVAL; break; } @@ -469,16 +484,56 @@ eth_dev_devargs_tokenise(struct rte_kvargs *arglist, const char *str_in) } } +static int +eth_dev_tokenise_representor_list(char *p_val, struct rte_eth_devargs *eth_devargs, + uint8_t nb_da) +{ + struct rte_eth_devargs *eth_da; + char da_val[BUFSIZ]; + char delim[] = "]"; + int devargs = 0; + int result = 0; + char *token; + + token = strtok(&p_val[1], delim); + while (token != NULL) { + eth_da = ð_devargs[devargs]; + memset(eth_da, 0, sizeof(*eth_da)); + snprintf(da_val, BUFSIZ, "%s%c", (token[0] == ',') ? ++token : token, ']'); + /* Parse the tokenised devarg value */ + result = rte_eth_devargs_parse_representor_ports(da_val, eth_da); + if (result < 0) + goto parse_cleanup; + devargs++; + if (devargs > nb_da) { + RTE_ETHDEV_LOG_LINE(ERR, + "Devargs parsed %d > max array size %d", + devargs, nb_da); + result = -1; + goto parse_cleanup; + } + token = strtok(NULL, delim); + } + + result = devargs; + +parse_cleanup: + return result; + +} + int -rte_eth_devargs_parse(const char *dargs, struct rte_eth_devargs *eth_da) +rte_eth_devargs_parse(const char *dargs, struct rte_eth_devargs *eth_devargs, + uint8_t nb_da) { - struct rte_kvargs args; + struct rte_eth_devargs *eth_da; struct rte_kvargs_pair *pair; + struct rte_kvargs args; + static bool dup_rep; + int devargs = 0; unsigned int i; int result = 0; - memset(eth_da, 0, sizeof(*eth_da)); - result = eth_dev_devargs_tokenise(&args, dargs); if (result < 0) goto parse_cleanup; @@ -486,18 +541,40 @@ rte_eth_devargs_parse(const char *dargs, struct rte_eth_devargs *eth_da) for (i = 0; i < args.count; i++) { pair = &args.pairs[i]; if (strcmp("representor", pair->key) == 0) { - if (eth_da->type != RTE_ETH_REPRESENTOR_NONE) { - RTE_ETHDEV_LOG_LINE(ERR, "duplicated representor key: %s", - dargs); + if (dup_rep) { + RTE_ETHDEV_LOG_LINE(ERR, "Duplicated representor key: %s", + pair->value); result = -1; goto parse_cleanup; } - result = rte_eth_devargs_parse_representor_ports( - pair->value, eth_da); - if (result < 0) - goto parse_cleanup; + + if (pair->value[0] == '[' && !isdigit(pair->value[1])) { + /* Multiple representor list case */ + devargs = eth_dev_tokenise_representor_list(pair->value, + eth_devargs, nb_da); + if (devargs < 0) + goto parse_cleanup; + } else { + /* Single representor case */ + eth_da = ð_devargs[devargs]; + memset(eth_da, 0, sizeof(*eth_da)); + result = + rte_eth_devargs_parse_representor_ports(pair->value, + eth_da); + if (result < 0) + goto parse_cleanup; + devargs++; + if (devargs > nb_da) { + RTE_ETHDEV_LOG_LINE(ERR, "Devargs parsed %d > max array size %d", + devargs, nb_da); + result = -1; + goto parse_cleanup; + } + } + dup_rep = true; } } + result = devargs; parse_cleanup: free(args.str); diff --git a/lib/ethdev/ethdev_driver.h b/lib/ethdev/ethdev_driver.h index b482cd12bb..e4b99448dd 100644 --- a/lib/ethdev/ethdev_driver.h +++ b/lib/ethdev/ethdev_driver.h @@ -1800,14 +1800,17 @@ rte_eth_representor_id_get(uint16_t port_id, * @param devargs * device arguments * @param eth_devargs - * parsed ethdev specific arguments. + * contiguous memory populated with parsed ethdev specific arguments. + * @param nb_da + * size of eth_devargs array passed * * @return - * Negative errno value on error, 0 on success. + * Negative errno value on error, no of devargs parsed on success. */ __rte_internal int -rte_eth_devargs_parse(const char *devargs, struct rte_eth_devargs *eth_devargs); +rte_eth_devargs_parse(const char *devargs, struct rte_eth_devargs *eth_devargs, + uint8_t nb_da); typedef int (*ethdev_init_t)(struct rte_eth_dev *ethdev, void *init_params);