【2021/1/17修订】【梳理】计算机网络:自顶向下方法 第四章 网络层——数据(docx)

计算机网络

知 识 梳 理

(第一版)

建议先修课程:数据结构。
配套教材:
Computer Networking - A Top Down Approach, 7th edition James F. Kurose, Keith W. Ross
参考书目:
1、计算机网络(第7版) 谢希仁 编著 高等教育出版社


链接:https://pan.baidu.com/s/1BACZnHxo8ZO-5Q4CwAENqA
提取码:0000
复制这段内容后打开百度网盘手机App,操作更方便哦


四 网络层——数据

4.1 网络层概览
网络层的功能主要有:
·转发。当一个分组到达路由器的输入链路时,路由器将其移动到适当的输出链路。这是最常见、最重要的功能。不过,分组也可能被路由器阻挡(如果分组来源于一台已知的恶意主机,或发向一台被禁止的目标主机),或者可能是冗余的。
·路由选择。当分组从发送方流向接收方时,网络层必须决定这些分组经过的路由。计算这些路径的算法称为路由算法。
使用相同网络层协议的异构(heterogeneous,即架构不同)网络可以被路由器互连起来。

在讨论网络层时,许多作者经常交替使用转发和路由选择这两个术语。为了避免混淆,这里统一一下用法:
转发(forwarding),是指将分组从一个输入链路转移到适当的输出链路的、路由器的本地动作,也就是说转发仅涉及单一的路由器。转发的耗时很短(例如几ns),多用硬件实现。
路由选择(routing),是指确定分组从源到目的地所采取的端到端路径的、网络范围的处理过程,也就是说路由涉及到多台路由器。路由选择的用时长得多(比如几秒),多用软件实现。
每台路由器都有一个关键部分:转发表(forwarding table)。路由器检查到达的分组首部的若干个字段的值,使用这些值在其转发表中索引(查找),并转发分组。这些值对应存储在转发表项中的值,后者指出该分组将被转发到的输出链路。

路由算法决定该路由器的转发表。路由选择算法可以运行在每台路由器中,每台路由器都包含转发和路由选择两种功能。我们将在5.3、5.4节学到:一台路由器中的路由选择算法与其它路由器的路由选择算法通信,以计算出它的转发表的值。这种通信是如何执行的呢?答案是:根据路由选择协议,交换包含路由选择信息的路由选择报文。

上述方法是传统方法。使用该方法,每台路由器都具备与其它路由器的路由选择组件通信的路由选择组件。然而,也存在其它方式来确定转发表的内容。
另一种方法是:远程控制器计算并分发转发表,供每台路由器使用。上下两图中,数据层面相同;而在下图中,控制层面的路由功能与路由器在物理上分离:路由器仅执行转发,而远程控制器给出转发表。远程控制器使用高可靠、高冗余的数据中心实现,并由ISP或第三方管理。路由器和远程控制器通过交换包含转发表和其它路由信息的报文来通信。此方法称为软件定义网络(Software-Defined Networking,SDN),因为计算转发表并与路由器交互的控制器是用软件实现的,故网络是“软件定义”的。这些软件实现也越来越开放,类似于Linux:这些代码可为公众所用,允许ISP(以及科研人员和学生)去创新并对控制网络层功能的软件提出更改建议。5.5节将进一步学习SDN。

网络层能提供的服务包括:
·确保交付。即保证分组最终到达目的地。
·具有时延上界的确保交付。即不仅确保分组的交付,而且在特定的主机到主机时延上界内(例如在100 ms内)交付。
·有序分组交付。该服务确保分组以它们发送的顺序到达目的地。
·确保最小带宽。只要发送主机以低于特定比特率的速率传输,则保证所有分组最终会交付到目标主机。
·安全性。网络层能够在源点加密所有数据报,并在目的地解密这些分组,从而对所有运输层报文段提供机密性。
这只是网络层能提供的部分服务。具体能提供哪些,视实现的不同而不同。
Internet的网络层仅提供单一的尽力而为服务(best-effort service):分组既不能保证按发送的顺序被接收,也不能保证最终成功交付;既不能保证分组不出错,也不能保证分组不重复;既不能保证端到端时延,也不能保证最小的带宽。这似乎是“根本无服务”的一种委婉说法:一个从来不向目的地交付分组的网络也符合尽力而为服务的定义!许多网络架构已定义和实现了超过Internet尽力而为服务的服务模型。例如,ATM(Asynchronous Transfer Mode,异步传输模式)网络体系结构确保按序时延、有界时延及最小带宽,但ATM网络现已很少使用。还有新提出的对Internet体系结构的服务模型扩展,例如,集成服务体系结构RFC 1633的目标是提供端到端时延保证与无拥塞通信。诚然,这些方案也许都很不错;但大量事实证明,Internet的尽力而为服务在带宽足够的情形下,已经表现得足够好,能够用于无数应用,包括Netflix、IP语音等串流影音,以及Skype和Facetime等实时会议应用。互联网能发展到今日的规模,充分证明了当初采用这种设计思路的正确性。

在继续学习之前,先明确几个常用术语:
路由器(router)和交换机(switch)都可以转发分组,即将分组从入站(输入)链路转移到出站(输出)链路。但路由器根据网络层数据报的报头来决定如何转发,而交换机既可能根据数据报的报头也可能根据链路层帧的报头来选择转发策略。因此,路由器工作在网络层,即第三层。工作在链路层和网络层的交换机常称为二层交换机和三层交换机。三层交换机具备一定的路由功能。随着技术的发展,三层交换机和路由器的功能越来越相似了(特别是高端产品)。
4.2 路由器的内部有什么?
路由器的结构通常是这样的:

主要的组件有:
·输入端口(input port)。输入端口执行几项重要功能:接收传输的位,这是物理层功能;与位于输入链路远端的链路层交互、传送帧,这是数据链路层功能;更重要的是,在输入端口还要执行查找功能(网络层功能)。这三个功能由各自的处理模块处理,在图上画成了三个方框。控制分组(如携带路由协议信息的分组)从输入端口转发到路由处理器。对于一般的数据分组,则按照分组首部中的目的地址查找转发表并进行转发。
一台路由器的端口数量可以很少,比如企业路由器;而位于某ISP边缘的路由器可以具有数百乃至上千个Gbps级别的端口,输入线路的数量在网络中也接近最大。
·交换结构(switching fabric)。交换结构将路由器的输入端口连接到它的输出端口。这种复杂的结构通常做成芯片(例如BCM83XX),位于路由器中,是一个网络路由器中的网络。
·输出端口。输出端口存储从交换结构接收的分组,并通过执行必要的链路层和物理层功能。在输出链路上传输这些分组。如果一条链路是双向的,那么输出端口通常与该链路的输入端口成对出现在同一线路卡上。
线路卡(line card)也称数字线路卡(digital line card),是一种用于交换机、路由器或其它网络设备的访问线路与访问设备间的一种设备接口。
·路由处理器。路由选择处理器通常比较接近传统的CPU,执行控制功能。在传统路由器中,它执行路由协议(见5.3、5.4节),对链路进行响应,维护路由表(见下文)、转发表与关联链路的状态信息。在SDN路由器中,它负责与远程控制器通信,接收由远程控制器计算的转发表项,并在路由器的输入端口写入这些表项。路由选择处理器还执行网络管理功能,将在5.7节学习相关内容。

如图,在交换结构之前,在每个输入端口处就可以查找转发表副本(影子副本,shadow copy)并决定转发路径,而无需统一交由路由处理器,避免了集中式处理的瓶颈。

如何构造转发表呢?暴力法是不可取的:即使只使用IPv4,整个表就可以具有30 ~ 40亿个条目。
一种方法是通过前缀选择出站链路。举例:一张转发表可以是这样的(每一项的其它内容未列出):

使用这种转发表,路由器用分组目标地址的前缀与表项匹配;如果存在匹配项,则向匹配项对应的链路转发分组。有多个匹配时,使用最长前缀匹配(longest prefix matching,LPM)算法:选择最长的匹配项,并向对应的链路转发分组。在4.3节学习Internet编址时,你将明白使用LPM的理由:网络前缀越长,其地址块就越小,因而路由就越具体。
查表理论上很简单,硬件逻辑只是搜索转发表查找最长前缀匹配。但在Gbps级别的速率下,这种查找必须在纳秒级的时间内执行完毕(设想一条10 G链路每秒能传送多少份几十到几百字节的IP数据报)。因此,不仅必须使用硬件执行查找,而且需要对大型转发表使用先进的搜索算法,还必须特别留意内存访问时间。为缩短这些时间,芯片上被整合DRAM和SRAM。实践中也经常使用三态内容寻址存储器(Ternary Content Address Memory,TCAM)来查找:32位的IP地址被放入内存,TCAM基本能在常数时间内返回对该地址的转发表项。一些路由器能保存上百万TCAM转发表项。

给定一个32位的目标IPv4地址(IPv4地址的格式见4.3节),一个最简单的匹配最长前缀的办法是:枚举全部可能的32种前缀,并在路由表中查找每一个枚举。当路由表中不具有相应的表项时,算法达到最坏情况。即便是对经常使用的路由,也需要浪费很多查找次数。
为了进行更加有效的查找,可以使用二叉字典树(binary trie)。字典树(trie)也称前缀树(prefix tree)、单词查找树,其每个节点代表一个字符串的前缀,任何一个节点的子节点代表的字符串都与该节点代表的字符串的前缀相同。下图给出了字典树与二叉字典树的示例:

根节点代表空字符串。在查找字符串时,从根节点出发,每读取前缀的一个字符,就根据读到的字符向深一层移动。如果能从根节点走到叶节点,就匹配到了一个完整的字符串(单词)。根据需求的不同,每个节点还可以存取额外的信息,比如单词的出现次数,等等。字符串本身不需要保存在节点中。图示中标注出完整的单词,只是为了演示trie的原理。
trie中的键通常是字符串,但也可以是其它的结构。trie的算法很容易修改为处理其它结构的有序序列,比如一串数字或者形状的排列。比如,bitwise trie(按位字典树)中的键是一串二进制位,可以用于表示整数或者内存地址等。位数据的存取由 CPU 指令一次直接实现,对于二进制数据,它理论上要比普通的trie快。
顺带一提,trie一词来自于retrieval(检索),具有两种读音(tree或try)。
事实上,我们在词典中查找单词时,根据前缀列出可能需要的单词这个功能就可以用字典树实现。如图:

为了进一步提高查找速率,常常对字典树进行压缩,以减少比较次数,进而减小查找时间。制作经过压缩的二叉字典树需要更多的计算,但由于每一次查找路由表时都可以提高查找速度,因此这样做还是值得的。
有的压缩技术则减小字典树的占用空间。此外,字典树的许多变种也已经问世。

注意:转发表和路由表是有区别的。路由表一般仅包含从目的网络到下一跳(用IP地址表示)的映射,而转发表是从路由表得出的。转发表必须包含完成转发所必需的信息:转发表的每一行都包含从要到达的目的网络到输出端口和某些MAC地址(见第6章)信息(如下一跳的MAC地址)的映射。将转发表和路由表用不同的数据结构实现有好处。因为在转发分组时,转发表的结构应当使查找过程最优化,但路由表则需要令网络拓扑变化时带来的计算量最少。路由表总是用软件实现的,但转发表可用特殊的硬件来实现。有的资料往往不去区分转发表和路由表的区别,而笼统地使用路由表这一名词。

