TCP/IP协议总结(一)-TCP首部格式和TCP建立连接和释放连接

平时我们谈到TCP/IP协议时总会自然的想到三次握手、四次挥手、面向字节流和可靠传输等等。但是我们要知道TCP/IP协议不仅仅是一个简单的协议,而是一个TCP/IP协议族,里面包括TCP、UDP、IP和ARP等等许多协议。但是这里我们主要详细介绍传输控制协议TCP。

首先,在TCP/IP协议族中进行了分层(流水线工作,专一迅速而高效),由上到下分为以下四层:
这里写图片描述
应用层:包含HTTP(超文传输协议)、FTP(文件传输协议)、Telnet运程登陆、SMTP和SNMP等等协议。
传输层:TCP(传输控制协议)和UDP(用户数据报协议)。
网络层:处理分组在网络中的活动。IP协议(网络协议)、ICMP协议(Internet互联网控制报文协议),以及IGMP协议(Internet组管理协议)。
链路层:以太网协议、设备驱动程序和接口卡等等功能。
这里写图片描述
一个基本的通信过程各个分层主要负责的功能如下图:
这里写图片描述

TCP是TCP/IP协议族中最复杂的一个协议,具有以下特点:
1)TCP是面向连接的运输协议。意思就是使用TCP之前,必须先建立连接,使用完后,必须释放已经建立的TCP链接。
2)每一条TCP连接只能有两个端点,每一次TCP连接必须是点到点的(一对一)。
3)TCP提供可靠交付服务。保证数据的误差错、不丢失、不重复、按顺序到达。
4)TCP提供全双工通信。通信双方随时都可以向对方发送数据,两端都有自己的接收缓冲区和发送缓冲区。
5)面向字节流。虽然TCP和用用程序的交互是一次一个数据块(大小不等)但是TCP把应用程序交下来的数据看成一连串的无结构的字节流。

在上面的特点中,可靠传输是其最重要的一个特点。我们知道TCP发送报文段是交给TP层传送的。但是IP层只是尽最大努力服务,并不保证每一个报文段都到达,那么TCP只有自己采取一系列的措施才能保证传输的可靠性。比如说以字节为单位的滑动窗口,超时重传,当网络出现拥塞时有拥塞控制的方法。

下面我们详细的介绍TCP

一、TCP报文段的首部格式
TCP报文段前20个字节是固定的,后面的4n个字节是根据需要而增加的。
这里写图片描述
首部固定部分各个字段含义如下:
(1)源端口和目的端口:各占两个字节,分别写入源端口和目的端口。TCP的分用功能也是通过端口实现的。
(2)序号:4个字节32位,序号的范围是[0, 2^32 - 1],共2^32(4294967296)个序号。序号到2^32时,下一个序号又回到0。因为TCP传输是面向字节流的,每一个报文段的每个自己都按顺序编号。要传输的整个字节流的首序号必须在连接建立时设置。字节流按顺序传输,首部的序号段是本报文段所发送第一个字节的序号。由本报文段最后一个字节的序号可以得到下一个报文段要发送的报文段的首个字节序列号。
(3)确认号:和序列号一样也是4个字节32位。是期望收到对方下一个报文段的第一个数据字节的序号。接收方可以根据发送方发过来的字段序号和数据长度来确定给发送方回复的确认号。确认号 = 字段值号 + 数据长度。
(4)数据偏移(4位):指出TCP报文段的数据起始处距离TCP报文段的起始处距离。实际上也就是TCP报文段的头部长度。
(5)保留(6位):保留今后使用,目前为0.
(6)紧急(URG):当URG=1时,表示紧急指针有效。告诉系统此报文段含有紧急数据。
(7)确认(ACK):当ACK=1时,确认号才有效。在建立连接后所有的报文段ACK都要设置为1。
(8)推送(PSH):当PSH=1时,表示此报文段尽快的交给接受应用进程,不再等到缓冲区填满在向上交付。为了满足一端希望键入一个命令后立即受到对方的恢复。
(9)复位(RST):当RST=1时,表示TCP连接出现了严重错误,必须释放连接。还可以用来拒绝一个非法的报文段或打开一个连接。
(10)同步(SYN):在建立连接时用来同步的序号。SYN=1,ACK=0时,表明这是一个请求连接报文段。对方同意连接,则在相应的报文段中SYN=1,ACK=1.
(11)终止(FIN):FIN=1用来释放一个连接。
(12)窗口:2个字节,窗口值(接收方)[0, 2^16-1],接收方使用窗口值来设置发送方发送窗口大小的设置。(窗口值经常动态变化)。
(13)检验和:2个字节
(14)紧急指针:2个字节,紧急指针只有在URG=1时才有意义,指出本报文段紧急数据的字节数,也就是紧急数据末尾在报文段中的位置,窗口为0也可以发送紧急数据。
(16)选项:长度可变。没有使用选项时,TCP首部的长度为20字节。
最初TCP只规定了最大报文段长度MSS(数据字段的的大长度)。到了现在,随着网络的发展,增加了选择确认(SACK)、窗口扩大选项(3字节)、时间戳(10字节)包含时间戳值字段(4字节)和时间戳回送回答字段(4字节)。

