Prhub

#27863 [Fix][MTP][MM] Fix EAGLE v2 chunked-prefill next-token chain crash on multimodal models due to placeholder tokens

原始 PR 作者 litmei 合并时间 2026-06-15 21:30 文件变更 1 提交数 4 评论 10 代码增减 +10 / -3

执行摘要

修复 EAGLE3 多模态 chunked-prefill crash

运行多模态模型并启用 SpecV2 时触发崩溃。调试发现崩溃发生在 embedding 层,归因于 PR #26800 引入的 _compute_chunked_req_next_prompt_token 方法未考虑多模态场景——多模态输入中的 placeholder/padding token 值可能远超 vocab_size,导致 embedding 层越界错误。

该 PR 是一个精准的定点 bugfix,改动量小,逻辑清晰,值得精读以理解多模态与 speculative decoding 交互时的边界情况。设计决策中值得关注的是:不对占位符 token 做硬编码过滤,而是依赖 vocab_size 作为通用判据——既简洁又与模型无关。

讨论亮点

未发现实质性的审查讨论。PR 由 sglang-npu-bot 自动批准,无 review 评论。

实现拆解

  1. 增加 vocab_size 参数并在调用处传参:在 python/sglang/srt/managers/schedule_batch.py 中,修改 _compute_chunked_req_next_prompt_token 函数签名,新增 vocab_size: int 参数。在 ScheduleBatch.init_new 中调用该函数时,传入 model_config.vocab_size
  2. 添加 token 有效性检查:在函数内部,从 chunked_req.origin_input_ids 获取待处理的 token id 后,先检查该 id 是否小于 vocab_size;只有合法 token 才返回,否则返回 None。
  3. 简化局部变量:将 chunked_req.origin_input_ids 提取为局部变量 origin_ids,提升可读性。
  4. 添加文档字符串:为新逻辑添加 docstring,说明其作用是跳过多模态占位符(hash)token。
文件 模块 状态 重要度
python/sglang/srt/managers/schedule_batch.py 调度器 modified 5.99

关键符号

_compute_chunked_req_next_prompt_token ScheduleBatch.init_new

关键源码片段

python/sglang/srt/managers/schedule_batch.py core-logic

核心修复文件,包含 `_compute_chunked_req_next_prompt_token` 的修改和调用处传参调整。

def _compute_chunked_req_next_prompt_token(
    chunked_req: Optional[Req],
    vocab_size: int,
) -> Optional[int]:
    """Return the next real prompt token after the fill boundary, skipping
    multimodal placeholder (hash) tokens that lie outside the model vocab."""
    if chunked_req is None:
        return None
    fill_len = chunked_req.fill_len
    origin_ids = chunked_req.origin_input_ids
    if fill_len >= len(origin_ids):
        return None
    # 多模态 placeholder 的 token id 往往远大于 vocab_size(例如 hash 值),
    # 直接索引 embedding 会越界崩溃。这里通过 vocab_size 边界检查过滤之。
    if origin_ids[fill_len] < vocab_size:
        return int(origin_ids[fill_len])
    return None

评论区精华

没有提炼出高价值讨论线程

当前评论区没有形成足够清晰的争议点或结论,后续有更多讨论时会体现在这里。

风险与影响

修复非常集中,仅修改一个函数的参数和逻辑,且增加了显式的词表边界检查,回归风险极低。风险主要是:若 vocab_size 获取不正确(例如 model_config.vocab_size 为 None 或错误值),可能导致意外行为;但现有代码中该值总能正确获取。另外,若模型 tokenizer 在特殊 token 的 id 设计上小于 vocab_size 但实际不应作为下一个 prompt token,本次修复不会过滤此类情况——不过此类场景很少,不影响本次 fix 目标。

影响范围:启用 Speculative Decoding V2(EAGLE3)且处理多模态请求的场景。修复前会崩溃,修复后正常运行。影响程度:仅对特定配置组合生效,不影响普通 prefill 或非多模态请求。用户影响:修复了特定场景的崩溃,用户无需修改配置即可受益。

修复范围小,风险低

关联 Issue

未识别关联 Issue

当前没有检测到明确关联的 Issue 链接,后续同步到相关引用后会出现在这里。

完整报告

参与讨论