《TCP/IP详解 卷一》第8章 ICMPv4 和 ICMPv6
目录
8.1 引言
8.1.1 在IPv4和IPv6中的封装
8.2 ICMP 报文
8.2.1 ICMPv4 报文
8.2.2 ICMPv6 报文
8.2.3 处理ICMP报文
8.3 ICMP差错报文
8.3.1 扩展的ICMP和多部报文
8.3.2 目的不可达和数据包太大
8.3.3 重定向
8.3.4 ICMP 超时
8.3.5 参数问题
8.4 ICMP查询/信息类报文
8.4.1 回显请求 / 应答
8.4.2 路由器发现:路由器请求RS和通告RA
8.4.3 本地代理地址发现请求/应答
8.4.4 移动前缀请求/通告
8.4.5 移动IPv6快速切换报文
8.4.6 组播侦听查询/报告/完成
8.4.7 版本2组播侦听发现
8.4.8 组播路由器发现
8.5 IPv6中的邻居发现
8.5.1 ICMPv6路由器请求和通告
8.5.2 ICMPv6邻居请求和通告
8.5.3 ICMPv6反向邻居发现请求/通告
8.5.4邻居不可达检测
8.5.5安全邻居发现
8.5.6 ICMPv6邻居发现选项
8.6 ICMPv4 和 ICMPv6 转换
8.7 与ICMP相关的攻击
8.8 总结
8.1 引言
ICMP位于网络层和传输层之间。
因为路由器缓冲区溢出的丢包不会触发任何ICMP差错报文。而由TCP等处理(重传等)。
黑客在大量攻击中使用ICMP。由于担心攻击,通常防火墙封阻ICMP报文,特别是边界路由器。此时诊断程序(ping, traceroute)无法正常工作。
ICMPv6包含:
错误报告。
邻居请求,邻居通告。
路由器请求,路由器通告。
重定向:优化路由。
报文过滤: 引入Packet Too Big报文,通知源主机包超过了链路层MTU。
8.1.1 在IPv4和IPv6中的封装
报文格式:
其中ICMPv4头:
字段介绍:
类型:指定报文类型,常用8个值。
代码:进一步指定报文类型。
校验和:IP层没有对载荷完整性保护。所以ICMP需包含校验和。
8.2 ICMP 报文
ICMP报文分类:
差错报文:用于通知发送端数据包传输中的错误情况。
查询/信息类报文:用于信息采集和配置。
8.2.1 ICMPv4 报文
差错报文:
目的不可达(类型3),重定向(类型5),超时(类型11 ),参数问题(类型12)
查询/信息类报文:
回显请求(类型8),回显应答(类型0),路由器通告(类型9),路由器请求(类型10)
其中重定向报文目的:指导主机或路由器改变路由决策,将数据发送到更优路径上。
8.2.2 ICMPv6 报文
ICMPv6不仅包含差错和查询/信息类报文,还有大量IPv6路由器和主机的配置,如RS,RA,NS,NA。
ICMPv6类型字段值:
从0到127是差错类报文,从128到255是信息类报文。
ICMPv6也使用代码字段。
ICMPv6还支持大量标准选项,而ICMPv4不支持选项。
8.2.3 处理ICMP报文
收到重定向报文:会更新路由表。
目的不可达报文:可用于路径MTU发现(PMTUD)
ICMPv6报文处理规则:
1. 收到未知ICMPv6差错报文,须传递给上层产生差错报文的进程。
2. 收到未知ICMPv6信息类报文,丢弃。
3. 发送ICMPv6差错报文时,应尽可能多地包含导致差错的原始IPv6报文,但不超过最小的IPv6 MTU ( 1280字节)
4. IPv6节点须限制发送ICMPv6差错报文速率。
IPv6网络中链路层最小MTU是1280字节。IPv4中是576字节。
8.3 ICMP差错报文
请注意8.3.1到8.3.5章节都属于ICMP差错报文。
不会用ICMP差错报文响应以下报文:
另一个ICMP差错报文。
头部损坏的数据报(例如校验和错误)。
IP层广播或组播数据。
链路层广播或组播帧数据。
无效地址(零地址、环回地址、广播地址,组播地址)
第一个之外的分片。
发送ICMP差错报文:应包含导致错误数据报的IP头副本,包括IP选项和原始IP载荷,生成的ICMP数据报大小不超过网络最小MTU。
差错报文包含原始IP包载荷作用:
使接收ICMP差错报文主机能根据IP头中协议或下一个头部将该差错报文传递到对应传输层和应用进程。
8.3.1 扩展的ICMP和多部报文
扩展的ICMP差错报文: 使ICMP差错报文包含额外信息以提供更多诊断信息。
用ICMP中代码字段指明具体原因,实现扩展功能。
后续章节详解。
8.3.2 目的不可达和数据包太大
ICMPv4目的不可达差错报文:
网络不可达:code 0,无路由信息。
主机不可达:Code 1,如目标主机关机等。
协议不可达:Code 2,目标主机无法处理数据包传输层协议。
端口不可达:Code 3,该端口未打开或没有对应端口的应用程序。
需要进行分片,但设置了DF位:Code 4
源站选路失败:Code 5,IP包中包含源站路由选项,但无法按照指定路由转发数据包。
ICMPv6目的不可达差错报文:
无路由:code 0,无路由信息。
目的地被管理员禁止通信:code 1
源地址的范围之外:code 2,如访问公网时,源IP地址是本地链路地址,不属于全局地址。
地址不可达:code 3,目标主机未响应或不可达
端口不可达:code 4
源地址失败进/出策略:code 5,如因为接口ACL导致数据报无法传递。
数据包太大差错报文
即PTB(Packet Too Big)
路由器转发的数据大于出接口MTU,但数据IP头设置了不分片位,则丢弃该数据,并回复PTB差错报文。
PTB报文中会包含路由器自身 MTU值,以告知源地址减小数据包。
因此该报文可用于PMTU发现,PMTU是路径中MTU最小值。
net.ipv4.icmp_ratemask = 6168(哪些ICMP报文有速率限制,对应code字段)
应用程序使用如下代码接口ICMP报文:
sockfd = socket(AF_INET, SOCK_RAW, IPPROTO_ICMP);
应用层收到ICMP差错报文后,可进行对应操作。
8.3.3 重定向
使用不多。
主机根据ICMP重定向报文信息来更新转发表
8.3.4 ICMP 超时
IPv4头部中TTL字段:表示丢弃前最多可经过的路由器跳数。
IPv6头部中同样有跳数限制(Hop Limit)字段表示。
超时报文差错报文:
TTL超时:Code 0,指示数据报TTL值已减至零。
分片重组超时:Code 1,指示数据报片段重组未能在一定时间内完成。
traceroute原理:
主机先发送IPv4 TTL=1数据,到达第一个路由器,此时TTL到期,路由器回复ICMPv4超时报文。主机下一次数据包TTL加1。导致在更远一跳路由器超时,并回复ICMP超时报文,重复该过程。
ICMP响应报文中包含响应路由器自身IP,由此得到沿途所有路由器IP。
8.3.5 参数问题
场景:IP头部存在不可修复错误。
该报文是"包罗万象”的错误指示器。无法指明具体原因,但会指出错误相对IP头部的偏移值。
ICMPv6中细分为三种:
错误头部字段。
无法识别下一个头部。
无法识别IPv6选项。
8.4 ICMP查询/信息类报文
注意:8.3 讲解的全是ICMP差错报文。
广泛使用的ICMP查询/信息类报文:回显请求,回显应答(ping使用)
8.4.1 回显请求 / 应答
即ping使用的ICMP报文类型。
回显请求报文大小任意(但受限于IP数据报大小),回显应答时需要将收到数据返回给发送者,即使需要IP分片。
字段介绍:
标识符:UNIX用发送进程PID表示。方便识别同一主机多个ping程序。
序列号:从0开始,每个回显请求加1。方便查看丢包、重复问题。
可选数据:如ping在回显请求和应答包含本地时,方便计算RTT。
之前提过NAT处理ICMP时,会结合标识符和序列号进行NAT转换,因为ICMP报文没有端口号信息。
ping -b 10.0.0.254
ping广播地址作用:
子网所有主机收到该ping包后,都需要响应,所以都需要知道ping主机的MAC,于是都向ping主机发ARP请求,最终快速广播ping主机ARP。
Linux默认允许回复CMP应答报文给广播地址的ICMP请求。
8.4.2 路由器发现:路由器请求RS和通告RA
路由器发现:RD(Router Discovery)
RD:IPv4使用少。主要用于IPv6,是IPv6 SLAAC功能一部分。
IPv6 RD包括:
路由器请求RS(Router Solicitation)报文
路由器通告RA(Router Advertisement)报文
ICMP type 133,表示路由器请求RS。请求网络配置,如DNS,IPv6网络前缀。
ICMP type 134,表示路由器通告RA。要么用于回复RS,要么周期多播发送。
使用场景:
无状态地址配置:RA中包含网络前缀信息。
8.4.3 本地代理地址发现请求/应答
允许移动网络IPv6节点在移动时保持其IPv6地址不变,并且可以在外部网络上通过本地代理进行通信。
8.4.4 移动前缀请求/通告
当节点的本地地址将无效时,请求更新路由前缀。
8.4.5 移动IPv6快速切换报文
改善IP层切换延迟
8.4.6 组播侦听查询/报告/完成
允许节点查询或报告本地链路上的组播组成员信息,并执行组播组成员的管理。
8.4.7 版本2组播侦听发现
8.4.8 组播路由器发现
通过ICMPv6组播路由器发现报文,主机确定哪些路由器支持 IPv6 组播,从而决定是否启用 IPv6 组播功能。
8.5 IPv6中的邻居发现
邻居发现:(Neighbor Discovery,ND),类似IPv4的ARP。
IPv6中没有广播地址。
ND用于在同一个链路或者网段的节点找到彼此,确定一个邻居是否变得可用。
ND使用ICMPv6报文。
ND包含:
邻居请求NS(Neighbor Solicitation),ICMP type为135。
邻居通告NA(Neighbor Advertisement),ICMP type为136。
功能:地址解析,邻居发现,地址自动配置。
8.5.1 ICMPv6路由器请求和通告
路由器通告(RA)报文:
通告网络前缀,MTU,DNS,NTP服务器等配置。
通常会定期发送,或者用于响应路由器请求(RS)报文。
RS报文目的IP:ff02::2(所有路由器组播地址)
RA报文目的IP:ff02::1(所有节点的组播地址)或者单播RS主机
结合无状态DHCPv6 SLAAC使用。
8.5.2 ICMPv6邻居请求和通告
ICMPv6中的邻居请求(NS)报文:取代IPv4 ARP
目的:
IPv6中ARP功能,获取IPv6地址对应MAC。
检测附近节点是否可达。
8.5.3 ICMPv6反向邻居发现请求/通告
在帧中继网络中确定给定的MAC地址对应IPv6地址
8.5.4邻居不可达检测
(Neighbor Unreachability Detection, NUD)
定期检测邻居节点的存活状态
如果检测到邻居不可达,更新邻居表和路由表,切换到备用网络。
8.5.5安全邻居发现
安全邻居发现(Secure Neighbor Discovery,SEND)
安全性增强的邻居发现协议。
作用:
邻居发现,且解决传统IPv6邻居发现过程安全漏洞。
8.5.6 ICMPv6邻居发现选项
使用一些可选的选项(Options)来提供额外信息或配置。
源/目标链路层地址选项
前缀信息选项PIO
重定向头部选项
MTU 选项
通告间隔选项
源和目标地址列表选项
时间戳选项
随机数选项
证书选项
IP地址/前缀选项
链路层地址选项
邻居通告确认选项
路由信息选项
递归DNS服务器选项
切换密钥请求选项
切换密钥应答选项
8.6 ICMPv4 和 ICMPv6 转换
8.7 与ICMP相关的攻击
分为3类:
泛洪(flood):DoS
炸弹(bomb):发送特殊构造报文,导致IP或者ICMP的处理崩溃。
信息泄露(information disclosure)