From: <jerinj@marvell.com>
To: <dev@dpdk.org>
Cc: <pkapoor@marvell.com>, <ndabilpuram@marvell.com>,
<kirankumark@marvell.com>, <pbhagavatula@marvell.com>,
<pathreya@marvell.com>, <nsaxena@marvell.com>,
<sshankarnara@marvell.com>, <honnappa.nagarahalli@arm.com>,
<thomas@monjalon.net>, <david.marchand@redhat.com>,
<ferruh.yigit@intel.com>, <arybchenko@solarflare.com>,
<ajit.khaparde@broadcom.com>, <xiaolong.ye@intel.com>,
<rasland@mellanox.com>, <maxime.coquelin@redhat.com>,
<akhil.goyal@nxp.com>, <cristian.dumitrescu@intel.com>,
<john.mcnamara@intel.com>, <bruce.richardson@intel.com>,
<anatoly.burakov@intel.com>, <gavin.hu@arm.com>,
<drc@linux.vnet.ibm.com>, <konstantin.ananyev@intel.com>,
<pallavi.kadam@intel.com>, <olivier.matz@6wind.com>,
<gage.eads@intel.com>, <nikhil.rao@intel.com>,
<erik.g.carrillo@intel.com>, <hemant.agrawal@nxp.com>,
<artem.andreev@oktetlabs.ru>, <sthemmin@microsoft.com>,
<shahafs@mellanox.com>, <keith.wiles@intel.com>,
<mattias.ronnblom@ericsson.com>, <jasvinder.singh@intel.com>,
<vladimir.medvedkin@intel.com>, <mdr@ashroe.eu>,
<techboard@dpdk.org>
Subject: [dpdk-dev] [RFC PATCH 3/5] test: add graph functional tests
Date: Fri, 31 Jan 2020 22:31:59 +0530 [thread overview]
Message-ID: <20200131170201.3236153-4-jerinj@marvell.com> (raw)
In-Reply-To: <20200131170201.3236153-1-jerinj@marvell.com>
From: Kiran Kumar K <kirankumark@marvell.com>
Example command to execute the test:
echo "graph_autotest" | sudo ./build/app/test/dpdk-test -c 0x30
Signed-off-by: Kiran Kumar K <kirankumark@marvell.com>
---
app/test/Makefile | 4 +
app/test/meson.build | 1 +
app/test/test_graph.c | 820 ++++++++++++++++++++++++++++++++++++++++++
3 files changed, 825 insertions(+)
create mode 100644 app/test/test_graph.c
diff --git a/app/test/Makefile b/app/test/Makefile
index 57930c00b..e1dbe297e 100644
--- a/app/test/Makefile
+++ b/app/test/Makefile
@@ -220,6 +220,10 @@ SRCS-y += test_event_timer_adapter.c
SRCS-y += test_event_crypto_adapter.c
endif
+ifeq ($(CONFIG_RTE_LIBRTE_GRAPH), y)
+SRCS-y += test_graph.c
+endif
+
ifeq ($(CONFIG_RTE_LIBRTE_RAWDEV),y)
SRCS-y += test_rawdev.c
endif
diff --git a/app/test/meson.build b/app/test/meson.build
index 7d761c8fa..d5d0c2173 100644
--- a/app/test/meson.build
+++ b/app/test/meson.build
@@ -54,6 +54,7 @@ test_sources = files('commands.c',
'test_fib6_perf.c',
'test_func_reentrancy.c',
'test_flow_classify.c',
+ 'test_graph.c',
'test_hash.c',
'test_hash_functions.c',
'test_hash_multiwriter.c',
diff --git a/app/test/test_graph.c b/app/test/test_graph.c
new file mode 100644
index 000000000..16a1373e8
--- /dev/null
+++ b/app/test/test_graph.c
@@ -0,0 +1,820 @@
+/* SPDX-License-Identifier: BSD-3-Clause
+ * Copyright(C) 2020 Marvell International Ltd.
+ */
+#include <stdio.h>
+#include <string.h>
+#include <inttypes.h>
+#include <signal.h>
+#include <unistd.h>
+#include <assert.h>
+
+#include <rte_errno.h>
+#include <rte_graph.h>
+#include <rte_graph_worker.h>
+#include <rte_mbuf.h>
+
+#include "test.h"
+
+
+uint16_t
+test_node_worker_source(struct rte_graph *graph, struct rte_node *node,
+ void **objs, uint16_t nb_objs);
+
+uint16_t
+test_node0_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs);
+
+uint16_t
+test_node1_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs);
+
+uint16_t
+test_node2_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs);
+
+uint16_t
+test_node3_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs);
+
+#define MBUFF_SIZE 512
+#define MAX_NODES 4
+
+static struct rte_mbuf mbuf[MAX_NODES + 1][MBUFF_SIZE];
+static void *mbuf_p[MAX_NODES + 1][MBUFF_SIZE];
+static rte_graph_t graph_id;
+static uint64_t obj_stats[MAX_NODES + 1];
+static uint64_t fn_calls[MAX_NODES + 1];
+
+const char *node_patterns[] = {
+ "test_node_source1",
+ "test_node00",
+ "test_node00-test_node11",
+ "test_node00-test_node22",
+ "test_node00-test_node33",
+};
+
+const char *node_names[] = {
+ "test_node00",
+ "test_node00-test_node11",
+ "test_node00-test_node22",
+ "test_node00-test_node33",
+};
+
+struct test_node_register {
+#define NODE_NAMESIZE 64
+ char name[NODE_NAMESIZE];
+ rte_node_process_t process;
+ uint16_t nb_edges;
+ const char *next_nodes[MAX_NODES];
+};
+
+typedef struct {
+ uint32_t idx;
+ struct test_node_register node;
+} test_node_t;
+
+typedef struct {
+ test_node_t test_node[MAX_NODES];
+} test_main_t;
+
+static test_main_t test_main = {
+ .test_node = {
+ {
+ .node = {
+ .name = "test_node00",
+ .process = test_node0_worker,
+ .nb_edges = 2,
+ .next_nodes = {"test_node00-test_node11",
+ "test_node00-test_node22"},
+ },
+ },
+ {
+ .node = {
+ .name = "test_node11",
+ .process = test_node1_worker,
+ .nb_edges = 1,
+ .next_nodes = {"test_node00-test_node22"},
+ },
+ },
+ {
+ .node = {
+ .name = "test_node22",
+ .process = test_node2_worker,
+ .nb_edges = 1,
+ .next_nodes = {"test_node00-test_node33"},
+ },
+ },
+ {
+ .node = {
+ .name = "test_node33",
+ .process = test_node3_worker,
+ .nb_edges = 1,
+ .next_nodes = {"test_node00"},
+ },
+ },
+ },
+};
+
+static int node_init(const struct rte_graph *graph, struct rte_node *node)
+{
+ RTE_SET_USED(graph);
+
+ *(uint32_t*)node->ctx = node->id;
+
+ return 0;
+}
+
+static struct rte_node_register test_node_source = {
+ .name = "test_node_source1",
+ .process = test_node_worker_source,
+ .flags = RTE_NODE_SOURCE_F,
+ .nb_edges = 2,
+ .init = node_init,
+ .next_nodes = {"test_node00","test_node00-test_node11"},
+};
+RTE_NODE_REGISTER(test_node_source);
+
+static struct rte_node_register test_node0 = {
+ .name = "test_node00",
+ .process = test_node0_worker,
+ .init = node_init,
+};
+RTE_NODE_REGISTER(test_node0);
+
+uint16_t
+test_node_worker_source(struct rte_graph *graph, struct rte_node *node,
+ void **objs, uint16_t nb_objs)
+{
+ uint32_t obj_node0 = rand()%100, obj_node1;
+ test_main_t *tm = &test_main;
+ struct rte_mbuf *data;
+ void **next_stream;
+ rte_node_t next;
+ uint32_t i;
+
+ RTE_SET_USED(objs);
+
+ nb_objs = RTE_GRAPH_BURST_SIZE;
+ obj_node0 = nb_objs * obj_node0 * 0.01;
+ next = 0;
+ next_stream = rte_node_next_stream_get(graph, node, next, obj_node0);
+ for (i = 0; i < obj_node0; i++) {
+ data = &mbuf[0][i];
+ data->udata64 = ((uint64_t)tm->test_node[0].idx << 32) | i;
+ if ((i + 1) == obj_node0)
+ data->udata64 |= (1 << 16);
+ next_stream[i] = &mbuf[0][i];
+ }
+ rte_node_next_stream_put(graph, node, next, obj_node0);
+
+ obj_node1 = nb_objs - obj_node0;
+ next = 1;
+ next_stream = rte_node_next_stream_get(graph, node, next, obj_node1);
+ for (i = 0; i < obj_node1; i++) {
+ data = &mbuf[0][obj_node0 + i];
+ data->udata64 = ((uint64_t)tm->test_node[1].idx << 32) | i;
+ if ((i + 1) == obj_node1)
+ data->udata64 |= (1 << 16);
+ next_stream[i] = &mbuf[0][obj_node0 + i];
+ }
+ rte_node_next_stream_put(graph, node, next, obj_node1);
+
+ obj_stats[0] += nb_objs;
+ fn_calls[0] += 1;
+ return nb_objs;
+}
+
+uint16_t
+test_node0_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs)
+{
+ test_main_t *tm = &test_main;
+
+ if (*(uint32_t*)node->ctx == test_node0.id) {
+ uint32_t obj_node0 = rand()%100, obj_node1;
+ struct rte_mbuf *data;
+ uint8_t second_pass = 0;
+ uint32_t count = 0;
+ uint32_t i;
+
+ obj_stats[1] += nb_objs;
+ fn_calls[1] += 1;
+
+ for (i = 0; i < nb_objs; i++) {
+ data = (struct rte_mbuf*)objs[i];
+ if ((data->udata64 >> 32) != tm->test_node[0].idx) {
+ printf("Data idx miss match at node 0, expected"
+ " = %u got = %u\n",tm->test_node[0].idx,
+ (uint32_t)(data->udata64 >> 32));
+ goto end;
+ }
+
+ if ((data->udata64 & 0xffff) != (i - count)) {
+ printf("Expected buff count miss match at "
+ "node 0\n");
+ goto end;
+ }
+
+ if (data->udata64 & (0x1 << 16))
+ count = i + 1;
+ if (data->udata64 & (0x1 << 17))
+ second_pass = 1;
+ }
+
+ if (count != i) {
+ printf("Count missmatch at node 0\n");
+ goto end;
+ }
+
+ obj_node0 = nb_objs * obj_node0 * 0.01;
+ for (i = 0; i < obj_node0; i++) {
+ data = &mbuf[1][i];
+ data->udata64 = ((uint64_t)tm->test_node[1].idx << 32)
+ | i;
+ if ((i + 1) == obj_node0)
+ data->udata64 |= (1 << 16);
+ if (second_pass)
+ data->udata64 |= (1 << 17);
+ }
+ rte_node_enqueue(graph, node, 0, (void**)&mbuf_p[1][0],
+ obj_node0);
+
+ obj_node1 = nb_objs - obj_node0;
+ for (i = 0; i < obj_node1; i++) {
+ data = &mbuf[1][obj_node0 + i];
+ data->udata64 = ((uint64_t)tm->test_node[2].idx << 32)
+ | i;
+ if ((i + 1) == obj_node1)
+ data->udata64 |= (1 << 16);
+ if (second_pass)
+ data->udata64 |= (1 << 17);
+ }
+ rte_node_enqueue(graph, node, 1,
+ (void**)&mbuf_p[1][obj_node0], obj_node1);
+
+ } else if (*(uint32_t*)node->ctx == tm->test_node[1].idx)
+ test_node1_worker(graph, node, objs, nb_objs);
+ else if (*(uint32_t*)node->ctx == tm->test_node[2].idx)
+ test_node2_worker(graph, node, objs, nb_objs);
+ else if (*(uint32_t*)node->ctx == tm->test_node[3].idx)
+ test_node3_worker(graph, node, objs, nb_objs);
+ else
+ assert(0);
+end:
+ return nb_objs;
+}
+
+uint16_t
+test_node1_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs)
+{
+ test_main_t *tm = &test_main;
+ uint8_t second_pass = 0;
+ uint32_t obj_node0 = 0;
+ struct rte_mbuf *data;
+ uint32_t count = 0;
+ uint32_t i;
+
+ obj_stats[2] += nb_objs;
+ fn_calls[2] += 1;
+ for (i = 0; i < nb_objs; i++) {
+ data = (struct rte_mbuf*)objs[i];
+ if ((data->udata64 >> 32) != tm->test_node[1].idx) {
+ printf("Data idx miss match at node 1, expected = %u"
+ " got = %u\n",tm->test_node[1].idx,
+ (uint32_t)(data->udata64 >> 32));
+ goto end;
+ }
+
+ if ((data->udata64 & 0xffff) != (i - count)) {
+ printf("Expected buff count miss match at node 1\n");
+ goto end;
+ }
+
+ if (data->udata64 & (0x1 << 16))
+ count = i + 1;
+ if (data->udata64 & (0x1 << 17))
+ second_pass = 1;
+ }
+
+ if (count != i) {
+ printf("Count missmatch at node 1\n");
+ goto end;
+ }
+
+ obj_node0 = nb_objs;
+ for (i = 0; i < obj_node0; i++) {
+ data = &mbuf[2][i];
+ data->udata64 = ((uint64_t)tm->test_node[2].idx << 32) | i;
+ if ((i + 1) == obj_node0)
+ data->udata64 |= (1 << 16);
+ if (second_pass)
+ data->udata64 |= (1 << 17);
+ }
+ rte_node_enqueue(graph, node, 0,
+ (void**)&mbuf_p[2][0], obj_node0);
+end:
+ return nb_objs;
+}
+
+uint16_t
+test_node2_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs)
+{
+ test_main_t *tm = &test_main;
+ uint8_t second_pass = 0;
+ struct rte_mbuf *data;
+ uint32_t count = 0;
+ uint32_t obj_node0;
+ uint32_t i;
+
+ obj_stats[3] += nb_objs;
+ fn_calls[3] += 1;
+ for (i = 0; i < nb_objs; i++) {
+ data = (struct rte_mbuf*)objs[i];
+ if ((data->udata64 >> 32) != tm->test_node[2].idx) {
+ printf("Data idx miss match at node 2, expected = %u"
+ " got = %u\n",tm->test_node[2].idx,
+ (uint32_t)(data->udata64 >> 32));
+ goto end;
+ }
+
+ if ((data->udata64 & 0xffff) != (i - count)) {
+ printf("Expected buff count miss match at node 2\n");
+ goto end;
+ }
+
+ if (data->udata64 & (0x1 << 16))
+ count = i + 1;
+ if (data->udata64 & (0x1 << 17))
+ second_pass = 1;
+ }
+
+ if (count != i) {
+ printf("Count missmatch at node 2\n");
+ goto end;
+ }
+
+ if (!second_pass) {
+ obj_node0 = nb_objs;
+ for (i = 0; i < obj_node0; i++) {
+ data = &mbuf[3][i];
+ data->udata64 = ((uint64_t)tm->test_node[3].idx << 32)
+ | i;
+ if ((i + 1) == obj_node0)
+ data->udata64 |= (1 << 16);
+ }
+ rte_node_enqueue(graph, node, 0, (void**)&mbuf_p[3][0],
+ obj_node0);
+ }
+end:
+ return nb_objs;
+}
+
+uint16_t
+test_node3_worker(struct rte_graph *graph, struct rte_node *node, void **objs,
+ uint16_t nb_objs)
+{
+ test_main_t *tm = &test_main;
+ uint8_t second_pass = 0;
+ struct rte_mbuf *data;
+ uint32_t count = 0;
+ uint32_t obj_node0;
+ uint32_t i;
+
+ obj_stats[4] += nb_objs;
+ fn_calls[4] += 1;
+ for (i = 0; i < nb_objs; i++) {
+ data = (struct rte_mbuf*)objs[i];
+ if ((data->udata64 >> 32) != tm->test_node[3].idx) {
+ printf("Data idx miss match at node 3, expected = %u"
+ " got = %u\n",tm->test_node[3].idx,
+ (uint32_t)(data->udata64 >> 32));
+ goto end;
+ }
+
+ if ((data->udata64 & 0xffff) != (i - count)) {
+ printf("Expected buff count miss match at node 3\n");
+ goto end;
+ }
+
+ if (data->udata64 & (0x1 << 16))
+ count = i + 1;
+ if (data->udata64 & (0x1 << 17))
+ second_pass = 1;
+ }
+
+ if (count != i) {
+ printf("Count missmatch at node 3\n");
+ goto end;
+ }
+
+ if (second_pass) {
+ printf("Unexpected buffers are at node 3\n");
+ goto end;
+ } else {
+ obj_node0 = nb_objs * 2;
+ for (i = 0; i < obj_node0; i++) {
+ data = &mbuf[4][i];
+ data->udata64 = ((uint64_t)tm->test_node[0].idx << 32)
+ | i;
+ data->udata64 |= (1 << 17);
+ if ((i + 1) == obj_node0)
+ data->udata64 |= (1 << 16);
+ }
+ rte_node_enqueue(graph, node, 0, (void**)&mbuf_p[4][0],
+ obj_node0);
+ }
+end:
+ return nb_objs;
+}
+
+static int test_lookup_functions(void)
+{
+ test_main_t *tm = &test_main;
+ int i;
+
+
+ /* Verify the name with ID */
+ for (i = 1; i < MAX_NODES; i++) {
+ char *name = rte_node_id_to_name(tm->test_node[i].idx);
+ if (strcmp(name, node_names[i]) != 0) {
+ printf("Test node name verify by ID = %d failed "
+ "Expected = %s, got %s\n",
+ i, node_names[i], name);
+ return -1;
+ }
+ }
+
+ /* verify by name */
+ for (i = 1; i < MAX_NODES; i++) {
+ uint32_t idx = rte_node_from_name(node_names[i]);
+ if (idx != tm->test_node[i].idx) {
+ printf("Test node ID verify by name = %s failed "
+ "Expected = %d, got %d\n",
+ node_names[i], tm->test_node[i].idx,
+ idx);
+ return -1;
+ }
+ }
+
+ /* Verify edge count */
+ for (i = 1; i < MAX_NODES; i++) {
+ uint32_t count = rte_node_edge_count(tm->test_node[i].idx);
+ if (count != tm->test_node[i].node.nb_edges) {
+ printf("Test number of edges for node = %s failed "
+ "Expected = %d, got = %d\n",
+ tm->test_node[i].node.name,
+ tm->test_node[i].node.nb_edges,
+ count);
+ return -1;
+ }
+ }
+
+ /* verify edge names */
+ for (i = 1; i < MAX_NODES; i++) {
+ uint32_t j, count;
+ char **next_edges;
+
+ count = rte_node_edge_get(tm->test_node[i].idx, NULL);
+ if (count != tm->test_node[i].node.nb_edges * sizeof(char*)) {
+ printf("Test number of edge count for node = %s failed"
+ " Expected = %d, got = %d\n",
+ tm->test_node[i].node.name,
+ tm->test_node[i].node.nb_edges,
+ count);
+ return -1;
+ }
+ next_edges = malloc(count);
+ count = rte_node_edge_get(tm->test_node[i].idx,
+ next_edges);
+ if (count != tm->test_node[i].node.nb_edges) {
+ printf("Test number of edges for node = %s failed "
+ "Expected = %d, got %d\n",
+ tm->test_node[i].node.name,
+ tm->test_node[i].node.nb_edges,
+ count);
+ return -1;
+ }
+
+ for (j = 0; j < count; j++) {
+ if (strcmp(next_edges[j],
+ tm->test_node[i].node.next_nodes[j]) != 0) {
+ printf("Edge name miss match, expected = %s"
+ " got = %s\n",
+ tm->test_node[i].node.next_nodes[j],
+ next_edges[j]);
+ return -1;
+ }
+ }
+ free(next_edges);
+ }
+ return 0;
+}
+
+static int test_node_clone(void)
+{
+ test_main_t *tm = &test_main;
+ uint32_t node_id, dummy_id;
+ int i;
+
+ node_id = rte_node_from_name("test_node00");
+ tm->test_node[0].idx = node_id;
+
+ /* Clone with same name, should fail */
+ dummy_id = rte_node_clone(node_id, "test_node00");
+ if (!rte_node_is_invalid(dummy_id)) {
+ printf("Got valid id when clone with same name, "
+ " Expecting fail\n");
+ return -1;
+ }
+
+ for (i = 1; i < MAX_NODES; i++) {
+ tm->test_node[i].idx =
+ rte_node_clone(node_id, tm->test_node[i].node.name);
+ if (rte_node_is_invalid(tm->test_node[i].idx)) {
+ printf("Got invalid node id \n");
+ return -1;
+ }
+ }
+
+ /* clone from cloned node should fail */
+ dummy_id = rte_node_clone(tm->test_node[1].idx, "dummy_node");
+ if (!rte_node_is_invalid(dummy_id)) {
+ printf("Got valid node id when cloning from cloned node"
+ " Expected fail\n");
+ return -1;
+ }
+ return 0;
+}
+
+static int test_update_edges(void)
+{
+ test_main_t *tm = &test_main;
+ uint32_t node_id;
+ uint16_t count;
+ int i;
+
+
+ node_id = rte_node_from_name("test_node00");
+ count = rte_node_edge_update(node_id,
+ 0,
+ tm->test_node[0].node.next_nodes,
+ tm->test_node[0].node.nb_edges);
+ if (count != tm->test_node[0].node.nb_edges) {
+ printf("Update edges failed expected: %d"
+ " got = %d\n",
+ tm->test_node[0].node.nb_edges,
+ count);
+ return -1;
+ }
+
+ for (i = 1; i < MAX_NODES; i++) {
+ count = rte_node_edge_update(tm->test_node[i].idx,
+ 0,
+ tm->test_node[i].node.next_nodes,
+ tm->test_node[i].node.nb_edges);
+ if (count != tm->test_node[i].node.nb_edges) {
+ printf("Update edges failed expected: %d"
+ " got = %d\n",
+ tm->test_node[i].node.nb_edges,
+ count);
+ return -1;
+ }
+
+ count = rte_node_edge_shrink(tm->test_node[i].idx,
+ tm->test_node[i].node.nb_edges);
+ if (count != tm->test_node[i].node.nb_edges) {
+ printf("Shrink edges failed\n");
+ return -1;
+ }
+ }
+ return 0;
+}
+
+static int test_create_graph(void)
+{
+ const char *node_patterns_dummy[] = {
+ "test_node_source1",
+ "test_node00",
+ "test_node00-test_node11",
+ "test_node00-test_node22",
+ "test_node00-test_node33",
+ "test_node00-dummy_node",
+ };
+ struct rte_graph_param gconf = {
+ .socket_id = SOCKET_ID_ANY,
+ .nb_node_patterns = 6,
+ .node_patterns = node_patterns_dummy,
+ };
+ uint32_t dummy_node_id;
+ uint32_t node_id;
+
+
+ node_id = rte_node_from_name("test_node00");
+ dummy_node_id = rte_node_clone(node_id, "dummy_node");
+ if (rte_node_is_invalid(dummy_node_id)) {
+ printf("Got invalid node id \n");
+ return -1;
+ }
+ graph_id = rte_graph_create("worker0", &gconf);
+ if (graph_id != RTE_GRAPH_ID_INVALID) {
+ printf("Graph creation success with isolated node"
+ " Expected graph creation fail\n");
+ return -1;
+ }
+ gconf.nb_node_patterns = 5;
+ gconf.node_patterns = node_patterns;
+ graph_id = rte_graph_create("worker0", &gconf);
+ if (graph_id == RTE_GRAPH_ID_INVALID) {
+ printf("Graph creation failed with error = %d\n", rte_errno);
+ return -1;
+ }
+ return 0;
+}
+
+static int test_graph_walk(void)
+{
+ struct rte_graph *graph = rte_graph_lookup("worker0");
+ int i;
+
+ if (!graph) {
+ printf("Graph lookup failed\n");
+ return -1;
+ }
+
+ for (i = 0; i < 5; i++) {
+ rte_graph_walk(graph);
+ }
+
+ return 0;
+}
+
+
+static int test_graph_lookup_functions(void)
+{
+ test_main_t *tm = &test_main;
+ struct rte_node *node;
+ int i;
+
+
+ for (i = 0; i < MAX_NODES; i++) {
+ node = rte_graph_node_get(graph_id, tm->test_node[i].idx);
+ if (!node) {
+ printf("rte_graph_node_get, failed for node = %d\n",
+ tm->test_node[i].idx);
+ return -1;
+ }
+
+ if (tm->test_node[i].idx != node->id) {
+ printf("Node id didn't match, expected = %d"
+ " got = %d\n", tm->test_node[i].idx, node->id);
+ return 0;
+ }
+
+ if (strncmp(node->name, node_names[i], RTE_NODE_NAMESIZE)) {
+ printf("Node name didn't match, expected = %s"
+ " got %s\n",node_names[i], node->name);
+ return -1;
+ }
+ }
+
+ for (i = 0; i < MAX_NODES; i++) {
+ node = rte_graph_node_get_by_name("worker0", node_names[i]);
+ if (!node) {
+ printf("rte_graph_node_get, failed for node = %d\n",
+ tm->test_node[i].idx);
+ return -1;
+ }
+
+ if (tm->test_node[i].idx != node->id) {
+ printf("Node id didn't match, expected = %d"
+ " got = %d\n", tm->test_node[i].idx, node->id);
+ return 0;
+ }
+
+ if (strncmp(node->name, node_names[i], RTE_NODE_NAMESIZE)) {
+ printf("Node name didn't match, expected = %s"
+ " got %s\n",node_names[i], node->name);
+ return -1;
+ }
+ }
+ return 0;
+}
+
+static int
+graph_cluster_stats_cb_t(bool is_first, bool is_last, void *cookie,
+ const struct rte_graph_cluster_node_stats *st)
+{
+ int i;
+
+ RTE_SET_USED(is_first);
+ RTE_SET_USED(is_last);
+ RTE_SET_USED(cookie);
+
+ for (i = 0; i < MAX_NODES + 1; i++) {
+ rte_node_t id = rte_node_from_name(node_patterns[i]);
+ if (id == st->id) {
+ if (obj_stats[i] != st->objs) {
+ printf("Obj count miss match for node = %s"
+ "expected=%"PRId64" , got=%"PRId64"\n",
+ node_patterns[i], obj_stats[i],
+ st->objs);
+ return -1;
+ }
+
+ if (fn_calls[i] != st->calls) {
+ printf("func call miss match for node = %s"
+ "expected= %"PRId64" , got=%"PRId64"\n",
+ node_patterns[i], fn_calls[i],
+ st->calls);
+ return -1;
+ }
+ }
+ }
+ return 0;
+}
+
+static int
+test_print_stats(void)
+{
+ struct rte_graph_cluster_stats_param s_param;
+ struct rte_graph_cluster_stats *stats;
+ const char *pattern = "worker0";
+
+ if (!rte_graph_has_stats_feature())
+ return 0;
+
+ /* 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;
+ s_param.fn = graph_cluster_stats_cb_t;
+
+ stats = rte_graph_cluster_stats_create(&s_param);
+ if (stats == NULL) {
+ printf("Unable to get stats\n");
+ return -1;
+ }
+
+ /* Clear screen and move to top left */
+ rte_graph_cluster_stats_get(stats, 0);
+
+ rte_graph_cluster_stats_destroy(stats);
+
+ return 0;
+}
+
+static int graph_setup(void)
+{
+ int i, j;
+
+ for (i = 0; i <= MAX_NODES; i++) {
+ for (j = 0 ; j < MBUFF_SIZE; j++) {
+ mbuf_p[i][j] = &mbuf[i][j];
+ }
+ }
+
+ if (test_node_clone()) {
+ printf("test_node_clone: fail\n");
+ return -1;
+ }
+ printf("test_node_clone: pass\n");
+ return 0;
+}
+
+static void graph_teardown(void)
+{
+ rte_graph_t id;
+
+ id = rte_graph_destroy("worker0");
+ if (id == RTE_GRAPH_ID_INVALID) {
+ printf("Graph Destroy failed\n");
+ }
+}
+
+static struct unit_test_suite graph_testsuite = {
+ .suite_name = "Graph library test suite",
+ .setup = graph_setup,
+ .teardown = graph_teardown,
+ .unit_test_cases = {
+ TEST_CASE(test_update_edges),
+ TEST_CASE(test_lookup_functions),
+ TEST_CASE(test_create_graph),
+ TEST_CASE(test_graph_lookup_functions),
+ TEST_CASE(test_graph_walk),
+ TEST_CASE(test_print_stats),
+ // add test case for rte_graph_cluster_stats_reset
+ TEST_CASES_END(), /**< NULL terminate unit test array */
+ }
+};
+
+static int
+graph_autotest_fn(void)
+{
+ return unit_test_suite_runner(&graph_testsuite);
+}
+
+REGISTER_TEST_COMMAND(graph_autotest, graph_autotest_fn);
--
2.24.1
next prev parent reply other threads:[~2020-01-31 17:03 UTC|newest]
Thread overview: 31+ messages / expand[flat|nested] mbox.gz Atom feed top
2020-01-31 17:01 [dpdk-dev] [RFC PATCH 0/5] graph: introduce graph subsystem jerinj
2020-01-31 17:01 ` [dpdk-dev] [RFC PATCH 1/5] " jerinj
2020-02-02 10:34 ` Stephen Hemminger
2020-02-02 10:35 ` Stephen Hemminger
2020-02-02 11:08 ` Jerin Jacob
2020-02-02 10:38 ` Stephen Hemminger
2020-02-02 11:21 ` Jerin Jacob
2020-02-03 9:14 ` Gaetan Rivet
2020-02-03 9:49 ` Jerin Jacob
2020-01-31 17:01 ` [dpdk-dev] [RFC PATCH 2/5] node: add packet processing nodes jerinj
2020-01-31 17:01 ` jerinj [this message]
2020-01-31 17:02 ` [dpdk-dev] [RFC PATCH 4/5] test: add graph performance test cases jerinj
2020-01-31 17:02 ` [dpdk-dev] [RFC PATCH 5/5] example/l3fwd_graph: l3fwd using graph architecture jerinj
2020-01-31 18:34 ` [dpdk-dev] [RFC PATCH 0/5] graph: introduce graph subsystem Ray Kinsella
2020-02-01 5:44 ` Jerin Jacob
2020-02-17 7:19 ` Jerin Jacob
2020-02-17 8:38 ` Thomas Monjalon
2020-02-17 10:58 ` Jerin Jacob
2020-02-21 10:30 ` Jerin Jacob
2020-02-21 11:10 ` Thomas Monjalon
2020-02-21 15:38 ` Mattias Rönnblom
2020-02-21 15:53 ` dave
2020-02-21 16:04 ` Thomas Monjalon
2020-02-21 15:56 ` Jerin Jacob
2020-02-21 16:14 ` Thomas Monjalon
2020-02-22 9:05 ` Jerin Jacob
2020-02-22 9:52 ` Thomas Monjalon
2020-02-22 10:24 ` Jerin Jacob
2020-02-24 10:59 ` Ray Kinsella
2020-02-25 5:22 ` Honnappa Nagarahalli
2020-02-25 6:14 ` Jerin Jacob
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20200131170201.3236153-4-jerinj@marvell.com \
--to=jerinj@marvell.com \
--cc=ajit.khaparde@broadcom.com \
--cc=akhil.goyal@nxp.com \
--cc=anatoly.burakov@intel.com \
--cc=artem.andreev@oktetlabs.ru \
--cc=arybchenko@solarflare.com \
--cc=bruce.richardson@intel.com \
--cc=cristian.dumitrescu@intel.com \
--cc=david.marchand@redhat.com \
--cc=dev@dpdk.org \
--cc=drc@linux.vnet.ibm.com \
--cc=erik.g.carrillo@intel.com \
--cc=ferruh.yigit@intel.com \
--cc=gage.eads@intel.com \
--cc=gavin.hu@arm.com \
--cc=hemant.agrawal@nxp.com \
--cc=honnappa.nagarahalli@arm.com \
--cc=jasvinder.singh@intel.com \
--cc=john.mcnamara@intel.com \
--cc=keith.wiles@intel.com \
--cc=kirankumark@marvell.com \
--cc=konstantin.ananyev@intel.com \
--cc=mattias.ronnblom@ericsson.com \
--cc=maxime.coquelin@redhat.com \
--cc=mdr@ashroe.eu \
--cc=ndabilpuram@marvell.com \
--cc=nikhil.rao@intel.com \
--cc=nsaxena@marvell.com \
--cc=olivier.matz@6wind.com \
--cc=pallavi.kadam@intel.com \
--cc=pathreya@marvell.com \
--cc=pbhagavatula@marvell.com \
--cc=pkapoor@marvell.com \
--cc=rasland@mellanox.com \
--cc=shahafs@mellanox.com \
--cc=sshankarnara@marvell.com \
--cc=sthemmin@microsoft.com \
--cc=techboard@dpdk.org \
--cc=thomas@monjalon.net \
--cc=vladimir.medvedkin@intel.com \
--cc=xiaolong.ye@intel.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).