tcp的报文头部的一些信息
- ACK:表示应答域有效,有两个值0和1,tcp三次握手时第一次发送时ACK为0。1表示应答域有效,反之为0。
- Acknowledge Number:确认序号,确认序号应该是上次成功接受的序号+1,表示期望下一次收到的序号。主要用来解决不丢包的问题。(相当于表示上一次的内容成功接收到了)
- Sequence Number:序号,表示报文中第一个字节在发送的数据流中的序号,解决乱序的问题。Sequence Number是跟Acknowledge Number一起使用的,举个例子,主机1发送了Sequence Number = x给主机2,那么主机2收到之后就将Acknowledge Number设置为x+1,意思是这次的消息收到了,下次主机1应该发送的下一个Sequence Number为x+1。
- SYN:同步序号,用来建立连接,SYN与ACK一起搭配使用,tcp第一次握手时(连接请求)SYN = 1,ACK = 0,tcp第二次握手时(响应连接)SYN = 1,ACK = 0(这个标志的数据包经常被用来进行端口扫描。扫描者发送一个只有SYN的数据包,如果对方主机响应了一个数据包回来 ,就表明这台主机存在这个端口;但是由于这种扫描方式只是进行TCP三次握手的第一次握手,因此这种扫描的成功表示被扫描的机器不很安全,一台安全的主机将会强制要求一个连接严格的进行TCP的三次握手)
- FIN:表示发送端已经达到数据末尾,也就是说双方的数据传送完成,没有数据可以传送了,发送FIN标志位的TCP数据包后,连接将被断开。

-
tcp连接首先要经过三次握手来建立连接,三次握手之后成功建立连接,然后才开始进行数据的传输
-
第一次握手:客户端发送连接请求报文段(SYN报文),将SYN设置为1,Sequence Number为x,发送之后进入SYN_SEND状态,等待服务器确认
- 第二次握手:服务端对接收到的SYN请求报文进行确认,确认SYN(设置Acknowledgement Number为 x+1(Sequence Number+1)),SYN设置为1,Sequence Number设置为y,ACK设置为1(ACK不等于Acknowledge Number),服务端将这些信息放到一个报文段(即发送SYN+ACK包)一起发送给客户端,此时进入SYN_RECV状态
- 第三次握手:客户端收到服务器的SYN+ACK报文后检查Acknowledge Number是否正确,将Acknowledge Number设置为y+1,然后像服务器发送ACK报文段,这个报文段发送完之后服务端客户端都进入ESTABLISHED状态,此时就完成了三次握手
为什么要采用三次握手

- 如果不采用三次握手,假如主动方发送一个连接请求报文,但是由于网络原因延迟到达了请求方。但是这个请求已经失效了,于是被动方就同意连接请求等待主动方发送信息,但是由于这个请求已经失效,主动方不会给被动方发送信息,就会导致被动方一直等待而浪费资源。
tcp的四次挥手(四次分手)
- 说明当主机之间通过三次挥手建立了连接,数据传输完毕之后就需要断开连接,断开这个过程就需要四次挥手
- 第一次挥手:主机1设置Sequence Number ,发送FIN报文段(请求关闭连接),之后进入FIN_WAIT_1状态(表示主机1没有消息发送了)
- 第二次挥手:主机2收到主机1的报文之后设置Acknowledge Number同时发送ACK报文告知对方同意对方的关闭请求,主机1(注意不是主机2)进入FIN_WAIT_2状态,主机2会进入CLOSE_WAIT状态。
- 第三次挥手:主机2发送FIN报文请求关闭连接,同时进入LAST_ACK状态
- 第四次分手:主机1收到主机2发送的FIN报文段之后,像主机回复一个ACK报文段,同时进入TIME_WAIT状态。主机2收到这个ACK报文段之后就关闭连接。主机1在等待2MSL之后没收到回复表示主机2已经正常关闭连接了,那么主机1关闭连接
- 四次握手的几个状态
- FIN_WAIT_1:在主机第一次发送FIN报文之后就会进入这个状态,这个跟FIN_WAIT_2状态比较类似,表示等待对方的FIN报文。区别是当主机在连接建立时(ESTABLISHED状态),想要主动关闭连接,就发送一个FIN报文之后就进入FIN_WAIT_1状态,在对方回复了ACK报文之后就进入FIN_WAIT_2状态,这个时候就等待对方的FIN报文。(主动方)
- FIN_WAIT_2:FIN_WAIT_2状态表示半连接状态,表示一方要求关闭连接,但另外还告诉对方,我暂时还有点数据需要传送给你(ACK信息),稍后再关闭连接。(主动方)。 CLOSE_WAIT:在被动关闭连接情况下,在已经接收到FIN,但是还没有发送自己的FIN的时刻,连接处于CLOSE_WAIT状态。接下来呢,实际上你真正需要考虑的事情是察看你是否还有数据发送给对方,如果没有的话,那么你也就可以 close这个SOCKET,发送FIN报文给对方,也即关闭连接。所以你在CLOSE_WAIT状态下,需要完成的事情是等待你去关闭连接。(被动方)
- LAST_ACK:被动的一方发送了FIN(上面的主机2)报文之后等待对方的ACK报文。当收到ACK报文后,也即可以进入到CLOSED可用状态了。(被动方)
- TIME_WAIT:表示收到对方的FIN报文之后回复ACK报文,等待2MSL之后就进入CLOSED可用状态。如果FINWAIT1状态下,收到了对方同时带FIN标志和ACK标志的报文时,可以直接进入到TIME_WAIT状态,而无须经过FIN_WAIT_2状态。(主动方)
- CLOSED:连接中断。
为什么要采取四次挥手
- 主动方发送FIN报文之后表示主动方没有要发送的数据但是还可以接收数据,被动方收到主动方发送的FIN报文后回复一个ACK报文表示被动方已经知道主动方没有信息发送了,然后被动方回复一个FIN报文表示告诉主动方被动方也没信息发送了,之后主动方回复一个ACK报文后告诉被动方收到消息,之后两者就能结束连接了。