/* main.c - Application main entry point */

/*
 * Copyright (c) 2016 Intel Corporation
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#include <zephyr/logging/log.h>
LOG_MODULE_REGISTER(net_test, CONFIG_NET_ARP_LOG_LEVEL);

#include <zephyr/kernel.h>
#include <zephyr/linker/sections.h>

#include <zephyr/tc_util.h>

#include <zephyr/types.h>
#include <stddef.h>
#include <string.h>
#include <errno.h>
#include <zephyr/device.h>
#include <zephyr/init.h>
#include <zephyr/net/net_core.h>
#include <zephyr/net/net_pkt.h>
#include <zephyr/net/net_ip.h>
#include <zephyr/net/dummy.h>
#include <zephyr/ztest.h>
#include <zephyr/random/random.h>

#include "arp.h"

#define NET_LOG_ENABLED 1
#include "net_private.h"

static bool req_test;

static char *app_data = "0123456789";

static bool entry_found;
static struct net_eth_addr *expected_hwaddr;

static struct net_pkt *pending_pkt;

static struct net_eth_addr eth_hwaddr = { { 0x42, 0x11, 0x69, 0xde, 0xfa, 0xec } };

static int send_status = -EINVAL;

struct net_arp_context {
	uint8_t mac_addr[sizeof(struct net_eth_addr)];
	struct net_linkaddr ll_addr;
};

int net_arp_dev_init(const struct device *dev)
{
	struct net_arp_context *net_arp_context = dev->data;

	net_arp_context = net_arp_context;

	return 0;
}

static uint8_t *net_arp_get_mac(const struct device *dev)
{
	struct net_arp_context *context = dev->data;

	if (context->mac_addr[2] == 0x00) {
		/* 00-00-5E-00-53-xx Documentation RFC 7042 */
		context->mac_addr[0] = 0x00;
		context->mac_addr[1] = 0x00;
		context->mac_addr[2] = 0x5E;
		context->mac_addr[3] = 0x00;
		context->mac_addr[4] = 0x53;
		context->mac_addr[5] = sys_rand8_get();
	}

	return context->mac_addr;
}

static void net_arp_iface_init(struct net_if *iface)
{
	uint8_t *mac = net_arp_get_mac(net_if_get_device(iface));

	net_if_set_link_addr(iface, mac, 6, NET_LINK_ETHERNET);
}

static int tester_send(const struct device *dev, struct net_pkt *pkt)
{
	struct net_eth_hdr *hdr;

	if (!pkt->buffer) {
		printk("No data to send!\n");
		return -ENODATA;
	}

	hdr = (struct net_eth_hdr *)net_pkt_data(pkt);

	if (ntohs(hdr->type) == NET_ETH_PTYPE_ARP) {
		/* First frag has eth hdr */
		struct net_arp_hdr *arp_hdr =
			(struct net_arp_hdr *)pkt->frags->frags;

		if (ntohs(arp_hdr->opcode) == NET_ARP_REPLY) {
			if (!req_test && pkt != pending_pkt) {
				printk("Pending data but to be sent is wrong, "
				       "expecting %p but got %p\n",
				       pending_pkt, pkt);
				return -EINVAL;
			}

			if (!req_test && memcmp(&hdr->dst, &eth_hwaddr,
						sizeof(struct net_eth_addr))) {
				char out[sizeof("xx:xx:xx:xx:xx:xx")];

				snprintk(out, sizeof(out), "%s",
					 net_sprint_ll_addr(
						 (uint8_t *)&hdr->dst,
						 sizeof(struct net_eth_addr)));
				printk("Invalid dst hwaddr %s, should be %s\n",
				       out,
				       net_sprint_ll_addr(
					       (uint8_t *)&eth_hwaddr,
					       sizeof(struct net_eth_addr)));
				send_status = -EINVAL;
				return send_status;
			}

		} else if (ntohs(arp_hdr->opcode) == NET_ARP_REQUEST) {
			if (memcmp(&hdr->src, &eth_hwaddr,
				   sizeof(struct net_eth_addr))) {
				char out[sizeof("xx:xx:xx:xx:xx:xx")];

				snprintk(out, sizeof(out), "%s",
					 net_sprint_ll_addr(
						 (uint8_t *)&hdr->src,
						 sizeof(struct net_eth_addr)));
				printk("Invalid src hwaddr %s, should be %s\n",
				       out,
				       net_sprint_ll_addr(
					       (uint8_t *)&eth_hwaddr,
					       sizeof(struct net_eth_addr)));
				send_status = -EINVAL;
				return send_status;
			}
		}
	}

	send_status = 0;

	return 0;
}

