struct
iphdr {
#if BYTE_ORDER ==
LITTLE_ENDIAN/*小端字节模式*/
uint8_t ihl:4,
version:4;/*头长度:版本号*/
#elif BYTE_ORDER ==
BIG_ENDIAN/*大端字节模式*/
uint8_t version:4, ihl:4;/*版本号:头长度*/
#else
# error "BYTE_ORDER must be
defined"
#endif
uint8_t tos;/*服务类型*/
uint16_t tot_len;/*包的总长度*/
uint16_t id;/*标示*/
uint16_t
frag_off;/*片偏移*/
uint8_t ttl;/*生存时间*/
uint8_t protocol;/*协议类型*/
uint16_t check;/*校验和*/
uint32_t
saddr;/*源IP地址*/
uint32_t daddr;/*目的IP地址*/
};
IP数据报的首部长度和数据长度都是可变长的,但总是4字节的整数倍。
对于IPv4,4位版本字段是4。4位首部长度的数值是以4字节为单位的,最小值为5,也就是说首部长度最小是4x5=20字节,也就是不带任何选项的IP首部,4位能表示的最大值是15,也就是说首部长度最大是60字节。
8位TOS字段有3个位用来指定IP数据报的优先级(目前已经废弃不用),还有4个位表示可选的服务类型(最小延迟、最大呑吐量、最大可靠性、最小成本),还有一个位总是0。
总长度是整个数据报(包括IP首部和IP层payload)的字节数。每传一个IP数据报,16位的标识加1,可用于分片和重新组装数据报。
3位标志和13位片偏移用于分片。
TTL(Time to live)是这样用的:源主机为数据包设定一个生存时间,比如64,每过一个路由器就把该值减1,如果减到0就表示路由已经太长了仍然找不到目的主机的网络,就丢弃该包,因此这个生存时间的单位不是秒,而是跳(hop)。 协议字段指示上层协议是TCP、UDP、ICMP还是IGMP。
然后是校验和,只校验IP首部,数据的校验由更高层协议负责。
IPv4的IP地址长度为32位。选项字段的解释从略。
阅读(2095) | 评论(0) | 转发(0) |