TCP/IP详解 卷1:协议 学习笔记 第十六章 BOOTP:引导程序协议

一个无盘系统在不知道自身IP地址情况下,进行系统引导时能通过RARP协议获取它的IP地址,使用RARP会有两个问题:(1)IP地址是返回的唯一结果;(2)RARP使用链路层广播,RARP请求不会被路由器转发,每个实际网络必须设置一个RARP服务器。

BOOTP使用UDP,通常需要与TFTP协同工作。
TCP/IP详解 卷1:协议 学习笔记 第十六章 BOOTP:引导程序协议_第1张图片
TCP/IP详解 卷1:协议 学习笔记 第十六章 BOOTP:引导程序协议_第2张图片
操作码字段为1时表示请求,为2时表示应答。

硬件类型字段为1时表示10Mb/s的以太网,此字段和ARP请求或应答中同名字段表示的含义相同。

对于以太网,硬件地址长度字段为6。

跳数字段由客户设为0,但也能被代理服务器设置。

事务标识字段是由客户设置并由服务器返回的32bit整数,客户用它对请求和应答进程匹配,对于每个请求,客户应将该字段设为一个随机数。

秒数字段设置为一个时间值,备用服务器在等待此时间值后才会响应客户的请求,这意味着主服务器没有启动。

客户IP地址字段当客户知道自己的IP时,客户将其写入此字段,否则将此字段置0,当置0时,服务器会将客户的IP写入你的IP地址字段。

服务器IP地址字段由服务器填写。

如果使用了某个代理服务器,则该代理服务器填写网关IP地址字段。

客户必须设置它的客户硬件地址字段,尽管这个值与以太网数据帧头中的值相同,因为一个进程通过查看UDP数据报确定以太网帧首部中的硬件地址字段通常是很困难的(或是不可能的)。

服务器主机名字段是一个空值终止的串,由服务器填写,此外,服务器还在引导文件名字段填入用于系统引导的文件名及其所在位置的路径全名。

特定厂商区域字段用于对BOOTP进行扩展。

当一个客户使用BOOTP(操作码为1)进行系统引导时,引导请求通常是采用链路层广播,IP首部中的目的IP地址为255.255.255.255(受限的广播),源IP通常是0.0.0.0(在进行系统自引导时,此IP是一个有效IP地址),因为此时客户还不知道它的IP。

BOOTP有两个熟知端口,BOOTP服务器为67,客户为68,这意味这BOOTP客户不会选择未用的临时端口,选择两个端口的原因是服务器的应答可以进行广播(但通常不广播),如果应答进行了广播,而客户又选择临时端口,那么这些广播也能被其他主机中碰巧使用相同临时端口的应用进程收到,因此,采用临时随机端口对广播来说是一个不好的选择。

如果BOOTP客户也使用67作为熟知端口,则对于每个BOOTP服务器的应答,网络内所有BOOTP服务器都会被唤醒,之后通过检查操作码会发现这是一个应答而非请求,就不用做任何处理,因此BOOTP客户选择一个与BOOTP服务器不同的熟知端口就可以避免以上过程。

如果多个客户同时进行系统引导,并且服务器广播所有应答,这样每个客户都会收到其他客户的应答,此时客户可通过BOOTP首部中的事务标识字段或检查客户的硬件地址进行区分。

用BOOTP引导一个X终端,其中客户名为proteus,服务器名为mercury:
TCP/IP详解 卷1:协议 学习笔记 第十六章 BOOTP:引导程序协议_第3张图片
第一行中,客户的请求来自0.0.0.0:68,发送的目的站是255.255.255.255:67,客户已经填写的字段是秒数(客户通常将秒数设为100秒)和以太网地址,跳数字段和事务标识没有显示出来,因为它们均为0,事务标识0表示客户忽略这个字段,因为如果打算对返回响应进行验证,它将把这个字段设置为一个随机数。

第二行是服务器的应答,服务器填写的字段是你的IP地址(tcpdump将其显示为名字proteus),服务器的IP地址(显示为名字mercury),网关的IP地址(显示为名字mercury)和引导文件名。

收到BOOTP应答后,客户立即发送了一个ARP请求来了解网络中其他主机是否已经占有了此IP地址,跟在who-has后的proteus对应目的IP,第三行和第四行中发送者IP为0.0.0.0,而第五行中发送者变成了proteus,这是一个没有意义的ARP请求。

第六行显示客户等待0.5s后广播了另一个BOOTP请求,这个请求与第一行唯一不同的是它将自己的IP写入IP首部字段中。之后第七行它收到了同一个服务器的相同应答。

第八行显示,客户在等待2秒后,又广播了一个BOOTP请求,之后在第九行收到了相同服务器的相同应答。

第十行显示,客户等待2秒后,向它的服务器mercury发送一个ARP请求,之后收到了第十一行的ARP应答。

