【网络原理】TCP协议的相关机制(确认应答、超时重传)

系列文章目录

【网络通信基础】网络中的常见基本概念

【网络编程】Java网络编程中的基本概念及实现UDP、TCP客户端服务器程序(万字博文)

【网络原理】UDP协议的报文结构 及 校验和字段的错误检测机制(CRC算法、MD5算法)


文章目录

一、TCP协议的特性

TCP协议段格式

二、TCP协议的相关机制

1. 确认应答

2. 超时重传


一、TCP协议的特性

前面介绍过,TCP(Transmission Control Protocol,传输控制协议)是互联网中的一种有连接的、可靠的、面向字节流、全双工的传输层协议。它是TCP/IP协议族中的一个重要组成部分,用于在网络中可靠地传输数据。

TCP协议是以后工作中最常用到的传输层协议,也是面试最常考的协议,非常非常重要!

TCP协议段格式

TCP协议段(Segment)的格式如下图所示:

301444ec6e994608a0c82b21befa385d.png

由于TCP报头最大长度是60字节,而除选项外,其余报头字段加起来一共是20字节,是固定的。这个选项部分是可选的,因此选项部分为0 ~ 40个字节。

可以看到,TCP报头是比UDP报头复杂很多的。

TCP的内部机制也是很多的,需要了解TCP的这些机制,才能理解报头的含义。

二、TCP协议的相关机制

1. 确认应答

确认应答,可以说是TCP协议用来确保可靠性,最核心的机制。

假设你给“朋友“发了一条短信:

  • 当你发出短信后,你可能会期待朋友收到并回复你,以确认他已经收到了你的短信。如果你很长时间没有收到回复,你可能会怀疑短信没有发送成功(前提是朋友一定会回复你的短信)。
  • 如果朋友此时收到短信,并给你回复了,你看到回复,就可以知道之前发的短信是一定被正确收到了。在这里,朋友的回复就相当于确认应答

再假设,你给“朋友”发了两条短信: 

  • 由于网络传输过程中,经常会出现"后发先至"的情况。导致朋友回复短信的时候,回复短信的顺序和发送短信的顺序是不一致的,就容易发生“答非所问”的情况。

出现后发先至的情况是,由于网络拥塞或者数据包的路由选择引起的。这种情况可能发生在网络中存在多条路径,但是不同路径的延迟不同,导致一些数据包比其他数据包先到达目的地。

为了解决上述问题,TCP就入了序号和确认序号。通过对数据进行编号,应答报文里就告诉发送方,我这次应答的是哪个数据。

而TCP是面向字节流的,以字节为单位进行传输的。因此,TCP的序号和确认序号都是以字节来进行编号的。如下图:

  • 假设载荷有1000个字节,一个载荷就有1000个序号,由于序号是连续的,只需要在报头保存第一个字节的序号即可,后续字节的序号都是很容易计算得到的。
  • 应答报文中的确认序号,是按照发送过去的最后一个字节的序号+1,来进行设定的。

如上图,当发送第一条数据:

  • 数据报头的序号就是1,主机B收到了1 - 1000这些字节数据后,反馈一个应答报文,应答报文中的确认序号的值就是1001

此处1001的含义,有两种理解方式:

  1. 小于1001的数据,都已经收到了.
  2. 发送方接下来要给我发的数据是从1001开始的.

确认应答中,通过应答报文来反馈给发送方,当前的数据正确收到了。应答报文,也叫 ACK 报文,ACK => acknowledge 单词的缩写。

ACK报文也就是TCP报头中六位标志位的第二位。平时该位是0,如果当前报文时应答报文,则这一位就是1.

2. 超时重传

超时重传,可以被视为是确认应答机制的一种补充。

发送方发送数据,如果一切顺利,接收方通过 ACK 标志位就可以告诉发送方,当前数据是否成功收到了。

但是,在某些情况下,1. 如果接收方没有及时发送 ACK 确认,2. 或者数据包丢失(丢包),发送方就无法得知数据是否已成功传输(至于为什么会丢包,这里就不细说了)。这时就需要超时重传来补充确认应答机制。

简单来说:

  • 发送方发了个数据之后,要等待接收来自接收方的ACK确认。
  • 如果等了很久,ACK还没等到,此时发送方就认为数据的传输出现丢包了。
  • 当认为丢包之后,就会把刚才的数据包再传输一次(重传)。
  • 而这个等待的过程有一个时间阈值(定时器),超过等待时间,就是(超时)。

上面的过程,我们认为没收到ACK就是丢包。实际上,超时重传的触发可能不仅是由于数据包丢失导致的,还可能是由于ACK确认丢失导致的。

不论是数据包丢了,还是ACK丢了,从发送方的角度来看,是区分不了的,都是认为ACK没收到。如下图,对比一下这两种情况:

