网络原理--TCP的特性

TCP报文的结构:

TCP的报头前20字节是固定长度,也可以通过“选项”来增加。

一、用来确保可靠性,最核心的机制,称为“确认应答”

引入一个情景:

A向B询问cat和dog的意思:

这种情况是理想情况,但是在互联网中经常存在后发先至的情况,例如:

这时A就会误认为cat是小狗,dog是小猫。

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

接受方将接收到的数据先放入到接受缓存区中,而接收缓冲区又可以认为成一个优先级队列(以序号作为优先级的参考依据)。

但是应答报文的确认序号,是按照发送过去的最后的一个字节的序号加1来进行设定的,而不是接受到的最后的一个数据序号。

TCP的确认应答机制是确保TCP可靠性的最核心机制。当报文为应答报文时,报头中的ACK为1,其他时候为0。

二、超时重传,是确认应答的补充

如果一切顺利,通过应答报文可以告诉发送方当前的数据是不是成功收到,但是网络上会存在“丢包”的情况,如果数据包丢了,对面没接收到,也就不会发送ack报文。

这个情况下,就需要超时重传了。

TCP的可靠性就是对抗丢包,在发送方发送一个数据包后,如果在一定时间里没有接收到ack报文,就会认为丢包了,就会把刚才的数据包再重写传输一次。这个等待有一个时间的阈值。

丢包也分为两种情况,如果丢的是数据包,再次重传一次理所当然;但是如果丢掉的是ack报文,接收方就会重复接受,这时就需要丢弃重复的数据。

关于TCP是如何判断重复的:TCP socket在内核中存在接收缓冲区,发送来的数据是要先放到缓冲区里的,然后应用程序调用read/scannner.next才可以读到数据。

当数据到达接收缓冲区里后,接收方会先判断这个数据双是否已经有了或者曾经存在过。如果存在了或者曾经存在过了,就会丢弃这个数据包。接收方判断方法就是通过数据的序号:

1.数据还在缓冲区里,拿着新收到数据的序号,和缓冲区里所以的数据序号对比一下,看看有没有一样的,有的话就丢弃。

2.数据已经被read了,因为应用程序在读取数据包时,是按照序号的先后顺序来读取的,例如:1000~2000,2001~3000,一定是先读序号小的再读序号大的,而socket会记录上次读到的最后一个字节的序号是多少。如果发现这个序号小于最后一个字节的序号,就会把这个包判断为重复数据包,并丢弃。

                        重传的策略:

1.重传次数是上限的,重传到一定程度还没有ack,就尝试重置连接,如果重置也失败,就直接放弃连接。

2.重传的超时阈值也不是一成不变的,随着重传的次数增加而增加。

三、连接管理

1.建立连接

socket = new Sockket(serverIp,serverPort);这个代码就是在建立连接,但真正建立连接的过程是在操作系统内核中完成的。

内核建立连接的过程称为“三次握手”。过程如下:

syn:一个特殊的报文段,1.没有载荷,不会携带应用层数据。2.六个标志位的第五个,为1。

在实际情况中,有两次交互可以合二为一,最终就形成了“三次握手”。

所谓建立连接的过程,本质上就是通信双方各自给对方发一个syn,各自给对方发一个ack。由于ack是六个标志位的第二位,syn是第五位,所以完全可以用一个数据包同时将ack和syn置为1。这样就可以合并为一个数据包。就将四次交互合为三次握手。

                三次握手的意义:

1.三次握手,可以先针对通信路径进行投石问路,初步确认一下通信链路是否通畅。

2.也是在验证通信双方的发送能力和接收能力是否正常。

3.三次握手也会协商一些必要的参数。TCP中也是有很多参数需要协商的,往往是以“选项”来体现的。最少0字节,最多40字节。其中有一个关键信息是TCP通信序号的起始值。TCP每次通信序号的起始值都是一个比较大数字,即使是同一个客户端和服务器,每次连接开始的序号也不同。这样上次传输的数据包即使因为某些原因到达了接收端,也会因为序号差别太大而被丢弃。

2.释放连接

释放连接称为四次挥手,和三次握手是由客户端发起不同的是,四次挥手可以是双方的任意一方发起的。它是通过发送fin(结束报文段)来结束连接。调用socket.close()就会触发fin,如果进程直接结束,也会触发fin。

面试经典题:四次挥手是否可以像三次握手一样合二为一呢:

看情况:如上图,如果服务器发送FIN和ACK时机时间间隔很小,是有可能合二为一的,如果时间间隔过大,就需要分两次发送了。

  连接管理过程中涉及到的TCP状态转换:

LISTED状态表示服务器已经创建和 severSocket了,并且绑定了端口。

ESTABLISHED 已确立的,表示客户机与服务器已经建立了连接。三次握手完了。

四次挥手中涉及到的状态转换

CLOSED_WAIT表示接下来的代码需要调用close来主动发起fin,一般是谁被动断开连接,谁进入CLOSED_WAIT。

TIME_WAIT表示本端给对方发起fin后,对端也给我发fin,此时本端进入TIME_WAIT,给最后一个ACK的传送留有一定的时间。一般是谁主动断开连接,谁进入TIME_WAIT。

TIME_WAIT存在的意义是:防止最后一个ACK丢包。如果最后一个ACK没有传到,那么接受ACK的一方就会重传fin,如果在断开连接发起方发送ACK后很长时间(2 MSL)都没有收到重传的fin,就认为已经ACK发送成功,连接断开。

四、滑动窗口,减小传输效率的折损

因为TCP为了实现可靠传输付出了很多代价,比如传输效率就大大减小了。例如在确认应答的机制下,每次发送方接收到一个ack后才会发送下一个数据,导致大量时间浪费在了等待ack上。

而滑动窗口的出现就是为了解决上述问题的。

它采用批量传输的方式:发送了一个数据后,不必等待ack,而是继续往下发,连续发送了一定的数据后,统一等待一波ack。

滑动窗口处理丢包问题:

1.ack丢了

如果是最后到达的ack报文前的ack丢了,因为数据发送是按照序号从小到大发送的,所以这并没有什么问题。后面的ack都到了,前面的到不到无所谓了。如果丢掉的是最后一个,接收方的接受缓存也会将发送方重复发送的数据丢弃。

2.数据丢了

这时接收方会重复向发送方发送丢失数据的ack报文,当重复发送三个一样的ack报文后,发送方会将丢失的报文重新发送。这种重传是针对性的重传,整体效率很高。被称为“快速重传”。

注意:确认应答中的超时重传和滑动窗口的快速重传是并不冲突的,当数据量很少时,采用确认应答的超时重传,当短时间发送大量数据时,采用滑动窗口的快速重传。

五、流量控制,使接收双方速率一致

通过滑动窗口可以提高传输效率,理论上窗口越大,效率越高。但是由于接收方的接收缓存是有限的,所以窗口不可以无限大。因为如果发送过快,接收缓存满了后,继续发送会导致丢包问题,数据传输的可靠性就会下降。

为了解决这个问题,TCP报头就增加了窗口大小的字节段。

接收方通过这个字段来反馈给发送方发送速度,这个字段在普通报文中无效,只有在ack报文中才有用,发送方就会根据这个大小来调整发送速率。当接收缓存为0后,发送方会周期性的发送“窗口探测包”,并不携带载荷,只是用来检测接收缓存是否不为0。

六、拥塞控制

同流量控制类似,都是限制发送方发送数据的速率。拥塞控制将通信双方之间的路由器,交换机等视作一个整体,然后通过实验的方式,计算出一个较合适的速率。

在实际中,滑动窗口的大小是由流量控制和拥塞控制中较小的一方决定的。

拥塞控制具体计算窗口大小的方法:

1.慢启动。刚开始传输时,速率比较小,窗口大小也比较小。

2.如果传输过程中没有丢包,说明网络很通畅,就会增大窗口大小,而且是按照指数增长发送来增大。(*2)

3.指数增长,不会一直持续下去,当到达某一个阈值后,便会转化为线性增长。

4.线性增长是持续的,当增长到丢包后,就把拥塞窗口重置为较小的值,回到最初的慢启动,而且还要根据刚才丢包时的窗口大小来重新设置指数增长的阈值。(新版本的TCP在发送丢包后会直接跳过指数增长的过程,直接进入到线性增长的环节)。

七、延时应答

也是基于滑动窗口,目的是再提升一点传输效率。核心是在允许的范围内把滑动窗口的大小再扩大一些。

原理:接收方收到数据后,不会立即返回ack,而是稍等一下再返回ack,等了这一会,相当于给接收方的应用程序这里腾出来更多的时间来消费发送方发送的数据。这时接收方接收缓存的大小会更大一些了,返回给发送方的窗口值也会更大,滑动窗口也就会更大了。

八、捎带应答

基于延时应答引入的机制,可以提升传输效率。

