我不太明白是否可以限制速率传入交通。我意识到没有直接的方法来控制远程服务器发送数据包的速率(除非您控制两个端点),但考虑到这个限制,下载管理器究竟如何允许我成功设置下载速度限制?
这两者之间有什么联系吗?TCP 慢启动并限制传入流量的速率?是否可以使用慢启动所描述的方法来人为地限制发送方发送数据包的速率?
作为额外的考虑,应该注意的是,我想要实现流量整形的服务器本身建立 PPPoE 连接,并充当网络其余部分的路由器。
更新:到目前为止,这些答案已经对我提出的问题进行了公正的概述,但我仍然不知道下载管理器如何限制传入流量,更具体地说,是否有可能在 Linux 网关盒上实施类似的策略。
答案1
下载管理器最有可能按照滴流纸。
使用 BSD 套接字的进程可以执行其自己的速率限制。对于上游限制,应用程序可以通过简单地限制写入套接字的数据速率来实现此目的。同样,对于下游限制,应用程序可以限制从套接字读取数据的速率。但是,这种方法有效的原因并不显而易见。当应用程序忽略从套接字读取某些数据时,其套接字接收缓冲区将被填满。这反过来会导致接收 TCP 通告较小的接收窗口 (rwnd),从而对底层 TCP 连接产生背压,从而限制其数据流。最终,这种“涓滴效应”实现了端到端速率限制。根据网络堆栈所有层的缓冲情况,这种影响可能需要一些时间才能传播。
如果你偶尔需要在 UNIX 系统上对单个程序进行速率限制,一个简单的解决方案是涓涓细流。真正的流量整形,就像你在网关上执行的一样,可以用 来完成tc
。这在第 9 章 带宽管理的排队原则Linux 高级路由和流量控制 HOWTO。
答案2
在 56k 调制解调器与 4 Mbps DSl 线路的情况下,通常不存在造成速度差异的整形,仅仅是链路速度的差异。
难以对传入流量进行整形的原因是传输介质中没有缓冲区。您要么接受传入的位,要么丢失它们。对于即将离开接口的流量,您可以根据需要缓冲和重新排序数据包(或者,至少在设备中可用的缓冲内存范围内)。
对于在 TCP 之上有一层的协议(我不知道 torrent 是否也是如此),只需对进一步的数据请求进行步调调整即可。否则,应用程序将需要与操作系统进行通信,以延迟确认数据包。大多数基于 UDP 的协议必然会在特定于应用程序的协议中具有确认/重新发送逻辑,因此在这一点上,对它们进行步调调整几乎是微不足道的。
一种可能的方法是,在 DSL 路由器的 LAN 侧对来自 Internet 的流量进行整形,因为此时,您将在出口端口上进行整形。
答案3
我无法回答为什么你没有找到任何允许塑造传入数据的解决方案(并且我不知道任何解决方案),但是对于发送方如何知道接收方接收数据的速度:
TCP/IP 的基本设计是,对于源发送到目的地的每个数据包,它都必须等待目的地回复(带有数据ACK
包)以表明它已收到该数据包。
因此,如果您有一个 4Mbps 发送器和一个 56Kbps 接收器,那么发送器必须在发送数据包之间等待接收器对每个数据包做出响应(有一些技术细节可以减少这种开销,但前提在抽象层面上仍然成立)。
那么,如果发送方已经发送了 56Kbps 的数据,然后尝试发送更多一点的数据,会发生什么情况?
数据包丢失了。(好吧,可能在交换机的缓冲区中排队,但当缓冲区填满时,数据包就会丢失)。由于数据包丢失,接收方永远不会收到它,因此永远不会发送数据包ACK
。由于发送方永远不会收到这个ACK
数据包(因为它从未发送过,但也可能丢失,或者网络中断),发送方必须重发额外的数据包。它会停下来并尝试重新发送数据包,直到成功发送并ACK
收到回复为止。
因此,总结一下,一旦发送方耗尽了接收方的带宽,它就必须停止并反复重新发送下一个数据包,直到有足够的可用带宽供其发送。这实际上将发送速度降低到客户端可以接收的最大速度。(在这种情况下,有优化方法可以减少数据包必须重新发送的次数,基本上发送方每次必须重新发送数据包时都会减慢速度,但这超出了本文简化描述的范围。
答案4
查看 wondershaper:http://lartc.org/wondershaper/
关于传入流量:
This is slightly trickier as we can't really influence how fast the internet
ships us data. We can however drop packets that are coming in too fast,
which causes TCP/IP to slow down to just the rate we want. Because we don't
want to drop traffic unnecessarily, we configure a 'burst' size we allow at
higher speed.
Now, once we have done this, we have eliminated the downstream queue totally
(except for short bursts), and gain the ability to manage the upstream queue
with all the power Linux offers.