网络协议笔记(一)

目录


1. 基本介绍


1.1 网络互连模型

- 应用层: Application
    * 协议: FTP, HTTP, SMTP, DNS, DHCP
    * 报文,用户数据
- 运输层: Transport
    * 协议: TCP, UDP
    * 段, segments
- 网络层: Network
    * 协议: IP
    * 包,Packet
- 数据链路层: Data Link
    * 帧(Frames)
- 物理层: Physical
    * 比特流(Bits)

1.2 同一网段,同一广播域计算机连接方式
  • 通信基础

    1. 知道对方的IP地址
    2. 最终是根据MAC地址传输数据到网卡,被网卡接收
        2.1 如果网卡发现MAC地址是自己的地址,会传输到上一层进行处理
        2.2 如果网卡发现MAC地址不是自己,则会将数据丢弃
    
  • 网线直连

    需要使用交叉线

  • 同轴电缆

    1. 半双工通信
    2. 容易冲突,不安全
    
  • 集线器(Hub)
1. 集线器,没有智商,没有存储功能(和同轴电缆一样)
2. 半双工通信
  • 网桥(Bridge)
1. 可以知道两侧接口的MAC地址
2. 起到隔绝冲突域的作用
  • 交换机(Switch)

    1. 相当于接口更多的网桥
    2. 全双工通信
    3. 比集线器安全
    

1.3 不同网段,不同广播域计算机连接方式
  • 路由器(Router)

    1. 可以在不同的网段之间转发数据
    2. 隔绝广播域
    



2. MAC地址 & IP地址

2.1 MAC地址
  • MAC地址:

    1. 6字节,48bit;全球唯一
    2. 固化在网卡的ROM中
    3. 前三个字节: 组织唯一标识符,厂商的标志,OUI
    4. 后三个字节: 网络接口标识符,由厂商分配
    5. 当48位全部为1是,代表广播地址:FF:FF:FF:FF:FF:FF
    
> _KP:  广播地址**(FF:FF:FF:FF:FF:FF)**_
  • MAC地址的获取

    1. 当不知道别人的MAC地址的时候,可以发送**ARP广播来获取对方的MAC地址**
    2. 获取成功后,会缓存IP地址,MAC地址映射信息,称为ARP缓存
    3. 通过ARP广播获取的MAC地址,属于动态缓存(时间较短,默认两分钟后删除)
    

    KP: 发送ARP广播来获取对方MAC地址

  • ARP协议

    1. 地址解析协议,Address resolution Protocol
    2. 通过IP地址获取MAC地址
    

2.2 IP地址
  • IPv4:32bit,4字节
  • IPv6:128bit,16字节
  • IP地址组成

    1. 互联网上的每一个主机都有一个IP地址
    2. 由网络标识(网络ID),主机标识(主机ID)组成;通过子网掩码可以知道网络ID和主机ID
    3. 主机的网段: **子网掩码&IP地址**
    4. 通信前会判断目标主机和自己是否在同一网段,不在同一网段需要交给路由器处理
    
2.2.1 IP地址分类
  • 前提

    1. 只有A,B,C类地址才可以分配给主机
    2. 如果主机ID全为0,表示主机所在的网段
    3. 如果主机ID全为1,表示主机所在网段的全部主机(广播)
    

    KP: 主机ID全部为0,表示主机所在网段

    KP: 主机ID全部为1,表示主机所在网段的全部主机(广播)

  • A类地址

    • 默认子网掩码是255.0.0.0
    • 网络ID:8位(0开头),主机ID:24位

      网络ID: 0不可用,127作为保留网段;其中127.0.0.1是本地环回地址,代表本机地址
      网络ID: 可以分配给主机的取值为1-126
      
    • 主机ID: 第2,3,4部分的取值范围是: 0-255

    • 每个A类网络能容纳的最大主机数为

      256 256 256 - 2 = 2^24 - 2 = 16777214


  • B类地址

    • 默认子网掩码是255.255.0.0
    • 网络ID: 16位(10开头),主机ID: 16位

      网络ID: 第一个字节可以分配的为 128-191
      网络ID: 第二个字节可以分配的为 0-255
      
    • 主机ID: 第3,4部分的取值范围是0-255

    • 每个B类网络能容纳的最大主机数为

      256 * 256 - 2 = 2^16 - 2 = 65534


  • C类地址

    • 默认子网掩码是:255.255.255.0
    • 网络ID: 24位(110开头),主机ID: 8位
    • 网络ID: 110开头

      网络ID: 可以分配给主机的第一部分,第一个字节的取值范围是 192-223
      网络ID: 第2,3部分的取值范围是0-255
      
    • 主机ID: 第四部分的取值范围是 0-255
    • 每个C类网络能容纳的最大主机数是:

      256-2=254


  • D类地址

    • 没有子网掩码,用于多播,组播地址
    • 网络ID: 32位(110开头)
    • 第一个字节取值为: 224-239


  • E类地址

    • 网络ID: 32位(1111开头)
    • 保留为以后使用
    • 第一个字节地址为: 240-255


