# PR #27366 完整报告

- 仓库：`sgl-project/sglang`
- 标题：[BugFix]: Fix HiMamba HiCache prefetch hang after L3 sidecar transfer 
- 合并时间：2026-06-05 20:37
- 原文链接：http://prhub.com.cn/sgl-project/sglang/pull/27366

---

# 执行摘要

- 一句话：修复 HiMamba HiCache 预取在 L3 传输后挂起
- 推荐动作：精读价值中等；对于使用 HiCache 和 Mamba 模型的开发者值得关注。建议阅读 `hi_mamba_radix_cache.py` 的 `can_terminate_prefetch` 方法，理解预取生命周期管理。

# 功能与动机

PR body 指出该修复针对 Qwen3.5 HiCache 挂起问题，引用 CI 运行失败链接（https://github.com/sgl-project/sglang/actions/runs/26985767961/job/79634930991），表明在 L3 sidecar 传输后出现挂起，需要确保预取操作在 pool 传输完成前不被终止。

# 实现拆解

1. **定位问题**：在 `hi_mamba_radix_cache.py` 的 `can_terminate_prefetch` 方法中，当操作已完成（`completed` 为 True）但仍有未完成的 pool 传输时，原本的逻辑会错误地允许终止，导致后续同步等待超时。

2. **增加检查**：在第 1665 行（head 版本）插入一个条件判断：若 `completed` 为 True 且 `operation.pool_transfers` 存在且 `operation.pool_transfers_done` 为 False，则将 `can_terminate` 设为 False。这样即使预取数据已传输完成，但只要 pool 端的页面转移还未结束，就不允许终止操作。

3. **变更范围**：仅修改一个文件，新增 3 行代码，无其他改动。

关键文件：
- `python/sglang/srt/mem_cache/hi_mamba_radix_cache.py`（模块 缓存层；类别 source；类型 core-logic；符号 can_terminate_prefetch）: 核心变更文件，新增条件判断防止预取在 pool 传输未完成时终止。

关键符号：can_terminate_prefetch

## 关键源码片段

### `python/sglang/srt/mem_cache/hi_mamba_radix_cache.py`

核心变更文件，新增条件判断防止预取在 pool 传输未完成时终止。

```python
# python/sglang/srt/mem_cache/hi_mamba_radix_cache.py
class HiMambaRadixCache:
    # ...
    def can_terminate_prefetch(self, operation: PrefetchOperation):
        can_terminate = True
        if self.prefetch_stop_policy == "best_effort":
            return can_terminate
        if len(operation.hash_value) == 0:
            completed = False
        else:
            completed = (
                operation.completed_tokens == len(operation.hash_value) * self.page_size
            )
        if self.prefetch_stop_policy == "wait_complete":
            can_terminate = completed
        elif self.prefetch_stop_policy == "timeout":
            can_terminate = completed or self.is_prefetch_timeout(operation)
        else:
            return True
        # Fix: if prefetch completed but pool transfers still ongoing, do NOT terminate
        if completed and operation.pool_transfers and not operation.pool_transfers_done:
            can_terminate = False
        operation_terminated = operation.is_terminated()
        if self.tp_world_size > 1:
            states = torch.tensor(
                [1 - int(can_terminate), int(operation_terminated)],
                dtype=torch.int,
            )
            torch.distributed.all_reduce(
                states,
                op=torch.distributed.ReduceOp.MAX,
                group=self.tp_group,
            )
            can_terminate = states[0].item() == 0
            operation_terminated = states[1].item() == 1
        can_terminate = can_terminate or operation_terminated
        return can_terminate

```

# 评论区精华

Review 中无多轮讨论，只有自动化 bot 的确认。PR 作者和合并者通过 CI rerun 确认修复，包括 rerun 了 hicache 和 unified_radix_tree 测试组，大部分通过，但一个 3fs 相关测试因外部 issue 失败。

- 3fs 存储后端测试失败 (other): 3fs 测试失败是独立问题，本 PR 合并前已确认其他关键测试通过。

# 风险与影响

- 风险：变更仅新增一个条件判断，逻辑清晰，风险较低。但可能对性能有轻微影响：当 pool 传输较慢时，prefetch 会延迟终止，但这是保证正确性的必要代价。需确保 `operation.pool_transfers` 和 `operation.pool_transfers_done` 在所有路径下正确初始化。
- 影响：影响范围：仅 HiMamba HiCache 路径，具体为 Qwen3.5 等使用 HiMamba 缓存模型的预取终止逻辑。修复后避免了因提前终止导致的挂起，提升了系统稳定性。用户无需更改配置。
- 风险标记：核心路径变更 , 缺少测试覆盖

# 关联脉络

- PR #27264 [UnifiedTree]: Sync sidecar component hits across TP ranks and make SWA prefetch all-or-nothing: 同时修改了 HiCache 预取逻辑，涉及 sidecar 传输和预取终止；本 PR 进一步修复了该改动中未被覆盖的 pool 传输场景。