【Bug已解决】[Bug]:  GPU coredump during FlashInfer `trtllm_bf16_moe` autotune with Qwen3.5-35B-A3B on B2 【Bug已解决】[Bug] GPU coredump during FlashInfertrtllm_bf16_moeautotune with Qwen3.5-35B-A3B on B200 (DP2 EP) 解决方案一、现象长什么样在 B200Blackwell, sm_100上跑Qwen3.5-35B-A3BMoE并行配置是DP2 EP首次推理时在 FlashInfer 的 MoE 内核autotune自动调优阶段整个进程直接GPU coredumpGPU coredump captured for process ... (SIGSEGV in trtllm_bf16_moe kernel)或者驱动层看到CUDA error: an illegal instruction was encountered (during FlashInfer autotune)几个特征崩在autotune 阶段不是正常推理阶段——也就是「找最优 kernel 配置」那一步就炸了。只在B200上炸换 H100/H200 能过sm_90 上那个坏候选没被选中或不触发。只在Qwen3.5-35B-A3BDP2 EP这个组合下炸单独 EP 或更小模型有时能过。崩的是进程级 coredumpPython 层面抓不到异常因为 GPU 硬件故障直接 SIGSEGV不会变成 Python 异常只能重启。本质FlashInfer 的 autotune 会枚举一堆候选 kernel 配置不同 tile 大小、stage 数、workspace 大小逐一试跑找出最快的。其中某个候选配置在 B200 DP2EP 的特定张量形状下算出的 workspace / scratch 尺寸或 tile 维度越界触发 GPU 硬件缺页 → coredump。autotune 在试跑前没有校验候选的「可行性」于是坏候选一launch就炸穿进程。二、背景先说 autotune 是什么。GPU kernel 的性能对「块大小block size、流水线级数num stages、shared memory 用量」这些参数极度敏感。FlashInfer 为了在给定形状下跑最快会在第一次遇到某个形状时枚举一组候选配置每个都实际 launch 一次、测耗时选最快的。这个过程叫 autotune结果会缓存起来供后续复用。问题出在「枚举的候选里有一个在 B200 上是坏的」B200 是 sm_100shared memory / 寄存器 / workspace 上限和 sm_90 不同。某个候选用了一个在 sm_90 合法、但在 sm_100 上溢出的 tile / stage 组合。Qwen3.5-35B-A3BDP2 EP决定了 MoE 的「token 数 × expert 数 × 隐藏维度」形状。autotune 针对这个形状挑候选恰好命中那个坏候选。坏候选 launch 时workspace 缓冲区被越界写或 tile 维度触发非法指令GPU 硬件直接 fault → 进程 coredump。为什么 Python 抓不到因为 coredump 是GPU 硬件级故障沿驱动上报为 SIGSEGV发生在 GPU 侧、异步于 Python 解释器Python 的try/except管不到。所以这类问题不能靠「try 一下」来恢复只能靠「别让坏候选被 launch」来预防。三、根因根因是autotune 在 launch 候选 kernel 前没有校验候选配置在当前设备B200和当前张量形状下的「硬件可行性」导致一个 workspace/tile 越界的坏候选被实际执行、触发 GPU coredump三层第一层主因候选配置未做设备能力校验。autotune 的候选列表是「写死的一组经验配置」没有针对sm_100的 workspace 上限、max shared memory、max tile 维度做过滤。于是 sm_90 上合法的候选在 B200 上 launch 即越界。第二层workspace 大小按「乐观估计」分配没留校验余量。trtllm_bf16_moe的 autotune 候选需要一块 scratch workspace。某候选实际需要的 workspace 比分配的大因为 B200 上 token 分布形状不同写入越界 → GPU 缺页。分配侧和 launch 侧对 workspace 大小的算法不一致是典型根因。第三层DP2EP 放大了触发概率。EP 下 token 要先 all-to-all 重排token 在每张卡上的「每 expert 的 token 数」分布特殊DP2 又让这个分布翻倍变化。autotune 正是在这个特殊形状下枚举候选恰好选中坏候选的概率被这两个并行维度显著放大。一句话autotune 枚举的候选里有一个在 B200DP/EP 形状下 workspace/tile 越界launch 即 GPU coredump且 Python 无法捕获只能预防。四、最小可运行复现下面用纯 Python 模拟「autotune 枚举候选、不校验设备能力就 launch、坏候选触发 crash不可恢复的 SIGSEGV 等价物」的控制流不需要 GPUclass DeviceCaps: def __init__(self, sm, max_shared_mem, max_workspace): self.sm sm self.max_shared_mem max_shared_mem self.max_workspace max_workspace def candidate_configs(): # 经验写死的候选列表含一个对 sm_100 越界的 return [ {tile: 64, stages: 2, workspace: 1024}, # sm_90 良性 {tile: 256, stages: 8, workspace: 8192}, # sm_90 良性 {tile: 512, stages: 16, workspace: 99999}, # sm_100 上越界 ] def launch(cfg, caps): # 不校验直接 launch坏候选触发不可恢复故障 if cfg[workspace] caps.max_workspace or cfg[tile] 256: raise RuntimeError(GPU coredump (SIGSEGV) - unrecoverable) return cfg def autotune_buggy(caps, shape): best None for cfg in candidate_configs(): try: launch(cfg, caps) except RuntimeError: # 注意真实的 GPU coredump 根本到不了 except进程已死 # 这里只是演示「若能被捕获也不该让坏候选静默通过」 continue best cfg return best def main(): caps DeviceCaps(sm100, max_shared_mem256, max_workspace8192) try: autotune_buggy(caps, dp2_ep) except RuntimeError as e: print(复现成功:, e) if __name__ __main__: main()跑出来会打印复现成功: GPU coredump (SIGSEGV) - unrecoverable模拟了「坏候选 launch 即崩、且本不该被静默放过」。真实场景里这一步直接 coredump连except都进不去。五、解决方案第一层最小直接修复最省事的救火关掉 autotune固定使用一个已知在 B200 上安全的 kernel 配置避免坏候选被 launch# FlashInfer / vLLM 通常提供关闭 autotune 的开关 llm LLM( modelQwen3.5-35B-A3B, # 关键禁用 MoE kernel autotune使用默认经验安全配置 override_pooler_configNone, # 或通过环境变量 / 编译配置固定 compilation_config{ cudagraph_capture_mode: kernel, }, )更具体FlashInfer 的 MoE 常支持环境变量跳过 autotune# 禁用 FlashInfer 的 trtllm_moe autotune不同版本变量名可能不同 export FLASHINFER_DISABLE_MOE_AUTOTUNE1 # 或固定 workspace 上限 export TRTLLM_MOE_MAX_WORKSPACE8192 vllm serve Qwen3.5-35B-A3B --tensor-parallel-size 1 ...如果你确认哪个候选是坏的也可以把并行度降一档比如 DP1 或 EP 减小组避开那个触发形状——这是临时规避的常用手段。六、解决方案第二层结构性改进第一层是「避开 autotune」第二层是「让 autotune 在 launch 前校验候选的设备可行性并给 workspace 留硬上限」从设计上消灭坏候选被 launchfrom dataclasses import dataclass from typing import List, Dict dataclass class DeviceLimits: sm: int max_shared_mem: int max_workspace: int max_tile: int def feasible(self, cfg: Dict) - bool: # 候选必须满足设备硬限制否则直接排除 if cfg[workspace] self.max_workspace: return False if cfg[tile] self.max_tile: return False if cfg[stages] * cfg[tile] self.max_shared_mem: return False return True def autotune_safe(limits: DeviceLimits, shape: str) - Dict: feasible [c for c in candidate_configs() if limits.feasible(c)] if not feasible: raise RuntimeError( f没有可行的 MoE kernel 候选shape{shape} 请检查 B200 的 workspace 上限配置或降低并行度 ) # 在「已校验可行」的候选里选最快这里用估算耗时代替真实 launch return min(feasible, keylambda c: estimate_cost(c, shape)) def estimate_cost(cfg: Dict, shape: str) - float: # 真实实现里是 launch 测时这里用近似 return cfg[tile] * cfg[stages] / 1000.0同时把 workspace 分配改成「按 limits 校验后分配且 launch 前再比对一次」def allocate_workspace(cfg: Dict, limits: DeviceLimits) - int: need compute_workspace_need(cfg) # launch 侧真实需求 assert need limits.max_workspace, ( f候选 {cfg} 需要 workspace {need} 上限 {limits.max_workspace} ) return need这样坏候选在「进入 launch」之前就被feasible过滤掉永远不会触发 GPU coredump。七、解决方案第三层断言 / CI 守护把「候选可行性校验」「workspace 不越界」「B200 专用候选集」固化成测试import pytest def test_bad_candidate_excluded_on_b200(): limits DeviceLimits(sm100, max_shared_mem256, max_workspace8192, max_tile256) feasible [c for c in candidate_configs() if limits.feasible(c)] # 那个 workspace99999 的坏候选必须被排除 assert all(c[workspace] 8192 for c in feasible) def test_autotune_safe_returns_feasible(): limits DeviceLimits(sm100, max_shared_mem256, max_workspace8192, max_tile256) best autotune_safe(limits, dp2_ep) assert limits.feasible(best) def test_autotune_raises_when_none_feasible(): limits DeviceLimits(sm100, max_shared_mem1, max_workspace1, max_tile1) with pytest.raises(RuntimeError): autotune_safe(limits, dp2_ep) def test_workspace_alloc_checked(): limits DeviceLimits(sm100, max_shared_mem256, max_workspace8192, max_tile256) bad {tile: 64, stages: 2, workspace: 99999} with pytest.raises(AssertionError): allocate_workspace(bad, limits) def test_no_coredump_shape_dp_ep(): # 端到端DP2EP 形状下autotune 不应选中坏候选 limits DeviceLimits(sm100, max_shared_mem256, max_workspace8192, max_tile256) chosen autotune_safe(limits, dp2_ep) assert chosen[workspace] limits.max_workspace再加一个「禁用 autotune 开关」的回归def test_disable_autotune_uses_safe_default(): cfg resolve_moe_config(disable_autotuneTrue, deviceB200) assert cfg[autotune] is False assert cfg[tile] 256 # 用经验安全默认不枚举八、排查清单看是否崩在 autotune 阶段日志里有autotune/trtllm_bf16_moe/tuning且是进程级 coredump非 Python 异常→ 坐实本问题。是否只在 B200sm_100炸、H100 能过 → 是设备相关候选越界。临时救火FLASHINFER_DISABLE_MOE_AUTOTUNE1关 autotune或降 DP/EP 避开触发形状。检查 coredump 报告里 fault 的 kernel 是否是trtllm_bf16_moe确认 autotune 候选问题。长期修复autotune 前按 DeviceLimits 过滤候选workspace 分配加断言校验。升级 FlashInfer / vLLM 到合了 B200 候选校验的版本并跑上面的「坏候选剔除」用例。若 coredump 无法复现稳定用cuda-gdb/compute-sanitizer抓越界写的具体行。九、小结B200 上 FlashInfertrtllm_bf16_moeautotune 的 GPU coredump不是模型或 B200 硬件坏了而是autotune 枚举的候选里有在 B200 DP2EP 形状下 workspace/tile 越界的坏配置launch 即触发 GPU 硬件故障、进程级 coredump且 Python 无法捕获只能预防。最小修复是关 autotune 或降并行度避开触发形状结构性修复是 autotune 前按设备能力过滤候选、workspace 分配加断言最后用 pytest 把「坏候选剔除」「workspace 不越界」「B200 专用候选集」锁死。抓住「不可恢复的 GPU 故障只能预防、不能 try/except」这条所有 autotune/coredump 类问题都要从「不让坏配置 launch」入手。

