ICMP包分析
ICMP
原理
ICMP协议核心原理
- ICMP协议全称Internet Control Message Protocol(互联网控制报文协议),工作在网络层,是IP协议的“配套协作者”,不直接承载用户数据
- 核心作用是:检测网络连通性、反馈通信错误、传递控制信息
- 核心特点:无连接、无端口(区别于TCP/UDP),报文直接封装在IP数据报的数据字段中传输,IP首部中的协议字段值为1(IPv4),标识其载荷为ICMP报文
- 我们常用的“ping”命令,本质就是基于ICMP协议实现的
- ping请求=ICMP Echo Request
- ping响应=ICMP Echo Reply
- 核心分类:ICMP报文分为两大类
- 差错报文(如目标不可达、TTL超时)
- 查询报文(如Echo请求/ 响应、时间戳请求/响应)
- 实验中最常用、最易捕获的是查询报文中的Echo请求和响应
命令
1 | |
Identification(标识)
Identification字段的唯一使命就是:让接收方能够准确识别出哪些分片属于同一个原始数据包,从而把它们重新拼回完整的数据包。
Flags(标志位)
- DF 位(不分片标志):网络排错的关键
- 核心作用:告诉网络中的所有路由器:”这个数据包绝对不能被拆分,要么完整转发,要么直接丢弃”。
- 为什么 TCP 默认设置 DF=1:
TCP 是面向连接的可靠协议,它自己会在传输层进行分段(Segment),保证每个 TCP 段加上 IP 首部后不超过默认 MTU(1500 字节)。如果允许 IP 层再分片,一旦某个分片丢失,整个 TCP 段都需要重传,效率极低。 - 路径 MTU 发现(PMTUd)原理:
当路由器收到一个 DF=1 但大小超过出接口 MTU 的数据包时,会丢弃该包,并向源主机返回一个ICMP错误消息:”需要分片但DF位已设置(Type 3, Code 4)”。源主机收到后,会自动减小发送的数据包大小,直到找到整条路径上的最小 MTU。
- MF位(更多分片标志):判断分片是否结束
- MF=1 明确表示:”这不是最后一个分片,后面还有数据”。
- MF=0 有两种可能:
- 这是一个完整的、没有被分片的数据包(片偏移 = 0)
- 这是最后一个分片(片偏移 > 0)
- 关键判断:必须结合 片偏移(Fragment Offset 字段才能区分这两种情况。只有当
MF=0 且 片偏移=0时,才是完整的数据包。
Protocol(协议)
互联网是分层设计的,每一层只负责自己的工作:
- IP层(网络层):负责把数据包从源主机送到目的主机
- 上层协议(传输层 / 网络层控制协议):负责处理数据包里的具体内容
Protocol 字段的唯一使命就是:在 IP 层完成投递后,准确地将数据 “转交给” 正确的上层协议处理程序。
| 协议号(十进制) | 协议名称 | 英文全称 | 典型应用 |
|---|---|---|---|
| 1 | ICMP | Internet Control Message Protocol | ping、traceroute、网络错误通知 |
| 6 | TCP | Transmission Control Protocol | HTTP、HTTPS、SSH、FTP、SMTP |
| 17 | UDP | User Datagram Protocol | DNS、DHCP、视频直播、游戏、语音通话 |
| 2 | IGMP | Internet Group Management Protocol | 组播通信 |
| 4 | IP-in-IP | IP Encapsulation within IP | VPN 隧道 |
| 41 | IPv6 | IPv6 Encapsulation | IPv6 over IPv4 隧道 |
| 47 | GRE | Generic Routing Encapsulation | VPN 隧道、PPTP |
| 50 | ESP | Encapsulating Security Payload | IPsec VPN(加密) |
| 51 | AH | Authentication Header | IPsec VPN(认证) |
| 89 | OSPF | Open Shortest Path First | 内部网关路由协议 |
| 112 | VRRP | Virtual Router Redundancy Protocol | 虚拟路由器冗余协议 |
Fragment Offset(片偏移)
- MTU=1500 字节:指的是整个 IP 数据包的最大长度,包括20 字节的 IP 头部和1480 字节的数据部分
- 片偏移:只计算数据部分在原始 IP 数据报中的偏移量,不包含 IP 头部
- 片偏移单位:RFC 791 规定片偏移以8 字节为单位
ICMP包分析
- 打开wireshark抓包功能
- 随便ping局域网ip或者域名
- 停止抓包
在捕获过滤器中输入icmp,筛选出来8个包,4个请求包和4个响应包一一对应
ICMP请求包
Info:Echo (ping) request id=0x0001, seq=16/4096, ttl=128 (reply in 465)
Ethernet II(数据链路层):
- Destination: 70:e0:4c:68:53:2e (70:e0:4c:68:53:2e)
- 目的
MAC地址(目标IP对应的MAC,来自ARP缓存)
- 目的
- Source: ASUSTekCOMPU_07:e9:fb (cc:28:aa:07:e9:fb)
- 源
MAC地址,即自己的MAC地址
- 源
- Type: IPv4 (0x0800)
- 类型字段,该数据帧是IPv4数据包
Internet Protocol Version 4(网络层IPv4):
- Version: 4
- IP版本
- Header Length: 20 bytes
- IP头部长度
- Differentiated Services Field: 0x00
- 服务类型,默认0,无特殊
- Total Length: 60
- IP数据包总长度(20头部+40ICMP报文)
- Identification: 0xdaa8 (55976)
- 标识
- Flags: 0x0
- 标志位,当前无分片
- Fragment Offset: 0
- 片偏移,0表明是没有分片或者分片的最后一片,再结合标识位来看该数据包未被分片
- Time to Live: 128
- 生存周期
- Protocol: ICMP (1)
- 协议,封装的是上层的ICMP协议
- Header Checksum: 0x0000 [validation disabled]
- 首部校验和,验证IP首部完整性
- Source Address: 192.168.100.100
- 源IP
- Destination Address: 28.0.0.62
- 目的IP
Internet Control Message Protocol(ICMP层)
- Type: 8 (Echo (ping) request)
- 类型字段,值为8,表示”ICMP Echo请求”
- Code: 0
- 配合Tpye使用,Type=8时,code只能为0
- Checksum: 0x4d4a [correct]
- 校验和,correct标识正常
- Identifier (BE): 1 (0x0001)
- 标识标志,用于匹配请求和响应(请求和响应的Identifier必须一致)
- Identifier (LE): 256 (0x0100)
- 标识标志的小端模式,不用管,可忽略
- Sequence Number (BE): 17 (0x0011)
- 序列号,用于标识第几个请求包(ping默认发送4个,序列号依次为1、2、3、4)
- Sequence Number (LE): 4352 (0x1100)
- 小端模式,不用管,可忽略
- Data (32 bytes)
- 数据部分,默认长度64字节,内容无实际意义
ICMP响应包

Ethernet II(数据链路层):
其他没啥区别
目的地址和源地址反过来
Internet Protocol Version 4(网络层IPv4):
其他没啥区别
目的地址和源地址反过来
Internet Control Message Protocol(ICMP层)
- Type: 8 (Echo (ping) request)
- 类型字段,值为0,Type=0对应响应
- Code: 0
- 配合Tpye使用,Type=8时,code只能为0
- Checksum: 0x554b [correct]
- 校验和,correct标识正常
- Identifier (BE): 1 (0x0001)
- 标识标志,和请求包的Identifier一致,确保这是对序号1请求包的响应
- Sequence Number (BE): 17 (0x0011)
- 和请求包的序列号一致,对应第一个请求包的响应
- Data (32 bytes)
- 数据部分,和请求包的数据部分完全一致
分片
wireshark捕获过滤:ip.flags.mf == 1 or ip.frag_offset > 0
关于分片主要是Internet Protocol Version 4(网络层IPv4)中Identification,Flags,Fragment Offset,Total Length,Header Checksum的区别
| 字段 | 普通 ICMP 包(你的抓包) | 分片 ICMP 包(非最后一个分片) | 分片 ICMP 包(最后一个分片) |
|---|---|---|---|
| Flags (标志位) | 0x00(MF=0, DF=0) | 0x01(MF=1, 表示 “还有更多分片”) | 0x00(MF=0, 表示 “这是最后一个分片”) |
| Fragment Offset (片偏移) | 0(无分片) | 非 0 值,以 8 字节为单位,表示该分片数据在原始包中的起始位置 | 非 0 值,最后一个分片的偏移 |
| Identification (标识) | 唯一标识该数据包 | 与原始包完全相同,所有分片共享此 ID | 与原始包完全相同 |
| Total Length (总长度) | 60 字节(整个包长度) | 1500 字节(MTU 最大值,20IP 头 + 1480 数据) | 小于 1500 字节(剩余数据 + 20IP 头) |
| Header Checksum | 整个 IP 头的校验和 | 每个分片独立计算(因片偏移不同) | 每个分片独立计算 |
第一个分片
第二个分片(图中片偏移写错了,应该是这个是第二个分片,不是第二个包)
第三个分片
从以上图片可以看出三个分片共用了一个Identification (标识)
分片过的请求包和响应包都是差不多的,只是源和目的地址反过来了