validation: pktio: test batch receive

Message ID 1447865953-2618-1-git-send-email-stuart.haslam@linaro.org
State New
Headers show

Commit Message

Stuart Haslam Nov. 18, 2015, 4:59 p.m.
Modify the tests that currently transmit packets in batches to also
receive packets in batches. This adds coverage of odp_queue_deq_multi()
and odp_schedule_multi() specifically against a packet input queue,
as this doesn't get tested anywhere else in the validation suite.

Signed-off-by: Stuart Haslam <stuart.haslam@linaro.org>
---
 test/validation/pktio/pktio.c | 137 +++++++++++++++++++++---------------------
 1 file changed, 68 insertions(+), 69 deletions(-)

Comments

Ivan Khoronzhuk Nov. 19, 2015, 11:43 a.m. | #1
Sruart, Maxim

It will likely have conflicts with time API that gets rid of cycles dependency.
It should be rebased on api-next or api-next merged in master and then rebased.

On 18.11.15 18:59, Stuart Haslam wrote:
> Modify the tests that currently transmit packets in batches to also
> receive packets in batches. This adds coverage of odp_queue_deq_multi()
> and odp_schedule_multi() specifically against a packet input queue,
> as this doesn't get tested anywhere else in the validation suite.
>
> Signed-off-by: Stuart Haslam <stuart.haslam@linaro.org>
> ---
>   test/validation/pktio/pktio.c | 137 +++++++++++++++++++++---------------------
>   1 file changed, 68 insertions(+), 69 deletions(-)
>
> diff --git a/test/validation/pktio/pktio.c b/test/validation/pktio/pktio.c
> index 41106b0..9cccaf2 100644
> --- a/test/validation/pktio/pktio.c
> +++ b/test/validation/pktio/pktio.c
> @@ -137,7 +137,7 @@ static uint32_t pktio_pkt_seq(odp_packet_t pkt)
>   	pkt_tail_t tail;
>
>   	if (pkt == ODP_PACKET_INVALID)
> -		return -1;
> +		return TEST_SEQ_INVALID;
>
>   	off = odp_packet_l4_offset(pkt);
>   	if (off ==  ODP_PACKET_OFFSET_INVALID)
> @@ -330,68 +330,76 @@ static int destroy_inq(odp_pktio_t pktio)
>   	return odp_queue_destroy(inq);
>   }
>
> -static odp_event_t queue_deq_wait_time(odp_queue_t queue, uint64_t ns)
> +static int get_packets(pktio_info_t *pktio_rx, odp_packet_t pkt_tbl[], int num)
>   {
> -	uint64_t start, now, diff;
> -	odp_event_t ev;
> +	odp_event_t evt_tbl[num];
> +	int num_evts = 0;
> +	int num_pkts = 0;
> +	int i;
>
> -	start = odp_time_cycles();
> +	if (pktio_rx->in_mode == ODP_PKTIN_MODE_RECV)
> +		return odp_pktio_recv(pktio_rx->id, pkt_tbl, num);
>
> -	do {
> -		ev = odp_queue_deq(queue);
> -		if (ev != ODP_EVENT_INVALID)
> -			return ev;
> -		now = odp_time_cycles();
> -		diff = odp_time_diff_cycles(start, now);
> -	} while (odp_time_cycles_to_ns(diff) < ns);
> +	if (num > 1) {
> +		if (pktio_rx->in_mode == ODP_PKTIN_MODE_POLL)
> +			num_evts = odp_queue_deq_multi(pktio_rx->inq, evt_tbl,
> +						       num);
> +		else
> +			num_evts = odp_schedule_multi(NULL, ODP_SCHED_NO_WAIT,
> +						      evt_tbl, num);
> +	} else {
> +		odp_event_t evt_tmp;
> +
> +		if (pktio_rx->in_mode == ODP_PKTIN_MODE_POLL)
> +			evt_tmp = odp_queue_deq(pktio_rx->inq);
> +		else
> +			evt_tmp = odp_schedule(NULL, ODP_SCHED_NO_WAIT);
> +
> +		if (evt_tmp != ODP_EVENT_INVALID)
> +			evt_tbl[num_evts++] = evt_tmp;
> +	}
> +
> +	/* convert events to packets, discarding any non-packet events */
> +	for (i = 0; i < num_evts; ++i) {
> +		if (odp_event_type(evt_tbl[i]) == ODP_EVENT_PACKET)
> +			pkt_tbl[num_pkts++] = odp_packet_from_event(evt_tbl[i]);
> +		else
> +			odp_event_free(evt_tbl[i]);
> +	}
>
> -	return ODP_EVENT_INVALID;
> +	return num_pkts;
>   }
>
> -static odp_packet_t wait_for_packet(pktio_info_t *pktio_rx,
> -				    uint32_t seq, uint64_t ns)
> +static int wait_for_packets(pktio_info_t *pktio_rx, odp_packet_t pkt_tbl[],
> +			    uint32_t seq_tbl[], int num, uint64_t ns)
>   {
>   	uint64_t start, now, diff;
> -	odp_event_t ev;
> -	odp_packet_t pkt;
> -	uint64_t wait;
> +	int num_rx = 0;
> +	int i;
> +	odp_packet_t pkt_tmp[num];
>
>   	start = odp_time_cycles();
> -	wait = odp_schedule_wait_time(ns);
>
>   	do {
> -		pkt = ODP_PACKET_INVALID;
> -
> -		if (pktio_rx->in_mode == ODP_PKTIN_MODE_RECV) {
> -			odp_pktio_recv(pktio_rx->id, &pkt, 1);
> -		} else {
> -			if (pktio_rx->in_mode == ODP_PKTIN_MODE_POLL)
> -				ev = queue_deq_wait_time(pktio_rx->inq, ns);
> -			else
> -				ev = odp_schedule(NULL, wait);
> -
> -			if (ev != ODP_EVENT_INVALID) {
> -				if (odp_event_type(ev) == ODP_EVENT_PACKET)
> -					pkt = odp_packet_from_event(ev);
> -				else
> -					odp_event_free(ev);
> -			}
> -		}
> +		int n = get_packets(pktio_rx, pkt_tmp, num);
>
> -		if (pkt != ODP_PACKET_INVALID) {
> -			if (pktio_pkt_seq(pkt) == seq)
> -				return pkt;
> +		if (n < 0)
> +			break;
>
> -			odp_packet_free(pkt);
> +		for (i = 0; i < n; ++i) {
> +			if (pktio_pkt_seq(pkt_tmp[i]) == seq_tbl[num_rx]) {
> +				pkt_tbl[num_rx++] = pkt_tmp[i];
> +				num--;
> +			} else {
> +				odp_packet_free(pkt_tmp[i]);
> +			}
>   		}
>
>   		now = odp_time_cycles();
>   		diff = odp_time_diff_cycles(start, now);
> -	} while (odp_time_cycles_to_ns(diff) < ns);
> +	} while (num_rx < num && odp_time_cycles_to_ns(diff) < ns);
>
> -	CU_FAIL("failed to receive transmitted packet");
> -
> -	return ODP_PACKET_INVALID;
> +	return num_rx;
>   }
>
>   static void pktio_txrx_multi(pktio_info_t *pktio_a, pktio_info_t *pktio_b,
> @@ -399,9 +407,9 @@ static void pktio_txrx_multi(pktio_info_t *pktio_a, pktio_info_t *pktio_b,
>   {
>   	odp_packet_t tx_pkt[num_pkts];
>   	odp_event_t tx_ev[num_pkts];
> -	odp_packet_t rx_pkt;
> +	odp_packet_t rx_pkt[num_pkts];
>   	uint32_t tx_seq[num_pkts];
> -	int i, ret;
> +	int i, ret, num_rx;
>
>   	/* generate test packets to send */
>   	for (i = 0; i < num_pkts; ++i) {
> @@ -445,17 +453,16 @@ static void pktio_txrx_multi(pktio_info_t *pktio_a, pktio_info_t *pktio_b,
>   	}
>
>   	/* and wait for them to arrive back */
> -	for (i = 0; i < num_pkts; ++i) {
> -		rx_pkt = wait_for_packet(pktio_b, tx_seq[i], ODP_TIME_SEC);
> -
> -		if (rx_pkt == ODP_PACKET_INVALID)
> -			break;
> -		CU_ASSERT(odp_packet_input(rx_pkt) == pktio_b->id);
> -		CU_ASSERT(odp_packet_has_error(rx_pkt) == 0);
> -		odp_packet_free(rx_pkt);
> +	num_rx = wait_for_packets(pktio_b, rx_pkt, tx_seq,
> +				  num_pkts, ODP_TIME_SEC);
> +	CU_ASSERT(num_rx == num_pkts);
> +
> +	for (i = 0; i < num_rx; ++i) {
> +		CU_ASSERT_FATAL(rx_pkt[i] != ODP_PACKET_INVALID);
> +		CU_ASSERT(odp_packet_input(rx_pkt[i]) == pktio_b->id);
> +		CU_ASSERT(odp_packet_has_error(rx_pkt[i]) == 0);
> +		odp_packet_free(rx_pkt[i]);
>   	}
> -
> -	CU_ASSERT(i == num_pkts);
>   }
>
>   static void test_txrx(odp_pktio_input_mode_t in_mode, int num_pkts)
> @@ -913,12 +920,8 @@ static void pktio_test_send_failure(void)
>   		info_rx.inq  = ODP_QUEUE_INVALID;
>   		info_rx.in_mode = ODP_PKTIN_MODE_RECV;
>
> -		for (i = 0; i < ret; ++i) {
> -			pkt_tbl[i] = wait_for_packet(&info_rx,
> -						     pkt_seq[i], ODP_TIME_SEC);
> -			if (pkt_tbl[i] == ODP_PACKET_INVALID)
> -				break;
> -		}
> +		i = wait_for_packets(&info_rx, pkt_tbl, pkt_seq,
> +				     ret, ODP_TIME_SEC);
>
>   		if (i == ret) {
>   			/* now try to send starting with the too-long packet
> @@ -944,13 +947,9 @@ static void pktio_test_send_failure(void)
>   		ret = odp_pktio_send(pktio_tx, &pkt_tbl[i], TX_BATCH_LEN - i);
>   		CU_ASSERT_FATAL(ret == (TX_BATCH_LEN - i));
>
> -		for (; i < TX_BATCH_LEN; ++i) {
> -			pkt_tbl[i] = wait_for_packet(&info_rx,
> -						     pkt_seq[i], ODP_TIME_SEC);
> -			if (pkt_tbl[i] == ODP_PACKET_INVALID)
> -				break;
> -		}
> -		CU_ASSERT(i == TX_BATCH_LEN);
> +		i = wait_for_packets(&info_rx, &pkt_tbl[i], &pkt_seq[i],
> +				     ret, ODP_TIME_SEC);
> +		CU_ASSERT(i == ret);
>   	} else {
>   		CU_FAIL("failed to generate test packets\n");
>   	}
>
Stuart Haslam Nov. 19, 2015, 11:51 a.m. | #2
On Thu, Nov 19, 2015 at 01:43:23PM +0200, Ivan Khoronzhuk wrote:
> Sruart, Maxim
> 
> It will likely have conflicts with time API that gets rid of cycles dependency.
> It should be rebased on api-next or api-next merged in master and then rebased.
> 

OK, I'll wait for it to get a Reviewed-by on master then I can do
whatever merging Maxim wants.
Ivan Khoronzhuk Nov. 19, 2015, 11:54 a.m. | #3
On 19.11.15 13:51, Stuart Haslam wrote:
> On Thu, Nov 19, 2015 at 01:43:23PM +0200, Ivan Khoronzhuk wrote:
>> Sruart, Maxim
>>
>> It will likely have conflicts with time API that gets rid of cycles dependency.
>> It should be rebased on api-next or api-next merged in master and then rebased.
>>
>
> OK, I'll wait for it to get a Reviewed-by on master then I can do
> whatever merging Maxim wants.
>

Smth strange happening here. New time api names should be present in master already.
They are present in v1.4.1.0....
Ivan Khoronzhuk Nov. 19, 2015, 11:59 a.m. | #4
On 19.11.15 13:54, Ivan Khoronzhuk wrote:
>
>
> On 19.11.15 13:51, Stuart Haslam wrote:
>> On Thu, Nov 19, 2015 at 01:43:23PM +0200, Ivan Khoronzhuk wrote:
>>> Sruart, Maxim
>>>
>>> It will likely have conflicts with time API that gets rid of cycles dependency.
>>> It should be rebased on api-next or api-next merged in master and then rebased.
>>>
>>
>> OK, I'll wait for it to get a Reviewed-by on master then I can do
>> whatever merging Maxim wants.
>>
>
> Smth strange happening here. New time api names should be present in master already.
> They are present in v1.4.1.0....
>

No, not present in v1.4.1.0. But should be.
Anyway we this patch should contain correct API.

Patch

diff --git a/test/validation/pktio/pktio.c b/test/validation/pktio/pktio.c
index 41106b0..9cccaf2 100644
--- a/test/validation/pktio/pktio.c
+++ b/test/validation/pktio/pktio.c
@@ -137,7 +137,7 @@  static uint32_t pktio_pkt_seq(odp_packet_t pkt)
 	pkt_tail_t tail;
 
 	if (pkt == ODP_PACKET_INVALID)
-		return -1;
+		return TEST_SEQ_INVALID;
 
 	off = odp_packet_l4_offset(pkt);
 	if (off ==  ODP_PACKET_OFFSET_INVALID)
@@ -330,68 +330,76 @@  static int destroy_inq(odp_pktio_t pktio)
 	return odp_queue_destroy(inq);
 }
 
-static odp_event_t queue_deq_wait_time(odp_queue_t queue, uint64_t ns)
+static int get_packets(pktio_info_t *pktio_rx, odp_packet_t pkt_tbl[], int num)
 {
-	uint64_t start, now, diff;
-	odp_event_t ev;
+	odp_event_t evt_tbl[num];
+	int num_evts = 0;
+	int num_pkts = 0;
+	int i;
 
-	start = odp_time_cycles();
+	if (pktio_rx->in_mode == ODP_PKTIN_MODE_RECV)
+		return odp_pktio_recv(pktio_rx->id, pkt_tbl, num);
 
-	do {
-		ev = odp_queue_deq(queue);
-		if (ev != ODP_EVENT_INVALID)
-			return ev;
-		now = odp_time_cycles();
-		diff = odp_time_diff_cycles(start, now);
-	} while (odp_time_cycles_to_ns(diff) < ns);
+	if (num > 1) {
+		if (pktio_rx->in_mode == ODP_PKTIN_MODE_POLL)
+			num_evts = odp_queue_deq_multi(pktio_rx->inq, evt_tbl,
+						       num);
+		else
+			num_evts = odp_schedule_multi(NULL, ODP_SCHED_NO_WAIT,
+						      evt_tbl, num);
+	} else {
+		odp_event_t evt_tmp;
+
+		if (pktio_rx->in_mode == ODP_PKTIN_MODE_POLL)
+			evt_tmp = odp_queue_deq(pktio_rx->inq);
+		else
+			evt_tmp = odp_schedule(NULL, ODP_SCHED_NO_WAIT);
+
+		if (evt_tmp != ODP_EVENT_INVALID)
+			evt_tbl[num_evts++] = evt_tmp;
+	}
+
+	/* convert events to packets, discarding any non-packet events */
+	for (i = 0; i < num_evts; ++i) {
+		if (odp_event_type(evt_tbl[i]) == ODP_EVENT_PACKET)
+			pkt_tbl[num_pkts++] = odp_packet_from_event(evt_tbl[i]);
+		else
+			odp_event_free(evt_tbl[i]);
+	}
 
-	return ODP_EVENT_INVALID;
+	return num_pkts;
 }
 
-static odp_packet_t wait_for_packet(pktio_info_t *pktio_rx,
-				    uint32_t seq, uint64_t ns)
+static int wait_for_packets(pktio_info_t *pktio_rx, odp_packet_t pkt_tbl[],
+			    uint32_t seq_tbl[], int num, uint64_t ns)
 {
 	uint64_t start, now, diff;
-	odp_event_t ev;
-	odp_packet_t pkt;
-	uint64_t wait;
+	int num_rx = 0;
+	int i;
+	odp_packet_t pkt_tmp[num];
 
 	start = odp_time_cycles();
-	wait = odp_schedule_wait_time(ns);
 
 	do {
-		pkt = ODP_PACKET_INVALID;
-
-		if (pktio_rx->in_mode == ODP_PKTIN_MODE_RECV) {
-			odp_pktio_recv(pktio_rx->id, &pkt, 1);
-		} else {
-			if (pktio_rx->in_mode == ODP_PKTIN_MODE_POLL)
-				ev = queue_deq_wait_time(pktio_rx->inq, ns);
-			else
-				ev = odp_schedule(NULL, wait);
-
-			if (ev != ODP_EVENT_INVALID) {
-				if (odp_event_type(ev) == ODP_EVENT_PACKET)
-					pkt = odp_packet_from_event(ev);
-				else
-					odp_event_free(ev);
-			}
-		}
+		int n = get_packets(pktio_rx, pkt_tmp, num);
 
-		if (pkt != ODP_PACKET_INVALID) {
-			if (pktio_pkt_seq(pkt) == seq)
-				return pkt;
+		if (n < 0)
+			break;
 
-			odp_packet_free(pkt);
+		for (i = 0; i < n; ++i) {
+			if (pktio_pkt_seq(pkt_tmp[i]) == seq_tbl[num_rx]) {
+				pkt_tbl[num_rx++] = pkt_tmp[i];
+				num--;
+			} else {
+				odp_packet_free(pkt_tmp[i]);
+			}
 		}
 
 		now = odp_time_cycles();
 		diff = odp_time_diff_cycles(start, now);
-	} while (odp_time_cycles_to_ns(diff) < ns);
+	} while (num_rx < num && odp_time_cycles_to_ns(diff) < ns);
 
-	CU_FAIL("failed to receive transmitted packet");
-
-	return ODP_PACKET_INVALID;
+	return num_rx;
 }
 
 static void pktio_txrx_multi(pktio_info_t *pktio_a, pktio_info_t *pktio_b,
@@ -399,9 +407,9 @@  static void pktio_txrx_multi(pktio_info_t *pktio_a, pktio_info_t *pktio_b,
 {
 	odp_packet_t tx_pkt[num_pkts];
 	odp_event_t tx_ev[num_pkts];
-	odp_packet_t rx_pkt;
+	odp_packet_t rx_pkt[num_pkts];
 	uint32_t tx_seq[num_pkts];
-	int i, ret;
+	int i, ret, num_rx;
 
 	/* generate test packets to send */
 	for (i = 0; i < num_pkts; ++i) {
@@ -445,17 +453,16 @@  static void pktio_txrx_multi(pktio_info_t *pktio_a, pktio_info_t *pktio_b,
 	}
 
 	/* and wait for them to arrive back */
-	for (i = 0; i < num_pkts; ++i) {
-		rx_pkt = wait_for_packet(pktio_b, tx_seq[i], ODP_TIME_SEC);
-
-		if (rx_pkt == ODP_PACKET_INVALID)
-			break;
-		CU_ASSERT(odp_packet_input(rx_pkt) == pktio_b->id);
-		CU_ASSERT(odp_packet_has_error(rx_pkt) == 0);
-		odp_packet_free(rx_pkt);
+	num_rx = wait_for_packets(pktio_b, rx_pkt, tx_seq,
+				  num_pkts, ODP_TIME_SEC);
+	CU_ASSERT(num_rx == num_pkts);
+
+	for (i = 0; i < num_rx; ++i) {
+		CU_ASSERT_FATAL(rx_pkt[i] != ODP_PACKET_INVALID);
+		CU_ASSERT(odp_packet_input(rx_pkt[i]) == pktio_b->id);
+		CU_ASSERT(odp_packet_has_error(rx_pkt[i]) == 0);
+		odp_packet_free(rx_pkt[i]);
 	}
-
-	CU_ASSERT(i == num_pkts);
 }
 
 static void test_txrx(odp_pktio_input_mode_t in_mode, int num_pkts)
@@ -913,12 +920,8 @@  static void pktio_test_send_failure(void)
 		info_rx.inq  = ODP_QUEUE_INVALID;
 		info_rx.in_mode = ODP_PKTIN_MODE_RECV;
 
-		for (i = 0; i < ret; ++i) {
-			pkt_tbl[i] = wait_for_packet(&info_rx,
-						     pkt_seq[i], ODP_TIME_SEC);
-			if (pkt_tbl[i] == ODP_PACKET_INVALID)
-				break;
-		}
+		i = wait_for_packets(&info_rx, pkt_tbl, pkt_seq,
+				     ret, ODP_TIME_SEC);
 
 		if (i == ret) {
 			/* now try to send starting with the too-long packet
@@ -944,13 +947,9 @@  static void pktio_test_send_failure(void)
 		ret = odp_pktio_send(pktio_tx, &pkt_tbl[i], TX_BATCH_LEN - i);
 		CU_ASSERT_FATAL(ret == (TX_BATCH_LEN - i));
 
-		for (; i < TX_BATCH_LEN; ++i) {
-			pkt_tbl[i] = wait_for_packet(&info_rx,
-						     pkt_seq[i], ODP_TIME_SEC);
-			if (pkt_tbl[i] == ODP_PACKET_INVALID)
-				break;
-		}
-		CU_ASSERT(i == TX_BATCH_LEN);
+		i = wait_for_packets(&info_rx, &pkt_tbl[i], &pkt_seq[i],
+				     ret, ODP_TIME_SEC);
+		CU_ASSERT(i == ret);
 	} else {
 		CU_FAIL("failed to generate test packets\n");
 	}