计算机网络-5-8-TCP流量控制

TCP流量控制

利用滑动窗口实现流量控制

我们总是希望数据传速能够更快一些,但如果发送方把数据发送的太快,接收方就有可能来不及接收,这样就会导致数据丢失,所谓的流量控制(flow control)就是让发送方的数据发送速率不要太快,要让接收方来得及接收,避免数据丢失情况的发生。

利用滑动窗口机制可以很方便的在TCP连接上实现发送方的流量控制。

下面图5-22的例子说明如何利用滑动窗口机制实现流量控制。

image

设A向B发送数据,在建立连接的时候,B告诉A:“我的接收窗口rwnd=400字节(receiver window)”。因此,发送方的发送窗口不能超过接收窗口值

我么注意到,接收到的主机B进行了三次流量监控。第一次把窗口减少到rwnd=300,第二次把窗口减小到100,第三次减少到了0,即不允许再发送数据了,这种是发送方暂停发送的状态将会持续到主机B重新发送一个新的窗口为止,我们还应该注意到,B向A发送的三个报文段都设置了ACK=1,只有在ACK=1的时候,确认号字段才有效。注意(大写ACK表示首部中的确认位ACK,小写ack表示的是确认字段的值)。

我们应注意到,接收方的主机B进行了三次流量控制。第一次把窗口减小到rwnd = 300,第二次又减到rwnd = 100,最后减到 rwnd = 0,即不允许发送方再发送数据了。这种使发送
方暂停发送的状态将持续到主机 B 重新发出一个新的窗口值为止。我们还应注意到,B 向
A 发送的三个报文段都设置了ACK=1,只有在ACK=1时确认号字段才有意义。

​现在我们考虑另一种情况,在图5-22中,B向A发送零窗口不久后,B的接收缓存又有了一些空闲的空间,,于是B向A发送了一个rwnd=400的报文段,然而这个报文段在传输过程中丢失了,A一直在等待B发送非零窗口的通知,,B也一直等待A发送的数据,如果没有采取任何措施,这种相互等待的死锁将会一直持续下去。

​为了解决这个问题,TCP连接为每一个连接设有持续计数器(persistence timer),只要TCP连接的一方收到另一方的零窗口通知,就启动持续计数器,若持续计数器设定的时间到期,发送方就发送一个零窗口的 探测报文段(仅携带一字节的数据),接收方在接收到这个零探头报文段的时候会返回自己当前的窗口值,如果窗口值还是0,那么收到这个报文段的另一方重新设置持续计数器,如果不是0,那么死锁的僵局就可以互相打破。

TCP传输效率

前面已经讲过,应用进程数据把数据传送到TCP的发送缓存中,剩下的发送任务就由TCP来控制了,可以用不同的机制来控制TCP报文段的发送时机。例如,第一种机制就是TCP维持一个变量,它等于最大报文段长度MSS。只要缓存中存放的数据到达MSS字节的时,就组装成一个TCP报文段发送出去。第二种机制是由发送方的应用进程指明要求发送报文段,即TCP支持的推送(push) 操作。第三种机制就是发送方的计时器期限到了,这时就把当前已有的缓存数据装入到报文段(但程度不能超过MSS)发送出去。

在TCP的实现中,使用广泛的是Nagle算法,算法如下:

若发送应用进程要把发送的数据逐个字节送到TCP缓发送存中,则发送方把第一个字节的数据先发送出去,把后面到达的数据字节都缓存起来,当发送方收到第一个字节的确认的时候,再把发送缓存中的所有数据组装成一个报文段发送出去,同时继续对随后到达的数据进行缓存。只有收到对前一个报文段的确认之后才继续发送下一个报文段。当数据到达较快而网络速率较慢的时候,用这样的方法可以明显的减少使用的网络带宽,Nagle算法还规定,当到达的数据已经达到发送窗口大小的一半或者已达到报文段最大长度时,就立即发送一个报文段,这样做,就可以有效提高网络吞吐量,

另一个问题叫做糊涂窗口综合征(silly window syndrome):有时候也会使得TCP的性能变坏,设想一种情况,TCP接收方的缓存是满的,而交互式的应用进程一次只从接收缓存中读取一字节的数据,然后向发送方发送确认,并把窗口设置为1字节。接着发送方又发来1字节的数据,接收方发回确认,仍将窗口大小设置为1字节,这样下去,使得网络传输效率很低。

要解决这个问题,可以让接收方等待一段时,使得接收缓存已有足够的空间容纳一个最长的报文段,或者等待接收缓存已有一半的空闲空间,只要出现这两种情况之一,接收方就发出确认报文,并向发送方通知当前窗口大小。

posted @ 2021-09-05 17:13  LilyFlower  阅读(340)  评论(0编辑  收藏  举报