2、TCP协议

一、TCP 协议是什么

首先,我们需要知道TCP在网络OSI的七层模型中的第四层——Transport层(传输层),IP在第三层——Network层(网络层),ARP在第二层——Data Link层(数据链路层),在第二层上的数据,我们叫Frame,在第三层上的数据叫Packet,第四层的数据叫Segment。
程序的数据首先会打到TCP的Segment中,然后TCP的Segment会打到IP的Packet中,然后再打到以太网Ethernet的Frame中,传到对端后,各个层解析自己的协议,然后把数据交给更高层的协议处理。
我们可以使用tcpdump抓包查看一个TCP数据包或者使用Wireshark进行抓包。

 

 

二、TCP 的状态机
网络上的传输是没有连接的,包括TCP也一样,所谓的TCP连接,其实是通讯双方共同维护的一个连接状态,让上层看起来像是有连接一样,实现连接状态的基础就是TCP协议状态机.
一个经典的问题出现了,为什么建立连接需要3次握手,断开连接需要4次握手?
对于建链接的3次握手:主要是要初始化Sequence Number的初始值。通信的双方要互相通知对方自己的初始化的Sequence Number(缩写为ISN:Inital Sequence Number)——所以叫SYN,全称Synchronize Sequence Numbers。也就上图中的 x 和 y。这个号要作为以后的数据通信的序号,以保证应用层接收到的数据不会因为网络上的传输的问题而乱序(TCP会用这个序号来拼接数据)。
对于4次挥手:其实你仔细看是2次,因为TCP是全双工的,所以,发送方和接收方都需要Fin和Ack。只不过,有一方是被动的,所以看上去就成了所谓的4次挥手。如果两边同时断连接,那就会就进入到CLOSING状态,然后到达TIME_WAIT状态。

三、TCP三次握手

TCP协议详解可靠协议TCP协议三次握手建立双向链接
三次握手的时候并未传送真正的数据,只是在为了后续发送数据做准备的
先对相关的符号作一下说明:确认号字段(ack):占四个字节,是期望收到对方的下一个报文段的数据的第一个字节的序号。若ack = N,则表明到序号N-1为止的所有数据都已正确收到。
确认位(ACK):只有当ACK=1时确认号字段才有效。当ACK=0时,确认号无效。
同步位(SYN):同步 SYN=1 表示这是一个连接请求或连接接收报文。当SYN=1,ACK=0时,表明这是一个连接请求报文,对方若同意建立连接,则在响应报文中使用SYN=1,ACK=1。即,SYN=1就表示这是一个连接请求或连接接收报文。

四、TCP四次挥手

链接状态CLOSE : 起始状态,无任何连接;
LISTEN : 服务端建立socket之后需要listen进入LISTEN(侦听)模式,侦听来自远方的TCP连接请求。
SYN_SENT : 客户端建立socket之后需要connect服务器,向服务端发送seq=x(随机数)申请连接,然后进入SYN_SENT状态。
SYN_RECVD : 服务端在**侦听模式 *下收到seq后会向客户端回应ack=x+1,同时发送seq=y,然后进入SYN_RCVD状态。
ESTABLISHED : 客户端收到ack后进行验证,同时回应服务端发来的seq,返回ack=y+1,然后进入ESTABLISHED状态。服务端收到最后一个ack后验证,然后进入ESTABLISHED。表示双方的连接建立完成,可以进行数据传输。
四次挥手断开链接终止位(FIN):用来释放连接。FIN=1表明此报文段的发送方的数据已发送完毕,并要求释放传输连接。
第一步:客户机打算关闭连接,就向其TCP发送一个连接释放报文段,并停止再发送数据,主动关闭TCP连接,该报文段的FIN标志位被置为1,seq = u,它等于前面已传送过的数据的最后一个自己的序号加1(FIN报文段即使不携带数据,也要消耗一个序号)。TCP是全双工的,即可以想象成是一条TCP连接上有两条数据通路。当发送FIN报文时,发送FIN报文的一段就不能再发送数据,也就是关闭了其中一条数据通路,但对方还可以发送数据。
第二步:服务器收到连接释放报文段后即发出确认,确认号是ack = u+1,而这个报文段自己的序号是v,等于它们前面已传送过的数据的最后一个字节的序号加1。此时,从客户机到服务器这个方向的连接就释放了,TCP连接处于半关闭状态。但服务器若发送数据,客户机仍要接收,即从服务器到客户机这个方向的连接并未关闭。
第三步:若服务器已经没有要向客户机发送的数据,就通知TCP释放连接,此时其发出FIN=1的连接释放报文段。
第四步:客户机收到连接释放报文段后,必须发出确认。在确认报文段中,ACK字段被置为1,确认号ack = w+1,序号seq = u+1。此时TCP连接还没有释放掉,必须经过时间等待计时器设置的时间2MSL后,A才进入到连接关闭状态。

