From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mga12.intel.com (mga12.intel.com [192.55.52.136]) by dpdk.org (Postfix) with ESMTP id 266101BA5A for ; Thu, 10 May 2018 12:23:30 +0200 (CEST) X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga007.fm.intel.com ([10.253.24.52]) by fmsmga106.fm.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 10 May 2018 03:23:29 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.49,385,1520924400"; d="scan'208";a="38242539" Received: from sivswdev02.ir.intel.com (HELO localhost.localdomain) ([10.237.217.46]) by fmsmga007.fm.intel.com with ESMTP; 10 May 2018 03:23:29 -0700 From: Konstantin Ananyev To: dev@dpdk.org Cc: Konstantin Ananyev Date: Thu, 10 May 2018 11:23:08 +0100 Message-Id: <1525947791-24031-7-git-send-email-konstantin.ananyev@intel.com> X-Mailer: git-send-email 1.7.0.7 In-Reply-To: <1525437945-8207-2-git-send-email-konstantin.ananyev@intel.com> References: <1525437945-8207-2-git-send-email-konstantin.ananyev@intel.com> Subject: [dpdk-dev] [PATCH v6 6/9] testpmd: new commands to load/unload BPF filters X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.15 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 10 May 2018 10:23:30 -0000 Introduce new testpmd commands to load/unload RX/TX BPF-based filters. Signed-off-by: Konstantin Ananyev Acked-by: Ferruh Yigit --- app/test-pmd/Makefile | 1 + app/test-pmd/bpf_cmd.c | 175 ++++++++++++++++++++++++++++++++++++++++ app/test-pmd/bpf_cmd.h | 16 ++++ app/test-pmd/cmdline.c | 5 ++ app/test-pmd/meson.build | 4 + lib/librte_bpf/rte_bpf_ethdev.h | 10 +++ 6 files changed, 211 insertions(+) create mode 100644 app/test-pmd/bpf_cmd.c create mode 100644 app/test-pmd/bpf_cmd.h diff --git a/app/test-pmd/Makefile b/app/test-pmd/Makefile index 60ae9b9c1..a5a827bbd 100644 --- a/app/test-pmd/Makefile +++ b/app/test-pmd/Makefile @@ -33,6 +33,7 @@ SRCS-y += txonly.c SRCS-y += csumonly.c SRCS-y += icmpecho.c SRCS-$(CONFIG_RTE_LIBRTE_IEEE1588) += ieee1588fwd.c +SRCS-$(CONFIG_RTE_LIBRTE_BPF) += bpf_cmd.c ifeq ($(CONFIG_RTE_LIBRTE_PMD_SOFTNIC)$(CONFIG_RTE_LIBRTE_SCHED),yy) SRCS-y += tm.c diff --git a/app/test-pmd/bpf_cmd.c b/app/test-pmd/bpf_cmd.c new file mode 100644 index 000000000..584fad908 --- /dev/null +++ b/app/test-pmd/bpf_cmd.c @@ -0,0 +1,175 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2018 Intel Corporation + */ + +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include "testpmd.h" + +static const struct rte_bpf_xsym bpf_xsym[] = { + { + .name = RTE_STR(stdout), + .type = RTE_BPF_XTYPE_VAR, + .var = &stdout, + }, + { + .name = RTE_STR(rte_pktmbuf_dump), + .type = RTE_BPF_XTYPE_FUNC, + .func = (void *)rte_pktmbuf_dump, + }, +}; + +/* *** load BPF program *** */ +struct cmd_bpf_ld_result { + cmdline_fixed_string_t bpf; + cmdline_fixed_string_t dir; + uint8_t port; + uint16_t queue; + cmdline_fixed_string_t op; + cmdline_fixed_string_t flags; + cmdline_fixed_string_t prm; +}; + +static void +bpf_parse_flags(const char *str, struct rte_bpf_arg *arg, uint32_t *flags) +{ + uint32_t i, v; + + *flags = RTE_BPF_ETH_F_NONE; + arg->type = RTE_BPF_ARG_PTR; + arg->size = mbuf_data_size; + + for (i = 0; str[i] != 0; i++) { + v = toupper(str[i]); + if (v == 'J') + *flags |= RTE_BPF_ETH_F_JIT; + else if (v == 'M') { + arg->type = RTE_BPF_ARG_PTR_MBUF; + arg->size = sizeof(struct rte_mbuf); + arg->buf_size = mbuf_data_size; + } else if (v == '-') + continue; + else + printf("unknown flag: \'%c\'", v); + } +} + +static void cmd_operate_bpf_ld_parsed(void *parsed_result, + __attribute__((unused)) struct cmdline *cl, + __attribute__((unused)) void *data) +{ + int32_t rc; + uint32_t flags; + struct cmd_bpf_ld_result *res; + struct rte_bpf_prm prm; + const char *fname, *sname; + + res = parsed_result; + memset(&prm, 0, sizeof(prm)); + prm.xsym = bpf_xsym; + prm.nb_xsym = RTE_DIM(bpf_xsym); + + bpf_parse_flags(res->flags, &prm.prog_arg, &flags); + fname = res->prm; + sname = ".text"; + + if (strcmp(res->dir, "rx") == 0) { + rc = rte_bpf_eth_rx_elf_load(res->port, res->queue, &prm, + fname, sname, flags); + printf("%d:%s\n", rc, strerror(-rc)); + } else if (strcmp(res->dir, "tx") == 0) { + rc = rte_bpf_eth_tx_elf_load(res->port, res->queue, &prm, + fname, sname, flags); + printf("%d:%s\n", rc, strerror(-rc)); + } else + printf("invalid value: %s\n", res->dir); +} + +cmdline_parse_token_string_t cmd_load_bpf_start = + TOKEN_STRING_INITIALIZER(struct cmd_bpf_ld_result, + bpf, "bpf-load"); +cmdline_parse_token_string_t cmd_load_bpf_dir = + TOKEN_STRING_INITIALIZER(struct cmd_bpf_ld_result, + dir, "rx#tx"); +cmdline_parse_token_num_t cmd_load_bpf_port = + TOKEN_NUM_INITIALIZER(struct cmd_bpf_ld_result, port, UINT8); +cmdline_parse_token_num_t cmd_load_bpf_queue = + TOKEN_NUM_INITIALIZER(struct cmd_bpf_ld_result, queue, UINT16); +cmdline_parse_token_string_t cmd_load_bpf_flags = + TOKEN_STRING_INITIALIZER(struct cmd_bpf_ld_result, + flags, NULL); +cmdline_parse_token_string_t cmd_load_bpf_prm = + TOKEN_STRING_INITIALIZER(struct cmd_bpf_ld_result, + prm, NULL); + +cmdline_parse_inst_t cmd_operate_bpf_ld_parse = { + .f = cmd_operate_bpf_ld_parsed, + .data = NULL, + .help_str = "bpf-load rx|tx ", + .tokens = { + (void *)&cmd_load_bpf_start, + (void *)&cmd_load_bpf_dir, + (void *)&cmd_load_bpf_port, + (void *)&cmd_load_bpf_queue, + (void *)&cmd_load_bpf_flags, + (void *)&cmd_load_bpf_prm, + NULL, + }, +}; + +/* *** unload BPF program *** */ +struct cmd_bpf_unld_result { + cmdline_fixed_string_t bpf; + cmdline_fixed_string_t dir; + uint8_t port; + uint16_t queue; +}; + +static void cmd_operate_bpf_unld_parsed(void *parsed_result, + __attribute__((unused)) struct cmdline *cl, + __attribute__((unused)) void *data) +{ + struct cmd_bpf_unld_result *res; + + res = parsed_result; + + if (strcmp(res->dir, "rx") == 0) + rte_bpf_eth_rx_unload(res->port, res->queue); + else if (strcmp(res->dir, "tx") == 0) + rte_bpf_eth_tx_unload(res->port, res->queue); + else + printf("invalid value: %s\n", res->dir); +} + +cmdline_parse_token_string_t cmd_unload_bpf_start = + TOKEN_STRING_INITIALIZER(struct cmd_bpf_unld_result, + bpf, "bpf-unload"); +cmdline_parse_token_string_t cmd_unload_bpf_dir = + TOKEN_STRING_INITIALIZER(struct cmd_bpf_unld_result, + dir, "rx#tx"); +cmdline_parse_token_num_t cmd_unload_bpf_port = + TOKEN_NUM_INITIALIZER(struct cmd_bpf_unld_result, port, UINT8); +cmdline_parse_token_num_t cmd_unload_bpf_queue = + TOKEN_NUM_INITIALIZER(struct cmd_bpf_unld_result, queue, UINT16); + +cmdline_parse_inst_t cmd_operate_bpf_unld_parse = { + .f = cmd_operate_bpf_unld_parsed, + .data = NULL, + .help_str = "bpf-unload rx|tx ", + .tokens = { + (void *)&cmd_unload_bpf_start, + (void *)&cmd_unload_bpf_dir, + (void *)&cmd_unload_bpf_port, + (void *)&cmd_unload_bpf_queue, + NULL, + }, +}; diff --git a/app/test-pmd/bpf_cmd.h b/app/test-pmd/bpf_cmd.h new file mode 100644 index 000000000..5ee4c9f79 --- /dev/null +++ b/app/test-pmd/bpf_cmd.h @@ -0,0 +1,16 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2018 Intel Corporation + */ + +#ifndef _BPF_CMD_H_ +#define _BPF_CMD_H_ + +#ifdef RTE_LIBRTE_BPF + + /* BPF CLI */ +extern cmdline_parse_inst_t cmd_operate_bpf_ld_parse; +extern cmdline_parse_inst_t cmd_operate_bpf_unld_parse; + +#endif /* RTE_LIBRTE_BPF */ + +#endif /* _BPF_CMD_H_ */ diff --git a/app/test-pmd/cmdline.c b/app/test-pmd/cmdline.c index 961567070..5c4bf4e5b 100644 --- a/app/test-pmd/cmdline.c +++ b/app/test-pmd/cmdline.c @@ -75,6 +75,7 @@ #include "testpmd.h" #include "cmdline_mtr.h" #include "cmdline_tm.h" +#include "bpf_cmd.h" static struct cmdline *testpmd_cl; @@ -16695,6 +16696,10 @@ cmdline_parse_ctx_t main_ctx[] = { (cmdline_parse_inst_t *)&cmd_resume_port_tm_node, (cmdline_parse_inst_t *)&cmd_port_tm_hierarchy_commit, (cmdline_parse_inst_t *)&cmd_cfg_tunnel_udp_port, +#ifdef RTE_LIBRTE_BPF + (cmdline_parse_inst_t *)&cmd_operate_bpf_ld_parse, + (cmdline_parse_inst_t *)&cmd_operate_bpf_unld_parse, +#endif NULL, }; diff --git a/app/test-pmd/meson.build b/app/test-pmd/meson.build index b47537642..a51514b03 100644 --- a/app/test-pmd/meson.build +++ b/app/test-pmd/meson.build @@ -38,3 +38,7 @@ endif if dpdk_conf.has('RTE_LIBRTE_DPAA_PMD') deps += ['bus_dpaa', 'mempool_dpaa', 'pmd_dpaa'] endif +if dpdk_conf.has('RTE_LIBRTE_BPF') + sources += files('bpf_cmd.c') + deps += 'bpf' +endif diff --git a/lib/librte_bpf/rte_bpf_ethdev.h b/lib/librte_bpf/rte_bpf_ethdev.h index 4800bbdaa..b4d4d3b16 100644 --- a/lib/librte_bpf/rte_bpf_ethdev.h +++ b/lib/librte_bpf/rte_bpf_ethdev.h @@ -69,6 +69,11 @@ void rte_bpf_eth_tx_unload(uint16_t port, uint16_t queue); * Pathname for a ELF file. * @param sname * Name of the executable section within the file to load. + * @param prm + * Parameters used to create and initialise the BPF exeution context. + * @param flags + * Flags that define expected expected behavior of the loaded filter + * (i.e. jited/non-jited version to use). * @return * Zero on successful completion or negative error code otherwise. */ @@ -88,6 +93,11 @@ int rte_bpf_eth_rx_elf_load(uint16_t port, uint16_t queue, * Pathname for a ELF file. * @param sname * Name of the executable section within the file to load. + * @param prm + * Parameters used to create and initialise the BPF exeution context. + * @param flags + * Flags that define expected expected behavior of the loaded filter + * (i.e. jited/non-jited version to use). * @return * Zero on successful completion or negative error code otherwise. */ -- 2.13.6