RDMA性能测试实战(1):perftest工具原理与基线测试方法

摘要:本文系统剖析RDMA性能基准测试工具perftest的技术架构、核心工具矩阵、Verbs级实现机制与标准测试流程,详细讲解ib_write_bw/ib_write_lat的参数体系、输出指标含义与环境配置要点,帮助测试工程师建立RDMA性能基线测试的标准化方法。


一、perftest的技术定位与架构

perftest是基于InfiniBand Verbs API实现的RDMA性能基准测试工具集,由Mellanox(现NVIDIA)主导开发,作为OFED发行版的标准组件随驱动一起发布。它的核心设计原则是直接操作Verbs原语,跳过所有中间协议栈,测出RDMA硬件的极限性能------这使它成为行业内评估网卡、交换机、DPU等RDMA设备性能的事实标准。

1.1 在测试体系中的位置

复制代码
┌───────────────────────────────────────────────────────┐
│                   业务层应用性能                        │
│   (NCCL / MPI / NVMe-oF / 分布式数据库 / AI推理框架)    │
├───────────────────────────────────────────────────────┤
│                   中间件/框架层                         │
│           (UCX / libfabric / ROCm / CUDA)             │
├───────────────────────────────────────────────────────┤
│              协议栈层(内核+用户态)                     │
│       (RDMA-Core / libibverbs / 内核ULP驱动)          │
├───────────────────────────────────────────────────────┤
│  perftest  ←── 直接调用Verbs,处于协议栈之上、业务之下  │
├───────────────────────────────────────────────────────┤
│                   硬件层                               │
│          (RDMA网卡 / DPU / 交换机 / 线缆)             │
└───────────────────────────────────────────────────────┘

perftest的价值在于:当上层业务性能不达预期时,先用perftest确认硬件+驱动+基础网络这三层是否正常,再往上排查。如果perftest都跑不满,那问题一定在底层,调业务代码毫无意义。

1.2 代码结构与核心组件

perftest的源码组织结构清晰:

模块 功能
perftest_communication.c Client/Server间的控制通道(TCP套接字),用于交换GID、QPN、PSN等建链信息
perftest_resources.c RDMA资源管理:PD、CQ、QP、MR、SRQ等的创建与销毁
perftest_parameters.c 命令行参数解析与默认值管理
perftest_bench_calls.c 真正的测试循环逻辑:post_send、poll_cq、计时、统计
perftest_reporting.c 结果格式化输出(带宽/延迟/百分位计算)
write_bw.c / write_lat.c 每种测试的入口文件,定义操作类型和测试参数

核心测试循环的伪代码如下:

c 复制代码
// 带宽测试主循环
for (iteration = 0; iteration < num_iterations; iteration++) {
    // 1. 批量post WR(发送工作请求)到SQ
    for (i = 0; i < burst_size; i++) {
        ibv_post_send(qp, &wr);
    }
    // 2. 轮询CQ(完成队列)等待完成
    while (completed < burst_size) {
        ibv_poll_cq(cq, batch_size, wc_array);
        completed += batch_size;
    }
    // 3. 更新字节计数与时间戳
    bytes_done += msg_size * burst_size;
}
// 4. 计算带宽 = 总字节 / 时间
bandwidth = (bytes_done * 8) / elapsed_time; // 转成bit/s

延迟测试的逻辑更简单------每发一个WR就立刻poll CQ等完成,测的是单次操作的端到端时间。


二、八大工具矩阵与操作语义

perftest按"RDMA操作类型 × 测试维度"形成8个核心工具,每个工具对应一种独立测试场景。

2.1 工具矩阵

