3. 基础概念:GPU架构、线程层次、内存层次、性能指标(占用率、吞吐量、延迟)

3.1 GPU架构:从SM到CUDA Core的硬件视角

要读懂Nsight Compute的分析报告,首先需要理解GPU的硬件组织方式。NVIDIA GPU采用流式多处理器(Streaming Multiprocessor, SM)作为基本计算单元。以Ampere架构的A100为例,一颗GPU包含108个SM,每个SM内部又划分为4个处理块,每个处理块包含一组CUDA Core(FP32单元)、Tensor Core、特殊函数单元(SFU)以及加载/存储单元(LSU)。

从软件视角看,CUDA Core执行的是最基础的浮点或整数运算指令;而从Nsight Compute的报告中,你会频繁看到sm__inst_executed、sm__pipe_fma_cycles_active等以sm__为前缀的硬件计数器指标,它们直接反映SM内部各执行流水线的活动状态。理解SM的物理结构,是解读这些计数器含义的前提。

关键认知:GPU的并行能力并非“无限线程同时执行”,而是由有限数量的SM分时复用、以线程束(Warp)为单位调度执行。每个Warp包含32个线程,SM以Warp为最小调度粒度,而非单个线程。

GPU (A100 示例) SM 0 处理块 0 16 CUDA Core 4 Tensor Core 4 LSU / SFU 处理块 1 16 CUDA Core 4 Tensor Core 4 LSU / SFU 共享内存 + 寄存器堆 Shared Mem: 164 KB / SM Registers: 64K × 32-bit / SM 4 个 Warp 调度器 每周期每调度器发射 1 条指令 Warp = 32 线程 SM 1 (同 SM 0 结构) SM 2 (同 SM 0 结构) SM ... A100: 108 SM Nsight Compute 计数器作用域

3.2 线程层次:Grid → Block → Warp → Thread

CUDA的线程组织呈三层结构:Grid(网格)包含多个Block(线程块),每个Block包含若干Thread(线程)。硬件执行时,Block被分配到SM上,SM再将Block中的线程划分为32个一组的Warp执行。Nsight Compute的占用率分析中,launch__occupancy_limit_blocks和launch__occupancy_limit_warps分别表示受Block数量或Warp数量限制的理论占用率上限。

理解线程层次对性能分析至关重要:

  • Block大小影响SM内Block的分配数量。例如,若每个Block含1024线程,则A100的SM(最大2048线程/SM)最多容纳2个Block;若Block为256线程,则可容纳8个Block。
  • Warp发散:若Warp内32个线程执行不同分支,则所有分支路径串行执行,导致指令吞吐下降。Nsight Compute的smsp__warp_issue_stalled_branch_resolving指标可检测此类问题。
  • Block调度:Block间不保证执行顺序,因此跨Block通信只能通过全局内存或原子操作完成。

3.3 内存层次:寄存器 → 共享内存 → 全局内存

GPU内存层次从快到慢、从近到远排列如下:

内存类型 位置 延迟(周期) 容量 作用域
寄存器文件 SM内部 ~1 64K×32bit / SM 单个线程
共享内存 SM内部 ~20-30 164 KB / SM Block内线程
L1缓存 SM内部 ~30-40 256 KB / SM SM内所有线程
L2缓存 芯片级 ~200 40 MB (A100) 整个GPU
全局内存 (HBM) 片外 ~400-800 40 GB (A100) 所有线程

Nsight Compute的内存工作负载分析(Memory Workload Analysis)会分别报告l1tex__data_pipe_lsu_wavefronts_mem_shared(共享内存访问)和l1tex__data_pipe_lsu_wavefronts_mem_global(全局内存访问)等计数器,帮助你判断瓶颈位于哪一级内存。

实践建议:当全局内存访问延迟成为瓶颈时,优先考虑:① 使用共享内存做数据复用;② 确保合并访问(Coalesced Access),即Warp内32个线程访问连续地址;③ 利用只读缓存(__ldg)或纹理路径。

3.4 三大性能指标:占用率、吞吐量、延迟

Nsight Compute的GPU Speed of Light(SOL)章节围绕三个核心指标展开:

3.4.1 占用率(Occupancy)

