From patchwork Thu Aug 4 16:58:19 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Dumitrescu X-Patchwork-Id: 114625 X-Patchwork-Delegate: andrew.rybchenko@oktetlabs.ru 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 B70B7A00C4; Thu, 4 Aug 2022 18:59:06 +0200 (CEST) Received: from [217.70.189.124] (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id E7F0E42BF9; Thu, 4 Aug 2022 18:58:56 +0200 (CEST) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by mails.dpdk.org (Postfix) with ESMTP id A52994282B for ; Thu, 4 Aug 2022 18:58:52 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1659632332; x=1691168332; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=/BqxQgBetOpiQK9lC+vS8pGlGe8LHY9HOxktHgXjS74=; b=O5tQgKiDU2sL7nbhHCoNb3bRxAZ9MPPywCzlv0jIdneCaFr/YeC9MCc1 b9jOPdTZbw+YgCNfgog7TatBH+FmHX32ENkCMeTNEznoqG3+Qv/zwCBL8 qVHIqC/YSxMe+o6oR2MSnxo5xthzfg9QMLx9lHUkI8N5ir8zE3iTciaZq FUU62iTS0FtdcKNN+9wYZKptsiKDyqRazGqH6emTWZg2rlWZOrRd1a1xM M3WDP32mioZZUzo/+uWNOAaepPg8TwAJoaO/iqHBM0AxNgaP5egDYOzhM 93+muPb1G/CllgABLzxtEyi6exT3vT2wZEwyKcVf1yT/NHh2shWdoA8JZ w==; X-IronPort-AV: E=McAfee;i="6400,9594,10429"; a="290000083" X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="290000083" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 04 Aug 2022 09:58:44 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="636163068" Received: from silpixa00400573.ir.intel.com (HELO silpixa00400573.ger.corp.intel.com) ([10.237.223.157]) by orsmga001.jf.intel.com with ESMTP; 04 Aug 2022 09:58:41 -0700 From: Cristian Dumitrescu To: dev@dpdk.org Cc: jasvinder.singh@intel.com, yogesh.jangra@intel.com Subject: [PATCH 01/21] net/softnic: remove the traffic manager support Date: Thu, 4 Aug 2022 16:58:19 +0000 Message-Id: <20220804165839.1074817-2-cristian.dumitrescu@intel.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> References: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> MIME-Version: 1.0 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 Remove the Ethernet device traffic manager API support. Signed-off-by: Cristian Dumitrescu Signed-off-by: Yogesh Jangra --- drivers/net/softnic/meson.build | 3 +- drivers/net/softnic/rte_eth_softnic.c | 170 - drivers/net/softnic/rte_eth_softnic.h | 10 - drivers/net/softnic/rte_eth_softnic_cli.c | 1328 ------ .../net/softnic/rte_eth_softnic_internals.h | 176 - .../net/softnic/rte_eth_softnic_pipeline.c | 31 - drivers/net/softnic/rte_eth_softnic_tm.c | 3657 ----------------- 7 files changed, 1 insertion(+), 5374 deletions(-) delete mode 100644 drivers/net/softnic/rte_eth_softnic_tm.c diff --git a/drivers/net/softnic/meson.build b/drivers/net/softnic/meson.build index aff5fb3bf2..e2dbd6166e 100644 --- a/drivers/net/softnic/meson.build +++ b/drivers/net/softnic/meson.build @@ -21,6 +21,5 @@ sources = files( 'rte_eth_softnic_swq.c', 'rte_eth_softnic_tap.c', 'rte_eth_softnic_thread.c', - 'rte_eth_softnic_tm.c', ) -deps += ['pipeline', 'port', 'table', 'sched', 'cryptodev'] +deps += ['pipeline', 'port', 'table', 'cryptodev'] diff --git a/drivers/net/softnic/rte_eth_softnic.c b/drivers/net/softnic/rte_eth_softnic.c index 8c098cad5b..ae3e8b3bcd 100644 --- a/drivers/net/softnic/rte_eth_softnic.c +++ b/drivers/net/softnic/rte_eth_softnic.c @@ -13,7 +13,6 @@ #include #include #include -#include #include #include "rte_eth_softnic.h" @@ -23,20 +22,6 @@ #define PMD_PARAM_CONN_PORT "conn_port" #define PMD_PARAM_CPU_ID "cpu_id" #define PMD_PARAM_SC "sc" -#define PMD_PARAM_TM_N_QUEUES "tm_n_queues" -#define PMD_PARAM_TM_QSIZE0 "tm_qsize0" -#define PMD_PARAM_TM_QSIZE1 "tm_qsize1" -#define PMD_PARAM_TM_QSIZE2 "tm_qsize2" -#define PMD_PARAM_TM_QSIZE3 "tm_qsize3" -#define PMD_PARAM_TM_QSIZE4 "tm_qsize4" -#define PMD_PARAM_TM_QSIZE5 "tm_qsize5" -#define PMD_PARAM_TM_QSIZE6 "tm_qsize6" -#define PMD_PARAM_TM_QSIZE7 "tm_qsize7" -#define PMD_PARAM_TM_QSIZE8 "tm_qsize8" -#define PMD_PARAM_TM_QSIZE9 "tm_qsize9" -#define PMD_PARAM_TM_QSIZE10 "tm_qsize10" -#define PMD_PARAM_TM_QSIZE11 "tm_qsize11" -#define PMD_PARAM_TM_QSIZE12 "tm_qsize12" static const char * const pmd_valid_args[] = { @@ -44,20 +29,6 @@ static const char * const pmd_valid_args[] = { PMD_PARAM_CONN_PORT, PMD_PARAM_CPU_ID, PMD_PARAM_SC, - PMD_PARAM_TM_N_QUEUES, - PMD_PARAM_TM_QSIZE0, - PMD_PARAM_TM_QSIZE1, - PMD_PARAM_TM_QSIZE2, - PMD_PARAM_TM_QSIZE3, - PMD_PARAM_TM_QSIZE4, - PMD_PARAM_TM_QSIZE5, - PMD_PARAM_TM_QSIZE6, - PMD_PARAM_TM_QSIZE7, - PMD_PARAM_TM_QSIZE8, - PMD_PARAM_TM_QSIZE9, - PMD_PARAM_TM_QSIZE10, - PMD_PARAM_TM_QSIZE11, - PMD_PARAM_TM_QSIZE12, NULL }; @@ -193,12 +164,10 @@ pmd_dev_stop(struct rte_eth_dev *dev) softnic_table_action_profile_free(p); softnic_port_in_action_profile_free(p); softnic_tap_free(p); - softnic_tmgr_free(p); softnic_link_free(p); softnic_softnic_swq_free_keep_rxq_txq(p); softnic_mempool_free(p); - tm_hierarchy_free(p); softnic_mtr_free(p); return 0; @@ -218,12 +187,10 @@ pmd_free(struct pmd_internals *p) softnic_table_action_profile_free(p); softnic_port_in_action_profile_free(p); softnic_tap_free(p); - softnic_tmgr_free(p); softnic_link_free(p); softnic_swq_free(p); softnic_mempool_free(p); - tm_hierarchy_free(p); softnic_mtr_free(p); rte_free(p); @@ -256,14 +223,6 @@ pmd_flow_ops_get(struct rte_eth_dev *dev __rte_unused, return 0; } -static int -pmd_tm_ops_get(struct rte_eth_dev *dev __rte_unused, void *arg) -{ - *(const struct rte_tm_ops **)arg = &pmd_tm_ops; - - return 0; -} - static int pmd_mtr_ops_get(struct rte_eth_dev *dev __rte_unused, void *arg) { @@ -282,7 +241,6 @@ static const struct eth_dev_ops pmd_ops = { .rx_queue_setup = pmd_rx_queue_setup, .tx_queue_setup = pmd_tx_queue_setup, .flow_ops_get = pmd_flow_ops_get, - .tm_ops_get = pmd_tm_ops_get, .mtr_ops_get = pmd_mtr_ops_get, }; @@ -325,13 +283,11 @@ pmd_init(struct pmd_params *params) memcpy(&p->params, params, sizeof(p->params)); /* Resources */ - tm_hierarchy_init(p); softnic_mtr_init(p); softnic_mempool_init(p); softnic_swq_init(p); softnic_link_init(p); - softnic_tmgr_init(p); softnic_tap_init(p); softnic_cryptodev_init(p); softnic_port_in_action_profile_init(p); @@ -459,20 +415,6 @@ pmd_parse_args(struct pmd_params *p, const char *params) } p->cpu_id = SOFTNIC_CPU_ID; p->sc = SOFTNIC_SC; - p->tm.n_queues = SOFTNIC_TM_N_QUEUES; - p->tm.qsize[0] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[1] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[2] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[3] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[4] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[5] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[6] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[7] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[8] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[9] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[10] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[11] = SOFTNIC_TM_QUEUE_SIZE; - p->tm.qsize[12] = SOFTNIC_TM_QUEUE_SIZE; /* Firmware script (optional) */ if (rte_kvargs_count(kvlist, PMD_PARAM_FIRMWARE) == 1) { @@ -517,104 +459,6 @@ pmd_parse_args(struct pmd_params *p, const char *params) goto out_free; } - /* TM number of queues (optional) */ - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_N_QUEUES) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_N_QUEUES, - &get_uint32, &p->tm.n_queues); - if (ret < 0) - goto out_free; - } - - /* TM queue size 0 .. 3 (optional) */ - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE0) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE0, - &get_uint32, &p->tm.qsize[0]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE1) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE1, - &get_uint32, &p->tm.qsize[1]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE2) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE2, - &get_uint32, &p->tm.qsize[2]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE3) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE3, - &get_uint32, &p->tm.qsize[3]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE4) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE4, - &get_uint32, &p->tm.qsize[4]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE5) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE5, - &get_uint32, &p->tm.qsize[5]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE6) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE6, - &get_uint32, &p->tm.qsize[6]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE7) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE7, - &get_uint32, &p->tm.qsize[7]); - if (ret < 0) - goto out_free; - } - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE8) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE8, - &get_uint32, &p->tm.qsize[8]); - if (ret < 0) - goto out_free; - } - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE9) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE9, - &get_uint32, &p->tm.qsize[9]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE10) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE10, - &get_uint32, &p->tm.qsize[10]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE11) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE11, - &get_uint32, &p->tm.qsize[11]); - if (ret < 0) - goto out_free; - } - - if (rte_kvargs_count(kvlist, PMD_PARAM_TM_QSIZE12) == 1) { - ret = rte_kvargs_process(kvlist, PMD_PARAM_TM_QSIZE12, - &get_uint32, &p->tm.qsize[12]); - if (ret < 0) - goto out_free; - } - out_free: rte_kvargs_free(kvlist); return ret; @@ -696,20 +540,6 @@ RTE_PMD_REGISTER_PARAM_STRING(net_softnic, PMD_PARAM_FIRMWARE "= " PMD_PARAM_CONN_PORT "= " PMD_PARAM_CPU_ID "= " - PMD_PARAM_TM_N_QUEUES "= " - PMD_PARAM_TM_QSIZE0 "= " - PMD_PARAM_TM_QSIZE1 "= " - PMD_PARAM_TM_QSIZE2 "= " - PMD_PARAM_TM_QSIZE3 "=" - PMD_PARAM_TM_QSIZE4 "= " - PMD_PARAM_TM_QSIZE5 "= " - PMD_PARAM_TM_QSIZE6 "= " - PMD_PARAM_TM_QSIZE7 "= " - PMD_PARAM_TM_QSIZE8 "= " - PMD_PARAM_TM_QSIZE9 "= " - PMD_PARAM_TM_QSIZE10 "= " - PMD_PARAM_TM_QSIZE11 "=" - PMD_PARAM_TM_QSIZE12 "=" ); int diff --git a/drivers/net/softnic/rte_eth_softnic.h b/drivers/net/softnic/rte_eth_softnic.h index 6c11d89ab6..3fd80fa571 100644 --- a/drivers/net/softnic/rte_eth_softnic.h +++ b/drivers/net/softnic/rte_eth_softnic.h @@ -46,16 +46,6 @@ extern "C" { #define SOFTNIC_SC 1 #endif -/** Traffic Manager: Number of scheduler queues. */ -#ifndef SOFTNIC_TM_N_QUEUES -#define SOFTNIC_TM_N_QUEUES (64 * 1024) -#endif - -/** Traffic Manager: Scheduler queue size (per traffic class). */ -#ifndef SOFTNIC_TM_QUEUE_SIZE -#define SOFTNIC_TM_QUEUE_SIZE 64 -#endif - /** * Soft NIC run. * diff --git a/drivers/net/softnic/rte_eth_softnic_cli.c b/drivers/net/softnic/rte_eth_softnic_cli.c index 7acbeecae7..7556e50831 100644 --- a/drivers/net/softnic/rte_eth_softnic_cli.c +++ b/drivers/net/softnic/rte_eth_softnic_cli.c @@ -186,1270 +186,6 @@ cmd_swq(struct pmd_internals *softnic, } } -/** - * tmgr shaper profile - * id - * rate size - * adj - */ -static void -cmd_tmgr_shaper_profile(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct rte_tm_shaper_params sp; - struct rte_tm_error error; - uint32_t shaper_profile_id; - uint16_t port_id; - int status; - - memset(&sp, 0, sizeof(struct rte_tm_shaper_params)); - - if (n_tokens != 11) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "shaper") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "shaper"); - return; - } - - if (strcmp(tokens[2], "profile") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "profile"); - return; - } - - if (strcmp(tokens[3], "id") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "id"); - return; - } - - if (softnic_parser_read_uint32(&shaper_profile_id, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "profile_id"); - return; - } - - if (strcmp(tokens[5], "rate") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "rate"); - return; - } - - if (softnic_parser_read_uint64(&sp.peak.rate, tokens[6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tb_rate"); - return; - } - - if (strcmp(tokens[7], "size") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "size"); - return; - } - - if (softnic_parser_read_uint64(&sp.peak.size, tokens[8]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tb_size"); - return; - } - - if (strcmp(tokens[9], "adj") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "adj"); - return; - } - - if (softnic_parser_read_int32(&sp.pkt_length_adjust, tokens[10]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "packet_length_adjust"); - return; - } - - status = rte_eth_dev_get_port_by_name(softnic->params.name, &port_id); - if (status) - return; - - status = rte_tm_shaper_profile_add(port_id, shaper_profile_id, &sp, &error); - if (status != 0) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * tmgr shared shaper - * id - * profile - */ -static void -cmd_tmgr_shared_shaper(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct rte_tm_error error; - uint32_t shared_shaper_id, shaper_profile_id; - uint16_t port_id; - int status; - - if (n_tokens != 7) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "shared") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "shared"); - return; - } - - if (strcmp(tokens[2], "shaper") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "shaper"); - return; - } - - if (strcmp(tokens[3], "id") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "id"); - return; - } - - if (softnic_parser_read_uint32(&shared_shaper_id, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared_shaper_id"); - return; - } - - if (strcmp(tokens[5], "profile") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "profile"); - return; - } - - if (softnic_parser_read_uint32(&shaper_profile_id, tokens[6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shaper_profile_id"); - return; - } - - status = rte_eth_dev_get_port_by_name(softnic->params.name, &port_id); - if (status) - return; - - status = rte_tm_shared_shaper_add_update(port_id, - shared_shaper_id, - shaper_profile_id, - &error); - if (status != 0) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * tmgr node - * id - * parent - * priority - * weight - * [shaper profile ] - * [shared shaper ] - * [nonleaf sp ] - */ -static void -cmd_tmgr_node(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct rte_tm_error error; - struct rte_tm_node_params np; - uint32_t node_id, parent_node_id, priority, weight, shared_shaper_id; - uint16_t port_id; - int status; - - memset(&np, 0, sizeof(struct rte_tm_node_params)); - np.shaper_profile_id = RTE_TM_SHAPER_PROFILE_ID_NONE; - np.nonleaf.n_sp_priorities = 1; - - if (n_tokens < 10) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "node") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "node"); - return; - } - - if (strcmp(tokens[2], "id") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "id"); - return; - } - - if (softnic_parser_read_uint32(&node_id, tokens[3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "node_id"); - return; - } - - if (strcmp(tokens[4], "parent") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "parent"); - return; - } - - if (strcmp(tokens[5], "none") == 0) - parent_node_id = RTE_TM_NODE_ID_NULL; - else { - if (softnic_parser_read_uint32(&parent_node_id, tokens[5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "parent_node_id"); - return; - } - } - - if (strcmp(tokens[6], "priority") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "priority"); - return; - } - - if (softnic_parser_read_uint32(&priority, tokens[7]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "priority"); - return; - } - - if (strcmp(tokens[8], "weight") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "weight"); - return; - } - - if (softnic_parser_read_uint32(&weight, tokens[9]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "weight"); - return; - } - - tokens += 10; - n_tokens -= 10; - - if (n_tokens >= 2 && - (strcmp(tokens[0], "shaper") == 0) && - (strcmp(tokens[1], "profile") == 0)) { - if (n_tokens < 3) { - snprintf(out, out_size, MSG_ARG_MISMATCH, "tmgr node"); - return; - } - - if (strcmp(tokens[2], "none") == 0) { - np.shaper_profile_id = RTE_TM_SHAPER_PROFILE_ID_NONE; - } else { - if (softnic_parser_read_uint32(&np.shaper_profile_id, tokens[2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shaper_profile_id"); - return; - } - } - - tokens += 3; - n_tokens -= 3; - } /* shaper profile */ - - if (n_tokens >= 2 && - (strcmp(tokens[0], "shared") == 0) && - (strcmp(tokens[1], "shaper") == 0)) { - if (n_tokens < 3) { - snprintf(out, out_size, MSG_ARG_MISMATCH, "tmgr node"); - return; - } - - if (softnic_parser_read_uint32(&shared_shaper_id, tokens[2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared_shaper_id"); - return; - } - - np.shared_shaper_id = &shared_shaper_id; - np.n_shared_shapers = 1; - - tokens += 3; - n_tokens -= 3; - } /* shared shaper */ - - if (n_tokens >= 2 && - (strcmp(tokens[0], "nonleaf") == 0) && - (strcmp(tokens[1], "sp") == 0)) { - if (n_tokens < 3) { - snprintf(out, out_size, MSG_ARG_MISMATCH, "tmgr node"); - return; - } - - if (softnic_parser_read_uint32(&np.nonleaf.n_sp_priorities, tokens[2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_sp_priorities"); - return; - } - - tokens += 3; - n_tokens -= 3; - } /* nonleaf sp */ - - if (n_tokens) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - status = rte_eth_dev_get_port_by_name(softnic->params.name, &port_id); - if (status != 0) - return; - - status = rte_tm_node_add(port_id, - node_id, - parent_node_id, - priority, - weight, - RTE_TM_NODE_LEVEL_ID_ANY, - &np, - &error); - if (status != 0) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -static uint32_t -root_node_id(uint32_t n_spp, - uint32_t n_pps) -{ - uint32_t n_queues = n_spp * n_pps * RTE_SCHED_QUEUES_PER_PIPE; - uint32_t n_tc = n_spp * n_pps * RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; - uint32_t n_pipes = n_spp * n_pps; - - return n_queues + n_tc + n_pipes + n_spp; -} - -static uint32_t -subport_node_id(uint32_t n_spp, - uint32_t n_pps, - uint32_t subport_id) -{ - uint32_t n_pipes = n_spp * n_pps; - uint32_t n_tc = n_pipes * RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; - uint32_t n_queues = n_pipes * RTE_SCHED_QUEUES_PER_PIPE; - - return n_queues + n_tc + n_pipes + subport_id; -} - -static uint32_t -pipe_node_id(uint32_t n_spp, - uint32_t n_pps, - uint32_t subport_id, - uint32_t pipe_id) -{ - uint32_t n_pipes = n_spp * n_pps; - uint32_t n_tc = n_pipes * RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; - uint32_t n_queues = n_pipes * RTE_SCHED_QUEUES_PER_PIPE; - - return n_queues + - n_tc + - pipe_id + - subport_id * n_pps; -} - -static uint32_t -tc_node_id(uint32_t n_spp, - uint32_t n_pps, - uint32_t subport_id, - uint32_t pipe_id, - uint32_t tc_id) -{ - uint32_t n_pipes = n_spp * n_pps; - uint32_t n_queues = n_pipes * RTE_SCHED_QUEUES_PER_PIPE; - - return n_queues + - tc_id + - (pipe_id + subport_id * n_pps) * RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; -} - -static uint32_t -queue_node_id(uint32_t n_spp __rte_unused, - uint32_t n_pps, - uint32_t subport_id, - uint32_t pipe_id, - uint32_t tc_id, - uint32_t queue_id) -{ - return queue_id + tc_id + - (pipe_id + subport_id * n_pps) * RTE_SCHED_QUEUES_PER_PIPE; -} - -struct tmgr_hierarchy_default_params { - uint32_t n_spp; /**< Number of subports per port. */ - uint32_t n_pps; /**< Number of pipes per subport. */ - - struct { - uint32_t port; - uint32_t subport; - uint32_t pipe; - uint32_t tc[RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE]; - } shaper_profile_id; - - struct { - uint32_t tc[RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE]; - uint32_t tc_valid[RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE]; - } shared_shaper_id; - - struct { - uint32_t queue[RTE_SCHED_QUEUES_PER_PIPE]; - } weight; -}; - -static int -tmgr_hierarchy_default(struct pmd_internals *softnic, - struct tmgr_hierarchy_default_params *params) -{ - struct rte_tm_node_params root_node_params = { - .shaper_profile_id = params->shaper_profile_id.port, - .nonleaf = { - .n_sp_priorities = 1, - }, - }; - - struct rte_tm_node_params subport_node_params = { - .shaper_profile_id = params->shaper_profile_id.subport, - .nonleaf = { - .n_sp_priorities = 1, - }, - }; - - struct rte_tm_node_params pipe_node_params = { - .shaper_profile_id = params->shaper_profile_id.pipe, - .nonleaf = { - .n_sp_priorities = RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - }, - }; - - uint32_t *shared_shaper_id = - (uint32_t *)calloc(RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - sizeof(uint32_t)); - - if (shared_shaper_id == NULL) - return -1; - - memcpy(shared_shaper_id, params->shared_shaper_id.tc, - sizeof(params->shared_shaper_id.tc)); - - struct rte_tm_node_params tc_node_params[] = { - [0] = { - .shaper_profile_id = params->shaper_profile_id.tc[0], - .shared_shaper_id = &shared_shaper_id[0], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[0]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [1] = { - .shaper_profile_id = params->shaper_profile_id.tc[1], - .shared_shaper_id = &shared_shaper_id[1], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[1]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [2] = { - .shaper_profile_id = params->shaper_profile_id.tc[2], - .shared_shaper_id = &shared_shaper_id[2], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[2]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [3] = { - .shaper_profile_id = params->shaper_profile_id.tc[3], - .shared_shaper_id = &shared_shaper_id[3], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[3]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [4] = { - .shaper_profile_id = params->shaper_profile_id.tc[4], - .shared_shaper_id = &shared_shaper_id[4], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[4]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [5] = { - .shaper_profile_id = params->shaper_profile_id.tc[5], - .shared_shaper_id = &shared_shaper_id[5], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[5]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [6] = { - .shaper_profile_id = params->shaper_profile_id.tc[6], - .shared_shaper_id = &shared_shaper_id[6], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[6]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [7] = { - .shaper_profile_id = params->shaper_profile_id.tc[7], - .shared_shaper_id = &shared_shaper_id[7], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[7]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [8] = { - .shaper_profile_id = params->shaper_profile_id.tc[8], - .shared_shaper_id = &shared_shaper_id[8], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[8]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [9] = { - .shaper_profile_id = params->shaper_profile_id.tc[9], - .shared_shaper_id = &shared_shaper_id[9], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[9]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [10] = { - .shaper_profile_id = params->shaper_profile_id.tc[10], - .shared_shaper_id = &shared_shaper_id[10], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[10]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [11] = { - .shaper_profile_id = params->shaper_profile_id.tc[11], - .shared_shaper_id = &shared_shaper_id[11], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[11]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - - [12] = { - .shaper_profile_id = params->shaper_profile_id.tc[12], - .shared_shaper_id = &shared_shaper_id[12], - .n_shared_shapers = - (params->shared_shaper_id.tc_valid[12]) ? 1 : 0, - .nonleaf = { - .n_sp_priorities = 1, - }, - }, - }; - - struct rte_tm_node_params queue_node_params = { - .shaper_profile_id = RTE_TM_SHAPER_PROFILE_ID_NONE, - }; - - struct rte_tm_error error; - uint32_t n_spp = params->n_spp, n_pps = params->n_pps, s; - int status; - uint16_t port_id; - - status = rte_eth_dev_get_port_by_name(softnic->params.name, &port_id); - if (status) - return -1; - - /* Hierarchy level 0: Root node */ - status = rte_tm_node_add(port_id, - root_node_id(n_spp, n_pps), - RTE_TM_NODE_ID_NULL, - 0, - 1, - RTE_TM_NODE_LEVEL_ID_ANY, - &root_node_params, - &error); - if (status) - return -1; - - /* Hierarchy level 1: Subport nodes */ - for (s = 0; s < params->n_spp; s++) { - uint32_t p; - - status = rte_tm_node_add(port_id, - subport_node_id(n_spp, n_pps, s), - root_node_id(n_spp, n_pps), - 0, - 1, - RTE_TM_NODE_LEVEL_ID_ANY, - &subport_node_params, - &error); - if (status) - return -1; - - /* Hierarchy level 2: Pipe nodes */ - for (p = 0; p < params->n_pps; p++) { - uint32_t t; - - status = rte_tm_node_add(port_id, - pipe_node_id(n_spp, n_pps, s, p), - subport_node_id(n_spp, n_pps, s), - 0, - 1, - RTE_TM_NODE_LEVEL_ID_ANY, - &pipe_node_params, - &error); - if (status) - return -1; - - /* Hierarchy level 3: Traffic class nodes */ - for (t = 0; t < RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; t++) { - uint32_t q; - - status = rte_tm_node_add(port_id, - tc_node_id(n_spp, n_pps, s, p, t), - pipe_node_id(n_spp, n_pps, s, p), - t, - 1, - RTE_TM_NODE_LEVEL_ID_ANY, - &tc_node_params[t], - &error); - if (status) - return -1; - - /* Hierarchy level 4: Queue nodes */ - if (t < RTE_SCHED_TRAFFIC_CLASS_BE) { - /* Strict-priority traffic class queues */ - q = 0; - status = rte_tm_node_add(port_id, - queue_node_id(n_spp, n_pps, s, p, t, q), - tc_node_id(n_spp, n_pps, s, p, t), - 0, - params->weight.queue[q], - RTE_TM_NODE_LEVEL_ID_ANY, - &queue_node_params, - &error); - if (status) - return -1; - - continue; - } - /* Best-effort traffic class queues */ - for (q = 0; q < RTE_SCHED_BE_QUEUES_PER_PIPE; q++) { - status = rte_tm_node_add(port_id, - queue_node_id(n_spp, n_pps, s, p, t, q), - tc_node_id(n_spp, n_pps, s, p, t), - 0, - params->weight.queue[q], - RTE_TM_NODE_LEVEL_ID_ANY, - &queue_node_params, - &error); - if (status) - return -1; - } - } /* TC */ - } /* Pipe */ - } /* Subport */ - - return 0; -} - - -/** - * tmgr hierarchy-default - * spp - * pps - * shaper profile - * port - * subport - * pipe - * tc0 - * tc1 - * tc2 - * tc3 - * tc4 - * tc5 - * tc6 - * tc7 - * tc8 - * tc9 - * tc10 - * tc11 - * tc12 - * shared shaper - * tc0 - * tc1 - * tc2 - * tc3 - * tc4 - * tc5 - * tc6 - * tc7 - * tc8 - * tc9 - * tc10 - * tc11 - * tc12 - * weight - * queue ... - */ -static void -cmd_tmgr_hierarchy_default(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct tmgr_hierarchy_default_params p; - int i, j, status; - - memset(&p, 0, sizeof(p)); - - if (n_tokens != 74) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "hierarchy-default") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "hierarchy-default"); - return; - } - - if (strcmp(tokens[2], "spp") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "spp"); - return; - } - - if (softnic_parser_read_uint32(&p.n_spp, tokens[3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_subports_per_port"); - return; - } - - if (strcmp(tokens[4], "pps") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "pps"); - return; - } - - if (softnic_parser_read_uint32(&p.n_pps, tokens[5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_pipes_per_subport"); - return; - } - - /* Shaper profile */ - - if (strcmp(tokens[6], "shaper") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "shaper"); - return; - } - - if (strcmp(tokens[7], "profile") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "profile"); - return; - } - - if (strcmp(tokens[8], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.port, tokens[9]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port profile id"); - return; - } - - if (strcmp(tokens[10], "subport") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "subport"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.subport, tokens[11]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "subport profile id"); - return; - } - - if (strcmp(tokens[12], "pipe") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "pipe"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.pipe, tokens[13]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "pipe_profile_id"); - return; - } - - if (strcmp(tokens[14], "tc0") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc0"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[0], tokens[15]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc0 profile id"); - return; - } - - if (strcmp(tokens[16], "tc1") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc1"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[1], tokens[17]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc1 profile id"); - return; - } - - if (strcmp(tokens[18], "tc2") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc2"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[2], tokens[19]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc2 profile id"); - return; - } - - if (strcmp(tokens[20], "tc3") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc3"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[3], tokens[21]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc3 profile id"); - return; - } - - if (strcmp(tokens[22], "tc4") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc4"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[4], tokens[23]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc4 profile id"); - return; - } - - if (strcmp(tokens[24], "tc5") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc5"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[5], tokens[25]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc5 profile id"); - return; - } - - if (strcmp(tokens[26], "tc6") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc6"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[6], tokens[27]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc6 profile id"); - return; - } - - if (strcmp(tokens[28], "tc7") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc7"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[7], tokens[29]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc7 profile id"); - return; - } - - if (strcmp(tokens[30], "tc8") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc8"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[8], tokens[31]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc8 profile id"); - return; - } - - if (strcmp(tokens[32], "tc9") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc9"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[9], tokens[33]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc9 profile id"); - return; - } - - if (strcmp(tokens[34], "tc10") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc10"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[10], tokens[35]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc10 profile id"); - return; - } - - if (strcmp(tokens[36], "tc11") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc11"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[11], tokens[37]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc11 profile id"); - return; - } - - if (strcmp(tokens[38], "tc12") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc12"); - return; - } - - if (softnic_parser_read_uint32(&p.shaper_profile_id.tc[12], tokens[39]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "tc12 profile id"); - return; - } - - /* Shared shaper */ - - if (strcmp(tokens[40], "shared") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "shared"); - return; - } - - if (strcmp(tokens[41], "shaper") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "shaper"); - return; - } - - if (strcmp(tokens[42], "tc0") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc0"); - return; - } - - if (strcmp(tokens[43], "none") == 0) - p.shared_shaper_id.tc_valid[0] = 0; - else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[0], - tokens[43]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc0"); - return; - } - - p.shared_shaper_id.tc_valid[0] = 1; - } - - if (strcmp(tokens[44], "tc1") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc1"); - return; - } - - if (strcmp(tokens[45], "none") == 0) - p.shared_shaper_id.tc_valid[1] = 0; - else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[1], - tokens[45]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc1"); - return; - } - - p.shared_shaper_id.tc_valid[1] = 1; - } - - if (strcmp(tokens[46], "tc2") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc2"); - return; - } - - if (strcmp(tokens[47], "none") == 0) - p.shared_shaper_id.tc_valid[2] = 0; - else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[2], - tokens[47]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc2"); - return; - } - - p.shared_shaper_id.tc_valid[2] = 1; - } - - if (strcmp(tokens[48], "tc3") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc3"); - return; - } - - if (strcmp(tokens[49], "none") == 0) - p.shared_shaper_id.tc_valid[3] = 0; - else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[3], - tokens[49]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc3"); - return; - } - - p.shared_shaper_id.tc_valid[3] = 1; - } - - if (strcmp(tokens[50], "tc4") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc4"); - return; - } - - if (strcmp(tokens[51], "none") == 0) { - p.shared_shaper_id.tc_valid[4] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[4], - tokens[51]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc4"); - return; - } - - p.shared_shaper_id.tc_valid[4] = 1; - } - - if (strcmp(tokens[52], "tc5") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc5"); - return; - } - - if (strcmp(tokens[53], "none") == 0) { - p.shared_shaper_id.tc_valid[5] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[5], - tokens[53]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc5"); - return; - } - - p.shared_shaper_id.tc_valid[5] = 1; - } - - if (strcmp(tokens[54], "tc6") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc6"); - return; - } - - if (strcmp(tokens[55], "none") == 0) { - p.shared_shaper_id.tc_valid[6] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[6], - tokens[55]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc6"); - return; - } - - p.shared_shaper_id.tc_valid[6] = 1; - } - - if (strcmp(tokens[56], "tc7") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc7"); - return; - } - - if (strcmp(tokens[57], "none") == 0) { - p.shared_shaper_id.tc_valid[7] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[7], - tokens[57]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc7"); - return; - } - - p.shared_shaper_id.tc_valid[7] = 1; - } - - if (strcmp(tokens[58], "tc8") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc8"); - return; - } - - if (strcmp(tokens[59], "none") == 0) { - p.shared_shaper_id.tc_valid[8] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[8], - tokens[59]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc8"); - return; - } - - p.shared_shaper_id.tc_valid[8] = 1; - } - - if (strcmp(tokens[60], "tc9") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc9"); - return; - } - - if (strcmp(tokens[61], "none") == 0) { - p.shared_shaper_id.tc_valid[9] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[9], - tokens[61]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc9"); - return; - } - - p.shared_shaper_id.tc_valid[9] = 1; - } - - if (strcmp(tokens[62], "tc10") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc10"); - return; - } - - if (strcmp(tokens[63], "none") == 0) { - p.shared_shaper_id.tc_valid[10] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[10], - tokens[63]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc10"); - return; - } - - p.shared_shaper_id.tc_valid[10] = 1; - } - - if (strcmp(tokens[64], "tc11") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc11"); - return; - } - - if (strcmp(tokens[65], "none") == 0) { - p.shared_shaper_id.tc_valid[11] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[11], - tokens[65]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc11"); - return; - } - - p.shared_shaper_id.tc_valid[11] = 1; - } - - if (strcmp(tokens[66], "tc12") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc12"); - return; - } - - if (strcmp(tokens[67], "none") == 0) { - p.shared_shaper_id.tc_valid[12] = 0; - } else { - if (softnic_parser_read_uint32(&p.shared_shaper_id.tc[12], - tokens[67]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "shared shaper tc12"); - return; - } - - p.shared_shaper_id.tc_valid[12] = 1; - } - - /* Weight */ - - if (strcmp(tokens[68], "weight") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "weight"); - return; - } - - if (strcmp(tokens[69], "queue") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "queue"); - return; - } - - for (i = 0, j = 0; i < 16; i++) { - if (i < RTE_SCHED_TRAFFIC_CLASS_BE) { - p.weight.queue[i] = 1; - } else { - if (softnic_parser_read_uint32(&p.weight.queue[i], - tokens[70 + j]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "weight queue"); - return; - } - j++; - } - } - - status = tmgr_hierarchy_default(softnic, &p); - if (status != 0) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * tmgr hierarchy commit - */ -static void -cmd_tmgr_hierarchy_commit(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct rte_tm_error error; - uint16_t port_id; - int status; - - if (n_tokens != 3) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "hierarchy") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "hierarchy"); - return; - } - - if (strcmp(tokens[2], "commit") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "commit"); - return; - } - - status = rte_eth_dev_get_port_by_name(softnic->params.name, &port_id); - if (status != 0) - return; - - status = rte_tm_hierarchy_commit(port_id, 1, &error); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * tmgr - */ -static void -cmd_tmgr(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - char *name; - struct softnic_tmgr_port *tmgr_port; - - if (n_tokens != 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - name = tokens[1]; - - tmgr_port = softnic_tmgr_port_create(softnic, name); - if (tmgr_port == NULL) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - /** * tap */ @@ -2247,7 +983,6 @@ cmd_pipeline(struct pmd_internals *softnic, * bsz * link rxq * | swq - * | tmgr * | tap mempool mtu * | source mempool file bpp * | cryptodev rxq @@ -2331,18 +1066,6 @@ cmd_pipeline_port_in(struct pmd_internals *softnic, strlcpy(p.dev_name, tokens[t0 + 1], sizeof(p.dev_name)); - t0 += 2; - } else if (strcmp(tokens[t0], "tmgr") == 0) { - if (n_tokens < t0 + 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port in tmgr"); - return; - } - - p.type = PORT_IN_TMGR; - - strlcpy(p.dev_name, tokens[t0 + 1], sizeof(p.dev_name)); - t0 += 2; } else if (strcmp(tokens[t0], "tap") == 0) { if (n_tokens < t0 + 6) { @@ -2482,7 +1205,6 @@ cmd_pipeline_port_in(struct pmd_internals *softnic, * bsz * link txq * | swq - * | tmgr * | tap * | sink [file pkts ] * | cryptodev txq offset @@ -2557,16 +1279,6 @@ cmd_pipeline_port_out(struct pmd_internals *softnic, p.type = PORT_OUT_SWQ; - strlcpy(p.dev_name, tokens[7], sizeof(p.dev_name)); - } else if (strcmp(tokens[6], "tmgr") == 0) { - if (n_tokens != 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out tmgr"); - return; - } - - p.type = PORT_OUT_TMGR; - strlcpy(p.dev_name, tokens[7], sizeof(p.dev_name)); } else if (strcmp(tokens[6], "tap") == 0) { if (n_tokens != 8) { @@ -6129,46 +4841,6 @@ softnic_cli_process(char *in, char *out, size_t out_size, void *arg) return; } - if (strcmp(tokens[0], "tmgr") == 0) { - if (n_tokens == 2) { - cmd_tmgr(softnic, tokens, n_tokens, out, out_size); - return; - } - - if (n_tokens >= 3 && - (strcmp(tokens[1], "shaper") == 0) && - (strcmp(tokens[2], "profile") == 0)) { - cmd_tmgr_shaper_profile(softnic, tokens, n_tokens, out, out_size); - return; - } - - if (n_tokens >= 3 && - (strcmp(tokens[1], "shared") == 0) && - (strcmp(tokens[2], "shaper") == 0)) { - cmd_tmgr_shared_shaper(softnic, tokens, n_tokens, out, out_size); - return; - } - - if (n_tokens >= 2 && - (strcmp(tokens[1], "node") == 0)) { - cmd_tmgr_node(softnic, tokens, n_tokens, out, out_size); - return; - } - - if (n_tokens >= 2 && - (strcmp(tokens[1], "hierarchy-default") == 0)) { - cmd_tmgr_hierarchy_default(softnic, tokens, n_tokens, out, out_size); - return; - } - - if (n_tokens >= 3 && - (strcmp(tokens[1], "hierarchy") == 0) && - (strcmp(tokens[2], "commit") == 0)) { - cmd_tmgr_hierarchy_commit(softnic, tokens, n_tokens, out, out_size); - return; - } - } - if (strcmp(tokens[0], "tap") == 0) { cmd_tap(softnic, tokens, n_tokens, out, out_size); return; diff --git a/drivers/net/softnic/rte_eth_softnic_internals.h b/drivers/net/softnic/rte_eth_softnic_internals.h index 07285ca315..4cc98b7aad 100644 --- a/drivers/net/softnic/rte_eth_softnic_internals.h +++ b/drivers/net/softnic/rte_eth_softnic_internals.h @@ -13,14 +13,12 @@ #include #include #include -#include #include #include #include #include #include -#include #include #include @@ -40,12 +38,6 @@ struct pmd_params { uint16_t conn_port; uint32_t cpu_id; int sc; /**< Service cores. */ - - /** Traffic Management (TM) */ - struct { - uint32_t n_queues; /**< Number of queues */ - uint16_t qsize[RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE]; - } tm; }; /** @@ -161,134 +153,6 @@ struct softnic_link { TAILQ_HEAD(softnic_link_list, softnic_link); -/** - * TMGR - */ - -#ifndef TM_MAX_SUBPORTS -#define TM_MAX_SUBPORTS 8 -#endif - -#ifndef TM_MAX_PIPES_PER_SUBPORT -#define TM_MAX_PIPES_PER_SUBPORT 4096 -#endif - -#ifndef TM_MAX_PIPE_PROFILE -#define TM_MAX_PIPE_PROFILE 256 -#endif - -#ifndef TM_MAX_SUBPORT_PROFILE -#define TM_MAX_SUBPORT_PROFILE 256 -#endif - -struct tm_params { - struct rte_sched_port_params port_params; - struct rte_sched_subport_params subport_params[TM_MAX_SUBPORTS]; - struct rte_sched_subport_profile_params - subport_profile[TM_MAX_SUBPORT_PROFILE]; - uint32_t n_subport_profiles; - uint32_t subport_to_profile[TM_MAX_SUBPORT_PROFILE]; - struct rte_sched_pipe_params pipe_profiles[TM_MAX_PIPE_PROFILE]; - uint32_t n_pipe_profiles; - uint32_t pipe_to_profile[TM_MAX_SUBPORTS * TM_MAX_PIPES_PER_SUBPORT]; -}; - -/* TM Levels */ -enum tm_node_level { - TM_NODE_LEVEL_PORT = 0, - TM_NODE_LEVEL_SUBPORT, - TM_NODE_LEVEL_PIPE, - TM_NODE_LEVEL_TC, - TM_NODE_LEVEL_QUEUE, - TM_NODE_LEVEL_MAX, -}; - -/* TM Shaper Profile */ -struct tm_shaper_profile { - TAILQ_ENTRY(tm_shaper_profile) node; - uint32_t shaper_profile_id; - uint32_t n_users; - struct rte_tm_shaper_params params; -}; - -TAILQ_HEAD(tm_shaper_profile_list, tm_shaper_profile); - -/* TM Shared Shaper */ -struct tm_shared_shaper { - TAILQ_ENTRY(tm_shared_shaper) node; - uint32_t shared_shaper_id; - uint32_t n_users; - uint32_t shaper_profile_id; -}; - -TAILQ_HEAD(tm_shared_shaper_list, tm_shared_shaper); - -/* TM WRED Profile */ -struct tm_wred_profile { - TAILQ_ENTRY(tm_wred_profile) node; - uint32_t wred_profile_id; - uint32_t n_users; - struct rte_tm_wred_params params; -}; - -TAILQ_HEAD(tm_wred_profile_list, tm_wred_profile); - -/* TM Node */ -struct tm_node { - TAILQ_ENTRY(tm_node) node; - uint32_t node_id; - uint32_t parent_node_id; - uint32_t priority; - uint32_t weight; - uint32_t level; - struct tm_node *parent_node; - struct tm_shaper_profile *shaper_profile; - struct tm_wred_profile *wred_profile; - struct rte_tm_node_params params; - struct rte_tm_node_stats stats; - uint32_t n_children; -}; - -TAILQ_HEAD(tm_node_list, tm_node); - -/* TM Hierarchy Specification */ -struct tm_hierarchy { - struct tm_shaper_profile_list shaper_profiles; - struct tm_shared_shaper_list shared_shapers; - struct tm_wred_profile_list wred_profiles; - struct tm_node_list nodes; - - uint32_t n_shaper_profiles; - uint32_t n_shared_shapers; - uint32_t n_wred_profiles; - uint32_t n_nodes; - - uint32_t n_tm_nodes[TM_NODE_LEVEL_MAX]; -}; - -struct tm_internals { - /** Hierarchy specification - * - * -Hierarchy is unfrozen at init and when port is stopped. - * -Hierarchy is frozen on successful hierarchy commit. - * -Run-time hierarchy changes are not allowed, therefore it makes - * sense to keep the hierarchy frozen after the port is started. - */ - struct tm_hierarchy h; - int hierarchy_frozen; - - /** Blueprints */ - struct tm_params params; -}; - -struct softnic_tmgr_port { - TAILQ_ENTRY(softnic_tmgr_port) node; - char name[NAME_SIZE]; - struct rte_sched_port *s; -}; - -TAILQ_HEAD(softnic_tmgr_port_list, softnic_tmgr_port); - /** * TAP */ @@ -385,7 +249,6 @@ struct pipeline_params { enum softnic_port_in_type { PORT_IN_RXQ, PORT_IN_SWQ, - PORT_IN_TMGR, PORT_IN_TAP, PORT_IN_SOURCE, PORT_IN_CRYPTODEV, @@ -426,7 +289,6 @@ struct softnic_port_in_params { enum softnic_port_out_type { PORT_OUT_TXQ, PORT_OUT_SWQ, - PORT_OUT_TMGR, PORT_OUT_TAP, PORT_OUT_SINK, PORT_OUT_CRYPTODEV, @@ -619,10 +481,6 @@ struct pmd_internals { /** Params */ struct pmd_params params; - struct { - struct tm_internals tm; /**< Traffic Management */ - } soft; - struct flow_internals flow; struct mtr_internals mtr; @@ -630,7 +488,6 @@ struct pmd_internals { struct softnic_mempool_list mempool_list; struct softnic_swq_list swq_list; struct softnic_link_list link_list; - struct softnic_tmgr_port_list tmgr_port_list; struct softnic_tap_list tap_list; struct softnic_cryptodev_list cryptodev_list; struct softnic_port_in_action_profile_list port_in_action_profile_list; @@ -753,39 +610,6 @@ softnic_link_create(struct pmd_internals *p, const char *name, struct softnic_link_params *params); -/** - * TMGR - */ -int -softnic_tmgr_init(struct pmd_internals *p); - -void -softnic_tmgr_free(struct pmd_internals *p); - -struct softnic_tmgr_port * -softnic_tmgr_port_find(struct pmd_internals *p, - const char *name); - -struct softnic_tmgr_port * -softnic_tmgr_port_create(struct pmd_internals *p, - const char *name); - -void -tm_hierarchy_init(struct pmd_internals *p); - -void -tm_hierarchy_free(struct pmd_internals *p); - -static inline int -tm_used(struct rte_eth_dev *dev) -{ - struct pmd_internals *p = dev->data->dev_private; - - return p->soft.tm.h.n_tm_nodes[TM_NODE_LEVEL_PORT]; -} - -extern const struct rte_tm_ops pmd_tm_ops; - /** * TAP */ diff --git a/drivers/net/softnic/rte_eth_softnic_pipeline.c b/drivers/net/softnic/rte_eth_softnic_pipeline.c index 337aa32e57..c7d2a7de19 100644 --- a/drivers/net/softnic/rte_eth_softnic_pipeline.c +++ b/drivers/net/softnic/rte_eth_softnic_pipeline.c @@ -305,21 +305,6 @@ softnic_pipeline_port_in_create(struct pmd_internals *softnic, break; } - case PORT_IN_TMGR: - { - struct softnic_tmgr_port *tmgr_port; - - tmgr_port = softnic_tmgr_port_find(softnic, params->dev_name); - if (tmgr_port == NULL) - return -1; - - pp.sched.sched = tmgr_port->s; - - p.ops = &rte_port_sched_reader_ops; - p.arg_create = &pp.sched; - break; - } - case PORT_IN_TAP: { struct softnic_tap *tap; @@ -545,22 +530,6 @@ softnic_pipeline_port_out_create(struct pmd_internals *softnic, break; } - case PORT_OUT_TMGR: - { - struct softnic_tmgr_port *tmgr_port; - - tmgr_port = softnic_tmgr_port_find(softnic, params->dev_name); - if (tmgr_port == NULL) - return -1; - - pp.sched.sched = tmgr_port->s; - pp.sched.tx_burst_sz = params->burst_size; - - p.ops = &rte_port_sched_writer_ops; - p.arg_create = &pp.sched; - break; - } - case PORT_OUT_TAP: { struct softnic_tap *tap; diff --git a/drivers/net/softnic/rte_eth_softnic_tm.c b/drivers/net/softnic/rte_eth_softnic_tm.c deleted file mode 100644 index 6a7766ba1c..0000000000 --- a/drivers/net/softnic/rte_eth_softnic_tm.c +++ /dev/null @@ -1,3657 +0,0 @@ -/* SPDX-License-Identifier: BSD-3-Clause - * Copyright(c) 2017 Intel Corporation - */ - -#include -#include -#include - -#include -#include - -#include "rte_eth_softnic_internals.h" -#include "rte_eth_softnic.h" - -#define SUBPORT_TC_PERIOD 10 -#define PIPE_TC_PERIOD 40 - -int -softnic_tmgr_init(struct pmd_internals *p) -{ - TAILQ_INIT(&p->tmgr_port_list); - - return 0; -} - -void -softnic_tmgr_free(struct pmd_internals *p) -{ - for ( ; ; ) { - struct softnic_tmgr_port *tmgr_port; - - tmgr_port = TAILQ_FIRST(&p->tmgr_port_list); - if (tmgr_port == NULL) - break; - - TAILQ_REMOVE(&p->tmgr_port_list, tmgr_port, node); - rte_sched_port_free(tmgr_port->s); - free(tmgr_port); - } -} - -struct softnic_tmgr_port * -softnic_tmgr_port_find(struct pmd_internals *p, - const char *name) -{ - struct softnic_tmgr_port *tmgr_port; - - if (name == NULL) - return NULL; - - TAILQ_FOREACH(tmgr_port, &p->tmgr_port_list, node) - if (strcmp(tmgr_port->name, name) == 0) - return tmgr_port; - - return NULL; -} - -struct softnic_tmgr_port * -softnic_tmgr_port_create(struct pmd_internals *p, - const char *name) -{ - struct softnic_tmgr_port *tmgr_port; - struct tm_params *t = &p->soft.tm.params; - struct rte_sched_port *sched; - uint32_t n_subports, subport_id; - - /* Check input params */ - if (name == NULL || - softnic_tmgr_port_find(p, name)) - return NULL; - - /* - * Resource - */ - - /* Is hierarchy frozen? */ - if (p->soft.tm.hierarchy_frozen == 0) - return NULL; - - /* Port */ - sched = rte_sched_port_config(&t->port_params); - if (sched == NULL) - return NULL; - - /* Subport */ - n_subports = t->port_params.n_subports_per_port; - for (subport_id = 0; subport_id < n_subports; subport_id++) { - uint32_t n_pipes_per_subport = - t->subport_params[subport_id].n_pipes_per_subport_enabled; - uint32_t pipe_id; - int status; - - status = rte_sched_subport_config(sched, - subport_id, - &t->subport_params[subport_id], - t->subport_to_profile[subport_id]); - if (status) { - rte_sched_port_free(sched); - return NULL; - } - - /* Pipe */ - for (pipe_id = 0; pipe_id < n_pipes_per_subport; pipe_id++) { - int pos = subport_id * TM_MAX_PIPES_PER_SUBPORT + pipe_id; - int profile_id = t->pipe_to_profile[pos]; - - if (profile_id < 0) - continue; - - status = rte_sched_pipe_config(sched, - subport_id, - pipe_id, - profile_id); - if (status) { - rte_sched_port_free(sched); - return NULL; - } - } - } - - /* Node allocation */ - tmgr_port = calloc(1, sizeof(struct softnic_tmgr_port)); - if (tmgr_port == NULL) { - rte_sched_port_free(sched); - return NULL; - } - - /* Node fill in */ - strlcpy(tmgr_port->name, name, sizeof(tmgr_port->name)); - tmgr_port->s = sched; - - /* Node add to list */ - TAILQ_INSERT_TAIL(&p->tmgr_port_list, tmgr_port, node); - - return tmgr_port; -} - -static struct rte_sched_port * -SCHED(struct pmd_internals *p) -{ - struct softnic_tmgr_port *tmgr_port; - - tmgr_port = softnic_tmgr_port_find(p, "TMGR"); - if (tmgr_port == NULL) - return NULL; - - return tmgr_port->s; -} - -void -tm_hierarchy_init(struct pmd_internals *p) -{ - memset(&p->soft.tm, 0, sizeof(p->soft.tm)); - - /* Initialize shaper profile list */ - TAILQ_INIT(&p->soft.tm.h.shaper_profiles); - - /* Initialize shared shaper list */ - TAILQ_INIT(&p->soft.tm.h.shared_shapers); - - /* Initialize wred profile list */ - TAILQ_INIT(&p->soft.tm.h.wred_profiles); - - /* Initialize TM node list */ - TAILQ_INIT(&p->soft.tm.h.nodes); -} - -void -tm_hierarchy_free(struct pmd_internals *p) -{ - /* Remove all nodes*/ - for ( ; ; ) { - struct tm_node *tm_node; - - tm_node = TAILQ_FIRST(&p->soft.tm.h.nodes); - if (tm_node == NULL) - break; - - TAILQ_REMOVE(&p->soft.tm.h.nodes, tm_node, node); - free(tm_node); - } - - /* Remove all WRED profiles */ - for ( ; ; ) { - struct tm_wred_profile *wred_profile; - - wred_profile = TAILQ_FIRST(&p->soft.tm.h.wred_profiles); - if (wred_profile == NULL) - break; - - TAILQ_REMOVE(&p->soft.tm.h.wred_profiles, wred_profile, node); - free(wred_profile); - } - - /* Remove all shared shapers */ - for ( ; ; ) { - struct tm_shared_shaper *shared_shaper; - - shared_shaper = TAILQ_FIRST(&p->soft.tm.h.shared_shapers); - if (shared_shaper == NULL) - break; - - TAILQ_REMOVE(&p->soft.tm.h.shared_shapers, shared_shaper, node); - free(shared_shaper); - } - - /* Remove all shaper profiles */ - for ( ; ; ) { - struct tm_shaper_profile *shaper_profile; - - shaper_profile = TAILQ_FIRST(&p->soft.tm.h.shaper_profiles); - if (shaper_profile == NULL) - break; - - TAILQ_REMOVE(&p->soft.tm.h.shaper_profiles, - shaper_profile, node); - free(shaper_profile); - } - - tm_hierarchy_init(p); -} - -static struct tm_shaper_profile * -tm_shaper_profile_search(struct rte_eth_dev *dev, uint32_t shaper_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_shaper_profile_list *spl = &p->soft.tm.h.shaper_profiles; - struct tm_shaper_profile *sp; - - TAILQ_FOREACH(sp, spl, node) - if (shaper_profile_id == sp->shaper_profile_id) - return sp; - - return NULL; -} - -static struct tm_shared_shaper * -tm_shared_shaper_search(struct rte_eth_dev *dev, uint32_t shared_shaper_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_shared_shaper_list *ssl = &p->soft.tm.h.shared_shapers; - struct tm_shared_shaper *ss; - - TAILQ_FOREACH(ss, ssl, node) - if (shared_shaper_id == ss->shared_shaper_id) - return ss; - - return NULL; -} - -static struct tm_wred_profile * -tm_wred_profile_search(struct rte_eth_dev *dev, uint32_t wred_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_wred_profile_list *wpl = &p->soft.tm.h.wred_profiles; - struct tm_wred_profile *wp; - - TAILQ_FOREACH(wp, wpl, node) - if (wred_profile_id == wp->wred_profile_id) - return wp; - - return NULL; -} - -static struct tm_node * -tm_node_search(struct rte_eth_dev *dev, uint32_t node_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *n; - - TAILQ_FOREACH(n, nl, node) - if (n->node_id == node_id) - return n; - - return NULL; -} - -static struct tm_node * -tm_root_node_present(struct rte_eth_dev *dev) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *n; - - TAILQ_FOREACH(n, nl, node) - if (n->parent_node_id == RTE_TM_NODE_ID_NULL) - return n; - - return NULL; -} - -static uint32_t -tm_node_subport_id(struct rte_eth_dev *dev, struct tm_node *subport_node) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *ns; - uint32_t subport_id; - - subport_id = 0; - TAILQ_FOREACH(ns, nl, node) { - if (ns->level != TM_NODE_LEVEL_SUBPORT) - continue; - - if (ns->node_id == subport_node->node_id) - return subport_id; - - subport_id++; - } - - return UINT32_MAX; -} - -static uint32_t -tm_node_pipe_id(struct rte_eth_dev *dev, struct tm_node *pipe_node) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *np; - uint32_t pipe_id; - - pipe_id = 0; - TAILQ_FOREACH(np, nl, node) { - if (np->level != TM_NODE_LEVEL_PIPE || - np->parent_node_id != pipe_node->parent_node_id) - continue; - - if (np->node_id == pipe_node->node_id) - return pipe_id; - - pipe_id++; - } - - return UINT32_MAX; -} - -static uint32_t -tm_node_tc_id(struct rte_eth_dev *dev __rte_unused, struct tm_node *tc_node) -{ - return tc_node->priority; -} - -static uint32_t -tm_node_queue_id(struct rte_eth_dev *dev, struct tm_node *queue_node) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *nq; - uint32_t queue_id; - - queue_id = 0; - TAILQ_FOREACH(nq, nl, node) { - if (nq->level != TM_NODE_LEVEL_QUEUE || - nq->parent_node_id != queue_node->parent_node_id) - continue; - - if (nq->node_id == queue_node->node_id) - return queue_id; - - queue_id++; - } - - return UINT32_MAX; -} - -static uint32_t -tm_level_get_max_nodes(struct rte_eth_dev *dev, enum tm_node_level level) -{ - struct pmd_internals *p = dev->data->dev_private; - uint32_t n_queues_max = p->params.tm.n_queues; - uint32_t n_tc_max = - (n_queues_max * RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE) - / RTE_SCHED_QUEUES_PER_PIPE; - uint32_t n_pipes_max = n_tc_max / RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; - uint32_t n_subports_max = n_pipes_max; - uint32_t n_root_max = 1; - - switch (level) { - case TM_NODE_LEVEL_PORT: - return n_root_max; - case TM_NODE_LEVEL_SUBPORT: - return n_subports_max; - case TM_NODE_LEVEL_PIPE: - return n_pipes_max; - case TM_NODE_LEVEL_TC: - return n_tc_max; - case TM_NODE_LEVEL_QUEUE: - default: - return n_queues_max; - } -} - -/* Traffic manager node type get */ -static int -pmd_tm_node_type_get(struct rte_eth_dev *dev, - uint32_t node_id, - int *is_leaf, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - - if (is_leaf == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - - if (node_id == RTE_TM_NODE_ID_NULL || - (tm_node_search(dev, node_id) == NULL)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - *is_leaf = node_id < p->params.tm.n_queues; - - return 0; -} - -#ifdef RTE_SCHED_CMAN -#define WRED_SUPPORTED 1 -#else -#define WRED_SUPPORTED 0 -#endif - -#define STATS_MASK_DEFAULT \ - (RTE_TM_STATS_N_PKTS | \ - RTE_TM_STATS_N_BYTES | \ - RTE_TM_STATS_N_PKTS_GREEN_DROPPED | \ - RTE_TM_STATS_N_BYTES_GREEN_DROPPED) - -#define STATS_MASK_QUEUE \ - (STATS_MASK_DEFAULT | \ - RTE_TM_STATS_N_PKTS_QUEUED) - -static const struct rte_tm_capabilities tm_cap = { - .n_nodes_max = UINT32_MAX, - .n_levels_max = TM_NODE_LEVEL_MAX, - - .non_leaf_nodes_identical = 0, - .leaf_nodes_identical = 1, - - .shaper_n_max = UINT32_MAX, - .shaper_private_n_max = UINT32_MAX, - .shaper_private_dual_rate_n_max = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - - .shaper_shared_n_max = UINT32_MAX, - .shaper_shared_n_nodes_per_shaper_max = UINT32_MAX, - .shaper_shared_n_shapers_per_node_max = 1, - .shaper_shared_dual_rate_n_max = 0, - .shaper_shared_rate_min = 1, - .shaper_shared_rate_max = UINT32_MAX, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 1, - - .shaper_pkt_length_adjust_min = RTE_TM_ETH_FRAMING_OVERHEAD_FCS, - .shaper_pkt_length_adjust_max = RTE_TM_ETH_FRAMING_OVERHEAD_FCS, - - .sched_n_children_max = UINT32_MAX, - .sched_sp_n_priorities_max = RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - .sched_wfq_n_children_per_group_max = UINT32_MAX, - .sched_wfq_n_groups_max = 1, - .sched_wfq_weight_max = UINT32_MAX, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 1, - - .cman_wred_packet_mode_supported = WRED_SUPPORTED, - .cman_wred_byte_mode_supported = 0, - .cman_head_drop_supported = 0, - .cman_wred_context_n_max = 0, - .cman_wred_context_private_n_max = 0, - .cman_wred_context_shared_n_max = 0, - .cman_wred_context_shared_n_nodes_per_context_max = 0, - .cman_wred_context_shared_n_contexts_per_node_max = 0, - - .mark_vlan_dei_supported = {0, 0, 0}, - .mark_ip_ecn_tcp_supported = {0, 0, 0}, - .mark_ip_ecn_sctp_supported = {0, 0, 0}, - .mark_ip_dscp_supported = {0, 0, 0}, - - .dynamic_update_mask = 0, - - .stats_mask = STATS_MASK_QUEUE, -}; - -/* Traffic manager capabilities get */ -static int -pmd_tm_capabilities_get(struct rte_eth_dev *dev __rte_unused, - struct rte_tm_capabilities *cap, - struct rte_tm_error *error) -{ - if (cap == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_CAPABILITIES, - NULL, - rte_strerror(EINVAL)); - - memcpy(cap, &tm_cap, sizeof(*cap)); - - cap->n_nodes_max = tm_level_get_max_nodes(dev, TM_NODE_LEVEL_PORT) + - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_SUBPORT) + - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_PIPE) + - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_TC) + - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_QUEUE); - - cap->shaper_private_n_max = - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_PORT) + - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_SUBPORT) + - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_PIPE) + - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_TC); - - cap->shaper_shared_n_max = RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE * - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_SUBPORT); - - cap->shaper_n_max = cap->shaper_private_n_max + - cap->shaper_shared_n_max; - - cap->shaper_shared_n_nodes_per_shaper_max = - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_PIPE); - - cap->sched_n_children_max = RTE_MAX( - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_PIPE), - (uint32_t)RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE); - - cap->sched_wfq_n_children_per_group_max = cap->sched_n_children_max; - - if (WRED_SUPPORTED) - cap->cman_wred_context_private_n_max = - tm_level_get_max_nodes(dev, TM_NODE_LEVEL_QUEUE); - - cap->cman_wred_context_n_max = cap->cman_wred_context_private_n_max + - cap->cman_wred_context_shared_n_max; - - return 0; -} - -static const struct rte_tm_level_capabilities tm_level_cap[] = { - [TM_NODE_LEVEL_PORT] = { - .n_nodes_max = 1, - .n_nodes_nonleaf_max = 1, - .n_nodes_leaf_max = 0, - .non_leaf_nodes_identical = 1, - .leaf_nodes_identical = 0, - - {.nonleaf = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - .sched_n_children_max = UINT32_MAX, - .sched_sp_n_priorities_max = 1, - .sched_wfq_n_children_per_group_max = UINT32_MAX, - .sched_wfq_n_groups_max = 1, - .sched_wfq_weight_max = 1, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 1, - - .stats_mask = STATS_MASK_DEFAULT, - } }, - }, - - [TM_NODE_LEVEL_SUBPORT] = { - .n_nodes_max = UINT32_MAX, - .n_nodes_nonleaf_max = UINT32_MAX, - .n_nodes_leaf_max = 0, - .non_leaf_nodes_identical = 1, - .leaf_nodes_identical = 0, - - {.nonleaf = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - .sched_n_children_max = UINT32_MAX, - .sched_sp_n_priorities_max = 1, - .sched_wfq_n_children_per_group_max = UINT32_MAX, - .sched_wfq_n_groups_max = 1, - .sched_wfq_weight_max = UINT32_MAX, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 1, - - .stats_mask = STATS_MASK_DEFAULT, - } }, - }, - - [TM_NODE_LEVEL_PIPE] = { - .n_nodes_max = UINT32_MAX, - .n_nodes_nonleaf_max = UINT32_MAX, - .n_nodes_leaf_max = 0, - .non_leaf_nodes_identical = 1, - .leaf_nodes_identical = 0, - - {.nonleaf = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - .sched_n_children_max = - RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - .sched_sp_n_priorities_max = - RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - .sched_wfq_n_children_per_group_max = 1, - .sched_wfq_n_groups_max = 0, - .sched_wfq_weight_max = 1, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 0, - - .stats_mask = STATS_MASK_DEFAULT, - } }, - }, - - [TM_NODE_LEVEL_TC] = { - .n_nodes_max = UINT32_MAX, - .n_nodes_nonleaf_max = UINT32_MAX, - .n_nodes_leaf_max = 0, - .non_leaf_nodes_identical = 1, - .leaf_nodes_identical = 0, - - {.nonleaf = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 1, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 1, - - .sched_n_children_max = - RTE_SCHED_BE_QUEUES_PER_PIPE, - .sched_sp_n_priorities_max = 1, - .sched_wfq_n_children_per_group_max = - RTE_SCHED_BE_QUEUES_PER_PIPE, - .sched_wfq_n_groups_max = 1, - .sched_wfq_weight_max = UINT32_MAX, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 1, - - .stats_mask = STATS_MASK_DEFAULT, - } }, - }, - - [TM_NODE_LEVEL_QUEUE] = { - .n_nodes_max = UINT32_MAX, - .n_nodes_nonleaf_max = 0, - .n_nodes_leaf_max = UINT32_MAX, - .non_leaf_nodes_identical = 0, - .leaf_nodes_identical = 1, - - {.leaf = { - .shaper_private_supported = 0, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 0, - .shaper_private_rate_max = 0, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 0, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - .cman_head_drop_supported = 0, - .cman_wred_packet_mode_supported = WRED_SUPPORTED, - .cman_wred_byte_mode_supported = 0, - .cman_wred_context_private_supported = WRED_SUPPORTED, - .cman_wred_context_shared_n_max = 0, - - .stats_mask = STATS_MASK_QUEUE, - } }, - }, -}; - -/* Traffic manager level capabilities get */ -static int -pmd_tm_level_capabilities_get(struct rte_eth_dev *dev __rte_unused, - uint32_t level_id, - struct rte_tm_level_capabilities *cap, - struct rte_tm_error *error) -{ - if (cap == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_CAPABILITIES, - NULL, - rte_strerror(EINVAL)); - - if (level_id >= TM_NODE_LEVEL_MAX) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_LEVEL_ID, - NULL, - rte_strerror(EINVAL)); - - memcpy(cap, &tm_level_cap[level_id], sizeof(*cap)); - - switch (level_id) { - case TM_NODE_LEVEL_PORT: - cap->nonleaf.sched_n_children_max = - tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_SUBPORT); - cap->nonleaf.sched_wfq_n_children_per_group_max = - cap->nonleaf.sched_n_children_max; - break; - - case TM_NODE_LEVEL_SUBPORT: - cap->n_nodes_max = tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_SUBPORT); - cap->n_nodes_nonleaf_max = cap->n_nodes_max; - cap->nonleaf.sched_n_children_max = - tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_PIPE); - cap->nonleaf.sched_wfq_n_children_per_group_max = - cap->nonleaf.sched_n_children_max; - break; - - case TM_NODE_LEVEL_PIPE: - cap->n_nodes_max = tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_PIPE); - cap->n_nodes_nonleaf_max = cap->n_nodes_max; - break; - - case TM_NODE_LEVEL_TC: - cap->n_nodes_max = tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_TC); - cap->n_nodes_nonleaf_max = cap->n_nodes_max; - break; - - case TM_NODE_LEVEL_QUEUE: - default: - cap->n_nodes_max = tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_QUEUE); - cap->n_nodes_leaf_max = cap->n_nodes_max; - break; - } - - return 0; -} - -static const struct rte_tm_node_capabilities tm_node_cap[] = { - [TM_NODE_LEVEL_PORT] = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - {.nonleaf = { - .sched_n_children_max = UINT32_MAX, - .sched_sp_n_priorities_max = 1, - .sched_wfq_n_children_per_group_max = UINT32_MAX, - .sched_wfq_n_groups_max = 1, - .sched_wfq_weight_max = 1, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 1, - } }, - - .stats_mask = STATS_MASK_DEFAULT, - }, - - [TM_NODE_LEVEL_SUBPORT] = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - {.nonleaf = { - .sched_n_children_max = UINT32_MAX, - .sched_sp_n_priorities_max = 1, - .sched_wfq_n_children_per_group_max = UINT32_MAX, - .sched_wfq_n_groups_max = 1, - .sched_wfq_weight_max = UINT32_MAX, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 1, - } }, - - .stats_mask = STATS_MASK_DEFAULT, - }, - - [TM_NODE_LEVEL_PIPE] = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - {.nonleaf = { - .sched_n_children_max = - RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - .sched_sp_n_priorities_max = - RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - .sched_wfq_n_children_per_group_max = 1, - .sched_wfq_n_groups_max = 0, - .sched_wfq_weight_max = 1, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 0, - } }, - - .stats_mask = STATS_MASK_DEFAULT, - }, - - [TM_NODE_LEVEL_TC] = { - .shaper_private_supported = 1, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 1, - .shaper_private_rate_max = UINT32_MAX, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 1, - .shaper_shared_n_max = 1, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 1, - - {.nonleaf = { - .sched_n_children_max = - RTE_SCHED_BE_QUEUES_PER_PIPE, - .sched_sp_n_priorities_max = 1, - .sched_wfq_n_children_per_group_max = - RTE_SCHED_BE_QUEUES_PER_PIPE, - .sched_wfq_n_groups_max = 1, - .sched_wfq_weight_max = UINT32_MAX, - .sched_wfq_packet_mode_supported = 0, - .sched_wfq_byte_mode_supported = 1, - } }, - - .stats_mask = STATS_MASK_DEFAULT, - }, - - [TM_NODE_LEVEL_QUEUE] = { - .shaper_private_supported = 0, - .shaper_private_dual_rate_supported = 0, - .shaper_private_rate_min = 0, - .shaper_private_rate_max = 0, - .shaper_private_packet_mode_supported = 0, - .shaper_private_byte_mode_supported = 0, - .shaper_shared_n_max = 0, - .shaper_shared_packet_mode_supported = 0, - .shaper_shared_byte_mode_supported = 0, - - - {.leaf = { - .cman_head_drop_supported = 0, - .cman_wred_packet_mode_supported = WRED_SUPPORTED, - .cman_wred_byte_mode_supported = 0, - .cman_wred_context_private_supported = WRED_SUPPORTED, - .cman_wred_context_shared_n_max = 0, - } }, - - .stats_mask = STATS_MASK_QUEUE, - }, -}; - -/* Traffic manager node capabilities get */ -static int -pmd_tm_node_capabilities_get(struct rte_eth_dev *dev __rte_unused, - uint32_t node_id, - struct rte_tm_node_capabilities *cap, - struct rte_tm_error *error) -{ - struct tm_node *tm_node; - - if (cap == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_CAPABILITIES, - NULL, - rte_strerror(EINVAL)); - - tm_node = tm_node_search(dev, node_id); - if (tm_node == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - memcpy(cap, &tm_node_cap[tm_node->level], sizeof(*cap)); - - switch (tm_node->level) { - case TM_NODE_LEVEL_PORT: - cap->nonleaf.sched_n_children_max = - tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_SUBPORT); - cap->nonleaf.sched_wfq_n_children_per_group_max = - cap->nonleaf.sched_n_children_max; - break; - - case TM_NODE_LEVEL_SUBPORT: - cap->nonleaf.sched_n_children_max = - tm_level_get_max_nodes(dev, - TM_NODE_LEVEL_PIPE); - cap->nonleaf.sched_wfq_n_children_per_group_max = - cap->nonleaf.sched_n_children_max; - break; - - case TM_NODE_LEVEL_PIPE: - case TM_NODE_LEVEL_TC: - case TM_NODE_LEVEL_QUEUE: - default: - break; - } - - return 0; -} - -static int -shaper_profile_check(struct rte_eth_dev *dev, - uint32_t shaper_profile_id, - struct rte_tm_shaper_params *profile, - struct rte_tm_error *error) -{ - struct tm_shaper_profile *sp; - - /* Shaper profile ID must not be NONE. */ - if (shaper_profile_id == RTE_TM_SHAPER_PROFILE_ID_NONE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Shaper profile must not exist. */ - sp = tm_shaper_profile_search(dev, shaper_profile_id); - if (sp) - return -rte_tm_error_set(error, - EEXIST, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EEXIST)); - - /* Profile must not be NULL. */ - if (profile == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE, - NULL, - rte_strerror(EINVAL)); - - /* Peak rate: non-zero, 32-bit */ - if (profile->peak.rate == 0 || - profile->peak.rate >= UINT32_MAX) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_PEAK_RATE, - NULL, - rte_strerror(EINVAL)); - - /* Peak size: non-zero, 32-bit */ - if (profile->peak.size == 0 || - profile->peak.size >= UINT32_MAX) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_PEAK_SIZE, - NULL, - rte_strerror(EINVAL)); - - /* Dual-rate profiles are not supported. */ - if (profile->committed.rate != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_COMMITTED_RATE, - NULL, - rte_strerror(EINVAL)); - - /* Packet length adjust: 24 bytes */ - if (profile->pkt_length_adjust != RTE_TM_ETH_FRAMING_OVERHEAD_FCS) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_PKT_ADJUST_LEN, - NULL, - rte_strerror(EINVAL)); - - /* Packet mode is not supported. */ - if (profile->packet_mode != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_PACKET_MODE, - NULL, - rte_strerror(EINVAL)); - return 0; -} - -/* Traffic manager shaper profile add */ -static int -pmd_tm_shaper_profile_add(struct rte_eth_dev *dev, - uint32_t shaper_profile_id, - struct rte_tm_shaper_params *profile, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_shaper_profile_list *spl = &p->soft.tm.h.shaper_profiles; - struct tm_shaper_profile *sp; - int status; - - /* Check input params */ - status = shaper_profile_check(dev, shaper_profile_id, profile, error); - if (status) - return status; - - /* Memory allocation */ - sp = calloc(1, sizeof(struct tm_shaper_profile)); - if (sp == NULL) - return -rte_tm_error_set(error, - ENOMEM, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(ENOMEM)); - - /* Fill in */ - sp->shaper_profile_id = shaper_profile_id; - memcpy(&sp->params, profile, sizeof(sp->params)); - - /* Add to list */ - TAILQ_INSERT_TAIL(spl, sp, node); - p->soft.tm.h.n_shaper_profiles++; - - return 0; -} - -/* Traffic manager shaper profile delete */ -static int -pmd_tm_shaper_profile_delete(struct rte_eth_dev *dev, - uint32_t shaper_profile_id, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_shaper_profile *sp; - - /* Check existing */ - sp = tm_shaper_profile_search(dev, shaper_profile_id); - if (sp == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Check unused */ - if (sp->n_users) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EBUSY)); - - /* Remove from list */ - TAILQ_REMOVE(&p->soft.tm.h.shaper_profiles, sp, node); - p->soft.tm.h.n_shaper_profiles--; - free(sp); - - return 0; -} - -static struct tm_node * -tm_shared_shaper_get_tc(struct rte_eth_dev *dev, - struct tm_shared_shaper *ss) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *n; - - /* Subport: each TC uses shared shaper */ - TAILQ_FOREACH(n, nl, node) { - if (n->level != TM_NODE_LEVEL_TC || - n->params.n_shared_shapers == 0 || - n->params.shared_shaper_id[0] != ss->shared_shaper_id) - continue; - - return n; - } - - return NULL; -} - -static int -subport_profile_exists(struct rte_eth_dev *dev, - struct rte_sched_subport_profile_params *sp, - uint32_t *subport_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - uint32_t i; - - for (i = 0; i < t->n_subport_profiles; i++) - if (memcmp(&t->subport_profile[i], sp, sizeof(*sp)) == 0) { - if (subport_profile_id) - *subport_profile_id = i; - return 1; - } - - return 0; -} - -static int -update_subport_tc_rate(struct rte_eth_dev *dev, - struct tm_node *nt, - struct tm_shared_shaper *ss, - struct tm_shaper_profile *sp_new) -{ - struct rte_sched_subport_profile_params subport_profile; - struct pmd_internals *p = dev->data->dev_private; - uint32_t tc_id = tm_node_tc_id(dev, nt); - struct tm_node *np = nt->parent_node; - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - struct tm_params *t = &p->soft.tm.params; - uint32_t subport_profile_id; - struct tm_shaper_profile *sp_old = tm_shaper_profile_search(dev, - ss->shaper_profile_id); - - if (subport_id >= TM_MAX_SUBPORT_PROFILE) - return -1; - - subport_profile_id = t->subport_to_profile[subport_id]; - - /* Derive new subport configuration. */ - memcpy(&subport_profile, - &p->soft.tm.params.subport_profile[subport_profile_id], - sizeof(subport_profile)); - subport_profile.tc_rate[tc_id] = sp_new->params.peak.rate; - - /* Update the subport configuration. */ - if (rte_sched_subport_config(SCHED(p), - subport_id, NULL, subport_profile_id)) - return -1; - - /* Commit changes. */ - sp_old->n_users--; - - ss->shaper_profile_id = sp_new->shaper_profile_id; - sp_new->n_users++; - - memcpy(&p->soft.tm.params.subport_profile[subport_profile_id], - &subport_profile, - sizeof(subport_profile)); - - return 0; -} - -/* Traffic manager shared shaper add/update */ -static int -pmd_tm_shared_shaper_add_update(struct rte_eth_dev *dev, - uint32_t shared_shaper_id, - uint32_t shaper_profile_id, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_shared_shaper *ss; - struct tm_shaper_profile *sp; - struct tm_node *nt; - - /* Shaper profile must be valid. */ - sp = tm_shaper_profile_search(dev, shaper_profile_id); - if (sp == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /** - * Add new shared shaper - */ - ss = tm_shared_shaper_search(dev, shared_shaper_id); - if (ss == NULL) { - struct tm_shared_shaper_list *ssl = - &p->soft.tm.h.shared_shapers; - - /* Hierarchy must not be frozen */ - if (p->soft.tm.hierarchy_frozen) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - /* Memory allocation */ - ss = calloc(1, sizeof(struct tm_shared_shaper)); - if (ss == NULL) - return -rte_tm_error_set(error, - ENOMEM, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(ENOMEM)); - - /* Fill in */ - ss->shared_shaper_id = shared_shaper_id; - ss->shaper_profile_id = shaper_profile_id; - - /* Add to list */ - TAILQ_INSERT_TAIL(ssl, ss, node); - p->soft.tm.h.n_shared_shapers++; - - return 0; - } - - /** - * Update existing shared shaper - */ - /* Hierarchy must be frozen (run-time update) */ - if (p->soft.tm.hierarchy_frozen == 0) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - - /* Propagate change. */ - nt = tm_shared_shaper_get_tc(dev, ss); - if (update_subport_tc_rate(dev, nt, ss, sp)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - - return 0; -} - -/* Traffic manager shared shaper delete */ -static int -pmd_tm_shared_shaper_delete(struct rte_eth_dev *dev, - uint32_t shared_shaper_id, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_shared_shaper *ss; - - /* Check existing */ - ss = tm_shared_shaper_search(dev, shared_shaper_id); - if (ss == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHARED_SHAPER_ID, - NULL, - rte_strerror(EINVAL)); - - /* Check unused */ - if (ss->n_users) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_SHARED_SHAPER_ID, - NULL, - rte_strerror(EBUSY)); - - /* Remove from list */ - TAILQ_REMOVE(&p->soft.tm.h.shared_shapers, ss, node); - p->soft.tm.h.n_shared_shapers--; - free(ss); - - return 0; -} - -static int -wred_profile_check(struct rte_eth_dev *dev, - uint32_t wred_profile_id, - struct rte_tm_wred_params *profile, - struct rte_tm_error *error) -{ - struct tm_wred_profile *wp; - enum rte_color color; - - /* WRED profile ID must not be NONE. */ - if (wred_profile_id == RTE_TM_WRED_PROFILE_ID_NONE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_WRED_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* WRED profile must not exist. */ - wp = tm_wred_profile_search(dev, wred_profile_id); - if (wp) - return -rte_tm_error_set(error, - EEXIST, - RTE_TM_ERROR_TYPE_WRED_PROFILE_ID, - NULL, - rte_strerror(EEXIST)); - - /* Profile must not be NULL. */ - if (profile == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_WRED_PROFILE, - NULL, - rte_strerror(EINVAL)); - - /* WRED profile should be in packet mode */ - if (profile->packet_mode == 0) - return -rte_tm_error_set(error, - ENOTSUP, - RTE_TM_ERROR_TYPE_WRED_PROFILE, - NULL, - rte_strerror(ENOTSUP)); - - /* min_th <= max_th, max_th > 0 */ - for (color = RTE_COLOR_GREEN; color < RTE_COLORS; color++) { - uint32_t min_th = profile->red_params[color].min_th; - uint32_t max_th = profile->red_params[color].max_th; - - if (min_th > max_th || - max_th == 0 || - min_th > UINT16_MAX || - max_th > UINT16_MAX) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_WRED_PROFILE, - NULL, - rte_strerror(EINVAL)); - } - - return 0; -} - -/* Traffic manager WRED profile add */ -static int -pmd_tm_wred_profile_add(struct rte_eth_dev *dev, - uint32_t wred_profile_id, - struct rte_tm_wred_params *profile, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_wred_profile_list *wpl = &p->soft.tm.h.wred_profiles; - struct tm_wred_profile *wp; - int status; - - /* Check input params */ - status = wred_profile_check(dev, wred_profile_id, profile, error); - if (status) - return status; - - /* Memory allocation */ - wp = calloc(1, sizeof(struct tm_wred_profile)); - if (wp == NULL) - return -rte_tm_error_set(error, - ENOMEM, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(ENOMEM)); - - /* Fill in */ - wp->wred_profile_id = wred_profile_id; - memcpy(&wp->params, profile, sizeof(wp->params)); - - /* Add to list */ - TAILQ_INSERT_TAIL(wpl, wp, node); - p->soft.tm.h.n_wred_profiles++; - - return 0; -} - -/* Traffic manager WRED profile delete */ -static int -pmd_tm_wred_profile_delete(struct rte_eth_dev *dev, - uint32_t wred_profile_id, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_wred_profile *wp; - - /* Check existing */ - wp = tm_wred_profile_search(dev, wred_profile_id); - if (wp == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_WRED_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Check unused */ - if (wp->n_users) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_WRED_PROFILE_ID, - NULL, - rte_strerror(EBUSY)); - - /* Remove from list */ - TAILQ_REMOVE(&p->soft.tm.h.wred_profiles, wp, node); - p->soft.tm.h.n_wred_profiles--; - free(wp); - - return 0; -} - -static int -node_add_check_port(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id __rte_unused, - uint32_t priority, - uint32_t weight, - uint32_t level_id __rte_unused, - struct rte_tm_node_params *params, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_shaper_profile *sp = tm_shaper_profile_search(dev, - params->shaper_profile_id); - - /* node type: non-leaf */ - if (node_id < p->params.tm.n_queues) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Priority must be 0 */ - if (priority != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PRIORITY, - NULL, - rte_strerror(EINVAL)); - - /* Weight must be 1 */ - if (weight != 1) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - - /* Shaper must be valid */ - if (params->shaper_profile_id == RTE_TM_SHAPER_PROFILE_ID_NONE || - sp == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* No shared shapers */ - if (params->n_shared_shapers != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SHARED_SHAPERS, - NULL, - rte_strerror(EINVAL)); - - /* Number of SP priorities must be 1 */ - if (params->nonleaf.n_sp_priorities != 1) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SP_PRIORITIES, - NULL, - rte_strerror(EINVAL)); - - /* Stats */ - if (params->stats_mask & ~STATS_MASK_DEFAULT) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_STATS, - NULL, - rte_strerror(EINVAL)); - - return 0; -} - -static int -node_add_check_subport(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id __rte_unused, - uint32_t priority, - uint32_t weight, - uint32_t level_id __rte_unused, - struct rte_tm_node_params *params, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - - /* node type: non-leaf */ - if (node_id < p->params.tm.n_queues) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Priority must be 0 */ - if (priority != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PRIORITY, - NULL, - rte_strerror(EINVAL)); - - /* Weight must be 1 */ - if (weight != 1) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - - /* Shaper must be valid */ - if (params->shaper_profile_id == RTE_TM_SHAPER_PROFILE_ID_NONE || - (!tm_shaper_profile_search(dev, params->shaper_profile_id))) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* No shared shapers */ - if (params->n_shared_shapers != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SHARED_SHAPERS, - NULL, - rte_strerror(EINVAL)); - - /* Number of SP priorities must be 1 */ - if (params->nonleaf.n_sp_priorities != 1) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SP_PRIORITIES, - NULL, - rte_strerror(EINVAL)); - - /* Stats */ - if (params->stats_mask & ~STATS_MASK_DEFAULT) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_STATS, - NULL, - rte_strerror(EINVAL)); - - return 0; -} - -static int -node_add_check_pipe(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id __rte_unused, - uint32_t priority, - uint32_t weight __rte_unused, - uint32_t level_id __rte_unused, - struct rte_tm_node_params *params, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - - /* node type: non-leaf */ - if (node_id < p->params.tm.n_queues) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Priority must be 0 */ - if (priority != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PRIORITY, - NULL, - rte_strerror(EINVAL)); - - /* Shaper must be valid */ - if (params->shaper_profile_id == RTE_TM_SHAPER_PROFILE_ID_NONE || - (!tm_shaper_profile_search(dev, params->shaper_profile_id))) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* No shared shapers */ - if (params->n_shared_shapers != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SHARED_SHAPERS, - NULL, - rte_strerror(EINVAL)); - - /* Number of SP priorities must be 4 */ - if (params->nonleaf.n_sp_priorities != - RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SP_PRIORITIES, - NULL, - rte_strerror(EINVAL)); - - /* WFQ mode must be byte mode */ - if (params->nonleaf.wfq_weight_mode != NULL && - params->nonleaf.wfq_weight_mode[0] != 0 && - params->nonleaf.wfq_weight_mode[1] != 0 && - params->nonleaf.wfq_weight_mode[2] != 0 && - params->nonleaf.wfq_weight_mode[3] != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_WFQ_WEIGHT_MODE, - NULL, - rte_strerror(EINVAL)); - - /* Stats */ - if (params->stats_mask & ~STATS_MASK_DEFAULT) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_STATS, - NULL, - rte_strerror(EINVAL)); - - return 0; -} - -static int -node_add_check_tc(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id __rte_unused, - uint32_t priority __rte_unused, - uint32_t weight, - uint32_t level_id __rte_unused, - struct rte_tm_node_params *params, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - - /* node type: non-leaf */ - if (node_id < p->params.tm.n_queues) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Weight must be 1 */ - if (weight != 1) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - - /* Shaper must be valid */ - if (params->shaper_profile_id == RTE_TM_SHAPER_PROFILE_ID_NONE || - (!tm_shaper_profile_search(dev, params->shaper_profile_id))) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Single valid shared shaper */ - if (params->n_shared_shapers > 1) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SHARED_SHAPERS, - NULL, - rte_strerror(EINVAL)); - - if (params->n_shared_shapers == 1 && - (params->shared_shaper_id == NULL || - (!tm_shared_shaper_search(dev, params->shared_shaper_id[0])))) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_SHARED_SHAPER_ID, - NULL, - rte_strerror(EINVAL)); - - /* Number of priorities must be 1 */ - if (params->nonleaf.n_sp_priorities != 1) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SP_PRIORITIES, - NULL, - rte_strerror(EINVAL)); - - /* Stats */ - if (params->stats_mask & ~STATS_MASK_DEFAULT) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_STATS, - NULL, - rte_strerror(EINVAL)); - - return 0; -} - -static int -node_add_check_queue(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id __rte_unused, - uint32_t priority, - uint32_t weight __rte_unused, - uint32_t level_id __rte_unused, - struct rte_tm_node_params *params, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - - /* node type: leaf */ - if (node_id >= p->params.tm.n_queues) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Priority must be 0 */ - if (priority != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PRIORITY, - NULL, - rte_strerror(EINVAL)); - - /* No shaper */ - if (params->shaper_profile_id != RTE_TM_SHAPER_PROFILE_ID_NONE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_SHAPER_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* No shared shapers */ - if (params->n_shared_shapers != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SHARED_SHAPERS, - NULL, - rte_strerror(EINVAL)); - - /* Congestion management must not be head drop */ - if (params->leaf.cman == RTE_TM_CMAN_HEAD_DROP) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_CMAN, - NULL, - rte_strerror(EINVAL)); - - /* Congestion management set to WRED */ - if (params->leaf.cman == RTE_TM_CMAN_WRED) { - uint32_t wred_profile_id = params->leaf.wred.wred_profile_id; - struct tm_wred_profile *wp = tm_wred_profile_search(dev, - wred_profile_id); - - /* WRED profile (for private WRED context) must be valid */ - if (wred_profile_id == RTE_TM_WRED_PROFILE_ID_NONE || - wp == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_WRED_PROFILE_ID, - NULL, - rte_strerror(EINVAL)); - - /* No shared WRED contexts */ - if (params->leaf.wred.n_shared_wred_contexts != 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_N_SHARED_WRED_CONTEXTS, - NULL, - rte_strerror(EINVAL)); - } - - /* Stats */ - if (params->stats_mask & ~STATS_MASK_QUEUE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS_STATS, - NULL, - rte_strerror(EINVAL)); - - return 0; -} - -static int -node_add_check(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id, - uint32_t priority, - uint32_t weight, - uint32_t level_id, - struct rte_tm_node_params *params, - struct rte_tm_error *error) -{ - struct tm_node *pn; - uint32_t level; - int status; - - /* node_id, parent_node_id: - * -node_id must not be RTE_TM_NODE_ID_NULL - * -node_id must not be in use - * -root node add (parent_node_id is RTE_TM_NODE_ID_NULL): - * -root node must not exist - * -non-root node add (parent_node_id is not RTE_TM_NODE_ID_NULL): - * -parent_node_id must be valid - */ - if (node_id == RTE_TM_NODE_ID_NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - if (tm_node_search(dev, node_id)) - return -rte_tm_error_set(error, - EEXIST, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EEXIST)); - - if (parent_node_id == RTE_TM_NODE_ID_NULL) { - pn = NULL; - if (tm_root_node_present(dev)) - return -rte_tm_error_set(error, - EEXIST, - RTE_TM_ERROR_TYPE_NODE_PARENT_NODE_ID, - NULL, - rte_strerror(EEXIST)); - } else { - pn = tm_node_search(dev, parent_node_id); - if (pn == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARENT_NODE_ID, - NULL, - rte_strerror(EINVAL)); - } - - /* priority: must be 0 .. 3 */ - if (priority >= RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PRIORITY, - NULL, - rte_strerror(EINVAL)); - - /* weight: must be 1 .. 255 */ - if (weight == 0 || weight >= UINT8_MAX) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - - /* level_id: if valid, then - * -root node add (parent_node_id is RTE_TM_NODE_ID_NULL): - * -level_id must be zero - * -non-root node add (parent_node_id is not RTE_TM_NODE_ID_NULL): - * -level_id must be parent level ID plus one - */ - level = (pn == NULL) ? 0 : pn->level + 1; - if (level_id != RTE_TM_NODE_LEVEL_ID_ANY && level_id != level) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_LEVEL_ID, - NULL, - rte_strerror(EINVAL)); - - /* params: must not be NULL */ - if (params == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARAMS, - NULL, - rte_strerror(EINVAL)); - - /* params: per level checks */ - switch (level) { - case TM_NODE_LEVEL_PORT: - status = node_add_check_port(dev, node_id, - parent_node_id, priority, weight, level_id, - params, error); - if (status) - return status; - break; - - case TM_NODE_LEVEL_SUBPORT: - status = node_add_check_subport(dev, node_id, - parent_node_id, priority, weight, level_id, - params, error); - if (status) - return status; - break; - - case TM_NODE_LEVEL_PIPE: - status = node_add_check_pipe(dev, node_id, - parent_node_id, priority, weight, level_id, - params, error); - if (status) - return status; - break; - - case TM_NODE_LEVEL_TC: - status = node_add_check_tc(dev, node_id, - parent_node_id, priority, weight, level_id, - params, error); - if (status) - return status; - break; - - case TM_NODE_LEVEL_QUEUE: - status = node_add_check_queue(dev, node_id, - parent_node_id, priority, weight, level_id, - params, error); - if (status) - return status; - break; - - default: - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_LEVEL_ID, - NULL, - rte_strerror(EINVAL)); - } - - return 0; -} - -/* Traffic manager node add */ -static int -pmd_tm_node_add(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id, - uint32_t priority, - uint32_t weight, - uint32_t level_id, - struct rte_tm_node_params *params, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *n; - uint32_t i; - int status; - - /* Checks */ - if (p->soft.tm.hierarchy_frozen) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - status = node_add_check(dev, node_id, parent_node_id, priority, weight, - level_id, params, error); - if (status) - return status; - - /* Memory allocation */ - n = calloc(1, sizeof(struct tm_node)); - if (n == NULL) - return -rte_tm_error_set(error, - ENOMEM, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(ENOMEM)); - - /* Fill in */ - n->node_id = node_id; - n->parent_node_id = parent_node_id; - n->priority = priority; - n->weight = weight; - - if (parent_node_id != RTE_TM_NODE_ID_NULL) { - n->parent_node = tm_node_search(dev, parent_node_id); - n->level = n->parent_node->level + 1; - } - - if (params->shaper_profile_id != RTE_TM_SHAPER_PROFILE_ID_NONE) - n->shaper_profile = tm_shaper_profile_search(dev, - params->shaper_profile_id); - - if (n->level == TM_NODE_LEVEL_QUEUE && - params->leaf.cman == RTE_TM_CMAN_WRED) - n->wred_profile = tm_wred_profile_search(dev, - params->leaf.wred.wred_profile_id); - - memcpy(&n->params, params, sizeof(n->params)); - - /* Add to list */ - TAILQ_INSERT_TAIL(nl, n, node); - p->soft.tm.h.n_nodes++; - - /* Update dependencies */ - if (n->parent_node) - n->parent_node->n_children++; - - if (n->shaper_profile) - n->shaper_profile->n_users++; - - for (i = 0; i < params->n_shared_shapers; i++) { - struct tm_shared_shaper *ss; - - ss = tm_shared_shaper_search(dev, params->shared_shaper_id[i]); - ss->n_users++; - } - - if (n->wred_profile) - n->wred_profile->n_users++; - - p->soft.tm.h.n_tm_nodes[n->level]++; - - return 0; -} - -/* Traffic manager node delete */ -static int -pmd_tm_node_delete(struct rte_eth_dev *dev, - uint32_t node_id, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node *n; - uint32_t i; - - /* Check hierarchy changes are currently allowed */ - if (p->soft.tm.hierarchy_frozen) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - /* Check existing */ - n = tm_node_search(dev, node_id); - if (n == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Check unused */ - if (n->n_children) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EBUSY)); - - /* Update dependencies */ - p->soft.tm.h.n_tm_nodes[n->level]--; - - if (n->wred_profile) - n->wred_profile->n_users--; - - for (i = 0; i < n->params.n_shared_shapers; i++) { - struct tm_shared_shaper *ss; - - ss = tm_shared_shaper_search(dev, - n->params.shared_shaper_id[i]); - ss->n_users--; - } - - if (n->shaper_profile) - n->shaper_profile->n_users--; - - if (n->parent_node) - n->parent_node->n_children--; - - /* Remove from list */ - TAILQ_REMOVE(&p->soft.tm.h.nodes, n, node); - p->soft.tm.h.n_nodes--; - free(n); - - return 0; -} - - -static void -pipe_profile_build(struct rte_eth_dev *dev, - struct tm_node *np, - struct rte_sched_pipe_params *pp) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - struct tm_node_list *nl = &h->nodes; - struct tm_node *nt, *nq; - - memset(pp, 0, sizeof(*pp)); - - /* Pipe */ - pp->tb_rate = np->shaper_profile->params.peak.rate; - pp->tb_size = np->shaper_profile->params.peak.size; - - /* Traffic Class (TC) */ - pp->tc_period = PIPE_TC_PERIOD; - - pp->tc_ov_weight = np->weight; - - TAILQ_FOREACH(nt, nl, node) { - uint32_t queue_id = 0; - - if (nt->level != TM_NODE_LEVEL_TC || - nt->parent_node_id != np->node_id) - continue; - - pp->tc_rate[nt->priority] = - nt->shaper_profile->params.peak.rate; - - /* Queue */ - TAILQ_FOREACH(nq, nl, node) { - - if (nq->level != TM_NODE_LEVEL_QUEUE || - nq->parent_node_id != nt->node_id) - continue; - - if (nt->priority == RTE_SCHED_TRAFFIC_CLASS_BE) - pp->wrr_weights[queue_id] = nq->weight; - - queue_id++; - } - } -} - -static int -pipe_profile_free_exists(struct rte_eth_dev *dev, - uint32_t *pipe_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - - if (t->n_pipe_profiles < TM_MAX_PIPE_PROFILE) { - *pipe_profile_id = t->n_pipe_profiles; - return 1; - } - - return 0; -} - -static int -pipe_profile_exists(struct rte_eth_dev *dev, - struct rte_sched_pipe_params *pp, - uint32_t *pipe_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - uint32_t i; - - for (i = 0; i < t->n_pipe_profiles; i++) - if (memcmp(&t->pipe_profiles[i], pp, sizeof(*pp)) == 0) { - if (pipe_profile_id) - *pipe_profile_id = i; - return 1; - } - - return 0; -} - -static void -pipe_profile_install(struct rte_eth_dev *dev, - struct rte_sched_pipe_params *pp, - uint32_t pipe_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - - memcpy(&t->pipe_profiles[pipe_profile_id], pp, sizeof(*pp)); - t->n_pipe_profiles++; -} - -static void -pipe_profile_mark(struct rte_eth_dev *dev, - uint32_t subport_id, - uint32_t pipe_id, - uint32_t pipe_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - struct tm_params *t = &p->soft.tm.params; - uint32_t n_pipes_per_subport, pos; - - n_pipes_per_subport = h->n_tm_nodes[TM_NODE_LEVEL_PIPE] / - h->n_tm_nodes[TM_NODE_LEVEL_SUBPORT]; - pos = subport_id * n_pipes_per_subport + pipe_id; - - t->pipe_to_profile[pos] = pipe_profile_id; -} - -static struct rte_sched_pipe_params * -pipe_profile_get(struct rte_eth_dev *dev, struct tm_node *np) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - struct tm_params *t = &p->soft.tm.params; - uint32_t n_pipes_per_subport = h->n_tm_nodes[TM_NODE_LEVEL_PIPE] / - h->n_tm_nodes[TM_NODE_LEVEL_SUBPORT]; - - uint32_t subport_id = tm_node_subport_id(dev, np->parent_node); - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - uint32_t pos = subport_id * n_pipes_per_subport + pipe_id; - uint32_t pipe_profile_id = t->pipe_to_profile[pos]; - - return &t->pipe_profiles[pipe_profile_id]; -} - -static int -pipe_profiles_generate(struct rte_eth_dev *dev) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - struct tm_node_list *nl = &h->nodes; - struct tm_node *ns, *np; - uint32_t subport_id; - - /* Objective: Fill in the following fields in struct tm_params: - * - pipe_profiles - * - n_pipe_profiles - * - pipe_to_profile - */ - - subport_id = 0; - TAILQ_FOREACH(ns, nl, node) { - uint32_t pipe_id; - - if (ns->level != TM_NODE_LEVEL_SUBPORT) - continue; - - pipe_id = 0; - TAILQ_FOREACH(np, nl, node) { - struct rte_sched_pipe_params pp; - uint32_t pos; - - memset(&pp, 0, sizeof(pp)); - - if (np->level != TM_NODE_LEVEL_PIPE || - np->parent_node_id != ns->node_id) - continue; - - pipe_profile_build(dev, np, &pp); - - if (!pipe_profile_exists(dev, &pp, &pos)) { - if (!pipe_profile_free_exists(dev, &pos)) - return -1; - - pipe_profile_install(dev, &pp, pos); - } - - pipe_profile_mark(dev, subport_id, pipe_id, pos); - - pipe_id++; - } - - subport_id++; - } - - return 0; -} - -static struct tm_wred_profile * -tm_tc_wred_profile_get(struct rte_eth_dev *dev, uint32_t tc_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - struct tm_node_list *nl = &h->nodes; - struct tm_node *nq; - - TAILQ_FOREACH(nq, nl, node) { - if (nq->level != TM_NODE_LEVEL_QUEUE || - nq->parent_node->priority != tc_id) - continue; - - return nq->wred_profile; - } - - return NULL; -} - -#ifdef RTE_SCHED_CMAN - -static void -wred_profiles_set(struct rte_eth_dev *dev, uint32_t subport_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct rte_sched_subport_params *pp = - &p->soft.tm.params.subport_params[subport_id]; - - uint32_t tc_id; - enum rte_color color; - - for (tc_id = 0; tc_id < RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; tc_id++) - for (color = RTE_COLOR_GREEN; color < RTE_COLORS; color++) { - struct rte_red_params *dst = - &pp->cman_params->red_params[tc_id][color]; - struct tm_wred_profile *src_wp = - tm_tc_wred_profile_get(dev, tc_id); - struct rte_tm_red_params *src = - &src_wp->params.red_params[color]; - - memcpy(dst, src, sizeof(*dst)); - } -} - -#else - -#define wred_profiles_set(dev, subport_id) - -#endif - -static struct tm_shared_shaper * -tm_tc_shared_shaper_get(struct rte_eth_dev *dev, struct tm_node *tc_node) -{ - return (tc_node->params.n_shared_shapers) ? - tm_shared_shaper_search(dev, - tc_node->params.shared_shaper_id[0]) : - NULL; -} - -static struct tm_shared_shaper * -tm_subport_tc_shared_shaper_get(struct rte_eth_dev *dev, - struct tm_node *subport_node, - uint32_t tc_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_node_list *nl = &p->soft.tm.h.nodes; - struct tm_node *n; - - TAILQ_FOREACH(n, nl, node) { - if (n->level != TM_NODE_LEVEL_TC || - n->parent_node->parent_node_id != - subport_node->node_id || - n->priority != tc_id) - continue; - - return tm_tc_shared_shaper_get(dev, n); - } - - return NULL; -} - -static struct rte_sched_subport_profile_params * -subport_profile_get(struct rte_eth_dev *dev, struct tm_node *np) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - uint32_t subport_id = tm_node_subport_id(dev, np->parent_node); - - if (subport_id >= TM_MAX_SUBPORT_PROFILE) - return NULL; - - return &t->subport_profile[subport_id]; -} - -static void -subport_profile_mark(struct rte_eth_dev *dev, - uint32_t subport_id, - uint32_t subport_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - - t->subport_to_profile[subport_id] = subport_profile_id; -} - -static void -subport_profile_install(struct rte_eth_dev *dev, - struct rte_sched_subport_profile_params *sp, - uint32_t subport_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - - memcpy(&t->subport_profile[subport_profile_id], - sp, sizeof(*sp)); - t->n_subport_profiles++; -} - -static int -subport_profile_free_exists(struct rte_eth_dev *dev, - uint32_t *subport_profile_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - - if (t->n_subport_profiles < TM_MAX_SUBPORT_PROFILE) { - *subport_profile_id = t->n_subport_profiles; - return 1; - } - - return 0; -} - -static void -subport_profile_build(struct rte_eth_dev *dev, struct tm_node *np, - struct rte_sched_subport_profile_params *sp) -{ - uint32_t i; - memset(sp, 0, sizeof(*sp)); - - sp->tb_rate = np->shaper_profile->params.peak.rate; - sp->tb_size = np->shaper_profile->params.peak.size; - - for (i = 0; i < RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; i++) { - struct tm_shared_shaper *ss; - struct tm_shaper_profile *ssp; - - ss = tm_subport_tc_shared_shaper_get(dev, np, i); - ssp = (ss) ? tm_shaper_profile_search(dev, - ss->shaper_profile_id) : - np->shaper_profile; - sp->tc_rate[i] = ssp->params.peak.rate; - } - - /* Traffic Class (TC) */ - sp->tc_period = SUBPORT_TC_PERIOD; -} - -static int -subport_profiles_generate(struct rte_eth_dev *dev) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - struct tm_node_list *nl = &h->nodes; - struct tm_node *ns; - uint32_t subport_id; - - /* Objective: Fill in the following fields in struct tm_params: - * - subport_profiles - * - n_subport_profiles - * - subport_to_profile - */ - - subport_id = 0; - TAILQ_FOREACH(ns, nl, node) { - if (ns->level != TM_NODE_LEVEL_SUBPORT) - continue; - - struct rte_sched_subport_profile_params sp; - uint32_t pos; - - memset(&sp, 0, sizeof(sp)); - - subport_profile_build(dev, ns, &sp); - - if (!subport_profile_exists(dev, &sp, &pos)) { - if (!subport_profile_free_exists(dev, &pos)) - return -1; - - subport_profile_install(dev, &sp, pos); - } - - subport_profile_mark(dev, subport_id, pos); - - subport_id++; - } - - return 0; -} - - -static int -hierarchy_commit_check(struct rte_eth_dev *dev, struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - struct tm_node_list *nl = &h->nodes; - struct tm_shared_shaper_list *ssl = &h->shared_shapers; - struct tm_wred_profile_list *wpl = &h->wred_profiles; - struct tm_node *nr = tm_root_node_present(dev), *ns, *np, *nt, *nq; - struct tm_shared_shaper *ss; - - uint32_t n_pipes_per_subport; - - /* Root node exists. */ - if (nr == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_LEVEL_ID, - NULL, - rte_strerror(EINVAL)); - - /* There is at least one subport, max is not exceeded. */ - if (nr->n_children == 0 || nr->n_children > TM_MAX_SUBPORTS) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_LEVEL_ID, - NULL, - rte_strerror(EINVAL)); - - /* There is at least one pipe. */ - if (h->n_tm_nodes[TM_NODE_LEVEL_PIPE] == 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_LEVEL_ID, - NULL, - rte_strerror(EINVAL)); - - /* Number of pipes is the same for all subports. Maximum number of pipes - * per subport is not exceeded. - */ - n_pipes_per_subport = h->n_tm_nodes[TM_NODE_LEVEL_PIPE] / - h->n_tm_nodes[TM_NODE_LEVEL_SUBPORT]; - - if (n_pipes_per_subport > TM_MAX_PIPES_PER_SUBPORT) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - - TAILQ_FOREACH(ns, nl, node) { - if (ns->level != TM_NODE_LEVEL_SUBPORT) - continue; - - if (ns->n_children != n_pipes_per_subport) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } - - /* Each pipe has exactly 13 TCs, with exactly one TC for each priority */ - TAILQ_FOREACH(np, nl, node) { - uint32_t mask = 0, mask_expected = - RTE_LEN2MASK(RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE, - uint32_t); - - if (np->level != TM_NODE_LEVEL_PIPE) - continue; - - if (np->n_children != RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - - TAILQ_FOREACH(nt, nl, node) { - if (nt->level != TM_NODE_LEVEL_TC || - nt->parent_node_id != np->node_id) - continue; - - mask |= 1 << nt->priority; - } - - if (mask != mask_expected) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } - - /** Each Strict priority TC has exactly 1 packet queues while - * lowest priority TC (Best-effort) has 4 queues. - */ - TAILQ_FOREACH(nt, nl, node) { - if (nt->level != TM_NODE_LEVEL_TC) - continue; - - if (nt->n_children != 1 && nt->n_children != RTE_SCHED_BE_QUEUES_PER_PIPE) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } - - /** - * Shared shapers: - * -For each TC #i, all pipes in the same subport use the same - * shared shaper (or no shared shaper) for their TC#i. - * -Each shared shaper needs to have at least one user. All its - * users have to be TC nodes with the same priority and the same - * subport. - */ - TAILQ_FOREACH(ns, nl, node) { - struct tm_shared_shaper *s[RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE]; - uint32_t id; - - if (ns->level != TM_NODE_LEVEL_SUBPORT) - continue; - - for (id = 0; id < RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; id++) - s[id] = tm_subport_tc_shared_shaper_get(dev, ns, id); - - TAILQ_FOREACH(nt, nl, node) { - struct tm_shared_shaper *subport_ss, *tc_ss; - - if (nt->level != TM_NODE_LEVEL_TC || - nt->parent_node->parent_node_id != - ns->node_id) - continue; - - subport_ss = s[nt->priority]; - tc_ss = tm_tc_shared_shaper_get(dev, nt); - - if (subport_ss == NULL && tc_ss == NULL) - continue; - - if ((subport_ss == NULL && tc_ss != NULL) || - (subport_ss != NULL && tc_ss == NULL) || - subport_ss->shared_shaper_id != - tc_ss->shared_shaper_id) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } - } - - TAILQ_FOREACH(ss, ssl, node) { - struct tm_node *nt_any = tm_shared_shaper_get_tc(dev, ss); - uint32_t n_users = 0; - - if (nt_any != NULL) - TAILQ_FOREACH(nt, nl, node) { - if (nt->level != TM_NODE_LEVEL_TC || - nt->priority != nt_any->priority || - nt->parent_node->parent_node_id != - nt_any->parent_node->parent_node_id) - continue; - - n_users++; - } - - if (ss->n_users == 0 || ss->n_users != n_users) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } - - /* Not too many subport profiles. */ - if (subport_profiles_generate(dev)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - - - /* Not too many pipe profiles. */ - if (pipe_profiles_generate(dev)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - - /** - * WRED (when used, i.e. at least one WRED profile defined): - * -Each WRED profile must have at least one user. - * -All leaf nodes must have their private WRED context enabled. - * -For each TC #i, all leaf nodes must use the same WRED profile - * for their private WRED context. - */ - if (h->n_wred_profiles) { - struct tm_wred_profile *wp; - struct tm_wred_profile *w[RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE]; - uint32_t id; - - TAILQ_FOREACH(wp, wpl, node) - if (wp->n_users == 0) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - - for (id = 0; id < RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; id++) { - w[id] = tm_tc_wred_profile_get(dev, id); - - if (w[id] == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } - - TAILQ_FOREACH(nq, nl, node) { - uint32_t id; - - if (nq->level != TM_NODE_LEVEL_QUEUE) - continue; - - id = nq->parent_node->priority; - - if (nq->wred_profile == NULL || - nq->wred_profile->wred_profile_id != - w[id]->wred_profile_id) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } - } - - return 0; -} - -static void -hierarchy_blueprints_create(struct rte_eth_dev *dev) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_params *t = &p->soft.tm.params; - struct tm_hierarchy *h = &p->soft.tm.h; - - struct tm_node_list *nl = &h->nodes; - struct tm_node *root = tm_root_node_present(dev), *n; - - uint32_t subport_id; - - t->port_params = (struct rte_sched_port_params) { - .name = dev->data->name, - .socket = dev->data->numa_node, - .rate = root->shaper_profile->params.peak.rate, - .mtu = dev->data->mtu, - .frame_overhead = - root->shaper_profile->params.pkt_length_adjust, - .n_subports_per_port = root->n_children, - .n_subport_profiles = t->n_subport_profiles, - .subport_profiles = t->subport_profile, - .n_max_subport_profiles = TM_MAX_SUBPORT_PROFILE, - .n_pipes_per_subport = TM_MAX_PIPES_PER_SUBPORT, - }; - - subport_id = 0; - TAILQ_FOREACH(n, nl, node) { - - if (n->level != TM_NODE_LEVEL_SUBPORT) - continue; - - t->subport_params[subport_id] = - (struct rte_sched_subport_params) { - .n_pipes_per_subport_enabled = - h->n_tm_nodes[TM_NODE_LEVEL_PIPE] / - h->n_tm_nodes[TM_NODE_LEVEL_SUBPORT], - .qsize = {p->params.tm.qsize[0], - p->params.tm.qsize[1], - p->params.tm.qsize[2], - p->params.tm.qsize[3], - p->params.tm.qsize[4], - p->params.tm.qsize[5], - p->params.tm.qsize[6], - p->params.tm.qsize[7], - p->params.tm.qsize[8], - p->params.tm.qsize[9], - p->params.tm.qsize[10], - p->params.tm.qsize[11], - p->params.tm.qsize[12], - }, - .pipe_profiles = t->pipe_profiles, - .n_pipe_profiles = t->n_pipe_profiles, - .n_max_pipe_profiles = TM_MAX_PIPE_PROFILE, - }; - wred_profiles_set(dev, subport_id); - subport_id++; - } -} - -/* Traffic manager hierarchy commit */ -static int -pmd_tm_hierarchy_commit(struct rte_eth_dev *dev, - int clear_on_fail, - struct rte_tm_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - int status; - - /* Checks */ - if (p->soft.tm.hierarchy_frozen) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - status = hierarchy_commit_check(dev, error); - if (status) { - if (clear_on_fail) - tm_hierarchy_free(p); - - return status; - } - - /* Create blueprints */ - hierarchy_blueprints_create(dev); - - /* Freeze hierarchy */ - p->soft.tm.hierarchy_frozen = 1; - - return 0; -} - -static int -update_pipe_weight(struct rte_eth_dev *dev, struct tm_node *np, uint32_t weight) -{ - struct pmd_internals *p = dev->data->dev_private; - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - - struct rte_sched_pipe_params *profile0 = pipe_profile_get(dev, np); - struct rte_sched_pipe_params profile1; - uint32_t pipe_profile_id; - - /* Derive new pipe profile. */ - memcpy(&profile1, profile0, sizeof(profile1)); - profile1.tc_ov_weight = (uint8_t)weight; - - /* Since implementation does not allow adding more pipe profiles after - * port configuration, the pipe configuration can be successfully - * updated only if the new profile is also part of the existing set of - * pipe profiles. - */ - if (pipe_profile_exists(dev, &profile1, &pipe_profile_id) == 0) - return -1; - - /* Update the pipe profile used by the current pipe. */ - if (rte_sched_pipe_config(SCHED(p), subport_id, pipe_id, - (int32_t)pipe_profile_id)) - return -1; - - /* Commit changes. */ - pipe_profile_mark(dev, subport_id, pipe_id, pipe_profile_id); - np->weight = weight; - - return 0; -} - -static int -update_queue_weight(struct rte_eth_dev *dev, - struct tm_node *nq, uint32_t weight) -{ - struct pmd_internals *p = dev->data->dev_private; - uint32_t queue_id = tm_node_queue_id(dev, nq); - - struct tm_node *nt = nq->parent_node; - - struct tm_node *np = nt->parent_node; - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - - uint32_t pipe_be_queue_id = - queue_id - RTE_SCHED_TRAFFIC_CLASS_BE; - - struct rte_sched_pipe_params *profile0 = pipe_profile_get(dev, np); - struct rte_sched_pipe_params profile1; - uint32_t pipe_profile_id; - - /* Derive new pipe profile. */ - memcpy(&profile1, profile0, sizeof(profile1)); - profile1.wrr_weights[pipe_be_queue_id] = (uint8_t)weight; - - /* Since implementation does not allow adding more pipe profiles after - * port configuration, the pipe configuration can be successfully - * updated only if the new profile is also part of the existing set - * of pipe profiles. - */ - if (pipe_profile_exists(dev, &profile1, &pipe_profile_id) == 0) - return -1; - - /* Update the pipe profile used by the current pipe. */ - if (rte_sched_pipe_config(SCHED(p), subport_id, pipe_id, - (int32_t)pipe_profile_id)) - return -1; - - /* Commit changes. */ - pipe_profile_mark(dev, subport_id, pipe_id, pipe_profile_id); - nq->weight = weight; - - return 0; -} - -/* Traffic manager node parent update */ -static int -pmd_tm_node_parent_update(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t parent_node_id, - uint32_t priority, - uint32_t weight, - struct rte_tm_error *error) -{ - struct tm_node *n; - - /* Port must be started and TM used. */ - if (dev->data->dev_started == 0 && (tm_used(dev) == 0)) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - /* Node must be valid */ - n = tm_node_search(dev, node_id); - if (n == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Parent node must be the same */ - if (n->parent_node_id != parent_node_id) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PARENT_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Priority must be the same */ - if (n->priority != priority) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_PRIORITY, - NULL, - rte_strerror(EINVAL)); - - /* weight: must be 1 .. 255 */ - if (weight == 0 || weight >= UINT8_MAX) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - - switch (n->level) { - case TM_NODE_LEVEL_PORT: - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - /* fall-through */ - case TM_NODE_LEVEL_SUBPORT: - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - /* fall-through */ - case TM_NODE_LEVEL_PIPE: - if (update_pipe_weight(dev, n, weight)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - /* fall-through */ - case TM_NODE_LEVEL_TC: - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_WEIGHT, - NULL, - rte_strerror(EINVAL)); - /* fall-through */ - case TM_NODE_LEVEL_QUEUE: - /* fall-through */ - default: - if (update_queue_weight(dev, n, weight)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - } -} - -static int -update_subport_rate(struct rte_eth_dev *dev, - struct tm_node *ns, - struct tm_shaper_profile *sp) -{ - struct pmd_internals *p = dev->data->dev_private; - uint32_t subport_id = tm_node_subport_id(dev, ns); - - struct rte_sched_subport_profile_params *profile0 = - subport_profile_get(dev, ns); - struct rte_sched_subport_profile_params profile1; - uint32_t subport_profile_id; - - if (profile0 == NULL) - return -1; - - /* Derive new pipe profile. */ - memcpy(&profile1, profile0, sizeof(profile1)); - profile1.tb_rate = sp->params.peak.rate; - profile1.tb_size = sp->params.peak.size; - - /* Since implementation does not allow adding more subport profiles - * after port configuration, the pipe configuration can be successfully - * updated only if the new profile is also part of the existing set of - * pipe profiles. - */ - if (subport_profile_exists(dev, &profile1, &subport_profile_id) == 0) - return -1; - - /* Update the subport configuration. */ - if (rte_sched_subport_config(SCHED(p), subport_id, - NULL, subport_profile_id)) - return -1; - - /* Commit changes. */ - ns->shaper_profile->n_users--; - - ns->shaper_profile = sp; - ns->params.shaper_profile_id = sp->shaper_profile_id; - sp->n_users++; - - subport_profile_mark(dev, subport_id, subport_profile_id); - - memcpy(&p->soft.tm.params.subport_profile[subport_profile_id], - &profile1, - sizeof(profile1)); - - return 0; -} - -static int -update_pipe_rate(struct rte_eth_dev *dev, - struct tm_node *np, - struct tm_shaper_profile *sp) -{ - struct pmd_internals *p = dev->data->dev_private; - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - - struct rte_sched_pipe_params *profile0 = pipe_profile_get(dev, np); - struct rte_sched_pipe_params profile1; - uint32_t pipe_profile_id; - - /* Derive new pipe profile. */ - memcpy(&profile1, profile0, sizeof(profile1)); - profile1.tb_rate = sp->params.peak.rate; - profile1.tb_size = sp->params.peak.size; - - /* Since implementation does not allow adding more pipe profiles after - * port configuration, the pipe configuration can be successfully - * updated only if the new profile is also part of the existing set of - * pipe profiles. - */ - if (pipe_profile_exists(dev, &profile1, &pipe_profile_id) == 0) - return -1; - - /* Update the pipe profile used by the current pipe. */ - if (rte_sched_pipe_config(SCHED(p), subport_id, pipe_id, - (int32_t)pipe_profile_id)) - return -1; - - /* Commit changes. */ - pipe_profile_mark(dev, subport_id, pipe_id, pipe_profile_id); - np->shaper_profile->n_users--; - np->shaper_profile = sp; - np->params.shaper_profile_id = sp->shaper_profile_id; - sp->n_users++; - - return 0; -} - -static int -update_tc_rate(struct rte_eth_dev *dev, - struct tm_node *nt, - struct tm_shaper_profile *sp) -{ - struct pmd_internals *p = dev->data->dev_private; - uint32_t tc_id = tm_node_tc_id(dev, nt); - - struct tm_node *np = nt->parent_node; - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - - struct rte_sched_pipe_params *profile0 = pipe_profile_get(dev, np); - struct rte_sched_pipe_params profile1; - uint32_t pipe_profile_id; - - /* Derive new pipe profile. */ - memcpy(&profile1, profile0, sizeof(profile1)); - profile1.tc_rate[tc_id] = sp->params.peak.rate; - - /* Since implementation does not allow adding more pipe profiles after - * port configuration, the pipe configuration can be successfully - * updated only if the new profile is also part of the existing set of - * pipe profiles. - */ - if (pipe_profile_exists(dev, &profile1, &pipe_profile_id) == 0) - return -1; - - /* Update the pipe profile used by the current pipe. */ - if (rte_sched_pipe_config(SCHED(p), subport_id, pipe_id, - (int32_t)pipe_profile_id)) - return -1; - - /* Commit changes. */ - pipe_profile_mark(dev, subport_id, pipe_id, pipe_profile_id); - nt->shaper_profile->n_users--; - nt->shaper_profile = sp; - nt->params.shaper_profile_id = sp->shaper_profile_id; - sp->n_users++; - - return 0; -} - -/* Traffic manager node shaper update */ -static int -pmd_tm_node_shaper_update(struct rte_eth_dev *dev, - uint32_t node_id, - uint32_t shaper_profile_id, - struct rte_tm_error *error) -{ - struct tm_node *n; - struct tm_shaper_profile *sp; - - /* Port must be started and TM used. */ - if (dev->data->dev_started == 0 && (tm_used(dev) == 0)) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - /* Node must be valid */ - n = tm_node_search(dev, node_id); - if (n == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - /* Shaper profile must be valid. */ - sp = tm_shaper_profile_search(dev, shaper_profile_id); - if (sp == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_SHAPER_PROFILE, - NULL, - rte_strerror(EINVAL)); - - switch (n->level) { - case TM_NODE_LEVEL_PORT: - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - /* fall-through */ - case TM_NODE_LEVEL_SUBPORT: - if (update_subport_rate(dev, n, sp)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - /* fall-through */ - case TM_NODE_LEVEL_PIPE: - if (update_pipe_rate(dev, n, sp)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - /* fall-through */ - case TM_NODE_LEVEL_TC: - if (update_tc_rate(dev, n, sp)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - /* fall-through */ - case TM_NODE_LEVEL_QUEUE: - /* fall-through */ - default: - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - } -} - -static inline uint32_t -tm_port_queue_id(struct rte_eth_dev *dev, - uint32_t port_subport_id, - uint32_t subport_pipe_id, - uint32_t pipe_tc_id, - uint32_t tc_queue_id) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - uint32_t n_pipes_per_subport = h->n_tm_nodes[TM_NODE_LEVEL_PIPE] / - h->n_tm_nodes[TM_NODE_LEVEL_SUBPORT]; - - uint32_t port_pipe_id = - port_subport_id * n_pipes_per_subport + subport_pipe_id; - - uint32_t port_queue_id = - port_pipe_id * RTE_SCHED_QUEUES_PER_PIPE + pipe_tc_id + tc_queue_id; - - return port_queue_id; -} - -static int -read_port_stats(struct rte_eth_dev *dev, - struct tm_node *nr, - struct rte_tm_node_stats *stats, - uint64_t *stats_mask, - int clear) -{ - struct pmd_internals *p = dev->data->dev_private; - struct tm_hierarchy *h = &p->soft.tm.h; - uint32_t n_subports_per_port = h->n_tm_nodes[TM_NODE_LEVEL_SUBPORT]; - uint32_t subport_id; - - for (subport_id = 0; subport_id < n_subports_per_port; subport_id++) { - struct rte_sched_subport_stats s; - uint32_t tc_ov, id; - - /* Stats read */ - int status = rte_sched_subport_read_stats(SCHED(p), - subport_id, - &s, - &tc_ov); - if (status) - return status; - - /* Stats accumulate */ - for (id = 0; id < RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; id++) { - nr->stats.n_pkts += - s.n_pkts_tc[id] - s.n_pkts_tc_dropped[id]; - nr->stats.n_bytes += - s.n_bytes_tc[id] - s.n_bytes_tc_dropped[id]; - nr->stats.leaf.n_pkts_dropped[RTE_COLOR_GREEN] += - s.n_pkts_tc_dropped[id]; - nr->stats.leaf.n_bytes_dropped[RTE_COLOR_GREEN] += - s.n_bytes_tc_dropped[id]; - } - } - - /* Stats copy */ - if (stats) - memcpy(stats, &nr->stats, sizeof(*stats)); - - if (stats_mask) - *stats_mask = STATS_MASK_DEFAULT; - - /* Stats clear */ - if (clear) - memset(&nr->stats, 0, sizeof(nr->stats)); - - return 0; -} - -static int -read_subport_stats(struct rte_eth_dev *dev, - struct tm_node *ns, - struct rte_tm_node_stats *stats, - uint64_t *stats_mask, - int clear) -{ - struct pmd_internals *p = dev->data->dev_private; - uint32_t subport_id = tm_node_subport_id(dev, ns); - struct rte_sched_subport_stats s; - uint32_t tc_ov, tc_id; - - /* Stats read */ - int status = rte_sched_subport_read_stats(SCHED(p), - subport_id, - &s, - &tc_ov); - if (status) - return status; - - /* Stats accumulate */ - for (tc_id = 0; tc_id < RTE_SCHED_TRAFFIC_CLASSES_PER_PIPE; tc_id++) { - ns->stats.n_pkts += - s.n_pkts_tc[tc_id] - s.n_pkts_tc_dropped[tc_id]; - ns->stats.n_bytes += - s.n_bytes_tc[tc_id] - s.n_bytes_tc_dropped[tc_id]; - ns->stats.leaf.n_pkts_dropped[RTE_COLOR_GREEN] += - s.n_pkts_tc_dropped[tc_id]; - ns->stats.leaf.n_bytes_dropped[RTE_COLOR_GREEN] += - s.n_bytes_tc_dropped[tc_id]; - } - - /* Stats copy */ - if (stats) - memcpy(stats, &ns->stats, sizeof(*stats)); - - if (stats_mask) - *stats_mask = STATS_MASK_DEFAULT; - - /* Stats clear */ - if (clear) - memset(&ns->stats, 0, sizeof(ns->stats)); - - return 0; -} - -static int -read_pipe_stats(struct rte_eth_dev *dev, - struct tm_node *np, - struct rte_tm_node_stats *stats, - uint64_t *stats_mask, - int clear) -{ - struct pmd_internals *p = dev->data->dev_private; - - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - uint32_t tc_id, queue_id; - uint32_t i; - - /* Stats read */ - for (i = 0; i < RTE_SCHED_QUEUES_PER_PIPE; i++) { - struct rte_sched_queue_stats s; - uint16_t qlen; - - if (i < RTE_SCHED_TRAFFIC_CLASS_BE) { - tc_id = i; - queue_id = i; - } else { - tc_id = RTE_SCHED_TRAFFIC_CLASS_BE; - queue_id = i - tc_id; - } - - uint32_t qid = tm_port_queue_id(dev, - subport_id, - pipe_id, - tc_id, - queue_id); - - int status = rte_sched_queue_read_stats(SCHED(p), - qid, - &s, - &qlen); - if (status) - return status; - - /* Stats accumulate */ - np->stats.n_pkts += s.n_pkts - s.n_pkts_dropped; - np->stats.n_bytes += s.n_bytes - s.n_bytes_dropped; - np->stats.leaf.n_pkts_dropped[RTE_COLOR_GREEN] += s.n_pkts_dropped; - np->stats.leaf.n_bytes_dropped[RTE_COLOR_GREEN] += - s.n_bytes_dropped; - np->stats.leaf.n_pkts_queued = qlen; - } - - /* Stats copy */ - if (stats) - memcpy(stats, &np->stats, sizeof(*stats)); - - if (stats_mask) - *stats_mask = STATS_MASK_DEFAULT; - - /* Stats clear */ - if (clear) - memset(&np->stats, 0, sizeof(np->stats)); - - return 0; -} - -static int -read_tc_stats(struct rte_eth_dev *dev, - struct tm_node *nt, - struct rte_tm_node_stats *stats, - uint64_t *stats_mask, - int clear) -{ - struct pmd_internals *p = dev->data->dev_private; - - uint32_t tc_id = tm_node_tc_id(dev, nt); - - struct tm_node *np = nt->parent_node; - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - struct rte_sched_queue_stats s; - uint32_t qid, i; - uint16_t qlen; - int status; - - /* Stats read */ - if (tc_id < RTE_SCHED_TRAFFIC_CLASS_BE) { - qid = tm_port_queue_id(dev, - subport_id, - pipe_id, - tc_id, - 0); - - status = rte_sched_queue_read_stats(SCHED(p), - qid, - &s, - &qlen); - if (status) - return status; - - /* Stats accumulate */ - nt->stats.n_pkts += s.n_pkts - s.n_pkts_dropped; - nt->stats.n_bytes += s.n_bytes - s.n_bytes_dropped; - nt->stats.leaf.n_pkts_dropped[RTE_COLOR_GREEN] += s.n_pkts_dropped; - nt->stats.leaf.n_bytes_dropped[RTE_COLOR_GREEN] += - s.n_bytes_dropped; - nt->stats.leaf.n_pkts_queued = qlen; - } else { - for (i = 0; i < RTE_SCHED_BE_QUEUES_PER_PIPE; i++) { - qid = tm_port_queue_id(dev, - subport_id, - pipe_id, - tc_id, - i); - - status = rte_sched_queue_read_stats(SCHED(p), - qid, - &s, - &qlen); - if (status) - return status; - - /* Stats accumulate */ - nt->stats.n_pkts += s.n_pkts - s.n_pkts_dropped; - nt->stats.n_bytes += s.n_bytes - s.n_bytes_dropped; - nt->stats.leaf.n_pkts_dropped[RTE_COLOR_GREEN] += - s.n_pkts_dropped; - nt->stats.leaf.n_bytes_dropped[RTE_COLOR_GREEN] += - s.n_bytes_dropped; - nt->stats.leaf.n_pkts_queued = qlen; - } - } - - /* Stats copy */ - if (stats) - memcpy(stats, &nt->stats, sizeof(*stats)); - - if (stats_mask) - *stats_mask = STATS_MASK_DEFAULT; - - /* Stats clear */ - if (clear) - memset(&nt->stats, 0, sizeof(nt->stats)); - - return 0; -} - -static int -read_queue_stats(struct rte_eth_dev *dev, - struct tm_node *nq, - struct rte_tm_node_stats *stats, - uint64_t *stats_mask, - int clear) -{ - struct pmd_internals *p = dev->data->dev_private; - struct rte_sched_queue_stats s; - uint16_t qlen; - - uint32_t queue_id = tm_node_queue_id(dev, nq); - - struct tm_node *nt = nq->parent_node; - uint32_t tc_id = tm_node_tc_id(dev, nt); - - struct tm_node *np = nt->parent_node; - uint32_t pipe_id = tm_node_pipe_id(dev, np); - - struct tm_node *ns = np->parent_node; - uint32_t subport_id = tm_node_subport_id(dev, ns); - - /* Stats read */ - uint32_t qid = tm_port_queue_id(dev, - subport_id, - pipe_id, - tc_id, - queue_id); - - int status = rte_sched_queue_read_stats(SCHED(p), - qid, - &s, - &qlen); - if (status) - return status; - - /* Stats accumulate */ - nq->stats.n_pkts += s.n_pkts - s.n_pkts_dropped; - nq->stats.n_bytes += s.n_bytes - s.n_bytes_dropped; - nq->stats.leaf.n_pkts_dropped[RTE_COLOR_GREEN] += s.n_pkts_dropped; - nq->stats.leaf.n_bytes_dropped[RTE_COLOR_GREEN] += - s.n_bytes_dropped; - nq->stats.leaf.n_pkts_queued = qlen; - - /* Stats copy */ - if (stats) - memcpy(stats, &nq->stats, sizeof(*stats)); - - if (stats_mask) - *stats_mask = STATS_MASK_QUEUE; - - /* Stats clear */ - if (clear) - memset(&nq->stats, 0, sizeof(nq->stats)); - - return 0; -} - -/* Traffic manager read stats counters for specific node */ -static int -pmd_tm_node_stats_read(struct rte_eth_dev *dev, - uint32_t node_id, - struct rte_tm_node_stats *stats, - uint64_t *stats_mask, - int clear, - struct rte_tm_error *error) -{ - struct tm_node *n; - - /* Port must be started and TM used. */ - if (dev->data->dev_started == 0 && (tm_used(dev) == 0)) - return -rte_tm_error_set(error, - EBUSY, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EBUSY)); - - /* Node must be valid */ - n = tm_node_search(dev, node_id); - if (n == NULL) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_NODE_ID, - NULL, - rte_strerror(EINVAL)); - - switch (n->level) { - case TM_NODE_LEVEL_PORT: - if (read_port_stats(dev, n, stats, stats_mask, clear)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - - case TM_NODE_LEVEL_SUBPORT: - if (read_subport_stats(dev, n, stats, stats_mask, clear)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - - case TM_NODE_LEVEL_PIPE: - if (read_pipe_stats(dev, n, stats, stats_mask, clear)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - - case TM_NODE_LEVEL_TC: - if (read_tc_stats(dev, n, stats, stats_mask, clear)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - - case TM_NODE_LEVEL_QUEUE: - default: - if (read_queue_stats(dev, n, stats, stats_mask, clear)) - return -rte_tm_error_set(error, - EINVAL, - RTE_TM_ERROR_TYPE_UNSPECIFIED, - NULL, - rte_strerror(EINVAL)); - return 0; - } -} - -const struct rte_tm_ops pmd_tm_ops = { - .node_type_get = pmd_tm_node_type_get, - .capabilities_get = pmd_tm_capabilities_get, - .level_capabilities_get = pmd_tm_level_capabilities_get, - .node_capabilities_get = pmd_tm_node_capabilities_get, - - .wred_profile_add = pmd_tm_wred_profile_add, - .wred_profile_delete = pmd_tm_wred_profile_delete, - .shared_wred_context_add_update = NULL, - .shared_wred_context_delete = NULL, - - .shaper_profile_add = pmd_tm_shaper_profile_add, - .shaper_profile_delete = pmd_tm_shaper_profile_delete, - .shared_shaper_add_update = pmd_tm_shared_shaper_add_update, - .shared_shaper_delete = pmd_tm_shared_shaper_delete, - - .node_add = pmd_tm_node_add, - .node_delete = pmd_tm_node_delete, - .node_suspend = NULL, - .node_resume = NULL, - .hierarchy_commit = pmd_tm_hierarchy_commit, - - .node_parent_update = pmd_tm_node_parent_update, - .node_shaper_update = pmd_tm_node_shaper_update, - .node_shared_shaper_update = NULL, - .node_stats_update = NULL, - .node_wfq_weight_mode_update = NULL, - .node_cman_update = NULL, - .node_wred_context_update = NULL, - .node_shared_wred_context_update = NULL, - - .node_stats_read = pmd_tm_node_stats_read, -}; From patchwork Thu Aug 4 16:58:20 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Dumitrescu X-Patchwork-Id: 114624 X-Patchwork-Delegate: andrew.rybchenko@oktetlabs.ru 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 8C701A00C4; Thu, 4 Aug 2022 18:58:59 +0200 (CEST) Received: from [217.70.189.124] (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 01CD142BCA; Thu, 4 Aug 2022 18:58:56 +0200 (CEST) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by mails.dpdk.org (Postfix) with ESMTP id A02BE4067C for ; Thu, 4 Aug 2022 18:58:52 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1659632332; x=1691168332; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=uujgay7c9l4lHgKBaTPTUY7SnW5GFO3leLkIri2gFqo=; b=GwEhj6r8HcsOKQEUSaKyNMPRGOwpqmag4nuyXS18lB0Xifbqca1nq211 LefM3yz/Oe+Jy3YjIBIqj4fSAEgkoHpyFjP6vckP2DqvgbGUJ6n4/IKzs G7pw195Zqu1adP2Bf98drld/7ydCLCak7piO10HVJ4K4vQn0fFS6q8c6H Nu47L5eLh4BQg91pI1LB79TeptgOl5SOy0yKop120r5/PIunvFtBFUGHS cLL3C0qQ8jGdCHh9Co0sz52V+AZYVwT4nJSGRnrm6nmPnczm6Y1S1u+OB FyAyyA088kla4A54pdSf4d2F3qoQJ2jdUK7q1FTXQFRdr+/wGX9cIDjub A==; X-IronPort-AV: E=McAfee;i="6400,9594,10429"; a="290000087" X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="290000087" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 04 Aug 2022 09:58:46 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="636163087" Received: from silpixa00400573.ir.intel.com (HELO silpixa00400573.ger.corp.intel.com) ([10.237.223.157]) by orsmga001.jf.intel.com with ESMTP; 04 Aug 2022 09:58:44 -0700 From: Cristian Dumitrescu To: dev@dpdk.org Cc: jasvinder.singh@intel.com, yogesh.jangra@intel.com Subject: [PATCH 02/21] net/softnic: remove flow support Date: Thu, 4 Aug 2022 16:58:20 +0000 Message-Id: <20220804165839.1074817-3-cristian.dumitrescu@intel.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> References: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> MIME-Version: 1.0 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 Remove the Ethernet device flow API support. Signed-off-by: Cristian Dumitrescu Signed-off-by: Yogesh Jangra --- drivers/net/softnic/meson.build | 1 - drivers/net/softnic/rte_eth_softnic.c | 9 - drivers/net/softnic/rte_eth_softnic_cli.c | 81 - drivers/net/softnic/rte_eth_softnic_flow.c | 2293 -------------------- 4 files changed, 2384 deletions(-) delete mode 100644 drivers/net/softnic/rte_eth_softnic_flow.c diff --git a/drivers/net/softnic/meson.build b/drivers/net/softnic/meson.build index e2dbd6166e..4ebe60921c 100644 --- a/drivers/net/softnic/meson.build +++ b/drivers/net/softnic/meson.build @@ -13,7 +13,6 @@ sources = files( 'rte_eth_softnic_action.c', 'rte_eth_softnic_cli.c', 'rte_eth_softnic_cryptodev.c', - 'rte_eth_softnic_flow.c', 'rte_eth_softnic_link.c', 'rte_eth_softnic_mempool.c', 'rte_eth_softnic_meter.c', diff --git a/drivers/net/softnic/rte_eth_softnic.c b/drivers/net/softnic/rte_eth_softnic.c index ae3e8b3bcd..8e361adbad 100644 --- a/drivers/net/softnic/rte_eth_softnic.c +++ b/drivers/net/softnic/rte_eth_softnic.c @@ -215,14 +215,6 @@ pmd_link_update(struct rte_eth_dev *dev __rte_unused, return 0; } -static int -pmd_flow_ops_get(struct rte_eth_dev *dev __rte_unused, - const struct rte_flow_ops **ops) -{ - *ops = &pmd_flow_ops; - return 0; -} - static int pmd_mtr_ops_get(struct rte_eth_dev *dev __rte_unused, void *arg) { @@ -240,7 +232,6 @@ static const struct eth_dev_ops pmd_ops = { .dev_infos_get = pmd_dev_infos_get, .rx_queue_setup = pmd_rx_queue_setup, .tx_queue_setup = pmd_tx_queue_setup, - .flow_ops_get = pmd_flow_ops_get, .mtr_ops_get = pmd_mtr_ops_get, }; diff --git a/drivers/net/softnic/rte_eth_softnic_cli.c b/drivers/net/softnic/rte_eth_softnic_cli.c index 7556e50831..671f96cf77 100644 --- a/drivers/net/softnic/rte_eth_softnic_cli.c +++ b/drivers/net/softnic/rte_eth_softnic_cli.c @@ -4731,81 +4731,6 @@ cmd_softnic_thread_pipeline_disable(struct pmd_internals *softnic, } } -/** - * flowapi map - * group - * ingress | egress - * pipeline - * table - */ -static void -cmd_softnic_flowapi_map(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - char *pipeline_name; - uint32_t group_id, table_id; - int ingress, status; - - if (n_tokens != 9) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "map") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "map"); - return; - } - - if (strcmp(tokens[2], "group") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "group"); - return; - } - - if (softnic_parser_read_uint32(&group_id, tokens[3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "group_id"); - return; - } - - if (strcmp(tokens[4], "ingress") == 0) { - ingress = 1; - } else if (strcmp(tokens[4], "egress") == 0) { - ingress = 0; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "ingress | egress"); - return; - } - - if (strcmp(tokens[5], "pipeline") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "pipeline"); - return; - } - - pipeline_name = tokens[6]; - - if (strcmp(tokens[7], "table") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "table"); - return; - } - - if (softnic_parser_read_uint32(&table_id, tokens[8]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "table_id"); - return; - } - - status = flow_attr_map_set(softnic, - group_id, - ingress, - pipeline_name, - table_id); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - void softnic_cli_process(char *in, char *out, size_t out_size, void *arg) { @@ -5063,12 +4988,6 @@ softnic_cli_process(char *in, char *out, size_t out_size, void *arg) } } - if (strcmp(tokens[0], "flowapi") == 0) { - cmd_softnic_flowapi_map(softnic, tokens, n_tokens, out, - out_size); - return; - } - snprintf(out, out_size, MSG_CMD_UNKNOWN, tokens[0]); } diff --git a/drivers/net/softnic/rte_eth_softnic_flow.c b/drivers/net/softnic/rte_eth_softnic_flow.c deleted file mode 100644 index ad96288e7e..0000000000 --- a/drivers/net/softnic/rte_eth_softnic_flow.c +++ /dev/null @@ -1,2293 +0,0 @@ -/* SPDX-License-Identifier: BSD-3-Clause - * Copyright(c) 2018 Intel Corporation - */ -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include - -#include "rte_eth_softnic_internals.h" -#include "rte_eth_softnic.h" - -#define rte_htons rte_cpu_to_be_16 -#define rte_htonl rte_cpu_to_be_32 - -#define rte_ntohs rte_be_to_cpu_16 -#define rte_ntohl rte_be_to_cpu_32 - -static struct rte_flow * -softnic_flow_find(struct softnic_table *table, - struct softnic_table_rule_match *rule_match) -{ - struct rte_flow *flow; - - TAILQ_FOREACH(flow, &table->flows, node) - if (memcmp(&flow->match, rule_match, sizeof(*rule_match)) == 0) - return flow; - - return NULL; -} - -int -flow_attr_map_set(struct pmd_internals *softnic, - uint32_t group_id, - int ingress, - const char *pipeline_name, - uint32_t table_id) -{ - struct pipeline *pipeline; - struct flow_attr_map *map; - - if (group_id >= SOFTNIC_FLOW_MAX_GROUPS || - pipeline_name == NULL) - return -1; - - pipeline = softnic_pipeline_find(softnic, pipeline_name); - if (pipeline == NULL || - table_id >= pipeline->n_tables) - return -1; - - map = (ingress) ? &softnic->flow.ingress_map[group_id] : - &softnic->flow.egress_map[group_id]; - strlcpy(map->pipeline_name, pipeline_name, sizeof(map->pipeline_name)); - map->table_id = table_id; - map->valid = 1; - - return 0; -} - -struct flow_attr_map * -flow_attr_map_get(struct pmd_internals *softnic, - uint32_t group_id, - int ingress) -{ - if (group_id >= SOFTNIC_FLOW_MAX_GROUPS) - return NULL; - - return (ingress) ? &softnic->flow.ingress_map[group_id] : - &softnic->flow.egress_map[group_id]; -} - -static int -flow_pipeline_table_get(struct pmd_internals *softnic, - const struct rte_flow_attr *attr, - const char **pipeline_name, - uint32_t *table_id, - struct rte_flow_error *error) -{ - struct flow_attr_map *map; - - if (attr == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ATTR, - NULL, - "Null attr"); - - if (!attr->ingress && !attr->egress) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ATTR_INGRESS, - attr, - "Ingress/egress not specified"); - - if (attr->ingress && attr->egress) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ATTR_INGRESS, - attr, - "Setting both ingress and egress is not allowed"); - - map = flow_attr_map_get(softnic, - attr->group, - attr->ingress); - if (map == NULL || - map->valid == 0) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ATTR_GROUP, - attr, - "Invalid group ID"); - - if (pipeline_name) - *pipeline_name = map->pipeline_name; - - if (table_id) - *table_id = map->table_id; - - return 0; -} - -union flow_item { - uint8_t raw[TABLE_RULE_MATCH_SIZE_MAX]; - struct rte_flow_item_eth eth; - struct rte_flow_item_vlan vlan; - struct rte_flow_item_ipv4 ipv4; - struct rte_flow_item_ipv6 ipv6; - struct rte_flow_item_icmp icmp; - struct rte_flow_item_udp udp; - struct rte_flow_item_tcp tcp; - struct rte_flow_item_sctp sctp; - struct rte_flow_item_vxlan vxlan; - struct rte_flow_item_e_tag e_tag; - struct rte_flow_item_nvgre nvgre; - struct rte_flow_item_mpls mpls; - struct rte_flow_item_gre gre; - struct rte_flow_item_gtp gtp; - struct rte_flow_item_esp esp; - struct rte_flow_item_geneve geneve; - struct rte_flow_item_vxlan_gpe vxlan_gpe; - struct rte_flow_item_arp_eth_ipv4 arp_eth_ipv4; - struct rte_flow_item_ipv6_ext ipv6_ext; - struct rte_flow_item_icmp6 icmp6; - struct rte_flow_item_icmp6_nd_ns icmp6_nd_ns; - struct rte_flow_item_icmp6_nd_na icmp6_nd_na; - struct rte_flow_item_icmp6_nd_opt icmp6_nd_opt; - struct rte_flow_item_icmp6_nd_opt_sla_eth icmp6_nd_opt_sla_eth; - struct rte_flow_item_icmp6_nd_opt_tla_eth icmp6_nd_opt_tla_eth; -}; - -static const union flow_item flow_item_raw_mask; - -static int -flow_item_is_proto(enum rte_flow_item_type type, - const void **mask, - size_t *size) -{ - switch (type) { - case RTE_FLOW_ITEM_TYPE_RAW: - *mask = &flow_item_raw_mask; - *size = sizeof(flow_item_raw_mask); - return 1; /* TRUE */ - - case RTE_FLOW_ITEM_TYPE_ETH: - *mask = &rte_flow_item_eth_mask; - *size = sizeof(struct rte_ether_hdr); - return 1; /* TRUE */ - - case RTE_FLOW_ITEM_TYPE_VLAN: - *mask = &rte_flow_item_vlan_mask; - *size = sizeof(struct rte_vlan_hdr); - return 1; - - case RTE_FLOW_ITEM_TYPE_IPV4: - *mask = &rte_flow_item_ipv4_mask; - *size = sizeof(struct rte_ipv4_hdr); - return 1; - - case RTE_FLOW_ITEM_TYPE_IPV6: - *mask = &rte_flow_item_ipv6_mask; - *size = sizeof(struct rte_ipv6_hdr); - return 1; - - case RTE_FLOW_ITEM_TYPE_ICMP: - *mask = &rte_flow_item_icmp_mask; - *size = sizeof(struct rte_flow_item_icmp); - return 1; - - case RTE_FLOW_ITEM_TYPE_UDP: - *mask = &rte_flow_item_udp_mask; - *size = sizeof(struct rte_flow_item_udp); - return 1; - - case RTE_FLOW_ITEM_TYPE_TCP: - *mask = &rte_flow_item_tcp_mask; - *size = sizeof(struct rte_flow_item_tcp); - return 1; - - case RTE_FLOW_ITEM_TYPE_SCTP: - *mask = &rte_flow_item_sctp_mask; - *size = sizeof(struct rte_flow_item_sctp); - return 1; - - case RTE_FLOW_ITEM_TYPE_VXLAN: - *mask = &rte_flow_item_vxlan_mask; - *size = sizeof(struct rte_flow_item_vxlan); - return 1; - - case RTE_FLOW_ITEM_TYPE_E_TAG: - *mask = &rte_flow_item_e_tag_mask; - *size = sizeof(struct rte_flow_item_e_tag); - return 1; - - case RTE_FLOW_ITEM_TYPE_NVGRE: - *mask = &rte_flow_item_nvgre_mask; - *size = sizeof(struct rte_flow_item_nvgre); - return 1; - - case RTE_FLOW_ITEM_TYPE_MPLS: - *mask = &rte_flow_item_mpls_mask; - *size = sizeof(struct rte_flow_item_mpls); - return 1; - - case RTE_FLOW_ITEM_TYPE_GRE: - *mask = &rte_flow_item_gre_mask; - *size = sizeof(struct rte_flow_item_gre); - return 1; - - case RTE_FLOW_ITEM_TYPE_GTP: - case RTE_FLOW_ITEM_TYPE_GTPC: - case RTE_FLOW_ITEM_TYPE_GTPU: - *mask = &rte_flow_item_gtp_mask; - *size = sizeof(struct rte_flow_item_gtp); - return 1; - - case RTE_FLOW_ITEM_TYPE_ESP: - *mask = &rte_flow_item_esp_mask; - *size = sizeof(struct rte_flow_item_esp); - return 1; - - case RTE_FLOW_ITEM_TYPE_GENEVE: - *mask = &rte_flow_item_geneve_mask; - *size = sizeof(struct rte_flow_item_geneve); - return 1; - - case RTE_FLOW_ITEM_TYPE_VXLAN_GPE: - *mask = &rte_flow_item_vxlan_gpe_mask; - *size = sizeof(struct rte_flow_item_vxlan_gpe); - return 1; - - case RTE_FLOW_ITEM_TYPE_ARP_ETH_IPV4: - *mask = &rte_flow_item_arp_eth_ipv4_mask; - *size = sizeof(struct rte_flow_item_arp_eth_ipv4); - return 1; - - case RTE_FLOW_ITEM_TYPE_IPV6_EXT: - *mask = &rte_flow_item_ipv6_ext_mask; - *size = sizeof(struct rte_flow_item_ipv6_ext); - return 1; - - case RTE_FLOW_ITEM_TYPE_ICMP6: - *mask = &rte_flow_item_icmp6_mask; - *size = sizeof(struct rte_flow_item_icmp6); - return 1; - - case RTE_FLOW_ITEM_TYPE_ICMP6_ND_NS: - *mask = &rte_flow_item_icmp6_nd_ns_mask; - *size = sizeof(struct rte_flow_item_icmp6_nd_ns); - return 1; - - case RTE_FLOW_ITEM_TYPE_ICMP6_ND_NA: - *mask = &rte_flow_item_icmp6_nd_na_mask; - *size = sizeof(struct rte_flow_item_icmp6_nd_na); - return 1; - - case RTE_FLOW_ITEM_TYPE_ICMP6_ND_OPT: - *mask = &rte_flow_item_icmp6_nd_opt_mask; - *size = sizeof(struct rte_flow_item_icmp6_nd_opt); - return 1; - - case RTE_FLOW_ITEM_TYPE_ICMP6_ND_OPT_SLA_ETH: - *mask = &rte_flow_item_icmp6_nd_opt_sla_eth_mask; - *size = sizeof(struct rte_flow_item_icmp6_nd_opt_sla_eth); - return 1; - - case RTE_FLOW_ITEM_TYPE_ICMP6_ND_OPT_TLA_ETH: - *mask = &rte_flow_item_icmp6_nd_opt_tla_eth_mask; - *size = sizeof(struct rte_flow_item_icmp6_nd_opt_tla_eth); - return 1; - - default: return 0; /* FALSE */ - } -} - -static int -flow_item_raw_preprocess(const struct rte_flow_item *item, - union flow_item *item_spec, - union flow_item *item_mask, - size_t *item_size, - int *item_disabled, - struct rte_flow_error *error) -{ - const struct rte_flow_item_raw *item_raw_spec = item->spec; - const struct rte_flow_item_raw *item_raw_mask = item->mask; - const uint8_t *pattern; - const uint8_t *pattern_mask; - uint8_t *spec = (uint8_t *)item_spec; - uint8_t *mask = (uint8_t *)item_mask; - size_t pattern_length, pattern_offset, i; - int disabled; - - if (!item->spec) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Null specification"); - - if (item->last) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Range not allowed (last must be NULL)"); - - if (item_raw_spec->relative == 0) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Absolute offset not supported"); - - if (item_raw_spec->search) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Search not supported"); - - if (item_raw_spec->offset < 0) - return rte_flow_error_set(error, - ENOTSUP, RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Negative offset not supported"); - - if (item_raw_spec->length == 0) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Zero pattern length"); - - if (item_raw_spec->offset + item_raw_spec->length > - TABLE_RULE_MATCH_SIZE_MAX) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Item too big"); - - if (!item_raw_spec->pattern && item_raw_mask && item_raw_mask->pattern) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "RAW: Non-NULL pattern mask not allowed with NULL pattern"); - - pattern = item_raw_spec->pattern; - pattern_mask = (item_raw_mask) ? item_raw_mask->pattern : NULL; - pattern_length = (size_t)item_raw_spec->length; - pattern_offset = (size_t)item_raw_spec->offset; - - disabled = 0; - if (pattern_mask == NULL) - disabled = 1; - else - for (i = 0; i < pattern_length; i++) - if ((pattern)[i]) - disabled = 1; - - memset(spec, 0, TABLE_RULE_MATCH_SIZE_MAX); - if (pattern) - memcpy(&spec[pattern_offset], pattern, pattern_length); - - memset(mask, 0, TABLE_RULE_MATCH_SIZE_MAX); - if (pattern_mask) - memcpy(&mask[pattern_offset], pattern_mask, pattern_length); - - *item_size = pattern_offset + pattern_length; - *item_disabled = disabled; - - return 0; -} - -static int -flow_item_proto_preprocess(const struct rte_flow_item *item, - union flow_item *item_spec, - union flow_item *item_mask, - size_t *item_size, - int *item_disabled, - struct rte_flow_error *error) -{ - const void *mask_default; - uint8_t *spec = (uint8_t *)item_spec; - uint8_t *mask = (uint8_t *)item_mask; - size_t size, i; - - if (!flow_item_is_proto(item->type, &mask_default, &size)) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "Item type not supported"); - - if (item->type == RTE_FLOW_ITEM_TYPE_RAW) - return flow_item_raw_preprocess(item, - item_spec, - item_mask, - item_size, - item_disabled, - error); - - /* spec */ - if (!item->spec) { - /* If spec is NULL, then last and mask also have to be NULL. */ - if (item->last || item->mask) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "Invalid item (NULL spec with non-NULL last or mask)"); - - memset(item_spec, 0, size); - memset(item_mask, 0, size); - *item_size = size; - *item_disabled = 1; /* TRUE */ - return 0; - } - - memcpy(spec, item->spec, size); - *item_size = size; - - /* mask */ - if (item->mask) - memcpy(mask, item->mask, size); - else - memcpy(mask, mask_default, size); - - /* disabled */ - for (i = 0; i < size; i++) - if (mask[i]) - break; - *item_disabled = (i == size) ? 1 : 0; - - /* Apply mask over spec. */ - for (i = 0; i < size; i++) - spec[i] &= mask[i]; - - /* last */ - if (item->last) { - uint8_t last[size]; - - /* init last */ - memcpy(last, item->last, size); - for (i = 0; i < size; i++) - last[i] &= mask[i]; - - /* check for range */ - for (i = 0; i < size; i++) - if (last[i] != spec[i]) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "Range not supported"); - } - - return 0; -} - -/*** - * Skip disabled protocol items and VOID items - * until any of the mutually exclusive conditions - * from the list below takes place: - * (A) A protocol present in the proto_mask - * is met (either ENABLED or DISABLED); - * (B) A protocol NOT present in the proto_mask is met in ENABLED state; - * (C) The END item is met. - */ -static int -flow_item_skip_disabled_protos(const struct rte_flow_item **item, - uint64_t proto_mask, - size_t *length, - struct rte_flow_error *error) -{ - size_t len = 0; - - for ( ; (*item)->type != RTE_FLOW_ITEM_TYPE_END; (*item)++) { - union flow_item spec, mask; - size_t size; - int disabled = 0, status; - - if ((*item)->type == RTE_FLOW_ITEM_TYPE_VOID) - continue; - - status = flow_item_proto_preprocess(*item, - &spec, - &mask, - &size, - &disabled, - error); - if (status) - return status; - - if ((proto_mask & (1LLU << (*item)->type)) || - !disabled) - break; - - len += size; - } - - if (length) - *length = len; - - return 0; -} - -#define FLOW_ITEM_PROTO_IP \ - ((1LLU << RTE_FLOW_ITEM_TYPE_IPV4) | \ - (1LLU << RTE_FLOW_ITEM_TYPE_IPV6)) - -static void -flow_item_skip_void(const struct rte_flow_item **item) -{ - for ( ; ; (*item)++) - if ((*item)->type != RTE_FLOW_ITEM_TYPE_VOID) - return; -} - -#define IP_PROTOCOL_TCP 0x06 -#define IP_PROTOCOL_UDP 0x11 -#define IP_PROTOCOL_SCTP 0x84 - -static int -mask_to_depth(uint64_t mask, - uint32_t *depth) -{ - uint64_t n; - - if (mask == UINT64_MAX) { - if (depth) - *depth = 64; - - return 0; - } - - mask = ~mask; - - if (mask & (mask + 1)) - return -1; - - n = __builtin_popcountll(mask); - if (depth) - *depth = (uint32_t)(64 - n); - - return 0; -} - -static int -ipv4_mask_to_depth(uint32_t mask, - uint32_t *depth) -{ - uint32_t d; - int status; - - status = mask_to_depth(mask | (UINT64_MAX << 32), &d); - if (status) - return status; - - d -= 32; - if (depth) - *depth = d; - - return 0; -} - -static int -ipv6_mask_to_depth(uint8_t *mask, - uint32_t *depth) -{ - uint64_t *m = (uint64_t *)mask; - uint64_t m0 = rte_be_to_cpu_64(m[0]); - uint64_t m1 = rte_be_to_cpu_64(m[1]); - uint32_t d0, d1; - int status; - - status = mask_to_depth(m0, &d0); - if (status) - return status; - - status = mask_to_depth(m1, &d1); - if (status) - return status; - - if (d0 < 64 && d1) - return -1; - - if (depth) - *depth = d0 + d1; - - return 0; -} - -static int -port_mask_to_range(uint16_t port, - uint16_t port_mask, - uint16_t *port0, - uint16_t *port1) -{ - int status; - uint16_t p0, p1; - - status = mask_to_depth(port_mask | (UINT64_MAX << 16), NULL); - if (status) - return -1; - - p0 = port & port_mask; - p1 = p0 | ~port_mask; - - if (port0) - *port0 = p0; - - if (port1) - *port1 = p1; - - return 0; -} - -static int -flow_rule_match_acl_get(struct pmd_internals *softnic __rte_unused, - struct pipeline *pipeline __rte_unused, - struct softnic_table *table __rte_unused, - const struct rte_flow_attr *attr, - const struct rte_flow_item *item, - struct softnic_table_rule_match *rule_match, - struct rte_flow_error *error) -{ - union flow_item spec, mask; - size_t size, length = 0; - int disabled = 0, status; - uint8_t ip_proto, ip_proto_mask; - - memset(rule_match, 0, sizeof(*rule_match)); - rule_match->match_type = TABLE_ACL; - rule_match->match.acl.priority = attr->priority; - - /* VOID or disabled protos only, if any. */ - status = flow_item_skip_disabled_protos(&item, - FLOW_ITEM_PROTO_IP, &length, error); - if (status) - return status; - - /* IP only. */ - status = flow_item_proto_preprocess(item, &spec, &mask, - &size, &disabled, error); - if (status) - return status; - - switch (item->type) { - case RTE_FLOW_ITEM_TYPE_IPV4: - { - uint32_t sa_depth, da_depth; - - status = ipv4_mask_to_depth(rte_ntohl(mask.ipv4.hdr.src_addr), - &sa_depth); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal IPv4 header source address mask"); - - status = ipv4_mask_to_depth(rte_ntohl(mask.ipv4.hdr.dst_addr), - &da_depth); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal IPv4 header destination address mask"); - - ip_proto = spec.ipv4.hdr.next_proto_id; - ip_proto_mask = mask.ipv4.hdr.next_proto_id; - - rule_match->match.acl.ip_version = 1; - rule_match->match.acl.ipv4.sa = - rte_ntohl(spec.ipv4.hdr.src_addr); - rule_match->match.acl.ipv4.da = - rte_ntohl(spec.ipv4.hdr.dst_addr); - rule_match->match.acl.sa_depth = sa_depth; - rule_match->match.acl.da_depth = da_depth; - rule_match->match.acl.proto = ip_proto; - rule_match->match.acl.proto_mask = ip_proto_mask; - break; - } /* RTE_FLOW_ITEM_TYPE_IPV4 */ - - case RTE_FLOW_ITEM_TYPE_IPV6: - { - uint32_t sa_depth, da_depth; - - status = ipv6_mask_to_depth(mask.ipv6.hdr.src_addr, &sa_depth); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal IPv6 header source address mask"); - - status = ipv6_mask_to_depth(mask.ipv6.hdr.dst_addr, &da_depth); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal IPv6 header destination address mask"); - - ip_proto = spec.ipv6.hdr.proto; - ip_proto_mask = mask.ipv6.hdr.proto; - - rule_match->match.acl.ip_version = 0; - memcpy(rule_match->match.acl.ipv6.sa, - spec.ipv6.hdr.src_addr, - sizeof(spec.ipv6.hdr.src_addr)); - memcpy(rule_match->match.acl.ipv6.da, - spec.ipv6.hdr.dst_addr, - sizeof(spec.ipv6.hdr.dst_addr)); - rule_match->match.acl.sa_depth = sa_depth; - rule_match->match.acl.da_depth = da_depth; - rule_match->match.acl.proto = ip_proto; - rule_match->match.acl.proto_mask = ip_proto_mask; - break; - } /* RTE_FLOW_ITEM_TYPE_IPV6 */ - - default: - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: IP protocol required"); - } /* switch */ - - if (ip_proto_mask != UINT8_MAX) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal IP protocol mask"); - - item++; - - /* VOID only, if any. */ - flow_item_skip_void(&item); - - /* TCP/UDP/SCTP only. */ - status = flow_item_proto_preprocess(item, &spec, &mask, - &size, &disabled, error); - if (status) - return status; - - switch (item->type) { - case RTE_FLOW_ITEM_TYPE_TCP: - { - uint16_t sp0, sp1, dp0, dp1; - - if (ip_proto != IP_PROTOCOL_TCP) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Item type is TCP, but IP protocol is not"); - - status = port_mask_to_range(rte_ntohs(spec.tcp.hdr.src_port), - rte_ntohs(mask.tcp.hdr.src_port), - &sp0, - &sp1); - - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal TCP source port mask"); - - status = port_mask_to_range(rte_ntohs(spec.tcp.hdr.dst_port), - rte_ntohs(mask.tcp.hdr.dst_port), - &dp0, - &dp1); - - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal TCP destination port mask"); - - rule_match->match.acl.sp0 = sp0; - rule_match->match.acl.sp1 = sp1; - rule_match->match.acl.dp0 = dp0; - rule_match->match.acl.dp1 = dp1; - - break; - } /* RTE_FLOW_ITEM_TYPE_TCP */ - - case RTE_FLOW_ITEM_TYPE_UDP: - { - uint16_t sp0, sp1, dp0, dp1; - - if (ip_proto != IP_PROTOCOL_UDP) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Item type is UDP, but IP protocol is not"); - - status = port_mask_to_range(rte_ntohs(spec.udp.hdr.src_port), - rte_ntohs(mask.udp.hdr.src_port), - &sp0, - &sp1); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal UDP source port mask"); - - status = port_mask_to_range(rte_ntohs(spec.udp.hdr.dst_port), - rte_ntohs(mask.udp.hdr.dst_port), - &dp0, - &dp1); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal UDP destination port mask"); - - rule_match->match.acl.sp0 = sp0; - rule_match->match.acl.sp1 = sp1; - rule_match->match.acl.dp0 = dp0; - rule_match->match.acl.dp1 = dp1; - - break; - } /* RTE_FLOW_ITEM_TYPE_UDP */ - - case RTE_FLOW_ITEM_TYPE_SCTP: - { - uint16_t sp0, sp1, dp0, dp1; - - if (ip_proto != IP_PROTOCOL_SCTP) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Item type is SCTP, but IP protocol is not"); - - status = port_mask_to_range(rte_ntohs(spec.sctp.hdr.src_port), - rte_ntohs(mask.sctp.hdr.src_port), - &sp0, - &sp1); - - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal SCTP source port mask"); - - status = port_mask_to_range(rte_ntohs(spec.sctp.hdr.dst_port), - rte_ntohs(mask.sctp.hdr.dst_port), - &dp0, - &dp1); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Illegal SCTP destination port mask"); - - rule_match->match.acl.sp0 = sp0; - rule_match->match.acl.sp1 = sp1; - rule_match->match.acl.dp0 = dp0; - rule_match->match.acl.dp1 = dp1; - - break; - } /* RTE_FLOW_ITEM_TYPE_SCTP */ - - default: - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: TCP/UDP/SCTP required"); - } /* switch */ - - item++; - - /* VOID or disabled protos only, if any. */ - status = flow_item_skip_disabled_protos(&item, 0, NULL, error); - if (status) - return status; - - /* END only. */ - if (item->type != RTE_FLOW_ITEM_TYPE_END) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "ACL: Expecting END item"); - - return 0; -} - -/*** - * Both *tmask* and *fmask* are byte arrays of size *tsize* and *fsize* - * respectively. - * They are located within a larger buffer at offsets *toffset* and *foffset* - * respectively. Both *tmask* and *fmask* represent bitmasks for the larger - * buffer. - * Question: are the two masks equivalent? - * - * Notes: - * 1. Offset basically indicates that the first offset bytes in the buffer - * are "don't care", so offset is equivalent to pre-pending an "all-zeros" - * array of *offset* bytes to the *mask*. - * 2. Each *mask* might contain a number of zero bytes at the beginning or - * at the end. - * 3. Bytes in the larger buffer after the end of the *mask* are also considered - * "don't care", so they are equivalent to appending an "all-zeros" array of - * bytes to the *mask*. - * - * Example: - * Buffer = [xx xx xx xx xx xx xx xx], buffer size = 8 bytes - * tmask = [00 22 00 33 00], toffset = 2, tsize = 5 - * => buffer mask = [00 00 00 22 00 33 00 00] - * fmask = [22 00 33], foffset = 3, fsize = 3 => - * => buffer mask = [00 00 00 22 00 33 00 00] - * Therefore, the tmask and fmask from this example are equivalent. - */ -static int -hash_key_mask_is_same(uint8_t *tmask, - size_t toffset, - size_t tsize, - uint8_t *fmask, - size_t foffset, - size_t fsize, - size_t *toffset_plus, - size_t *foffset_plus) -{ - size_t tpos; /* Position of first non-zero byte in the tmask buffer. */ - size_t fpos; /* Position of first non-zero byte in the fmask buffer. */ - - /* Compute tpos and fpos. */ - for (tpos = 0; tmask[tpos] == 0; tpos++) - ; - for (fpos = 0; fmask[fpos] == 0; fpos++) - ; - - if (toffset + tpos != foffset + fpos) - return 0; /* FALSE */ - - tsize -= tpos; - fsize -= fpos; - - if (tsize < fsize) { - size_t i; - - for (i = 0; i < tsize; i++) - if (tmask[tpos + i] != fmask[fpos + i]) - return 0; /* FALSE */ - - for ( ; i < fsize; i++) - if (fmask[fpos + i]) - return 0; /* FALSE */ - } else { - size_t i; - - for (i = 0; i < fsize; i++) - if (tmask[tpos + i] != fmask[fpos + i]) - return 0; /* FALSE */ - - for ( ; i < tsize; i++) - if (tmask[tpos + i]) - return 0; /* FALSE */ - } - - if (toffset_plus) - *toffset_plus = tpos; - - if (foffset_plus) - *foffset_plus = fpos; - - return 1; /* TRUE */ -} - -static int -flow_rule_match_hash_get(struct pmd_internals *softnic __rte_unused, - struct pipeline *pipeline __rte_unused, - struct softnic_table *table, - const struct rte_flow_attr *attr __rte_unused, - const struct rte_flow_item *item, - struct softnic_table_rule_match *rule_match, - struct rte_flow_error *error) -{ - struct softnic_table_rule_match_hash key, key_mask; - struct softnic_table_hash_params *params = &table->params.match.hash; - size_t offset = 0, length = 0, tpos, fpos; - int status; - - memset(&key, 0, sizeof(key)); - memset(&key_mask, 0, sizeof(key_mask)); - - /* VOID or disabled protos only, if any. */ - status = flow_item_skip_disabled_protos(&item, 0, &offset, error); - if (status) - return status; - - if (item->type == RTE_FLOW_ITEM_TYPE_END) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "HASH: END detected too early"); - - /* VOID or any protocols (enabled or disabled). */ - for ( ; item->type != RTE_FLOW_ITEM_TYPE_END; item++) { - union flow_item spec, mask; - size_t size; - int disabled, status; - - if (item->type == RTE_FLOW_ITEM_TYPE_VOID) - continue; - - status = flow_item_proto_preprocess(item, - &spec, - &mask, - &size, - &disabled, - error); - if (status) - return status; - - if (length + size > sizeof(key)) { - if (disabled) - break; - - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "HASH: Item too big"); - } - - memcpy(&key.key[length], &spec, size); - memcpy(&key_mask.key[length], &mask, size); - length += size; - } - - if (item->type != RTE_FLOW_ITEM_TYPE_END) { - /* VOID or disabled protos only, if any. */ - status = flow_item_skip_disabled_protos(&item, 0, NULL, error); - if (status) - return status; - - /* END only. */ - if (item->type != RTE_FLOW_ITEM_TYPE_END) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "HASH: Expecting END item"); - } - - /* Compare flow key mask against table key mask. */ - offset += sizeof(struct rte_mbuf) + RTE_PKTMBUF_HEADROOM; - - if (!hash_key_mask_is_same(params->key_mask, - params->key_offset, - params->key_size, - key_mask.key, - offset, - length, - &tpos, - &fpos)) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "HASH: Item list is not observing the match format"); - - /* Rule match. */ - memset(rule_match, 0, sizeof(*rule_match)); - rule_match->match_type = TABLE_HASH; - memcpy(&rule_match->match.hash.key[tpos], - &key.key[fpos], - RTE_MIN(sizeof(rule_match->match.hash.key) - tpos, - length - fpos)); - - return 0; -} - -static int -flow_rule_match_get(struct pmd_internals *softnic, - struct pipeline *pipeline, - struct softnic_table *table, - const struct rte_flow_attr *attr, - const struct rte_flow_item *item, - struct softnic_table_rule_match *rule_match, - struct rte_flow_error *error) -{ - switch (table->params.match_type) { - case TABLE_ACL: - return flow_rule_match_acl_get(softnic, - pipeline, - table, - attr, - item, - rule_match, - error); - - /* FALLTHROUGH */ - - case TABLE_HASH: - return flow_rule_match_hash_get(softnic, - pipeline, - table, - attr, - item, - rule_match, - error); - - /* FALLTHROUGH */ - - default: - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Unsupported pipeline table match type"); - } -} - -static int -flow_rule_action_get(struct pmd_internals *softnic, - struct pipeline *pipeline, - struct softnic_table *table, - const struct rte_flow_attr *attr, - const struct rte_flow_action *action, - struct softnic_table_rule_action *rule_action, - struct rte_flow_error *error) -{ - struct softnic_table_action_profile *profile; - struct softnic_table_action_profile_params *params; - struct softnic_mtr_meter_policy *policy; - int n_jump_queue_rss_drop = 0; - int n_count = 0; - int n_mark = 0; - int n_vxlan_decap = 0; - - profile = softnic_table_action_profile_find(softnic, - table->params.action_profile_name); - if (profile == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - action, - "JUMP: Table action profile"); - - params = &profile->params; - - for ( ; action->type != RTE_FLOW_ACTION_TYPE_END; action++) { - if (action->type == RTE_FLOW_ACTION_TYPE_VOID) - continue; - - switch (action->type) { - case RTE_FLOW_ACTION_TYPE_JUMP: - { - const struct rte_flow_action_jump *conf = action->conf; - struct flow_attr_map *map; - - if (conf == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "JUMP: Null configuration"); - - if (n_jump_queue_rss_drop) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Only one termination action is" - " allowed per flow"); - - if ((params->action_mask & - (1LLU << RTE_TABLE_ACTION_FWD)) == 0) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "JUMP action not enabled for this table"); - - n_jump_queue_rss_drop = 1; - - map = flow_attr_map_get(softnic, - conf->group, - attr->ingress); - if (map == NULL || map->valid == 0) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "JUMP: Invalid group mapping"); - - if (strcmp(pipeline->name, map->pipeline_name) != 0) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "JUMP: Jump to table in different pipeline"); - - /* RTE_TABLE_ACTION_FWD */ - rule_action->fwd.action = RTE_PIPELINE_ACTION_TABLE; - rule_action->fwd.id = map->table_id; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_FWD; - break; - } /* RTE_FLOW_ACTION_TYPE_JUMP */ - - case RTE_FLOW_ACTION_TYPE_QUEUE: - { - char name[NAME_SIZE]; - struct rte_eth_dev *dev; - const struct rte_flow_action_queue *conf = action->conf; - uint32_t port_id; - int status; - - if (conf == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "QUEUE: Null configuration"); - - if (n_jump_queue_rss_drop) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Only one termination action is allowed" - " per flow"); - - if ((params->action_mask & - (1LLU << RTE_TABLE_ACTION_FWD)) == 0) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "QUEUE action not enabled for this table"); - - n_jump_queue_rss_drop = 1; - - dev = ETHDEV(softnic); - if (dev == NULL || - conf->index >= dev->data->nb_rx_queues) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "QUEUE: Invalid RX queue ID"); - - snprintf(name, sizeof(name), "RXQ%u", - (uint32_t)conf->index); - - status = softnic_pipeline_port_out_find(softnic, - pipeline->name, - name, - &port_id); - if (status) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "QUEUE: RX queue not accessible from this pipeline"); - - /* RTE_TABLE_ACTION_FWD */ - rule_action->fwd.action = RTE_PIPELINE_ACTION_PORT; - rule_action->fwd.id = port_id; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_FWD; - break; - } /*RTE_FLOW_ACTION_TYPE_QUEUE */ - - case RTE_FLOW_ACTION_TYPE_RSS: - { - const struct rte_flow_action_rss *conf = action->conf; - uint32_t i; - - if (conf == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "RSS: Null configuration"); - - if (!rte_is_power_of_2(conf->queue_num)) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION_CONF, - conf, - "RSS: Number of queues must be a power of 2"); - - if (conf->queue_num > RTE_DIM(rule_action->lb.out)) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION_CONF, - conf, - "RSS: Number of queues too big"); - - if (n_jump_queue_rss_drop) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Only one termination action is allowed per flow"); - - if (((params->action_mask & - (1LLU << RTE_TABLE_ACTION_FWD)) == 0) || - ((params->action_mask & - (1LLU << RTE_TABLE_ACTION_LB)) == 0)) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "RSS action not supported by this table"); - - if (params->lb.out_offset != - pipeline->params.offset_port_id) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "RSS action not supported by this pipeline"); - - n_jump_queue_rss_drop = 1; - - /* RTE_TABLE_ACTION_LB */ - for (i = 0; i < conf->queue_num; i++) { - char name[NAME_SIZE]; - struct rte_eth_dev *dev; - uint32_t port_id; - int status; - - dev = ETHDEV(softnic); - if (dev == NULL || - conf->queue[i] >= - dev->data->nb_rx_queues) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "RSS: Invalid RX queue ID"); - - snprintf(name, sizeof(name), "RXQ%u", - (uint32_t)conf->queue[i]); - - status = softnic_pipeline_port_out_find(softnic, - pipeline->name, - name, - &port_id); - if (status) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "RSS: RX queue not accessible from this pipeline"); - - rule_action->lb.out[i] = port_id; - } - - for ( ; i < RTE_DIM(rule_action->lb.out); i++) - rule_action->lb.out[i] = - rule_action->lb.out[i % conf->queue_num]; - - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_LB; - - /* RTE_TABLE_ACTION_FWD */ - rule_action->fwd.action = RTE_PIPELINE_ACTION_PORT_META; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_FWD; - break; - } /* RTE_FLOW_ACTION_TYPE_RSS */ - - case RTE_FLOW_ACTION_TYPE_DROP: - { - const void *conf = action->conf; - - if (conf != NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "DROP: No configuration required"); - - if (n_jump_queue_rss_drop) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Only one termination action is allowed per flow"); - if ((params->action_mask & - (1LLU << RTE_TABLE_ACTION_FWD)) == 0) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "DROP action not supported by this table"); - - n_jump_queue_rss_drop = 1; - - /* RTE_TABLE_ACTION_FWD */ - rule_action->fwd.action = RTE_PIPELINE_ACTION_DROP; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_FWD; - break; - } /* RTE_FLOW_ACTION_TYPE_DROP */ - - case RTE_FLOW_ACTION_TYPE_COUNT: - { - const struct rte_flow_action_count *conf = action->conf; - - if (conf == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "COUNT: Null configuration"); - - if (n_count) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Only one COUNT action per flow"); - - if ((params->action_mask & - (1LLU << RTE_TABLE_ACTION_STATS)) == 0) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "COUNT action not supported by this table"); - - n_count = 1; - - /* RTE_TABLE_ACTION_STATS */ - rule_action->stats.n_packets = 0; - rule_action->stats.n_bytes = 0; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_STATS; - break; - } /* RTE_FLOW_ACTION_TYPE_COUNT */ - - case RTE_FLOW_ACTION_TYPE_MARK: - { - const struct rte_flow_action_mark *conf = action->conf; - - if (conf == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "MARK: Null configuration"); - - if (n_mark) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Only one MARK action per flow"); - - if ((params->action_mask & - (1LLU << RTE_TABLE_ACTION_TAG)) == 0) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "MARK action not supported by this table"); - - n_mark = 1; - - /* RTE_TABLE_ACTION_TAG */ - rule_action->tag.tag = conf->id; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_TAG; - break; - } /* RTE_FLOW_ACTION_TYPE_MARK */ - - case RTE_FLOW_ACTION_TYPE_VXLAN_DECAP: - { - const struct rte_flow_action_mark *conf = action->conf; - - if (conf) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "VXLAN DECAP: Non-null configuration"); - - if (n_vxlan_decap) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Only one VXLAN DECAP action per flow"); - - if ((params->action_mask & - (1LLU << RTE_TABLE_ACTION_DECAP)) == 0) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "VXLAN DECAP action not supported by this table"); - - n_vxlan_decap = 1; - - /* RTE_TABLE_ACTION_DECAP */ - rule_action->decap.n = 50; /* Ether/IPv4/UDP/VXLAN */ - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_DECAP; - break; - } /* RTE_FLOW_ACTION_TYPE_VXLAN_DECAP */ - - case RTE_FLOW_ACTION_TYPE_METER: - { - const struct rte_flow_action_meter *conf = action->conf; - struct softnic_mtr_meter_profile *mp; - struct softnic_mtr *m; - uint32_t table_id = table - pipeline->table; - uint32_t meter_profile_id; - int status; - - if ((params->action_mask & (1LLU << RTE_TABLE_ACTION_MTR)) == 0) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "METER: Table action not supported"); - - if (params->mtr.n_tc != 1) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "METER: Multiple TCs not supported"); - - if (conf == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "METER: Null configuration"); - - m = softnic_mtr_find(softnic, conf->mtr_id); - - if (m == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION_CONF, - NULL, - "METER: Invalid meter ID"); - - if (m->flow) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION_CONF, - NULL, - "METER: Meter already attached to a flow"); - - meter_profile_id = m->params.meter_profile_id; - mp = softnic_mtr_meter_profile_find(softnic, meter_profile_id); - - /* Add meter profile to pipeline table */ - if (!softnic_pipeline_table_meter_profile_find(table, - meter_profile_id)) { - struct rte_table_action_meter_profile profile; - - memset(&profile, 0, sizeof(profile)); - profile.alg = RTE_TABLE_ACTION_METER_TRTCM; - profile.trtcm.cir = mp->params.trtcm_rfc2698.cir; - profile.trtcm.pir = mp->params.trtcm_rfc2698.pir; - profile.trtcm.cbs = mp->params.trtcm_rfc2698.cbs; - profile.trtcm.pbs = mp->params.trtcm_rfc2698.pbs; - - status = softnic_pipeline_table_mtr_profile_add(softnic, - pipeline->name, - table_id, - meter_profile_id, - &profile); - if (status) { - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "METER: Table meter profile add failed"); - return -1; - } - } - /* Meter policy must exist */ - policy = softnic_mtr_meter_policy_find(softnic, - m->params.meter_policy_id); - if (policy == NULL) { - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "METER: fail to find meter policy"); - return -1; - } - /* RTE_TABLE_ACTION_METER */ - rule_action->mtr.mtr[0].meter_profile_id = meter_profile_id; - rule_action->mtr.mtr[0].policer[RTE_COLOR_GREEN] = - policy->policer[RTE_COLOR_GREEN]; - rule_action->mtr.mtr[0].policer[RTE_COLOR_YELLOW] = - policy->policer[RTE_COLOR_YELLOW]; - rule_action->mtr.mtr[0].policer[RTE_COLOR_RED] = - policy->policer[RTE_COLOR_RED]; - rule_action->mtr.tc_mask = 1; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_MTR; - break; - } /* RTE_FLOW_ACTION_TYPE_METER */ - - case RTE_FLOW_ACTION_TYPE_VXLAN_ENCAP: - { - const struct rte_flow_action_vxlan_encap *conf = - action->conf; - const struct rte_flow_item *item; - union flow_item spec, mask; - int disabled = 0, status; - size_t size; - - if (conf == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "VXLAN ENCAP: Null configuration"); - - item = conf->definition; - if (item == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "VXLAN ENCAP: Null configuration definition"); - - if (!(params->action_mask & - (1LLU << RTE_TABLE_ACTION_ENCAP))) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "VXLAN ENCAP: Encap action not enabled for this table"); - - /* Check for Ether. */ - flow_item_skip_void(&item); - status = flow_item_proto_preprocess(item, &spec, &mask, - &size, &disabled, error); - if (status) - return status; - - if (item->type != RTE_FLOW_ITEM_TYPE_ETH) { - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "VXLAN ENCAP: first encap item should be ether"); - } - rte_ether_addr_copy(&spec.eth.dst, - &rule_action->encap.vxlan.ether.da); - rte_ether_addr_copy(&spec.eth.src, - &rule_action->encap.vxlan.ether.sa); - - item++; - - /* Check for VLAN. */ - flow_item_skip_void(&item); - status = flow_item_proto_preprocess(item, &spec, &mask, - &size, &disabled, error); - if (status) - return status; - - if (item->type == RTE_FLOW_ITEM_TYPE_VLAN) { - if (!params->encap.vxlan.vlan) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "VXLAN ENCAP: vlan encap not supported by table"); - - uint16_t tci = rte_ntohs(spec.vlan.tci); - rule_action->encap.vxlan.vlan.pcp = - tci >> 13; - rule_action->encap.vxlan.vlan.dei = - (tci >> 12) & 0x1; - rule_action->encap.vxlan.vlan.vid = - tci & 0xfff; - - item++; - - flow_item_skip_void(&item); - status = flow_item_proto_preprocess(item, &spec, - &mask, &size, &disabled, error); - if (status) - return status; - } else { - if (params->encap.vxlan.vlan) - return rte_flow_error_set(error, - ENOTSUP, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "VXLAN ENCAP: expecting vlan encap item"); - } - - /* Check for IPV4/IPV6. */ - switch (item->type) { - case RTE_FLOW_ITEM_TYPE_IPV4: - { - rule_action->encap.vxlan.ipv4.sa = - rte_ntohl(spec.ipv4.hdr.src_addr); - rule_action->encap.vxlan.ipv4.da = - rte_ntohl(spec.ipv4.hdr.dst_addr); - rule_action->encap.vxlan.ipv4.dscp = - spec.ipv4.hdr.type_of_service >> 2; - rule_action->encap.vxlan.ipv4.ttl = - spec.ipv4.hdr.time_to_live; - break; - } - case RTE_FLOW_ITEM_TYPE_IPV6: - { - uint32_t vtc_flow; - - memcpy(&rule_action->encap.vxlan.ipv6.sa, - &spec.ipv6.hdr.src_addr, - sizeof(spec.ipv6.hdr.src_addr)); - memcpy(&rule_action->encap.vxlan.ipv6.da, - &spec.ipv6.hdr.dst_addr, - sizeof(spec.ipv6.hdr.dst_addr)); - vtc_flow = rte_ntohl(spec.ipv6.hdr.vtc_flow); - rule_action->encap.vxlan.ipv6.flow_label = - vtc_flow & 0xfffff; - rule_action->encap.vxlan.ipv6.dscp = - (vtc_flow >> 22) & 0x3f; - rule_action->encap.vxlan.ipv6.hop_limit = - spec.ipv6.hdr.hop_limits; - break; - } - default: - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "VXLAN ENCAP: encap item after ether should be ipv4/ipv6"); - } - - item++; - - /* Check for UDP. */ - flow_item_skip_void(&item); - status = flow_item_proto_preprocess(item, &spec, &mask, - &size, &disabled, error); - if (status) - return status; - - if (item->type != RTE_FLOW_ITEM_TYPE_UDP) { - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "VXLAN ENCAP: encap item after ipv4/ipv6 should be udp"); - } - rule_action->encap.vxlan.udp.sp = - rte_ntohs(spec.udp.hdr.src_port); - rule_action->encap.vxlan.udp.dp = - rte_ntohs(spec.udp.hdr.dst_port); - - item++; - - /* Check for VXLAN. */ - flow_item_skip_void(&item); - status = flow_item_proto_preprocess(item, &spec, &mask, - &size, &disabled, error); - if (status) - return status; - - if (item->type != RTE_FLOW_ITEM_TYPE_VXLAN) { - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "VXLAN ENCAP: encap item after udp should be vxlan"); - } - rule_action->encap.vxlan.vxlan.vni = - (spec.vxlan.vni[0] << 16U | - spec.vxlan.vni[1] << 8U - | spec.vxlan.vni[2]); - - item++; - - /* Check for END. */ - flow_item_skip_void(&item); - - if (item->type != RTE_FLOW_ITEM_TYPE_END) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - item, - "VXLAN ENCAP: expecting END item"); - - rule_action->encap.type = RTE_TABLE_ACTION_ENCAP_VXLAN; - rule_action->action_mask |= 1 << RTE_TABLE_ACTION_ENCAP; - break; - } /* RTE_FLOW_ACTION_TYPE_VXLAN_ENCAP */ - - default: - return -ENOTSUP; - } - } - - if (n_jump_queue_rss_drop == 0) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - action, - "Flow does not have any terminating action"); - - return 0; -} - -static int -pmd_flow_validate(struct rte_eth_dev *dev, - const struct rte_flow_attr *attr, - const struct rte_flow_item item[], - const struct rte_flow_action action[], - struct rte_flow_error *error) -{ - struct softnic_table_rule_match rule_match; - struct softnic_table_rule_action rule_action; - - struct pmd_internals *softnic = dev->data->dev_private; - struct pipeline *pipeline; - struct softnic_table *table; - const char *pipeline_name = NULL; - uint32_t table_id = 0; - int status; - - /* Check input parameters. */ - if (attr == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ATTR, - NULL, "Null attr"); - - if (item == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, - "Null item"); - - if (action == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - NULL, - "Null action"); - - /* Identify the pipeline table to add this flow to. */ - status = flow_pipeline_table_get(softnic, attr, &pipeline_name, - &table_id, error); - if (status) - return status; - - pipeline = softnic_pipeline_find(softnic, pipeline_name); - if (pipeline == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Invalid pipeline name"); - - if (table_id >= pipeline->n_tables) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Invalid pipeline table ID"); - - table = &pipeline->table[table_id]; - - /* Rule match. */ - memset(&rule_match, 0, sizeof(rule_match)); - status = flow_rule_match_get(softnic, - pipeline, - table, - attr, - item, - &rule_match, - error); - if (status) - return status; - - /* Rule action. */ - memset(&rule_action, 0, sizeof(rule_action)); - status = flow_rule_action_get(softnic, - pipeline, - table, - attr, - action, - &rule_action, - error); - if (status) - return status; - - return 0; -} - -static struct softnic_mtr * -flow_action_meter_get(struct pmd_internals *softnic, - const struct rte_flow_action *action) -{ - for ( ; action->type != RTE_FLOW_ACTION_TYPE_END; action++) - if (action->type == RTE_FLOW_ACTION_TYPE_METER) { - const struct rte_flow_action_meter *conf = action->conf; - - if (conf == NULL) - return NULL; - - return softnic_mtr_find(softnic, conf->mtr_id); - } - - return NULL; -} - -static void -flow_meter_owner_reset(struct pmd_internals *softnic, - struct rte_flow *flow) -{ - struct softnic_mtr_list *ml = &softnic->mtr.mtrs; - struct softnic_mtr *m; - - TAILQ_FOREACH(m, ml, node) - if (m->flow == flow) { - m->flow = NULL; - break; - } -} - -static void -flow_meter_owner_set(struct pmd_internals *softnic, - struct rte_flow *flow, - struct softnic_mtr *mtr) -{ - /* Reset current flow meter */ - flow_meter_owner_reset(softnic, flow); - - /* Set new flow meter */ - mtr->flow = flow; -} - -static int -is_meter_action_enable(struct pmd_internals *softnic, - struct softnic_table *table) -{ - struct softnic_table_action_profile *profile = - softnic_table_action_profile_find(softnic, - table->params.action_profile_name); - struct softnic_table_action_profile_params *params = &profile->params; - - return (params->action_mask & (1LLU << RTE_TABLE_ACTION_MTR)) ? 1 : 0; -} - -static struct rte_flow * -pmd_flow_create(struct rte_eth_dev *dev, - const struct rte_flow_attr *attr, - const struct rte_flow_item item[], - const struct rte_flow_action action[], - struct rte_flow_error *error) -{ - struct softnic_table_rule_match rule_match; - struct softnic_table_rule_action rule_action; - void *rule_data; - - struct pmd_internals *softnic = dev->data->dev_private; - struct pipeline *pipeline; - struct softnic_table *table; - struct rte_flow *flow; - struct softnic_mtr *mtr; - const char *pipeline_name = NULL; - uint32_t table_id = 0; - int new_flow, status; - - /* Check input parameters. */ - if (attr == NULL) { - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ATTR, - NULL, - "Null attr"); - return NULL; - } - - if (item == NULL) { - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ITEM, - NULL, - "Null item"); - return NULL; - } - - if (action == NULL) { - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_ACTION, - NULL, - "Null action"); - return NULL; - } - - /* Identify the pipeline table to add this flow to. */ - status = flow_pipeline_table_get(softnic, attr, &pipeline_name, - &table_id, error); - if (status) - return NULL; - - pipeline = softnic_pipeline_find(softnic, pipeline_name); - if (pipeline == NULL) { - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Invalid pipeline name"); - return NULL; - } - - if (table_id >= pipeline->n_tables) { - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Invalid pipeline table ID"); - return NULL; - } - - table = &pipeline->table[table_id]; - - /* Rule match. */ - memset(&rule_match, 0, sizeof(rule_match)); - status = flow_rule_match_get(softnic, - pipeline, - table, - attr, - item, - &rule_match, - error); - if (status) - return NULL; - - /* Rule action. */ - memset(&rule_action, 0, sizeof(rule_action)); - status = flow_rule_action_get(softnic, - pipeline, - table, - attr, - action, - &rule_action, - error); - if (status) - return NULL; - - /* Flow find/allocate. */ - new_flow = 0; - flow = softnic_flow_find(table, &rule_match); - if (flow == NULL) { - new_flow = 1; - flow = calloc(1, sizeof(struct rte_flow)); - if (flow == NULL) { - rte_flow_error_set(error, - ENOMEM, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Not enough memory for new flow"); - return NULL; - } - } - - /* Rule add. */ - status = softnic_pipeline_table_rule_add(softnic, - pipeline_name, - table_id, - &rule_match, - &rule_action, - &rule_data); - if (status) { - if (new_flow) - free(flow); - - rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Pipeline table rule add failed"); - return NULL; - } - - /* Flow fill in. */ - memcpy(&flow->match, &rule_match, sizeof(rule_match)); - memcpy(&flow->action, &rule_action, sizeof(rule_action)); - flow->data = rule_data; - flow->pipeline = pipeline; - flow->table_id = table_id; - - mtr = flow_action_meter_get(softnic, action); - if (mtr) - flow_meter_owner_set(softnic, flow, mtr); - - /* Flow add to list. */ - if (new_flow) - TAILQ_INSERT_TAIL(&table->flows, flow, node); - - return flow; -} - -static int -pmd_flow_destroy(struct rte_eth_dev *dev, - struct rte_flow *flow, - struct rte_flow_error *error) -{ - struct pmd_internals *softnic = dev->data->dev_private; - struct softnic_table *table; - int status; - - /* Check input parameters. */ - if (flow == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_HANDLE, - NULL, - "Null flow"); - - table = &flow->pipeline->table[flow->table_id]; - - /* Rule delete. */ - status = softnic_pipeline_table_rule_delete(softnic, - flow->pipeline->name, - flow->table_id, - &flow->match); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Pipeline table rule delete failed"); - - /* Update dependencies */ - if (is_meter_action_enable(softnic, table)) - flow_meter_owner_reset(softnic, flow); - - /* Flow delete. */ - TAILQ_REMOVE(&table->flows, flow, node); - free(flow); - - return 0; -} - -static int -pmd_flow_flush(struct rte_eth_dev *dev, - struct rte_flow_error *error) -{ - struct pmd_internals *softnic = dev->data->dev_private; - struct pipeline *pipeline; - int fail_to_del_rule = 0; - uint32_t i; - - TAILQ_FOREACH(pipeline, &softnic->pipeline_list, node) { - /* Remove all the flows added to the tables. */ - for (i = 0; i < pipeline->n_tables; i++) { - struct softnic_table *table = &pipeline->table[i]; - struct rte_flow *flow; - void *temp; - int status; - - RTE_TAILQ_FOREACH_SAFE(flow, &table->flows, node, - temp) { - /* Rule delete. */ - status = softnic_pipeline_table_rule_delete - (softnic, - pipeline->name, - i, - &flow->match); - if (status) - fail_to_del_rule = 1; - /* Update dependencies */ - if (is_meter_action_enable(softnic, table)) - flow_meter_owner_reset(softnic, flow); - - /* Flow delete. */ - TAILQ_REMOVE(&table->flows, flow, node); - free(flow); - } - } - } - - if (fail_to_del_rule) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Some of the rules could not be deleted"); - - return 0; -} - -static int -pmd_flow_query(struct rte_eth_dev *dev __rte_unused, - struct rte_flow *flow, - const struct rte_flow_action *action __rte_unused, - void *data, - struct rte_flow_error *error) -{ - struct rte_table_action_stats_counters stats; - struct softnic_table *table; - struct rte_flow_query_count *flow_stats = data; - int status; - - /* Check input parameters. */ - if (flow == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_HANDLE, - NULL, - "Null flow"); - - if (data == NULL) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Null data"); - - table = &flow->pipeline->table[flow->table_id]; - - /* Rule stats read. */ - status = rte_table_action_stats_read(table->a, - flow->data, - &stats, - flow_stats->reset); - if (status) - return rte_flow_error_set(error, - EINVAL, - RTE_FLOW_ERROR_TYPE_UNSPECIFIED, - NULL, - "Pipeline table rule stats read failed"); - - /* Fill in flow stats. */ - flow_stats->hits_set = - (table->ap->params.stats.n_packets_enabled) ? 1 : 0; - flow_stats->bytes_set = - (table->ap->params.stats.n_bytes_enabled) ? 1 : 0; - flow_stats->hits = stats.n_packets; - flow_stats->bytes = stats.n_bytes; - - return 0; -} - -const struct rte_flow_ops pmd_flow_ops = { - .validate = pmd_flow_validate, - .create = pmd_flow_create, - .destroy = pmd_flow_destroy, - .flush = pmd_flow_flush, - .query = pmd_flow_query, - .isolate = NULL, -}; From patchwork Thu Aug 4 16:58:21 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Dumitrescu X-Patchwork-Id: 114626 X-Patchwork-Delegate: andrew.rybchenko@oktetlabs.ru 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 7AF14A00C4; Thu, 4 Aug 2022 18:59:14 +0200 (CEST) Received: from [217.70.189.124] (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id E2AC142C00; Thu, 4 Aug 2022 18:58:57 +0200 (CEST) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by mails.dpdk.org (Postfix) with ESMTP id C32D34067C for ; Thu, 4 Aug 2022 18:58:53 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1659632333; x=1691168333; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=0SHXydqNuJHPkP4rbNsDBy2cHD2oK9rRF0WI7AJ9OJQ=; b=knOJ7UtzcLC3bMlhFhEYrqedmvcsomITuWF2qQkkjjwAEeJtkM3RB1de nAfxc7YPXZ4HEtWEpHfzApZFT9toHaoqPhTvYpmYWj75QCDpgljrbeo9X z8pn3M7HFELOFg5GUrFUJi5ZA66LlbM2PaX0u0G62FVQacbS2UNOwQKB1 kZRI5XtQ1TBHwcPKb/kLjIgW7QzRvqcxkFyll6WNxanGSKfwzA8e727hW UMAL+crIoWEav9+9ZKlRzZSnWZWBO7fdjaHQNYcMpr1VVSjFvEvKCDBTg CndNYSXn1lG3whiPAB2Wsg389MJyHoNNM9zdRzKO7KwqsgBY/7FEvk3I1 A==; X-IronPort-AV: E=McAfee;i="6400,9594,10429"; a="290000092" X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="290000092" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 04 Aug 2022 09:58:47 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="636163099" Received: from silpixa00400573.ir.intel.com (HELO silpixa00400573.ger.corp.intel.com) ([10.237.223.157]) by orsmga001.jf.intel.com with ESMTP; 04 Aug 2022 09:58:46 -0700 From: Cristian Dumitrescu To: dev@dpdk.org Cc: jasvinder.singh@intel.com, yogesh.jangra@intel.com Subject: [PATCH 03/21] net/softnic: remove the meter support Date: Thu, 4 Aug 2022 16:58:21 +0000 Message-Id: <20220804165839.1074817-4-cristian.dumitrescu@intel.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> References: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> MIME-Version: 1.0 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 Remove the Ethernet device meter API support. Signed-off-by: Cristian Dumitrescu Signed-off-by: Yogesh Jangra --- drivers/net/softnic/meson.build | 1 - drivers/net/softnic/rte_eth_softnic.c | 16 - .../net/softnic/rte_eth_softnic_internals.h | 117 --- drivers/net/softnic/rte_eth_softnic_meter.c | 945 ------------------ .../net/softnic/rte_eth_softnic_pipeline.c | 12 - 5 files changed, 1091 deletions(-) delete mode 100644 drivers/net/softnic/rte_eth_softnic_meter.c diff --git a/drivers/net/softnic/meson.build b/drivers/net/softnic/meson.build index 4ebe60921c..d466dc7700 100644 --- a/drivers/net/softnic/meson.build +++ b/drivers/net/softnic/meson.build @@ -15,7 +15,6 @@ sources = files( 'rte_eth_softnic_cryptodev.c', 'rte_eth_softnic_link.c', 'rte_eth_softnic_mempool.c', - 'rte_eth_softnic_meter.c', 'rte_eth_softnic_pipeline.c', 'rte_eth_softnic_swq.c', 'rte_eth_softnic_tap.c', diff --git a/drivers/net/softnic/rte_eth_softnic.c b/drivers/net/softnic/rte_eth_softnic.c index 8e361adbad..a7136bb0c0 100644 --- a/drivers/net/softnic/rte_eth_softnic.c +++ b/drivers/net/softnic/rte_eth_softnic.c @@ -13,7 +13,6 @@ #include #include #include -#include #include "rte_eth_softnic.h" #include "rte_eth_softnic_internals.h" @@ -168,8 +167,6 @@ pmd_dev_stop(struct rte_eth_dev *dev) softnic_softnic_swq_free_keep_rxq_txq(p); softnic_mempool_free(p); - softnic_mtr_free(p); - return 0; } @@ -191,8 +188,6 @@ pmd_free(struct pmd_internals *p) softnic_swq_free(p); softnic_mempool_free(p); - softnic_mtr_free(p); - rte_free(p); } @@ -215,14 +210,6 @@ pmd_link_update(struct rte_eth_dev *dev __rte_unused, return 0; } -static int -pmd_mtr_ops_get(struct rte_eth_dev *dev __rte_unused, void *arg) -{ - *(const struct rte_mtr_ops **)arg = &pmd_mtr_ops; - - return 0; -} - static const struct eth_dev_ops pmd_ops = { .dev_configure = pmd_dev_configure, .dev_start = pmd_dev_start, @@ -232,7 +219,6 @@ static const struct eth_dev_ops pmd_ops = { .dev_infos_get = pmd_dev_infos_get, .rx_queue_setup = pmd_rx_queue_setup, .tx_queue_setup = pmd_tx_queue_setup, - .mtr_ops_get = pmd_mtr_ops_get, }; static uint16_t @@ -274,8 +260,6 @@ pmd_init(struct pmd_params *params) memcpy(&p->params, params, sizeof(p->params)); /* Resources */ - softnic_mtr_init(p); - softnic_mempool_init(p); softnic_swq_init(p); softnic_link_init(p); diff --git a/drivers/net/softnic/rte_eth_softnic_internals.h b/drivers/net/softnic/rte_eth_softnic_internals.h index 4cc98b7aad..d578cb1f25 100644 --- a/drivers/net/softnic/rte_eth_softnic_internals.h +++ b/drivers/net/softnic/rte_eth_softnic_internals.h @@ -19,8 +19,6 @@ #include #include -#include -#include #include "rte_eth_softnic.h" #include "conn.h" @@ -40,68 +38,6 @@ struct pmd_params { int sc; /**< Service cores. */ }; -/** - * Ethdev Flow API - */ -struct rte_flow; - -TAILQ_HEAD(flow_list, rte_flow); - -struct flow_attr_map { - char pipeline_name[NAME_SIZE]; - uint32_t table_id; - int valid; -}; - -#ifndef SOFTNIC_FLOW_MAX_GROUPS -#define SOFTNIC_FLOW_MAX_GROUPS 64 -#endif - -struct flow_internals { - struct flow_attr_map ingress_map[SOFTNIC_FLOW_MAX_GROUPS]; - struct flow_attr_map egress_map[SOFTNIC_FLOW_MAX_GROUPS]; -}; - -/** - * Meter - */ - -/* MTR meter profile */ -struct softnic_mtr_meter_profile { - TAILQ_ENTRY(softnic_mtr_meter_profile) node; - uint32_t meter_profile_id; - struct rte_mtr_meter_profile params; - uint32_t n_users; -}; - -TAILQ_HEAD(softnic_mtr_meter_profile_list, softnic_mtr_meter_profile); - -/* MTR meter policy */ -struct softnic_mtr_meter_policy { - TAILQ_ENTRY(softnic_mtr_meter_policy) node; - uint32_t meter_policy_id; - enum rte_table_action_policer policer[RTE_COLORS]; - uint32_t n_users; -}; - -TAILQ_HEAD(softnic_mtr_meter_policy_list, softnic_mtr_meter_policy); - -/* MTR meter object */ -struct softnic_mtr { - TAILQ_ENTRY(softnic_mtr) node; - uint32_t mtr_id; - struct rte_mtr_params params; - struct rte_flow *flow; -}; - -TAILQ_HEAD(softnic_mtr_list, softnic_mtr); - -struct mtr_internals { - struct softnic_mtr_meter_profile_list meter_profiles; - struct softnic_mtr_meter_policy_list meter_policies; - struct softnic_mtr_list mtrs; -}; - /** * MEMPOOL */ @@ -383,7 +319,6 @@ struct softnic_table { struct softnic_table_params params; struct softnic_table_action_profile *ap; struct rte_table_action *a; - struct flow_list flows; struct rte_table_action_dscp_table dscp_table; struct softnic_table_meter_profile_list meter_profiles; }; @@ -481,9 +416,6 @@ struct pmd_internals { /** Params */ struct pmd_params params; - struct flow_internals flow; - struct mtr_internals mtr; - struct softnic_conn *conn; struct softnic_mempool_list mempool_list; struct softnic_swq_list swq_list; @@ -513,46 +445,6 @@ ETHDEV(struct pmd_internals *softnic) return &rte_eth_devices[port_id]; } -/** - * Ethdev Flow API - */ -int -flow_attr_map_set(struct pmd_internals *softnic, - uint32_t group_id, - int ingress, - const char *pipeline_name, - uint32_t table_id); - -struct flow_attr_map * -flow_attr_map_get(struct pmd_internals *softnic, - uint32_t group_id, - int ingress); - -extern const struct rte_flow_ops pmd_flow_ops; - -/** - * Meter - */ -int -softnic_mtr_init(struct pmd_internals *p); - -void -softnic_mtr_free(struct pmd_internals *p); - -struct softnic_mtr * -softnic_mtr_find(struct pmd_internals *p, - uint32_t mtr_id); - -struct softnic_mtr_meter_profile * -softnic_mtr_meter_profile_find(struct pmd_internals *p, - uint32_t meter_profile_id); - -struct softnic_mtr_meter_policy * -softnic_mtr_meter_policy_find(struct pmd_internals *p, - uint32_t meter_policy_id); - -extern const struct rte_mtr_ops pmd_mtr_ops; - /** * MEMPOOL */ @@ -814,15 +706,6 @@ struct softnic_table_rule_action { uint8_t sym_crypto_key[SYM_CRYPTO_MAX_KEY_SIZE]; }; -struct rte_flow { - TAILQ_ENTRY(rte_flow) node; - struct softnic_table_rule_match match; - struct softnic_table_rule_action action; - void *data; - struct pipeline *pipeline; - uint32_t table_id; -}; - int softnic_pipeline_port_in_stats_read(struct pmd_internals *p, const char *pipeline_name, diff --git a/drivers/net/softnic/rte_eth_softnic_meter.c b/drivers/net/softnic/rte_eth_softnic_meter.c deleted file mode 100644 index 6b02f43e31..0000000000 --- a/drivers/net/softnic/rte_eth_softnic_meter.c +++ /dev/null @@ -1,945 +0,0 @@ -/* SPDX-License-Identifier: BSD-3-Clause - * Copyright(c) 2018 Intel Corporation - */ - -#include -#include -#include - -#include -#include - -#include "rte_eth_softnic_internals.h" - -int -softnic_mtr_init(struct pmd_internals *p) -{ - /* Initialize meter profiles list */ - TAILQ_INIT(&p->mtr.meter_profiles); - - /* Initialize meter policies list */ - TAILQ_INIT(&p->mtr.meter_policies); - - /* Initialize MTR objects list */ - TAILQ_INIT(&p->mtr.mtrs); - - return 0; -} - -void -softnic_mtr_free(struct pmd_internals *p) -{ - /* Remove MTR objects */ - for ( ; ; ) { - struct softnic_mtr *m; - - m = TAILQ_FIRST(&p->mtr.mtrs); - if (m == NULL) - break; - - TAILQ_REMOVE(&p->mtr.mtrs, m, node); - free(m); - } - - /* Remove meter profiles */ - for ( ; ; ) { - struct softnic_mtr_meter_profile *mp; - - mp = TAILQ_FIRST(&p->mtr.meter_profiles); - if (mp == NULL) - break; - - TAILQ_REMOVE(&p->mtr.meter_profiles, mp, node); - free(mp); - } - - /* Remove meter policies */ - for ( ; ; ) { - struct softnic_mtr_meter_policy *mp; - - mp = TAILQ_FIRST(&p->mtr.meter_policies); - if (mp == NULL) - break; - - TAILQ_REMOVE(&p->mtr.meter_policies, mp, node); - free(mp); - } -} - -struct softnic_mtr_meter_profile * -softnic_mtr_meter_profile_find(struct pmd_internals *p, - uint32_t meter_profile_id) -{ - struct softnic_mtr_meter_profile_list *mpl = &p->mtr.meter_profiles; - struct softnic_mtr_meter_profile *mp; - - TAILQ_FOREACH(mp, mpl, node) - if (meter_profile_id == mp->meter_profile_id) - return mp; - - return NULL; -} - -static int -meter_profile_check(struct rte_eth_dev *dev, - uint32_t meter_profile_id, - struct rte_mtr_meter_profile *profile, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_meter_profile *mp; - - /* Meter profile ID must be valid. */ - if (meter_profile_id == UINT32_MAX) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE_ID, - NULL, - "Meter profile id not valid"); - - /* Meter profile must not exist. */ - mp = softnic_mtr_meter_profile_find(p, meter_profile_id); - if (mp) - return -rte_mtr_error_set(error, - EEXIST, - RTE_MTR_ERROR_TYPE_METER_PROFILE_ID, - NULL, - "Meter prfile already exists"); - - /* Profile must not be NULL. */ - if (profile == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE, - NULL, - "profile null"); - - /* Traffic metering algorithm : TRTCM_RFC2698 */ - if (profile->alg != RTE_MTR_TRTCM_RFC2698) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE, - NULL, - "Metering alg not supported"); - - /* Not support packet mode, just support byte mode. */ - if (profile->packet_mode) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE_PACKET_MODE, - NULL, - "Meter packet mode not supported"); - - return 0; -} - -/* MTR meter profile add */ -static int -pmd_mtr_meter_profile_add(struct rte_eth_dev *dev, - uint32_t meter_profile_id, - struct rte_mtr_meter_profile *profile, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_meter_profile_list *mpl = &p->mtr.meter_profiles; - struct softnic_mtr_meter_profile *mp; - int status; - - /* Check input params */ - status = meter_profile_check(dev, meter_profile_id, profile, error); - if (status) - return status; - - /* Memory allocation */ - mp = calloc(1, sizeof(struct softnic_mtr_meter_profile)); - if (mp == NULL) - return -rte_mtr_error_set(error, - ENOMEM, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Memory alloc failed"); - - /* Fill in */ - mp->meter_profile_id = meter_profile_id; - memcpy(&mp->params, profile, sizeof(mp->params)); - - /* Add to list */ - TAILQ_INSERT_TAIL(mpl, mp, node); - - return 0; -} - -/* MTR meter profile delete */ -static int -pmd_mtr_meter_profile_delete(struct rte_eth_dev *dev, - uint32_t meter_profile_id, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_meter_profile *mp; - - /* Meter profile must exist */ - mp = softnic_mtr_meter_profile_find(p, meter_profile_id); - if (mp == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE_ID, - NULL, - "Meter profile id invalid"); - - /* Check unused */ - if (mp->n_users) - return -rte_mtr_error_set(error, - EBUSY, - RTE_MTR_ERROR_TYPE_METER_PROFILE_ID, - NULL, - "Meter profile in use"); - - /* Remove from list */ - TAILQ_REMOVE(&p->mtr.meter_profiles, mp, node); - free(mp); - - return 0; -} - -struct softnic_mtr_meter_policy * -softnic_mtr_meter_policy_find(struct pmd_internals *p, - uint32_t meter_policy_id) -{ - struct softnic_mtr_meter_policy_list *mpl = &p->mtr.meter_policies; - struct softnic_mtr_meter_policy *mp; - - TAILQ_FOREACH(mp, mpl, node) - if (meter_policy_id == mp->meter_policy_id) - return mp; - - return NULL; -} - -/* MTR meter policy add */ -static int -pmd_mtr_meter_policy_add(struct rte_eth_dev *dev, - uint32_t meter_policy_id, - struct rte_mtr_meter_policy_params *policy, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_meter_policy_list *mpl = &p->mtr.meter_policies; - struct softnic_mtr_meter_policy *mp; - const struct rte_flow_action *act; - const struct rte_flow_action_meter_color *recolor; - uint32_t i; - bool valid_act_found; - - if (policy == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY, - NULL, - "Null meter policy invalid"); - - /* Meter policy must not exist. */ - mp = softnic_mtr_meter_policy_find(p, meter_policy_id); - if (mp != NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY_ID, - NULL, - "Meter policy already exists"); - - for (i = 0; i < RTE_COLORS; i++) { - if (policy->actions[i] == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY, - NULL, - "Null action list"); - for (act = policy->actions[i], valid_act_found = false; - act->type != RTE_FLOW_ACTION_TYPE_END; act++) { - if (act->type == RTE_FLOW_ACTION_TYPE_VOID) - continue; - /* - * Support one (and one only) of - * METER_COLOR or DROP action. - */ - if ((act->type != RTE_FLOW_ACTION_TYPE_METER_COLOR && - act->type != RTE_FLOW_ACTION_TYPE_DROP) || - valid_act_found) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY, - NULL, - "Action invalid"); - valid_act_found = true; - } - if (!valid_act_found) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY, - NULL, - "No valid action found"); - } - - /* Memory allocation */ - mp = calloc(1, sizeof(struct softnic_mtr_meter_policy)); - if (mp == NULL) - return -rte_mtr_error_set(error, - ENOMEM, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Memory alloc failed"); - - /* Fill in */ - mp->meter_policy_id = meter_policy_id; - for (i = 0; i < RTE_COLORS; i++) { - mp->policer[i] = RTE_TABLE_ACTION_POLICER_DROP; - act = policy->actions[i]; - if (!act) - continue; - if (act->type == RTE_FLOW_ACTION_TYPE_METER_COLOR) { - recolor = act->conf; - switch (recolor->color) { - case RTE_COLOR_GREEN: - mp->policer[i] = - RTE_TABLE_ACTION_POLICER_COLOR_GREEN; - break; - case RTE_COLOR_YELLOW: - mp->policer[i] = - RTE_TABLE_ACTION_POLICER_COLOR_YELLOW; - break; - case RTE_COLOR_RED: - mp->policer[i] = - RTE_TABLE_ACTION_POLICER_COLOR_RED; - break; - default: - break; - } - } - } - - /* Add to list */ - TAILQ_INSERT_TAIL(mpl, mp, node); - - return 0; -} - -/* MTR meter policy delete */ -static int -pmd_mtr_meter_policy_delete(struct rte_eth_dev *dev, - uint32_t meter_policy_id, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_meter_policy *mp; - - /* Meter policy must exist */ - mp = softnic_mtr_meter_policy_find(p, meter_policy_id); - if (mp == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY_ID, - NULL, - "Meter policy id invalid"); - - /* Check unused */ - if (mp->n_users) - return -rte_mtr_error_set(error, - EBUSY, - RTE_MTR_ERROR_TYPE_METER_POLICY_ID, - NULL, - "Meter policy in use"); - - /* Remove from list */ - TAILQ_REMOVE(&p->mtr.meter_policies, mp, node); - free(mp); - - return 0; -} - -struct softnic_mtr * -softnic_mtr_find(struct pmd_internals *p, uint32_t mtr_id) -{ - struct softnic_mtr_list *ml = &p->mtr.mtrs; - struct softnic_mtr *m; - - TAILQ_FOREACH(m, ml, node) - if (m->mtr_id == mtr_id) - return m; - - return NULL; -} - - -static int -mtr_check(struct pmd_internals *p, - uint32_t mtr_id, - struct rte_mtr_params *params, - int shared, - struct rte_mtr_error *error) -{ - /* MTR id valid */ - if (softnic_mtr_find(p, mtr_id)) - return -rte_mtr_error_set(error, - EEXIST, - RTE_MTR_ERROR_TYPE_MTR_ID, - NULL, - "MTR object already exists"); - - /* MTR params must not be NULL */ - if (params == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_MTR_PARAMS, - NULL, - "MTR object params null"); - - /* Previous meter color not supported */ - if (params->use_prev_mtr_color) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_MTR_PARAMS, - NULL, - "Previous meter color not supported"); - - /* Shared MTR object not supported */ - if (shared) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_SHARED, - NULL, - "Shared MTR object not supported"); - - return 0; -} - -/* MTR object create */ -static int -pmd_mtr_create(struct rte_eth_dev *dev, - uint32_t mtr_id, - struct rte_mtr_params *params, - int shared, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_list *ml = &p->mtr.mtrs; - struct softnic_mtr_meter_profile *mp; - struct softnic_mtr_meter_policy *policy; - struct softnic_mtr *m; - int status; - - /* Check parameters */ - status = mtr_check(p, mtr_id, params, shared, error); - if (status) - return status; - - /* Meter profile must exist */ - mp = softnic_mtr_meter_profile_find(p, params->meter_profile_id); - if (mp == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE_ID, - NULL, - "Meter profile id not valid"); - - /* Meter policy must exist */ - policy = softnic_mtr_meter_policy_find(p, params->meter_policy_id); - if (policy == NULL) { - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY_ID, - NULL, - "Meter policy id invalid"); - } - - /* Memory allocation */ - m = calloc(1, sizeof(struct softnic_mtr)); - if (m == NULL) - return -rte_mtr_error_set(error, - ENOMEM, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Memory alloc failed"); - - /* Fill in */ - m->mtr_id = mtr_id; - memcpy(&m->params, params, sizeof(m->params)); - - /* Add to list */ - TAILQ_INSERT_TAIL(ml, m, node); - - /* Update dependencies */ - mp->n_users++; - policy->n_users++; - - return 0; -} - -/* MTR object destroy */ -static int -pmd_mtr_destroy(struct rte_eth_dev *dev, - uint32_t mtr_id, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_list *ml = &p->mtr.mtrs; - struct softnic_mtr_meter_profile *mp; - struct softnic_mtr *m; - struct softnic_mtr_meter_policy *policy; - - /* MTR object must exist */ - m = softnic_mtr_find(p, mtr_id); - if (m == NULL) - return -rte_mtr_error_set(error, - EEXIST, - RTE_MTR_ERROR_TYPE_MTR_ID, - NULL, - "MTR object id not valid"); - - /* MTR object must not have any owner */ - if (m->flow != NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "MTR object is being used"); - - /* Get meter profile */ - mp = softnic_mtr_meter_profile_find(p, m->params.meter_profile_id); - if (mp == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE_ID, - NULL, - "MTR object meter profile invalid"); - - /* Meter policy must exist */ - policy = softnic_mtr_meter_policy_find(p, m->params.meter_policy_id); - if (policy == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY_ID, - NULL, - "MTR object meter policy invalid"); - - /* Update dependencies */ - mp->n_users--; - policy->n_users--; - - /* Remove from list */ - TAILQ_REMOVE(ml, m, node); - free(m); - - return 0; -} - -/* MTR object meter profile update */ -static int -pmd_mtr_meter_profile_update(struct rte_eth_dev *dev, - uint32_t mtr_id, - uint32_t meter_profile_id, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr_meter_profile *mp_new, *mp_old; - struct softnic_mtr *m; - int status; - - /* MTR object id must be valid */ - m = softnic_mtr_find(p, mtr_id); - if (m == NULL) - return -rte_mtr_error_set(error, - EEXIST, - RTE_MTR_ERROR_TYPE_MTR_ID, - NULL, - "MTR object id not valid"); - - /* Meter profile id must be valid */ - mp_new = softnic_mtr_meter_profile_find(p, meter_profile_id); - if (mp_new == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_PROFILE_ID, - NULL, - "Meter profile not valid"); - - /* MTR object already set to meter profile id */ - if (m->params.meter_profile_id == meter_profile_id) - return 0; - - /* MTR object owner table update */ - if (m->flow) { - uint32_t table_id = m->flow->table_id; - struct softnic_table *table = &m->flow->pipeline->table[table_id]; - struct softnic_table_rule_action action; - - if (!softnic_pipeline_table_meter_profile_find(table, - meter_profile_id)) { - struct rte_table_action_meter_profile profile; - - memset(&profile, 0, sizeof(profile)); - - profile.alg = RTE_TABLE_ACTION_METER_TRTCM; - profile.trtcm.cir = mp_new->params.trtcm_rfc2698.cir; - profile.trtcm.pir = mp_new->params.trtcm_rfc2698.pir; - profile.trtcm.cbs = mp_new->params.trtcm_rfc2698.cbs; - profile.trtcm.pbs = mp_new->params.trtcm_rfc2698.pbs; - - /* Add meter profile to pipeline table */ - status = softnic_pipeline_table_mtr_profile_add(p, - m->flow->pipeline->name, - table_id, - meter_profile_id, - &profile); - if (status) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Table meter profile add failed"); - } - - /* Set meter action */ - memcpy(&action, &m->flow->action, sizeof(action)); - - action.mtr.mtr[0].meter_profile_id = meter_profile_id; - - /* Re-add rule */ - status = softnic_pipeline_table_rule_add(p, - m->flow->pipeline->name, - table_id, - &m->flow->match, - &action, - &m->flow->data); - if (status) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Pipeline table rule add failed"); - - /* Flow: update meter action */ - memcpy(&m->flow->action, &action, sizeof(m->flow->action)); - } - - mp_old = softnic_mtr_meter_profile_find(p, m->params.meter_profile_id); - - /* Meter: Set meter profile */ - m->params.meter_profile_id = meter_profile_id; - - /* Update dependencies*/ - mp_old->n_users--; - mp_new->n_users++; - - return 0; -} - -/* MTR object meter DSCP table update */ -static int -pmd_mtr_meter_dscp_table_update(struct rte_eth_dev *dev, - uint32_t mtr_id, - enum rte_color *dscp_table, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct rte_table_action_dscp_table dt; - struct pipeline *pipeline; - struct softnic_table *table; - struct softnic_mtr *m; - uint32_t table_id, i; - int status; - - /* MTR object id must be valid */ - m = softnic_mtr_find(p, mtr_id); - if (m == NULL) - return -rte_mtr_error_set(error, - EEXIST, - RTE_MTR_ERROR_TYPE_MTR_ID, - NULL, - "MTR object id not valid"); - - /* MTR object owner valid? */ - if (m->flow == NULL) - return 0; - - pipeline = m->flow->pipeline; - table_id = m->flow->table_id; - table = &pipeline->table[table_id]; - - memcpy(&dt, &table->dscp_table, sizeof(dt)); - for (i = 0; i < RTE_DIM(dt.entry); i++) - dt.entry[i].color = (enum rte_color)dscp_table[i]; - - /* Update table */ - status = softnic_pipeline_table_dscp_table_update(p, - pipeline->name, - table_id, - UINT64_MAX, - &dt); - if (status) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Table action dscp table update failed"); - - return 0; -} - -/* MTR object policy update */ -static int -pmd_mtr_meter_policy_update(struct rte_eth_dev *dev, - uint32_t mtr_id, - uint32_t meter_policy_id, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct softnic_mtr *m; - uint32_t i; - int status; - struct softnic_mtr_meter_policy *mp_new, *mp_old; - - /* MTR object id must be valid */ - m = softnic_mtr_find(p, mtr_id); - if (m == NULL) - return -rte_mtr_error_set(error, - EEXIST, - RTE_MTR_ERROR_TYPE_MTR_ID, - NULL, - "MTR object id not valid"); - - if (m->params.meter_policy_id == meter_policy_id) - return 0; - - /* Meter policy must exist */ - mp_new = softnic_mtr_meter_policy_find(p, meter_policy_id); - if (mp_new == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY_ID, - NULL, - "Meter policy id invalid"); - - /* MTR object owner valid? */ - if (m->flow) { - struct pipeline *pipeline = m->flow->pipeline; - struct softnic_table *table = &pipeline->table[m->flow->table_id]; - struct softnic_table_rule_action action; - - memcpy(&action, &m->flow->action, sizeof(action)); - - /* Set action */ - for (i = 0; i < RTE_COLORS; i++) - action.mtr.mtr[0].policer[i] = mp_new->policer[i]; - - /* Re-add the rule */ - status = softnic_pipeline_table_rule_add(p, - pipeline->name, - m->flow->table_id, - &m->flow->match, - &action, - &m->flow->data); - if (status) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Pipeline table rule re-add failed"); - - /* Flow: Update meter action */ - memcpy(&m->flow->action, &action, sizeof(m->flow->action)); - - /* Reset the meter stats */ - rte_table_action_meter_read(table->a, m->flow->data, - 1, NULL, 1); - } - - mp_old = softnic_mtr_meter_policy_find(p, m->params.meter_policy_id); - if (mp_old == NULL) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_METER_POLICY_ID, - NULL, - "Old meter policy id invalid"); - - /* Meter: Set meter profile */ - m->params.meter_policy_id = meter_policy_id; - - /* Update dependencies*/ - mp_old->n_users--; - mp_new->n_users++; - - return 0; -} - -#define MTR_STATS_PKTS_DEFAULT (RTE_MTR_STATS_N_PKTS_GREEN | \ - RTE_MTR_STATS_N_PKTS_YELLOW | \ - RTE_MTR_STATS_N_PKTS_RED | \ - RTE_MTR_STATS_N_PKTS_DROPPED) - -#define MTR_STATS_BYTES_DEFAULT (RTE_MTR_STATS_N_BYTES_GREEN | \ - RTE_MTR_STATS_N_BYTES_YELLOW | \ - RTE_MTR_STATS_N_BYTES_RED | \ - RTE_MTR_STATS_N_BYTES_DROPPED) - -/* MTR object stats read */ -static void -mtr_stats_convert(struct pmd_internals *p, - struct softnic_mtr *m, - struct rte_table_action_mtr_counters_tc *in, - struct rte_mtr_stats *out, - uint64_t *out_mask) -{ - struct softnic_mtr_meter_policy *mp; - - memset(&out, 0, sizeof(out)); - *out_mask = 0; - - /* Meter policy must exist */ - mp = softnic_mtr_meter_policy_find(p, m->params.meter_policy_id); - if (mp == NULL) - return; - - if (in->n_packets_valid) { - uint32_t i; - - for (i = 0; i < RTE_COLORS; i++) { - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_COLOR_GREEN) - out->n_pkts[RTE_COLOR_GREEN] += in->n_packets[i]; - - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_COLOR_YELLOW) - out->n_pkts[RTE_COLOR_YELLOW] += in->n_packets[i]; - - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_COLOR_RED) - out->n_pkts[RTE_COLOR_RED] += in->n_packets[i]; - - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_DROP) - out->n_pkts_dropped += in->n_packets[i]; - } - - *out_mask |= MTR_STATS_PKTS_DEFAULT; - } - - if (in->n_bytes_valid) { - uint32_t i; - - for (i = 0; i < RTE_COLORS; i++) { - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_COLOR_GREEN) - out->n_bytes[RTE_COLOR_GREEN] += in->n_bytes[i]; - - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_COLOR_YELLOW) - out->n_bytes[RTE_COLOR_YELLOW] += in->n_bytes[i]; - - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_COLOR_RED) - out->n_bytes[RTE_COLOR_RED] += in->n_bytes[i]; - - if (mp->policer[i] == - RTE_TABLE_ACTION_POLICER_DROP) - out->n_bytes_dropped += in->n_bytes[i]; - } - - *out_mask |= MTR_STATS_BYTES_DEFAULT; - } -} - -/* MTR object stats read */ -static int -pmd_mtr_stats_read(struct rte_eth_dev *dev, - uint32_t mtr_id, - struct rte_mtr_stats *stats, - uint64_t *stats_mask, - int clear, - struct rte_mtr_error *error) -{ - struct pmd_internals *p = dev->data->dev_private; - struct rte_table_action_mtr_counters counters; - struct pipeline *pipeline; - struct softnic_table *table; - struct softnic_mtr *m; - int status; - - /* MTR object id must be valid */ - m = softnic_mtr_find(p, mtr_id); - if (m == NULL) - return -rte_mtr_error_set(error, - EEXIST, - RTE_MTR_ERROR_TYPE_MTR_ID, - NULL, - "MTR object id not valid"); - - /* MTR meter object owner valid? */ - if (m->flow == NULL) { - if (stats != NULL) - memset(stats, 0, sizeof(*stats)); - - if (stats_mask) - *stats_mask = MTR_STATS_PKTS_DEFAULT | - MTR_STATS_BYTES_DEFAULT; - - return 0; - } - - pipeline = m->flow->pipeline; - table = &pipeline->table[m->flow->table_id]; - - /* Meter stats read. */ - status = rte_table_action_meter_read(table->a, - m->flow->data, - 1, - &counters, - clear); - if (status) - return -rte_mtr_error_set(error, - EINVAL, - RTE_MTR_ERROR_TYPE_UNSPECIFIED, - NULL, - "Meter stats read failed"); - - /* Stats format conversion. */ - if (stats || stats_mask) { - struct rte_mtr_stats s; - uint64_t s_mask = 0; - - mtr_stats_convert(p, - m, - &counters.stats[0], - &s, - &s_mask); - - if (stats) - memcpy(stats, &s, sizeof(*stats)); - - if (stats_mask) - *stats_mask = s_mask; - } - - return 0; -} - -const struct rte_mtr_ops pmd_mtr_ops = { - .capabilities_get = NULL, - - .meter_profile_add = pmd_mtr_meter_profile_add, - .meter_profile_delete = pmd_mtr_meter_profile_delete, - - .meter_policy_add = pmd_mtr_meter_policy_add, - .meter_policy_delete = pmd_mtr_meter_policy_delete, - - .create = pmd_mtr_create, - .destroy = pmd_mtr_destroy, - .meter_enable = NULL, - .meter_disable = NULL, - - .meter_profile_update = pmd_mtr_meter_profile_update, - .meter_dscp_table_update = pmd_mtr_meter_dscp_table_update, - .meter_policy_update = pmd_mtr_meter_policy_update, - .stats_update = NULL, - - .stats_read = pmd_mtr_stats_read, -}; diff --git a/drivers/net/softnic/rte_eth_softnic_pipeline.c b/drivers/net/softnic/rte_eth_softnic_pipeline.c index c7d2a7de19..2cf7fa52d1 100644 --- a/drivers/net/softnic/rte_eth_softnic_pipeline.c +++ b/drivers/net/softnic/rte_eth_softnic_pipeline.c @@ -46,17 +46,6 @@ softnic_pipeline_init(struct pmd_internals *p) static void softnic_pipeline_table_free(struct softnic_table *table) { - for ( ; ; ) { - struct rte_flow *flow; - - flow = TAILQ_FIRST(&table->flows); - if (flow == NULL) - break; - - TAILQ_REMOVE(&table->flows, flow, node); - free(flow); - } - for ( ; ; ) { struct softnic_table_meter_profile *mp; @@ -1035,7 +1024,6 @@ softnic_pipeline_table_create(struct pmd_internals *softnic, memcpy(&table->params, params, sizeof(*params)); table->ap = ap; table->a = action; - TAILQ_INIT(&table->flows); TAILQ_INIT(&table->meter_profiles); memset(&table->dscp_table, 0, sizeof(table->dscp_table)); pipeline->n_tables++; From patchwork Thu Aug 4 16:58:22 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Dumitrescu X-Patchwork-Id: 114627 X-Patchwork-Delegate: andrew.rybchenko@oktetlabs.ru 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 8D706A00C4; Thu, 4 Aug 2022 18:59:21 +0200 (CEST) Received: from [217.70.189.124] (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id C71AE42C09; Thu, 4 Aug 2022 18:58:58 +0200 (CEST) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by mails.dpdk.org (Postfix) with ESMTP id 1945B42BE8 for ; Thu, 4 Aug 2022 18:58:53 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1659632334; x=1691168334; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=HvyFX9xalBofYK7SjFBXjTpxxHepbB7sYFI/oC0GSMU=; b=c9SsVJ3fHGzQQAIVBWV8ikWHpzQvwupE1eT7BYGullEpZkexvs48zr77 4m/YoWIiPI0R3IUFF793/Y4xroZfNoUrVq6we4O+OkeU4BcRce4+KcUT4 XE8MWDFGn6kW09DR3j780Eb6yiUPPruRyGaRPNbL6R5ls75VfowrwLeDj IhD4xNwroLOqtDo0sXJYU5/9EOimPlpz6l6ZygLVqV6h+YmXLQnXIXoYA +4y1Vg5G6cXgSZGd73TYFz8PJM6Jq1glbIwMXeqfsm3pY7Nj+yX+rC0dY AIGBiQi2/uGPdFL0MDhYQXn2iO52EWPc8z3C4p8Bo2Ke6JD+8Uv5c43jA Q==; X-IronPort-AV: E=McAfee;i="6400,9594,10429"; a="290000097" X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="290000097" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 04 Aug 2022 09:58:49 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="636163110" Received: from silpixa00400573.ir.intel.com (HELO silpixa00400573.ger.corp.intel.com) ([10.237.223.157]) by orsmga001.jf.intel.com with ESMTP; 04 Aug 2022 09:58:48 -0700 From: Cristian Dumitrescu To: dev@dpdk.org Cc: jasvinder.singh@intel.com, yogesh.jangra@intel.com Subject: [PATCH 04/21] net/softnic: remove cryptodev support Date: Thu, 4 Aug 2022 16:58:22 +0000 Message-Id: <20220804165839.1074817-5-cristian.dumitrescu@intel.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> References: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> MIME-Version: 1.0 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 Remove the cryptographic device API support. Signed-off-by: Cristian Dumitrescu Signed-off-by: Yogesh Jangra --- drivers/net/softnic/meson.build | 3 +- drivers/net/softnic/rte_eth_softnic.c | 1 - drivers/net/softnic/rte_eth_softnic_cli.c | 171 ------------------ .../net/softnic/rte_eth_softnic_cryptodev.c | 168 ----------------- .../net/softnic/rte_eth_softnic_internals.h | 54 ------ .../net/softnic/rte_eth_softnic_pipeline.c | 54 ------ 6 files changed, 1 insertion(+), 450 deletions(-) delete mode 100644 drivers/net/softnic/rte_eth_softnic_cryptodev.c diff --git a/drivers/net/softnic/meson.build b/drivers/net/softnic/meson.build index d466dc7700..b3d235841d 100644 --- a/drivers/net/softnic/meson.build +++ b/drivers/net/softnic/meson.build @@ -12,7 +12,6 @@ sources = files( 'rte_eth_softnic.c', 'rte_eth_softnic_action.c', 'rte_eth_softnic_cli.c', - 'rte_eth_softnic_cryptodev.c', 'rte_eth_softnic_link.c', 'rte_eth_softnic_mempool.c', 'rte_eth_softnic_pipeline.c', @@ -20,4 +19,4 @@ sources = files( 'rte_eth_softnic_tap.c', 'rte_eth_softnic_thread.c', ) -deps += ['pipeline', 'port', 'table', 'cryptodev'] +deps += ['pipeline', 'port', 'table'] diff --git a/drivers/net/softnic/rte_eth_softnic.c b/drivers/net/softnic/rte_eth_softnic.c index a7136bb0c0..1ea5989223 100644 --- a/drivers/net/softnic/rte_eth_softnic.c +++ b/drivers/net/softnic/rte_eth_softnic.c @@ -264,7 +264,6 @@ pmd_init(struct pmd_params *params) softnic_swq_init(p); softnic_link_init(p); softnic_tap_init(p); - softnic_cryptodev_init(p); softnic_port_in_action_profile_init(p); softnic_table_action_profile_init(p); softnic_pipeline_init(p); diff --git a/drivers/net/softnic/rte_eth_softnic_cli.c b/drivers/net/softnic/rte_eth_softnic_cli.c index 671f96cf77..bca0b176d6 100644 --- a/drivers/net/softnic/rte_eth_softnic_cli.c +++ b/drivers/net/softnic/rte_eth_softnic_cli.c @@ -213,80 +213,6 @@ cmd_tap(struct pmd_internals *softnic, } } -/** - * cryptodev dev | dev_id - * queue max_sessions - **/ - -static void -cmd_cryptodev(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct softnic_cryptodev_params params; - char *name; - - memset(¶ms, 0, sizeof(params)); - if (n_tokens != 9) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - name = tokens[1]; - - if (strcmp(tokens[2], "dev") == 0) - params.dev_name = tokens[3]; - else if (strcmp(tokens[2], "dev_id") == 0) { - if (softnic_parser_read_uint32(¶ms.dev_id, tokens[3]) < 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "dev_id"); - return; - } - } else { - snprintf(out, out_size, MSG_ARG_INVALID, - "cryptodev"); - return; - } - - if (strcmp(tokens[4], "queue")) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "4"); - return; - } - - if (softnic_parser_read_uint32(¶ms.n_queues, tokens[5]) < 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "q"); - return; - } - - if (softnic_parser_read_uint32(¶ms.queue_size, tokens[6]) < 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "queue_size"); - return; - } - - if (strcmp(tokens[7], "max_sessions")) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "4"); - return; - } - - if (softnic_parser_read_uint32(¶ms.session_pool_size, tokens[8]) - < 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "q"); - return; - } - - if (softnic_cryptodev_create(softnic, name, ¶ms) == NULL) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - /** * port in action profile * [filter match | mismatch offset mask key port ] @@ -879,41 +805,6 @@ cmd_table_action_profile(struct pmd_internals *softnic, t0 += 1; } /* decap */ - if (t0 < n_tokens && (strcmp(tokens[t0], "sym_crypto") == 0)) { - struct softnic_cryptodev *cryptodev; - - if (n_tokens < t0 + 5 || - strcmp(tokens[t0 + 1], "dev") || - strcmp(tokens[t0 + 3], "offset")) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "table action profile sym_crypto"); - return; - } - - cryptodev = softnic_cryptodev_find(softnic, tokens[t0 + 2]); - if (cryptodev == NULL) { - snprintf(out, out_size, MSG_ARG_INVALID, - "table action profile sym_crypto"); - return; - } - - p.sym_crypto.cryptodev_id = cryptodev->dev_id; - - if (softnic_parser_read_uint32(&p.sym_crypto.op_offset, - tokens[t0 + 4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "table action profile sym_crypto"); - return; - } - - p.sym_crypto.mp_create = cryptodev->mp_create; - p.sym_crypto.mp_init = cryptodev->mp_init; - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_SYM_CRYPTO; - - t0 += 5; - } /* sym_crypto */ - if (t0 < n_tokens) { snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); return; @@ -985,7 +876,6 @@ cmd_pipeline(struct pmd_internals *softnic, * | swq * | tap mempool mtu * | source mempool file bpp - * | cryptodev rxq * [action ] * [disabled] */ @@ -1138,27 +1028,6 @@ cmd_pipeline_port_in(struct pmd_internals *softnic, } t0 += 7; - } else if (strcmp(tokens[t0], "cryptodev") == 0) { - if (n_tokens < t0 + 3) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port in cryptodev"); - return; - } - - p.type = PORT_IN_CRYPTODEV; - - strlcpy(p.dev_name, tokens[t0 + 1], sizeof(p.dev_name)); - if (softnic_parser_read_uint16(&p.rxq.queue_id, - tokens[t0 + 3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "rxq"); - return; - } - - p.cryptodev.arg_callback = NULL; - p.cryptodev.f_callback = NULL; - - t0 += 4; } else { snprintf(out, out_size, MSG_ARG_INVALID, tokens[0]); return; @@ -1207,7 +1076,6 @@ cmd_pipeline_port_in(struct pmd_internals *softnic, * | swq * | tap * | sink [file pkts ] - * | cryptodev txq offset */ static void cmd_pipeline_port_out(struct pmd_internals *softnic, @@ -1322,40 +1190,6 @@ cmd_pipeline_port_out(struct pmd_internals *softnic, return; } } - } else if (strcmp(tokens[6], "cryptodev") == 0) { - if (n_tokens != 12) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out cryptodev"); - return; - } - - p.type = PORT_OUT_CRYPTODEV; - - strlcpy(p.dev_name, tokens[7], sizeof(p.dev_name)); - - if (strcmp(tokens[8], "txq")) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out cryptodev"); - return; - } - - if (softnic_parser_read_uint16(&p.cryptodev.queue_id, tokens[9]) - != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "queue_id"); - return; - } - - if (strcmp(tokens[10], "offset")) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out cryptodev"); - return; - } - - if (softnic_parser_read_uint32(&p.cryptodev.op_offset, - tokens[11]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "queue_id"); - return; - } } else { snprintf(out, out_size, MSG_ARG_INVALID, tokens[0]); return; @@ -4771,11 +4605,6 @@ softnic_cli_process(char *in, char *out, size_t out_size, void *arg) return; } - if (strcmp(tokens[0], "cryptodev") == 0) { - cmd_cryptodev(softnic, tokens, n_tokens, out, out_size); - return; - } - if (strcmp(tokens[0], "port") == 0) { cmd_port_in_action_profile(softnic, tokens, n_tokens, out, out_size); return; diff --git a/drivers/net/softnic/rte_eth_softnic_cryptodev.c b/drivers/net/softnic/rte_eth_softnic_cryptodev.c deleted file mode 100644 index e4754055e9..0000000000 --- a/drivers/net/softnic/rte_eth_softnic_cryptodev.c +++ /dev/null @@ -1,168 +0,0 @@ -/* SPDX-License-Identifier: BSD-3-Clause - * Copyright(c) 2018 Intel Corporation - */ - -#include -#include - -#include -#include -#include - -#include "rte_eth_softnic_internals.h" - -#define SOFTNIC_CRYPTO_SESSION_CACHE_SIZE 128 - -int -softnic_cryptodev_init(struct pmd_internals *p) -{ - TAILQ_INIT(&p->cryptodev_list); - - return 0; -} - -void -softnic_cryptodev_free(struct pmd_internals *p) -{ - for ( ; ; ) { - struct softnic_cryptodev *cryptodev; - - cryptodev = TAILQ_FIRST(&p->cryptodev_list); - if (cryptodev == NULL) - break; - - TAILQ_REMOVE(&p->cryptodev_list, cryptodev, node); - free(cryptodev); - } -} - -struct softnic_cryptodev * -softnic_cryptodev_find(struct pmd_internals *p, - const char *name) -{ - struct softnic_cryptodev *cryptodev; - - if (name == NULL) - return NULL; - - TAILQ_FOREACH(cryptodev, &p->cryptodev_list, node) - if (strcmp(cryptodev->name, name) == 0) - return cryptodev; - - return NULL; -} - -struct softnic_cryptodev * -softnic_cryptodev_create(struct pmd_internals *p, - const char *name, - struct softnic_cryptodev_params *params) -{ - struct rte_cryptodev_info dev_info; - struct rte_cryptodev_config dev_conf; - struct rte_cryptodev_qp_conf queue_conf; - struct softnic_cryptodev *cryptodev; - uint32_t dev_id, i; - uint32_t socket_id; - uint32_t cache_size; - char mp_name[NAME_SIZE]; - int status; - - /* Check input params */ - if ((name == NULL) || - softnic_cryptodev_find(p, name) || - (params->n_queues == 0) || - (params->queue_size == 0) || - (params->session_pool_size == 0)) - return NULL; - - if (params->dev_name) { - status = rte_cryptodev_get_dev_id(params->dev_name); - if (status == -1) - return NULL; - - dev_id = (uint32_t)status; - } else { - if (rte_cryptodev_is_valid_dev(params->dev_id) == 0) - return NULL; - - dev_id = params->dev_id; - } - - cache_size = (params->session_pool_size / 2 < - SOFTNIC_CRYPTO_SESSION_CACHE_SIZE) ? - (params->session_pool_size / 2) : - SOFTNIC_CRYPTO_SESSION_CACHE_SIZE; - - socket_id = rte_cryptodev_socket_id(dev_id); - rte_cryptodev_info_get(dev_id, &dev_info); - - if (dev_info.max_nb_queue_pairs < params->n_queues) - return NULL; - if (dev_info.feature_flags & RTE_CRYPTODEV_FF_HW_ACCELERATED) - return NULL; - - dev_conf.socket_id = socket_id; - dev_conf.nb_queue_pairs = params->n_queues; - - status = rte_cryptodev_configure(dev_id, &dev_conf); - if (status < 0) - return NULL; - - queue_conf.nb_descriptors = params->queue_size; - for (i = 0; i < params->n_queues; i++) { - status = rte_cryptodev_queue_pair_setup(dev_id, i, - &queue_conf, socket_id); - if (status < 0) - return NULL; - } - - if (rte_cryptodev_start(dev_id) < 0) - return NULL; - - cryptodev = calloc(1, sizeof(struct softnic_cryptodev)); - if (cryptodev == NULL) { - rte_cryptodev_stop(dev_id); - return NULL; - } - - strlcpy(cryptodev->name, name, sizeof(cryptodev->name)); - cryptodev->dev_id = dev_id; - cryptodev->n_queues = params->n_queues; - - snprintf(mp_name, NAME_SIZE, "%s_mp%u", name, dev_id); - cryptodev->mp_create = rte_cryptodev_sym_session_pool_create(mp_name, - params->session_pool_size, - 0, - cache_size, - 0, - socket_id); - if (!cryptodev->mp_create) - goto error_exit; - - snprintf(mp_name, NAME_SIZE, "%s_priv_mp%u", name, dev_id); - cryptodev->mp_init = rte_mempool_create(mp_name, - params->session_pool_size, - rte_cryptodev_sym_get_private_session_size(dev_id), - cache_size, - 0, - NULL, - NULL, - NULL, - NULL, - socket_id, - 0); - if (!cryptodev->mp_init) - goto error_exit; - - TAILQ_INSERT_TAIL(&p->cryptodev_list, cryptodev, node); - - return cryptodev; - -error_exit: - rte_mempool_free(cryptodev->mp_create); - rte_mempool_free(cryptodev->mp_init); - - free(cryptodev); - - return NULL; -} diff --git a/drivers/net/softnic/rte_eth_softnic_internals.h b/drivers/net/softnic/rte_eth_softnic_internals.h index d578cb1f25..ddcde99b98 100644 --- a/drivers/net/softnic/rte_eth_softnic_internals.h +++ b/drivers/net/softnic/rte_eth_softnic_internals.h @@ -100,28 +100,6 @@ struct softnic_tap { TAILQ_HEAD(softnic_tap_list, softnic_tap); -/** - * Cryptodev - */ -struct softnic_cryptodev_params { - const char *dev_name; - uint32_t dev_id; /**< Valid only when *dev_name* is NULL. */ - uint32_t n_queues; - uint32_t queue_size; - uint32_t session_pool_size; -}; - -struct softnic_cryptodev { - TAILQ_ENTRY(softnic_cryptodev) node; - char name[NAME_SIZE]; - uint16_t dev_id; - uint32_t n_queues; - struct rte_mempool *mp_create; - struct rte_mempool *mp_init; -}; - -TAILQ_HEAD(softnic_cryptodev_list, softnic_cryptodev); - /** * Input port action */ @@ -187,7 +165,6 @@ enum softnic_port_in_type { PORT_IN_SWQ, PORT_IN_TAP, PORT_IN_SOURCE, - PORT_IN_CRYPTODEV, }; struct softnic_port_in_params { @@ -209,12 +186,6 @@ struct softnic_port_in_params { const char *file_name; uint32_t n_bytes_per_pkt; } source; - - struct { - uint16_t queue_id; - void *f_callback; - void *arg_callback; - } cryptodev; }; uint32_t burst_size; @@ -227,7 +198,6 @@ enum softnic_port_out_type { PORT_OUT_SWQ, PORT_OUT_TAP, PORT_OUT_SINK, - PORT_OUT_CRYPTODEV, }; struct softnic_port_out_params { @@ -242,11 +212,6 @@ struct softnic_port_out_params { const char *file_name; uint32_t max_n_pkts; } sink; - - struct { - uint16_t queue_id; - uint32_t op_offset; - } cryptodev; }; uint32_t burst_size; int retry; @@ -421,7 +386,6 @@ struct pmd_internals { struct softnic_swq_list swq_list; struct softnic_link_list link_list; struct softnic_tap_list tap_list; - struct softnic_cryptodev_list cryptodev_list; struct softnic_port_in_action_profile_list port_in_action_profile_list; struct softnic_table_action_profile_list table_action_profile_list; struct pipeline_list pipeline_list; @@ -519,24 +483,6 @@ struct softnic_tap * softnic_tap_create(struct pmd_internals *p, const char *name); -/** - * Sym Crypto - */ -int -softnic_cryptodev_init(struct pmd_internals *p); - -void -softnic_cryptodev_free(struct pmd_internals *p); - -struct softnic_cryptodev * -softnic_cryptodev_find(struct pmd_internals *p, - const char *name); - -struct softnic_cryptodev * -softnic_cryptodev_create(struct pmd_internals *p, - const char *name, - struct softnic_cryptodev_params *params); - /** * Input port action */ diff --git a/drivers/net/softnic/rte_eth_softnic_pipeline.c b/drivers/net/softnic/rte_eth_softnic_pipeline.c index 2cf7fa52d1..51a1ea73c0 100644 --- a/drivers/net/softnic/rte_eth_softnic_pipeline.c +++ b/drivers/net/softnic/rte_eth_softnic_pipeline.c @@ -227,7 +227,6 @@ softnic_pipeline_port_in_create(struct pmd_internals *softnic, struct rte_port_sched_reader_params sched; struct rte_port_fd_reader_params fd; struct rte_port_source_params source; - struct rte_port_sym_crypto_reader_params cryptodev; } pp; struct pipeline *pipeline; @@ -330,23 +329,6 @@ softnic_pipeline_port_in_create(struct pmd_internals *softnic, break; } - case PORT_IN_CRYPTODEV: - { - struct softnic_cryptodev *cryptodev; - - cryptodev = softnic_cryptodev_find(softnic, params->dev_name); - if (cryptodev == NULL) - return -1; - - pp.cryptodev.cryptodev_id = cryptodev->dev_id; - pp.cryptodev.queue_id = params->cryptodev.queue_id; - pp.cryptodev.f_callback = params->cryptodev.f_callback; - pp.cryptodev.arg_callback = params->cryptodev.arg_callback; - p.ops = &rte_port_sym_crypto_reader_ops; - p.arg_create = &pp.cryptodev; - break; - } - default: return -1; } @@ -433,14 +415,12 @@ softnic_pipeline_port_out_create(struct pmd_internals *softnic, struct rte_port_sched_writer_params sched; struct rte_port_fd_writer_params fd; struct rte_port_sink_params sink; - struct rte_port_sym_crypto_writer_params cryptodev; } pp; union { struct rte_port_ethdev_writer_nodrop_params ethdev; struct rte_port_ring_writer_nodrop_params ring; struct rte_port_fd_writer_nodrop_params fd; - struct rte_port_sym_crypto_writer_nodrop_params cryptodev; } pp_nodrop; struct pipeline *pipeline; @@ -554,40 +534,6 @@ softnic_pipeline_port_out_create(struct pmd_internals *softnic, break; } - case PORT_OUT_CRYPTODEV: - { - struct softnic_cryptodev *cryptodev; - - cryptodev = softnic_cryptodev_find(softnic, params->dev_name); - if (cryptodev == NULL) - return -1; - - if (params->cryptodev.queue_id >= cryptodev->n_queues) - return -1; - - pp.cryptodev.cryptodev_id = cryptodev->dev_id; - pp.cryptodev.queue_id = params->cryptodev.queue_id; - pp.cryptodev.tx_burst_sz = params->burst_size; - pp.cryptodev.crypto_op_offset = params->cryptodev.op_offset; - - pp_nodrop.cryptodev.cryptodev_id = cryptodev->dev_id; - pp_nodrop.cryptodev.queue_id = params->cryptodev.queue_id; - pp_nodrop.cryptodev.tx_burst_sz = params->burst_size; - pp_nodrop.cryptodev.n_retries = params->retry; - pp_nodrop.cryptodev.crypto_op_offset = - params->cryptodev.op_offset; - - if (params->retry == 0) { - p.ops = &rte_port_sym_crypto_writer_ops; - p.arg_create = &pp.cryptodev; - } else { - p.ops = &rte_port_sym_crypto_writer_nodrop_ops; - p.arg_create = &pp_nodrop.cryptodev; - } - - break; - } - default: return -1; } From patchwork Thu Aug 4 16:58:23 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Dumitrescu X-Patchwork-Id: 114628 X-Patchwork-Delegate: andrew.rybchenko@oktetlabs.ru 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 EB6A2A00C4; Thu, 4 Aug 2022 18:59:27 +0200 (CEST) Received: from [217.70.189.124] (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id B07CB42C0F; Thu, 4 Aug 2022 18:58:59 +0200 (CEST) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by mails.dpdk.org (Postfix) with ESMTP id 32C0142BF1 for ; Thu, 4 Aug 2022 18:58:54 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1659632334; x=1691168334; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=6WklVaKDbqddeo1Nn5SNNCuoIBb7qyEX3VtGVbcO7hs=; b=VKQaKEFWIbYIDzMkREwTbtgqfXkxYnk3HmOkblOBjoCxtVSaJFwy5AA4 Xsm3suNQS+rfRWzVMoTrsL3kXf+QMF3KewDGRmLxO8UsOXq3MscMFvucE 5imStyrDKDazexhqmscYZuqwhueTldFumEALFKjOhn8I0yLz/HNdnDpQt AJHipLzd+CjS//0yG99ivfO0+g+9CgIwN/ZfIIY8IuViG0ir0XUhTDZ5O AsQe0G2hrBTzcI7yhdU36Z06aS1h9EyRsPR46gD6N3cHlwS00T8Dm7xTe TCR8+2//ytz1y7d6c2cBxh4o2Yph9PuPKwZ0aSmVpbWlBnh07svo7yPrB Q==; X-IronPort-AV: E=McAfee;i="6400,9594,10429"; a="290000100" X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="290000100" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 04 Aug 2022 09:58:51 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="636163121" Received: from silpixa00400573.ir.intel.com (HELO silpixa00400573.ger.corp.intel.com) ([10.237.223.157]) by orsmga001.jf.intel.com with ESMTP; 04 Aug 2022 09:58:49 -0700 From: Cristian Dumitrescu To: dev@dpdk.org Cc: jasvinder.singh@intel.com, yogesh.jangra@intel.com Subject: [PATCH 05/21] net/softnic: remove tap support Date: Thu, 4 Aug 2022 16:58:23 +0000 Message-Id: <20220804165839.1074817-6-cristian.dumitrescu@intel.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> References: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> MIME-Version: 1.0 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 Remove the TUN/TAP device support. The TUN/TAP devices are still supported as virtual Ethernet devices through the TAP Poll Mode Driver. Signed-off-by: Cristian Dumitrescu Signed-off-by: Yogesh Jangra --- drivers/net/softnic/meson.build | 1 - drivers/net/softnic/rte_eth_softnic.c | 3 - drivers/net/softnic/rte_eth_softnic_cli.c | 76 ----------- .../net/softnic/rte_eth_softnic_internals.h | 36 ------ .../net/softnic/rte_eth_softnic_pipeline.c | 44 ------- drivers/net/softnic/rte_eth_softnic_tap.c | 118 ------------------ 6 files changed, 278 deletions(-) delete mode 100644 drivers/net/softnic/rte_eth_softnic_tap.c diff --git a/drivers/net/softnic/meson.build b/drivers/net/softnic/meson.build index b3d235841d..91f1f3220f 100644 --- a/drivers/net/softnic/meson.build +++ b/drivers/net/softnic/meson.build @@ -16,7 +16,6 @@ sources = files( 'rte_eth_softnic_mempool.c', 'rte_eth_softnic_pipeline.c', 'rte_eth_softnic_swq.c', - 'rte_eth_softnic_tap.c', 'rte_eth_softnic_thread.c', ) deps += ['pipeline', 'port', 'table'] diff --git a/drivers/net/softnic/rte_eth_softnic.c b/drivers/net/softnic/rte_eth_softnic.c index 1ea5989223..eb97ae7185 100644 --- a/drivers/net/softnic/rte_eth_softnic.c +++ b/drivers/net/softnic/rte_eth_softnic.c @@ -162,7 +162,6 @@ pmd_dev_stop(struct rte_eth_dev *dev) softnic_pipeline_free(p); softnic_table_action_profile_free(p); softnic_port_in_action_profile_free(p); - softnic_tap_free(p); softnic_link_free(p); softnic_softnic_swq_free_keep_rxq_txq(p); softnic_mempool_free(p); @@ -183,7 +182,6 @@ pmd_free(struct pmd_internals *p) softnic_pipeline_free(p); softnic_table_action_profile_free(p); softnic_port_in_action_profile_free(p); - softnic_tap_free(p); softnic_link_free(p); softnic_swq_free(p); softnic_mempool_free(p); @@ -263,7 +261,6 @@ pmd_init(struct pmd_params *params) softnic_mempool_init(p); softnic_swq_init(p); softnic_link_init(p); - softnic_tap_init(p); softnic_port_in_action_profile_init(p); softnic_table_action_profile_init(p); softnic_pipeline_init(p); diff --git a/drivers/net/softnic/rte_eth_softnic_cli.c b/drivers/net/softnic/rte_eth_softnic_cli.c index bca0b176d6..501ef08c4c 100644 --- a/drivers/net/softnic/rte_eth_softnic_cli.c +++ b/drivers/net/softnic/rte_eth_softnic_cli.c @@ -186,33 +186,6 @@ cmd_swq(struct pmd_internals *softnic, } } -/** - * tap - */ -static void -cmd_tap(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - char *name; - struct softnic_tap *tap; - - if (n_tokens != 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - name = tokens[1]; - - tap = softnic_tap_create(softnic, name); - if (tap == NULL) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - /** * port in action profile * [filter match | mismatch offset mask key port ] @@ -874,7 +847,6 @@ cmd_pipeline(struct pmd_internals *softnic, * bsz * link rxq * | swq - * | tap mempool mtu * | source mempool file bpp * [action ] * [disabled] @@ -957,38 +929,6 @@ cmd_pipeline_port_in(struct pmd_internals *softnic, strlcpy(p.dev_name, tokens[t0 + 1], sizeof(p.dev_name)); t0 += 2; - } else if (strcmp(tokens[t0], "tap") == 0) { - if (n_tokens < t0 + 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port in tap"); - return; - } - - p.type = PORT_IN_TAP; - - strlcpy(p.dev_name, tokens[t0 + 1], sizeof(p.dev_name)); - - if (strcmp(tokens[t0 + 2], "mempool") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "mempool"); - return; - } - - p.tap.mempool_name = tokens[t0 + 3]; - - if (strcmp(tokens[t0 + 4], "mtu") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "mtu"); - return; - } - - if (softnic_parser_read_uint32(&p.tap.mtu, - tokens[t0 + 5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "mtu"); - return; - } - - t0 += 6; } else if (strcmp(tokens[t0], "source") == 0) { if (n_tokens < t0 + 6) { snprintf(out, out_size, MSG_ARG_MISMATCH, @@ -1074,7 +1014,6 @@ cmd_pipeline_port_in(struct pmd_internals *softnic, * bsz * link txq * | swq - * | tap * | sink [file pkts ] */ static void @@ -1147,16 +1086,6 @@ cmd_pipeline_port_out(struct pmd_internals *softnic, p.type = PORT_OUT_SWQ; - strlcpy(p.dev_name, tokens[7], sizeof(p.dev_name)); - } else if (strcmp(tokens[6], "tap") == 0) { - if (n_tokens != 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out tap"); - return; - } - - p.type = PORT_OUT_TAP; - strlcpy(p.dev_name, tokens[7], sizeof(p.dev_name)); } else if (strcmp(tokens[6], "sink") == 0) { if ((n_tokens != 7) && (n_tokens != 11)) { @@ -4600,11 +4529,6 @@ softnic_cli_process(char *in, char *out, size_t out_size, void *arg) return; } - if (strcmp(tokens[0], "tap") == 0) { - cmd_tap(softnic, tokens, n_tokens, out, out_size); - return; - } - if (strcmp(tokens[0], "port") == 0) { cmd_port_in_action_profile(softnic, tokens, n_tokens, out, out_size); return; diff --git a/drivers/net/softnic/rte_eth_softnic_internals.h b/drivers/net/softnic/rte_eth_softnic_internals.h index ddcde99b98..df74c1fbdc 100644 --- a/drivers/net/softnic/rte_eth_softnic_internals.h +++ b/drivers/net/softnic/rte_eth_softnic_internals.h @@ -89,17 +89,6 @@ struct softnic_link { TAILQ_HEAD(softnic_link_list, softnic_link); -/** - * TAP - */ -struct softnic_tap { - TAILQ_ENTRY(softnic_tap) node; - char name[NAME_SIZE]; - int fd; -}; - -TAILQ_HEAD(softnic_tap_list, softnic_tap); - /** * Input port action */ @@ -163,7 +152,6 @@ struct pipeline_params { enum softnic_port_in_type { PORT_IN_RXQ, PORT_IN_SWQ, - PORT_IN_TAP, PORT_IN_SOURCE, }; @@ -176,11 +164,6 @@ struct softnic_port_in_params { uint16_t queue_id; } rxq; - struct { - const char *mempool_name; - uint32_t mtu; - } tap; - struct { const char *mempool_name; const char *file_name; @@ -196,7 +179,6 @@ struct softnic_port_in_params { enum softnic_port_out_type { PORT_OUT_TXQ, PORT_OUT_SWQ, - PORT_OUT_TAP, PORT_OUT_SINK, }; @@ -385,7 +367,6 @@ struct pmd_internals { struct softnic_mempool_list mempool_list; struct softnic_swq_list swq_list; struct softnic_link_list link_list; - struct softnic_tap_list tap_list; struct softnic_port_in_action_profile_list port_in_action_profile_list; struct softnic_table_action_profile_list table_action_profile_list; struct pipeline_list pipeline_list; @@ -466,23 +447,6 @@ softnic_link_create(struct pmd_internals *p, const char *name, struct softnic_link_params *params); -/** - * TAP - */ -int -softnic_tap_init(struct pmd_internals *p); - -void -softnic_tap_free(struct pmd_internals *p); - -struct softnic_tap * -softnic_tap_find(struct pmd_internals *p, - const char *name); - -struct softnic_tap * -softnic_tap_create(struct pmd_internals *p, - const char *name); - /** * Input port action */ diff --git a/drivers/net/softnic/rte_eth_softnic_pipeline.c b/drivers/net/softnic/rte_eth_softnic_pipeline.c index 51a1ea73c0..7a2828b785 100644 --- a/drivers/net/softnic/rte_eth_softnic_pipeline.c +++ b/drivers/net/softnic/rte_eth_softnic_pipeline.c @@ -293,25 +293,6 @@ softnic_pipeline_port_in_create(struct pmd_internals *softnic, break; } - case PORT_IN_TAP: - { - struct softnic_tap *tap; - struct softnic_mempool *mempool; - - tap = softnic_tap_find(softnic, params->dev_name); - mempool = softnic_mempool_find(softnic, params->tap.mempool_name); - if (tap == NULL || mempool == NULL) - return -1; - - pp.fd.fd = tap->fd; - pp.fd.mempool = mempool->m; - pp.fd.mtu = params->tap.mtu; - - p.ops = &rte_port_fd_reader_ops; - p.arg_create = &pp.fd; - break; - } - case PORT_IN_SOURCE: { struct softnic_mempool *mempool; @@ -499,31 +480,6 @@ softnic_pipeline_port_out_create(struct pmd_internals *softnic, break; } - case PORT_OUT_TAP: - { - struct softnic_tap *tap; - - tap = softnic_tap_find(softnic, params->dev_name); - if (tap == NULL) - return -1; - - pp.fd.fd = tap->fd; - pp.fd.tx_burst_sz = params->burst_size; - - pp_nodrop.fd.fd = tap->fd; - pp_nodrop.fd.tx_burst_sz = params->burst_size; - pp_nodrop.fd.n_retries = params->n_retries; - - if (params->retry == 0) { - p.ops = &rte_port_fd_writer_ops; - p.arg_create = &pp.fd; - } else { - p.ops = &rte_port_fd_writer_nodrop_ops; - p.arg_create = &pp_nodrop.fd; - } - break; - } - case PORT_OUT_SINK: { pp.sink.file_name = params->sink.file_name; diff --git a/drivers/net/softnic/rte_eth_softnic_tap.c b/drivers/net/softnic/rte_eth_softnic_tap.c deleted file mode 100644 index 36fe9f0287..0000000000 --- a/drivers/net/softnic/rte_eth_softnic_tap.c +++ /dev/null @@ -1,118 +0,0 @@ -/* SPDX-License-Identifier: BSD-3-Clause - * Copyright(c) 2010-2018 Intel Corporation - */ - -#include -#ifdef RTE_EXEC_ENV_LINUX -#include -#include -#endif -#include - -#include -#include -#include -#include -#include - -#include - -#include "rte_eth_softnic_internals.h" - -#define TAP_DEV "/dev/net/tun" - -int -softnic_tap_init(struct pmd_internals *p) -{ - TAILQ_INIT(&p->tap_list); - - return 0; -} - -void -softnic_tap_free(struct pmd_internals *p) -{ - for ( ; ; ) { - struct softnic_tap *tap; - - tap = TAILQ_FIRST(&p->tap_list); - if (tap == NULL) - break; - - TAILQ_REMOVE(&p->tap_list, tap, node); - free(tap); - } -} - -struct softnic_tap * -softnic_tap_find(struct pmd_internals *p, - const char *name) -{ - struct softnic_tap *tap; - - if (name == NULL) - return NULL; - - TAILQ_FOREACH(tap, &p->tap_list, node) - if (strcmp(tap->name, name) == 0) - return tap; - - return NULL; -} - -#ifndef RTE_EXEC_ENV_LINUX - -struct softnic_tap * -softnic_tap_create(struct pmd_internals *p __rte_unused, - const char *name __rte_unused) -{ - return NULL; -} - -#else - -struct softnic_tap * -softnic_tap_create(struct pmd_internals *p, - const char *name) -{ - struct softnic_tap *tap; - struct ifreq ifr; - int fd, status; - - /* Check input params */ - if (name == NULL || - softnic_tap_find(p, name)) - return NULL; - - /* Resource create */ - fd = open(TAP_DEV, O_RDWR | O_NONBLOCK); - if (fd < 0) - return NULL; - - memset(&ifr, 0, sizeof(ifr)); - ifr.ifr_flags = IFF_TAP | IFF_NO_PI; /* No packet information */ - strlcpy(ifr.ifr_name, name, IFNAMSIZ); - - status = ioctl(fd, TUNSETIFF, (void *)&ifr); - if (status < 0) { - close(fd); - return NULL; - } - - /* Node allocation */ - tap = calloc(1, sizeof(struct softnic_tap)); - if (tap == NULL) { - close(fd); - return NULL; - } - /* Node fill in */ - strlcpy(tap->name, name, sizeof(tap->name)); - tap->fd = fd; - - /* Node add to list */ - TAILQ_INSERT_TAIL(&p->tap_list, tap, node); - - return tap; -} - -#endif From patchwork Thu Aug 4 16:58:24 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Cristian Dumitrescu X-Patchwork-Id: 114629 X-Patchwork-Delegate: andrew.rybchenko@oktetlabs.ru 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 42D0FA00C4; Thu, 4 Aug 2022 18:59:34 +0200 (CEST) Received: from [217.70.189.124] (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 91BC642C11; Thu, 4 Aug 2022 18:59:00 +0200 (CEST) Received: from mga14.intel.com (mga14.intel.com [192.55.52.115]) by mails.dpdk.org (Postfix) with ESMTP id 8BB904067C for ; Thu, 4 Aug 2022 18:58:54 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=intel.com; i=@intel.com; q=dns/txt; s=Intel; t=1659632334; x=1691168334; h=from:to:cc:subject:date:message-id:in-reply-to: references:mime-version:content-transfer-encoding; bh=yoQpkTC8iw6xIoVUr7HzjF30M1vhbnmYoG2egDsmI+Y=; b=iXZikqrjEGe7946IWDB3VPq+8Fhw2BlIfDF5laGVVLqmFSzDPWMW7dyM 4NMA/2tIsLLSg8JRf2Z6T3SFXGZOUv1L7mXCMZyd0iKQbOj1M2JR28++k ErkOGuEp0zAuIGj9/XXe36J7iStLjKWiHN7XSrGlleV9v5eWLIYxkJsNa Sa45ESujIm86qdgVXhW1YFNE2aJi0UlYw8WslTppdIxuhTciAQ9yRwbsz /qXsSTHcnFM6DUv2fJmhr0+9DnMQMrEYkWHw0yyfBJyWYsPx9QJ+gqilv qk72E420NB1VKxVI1YVJl2mqhxUcQQePP0U4jIJCGatsU5nMjEy6jtVnj g==; X-IronPort-AV: E=McAfee;i="6400,9594,10429"; a="290000107" X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="290000107" Received: from orsmga001.jf.intel.com ([10.7.209.18]) by fmsmga103.fm.intel.com with ESMTP/TLS/ECDHE-RSA-AES256-GCM-SHA384; 04 Aug 2022 09:58:53 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.93,216,1654585200"; d="scan'208";a="636163133" Received: from silpixa00400573.ir.intel.com (HELO silpixa00400573.ger.corp.intel.com) ([10.237.223.157]) by orsmga001.jf.intel.com with ESMTP; 04 Aug 2022 09:58:51 -0700 From: Cristian Dumitrescu To: dev@dpdk.org Cc: jasvinder.singh@intel.com, yogesh.jangra@intel.com Subject: [PATCH 06/21] net/softnic: remove the legacy pipeline CLI commands Date: Thu, 4 Aug 2022 16:58:24 +0000 Message-Id: <20220804165839.1074817-7-cristian.dumitrescu@intel.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> References: <20220804165839.1074817-1-cristian.dumitrescu@intel.com> MIME-Version: 1.0 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 Remove the legacy pipeline CLI commands. Signed-off-by: Cristian Dumitrescu Signed-off-by: Yogesh Jangra --- drivers/net/softnic/rte_eth_softnic_cli.c | 4527 --------------------- 1 file changed, 4527 deletions(-) diff --git a/drivers/net/softnic/rte_eth_softnic_cli.c b/drivers/net/softnic/rte_eth_softnic_cli.c index 501ef08c4c..abe275ec83 100644 --- a/drivers/net/softnic/rte_eth_softnic_cli.c +++ b/drivers/net/softnic/rte_eth_softnic_cli.c @@ -10,7 +10,6 @@ #include #include #include -#include #include "rte_eth_softnic_internals.h" #include "parser.h" @@ -186,4227 +185,6 @@ cmd_swq(struct pmd_internals *softnic, } } -/** - * port in action profile - * [filter match | mismatch offset mask key port ] - * [balance offset mask port ... ] - */ -static void -cmd_port_in_action_profile(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct softnic_port_in_action_profile_params p; - struct softnic_port_in_action_profile *ap; - char *name; - uint32_t t0; - - memset(&p, 0, sizeof(p)); - - if (n_tokens < 5) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "in") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "in"); - return; - } - - if (strcmp(tokens[2], "action") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "action"); - return; - } - - if (strcmp(tokens[3], "profile") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "profile"); - return; - } - - name = tokens[4]; - - t0 = 5; - - if (t0 < n_tokens && - (strcmp(tokens[t0], "filter") == 0)) { - uint32_t size; - - if (n_tokens < t0 + 10) { - snprintf(out, out_size, MSG_ARG_MISMATCH, "port in action profile filter"); - return; - } - - if (strcmp(tokens[t0 + 1], "match") == 0) { - p.fltr.filter_on_match = 1; - } else if (strcmp(tokens[t0 + 1], "mismatch") == 0) { - p.fltr.filter_on_match = 0; - } else { - snprintf(out, out_size, MSG_ARG_INVALID, "match or mismatch"); - return; - } - - if (strcmp(tokens[t0 + 2], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.fltr.key_offset, - tokens[t0 + 3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_offset"); - return; - } - - if (strcmp(tokens[t0 + 4], "mask") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "mask"); - return; - } - - size = RTE_PORT_IN_ACTION_FLTR_KEY_SIZE; - if ((softnic_parse_hex_string(tokens[t0 + 5], - p.fltr.key_mask, &size) != 0) || - size != RTE_PORT_IN_ACTION_FLTR_KEY_SIZE) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_mask"); - return; - } - - if (strcmp(tokens[t0 + 6], "key") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "key"); - return; - } - - size = RTE_PORT_IN_ACTION_FLTR_KEY_SIZE; - if ((softnic_parse_hex_string(tokens[t0 + 7], - p.fltr.key, &size) != 0) || - size != RTE_PORT_IN_ACTION_FLTR_KEY_SIZE) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_value"); - return; - } - - if (strcmp(tokens[t0 + 8], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (softnic_parser_read_uint32(&p.fltr.port_id, - tokens[t0 + 9]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port_id"); - return; - } - - p.action_mask |= 1LLU << RTE_PORT_IN_ACTION_FLTR; - t0 += 10; - } /* filter */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "balance") == 0)) { - uint32_t i; - - if (n_tokens < t0 + 22) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "port in action profile balance"); - return; - } - - if (strcmp(tokens[t0 + 1], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.lb.key_offset, - tokens[t0 + 2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_offset"); - return; - } - - if (strcmp(tokens[t0 + 3], "mask") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "mask"); - return; - } - - p.lb.key_size = RTE_PORT_IN_ACTION_LB_KEY_SIZE_MAX; - if (softnic_parse_hex_string(tokens[t0 + 4], - p.lb.key_mask, &p.lb.key_size) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_mask"); - return; - } - - if (strcmp(tokens[t0 + 5], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - for (i = 0; i < 16; i++) - if (softnic_parser_read_uint32(&p.lb.port_id[i], - tokens[t0 + 6 + i]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port_id"); - return; - } - - p.action_mask |= 1LLU << RTE_PORT_IN_ACTION_LB; - t0 += 22; - } /* balance */ - - if (t0 < n_tokens) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - ap = softnic_port_in_action_profile_create(softnic, name, &p); - if (ap == NULL) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * table action profile - * ipv4 | ipv6 - * offset - * fwd - * [balance offset mask outoffset ] - * [meter srtcm | trtcm - * tc - * stats none | pkts | bytes | both] - * [tm spp pps ] - * [encap ether | vlan | qinq | mpls | pppoe | qinq_pppoe | - * vxlan offset ipv4 | ipv6 vlan on | off] - * [nat src | dst - * proto udp | tcp] - * [ttl drop | fwd - * stats none | pkts] - * [stats pkts | bytes | both] - * [time] - * [tag] - * [decap] - * - */ -static void -cmd_table_action_profile(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct softnic_table_action_profile_params p; - struct softnic_table_action_profile *ap; - char *name; - uint32_t t0; - - memset(&p, 0, sizeof(p)); - - if (n_tokens < 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - if (strcmp(tokens[1], "action") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "action"); - return; - } - - if (strcmp(tokens[2], "profile") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "profile"); - return; - } - - name = tokens[3]; - - if (strcmp(tokens[4], "ipv4") == 0) { - p.common.ip_version = 1; - } else if (strcmp(tokens[4], "ipv6") == 0) { - p.common.ip_version = 0; - } else { - snprintf(out, out_size, MSG_ARG_INVALID, "ipv4 or ipv6"); - return; - } - - if (strcmp(tokens[5], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.common.ip_offset, - tokens[6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "ip_offset"); - return; - } - - if (strcmp(tokens[7], "fwd") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "fwd"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_FWD; - - t0 = 8; - if (t0 < n_tokens && - (strcmp(tokens[t0], "balance") == 0)) { - if (n_tokens < t0 + 7) { - snprintf(out, out_size, MSG_ARG_MISMATCH, "table action profile balance"); - return; - } - - if (strcmp(tokens[t0 + 1], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.lb.key_offset, - tokens[t0 + 2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_offset"); - return; - } - - if (strcmp(tokens[t0 + 3], "mask") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "mask"); - return; - } - - p.lb.key_size = RTE_PORT_IN_ACTION_LB_KEY_SIZE_MAX; - if (softnic_parse_hex_string(tokens[t0 + 4], - p.lb.key_mask, &p.lb.key_size) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_mask"); - return; - } - - if (strcmp(tokens[t0 + 5], "outoffset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "outoffset"); - return; - } - - if (softnic_parser_read_uint32(&p.lb.out_offset, - tokens[t0 + 6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "out_offset"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_LB; - t0 += 7; - } /* balance */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "meter") == 0)) { - if (n_tokens < t0 + 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "table action profile meter"); - return; - } - - if (strcmp(tokens[t0 + 1], "srtcm") == 0) { - p.mtr.alg = RTE_TABLE_ACTION_METER_SRTCM; - } else if (strcmp(tokens[t0 + 1], "trtcm") == 0) { - p.mtr.alg = RTE_TABLE_ACTION_METER_TRTCM; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "srtcm or trtcm"); - return; - } - - if (strcmp(tokens[t0 + 2], "tc") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "tc"); - return; - } - - if (softnic_parser_read_uint32(&p.mtr.n_tc, - tokens[t0 + 3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_tc"); - return; - } - - if (strcmp(tokens[t0 + 4], "stats") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "stats"); - return; - } - - if (strcmp(tokens[t0 + 5], "none") == 0) { - p.mtr.n_packets_enabled = 0; - p.mtr.n_bytes_enabled = 0; - } else if (strcmp(tokens[t0 + 5], "pkts") == 0) { - p.mtr.n_packets_enabled = 1; - p.mtr.n_bytes_enabled = 0; - } else if (strcmp(tokens[t0 + 5], "bytes") == 0) { - p.mtr.n_packets_enabled = 0; - p.mtr.n_bytes_enabled = 1; - } else if (strcmp(tokens[t0 + 5], "both") == 0) { - p.mtr.n_packets_enabled = 1; - p.mtr.n_bytes_enabled = 1; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "none or pkts or bytes or both"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_MTR; - t0 += 6; - } /* meter */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "tm") == 0)) { - if (n_tokens < t0 + 5) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "table action profile tm"); - return; - } - - if (strcmp(tokens[t0 + 1], "spp") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "spp"); - return; - } - - if (softnic_parser_read_uint32(&p.tm.n_subports_per_port, - tokens[t0 + 2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "n_subports_per_port"); - return; - } - - if (strcmp(tokens[t0 + 3], "pps") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "pps"); - return; - } - - if (softnic_parser_read_uint32(&p.tm.n_pipes_per_subport, - tokens[t0 + 4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "n_pipes_per_subport"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_TM; - t0 += 5; - } /* tm */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "encap") == 0)) { - uint32_t n_extra_tokens = 0; - - if (n_tokens < t0 + 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "action profile encap"); - return; - } - - if (strcmp(tokens[t0 + 1], "ether") == 0) { - p.encap.encap_mask = 1LLU << RTE_TABLE_ACTION_ENCAP_ETHER; - } else if (strcmp(tokens[t0 + 1], "vlan") == 0) { - p.encap.encap_mask = 1LLU << RTE_TABLE_ACTION_ENCAP_VLAN; - } else if (strcmp(tokens[t0 + 1], "qinq") == 0) { - p.encap.encap_mask = 1LLU << RTE_TABLE_ACTION_ENCAP_QINQ; - } else if (strcmp(tokens[t0 + 1], "mpls") == 0) { - p.encap.encap_mask = 1LLU << RTE_TABLE_ACTION_ENCAP_MPLS; - } else if (strcmp(tokens[t0 + 1], "pppoe") == 0) { - p.encap.encap_mask = 1LLU << RTE_TABLE_ACTION_ENCAP_PPPOE; - } else if (strcmp(tokens[t0 + 1], "vxlan") == 0) { - if (n_tokens < t0 + 2 + 5) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "action profile encap vxlan"); - return; - } - - if (strcmp(tokens[t0 + 2], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "vxlan: offset"); - return; - } - - if (softnic_parser_read_uint32(&p.encap.vxlan.data_offset, - tokens[t0 + 2 + 1]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "vxlan: ether_offset"); - return; - } - - if (strcmp(tokens[t0 + 2 + 2], "ipv4") == 0) - p.encap.vxlan.ip_version = 1; - else if (strcmp(tokens[t0 + 2 + 2], "ipv6") == 0) - p.encap.vxlan.ip_version = 0; - else { - snprintf(out, out_size, MSG_ARG_INVALID, - "vxlan: ipv4 or ipv6"); - return; - } - - if (strcmp(tokens[t0 + 2 + 3], "vlan") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "vxlan: vlan"); - return; - } - - if (strcmp(tokens[t0 + 2 + 4], "on") == 0) - p.encap.vxlan.vlan = 1; - else if (strcmp(tokens[t0 + 2 + 4], "off") == 0) - p.encap.vxlan.vlan = 0; - else { - snprintf(out, out_size, MSG_ARG_INVALID, - "vxlan: on or off"); - return; - } - - p.encap.encap_mask = 1LLU << RTE_TABLE_ACTION_ENCAP_VXLAN; - n_extra_tokens = 5; - - } else if (strcmp(tokens[t0 + 1], "qinq_pppoe") == 0) { - p.encap.encap_mask = - 1LLU << RTE_TABLE_ACTION_ENCAP_QINQ_PPPOE; - } else { - snprintf(out, out_size, MSG_ARG_MISMATCH, "encap"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_ENCAP; - t0 += 2 + n_extra_tokens; - } /* encap */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "nat") == 0)) { - if (n_tokens < t0 + 4) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "table action profile nat"); - return; - } - - if (strcmp(tokens[t0 + 1], "src") == 0) { - p.nat.source_nat = 1; - } else if (strcmp(tokens[t0 + 1], "dst") == 0) { - p.nat.source_nat = 0; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "src or dst"); - return; - } - - if (strcmp(tokens[t0 + 2], "proto") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "proto"); - return; - } - - if (strcmp(tokens[t0 + 3], "tcp") == 0) { - p.nat.proto = 0x06; - } else if (strcmp(tokens[t0 + 3], "udp") == 0) { - p.nat.proto = 0x11; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "tcp or udp"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_NAT; - t0 += 4; - } /* nat */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "ttl") == 0)) { - if (n_tokens < t0 + 4) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "table action profile ttl"); - return; - } - - if (strcmp(tokens[t0 + 1], "drop") == 0) { - p.ttl.drop = 1; - } else if (strcmp(tokens[t0 + 1], "fwd") == 0) { - p.ttl.drop = 0; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "drop or fwd"); - return; - } - - if (strcmp(tokens[t0 + 2], "stats") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "stats"); - return; - } - - if (strcmp(tokens[t0 + 3], "none") == 0) { - p.ttl.n_packets_enabled = 0; - } else if (strcmp(tokens[t0 + 3], "pkts") == 0) { - p.ttl.n_packets_enabled = 1; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "none or pkts"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_TTL; - t0 += 4; - } /* ttl */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "stats") == 0)) { - if (n_tokens < t0 + 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "table action profile stats"); - return; - } - - if (strcmp(tokens[t0 + 1], "pkts") == 0) { - p.stats.n_packets_enabled = 1; - p.stats.n_bytes_enabled = 0; - } else if (strcmp(tokens[t0 + 1], "bytes") == 0) { - p.stats.n_packets_enabled = 0; - p.stats.n_bytes_enabled = 1; - } else if (strcmp(tokens[t0 + 1], "both") == 0) { - p.stats.n_packets_enabled = 1; - p.stats.n_bytes_enabled = 1; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "pkts or bytes or both"); - return; - } - - p.action_mask |= 1LLU << RTE_TABLE_ACTION_STATS; - t0 += 2; - } /* stats */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "time") == 0)) { - p.action_mask |= 1LLU << RTE_TABLE_ACTION_TIME; - t0 += 1; - } /* time */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "tag") == 0)) { - p.action_mask |= 1LLU << RTE_TABLE_ACTION_TAG; - t0 += 1; - } /* tag */ - - if (t0 < n_tokens && - (strcmp(tokens[t0], "decap") == 0)) { - p.action_mask |= 1LLU << RTE_TABLE_ACTION_DECAP; - t0 += 1; - } /* decap */ - - if (t0 < n_tokens) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - ap = softnic_table_action_profile_create(softnic, name, &p); - if (ap == NULL) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline - * period - * offset_port_id - */ -static void -cmd_pipeline(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct pipeline_params p; - char *name; - struct pipeline *pipeline; - - if (n_tokens != 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - name = tokens[1]; - - if (strcmp(tokens[2], "period") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "period"); - return; - } - - if (softnic_parser_read_uint32(&p.timer_period_ms, - tokens[3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "timer_period_ms"); - return; - } - - if (strcmp(tokens[4], "offset_port_id") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset_port_id"); - return; - } - - if (softnic_parser_read_uint32(&p.offset_port_id, - tokens[5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "offset_port_id"); - return; - } - - pipeline = softnic_pipeline_create(softnic, name, &p); - if (pipeline == NULL) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline port in - * bsz - * link rxq - * | swq - * | source mempool file bpp - * [action ] - * [disabled] - */ -static void -cmd_pipeline_port_in(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct softnic_port_in_params p; - char *pipeline_name; - uint32_t t0; - int enabled, status; - - memset(&p, 0, sizeof(p)); - - if (n_tokens < 7) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (strcmp(tokens[3], "in") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "in"); - return; - } - - if (strcmp(tokens[4], "bsz") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "bsz"); - return; - } - - if (softnic_parser_read_uint32(&p.burst_size, tokens[5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "burst_size"); - return; - } - - t0 = 6; - - if (strcmp(tokens[t0], "link") == 0) { - if (n_tokens < t0 + 4) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port in link"); - return; - } - - p.type = PORT_IN_RXQ; - - strlcpy(p.dev_name, tokens[t0 + 1], sizeof(p.dev_name)); - - if (strcmp(tokens[t0 + 2], "rxq") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "rxq"); - return; - } - - if (softnic_parser_read_uint16(&p.rxq.queue_id, - tokens[t0 + 3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "queue_id"); - return; - } - t0 += 4; - } else if (strcmp(tokens[t0], "swq") == 0) { - if (n_tokens < t0 + 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port in swq"); - return; - } - - p.type = PORT_IN_SWQ; - - strlcpy(p.dev_name, tokens[t0 + 1], sizeof(p.dev_name)); - - t0 += 2; - } else if (strcmp(tokens[t0], "source") == 0) { - if (n_tokens < t0 + 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port in source"); - return; - } - - p.type = PORT_IN_SOURCE; - - if (strcmp(tokens[t0 + 1], "mempool") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "mempool"); - return; - } - - p.source.mempool_name = tokens[t0 + 2]; - - if (strcmp(tokens[t0 + 3], "file") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "file"); - return; - } - - p.source.file_name = tokens[t0 + 4]; - - if (strcmp(tokens[t0 + 5], "bpp") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "bpp"); - return; - } - - if (softnic_parser_read_uint32(&p.source.n_bytes_per_pkt, - tokens[t0 + 6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "n_bytes_per_pkt"); - return; - } - - t0 += 7; - } else { - snprintf(out, out_size, MSG_ARG_INVALID, tokens[0]); - return; - } - - if (n_tokens > t0 && - (strcmp(tokens[t0], "action") == 0)) { - if (n_tokens < t0 + 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, "action"); - return; - } - - strlcpy(p.action_profile_name, tokens[t0 + 1], - sizeof(p.action_profile_name)); - - t0 += 2; - } - - enabled = 1; - if (n_tokens > t0 && - (strcmp(tokens[t0], "disabled") == 0)) { - enabled = 0; - - t0 += 1; - } - - if (n_tokens != t0) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - status = softnic_pipeline_port_in_create(softnic, - pipeline_name, - &p, - enabled); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline port out - * bsz - * link txq - * | swq - * | sink [file pkts ] - */ -static void -cmd_pipeline_port_out(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct softnic_port_out_params p; - char *pipeline_name; - int status; - - memset(&p, 0, sizeof(p)); - - if (n_tokens < 7) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (strcmp(tokens[3], "out") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "out"); - return; - } - - if (strcmp(tokens[4], "bsz") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "bsz"); - return; - } - - if (softnic_parser_read_uint32(&p.burst_size, tokens[5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "burst_size"); - return; - } - - if (strcmp(tokens[6], "link") == 0) { - if (n_tokens != 10) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out link"); - return; - } - - p.type = PORT_OUT_TXQ; - - strlcpy(p.dev_name, tokens[7], sizeof(p.dev_name)); - - if (strcmp(tokens[8], "txq") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "txq"); - return; - } - - if (softnic_parser_read_uint16(&p.txq.queue_id, - tokens[9]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "queue_id"); - return; - } - } else if (strcmp(tokens[6], "swq") == 0) { - if (n_tokens != 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out swq"); - return; - } - - p.type = PORT_OUT_SWQ; - - strlcpy(p.dev_name, tokens[7], sizeof(p.dev_name)); - } else if (strcmp(tokens[6], "sink") == 0) { - if ((n_tokens != 7) && (n_tokens != 11)) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline port out sink"); - return; - } - - p.type = PORT_OUT_SINK; - - if (n_tokens == 7) { - p.sink.file_name = NULL; - p.sink.max_n_pkts = 0; - } else { - if (strcmp(tokens[7], "file") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "file"); - return; - } - - p.sink.file_name = tokens[8]; - - if (strcmp(tokens[9], "pkts") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "pkts"); - return; - } - - if (softnic_parser_read_uint32(&p.sink.max_n_pkts, - tokens[10]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "max_n_pkts"); - return; - } - } - } else { - snprintf(out, out_size, MSG_ARG_INVALID, tokens[0]); - return; - } - - status = softnic_pipeline_port_out_create(softnic, pipeline_name, &p); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline table - * match - * acl - * ipv4 | ipv6 - * offset - * size - * | array - * offset - * size - * | hash - * ext | lru - * key - * mask - * offset - * buckets - * size - * | lpm - * ipv4 | ipv6 - * offset - * size - * | stub - * [action ] - */ -static void -cmd_pipeline_table(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct softnic_table_params p; - char *pipeline_name; - uint32_t t0; - int status; - - memset(&p, 0, sizeof(p)); - - if (n_tokens < 5) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "table") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "table"); - return; - } - - if (strcmp(tokens[3], "match") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "match"); - return; - } - - t0 = 4; - if (strcmp(tokens[t0], "acl") == 0) { - if (n_tokens < t0 + 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline table acl"); - return; - } - - p.match_type = TABLE_ACL; - - if (strcmp(tokens[t0 + 1], "ipv4") == 0) { - p.match.acl.ip_version = 1; - } else if (strcmp(tokens[t0 + 1], "ipv6") == 0) { - p.match.acl.ip_version = 0; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "ipv4 or ipv6"); - return; - } - - if (strcmp(tokens[t0 + 2], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.match.acl.ip_header_offset, - tokens[t0 + 3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "ip_header_offset"); - return; - } - - if (strcmp(tokens[t0 + 4], "size") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "size"); - return; - } - - if (softnic_parser_read_uint32(&p.match.acl.n_rules, - tokens[t0 + 5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_rules"); - return; - } - - t0 += 6; - } else if (strcmp(tokens[t0], "array") == 0) { - if (n_tokens < t0 + 5) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline table array"); - return; - } - - p.match_type = TABLE_ARRAY; - - if (strcmp(tokens[t0 + 1], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.match.array.key_offset, - tokens[t0 + 2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_offset"); - return; - } - - if (strcmp(tokens[t0 + 3], "size") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "size"); - return; - } - - if (softnic_parser_read_uint32(&p.match.array.n_keys, - tokens[t0 + 4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_keys"); - return; - } - - t0 += 5; - } else if (strcmp(tokens[t0], "hash") == 0) { - uint32_t key_mask_size = TABLE_RULE_MATCH_SIZE_MAX; - - if (n_tokens < t0 + 12) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline table hash"); - return; - } - - p.match_type = TABLE_HASH; - - if (strcmp(tokens[t0 + 1], "ext") == 0) { - p.match.hash.extendable_bucket = 1; - } else if (strcmp(tokens[t0 + 1], "lru") == 0) { - p.match.hash.extendable_bucket = 0; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "ext or lru"); - return; - } - - if (strcmp(tokens[t0 + 2], "key") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "key"); - return; - } - - if ((softnic_parser_read_uint32(&p.match.hash.key_size, - tokens[t0 + 3]) != 0) || - p.match.hash.key_size == 0 || - p.match.hash.key_size > TABLE_RULE_MATCH_SIZE_MAX) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_size"); - return; - } - - if (strcmp(tokens[t0 + 4], "mask") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "mask"); - return; - } - - if ((softnic_parse_hex_string(tokens[t0 + 5], - p.match.hash.key_mask, &key_mask_size) != 0) || - key_mask_size != p.match.hash.key_size) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_mask"); - return; - } - - if (strcmp(tokens[t0 + 6], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.match.hash.key_offset, - tokens[t0 + 7]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_offset"); - return; - } - - if (strcmp(tokens[t0 + 8], "buckets") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "buckets"); - return; - } - - if (softnic_parser_read_uint32(&p.match.hash.n_buckets, - tokens[t0 + 9]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_buckets"); - return; - } - - if (strcmp(tokens[t0 + 10], "size") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "size"); - return; - } - - if (softnic_parser_read_uint32(&p.match.hash.n_keys, - tokens[t0 + 11]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_keys"); - return; - } - - t0 += 12; - } else if (strcmp(tokens[t0], "lpm") == 0) { - if (n_tokens < t0 + 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "pipeline table lpm"); - return; - } - - p.match_type = TABLE_LPM; - - if (strcmp(tokens[t0 + 1], "ipv4") == 0) { - p.match.lpm.key_size = 4; - } else if (strcmp(tokens[t0 + 1], "ipv6") == 0) { - p.match.lpm.key_size = 16; - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "ipv4 or ipv6"); - return; - } - - if (strcmp(tokens[t0 + 2], "offset") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "offset"); - return; - } - - if (softnic_parser_read_uint32(&p.match.lpm.key_offset, - tokens[t0 + 3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key_offset"); - return; - } - - if (strcmp(tokens[t0 + 4], "size") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "size"); - return; - } - - if (softnic_parser_read_uint32(&p.match.lpm.n_rules, - tokens[t0 + 5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "n_rules"); - return; - } - - t0 += 6; - } else if (strcmp(tokens[t0], "stub") == 0) { - p.match_type = TABLE_STUB; - - t0 += 1; - } else { - snprintf(out, out_size, MSG_ARG_INVALID, tokens[0]); - return; - } - - if (n_tokens > t0 && - (strcmp(tokens[t0], "action") == 0)) { - if (n_tokens < t0 + 2) { - snprintf(out, out_size, MSG_ARG_MISMATCH, "action"); - return; - } - - strlcpy(p.action_profile_name, tokens[t0 + 1], - sizeof(p.action_profile_name)); - - t0 += 2; - } - - if (n_tokens > t0) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - status = softnic_pipeline_table_create(softnic, pipeline_name, &p); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline port in table - */ -static void -cmd_pipeline_port_in_table(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - char *pipeline_name; - uint32_t port_id, table_id; - int status; - - if (n_tokens != 7) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (strcmp(tokens[3], "in") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "in"); - return; - } - - if (softnic_parser_read_uint32(&port_id, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port_id"); - return; - } - - if (strcmp(tokens[5], "table") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "table"); - return; - } - - if (softnic_parser_read_uint32(&table_id, tokens[6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "table_id"); - return; - } - - status = softnic_pipeline_port_in_connect_to_table(softnic, - pipeline_name, - port_id, - table_id); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline port in stats read [clear] - */ - -#define MSG_PIPELINE_PORT_IN_STATS \ - "Pkts in: %" PRIu64 "\n" \ - "Pkts dropped by AH: %" PRIu64 "\n" \ - "Pkts dropped by other: %" PRIu64 "\n" - -static void -cmd_pipeline_port_in_stats(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct rte_pipeline_port_in_stats stats; - char *pipeline_name; - uint32_t port_id; - int clear, status; - - if (n_tokens != 7 && - n_tokens != 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (strcmp(tokens[3], "in") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "in"); - return; - } - - if (softnic_parser_read_uint32(&port_id, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port_id"); - return; - } - - if (strcmp(tokens[5], "stats") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "stats"); - return; - } - - if (strcmp(tokens[6], "read") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "read"); - return; - } - - clear = 0; - if (n_tokens == 8) { - if (strcmp(tokens[7], "clear") != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "clear"); - return; - } - - clear = 1; - } - - status = softnic_pipeline_port_in_stats_read(softnic, - pipeline_name, - port_id, - &stats, - clear); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } - - snprintf(out, out_size, MSG_PIPELINE_PORT_IN_STATS, - stats.stats.n_pkts_in, - stats.n_pkts_dropped_by_ah, - stats.stats.n_pkts_drop); -} - -/** - * pipeline port in enable - */ -static void -cmd_softnic_pipeline_port_in_enable(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - char *pipeline_name; - uint32_t port_id; - int status; - - if (n_tokens != 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (strcmp(tokens[3], "in") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "in"); - return; - } - - if (softnic_parser_read_uint32(&port_id, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port_id"); - return; - } - - if (strcmp(tokens[5], "enable") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "enable"); - return; - } - - status = softnic_pipeline_port_in_enable(softnic, pipeline_name, port_id); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline port in disable - */ -static void -cmd_softnic_pipeline_port_in_disable(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - char *pipeline_name; - uint32_t port_id; - int status; - - if (n_tokens != 6) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (strcmp(tokens[3], "in") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "in"); - return; - } - - if (softnic_parser_read_uint32(&port_id, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port_id"); - return; - } - - if (strcmp(tokens[5], "disable") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "disable"); - return; - } - - status = softnic_pipeline_port_in_disable(softnic, pipeline_name, port_id); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } -} - -/** - * pipeline port out stats read [clear] - */ -#define MSG_PIPELINE_PORT_OUT_STATS \ - "Pkts in: %" PRIu64 "\n" \ - "Pkts dropped by AH: %" PRIu64 "\n" \ - "Pkts dropped by other: %" PRIu64 "\n" - -static void -cmd_pipeline_port_out_stats(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct rte_pipeline_port_out_stats stats; - char *pipeline_name; - uint32_t port_id; - int clear, status; - - if (n_tokens != 7 && - n_tokens != 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "port") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (strcmp(tokens[3], "out") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "out"); - return; - } - - if (softnic_parser_read_uint32(&port_id, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "port_id"); - return; - } - - if (strcmp(tokens[5], "stats") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "stats"); - return; - } - - if (strcmp(tokens[6], "read") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "read"); - return; - } - - clear = 0; - if (n_tokens == 8) { - if (strcmp(tokens[7], "clear") != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "clear"); - return; - } - - clear = 1; - } - - status = softnic_pipeline_port_out_stats_read(softnic, - pipeline_name, - port_id, - &stats, - clear); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } - - snprintf(out, out_size, MSG_PIPELINE_PORT_OUT_STATS, - stats.stats.n_pkts_in, - stats.n_pkts_dropped_by_ah, - stats.stats.n_pkts_drop); -} - -/** - * pipeline table stats read [clear] - */ -#define MSG_PIPELINE_TABLE_STATS \ - "Pkts in: %" PRIu64 "\n" \ - "Pkts in with lookup miss: %" PRIu64 "\n" \ - "Pkts in with lookup hit dropped by AH: %" PRIu64 "\n" \ - "Pkts in with lookup hit dropped by others: %" PRIu64 "\n" \ - "Pkts in with lookup miss dropped by AH: %" PRIu64 "\n" \ - "Pkts in with lookup miss dropped by others: %" PRIu64 "\n" - -static void -cmd_pipeline_table_stats(struct pmd_internals *softnic, - char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size) -{ - struct rte_pipeline_table_stats stats; - char *pipeline_name; - uint32_t table_id; - int clear, status; - - if (n_tokens != 6 && - n_tokens != 7) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return; - } - - pipeline_name = tokens[1]; - - if (strcmp(tokens[2], "table") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "port"); - return; - } - - if (softnic_parser_read_uint32(&table_id, tokens[3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "table_id"); - return; - } - - if (strcmp(tokens[4], "stats") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "stats"); - return; - } - - if (strcmp(tokens[5], "read") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "read"); - return; - } - - clear = 0; - if (n_tokens == 7) { - if (strcmp(tokens[6], "clear") != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "clear"); - return; - } - - clear = 1; - } - - status = softnic_pipeline_table_stats_read(softnic, - pipeline_name, - table_id, - &stats, - clear); - if (status) { - snprintf(out, out_size, MSG_CMD_FAIL, tokens[0]); - return; - } - - snprintf(out, out_size, MSG_PIPELINE_TABLE_STATS, - stats.stats.n_pkts_in, - stats.stats.n_pkts_lookup_miss, - stats.n_pkts_dropped_by_lkp_hit_ah, - stats.n_pkts_dropped_lkp_hit, - stats.n_pkts_dropped_by_lkp_miss_ah, - stats.n_pkts_dropped_lkp_miss); -} - -/** - * ::= - * - * match - * acl - * priority - * ipv4 | ipv6 - * - * | array - * | hash - * raw - * | ipv4_5tuple - * | ipv6_5tuple - * | ipv4_addr - * | ipv6_addr - * | qinq - * | lpm - * ipv4 | ipv6 - */ -struct pkt_key_qinq { - uint16_t ethertype_svlan; - uint16_t svlan; - uint16_t ethertype_cvlan; - uint16_t cvlan; -} __rte_packed; - -struct pkt_key_ipv4_5tuple { - uint8_t time_to_live; - uint8_t proto; - uint16_t hdr_checksum; - uint32_t sa; - uint32_t da; - uint16_t sp; - uint16_t dp; -} __rte_packed; - -struct pkt_key_ipv6_5tuple { - uint16_t payload_length; - uint8_t proto; - uint8_t hop_limit; - uint8_t sa[16]; - uint8_t da[16]; - uint16_t sp; - uint16_t dp; -} __rte_packed; - -struct pkt_key_ipv4_addr { - uint32_t addr; -} __rte_packed; - -struct pkt_key_ipv6_addr { - uint8_t addr[16]; -} __rte_packed; - -static uint32_t -parse_match(char **tokens, - uint32_t n_tokens, - char *out, - size_t out_size, - struct softnic_table_rule_match *m) -{ - memset(m, 0, sizeof(*m)); - - if (n_tokens < 2) - return 0; - - if (strcmp(tokens[0], "match") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "match"); - return 0; - } - - if (strcmp(tokens[1], "acl") == 0) { - if (n_tokens < 14) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return 0; - } - - m->match_type = TABLE_ACL; - - if (strcmp(tokens[2], "priority") != 0) { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, "priority"); - return 0; - } - - if (softnic_parser_read_uint32(&m->match.acl.priority, - tokens[3]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "priority"); - return 0; - } - - if (strcmp(tokens[4], "ipv4") == 0) { - struct in_addr saddr, daddr; - - m->match.acl.ip_version = 1; - - if (softnic_parse_ipv4_addr(tokens[5], &saddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sa"); - return 0; - } - m->match.acl.ipv4.sa = rte_be_to_cpu_32(saddr.s_addr); - - if (softnic_parse_ipv4_addr(tokens[7], &daddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "da"); - return 0; - } - m->match.acl.ipv4.da = rte_be_to_cpu_32(daddr.s_addr); - } else if (strcmp(tokens[4], "ipv6") == 0) { - struct in6_addr saddr, daddr; - - m->match.acl.ip_version = 0; - - if (softnic_parse_ipv6_addr(tokens[5], &saddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sa"); - return 0; - } - memcpy(m->match.acl.ipv6.sa, saddr.s6_addr, 16); - - if (softnic_parse_ipv6_addr(tokens[7], &daddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "da"); - return 0; - } - memcpy(m->match.acl.ipv6.da, daddr.s6_addr, 16); - } else { - snprintf(out, out_size, MSG_ARG_NOT_FOUND, - "ipv4 or ipv6"); - return 0; - } - - if (softnic_parser_read_uint32(&m->match.acl.sa_depth, - tokens[6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sa_depth"); - return 0; - } - - if (softnic_parser_read_uint32(&m->match.acl.da_depth, - tokens[8]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "da_depth"); - return 0; - } - - if (softnic_parser_read_uint16(&m->match.acl.sp0, tokens[9]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sp0"); - return 0; - } - - if (softnic_parser_read_uint16(&m->match.acl.sp1, tokens[10]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sp1"); - return 0; - } - - if (softnic_parser_read_uint16(&m->match.acl.dp0, tokens[11]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "dp0"); - return 0; - } - - if (softnic_parser_read_uint16(&m->match.acl.dp1, tokens[12]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "dp1"); - return 0; - } - - if (softnic_parser_read_uint8(&m->match.acl.proto, tokens[13]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "proto"); - return 0; - } - - m->match.acl.proto_mask = 0xff; - - return 14; - } /* acl */ - - if (strcmp(tokens[1], "array") == 0) { - if (n_tokens < 3) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return 0; - } - - m->match_type = TABLE_ARRAY; - - if (softnic_parser_read_uint32(&m->match.array.pos, tokens[2]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "pos"); - return 0; - } - - return 3; - } /* array */ - - if (strcmp(tokens[1], "hash") == 0) { - if (n_tokens < 3) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return 0; - } - - m->match_type = TABLE_HASH; - - if (strcmp(tokens[2], "raw") == 0) { - uint32_t key_size = TABLE_RULE_MATCH_SIZE_MAX; - - if (n_tokens < 4) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - tokens[0]); - return 0; - } - - if (softnic_parse_hex_string(tokens[3], - m->match.hash.key, &key_size) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "key"); - return 0; - } - - return 4; - } /* hash raw */ - - if (strcmp(tokens[2], "ipv4_5tuple") == 0) { - struct pkt_key_ipv4_5tuple *ipv4 = - (struct pkt_key_ipv4_5tuple *)m->match.hash.key; - struct in_addr saddr, daddr; - uint16_t sp, dp; - uint8_t proto; - - if (n_tokens < 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - tokens[0]); - return 0; - } - - if (softnic_parse_ipv4_addr(tokens[3], &saddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sa"); - return 0; - } - - if (softnic_parse_ipv4_addr(tokens[4], &daddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "da"); - return 0; - } - - if (softnic_parser_read_uint16(&sp, tokens[5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sp"); - return 0; - } - - if (softnic_parser_read_uint16(&dp, tokens[6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "dp"); - return 0; - } - - if (softnic_parser_read_uint8(&proto, tokens[7]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "proto"); - return 0; - } - - ipv4->sa = saddr.s_addr; - ipv4->da = daddr.s_addr; - ipv4->sp = rte_cpu_to_be_16(sp); - ipv4->dp = rte_cpu_to_be_16(dp); - ipv4->proto = proto; - - return 8; - } /* hash ipv4_5tuple */ - - if (strcmp(tokens[2], "ipv6_5tuple") == 0) { - struct pkt_key_ipv6_5tuple *ipv6 = - (struct pkt_key_ipv6_5tuple *)m->match.hash.key; - struct in6_addr saddr, daddr; - uint16_t sp, dp; - uint8_t proto; - - if (n_tokens < 8) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - tokens[0]); - return 0; - } - - if (softnic_parse_ipv6_addr(tokens[3], &saddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sa"); - return 0; - } - - if (softnic_parse_ipv6_addr(tokens[4], &daddr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "da"); - return 0; - } - - if (softnic_parser_read_uint16(&sp, tokens[5]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "sp"); - return 0; - } - - if (softnic_parser_read_uint16(&dp, tokens[6]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "dp"); - return 0; - } - - if (softnic_parser_read_uint8(&proto, tokens[7]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "proto"); - return 0; - } - - memcpy(ipv6->sa, saddr.s6_addr, 16); - memcpy(ipv6->da, daddr.s6_addr, 16); - ipv6->sp = rte_cpu_to_be_16(sp); - ipv6->dp = rte_cpu_to_be_16(dp); - ipv6->proto = proto; - - return 8; - } /* hash ipv6_5tuple */ - - if (strcmp(tokens[2], "ipv4_addr") == 0) { - struct pkt_key_ipv4_addr *ipv4_addr = - (struct pkt_key_ipv4_addr *)m->match.hash.key; - struct in_addr addr; - - if (n_tokens < 4) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - tokens[0]); - return 0; - } - - if (softnic_parse_ipv4_addr(tokens[3], &addr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "addr"); - return 0; - } - - ipv4_addr->addr = addr.s_addr; - - return 4; - } /* hash ipv4_addr */ - - if (strcmp(tokens[2], "ipv6_addr") == 0) { - struct pkt_key_ipv6_addr *ipv6_addr = - (struct pkt_key_ipv6_addr *)m->match.hash.key; - struct in6_addr addr; - - if (n_tokens < 4) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - tokens[0]); - return 0; - } - - if (softnic_parse_ipv6_addr(tokens[3], &addr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "addr"); - return 0; - } - - memcpy(ipv6_addr->addr, addr.s6_addr, 16); - - return 4; - } /* hash ipv6_5tuple */ - - if (strcmp(tokens[2], "qinq") == 0) { - struct pkt_key_qinq *qinq = - (struct pkt_key_qinq *)m->match.hash.key; - uint16_t svlan, cvlan; - - if (n_tokens < 5) { - snprintf(out, out_size, MSG_ARG_MISMATCH, - tokens[0]); - return 0; - } - - if ((softnic_parser_read_uint16(&svlan, tokens[3]) != 0) || - svlan > 0xFFF) { - snprintf(out, out_size, MSG_ARG_INVALID, - "svlan"); - return 0; - } - - if ((softnic_parser_read_uint16(&cvlan, tokens[4]) != 0) || - cvlan > 0xFFF) { - snprintf(out, out_size, MSG_ARG_INVALID, - "cvlan"); - return 0; - } - - qinq->svlan = rte_cpu_to_be_16(svlan); - qinq->cvlan = rte_cpu_to_be_16(cvlan); - - return 5; - } /* hash qinq */ - - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return 0; - } /* hash */ - - if (strcmp(tokens[1], "lpm") == 0) { - if (n_tokens < 5) { - snprintf(out, out_size, MSG_ARG_MISMATCH, tokens[0]); - return 0; - } - - m->match_type = TABLE_LPM; - - if (strcmp(tokens[2], "ipv4") == 0) { - struct in_addr addr; - - m->match.lpm.ip_version = 1; - - if (softnic_parse_ipv4_addr(tokens[3], &addr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "addr"); - return 0; - } - - m->match.lpm.ipv4 = rte_be_to_cpu_32(addr.s_addr); - } else if (strcmp(tokens[2], "ipv6") == 0) { - struct in6_addr addr; - - m->match.lpm.ip_version = 0; - - if (softnic_parse_ipv6_addr(tokens[3], &addr) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, - "addr"); - return 0; - } - - memcpy(m->match.lpm.ipv6, addr.s6_addr, 16); - } else { - snprintf(out, out_size, MSG_ARG_MISMATCH, - "ipv4 or ipv6"); - return 0; - } - - if (softnic_parser_read_uint8(&m->match.lpm.depth, tokens[4]) != 0) { - snprintf(out, out_size, MSG_ARG_INVALID, "depth"); - return 0; - } - - return 5; - } /* lpm */ - - snprintf(out, out_size, MSG_ARG_MISMATCH, - "acl or array or hash or lpm"); - return 0; -} - -/** - * table_action ::= - * - * action - * fwd - * drop - * | port - * | meta - * | table - * [balance ... ] - * [meter - * tc0 meter policer g y r - * [tc1 meter policer g y r - * tc2 meter policer g y r - * tc3 meter policer g y r ]] - * [tm subport pipe ] - * [encap - * ether - * | vlan - * | qinq - * | qinq_pppoe - * | mpls unicast | multicast - * - * label0