计算机网络理论笔记 (3): 传输层 (Transport Layer),UDP和TCP

总览

传输层通常运行在操作系统内核中。
先说一下网络层,网络层可以帮我们在网络中找到合适的转发路径 (从一个主机路由到另一个)。但是其并不保证传输,这种被称为尽力而为 (best effort) 的转发。我们可以将网络层想象为给我们提供了一个函数 send_to_host(data, host),并给我们承诺,数据(通常)都会到达目标主机。
传输层服务和协议提供了在不同主机上运行的应用程序进程之间的逻辑通信 (logical communication)。

传输层协议在终端系统中运行:

  • 发送端 (sender side) : 将应用的消息分解为 段 (segments) 并传递到网络层。
  • 接收端 (receiver side): 将 段 重新组合成 消息,并传输给应用层。

在这里插入图片描述

多路复用/多路分解 (Multiplexing/demultiplexing)

  • 发送方的多路复用: 处理来自多个套接字 (socket) 的数据,添加传输层头部(后来用于多路分解)。
  • 接收方的多路分解: 使用 头部信息 传递 接收到的段 到正确的套接字。

在这里插入图片描述

无连接的多路分解

创建一个带有主机本地端口号的套接字:

DatagramSocket my_socket = new DatagramSocket(12534);

当创建以UDP套接字发送的数据帧时,我们必须指定:

  1. 目标IP地址。
  2. 目标端口号。

当主机接收到UDP数据帧段时,主机会检查段中的目标端口号,并将该UDP段定向到指定端口号的套接字中。这会导致 拥有相同的目标端口号但是来自不同IP和源端口号的帧被定向到同一个目标套接字中。
在这里插入图片描述

连接导向的多路分解

TCP套接字由一个四元组来指定:

  • 源IP地址。
  • 源端口号。
  • 目标IP地址。
  • 目标端口号。

多路分解: 接收者使用上面这四个值将 段 定向到合适的套接字中。

服务器主机会同时支持多个TCP套接字: 每个套接字都被其自身的四元组所定义。Web服务器拥有每一个连接着的客户端的套接字。(非持久HTTP将会在每次请求中拥有不同的套接字)

在这里插入图片描述

UDP (User Datagram Protocol)

UDP属于尽力而为的服务,因为UDP数据段可能会 丢失,以及 不按顺序地 被应用接收到。非连接的特点:

  • 在UDP发送者和接收者之间没有 握手 (handshaking)。
  • 每一个UDP段都独立处理。

UDP头部

在这里插入图片描述
为什么我们需要UDP:

  • 无连接建立 (建立连接可能会增加延迟)
  • 简单 (发送端和接收端的无连接状态)
  • 小的头部大小。
  • 没有拥塞控制 (UDP可以按照需要的速度传递)

UDP校验和 (checksum)

目标: 检测传输段的错误 (如反转位 flipped bits),可能由 路由器内存错误,驱动程序错误或者电磁干扰导致。

做法:

  • 发送端: 将段内容 (包括头部) 视为16位整数的序列。校验和就是段内容的加法 (一个补码之和)。发送端将校验和的值放进UDP头部的检验和区域 (UDP checksum field) 中。
  • 接收端: 将接收到的所有内容相加为16位整数的序列。并将其与校验和相加。如果相加结果不是 1111 1111 1111 1111,则表明传输有错误。

在这里插入图片描述
注意: 相加数字时,需要将最高有效位的进位值添加到结果中。

校验和是 数据,UDP报头 和 IP头部中的伪信息头部的补码和 (complement sum of pseudo header of information) 的 16位补码和,在末尾填充 八个零 已形成 两个 八位位组(octets) 的倍数。
在这里插入图片描述
注: 在TCP中,校验和的计算也是类似的。

校验和例子

在这里插入图片描述

UDP应用

延迟敏感/时间关键的任务:

  • 快速请求/响应 (DNS, DHCP)
  • 网络管理 (SNMP)
  • 路由更新 (RIP)
  • 语音/视频聊天
  • 游戏 (尤其是FPS)

UDP由定期消息 (periodic messages) 管理的纠错。

QUIC (Quick UDP Internet Connnections)

  • 核心思想: 在UDP上的HTTP/2。
  • 更快的连接建立。
  • 克服由于丢失数据包导致的HoL阻塞。
  • 改善拥塞控制。
  • 前向纠错。
  • 连接迁移。

在这里插入图片描述

可靠连接的需求

尽力而为方法会带来的不良反应:

  • 数据包被污染。
  • 数据包丢失。
  • 数据包延迟。
  • 数据包乱序。
  • 数据包重复。

我们将

  • 逐步开发 可靠数据传输协议 (reliable data transfer - rdt) 的接收方和发送方。
  • 考虑单向数据传输 (但控制信息将会双向流动)。
  • 通道不会对报文进行重新排序。

rdt 1.0

在该设计中,必须保证底层通道完全可靠,这包括了无误码和无丢包。实际上,传输层并没有发挥作用。
在这里插入图片描述

rdt 2.0

底层通道将在数据包中翻转一些位 (校验和会检验到位错误)。

如何进行错误恢复:

  • 确认包 (acknowledgements - ACKs): 接收端明确告诉发送者,数据包已经正确收到了。
  • 负确认包 (negative acknowledgements - NAKs): 接收端明确告诉发送者,数据包有错误。
  • 发送者重新传输数据包以作为NAK的回复。