在第十二行,客户收到ARP应答后,发送了一个TFTP读请求,请求读取它的引导文件,之后TFTP服务器和客户传送了2464个TFTP数据分组和确认,传送的数据量为512*2463+224=1261280字节。在传送数据的过程中,由于客户一直使用的都是TFTP服务器的知名端口69,因此tcpdump能用TFTP解释每个分组。由于TFTP服务器作为一个多用户系统,且使用TFTP的知名端口,因此通常TFTP客户不能使用这个端口,但由于系统正处于被引导过程,无法提供一个TFTP服务器,因此允许客户使用TFTP知名端口,这也暗示mercury上的TFTP服务器不关心客户的端口号是什么。

上图中没看到客户广播一个ICMP地址掩码请求来获取它的子网掩码,可认为客户所在网络的子网掩码在返回的BOOTP应答的特定厂商信息字段中,尽管tcpdump没有显示出来,RFC推荐使用BOOTP而非ICMP获取它的子网掩码。

X终端系统引导后,还需使用TFTP传送终端的字体文件、某些DNS名字服务器,然后进行X协议的初始化。

BOOTP客户通常固化在无盘系统的只读存储器中。

BOOTP服务器从它的熟知端口67读取UDP数据报,它不同于RARP服务器(必须读取帧类型字段为RARP请求的以太网帧)。由于BOOTP使用UDP,因此应用很难获取帧头中的客户硬件地址字段,所以BOOTP通过将客户的硬件地址放入BOOTP分组中去,使得服务器很容易获取客户的硬件地址。

对于BOOTP服务器,它发送一个UDP响应给客户时,如果服务器知道客户的IP(可能通过读取服务器上的配置文件),此时服务器可能向客户的IP发送一个ARP请求,但客户不会响应这个ARP请求,因为客户还不知道自己的IP。解决方法有两个:(1)此方法通常被UNIX服务器使用,即服务器发送一个ioctl请求给内核,将该客户的硬件地址和IP地址设置到ARP高速缓存中(与arp -s类似);(2)服务器广播这个BOOTP应答,最好当服务器不能设置ARP缓存时使用(因为通常期望网络广播越少越好),通常只有超级用户权限才能在ARP高速缓存中设置条目。

绝大多数路由器都支持BOOTP协议,使得BOOTP能够由路由器转发。

当路由器(也称BOOTP中继代理)在熟知端口67接收到BOOTP请求时,中继代理将它的IP(收到BOOTP请求的接口的IP地址)填入收到的BOOTP请求中的网关IP地址字段,然后将该请求发送到真正的BOOTP服务器,中继代理还将跳数字段值加1,这是为了防止请求无限地在网络内转发,RFC 951认为跳数达到3就可以丢弃该请求。BOOTP服务器收到这个请求后,产生BOOTP应答,这个应答发送回中继代理而非请求的客户(服务器通过网关IP地址字段不为空就知道了请求是否经过了转发),中继代理收到后,将它发给请求的客户。

64字节的特定厂商信息字段是服务器返回给客户的可选信息,如果有信息要提供,这个区域前4字节被设置为IP地址99.130.83.99,表示该区域包含信息,这称作magic cookie。之后跟一个条目表,其中的每个条目的开始是1字节的标志字段,条目的格式:
TCP/IP详解 卷1:协议 学习笔记 第十六章 BOOTP:引导程序协议_第4张图片
标志为0的条目作为填充字节(为使后面的条目有更好的字节边界)。

标志为255的条目表示结尾条目,结尾条目后剩余的字节都应设为255。

标志为1的条目是子网掩码条目,它的len字段总是4字节。

标志为2的条目是时间偏移条目,它的len字段总是4字节,它显示的是协调世界时(UTC,linux时间戳是从UTC 1970-01-01 00:00:00以来经过的秒数),它是一个二进制补码表示的值,负的偏移量表示一个本初子午线以东的位置,正的偏移量表示一个本初子午线以西的位置。

标志为3的条目是网关条目,它的len字段是4的倍数,它的值是一个或多个供客户使用的客户子网内的网关(路由器)IP地址,第一个是首选的网关。

厂商说明区域大小被限制为64字节,这对某些应用是个约束,一个新的协议称为动态主机配置协议DHCP(Dynamic Host Configuration Protocol)已经出现,它不是代替BOOTP的,DHCP将这个区域长度扩展到312字节。

假设路由器也转发RARP请求,路由器将RARP请求转发到路由器连接的其他网络中,这样路由器还要转发RARP应答,由于RARP只使用了链路层地址,路由器不会知道没有连接到路由器上的网络中的主机的链路层地址。

你可能感兴趣的:(TCP/IP详解,卷1:协议,tcp/ip,学习,服务器)