工具名 操作类型 测试维度 典型用途
ib_send_bw RDMA Send 带宽(Bandwidth) 双边操作吞吐量,验证Send路径性能
ib_send_lat RDMA Send 延迟(Latency) 双边操作往返延迟
ib_write_bw RDMA Write 带宽 最常用,单边写入吞吐量,对标线速
ib_write_lat RDMA Write 延迟 单边写入延迟,通常最低
ib_read_bw RDMA Read 带宽 单边读取吞吐量
ib_read_lat RDMA Read 延迟 单边读取延迟
ib_atomic_bw Atomic(FetchAdd/CmpSwap) 带宽 原子操作吞吐量
ib_atomic_lat Atomic(FetchAdd/CmpSwap) 延迟 原子操作延迟

2.2 四种RDMA操作的语义差异

理解这四种操作的本质,是理解它们性能差异的基础。

RDMA Write(单边写入)
  • 发起端指定本地源地址、远端目的地址、长度
  • 对端CPU完全不参与,硬件直接把数据写入对端内存
  • 不需要对端post receive
  • 性能最高,是衡量网卡线速的标准操作
RDMA Read(单边读取)
  • 发起端指定本地目的地址、远端源地址、长度
  • 对端CPU不参与,硬件直接从对端内存读取数据
  • 需要对端先注册MR(内存注册)并把rkey+地址告诉本端
  • 性能略低于Write,因为读操作涉及远端内存响应和回传
RDMA Send(双边发送)
  • 发送端把数据发到对端的Receive Queue
  • 对端必须post receive buffer才能收到数据
  • 需要两端配合,有接收侧开销
  • 性能通常低于Write,尤其是小包场景(每次都要消耗Receive WQE)
Atomic(原子操作)
  • FetchAdd:远端内存原子加法并返回旧值
  • CmpSwap:远端内存原子比较交换
  • 硬件级原子性,保证并发安全
  • 性能最低,因为需要远端读-改-写,且原子操作串行化

2.3 性能数量级对比(100G网卡典型值)

操作 带宽(大包) 延迟(小包) 说明
Write ~97 Gb/s ~1.0 μs 最高,线速基准
Read ~90 Gb/s ~1.5 μs 略低,需要远端响应
Send ~85 Gb/s ~2.0 μs 更低,双边开销
Atomic ~10-20 Gb/s ~3-5 μs 最低,原子串行化

以上数值为典型100G RoCE网卡的大致量级,具体数值取决于网卡型号、固件版本、PCIe代际和测试配置。


三、标准测试环境配置

性能测试结果的可靠性,90%取决于测试环境是否配置正确。以下是标准化的环境配置Checklist。

3.1 硬件检查

bash 复制代码
# 1. 确认网卡型号与固件版本
lspci -vvv -s <BDF> | grep -E "Product|Part|Firmware"

# 2. 确认PCIe链路状态(必须是x16 + Gen4/Gen5)
lspci -s <BDF> -vv | grep LnkSta:
# 期望输出:LnkSta: Speed 16GT/s (ok), Width x16 (ok)   ← PCIe 4.0 x16

# 3. 确认网卡端口数量与速率
ibv_devices              # 列出所有RDMA设备
ibv_devinfo -d <dev>     # 查看设备详细信息

# 4. 确认网口协商速率
ethtool <netdev> | grep -E "Speed|Duplex"

PCIe是最容易出问题的环节。如果PCIe只有x8或降到了Gen3,RDMA带宽一定跑不满。

网卡速率 最低PCIe要求
25G PCIe 3.0 x8
100G PCIe 4.0 x8 或 PCIe 3.0 x16
200G PCIe 4.0 x16
400G PCIe 5.0 x16

3.2 驱动与系统配置

bash 复制代码
# 1. 确认驱动版本
ofed_info -s
modinfo mlx5_core | grep version

# 2. 确认RDMA栈正常
lsmod | grep -E "rdma|ib_uverbs|mlx5"

# 3. 开启巨页(性能测试强烈建议)
echo 8192 > /proc/sys/vm/nr_hugepages
# 验证
grep Huge /proc/meminfo

# 4. 调整内存锁限制(perftest注册MR需要)
ulimit -l unlimited
# 永久生效:/etc/security/limits.conf 中加入
# * soft memlock unlimited
# * hard memlock unlimited