static inline struct in_addr *if_get_addr(struct net_if *iface)
{
	int i;

	for (i = 0; i < NET_IF_MAX_IPV4_ADDR; i++) {
		if (iface->config.ip.ipv4->unicast[i].ipv4.is_used &&
		    iface->config.ip.ipv4->unicast[i].ipv4.address.family ==
								AF_INET &&
		    iface->config.ip.ipv4->unicast[i].ipv4.addr_state ==
							NET_ADDR_PREFERRED) {
			return
			    &iface->config.ip.ipv4->unicast[i].ipv4.address.in_addr;
		}
	}

	return NULL;
}

static inline struct net_pkt *prepare_arp_reply(struct net_if *iface,
						struct net_pkt *req,
						struct net_eth_addr *addr,
						struct net_eth_hdr **eth_rep)
{
	struct net_pkt *pkt;
	struct net_arp_hdr *hdr;
	struct net_eth_hdr *eth;

	pkt = net_pkt_alloc_with_buffer(iface, sizeof(struct net_eth_hdr) +
					sizeof(struct net_eth_hdr) +
					sizeof(struct net_arp_hdr),
					AF_UNSPEC, 0, K_SECONDS(1));
	zassert_not_null(pkt, "out of mem reply");

	eth = NET_ETH_HDR(pkt);

	net_buf_add(pkt->buffer, sizeof(struct net_eth_hdr));
	net_buf_pull(pkt->buffer, sizeof(struct net_eth_hdr));

	(void)memset(&eth->dst.addr, 0xff, sizeof(struct net_eth_addr));
	memcpy(&eth->src.addr, net_if_get_link_addr(iface)->addr,
	       sizeof(struct net_eth_addr));
	eth->type = htons(NET_ETH_PTYPE_ARP);

	*eth_rep = eth;

	net_buf_add(pkt->buffer, sizeof(struct net_eth_hdr));
	net_buf_pull(pkt->buffer, sizeof(struct net_eth_hdr));

	hdr = NET_ARP_HDR(pkt);

	hdr->hwtype = htons(NET_ARP_HTYPE_ETH);
	hdr->protocol = htons(NET_ETH_PTYPE_IP);
	hdr->hwlen = sizeof(struct net_eth_addr);
	hdr->protolen = sizeof(struct in_addr);
	hdr->opcode = htons(NET_ARP_REPLY);

	memcpy(&hdr->dst_hwaddr.addr, &eth->src.addr,
	       sizeof(struct net_eth_addr));
	memcpy(&hdr->src_hwaddr.addr, addr,
	       sizeof(struct net_eth_addr));

	net_ipv4_addr_copy_raw(hdr->dst_ipaddr, NET_ARP_HDR(req)->src_ipaddr);
	net_ipv4_addr_copy_raw(hdr->src_ipaddr, NET_ARP_HDR(req)->dst_ipaddr);

	net_buf_add(pkt->buffer, sizeof(struct net_arp_hdr));

	return pkt;
}

static inline struct net_pkt *prepare_arp_request(struct net_if *iface,
						  struct net_pkt *req,
						  struct net_eth_addr *addr,
						  struct net_eth_hdr **eth_hdr)
{
	struct net_pkt *pkt;
	struct net_arp_hdr *hdr, *req_hdr;
	struct net_eth_hdr *eth, *eth_req;

	pkt = net_pkt_alloc_with_buffer(iface, sizeof(struct net_eth_hdr) +
					sizeof(struct net_arp_hdr),
					AF_UNSPEC, 0, K_SECONDS(1));
	zassert_not_null(pkt, "out of mem request");

	eth_req = NET_ETH_HDR(req);
	eth = NET_ETH_HDR(pkt);

	net_buf_add(req->buffer, sizeof(struct net_eth_hdr));
	net_buf_pull(req->buffer, sizeof(struct net_eth_hdr));

	req_hdr = NET_ARP_HDR(req);

	(void)memset(&eth->dst.addr, 0xff, sizeof(struct net_eth_addr));
	memcpy(&eth->src.addr, addr, sizeof(struct net_eth_addr));