上面我们看到了TCP头报文段的首部格式,下来我们先来看看TCP的建立连接(三次握手)和关闭连接(四次挥手)
先来看建立连接,在建立连接过程中要解决以下三个问题:
(1)双方要让对方确知自己的存在。
(2)双方要在建立连接的过程中商定一些些参数,比如说最大窗口值,是否使用窗口扩大选项和时间戳等等。
(3)可以对运输实体资源(缓存大小,连接表中的项目等)进行分配。
这里写图片描述

如上图,在客户端主动connect发起连接之前,客户端是处于CLOSED状态,服务端在开启listen之前也是处于CLOSED状态。
在CLOSED状态时服务端进程先创建传输控制块(TCB),准备接收客户进程的连接请求。然后后就进入LISTEN。
客户端进程也要首先创建传输控制块(TCB),然后想服务端发出连接请求报文段,这时TCP首部中的SYN=1,同时选择一个初始序号seq=x。TCP客户端进入STN_SENT(同步已发送)。
服务端accept到客户端的连接请求时,如果同意连接,向客户端发送确认。确认报文段中SYN和ACK都置为1,确认号ack=x+1,同时也发出一个自己的初始序号seq=y。TCP服务端进入SYN_RCVD(同步收到)。
客户端在收到服务端的确认后,还要向服务端发出确认(connect返回)。该确认报文段ACK=1,确认号seq=y+1,自己的序号seq=x+1。(TCP标准规定ACK报文段可以携带数据,但如果不带数据则不消耗序号),发出后客户端进入ESTABLISHED(建立连接)。
服务端收到(accept接受)确认后也进入ESTABLISHED状态,进行数据的传输。
以连接建立上过程就被称为三次握手。
客户端调用connect将激发TCP的三次握手,仅在连接建立成功或者出错时才返回,上面介绍了建立成功的情况,下面列出了出错返回可能有的几种情况:
(1)客户端发送的建立连接的SYN报文丢失或者服务器回复的ACK报文丢失。客户端因为没有收到服务器的回复,会等待6s再发一次,若无响应则等待24s再发一次,总共等75s还未收到响应就返回本错误。
(2)服务器回复的TCP报文中复位标志RST置位1。表示服务器主机没有在指定的端口上监听或接受该连接或服务器程序根本没有运行。
(3)客户端发送的SYN报文不可达。IP数据报中有一个生存时间(TTL)的标志,它每进过一个路由器都会减1,当它减到0时还没到达目的地,会发送一个ICMP错误。然后客户端会和第一种情况一样每隔一段时间重发一次。

