X-Git-Url: https://gerrit.fd.io/r/gitweb?a=blobdiff_plain;f=src%2Fplugins%2Funittest%2Fsvm_fifo_test.c;h=4351bced92190429ff1fcf04cf3da0bbced9eae7;hb=4ec02990a73e0549cababa3a8e9f2d69e5cdffac;hp=a3f88d35b9cdf79e665d9c1cb822ccafd4003042;hpb=07b94558087facbb16c0fa82a79fcbbd9b44c485;p=vpp.git diff --git a/src/plugins/unittest/svm_fifo_test.c b/src/plugins/unittest/svm_fifo_test.c index a3f88d35b9c..4351bced921 100644 --- a/src/plugins/unittest/svm_fifo_test.c +++ b/src/plugins/unittest/svm_fifo_test.c @@ -256,7 +256,7 @@ sfifo_test_fifo1 (vlib_main_t * vm, unformat_input_t * input) */ rv = svm_fifo_enqueue (f, sizeof (u32), (u8 *) test_data); SFIFO_TEST ((rv == sizeof (u32)), "enqueued %d", rv); - SFIFO_TEST ((f->tail == 4), "fifo tail %u", f->tail); + SFIFO_TEST ((f->shr->tail == 4), "fifo tail %u", f->shr->tail); /* * Create 3 chunks in the future. The offsets are relative @@ -264,7 +264,7 @@ sfifo_test_fifo1 (vlib_main_t * vm, unformat_input_t * input) */ for (i = 0; i < 3; i++) { - offset = (2 * i + 1) * sizeof (u32) - f->tail; + offset = (2 * i + 1) * sizeof (u32) - f->shr->tail; data = (u8 *) (test_data + (2 * i + 1)); if (i == 0) { @@ -286,14 +286,14 @@ sfifo_test_fifo1 (vlib_main_t * vm, unformat_input_t * input) if (verbose) vlib_cli_output (vm, "fifo after odd segs: %U", format_svm_fifo, f, 1); - SFIFO_TEST ((f->tail == 8), "fifo tail %u", f->tail); + SFIFO_TEST ((f->shr->tail == 8), "fifo tail %u", f->shr->tail); SFIFO_TEST ((svm_fifo_n_ooo_segments (f) == 2), "number of ooo segments %u", svm_fifo_n_ooo_segments (f)); /* * Try adding a completely overlapped segment */ - offset = 3 * sizeof (u32) - f->tail; + offset = 3 * sizeof (u32) - f->shr->tail; data = (u8 *) (test_data + 3); rv = svm_fifo_enqueue_with_offset (f, offset, sizeof (u32), data); if (rv) @@ -319,7 +319,7 @@ sfifo_test_fifo1 (vlib_main_t * vm, unformat_input_t * input) */ for (i = 3; i > 1; i--) { - offset = (2 * i + 0) * sizeof (u32) - f->tail; + offset = (2 * i + 0) * sizeof (u32) - f->shr->tail; data = (u8 *) (test_data + (2 * i + 0)); rv = svm_fifo_enqueue_with_offset (f, offset, sizeof (u32), data); if (verbose) @@ -381,7 +381,7 @@ sfifo_test_fifo1 (vlib_main_t * vm, unformat_input_t * input) for (i = 0; i < 4; i++) { - offset = (2 * i + 1) * sizeof (u32) - f->tail; + offset = (2 * i + 1) * sizeof (u32) - f->shr->tail; data = (u8 *) (test_data + (2 * i + 1)); rv = svm_fifo_enqueue_with_offset (f, offset, sizeof (u32), data); if (verbose) @@ -394,7 +394,7 @@ sfifo_test_fifo1 (vlib_main_t * vm, unformat_input_t * input) } } - rv = svm_fifo_enqueue_with_offset (f, 8 - f->tail, 21, data); + rv = svm_fifo_enqueue_with_offset (f, 8 - f->shr->tail, 21, data); SFIFO_TEST ((rv == 0), "ooo enqueued %u", rv); SFIFO_TEST ((svm_fifo_n_ooo_segments (f) == 1), "number of ooo segments %u", svm_fifo_n_ooo_segments (f)); @@ -422,7 +422,7 @@ sfifo_test_fifo1 (vlib_main_t * vm, unformat_input_t * input) for (i = 0; i < 4; i++) { - offset = (2 * i + 1) * sizeof (u32) - f->tail; + offset = (2 * i + 1) * sizeof (u32) - f->shr->tail; data = (u8 *) (test_data + (2 * i + 1)); rv = svm_fifo_enqueue_with_offset (f, offset, sizeof (u32), data); if (verbose) @@ -500,8 +500,8 @@ sfifo_test_fifo2 (vlib_main_t * vm) { tp = vp + i; data64 = tp->offset; - svm_fifo_enqueue_with_offset (f, tp->offset - f->tail, tp->len, - (u8 *) & data64); + svm_fifo_enqueue_with_offset (f, tp->offset - f->shr->tail, tp->len, + (u8 *) &data64); } /* Expected result: one big fat chunk at offset 4 */ @@ -530,8 +530,8 @@ sfifo_test_fifo2 (vlib_main_t * vm) { tp = &test_data[i]; data64 = tp->offset; - rv = svm_fifo_enqueue_with_offset (f, tp->offset - f->tail, tp->len, - (u8 *) & data64); + rv = svm_fifo_enqueue_with_offset (f, tp->offset - f->shr->tail, tp->len, + (u8 *) &data64); if (rv) { clib_warning ("enqueue returned %d", rv); @@ -704,10 +704,9 @@ sfifo_test_fifo3 (vlib_main_t * vm, unformat_input_t * input) for (i = !randomize; i < vec_len (generate); i++) { tp = generate + i; - svm_fifo_enqueue_with_offset (f, - fifo_initial_offset + tp->offset - - f->tail, tp->len, - (u8 *) data_pattern + tp->offset); + svm_fifo_enqueue_with_offset ( + f, fifo_initial_offset + tp->offset - f->shr->tail, tp->len, + (u8 *) data_pattern + tp->offset); } /* Add the first segment in order for non random data */ @@ -823,8 +822,8 @@ sfifo_test_fifo4 (vlib_main_t * vm, unformat_input_t * input) for (i = test_n_bytes - 1; i > 0; i--) { - rv = svm_fifo_enqueue_with_offset (f, fifo_initial_offset + i - f->tail, - sizeof (u8), &test_data[i]); + rv = svm_fifo_enqueue_with_offset ( + f, fifo_initial_offset + i - f->shr->tail, sizeof (u8), &test_data[i]); if (verbose) vlib_cli_output (vm, "add [%d] [%d, %d]", i, i, i + sizeof (u8)); if (rv) @@ -1150,7 +1149,8 @@ sfifo_test_fifo7 (vlib_main_t * vm, unformat_input_t * input) if (compare_data (data_buf, test_data, 0, n_test_bytes, (u32 *) & j)) SFIFO_TEST (0, "[%d] dequeued %u expected %u", j, data_buf[j], test_data[j]); - svm_fifo_init_pointers (f, (~0 - i) % f->size, (~0 - i) % f->size); + svm_fifo_init_pointers (f, (~0 - i) % f->shr->size, + (~0 - i) % f->shr->size); } SFIFO_TEST (1, "passed multiple ooo enqueue/dequeue"); @@ -1412,13 +1412,13 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (rv == 2, "should have 2 chunks has %u", rv); SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); - c = f->head_chunk; + c = f_head_cptr (f); SFIFO_TEST (c->start_byte == 0, "head start byte should be %u", 0); SFIFO_TEST (c->length == 4096, "head chunk length should be %u", 4096); - SFIFO_TEST (f->tail_chunk == 0, "no tail chunk"); + SFIFO_TEST (f->shr->tail_chunk == 0, "no tail chunk"); SFIFO_TEST (f->ooo_enq == 0, "should have no ooo enq chunk"); SFIFO_TEST (f->ooo_deq == 0, "should have no ooo deq chunk"); - c = f->end_chunk; + c = f_end_cptr (f); SFIFO_TEST (c->start_byte == last_start_byte, "end chunk start byte should" " be %u", last_start_byte); SFIFO_TEST (c->length == 4096, "end chunk length should be %u", 4096); @@ -1438,8 +1438,8 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) vlib_cli_output (vm, "[%d] dequeued %u expected %u", i, data_buf[i], test_data[i]); SFIFO_TEST ((rv == 0), "dequeued compared to original returned %d", rv); - SFIFO_TEST (f->head_chunk == 0, "head chunk should be 0"); - SFIFO_TEST (f->tail_chunk == 0, "tail chunk should be 0"); + SFIFO_TEST (f->shr->head_chunk == 0, "head chunk should be 0"); + SFIFO_TEST (f->shr->tail_chunk == 0, "tail chunk should be 0"); SFIFO_TEST (f->ooo_deq == 0, "should have no ooo deq chunk"); SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); @@ -1461,12 +1461,12 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (rv == 2, "should have %u chunks has %u", 2, rv); SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); - SFIFO_TEST (f->head_chunk == 0, "should have no head chunk"); + SFIFO_TEST (f->shr->head_chunk == 0, "should have no head chunk"); /* When new fifo chunks are allocated, tail is initialized */ - SFIFO_TEST (f->tail_chunk != 0, "should have no tail chunk"); + SFIFO_TEST (f->shr->tail_chunk != 0, "should have no tail chunk"); SFIFO_TEST (f->ooo_enq != 0, "should have an ooo enq chunk"); - c = f->end_chunk; + c = f_end_cptr (f); SFIFO_TEST (c->start_byte == last_start_byte, "end chunk should start at %u", last_start_byte); SFIFO_TEST (c->length == 8192, "end chunk length should be %u", 8192); @@ -1483,9 +1483,9 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (rv == 2, "should have %u chunks has %u", 2, rv); SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); - SFIFO_TEST (f->head_chunk == 0, "should have no head chunk"); + SFIFO_TEST (f->shr->head_chunk == 0, "should have no head chunk"); /* Fifo is full so tail and ooo_enq should be 0 */ - SFIFO_TEST (f->tail_chunk == 0, "should have no tail chunk"); + SFIFO_TEST (f->shr->tail_chunk == 0, "should have no tail chunk"); SFIFO_TEST (f->ooo_enq == 0, "should have no ooo enq chunk"); /* @@ -1542,8 +1542,8 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) last_start_byte += 8192; SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); - SFIFO_TEST (f->head_chunk == 0, "should have no head chunk"); - SFIFO_TEST (f->tail_chunk == 0, "should have no tail chunk"); + SFIFO_TEST (f->shr->head_chunk == 0, "should have no head chunk"); + SFIFO_TEST (f->shr->tail_chunk == 0, "should have no tail chunk"); /* We don't remove the last chunk even when the fifo goes empty */ rv = svm_fifo_n_chunks (f); @@ -1575,12 +1575,12 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (rv == 2, "should have %u chunks has %u", 2, rv); SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); - SFIFO_TEST (f->head_chunk == 0, "should have no head chunk"); + SFIFO_TEST (f->shr->head_chunk == 0, "should have no head chunk"); /* When new fifo chunks are allocated, tail is initialized */ - SFIFO_TEST (f->tail_chunk != 0, "should have no tail chunk"); + SFIFO_TEST (f->shr->tail_chunk != 0, "should have no tail chunk"); SFIFO_TEST (f->ooo_enq != 0, "should have an ooo enq chunk"); - c = f->end_chunk; + c = f_end_cptr (f); SFIFO_TEST (c->start_byte == last_start_byte, "end chunk should start at %u", last_start_byte); SFIFO_TEST (c->length == 16384, "end chunk length should be %u", 16384); @@ -1623,7 +1623,7 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); last_start_byte += 16384; - c = f->end_chunk; + c = f_end_cptr (f); SFIFO_TEST (c->start_byte == last_start_byte, "end chunk should start at %u", last_start_byte); SFIFO_TEST (c->length == 4096, "end chunk length should be %u", 4096); @@ -1647,8 +1647,8 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); /* fifo does not end on chunk boundary because of the - 100 */ - SFIFO_TEST (f->head_chunk != 0, "should have head chunk"); - SFIFO_TEST (f->tail_chunk != 0, "should have tail chunk"); + SFIFO_TEST (f->shr->head_chunk != 0, "should have head chunk"); + SFIFO_TEST (f->shr->tail_chunk != 0, "should have tail chunk"); /* * Enqueue and dequeue byte-by-byte ooo @@ -1673,7 +1673,7 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); last_start_byte += 4096; - c = f->end_chunk; + c = f_end_cptr (f); SFIFO_TEST (c->start_byte == last_start_byte, "end chunk should start at %u", last_start_byte); SFIFO_TEST (c->length == 16384, "end chunk length should be %u", 16384); @@ -1688,8 +1688,8 @@ sfifo_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST ((rv == fifo_size), "all bytes should be dropped %u", rv); SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); - SFIFO_TEST (f->head_chunk != 0, "should have head chunk"); - SFIFO_TEST (f->tail_chunk != 0, "should have tail chunk"); + SFIFO_TEST (f->shr->head_chunk != 0, "should have head chunk"); + SFIFO_TEST (f->shr->tail_chunk != 0, "should have tail chunk"); /* We don't remove the last chunk even when the fifo goes empty */ rv = svm_fifo_n_chunks (f); @@ -1941,12 +1941,13 @@ sfifo_test_fifo_indirect (vlib_main_t * vm, unformat_input_t * input) svm_fifo_set_size (f, fifo_size); validate_test_and_buf_vecs (&test_data, &data_buf, fifo_size); - c = f->start_chunk; + c = f_start_cptr (f); SFIFO_TEST (c->next == 0, "no next"); svm_fifo_fill_chunk_list (f); SFIFO_TEST (c->next != 0, "new chunk should've been allocated"); - SFIFO_TEST (c->next->length == 4 << 20, "new chunk should be 4MB"); + SFIFO_TEST (f_cptr (f, c->next)->length == 4 << 20, + "new chunk should be 4MB"); rv = svm_fifo_max_write_chunk (f); SFIFO_TEST (rv == 4096, "max write chunk %u", rv); @@ -1958,7 +1959,7 @@ sfifo_test_fifo_indirect (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (svm_fifo_is_sane (f), "fifo should be sane"); c = svm_fifo_tail_chunk (f); - SFIFO_TEST (c == f->end_chunk, "tail is end chunk"); + SFIFO_TEST (c == f_end_cptr (f), "tail is end chunk"); /* Initialize head chunk */ rv = svm_fifo_max_read_chunk (f); @@ -1972,7 +1973,7 @@ sfifo_test_fifo_indirect (vlib_main_t * vm, unformat_input_t * input) SFIFO_TEST (rv == 4096, "dequeue should work"); c = svm_fifo_head_chunk (f); - SFIFO_TEST (c == f->end_chunk, "head chunk should be last"); + SFIFO_TEST (c == f_end_cptr (f), "head chunk should be last"); rv = svm_fifo_max_read_chunk (f); SFIFO_TEST (rv == 0, "max read chunk %u", rv); @@ -2103,6 +2104,7 @@ sfifo_test_fifo_segment_hello_world (int verbose) clib_memset (a, 0, sizeof (*a)); a->segment_name = "fifo-test1"; a->segment_size = 256 << 10; + a->segment_type = SSVM_SEGMENT_PRIVATE; rv = fifo_segment_create (sm, a); SFIFO_TEST (!rv, "svm_fifo_segment_create returned %d", rv); @@ -2153,6 +2155,9 @@ sfifo_test_fifo_segment_fifo_grow (int verbose) a->segment_name = "fifo-test1"; /* size chosen to be able to force multi chunk allocation lower */ a->segment_size = 256 << 10; + /* overhead that reduces the amount of space dedicated to fifos */ + a->segment_size += 1 << 14; + a->segment_type = SSVM_SEGMENT_PRIVATE; /* fifo allocation allocates chunks in batch */ n_batch = FIFO_SEGMENT_ALLOC_BATCH_SIZE; @@ -2405,13 +2410,13 @@ sfifo_test_fifo_segment_slave (int verbose) svm_fifo_dequeue (f, vec_len (retrieved_data), retrieved_data); if (memcmp (retrieved_data, test_data, vec_len (retrieved_data))) { - result = (u32 *) f->head_chunk->data; + result = (u32 *) f_head_cptr (f)->data; *result = 1; _exit (0); } } - result = (u32 *) f->head_chunk->data; + result = (u32 *) f_head_cptr (f)->data; *result = 0; vec_free (test_data); @@ -2465,7 +2470,7 @@ sfifo_test_fifo_segment_master_slave (int verbose) usleep (1e3); - result = (u32 *) f->head_chunk->data; + result = (u32 *) f_head_cptr (f)->data; SFIFO_TEST (*result == 0, "slave reported no error"); vec_free (a->new_segment_indices); @@ -2490,6 +2495,7 @@ sfifo_test_fifo_segment_mempig (int verbose) a->segment_name = "fifo-test1"; a->segment_size = 256 << 10; + a->segment_type = SSVM_SEGMENT_PRIVATE; rv = fifo_segment_create (sm, a); @@ -2535,21 +2541,32 @@ sfifo_test_fifo_segment_mempig (int verbose) return 0; } +static int +approx_leq (uword a, uword b, u32 margin) +{ + if (a - margin <= b && b <= a) + return 1; + return 0; +} + static int sfifo_test_fifo_segment_prealloc (int verbose) { + u32 max_pairs, pairs_req, free_space, pair_mem, overhead; fifo_segment_create_args_t _a, *a = &_a; fifo_segment_main_t *sm = &segment_main; - u32 max_pairs, pairs_req, free_space, pair_mem; svm_fifo_t *f, *tf, *old; fifo_segment_t *fs; int rv, alloc; clib_memset (a, 0, sizeof (*a)); + /* Overhead due to segment internal headers and offsets. The magic 384 + * bytes are the fsh->n_reserved_bytes after seg init */ + overhead = (8 << 10) + 384; a->segment_name = "fifo-test-prealloc"; - a->segment_size = 256 << 10; - a->segment_type = SSVM_SEGMENT_MEMFD; + a->segment_size = (256 << 10) + overhead; + a->segment_type = SSVM_SEGMENT_PRIVATE; rv = fifo_segment_create (sm, a); SFIFO_TEST (!rv, "svm_fifo_segment_create returned %d", rv); @@ -2560,7 +2577,7 @@ sfifo_test_fifo_segment_prealloc (int verbose) * Prealloc chunks and headers */ free_space = fifo_segment_free_bytes (fs); - SFIFO_TEST (free_space <= 256 << 10, "free space expected %u is %u", + SFIFO_TEST (free_space - 4096 <= 256 << 10, "free space expected %u is %u", 256 << 10, free_space); rv = fifo_segment_prealloc_fifo_chunks (fs, 0, 4096, 50); SFIFO_TEST (rv == 0, "chunk prealloc should work"); @@ -2568,8 +2585,10 @@ sfifo_test_fifo_segment_prealloc (int verbose) SFIFO_TEST (rv == 50, "prealloc chunks expected %u is %u", 50, rv); rv = fifo_segment_free_bytes (fs); free_space -= (sizeof (svm_fifo_chunk_t) + 4096) * 50; - SFIFO_TEST (rv == free_space, "free space expected %u is %u", free_space, - rv); + /* Memory alloc alignment accounts for the difference */ + SFIFO_TEST (approx_leq (free_space, rv, 16), "free space expected %u is %u", + free_space, rv); + free_space = rv; rv = fifo_segment_fl_chunk_bytes (fs); SFIFO_TEST (rv == 4096 * 50, "chunk free space expected %u is %u", 4096 * 50, rv); @@ -2579,11 +2598,12 @@ sfifo_test_fifo_segment_prealloc (int verbose) rv = fifo_segment_num_free_fifos (fs); SFIFO_TEST (rv == 50, "prealloc fifo hdrs expected %u is %u", 50, rv); rv = fifo_segment_free_bytes (fs); - free_space -= sizeof (svm_fifo_t) * 50; - SFIFO_TEST (rv == free_space, "free space expected %u is %u", free_space, - rv); + free_space -= sizeof (svm_fifo_shared_t) * 50; + /* Memory alloc alignment accounts for the difference */ + SFIFO_TEST (approx_leq (free_space, rv, 128), "free space expected %u is %u", + free_space, rv); + free_space = rv; - fifo_segment_update_free_bytes (fs); rv = fifo_segment_free_bytes (fs); SFIFO_TEST (clib_abs (rv - (int) free_space) < 512, "free space expected %u is %u", free_space, rv); @@ -2606,7 +2626,6 @@ sfifo_test_fifo_segment_prealloc (int verbose) /* * Multiple preallocs that consume the remaining space */ - fifo_segment_update_free_bytes (fs); free_space = fifo_segment_free_bytes (fs); pair_mem = 2 * (4096 + sizeof (*f) + sizeof (svm_fifo_chunk_t)); max_pairs = pairs_req = (free_space / pair_mem) - 1; @@ -2616,7 +2635,6 @@ sfifo_test_fifo_segment_prealloc (int verbose) SFIFO_TEST (rv == max_pairs * 2, "prealloc chunks expected %u is %u", max_pairs * 2, rv); - fifo_segment_update_free_bytes (fs); rv = fifo_segment_free_bytes (fs); SFIFO_TEST (rv < 2 * pair_mem, "free bytes %u less than %u", rv, 2 * pair_mem); @@ -2657,7 +2675,6 @@ sfifo_test_fifo_segment_prealloc (int verbose) */ fifo_segment_free_fifo (fs, old); fifo_segment_free_fifo (fs, tf); - close (fs->ssvm.fd); fifo_segment_delete (sm, fs); return 0; }