一旦确定了输出端口,分组通常就进入交换结构。如果其它输入端口的分组占用了交换结构,后到的分组可能会被暂时阻塞,在输入端口排队,等待稍后处理。其它动作也需及时进行:①必须进行物理层和链路层相关的处理;②必须检查分组的版本号、校验和及寿命字段(见4.3节),并重写后两个字段;③必须更新用于网络管理(5.7节)的计数器(如接收到的IP数据报的数目)。
在输入端口查找目的IP地址,这是匹配(matching);发送该分组进入交换结构,这是动作(action)。“匹配 + 动作”(match-plus-action)的基本思想在许多网络设备中都能看到。在链路层交换机(第6章)中,除了发送帧进入交换结构去往输出端口外,还要查找链路层目的地址,并采取若干其它措施。在防火墙(第8章)中,首部符合过滤规则的分组可能被阻止转发。在网络地址转换(4.3节)中,一个运输层端口号匹配某给定值的输入分组,在转发(动作)前其端口号将被重写。这个思想对于我们将在4.4节中学习的通用转发是至关重要的。

常用的分组转发(交换)技术大致分为三种:
·内存交换(memory switching)。最简单、最早的路由器是传统的计算机,输入输出端口之间的交换是在CPU(路由选择处理器)的直接控制下完成的。I/O端口的功能就像传统操作系统中的I/O设备一样。一个分组到达输入端口时,该端口产生中断,向路由处理器发出信号。于是,分组从输入端口被复制到处理器内存中。路由处理器则从其首部提取目的地址,在转发表中找出适当的输出端口,将该分组复制到输出端口的缓存中。在这种情况下,如果内存带宽为每秒写入或读出N个分组,则总的转发吞吐量(分组从输入端口被传送到输出端口的总速率)必然小于N / 2。此外,不能同时转发两个分组,即使它们有不同的目标端口,因为通过共享系统总线一次仅能执行一个内存读 / 写操作。
许多现代路由器通过内存进行交换。然而,与早期路由器的一个主要差别是,目的地址的查找和将分组存储(交换)进适当的内存位置是由输入线路卡来处理的。在某些方面,经内存交换的路由器很像共享内存的多处理器,通过一张线路卡上的处理,将分组交换(写)进适当的输出端口的内存中。

·总线交换(bus switching)。在这种方法中,输入端口经一根共享总线将分组直接传送到输出端口,无需路由处理器的干预。这通常按以下方式完成:输入端口为分组预先设定一个交换机内部标签(首部),使分组在总线上传送并正确发送到对应的输出端口。该分组能由所有输出端口收到,但只有与该标签匹配的端口才能保存该分组(类似的情况非常常见,相信大家在数字逻辑电路必修课及其实验课上已经注意到了)。标签在输出端口被移除,因为其仅用于交换机内部来区别分组。如果多个分组同时到达路由器,每个位于不同的输出端口,则除了某一分组以外的其它分组必须等待,因为一次只有一个分组能够跨越总线。故路由器的交换带宽受总线速率的限制。较新的路由器中,总线带宽已经达到Gbps级别。

·互连网络交换(interconnection network switching)。克服单一、共享式总线的带宽限制的一种方法是:使用更复杂的互联网络,类似于互连多个CPU和GPU的拓扑结构。crossbar交换机具有一种由2N条总线组成的互联网络,连接输入输出端口各N个。每条垂直总线在交叉点与每条水平总线相交,交点由交换结构中的控制器控制,能够在任何时候开启和闭合。如上图,某分组到达端口A,需要转发到端口Y时,控制器闭合总线A和Y的交点,端口A在其总线上发送该分组,该分组仅由总线Y接收。来自端口B的一个分组在同一时间能够转发到端口X,因为A到Y和B到X的分组使用不同的输入输出总线。因此,与前面两种交换方法不同,这种结构可并行转发多个分组。纵横式交换机是非阻塞的(non-blocking),即只要没有其它分组被转发到该输出端口,转发到输出端口的分组就不会被阻塞。然而,如果来自两个不同输入端口的两个分组的目的地为相同的输出端口,则一个分组必须在输入端等待,因为在某个时刻经给定总线仍然仅能发送一个分组。更为复杂的互联网络使用多级交换,以使不同输入端口的分组可以同时转发到同一输出端口。路由器的交换能力也能够通过并行运行多种交换结构进行扩展。通过此方法,输入输出端口被连接到并行运行的N个交换结构。一个输入端口将一个分组分成K小块并且通过N个交换结构中的K个发送这些块到所选择的输出端口,输出端口再将K个块组装成原始的分组。

在路由器内部完成交换后,输出端口开始处理分组并发送到输出链路上,过程大致与输入端口的相应过程相反。

如果数据包来得太快,那么在输入和输出端口都可以形成等待队列。排队的位置和程度取决于流量负载、交换结构速率和线路速率。随着这些队列的增长,路由器的缓存空间将会耗尽。当无内存可用于存储到达的分组时,就出现丢包(packet loss)。前面我们常说分组“在网络中丢失”或“被路由器丢弃”。正是在路由器的这些队列中,分组被丢弃。当然,设备或线路出故障也可能使分组丢失。
为了尽量减少队列长度,路由器内部的交换结构转发分组的速率必须远远快于输入线路与输出线路的传输速率。

输入排队是路由器缓冲区排队的一种情况。如果交换结构的转发速率不够快,那么输入排队出现的概率就不低。
举例来说,现有一台使用crossbar形式的交换结构的路由器,并且:
【1】所有输入输出链路的传输速率相同;
【2】分组从任何一个输入端口传送到任何一个输出端口的用时都相同;
【3】分组按照FCFS(先来先服务)的方式进行转发。
那么,只要分组们的输出端口不同,多个分组就可以并行传送。然而,如果两个输入队列前端的两个分组发往同一输出队列,则其中一个分组将被阻塞,必须在输入队列等待,因为单个交换结构一次只能传送一个分组到指定端口。
如下图,左上和左下的输入队列中,最开始的分组都需要发往右上的输出队列。假设交换结构决定令左上的输入端口头部的分组先行传送,如此一来,左下的输入端口的头部的分组,连同它后面的一个分组,都需要在队列中等待,即便它之后的那个分组并不是要一起发送到右上的输出端口,而是将发送到中间的输出端口,且中间的输出端口并未被其它分组占用。这称为线路头部(Head-of-the-Line,HOL)阻塞。有研究指出,当发生HOL阻塞时,只要输入链路上的分组到达速率达到其容量的58%,在某些情况下,输入队列长度就可无限增大,导致大量丢包。现在已有多种解决线头阻塞的方法。

即便交换结构的转发速率足够高了,如果多个包同时指向一个输出端口,那么也有不低的几率引发输出排队。
这是路由器缓冲区排队的另一种情况,如下图。

当没有足够的内存来缓存输入分组时,要么丢弃到达的分组,即弃尾(drop-tail),要么删除若干个已排队的分组来腾出空间。某些情况下,在缓存填满之前丢弃部分分组(或在其首部加上标记)的做法是有利的,这可以向发送方提供拥塞信号。多年来,已经提出了许多分组丢弃与标记策略,统称主动队列管理(Active Queue Management,AQM)算法。随机早期检测(Random Early Detection,RED)算法是研究和实现最广泛的AQM算法之一。

AQM策略是TCP拥塞控制行为的最大影响因素。路由器的尾部丢弃往往会导致一连串分组的丢失,这就使发送方出现超时重传,使TCP进入拥塞控制的慢开始状态,结果使TCP连接的发送方突然把数据的发送速率降低到很小的数值。
更为严重的是,网络中通常有非常多的TCP连接,这些连接中的报文段通常是复用在网络层的 IP 数据报中传送的。在这种情况下,若路由器进行尾部丢弃,就可能会同时影响很多条TCP连接,结果使大量TCP连接突然同时进入慢开始状态。这在TCP术语中称为全局同步(global synchronization)。
全局同步使全网的通信量突然下降了很多,而在网络恢复正常后,其通信量又突然增大很多。

RED需要使路由器维持两个参数:队列长度最小门限T_min和最大门限T_max。当每个分组到达时,RED按照规定的算法先计算当前的平均队列长度L_ave。
(1) 若平均队列长度小于最小门限,则把新到达的分组放入队列进行排队。
(2) 若平均队列长度超过最大门限,则把新到达的分组丢弃。
(3) 若平均队列长度在最小门限和最大门限之间,则有概率p把新到达的分组丢弃(丢弃分组的随机性)。
由此可见,RED不是等到已经发生网络拥塞后才把所有在队列尾部的分组全部丢弃,而是在检测到网络拥塞的早期征兆(路由器的平均队列长度达到一定数值时)时,就以概率p丢弃个别的分组,让拥塞控制只在个别的TCP连接上进行,因而避免发生全局性的拥塞控制。
在RED中,最难处理的就是丢弃概率p的选择,因为p并不是个常数。对每一个到达的分组,都必须计算丢弃概率p的数值。IETF曾经推荐在互联网中的路由器使用RED机制 [RFC 2309],但多年的实践证明,RED的使用效果并不太理想。因此,在2015年公布的RFC 7567已经把过去的RFC 2309列为“陈旧的”,并且不再推荐使用RED。然而,对路由器进行AQM仍是必要的。AQM实际上就是对路由器中的分组排队进行智能管理,而不是简单地把队列的尾部丢弃。现在已经有几种不同的算法代替旧的RED,但都还在实验阶段。目前还没有一种算法成为IETF的标准。读者可留意这方面的进展。

路由器通过缓存来吸收流量负载的波动。经验建议将缓存容量设为与时延带宽积相等的值。例如,一条10 Gbps链路,如果其RTT为250 ms,则该链路连接的路由器需要2.5 Gb的缓存。不过,也有后续理论和实验表明,当有大量的TCP流(N条)流过一条链路时,所需要的缓存容量是在时延带宽积的基础上再除以√N。

先进先出(FIFO)也称先来先服务(FCFS),是分组调度的常用算法之一。它按照分组到达输出链路队列的先后次序来选择在链路上传输的分组。如果链路当前正忙于传输另一个分组,后到达的分组就要排队等待。如果缓存耗尽,队列的分组丢弃策略则确定要丢弃哪些分组。下面的讨论将忽略分组丢弃。当一个分组通过输出链路传输完毕时,将其移出队列。

在优先队列(priority queuing)规则下,到达输出链路的分组被分类放入多条队列,每个队列的优先级不同。例如,携带网络管理信息的分组(如:由源或目的TCP/UDP端口号所标识)可以获得超过用户流量的优先权;基于IP的实时话音分组可能获得超过非实时流量(如SMTP或IMAP邮件分组)的优先权。当选择一个分组传输时,此算法从优先级最高的队列中选择。同一优先权的分组常以FIFO方式处理。在非抢占(non-preemptive)优先队列规则下,一旦分组开始传输,就不会被打断。

在循环排队(round-robin queuing)规则下,分组也被分类。然而,类之间不存在严格的优先权,调度器在这些类之间轮流提供服务。保持工作排队(work-conserving queuing)规则在有分组排队等待传输时,不允许链路保持空闲:当给定类为空时,要求立即检查循环序列中的下一个类。
广泛使用于路由器中的RR算法是加权公平排队(weighted fair queuing,WFQ)算法。WFQ和一般的RR算法的不同在于,每个类分到的服务时间一般不同。
4.3 Internet协议(IP):IPv4、编址、IPv6和其它
Internet协议版本4(IPv4)数据报的报头结构如下:

各字段的含义是:
·版本(version)。这4位指示IP版本。路由器通过版本号确定如何解释IP数据报的剩余部分。不同的IP版本使用不同的数据报格式。IPv4的数据报格式如上图。IPv6的数据报格式将在后续讨论。

·报头长度(header length)。4位。一个IPv4数据报的报头可以包含可变数量的选项,故需要用这4位确定IP数据报中载荷(例如运输层段)开始的位置。大多数IP数据报不包含选项,所以一般的IP数据报具有20字节的首部。
首部的实际长度=首部长度字段值×4。因此,首部为20字节的IP数据报,其首部长度字段为5。如果IP数据报的首部长度不是4字节的整数倍,那么需要在首部的最后补齐。
如果首部没有选项的IP数据报承载一个TCP报文段,则每个数据报共承载了总长40字节的首部(20字节的IP首部加上20字节的TCP首部)以及应用层报文。

·服务类型(type of service)。8位,新标准(1998年)称区分服务(differentiated service)。使不同类型的IP数据报(例如,一些特别要求低时延、高吞吐量或可靠性的数据报)能区别开来。网络管理员配置路由器,明确需要提供哪些特定等级的服务。在3.7节学习显式拥塞通知(ECN)时,已经提到过需要两个TOS位。多数情况下,该字段都不使用。

·数据报长度(datagram length)。16位,IP数据报的理论最大长度为65535字节。该字段代表IP数据报的总长(报头 + 数据),以字节计。然而,数据报很少超过1500字节,因为IP数据报需要放在单个以太网帧里。
在第6章将看到,不是所有链路层协议都能承载相同长度的网络层分组。有的协议能承载大数据报,有的不能。例如,以太网帧能够承载不超过1500字节的数据,而某些广域网链路的帧只能承载不超过576字节的数据。一个链路层帧能承载的最大数据量叫做最大传送单元(Maximum Transmission Unit,MTU)。每份IP数据报封装在链路层帧中从一台路由器传输到下一台路由器,故链路层协议的MTU严格限制了IP数据报的长度。不过这并非主要问题,主要问题在于发送方与接收方路径上的每段链路可能使用不同的链路层协议,且每种协议可能具有不同的MTU。
虽然使用长的IP数据报会使传输效率提高(报头占总长度的比例更小),但数据报短些也有好处。IP数据报越短,路由器转发的速度就越快。为此,IP规定,互联网中所有的主机和路由器,必须能够接受长度不超过576字节的数据报。假定上层交下来的数据有512字节(合理的长度),加上最长的IP首部60字节和4字节的余量,就得到576字节。当主机需要发送超过576字节的数据报时,应当先确定目标主机可以接受所要发送的数据报长度,否则就要分片(见下文)。

·标识符(identifier)、标志位(flags)和片偏移(fragmentation offset)。分别占16位、3位和13位。这三个字段与IP分片有关。IPv6不允许在路由器上对分组分片。
标识号并不是序号,因为IP是无连接服务,不用管数据报是否被按序接收。
标志字段目前只有2位有意义:最低位MF(more fragment)。MF = 1表示后面还有分片的数据报;MF = 0表示这已是若干数据报片的最后一片。中间的一位记为DF(Don’t Fragment)。仅DF = 0时才允许分片。
为了把过大的数据报放入不同协议的链路层帧中,需要对数据报分片(fragmentation),再封装进链路层帧。到达目标主机后,分片被重新组装。TCP与UDP都希望从网络层收到完整的、未分片的报文。IPv4的设计者认为:如果在路由器中重新组装数据报,会将协议变得极其复杂并影响路由器的性能。为使网络内核保持简单,他们将数据报的重组任务交由目标主机,而不是路由器。
当目标主机从相同的源收到一系列数据报时,它需要确定这些数据报中的某些是否是一些原来的较大数据报的片。若是,则它必须进一步确定何时收到了最后一片,如何将这些片拼接成原始的数据报。为了让目标主机执行重组任务,IPv4的设计者将标识符、标志位和片偏移字段放在了IP数据报首部中。
生成一份数据报时,发送主机为该数据报设置源和目的地址,并分配标识符。发送主机通常依次将发送的每个数据报的标识符加1。当路由器需要对一份数据报分片时,形成的每片数据报都具有相同的(即初始数据报的)源与目的地址和标识符。当目的地收到同一主机的一系列数据报时,它检查数据报的标识符,确定哪些数据报实际上是同一较大数据报的片。由于IP是不可靠服务,一些片可能永远到达不了目的地。为了让目标主机确信已收到初始数据报的最后一个片,最后一片的标志位中的MF位置0,而其它片的MF位置1。
另外,为了让目标主机确定是否丢失了片并按正确的顺序重新组装片,使用偏移字段指定该片应放在初始IP数据报的哪个位置。也就是说,相对于用户数据字段的起点,该片从何处开始。片偏移以8个字节为偏移单位。这就是说,每个分片的长度一定是8字节(64位)的整数倍。
现在已经有了多种确定路径MTU(Path MTU,一条路径上的多个实体的MTU的最小值)的方法,并基于路径MTU值设置MSS。发送端主机发送IP数据报时,设置报头的分片标志DF = 1(不能分片),这样途中的路由器即使遇到需要分片才能处理的大包,也不会去分片,而是将包丢弃。然后,路由器通过一个ICMP(5.6节)的目标不可达消息将数据链路上的MTU的值给发送主机。接着,发送端主机发送给同一台目标主机的IP数据报就按这个MTU值大小分片。如此反复,直到数据报被发送到目标主机为止没有再收到任何ICMP消息,就认为最后一次ICMP所通知的MTU即是一个合适的MTU值。这个MTU就是Path MTU。

·生存时间(time-to-live,TTL)。8位。TTL字段确保数据报不会在环路中长期循环。数据报每被一台路由器处理,该字段的值就减1。若TTL字段减为0,则数据报必须丢弃。当终点在预定时间内不能收到一份数据报的全部片时,就无法组装成原来的数据报,于是只能把已收到的片都丢弃,并向源点发送超时报文(见5.6 ICMP)。

·上层协议(upper-layer protocol)。8位。该字段通常仅当IP数据报到达目的地时才有用,指示了IP数据报的数据部分应交给哪个运输层协议。值为6表明交给TCP,而值为17表明交给UDP。这些值由IANA规定。IP数据报中的协议号所起的作用,类似于运输层报文段的端口号的作用。协议号将网络层与运输层绑定到一起,而端口号将运输层和应用层绑定到一起。在第6章将看到,链路层帧也有一个特殊字段用于将链路层与网络层绑定到一起。

·报头校验和(header checksum)。首部校验和用于帮助路由器检测收到的IP数据报中的位错误。校验和是这样计算的:先将校验和字段填零,然后将参与校验的部分以16位为单位累加起来(最高位的进位加到最低位),最后取反。得到的校验和称为Internet校验和,此方法在3.3节已经讨论过了。路由器要对收到的每份IP数据报计算首部检验和,如果数据报首部携带的检验和与计算的检验和不一致,则判定该包出错。路由器一般直接丢弃出错的数据报。在每台路由器上,必须重新计算检验和并再次写入报头,因为TTL及选项字段都可能会改变。Internet检验和的快速算法也被发明出来了。
为什么TCP/IP在运输层与网络层都执行差错检测?首先,IP层只对IP首部计算了检验和,而TCP/UDP检验和是对整个TCP/UDP报文段进行的。其次,TCP/UDP与IP不一定必须属于同一个协议栈。TCP能够运行在不同的协议(如ATM)上,而IP能够携带不传递给TCP/UDP的数据。即:其它协议未必提供检错功能,所以一些协议选择提供检错机制。

·源IP地址(source IP address)和目标IP地址(destination IP address)。源生成数据报时,它在源IP和目标IP字段分别写入它的IP地址和目的地的地址。通常源主机通过DNS查找来决定目标地址。后文将详细讨论IP编址。

·选项(options)。选项字段允许扩展IP首部,但很少使用,因此IP数据报首部一般不包括选项字段,这样能够节约开销。然而,少量选项的存在的确使问题复杂了。因为数据报首部长度可变,故不能预先确定数据字段从何处开始。而且有些数据报要求处理选项,而有些数据报则不要求,这导致路由器处理IP数据报所需的时间可能波动很大。这些影响对于高性能路由器和主机上的IP处理来说,都是必须考虑的。由于种种原因,很多路由器都不理会选项字段,并且在IPv6首部中也已去掉了IP选项。
选项字段用来支持排错、测量以及安全等措施,内容很丰富。此字段的长度可变,从1个字节到40个字节不等,取决于所选择的项目。某些选项项目只需要1个字节,它只包括1个字节的选项代码。而有些选项需要多个字节,这些选项一个个拼接起来,中间没有分隔符,最后用全0填充补齐为4字节的整数倍。

·数据(有效载荷)。多数情况下,IP数据报的数据字段包含要交付给目的地的运输层报文段(TCP或UDP)。然而,数据字段也可承载其它类型的数据,如ICMP报文(5.6节)。

在讨论IP编址之前,简述一下主机与路由器连入网络的方法。一台主机通常只有一条链路连接到网络;主机中的IP发送数据报时,就在该链路上发送。主机与物理链路之间的边界叫做接口(interface)。路由器负责从链路上接收数据报并转发,所以路由器必须至少拥有两条链路。路由器与它的任意一条链路之间的边界也叫接口,因而一台路由器有多个接口,每个接口连接一条链路。因为每台主机与路由器都能收发IP数据报,所以IP要求每台主机和路由器的接口拥有自己的IP地址。如果主机具有多张网卡,则每张网卡访问网络后都会获得自己的IP地址。因此,从技术上讲,一个IP地址与一个接口关联,而不是与接口所在的主机或路由器关联。
当两台路由器直接相连时(例如通过一条租用线路),在连线两端的接口处,可以分配也可以不分配IP地址。如分配了IP地址,则这一段连线就构成了一种只包含一段线路的特殊“网络”。之所以叫做“网络”是因为它有IP地址。但为了节省IP地址资源,对于这种仅由一段连线构成的特殊“网络”,现在也常常不分配IP地址。通常把这样的特殊网络叫做无编号网络(unnumbered network)或匿名网络(anonymous network)。

每个IP地址长32位(4字节),因此总共有232个(约42亿)可能的IP地址。这些地址通常按点分十进制记法(dotted-decimal notation)书写,即地址中的每个字节用十进制书写,字节间以句点隔开。例如:
193.32.216.9
Internet中的每台主机和路由器上的每个接口,都必须具有全球唯一的IP地址(使用NAT时除外,见4.3节)。然而,这些地址不能随意地自由选择。一个接口的IP地址的一部分需要由其连接的子网来决定。

子网(subnet),在IP中指的是从分类网络中划分出来的一部分。分类网络也称分级定址(classful addressing)。这种方法应用于早期,它将IPv4的地址分为了5类:

分类的IP地址,前若干位是网络号(net-id),标识主机或路由器连接到的网络。一个网络号在整个互联网范围内必须是唯一的。剩余部分是主机号(host-id),标识主机或路由器。一个主机号在它前面的网络号所指明的网络范围内必须是唯一的。最终,一个IP地址在整个互联网范围内是唯一的。

