Add BMM_Theory: docs/04_差异对照_bmmv3_vs_BMM_Theory.md

This commit is contained in:
2026-09-03 12:35:49 +00:00
parent f4e8eff040
commit 88b1e4946c

View File

@@ -0,0 +1,175 @@
# bmmv3 vs BMM_Theory 差异对照
> 对照对象:`bmmv3/bmmv3/bmmv3_arch35_branch_checker.py`(下称 **bmmv3**)与本仓库 `bmm_theory/branches/merge_batch.py` + `iter_batch.py`(下称 **BMM_Theory**)。
> 写作目的:说清两版"是什么关系、差在哪、各自什么时候用、该互相吸收什么"。
---
## 0. 一句话结论
**两版不是竞争关系,是互补关系。**
- **bmmv3** = 现有算子源码行为的**预测器/对拍器**source-of-truth 是 `batch_matmul_v3_mergebatch_basicapi_tiling.cpp` / `iterbatch_tiling.cpp`
- **BMM_Theory** = 理论最优实现的**推导器**source-of-truth 是《BMM算子优化分析 v0.98》《MergeBatch_vs_IterBatch分析 v1.1》)。
要"知道现有 kernel 实际会怎么跑"→ 用 bmmv3要"知道理论上应该怎么跑最优"→ 用 BMM_Theory。
---
## 1. 根本定位差异
| 维度 | bmmv3 | BMM_Theory |
|---|---|---|
| 目的 | 判断 case 能否进**现有源码**的 `MERGE_BATCH_BASICAPI` / `ITER_BATCH` | 推导 case 的**理论最优**实现方案 |
| 依据 | ops-nn 源码逐条件还原 | 理论文档推导 + 硬件容量/带宽约束 |
| tile 语义 | 按源码硬编码ping_pong 开关、step 幂次搜索) | 按理论容量极限 + 生成后自检 |
| 时延模型 | 三行带宽公式CUBE/FIXP/MTE2 各一行) | 分阶段 max(MMAD,MTE2,FIXPIPE)+drain对齐 v1.1 |
| 分支覆盖 | 仅 MergeBatch + IterBatch | 六分支全转Matmul/特殊/MergeBatch/IterBatch/StreamK/ASW_Basic |
| 输入校验 | 无(静默接受非法输入) | `__post_init__` 明确报错issue#15 |
| 生成后自检 | 无 | constraints.py 同源校验issue#5 |
---
## 2. MergeBatch 分支逐项对照
### 2.1 准入条件
| 条件 | bmmv3 | BMM_Theory | 差异说明 |
|---|---|---|---|
| batch 关系 | A/B 4 个 batch 轴完全相等 | BatchA==BatchB | bmmv3 更严(源码实现细节) |
| 每核 batch 下限 | `min_batch_l0=4`每核≥4 batch | `b_core ≥ 2*b0`b0≥2 即每核≥4 | 等价bmmv3 硬编码 4我们参数化 |
| L0C 容量 | `l0cSize = tempAlignM×tempAlignN×4×l0c_factor ≤ L0C` | `2×(b0·M)×(b0·N)×4 ≤ L0C` | 一致l0c_factor=2 即双缓冲) |
| L0A/L0B 容量 | 准入条件 21/22 查(`al0Size/bl0Size` | **b0 计算时显式收敛issue#13** | **我们更完整**——bmmv3 只在准入查,没在 b0 计算里收敛 |
| K 对齐下限 | `alignK ≥ merge_min_align_k=64` | 无 | bmmv3 源码特有 |
| M≤N 约束 | 有(条件 13 | 无 | bmmv3 源码特有(实现限制,非理论必要) |
| 转置 view | 非连续转置 view 排除 | 不建模 | bmmv3 源码特有 |
| bias | `has_bias=false` | 不建模 | bmmv3 源码特有 |
| 访存 Bound | `2MN/(M+N) < 607/2`(经验常数) | `2MN/(M+N) < R16/b0`R16=算存比) | **我们更通用**——607.5 是 R16 在 fp16 下的数值实例fp32 时 R16 减半但 bmmv3 不会 |
### 2.2 b0 计算
```
bmmv3: b0 = min(L0C/(2·M·N·4), ceil(B/C), 607.5·(M+N)/(2·M·N))
我们: b0 = min(√(L0C/(8MN)), R16·(M+N)/(2MN), √(L0A/(2·M·16·dt)), √(L0B/(2·N·16·dt)), b_core) 取因子
```
**关键差异**:我们多了 L0A/L0B 上限issue#13bmmv3 靠 `min_batch_l0=4` 间接保证 L0A/L0B 不溢出但不如显式约束通用b0=2 时 bmmv3 的间接保证失效)。
### 2.3 KL0/KL1 计算
| | bmmv3 | BMM_Theory |
|---|---|---|
| KL0 | `floor_align16(min(L0A/(2·b0·M·dt), L0B/(2·b0·N·dt)))` | 同(`align_down(min(...), fractal)` |
| KL1 | `ceil_align16(min(K, 512/dt, L1/(2·b0·(M+N)·dt)))`,不满足 L1 则减 16 循环 | `align_down(min(k_l1_star, K, dvalue_cap), fractal)` |
| 实现风格 | 源码试探式ceil 后逐步减) | 理论反推式(直接 align_down |
**差异说明**bmmv3 的"ceil 后减 16 循环"是源码实现细节(为了向上对齐后再试探),理论反推直接用 `align_down` 即可,结果等价但我们更简洁。
---
## 3. IterBatch 分支逐项对照
### 3.1 准入条件
| 条件 | bmmv3 | BMM_Theory |
|---|---|---|
| 每核 batch | `floor(B/C) ≥ 1` | `b_core ≥ 1`ceil | 一致 |
| 负载均衡 | `B mod C == 0``≥ 26`(硬编码) | `B mod C == 0``≥ min_core_num`(参数化) | **我们更通用** |
| L1 形态 | a/b/c1/c2/d 五种 | a/b/c/d 四种 | **bmmv3 更细**c 拆 c1/c2 |
### 3.2 c 形态处理
**bmmv3**
- c1MK 整体驻留 + KN/step 分块
- c2KN 整体驻留 + MK/step 分块
- step 按 2/4/8/16… 幂次递增遍历取最大
**BMM_Theory**
- c 形态统一:"驻留较小侧 + 对侧切 K"
- k_l1 连续反推:`k_l1 = (budget - resident) / (other·dt) / 2`
**差异说明**bmmv3 的 step 幂次搜索是源码为了 tiling 生成方便做的离散化;理论极限下 k_l1 连续取最优即可。**做理论推导用我们的,做源码对拍用 bmmv3 的。**
### 3.3 d 形态处理
**bmmv3**`step_d` 由 16KB 和 128B 两条规则推导,`KL1 = ceil_align16(K/step_d)`,不满足 L1 则减 16 循环。
**BMM_Theory**`k_l1 = align_down(L1/(2·(M+N)·dt), fractal)`,直接反推。
**差异说明**同上bmmv3 是源码试探式实现,我们是理论反推。
---
## 4. 时延模型对照
| | bmmv3 | BMM_Theory |
|---|---|---|
| CUBE | `2·B·M·K·N / (MAC_TFLOPS·1e6)` | `2·b_core·M·N·K / q16`(单核) |
| MTE2 | `(2·M·K + 2·K·N)·B / (MTE2_BW·1e6)` | 分 GM/L2 两段 + T_cmd + drain |
| FIXP | `2·M·N·B / (FIXP_BW·1e6)` | `b_core·M·N·out_dtype / bw_pc` + unitflag |
| 流水掩盖 | 无 | max(MMAD,MTE2,FIXPIPE) + drain |
| 分支仲裁 | 无 | MergeBatch vs IterBatch 谁优 |
**差异说明**bmmv3 的时延是纯带宽粗估(三行公式),我们做分阶段 + drain + 仲裁,能定位瓶颈。
---
## 5. 各自适用场景
| 场景 | 推荐 |
|---|---|
| 预测现有 kernel 实际行为(对拍) | **bmmv3** |
| 推导理论最优方案(设计) | **BMM_Theory** |
| 分析瓶颈MTE2/Cube/Fixpipe 谁卡) | **BMM_Theory**bmmv3 无瓶颈分析) |
| 验证源码准入条件是否正确 | **bmmv3**BMM_Theory 不管源码现状) |
| 大批量 case 筛选XLSX 原表追加) | **bmmv3**(我们暂无 XLSX |
---
## 6. 可吸收点清单
### 6.1 bmmv3 → BMM_Theory我们该补的
| 项 | 优先级 | 状态 |
|---|---|---|
| fp40.5Bdtype 支持 | 高 | ✅ **已补(本期)**——`DTYPE_BYTES``"fp4": 0.5` / `"fp4_e2m1": 0.5``dtype_bytes()` 返回 float |
| 转置对 dValue/base_k 的影响建模 | 高 | ✅ **已补(本期)**——MergeBatch 加条件 6A 转置对齐IterBatch dValue 判定按转置调整连续维 |
| XLSX 原表追加输出 | 中 | 待做 |
| c1/c2 的 step 幂次搜索 | 低 | 不做(理论极限不需要离散化) |
**fp4 已补细节**
- `models.py`: `DTYPE_BYTES``"fp4": 0.5` / `"fp4_e2m1": 0.5`
- `dtype_bytes()` 返回类型改为 `float`(兼容 0.5
- `dtype_in_bytes`/`dtype_out_bytes` 属性返回类型改为 `float`
- 测试:`TestFp4Support` 3 个用例
**转置建模已补细节**
- **MergeBatch**`merge_batch.py`):新增条件 6——A 转置且 M>1 时 `tempAlignM = b0 * alignM`,校验 L0A 容量
- **IterBatch**`iter_batch.py`dValue 判定按转置调整连续维——A 不转置判 `K*dt`A 转置判 `M*dt`B 不转置判 `N*dt`B 转置判 `K*dt`
- 测试:`TestTransposeModeling` 3 个用例(含 A 转置大 M 小 K 通过、A 不转置小 K 失败的边界 case
### 6.2 BMM_Theory → bmmv3他们可参考的
| 项 | 说明 |
|---|---|
| 分支仲裁 | MergeBatch vs IterBatch 谁优的判断 |
| 时延 drain/流水掩盖 | 三行公式 → 分阶段 max + drain |
| 生成后自检 | 生成即输出 → 生成后跑约束校验 |
| L0A/L0B 的 b0 显式收敛 | issue#13b0 计算时直接纳入 L0A/L0B 上限 |
| 输入校验 | issue#15:非法维度/dtype 明确报错 |
---
## 7. 结论
两版**互补不替代**。bmmv3 是"源码行为预测器"对拍用BMM_Theory 是"理论最优推导器"(设计用)。
**已吸收**fp4 支持 + 转置对 dValue 的建模(本期补入)。
**不建议吸收**c1/c2 的 step 幂次搜索(源码离散化细节,理论推导不需要)。
**待考虑**XLSX 输出(如用户需要)。
---
*版本v1.0 | 2026-09-03 | 基于 BMM_Theory 最新版(含 issue#11-#16 修复)与 bmmv3 最新版对照*