第三部分 · 1 / 6
高层工具的
cmd 性能工具
理论讲完了,来看能直接跑的东西。cmd/ 下有 8 个独立命令,前 6 个对标 C 版
perftest,后 2 个测的是高层 rdmanet API。
每个工具不带地址就是服务端,带对端地址就是客户端。
8 个工具
| 工具 | 对标 | 传输 | 连接方式 |
|---|---|---|---|
go_send_bw | ib_send_bw | RC, UD | TCP 或 rdma_cm |
go_send_lat | ib_send_lat | RC, UD | TCP 或 rdma_cm |
go_write_bw | ib_write_bw | RC | TCP |
go_write_lat | ib_write_lat | RC | TCP |
go_read_bw | ib_read_bw | RC | TCP |
go_read_lat | ib_read_lat | RC | TCP |
go_rdmanet_bw | —(高层) | rdmanet | rdma_cm |
go_rdmanet_lat | —(高层) | rdmanet | rdma_cm |
命名规律
名字由「操作 + 指标」拼成,正好对应第一部分讲的操作类型:
send
双边 Send/Recv,最接近 socket 语义;唯一支持 UD(
-c UD)的一组。write
单边 RDMA Write,发起方直接写进对端内存。
read
单边 RDMA Read,发起方直接从对端内存读。
*_bw:测带宽(Gb/s),持续打流、统计吞吐。*_lat:测时延(往返),可加--output=histogram出完整分布。
它们怎么搭起来的
每个工具的 main.go 都很薄,真正的逻辑在共享的 perftest 包里。以 go_send_bw 为例:
func run(cfg perftest.Config) error {
ep, mr, _ := perftest.SetupTCPOrCM(cfg) // 建资源 + 握手/CM
defer ep.Close(); defer mr.Close()
res, _ := perftest.RunSendBW(cfg, ep, mr) // 打流并统计
perftest.PrintBW(os.Stdout, res) // 客户端打印结果
}
也就是说,cmd 工具是第一部分那「七步流程」的完整实操样本——想看底层 API 怎么用,
读 perftest/ 包是最好的范例。
高层工具的 --batch
go_rdmanet_bw 默认用 SendMsg 逐条发送,是延迟受限的——同一时刻只有一条消息在飞,
吞吐 ≈ 1/单条往返延迟,远喂不满网卡(这也是它默认明显慢于 go_send_bw 的原因)。
加上 --batch N(简写 -b N)后,客户端改用 SendBatch、服务端用 RecvBatch,
每次保持 N 条在飞,接近 perftest 工具的流水线吞吐。配合 --poll busy 去掉事件唤醒延迟效果更好:
# 服务端(两端 -b 要一致)
./bin/go_rdmanet_bw -d mlx5_1 -x 3 -b 32
# 客户端:批量 + 忙轮询
./bin/go_rdmanet_bw -s 65536 -n 1000000 -d mlx5_1 -x 3 -b 32 --poll busy 33.0.226.25:18515
仍有差距是正常的
即便开了
--batch 和 --poll busy,go_rdmanet_bw 通常仍略低于 go_send_bw——
rdmanet 多了消息分帧、信用流控、bounce 拷贝这些为「易用、保留消息边界、带背压」付出的固定成本。
这正是两层 API 的取舍:要榨干硬件用底层 gordma(perftest 即范例)。
下一步
这些工具共享一套命令行参数。下一节是 通用命令行参数 速查。
gordma 教程