
1. 智算集群为什么需要一套“听诊器”搞过大规模训练的人都有一个共同体会集群规模一旦上去故障就不再是“某台机器坏了”这么简单而是变成了一种系统性、间歇性、难以复现的疑难杂症。你可能遇到过训练跑了三天突然 loss 炸了重启之后又好了也可能遇到过某个节点吞吐量莫名其妙比其他节点低 30%但查遍日志什么错误都没有。这类问题靠传统的nvidia-smi和dmesg根本定位不了你需要一套专门为 AI 集群设计的“听诊器”——这就是Benchmark、监控与故障诊断体系存在的意义。这套体系解决的核心问题有三个第一性能基线问题你得知道集群在健康状态下应该跑出什么数字才能判断现在是不是有问题第二实时可观测性问题训练过程中的 GPU 利用率、显存带宽、NVLink 流量、网络 RDMA 吞吐这些指标必须持续采集而不是出事了才去看第三故障归因问题当性能下降发生时能快速定位到是计算、通信、存储还是调度层面的瓶颈。适合读这篇内容的人包括正在搭建或运维 GPU 集群的工程师、负责大模型训练基础设施的 SRE、需要做集群验收和性能调优的技术负责人以及想了解 AI 集群运维体系长什么样的开发者。我会从整体设计思路讲到具体实操包括 NCCL 测试怎么做、Prometheus 怎么采集 GPU 指标、常见故障怎么排查尽量把踩过的坑都摊开讲。2. 整体设计思路从“事后救火”到“事前体检”2.1 为什么传统监控方案在 AI 集群上不够用传统 IDC 监控关注的是 CPU、内存、磁盘、网络带宽这些通用指标用 Zabbix 或者基础的 Prometheus 就能覆盖。但 AI 集群的负载特征完全不同GPU 是核心计算资源它的利用率、显存占用、温度、功耗、ECC 错误、NVLink 带宽这些指标传统工具根本采集不到。更关键的是AI 训练是集合通信密集型的负载一次 AllReduce 操作涉及成百上千张卡同步任何一张卡或任何一条链路出现微小的性能抖动都会拖慢整个通信组进而拖慢整个训练任务。我见过一个真实案例一个 64 卡集群训练吞吐比预期低了 15%查了一周没找到原因最后用 NCCL 的带宽测试逐对检测发现其中两台机器之间的 InfiniBand 链路协商速率从 200Gbps 降到了 100Gbps原因是其中一端的线缆接头有轻微松动。这种问题传统监控完全看不到只有专门的集合通信 Benchmark 才能暴露出来。所以 AI 集群的“听诊器”体系必须包含三个层次基准测试层Benchmark回答“应该多快”、持续监控层Monitoring回答“现在多快”、故障诊断层Diagnosis回答“为什么变慢”。三者缺一不可而且必须形成闭环——Benchmark 提供基线监控对比基线发现异常诊断定位根因。2.2 三层体系的具体分工与工具选型基准测试层的核心工具是 NCCL Tests、GPU Burn、STREAM Benchmark、FIO存储、iperf3网络。其中 NCCL Tests 是重中之重因为集合通信性能直接决定分布式训练效率。NCCL Tests 包含 all_reduce、all_gather、broadcast、reduce_scatter 等多个测试项可以测不同消息大小下的带宽和延迟。持续监控层的标准组合是 Prometheus Grafana DCGM Exporter。DCGM 是 NVIDIA 的数据中心 GPU 管理器它暴露的指标非常全面包括 GPU 利用率、显存使用、SM 活跃度、Tensor Core 活跃度、NVLink 带宽、PCIe 带宽、ECC 错误计数、XID 错误等。Prometheus 负责拉取和存储Grafana 负责可视化。对于网络层可以加上 InfiniBand 的 performance counters 采集对于节点层node_exporter 负责 CPU、内存、磁盘指标。故障诊断层则更多依赖工具组合和排查经验。常用手段包括NCCL 的 debug 日志NCCL_DEBUGINFO、nvidia-smi -q的详细输出、DCGM 的诊断模式dcgmi diag、XID 错误码查询、以及针对性的微基准测试。这一层没有银弹更多是靠体系化的排查流程和积累的经验。注意工具选型不要贪多求全。我见过有团队同时跑了三套监控系统结果数据互相矛盾排查时反而更混乱。建议以 Prometheus DCGM Exporter 为核心其他工具按需补充。2.3 基线建立一切诊断的前提没有基线的监控就是一堆没有意义的数字。建立基线的方法是在集群健康且空闲的状态下跑一轮完整的 Benchmark 套件记录下每个测试项的性能数据。这个基线要包括单卡 FP16/FP32 算力用 GPU Burn 或专门的算力测试、单机内 NVLink 带宽、跨机 InfiniBand 带宽用 NCCL Tests 的 all_reduce、存储读写带宽用 FIO、以及典型训练任务的吞吐tokens/sec 或 samples/sec。基线数据要存档并且标注测试时的环境信息驱动版本、CUDA 版本、NCCL 版本、交换机固件版本、拓扑结构。因为任何一项变更都可能导致基线漂移比如 NCCL 版本升级后 all_reduce 带宽可能提升也可能下降没有版本标注的基线数据是没有参考价值的。3. 核心细节解析NCCL Benchmark 与 GPU 监控实操3.1 NCCL Tests 的正确打开方式NCCL Tests 的编译很简单从官方仓库 clone 下来make就行但关键在于怎么跑才有意义。很多人直接跑一个默认参数的 all_reduce 就完事了这样得到的数据参考价值有限。正确的做法是覆盖多个维度消息大小从 8 bytes 到 8 GB覆盖小消息延迟敏感和大消息带宽敏感两个区间GPU 数量至少测 2 卡、8 卡单机、16 卡、32 卡、64 卡跨机观察扩展效率拓扑感知用NCCL_TOPO_DUMP_FILE导出拓扑确认 NCCL 是否识别到了正确的 NVLink 和 InfiniBand 路径一个典型的 all_reduce 测试命令如下# 8 卡单机 all_reduce 测试 ./build/all_reduce_perf -b 8 -e 8G -f 2 -g 8 # 跨机测试需要 mpirun 或 torchrun 启动 mpirun -np 16 -H node1:8,node2:8 \ -x NCCL_DEBUGINFO \ -x NCCL_IB_HCAmlx5_0,mlx5_1 \ ./build/all_reduce_perf -b 8 -e 8G -f 2 -g 1参数解释-b是起始消息大小-e是结束大小-f是倍增因子2 表示每次翻倍-g是每进程使用的 GPU 数。跨机测试时-g 1表示每个进程用一张卡总共 16 个进程对应 16 张卡。跑完之后重点看两个数字algbw算法带宽和busbw总线带宽。busbw 更能反映实际链路利用率计算公式是busbw algbw * 2 * (n-1) / n其中 n 是参与通信的 GPU 数。对于 8 卡 NVLink 全互联的机器busbw 应该接近 NVLink 的理论带宽对于跨机 InfiniBandbusbw 应该接近 IB 链路带宽的 80% 以上。实操心得跑 NCCL Tests 之前一定要确认 GPU 处于空闲状态并且锁定频率。用nvidia-smi -lgc锁定 GPU 时钟用nvidia-smi -lmc锁定显存时钟否则 GPU 会因为功耗管理动态调频导致测试结果波动很大。我一般会把时钟锁在基频这样测出来的数据可比性最强。3.2 DCGM Exporter 部署与关键指标解读DCGM Exporter 的部署方式取决于你的环境。如果是 Kubernetes 集群用 Helm chart 部署最方便如果是裸机可以用 Docker 跑docker run -d --gpus all --rm \ -p 9400:9400 \ --name dcgm-exporter \ nvcr.io/nvidia/k8s/dcgm-exporter:3.3.0-3.2.0-ubuntu22.04跑起来之后访问http://localhost:9400/metrics就能看到所有指标。指标很多但真正需要重点关注的其实就那么几个指标名称含义异常判断DCGM_FI_DEV_GPU_UTILGPU 计算利用率持续低于 80% 可能有瓶颈DCGM_FI_DEV_MEM_COPY_UTIL显存带宽利用率接近 100% 说明显存瓶颈DCGM_FI_DEV_NVLINK_BANDWIDTH_TOTALNVLink 总带宽突然下降可能是链路问题DCGM_FI_DEV_PCIE_REPLAY_COUNTERPCIe 重传计数持续增长说明 PCIe 有问题DCGM_FI_DEV_XID_ERRORSXID 错误码非零值需要立即排查DCGM_FI_DEV_ECC_DBE_VOL_TOTAL显存双比特错误非零值说明显存硬件故障DCGM_FI_DEV_POWER_USAGE功耗异常低可能是降频DCGM_FI_DEV_GPU_TEMP温度超过 85 度需要关注散热这些指标接入 Prometheus 之后在 Grafana 上配置看板。我建议至少做三个看板集群总览所有 GPU 的利用率热力图、单节点详情单机 8 卡的各项指标曲线、异常告警XID 错误、ECC 错误、温度超限的实时列表。3.3 Prometheus 告警规则配置要点监控没有告警等于没有监控。Prometheus 的告警规则用 YAML 配置以下是我在实际环境中验证过有效的几条核心规则groups: - name: gpu_alerts rules: - alert: GPUXIDError expr: DCGM_FI_DEV_XID_ERRORS 0 for: 1m labels: severity: critical annotations: summary: GPU XID error detected on {{ $labels.instance }} - alert: GPUTemperatureHigh expr: DCGM_FI_DEV_GPU_TEMP 83 for: 5m labels: severity: warning annotations: summary: GPU temperature high on {{ $labels.instance }} - alert: GPUMemoryECCDoubleBit expr: DCGM_FI_DEV_ECC_DBE_VOL_TOTAL 0 for: 1m labels: severity: critical annotations: summary: GPU double-bit ECC error on {{ $labels.instance }} - alert: NCCLBandwidthDrop expr: rate(DCGM_FI_DEV_NVLINK_BANDWIDTH_TOTAL[5m]) 100e9 for: 10m labels: severity: warning annotations: summary: NVLink bandwidth dropped on {{ $labels.instance }}注意告警阈值不要照搬网上的配置。不同型号的 GPU 温度阈值不同A100 和 H100 的功耗曲线也不一样。建议先跑一周的监控观察正常波动范围再设定阈值。告警太敏感会导致“狼来了”效应运维人员逐渐忽略告警这比没有告警更危险。4. 故障诊断实战从现象到根因的排查路径4.1 训练吞吐下降的排查决策树训练吞吐下降是最常见的故障现象但原因可能五花八门。我总结了一套排查决策树按顺序执行可以覆盖 90% 以上的场景第一步确认是全局问题还是局部问题。对比所有节点的 GPU 利用率如果所有节点都低说明是全局性问题可能是数据加载瓶颈、通信瓶颈、或者调度问题如果只有部分节点低说明是局部性问题可能是某张卡降频、某条链路故障。第二步检查 GPU 状态。用nvidia-smi -q查看是否有降频clocks throttle reason、是否有 ECC 错误、是否有 XID 错误。特别关注Clocks Throttle Reasons字段如果显示HW Slowdown或SW Thermal Slowdown说明是散热或功耗问题。第三步检查通信。在训练脚本里设置NCCL_DEBUGINFO和NCCL_DEBUG_SUBSYSALL观察 NCCL 初始化时选择的通信路径。如果发现 NCCL 没有走 InfiniBand 而是走了 TCP socket那性能肯定差。常见原因是NCCL_IB_HCA没设置对或者 IB 驱动有问题。第四步检查存储。如果数据加载是瓶颈GPU 利用率会呈现周期性波动等待数据时降到 0数据来了又升上去。用iostat和fio检查存储带宽是否达到预期。第五步检查 CPU 和内存。数据预处理如果放在 CPU 上做CPU 可能成为瓶颈。用htop看 CPU 利用率如果某个核跑满而 GPU 在等那就是数据加载的问题。4.2 XID 错误码速查与处理XID 错误是 NVIDIA GPU 的硬件级错误码每个码对应不同的故障类型。以下是我实际遇到过的高频 XID 错误XID 码含义处理方式13Graphics engine exception通常是应用程序 bug检查 CUDA 代码31GPU memory page fault显存访问越界检查 kernel 代码43GPU stopped processingGPU 挂起需要重置 GPU48Double-bit ECC error显存硬件故障需要更换 GPU63ECC page retirement显存页退役记录并观察74NVLink errorNVLink 链路故障检查物理连接79GPU has fallen off the busGPU 掉卡通常是硬件或供电问题92High single-bit ECC error rate单比特错误率过高可能发展为双比特94Contained ECC error可纠正的 ECC 错误记录观察95Uncontained ECC error不可纠正的 ECC 错误需要重置 GPU遇到 XID 错误第一步是记录错误码和发生时间第二步是查 NVIDIA 官方的 XID 错误码文档确认含义第三步是根据严重程度决定是重置 GPU、重启节点还是报修硬件。XID 48 和 95 基本意味着 GPU 需要更换XID 74 需要检查 NVLink 线缆和连接器。4.3 NCCL 通信故障的典型场景NCCL 相关的故障有几个经典场景我逐个说一下排查方法。场景一NCCL 初始化超时。训练启动时卡在 NCCL 初始化阶段日志显示NCCL INFO Bootstrap之后就没有下文了。这通常是网络连通性问题检查所有节点之间的 SSH 免密是否配置正确、防火墙是否放行了 NCCL 使用的端口范围、IB 网络是否正常。可以用ibstat检查 IB 卡状态用ibping测试节点间连通性。场景二NCCL 走了错误的通信路径。日志显示NCCL INFO NET/Socket而不是NCCL INFO NET/IB说明 NCCL 没有使用 InfiniBand。检查NCCL_IB_HCA环境变量是否指向了正确的 HCA 设备检查NCCL_IB_DISABLE是否被设为了 1检查 IB 驱动是否加载lsmod | grep ib。场景三AllReduce 带宽远低于预期。用 NCCL Tests 测出来的 busbw 只有理论值的 30%。可能原因包括GPU 降频、NVLink 链路降速、IB 交换机拥塞、NCCL 算法选择不当。可以尝试设置NCCL_ALGORing或NCCL_ALGOTree强制使用不同算法看是否有改善。也可以设置NCCL_PROTOLL或NCCL_PROTOSimple切换协议。场景四训练过程中随机出现 NCCL timeout。这种间歇性故障最难排查。常见原因是某条链路有丢包或误码导致偶发的通信超时。检查 IB 的 error countersperfquery命令如果SymbolErrorCounter或LinkErrorRecoveryCounter在增长说明链路质量有问题。也可能是 GPU 偶发降频导致通信超时检查是否有 XID 错误或温度告警。实操心得NCCL 的日志级别用NCCL_DEBUGWARN就够了INFO级别日志量太大在千卡集群上会把日志系统冲垮。只有在排查特定问题时才临时开到INFO并且只对可疑节点开。另外NCCL_DEBUG_FILE可以把日志写到文件而不是 stderr方便后续分析。5. 监控体系的持续运营与常见问题5.1 监控数据采集频率与存储规划Prometheus 的采集频率直接影响监控精度和存储成本。对于 GPU 指标我建议采集间隔设为 15 秒这个精度足以捕捉到大多数性能波动同时不会产生太大的存储压力。按 1000 张 GPU 计算每张卡约 50 个指标15 秒采集一次每天产生的数据量大约是 1000 × 50 × 5760 2.88 亿个数据点。Prometheus 的压缩率大约是每样本 1-2 字节所以每天约 300-600 MB保留 30 天需要 10-20 GB 存储完全可以接受。如果需要更高精度的数据比如排查瞬时的性能抖动可以临时把采集间隔调到 1 秒但只针对可疑节点排查完就调回去。长期 1 秒采集会导致存储爆炸。Grafana 看板的配置也有讲究。集群总览看板不要放太多面板否则加载慢且信息过载。我一般放四个核心面板GPU 利用率热力图、GPU 温度分布、XID 错误统计、NCCL 带宽趋势。详细指标放到下钻看板里需要时再点进去看。5.2 常见监控问题与排查问题一DCGM Exporter 采集不到数据。首先确认容器是否有--gpus all权限其次确认 NVIDIA 驱动版本和 DCGM 版本是否兼容。DCGM 3.x 需要驱动 450 以上DCGM 3.3 需要驱动 525 以上。如果驱动版本太低升级驱动或者降级 DCGM。问题二Prometheus 抓取目标显示 down。检查 DCGM Exporter 的端口是否监听netstat -tlnp | grep 9400检查 Prometheus 配置的 target 地址是否正确检查防火墙是否放行了 9400 端口。如果是 Kubernetes 环境检查 Service 和 Pod 的标签选择器是否匹配。问题三Grafana 看板显示 No Data。最常见的原因是时间范围选错了或者 Prometheus 数据源配置错误。检查 Grafana 的 Data Source 设置点“Save Test”确认连接正常。如果数据源正常但还是 No Data检查查询语句的指标名称是否和 DCGM Exporter 暴露的一致不同版本的 DCGM Exporter 指标名称可能有差异。问题四监控数据与实际不符。比如nvidia-smi显示 GPU 利用率 90%但 DCGM 显示 60%。这种差异通常是因为采样时间窗口不同。nvidia-smi显示的是瞬时值DCGM 采集的是采样周期内的平均值。另外 DCGM 的 GPU 利用率定义和nvidia-smi可能略有不同以 DCGM 为准即可因为它是专门为数据中心场景设计的。5.3 故障诊断的自动化尝试手动排查故障效率低且依赖经验我尝试过一些自动化手段。最简单的是写一个巡检脚本定期跑 NCCL Tests 和 GPU 健康检查把结果写入数据库发现异常时自动告警。这个脚本用 Python 写就行核心逻辑是调用subprocess执行测试命令解析输出对比基线。更进一步的做法是用 DCGM 的诊断模式dcgmi diag它内置了一套完整的硬件诊断流程包括 GPU 计算测试、显存测试、PCIe 测试、NVLink 测试等。可以设置成每天凌晨自动跑一次生成诊断报告。如果诊断不通过说明硬件可能有问题提前报修避免训练中断。不过自动化诊断也有局限。它只能发现已知的、有明确判断标准的问题对于性能退化这类模糊问题还是需要人工分析监控数据。我的经验是自动化负责“发现异常”人工负责“定位根因”两者配合效率最高。6. 一些踩过的坑和实用建议先说一个最容易被忽略的点GPU 时钟锁定。很多集群为了省电默认开启 GPU 的动态调频。这在推理场景没问题但在训练场景会导致性能波动。我建议在训练节点上通过nvidia-smi -lgc锁定 GPU 时钟到基频或略高于基频显存时钟也锁定。这样虽然功耗高一些但性能稳定可预测。实测下来锁定时钟后 NCCL 带宽测试的波动从 ±15% 降到了 ±3%。第二个坑是NCCL 版本与驱动的兼容性。NCCL 版本更新很快新版本通常性能更好但也可能引入新的 bug。我遇到过升级 NCCL 后 all_reduce 带宽反而下降 20% 的情况回退版本后恢复正常。所以升级 NCCL 之前一定要在测试环境验证确认性能不降反升再上生产。另外 NCCL 版本要和 CUDA 版本匹配CUDA 11.x 配 NCCL 2.10-2.14CUDA 12.x 配 NCCL 2.16 以上。第三个坑是InfiniBand 的 PFC 和 ECN 配置。在 RoCE 环境下PFCPriority Flow Control和 ECNExplicit Congestion Notification的配置直接影响网络性能。配置不当会导致丢包和重传进而导致 NCCL 超时。建议参考交换机和网卡厂商的最佳实践文档来配置不要用默认值。配置完之后用ib_send_bw和ib_send_lat测试一下实际带宽和延迟。第四个坑是监控数据的保留策略。Prometheus 默认保留 15 天数据对于故障排查来说可能不够。我建议至少保留 30 天重要集群保留 90 天。可以用 Prometheus 的 remote write 功能把数据写到长期存储比如 Thanos 或 VictoriaMetrics这样既不影响 Prometheus 的性能又能长期保留数据。最后一个建议建立故障知识库。每次排查完一个故障把现象、排查过程、根因、解决方案记录下来。时间长了这就是团队最宝贵的财富。我现在的团队有一个内部 Wiki记录了上百个故障案例新同事遇到问题先查知识库80% 的情况能直接找到答案。这比任何监控工具都管用。这套“听诊器”体系不是一次建成的而是随着集群规模增长和故障经验积累逐步完善的。从最基础的nvidia-smi巡检开始到部署 DCGM Prometheus Grafana再到建立 NCCL Benchmark 基线和故障知识库每一步都能实实在在提升集群的可用性和训练效率。