# 5. 关闭防火墙(RoCE场景)
systemctl stop firewalld
systemctl disable firewalld
# 或开放UDP/4791(RoCE v2端口)

# 6. 关闭SELinux
setenforce 0

3.3 CPU绑定配置

性能测试必须绑核,否则调度抖动会导致结果严重不准。

bash 复制代码
# 先查网卡所在的NUMA节点
cat /sys/class/net/<netdev>/device/numa_node
# 返回0或1,表示属于NUMA0或NUMA1

# 查该NUMA节点的CPU列表
lscpu | grep -A 10 "NUMA node0 CPU(s):"

# 测试时用 -c 参数绑到对应NUMA的核心上
# 例如网卡在NUMA0,绑到core 2
ib_write_bw -d <dev> -c 2 -F <server_ip>

3.4 网络侧配置(RoCE场景)

交换机侧必须确保:

  1. PFC(优先级流量控制)已启用------RDMA需要无损以太网
  2. ECN(显式拥塞通知)已配置------拥塞控制需要
  3. 两端交换机端口的MTU一致(建议9000巨帧)
  4. 没有ACL或QoS策略意外拦截RDMA流量

四、基线测试标准流程

4.1 连通性验证(先确认链路OK)

跑性能之前,先用最简单的工具确认RDMA链路通畅:

bash 复制代码
# 方式一:ibv_rc_pingpong(最基础的连通性测试)
# Server端
ibv_rc_pingpong -d <dev>
# Client端
ibv_rc_pingpong -d <dev> <server_ip>

# 方式二:rping(类似ping的RDMA版)
# Server端
rping -s -a <server_ip>
# Client端
rping -c -a <server_ip> -C 10

能ping通再上性能测试,不要上来就跑带宽。

4.2 带宽基线测试

标准的带宽测试命令:

bash 复制代码
# Server端
ib_write_bw -d <dev> -F -c <core_id>

# Client端(大包测线速)
ib_write_bw -d <dev> -F -c <core_id> -s 8388608 -n 10000 <server_ip>

# Client端(自动遍历所有消息大小)
ib_write_bw -d <dev> -F -c <core_id> -a <server_ip>

参数选择说明:

  • -s 8388608:8MB消息,确保带宽跑满(消息越大,协议开销占比越低)
  • -n 10000:足够多的迭代次数,消除启动波动
  • -F:不自动降MTU(避免跟环境配置不一致)
  • -c:绑定CPU核心,必加

4.3 延迟基线测试

bash 复制代码
# Server端
ib_write_lat -d <dev> -F -c <core_id>

# Client端(小包测最低延迟)
ib_write_lat -d <dev> -F -c <core_id> -s 2 -n 10000 -I <server_ip>

# Client端(自动遍历所有消息大小)
ib_write_lat -d <dev> -F -c <core_id> -a <server_ip>

参数说明:

  • -s 2:最小消息size,测理论最低延迟
  • -I:Inline模式,小包走网卡Inline路径,绕过PCIe内存访问,延迟更低
  • 延迟测试迭代次数不需要太多(1000次足够),但要关注P99和P999

4.4 多流并发测试

单流往往跑不满线速,需要多流并发:

bash 复制代码
# 8流并发带宽测试
ib_write_bw -d <dev> -F -c <core_id> -q 8 -b 64 -s 65536 -n 10000 <server_ip>

# 参数组合:8个QP + 每QP 64个burst + 64KB消息 = 高聚合带宽

4.5 长稳测试

bash 复制代码
# 跑1小时稳定性测试,输出最终结果
ib_write_bw -d <dev> -F -c <core_id> -D 3600 -s 65536 -N <server_ip>

长稳测试关注的不是峰值带宽,而是稳定性------有没有丢包、有没有性能下跌、有没有报错。


五、输出指标详解

5.1 带宽测试输出

复制代码
 #bytes     #iterations    BW peak[Gb/sec]    BW average[Gb/sec]   MsgRate[Mpps]
 65536       5000            97.32              96.85              0.1846
