This is an automated email from the ASF dual-hosted git repository. xiaoxiang pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/nuttx.git
commit adb161aa10ec70f0643e0dca8d715c49e5a38724 Author: zhanghongyu <[email protected]> AuthorDate: Fri Aug 29 16:15:18 2025 +0800 arp: the manually configured arp table should not have a timeout period Improve the behavior of the ARP table so that the manually configured ARP table has the highest priority, can only be manually modified to other values, otherwise will never change again, and will not time out. The modified behavior is consistent with that of Linux. Signed-off-by: zhanghongyu <[email protected]> --- net/arp/arp.h | 6 ++++-- net/arp/arp_out.c | 2 +- net/arp/arp_send.c | 2 +- net/arp/arp_table.c | 28 +++++++++++++++++++--------- net/netdev/netdev_ioctl.c | 3 ++- 5 files changed, 27 insertions(+), 14 deletions(-) diff --git a/net/arp/arp.h b/net/arp/arp.h index 1c4d44849c6..06a715b93db 100644 --- a/net/arp/arp.h +++ b/net/arp/arp.h @@ -164,6 +164,7 @@ struct arp_entry_s in_addr_t at_ipaddr; /* IP address */ struct ether_addr at_ethaddr; /* Hardware address */ clock_t at_time; /* Time of last usage */ + uint8_t at_flags; /* Flags, examples: ATF_PERM */ FAR struct net_driver_s *at_dev; /* The device driver structure */ }; @@ -471,6 +472,7 @@ void arp_cleanup(FAR struct net_driver_s *dev); * dev - The device driver structure * ipaddr - The IP address as an inaddr_t * ethaddr - Refers to a HW address uint8_t[IFHWADDRLEN] + * flags - Flags, examples: ATF_PERM(Permanent entry) * * Returned Value: * Zero (OK) if the ARP table entry was successfully modified. A negated @@ -482,7 +484,7 @@ void arp_cleanup(FAR struct net_driver_s *dev); ****************************************************************************/ int arp_update(FAR struct net_driver_s *dev, in_addr_t ipaddr, - FAR const uint8_t *ethaddr); + FAR const uint8_t *ethaddr, uint8_t flags); /**************************************************************************** * Name: arp_hdr_update @@ -623,7 +625,7 @@ void arp_acd_setup(FAR struct net_driver_s *dev); # define arp_find(i,e,d,u) (-ENOSYS) # define arp_delete(i,d) (-ENOSYS) # define arp_cleanup(d) -# define arp_update(d,i,m); +# define arp_update(d,i,m,f); # define arp_hdr_update(d,i,m); # define arp_snapshot(s,n) (0) # define arp_dump(arp) diff --git a/net/arp/arp_out.c b/net/arp/arp_out.c index fa465e30922..120b2deef10 100644 --- a/net/arp/arp_out.c +++ b/net/arp/arp_out.c @@ -283,7 +283,7 @@ void arp_out(FAR struct net_driver_s *dev) * send ARP request for same destination. */ - arp_update(dev, ipaddr, NULL); + arp_update(dev, ipaddr, NULL, 0); /* The destination address was not in our ARP table, so we overwrite * the IP packet with an ARP request. diff --git a/net/arp/arp_send.c b/net/arp/arp_send.c index 34c5f1acf14..a44bf3dd763 100644 --- a/net/arp/arp_send.c +++ b/net/arp/arp_send.c @@ -367,7 +367,7 @@ int arp_send(in_addr_t ipaddr) if (state.snd_retries == 0) { - arp_update(dev, ipaddr, NULL); + arp_update(dev, ipaddr, NULL, 0); sending = true; } diff --git a/net/arp/arp_table.c b/net/arp/arp_table.c index 3cdf35c4c0a..7c65b0f498f 100644 --- a/net/arp/arp_table.c +++ b/net/arp/arp_table.c @@ -169,6 +169,10 @@ arp_return_old_entry(FAR struct arp_entry_s *e1, FAR struct arp_entry_s *e2) { return e2; } + else if ((e1->at_flags & ATF_PERM) != (e2->at_flags & ATF_PERM)) + { + return (e1->at_flags & ATF_PERM) == 0 ? e1 : e2; + } else if ((int)(e1->at_time - e2->at_time) <= 0) { return e1; @@ -220,7 +224,8 @@ static FAR struct arp_entry_s *arp_lookup(in_addr_t ipaddr, /* Check if it has expired */ - if (clock_systime_ticks() - tabptr->at_time <= ARP_MAXAGE_TICK) + if ((tabptr->at_flags & ATF_PERM) != 0 || + clock_systime_ticks() - tabptr->at_time <= ARP_MAXAGE_TICK) { return tabptr; } @@ -279,6 +284,7 @@ static void arp_get_arpreq(FAR struct arpreq *output, * dev - The device driver structure * ipaddr - The IP address as an inaddr_t * ethaddr - Refers to a HW address uint8_t[IFHWADDRLEN] + * flags - Flags, examples: ATF_PERM(Permanent entry) * * Returned Value: * Zero (OK) if the ARP table entry was successfully modified. A negated @@ -290,7 +296,7 @@ static void arp_get_arpreq(FAR struct arpreq *output, ****************************************************************************/ int arp_update(FAR struct net_driver_s *dev, in_addr_t ipaddr, - FAR const uint8_t *ethaddr) + FAR const uint8_t *ethaddr, uint8_t flags) { FAR struct arp_entry_s *tabptr = &g_arptable[0]; #ifdef CONFIG_NETLINK_ROUTE @@ -355,10 +361,14 @@ int arp_update(FAR struct net_driver_s *dev, in_addr_t ipaddr, * information. */ - tabptr->at_ipaddr = ipaddr; - memcpy(tabptr->at_ethaddr.ether_addr_octet, ethaddr, ETHER_ADDR_LEN); - tabptr->at_dev = dev; - tabptr->at_time = clock_systime_ticks(); + if ((tabptr->at_flags & ATF_PERM) == 0 || (flags & ATF_PERM) != 0) + { + memcpy(tabptr->at_ethaddr.ether_addr_octet, ethaddr, ETHER_ADDR_LEN); + tabptr->at_ipaddr = ipaddr; + tabptr->at_time = clock_systime_ticks(); + tabptr->at_flags = flags; + tabptr->at_dev = dev; + } /* Notify the new entry */ @@ -401,7 +411,7 @@ void arp_hdr_update(FAR struct net_driver_s *dev, FAR uint16_t *pipaddr, /* Update the ARP table */ - arp_update(dev, ipaddr, ethaddr); + arp_update(dev, ipaddr, ethaddr, 0); } /**************************************************************************** @@ -598,8 +608,8 @@ unsigned int arp_snapshot(FAR struct arpreq *snapshot, i++) { tabptr = &g_arptable[i]; - if (tabptr->at_ipaddr != 0 && - now - tabptr->at_time <= ARP_MAXAGE_TICK) + if (tabptr->at_ipaddr != 0 && ((tabptr->at_flags & ATF_PERM) != 0 || + now - tabptr->at_time <= ARP_MAXAGE_TICK)) { arp_get_arpreq(&snapshot[ncopied], tabptr); ncopied++; diff --git a/net/netdev/netdev_ioctl.c b/net/netdev/netdev_ioctl.c index 61efcac5f0f..70b05275f7d 100644 --- a/net/netdev/netdev_ioctl.c +++ b/net/netdev/netdev_ioctl.c @@ -1491,7 +1491,8 @@ static int netdev_arp_ioctl(FAR struct socket *psock, int cmd, */ ret = arp_update(dev, addr->sin_addr.s_addr, - (FAR const uint8_t *)req->arp_ha.sa_data); + (FAR const uint8_t *)req->arp_ha.sa_data, + req->arp_flags); } else {
