资讯详情

资讯详情

rdma-core 高性能 RDMA 应用实战:从设备发现到 CQ 调优的完整路径

rdma-core 高性能 RDMA 应用实战从设备发现到 CQ 调优的完整路径【免费下载链接】rdma-coreRDMA core userspace libraries and daemons项目地址: https://gitcode.com/GitHub_Trending/rd/rdma-core如果你在 25G 网络上跑 TCP send/recv 时发现每传一个 4KB 消息都要付出一次系统调用、一整段协议栈处理和内存拷贝的代价大概率已经想过换 RDMA。rdma-core 正是 Linux 内核 RDMA 子系统的用户态配套它用 libibverbs、librdmacm 等库让应用直接访问 InfiniBand、RoCE 等 RDMA 硬件做到零拷贝传输与内核旁路这就是它成为高性能网络底座的原因。本文按从零跑通一条完整 RDMA 链路的顺序结合 rdma-core 仓库里真实存在的示例与文档讲清楚开发流程、连接建立的两种路线和生产环境里最容易被坑的几个点适合准备动手写第一个 RDMA 应用的工程师。 先搞懂性能从哪来设备节点和 verbs 指令别急着写代码先建立一个正确的心理模型。rdma-core 里所有库都是围绕内核导出的设备节点工作的/dev/infiniband/uverbsN对应 libibverbs/dev/infiniband/rdma_cm对应 librdmacm/dev/infiniband/umadX对应管理面库 libibumad。你在 providers/ 目录下能看到 mlx5、efa、irdma、siw 等十几个子目录每个子目录就是某个内核驱动比如 mlx5_ib、efa.ko的用户态实现——库本身是通用的硬件差异被隔离在这些 provider 里。所谓verbs本质上是发给硬件的指令集合建队列对QP、投递工作请求WR、查询完成队列CQ。数据搬运动作由网卡 DMA 直接完成CPU 只负责下指令和收完成通知内核网络栈完全不在数据路径上。这也是为什么性能能做到微秒级延迟——绕开的不是某一次拷贝而是整条内核路径。用户态与内核之间共享的 ABI 定义可以翻 kernel-headers/rdma/ 下的头文件比如 ib_user_verbs.h排障或写 provider 时用得上。 最小可运行链路三步建好设备、内存与传输通道以下调用序列浓缩自仓库里的 RC PingPong 示例它用 Reliable Connection可靠连接队列跑 send/recv是学 verbs 最经典的一条路径。第一步发现设备并打开上下文。这段在做设备枚举、打开设备并分配保护域int n; struct ibv_device **list ibv_get_device_list(n); struct ibv_context *ctx ibv_open_device(list[0]); struct ibv_pd *pd ibv_alloc_pd(ctx);注意先检查 n 是否大于 0而且 list 里的设备顺序不代表你的网卡顺序生产代码里应按设备名ibv_get_device_name匹配别偷懒写死下标。想快速列出本机有哪些 RDMA 设备仓库自带 device_list 示例对应的命令行工具 ibv_devices、ibv_devinfo 也出自同一个库。第二步注册内存区域。这段在把一段堆内存注册成对网卡可见的 MRMemory Regionchar *buf malloc(65536); struct ibv_mr *mr ibv_reg_mr(pd, buf, 65536, IBV_ACCESS_LOCAL_WRITE | IBV_ACCESS_REMOTE_READ | IBV_ACCESS_REMOTE_WRITE);这里最容易被坑注册内存需要内核锁住物理页如果ulimit -l只显示几十 KB默认值常常就是 32注册直接失败要通过 limits.conf 调大libibverbs 文档里专门有一段讲这个。另外访问权限只开了 LOCAL_WRITE 的话远端发起的 READ/WRITE 会被硬件拒绝——权限是按谁发起区分的别配错。第三步建 CQ 和 QP投递请求并轮询完成。rc_pingpong.c 里 QP 状态机走的是 INIT→RTR→RTS 三步对端信息qpn、psn、lid/gid通过一条普通 TCP 连接交换这是 verbs 裸写的标准套路struct ibv_sge sge { .addr (uintptr_t)buf, .length len, .lkey mr-lkey }; struct ibv_send_wr wr { .wr_id 1, .sg_list sge, .num_sge 1 }, *bad; ibv_post_send(qp, wr, bad); struct ibv_wc wc; while (!ibv_poll_cq(cq, 1, wc)) ;注意 poll 返回后要检查 wc.statusIBV_WC_SUCCESS 之外的值比如 RNR、RETRY_EXC就是排障线索另外 RC 队列跑 send/recv 时对端必须提前 post 好数量足够的 recv WR否则消息会被网卡按 RNR 规则处理。 连接建立的两条路线裸 verbs 与 rdma_cm上面用 TCP 交换 QP 信息的方式虽然透明但要自己处理寻址、GID 选择、端口状态代码量不小。如果不想碰这些librdmacm 提供的 RDMA Connection Manager 把建链过程封装成了类 socket 的 API仓库里的 rping 示例 就是完整示范rdma_create_id(channel, id, id, RDMA_PS_TCP); /* 收到 RDMA_CM_EVENT_ESTABLISHED 回调后 */ rdma_connect(id, conn_param); rdma_create_qp(id, pd, init_attr);注意 rdma_create_qp 必须在收到 ESTABLISHED 事件之后调用地址解析、端口状态迁移都由 CM 替你完成rdma_cm 内部依赖 ARP 做地址解析这在后面坑的部分会展开。选择依据很简单需要完全控制连接属性比如做库、做中间件就裸写 verbs业务层只需要连上然后传数据就用 rdma_cm。连接型RC之外还有无连接型UD玩法librdmacm 的 examples 目录下 udaddy.c、udpong.c 可以看 UDP 风格的用法。⚡ CQ 轮询还是事件驱动pingpong 系列示例默认是忙轮询busy poll一个线程死循环调 ibv_poll_cq好处是完成到可见的延迟最低代价是烧一个核。另一条路是事件驱动——建 CQ 时传一个 comp_channel用 epoll 等 ibv_get_cq_event仓库里的 asyncwatch 示例 演示了如何同时盯 CQ 事件和设备异步事件。经验法则是延迟敏感的短路径轮询长连接、多队列并存的事件驱动很多生产系统折中成先 poll 一小段没完成再睡进 epoll。配套的两个手段一是批量 WR一次 post_send 里挂一串链表二是选择性发信号IBV_SEND_SIGNALED低流量场景下让大部分 WR 不产生完成通知能显著减少 CQ 压力。rc_pingpong.c 里对这些选项都有开关读它的 main 函数参数表比读十遍手册快。️ 生产环境必踩的四个坑没硬件不等于没法开发。rdma-core 自带软件 RDMA 驱动没有 RDMA 网卡时执行modprobe rdma_rxe或 siw再rdma link add NAME type rxe netdev DEVICE就能在普通以太网口上跑全套 verbsrxe 文档 和 README 的 Usage 一节都有说明。CI 里验证逻辑用 rxe性能调优才上真卡。多网卡机器上 CM 可能选错口。librdmacm 文档 明确写了多接口场景要设sysctl net.ipv4.conf.all.arp_ignore2否则 ARP 可能从错误的接口应答IP 到 RDMA 设备的映射就歪了同机 loopback 测试则还要加accept_local1。这两个 sysctl 我见过不止一次把人卡半天。调试先开日志再怀疑人生。库支持VERBS_LOG_LEVEL和VERBS_LOG_FILE环境变量输出调试信息见 libibverbs 文档配合 perfquery、ibv_devinfo 观察端口计数器和错误统计能覆盖大部分消息没到但没报错类问题。别急着上多线程。单线程 轮询 少量大深度 QP 的组合在多数吞吐场景下优于多线程拆分锁竞争和跨核缓存迁移的开销常常超过它省下的东西。等单线程模型跑到了硬件瓶颈再考虑 per-queue 线程切分。下一步可以做什么与其通读文档不如把 rc_pingpong.c 当主线读一遍——从 pingpong_dest 结构体到 QP 状态迁移它把一条 RC 链路需要的所有决定都摊在明面上读完后用 tests/ 里的 Python 测试框架test_qp.py、test_atomic.py 等在自己设备上跑回归它会自动遍历设备、端口和 GID。还有一个值得深思的判断在确定架构前先确认你的负载是否真的需要 RDMA——如果消息在 1KB 以下、连接数上万用户态 TCP 加好的内核参数未必输RDMA 的主场在大块数据 延迟敏感这一侧。想往硬件特性走tag matching 文档 里描述的 MPI 风格收包匹配是 mlx5 等 provider 已经落地的方向那是下一个值得研究的性能来源。【免费下载链接】rdma-coreRDMA core userspace libraries and daemons项目地址: https://gitcode.com/GitHub_Trending/rd/rdma-core创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
觉得有用,分享给同行:

为您的企业打造数字门面

稳重轻奢商务风格,端正雅致视觉,长效耐看不易过时。

立即咨询 →