指标 计算方式 验收关注点
BW peak 采样窗口内的最大瞬时带宽 判断硬件极限
BW average 总字节数 / 总时间 验收通过标准,必须达到标称值的95%以上
MsgRate 迭代次数 / 总时间 小包场景的PPS指标

5.2 延迟测试输出

复制代码
 #bytes  #iterations  t_min  t_max  t_typical  t_avg  t_stdev  t_99%  t_99.9%
 65536    1000        1.02   3.56   1.15       1.18   0.15     1.45   2.20
         [usec]       [usec] [usec] [usec]     [usec] [usec]   [usec] [usec]
指标 含义 工程意义
t_min 所有采样中的最小值 理论最佳情况
t_max 所有采样中的最大值 最坏情况,排查长尾问题时关注
t_typical 典型值(众数/中位数) 最能反映正常延迟的指标,比average可靠
t_avg 算术平均值 被大值拉高后失真,参考价值有限
t_stdev 标准差 稳定性指标,越小越稳定
t_99% P99分位延迟 99%的请求都低于此值,业务体验的下限
t_99.9% P99.9分位延迟 千分之一的最坏情况,AI训练/高频交易场景关键指标

P99为什么重要: 假设一个业务有1000次RDMA操作,P99是2μs意味着有10次操作延迟超过2μs。在AI大模型训练中,AllReduce操作需要所有节点同步完成,最慢的节点决定整体速度------这就是所谓的"长尾效应"。


六、常用参数完整手册

6.1 设备与连接参数

参数 全称 说明 默认值
-d device RDMA设备名 第一个可用设备
-i port 端口号 1
-p port 控制通道TCP端口 18515
-x gid-index GID索引(选RoCE v1/v2) 第一个可用GID
-m mtu 路径MTU(1024/2048/4096) 自动协商
-F force 强制不修改MTU 关闭
-R uc 使用UC(不可靠连接) RC
-U ud 使用UD(不可靠数据报) RC
-X xrc 使用XRC 关闭

6.2 测试参数

参数 全称 说明 默认值
-s size 消息大小(字节) BW: 65536, Lat: 2
-n iterations 迭代次数 BW: 5000, Lat: 1000
-a all 自动遍历所有消息大小 关闭
-D duration 按时间测试(秒),替代迭代数 关闭
-N no-echo 不输出中间进度 关闭
-V verify 验证数据正确性 关闭

6.3 性能调优参数

参数 全称 说明 对性能的影响
-q qp 并发QP数量 多流提高聚合带宽
-Q cq-size CQ深度 防止overflow
-b burst 每次post的WR数量 提高带宽,增加延迟
-c cpu 绑定CPU核心 必加,消除调度抖动
-H hugepages 使用巨页 减少TLB miss,提高性能
-I inline 使用Inline数据 小包延迟降低
-S srq 使用共享接收队列 节省内存,UD/Send场景
-l sl 服务级别(优先级) 对应VL和PFC优先级

6.4 特殊测试模式

参数 说明
-u 单向转双向(带宽测试)
-B 双向同时测试(全双工)
-A 原子操作类型(fetch_add / cmp_swp)
-t 反向路径SL
-o 内存偏移量
-r 接收队列深度(Send/UD测试)

七、性能不达预期的系统化排查方法

当perftest结果明显低于预期时,按照以下顺序逐层排查,效率最高。

第一层:硬件层

bash 复制代码
# 1. PCIe链路是否正常?
lspci -s <BDF> -vv | grep LnkSta:
# 期望:Speed 16GT/s (Gen4), Width x16

# 2. 光模块/线缆速率匹配吗?
ethtool -m <netdev> | grep -E "Rate|Speed"

# 3. 网卡温度/状态正常吗?
ethtool <netdev> | grep -E "Link detected|Speed"

第二层:驱动与固件层

bash 复制代码
# 1. 驱动版本是否匹配?
ofed_info -s
modinfo mlx5_core | grep -E "version|firmware"