原理就是尽可能将能合并的数据包进行合并,从而达到提升效率的效果。

在延时应答的加持下,原本①和②之间的时间间隔就会减小,此时便可以合二为一,类似于三次握手。

九、面向字节流

此处重点讨论,面向字节流中的一个非常重要的问题“粘包问题”。

由于TCP是面向字节流的,所以对于发送过来的数据包的界限便很难区分,比如将aaa和bbb读成aaab和bb。

解决方法:

1.通过特殊符号作为分隔符,

2.指定出包的长度,比如在包开始位置加上一个特殊空间来表示整个数据的长度。

十、异常情况

这里列举一些常见的异常情况:

1.其中一方出现了进程崩溃:

进程无论是正常结束还是异常崩溃,都会触发到回收文件资源,关闭文件这样的效果。就会触发 四次挥手。

TCP连接的生命周期会比进程更长一些,虽然进程已经退出了,但是TCP连接还在,仍然可以继续进行四次挥手。

2.其中有一方出现了关机(正常流程关机):

当有个主机触发关机操作时,就会先强制终止所以的进程,终止进程自然就会触发四次挥手。

3.其中一方出现了断电:

a.断电的是接收方,发送方就会突然发现没了ack,就要重传。重传了几次后,TCP就会尝试复位,即六个标志位中的“RST”,清除TCP中的各种临时数据,重新开始。如果重置了还不行,就会单方面放弃连接。

b.断电的是发送方,此时接收方一直处于阻塞状态,但是会发送“心跳包”来询问对方的情况。(不携带数据,周期性的),如果对面没回应,本段就会尝试复位并单方面释放连接了。

4.网线断开

这个情况本质上就是a和b的结合了。

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

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

相关文章

Java 大视界 -- 深度洞察 Java 大数据安全多方计算的前沿趋势与应用革新(52)

💖💖💖亲爱的朋友们,热烈欢迎你们来到 青云交的博客!能与你们在此邂逅,我满心欢喜,深感无比荣幸。在这个瞬息万变的时代,我们每个人都在苦苦追寻一处能让心灵安然栖息的港湾。而 我的…

【HTML— 快速入门】HTML 基础

准备工作 vscode下载 百度网盘 Subline Text 下载 Sublime Text下载 百度网盘 vscode 下载 Sublime Text 是一款轻量好用的文本编辑器,我们在写前端代码时,使用 Sublime Text 打开比使用记事本打开,得到的代码体验更好,比 vscode…

深圳南柯电子|医疗设备EMC测试整改检测:零到一,保障医疗安全

在当今医疗科技飞速发展的时代,医疗设备的电磁兼容性(EMC)已成为确保其安全、有效运行的关键要素之一。EMC测试整改检测不仅关乎设备的性能稳定性,更是保障患者安全、避免电磁干扰引发医疗事故的重要措施。 一、医疗设备EMC测试整…

Tomcat安装与环境变量配置(图文详解)

一、前置条件 tomcat依赖java环境,需要先安装java环境。 jdk环境变量配置可参考:win7、win10系统JDK环境变量配置-CSDN博客 二、Tomcat的下载与安装 1.进入Tomcat官网: https://tomcat.apache.org/ 2.在该网页左侧栏红框标记的download…

网络安全之Web后端PHP

目录 一、PHP基础语法 1.PHP基础 (1)php的优点 (2)PhpStorm的优点 2.PHP基本语法 3.PHP变量 4.PHP运算符 二、PHP流控与数组 1.php流程控制语句以及循环 (1)if 语句 (2)if…

Python 批量横屏转竖屏视频处理工具

Python 批量横屏转竖屏视频处理工具 相关资源文件已经打包成EXE文件,可双击直接运行程序,且文章末尾已附上相关源码,以供大家学习交流,博主主页还有更多Python相关程序案例,秉着开源精神的想法,望大家喜欢&…

ESP32S3:解决RWDT无法触发中断问题,二次开发者怎么才能使用内部RTC看门狗中断RWDT呢?

目录 基于ESP32S3:解决RWDT无法触发中断问题引言解决方案1. 查看报错日志2. 分析报错及一步一步找到解决方法3.小结我的源码基于ESP32S3:解决RWDT无法触发中断问题 引言 在嵌入式系统中,RWDT(看门狗定时器)是确保系统稳定性的重要组件。然而,在某些情况下,RWDT可能无法…

在windows下安装windows+Ubuntu16.04双系统(上)