子网的定义也可以这样表述:
To determine the subnets, detach each interface from its host or router, creating islands of isolated networks, with interfaces terminating the end points of the isolated networks. Each of these isolated networks is called a subnet.
译:为了确定子网,将每个接口从所属主机或路由器分开,产生几个隔离的网络岛,接口端连接这些隔离的网络的端点。这些隔离的网络中的每一个都叫做一个子网(subnet)。

A、B、C类地址都是单播地址。单播(unicast)是指封包在計算機網絡的傳輸中,目標地址為單一目標的一種傳輸方式。它在現今網絡應用最為廣泛,通常所使用的網絡協議或服務大多采用單播傳輸,比如一切基於TCP的協議。單播通訊中,每次只有兩個實體相互通訊,發送端和接收端都是唯一確定的。
除單播傳輸方式外,還有广播(broadcast)和多播(multicast,也称组播或群播)。它們與單播的區別是:廣播的目標地址為網絡中的全體目標,而多播的目標地址是一組目標,加入該組的成員均是封包的目的地。此外還有任播(anycast),這是一種網路定址和路由的策略,使得資料可以根據路由拓扑來決定送到“最近”或“最好”的目的地。
在單播中,網路位址和網路節點之間存在一一對應的關係。
在廣播和多播中,網路位址和網路節點之間存在一對多的關係:每一個发送位址對應一群接收可以複製資訊的節點。
在任播中,網路位址和網路節點之間存在一對多的關係:每一個位址對應一群接收節點,但在任何給定時間,只有其中之一可以接收到傳送端來的資訊。

A类地址的网络号占1字节,只有7位可供使用(最高位固定为0)。但可指派的网络号是126个(27—2)。—2是因为:
【1】IP地址中的全0表示“这个(this)”。网络号全0的IP地址是保留地址,意思是“本网络”。
【2】网络号为127(01111111b)的地址保留作为本地软件环回测试(回环测试,loopback test)本主机的进程间通信之用。若主机发送目的地址为环回地址(回送地址,如127.0.0.1)的IP数据报,则本主机中的协议软件就处理数据报中的数据,而不会把数据报发送到任何网络。许多计算机都将域名localhost指向127.0.0.1。localhost指代本计算机或本主机,可以用它来获取运行在本机上的网络服务。将网络服务的监听地址设为127.0.0.1,则会接收所有来自本地的请求。
注意:对于A类地址127...*,主机号为全0或全1的地址不属于回送地址。
除了进行回环测试以外,127开头的地址还可以用于DDoS攻击防御:网站收到DDoS攻击之后,将域名记录到127.0.0.1,即让攻击者自己攻击自己。但127.0.0.1是一个环回地址,严格来说并不表示“本机”。

A类地址的主机号占3字节,因此每个A类网络的最大主机数是224 – 2 = 16777214。减2的原因是:
【1】全0的主机号字段表示的IP地址是本主机连接到的单个网络的地址。例如,主机的IP地址为5.6.7.8,则所在网络的地址就是5.0.0.0。
如果主机号连同网络号也一起是0(0.0.0.0),则表示一个无效的,未知的或者不可用的目标。
不过,在服务器中,0.0.0.0也可以指所有IPv4地址。例如,如果主机上的一项服务监听的地址是0.0.0.0,那么通过所有IP地址都能够访问该服务。
在路由中,0.0.0.0表示的是默认路由(任意IPv4主机,见5.1节),路由表中找不到完全匹配的路由时,使用默认路由。
此外,当主机还没有被分配IP地址(参见下文DHCP)的时候,0.0.0.0也用于表示主机本身(本网络中的本机)。
【2】全1表示“所有的(all)”,因此全1的主机号字段表示该网络上的所有主机。

B类地址的网络号字段有2字节,但前面两位(10)已经固定了,剩下14位可以分配。因为网络号字段后面的14位无论怎样取值也不可能使网络号全0或全1,因此不存在网络总数减2的问题。B类地址可指派的网络数为214,即16384。B类地址的每一个网络上的最大主机数是216 – 2,即65534。这里需要减2是因为要扣除全0和全1的主机号。
C类地址有3字节的网络号字段,最前面的3位是110,还有21位可以分配。因此C类地址可指派的网络总数是221,即2097152。每一个C类地址的最大主机数是28 – 2,即254。
勘误:从亚太网络信息中心(Asia Pacific Network Information Center,APNIC)中可以查到,地址128.0.0.已经被分配。RFC 3330指出,因为无类(见下文CIDR)地址空间的原因,128.0..*和192.0.0.*不再需要保留。谢希仁《计算机网络》直到最新版本(第7版)也没有纠正。192.0.0.*虽然目前尚未分配,但将在今后进行分配。

在早期,IP地址的网络部分的长度限制为8、16或24位。这种限制难以应对中小规模组织迅速增加的联网需求。一个C类子网仅能容纳254台主机,对许多机构来说太小了;而一个B类子网可支持多达65534台主机,又太多了。在分类编址方法下,超过254台需要接入Internet的主机的机构只能使用B类地址,这会导致B类地址空间的迅速损耗,地址空间的利用率也很低下。例如,为具有2000台主机的组织分配一个B类地址,该组织就具有足以支持多达65534个接口的地址空间;但剩下的63000余个地址却不能被其它机构使用。
而且,给每个物理网络分配网络号会使路由表变得太大,令网络性能变坏。每台路由器都应当能够从路由表查出到达其它网络的下一跳路由器。因此,互联网中的网络数越多,路由表的项目数也越多。这不仅增加了路由器的存储成本,还使查找路由耗费更多的时间,也使路由器之间定期交换的路由信息急剧增加,使整个互联网的性能都大大下降。
此外,如果IP地址仅被分成两级,就不够灵活。有时情况紧急,一个单位需要在新的地点马上开通一个新的网络。如果按照原有方案,在申请到一个新的IP地址之前,新网络是不能连接到互联网的。我们希望有一种方法,使一个单位能随时灵活地增加本单位的网络,而不必事先到互联网管理机构申请新的网络号。原来的两级IP地址无法做到这一点。

1985年,IP地址中增加了子网号字段。这能较好地解决上述问题,使用起来也很灵活。这种做法叫划分子网(subnetting)或子网寻址或子网路由。划分子网已成为互联网的正式标准协议。
于是,IP地址分成了三级:网络号、子网号和主机号。原先的两级IP地址中的主机号的高若干位被借用为子网号了。划分子网只是把IP地址的主机号这部分进行再划分,而不改变IP地址原来的网络号。
一个拥有许多物理网络的单位,可将管辖的物理网络分为若干个子网。划分子网是单位内部的事情,本单位以外的网络看不见这个网络由多少个子网组成,因为单位网络对外仍然表现为一个网络。凡是从其它网络发送给本单位主机的IP数据报,仍然是根据IP数据报的目的网络号找到连接在本单位网络上的路由器。这些路由器收到IP数据报后,再按目的网络号和子网号找到目的子网,把IP数据报交付目的主机。

从IP地址乃至整个IP数据报报头都无法得知子网号,这就需要用到子网掩码(subnet mask)。每个子网都有一个子网掩码。有时子网掩码和子网的地址记在一起,如:
223.1.1.0/24
代表子网掩码为255.255.255.0(高24位都是1),前24位是子网地址。同一子网所有主机的地址前缀都相同。上例中,该子网的每台主机的地址都是223.1.1.*。虽然RFC文档没有规定子网掩码中的1必须是连续的,但极力推荐在子网掩码中选用连续的1,以免出错。用主机的IP地址与子网掩码进行按位与运算,就得到子网的IP地址。
在不划分子网时,还要使用子网掩码,这是为了更便于查找路由表。互联网的标准规定:所有的网络都必须使用子网掩码,同时在路由器的路由表中也必须有子网掩码这一栏。如果一个网络不划分子网,那么该网络的子网掩码就使用默认子网掩码。默认子网掩码中1的位置和IP地址中的网络号字段正好对应。于是,不用查找该地址的类别位就能知道这是哪一类的IP地址。A、B、C类地址的默认子网掩码分别是255.0.0.0(FF 00 00 00)、255.255.0.0(FF FF 00 00)和255.255.255.0(FF FF FF 00)。
然后提一提变长子网掩码(variable length subnet mask,VLSM)。VLSM其实就是相对于类的IP地址来说的。A、B、C类的网络号分别占高8位、高16位和高24位。而VLSM的作用就是在类的IP地址的基础上,从它们的主机号借用相应的位数作为网络号,也就是增加网络号的位数。A类有24位可以借,B类有16位可以借,C类有8位可以借。但实际上不可以都借出来,因为IP地址中必须要有主机号的部分;而且主机号部分剩下1位是没有意义的,剩下1位的时候不是代表主机所在的网络号就是代表广播号。所以在实际中可以借的位数要减去2。

子网掩码是网络或子网的重要属性。在RFC 950成为互联网的正式标准后,相邻路由器交换路由信息时,必须把自己所在网络(子网)的子网掩码告诉相邻路由器。若一台路由器连接在两个子网上,就拥有两个网络地址和两个子网掩码。
虽然根据RFC 950,子网号不能为全1或全0,但随着CIDR(见下文)的广泛使用,现在全1和全0的子网号也可以使用了,但要弄清你的路由器软件是否支持全0或全1的子网号。如果你需要在试卷上作答,则以课本答案或老师要求为准。
划分子网增加了灵活性,但却减少了能够连接在网络上的主机总数,因为除了子网号一般不能为全0或全1以外,每个子网的主机号都不能是全0或全1。

Internet的地址分配策略称为无类别域间路由(Classless Interdomain Routing,CIDR)。CIDR将子网寻址的概念一般化了。使用子网寻址时,32位的IP地址分为两部分(IP地址又回到了两级编址),并且也具有点分十进制形式a.b.c.d/x,其中x指示第一部分的位数。
形如a.b.c.d/x的地址的高x位构成了IP地址的网络部分,常称为该地址的前缀(prefix,或网络前缀)。一个组织通常被分配一块连续的地址,即具有相同前缀的一段地址,也称“/x地址块”。“/x”称作地址掩码(address mask),与子网掩码类似。虽然CIDR不使用子网了,但由于目前仍有一些网络还使用子网划分和子网掩码,因此CIDR使用的地址掩码也可继续称为子网掩码。“CIDR不使用子网”是指CIDR本身并没有在32位地址中指明若干位作为子网字段。但分配到一个CIDR地址块的单位,仍然可以在本单位内根据需要划分出一些子网。这些子网也都只有一个网络前缀和一个主机号字段,但子网的网络前缀比整个单位的网络前缀要长些。
这种情况下,组织内部的设备的IP地址共享相同前缀。5.4节讲解BGP时,将看到组织网络外部的路由器仅考虑前缀。这就是说,组织外部的路由器转发的数据报的目的地址位于组织内部时,仅需考虑地址的前x位。这极大减少了参与转发的路由器中转发表的长度:形如a.b.c.d/x的单一表项足以支持将数据报从组织外转发到该组织内的任何目标。
CIDR记法有多种形式,例如,地址块10.0.0.0/10可简写为10/10,也就是把点分十进制中低位连续的0省略。另一种简化表示方法是在网络前缀的后面加一个星号*,如:00001010 00的意思是:在星号之前是网络前缀,而星号*表示IP地址中的主机号,可以是任意值。