常见问题:可以把TCP连接时的三次握手换成两次握手吗?
当然是不可以的,主要是防止客户端已经失效的连接请求突然又传到了服务端。
所谓“已经失效的请求报文段”是这样产生的。假如客户端发出的第一个连接请求报文段并没有丢失,而是在某个网络结点长时间的滞留了,以致延误到连接释放以后的某个时间才到达服务器。也就是说这是一个早已失效的报文段。但服务器端收到此失效的连接请求报文段后,就误认为是客户端再次发出的一个新的连接请求。于是就向客户端发出确认报文段,同意建立连接。假设不采用“三次握手”,那么只要服务器端发出确认,新的连接就建立了。由于现在客户端并没有发出建立连接的请求,因此不会理会服务器端的确认。经过三次握手,客户端和服务器都有应有答可以确保TCP正确连接。
这里写图片描述
看完TCP连接建立下来我们来看TCP连接释放。
观察上图,TCP连接释放还是比较复杂的。首先客户端的应用进程先向其TCP发送(close)连接释放报文段,并停止发送数据,主动关闭TCP来接。客户端发送的连接释放报文段首部的终止控制位FIN置为1,期序号seq=u(前面传送过的数据最后一个字节序号加1)。然后客户端进入FIN-WAIT-1(终止等待1)状态。(TCP标准规定,FIN报文段即使不传送数据也要消耗一个序号)
服务端收到发来的连接释放报文段后立即发出确认,确认号seq=u+1,而这个报文段自己的序号为v,等于服务端前面传送的数据最后一个序号加1。服务端就进入CLOSED-WAIT(关闭等待)状态。然后服务端通知高层应用进程,客户端到服务端的连接就释放,这时TCP处于半关闭状态,因为服务端到客户端的连接还没有释放。
客户端收到发来的确认后,就进入FIN-WAIT2(终止等待2)状态,继续等待服务端发来的报文段。
若服务端没有向客户端发的数据了,其应用进程就通知TCP释放连接。这时服务端发出的报文段FIN必须置为1。现在假定服务端的序号为w(半关闭状态服务端还可能发送一些数据)。但服务端还要重复发送上次发送的确认号ack=u+1。下来服务端就进入LAST-ACK(最后确认)状态,等待客户端确认。
客户端收到发来的释放报文段后,必须发送确认。在确认报文段中ACK=1,确认号ack=w+1,自己的序号seq=u+1(前面发送的FIN报文段消耗一个序号)。然后客户端进入TIME-WAIT(时间等待)状态。注意,现在的TCP连接还没有释放,必须经过时间等待器设置的时间2MSL(最长报文寿命,RFC建议MSL=2分钟)后,客户端才进入CLOSED状态。下来才可以新建立一个连接。当客户端撤销TCB后,结束这次TCP连接。
服务端收到确认后,就进入CLOSED状态。同样服务端撤销TCB,结束这次TCP连接。
客户端为什么在TIME-WAIT状态后还要等待2MSL的时间呢?
第一,保证客户端发的确认报文段一定要到达服务端。因为这个ACK报文段有可能在网络中丢失,或者拥塞等等情况,如果服务端按时没有收到确认的话,将会重新发送终止报文段,客户端重新收到之后,重启2MSL计时器。等待2MSL就是为了防止这种意外的发生。
第二,为了防止本次连接中的“已失效的请求报文段”出现在本次连接中。等待的2MSL确保本次连接中产生的所有报文段都从网络之中消失。下一个连接不会受到旧的报文段。
终之一句话 ,所有的设计都是为了确保TCP可靠传输。
除了时间等待计时器外,TCP连接还有一个保活计时器,这个计时器为了防止这样一种情况:建立了TCP连接后,客户端突然出现故障,服务器再也收不到数据,服务器肯定不能白等下去。服务器为了防着这种情况出现,在每次接受到一个新的报文段后,重新设置保活计时器(通常为2小时)。两小时之后没有收到数据,服务端会发送一个探测报文段,以后每75分钟发送一个。如果连发10个客户端都没有回复的话,服务端将断开连接。

TCP有限状态机图:
这里写图片描述
红色箭头为服务端进程的正常变迁,虚线箭头为客户端进程正常变迁,细线箭头为异常变迁。

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值