TCP相关知识
TCP(传输控制协议)
tcp是面向连接的,在通信前需要首先建立连接,通信结束时需要释放连接。
tcp特点
tcp提供可靠交付服务:tcp发送的数据无重复,无丢失,无错误,与发送端顺序一致
tcp是面向字节流的:tcp以字节为单位
tcp提供全双工通信:tcp的两端既可作为发送端也可作为接收端
一条tcp连接的两端只能有两个端点:tcp只能提供点到点的通信
tcp的标识符
tcp有7种标识符,用于表示tcp报文的性质。它们的值只能为0或1
这里主要介绍常见的几种标识符
*URG=1
当URG=1时,表示本数据报的数据部分包涵紧急信息,此时紧急指针有效
ACK=1
ACK被置为1后确认号字段才有效
此外,TCP规定,在连接建立后传送的所有报文段都必须把ACK置1
RST=1
当该值为1时,表示当前TCP连接出现严重问题,必须释放重新连接
SYN=1
SYN在建立连接时使用
当SYN=1,ACK=0时,表示当前报文段是一个连接请求报文
当SYN=1,ACK=1时,表示当前报文段是一个同意建立连接的应答报文
FIN=1
FIN=1,表示此报文段是一个释放连接的请求报文
TCP三次握手过程如下:
起初,服务端和客户端都为closed状态,在通信开始前,客户端和服务端都要创建各自的传输控制块(TCB)。
服务器创建完tcb后便进入listen状态,此时准备接受客户端发送来的链接请求。
第一次握手
客户端向服务端发送请求连接报文,该报文段的头部中SYN=1,ACK=0,seq=x。请求发送后,客户端便进入SYN-SENT状态。
SYN=1, ACK=0表示该报文为请求连接报文
seq=x,表示本次tcp通信的字节流的初始序号
tcp规定syn=1的报文段不能有数据部分,但是要消耗掉一个序号
第二次握手
服务端收到连接请求报文后,如果同意连接,则会发送一个应答:SYN=1, ACK=1, seq=y,ack=x+1,该应答报文发送完成后,服务端便进入SYN-RCVD状态
SYN=1, ACK=1,表示该报文为同意连接的应答报文
seq=y,表示服务端作为发送者时,发送字节流的初始序号
ack=x+1,表示服务端希望下一个数据报发送序号是从x+1开始的字节流
第三次握手
当客户端接收到同意连接的应答报文时,还需向服务端发送一个确认报文段,表示:服务端发送过来的同意连接的应答报文已成功接收到。
该报文段的头部为:ACK=1,seq=x+1,ack=y+1
客户端发送完这个报文段后,便进入了ESTABLISHED状态,服务端收到这个应答报文后,也进入ESTABLISHED状态,此时整个连接建立完成。
为何tcp连接的建立需要三次握手,两次握手行不行?
答案是不行
三次握手的目的是:防止实效的请求连接报文段被服务端接收,从而产生错误
失效的请求连接报文:客户端向服务端发送的连接请求丢失,客户端等待应答超时后就会重新发送请求连接报文,此时,上一个链接请求就是实效的
如果连接只建立两次握手,客户端并无大的改变,仍然需要获得服务端的应答报文后进入ESTABLISHED状态,而此时,服务端在接收到请求连接报文后就进入ESTABLISHED状态;
如果网络堵塞,客户端发送的请求连接报文迟迟无法到达服务端,客户端请求超时就会重新发送连接请求,此时,如果服务端正确的接受了该次连接请求,并正确应答,双发便开始通信,接收通信时释放连接;
如果此时那个实效的连接请求到达了服务端,由于只有两次握手,服务端接收到请求连接报文后就进入ESTABLISHED状态,等待客户端发送数据,或者主动发送数据,但是此时,客户端早已进入CLOSED状态,服务端就会一直等待下去,造成服务端连接资源的浪费。
TCP的四次挥手
tcp连接是双向的,其释放连接需要四步 。
在四次挥手中,前两次挥手用于断开一个方向的连接,后两次挥手用于断开另一个方向的连接
第一次挥手
如果A认为数据发送完成后,则需要向B发送链接释放请求;该请求只有报文头,主要携带的参数为:FIN=1,seq=u。 此时A将进入FIN-WAIT-1状态。
FIN=1; 表示该报文段是一个链接释放请求
seq=u; 表示A向B发送的最后一个字节序号为u-1
第二次挥手
B收到A的连接释放请求后,会通知相应的应用程序,告诉它A向B方向的链接已经释放,此时B进入CLOSE-WAIT状态,并向A发送链接释放的应答,其报文头包含:ACK=1,seq=v,ack=u+1
ACK=1;除tcp链接请求报文外,tcp通信过程中所有的数据报的ack都为1,表示应答
seq=v;表示B向A发送的最后一个字节序号为v-1
ack=u+1;表示希望收到从第u+1个字节开始的报文段,并已经成功接收前u个字节
A收到该应答,便进入FIN-WAIT-2状态,等待B发送连接释放请求
第二次挥手完成后,A到B方向的链接已经释放,B不会再接受数据,A也不会再向B发送数据;但是B向A方向的链接仍然存在,B可以继续向A发送数据
* 第三次挥手*
当B向A发送完数据后,向A发送链接释放请求,请求头:FIN=1,ACK=1,seq=w,ack=u+1;
报文头中的标识符含义同上
第四次挥手
A收到释放请求报文后,向B发送确认应答,此时,A进入TIME-WAIT状态,该状态会持续2MSL时间,若该时间段内,B没有重新发送请求的话,A便进入CLOSED状态,撤销TCB。当B受到确认应答后,也进入CLOSED状态,撤销TCB
为何第四次挥手时,A要进入TIME-WAIT状态,并等待2MSL时间,然后才进入CLOSED状态
目的: 为了确保B收到A的确认应答
如果当a发送完确认应答之后,直接进入closed状态,如果该应答丢失,b等待超时,就会重新发送链接释放请求,但是此时a已经关闭,不会作出任何响应,因此b永远无法正确关闭。