相关新闻

最新新闻

微信聊天记录永久保存终极指南:3步轻松导出HTML/Word/CSV完整教程

微信聊天记录永久保存终极指南:3步轻松导出HTML/Word/CSV完整教程

微信聊天记录永久保存终极指南:3步轻松导出HTML/Word/CSV完整教程 【免费下载链接】WeChatMsg 提取微信聊天记录,将其导出成HTML、Word、CSV文档永久保存,对聊天记录进行分析生成年度聊天报告 项目地址: https://gitcode.com/GitHub_Trendi…

2026/7/30 21:51:41
BFOA-LSTM混合算法在无人机路径规划中的应用

BFOA-LSTM混合算法在无人机路径规划中的应用

1. 项目概述:当生物智能遇上深度学习去年在给某农业无人机项目做路径优化时,我遇到了一个典型困境:传统A*算法规划的路径虽然最短,但遇到突发风场变化时,无人机响应总是慢半拍。这促使我开始尝试将生物启发算法与LSTM时…

2026/7/30 21:51:41
微信聊天记录如何永久保存?3步导出完整备份终极指南

微信聊天记录如何永久保存?3步导出完整备份终极指南

微信聊天记录如何永久保存?3步导出完整备份终极指南 【免费下载链接】WeChatMsg 提取微信聊天记录,将其导出成HTML、Word、CSV文档永久保存,对聊天记录进行分析生成年度聊天报告 项目地址: https://gitcode.com/GitHub_Trending/we/WeChatM…

