From patchwork Tue Sep 19 16:04:42 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131640 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 6DB484260C; Tue, 19 Sep 2023 18:05:22 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 4EBD640633; Tue, 19 Sep 2023 18:05:22 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id B946940277 for ; Tue, 19 Sep 2023 18:05:20 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02F012050 for ; Tue, 19 Sep 2023 09:05:19 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=OSLmPwg4OV3ct4eK898u7lgWwEQyUgSlJ1Ohoveuxqw=; b=fmNeYyXcBQEaC3K/9+75n2xpeApuwgLe1YBdJ+MTNN5IEwxRgAZ+iDCay3S06AbMMjDv yi7Uf7fVcfkWMDlmupqfIXwehQjAfclJ/9ttL6zyhC8nvQKgiWizeRaNVQ5a/hpqxX3O zJlspGBq6EJXa8bKQjG0HPFR7CbTeFJBifUoM8pT7IeWClHAuE5E5lAVTgM3p/LAEqfA PSRJ0+I40k27duYkkDDWQS56NiLspnnLaL1Nwq3Qa3JE4l44x7eV8nRW2fSiDQCHhflw /7ymqreDc8LyqDFjjN9In42ATo4aap2u9FP+eReiLxJc08xGIThqwgcvj8iqc9cv14oD aA== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-2 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:19 -0700 Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:03 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:03 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 8A90D3F709C; Tue, 19 Sep 2023 09:05:02 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 01/14] app/graph: add application framework to read CLI Date: Tue, 19 Sep 2023 21:34:42 +0530 Message-ID: <20230919160455.1678716-1-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230908104907.4060511-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: eVV4-b7gdD0Tl5CFnuO8pVz3JEZDJPPc X-Proofpoint-GUID: eVV4-b7gdD0Tl5CFnuO8pVz3JEZDJPPc X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori It adds base framework to read a given .cli file as a command line parameter "-s". Example: # ./dpdk-graph -c 0xff -- -s ./app/graph/examples/dummy.cli Each .cli file will contain commands to configure different module like mempool, ethdev, lookup tables, graph etc. Command parsing is backed by commandline library. Each module needs to expose its supported commands & corresponding callback functions to commandline library to get them parsed. Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- v3..v4: - Addressed Nithin's review comments app/graph/cli.c | 113 ++++++++++++++++++++++++++++++++++++ app/graph/cli.h | 32 +++++++++++ app/graph/main.c | 127 +++++++++++++++++++++++++++++++++++++++++ app/graph/meson.build | 14 +++++ app/graph/module_api.h | 16 ++++++ app/meson.build | 1 + 6 files changed, 303 insertions(+) create mode 100644 app/graph/cli.c create mode 100644 app/graph/cli.h create mode 100644 app/graph/main.c create mode 100644 app/graph/meson.build create mode 100644 app/graph/module_api.h diff --git a/app/graph/cli.c b/app/graph/cli.c new file mode 100644 index 0000000000..473fa1635a --- /dev/null +++ b/app/graph/cli.c @@ -0,0 +1,113 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +#include "module_api.h" + +#define CMD_MAX_TOKENS 256 +#define MAX_LINE_SIZE 2048 + +cmdline_parse_ctx_t modules_ctx[] = { + NULL, +}; + +static struct cmdline *cl; + +static int +is_comment(char *in) +{ + if ((strlen(in) && index("!#%;", in[0])) || + (strncmp(in, "//", 2) == 0) || + (strncmp(in, "--", 2) == 0)) + return 1; + + return 0; +} + +void +cli_init(void) +{ + cl = cmdline_stdin_new(modules_ctx, ""); +} + +void +cli_exit(void) +{ + cmdline_stdin_exit(cl); +} + +void +cli_process(char *in, char *out, size_t out_size, __rte_unused void *obj) +{ + int rc; + + if (is_comment(in)) + return; + + rc = cmdline_parse(cl, in); + if (rc == CMDLINE_PARSE_AMBIGUOUS) + snprintf(out, out_size, MSG_CMD_FAIL, "Ambiguous command"); + else if (rc == CMDLINE_PARSE_NOMATCH) + snprintf(out, out_size, MSG_CMD_FAIL, "Command mismatch"); + else if (rc == CMDLINE_PARSE_BAD_ARGS) + snprintf(out, out_size, MSG_CMD_FAIL, "Bad arguments"); + + return; + +} + +int +cli_script_process(const char *file_name, size_t msg_in_len_max, size_t msg_out_len_max, void *obj) +{ + char *msg_in = NULL, *msg_out = NULL; + FILE *f = NULL; + + /* Check input arguments */ + if ((file_name == NULL) || (strlen(file_name) == 0) || (msg_in_len_max == 0) || + (msg_out_len_max == 0)) + return -EINVAL; + + msg_in = malloc(msg_in_len_max + 1); + msg_out = malloc(msg_out_len_max + 1); + if ((msg_in == NULL) || (msg_out == NULL)) { + free(msg_out); + free(msg_in); + return -ENOMEM; + } + + /* Open input file */ + f = fopen(file_name, "r"); + if (f == NULL) { + free(msg_out); + free(msg_in); + return -EIO; + } + + /* Read file */ + while (fgets(msg_in, msg_in_len_max, f) != NULL) { + msg_out[0] = 0; + + cli_process(msg_in, msg_out, msg_out_len_max, obj); + + if (strlen(msg_out)) + printf("%s", msg_out); + } + + /* Close file */ + fclose(f); + free(msg_out); + free(msg_in); + return 0; +} diff --git a/app/graph/cli.h b/app/graph/cli.h new file mode 100644 index 0000000000..652f948352 --- /dev/null +++ b/app/graph/cli.h @@ -0,0 +1,32 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_CLI_H +#define APP_GRAPH_CLI_H + +/* Macros */ +#define MSG_OUT_OF_MEMORY "Not enough memory.\n" +#define MSG_CMD_UNKNOWN "Unknown command \"%s\".\n" +#define MSG_CMD_UNIMPLEM "Command \"%s\" not implemented.\n" +#define MSG_ARG_NOT_ENOUGH "Not enough arguments for command \"%s\".\n" +#define MSG_ARG_TOO_MANY "Too many arguments for command \"%s\".\n" +#define MSG_ARG_MISMATCH "Wrong number of arguments for command \"%s\".\n" +#define MSG_ARG_NOT_FOUND "Argument \"%s\" not found.\n" +#define MSG_ARG_INVALID "Invalid value for argument \"%s\".\n" +#define MSG_FILE_ERR "Error in file \"%s\" at line %u.\n" +#define MSG_FILE_NOT_ENOUGH "Not enough rules in file \"%s\".\n" +#define MSG_CMD_FAIL "Command \"%s\" failed.\n" + +#define APP_CLI_CMD_NAME_SIZE 64 + +void cli_init(void); + +void cli_exit(void); + +void cli_process(char *in, char *out, size_t out_size, void *arg); + +int cli_script_process(const char *file_name, size_t msg_in_len_max, size_t msg_out_len_max, + void *arg); + +#endif diff --git a/app/graph/main.c b/app/graph/main.c new file mode 100644 index 0000000000..a4af1ec7e1 --- /dev/null +++ b/app/graph/main.c @@ -0,0 +1,127 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include "module_api.h" + +volatile bool force_quit; + +static const char usage[] = "%s EAL_ARGS -- -s SCRIPT " + "[--help]\n"; + +static struct app_params { + char *script_name; +} app = { + .script_name = NULL, +}; + +static void +signal_handler(int signum) +{ + if (signum == SIGINT || signum == SIGTERM) { + printf("\n\nSignal %d received, preparing to exit...\n", signum); + force_quit = true; + } +} + +static int +app_args_parse(int argc, char **argv) +{ + struct option lgopts[] = { + {"help", 0, 0, 'H'}, + }; + int s_present, n_args, i; + char *app_name = argv[0]; + int opt, option_index; + + /* Skip EAL input args */ + n_args = argc; + for (i = 0; i < n_args; i++) + if (strcmp(argv[i], "--") == 0) { + argc -= i; + argv += i; + break; + } + + if (i == n_args) + return 0; + + /* Parse args */ + s_present = 0; + + while ((opt = getopt_long(argc, argv, "s:", lgopts, &option_index)) != EOF) { + switch (opt) { + case 's': + if (s_present) { + printf("Error: Multiple -s arguments\n"); + return -1; + } + s_present = 1; + + if (!strlen(optarg)) { + printf("Error: Argument for -s not provided\n"); + return -1; + } + + app.script_name = strdup(optarg); + if (app.script_name == NULL) { + printf("Error: Not enough memory\n"); + return -1; + } + break; + + case 'H': + default: + printf(usage, app_name); + return -1; + } + } + optind = 1; /* reset getopt lib */ + + return 0; +} + +int +main(int argc, char **argv) +{ + int rc; + + /* Parse application arguments */ + rc = app_args_parse(argc, argv); + if (rc < 0) + return rc; + + /* EAL */ + rc = rte_eal_init(argc, argv); + if (rc < 0) { + printf("Error: EAL initialization failed (%d)\n", rc); + return rc; + }; + + force_quit = false; + signal(SIGINT, signal_handler); + signal(SIGTERM, signal_handler); + + cli_init(); + + /* Script */ + if (app.script_name) { + cli_script_process(app.script_name, 0, + 0, NULL); + } + + cli_exit(); + rte_eal_cleanup(); + return 0; +} \ No newline at end of file diff --git a/app/graph/meson.build b/app/graph/meson.build new file mode 100644 index 0000000000..87c4ce30a8 --- /dev/null +++ b/app/graph/meson.build @@ -0,0 +1,14 @@ +# SPDX-License-Identifier: BSD-3-Clause +# Copyright(c) 2023 Marvell. + +# override default name to drop the hyphen +name = 'graph' +if not build + subdir_done() +endif + +deps += ['bus_pci', 'graph', 'eal', 'lpm', 'ethdev', 'node', 'cmdline'] +sources = files( + 'cli.c', + 'main.c', +) diff --git a/app/graph/module_api.h b/app/graph/module_api.h new file mode 100644 index 0000000000..372aeae7e3 --- /dev/null +++ b/app/graph/module_api.h @@ -0,0 +1,16 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_MODULE_API_H +#define APP_GRAPH_MODULE_API_H + +#include +#include +#include "cli.h" +/* + * Externs + */ +extern volatile bool force_quit; + +#endif diff --git a/app/meson.build b/app/meson.build index e4bf5c531c..728c936383 100644 --- a/app/meson.build +++ b/app/meson.build @@ -17,6 +17,7 @@ endif apps = [ 'dumpcap', 'pdump', + 'graph', 'proc-info', 'test-acl', 'test-bbdev', From patchwork Tue Sep 19 16:04:43 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131641 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 10BAB4260C; Tue, 19 Sep 2023 18:05:28 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 628D740E64; Tue, 19 Sep 2023 18:05:24 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id E377B40E4A for ; Tue, 19 Sep 2023 18:05:22 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02I012050 for ; Tue, 19 Sep 2023 09:05:22 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=ZdXqmLNYvuv5fgt8q3hli/glpntV64SdSYdTWlKplkk=; b=CJ45sy91wzJ6kKvQxLtIhfWrC6KSPkrj1xhqKV64s1yfIRQod1kjm/l2QvxoDCsbjW+s ghLosxzikM3V0mY4VX00MnjeJJNq3hIxFagIN/DaCc580jL6rxmSiAA5aJK1Kpep64xF xgMjasfy0suufYirR47wtD4ZmTxbPJGUv9vUNdgUIutTpkavC/oqgyEAdqn3R4btdrYx mYNdR2Yr9EjG0Mym2WW80z/Pi60kNOl9fRbAc56lTBZ5/uVjaOH7amn4eiLyrW51rkL6 LE/Pz6GAr3EurRXrqAJAPum1txvrGlxRlKLWwXQ4x6nvYWQhiuty4/Xwor7acUsqC7AG gw== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-3 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:21 -0700 Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:05 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:05 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 631413F7099; Tue, 19 Sep 2023 09:05:04 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 02/14] app/graph: add telnet connectivity framework Date: Tue, 19 Sep 2023 21:34:43 +0530 Message-ID: <20230919160455.1678716-2-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: OrbaAhxlhrfQEelfG_k6gyexOLbY5lul X-Proofpoint-GUID: OrbaAhxlhrfQEelfG_k6gyexOLbY5lul X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori It adds framework to initate a telnet session with application. Some configurations and debug commands are exposed as runtime APIs. Those commands can be invoked using telnet session. Application initiates a telnet server with host address 0.0.0.0 and port number 8086 by default. To make it configurable, "-h" and "-p" options are provided. Using them user can pass host address and port number on which application will start telnet server. Using same host address and port number, telnet client can connect to application. Syntax to connect with application: # telnet Once session is connected, "graph> " prompt will be available. Example: # telnet 10.28.35.207 50000 Trying 10.28.35.207... Connected to 10.28.35.207. Escape character is '^]'. Welcome! graph> Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/conn.c | 284 +++++++++++++++++++++++++++++++++++++++++ app/graph/conn.h | 46 +++++++ app/graph/main.c | 75 ++++++++++- app/graph/meson.build | 1 + app/graph/module_api.h | 2 + 5 files changed, 403 insertions(+), 5 deletions(-) create mode 100644 app/graph/conn.c create mode 100644 app/graph/conn.h diff --git a/app/graph/conn.c b/app/graph/conn.c new file mode 100644 index 0000000000..dabc8deca2 --- /dev/null +++ b/app/graph/conn.c @@ -0,0 +1,284 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "module_api.h" + +#define MSG_CMD_TOO_LONG "Command too long." + +static int +data_event_handle(struct conn *conn, int fd_client) +{ + ssize_t len, i, rc = 0; + + /* Read input message */ + len = read(fd_client, conn->buf, conn->buf_size); + if (len == -1) { + if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) + return 0; + + return -1; + } + + if (len == 0) + return rc; + + /* Handle input messages */ + for (i = 0; i < len; i++) { + if (conn->buf[i] == '\n') { + size_t n; + + conn->msg_in[conn->msg_in_len] = 0; + conn->msg_out[0] = 0; + + conn->msg_handle(conn->msg_in, conn->msg_out, conn->msg_out_len_max, + conn->msg_handle_arg); + + n = strlen(conn->msg_out); + if (n) { + rc = write(fd_client, conn->msg_out, n); + if (rc == -1) + goto exit; + } + + conn->msg_in_len = 0; + } else if (conn->msg_in_len < conn->msg_in_len_max) { + conn->msg_in[conn->msg_in_len] = conn->buf[i]; + conn->msg_in_len++; + } else { + rc = write(fd_client, MSG_CMD_TOO_LONG, strlen(MSG_CMD_TOO_LONG)); + if (rc == -1) + goto exit; + + conn->msg_in_len = 0; + } + } + + /* Write prompt */ + rc = write(fd_client, conn->prompt, strlen(conn->prompt)); + rc = (rc == -1) ? -1 : 0; + +exit: + return rc; +} + +static int +control_event_handle(struct conn *conn, int fd_client) +{ + int rc; + + rc = epoll_ctl(conn->fd_client_group, EPOLL_CTL_DEL, fd_client, NULL); + if (rc == -1) + goto exit; + + rc = close(fd_client); + if (rc == -1) + goto exit; + + rc = 0; + +exit: + return rc; +} + +struct conn * +conn_init(struct conn_params *p) +{ + int fd_server, fd_client_group, rc; + struct sockaddr_in server_address; + struct conn *conn = NULL; + + memset(&server_address, 0, sizeof(server_address)); + + /* Check input arguments */ + if ((p == NULL) || (p->welcome == NULL) || (p->prompt == NULL) || (p->addr == NULL) || + (p->buf_size == 0) || (p->msg_in_len_max == 0) || (p->msg_out_len_max == 0) || + (p->msg_handle == NULL)) + goto exit; + + rc = inet_aton(p->addr, &server_address.sin_addr); + if (rc == 0) + goto exit; + + /* Memory allocation */ + conn = calloc(1, sizeof(struct conn)); + if (conn == NULL) + goto exit; + + conn->welcome = calloc(1, CONN_WELCOME_LEN_MAX + 1); + conn->prompt = calloc(1, CONN_PROMPT_LEN_MAX + 1); + conn->buf = calloc(1, p->buf_size); + conn->msg_in = calloc(1, p->msg_in_len_max + 1); + conn->msg_out = calloc(1, p->msg_out_len_max + 1); + + if ((conn->welcome == NULL) || (conn->prompt == NULL) || (conn->buf == NULL) || + (conn->msg_in == NULL) || (conn->msg_out == NULL)) { + conn_free(conn); + conn = NULL; + goto exit; + } + + /* Server socket */ + server_address.sin_family = AF_INET; + server_address.sin_port = htons(p->port); + + fd_server = socket(AF_INET, SOCK_STREAM | SOCK_NONBLOCK, 0); + if (fd_server == -1) { + conn_free(conn); + conn = NULL; + goto exit; + } + + rc = bind(fd_server, (struct sockaddr *)&server_address, sizeof(server_address)); + if (rc == -1) { + conn_free(conn); + close(fd_server); + conn = NULL; + goto exit; + } + + rc = listen(fd_server, 16); + if (rc == -1) { + conn_free(conn); + close(fd_server); + conn = NULL; + goto exit; + } + + /* Client group */ + fd_client_group = epoll_create(1); + if (fd_client_group == -1) { + conn_free(conn); + close(fd_server); + conn = NULL; + goto exit; + } + + /* Fill in */ + strncpy(conn->welcome, p->welcome, CONN_WELCOME_LEN_MAX); + strncpy(conn->prompt, p->prompt, CONN_PROMPT_LEN_MAX); + conn->buf_size = p->buf_size; + conn->msg_in_len_max = p->msg_in_len_max; + conn->msg_out_len_max = p->msg_out_len_max; + conn->msg_in_len = 0; + conn->fd_server = fd_server; + conn->fd_client_group = fd_client_group; + conn->msg_handle = p->msg_handle; + conn->msg_handle_arg = p->msg_handle_arg; + +exit: + return conn; +} + +void +conn_free(struct conn *conn) +{ + if (conn == NULL) + return; + + if (conn->fd_client_group) + close(conn->fd_client_group); + + if (conn->fd_server) + close(conn->fd_server); + + free(conn->msg_out); + free(conn->msg_in); + free(conn->prompt); + free(conn->welcome); + free(conn); +} + +int +conn_req_poll(struct conn *conn) +{ + struct sockaddr_in client_address; + socklen_t client_address_length; + struct epoll_event event; + int fd_client, rc; + + /* Check input arguments */ + if (conn == NULL) + return -1; + + /* Server socket */ + client_address_length = sizeof(client_address); + fd_client = accept4(conn->fd_server, (struct sockaddr *)&client_address, + &client_address_length, SOCK_NONBLOCK); + if (fd_client == -1) { + if ((errno == EAGAIN) || (errno == EWOULDBLOCK)) + return 0; + + return -1; + } + + /* Client group */ + event.events = EPOLLIN | EPOLLRDHUP | EPOLLHUP; + event.data.fd = fd_client; + + rc = epoll_ctl(conn->fd_client_group, EPOLL_CTL_ADD, fd_client, &event); + if (rc == -1) { + close(fd_client); + goto exit; + } + + /* Client */ + rc = write(fd_client, conn->welcome, strlen(conn->welcome)); + if (rc == -1) { + close(fd_client); + goto exit; + } + + rc = write(fd_client, conn->prompt, strlen(conn->prompt)); + if (rc == -1) { + close(fd_client); + goto exit; + } + + rc = 0; + +exit: + return rc; +} + +int +conn_msg_poll(struct conn *conn) +{ + int fd_client, rc, rc_data = 0, rc_control = 0; + struct epoll_event event; + + /* Check input arguments */ + if (conn == NULL) + return -1; + + /* Client group */ + rc = epoll_wait(conn->fd_client_group, &event, 1, 0); + if ((rc == -1) || rc == 0) + return rc; + + fd_client = event.data.fd; + + /* Data available */ + if (event.events & EPOLLIN) + rc_data = data_event_handle(conn, fd_client); + + /* Control events */ + if (event.events & (EPOLLRDHUP | EPOLLERR | EPOLLHUP)) + rc_control = control_event_handle(conn, fd_client); + + if (rc_data || rc_control) + return -1; + + return 0; +} diff --git a/app/graph/conn.h b/app/graph/conn.h new file mode 100644 index 0000000000..770964cf4c --- /dev/null +++ b/app/graph/conn.h @@ -0,0 +1,46 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_CONN_H +#define APP_GRAPH_CONN_H + +#define CONN_WELCOME_LEN_MAX 1024 +#define CONN_PROMPT_LEN_MAX 16 + +typedef void (*conn_msg_handle_t)(char *msg_in, char *msg_out, size_t msg_out_len_max, void *arg); + +struct conn { + char *welcome; + char *prompt; + char *buf; + char *msg_in; + char *msg_out; + size_t buf_size; + size_t msg_in_len_max; + size_t msg_out_len_max; + size_t msg_in_len; + int fd_server; + int fd_client_group; + conn_msg_handle_t msg_handle; + void *msg_handle_arg; +}; + +struct conn_params { + const char *welcome; + const char *prompt; + const char *addr; + uint16_t port; + size_t buf_size; + size_t msg_in_len_max; + size_t msg_out_len_max; + conn_msg_handle_t msg_handle; + void *msg_handle_arg; +}; + +struct conn *conn_init(struct conn_params *p); +void conn_free(struct conn *conn); +int conn_req_poll(struct conn *conn); +int conn_msg_poll(struct conn *conn); + +#endif diff --git a/app/graph/main.c b/app/graph/main.c index a4af1ec7e1..79575fa2a6 100644 --- a/app/graph/main.c +++ b/app/graph/main.c @@ -16,13 +16,26 @@ #include "module_api.h" volatile bool force_quit; +struct conn *conn; -static const char usage[] = "%s EAL_ARGS -- -s SCRIPT " +static const char usage[] = "%s EAL_ARGS -- -s SCRIPT [-h HOST] [-p PORT] " "[--help]\n"; static struct app_params { + struct conn_params conn; char *script_name; } app = { + .conn = { + .welcome = "\nWelcome!\n\n", + .prompt = "graph> ", + .addr = "0.0.0.0", + .port = 8086, + .buf_size = 1024 * 1024, + .msg_in_len_max = 1024, + .msg_out_len_max = 1024 * 1024, + .msg_handle = cli_process, + .msg_handle_arg = NULL, /* set later. */ + }, .script_name = NULL, }; @@ -41,7 +54,7 @@ app_args_parse(int argc, char **argv) struct option lgopts[] = { {"help", 0, 0, 'H'}, }; - int s_present, n_args, i; + int h_present, p_present, s_present, n_args, i; char *app_name = argv[0]; int opt, option_index; @@ -58,10 +71,46 @@ app_args_parse(int argc, char **argv) return 0; /* Parse args */ + h_present = 0; + p_present = 0; s_present = 0; - while ((opt = getopt_long(argc, argv, "s:", lgopts, &option_index)) != EOF) { + while ((opt = getopt_long(argc, argv, "h:p:s:", lgopts, &option_index)) != EOF) { switch (opt) { + case 'h': + if (h_present) { + printf("Error: Multiple -h arguments\n"); + return -1; + } + h_present = 1; + + if (!strlen(optarg)) { + printf("Error: Argument for -h not provided\n"); + return -1; + } + + app.conn.addr = strdup(optarg); + if (app.conn.addr == NULL) { + printf("Error: Not enough memory\n"); + return -1; + } + break; + + case 'p': + if (p_present) { + printf("Error: Multiple -p arguments\n"); + return -1; + } + p_present = 1; + + if (!strlen(optarg)) { + printf("Error: Argument for -p not provided\n"); + return -1; + } + + app.conn.port = (uint16_t)strtoul(optarg, NULL, 10); + break; + case 's': if (s_present) { printf("Error: Multiple -s arguments\n"); @@ -117,10 +166,26 @@ main(int argc, char **argv) /* Script */ if (app.script_name) { - cli_script_process(app.script_name, 0, - 0, NULL); + cli_script_process(app.script_name, app.conn.msg_in_len_max, + app.conn.msg_out_len_max, NULL); + } + + /* Connectivity */ + app.conn.msg_handle_arg = NULL; + conn = conn_init(&app.conn); + if (!conn) { + printf("Error: Connectivity initialization failed\n"); + return -1; + }; + + /* Dispatch loop */ + while (!force_quit) { + conn_req_poll(conn); + + conn_msg_poll(conn); } + conn_free(conn); cli_exit(); rte_eal_cleanup(); return 0; diff --git a/app/graph/meson.build b/app/graph/meson.build index 87c4ce30a8..7e1ab0a214 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -10,5 +10,6 @@ endif deps += ['bus_pci', 'graph', 'eal', 'lpm', 'ethdev', 'node', 'cmdline'] sources = files( 'cli.c', + 'conn.c', 'main.c', ) diff --git a/app/graph/module_api.h b/app/graph/module_api.h index 372aeae7e3..b927de9470 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -7,7 +7,9 @@ #include #include + #include "cli.h" +#include "conn.h" /* * Externs */ From patchwork Tue Sep 19 16:04:44 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131642 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 6EB4E4260C; Tue, 19 Sep 2023 18:05:37 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id B8B4F40EE4; Tue, 19 Sep 2023 18:05:27 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id BBF4240E64 for ; Tue, 19 Sep 2023 18:05:23 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02K012050 for ; Tue, 19 Sep 2023 09:05:22 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=MqAdiW6fwUKlP3oWw4/ShTU4xBCMBOL0BqoMaCMdPkU=; b=IgVO88WxOeLm6G9cV56DJQ1OQfFWjx2XzDStv+VZzh3IIoRS/HRtTj9YnUpyMWliUvdL avs3SEbSGdsqWPbxEzgOJrClwggDxhhz8aFfbe0RZKLJshxeS6lEY8pEhDYWuGqQlYRe aqHzSl9DRRs6+n/vrK4FzbDzERYCae7pSeiDNbsI7pHpdY+Cu+6uw78UHImNBuiqBS4x 0VyeuFo61xWL2/Q30c8B64JXn6mvsomweqBoTSCvkrUNVJMIdtBCUfjZPuvep2Me8Tuf tLPgZtEXTGSfcNhPrcUEUrA1w6iFeusH+6rGfCUZcTzn6dNyeUz8XqhjO6N6R3po7u95 cg== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-4 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:22 -0700 Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:07 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:07 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 3EDBD3F709B; Tue, 19 Sep 2023 09:05:06 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 03/14] app/graph: add parser utility APIs Date: Tue, 19 Sep 2023 21:34:44 +0530 Message-ID: <20230919160455.1678716-3-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: IiIgTCm_wC_6x87ON7mjQjl6hivaEQYX X-Proofpoint-GUID: IiIgTCm_wC_6x87ON7mjQjl6hivaEQYX X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori It adds some helper functions to parse IPv4, IPv6 and MAC addresses string into respective datatype. Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/meson.build | 1 + app/graph/module_api.h | 1 + app/graph/utils.c | 156 +++++++++++++++++++++++++++++++++++++++++ app/graph/utils.h | 14 ++++ 4 files changed, 172 insertions(+) create mode 100644 app/graph/utils.c create mode 100644 app/graph/utils.h diff --git a/app/graph/meson.build b/app/graph/meson.build index 7e1ab0a214..ed3bcb1567 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -12,4 +12,5 @@ sources = files( 'cli.c', 'conn.c', 'main.c', + 'utils.c', ) diff --git a/app/graph/module_api.h b/app/graph/module_api.h index b927de9470..acf63d15fa 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -10,6 +10,7 @@ #include "cli.h" #include "conn.h" +#include "utils.h" /* * Externs */ diff --git a/app/graph/utils.c b/app/graph/utils.c new file mode 100644 index 0000000000..c7b6ae83cf --- /dev/null +++ b/app/graph/utils.c @@ -0,0 +1,156 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include +#include +#include + +#include + +#include "module_api.h" + +#define white_spaces_skip(pos) \ +({ \ + __typeof__(pos) _p = (pos); \ + for ( ; isspace(*_p); _p++) \ + ; \ + _p; \ +}) + +static void +hex_string_to_uint64(uint64_t *dst, const char *hexs) +{ + char buf[2] = {0}; + uint8_t shift = 4; + int iter = 0; + char c; + + while ((c = *hexs++)) { + buf[0] = c; + *dst |= (strtol(buf, NULL, 16) << shift); + shift -= 4; + iter++; + if (iter == 2) { + iter = 0; + shift = 4; + dst++; + } + } +} + +int +parser_uint64_read(uint64_t *value, const char *p) +{ + char *next; + uint64_t val; + + p = white_spaces_skip(p); + if (!isdigit(*p)) + return -EINVAL; + + val = strtoul(p, &next, 0); + if (p == next) + return -EINVAL; + + p = next; + switch (*p) { + case 'T': + val *= 1024ULL; + /* fall through */ + case 'G': + val *= 1024ULL; + /* fall through */ + case 'M': + val *= 1024ULL; + /* fall through */ + case 'k': + case 'K': + val *= 1024ULL; + p++; + break; + } + + p = white_spaces_skip(p); + if (*p != '\0') + return -EINVAL; + + *value = val; + return 0; +} + +int +parser_uint32_read(uint32_t *value, const char *p) +{ + uint64_t val = 0; + int rc = parser_uint64_read(&val, p); + + if (rc < 0) + return rc; + + if (val > UINT32_MAX) + return -ERANGE; + + *value = val; + return 0; +} + +int +parser_ip4_read(uint32_t *value, char *p) +{ + uint8_t shift = 24; + uint32_t ip = 0; + char *token; + + token = strtok(p, "."); + while (token != NULL) { + ip |= (((uint32_t)strtoul(token, NULL, 10)) << shift); + token = strtok(NULL, "."); + shift -= 8; + } + + *value = ip; + + return 0; +} + +int +parser_ip6_read(uint8_t *value, char *p) +{ + uint64_t val = 0; + char *token; + + token = strtok(p, ":"); + while (token != NULL) { + hex_string_to_uint64(&val, token); + *value = val; + token = strtok(NULL, ":"); + value++; + val = 0; + } + + return 0; +} + +int +parser_mac_read(uint64_t *value, char *p) +{ + uint64_t mac = 0, val = 0; + uint8_t shift = 40; + char *token; + + token = strtok(p, ":"); + while (token != NULL) { + hex_string_to_uint64(&val, token); + mac |= val << shift; + token = strtok(NULL, ":"); + shift -= 8; + val = 0; + } + + *value = mac; + + return 0; +} diff --git a/app/graph/utils.h b/app/graph/utils.h new file mode 100644 index 0000000000..0ebb5de55a --- /dev/null +++ b/app/graph/utils.h @@ -0,0 +1,14 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_UTILS_H +#define APP_GRAPH_UTILS_H + +int parser_uint64_read(uint64_t *value, const char *p); +int parser_uint32_read(uint32_t *value, const char *p); +int parser_ip4_read(uint32_t *value, char *p); +int parser_ip6_read(uint8_t *value, char *p); +int parser_mac_read(uint64_t *value, char *p); + +#endif From patchwork Tue Sep 19 16:04:45 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131643 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 8FD584260C; Tue, 19 Sep 2023 18:05:45 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id EEA0540FDE; Tue, 19 Sep 2023 18:05:28 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id CDA0740EDB for ; Tue, 19 Sep 2023 18:05:24 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02L012050 for ; Tue, 19 Sep 2023 09:05:24 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=IFwnVXT+eMyJEXuAsaPUYnj0NZsU612n6Qh/uAQzF7o=; b=jH0XtTBxQt3scZUi5m1U5w+kW2eVN2VLuDXYnf2wRVz0MOPkxGNaEWwmdXkYpiuaZK2U rwjs9IYU2x/yPXUjIqm3H7NUDcokBZEhelRXbAZ1/xG+yefjOrJatBZzZPCfJC99i0Nd ly5YVSxthySBztI8WxfObbky5J4b5sM6vJQYfiW4tgCo+iUKXhACiRWBOApgoqsWROhl ayrHeIRcohk2kzHUTv/31R381RXk5vrwqjmbiVNXZz/0/S2PdiI8uaXC1FfIY5eNy832 SSk9Q6hhZmy5TKAZ5/wt2cWhBqTlLIq3+kRcuQpoTmYWwahJssayiWPZEzetf9xs2aih cg== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-5 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:23 -0700 Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:09 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:09 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 182B53F7099; Tue, 19 Sep 2023 09:05:07 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 04/14] app/graph: add mempool command line interfaces Date: Tue, 19 Sep 2023 21:34:45 +0530 Message-ID: <20230919160455.1678716-4-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: p5lDBj1ERiXvTyrcpzsOnn4un2F4NePG X-Proofpoint-GUID: p5lDBj1ERiXvTyrcpzsOnn4un2F4NePG X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Rakesh Kudurumalla It adds mempool module which will be creating mempools. Following commands are exposed: - mempool size buffers \ cache numa - help mempool User will add this command in .cli file according to its need. Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/cli.c | 2 + app/graph/mempool.c | 140 +++++++++++++++++++++++++++++++++++++++ app/graph/mempool.h | 24 +++++++ app/graph/mempool_priv.h | 34 ++++++++++ app/graph/meson.build | 1 + app/graph/module_api.h | 2 + 6 files changed, 203 insertions(+) create mode 100644 app/graph/mempool.c create mode 100644 app/graph/mempool.h create mode 100644 app/graph/mempool_priv.h diff --git a/app/graph/cli.c b/app/graph/cli.c index 473fa1635a..c9f932517e 100644 --- a/app/graph/cli.c +++ b/app/graph/cli.c @@ -20,6 +20,8 @@ #define MAX_LINE_SIZE 2048 cmdline_parse_ctx_t modules_ctx[] = { + (cmdline_parse_inst_t *)&mempool_config_cmd_ctx, + (cmdline_parse_inst_t *)&mempool_help_cmd_ctx, NULL, }; diff --git a/app/graph/mempool.c b/app/graph/mempool.c new file mode 100644 index 0000000000..901f07f461 --- /dev/null +++ b/app/graph/mempool.c @@ -0,0 +1,140 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +#include "mempool_priv.h" +#include "module_api.h" + +static const char +cmd_mempool_help[] = "mempool size buffers " + "cache numa "; + +struct mempools mpconfig; + +int +mempool_process(struct mempool_config *config) +{ + struct rte_mempool *mp; + uint8_t nb_pools; + + nb_pools = mpconfig.nb_pools; + strcpy(mpconfig.config[nb_pools].name, config->name); + mpconfig.config[nb_pools].pool_size = config->pool_size; + mpconfig.config[nb_pools].buffer_size = config->buffer_size; + mpconfig.config[nb_pools].cache_size = config->cache_size; + mpconfig.config[nb_pools].numa_node = config->numa_node; + + mp = rte_pktmbuf_pool_create(config->name, config->pool_size, config->cache_size, + 64, config->buffer_size, config->numa_node); + if (!mp) + return -EINVAL; + + mpconfig.mp[nb_pools] = mp; + nb_pools++; + mpconfig.nb_pools = nb_pools; + + return 0; +} + +static void +cli_mempool_help(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + size_t len; + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, "\n%s\n%s\n", + "----------------------------- mempool command help -----------------------------", + cmd_mempool_help); + + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; +} + +static void +cli_mempool(void *parsed_result, __rte_unused struct cmdline *cl, __rte_unused void *data) +{ + struct mempool_config_cmd_tokens *res = parsed_result; + struct mempool_config config; + int rc = -EINVAL; + + + strcpy(config.name, res->name); + config.name[strlen(res->name)] = '\0'; + config.pool_size = res->nb_bufs; + config.buffer_size = res->buf_sz; + config.cache_size = res->cache_size; + config.numa_node = res->node; + + rc = mempool_process(&config); + if (rc < 0) + printf(MSG_CMD_FAIL, "mempool"); +} + +cmdline_parse_token_string_t mempool_config_add_mempool = + TOKEN_STRING_INITIALIZER(struct mempool_config_cmd_tokens, mempool, "mempool"); +cmdline_parse_token_string_t mempool_config_add_name = + TOKEN_STRING_INITIALIZER(struct mempool_config_cmd_tokens, name, NULL); +cmdline_parse_token_string_t mempool_config_add_size = + TOKEN_STRING_INITIALIZER(struct mempool_config_cmd_tokens, size, "size"); +cmdline_parse_token_num_t mempool_config_add_buf_sz = + TOKEN_NUM_INITIALIZER(struct mempool_config_cmd_tokens, buf_sz, RTE_UINT16); +cmdline_parse_token_string_t mempool_config_add_buffers = + TOKEN_STRING_INITIALIZER(struct mempool_config_cmd_tokens, buffers, "buffers"); +cmdline_parse_token_num_t mempool_config_add_nb_bufs = + TOKEN_NUM_INITIALIZER(struct mempool_config_cmd_tokens, nb_bufs, RTE_UINT16); +cmdline_parse_token_string_t mempool_config_add_cache = + TOKEN_STRING_INITIALIZER(struct mempool_config_cmd_tokens, cache, "cache"); +cmdline_parse_token_num_t mempool_config_add_cache_size = + TOKEN_NUM_INITIALIZER(struct mempool_config_cmd_tokens, cache_size, RTE_UINT16); +cmdline_parse_token_string_t mempool_config_add_numa = + TOKEN_STRING_INITIALIZER(struct mempool_config_cmd_tokens, numa, "numa"); +cmdline_parse_token_num_t mempool_config_add_node = + TOKEN_NUM_INITIALIZER(struct mempool_config_cmd_tokens, node, RTE_UINT16); + +cmdline_parse_inst_t mempool_config_cmd_ctx = { + .f = cli_mempool, + .data = NULL, + .help_str = cmd_mempool_help, + .tokens = { + (void *)&mempool_config_add_mempool, + (void *)&mempool_config_add_name, + (void *)&mempool_config_add_size, + (void *)&mempool_config_add_buf_sz, + (void *)&mempool_config_add_buffers, + (void *)&mempool_config_add_nb_bufs, + (void *)&mempool_config_add_cache, + (void *)&mempool_config_add_cache_size, + (void *)&mempool_config_add_numa, + (void *)&mempool_config_add_node, + NULL, + }, +}; + +cmdline_parse_token_string_t mempool_help_cmd = + TOKEN_STRING_INITIALIZER(struct mempool_help_cmd_tokens, help, "help"); +cmdline_parse_token_string_t mempool_help_mempool = + TOKEN_STRING_INITIALIZER(struct mempool_help_cmd_tokens, mempool, "mempool"); + +cmdline_parse_inst_t mempool_help_cmd_ctx = { + .f = cli_mempool_help, + .data = NULL, + .help_str = "", + .tokens = { + (void *)&mempool_help_cmd, + (void *)&mempool_help_mempool, + NULL, + }, +}; diff --git a/app/graph/mempool.h b/app/graph/mempool.h new file mode 100644 index 0000000000..0808c4259e --- /dev/null +++ b/app/graph/mempool.h @@ -0,0 +1,24 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_MEMPOOL_H +#define APP_GRAPH_MEMPOOL_H + +#include +#include + +struct mempool_config { + char name[RTE_MEMPOOL_NAMESIZE]; + int pool_size; + int cache_size; + int buffer_size; + int numa_node; +}; + +extern cmdline_parse_inst_t mempool_config_cmd_ctx; +extern cmdline_parse_inst_t mempool_help_cmd_ctx; + +int mempool_process(struct mempool_config *config); + +#endif diff --git a/app/graph/mempool_priv.h b/app/graph/mempool_priv.h new file mode 100644 index 0000000000..3ce64702a9 --- /dev/null +++ b/app/graph/mempool_priv.h @@ -0,0 +1,34 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_MEMPOOL_PRIV_H +#define APP_GRAPH_MEMPOOL_PRIV_H + +#include "mempool.h" + +struct mempool_config_cmd_tokens { + cmdline_fixed_string_t mempool; + cmdline_fixed_string_t size; + cmdline_fixed_string_t buffers; + cmdline_fixed_string_t cache; + cmdline_fixed_string_t numa; + cmdline_fixed_string_t name; + uint16_t buf_sz; + uint16_t nb_bufs; + uint16_t cache_size; + uint16_t node; +}; + +struct mempool_help_cmd_tokens { + cmdline_fixed_string_t help; + cmdline_fixed_string_t mempool; +}; + +struct mempools { + struct mempool_config config[RTE_MAX_ETHPORTS]; + struct rte_mempool *mp[RTE_MAX_ETHPORTS]; + uint8_t nb_pools; +}; + +#endif diff --git a/app/graph/meson.build b/app/graph/meson.build index ed3bcb1567..d35287be14 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -12,5 +12,6 @@ sources = files( 'cli.c', 'conn.c', 'main.c', + 'mempool.c', 'utils.c', ) diff --git a/app/graph/module_api.h b/app/graph/module_api.h index acf63d15fa..de154f5f93 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -10,10 +10,12 @@ #include "cli.h" #include "conn.h" +#include "mempool.h" #include "utils.h" /* * Externs */ extern volatile bool force_quit; +extern struct conn *conn; #endif From patchwork Tue Sep 19 16:04:46 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131644 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id E2F004260C; Tue, 19 Sep 2023 18:05:58 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 0D97D410F9; Tue, 19 Sep 2023 18:05:31 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id B24A540EE1 for ; Tue, 19 Sep 2023 18:05:26 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02M012050 for ; Tue, 19 Sep 2023 09:05:25 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=XTmEbzmmfc4jq6nwI0AJm48bRR6H36JyHZSU3TtX7Ww=; b=jboXSDAYxpOUWk+JlUeEoSX6K4QAVp3Bnbf/W0IwvkOV260810d1irfIhOQ5kiDOv+je rcE09W5HZgFXg78b007JfxyMES6MkVGwiVo3o5trZuC9vVU4spdO7HAWYXj71jkMq8Vh zoI7pVZFegGoBFgL5GrsMeuG3GKgDzLhTQl3gPwUlJjPbb3G1+NwZbQTgri+WwNdLeME mH4/8WdAnbmo5xq044Cr0FN75YqYfAnw+5U+zjghljpcIqgDirypPvS7h0xywBNWgoHg 0FfWUvehGt2h8AFknvpkiHsNHbiM5+R05t8Jhe6MshzrbuAoFxZj7L9BR+F9n8HS21OK 6w== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-7 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:25 -0700 Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:11 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:10 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id E6EBB3F709B; Tue, 19 Sep 2023 09:05:09 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 05/14] app/graph: add ethdev command line interfaces Date: Tue, 19 Sep 2023 21:34:46 +0530 Message-ID: <20230919160455.1678716-5-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: X8Z5raGrk6zDPmBafpNaRGhBhg5Dw1SM X-Proofpoint-GUID: X8Z5raGrk6zDPmBafpNaRGhBhg5Dw1SM X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori It adds ethdev module to configure ethernet devices. Following commands are exposed: - ethdev rxq txq - ethdev mtu - ethdev promiscuous - ethdev show - ethdev stats - ethdev ip4 addr add netmask - ethdev ip6 addr add netmask - help ethdev Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/cli.c | 8 + app/graph/ethdev.c | 882 ++++++++++++++++++++++++++++++++++++++++ app/graph/ethdev.h | 40 ++ app/graph/ethdev_priv.h | 112 +++++ app/graph/main.c | 3 +- app/graph/meson.build | 1 + app/graph/module_api.h | 1 + 7 files changed, 1046 insertions(+), 1 deletion(-) create mode 100644 app/graph/ethdev.c create mode 100644 app/graph/ethdev.h create mode 100644 app/graph/ethdev_priv.h diff --git a/app/graph/cli.c b/app/graph/cli.c index c9f932517e..c4b5cf3ce1 100644 --- a/app/graph/cli.c +++ b/app/graph/cli.c @@ -22,6 +22,14 @@ cmdline_parse_ctx_t modules_ctx[] = { (cmdline_parse_inst_t *)&mempool_config_cmd_ctx, (cmdline_parse_inst_t *)&mempool_help_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_show_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_stats_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_mtu_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_prom_mode_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_ip4_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_ip6_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_help_cmd_ctx, NULL, }; diff --git a/app/graph/ethdev.c b/app/graph/ethdev.c new file mode 100644 index 0000000000..81ad8c4757 --- /dev/null +++ b/app/graph/ethdev.c @@ -0,0 +1,882 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include "ethdev_priv.h" +#include "module_api.h" + +static const char +cmd_ethdev_mtu_help[] = "ethdev mtu "; + +static const char +cmd_ethdev_prom_mode_help[] = "ethdev promiscuous "; + +static const char +cmd_ethdev_help[] = "ethdev rxq txq "; +static const char +cmd_ethdev_show_help[] = "ethdev show"; + +static const char +cmd_ethdev_ip4_addr_help[] = "ethdev ip4 addr add netmask "; + +static const char +cmd_ethdev_ip6_addr_help[] = "ethdev ip6 addr add netmask "; + +static struct rte_eth_conf port_conf_default = { + .link_speeds = 0, + .rxmode = { + .mq_mode = RTE_ETH_MQ_RX_NONE, + .mtu = 9000 - (RTE_ETHER_HDR_LEN + RTE_ETHER_CRC_LEN), /* Jumbo frame MTU */ + }, + .rx_adv_conf = { + .rss_conf = { + .rss_key = NULL, + .rss_key_len = 40, + .rss_hf = 0, + }, + }, + .txmode = { + .mq_mode = RTE_ETH_MQ_TX_NONE, + }, + .lpbk_mode = 0, +}; + +uint32_t enabled_port_mask; +static struct ethdev_head eth_node = TAILQ_HEAD_INITIALIZER(eth_node); + + +static struct ethdev* +ethdev_port_by_id(uint16_t port_id) +{ + struct ethdev *port; + + TAILQ_FOREACH(port, ð_node, next) { + if (port->config.port_id == port_id) + return port; + } + return NULL; +} + +void * +ethdev_mempool_list_by_portid(uint16_t portid) +{ + struct ethdev *port; + + if (portid >= RTE_MAX_ETHPORTS) + return NULL; + + port = ethdev_port_by_id(portid); + if (port) + return &(port->config.rx.mp); + else + return NULL; +} + +int16_t +ethdev_portid_by_ip4(uint32_t ip, uint32_t mask) +{ + int portid = -EINVAL; + struct ethdev *port; + + TAILQ_FOREACH(port, ð_node, next) { + if (mask == 0) { + if ((port->ip4_addr.ip & port->ip4_addr.mask) == (ip & port->ip4_addr.mask)) + return port->config.port_id; + } else { + if ((port->ip4_addr.ip & port->ip4_addr.mask) == (ip & mask)) + return port->config.port_id; + } + } + + return portid; +} + +int16_t +ethdev_portid_by_ip6(uint8_t *ip, uint8_t *mask) +{ + int portid = -EINVAL; + struct ethdev *port; + int j; + + TAILQ_FOREACH(port, ð_node, next) { + for (j = 0; j < ETHDEV_IPV6_ADDR_LEN; j++) { + if (mask == NULL) { + if ((port->ip6_addr.ip[j] & port->ip6_addr.mask[j]) != + (ip[j] & port->ip6_addr.mask[j])) + break; + + } else { + if ((port->ip6_addr.ip[j] & port->ip6_addr.mask[j]) != + (ip[j] & mask[j])) + break; + } + } + if (j == ETHDEV_IPV6_ADDR_LEN) + return port->config.port_id; + } + + return portid; +} + +void +ethdev_list_clean(void) +{ + struct ethdev *port; + + while (!TAILQ_EMPTY(ð_node)) { + port = TAILQ_FIRST(ð_node); + TAILQ_REMOVE(ð_node, port, next); + } +} + +void +ethdev_stop(void) +{ + uint16_t portid; + int rc; + + RTE_ETH_FOREACH_DEV(portid) { + if ((enabled_port_mask & (1 << portid)) == 0) + continue; + printf("Closing port %d...", portid); + rc = rte_eth_dev_stop(portid); + if (rc != 0) + printf("Failed to stop port %u: %s\n", + portid, rte_strerror(-rc)); + rte_eth_dev_close(portid); + printf(" Done\n"); + } + + ethdev_list_clean(); + rte_eal_cleanup(); + printf("Bye...\n"); +} + +void +ethdev_start(void) +{ + uint16_t portid; + int rc; + + RTE_ETH_FOREACH_DEV(portid) + { + if ((enabled_port_mask & (1 << portid)) == 0) + continue; + + rc = rte_eth_dev_start(portid); + if (rc < 0) + rte_exit(EXIT_FAILURE, "rte_eth_dev_start: err=%d, port=%d\n", rc, portid); + } +} + + +static int +ethdev_show(const char *name) +{ + uint16_t mtu = 0, port_id = 0; + struct rte_eth_dev_info info; + struct rte_eth_stats stats; + struct rte_ether_addr addr; + struct rte_eth_link link; + uint32_t length; + int rc; + + rc = rte_eth_dev_get_port_by_name(name, &port_id); + if (rc < 0) + return rc; + + rte_eth_dev_info_get(port_id, &info); + rte_eth_stats_get(port_id, &stats); + rte_eth_macaddr_get(port_id, &addr); + rte_eth_link_get(port_id, &link); + rte_eth_dev_get_mtu(port_id, &mtu); + + length = strlen(conn->msg_out); + conn->msg_out += length; + snprintf(conn->msg_out, conn->msg_out_len_max, + "%s: flags=<%s> mtu %u\n" + "\tether " RTE_ETHER_ADDR_PRT_FMT " rxqueues %u txqueues %u\n" + "\tport# %u speed %s\n" + "\tRX packets %" PRIu64" bytes %" PRIu64"\n" + "\tRX errors %" PRIu64" missed %" PRIu64" no-mbuf %" PRIu64"\n" + "\tTX packets %" PRIu64" bytes %" PRIu64"\n" + "\tTX errors %" PRIu64"\n\n", + name, + link.link_status ? "UP" : "DOWN", + mtu, + RTE_ETHER_ADDR_BYTES(&addr), + info.nb_rx_queues, + info.nb_tx_queues, + port_id, + rte_eth_link_speed_to_str(link.link_speed), + stats.ipackets, + stats.ibytes, + stats.ierrors, + stats.imissed, + stats.rx_nombuf, + stats.opackets, + stats.obytes, + stats.oerrors); + + length = strlen(conn->msg_out); + conn->msg_out_len_max -= length; + return 0; +} + +static int +ethdev_ip4_addr_add(const char *name, struct ipv4_addr_config *config) +{ + struct ethdev *eth_hdl; + uint16_t portid = 0; + int rc; + + rc = rte_eth_dev_get_port_by_name(name, &portid); + if (rc < 0) + return rc; + + eth_hdl = ethdev_port_by_id(portid); + + if (eth_hdl) { + eth_hdl->ip4_addr.ip = config->ip; + eth_hdl->ip4_addr.mask = config->mask; + return 0; + } + + rc = -EINVAL; + return rc; +} + +static int +ethdev_ip6_addr_add(const char *name, struct ipv6_addr_config *config) +{ + struct ethdev *eth_hdl; + uint16_t portid = 0; + int rc, i; + + rc = rte_eth_dev_get_port_by_name(name, &portid); + if (rc < 0) + return rc; + + eth_hdl = ethdev_port_by_id(portid); + + if (eth_hdl) { + for (i = 0; i < ETHDEV_IPV6_ADDR_LEN; i++) { + eth_hdl->ip6_addr.ip[i] = config->ip[i]; + eth_hdl->ip6_addr.mask[i] = config->mask[i]; + } + return 0; + } + rc = -EINVAL; + return rc; +} + +static int +ethdev_prom_mode_config(const char *name, bool enable) +{ + struct ethdev *eth_hdl; + uint16_t portid = 0; + int rc; + + rc = rte_eth_dev_get_port_by_name(name, &portid); + if (rc < 0) + return rc; + + eth_hdl = ethdev_port_by_id(portid); + + if (eth_hdl) { + if (enable) + rc = rte_eth_promiscuous_enable(portid); + else + rc = rte_eth_promiscuous_disable(portid); + if (rc < 0) + return rc; + + eth_hdl->config.promiscuous = enable; + return 0; + } + + rc = -EINVAL; + return rc; +} + +static int +ethdev_mtu_config(const char *name, uint32_t mtu) +{ + struct ethdev *eth_hdl; + uint16_t portid = 0; + int rc; + + rc = rte_eth_dev_get_port_by_name(name, &portid); + if (rc < 0) + return rc; + + eth_hdl = ethdev_port_by_id(portid); + + if (eth_hdl) { + rc = rte_eth_dev_set_mtu(portid, mtu); + if (rc < 0) + return rc; + + eth_hdl->config.mtu = mtu; + return 0; + } + + rc = -EINVAL; + return rc; +} + + +static int +ethdev_process(const char *name, struct ethdev_config *params) +{ + struct rte_eth_dev_info port_info; + struct rte_eth_conf port_conf; + struct ethdev_rss_config *rss; + struct rte_mempool *mempool; + struct ethdev *ethdev_port; + struct rte_ether_addr smac; + int numa_node, rc; + uint16_t port_id = 0; + uint32_t i; + + /* Check input params */ + if (!name || !name[0] || !params || !params->rx.n_queues || !params->rx.queue_size || + !params->tx.n_queues || !params->tx.queue_size) + return -EINVAL; + + rc = rte_eth_dev_get_port_by_name(name, &port_id); + if (rc) + return -EINVAL; + + if (!ethdev_port_by_id(port_id)) { + ethdev_port = malloc(sizeof(struct ethdev)); + if (!ethdev_port) + return -EINVAL; + } else { + return 0; + } + + rc = rte_eth_dev_info_get(port_id, &port_info); + if (rc) { + rc = -EINVAL; + goto exit; + } + + mempool = rte_mempool_lookup(params->rx.mempool_name); + if (!mempool) { + rc = -EINVAL; + goto exit; + } + + params->rx.mp = mempool; + + rss = params->rx.rss; + if (rss) { + if (!port_info.reta_size || port_info.reta_size > RTE_ETH_RSS_RETA_SIZE_512) { + rc = -EINVAL; + goto exit; + } + + if (!rss->n_queues || rss->n_queues >= ETHDEV_RXQ_RSS_MAX) { + rc = -EINVAL; + goto exit; + } + + for (i = 0; i < rss->n_queues; i++) + if (rss->queue_id[i] >= port_info.max_rx_queues) { + rc = -EINVAL; + goto exit; + } + } + + /* Port */ + memcpy(&port_conf, &port_conf_default, sizeof(struct rte_eth_conf)); + if (rss) { + uint64_t rss_hf = RTE_ETH_RSS_IP | RTE_ETH_RSS_TCP | RTE_ETH_RSS_UDP; + + port_conf.rxmode.mq_mode = RTE_ETH_MQ_RX_RSS; + port_conf.rx_adv_conf.rss_conf.rss_hf = rss_hf & port_info.flow_type_rss_offloads; + } + + numa_node = rte_eth_dev_socket_id(port_id); + if (numa_node == SOCKET_ID_ANY) + numa_node = 0; + + if (params->mtu) + port_conf.rxmode.mtu = params->mtu; + + rc = rte_eth_dev_configure(port_id, params->rx.n_queues, params->tx.n_queues, + &port_conf); + if (rc < 0) { + rc = -EINVAL; + goto exit; + } + + rc = rte_eth_macaddr_get(port_id, &smac); + if (rc < 0) { + rc = -EINVAL; + goto exit; + } + + printf("Port_id = %d srcmac = %x:%x:%x:%x:%x:%x\n", port_id, + smac.addr_bytes[0], smac.addr_bytes[1], + smac.addr_bytes[2], smac.addr_bytes[3], + smac.addr_bytes[4], smac.addr_bytes[5]); + + /* Port RX */ + for (i = 0; i < params->rx.n_queues; i++) { + rc = rte_eth_rx_queue_setup(port_id, i, params->rx.queue_size, numa_node, NULL, + mempool); + if (rc < 0) { + rc = -EINVAL; + goto exit; + } + } + + /* Port TX */ + for (i = 0; i < params->tx.n_queues; i++) { + rc = rte_eth_tx_queue_setup(port_id, i, params->tx.queue_size, numa_node, NULL); + if (rc < 0) { + rc = -EINVAL; + goto exit; + } + } + + memcpy(ðdev_port->config, params, sizeof(struct ethdev_config)); + memcpy(ethdev_port->config.dev_name, name, strlen(name)); + ethdev_port->config.port_id = port_id; + enabled_port_mask |= RTE_BIT32(port_id); + + TAILQ_INSERT_TAIL(ð_node, ethdev_port, next); + return 0; +exit: + free(ethdev_port); + return rc; + +} + +static int +ethdev_stats_show(const char *name) +{ + uint64_t diff_pkts_rx, diff_pkts_tx, diff_bytes_rx, diff_bytes_tx; + static uint64_t prev_pkts_rx[RTE_MAX_ETHPORTS]; + static uint64_t prev_pkts_tx[RTE_MAX_ETHPORTS]; + static uint64_t prev_bytes_rx[RTE_MAX_ETHPORTS]; + static uint64_t prev_bytes_tx[RTE_MAX_ETHPORTS]; + static uint64_t prev_cycles[RTE_MAX_ETHPORTS]; + uint64_t mpps_rx, mpps_tx, mbps_rx, mbps_tx; + uint64_t diff_ns, diff_cycles, curr_cycles; + struct rte_eth_stats stats; + static const char *nic_stats_border = "########################"; + uint16_t port_id, len; + int rc; + + rc = rte_eth_dev_get_port_by_name(name, &port_id); + if (rc < 0) + return rc; + + rc = rte_eth_stats_get(port_id, &stats); + if (rc != 0) { + fprintf(stderr, + "%s: Error: failed to get stats (port %u): %d", + __func__, port_id, rc); + return rc; + } + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, + "\n %s NIC statistics for port %-2d %s\n" + " RX-packets: %-10"PRIu64" RX-missed: %-10"PRIu64" RX-bytes: ""%-"PRIu64"\n" + " RX-errors: %-"PRIu64"\n" + " RX-nombuf: %-10"PRIu64"\n" + " TX-packets: %-10"PRIu64" TX-errors: %-10"PRIu64" TX-bytes: ""%-"PRIu64"\n", + nic_stats_border, port_id, nic_stats_border, stats.ipackets, stats.imissed, + stats.ibytes, stats.ierrors, stats.rx_nombuf, stats.opackets, stats.oerrors, + stats.obytes); + + len = strlen(conn->msg_out) - len; + conn->msg_out_len_max -= len; + + diff_ns = 0; + diff_cycles = 0; + + curr_cycles = rte_rdtsc(); + if (prev_cycles[port_id] != 0) + diff_cycles = curr_cycles - prev_cycles[port_id]; + + prev_cycles[port_id] = curr_cycles; + diff_ns = diff_cycles > 0 ? + diff_cycles * (1 / (double)rte_get_tsc_hz()) * NS_PER_SEC : 0; + + diff_pkts_rx = (stats.ipackets > prev_pkts_rx[port_id]) ? + (stats.ipackets - prev_pkts_rx[port_id]) : 0; + diff_pkts_tx = (stats.opackets > prev_pkts_tx[port_id]) ? + (stats.opackets - prev_pkts_tx[port_id]) : 0; + prev_pkts_rx[port_id] = stats.ipackets; + prev_pkts_tx[port_id] = stats.opackets; + mpps_rx = diff_ns > 0 ? + (double)diff_pkts_rx / diff_ns * NS_PER_SEC : 0; + mpps_tx = diff_ns > 0 ? + (double)diff_pkts_tx / diff_ns * NS_PER_SEC : 0; + + diff_bytes_rx = (stats.ibytes > prev_bytes_rx[port_id]) ? + (stats.ibytes - prev_bytes_rx[port_id]) : 0; + diff_bytes_tx = (stats.obytes > prev_bytes_tx[port_id]) ? + (stats.obytes - prev_bytes_tx[port_id]) : 0; + prev_bytes_rx[port_id] = stats.ibytes; + prev_bytes_tx[port_id] = stats.obytes; + mbps_rx = diff_ns > 0 ? + (double)diff_bytes_rx / diff_ns * NS_PER_SEC : 0; + mbps_tx = diff_ns > 0 ? + (double)diff_bytes_tx / diff_ns * NS_PER_SEC : 0; + + len = strlen(conn->msg_out); + snprintf(conn->msg_out + len, conn->msg_out_len_max, + "\n Throughput (since last show)\n" + " Rx-pps: %12"PRIu64" Rx-bps: %12"PRIu64"\n Tx-pps: %12" + PRIu64" Tx-bps: %12"PRIu64"\n" + " %s############################%s\n", + mpps_rx, mbps_rx * 8, mpps_tx, mbps_tx * 8, nic_stats_border, nic_stats_border); + return 0; +} + +static void +cli_ethdev_mtu(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_mtu_cmd_tokens *res = parsed_result; + int rc = -EINVAL; + + rc = ethdev_mtu_config(res->dev, res->size); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +static void +cli_ethdev_prom_mode(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_prom_mode_cmd_tokens *res = parsed_result; + bool enable = false; + int rc = -EINVAL; + + if (!strcmp(res->enable, "on")) + enable = true; + + rc = ethdev_prom_mode_config(res->dev, enable); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +static void +cli_ip4_addr(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_ip4_cmd_tokens *res = parsed_result; + struct ipv4_addr_config config; + int rc = -EINVAL; + + if (parser_ip4_read(&config.ip, res->ip)) { + printf(MSG_ARG_INVALID, "ip"); + return; + } + + if (parser_ip4_read(&config.mask, res->mask)) { + printf(MSG_ARG_INVALID, "netmask"); + return; + } + + rc = ethdev_ip4_addr_add(res->dev, &config); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +static void +cli_ip6_addr(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_ip6_cmd_tokens *res = parsed_result; + struct ipv6_addr_config config; + int rc = -EINVAL; + + if (parser_ip6_read(config.ip, res->ip)) { + printf(MSG_ARG_INVALID, "ip"); + return; + } + + if (parser_ip6_read(config.mask, res->mask)) { + printf(MSG_ARG_INVALID, "netmask"); + return; + } + + rc = ethdev_ip6_addr_add(res->dev, &config); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +static void +cli_ethdev_show(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_show_cmd_tokens *res = parsed_result; + int rc = -EINVAL; + + rc = ethdev_show(res->dev); + if (rc < 0) + printf(MSG_ARG_INVALID, res->dev); +} + +static void +cli_ethdev_stats(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_stats_cmd_tokens *res = parsed_result; + int rc = -EINVAL; + + rc = ethdev_stats_show(res->dev); + if (rc < 0) + printf(MSG_ARG_INVALID, res->dev); +} + +static void +cli_ethdev(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_cmd_tokens *res = parsed_result; + struct ethdev_config config; + int rc; + + memset(&config, 0, sizeof(struct ethdev_config)); + config.rx.n_queues = res->nb_rxq; + config.rx.queue_size = ETHDEV_RX_DESC_DEFAULT; + memcpy(config.rx.mempool_name, res->mempool, strlen(res->mempool)); + + config.tx.n_queues = res->nb_txq; + config.tx.queue_size = ETHDEV_TX_DESC_DEFAULT; + + config.mtu = port_conf_default.rxmode.mtu; + + rc = ethdev_process(res->dev, &config); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +static void +cli_ethdev_help(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + size_t len; + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, "\n%s\n%s\n%s\n%s\n%s\n%s\n%s\n", + "----------------------------- ethdev command help -----------------------------", + cmd_ethdev_help, cmd_ethdev_ip4_addr_help, cmd_ethdev_ip6_addr_help, + cmd_ethdev_prom_mode_help, cmd_ethdev_mtu_help, cmd_ethdev_show_help); + + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; +} + +cmdline_parse_token_string_t ethdev_stats_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_stats_cmd_tokens, cmd, "ethdev"); +cmdline_parse_token_string_t ethdev_stats_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_stats_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_stats_stats = + TOKEN_STRING_INITIALIZER(struct ethdev_stats_cmd_tokens, stats, "stats"); + +cmdline_parse_inst_t ethdev_stats_cmd_ctx = { + .f = cli_ethdev_stats, + .data = NULL, + .help_str = "", + .tokens = { + (void *)ðdev_stats_cmd, + (void *)ðdev_stats_dev, + (void *)ðdev_stats_stats, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_show_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_show_cmd_tokens, cmd, "ethdev"); +cmdline_parse_token_string_t ethdev_show_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_show_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_show_show = + TOKEN_STRING_INITIALIZER(struct ethdev_show_cmd_tokens, show, "show"); + +cmdline_parse_inst_t ethdev_show_cmd_ctx = { + .f = cli_ethdev_show, + .data = NULL, + .help_str = cmd_ethdev_show_help, + .tokens = { + (void *)ðdev_show_cmd, + (void *)ðdev_show_dev, + (void *)ðdev_show_show, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_mtu_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_mtu_cmd_tokens, cmd, "ethdev"); +cmdline_parse_token_string_t ethdev_mtu_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_mtu_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_mtu_mtu = + TOKEN_STRING_INITIALIZER(struct ethdev_mtu_cmd_tokens, mtu, "mtu"); +cmdline_parse_token_num_t ethdev_mtu_size = + TOKEN_NUM_INITIALIZER(struct ethdev_mtu_cmd_tokens, size, RTE_UINT16); + +cmdline_parse_inst_t ethdev_mtu_cmd_ctx = { + .f = cli_ethdev_mtu, + .data = NULL, + .help_str = cmd_ethdev_mtu_help, + .tokens = { + (void *)ðdev_mtu_cmd, + (void *)ðdev_mtu_dev, + (void *)ðdev_mtu_mtu, + (void *)ðdev_mtu_size, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_prom_mode_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_prom_mode_cmd_tokens, cmd, "ethdev"); +cmdline_parse_token_string_t ethdev_prom_mode_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_prom_mode_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_prom_mode_prom = + TOKEN_STRING_INITIALIZER(struct ethdev_prom_mode_cmd_tokens, prom, "promiscuous"); +cmdline_parse_token_string_t ethdev_prom_mode_enable = + TOKEN_STRING_INITIALIZER(struct ethdev_prom_mode_cmd_tokens, enable, "on#off"); + +cmdline_parse_inst_t ethdev_prom_mode_cmd_ctx = { + .f = cli_ethdev_prom_mode, + .data = NULL, + .help_str = cmd_ethdev_prom_mode_help, + .tokens = { + (void *)ðdev_prom_mode_cmd, + (void *)ðdev_prom_mode_dev, + (void *)ðdev_prom_mode_prom, + (void *)ðdev_prom_mode_enable, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_ip4_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, cmd, "ethdev"); +cmdline_parse_token_string_t ethdev_ip4_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_ip4_ip4 = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, ip4, "ip4"); +cmdline_parse_token_string_t ethdev_ip4_addr = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, addr, "addr"); +cmdline_parse_token_string_t ethdev_ip4_add = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, add, "add"); +cmdline_parse_token_string_t ethdev_ip4_ip = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, ip, NULL); +cmdline_parse_token_string_t ethdev_ip4_netmask = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, netmask, "netmask"); +cmdline_parse_token_string_t ethdev_ip4_mask = + TOKEN_STRING_INITIALIZER(struct ethdev_ip4_cmd_tokens, mask, NULL); + +cmdline_parse_inst_t ethdev_ip4_cmd_ctx = { + .f = cli_ip4_addr, + .data = NULL, + .help_str = cmd_ethdev_ip4_addr_help, + .tokens = { + (void *)ðdev_ip4_cmd, + (void *)ðdev_ip4_dev, + (void *)ðdev_ip4_ip4, + (void *)ðdev_ip4_addr, + (void *)ðdev_ip4_add, + (void *)ðdev_ip4_ip, + (void *)ðdev_ip4_netmask, + (void *)ðdev_ip4_mask, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_ip6_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, cmd, "ethdev"); +cmdline_parse_token_string_t ethdev_ip6_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_ip6_ip6 = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, ip6, "ip6"); +cmdline_parse_token_string_t ethdev_ip6_addr = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, addr, "addr"); +cmdline_parse_token_string_t ethdev_ip6_add = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, add, "add"); +cmdline_parse_token_string_t ethdev_ip6_ip = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, ip, NULL); +cmdline_parse_token_string_t ethdev_ip6_netmask = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, netmask, "netmask"); +cmdline_parse_token_string_t ethdev_ip6_mask = + TOKEN_STRING_INITIALIZER(struct ethdev_ip6_cmd_tokens, mask, NULL); + +cmdline_parse_inst_t ethdev_ip6_cmd_ctx = { + .f = cli_ip6_addr, + .data = NULL, + .help_str = cmd_ethdev_ip6_addr_help, + .tokens = { + (void *)ðdev_ip6_cmd, + (void *)ðdev_ip6_dev, + (void *)ðdev_ip6_ip6, + (void *)ðdev_ip6_addr, + (void *)ðdev_ip6_add, + (void *)ðdev_ip6_ip, + (void *)ðdev_ip6_netmask, + (void *)ðdev_ip6_mask, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_cmd_tokens, cmd, "ethdev"); +cmdline_parse_token_string_t ethdev_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_rxq = + TOKEN_STRING_INITIALIZER(struct ethdev_cmd_tokens, rxq, "rxq"); +cmdline_parse_token_num_t ethdev_nb_rxq = + TOKEN_NUM_INITIALIZER(struct ethdev_cmd_tokens, nb_rxq, RTE_UINT16); +cmdline_parse_token_string_t ethdev_txq = + TOKEN_STRING_INITIALIZER(struct ethdev_cmd_tokens, txq, "txq"); +cmdline_parse_token_num_t ethdev_nb_txq = + TOKEN_NUM_INITIALIZER(struct ethdev_cmd_tokens, nb_txq, RTE_UINT16); +cmdline_parse_token_string_t ethdev_mempool = + TOKEN_STRING_INITIALIZER(struct ethdev_cmd_tokens, mempool, NULL); + +cmdline_parse_inst_t ethdev_cmd_ctx = { + .f = cli_ethdev, + .data = NULL, + .help_str = cmd_ethdev_help, + .tokens = { + (void *)ðdev_cmd, + (void *)ðdev_dev, + (void *)ðdev_rxq, + (void *)ðdev_nb_rxq, + (void *)ðdev_txq, + (void *)ðdev_nb_txq, + (void *)ðdev_mempool, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_help_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_help_cmd_tokens, help, "help"); +cmdline_parse_token_string_t ethdev_help_ethdev = + TOKEN_STRING_INITIALIZER(struct ethdev_help_cmd_tokens, ethdev, "ethdev"); + +cmdline_parse_inst_t ethdev_help_cmd_ctx = { + .f = cli_ethdev_help, + .data = NULL, + .help_str = "", + .tokens = { + (void *)ðdev_help_cmd, + (void *)ðdev_help_ethdev, + NULL, + }, +}; diff --git a/app/graph/ethdev.h b/app/graph/ethdev.h new file mode 100644 index 0000000000..94d3247a2c --- /dev/null +++ b/app/graph/ethdev.h @@ -0,0 +1,40 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_ETHDEV_H +#define APP_GRAPH_ETHDEV_H + +#include + +#define ETHDEV_IPV6_ADDR_LEN 16 + +extern cmdline_parse_inst_t ethdev_show_cmd_ctx; +extern cmdline_parse_inst_t ethdev_stats_cmd_ctx; +extern cmdline_parse_inst_t ethdev_mtu_cmd_ctx; +extern cmdline_parse_inst_t ethdev_prom_mode_cmd_ctx; +extern cmdline_parse_inst_t ethdev_ip4_cmd_ctx; +extern cmdline_parse_inst_t ethdev_ip6_cmd_ctx; +extern cmdline_parse_inst_t ethdev_cmd_ctx; +extern cmdline_parse_inst_t ethdev_help_cmd_ctx; + +struct ipv4_addr_config { + uint32_t ip; + uint32_t mask; +}; + +struct ipv6_addr_config { + uint8_t ip[ETHDEV_IPV6_ADDR_LEN]; + uint8_t mask[ETHDEV_IPV6_ADDR_LEN]; +}; + +extern uint32_t enabled_port_mask; + +void ethdev_start(void); +void ethdev_stop(void); +void *ethdev_mempool_list_by_portid(uint16_t portid); +int16_t ethdev_portid_by_ip4(uint32_t ip, uint32_t mask); +int16_t ethdev_portid_by_ip6(uint8_t *ip, uint8_t *mask); +void ethdev_list_clean(void); + +#endif diff --git a/app/graph/ethdev_priv.h b/app/graph/ethdev_priv.h new file mode 100644 index 0000000000..f231f3f3e1 --- /dev/null +++ b/app/graph/ethdev_priv.h @@ -0,0 +1,112 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_ETHDEV_PRIV_H +#define APP_GRAPH_ETHDEV_PRIV_H + +#include "ethdev.h" + +#define NS_PER_SEC 1E9 + +#define ETHDEV_RXQ_RSS_MAX 16 +#define ETHDEV_RX_DESC_DEFAULT 1024 +#define ETHDEV_TX_DESC_DEFAULT 1024 + +struct ethdev_show_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t show; +}; + +struct ethdev_stats_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t stats; +}; + +struct ethdev_mtu_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t mtu; + uint16_t size; +}; + +struct ethdev_prom_mode_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t prom; + cmdline_fixed_string_t enable; +}; + +struct ethdev_ip4_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t ip4; + cmdline_fixed_string_t addr; + cmdline_fixed_string_t add; + cmdline_fixed_string_t ip; + cmdline_fixed_string_t netmask; + cmdline_fixed_string_t mask; +}; + +struct ethdev_ip6_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t ip6; + cmdline_fixed_string_t addr; + cmdline_fixed_string_t add; + cmdline_fixed_string_t ip; + cmdline_fixed_string_t netmask; + cmdline_fixed_string_t mask; +}; + +struct ethdev_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t rxq; + cmdline_fixed_string_t txq; + cmdline_fixed_string_t mempool; + uint16_t nb_rxq; + uint16_t nb_txq; +}; + +struct ethdev_help_cmd_tokens { + cmdline_fixed_string_t help; + cmdline_fixed_string_t ethdev; +}; + +struct ethdev_rss_config { + uint32_t queue_id[ETHDEV_RXQ_RSS_MAX]; + uint32_t n_queues; +}; + +struct ethdev_config { + char dev_name[RTE_ETH_NAME_MAX_LEN]; + uint16_t port_id; + + struct { + uint32_t n_queues; + uint32_t queue_size; + char mempool_name[RTE_MEMPOOL_NAMESIZE]; + struct rte_mempool *mp; + struct ethdev_rss_config *rss; + } rx; + + struct { + uint32_t n_queues; + uint32_t queue_size; + } tx; + + int promiscuous; + uint32_t mtu; +}; + +struct ethdev { + TAILQ_ENTRY(ethdev) next; + struct ethdev_config config; + struct ipv4_addr_config ip4_addr; + struct ipv6_addr_config ip6_addr; +}; +TAILQ_HEAD(ethdev_head, ethdev); +#endif diff --git a/app/graph/main.c b/app/graph/main.c index 79575fa2a6..6368019712 100644 --- a/app/graph/main.c +++ b/app/graph/main.c @@ -186,7 +186,8 @@ main(int argc, char **argv) } conn_free(conn); + ethdev_stop(); cli_exit(); rte_eal_cleanup(); return 0; -} \ No newline at end of file +} diff --git a/app/graph/meson.build b/app/graph/meson.build index d35287be14..d0369f1c09 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -11,6 +11,7 @@ deps += ['bus_pci', 'graph', 'eal', 'lpm', 'ethdev', 'node', 'cmdline'] sources = files( 'cli.c', 'conn.c', + 'ethdev.c', 'main.c', 'mempool.c', 'utils.c', diff --git a/app/graph/module_api.h b/app/graph/module_api.h index de154f5f93..d509f38837 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -10,6 +10,7 @@ #include "cli.h" #include "conn.h" +#include "ethdev.h" #include "mempool.h" #include "utils.h" /* From patchwork Tue Sep 19 16:04:47 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131645 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 6B7B44260C; Tue, 19 Sep 2023 18:06:09 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 47C9C410FA; Tue, 19 Sep 2023 18:05:32 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 3155740EE4 for ; Tue, 19 Sep 2023 18:05:27 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02N012050 for ; Tue, 19 Sep 2023 09:05:26 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=2CWs2Ybka/Tv892SsbeOtOMGt47iVEqiNdRUEOrE874=; b=dH2LuVOGD4LCddUdaitvGHU7VnRzyvcsGyrSkGmmKJdVA5n0bbYtxiessUOnUY/95KhI UD+eappH6BqdX1Tb66IXBBGTB6MSwZuTr1ERQBfNrqDAwS/88GzyGmdre2XDTyP9KraO fRPyzRZxPaRG5kaQ77d1/3v9Thn1figZWzBiC/fpmAWKyCFRAVMlbcU+wxhn+3QDUif6 EiPr/VL56aVTpSCWX/pR1+iHARbQe4yVPCSyp87XEt9mhTpVngaGFw9jQmI6gvpmFipf dlMyeMv27AI7hAeLIs9x5OZbC1udmChdRTIAXvdDJ80odkvJbNKklcFs2Njhe6+qCxa8 3g== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-8 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:26 -0700 Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:12 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:12 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id C2D423F7099; Tue, 19 Sep 2023 09:05:11 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 06/14] app/graph: add ipv4_lookup command line interfaces Date: Tue, 19 Sep 2023 21:34:47 +0530 Message-ID: <20230919160455.1678716-6-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: JG5Ct0ujWv1KF7mmKSNGngNiJV_eM1Gr X-Proofpoint-GUID: JG5Ct0ujWv1KF7mmKSNGngNiJV_eM1Gr X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori It adds ipv4_lookup module to configure LPM table. This LPM table will be used for IPv4 lookup and forwarding. Following commands are exposed: - ipv4_lookup route add ipv4 netmask via - help ipv4_lookup Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/cli.c | 2 + app/graph/ethdev.c | 2 +- app/graph/ip4_route.c | 205 +++++++++++++++++++++++++++++++++++++++++ app/graph/meson.build | 1 + app/graph/module_api.h | 1 + app/graph/route.h | 26 ++++++ app/graph/route_priv.h | 44 +++++++++ 7 files changed, 280 insertions(+), 1 deletion(-) create mode 100644 app/graph/ip4_route.c create mode 100644 app/graph/route.h create mode 100644 app/graph/route_priv.h diff --git a/app/graph/cli.c b/app/graph/cli.c index c4b5cf3ce1..430750db6e 100644 --- a/app/graph/cli.c +++ b/app/graph/cli.c @@ -30,6 +30,8 @@ cmdline_parse_ctx_t modules_ctx[] = { (cmdline_parse_inst_t *)ðdev_ip6_cmd_ctx, (cmdline_parse_inst_t *)ðdev_cmd_ctx, (cmdline_parse_inst_t *)ðdev_help_cmd_ctx, + (cmdline_parse_inst_t *)&ipv4_lookup_cmd_ctx, + (cmdline_parse_inst_t *)&ipv4_lookup_help_cmd_ctx, NULL, }; diff --git a/app/graph/ethdev.c b/app/graph/ethdev.c index 81ad8c4757..cb29c9054d 100644 --- a/app/graph/ethdev.c +++ b/app/graph/ethdev.c @@ -160,7 +160,7 @@ ethdev_stop(void) } ethdev_list_clean(); - rte_eal_cleanup(); + route_ip4_list_clean(); printf("Bye...\n"); } diff --git a/app/graph/ip4_route.c b/app/graph/ip4_route.c new file mode 100644 index 0000000000..a8fb8ba8d5 --- /dev/null +++ b/app/graph/ip4_route.c @@ -0,0 +1,205 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include + +#include +#include +#include +#include +#include + +#include "module_api.h" +#include "route_priv.h" + +static const char +cmd_ipv4_lookup_help[] = "ipv4_lookup route add ipv4 netmask via "; + +struct ip4_route route4 = TAILQ_HEAD_INITIALIZER(route4); + + +void +route_ip4_list_clean(void) +{ + struct route_ipv4_config *route; + + while (!TAILQ_EMPTY(&route4)) { + route = TAILQ_FIRST(&route4); + TAILQ_REMOVE(&route4, route, next); + } +} + +static struct route_ipv4_config * +find_route4_entry(struct route_ipv4_config *route) +{ + struct route_ipv4_config *ipv4route; + + TAILQ_FOREACH(ipv4route, &route4, next) { + if (!memcmp(ipv4route, route, sizeof(*route))) + return ipv4route; + } + return NULL; + +} + +static uint8_t +convert_netmask_to_depth(uint32_t netmask) +{ + uint8_t zerobits = 0; + + while ((netmask & 0x1) == 0) { + netmask = netmask >> 1; + zerobits++; + } + + return (32 - zerobits); +} + +static int +route_ip4_add(struct route_ipv4_config *route) +{ + struct route_ipv4_config *ipv4route; + + ipv4route = find_route4_entry(route); + + if (!ipv4route) { + ipv4route = malloc(sizeof(struct route_ipv4_config)); + if (!ipv4route) + return -ENOMEM; + } else { + return 0; + } + + ipv4route->ip = route->ip; + ipv4route->netmask = route->netmask; + ipv4route->via = route->via; + ipv4route->is_used = true; + + TAILQ_INSERT_TAIL(&route4, ipv4route, next); + return 0; +} + +int +route_ip4_add_to_lookup(void) +{ + struct route_ipv4_config *route = NULL; + int rc = -EINVAL; + uint8_t depth; + int portid; + + TAILQ_FOREACH(route, &route4, next) { + portid = ethdev_portid_by_ip4(route->via, route->netmask); + if (portid < 0) { + printf("Invalid portid found to install the route\n"); + return rc; + } + + depth = convert_netmask_to_depth(route->netmask); + + rc = rte_node_ip4_route_add(route->ip, depth, portid, + RTE_NODE_IP4_LOOKUP_NEXT_REWRITE); + if (rc < 0) + return rc; + } + + return 0; +} + +static void +cli_ipv4_lookup_help(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + size_t len; + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, "\n%s\n%s\n", + "--------------------------- ipv4_lookup command help ---------------------------", + cmd_ipv4_lookup_help); + + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; +} + +static void +cli_ipv4_lookup(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ip4_lookup_cmd_tokens *res = parsed_result; + struct route_ipv4_config config; + int rc = -EINVAL; + + if (parser_ip4_read(&config.ip, res->ip)) { + printf(MSG_ARG_INVALID, "ipv4"); + return; + } + + if (parser_ip4_read(&config.netmask, res->mask)) { + printf(MSG_ARG_INVALID, "netmask"); + return; + } + + if (parser_ip4_read(&config.via, res->via_ip)) { + printf(MSG_ARG_INVALID, "via ip"); + return; + } + + rc = route_ip4_add(&config); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +cmdline_parse_token_string_t ip4_lookup_cmd = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, cmd, "ipv4_lookup"); +cmdline_parse_token_string_t ip4_lookup_route = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, route, "route"); +cmdline_parse_token_string_t ip4_lookup_add = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, add, "add"); +cmdline_parse_token_string_t ip4_lookup_ip4 = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, ip4, "ipv4"); +cmdline_parse_token_string_t ip4_lookup_ip = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, ip, NULL); +cmdline_parse_token_string_t ip4_lookup_netmask = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, netmask, "netmask"); +cmdline_parse_token_string_t ip4_lookup_mask = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, mask, NULL); +cmdline_parse_token_string_t ip4_lookup_via = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, via, "via"); +cmdline_parse_token_string_t ip4_lookup_via_ip = + TOKEN_STRING_INITIALIZER(struct ip4_lookup_cmd_tokens, via_ip, NULL); + +cmdline_parse_inst_t ipv4_lookup_cmd_ctx = { + .f = cli_ipv4_lookup, + .data = NULL, + .help_str = cmd_ipv4_lookup_help, + .tokens = { + (void *)&ip4_lookup_cmd, + (void *)&ip4_lookup_route, + (void *)&ip4_lookup_add, + (void *)&ip4_lookup_ip4, + (void *)&ip4_lookup_ip, + (void *)&ip4_lookup_netmask, + (void *)&ip4_lookup_mask, + (void *)&ip4_lookup_via, + (void *)&ip4_lookup_via_ip, + NULL, + }, +}; + +cmdline_parse_token_string_t ipv4_lookup_help_cmd = + TOKEN_STRING_INITIALIZER(struct ipv4_lookup_help_cmd_tokens, cmd, "help"); +cmdline_parse_token_string_t ipv4_lookup_help_module = + TOKEN_STRING_INITIALIZER(struct ipv4_lookup_help_cmd_tokens, module, "ipv4_lookup"); + +cmdline_parse_inst_t ipv4_lookup_help_cmd_ctx = { + .f = cli_ipv4_lookup_help, + .data = NULL, + .help_str = "", + .tokens = { + (void *)&ipv4_lookup_help_cmd, + (void *)&ipv4_lookup_help_module, + NULL, + }, +}; diff --git a/app/graph/meson.build b/app/graph/meson.build index d0369f1c09..b993d6375f 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -12,6 +12,7 @@ sources = files( 'cli.c', 'conn.c', 'ethdev.c', + 'ip4_route.c', 'main.c', 'mempool.c', 'utils.c', diff --git a/app/graph/module_api.h b/app/graph/module_api.h index d509f38837..da049a1faa 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -12,6 +12,7 @@ #include "conn.h" #include "ethdev.h" #include "mempool.h" +#include "route.h" #include "utils.h" /* * Externs diff --git a/app/graph/route.h b/app/graph/route.h new file mode 100644 index 0000000000..a44d401d55 --- /dev/null +++ b/app/graph/route.h @@ -0,0 +1,26 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_ROUTE_H +#define APP_GRAPH_ROUTE_H + +#define MAX_ROUTE_ENTRIES 32 + +extern cmdline_parse_inst_t ipv4_lookup_cmd_ctx; +extern cmdline_parse_inst_t ipv4_lookup_help_cmd_ctx; + +struct route_ipv4_config { + TAILQ_ENTRY(route_ipv4_config) next; + uint32_t ip; + uint32_t netmask; + uint32_t via; + bool is_used; +}; + +TAILQ_HEAD(ip4_route, route_ipv4_config); + +int route_ip4_add_to_lookup(void); +void route_ip4_list_clean(void); + +#endif diff --git a/app/graph/route_priv.h b/app/graph/route_priv.h new file mode 100644 index 0000000000..f363a551a9 --- /dev/null +++ b/app/graph/route_priv.h @@ -0,0 +1,44 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_ROUTE_PRIV_H +#define APP_GRAPH_ROUTE_PRIV_H + +#define MAX_ROUTE_ENTRIES 32 + +struct ip4_lookup_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t route; + cmdline_fixed_string_t add; + cmdline_fixed_string_t ip4; + cmdline_fixed_string_t ip; + cmdline_fixed_string_t netmask; + cmdline_fixed_string_t mask; + cmdline_fixed_string_t via; + cmdline_fixed_string_t via_ip; +}; + +struct ip6_lookup_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t route; + cmdline_fixed_string_t add; + cmdline_fixed_string_t ip6; + cmdline_fixed_string_t ip; + cmdline_fixed_string_t netmask; + cmdline_fixed_string_t mask; + cmdline_fixed_string_t via; + cmdline_fixed_string_t via_ip; +}; + +struct ipv4_lookup_help_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t module; +}; + +struct ipv6_lookup_help_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t module; +}; + +#endif From patchwork Tue Sep 19 16:04:48 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131647 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id AEE8D4260C; Tue, 19 Sep 2023 18:06:33 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 6238741157; Tue, 19 Sep 2023 18:05:37 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id BC56640E5E for ; Tue, 19 Sep 2023 18:05:29 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa2LB012098 for ; Tue, 19 Sep 2023 09:05:29 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=Ha7DPJ7CH5PND7gkmBCq1Mc2Wd6Bkjs3hILWKo0GW/s=; b=Xn+RxhIBDrCCQUbj0uT3o4xJsTiDRB7Su8PJXSIjQjmN+iV1yP9TZjH39PqKnT/8JA8P njc6s5SRodOUW0+B8Myd7vN8HwnXGl3Y6l2SD5zUpoxNr/thtOgjX/xhJtqGgGWG0UCg /f8BYW7XTHfd/OaokMJqIWq4WqtPNt0pXnnJz5HgPAt2GIQVi1CLwu8KLjOlyYZZU3nF PrkDRxYZNxgyY0CiEaFBklUSqAYrOePVZ/7LUhKpk5KSmys3HCtdGtADxreH3F1dPqNd gjwNzL0AEQqcM/CcYc2W2M8H6mxtewaoRevZnmSjNkJBTr48ebv249OfJSW6abs8KkDD Rw== Received: from dc5-exch01.marvell.com ([199.233.59.181]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6c-7 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:28 -0700 Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:14 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:14 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 9B27C3F709B; Tue, 19 Sep 2023 09:05:13 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 07/14] app/graph: add ipv6_lookup command line interfaces Date: Tue, 19 Sep 2023 21:34:48 +0530 Message-ID: <20230919160455.1678716-7-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: 6Dpy4dkQs8WsfpANm99KGWxj0og0ugYB X-Proofpoint-GUID: 6Dpy4dkQs8WsfpANm99KGWxj0og0ugYB X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Rakesh Kudurumalla It adds ipv6_lookup module to configure LPM6 table. This LPM6 table will be used for IPv6 lookup and forwarding. Following commands are exposed: - ipv6_lookup route add ipv6 netmask via - help ipv6_lookup Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/cli.c | 2 + app/graph/ethdev.c | 1 + app/graph/ip6_route.c | 210 ++++++++++++++++++++++++++++++++++++++++++ app/graph/meson.build | 1 + app/graph/route.h | 14 +++ 5 files changed, 228 insertions(+) create mode 100644 app/graph/ip6_route.c diff --git a/app/graph/cli.c b/app/graph/cli.c index 430750db6e..7213a91ad2 100644 --- a/app/graph/cli.c +++ b/app/graph/cli.c @@ -32,6 +32,8 @@ cmdline_parse_ctx_t modules_ctx[] = { (cmdline_parse_inst_t *)ðdev_help_cmd_ctx, (cmdline_parse_inst_t *)&ipv4_lookup_cmd_ctx, (cmdline_parse_inst_t *)&ipv4_lookup_help_cmd_ctx, + (cmdline_parse_inst_t *)&ipv6_lookup_cmd_ctx, + (cmdline_parse_inst_t *)&ipv6_lookup_help_cmd_ctx, NULL, }; diff --git a/app/graph/ethdev.c b/app/graph/ethdev.c index cb29c9054d..0a4eb7be4f 100644 --- a/app/graph/ethdev.c +++ b/app/graph/ethdev.c @@ -161,6 +161,7 @@ ethdev_stop(void) ethdev_list_clean(); route_ip4_list_clean(); + route_ip6_list_clean(); printf("Bye...\n"); } diff --git a/app/graph/ip6_route.c b/app/graph/ip6_route.c new file mode 100644 index 0000000000..93c2c967aa --- /dev/null +++ b/app/graph/ip6_route.c @@ -0,0 +1,210 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include +#include +#include +#include +#include + +#include + +#include "module_api.h" +#include "route_priv.h" + +static const char +cmd_ipv6_lookup_help[] = "ipv6_lookup route add ipv6 netmask via "; + +struct ip6_route route6 = TAILQ_HEAD_INITIALIZER(route6); + +void +route_ip6_list_clean(void) +{ + struct route_ipv6_config *route; + + while (!TAILQ_EMPTY(&route6)) { + route = TAILQ_FIRST(&route6); + TAILQ_REMOVE(&route6, route, next); + } +} + +static struct route_ipv6_config * +find_route6_entry(struct route_ipv6_config *route) +{ + struct route_ipv6_config *ipv6route; + + TAILQ_FOREACH(ipv6route, &route6, next) { + if (!memcmp(ipv6route, route, sizeof(*route))) + return ipv6route; + } + return NULL; +} + +static uint8_t +convert_ip6_netmask_to_depth(uint8_t *netmask) +{ + uint8_t setbits = 0; + uint8_t mask; + int i; + + for (i = 0; i < ETHDEV_IPV6_ADDR_LEN; i++) { + mask = netmask[i]; + while (mask & 0x80) { + mask = mask << 1; + setbits++; + } + } + + return setbits; +} + +static int +route_ip6_add(struct route_ipv6_config *route) +{ + int j; + + struct route_ipv6_config *ipv6route; + + ipv6route = find_route6_entry(route); + if (!ipv6route) { + ipv6route = malloc(sizeof(struct route_ipv6_config)); + if (!ipv6route) + return -ENOMEM; + } else { + return 0; + } + + for (j = 0; j < ETHDEV_IPV6_ADDR_LEN; j++) { + ipv6route->ip[j] = route->ip[j]; + ipv6route->mask[j] = route->mask[j]; + ipv6route->gateway[j] = route->gateway[j]; + } + ipv6route->is_used = true; + + return 0; +} + +int +route_ip6_add_to_lookup(void) +{ + struct route_ipv6_config *route = NULL; + int rc = -EINVAL; + uint8_t depth; + int portid; + + TAILQ_FOREACH(route, &route6, next) { + + portid = ethdev_portid_by_ip6(route->gateway, route->mask); + if (portid < 0) { + printf("Invalid portid found to install the route\n"); + return rc; + } + depth = convert_ip6_netmask_to_depth(route->mask); + + rc = rte_node_ip6_route_add(route->ip, depth, portid, + RTE_NODE_IP6_LOOKUP_NEXT_REWRITE); + if (rc < 0) + return rc; + } + + return 0; +} + +static void +cli_ipv6_lookup_help(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + size_t len; + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, "\n%s\n%s\n", + "--------------------------- ipv6_lookup command help ---------------------------", + cmd_ipv6_lookup_help); + + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; +} + +static void +cli_ipv6_lookup(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ip6_lookup_cmd_tokens *res = parsed_result; + struct route_ipv6_config config; + int rc = -EINVAL; + + if (parser_ip6_read(config.ip, res->ip)) { + printf(MSG_ARG_INVALID, "ipv6"); + return; + } + + if (parser_ip6_read(config.mask, res->mask)) { + printf(MSG_ARG_INVALID, "netmask"); + return; + } + + if (parser_ip6_read(config.gateway, res->via_ip)) { + printf(MSG_ARG_INVALID, "gateway ip"); + return; + } + + rc = route_ip6_add(&config); + if (rc) + printf(MSG_CMD_FAIL, res->cmd); +} + +cmdline_parse_token_string_t ip6_lookup_cmd = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, cmd, "ipv6_lookup"); +cmdline_parse_token_string_t ip6_lookup_route = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, route, "route"); +cmdline_parse_token_string_t ip6_lookup_add = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, add, "add"); +cmdline_parse_token_string_t ip6_lookup_ip6 = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, ip6, "ipv6"); +cmdline_parse_token_string_t ip6_lookup_ip = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, ip, NULL); +cmdline_parse_token_string_t ip6_lookup_netmask = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, netmask, "netmask"); +cmdline_parse_token_string_t ip6_lookup_mask = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, mask, NULL); +cmdline_parse_token_string_t ip6_lookup_via = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, via, "via"); +cmdline_parse_token_string_t ip6_lookup_via_ip = + TOKEN_STRING_INITIALIZER(struct ip6_lookup_cmd_tokens, via_ip, NULL); + +cmdline_parse_inst_t ipv6_lookup_cmd_ctx = { + .f = cli_ipv6_lookup, + .data = NULL, + .help_str = cmd_ipv6_lookup_help, + .tokens = { + (void *)&ip6_lookup_cmd, + (void *)&ip6_lookup_route, + (void *)&ip6_lookup_add, + (void *)&ip6_lookup_ip6, + (void *)&ip6_lookup_ip, + (void *)&ip6_lookup_netmask, + (void *)&ip6_lookup_mask, + (void *)&ip6_lookup_via, + (void *)&ip6_lookup_via_ip, + NULL, + }, +}; + +cmdline_parse_token_string_t ipv6_lookup_help_cmd = + TOKEN_STRING_INITIALIZER(struct ipv6_lookup_help_cmd_tokens, cmd, "help"); +cmdline_parse_token_string_t ipv6_lookup_help_module = + TOKEN_STRING_INITIALIZER(struct ipv6_lookup_help_cmd_tokens, module, "ipv6_lookup"); + +cmdline_parse_inst_t ipv6_lookup_help_cmd_ctx = { + .f = cli_ipv6_lookup_help, + .data = NULL, + .help_str = "", + .tokens = { + (void *)&ipv6_lookup_help_cmd, + (void *)&ipv6_lookup_help_module, + NULL, + }, +}; diff --git a/app/graph/meson.build b/app/graph/meson.build index b993d6375f..6841a25eb6 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -13,6 +13,7 @@ sources = files( 'conn.c', 'ethdev.c', 'ip4_route.c', + 'ip6_route.c', 'main.c', 'mempool.c', 'utils.c', diff --git a/app/graph/route.h b/app/graph/route.h index a44d401d55..0d271d1350 100644 --- a/app/graph/route.h +++ b/app/graph/route.h @@ -8,7 +8,9 @@ #define MAX_ROUTE_ENTRIES 32 extern cmdline_parse_inst_t ipv4_lookup_cmd_ctx; +extern cmdline_parse_inst_t ipv6_lookup_cmd_ctx; extern cmdline_parse_inst_t ipv4_lookup_help_cmd_ctx; +extern cmdline_parse_inst_t ipv6_lookup_help_cmd_ctx; struct route_ipv4_config { TAILQ_ENTRY(route_ipv4_config) next; @@ -20,7 +22,19 @@ struct route_ipv4_config { TAILQ_HEAD(ip4_route, route_ipv4_config); +struct route_ipv6_config { + TAILQ_ENTRY(route_ipv6_config) next; + uint8_t ip[16]; + uint8_t mask[16]; + uint8_t gateway[16]; + bool is_used; +}; + +TAILQ_HEAD(ip6_route, route_ipv6_config); + int route_ip4_add_to_lookup(void); +int route_ip6_add_to_lookup(void); void route_ip4_list_clean(void); +void route_ip6_list_clean(void); #endif From patchwork Tue Sep 19 16:04:49 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131648 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 860ED4260C; Tue, 19 Sep 2023 18:06:42 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 8FEDD427D8; Tue, 19 Sep 2023 18:05:38 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 525C3410ED for ; Tue, 19 Sep 2023 18:05:30 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa2LD012098 for ; Tue, 19 Sep 2023 09:05:29 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=gw26JXuoeES8Xp3q3569+ELcOIWtdHmnlvFH9o/qQAE=; b=dbdc45JpPXXSp2L3d1xTaKvgL9mEAFgBN2+n7RDL7XVUd9n6V1iIQKYFQ9ePJ3izI5Sc 5q/IWDAdGRP9Su8RMSHZEDrDPGER5+5kD7slr8c65rFpHjGVwHbiwnrb+qFzD+596rms UiCs79Bf+tWbleVHpaE+ykUAlbZCnBlao8grwv8ZEolHFSbq73OsttspWI7YNouDfY24 KxKbHfFSOtgs6J94ybDkXOkcJR6YFb2IMd2fTfyK+rWhGZjGtgyblUV+Wpqqo4U8zJth GJgr8kZ5Yjy00FV3TZZLo20/MMEaYibmKPp1MOAEzCRbR6zGqw/yn0CI/uDf05GfRN3K fg== Received: from dc5-exch01.marvell.com ([199.233.59.181]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6c-8 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:29 -0700 Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:17 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:17 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 755C43F70A0; Tue, 19 Sep 2023 09:05:15 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 08/14] app/graph: add neigh command line interfaces Date: Tue, 19 Sep 2023 21:34:49 +0530 Message-ID: <20230919160455.1678716-8-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: Ur3mV5dL0jgEV6NfeRrY9kJHYY1lV_P- X-Proofpoint-GUID: Ur3mV5dL0jgEV6NfeRrY9kJHYY1lV_P- X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori It adds neigh module to configure arp/neigh. This module uses ipv4_rewrite and ipv6_rewrite node to write neigh information. Following commands are exposed: - neigh add ipv4 - neigh add ipv6 - help neigh Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/cli.c | 3 + app/graph/ethdev.c | 2 + app/graph/meson.build | 1 + app/graph/module_api.h | 2 + app/graph/neigh.c | 331 +++++++++++++++++++++++++++++++++++++++++ app/graph/neigh.h | 17 +++ app/graph/neigh_priv.h | 49 ++++++ 7 files changed, 405 insertions(+) create mode 100644 app/graph/neigh.c create mode 100644 app/graph/neigh.h create mode 100644 app/graph/neigh_priv.h diff --git a/app/graph/cli.c b/app/graph/cli.c index 7213a91ad2..36338d5173 100644 --- a/app/graph/cli.c +++ b/app/graph/cli.c @@ -34,6 +34,9 @@ cmdline_parse_ctx_t modules_ctx[] = { (cmdline_parse_inst_t *)&ipv4_lookup_help_cmd_ctx, (cmdline_parse_inst_t *)&ipv6_lookup_cmd_ctx, (cmdline_parse_inst_t *)&ipv6_lookup_help_cmd_ctx, + (cmdline_parse_inst_t *)&neigh_v4_cmd_ctx, + (cmdline_parse_inst_t *)&neigh_v6_cmd_ctx, + (cmdline_parse_inst_t *)&neigh_help_cmd_ctx, NULL, }; diff --git a/app/graph/ethdev.c b/app/graph/ethdev.c index 0a4eb7be4f..fc0bd8f05f 100644 --- a/app/graph/ethdev.c +++ b/app/graph/ethdev.c @@ -162,6 +162,8 @@ ethdev_stop(void) ethdev_list_clean(); route_ip4_list_clean(); route_ip6_list_clean(); + neigh4_list_clean(); + neigh6_list_clean(); printf("Bye...\n"); } diff --git a/app/graph/meson.build b/app/graph/meson.build index 6841a25eb6..c0b8418b89 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -16,5 +16,6 @@ sources = files( 'ip6_route.c', 'main.c', 'mempool.c', + 'neigh.c', 'utils.c', ) diff --git a/app/graph/module_api.h b/app/graph/module_api.h index da049a1faa..660d0d2f34 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -12,8 +12,10 @@ #include "conn.h" #include "ethdev.h" #include "mempool.h" +#include "neigh.h" #include "route.h" #include "utils.h" + /* * Externs */ diff --git a/app/graph/neigh.c b/app/graph/neigh.c new file mode 100644 index 0000000000..f59d61152b --- /dev/null +++ b/app/graph/neigh.c @@ -0,0 +1,331 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include "neigh_priv.h" +#include "module_api.h" + +static const char +cmd_neigh_v4_help[] = "neigh add ipv4 "; + +static const char +cmd_neigh_v6_help[] = "neigh add ipv6 "; + +struct neigh4_head neigh4 = TAILQ_HEAD_INITIALIZER(neigh4); +struct neigh6_head neigh6 = TAILQ_HEAD_INITIALIZER(neigh6); + +void +neigh4_list_clean(void) +{ + struct neigh_ipv4_config *v4_config; + + while (!TAILQ_EMPTY(&neigh4)) { + v4_config = TAILQ_FIRST(&neigh4); + TAILQ_REMOVE(&neigh4, v4_config, next); + } +} + +void +neigh6_list_clean(void) +{ + struct neigh_ipv6_config *v6_config; + + while (!TAILQ_EMPTY(&neigh6)) { + v6_config = TAILQ_FIRST(&neigh6); + TAILQ_REMOVE(&neigh6, v6_config, next); + } +} + +static struct neigh_ipv4_config * +find_neigh4_entry(uint32_t ip, uint64_t mac) +{ + struct neigh_ipv4_config *v4_config; + + TAILQ_FOREACH(v4_config, &neigh4, next) { + if ((v4_config->ip == ip) && (v4_config->mac == mac)) + return v4_config; + } + return NULL; +} + +static struct neigh_ipv6_config * +find_neigh6_entry(uint8_t *ip, uint64_t mac) +{ + struct neigh_ipv6_config *v6_config; + + TAILQ_FOREACH(v6_config, &neigh6, next) { + if (!(memcmp(v6_config->ip, ip, 16)) && (v6_config->mac == mac)) + return v6_config; + } + return NULL; +} + +static int +neigh_ip4_add(uint32_t ip, uint64_t mac) +{ + struct neigh_ipv4_config *v4_config; + + v4_config = find_neigh4_entry(ip, mac); + + if (!v4_config) { + v4_config = malloc(sizeof(struct neigh_ipv4_config)); + if (!v4_config) + return -ENOMEM; + } + + v4_config->ip = ip; + v4_config->mac = mac; + v4_config->is_used = true; + + TAILQ_INSERT_TAIL(&neigh4, v4_config, next); + return 0; +} + +static int +neigh_ip6_add(uint8_t *ip, uint64_t mac) +{ + int j; + struct neigh_ipv6_config *v6_config; + + v6_config = find_neigh6_entry(ip, mac); + + if (!v6_config) { + v6_config = malloc(sizeof(struct neigh_ipv6_config)); + if (!v6_config) + return -ENOMEM; + } + + for (j = 0; j < ETHDEV_IPV6_ADDR_LEN; j++) + v6_config->ip[j] = ip[j]; + + v6_config->mac = mac; + v6_config->is_used = true; + + TAILQ_INSERT_TAIL(&neigh6, v6_config, next); + return 0; +} + +int +neigh_ip4_add_to_rewrite(void) +{ + uint8_t data[2 * RTE_ETHER_ADDR_LEN]; + uint8_t len = 2 * RTE_ETHER_ADDR_LEN; + struct rte_ether_addr smac = {0}; + struct neigh_ipv4_config *neigh; + int16_t portid = 0; + int rc; + + TAILQ_FOREACH(neigh, &neigh4, next) { + portid = ethdev_portid_by_ip4(neigh->ip, 0); + if (portid < 0) { + printf("Invalid portid found to add neigh\n"); + return -EINVAL; + } + + memset(data, 0, len); + + /* Copy dst mac */ + rte_memcpy((void *)&data[0], (void *)&neigh->mac, RTE_ETHER_ADDR_LEN); + + /* Copy src mac */ + rc = rte_eth_macaddr_get(portid, &smac); + if (rc < 0) { + printf("Cannot get MAC address: err=%d, port=%d\n", rc, portid); + return rc; + } + + rte_memcpy(&data[RTE_ETHER_ADDR_LEN], smac.addr_bytes, RTE_ETHER_ADDR_LEN); + + rc = rte_node_ip4_rewrite_add(portid, data, len, portid); + if (rc < 0) { + printf("Error in writing rewrite data: err=%d, port=%d\n", rc, portid); + return rc; + } + } + return 0; +} + +int +neigh_ip6_add_to_rewrite(void) +{ + uint8_t data[2 * RTE_ETHER_ADDR_LEN]; + uint8_t len = 2 * RTE_ETHER_ADDR_LEN; + struct rte_ether_addr smac = {0}; + struct neigh_ipv6_config *neigh; + int16_t portid = 0; + int rc; + + + TAILQ_FOREACH(neigh, &neigh6, next) { + + portid = ethdev_portid_by_ip6(neigh->ip, NULL); + if (portid < 0) { + printf("Invalid portid found to add neigh\n"); + return -EINVAL; + } + + memset(data, 0, len); + + /* Copy dst mac */ + rte_memcpy((void *)&data[0], (void *)&neigh->mac, RTE_ETHER_ADDR_LEN); + + /* Copy src mac */ + rc = rte_eth_macaddr_get(portid, &smac); + if (rc < 0) { + printf("Cannot get MAC address: err=%d, port=%d\n", + rc, portid); + return rc; + } + + rte_memcpy(&data[RTE_ETHER_ADDR_LEN], smac.addr_bytes, RTE_ETHER_ADDR_LEN); + + rc = rte_node_ip6_rewrite_add(portid, data, len, portid); + if (rc < 0) { + printf("Error in writing rewrite data: err=%d, port=%d\n", rc, portid); + return rc; + } + } + + return 0; +} + +static void +cli_neigh_v4(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct neigh_v4_cmd_tokens *res = parsed_result; + int rc = -EINVAL; + uint64_t mac; + uint32_t ip; + + if (parser_ip4_read(&ip, res->ip)) { + printf(MSG_ARG_INVALID, "ip"); + return; + } + + if (parser_mac_read(&mac, res->mac)) { + printf(MSG_ARG_INVALID, "mac"); + return; + } + + rc = neigh_ip4_add(ip, mac); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +static void +cli_neigh_v6(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct neigh_v6_cmd_tokens *res = parsed_result; + uint8_t ip[ETHDEV_IPV6_ADDR_LEN]; + int rc = -EINVAL; + uint64_t mac; + + if (parser_ip6_read(ip, res->ip)) { + printf(MSG_ARG_INVALID, "ip"); + return; + } + + if (parser_mac_read(&mac, res->mac)) { + printf(MSG_ARG_INVALID, "mac"); + return; + } + + rc = neigh_ip6_add(ip, mac); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +static void +cli_neigh_help(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + size_t len; + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, "\n%s\n%s\n%s\n", + "--------------------------- neigh command help ---------------------------", + cmd_neigh_v4_help, cmd_neigh_v6_help); + + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; +} + +cmdline_parse_token_string_t neigh_v4_cmd = + TOKEN_STRING_INITIALIZER(struct neigh_v4_cmd_tokens, cmd, "neigh"); +cmdline_parse_token_string_t neigh_v4_add = + TOKEN_STRING_INITIALIZER(struct neigh_v4_cmd_tokens, add, "add"); +cmdline_parse_token_string_t neigh_v4_ip4 = + TOKEN_STRING_INITIALIZER(struct neigh_v4_cmd_tokens, ip4, "ipv4"); +cmdline_parse_token_string_t neigh_v4_ip = + TOKEN_STRING_INITIALIZER(struct neigh_v4_cmd_tokens, ip, NULL); +cmdline_parse_token_string_t neigh_v4_mac = + TOKEN_STRING_INITIALIZER(struct neigh_v4_cmd_tokens, mac, NULL); + +cmdline_parse_inst_t neigh_v4_cmd_ctx = { + .f = cli_neigh_v4, + .data = NULL, + .help_str = cmd_neigh_v4_help, + .tokens = { + (void *)&neigh_v4_cmd, + (void *)&neigh_v4_add, + (void *)&neigh_v4_ip4, + (void *)&neigh_v4_ip, + (void *)&neigh_v4_mac, + NULL, + }, +}; + +cmdline_parse_token_string_t neigh_v6_cmd = + TOKEN_STRING_INITIALIZER(struct neigh_v6_cmd_tokens, cmd, "neigh"); +cmdline_parse_token_string_t neigh_v6_add = + TOKEN_STRING_INITIALIZER(struct neigh_v6_cmd_tokens, add, "add"); +cmdline_parse_token_string_t neigh_v6_ip6 = + TOKEN_STRING_INITIALIZER(struct neigh_v6_cmd_tokens, ip6, "ipv6"); +cmdline_parse_token_string_t neigh_v6_ip = + TOKEN_STRING_INITIALIZER(struct neigh_v6_cmd_tokens, ip, NULL); +cmdline_parse_token_string_t neigh_v6_mac = + TOKEN_STRING_INITIALIZER(struct neigh_v6_cmd_tokens, mac, NULL); + +cmdline_parse_inst_t neigh_v6_cmd_ctx = { + .f = cli_neigh_v6, + .data = NULL, + .help_str = cmd_neigh_v6_help, + .tokens = { + (void *)&neigh_v6_cmd, + (void *)&neigh_v6_add, + (void *)&neigh_v6_ip6, + (void *)&neigh_v6_ip, + (void *)&neigh_v6_mac, + NULL, + }, +}; + +cmdline_parse_token_string_t neigh_help_cmd = + TOKEN_STRING_INITIALIZER(struct neigh_help_cmd_tokens, cmd, "help"); +cmdline_parse_token_string_t neigh_help_module = + TOKEN_STRING_INITIALIZER(struct neigh_help_cmd_tokens, module, "neigh"); + +cmdline_parse_inst_t neigh_help_cmd_ctx = { + .f = cli_neigh_help, + .data = NULL, + .help_str = "", + .tokens = { + (void *)&neigh_help_cmd, + (void *)&neigh_help_module, + NULL, + }, +}; diff --git a/app/graph/neigh.h b/app/graph/neigh.h new file mode 100644 index 0000000000..928981fc31 --- /dev/null +++ b/app/graph/neigh.h @@ -0,0 +1,17 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_NEIGH_H +#define APP_GRAPH_NEIGH_H + +extern cmdline_parse_inst_t neigh_v4_cmd_ctx; +extern cmdline_parse_inst_t neigh_v6_cmd_ctx; +extern cmdline_parse_inst_t neigh_help_cmd_ctx; + +void neigh4_list_clean(void); +void neigh6_list_clean(void); +int neigh_ip4_add_to_rewrite(void); +int neigh_ip6_add_to_rewrite(void); + +#endif diff --git a/app/graph/neigh_priv.h b/app/graph/neigh_priv.h new file mode 100644 index 0000000000..0ec9b1510f --- /dev/null +++ b/app/graph/neigh_priv.h @@ -0,0 +1,49 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_NEIGH_PRIV_H +#define APP_GRAPH_NEIGH_PRIV_H + +#define MAX_NEIGH_ENTRIES 32 + +struct neigh_v4_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t add; + cmdline_fixed_string_t ip4; + cmdline_fixed_string_t ip; + cmdline_fixed_string_t mac; +}; + +struct neigh_v6_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t add; + cmdline_fixed_string_t ip6; + cmdline_fixed_string_t ip; + cmdline_fixed_string_t mac; +}; + +struct neigh_help_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t module; +}; + +struct neigh_ipv4_config { + TAILQ_ENTRY(neigh_ipv4_config) next; + uint32_t ip; + uint64_t mac; + bool is_used; +}; + +TAILQ_HEAD(neigh4_head, neigh_ipv4_config); + +struct neigh_ipv6_config { + TAILQ_ENTRY(neigh_ipv6_config) next; + uint8_t ip[16]; + uint64_t mac; + bool is_used; +}; + +TAILQ_HEAD(neigh6_head, neigh_ipv6_config); + +#endif From patchwork Tue Sep 19 16:04:50 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131650 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id C982C4260C; Tue, 19 Sep 2023 18:06:59 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id EC5E3427E0; Tue, 19 Sep 2023 18:05:40 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 64790410FD for ; Tue, 19 Sep 2023 18:05:33 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa2LF012098 for ; Tue, 19 Sep 2023 09:05:32 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=i1u98hSh+lIPLMLg37HNvz27IdwWFEPu7RzYJkHrYk0=; b=O+vSQ45IYDYOZY7se3Yua7YhedUAhBxDitDLbLEVAxOjgp/tYdEwKCnP+Dq6RUMY2bAy /FUouNChusHx08SQ+aiDuJK9nrXFHPaivW6VCxUWoVkcW7lDfUBfjKvduVPP1qFDtEAU c1a3/bohmIaKqA8aJxvLEqTQb6BeYVmUfdqLK6ndmn9BkFAmdIg57NpKHTrN9XdXsy2+ 2Qys8zHe1SDcNzBUFqe8eGG3U/5uaPJu66nj0r04e92JCt7hRUBts3bE3ePHHYDmwX0W K1LC7PL8myrgHiARRjbtQmSUTquCXn396+GCqLjNh+405zZVNUTOxZhIEjiujkWG7/fY Eg== Received: from dc5-exch01.marvell.com ([199.233.59.181]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6c-9 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:29 -0700 Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:19 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:19 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 4E2EC3F70EF; Tue, 19 Sep 2023 09:05:17 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 09/14] app/graph: add ethdev_rx command line interfaces Date: Tue, 19 Sep 2023 21:34:50 +0530 Message-ID: <20230919160455.1678716-9-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: i7j-w-klEBa2zQfkglNkaGa8Vdjutvuv X-Proofpoint-GUID: i7j-w-klEBa2zQfkglNkaGa8Vdjutvuv X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Rakesh Kudurumalla It adds ethdev_rx module to create port-queue-core mapping. Mapping will be used to launch graph worker thread and dequeue packets on mentioned core from desired port/queue. Following commands are exposed: - ethdev_rx map port queue core - help ethdev_rx Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/cli.c | 2 + app/graph/ethdev_rx.c | 155 +++++++++++++++++++++++++++++++++++++ app/graph/ethdev_rx.h | 37 +++++++++ app/graph/ethdev_rx_priv.h | 39 ++++++++++ app/graph/meson.build | 1 + app/graph/module_api.h | 1 + 6 files changed, 235 insertions(+) create mode 100644 app/graph/ethdev_rx.c create mode 100644 app/graph/ethdev_rx.h create mode 100644 app/graph/ethdev_rx_priv.h diff --git a/app/graph/cli.c b/app/graph/cli.c index 36338d5173..e947f61ee4 100644 --- a/app/graph/cli.c +++ b/app/graph/cli.c @@ -30,6 +30,8 @@ cmdline_parse_ctx_t modules_ctx[] = { (cmdline_parse_inst_t *)ðdev_ip6_cmd_ctx, (cmdline_parse_inst_t *)ðdev_cmd_ctx, (cmdline_parse_inst_t *)ðdev_help_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_rx_cmd_ctx, + (cmdline_parse_inst_t *)ðdev_rx_help_cmd_ctx, (cmdline_parse_inst_t *)&ipv4_lookup_cmd_ctx, (cmdline_parse_inst_t *)&ipv4_lookup_help_cmd_ctx, (cmdline_parse_inst_t *)&ipv6_lookup_cmd_ctx, diff --git a/app/graph/ethdev_rx.c b/app/graph/ethdev_rx.c new file mode 100644 index 0000000000..8cd1c323e3 --- /dev/null +++ b/app/graph/ethdev_rx.c @@ -0,0 +1,155 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include + +#include +#include +#include +#include +#include + +#include "ethdev_rx_priv.h" +#include "module_api.h" + +static const char +cmd_ethdev_rx_help[] = "ethdev_rx map port queue core "; + +static struct lcore_params lcore_params_array[ETHDEV_RX_LCORE_PARAMS_MAX]; +struct rte_node_ethdev_config ethdev_conf[RTE_MAX_ETHPORTS]; +struct lcore_params *lcore_params = lcore_params_array; +struct lcore_conf lcore_conf[RTE_MAX_LCORE]; +uint16_t nb_lcore_params; + +static void +rx_map_configure(uint8_t port_id, uint32_t queue, uint32_t core) +{ + uint8_t n_rx_queue; + + n_rx_queue = lcore_conf[core].n_rx_queue; + lcore_conf[core].rx_queue_list[n_rx_queue].port_id = port_id; + lcore_conf[core].rx_queue_list[n_rx_queue].queue_id = queue; + lcore_conf[core].n_rx_queue++; +} + +uint8_t +ethdev_rx_num_rx_queues_get(uint16_t port) +{ + int queue = -1; + uint16_t i; + + for (i = 0; i < nb_lcore_params; ++i) { + if (lcore_params[i].port_id == port) { + if (lcore_params[i].queue_id == queue + 1) + queue = lcore_params[i].queue_id; + else + rte_exit(EXIT_FAILURE, + "Queue ids of the port %d must be" + " in sequence and must start with 0\n", + lcore_params[i].port_id); + } + } + + return (uint8_t)(++queue); +} + +static int +ethdev_rx_map_add(char *name, uint32_t queue, uint32_t core) +{ + uint16_t port_id; + int rc; + + if (nb_lcore_params >= ETHDEV_RX_LCORE_PARAMS_MAX) + return -EINVAL; + + rc = rte_eth_dev_get_port_by_name(name, &port_id); + if (rc) + return -EINVAL; + + rx_map_configure(port_id, queue, core); + + lcore_params_array[nb_lcore_params].port_id = port_id; + lcore_params_array[nb_lcore_params].queue_id = queue; + lcore_params_array[nb_lcore_params].lcore_id = core; + nb_lcore_params++; + return 0; +} + +static void +cli_ethdev_rx_help(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + size_t len; + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, "\n%s\n%s\n", + "----------------------------- ethdev_rx command help -----------------------------", + cmd_ethdev_rx_help); + + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; +} + +static void +cli_ethdev_rx(void *parsed_result, __rte_unused struct cmdline *cl, void *data __rte_unused) +{ + struct ethdev_rx_cmd_tokens *res = parsed_result; + int rc = -EINVAL; + + rc = ethdev_rx_map_add(res->dev, res->qid, res->core_id); + if (rc < 0) + printf(MSG_CMD_FAIL, res->cmd); +} + +cmdline_parse_token_string_t ethdev_rx_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_cmd_tokens, cmd, "ethdev_rx"); +cmdline_parse_token_string_t ethdev_rx_map = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_cmd_tokens, map, "map"); +cmdline_parse_token_string_t ethdev_rx_port = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_cmd_tokens, port, "port"); +cmdline_parse_token_string_t ethdev_rx_dev = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_cmd_tokens, dev, NULL); +cmdline_parse_token_string_t ethdev_rx_queue = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_cmd_tokens, queue, "queue"); +cmdline_parse_token_num_t ethdev_rx_qid = + TOKEN_NUM_INITIALIZER(struct ethdev_rx_cmd_tokens, qid, RTE_UINT32); +cmdline_parse_token_string_t ethdev_rx_core = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_cmd_tokens, core, "core"); +cmdline_parse_token_num_t ethdev_rx_core_id = + TOKEN_NUM_INITIALIZER(struct ethdev_rx_cmd_tokens, core_id, RTE_UINT32); + +cmdline_parse_inst_t ethdev_rx_cmd_ctx = { + .f = cli_ethdev_rx, + .data = NULL, + .help_str = cmd_ethdev_rx_help, + .tokens = { + (void *)ðdev_rx_cmd, + (void *)ðdev_rx_map, + (void *)ðdev_rx_port, + (void *)ðdev_rx_dev, + (void *)ðdev_rx_queue, + (void *)ðdev_rx_qid, + (void *)ðdev_rx_core, + (void *)ðdev_rx_core_id, + NULL, + }, +}; + +cmdline_parse_token_string_t ethdev_rx_help_cmd = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_help_cmd_tokens, cmd, "help"); +cmdline_parse_token_string_t ethdev_rx_help_module = + TOKEN_STRING_INITIALIZER(struct ethdev_rx_help_cmd_tokens, module, "ethdev_rx"); + +cmdline_parse_inst_t ethdev_rx_help_cmd_ctx = { + .f = cli_ethdev_rx_help, + .data = NULL, + .help_str = "", + .tokens = { + (void *)ðdev_rx_help_cmd, + (void *)ðdev_rx_help_module, + NULL, + }, +}; diff --git a/app/graph/ethdev_rx.h b/app/graph/ethdev_rx.h new file mode 100644 index 0000000000..8e7b31448c --- /dev/null +++ b/app/graph/ethdev_rx.h @@ -0,0 +1,37 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_ETHDEV_RX_H +#define APP_GRAPH_ETHDEV_RX_H + +#include +#include + +#define ETHDEV_RX_LCORE_PARAMS_MAX 1024 +#define ETHDEV_RX_QUEUE_PER_LCORE_MAX 16 + +struct lcore_rx_queue { + uint16_t port_id; + uint8_t queue_id; + char node_name[RTE_NODE_NAMESIZE]; +}; + +struct lcore_conf { + uint16_t n_rx_queue; + struct lcore_rx_queue rx_queue_list[ETHDEV_RX_QUEUE_PER_LCORE_MAX]; + struct rte_graph *graph; + char name[RTE_GRAPH_NAMESIZE]; + rte_graph_t graph_id; +} __rte_cache_aligned; + +uint8_t ethdev_rx_num_rx_queues_get(uint16_t port); + +extern struct rte_node_ethdev_config ethdev_conf[RTE_MAX_ETHPORTS]; +extern struct lcore_conf lcore_conf[RTE_MAX_LCORE]; +extern cmdline_parse_inst_t ethdev_rx_help_cmd_ctx; +extern cmdline_parse_inst_t ethdev_rx_cmd_ctx; +extern struct lcore_params *lcore_params; +extern uint16_t nb_lcore_params; + +#endif diff --git a/app/graph/ethdev_rx_priv.h b/app/graph/ethdev_rx_priv.h new file mode 100644 index 0000000000..5d155be043 --- /dev/null +++ b/app/graph/ethdev_rx_priv.h @@ -0,0 +1,39 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_ETHDEV_RX_PRIV_H +#define APP_GRAPH_ETHDEV_RX_PRIV_H + +#include + +#include +#include + +#define MAX_RX_QUEUE_PER_PORT 128 +#define MAX_JUMBO_PKT_LEN 9600 +#define NB_SOCKETS 8 + +struct ethdev_rx_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t map; + cmdline_fixed_string_t port; + cmdline_fixed_string_t dev; + cmdline_fixed_string_t queue; + cmdline_fixed_string_t core; + uint32_t core_id; + uint32_t qid; +}; + +struct ethdev_rx_help_cmd_tokens { + cmdline_fixed_string_t cmd; + cmdline_fixed_string_t module; +}; + +struct lcore_params { + uint16_t port_id; + uint8_t queue_id; + uint8_t lcore_id; +} __rte_cache_aligned; + +#endif diff --git a/app/graph/meson.build b/app/graph/meson.build index c0b8418b89..caf2d20735 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -11,6 +11,7 @@ deps += ['bus_pci', 'graph', 'eal', 'lpm', 'ethdev', 'node', 'cmdline'] sources = files( 'cli.c', 'conn.c', + 'ethdev_rx.c', 'ethdev.c', 'ip4_route.c', 'ip6_route.c', diff --git a/app/graph/module_api.h b/app/graph/module_api.h index 660d0d2f34..0a4e383f50 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -11,6 +11,7 @@ #include "cli.h" #include "conn.h" #include "ethdev.h" +#include "ethdev_rx.h" #include "mempool.h" #include "neigh.h" #include "route.h" From patchwork Tue Sep 19 16:04:51 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131651 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id AD2C54260C; Tue, 19 Sep 2023 18:07:10 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id B0A5F4281D; Tue, 19 Sep 2023 18:05:42 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 5977F410D3 for ; Tue, 19 Sep 2023 18:05:35 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa2LG012098 for ; Tue, 19 Sep 2023 09:05:34 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=ShsALMqjSDOJHVKEN6b3exze3cYopY+jYAL8JDGWZBc=; b=C/YbykVeY/oZ18w4oYb+IlldFcn3keWPoGmXB1j8xOzRVgslFgcPy38pCnABlSiUj1R0 IqdkV6TpmVZmb795Env0Vxwxf3JwHqJvzXeScdzkgZTNW0dH+618ay27E7q3BGNpLO2I Sg9C3pVrKymPY83fKA1oU5oHmpKOrATTRKn87YHaG3qsGVJu+/Vu3H+SxQvH+8eYUxDi pjQ/Fw4YXgjBDIDSzAOFiYYZN0we6yFPFOzlpbsfnHza8EbkMvLspMmWxomPkf2Gp0up Q3UhnEjl4X26OMkVc1zjX0nlbLlXv8SAVVJu18FkeQr4TDRF6wzSqNYO2HJZ7ClIDjoX lQ== Received: from dc5-exch01.marvell.com ([199.233.59.181]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6c-10 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:32 -0700 Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:20 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:20 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 2796B3F709B; Tue, 19 Sep 2023 09:05:18 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 10/14] app/graph: add graph command line interfaces Date: Tue, 19 Sep 2023 21:34:51 +0530 Message-ID: <20230919160455.1678716-10-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: iAqzVT7WfvdLOfBIY8I-yuhnn1xP8YDv X-Proofpoint-GUID: iAqzVT7WfvdLOfBIY8I-yuhnn1xP8YDv X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Rakesh Kudurumalla It adds graph module to create a graph for a given usecase like l3fwd. Following commands are exposed: - graph [bsz ] [tmo ] [coremask ] \ model - graph start - graph stats show - help graph Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/cli.c | 4 + app/graph/graph.c | 473 +++++++++++++++++++++++++++++++++++++++++ app/graph/graph.h | 18 ++ app/graph/graph_priv.h | 61 ++++++ app/graph/meson.build | 1 + app/graph/module_api.h | 1 + 6 files changed, 558 insertions(+) create mode 100644 app/graph/graph.c create mode 100644 app/graph/graph.h create mode 100644 app/graph/graph_priv.h diff --git a/app/graph/cli.c b/app/graph/cli.c index e947f61ee4..c43af5925c 100644 --- a/app/graph/cli.c +++ b/app/graph/cli.c @@ -20,6 +20,10 @@ #define MAX_LINE_SIZE 2048 cmdline_parse_ctx_t modules_ctx[] = { + (cmdline_parse_inst_t *)&graph_config_cmd_ctx, + (cmdline_parse_inst_t *)&graph_start_cmd_ctx, + (cmdline_parse_inst_t *)&graph_stats_cmd_ctx, + (cmdline_parse_inst_t *)&graph_help_cmd_ctx, (cmdline_parse_inst_t *)&mempool_config_cmd_ctx, (cmdline_parse_inst_t *)&mempool_help_cmd_ctx, (cmdline_parse_inst_t *)ðdev_show_cmd_ctx, diff --git a/app/graph/graph.c b/app/graph/graph.c new file mode 100644 index 0000000000..d44c5f0464 --- /dev/null +++ b/app/graph/graph.c @@ -0,0 +1,473 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include "graph_priv.h" +#include "module_api.h" + +#define RTE_LOGTYPE_APP_GRAPH RTE_LOGTYPE_USER1 + +static const char +cmd_graph_help[] = "graph bsz tmo coremask " + "model "; + +static const char * const supported_usecases[] = {"l3fwd"}; +struct graph_config graph_config; + +/* Check the link rc of all ports in up to 9s, and print them finally */ +static void +check_all_ports_link_status(uint32_t port_mask) +{ +#define CHECK_INTERVAL 100 /* 100ms */ +#define MAX_CHECK_TIME 90 /* 9s (90 * 100ms) in total */ + char link_rc_text[RTE_ETH_LINK_MAX_STR_LEN]; + uint8_t count, all_ports_up, print_flag = 0; + struct rte_eth_link link; + uint16_t portid; + int rc; + + printf("\nChecking link rc"); + fflush(stdout); + for (count = 0; count <= MAX_CHECK_TIME; count++) { + if (force_quit) + return; + + all_ports_up = 1; + RTE_ETH_FOREACH_DEV(portid) + { + if (force_quit) + return; + + if ((port_mask & (1 << portid)) == 0) + continue; + + memset(&link, 0, sizeof(link)); + rc = rte_eth_link_get_nowait(portid, &link); + if (rc < 0) { + all_ports_up = 0; + if (print_flag == 1) + printf("Port %u link get failed: %s\n", + portid, rte_strerror(-rc)); + continue; + } + + /* Print link rc if flag set */ + if (print_flag == 1) { + rte_eth_link_to_str(link_rc_text, sizeof(link_rc_text), + &link); + printf("Port %d %s\n", portid, link_rc_text); + continue; + } + + /* Clear all_ports_up flag if any link down */ + if (link.link_status == RTE_ETH_LINK_DOWN) { + all_ports_up = 0; + break; + } + } + + /* After finally printing all link rc, get out */ + if (print_flag == 1) + break; + + if (all_ports_up == 0) { + printf("."); + fflush(stdout); + rte_delay_ms(CHECK_INTERVAL); + } + + /* Set the print_flag if all ports up or timeout */ + if (all_ports_up == 1 || count == (MAX_CHECK_TIME - 1)) { + print_flag = 1; + printf("Done\n"); + } + } +} + +static bool +parser_usecases_read(char *usecases) +{ + bool valid = false; + uint32_t i, j = 0; + char *token; + + token = strtok(usecases, ","); + while (token != NULL) { + for (i = 0; i < RTE_DIM(supported_usecases); i++) { + if (strcmp(supported_usecases[i], token) == 0) { + graph_config.usecases[j].enabled = true; + strcpy(graph_config.usecases[j].name, token); + valid = true; + j++; + break; + } + } + token = strtok(NULL, ","); + } + + return valid; +} + +static uint64_t +graph_worker_count_get(void) +{ + uint64_t nb_worker = 0; + uint64_t coremask; + + coremask = graph_config.params.coremask; + while (coremask) { + if (coremask & 0x1) + nb_worker++; + + coremask = (coremask >> 1); + } + + return nb_worker; +} + +static struct rte_node_ethdev_config * +graph_rxtx_node_config_get(uint32_t *num_conf, uint32_t *num_graphs) +{ + uint32_t n_tx_queue, nb_conf = 0, lcore_id; + uint16_t queueid, portid, nb_graphs = 0; + uint8_t nb_rx_queue, queue; + struct lcore_conf *qconf; + + n_tx_queue = graph_worker_count_get(); + if (n_tx_queue > RTE_MAX_ETHPORTS) + n_tx_queue = RTE_MAX_ETHPORTS; + + RTE_ETH_FOREACH_DEV(portid) { + /* Skip ports that are not enabled */ + if ((enabled_port_mask & (1 << portid)) == 0) { + printf("\nSkipping disabled port %d\n", portid); + continue; + } + + nb_rx_queue = ethdev_rx_num_rx_queues_get(portid); + + /* Setup ethdev node config */ + ethdev_conf[nb_conf].port_id = portid; + ethdev_conf[nb_conf].num_rx_queues = nb_rx_queue; + ethdev_conf[nb_conf].num_tx_queues = n_tx_queue; + ethdev_conf[nb_conf].mp = ethdev_mempool_list_by_portid(portid); + ethdev_conf[nb_conf].mp_count = 1; /* Check with pools */ + + nb_conf++; + } + + for (lcore_id = 0; lcore_id < RTE_MAX_LCORE; lcore_id++) { + if (rte_lcore_is_enabled(lcore_id) == 0) + continue; + + qconf = &lcore_conf[lcore_id]; + printf("\nInitializing rx queues on lcore %u ... ", lcore_id); + fflush(stdout); + + /* Init RX queues */ + for (queue = 0; queue < qconf->n_rx_queue; ++queue) { + portid = qconf->rx_queue_list[queue].port_id; + queueid = qconf->rx_queue_list[queue].queue_id; + + /* Add this queue node to its graph */ + snprintf(qconf->rx_queue_list[queue].node_name, RTE_NODE_NAMESIZE, + "ethdev_rx-%u-%u", portid, queueid); + } + if (qconf->n_rx_queue) + nb_graphs++; + } + + printf("\n"); + + ethdev_start(); + check_all_ports_link_status(enabled_port_mask); + + *num_conf = nb_conf; + *num_graphs = nb_graphs; + return ethdev_conf; +} + +static void +graph_stats_print_to_file(void) +{ + struct rte_graph_cluster_stats_param s_param; + struct rte_graph_cluster_stats *stats; + const char *pattern = "worker_*"; + FILE *fp = NULL; + size_t sz, len; + + /* Prepare stats object */ + fp = fopen("/tmp/graph_stats.txt", "w+"); + memset(&s_param, 0, sizeof(s_param)); + s_param.f = fp; + s_param.socket_id = SOCKET_ID_ANY; + s_param.graph_patterns = &pattern; + s_param.nb_graph_patterns = 1; + + stats = rte_graph_cluster_stats_create(&s_param); + if (stats == NULL) + rte_exit(EXIT_FAILURE, "Unable to create stats object\n"); + + /* Clear screen and move to top left */ + rte_graph_cluster_stats_get(stats, 0); + rte_delay_ms(1E3); + + fseek(fp, 0L, SEEK_END); + sz = ftell(fp); + fseek(fp, 0L, SEEK_SET); + + len = strlen(conn->msg_out); + conn->msg_out += len; + + sz = fread(conn->msg_out, sizeof(char), sz, fp); + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; + rte_graph_cluster_stats_destroy(stats); + + fclose(fp); +} + +static void +cli_graph_stats(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + graph_stats_print_to_file(); +} + +static void +cli_graph_start(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + struct rte_node_ethdev_config *conf; + uint32_t nb_graphs = 0, nb_conf, i; + + conf = graph_rxtx_node_config_get(&nb_conf, &nb_graphs); + for (i = 0; i < MAX_GRAPH_USECASES; i++) { + if (!strcmp(graph_config.usecases[i].name, "l3fwd")) { + if (graph_config.usecases[i].enabled) { + RTE_SET_USED(conf); + break; + } + } + } +} + +static int +graph_config_add(char *usecases, struct graph_config *config) +{ + if (!parser_usecases_read(usecases)) + return -EINVAL; + + graph_config.params.bsz = config->params.bsz; + graph_config.params.tmo = config->params.tmo; + graph_config.params.coremask = config->params.coremask; + graph_config.model = config->model; + + return 0; +} + +int +graph_walk_start(void *conf) +{ + struct lcore_conf *qconf; + struct rte_graph *graph; + uint32_t lcore_id; + + RTE_SET_USED(conf); + + lcore_id = rte_lcore_id(); + qconf = &lcore_conf[lcore_id]; + graph = qconf->graph; + + if (!graph) { + RTE_LOG(INFO, APP_GRAPH, "Lcore %u has nothing to do\n", lcore_id); + return 0; + } + + RTE_LOG(INFO, APP_GRAPH, "Entering main loop on lcore %u, graph %s(%p)\n", lcore_id, + qconf->name, graph); + + while (likely(!force_quit)) + rte_graph_walk(graph); + + return 0; +} + +void +graph_stats_print(void) +{ + const char topLeft[] = {27, '[', '1', ';', '1', 'H', '\0'}; + const char clr[] = {27, '[', '2', 'J', '\0'}; + struct rte_graph_cluster_stats_param s_param; + struct rte_graph_cluster_stats *stats; + const char *pattern = "worker_*"; + + /* Prepare stats object */ + memset(&s_param, 0, sizeof(s_param)); + s_param.f = stdout; + s_param.socket_id = SOCKET_ID_ANY; + s_param.graph_patterns = &pattern; + s_param.nb_graph_patterns = 1; + + stats = rte_graph_cluster_stats_create(&s_param); + if (stats == NULL) + rte_exit(EXIT_FAILURE, "Unable to create stats object\n"); + + while (!force_quit) { + /* Clear screen and move to top left */ + printf("%s%s", clr, topLeft); + rte_graph_cluster_stats_get(stats, 0); + rte_delay_ms(1E3); + } + + rte_graph_cluster_stats_destroy(stats); +} + +static void +cli_graph(void *parsed_result, __rte_unused struct cmdline *cl, __rte_unused void *data) +{ + struct graph_config_cmd_tokens *res = parsed_result; + struct graph_config config; + char *model_name; + uint8_t model; + int rc; + + model_name = res->model_name; + if (strcmp(model_name, "default") == 0) { + model = GRAPH_MODEL_RTC; + } else if (strcmp(model_name, "rtc") == 0) { + model = GRAPH_MODEL_RTC; + } else if (strcmp(model_name, "mcd") == 0) { + model = GRAPH_MODEL_MCD; + } else { + printf(MSG_ARG_NOT_FOUND, "model arguments"); + return; + } + + config.params.bsz = res->size; + config.params.tmo = res->ns; + config.params.coremask = res->mask; + config.model = model; + rc = graph_config_add(res->usecase, &config); + if (rc < 0) + printf(MSG_CMD_FAIL, "graph"); +} + +static void +cli_graph_help(__rte_unused void *parsed_result, __rte_unused struct cmdline *cl, + __rte_unused void *data) +{ + size_t len; + + len = strlen(conn->msg_out); + conn->msg_out += len; + snprintf(conn->msg_out, conn->msg_out_len_max, "\n%s\n%s\n%s\n", + "----------------------------- graph command help -----------------------------", + cmd_graph_help, "graph start"); + + len = strlen(conn->msg_out); + conn->msg_out_len_max -= len; +} + +cmdline_parse_token_string_t graph_display_graph = + TOKEN_STRING_INITIALIZER(struct graph_stats_cmd_tokens, graph, "graph"); +cmdline_parse_token_string_t graph_display_stats = + TOKEN_STRING_INITIALIZER(struct graph_stats_cmd_tokens, stats, "stats"); +cmdline_parse_token_string_t graph_display_show = + TOKEN_STRING_INITIALIZER(struct graph_stats_cmd_tokens, show, "show"); + +cmdline_parse_inst_t graph_stats_cmd_ctx = { + .f = cli_graph_stats, + .data = NULL, + .help_str = "graph stats show", + .tokens = { + (void *)&graph_display_graph, + (void *)&graph_display_stats, + (void *)&graph_display_show, + NULL, + }, +}; + +cmdline_parse_token_string_t graph_config_start_graph = + TOKEN_STRING_INITIALIZER(struct graph_start_cmd_tokens, graph, "graph"); +cmdline_parse_token_string_t graph_config_start = + TOKEN_STRING_INITIALIZER(struct graph_start_cmd_tokens, start, "start"); + +cmdline_parse_inst_t graph_start_cmd_ctx = { + .f = cli_graph_start, + .data = NULL, + .help_str = "graph start", + .tokens = { + (void *)&graph_config_start_graph, + (void *)&graph_config_start, + NULL, + }, +}; + +cmdline_parse_token_string_t graph_config_add_graph = + TOKEN_STRING_INITIALIZER(struct graph_config_cmd_tokens, graph, "graph"); +cmdline_parse_token_string_t graph_config_add_usecase = + TOKEN_STRING_INITIALIZER(struct graph_config_cmd_tokens, usecase, NULL); +cmdline_parse_token_string_t graph_config_add_coremask = + TOKEN_STRING_INITIALIZER(struct graph_config_cmd_tokens, coremask, "coremask"); +cmdline_parse_token_num_t graph_config_add_mask = + TOKEN_NUM_INITIALIZER(struct graph_config_cmd_tokens, mask, RTE_UINT64); +cmdline_parse_token_string_t graph_config_add_bsz = + TOKEN_STRING_INITIALIZER(struct graph_config_cmd_tokens, bsz, "bsz"); +cmdline_parse_token_num_t graph_config_add_size = + TOKEN_NUM_INITIALIZER(struct graph_config_cmd_tokens, size, RTE_UINT16); +cmdline_parse_token_string_t graph_config_add_tmo = + TOKEN_STRING_INITIALIZER(struct graph_config_cmd_tokens, tmo, "tmo"); +cmdline_parse_token_num_t graph_config_add_ns = + TOKEN_NUM_INITIALIZER(struct graph_config_cmd_tokens, ns, RTE_UINT64); +cmdline_parse_token_string_t graph_config_add_model = + TOKEN_STRING_INITIALIZER(struct graph_config_cmd_tokens, model, "model"); +cmdline_parse_token_string_t graph_config_add_model_name = + TOKEN_STRING_INITIALIZER(struct graph_config_cmd_tokens, model_name, "rtc#mcd#default"); + +cmdline_parse_inst_t graph_config_cmd_ctx = { + .f = cli_graph, + .data = NULL, + .help_str = cmd_graph_help, + .tokens = { + (void *)&graph_config_add_graph, + (void *)&graph_config_add_usecase, + (void *)&graph_config_add_coremask, + (void *)&graph_config_add_mask, + (void *)&graph_config_add_bsz, + (void *)&graph_config_add_size, + (void *)&graph_config_add_tmo, + (void *)&graph_config_add_ns, + (void *)&graph_config_add_model, + (void *)&graph_config_add_model_name, + NULL, + }, +}; + +cmdline_parse_token_string_t graph_help_cmd = + TOKEN_STRING_INITIALIZER(struct graph_help_cmd_tokens, help, "help"); +cmdline_parse_token_string_t graph_help_graph = + TOKEN_STRING_INITIALIZER(struct graph_help_cmd_tokens, graph, "graph"); + +cmdline_parse_inst_t graph_help_cmd_ctx = { + .f = cli_graph_help, + .data = NULL, + .help_str = "", + .tokens = { + (void *)&graph_help_cmd, + (void *)&graph_help_graph, + NULL, + }, +}; diff --git a/app/graph/graph.h b/app/graph/graph.h new file mode 100644 index 0000000000..f431ae10d2 --- /dev/null +++ b/app/graph/graph.h @@ -0,0 +1,18 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_H +#define APP_GRAPH_H + +#include + +extern cmdline_parse_inst_t graph_config_cmd_ctx; +extern cmdline_parse_inst_t graph_start_cmd_ctx; +extern cmdline_parse_inst_t graph_stats_cmd_ctx; +extern cmdline_parse_inst_t graph_help_cmd_ctx; + +int graph_walk_start(void *conf); +void graph_stats_print(void); + +#endif diff --git a/app/graph/graph_priv.h b/app/graph/graph_priv.h new file mode 100644 index 0000000000..c61e20672a --- /dev/null +++ b/app/graph/graph_priv.h @@ -0,0 +1,61 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_PRIV_H +#define APP_GRAPH_PRIV_H + +#define MAX_GRAPH_USECASES 32 + +struct graph_help_cmd_tokens { + cmdline_fixed_string_t help; + cmdline_fixed_string_t graph; +}; + +struct graph_start_cmd_tokens { + cmdline_fixed_string_t graph; + cmdline_fixed_string_t start; +}; + +struct graph_stats_cmd_tokens { + cmdline_fixed_string_t show; + cmdline_fixed_string_t graph; + cmdline_fixed_string_t stats; +}; + +struct graph_config_cmd_tokens { + cmdline_fixed_string_t graph; + cmdline_fixed_string_t usecase; + cmdline_fixed_string_t bsz; + cmdline_fixed_string_t tmo; + cmdline_fixed_string_t coremask; + cmdline_fixed_string_t model; + cmdline_fixed_string_t model_name; + uint16_t size; + uint64_t ns; + uint64_t mask; +}; + +enum graph_model { + GRAPH_MODEL_RTC = 0x01, + GRAPH_MODEL_MCD = 0x02, +}; + +struct usecases { + char name[32]; + bool enabled; +}; + +struct usecase_params { + uint64_t coremask; + uint32_t bsz; + uint32_t tmo; +}; + +struct graph_config { + struct usecases usecases[MAX_GRAPH_USECASES]; + struct usecase_params params; + enum graph_model model; +}; + +#endif diff --git a/app/graph/meson.build b/app/graph/meson.build index caf2d20735..6292fc9684 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -13,6 +13,7 @@ sources = files( 'conn.c', 'ethdev_rx.c', 'ethdev.c', + 'graph.c', 'ip4_route.c', 'ip6_route.c', 'main.c', diff --git a/app/graph/module_api.h b/app/graph/module_api.h index 0a4e383f50..8417c2d3dd 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -12,6 +12,7 @@ #include "conn.h" #include "ethdev.h" #include "ethdev_rx.h" +#include "graph.h" #include "mempool.h" #include "neigh.h" #include "route.h" From patchwork Tue Sep 19 16:04:52 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131646 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 66F374260C; Tue, 19 Sep 2023 18:06:23 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 0E5D241141; Tue, 19 Sep 2023 18:05:36 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 9DE5240EF0 for ; Tue, 19 Sep 2023 18:05:28 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02O012050 for ; Tue, 19 Sep 2023 09:05:27 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=H7P/oHpSfeJIy0pS7edw3I7juriDhD4MuAYnzAxXAyg=; b=g0la+a2V8jr/W9nNKU3jLiSgQsvGFeVWUh8qiLBu8xBtRqpaeJicC5oSO5Hztfp7RRnb yBvt3AJFROnyp1XbMfgBts3vPL5+3qLLDEN30FK2Jb+xqcShgd8eYJLWjqYE4mA7PpqU eBC/C7ejp8V2g8DOr1ImwLsQhbw7Z1nyCI/+wT18OxPF3iqtLTqANNBNO43z7KCc+4BC EQjY0fop13NLi0ZYlvWvrkTqal21tPOls1NT/gAK8ydULu8hjYH8rTMJzRUxpQHhnXBq QQHoZRiwHmkwBZRvsiEGfJ6N+sCzchru/82vYkcQoHX2DFl2Pev6KADSs2TGSwJlWvsg jg== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-10 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:27 -0700 Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:22 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:21 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id F07A73F7099; Tue, 19 Sep 2023 09:05:20 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 11/14] app/graph: add CLI option to enable graph stats Date: Tue, 19 Sep 2023 21:34:52 +0530 Message-ID: <20230919160455.1678716-11-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: ZH8L03oqCk6RxqEW42utOI4sIoCjpWKl X-Proofpoint-GUID: ZH8L03oqCk6RxqEW42utOI4sIoCjpWKl X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori It adds application's command line parameter "--enable-graph-stats" to enable dumping graph stats on console. By default, no graph stats will be printed on console but same can be dumped via telnet session using "graph stats show" command. Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/main.c | 17 ++++++++++++++++- app/graph/module_api.h | 2 ++ 2 files changed, 18 insertions(+), 1 deletion(-) diff --git a/app/graph/main.c b/app/graph/main.c index 6368019712..de583ac0a4 100644 --- a/app/graph/main.c +++ b/app/graph/main.c @@ -18,12 +18,13 @@ volatile bool force_quit; struct conn *conn; -static const char usage[] = "%s EAL_ARGS -- -s SCRIPT [-h HOST] [-p PORT] " +static const char usage[] = "%s EAL_ARGS -- -s SCRIPT [-h HOST] [-p PORT] [--enable-graph-stats] " "[--help]\n"; static struct app_params { struct conn_params conn; char *script_name; + bool enable_graph_stats; } app = { .conn = { .welcome = "\nWelcome!\n\n", @@ -37,6 +38,7 @@ static struct app_params { .msg_handle_arg = NULL, /* set later. */ }, .script_name = NULL, + .enable_graph_stats = false, }; static void @@ -53,6 +55,7 @@ app_args_parse(int argc, char **argv) { struct option lgopts[] = { {"help", 0, 0, 'H'}, + {"enable-graph-stats", 0, 0, 'g'}, }; int h_present, p_present, s_present, n_args, i; char *app_name = argv[0]; @@ -130,6 +133,12 @@ app_args_parse(int argc, char **argv) } break; + case 'g': + app.enable_graph_stats = true; + printf("WARNING! Telnet session can not be accessed with" + "--enable-graph-stats"); + break; + case 'H': default: printf(usage, app_name); @@ -141,6 +150,12 @@ app_args_parse(int argc, char **argv) return 0; } +bool +app_graph_stats_enabled(void) +{ + return app.enable_graph_stats; +} + int main(int argc, char **argv) { diff --git a/app/graph/module_api.h b/app/graph/module_api.h index 8417c2d3dd..9bb4b39edd 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -24,4 +24,6 @@ extern volatile bool force_quit; extern struct conn *conn; +bool app_graph_stats_enabled(void); + #endif From patchwork Tue Sep 19 16:04:53 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131652 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 5A2EC4260C; Tue, 19 Sep 2023 18:07:22 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id B0F7E42D28; Tue, 19 Sep 2023 18:05:44 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 23D1641144 for ; Tue, 19 Sep 2023 18:05:35 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa2LI012098 for ; Tue, 19 Sep 2023 09:05:35 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=97C3KJdKICtCJgMv/NKDUtDnIwYivrSTMurIaBd4yrw=; b=LXFeRgRZsmSi6z/rtc2QEfdwpiPW3PPt3W3fvAF9gqfNK9lFRed+Sk7fFFp/GMxNUiNI mi4BV0UOMnIgs9WUv2l1rm9mvvjsOqSmiapfPCct88tPbIzUfKYtJDfzNS4Xl5u1mzVS nYJgrZIzfTkt+xEsa3dyfPMDx3aR0iD95voR9JYap8wiZVU0nN3w5hoZxvNaUv8sUHT6 L+AcWCgjgdeFY9q38w1S2kUZ1rT1eb7O434vV1EERe89lcZ4stgUfKO5yDDeZwBTR0XS ZKQSKY4oH4TTt70EHAHXlETM3AGGYcBfKHqctpZsoNzGEq02I/VK4yIQSUdGzVGM0qMn MA== Received: from dc5-exch01.marvell.com ([199.233.59.181]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6c-11 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:34 -0700 Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:23 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:23 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id CA1203F709B; Tue, 19 Sep 2023 09:05:22 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 12/14] app/graph: add l3fwd usecase Date: Tue, 19 Sep 2023 21:34:53 +0530 Message-ID: <20230919160455.1678716-12-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: gdO2SW5Y7_uLXA--fOyd61Fi3hZ4viHZ X-Proofpoint-GUID: gdO2SW5Y7_uLXA--fOyd61Fi3hZ4viHZ X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Rakesh Kudurumalla It adds an usecase l3fwd. It contains a dedicated l3fwd.cli file mentioning commands to configure the required resources. Once application successfully parses the l3fwd.cli then a graph is created having below nodes: - ethdev_rx -> pkt_cls - pkt_cls -> ip4_lookup - pkt_cls -> ip6_lookup - pkt_cls -> pkt_drop - ip4_lookup -> ip4_rewrite - ip4_lookup -> pkt_drop - ip6_lookup -> ip6_rewrite - ip6_lookup -> pkt_drop - ip4_rewrite -> ethdev_tx - ip4_rewrite -> pkt_drop - ip6_rewrite -> ethdev_tx - ip6_rewrite -> pkt_drop - ethdev_tx -> pkt_drop Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- app/graph/examples/l3fwd.cli | 87 ++++++++++++++++++++++ app/graph/graph.c | 2 +- app/graph/l3fwd.c | 138 +++++++++++++++++++++++++++++++++++ app/graph/l3fwd.h | 11 +++ app/graph/meson.build | 1 + app/graph/module_api.h | 1 + 6 files changed, 239 insertions(+), 1 deletion(-) create mode 100644 app/graph/examples/l3fwd.cli create mode 100644 app/graph/l3fwd.c create mode 100644 app/graph/l3fwd.h diff --git a/app/graph/examples/l3fwd.cli b/app/graph/examples/l3fwd.cli new file mode 100644 index 0000000000..6b0d9ac770 --- /dev/null +++ b/app/graph/examples/l3fwd.cli @@ -0,0 +1,87 @@ +; SPDX-License-Identifier: BSD-3-Clause +; Copyright(c) 2023 Marvell. + +; +; Graph configuration for given usecase +; +graph l3fwd coremask 0xff bsz 32 tmo 10 model default + +; +; Mempools to be attached with ethdev +; +mempool mempool0 size 8192 buffers 4000 cache 256 numa 0 + +; +; DPDK devices and configuration. +; +; Note: Customize the parameters below to match your setup. +; +ethdev 0002:04:00.0 rxq 1 txq 8 mempool0 +ethdev 0002:05:00.0 rxq 1 txq 8 mempool0 +ethdev 0002:06:00.0 rxq 1 txq 8 mempool0 +ethdev 0002:07:00.0 rxq 1 txq 8 mempool0 +ethdev 0002:04:00.0 mtu 1700 +ethdev 0002:05:00.0 promiscuous on + +; +; IPv4 addresses assigned to DPDK devices +; +ethdev 0002:04:00.0 ip4 addr add 10.0.2.1 netmask 255.255.255.0 +ethdev 0002:05:00.0 ip4 addr add 20.0.2.1 netmask 255.255.255.0 +ethdev 0002:06:00.0 ip4 addr add 30.0.2.1 netmask 255.255.255.0 +ethdev 0002:07:00.0 ip4 addr add 40.0.2.1 netmask 255.255.255.0 + +; +; IPv6 addresses assigned to DPDK devices +; +ethdev 0002:04:00.0 ip6 addr add 52:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4A netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 +ethdev 0002:05:00.0 ip6 addr add 62:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4B netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 +ethdev 0002:06:00.0 ip6 addr add 72:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4C netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 +ethdev 0002:07:00.0 ip6 addr add 82:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4D netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 + +; +; IPv4 routes which are installed to ipv4_lookup node for LPM processing +; +ipv4_lookup route add ipv4 10.0.2.0 netmask 255.255.255.0 via 10.0.2.1 +ipv4_lookup route add ipv4 20.0.2.0 netmask 255.255.255.0 via 20.0.2.1 +ipv4_lookup route add ipv4 30.0.2.0 netmask 255.255.255.0 via 30.0.2.1 +ipv4_lookup route add ipv4 40.0.2.0 netmask 255.255.255.0 via 40.0.2.1 + +; +; IPv6 routes which are installed to ipv6_lookup node for LPM processing +; +ipv6_lookup route add ipv6 52:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4A netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 via 52:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4A +ipv6_lookup route add ipv6 62:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4B netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 via 62:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4B +ipv6_lookup route add ipv6 72:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4C netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 via 72:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4C +ipv6_lookup route add ipv6 82:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4D netmask FF:FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00 via 82:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4D + +; +; Peer MAC and IPv4 address mapping +; +neigh add ipv4 10.0.2.2 52:20:DA:4F:68:70 +neigh add ipv4 20.0.2.2 62:20:DA:4F:68:70 +neigh add ipv4 30.0.2.2 72:20:DA:4F:68:70 +neigh add ipv4 40.0.2.2 82:20:DA:4F:68:70 + +; +; Peer MAC and IPv6 address mapping +; +neigh add ipv6 52:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4A 52:20:DA:4F:68:70 +neigh add ipv6 62:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4B 62:20:DA:4F:68:70 +neigh add ipv6 72:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4C 72:20:DA:4F:68:70 +neigh add ipv6 82:20:DA:4F:68:70:52:20:DA:4F:68:70:52:20:DA:4D 82:20:DA:4F:68:70 + +; +; Port-Queue-Core mapping for ethdev_rx node +; +ethdev_rx map port 0002:04:00.0 queue 0 core 1 +ethdev_rx map port 0002:05:00.0 queue 0 core 2 +ethdev_rx map port 0002:06:00.0 queue 0 core 3 +ethdev_rx map port 0002:07:00.0 queue 0 core 4 + +; +; Graph start command to create graph. +; +; Note: No more command should come after this. +; +graph start diff --git a/app/graph/graph.c b/app/graph/graph.c index d44c5f0464..659ed654bd 100644 --- a/app/graph/graph.c +++ b/app/graph/graph.c @@ -257,7 +257,7 @@ cli_graph_start(__rte_unused void *parsed_result, __rte_unused struct cmdline *c for (i = 0; i < MAX_GRAPH_USECASES; i++) { if (!strcmp(graph_config.usecases[i].name, "l3fwd")) { if (graph_config.usecases[i].enabled) { - RTE_SET_USED(conf); + usecase_l3fwd_configure(conf, nb_conf, nb_graphs); break; } } diff --git a/app/graph/l3fwd.c b/app/graph/l3fwd.c new file mode 100644 index 0000000000..5ab57dfa00 --- /dev/null +++ b/app/graph/l3fwd.c @@ -0,0 +1,138 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include + +#include "module_api.h" + +static char pcap_filename[RTE_GRAPH_PCAP_FILE_SZ]; +static uint64_t packet_to_capture; +static int pcap_trace_enable; + +static int +l3fwd_pattern_configure(void) +{ + /* Graph initialization. 8< */ + static const char * const default_patterns[] = { + "ip4*", + "ethdev_tx-*", + "pkt_drop", + }; + + struct rte_graph_param graph_conf; + const char **node_patterns; + struct lcore_conf *qconf; + uint16_t nb_patterns; + uint8_t lcore_id; + int rc; + + nb_patterns = RTE_DIM(default_patterns); + node_patterns = malloc((ETHDEV_RX_QUEUE_PER_LCORE_MAX + nb_patterns) * + sizeof(*node_patterns)); + if (!node_patterns) + return -ENOMEM; + memcpy(node_patterns, default_patterns, + nb_patterns * sizeof(*node_patterns)); + + memset(&graph_conf, 0, sizeof(graph_conf)); + graph_conf.node_patterns = node_patterns; + + /* Pcap config */ + graph_conf.pcap_enable = pcap_trace_enable; + graph_conf.num_pkt_to_capture = packet_to_capture; + graph_conf.pcap_filename = pcap_filename; + + for (lcore_id = 0; lcore_id < RTE_MAX_LCORE; lcore_id++) { + rte_graph_t graph_id; + rte_edge_t i; + + if (rte_lcore_is_enabled(lcore_id) == 0) + continue; + + qconf = &lcore_conf[lcore_id]; + + /* Skip graph creation if no source exists */ + if (!qconf->n_rx_queue) + continue; + + /* Add rx node patterns of this lcore */ + for (i = 0; i < qconf->n_rx_queue; i++) { + graph_conf.node_patterns[nb_patterns + i] = + qconf->rx_queue_list[i].node_name; + } + + graph_conf.nb_node_patterns = nb_patterns + i; + graph_conf.socket_id = rte_lcore_to_socket_id(lcore_id); + + snprintf(qconf->name, sizeof(qconf->name), "worker_%u", + lcore_id); + + graph_id = rte_graph_create(qconf->name, &graph_conf); + if (graph_id == RTE_GRAPH_ID_INVALID) + rte_exit(EXIT_FAILURE, + "rte_graph_create(): graph_id invalid" + " for lcore %u\n", lcore_id); + + qconf->graph_id = graph_id; + qconf->graph = rte_graph_lookup(qconf->name); + /* >8 End of graph initialization. */ + if (!qconf->graph) + rte_exit(EXIT_FAILURE, + "rte_graph_lookup(): graph %s not found\n", + qconf->name); + } + + rc = route_ip4_add_to_lookup(); + if (rc < 0) + rte_exit(EXIT_FAILURE, "Unable to add v4 route to lookup table\n"); + + rc = route_ip6_add_to_lookup(); + if (rc < 0) + rte_exit(EXIT_FAILURE, "Unable to add v6 route to lookup table\n"); + + rc = neigh_ip4_add_to_rewrite(); + if (rc < 0) + rte_exit(EXIT_FAILURE, "Unable to add v4 to rewrite node\n"); + + rc = neigh_ip6_add_to_rewrite(); + if (rc < 0) + rte_exit(EXIT_FAILURE, "Unable to add v6 to rewrite node\n"); + + /* Launch per-lcore init on every worker lcore */ + rte_eal_mp_remote_launch(graph_walk_start, NULL, SKIP_MAIN); + + /* Accumulate and print stats on main until exit */ + if (rte_graph_has_stats_feature() && app_graph_stats_enabled()) + graph_stats_print(); + + return rc; +} + +int +usecase_l3fwd_configure(struct rte_node_ethdev_config *conf, uint16_t nb_confs, uint16_t nb_graphs) +{ + int rc; + + rc = rte_node_eth_config(conf, nb_confs, nb_graphs); + if (rc) + rte_exit(EXIT_FAILURE, "rte_node_eth_config: err=%d\n", rc); + + rc = l3fwd_pattern_configure(); + if (rc) + rte_exit(EXIT_FAILURE, "l3fwd_pattern_failure: err=%d\n", rc); + + return rc; +} diff --git a/app/graph/l3fwd.h b/app/graph/l3fwd.h new file mode 100644 index 0000000000..e1d23165e6 --- /dev/null +++ b/app/graph/l3fwd.h @@ -0,0 +1,11 @@ +/* SPDX-License-Identifier: BSD-3-Clause + * Copyright(c) 2023 Marvell. + */ + +#ifndef APP_GRAPH_L3FWD_H +#define APP_GRAPH_L3FWD_H + +int usecase_l3fwd_configure(struct rte_node_ethdev_config *conf, uint16_t nb_conf, + uint16_t nb_graphs); + +#endif diff --git a/app/graph/meson.build b/app/graph/meson.build index 6292fc9684..d8434fc90f 100644 --- a/app/graph/meson.build +++ b/app/graph/meson.build @@ -16,6 +16,7 @@ sources = files( 'graph.c', 'ip4_route.c', 'ip6_route.c', + 'l3fwd.c', 'main.c', 'mempool.c', 'neigh.c', diff --git a/app/graph/module_api.h b/app/graph/module_api.h index 9bb4b39edd..73f013143f 100644 --- a/app/graph/module_api.h +++ b/app/graph/module_api.h @@ -13,6 +13,7 @@ #include "ethdev.h" #include "ethdev_rx.h" #include "graph.h" +#include "l3fwd.h" #include "mempool.h" #include "neigh.h" #include "route.h" From patchwork Tue Sep 19 16:04:54 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131649 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id 5EA564260C; Tue, 19 Sep 2023 18:06:51 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id CBC90427DC; Tue, 19 Sep 2023 18:05:39 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 74500410F2 for ; Tue, 19 Sep 2023 18:05:30 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa02Q012050 for ; Tue, 19 Sep 2023 09:05:29 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=XOabzoNY7w+2bse1b4SffYUZX8ZJYRmdld0iHkY9vE4=; b=N03TuRJUImtMXLNfnBLU+cFUppsS/o/k+R4/pdOBVDQQ4ubc0w88GhIRTG9EywD5M1Rh 33qib4I99Y7sQYfkZWB7SGzCCHBXF6RqO3q1xI5lTH/m0Sk/vdMJ4DiTT92EqeQsI3Ba IPyM/IxymJNU1LUk8Sl/+E/AIVBTrSjS8EnQwOBNGAjM9Z3qGZUBXxxVIjZEAX7xOFRI 2yZzvefq0BkOCHkdSEC1BHJWKOv1sEurcAAh38qNQAfhDy/y2BS5sZ/JP/mv1OqOSARZ 1eNw44O5jKDOH6cQ9X21hC/BrbBwf6aohsmxzg/zU2Hg92/FwmKMVPXeZwU11XRnmnkm 3w== Received: from dc5-exch02.marvell.com ([199.233.59.182]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6d-11 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT) for ; Tue, 19 Sep 2023 09:05:28 -0700 Received: from DC5-EXCH01.marvell.com (10.69.176.38) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:25 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:25 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id A14C93F7099; Tue, 19 Sep 2023 09:05:24 -0700 (PDT) From: To: Sunil Kumar Kori , Rakesh Kudurumalla CC: Subject: [PATCH v4 13/14] doc: add graph application user guide Date: Tue, 19 Sep 2023 21:34:54 +0530 Message-ID: <20230919160455.1678716-13-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: pJfIe_tbAzIj3OedrMepE51CVfxGxkR9 X-Proofpoint-GUID: pJfIe_tbAzIj3OedrMepE51CVfxGxkR9 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Rakesh Kudurumalla It adds application user guide with detailed infomration about application's parameter, exposed commands by each module etc. Signed-off-by: Sunil Kumar Kori Signed-off-by: Rakesh Kudurumalla --- doc/guides/tools/graph.rst | 240 +++++++++++++++++++ doc/guides/tools/img/graph-usecase-l3fwd.svg | 210 ++++++++++++++++ doc/guides/tools/index.rst | 1 + 3 files changed, 451 insertions(+) create mode 100644 doc/guides/tools/graph.rst create mode 100644 doc/guides/tools/img/graph-usecase-l3fwd.svg diff --git a/doc/guides/tools/graph.rst b/doc/guides/tools/graph.rst new file mode 100644 index 0000000000..52d732cc88 --- /dev/null +++ b/doc/guides/tools/graph.rst @@ -0,0 +1,240 @@ +.. SPDX-License-Identifier: BSD-3-Clause + Copyright(c) 2023 Marvell. + +dpdk-graph Application +====================== + +The ``dpdk-graph`` tool is a Data Plane Development Kit (DPDK) +application that allows exercising various graph use cases. +This application has a generic framework to add new graph based use cases to +verify functionality. Each use case is defined as a ``.cli`` file. +Based on the input file, application creates a graph to cater the use case. + +Supported Use cases +------------------- + * l3fwd + +Running the Application +----------------------- + +The application has a number of command line options which can be provided in +following syntax + +.. code-block:: console + + dpdk-graph [EAL Options] -- [application options] + +EAL Options +~~~~~~~~~~~ + +Following are the EAL command-line options that can be used in conjunction +with the ``dpdk-graph`` application. +See the DPDK Getting Started Guides for more information on these options. + +* ``-c `` or ``-l `` + + Set the hexadecimal bit mask of the cores to run on. The CORELIST is a + list of cores to be used. + +Application Options +~~~~~~~~~~~~~~~~~~~ + +Following are the application command-line options: + +* ``-h`` + + Set the host IPv4 address over which telnet session can be opened. + It is an optional parameter. Default host address is 0.0.0.0. + +* ``-p`` + + Set the L4 port number over which telnet session can be opened. + It is an optional parameter. Default port is 8086. + +* ``-s`` + + Script name with absolute path which specifies the use case. It is + a mandatory parameter which will be used to create desired graph + for a given use case. + +* ``--enable-graph-stats`` + + Enable graph statistics printing on console. By default graph statistics are disabled. + +* ``--help`` + + Dumps application usage + +Supported CLI commands +---------------------- + +This section provides details on commands which can be used in ``.cli`` +file to express the requested use case configuration. + +.. list-table:: Exposed CLIs + :widths: 40 40 10 10 + :header-rows: 1 + :class: longtable + + * - Command + - Description + - Dynamic + - Optional + * - graph [bsz ] [tmo ] [coremask ] model + - Command to express the desired use case + - No + - No + * - graph start + - Command to start the graph. + This command triggers that no more commands are left to be parsed and graph + initialization can be started now. It must be the last command in ``.cli`` + - No + - No + * - graph stats show + - Command to dump current graph statistics + - Yes + - Yes + * - help graph + - Command to dump graph help message + - Yes + - Yes + * - mempool size buffers cache numa + - Command to create mempool which will be further associated to RxQ to dequeue the packets + - No + - No + * - help mempool + - Command to dump mempool help message + - Yes + - Yes + * - ethdev rxq txq + - Command to create DPDK port with given number of Rx and Tx queues. Also attached + RxQ with given mempool. Each port can have single mempool only i.e. all RxQs will + share the same mempool. + - No + - No + * - ethdev mtu + - Command to configure MTU of DPDK port + - Yes + - Yes + * - ethdev promiscuous + - Command to enable/disable promiscuous mode on DPDK port + - Yes + - Yes + * - ethdev show + - Command to dump current ethdev configuration + - Yes + - Yes + * - ethdev stats + - Command to dump current ethdev statistics + - Yes + - Yes + * - ethdev ip4 addr add netmask + - Command to configure IPv4 address on given PCI device. It is needed if user + wishes to use ``ipv4_lookup`` node + - No + - Yes + * - ethdev ip6 addr add netmask + - Command to configure IPv6 address on given PCI device. It is needed if user + wishes to use ``ipv6_lookup`` node + - No + - Yes + * - help ethdev + - Command to dump ethdev help message + - Yes + - Yes + * - ipv4_lookup route add ipv4 netmask via + - Command to add a route into ``ipv4_lookup`` LPM table. It is needed if user + wishes to route the packets based on LPM lookup table. + - No + - Yes + * - help ipv4_lookup + - Command to dump ipv4_lookup help message + - Yes + - Yes + * - ipv6_lookup route add ipv6 netmask via + - Command to add a route into ``ipv6_lookup`` LPM table. It is needed if user + wishes to route the packets based on LPM6 lookup table. + - No + - Yes + * - help ipv6_lookup + - Command to dump ipv6_lookup help message + - Yes + - Yes + * - neigh add ipv4 + - Command to add a neighbour information into ``ipv4_rewrite`` node. + - No + - Yes + * - neigh add ipv6 + - Command to add a neighbour information into ``ipv6_rewrite`` node. + - No + - Yes + * - help neigh + - Command to dump neigh help message + - Yes + - Yes + * - ethdev_rx map port queue core + - Command to add port-queue-core mapping to ``ethdev_rx`` node. ``ethdev_rx`` + node instance will be pinned on given core and will poll on requested + port/queue pair. + - No + - No + * - help ethdev_rx + - Command to dump ethdev_rx help message + - Yes + - Yes + +Runtime configuration +--------------------- + +Application allows some configuration to be modified at runtime using a telnet session. +Application initiates a telnet server with host address ``0.0.0.0`` and port number ``8086`` +by default. + +if user passes ``-h`` and ``-p`` options while running application then corresponding +IPv4 address and port number will be used for telnet session. + +After successful launch of application, client can connect to application using given +host & port and console will be accessed with prompt ``graph>``. + +Command to access a telnet session + +.. code-block:: console + + telnet + +Example: ``dpdk-graph`` is started with -h 10.28.35.207 and -p 50000 then + +.. code-block:: console + + $ telnet 10.28.35.207 50000 + Trying 10.28.35.207... + Connected to 10.28.35.207. + Escape character is '^]'. + + Welcome! + + graph> + graph> + graph> help ethdev + + ----------------------------- ethdev command help ----------------------------- + ethdev rxq txq + ethdev ip4 addr add netmask + ethdev ip6 addr add netmask + ethdev promiscuous + ethdev mtu + ethdev show + graph> + +Created graph for use case +-------------------------- + +On the successful execution of ``.cli`` file, corresponding graph will be created. +This section mentions the created graph for each use case. + +l3fwd +~~~~~ + +.. _figure_l3fwd_graph: + +.. figure:: img/graph-usecase-l3fwd.* diff --git a/doc/guides/tools/img/graph-usecase-l3fwd.svg b/doc/guides/tools/img/graph-usecase-l3fwd.svg new file mode 100644 index 0000000000..3b991c4cf0 --- /dev/null +++ b/doc/guides/tools/img/graph-usecase-l3fwd.svg @@ -0,0 +1,210 @@ + + + + + + + + + +dpdk_app_graph_l3fwd_nodes_flow + + + +ingress_port + +ingress_port + + + +ethdev_rx + +ethdev_rx + + + +ingress_port->ethdev_rx + + +ingress packet + + + +pkt_cls + +pkt_cls + + + +ethdev_rx->pkt_cls + + + + + +ip4_lookup + +ip4_lookup + + + +pkt_cls->ip4_lookup + + + + + +ip6_lookup + +ip6_lookup + + + +pkt_cls->ip6_lookup + + + + + +pkt_drop + +pkt_drop + + + +pkt_cls->pkt_drop + + + + + +ip4_rewrite + +ip4_rewrite + + + +ip4_lookup->ip4_rewrite + + + + + +ip4_lookup->pkt_drop + + + + + +ip6_rewrite + +ip6_rewrite + + + +ip6_lookup->ip6_rewrite + + + + + +ip6_lookup->pkt_drop + + + + + +ethdev_tx + +ethdev_tx + + + +ip4_rewrite->ethdev_tx + + + + + +ip4_rewrite->pkt_drop + + + + + +ip6_rewrite->ethdev_tx + + + + + +ip6_rewrite->pkt_drop + + + + + +ethdev_tx->pkt_drop + + + + + +egress_port + +egress_port + + + +ethdev_tx->egress_port + + +egress packet + + + diff --git a/doc/guides/tools/index.rst b/doc/guides/tools/index.rst index f2afb1fcc5..4f4dc8b518 100644 --- a/doc/guides/tools/index.rst +++ b/doc/guides/tools/index.rst @@ -23,4 +23,5 @@ DPDK Tools User Guides testeventdev testregex testmldev + graph dts From patchwork Tue Sep 19 16:04:55 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Sunil Kumar Kori X-Patchwork-Id: 131653 X-Patchwork-Delegate: thomas@monjalon.net Return-Path: X-Original-To: patchwork@inbox.dpdk.org Delivered-To: patchwork@inbox.dpdk.org Received: from mails.dpdk.org (mails.dpdk.org [217.70.189.124]) by inbox.dpdk.org (Postfix) with ESMTP id CF5A44260C; Tue, 19 Sep 2023 18:07:29 +0200 (CEST) Received: from mails.dpdk.org (localhost [127.0.0.1]) by mails.dpdk.org (Postfix) with ESMTP id 1A09742D3F; Tue, 19 Sep 2023 18:05:46 +0200 (CEST) Received: from mx0b-0016f401.pphosted.com (mx0a-0016f401.pphosted.com [67.231.148.174]) by mails.dpdk.org (Postfix) with ESMTP id 209C64113C for ; Tue, 19 Sep 2023 18:05:37 +0200 (CEST) Received: from pps.filterd (m0045849.ppops.net [127.0.0.1]) by mx0a-0016f401.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 38JDa2LN012098; Tue, 19 Sep 2023 09:05:37 -0700 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=marvell.com; h=from : to : cc : subject : date : message-id : in-reply-to : references : mime-version : content-transfer-encoding : content-type; s=pfpt0220; bh=Lqtf8suHDZwZjKTj6GA0bxQq7IX45vkvZ0omt7XwmZQ=; b=UoLrm6G+sLnNBJzN+7zcTtU5aiqHkF4hvSPRLs58b5k+3yeWDLVEfG4akb8jkgLImkpd sepn72xSKnd5cSMRrfRNTdlPNUR7296zWXs2qIRSWMgmGCxrZO+c1cxGrIz+wDOBkMqq QI0+iXG3ecQNB6Km8Xrmycvd1oAAlrJ+qHFptVmxmaVJhoGGetATTGk93qzhR4Vq6+gV h+V1F7N+F2wyyx3C/a8BNKOVOoxlX208NPG+fD6TbnpYCK7i3KxLWcJMfpoKFOppLtRc ZVXGAQP5yIyhnvuD4FMBPBr3MH/KJpto/aCTiUEgzB+fvjh1wmCqTHMnBa8GfEc+oJu+ YQ== Received: from dc5-exch01.marvell.com ([199.233.59.181]) by mx0a-0016f401.pphosted.com (PPS) with ESMTPS id 3t7cnq0p6c-15 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-SHA384 bits=256 verify=NOT); Tue, 19 Sep 2023 09:05:37 -0700 Received: from DC5-EXCH02.marvell.com (10.69.176.39) by DC5-EXCH01.marvell.com (10.69.176.38) with Microsoft SMTP Server (TLS) id 15.0.1497.48; Tue, 19 Sep 2023 09:05:27 -0700 Received: from maili.marvell.com (10.69.176.80) by DC5-EXCH02.marvell.com (10.69.176.39) with Microsoft SMTP Server id 15.0.1497.48 via Frontend Transport; Tue, 19 Sep 2023 09:05:27 -0700 Received: from localhost.localdomain (unknown [10.28.34.25]) by maili.marvell.com (Postfix) with ESMTP id 70E183F709B; Tue, 19 Sep 2023 09:05:26 -0700 (PDT) From: To: Thomas Monjalon CC: , Sunil Kumar Kori Subject: [PATCH v4 14/14] maintainers: add maintainers for graph app Date: Tue, 19 Sep 2023 21:34:55 +0530 Message-ID: <20230919160455.1678716-14-skori@marvell.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20230919160455.1678716-1-skori@marvell.com> References: <20230908104907.4060511-1-skori@marvell.com> <20230919160455.1678716-1-skori@marvell.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: tkWhMwRtWisfP_Thctelx2J11pbghg-I X-Proofpoint-GUID: tkWhMwRtWisfP_Thctelx2J11pbghg-I X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.267,Aquarius:18.0.980,Hydra:6.0.601,FMLib:17.11.176.26 definitions=2023-09-19_07,2023-09-19_01,2023-05-22_02 X-BeenThere: dev@dpdk.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: DPDK patches and discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dev-bounces@dpdk.org From: Sunil Kumar Kori Add Sunil Kumar Kori and Rakesh Kudurumalla as maintainers for graph application. Signed-off-by: Sunil Kumar Kori --- MAINTAINERS | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/MAINTAINERS b/MAINTAINERS index 698608cdb2..7f149bd060 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -1806,6 +1806,13 @@ F: dts/ F: devtools/dts-check-format.sh F: doc/guides/tools/dts.rst +Graph application +M: Sunil Kumar Kori +M: Rakesh Kudurumalla +F: app/graph/ +F: doc/guides/tools/graph.rst +F: doc/guides/tools/img/graph-usecase-l3fwd.svg + Other Example Applications --------------------------