对于ACK丢失而导致的主机B收到很多重复数据这种情况,这里涉及到的内容也很多:

  • TCP socket 在内核中存在接收缓冲区,对于发送方发来的数据,是要先放到接收缓冲区中的。而应用程序调用读方法读数据的操作,其实是读取接收缓冲区的数据。
  • 当数据到达接收缓冲区的时候,接收方首先会判定当前缓冲区是否已经有,或者有过这个数据了。
  • 如果这个数据已经存在或者存在过,TCP就会直接把重复发来的数据丢弃(去重),这样就能确保应用程序,调用读方法的时候,不会出现重复数据了。

※ 接收缓冲区,除了能进行去重之外,还能够进行排序,对收到的数据按照序号进行排序,确保上层应用程序读到的数据和发送的数据顺序是一致的

接收方如何判定这个数据是否是"重复数据"?

核心判定依据:前面谈到的数据的序号。

  1. 数据还在接收缓冲区,还没被读走。此时,拿着新收到的数据的序号,和缓冲区中所有的数据的序号对一下,看看有没有一样的。有一样的就是重复了,就把这个数据丢弃了。
  2. 数据已经不在接收缓冲区,被应用程序读走了。此时,新来的数据序号是无法从接收缓冲区查到的。但是!应用程序读取数据的时候,是按照序号的先后顺序进行读取的。例如,1-1000,1001-2000,2001-3000。一定是先读序号小的,后读序号大的数据。此时, socket api中就可以记录上次读的最后一个字节的序号是多少。比如,上次读到的最后一个字节的序号是3000,新收到的数据的序号是1001,而这个1001一定是之前已经读过了。这个时候同样可以把这个新的数据包判定为“重复数据”直接丢弃了。

上述这些机制,都是TCP内置的,我们在使用TCP的api的时候,不需要考虑这些。但是学习这些能够让我们了解TCP内部做了哪些事情,从而写出更正确的代码。

TCP为了保证较高性能通信,此处的超时重传也不是无限重传,重传过程也是有一定的策略的。

  1. 重传次数是有上限的。如果累计到一定次数,还没有收到ACK,TCP认为网络或者对端主机出现异常,强制关闭连接。
  2. 重传的超时时间也不是固定不变的。随着重传次数的增加,这个超时时间会动态增长。

使用上述策略1的原因:

  • 假设,一次网络通信过程中,丢包的概率是10%(已经是一个很大的数字了),包顺利到达的概率是90%
  • 如果此时重传了一次,两次都丢包的概率只有10% * 10%,即1%;而两次至少有一次传输成功的概率,就是99%
  • 随着重传次数的增加,包能到达接收端的概率也会大大增加,这个概率就非常高了。

如果继续重传,在成功概率这么高的情况下,还是出现丢包的情况,说明当前网络已经出现非常严重的故障了,再重传也意义不大了。因此,就会关闭连接。

使用上述策略2的原因:

结合策略1的分析,数据经过了重传之后还是丢包,大概率是网络出现严重问题了,在没达到重传次数上限之前,重传还是要重传的,但是可以省点力气,少传几次(降低重传频率)。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/5112.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

# 谷歌 Chrome 浏览器无法安装插件的解决方法

谷歌 Chrome 浏览器无法安装插件的解决方法 运用开发模式安装 安装步骤: 1、 将 XX.crx 插件的扩展名改成 .zip 或者 .rar 并解压到文件夹 XX 目录。 1)如:下载的 前端框架 vue.js 插件 nhdogjmejiglipccpnnnanhbledajbpd-6.6.1-Crx4Chro…

大数据 - Doris系列《四》- Doris常用函数

往期文章: 大数据 - Doris系列《一》- Doris简介_doris详细介绍-CSDN博客 大数据 - Doris系列《二》- Doris安装(亲测成功版)_java8 please set vm.max_map_count to be 2000000 un-CSDN博客 大数据 - Doris系列《三》- 数据表设计之表的基…

Pytest:hooks钩子函数

Pytest:hooks钩子函数 Bootstrapping hooks 引导钩子Initialization hooks 初始化钩子Collection hooks 测试用例收集钩子Test running (runtest) hooks 测试运行钩子Reporting hooks 测试报告钩子Debugging/Interaction hooks 调试/交互钩子 Pytest的钩子函数可分为…

面试重点2:网页访问不了,从服务器层面如何排查

从服务器层面排查网页访问问题可以按照以下步骤进行: 1. 检查网络连接 确保服务器的网络连接正常,可以通过 ping 命令测试网络是否通畅,例如 ping www.example.com。 2. 排查 DNS 问题 如果访问域名无法解析,可能是 DNS 配置问…

Python深度学习实践:使用TensorFlow构建图像分类器

摘要 随着深度学习技术的飞速发展,图像识别已成为AI领域的热点应用之一。本篇文章将引导读者使用Python和Google的TensorFlow框架,从零开始构建一个简单的图像分类器。我们将深入探讨卷积神经网络(CNN)的基本原理,实现一个能够识别MNIST手写数字的数据集模型,并通过实战代…

Java自定义工具类中使用RedisTemplate的遇到空指针问题

