4.3.1 IPv4 Datagram Format
我们先通过了解 IPv4 数据包来开始 IP 的学习。
IPv4 datagram format各个字段的含义为:
Field | Size (bit) | Comment |
---|---|---|
Version number | 4 | 指定协议版本(v4 or v6),路由依据版本解析 IP 数据包 |
Header length | 4 | 指定了 header 的长度(32bit为单位),通常 options field 是空所以 header 长度一般是 20 bytes,也就是 5 words |
Type of service | 8 | 用于区分不同类型的数据包,例如,来自实时服务的和非实时服务的。 |
Datagram length | 16 | IP 数据包的最大长度(以字节计),虽然它支持最大 65535 bytes,但是由于链路层 Ethernet 只允许最大 1500,所以设置为 1500 以内,即最大传输单元 MTU |
Identifier | 16 | 分片和重组 |
Flags | 3 | 分片和重组 |
Fragmentation offset | 13 | 分片和重组 |
Time-to-live | 8 | 保证数据包不永远在网络中游荡,TTL 每经过一次路由就减1,减少至0就会被丢弃 |
Upper-layer-protocol | 8 | 在到达目的主机时使用,指定了应该将数据包交给哪个传输层协议。例如,6 表示给 TCP,17 表示给 UDP。port 是传输层和应用层之间的分用-复用,而这是网络层和传输层的 |
Header checksum | 16 | 检测 bit error,路由器如果发现问题就会丢弃这个数据包 |
Source IP Address | 32 | |
Destination IP Address | 32 | |
Data | ? | 网络层需要发送的内容,即传输层的数据包。也可以传输其他信息,如 ICMP 消息 |
其 header 一共占 20 字节。和 TCP 协议的 header 大小一样。
4.3.2 IPv4 Datagram Fragmentation
不同的链路层协议的 MTU (maximum transmission unit) 不同。例如,Ethernet 可以支持最多 1500 字节的数据。由于 IP 数据包会通过链路层发送,MTU 也限制了它的大小。由于数据可能通过不同的链路层协议发送,我们在传输过程中可能会进行分片,并在到达目的主机时重组。这些都发生在网络层。
当主机收到一系列来自同一个源的数据包时,它首先需要辨别哪些是“碎片”,然后再决定如何将这些“碎片”重组成原始数据包。这也是header中的三个字段 identification
, flag
和 fragmentation offset
的作用。
Field | Size | Comment |
---|---|---|
identification | 16 | 由 Sender 为每个数据包指定,当 Router 对其分片时,每个碎片都继承了这个 id,用于组装碎片 |
flags | 3 | 用于判断是否接收完成,最后一个碎片 flag 为0,其他为 1 |
offset | 13 | 用于判断是否有丢失的碎片,指明了碎片在原始数据包中的位置 |
4.3.3 IPv4 Addressing
每个 IP 地址都是 32 bit,因此一共有约 4 亿个 IP 地址。这些地址都被分为 4 段,每段 1 字节(8 bit),用 .
隔开。例如 193.32.216.9
,每个数字都是 10 进制。
如图所示,223.1.1.*
组成了一个子网。我们可以用 223.1.1.0/24
来表示这个子网,其中 24 是指前 24 个 bit 定义了这个子网。同理,其他两个子网可以表示为 223.1.2.0/24
和 223.1.3.0/24
。这些子网通过路由器连接在一起。
形如 a.b.c.d/x
的 IP 地址格式被称作 Classless Interdomain Routing (CIDR)。只有前 x
个 bit 会对外界的路由可见。即,当外界路由转发数据给在该地址下的主机时,只根据前 x
位查找。这降低了路由转发表的大小。
剩下的 32-x
位可以在子网内区别各个设备。例如,对于 a.b.c.d/21
,前 21 bit 用于这个子网内所有设备的公共前缀,用户可以改变后 11 bit 来继续拆分子网,例如,可以拆分出 8 个形如 a.b.c.d/24
的子网。
在 CIDR 应用之前,所有的 IP 地址分割被限制在 8,16,24 bit 上。分别为 A 类网络,B 类网络,C 类网络。这样的分类方法很不灵活。例如,C 类地址只能支持 个设备。因为 a.b.c.0
和 a.b.c.255
为特殊地址。而 B 类地址则支持 65634 个地址,对于某个需要 500 个 IP 的机构,只能分配一个 B 类地址,浪费资源。
Obtaining a Block of Addresses
机构需要向 ISP (internet service provider) 申请自己的网段。ISP 会将自己的子网做进一步切分,例如,ISP 自己的网段是 200.23.16.0/20
,它可能会将其分为 8 个子网,并分配给不同客户,即:
200.23.16.0/23
200.23.18.0/23
200.23.20.0/23
200.23.22.0/23
200.23.24.0/23
200.23.26.0/23
200.23.28.0/23
200.23.30.0/23
那么 ISP 的这个网段从哪里获得呢?实际上,有一个负责分配全球所有 ISP 地址的机构,即 Internet Corporation for Assigned Names and Numbers(ICANN),他们还会负责管理 DNS 根服务器。
Obtaining a Host Address: The Dynamic Host Configuration Protocol
设备地址可以手动配置,但是通常我们使用 DHCP 自动分配。DHCP 能够自动为设备分配 IP 地址,并获取所在网络的子网掩码,默认网关,本地 DNS 服务器等。
DHCP 是一个 client-server 协议。client 就是需要分配地址的设备,当一个新的设备接入时,DHCP 会进行 4 个步骤的操作为其自动分配 IP。
DHCP client-server interaction1. DHCP server discovery
第一步是要找到 DHCP server,利用 DHCP discover message 来实现。client 会发送一个 UDP 包至 67 端口。但是既然现在 client 还不知道所处的网络,这个包的源地址和目的地址是什么?此时,DHCP 会创建一个目标地址是 255.255.255.255
,源地址是 0.0.0.0
的特殊 IP 数据包。这个包会被广播到该子网内的所有节点。
2. DHCP server offer(s)
DHCP server 收到 DHCP discover message 后,会回复一条 DHCP offer message。这个回复也是通过广播的形式(因为源地址是 0.0.0.0
,server 无法得知应该发往哪个地址)。DHCP offer message 包含以下信息:
- DHCP discover messge 的 ID
- 给 client 分配的 IP 地址
- IP 地址释放时间(IP 地址有效的时间)
- 掩码
3. DHCP request
client 回复 DHCP offer message,告诉 DHCP server 配置好的参数
4. DHCP ack
DHCP server 确认 DHCP request 的参数
client 收到 DHCP ack 后,就能使用分配好的 IP 了,这个 IP 是有时限的,但是 client 可以申请续租。
4.3.4 Network Address Translation (NAT)
NAT 允许一个机构仅使用一个公网 IP 地址出现在 Internet 上。他不仅解决了公网 IP 地址不足的问题,还能有效避免来自外部网络的攻击。
Network address translation我们可以看到内网的设备都分配了 10.0.0.0/24
的网段。这是由于 10.0.0.0/8
是 RFC 标准保留的私有网段,私有地址是指仅对本网络内的设备有意义的地址。Internet 上很多机构内部都用着 10.0.0.0/8
网段,但是彼此是不可见的。他们彼此的通信都要经过 NAT。
启用 NAT 的路由器在 Internet 上的行为不像是路由器,反而像是一个仅具有一个网络的地址的设备。如图 4.25 所示,所有需要发送到 Internet 的网络流量都具有同样的源地址 138.78.29.7
,所有从 Internet 接收的网络流量都具有同样的目的地址 138.78.29.7
。在外界看来,他们是在与这个地址为 138.78.29.7
的设备通信,内网的诸多设备都被隐藏掉了。
我们可以看到,内网的设备实际上并不需要 Internet 上的 DHCP server 提供的地址分配服务(因为他们使用的是私有地址)。实际上,路由器会运行一个 DHCP server 并给内网设备提供地址分配服务。
那么路由器如何将收到的数据分发给不同的设备呢?实际上是将不同的设备映射到不同的端口实现的。
如图 4.25 所示,内网设备 10.0.0.1
希望发送 http 请求给外网的 128.119.40.186
。它会将目标地址设为 128.119.40.186: 80
,源地址是 10.0.0.1: 3345
,3345 是随机分配的。
到路由器后,路由器为 10.0.0.1
分配一个新的端口 5001,并将源地址从 10.0.0.1: 3345
改为 138.78.29.7: 5001
,并在 NAT 表中添加 10.0.0.1: 3345
到 138.78.29.7: 5001
的映射。
Web server 并不知道这些细节,只知道需要处理来自 138.78.29.7: 5001
的 http 请求。当 http 请求返回时,路由器会查询 NAT 表,将 138.78.29.7: 5001
收到的数据转发给 10.0.0.1: 3345
。
网友评论