Stanford CS144 lab3

  • 总览
    • lab3需要实现TCPSender ,TCPSender的作用是将发送字节流转化为TCPsegment
    • 激动人心的是,在lab4中,将实现一个真实的TCPConnection,并通过它联通Internet世界
  • TCP Sender
    • TCPSender负责从一个ByteStream读取字节并将其转换成一序列外送TCP segments;另外,TCP revceiver可以是任何一个可靠的TCP receiver,建立一套Internet通信标准才是最重要的。
    • TCPSender在TCPSegment中写入各个字段,比如序列号,SYN标志,有效载荷,FIN标志,TCPSender只能够读ackno和the window size这两个字段,标红的字段就是了
    • TCPSender需要做的是
      • 查看追踪接受者的window,也就是处理ackno与window size
      • 尽可能填满窗口,也就是说及时的从ByteStream读数据,并创建与发送TCPsegments,直到the window满了或者ByteStream空了
      • 跟踪查看哪个报文段流失了,我们将这种报文段称作outstanding segments,也就是未完成的报文段
      • 对于outstandin sgements,需要做到超时重传,这里实现了ARQ,ARQ是OSI模型中数据链路层和传输层的错误纠正协议之一。它通过使用确认和超时这两个机制,在不可靠服务的基础上实现可靠的信息传输。如果发送方在发送后一段时间之内没有收到确认帧,它通常会重新发送。ARQ包括停止等待ARQ协议和连续ARQ协议,连续ARQ又分为回退N帧ARQ协议、选择性重传ARQ协议。ARQ协议是对滑动窗口的一个很好的实现
    • TCPSender如何知道一个报文丢失了?
      • TCPSender有一个计时器函数,也就是tick方法。TCP中超时的处理方式是:每次超时重传最老的的报文段,并重新启动定时器;每次收到确认时,更新已被确认的报文段,重新启动计时器,如果还有未被确认大的报文段,重新启动定时器
      • 每过几毫秒,TCPSender会调用tick函数,以此来及时,不要去调用其他⏲函数,比如time或者clock
      • 初始时,RTO(retransmission timeout)会被设置为initial value,RTO就是超时值,它变化,但是initial value不会变化,变量initial_retransmission_timeout保存了initial value
      • 通过RTO实现重传计时器,这里的时间与真实时间并不一致
      • 只要一个报文段发出了,不论是否是重传,计时器都会启动,并在RTO的时间之后,终止报警
      • 所有的发出的报文段都收到了确认,停止计时器
      • 计时器报警超时的话,需要重传最老的未收到确认的报文段,需要建立一些内部数据结构去记录outstanding segment, 这里的指数退避😵,1.指数退避是重传的一种方法,并且这里是只重传最早的未被确认的报文,好处是使得网络拥塞减轻,但是慢,2.可以选择重传所有包,但是这样会加剧网络拥塞,3.还有其他策略,比如快重传,连续收到三个重复ACK(不包括第一个),便立刻重传,而这仍然存在是重传一个还是所有的问题。4.SACK可以解决这个问题,不过SACK存在接收方Reneging情况,所谓Reneging的意思就是接收方有权把已经报给发送端SACK里的数据给丢了。这样干是不被鼓励的,因为这个事会把问题复杂化了,但是,接收方这么做可能会有些极端情况,比如要把内存给别的更重要的东西。所以,发送方也不能完全依赖SACK,还是要依赖ACK,并维护Time-Out,如果后续的ACK没有增长,那么还是要把SACK的东西重传,另外,接收端这边永远不能把SACK的包标记为Ack
  • 实现TCP sender(看测试逐步实现是个不错的方式)
    • 根据文档可以知道,我们不需要实现SR,只需要实现类似GBN,不过不同的是GBN要重传所有所有未确认分组
    • 这个函数下一个lab要用
    • 如果receiver的window为0,那么假设sender啥也不发,sender永远也没有机会接受到新的ack,即使receiver的window不再是0了
  • 实现中的问题
    • 这里需要特判TCPSegment中只有fin标志, 因为Remember that the SYN and FIN flags also occupy a sequence number each, which means that they occupy space in the window.
    • 初始的的_receiver_window_size需要设置为1,不然这个测试用例会出错,如果设置为0,会使的remain溢出,也就是发完SYN包之后,remain -= 1,会翻到最大值
    • 这个测试用例需要特殊处理fin包的发送`
    • window_size为零的时候需要特判,并且RTO不能指数退避,
    • 需要特判重复的ack是无效的不然会引发如下错误
    • 在send_ack.cc中有个注释了的测试,它想要实现的效果是,如果传送的ackno过大,sender需要发送一个报文去告诉receiver
posted @   抿了抿嘴丶  阅读(468)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 周边上新:园子的第一款马克杯温暖上架
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器
· DeepSeek如何颠覆传统软件测试?测试工程师会被淘汰吗?
· 使用C#创建一个MCP客户端
点击右上角即可分享
微信分享提示