TCP 三次握手和四次挥手的面试题型
TCP 传输层通信协议
什么是TCP
TCP是面向连接、可靠的、基于字节流的传输层通信协议。
面向连接
一对一,
UDP 协议 :可以一个主机同时向多个主机发送消息。
可靠的
无论的网络链路中出现了怎样的链路变化,TCP 都可以保证一个报文一定能够到达接收端;
字节流
消息是有序的,当前一个消息没有收到时,即使他先收到了后面的字节,也不会扔到应用层处理,同时对重复的报文丢弃。
TCP头部格式
***
在建立连接时由计算机生成的随机数作为其初始值,通过SYN包传给接收端主机。每发送一次数据,就累加一次该数据字节数的大小。
用来解决网络包乱序的问题。
确认应答号
指下次期望收到的数据的***,发送端收到这个确认应答之后就可以认 为这个***以前发送的数据都已经被正常接收了。
用来解决不丢包问题。
控制位 ACK, RST, SYC, FIN
ACK: 该位为 1 时,确认应答的字段变为有效。
RST: 该位为 1 时,表示TCP连接异常,对方要求重新建立连接,复位。
SYC: 该位为 1 时,表示希望建立连接,并在其***的字段进 行***初始值的设定。
FIN: 该位为 1 时,表示今后不会再有数据发送,希望断开连接。
当通信结束希望断开连接是,双方主机之间交换FIN位置为1的TCP段。
为什么需要TCP协议
IP层是不可靠的,它既不能保证网络包按序交付,也不能保证数据的完整性。
如果要保障可靠性,就需要传输层的TCP协议负责。
什么是TCP连接
用于保证可靠性和流量控制的某些状态信息。
建立TCP连接需要客户端与服务器端达成三个共识:
- Socket: 由IP地址和端口号组成。
- ***: 解决乱序问题。
- 窗口大小 流量控制
UDP和TCP区别
-
连接
TCP 传输前要确认连接。
UDP 不需要连接,直接传数据。 -
服务对象
TCP 一对一
UDP 支持一对一,一对多,多对多 -
可靠性
TCP 可靠性强,数据可以无差别、不丢失、不重复、按需到达。
UDP 不能保证可靠性 -
拥塞控制、流量控制
TCP 有拥塞控制、流量控制机制,保证传输的安全性
UDP 则没有,即使网络拥堵,也不会影响传输效率。 -
首部开销
TCP 是可变长的选项字段,没有使用选项是20个字节,使用选项会更长。
UDP 头部长度是不可变化的,首部只有8个字节。 -
应用场景
TCP 可靠性强经常用于:- FTP文件传输
- HTTP / HTTPS
UDP简单高效,经常用于:
- 包总量较少的通信,如DNS(域名系统(服务)协议)
- 视频、音频等多媒体通信
- 广播通信
TCP建立连接(三次握手)
TCP前必须先建立连接,而建立连接是通过三次握手进行的。
1.客户端C随机选中 1 个***作为初始***seq=x发给服务端;
2.服务端S使用确认序号ACK对客户端数据包进行确认,如果已经收到seq=x的数据包,准备接受seq=x+1的包,S 告诉 C 自己的初始序列是 seq=y.
3. C告诉S接收到了S的确认消息,并准备建立连接,C的 seq=x+1,ACK=y+1 表示C准备接收S***为 y+1 的数据包。
从上面过程可以发现,第三次握手可以携带数据,前两次握手不可以携带数据。
三次握手(两次确定)的原因
防止已失效的连接请求报文段突然又传给服务器端。
三次握手才可以同步双方的初始***。
三次握手才可以避免资源浪费。
四次挥手
TCP 断开连接是通过四次挥手实现的。TCP 连接全双工,每个方向必须单独关闭。C,S双方都可以主动断开连接,断开连接后主机中的资源将被释放。
当一方完成数据发送任务之后,发送一个FIN终止这一方向的连接,不再接收数据,但仍可以发送数据。直到这一方向发送FIN。
首先执行关闭的一方执行主动关闭,但另一方执行被动关闭。
1.数据传输接收后,S进程发出连接释放报文段,停止发送数据,仍可接收数据。C发送FIN和初始***seq,关闭数据传送,C进入FIN_WAIT状态;
2.S接收FIN,发送一个确认序列ACK到C,确认序列为收到序列+1(一个FIN占一个***),S进入CLOSE_WAIT状态;
3.S发送FIN,关闭S->C的数据传送,S进入LASK_ACK状态。
4.C收到FIN,进入TIME_WAIT状态,发送ACK给S,确认序列为收到序列+1,S进入CLOSE状态。
四次挥手的原因
关闭连接时,C向S发送FIN,仅仅表示C端不再发送数据了,但是还能接收数据。
S端收到C端的FIN报文时,先回一个ACK应答报文,告诉Client端,“你发的FIN报文我收到了”。而S端可能还有数据需要处理和发送,等S端不再发送数据,才向C端发送FIN表示同意关闭连接。
S端通常需要等待完成数据的发送和处理,所以S端的ACK和FIN一般会分开发送,所以比三次握手多了一次。
为什么TIME_wait等待时间是2MSL?
MSL 报文最大生存时间。超过这个时间报文将被丢弃。
网络中可能存在来自发送方的数据包,而这些发送方的数据包被接收方处理后 又会向对方发送请求,所以一来一回需要等待2倍时间。
Linux 系统停留在 TIME_WAIT 的时间为固定的 60 秒。
为什么需要 TIME_WAIT 状态?
主动发起关闭连接的一方,才会有 TIME-WAIT 状态。
需要 TIME-WAIT 状态,主要是两个原因:
- 防止旧数据包被收到;
- 等待足够的时间以确保ACK能让被动关闭方接收,从而帮助双方的连接都可以正常关闭;
如果服务端 TIME_WAIT 状态过多,占满了所有端口资源,则会导致无法创建新连接。
Socket编程
针对 TCP 应该如何 Socket 编程?
监听的 socket 和真正用来传送数据的 socket,是「两个」 socket,一个叫作监听 socket,一个叫作已完成连接 socket。
成功连接建立之后,双方开始通过 read 和 write 函数来读写数据,就像往一个文件流里面写东西一样。
accept发生在三次握手哪一步?
客户端 connect 成功返回是在第二次握手,服务端 accept 成功返回是在三次握手成功之后。