计算机网络-自顶向下方法第三章
状态机与可靠数据传输的双方模型
重新研究一下可靠数据传输模型
运输层服务:为不同主机上运行的进程之间提供 逻辑通信(好像直接相连, 其实不是)
报文段(为什么用报文?)
网络层提供了”不同主机的逻辑通信”, 运输层提供了”不同主机上运行的进程之间的逻辑通信”
- 运输层协议只工作在端系统上;
IP的服务模型: 尽力而为交付服务, 不可靠服务
运输层的多路复用与多路分解
TCP: 提供可靠数据传输, 流量控制, 序号, 确认, 定时器
进程模型的网络通信:
- 一个和多个套接字(套接字 = 网络to进程 或者 进程to网络之间数据传输的管道)
报文段数据 => 正确的套接字: 多路分解
在源主机从不同的套接字中收集数据块, 封装header, 生成报文段, 传输到网络层: 多路复用
这里介绍这些我感觉可以和header的结构中设置的(源端口号, 目的端口号)的标识放在一起;
每个进程都可以通过一个或者多个套接字, 套接字再绑定一个端口号, 从而连接了进程和网络系统, 进行数据传输时标记地址天然的就可以使用以上的信息.
web服务器, 假设运行在80端口上;
发送HTTP请求 => 建立与80端口的连接 => 对应服务器的一个进程;
现代服务器的实现方式:
单进程, 新连接分配一个连接的线程, 建立一个新的连接套接字, 用户进程与这个线程套接字连接, 数据传输; 一个进程管理多个线程(当然这样的问题就是客户使用非连续HTTP时, 线程不断创建销毁套接字的开销会很大)
运输方式的不同, 对应了运输层的两种基本实现类型: 无连接运输/有连接的运输.
如何构造一个可靠数据传输的协议?
- 假设底层的信道完全可靠 1.0
发送端: 只需要考虑两件事 发送数据 和 等待上层调用的数据, 处理打包
接收端: 收到数据包 / 提取数据,传给上层应用使用
状态机模型在这里有助于理解为啥我们要这么设计(直觉上合理)
- 信道存在比特的差错 2.0
数据包内部的数据比特可能出错了! 我们需要加一层验证判断是否数据是否正确?
- 确认机制: 确认数据是否正确? ACK/NAK
重传确认 => 根据数据自动反馈 => 基于这样重传机制的协议就是 ARQ(自动重传协议)
ARQ需要以下三个功能实现bit差错的校验:
- 差错检测
- 接收方反馈
- 重传机制
rdt2.0的状态机:
发送端有两个状态
- 等待来自上层的调用 -> 发送数据包, 进入2状态
- 等待ACK/NAK -> 收到NAK,重发,回到2状态 / 收到ACK,进入1状态发送下一个数据包
接收端的状态:
- 等待来自下层的调用 -> 收到数据包,数据包出现差错, 发送NAK回复 / 收到数据包, 数据包正确, 发送ACK回复同时把数据传递给上层应用
-> 继续进入等待状态
注意到这样的协议属于停等协议, 但是2.0一个重要的问题时NAK/ACK报文也可能损坏! 如何处理这种情况?
- 出错就要求发送一个特殊信号 -> 还是可能继续出错!
- 增加足够的校验和bit位, 恢复差错 -> 仅对不会丢包的信道有效
- 发送方收到含糊不清的ACK/NAK时, 直接重新传输当前的数据分组 -> 那么无法知道回答的是对哪个数据包的发送情况? 是重传的还是新的?
为了解决分组的属性问题, 需要添加字段: 数据分组的序号
使用停等协议, 我们只需要1个bit的序号, 用mod2运算来模拟向前移动, ACK/NAK分组本身不需要指明自身所在的分组, 含义是响应最近发送的数据分组序号.
rdt2.1的状态机 -> 2倍扩展2.0的状态
rdt2.2的状态机 -> 改进2.1 去掉了否定确认信号NAK
接收方必须包括由一个ACK报文确认的分组序号, 发送方此时必须检查接收到的ACK报文中被确认的分组序号;
rdt3.0: 在bit可能出错, 且数据包可能丢包的信道上建立可靠传输
- bit受损
- 底层信道丢包的情况
如何判断一个数据包丢失了?(有很多的方法)
- 一种方法是: 发送方愿意等待足够长的时间, 以确认分组已经丢失, 那么只需要重传这一个分组即可.
基本的延迟 = 往返时延 + 接收方处理一个分组需要的时间
如何选择这个等待时间的长度?(经验公式)
实现方式:
- 一个countdown timer
计时器基本操作:
- 每次发送一个分组时, 启动计时器;
- 响应计时器中断;
- 中止计时器
rdt3.0 加入计时器, 超时重传的状态机
比特交替协议(只有两个序号的, 停等, 支持差错/丢包的基本可靠传输协议)
问题: 停等的有效利用率太低了
流水线可靠数据传输协议: 不停等, 允许发送方一次多发数据包, 不需要等到每个都确认再继续发送新的数据.
相应的变化:
增加序号范围
发送端/接收端需要支持缓存多个分组: 例如发送端至少需要缓存那些已发送未确认的分组;
解决流水线的差错恢复: GBN(回退N) 和 SR(选择重传)
比较简单的GBN协议:
- 发送方的发送窗口限制: 已发送未确认+ 可用未发送的数据包序号范围 = N(流量控制,是对发送方添加的限制)