分享

TCP状态机:学习TCP连接必须掌握的技术点

 2017helloworld 2018-02-05

一、TCP状态机是TCP连接的变化过程。

Tcp在三次握手和四次挥手的过程,就是一个tcp的状态说明,由于tcp是一个面向连接的,可靠的传输,每一次的传输都会经历连接,传输,关闭的过程,无论是哪个方向的传输,必须建立连接才行,在双方通信的过程中,tcp 的状态是不一样的。

下面介绍一下,在三次握手和四次挥手的过程中的几种状态,如下图所示,是tcp状态的变化过程

TCP状态机:学习TCP连接必须掌握的技术点

各种状态的解释

LISTEN:侦听来自远方TCP端口的连接请求

SYN-SENT:发送连接请求后等待匹配的连接请求

SYN-RECEIVED(syn已经收到的):收到和发送给一个连接请求后等待对连接请求的确认

ESTABLISHED(已建立的):代表一个打开的连接,数据可以传送给客户

FIN-WAIT-1:等待远程TCP的连接中断请求,或者先前的连接中断请求的确认

FIN-WAIT-2:从远程TCP等待连接中断请求

CLOSE-WAIT:等待从本地用户发来的连接中断请求

CLOSEING:等待远程TCP对连接中断的确认

LAST-ACK:等待原来发向远程TCP的连接中断请求的确认

TIME-WAIT:等待足够的时间一确保远程TCP接受到连接中断请求的确认

CLOSED:没有任何连接状态

下图是时序图

TCP状态机:学习TCP连接必须掌握的技术点

二、tcp建立连接的三次握手和四次挥手。

TCP状态机:学习TCP连接必须掌握的技术点

客户方主动打开TCP连接,向另一端的服务器方发送一个SYN同步序号来请求发起一个连接,客户方发送SYN后会变为SYN_SENT状态,这种状态时等待对端回应状态。

再看服务器端,服务器作为被动打开方回收到客户方发来的SYN连接请求信息(在图中为SYN j),服务器收到SYN请求后本身状态会从监听LISTEN状态转化到SYN_RCVD状态,会发送一个与收到的SYN相对应的ACK确认序号有效信息(图中ACK j+1)和自身向对端请求连接的同步序号SYN(在图中为SYN k)。

处于SYN_SENT状态的客户方一直等待着对端回应ACK信息和SYN信息,当收到回应信息后客户方的状态会从SYN_SENT状态转换到ESTABLISHED,此时客户方能够进行双向数据传递,向对端发送一个服务器发来的SYN相对应的ACK信息(及图中的ACK k+1)。如果客户方一直没有收到回应信息,客户方的SYN_SENT状态会超时重新回到初始状态。

服务器方收到客户方发来的ACK回应信息后会从先前的SYN接收状态SYN_RCVD转换到ESTABLISHED,之后服务器方也能够进行双向数据传递。当TCP连接的双方都进入ESTABLISHED状态后,这个TCP连接便建立成功了,连接双方都能够进行双向数据传输。

当通信双方通信结束需要终止TCP连接,再此假定客户方发起主动关闭,此时客户方会向服务器方发送FIN完成数据发送信息(图中FIN m),客户方发送FIN信息后状态会从ESTABLISHED数据传输状态转换到FIN_WAIT_1状态,等待服务器方返回的确认信息。

服务器方收到客户方发来的FIN信息后状态会由ESTABLISHED数据传输状态转换到CLOSE_WAIT状态。检查自身的数据发送状态,如果此时还有数据在发送,服务器方会先回复客户方一个与收到的FIN信息相对应的ACK确认信息(图中ACK m+1),等到自身数据发送结束之后再次向客户方发送一个自己的FIN完成数据发送信息(图中FIN n),之后状态再次转换到LAST_ACK状态;如果此时检查自身的数据也发送结束,会向客户方同时发送ACK和FIN信息,状态再次转换到LAST_ACK状态。

