• TCP_IP协议


    传输层协议

    传输层的主要作用是负责向两台主机进程之间的通信提供数据传输服务。
    传输层的协议主要有传输控制协议TCP和用户数据协议UDP。

    UDP协议

    先从较简单的UDP协议来看, UDP报文由 UDP报头 和 UDP数据荷载 组成. 可以认为UDP协议就是在应用层数据的基础上添加 8 个字节的报头. 其中 源端口号, 目的端口号, 数据报长度,校验和 都为两个字节.
    在这里插入图片描述

    1. 源端口是客户端的端口, 目的端端口就是服务区的端口
    2. 数据报长度为两个字节, 也就是0-65535, 但是在现代来说, 这个数据量就十分微小了, 所以在面对数据量大的时候, 我们会对数据进行拆包, 在发送.接收端在把数据拼接起来, 但是这就会出现数据混乱或丢失的情况. 这时候我们就可以用没有大小限制的TCP来解决.
    3. 校验和就是来验证数据在网络传输的过程中有没有发生改变.

    TCP协议

    TCP具有可靠连接, 有连接, 面向字节流, 全双工的特点.
    TCP报头:

    在这里插入图片描述

    1. 源端口和目的端口和上文中UDP的作用一样
    2. 序列号 是对每个数据都进行了编号(TCP是面向字节流的,所以编号是对字节编号), 确认号 是当目前报文时普通报文时,确认号不生效, 如果当前报文时应答报文, 确认序号就宝石要应答的是哪个报文
    3. 保留位是为了未来升级UDP而保留的位置
    4. 窗口在下文中解释

    可靠传输

    可靠传输是TCP十分关键的机制. 在数据传输的时候, 很可能遇到数据传输不知道是否收到和乱序的特点, 如下, 对一位爱学习的朋友发出邀请:
    在这里插入图片描述
    明明 “不去” 回复的是去网吧,此处却乱序了,意思也就随之改变, 这样的传输是不可靠的.
    但为了实现可靠传输, 我们就采用了确认应答.

    确认应答
    1. 确认应答就是当数据发出去后, 我们知道对方有没有收到数据, 就像"已读"
    2. 但为了避免上文的乱序现象, 就采用了编号机制, 根据编号就知道传输的信息是第几条了.
    3. 根据传来的信息的编号, 我们就可以确认应答报文要应答的是哪条信息.
      例如:
      在这里插入图片描述
      在这里插入图片描述
    超时重传

    超时重传是在确认应答的基础上对可靠传输做出进一步保证. 如果数据在传输过程中丢失, 那么应答报文就无法发出. 发出数据方长时间没有接收到应答报文后, 明白是数据传输出现了问题, 在重新发送数据.

    1. 数据发出时丢失, 那么应答报文无法返回, 数据发出放没有接收到应答报文就会再次发出数据.
    2. 应答报文丢失, 那么数据发出方还是没有接收到应答报文, 数据发出方就会再次发出数据. 数据接收方再次接收到数据时, 明白应答报文出现了问题, 会再次发出应答报文.

    重传如果再次失败, 还会再次重传, 但也不是无止尽的, 在多次重传失败后, 就明白网络出现了问题, 会断掉此次连接.

    连接管理

    连接管理主要是两个部分:

    1. 建立连接
    2. 断开连接
    建立连接的方法
    三次握手

    三次握手就是为了确认客户端和服务器双方的接收和发送能力都正常.
    客户端和服务端之间, 经过三次交互, 完成了连接的建立(见面,你好,握手嘛), 三次握手是抽象的比喻:

    1. 一次握手, 就相当于完成一次交互, 也就是客户端先发送一个SYN同步报文
    2. 服务端接收到SYN同步报文后, 返回SYN同步报文和ACK应答报文给客户端
    3. 客户端接收到AKC应答报文后,此时客户端发送和接收数据功能正常, 客户端接收到SYN同步报文后, 客户端为了表示接收数据正常, 就会发送一个ACK应答报文给服务端.
      流程如下:
      在这里插入图片描述

    同步报文:
    TCP协议的首部有六个标志位
    在这里插入图片描述
    应答报文:
    在这里插入图片描述
    明明双方一共发送了四次数据, 问什么说是三次握手呢, 这是因为中间的一次 SYN同步报和ACK应答是一起返回的, 所以说是三次握手.
    总结, 三次握手的意义:1. 确定双方接收发送数据的能力正常 2.协商数据传输的重要参数

    为什么是三次握手
    1. 假设建立TCP连接仅需要两次握手,那么如果第二次握手时,服务端返回给客户端的确认报文丢失了,客户端这边认为服务端没有和他建立连接,而服务端却以为已经和客户端建立了连接,并且可能向服务端已经开始向客户端发送数据,但客户端并不会接收这些数据,浪费了资源。如果是三次握手,不会出现双方连接还未完全建立成功就开始发送数据的情况。
    2. 如果服务端接收到了一个早已失效的来自客户端的连接请求报文,会向客户端发送确认报文同意建立TCP连接。但因为客户端并不需要向服务端发送数据,所以此次TCP连接没有意义并且浪费了资源。
    断开连接的方法
    四次挥手

    挥手, 可以形象的认为是再见, 也就是断开连接.
    所谓四次, 就是客户端和服务器双方各自发送一个FIN结束报文和接收一个ACK应答报文, 这样完成四次挥手后, 断开连接.
    在这里插入图片描述
    此处我们可以看到 中间的FIN结束报文 和 ACK应答报文 并没有结合到一起. 所以是四次挥手.

    为什么连接要握手三次, 断开连接要挥手四次?
    因为需要确保通信双方都能通知对方释放连接,假设客服端发送完数据向服务端发送释放连接请求,当客服端并不知道,服务端是否已经发送完数据,所以此次断开的是客服端到服务端的单向连接,服务端返回给客户端确认报文后,服务端还能继续单向给客户端发送数据。当服务端发送完数据后还需要向客户端发送释放连接请求,客户端返回确认报文,TCP连接彻底关闭。所以断开TCP连接需要客户端和服务端分别通知对方并分别收到确认报文,一共需要四次。
    客户端发出第四次挥手的确认报文后要等2MSL的时间才能释放TCP连接, 为什么呢?
    MSL的意思是报文的最长寿命,可以从两方面考虑:

    1. 客户端发送第四次挥手中的报文后,再经过2MSL,可使本次TCP连接中的所有报文全部消失,不会出现在下一个TCP连接中。
    2. 考虑丢包问题,如果第四挥手发送的报文在传输过程中丢失了,那么服务端没收到确认ack报文就会重发第三次挥手的报文。如果客户端发送完第四次挥手的确认报文后直接关闭,而这次报文又恰好丢失,则会造成服务端无法正常关闭。

    滑动窗口

    滑动窗口是在TCP可靠性的前提下, 尽量提升传输效率. 这个提高传输效率的本质是就是把等待ACK的时间叠加起来, 减少了等待时间.

    等待时间, 等待的就是数据传输和发送过程中的时间. 这是占用的大部分时间.
    所以我们使用滑动窗口进行数据的批次发送, 从而减少等待的时间.
    在这里插入图片描述
    假设发送方一次发四组数据(1000,2000,3000,4000), 然后接收方一起返回(1001,2001,3001,4001)的应答报文, 但是并不是要全接收到这四个应答报文才能继续发送, 只要返回了1001这一起始应答报文, 发送方就可以发送5000这一个数据, 但是如果起始报文1001丢失, 那么就要重新发送1000, 并且等待1001应答报文重新返回.
    此处可以看视频理解一下.

    https://www.bilibili.com/video/BV1FE411C7dk?spm_id_from=333.337.search-card.all.click&vd_source=baed8503050d4848a91c4ca352c8dc9b

    丢包

    丢包分为两种情况:

    1. ACK应答报丢失
    2. 数据包丢失
    ACK丢失

    在这里插入图片描述
    如果是ACK丢失, 类似1001应答报文丢失, 但是 2001应答报文接收到了, 我们就认为1000数据也发送到了, 也就是ACK报文可以通过后续的ACK报文确认.

    数据包丢失

    1.在这里插入图片描述
    由于 1001-2000 这个数据丢了,所以 B 就再反复索要 1001 这个数据。即使 A 给 B 已经发后面的数据了,这个时候 B 仍然再索要 1001 这个数据.

    当 A 被 B 索要多次之后,A 就明白了这个数据丢了,就会触发重传.
    一直到B接收到1001-2000数据后, 就会返回7001的应答报文.

    流量控制

    流量控制本质上就是对滑动窗口的制约, 同时也又考虑了可靠性, 滑动窗口的窗口越大, 那么数据发送的就越快, 那么流量控制就是对发送速率做制约.

    1. 发送方发送的速率越快, 接收方接受的速率如果跟不上, 那么就会发生数据丢失
    2. 流量控制要做的就是使发送方和接收方的速率相当, 根据接收方接收数据缓冲区的剩余空间大小来衡量数据发送速率的大小
    3. 接收缓冲区剩余空间的大小会在返回的ACK报文中带上这个信息(即TCP首部的16位窗口大小,如果接收方反馈的窗口大小是 0, 就表示接收方的缓冲区没有空间了,不过当发送方知晓接收方缓冲区没有空间时, 发送方也会发送一个探测报文来确定是否缓冲区真的没有空间了)
      在这里插入图片描述

    拥塞控制

    流量控制, 是站在接收方的角度, 来控制发送效率.
    但是整体的传输, 不仅在于接收方和发送方的速率, 也取决于中间一系列用于转发的设备.
    在这里插入图片描述
    那么, 我们如何知道多少的数据流量(窗口大小)才是最合适的呢?
    这就需要我们通过做实验的方式来得到最合适的窗口大小:

    1. 首先我们按照小的窗口发送
    2. 如果不丢包, 就说明网络比较通畅, 就可以逐渐增加窗口的大小
    3. 当放大到一定程度时, 速率较快, 窗口较大, 网络就容易出现拥堵, 就容易丢包, 当发送方发现丢包后, 就逐渐减小发送的窗口, 直到达到一个动态的平衡.
      在这里插入图片描述
      一开始指数增长是因为,初始窗口太小,而我们实际上可能触发丢包的值很大.因此,指数增长就可以帮我们快速找到,丢包的界限.
      但是增长到一定的程度时,就会进入线性增长。因为即将达到丢包的界限,如果再来指数增长,就可能一次越界,直接触发丢包.
      当线性增长达到丢包的界限,发生丢包之后,就让拥塞窗口立即变小,回归到初始窗口的大小.一次变得很小之后,也就是希望这次传输一定能成功.

    延时应答

    延时应答也是一个提高效率的机制, 延时应答, 就是为了使窗口可以大一些.
    延时应答, 顾名思义, 就是将ACK应答报文的发送时间减后, 使发送ACK应答报文的这边可以处理缓冲区的数据, 使缓冲区更大, 从而使数据一次传输的量更大.

    捎带应答

    捎带应答说基于延时应答的基础上, 为了提高传输数据而产生的.
    正常来说, ACK报文是应该立即返回的, 但是基于上文的延时应答, 我们可以将ACK应答报文和响应数据一起返回, 从而减少等待数据传输等待的总时间.
    在这里插入图片描述

    面向字节流

    面向字节流, 指的是读写载荷数据的时候, 是按照"字节流"的方式来读写的,但是 TCP数据报, 本身仍是以数据报的形式传输的(应用程序是感知不到哪里到哪里是一个数据报的)

    粘包问题

    粘包问题指的是, 一个TCP连接里, 传输多个应用层数据报, 这时候就容易区分不出哪里到哪里是一个完整的数据报.

    在这里插入图片描述
    粘包问题的根本原因是TCP面向字节流, 直接影响的是应用层代码
    粘包问题的解决方案:

    1. 使用分割符
    2. 约定长度
      也就是指定应用层协议.

    TCP异常处理

    1. 进程终止

    进程终止就相当于在任务管理器中关闭程序,
    就会触发 杀死进程-> 释放进程PCB -> 释放文件描述符表上对应的资源, 然后出发FIN, 并进行四次挥手.

    2. 主机关机

    主机关机之前会先关闭进程, 即先出发上文的进程终止.

    3. 程序崩溃

    也是需要释放进程的资源, 并四次挥手

    4. 主机掉电

    如果是台式机掉电, 那么连接直接就断开, 也就来不及挥手了
    a. 如果台式机是接收方: 发送方尝试发送数据, 发现没有ACK, 会多次传输数据, 当一直没又ACK时, 会知晓网络出现了问题, 也就会断开连接
    b. 如果台式机时发送方: 接收方一直在等待发送方的数据传输, 但是发送方出现了问题, 这时候数据长时间没有传输, 这时候接收方就会发送一个心跳包.
    心跳包: 是周期性的, 判断对方是否存活的报文
    接收方给发送方发送一个特殊的报文(ping),
    发送方如果存活, 就应该返回一个特殊的报文(pong)
    如果没有返回, 就认为发送方挂了

    TCP和UDP的对比

    1. 如果优先考虑可靠性, 优选TCP
    2. 如果传输的单个数据报比较大(UDP的上限是64KB), 优选TCP
    3. 如果对可靠性要求不高, 但是对效率要求很高, 使用UDP

    网络层协议(IP协议)

    网络层协议的工作:

    1. 路由选择

    2. 地址管理
      IP协议报头:
      在这里插入图片描述

    3. 4位版本号 : 只有 4 和 6 --> ipv4 ipv6

    4. 4位首部长度: IP报头的长度

    5. 8位服务类型:
      在这里插入图片描述

    6. 16位总长度: 指的是一个IP数据报又多长(报头 + 荷载), 荷载就是一个(完整的TCP数据报)
      在这里插入图片描述
      在这里插入图片描述

    7. 8位协议: 表示了传输层使用了哪些协议

    8. 16位首部检验: 这个检验是对首部的检验, 对数据部分的检验由传输层负责

    IP地址分为两部分: 网络号 + 主机号

    1. 网络号: 描述了当前网段的信息(局域网的标识)
    2. 主机号: 区分局域网内的主机

    要求: 同一个局域网里的网络号是相同的, 主机号是不同的. 两个相邻的局域网, 网络号是不同的.
    但是对于一个32位的IP地址来说, 到底前多少个bit位是网络号是不固定的, 我们也就引入了 “子网掩码” 来表示前多少个bit位是网络号.
    子网掩码: 32位, 用点分十进制来表示的整数

    1. 子网掩码的左侧都是1, 右侧都是0.(不会混乱)
    2. 左侧的1表示哪些是网络号, 剩下的0的位置是主机号.
      常见的子网掩码就是 255.255.255.0,如果一个局域网设备多了,子网掩码就会出现一些其他值

    特殊IP地址

    a. 如果主机号全为0, 就表示该IP为网络号
    b. 如果IP的主机号为1, 那么该IP就是一个"广播IP", 往这个IP上发的信息, 整个局域网都能收到.
    c. IP地址是127开头的, 就是环回IP表示主机自己
    d. 局域网内部IP: 10 开头 或192.168 开头或172.16-172.31 开头
    e. 广域网的IP(外网IP), 是唯一的, 一个IP对应唯一一个设备.

    IP地址不够用

    当前的 IPv4 协议,使用的地址是 32 位的整数。32 位整数表示的数据范围,就是 42亿9千.但是当前世界的网络设备远远超过这个数字, 所以就有了其他方法:

    1. 动态分配IP地址(DHCP): 一个设备上网的时才有IP, 不上网的时候没有IP
    2. NAT机制: 用一个外网IP来代表一大批的内网IP
    3. IPv6(终极方案): IPv6相当于另一个网络层协议, 和IPv4是完全不同的协议, IPV6 在报头中使用了更长的字段来表示 IP地址,使用 16 个字节来表示。16个字节,128位,之前是 4个字节,32位. IPv6 比 IPv4 能表示的多很多很多.

    路由选择

    路由选择也就是规划路径,当两个设备之间,要找出一条通道,能够完成传输的过程, 类似于"问路",一跳一跳进行转发.
    路由器内部维护了一个数据结构(路由表),记录了一些网段信息(网络号)

    ARP协议

    ARP协议属于网络层的协议,主要作用是实现从IP地址转换为MAC地址。在每个主机或者路由器中都建有一个ARP缓存表,表中有IP地址及IP地址对应的MAC地址。先来看一下什么时IP地址和MAC地址:
    IP地址:IP地址是指互联网协议地址,IP地址是IP协议提供的一种统一的地址格式,它为互联网上的每一个网络和每一台主机分配一个逻辑地址,以此来屏蔽物理地址的差异。
    MAC地址:MAC地址又称物理地址,由网络设备制造商生产时写在硬件内部,不可更改,并且每个以太网设备的MAC地址都是唯一的。

    数据链路层

    数据链路网的主要协议是: 以太网. 每个网卡都有一个唯一的mac地址, mac地址是唯一的, 在出厂时就固定了.
    在这里插入图片描述
    mac地址是6个字节的, 所以足够.

    1. mac地址,表示传输过程中相邻两个设备的关系
    2. IP 用来表示一次传输过程中的起点和终点
    3. mac 用来表述传输过程中,任意两个相邻节点之间的地址(一个以太网数据帧,在每次转发过程中,源 mac 和 目的 mac 都会改变)

    有了IP地址,为什么还要用MAC地址?

    简单来说,标识网络中的一台计算机,比较常用的就是IP地址和MAC地址,但计算机的IP地址可由用户自行更改,管理起来相对困难,而MAC地址不可更改,所以一般会把IP地址和MAC地址组合起来使用。具体是如何组合使用的在上面的ARP协议中已经讲的很清楚了。

    DNS协议

    DNS的定义:DNS的全称是(domain name system),即域名系统。DNS是因特网上作为域名和IP地址相互映射的一个分布式数据库,能够使用户更方便的去访问互联网而不用去记住能够被机器直接读取的IP地址。比如大家访问百度,更多地肯定是访问 www.baidu.com ,而不是访问112.80.248.74,因为这几乎无规则的IP地址实在太难记了。DNS要做的就是将www.baidu.com解析成112.80.248.74。

    DNS工作流程

    1. 在浏览器中输入www.mianshi.online域名,操作系统会先检查自己本地的hosts文件是否有这个域名的映射关系,如果有,就先调用这个IP地址映射,完成域名解析。
    2. 如果hosts文件中没有,则查询本地DNS解析器缓存,如果有,则完成地址解析。
    3. 如果本地DNS解析器缓存中没有,则去查找本地DNS服务器,如果查到,完成解析。
    4. 如果没有,则本地服务器会向根域名服务器发起查询请求。根域名服务器会告诉本地域名服务器去查询哪个顶级域名服务器。
    5. 本地域名服务器向顶级域名服务器发起查询请求,顶级域名服务器会告诉本地域名服务器去查找哪个权限域名服务器。
    6. 本地域名服务器向权限域名服务器发起查询请求,权限域名服务器告诉本地域名服务器www.mianshi.online所对应的IP地址。
    7. 本地域名服务器告诉主机www.mianshi.online所对应的IP地址。
  • 相关阅读:
    K8S 安全机制
    2022 年 8 月 GameFi 报告
    基于C#语言的一款录屏转GIF工具(C#源码)
    统计学习、机器学习以及python的学习顺序是什么
    【刷题笔记】之牛客面试必刷TOP101(1)
    从c++到Java,关于Java面向对象基础的学习(一)
    JS 原型的原理
    功能测试与性能测试的区别是什么?
    5-MySQL常用查询语句,集合函数,分组统计,分页查询
    最新Next14 路由处理器 Route Handlers
  • 原文地址:https://blog.csdn.net/m0_62476684/article/details/126466779