# 2. 固件版本是否是推荐版?
mlxfwmanager --query   # NVIDIA网卡专用

第三层:系统配置层

bash 复制代码
# 1. CPU绑核对了吗?有没有跨NUMA?
numactl -H
cat /sys/class/net/<netdev>/device/numa_node

# 2. 巨页开了吗?
grep Huge /proc/meminfo

# 3. 中断亲和性配置了吗?
cat /proc/interrupts | grep mlx5

# 4. irqbalance关了吗?
systemctl status irqbalance

第四层:测试参数层

bash 复制代码
# 1. 消息大小够吗?(小包天然带宽低)
# 用 -s 8388608 测大包

# 2. 多流开了吗?
# 用 -q 8 或 -q 16

# 3. Burst够大吗?
# 用 -b 128 或 -b 256

# 4. CQ深度够吗?
# 用 -Q 2048 或更大

第五层:网络层

bash 复制代码
# 1. PFC开了吗?(RoCE场景必须)
# 查交换机配置

# 2. 有没有丢包?
ibv_devinfo -d <dev> -i 1 | grep -E "port_rcv_errors|port_xmit_discards"

# 3. ECN配置对吗?
# 查交换机和网卡的ECN marking配置

八、进阶工具与同类对比

8.1 perftest进阶工具

工具 用途
ib_write_bw_post_list 批量post list测试,优化send策略
raw_ethernet_bw/lat Raw Ethernet模式,非RDMA,用于对比有/无RDMA的性能差
ib_clock_test 两端时钟同步测试,排查延迟测试的时钟偏差

8.2 同类工具对比

工具 层级 特点 适用场景
perftest Verbs层 最底层、最准、功能最全 性能基线、硬件验收
qperf Verbs层 同时测带宽+延迟+CPU占用 快速摸底对比
ibv_rc_pingpong Verbs层 极简,只有连通性测试 链路排障
rping RDMA-CM层 类似ping,连通性+延迟 快速验证
ucx_perftest UCX中间件层 基于UCX框架 UCX生态测试
nccl-tests NCCL框架层 AllReduce/AllGather等集合通信 AI训练真实性能
mpi_perftest MPI层 MPI级别的集合通信测试 HPC场景

结论: perftest是标尺,nccl-tests/mpi_perftest是真实业务场景。做性能验收时,先过perftest(硬件层面达标),再过nccl-tests(业务层面达标),两层都过才算真正达标。

作者简介: 资深RDMA智能网卡、存储技术专家,拥有十余年DPU/RDMA/NVMe SSD芯片测试与工程经验,致力于推动高性能网络技术的开源与普及。

参考资料:

相关推荐
gwf2161 天前
国产RDMA网卡驱动现状、挑战与未来:从内核上游到数据中心实践
rdma·rocev2·linuxkernel·数据中心网络·devicedriver·auxiliarybus·erdma
zuozewei3 天前
第02篇-k6-脚本结构与生命周期
软件测试·jmeter·性能测试·k6·ai 编程
zwleagle3 天前
RDMA基本元素之间的关系
rdma
Eloudy3 天前
OpenSM 管理 IB 网络简介 与 FabricManager 的设计思路
gpu·rdma·roce
泽众云测试4 天前
国产化替代国外性能测试工具推荐:泽众PerformanceRunner
软件测试·测试工具·性能测试
Eloudy4 天前
【无标题】
网络·gpu·rdma·roce
gwf2165 天前
内核态RDMA驱动调试技巧:ftrace/tracepoint/crash分析 —— 深入驱动底层的排错艺术
性能调优·linux驱动·ftrace·rdma·tracepoint·内核调试·crash分析
Eloudy5 天前
Debug Soft-RoCE (RXE) 完整流程
rdma·roce
gwf2166 天前
常见驱动问题定位与解决:设备识别、性能不达预期、CQ错误码 —— 资深RDMA驱动调试排错指南
驱动开发·linux内核·性能调优·rdma·故障排查·mlx5·irdma