ARTICLE DETAIL

建站实战干货

来自一线的建站与推广经验沉淀,每一条都经过真实交付验证。

基于 HCCL AIV 通信引擎开发 ReduceScatter 自定义通信算子:完整实战指南

2026/9/18 12:55:05 拓冰建站 浏览量
基于 HCCL AIV 通信引擎开发 ReduceScatter 自定义通信算子:完整实战指南 基于 HCCL AIV 通信引擎开发 ReduceScatter 自定义通信算子完整实战指南【免费下载链接】hccl集合通信库Huawei Collective Communication Library简称HCCL是基于昇腾AI处理器的高性能集合通信库为计算集群提供高性能、高可靠的通信方案项目地址: https://gitcode.com/cann/hccl导读本文基于 CANN HCCL 开源仓库中的examples/06_custom_ops_reduce_scatter/aiv样例系统讲解如何基于 AIVAI Vector通信引擎从零开发一个 ReduceScatter 自定义集合通信算子涵盖工程目录设计、Host 侧算子逻辑、Device 侧 Kernel 实现、资源申请与通道建立、编译安装包生成以及基于 MPI 的多卡测试验证全流程。读完本文你将掌握 HCCL 自定义通信算子的完整开发范式能够照此方法扩展实现 AllReduce、AllGather 等其它集合通信算子。一、样例总体介绍本样例的核心目标是绕过 HCCL 内置算子逻辑直接基于 AIV 通信编程接口实现 ReduceScatter 集合通信算子。ReduceScatter 的语义是通信域内每个 rank 将自己的完整输入数据按 rank 数均分对每个分片在所有 rank 上做规约如 SUM最终每个 rank 得到对应自己分片的规约结果。样例的主要功能点基于 AIVAI Vector通信引擎实现 ReduceScatter 集合通信算子包含 Host 侧算子逻辑与 Device 侧 Kernel 实现两者通过OpParam结构体传递参数提供完整的 CMake 编译构建流程与基于 MPI 的多卡测试验证流程。从仓库结构看整个样例位于 examples/06_custom_ops_reduce_scatter其下又分为aiv/AIV 引擎实现本文主题、ccu/CCU 实现与testcase/测试用例三个子工程体现了 HCCL 自定义算子支持多种通信引擎的设计理念。二、工程目录结构解析样例的目录结构如下来自 aiv/README.md 并补充了源码文件说明├── CMakeLists.txt # 根目录编译/构建配置文件 ├── op_host/ │ ├── CMakeLists.txt │ ├── reduce_scatter.cc # HcclReduceScatterCustom 算子Host侧实现 │ ├── launch_kernel.cc # Kernel 下发逻辑实现 │ └── launch_kernel.h # Kernel 下发接口定义 ├── op_kernel/ │ ├── CMakeLists.txt │ └── launch_kernel_asc.asc # 算子 Kernel 侧实现 (Ascend C) └── inc/ ├── hccl_custom_reduce_scatter.h # 自定义算子对外接口头文件 ├── common.h # 公共类型定义与宏 ├── aiv_reduce_scatter_mesh_1d.h # AIV ReduceScatter 核心算法实现 ├── aiv_communication_base_v2.h # AIV 通信基类 ├── log.h # 日志工具 ├── extra_args.h # 额外参数定义 └── sync_interface.h # 同步接口定义各模块职责划分op_host/运行在 Host 侧的算子逻辑。reduce_scatter.cc负责组装参数、申请通信资源、建立通道launch_kernel.cc负责加载 kernel 二进制并通过 ACL 接口下发到 Device。op_kernel/Device 侧 Ascend C kernel。launch_kernel_asc.asc定义HcclReduceScatterAivKernel入口按数据类型分发到具体的模板实现。inc/公共头文件。common.h中定义了 Host 与 Device 共享的OpParam参数结构体和数据类型字节大小表aiv_reduce_scatter_mesh_1d.h是 1D Mesh 拓扑下的核心通信算法。三、环境准备3.1 环境要求本样例支持以下产品组网为单机 N 卡N2Ascend 950PR / Ascend 950DT需要说明的是AIV 通信引擎的可用性与硬件平台强相关以上产品列表是当前样例明确声明支持的范围换用其它型号硬件时需以实际支持的通信引擎为准。3.2 安装 CANN Toolkit 开发套件包参考昇腾文档中心的 CANN 软件安装指南安装最新版本 CANN Toolkit 开发套件包。CANN Toolkit 提供了编译自定义算子所需的hccl_comm.h、hccl_res.h、hcomm_primitives.h等头文件以及libhccl.so、libascendcl.so等运行库。3.3 配置环境变量以 root 用户默认安装路径为例执行source /usr/local/Ascend/cann/set_env.sh此外运行测试用例需要 MPI 环境支持请确保已安装并配置好 MPI。MPI 配置请参考配套版本的昇腾文档中心 HCCL 性能测试工具使用指南中的MPI 安装与配置章节。MPI 在本样例中承担两个职责一是通过MPI_Init/MPI_Comm_rank/MPI_Comm_size获取全局 rank 与总进程数二是通过MPI_Bcast将 0 号 rank 生成的HcclRootInfo根节点信息广播给所有进程用于建立通信域。四、编译与运行4.1 编译自定义算子库样例提供了基于 CMake 的构建流程在仓库根目录下执行以下命令bash build.sh --vendorcust --opsreduce_scatter_aiv --custom_ops_path./examples/06_custom_ops_reduce_scatter/aiv参数说明--vendor自定义算子标识这里为cust对应 CANN 的opp/vendors/cust自定义算子厂商目录--ops自定义算子名称reduce_scatter_aiv对应aiv子工程的实现--custom_ops_path自定义算子工程路径即仓库根目录下的./examples/06_custom_ops_reduce_scatter/aiv。从 aiv/CMakeLists.txt 可以看到构建过程会通过find_package(ASC REQUIRED)引入 Ascend C 编译工具链project(hccl_custom_${OP_NAME} LANGUAGES CXX ASC)同时编译 C 与 ASCAscend C kernel 源文件并将对外头文件hccl_custom_reduce_scatter.h安装到自定义算子头文件目录。构建中还会将 op_kernel/CMakeLists.txt 编译生成的 kernel 二进制与 op_host/CMakeLists.txt 编译生成的 Host 侧动态库一起打包进安装包。4.2 安装算子包自定义算子安装包生成在./build_out目录下通过--install参数进行安装./build_out/cann-hccl_custom_reduce_scatter_aiv_linux-arch.run --install --install-pathascend_cann_path其中arch是当前编译环境的系统架构如aarch64或x86_64ascend_cann_path是可选参数表示 CANN 软件包安装目录。默认为ASCEND_CUSTOM_OPP_PATH或ASCEND_OPP_PATH环境变量所在的 CANN 软件包路径。自定义算子包安装后的关键产物头文件${ASCEND_HOME_PATH}/opp/vendors/cust/include/hccl_custom_reduce_scatter.h动态库${ASCEND_HOME_PATH}/opp/vendors/cust/lib64/libhccl_custom_reduce_scatter.so其中${ASCEND_HOME_PATH}为 CANN-Toolkit 安装路径。该动态库即测试程序需要链接的自定义算子库见 testcase/CMakeLists.txt 中的target_link_libraries(... hccl_custom_reduce_scatter)。4.3 运行测试用例测试代码位于 testcase/main.cc已在前节编译自定义算子库中一并编译。测试样例二进制文件路径为./build/examples/06_custom_ops_reduce_scatter/testcase/custom_reduce_scatter_test从仓库根目录开始执行以下命令export LD_LIBRARY_PATH${ASCEND_HOME_PATH}/opp/vendors/cust/lib64:${LD_LIBRARY_PATH} cd build/examples/06_custom_ops_reduce_scatter/testcase/ mpirun -n rank_size ./custom_reduce_scatter_test data_len参数说明rank_size使用的卡数data_len数据长度每个 rank 接收分片包含的元素个数。测试用例支持两种运行模式由是否定义ENABLE_MPI宏决定MPI 模式ENABLE_MPI各 MPI 进程分别绑定设备0 号进程生成HcclRootInfo后经MPI_Bcast广播所有进程通过HcclCommInitRootInfo建立通信域线程模式单进程内创建rank_size个线程每个线程绑定一块设备共享同一份HcclRootInfo同样通过HcclCommInitRootInfo建立通信域。4.4 预期结果运行成功后终端将输出类似以下的日志信息以 2 卡运行为例来自 aiv/README.md[1786071476.120968] [Rank 0] MPI Initialized. World Size: 2 [1786071476.120968] [Rank 1] MPI Initialized. World Size: 2 [1786071476.127411] [Rank 0] Device 0 selected (Total devices: 8) [1786071476.127411] [Rank 1] Device 1 selected (Total devices: 8) [1786071478.023709] [Rank 0] Root info generated [1786071478.023786] [Rank 0] HCCL set device[0] [1786071478.023778] [Rank 1] HCCL set device[1] [1786071483.214938] [Rank 0] HCCL Comm Initialized [1786071483.221873] [Rank 0] Buffers allocated and initialized [1786071483.254098] [Rank 1] HCCL Comm Initialized [1786071483.259378] [Rank 1] Buffers allocated and initialized rank1 dataLen1024 time835 ms [1786071484.095144] [Rank 1] VerifyResult Passed! rank0 dataLen1024 time873 ms [1786071484.095200] [Rank 0] VerifyResult Passed!日志中的关键节点对应测试用例的执行阶段MPI 初始化 → 设备选择 → RootInfo 生成与广播 → 设置设备 → 通信域初始化 → 缓冲区分配与初始化 → 执行自定义算子 → 结果校验通过。五、源码级解析自定义算子如何工作5.1 对外接口定义自定义算子的对外 API 定义在 hccl_custom_reduce_scatter.h签名与 HCCL 内置HcclReduceScatter保持一致的调用习惯HcclResult HcclReduceScatterCustom( void* sendBuf, void* recvBuf, uint64_t recvCount, HcclDataType dataType, HcclReduceOp op, HcclComm comm, aclrtStream stream);各参数含义sendBuf发送缓冲区Device 侧内存长度为recvCount * rankSize个元素recvBuf接收缓冲区Device 侧内存长度为recvCount个元素recvCount每个 rank 接收分片的元素个数dataType数据类型如HCCL_DATA_TYPE_FP32op规约操作如HCCL_REDUCE_SUMcomm已初始化的 HCCL 通信域句柄streamACL 任务流。5.2 Host 侧实现reduce_scatter.ccHost 侧核心逻辑位于 op_host/reduce_scatter.cc整个执行流程分为三步第一步申请 AIV 通信上下文缓冲区InitAivBuffer调用HcclEngineCtxGet/HcclEngineCtxCreate以CommEngine::COMM_ENGINE_AIV引擎类型申请一块 2MB 的标签缓冲区AIV_TAG_BUFF_LEN 2 * 1024 * 1024定义于 common.h清零后通过HcclCommMemReg注册到通信域并获得HcclMemHandle。缓冲区按算子 tag 缓存在g_memHandleCache中带互斥锁保护避免重复申请。注意AIV_TAG_ADDR_OFFSET 16 * 1024的偏移量设计缓冲区前 16KB 存放远端 rank 的发送缓冲区地址表偏移之后存放接收缓冲区地址表。第二步建立通道BuildChannelRequests/AcquireChannelsAndBuffers通过HcclRankGraphGetLayers获取网络分层、HcclRankGraphGetLinks获取本地 rank 与每个远端 rank 之间的链路信息筛选出COMM_PROTOCOL_UB_MEMUB 内存协议的链路为每个远端 rank 构建一个HcclChannelDesc通道描述notifyNum 3即每个通道需要 3 个通知信号。随后调用HcclChannelAcquire批量申请通道并通过HcclChannelGetHcclBuffer与HcclChannelGetRemoteMems获取本地与远端的通信缓冲区地址填入buffersIn/buffersOut数组。第三步组装参数并下发 KernelHcclReduceScatterCustom通过HcclGetCommName获取通信域名拼接生成算子 tag格式commName_opbase通过HcclGetRankId/HcclGetRankSize获取当前 rank 与总 rank 数计算param.len recvCount * SIZE_TABLE[dataType]字节数SIZE_TABLE定义了各数据类型的字节大小设置切片步长inputSliceStride param.len、outputSliceStride param.len、repeatNum 1等 Mesh 1D 算法参数将本 rank 的发送缓冲区地址写入buffersIn[rank]、接收缓冲区地址写入buffersOut[rank]连同远端地址表一并拷贝到 AIV 缓冲区中使 Device 侧 Kernel 可以直接索引调用LaunchKernel(param, stream)完成下发。5.3 Kernel 下发机制launch_kernel.ccKernel 的加载与下发实现在 op_host/launch_kernel.cc采用加载一次、多次复用的注册机制RegisterKernel从hccl_custom_reduce_scatter_kernels.o二进制文件读取编译产物依次调用aclrtCreateBinary、aclrtBinaryLoad、aclrtBinaryGetFunction获取HcclReduceScatterAivKernel函数句柄。整个过程由互斥锁和原子变量g_init保护保证单例注册ExecuteKernelLaunch构造aclrtLaunchKernelCfg配置设置三个关键属性ACL_RT_LAUNCH_KERNEL_ATTR_SCHEM_MODE 1启用 scheme 模式调度ACL_RT_LAUNCH_KERNEL_ATTR_TIMEOUT_US超时时间取CUSTOM_TIMEOUT * 1000000微秒CUSTOM_TIMEOUT 1836见 common.hACL_RT_LAUNCH_KERNEL_ATTR_ENGINE_TYPE ACL_RT_ENGINE_TYPE_AIV指定在 AIV 引擎上执行最终通过aclrtLaunchKernelWithHostArgs(g_funcHandle, 1, stream, cfg, param, sizeof(OpParam), nullptr, 0)将整个OpParam结构体以 Host 参数形式原样传递给 Device Kernel。5.4 Device 侧 Kernel 实现launch_kernel_asc.ascDevice 侧入口定义在 op_kernel/launch_kernel_asc.asc是一个extern C __global__ __aicore__内核函数按param.dataType分发到具体类型模板extern C __global__ __aicore__ void HcclReduceScatterAivKernel(OpParam param) { switch(param.dataType) { case AscendC::HCCL_DATA_TYPE_INT8: CALL_AIV_KERNEL(int8_t); break; case AscendC::HCCL_DATA_TYPE_INT32: CALL_AIV_KERNEL(int32_t); break; case AscendC::HCCL_DATA_TYPE_FP16: CALL_AIV_KERNEL(half); break; case AscendC::HCCL_DATA_TYPE_FP32: CALL_AIV_KERNEL(float); break; default: break; } }CALL_AIV_KERNEL宏将OpParam的各字段展开为AivReduceScatterMesh1DT的形参包括输入/输出地址、rank/rankSize、三维拓扑尺寸xRankSize/yRankSize/zRankSize本样例仅使用 1D Mesh故yRankSize/zRankSize置 0、数据长度、规约操作、切片步长与 repeat 参数等。5.5 核心算法AivReduceScatterMesh1D核心通信算法位于 aiv_reduce_scatter_mesh_1d.h类AivReduceScatterMesh1DOp继承自AivCommBase定义于 aiv_communication_base_v2.h算法分两个阶段阶段一本 rank 数据搬入通信区InitCoreInfo按coreId对总数据量做均分含余数分配计算出每个 AIV Core 负责的字节偏移coreOffset与元素数curCount。Run中首先执行CpGM2GM将本 rank 输入数据中属于自己分片的部分rank_ * stride coreOffset拷贝到本 rank 的 AIV 通信缓冲区随后调用Record(rank_, GetBlockIdx() * FLAG_SIZE flagOffset, curTag)记录完成标志PipeBarrierPIPE_ALL()保证流水线同步。阶段二跨 rank 规约遍历所有 rankWaitFlag等待对应远端 rank 的数据就绪标志然后将本 rank AIV 缓冲区中远端 rank 对应分片的数据累加到自己的输出缓冲区output_ coreOffsetCpGM2GM(output, gmOthers, curCount, reduceOp_)携带规约操作符。最终每个 rank 的输出缓冲区即所有 rank 对应分片的规约结果。从源码实现可以推断该算法采用先本地数据上板、再逐 rank 规约累加的 Mesh 1D 通信模式通信量在 rank 间直接对等交换配合Record/WaitFlag标志机制实现跨卡同步属于典型的 AIV 通信原语组合。六、测试用例设计要点测试程序 testcase/main.cc 的验证逻辑设计值得借鉴数据构造每个 rank 的发送缓冲区填充float(rank TEST_DATA_VALUE)其中TEST_DATA_VALUE 2026即 rank0 全为 2026.0、rank1 全为 2027.0……接收缓冲区清零期望值计算float sum (TEST_DATA_VALUE TEST_DATA_VALUE rankSize - 1) * rankSize / 2即等差数列求和。对 FP32 SUM 规约而言每个 rank 分片的期望值都等于所有 rank 数据的累加和结果校验VerifyResult将接收缓冲区拷回 Host逐元素与期望值比较容差1e-5全部通过则打印VerifyResult Passed!性能观测使用high_resolution_clock统计HcclReduceScatterCustom调用到aclrtSynchronizeStream返回的耗时并打印rankN dataLen... time... ms。测试用例通过 testcase/CMakeLists.txt 链接ascendcl、hccl、hccl_custom_reduce_scatter三个库MPI 模式下追加 MPI 库并显式设置_GLIBCXX_USE_CXX11_ABI0与-stdc17与 CANN 运行时保持 ABI 一致。七、小结与扩展建议本文完整走通了环境准备 → 编译 → 安装 → 运行 → 验证的 HCCL AIV 自定义 ReduceScatter 算子开发链路并从源码层面剖析了 Host 侧资源申请/通道建立/参数组装、Kernel 加载下发、Device 侧 Mesh 1D 规约算法与测试验证机制。如果想基于此样例做扩展可参考以下方向更换规约操作修改HcclReduceScatterCustom传入的op参数如HCCL_REDUCE_MAX并确认 Device 侧CpGM2GM携带的reduceOp_支持对应操作扩展数据类型在launch_kernel_asc.asc的 switch 分支中增加如HCCL_DATA_TYPE_INT16、HCCL_DATA_TYPE_FP64等类型分支移植到其它集合通信算子本样例的工程骨架op_hostop_kernelinc三段式结构、OpParam参数传递、RegisterKernel单例注册同样适用于 AllGather、AllReduce 等算子的自定义实现仓库中的 05_custom_ops_allgather 即提供了 AIV 版 AllGather 的对照实现。需要注意的是本样例的运行前提是Ascend 950 系列硬件、已安装 CANN Toolkit 且版本配套、MPI 环境可用。AIV 通信引擎与底层 UBR 链路能力在不同型号硬件上存在差异实际部署时请以硬件规格与 CANN 版本文档为准。【免费下载链接】hccl集合通信库Huawei Collective Communication Library简称HCCL是基于昇腾AI处理器的高性能集合通信库为计算集群提供高性能、高可靠的通信方案项目地址: https://gitcode.com/cann/hccl创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考