Kernel(算子)
2026/7/23大约 9 分钟
在 AI Infra、大模型底层架构和高性能计算(HPC)的语境下,算子(Kernel / Operator) 是指一段在硬件芯片(如 GPU、CPU、TPU)上真正执行特定数学运算、数据排布或分布式通信的底层核心代码。
如果把大模型算法看作是一张精美的“建筑设计图纸”,那么算子就是真正在前线搬砖、砌墙、打地基的“施工工人”。芯片本身无法直接读懂高层的 Python 神经网络代码,必须依靠算子将这些抽象逻辑翻译成成千上万个线程如何读写显存、如何操纵硬件计算单元(如 Tensor Core)的物理执行指令。
一、 算子的物理工作机理与软硬件映射
当算法工程师在高级框架(如 PyTorch)中写下最简单的一行:C = A + B(两个大矩阵相加),底层的 Element-wise Add(逐元素相加)算子 会被触发并执行以下动作:
- 线程与网格编排(Grid & Block Topology):算子代码会向 GPU 申请成千上万个并发线程,并将它们划分为多个线程块(Thread Blocks)。这些块被组织成网格(Grid),映射到 GPU 的物理计算单元(流多处理器,SM)上。
- 硬件寻址与数据加载(Load):每个线程根据自己的编号(Thread ID/Block ID),计算出自己应该负责矩阵的哪一个行、哪一个列(物理内存偏移量),然后发出指令,从慢速的片外主显存(HBM/VRAM)中读取对应的 $A_{i,j}$ 和 $B_{i,j}$ 数据。
- 片上流水线计算(Compute):数据被加载到 GPU SM 内部的寄存器(Registers)或片上超高速缓存(SRAM/Shared Memory)中,调用算术逻辑单元(ALU)进行物理加法运算。
- 结果写回(Store):算完后,线程再次发起内存总线请求,把计算结果 $C_{i,j}$ 精准地写回到显存的指定物理地址中。
这一整套规定了“线程怎么分、数据怎么搬、硬件怎么算、结果怎么写”的底层 C++/Triton/汇编代码,就叫作一个算子。
二、 工业界最核心的三大算子家族
在大模型预训练、微调与大规模高并发推理服务中,算力集群每天都在高频疯狂调用以下三类算子:
- 计算密集型算子(Compute-Bound Operators)
- 代表:GEMM(通用矩阵乘法)算子、Conv3D(三维卷积)算子。
- 物理特征:它的计算访存比(Operational Intensity)极高。也就是说,搬运少量的字节(Bytes),就需要进行海量的浮点数运算(FLOPs)。大模型里最吃算力的 Linear 层、LM Head 层,底层全是一次次 GEMM 算子。
- 访存密集型算子(Memory-Bound Operators)
- 代表:LayerNorm/RMSNorm(层归一化)算子、Softmax 算子、GELU/SiLU(激活函数)算子、Element-wise Add(逐元素相加)算子。
- 物理特征:计算逻辑极其简单(通常只是简单的加减乘除、指数开方),但需要高频、大吞吐地读写显存。由于 GPU 的片外显存带宽(HBM)速度远远慢于 SM 内部的计算速度,这类算子会导致 GPU 的计算单元(Tensor Core)经常处于“等数据输入输出”的饥饿转圈状态。它是拉低模型整体 MFU(模型利用率)的头号罪魁祸首。
- 分布式通信与数据编排型算子(Communication & Utility Operators)
- 代表:NCCL 集合通信算子(如 AllReduce, AllGather, ReduceScatter)、时空 Tokenization(视频切片 Patching)算子、Transpose/Reshape(张量转置与重排)算子。
- 物理特征:不负责具体的模型数学推理,但负责调度数据流和算力集群协同。它们频繁触发跨节点、跨显卡的高带宽网络传输,或者在显存内重构张量的物理连续性。
三、 算子优化的核心手段(如何榨干硬件性能)
算子优化的终极目标是:在有限的 GPU 功耗和显存带宽下,榨干 Tensor Core 的每一维算力,完全抹平计算与搬运之间的时间差,消除一切不必要的显存(HBM)读写。 核心技术外挂包括:
1. 算子融合(Kernel Fusion)
- 原理:将多个在数学上连续执行的算子(例如
矩阵乘法 + Bias添加 + GELU激活 + LayerNorm)合并写入同一个底层 Kernel 中。 - 物理收益:原生 PyTorch 会为每个操作拉起一个独立的算子,导致中间结果频繁在 HBM 中“写进去、读出来”。融合算子让数据被加载到 GPU 片上的超高速缓存(SRAM/Shared Memory)后,在内部一口气算完所有非线性逻辑,自始至终只对片外主显存进行一次读取和一次写回,瞬间消除 Memory-Bound 瓶颈。
2. 分块计算与分级缓存复用(Tiling & Blocking)
- 原理:面对数万维的超大矩阵,算子不可能将其一次性塞入芯片。优化算法会将巨型矩阵物理切碎为适合 GPU 寄存器、L1/L2 Cache、SRAM 大小的“小瓷砖(Tiles)”。
- 物理收益:通过精密的循环展开(Loop Unrolling)和索引计算,确保计算单元在处理这块 Tile 时,所有相关的中间变量都在片上高速缓存中高频循环复用,最大化减少对慢速主显存的总线请求。
3. 异步数据搬运与计算重叠(Asynchronous Pipelining & Overlap)
- 原理:利用现代 GPU(如 Ampere, Hopper, Blackwell 架构)底层的硬件级异步拷贝指令(如
cp.async)。 - 物理收益:传统的算子是“读一块数据 $\rightarrow$ 算一块数据 $\rightarrow$ 再读下一块”。优化后的多级流水线允许“计算单元(SM/Tensor Core)正在疯狂暴算当前第 $N$ 个 Tile”的同时,“数据异步搬运单元正在悄悄将第 $N+1$ 个 Tile 的数据从 HBM 运往 SRAM”。两者在物理时间轴上完全重叠(Overlap),实现硬件完全零等待。
4. 显存合并访存与对齐(Coalesced Memory Access)
- 原理:GPU 的显存控制器是以 32 字节、64 字节或 128 字节的硬件“内存段(Memory Segments)”为单位进行批量并发读取的。
- 物理收益:如果同一个 Warp(32个线程)在同一时刻访问的内存地址在物理上是连续的、对齐的,GPU 只需要发动一次显存总线事务(Bus Transaction)就能把全量数据填满;反之,如果非连续访存(如多模态视频跨帧采样、稀疏算子),会触发几十次零碎的总线事务,导致带宽利用率暴跌。优化算子需要手工设计线程索引布局(Layout),强行实现全量合并访存。
四、 现代工业界算子优化工具链
为了应对算子优化极其陡峭的门槛,目前业界已经分化出几大极其好用且硬核的编译器和专用语言工具链:
- OpenAI Triton(全行业标配,Python 战 CUDA 的神兵)
- 机制:它是一门基于 Python 的领域专用语言(DSL)。它抛弃了 CUDA 琐碎的“单线程单标量”视角,改用块级(Block-level)编程。
- 优势:你用 Python 编写数据块之间的乘加逻辑,Triton 编译器在后台利用 MLIR(多级中间表示编译器框架) 自动帮你完成最恶心的寄存器分配、共享内存同步、指令流水线编排和内存对齐。它的性能逼近原生 CUDA,大名鼎鼎的 FlashAttention 大部分代码都已采用 Triton 落地。
- NVIDIA cuTile / TileGym(英伟达官方新一代编程范式)
- 机制:NVIDIA 专为 GPU 设计的全新并行编程模型,提供了一个基于 Python 的 DSL 接口,核心围绕 Tile-based(分块) 架构进行编译优化。
- 优势:它是英伟达官方用来在“Python 开发高性能算子”这一生态上对冲 Triton 的核武器。cuTile 将代码编译为新打造的 CUDA Tile IR,能以官方姿态更极致地榨干 Hopper(H100/H200)和 Blackwell(B200/B300)架构的硬件底层微架构红利。
- Cutlass / CuTe(英伟达 C++ 极限硬件肉搏库)
- 机制:英伟达官方开源的、纯 C++ 模板驱动的通用矩阵乘法(GEMM)高阶库。
- 优势:其中的 CuTe 组件将物理存储抽象成极具数学美感的
Layout(形状与步长)。它是专门用来直接操纵 Tensor Core 硬件物理极限的工具。大模型中最顶尖的变长注意力机制、稀疏矩阵微调算子,往往需要由高级 Infra 工程师用 Cutlass 精密魔改出来。
五、 系统化攻克算子优化的路线图建议
算子优化是一门典型的动手物理学,建议采取“打牢底层硬件认知 $\rightarrow$ 跑通高回报工具 $\rightarrow$ 研读行业经典实现 $\rightarrow$ 性能数据调优”的升级路线:
- 第一步:看清显卡的物理构造(建立物理直觉):不要急着写代码,先去看《CUDA Programming Guide》。弄明白一个 Grid 怎么分成多个 Block,一个 Block 怎么包含 32 个线程的 Warp;搞懂为什么 Shared Memory 会发生 Bank Conflict(Bank 冲突)导致减速。
- 第二步:死磕 Triton 官方 Tutorials(建立开发肌肉记忆):克隆
openai/triton仓库,进入python/tutorials目录。把里面的经典例子(01-vector-add.py、02-fused-softmax.py、03-matrix-multiplication.py)的代码全部删掉,不看答案自己亲手重写调通。你会直观体会到什么叫指针偏移寻址,以及怎么通过算子融合干掉 Softmax 的显存延迟。 - 第三步:生啃行业神作(对齐大厂线上实战):去研读
Dao-AILab/flash-attention的源码,搞懂它如何利用 Online Softmax 算法在片上 SRAM 里一边分块计算一边动态更新最大值和分母,从而完全不往显存里写那张庞大的 Attention 矩阵。 - 第四步:亮出 Nsight Compute 性能画笔(定量调优):学会使用 NVIDIA 的 Nsight Compute (NCU) 分析工具去抓取你的算子。在跑代码时,死死盯着两个指标调优:
Memory Throughput(显存带宽利用率)和Tensor Statistics(Tensor Core 吞吐率)。通过不断微调 Triton 或 cuTile 中的BLOCK_SIZE和num_warps,直到把这两根性能柱状图完全顶满,即大功告成。
