说一下UDP
(
首先是伪首部:
伪首部是计算检验和时临时添加在UDP用户数据报前面
伪首部(pseudo header),通常有TCP伪首部和UDP伪首部。在UDP/TCP伪首部中,包含32位源IP地址,32位目的IP地址,8位填充0,8位协议,16位TCP/UDP长度。通过伪首部的校验,UDP可以确定该数据报是不是发给本机的,通过首部协议字段,UDP可以确认有没有误传。
伪首部并非TCP&UDP数据报中实际的有效成分。伪首部是一个虚拟的数据结构,其中的信息是从数据报所在IP分组头的分组头中提取的,既不向下传送也不向上递交,而仅仅是为计算校验和。
这样的校验和,既校验了TCP&UDP用户数据的源 端口号和目的端口号以及TCP&UDP用户数据报的数据部分,又检验了IP数据报的源IP地址和目的地址。
伪报头保证TCP&UDP数据单元到达正确的目的地址。因此,伪报头中包含IP地址并且作为计算校验和需要考虑的一部分。
最终目的端根据伪报头和数据单元计算 校验和以验证通信数据在传输过程中没有改变而且到达了正确的目的地址。
伪首部,更确切的说是包含的—个96位的伪首标,是个理论上的值,只是理论上它位于TCP&UDP首标的前面。这个伪首标包含了源地址、目的地址、协议和TCP&UDP长度等字段,这使得TCP&UDP能够防止出现路由选择错误的数据段 。这些信息由网际协议 (IP)承载,通过TCP&UDP网络接口,在IP上运行的TCP&UDP调用参数或者结果中传递。
源端口:16 bit (2 个字节),是一个大于 1023 的 16 位数字,由基于 UDP 应用程序的用户进程随机选择。
目的端口:16 bit (2 个字节),指明接收者所用的端口号,一般由应用程序来指定。
数据长度:16 bit (2 个字节),标明 UDP 头部和 UDP 数据的总字节长度。
校验和字段:16 bit (2 个字节),用来对 UDP 头部和 UDP 数据进行校验。与 TCP 不同的是,此字段是可选项,而 TCP 数据段中必须包含校验和字段。
首部长度总长为8个字节
数据:不定长度,为上层协议封装好的数据。
首先是TCP
我们先看一下TCP帧的格式
这里有两种,第一种是保留有6位,6字节,第二种是保留四位,然后标志位增添了CWR和ECE
1-1.源始端口16位,范围当然是0-65535啦。
1-2.目的端口,同上。
2-1.数据序号32位,TCP为发送的每个字节都编一个号码,这里存储当前数据包数据第一个字节的序号。
3-1.确认序号32位,为了安全,TCP告诉接受者希望他下次接到数据包的第一个字节的序号。
4-1.数据偏移/首部长度4位,类似IP,表明数据距包头有多少个32位。
4-2.保留6位,未使用,应置零。
4-3.紧急比特URG—当URG=1时,表明紧急指针字段有效。它告诉系统此报文段中有紧急数据,应尽快传送(相当于高优先级的数据)。
4-3.确认比特ACK—只有当ACK=1时确认号字段才有效。当ACK=0时,确认号无效。参考TCP三次握手
4-4.复位比特RST(Reset) —当RST=1时,表明TCP连接中出现严重差错(如由于主机崩溃或其他原因),必须释放连接,然后再重新建立运输连接。参考TCP三次握手
4-5.同步比特SYN—同步比特SYN置为1,就表示这是一个连接请求或连接接受报文。参考TCP三次握手
4-6.终止比特FIN(FINal)—用来释放一个连接。当FIN=1时,表明此报文段的发送端的数据已发送完毕,并要求释放运输连接。
4-7.窗口字段16位,窗口字段用来控制对方发送的数据量,单位为字节。TCP连接的一端根据设置的缓存空间大小确定自己的接收窗口大小,然后通知对方以确定对方的发送窗口的上限。
5-1.包校验和16位,包括首部和数据这两部分。在计算检验和时,要在TCP报文段的前面加上12字节的伪首部。
5-2.紧急指针16位,紧急指针指出在本报文段中的紧急数据的最后一个字节的序号。
6-1.可选选项24位,类似IP,是可选选项。
6-2.填充8位,使选项凑足32位。
7-1.用户数据……
可以看出,每个IP包至少要20字节的头部长度,这些与下载内容无关,加上目前多数传输,包括http协议(就是IE直接下载),都是基于TCP协议的,所以IP包裹还要从用户数据中扣除20字节的TCP包头,这里已经是40字节,加上其他程序的连接,状态确认等等包裹,因而算出来要比理论值要小。
TCP的源端口、目的端口、以及IP层的源IP地址、目的IP地址四元组唯一的标识了一个TCP连接
TCP各字段释义:
TCP源端口(Source Port):16位的源端口其中包含发送方应用程序对应的端口。源端口和源IP地址标示报文发送端的地址。
TCP目的端口(Destination port):16位的目的端口域定义传输的目的。这个端口指明报文接收计算机上的应用程序地址接口。
TCP序列号(SequenceNumber):32位的序列号标识了TCP报文中第一个byte在对应方向的传输中对应的字节序号。当SYN出现,SN=ISN(随机值)单位是byte。比如发送端发送的一个TCP包净荷(不包含TCP头)为12byte,SN为5,则发送端接着发送的下一个数据包的时候,SN应该设置为5+12=17。通过序列号,TCP接收端可以识别出重复接收到的TCP包,从而丢弃重复包,同时对于乱序数据包也可以依靠系列号进行重排序,进而对高层提供有序的数据流。另外如果接收的包中包含SYN或FIN标志位,逻辑上也占用1个byte,应答号需加1。
TCP应答号(Acknowledgment Number简称ACK Number):32位的ACK Number标识了报文发送端期望接收的字节序列。如果设置了ACK控制位,这个值表示一个准备接收的包的序列码,注意是准备接收的包,比如当前接收端接收到一个净荷为12byte的数据包,SN为5,则会回复一个确认收到的数据包,如果这个数据包之前的数据也都已经收到了,这个数据包中的ACK Number则设置为12+5=17,表示之前的数据都已经收到了,准备接受SN=17的数据包。
注:关于TCP序列号和应答号,也可以参考文章:http://blog.csdn.net/a19881029/article/details/38091243/
头长(Header Length):4位包括TCP头大小,指示TCP头的长度,即数据从何处开始。
保留(Reserved):4位值域,这些位必须是0。为了将来定义新的用途所保留,其中RFC3540将Reserved字段中的最后一位定义为Nonce标志。后续拥塞控制部分的讲解我们会简单介绍Nonce标志位。
标志(Code Bits):8位标志位,下面介绍。
窗口大小(Window Size):16位,该值指示了从Ack Number开始还愿意接收多少byte的数据量,也即用来表示当前接收端的接收窗还有多少剩余空间,用于TCP的流量控制。
校验位(Checksum):16位TCP头。发送端基于数据内容计算一个数值,接收端要与发送端数值结果完全一样,才能证明数据的有效性。接收端checksum校验失败的时候会直接丢掉这个数据包。CheckSum是根据伪头+TCP头+TCP数据三部分进行计算的。
优先指针(紧急,Urgent Pointer):16位,指向后面是优先数据的字节,在URG标志设置了时才有效。如果URG标志没有被设置,紧急域作为填充。
选项(Option):长度不定,但长度必须以是32bits的整数倍。常见的选项包括MSS、SACK、Timestamp等等。
八位标志位分别介绍如下:
CWR(Congestion Window Reduce):拥塞窗口减少标志set by sender,用来表明它接收到了设置ECE标志的TCP包。并且sender 在收到消息之后已经通过降低发送窗口的大小来降低发送速率。
ECE(ECN Echo):ECN响应标志被用来在TCP3次握手时表明一个TCP端是具备ECN功能的。在数据传输过程中也用来表明接收到的TCP包的IP头部的ECN被设置为11。注:IP头部的ECN被设置为11表明网络线路拥堵。
注:关于CWR和ECE标记为详细信息可参考:http://www.cnblogs.com/hadis-yuki/p/5467787.html
URG(Urgent):该标志位置位表示紧急(The urgent pointer) 标志有效。该标志位目前已经很少使用参考后面流量控制和窗口管理部分的介绍。
ACK:取值1代表Acknowledgment Number字段有效,这是一个确认的TCP包,取值0则不是确认包。后续文章介绍中当ACK标志位有效的时候我们称呼这个包为ACK包,使用大写的ACK称呼。
PSH(Push):该标志置位时,一般是表示发送端缓存中已经没有待发送的数据,接收端不将该数据进行队列处理,而是尽可能快将数据转由应用处理。在处理 telnet 或 rlogin 等交互模式的连接时,该标志总是置位的。
所谓Push操作就是指在数据包到达接收端以后,立即传送给应用程序,而不是在缓冲区中排队;
RST(Reset):用于reset相应的TCP连接。通常在发生异常或者错误的时候会触发复位TCP连接。
SYN:同步序列编号(Synchronize Sequence Numbers)有效。该标志仅在三次握手建立TCP连接时有效。
FIN(Finish):No more data from sender。当FIN标志有效的时候我们称呼这个包为FIN包。
总结
TCP有20个字节的固定首部,因此TCP首部最小长度是20个字节。
IP数据报的最大长度=2^16-1=65535(字节)
TCP报文段的数据部分=IP数据报的最大长度-IP数据报的首部-TCP报文段的首部=65535-20-20=65495(字节)