2.3 子网掩码
  • CIDR: 无类别域间路由,Classless Inter-Domain Routing
  • 表示方法

    192.168.1.100/24,代表子网掩码有24个1,也就是255.255.255.0

    123.210.100.200/16,代表子网掩码有16个1,也就是255.255.0.0

  • 如何避免浪费IP地址 -> 合理进行子网划分

  • 子网划分
    • 借用主机位作子网位,划分出多个子网,等长子网划分+变长子网划分两种形式
    • 步骤
      • 确定子网的子网掩码长度
      • 确定子网中你那个第一个和最后一个主机可用的IP地址



3. 路由

3.1 概念
  • 在不同的网段之间转发数据,需要路由器的支持
  • 静态路由

    1. 管理员手动添加的路由信息
    2. 适用于小规模网络
    
  • 动态路由

    1. 路由器通过路由选择协议(RIP,OSPF),自动获取路由信息
    2. 适合大规模网络
    
  • 互联网(internet);最大的互联网: 因特网(Internet)

  • ISP(服务提供商): Internet Service Provider

  • 网络分类

    • 按照网络范围进行分类,可分为: 局域网,城域网,广域网
    • 局域网(LAN,Local Area Network)

      1. 一般是范围在几百米到十几公里的计算机网络
      2. 局域网中最广泛的技术是,以太网 Ethernet
      
    • 城域网(MAN, Metropolitan Area Network)

      1. 一般可以覆盖一个城市
      
    • 广域网(WAN, Wide Area Network)

      1. 一般都需要租用ISP路线
      
  • 上网方式

    1. 猫(Modem),用于ADSL(电话线上网),将数字信号和模拟信号转换
    2. 光猫(Optical Modem),光调制解调器,用于光纤入户使用,将数字信号和光信号进行转换
    

3.2 公网IP&私网IP
  • IP地址分为公网IP,私网IP

    • 公网IP

      1. Internet上的路由器只有到达公网的路由表,没有到达私网的路由表
      2. 公网IP由Internet NIC,_统一分配和管理_
      3. ISP需要申请公网IP
      
    • 私网IP

      1. 主要用于局域网
      2. A类网络保留私网网段: 10.0.0.0/8, 1个A类网络
      3. B类网络保留私网网段: 172.16.0.0/16 - 173.31.0.0/16, 16个B类网络
      4. C类网络保留私网网段: 192.168.0.0/24 - 192.168.255.0/24, 256个C类网络
      
  • NAT(Network Address Translation)

    • 私网IP访问Internet需要进行NAT转换为公网IP
    • 由路由器来完成
    • 特点

      1. 可以节约公网IP地址
      2. 可以隐藏内部IP
      
    • 分类

      • 静态转换: 手动配置NAT映射表,一对一转换
      • 动态转换: 定义外部地址池,动态随机转换,一对一转换
      • PAT(Port Address Translation): 目前主要应用

        1. 多对一转换,最大程度节约公网IP资源
        2. 端口多路复用,通过端口号标示不同的数据流
        3. 目前应用最广泛的NAT实现方式
        



4. 物理层和数据链路层

