Qwen3.5-27B × Ascend 910A × Transformers 适配踩坑总结
环境:Qwen3.5-27B(含多模态 / Linear Attention 变体)/ Ascend 910A ×2 / Transformers + torch_npu / device_map 自动切分
Docker环境准备:
拉取CANN 910A镜像:https://www.hiascend.com/developer/ascendhub/detail/17da20d1c2b6493cb38765adeba85884
比如:
Docker容器启动:
进入容器:
更新transformers库到最新版本,安装torch(这里安装了torch2.8.0)
参考 https://www.hiascend.com/document/detail/zh/Pytorch/720/configandinstg/instg/insg_0004.html
设置环境变量至少需要2卡,export ASCEND_RT_VISIBLE_DEVICES=0,1,启动以下推理脚本即可:
问答推理:
运行问答:
测试回答速度: 文本推理:约首字时延 4571 ms | 每秒 5 tokens 图片推理:首字时延 15812 ms | 每秒 4 tokens
坑一:模型加载类不匹配 → 大量 UNEXPECTED 权重警告
现象
加载时控制台输出大量 UNEXPECTED 权重警告,visual 模块和 mtp 模块未能正确建模,但仍参与初始化流程,不报错、不中断,极难察觉。
根因
使用了 AutoModelForCausalLM 加载一个 ConditionalGeneration(多模态)模型。两者的权重映射表不同,视觉编码器等模块被当作"意外权重"跳过。
解决方案
坑二:bf16 在 910A 上部分算子不支持 → inplace 初始化报错
现象
模型加载阶段报错,错误涉及 uniform_ / A_log 等 inplace 随机初始化操作:
根因
Ascend 910A 对 bfloat16 的支持不完整,部分 inplace 随机初始化算子(uniform_、normal_ 等)在 bf16 精度下未实现。
解决方案
坑三:Flash Linear Attention 依赖缺失 → 性能严重退化
现象
模型可以正常推理,但速度极慢(实测约 2.45 tokens/s),日志中出现 fallback 到纯 Torch 实现的提示。
根因
Qwen3.5 的 Linear Attention 变体依赖 flash-linear-attention 和 causal-conv1d 两个库实现高效 kernel。这两个库底层基于 CUDA Triton 生态,Ascend 910A 无法使用,强制 fallback 到纯 Python/Torch 实现,性能损失极大。
影响
结论
这是当前 910A 部署该模型最核心的性能瓶颈,属于生态缺失问题,无法通过调参解决,需等待 CANN 官方适配或 Ascend 专用 kernel 实现。
坑四:SDPA attention 维度不匹配 → shape mismatch 报错
现象
推理时报错:
错误发生在 attention 计算阶段。
根因
Qwen3.5 使用 GQA(Grouped Query Attention),query heads 与 key/value heads 数量不同。sdpa(Scaled Dot-Product Attention)的实现在处理 GQA 时未正确适配 kv heads 的广播逻辑,导致维度对不上。
解决方案
坑五:multinomial 采样触发 AICPU 崩溃
现象
调用 model.generate() 时崩溃,错误信息:
或 AICPU 异常退出。
根因
do_sample=True 时 generate 内部调用 multinomial 随机采样 kernel,Ascend AICPU 对该 kernel 的支持不稳定,在某些输入形状下直接崩溃。
解决方案
注意:关闭 do_sample 会使输出确定性更强,如需多样性可在应用层做多次调用变通。
本质结论
当前速度慢的问题不是单一调参问题,而是 Qwen3.5 模型需要的 Attention 融合算子 Ascend 910A系列产品 生态缺失的问题。
性能瓶颈主要来自 融合算子缺失 fallback到torch基本算子过慢 算力问题通过参数调整可以缓解,但 flash-linear-attention / causal-conv1d 的 Ascend 适配需等待官方支持。
希望昇腾官方MINDIE等支持910系列产品
Qwen3.5-27B × Ascend 910A × Transformers 适配踩坑总结
Docker环境准备:
拉取CANN 910A镜像:https://www.hiascend.com/developer/ascendhub/detail/17da20d1c2b6493cb38765adeba85884
比如:
Docker容器启动:
docker run -itd --privileged \ --network host \ --name cann_8.3.rc1 \ --device /dev/davinci1 \ --device /dev/davinci_manager \ --device /dev/devmm_svm \ --device /dev/hisi_hdc \ -v /usr/local/dcmi:/usr/local/dcmi \ -v /usr/local/bin/npu-smi:/usr/local/bin/npu-smi \ -v /usr/local/Ascend/driver/lib64/:/usr/local/Ascend/driver/lib64/ \ -v /usr/local/Ascend/driver/version.info:/usr/local/Ascend/driver/version.info \ -v /etc/ascend_install.info:/etc/ascend_install.info \ -v /mnt/sdc:/mnt/sdc \ swr.cn-south-1.myhuaweicloud.com/ascendhub/cann:8.3.rc1-910-ubuntu22.04-py3.11 bash进入容器:
更新transformers库到最新版本,安装torch(这里安装了torch2.8.0)
参考 https://www.hiascend.com/document/detail/zh/Pytorch/720/configandinstg/instg/insg_0004.html
设置环境变量至少需要2卡,export ASCEND_RT_VISIBLE_DEVICES=0,1,启动以下推理脚本即可:
问答推理:
import time import threading import torch import torch_npu from transformers import ( AutoProcessor, Qwen3_5ForConditionalGeneration, TextIteratorStreamer, ) # ==================================== # Ascend配置 # ==================================== torch.npu.set_compile_mode(jit_compile=False) MODEL_PATH = "/mnt/sdc/modelscope/Qwen3.5-27B/" print("Loading processor...") processor = AutoProcessor.from_pretrained( MODEL_PATH, trust_remote_code=True ) tokenizer = processor.tokenizer print("Loading model...") model = Qwen3_5ForConditionalGeneration.from_pretrained( MODEL_PATH, trust_remote_code=True, torch_dtype=torch.float16, device_map="auto", low_cpu_mem_usage=True, attn_implementation="eager", ) model.eval() print("Model loaded.") # ==================================== # 输入 # ==================================== messages = [ {"role": "system", "content": "你是一个乐于助人的助手。"}, {"role": "user", "content": "介绍一下你自己。"} ] prompt = tokenizer.apply_chat_template( messages, tokenize=False, add_generation_prompt=True ) inputs = tokenizer( prompt, return_tensors="pt" ) device = next(model.parameters()).device inputs = { k: v.to(device) for k, v in inputs.items() } # ==================================== # Streamer # ==================================== streamer = TextIteratorStreamer( tokenizer, skip_prompt=True, skip_special_tokens=True ) generate_kwargs = dict( **inputs, streamer=streamer, max_new_tokens=512, do_sample=False, # Ascend避开multinomial num_beams=1, use_cache=True, eos_token_id=tokenizer.eos_token_id, pad_token_id=tokenizer.eos_token_id, ) print("\nAssistant:\n") start_time = time.time() first_token_time = None generated_text = "" thread = threading.Thread( target=model.generate, kwargs=generate_kwargs ) thread.start() for text in streamer: if first_token_time is None: first_token_time = time.time() print(text, end="", flush=True) generated_text += text thread.join() end_time = time.time() print("\n") # ==================================== # TPS统计 # ==================================== output_tokens = len( tokenizer.encode( generated_text, add_special_tokens=False ) ) total_time = end_time - start_time if first_token_time: ttft = first_token_time - start_time else: ttft = total_time gen_time = max(end_time - first_token_time, 1e-6) tps = output_tokens / gen_time print("====================================") print(f"Output Tokens : {output_tokens}") print(f"TTFT : {ttft:.3f} sec") print(f"Generation : {gen_time:.3f} sec") print(f"Tokens/sec : {tps:.2f}") print("====================================")运行问答:
测试回答速度: 文本推理:约首字时延 4571 ms | 每秒 5 tokens 图片推理:首字时延 15812 ms | 每秒 4 tokens
坑一:模型加载类不匹配 → 大量 UNEXPECTED 权重警告
现象
加载时控制台输出大量
UNEXPECTED权重警告,visual模块和mtp模块未能正确建模,但仍参与初始化流程,不报错、不中断,极难察觉。根因
使用了
AutoModelForCausalLM加载一个ConditionalGeneration(多模态)模型。两者的权重映射表不同,视觉编码器等模块被当作"意外权重"跳过。解决方案
坑二:bf16 在 910A 上部分算子不支持 → inplace 初始化报错
现象
模型加载阶段报错,错误涉及
uniform_/A_log等 inplace 随机初始化操作:根因
Ascend 910A 对
bfloat16的支持不完整,部分 inplace 随机初始化算子(uniform_、normal_等)在 bf16 精度下未实现。解决方案
坑三:Flash Linear Attention 依赖缺失 → 性能严重退化
现象
模型可以正常推理,但速度极慢(实测约 2.45 tokens/s),日志中出现 fallback 到纯 Torch 实现的提示。
根因
Qwen3.5 的 Linear Attention 变体依赖
flash-linear-attention和causal-conv1d两个库实现高效 kernel。这两个库底层基于 CUDA Triton 生态,Ascend 910A 无法使用,强制 fallback 到纯 Python/Torch 实现,性能损失极大。影响
结论
这是当前 910A 部署该模型最核心的性能瓶颈,属于生态缺失问题,无法通过调参解决,需等待 CANN 官方适配或 Ascend 专用 kernel 实现。
坑四:SDPA attention 维度不匹配 → shape mismatch 报错
现象
推理时报错:
错误发生在 attention 计算阶段。
根因
Qwen3.5 使用 GQA(Grouped Query Attention),query heads 与 key/value heads 数量不同。
sdpa(Scaled Dot-Product Attention)的实现在处理 GQA 时未正确适配 kv heads 的广播逻辑,导致维度对不上。解决方案
model = ...from_pretrained( ..., attn_implementation="eager", # 放弃 sdpa,回退到标准实现 )坑五:multinomial 采样触发 AICPU 崩溃
现象
调用
model.generate()时崩溃,错误信息:或 AICPU 异常退出。
根因
do_sample=True时 generate 内部调用 multinomial 随机采样 kernel,Ascend AICPU 对该 kernel 的支持不稳定,在某些输入形状下直接崩溃。解决方案
outputs = model.generate( **inputs, do_sample=False, # 关闭随机采样,改用贪心解码 num_beams=1, # 配合贪心,避免 beam search 相关算子 ... )本质结论
希望昇腾官方MINDIE等支持910系列产品