您好,欢迎访问三七文档
ICMP协议详解一.什么是ICMP协议ICMP全称InternetControlMessageProtocol(网际控制信息协议)提起ICMP,一些人可能会感到陌生,实际上,ICMP与我们息息相关。在网络体系结构的各层次中,都需要控制,而不同的层次有不同的分工和控制内容,IP层的控制功能是最复杂的,主要负责差错控制、拥塞控制等,任何控制都是建立在信息的基础之上的,在基于IP数据报的网络体系中,网关必须自己处理数据报的传输工作,而IP协议自身没有内在机制来获取差错信息并处理。为了处理这些错误,TCP/IP设计了ICMP协议,当某个网关发现传输错误时,立即向信源主机发送ICMP报文,报告出错信息,让信源主机采取相应处理措施,它是一种差错和控制报文协议,不仅用于传输差错报文,还传输控制报文。二.ICMP报文格式ICMP所有报文的前4个字节都是一样的,但是剩下的其他字节则互不相同。。类型字段可以有15个不同的值,以描述特定类型的ICMP报文。某些ICMP报文还使用代码字段的值来进一步描述不同的条件。表示ICMP头部的数据结构typedefstructicmp_hdr{unsignedcharicmp_type;//消息类型unsignedcharicmp_code;//代码unsignedshorticmp_checksum;//校验和unsignedshorticmp_id;//ID号unsignedshorticmp_sequence;//序列号unsignedlongicmp_timestamp;//时间戳}ICMP_HDR,*PICMP_HDR;三ICMP报文的类型各种类型的ICMP报文如图所示,不同类型由报文中的类型字段和代码字段来共同决定。图中的最后两列表明ICMP报文是一份查询报文还是一份差错报文。因为对ICMP差错报文有时需要作特殊处理,因此我们需要对它们进行区分。例如,在对ICMP差错报文进行响应时,永远不会生成另一份ICMP差错报文(如果没有这个限制规则,可能会遇到一个差错产生另一个差错的情况,而差错再产生差错,这样会无休止地循环下去)。当发送一份ICMP差错报文时,报文始终包含IP的首部和产生ICMP差错报文的IP数据报的前8个字节。这样,接收ICMP差错报文的模块就会把它与某个特定的协议(根据IP数据报首部中的协议字段来判断)和用户进程(根据包含在IP数据报前8个字节中的TCP或UDP报文首部中的TCP或UDP端口号来判断)联系起来。6.5节将举例来说明一点。下面各种情况都不会导致产生ICMP差错报文:1)ICMP差错报文(但是,ICMP查询报文可能会产生ICMP差错报文)。2)目的地址是广播地址或多播地址的IP数据报。3)作为链路层广播的数据报。4)不是IP分片的第一片。5)源地址不是单个主机的数据报。这就是说,源地址不能为零地址、环回地址、广播地址或多播地址。这些规则是为了防止过去允许ICMP差错报文对广播分组响应所带来的广播风暴。下面是几种常见的ICMP报文:1.响应请求我们日常使用最多的ping,就是响应请求(Type=8)和应答(Type=0),一台主机向一个节点发送一个Type=8的ICMP报文,如果途中没有异常(例如被路由器丢弃、目标不回应ICMP或传输失败),则目标返回Type=0的ICMP报文,说明这台主机存在,更详细的tracert通过计算ICMP报文通过的节点来确定主机与目标之间的网络距离。2.目标不可到达、源抑制和超时报文这三种报文的格式是一样的,目标不可到达报文(Type=3)在路由器或主机不能传递数据报时使用,例如我们要连接对方一个不存在的系统端口(端口号小于1024)时,将返回Type=3、Code=3的ICMP报文,它要告诉我们:“嘿,别连接了,我不在家的!”,常见的不可到达类型还有网络不可到达(Code=0)、主机不可到达(Code=1)、协议不可到达(Code=2)等。源抑制则充当一个控制流量的角色,它通知主机减少数据报流量,由于ICMP没有恢复传输的报文,所以只要停止该报文,主机就会逐渐恢复传输速率。最后,无连接方式网络的问题就是数据报会丢失,或者长时间在网络游荡而找不到目标,或者拥塞导致主机在规定时间内无法重组数据报分段,这时就要触发ICMP超时报文的产生。超时报文的代码域有两种取值:Code=0表示传输超时,Code=1表示重组分段超时。3.时间戳时间戳请求报文(Type=13)和时间戳应答报文(Type=14)用于测试两台主机之间数据报来回一次的传输时间。传输时,主机填充原始时间戳,接收方收到请求后填充接收时间戳后以Type=14的报文格式返回,发送方计算这个时间差。一些系统不响应这种报文。四.ICMP协议的运用1ICMP地址掩码请求与应答ICMP地址掩码请求用于无盘系统在引导过程中获取自己的子网掩码。系统广播它的ICMP请求报文(这一过程与无盘系统在引导过程中用RARP获取IP地址是类似的)。无盘系统获取子网掩码的另一个方法是BOOTP协议。如图ICMP报文中的标识符和序列号字段由发送端任意选择设定,这些值在应答中将被返回。这样,发送端就可以把应答与请求进行匹配。我们可以写一个简单的程序(取名为icmpaddrmask),它发送一份ICMP地址掩码请求报文,然后打印出所有的应答。由于一般是把请求报文发往广播地址,因此这里我们也这样做。目的地址(140.252.13.63)是子网140.252.13.32的广播地址。sun%icmpaddrmask140.252.13.63receivedmask=ffffffe0,from140.252.13.来3自3本机receivedmask=ffffffe0,from140.252.13.来3自5bsdireceivedmask=ffff0000,from140.252.13.来3自4svr4在输出中我们首先注意到的是,从svr4返回的子网掩码是错的。显然,尽管svr4接口已经设置了正确的子网掩码,但是SVR4还是返回了一个普通的B类地址掩码,就好像子网并不存在一样。svr4%ifconfigemd0emd0:flags=23UP,BROADCAST,NOTRAILERSinet140.252.13.34netmaskffffffe0broadcast140.252.13.63SVR4处理ICMP地址掩码请求过程存在差错。我们用tcpdump命令来查看主机bsdi上的情况,输出如图6-5所示。我们用-e选项来查看硬件地址。发到广播地址的ICMP地址掩码请求注意,尽管在线路上什么也看不见,但是发送主机sun也能接收到ICMP应答(带有上面“来自本机”的输出行)。这是广播的一般特性:发送主机也能通过某种内部环回机制收到一份广播报文拷贝。由于术语“广播”的定义是指局域网上的所有主机,因此它必须包括发送主机在内。接下来,bsdi广播应答,而svr4却只把应答传给请求主机。通常,应答地址必须是单播地址,除非请求端的源IP地址是0.0.0.0。本例不属于这种情况,因此,把应答发送到广播地址是BSD/386的一个内部差错。RFC规定,除非系统是地址掩码的授权代理,否则它不能发送地址掩码应答(为了成为授权代理,它必须进行特殊配置,以发送这些应答。参见附录E)。但是,正如我们从本例中看到的那样,大多数主机在收到请求时都发送一个应答,甚至有一些主机还发送差错的应答。最后一点可以通过下面的例子来说明。我们向本机IP地址和环回地址分别发送地址掩码请求:sun%icmpaddrmasksunreceivedmask=ff000000,from140.252.13.33sun%icmpaddrmasklocalhostreceivedmask=ff000000,from127.0.0.1上述两种情况下返回的地址掩码对应的都是环回地址,即A类地址127.0.0.1。发送给本机IP地址的数据报(140.252.12.33)实际上是送到环回接口。ICMP地址掩码应答必须是收到请求接口的子网掩码(这是因为多接口主机每个接口有不同的子网掩码),因此两种情况下地址掩码请求都来自于环回接口。2ICMP时间戳请求与应答ICMP时间戳请求允许系统向另一个系统查询当前的时间。返回的建议值是自午夜开始计算的毫秒数,协调的统一时间(CoordinatedUniversalTime,UTC)(早期的参考手册认为UTC是格林尼治时间)。这种ICMP报文的好处是它提供了毫秒级的分辨率,而利用其他方法从别的主机获取的时间(如某些Unix系统提供的rdate命令)只能提供秒级的分辨率。由于返回的时间是从午夜开始计算的,因此调用者必须通过其他方法获知当时的日期,这是它的一个缺陷。ICMP时间戳请求和应答报文格式如图所示。请求端填写发起时间戳,然后发送报文。应答系统收到请求报文时填写接收时间戳,在发送应答时填写发送时间戳。但是,实际上,大多数的实现把后面两个字段都设成相同的值(提供三个字段的原因是可以让发送方分别计算发送请求的时间和发送应答的时间)。
本文标题:ICMP协议详解
链接地址:https://www.777doc.com/doc-2876744 .html