注: rdt 2.0 相比起 rdt 1.0,多了以下机制,错误检测,反馈 (ACK, NAK),重传。
在这里插入图片描述

然而,rdt 2.0依旧有致命缺陷:
ACK/NAK包 被污染的情况。 由于发送端并不能了解接收端发生的事情,这有可能会导致由重传引起的包重复。为了处理 包重复 (duplicate) 现象,发送端可以发送带有序号的数据包,如果接收端收到重复的数据包,就将其丢弃。

rdt 2.1

  • 发送端: 往数据包中添加序号 (seq) (0和1)。并且,检查接收到的ACK/NAK是否被污染了。(状态必须记住期望的数据包是否拥有序号0或者1)
  • 接收端: 必须检查接收到的数据包是否冗余 (状态指示,0或者1是否是期待的数据包序号)。注: 接收端并无法知道其上一个ACK/NAK是否被发送端正确接收。

该版本的新机制: 序列号 (sequence number),ACK/NAK的校验和,冗余检测。

在这里插入图片描述

rdt 2.2 (不需要NAK了!)

rdt 2.2 和 rdt 2.1类似,但是只使用 ACK 了。该方法不使用NAK,接收端为上一个正确接收的数据包发送ACK。接收端必须明确地包含被ACK的数据包的seq号。
在发送端 重复的ACK 会导致重传当前的数据包 (由此可见,重复的ACK 和NAK的效果一致)。
在这里插入图片描述

rdt 3.0

新的假设: 底层通道会导致丢包 (包括数据包,ACK包),就算用上校验和,序列号,确认包和重传都不足以解决该问题。

方法: 发送端等待ACK一段合理的时间。若在该时间段内,发送端没有接收到ACK包,那么就重传。如果数据包或者ACK包只是延迟了,那么重传就会导致冗余,但是seq号已经处理该问题。接收端必须指定已经被确认的数据包的seq号。该方法需要倒计时器 (countdown timer)。对于冗余的ACK没有重传。


在这里插入图片描述
rdt 3.0 是正确的,但是性能较差。协议限制了物理资源的使用。
流水线 (滑动窗口): 发送端允许多个 “正在进行中” 但尚未确认的数据包。序列号范围必须增加。在发送端和接收端需要缓冲。
有两种滑动窗口的协议: go-back-N, selective repeat。

滑动窗口

Go-Back-N

发送端能够在窗口中拥有最多N个数据包。发送端仅拥有单个计时器用于最早的未确认数据包。当计时器到期时,重新传输所有未确认的数据包。接收端上没有可用的缓冲区,乱序的数据包将会被丢弃。接收端仅发送累积确认包 (cummulative ack),如果存在间隙,则不确认新数据包。

在这里插入图片描述

在发送端中,数据包头部拥有 k位 的序列号。ACK(n),确认所有数据包,包括序列号n (可能会接收到冗余的确认包)。计时器对最早的在传输中的数据包有用。当数据包传输超时时 ( timeout(n) ),重传数据包 n 和所有在窗口中序号大于 n 的数据包。
在这里插入图片描述

Selective Repeat

发送端能够在窗口中拥有最多N个数据包。发送端对每个未确认数据包都维持一个计时器。当计时器到期时,仅重新传输未确认的数据包。接收端拥有缓存区,可以接受乱序的数据包。接收端发送单个确认包 (individual ack) 给每个数据包。

接收端独立地确认所有接收到的正确的数据包 (根据需要缓冲数据包,以便最终按照顺序传送到上层)。发送端仅重传没有接收到确认包的数据包 (对每个未确认的数据包,维护发送者计时器)。

在这里插入图片描述
发送端

  • 如果下一个可用的序列号在窗口中,则发送数据包。
  • 超时 timeout(n): 重传数据包n,重新开启该包的计时器。
  • 在 [sendbase, sendbase + N] 中的 ACK(n): 将数据包 n 标记为已接收。如果n是最小的未确认包,则移动窗口 (window base) 到下一个未确认包的序号。

接收端

  • 在 [rcvbase, rcvbase + N - 1] 中的 数据包n: 发送ACK(n)给发送端。如果该包在当前是乱序的,则加入缓存。如果该包顺序正确,则转发所有正在被缓存的,但是顺序正确的包,移动窗口到下一个还未接收到的数据包。
  • 在 [rcvbase - N, rcvbase - 1] 中的 数据包n: 发送ACK(n)。
  • 否则,则忽视该包。

在这里插入图片描述
Selective Repeat 问题:
比如,当序列号是 0, 1, 2, 3,而窗口大小为 3 时。接收端在两个场景中不能感受到不同。冗余数据将会被当作是新数据而被接受 (如图b所示)。
在这里插入图片描述
因此,窗口大小应该 不大于 序列号空间的二分之一。

为了连接的可靠性而做出的努力

  • 校验和 (为了错误检测)
  • 计时器 (为了丢包检测)
  • 确认包,包括累积和选择的 (cummulative and selective)。
  • 序列号 (冗余,窗口)
  • 滑动窗口 (为了高效)

可靠性协议使用以上内容来决定何时以及以什么方式重新传输或者确认。

  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值