	eth->type = htons(NET_ETH_PTYPE_ARP);
	*eth_hdr = eth;

	net_buf_add(pkt->buffer, sizeof(struct net_eth_hdr));
	net_buf_pull(pkt->buffer, sizeof(struct net_eth_hdr));

	hdr = NET_ARP_HDR(pkt);

	hdr->hwtype = htons(NET_ARP_HTYPE_ETH);
	hdr->protocol = htons(NET_ETH_PTYPE_IP);
	hdr->hwlen = sizeof(struct net_eth_addr);
	hdr->protolen = sizeof(struct in_addr);
	hdr->opcode = htons(NET_ARP_REQUEST);

	(void)memset(&hdr->dst_hwaddr.addr, 0x00, sizeof(struct net_eth_addr));
	memcpy(&hdr->src_hwaddr.addr, addr, sizeof(struct net_eth_addr));

	net_ipv4_addr_copy_raw(hdr->src_ipaddr, req_hdr->src_ipaddr);
	net_ipv4_addr_copy_raw(hdr->dst_ipaddr, req_hdr->dst_ipaddr);

	net_buf_add(pkt->buffer, sizeof(struct net_arp_hdr));

	return pkt;
}

static void setup_eth_header(struct net_if *iface, struct net_pkt *pkt,
			     const struct net_eth_addr *hwaddr, uint16_t type)
{
	struct net_eth_hdr *hdr = (struct net_eth_hdr *)net_pkt_data(pkt);

	memcpy(&hdr->dst.addr, hwaddr, sizeof(struct net_eth_addr));
	memcpy(&hdr->src.addr, net_if_get_link_addr(iface)->addr,
	       sizeof(struct net_eth_addr));

	hdr->type = htons(type);
}

struct net_arp_context net_arp_context_data;

#if defined(CONFIG_NET_ARP) && defined(CONFIG_NET_L2_ETHERNET)
static const struct ethernet_api net_arp_if_api = {
	.iface_api.init = net_arp_iface_init,
	.send = tester_send,
};

#define _ETH_L2_LAYER ETHERNET_L2
#define _ETH_L2_CTX_TYPE NET_L2_GET_CTX_TYPE(ETHERNET_L2)
#else
static const struct dummy_api net_arp_if_api = {
	.iface_api.init = net_arp_iface_init,
	.send = tester_send,
};

#define _ETH_L2_LAYER DUMMY_L2
#define _ETH_L2_CTX_TYPE NET_L2_GET_CTX_TYPE(DUMMY_L2)
#endif

NET_DEVICE_INIT(net_arp_test, "net_arp_test",
		net_arp_dev_init, NULL,
		&net_arp_context_data, NULL,
		CONFIG_KERNEL_INIT_PRIORITY_DEFAULT,
		&net_arp_if_api, _ETH_L2_LAYER, _ETH_L2_CTX_TYPE, 127);

static void arp_cb(struct arp_entry *entry, void *user_data)
{
	struct in_addr *addr = user_data;

	if (memcmp(&entry->ip, addr, sizeof(struct in_addr)) == 0 &&
	    memcmp(&entry->eth, expected_hwaddr,
		   sizeof(struct net_eth_addr)) == 0) {
		entry_found = true;
	}
}