如上图,该例可以说明使用CIDR策略时,仔细设计分配方案有利于路由。名为Fly-By-Night的ISP负责了8个组织的联网服务。该ISP向外界通告,应当发送所有地址的前20位与200.23.16.0/20相符的数据报。外界不需要知道在地址块200.23.16.0/20内实际上还存在8个子组织,每个组织还有自己的子网。这种使用单个前缀通告多个网络的能力通常称为地址聚合(address aggregation),也称路由聚合(route aggregation)或路由摘要(route summarization)或构建超网(supernetting)。路由聚合使得路由表中的单个表项可以表示更多地址的路由,大大减小了路由表的大小。
当地址像这样整块整块分给ISP,又由ISP分给客户组织时,地址聚合工作极为有效。但是当地址不是按这样的层次方式分配时,会是什么情况呢?例如,如果Fly-By-Night-RP把ISPs-R-Us也收购了,然后让组织1通过ISPs-R-Us与Internet相连,会发生什么?ISPs-R-Us拥有地址块199.31.0.0/16,但组织1的IP地址在该地址块之外。这里应该怎么办?
组织1当然可以将其所有的路由器和主机重新编号,使得地址在ISPs-R-Us的地址块内。但这种方案代价很高,而且组织1将来也许还会被Fly-By-Night-ISP分配另一个ISP。
典型的解决方案是:组织1保持其IP地址在200.23.18.0/23内。如下图,Fly-By-Night-ISP继续通告地址块200.23.16.0/20,ISPs-R-Us同时向外界通告地址块199.31.0.0/16和组织1的地址块200.23.18.0/23。当Internet上的其它路由器检测到地址块200.23.16.0/20(来自Fly-By-Night-ISP)和200.23.18.0/23(来自ISPs-R-Us),并且想路由到地址块200.23.18.0/23内的一个地址时,它们将使用最长前缀匹配(4.2节),并朝着ISPs-R-Us路由,因为它通告了与目的地址相匹配的最长(最具体)的地址前缀。

当一台主机发出一个目的地址为255.255.255.255的数据报时,该报文会交付(广播)给同一子网中的所有主机。路由器也可以向邻近的子网转发该报文(虽然它们通常不这样做)。

下面来看一看组织机构和主机如何获得IP地址。
网络管理员可以从ISP获取一些IP地址(地址块)。ISP本身也是用这种方法向其上级ISP获取地址的。不断向上追溯,Internet名称和数字分配机构(Internet Corporation for Assigned Names and Numbers,ICANN)向各ISP和其它组织分配地址块。作为NPO(非营利组织)的ICANN不仅负责分配IP地址,还管理DNS根服务器,还负责分配域名、解决域名纷争。ICANN向区域Internet注册机构(如ARIN、RIPE、APNIC、AFRINIC和LACNIC)分配地址,这些机构一起形成了ICANN的地址支持组织,处理本区域内的地址分配和管理。ICANN行使Internet数字分配机构(Internet Assigned Numbers Authority,IANA)的职能。

组织机构的网络管理员获取了一块IP地址后,为管理的网络中的主机分配地址。主机地址可以手动配置,但操作繁琐,因此多使用动态主机配置协议(dynamic host configuration protocol,DHCP)完成。运行DHCP的主机(客户端或服务器)自动获取IP地址。网络管理员能配置DHCP,可以使特定的主机总是得到相同的IP地址,或只是临时为其分配IP地址,一段时间后改变。DHCP还允许一台主机得知其它信息,例如它的子网掩码、它的第一跳路由器地址(常称为默认网关)与本地DNS服务器的地址。
由于DHCP具有将主机连接进一个网络的网络相关方面的自动能力,故它属于即插即用协议(plug-and-play protocol)或零配置(zeroconf)协议。这对网管和用户都非常有吸引力:如果没有DHCP,网管和用户在接入每个不同的网络时,都将不得不手工执行这些任务。
DHCP也是客户端-服务器协议。通常,每个子网会有一台DHCP服务器。如果没有,则DHCP依赖一个知道此网络的DHCP服务器地址的中继代理(relay agent,一般是路由器)。

当新主机加入一个子网时,DHCP协议需要执行4个步骤:
【1】DHCP服务器发现。新主机通过68端口发送一个UDP包(DHCP发现报文,DHCP discover message)。但此时该主机还不知道DHCP服务器的地址,甚至连加入的这个网络的地址也不知道。实际上,DHCP客户端发送一个源地址和目标地址分别为0.0.0.0(无IP地址)和255.255.255.255的广播信息。该报文将在链路层(见第6章)被广播到所在子网的全部结点。如果DHCP发现报文由DHCP中继代理收到,则代理以单播方式向DHCP服务器转发此报文,并等待其响应。
勘误:《计算机网络;自顶向下方法》(第7版)的“……a client sends within a UDP packet to port 67……”与实际不符。
【2】DHCP服务器提供。当DHCP服务器的UDP端口67收到DHCP发现报文后,便向客户端发送DHCP提供报文(DHCP offer message),该报文亦将广播到子网的全部结点(目标地址为广播地址)。一个网络可以具有多台DHCP服务器,此时客户端可以任选一台。每份DHCP提供报文都包含接收到的DHCP发现报文的事务ID、客户端IP地址、子网掩码和IP地址租约时间(address lease time)——在此时间之前,IP地址保持有效。租约时间常为数小时或数天,使用4字节表示,单位为秒。因此可供选择的租用期范围从1秒到136年。如果使用了DHCP中继代理,则代理收到DHCP服务器回答的提供报文后,把此提供报文发回给主机。
【3】DHCP请求。连接到子网的新客户端选择其中一台或多台服务器发送DHCP请求报文作为DHCP offer报文的回应,将配置参数回传。
【4】DHCP确认。服务器收到DHCP请求后,返回一条DHCP ACK报文,确认请求的参数。

当客户端收到DHCP ACK后,交互完成,客户端可以在租约期限内使用DHCP分配的IP地址。
客户端可能希望租约过期后仍使用此IP地址,DHCP也提供了相应的续约机制。DHCP客户端设置两个计时器T1和T2,默认超时分别是0.5T和0.875T(RFC 2131)。RFC 2131建议超时随机上下浮动,避免大量DHCP客户端在短时间内请求续约。在租约时间剩余1/2和1/8时,可以请求更新租约时间。若DHCP服务器同意续约,则发回DHCP ACK报文,租约时间重新计时。若服务器发回DHCP NACK报文,这时DHCP客户必须立即停止使用原来的IP地址,而必须重新申请IP地址。DHCP服务器可以不响应续约请求,此时原有租约继续有效。
此外,DHCP客户可以提前终止服务器提供的租用期,这时只需向DHCP服务器发送释放报文DHCP RELEASE即可。

从移动性来说,DHCP有一个非常显著的缺点:一个结点每次连入新子网时,都需要通过DHCP获得新的IP地址,于是当这台主机不断在不同的子网之间切换时(例如:此结点是移动中的手机),TCP连接将无法持续。第7章将介绍移动IP(mobile IP),这个IP基础设施扩展允许移动设备在切换子网时长期使用单一地址。

随着小型办公室和家庭办公室(Small Office and Home Office,SOHO)的崛起,小范围局域网的需求也在暴涨。如果每个小型网络都向运营商获得一片连续的IPv4地址,那么地址将极快耗尽。启用了网络地址翻译(network address translation,NAT,网络地址转换)的路由器允许将使用私网地址(private address)连接的接口转换为公网地址(反向转换亦可)。使用私网地址连接到该路由器的子网后,子网内的主机可以使用私网地址相互通信。私网地址也称本地地址、专用地址,用于局域网内部,与需要向互联网管理机构申请的全球唯一的IP地址(也称公网地址或全球地址)相对,仅在特定的网络内有意义。采用私网地址的互联网也称专用互联网或本地互联网,简称专用网。互联网上的路由器都不转发目的地址是专用网本地IP地址的IP数据报。
RFC 1918规定,IPv4具有三类私网地址,它们分别是:
类别 范围 或简记为
A类(24位块) 10.0.0.0 ~ 10.255.255.255 10.0.0.0/8
B类(20位块) 172.16.0.0 ~ 172.31.255.255 172.16.0.0/12
C类(16位块) 192.168.0.0 ~ 192.168.255.255 192.168.0.0/16
10.0.0.0本来是分配给ARPANET的。由于ARPANET已经停止运行,因此这个地址就用作专用地址。
启用了NAT的路由器与一般的路由器表现得不同些。该路由器对外等效于一台仅具有公网IP地址的设备:任何从外部向连接到该路由器的小型局域网通信时,必须使用该路由器对外的公网地址;而从局域网内向外发送的报文离开路由器后,也都具有路由器的公网IP地址。局域网内的各计算机和路由器本身的公网地址均可通过DHCP获得:路由器从ISP的DHCP服务器获得IP地址;而路由器自己作为该局域网的DHCP服务器,向网内的各台计算机分配IP地址。

NAT翻译表(NAT translation table)负责实现公网与私网地址的互相转换。当私网内的计算机向公网发送数据时,NAT路由器重写数据报的源端口号为一个唯一的号码(如果是第一次用到这个新端口,则向NAT翻译表添加新的表项),源IP也被替换为路由器对外的IP,再进行发送;而公网向私网发送数据时,NAT路由器根据数据报的目标端口号在翻译表中找出相应的计算机,重写目标IP地址和目标端口号后,将其发送给正确的主机。因为端口号的长度为16位,因此具有一个全球IP地址的NAT可以为一个局域网的超过6万台计算机同时提供NAT服务。如果路由器具有n个全球IP地址,专用网能容纳的计算机数量就达到原来的n倍。使用端口号的NAT也叫做网络地址与端口号翻译NAPT(Network Address and Port Translation,网络地址与端口号转换)。但在许多文献中并没有这样与不使用端口号的传统NAT区分,而是都使用NAT这个更加简洁的缩写词。

当然,NAT也不是没有缺点的。首先,端口号原本是用于区分一台计算机上的进程,但现在NAT机制将其用于区分一个局域网内的主机,这就可能导致局域网内的服务器出现问题。例如,P2P协议中的对等方在充当服务器时需要接受进入连接(incoming connection)。NAT穿透(NAT traversal)工具和通用即插即用(Universal Plug-and-Play,UPnP)等手段可以解决此问题。UPnP允许主机发现和配置邻近NAT。

架构纯粹主义者对NAT提出了反对:他们认为路由器作为三层设备,应当仅在网络层及以下处理分组。NAT违反了主机应当直接对话而不修改IP地址和端口号的原则。但无论他们喜欢与否,NAT已经成为了Internet的重要组件,也称中间件(middlebox)。中间件并不执行传统的数据报转发,而是执行诸如NAT、流量流的负载均衡、流量防火墙等功能。4.4节将学习通用转发:除了传统的路由转发外,还允许一些这样的中间盒功能,从而以通用、综合的方式完成转发。