4.1 物理层
  • 物理层定义了: 接口标准,线缆标准,传输速率,传输方式
  • 模拟信号

    1. 适合长距离传输,连续的信号
    2. 抗干扰能力差,受到干扰时波形变动难以纠正
    
  • 数字信号

    1. 不适合长距离传输,离散的信号
    2. 抗干扰能力强,受到干扰时波形失真可修复
    
  • 数据通信模型

    • 局域网: 网线长度不能超过100m
    • 广域网:(数字信号-模拟信号-数字信号)
  • 信道(channel)

    • 信息传输的通道,一条传输介质(网线),可以有多条信道
    • 单工通信

      1. 信号只能朝着一个方向传输,且不能改变传输方向
      2. 使用场景: 无线电广播,有线电视广播
      
    • 半双工通信

      1. 信号可以双向传输
      2. 但是必须是交替进行,同一时间只能一个方向传输
      3. 使用场景: 对讲机
      
    • 全双工通信

      1. 信号可以同时双向传输
      2. 使用场景: 电话
      

4.2 数据链路层
  • 链路: 从一个节点到相邻节点的一段物理线路(有线或者无线),中间没有其他交换节点
  • 一条链路上传输数据,需要对应的通信协议来控制数据的传输
  • 不同类型的数据链路,所用的通信协议可能是不同的

    1. 广播通道: CSMA/CD协议        
    2. 点对点信道: PPP协议
    
  • 3个基本问题

    • 封装成帧

      1. 最大传输单元(MTU),每一种数据链路层协议都规定了传送帧的数据部分的长度上限
      2. 以太网的MTU为1500字节
      
    • 透明传输

      1. SOH(start of header),作为帧开始符
      2. EOT(end of transmission),作为帧的结束符
      3. 数据部分一旦出现EOT,就需要进行转义(填充字节,在接收端去除转义字符)
      
    • 差错检验(FCS)

      1. FCS是根据数据部分+数据链路层首部计算出来  
      
  • CSMA/CD协议
    • 载波侦听多路访问/冲突检测
    • 使用了CSMA/CD的网络可以称为以太网,传输的是以太网帧
    • 格式: Ethernet V2(使用广泛) & IEEE802.3
    • 为了检测正在发送的帧数据是否发生了冲突,以太网的帧至少要64字节
    • 用交换机组建的网络,已经支持全双工通信,不需要再使用CSMA/CD,但是传输的帧依然是以太网帧
  • Ethernet V2
    -格式

    ![](https://forbloghexo-1258063746.cos.ap-guangzhou.myqcloud.com/%E7%BD%91%E7%BB%9C%E5%8D%8F%E8%AE%AE/2021-02-15_10-19-46.jpg)
    
        1. 首部: 目标MAC + 源MAC + 网络类型
        2. 以太网帧: 首部 + 数据部分 + FCS
        3. 数据的长度最小为 64 - 6(目标MAC) - 6(源MAC) - 2(网络类型) - 4(FCS) = 46字节
        4. 当数据部分长度小于46字节时,数据链路层会在数据部分在一些填充
    ![](https://forbloghexo-1258063746.cos.ap-guangzhou.myqcloud.com/%E7%BD%91%E7%BB%9C%E5%8D%8F%E8%AE%AE/2021-02-15_10-21-19.jpg)
    
    • 长度总结

      1. 以太网帧的数据长度: 46-1500字节
      2. 以太网帧的长度: 64-1518字节 (18字节为:目标MAC+源MAC+网络类型+FCS)
      
  • 网卡

    负责功能: 帧的封装与拆封,帧的差错校验,介质访问控制

    1. 网卡接收到一个帧,会先进行差错校验,校验通过则接收,负责则丢弃
    2. 接收到的帧,硬件会去除帧尾的FCS信息
    3. 抓包工具抓不到差错校验失败的工具
    
  • PPP协议(Point to Point Protocol)

    • 点对点协议帧首部不需要: 目标MAC和源MAC

      1. Address字段: 0xFF,没有实际意义,不需要目标MAC和源MAC
      2. Control字段: 0x03,目前没有作用
      3. Protocol字段
      4. 帧开始符,结束符: 0x7E,如果帧数据内容部分有0x7E内容也需要做内容填充
      



5. 网络层

  • 网络层数据包(IP数据包,Packet),由数据和首部两部分组成

    数据部分多为传输层传下来的数据段(segment)

  • 网络层首部: 版本

    1. 4位
    2. IPv4(0b0100) || IPv6(0b0110)
    
  • 网络层首部: 首部长度

    1. 4位,二进制值乘以4才是最终长度
    2. 最小值: 0b0101 -> 20
    3. 最大值: 0b1111 -> 60
    
  • 网络层首部: 区分服务

    1. 8位
    2. 用途: 提高网络服务质量
    
  • 网络层首部: 总长度

    ![](https://forbloghexo-1258063746.cos.ap-guangzhou.myqcloud.com/%E7%BD%91%E7%BB%9C%E5%8D%8F%E8%AE%AE/Xnip2021-02-15_16-40-43.jpg)
    
    1. 16位
    2. 首部+数据的长度之和,最大值为65535
    3. 网络层的数据部分和首部成为数据链路层帧的数据部分
    4. 帧的数据部分不能超过1500字节,过大的IP数据包需要分片(fragment)传给数据链路层
    5. 分片后每一片fragment都有自己的数据层首部
    
  • 网络层首部: 标识

    1. 16位,数据包的ID
    2. 当一个数据包过大时,分片后每一片的标识ID都一样
    3. 由专门计数器管理数据包ID,每发送一个数据包.ID+1
    
  • 网络层首部: 标志

    1. 3位,主要用于处理分片信息
    2. 第一位,保留
    3. 第二位(DF,Don't Fragment): 0代表允许分片,1代表不允许分片
    4. 第三位(MF, More Fragments): 0表示是最后一片,1表示不是最后一片
    
  • 网络层首部: 片偏移

    1. 13位
    2. 片偏移乘以8,字节偏移
    3. 每一片的长度一定是8的整数倍
    

    KP: 每一片的长度一定是8的整数倍

    ![](https://forbloghexo-1258063746.cos.ap-guangzhou.myqcloud.com/%E7%BD%91%E7%BB%9C%E5%8D%8F%E8%AE%AE/Xnip2021-02-15_16-58-36.jpg) 
    
  • 网络层首部: 生存时间

    1. 8位,Time To Live
    2. 每个路由器转发之前会将TTL减1,一旦TTL减为0,路由器会返回错误报告
    
  • 网络层首部: 协议

    1. 8位
    2. 表明所封装的数据是使用了什么协议
    

  • 网络层首部: 首部检验和

    1. 16位
    2. 用于检查首部是否有错误
    



6. 传输层

  • 协议

    1. TCP: Transmiss Control Protocol, 传输控制协议
    2. UDP: User Datagram Protocol, 用户数据报协议
    

6.1 UDP协议
  • UDP是无连接的,减少了建立和释放连接的开销
  • 不保证可靠传输(因此不需要首部维护一些复杂参数)
  • 首部只有8个字节

    • UDP长度

      1. 2字节,16位
      2. 首部的长度+数据的长度
      
    • UDP检验和

      1. 检验和的计算内容: 伪首部 + 首部 + 数据
      2. 伪首部: 只在计算检验和起作用,并不会传递给网络层
      

    • _端口_

      1. 2个字节.取值范围: 0 - 65535
      2. 客户端的源端口是临时开启的随机端口(不同协议有不同默认端口号)
      3. HTTP协议默认端口是80; HTTPS协议默认端口是443            
      


6.2 TCP首部
  • 首部长度是: 20-60字节

  • 首部: 数据偏移(Data offset)

    1. 4位,取值范围是0x0101-0x1111
    2. 数据偏移的值乘以 4 是首部的实际长度
    3. 首部的长度20-60字节
    
    • 问题1: UDP首部有16位字段记录UDP报文段的长度(首部+数据);TCP首部仅4位偏移量字段记录了TCP报文段的首部长度,并未记录TCP报文段的数据长度?

      1. UDP中的16位记录UDP长度的字段是冗余的,纯粹是为了保证首部是32位对齐
      2. TCP/UDP的数据长度,可以由IP数据包的首部推测出来: 传输层的数据长度 = 网络层的总长度 - 网络层首部的长度 - 传输层的首部长度
      
  • 首部: 保留(Reserved)

    1. 6位,目前都是0
    2. 部分资料中,TCP首部的保留字段占3位,标志字段占9位
    
  • 首部: 检验和(Checksum)

    1. 和UDP一致,TCP检验和的计算内容: 伪首部 + 首部 + 数据
    2. 伪首部: 占用12字节,不会传递给网络层
    
  • 首部: 标志位(Flags)

    • URG(Urgent)

      1. 当URG=1时,紧急指针字段才有效,表明当前报文段中有紧急数据,应优先尽快传送
      
    • ACK(Acknowledgment)

      1. 当ACK=1时,确认号字段才有效
      
    • PSH(Push)

    • RST(Reset)

      1. 当RST=1时,表明连接中出现了差错,需要释放连接,再重新建立连接
      
    • SYN(Synchronization)

      1. 当SYN=1,ACK=0时,表明这是一个建立连接的请求
      2. 若对方同意建立连接,则返回SYN=1,ACK=1
      
    • FIN(Finish)

      1. 当FIN=1时,表明数据已经发送完毕,要求释放连接
      
  • 首部: 需要(Sequence Number)

    1. 占4个字节
    2. 建立连接后,序号代表,这一次传给对方的TCP数据部分的第一个字节的编号
    
  • 首部: 确认号(Acknowledge Number)

    1. 占4个字节
    2. 建立连接后,确认好代表,期望对方下一次传的TCP数据部分的第一个字节的编号
    
  • 窗口: (Window)

    1. 占2个字节
    2. 流量控制功能,告知对方下一次发送的数据的上限(单位为字节)
    
  • 序号,确认号

    1. 建立连接时,接收方的确认ack为发送方的seq+1
    






6.3 TCP:可靠传输
  • 停止等待ARQ协议

    1. ARQ: automatic repeat-request, 自动重传请求
    2. 包如果重传了多次没有收到确认,还是失败,不会一直重传,会根据系统设置,重传多次后未成功就发送reset报文(RST)断开TCP连接
    
![](https://forbloghexo-1258063746.cos.ap-guangzhou.myqcloud.com/%E7%BD%91%E7%BB%9C%E5%8D%8F%E8%AE%AE/Xnip2021-02-17_16-17-39.jpg)

![](https://forbloghexo-1258063746.cos.ap-guangzhou.myqcloud.com/%E7%BD%91%E7%BB%9C%E5%8D%8F%E8%AE%AE/Xnip2021-02-17_16-17-52.jpg)
  • 连续ARQ协议 + 滑动窗口协议

    1. 停止等待ARQ协议: 发送一个分组就停止发送等待确认
    2. 连续ARQ协议和滑动窗口协议: 发送窗口中的分组连续发送完后,停止等待确认
    
    • 问题1: 如果接受放最多接受4个包,但发送方只发了2个包,接收方如何确定后面还有没有剩余两个包?

      1. 接受方仔等待一段时候后没有收到第三个包
      2. 就会返回确认收到的2个包给发送方
      
  • SACK选择性确认

    1. 在TCP通信过程中,如果发送序列中(1,2,3,4)某个数据包丢失,比如3丢失
    2. TCP会根据重传最后确认的分组后续的分组(最后确认的是2,会重传3,4)
    3. 这样原来已经正确传输的分组比如分组4也会重新发送,降低了TCP性能
    
    • 为了解决上述问题, 发展出了SACK(Selective acknowledgment)选择性确认技术
    • 告诉发送方哪些数据丢失,哪些数据已经提前得到
    • 使TCP只需要重新发送丢失的包,而不需要重新发送丢失的包后面的所有分组序列
    • SACK信息会放在TCP首部的选项部分

      1. Kind,1字节,值为5表示SACK选项
      2. Length,1字节
      3. Left Edge,4字节,左边界
      4. Right Edge,4字节,右边界
      


    • 一对边界占用8个字节,由于TCP首部的选项部分最多40字节

      1. SACK选项最多携带4组边界信息
      2. SACK选项最多占用字节数 4*8 + 2 = 34
      
    • 问题: 为什么要在传输层就将数据分成多组,而不是等到网络层再分片传递给数据链路层?

1. 可以提高重传性能
2. 可靠传输是在传输层进行控制的
3. 如果传输层不分段,一旦数据丢失,整个传输层的数据都需要重传
4. 如果传输层分了段,一旦数据丢失,只需要重传丢失部分即可

6.4 TCP:流量控制
  • 目的:

    1. 接收方缓存区已满,发送方还在发送数据
    2. 接收方只能吧接收到的数据包丢掉,大量丢包会造成网络资源浪费
    3. 因此需要进行流量控制
    
  • 什么是流量控制: 让发送方的发送速率不要太快,让接收方来得及接收处理

  • 原理

    1. 确认报文中窗口字段来控制发送方的发送速率
    2. 发送方的发送窗口不能大于接收方的接收窗口
    3. 发送方接收到的窗口大小为0时,发送方停止发送数据
    
  • 特殊情况

    1. 建立连接后,接收方给发送方发送了窗口为0的报文段,但是后续接收方有了存储空间,给发送方发送了窗口非0的报文丢失了,发送方因为接收窗口为0,无法发送数据,如何解决? 
    

    解决方案: 1. 发送方收到0窗口报文时,停止发送报文;

    1. 同时开启一个定时器,一定间隔下会发测试报文去询问接收方最新的窗口大小;
    2. 如果接收方窗口仍为0,会再次刷新定时器;
  • 点对点的通信控制


6.5 TCP:拥塞控制
  • 目的

    1. 防止过多的数据注入网络中
    2. 防止互联网中的路由器和链路过载
    
  • 拥塞控制是一个全局性的控制

    1. 涉及到所有主机和路由器以及降低网络传输性能有关的因素
    
  • 方法

    • 专有名词

      1. MSS(Maximum Segment Size),每个段最大的数据部分大小,在建立连接是确定
      2. cwnd(congestion window),拥塞窗口
      3. rwnd(receive window),接收窗口
      4. swnd(send window),发送窗口,swnd=min(cwnd,rwnd)
      5. 当rwnd<cwnd,是接收方接收能力限制了发送窗口的最大值
      6. 当cwnd<rwnd,是网络的拥塞限制了发送窗口的最大值
      
    • 慢开始(slow start)

    • 拥塞避免(congestion avoidance)
    • 快速重传(fast retransmit)
    • 快速恢复(fast recovery)
  • 慢开始(slow start)

    cwnd初始值较小,随着数据包被接收方确认后,cwnd指数增长


  • 拥塞避免(congestion avoidance)

    • ssthresh(slow start threshold): 慢开始阀值,cwnd达到阀值后,已线性增加窗口
    • 拥塞窗口缓慢增大(加法增大),以防止网络过早出现拥塞
    • 只要网络出现拥塞,把ssthresh_减为拥塞峰值的一半,同时执行慢开始算法(cwnd,恢复为原有的初始值)_
    • 网络出现频繁拥塞时,ssthresh值就下降的很快

  • 快速重传(fast retransmit)

    • 接收方

      1. 收到一个失序的分组就立即发出重复确认
      2. 让发送方即使知道有分组没有到达,不要等待到下一次自己发送数据才确认
    • 发送发

      1. 连续收到三个重复确认(共四个),立即重传接收方未收到的报文段
      2. 不需要等待计时器重传到期后再重传

  • 快速恢复(fast recovery)

    1. 发送方连续收到三个重复确认,说明网络出现拥塞;执行乘法减小算法,把ssthresh减为拥塞峰值的一半
    2. 与慢开始不同是,cwnd不恢复到初始值;而是将cwnd值设为新的ssthresh值,再开始将拥塞窗口缓慢的线性增大
    
  • 快重传+快恢复

    1. 当执行拥塞乘法减小后,不重新开始慢开始,拥塞避免等方式;
    2. 而是降低ssthresh,继续执行拥塞避免,线性增加cwnd
    


6.6 TCP:建立连接
  • 3次握手
  • 流程

  • 状态

    • CLOSED: client处于_关闭_状态
    • LISTEN: server处于_监听_状态,等待client连接
    • SYN-RCVD: 表示server接收到了SYN报文,当收到client的ACK报文后,会进入到ESTABLISH状态
    • SYN-SENT: 表示client已发送SYN报文,等待server的二次握手
    • _ _ESTABLISH__: 表示连接已建立
  • 前两次握手的特点

    1. SYN都设置为1
    2. 数据部分长度都为0
    3. TCP头部长度一般是32字节,头部固定20字节 / 选项部分12字节
    4. 双方会交换一些信息(比如MSS,是否支持SACK,WindowScale窗口缩放系数等),这些数据都放在TCP头部选项中
    5. 头部选项部分占用12字节
    
  • 问题1: 2次握手是否可行?为什么一定要3次握手

    1. 3次的目的是: 防止server一直等待,浪费资源
    2. 如果只需要2次握手,会出现如下情况
        2.1 假设client发出第一个连接请求报文段,因为延迟,在连接释放后才到达server
        2.2 本来是一个早已失效的连接请求,但是server收到此失效的请求后,误认为是client再次发出一个新的连接请求
        2.3 server就像client发出确认报文段,同意建立连接
        2.4 如果只采用2次握手,那么server发出确认,既建立连接
        2.5 由于此时client并没有真正想连接服务器,不会给server发送数据
        2.6 但是server已经建立新的连接,一直在等待celient发数据,造成server资源浪费
    
    3. 采用2次握手就可以防止上述现象
        3.1 client收到确认后不向server发出确认,server因为收不到确认,就知道client并没有要求建立连接
    
  • 问题2: 第3次握手失败了,会怎么处理

    1. 此时server的状态为SYN-RCVD,若等不到client的ACK,server会重新发送SYN=1,ACK=1包
    2. 如果server多次重发SYN=1,ACK=1的包,但是未收到client的ACK,会发送RST包,强制关闭连接
    

6.7 TCP:释放连接
  • 4次挥手
  • 流程

  • 状态

    • FIN-WAIT-1: 表示想主动关闭连接,向对方发送FIN报文,进入到FIN-WAIT-1状态
    • CLOSE-WAIT: 表示在等待关闭
      • 当对方发送FIN给自己,自己会回应一个ACK报文给对方,此时进入到CLOSE-WAIT状态
      • 在此状态下,检查考虑是否还有数据需要发送给对方,如果没有,发送FIN报文给对方
    • FIN-WAIT-2: 收到对方的ACK确认报文后,主动断开连接方会进入到FIN-WAIT-2状态,然后等待对方发送FIN报文
    • CLOSING: 一种例外状态
      • 当你发送FIN报文时,未收到对方的ACK报文,反而受到对方的FIN报文
      • 双方几乎同时准备关闭连接,就出现了同时发送FIN报文的情况
      • 会出现CLOSING状态
      • 表示双方都正在关闭连接
    • LAST-ACk: 被动关闭方发送FIN报文后,等待对方的ACK报文

      • 当收到ACK报文后,会进入CLOSED状态
    • _TIME_WAIT_: 表示收到对方的FIN报文,并发送了ACK报文,就等2MSL后进入CLOSED状态

      • 如果FIN-WAIT-1状态下,收到了对方同时带有FIN和ACK标志的报文
      • 可以直接进入到TIME-WAIT状态,无需进入到FIN-WAIT-2
    • CLOSED: 关闭状态

    • 部分状态比较短暂,例如: _SYN_RCVD_, FIN-WAIT-1

  • TCP/IP协议涉及允许任何一方先发起断开连接

  • Client(主动断开方),需要个TIME-WAIT状态,等待一段时间后,在真正关闭连接

    • 一般是2MSL(maximum segment lifetime),最大分段生存期
    • MSL: TCP报文在Internet的最长生存时间
    • 每个具体的TCP实现都需要一个确定的MSL值,官方建议是2mins
    • 可以防止本次连接产生的数据包误传到下一次连接中
    • 如果主动断开方发送ACK后立刻释放了,如果因为网络原因被动断开方未收到ACK,server会重发FIN造成一定问题
  • 问题1: 为什么释放连接的时候吗,要进行4次挥手

    • TCP是全双工模式
    • 第一次挥手: 主机1发出FIN报文段

      1. 主机1发出FIN报文段时,表示主机1告诉主机2,主机1已经没有数据需要发送了,但是主机1还是能接受主机2发送的数据
      
    • 第二次挥手: 主机2返回ACK报文段

      1. 表明主机2已经知道主机1没有数据发送了,但是主机2还是可以发送数据到主机1 
      
    • 第三次挥手: 主机2发送FIN报文段

      1. 表明主机2告诉主机1,主机2已经没有数据需要发送了
      
    • 第四次挥手: 主机1返回ACk报文段

      1. 表明主机1已经知道主机2没有数据发送了,随后正式断开整个TCP连接
      
  • 问题2: 为什么抓包有时只能看到3次挥手

    1. 因为: 第二次和第三次挥手合并
    2. 当被动断开方接收到主动断开方的FIN时,此时无数据发送了
    3. 会将2&3次挥手合并,告诉主动断开方: 已经知道断开方已经没有数据要发了,且自己也没有数据要发送了