常见的二层协议和三层协议结构以及IP头checksum计算方法
一、常见的二层协议1、802.3/ETH2帧格式2、802.1Q VLAN帧格式3、802.11帧格式总结:三种二层协议帧只有二层头不一样。换句话说,去掉二层头,上述三种二层协议帧都拥有相同的结构,包括:802.2 LLC + 802.2 SNAP + data。二、最常见的三层协议——IP协议1、IP数据报格式(封装在802.3/ETH-II/802.1Q/802.11的数据字段)类似的还有AR
一、常见的二层协议
1、802.3/ETH2帧格式
2、802.1Q VLAN帧格式
3、802.11帧格式
总结:三种二层协议帧只有二层头不一样。换句话说,去掉二层头,上述三种二层协议帧都拥有相同的结构,包括:
802.2 LLC + 802.2 SNAP + data。
二、最常见的三层协议——IP协议
1、IP数据报格式(封装在802.3/ETH2/802.1Q/802.11等二层协议的数据字段)
类似的还有ARP等。
三、常见的IP子协议
1、IP子协议1——ICMP
2、IP子协议2——TCP
3、IP子协议3——UDP
总结:三种IP子协议拥有相同的IP头格式,如下(对照二.1的图来看):
struct{
uchar ver; /* version and internet header length */
uchar tos; /* type of service,通过该字段指定有线报文的优先级 */
ushort totlen; /* number of bytes in packet (max 65535) */
ushort usId;
ushort frag; /* 3 flag bits and fragment offset */
uchar ttl; /* Time To Live */
uchar prot; /* Protocol ,ICMP/TCP/UDP等就通过这个字段区分*/
ushort chksum; /* IP header checksum,如果修改了IP头某个字段,需要重新计算IP头checksum */
uint srcip; /* Source IP Address */
uint destip; /* Destination IP Address */
} ip_headers;
三、IP头的修改注意事项
1、如果修改了IP头中的某个字段,需要重新计算IP头的校验和,并写回到IP头的chksum字段,对端接收到该
报文会利用该值对IP头做校验,校验通过,认为报文OK,否则丢弃报文。
2、具体操作流程如下
(1)修改IP头某个字段
(2)将IP头chksum字段清零
(3)计算IP头的checksum,方法参见博文:
https://www.cnblogs.com/adamite/p/3317376.html
(4)将计算好的IP头的checksum写回IP头chksum字段
3.计算IP头checksum代码实现
USHORT CalIPHeaderChecksum(UCHAR *pstIPHeader, UINT uiLen)
{
ULONG usChecksum = 0x0;
while(uiLen > 1)
{
usChecksum += (USHORT)ntohs(*(USHORT*)pstIPHeader);
pstIPHeader += sizeof(USHORT); /* 每次累加2个字节 */
uiLen -= sizeof(USHORT); /* 需要计算的IP头长度减2字节 */
}
if(uiLen) /* IP header长度为奇数的情况,普通IP首部长度为20个字节,除非含有选项字段(见TCP/IP协议卷) */
{
usChecksum += (USHORT)ntohs(*pstIPHeader);
}
while((usChecksum >> 16) != 0x0) /* 如果有进位 */
{
usChecksum = (usChecksum >> 16) + (usChecksum & 0xffff);
}
return (USHORT)(~(USHORT)usChecksum);
}
更多推荐
所有评论(0)