防火墙(firewall)和侵入监测系统(intrusion detection system,IDS)是常用的网络防御手段。
防火墙可以安装在Internet与网管负责的局域网之间。许多路由器都具有防火墙功能。防火墙监测运输层段和数据报的报头,拒绝可疑的分组进入内网。防火墙可以粗暴地阻止全部ICMP(5.6节)回送请求包,防止攻击者对LAN进行传统的端口扫描;防火墙还能根据源地址、目标地址及端口号来过滤分组;也可以追踪TCP连接,仅允许指定程序的数据报进入。
IDS一般部署在网络边缘,进行“深度分组检查”(deep packet inspection,DPI),同时检验数据报的报头和数据段(含应用层数据)。IDS拥有数据库,库中记录了恶意攻击分组的签名。为了确保防御效果,此数据库必须及时更新。当分组通过IDS时,IDS尝试检验报头和负载数据的签名,并与数据库中的记录比对。如果找到符合的条目,则产生警告。而侵入阻止系统(intrusion prevention system,IPS)则在产生警告的基础上阻止恶意分组进入。
防火墙和IDS并不能防范全新的网络攻击,但至少可以对付已有攻击。

1990年代早期,IETF就已着手IPv4继任者的开发,以应对爆炸性增长的子网和IP结点数量。IPv6便是在这样的背景下诞生的。2011年2月,IANA分配了最后一个IPv4地址池给地区注册登记机构,ISP已经无法再申请到新的IPv4地址块。2019年11月26日,欧洲RIPE NCC终于耗尽了存储,全球IPv4地址耗尽——所有IPv4地址(近43亿个)已分配完毕。这意味着没有更多的IPv4地址可以分配给ISP和其它大型网络基础设施提供商。
ST-2协议原本可能作为IPv5,但此协议后来被放弃。我国在2014年至2015年也逐步停止了向新用户和应用分配IPv4地址,同时全面开始商用部署IPv6。
IPv6将PDU称为分组而非数据报。但为了方便,这里我们仍然使用数据报这一名词。

IPv6的主要改进包括:
·地址长度由32位增加到128位。理论上,可以为地球上的每一个沙粒分配一个唯一的IPv6地址。除了单播和多播地址,IPv6引入了任播地址,允许一个数据包发送至任意一组主机。例如,HTTP GET请求可以通过任播由距离最近的镜像站(mirror site)接收,并返回指定的文档作为响应。
·扩展的地址层次结构。IPv6的地址空间很大,因此允许使用多级的子网划分和地址分配。
·40字节报头。一些IPv4报头的字段是可选的,导致IPv4报头的长度不定;但IPv6的报头长度是固定的。固定长度的报头有利于让路由器更快地处理IPv6数据报。
·允许协议继续扩充。这一点很重要,因为技术总是在不断地发展(如网络硬件的更新),而新的应用也还会出现。但我们知道,IPv4的功能是固定不变的。
·支持即插即用(即自动配置)。因此IPv6不需要使用DHCP。
·IPv6首部改为8字节对齐(首部长度必须是8字节的整数倍)。原来的IPv4首部是4字节对齐。
·流标签(flow labeling)。IPv6对流的定义很复杂。简单来说,所谓“流”就是互联网络上从特定源点到特定终点(单播或多播)的一系列数据报(如实时音频或视频传输),而在这个“流”所经过的路径上的路由器都保证指明的服务质量。RFC 2460指出,这个字段允许“对发送方请求特殊处理的指定流的分组进行标签,例如非默认质量服务或实时服务”(Labeling of packets belonging to particular flows for which the sender requests special handling, such as a non-default quality of service or real-time service.)。例如,音视频传输通常被当作流来处理。另一方面,对于传统应用,比如文件传输或电子邮件,则不被视作流。高优先级用户(例如花钱购买了增值服务的用户)携带的流量也可能被当作流。显然,IPv6设计者预见到了区别对待不同数据的需求。
·增强的安全性。IPv6支持Internet协议安全(Internet Protocol Security,IPsec)。
·使用全新的协议处理邻接节点的交互性。IPv6的邻居发现协议(Neighbor Discovery Protocol,NDP)用更加有效的多播和单播的邻节点发现报文取代ARP(6.4节),ICMPv4(5.6节)路由发现和ICMPv4重定向报文。
·IPv6自动配置分为有状态(stateful)和无状态(stateless)两种。有状态情况下使用DHCPv6配置地址,无状态情况下主机自动配置链路本地地址(见后文)。

IPv6数据报报头的各个字段说明如下:
·版本(version)。此字段占4位。IPv4和IPv6数据报的此字段的值分别为4和6。如果该字段为4,但后续为IPv6数据报的格式,则此数据报无效。
·流量类型(traffic class)。8位。类似IPv4的服务类型(TOS)字段。该字段可用于指定流或应用的数据报的优先级。
·流标签(flow label)。20位。标记数据报属于哪些流。所有属于同一个流的数据报都具有同样的流标号。
·负载长度(payload length)。16位。一个IPv6数据报最多允许携带65535字节的数据。
·下一个报头(next header)。8位。指示此数据报将被交由哪个协议(如TCP或UDP)。IPv4的协议字段可取的各个值的意义在此字段中不变。
·跳数限制(hop limit)。8位。该字段的功能与IPv4报头的TTL字段是一样的。数据报的传输过程中,每经过一台路由器,该值就减1。此值为0时,数据报将被丢弃。
·源和目标地址(source and destination addresses)。每个128位,共256位。RFC 4291规定了IPv6地址的多种格式。
·数据。此为IPv6数据报的有效负载。当IPv6数据报到达目标主机后,携带的数据被取出,传递给指定的上层协议。

对比IPv4报头格式,我们发现下述字段在IPv6报头中消失了:
·报头长度。IPv6的报头一定是40字节。
·服务类型。流量类型和流标签可以等效实现区分不同上层服务的功能。
·总长度。改用了负载长度字段。
·标识符、标志位、片偏移。IPv6不再允许路由器进行分片,分片和重组分别交由源主机和目标主机完成。如果路由器收到了过大的IPv6数据报,则直接丢弃,并向发送方返回“Packet too big”ICMP错误报文。发送方可以重新以更小的数据报传输数据。分片和重组是非常消耗时间的。将此任务交给终端,可以大大加快网络核心的转发速率。
·首部检验和。运输层(TCP,UDP)和链路层(以太网)协议均可以提供校验和检错,因此IP设计者很可能认为此功能赘余,于是将其移除。在当今极其巨大的Internet流量规模之下,尽可能加快IP分组的处理成为首要的考虑因素。IPv4的TTL字段每经过一跳便会减1,于是每台路由器都要重新计算此IPv4数据报的校验和并重新填入头部,带来的负载也是很重的。
·选项。IPv4的数据报如果在报头中使用选项,那么沿着数据报传送的路径上的每一台路由器都必须对这些选项一一检查,这就降低了路由器处理数据报的速率。然而实际上很多选项在途中的路由器上是不需检查的(用不到这些选项的信息)。IPv6把原来IPv4报头中选项的功能都放在扩展报头中,并把扩展报头留给源点和终点的主机来处理,而数据报经过的路由器都不处理这些扩展报头(只有逐跳选项扩展报头例外),大大提高了路由器的处理效率。虽然选项不再作为报头内容,但可以由Next hdr(下一报头)字段指向选项参数。该字段不但可以指向TCP和UDP协议头,还可以指向IPv6扩展报头。注意:扩展报头是放在数据报的数据(有效载荷)部分的,插入在携带的数据之前,不属于IPv6数据报的报头。

RFC 2460中定义了以下六种扩展首部:
(1) 逐跳选项。当源端需要将信息传递给数据包经过的所有路由器时,使用逐跳选项。
(2) 路由选择。将IPv4选项中的严格源路由和松散源路由结合在一起。严格源路由选项规定IP数据报要经过路径上的每一个路由器,相邻路由器之间不得有中间路由器,并且所经过路由器的顺序不可更改。对于松散源路由,发送端指明了流量或者数据包必须经过的IP地址清单,但可以在需要时经过一些其它的地址。换句话说,不用严格限制数据包经过的确切地址,只要它经过的地址包含这些指定的地址就可以。
(3) 分片。源端使用路径MTU发现技术找到最小MTU,然后在必要时进行分片。
(4) 鉴别。验证报文发送者并验证其完整性。
(5) 封装安全有效载荷。提供保密性并防止窃听。
(6) 目的站选项。用于当源端需要令信息仅传递给目的端时,中间的路由器不允许读取这些信息。
每个扩展首部都由若干个字段组成,长度也各不同。但所有扩展首部的第一个字段都是8位的“下一个首部”字段,指出在该扩展首部后面的字段是什么。使用多个扩展首部时,应按以上的先后顺序出现。高层首部总是放在最后。

IPv6将实现IPv6的主机和路由器均称为结点。一个结点就可能有多个与链路相连的接口。IPv6地址是分配给结点上面的接口的。一个接口可以有多个单播地址,其中的任何一个地址都可以当作到达该结点的目的地址。

为了使得记法更简洁,IPv6采用冒号十六进制记法(colon hexadecimal notation,colon hex):它把每个16位的值用十六进制值表示,各值之间用冒号分隔。例如:
68E6:8C64:FFFF:FFFF:0:1180:960A:FFFF
在十六进制记法中,允许把数字前面的0省略。上面就把0000中的前三个0省略了。
冒号十六进制记法可以允许零压缩(zero compression),即一连串连续的零可以为一对冒号所取代。例如:
FF05:0:0:0:0:0:0:B3
可以简记为FF05::B3。
为了保证每个零压缩后的地址都唯一对应压缩前的地址,规定在任一地址中只能使用一次零压缩。该技术对已建议的分配策略特别有用,因为会有许多地址包含较长连续的零串。
冒号十六进制记法可结合使用点分十进制记法的后缀。我们下面会看到这种结合在IPv4向IPv6的转换阶段特别有用。例如,下面的串是一个合法的冒号十六进制记法:
0:0:0:0:0:0:128.10.2.1
在这种记法中,虽然为冒号所分隔的每个值是两个字节(16位)的量,但每个点分十进制部分的值则指明一个字节(8位)的值。再使用零压缩即可得出:
::128.10.2.1
CIDR的斜线表示法仍然可用。例如,60位的前缀12AB 0000 0000 CD3可记为下述三种方式的任意一种:
12AB:0000:0000:CD30:0000:0000:0000:0000/60
12AB::CD30:0:0:0:0/60
12AB:0:0:CD30::/60

RFC 4291规定,IPv6地址分为5类:

下面简单解释这几种地址:
·未指明地址。这是16字节的全0地址,可缩写为两个冒号“::”。这个地址不能用作目标地址,而只能为某台主机当作源地址使用,条件是这台主机还没有配置到一个标准的IP地址。这类地址仅此一个。
·环回地址。IPv6的环回地址固定为0000:0000:0000:0000:0000:0000:0000:0001,缩写::1。它的作用和IPv4环回地址一样。
·多播地址。功能和IPv4的一样。
·链路本地单播地址(link-local unicast address)。这是计算机网络中一类特殊的地址,仅供在网段或广播域(见6.4节)中的主机相互通信使用。这类主机通常不需要外部互联网服务,仅有主机间相互通讯的需求。位于同一子网的未连接到Internet的主机可以使用这种本地地址进行通信,但无法和Internet上的其它主机通信。IPv4的本地链路单播地址是169.254.0.0/16。如果通过DHCP获取IP地址失败,则Windows为主机分配此地址。
·全球单播地址。IPv6的这一类单播地址是使用得最多的一类。曾提出过多种方案来进一步划分这128位的单播地址。根据2006年发布的草案标准RFC 4291的建议,IPv6单播地址的划分方法非常灵活。例如,可把128位都作为一个结点的地址。也可用n位作为子网前缀,用剩下的(128-n)位作为接口标识符(相当于IPv4的主机号)。当然也可以划分为三级:用m位作为全球路由选择前缀,用n比特作为子网前缀,而用剩下的(128-m-n)比特作为接口标识符。

