如何用程序而不是命令清除linux中的arp缓存

如何用程序而不是命令清除linux中的arp缓存,linux,arp,Linux,Arp,如何通过程序而不是使用arp命令清除linux中的arp缓存?是否有可用的库函数来实现此功能 =========================================================================== 编辑 在linux中,我希望定期清除arp缓存,并发送ping数据包以查找局域网中的主机(通过收集arp响应和ICMP响应)。由于一些主机不回复ping,我尝试在程序中接收arp响应和ICMP响应。但是如果arp缓存有IP信息,它不会发送该IP的arp请

如何通过程序而不是使用arp命令清除linux中的arp缓存?是否有可用的库函数来实现此功能

=========================================================================== 编辑


linux
中,我希望定期清除
arp缓存
,并发送ping数据包以查找局域网中的主机(通过收集arp响应和ICMP响应)。由于一些主机不回复ping,我尝试在程序中接收arp响应和ICMP响应。但是如果arp缓存有IP信息,它不会发送该IP的arp请求,并且拓扑可能不完整。所以我想定期清除arp缓存。如何在我的程序中定期清除arp缓存?谢谢您的时间。

arp缓存可能包含在以下文件之一中(没有官方建议):


您可以通过程序访问此文件,并对其执行任何操作。

事实证明,它并没有那么糟糕。你必须:

  • 如果尚未创建原始套接字,请创建原始套接字。您可以使用ICMP套接字或任何您想要的IPPROTO来完成。我已经用ICMP套接字对它进行了测试
  • int sd=socket(PF_INET、SOCK_RAW、IPPROTO_ICMP);
    

  • 从缓存中获取要刷新的IP的sockaddr。您可以使用gethostbyname或各种机制来实现这一点。我会打电话给我们的地址
    hostaddy

  • 创建一个arpreq结构,并将除arp_pa字段外的所有字段设置为零

  • struct-arpreq-ar;
    memset(&ar,0,sizeof(ar));
    memcpy(&ar.arp_pa,hostaddy,sizeof(struct sockaddr_in));
    

  • 在套接字和结构上调用
    ioctl
    ,使用
    SIOCDARP
  • int-ret=ioctl(sd、SIOCDARP和ar);
    if(ret)fprintf(stderr,“清除条目失败。\n”);
    

  • 如果您不打算再使用套接字,请不要忘记关闭它。
    close(sd)
  • 资料来源:(1)
    strace arp-d

    (2)

    以下是我为python制作的示例:

    import fcntl
    import socket
    import struct
    import ipaddress
    
    def clear_arp(ip, ifname=''):
        while True:
            try:
                sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)    
                ip_bytes = int(ipaddress.IPv4Address(ip)).to_bytes(4, byteorder='big')
                fcntl.ioctl(
                    sock.fileno(),
                        0x8953, # SIOCDARP
                        struct.pack('hh48s16s', socket.AF_INET, 0, ip_bytes, ifname[:15].encode())
                    )
            except OSError as e:
                break
            finally:
                sock.close()
    
                        struct.pack('hh48s16s', socket.AF_INET, 0, ip_bytes, ifname[:15].encode())
                    )
            except OSError as e:
                break
            finally:
                sock.close()
    

    你用哪种语言编程?对于C,可以使用
    execv
    调用。关于代码示例,请参见此答案:,对于Java,请参见谢谢!是的,对于C。程序需要定期清除arp缓存并执行其他操作。我不认为
    execv
    可以做到这一点。如果执行另一个文件,我如何控制流程来做其他事情?如果您需要定期这样做,您可以将您的bin放在cron.*文件夹中(还有其他解决方案),我不明白。它在
    linux
    中,谢谢!我编辑了这个问题,使它更清楚。是否有可以清除arp缓存的函数?否,您应该使用您使用的语言I/O函数来访问这些文件(
    fopen()
    fread()
    在C中,等等)
    import fcntl
    import socket
    import struct
    import ipaddress
    
    def clear_arp(ip, ifname=''):
        while True:
            try:
                sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)    
                ip_bytes = int(ipaddress.IPv4Address(ip)).to_bytes(4, byteorder='big')
                fcntl.ioctl(
                    sock.fileno(),
                        0x8953, # SIOCDARP
                        struct.pack('hh48s16s', socket.AF_INET, 0, ip_bytes, ifname[:15].encode())
                    )
            except OSError as e:
                break
            finally:
                sock.close()
    
                        struct.pack('hh48s16s', socket.AF_INET, 0, ip_bytes, ifname[:15].encode())
                    )
            except OSError as e:
                break
            finally:
                sock.close()