API Reference Manual 1.51.0
Loading...
Searching...
No Matches
odp_packet_dump.c
1/* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright (c) 2018 Linaro Limited
3 * Copyright (c) 2024 Nokia
4 */
5
14#include <stdio.h>
15#include <string.h>
16#include <signal.h>
17#include <stdlib.h>
18#include <stdint.h>
19#include <inttypes.h>
20#include <getopt.h>
21
22#include <odp_api.h>
23#include <odp/helper/odph_api.h>
24
25#define MAX_PKTIOS 32
26#define MAX_PKTIO_NAME 255
27#define MAX_PKT_NUM 1024
28#define MAX_FILTERS 32
29
30typedef struct test_options_t {
31 uint64_t num_packet;
32 uint32_t data_offset;
33 uint32_t data_len;
34 int verbose;
35 int num_pktio;
36 char pktio_name[MAX_PKTIOS][MAX_PKTIO_NAME + 1];
37 int num_filter_l3;
38 int filter_l3[MAX_FILTERS];
39 int num_filter_l4;
40 int filter_l4[MAX_FILTERS];
41
42} test_options_t;
43
44typedef struct test_global_t {
45 test_options_t opt;
46 odp_pool_t pool;
48
49 struct {
50 odp_pktio_t pktio;
51 int started;
52
53 } pktio[MAX_PKTIOS];
54
55} test_global_t;
56
57static test_global_t test_global;
58
59static void sig_handler(int signo)
60{
61 (void)signo;
62
63 odp_atomic_store_u32(&test_global.stop, 1);
64}
65
66static void print_usage(void)
67{
68 printf("\n"
69 "Print received packets\n"
70 "\n"
71 "OPTIONS:\n"
72 " -i, --interface <name> Packet IO interfaces (comma-separated, no spaces)\n"
73 " -n, --num_packet <number> Exit after this many packets. Use 0 to run infinitely. Default 0.\n"
74 " -o, --data_offset <number> Data print start offset in bytes. Default 0.\n"
75 " -l, --data_length <number> Data print length in bytes. Default 0.\n"
76 " --filter_l3 <type> Print only packets with matching L3 type. Comma-separated\n"
77 " list (no spaces) of ODP L3 type values (e.g. value of ODP_PROTO_L3_TYPE_IPV4).\n"
78 " --filter_l4 <type> Print only packets with matching L4 type. Comma-separated\n"
79 " list (no spaces) of ODP L4 type values (e.g. value of ODP_PROTO_L4_TYPE_TCP).\n"
80 " -v, --verbose Print extra packet information.\n"
81 " -h, --help Display help and exit.\n\n");
82}
83
84static int parse_int_list(char *str, int integer[], int max_num)
85{
86 int str_len, len;
87 int i = 0;
88
89 str_len = strlen(str);
90
91 while (str_len > 0) {
92 len = strcspn(str, ",");
93 str[len] = 0;
94
95 if (i == max_num) {
96 ODPH_ERR("Maximum number of options is %i\n", max_num);
97 return -1;
98 }
99
100 integer[i] = atoi(str);
101
102 str_len -= len + 1;
103 str += len + 1;
104 i++;
105 }
106
107 return i;
108}
109
110static int parse_options(int argc, char *argv[], test_global_t *global)
111{
112 int i, opt;
113 char *name, *str;
114 int len, str_len, num;
115
116 const struct option longopts[] = {
117 {"interface", required_argument, NULL, 'i'},
118 {"num_packet", required_argument, NULL, 'n'},
119 {"data_offset", required_argument, NULL, 'o'},
120 {"data_length", required_argument, NULL, 'l'},
121 {"verbose", no_argument, NULL, 'v'},
122 {"help", no_argument, NULL, 'h'},
123 {"filter_l3", required_argument, NULL, 0 },
124 {"filter_l4", required_argument, NULL, 1 },
125 {NULL, 0, NULL, 0}
126 };
127 const char *shortopts = "+i:n:o:l:vh";
128 int ret = 0;
129
130 while (1) {
131 opt = getopt_long(argc, argv, shortopts, longopts, NULL);
132
133 if (opt == -1)
134 break; /* No more options */
135
136 switch (opt) {
137 case 0:
138 /* --filter_l3 */
139 num = parse_int_list(optarg, global->opt.filter_l3,
140 MAX_FILTERS);
141 global->opt.num_filter_l3 = num;
142
143 if (num < 0)
144 ret = -1;
145 break;
146 case 1:
147 /* --filter_l4 */
148 num = parse_int_list(optarg, global->opt.filter_l4,
149 MAX_FILTERS);
150 global->opt.num_filter_l4 = num;
151
152 if (num < 0)
153 ret = -1;
154 break;
155 case 'i':
156 i = 0;
157 str = optarg;
158 str_len = strlen(str);
159
160 while (str_len > 0) {
161 len = strcspn(str, ",");
162 str_len -= len + 1;
163
164 if (i == MAX_PKTIOS) {
165 ODPH_ERR("Too many interfaces\n");
166 ret = -1;
167 break;
168 }
169
170 if (len > MAX_PKTIO_NAME) {
171 ODPH_ERR("Too long interface name %s\n", str);
172 ret = -1;
173 break;
174 }
175
176 name = global->opt.pktio_name[i];
177 memcpy(name, str, len);
178 str += len + 1;
179 i++;
180 }
181
182 global->opt.num_pktio = i;
183
184 break;
185 case 'o':
186 global->opt.data_offset = atoi(optarg);
187 break;
188 case 'l':
189 global->opt.data_len = atoi(optarg);
190 break;
191 case 'n':
192 global->opt.num_packet = atoll(optarg);
193 break;
194 case 'v':
195 global->opt.verbose = 1;
196 break;
197 case 'h':
198 default:
199 print_usage();
200 return -1;
201 }
202 }
203
204 if (global->opt.num_pktio == 0) {
205 ODPH_ERR("At least one pktio interface needed\n");
206 ret = -1;
207 }
208
209 return ret;
210}
211
212static int open_pktios(test_global_t *global)
213{
214 odp_pool_param_t pool_param;
215 odp_pktio_param_t pktio_param;
216 odp_pool_t pool;
217 odp_pktio_capability_t pktio_capa;
218 odp_pool_capability_t pool_capa;
219 odp_pktio_t pktio;
220 odp_pktio_config_t pktio_config;
221 odp_pktin_queue_param_t pktin_param;
222 char *name;
223 int i, num_pktio;
224 uint32_t num_pkt = MAX_PKT_NUM;
225
226 num_pktio = global->opt.num_pktio;
227
228 if (odp_pool_capability(&pool_capa)) {
229 ODPH_ERR("Pool capability failed\n");
230 return -1;
231 }
232
233 if (pool_capa.pkt.max_num < MAX_PKT_NUM)
234 num_pkt = pool_capa.pkt.max_num;
235
236 odp_pool_param_init(&pool_param);
237 pool_param.pkt.num = num_pkt;
238 pool_param.type = ODP_POOL_PACKET;
239
240 pool = odp_pool_create("packet pool", &pool_param);
241
242 global->pool = pool;
243
244 if (pool == ODP_POOL_INVALID) {
245 ODPH_ERR("Pool create failed\n");
246 return -1;
247 }
248
249 odp_pktio_param_init(&pktio_param);
250 pktio_param.in_mode = ODP_PKTIN_MODE_SCHED;
252
253 for (i = 0; i < num_pktio; i++)
254 global->pktio[i].pktio = ODP_PKTIO_INVALID;
255
256 /* Open and configure interfaces */
257 for (i = 0; i < num_pktio; i++) {
258 name = global->opt.pktio_name[i];
259 pktio = odp_pktio_open(name, pool, &pktio_param);
260
261 if (pktio == ODP_PKTIO_INVALID) {
262 ODPH_ERR("Pktio open failed for %s\n", name);
263 return -1;
264 }
265
266 global->pktio[i].pktio = pktio;
267
268 if (odp_pktio_capability(pktio, &pktio_capa)) {
269 ODPH_ERR("Pktio capability failed for %s\n", name);
270 return -1;
271 }
272
273 odp_pktio_print(pktio);
274
275 odp_pktio_config_init(&pktio_config);
276 pktio_config.pktin.bit.ts_all = pktio_capa.config.pktin.bit.ts_all;
277 pktio_config.parser.layer = ODP_PROTO_LAYER_ALL;
278
279 odp_pktio_config(pktio, &pktio_config);
280
281 odp_pktin_queue_param_init(&pktin_param);
282
286 pktin_param.num_queues = 1;
287
288 if (odp_pktin_queue_config(pktio, &pktin_param)) {
289 ODPH_ERR("Pktin config failed for %s\n", name);
290 return -1;
291 }
292 }
293
294 return 0;
295}
296
297static int start_pktios(test_global_t *global)
298{
299 int i;
300
301 for (i = 0; i < global->opt.num_pktio; i++) {
302 if (odp_pktio_start(global->pktio[i].pktio)) {
303 ODPH_ERR("Pktio start failed for %s\n", global->opt.pktio_name[i]);
304
305 return -1;
306 }
307
308 global->pktio[i].started = 1;
309 }
310
311 return 0;
312}
313
314static int stop_pktios(test_global_t *global)
315{
316 odp_pktio_t pktio;
317 int i, ret = 0;
318
319 for (i = 0; i < global->opt.num_pktio; i++) {
320 pktio = global->pktio[i].pktio;
321
322 if (pktio == ODP_PKTIO_INVALID || global->pktio[i].started == 0)
323 continue;
324
325 if (odp_pktio_stop(pktio)) {
326 ODPH_ERR("Pktio stop failed for %s\n", global->opt.pktio_name[i]);
327 ret = -1;
328 }
329 }
330
331 return ret;
332}
333
334static void empty_queues(void)
335{
336 odp_event_t ev;
337 uint64_t wait_time = odp_schedule_wait_time(ODP_TIME_SEC_IN_NS / 2);
338
339 /* Drop all events from all queues */
340 while (1) {
341 ev = odp_schedule(NULL, wait_time);
342
343 if (ev == ODP_EVENT_INVALID)
344 break;
345
346 odp_event_free(ev);
347 }
348}
349
350static int close_pktios(test_global_t *global)
351{
352 odp_pktio_t pktio;
353 odp_pool_t pool;
354 int i, ret = 0;
355
356 for (i = 0; i < global->opt.num_pktio; i++) {
357 pktio = global->pktio[i].pktio;
358
359 if (pktio == ODP_PKTIO_INVALID)
360 continue;
361
362 if (odp_pktio_close(pktio)) {
363 ODPH_ERR("Pktio close failed for %s\n", global->opt.pktio_name[i]);
364 ret = -1;
365 }
366 }
367
368 pool = global->pool;
369
370 if (pool == ODP_POOL_INVALID)
371 return ret;
372
373 if (odp_pool_destroy(pool)) {
374 ODPH_ERR("Pool destroy failed\n");
375 ret = -1;
376 }
377
378 return ret;
379}
380
381static void print_mac_addr(uint8_t *addr)
382{
383 printf("%02x:%02x:%02x:%02x:%02x:%02x\n",
384 addr[0], addr[1], addr[2], addr[3], addr[4], addr[5]);
385}
386
387static void print_ipv4_addr(uint8_t *addr)
388{
389 printf("%u.%u.%u.%u\n",
390 addr[0], addr[1], addr[2], addr[3]);
391}
392
393static void print_port(uint8_t *ptr)
394{
395 uint16_t *port = (uint16_t *)(uintptr_t)ptr;
396
397 printf("%u\n", odp_be_to_cpu_16(*port));
398}
399
400static void print_data(odp_packet_t pkt, uint32_t offset, uint32_t len)
401{
402 const uint32_t bytes_per_row = 16;
403 const uint32_t num_char = 1 + (bytes_per_row * 3) + 1;
404 uint8_t data[bytes_per_row];
405 char row[num_char];
406 uint32_t copy_len, i, j;
407 uint32_t data_len = odp_packet_len(pkt);
408
409 if (offset > data_len)
410 return;
411
412 if (offset + len > data_len)
413 len = data_len - offset;
414
415 while (len) {
416 i = 0;
417
418 if (len > bytes_per_row)
419 copy_len = bytes_per_row;
420 else
421 copy_len = len;
422
423 odp_packet_copy_to_mem(pkt, offset, copy_len, data);
424
425 i += snprintf(&row[i], num_char - i, " ");
426
427 for (j = 0; j < copy_len; j++)
428 i += snprintf(&row[i], num_char - i, " %02x", data[j]);
429
430 row[i] = 0;
431 printf("%s\n", row);
432
433 len -= copy_len;
434 offset += copy_len;
435 }
436}
437
438static int print_packet(test_global_t *global, odp_packet_t pkt,
439 uint64_t num_packet)
440{
441 odp_pktio_t pktio = odp_packet_input(pkt);
442 odp_pktio_info_t pktio_info;
443 odp_time_t pktio_time, time;
444 uint64_t sec, nsec;
445 uint32_t offset;
446 int i, type, match;
447 int num_filter_l3 = global->opt.num_filter_l3;
448 int num_filter_l4 = global->opt.num_filter_l4;
449 uint8_t *data = odp_packet_data(pkt);
450 uint32_t seg_len = odp_packet_seg_len(pkt);
451 uint32_t l2_offset = odp_packet_l2_offset(pkt);
452 uint32_t l3_offset = odp_packet_l3_offset(pkt);
453 uint32_t l4_offset = odp_packet_l4_offset(pkt);
454 int tcp = odp_packet_has_tcp(pkt);
455 int udp = odp_packet_has_udp(pkt);
456 int sctp = odp_packet_has_sctp(pkt);
457 int icmp = odp_packet_has_icmp(pkt);
458 int ipv4 = odp_packet_has_ipv4(pkt);
459
460 if (odp_packet_has_ts(pkt)) {
461 pktio_time = odp_pktio_time(pktio, NULL);
462 time = odp_packet_ts(pkt);
463 } else {
464 time = odp_time_local();
465 pktio_time = ODP_TIME_NULL;
466 }
467
468 /* Filter based on L3 type */
469 if (num_filter_l3) {
470 match = 0;
471
472 for (i = 0; i < num_filter_l3; i++) {
473 type = global->opt.filter_l3[i];
474
475 if (type == odp_packet_l3_type(pkt)) {
476 match = 1;
477 break;
478 }
479 }
480
481 if (!match)
482 return 0;
483 }
484
485 /* Filter based on L4 type */
486 if (num_filter_l4) {
487 match = 0;
488
489 for (i = 0; i < num_filter_l4; i++) {
490 type = global->opt.filter_l4[i];
491
492 if (type == odp_packet_l4_type(pkt)) {
493 match = 1;
494 break;
495 }
496 }
497
498 if (!match)
499 return 0;
500 }
501
502 nsec = odp_time_to_ns(time);
503 sec = nsec / ODP_TIME_SEC_IN_NS;
504 nsec = nsec - (sec * ODP_TIME_SEC_IN_NS);
505
506 if (odp_pktio_info(pktio, &pktio_info)) {
507 ODPH_ERR("Pktio info failed\n");
508 return -1;
509 }
510
511 printf("PACKET [%" PRIu64 "]\n", num_packet);
512 printf(" time: %" PRIu64 ".%09" PRIu64 " sec\n", sec, nsec);
513
514 if (odp_time_cmp(pktio_time, ODP_TIME_NULL)) {
515 nsec = odp_time_to_ns(pktio_time);
516 sec = nsec / ODP_TIME_SEC_IN_NS;
517 nsec = nsec - (sec * ODP_TIME_SEC_IN_NS);
518 printf(" pktio time: %" PRIu64 ".%09" PRIu64 " sec\n", sec, nsec);
519 printf(" input delay: %" PRIu64 " nsec\n", odp_time_diff_ns(pktio_time, time));
520 }
521
522 printf(" interface name: %s\n", pktio_info.name);
523 printf(" packet length: %u bytes\n", odp_packet_len(pkt));
524
525 /* L2 */
526 if (odp_packet_has_eth(pkt)) {
527 uint8_t *eth = data + l2_offset;
528
529 printf(" Ethernet offset: %u bytes\n", l2_offset);
530 if (l2_offset + 6 <= seg_len) {
531 printf(" dst address: ");
532 print_mac_addr(eth);
533 }
534
535 if (l2_offset + 12 <= seg_len) {
536 printf(" src address: ");
537 print_mac_addr(eth + 6);
538 }
539
540 /* VLAN */
541 if (odp_packet_has_vlan(pkt)) {
542 int qinq = odp_packet_has_vlan_qinq(pkt);
543 uint16_t *tpid = (uint16_t *)(uintptr_t)(eth + 12);
544 uint16_t *tci = tpid + 1;
545
546 if (qinq)
547 printf(" VLAN (outer):\n");
548 else
549 printf(" VLAN:\n");
550
551 if (l2_offset + 14 <= seg_len) {
552 printf(" TPID: 0x%04x\n",
553 odp_be_to_cpu_16(*tpid));
554 }
555
556 if (l2_offset + 16 <= seg_len) {
557 printf(" TCI: 0x%04x (VID: %u)\n",
558 odp_be_to_cpu_16(*tci),
559 odp_be_to_cpu_16(*tci) & 0x0fff);
560 }
561
562 if (qinq) {
563 printf(" VLAN (inner):\n");
564 tpid += 2;
565 tci += 2;
566
567 if (l2_offset + 18 <= seg_len) {
568 printf(" TPID: 0x%04x\n",
569 odp_be_to_cpu_16(*tpid));
570 }
571
572 if (l2_offset + 20 <= seg_len) {
573 printf(" TCI: 0x%04x (VID: %u)\n",
574 odp_be_to_cpu_16(*tci),
575 odp_be_to_cpu_16(*tci) & 0x0fff);
576 }
577 }
578 }
579
580 } else if (odp_packet_has_l2(pkt)) {
581 printf(" L2 (%i) offset: %u bytes\n",
582 odp_packet_l2_type(pkt), l2_offset);
583 }
584
585 /* L3 */
586 if (ipv4) {
587 printf(" IPv4 offset: %u bytes\n", l3_offset);
588 offset = l3_offset + 12;
589 if (offset + 4 <= seg_len) {
590 printf(" src address: ");
591 print_ipv4_addr(data + offset);
592 }
593
594 offset = l3_offset + 16;
595 if (offset + 4 <= seg_len) {
596 printf(" dst address: ");
597 print_ipv4_addr(data + offset);
598 }
599 } else if (odp_packet_has_ipv6(pkt)) {
600 printf(" IPv6 offset: %u bytes\n", l3_offset);
601 } else if (odp_packet_has_l3(pkt)) {
602 printf(" L3 (%i) offset: %u bytes\n",
603 odp_packet_l3_type(pkt), l3_offset);
604 }
605
606 /* L4 */
607 if (tcp || udp || sctp) {
608 if (tcp)
609 printf(" TCP offset: %u bytes\n", l4_offset);
610 else if (udp)
611 printf(" UDP offset: %u bytes\n", l4_offset);
612 else
613 printf(" SCTP offset: %u bytes\n", l4_offset);
614
615 offset = l4_offset;
616 if (offset + 2 <= seg_len) {
617 printf(" src port: ");
618 print_port(data + offset);
619 }
620
621 offset = l4_offset + 2;
622 if (offset + 2 <= seg_len) {
623 printf(" dst port: ");
624 print_port(data + offset);
625 }
626 } else if (icmp) {
627 printf(" ICMP offset: %u bytes\n", l4_offset);
628 if (ipv4) {
629 uint32_t len;
630 uint8_t *u8 = odp_packet_l4_ptr(pkt, &len);
631
632 if (u8 && len >= 2) {
633 printf(" type: %u\n", u8[0]);
634 printf(" code: %u\n", u8[1]);
635 }
636 }
637 } else if (odp_packet_has_l4(pkt)) {
638 printf(" L4 (%i) offset: %u bytes\n",
639 odp_packet_l4_type(pkt), l4_offset);
640 }
641
642 /* User defined data range */
643 if (global->opt.data_len)
644 print_data(pkt, global->opt.data_offset, global->opt.data_len);
645
646 if (global->opt.verbose)
647 odp_packet_print(pkt);
648
649 printf("\n");
650
651 return 1;
652}
653
654static int receive_packets(test_global_t *global)
655{
656 odp_event_t ev;
657 odp_packet_t pkt;
658 int printed;
659 uint64_t num_packet = 0;
660
661 while (!odp_atomic_load_u32(&global->stop)) {
663
664 if (ev == ODP_EVENT_INVALID)
665 continue;
666
667 if (odp_event_type(ev) != ODP_EVENT_PACKET) {
668 ODPH_ERR("Bad event type: %i\n", odp_event_type(ev));
669 odp_event_free(ev);
670 continue;
671 }
672
673 pkt = odp_packet_from_event(ev);
674
675 printed = print_packet(global, pkt, num_packet);
676
677 odp_packet_free(pkt);
678
679 if (odp_unlikely(printed < 0))
680 return -1;
681
682 if (!printed)
683 continue;
684
685 num_packet++;
686 if (global->opt.num_packet &&
687 num_packet >= global->opt.num_packet)
688 break;
689 }
690
691 return 0;
692}
693
694int main(int argc, char *argv[])
695{
696 odp_instance_t instance;
697 test_global_t *global;
698 int ret = 0;
699
700 global = &test_global;
701 memset(global, 0, sizeof(test_global_t));
702 odp_atomic_init_u32(&global->stop, 0);
703
704 signal(SIGINT, sig_handler);
705
706 if (parse_options(argc, argv, global))
707 return -1;
708
709 /* Init ODP before calling anything else */
710 if (odp_init_global(&instance, NULL, NULL)) {
711 ODPH_ERR("Global init failed\n");
712 return -1;
713 }
714
715 /* Init this thread */
716 if (odp_init_local(instance, ODP_THREAD_CONTROL)) {
717 ODPH_ERR("Local init failed\n");
718 return -1;
719 }
720
721 global->pool = ODP_POOL_INVALID;
722
724
726
727 if (open_pktios(global)) {
728 ODPH_ERR("Pktio open failed\n");
729 return -1;
730 }
731
732 if (start_pktios(global)) {
733 ODPH_ERR("Pktio start failed\n");
734 return -1;
735 }
736
737 if (receive_packets(global)) {
738 ODPH_ERR("Packet receive failed\n");
739 return -1;
740 }
741
742 if (stop_pktios(global)) {
743 ODPH_ERR("Pktio stop failed\n");
744 return -1;
745 }
746
747 empty_queues();
748
749 if (close_pktios(global)) {
750 ODPH_ERR("Pktio close failed\n");
751 return -1;
752 }
753
754 if (odp_term_local()) {
755 ODPH_ERR("Term local failed\n");
756 return -1;
757 }
758
759 if (odp_term_global(instance)) {
760 ODPH_ERR("Term global failed\n");
761 return -1;
762 }
763
764 return ret;
765}
void odp_atomic_init_u32(odp_atomic_u32_t *atom, uint32_t val)
Initialize atomic uint32 variable.
uint32_t odp_atomic_load_u32(odp_atomic_u32_t *atom)
Load value of atomic uint32 variable.
void odp_atomic_store_u32(odp_atomic_u32_t *atom, uint32_t val)
Store value to atomic uint32 variable.
#define odp_unlikely(x)
Branch unlikely taken.
Definition spec/hints.h:64
uint16_t odp_be_to_cpu_16(odp_u16be_t be16)
Convert 16bit big endian to cpu native uint16_t.
void odp_event_free(odp_event_t event)
Free event.
odp_event_type_t odp_event_type(odp_event_t event)
Event type of an event.
#define ODP_EVENT_INVALID
Invalid event.
int odp_init_local(odp_instance_t instance, odp_thread_type_t thr_type)
Thread local ODP initialization.
int odp_init_global(odp_instance_t *instance, const odp_init_t *params, const odp_platform_init_t *platform_params)
Global ODP initialization.
int odp_term_local(void)
Thread local ODP termination.
int odp_term_global(odp_instance_t instance)
Global ODP termination.
uint64_t odp_instance_t
ODP instance ID.
void odp_pktin_queue_param_init(odp_pktin_queue_param_t *param)
Initialize packet input queue parameters.
void odp_pktio_param_init(odp_pktio_param_t *param)
Initialize pktio params.
int odp_pktio_close(odp_pktio_t pktio)
Close a packet IO interface.
int odp_pktio_info(odp_pktio_t pktio, odp_pktio_info_t *info)
Retrieve information about a pktio.
void odp_pktio_config_init(odp_pktio_config_t *config)
Initialize packet IO configuration options.
odp_pktio_t odp_pktio_open(const char *name, odp_pool_t pool, const odp_pktio_param_t *param)
Open a packet IO interface.
int odp_pktio_config(odp_pktio_t pktio, const odp_pktio_config_t *config)
Configure packet IO interface options.
void odp_pktio_print(odp_pktio_t pktio)
Print pktio info to the console.
int odp_pktio_start(odp_pktio_t pktio)
Start packet receive and transmit.
#define ODP_PKTIO_INVALID
Invalid packet IO handle.
odp_time_t odp_pktio_time(odp_pktio_t pktio, odp_time_t *ts_global)
Current packet IO time and global time.
int odp_pktio_stop(odp_pktio_t pktio)
Stop packet receive and transmit.
int odp_pktio_capability(odp_pktio_t pktio, odp_pktio_capability_t *capa)
Query packet IO interface capabilities.
int odp_pktin_queue_config(odp_pktio_t pktio, const odp_pktin_queue_param_t *param)
Configure packet input queues.
@ ODP_PKTOUT_MODE_DISABLED
Application will never send to this interface.
@ ODP_PKTIN_MODE_SCHED
Packet input through scheduler and scheduled event queues.
int odp_packet_has_l3(odp_packet_t pkt)
Check for layer 3 protocols.
odp_proto_l4_type_t odp_packet_l4_type(odp_packet_t pkt)
Layer 4 protocol type.
int odp_packet_has_ts(odp_packet_t pkt)
Check for packet timestamp.
uint32_t odp_packet_seg_len(odp_packet_t pkt)
Packet data length following the data pointer.
int odp_packet_has_icmp(odp_packet_t pkt)
Check for ICMP.
int odp_packet_has_ipv4(odp_packet_t pkt)
Check for IPv4.
uint32_t odp_packet_l4_offset(odp_packet_t pkt)
Layer 4 start offset.
void * odp_packet_data(odp_packet_t pkt)
Packet data pointer.
int odp_packet_has_eth(odp_packet_t pkt)
Check for Ethernet header.
int odp_packet_has_vlan_qinq(odp_packet_t pkt)
Check for VLAN QinQ (stacked VLAN)
odp_proto_l2_type_t odp_packet_l2_type(odp_packet_t pkt)
Layer 2 protocol type.
int odp_packet_has_l4(odp_packet_t pkt)
Check for layer 4 protocols.
uint32_t odp_packet_len(odp_packet_t pkt)
Packet data length.
int odp_packet_has_ipv6(odp_packet_t pkt)
Check for IPv6.
int odp_packet_has_l2(odp_packet_t pkt)
Check for layer 2 protocols.
odp_packet_t odp_packet_from_event(odp_event_t ev)
Get packet handle from event.
void odp_packet_free(odp_packet_t pkt)
Free packet.
int odp_packet_has_vlan(odp_packet_t pkt)
Check for VLAN.
uint32_t odp_packet_l3_offset(odp_packet_t pkt)
Layer 3 start offset.
int odp_packet_has_sctp(odp_packet_t pkt)
Check for SCTP.
odp_proto_l3_type_t odp_packet_l3_type(odp_packet_t pkt)
Layer 3 protocol type.
int odp_packet_has_tcp(odp_packet_t pkt)
Check for TCP.
void odp_packet_print(odp_packet_t pkt)
Print packet debug information.
void * odp_packet_l4_ptr(odp_packet_t pkt, uint32_t *len)
Layer 4 start pointer.
int odp_packet_copy_to_mem(odp_packet_t pkt, uint32_t offset, uint32_t len, void *dst)
Copy data from packet to memory.
odp_time_t odp_packet_ts(odp_packet_t pkt)
Packet timestamp.
int odp_packet_has_udp(odp_packet_t pkt)
Check for UDP.
odp_pktio_t odp_packet_input(odp_packet_t pkt)
Packet input interface.
uint32_t odp_packet_l2_offset(odp_packet_t pkt)
Layer 2 start offset.
@ ODP_PROTO_LAYER_ALL
All layers.
odp_pool_t odp_pool_create(const char *name, const odp_pool_param_t *param)
Create a pool.
int odp_pool_capability(odp_pool_capability_t *capa)
Query pool capabilities.
void odp_pool_param_init(odp_pool_param_t *param)
Initialize pool params.
int odp_pool_destroy(odp_pool_t pool)
Destroy a pool previously created by odp_pool_create()
#define ODP_POOL_INVALID
Invalid pool.
@ ODP_POOL_PACKET
Packet pool.
#define ODP_SCHED_SYNC_ATOMIC
Atomic queue synchronization.
#define ODP_SCHED_NO_WAIT
Do not wait.
int odp_schedule_default_prio(void)
Default scheduling priority level.
int odp_schedule_config(const odp_schedule_config_t *config)
Global schedule configuration.
uint64_t odp_schedule_wait_time(uint64_t ns)
Schedule wait time.
odp_event_t odp_schedule(odp_queue_t *from, uint64_t wait)
Schedule an event.
#define ODP_SCHED_GROUP_ALL
Group of all threads.
void odp_sys_info_print(void)
Print system info.
@ ODP_THREAD_CONTROL
Control thread.
uint64_t odp_time_to_ns(odp_time_t time)
Convert time to nanoseconds.
#define ODP_TIME_SEC_IN_NS
A second in nanoseconds.
odp_time_t odp_time_local(void)
Current local time.
#define ODP_TIME_NULL
Zero time stamp.
int odp_time_cmp(odp_time_t t2, odp_time_t t1)
Compare two times.
uint64_t odp_time_diff_ns(odp_time_t t2, odp_time_t t1)
Time difference in nanoseconds.
The OpenDataPlane API.
Packet input queue parameters.
uint32_t num_queues
Number of input queues to be created.
odp_queue_param_t queue_param
Queue parameters.
odp_pktio_config_t config
Supported pktio configuration options.
Packet IO configuration options.
odp_pktio_parser_config_t parser
Packet input parser configuration.
odp_pktin_config_opt_t pktin
Packet input configuration options bit field.
Packet IO information.
const char * name
Packet IO device name.
Packet IO parameters.
odp_pktin_mode_t in_mode
Packet input mode.
odp_pktout_mode_t out_mode
Packet output mode.
odp_proto_layer_t layer
Protocol parsing level in packet input.
uint32_t max_num
Maximum number of buffers of any size.
struct odp_pool_capability_t::@134 pkt
Packet pool capabilities
uint32_t num
Number of buffers in the pool.
struct odp_pool_param_t::@139 pkt
Parameters for packet pools.
odp_pool_type_t type
Pool type.
odp_schedule_param_t sched
Scheduler parameters.
odp_schedule_group_t group
Thread group.
odp_schedule_prio_t prio
Priority level.
odp_schedule_sync_t sync
Synchronization method.
uint64_t ts_all
Timestamp all packets on packet input.
struct odp_pktin_config_opt_t::@108 bit
Option flags.