为了使主机逐步过渡到IPv6,现在的许多计算机中都具有双协议栈。双协议栈主机(或路由器)同时具有IPv4和IPv6地址,既能和IPv6的系统通信,又能和IPv4的系统通信。双协议栈主机使用DNS查询时可以判定目标主机使用何种IP地址,进而决定自己应当使用哪种IP地址。若DNS返回的是IPv4地址,双协议栈的源主机就使用IPv4地址。但当DNS返回的是IPv6地址,源主机就使用IPv6地址。

为了向后兼容IPv4网络,隧道(tunneling)技术被引入了。隧道技术是一种数据包封装技术,它是将原始IP包(其报头包含原始发送者和最终目的地)封装在另一个数据包(称为封装的IP包)的数据部分进行传输。
使用隧道的原因通常是:在与使用的某些协议不兼容的网络上传输数据,或在不安全网络上提供一条安全路径。隧道协议通常(但并非总是)在一个比负载的协议还高的层级,或同一层。
隧道在这里指IPv4路由器和IPv6路由器之间的部分。隧道发送端的IPv6结点将整份IPv6数据报都放入IPv4数据报的数据段中。这个IPv4数据报将沿着隧道到达接收端的IPv6结点。隧道内的全部IPv4结点按照既有方式处理该IPv4数据报即可,它们并不知道数据段传输的其实是一份完整的IPv6数据报。接收端的IPv6结点探测到发送的IPv4数据报的数据段为完整的IPv6数据报(IPv4数据报报头的协议字段值为41)后,将其提取,并在IPv6网络中继续传输。但是,IPv6数据报的一些字段,比如流标签,是无法恢复的。
隧道背后的基本思想也在其它地方有着广泛应用。

美国国家标准技术研究所(NIST)的报告显示,2015年左右已有超过1 / 3的美国政府二级域名启用了IPv6。而2015年左右的Google的报告显示,仅8 %的客户端通过IPv6访问Google。不过,许多研究证实,升级到IPv6的进程正在加快。

在中国,自2017年中央印发《推进互联网协议第六版(IPv6)规模部署行动计划》以来,IPv6规模部署工作逐渐有序地铺展开。“推进IPv6规模部署专家委员会”于2020年8月发布了《中国IPv6发展状况白皮书》。
我国IPv6活跃用户数逐步上升,截至2020年7月,我国IPv6活跃用户数为3.62亿,占比达40.01%。三大基础电信企业加快改造进度,为全国LTE(见第7章)用户和固定宽带接入用户分配IPv6地址。
2020年7月,三大基础电信企业LTE网络已分配IPv6地址用户数为12.17亿;三大基础电信企业固定宽带接入网络已分配IPv6地址用户数达2.26亿。
截至2020年7月,我国已申请IPv6地址资源总量达到50209块(/32),位居世界第二;我国已在互联网中通告的AS数量为609个。在已通告的AS中,支持IPv6的AS数量为325个,占比53.4%。
网络就绪度反映我国网络基础设施的IPv6支持就绪程度。截至2020年7月:
中国电信、中国移动和中国联通均完成了全国30个省,333个地级市的LTE网络IPv6改造和30个省的城域网网络IPv6改造;同时,其骨干网设备已全部支持IPv6,全面开启IPv6承载服务。
13个骨干网直联点已经全部实现了IPv6互联互通,中国电信、中国移动、中国联通、中国广电、教育网和科研网累计开通IPv6网间带宽6.39 Tbps;骨干直联点IPv6流量与已开通节点带宽比例小于3%,占比较低,空闲资源较多,利用率不高。
三大基础电信企业已开通IPv6国际出入口带宽90 Gbps。目前国际出入口IPv6总流量超过已开通总带宽的90%,需加快扩容升级IPv6国际出入口带宽。
应用可用度反映我国IPv6网站和移动互联网应用部署的情况。截至2020年7月,国内用户量排名前100位的商业网站及应用,可通过IPv6访问;全国91家省部级政府网站中,主页可通过IPv6访问的网站共有88家,占比为96.7%。全国96家中央企业网站中主页可通过IPv6访问的网站有81个,占比为84.38%;13家中央重点新闻媒体网站中主页可通过IPv6访问的网站共有6家,占比为46.15%;教育部公布的137所“双一流”高校网站中,主页可通过IPv6访问的网站共有73家,占比为53.3%。
4.4 广义转发和SDN
当今已经出现了非常多的执行三层功能的中间件。NAT会重写报头的IP和端口;防火墙会过滤恶意流量或将流量重定向以进行其它处理;负载均衡器将特定的服务请求转发到相应的服务器。
此外,交换机和路由器都有自己的硬件、软件和管理界面,这令网络操作员很头疼。软件定义网络(software defined network,SDN)正尝试提出一种统一的方法,以一种现代、简洁和综合方式,提供多种网络层功能及特定的链路层功能。

路由器的转发一般仅考虑目标地址和目标端口号;而广义转发也称通用转发(generalized forwarding),则基于更抽象、更基本的“匹配-动作”(match-plus-action)思想。
OpenFlow是一个受到高度认可的协议,是匹配-动作、控制器和SDN等概念的先驱。
匹配-动作转发表的每一项称作流表(flow table),包括:
·进入的分组将要匹配的一组报头字段值。在基于目的地的转发中,硬件匹配如果在TCAM内存中执行,可以获得最快的速度。实际上,出于性能与成本的考虑,流表往往被拆成多张表。但为了讲解方便,我们主要举单张流表的例子。
·一组当分组与流表项匹配时更新的计数器。这些计数器可以为每个表项已匹配的分组数量、距离该表项上次更新的时间等数据计数。
·一组当分组与流表项匹配时的动作。这些动作可以是将分组转发到特定的输出端口、丢弃分组、产生分组的副本并转发给多个输出端口、重写头部字段等。

下图展示了11个可以同时由OpenFlow 1.0匹配的分组头字段。回忆1.5节,到达分组交换机的链路层帧的数据部分为网络层数据报;数据报的数据部分一般为运输层(四层)段。OpenFlow允许一次匹配三个层的协议头,而不遵循1.5节开始学习的分层原则。链路层我们还没有学,这里只简单介绍涉及到的内容:源和目标MAC地址是链路层地址,与帧的发送与接收接口有关;基于以太网地址而非IP地址进行转发,我们发现启用了OpenFlow的设备可以作为路由器转发数据报,也可以作为交换机转发帧。以太网类型(Eth type)字段与上层协议(例如IP)有关。OpenFlow 1.0可以匹配这12个值,但最近版本的OpenFlow可以匹配的值已经多得多。
进入端口(ingress port)指的是收到分组的输入端口。

流表的项可以具有通配符,也可以具有优先级。如果一个分组与多个表项匹配,则选择优先级最高的项。
并不是IP数据报报头的所有字段都能参与匹配,例如TTL字段。因为考虑太多的细节会严重增加功能的复杂度。

流表中的常见动作有:
·转发。接收到一个分组后,可以直接转发到一个物理输出端口,也可以复制若干份,多播到多个端口。分组也可以被封装并送入此设备的远程控制器。控制器可以对包进行处理(如:增加流表项,将包返回给设备并按照新的流表转发),也可以不处理。
·丢弃。一个不具有任何操作的流表项意味着要丢弃匹配的分组。
·修改字段。将包转发到正确的输出端口之前,修改首部的某些字段。
4.A IP多播
在互联网上进行多播就叫做IP多播。IP多播已成为互联网的一个热门课题。这是由于有许多的应用需要由一个源点发送到许多个终点,即一对多的通信。例如,实时信息的交付(如新闻、股市行情等),软件更新,交互式会议和多媒体通信等。随着互联网的用户数目的急剧增加,以及多媒体通信的大规模铺开,有更多的业务需要多播来支持。
与单播相比,在一对多的通信中,多播可大大节约网络资源。例如,学校演播室要向位于教学楼的全部n台计算机播送视频节目。如果使用单播方式,则需发送n个单播,即每个视频分组都要发送n个副本。但如果将这些计算机都全部划入同一个多播组,则视频服务器仅需发送1次多播数据报,而由路由器不断复制分组并转发。当分组到达目标局域网时,由于局域网具有硬件多播功能(见第六章),因此不需要复制分组,在局域网上的多播组成员都能收到这个视频分组。
当多播组的主机数很大时,采用多播能明显减轻网络中各种资源的消耗。互联网范围的多播要靠路由器来实现,这些路由器必须增加能够识别多播数据报的软件。能够运行多播协议的路由器称为多播路由器(multicast router)。多播路由器当然也可以转发普通的单播IP数据报。
为了适应交互式音频和视频信息的多播,从1992年起,在互联网上开始试验虚拟的多播主干网(multicast backbone,MBONE)。MBONE可把分组传播给地点分散但属于一个组的许多台主机。现在多播主干网已经有了相当大的规模。

多播数据报报头的目标地址不可能写入全部需要接收多播数据报的主机的地址。多播数据报的目标地址写入的是多播组的标识符,然后设法让加入到这个多播组的主机的IP地址与多播组的标识符关联起来。在使用IPv4时,多播组标识符就是D类IP地址,其前4位是1110,因此D类地址的范围是224.0.0.0到239.255.255.255。每一个D类地址标志一个多播组。这样,D类地址共可标志228个多播组。同一时间可以有超过2.6亿个IPv4多播组在互联网上运行。
多播地址只能用于目的地址,而不能用于源地址。此外,对多播数据报不产生ICMP(见5.6节)差错报文。因此,若在PING命令后面键入多播地址,将永远不会收到响应。

IP多播可以分为两种。一种是只在本局域网上进行硬件多播,另一种则是在互联网的范围进行多播。前一种虽然比较简单,但很重要,因为现在大部分主机都是通过局域网接入到互联网的。在互联网上进行多播的最后阶段,还是要把多播数据报在局域网上用硬件多播交付多播组的所有成员。

多播数据报也是“尽最大努力交付”,不保证一定能够交付多播组内的所有成员。因此,多播数据报和一般的IP数据报的区别就是它使用D类IP地址作为目的地址,并且报头中的协议字段值是2,表明使用Internet组管理协议(Internet group management protocol,IGMP)。
IGMP是用于获取多播组的成员信息的。IGMP不对Internet内的所有多播组成员进行管理,既不知道IP多播组包含的成员数,也不知道这些成员都分布在哪些网络上。IGMP让连接在本地局域网上的多播路由器知道本局域网上是否有主机(严格讲,是主机上的某个进程)参加或退出了某个多播组。
IGMPv3(RFC 3376)是IGMP的最新版本。RFC 3376也定义了IGMP报文格式,这里从略。RFC 2236(IGMPv2)已经被宣布为陈旧的。
IGMP使用IP数据报传递其报文(即IGMP报文加上IP首部构成IP数据报),但它也向IP提供服务。因此,可以不把IGMP看成是一个单独的协议,而是属于整个网际协议IP的一个组成部分。

