📄 以太地址转换协议.htm
字号:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
<!-- saved from url=(0077)http://www.longen.org/E-K/detaile~k/EthernetAddressResolveGeneralProtocol.htm -->
<HTML><HEAD><TITLE>新建网页 0</TITLE>
<META http-equiv=Content-Language content=zh-cn>
<META content="MSHTML 6.00.2800.1400" name=GENERATOR>
<META content=FrontPage.Editor.Document name=ProgId>
<META http-equiv=Content-Type content="text/html; charset=gb2312"></HEAD>
<BODY>
<TABLE id=AutoNumber1 style="BORDER-COLLAPSE: collapse" borderColor=#111111
cellSpacing=0 cellPadding=0 width="100%" border=0>
<TBODY>
<TR>
<TD width="100%">
<H4>一个以太地址转换协议</H4>
<P>摘要</P>
<P>实现一个协议P,要使S主机通过P协议的路由机器发现目标机T并最终将数据传送到目标机。这一切要求通过以太网进行,为了完成传送必须知道以太网上的以太网地址才行,但是P协议中的地址可能并不与以太网地址相兼容,因此必须有一种机制使P协议中的地址A变成以太网地址。本文并不针对某一种协议,而是一个通用的方法。这里使用的数字遵守以太网标准,即高位优先。这与一些机器的地址标准不同,如PDP-11s和VAX机。因此我们必须注意以下要描述的操作码域(ar$op)。</P>
<P>问题:</P>
<P>------------</P>
<P>在网络的各层中,有不同的协议可供使用,而以太网标准使得所有的数据可被封装在一个包中,再加上一个标记就能够在同一个电缆上传送。但这也带来了问题,因为以太网使用的是48位的地址,而其它协议中使用的地址却不一定与它长度一致。因此我们要求某一个协议X能够动态地在<protocol,
address>和48位以太网地址之前进行转换。</P>
<P>提议:</P>
<P>-----------</P>
<P>现在以太网已经成为一种广泛使用的标准,在如果进行这种地址转换的问题上有两种做法:(1)每个厂商自己设置标准,进行自己的地址转换,或(2)大家遵守一个共同的标准,以便得软件在转移到另外的系统时不需要进行变化。本文即希望提出这样一个标准。</P>
<P>定义:</P>
<P>------------</P>
<P>我们定义下面的一些数值用于填充现有的以太包头:</P>
<P>ether_type$XEROX_PUP,<BR>ether_type$DOD_INTERNET,<BR>ether_type$CHAOS,
<BR>下面这个域是新加入的域:<BR>ether_type$ADDRESS_RESOLUTION.
<BR>我们也定义下面的一些值:<BR>ares_op$REQUEST (= 1, 高位优先)<BR>ares_op$REPLY (= 2),
<BR>ares_hrd$Ethernet (= 1).</P>
<P>包格式:</P>
<P>--------------</P>
<P>为了将<protocol,
address>映射到48位以太地址,我们需要一个可以包括地址解析协议的包格式。这个包的格式如下:</P>
<P>Ethernet传输层(可以不让用户访问这些域)<BR>48.bit: 目的以太地址<BR>48.bit: 源以太地址<BR>16.bit:
Protocol type = ether_type$ADDRESS_RESOLUTION<BR>Ethernet包数据:<BR>16.bit:
(ar$hrd) 硬件地址<BR>16.bit: (ar$pro)
协议地址空间,对于以太网硬件来说,这来自ether_typ$<protocol>的值<BR>8.bit: (ar$hln)
每个硬件地址的字节长度<BR>8.bit: (ar$pln) 每个协议地址的字节长度<BR>16.bit: (ar$op) opcode
(ares_op$REQUEST | ares_op$REPLY)<BR>nbytes: (ar$sha)
发送者硬件地址,n来自ar$hln的值<BR>mbytes: (ar$spa) 发送者协议地址,m来自ar$pln的值<BR>nbytes:
(ar$tha) 目标地址(可能未知)<BR>mbytes: (ar$tpa) 目标机协议地址</P>
<P>产生包:</P>
<P>------------------</P>
<P>在网络层传送数据包的时候需要知道如何通过路由机制将数据传送到目的机,因此我们必须知道如果将当前包传送到下一个接收单位去。在以太网的情况下,我们必须通过一个地址转换模块将<protocol
type, target protocol
address>转换到以太网地址。这个模块基本是试图在一个表中寻找这个这个对应关系。如果找到了,那万事大吉;如果没有找到,模块会通知用户重新传送这个包,自己已经将这个包抛弃(因为此模块假定更高的网络层会重新传送这个包),同时模块会产生一个以太包,这个包中有一个类型域ther_type$ADDRESS_RESOLUTION。地址解析模块要设置</P>
<P>ar$hrd域=ares_hrd$Ethernet<BR>r$pro=需要被解析的协议类型<BR>ar$hln=6(以太网地址的字节数,48位/8位=6)<BR>ar$pln=协议地址长度<BR>ar$op=ares_op$REQUEST<BR>ar$sha=自己的以太地址<BR>ar$spa=自己的协议地址<BR>ar$tpa=机器试图访问的协议地址<BR>模块不设置ar$tha,因此此值是要求的值,当然为了实现方便可以将它设置为硬件的广播地址。</P>
<P>接收包</P>
<P>-----------------</P>
<P>当收到地址解析包时,接收方的解析模块利用下面的算法确定需要的地址,最后一个ELSE代表处理结束,要抛弃这个包。</P>
<P>?Do I have the hardware type in ar$hrd?<BR>Yes: (almost
definitely)<BR>[可以检查硬件长度ar$hln]<BR>?Do I speak the protocol in
ar$pro?<BR>Yes:<BR>[可以检查协议长度ar$pln]<BR> Merge_flag :=
false<BR> If the pair <protocol type, sender protocol address>
is already in my translation table, update the sender hardware address
field of the entry with the new information in the packet and set
Merge_flag to true. <BR>[因为接收到的数据包中已经包括发送方的协议地址和硬件地址,这可是宝贵的信息呀]<BR>
?Am I the target protocol address?<BR> Yes:<BR> If
Merge_flag is false, add the triplet <protocol type,sender protocol
address, sender hardware address> to the translation table.<BR>
?Is the opcode ares_op$REQUEST? (NOW look at the
opcode!!)<BR> Yes:<BR>
Swap hardware and protocol fields, putting the local hardware and protocol
addresses in the sender fields. Set the ar$op field to ares_op$REPLY Send
the packet to the (new) target hardware address on the same hardware on
which the request was received.</P>
<P>这里要注意的是在进行操作以前<protocol type, sender protocol address, sender
hardware
address>已经被加入到包中,因为接收方可以利用这个数据包中已经有的协议地址和硬件地址,说不定以后要通信的时候这个可以用得上呢。一般地说,ar$hrd和ar$hln域也可用于非以太网的情况。</P>
<P>为什么这么处理?</P>
<P>-------------------------</P>
<P>定时进行广播不是不行,假设有100个工作站,每个工作站每10分钟广播一次消息,整个网络每6秒有一个这样的数据,也不是不行,可这样的数据有什么用呢?本文中的协议只在需要的时候进行广播,或者只在启动的时候进行一次广播。本文的协议只考虑用一个包进行解析,没有考虑到一个包进行多个地址的解析,一个为了方便,另一个考虑到需要一个包解析多个地址的情况不多,这样会造成浪费。本文中的格式考虑到了应答包中的信息可以再次被使用,因为应答包和请示包的长度和格式一样,因此程序实现起来比较方便。ares_hrd$Ethernet
=
1这个值即是为了以后扩展而使用的。如果以后再有协议需要使用此协议,则可以将这个值设置为其它值。对于以太网,ar$pro指定的是协议类型,它和ar$op一起共用1个域,这使得可指定的协议数减少,而且使得网络监视变得比较复杂。我们希望不要看到以后出现32768个协议,但我们不能做这个假设。理论上,ar$hln和ar$pln是多余的,因为这两个长度可以通过硬件类型(在ar$hrd中)和协议类型(在ar$pro中)获得,包括它们只是为了进行一致性校验和网络监视。其中opcode表示这个包是请求还是对原先请求的应答,16位是多了一点,但这个标记还是需要的。其它的一些位是需要的。包中没有填充位,可以将它看做一个流。</P>
<P>网络监视:</P>
<P>---------------------------------</P>
<P>这个协议可以让下层了解上层协议的一些运转情况。我们可以假设有一个监视机收到一个解析包,它将<protocol type, sender
protocol address, sender hardware
address>输入一个表。监视机可以通过ar$hln和ar$pln确定硬件地址长度和协议地址长度。如果opcode=REPLY,此包被抛弃,如果opcode=REQUEST而且目标地址与本机的目标地址一致,监视机返回REPLY。监视机也可能会发出自己的REQUEST,在这种情况下,两台监视机可能会产生一个REQUEST的循环,这一点要特别注意。</P>
<P>例子:</P>
<P>-----------</P>
<P>有两台机器共在一个以太网中,它们的以太网地址分别是:EA(X)和EA(Y)。网络地址分别是:IPA(X)和IPA(Y),我们设置网络的以太类型为ET(IP),机器X刚刚启动,迟早它要与Y机进行通信,它知道Y机的协议地址IPA(Y),现在X机需要通过<ET(IP),IPA(Y)>知道Y机的以太网地址。下面即是它发出的数据包:</P>
<P>(ar$hrd) = ares_hrd$Ethernet<BR>(ar$pro) = ET(IP)<BR>(ar$hln) =
length(EA(X))<BR>(ar$pln) = length(IPA(X))<BR>(ar$op) =
ares_op$REQUEST<BR>(ar$sha) = EA(X)<BR>(ar$spa) = IPA(X)<BR>(ar$tha) =
任意值<BR>(ar$tpa) = IPA(Y)</P>
<P>此包被广播。</P>
<P>Y机接收到这个包,发现包中的协议地址与自己的协议地址一致,它将X机的协议地址和以太地址先保存在自己的表中。因此此包表示的是请求,因此Y机将自己的硬件写入到包中,将包设置为REPLY,此时Y已经知道如何将此包返回给X,而X还不知道Y的信息。当X收这个包的时候,它已经从<ET(IP),
IPA(Y)>求得了EA(Y),因为是应答包,因此X机将此包抛弃。下回它再要与Y机进行通信的时候就不用再广播了,因为已经知道Y机的以太地址了。同样Y机要与X机进行通信时也不需要进行广播,因此它已经从X机的请示包中知道了X机的以太地址。</P>
<P>其它问题:</P>
<P>---------------</P>
<P>在这一节里我们要了解如何使对应表中的表项使效。如何进行失效已超出本文的范围,在这里仅做以介绍。如果一个机器移动,或因为某种原因改变了协议地址与物理地址的对应关系,这时就需要一种失效算法。我们可以假设利用包中的以太地址进行传输时如果传输延时超过某一个定值,我们就认为这个表项已经失效。我们可以要求改变了的主机在启动时重新广播自己的协议地址和硬件地址,也可以利用一个守护进程定时向目标机发出数据包以检查表中的表项是不是已经不存在。如果因为机器已经更换了网卡,换了以太网地址,这时手工进行设置也是办法。</P></TD></TR></TBODY></TABLE></BODY></HTML>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -