已关闭
[Requirement|需求建议]: 新增 M3 MSA Index Score 算子 #4117
oscillated创建于  8月4日关闭于  8月20日
oscillated
oscillated成员
8月4日 创建

Thanks for sending an requirement! Please fill in the following template to help quickly solve your problem.

Backgroud(背景信息)

MiniMax M3模型中,稀疏注意力MSA(Minimax Sparse Attention)模块的 Indexer 支路用轻量级的 index Q/K 为每个 KV sparse block 打分,再由 topk 选块喂给正式的 sparse attention。其中的“打分”计算流程当前无高性能算子实现,只能通过小算子拼接实现,性能较差且在模型中占比高,存在使用AscendC开发融合算子实现上述计算过程的性能优化空间。

Benefit / Necessity (价值/作用)

价值:开发融合算子实现,可优化性能,提升推理速度。

应用场景:Minimax M3相关模型部署场景。

Design(设计方案)

算子名:MsaIndexScore

aclnn接口名:aclnnMsaIndexScore

torch_extension:msa_index_score

具体实现路径为:基于当前ops-transformer仓已引入的catlass三方库,进行模板化组装,最终以对应功能的torch接口形式交付调用。

index_q ──┐
          ├─► [本算子 MsaIndexScore] ─► score[H, T, NB] ─► torch.topk ─► topk_idx ─► sparse attention
index_k ──┘  (QK^T + mask + 分段 max)                             ↑
  (已写入 paged cache)                                        本算子不覆盖

算子参数说明

TT = total_q(varlen 扁平后的 query token 总数),BB = batch,
HqH_q = num_q_heads(index heads),HkvH_{kv} = num_kv_heads,DD = head_dim,
PP = block_size,NPNP = KV cache 的物理 page 数,MBMB = 每 batch 最大 block 数。

参数名 输入/输出/属性 描述 数据类型 数据格式
query 输入 index query,shape [T,Hq,D][T, H_q, D] BFLOAT16, FLOAT16 ND (TND)
key_cache 输入 分页 index key cache,shape [NP,P,Hkv,D][NP, P, H_{kv}, D] 同 query,或 INT8(前融合量化) ND (BSND)
block_table 输入 逻辑 block → 物理 page 映射,shape [B,MB][B, MB] INT32 ND
scale 可选输入 仅 int8 路径:反量化系数 [NP,Nkv,P][NP, N_{kv}, P];非量化必须为空 FLOAT ND
actual_seq_lengths_query 输入 query 长度前缀和(cumsum),shape [B+1][B+1],首元素为 0 INT32 ND
actual_seq_lengths_key 输入 每个请求可见的 kv 长度,shape [B][B] INT32 ND
start_loc 输入 每个请求首个 query token 在自身 kv 序列中的位置,shape [B][B] INT32 ND
block_size 属性 一个 sparse block / page 的 token 数,默认 128 INT -
fill_invalid_tail 属性 是否把不可见 block 写成 −∞-\infty,默认 true BOOL -
score 输出 block score,shape [Hq,T,RoundUp(MB,16)][H_q, T, \text{RoundUp}(MB, 16)] FLOAT ND

计算过程

设:

  • 请求(request)索引 b∈[0,B)b \in [0, B);
  • q_len 以 cumsum 形式给出,cuq[b]\mathrm{cu}_q[b] 为第 bb 个请求首个 query token 的全局扁平下标,Lq(b)=cuq[b+1]−cuq[b]L_q^{(b)} = \mathrm{cu}_q[b{+}1] - \mathrm{cu}_q[b];
  • start_loc[b] 为该请求首个 query token 在自身 KV 序列中的位置(等价于 Triton 的 prefix_lens / context_lens);
  • kv_len[b] 为该请求当前可见的 KV 总长度;
  • HqH_q 为 query/index head 数,HkvH_{kv} 为 KV head 数,GQA 组大小 g=Hq/Hkvg = H_q / H_{kv},hkv=⌊h/g⌋h_{kv} = \lfloor h / g \rfloor;
  • block_size =P= P(默认 128),block 数 NB(b)=⌈kv_len[b]/P⌉NB^{(b)} = \lceil kv\_len[b] / P \rceil。

对全局 token tt(属于请求 bb)、head hh、逻辑 block β\beta:

qpos(t)=start_loc[b]+(t−cuq[b])q_{\text{pos}}(t) = \texttt{start\_loc}[b] + \bigl(t - \mathrm{cu}_q[b]\bigr)

score[h,t,β]  =  max⁡j∈[βP, βP+P)j≤qpos(t)j<kv_len[b]⟨qt,h, k~j,hkv⟩\mathrm{score}[h, t, \beta] \;=\; \max_{\substack{j \in [\beta P,\ \beta P + P) \\ j \le q_{\text{pos}}(t) \\ j < kv\_len[b]}} \Bigl\langle \mathbf{q}_{t,h},\ \tilde{\mathbf{k}}_{j, h_{kv}} \Bigr\rangle

其中非量化:k~=key_cache[block_table[…]]\tilde{\mathbf{k}} = \texttt{key\_cache}[\texttt{block\_table}[\ldots]](与 query 同 dtype)。

int8 前融合量化(MSA 预量化 K cache):

k~j,hkv=castfp(key_cacheint8[page,j mod P,hkv,:])⋅scale[page,hkv,j mod P]\tilde{\mathbf{k}}_{j,h_{kv}} = \mathrm{cast}_{\mathrm{fp}}\bigl(\texttt{key\_cache}^{\mathrm{int8}}[\mathrm{page}, j\bmod P, h_{kv}, :]\bigr) \cdot \texttt{scale}[\mathrm{page}, h_{kv}, j\bmod P]

scale shape = [NP,Nkv,P][NP, N_{kv}, P](per-token + per-head 反量化)。实现上:
AIV 将 int8 page DataCopy+Cast 到 GM scratch → FFTS K_READY → AIC Mmad(Q, cast(K)) →
S_READY → AIV 在 mask 前对 S 做列乘 scale(因 Q⋅(Ks)=(Q⋅cast(K))⋅sQ\cdot(K s)=(Q\cdot\mathrm{cast}(K))\cdot s)。

若窗口内无任何可见 jj,则 score=fill_value\mathrm{score} = \texttt{fill\_value}(默认 −∞-\infty)。

核心运算 = 矩阵乘(Mmad)+ 段长为 PP 的行方向分段最大值(ReduceMax)。顺序:DOT →(可选 DEQUANT 列乘)→ MASK → MAX。

likedislike
oscillatedoscillated成员
8月4日 添加了label:requirement
oscillatedoscillated成员
8月4日 修改了issue 的描述
oscillated
oscillated成员
8月4日 评论:

/assign

likedislike
CANN-robotCANN-robot成员
8月4日 将 oscillated 设为负责人
oscillatedoscillated成员
8月4日 关联了pull request:[WIP]新增 msa index score 算子
oscillatedoscillated成员
8月4日 修改了issue 的描述
oscillatedoscillated成员
8月4日 修改了issue 的描述
oscillatedoscillated成员
8月4日 修改了issue 的描述
oscillatedoscillated成员
8月4日 修改了issue 的描述
CANN-robotCANN-robot成员
8月20日 关闭了 issue
CANN-robotCANN-robot成员
8月20日 添加了label:resolved
oscillatedoscillated成员
8月21日 关联了pull request:新增 MsaIndexScore 算子 (A2/A3)