IGMP的工作可分为两个阶段。
第一阶段:当某台主机加入新的多播组时,该主机应向多播组的多播地址发送一份IGMP报文,声明自己要成为该组的成员。本地的多播路由器收到IGMP报文后,还要利用多播路由选择协议(见下文)把这种组成员关系转发给互联网上的其它多播路由器。也就是说,IGMP使多播路由器知道多播组成员信息。
第二阶段:组成员关系是动态的。本地多播路由器要周期性地探询本地局域网上的主机,以便知道这些主机是否还继续是组的成员。只要有一台主机对某个组响应,那么多播路由器就认为这个组是活跃的。但一个组在经过几次的探询后仍然没有一台主机响应,多播路由器就认为本网络上的主机已经都离开了这个组,因此也就不再把这个组的成员关系转发给其它的多播路由器。

IGMP设计得很仔细,避免了多播控制信息给网络增加大量的开销。一些具体措施包括:
(1)在主机和多播路由器之间的所有通信都是使用IP多播。只要有可能,携带IGMP报文的数据报都用硬件多播来传送。因此在支持硬件多播的网络上,没有参加IP多播的主机不会收到IGMP报文。
(2)多播路由器在探询组成员关系时,只需要对所有的组发送一个请求信息的询问报文,而不需要对每一个组发送一个询问报文(虽然也允许对一个特定组发送询问报文)。默认的询问速率是每125秒发送一次,通信量并不太大。
(3)当同一个网络上连接有几台多播路由器时,它们能够迅速有效地选择其中一台来询问主机的成员关系。因此,网络上多个多播路由器并不会引起IGMP通信量的增大。
(4)在IGMP的询问报文中有一个数值N,代表最长响应时间(默认值10秒)。当收到询问时,主机在0到N之间随机选择发送响应所需经过的时延。因此,若一台主机同时参加了几个多播组,则主机对每一个多播组选择不同的随机数。对应于最小时延的响应最先发送。
(5)同一个组内的每一台主机都要监听响应,只要有本组的其它主机发送了响应,自己就可以不再发送响应了。这样就抑制了不必要的通信量。

多播路由器并不需要保留组成员关系的准确记录,因为向局域网上的组成员转发数据报是使用硬件多播。多播路由器只需要知道网络上是否至少还有一台主机是本组成员即可。实际上,每一个组只需有一台主机对询问报文发送响应。
多播数据报的发送者和接收者都不知道(也无法找出)一个多播组的成员有多少,以及这些成员是哪些主机。互联网中的路由器和主机都不知道哪个应用进程将要向哪个多播组发送多播数据报,因为任何应用进程都可以在任何时候向任何一个多播组发送多播数据报,而这个应用进程并不需要加入这个多播组。

仅有IGMP是不能完成多播任务的。连接在局域网上的多播路由器还必须和互联网上的其它多播路由器协同工作,以便把多播数据报用最小代价传送给所有的组成员。这就需要使用多播路由协议。虽然在TCP/IP中IP多播协议已成为建议标准,但多播路由选择协议(用来在多播路由器之间传播路由信息)则尚未标准化。
多播转发必须动态地适应多播组成员的变化(这时网络拓扑可以未发生变化)。请注意,单播路由选择通常是在网络拓扑发生变化时才需要更新路由。多播路由器在转发多播数据报时,不能仅仅根据多播数据报中的目的地址,还需要考虑源地址,再综合选择一条路由。多播数据报所经过的许多网络,也不一定非要有多播组成员。多播数据报可以由没有加入多播组的主机发出(分发多播数据报的服务器可以不是多播组的成员),也可以通过没有组成员接入的网络。

在多播过程中一个多播组中的成员是动态变化的。例如在收听网上某个广播节目时,随时会有主机加入或离开这个多播组。多播路由实际上就是要构建以源主机为根节点的多播转发树。在多播转发树上,每一台多播路由器向树的叶节点方向转发收到的多播数据报,但在多播转发树上的路由器不会收到重复的多播数据报(即多播数据报不应在互联网中绕圈子)。不难看出,不同的多播组对应不同的多播转发树。同一个多播组,对不同的源点也会有不同的多播转发树。

当前已有多种实用的多播路由选择协议,它们在转发多播数据报时主要使用了以下的三种方法:
(1)洪泛与剪除。这种方法适合于较小的多播组,而所有的组成员接入的局域网也是相邻接的。一开始,路由器转发多播数据报使用洪泛(广播)的方法。为了避免兜圈子,需要采用反向路径广播(Reverse Path Broadcasting,RPB)策略。RPB的要点是:每一台路由器收到一份多播数据报时,先检查数据报是否是从源点经最短路径传送来的。进行这种检查很容易,只要从本路由器寻找到源点的最短路径上(之所以叫做反向路径,因为在计算最短路径时是把源点当作终点)的第一台路由器是否就是刚才把多播数据报送来的路由器。若是,就向所有其它方向转发刚才收到的多播数据报(但进入的方向除外),否则就丢弃而不转发。如果本路由器有好几台相邻路由器都处在到源点的最短路径上(也就是说,存在几条同样长度的最短路径),那么只能选择一条最短路径,选择的准则就是看这几条最短路径中的相邻路由器谁的IP地址最小。最后可以得出用来转发多播数据报的多播转发树(在下图中用粗线表示),以后就按这棵多播转发树来转发多播数据报。这样就避免了多播数据报兜圈子,同时每一个路由器也不会接收重复的多播数据报。
如果在多播转发树上的某个路由器发现它的下游树枝(即叶节点方向)已没有该多播组的成员,就应把它和下游的树枝一起剪除。当某个树枝有新增加的组成员时,可以再接入到多播转发树上。

(2)隧道(tunneling)。隧道技术适用于多播组的位置在地理上很分散的情况。当多播网络之间存在不支持多播的网络时,路由器就对多播数据报进行再次封装,即再加上普通数据报报头,使之成为向单一目的站发送的单播数据报,再进行发送。单播数据报离开隧道以后,由隧道另一端的路由器剥去报头,又恢复成原来的数据报,继续向目标站点转发。使用隧道技术传送数据报又叫做IP中的IP(IP-in-IP)。
(3)基于核心的发现技术。这种方法对于多播组的大小在较大范围内变化时都适合。这种方法是对每一个多播组G指定一台核心路由器,给出它的IP单播地址。核心路由器按照前面讲过的方法创建出对应于多播组G的转发树。如果有一台路由器R1向核心路由器发送数据报,那么途中经过的每一台路由器都要检查其内容。当数据报到达参加了多播组G的路由器R2时,R2就处理这个数据报。如果R1发出的是一份多播数据报,其目的地址是G的组地址,R2就向多播组G的成员转发这个多播数据报。如果R1发出的数据报是一份请求加入多播组G的数据报,R2就把这个信息添加到它的路由中,并用隧道技术向R1转发每一份多播数据报的一个副本。这样,参加到多播组G的路由器就从核心向外增多了,扩大了多播转发树的覆盖范围。

目前还没有在整个互联网范围使用的多播路由协议。下面是一些建议使用的多播路由协议(在第五章,我们会稍微详细地学习一些路由协议):
距离向量多播路由选择协议DVMRP(Distance Vector Multicast Routing Protocol)是在互联网上使用的第一个多播路由选择协议[RFC 1075]。由于在UNIX系统中实现RIP(见5.3节)的程序叫做routed,所以在routed的前面加表示多播的字母m,叫做mrouted,它使用DVMRP在路由器之间传播路由信息。
基于核心的转发树CBT(Core Based Tree)[RFC 2189,2201]。这个协议使用核心路由器作为转发树的根节点。一个大的自治系统AS(见5.3节)可划分为几个区域,每一个区域选择一个核心路由器(也叫做中心路由器center router,或汇聚点路由器rendezvous router)。
开放最短通路优先的多播扩展MOSPF(Multicast extensions to OSPF)[RF C1585]。这个协议是单播路由选择协议OSPF(见5.3节)的扩充,使用于一个机构内。MOSPF使用多播链路状态路由选择创建出基于源点的多播转发树。
协议无关多播-稀疏方式PIM-SM(Protocol Independent Multicast-Sparse Mode)[RFC 4601]。这个协议使用和CBT同样的方法构成多播转发树。采用“协议无关”这个名词是强调:虽然在建立多播转发树时是使用单播数据报来和远程路由器联系的,但这并不要求使用特定的单播路由选择协议。这个协议适用于组成员的分布非常分散的情况。
协议无关多播-密集方式PIM-DM(Protocol Independent Multicast-Dense Mode)[RFC 3973]。这个协议适用于组成员的分布非常集中的情况,例如组成员都在一个机构之内。PIM-DM不使用核心路由器,而是使用洪泛方式转发数据报。
4.B 虚拟专用网络
一些很大的机构的部门分布的范围很广(例如在世界各地),这些部门经常要交换信息。这可以有两种方法:(1)租用电信公司的通信线路为本机构专用。这种方法简单方便,但线路租金太高,一般难于承受。(2)利用公用的互联网作为本机构各专用网之间的通信载体,这样的专用网又称为虚拟专用网(Virtual Private Network,VPN)。
之所以称为“专用网”是因为这种网络被本机构的主机用于机构内部的通信,而不是和网络外非本机构的主机通信。如果专用网不同网点之间的通信必须经过公用的互联网,但又有保密的要求,那么所有通过互联网传送的数据都必须加密。 “虚拟”表示“好像是”,但实际上并不是,因为VPN并没有真正使用通信专线,而只是在效果上和真正的专用网一样。一个机构要构建自己的VPN就必须为它的每一个场所购买专门的硬件和软件并进行配置,使每一个场所的VPN系统都知道其它场所的地址。

假设两个场所有自己的专用网A(10.1.0.0)、B(10.2.0.0),再加上公用的互联网,就构成了一个VPN。每一个场所至少要有一台路由器(的一个接口)具有合法的全球IP地址。
每一个场所A或B内部的通信都不经过互联网。但如果场所A的主机X要和场所B的主机Y通信,就需要经过专用网和公网之间的路由器R1、R2。路由器R1负责在A端将数据报加密,加上新的报头(这个过程执行了NAT)后封装成外部数据报发送到互联网。在互联网上传递的数据报,其报头的目标地址为场所B与互联网之间的路由器R2的一个接口的地址。目标路由器R2收到数据报后取出数据部分并解密,将恢复出来的原有数据报交付给指定的主机Y。可见,虽然X向Y发送的数据报是通过了公用的互联网,但在效果上就好像是在本部门的专用网上传送一样。如果主机Y要向X发送数据报,那么所进行的步骤也是类似的。
数据报从R1传送到R2可能要经过互联网中的很多个网络和路由器。但从逻辑上看,在R1到R2之间好像是一条直通的点对点链路。我们说,在R1到R2之间有一条隧道。
在本例中,场所A、B和互联网构成的VPN也称内联网(intranet或intranet VPN)。有时一个机构的VPN需要有某些外部机构(通常就是合作伙伴)参加进来。这样的VPN就称为外联网(extranet或extranet VPN)。

VPN还有一种类型:远程接入VPN(remote access VPN)。有的公司并没有分布在不同场所的部门,但却有很多流动员工在外地工作。公司需要和他们保持联系,有时还需进行音视频会议。远程接入VPN可以满足这种需求。在外地工作的员工接入互联网,而员工的PC中的VPN软件可以在员工的个人电脑和公司的主机之间建立VPN隧道,因而外地员工与公司通信的内容也是保密的,员工们感到好像就是使用公司内部的本地网络。在大学外连接学校内网时,也常用这种方法。

猜你喜欢

转载自blog.csdn.net/COFACTOR/article/details/111740529
今日推荐