在 Linux 上模拟延迟和丢弃的数据包

Posted

技术标签:

【中文标题】在 Linux 上模拟延迟和丢弃的数据包【英文标题】:Simulate delayed and dropped packets on Linux 【发布时间】:2010-10-11 12:24:22 【问题描述】:

我想在 Linux 上模拟 UDPTCP 的数据包延迟和丢失,以测量应用程序的性能。有没有简单的方法可以做到这一点?

【问题讨论】:

另见/欺骗:Network tools that simulate slow network connection 对于 OS X,请参阅:superuser.com/questions/173882/… 【参考方案1】:

netem 利用 Linux 和用户空间实用程序中已内置的功能来模拟网络。这实际上是 Mark 的答案所指的,但名称不同。

their homepage 上的示例已经展示了如何实现您的要求:

示例

模拟广域网延迟

这是最简单的例子,它只是为所有从本地以太网传出的数据包增加了固定量的延迟。

# tc qdisc add dev eth0 root netem delay 100ms

现在对本地网络上的主机进行简单的 ping 测试应该显示增加了 100 毫秒。延迟受内核时钟分辨率 (Hz) 的限制。在大多数 2.4 系统上,系统时钟以 100 Hz 运行,允许以 10 ms 为增量进行延迟。在 2.6 上,该值是从 1000 到 100 Hz 的配置参数。

后面的例子只是改变参数而不重新加载 qdisc

真正的广域网显示出可变性,因此可以添加随机变化。

# tc qdisc change dev eth0 root netem delay 100ms 10ms

这会导致增加的延迟为 100 ± 10 毫秒。网络延迟变化不是纯粹随机的,因此要模拟也存在相关值。

# tc qdisc change dev eth0 root netem delay 100ms 10ms 25%

这导致添加的延迟为 100 ± 10 毫秒,下一个随机元素取决于最后一个元素的 25%。这不是真正的统计相关性,而是一个近似值。

延迟分布

通常,网络中的延迟是不统一的。更常见的是使用正态分布之类的东西来描述延迟的变化。 netem 规程可以使用一个表来指定非均匀分布。

# tc qdisc change dev eth0 root netem delay 100ms 20ms distribution normal

实际的表(normal、pareto、paretonormal)作为 iproute2 编译的一部分生成并放置在 /usr/lib/tc 中;因此可以根据实验数据做出自己的分布。

丢包

随机数据包丢失在“tc”命令中以百分比指定。最小可能的非零值是:

2−32 = 0.0000000232%

# tc qdisc change dev eth0 root netem loss 0.1%

这会导致百分之 1/10(即千分之一)的数据包被随机丢弃。

还可以添加可选的相关性。这会导致随机数生成器的随机性降低,可用于模拟数据包突发丢失。

# tc qdisc change dev eth0 root netem loss 0.3% 25%

这将导致 0.3% 的数据包丢失,并且每个连续的概率取决于最后一个的四分之一。

概率n = 0.25 × 概率n-1 + 0.75 × 随机

注意,如果您没有该接口的规则,则应使用tc qdisc add;如果您已经有该接口的规则,则应使用tc qdisc change。尝试在没有规则的接口上使用tc qdisc change 会报错RTNETLINK answers: No such file or directory

【讨论】:

原网站有这个错误,我只是直接复制了那个文本。但是,是的,2^(-32)=2.33e-10 注意tc -p qdisc ls dev eth0会列出当前定义的规则,tc qdisc del dev eth0 root会删除它们 在尝试更改不存在的条目时指出错误而被赞成 @ephemient 可以在 IP 级别上做类似的事情吗?例如。丢弃和延迟单个 IP 地址的数据包? ***.com/questions/46945705 这只适用于传出的数据包,不适合模拟网络丢失。 iptables 正确应用于传入流量。【参考方案2】:

对于丢弃的数据包,我只需使用 iptables 和 statistic module。

iptables -A INPUT -m statistic --mode random --probability 0.01 -j DROP

以上将以 1% 的概率丢弃传入的数据包。请注意,任何高于 0.14 的值以及大多数 tcp 连接很可能会完全停止。

查看 man iptables 并搜索“statistic”以获取更多信息。

【讨论】:

为什么 TCP 连接会停滞在 14% 以上? @DavidWolever:因为调整 tcp 滑动窗口大小的方式。但是这 14% 纯粹是经验之谈,自己尝试一下,你会发现 ssh 在 14% 及以上时变得几乎无法使用,但实际上在丢包率较低的情况下工作得很好。 为了安全起见,最好将规则限制为仅适用于您要测试的端口:iptables -A INPUT --dport FOO -m statistics .... 这个这样,您的 ssh 和其他连接将保持不受干扰,并且您可以提高相关服务的丢弃率,以便能够更快地重现任何问题。 请注意,出站 连接上的DROP 相当荒谬地导致send() 操作返回EPERM,而不是仅仅丢弃数据包(就像它应该的那样)。 这就是撤消该命令所需的全部内容吗? iptables -D INPUT -m statistic --mode random --probability 0.01 -j DROP【参考方案3】:

我的一位同事使用 tc 来执行此操作。有关更多信息,请参阅手册页。您可以查看其用法示例here。

【讨论】:

我觉得iptables比较好用:) 当然,但是 tc 比 iptables 快得多【参考方案4】:

iptables(8) 有一个统计匹配模块,可用于匹配每个第 n 个数据包。要丢弃此数据包,只需附加 -j DROP

【讨论】:

【参考方案5】:

tutorial on networking physics simulations 在sample code 中包含一个 C++ 类,用于模拟 UDP 连接中的延迟和数据包丢失,可能具有指导意义。请参阅@987654323 的 Connection.h 文件中的 Connection 类的公共 latencypacketLoss 变量@。

【讨论】:

【参考方案6】:

自己没试过,但this page 有一个在Linux 中运行的插件模块列表,内置iptables IP 过滤系统。其中一个模块称为“nth”,它允许您设置一个规则,该规则将丢弃可配置的数据包速率。至少可能是一个不错的起点。

【讨论】:

【参考方案7】:

一个易于使用的网络故障注入工具是Saboteur。它可以模拟:

网络总分区 远程服务停止(不在预期的端口上监听) 延误 丢包 -TCP 连接超时(当两个系统被有状态防火墙隔开时经常发生)

【讨论】:

遗憾的是,该项目的最后一次提交是在 2015 年 8 月 28 日,也就是将近 4 年前。未解决的问题现在已经 5 年了。【参考方案8】:

科学界为此目的最常用的工具之一是DummyNet。一旦你安装了ipfw 内核模块,为了在两台机器之间引入 50ms 的传播延迟,只需运行以下命令:

./ipfw pipe 1 config delay 50ms
./ipfw add 1000 pipe 1 ip from $IP_MACHINE_1 to $IP_MACHINE_2

为了同时引入 50% 的数据包丢失,您必须运行:

./ipfw pipe 1 config plr 0.5

Here 更多详情。

【讨论】:

【参考方案9】:

你可以试试http://snad.ncsl.nist.gov/nistnet/https://www-x.antd.nist.gov/nistnet/ 这是一个相当古老的 NIST 项目(2005 年最后一个版本),但它对我有用。

【讨论】:

以上是关于在 Linux 上模拟延迟和丢弃的数据包的主要内容,如果未能解决你的问题,请参考以下文章

网络模拟工具Clumsy

入队数据包延迟时,IOS AudioQueue 不播放

Windows下弱网模拟工具Clumsy

牛仔在端口 80 上丢弃一些数据包

混合 TCP 和 UDP

Linux流量控制(TC)之表面