ZTEST(arp_fn_tests, test_arp)
{
	if (IS_ENABLED(CONFIG_NET_TC_THREAD_COOPERATIVE)) {
		k_thread_priority_set(k_current_get(),
				K_PRIO_COOP(CONFIG_NUM_COOP_PRIORITIES - 1));
	} else {
		k_thread_priority_set(k_current_get(), K_PRIO_PREEMPT(9));
	}

	struct net_eth_hdr *eth_hdr = NULL;
	struct net_pkt *pkt;
	struct net_pkt *pkt2;
	struct net_if *iface;
	struct net_if_addr *ifaddr;
	struct net_arp_hdr *arp_hdr;
	struct net_ipv4_hdr *ipv4;
	int len;

	struct in_addr dst = { { { 192, 168, 0, 2 } } };
	struct in_addr dst_far = { { { 10, 11, 12, 13 } } };
	struct in_addr dst_far2 = { { { 172, 16, 14, 186 } } };
	struct in_addr src = { { { 192, 168, 0, 1 } } };
	struct in_addr netmask = { { { 255, 255, 255, 0 } } };
	struct in_addr gw = { { { 192, 168, 0, 42 } } };

	net_arp_init();

	iface = net_if_lookup_by_dev(DEVICE_GET(net_arp_test));

	net_if_ipv4_set_gw(iface, &gw);

	/* Unicast test */
	ifaddr = net_if_ipv4_addr_add(iface,
				      &src,
				      NET_ADDR_MANUAL,
				      0);
	zassert_not_null(ifaddr, "Cannot add address");
	ifaddr->addr_state = NET_ADDR_PREFERRED;

	net_if_ipv4_set_netmask_by_addr(iface, &src, &netmask);

	len = strlen(app_data);

	/* Application data for testing */
	pkt = net_pkt_alloc_with_buffer(iface, sizeof(struct net_ipv4_hdr) +
		len, AF_INET, 0, K_SECONDS(1));
	zassert_not_null(pkt, "out of mem");

	net_pkt_lladdr_src(pkt)->addr = (uint8_t *)net_if_get_link_addr(iface);
	net_pkt_lladdr_src(pkt)->len = sizeof(struct net_eth_addr);

	ipv4 = (struct net_ipv4_hdr *)net_buf_add(pkt->buffer,
						  sizeof(struct net_ipv4_hdr));
	net_ipv4_addr_copy_raw(ipv4->src, (uint8_t *)&src);
	net_ipv4_addr_copy_raw(ipv4->dst, (uint8_t *)&dst);

	memcpy(net_buf_add(pkt->buffer, len), app_data, len);

	pkt2 = net_arp_prepare(pkt, &dst, NULL);

	/* pkt2 is the ARP packet and pkt is the IPv4 packet and it was
	 * stored in ARP table.
	 */

	/**TESTPOINTS: Check packets*/
	zassert_not_equal((void *)(pkt2), (void *)(pkt),
		/* The packets cannot be the same as the ARP cache has
		 * still room for the pkt.
		 */
		"ARP cache should still have free space");

	zassert_not_null(pkt2, "ARP pkt is empty");

	/* The ARP cache should now have a link to pending net_pkt
	 * that is to be sent after we have got an ARP reply.
	 */
	zassert_not_null(pkt->buffer,
		"Pending pkt buffer is NULL");

	pending_pkt = pkt;

	/* pkt2 should contain the arp header, verify it */
	arp_hdr = NET_ARP_HDR(pkt2);

	if (arp_hdr->hwtype != htons(NET_ARP_HTYPE_ETH)) {
		printk("ARP hwtype 0x%x, should be 0x%x\n",
		       arp_hdr->hwtype, htons(NET_ARP_HTYPE_ETH));
		zassert_true(0, "exiting");
	}

	if (arp_hdr->protocol != htons(NET_ETH_PTYPE_IP)) {
		printk("ARP protocol 0x%x, should be 0x%x\n",
		       arp_hdr->protocol, htons(NET_ETH_PTYPE_IP));
		zassert_true(0, "exiting");
	}

	if (arp_hdr->hwlen != sizeof(struct net_eth_addr)) {
		printk("ARP hwlen 0x%x, should be 0x%zx\n",
		       arp_hdr->hwlen, sizeof(struct net_eth_addr));
		zassert_true(0, "exiting");
	}

	if (arp_hdr->protolen != sizeof(struct in_addr)) {
		printk("ARP IP addr len 0x%x, should be 0x%zx\n",
		       arp_hdr->protolen, sizeof(struct in_addr));
		zassert_true(0, "exiting");
	}

	if (arp_hdr->opcode != htons(NET_ARP_REQUEST)) {
		printk("ARP opcode 0x%x, should be 0x%x\n",
		       arp_hdr->opcode, htons(NET_ARP_REQUEST));
		zassert_true(0, "exiting");
	}

	if (!net_ipv4_addr_cmp_raw(arp_hdr->dst_ipaddr,
				   NET_IPV4_HDR(pkt)->dst)) {
		printk("ARP IP dest invalid %s, should be %s",
			net_sprint_ipv4_addr(&arp_hdr->dst_ipaddr),
			net_sprint_ipv4_addr(&NET_IPV4_HDR(pkt)->dst));
		zassert_true(0, "exiting");
	}

	if (!net_ipv4_addr_cmp_raw(arp_hdr->src_ipaddr,
				   NET_IPV4_HDR(pkt)->src)) {
		printk("ARP IP src invalid %s, should be %s",
			net_sprint_ipv4_addr(&arp_hdr->src_ipaddr),
			net_sprint_ipv4_addr(&NET_IPV4_HDR(pkt)->src));
		zassert_true(0, "exiting");
	}

	/* We could have send the new ARP request but for this test we
	 * just free it.
	 */
	net_pkt_unref(pkt2);

	zassert_equal(atomic_get(&pkt->atomic_ref), 2,
		"ARP cache should own the original packet");

	/* Then a case where target is not in the same subnet */
	net_ipv4_addr_copy_raw(ipv4->dst, (uint8_t *)&dst_far);

	pkt2 = net_arp_prepare(pkt, &dst_far, NULL);

	zassert_not_equal((void *)(pkt2), (void *)(pkt),
		"ARP cache should not find anything");

	/**TESTPOINTS: Check if packets not empty*/
	zassert_not_null(pkt2,
		"ARP pkt2 is empty");

	arp_hdr = NET_ARP_HDR(pkt2);

	if (!net_ipv4_addr_cmp_raw(arp_hdr->dst_ipaddr,
				   (uint8_t *)&iface->config.ip.ipv4->gw)) {
		printk("ARP IP dst invalid %s, should be %s\n",
			net_sprint_ipv4_addr(&arp_hdr->dst_ipaddr),
			net_sprint_ipv4_addr(&iface->config.ip.ipv4->gw));
		zassert_true(0, "exiting");
	}

	net_pkt_unref(pkt2);

	/* Try to find the same destination again, this should fail as there
	 * is a pending request in ARP cache.
	 */
	net_ipv4_addr_copy_raw(ipv4->dst, (uint8_t *)&dst_far);

	/* Make sure prepare will not free the pkt because it will be
	 * needed in the later test case.
	 */
	net_pkt_ref(pkt);

	pkt2 = net_arp_prepare(pkt, &dst_far, NULL);

	zassert_not_null(pkt2,
		"ARP cache is not sending the request again");

	net_pkt_unref(pkt2);

	/* Try to find the different destination, this should fail too
	 * as the cache table should be full.
	 */
	net_ipv4_addr_copy_raw(ipv4->dst, (uint8_t *)&dst_far2);

	/* Make sure prepare will not free the pkt because it will be
	 * needed in the next test case.
	 */
	net_pkt_ref(pkt);

	pkt2 = net_arp_prepare(pkt, &dst_far2, NULL);

	zassert_not_null(pkt2,
		"ARP cache did not send a req");

	/* Restore the original address so that following test case can
	 * work properly.
	 */
	net_ipv4_addr_copy_raw(ipv4->dst, (uint8_t *)&dst);

	/* The arp request packet is now verified, create an arp reply.
	 * The previous value of pkt is stored in arp table and is not lost.
	 */
	pkt = net_pkt_alloc_with_buffer(iface, sizeof(struct net_eth_hdr) +
					sizeof(struct net_arp_hdr),
					AF_UNSPEC, 0, K_SECONDS(1));
	zassert_not_null(pkt, "out of mem reply");

	arp_hdr = NET_ARP_HDR(pkt);
	net_buf_add(pkt->buffer, sizeof(struct net_arp_hdr));

	net_ipv4_addr_copy_raw(arp_hdr->dst_ipaddr, (uint8_t *)&dst);
	net_ipv4_addr_copy_raw(arp_hdr->src_ipaddr, (uint8_t *)&src);

	pkt2 = prepare_arp_reply(iface, pkt, &eth_hwaddr, &eth_hdr);

	zassert_not_null(pkt2, "ARP reply generation failed.");

	/* The pending packet should now be sent */
	switch (net_arp_input(pkt2, eth_hdr)) {
	case NET_OK:
	case NET_CONTINUE:
		break;
	case NET_DROP:
		break;
	}

	/* Yielding so that network interface TX thread can proceed. */
	k_yield();

	/**TESTPOINTS: Check ARP reply*/
	zassert_false(send_status < 0, "ARP reply was not sent");

	zassert_equal(atomic_get(&pkt->atomic_ref), 1,
		      "ARP cache should no longer own the original packet");

	net_pkt_unref(pkt);

	/* Then feed in ARP request */
	pkt = net_pkt_alloc_with_buffer(iface, sizeof(struct net_eth_hdr) +
					sizeof(struct net_arp_hdr),
					AF_UNSPEC, 0, K_SECONDS(1));
	zassert_not_null(pkt, "out of mem reply");

	send_status = -EINVAL;

	setup_eth_header(iface, pkt, &eth_hwaddr, NET_ETH_PTYPE_ARP);

	arp_hdr = (struct net_arp_hdr *)(pkt->buffer->data +
					 (sizeof(struct net_eth_hdr)));
	net_buf_add(pkt->buffer, sizeof(struct net_arp_hdr));

	net_ipv4_addr_copy_raw(arp_hdr->dst_ipaddr, (uint8_t *)&src);
	net_ipv4_addr_copy_raw(arp_hdr->src_ipaddr, (uint8_t *)&dst);

	pkt2 = prepare_arp_request(iface, pkt, &eth_hwaddr, &eth_hdr);

	/**TESTPOINT: Check if ARP request generation failed*/
	zassert_not_null(pkt2, "ARP request generation failed.");

	req_test = true;

	switch (net_arp_input(pkt2, eth_hdr)) {
	case NET_OK:
	case NET_CONTINUE:
		break;
	case NET_DROP:
		break;
	}

	/* Yielding so that network interface TX thread can proceed. */
	k_yield();

	/**TESTPOINT: Check if ARP request sent*/
	zassert_false(send_status < 0, "ARP req was not sent");

	net_pkt_unref(pkt);

	/**TESTPOINT: Check gratuitous ARP */
	if (IS_ENABLED(CONFIG_NET_ARP_GRATUITOUS)) {
		struct net_eth_addr new_hwaddr = {
			{ 0x11, 0x12, 0x13, 0x14, 0x15, 0x16 }
		};
		enum net_verdict verdict;

		/* First make sure that we have an entry in cache */
		entry_found = false;
		expected_hwaddr = &eth_hwaddr;
		net_arp_foreach(arp_cb, &dst);
		zassert_true(entry_found, "Entry not found");

		pkt = net_pkt_alloc_with_buffer(iface,
						sizeof(struct net_eth_hdr) +
						sizeof(struct net_arp_hdr),
						AF_UNSPEC, 0, K_SECONDS(1));
		zassert_not_null(pkt, "out of mem request");

		setup_eth_header(iface, pkt, net_eth_broadcast_addr(),
				 NET_ETH_PTYPE_ARP);

		eth_hdr = (struct net_eth_hdr *)net_pkt_data(pkt);
		net_buf_add(pkt->buffer, sizeof(struct net_eth_hdr));
		net_buf_pull(pkt->buffer, sizeof(struct net_eth_hdr));
		arp_hdr = NET_ARP_HDR(pkt);

		arp_hdr->hwtype = htons(NET_ARP_HTYPE_ETH);
		arp_hdr->protocol = htons(NET_ETH_PTYPE_IP);
		arp_hdr->hwlen = sizeof(struct net_eth_addr);
		arp_hdr->protolen = sizeof(struct in_addr);
		arp_hdr->opcode = htons(NET_ARP_REQUEST);
		memcpy(&arp_hdr->src_hwaddr, &new_hwaddr, 6);
		memcpy(&arp_hdr->dst_hwaddr, net_eth_broadcast_addr(), 6);
		net_ipv4_addr_copy_raw(arp_hdr->dst_ipaddr, (uint8_t *)&dst);
		net_ipv4_addr_copy_raw(arp_hdr->src_ipaddr, (uint8_t *)&dst);

		net_buf_add(pkt->buffer, sizeof(struct net_arp_hdr));

		verdict = net_arp_input(pkt, eth_hdr);
		zassert_not_equal(verdict, NET_DROP, "Gratuitous ARP failed");

		/* Then check that the HW address is changed for an existing
		 * entry.
		 */
		entry_found = false;
		expected_hwaddr = &new_hwaddr;
		net_arp_foreach(arp_cb, &dst);
		zassert_true(entry_found, "Changed entry not found");

		net_pkt_unref(pkt);
	}
}

ZTEST_SUITE(arp_fn_tests, NULL, NULL, NULL, NULL, NULL);