2026/7/30 21:51:41
VMware虚拟机硬盘扩容完整指南:从底层原理到实战避坑

VMware虚拟机硬盘扩容完整指南:从底层原理到实战避坑

1. 项目概述与核心价值给VMware虚拟机硬盘扩容,这事儿听起来简单,不就是点点鼠标、改改数字吗?但真上手操作过的朋友都知道,这里面的坑可不少。我见过太多人,包括一些运维老手,在扩容后要么系统里看不到新增…

2026/7/30 21:51:41
AI因子工程的终极瓶颈在哪?——揭秘头部量化团队正在封存的4类非结构化另类数据清洗黑箱

AI因子工程的终极瓶颈在哪?——揭秘头部量化团队正在封存的4类非结构化另类数据清洗黑箱

更多请点击: https://intelliparadigm.com 第一章:AI因子工程的终极瓶颈在哪?——揭秘头部量化团队正在封存的4类非结构化另类数据清洗黑箱 当主流量化机构仍在用传统NLP pipeline处理社交媒体情绪时,顶级对冲基金已将93%的另类数…

2026/7/30 21:51:41
从同步到异步:使用asynq重构Python代码的10个实用技巧

从同步到异步:使用asynq重构Python代码的10个实用技巧

从同步到异步:使用asynq重构Python代码的10个实用技巧 【免费下载链接】asynq Python library for asynchronous programming 项目地址: https://gitcode.com/gh_mirrors/asy/asynq asynq是一个强大的Python异步编程库,它能帮助开发者轻松地将同步…

2026/7/30 21:46:40

月新闻