Misc. bug: Hexagon: dma_queue_push’s stride overflow fallback breaks callee expectations

该报错通常出现在 llama.cpp Hexagon(HTP/HVX)后端加载并执行大模型时,DMA 队列在 stride overflow 回退路径中提前 flush,破坏了调用方对 push/pop 数量及 dst 指针的预期,进而让 DSP 崩溃。优先确认是否运行在 HVX < 75 的 He

快速结论:该报错通常出现在 llama.cpp Hexagon(HTP/HVX)后端加载并执行大模型时,DMA 队列在 stride overflow 回退路径中提前 flush,破坏了调用方对 push/pop 数量及 dst 指针的预期,进而让 DSP 崩溃。优先确认是否运行在 HVX < 75 的 Hexagon 后端,并升级到包含 #29197 修复的版本。

适用环境:llama.cpp 版本 3173a5;操作系统 Windows;受影响模块为 libllama (core library);触发平台为 Snapdragon X Elite;触发场景为运行 Qwen-3.8-27B;触发路径为 HVX < 75 上的 stride overflow 回退,stride = 69632,位于 transfer_activation_chunk_f32_to_f16。

最快修复方案:升级到包含 #29197 修复的 llama.cpp 版本(该 Issue 已标记 Fixed in #29197)。Issue 中未给出其他已验证的一步修复方案。

注意事项:正文中贴出的“删除最后无条件 dma_queue_flush”的补丁只是当时的临时改动,作者本人也认为该做法很可能不正确,不要把它当作正式修复。官方修复涉及 DMA 接口重构(为 64 位 DMA 做准备),建议以合并后的 #29197 为准。

问题场景

用户在 Windows 上使用 llama.cpp 的 Hexagon(HTP/HVX)后端,尝试在 Snapdragon X Elite 上运行 Qwen-3.8-27B。运行过程中进入 dma_queue_push 的 stride overflow 回退分支(HVX < 75),随后 DSP 崩溃。报错定位在 ggml/src/ggml-hexagon/htp/dma-queue.h 的 dma_queue_push,崩在 transfer_activation_chunk_f32_to_f16 且 stride = 69632 的传输上。

报错原文

Misc. bug: Hexagon: dma_queue_push's stride overflow fallback breaks callee expectations

原因分析

核心原因是 dma_queue_push 在 “Stride overflow” 回退路径中调用了 dma_queue_flush,破坏了调用方对接口的约定:

  • 调用方预期 “做了多少次 dma_queue_push,就能做同样多次 dma_queue_pop”,但回退路径中的 flush 可能把之前已经 push 的项一并刷掉,从而打破这个数量对应关系。
  • 另一种常见用法是 dma_queue_pop(q).dst,并期望拿到的 dst 就是当初传给 dma_queue_push 的那个 dst。回退路径会让取回的 dst 变成 dst + (n_rows - 1) * dst_stride,与预期不符。

维护者确认了这个场景确实被遗漏,并指出不能直接 flush 早先的事务,因为会破坏 _pop().dst/src 的用法;可能的原因是回退路径需要一个临时 ring 来缓存这些项,以便按需 enqueue/flush。该修复随后被并入为 64 位 DMA 做接口重构的 PR #29197。

环境排查

  • 确认 llama.cpp 版本是否为 3173a5 或同样包含旧版 dma-queue.h 的提交。
  • 确认运行平台是否为 Snapdragon X Elite 等 Hexagon(HTP/HVX)环境。
  • 确认 HVX 版本是否低于 75,因为该回退路径只在 HVX < 75 的 stride overflow 情况下进入。
  • 确认触发时的 stride 大小(本 Issue 为 69632)以及是否发生在 transfer_activation_chunk_f32_to_f16。
  • 若使用自定义补丁(例如去掉最后无条件 flush 的改动),先回退到官方代码再复现,以排除补丁本身引入的问题。

解决步骤

  1. 记录当前运行的模型、llama.cpp 提交版本和平台信息,确认问题发生在 Hexagon 后端的 stride overflow 回退路径上。
  2. 不要采用“直接删掉 dma_queue_flush”的临时 diff 作为长期修复,Issue 作者本人认为该改动很可能不正确。
  3. 更新 llama.cpp 到包含 #29197 修复的版本,该 PR 在做 64 位 DMA 接口重构的同时修复了此问题。
  4. 更新后重新用同样条件(Qwen-3.8-27B、Snapdragon X Elite、相同量化与运行参数)复现,确认不再进入崩溃。

验证方法

用升级后的版本重新运行先前触发崩溃的相同模型与命令,观察 DSP 是否仍然崩溃。如果 dma_queue_push 不再在 stride overflow 回退中提前 flush、且 dma_queue_pop 返回的 dst/src 与 push 时一致,则说明调用方对 push/pop 数量和指针的预期已被恢复。需要说明的是,Issue 中未提供修复后的具体日志或回归结果,此验证方式基于对问题成因的推断。

参考来源

ggml-org/llama.cpp #27979

GamsGo AI

AI 工具推荐

想把多个 AI 模型放在一个入口?

GamsGo AI 集成 ChatGPT、DeepSeek、Gemini、Claude、Midjourney、Veo 等常用模型,适合写作、绘图、视频和日常 AI 工作流。

了解 GamsGo AI

推广链接:通过此链接购买,我可能获得佣金,不影响你的价格。

这个方案解决了吗?

celebrityanime
celebrityanime
文章: 25698

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注