这篇文章的内容主要来源于这篇文章,给文章很详细的介绍了如何从windows下安装windowsubuntu16.04双系统。我刚开始装双系统都是参照这个方法,该作者前后更新了两个版本,在这里对其稍微进行整理一下。 一、准备:(这里推…

计算机单位之详解——存储单位Byte 网络传输单位bps 视频码率单位bps

前言: 计算机里面单位有点复杂,容易混淆,很多时候混起来就容易概念不理解,包括一些小问题,比如说:为什么我买了1T硬盘,实际存在虚标。为什么所谓的千兆宽带,下载起来没有1G每秒&…

博客系统完整开发流程

前言 通过前⾯课程的学习, 我们掌握了Spring框架和MyBatis的基本使用, 并完成了图书管理系统的常规功能开发, 接下来我们系统的从0到1完成⼀个项⽬的开发. 企业开发的流程 1. 需求评审(产品经理(PM)会和运营(想口号),UI,测试,开发等沟通) ,会涉及到背景/目标/怎么做,可能会有多…

MFC笔记:本专栏课件

专栏导航 上一篇:在VS2019里面,调整代码字体大小 回到目录 下一篇:无 本节前言 在之前的讲解里面,我讲解了 Visual Studio 软件的一些个基础操作步骤。从本节开始,我们进入预备章。 本节内容,属于是 …

Flutter - 基础Widget

Flutter 中万物皆 Widget,基础Widget 同步对应 Android View. 普通文本 Text /*** 控制文本样式统一使用 style:TextStyle, 例:fontSize(字体大小),color(颜色),shadows(阴影)等等* 控制文本布局需单独设置:* textAlign(文不对齐方式)* te…

蓝桥杯之日期题

文章目录 1.蓝桥杯必备知识点2. 题型13.需求2 1.蓝桥杯必备知识点 蓝桥杯是一个面向全国高校计算机相关专业学生的学科竞赛,涵盖多个赛道,常见的有软件类(如 C/C 程序设计、Java 软件开发、Python 程序设计)和电子类(…

本地部署大模型: LM Studio、Open WebUI 与 Chatbox 全面对比以及选型指南

1. 工具概述 LM Studio 定位:专注于本地化大模型实验与推理的桌面工具,支持多模型并行、Hugging Face集成及离线运行。 核心功能: 图形化界面直接加载GGUF模型文件,支持NVIDIA/AMD GPU加速。 内置OpenAI兼容API,可搭…

springboot实现多文件上传

springboot实现多文件上传 代码 package com.sh.system.controller;import org.springframework.http.HttpStatus; import org.springframework.http.ResponseEntity; import org.springframework.util.StringUtils; import org.springframework.web.bind.annotation.PostMap…

最新版IDEA下载安装教程

一、下载IDEA 点击前往官网下载 或者去网盘下载 点击前往百度网盘下载 点击前往夸克网盘下载 进去后点击IDEA 然后点击Download 选择自己电脑对应的系统 点击下载 等待下载即可 二、安装IDEA 下载好后双击应用程序 点击下一步 选择好安装目录后点击下一步 勾选这两项后点击…

vue3学习2

ts定义接口: 引入的时候要加type: 调用: ts创建自定义type类型,引入的时候也要加type: reactive可以直接传泛型: 加?声明不强制: defineProps接收父组件传递的props,其中defineProp…

Proof Beyond Boundaries: Hong Kong zkNight 活动精彩回顾

2 月 19 日,随着夜幕的降临,一场汇聚行业智慧与前瞻视野的高端主题活动 ——Proof Beyond Boundaries: Hong Kong zkNight,在香港铜锣湾 Vpoint 的 6/F 盛大启幕。本次活动由 ZEROBASE 主办,Techub News 承办,吸引了众…

PDF转HTML 超级好用 免费在线转换PDF 完美转换格式

PDF转HTML 超级好用 免费在线转换PDF 完美转换格式,PDF已成为一种广泛使用的文件格式,用于保存和分享文档。然而,PDF文件在某些场景下可能不够灵活,特别是在需要在网页上直接展示其内容时。为了满足这一需求,小白工具推…

星环科技推出DeepSeek全场景解决方案:即开即用、企业级部署、端侧智能三位一体

星环科技(688031.SH)正式发布DeepSeek全场景解决方案,全面覆盖个人用户、企业客户及行业场景需求,为用户提供从个人到企业、从云端到本地的全方位AI应用支持,为不同需求的用户提供了灵活、高效且安全的AI解决方案。 省…