aboutsummaryrefslogtreecommitdiffstats
path: root/src/plugins
diff options
context:
space:
mode:
authorFlorin Coras <fcoras@cisco.com>2019-04-19 15:56:00 -0700
committerDamjan Marion <dmarion@me.com>2019-04-24 11:31:55 +0000
commit4375fa312e91ffeef0d34ab0594bda4a8c9189ea (patch)
treeabd9fce225e8bd351f53d36d446fe61ec107dbc2 /src/plugins
parentd35d4232953aa32a27a5a1024377191360441416 (diff)
svm: fifo ooo reads/writes with multiple chunks
Change-Id: If23a04623a7138c9f6c98ee9ecfa587396618a60 Signed-off-by: Florin Coras <fcoras@cisco.com>
Diffstat (limited to 'src/plugins')
-rw-r--r--src/plugins/unittest/svm_fifo_test.c177
1 files changed, 161 insertions, 16 deletions
diff --git a/src/plugins/unittest/svm_fifo_test.c b/src/plugins/unittest/svm_fifo_test.c
index 14ebfcacebd..af806e4782f 100644
--- a/src/plugins/unittest/svm_fifo_test.c
+++ b/src/plugins/unittest/svm_fifo_test.c
@@ -645,7 +645,7 @@ tcp_test_fifo3 (vlib_main_t * vm, unformat_input_t * input)
/* manually set head and tail pointers to validate modular arithmetic */
fifo_initial_offset = fifo_initial_offset % fifo_size;
- svm_fifo_init_pointers (f, fifo_initial_offset);
+ svm_fifo_init_pointers (f, fifo_initial_offset, fifo_initial_offset);
for (i = !randomize; i < vec_len (generate); i++)
{
@@ -759,7 +759,7 @@ tcp_test_fifo4 (vlib_main_t * vm, unformat_input_t * input)
/* Set head and tail pointers */
fifo_initial_offset = fifo_initial_offset % fifo_size;
- svm_fifo_init_pointers (f, fifo_initial_offset);
+ svm_fifo_init_pointers (f, fifo_initial_offset, fifo_initial_offset);
vec_validate (test_data, test_n_bytes - 1);
for (i = 0; i < vec_len (test_data); i++)
@@ -825,7 +825,7 @@ tcp_test_fifo5 (vlib_main_t * vm, unformat_input_t * input)
}
f = fifo_prepare (fifo_size);
- svm_fifo_init_pointers (f, offset);
+ svm_fifo_init_pointers (f, offset, offset);
vec_validate (test_data, 399);
for (i = 0; i < vec_len (test_data); i++)
@@ -934,10 +934,11 @@ tcp_test_fifo5 (vlib_main_t * vm, unformat_input_t * input)
static int
tcp_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input)
{
- int __clib_unused verbose, fifo_size = 201, start_offset = 100, i;
+ int verbose = 0, fifo_size = 201, start_offset = 100, i, j, rv;
+ int test_n_bytes, deq_bytes, enq_bytes, n_deqs, n_enqs;
svm_fifo_chunk_t *c, *next, *prev;
+ u8 *test_data = 0, *data_buf = 0;
svm_fifo_t *f;
- u8 *buf = 0;
while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
{
@@ -952,7 +953,7 @@ tcp_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input)
}
f = fifo_prepare (fifo_size);
- svm_fifo_init_pointers (f, start_offset);
+ svm_fifo_init_pointers (f, start_offset, start_offset);
/*
* Add with fifo not wrapped
@@ -973,7 +974,7 @@ tcp_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input)
* Add with fifo wrapped
*/
- f->tail = f->head + f->nitems;
+ svm_fifo_init_pointers (f, f->nitems - 100, f->nitems + 100);
c = clib_mem_alloc (sizeof (svm_fifo_chunk_t) + 100);
c->length = 100;
c->start_byte = ~0;
@@ -984,14 +985,14 @@ tcp_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input)
SFIFO_TEST (f->end_chunk != c, "tail chunk should not be updated");
SFIFO_TEST (f->size == fifo_size + 100, "size expected %u is %u",
fifo_size + 100, f->size);
- SFIFO_TEST (c->start_byte == ~0, "start byte expected %u is %u", ~0,
- c->start_byte);
+ SFIFO_TEST (c->start_byte == fifo_size + 100, "start byte expected %u is "
+ " %u", fifo_size + 100, c->start_byte);
/*
* Unwrap fifo
*/
- vec_validate (buf, 200);
- svm_fifo_dequeue_nowait (f, 201, buf);
+ vec_validate (data_buf, 200);
+ svm_fifo_dequeue_nowait (f, 201, data_buf);
SFIFO_TEST (f->end_chunk == c, "tail chunk should be updated");
SFIFO_TEST (f->size == fifo_size + 200, "size expected %u is %u",
@@ -1002,9 +1003,7 @@ tcp_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input)
/*
* Add N chunks
*/
-
- f->head = f->nitems - 100;
- f->tail = f->head + f->nitems;
+ svm_fifo_init_pointers (f, f->nitems - 100, f->nitems + 100);
prev = 0;
for (i = 0; i < 5; i++)
@@ -1034,14 +1033,160 @@ tcp_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input)
SFIFO_TEST (f->size == fifo_size + 200, "size expected %u is %u",
fifo_size + 200, f->size);
- svm_fifo_dequeue_nowait (f, 201, buf);
+ svm_fifo_dequeue_nowait (f, 201, data_buf);
SFIFO_TEST (f->size == fifo_size + 200 + 10 * 100, "size expected %u is %u",
fifo_size + 200 + 10 * 100, f->size);
+ /*
+ * Enqueue/dequeue tests
+ */
+
+ test_n_bytes = f->nitems;
+ vec_validate (test_data, test_n_bytes - 1);
+ vec_validate (data_buf, vec_len (test_data));
+ n_deqs = n_enqs = 6;
+ deq_bytes = enq_bytes = vec_len (test_data) / n_deqs;
+
+ for (i = 0; i < vec_len (test_data); i++)
+ test_data[i] = i;
+
+ /*
+ * Enqueue/deq boundary conditions
+ */
+ svm_fifo_init_pointers (f, 201, 201);
+ SFIFO_TEST (f->tail_chunk->start_byte == 201, "start byte expected %u is "
+ "%u", 201, f->tail_chunk->start_byte);
+
+ svm_fifo_enqueue_nowait (f, 200, test_data);
+ SFIFO_TEST (f->tail_chunk->start_byte == 401, "start byte expected %u is "
+ "%u", 401, f->tail_chunk->start_byte);
+
+ svm_fifo_dequeue_nowait (f, 200, data_buf);
+ SFIFO_TEST (f->head_chunk->start_byte == 401, "start byte expected %u is "
+ "%u", 401, f->head_chunk->start_byte);
+
+ /*
+ * Simple enqueue/deq and data validation (1)
+ */
+ svm_fifo_init_pointers (f, f->nitems / 2, f->nitems / 2);
+ for (i = 0; i < test_n_bytes; i++)
+ {
+ rv = svm_fifo_enqueue_nowait (f, sizeof (u8), &test_data[i]);
+ if (rv < 0)
+ {
+ clib_warning ("enqueue returned %d", rv);
+ goto cleanup;
+ }
+ }
+
+ SFIFO_TEST (svm_fifo_max_dequeue (f) == test_n_bytes, "max deq expected %u "
+ "is %u", test_n_bytes, svm_fifo_max_dequeue (f));
+
+ for (i = 0; i < test_n_bytes; i++)
+ svm_fifo_dequeue_nowait (f, 1, &data_buf[i]);
+
+ rv = compare_data (data_buf, test_data, 0, vec_len (test_data),
+ (u32 *) & j);
+ if (rv)
+ vlib_cli_output (vm, "[%d] dequeued %u expected %u", j, data_buf[j],
+ test_data[j]);
+ SFIFO_TEST ((rv == 0), "dequeued compared to original returned %d", rv);
+
+ /*
+ * Simple enqueue/deq and data validation (2)
+ */
+ for (i = 0; i <= n_enqs; i++)
+ {
+ rv = svm_fifo_enqueue_nowait (f, enq_bytes, test_data + i * enq_bytes);
+ if (rv < 0)
+ {
+ clib_warning ("enqueue returned %d", rv);
+ goto cleanup;
+ }
+ }
+
+ SFIFO_TEST (svm_fifo_max_dequeue (f) == test_n_bytes, "max deq expected %u "
+ "is %u", test_n_bytes, svm_fifo_max_dequeue (f));
+
+ for (i = 0; i <= n_deqs; i++)
+ svm_fifo_dequeue_nowait (f, deq_bytes, data_buf + i * deq_bytes);
+
+ rv = compare_data (data_buf, test_data, 0, vec_len (test_data),
+ (u32 *) & j);
+ if (rv)
+ vlib_cli_output (vm, "[%d] dequeued %u expected %u", j, data_buf[j],
+ test_data[j]);
+ SFIFO_TEST ((rv == 0), "dequeued compared to original returned %d", rv);
+
+ /*
+ * OOO enqueues/dequeues and data validation (1)
+ */
+ for (i = test_n_bytes - 1; i > 0; i--)
+ {
+ rv = svm_fifo_enqueue_with_offset (f, i, sizeof (u8), &test_data[i]);
+ if (verbose)
+ vlib_cli_output (vm, "add [%d] [%d, %d]", i, i, i + sizeof (u8));
+ if (rv)
+ {
+ clib_warning ("enqueue returned %d", rv);
+ goto cleanup;
+ }
+ }
+
+ SFIFO_TEST (svm_fifo_max_dequeue (f) == 0, "max deq expected %u is %u",
+ 0, svm_fifo_max_dequeue (f));
+
+ svm_fifo_enqueue_nowait (f, sizeof (u8), &test_data[0]);
+
+ memset (data_buf, 0, vec_len (data_buf));
+ for (i = 0; i <= n_deqs; i++)
+ svm_fifo_dequeue_nowait (f, deq_bytes, data_buf + i * deq_bytes);
+
+ rv = compare_data (data_buf, test_data, 0, vec_len (test_data),
+ (u32 *) & j);
+ if (rv)
+ vlib_cli_output (vm, "[%d] dequeued %u expected %u", j, data_buf[j],
+ test_data[j]);
+ SFIFO_TEST ((rv == 0), "dequeued compared to original returned %d", rv);
+
+ /*
+ * OOO enqueues/dequeues and data validation (2)
+ */
+
+ for (i = n_enqs; i > 0; i--)
+ {
+ u32 enq_now = clib_min (enq_bytes, vec_len (test_data) - i * enq_bytes);
+ rv = svm_fifo_enqueue_with_offset (f, i * enq_bytes, enq_now,
+ test_data + i * enq_bytes);
+ if (verbose)
+ vlib_cli_output (vm, "add [%d, %d]", i * enq_bytes,
+ i * enq_bytes + enq_now);
+ if (rv)
+ {
+ clib_warning ("enqueue returned %d", rv);
+ goto cleanup;
+ }
+ }
+
+ svm_fifo_enqueue_nowait (f, enq_bytes, &test_data[0]);
+
+ memset (data_buf, 0, vec_len (data_buf));
+ for (i = 0; i <= n_deqs; i++)
+ svm_fifo_dequeue_nowait (f, deq_bytes, data_buf + i * deq_bytes);
+
+ rv = compare_data (data_buf, test_data, 0, vec_len (test_data),
+ (u32 *) & j);
+ if (rv)
+ vlib_cli_output (vm, "[%d] dequeued %u expected %u", j, data_buf[j],
+ test_data[j]);
+ SFIFO_TEST ((rv == 0), "dequeued compared to original returned %d", rv);
/*
* Cleanup
*/
+
+cleanup:
+
c = f->start_chunk->next;
while (c && c != f->start_chunk)
{
@@ -1052,7 +1197,7 @@ tcp_test_fifo_grow (vlib_main_t * vm, unformat_input_t * input)
svm_fifo_free (f);
- vec_free (buf);
+ vec_free (data_buf);
return 0;
}