| |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
-> 网络协议 -> 计算机网络-传输层的工作原理以及TCP协议:三次握手 -> 正文阅读 |
|
[网络协议]计算机网络-传输层的工作原理以及TCP协议:三次握手 |
传输层的定义TCP协议是工作在传输层的,应用层的应用程序准备好数据后委托给传输层处理
那传输层具体是什么样子的,传输层做了些什么工作呢? 传输层的功能是由操作系统提供负责实现的,传输层位于操作系统的协议栈。操作系统通过socket(即套接字)向应用层提供接口,应用层的程序仅需使用socket套接字的接口即可完成网络通讯(应用层只管调用socket的接口,就可以委托给传操作系统的协议栈处理了)。即应用程序调用socket(即套接字)库向把数据包发给操作系统的协议栈。 如下图,协议栈有两部分组成,即传输层和应用层两部分都在这里,协议栈的上半部分是传输层,这里还有两块,分别是负责用 TCP 协议收发数据的部分和负责用 UDP 协议收发数据的部分,它们会接受应用程序的委托执行收发数据的操作。下半部分是用 IP 协议控制网络包收发操作的网络层部分。
上面我们已经了解了协议栈的内部结构了,应用层的程序通过Socket接口委派工作到协议栈的传输层。 协议栈里面还有一个重要概念: Socket,中文解释叫套接字 我下面统一叫套接字,但是socket也是指它。那么套接字到底是什么来的呢?套接字看起来挺抽象的,因为在操作系统控制的,我们看不到。套接字的概念表示的是包含了通讯对象的客户端IP、客户端端口,服务器IP、服务器端口、连接状态等通讯需要的控制信息的一个称呼。一个套接字实体,表示的就是一块保存有这些控制信息的内存空间。
套接字的具体样子我们在windows的cmd命令输入netstat -ano就可以看到下面的表,这个表的每一行就可以理解为套接字的一个实体。 其中本地 IP 地址和远程 IP 地址都是 0.0.0.0,这表示通信还没开始,IP 地址不确定,这个时候状态是LISTENING 传输层的工作原理上面知道了套接字的定义了,那么看看怎么使用套接字在传输层进行连接和收发数据 首先,客户端的数据收发需要经过下面 4 个阶段: 相对地,服务器是将阶段(2)改成了等待连接,具体如下: 客户端的套接字具体工作流程1. 创建套接字的阶段??????首先是创建套接字的阶段 。应用程序调用 socket 申请创建套接字,协议栈根据应用程序的申请执行创建套接字的操作。在这个过程中,协议栈首先会分配用于存放一个套接字所需的内存空间。用于记录套接字控制信息的内存空间并不是一开始就存在的,因此我们先要开辟出这样一块空间来 ,这相当于为控制信息准备一个容器。但光一个容器并没有什么用,还需要往里面存入控制信息。套接字刚刚创建时,数据收发操作还没有开始,因此需要在套接字的内存空间中写入表示这一初始状态的控制信息。到这里,创建套接字的操作就完成了。
2. 连接阶段??????这个阶段就是要把客户端的套接字和服务器的套接字连接起来
具体的连接过程是从应用程序调用套接字的connect开始的,程序调用connect会提供服务器的IP地址和端口号,TCP将这些控制信息(客户端IP和端口、服务器IP和端口)作为TCP头部加在数据包上。
接下在网络层的IP模块,这里会在原来加上了TCP头部的数据包,再加上IP头部,以及根据本地路由表找到找到转发的下一个路由IP,然后再根据ARP协议找到这个IP所在的设备的MAC地址,把MAC地址也加在IP头部外面。再下一个路由再不断重复这个过程,直到把数据包传输到服务器上去为止。具体的过程看这篇有详细描述《计算机网络-学习路由器》
??????然后,网络包就会返回到客户端,通过 IP 模块到达 TCP 模块,并通过 TCP 头部的信息确认连接服务器的操作是否成功。如果 SYN 为 1 则表示连接成功,这时会向套接字中写入服务器的 IP 地址、端口号等信息,同时还会将状态改为连接完毕。到这里,客户端的操作就已经完成,但其实还剩下最后一个步骤。刚才服务器返回响应时将 ACK 比特设置为 1,相应地,客户端也需要将 ACK 比特设置为 1 并发回服务器,告诉服务器刚才的响应包已经收到。当这个服务器收到这个返回包之后,连接操作才算全部完成。
3.接入第三阶段收发数据??????连接成功之后客户端和服务器就可以相互发数据了协议栈并不关心应用程序传来的数据是什么内容。应用程序在调用 write 时会指定发送数据的长度,在协议栈看来,要发送的数据就是一定长度的二进制字节序列而已。其次,协议栈并不是一收到数据就马上发送出去,而是会将数据存放在内部的发送缓冲区中,并等待应用程序的下一段数据。 ??????应用程序交给协议栈发送的数据长度是由应用程序本身来决定的,不同的应用程序在实现上有所不同,有些程序会一次性传递所有的数据,有些程序则会逐字节或者逐行传递数据。总之,一次将多少数据交给协议栈是由应用程序自行决定的,协议栈并不能控制这一行为。在这样的情况下,如果一收到数据就马上发送出去,就可能会发送大量的小包,导致网络效率下降,因此需要在数据积累到一定量时再发送出去。至于要积累多少数据才能发送,不同种类和版本的操作系统会有所不同,不能一概而论,但都是根据下面几个要素来判断的。 ??????第一个判断要素是每个网络包能容纳的数据长度,协议栈会根据一个叫作 MTUA 的参数来进行判断。MTU 表示一个网络包的最大长度,在以太网中一般是 1500 字节(图 2.5)B。MTU 是包含头部的总长度,因此需要从MTU 减去头部的长度,然后得到的长度就是一个网络包中所能容纳的最大数据长度,这一长度叫作 MSSC。当从应用程序收到的数据长度超过或者接近 MSS 时再发送出去,就可以避免发送大量小包的问题了
??????另一个判断要素是时间。当应用程序发送数据的频率不高的时候,如果每次都等到长度接近 MSS 时再发送,可能会因为等待时间太长而造成发送延迟,这种情况下,即便缓冲区中的数据长度没有达到 MSS,也应该果断发送出去。为此,协议栈的内部有一个计时器,当经过一定时间之后,就会把网络包发送出去。 这个阶段还有一个重要问题。TCP是如何确认对方收到网络包的,以及数据拆分成多个包发送到达另一边后,另一边的计算机是如何还原这些数据的,因为数据包到达的顺序不一定一样,可能后面的比前面的到达更快。(这一部分还有挺多逻辑,后面再写一篇补充,暂时不描述了) 4.断开管道并删除套接字协议栈允许任何一方先发起断开过程。
断开的操作顺序如下: 具体流程:
TCP的三次握手为了进行可靠的传输,无非是要保证客户端与服务器之间的数据发送和接收的正常进行。
为什么需要进行第三次握手了?一句话,主要防止已经失效的连接请求报文突然又传送到了服务器,从而产生错误。 通过上面的三个步骤,Client和Server能够进行可靠的传输,缺一不可
|
|
网络协议 最新文章 |
使用Easyswoole 搭建简单的Websoket服务 |
常见的数据通信方式有哪些? |
Openssl 1024bit RSA算法---公私钥获取和处 |
HTTPS协议的密钥交换流程 |
《小白WEB安全入门》03. 漏洞篇 |
HttpRunner4.x 安装与使用 |
2021-07-04 |
手写RPC学习笔记 |
K8S高可用版本部署 |
mySQL计算IP地址范围 |
|
上一篇文章 查看所有文章 |
|
开发:
C++知识库
Java知识库
JavaScript
Python
PHP知识库
人工智能
区块链
大数据
移动开发
嵌入式
开发工具
数据结构与算法
开发测试
游戏开发
网络协议
系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程 数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁 |
360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 | -2024/11/25 19:49:48- |
|
网站联系: qq:121756557 email:121756557@qq.com IT数码 |