文章目录
-
- [1. ARP状态机](#1. ARP状态机)
-
- [1.1 ARP状态类型](#1.1 ARP状态类型)
- [1.2 状态转换图](#1.2 状态转换图)
- [2. 超时时间与参数](#2. 超时时间与参数)
-
- [2.1 主要超时参数](#2.1 主要超时参数)
-
- [2.1.1 基础时间参数](#2.1.1 基础时间参数)
- [2.1.2 探测相关参数](#2.1.2 探测相关参数)
- [2.1.3 垃圾回收参数](#2.1.3 垃圾回收参数)
- [3. 主机发送ARP报文的时机](#3. 主机发送ARP报文的时机)
-
- [3.1 发送数据包时发现ARP缓存中没有目标IP的MAC地址](#3.1 发送数据包时发现ARP缓存中没有目标IP的MAC地址)
- [3.2 ARP条目进入STALE状态后需要发送数据](#3.2 ARP条目进入STALE状态后需要发送数据)
- [3.3 定期维护ARP缓存](#3.3 定期维护ARP缓存)
- [3.4 处理ARP冲突](#3.4 处理ARP冲突)
- [3.5 响应ARP请求](#3.5 响应ARP请求)
- [4. 状态转换详解](#4. 状态转换详解)
-
- [4.1 REACHABLE状态](#4.1 REACHABLE状态)
- [4.2 STALE状态](#4.2 STALE状态)
- [4.3 DELAY状态](#4.3 DELAY状态)
- [4.4 PROBE状态](#4.4 PROBE状态)
- [4.5 INCOMPLETE状态](#4.5 INCOMPLETE状态)
- [5. 垃圾回收机制](#5. 垃圾回收机制)
-
- [5.1 触发条件](#5.1 触发条件)
- [5.2 清理策略](#5.2 清理策略)
- [6. 参数调优建议](#6. 参数调优建议)
-
- [6.1 高可用性网络](#6.1 高可用性网络)
- [6.2 动态网络环境](#6.2 动态网络环境)
- [6.3 大规模网络](#6.3 大规模网络)
- [7. 监控和调试](#7. 监控和调试)
-
- [7.1 查看ARP表](#7.1 查看ARP表)
- [7.2 ip neigh命令详细使用方法](#7.2 ip neigh命令详细使用方法)
-
- [7.2.1 基本语法](#7.2.1 基本语法)
- [7.2.2 查看操作](#7.2.2 查看操作)
- [7.2.3 添加和修改操作](#7.2.3 添加和修改操作)
- [7.2.4 删除操作](#7.2.4 删除操作)
- [7.2.5 常用参数说明](#7.2.5 常用参数说明)
- [7.3 查看统计信息](#7.3 查看统计信息)
- [7.4 实时监控](#7.4 实时监控)
- [8. 常见问题和解决方案](#8. 常见问题和解决方案)
-
- [8.1 ARP表项频繁变化](#8.1 ARP表项频繁变化)
- [8.2 ARP请求失败](#8.2 ARP请求失败)
- [8.3 ARP表溢出](#8.3 ARP表溢出)
1. ARP状态机
Linux内核中ARP表项具有多种状态,这些状态会根据网络通信情况和时间进行转换。ARP状态主要包括:
1.1 ARP状态类型
- NUD_INCOMPLETE: 地址解析中,正在解析硬件地址但尚未收到回复
- NUD_REACHABLE: 可达状态,已确认邻居可达
- NUD_STALE: 陈旧状态,之前可达但已超过可达时间
- NUD_DELAY: 延迟状态,临时状态,在进入PROBE前等待上层确认
- NUD_PROBE: 探测状态,正在主动探测邻居是否仍然可达
- NUD_FAILED: 失败状态,多次尝试后仍无法解析或确认邻居
- NUD_NOARP: 无需ARP状态,如本地回环地址或点对点链路
- NUD_PERMANENT: 永久状态,静态ARP条目,不会超时
1.2 状态转换图
CREATE RECV 多次请求无响应 AGED(超时) UPDATE USED(有数据发送) 长时间未使用(垃圾回收) 超时 收到响应 多次探测无响应 垃圾回收 直接探测 INCOMPLETE REACHABLE FAILED STALE DELAY PROBE
2. 超时时间与参数
2.1 主要超时参数
Linux ARP老化机制涉及多个可配置参数,这些参数控制着ARP条目的状态转换和超时行为。
2.1.1 基础时间参数
-
base_reachable_time_ms: 基础可达时间(毫秒)
- 默认值:30000ms(30秒)
- 作用:ARP条目保持REACHABLE状态的时间
- 路径:
/proc/sys/net/ipv4/neigh/*/base_reachable_time_ms
-
gc_stale_time: 垃圾回收陈旧时间(秒)
- 默认值:60秒
- 作用:ARP条目在未被使用后变为STALE状态的时间
- 路径:
/proc/sys/net/ipv4/neigh/*/gc_stale_time
-
retrans_time_ms: 重传时间(毫秒)
- 默认值:1000ms(1秒)
- 作用:ARP请求重传的间隔时间
- 路径:
/proc/sys/net/ipv4/neigh/*/retrans_time_ms
2.1.2 探测相关参数
-
ucast_solicit: 单播探测次数
- 默认值:3次
- 作用:在PROBE状态下发送单播ARP请求的次数
- 路径:
/proc/sys/net/ipv4/neigh/*/ucast_solicit
-
mcast_solicit: 组播探测次数
- 默认值:3次
- 作用:在INCOMPLETE状态下发送组播ARP请求的次数
- 路径:
/proc/sys/net/ipv4/neigh/*/mcast_solicit
-
anycast_delay: 任播延迟(毫秒)
- 默认值:1000ms(1秒)
- 作用:任播地址的延迟探测时间
- 路径:
/proc/sys/net/ipv4/neigh/*/anycast_delay
-
proxy_delay: 代理ARP延迟(毫秒)
- 默认值:800ms
- 作用:代理ARP回复前的延迟时间
- 路径:
/proc/sys/net/ipv4/neigh/*/proxy_delay
2.1.3 垃圾回收参数
-
gc_thresh1: 垃圾回收阈值1
- 默认值:128
- 作用:ARP表项数量低于此值时不会进行垃圾回收
-
gc_thresh2: 垃圾回收阈值2
- 默认值:512
- 作用:ARP表项数量超过此值时开始进行垃圾回收
-
gc_thresh3: 垃圾回收阈值3
- 默认值:1024
- 作用:ARP表项数量上限,超过时强制清理
这些参数的路径通常在:
/proc/sys/net/ipv4/neigh/*/
(*代表具体网络接口如eth0,default代表默认值)/proc/sys/net/ipv6/neigh/*/
(IPv6邻居发现参数)
3. 主机发送ARP报文的时机
主机在以下几种情况下会发送ARP报文:
3.1 发送数据包时发现ARP缓存中没有目标IP的MAC地址
当主机需要向同一局域网内的另一个IP地址发送数据包时,如果ARP缓存中没有该IP对应的MAC地址,主机将发送ARP请求报文来解析目标MAC地址。
过程如下:
- 检查ARP缓存表中是否存在目标IP的条目
- 如果不存在或状态为FAILED,则创建INCOMPLETE状态的条目
- 发送ARP请求广播报文
- 等待ARP响应,收到响应后更新ARP缓存并进入REACHABLE状态
3.2 ARP条目进入STALE状态后需要发送数据
当ARP条目处于STALE状态且主机需要向该目标发送数据时,会触发ARP解析过程:
- ARP条目从STALE状态进入DELAY状态
- 在DELAY状态等待短暂时间,期望上层协议提供确认
- 如果未收到确认,则进入PROBE状态
- 发送单播ARP请求探测目标是否仍然可达
- 收到响应后返回REACHABLE状态
3.3 定期维护ARP缓存
系统会定期检查ARP表项的状态,并在必要时发送ARP请求来验证邻居的可达性:
- 当条目接近或超过base_reachable_time_ms设置的时间时
- 系统可能会主动发送ARP请求来确认邻居仍然可达
- 这有助于在网络拓扑发生变化时及时更新ARP表
3.4 处理ARP冲突
当主机检测到IP地址冲突时,可能会发送ARP报文来解决冲突:
- 收到ARP请求或响应中包含与自己IP相同的地址
- 主动发送ARP请求或响应声明自己的IP和MAC地址
- 这种机制有助于检测和解决IP地址冲突
3.5 响应ARP请求
当主机收到针对自己IP地址的ARP请求时,会发送ARP响应报文:
- 接收ARP请求广播报文
- 检查请求的IP地址是否为自己配置的IP地址
- 如果匹配,则发送包含自己MAC地址的ARP响应报文
- 更新自己的ARP缓存表(如果需要)
4. 状态转换详解
4.1 REACHABLE状态
当系统成功发送或接收到目标主机的数据包时,ARP条目进入REACHABLE状态。在此状态下,系统认为邻居是可达的,无需进行额外的ARP请求。
- 超时时间 :由
base_reachable_time_ms
参数决定 - 状态转换 :
- 超时后进入STALE状态
- 收到更新的ARP回复时保持在REACHABLE状态
4.2 STALE状态
当ARP条目在REACHABLE状态超时后,会进入STALE状态。在此状态下,ARP条目仍然可用,但系统不确定邻居是否仍然可达。
- 超时时间 :由
gc_stale_time
参数决定 - 状态转换 :
- 当有数据包需要发送给该邻居时,进入DELAY状态
- 如果长时间未使用,会被垃圾回收机制清理
4.3 DELAY状态
当有数据包需要发送给处于STALE状态的邻居时,ARP条目会先进入DELAY状态。
- 超时时间:通常为几秒钟(由内核实现决定)
- 状态转换 :
- 超时后进入PROBE状态
- 如果在延迟期间收到上层确认,可能返回REACHABLE状态
4.4 PROBE状态
在PROBE状态下,系统会主动探测邻居是否仍然可达。
- 探测次数 :由
ucast_solicit
参数决定 - 探测间隔 :由
retrans_time_ms
参数决定 - 状态转换 :
- 收到ARP回复则进入REACHABLE状态
- 探测次数用尽仍未收到回复则进入FAILED状态
4.5 INCOMPLETE状态
当系统需要解析一个新的IP地址对应的MAC地址时,ARP条目处于INCOMPLETE状态。
- 探测次数 :由
mcast_solicit
参数决定 - 探测间隔 :由
retrans_time_ms
参数决定 - 状态转换 :
- 收到ARP回复则进入REACHABLE状态
- 探测次数用尽仍未收到回复则进入FAILED状态
5. 垃圾回收机制
Linux内核通过垃圾回收机制定期清理无用的ARP条目,以防止ARP表无限增长。
5.1 触发条件
- ARP表项数量超过
gc_thresh2
- 系统定时检查(通常每30秒)
- ARP表项数量超过
gc_thresh3
时强制清理
5.2 清理策略
- 优先清理FAILED状态的条目
- 清理长时间处于STALE状态的条目
- 根据最近使用时间清理条目
6. 参数调优建议
6.1 高可用性网络
对于要求高可用性的网络环境:
# 增加可达时间,减少ARP请求频率
net.ipv4.neigh.default.base_reachable_time_ms = 60000
# 延长陈旧时间
net.ipv4.neigh.default.gc_stale_time = 120
6.2 动态网络环境
对于设备频繁接入/断开的网络环境:
# 缩短可达时间,快速发现设备状态变化
net.ipv4.neigh.default.base_reachable_time_ms = 15000
# 缩短陈旧时间
net.ipv4.neigh.default.gc_stale_time = 30
6.3 大规模网络
对于大规模网络环境,需要调整ARP表大小:
# 增加ARP表项上限
net.ipv4.neigh.default.gc_thresh1 = 256
net.ipv4.neigh.default.gc_thresh2 = 1024
net.ipv4.neigh.default.gc_thresh3 = 2048
7. 监控和调试
7.1 查看ARP表
# 查看所有ARP条目
ip neighbour show
# 查看特定接口的ARP条目
ip neighbour show dev eth0
# 查看特定状态的ARP条目
ip neighbour show nud reachable
7.2 ip neigh命令详细使用方法
ip neigh\](file:///home/avatr/work/github/kg/fragment/c/test-socket-tcp/tcp_client.c#L54-L54)命令是Linux系统中用于管理邻居表(ARP表)的强大工具,提供了丰富的选项来查看、添加、删除和修改ARP条目。 ##### 7.2.1 基本语法 ip neighbour { add | del | change | replace | show } { IP地址 } [参数] ##### 7.2.2 查看操作 # 显示所有邻居条目 ip neighbour show # 显示特定接口的邻居条目 ip neighbour show dev eth0 # 显示特定状态的邻居条目 ip neighbour show nud reachable ip neighbour show nud stale ip neighbour show nud failed # 显示特定IP地址的邻居条目 ip neighbour show 192.168.1.100 # 显示代理ARP条目 ip neighbour show proxy # 实时监控邻居表变化 ip neighbour monitor ##### 7.2.3 添加和修改操作 # 添加静态ARP条目 ip neighbour add 192.168.1.100 lladdr 00:11:22:33:44:55 dev eth0 # 添加永久ARP条目 ip neighbour add 192.168.1.100 lladdr 00:11:22:33:44:55 dev eth0 nud permanent # 添加代理ARP条目 ip neighbour add proxy 192.168.1.100 dev eth0 # 修改现有ARP条目 ip neighbour change 192.168.1.100 lladdr 00:11:22:33:44:56 dev eth0 # 替换ARP条目(如果不存在则添加) ip neighbour replace 192.168.1.100 lladdr 00:11:22:33:44:55 dev eth0 nud permanent ##### 7.2.4 删除操作 # 删除特定IP的ARP条目 ip neighbour del 192.168.1.100 dev eth0 # 删除代理ARP条目 ip neighbour del proxy 192.168.1.100 dev eth0 # 清空指定接口的所有ARP条目 ip neighbour flush dev eth0 # 清空特定状态的ARP条目 ip neighbour flush nud stale ip neighbour flush nud failed # 清空所有ARP条目(有时并不清除permanent条目) ip neighbour flush all # 清空PERMANENT状态的ARP条目 ip neighbour flush nud permanent ##### 7.2.5 常用参数说明 * **lladdr**: 指定邻居的链路层地址(MAC地址) * **dev**: 指定网络接口 * **nud**: 指定邻居状态(reachable、stale、delay、probe、failed、noarp、permanent、all) * **proxy**: 指定代理ARP条目 #### 7.3 查看统计信息 # 查看ARP相关统计信息 cat /proc/net/netstat | grep -A 1 "Neigh" # 查看更详细的邻居子系统统计 cat /proc/net/neigh/eth0/ #### 7.4 实时监控 # 实时监控ARP表变化 watch -n 1 'ip neighbour show' ### 8. 常见问题和解决方案 #### 8.1 ARP表项频繁变化 问题:网络中ARP表项频繁在REACHABLE和STALE状态间切换。 解决方案: 1. 增加`base_reachable_time_ms`值 2. 检查网络中是否存在重复IP地址 #### 8.2 ARP请求失败 问题:ARP请求发送后无响应,条目进入FAILED状态。 解决方案: 1. 检查网络连通性 2. 增加`mcast_solicit`和`ucast_solicit`值 3. 检查防火墙是否阻止了ARP请求 #### 8.3 ARP表溢出 问题:ARP表项数量超过限制,新条目无法添加。 解决方案: 1. 增加`gc_thresh3`值 2. 检查网络中是否存在ARP扫描等异常行为 3. 考虑网络架构优化,减少需要维护的邻居数量