连接状态:FIN_WAIT_1 : 在ESTABLISHED(连接)状态下,主动断开连接会向对端发送FIN=1,然后进入FIN_WAIT_1状态。
CLOSED_WAIT : 被动断开连接的一端收到FIN之后,会回应ack,然后进入CLOSED_WAIT状态,在CLOSED_WAIT状态下,连接只能发送数据不能接收数据。
FIN_WAIT_2 : 主动断开连接的一端收到FIN的ack回应后会进入FIN_WAIT_2状态。此时无法再发送数据但是可以接受数据。
LAST_ACK : 被动断开连接的一端在缓冲区数据发送完成后会发送FIN = 1然后进入LAST_ACK状态。如果程序健壮性较差,在socket收到文件结束符之后没有关闭socket,此处不会发出FIN,导致连接停留在CLOSED_WAIT&FIN_WAIT_2状态。
TIME_WAIT : 主动断开连接的一端在收到对端的FIN后回应ACK然后进入TIME_WAIT。此状态下连接已断开,但为了避免最后一个ACK在网络中迷路,而导致的状态紊乱,端口会被保留2*MSL的时长。
CLOSED : 在TIME_WAIT状态停留时间达到2*MSL之后进入CLOSED状态,表示无任何连接。

 五、TCP协议与UDP协议的区别

UDP协议不可靠协议传输UDP协议UDP无连接,时间上不存在建立连接需要的时延。空间上,TCP需要在端系统中维护连接状态,需要一定的开销。此连接装入包括接收和发送缓存,拥塞控制参数和序号与确认号的参数。UCP不维护连接状态,也不跟踪这些参数,开销小。空间和时间上都具有优势。
UDP没有拥塞控制,应用层能够更好的控制要发送的数据和发送时间,网络中的拥塞控制也不会影响主机的发送速率。某些实时应用要求以稳定的速度发送,能容 忍一些数据的丢失,但是不能允许有较大的时延(比如实时视频,直播等)
UDP提供尽最大努力的交付,不保证可靠交付。所有维护传输可靠性的工作需要用户在应用层来完成。没有TCP的确认机制、重传机制。如果因为网络原因没有传送到对端,UDP也不会给应用层返回错误信息
UDP是面向报文的,对应用层交下来的报文,添加首部后直接乡下交付为IP层,既不合并,也不拆分,保留这些报文的边界。对IP层交上来UDP用户数据报,在去除首部后就原封不动地交付给上层应用进程,报文不可分割,是UDP数据报处理的最小单位。
正是因为这样,UDP显得不够灵活,不能控制读写数据的次数和数量。比如我们要发送100个字节的报文,我们调用一次sendto函数就会发送100字节,对端也需要用recvfrom函数一次性接收100字节,不能使用循环每次获取10个字节,获取十次这样的做法。
UDP常用一次性传输比较少量数据的网络应用,如DNS,SNMP等,因为对于这些应用,若是采用TCP,为连接的创建,维护和拆除带来不小的开销。UDP也常用于多媒体应用(如IP电话,实时视频会议,流媒体等)数据的可靠传输对他们而言并不重要,TCP的拥塞控制会使他们有较大的延迟,也是不可容忍的

posted @ 2021-01-06 16:37  断魂刀王  阅读(161)  评论(0)    收藏  举报