1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(c) 2018 Intel Corporation
3 */
4
5 #include <string.h>
6
7 #include <rte_bus_vdev.h>
8 #include <rte_common.h>
9 #include <rte_ethdev.h>
10 #include <rte_eth_ring.h>
11 #include <rte_eventdev.h>
12 #include <rte_event_eth_tx_adapter.h>
13 #include <rte_mbuf.h>
14 #include <rte_mempool.h>
15 #include <rte_service.h>
16
17 #include "test.h"
18
19 #ifdef RTE_EXEC_ENV_WINDOWS
20 static int
test_event_eth_tx_adapter_common(void)21 test_event_eth_tx_adapter_common(void)
22 {
23 printf("event_eth_tx_adapter not supported on Windows, skipping test\n");
24 return TEST_SKIPPED;
25 }
26
27 #else
28
29 #define MAX_NUM_QUEUE RTE_PMD_RING_MAX_RX_RINGS
30 #define TEST_INST_ID 0
31 #define TEST_DEV_ID 0
32 #define TEST_ETH_QUEUE_ID 0
33 #define SOCKET0 0
34 #define RING_SIZE 256
35 #define ETH_NAME_LEN 32
36 #define NUM_ETH_PAIR 1
37 #define NUM_ETH_DEV (2 * NUM_ETH_PAIR)
38 #define NB_MBUF 512
39 #define PAIR_PORT_INDEX(p) ((p) + NUM_ETH_PAIR)
40 #define PORT(p) default_params.port[(p)]
41 #define TEST_ETHDEV_ID PORT(0)
42 #define TEST_ETHDEV_PAIR_ID PORT(PAIR_PORT_INDEX(0))
43 #define DEFAULT_FLUSH_THRESHOLD 1024
44 #define TXA_NB_TX_WORK_DEFAULT 128
45
46 #define EDEV_RETRY 0xffff
47
48 struct event_eth_tx_adapter_test_params {
49 struct rte_mempool *mp;
50 uint16_t rx_rings, tx_rings;
51 struct rte_ring *r[NUM_ETH_DEV][MAX_NUM_QUEUE];
52 int port[NUM_ETH_DEV];
53 };
54
55 static int event_dev_delete;
56 static struct event_eth_tx_adapter_test_params default_params;
57 static uint64_t eid = ~0ULL;
58 static uint32_t tid;
59
60 static inline int
port_init_common(uint16_t port,const struct rte_eth_conf * port_conf,struct rte_mempool * mp)61 port_init_common(uint16_t port, const struct rte_eth_conf *port_conf,
62 struct rte_mempool *mp)
63 {
64 const uint16_t rx_ring_size = RING_SIZE, tx_ring_size = RING_SIZE;
65 int retval;
66 uint16_t q;
67
68 if (!rte_eth_dev_is_valid_port(port))
69 return -1;
70
71 default_params.rx_rings = MAX_NUM_QUEUE;
72 default_params.tx_rings = MAX_NUM_QUEUE;
73
74 /* Configure the Ethernet device. */
75 retval = rte_eth_dev_configure(port, default_params.rx_rings,
76 default_params.tx_rings, port_conf);
77 if (retval != 0)
78 return retval;
79
80 for (q = 0; q < default_params.rx_rings; q++) {
81 retval = rte_eth_rx_queue_setup(port, q, rx_ring_size,
82 rte_eth_dev_socket_id(port), NULL, mp);
83 if (retval < 0)
84 return retval;
85 }
86
87 for (q = 0; q < default_params.tx_rings; q++) {
88 retval = rte_eth_tx_queue_setup(port, q, tx_ring_size,
89 rte_eth_dev_socket_id(port), NULL);
90 if (retval < 0)
91 return retval;
92 }
93
94 /* Start the Ethernet port. */
95 retval = rte_eth_dev_start(port);
96 if (retval < 0)
97 return retval;
98
99 /* Display the port MAC address. */
100 struct rte_ether_addr addr;
101 retval = rte_eth_macaddr_get(port, &addr);
102 if (retval < 0)
103 return retval;
104 printf("Port %u MAC: %02" PRIx8 " %02" PRIx8 " %02" PRIx8
105 " %02" PRIx8 " %02" PRIx8 " %02" PRIx8 "\n",
106 (unsigned int)port, RTE_ETHER_ADDR_BYTES(&addr));
107
108 /* Enable RX in promiscuous mode for the Ethernet device. */
109 retval = rte_eth_promiscuous_enable(port);
110 if (retval != 0)
111 return retval;
112
113 return 0;
114 }
115
116 static inline int
port_init(uint16_t port,struct rte_mempool * mp)117 port_init(uint16_t port, struct rte_mempool *mp)
118 {
119 struct rte_eth_conf conf = { 0 };
120 return port_init_common(port, &conf, mp);
121 }
122
123 #define RING_NAME_LEN 20
124 #define DEV_NAME_LEN 20
125
126 static int
init_ports(void)127 init_ports(void)
128 {
129 char ring_name[ETH_NAME_LEN];
130 unsigned int i, j;
131 struct rte_ring * const *c1;
132 struct rte_ring * const *c2;
133 int err;
134
135 if (!default_params.mp)
136 default_params.mp = rte_pktmbuf_pool_create("mbuf_pool",
137 NB_MBUF, 32,
138 0, RTE_MBUF_DEFAULT_BUF_SIZE, rte_socket_id());
139
140 if (!default_params.mp)
141 return -ENOMEM;
142
143 for (i = 0; i < NUM_ETH_DEV; i++) {
144 for (j = 0; j < MAX_NUM_QUEUE; j++) {
145 snprintf(ring_name, sizeof(ring_name), "R%u%u", i, j);
146 default_params.r[i][j] = rte_ring_create(ring_name,
147 RING_SIZE,
148 SOCKET0,
149 RING_F_SP_ENQ | RING_F_SC_DEQ);
150 TEST_ASSERT((default_params.r[i][j] != NULL),
151 "Failed to allocate ring");
152 }
153 }
154
155 /*
156 * To create two pseudo-Ethernet ports where the traffic is
157 * switched between them, that is, traffic sent to port 1 is
158 * read back from port 2 and vice-versa
159 */
160 for (i = 0; i < NUM_ETH_PAIR; i++) {
161 char dev_name[DEV_NAME_LEN];
162 int p;
163
164 c1 = default_params.r[i];
165 c2 = default_params.r[PAIR_PORT_INDEX(i)];
166
167 snprintf(dev_name, DEV_NAME_LEN, "%u-%u", i, i + NUM_ETH_PAIR);
168 p = rte_eth_from_rings(dev_name, c1, MAX_NUM_QUEUE,
169 c2, MAX_NUM_QUEUE, SOCKET0);
170 TEST_ASSERT(p >= 0, "Port creation failed %s", dev_name);
171 err = port_init(p, default_params.mp);
172 TEST_ASSERT(err == 0, "Port init failed %s", dev_name);
173 default_params.port[i] = p;
174
175 snprintf(dev_name, DEV_NAME_LEN, "%u-%u", i + NUM_ETH_PAIR, i);
176 p = rte_eth_from_rings(dev_name, c2, MAX_NUM_QUEUE,
177 c1, MAX_NUM_QUEUE, SOCKET0);
178 TEST_ASSERT(p > 0, "Port creation failed %s", dev_name);
179 err = port_init(p, default_params.mp);
180 TEST_ASSERT(err == 0, "Port init failed %s", dev_name);
181 default_params.port[PAIR_PORT_INDEX(i)] = p;
182 }
183
184 return 0;
185 }
186
187 static void
deinit_ports(void)188 deinit_ports(void)
189 {
190 uint16_t i, j;
191 char name[ETH_NAME_LEN];
192
193 for (i = 0; i < RTE_DIM(default_params.port); i++) {
194 rte_eth_dev_stop(default_params.port[i]);
195 rte_eth_dev_get_name_by_port(default_params.port[i], name);
196 rte_vdev_uninit(name);
197 for (j = 0; j < RTE_DIM(default_params.r[i]); j++)
198 rte_ring_free(default_params.r[i][j]);
199 }
200 }
201
202 static int
testsuite_setup(void)203 testsuite_setup(void)
204 {
205 const char *vdev_name = "event_sw0";
206
207 int err = init_ports();
208 TEST_ASSERT(err == 0, "Port initialization failed err %d\n", err);
209
210 if (rte_event_dev_count() == 0) {
211 printf("Failed to find a valid event device,"
212 " testing with event_sw0 device\n");
213 err = rte_vdev_init(vdev_name, NULL);
214 TEST_ASSERT(err == 0, "vdev %s creation failed %d\n",
215 vdev_name, err);
216 event_dev_delete = 1;
217 }
218 return err;
219 }
220
221 #define DEVICE_ID_SIZE 64
222
223 static void
testsuite_teardown(void)224 testsuite_teardown(void)
225 {
226 deinit_ports();
227 rte_mempool_free(default_params.mp);
228 default_params.mp = NULL;
229 if (event_dev_delete)
230 rte_vdev_uninit("event_sw0");
231 }
232
233 static int
tx_adapter_create(void)234 tx_adapter_create(void)
235 {
236 int err;
237 struct rte_event_dev_info dev_info;
238 struct rte_event_port_conf tx_p_conf;
239 uint8_t priority;
240 uint8_t queue_id;
241
242 struct rte_event_dev_config config = {
243 .nb_event_queues = 1,
244 .nb_event_ports = 1,
245 };
246
247 struct rte_event_queue_conf wkr_q_conf = {
248 .schedule_type = RTE_SCHED_TYPE_ORDERED,
249 .priority = RTE_EVENT_DEV_PRIORITY_NORMAL,
250 .nb_atomic_flows = 1024,
251 .nb_atomic_order_sequences = 1024,
252 };
253
254 memset(&tx_p_conf, 0, sizeof(tx_p_conf));
255 err = rte_event_dev_info_get(TEST_DEV_ID, &dev_info);
256 config.nb_event_queue_flows = dev_info.max_event_queue_flows;
257 config.nb_event_port_dequeue_depth =
258 dev_info.max_event_port_dequeue_depth;
259 config.nb_event_port_enqueue_depth =
260 dev_info.max_event_port_enqueue_depth;
261 config.nb_events_limit =
262 dev_info.max_num_events;
263
264 err = rte_event_dev_configure(TEST_DEV_ID, &config);
265 TEST_ASSERT(err == 0, "Event device initialization failed err %d\n",
266 err);
267
268 queue_id = 0;
269 err = rte_event_queue_setup(TEST_DEV_ID, 0, &wkr_q_conf);
270 TEST_ASSERT(err == 0, "Event queue setup failed %d\n", err);
271
272 err = rte_event_port_setup(TEST_DEV_ID, 0, NULL);
273 TEST_ASSERT(err == 0, "Event port setup failed %d\n", err);
274
275 priority = RTE_EVENT_DEV_PRIORITY_LOWEST;
276 err = rte_event_port_link(TEST_DEV_ID, 0, &queue_id, &priority, 1);
277 TEST_ASSERT(err == 1, "Error linking port %s\n",
278 rte_strerror(rte_errno));
279 err = rte_event_dev_info_get(TEST_DEV_ID, &dev_info);
280 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
281
282 tx_p_conf.new_event_threshold = dev_info.max_num_events;
283 tx_p_conf.dequeue_depth = dev_info.max_event_port_dequeue_depth;
284 tx_p_conf.enqueue_depth = dev_info.max_event_port_enqueue_depth;
285 err = rte_event_eth_tx_adapter_create(TEST_INST_ID, TEST_DEV_ID,
286 &tx_p_conf);
287 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
288
289 return err;
290 }
291
292 static void
tx_adapter_free(void)293 tx_adapter_free(void)
294 {
295 rte_event_eth_tx_adapter_free(TEST_INST_ID);
296 }
297
298 static int
tx_adapter_create_free(void)299 tx_adapter_create_free(void)
300 {
301 int err;
302 struct rte_event_dev_info dev_info;
303 struct rte_event_port_conf tx_p_conf;
304
305 err = rte_event_dev_info_get(TEST_DEV_ID, &dev_info);
306 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
307
308 tx_p_conf.new_event_threshold = dev_info.max_num_events;
309 tx_p_conf.dequeue_depth = dev_info.max_event_port_dequeue_depth;
310 tx_p_conf.enqueue_depth = dev_info.max_event_port_enqueue_depth;
311
312 err = rte_event_eth_tx_adapter_create(TEST_INST_ID, TEST_DEV_ID,
313 NULL);
314 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
315
316 err = rte_event_eth_tx_adapter_create(TEST_INST_ID, TEST_DEV_ID,
317 &tx_p_conf);
318 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
319
320 err = rte_event_eth_tx_adapter_create(TEST_INST_ID,
321 TEST_DEV_ID, &tx_p_conf);
322 TEST_ASSERT(err == -EEXIST, "Expected -EEXIST %d got %d", -EEXIST, err);
323
324 err = rte_event_eth_tx_adapter_free(TEST_INST_ID);
325 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
326
327 err = rte_event_eth_tx_adapter_free(TEST_INST_ID);
328 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL %d got %d", -EINVAL, err);
329
330 err = rte_event_eth_tx_adapter_free(1);
331 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL %d got %d", -EINVAL, err);
332
333 return TEST_SUCCESS;
334 }
335
336 static int
tx_adapter_queue_add_del(void)337 tx_adapter_queue_add_del(void)
338 {
339 int err;
340 uint32_t cap;
341
342 err = rte_event_eth_tx_adapter_caps_get(TEST_DEV_ID, TEST_ETHDEV_ID,
343 &cap);
344 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
345
346
347 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
348 rte_eth_dev_count_total(),
349 -1);
350 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
351
352 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
353 TEST_ETHDEV_ID,
354 0);
355 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
356
357 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
358 TEST_ETHDEV_ID,
359 -1);
360 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
361
362 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID,
363 TEST_ETHDEV_ID,
364 0);
365 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
366
367 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID,
368 TEST_ETHDEV_ID,
369 -1);
370 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
371
372 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID,
373 TEST_ETHDEV_ID,
374 -1);
375 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
376
377 err = rte_event_eth_tx_adapter_queue_add(1, TEST_ETHDEV_ID, -1);
378 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
379
380 err = rte_event_eth_tx_adapter_queue_del(1, TEST_ETHDEV_ID, -1);
381 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
382
383 return TEST_SUCCESS;
384 }
385
386 static int
tx_adapter_start_stop(void)387 tx_adapter_start_stop(void)
388 {
389 int err;
390
391 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID, TEST_ETHDEV_ID,
392 -1);
393 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
394
395 err = rte_event_eth_tx_adapter_start(TEST_INST_ID);
396 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
397
398 err = rte_event_eth_tx_adapter_stop(TEST_INST_ID);
399 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
400
401 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID, TEST_ETHDEV_ID,
402 -1);
403 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
404
405 err = rte_event_eth_tx_adapter_start(TEST_INST_ID);
406 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
407
408 err = rte_event_eth_tx_adapter_stop(TEST_INST_ID);
409 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
410
411 err = rte_event_eth_tx_adapter_start(1);
412
413 err = rte_event_eth_tx_adapter_stop(1);
414 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
415
416 return TEST_SUCCESS;
417 }
418
419
420 static int
tx_adapter_single(uint16_t port,uint16_t tx_queue_id,struct rte_mbuf * m,uint8_t qid,uint8_t sched_type)421 tx_adapter_single(uint16_t port, uint16_t tx_queue_id,
422 struct rte_mbuf *m, uint8_t qid,
423 uint8_t sched_type)
424 {
425 struct rte_event event;
426 struct rte_mbuf *r;
427 int ret;
428 unsigned int l;
429
430 event.queue_id = qid;
431 event.op = RTE_EVENT_OP_NEW;
432 event.event_type = RTE_EVENT_TYPE_CPU;
433 event.sched_type = sched_type;
434 event.mbuf = m;
435
436 m->port = port;
437 rte_event_eth_tx_adapter_txq_set(m, tx_queue_id);
438
439 l = 0;
440 while (rte_event_enqueue_burst(TEST_DEV_ID, 0, &event, 1) != 1) {
441 l++;
442 if (l > EDEV_RETRY)
443 break;
444 }
445
446 TEST_ASSERT(l < EDEV_RETRY, "Unable to enqueue to eventdev");
447 l = 0;
448 while (l++ < EDEV_RETRY) {
449
450 if (eid != ~0ULL) {
451 ret = rte_service_run_iter_on_app_lcore(eid, 0);
452 TEST_ASSERT(ret == 0, "failed to run service %d", ret);
453 }
454
455 ret = rte_service_run_iter_on_app_lcore(tid, 0);
456 TEST_ASSERT(ret == 0, "failed to run service %d", ret);
457
458 if (rte_eth_rx_burst(TEST_ETHDEV_PAIR_ID, tx_queue_id,
459 &r, 1)) {
460 TEST_ASSERT_EQUAL(r, m, "mbuf comparison failed"
461 " expected %p received %p", m, r);
462 return 0;
463 }
464 }
465
466 TEST_ASSERT(0, "Failed to receive packet");
467 return -1;
468 }
469
470 static int
tx_adapter_service(void)471 tx_adapter_service(void)
472 {
473 struct rte_event_eth_tx_adapter_stats stats;
474 uint32_t i;
475 int err;
476 uint8_t ev_port, ev_qid;
477 struct rte_mbuf bufs[RING_SIZE];
478 struct rte_mbuf *pbufs[RING_SIZE];
479 struct rte_event_dev_info dev_info;
480 struct rte_event_dev_config dev_conf;
481 struct rte_event_queue_conf qconf;
482 uint32_t qcnt, pcnt;
483 uint16_t q;
484 int internal_port;
485 uint32_t cap;
486
487 /* Initialize mbufs */
488 for (i = 0; i < RING_SIZE; i++)
489 rte_pktmbuf_reset(&bufs[i]);
490
491 memset(&dev_conf, 0, sizeof(dev_conf));
492 err = rte_event_eth_tx_adapter_caps_get(TEST_DEV_ID, TEST_ETHDEV_ID,
493 &cap);
494 TEST_ASSERT(err == 0, "Failed to get adapter cap err %d\n", err);
495
496 internal_port = !!(cap & RTE_EVENT_ETH_TX_ADAPTER_CAP_INTERNAL_PORT);
497 if (internal_port)
498 return TEST_SUCCESS;
499
500 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID, TEST_ETHDEV_ID,
501 -1);
502 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
503
504 err = rte_event_eth_tx_adapter_event_port_get(TEST_INST_ID,
505 &ev_port);
506 TEST_ASSERT_SUCCESS(err, "Failed to get event port %d", err);
507
508 err = rte_event_dev_attr_get(TEST_DEV_ID, RTE_EVENT_DEV_ATTR_PORT_COUNT,
509 &pcnt);
510 TEST_ASSERT_SUCCESS(err, "Port count get failed");
511
512 err = rte_event_dev_attr_get(TEST_DEV_ID,
513 RTE_EVENT_DEV_ATTR_QUEUE_COUNT, &qcnt);
514 TEST_ASSERT_SUCCESS(err, "Queue count get failed");
515
516 err = rte_event_dev_info_get(TEST_DEV_ID, &dev_info);
517 TEST_ASSERT_SUCCESS(err, "Dev info failed");
518
519 dev_conf.nb_event_queue_flows = dev_info.max_event_queue_flows;
520 dev_conf.nb_event_port_dequeue_depth =
521 dev_info.max_event_port_dequeue_depth;
522 dev_conf.nb_event_port_enqueue_depth =
523 dev_info.max_event_port_enqueue_depth;
524 dev_conf.nb_events_limit =
525 dev_info.max_num_events;
526 dev_conf.nb_event_queues = qcnt + 1;
527 dev_conf.nb_event_ports = pcnt;
528 err = rte_event_dev_configure(TEST_DEV_ID, &dev_conf);
529 TEST_ASSERT(err == 0, "Event device initialization failed err %d\n",
530 err);
531
532 ev_qid = qcnt;
533 qconf.nb_atomic_flows = dev_info.max_event_queue_flows;
534 qconf.nb_atomic_order_sequences = 32;
535 qconf.schedule_type = RTE_SCHED_TYPE_ATOMIC;
536 qconf.priority = RTE_EVENT_DEV_PRIORITY_HIGHEST;
537 qconf.event_queue_cfg = RTE_EVENT_QUEUE_CFG_SINGLE_LINK;
538 err = rte_event_queue_setup(TEST_DEV_ID, ev_qid, &qconf);
539 TEST_ASSERT_SUCCESS(err, "Failed to setup queue %u", ev_qid);
540
541 /*
542 * Setup ports again so that the newly added queue is visible
543 * to them
544 */
545 for (i = 0; i < pcnt; i++) {
546
547 int n_links;
548 uint8_t queues[RTE_EVENT_MAX_QUEUES_PER_DEV];
549 uint8_t priorities[RTE_EVENT_MAX_QUEUES_PER_DEV];
550
551 if (i == ev_port)
552 continue;
553
554 n_links = rte_event_port_links_get(TEST_DEV_ID, i, queues,
555 priorities);
556 TEST_ASSERT(n_links > 0, "Failed to get port links %d\n",
557 n_links);
558 err = rte_event_port_setup(TEST_DEV_ID, i, NULL);
559 TEST_ASSERT(err == 0, "Failed to setup port err %d\n", err);
560 err = rte_event_port_link(TEST_DEV_ID, i, queues, priorities,
561 n_links);
562 TEST_ASSERT(n_links == err, "Failed to link all queues"
563 " err %s\n", rte_strerror(rte_errno));
564 }
565
566 err = rte_event_port_link(TEST_DEV_ID, ev_port, &ev_qid, NULL, 1);
567 TEST_ASSERT(err == 1, "Failed to link queue port %u",
568 ev_port);
569
570 err = rte_event_eth_tx_adapter_start(TEST_INST_ID);
571 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
572
573 if (!(dev_info.event_dev_cap & RTE_EVENT_DEV_CAP_DISTRIBUTED_SCHED)) {
574 err = rte_event_dev_service_id_get(0, (uint32_t *)&eid);
575 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
576
577 err = rte_service_runstate_set(eid, 1);
578 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
579
580 err = rte_service_set_runstate_mapped_check(eid, 0);
581 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
582 }
583
584 err = rte_event_eth_tx_adapter_service_id_get(TEST_INST_ID, &tid);
585 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
586
587 err = rte_service_runstate_set(tid, 1);
588 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
589
590 err = rte_service_set_runstate_mapped_check(tid, 0);
591 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
592
593 err = rte_event_dev_start(TEST_DEV_ID);
594 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
595
596 for (q = 0; q < MAX_NUM_QUEUE; q++) {
597 for (i = 0; i < RING_SIZE; i++)
598 pbufs[i] = &bufs[i];
599 for (i = 0; i < RING_SIZE; i++) {
600 pbufs[i] = &bufs[i];
601 err = tx_adapter_single(TEST_ETHDEV_ID, q, pbufs[i],
602 ev_qid,
603 RTE_SCHED_TYPE_ORDERED);
604 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
605 }
606 for (i = 0; i < RING_SIZE; i++) {
607 TEST_ASSERT_EQUAL(pbufs[i], &bufs[i],
608 "Error: received data does not match"
609 " that transmitted");
610 }
611 }
612
613 err = rte_event_eth_tx_adapter_stats_get(TEST_INST_ID, NULL);
614 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
615
616 err = rte_event_eth_tx_adapter_stats_get(TEST_INST_ID, &stats);
617 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
618 TEST_ASSERT_EQUAL(stats.tx_packets, MAX_NUM_QUEUE * RING_SIZE,
619 "stats.tx_packets expected %u got %"PRIu64,
620 MAX_NUM_QUEUE * RING_SIZE,
621 stats.tx_packets);
622
623 err = rte_event_eth_tx_adapter_stats_reset(TEST_INST_ID);
624 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
625
626 err = rte_event_eth_tx_adapter_stats_get(TEST_INST_ID, &stats);
627 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
628 TEST_ASSERT_EQUAL(stats.tx_packets, 0,
629 "stats.tx_packets expected %u got %"PRIu64,
630 0,
631 stats.tx_packets);
632
633 err = rte_event_eth_tx_adapter_stats_get(1, &stats);
634 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
635
636 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID, TEST_ETHDEV_ID,
637 -1);
638 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
639
640 err = rte_event_eth_tx_adapter_free(TEST_INST_ID);
641 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
642
643 rte_event_dev_stop(TEST_DEV_ID);
644
645 return TEST_SUCCESS;
646 }
647
648 static int
tx_adapter_instance_get(void)649 tx_adapter_instance_get(void)
650 {
651 int err;
652 uint8_t inst_id;
653 uint16_t eth_dev_id;
654 struct rte_eth_dev_info dev_info;
655
656 /* Case 1: Test without configuring eth */
657 err = rte_event_eth_tx_adapter_instance_get(TEST_ETHDEV_ID,
658 TEST_ETH_QUEUE_ID,
659 &inst_id);
660 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
661
662 /* Case 2: Test with wrong eth port */
663 eth_dev_id = rte_eth_dev_count_total() + 1;
664 err = rte_event_eth_tx_adapter_instance_get(eth_dev_id,
665 TEST_ETH_QUEUE_ID,
666 &inst_id);
667 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
668
669 /* Case 3: Test with wrong tx queue */
670 err = rte_eth_dev_info_get(TEST_ETHDEV_ID, &dev_info);
671 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
672
673 err = rte_event_eth_tx_adapter_instance_get(TEST_ETHDEV_ID,
674 dev_info.max_tx_queues + 1,
675 &inst_id);
676 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
677
678 /* Case 4: Test with right instance, port & rxq */
679 /* Add queue to tx adapter */
680 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
681 TEST_ETHDEV_ID,
682 TEST_ETH_QUEUE_ID);
683 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
684
685 err = rte_event_eth_tx_adapter_instance_get(TEST_ETHDEV_ID,
686 TEST_ETH_QUEUE_ID,
687 &inst_id);
688 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
689 TEST_ASSERT(inst_id == TEST_INST_ID, "Expected %d got %d",
690 TEST_INST_ID, err);
691
692 /* Add another queue to tx adapter */
693 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
694 TEST_ETHDEV_ID,
695 TEST_ETH_QUEUE_ID + 1);
696 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
697
698 err = rte_event_eth_tx_adapter_instance_get(TEST_ETHDEV_ID,
699 TEST_ETH_QUEUE_ID + 1,
700 &inst_id);
701 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
702 TEST_ASSERT(inst_id == TEST_INST_ID, "Expected %d got %d",
703 TEST_INST_ID, err);
704
705 /* Case 5: Test with right instance, port & wrong rxq */
706 err = rte_event_eth_tx_adapter_instance_get(TEST_ETHDEV_ID,
707 TEST_ETH_QUEUE_ID + 2,
708 &inst_id);
709 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
710
711 /* Delete all queues from the Tx adapter */
712 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID,
713 TEST_ETHDEV_ID,
714 -1);
715 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
716
717 return TEST_SUCCESS;
718 }
719
720 static int
tx_adapter_queue_start_stop(void)721 tx_adapter_queue_start_stop(void)
722 {
723 int err;
724 uint16_t eth_dev_id;
725 struct rte_eth_dev_info dev_info;
726
727 /* Case 1: Test without adding eth Tx queue */
728 err = rte_event_eth_tx_adapter_queue_start(TEST_ETHDEV_ID,
729 TEST_ETH_QUEUE_ID);
730 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
731
732 err = rte_event_eth_tx_adapter_queue_stop(TEST_ETHDEV_ID,
733 TEST_ETH_QUEUE_ID);
734 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
735
736 /* Case 2: Test with wrong eth port */
737 eth_dev_id = rte_eth_dev_count_total() + 1;
738 err = rte_event_eth_tx_adapter_queue_start(eth_dev_id,
739 TEST_ETH_QUEUE_ID);
740 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
741
742 err = rte_event_eth_tx_adapter_queue_stop(eth_dev_id,
743 TEST_ETH_QUEUE_ID);
744 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
745
746 /* Case 3: Test with wrong tx queue */
747 err = rte_eth_dev_info_get(TEST_ETHDEV_ID, &dev_info);
748 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
749
750 err = rte_event_eth_tx_adapter_queue_start(TEST_ETHDEV_ID,
751 dev_info.max_tx_queues + 1);
752 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
753
754 err = rte_event_eth_tx_adapter_queue_stop(TEST_ETHDEV_ID,
755 dev_info.max_tx_queues + 1);
756 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
757
758 /* Case 4: Test with right instance, port & rxq */
759 /* Add queue to tx adapter */
760 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
761 TEST_ETHDEV_ID,
762 TEST_ETH_QUEUE_ID);
763 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
764
765 err = rte_event_eth_tx_adapter_queue_stop(TEST_ETHDEV_ID,
766 TEST_ETH_QUEUE_ID);
767 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
768
769 err = rte_event_eth_tx_adapter_queue_start(TEST_ETHDEV_ID,
770 TEST_ETH_QUEUE_ID);
771 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
772
773 /* Add another queue to tx adapter */
774 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
775 TEST_ETHDEV_ID,
776 TEST_ETH_QUEUE_ID + 1);
777 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
778
779 err = rte_event_eth_tx_adapter_queue_stop(TEST_ETHDEV_ID,
780 TEST_ETH_QUEUE_ID + 1);
781 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
782 err = rte_event_eth_tx_adapter_queue_start(TEST_ETHDEV_ID,
783 TEST_ETH_QUEUE_ID + 1);
784 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
785
786 /* Case 5: Test with right instance, port & wrong rxq */
787 err = rte_event_eth_tx_adapter_queue_stop(TEST_ETHDEV_ID,
788 TEST_ETH_QUEUE_ID + 2);
789 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
790
791 err = rte_event_eth_tx_adapter_queue_start(TEST_ETHDEV_ID,
792 TEST_ETH_QUEUE_ID + 2);
793 TEST_ASSERT(err == -EINVAL, "Expected -EINVAL got %d", err);
794
795 /* Delete all queues from the Tx adapter */
796 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID,
797 TEST_ETHDEV_ID,
798 -1);
799 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
800
801 return TEST_SUCCESS;
802 }
803
804 static int
tx_adapter_set_get_params(void)805 tx_adapter_set_get_params(void)
806 {
807 int err, rc;
808 struct rte_event_eth_tx_adapter_runtime_params in_params;
809 struct rte_event_eth_tx_adapter_runtime_params out_params;
810
811 err = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
812 TEST_ETHDEV_ID,
813 0);
814 if (err == -ENOTSUP) {
815 rc = TEST_SKIPPED;
816 goto skip;
817 }
818 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
819
820 err = rte_event_eth_tx_adapter_runtime_params_init(&in_params);
821 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
822 err = rte_event_eth_tx_adapter_runtime_params_init(&out_params);
823 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
824
825 /* Case 1: Get the default values of adapter */
826 err = rte_event_eth_tx_adapter_runtime_params_get(TEST_INST_ID,
827 &out_params);
828 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
829 TEST_ASSERT(out_params.flush_threshold == DEFAULT_FLUSH_THRESHOLD,
830 "Expected %u got %u",
831 DEFAULT_FLUSH_THRESHOLD, out_params.flush_threshold);
832 TEST_ASSERT(out_params.max_nb_tx == TXA_NB_TX_WORK_DEFAULT,
833 "Expected %u got %u",
834 TXA_NB_TX_WORK_DEFAULT, out_params.max_nb_tx);
835
836 /* Case 2: Set max_nb_tx = 32 (=TXA_BATCH_SEIZE) */
837 in_params.max_nb_tx = 32;
838 in_params.flush_threshold = DEFAULT_FLUSH_THRESHOLD;
839
840 err = rte_event_eth_tx_adapter_runtime_params_set(TEST_INST_ID,
841 &in_params);
842 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
843
844 err = rte_event_eth_tx_adapter_runtime_params_get(TEST_INST_ID,
845 &out_params);
846 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
847 TEST_ASSERT(in_params.max_nb_tx == out_params.max_nb_tx,
848 "Expected %u got %u",
849 in_params.max_nb_tx, out_params.max_nb_tx);
850 TEST_ASSERT(in_params.flush_threshold == out_params.flush_threshold,
851 "Expected %u got %u",
852 in_params.flush_threshold, out_params.flush_threshold);
853
854 /* Case 3: Set max_nb_tx = 192 */
855 in_params.max_nb_tx = 192;
856
857 err = rte_event_eth_tx_adapter_runtime_params_set(TEST_INST_ID,
858 &in_params);
859 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
860
861 err = rte_event_eth_tx_adapter_runtime_params_get(TEST_INST_ID,
862 &out_params);
863 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
864 TEST_ASSERT(in_params.max_nb_tx == out_params.max_nb_tx,
865 "Expected %u got %u",
866 in_params.max_nb_tx, out_params.max_nb_tx);
867
868 /* Case 4: Set max_nb_tx = 256 */
869 in_params.max_nb_tx = 256;
870
871 err = rte_event_eth_tx_adapter_runtime_params_set(TEST_INST_ID,
872 &in_params);
873 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
874
875 err = rte_event_eth_tx_adapter_runtime_params_get(TEST_INST_ID,
876 &out_params);
877 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
878 TEST_ASSERT(in_params.max_nb_tx == out_params.max_nb_tx,
879 "Expected %u got %u",
880 in_params.max_nb_tx, out_params.max_nb_tx);
881
882 /* Case 5: Set max_nb_tx = 30(<TXA_BATCH_SIZE) */
883 in_params.max_nb_tx = 30;
884
885 err = rte_event_eth_tx_adapter_runtime_params_set(TEST_INST_ID,
886 &in_params);
887 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
888
889 err = rte_event_eth_tx_adapter_runtime_params_get(TEST_INST_ID,
890 &out_params);
891 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
892 TEST_ASSERT(in_params.max_nb_tx == out_params.max_nb_tx,
893 "Expected %u got %u",
894 in_params.max_nb_tx, out_params.max_nb_tx);
895
896 /* Case 6: Set max_nb_tx = 512 */
897 in_params.max_nb_tx = 512;
898
899 err = rte_event_eth_tx_adapter_runtime_params_set(TEST_INST_ID,
900 &in_params);
901 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
902
903 err = rte_event_eth_tx_adapter_runtime_params_get(TEST_INST_ID,
904 &out_params);
905 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
906 TEST_ASSERT(in_params.max_nb_tx == out_params.max_nb_tx,
907 "Expected %u got %u",
908 in_params.max_nb_tx, out_params.max_nb_tx);
909
910 /* Case 7: Set flush_threshold = 10 */
911 in_params.max_nb_tx = 128;
912 in_params.flush_threshold = 10;
913
914 err = rte_event_eth_tx_adapter_runtime_params_set(TEST_INST_ID,
915 &in_params);
916 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
917
918 err = rte_event_eth_tx_adapter_runtime_params_get(TEST_INST_ID,
919 &out_params);
920 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
921 TEST_ASSERT(in_params.max_nb_tx == out_params.max_nb_tx,
922 "Expected %u got %u",
923 in_params.max_nb_tx, out_params.max_nb_tx);
924 TEST_ASSERT(in_params.flush_threshold == out_params.flush_threshold,
925 "Expected %u got %u",
926 in_params.flush_threshold, out_params.flush_threshold);
927 rc = TEST_SUCCESS;
928 skip:
929 err = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID,
930 TEST_ETHDEV_ID,
931 0);
932 TEST_ASSERT(err == 0, "Expected 0 got %d", err);
933
934 return rc;
935 }
936
937 static int
tx_adapter_dynamic_device(void)938 tx_adapter_dynamic_device(void)
939 {
940 uint16_t port_id = rte_eth_dev_count_avail();
941 const char *null_dev[2] = { "eth_null0", "eth_null1" };
942 struct rte_eth_conf dev_conf;
943 int ret;
944 size_t i;
945
946 memset(&dev_conf, 0, sizeof(dev_conf));
947 for (i = 0; i < RTE_DIM(null_dev); i++) {
948 ret = rte_vdev_init(null_dev[i], NULL);
949 TEST_ASSERT_SUCCESS(ret, "%s Port creation failed %d",
950 null_dev[i], ret);
951
952 if (i == 0) {
953 ret = tx_adapter_create();
954 TEST_ASSERT_SUCCESS(ret, "Adapter create failed %d",
955 ret);
956 }
957
958 ret = rte_eth_dev_configure(port_id + i, MAX_NUM_QUEUE,
959 MAX_NUM_QUEUE, &dev_conf);
960 TEST_ASSERT_SUCCESS(ret, "Failed to configure device %d", ret);
961
962 ret = rte_event_eth_tx_adapter_queue_add(TEST_INST_ID,
963 port_id + i, 0);
964 TEST_ASSERT_SUCCESS(ret, "Failed to add queues %d", ret);
965
966 }
967
968 for (i = 0; i < RTE_DIM(null_dev); i++) {
969 ret = rte_event_eth_tx_adapter_queue_del(TEST_INST_ID,
970 port_id + i, -1);
971 TEST_ASSERT_SUCCESS(ret, "Failed to delete queues %d", ret);
972 }
973
974 tx_adapter_free();
975
976 for (i = 0; i < RTE_DIM(null_dev); i++)
977 rte_vdev_uninit(null_dev[i]);
978
979 return TEST_SUCCESS;
980 }
981
982 static struct unit_test_suite event_eth_tx_tests = {
983 .setup = testsuite_setup,
984 .teardown = testsuite_teardown,
985 .suite_name = "tx event eth adapter test suite",
986 .unit_test_cases = {
987 TEST_CASE_ST(NULL, NULL, tx_adapter_create_free),
988 TEST_CASE_ST(tx_adapter_create, tx_adapter_free,
989 tx_adapter_queue_add_del),
990 TEST_CASE_ST(tx_adapter_create, tx_adapter_free,
991 tx_adapter_start_stop),
992 TEST_CASE_ST(tx_adapter_create, tx_adapter_free,
993 tx_adapter_service),
994 TEST_CASE_ST(tx_adapter_create, tx_adapter_free,
995 tx_adapter_instance_get),
996 TEST_CASE_ST(tx_adapter_create, tx_adapter_free,
997 tx_adapter_queue_start_stop),
998 TEST_CASE_ST(tx_adapter_create, tx_adapter_free,
999 tx_adapter_set_get_params),
1000 TEST_CASE_ST(NULL, NULL, tx_adapter_dynamic_device),
1001 TEST_CASES_END() /**< NULL terminate unit test array */
1002 }
1003 };
1004
1005 static int
test_event_eth_tx_adapter_common(void)1006 test_event_eth_tx_adapter_common(void)
1007 {
1008 return unit_test_suite_runner(&event_eth_tx_tests);
1009 }
1010
1011 #endif /* !RTE_EXEC_ENV_WINDOWS */
1012
1013 REGISTER_FAST_TEST(event_eth_tx_adapter_autotest, false, true, test_event_eth_tx_adapter_common);
1014