TCP 粘包原理

导语:
    TCP 粘包原理。

总结

  • TCP 面向字节流的数据传输方式
  • 接收端根据需要在消息里加上识别消息边界的信息。不加就可能出现粘包问题。
  • TCP 粘包跟Nagle算法有关系,但关闭 Nagle 算法并不解决粘包问题。
  • UDP 是基于数据报的传输协议,不会有粘包问题。
  • IP 层也切片,但是因为不关心消息里有啥,因此有不会有粘包问题。
  • TCP 发送端可以发 10 次字节流数据,接收端可以分 100 次去取;UDP 发送端发了 10 次数据报,那接收端就要在 10 次收完。

正文

四层网络协议,应用层、传输层、网络层、接口层。消息再每进入一层时,都会多加一个报头。这个报头记录着消息从哪来,到哪去,以及消息多长等消息。 再从消息发到网络的时候给消息带上报头,消息在复杂的网络种通过这些信息在路由器间流转,最后到达目的机器上,接受者再通过这些报头,一步步还原出发送者最原始要发送的消息。 应用层是消息本身,传输层是 TCP 头部,网络层是 IP 头部,网络接口层是 MAC 头部。

软件是属于应用层上的,而消息再进入传输层时使用的是传输层上的 TCP 协议。消息再进入传输层时会被切片为一个个数据包。这个数据包的长度是 MSS。把网络比喻成一个水管,它是有一定的粗细的,这个粗细由网络接口层,即数据链路层提供给网络层,一般认为是 MTU, 直接传入整个消息,会超过水管的最大承受范围,那么就需要进行切片,成为一个个数据包,这样消息才能正常通过水管。

MTU MSS 的区别 MTU Maximum Transmit Unit 最大传输单元。由数据链路层提供给网络层最大一次传输数据的大小,一般 MTU = 1500 Byte. 假设 IP 层由 <= 1500 byte 需要发送,只需要一个 IP 包就可以完成发送任务;假设 IP 层有 > 1500 byte数据需要发送,需要分片才能完成发送,分片后的 IP Header ID 相同。 MSS Maximum Segment Size. TCP 提交给 IP 层最大分段大小,不包含 TCP Header 和 TCP Option, 只包含 TCP Payload, MSS 是 TCP 用来限制应用层最大的发送字节数。 Payload 有效载荷。 假设 MTU = 1500 Byte,那么 MSS = 1500-20-20=1460 byte,如果应用层 2000 byte 发送,那么需要两个切片才能完成发送,第一个 TCP 切片 = 1460,第二个 TCP 切片 = 540.

什么是粘包 在网络传输过程中,分片传输时,切分时的分段与预期不符合。

TCP 是一种面向连接的、可靠的、基于字节流的传输层通信协议。

字节流可以理解为一个双向的通道里流淌的数据,这个数据其实就是我们常说的二进制数据,简单来说就是一大堆01串。这些01串之间没有任何边界。 应用层传到 TCP 协议的数据,不是以消息报为单位向目的主机发送,二十以字节流的方式发送到下游,这些数据可能被切割和组装成各种数据包,接收端收到这些数据包后没有正确还原原来的消息,因此出现粘包现象。

nagle 算法,目的是为了避免发送小的数据包。

UDP

基于数据包是指无论应用层交给 UDP 多长的报文, UDP 都照样发送,即一次发送一个报文。如果数据包太长,需要分片,那也是 IP 层的事情。UDP 对应用层交下来的报文,既不合并,也不拆分,而是保留这些报文的边界。而接收方在接受数据报的时候,也不会像面对 TCP 的二进制流那样不知道何时结束。

TCP 发送端发 10 次字节流数据,而这时候接收端可以分 100 次去取数据,每次取数据的长度可以根据处理能力做调整;但 UDP 发送端发了 10 次数据报,那接收端就要在 10 次收完,且发了多少,就取多少,确保每次都是一个完整的数据报。

在报头中有 16bit 用于指示 UDP 数据报文的长度,假设这个长度是 n,以此作为数据边界。 因此在接收端的应用层能清晰地将不同的数据报文区分开,从报头开始取 n 位,就是一个完整的数据报。

TCP 发送端在发的时候不保证发的是一个完整的数据报。

接收端收到时知道长度也没用,因为它可能是完整消息的一部分。

IP 层没有粘包问题, 如果消息过长, IP 层会按 MTU 长度把消息分成 N 个切片,每个切片带有自身在包里的位置和同样的IP头信息。

各个切片在网络中进行传输,每个数据报切片可以在不同的路由中流转,然后再最后的重点汇合后再组装。

再接收端收到第一个切片包时会申请一块新内存,创建 IP 包的数据结构,等待其他切片分包数据到位。

等消息全部到位后把整个消息包给到上层进行处理。

PREVIOUSK8s minikube operation 1
NEXTTFX Airflow Tutorial