1 /* main.c - Application main entry point */
2 
3 /*
4  * Copyright (c) 2018 Intel Corporation
5  *
6  * SPDX-License-Identifier: Apache-2.0
7  */
8 
9 #define NET_LOG_LEVEL CONFIG_NET_L2_ETHERNET_LOG_LEVEL
10 
11 #include <logging/log.h>
12 LOG_MODULE_REGISTER(net_test, NET_LOG_LEVEL);
13 
14 #include <zephyr/types.h>
15 #include <stdbool.h>
16 #include <stddef.h>
17 #include <string.h>
18 #include <errno.h>
19 #include <sys/printk.h>
20 #include <linker/sections.h>
21 #include <random/rand32.h>
22 
23 #include <ztest.h>
24 
25 #include <net/ethernet.h>
26 #include <net/dummy.h>
27 #include <net/buf.h>
28 #include <net/net_ip.h>
29 #include <net/ethernet_vlan.h>
30 #include <net/net_l2.h>
31 
32 #include "ipv6.h"
33 
34 #define NET_LOG_ENABLED 1
35 #include "net_private.h"
36 
37 #if NET_LOG_LEVEL >= LOG_LEVEL_DBG
38 #define DBG(fmt, ...) printk(fmt, ##__VA_ARGS__)
39 #else
40 #define DBG(fmt, ...)
41 #endif
42 
43 #define TEST_PORT 9999
44 
45 #define VLAN_TAG_1 100
46 #define VLAN_TAG_2 200
47 #define VLAN_TAG_3 300
48 #define VLAN_TAG_4 400
49 #define VLAN_TAG_5 500
50 
51 static char *test_data = "Test data to be sent";
52 
53 /* Interface 1 addresses */
54 static struct in6_addr my_addr1 = { { { 0x20, 0x01, 0x0d, 0xb8, 1, 0, 0, 0,
55 					0, 0, 0, 0, 0, 0, 0, 0x1 } } };
56 
57 /* Interface 2 addresses */
58 static struct in6_addr my_addr2 = { { { 0x20, 0x01, 0x0d, 0xb8, 0, 0, 0, 0,
59 					0, 0, 0, 0, 0, 0, 0, 0x1 } } };
60 
61 /* Interface 3 addresses */
62 static struct in6_addr my_addr3 = { { { 0x20, 0x01, 0x0d, 0xb8, 2, 0, 0, 0,
63 					0, 0, 0, 0, 0, 0, 0, 0x1 } } };
64 
65 /* Destination address for test packets */
66 static struct in6_addr dst_addr = { { { 0x20, 0x01, 0x0d, 0xb8, 9, 0, 0, 0,
67 					0, 0, 0, 0, 0, 0, 0, 0x1 } } };
68 
69 /* Extra address is assigned to ll_addr */
70 static struct in6_addr ll_addr = { { { 0xfe, 0x80, 0x43, 0xb8, 0, 0, 0, 0,
71 				       0, 0, 0, 0xf2, 0xaa, 0x29, 0x02,
72 				       0x04 } } };
73 
74 /* Keep track of all ethernet interfaces */
75 static struct net_if *eth_interfaces[NET_VLAN_MAX_COUNT + 1];
76 static struct net_if *dummy_interfaces[2];
77 static struct net_if *extra_eth;
78 
79 static struct net_context *udp_v6_ctx;
80 
81 static bool test_failed;
82 static bool test_started;
83 
84 static K_SEM_DEFINE(wait_data, 0, UINT_MAX);
85 
86 #define WAIT_TIME K_SECONDS(1)
87 
88 struct eth_context {
89 	struct net_if *iface;
90 	uint8_t mac_addr[6];
91 
92 	uint16_t expecting_tag;
93 };
94 
95 static struct eth_context eth_vlan_context;
96 
eth_vlan_iface_init(struct net_if * iface)97 static void eth_vlan_iface_init(struct net_if *iface)
98 {
99 	const struct device *dev = net_if_get_device(iface);
100 	struct eth_context *context = dev->data;
101 
102 	net_if_set_link_addr(iface, context->mac_addr,
103 			     sizeof(context->mac_addr),
104 			     NET_LINK_ETHERNET);
105 
106 	ethernet_init(iface);
107 }
108 
eth_tx(const struct device * dev,struct net_pkt * pkt)109 static int eth_tx(const struct device *dev, struct net_pkt *pkt)
110 {
111 	struct eth_context *context = dev->data;
112 
113 	zassert_equal_ptr(&eth_vlan_context, context,
114 			  "Context pointers do not match (%p vs %p)",
115 			  eth_vlan_context, context);
116 
117 	if (!pkt->buffer) {
118 		DBG("No data to send!\n");
119 		return -ENODATA;
120 	}
121 
122 	if (test_started) {
123 		struct net_eth_vlan_hdr *hdr =
124 			(struct net_eth_vlan_hdr *)NET_ETH_HDR(pkt);
125 
126 		zassert_equal(context->expecting_tag,
127 			      net_pkt_vlan_tag(pkt),
128 			      "Invalid VLAN tag (%d vs %d) in TX pkt\n",
129 			      net_pkt_vlan_tag(pkt),
130 			      context->expecting_tag);
131 
132 		zassert_equal(context->expecting_tag,
133 			      net_eth_vlan_get_vid(ntohs(hdr->vlan.tci)),
134 			      "Invalid VLAN tag in ethernet header");
135 
136 		k_sem_give(&wait_data);
137 	}
138 
139 	return 0;
140 }
141 
eth_capabilities(const struct device * dev)142 static enum ethernet_hw_caps eth_capabilities(const struct device *dev)
143 {
144 	return ETHERNET_HW_VLAN;
145 }
146 
147 static struct ethernet_api api_funcs = {
148 	.iface_api.init = eth_vlan_iface_init,
149 
150 	.get_capabilities = eth_capabilities,
151 	.send = eth_tx,
152 };
153 
generate_mac(uint8_t * mac_addr)154 static void generate_mac(uint8_t *mac_addr)
155 {
156 	/* 00-00-5E-00-53-xx Documentation RFC 7042 */
157 	mac_addr[0] = 0x00;
158 	mac_addr[1] = 0x00;
159 	mac_addr[2] = 0x5E;
160 	mac_addr[3] = 0x00;
161 	mac_addr[4] = 0x53;
162 	mac_addr[5] = sys_rand32_get();
163 }
164 
eth_vlan_init(const struct device * dev)165 static int eth_vlan_init(const struct device *dev)
166 {
167 	struct eth_context *context = dev->data;
168 
169 	generate_mac(context->mac_addr);
170 
171 	return 0;
172 }
173 
174 ETH_NET_DEVICE_INIT(eth_vlan_test, "eth_vlan_test",
175 		    eth_vlan_init, NULL,
176 		    &eth_vlan_context, NULL, CONFIG_ETH_INIT_PRIORITY,
177 		    &api_funcs, NET_ETH_MTU);
178 
eth_init(const struct device * dev)179 static int eth_init(const struct device *dev)
180 {
181 	struct eth_context *context = dev->data;
182 
183 	generate_mac(context->mac_addr);
184 
185 	return 0;
186 }
187 
188 /* Create one ethernet interface that does not have VLAN support. This
189  * is quite unlikely that this would be done in real life but for testing
190  * purposes create it here.
191  */
192 NET_DEVICE_INIT(eth_test, "eth_test", eth_init, NULL,
193 		&eth_vlan_context, NULL, CONFIG_ETH_INIT_PRIORITY,
194 		&api_funcs, ETHERNET_L2, NET_L2_GET_CTX_TYPE(ETHERNET_L2),
195 		NET_ETH_MTU);
196 
197 struct net_if_test {
198 	uint8_t idx; /* not used for anything, just a dummy value */
199 	uint8_t mac_addr[sizeof(struct net_eth_addr)];
200 	struct net_linkaddr ll_addr;
201 };
202 
net_iface_dev_init(const struct device * dev)203 static int net_iface_dev_init(const struct device *dev)
204 {
205 	return 0;
206 }
207 
net_iface_get_mac(const struct device * dev)208 static uint8_t *net_iface_get_mac(const struct device *dev)
209 {
210 	struct net_if_test *data = dev->data;
211 
212 	if (data->mac_addr[2] == 0x00) {
213 		/* 00-00-5E-00-53-xx Documentation RFC 7042 */
214 		data->mac_addr[0] = 0x00;
215 		data->mac_addr[1] = 0x00;
216 		data->mac_addr[2] = 0x5E;
217 		data->mac_addr[3] = 0x00;
218 		data->mac_addr[4] = 0x53;
219 		data->mac_addr[5] = sys_rand32_get();
220 	}
221 
222 	data->ll_addr.addr = data->mac_addr;
223 	data->ll_addr.len = 6U;
224 
225 	return data->mac_addr;
226 }
227 
net_iface_init(struct net_if * iface)228 static void net_iface_init(struct net_if *iface)
229 {
230 	uint8_t *mac = net_iface_get_mac(net_if_get_device(iface));
231 
232 	net_if_set_link_addr(iface, mac, sizeof(struct net_eth_addr),
233 			     NET_LINK_ETHERNET);
234 }
235 
sender_iface(const struct device * dev,struct net_pkt * pkt)236 static int sender_iface(const struct device *dev, struct net_pkt *pkt)
237 {
238 	return 0;
239 }
240 
241 struct net_if_test net_iface1_data;
242 struct net_if_test net_iface2_data;
243 
244 static struct dummy_api net_iface_api = {
245 	.iface_api.init = net_iface_init,
246 	.send = sender_iface,
247 };
248 
249 /* For testing purposes, create two dummy network interfaces so we can check
250  * that no VLANs are created for it.
251  */
252 NET_DEVICE_INIT_INSTANCE(net_iface1_test,
253 			 "iface1",
254 			 iface1,
255 			 net_iface_dev_init,
256 			 NULL,
257 			 &net_iface1_data,
258 			 NULL,
259 			 CONFIG_KERNEL_INIT_PRIORITY_DEFAULT,
260 			 &net_iface_api,
261 			 DUMMY_L2,
262 			 NET_L2_GET_CTX_TYPE(DUMMY_L2),
263 			 127);
264 
265 NET_DEVICE_INIT_INSTANCE(net_iface2_test,
266 			 "iface2",
267 			 iface2,
268 			 net_iface_dev_init,
269 			 NULL,
270 			 &net_iface2_data,
271 			 NULL,
272 			 CONFIG_KERNEL_INIT_PRIORITY_DEFAULT,
273 			 &net_iface_api,
274 			 DUMMY_L2,
275 			 NET_L2_GET_CTX_TYPE(DUMMY_L2),
276 			 127);
277 
278 struct user_data {
279 	int eth_if_count;
280 	int dummy_if_count;
281 	int total_if_count;
282 };
283 
284 #if NET_LOG_LEVEL >= LOG_LEVEL_DBG
iface2str(struct net_if * iface)285 static const char *iface2str(struct net_if *iface)
286 {
287 #ifdef CONFIG_NET_L2_ETHERNET
288 	if (net_if_l2(iface) == &NET_L2_GET_NAME(ETHERNET)) {
289 		return "Ethernet";
290 	}
291 #endif
292 
293 #ifdef CONFIG_NET_L2_DUMMY
294 	if (net_if_l2(iface) == &NET_L2_GET_NAME(DUMMY)) {
295 		return "Dummy";
296 	}
297 #endif
298 
299 	return "<unknown type>";
300 }
301 #endif
302 
iface_cb(struct net_if * iface,void * user_data)303 static void iface_cb(struct net_if *iface, void *user_data)
304 {
305 	struct user_data *ud = user_data;
306 
307 	DBG("Interface %p (%s) [%d]\n", iface, iface2str(iface),
308 	    net_if_get_by_iface(iface));
309 
310 	if (net_if_l2(iface) == &NET_L2_GET_NAME(ETHERNET)) {
311 		if (PART_OF_ARRAY(NET_IF_GET_NAME(eth_test, 0), iface)) {
312 			if (!extra_eth) {
313 				/* Just use the first interface */
314 				extra_eth = iface;
315 			}
316 		} else {
317 			eth_interfaces[ud->eth_if_count++] = iface;
318 		}
319 	}
320 
321 	if (net_if_l2(iface) == &NET_L2_GET_NAME(DUMMY)) {
322 		dummy_interfaces[ud->dummy_if_count++] = iface;
323 
324 		zassert_true(ud->dummy_if_count <= 2,
325 			     "Too many dummy interfaces");
326 	}
327 
328 	/* By default all interfaces are down initially */
329 	net_if_down(iface);
330 
331 	ud->total_if_count++;
332 }
333 
test_vlan_setup(void)334 static void test_vlan_setup(void)
335 {
336 	struct user_data ud = { 0 };
337 
338 	/* Make sure we have enough virtual interfaces */
339 	net_if_foreach(iface_cb, &ud);
340 
341 	/* One extra eth interface without vlan support */
342 	zassert_equal(ud.eth_if_count, NET_VLAN_MAX_COUNT,
343 		      "Invalid number of VLANs %d vs %d\n",
344 		      ud.eth_if_count, NET_VLAN_MAX_COUNT);
345 
346 	zassert_equal(ud.total_if_count, NET_VLAN_MAX_COUNT + 1 + 2,
347 		      "Invalid number of interfaces");
348 
349 	/* Put the extra non-vlan ethernet interface to last */
350 	eth_interfaces[4] = extra_eth;
351 	zassert_not_null(extra_eth, "Extra interface missing");
352 	zassert_equal_ptr(net_if_l2(extra_eth), &NET_L2_GET_NAME(ETHERNET),
353 			  "Invalid L2 type %p for iface %p (should be %p)\n",
354 			  net_if_l2(extra_eth), extra_eth,
355 			  &NET_L2_GET_NAME(ETHERNET));
356 }
357 
test_address_setup(void)358 static void test_address_setup(void)
359 {
360 	struct net_if_addr *ifaddr;
361 	struct net_if *iface1, *iface2, *iface3;
362 
363 	iface1 = eth_interfaces[1]; /* This has VLAN enabled */
364 	iface2 = eth_interfaces[0]; /* and this one not */
365 	iface3 = eth_interfaces[3]; /* and this one has VLAN enabled */
366 
367 	zassert_not_null(iface1, "Interface 1");
368 	zassert_not_null(iface2, "Interface 2");
369 	zassert_not_null(iface3, "Interface 3");
370 
371 	ifaddr = net_if_ipv6_addr_add(iface1, &my_addr1,
372 				      NET_ADDR_MANUAL, 0);
373 	if (!ifaddr) {
374 		DBG("Cannot add IPv6 address %s\n",
375 		       net_sprint_ipv6_addr(&my_addr1));
376 		zassert_not_null(ifaddr, "addr1");
377 	}
378 
379 	/* For testing purposes we need to set the adddresses preferred */
380 	ifaddr->addr_state = NET_ADDR_PREFERRED;
381 
382 	ifaddr = net_if_ipv6_addr_add(iface1, &ll_addr,
383 				      NET_ADDR_MANUAL, 0);
384 	if (!ifaddr) {
385 		DBG("Cannot add IPv6 address %s\n",
386 		       net_sprint_ipv6_addr(&ll_addr));
387 		zassert_not_null(ifaddr, "ll_addr");
388 	}
389 
390 	ifaddr->addr_state = NET_ADDR_PREFERRED;
391 
392 	ifaddr = net_if_ipv6_addr_add(iface2, &my_addr2,
393 				      NET_ADDR_MANUAL, 0);
394 	if (!ifaddr) {
395 		DBG("Cannot add IPv6 address %s\n",
396 		       net_sprint_ipv6_addr(&my_addr2));
397 		zassert_not_null(ifaddr, "addr2");
398 	}
399 
400 	ifaddr->addr_state = NET_ADDR_PREFERRED;
401 
402 	ifaddr = net_if_ipv6_addr_add(iface3, &my_addr3,
403 				      NET_ADDR_MANUAL, 0);
404 	if (!ifaddr) {
405 		DBG("Cannot add IPv6 address %s\n",
406 		       net_sprint_ipv6_addr(&my_addr3));
407 		zassert_not_null(ifaddr, "addr3");
408 	}
409 
410 	net_if_up(iface1);
411 	net_if_up(iface2);
412 	net_if_up(iface3);
413 
414 	/* The interface might receive data which might fail the checks
415 	 * in the iface sending function, so we need to reset the failure
416 	 * flag.
417 	 */
418 	test_failed = false;
419 }
420 
test_vlan_tci(void)421 static void test_vlan_tci(void)
422 {
423 	struct net_pkt *pkt;
424 	uint16_t tci;
425 	uint16_t tag;
426 	uint8_t priority;
427 	bool dei;
428 
429 	pkt = net_pkt_alloc(K_FOREVER);
430 
431 	tag = NET_VLAN_TAG_UNSPEC;
432 	net_pkt_set_vlan_tag(pkt, tag);
433 
434 	priority = 0U;
435 	net_pkt_set_vlan_priority(pkt, priority);
436 
437 	zassert_equal(net_pkt_vlan_tag(pkt), NET_VLAN_TAG_UNSPEC,
438 		      "invalid VLAN tag unspec");
439 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
440 		      "invalid VLAN priority");
441 
442 	net_pkt_set_vlan_tag(pkt, 0);
443 	zassert_equal(net_pkt_vlan_tag(pkt), 0, "invalid VLAN tag");
444 
445 	/* TCI should be zero now */
446 	zassert_equal(net_pkt_vlan_tci(pkt), 0, "invalid VLAN TCI");
447 
448 	priority = 1U;
449 	net_pkt_set_vlan_priority(pkt, priority);
450 
451 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
452 		      "invalid VLAN priority");
453 
454 	net_pkt_set_vlan_tag(pkt, tag);
455 
456 	zassert_equal(net_pkt_vlan_tag(pkt), NET_VLAN_TAG_UNSPEC,
457 		      "invalid VLAN tag unspec");
458 
459 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
460 		      "invalid VLAN priority");
461 
462 	net_pkt_set_vlan_tag(pkt, 0);
463 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
464 		      "invalid VLAN priority");
465 
466 	dei = true;
467 	net_pkt_set_vlan_dei(pkt, dei);
468 
469 	zassert_equal(net_pkt_vlan_dei(pkt), dei, "invalid VLAN DEI");
470 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
471 		      "invalid VLAN priority");
472 	zassert_equal(net_pkt_vlan_tag(pkt), 0, "invalid VLAN tag");
473 
474 	net_pkt_set_vlan_tag(pkt, tag);
475 	zassert_equal(net_pkt_vlan_tag(pkt), tag, "invalid VLAN tag");
476 	zassert_equal(net_pkt_vlan_dei(pkt), dei, "invalid VLAN DEI");
477 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
478 		      "invalid VLAN priority");
479 
480 	dei = false;
481 	net_pkt_set_vlan_dei(pkt, dei);
482 	zassert_equal(net_pkt_vlan_tag(pkt), tag, "invalid VLAN tag");
483 	zassert_equal(net_pkt_vlan_dei(pkt), dei, "invalid VLAN DEI");
484 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
485 		      "invalid VLAN priority");
486 
487 	tag = 0U;
488 	net_pkt_set_vlan_tag(pkt, tag);
489 	zassert_equal(net_pkt_vlan_tag(pkt), tag, "invalid VLAN tag");
490 	zassert_equal(net_pkt_vlan_dei(pkt), dei, "invalid VLAN DEI");
491 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
492 		      "invalid VLAN priority");
493 
494 	priority = 0U;
495 	net_pkt_set_vlan_priority(pkt, priority);
496 	zassert_equal(net_pkt_vlan_tag(pkt), tag, "invalid VLAN tag");
497 	zassert_equal(net_pkt_vlan_dei(pkt), dei, "invalid VLAN DEI");
498 	zassert_equal(net_pkt_vlan_priority(pkt), priority,
499 		      "invalid VLAN priority");
500 
501 	zassert_equal(net_pkt_vlan_tci(pkt), 0, "invalid VLAN TCI");
502 
503 	tci = 0U;
504 	tag = 100U;
505 	priority = 3U;
506 
507 	tci = net_eth_vlan_set_vid(tci, tag);
508 	tci = net_eth_vlan_set_pcp(tci, priority);
509 
510 	zassert_equal(tag, net_eth_vlan_get_vid(tci), "Invalid VLAN tag");
511 	zassert_equal(priority, net_eth_vlan_get_pcp(tci),
512 		      "Invalid VLAN priority");
513 
514 	net_pkt_unref(pkt);
515 }
516 
517 /* Enable two VLAN tags and verity that proper interfaces are enabled.
518  */
test_vlan_enable(void)519 static void test_vlan_enable(void)
520 {
521 	struct ethernet_context *eth_ctx;
522 	struct net_if *iface;
523 	int ret;
524 
525 	ret = net_eth_vlan_enable(eth_interfaces[1], VLAN_TAG_1);
526 	zassert_equal(ret, 0, "Cannot enable %d (%d)\n", VLAN_TAG_1, ret);
527 	ret = net_eth_vlan_enable(eth_interfaces[3], VLAN_TAG_2);
528 	zassert_equal(ret, 0, "Cannot enable %d (%d)\n", VLAN_TAG_2, ret);
529 
530 	eth_ctx = net_if_l2_data(eth_interfaces[0]);
531 
532 	iface = net_eth_get_vlan_iface(eth_interfaces[0], VLAN_TAG_1);
533 	zassert_equal_ptr(iface, eth_interfaces[1],
534 			  "Invalid interface for tag %d (%p vs %p)\n",
535 			  VLAN_TAG_1, iface, eth_interfaces[1]);
536 
537 	iface = net_eth_get_vlan_iface(eth_interfaces[0], VLAN_TAG_2);
538 	zassert_equal_ptr(iface, eth_interfaces[3],
539 			  "Invalid interface for tag %d (%p vs %p)\n",
540 			  VLAN_TAG_2, iface, eth_interfaces[3]);
541 
542 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[0]);
543 	zassert_equal(ret, false, "VLAN enabled for interface 0");
544 
545 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[1]);
546 	zassert_equal(ret, true, "VLAN disabled for interface 1");
547 
548 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[2]);
549 	zassert_equal(ret, false, "VLAN enabled for interface 2");
550 
551 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[3]);
552 	zassert_equal(ret, true, "VLAN disabled for interface 3");
553 
554 	iface = eth_interfaces[0];
555 	ret = net_eth_vlan_enable(iface, NET_VLAN_TAG_UNSPEC);
556 	zassert_equal(ret, -EBADF, "Invalid VLAN tag value %d\n", ret);
557 
558 	iface = eth_interfaces[1];
559 	ret = net_eth_vlan_enable(iface, VLAN_TAG_1);
560 	zassert_equal(ret, -EALREADY, "VLAN tag %d enabled for iface 1\n",
561 		      VLAN_TAG_1);
562 }
563 
test_vlan_disable(void)564 static void test_vlan_disable(void)
565 {
566 	struct ethernet_context *eth_ctx;
567 	struct net_if *iface;
568 	int ret;
569 
570 	ret = net_eth_vlan_disable(eth_interfaces[1], VLAN_TAG_1);
571 	zassert_equal(ret, 0, "Cannot disable %d (%d)\n", VLAN_TAG_1, ret);
572 	ret = net_eth_vlan_disable(eth_interfaces[3], VLAN_TAG_2);
573 	zassert_equal(ret, 0, "Cannot disable %d (%d)\n", VLAN_TAG_2, ret);
574 
575 	eth_ctx = net_if_l2_data(eth_interfaces[0]);
576 
577 	iface = net_eth_get_vlan_iface(eth_interfaces[0], VLAN_TAG_1);
578 	zassert_equal_ptr(iface, eth_interfaces[0],
579 			  "Invalid interface for tag %d (%p vs %p)\n",
580 			  VLAN_TAG_1, iface, eth_interfaces[0]);
581 
582 	iface = net_eth_get_vlan_iface(eth_interfaces[0], VLAN_TAG_2);
583 	zassert_equal_ptr(iface, eth_interfaces[0],
584 			  "Invalid interface for tag %d (%p vs %p)\n",
585 			  VLAN_TAG_2, iface, eth_interfaces[0]);
586 
587 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[0]);
588 	zassert_equal(ret, false, "VLAN enabled for interface 0");
589 
590 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[1]);
591 	zassert_equal(ret, false, "VLAN enabled for interface 1");
592 
593 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[2]);
594 	zassert_equal(ret, false, "VLAN enabled for interface 2");
595 
596 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[3]);
597 	zassert_equal(ret, false, "VLAN enabled for interface 3");
598 
599 	iface = eth_interfaces[0];
600 	ret = net_eth_vlan_disable(iface, NET_VLAN_TAG_UNSPEC);
601 	zassert_equal(ret, -EBADF, "Invalid VLAN tag value %d\n", ret);
602 
603 	iface = eth_interfaces[1];
604 	ret = net_eth_vlan_disable(iface, VLAN_TAG_1);
605 	zassert_equal(ret, -ESRCH, "VLAN tag %d disabled for iface 1\n",
606 		      VLAN_TAG_1);
607 }
608 
test_vlan_enable_all(void)609 static void test_vlan_enable_all(void)
610 {
611 	struct ethernet_context *eth_ctx;
612 	struct net_if *iface;
613 	int ret;
614 
615 	ret = net_eth_vlan_enable(eth_interfaces[0], VLAN_TAG_1);
616 	zassert_equal(ret, 0, "Cannot enable %d\n", VLAN_TAG_1);
617 	ret = net_eth_vlan_enable(eth_interfaces[1], VLAN_TAG_2);
618 	zassert_equal(ret, 0, "Cannot enable %d\n", VLAN_TAG_2);
619 	ret = net_eth_vlan_enable(eth_interfaces[2], VLAN_TAG_3);
620 	zassert_equal(ret, 0, "Cannot enable %d\n", VLAN_TAG_3);
621 	ret = net_eth_vlan_enable(eth_interfaces[3], VLAN_TAG_4);
622 	zassert_equal(ret, 0, "Cannot enable %d\n", VLAN_TAG_4);
623 
624 	eth_ctx = net_if_l2_data(eth_interfaces[0]);
625 
626 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[0]);
627 	zassert_equal(ret, true, "VLAN disabled for interface 0");
628 
629 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[1]);
630 	zassert_equal(ret, true, "VLAN disabled for interface 1");
631 
632 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[2]);
633 	zassert_equal(ret, true, "VLAN disabled for interface 2");
634 
635 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[3]);
636 	zassert_equal(ret, true, "VLAN disabled for interface 3");
637 
638 	iface = net_if_get_first_by_type(&NET_L2_GET_NAME(DUMMY));
639 	zassert_not_null(iface, "No dummy iface found");
640 
641 	zassert_equal(net_if_l2(iface), &NET_L2_GET_NAME(DUMMY),
642 		      "Not a dummy interface");
643 
644 	ret = net_eth_vlan_enable(iface, VLAN_TAG_5);
645 	zassert_equal(ret, -EINVAL, "Wrong iface type (%d)\n", ret);
646 }
647 
test_vlan_disable_all(void)648 static void test_vlan_disable_all(void)
649 {
650 	struct ethernet_context *eth_ctx;
651 	struct net_if *iface;
652 	int ret;
653 
654 	ret = net_eth_vlan_disable(eth_interfaces[0], VLAN_TAG_1);
655 	zassert_equal(ret, 0, "Cannot disable %d\n", VLAN_TAG_1);
656 	ret = net_eth_vlan_disable(eth_interfaces[1], VLAN_TAG_2);
657 	zassert_equal(ret, 0, "Cannot disable %d\n", VLAN_TAG_2);
658 	ret = net_eth_vlan_disable(eth_interfaces[2], VLAN_TAG_3);
659 	zassert_equal(ret, 0, "Cannot disable %d\n", VLAN_TAG_3);
660 	ret = net_eth_vlan_disable(eth_interfaces[3], VLAN_TAG_4);
661 	zassert_equal(ret, 0, "Cannot disable %d\n", VLAN_TAG_4);
662 
663 	eth_ctx = net_if_l2_data(eth_interfaces[0]);
664 
665 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[0]);
666 	zassert_equal(ret, false, "VLAN enabled for interface 0");
667 
668 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[1]);
669 	zassert_equal(ret, false, "VLAN enabled for interface 1");
670 
671 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[2]);
672 	zassert_equal(ret, false, "VLAN enabled for interface 2");
673 
674 	ret = net_eth_is_vlan_enabled(eth_ctx, eth_interfaces[3]);
675 	zassert_equal(ret, false, "VLAN enabled for interface 3");
676 
677 	iface = net_if_get_first_by_type(&NET_L2_GET_NAME(DUMMY));
678 	zassert_not_null(iface, "No dummy iface found");
679 
680 	zassert_equal(net_if_l2(iface), &NET_L2_GET_NAME(DUMMY),
681 		      "Not a dummy interface");
682 
683 	ret = net_eth_vlan_disable(iface, VLAN_TAG_5);
684 	zassert_equal(ret, -EINVAL, "Wrong iface type (%d)\n", ret);
685 }
686 
add_neighbor(struct net_if * iface,struct in6_addr * addr)687 static bool add_neighbor(struct net_if *iface, struct in6_addr *addr)
688 {
689 	struct net_linkaddr_storage llstorage;
690 	struct net_linkaddr lladdr;
691 	struct net_nbr *nbr;
692 
693 	llstorage.addr[0] = 0x01;
694 	llstorage.addr[1] = 0x02;
695 	llstorage.addr[2] = 0x33;
696 	llstorage.addr[3] = 0x44;
697 	llstorage.addr[4] = 0x05;
698 	llstorage.addr[5] = 0x06;
699 
700 	lladdr.len = 6U;
701 	lladdr.addr = llstorage.addr;
702 	lladdr.type = NET_LINK_ETHERNET;
703 
704 	nbr = net_ipv6_nbr_add(iface, addr, &lladdr, false,
705 			       NET_IPV6_NBR_STATE_REACHABLE);
706 	if (!nbr) {
707 		DBG("Cannot add dst %s to neighbor cache\n",
708 		    net_sprint_ipv6_addr(addr));
709 		return false;
710 	}
711 
712 	return true;
713 }
714 
test_vlan_send_data(void)715 static void test_vlan_send_data(void)
716 {
717 	struct ethernet_context *eth_ctx; /* This is L2 context */
718 	struct eth_context *ctx; /* This is interface context */
719 	struct net_if *iface;
720 	int ret;
721 	struct sockaddr_in6 dst_addr6 = {
722 		.sin6_family = AF_INET6,
723 		.sin6_port = htons(TEST_PORT),
724 	};
725 	struct sockaddr_in6 src_addr6 = {
726 		.sin6_family = AF_INET6,
727 		.sin6_port = 0,
728 	};
729 
730 	/* Setup the interfaces */
731 	test_vlan_enable();
732 
733 	ret = net_context_get(AF_INET6, SOCK_DGRAM, IPPROTO_UDP,
734 			      &udp_v6_ctx);
735 	zassert_equal(ret, 0, "Create IPv6 UDP context failed");
736 
737 	memcpy(&src_addr6.sin6_addr, &my_addr1, sizeof(struct in6_addr));
738 	memcpy(&dst_addr6.sin6_addr, &dst_addr, sizeof(struct in6_addr));
739 
740 	ret = net_context_bind(udp_v6_ctx, (struct sockaddr *)&src_addr6,
741 			       sizeof(struct sockaddr_in6));
742 	zassert_equal(ret, 0, "Context bind failure test failed");
743 
744 	iface = eth_interfaces[1]; /* This is the VLAN interface */
745 	ctx = net_if_get_device(iface)->data;
746 	eth_ctx = net_if_l2_data(iface);
747 	ret = net_eth_is_vlan_enabled(eth_ctx, iface);
748 	zassert_equal(ret, true, "VLAN disabled for interface 1");
749 
750 	ctx->expecting_tag = VLAN_TAG_1;
751 
752 	iface = eth_interfaces[3]; /* This is also VLAN interface */
753 	ctx = net_if_get_device(iface)->data;
754 	eth_ctx = net_if_l2_data(iface);
755 	ret = net_eth_is_vlan_enabled(eth_ctx, iface);
756 	zassert_equal(ret, true, "VLAN disabled for interface 1");
757 
758 	test_started = true;
759 
760 	ret = add_neighbor(iface, &dst_addr);
761 	zassert_true(ret, "Cannot add neighbor");
762 
763 	ret = net_context_sendto(udp_v6_ctx, test_data, strlen(test_data),
764 				 (struct sockaddr *)&dst_addr6,
765 				 sizeof(struct sockaddr_in6),
766 				 NULL, K_NO_WAIT, NULL);
767 	zassert_true(ret > 0, "Send UDP pkt failed");
768 
769 	if (k_sem_take(&wait_data, WAIT_TIME)) {
770 		DBG("Timeout while waiting interface data\n");
771 		zassert_false(true, "Timeout");
772 	}
773 
774 	net_context_unref(udp_v6_ctx);
775 }
776 
test_main(void)777 void test_main(void)
778 {
779 	ztest_test_suite(net_vlan_test,
780 			 ztest_unit_test(test_vlan_setup),
781 			 ztest_unit_test(test_address_setup),
782 			 ztest_unit_test(test_vlan_tci),
783 			 ztest_unit_test(test_vlan_enable),
784 			 ztest_unit_test(test_vlan_disable),
785 			 ztest_unit_test(test_vlan_enable_all),
786 			 ztest_unit_test(test_vlan_disable_all),
787 			 ztest_unit_test(test_vlan_send_data)
788 			 );
789 
790 	ztest_run_test_suite(net_vlan_test);
791 }
792