占用率 = 活跃Warp数 / SM最大可容纳Warp数。它反映SM计算资源的“填满程度”。Nsight Compute显示的理论占用率(Theoretical Occupancy)受三类因素限制:

  • 寄存器限制:若每线程使用过多寄存器,则SM可容纳的线程数减少。
  • 共享内存限制:Block所需共享内存总量超过SM容量时,限制并发Block数。
  • Block大小限制:SM有最大Block数(通常32个)和最大线程数(2048)双重约束。
# Nsight Compute 占用率相关指标示例
launch__registers_per_thread           = 32
launch__shared_mem_per_block_static    = 8192 bytes
launch__occupancy_limit_registers      = 100%  (未受限)
launch__occupancy_limit_shared_mem     = 100%  (未受限)
launch__occupancy_limit_blocks         = 50%   (Block过大导致受限)
launch__occupancy_limit_warps          = 100%

3.4.2 吞吐量(Throughput)

吞吐量指单位时间内完成的操作数或数据量。Nsight Compute将SM内部执行流水线分为:FP32流水线、FP64流水线、Tensor流水线、LSU(加载存储)流水线、ALU(整数运算)流水线等。SOL图会显示各流水线的利用率百分比,若某条流水线接近100%而其他较低,则说明该流水线是计算瓶颈。

3.4.3 延迟(Latency)

延迟是单次操作从发出到完成的时间。GPU通过大量并发线程隐藏延迟,而非减少延迟本身。Nsight Compute的Warp State分析展示Warp处于活动(Active)、等待(Stalled)或阻塞(Blocked)状态的比例。常见的停顿原因包括:

  • long_scoreboard:等待全局内存数据返回
  • short_scoreboard:等待共享内存数据
  • barrier:等待Block内同步
  • mio_throttle:内存输入/输出队列满
  • not_selected:Warp可执行但未被调度器选中

3.5 案例:矩阵乘法内核的瓶颈识别

假设我们分析一个简单的sgemm内核(单精度矩阵乘法),Nsight Compute的SOL报告显示:

Section: GPU Speed of Light Throughput
Compute (SM) Throughput:    78.4%
Memory Throughput:          35.2%

SM Frequency:               1.41 GHz
Memory Frequency:           1.60 GHz
Memory Bandwidth:           1.55 TB/s

Compute Workload Analysis:
  FP32 Pipe:    92.3%   ← 接近饱和
  ALU Pipe:     12.5%
  LSU Pipe:     28.7%
  Tensor Pipe:  0.0%

从上述数据可判断:FP32流水线利用率达92.3%,而内存吞吐仅35.2%,说明该内核是计算密集型,瓶颈在FP32运算单元。优化方向应聚焦于:

  1. 减少冗余浮点运算(如强度削减)
  2. 使用Tensor Core(若精度允许)
  3. 检查是否存在Warp发散导致部分FP32周期空转

若反向观察到Memory Throughput接近100%而Compute较低,则属于内存密集型,应优先优化数据复用和访问模式。

3.6 误区与复盘:常见分析陷阱

误区一:盲目追求100%占用率。高占用率并不总是带来高性能。当内核已受计算吞吐限制时,继续提高占用率只会增加调度开销,无法提升性能。Nsight Compute的SOL图能帮你判断当前是计算受限还是延迟受限。

误区二:忽略Warp发散的影响。即使占用率很高,若Warp内频繁发散,实际指令吞吐会大幅下降。例如一个if-else分支各占一半线程,则两条路径串行执行,有效吞吐减半。应使用smsp__warp_issue_stalled_branch_resolving等指标确认发散程度。

误区三:混淆“理论占用率”与“实际占用率”。Nsight Compute报告的launch__occupancy_limit_*是理论值,而sm__warps_active.avg.pct_of_peak_sustained_active才是实际运行中的平均活跃Warp比例。两者差异可能源于Block调度不均或内核提前退出。

复盘要点:每次性能分析应遵循以下流程——先看SOL图判断计算/内存/延迟哪一端是瓶颈;再深入Warp State查看停顿原因;接着检查占用率限制因素;最后结合内存工作负载确认访问模式是否高效。只有将硬件架构、线程组织、内存层次与三项核心指标联动分析,才能准确解读Nsight Compute报告并制定有效的优化策略。