xref: /dpdk/app/test/test_link_bonding.c (revision d91c4b1b)
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright(c) 2010-2014 Intel Corporation
3  */
4 
5 #include "unistd.h"
6 #include <string.h>
7 #include <stdarg.h>
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <stdint.h>
11 #include <inttypes.h>
12 #include <errno.h>
13 #include <sys/queue.h>
14 #include <sys/time.h>
15 #include <rte_cycles.h>
16 #include <rte_byteorder.h>
17 #include <rte_common.h>
18 #include <rte_debug.h>
19 #include <rte_ethdev.h>
20 #include <ethdev_driver.h>
21 #include <rte_log.h>
22 #include <rte_lcore.h>
23 #include <rte_memory.h>
24 #include <rte_string_fns.h>
25 #include <rte_eth_bond.h>
26 
27 #include "virtual_pmd.h"
28 #include "packet_burst_generator.h"
29 
30 #include "test.h"
31 
32 #define TEST_MAX_NUMBER_OF_PORTS (6)
33 
34 #define RX_RING_SIZE 1024
35 #define RX_FREE_THRESH 32
36 #define RX_PTHRESH 8
37 #define RX_HTHRESH 8
38 #define RX_WTHRESH 0
39 
40 #define TX_RING_SIZE 1024
41 #define TX_FREE_THRESH 32
42 #define TX_PTHRESH 32
43 #define TX_HTHRESH 0
44 #define TX_WTHRESH 0
45 #define TX_RSBIT_THRESH 32
46 
47 #define MBUF_CACHE_SIZE (250)
48 #define BURST_SIZE (32)
49 
50 #define RTE_TEST_RX_DESC_MAX	(2048)
51 #define RTE_TEST_TX_DESC_MAX	(2048)
52 #define MAX_PKT_BURST			(512)
53 #define DEF_PKT_BURST			(16)
54 
55 #define BONDED_DEV_NAME			("net_bonding_ut")
56 
57 #define INVALID_SOCKET_ID		(-1)
58 #define INVALID_PORT_ID			(-1)
59 #define INVALID_BONDING_MODE	(-1)
60 
61 
62 uint8_t slave_mac[] = {0x00, 0xFF, 0x00, 0xFF, 0x00, 0x00 };
63 uint8_t bonded_mac[] = {0xAA, 0xFF, 0xAA, 0xFF, 0xAA, 0xFF };
64 
65 struct link_bonding_unittest_params {
66 	int16_t bonded_port_id;
67 	int16_t slave_port_ids[TEST_MAX_NUMBER_OF_PORTS];
68 	uint16_t bonded_slave_count;
69 	uint8_t bonding_mode;
70 
71 	uint16_t nb_rx_q;
72 	uint16_t nb_tx_q;
73 
74 	struct rte_mempool *mbuf_pool;
75 
76 	struct rte_ether_addr *default_slave_mac;
77 	struct rte_ether_addr *default_bonded_mac;
78 
79 	/* Packet Headers */
80 	struct rte_ether_hdr *pkt_eth_hdr;
81 	struct rte_ipv4_hdr *pkt_ipv4_hdr;
82 	struct rte_ipv6_hdr *pkt_ipv6_hdr;
83 	struct rte_udp_hdr *pkt_udp_hdr;
84 
85 };
86 
87 static struct rte_ipv4_hdr pkt_ipv4_hdr;
88 static struct rte_ipv6_hdr pkt_ipv6_hdr;
89 static struct rte_udp_hdr pkt_udp_hdr;
90 
91 static struct link_bonding_unittest_params default_params  = {
92 	.bonded_port_id = -1,
93 	.slave_port_ids = { -1 },
94 	.bonded_slave_count = 0,
95 	.bonding_mode = BONDING_MODE_ROUND_ROBIN,
96 
97 	.nb_rx_q = 1,
98 	.nb_tx_q = 1,
99 
100 	.mbuf_pool = NULL,
101 
102 	.default_slave_mac = (struct rte_ether_addr *)slave_mac,
103 	.default_bonded_mac = (struct rte_ether_addr *)bonded_mac,
104 
105 	.pkt_eth_hdr = NULL,
106 	.pkt_ipv4_hdr = &pkt_ipv4_hdr,
107 	.pkt_ipv6_hdr = &pkt_ipv6_hdr,
108 	.pkt_udp_hdr = &pkt_udp_hdr
109 
110 };
111 
112 static struct link_bonding_unittest_params *test_params = &default_params;
113 
114 static uint8_t src_mac[] = { 0xFF, 0xAA, 0xFF, 0xAA, 0xFF, 0xAA };
115 static uint8_t dst_mac_0[] = { 0xFF, 0xAA, 0xFF, 0xAA, 0xFF, 0xAA };
116 static uint8_t dst_mac_1[] = { 0xFF, 0xAA, 0xFF, 0xAA, 0xFF, 0xAB };
117 
118 static uint32_t src_addr = IPV4_ADDR(192, 168, 1, 98);
119 static uint32_t dst_addr_0 = IPV4_ADDR(192, 168, 1, 98);
120 static uint32_t dst_addr_1 = IPV4_ADDR(193, 166, 10, 97);
121 
122 static uint8_t src_ipv6_addr[] = { 0xFF, 0xAA, 0xFF, 0xAA, 0xFF, 0xAA, 0xFF,
123 		0xAA, 0xFF, 0xAA, 0xFF, 0xAA, 0xFF, 0xAA , 0xFF, 0xAA  };
124 static uint8_t dst_ipv6_addr_0[] = { 0xFF, 0xAA, 0xFF, 0xAA, 0xFF, 0xAA, 0xFF,
125 		0xAA, 0xFF, 0xAA,  0xFF, 0xAA , 0xFF, 0xAA, 0xFF, 0xAA  };
126 static uint8_t dst_ipv6_addr_1[] = { 0xFF, 0xAA, 0xFF, 0xAA, 0xFF, 0xAA, 0xFF,
127 		0xAA, 0xFF, 0xAA, 0xFF, 0xAA , 0xFF, 0xAA , 0xFF, 0xAB  };
128 
129 static uint16_t src_port = 1024;
130 static uint16_t dst_port_0 = 1024;
131 static uint16_t dst_port_1 = 2024;
132 
133 static uint16_t vlan_id = 0x100;
134 
135 static struct rte_eth_conf default_pmd_conf = {
136 	.rxmode = {
137 		.mq_mode = RTE_ETH_MQ_RX_NONE,
138 		.split_hdr_size = 0,
139 	},
140 	.txmode = {
141 		.mq_mode = RTE_ETH_MQ_TX_NONE,
142 	},
143 	.lpbk_mode = 0,
144 };
145 
146 static const struct rte_eth_rxconf rx_conf_default = {
147 	.rx_thresh = {
148 		.pthresh = RX_PTHRESH,
149 		.hthresh = RX_HTHRESH,
150 		.wthresh = RX_WTHRESH,
151 	},
152 	.rx_free_thresh = RX_FREE_THRESH,
153 	.rx_drop_en = 0,
154 };
155 
156 static struct rte_eth_txconf tx_conf_default = {
157 	.tx_thresh = {
158 		.pthresh = TX_PTHRESH,
159 		.hthresh = TX_HTHRESH,
160 		.wthresh = TX_WTHRESH,
161 	},
162 	.tx_free_thresh = TX_FREE_THRESH,
163 	.tx_rs_thresh = TX_RSBIT_THRESH,
164 };
165 
166 static void free_virtualpmd_tx_queue(void);
167 
168 
169 
170 static int
171 configure_ethdev(uint16_t port_id, uint8_t start, uint8_t en_isr)
172 {
173 	int q_id;
174 
175 	if (en_isr)
176 		default_pmd_conf.intr_conf.lsc = 1;
177 	else
178 		default_pmd_conf.intr_conf.lsc = 0;
179 
180 	TEST_ASSERT_SUCCESS(rte_eth_dev_configure(port_id, test_params->nb_rx_q,
181 			test_params->nb_tx_q, &default_pmd_conf),
182 			"rte_eth_dev_configure for port %d failed", port_id);
183 
184 	for (q_id = 0; q_id < test_params->nb_rx_q; q_id++)
185 		TEST_ASSERT_SUCCESS(rte_eth_rx_queue_setup(port_id, q_id, RX_RING_SIZE,
186 				rte_eth_dev_socket_id(port_id), &rx_conf_default,
187 				test_params->mbuf_pool) ,
188 				"rte_eth_rx_queue_setup for port %d failed", port_id);
189 
190 	for (q_id = 0; q_id < test_params->nb_tx_q; q_id++)
191 		TEST_ASSERT_SUCCESS(rte_eth_tx_queue_setup(port_id, q_id, TX_RING_SIZE,
192 				rte_eth_dev_socket_id(port_id), &tx_conf_default),
193 				"rte_eth_tx_queue_setup for port %d failed", port_id);
194 
195 	if (start)
196 		TEST_ASSERT_SUCCESS(rte_eth_dev_start(port_id),
197 				"rte_eth_dev_start for port %d failed", port_id);
198 
199 	return 0;
200 }
201 
202 static int slaves_initialized;
203 static int mac_slaves_initialized;
204 
205 static pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
206 static pthread_cond_t cvar = PTHREAD_COND_INITIALIZER;
207 
208 
209 static int
210 test_setup(void)
211 {
212 	int i, nb_mbuf_per_pool;
213 	struct rte_ether_addr *mac_addr = (struct rte_ether_addr *)slave_mac;
214 
215 	/* Allocate ethernet packet header with space for VLAN header */
216 	if (test_params->pkt_eth_hdr == NULL) {
217 		test_params->pkt_eth_hdr = malloc(sizeof(struct rte_ether_hdr) +
218 				sizeof(struct rte_vlan_hdr));
219 
220 		TEST_ASSERT_NOT_NULL(test_params->pkt_eth_hdr,
221 				"Ethernet header struct allocation failed!");
222 	}
223 
224 	nb_mbuf_per_pool = RTE_TEST_RX_DESC_MAX + DEF_PKT_BURST +
225 			RTE_TEST_TX_DESC_MAX + MAX_PKT_BURST;
226 	if (test_params->mbuf_pool == NULL) {
227 		test_params->mbuf_pool = rte_pktmbuf_pool_create("MBUF_POOL",
228 			nb_mbuf_per_pool, MBUF_CACHE_SIZE, 0,
229 			RTE_MBUF_DEFAULT_BUF_SIZE, rte_socket_id());
230 		TEST_ASSERT_NOT_NULL(test_params->mbuf_pool,
231 				"rte_mempool_create failed");
232 	}
233 
234 	/* Create / Initialize virtual eth devs */
235 	if (!slaves_initialized) {
236 		for (i = 0; i < TEST_MAX_NUMBER_OF_PORTS; i++) {
237 			char pmd_name[RTE_ETH_NAME_MAX_LEN];
238 
239 			mac_addr->addr_bytes[RTE_ETHER_ADDR_LEN-1] = i;
240 
241 			snprintf(pmd_name, RTE_ETH_NAME_MAX_LEN, "eth_virt_%d", i);
242 
243 			test_params->slave_port_ids[i] = virtual_ethdev_create(pmd_name,
244 					mac_addr, rte_socket_id(), 1);
245 			TEST_ASSERT(test_params->slave_port_ids[i] >= 0,
246 					"Failed to create virtual virtual ethdev %s", pmd_name);
247 
248 			TEST_ASSERT_SUCCESS(configure_ethdev(
249 					test_params->slave_port_ids[i], 1, 0),
250 					"Failed to configure virtual ethdev %s", pmd_name);
251 		}
252 		slaves_initialized = 1;
253 	}
254 
255 	return 0;
256 }
257 
258 static int
259 test_create_bonded_device(void)
260 {
261 	int current_slave_count;
262 
263 	uint16_t slaves[RTE_MAX_ETHPORTS];
264 
265 	/* Don't try to recreate bonded device if re-running test suite*/
266 	if (test_params->bonded_port_id == -1) {
267 		test_params->bonded_port_id = rte_eth_bond_create(BONDED_DEV_NAME,
268 				test_params->bonding_mode, rte_socket_id());
269 
270 		TEST_ASSERT(test_params->bonded_port_id >= 0,
271 				"Failed to create bonded ethdev %s", BONDED_DEV_NAME);
272 
273 		TEST_ASSERT_SUCCESS(configure_ethdev(test_params->bonded_port_id, 0, 0),
274 				"Failed to configure bonded ethdev %s", BONDED_DEV_NAME);
275 	}
276 
277 	TEST_ASSERT_SUCCESS(rte_eth_bond_mode_set(test_params->bonded_port_id,
278 			test_params->bonding_mode), "Failed to set ethdev %d to mode %d",
279 			test_params->bonded_port_id, test_params->bonding_mode);
280 
281 	current_slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id,
282 			slaves, RTE_MAX_ETHPORTS);
283 
284 	TEST_ASSERT_EQUAL(current_slave_count, 0,
285 			"Number of slaves %d is great than expected %d.",
286 			current_slave_count, 0);
287 
288 	current_slave_count = rte_eth_bond_active_slaves_get(
289 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS);
290 
291 	TEST_ASSERT_EQUAL(current_slave_count, 0,
292 			"Number of active slaves %d is great than expected %d.",
293 			current_slave_count, 0);
294 
295 	return 0;
296 }
297 
298 
299 static int
300 test_create_bonded_device_with_invalid_params(void)
301 {
302 	int port_id;
303 
304 	test_params->bonding_mode = BONDING_MODE_ROUND_ROBIN;
305 
306 	/* Invalid name */
307 	port_id = rte_eth_bond_create(NULL, test_params->bonding_mode,
308 			rte_socket_id());
309 	TEST_ASSERT(port_id < 0, "Created bonded device unexpectedly");
310 
311 	test_params->bonding_mode = INVALID_BONDING_MODE;
312 
313 	/* Invalid bonding mode */
314 	port_id = rte_eth_bond_create(BONDED_DEV_NAME, test_params->bonding_mode,
315 			rte_socket_id());
316 	TEST_ASSERT(port_id < 0, "Created bonded device unexpectedly.");
317 
318 	test_params->bonding_mode = BONDING_MODE_ROUND_ROBIN;
319 
320 	/* Invalid socket id */
321 	port_id = rte_eth_bond_create(BONDED_DEV_NAME, test_params->bonding_mode,
322 			INVALID_SOCKET_ID);
323 	TEST_ASSERT(port_id < 0, "Created bonded device unexpectedly.");
324 
325 	return 0;
326 }
327 
328 static int
329 test_add_slave_to_bonded_device(void)
330 {
331 	int current_slave_count;
332 
333 	uint16_t slaves[RTE_MAX_ETHPORTS];
334 
335 	TEST_ASSERT_SUCCESS(rte_eth_bond_slave_add(test_params->bonded_port_id,
336 			test_params->slave_port_ids[test_params->bonded_slave_count]),
337 			"Failed to add slave (%d) to bonded port (%d).",
338 			test_params->slave_port_ids[test_params->bonded_slave_count],
339 			test_params->bonded_port_id);
340 
341 	current_slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id,
342 			slaves, RTE_MAX_ETHPORTS);
343 	TEST_ASSERT_EQUAL(current_slave_count, test_params->bonded_slave_count + 1,
344 			"Number of slaves (%d) is greater than expected (%d).",
345 			current_slave_count, test_params->bonded_slave_count + 1);
346 
347 	current_slave_count = rte_eth_bond_active_slaves_get(
348 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS);
349 	TEST_ASSERT_EQUAL(current_slave_count, 0,
350 					"Number of active slaves (%d) is not as expected (%d).\n",
351 					current_slave_count, 0);
352 
353 	test_params->bonded_slave_count++;
354 
355 	return 0;
356 }
357 
358 static int
359 test_add_slave_to_invalid_bonded_device(void)
360 {
361 	/* Invalid port ID */
362 	TEST_ASSERT_FAIL(rte_eth_bond_slave_add(test_params->bonded_port_id + 5,
363 			test_params->slave_port_ids[test_params->bonded_slave_count]),
364 			"Expected call to failed as invalid port specified.");
365 
366 	/* Non bonded device */
367 	TEST_ASSERT_FAIL(rte_eth_bond_slave_add(test_params->slave_port_ids[0],
368 			test_params->slave_port_ids[test_params->bonded_slave_count]),
369 			"Expected call to failed as invalid port specified.");
370 
371 	return 0;
372 }
373 
374 
375 static int
376 test_remove_slave_from_bonded_device(void)
377 {
378 	int current_slave_count;
379 	struct rte_ether_addr read_mac_addr, *mac_addr;
380 	uint16_t slaves[RTE_MAX_ETHPORTS];
381 
382 	TEST_ASSERT_SUCCESS(rte_eth_bond_slave_remove(test_params->bonded_port_id,
383 			test_params->slave_port_ids[test_params->bonded_slave_count-1]),
384 			"Failed to remove slave %d from bonded port (%d).",
385 			test_params->slave_port_ids[test_params->bonded_slave_count-1],
386 			test_params->bonded_port_id);
387 
388 
389 	current_slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id,
390 			slaves, RTE_MAX_ETHPORTS);
391 
392 	TEST_ASSERT_EQUAL(current_slave_count, test_params->bonded_slave_count - 1,
393 			"Number of slaves (%d) is great than expected (%d).\n",
394 			current_slave_count, test_params->bonded_slave_count - 1);
395 
396 
397 	mac_addr = (struct rte_ether_addr *)slave_mac;
398 	mac_addr->addr_bytes[RTE_ETHER_ADDR_LEN-1] =
399 			test_params->bonded_slave_count-1;
400 
401 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(
402 			test_params->slave_port_ids[test_params->bonded_slave_count-1],
403 			&read_mac_addr),
404 			"Failed to get mac address (port %d)",
405 			test_params->slave_port_ids[test_params->bonded_slave_count-1]);
406 	TEST_ASSERT_SUCCESS(memcmp(mac_addr, &read_mac_addr, sizeof(read_mac_addr)),
407 			"bonded port mac address not set to that of primary port\n");
408 
409 	rte_eth_stats_reset(
410 			test_params->slave_port_ids[test_params->bonded_slave_count-1]);
411 
412 	virtual_ethdev_simulate_link_status_interrupt(test_params->bonded_port_id,
413 			0);
414 
415 	test_params->bonded_slave_count--;
416 
417 	return 0;
418 }
419 
420 static int
421 test_remove_slave_from_invalid_bonded_device(void)
422 {
423 	/* Invalid port ID */
424 	TEST_ASSERT_FAIL(rte_eth_bond_slave_remove(
425 			test_params->bonded_port_id + 5,
426 			test_params->slave_port_ids[test_params->bonded_slave_count - 1]),
427 			"Expected call to failed as invalid port specified.");
428 
429 	/* Non bonded device */
430 	TEST_ASSERT_FAIL(rte_eth_bond_slave_remove(
431 			test_params->slave_port_ids[0],
432 			test_params->slave_port_ids[test_params->bonded_slave_count - 1]),
433 			"Expected call to failed as invalid port specified.");
434 
435 	return 0;
436 }
437 
438 static int bonded_id = 2;
439 
440 static int
441 test_add_already_bonded_slave_to_bonded_device(void)
442 {
443 	int port_id, current_slave_count;
444 	uint16_t slaves[RTE_MAX_ETHPORTS];
445 	char pmd_name[RTE_ETH_NAME_MAX_LEN];
446 
447 	test_add_slave_to_bonded_device();
448 
449 	current_slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id,
450 			slaves, RTE_MAX_ETHPORTS);
451 	TEST_ASSERT_EQUAL(current_slave_count, 1,
452 			"Number of slaves (%d) is not that expected (%d).",
453 			current_slave_count, 1);
454 
455 	snprintf(pmd_name, RTE_ETH_NAME_MAX_LEN, "%s_%d", BONDED_DEV_NAME, ++bonded_id);
456 
457 	port_id = rte_eth_bond_create(pmd_name, test_params->bonding_mode,
458 			rte_socket_id());
459 	TEST_ASSERT(port_id >= 0, "Failed to create bonded device.");
460 
461 	TEST_ASSERT(rte_eth_bond_slave_add(port_id,
462 			test_params->slave_port_ids[test_params->bonded_slave_count - 1])
463 			< 0,
464 			"Added slave (%d) to bonded port (%d) unexpectedly.",
465 			test_params->slave_port_ids[test_params->bonded_slave_count-1],
466 			port_id);
467 
468 	return test_remove_slave_from_bonded_device();
469 }
470 
471 
472 static int
473 test_get_slaves_from_bonded_device(void)
474 {
475 	int current_slave_count;
476 	uint16_t slaves[RTE_MAX_ETHPORTS];
477 
478 	TEST_ASSERT_SUCCESS(test_add_slave_to_bonded_device(),
479 			"Failed to add slave to bonded device");
480 
481 	/* Invalid port id */
482 	current_slave_count = rte_eth_bond_slaves_get(INVALID_PORT_ID, slaves,
483 			RTE_MAX_ETHPORTS);
484 	TEST_ASSERT(current_slave_count < 0,
485 			"Invalid port id unexpectedly succeeded");
486 
487 	current_slave_count = rte_eth_bond_active_slaves_get(INVALID_PORT_ID,
488 			slaves, RTE_MAX_ETHPORTS);
489 	TEST_ASSERT(current_slave_count < 0,
490 			"Invalid port id unexpectedly succeeded");
491 
492 	/* Invalid slaves pointer */
493 	current_slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id,
494 			NULL, RTE_MAX_ETHPORTS);
495 	TEST_ASSERT(current_slave_count < 0,
496 			"Invalid slave array unexpectedly succeeded");
497 
498 	current_slave_count = rte_eth_bond_active_slaves_get(
499 			test_params->bonded_port_id, NULL, RTE_MAX_ETHPORTS);
500 	TEST_ASSERT(current_slave_count < 0,
501 			"Invalid slave array unexpectedly succeeded");
502 
503 	/* non bonded device*/
504 	current_slave_count = rte_eth_bond_slaves_get(
505 			test_params->slave_port_ids[0], NULL, RTE_MAX_ETHPORTS);
506 	TEST_ASSERT(current_slave_count < 0,
507 			"Invalid port id unexpectedly succeeded");
508 
509 	current_slave_count = rte_eth_bond_active_slaves_get(
510 			test_params->slave_port_ids[0],	NULL, RTE_MAX_ETHPORTS);
511 	TEST_ASSERT(current_slave_count < 0,
512 			"Invalid port id unexpectedly succeeded");
513 
514 	TEST_ASSERT_SUCCESS(test_remove_slave_from_bonded_device(),
515 			"Failed to remove slaves from bonded device");
516 
517 	return 0;
518 }
519 
520 
521 static int
522 test_add_remove_multiple_slaves_to_from_bonded_device(void)
523 {
524 	int i;
525 
526 	for (i = 0; i < TEST_MAX_NUMBER_OF_PORTS; i++)
527 		TEST_ASSERT_SUCCESS(test_add_slave_to_bonded_device(),
528 				"Failed to add slave to bonded device");
529 
530 	for (i = 0; i < TEST_MAX_NUMBER_OF_PORTS; i++)
531 		TEST_ASSERT_SUCCESS(test_remove_slave_from_bonded_device(),
532 				"Failed to remove slaves from bonded device");
533 
534 	return 0;
535 }
536 
537 static void
538 enable_bonded_slaves(void)
539 {
540 	int i;
541 
542 	for (i = 0; i < test_params->bonded_slave_count; i++) {
543 		virtual_ethdev_tx_burst_fn_set_success(test_params->slave_port_ids[i],
544 				1);
545 
546 		virtual_ethdev_simulate_link_status_interrupt(
547 				test_params->slave_port_ids[i], 1);
548 	}
549 }
550 
551 static int
552 test_start_bonded_device(void)
553 {
554 	struct rte_eth_link link_status;
555 
556 	int current_slave_count, current_bonding_mode, primary_port;
557 	uint16_t slaves[RTE_MAX_ETHPORTS];
558 	int retval;
559 
560 	/* Add slave to bonded device*/
561 	TEST_ASSERT_SUCCESS(test_add_slave_to_bonded_device(),
562 			"Failed to add slave to bonded device");
563 
564 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
565 		"Failed to start bonded pmd eth device %d.",
566 		test_params->bonded_port_id);
567 
568 	/* Change link status of virtual pmd so it will be added to the active
569 	 * slave list of the bonded device*/
570 	virtual_ethdev_simulate_link_status_interrupt(
571 			test_params->slave_port_ids[test_params->bonded_slave_count-1], 1);
572 
573 	current_slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id,
574 			slaves, RTE_MAX_ETHPORTS);
575 	TEST_ASSERT_EQUAL(current_slave_count, test_params->bonded_slave_count,
576 			"Number of slaves (%d) is not expected value (%d).",
577 			current_slave_count, test_params->bonded_slave_count);
578 
579 	current_slave_count = rte_eth_bond_active_slaves_get(
580 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS);
581 	TEST_ASSERT_EQUAL(current_slave_count, test_params->bonded_slave_count,
582 			"Number of active slaves (%d) is not expected value (%d).",
583 			current_slave_count, test_params->bonded_slave_count);
584 
585 	current_bonding_mode = rte_eth_bond_mode_get(test_params->bonded_port_id);
586 	TEST_ASSERT_EQUAL(current_bonding_mode, test_params->bonding_mode,
587 			"Bonded device mode (%d) is not expected value (%d).\n",
588 			current_bonding_mode, test_params->bonding_mode);
589 
590 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
591 	TEST_ASSERT_EQUAL(primary_port, test_params->slave_port_ids[0],
592 			"Primary port (%d) is not expected value (%d).",
593 			primary_port, test_params->slave_port_ids[0]);
594 
595 	retval = rte_eth_link_get(test_params->bonded_port_id, &link_status);
596 	TEST_ASSERT(retval >= 0,
597 			"Bonded port (%d) link get failed: %s\n",
598 			test_params->bonded_port_id, rte_strerror(-retval));
599 	TEST_ASSERT_EQUAL(link_status.link_status, 1,
600 			"Bonded port (%d) status (%d) is not expected value (%d).\n",
601 			test_params->bonded_port_id, link_status.link_status, 1);
602 
603 	return 0;
604 }
605 
606 static int
607 test_stop_bonded_device(void)
608 {
609 	int current_slave_count;
610 	uint16_t slaves[RTE_MAX_ETHPORTS];
611 
612 	struct rte_eth_link link_status;
613 	int retval;
614 
615 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
616 			"Failed to stop bonded port %u",
617 			test_params->bonded_port_id);
618 
619 	retval = rte_eth_link_get(test_params->bonded_port_id, &link_status);
620 	TEST_ASSERT(retval >= 0,
621 			"Bonded port (%d) link get failed: %s\n",
622 			test_params->bonded_port_id, rte_strerror(-retval));
623 	TEST_ASSERT_EQUAL(link_status.link_status, 0,
624 			"Bonded port (%d) status (%d) is not expected value (%d).",
625 			test_params->bonded_port_id, link_status.link_status, 0);
626 
627 	current_slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id,
628 			slaves, RTE_MAX_ETHPORTS);
629 	TEST_ASSERT_EQUAL(current_slave_count, test_params->bonded_slave_count,
630 			"Number of slaves (%d) is not expected value (%d).",
631 			current_slave_count, test_params->bonded_slave_count);
632 
633 	current_slave_count = rte_eth_bond_active_slaves_get(
634 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS);
635 	TEST_ASSERT_EQUAL(current_slave_count, 0,
636 			"Number of active slaves (%d) is not expected value (%d).",
637 			current_slave_count, 0);
638 
639 	return 0;
640 }
641 
642 static int
643 remove_slaves_and_stop_bonded_device(void)
644 {
645 	/* Clean up and remove slaves from bonded device */
646 	free_virtualpmd_tx_queue();
647 	while (test_params->bonded_slave_count > 0)
648 		TEST_ASSERT_SUCCESS(test_remove_slave_from_bonded_device(),
649 				"test_remove_slave_from_bonded_device failed");
650 
651 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
652 			"Failed to stop bonded port %u",
653 			test_params->bonded_port_id);
654 
655 	rte_eth_stats_reset(test_params->bonded_port_id);
656 	rte_eth_bond_mac_address_reset(test_params->bonded_port_id);
657 
658 	return 0;
659 }
660 
661 static int
662 test_set_bonding_mode(void)
663 {
664 	int i, bonding_mode;
665 
666 	int bonding_modes[] = { BONDING_MODE_ROUND_ROBIN,
667 							BONDING_MODE_ACTIVE_BACKUP,
668 							BONDING_MODE_BALANCE,
669 							BONDING_MODE_BROADCAST
670 							};
671 
672 	/* Test supported link bonding modes */
673 	for (i = 0; i < (int)RTE_DIM(bonding_modes);	i++) {
674 		/* Invalid port ID */
675 		TEST_ASSERT_FAIL(rte_eth_bond_mode_set(INVALID_PORT_ID,
676 				bonding_modes[i]),
677 				"Expected call to failed as invalid port (%d) specified.",
678 				INVALID_PORT_ID);
679 
680 		/* Non bonded device */
681 		TEST_ASSERT_FAIL(rte_eth_bond_mode_set(test_params->slave_port_ids[0],
682 				bonding_modes[i]),
683 				"Expected call to failed as invalid port (%d) specified.",
684 				test_params->slave_port_ids[0]);
685 
686 		TEST_ASSERT_SUCCESS(rte_eth_bond_mode_set(test_params->bonded_port_id,
687 				bonding_modes[i]),
688 				"Failed to set link bonding mode on port (%d) to (%d).",
689 				test_params->bonded_port_id, bonding_modes[i]);
690 
691 		bonding_mode = rte_eth_bond_mode_get(test_params->bonded_port_id);
692 		TEST_ASSERT_EQUAL(bonding_mode, bonding_modes[i],
693 				"Link bonding mode (%d) of port (%d) is not expected value (%d).",
694 				bonding_mode, test_params->bonded_port_id,
695 				bonding_modes[i]);
696 
697 		/* Invalid port ID */
698 		bonding_mode = rte_eth_bond_mode_get(INVALID_PORT_ID);
699 		TEST_ASSERT(bonding_mode < 0,
700 				"Expected call to failed as invalid port (%d) specified.",
701 				INVALID_PORT_ID);
702 
703 		/* Non bonded device */
704 		bonding_mode = rte_eth_bond_mode_get(test_params->slave_port_ids[0]);
705 		TEST_ASSERT(bonding_mode < 0,
706 				"Expected call to failed as invalid port (%d) specified.",
707 				test_params->slave_port_ids[0]);
708 	}
709 
710 	return remove_slaves_and_stop_bonded_device();
711 }
712 
713 static int
714 test_set_primary_slave(void)
715 {
716 	int i, j, retval;
717 	struct rte_ether_addr read_mac_addr;
718 	struct rte_ether_addr *expected_mac_addr;
719 
720 	/* Add 4 slaves to bonded device */
721 	for (i = test_params->bonded_slave_count; i < 4; i++)
722 		TEST_ASSERT_SUCCESS(test_add_slave_to_bonded_device(),
723 				"Failed to add slave to bonded device.");
724 
725 	TEST_ASSERT_SUCCESS(rte_eth_bond_mode_set(test_params->bonded_port_id,
726 			BONDING_MODE_ROUND_ROBIN),
727 			"Failed to set link bonding mode on port (%d) to (%d).",
728 			test_params->bonded_port_id, BONDING_MODE_ROUND_ROBIN);
729 
730 	/* Invalid port ID */
731 	TEST_ASSERT_FAIL(rte_eth_bond_primary_set(INVALID_PORT_ID,
732 			test_params->slave_port_ids[i]),
733 			"Expected call to failed as invalid port specified.");
734 
735 	/* Non bonded device */
736 	TEST_ASSERT_FAIL(rte_eth_bond_primary_set(test_params->slave_port_ids[i],
737 			test_params->slave_port_ids[i]),
738 			"Expected call to failed as invalid port specified.");
739 
740 	/* Set slave as primary
741 	 * Verify slave it is now primary slave
742 	 * Verify that MAC address of bonded device is that of primary slave
743 	 * Verify that MAC address of all bonded slaves are that of primary slave
744 	 */
745 	for (i = 0; i < 4; i++) {
746 		TEST_ASSERT_SUCCESS(rte_eth_bond_primary_set(test_params->bonded_port_id,
747 				test_params->slave_port_ids[i]),
748 				"Failed to set bonded port (%d) primary port to (%d)",
749 				test_params->bonded_port_id, test_params->slave_port_ids[i]);
750 
751 		retval = rte_eth_bond_primary_get(test_params->bonded_port_id);
752 		TEST_ASSERT(retval >= 0,
753 				"Failed to read primary port from bonded port (%d)\n",
754 					test_params->bonded_port_id);
755 
756 		TEST_ASSERT_EQUAL(retval, test_params->slave_port_ids[i],
757 				"Bonded port (%d) primary port (%d) not expected value (%d)\n",
758 				test_params->bonded_port_id, retval,
759 				test_params->slave_port_ids[i]);
760 
761 		/* stop/start bonded eth dev to apply new MAC */
762 		TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
763 				"Failed to stop bonded port %u",
764 				test_params->bonded_port_id);
765 
766 		TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
767 				"Failed to start bonded port %d",
768 				test_params->bonded_port_id);
769 
770 		expected_mac_addr = (struct rte_ether_addr *)&slave_mac;
771 		expected_mac_addr->addr_bytes[RTE_ETHER_ADDR_LEN-1] = i;
772 
773 		/* Check primary slave MAC */
774 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
775 				"Failed to get mac address (port %d)",
776 				test_params->slave_port_ids[i]);
777 		TEST_ASSERT_SUCCESS(memcmp(expected_mac_addr, &read_mac_addr,
778 				sizeof(read_mac_addr)),
779 				"bonded port mac address not set to that of primary port\n");
780 
781 		/* Check bonded MAC */
782 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
783 				"Failed to get mac address (port %d)",
784 				test_params->bonded_port_id);
785 		TEST_ASSERT_SUCCESS(memcmp(&read_mac_addr, &read_mac_addr,
786 				sizeof(read_mac_addr)),
787 				"bonded port mac address not set to that of primary port\n");
788 
789 		/* Check other slaves MACs */
790 		for (j = 0; j < 4; j++) {
791 			if (j != i) {
792 				TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[j],
793 						&read_mac_addr),
794 						"Failed to get mac address (port %d)",
795 						test_params->slave_port_ids[j]);
796 				TEST_ASSERT_SUCCESS(memcmp(expected_mac_addr, &read_mac_addr,
797 						sizeof(read_mac_addr)),
798 						"slave port mac address not set to that of primary "
799 						"port");
800 			}
801 		}
802 	}
803 
804 
805 	/* Test with none existent port */
806 	TEST_ASSERT_FAIL(rte_eth_bond_primary_get(test_params->bonded_port_id + 10),
807 			"read primary port from expectedly");
808 
809 	/* Test with slave port */
810 	TEST_ASSERT_FAIL(rte_eth_bond_primary_get(test_params->slave_port_ids[0]),
811 			"read primary port from expectedly\n");
812 
813 	TEST_ASSERT_SUCCESS(remove_slaves_and_stop_bonded_device(),
814 			"Failed to stop and remove slaves from bonded device");
815 
816 	/* No slaves  */
817 	TEST_ASSERT(rte_eth_bond_primary_get(test_params->bonded_port_id)  < 0,
818 			"read primary port from expectedly\n");
819 
820 	return 0;
821 }
822 
823 static int
824 test_set_explicit_bonded_mac(void)
825 {
826 	int i;
827 	struct rte_ether_addr read_mac_addr;
828 	struct rte_ether_addr *mac_addr;
829 
830 	uint8_t explicit_bonded_mac[] = { 0xDE, 0xAD, 0xBE, 0xEF, 0x00, 0x01 };
831 
832 	mac_addr = (struct rte_ether_addr *)explicit_bonded_mac;
833 
834 	/* Invalid port ID */
835 	TEST_ASSERT_FAIL(rte_eth_bond_mac_address_set(INVALID_PORT_ID, mac_addr),
836 			"Expected call to failed as invalid port specified.");
837 
838 	/* Non bonded device */
839 	TEST_ASSERT_FAIL(rte_eth_bond_mac_address_set(
840 			test_params->slave_port_ids[0],	mac_addr),
841 			"Expected call to failed as invalid port specified.");
842 
843 	/* NULL MAC address */
844 	TEST_ASSERT_FAIL(rte_eth_bond_mac_address_set(
845 			test_params->bonded_port_id, NULL),
846 			"Expected call to failed as NULL MAC specified");
847 
848 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_set(
849 			test_params->bonded_port_id, mac_addr),
850 			"Failed to set MAC address on bonded port (%d)",
851 			test_params->bonded_port_id);
852 
853 	/* Add 4 slaves to bonded device */
854 	for (i = test_params->bonded_slave_count; i < 4; i++) {
855 		TEST_ASSERT_SUCCESS(test_add_slave_to_bonded_device(),
856 				"Failed to add slave to bonded device.\n");
857 	}
858 
859 	/* Check bonded MAC */
860 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
861 			"Failed to get mac address (port %d)",
862 			test_params->bonded_port_id);
863 	TEST_ASSERT_SUCCESS(memcmp(mac_addr, &read_mac_addr, sizeof(read_mac_addr)),
864 			"bonded port mac address not set to that of primary port");
865 
866 	/* Check other slaves MACs */
867 	for (i = 0; i < 4; i++) {
868 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
869 				"Failed to get mac address (port %d)",
870 				test_params->slave_port_ids[i]);
871 		TEST_ASSERT_SUCCESS(memcmp(mac_addr, &read_mac_addr,
872 				sizeof(read_mac_addr)),
873 				"slave port mac address not set to that of primary port");
874 	}
875 
876 	/* test resetting mac address on bonded device */
877 	TEST_ASSERT_SUCCESS(
878 			rte_eth_bond_mac_address_reset(test_params->bonded_port_id),
879 			"Failed to reset MAC address on bonded port (%d)",
880 			test_params->bonded_port_id);
881 
882 	TEST_ASSERT_FAIL(
883 			rte_eth_bond_mac_address_reset(test_params->slave_port_ids[0]),
884 			"Reset MAC address on bonded port (%d) unexpectedly",
885 			test_params->slave_port_ids[1]);
886 
887 	/* test resetting mac address on bonded device with no slaves */
888 	TEST_ASSERT_SUCCESS(remove_slaves_and_stop_bonded_device(),
889 			"Failed to remove slaves and stop bonded device");
890 
891 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_reset(test_params->bonded_port_id),
892 			"Failed to reset MAC address on bonded port (%d)",
893 				test_params->bonded_port_id);
894 
895 	return 0;
896 }
897 
898 #define BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT (3)
899 
900 static int
901 test_set_bonded_port_initialization_mac_assignment(void)
902 {
903 	int i, slave_count;
904 
905 	uint16_t slaves[RTE_MAX_ETHPORTS];
906 	static int bonded_port_id = -1;
907 	static int slave_port_ids[BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT];
908 
909 	struct rte_ether_addr slave_mac_addr, bonded_mac_addr, read_mac_addr;
910 
911 	/* Initialize default values for MAC addresses */
912 	memcpy(&slave_mac_addr, slave_mac, sizeof(struct rte_ether_addr));
913 	memcpy(&bonded_mac_addr, slave_mac, sizeof(struct rte_ether_addr));
914 
915 	/*
916 	 * 1. a - Create / configure  bonded / slave ethdevs
917 	 */
918 	if (bonded_port_id == -1) {
919 		bonded_port_id = rte_eth_bond_create("net_bonding_mac_ass_test",
920 				BONDING_MODE_ACTIVE_BACKUP, rte_socket_id());
921 		TEST_ASSERT(bonded_port_id > 0, "failed to create bonded device");
922 
923 		TEST_ASSERT_SUCCESS(configure_ethdev(bonded_port_id, 0, 0),
924 					"Failed to configure bonded ethdev");
925 	}
926 
927 	if (!mac_slaves_initialized) {
928 		for (i = 0; i < BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT; i++) {
929 			char pmd_name[RTE_ETH_NAME_MAX_LEN];
930 
931 			slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN - 1] =
932 				i + 100;
933 
934 			snprintf(pmd_name, RTE_ETH_NAME_MAX_LEN,
935 				"eth_slave_%d", i);
936 
937 			slave_port_ids[i] = virtual_ethdev_create(pmd_name,
938 					&slave_mac_addr, rte_socket_id(), 1);
939 
940 			TEST_ASSERT(slave_port_ids[i] >= 0,
941 					"Failed to create slave ethdev %s",
942 					pmd_name);
943 
944 			TEST_ASSERT_SUCCESS(configure_ethdev(slave_port_ids[i], 1, 0),
945 					"Failed to configure virtual ethdev %s",
946 					pmd_name);
947 		}
948 		mac_slaves_initialized = 1;
949 	}
950 
951 
952 	/*
953 	 * 2. Add slave ethdevs to bonded device
954 	 */
955 	for (i = 0; i < BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT; i++) {
956 		TEST_ASSERT_SUCCESS(rte_eth_bond_slave_add(bonded_port_id,
957 				slave_port_ids[i]),
958 				"Failed to add slave (%d) to bonded port (%d).",
959 				slave_port_ids[i], bonded_port_id);
960 	}
961 
962 	slave_count = rte_eth_bond_slaves_get(bonded_port_id, slaves,
963 			RTE_MAX_ETHPORTS);
964 	TEST_ASSERT_EQUAL(BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT, slave_count,
965 			"Number of slaves (%d) is not as expected (%d)",
966 			slave_count, BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT);
967 
968 
969 	/*
970 	 * 3. Set explicit MAC address on bonded ethdev
971 	 */
972 	bonded_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-2] = 0xFF;
973 	bonded_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 0xAA;
974 
975 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_set(
976 			bonded_port_id, &bonded_mac_addr),
977 			"Failed to set MAC address on bonded port (%d)",
978 			bonded_port_id);
979 
980 
981 	/* 4. a - Start bonded ethdev
982 	 *    b - Enable slave devices
983 	 *    c - Verify bonded/slaves ethdev MAC addresses
984 	 */
985 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(bonded_port_id),
986 			"Failed to start bonded pmd eth device %d.",
987 			bonded_port_id);
988 
989 	for (i = 0; i < BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT; i++) {
990 		virtual_ethdev_simulate_link_status_interrupt(
991 				slave_port_ids[i], 1);
992 	}
993 
994 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(bonded_port_id, &read_mac_addr),
995 			"Failed to get mac address (port %d)",
996 			bonded_port_id);
997 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac_addr, &read_mac_addr,
998 			sizeof(read_mac_addr)),
999 			"bonded port mac address not as expected");
1000 
1001 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[0], &read_mac_addr),
1002 			"Failed to get mac address (port %d)",
1003 			slave_port_ids[0]);
1004 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac_addr, &read_mac_addr,
1005 			sizeof(read_mac_addr)),
1006 			"slave port 0 mac address not as expected");
1007 
1008 	slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 1 + 100;
1009 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[1], &read_mac_addr),
1010 			"Failed to get mac address (port %d)",
1011 			slave_port_ids[1]);
1012 	TEST_ASSERT_SUCCESS(memcmp(&slave_mac_addr, &read_mac_addr,
1013 			sizeof(read_mac_addr)),
1014 			"slave port 1 mac address not as expected");
1015 
1016 	slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 2 + 100;
1017 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[2], &read_mac_addr),
1018 			"Failed to get mac address (port %d)",
1019 			slave_port_ids[2]);
1020 	TEST_ASSERT_SUCCESS(memcmp(&slave_mac_addr, &read_mac_addr,
1021 			sizeof(read_mac_addr)),
1022 			"slave port 2 mac address not as expected");
1023 
1024 
1025 	/* 7. a - Change primary port
1026 	 *    b - Stop / Start bonded port
1027 	 *    d - Verify slave ethdev MAC addresses
1028 	 */
1029 	TEST_ASSERT_SUCCESS(rte_eth_bond_primary_set(bonded_port_id,
1030 			slave_port_ids[2]),
1031 			"failed to set primary port on bonded device.");
1032 
1033 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(bonded_port_id),
1034 			"Failed to stop bonded port %u",
1035 			bonded_port_id);
1036 
1037 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(bonded_port_id),
1038 				"Failed to start bonded pmd eth device %d.",
1039 				bonded_port_id);
1040 
1041 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(bonded_port_id, &read_mac_addr),
1042 			"Failed to get mac address (port %d)",
1043 			bonded_port_id);
1044 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac_addr, &read_mac_addr,
1045 			sizeof(read_mac_addr)),
1046 			"bonded port mac address not as expected");
1047 
1048 	slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 0 + 100;
1049 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[0], &read_mac_addr),
1050 			"Failed to get mac address (port %d)",
1051 			slave_port_ids[0]);
1052 	TEST_ASSERT_SUCCESS(memcmp(&slave_mac_addr, &read_mac_addr,
1053 			sizeof(read_mac_addr)),
1054 			"slave port 0 mac address not as expected");
1055 
1056 	slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 1 + 100;
1057 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[1], &read_mac_addr),
1058 			"Failed to get mac address (port %d)",
1059 			slave_port_ids[1]);
1060 	TEST_ASSERT_SUCCESS(memcmp(&slave_mac_addr, &read_mac_addr,
1061 			sizeof(read_mac_addr)),
1062 			"slave port 1 mac address not as expected");
1063 
1064 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[2], &read_mac_addr),
1065 			"Failed to get mac address (port %d)",
1066 			slave_port_ids[2]);
1067 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac_addr, &read_mac_addr,
1068 			sizeof(read_mac_addr)),
1069 			"slave port 2 mac address not as expected");
1070 
1071 	/* 6. a - Stop bonded ethdev
1072 	 *    b - remove slave ethdevs
1073 	 *    c - Verify slave ethdevs MACs are restored
1074 	 */
1075 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(bonded_port_id),
1076 			"Failed to stop bonded port %u",
1077 			bonded_port_id);
1078 
1079 	for (i = 0; i < BONDED_INIT_MAC_ASSIGNMENT_SLAVE_COUNT; i++) {
1080 		TEST_ASSERT_SUCCESS(rte_eth_bond_slave_remove(bonded_port_id,
1081 				slave_port_ids[i]),
1082 				"Failed to remove slave %d from bonded port (%d).",
1083 				slave_port_ids[i], bonded_port_id);
1084 	}
1085 
1086 	slave_count = rte_eth_bond_slaves_get(bonded_port_id, slaves,
1087 			RTE_MAX_ETHPORTS);
1088 
1089 	TEST_ASSERT_EQUAL(slave_count, 0,
1090 			"Number of slaves (%d) is great than expected (%d).",
1091 			slave_count, 0);
1092 
1093 	slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 0 + 100;
1094 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[0], &read_mac_addr),
1095 			"Failed to get mac address (port %d)",
1096 			slave_port_ids[0]);
1097 	TEST_ASSERT_SUCCESS(memcmp(&slave_mac_addr, &read_mac_addr,
1098 			sizeof(read_mac_addr)),
1099 			"slave port 0 mac address not as expected");
1100 
1101 	slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 1 + 100;
1102 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[1], &read_mac_addr),
1103 			"Failed to get mac address (port %d)",
1104 			slave_port_ids[1]);
1105 	TEST_ASSERT_SUCCESS(memcmp(&slave_mac_addr, &read_mac_addr,
1106 			sizeof(read_mac_addr)),
1107 			"slave port 1 mac address not as expected");
1108 
1109 	slave_mac_addr.addr_bytes[RTE_ETHER_ADDR_LEN-1] = 2 + 100;
1110 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(slave_port_ids[2], &read_mac_addr),
1111 			"Failed to get mac address (port %d)",
1112 			slave_port_ids[2]);
1113 	TEST_ASSERT_SUCCESS(memcmp(&slave_mac_addr, &read_mac_addr,
1114 			sizeof(read_mac_addr)),
1115 			"slave port 2 mac address not as expected");
1116 
1117 	return 0;
1118 }
1119 
1120 
1121 static int
1122 initialize_bonded_device_with_slaves(uint8_t bonding_mode, uint8_t bond_en_isr,
1123 		uint16_t number_of_slaves, uint8_t enable_slave)
1124 {
1125 	/* Configure bonded device */
1126 	TEST_ASSERT_SUCCESS(configure_ethdev(test_params->bonded_port_id, 0,
1127 			bond_en_isr), "Failed to configure bonding port (%d) in mode %d "
1128 			"with (%d) slaves.", test_params->bonded_port_id, bonding_mode,
1129 			number_of_slaves);
1130 
1131 	/* Add slaves to bonded device */
1132 	while (number_of_slaves > test_params->bonded_slave_count)
1133 		TEST_ASSERT_SUCCESS(test_add_slave_to_bonded_device(),
1134 				"Failed to add slave (%d to  bonding port (%d).",
1135 				test_params->bonded_slave_count - 1,
1136 				test_params->bonded_port_id);
1137 
1138 	/* Set link bonding mode  */
1139 	TEST_ASSERT_SUCCESS(rte_eth_bond_mode_set(test_params->bonded_port_id,
1140 			bonding_mode),
1141 			"Failed to set link bonding mode on port (%d) to (%d).",
1142 			test_params->bonded_port_id, bonding_mode);
1143 
1144 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
1145 		"Failed to start bonded pmd eth device %d.",
1146 		test_params->bonded_port_id);
1147 
1148 	if (enable_slave)
1149 		enable_bonded_slaves();
1150 
1151 	return 0;
1152 }
1153 
1154 static int
1155 test_adding_slave_after_bonded_device_started(void)
1156 {
1157 	int i;
1158 
1159 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1160 			BONDING_MODE_ROUND_ROBIN, 0, 4, 0),
1161 			"Failed to add slaves to bonded device");
1162 
1163 	/* Enabled slave devices */
1164 	for (i = 0; i < test_params->bonded_slave_count + 1; i++) {
1165 		virtual_ethdev_simulate_link_status_interrupt(
1166 				test_params->slave_port_ids[i], 1);
1167 	}
1168 
1169 	TEST_ASSERT_SUCCESS(rte_eth_bond_slave_add(test_params->bonded_port_id,
1170 			test_params->slave_port_ids[test_params->bonded_slave_count]),
1171 			"Failed to add slave to bonded port.\n");
1172 
1173 	rte_eth_stats_reset(
1174 			test_params->slave_port_ids[test_params->bonded_slave_count]);
1175 
1176 	test_params->bonded_slave_count++;
1177 
1178 	return remove_slaves_and_stop_bonded_device();
1179 }
1180 
1181 #define TEST_STATUS_INTERRUPT_SLAVE_COUNT	4
1182 #define TEST_LSC_WAIT_TIMEOUT_US	500000
1183 
1184 int test_lsc_interrupt_count;
1185 
1186 
1187 static int
1188 test_bonding_lsc_event_callback(uint16_t port_id __rte_unused,
1189 		enum rte_eth_event_type type  __rte_unused,
1190 		void *param __rte_unused,
1191 		void *ret_param __rte_unused)
1192 {
1193 	pthread_mutex_lock(&mutex);
1194 	test_lsc_interrupt_count++;
1195 
1196 	pthread_cond_signal(&cvar);
1197 	pthread_mutex_unlock(&mutex);
1198 
1199 	return 0;
1200 }
1201 
1202 static inline int
1203 lsc_timeout(int wait_us)
1204 {
1205 	int retval = 0;
1206 
1207 	struct timespec ts;
1208 	struct timeval tp;
1209 
1210 	gettimeofday(&tp, NULL);
1211 
1212 	/* Convert from timeval to timespec */
1213 	ts.tv_sec = tp.tv_sec;
1214 	ts.tv_nsec = tp.tv_usec * 1000;
1215 	ts.tv_nsec += wait_us * 1000;
1216 	/* Normalize tv_nsec to [0,999999999L] */
1217 	while (ts.tv_nsec > 1000000000L) {
1218 		ts.tv_nsec -= 1000000000L;
1219 		ts.tv_sec += 1;
1220 	}
1221 
1222 	pthread_mutex_lock(&mutex);
1223 	if (test_lsc_interrupt_count < 1)
1224 		retval = pthread_cond_timedwait(&cvar, &mutex, &ts);
1225 
1226 	pthread_mutex_unlock(&mutex);
1227 
1228 	if (retval == 0 && test_lsc_interrupt_count < 1)
1229 		return -1;
1230 
1231 	return retval;
1232 }
1233 
1234 static int
1235 test_status_interrupt(void)
1236 {
1237 	int slave_count;
1238 	uint16_t slaves[RTE_MAX_ETHPORTS];
1239 
1240 	/* initialized bonding device with T slaves */
1241 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1242 			BONDING_MODE_ROUND_ROBIN, 1,
1243 			TEST_STATUS_INTERRUPT_SLAVE_COUNT, 1),
1244 			"Failed to initialise bonded device");
1245 
1246 	test_lsc_interrupt_count = 0;
1247 
1248 	/* register link status change interrupt callback */
1249 	rte_eth_dev_callback_register(test_params->bonded_port_id,
1250 			RTE_ETH_EVENT_INTR_LSC, test_bonding_lsc_event_callback,
1251 			&test_params->bonded_port_id);
1252 
1253 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
1254 			slaves, RTE_MAX_ETHPORTS);
1255 
1256 	TEST_ASSERT_EQUAL(slave_count, TEST_STATUS_INTERRUPT_SLAVE_COUNT,
1257 			"Number of active slaves (%d) is not as expected (%d)",
1258 			slave_count, TEST_STATUS_INTERRUPT_SLAVE_COUNT);
1259 
1260 	/* Bring all 4 slaves link status to down and test that we have received a
1261 	 * lsc interrupts */
1262 	virtual_ethdev_simulate_link_status_interrupt(
1263 			test_params->slave_port_ids[0], 0);
1264 	virtual_ethdev_simulate_link_status_interrupt(
1265 			test_params->slave_port_ids[1], 0);
1266 	virtual_ethdev_simulate_link_status_interrupt(
1267 			test_params->slave_port_ids[2], 0);
1268 
1269 	TEST_ASSERT_EQUAL(test_lsc_interrupt_count, 0,
1270 			"Received a link status change interrupt unexpectedly");
1271 
1272 	virtual_ethdev_simulate_link_status_interrupt(
1273 			test_params->slave_port_ids[3], 0);
1274 
1275 	TEST_ASSERT(lsc_timeout(TEST_LSC_WAIT_TIMEOUT_US) == 0,
1276 			"timed out waiting for interrupt");
1277 
1278 	TEST_ASSERT(test_lsc_interrupt_count > 0,
1279 			"Did not receive link status change interrupt");
1280 
1281 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
1282 			slaves, RTE_MAX_ETHPORTS);
1283 
1284 	TEST_ASSERT_EQUAL(slave_count, 0,
1285 			"Number of active slaves (%d) is not as expected (%d)",
1286 			slave_count, 0);
1287 
1288 	/* bring one slave port up so link status will change */
1289 	test_lsc_interrupt_count = 0;
1290 
1291 	virtual_ethdev_simulate_link_status_interrupt(
1292 			test_params->slave_port_ids[0], 1);
1293 
1294 	TEST_ASSERT(lsc_timeout(TEST_LSC_WAIT_TIMEOUT_US) == 0,
1295 			"timed out waiting for interrupt");
1296 
1297 	/* test that we have received another lsc interrupt */
1298 	TEST_ASSERT(test_lsc_interrupt_count > 0,
1299 			"Did not receive link status change interrupt");
1300 
1301 	/* Verify that calling the same slave lsc interrupt doesn't cause another
1302 	 * lsc interrupt from bonded device */
1303 	test_lsc_interrupt_count = 0;
1304 
1305 	virtual_ethdev_simulate_link_status_interrupt(
1306 			test_params->slave_port_ids[0], 1);
1307 
1308 	TEST_ASSERT(lsc_timeout(TEST_LSC_WAIT_TIMEOUT_US) != 0,
1309 			"received unexpected interrupt");
1310 
1311 	TEST_ASSERT_EQUAL(test_lsc_interrupt_count, 0,
1312 			"Did not receive link status change interrupt");
1313 
1314 
1315 	/* unregister lsc callback before exiting */
1316 	rte_eth_dev_callback_unregister(test_params->bonded_port_id,
1317 				RTE_ETH_EVENT_INTR_LSC, test_bonding_lsc_event_callback,
1318 				&test_params->bonded_port_id);
1319 
1320 	/* Clean up and remove slaves from bonded device */
1321 	return remove_slaves_and_stop_bonded_device();
1322 }
1323 
1324 static int
1325 generate_test_burst(struct rte_mbuf **pkts_burst, uint16_t burst_size,
1326 		uint8_t vlan, uint8_t ipv4, uint8_t toggle_dst_mac,
1327 		uint8_t toggle_ip_addr, uint16_t toggle_udp_port)
1328 {
1329 	uint16_t pktlen, generated_burst_size, ether_type;
1330 	void *ip_hdr;
1331 
1332 	if (ipv4)
1333 		ether_type = RTE_ETHER_TYPE_IPV4;
1334 	else
1335 		ether_type = RTE_ETHER_TYPE_IPV6;
1336 
1337 	if (toggle_dst_mac)
1338 		initialize_eth_header(test_params->pkt_eth_hdr,
1339 				(struct rte_ether_addr *)src_mac,
1340 				(struct rte_ether_addr *)dst_mac_1,
1341 				ether_type, vlan, vlan_id);
1342 	else
1343 		initialize_eth_header(test_params->pkt_eth_hdr,
1344 				(struct rte_ether_addr *)src_mac,
1345 				(struct rte_ether_addr *)dst_mac_0,
1346 				ether_type, vlan, vlan_id);
1347 
1348 
1349 	if (toggle_udp_port)
1350 		pktlen = initialize_udp_header(test_params->pkt_udp_hdr, src_port,
1351 				dst_port_1, 64);
1352 	else
1353 		pktlen = initialize_udp_header(test_params->pkt_udp_hdr, src_port,
1354 				dst_port_0, 64);
1355 
1356 	if (ipv4) {
1357 		if (toggle_ip_addr)
1358 			pktlen = initialize_ipv4_header(test_params->pkt_ipv4_hdr, src_addr,
1359 					dst_addr_1, pktlen);
1360 		else
1361 			pktlen = initialize_ipv4_header(test_params->pkt_ipv4_hdr, src_addr,
1362 					dst_addr_0, pktlen);
1363 
1364 		ip_hdr = test_params->pkt_ipv4_hdr;
1365 	} else {
1366 		if (toggle_ip_addr)
1367 			pktlen = initialize_ipv6_header(test_params->pkt_ipv6_hdr,
1368 					(uint8_t *)src_ipv6_addr, (uint8_t *)dst_ipv6_addr_1,
1369 					pktlen);
1370 		else
1371 			pktlen = initialize_ipv6_header(test_params->pkt_ipv6_hdr,
1372 					(uint8_t *)src_ipv6_addr, (uint8_t *)dst_ipv6_addr_0,
1373 					pktlen);
1374 
1375 		ip_hdr = test_params->pkt_ipv6_hdr;
1376 	}
1377 
1378 	/* Generate burst of packets to transmit */
1379 	generated_burst_size = generate_packet_burst(test_params->mbuf_pool,
1380 			pkts_burst,	test_params->pkt_eth_hdr, vlan, ip_hdr, ipv4,
1381 			test_params->pkt_udp_hdr, burst_size, PACKET_BURST_GEN_PKT_LEN_128,
1382 			1);
1383 	TEST_ASSERT_EQUAL(generated_burst_size, burst_size,
1384 			"Failed to generate packet burst");
1385 
1386 	return generated_burst_size;
1387 }
1388 
1389 /** Round Robin Mode Tests */
1390 
1391 static int
1392 test_roundrobin_tx_burst(void)
1393 {
1394 	int i, burst_size;
1395 	struct rte_mbuf *pkt_burst[MAX_PKT_BURST];
1396 	struct rte_eth_stats port_stats;
1397 
1398 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1399 			BONDING_MODE_ROUND_ROBIN, 0, 2, 1),
1400 			"Failed to initialise bonded device");
1401 
1402 	burst_size = 20 * test_params->bonded_slave_count;
1403 
1404 	TEST_ASSERT(burst_size <= MAX_PKT_BURST,
1405 			"Burst size specified is greater than supported.");
1406 
1407 	/* Generate test bursts of packets to transmit */
1408 	TEST_ASSERT_EQUAL(generate_test_burst(pkt_burst, burst_size, 0, 1, 0, 0, 0),
1409 			burst_size, "failed to generate test burst");
1410 
1411 	/* Send burst on bonded port */
1412 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
1413 			test_params->bonded_port_id, 0, pkt_burst, burst_size), burst_size,
1414 			"tx burst failed");
1415 
1416 	/* Verify bonded port tx stats */
1417 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
1418 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
1419 			"Bonded Port (%d) opackets value (%u) not as expected (%d)\n",
1420 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
1421 			burst_size);
1422 
1423 	/* Verify slave ports tx stats */
1424 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1425 		rte_eth_stats_get(test_params->slave_port_ids[i], &port_stats);
1426 		TEST_ASSERT_EQUAL(port_stats.opackets,
1427 				(uint64_t)burst_size / test_params->bonded_slave_count,
1428 				"Slave Port (%d) opackets value (%u) not as expected (%d)\n",
1429 				test_params->bonded_port_id, (unsigned int)port_stats.opackets,
1430 				burst_size / test_params->bonded_slave_count);
1431 	}
1432 
1433 	/* Put all slaves down and try and transmit */
1434 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1435 		virtual_ethdev_simulate_link_status_interrupt(
1436 				test_params->slave_port_ids[i], 0);
1437 	}
1438 
1439 	/* Send burst on bonded port */
1440 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(test_params->bonded_port_id, 0,
1441 			pkt_burst, burst_size), 0,
1442 			"tx burst return unexpected value");
1443 
1444 	/* Clean up and remove slaves from bonded device */
1445 	return remove_slaves_and_stop_bonded_device();
1446 }
1447 
1448 static int
1449 verify_mbufs_ref_count(struct rte_mbuf **mbufs, int nb_mbufs, int val)
1450 {
1451 	int i, refcnt;
1452 
1453 	for (i = 0; i < nb_mbufs; i++) {
1454 		refcnt = rte_mbuf_refcnt_read(mbufs[i]);
1455 		TEST_ASSERT_EQUAL(refcnt, val,
1456 			"mbuf ref count (%d)is not the expected value (%d)",
1457 			refcnt, val);
1458 	}
1459 	return 0;
1460 }
1461 
1462 static void
1463 free_mbufs(struct rte_mbuf **mbufs, int nb_mbufs)
1464 {
1465 	int i;
1466 
1467 	for (i = 0; i < nb_mbufs; i++)
1468 		rte_pktmbuf_free(mbufs[i]);
1469 }
1470 
1471 #define TEST_RR_SLAVE_TX_FAIL_SLAVE_COUNT		(2)
1472 #define TEST_RR_SLAVE_TX_FAIL_BURST_SIZE		(64)
1473 #define TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT		(22)
1474 #define TEST_RR_SLAVE_TX_FAIL_FAILING_SLAVE_IDX	(1)
1475 
1476 static int
1477 test_roundrobin_tx_burst_slave_tx_fail(void)
1478 {
1479 	struct rte_mbuf *pkt_burst[MAX_PKT_BURST];
1480 	struct rte_mbuf *expected_tx_fail_pkts[MAX_PKT_BURST];
1481 
1482 	struct rte_eth_stats port_stats;
1483 
1484 	int i, first_fail_idx, tx_count;
1485 
1486 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1487 			BONDING_MODE_ROUND_ROBIN, 0,
1488 			TEST_RR_SLAVE_TX_FAIL_SLAVE_COUNT, 1),
1489 			"Failed to initialise bonded device");
1490 
1491 	/* Generate test bursts of packets to transmit */
1492 	TEST_ASSERT_EQUAL(generate_test_burst(pkt_burst,
1493 			TEST_RR_SLAVE_TX_FAIL_BURST_SIZE, 0, 1, 0, 0, 0),
1494 			TEST_RR_SLAVE_TX_FAIL_BURST_SIZE,
1495 			"Failed to generate test packet burst");
1496 
1497 	/* Copy references to packets which we expect not to be transmitted */
1498 	first_fail_idx = (TEST_RR_SLAVE_TX_FAIL_BURST_SIZE -
1499 			(TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT *
1500 			TEST_RR_SLAVE_TX_FAIL_SLAVE_COUNT)) +
1501 			TEST_RR_SLAVE_TX_FAIL_FAILING_SLAVE_IDX;
1502 
1503 	for (i = 0; i < TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT; i++) {
1504 		expected_tx_fail_pkts[i] = pkt_burst[first_fail_idx +
1505 				(i * TEST_RR_SLAVE_TX_FAIL_SLAVE_COUNT)];
1506 	}
1507 
1508 	/* Set virtual slave to only fail transmission of
1509 	 * TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT packets in burst */
1510 	virtual_ethdev_tx_burst_fn_set_success(
1511 			test_params->slave_port_ids[TEST_RR_SLAVE_TX_FAIL_FAILING_SLAVE_IDX],
1512 			0);
1513 
1514 	virtual_ethdev_tx_burst_fn_set_tx_pkt_fail_count(
1515 			test_params->slave_port_ids[TEST_RR_SLAVE_TX_FAIL_FAILING_SLAVE_IDX],
1516 			TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT);
1517 
1518 	tx_count = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkt_burst,
1519 			TEST_RR_SLAVE_TX_FAIL_BURST_SIZE);
1520 
1521 	TEST_ASSERT_EQUAL(tx_count, TEST_RR_SLAVE_TX_FAIL_BURST_SIZE -
1522 			TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT,
1523 			"Transmitted (%d) an unexpected (%d) number of packets", tx_count,
1524 			TEST_RR_SLAVE_TX_FAIL_BURST_SIZE -
1525 			TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT);
1526 
1527 	/* Verify that failed packet are expected failed packets */
1528 	for (i = 0; i < TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT; i++) {
1529 		TEST_ASSERT_EQUAL(expected_tx_fail_pkts[i], pkt_burst[i + tx_count],
1530 				"expected mbuf (%d) pointer %p not expected pointer %p",
1531 				i, expected_tx_fail_pkts[i], pkt_burst[i + tx_count]);
1532 	}
1533 
1534 	/* Verify bonded port tx stats */
1535 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
1536 
1537 	TEST_ASSERT_EQUAL(port_stats.opackets,
1538 			(uint64_t)TEST_RR_SLAVE_TX_FAIL_BURST_SIZE -
1539 			TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT,
1540 			"Bonded Port (%d) opackets value (%u) not as expected (%d)",
1541 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
1542 			TEST_RR_SLAVE_TX_FAIL_BURST_SIZE -
1543 			TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT);
1544 
1545 	/* Verify slave ports tx stats */
1546 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1547 		int slave_expected_tx_count;
1548 
1549 		rte_eth_stats_get(test_params->slave_port_ids[i], &port_stats);
1550 
1551 		slave_expected_tx_count = TEST_RR_SLAVE_TX_FAIL_BURST_SIZE /
1552 				test_params->bonded_slave_count;
1553 
1554 		if (i == TEST_RR_SLAVE_TX_FAIL_FAILING_SLAVE_IDX)
1555 			slave_expected_tx_count = slave_expected_tx_count -
1556 					TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT;
1557 
1558 		TEST_ASSERT_EQUAL(port_stats.opackets,
1559 				(uint64_t)slave_expected_tx_count,
1560 				"Slave Port (%d) opackets value (%u) not as expected (%d)",
1561 				test_params->slave_port_ids[i],
1562 				(unsigned int)port_stats.opackets, slave_expected_tx_count);
1563 	}
1564 
1565 	/* Verify that all mbufs have a ref value of zero */
1566 	TEST_ASSERT_SUCCESS(verify_mbufs_ref_count(&pkt_burst[tx_count],
1567 			TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT, 1),
1568 			"mbufs refcnts not as expected");
1569 	free_mbufs(&pkt_burst[tx_count], TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT);
1570 
1571 	/* Clean up and remove slaves from bonded device */
1572 	return remove_slaves_and_stop_bonded_device();
1573 }
1574 
1575 static int
1576 test_roundrobin_rx_burst_on_single_slave(void)
1577 {
1578 	struct rte_mbuf *gen_pkt_burst[MAX_PKT_BURST] = { NULL };
1579 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
1580 
1581 	struct rte_eth_stats port_stats;
1582 
1583 	int i, j, burst_size = 25;
1584 
1585 	/* Initialize bonded device with 4 slaves in round robin mode */
1586 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1587 			BONDING_MODE_ROUND_ROBIN, 0, 4, 1),
1588 			"Failed to initialize bonded device with slaves");
1589 
1590 	/* Generate test bursts of packets to transmit */
1591 	TEST_ASSERT_EQUAL(generate_test_burst(
1592 			gen_pkt_burst, burst_size, 0, 1, 0, 0, 0), burst_size,
1593 			"burst generation failed");
1594 
1595 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1596 		/* Add rx data to slave */
1597 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
1598 				&gen_pkt_burst[0], burst_size);
1599 
1600 		/* Call rx burst on bonded device */
1601 		/* Send burst on bonded port */
1602 		TEST_ASSERT_EQUAL(rte_eth_rx_burst(
1603 				test_params->bonded_port_id, 0, rx_pkt_burst,
1604 				MAX_PKT_BURST), burst_size,
1605 				"round-robin rx burst failed");
1606 
1607 		/* Verify bonded device rx count */
1608 		rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
1609 		TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
1610 				"Bonded Port (%d) ipackets value (%u) not as expected (%d)",
1611 				test_params->bonded_port_id,
1612 				(unsigned int)port_stats.ipackets, burst_size);
1613 
1614 
1615 
1616 		/* Verify bonded slave devices rx count */
1617 		/* Verify slave ports tx stats */
1618 		for (j = 0; j < test_params->bonded_slave_count; j++) {
1619 			rte_eth_stats_get(test_params->slave_port_ids[j], &port_stats);
1620 
1621 			if (i == j) {
1622 				TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
1623 						"Slave Port (%d) ipackets value (%u) not as expected"
1624 						" (%d)", test_params->slave_port_ids[i],
1625 						(unsigned int)port_stats.ipackets, burst_size);
1626 			} else {
1627 				TEST_ASSERT_EQUAL(port_stats.ipackets, 0,
1628 						"Slave Port (%d) ipackets value (%u) not as expected"
1629 						" (%d)", test_params->slave_port_ids[i],
1630 						(unsigned int)port_stats.ipackets, 0);
1631 			}
1632 
1633 			/* Reset bonded slaves stats */
1634 			rte_eth_stats_reset(test_params->slave_port_ids[j]);
1635 		}
1636 		/* reset bonded device stats */
1637 		rte_eth_stats_reset(test_params->bonded_port_id);
1638 	}
1639 
1640 	/* free mbufs */
1641 	for (i = 0; i < MAX_PKT_BURST; i++) {
1642 		rte_pktmbuf_free(rx_pkt_burst[i]);
1643 	}
1644 
1645 
1646 	/* Clean up and remove slaves from bonded device */
1647 	return remove_slaves_and_stop_bonded_device();
1648 }
1649 
1650 #define TEST_ROUNDROBIN_TX_BURST_SLAVE_COUNT (3)
1651 
1652 static int
1653 test_roundrobin_rx_burst_on_multiple_slaves(void)
1654 {
1655 	struct rte_mbuf *gen_pkt_burst[TEST_ROUNDROBIN_TX_BURST_SLAVE_COUNT][MAX_PKT_BURST];
1656 
1657 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
1658 	struct rte_eth_stats port_stats;
1659 
1660 	int burst_size[TEST_ROUNDROBIN_TX_BURST_SLAVE_COUNT] = { 15, 13, 36 };
1661 	int i, nb_rx;
1662 
1663 	/* Initialize bonded device with 4 slaves in round robin mode */
1664 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1665 			BONDING_MODE_ROUND_ROBIN, 0, 4, 1),
1666 			"Failed to initialize bonded device with slaves");
1667 
1668 	/* Generate test bursts of packets to transmit */
1669 	for (i = 0; i < TEST_ROUNDROBIN_TX_BURST_SLAVE_COUNT; i++) {
1670 		TEST_ASSERT_EQUAL(generate_test_burst(
1671 				&gen_pkt_burst[i][0], burst_size[i], 0, 1, 0, 0, 0),
1672 				burst_size[i], "burst generation failed");
1673 	}
1674 
1675 	/* Add rx data to slaves */
1676 	for (i = 0; i < TEST_ROUNDROBIN_TX_BURST_SLAVE_COUNT; i++) {
1677 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
1678 				&gen_pkt_burst[i][0], burst_size[i]);
1679 	}
1680 
1681 	/* Call rx burst on bonded device */
1682 	/* Send burst on bonded port */
1683 	nb_rx = rte_eth_rx_burst(test_params->bonded_port_id, 0, rx_pkt_burst,
1684 			MAX_PKT_BURST);
1685 	TEST_ASSERT_EQUAL(nb_rx , burst_size[0] + burst_size[1] + burst_size[2],
1686 			"round-robin rx burst failed (%d != %d)\n", nb_rx,
1687 			burst_size[0] + burst_size[1] + burst_size[2]);
1688 
1689 	/* Verify bonded device rx count */
1690 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
1691 	TEST_ASSERT_EQUAL(port_stats.ipackets,
1692 			(uint64_t)(burst_size[0] + burst_size[1] + burst_size[2]),
1693 			"Bonded Port (%d) ipackets value (%u) not as expected (%d)",
1694 			test_params->bonded_port_id, (unsigned int)port_stats.ipackets,
1695 			burst_size[0] + burst_size[1] + burst_size[2]);
1696 
1697 	/* Verify bonded slave devices rx counts */
1698 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
1699 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[0],
1700 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
1701 			test_params->slave_port_ids[0],
1702 			(unsigned int)port_stats.ipackets, burst_size[0]);
1703 
1704 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
1705 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[1],
1706 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
1707 			test_params->slave_port_ids[1], (unsigned int)port_stats.ipackets,
1708 			burst_size[1]);
1709 
1710 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
1711 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[2],
1712 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
1713 				test_params->slave_port_ids[2],
1714 				(unsigned int)port_stats.ipackets, burst_size[2]);
1715 
1716 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
1717 	TEST_ASSERT_EQUAL(port_stats.ipackets, 0,
1718 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
1719 			test_params->slave_port_ids[3],
1720 			(unsigned int)port_stats.ipackets, 0);
1721 
1722 	/* free mbufs */
1723 	for (i = 0; i < MAX_PKT_BURST; i++) {
1724 		rte_pktmbuf_free(rx_pkt_burst[i]);
1725 	}
1726 
1727 	/* Clean up and remove slaves from bonded device */
1728 	return remove_slaves_and_stop_bonded_device();
1729 }
1730 
1731 static int
1732 test_roundrobin_verify_mac_assignment(void)
1733 {
1734 	struct rte_ether_addr read_mac_addr;
1735 	struct rte_ether_addr expected_mac_addr_0, expected_mac_addr_2;
1736 
1737 	int i;
1738 
1739 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &expected_mac_addr_0),
1740 			"Failed to get mac address (port %d)",
1741 			test_params->slave_port_ids[0]);
1742 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[2], &expected_mac_addr_2),
1743 			"Failed to get mac address (port %d)",
1744 			test_params->slave_port_ids[2]);
1745 
1746 	/* Initialize bonded device with 4 slaves in round robin mode */
1747 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1748 				BONDING_MODE_ROUND_ROBIN, 0, 4, 1),
1749 				"Failed to initialize bonded device with slaves");
1750 
1751 	/* Verify that all MACs are the same as first slave added to bonded dev */
1752 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1753 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
1754 				"Failed to get mac address (port %d)",
1755 				test_params->slave_port_ids[i]);
1756 		TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
1757 				sizeof(read_mac_addr)),
1758 				"slave port (%d) mac address not set to that of primary port",
1759 				test_params->slave_port_ids[i]);
1760 	}
1761 
1762 	/* change primary and verify that MAC addresses haven't changed */
1763 	TEST_ASSERT_SUCCESS(rte_eth_bond_primary_set(test_params->bonded_port_id,
1764 			test_params->slave_port_ids[2]),
1765 			"Failed to set bonded port (%d) primary port to (%d)",
1766 			test_params->bonded_port_id, test_params->slave_port_ids[i]);
1767 
1768 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1769 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
1770 				"Failed to get mac address (port %d)",
1771 				test_params->slave_port_ids[i]);
1772 		TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
1773 				sizeof(read_mac_addr)),
1774 				"slave port (%d) mac address has changed to that of primary"
1775 				" port without stop/start toggle of bonded device",
1776 				test_params->slave_port_ids[i]);
1777 	}
1778 
1779 	/* stop / start bonded device and verify that primary MAC address is
1780 	 * propagate to bonded device and slaves */
1781 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
1782 			"Failed to stop bonded port %u",
1783 			test_params->bonded_port_id);
1784 
1785 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
1786 			"Failed to start bonded device");
1787 
1788 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
1789 			"Failed to get mac address (port %d)",
1790 			test_params->bonded_port_id);
1791 	TEST_ASSERT_SUCCESS(
1792 			memcmp(&expected_mac_addr_2, &read_mac_addr, sizeof(read_mac_addr)),
1793 			"bonded port (%d) mac address not set to that of new primary port",
1794 			test_params->slave_port_ids[i]);
1795 
1796 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1797 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
1798 				"Failed to get mac address (port %d)",
1799 				test_params->slave_port_ids[i]);
1800 		TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_2, &read_mac_addr,
1801 				sizeof(read_mac_addr)),
1802 				"slave port (%d) mac address not set to that of new primary"
1803 				" port", test_params->slave_port_ids[i]);
1804 	}
1805 
1806 	/* Set explicit MAC address */
1807 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_set(
1808 			test_params->bonded_port_id,
1809 			(struct rte_ether_addr *)bonded_mac),
1810 			"Failed to set MAC");
1811 
1812 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
1813 			"Failed to get mac address (port %d)",
1814 			test_params->bonded_port_id);
1815 	TEST_ASSERT_SUCCESS(memcmp(bonded_mac, &read_mac_addr,
1816 			sizeof(read_mac_addr)),
1817 			"bonded port (%d) mac address not set to that of new primary port",
1818 				test_params->slave_port_ids[i]);
1819 
1820 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1821 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
1822 				"Failed to get mac address (port %d)",
1823 				test_params->slave_port_ids[i]);
1824 		TEST_ASSERT_SUCCESS(memcmp(bonded_mac, &read_mac_addr,
1825 				sizeof(read_mac_addr)), "slave port (%d) mac address not set to"
1826 				" that of new primary port\n", test_params->slave_port_ids[i]);
1827 	}
1828 
1829 	/* Clean up and remove slaves from bonded device */
1830 	return remove_slaves_and_stop_bonded_device();
1831 }
1832 
1833 static int
1834 test_roundrobin_verify_promiscuous_enable_disable(void)
1835 {
1836 	int i, promiscuous_en;
1837 	int ret;
1838 
1839 	/* Initialize bonded device with 4 slaves in round robin mode */
1840 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1841 			BONDING_MODE_ROUND_ROBIN, 0, 4, 1),
1842 			"Failed to initialize bonded device with slaves");
1843 
1844 	ret = rte_eth_promiscuous_enable(test_params->bonded_port_id);
1845 	TEST_ASSERT_SUCCESS(ret,
1846 		"Failed to enable promiscuous mode for port %d: %s",
1847 		test_params->bonded_port_id, rte_strerror(-ret));
1848 
1849 	promiscuous_en = rte_eth_promiscuous_get(test_params->bonded_port_id);
1850 	TEST_ASSERT_EQUAL(promiscuous_en, 1,
1851 			"Port (%d) promiscuous mode not enabled",
1852 			test_params->bonded_port_id);
1853 
1854 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1855 		promiscuous_en = rte_eth_promiscuous_get(
1856 				test_params->slave_port_ids[i]);
1857 		TEST_ASSERT_EQUAL(promiscuous_en, 1,
1858 				"slave port (%d) promiscuous mode not enabled",
1859 				test_params->slave_port_ids[i]);
1860 	}
1861 
1862 	ret = rte_eth_promiscuous_disable(test_params->bonded_port_id);
1863 	TEST_ASSERT_SUCCESS(ret,
1864 		"Failed to disable promiscuous mode for port %d: %s",
1865 		test_params->bonded_port_id, rte_strerror(-ret));
1866 
1867 	promiscuous_en = rte_eth_promiscuous_get(test_params->bonded_port_id);
1868 	TEST_ASSERT_EQUAL(promiscuous_en, 0,
1869 			"Port (%d) promiscuous mode not disabled\n",
1870 			test_params->bonded_port_id);
1871 
1872 	for (i = 0; i < test_params->bonded_slave_count; i++) {
1873 		promiscuous_en = rte_eth_promiscuous_get(
1874 				test_params->slave_port_ids[i]);
1875 		TEST_ASSERT_EQUAL(promiscuous_en, 0,
1876 				"Port (%d) promiscuous mode not disabled\n",
1877 				test_params->slave_port_ids[i]);
1878 	}
1879 
1880 	/* Clean up and remove slaves from bonded device */
1881 	return remove_slaves_and_stop_bonded_device();
1882 }
1883 
1884 #define TEST_RR_LINK_STATUS_SLAVE_COUNT (4)
1885 #define TEST_RR_LINK_STATUS_EXPECTED_ACTIVE_SLAVE_COUNT (2)
1886 
1887 static int
1888 test_roundrobin_verify_slave_link_status_change_behaviour(void)
1889 {
1890 	struct rte_mbuf *tx_pkt_burst[MAX_PKT_BURST] = { NULL };
1891 	struct rte_mbuf *gen_pkt_burst[TEST_RR_LINK_STATUS_SLAVE_COUNT][MAX_PKT_BURST];
1892 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
1893 
1894 	struct rte_eth_stats port_stats;
1895 	uint16_t slaves[RTE_MAX_ETHPORTS];
1896 
1897 	int i, burst_size, slave_count;
1898 
1899 	/* NULL all pointers in array to simplify cleanup */
1900 	memset(gen_pkt_burst, 0, sizeof(gen_pkt_burst));
1901 
1902 	/* Initialize bonded device with TEST_RR_LINK_STATUS_SLAVE_COUNT slaves
1903 	 * in round robin mode */
1904 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
1905 			BONDING_MODE_ROUND_ROBIN, 0, TEST_RR_LINK_STATUS_SLAVE_COUNT, 1),
1906 			"Failed to initialize bonded device with slaves");
1907 
1908 	/* Verify Current Slaves Count /Active Slave Count is */
1909 	slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id, slaves,
1910 			RTE_MAX_ETHPORTS);
1911 	TEST_ASSERT_EQUAL(slave_count, TEST_RR_LINK_STATUS_SLAVE_COUNT,
1912 			"Number of slaves (%d) is not as expected (%d).",
1913 			slave_count, TEST_RR_LINK_STATUS_SLAVE_COUNT);
1914 
1915 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
1916 			slaves, RTE_MAX_ETHPORTS);
1917 	TEST_ASSERT_EQUAL(slave_count, TEST_RR_LINK_STATUS_SLAVE_COUNT,
1918 			"Number of active slaves (%d) is not as expected (%d).",
1919 			slave_count, TEST_RR_LINK_STATUS_SLAVE_COUNT);
1920 
1921 	/* Set 2 slaves eth_devs link status to down */
1922 	virtual_ethdev_simulate_link_status_interrupt(
1923 			test_params->slave_port_ids[1], 0);
1924 	virtual_ethdev_simulate_link_status_interrupt(
1925 			test_params->slave_port_ids[3], 0);
1926 
1927 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
1928 			slaves, RTE_MAX_ETHPORTS);
1929 	TEST_ASSERT_EQUAL(slave_count,
1930 			TEST_RR_LINK_STATUS_EXPECTED_ACTIVE_SLAVE_COUNT,
1931 			"Number of active slaves (%d) is not as expected (%d).\n",
1932 			slave_count, TEST_RR_LINK_STATUS_EXPECTED_ACTIVE_SLAVE_COUNT);
1933 
1934 	burst_size = 20;
1935 
1936 	/* Verify that pkts are not sent on slaves with link status down:
1937 	 *
1938 	 * 1. Generate test burst of traffic
1939 	 * 2. Transmit burst on bonded eth_dev
1940 	 * 3. Verify stats for bonded eth_dev (opackets = burst_size)
1941 	 * 4. Verify stats for slave eth_devs (s0 = 10, s1 = 0, s2 = 10, s3 = 0)
1942 	 */
1943 	TEST_ASSERT_EQUAL(
1944 			generate_test_burst(tx_pkt_burst, burst_size, 0, 1, 0, 0, 0),
1945 			burst_size, "generate_test_burst failed");
1946 
1947 	rte_eth_stats_reset(test_params->bonded_port_id);
1948 
1949 
1950 	TEST_ASSERT_EQUAL(
1951 			rte_eth_tx_burst(test_params->bonded_port_id, 0, tx_pkt_burst,
1952 			burst_size), burst_size, "rte_eth_tx_burst failed");
1953 
1954 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
1955 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
1956 			"Port (%d) opackets stats (%d) not expected (%d) value",
1957 			test_params->bonded_port_id, (int)port_stats.opackets,
1958 			burst_size);
1959 
1960 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
1961 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)10,
1962 			"Port (%d) opackets stats (%d) not expected (%d) value",
1963 			test_params->slave_port_ids[0], (int)port_stats.opackets, 10);
1964 
1965 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
1966 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)0,
1967 			"Port (%d) opackets stats (%d) not expected (%d) value",
1968 			test_params->slave_port_ids[1], (int)port_stats.opackets, 0);
1969 
1970 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
1971 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)10,
1972 			"Port (%d) opackets stats (%d) not expected (%d) value",
1973 			test_params->slave_port_ids[2], (int)port_stats.opackets, 10);
1974 
1975 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
1976 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)0,
1977 			"Port (%d) opackets stats (%d) not expected (%d) value",
1978 			test_params->slave_port_ids[3], (int)port_stats.opackets, 0);
1979 
1980 	/* Verify that pkts are not sent on slaves with link status down:
1981 	 *
1982 	 * 1. Generate test bursts of traffic
1983 	 * 2. Add bursts on to virtual eth_devs
1984 	 * 3. Rx burst on bonded eth_dev, expected (burst_ size *
1985 	 *    TEST_RR_LINK_STATUS_EXPECTED_ACTIVE_SLAVE_COUNT) received
1986 	 * 4. Verify stats for bonded eth_dev
1987 	 * 6. Verify stats for slave eth_devs (s0 = 10, s1 = 0, s2 = 10, s3 = 0)
1988 	 */
1989 	for (i = 0; i < TEST_RR_LINK_STATUS_SLAVE_COUNT; i++) {
1990 		TEST_ASSERT_EQUAL(generate_test_burst(
1991 				&gen_pkt_burst[i][0], burst_size, 0, 1, 0, 0, 0),
1992 				burst_size, "failed to generate packet burst");
1993 
1994 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
1995 				&gen_pkt_burst[i][0], burst_size);
1996 	}
1997 
1998 	TEST_ASSERT_EQUAL(rte_eth_rx_burst(
1999 			test_params->bonded_port_id, 0, rx_pkt_burst, MAX_PKT_BURST),
2000 			burst_size + burst_size,
2001 			"rte_eth_rx_burst failed");
2002 
2003 	/* Verify bonded device rx count */
2004 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
2005 	TEST_ASSERT_EQUAL(port_stats.ipackets , (uint64_t)(burst_size + burst_size),
2006 			"(%d) port_stats.ipackets not as expected\n",
2007 			test_params->bonded_port_id);
2008 
2009 	/* free mbufs */
2010 	for (i = 0; i < MAX_PKT_BURST; i++) {
2011 		rte_pktmbuf_free(rx_pkt_burst[i]);
2012 	}
2013 
2014 	/* Clean up and remove slaves from bonded device */
2015 	return remove_slaves_and_stop_bonded_device();
2016 }
2017 
2018 #define TEST_RR_POLLING_LINK_STATUS_SLAVE_COUNT (2)
2019 
2020 uint8_t polling_slave_mac[] = {0xDE, 0xAD, 0xBE, 0xEF, 0x00, 0x00 };
2021 
2022 
2023 int polling_test_slaves[TEST_RR_POLLING_LINK_STATUS_SLAVE_COUNT] = { -1, -1 };
2024 
2025 static int
2026 test_roundrobin_verfiy_polling_slave_link_status_change(void)
2027 {
2028 	struct rte_ether_addr *mac_addr =
2029 		(struct rte_ether_addr *)polling_slave_mac;
2030 	char slave_name[RTE_ETH_NAME_MAX_LEN];
2031 
2032 	int i;
2033 
2034 	for (i = 0; i < TEST_RR_POLLING_LINK_STATUS_SLAVE_COUNT; i++) {
2035 		/* Generate slave name / MAC address */
2036 		snprintf(slave_name, RTE_ETH_NAME_MAX_LEN, "eth_virt_poll_%d", i);
2037 		mac_addr->addr_bytes[RTE_ETHER_ADDR_LEN-1] = i;
2038 
2039 		/* Create slave devices with no ISR Support */
2040 		if (polling_test_slaves[i] == -1) {
2041 			polling_test_slaves[i] = virtual_ethdev_create(slave_name, mac_addr,
2042 					rte_socket_id(), 0);
2043 			TEST_ASSERT(polling_test_slaves[i] >= 0,
2044 					"Failed to create virtual virtual ethdev %s\n", slave_name);
2045 
2046 			/* Configure slave */
2047 			TEST_ASSERT_SUCCESS(configure_ethdev(polling_test_slaves[i], 0, 0),
2048 					"Failed to configure virtual ethdev %s(%d)", slave_name,
2049 					polling_test_slaves[i]);
2050 		}
2051 
2052 		/* Add slave to bonded device */
2053 		TEST_ASSERT_SUCCESS(rte_eth_bond_slave_add(test_params->bonded_port_id,
2054 				polling_test_slaves[i]),
2055 				"Failed to add slave %s(%d) to bonded device %d",
2056 				slave_name, polling_test_slaves[i],
2057 				test_params->bonded_port_id);
2058 	}
2059 
2060 	/* Initialize bonded device */
2061 	TEST_ASSERT_SUCCESS(configure_ethdev(test_params->bonded_port_id, 1, 1),
2062 			"Failed to configure bonded device %d",
2063 			test_params->bonded_port_id);
2064 
2065 
2066 	/* Register link status change interrupt callback */
2067 	rte_eth_dev_callback_register(test_params->bonded_port_id,
2068 			RTE_ETH_EVENT_INTR_LSC, test_bonding_lsc_event_callback,
2069 			&test_params->bonded_port_id);
2070 
2071 	/* link status change callback for first slave link up */
2072 	test_lsc_interrupt_count = 0;
2073 
2074 	virtual_ethdev_set_link_status(polling_test_slaves[0], 1);
2075 
2076 	TEST_ASSERT_SUCCESS(lsc_timeout(15000), "timed out waiting for interrupt");
2077 
2078 
2079 	/* no link status change callback for second slave link up */
2080 	test_lsc_interrupt_count = 0;
2081 
2082 	virtual_ethdev_set_link_status(polling_test_slaves[1], 1);
2083 
2084 	TEST_ASSERT_FAIL(lsc_timeout(15000), "unexpectedly succeeded");
2085 
2086 	/* link status change callback for both slave links down */
2087 	test_lsc_interrupt_count = 0;
2088 
2089 	virtual_ethdev_set_link_status(polling_test_slaves[0], 0);
2090 	virtual_ethdev_set_link_status(polling_test_slaves[1], 0);
2091 
2092 	TEST_ASSERT_SUCCESS(lsc_timeout(20000), "timed out waiting for interrupt");
2093 
2094 	/* Un-Register link status change interrupt callback */
2095 	rte_eth_dev_callback_unregister(test_params->bonded_port_id,
2096 			RTE_ETH_EVENT_INTR_LSC, test_bonding_lsc_event_callback,
2097 			&test_params->bonded_port_id);
2098 
2099 
2100 	/* Clean up and remove slaves from bonded device */
2101 	for (i = 0; i < TEST_RR_POLLING_LINK_STATUS_SLAVE_COUNT; i++) {
2102 
2103 		TEST_ASSERT_SUCCESS(
2104 				rte_eth_bond_slave_remove(test_params->bonded_port_id,
2105 						polling_test_slaves[i]),
2106 				"Failed to remove slave %d from bonded port (%d)",
2107 				polling_test_slaves[i], test_params->bonded_port_id);
2108 	}
2109 
2110 	return remove_slaves_and_stop_bonded_device();
2111 }
2112 
2113 
2114 /** Active Backup Mode Tests */
2115 
2116 static int
2117 test_activebackup_tx_burst(void)
2118 {
2119 	int i, pktlen, primary_port, burst_size;
2120 	struct rte_mbuf *pkts_burst[MAX_PKT_BURST];
2121 	struct rte_eth_stats port_stats;
2122 
2123 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2124 			BONDING_MODE_ACTIVE_BACKUP, 0, 1, 1),
2125 			"Failed to initialize bonded device with slaves");
2126 
2127 	initialize_eth_header(test_params->pkt_eth_hdr,
2128 			(struct rte_ether_addr *)src_mac,
2129 			(struct rte_ether_addr *)dst_mac_0,
2130 			RTE_ETHER_TYPE_IPV4,  0, 0);
2131 	pktlen = initialize_udp_header(test_params->pkt_udp_hdr, src_port,
2132 			dst_port_0, 16);
2133 	pktlen = initialize_ipv4_header(test_params->pkt_ipv4_hdr, src_addr,
2134 			dst_addr_0, pktlen);
2135 
2136 	burst_size = 20 * test_params->bonded_slave_count;
2137 
2138 	TEST_ASSERT(burst_size < MAX_PKT_BURST,
2139 			"Burst size specified is greater than supported.");
2140 
2141 	/* Generate a burst of packets to transmit */
2142 	TEST_ASSERT_EQUAL(generate_packet_burst(test_params->mbuf_pool, pkts_burst,
2143 			test_params->pkt_eth_hdr, 0, test_params->pkt_ipv4_hdr, 1,
2144 			test_params->pkt_udp_hdr, burst_size, PACKET_BURST_GEN_PKT_LEN, 1),
2145 			burst_size,	"failed to generate burst correctly");
2146 
2147 	/* Send burst on bonded port */
2148 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst,
2149 			burst_size),  burst_size, "tx burst failed");
2150 
2151 	/* Verify bonded port tx stats */
2152 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
2153 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
2154 			"Bonded Port (%d) opackets value (%u) not as expected (%d)",
2155 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
2156 			burst_size);
2157 
2158 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
2159 
2160 	/* Verify slave ports tx stats */
2161 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2162 		rte_eth_stats_get(test_params->slave_port_ids[i], &port_stats);
2163 		if (test_params->slave_port_ids[i] == primary_port) {
2164 			TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
2165 					"Slave Port (%d) opackets value (%u) not as expected (%d)",
2166 					test_params->bonded_port_id,
2167 					(unsigned int)port_stats.opackets,
2168 					burst_size / test_params->bonded_slave_count);
2169 		} else {
2170 			TEST_ASSERT_EQUAL(port_stats.opackets, 0,
2171 					"Slave Port (%d) opackets value (%u) not as expected (%d)",
2172 					test_params->bonded_port_id,
2173 					(unsigned int)port_stats.opackets, 0);
2174 		}
2175 	}
2176 
2177 	/* Put all slaves down and try and transmit */
2178 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2179 		virtual_ethdev_simulate_link_status_interrupt(
2180 				test_params->slave_port_ids[i], 0);
2181 	}
2182 
2183 	/* Send burst on bonded port */
2184 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(test_params->bonded_port_id, 0,
2185 			pkts_burst, burst_size), 0, "Sending empty burst failed");
2186 
2187 	/* Clean up and remove slaves from bonded device */
2188 	return remove_slaves_and_stop_bonded_device();
2189 }
2190 
2191 #define TEST_ACTIVE_BACKUP_RX_BURST_SLAVE_COUNT (4)
2192 
2193 static int
2194 test_activebackup_rx_burst(void)
2195 {
2196 	struct rte_mbuf *gen_pkt_burst[MAX_PKT_BURST] = { NULL };
2197 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
2198 
2199 	struct rte_eth_stats port_stats;
2200 
2201 	int primary_port;
2202 
2203 	int i, j, burst_size = 17;
2204 
2205 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2206 			BONDING_MODE_ACTIVE_BACKUP, 0,
2207 			TEST_ACTIVE_BACKUP_RX_BURST_SLAVE_COUNT, 1),
2208 			"Failed to initialize bonded device with slaves");
2209 
2210 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
2211 	TEST_ASSERT(primary_port >= 0,
2212 			"failed to get primary slave for bonded port (%d)",
2213 			test_params->bonded_port_id);
2214 
2215 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2216 		/* Generate test bursts of packets to transmit */
2217 		TEST_ASSERT_EQUAL(generate_test_burst(
2218 				&gen_pkt_burst[0], burst_size, 0, 1, 0, 0, 0),
2219 				burst_size, "burst generation failed");
2220 
2221 		/* Add rx data to slave */
2222 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
2223 				&gen_pkt_burst[0], burst_size);
2224 
2225 		/* Call rx burst on bonded device */
2226 		TEST_ASSERT_EQUAL(rte_eth_rx_burst(test_params->bonded_port_id, 0,
2227 				&rx_pkt_burst[0], MAX_PKT_BURST), burst_size,
2228 				"rte_eth_rx_burst failed");
2229 
2230 		if (test_params->slave_port_ids[i] == primary_port) {
2231 			/* Verify bonded device rx count */
2232 			rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
2233 			TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
2234 					"Bonded Port (%d) ipackets value (%u) not as expected (%d)",
2235 					test_params->bonded_port_id,
2236 					(unsigned int)port_stats.ipackets, burst_size);
2237 
2238 			/* Verify bonded slave devices rx count */
2239 			for (j = 0; j < test_params->bonded_slave_count; j++) {
2240 				rte_eth_stats_get(test_params->slave_port_ids[j], &port_stats);
2241 				if (i == j) {
2242 					TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
2243 							"Slave Port (%d) ipackets value (%u) not as "
2244 							"expected (%d)", test_params->slave_port_ids[i],
2245 							(unsigned int)port_stats.ipackets, burst_size);
2246 				} else {
2247 					TEST_ASSERT_EQUAL(port_stats.ipackets, 0,
2248 							"Slave Port (%d) ipackets value (%u) not as "
2249 							"expected (%d)\n", test_params->slave_port_ids[i],
2250 							(unsigned int)port_stats.ipackets, 0);
2251 				}
2252 			}
2253 		} else {
2254 			for (j = 0; j < test_params->bonded_slave_count; j++) {
2255 				rte_eth_stats_get(test_params->slave_port_ids[j], &port_stats);
2256 				TEST_ASSERT_EQUAL(port_stats.ipackets, 0,
2257 						"Slave Port (%d) ipackets value (%u) not as expected "
2258 						"(%d)", test_params->slave_port_ids[i],
2259 						(unsigned int)port_stats.ipackets, 0);
2260 			}
2261 		}
2262 
2263 		/* free mbufs */
2264 		for (i = 0; i < MAX_PKT_BURST; i++) {
2265 			if (rx_pkt_burst[i] != NULL) {
2266 				rte_pktmbuf_free(rx_pkt_burst[i]);
2267 				rx_pkt_burst[i] = NULL;
2268 			}
2269 		}
2270 
2271 		/* reset bonded device stats */
2272 		rte_eth_stats_reset(test_params->bonded_port_id);
2273 	}
2274 
2275 	/* Clean up and remove slaves from bonded device */
2276 	return remove_slaves_and_stop_bonded_device();
2277 }
2278 
2279 static int
2280 test_activebackup_verify_promiscuous_enable_disable(void)
2281 {
2282 	int i, primary_port, promiscuous_en;
2283 	int ret;
2284 
2285 	/* Initialize bonded device with 4 slaves in round robin mode */
2286 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2287 			BONDING_MODE_ACTIVE_BACKUP, 0, 4, 1),
2288 			"Failed to initialize bonded device with slaves");
2289 
2290 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
2291 	TEST_ASSERT(primary_port >= 0,
2292 			"failed to get primary slave for bonded port (%d)",
2293 			test_params->bonded_port_id);
2294 
2295 	ret = rte_eth_promiscuous_enable(test_params->bonded_port_id);
2296 	TEST_ASSERT_SUCCESS(ret,
2297 		"Failed to enable promiscuous mode for port %d: %s",
2298 		test_params->bonded_port_id, rte_strerror(-ret));
2299 
2300 	TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(test_params->bonded_port_id), 1,
2301 			"Port (%d) promiscuous mode not enabled",
2302 			test_params->bonded_port_id);
2303 
2304 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2305 		promiscuous_en = rte_eth_promiscuous_get(
2306 				test_params->slave_port_ids[i]);
2307 		if (primary_port == test_params->slave_port_ids[i]) {
2308 			TEST_ASSERT_EQUAL(promiscuous_en, 1,
2309 					"slave port (%d) promiscuous mode not enabled",
2310 					test_params->slave_port_ids[i]);
2311 		} else {
2312 			TEST_ASSERT_EQUAL(promiscuous_en, 0,
2313 					"slave port (%d) promiscuous mode enabled",
2314 					test_params->slave_port_ids[i]);
2315 		}
2316 
2317 	}
2318 
2319 	ret = rte_eth_promiscuous_disable(test_params->bonded_port_id);
2320 	TEST_ASSERT_SUCCESS(ret,
2321 		"Failed to disable promiscuous mode for port %d: %s",
2322 		test_params->bonded_port_id, rte_strerror(-ret));
2323 
2324 	TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(test_params->bonded_port_id), 0,
2325 			"Port (%d) promiscuous mode not disabled\n",
2326 			test_params->bonded_port_id);
2327 
2328 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2329 		promiscuous_en = rte_eth_promiscuous_get(
2330 				test_params->slave_port_ids[i]);
2331 		TEST_ASSERT_EQUAL(promiscuous_en, 0,
2332 				"slave port (%d) promiscuous mode not disabled\n",
2333 				test_params->slave_port_ids[i]);
2334 	}
2335 
2336 	/* Clean up and remove slaves from bonded device */
2337 	return remove_slaves_and_stop_bonded_device();
2338 }
2339 
2340 static int
2341 test_activebackup_verify_mac_assignment(void)
2342 {
2343 	struct rte_ether_addr read_mac_addr;
2344 	struct rte_ether_addr expected_mac_addr_0, expected_mac_addr_1;
2345 
2346 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &expected_mac_addr_0),
2347 			"Failed to get mac address (port %d)",
2348 			test_params->slave_port_ids[0]);
2349 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &expected_mac_addr_1),
2350 			"Failed to get mac address (port %d)",
2351 			test_params->slave_port_ids[1]);
2352 
2353 	/* Initialize bonded device with 2 slaves in active backup mode */
2354 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2355 			BONDING_MODE_ACTIVE_BACKUP, 0, 2, 1),
2356 			"Failed to initialize bonded device with slaves");
2357 
2358 	/* Verify that bonded MACs is that of first slave and that the other slave
2359 	 * MAC hasn't been changed */
2360 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
2361 			"Failed to get mac address (port %d)",
2362 			test_params->bonded_port_id);
2363 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
2364 			sizeof(read_mac_addr)),
2365 			"bonded port (%d) mac address not set to that of primary port",
2366 			test_params->bonded_port_id);
2367 
2368 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
2369 			"Failed to get mac address (port %d)",
2370 			test_params->slave_port_ids[0]);
2371 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
2372 			sizeof(read_mac_addr)),
2373 			"slave port (%d) mac address not set to that of primary port",
2374 			test_params->slave_port_ids[0]);
2375 
2376 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
2377 			"Failed to get mac address (port %d)",
2378 			test_params->slave_port_ids[1]);
2379 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
2380 			sizeof(read_mac_addr)),
2381 			"slave port (%d) mac address not as expected",
2382 			test_params->slave_port_ids[1]);
2383 
2384 	/* change primary and verify that MAC addresses haven't changed */
2385 	TEST_ASSERT_EQUAL(rte_eth_bond_primary_set(test_params->bonded_port_id,
2386 			test_params->slave_port_ids[1]), 0,
2387 			"Failed to set bonded port (%d) primary port to (%d)",
2388 			test_params->bonded_port_id, test_params->slave_port_ids[1]);
2389 
2390 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
2391 			"Failed to get mac address (port %d)",
2392 			test_params->bonded_port_id);
2393 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
2394 			sizeof(read_mac_addr)),
2395 			"bonded port (%d) mac address not set to that of primary port",
2396 			test_params->bonded_port_id);
2397 
2398 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
2399 			"Failed to get mac address (port %d)",
2400 			test_params->slave_port_ids[0]);
2401 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
2402 			sizeof(read_mac_addr)),
2403 			"slave port (%d) mac address not set to that of primary port",
2404 			test_params->slave_port_ids[0]);
2405 
2406 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
2407 			"Failed to get mac address (port %d)",
2408 			test_params->slave_port_ids[1]);
2409 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
2410 			sizeof(read_mac_addr)),
2411 			"slave port (%d) mac address not as expected",
2412 			test_params->slave_port_ids[1]);
2413 
2414 	/* stop / start bonded device and verify that primary MAC address is
2415 	 * propagated to bonded device and slaves */
2416 
2417 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
2418 			"Failed to stop bonded port %u",
2419 			test_params->bonded_port_id);
2420 
2421 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
2422 			"Failed to start device");
2423 
2424 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
2425 			"Failed to get mac address (port %d)",
2426 			test_params->bonded_port_id);
2427 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
2428 			sizeof(read_mac_addr)),
2429 			"bonded port (%d) mac address not set to that of primary port",
2430 			test_params->bonded_port_id);
2431 
2432 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
2433 			"Failed to get mac address (port %d)",
2434 			test_params->slave_port_ids[0]);
2435 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
2436 			sizeof(read_mac_addr)),
2437 			"slave port (%d) mac address not as expected",
2438 			test_params->slave_port_ids[0]);
2439 
2440 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
2441 			"Failed to get mac address (port %d)",
2442 			test_params->slave_port_ids[1]);
2443 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
2444 			sizeof(read_mac_addr)),
2445 			"slave port (%d) mac address not set to that of primary port",
2446 			test_params->slave_port_ids[1]);
2447 
2448 	/* Set explicit MAC address */
2449 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_set(
2450 			test_params->bonded_port_id,
2451 			(struct rte_ether_addr *)bonded_mac),
2452 			"failed to set MAC address");
2453 
2454 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
2455 			"Failed to get mac address (port %d)",
2456 			test_params->bonded_port_id);
2457 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac, &read_mac_addr,
2458 			sizeof(read_mac_addr)),
2459 			"bonded port (%d) mac address not set to that of bonded port",
2460 			test_params->bonded_port_id);
2461 
2462 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
2463 			"Failed to get mac address (port %d)",
2464 			test_params->slave_port_ids[0]);
2465 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
2466 			sizeof(read_mac_addr)),
2467 			"slave port (%d) mac address not as expected",
2468 			test_params->slave_port_ids[0]);
2469 
2470 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
2471 			"Failed to get mac address (port %d)",
2472 			test_params->slave_port_ids[1]);
2473 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac, &read_mac_addr,
2474 			sizeof(read_mac_addr)),
2475 			"slave port (%d) mac address not set to that of bonded port",
2476 			test_params->slave_port_ids[1]);
2477 
2478 	/* Clean up and remove slaves from bonded device */
2479 	return remove_slaves_and_stop_bonded_device();
2480 }
2481 
2482 static int
2483 test_activebackup_verify_slave_link_status_change_failover(void)
2484 {
2485 	struct rte_mbuf *pkt_burst[TEST_ACTIVE_BACKUP_RX_BURST_SLAVE_COUNT][MAX_PKT_BURST];
2486 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
2487 	struct rte_eth_stats port_stats;
2488 
2489 	uint16_t slaves[RTE_MAX_ETHPORTS];
2490 
2491 	int i, burst_size, slave_count, primary_port;
2492 
2493 	burst_size = 21;
2494 
2495 	memset(pkt_burst, 0, sizeof(pkt_burst));
2496 
2497 	/* Generate packet burst for testing */
2498 	TEST_ASSERT_EQUAL(generate_test_burst(
2499 			&pkt_burst[0][0], burst_size, 0, 1, 0, 0, 0), burst_size,
2500 			"generate_test_burst failed");
2501 
2502 	/* Initialize bonded device with 4 slaves in round robin mode */
2503 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2504 			BONDING_MODE_ACTIVE_BACKUP, 0,
2505 			TEST_ACTIVE_BACKUP_RX_BURST_SLAVE_COUNT, 1),
2506 			"Failed to initialize bonded device with slaves");
2507 
2508 	/* Verify Current Slaves Count /Active Slave Count is */
2509 	slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id, slaves,
2510 			RTE_MAX_ETHPORTS);
2511 	TEST_ASSERT_EQUAL(slave_count, 4,
2512 			"Number of slaves (%d) is not as expected (%d).",
2513 			slave_count, 4);
2514 
2515 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
2516 			slaves, RTE_MAX_ETHPORTS);
2517 	TEST_ASSERT_EQUAL(slave_count, 4,
2518 			"Number of active slaves (%d) is not as expected (%d).",
2519 			slave_count, 4);
2520 
2521 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
2522 	TEST_ASSERT_EQUAL(primary_port, test_params->slave_port_ids[0],
2523 			"Primary port not as expected");
2524 
2525 	/* Bring 2 slaves down and verify active slave count */
2526 	virtual_ethdev_simulate_link_status_interrupt(
2527 			test_params->slave_port_ids[1], 0);
2528 	virtual_ethdev_simulate_link_status_interrupt(
2529 			test_params->slave_port_ids[3], 0);
2530 
2531 	TEST_ASSERT_EQUAL(rte_eth_bond_active_slaves_get(
2532 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS), 2,
2533 			"Number of active slaves (%d) is not as expected (%d).",
2534 			slave_count, 2);
2535 
2536 	virtual_ethdev_simulate_link_status_interrupt(
2537 			test_params->slave_port_ids[1], 1);
2538 	virtual_ethdev_simulate_link_status_interrupt(
2539 			test_params->slave_port_ids[3], 1);
2540 
2541 
2542 	/* Bring primary port down, verify that active slave count is 3 and primary
2543 	 *  has changed */
2544 	virtual_ethdev_simulate_link_status_interrupt(
2545 			test_params->slave_port_ids[0], 0);
2546 
2547 	TEST_ASSERT_EQUAL(rte_eth_bond_active_slaves_get(
2548 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS),
2549 			3,
2550 			"Number of active slaves (%d) is not as expected (%d).",
2551 			slave_count, 3);
2552 
2553 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
2554 	TEST_ASSERT_EQUAL(primary_port, test_params->slave_port_ids[2],
2555 			"Primary port not as expected");
2556 
2557 	/* Verify that pkts are sent on new primary slave */
2558 
2559 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
2560 			test_params->bonded_port_id, 0, &pkt_burst[0][0],
2561 			burst_size), burst_size, "rte_eth_tx_burst failed");
2562 
2563 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
2564 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
2565 			"(%d) port_stats.opackets not as expected",
2566 			test_params->slave_port_ids[2]);
2567 
2568 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
2569 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
2570 			"(%d) port_stats.opackets not as expected\n",
2571 			test_params->slave_port_ids[0]);
2572 
2573 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
2574 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
2575 			"(%d) port_stats.opackets not as expected\n",
2576 			test_params->slave_port_ids[1]);
2577 
2578 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
2579 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
2580 			"(%d) port_stats.opackets not as expected\n",
2581 			test_params->slave_port_ids[3]);
2582 
2583 	/* Generate packet burst for testing */
2584 
2585 	for (i = 0; i < TEST_ACTIVE_BACKUP_RX_BURST_SLAVE_COUNT; i++) {
2586 		TEST_ASSERT_EQUAL(generate_test_burst(
2587 				&pkt_burst[i][0], burst_size, 0, 1, 0, 0, 0), burst_size,
2588 				"generate_test_burst failed");
2589 
2590 		virtual_ethdev_add_mbufs_to_rx_queue(
2591 			test_params->slave_port_ids[i], &pkt_burst[i][0], burst_size);
2592 	}
2593 
2594 	TEST_ASSERT_EQUAL(rte_eth_rx_burst(
2595 			test_params->bonded_port_id, 0, rx_pkt_burst, MAX_PKT_BURST),
2596 			burst_size, "rte_eth_rx_burst\n");
2597 
2598 	/* Verify bonded device rx count */
2599 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
2600 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
2601 			"(%d) port_stats.ipackets not as expected",
2602 			test_params->bonded_port_id);
2603 
2604 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
2605 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
2606 			"(%d) port_stats.opackets not as expected",
2607 			test_params->slave_port_ids[2]);
2608 
2609 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
2610 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
2611 			"(%d) port_stats.opackets not as expected",
2612 			test_params->slave_port_ids[0]);
2613 
2614 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
2615 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
2616 			"(%d) port_stats.opackets not as expected",
2617 			test_params->slave_port_ids[1]);
2618 
2619 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
2620 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
2621 			"(%d) port_stats.opackets not as expected",
2622 			test_params->slave_port_ids[3]);
2623 
2624 	/* Clean up and remove slaves from bonded device */
2625 	return remove_slaves_and_stop_bonded_device();
2626 }
2627 
2628 /** Balance Mode Tests */
2629 
2630 static int
2631 test_balance_xmit_policy_configuration(void)
2632 {
2633 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2634 			BONDING_MODE_ACTIVE_BACKUP, 0, 2, 1),
2635 			"Failed to initialize_bonded_device_with_slaves.");
2636 
2637 	/* Invalid port id */
2638 	TEST_ASSERT_FAIL(rte_eth_bond_xmit_policy_set(
2639 			INVALID_PORT_ID, BALANCE_XMIT_POLICY_LAYER2),
2640 			"Expected call to failed as invalid port specified.");
2641 
2642 	/* Set xmit policy on non bonded device */
2643 	TEST_ASSERT_FAIL(rte_eth_bond_xmit_policy_set(
2644 			test_params->slave_port_ids[0],	BALANCE_XMIT_POLICY_LAYER2),
2645 			"Expected call to failed as invalid port specified.");
2646 
2647 
2648 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
2649 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER2),
2650 			"Failed to set balance xmit policy.");
2651 
2652 	TEST_ASSERT_EQUAL(rte_eth_bond_xmit_policy_get(test_params->bonded_port_id),
2653 			BALANCE_XMIT_POLICY_LAYER2, "balance xmit policy not as expected.");
2654 
2655 
2656 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
2657 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER23),
2658 			"Failed to set balance xmit policy.");
2659 
2660 	TEST_ASSERT_EQUAL(rte_eth_bond_xmit_policy_get(test_params->bonded_port_id),
2661 			BALANCE_XMIT_POLICY_LAYER23,
2662 			"balance xmit policy not as expected.");
2663 
2664 
2665 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
2666 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER34),
2667 			"Failed to set balance xmit policy.");
2668 
2669 	TEST_ASSERT_EQUAL(rte_eth_bond_xmit_policy_get(test_params->bonded_port_id),
2670 			BALANCE_XMIT_POLICY_LAYER34,
2671 			"balance xmit policy not as expected.");
2672 
2673 	/* Invalid port id */
2674 	TEST_ASSERT_FAIL(rte_eth_bond_xmit_policy_get(INVALID_PORT_ID),
2675 			"Expected call to failed as invalid port specified.");
2676 
2677 	/* Clean up and remove slaves from bonded device */
2678 	return remove_slaves_and_stop_bonded_device();
2679 }
2680 
2681 #define TEST_BALANCE_L2_TX_BURST_SLAVE_COUNT (2)
2682 
2683 static int
2684 test_balance_l2_tx_burst(void)
2685 {
2686 	struct rte_mbuf *pkts_burst[TEST_BALANCE_L2_TX_BURST_SLAVE_COUNT][MAX_PKT_BURST];
2687 	int burst_size[TEST_BALANCE_L2_TX_BURST_SLAVE_COUNT] = { 10, 15 };
2688 
2689 	uint16_t pktlen;
2690 	int i;
2691 	struct rte_eth_stats port_stats;
2692 
2693 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2694 			BONDING_MODE_BALANCE, 0, TEST_BALANCE_L2_TX_BURST_SLAVE_COUNT, 1),
2695 			"Failed to initialize_bonded_device_with_slaves.");
2696 
2697 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
2698 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER2),
2699 			"Failed to set balance xmit policy.");
2700 
2701 	initialize_eth_header(test_params->pkt_eth_hdr,
2702 			(struct rte_ether_addr *)src_mac,
2703 			(struct rte_ether_addr *)dst_mac_0,
2704 			RTE_ETHER_TYPE_IPV4, 0, 0);
2705 	pktlen = initialize_udp_header(test_params->pkt_udp_hdr, src_port,
2706 			dst_port_0, 16);
2707 	pktlen = initialize_ipv4_header(test_params->pkt_ipv4_hdr, src_addr,
2708 			dst_addr_0, pktlen);
2709 
2710 	/* Generate a burst 1 of packets to transmit */
2711 	TEST_ASSERT_EQUAL(generate_packet_burst(test_params->mbuf_pool, &pkts_burst[0][0],
2712 			test_params->pkt_eth_hdr, 0, test_params->pkt_ipv4_hdr, 1,
2713 			test_params->pkt_udp_hdr, burst_size[0],
2714 			PACKET_BURST_GEN_PKT_LEN, 1), burst_size[0],
2715 			"failed to generate packet burst");
2716 
2717 	initialize_eth_header(test_params->pkt_eth_hdr,
2718 			(struct rte_ether_addr *)src_mac,
2719 			(struct rte_ether_addr *)dst_mac_1,
2720 			RTE_ETHER_TYPE_IPV4, 0, 0);
2721 
2722 	/* Generate a burst 2 of packets to transmit */
2723 	TEST_ASSERT_EQUAL(generate_packet_burst(test_params->mbuf_pool, &pkts_burst[1][0],
2724 			test_params->pkt_eth_hdr, 0, test_params->pkt_ipv4_hdr, 1,
2725 			test_params->pkt_udp_hdr, burst_size[1],
2726 			PACKET_BURST_GEN_PKT_LEN, 1), burst_size[1],
2727 			"failed to generate packet burst");
2728 
2729 	/* Send burst 1 on bonded port */
2730 	for (i = 0; i < TEST_BALANCE_L2_TX_BURST_SLAVE_COUNT; i++) {
2731 		TEST_ASSERT_EQUAL(rte_eth_tx_burst(test_params->bonded_port_id, 0,
2732 				&pkts_burst[i][0], burst_size[i]),
2733 				burst_size[i], "Failed to transmit packet burst");
2734 	}
2735 
2736 	/* Verify bonded port tx stats */
2737 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
2738 	TEST_ASSERT_EQUAL(port_stats.opackets,
2739 			(uint64_t)(burst_size[0] + burst_size[1]),
2740 			"Bonded Port (%d) opackets value (%u) not as expected (%d)",
2741 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
2742 			burst_size[0] + burst_size[1]);
2743 
2744 
2745 	/* Verify slave ports tx stats */
2746 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
2747 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size[0],
2748 			"Slave Port (%d) opackets value (%u) not as expected (%d)",
2749 			test_params->slave_port_ids[0], (unsigned int)port_stats.opackets,
2750 			burst_size[0]);
2751 
2752 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
2753 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size[1],
2754 			"Slave Port (%d) opackets value (%u) not as expected (%d)\n",
2755 			test_params->slave_port_ids[1], (unsigned int)port_stats.opackets,
2756 			burst_size[1]);
2757 
2758 	/* Put all slaves down and try and transmit */
2759 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2760 
2761 		virtual_ethdev_simulate_link_status_interrupt(
2762 				test_params->slave_port_ids[i], 0);
2763 	}
2764 
2765 	/* Send burst on bonded port */
2766 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
2767 			test_params->bonded_port_id, 0, &pkts_burst[0][0], burst_size[0]),
2768 			0, "Expected zero packet");
2769 
2770 	/* Clean up and remove slaves from bonded device */
2771 	return remove_slaves_and_stop_bonded_device();
2772 }
2773 
2774 static int
2775 balance_l23_tx_burst(uint8_t vlan_enabled, uint8_t ipv4,
2776 		uint8_t toggle_mac_addr, uint8_t toggle_ip_addr)
2777 {
2778 	int i, burst_size_1, burst_size_2, nb_tx_1, nb_tx_2;
2779 
2780 	struct rte_mbuf *pkts_burst_1[MAX_PKT_BURST];
2781 	struct rte_mbuf *pkts_burst_2[MAX_PKT_BURST];
2782 
2783 	struct rte_eth_stats port_stats;
2784 
2785 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2786 			BONDING_MODE_BALANCE, 0, 2, 1),
2787 			"Failed to initialize_bonded_device_with_slaves.");
2788 
2789 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
2790 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER23),
2791 			"Failed to set balance xmit policy.");
2792 
2793 	burst_size_1 = 20;
2794 	burst_size_2 = 10;
2795 
2796 	TEST_ASSERT(burst_size_1 < MAX_PKT_BURST || burst_size_2 < MAX_PKT_BURST,
2797 			"Burst size specified is greater than supported.");
2798 
2799 	/* Generate test bursts of packets to transmit */
2800 	TEST_ASSERT_EQUAL(generate_test_burst(
2801 			pkts_burst_1, burst_size_1, vlan_enabled, ipv4, 0, 0, 0),
2802 			burst_size_1, "failed to generate packet burst");
2803 
2804 	TEST_ASSERT_EQUAL(generate_test_burst(pkts_burst_2, burst_size_2, vlan_enabled, ipv4,
2805 			toggle_mac_addr, toggle_ip_addr, 0), burst_size_2,
2806 			"failed to generate packet burst");
2807 
2808 	/* Send burst 1 on bonded port */
2809 	nb_tx_1 = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst_1,
2810 			burst_size_1);
2811 	TEST_ASSERT_EQUAL(nb_tx_1, burst_size_1, "tx burst failed");
2812 
2813 	/* Send burst 2 on bonded port */
2814 	nb_tx_2 = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst_2,
2815 			burst_size_2);
2816 	TEST_ASSERT_EQUAL(nb_tx_2, burst_size_2, "tx burst failed");
2817 
2818 	/* Verify bonded port tx stats */
2819 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
2820 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)(nb_tx_1 + nb_tx_2),
2821 			"Bonded Port (%d) opackets value (%u) not as expected (%d)",
2822 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
2823 			nb_tx_1 + nb_tx_2);
2824 
2825 	/* Verify slave ports tx stats */
2826 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
2827 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)nb_tx_1,
2828 			"Slave Port (%d) opackets value (%u) not as expected (%d)",
2829 			test_params->slave_port_ids[0], (unsigned int)port_stats.opackets,
2830 			nb_tx_1);
2831 
2832 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
2833 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)nb_tx_2,
2834 			"Slave Port (%d) opackets value (%u) not as expected (%d)",
2835 			test_params->slave_port_ids[1], (unsigned int)port_stats.opackets,
2836 			nb_tx_2);
2837 
2838 	/* Put all slaves down and try and transmit */
2839 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2840 
2841 		virtual_ethdev_simulate_link_status_interrupt(
2842 				test_params->slave_port_ids[i], 0);
2843 	}
2844 
2845 	/* Send burst on bonded port */
2846 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
2847 			test_params->bonded_port_id, 0, pkts_burst_1,
2848 			burst_size_1), 0, "Expected zero packet");
2849 
2850 
2851 	/* Clean up and remove slaves from bonded device */
2852 	return remove_slaves_and_stop_bonded_device();
2853 }
2854 
2855 static int
2856 test_balance_l23_tx_burst_ipv4_toggle_ip_addr(void)
2857 {
2858 	return balance_l23_tx_burst(0, 1, 0, 1);
2859 }
2860 
2861 static int
2862 test_balance_l23_tx_burst_vlan_ipv4_toggle_ip_addr(void)
2863 {
2864 	return balance_l23_tx_burst(1, 1, 0, 1);
2865 }
2866 
2867 static int
2868 test_balance_l23_tx_burst_ipv6_toggle_ip_addr(void)
2869 {
2870 	return balance_l23_tx_burst(0, 0, 0, 1);
2871 }
2872 
2873 static int
2874 test_balance_l23_tx_burst_vlan_ipv6_toggle_ip_addr(void)
2875 {
2876 	return balance_l23_tx_burst(1, 0, 0, 1);
2877 }
2878 
2879 static int
2880 test_balance_l23_tx_burst_toggle_mac_addr(void)
2881 {
2882 	return balance_l23_tx_burst(0, 0, 1, 0);
2883 }
2884 
2885 static int
2886 balance_l34_tx_burst(uint8_t vlan_enabled, uint8_t ipv4,
2887 		uint8_t toggle_mac_addr, uint8_t toggle_ip_addr,
2888 		uint8_t toggle_udp_port)
2889 {
2890 	int i, burst_size_1, burst_size_2, nb_tx_1, nb_tx_2;
2891 
2892 	struct rte_mbuf *pkts_burst_1[MAX_PKT_BURST];
2893 	struct rte_mbuf *pkts_burst_2[MAX_PKT_BURST];
2894 
2895 	struct rte_eth_stats port_stats;
2896 
2897 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
2898 			BONDING_MODE_BALANCE, 0, 2, 1),
2899 			"Failed to initialize_bonded_device_with_slaves.");
2900 
2901 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
2902 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER34),
2903 			"Failed to set balance xmit policy.");
2904 
2905 	burst_size_1 = 20;
2906 	burst_size_2 = 10;
2907 
2908 	TEST_ASSERT(burst_size_1 < MAX_PKT_BURST || burst_size_2 < MAX_PKT_BURST,
2909 			"Burst size specified is greater than supported.");
2910 
2911 	/* Generate test bursts of packets to transmit */
2912 	TEST_ASSERT_EQUAL(generate_test_burst(
2913 			pkts_burst_1, burst_size_1, vlan_enabled, ipv4, 0, 0, 0),
2914 			burst_size_1, "failed to generate burst");
2915 
2916 	TEST_ASSERT_EQUAL(generate_test_burst(pkts_burst_2, burst_size_2,
2917 			vlan_enabled, ipv4, toggle_mac_addr, toggle_ip_addr,
2918 			toggle_udp_port), burst_size_2, "failed to generate burst");
2919 
2920 	/* Send burst 1 on bonded port */
2921 	nb_tx_1 = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst_1,
2922 			burst_size_1);
2923 	TEST_ASSERT_EQUAL(nb_tx_1, burst_size_1, "tx burst failed");
2924 
2925 	/* Send burst 2 on bonded port */
2926 	nb_tx_2 = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst_2,
2927 			burst_size_2);
2928 	TEST_ASSERT_EQUAL(nb_tx_2, burst_size_2, "tx burst failed");
2929 
2930 
2931 	/* Verify bonded port tx stats */
2932 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
2933 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)(nb_tx_1 + nb_tx_2),
2934 			"Bonded Port (%d) opackets value (%u) not as expected (%d)",
2935 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
2936 			nb_tx_1 + nb_tx_2);
2937 
2938 	/* Verify slave ports tx stats */
2939 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
2940 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)nb_tx_1,
2941 			"Slave Port (%d) opackets value (%u) not as expected (%d)",
2942 			test_params->slave_port_ids[0], (unsigned int)port_stats.opackets,
2943 			nb_tx_1);
2944 
2945 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
2946 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)nb_tx_2,
2947 			"Slave Port (%d) opackets value (%u) not as expected (%d)",
2948 			test_params->slave_port_ids[1], (unsigned int)port_stats.opackets,
2949 			nb_tx_2);
2950 
2951 	/* Put all slaves down and try and transmit */
2952 	for (i = 0; i < test_params->bonded_slave_count; i++) {
2953 
2954 		virtual_ethdev_simulate_link_status_interrupt(
2955 				test_params->slave_port_ids[i], 0);
2956 	}
2957 
2958 	/* Send burst on bonded port */
2959 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
2960 			test_params->bonded_port_id, 0, pkts_burst_1,
2961 			burst_size_1), 0, "Expected zero packet");
2962 
2963 	/* Clean up and remove slaves from bonded device */
2964 	return remove_slaves_and_stop_bonded_device();
2965 }
2966 
2967 static int
2968 test_balance_l34_tx_burst_ipv4_toggle_ip_addr(void)
2969 {
2970 	return balance_l34_tx_burst(0, 1, 0, 1, 0);
2971 }
2972 
2973 static int
2974 test_balance_l34_tx_burst_ipv4_toggle_udp_port(void)
2975 {
2976 	return balance_l34_tx_burst(0, 1, 0, 0, 1);
2977 }
2978 
2979 static int
2980 test_balance_l34_tx_burst_vlan_ipv4_toggle_ip_addr(void)
2981 {
2982 	return balance_l34_tx_burst(1, 1, 0, 1, 0);
2983 }
2984 
2985 static int
2986 test_balance_l34_tx_burst_ipv6_toggle_ip_addr(void)
2987 {
2988 	return balance_l34_tx_burst(0, 0, 0, 1, 0);
2989 }
2990 
2991 static int
2992 test_balance_l34_tx_burst_vlan_ipv6_toggle_ip_addr(void)
2993 {
2994 	return balance_l34_tx_burst(1, 0, 0, 1, 0);
2995 }
2996 
2997 static int
2998 test_balance_l34_tx_burst_ipv6_toggle_udp_port(void)
2999 {
3000 	return balance_l34_tx_burst(0, 0, 0, 0, 1);
3001 }
3002 
3003 #define TEST_BAL_SLAVE_TX_FAIL_SLAVE_COUNT			(2)
3004 #define TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1			(40)
3005 #define TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2			(20)
3006 #define TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT		(25)
3007 #define TEST_BAL_SLAVE_TX_FAIL_FAILING_SLAVE_IDX	(0)
3008 
3009 static int
3010 test_balance_tx_burst_slave_tx_fail(void)
3011 {
3012 	struct rte_mbuf *pkts_burst_1[TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1];
3013 	struct rte_mbuf *pkts_burst_2[TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2];
3014 
3015 	struct rte_mbuf *expected_fail_pkts[TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT];
3016 
3017 	struct rte_eth_stats port_stats;
3018 
3019 	int i, first_tx_fail_idx, tx_count_1, tx_count_2;
3020 
3021 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3022 			BONDING_MODE_BALANCE, 0,
3023 			TEST_BAL_SLAVE_TX_FAIL_SLAVE_COUNT, 1),
3024 			"Failed to initialise bonded device");
3025 
3026 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
3027 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER2),
3028 			"Failed to set balance xmit policy.");
3029 
3030 
3031 	/* Generate test bursts for transmission */
3032 	TEST_ASSERT_EQUAL(generate_test_burst(pkts_burst_1,
3033 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1, 0, 0, 0, 0, 0),
3034 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1,
3035 			"Failed to generate test packet burst 1");
3036 
3037 	first_tx_fail_idx = TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1 -
3038 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT;
3039 
3040 	/* copy mbuf references for expected transmission failures */
3041 	for (i = 0; i < TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT; i++)
3042 		expected_fail_pkts[i] = pkts_burst_1[i + first_tx_fail_idx];
3043 
3044 	TEST_ASSERT_EQUAL(generate_test_burst(pkts_burst_2,
3045 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2, 0, 0, 1, 0, 0),
3046 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2,
3047 			"Failed to generate test packet burst 2");
3048 
3049 
3050 	/* Set virtual slave TEST_BAL_SLAVE_TX_FAIL_FAILING_SLAVE_IDX to only fail
3051 	 * transmission of TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT packets of burst */
3052 	virtual_ethdev_tx_burst_fn_set_success(
3053 			test_params->slave_port_ids[TEST_BAL_SLAVE_TX_FAIL_FAILING_SLAVE_IDX],
3054 			0);
3055 
3056 	virtual_ethdev_tx_burst_fn_set_tx_pkt_fail_count(
3057 			test_params->slave_port_ids[TEST_BAL_SLAVE_TX_FAIL_FAILING_SLAVE_IDX],
3058 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT);
3059 
3060 
3061 	/* Transmit burst 1 */
3062 	tx_count_1 = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst_1,
3063 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1);
3064 
3065 	TEST_ASSERT_EQUAL(tx_count_1, TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1 -
3066 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT,
3067 			"Transmitted (%d) packets, expected to transmit (%d) packets",
3068 			tx_count_1, TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1 -
3069 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT);
3070 
3071 	/* Verify that failed packet are expected failed packets */
3072 	for (i = 0; i < TEST_RR_SLAVE_TX_FAIL_PACKETS_COUNT; i++) {
3073 		TEST_ASSERT_EQUAL(expected_fail_pkts[i], pkts_burst_1[i + tx_count_1],
3074 				"expected mbuf (%d) pointer %p not expected pointer %p",
3075 				i, expected_fail_pkts[i], pkts_burst_1[i + tx_count_1]);
3076 	}
3077 
3078 	/* Transmit burst 2 */
3079 	tx_count_2 = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst_2,
3080 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2);
3081 
3082 	TEST_ASSERT_EQUAL(tx_count_2, TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2,
3083 			"Transmitted (%d) packets, expected to transmit (%d) packets",
3084 			tx_count_2, TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2);
3085 
3086 
3087 	/* Verify bonded port tx stats */
3088 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
3089 
3090 	TEST_ASSERT_EQUAL(port_stats.opackets,
3091 			(uint64_t)((TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1 -
3092 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT) +
3093 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2),
3094 			"Bonded Port (%d) opackets value (%u) not as expected (%d)",
3095 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
3096 			(TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1 -
3097 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT) +
3098 			TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2);
3099 
3100 	/* Verify slave ports tx stats */
3101 
3102 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
3103 
3104 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)
3105 				TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1 -
3106 				TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT,
3107 				"Slave Port (%d) opackets value (%u) not as expected (%d)",
3108 				test_params->slave_port_ids[0],
3109 				(unsigned int)port_stats.opackets,
3110 				TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_1 -
3111 				TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT);
3112 
3113 
3114 
3115 
3116 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
3117 
3118 	TEST_ASSERT_EQUAL(port_stats.opackets,
3119 				(uint64_t)TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2,
3120 				"Slave Port (%d) opackets value (%u) not as expected (%d)",
3121 				test_params->slave_port_ids[1],
3122 				(unsigned int)port_stats.opackets,
3123 				TEST_BAL_SLAVE_TX_FAIL_BURST_SIZE_2);
3124 
3125 	/* Verify that all mbufs have a ref value of zero */
3126 	TEST_ASSERT_SUCCESS(verify_mbufs_ref_count(&pkts_burst_1[tx_count_1],
3127 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT, 1),
3128 			"mbufs refcnts not as expected");
3129 
3130 	free_mbufs(&pkts_burst_1[tx_count_1],
3131 			TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT);
3132 
3133 	/* Clean up and remove slaves from bonded device */
3134 	return remove_slaves_and_stop_bonded_device();
3135 }
3136 
3137 #define TEST_BALANCE_RX_BURST_SLAVE_COUNT (3)
3138 
3139 static int
3140 test_balance_rx_burst(void)
3141 {
3142 	struct rte_mbuf *gen_pkt_burst[TEST_BALANCE_RX_BURST_SLAVE_COUNT][MAX_PKT_BURST];
3143 
3144 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
3145 	struct rte_eth_stats port_stats;
3146 
3147 	int burst_size[TEST_BALANCE_RX_BURST_SLAVE_COUNT] = { 10, 5, 30 };
3148 	int i, j;
3149 
3150 	memset(gen_pkt_burst, 0, sizeof(gen_pkt_burst));
3151 
3152 	/* Initialize bonded device with 4 slaves in round robin mode */
3153 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3154 			BONDING_MODE_BALANCE, 0, 3, 1),
3155 			"Failed to initialise bonded device");
3156 
3157 	/* Generate test bursts of packets to transmit */
3158 	for (i = 0; i < TEST_BALANCE_RX_BURST_SLAVE_COUNT; i++) {
3159 		TEST_ASSERT_EQUAL(generate_test_burst(
3160 				&gen_pkt_burst[i][0], burst_size[i], 0, 0, 1,
3161 				0, 0), burst_size[i],
3162 				"failed to generate packet burst");
3163 	}
3164 
3165 	/* Add rx data to slaves */
3166 	for (i = 0; i < TEST_BALANCE_RX_BURST_SLAVE_COUNT; i++) {
3167 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
3168 				&gen_pkt_burst[i][0], burst_size[i]);
3169 	}
3170 
3171 	/* Call rx burst on bonded device */
3172 	/* Send burst on bonded port */
3173 	TEST_ASSERT_EQUAL(rte_eth_rx_burst(test_params->bonded_port_id, 0,
3174 			rx_pkt_burst, MAX_PKT_BURST),
3175 			burst_size[0] + burst_size[1] + burst_size[2],
3176 			"balance rx burst failed\n");
3177 
3178 	/* Verify bonded device rx count */
3179 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
3180 	TEST_ASSERT_EQUAL(port_stats.ipackets,
3181 			(uint64_t)(burst_size[0] + burst_size[1] + burst_size[2]),
3182 			"Bonded Port (%d) ipackets value (%u) not as expected (%d)",
3183 			test_params->bonded_port_id, (unsigned int)port_stats.ipackets,
3184 			burst_size[0] + burst_size[1] + burst_size[2]);
3185 
3186 
3187 	/* Verify bonded slave devices rx counts */
3188 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
3189 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[0],
3190 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3191 				test_params->slave_port_ids[0],
3192 				(unsigned int)port_stats.ipackets, burst_size[0]);
3193 
3194 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
3195 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[1],
3196 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3197 			test_params->slave_port_ids[1], (unsigned int)port_stats.ipackets,
3198 			burst_size[1]);
3199 
3200 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
3201 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[2],
3202 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3203 			test_params->slave_port_ids[2], (unsigned int)port_stats.ipackets,
3204 			burst_size[2]);
3205 
3206 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
3207 	TEST_ASSERT_EQUAL(port_stats.ipackets, 0,
3208 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3209 			test_params->slave_port_ids[3],	(unsigned int)port_stats.ipackets,
3210 			0);
3211 
3212 	/* free mbufs */
3213 	for (i = 0; i < TEST_BALANCE_RX_BURST_SLAVE_COUNT; i++) {
3214 		for (j = 0; j < MAX_PKT_BURST; j++) {
3215 			if (gen_pkt_burst[i][j] != NULL) {
3216 				rte_pktmbuf_free(gen_pkt_burst[i][j]);
3217 				gen_pkt_burst[i][j] = NULL;
3218 			}
3219 		}
3220 	}
3221 
3222 	/* Clean up and remove slaves from bonded device */
3223 	return remove_slaves_and_stop_bonded_device();
3224 }
3225 
3226 static int
3227 test_balance_verify_promiscuous_enable_disable(void)
3228 {
3229 	int i;
3230 	int ret;
3231 
3232 	/* Initialize bonded device with 4 slaves in round robin mode */
3233 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3234 			BONDING_MODE_BALANCE, 0, 4, 1),
3235 			"Failed to initialise bonded device");
3236 
3237 	ret = rte_eth_promiscuous_enable(test_params->bonded_port_id);
3238 	TEST_ASSERT_SUCCESS(ret,
3239 		"Failed to enable promiscuous mode for port %d: %s",
3240 		test_params->bonded_port_id, rte_strerror(-ret));
3241 
3242 	TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(test_params->bonded_port_id), 1,
3243 			"Port (%d) promiscuous mode not enabled",
3244 			test_params->bonded_port_id);
3245 
3246 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3247 		TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(
3248 				test_params->slave_port_ids[i]), 1,
3249 				"Port (%d) promiscuous mode not enabled",
3250 				test_params->slave_port_ids[i]);
3251 	}
3252 
3253 	ret = rte_eth_promiscuous_disable(test_params->bonded_port_id);
3254 	TEST_ASSERT_SUCCESS(ret,
3255 		"Failed to disable promiscuous mode for port %d: %s",
3256 		test_params->bonded_port_id, rte_strerror(-ret));
3257 
3258 	TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(test_params->bonded_port_id), 0,
3259 			"Port (%d) promiscuous mode not disabled",
3260 			test_params->bonded_port_id);
3261 
3262 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3263 		TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(
3264 				test_params->slave_port_ids[i]), 0,
3265 				"Port (%d) promiscuous mode not disabled",
3266 				test_params->slave_port_ids[i]);
3267 	}
3268 
3269 	/* Clean up and remove slaves from bonded device */
3270 	return remove_slaves_and_stop_bonded_device();
3271 }
3272 
3273 static int
3274 test_balance_verify_mac_assignment(void)
3275 {
3276 	struct rte_ether_addr read_mac_addr;
3277 	struct rte_ether_addr expected_mac_addr_0, expected_mac_addr_1;
3278 
3279 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &expected_mac_addr_0),
3280 			"Failed to get mac address (port %d)",
3281 			test_params->slave_port_ids[0]);
3282 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &expected_mac_addr_1),
3283 			"Failed to get mac address (port %d)",
3284 			test_params->slave_port_ids[1]);
3285 
3286 	/* Initialize bonded device with 2 slaves in active backup mode */
3287 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3288 			BONDING_MODE_BALANCE, 0, 2, 1),
3289 			"Failed to initialise bonded device");
3290 
3291 	/* Verify that bonded MACs is that of first slave and that the other slave
3292 	 * MAC hasn't been changed */
3293 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
3294 			"Failed to get mac address (port %d)",
3295 			test_params->bonded_port_id);
3296 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3297 			sizeof(read_mac_addr)),
3298 			"bonded port (%d) mac address not set to that of primary port",
3299 			test_params->bonded_port_id);
3300 
3301 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
3302 			"Failed to get mac address (port %d)",
3303 			test_params->slave_port_ids[0]);
3304 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3305 			sizeof(read_mac_addr)),
3306 			"slave port (%d) mac address not set to that of primary port",
3307 			test_params->slave_port_ids[0]);
3308 
3309 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
3310 			"Failed to get mac address (port %d)",
3311 			test_params->slave_port_ids[1]);
3312 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3313 			sizeof(read_mac_addr)),
3314 			"slave port (%d) mac address not set to that of primary port",
3315 			test_params->slave_port_ids[1]);
3316 
3317 	/* change primary and verify that MAC addresses haven't changed */
3318 	TEST_ASSERT_SUCCESS(rte_eth_bond_primary_set(test_params->bonded_port_id,
3319 			test_params->slave_port_ids[1]),
3320 			"Failed to set bonded port (%d) primary port to (%d)\n",
3321 			test_params->bonded_port_id, test_params->slave_port_ids[1]);
3322 
3323 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
3324 			"Failed to get mac address (port %d)",
3325 			test_params->bonded_port_id);
3326 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3327 			sizeof(read_mac_addr)),
3328 			"bonded port (%d) mac address not set to that of primary port",
3329 			test_params->bonded_port_id);
3330 
3331 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
3332 			"Failed to get mac address (port %d)",
3333 			test_params->slave_port_ids[0]);
3334 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3335 			sizeof(read_mac_addr)),
3336 			"slave port (%d) mac address not set to that of primary port",
3337 			test_params->slave_port_ids[0]);
3338 
3339 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
3340 			"Failed to get mac address (port %d)",
3341 			test_params->slave_port_ids[1]);
3342 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3343 			sizeof(read_mac_addr)),
3344 			"slave port (%d) mac address not set to that of primary port",
3345 			test_params->slave_port_ids[1]);
3346 
3347 	/* stop / start bonded device and verify that primary MAC address is
3348 	 * propagated to bonded device and slaves */
3349 
3350 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
3351 			"Failed to stop bonded port %u",
3352 			test_params->bonded_port_id);
3353 
3354 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
3355 			"Failed to start bonded device");
3356 
3357 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
3358 			"Failed to get mac address (port %d)",
3359 			test_params->bonded_port_id);
3360 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
3361 			sizeof(read_mac_addr)),
3362 			"bonded port (%d) mac address not set to that of primary port",
3363 			test_params->bonded_port_id);
3364 
3365 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
3366 			"Failed to get mac address (port %d)",
3367 			test_params->slave_port_ids[0]);
3368 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
3369 			sizeof(read_mac_addr)),
3370 			"slave port (%d) mac address not set to that of primary port",
3371 			test_params->slave_port_ids[0]);
3372 
3373 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
3374 			"Failed to get mac address (port %d)",
3375 			test_params->slave_port_ids[1]);
3376 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
3377 			sizeof(read_mac_addr)),
3378 			"slave port (%d) mac address not set to that of primary port",
3379 			test_params->slave_port_ids[1]);
3380 
3381 	/* Set explicit MAC address */
3382 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_set(
3383 			test_params->bonded_port_id,
3384 			(struct rte_ether_addr *)bonded_mac),
3385 			"failed to set MAC");
3386 
3387 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
3388 			"Failed to get mac address (port %d)",
3389 			test_params->bonded_port_id);
3390 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac, &read_mac_addr,
3391 			sizeof(read_mac_addr)),
3392 			"bonded port (%d) mac address not set to that of bonded port",
3393 			test_params->bonded_port_id);
3394 
3395 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
3396 			"Failed to get mac address (port %d)",
3397 			test_params->slave_port_ids[0]);
3398 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac, &read_mac_addr,
3399 			sizeof(read_mac_addr)),
3400 			"slave port (%d) mac address not as expected\n",
3401 				test_params->slave_port_ids[0]);
3402 
3403 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
3404 			"Failed to get mac address (port %d)",
3405 			test_params->slave_port_ids[1]);
3406 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac, &read_mac_addr,
3407 			sizeof(read_mac_addr)),
3408 			"slave port (%d) mac address not set to that of bonded port",
3409 			test_params->slave_port_ids[1]);
3410 
3411 	/* Clean up and remove slaves from bonded device */
3412 	return remove_slaves_and_stop_bonded_device();
3413 }
3414 
3415 #define TEST_BALANCE_LINK_STATUS_SLAVE_COUNT (4)
3416 
3417 static int
3418 test_balance_verify_slave_link_status_change_behaviour(void)
3419 {
3420 	struct rte_mbuf *pkt_burst[TEST_BALANCE_LINK_STATUS_SLAVE_COUNT][MAX_PKT_BURST];
3421 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
3422 	struct rte_eth_stats port_stats;
3423 
3424 	uint16_t slaves[RTE_MAX_ETHPORTS];
3425 
3426 	int i, burst_size, slave_count;
3427 
3428 	memset(pkt_burst, 0, sizeof(pkt_burst));
3429 
3430 	/* Initialize bonded device with 4 slaves in round robin mode */
3431 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3432 			BONDING_MODE_BALANCE, 0, TEST_BALANCE_LINK_STATUS_SLAVE_COUNT, 1),
3433 			"Failed to initialise bonded device");
3434 
3435 	TEST_ASSERT_SUCCESS(rte_eth_bond_xmit_policy_set(
3436 			test_params->bonded_port_id, BALANCE_XMIT_POLICY_LAYER2),
3437 			"Failed to set balance xmit policy.");
3438 
3439 
3440 	/* Verify Current Slaves Count /Active Slave Count is */
3441 	slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id, slaves,
3442 			RTE_MAX_ETHPORTS);
3443 	TEST_ASSERT_EQUAL(slave_count, TEST_BALANCE_LINK_STATUS_SLAVE_COUNT,
3444 			"Number of slaves (%d) is not as expected (%d).",
3445 			slave_count, TEST_BALANCE_LINK_STATUS_SLAVE_COUNT);
3446 
3447 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
3448 			slaves, RTE_MAX_ETHPORTS);
3449 	TEST_ASSERT_EQUAL(slave_count, TEST_BALANCE_LINK_STATUS_SLAVE_COUNT,
3450 			"Number of active slaves (%d) is not as expected (%d).",
3451 			slave_count, TEST_BALANCE_LINK_STATUS_SLAVE_COUNT);
3452 
3453 	/* Set 2 slaves link status to down */
3454 	virtual_ethdev_simulate_link_status_interrupt(
3455 			test_params->slave_port_ids[1], 0);
3456 	virtual_ethdev_simulate_link_status_interrupt(
3457 			test_params->slave_port_ids[3], 0);
3458 
3459 	TEST_ASSERT_EQUAL(rte_eth_bond_active_slaves_get(
3460 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS), 2,
3461 			"Number of active slaves (%d) is not as expected (%d).",
3462 			slave_count, 2);
3463 
3464 	/* Send to sets of packet burst and verify that they are balanced across
3465 	 *  slaves */
3466 	burst_size = 21;
3467 
3468 	TEST_ASSERT_EQUAL(generate_test_burst(
3469 			&pkt_burst[0][0], burst_size, 0, 1, 0, 0, 0), burst_size,
3470 			"generate_test_burst failed");
3471 
3472 	TEST_ASSERT_EQUAL(generate_test_burst(
3473 			&pkt_burst[1][0], burst_size, 0, 1, 1, 0, 0), burst_size,
3474 			"generate_test_burst failed");
3475 
3476 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
3477 			test_params->bonded_port_id, 0, &pkt_burst[0][0], burst_size),
3478 			burst_size, "rte_eth_tx_burst failed");
3479 
3480 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
3481 			test_params->bonded_port_id, 0, &pkt_burst[1][0], burst_size),
3482 			burst_size, "rte_eth_tx_burst failed");
3483 
3484 
3485 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
3486 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)(burst_size + burst_size),
3487 			"(%d) port_stats.opackets (%d) not as expected (%d).",
3488 			test_params->bonded_port_id, (int)port_stats.opackets,
3489 			burst_size + burst_size);
3490 
3491 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
3492 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
3493 			"(%d) port_stats.opackets (%d) not as expected (%d).",
3494 			test_params->slave_port_ids[0], (int)port_stats.opackets,
3495 			burst_size);
3496 
3497 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
3498 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
3499 			"(%d) port_stats.opackets (%d) not as expected (%d).",
3500 			test_params->slave_port_ids[2], (int)port_stats.opackets,
3501 			burst_size);
3502 
3503 	/* verify that all packets get send on primary slave when no other slaves
3504 	 * are available */
3505 	virtual_ethdev_simulate_link_status_interrupt(
3506 			test_params->slave_port_ids[2], 0);
3507 
3508 	TEST_ASSERT_EQUAL(rte_eth_bond_active_slaves_get(
3509 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS), 1,
3510 			"Number of active slaves (%d) is not as expected (%d).",
3511 			slave_count, 1);
3512 
3513 	TEST_ASSERT_EQUAL(generate_test_burst(
3514 			&pkt_burst[1][0], burst_size, 0, 1, 1, 0, 0), burst_size,
3515 			"generate_test_burst failed");
3516 
3517 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
3518 			test_params->bonded_port_id, 0, &pkt_burst[1][0], burst_size),
3519 			burst_size, "rte_eth_tx_burst failed");
3520 
3521 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
3522 	TEST_ASSERT_EQUAL(port_stats.opackets,
3523 			(uint64_t)(burst_size + burst_size + burst_size),
3524 			"(%d) port_stats.opackets (%d) not as expected (%d).\n",
3525 			test_params->bonded_port_id, (int)port_stats.opackets,
3526 			burst_size + burst_size + burst_size);
3527 
3528 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
3529 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)(burst_size + burst_size),
3530 			"(%d) port_stats.opackets (%d) not as expected (%d).",
3531 			test_params->slave_port_ids[0], (int)port_stats.opackets,
3532 			burst_size + burst_size);
3533 
3534 	virtual_ethdev_simulate_link_status_interrupt(
3535 			test_params->slave_port_ids[0], 0);
3536 	virtual_ethdev_simulate_link_status_interrupt(
3537 			test_params->slave_port_ids[1], 1);
3538 	virtual_ethdev_simulate_link_status_interrupt(
3539 			test_params->slave_port_ids[2], 1);
3540 	virtual_ethdev_simulate_link_status_interrupt(
3541 			test_params->slave_port_ids[3], 1);
3542 
3543 	for (i = 0; i < TEST_BALANCE_LINK_STATUS_SLAVE_COUNT; i++) {
3544 		TEST_ASSERT_EQUAL(generate_test_burst(
3545 				&pkt_burst[i][0], burst_size, 0, 1, 0, 0, 0), burst_size,
3546 				"Failed to generate packet burst");
3547 
3548 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
3549 				&pkt_burst[i][0], burst_size);
3550 	}
3551 
3552 	/* Verify that pkts are not received on slaves with link status down */
3553 
3554 	rte_eth_rx_burst(test_params->bonded_port_id, 0, rx_pkt_burst,
3555 			MAX_PKT_BURST);
3556 
3557 	/* Verify bonded device rx count */
3558 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
3559 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)(burst_size * 3),
3560 			"(%d) port_stats.ipackets (%d) not as expected (%d)\n",
3561 			test_params->bonded_port_id, (int)port_stats.ipackets,
3562 			burst_size * 3);
3563 
3564 	/* Clean up and remove slaves from bonded device */
3565 	return remove_slaves_and_stop_bonded_device();
3566 }
3567 
3568 static int
3569 test_broadcast_tx_burst(void)
3570 {
3571 	int i, pktlen, burst_size;
3572 	struct rte_mbuf *pkts_burst[MAX_PKT_BURST];
3573 
3574 	struct rte_eth_stats port_stats;
3575 
3576 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3577 			BONDING_MODE_BROADCAST, 0, 2, 1),
3578 			"Failed to initialise bonded device");
3579 
3580 	initialize_eth_header(test_params->pkt_eth_hdr,
3581 			(struct rte_ether_addr *)src_mac,
3582 			(struct rte_ether_addr *)dst_mac_0,
3583 			RTE_ETHER_TYPE_IPV4, 0, 0);
3584 
3585 	pktlen = initialize_udp_header(test_params->pkt_udp_hdr, src_port,
3586 			dst_port_0, 16);
3587 	pktlen = initialize_ipv4_header(test_params->pkt_ipv4_hdr, src_addr,
3588 			dst_addr_0, pktlen);
3589 
3590 	burst_size = 20 * test_params->bonded_slave_count;
3591 
3592 	TEST_ASSERT(burst_size < MAX_PKT_BURST,
3593 			"Burst size specified is greater than supported.");
3594 
3595 	/* Generate a burst of packets to transmit */
3596 	TEST_ASSERT_EQUAL(generate_packet_burst(test_params->mbuf_pool,
3597 			pkts_burst,	test_params->pkt_eth_hdr, 0, test_params->pkt_ipv4_hdr,
3598 			1, test_params->pkt_udp_hdr, burst_size, PACKET_BURST_GEN_PKT_LEN,
3599 			1), burst_size, "Failed to generate packet burst");
3600 
3601 	/* Send burst on bonded port */
3602 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(test_params->bonded_port_id, 0,
3603 			pkts_burst, burst_size), burst_size,
3604 			"Bonded Port (%d) rx burst failed, packets transmitted value "
3605 			"not as expected (%d)",
3606 			test_params->bonded_port_id, burst_size);
3607 
3608 	/* Verify bonded port tx stats */
3609 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
3610 	TEST_ASSERT_EQUAL(port_stats.opackets,
3611 			(uint64_t)burst_size * test_params->bonded_slave_count,
3612 			"Bonded Port (%d) opackets value (%u) not as expected (%d)",
3613 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
3614 			burst_size);
3615 
3616 	/* Verify slave ports tx stats */
3617 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3618 		rte_eth_stats_get(test_params->slave_port_ids[i], &port_stats);
3619 		TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
3620 				"Slave Port (%d) opackets value (%u) not as expected (%d)\n",
3621 				test_params->bonded_port_id,
3622 				(unsigned int)port_stats.opackets, burst_size);
3623 	}
3624 
3625 	/* Put all slaves down and try and transmit */
3626 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3627 
3628 		virtual_ethdev_simulate_link_status_interrupt(
3629 				test_params->slave_port_ids[i], 0);
3630 	}
3631 
3632 	/* Send burst on bonded port */
3633 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(
3634 			test_params->bonded_port_id, 0, pkts_burst, burst_size),  0,
3635 			"transmitted an unexpected number of packets");
3636 
3637 	/* Clean up and remove slaves from bonded device */
3638 	return remove_slaves_and_stop_bonded_device();
3639 }
3640 
3641 
3642 #define TEST_BCAST_SLAVE_TX_FAIL_SLAVE_COUNT		(3)
3643 #define TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE			(40)
3644 #define TEST_BCAST_SLAVE_TX_FAIL_MAX_PACKETS_COUNT	(15)
3645 #define TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT	(10)
3646 
3647 static int
3648 test_broadcast_tx_burst_slave_tx_fail(void)
3649 {
3650 	struct rte_mbuf *pkts_burst[TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE];
3651 	struct rte_mbuf *expected_fail_pkts[TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT];
3652 
3653 	struct rte_eth_stats port_stats;
3654 
3655 	int i, tx_count;
3656 
3657 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3658 			BONDING_MODE_BROADCAST, 0,
3659 			TEST_BCAST_SLAVE_TX_FAIL_SLAVE_COUNT, 1),
3660 			"Failed to initialise bonded device");
3661 
3662 	/* Generate test bursts for transmission */
3663 	TEST_ASSERT_EQUAL(generate_test_burst(pkts_burst,
3664 			TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE, 0, 0, 0, 0, 0),
3665 			TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE,
3666 			"Failed to generate test packet burst");
3667 
3668 	for (i = 0; i < TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT; i++) {
3669 		expected_fail_pkts[i] = pkts_burst[TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3670 			TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT + i];
3671 	}
3672 
3673 	/* Set virtual slave TEST_BAL_SLAVE_TX_FAIL_FAILING_SLAVE_IDX to only fail
3674 	 * transmission of TEST_BAL_SLAVE_TX_FAIL_PACKETS_COUNT packets of burst */
3675 	virtual_ethdev_tx_burst_fn_set_success(
3676 			test_params->slave_port_ids[0],
3677 			0);
3678 	virtual_ethdev_tx_burst_fn_set_success(
3679 			test_params->slave_port_ids[1],
3680 			0);
3681 	virtual_ethdev_tx_burst_fn_set_success(
3682 			test_params->slave_port_ids[2],
3683 			0);
3684 
3685 	virtual_ethdev_tx_burst_fn_set_tx_pkt_fail_count(
3686 			test_params->slave_port_ids[0],
3687 			TEST_BCAST_SLAVE_TX_FAIL_MAX_PACKETS_COUNT);
3688 
3689 	virtual_ethdev_tx_burst_fn_set_tx_pkt_fail_count(
3690 			test_params->slave_port_ids[1],
3691 			TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT);
3692 
3693 	virtual_ethdev_tx_burst_fn_set_tx_pkt_fail_count(
3694 			test_params->slave_port_ids[2],
3695 			TEST_BCAST_SLAVE_TX_FAIL_MAX_PACKETS_COUNT);
3696 
3697 	/* Transmit burst */
3698 	tx_count = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkts_burst,
3699 			TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE);
3700 
3701 	TEST_ASSERT_EQUAL(tx_count, TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3702 			TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT,
3703 			"Transmitted (%d) packets, expected to transmit (%d) packets",
3704 			tx_count, TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3705 			TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT);
3706 
3707 	/* Verify that failed packet are expected failed packets */
3708 	for (i = 0; i < TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT; i++) {
3709 		TEST_ASSERT_EQUAL(expected_fail_pkts[i], pkts_burst[i + tx_count],
3710 				"expected mbuf (%d) pointer %p not expected pointer %p",
3711 				i, expected_fail_pkts[i], pkts_burst[i + tx_count]);
3712 	}
3713 
3714 	/* Verify slave ports tx stats */
3715 
3716 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
3717 
3718 	TEST_ASSERT_EQUAL(port_stats.opackets,
3719 			(uint64_t)TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3720 			TEST_BCAST_SLAVE_TX_FAIL_MAX_PACKETS_COUNT,
3721 			"Port (%d) opackets value (%u) not as expected (%d)",
3722 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
3723 			TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3724 			TEST_BCAST_SLAVE_TX_FAIL_MAX_PACKETS_COUNT);
3725 
3726 
3727 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
3728 
3729 	TEST_ASSERT_EQUAL(port_stats.opackets,
3730 			(uint64_t)TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3731 			TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT,
3732 			"Port (%d) opackets value (%u) not as expected (%d)",
3733 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
3734 			TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3735 			TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT);
3736 
3737 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
3738 
3739 	TEST_ASSERT_EQUAL(port_stats.opackets,
3740 			(uint64_t)TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3741 			TEST_BCAST_SLAVE_TX_FAIL_MAX_PACKETS_COUNT,
3742 			"Port (%d) opackets value (%u) not as expected (%d)",
3743 			test_params->bonded_port_id, (unsigned int)port_stats.opackets,
3744 			TEST_BCAST_SLAVE_TX_FAIL_BURST_SIZE -
3745 			TEST_BCAST_SLAVE_TX_FAIL_MAX_PACKETS_COUNT);
3746 
3747 
3748 	/* Verify that all mbufs who transmission failed have a ref value of one */
3749 	TEST_ASSERT_SUCCESS(verify_mbufs_ref_count(&pkts_burst[tx_count],
3750 			TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT, 1),
3751 			"mbufs refcnts not as expected");
3752 
3753 	free_mbufs(&pkts_burst[tx_count],
3754 		TEST_BCAST_SLAVE_TX_FAIL_MIN_PACKETS_COUNT);
3755 
3756 	/* Clean up and remove slaves from bonded device */
3757 	return remove_slaves_and_stop_bonded_device();
3758 }
3759 
3760 #define BROADCAST_RX_BURST_NUM_OF_SLAVES (3)
3761 
3762 static int
3763 test_broadcast_rx_burst(void)
3764 {
3765 	struct rte_mbuf *gen_pkt_burst[BROADCAST_RX_BURST_NUM_OF_SLAVES][MAX_PKT_BURST];
3766 
3767 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
3768 	struct rte_eth_stats port_stats;
3769 
3770 	int burst_size[BROADCAST_RX_BURST_NUM_OF_SLAVES] = { 10, 5, 30 };
3771 	int i, j;
3772 
3773 	memset(gen_pkt_burst, 0, sizeof(gen_pkt_burst));
3774 
3775 	/* Initialize bonded device with 4 slaves in round robin mode */
3776 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3777 			BONDING_MODE_BROADCAST, 0, 3, 1),
3778 			"Failed to initialise bonded device");
3779 
3780 	/* Generate test bursts of packets to transmit */
3781 	for (i = 0; i < BROADCAST_RX_BURST_NUM_OF_SLAVES; i++) {
3782 		TEST_ASSERT_EQUAL(generate_test_burst(
3783 				&gen_pkt_burst[i][0], burst_size[i], 0, 0, 1, 0, 0),
3784 				burst_size[i], "failed to generate packet burst");
3785 	}
3786 
3787 	/* Add rx data to slave 0 */
3788 	for (i = 0; i < BROADCAST_RX_BURST_NUM_OF_SLAVES; i++) {
3789 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
3790 				&gen_pkt_burst[i][0], burst_size[i]);
3791 	}
3792 
3793 
3794 	/* Call rx burst on bonded device */
3795 	/* Send burst on bonded port */
3796 	TEST_ASSERT_EQUAL(rte_eth_rx_burst(
3797 			test_params->bonded_port_id, 0, rx_pkt_burst, MAX_PKT_BURST),
3798 			burst_size[0] + burst_size[1] + burst_size[2],
3799 			"rx burst failed");
3800 
3801 	/* Verify bonded device rx count */
3802 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
3803 	TEST_ASSERT_EQUAL(port_stats.ipackets,
3804 			(uint64_t)(burst_size[0] + burst_size[1] + burst_size[2]),
3805 			"Bonded Port (%d) ipackets value (%u) not as expected (%d)",
3806 			test_params->bonded_port_id, (unsigned int)port_stats.ipackets,
3807 			burst_size[0] + burst_size[1] + burst_size[2]);
3808 
3809 
3810 	/* Verify bonded slave devices rx counts */
3811 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
3812 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[0],
3813 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3814 			test_params->slave_port_ids[0], (unsigned int)port_stats.ipackets,
3815 			burst_size[0]);
3816 
3817 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
3818 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[1],
3819 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3820 			test_params->slave_port_ids[0], (unsigned int)port_stats.ipackets,
3821 			burst_size[1]);
3822 
3823 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
3824 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size[2],
3825 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3826 			test_params->slave_port_ids[2], (unsigned int)port_stats.ipackets,
3827 			burst_size[2]);
3828 
3829 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
3830 	TEST_ASSERT_EQUAL(port_stats.ipackets, 0,
3831 			"Slave Port (%d) ipackets value (%u) not as expected (%d)",
3832 			test_params->slave_port_ids[3], (unsigned int)port_stats.ipackets,
3833 			0);
3834 
3835 	/* free mbufs allocate for rx testing */
3836 	for (i = 0; i < BROADCAST_RX_BURST_NUM_OF_SLAVES; i++) {
3837 		for (j = 0; j < MAX_PKT_BURST; j++) {
3838 			if (gen_pkt_burst[i][j] != NULL) {
3839 				rte_pktmbuf_free(gen_pkt_burst[i][j]);
3840 				gen_pkt_burst[i][j] = NULL;
3841 			}
3842 		}
3843 	}
3844 
3845 	/* Clean up and remove slaves from bonded device */
3846 	return remove_slaves_and_stop_bonded_device();
3847 }
3848 
3849 static int
3850 test_broadcast_verify_promiscuous_enable_disable(void)
3851 {
3852 	int i;
3853 	int ret;
3854 
3855 	/* Initialize bonded device with 4 slaves in round robin mode */
3856 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3857 			BONDING_MODE_BROADCAST, 0, 4, 1),
3858 			"Failed to initialise bonded device");
3859 
3860 	ret = rte_eth_promiscuous_enable(test_params->bonded_port_id);
3861 	TEST_ASSERT_SUCCESS(ret,
3862 		"Failed to enable promiscuous mode for port %d: %s",
3863 		test_params->bonded_port_id, rte_strerror(-ret));
3864 
3865 
3866 	TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(test_params->bonded_port_id), 1,
3867 			"Port (%d) promiscuous mode not enabled",
3868 			test_params->bonded_port_id);
3869 
3870 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3871 		TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(
3872 				test_params->slave_port_ids[i]), 1,
3873 				"Port (%d) promiscuous mode not enabled",
3874 				test_params->slave_port_ids[i]);
3875 	}
3876 
3877 	ret = rte_eth_promiscuous_disable(test_params->bonded_port_id);
3878 	TEST_ASSERT_SUCCESS(ret,
3879 		"Failed to disable promiscuous mode for port %d: %s",
3880 		test_params->bonded_port_id, rte_strerror(-ret));
3881 
3882 	TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(test_params->bonded_port_id), 0,
3883 			"Port (%d) promiscuous mode not disabled",
3884 			test_params->bonded_port_id);
3885 
3886 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3887 		TEST_ASSERT_EQUAL(rte_eth_promiscuous_get(
3888 				test_params->slave_port_ids[i]), 0,
3889 				"Port (%d) promiscuous mode not disabled",
3890 				test_params->slave_port_ids[i]);
3891 	}
3892 
3893 	/* Clean up and remove slaves from bonded device */
3894 	return remove_slaves_and_stop_bonded_device();
3895 }
3896 
3897 static int
3898 test_broadcast_verify_mac_assignment(void)
3899 {
3900 	struct rte_ether_addr read_mac_addr;
3901 	struct rte_ether_addr expected_mac_addr_0, expected_mac_addr_1;
3902 
3903 	int i;
3904 
3905 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &expected_mac_addr_0),
3906 			"Failed to get mac address (port %d)",
3907 			test_params->slave_port_ids[0]);
3908 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[2], &expected_mac_addr_1),
3909 			"Failed to get mac address (port %d)",
3910 			test_params->slave_port_ids[2]);
3911 
3912 	/* Initialize bonded device with 4 slaves in round robin mode */
3913 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
3914 			BONDING_MODE_BROADCAST, 0, 4, 1),
3915 			"Failed to initialise bonded device");
3916 
3917 	/* Verify that all MACs are the same as first slave added to bonded
3918 	 * device */
3919 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3920 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
3921 				"Failed to get mac address (port %d)",
3922 				test_params->slave_port_ids[i]);
3923 		TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3924 				sizeof(read_mac_addr)),
3925 				"slave port (%d) mac address not set to that of primary port",
3926 				test_params->slave_port_ids[i]);
3927 	}
3928 
3929 	/* change primary and verify that MAC addresses haven't changed */
3930 	TEST_ASSERT_SUCCESS(rte_eth_bond_primary_set(test_params->bonded_port_id,
3931 			test_params->slave_port_ids[2]),
3932 			"Failed to set bonded port (%d) primary port to (%d)",
3933 			test_params->bonded_port_id, test_params->slave_port_ids[i]);
3934 
3935 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3936 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
3937 				"Failed to get mac address (port %d)",
3938 				test_params->slave_port_ids[i]);
3939 		TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
3940 				sizeof(read_mac_addr)),
3941 				"slave port (%d) mac address has changed to that of primary "
3942 				"port without stop/start toggle of bonded device",
3943 				test_params->slave_port_ids[i]);
3944 	}
3945 
3946 	/* stop / start bonded device and verify that primary MAC address is
3947 	 * propagated to bonded device and slaves */
3948 
3949 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
3950 			"Failed to stop bonded port %u",
3951 			test_params->bonded_port_id);
3952 
3953 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
3954 			"Failed to start bonded device");
3955 
3956 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
3957 			"Failed to get mac address (port %d)",
3958 			test_params->bonded_port_id);
3959 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
3960 			sizeof(read_mac_addr)),
3961 			"bonded port (%d) mac address not set to that of new primary  port",
3962 			test_params->slave_port_ids[i]);
3963 
3964 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3965 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
3966 				"Failed to get mac address (port %d)",
3967 				test_params->slave_port_ids[i]);
3968 		TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
3969 				sizeof(read_mac_addr)),
3970 				"slave port (%d) mac address not set to that of new primary "
3971 				"port", test_params->slave_port_ids[i]);
3972 	}
3973 
3974 	/* Set explicit MAC address */
3975 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_set(
3976 			test_params->bonded_port_id,
3977 			(struct rte_ether_addr *)bonded_mac),
3978 			"Failed to set MAC address");
3979 
3980 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
3981 			"Failed to get mac address (port %d)",
3982 			test_params->bonded_port_id);
3983 	TEST_ASSERT_SUCCESS(memcmp(bonded_mac, &read_mac_addr,
3984 			sizeof(read_mac_addr)),
3985 			"bonded port (%d) mac address not set to that of new primary port",
3986 			test_params->slave_port_ids[i]);
3987 
3988 
3989 	for (i = 0; i < test_params->bonded_slave_count; i++) {
3990 		TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[i], &read_mac_addr),
3991 				"Failed to get mac address (port %d)",
3992 				test_params->slave_port_ids[i]);
3993 		TEST_ASSERT_SUCCESS(memcmp(bonded_mac, &read_mac_addr,
3994 				sizeof(read_mac_addr)),
3995 				"slave port (%d) mac address not set to that of new primary "
3996 				"port", test_params->slave_port_ids[i]);
3997 	}
3998 
3999 	/* Clean up and remove slaves from bonded device */
4000 	return remove_slaves_and_stop_bonded_device();
4001 }
4002 
4003 #define BROADCAST_LINK_STATUS_NUM_OF_SLAVES (4)
4004 static int
4005 test_broadcast_verify_slave_link_status_change_behaviour(void)
4006 {
4007 	struct rte_mbuf *pkt_burst[BROADCAST_LINK_STATUS_NUM_OF_SLAVES][MAX_PKT_BURST];
4008 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
4009 	struct rte_eth_stats port_stats;
4010 
4011 	uint16_t slaves[RTE_MAX_ETHPORTS];
4012 
4013 	int i, burst_size, slave_count;
4014 
4015 	memset(pkt_burst, 0, sizeof(pkt_burst));
4016 
4017 	/* Initialize bonded device with 4 slaves in round robin mode */
4018 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
4019 				BONDING_MODE_BROADCAST, 0, BROADCAST_LINK_STATUS_NUM_OF_SLAVES,
4020 				1), "Failed to initialise bonded device");
4021 
4022 	/* Verify Current Slaves Count /Active Slave Count is */
4023 	slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id, slaves,
4024 			RTE_MAX_ETHPORTS);
4025 	TEST_ASSERT_EQUAL(slave_count, 4,
4026 			"Number of slaves (%d) is not as expected (%d).",
4027 			slave_count, 4);
4028 
4029 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
4030 			slaves, RTE_MAX_ETHPORTS);
4031 	TEST_ASSERT_EQUAL(slave_count, 4,
4032 			"Number of active slaves (%d) is not as expected (%d).",
4033 			slave_count, 4);
4034 
4035 	/* Set 2 slaves link status to down */
4036 	virtual_ethdev_simulate_link_status_interrupt(
4037 			test_params->slave_port_ids[1], 0);
4038 	virtual_ethdev_simulate_link_status_interrupt(
4039 			test_params->slave_port_ids[3], 0);
4040 
4041 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
4042 			slaves, RTE_MAX_ETHPORTS);
4043 	TEST_ASSERT_EQUAL(slave_count, 2,
4044 			"Number of active slaves (%d) is not as expected (%d).",
4045 			slave_count, 2);
4046 
4047 	for (i = 0; i < test_params->bonded_slave_count; i++)
4048 		rte_eth_stats_reset(test_params->slave_port_ids[i]);
4049 
4050 	/* Verify that pkts are not sent on slaves with link status down */
4051 	burst_size = 21;
4052 
4053 	TEST_ASSERT_EQUAL(generate_test_burst(
4054 			&pkt_burst[0][0], burst_size, 0, 0, 1, 0, 0), burst_size,
4055 			"generate_test_burst failed");
4056 
4057 	TEST_ASSERT_EQUAL(rte_eth_tx_burst(test_params->bonded_port_id, 0,
4058 			&pkt_burst[0][0], burst_size), burst_size,
4059 			"rte_eth_tx_burst failed\n");
4060 
4061 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
4062 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)(burst_size * slave_count),
4063 			"(%d) port_stats.opackets (%d) not as expected (%d)\n",
4064 			test_params->bonded_port_id, (int)port_stats.opackets,
4065 			burst_size * slave_count);
4066 
4067 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
4068 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
4069 			"(%d) port_stats.opackets not as expected",
4070 			test_params->slave_port_ids[0]);
4071 
4072 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
4073 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
4074 			"(%d) port_stats.opackets not as expected",
4075 				test_params->slave_port_ids[1]);
4076 
4077 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
4078 	TEST_ASSERT_EQUAL(port_stats.opackets, (uint64_t)burst_size,
4079 			"(%d) port_stats.opackets not as expected",
4080 				test_params->slave_port_ids[2]);
4081 
4082 
4083 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
4084 	TEST_ASSERT_EQUAL(port_stats.opackets, 0,
4085 			"(%d) port_stats.opackets not as expected",
4086 			test_params->slave_port_ids[3]);
4087 
4088 
4089 	for (i = 0; i < BROADCAST_LINK_STATUS_NUM_OF_SLAVES; i++) {
4090 		TEST_ASSERT_EQUAL(generate_test_burst(
4091 				&pkt_burst[i][0], burst_size, 0, 0, 1, 0, 0),
4092 				burst_size, "failed to generate packet burst");
4093 
4094 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
4095 				&pkt_burst[i][0], burst_size);
4096 	}
4097 
4098 	/* Verify that pkts are not received on slaves with link status down */
4099 	TEST_ASSERT_EQUAL(rte_eth_rx_burst(
4100 			test_params->bonded_port_id, 0, rx_pkt_burst, MAX_PKT_BURST),
4101 			burst_size + burst_size, "rte_eth_rx_burst failed");
4102 
4103 
4104 	/* Verify bonded device rx count */
4105 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
4106 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)(burst_size + burst_size),
4107 			"(%d) port_stats.ipackets not as expected\n",
4108 			test_params->bonded_port_id);
4109 
4110 	/* Clean up and remove slaves from bonded device */
4111 	return remove_slaves_and_stop_bonded_device();
4112 }
4113 
4114 static int
4115 test_reconfigure_bonded_device(void)
4116 {
4117 	test_params->nb_rx_q = 4;
4118 	test_params->nb_tx_q = 4;
4119 
4120 	TEST_ASSERT_SUCCESS(configure_ethdev(test_params->bonded_port_id, 0, 0),
4121 			"failed to reconfigure bonded device");
4122 
4123 	test_params->nb_rx_q = 2;
4124 	test_params->nb_tx_q = 2;
4125 
4126 	TEST_ASSERT_SUCCESS(configure_ethdev(test_params->bonded_port_id, 0, 0),
4127 			"failed to reconfigure bonded device with less rx/tx queues");
4128 
4129 	return 0;
4130 }
4131 
4132 
4133 static int
4134 test_close_bonded_device(void)
4135 {
4136 	rte_eth_dev_close(test_params->bonded_port_id);
4137 	return 0;
4138 }
4139 
4140 static void
4141 testsuite_teardown(void)
4142 {
4143 	free(test_params->pkt_eth_hdr);
4144 	test_params->pkt_eth_hdr = NULL;
4145 
4146 	/* Clean up and remove slaves from bonded device */
4147 	remove_slaves_and_stop_bonded_device();
4148 }
4149 
4150 static void
4151 free_virtualpmd_tx_queue(void)
4152 {
4153 	int i, slave_port, to_free_cnt;
4154 	struct rte_mbuf *pkts_to_free[MAX_PKT_BURST];
4155 
4156 	/* Free tx queue of virtual pmd */
4157 	for (slave_port = 0; slave_port < test_params->bonded_slave_count;
4158 			slave_port++) {
4159 		to_free_cnt = virtual_ethdev_get_mbufs_from_tx_queue(
4160 				test_params->slave_port_ids[slave_port],
4161 				pkts_to_free, MAX_PKT_BURST);
4162 		for (i = 0; i < to_free_cnt; i++)
4163 			rte_pktmbuf_free(pkts_to_free[i]);
4164 	}
4165 }
4166 
4167 static int
4168 test_tlb_tx_burst(void)
4169 {
4170 	int i, burst_size, nb_tx;
4171 	uint64_t nb_tx2 = 0;
4172 	struct rte_mbuf *pkt_burst[MAX_PKT_BURST];
4173 	struct rte_eth_stats port_stats[32];
4174 	uint64_t sum_ports_opackets = 0, all_bond_opackets = 0, all_bond_obytes = 0;
4175 	uint16_t pktlen;
4176 
4177 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves
4178 			(BONDING_MODE_TLB, 1, 3, 1),
4179 			"Failed to initialise bonded device");
4180 
4181 	burst_size = 20 * test_params->bonded_slave_count;
4182 
4183 	TEST_ASSERT(burst_size < MAX_PKT_BURST,
4184 			"Burst size specified is greater than supported.\n");
4185 
4186 
4187 	/* Generate bursts of packets */
4188 	for (i = 0; i < 400000; i++) {
4189 		/*test two types of mac src own(bonding) and others */
4190 		if (i % 2 == 0) {
4191 			initialize_eth_header(test_params->pkt_eth_hdr,
4192 					(struct rte_ether_addr *)src_mac,
4193 					(struct rte_ether_addr *)dst_mac_0,
4194 					RTE_ETHER_TYPE_IPV4, 0, 0);
4195 		} else {
4196 			initialize_eth_header(test_params->pkt_eth_hdr,
4197 					(struct rte_ether_addr *)test_params->default_slave_mac,
4198 					(struct rte_ether_addr *)dst_mac_0,
4199 					RTE_ETHER_TYPE_IPV4, 0, 0);
4200 		}
4201 		pktlen = initialize_udp_header(test_params->pkt_udp_hdr, src_port,
4202 				dst_port_0, 16);
4203 		pktlen = initialize_ipv4_header(test_params->pkt_ipv4_hdr, src_addr,
4204 				dst_addr_0, pktlen);
4205 		generate_packet_burst(test_params->mbuf_pool, pkt_burst,
4206 				test_params->pkt_eth_hdr, 0, test_params->pkt_ipv4_hdr,
4207 				1, test_params->pkt_udp_hdr, burst_size, 60, 1);
4208 		/* Send burst on bonded port */
4209 		nb_tx = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkt_burst,
4210 				burst_size);
4211 		nb_tx2 += nb_tx;
4212 
4213 		free_virtualpmd_tx_queue();
4214 
4215 		TEST_ASSERT_EQUAL(nb_tx, burst_size,
4216 				"number of packet not equal burst size");
4217 
4218 		rte_delay_us(5);
4219 	}
4220 
4221 
4222 	/* Verify bonded port tx stats */
4223 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats[0]);
4224 
4225 	all_bond_opackets = port_stats[0].opackets;
4226 	all_bond_obytes = port_stats[0].obytes;
4227 
4228 	TEST_ASSERT_EQUAL(port_stats[0].opackets, (uint64_t)nb_tx2,
4229 			"Bonded Port (%d) opackets value (%u) not as expected (%d)\n",
4230 			test_params->bonded_port_id, (unsigned int)port_stats[0].opackets,
4231 			burst_size);
4232 
4233 
4234 	/* Verify slave ports tx stats */
4235 	for (i = 0; i < test_params->bonded_slave_count; i++) {
4236 		rte_eth_stats_get(test_params->slave_port_ids[i], &port_stats[i]);
4237 		sum_ports_opackets += port_stats[i].opackets;
4238 	}
4239 
4240 	TEST_ASSERT_EQUAL(sum_ports_opackets, (uint64_t)all_bond_opackets,
4241 			"Total packets sent by slaves is not equal to packets sent by bond interface");
4242 
4243 	/* checking if distribution of packets is balanced over slaves */
4244 	for (i = 0; i < test_params->bonded_slave_count; i++) {
4245 		TEST_ASSERT(port_stats[i].obytes > 0 &&
4246 				port_stats[i].obytes < all_bond_obytes,
4247 						"Packets are not balanced over slaves");
4248 	}
4249 
4250 	/* Put all slaves down and try and transmit */
4251 	for (i = 0; i < test_params->bonded_slave_count; i++) {
4252 		virtual_ethdev_simulate_link_status_interrupt(
4253 				test_params->slave_port_ids[i], 0);
4254 	}
4255 
4256 	/* Send burst on bonded port */
4257 	nb_tx = rte_eth_tx_burst(test_params->bonded_port_id, 0, pkt_burst,
4258 			burst_size);
4259 	TEST_ASSERT_EQUAL(nb_tx, 0, " bad number of packet in burst");
4260 
4261 	/* Clean ugit checkout masterp and remove slaves from bonded device */
4262 	return remove_slaves_and_stop_bonded_device();
4263 }
4264 
4265 #define TEST_ADAPTIVE_TRANSMIT_LOAD_BALANCING_RX_BURST_SLAVE_COUNT (4)
4266 
4267 static int
4268 test_tlb_rx_burst(void)
4269 {
4270 	struct rte_mbuf *gen_pkt_burst[MAX_PKT_BURST] = { NULL };
4271 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
4272 
4273 	struct rte_eth_stats port_stats;
4274 
4275 	int primary_port;
4276 
4277 	uint16_t i, j, nb_rx, burst_size = 17;
4278 
4279 	/* Initialize bonded device with 4 slaves in transmit load balancing mode */
4280 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
4281 			BONDING_MODE_TLB,
4282 			TEST_ADAPTIVE_TRANSMIT_LOAD_BALANCING_RX_BURST_SLAVE_COUNT, 1, 1),
4283 			"Failed to initialize bonded device");
4284 
4285 
4286 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
4287 	TEST_ASSERT(primary_port >= 0,
4288 			"failed to get primary slave for bonded port (%d)",
4289 			test_params->bonded_port_id);
4290 
4291 	for (i = 0; i < test_params->bonded_slave_count; i++) {
4292 		/* Generate test bursts of packets to transmit */
4293 		TEST_ASSERT_EQUAL(generate_test_burst(
4294 				&gen_pkt_burst[0], burst_size, 0, 1, 0, 0, 0), burst_size,
4295 				"burst generation failed");
4296 
4297 		/* Add rx data to slave */
4298 		virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[i],
4299 				&gen_pkt_burst[0], burst_size);
4300 
4301 		/* Call rx burst on bonded device */
4302 		nb_rx = rte_eth_rx_burst(test_params->bonded_port_id, 0,
4303 				&rx_pkt_burst[0], MAX_PKT_BURST);
4304 
4305 		TEST_ASSERT_EQUAL(nb_rx, burst_size, "rte_eth_rx_burst failed\n");
4306 
4307 		if (test_params->slave_port_ids[i] == primary_port) {
4308 			/* Verify bonded device rx count */
4309 			rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
4310 			TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
4311 					"Bonded Port (%d) ipackets value (%u) not as expected (%d)\n",
4312 					test_params->bonded_port_id,
4313 					(unsigned int)port_stats.ipackets, burst_size);
4314 
4315 			/* Verify bonded slave devices rx count */
4316 			for (j = 0; j < test_params->bonded_slave_count; j++) {
4317 				rte_eth_stats_get(test_params->slave_port_ids[j], &port_stats);
4318 				if (i == j) {
4319 					TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
4320 							"Slave Port (%d) ipackets value (%u) not as expected (%d)\n",
4321 							test_params->slave_port_ids[i],
4322 							(unsigned int)port_stats.ipackets, burst_size);
4323 				} else {
4324 					TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)0,
4325 							"Slave Port (%d) ipackets value (%u) not as expected (%d)\n",
4326 							test_params->slave_port_ids[i],
4327 							(unsigned int)port_stats.ipackets, 0);
4328 				}
4329 			}
4330 		} else {
4331 			for (j = 0; j < test_params->bonded_slave_count; j++) {
4332 				rte_eth_stats_get(test_params->slave_port_ids[j], &port_stats);
4333 				TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)0,
4334 						"Slave Port (%d) ipackets value (%u) not as expected (%d)\n",
4335 						test_params->slave_port_ids[i],
4336 						(unsigned int)port_stats.ipackets, 0);
4337 			}
4338 		}
4339 
4340 		/* free mbufs */
4341 		for (i = 0; i < burst_size; i++)
4342 			rte_pktmbuf_free(rx_pkt_burst[i]);
4343 
4344 		/* reset bonded device stats */
4345 		rte_eth_stats_reset(test_params->bonded_port_id);
4346 	}
4347 
4348 	/* Clean up and remove slaves from bonded device */
4349 	return remove_slaves_and_stop_bonded_device();
4350 }
4351 
4352 static int
4353 test_tlb_verify_promiscuous_enable_disable(void)
4354 {
4355 	int i, primary_port, promiscuous_en;
4356 	int ret;
4357 
4358 	/* Initialize bonded device with 4 slaves in transmit load balancing mode */
4359 	TEST_ASSERT_SUCCESS( initialize_bonded_device_with_slaves(
4360 			BONDING_MODE_TLB, 0, 4, 1),
4361 			"Failed to initialize bonded device");
4362 
4363 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
4364 	TEST_ASSERT(primary_port >= 0,
4365 			"failed to get primary slave for bonded port (%d)",
4366 			test_params->bonded_port_id);
4367 
4368 	ret = rte_eth_promiscuous_enable(test_params->bonded_port_id);
4369 	TEST_ASSERT_SUCCESS(ret,
4370 		"Failed to enable promiscuous mode for port %d: %s",
4371 		test_params->bonded_port_id, rte_strerror(-ret));
4372 
4373 	promiscuous_en = rte_eth_promiscuous_get(test_params->bonded_port_id);
4374 	TEST_ASSERT_EQUAL(promiscuous_en, (int)1,
4375 			"Port (%d) promiscuous mode not enabled\n",
4376 			test_params->bonded_port_id);
4377 	for (i = 0; i < test_params->bonded_slave_count; i++) {
4378 		promiscuous_en = rte_eth_promiscuous_get(
4379 				test_params->slave_port_ids[i]);
4380 		if (primary_port == test_params->slave_port_ids[i]) {
4381 			TEST_ASSERT_EQUAL(promiscuous_en, (int)1,
4382 					"Port (%d) promiscuous mode not enabled\n",
4383 					test_params->bonded_port_id);
4384 		} else {
4385 			TEST_ASSERT_EQUAL(promiscuous_en, (int)0,
4386 					"Port (%d) promiscuous mode enabled\n",
4387 					test_params->bonded_port_id);
4388 		}
4389 
4390 	}
4391 
4392 	ret = rte_eth_promiscuous_disable(test_params->bonded_port_id);
4393 	TEST_ASSERT_SUCCESS(ret,
4394 		"Failed to disable promiscuous mode for port %d: %s\n",
4395 		test_params->bonded_port_id, rte_strerror(-ret));
4396 
4397 	promiscuous_en = rte_eth_promiscuous_get(test_params->bonded_port_id);
4398 	TEST_ASSERT_EQUAL(promiscuous_en, (int)0,
4399 			"Port (%d) promiscuous mode not disabled\n",
4400 			test_params->bonded_port_id);
4401 
4402 	for (i = 0; i < test_params->bonded_slave_count; i++) {
4403 		promiscuous_en = rte_eth_promiscuous_get(
4404 				test_params->slave_port_ids[i]);
4405 		TEST_ASSERT_EQUAL(promiscuous_en, (int)0,
4406 				"slave port (%d) promiscuous mode not disabled\n",
4407 				test_params->slave_port_ids[i]);
4408 	}
4409 
4410 	/* Clean up and remove slaves from bonded device */
4411 	return remove_slaves_and_stop_bonded_device();
4412 }
4413 
4414 static int
4415 test_tlb_verify_mac_assignment(void)
4416 {
4417 	struct rte_ether_addr read_mac_addr;
4418 	struct rte_ether_addr expected_mac_addr_0, expected_mac_addr_1;
4419 
4420 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &expected_mac_addr_0),
4421 			"Failed to get mac address (port %d)",
4422 			test_params->slave_port_ids[0]);
4423 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &expected_mac_addr_1),
4424 			"Failed to get mac address (port %d)",
4425 			test_params->slave_port_ids[1]);
4426 
4427 	/* Initialize bonded device with 2 slaves in active backup mode */
4428 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
4429 			BONDING_MODE_TLB, 0, 2, 1),
4430 			"Failed to initialize bonded device");
4431 
4432 	/* Verify that bonded MACs is that of first slave and that the other slave
4433 	 * MAC hasn't been changed */
4434 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
4435 			"Failed to get mac address (port %d)",
4436 			test_params->bonded_port_id);
4437 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
4438 			sizeof(read_mac_addr)),
4439 			"bonded port (%d) mac address not set to that of primary port",
4440 			test_params->bonded_port_id);
4441 
4442 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
4443 			"Failed to get mac address (port %d)",
4444 			test_params->slave_port_ids[0]);
4445 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
4446 			sizeof(read_mac_addr)),
4447 			"slave port (%d) mac address not set to that of primary port",
4448 			test_params->slave_port_ids[0]);
4449 
4450 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
4451 			"Failed to get mac address (port %d)",
4452 			test_params->slave_port_ids[1]);
4453 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
4454 			sizeof(read_mac_addr)),
4455 			"slave port (%d) mac address not as expected",
4456 			test_params->slave_port_ids[1]);
4457 
4458 	/* change primary and verify that MAC addresses haven't changed */
4459 	TEST_ASSERT_EQUAL(rte_eth_bond_primary_set(test_params->bonded_port_id,
4460 			test_params->slave_port_ids[1]), 0,
4461 			"Failed to set bonded port (%d) primary port to (%d)",
4462 			test_params->bonded_port_id, test_params->slave_port_ids[1]);
4463 
4464 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
4465 			"Failed to get mac address (port %d)",
4466 			test_params->bonded_port_id);
4467 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
4468 			sizeof(read_mac_addr)),
4469 			"bonded port (%d) mac address not set to that of primary port",
4470 			test_params->bonded_port_id);
4471 
4472 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
4473 			"Failed to get mac address (port %d)",
4474 			test_params->slave_port_ids[0]);
4475 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
4476 			sizeof(read_mac_addr)),
4477 			"slave port (%d) mac address not set to that of primary port",
4478 			test_params->slave_port_ids[0]);
4479 
4480 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
4481 			"Failed to get mac address (port %d)",
4482 			test_params->slave_port_ids[1]);
4483 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
4484 			sizeof(read_mac_addr)),
4485 			"slave port (%d) mac address not as expected",
4486 			test_params->slave_port_ids[1]);
4487 
4488 	/* stop / start bonded device and verify that primary MAC address is
4489 	 * propagated to bonded device and slaves */
4490 
4491 	TEST_ASSERT_SUCCESS(rte_eth_dev_stop(test_params->bonded_port_id),
4492 			"Failed to stop bonded port %u",
4493 			test_params->bonded_port_id);
4494 
4495 	TEST_ASSERT_SUCCESS(rte_eth_dev_start(test_params->bonded_port_id),
4496 			"Failed to start device");
4497 
4498 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
4499 			"Failed to get mac address (port %d)",
4500 			test_params->bonded_port_id);
4501 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
4502 			sizeof(read_mac_addr)),
4503 			"bonded port (%d) mac address not set to that of primary port",
4504 			test_params->bonded_port_id);
4505 
4506 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
4507 			"Failed to get mac address (port %d)",
4508 			test_params->slave_port_ids[0]);
4509 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
4510 			sizeof(read_mac_addr)),
4511 			"slave port (%d) mac address not as expected",
4512 			test_params->slave_port_ids[0]);
4513 
4514 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
4515 			"Failed to get mac address (port %d)",
4516 			test_params->slave_port_ids[1]);
4517 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_1, &read_mac_addr,
4518 			sizeof(read_mac_addr)),
4519 			"slave port (%d) mac address not set to that of primary port",
4520 			test_params->slave_port_ids[1]);
4521 
4522 
4523 	/* Set explicit MAC address */
4524 	TEST_ASSERT_SUCCESS(rte_eth_bond_mac_address_set(
4525 			test_params->bonded_port_id,
4526 			(struct rte_ether_addr *)bonded_mac),
4527 			"failed to set MAC address");
4528 
4529 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->bonded_port_id, &read_mac_addr),
4530 			"Failed to get mac address (port %d)",
4531 			test_params->bonded_port_id);
4532 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac, &read_mac_addr,
4533 			sizeof(read_mac_addr)),
4534 			"bonded port (%d) mac address not set to that of bonded port",
4535 			test_params->bonded_port_id);
4536 
4537 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[0], &read_mac_addr),
4538 			"Failed to get mac address (port %d)",
4539 			test_params->slave_port_ids[0]);
4540 	TEST_ASSERT_SUCCESS(memcmp(&expected_mac_addr_0, &read_mac_addr,
4541 			sizeof(read_mac_addr)),
4542 			"slave port (%d) mac address not as expected",
4543 			test_params->slave_port_ids[0]);
4544 
4545 	TEST_ASSERT_SUCCESS(rte_eth_macaddr_get(test_params->slave_port_ids[1], &read_mac_addr),
4546 			"Failed to get mac address (port %d)",
4547 			test_params->slave_port_ids[1]);
4548 	TEST_ASSERT_SUCCESS(memcmp(&bonded_mac, &read_mac_addr,
4549 			sizeof(read_mac_addr)),
4550 			"slave port (%d) mac address not set to that of bonded port",
4551 			test_params->slave_port_ids[1]);
4552 
4553 	/* Clean up and remove slaves from bonded device */
4554 	return remove_slaves_and_stop_bonded_device();
4555 }
4556 
4557 static int
4558 test_tlb_verify_slave_link_status_change_failover(void)
4559 {
4560 	struct rte_mbuf *pkt_burst[TEST_ADAPTIVE_TRANSMIT_LOAD_BALANCING_RX_BURST_SLAVE_COUNT][MAX_PKT_BURST];
4561 	struct rte_mbuf *rx_pkt_burst[MAX_PKT_BURST] = { NULL };
4562 	struct rte_eth_stats port_stats;
4563 
4564 	uint16_t slaves[RTE_MAX_ETHPORTS];
4565 
4566 	int i, burst_size, slave_count, primary_port;
4567 
4568 	burst_size = 21;
4569 
4570 	memset(pkt_burst, 0, sizeof(pkt_burst));
4571 
4572 
4573 
4574 	/* Initialize bonded device with 4 slaves in round robin mode */
4575 	TEST_ASSERT_SUCCESS(initialize_bonded_device_with_slaves(
4576 			BONDING_MODE_TLB, 0,
4577 			TEST_ADAPTIVE_TRANSMIT_LOAD_BALANCING_RX_BURST_SLAVE_COUNT, 1),
4578 			"Failed to initialize bonded device with slaves");
4579 
4580 	/* Verify Current Slaves Count /Active Slave Count is */
4581 	slave_count = rte_eth_bond_slaves_get(test_params->bonded_port_id, slaves,
4582 			RTE_MAX_ETHPORTS);
4583 	TEST_ASSERT_EQUAL(slave_count, 4,
4584 			"Number of slaves (%d) is not as expected (%d).\n",
4585 			slave_count, 4);
4586 
4587 	slave_count = rte_eth_bond_active_slaves_get(test_params->bonded_port_id,
4588 			slaves, RTE_MAX_ETHPORTS);
4589 	TEST_ASSERT_EQUAL(slave_count, (int)4,
4590 			"Number of slaves (%d) is not as expected (%d).\n",
4591 			slave_count, 4);
4592 
4593 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
4594 	TEST_ASSERT_EQUAL(primary_port, test_params->slave_port_ids[0],
4595 			"Primary port not as expected");
4596 
4597 	/* Bring 2 slaves down and verify active slave count */
4598 	virtual_ethdev_simulate_link_status_interrupt(
4599 			test_params->slave_port_ids[1], 0);
4600 	virtual_ethdev_simulate_link_status_interrupt(
4601 			test_params->slave_port_ids[3], 0);
4602 
4603 	TEST_ASSERT_EQUAL(rte_eth_bond_active_slaves_get(
4604 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS), 2,
4605 			"Number of active slaves (%d) is not as expected (%d).",
4606 			slave_count, 2);
4607 
4608 	virtual_ethdev_simulate_link_status_interrupt(
4609 			test_params->slave_port_ids[1], 1);
4610 	virtual_ethdev_simulate_link_status_interrupt(
4611 			test_params->slave_port_ids[3], 1);
4612 
4613 
4614 	/* Bring primary port down, verify that active slave count is 3 and primary
4615 	 *  has changed */
4616 	virtual_ethdev_simulate_link_status_interrupt(
4617 			test_params->slave_port_ids[0], 0);
4618 
4619 	TEST_ASSERT_EQUAL(rte_eth_bond_active_slaves_get(
4620 			test_params->bonded_port_id, slaves, RTE_MAX_ETHPORTS), 3,
4621 			"Number of active slaves (%d) is not as expected (%d).",
4622 			slave_count, 3);
4623 
4624 	primary_port = rte_eth_bond_primary_get(test_params->bonded_port_id);
4625 	TEST_ASSERT_EQUAL(primary_port, test_params->slave_port_ids[2],
4626 			"Primary port not as expected");
4627 	rte_delay_us(500000);
4628 	/* Verify that pkts are sent on new primary slave */
4629 	for (i = 0; i < 4; i++) {
4630 		TEST_ASSERT_EQUAL(generate_test_burst(
4631 				&pkt_burst[0][0], burst_size, 0, 1, 0, 0, 0), burst_size,
4632 				"generate_test_burst failed\n");
4633 		TEST_ASSERT_EQUAL(rte_eth_tx_burst(
4634 				test_params->bonded_port_id, 0, &pkt_burst[0][0], burst_size), burst_size,
4635 				"rte_eth_tx_burst failed\n");
4636 		rte_delay_us(11000);
4637 	}
4638 
4639 	rte_eth_stats_get(test_params->slave_port_ids[0], &port_stats);
4640 	TEST_ASSERT_EQUAL(port_stats.opackets, (int8_t)0,
4641 			"(%d) port_stats.opackets not as expected\n",
4642 			test_params->slave_port_ids[0]);
4643 
4644 	rte_eth_stats_get(test_params->slave_port_ids[1], &port_stats);
4645 	TEST_ASSERT_NOT_EQUAL(port_stats.opackets, (int8_t)0,
4646 			"(%d) port_stats.opackets not as expected\n",
4647 			test_params->slave_port_ids[1]);
4648 
4649 	rte_eth_stats_get(test_params->slave_port_ids[2], &port_stats);
4650 	TEST_ASSERT_NOT_EQUAL(port_stats.opackets, (int8_t)0,
4651 			"(%d) port_stats.opackets not as expected\n",
4652 			test_params->slave_port_ids[2]);
4653 
4654 	rte_eth_stats_get(test_params->slave_port_ids[3], &port_stats);
4655 	TEST_ASSERT_NOT_EQUAL(port_stats.opackets, (int8_t)0,
4656 			"(%d) port_stats.opackets not as expected\n",
4657 			test_params->slave_port_ids[3]);
4658 
4659 
4660 	/* Generate packet burst for testing */
4661 
4662 	for (i = 0; i < TEST_ADAPTIVE_TRANSMIT_LOAD_BALANCING_RX_BURST_SLAVE_COUNT; i++) {
4663 		if (generate_test_burst(&pkt_burst[i][0], burst_size, 0, 1, 0, 0, 0) !=
4664 				burst_size)
4665 			return -1;
4666 
4667 		virtual_ethdev_add_mbufs_to_rx_queue(
4668 				test_params->slave_port_ids[i], &pkt_burst[i][0], burst_size);
4669 	}
4670 
4671 	if (rte_eth_rx_burst(test_params->bonded_port_id, 0, rx_pkt_burst,
4672 			MAX_PKT_BURST) != burst_size) {
4673 		printf("rte_eth_rx_burst\n");
4674 		return -1;
4675 
4676 	}
4677 
4678 	/* Verify bonded device rx count */
4679 	rte_eth_stats_get(test_params->bonded_port_id, &port_stats);
4680 	TEST_ASSERT_EQUAL(port_stats.ipackets, (uint64_t)burst_size,
4681 			"(%d) port_stats.ipackets not as expected\n",
4682 			test_params->bonded_port_id);
4683 
4684 	/* Clean up and remove slaves from bonded device */
4685 	return remove_slaves_and_stop_bonded_device();
4686 }
4687 
4688 #define TEST_ALB_SLAVE_COUNT	2
4689 
4690 static uint8_t mac_client1[] = {0x00, 0xAA, 0x55, 0xFF, 0xCC, 1};
4691 static uint8_t mac_client2[] = {0x00, 0xAA, 0x55, 0xFF, 0xCC, 2};
4692 static uint8_t mac_client3[] = {0x00, 0xAA, 0x55, 0xFF, 0xCC, 3};
4693 static uint8_t mac_client4[] = {0x00, 0xAA, 0x55, 0xFF, 0xCC, 4};
4694 
4695 static uint32_t ip_host = IPV4_ADDR(192, 168, 0, 0);
4696 static uint32_t ip_client1 = IPV4_ADDR(192, 168, 0, 1);
4697 static uint32_t ip_client2 = IPV4_ADDR(192, 168, 0, 2);
4698 static uint32_t ip_client3 = IPV4_ADDR(192, 168, 0, 3);
4699 static uint32_t ip_client4 = IPV4_ADDR(192, 168, 0, 4);
4700 
4701 static int
4702 test_alb_change_mac_in_reply_sent(void)
4703 {
4704 	struct rte_mbuf *pkt;
4705 	struct rte_mbuf *pkts_sent[MAX_PKT_BURST];
4706 
4707 	struct rte_ether_hdr *eth_pkt;
4708 	struct rte_arp_hdr *arp_pkt;
4709 
4710 	int slave_idx, nb_pkts, pkt_idx;
4711 	int retval = 0;
4712 
4713 	struct rte_ether_addr bond_mac, client_mac;
4714 	struct rte_ether_addr *slave_mac1, *slave_mac2;
4715 
4716 	TEST_ASSERT_SUCCESS(
4717 			initialize_bonded_device_with_slaves(BONDING_MODE_ALB,
4718 					0, TEST_ALB_SLAVE_COUNT, 1),
4719 			"Failed to initialize_bonded_device_with_slaves.");
4720 
4721 	/* Flush tx queue */
4722 	rte_eth_tx_burst(test_params->bonded_port_id, 0, NULL, 0);
4723 	for (slave_idx = 0; slave_idx < test_params->bonded_slave_count;
4724 			slave_idx++) {
4725 		nb_pkts = virtual_ethdev_get_mbufs_from_tx_queue(
4726 				test_params->slave_port_ids[slave_idx], pkts_sent,
4727 				MAX_PKT_BURST);
4728 	}
4729 
4730 	rte_ether_addr_copy(
4731 			rte_eth_devices[test_params->bonded_port_id].data->mac_addrs,
4732 			&bond_mac);
4733 
4734 	/*
4735 	 * Generating four packets with different mac and ip addresses and sending
4736 	 * them through the bonding port.
4737 	 */
4738 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4739 	memcpy(client_mac.addr_bytes, mac_client1, RTE_ETHER_ADDR_LEN);
4740 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4741 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4742 			RTE_ETHER_TYPE_ARP, 0, 0);
4743 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4744 					sizeof(struct rte_ether_hdr));
4745 	initialize_arp_header(arp_pkt, &bond_mac, &client_mac, ip_host, ip_client1,
4746 			RTE_ARP_OP_REPLY);
4747 	rte_eth_tx_burst(test_params->bonded_port_id, 0, &pkt, 1);
4748 
4749 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4750 	memcpy(client_mac.addr_bytes, mac_client2, RTE_ETHER_ADDR_LEN);
4751 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4752 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4753 			RTE_ETHER_TYPE_ARP, 0, 0);
4754 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4755 					sizeof(struct rte_ether_hdr));
4756 	initialize_arp_header(arp_pkt, &bond_mac, &client_mac, ip_host, ip_client2,
4757 			RTE_ARP_OP_REPLY);
4758 	rte_eth_tx_burst(test_params->bonded_port_id, 0, &pkt, 1);
4759 
4760 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4761 	memcpy(client_mac.addr_bytes, mac_client3, RTE_ETHER_ADDR_LEN);
4762 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4763 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4764 			RTE_ETHER_TYPE_ARP, 0, 0);
4765 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4766 					sizeof(struct rte_ether_hdr));
4767 	initialize_arp_header(arp_pkt, &bond_mac, &client_mac, ip_host, ip_client3,
4768 			RTE_ARP_OP_REPLY);
4769 	rte_eth_tx_burst(test_params->bonded_port_id, 0, &pkt, 1);
4770 
4771 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4772 	memcpy(client_mac.addr_bytes, mac_client4, RTE_ETHER_ADDR_LEN);
4773 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4774 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4775 			RTE_ETHER_TYPE_ARP, 0, 0);
4776 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4777 					sizeof(struct rte_ether_hdr));
4778 	initialize_arp_header(arp_pkt, &bond_mac, &client_mac, ip_host, ip_client4,
4779 			RTE_ARP_OP_REPLY);
4780 	rte_eth_tx_burst(test_params->bonded_port_id, 0, &pkt, 1);
4781 
4782 	slave_mac1 =
4783 			rte_eth_devices[test_params->slave_port_ids[0]].data->mac_addrs;
4784 	slave_mac2 =
4785 			rte_eth_devices[test_params->slave_port_ids[1]].data->mac_addrs;
4786 
4787 	/*
4788 	 * Checking if packets are properly distributed on bonding ports. Packets
4789 	 * 0 and 2 should be sent on port 0 and packets 1 and 3 on port 1.
4790 	 */
4791 	for (slave_idx = 0; slave_idx < test_params->bonded_slave_count; slave_idx++) {
4792 		nb_pkts = virtual_ethdev_get_mbufs_from_tx_queue(
4793 				test_params->slave_port_ids[slave_idx], pkts_sent,
4794 				MAX_PKT_BURST);
4795 
4796 		for (pkt_idx = 0; pkt_idx < nb_pkts; pkt_idx++) {
4797 			eth_pkt = rte_pktmbuf_mtod(
4798 				pkts_sent[pkt_idx], struct rte_ether_hdr *);
4799 			arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4800 						sizeof(struct rte_ether_hdr));
4801 
4802 			if (slave_idx%2 == 0) {
4803 				if (!rte_is_same_ether_addr(slave_mac1,
4804 						&arp_pkt->arp_data.arp_sha)) {
4805 					retval = -1;
4806 					goto test_end;
4807 				}
4808 			} else {
4809 				if (!rte_is_same_ether_addr(slave_mac2,
4810 						&arp_pkt->arp_data.arp_sha)) {
4811 					retval = -1;
4812 					goto test_end;
4813 				}
4814 			}
4815 		}
4816 	}
4817 
4818 test_end:
4819 	retval += remove_slaves_and_stop_bonded_device();
4820 	return retval;
4821 }
4822 
4823 static int
4824 test_alb_reply_from_client(void)
4825 {
4826 	struct rte_ether_hdr *eth_pkt;
4827 	struct rte_arp_hdr *arp_pkt;
4828 
4829 	struct rte_mbuf *pkt;
4830 	struct rte_mbuf *pkts_sent[MAX_PKT_BURST];
4831 
4832 	int slave_idx, nb_pkts, pkt_idx, nb_pkts_sum = 0;
4833 	int retval = 0;
4834 
4835 	struct rte_ether_addr bond_mac, client_mac;
4836 	struct rte_ether_addr *slave_mac1, *slave_mac2;
4837 
4838 	TEST_ASSERT_SUCCESS(
4839 			initialize_bonded_device_with_slaves(BONDING_MODE_ALB,
4840 					0, TEST_ALB_SLAVE_COUNT, 1),
4841 			"Failed to initialize_bonded_device_with_slaves.");
4842 
4843 	/* Flush tx queue */
4844 	rte_eth_tx_burst(test_params->bonded_port_id, 0, NULL, 0);
4845 	for (slave_idx = 0; slave_idx < test_params->bonded_slave_count; slave_idx++) {
4846 		nb_pkts = virtual_ethdev_get_mbufs_from_tx_queue(
4847 				test_params->slave_port_ids[slave_idx], pkts_sent,
4848 				MAX_PKT_BURST);
4849 	}
4850 
4851 	rte_ether_addr_copy(
4852 			rte_eth_devices[test_params->bonded_port_id].data->mac_addrs,
4853 			&bond_mac);
4854 
4855 	/*
4856 	 * Generating four packets with different mac and ip addresses and placing
4857 	 * them in the rx queue to be received by the bonding driver on rx_burst.
4858 	 */
4859 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4860 	memcpy(client_mac.addr_bytes, mac_client1, RTE_ETHER_ADDR_LEN);
4861 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4862 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4863 			RTE_ETHER_TYPE_ARP, 0, 0);
4864 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4865 					sizeof(struct rte_ether_hdr));
4866 	initialize_arp_header(arp_pkt, &client_mac, &bond_mac, ip_client1, ip_host,
4867 			RTE_ARP_OP_REPLY);
4868 	virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[0], &pkt,
4869 			1);
4870 
4871 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4872 	memcpy(client_mac.addr_bytes, mac_client2, RTE_ETHER_ADDR_LEN);
4873 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4874 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4875 			RTE_ETHER_TYPE_ARP, 0, 0);
4876 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4877 					sizeof(struct rte_ether_hdr));
4878 	initialize_arp_header(arp_pkt, &client_mac, &bond_mac, ip_client2, ip_host,
4879 			RTE_ARP_OP_REPLY);
4880 	virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[0], &pkt,
4881 			1);
4882 
4883 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4884 	memcpy(client_mac.addr_bytes, mac_client3, RTE_ETHER_ADDR_LEN);
4885 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4886 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4887 			RTE_ETHER_TYPE_ARP, 0, 0);
4888 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4889 					sizeof(struct rte_ether_hdr));
4890 	initialize_arp_header(arp_pkt, &client_mac, &bond_mac, ip_client3, ip_host,
4891 			RTE_ARP_OP_REPLY);
4892 	virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[0], &pkt,
4893 			1);
4894 
4895 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4896 	memcpy(client_mac.addr_bytes, mac_client4, RTE_ETHER_ADDR_LEN);
4897 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4898 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4899 			RTE_ETHER_TYPE_ARP, 0, 0);
4900 	arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4901 					sizeof(struct rte_ether_hdr));
4902 	initialize_arp_header(arp_pkt, &client_mac, &bond_mac, ip_client4, ip_host,
4903 			RTE_ARP_OP_REPLY);
4904 	virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[0], &pkt,
4905 			1);
4906 
4907 	/*
4908 	 * Issue rx_burst and tx_burst to force bonding driver to send update ARP
4909 	 * packets to every client in alb table.
4910 	 */
4911 	rte_eth_rx_burst(test_params->bonded_port_id, 0, pkts_sent, MAX_PKT_BURST);
4912 	rte_eth_tx_burst(test_params->bonded_port_id, 0, NULL, 0);
4913 
4914 	slave_mac1 = rte_eth_devices[test_params->slave_port_ids[0]].data->mac_addrs;
4915 	slave_mac2 = rte_eth_devices[test_params->slave_port_ids[1]].data->mac_addrs;
4916 
4917 	/*
4918 	 * Checking if update ARP packets were properly send on slave ports.
4919 	 */
4920 	for (slave_idx = 0; slave_idx < test_params->bonded_slave_count; slave_idx++) {
4921 		nb_pkts = virtual_ethdev_get_mbufs_from_tx_queue(
4922 				test_params->slave_port_ids[slave_idx], pkts_sent, MAX_PKT_BURST);
4923 		nb_pkts_sum += nb_pkts;
4924 
4925 		for (pkt_idx = 0; pkt_idx < nb_pkts; pkt_idx++) {
4926 			eth_pkt = rte_pktmbuf_mtod(
4927 				pkts_sent[pkt_idx], struct rte_ether_hdr *);
4928 			arp_pkt = (struct rte_arp_hdr *)((char *)eth_pkt +
4929 						sizeof(struct rte_ether_hdr));
4930 
4931 			if (slave_idx%2 == 0) {
4932 				if (!rte_is_same_ether_addr(slave_mac1,
4933 						&arp_pkt->arp_data.arp_sha)) {
4934 					retval = -1;
4935 					goto test_end;
4936 				}
4937 			} else {
4938 				if (!rte_is_same_ether_addr(slave_mac2,
4939 						&arp_pkt->arp_data.arp_sha)) {
4940 					retval = -1;
4941 					goto test_end;
4942 				}
4943 			}
4944 		}
4945 	}
4946 
4947 	/* Check if proper number of packets was send */
4948 	if (nb_pkts_sum < 4) {
4949 		retval = -1;
4950 		goto test_end;
4951 	}
4952 
4953 test_end:
4954 	retval += remove_slaves_and_stop_bonded_device();
4955 	return retval;
4956 }
4957 
4958 static int
4959 test_alb_receive_vlan_reply(void)
4960 {
4961 	struct rte_ether_hdr *eth_pkt;
4962 	struct rte_vlan_hdr *vlan_pkt;
4963 	struct rte_arp_hdr *arp_pkt;
4964 
4965 	struct rte_mbuf *pkt;
4966 	struct rte_mbuf *pkts_sent[MAX_PKT_BURST];
4967 
4968 	int slave_idx, nb_pkts, pkt_idx;
4969 	int retval = 0;
4970 
4971 	struct rte_ether_addr bond_mac, client_mac;
4972 
4973 	TEST_ASSERT_SUCCESS(
4974 			initialize_bonded_device_with_slaves(BONDING_MODE_ALB,
4975 					0, TEST_ALB_SLAVE_COUNT, 1),
4976 			"Failed to initialize_bonded_device_with_slaves.");
4977 
4978 	/* Flush tx queue */
4979 	rte_eth_tx_burst(test_params->bonded_port_id, 0, NULL, 0);
4980 	for (slave_idx = 0; slave_idx < test_params->bonded_slave_count; slave_idx++) {
4981 		nb_pkts = virtual_ethdev_get_mbufs_from_tx_queue(
4982 				test_params->slave_port_ids[slave_idx], pkts_sent,
4983 				MAX_PKT_BURST);
4984 	}
4985 
4986 	rte_ether_addr_copy(
4987 			rte_eth_devices[test_params->bonded_port_id].data->mac_addrs,
4988 			&bond_mac);
4989 
4990 	/*
4991 	 * Generating packet with double VLAN header and placing it in the rx queue.
4992 	 */
4993 	pkt = rte_pktmbuf_alloc(test_params->mbuf_pool);
4994 	memcpy(client_mac.addr_bytes, mac_client1, RTE_ETHER_ADDR_LEN);
4995 	eth_pkt = rte_pktmbuf_mtod(pkt, struct rte_ether_hdr *);
4996 	initialize_eth_header(eth_pkt, &bond_mac, &client_mac,
4997 			RTE_ETHER_TYPE_VLAN, 0, 0);
4998 	vlan_pkt = (struct rte_vlan_hdr *)((char *)(eth_pkt + 1));
4999 	vlan_pkt->vlan_tci = rte_cpu_to_be_16(1);
5000 	vlan_pkt->eth_proto = rte_cpu_to_be_16(RTE_ETHER_TYPE_VLAN);
5001 	vlan_pkt = vlan_pkt+1;
5002 	vlan_pkt->vlan_tci = rte_cpu_to_be_16(2);
5003 	vlan_pkt->eth_proto = rte_cpu_to_be_16(RTE_ETHER_TYPE_ARP);
5004 	arp_pkt = (struct rte_arp_hdr *)((char *)(vlan_pkt + 1));
5005 	initialize_arp_header(arp_pkt, &client_mac, &bond_mac, ip_client1, ip_host,
5006 			RTE_ARP_OP_REPLY);
5007 	virtual_ethdev_add_mbufs_to_rx_queue(test_params->slave_port_ids[0], &pkt,
5008 			1);
5009 
5010 	rte_eth_rx_burst(test_params->bonded_port_id, 0, pkts_sent, MAX_PKT_BURST);
5011 	rte_eth_tx_burst(test_params->bonded_port_id, 0, NULL, 0);
5012 
5013 	/*
5014 	 * Checking if VLAN headers in generated ARP Update packet are correct.
5015 	 */
5016 	for (slave_idx = 0; slave_idx < test_params->bonded_slave_count; slave_idx++) {
5017 		nb_pkts = virtual_ethdev_get_mbufs_from_tx_queue(
5018 				test_params->slave_port_ids[slave_idx], pkts_sent,
5019 				MAX_PKT_BURST);
5020 
5021 		for (pkt_idx = 0; pkt_idx < nb_pkts; pkt_idx++) {
5022 			eth_pkt = rte_pktmbuf_mtod(
5023 				pkts_sent[pkt_idx], struct rte_ether_hdr *);
5024 			vlan_pkt = (struct rte_vlan_hdr *)(
5025 				(char *)(eth_pkt + 1));
5026 			if (vlan_pkt->vlan_tci != rte_cpu_to_be_16(1)) {
5027 				retval = -1;
5028 				goto test_end;
5029 			}
5030 			if (vlan_pkt->eth_proto != rte_cpu_to_be_16(
5031 					RTE_ETHER_TYPE_VLAN)) {
5032 				retval = -1;
5033 				goto test_end;
5034 			}
5035 			vlan_pkt = vlan_pkt+1;
5036 			if (vlan_pkt->vlan_tci != rte_cpu_to_be_16(2)) {
5037 				retval = -1;
5038 				goto test_end;
5039 			}
5040 			if (vlan_pkt->eth_proto != rte_cpu_to_be_16(
5041 					RTE_ETHER_TYPE_ARP)) {
5042 				retval = -1;
5043 				goto test_end;
5044 			}
5045 		}
5046 	}
5047 
5048 test_end:
5049 	retval += remove_slaves_and_stop_bonded_device();
5050 	return retval;
5051 }
5052 
5053 static int
5054 test_alb_ipv4_tx(void)
5055 {
5056 	int burst_size, retval, pkts_send;
5057 	struct rte_mbuf *pkt_burst[MAX_PKT_BURST];
5058 
5059 	retval = 0;
5060 
5061 	TEST_ASSERT_SUCCESS(
5062 			initialize_bonded_device_with_slaves(BONDING_MODE_ALB,
5063 					0, TEST_ALB_SLAVE_COUNT, 1),
5064 			"Failed to initialize_bonded_device_with_slaves.");
5065 
5066 	burst_size = 32;
5067 
5068 	/* Generate test bursts of packets to transmit */
5069 	if (generate_test_burst(pkt_burst, burst_size, 0, 1, 0, 0, 0) != burst_size) {
5070 		retval = -1;
5071 		goto test_end;
5072 	}
5073 
5074 	/*
5075 	 * Checking if ipv4 traffic is transmitted via TLB policy.
5076 	 */
5077 	pkts_send = rte_eth_tx_burst(
5078 			test_params->bonded_port_id, 0, pkt_burst, burst_size);
5079 	if (pkts_send != burst_size) {
5080 		retval = -1;
5081 		goto test_end;
5082 	}
5083 
5084 test_end:
5085 	retval += remove_slaves_and_stop_bonded_device();
5086 	return retval;
5087 }
5088 
5089 static struct unit_test_suite link_bonding_test_suite  = {
5090 	.suite_name = "Link Bonding Unit Test Suite",
5091 	.setup = test_setup,
5092 	.teardown = testsuite_teardown,
5093 	.unit_test_cases = {
5094 		TEST_CASE(test_create_bonded_device),
5095 		TEST_CASE(test_create_bonded_device_with_invalid_params),
5096 		TEST_CASE(test_add_slave_to_bonded_device),
5097 		TEST_CASE(test_add_slave_to_invalid_bonded_device),
5098 		TEST_CASE(test_remove_slave_from_bonded_device),
5099 		TEST_CASE(test_remove_slave_from_invalid_bonded_device),
5100 		TEST_CASE(test_get_slaves_from_bonded_device),
5101 		TEST_CASE(test_add_already_bonded_slave_to_bonded_device),
5102 		TEST_CASE(test_add_remove_multiple_slaves_to_from_bonded_device),
5103 		TEST_CASE(test_start_bonded_device),
5104 		TEST_CASE(test_stop_bonded_device),
5105 		TEST_CASE(test_set_bonding_mode),
5106 		TEST_CASE(test_set_primary_slave),
5107 		TEST_CASE(test_set_explicit_bonded_mac),
5108 		TEST_CASE(test_set_bonded_port_initialization_mac_assignment),
5109 		TEST_CASE(test_status_interrupt),
5110 		TEST_CASE(test_adding_slave_after_bonded_device_started),
5111 		TEST_CASE(test_roundrobin_tx_burst),
5112 		TEST_CASE(test_roundrobin_tx_burst_slave_tx_fail),
5113 		TEST_CASE(test_roundrobin_rx_burst_on_single_slave),
5114 		TEST_CASE(test_roundrobin_rx_burst_on_multiple_slaves),
5115 		TEST_CASE(test_roundrobin_verify_promiscuous_enable_disable),
5116 		TEST_CASE(test_roundrobin_verify_mac_assignment),
5117 		TEST_CASE(test_roundrobin_verify_slave_link_status_change_behaviour),
5118 		TEST_CASE(test_roundrobin_verfiy_polling_slave_link_status_change),
5119 		TEST_CASE(test_activebackup_tx_burst),
5120 		TEST_CASE(test_activebackup_rx_burst),
5121 		TEST_CASE(test_activebackup_verify_promiscuous_enable_disable),
5122 		TEST_CASE(test_activebackup_verify_mac_assignment),
5123 		TEST_CASE(test_activebackup_verify_slave_link_status_change_failover),
5124 		TEST_CASE(test_balance_xmit_policy_configuration),
5125 		TEST_CASE(test_balance_l2_tx_burst),
5126 		TEST_CASE(test_balance_l23_tx_burst_ipv4_toggle_ip_addr),
5127 		TEST_CASE(test_balance_l23_tx_burst_vlan_ipv4_toggle_ip_addr),
5128 		TEST_CASE(test_balance_l23_tx_burst_ipv6_toggle_ip_addr),
5129 		TEST_CASE(test_balance_l23_tx_burst_vlan_ipv6_toggle_ip_addr),
5130 		TEST_CASE(test_balance_l23_tx_burst_toggle_mac_addr),
5131 		TEST_CASE(test_balance_l34_tx_burst_ipv4_toggle_ip_addr),
5132 		TEST_CASE(test_balance_l34_tx_burst_ipv4_toggle_udp_port),
5133 		TEST_CASE(test_balance_l34_tx_burst_vlan_ipv4_toggle_ip_addr),
5134 		TEST_CASE(test_balance_l34_tx_burst_ipv6_toggle_ip_addr),
5135 		TEST_CASE(test_balance_l34_tx_burst_vlan_ipv6_toggle_ip_addr),
5136 		TEST_CASE(test_balance_l34_tx_burst_ipv6_toggle_udp_port),
5137 		TEST_CASE(test_balance_tx_burst_slave_tx_fail),
5138 		TEST_CASE(test_balance_rx_burst),
5139 		TEST_CASE(test_balance_verify_promiscuous_enable_disable),
5140 		TEST_CASE(test_balance_verify_mac_assignment),
5141 		TEST_CASE(test_balance_verify_slave_link_status_change_behaviour),
5142 		TEST_CASE(test_tlb_tx_burst),
5143 		TEST_CASE(test_tlb_rx_burst),
5144 		TEST_CASE(test_tlb_verify_mac_assignment),
5145 		TEST_CASE(test_tlb_verify_promiscuous_enable_disable),
5146 		TEST_CASE(test_tlb_verify_slave_link_status_change_failover),
5147 		TEST_CASE(test_alb_change_mac_in_reply_sent),
5148 		TEST_CASE(test_alb_reply_from_client),
5149 		TEST_CASE(test_alb_receive_vlan_reply),
5150 		TEST_CASE(test_alb_ipv4_tx),
5151 		TEST_CASE(test_broadcast_tx_burst),
5152 		TEST_CASE(test_broadcast_tx_burst_slave_tx_fail),
5153 		TEST_CASE(test_broadcast_rx_burst),
5154 		TEST_CASE(test_broadcast_verify_promiscuous_enable_disable),
5155 		TEST_CASE(test_broadcast_verify_mac_assignment),
5156 		TEST_CASE(test_broadcast_verify_slave_link_status_change_behaviour),
5157 		TEST_CASE(test_reconfigure_bonded_device),
5158 		TEST_CASE(test_close_bonded_device),
5159 
5160 		TEST_CASES_END() /**< NULL terminate unit test array */
5161 	}
5162 };
5163 
5164 
5165 static int
5166 test_link_bonding(void)
5167 {
5168 	return unit_test_suite_runner(&link_bonding_test_suite);
5169 }
5170 
5171 REGISTER_TEST_COMMAND(link_bonding_autotest, test_link_bonding);
5172