1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2010-2014 Intel Corporation 3 */ 4 5 #include <string.h> 6 #include <stdarg.h> 7 #include <stdio.h> 8 #include <stdlib.h> 9 #include <stdint.h> 10 #include <inttypes.h> 11 #include <errno.h> 12 #include <sys/queue.h> 13 14 #include <rte_common.h> 15 #include <rte_log.h> 16 #include <rte_memory.h> 17 #include <rte_launch.h> 18 #include <rte_cycles.h> 19 #include <rte_eal.h> 20 #include <rte_per_lcore.h> 21 #include <rte_lcore.h> 22 #include <rte_atomic.h> 23 #include <rte_branch_prediction.h> 24 #include <rte_malloc.h> 25 #include <rte_ring.h> 26 #include <rte_random.h> 27 #include <rte_errno.h> 28 #include <rte_hexdump.h> 29 30 #include "test.h" 31 32 /* 33 * Ring 34 * ==== 35 * 36 * #. Basic tests: done on one core: 37 * 38 * - Using single producer/single consumer functions: 39 * 40 * - Enqueue one object, two objects, MAX_BULK objects 41 * - Dequeue one object, two objects, MAX_BULK objects 42 * - Check that dequeued pointers are correct 43 * 44 * - Using multi producers/multi consumers functions: 45 * 46 * - Enqueue one object, two objects, MAX_BULK objects 47 * - Dequeue one object, two objects, MAX_BULK objects 48 * - Check that dequeued pointers are correct 49 * 50 * #. Performance tests. 51 * 52 * Tests done in test_ring_perf.c 53 */ 54 55 #define RING_SIZE 4096 56 #define MAX_BULK 32 57 58 static rte_atomic32_t synchro; 59 60 #define TEST_RING_VERIFY(exp) \ 61 if (!(exp)) { \ 62 printf("error at %s:%d\tcondition " #exp " failed\n", \ 63 __func__, __LINE__); \ 64 rte_ring_dump(stdout, r); \ 65 return -1; \ 66 } 67 68 #define TEST_RING_FULL_EMTPY_ITER 8 69 70 /* 71 * helper routine for test_ring_basic 72 */ 73 static int 74 test_ring_basic_full_empty(struct rte_ring *r, void * const src[], void *dst[]) 75 { 76 unsigned i, rand; 77 const unsigned rsz = RING_SIZE - 1; 78 79 printf("Basic full/empty test\n"); 80 81 for (i = 0; TEST_RING_FULL_EMTPY_ITER != i; i++) { 82 83 /* random shift in the ring */ 84 rand = RTE_MAX(rte_rand() % RING_SIZE, 1UL); 85 printf("%s: iteration %u, random shift: %u;\n", 86 __func__, i, rand); 87 TEST_RING_VERIFY(rte_ring_enqueue_bulk(r, src, rand, 88 NULL) != 0); 89 TEST_RING_VERIFY(rte_ring_dequeue_bulk(r, dst, rand, 90 NULL) == rand); 91 92 /* fill the ring */ 93 TEST_RING_VERIFY(rte_ring_enqueue_bulk(r, src, rsz, NULL) != 0); 94 TEST_RING_VERIFY(0 == rte_ring_free_count(r)); 95 TEST_RING_VERIFY(rsz == rte_ring_count(r)); 96 TEST_RING_VERIFY(rte_ring_full(r)); 97 TEST_RING_VERIFY(0 == rte_ring_empty(r)); 98 99 /* empty the ring */ 100 TEST_RING_VERIFY(rte_ring_dequeue_bulk(r, dst, rsz, 101 NULL) == rsz); 102 TEST_RING_VERIFY(rsz == rte_ring_free_count(r)); 103 TEST_RING_VERIFY(0 == rte_ring_count(r)); 104 TEST_RING_VERIFY(0 == rte_ring_full(r)); 105 TEST_RING_VERIFY(rte_ring_empty(r)); 106 107 /* check data */ 108 TEST_RING_VERIFY(0 == memcmp(src, dst, rsz)); 109 rte_ring_dump(stdout, r); 110 } 111 return 0; 112 } 113 114 static int 115 test_ring_basic(struct rte_ring *r) 116 { 117 void **src = NULL, **cur_src = NULL, **dst = NULL, **cur_dst = NULL; 118 int ret; 119 unsigned i, num_elems; 120 121 /* alloc dummy object pointers */ 122 src = malloc(RING_SIZE*2*sizeof(void *)); 123 if (src == NULL) 124 goto fail; 125 126 for (i = 0; i < RING_SIZE*2 ; i++) { 127 src[i] = (void *)(unsigned long)i; 128 } 129 cur_src = src; 130 131 /* alloc some room for copied objects */ 132 dst = malloc(RING_SIZE*2*sizeof(void *)); 133 if (dst == NULL) 134 goto fail; 135 136 memset(dst, 0, RING_SIZE*2*sizeof(void *)); 137 cur_dst = dst; 138 139 printf("enqueue 1 obj\n"); 140 ret = rte_ring_sp_enqueue_bulk(r, cur_src, 1, NULL); 141 cur_src += 1; 142 if (ret == 0) 143 goto fail; 144 145 printf("enqueue 2 objs\n"); 146 ret = rte_ring_sp_enqueue_bulk(r, cur_src, 2, NULL); 147 cur_src += 2; 148 if (ret == 0) 149 goto fail; 150 151 printf("enqueue MAX_BULK objs\n"); 152 ret = rte_ring_sp_enqueue_bulk(r, cur_src, MAX_BULK, NULL); 153 cur_src += MAX_BULK; 154 if (ret == 0) 155 goto fail; 156 157 printf("dequeue 1 obj\n"); 158 ret = rte_ring_sc_dequeue_bulk(r, cur_dst, 1, NULL); 159 cur_dst += 1; 160 if (ret == 0) 161 goto fail; 162 163 printf("dequeue 2 objs\n"); 164 ret = rte_ring_sc_dequeue_bulk(r, cur_dst, 2, NULL); 165 cur_dst += 2; 166 if (ret == 0) 167 goto fail; 168 169 printf("dequeue MAX_BULK objs\n"); 170 ret = rte_ring_sc_dequeue_bulk(r, cur_dst, MAX_BULK, NULL); 171 cur_dst += MAX_BULK; 172 if (ret == 0) 173 goto fail; 174 175 /* check data */ 176 if (memcmp(src, dst, cur_dst - dst)) { 177 rte_hexdump(stdout, "src", src, cur_src - src); 178 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 179 printf("data after dequeue is not the same\n"); 180 goto fail; 181 } 182 cur_src = src; 183 cur_dst = dst; 184 185 printf("enqueue 1 obj\n"); 186 ret = rte_ring_mp_enqueue_bulk(r, cur_src, 1, NULL); 187 cur_src += 1; 188 if (ret == 0) 189 goto fail; 190 191 printf("enqueue 2 objs\n"); 192 ret = rte_ring_mp_enqueue_bulk(r, cur_src, 2, NULL); 193 cur_src += 2; 194 if (ret == 0) 195 goto fail; 196 197 printf("enqueue MAX_BULK objs\n"); 198 ret = rte_ring_mp_enqueue_bulk(r, cur_src, MAX_BULK, NULL); 199 cur_src += MAX_BULK; 200 if (ret == 0) 201 goto fail; 202 203 printf("dequeue 1 obj\n"); 204 ret = rte_ring_mc_dequeue_bulk(r, cur_dst, 1, NULL); 205 cur_dst += 1; 206 if (ret == 0) 207 goto fail; 208 209 printf("dequeue 2 objs\n"); 210 ret = rte_ring_mc_dequeue_bulk(r, cur_dst, 2, NULL); 211 cur_dst += 2; 212 if (ret == 0) 213 goto fail; 214 215 printf("dequeue MAX_BULK objs\n"); 216 ret = rte_ring_mc_dequeue_bulk(r, cur_dst, MAX_BULK, NULL); 217 cur_dst += MAX_BULK; 218 if (ret == 0) 219 goto fail; 220 221 /* check data */ 222 if (memcmp(src, dst, cur_dst - dst)) { 223 rte_hexdump(stdout, "src", src, cur_src - src); 224 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 225 printf("data after dequeue is not the same\n"); 226 goto fail; 227 } 228 cur_src = src; 229 cur_dst = dst; 230 231 printf("fill and empty the ring\n"); 232 for (i = 0; i<RING_SIZE/MAX_BULK; i++) { 233 ret = rte_ring_mp_enqueue_bulk(r, cur_src, MAX_BULK, NULL); 234 cur_src += MAX_BULK; 235 if (ret == 0) 236 goto fail; 237 ret = rte_ring_mc_dequeue_bulk(r, cur_dst, MAX_BULK, NULL); 238 cur_dst += MAX_BULK; 239 if (ret == 0) 240 goto fail; 241 } 242 243 /* check data */ 244 if (memcmp(src, dst, cur_dst - dst)) { 245 rte_hexdump(stdout, "src", src, cur_src - src); 246 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 247 printf("data after dequeue is not the same\n"); 248 goto fail; 249 } 250 251 if (test_ring_basic_full_empty(r, src, dst) != 0) 252 goto fail; 253 254 cur_src = src; 255 cur_dst = dst; 256 257 printf("test default bulk enqueue / dequeue\n"); 258 num_elems = 16; 259 260 cur_src = src; 261 cur_dst = dst; 262 263 ret = rte_ring_enqueue_bulk(r, cur_src, num_elems, NULL); 264 cur_src += num_elems; 265 if (ret == 0) { 266 printf("Cannot enqueue\n"); 267 goto fail; 268 } 269 ret = rte_ring_enqueue_bulk(r, cur_src, num_elems, NULL); 270 cur_src += num_elems; 271 if (ret == 0) { 272 printf("Cannot enqueue\n"); 273 goto fail; 274 } 275 ret = rte_ring_dequeue_bulk(r, cur_dst, num_elems, NULL); 276 cur_dst += num_elems; 277 if (ret == 0) { 278 printf("Cannot dequeue\n"); 279 goto fail; 280 } 281 ret = rte_ring_dequeue_bulk(r, cur_dst, num_elems, NULL); 282 cur_dst += num_elems; 283 if (ret == 0) { 284 printf("Cannot dequeue2\n"); 285 goto fail; 286 } 287 288 /* check data */ 289 if (memcmp(src, dst, cur_dst - dst)) { 290 rte_hexdump(stdout, "src", src, cur_src - src); 291 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 292 printf("data after dequeue is not the same\n"); 293 goto fail; 294 } 295 296 cur_src = src; 297 cur_dst = dst; 298 299 ret = rte_ring_mp_enqueue(r, cur_src); 300 if (ret != 0) 301 goto fail; 302 303 ret = rte_ring_mc_dequeue(r, cur_dst); 304 if (ret != 0) 305 goto fail; 306 307 free(src); 308 free(dst); 309 return 0; 310 311 fail: 312 free(src); 313 free(dst); 314 return -1; 315 } 316 317 static int 318 test_ring_burst_basic(struct rte_ring *r) 319 { 320 void **src = NULL, **cur_src = NULL, **dst = NULL, **cur_dst = NULL; 321 int ret; 322 unsigned i; 323 324 /* alloc dummy object pointers */ 325 src = malloc(RING_SIZE*2*sizeof(void *)); 326 if (src == NULL) 327 goto fail; 328 329 for (i = 0; i < RING_SIZE*2 ; i++) { 330 src[i] = (void *)(unsigned long)i; 331 } 332 cur_src = src; 333 334 /* alloc some room for copied objects */ 335 dst = malloc(RING_SIZE*2*sizeof(void *)); 336 if (dst == NULL) 337 goto fail; 338 339 memset(dst, 0, RING_SIZE*2*sizeof(void *)); 340 cur_dst = dst; 341 342 printf("Test SP & SC basic functions \n"); 343 printf("enqueue 1 obj\n"); 344 ret = rte_ring_sp_enqueue_burst(r, cur_src, 1, NULL); 345 cur_src += 1; 346 if (ret != 1) 347 goto fail; 348 349 printf("enqueue 2 objs\n"); 350 ret = rte_ring_sp_enqueue_burst(r, cur_src, 2, NULL); 351 cur_src += 2; 352 if (ret != 2) 353 goto fail; 354 355 printf("enqueue MAX_BULK objs\n"); 356 ret = rte_ring_sp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 357 cur_src += MAX_BULK; 358 if (ret != MAX_BULK) 359 goto fail; 360 361 printf("dequeue 1 obj\n"); 362 ret = rte_ring_sc_dequeue_burst(r, cur_dst, 1, NULL); 363 cur_dst += 1; 364 if (ret != 1) 365 goto fail; 366 367 printf("dequeue 2 objs\n"); 368 ret = rte_ring_sc_dequeue_burst(r, cur_dst, 2, NULL); 369 cur_dst += 2; 370 if (ret != 2) 371 goto fail; 372 373 printf("dequeue MAX_BULK objs\n"); 374 ret = rte_ring_sc_dequeue_burst(r, cur_dst, MAX_BULK, NULL); 375 cur_dst += MAX_BULK; 376 if (ret != MAX_BULK) 377 goto fail; 378 379 /* check data */ 380 if (memcmp(src, dst, cur_dst - dst)) { 381 rte_hexdump(stdout, "src", src, cur_src - src); 382 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 383 printf("data after dequeue is not the same\n"); 384 goto fail; 385 } 386 387 cur_src = src; 388 cur_dst = dst; 389 390 printf("Test enqueue without enough memory space \n"); 391 for (i = 0; i< (RING_SIZE/MAX_BULK - 1); i++) { 392 ret = rte_ring_sp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 393 cur_src += MAX_BULK; 394 if (ret != MAX_BULK) 395 goto fail; 396 } 397 398 printf("Enqueue 2 objects, free entries = MAX_BULK - 2 \n"); 399 ret = rte_ring_sp_enqueue_burst(r, cur_src, 2, NULL); 400 cur_src += 2; 401 if (ret != 2) 402 goto fail; 403 404 printf("Enqueue the remaining entries = MAX_BULK - 2 \n"); 405 /* Always one free entry left */ 406 ret = rte_ring_sp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 407 cur_src += MAX_BULK - 3; 408 if (ret != MAX_BULK - 3) 409 goto fail; 410 411 printf("Test if ring is full \n"); 412 if (rte_ring_full(r) != 1) 413 goto fail; 414 415 printf("Test enqueue for a full entry \n"); 416 ret = rte_ring_sp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 417 if (ret != 0) 418 goto fail; 419 420 printf("Test dequeue without enough objects \n"); 421 for (i = 0; i<RING_SIZE/MAX_BULK - 1; i++) { 422 ret = rte_ring_sc_dequeue_burst(r, cur_dst, MAX_BULK, NULL); 423 cur_dst += MAX_BULK; 424 if (ret != MAX_BULK) 425 goto fail; 426 } 427 428 /* Available memory space for the exact MAX_BULK entries */ 429 ret = rte_ring_sc_dequeue_burst(r, cur_dst, 2, NULL); 430 cur_dst += 2; 431 if (ret != 2) 432 goto fail; 433 434 ret = rte_ring_sc_dequeue_burst(r, cur_dst, MAX_BULK, NULL); 435 cur_dst += MAX_BULK - 3; 436 if (ret != MAX_BULK - 3) 437 goto fail; 438 439 printf("Test if ring is empty \n"); 440 /* Check if ring is empty */ 441 if (1 != rte_ring_empty(r)) 442 goto fail; 443 444 /* check data */ 445 if (memcmp(src, dst, cur_dst - dst)) { 446 rte_hexdump(stdout, "src", src, cur_src - src); 447 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 448 printf("data after dequeue is not the same\n"); 449 goto fail; 450 } 451 452 cur_src = src; 453 cur_dst = dst; 454 455 printf("Test MP & MC basic functions \n"); 456 457 printf("enqueue 1 obj\n"); 458 ret = rte_ring_mp_enqueue_burst(r, cur_src, 1, NULL); 459 cur_src += 1; 460 if (ret != 1) 461 goto fail; 462 463 printf("enqueue 2 objs\n"); 464 ret = rte_ring_mp_enqueue_burst(r, cur_src, 2, NULL); 465 cur_src += 2; 466 if (ret != 2) 467 goto fail; 468 469 printf("enqueue MAX_BULK objs\n"); 470 ret = rte_ring_mp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 471 cur_src += MAX_BULK; 472 if (ret != MAX_BULK) 473 goto fail; 474 475 printf("dequeue 1 obj\n"); 476 ret = rte_ring_mc_dequeue_burst(r, cur_dst, 1, NULL); 477 cur_dst += 1; 478 if (ret != 1) 479 goto fail; 480 481 printf("dequeue 2 objs\n"); 482 ret = rte_ring_mc_dequeue_burst(r, cur_dst, 2, NULL); 483 cur_dst += 2; 484 if (ret != 2) 485 goto fail; 486 487 printf("dequeue MAX_BULK objs\n"); 488 ret = rte_ring_mc_dequeue_burst(r, cur_dst, MAX_BULK, NULL); 489 cur_dst += MAX_BULK; 490 if (ret != MAX_BULK) 491 goto fail; 492 493 /* check data */ 494 if (memcmp(src, dst, cur_dst - dst)) { 495 rte_hexdump(stdout, "src", src, cur_src - src); 496 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 497 printf("data after dequeue is not the same\n"); 498 goto fail; 499 } 500 501 cur_src = src; 502 cur_dst = dst; 503 504 printf("fill and empty the ring\n"); 505 for (i = 0; i<RING_SIZE/MAX_BULK; i++) { 506 ret = rte_ring_mp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 507 cur_src += MAX_BULK; 508 if (ret != MAX_BULK) 509 goto fail; 510 ret = rte_ring_mc_dequeue_burst(r, cur_dst, MAX_BULK, NULL); 511 cur_dst += MAX_BULK; 512 if (ret != MAX_BULK) 513 goto fail; 514 } 515 516 /* check data */ 517 if (memcmp(src, dst, cur_dst - dst)) { 518 rte_hexdump(stdout, "src", src, cur_src - src); 519 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 520 printf("data after dequeue is not the same\n"); 521 goto fail; 522 } 523 524 cur_src = src; 525 cur_dst = dst; 526 527 printf("Test enqueue without enough memory space \n"); 528 for (i = 0; i<RING_SIZE/MAX_BULK - 1; i++) { 529 ret = rte_ring_mp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 530 cur_src += MAX_BULK; 531 if (ret != MAX_BULK) 532 goto fail; 533 } 534 535 /* Available memory space for the exact MAX_BULK objects */ 536 ret = rte_ring_mp_enqueue_burst(r, cur_src, 2, NULL); 537 cur_src += 2; 538 if (ret != 2) 539 goto fail; 540 541 ret = rte_ring_mp_enqueue_burst(r, cur_src, MAX_BULK, NULL); 542 cur_src += MAX_BULK - 3; 543 if (ret != MAX_BULK - 3) 544 goto fail; 545 546 547 printf("Test dequeue without enough objects \n"); 548 for (i = 0; i<RING_SIZE/MAX_BULK - 1; i++) { 549 ret = rte_ring_mc_dequeue_burst(r, cur_dst, MAX_BULK, NULL); 550 cur_dst += MAX_BULK; 551 if (ret != MAX_BULK) 552 goto fail; 553 } 554 555 /* Available objects - the exact MAX_BULK */ 556 ret = rte_ring_mc_dequeue_burst(r, cur_dst, 2, NULL); 557 cur_dst += 2; 558 if (ret != 2) 559 goto fail; 560 561 ret = rte_ring_mc_dequeue_burst(r, cur_dst, MAX_BULK, NULL); 562 cur_dst += MAX_BULK - 3; 563 if (ret != MAX_BULK - 3) 564 goto fail; 565 566 /* check data */ 567 if (memcmp(src, dst, cur_dst - dst)) { 568 rte_hexdump(stdout, "src", src, cur_src - src); 569 rte_hexdump(stdout, "dst", dst, cur_dst - dst); 570 printf("data after dequeue is not the same\n"); 571 goto fail; 572 } 573 574 cur_src = src; 575 cur_dst = dst; 576 577 printf("Covering rte_ring_enqueue_burst functions \n"); 578 579 ret = rte_ring_enqueue_burst(r, cur_src, 2, NULL); 580 cur_src += 2; 581 if (ret != 2) 582 goto fail; 583 584 ret = rte_ring_dequeue_burst(r, cur_dst, 2, NULL); 585 cur_dst += 2; 586 if (ret != 2) 587 goto fail; 588 589 /* Free memory before test completed */ 590 free(src); 591 free(dst); 592 return 0; 593 594 fail: 595 free(src); 596 free(dst); 597 return -1; 598 } 599 600 /* 601 * it will always fail to create ring with a wrong ring size number in this function 602 */ 603 static int 604 test_ring_creation_with_wrong_size(void) 605 { 606 struct rte_ring * rp = NULL; 607 608 /* Test if ring size is not power of 2 */ 609 rp = rte_ring_create("test_bad_ring_size", RING_SIZE + 1, SOCKET_ID_ANY, 0); 610 if (NULL != rp) { 611 return -1; 612 } 613 614 /* Test if ring size is exceeding the limit */ 615 rp = rte_ring_create("test_bad_ring_size", (RTE_RING_SZ_MASK + 1), SOCKET_ID_ANY, 0); 616 if (NULL != rp) { 617 return -1; 618 } 619 return 0; 620 } 621 622 /* 623 * it tests if it would always fail to create ring with an used ring name 624 */ 625 static int 626 test_ring_creation_with_an_used_name(void) 627 { 628 struct rte_ring * rp; 629 630 rp = rte_ring_create("test", RING_SIZE, SOCKET_ID_ANY, 0); 631 if (NULL != rp) 632 return -1; 633 634 return 0; 635 } 636 637 /* 638 * Test to if a non-power of 2 count causes the create 639 * function to fail correctly 640 */ 641 static int 642 test_create_count_odd(void) 643 { 644 struct rte_ring *r = rte_ring_create("test_ring_count", 645 4097, SOCKET_ID_ANY, 0 ); 646 if(r != NULL){ 647 return -1; 648 } 649 return 0; 650 } 651 652 static int 653 test_lookup_null(void) 654 { 655 struct rte_ring *rlp = rte_ring_lookup("ring_not_found"); 656 if (rlp ==NULL) 657 if (rte_errno != ENOENT){ 658 printf( "test failed to returnn error on null pointer\n"); 659 return -1; 660 } 661 return 0; 662 } 663 664 /* 665 * it tests some more basic ring operations 666 */ 667 static int 668 test_ring_basic_ex(void) 669 { 670 int ret = -1; 671 unsigned i; 672 struct rte_ring *rp = NULL; 673 void **obj = NULL; 674 675 obj = rte_calloc("test_ring_basic_ex_malloc", RING_SIZE, sizeof(void *), 0); 676 if (obj == NULL) { 677 printf("test_ring_basic_ex fail to rte_malloc\n"); 678 goto fail_test; 679 } 680 681 rp = rte_ring_create("test_ring_basic_ex", RING_SIZE, SOCKET_ID_ANY, 682 RING_F_SP_ENQ | RING_F_SC_DEQ); 683 if (rp == NULL) { 684 printf("test_ring_basic_ex fail to create ring\n"); 685 goto fail_test; 686 } 687 688 if (rte_ring_lookup("test_ring_basic_ex") != rp) { 689 goto fail_test; 690 } 691 692 if (rte_ring_empty(rp) != 1) { 693 printf("test_ring_basic_ex ring is not empty but it should be\n"); 694 goto fail_test; 695 } 696 697 printf("%u ring entries are now free\n", rte_ring_free_count(rp)); 698 699 for (i = 0; i < RING_SIZE; i ++) { 700 rte_ring_enqueue(rp, obj[i]); 701 } 702 703 if (rte_ring_full(rp) != 1) { 704 printf("test_ring_basic_ex ring is not full but it should be\n"); 705 goto fail_test; 706 } 707 708 for (i = 0; i < RING_SIZE; i ++) { 709 rte_ring_dequeue(rp, &obj[i]); 710 } 711 712 if (rte_ring_empty(rp) != 1) { 713 printf("test_ring_basic_ex ring is not empty but it should be\n"); 714 goto fail_test; 715 } 716 717 /* Covering the ring burst operation */ 718 ret = rte_ring_enqueue_burst(rp, obj, 2, NULL); 719 if (ret != 2) { 720 printf("test_ring_basic_ex: rte_ring_enqueue_burst fails \n"); 721 goto fail_test; 722 } 723 724 ret = rte_ring_dequeue_burst(rp, obj, 2, NULL); 725 if (ret != 2) { 726 printf("test_ring_basic_ex: rte_ring_dequeue_burst fails \n"); 727 goto fail_test; 728 } 729 730 ret = 0; 731 fail_test: 732 rte_ring_free(rp); 733 if (obj != NULL) 734 rte_free(obj); 735 736 return ret; 737 } 738 739 static int 740 test_ring_with_exact_size(void) 741 { 742 struct rte_ring *std_ring = NULL, *exact_sz_ring = NULL; 743 void *ptr_array[16]; 744 static const unsigned int ring_sz = RTE_DIM(ptr_array); 745 unsigned int i; 746 int ret = -1; 747 748 std_ring = rte_ring_create("std", ring_sz, rte_socket_id(), 749 RING_F_SP_ENQ | RING_F_SC_DEQ); 750 if (std_ring == NULL) { 751 printf("%s: error, can't create std ring\n", __func__); 752 goto end; 753 } 754 exact_sz_ring = rte_ring_create("exact sz", ring_sz, rte_socket_id(), 755 RING_F_SP_ENQ | RING_F_SC_DEQ | RING_F_EXACT_SZ); 756 if (exact_sz_ring == NULL) { 757 printf("%s: error, can't create exact size ring\n", __func__); 758 goto end; 759 } 760 761 /* 762 * Check that the exact size ring is bigger than the standard ring 763 */ 764 if (rte_ring_get_size(std_ring) >= rte_ring_get_size(exact_sz_ring)) { 765 printf("%s: error, std ring (size: %u) is not smaller than exact size one (size %u)\n", 766 __func__, 767 rte_ring_get_size(std_ring), 768 rte_ring_get_size(exact_sz_ring)); 769 goto end; 770 } 771 /* 772 * check that the exact_sz_ring can hold one more element than the 773 * standard ring. (16 vs 15 elements) 774 */ 775 for (i = 0; i < ring_sz - 1; i++) { 776 rte_ring_enqueue(std_ring, NULL); 777 rte_ring_enqueue(exact_sz_ring, NULL); 778 } 779 if (rte_ring_enqueue(std_ring, NULL) != -ENOBUFS) { 780 printf("%s: error, unexpected successful enqueue\n", __func__); 781 goto end; 782 } 783 if (rte_ring_enqueue(exact_sz_ring, NULL) == -ENOBUFS) { 784 printf("%s: error, enqueue failed\n", __func__); 785 goto end; 786 } 787 788 /* check that dequeue returns the expected number of elements */ 789 if (rte_ring_dequeue_burst(exact_sz_ring, ptr_array, 790 RTE_DIM(ptr_array), NULL) != ring_sz) { 791 printf("%s: error, failed to dequeue expected nb of elements\n", 792 __func__); 793 goto end; 794 } 795 796 /* check that the capacity function returns expected value */ 797 if (rte_ring_get_capacity(exact_sz_ring) != ring_sz) { 798 printf("%s: error, incorrect ring capacity reported\n", 799 __func__); 800 goto end; 801 } 802 803 ret = 0; /* all ok if we get here */ 804 end: 805 rte_ring_free(std_ring); 806 rte_ring_free(exact_sz_ring); 807 return ret; 808 } 809 810 static int 811 test_ring(void) 812 { 813 struct rte_ring *r = NULL; 814 815 /* some more basic operations */ 816 if (test_ring_basic_ex() < 0) 817 goto test_fail; 818 819 rte_atomic32_init(&synchro); 820 821 r = rte_ring_create("test", RING_SIZE, SOCKET_ID_ANY, 0); 822 if (r == NULL) 823 goto test_fail; 824 825 /* retrieve the ring from its name */ 826 if (rte_ring_lookup("test") != r) { 827 printf("Cannot lookup ring from its name\n"); 828 goto test_fail; 829 } 830 831 /* burst operations */ 832 if (test_ring_burst_basic(r) < 0) 833 goto test_fail; 834 835 /* basic operations */ 836 if (test_ring_basic(r) < 0) 837 goto test_fail; 838 839 /* basic operations */ 840 if ( test_create_count_odd() < 0){ 841 printf("Test failed to detect odd count\n"); 842 goto test_fail; 843 } else 844 printf("Test detected odd count\n"); 845 846 if ( test_lookup_null() < 0){ 847 printf("Test failed to detect NULL ring lookup\n"); 848 goto test_fail; 849 } else 850 printf("Test detected NULL ring lookup\n"); 851 852 /* test of creating ring with wrong size */ 853 if (test_ring_creation_with_wrong_size() < 0) 854 goto test_fail; 855 856 /* test of creation ring with an used name */ 857 if (test_ring_creation_with_an_used_name() < 0) 858 goto test_fail; 859 860 if (test_ring_with_exact_size() < 0) 861 goto test_fail; 862 863 /* dump the ring status */ 864 rte_ring_list_dump(stdout); 865 866 rte_ring_free(r); 867 868 return 0; 869 870 test_fail: 871 rte_ring_free(r); 872 873 return -1; 874 } 875 876 REGISTER_TEST_COMMAND(ring_autotest, test_ring); 877