rperf是 3D-P 开发的基于 Rust 的iperf替代品,旨在避免iperf3中发现的一些可靠性和一致性问题,同时提供更丰富的指标数据,重点是在丢失容忍、更像物联网的环境中运行。虽然它可以用作iperf的近乎直接替代品,并且这样做可能有好处,但它的重点是封闭网络中监控能力的定期数据收集,这意味着它并不适合所有领域iperf可以提供服务。
rperf是一个独立的实现,引用iperf3和zapwireless的算法来评估正确性并得出适当的更正,但不复制任何代码。
尤其是iperf3解决的最重要问题如下:
任何给定的服务器都支持多个并发客户端。
rperf用于流抖动计算的 RFC 1889 实现首先假设序列中第一个和第二个数据包之间的增量以及序列中的间隙触发计数重置。相比之下, iperf3从 0 开始,这会人为地创建低值,而在出现间隙时,它只是简单地继续,这会人为地创建高值。
重复数据包在 UDP 交换中被考虑,无序数据包被计为独立事件。
所有流量都可以按规则的亚秒间隔按比例发出,从而允许更准确地反映真实数据传输和发送算法的配置。
流配置和结果通过专用连接进行交换,并且每个数据路径都具有明确定义的超时、完成和失败语义,因此当关键数据包丢失时,执行不会无限期地挂在测试的两侧。
rperf的 JSON 输出在结构上是合法的。没有不带引号的字符串、重复的键或悬空逗号,所有这些都需要在使用之前进行预处理,否则会导致意外错误。
与zapwireless相比,实现了以下改进:
rperf使用经典的客户端-服务器架构,因此无需在等待测试执行请求的设备上维护正在运行的进程。
计算抖动。
支持 IPv6。
作为测试的一部分,多个流可以并行运行。
可以使用omit
选项从结果中丢弃 TCP 加速时间。
输出以 JSON 格式提供,以便更轻松地收集遥测数据。
rperf应该在所有主要平台上构建和工作,尽管它的开发和使用重点是基于 Linux 的系统,因此这是它功能最完整的地方。
欢迎请求为其他系统实现等效功能。
所有内容都在--help
的输出中概述,大多数熟悉类似工具的用户应该会立即感到舒服。
rperf 的工作方式与iperf3非常相似,共享许多概念甚至命令行标志。它的一个关键区别在于客户端驱动所有配置过程,而服务器只是尽其所能并提供结果流。这意味着服务器不会直接通过其接口呈现测试结果,并且 TCP 和 UDP 测试可以针对同一实例运行,可能由许多客户端同时运行。
在正常操作模式下,客户端会将数据上传到服务器;当reverse
标志被设置时,客户端将接收数据。
与iperf3不同, rperf默认情况下不使用保留的端口范围。这样它就可以并行支持任意数量的客户端,而不会在实际上只能是少量连续端口的情况下发生资源争用。就其预期能力而言,这应该不是问题,但在涉及非宽松防火墙和 NAT 设置的情况下, --tcp[6]-port-pool
和--udp[6]-port-pool
选项可能会出现问题用于将非连续端口分配给将用于接收流量的端口集。
也没有测试相对于固定数据量的吞吐量的概念。相反,唯一的重点是测量大致已知的时间段内的吞吐量。
同样重要的是,如果服务器在 IPv6 模式下运行并且其主机支持双栈配置中的 IPv4 映射,则 IPv4 和 IPv6 客户端都可以连接到同一实例。
rperf使用货物。典型的过程很简单: cargo build --release
。
Cargo-deb也受支持,并将生成一个可用的 Debian 软件包,该软件包安装默认禁用的rperf
systemd服务。启动时,它以nobody:nogroup
运行,假设默认支持 IPv6。
与同时代的产品一样, rperf的核心概念是以预先安排的目标速度向 IP 目标发射 TCP 或 UDP 数据流。观察实际接收到的数据量并用于衡量网络链路的容量。
在这些领域内,收集有关交换质量的其他数据并可供审查。
从架构上来说, rperf让客户端建立到服务器的 TCP 连接,之后客户端发送有关要执行的测试的详细信息,服务器强制执行,在整个测试过程中向客户端报告观察结果。
客户端可以请求使用多个并行流进行测试,这可以通过在两侧建立多个 TCP 连接或 UDP 套接字以及各自的专用线程来实现,这些连接可以进一步固定到单个逻辑 CPU 核心以减少页面的影响- 数据交换故障。
客户端-服务器关系被视为此设计的一个非常核心的方面,这与iperf3和 zapwireless 形成鲜明对比,在 iperf3 中,它们更像是对等体,在zapwireless中,每个参与者运行自己的守护进程,并由第三个进程协调通信。
值得注意的是,所有数据收集、计算和显示都发生在客户端,服务器仅返回其观察到的内容。这可能会导致记录出现一些偏差,特别是在涉及时间的情况下(服务器间隔比相应的客户端值长几毫秒的情况并不罕见)。然而,假设连接没有丢失,观察到的数据总数将在所有操作模式下匹配。
服务器使用三层线程:一层用于主线程,一层用于所服务的每个客户端,还有一层用于与客户端通信的每个流。在客户端,主线程用于与服务器通信,并为与服务器通信的每个流生成一个附加线程。
当服务器收到来自客户端的请求时,它会生成一个线程来处理该客户端的特定请求;在内部,测试的每个流都会在两侧生成一个类似迭代器的处理程序。客户端和服务器都异步运行这些迭代器模拟,直到测试周期结束,此时发送方指示其流中的完成。
为了可靠地处理流级别断开连接的可能性,客户端-服务器流中的保活机制(通过该机制定期从服务器发送测试结果)将在几秒钟不活动后终止未完成的连接。
主机操作系统的 TCP 和 UDP 机制用于所有实际交换的流量,并公开一些调整参数。选择这种方法而不是第 2 层或第 3 层之上的用户空间实现,因为它最准确地代表了现实世界应用程序的行为方式。
JSON 序列化间隔数据中可见的“时间戳”值是与主机相关的,因此除非您的环境具有非常高的系统时钟精度,否则发送时间戳只能与其他发送时间戳进行比较,对于接收时间戳也是如此。然而,一般来说,这些数据在正确性验证之外没有用处。
在每个交换间隔期间,一次尝试发送length
字节,直到写入流的数量达到或超过带宽目标,此时发送方将保持沉默,直到下一个间隔开始;一个时间间隔内发送的数据应该在该时间段内均匀分布。
流索引从0
开始,而不是1
。这可能不会让任何人感到惊讶,但在报告中看到“stream 0”并不值得担心。
rperf由 Evtech Solutions, Ltd.(dba 3D-P)根据 GNU GPL 版本 3 分发,其文本可以在COPYING
中找到。
作者身份详细信息、版权细节和可转让性说明都存在于源代码本身中。