话不多说,上错误代码,以下是我在静态方法里使用RedisTemplate类,这里加了Autowired ****省略import包**** public class CommonUtils {Autowiredprivate static RedisTemplate redisTemplate;public static String test() {String info &qu…

邦注科技即热式节能模温机 模温机的工作原理

模温机是一种用于控制模具温度的设备,主要用于塑料注塑、压铸、橡胶成型等工艺中。 其工作原理主要包括以下几个步骤: 加热阶段: 当模具需要加热时,双温模温机会启动加热系统,将热传导油或热传导水加热至设定温度。加…

Spring Cloud学习笔记(Hystrix):execute,queue,observe,toObservable样例和特性

这是本人学习的总结,主要学习资料如下 - 马士兵教育 1、Overview2、execute()2.1、Overview2.2、示例 3、queue()3.1、Overview3.2、示例 4、observe()4.1、Overview4.2、示例 5、toObservable()5.1、observe()和toObservable()的区别 1、Overview 我们知道Hystrix…

HDFS架构

HDFS 是一个主从 Master/Slave 架构一个 HDFS 集群包含一个 NameNode,这是一个 Master Server,用来管理文件系统的命名空间,以及协调客户端对文件的访问一个 HDFS 集群包含多个 DataNode,用来存储数据HDFS 会对外暴露一个文件系统命名空间,并允许用户数据以文件的形式进行存储在…

iOS实现一个高性能的跑马灯

效果图 该跑马灯完全通过CATextLayer 实现,轻量级,并且通过 系统的位移动画实现滚动效果,避免了使用displaylink造成的性能瓶颈,使用系统动画,系统自动做了很多性能优化,实现更好的性能,并使用…

java设计模式 -- 工厂模式

1、基本概念 工厂模式(Factory Pattern)是 Java 中最常用的设计模式之一,这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。 工厂模式提供了一种创建对象的方式,而无需指定要创建的具体类。 工厂…

python与上位机开发day04

模块和包、异常、PyQt5 一、模块和包 1.1 模块 Python中模块就是一个.py文件,模块中可以定义函数,变量,类。模块可以被其他模块引用 1.1.1 导入模块 """ 导入格式1: import 模块名 使用格式: …

【yolov8目标检测部署】TensorRT int8量化

原作者github:https://github.com/xuanandsix/Tensorrt-int8-quantization-pipline/tree/main 改进: 源代码支持的TensorRT版本为7.许多属性已经弃用; 在原有的代码上将支持的TensorRT版本从7改到8. !!不知道如何安装T…

速盾:海外服务器如何加速

海外服务器加速是一种优化网络连接的方法,目的是提高用户对海外服务器的访问速度。由于地理位置、网络带宽等因素的限制,用户在访问海外服务器时常常会遇到访问缓慢的问题。为了解决这个问题,以下是一些常见的海外服务器加速方法。 使用CDN技…

【设计模式】简单工厂模式(Simple Factory Pattern)

工厂模式(Factory Pattern) 用于创建不同类型的奖品对象。您可以创建一个奖品工厂,根据配置的类型来实例化相应的奖品对象。 public interface Prize {void award(); }public class MoneyPrize implements Prize {Overridepublic void awar…

(Askchat.ai、ChatAI、智友AI、AI写作生成器助手、在线AI助手)分享好用的ChatGPT

目录 1、Askchat.ai - 梦想为蓝图,ChatGPT为笔。 2、ChatAI 3、智友AI - MyChatGPT 4、AI写作生成器助手

opencv-基本操作

本篇文章,我们将聊一聊利用opencv进行的一些基本操作,以便后续我们利用opencv进行更加复杂的处理。 1、图像的读取、显示与保存 opencv中利用cv2.imread读取RGB图像,利用cv2.imshow() 进行图像的显示。 # 注意: cv2.imread读取RGB图像时, 返回…

在 Windows 系统上安装 TeamViewer 13

在 Windows 系统上安装 TeamViewer 13 References 默认安装到所有用户 同意协议 安装目录 勾选内容 打开文件位置 打开 rClientID.exe Extras -> Options -> Advanced Show advanced options -> Display language 重新启动TeamViewer 语言可修改为中文简体 …

稳扎稳打 部署丝滑 开源即时通讯(IM)项目OpenIM源码部署流程(linux windows mac)

背景 OpenIM包含多个关键组件,每个都是系统功能必不可少的一部分。具体来说,MongoDB 用于持久化存储;Redis 用作缓存;Kafka 用于消息队列;Zookeeper 用于服务发现;Minio 用于对象存储。这些组件的众多可能会…

C++14之std::exchange的使用和原理分析

目录 1.概述 2.使用 2.1.交换操作 2.2.移动语义 3.原理 4.综合示例 5.总结 1.概述 std::exchange 是 C 标准库中的一个实用函数,它的主要作用是替换一个对象的值,并返回该对象的旧值。这个函数在 C14 中引入,主要用于简化和优化代码。…