22#include <odp/helper/odph_api.h>
24#include <export_results.h>
26#define MAX_QUEUES (32 * 1024)
33typedef struct test_options_t {
46 uint64_t memcpy_bytes;
50typedef struct test_stat_t {
60typedef struct test_global_t test_global_t;
63 test_global_t *global;
65 test_options_t *options;
67 uint32_t src_queue_id[MAX_QUEUES];
68 uint32_t dst_queue_id[MAX_QUEUES];
75typedef struct test_global_t {
77 test_options_t options;
87 test_common_options_t common_options;
91static void print_usage(
void)
94 "Plain queue performance test\n"
96 "Usage: odp_queue_perf [options]\n"
98 " -m, --mode <arg> Test mode:\n"
99 " 0: Loop: events are enqueued back to the same queue they\n"
100 " were dequeued from (default)\n"
101 " 1: Pair: queues are paired and events are always moved\n"
102 " between the queues when doing dequeue/enqueue. Requires\n"
103 " an even number of both queues and workers.\n"
104 " -c, --num_cpu Number of worker threads (default 1)\n"
105 " -q, --num_queue Number of queues (default 1)\n"
106 " -e, --num_event Number of events per queue (default 1)\n"
107 " -b, --burst_size Maximum number of events per operation (default 1). When 0,\n"
108 " single event enqueue/dequeue functions are used instead\n"
109 " of multi event variants.\n"
110 " -p, --private Use separate queues for each worker\n"
111 " -r, --num_round Number of rounds\n"
112 " -l, --lockfree Lock-free queues\n"
113 " -w, --waitfree Wait-free queues\n"
114 " -s, --single Single producer/consumer queues\n"
115 " -M, --memcpy <num> Number of bytes to memcpy per dequeue burst before\n"
116 " enqueueing events. Default: 0.\n"
117 " -W, --wait_ns <ns> Number of nsecs to wait per dequeue burst before.\n"
118 " enqueueing events. Default: 0.\n"
119 " -h, --help This help\n"
123static int parse_options(
int argc,
char *argv[], test_options_t *test_options)
128 static const struct option longopts[] = {
129 {
"num_cpu", required_argument, NULL,
'c'},
130 {
"num_queue", required_argument, NULL,
'q'},
131 {
"num_event", required_argument, NULL,
'e'},
132 {
"burst_size", required_argument, NULL,
'b'},
133 {
"mode", required_argument, NULL,
'm'},
134 {
"private", no_argument, NULL,
'p'},
135 {
"num_round", required_argument, NULL,
'r'},
136 {
"lockfree", no_argument, NULL,
'l'},
137 {
"waitfree", no_argument, NULL,
'w'},
138 {
"single", no_argument, NULL,
's'},
139 {
"wait_ns", required_argument, NULL,
'W'},
140 {
"memcpy", required_argument, NULL,
'M'},
141 {
"help", no_argument, NULL,
'h'},
145 static const char *shortopts =
"+c:q:e:b:m:M:pr:lwW:sh";
147 test_options->num_cpu = 1;
148 test_options->num_queue = 1;
149 test_options->num_event = 1;
150 test_options->max_burst = 1;
151 test_options->mode = TEST_MODE_LOOP;
152 test_options->num_round = 1000;
154 test_options->single =
false;
155 test_options->private_queues =
false;
158 opt = getopt_long(argc, argv, shortopts, longopts, NULL);
165 test_options->num_cpu = atoi(optarg);
168 test_options->num_queue = atoi(optarg);
171 test_options->num_event = atoi(optarg);
174 test_options->max_burst = atoi(optarg);
177 if (atoi(optarg) == TEST_MODE_PAIR)
178 test_options->mode = TEST_MODE_PAIR;
181 test_options->num_round = atoi(optarg);
190 test_options->private_queues =
true;
193 test_options->single =
true;
196 test_options->wait_ns = atoll(optarg);
199 test_options->memcpy_bytes = atoll(optarg);
210 if (test_options->num_queue > MAX_QUEUES || test_options->num_queue == 0) {
211 ODPH_ERR(
"Invalid number of queues %u. Test maximum %u.\n",
212 test_options->num_queue, MAX_QUEUES);
216 num_cpu = test_options->num_cpu;
220 if (test_options->private_queues) {
221 if ((
int)test_options->num_queue < num_cpu) {
222 ODPH_ERR(
"Not enough queues for %d workers.\n", num_cpu);
225 if (test_options->num_queue % num_cpu)
226 ODPH_ERR(
"Warn: %" PRIu32
" queues shared unevenly amongst %" PRIu32
" "
227 "workers.\n", test_options->num_queue, num_cpu);
230 if (test_options->single && !test_options->private_queues) {
231 if ((test_options->mode == TEST_MODE_LOOP && num_cpu != 1) ||
232 (test_options->mode == TEST_MODE_PAIR && num_cpu != 2)) {
233 ODPH_ERR(
"Multiple producers/consumers not allowed with single prod/cons queues.\n");
238 if (test_options->mode == TEST_MODE_PAIR && (test_options->num_queue % 2 || num_cpu % 2)) {
239 ODPH_ERR(
"Pair mode requires an even number of queues and workers.\n");
243 if (test_options->wait_ns || test_options->memcpy_bytes)
244 test_options->extra_features_enabled =
true;
249static int create_queues(test_global_t *global)
256 uint32_t i, j, max_size, max_num;
257 test_options_t *test_options = &global->options;
259 uint32_t num_queue = test_options->num_queue;
260 uint32_t num_event = test_options->num_event;
261 uint32_t num_round = test_options->num_round;
262 uint32_t tot_event = num_queue * num_event;
263 uint32_t queue_size = test_options->mode == TEST_MODE_PAIR ? 2 * num_event : num_event;
268 printf(
"\nTesting %s queues\n",
272 printf(
" mode %s\n", test_options->mode == TEST_MODE_LOOP ?
274 printf(
" private queues %s\n", test_options->private_queues ?
"yes" :
"no");
275 printf(
" single prod/cons %s\n", test_options->single ?
"yes" :
"no");
276 printf(
" num rounds %u\n", num_round);
277 printf(
" num queues %u\n", num_queue);
278 printf(
" num events per queue %u\n", num_event);
279 printf(
" queue size %u\n", queue_size);
280 printf(
" max burst size %u\n", test_options->max_burst);
281 printf(
" wait %" PRIu64
" ns\n", test_options->wait_ns);
282 printf(
" memcpy %" PRIu64
" bytes\n", test_options->memcpy_bytes);
284 for (i = 0; i < num_queue; i++)
287 for (i = 0; i < tot_event; i++)
291 ODPH_ERR(
"Queue capa failed.\n");
296 ODPH_ERR(
"Pool capa failed.\n");
302 ODPH_ERR(
"Max queues supported %u.\n", queue_capa.
plain.
max_num);
307 if (max_size && queue_size > max_size) {
308 ODPH_ERR(
"Max queue size supported %u.\n", max_size);
313 ODPH_ERR(
"Lockfree queues not supported.\n");
318 ODPH_ERR(
"Max lockfree queues supported %u.\n",
324 if (max_size && queue_size > max_size) {
325 ODPH_ERR(
"Max lockfree queue size supported %u.\n", max_size);
330 ODPH_ERR(
"Waitfree queues not supported.\n");
335 ODPH_ERR(
"Max waitfree queues supported %u.\n",
341 if (max_size && queue_size > max_size) {
342 ODPH_ERR(
"Max waitfree queue size supported %u.\n", max_size);
346 ODPH_ERR(
"Bad queue blocking type.\n");
352 if (max_num && tot_event > max_num) {
353 ODPH_ERR(
"Max events supported %u.\n", max_num);
359 pool_param.
buf.
num = tot_event;
364 ODPH_ERR(
"Pool create failed.\n");
373 queue_param.
size = queue_size;
375 if (test_options->single) {
380 for (i = 0; i < num_queue; i++) {
384 ODPH_ERR(
"Queue create failed %u.\n", i);
389 for (i = 0; i < tot_event; i++) {
393 ODPH_ERR(
"Event alloc failed %u.\n", i);
399 for (i = 0; i < num_queue; i++) {
400 for (j = 0; j < num_event; j++) {
401 uint32_t
id = i * num_event + j;
404 ODPH_ERR(
"Queue enq failed %u/%u.\n", i, j);
415 for (i = 0; i < tot_event; i++) {
421 ODPH_ERR(
"Initializing test queues failed.\n");
426static int destroy_queues(test_global_t *global)
430 test_options_t *test_options = &global->options;
431 uint32_t num_queue = test_options->num_queue;
435 for (i = 0; i < num_queue; i++) {
448 ODPH_ERR(
"Queue destroy failed %u.\n", i);
455 ODPH_ERR(
"Pool destroy failed.\n");
464 uint32_t num_queue, uint32_t queue_idx)
466 *src_queue = src_queue_tbl[queue_idx];
467 *dst_queue = dst_queue_tbl[queue_idx];
470 if (queue_idx == num_queue)
476static int reserve_memcpy_memory(test_global_t *global)
478 uint64_t total_bytes;
481 const test_options_t *options = &global->options;
484 if (options->memcpy_bytes == 0)
487 total_bytes = 2 * options->memcpy_bytes * options->num_cpu;
489 global->memcpy_shm =
odp_shm_reserve(
"memcpy_shm", total_bytes, ODP_CACHE_LINE_SIZE, 0);
491 ODPH_ERR(
"Reserving %" PRIu64
" bytes for memcpy failed.\n", total_bytes);
496 if (global->memcpy_data == NULL) {
497 ODPH_ERR(
"Shared mem addr for memcpy failed.\n");
501 for (uint32_t t = 0; t < options->num_cpu; t++) {
502 src = &global->memcpy_data[t * 2 * options->memcpy_bytes];
503 dst = src + options->memcpy_bytes;
504 memset(src, 0xA5, options->memcpy_bytes);
505 memset(dst, 0x00, options->memcpy_bytes);
511static inline void process_features(
const test_options_t *test_options)
513 if (test_options->extra_features_enabled) {
514 if (test_options->wait_ns)
517 if (test_options->memcpy_bytes) {
518 const uint64_t bytes = test_options->memcpy_bytes;
519 uint8_t *memcpy_src = test_options->memcpy_src;
520 uint8_t *memcpy_dst = memcpy_src + bytes;
522 memcpy(memcpy_dst, memcpy_src, bytes);
528 uint32_t num_queue, uint32_t num_round, test_stat_t *stat,
529 const test_options_t *test_options)
533 uint32_t queue_idx = 0;
535 for (uint32_t i = 0; i < num_round; i++) {
537 queue_idx = next_queues(&src_queue, &dst_queue, src_queue_tbl,
538 dst_queue_tbl, num_queue, queue_idx);
547 process_features(test_options);
560 stat->rounds = num_round;
563static inline void run_single_event_cleanup(
odp_queue_t src_queue_tbl[],
565 uint32_t num_queue, uint32_t num_workers,
570 uint32_t queue_idx = 0;
573 queue_idx = next_queues(&src_queue, &dst_queue, src_queue_tbl, dst_queue_tbl,
574 num_queue, queue_idx);
590 uint32_t num_queue, uint32_t num_round, uint32_t max_burst,
591 test_stat_t *stat,
const test_options_t *test_options)
596 uint32_t queue_idx = 0;
598 for (uint32_t i = 0; i < num_round; i++) {
602 queue_idx = next_queues(&src_queue, &dst_queue, src_queue_tbl,
603 dst_queue_tbl, num_queue, queue_idx);
606 ODPH_ABORT(
"odp_queue_deq_multi() failed\n");
611 }
while (num_ev == 0);
613 process_features(test_options);
615 while (num_enq < num_ev) {
619 ODPH_ABORT(
"odp_queue_enq_multi() failed\n");
626 stat->events += num_ev;
628 stat->rounds = num_round;
632 uint32_t num_queue, uint32_t max_burst,
638 uint32_t queue_idx = 0;
642 queue_idx = next_queues(&src_queue, &dst_queue, src_queue_tbl, dst_queue_tbl,
643 num_queue, queue_idx);
646 while (num_enq < num_ev) {
650 ODPH_ABORT(
"odp_queue_enq_multi() failed\n");
657static int run_test(
void *arg)
659 uint64_t c1, c2, cycles, nsec;
661 thread_args_t *thr_args = arg;
662 test_global_t *global = thr_args->global;
663 test_options_t test_options = global->options;
664 test_stat_t *stat = &thr_args->stats;
665 test_stat_t local_stat = {0};
666 const uint32_t num_queue = thr_args->num_queues;
667 const uint32_t num_round = thr_args->options->num_round;
668 const uint32_t num_workers = thr_args->options->num_cpu;
669 const uint32_t max_burst = thr_args->options->max_burst;
670 const odp_bool_t single_event = max_burst == 0 ? 1 : 0;
671 odp_queue_t *src_queue_tbl = thr_args->src_queue_tbl;
672 odp_queue_t *dst_queue_tbl = thr_args->dst_queue_tbl;
675 if (test_options.memcpy_bytes)
676 test_options.memcpy_src = &global->memcpy_data
677 [thr_args->thr_idx * 2 * test_options.memcpy_bytes];
679 for (uint32_t i = 0; i < num_queue; i++) {
680 src_queue_tbl[i] = global->queue[thr_args->src_queue_id[i]];
681 dst_queue_tbl[i] = global->queue[thr_args->dst_queue_id[i]];
691 run_single_event(src_queue_tbl, dst_queue_tbl, num_queue, num_round, &local_stat,
694 run_multi_event(src_queue_tbl, dst_queue_tbl, num_queue, num_round, max_burst,
695 &local_stat, &test_options);
703 if (thr_args->options->mode == TEST_MODE_PAIR) {
705 run_single_event_cleanup(src_queue_tbl, dst_queue_tbl, num_queue,
706 num_workers, &global->workers_finished);
708 run_multi_event_cleanup(src_queue_tbl, dst_queue_tbl, num_queue, max_burst,
709 num_workers, &global->workers_finished);
715 stat->rounds = local_stat.rounds;
716 stat->events = local_stat.events;
718 stat->cycles = cycles;
719 stat->deq_retry = local_stat.deq_retry;
720 stat->enq_retry = local_stat.enq_retry;
725static void map_queues_to_threads(test_global_t *global)
727 test_options_t *opt = &global->options;
729 if (opt->mode == TEST_MODE_LOOP) {
730 if (!opt->private_queues) {
731 for (uint32_t i = 0; i < opt->num_queue; i++) {
732 for (uint32_t j = 0; j < opt->num_cpu; j++) {
733 thread_args_t *thread_args = &global->thread_args[j];
735 thread_args->src_queue_id[i] = i;
736 thread_args->dst_queue_id[i] = i;
737 thread_args->num_queues++;
743 for (uint32_t i = 0; i < opt->num_queue; i++) {
744 thread_args_t *thread_args = &global->thread_args[i % opt->num_cpu];
745 uint32_t queue_idx = thread_args->num_queues;
747 thread_args->src_queue_id[queue_idx] = i;
748 thread_args->dst_queue_id[queue_idx] = i;
749 thread_args->num_queues++;
754 if (!opt->private_queues) {
755 for (uint32_t i = 0; i < opt->num_queue; i += 2) {
756 for (uint32_t j = 0; j < opt->num_cpu; j++) {
757 thread_args_t *thread_args = &global->thread_args[j];
758 uint32_t num_queues = thread_args->num_queues;
761 thread_args->src_queue_id[num_queues] = i;
762 thread_args->dst_queue_id[num_queues] = i + 1;
764 thread_args->src_queue_id[num_queues] = i + 1;
765 thread_args->dst_queue_id[num_queues] = i;
767 thread_args->num_queues++;
773 for (uint32_t i = 0; i < opt->num_queue; i += 2) {
775 uint32_t thread_a_idx = i % opt->num_cpu;
776 thread_args_t *thread_a_args = &global->thread_args[thread_a_idx];
777 thread_args_t *thread_b_args = &global->thread_args[thread_a_idx + 1];
779 num_queues = thread_a_args->num_queues;
780 thread_a_args->src_queue_id[num_queues] = i;
781 thread_a_args->dst_queue_id[num_queues] = i + 1;
782 thread_a_args->num_queues++;
784 num_queues = thread_b_args->num_queues;
785 thread_b_args->src_queue_id[num_queues] = i + 1;
786 thread_b_args->dst_queue_id[num_queues] = i;
787 thread_b_args->num_queues++;
791static void print_queue_mappings(test_global_t *global)
793 printf(
"Worker-queue mappings\n");
794 printf(
"---------------------\n");
796 for (uint32_t i = 0; i < global->options.num_cpu; i++) {
797 thread_args_t *thread_args = &global->thread_args[i];
798 uint32_t num_queues = thread_args->num_queues;
800 printf(
"Worker %u:\n", i);
802 printf(
" src queue idx:");
803 for (uint32_t j = 0; j < num_queues; j++)
804 printf(
" %" PRIu32
"", thread_args->src_queue_id[j]);
805 printf(
"\n dst queue idx:");
806 for (uint32_t j = 0; j < num_queues; j++)
807 printf(
" %" PRIu32
"", thread_args->dst_queue_id[j]);
812static void init_thread_args(test_global_t *global)
814 for (uint32_t i = 0; i < global->options.num_cpu; i++) {
815 thread_args_t *thread_args = &global->thread_args[i];
817 thread_args->global = global;
818 thread_args->barrier = &global->barrier;
819 thread_args->options = &global->options;
820 thread_args->thr_idx = i;
823 map_queues_to_threads(global);
825 print_queue_mappings(global);
828static int start_workers(test_global_t *global)
830 odph_thread_common_param_t thr_common;
834 test_options_t *test_options = &global->options;
835 int num_cpu = test_options->num_cpu;
839 if (num_cpu && ret != num_cpu) {
840 ODPH_ERR(
"Too many workers. Max supported %i\n.", ret);
847 test_options->num_cpu = num_cpu;
850 printf(
" num workers %u\n\n", num_cpu);
854 odph_thread_common_param_init(&thr_common);
855 thr_common.instance = global->instance;
856 thr_common.cpumask = &cpumask;
858 init_thread_args(global);
860 for (
int i = 0; i < num_cpu; i++) {
861 odph_thread_param_init(&thr_param[i]);
862 thr_param[i].start = run_test;
863 thr_param[i].arg = &global->thread_args[i];
867 if (odph_thread_create(global->thread_tbl, &thr_common, thr_param,
874static int output_results(test_global_t *global)
877 double rounds_ave, events_ave, nsec_ave, cycles_ave;
879 test_options_t *test_options = &global->options;
880 int num_cpu = test_options->num_cpu;
881 uint64_t rounds_sum = 0;
882 uint64_t events_sum = 0;
883 uint64_t nsec_sum = 0;
884 uint64_t cycles_sum = 0;
885 uint64_t deq_retry_sum = 0;
886 uint64_t enq_retry_sum = 0;
890 stats = &global->thread_args[i].stats;
891 rounds_sum += stats->rounds;
892 events_sum += stats->events;
893 nsec_sum += stats->nsec;
894 cycles_sum += stats->cycles;
895 deq_retry_sum += stats->deq_retry;
896 enq_retry_sum += stats->enq_retry;
899 if (rounds_sum == 0) {
900 printf(
"No results.\n");
904 rounds_ave = rounds_sum / num_cpu;
905 events_ave = events_sum / num_cpu;
906 nsec_ave = nsec_sum / num_cpu;
907 cycles_ave = cycles_sum / num_cpu;
910 printf(
"RESULTS - per thread (Million events per sec):\n");
911 printf(
"----------------------------------------------\n");
912 printf(
" 1 2 3 4 5 6 7 8 9 10");
915 stats = &global->thread_args[i].stats;
920 printf(
"%6.1f ", (1000.0 * stats->events) / stats->nsec);
926 printf(
"RESULTS - per thread average (%i threads):\n", num_cpu);
927 printf(
"------------------------------------------\n");
928 printf(
" duration: %.3f msec\n", nsec_ave / 1000000);
929 printf(
" num cycles: %.3f M\n", cycles_ave / 1000000);
930 printf(
" events per dequeue: %.3f\n",
931 events_ave / rounds_ave);
932 printf(
" cycles per event: %.3f\n",
933 cycles_ave / events_ave);
934 printf(
" dequeue retries: %" PRIu64
"\n", deq_retry_sum);
935 printf(
" enqueue retries: %" PRIu64
"\n", enq_retry_sum);
936 printf(
" events per sec: %.3f M\n\n",
937 (1000.0 * events_ave) / nsec_ave);
939 printf(
"TOTAL events per sec: %.3f M\n\n",
940 (1000.0 * events_sum) / nsec_ave);
942 if (global->common_options.is_export) {
943 if (test_common_write(
"cycles per event,events per sec (M),total events per sec (M),"
944 "dequeue retries,enqueue retries\n")) {
945 test_common_write_term();
948 if (test_common_write(
"%f,%f,%f,%" PRIu64
",%" PRIu64
"\n",
949 cycles_ave / events_ave,
950 (1000.0 * events_ave) / nsec_ave,
951 (1000.0 * events_sum) / nsec_ave,
954 test_common_write_term();
957 test_common_write_term();
963int main(
int argc,
char **argv)
965 odph_helper_options_t helper_options;
969 test_global_t *global;
970 test_common_options_t common_options;
973 argc = odph_parse_options(argc, argv);
974 if (odph_options(&helper_options)) {
975 ODPH_ERR(
"Reading ODP helper options failed.\n");
979 argc = test_common_parse_options(argc, argv);
980 if (test_common_options(&common_options)) {
981 ODPH_ERR(
"Reading test options failed.\n");
995 init.
mem_model = helper_options.mem_model;
999 ODPH_ERR(
"Global init failed.\n");
1005 ODPH_ERR(
"Local init failed.\n");
1009 shm =
odp_shm_reserve(
"queue_perf_global",
sizeof(test_global_t), ODP_CACHE_LINE_SIZE, 0);
1011 ODPH_ERR(
"Shared memory reserve failed.\n");
1016 if (global == NULL) {
1017 ODPH_ERR(
"Shared memory address read failed.\n");
1021 memset(global, 0,
sizeof(test_global_t));
1022 global->common_options = common_options;
1025 if (parse_options(argc, argv, &global->options))
1030 global->instance = instance;
1032 if (create_queues(global))
1035 if (reserve_memcpy_memory(global))
1038 if (start_workers(global)) {
1039 ODPH_ERR(
"Test start failed.\n");
1044 odph_thread_join(global->thread_tbl, global->options.num_cpu);
1046 if (output_results(global)) {
1047 ODPH_ERR(
"Outputting results failed.\n");
1052 if (destroy_queues(global)) {
1053 ODPH_ERR(
"Destroy queues failed.\n");
1058 ODPH_ERR(
"Shared memory free (memcpy) failed.\n");
1063 ODPH_ERR(
"Shared memory free failed.\n");
1068 ODPH_ERR(
"Term local failed.\n");
1073 ODPH_ERR(
"Term global failed.\n");
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_inc_u32(odp_atomic_u32_t *atom)
Increment atomic uint32 variable.
void odp_barrier_init(odp_barrier_t *barr, int count)
Initialize barrier with thread count.
void odp_barrier_wait(odp_barrier_t *barr)
Synchronize thread execution on barrier.
odp_event_t odp_buffer_to_event(odp_buffer_t buf)
Convert buffer handle to event.
odp_buffer_t odp_buffer_alloc(odp_pool_t pool)
Buffer alloc.
#define odp_unlikely(x)
Branch unlikely taken.
uint64_t odp_cpu_cycles_diff(uint64_t c2, uint64_t c1)
CPU cycle count difference.
uint64_t odp_cpu_cycles_strict(void)
Current CPU cycle count (strict)
int odp_cpumask_default_worker(odp_cpumask_t *mask, int num)
Default CPU mask for worker threads.
void odp_event_free(odp_event_t event)
Free event.
#define ODP_EVENT_INVALID
Invalid event.
void odp_init_param_init(odp_init_t *param)
Initialize the odp_init_t to default values for all fields.
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.
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_BUFFER
Buffer pool.
odp_nonblocking_t
Non-blocking level.
int odp_queue_enq_multi(odp_queue_t queue, const odp_event_t events[], int num)
Enqueue multiple events to a queue.
void odp_queue_param_init(odp_queue_param_t *param)
Initialize queue params.
int odp_queue_capability(odp_queue_capability_t *capa)
Query queue capabilities.
#define ODP_QUEUE_INVALID
Invalid queue.
odp_event_t odp_queue_deq(odp_queue_t queue)
Dequeue an event from a queue.
int odp_queue_enq(odp_queue_t queue, odp_event_t ev)
Enqueue an event to a queue.
odp_queue_t odp_queue_create(const char *name, const odp_queue_param_t *param)
Queue create.
int odp_queue_destroy(odp_queue_t queue)
Destroy ODP queue.
int odp_queue_deq_multi(odp_queue_t queue, odp_event_t events[], int num)
Dequeue multiple events from a queue.
@ ODP_NONBLOCKING_WF
Non-blocking and wait-free implementation.
@ ODP_BLOCKING
Blocking implementation.
@ ODP_NONBLOCKING_LF
Non-blocking and lock-free implementation.
@ ODP_QUEUE_TYPE_PLAIN
Plain queue.
@ ODP_QUEUE_OP_MT_UNSAFE
Not multithread safe operation.
int odp_shm_free(odp_shm_t shm)
Free a contiguous block of shared memory.
void * odp_shm_addr(odp_shm_t shm)
Shared memory block address.
#define ODP_SHM_INVALID
Invalid shared memory block.
odp_shm_t odp_shm_reserve(const char *name, uint64_t size, uint64_t align, uint32_t flags)
Reserve a contiguous block of shared memory.
bool odp_bool_t
Boolean type.
void odp_sys_info_print(void)
Print system info.
#define ODP_THREAD_COUNT_MAX
Maximum number of threads supported in build time.
@ ODP_THREAD_WORKER
Worker thread.
void odp_time_wait_ns(uint64_t ns)
Wait the specified number of nanoseconds.
odp_time_t odp_time_local_strict(void)
Current local time (strict)
uint64_t odp_time_diff_ns(odp_time_t t2, odp_time_t t1)
Time difference in nanoseconds.
Global initialization parameters.
odp_mem_model_t mem_model
Application memory model.
odp_feature_t not_used
Unused features.
uint32_t max_num
Maximum number of buffers of any size.
struct odp_pool_capability_t::@133 buf
Buffer pool capabilities
uint32_t num
Number of buffers in the pool.
odp_pool_type_t type
Pool type.
struct odp_pool_param_t::@138 buf
Parameters for buffer pools.
struct odp_queue_capability_t::@155 plain
Plain queue capabilities.
uint32_t max_size
Maximum number of events a plain (ODP_BLOCKING) queue can store simultaneously.
uint32_t max_num
Maximum number of plain (ODP_BLOCKING) queues of the default size.
struct odp_queue_capability_t::@155::@156 lockfree
Lock-free (ODP_NONBLOCKING_LF) implementation capabilities.
struct odp_queue_capability_t::@155::@157 waitfree
Wait-free (ODP_NONBLOCKING_WF) implementation capabilities.
odp_queue_op_mode_t enq_mode
Enqueue mode.
odp_queue_type_t type
Queue type.
odp_queue_op_mode_t deq_mode
Dequeue mode.
odp_nonblocking_t nonblocking
Non-blocking level.
uint32_t tm
Traffic Manager APIs, e.g., odp_tm_xxx()
uint32_t crypto
Crypto APIs, e.g., odp_crypto_xxx()
uint32_t ipsec
IPsec APIs, e.g., odp_ipsec_xxx()
uint32_t timer
Timer APIs, e.g., odp_timer_xxx(), odp_timeout_xxx()
uint32_t cls
Classifier APIs, e.g., odp_cls_xxx(), odp_cos_xxx()
struct odp_feature_t::@174 feat
Individual feature bits.
uint32_t schedule
Scheduler APIs, e.g., odp_schedule_xxx()
uint32_t compress
Compression APIs, e.g., odp_comp_xxx()