客户方的状态是由收到信息来决定的。当只收到服务器方给自己的ACK确认信息,客户方的状态会从FIN_WAIT_1状态转换成FIN_WAIT_2状态。这时候只有一方进程关闭,就进入了半连接状态,只有另一端数据传输完成也发来FIN信息,状态才会转换到TIME_WAIT状态;当同时收到服务器方发来ACK信息和服务器自己的FIN信息时,客户方的状态会从FIN_WAIT_1直接转换到TIME_WAIT状态。

服务器方收到客户方发给自己的ACK确认信息后,服务器方的状态会从LAST_ACK状态转换成初始状态CLOSED 。

客户方收到对方的FIN信息后,将状态转换到TIME_WAIT状态,会回复给服务器方一个对应的ACK确认信息(图中ACK n+1),同时客户方会在这个状态停留2MSL时间以防止最后发出的ACK丢失,服务器方再次发起重连。

客户端tcp状态迁移

CLOSED->SYN_SENT->ESTABLISHED->FIN_WAIT_1->FIN_WAIT_2->TIME_WAIT->CLOSED

服务器TCP状态迁移:

CLOSED->LISTEN->SYN收到->ESTABLISHED->CLOSE_WAIT->LAST_ACK->CLOSED

三、TCP/IP协议中采用三次握手建立一个连接为TCP协议提供可靠的连接服务。

(1)第一次握手:建立连接时,客户端A发送SYN包(SYN=j)到服务器B,并进入SYN_SEND状态,等待服务器B确认。

(2)第二次握手:服务器B收到SYN包,必须确认客户A的SYN(ACK=j+1),同时自己也发送一个SYN包(SYN=k),即SYN+ACK包,此时服务器B进入SYN_RECV状态。

(3)第三次握手:客户端A收到服务器B的SYN+ACK包,向服务器B发送确认包ACK(ACK=k+1),此包发送完毕,客户端A和服务器B进入ESTABLISHED状态,完成三次握手。

完成三次握手,客户端与服务器开始传送数据。

TCP状态机:学习TCP连接必须掌握的技术点

四、安全关闭连接。

由于TCP连接是全双工的,因此每个方向都必须单独进行关闭。这个原则是当一方完成它的数据发送任务后就能发送一个FIN来终止这个方向的连接。收到一个 FIN只意味着这一方向上没有数据流动,一个TCP连接在收到一个FIN后仍能发送数据。首先进行关闭的一方将执行主动关闭,而另一方执行被动关闭。

TCP的连接的拆除需要发送四个包,因此称为四次挥手(four-way handshake)。客户端或服务器均可主动发起挥手动作,在socket编程中,任何一方执行close()操作即可产生挥手操作。

(1)客户端A发送一个FIN,用来关闭客户A到服务器B的数据传送。

(2)服务器B收到这个FIN,它发回一个ACK,确认序号为收到的序号加1。和SYN一样,一个FIN将占用一个序号。

(3)服务器B关闭与客户端A的连接,发送一个FIN给客户端A。

(4)客户端A发回ACK报文确认,并将确认序号设置为收到序号加1。

TCP状态机:学习TCP连接必须掌握的技术点

【问题1】为什么连接的时候是三次握手,关闭的时候却是四次握手?答:因为当Server端收到Client端的SYN连接请求报文后,可以直接发送SYN+ACK报文。其中ACK报文是用来应答的,SYN报文是用来同步的。但是关闭连接时,当Server端收到FIN报文时,很可能并不会立即关闭SOCKET,所以只能先回复一个ACK报文,告诉Client端,'你发的FIN报文我收到了'。只有等到我Server端所有的报文都发送完了,我才能发送FIN报文,因此不能一起发送。故需要四步握手。

【问题2】为什么TIME_WAIT状态需要经过2MSL(最大报文段生存时间)才能返回到CLOSE状态?

答:虽然按道理,四个报文都发送完毕,我们可以直接进入CLOSE状态了,但是我们必须假象网络是不可靠的,有可以最后一个ACK丢失。所以TIME_WAIT状态就是用来重发可能丢失的ACK报文。

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多