Skip to content

Add preprocess function - #13

Open
wufan-ToBeWater wants to merge 3 commits into
HYGON-AI:mainfrom
wufan-ToBeWater:main
Open

wufan-ToBeWater wants to merge 3 commits into
HYGON-AI:mainfrom
wufan-ToBeWater:main

Conversation

@wufan-ToBeWater

@wufan-ToBeWater wufan-ToBeWater commented Oct 15, 2026 •

Copy link
Copy Markdown

1. Summary

新增独立 float 预处理(--alg preprocess),与后续 PTQ 解耦:先把旋转 / 通道缩放吸收进权重,写出仍是 BF16/FP16 的 Hugging Face 目录,再交给 slimquant_ptq / model_free_ptq / MoE-Quant 做 W4A8 等量化。

低比特量化时,少数激活通道的 outlier 会把 per-channel / per-token 的 scale 拉爆,其余值被挤成 0。预处理不写 INT4/INT8,只改浮点权重形状,让后面整次 GEMM 更好量化。

架构是 通用框架 + 每模型 adapter/recipe,不是「一份 yaml 跑通所有模型」。换模型只需加 adapters/.py 和 recipes/.yaml,不改 pipeline / absorb 核心。

2. 解决的问题

量化前缺少对离群数值outlier 处理:原先一键路径直接对原始权重做 PTQ,W4A8 在 MoE / MLA 上容易被激活尖刺打穿。预处理采用QuaRot、Flex AWQ、Flex Smooth等方法提前对权重进行处理,压扁离群数值,预防后续量化可能出现的精度问题。

image

已接入模型:

  • Kimi-K3:unpack MXFP4 → QuaRot + Flex AWQ(routed w3)+ Flex Smooth(共享 Norm 下游;w3 不进 Smooth)
  • DeepSeek-V3:unpack FP8 → QuaRot(含 MLA q_a/q_b、kv_a/kv_b)+ Flex AWQ(dense / shared / routed up)+ Flex Smooth(LN map,含 MTP shared_head)
  • Qwen3.8-Flash-Next:已是 BF16;默认不做 QuaRot(4×H hyper-connection + Gemma hc_norm 与 Hadamard 不对易);Flex AWQ 覆盖 shared / fused expert,Smooth 默认只做 MTP pre_fc_norm_*

文档:docs/preprocess.md(用法)、docs/预处理理论基础.md(方法与子图)。

3. 精度预期

  • QuaRot 降低「少数通道决定整行 scale」的损失,Attention / 残差维更稳。
  • Flex AWQ 针对专家中间维(up–down)把激活难度挪到权重,W4 专家层更友好。
  • Flex Smooth 针对 Norm 出口共享的多路 Linear,减轻 W8A8 下游挤兑。

用Kimi-K3测试,未使用预处理量化后,1300个gsm8k得分0.932。使用预处理量化后,1300个gsm8k得分0.946。

@hygon-ai-reviewer hygon-ai-reviewer Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI Review

🟡 建议修改

发现有明确证据的问题,建议核对并处理。

已确认 2 个问题,其中 1 个已添加到对应代码行。

变更概览

本次变更主要包含:

  • 本批在 README 中新增「独立预处理」章节及目录入口,说明通过 --alg preprocess 先产出浮点预处理目录、再经 --from-preprocessed 交给下游量化路线的两段式用法。
  • 新增 preprocess 模块文档,说明与后续 PTQ 解耦的浮点预处理流程、包结构、按模型 adapter/recipe 约定,以及 DeepSeek-V3、Qwen3.8-Flash-Next、Kimi-K3 的使用示例和 acts.pt 校准激活采集方法。
  • 在 docs/preprocess.md 中新增接入新模型的操作指引:adapter 类模板骨架、ADAPTER_REGISTRY 注册步骤、recipe yaml 示例及预处理产物与下游 PTQ 对接的验收标准。
  • 新增 preprocess 理论基础文档:解释 QuaRot 正交旋转吸收、残差坐标系、LN fuse 先行条件与数值示例,给出启用条件及 DeepSeek-V3、Kimi-K3 可用 QuaRot 而 Qwen3.8-Flash-Next 不适用的逐模型分析。
文件审查摘要
文件 变更 审查结果
preprocess/adapters/deepseek_v3.py 新增 · +631/-0 P3 × 1
preprocess/calib.py 新增 · +39/-0 P3 × 1
docs/预处理理论基础.md 新增 · +1205/-0 —
preprocess/adapters/kimi_k3.py 新增 · +592/-0 —
preprocess/pipeline.py 新增 · +529/-0 —
preprocess/io.py 新增 · +473/-0 —
preprocess/transforms/flex_smooth.py 新增 · +401/-0 —
preprocess/transforms/absorb.py 新增 · +358/-0 —
docs/preprocess.md 新增 · +283/-0 —
preprocess/collect_acts_kimi_k3.py 新增 · +280/-0 —
preprocess/transforms/quarot.py 新增 · +264/-0 —
preprocess/transforms/flex_awq_ssz.py 新增 · +251/-0 —
preprocess/adapters/qwen3_8_flash_next.py 新增 · +221/-0 —
preprocess/transforms/hadamard.py 新增 · +178/-0 —
preprocess/adapters/base.py 新增 · +93/-0 —
preprocess/adapters/init.py 新增 · +85/-0 —
templates/preprocess_ptq.py 新增 · +85/-0 —
preprocess/transforms/base.py 新增 · +77/-0 —
main.py 修改 · +57/-2 —
preprocess/recipes/deepseek_v3.yaml 新增 · +49/-0 —

其余 6 个文件未逐项展开。

无法定位到 diff 行的问题(1)

P3 · 缺 scale 时 FP8 权重原样复制却仍标记为已全量解包

  • 文件:preprocess/adapters/deepseek_v3.py(无法安全定位到当前 diff 行)
  • 触发条件:输入 checkpoint 中某 FP8 权重存在,但其 weight_scale_inv 不在 weight_map 中(数据缺失/索引异常时)。
  • 证据与影响:该分支仅打日志 'missing scale ... copy raw' 后将 FP8 原权重写入 batch;循环结束后代码无条件写入 config 的 deepseek_fp8_unpacked=True、index 及 status ok 的完成标记,不反映部分未解包状态。 输出目录混有未反量化的 FP8 张量,但元数据声明全部已解包;后续按浮点权重处理的量化/加载路径会遇到未转换数据,且完成标记会掩盖该部分解包实际未完成,问题被静默带入下游。
  • 修改建议:统计发生 raw 拷贝的模块,未解包时让完成标记/配置反映部分解包状态(或列出未解包模块),或对缺失 scale 直接抛错,避免输出与标记不一致。
审查信息
  • 变更统计:26 个文件,+6334/-3。
  • 覆盖情况:共 26 个文件,已完整审查 26 个。
  • 候选问题:5 项;证据复核过滤:3 项;发布前敏感信息保护:0 项。
  • 本服务以 GitHub 提供的 PR diff 为审查主体,PR 描述与按相关性选取的仓库片段仅用于核验;未执行代码或重跑测试,结论仍需维护者核验。
提交修复并推送新 commit 后,将自动审查 PR 的最新版本。

Comment thread preprocess/calib.py Outdated
p = Path(path)
if not p.is_file():
raise FileNotFoundError(f"act-stats file not found: {p}")
obj = torch.load(p, map_location="cpu", weights_only=False)

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P3 · torch.load 使用 weights_only=False 存在反序列化执行风险

触发条件: 用户通过 --act-stats 指向他人共享或来自外部的 .pt 文件并执行预处理加载时

证据与影响: 代码使用 torch.load(p, map_location="cpu", weights_only=False),关闭安全加载;pickle 反序列化可执行任意代码,而该接口约定内容仅为 Tensor 字典 加载不可信 act-stats 文件时,可在运行预处理的当前环境中执行任意代码,属于典型的反序列化安全暴露

修改建议: 期望内容为 dict[str, Tensor],可改用 weights_only=True 读取;如需兼容特殊存储格式,需人工核验后再显式放开并加来源校验

@wics1224

Copy link
Copy Markdown

P0

# | 位置 | 问题 | 后果 -- | -- | -- | -- 1 | preprocess/io.py:392 | commit_inplace_and_move 先 rmtree(save_dir) 再写 shard。merge 阶段的溢写数据块默认就在 save_dir/.preprocess_shards/merge_spill 下,会跟着一起被删掉。 | DeepSeek-V3/Kimi 多卡、FP8/MXFP4 源模型,没设 PREPROCESS_SPILL_ROOT:跑了几个小时后,_load_spilled 因找不到文件而崩溃 2 | preprocess/pipeline.py:467 | 设了 PREPROCESS_INPLACE_SAVE=1 后,即使 model_dir 是用户的原始 checkpoint 也会原地提交,绕过了 "拒绝原地覆盖" 的检查 | BF16 输入、多卡:原始模型被覆盖并改名,数据无法恢复 3 | preprocess/transforms/flex_awq_ssz.py:69、flex_smooth.py:51 | 搜索函数假设 act 是 [N, K],但 collect_acts_kimi_k3.py 默认(channel_max)输出的是一维 [K] | 用默认的 --act-stats 跑 Flex 搜索时,make_scales_from_alpha_beta 报长度不匹配;K > 2048 时通道被截断,matmul 出错 4 | preprocess/adapters/deepseek_v3.py:575 | MTP 的 eh_proj 输入做了旋转,但 enorm/hnorm 的 gamma 既没融合也没重置,而逐通道 gamma 和 Hadamard 旋转不能交换顺序 | DeepSeek-V3 默认就带 MTP(num_nextn_predict_layers=1),MTP 输出错误,投机解码接受率大幅下降,而且不报错


@hygon-ai-reviewer

hygon-ai-reviewer Bot commented Oct 16, 2026 •

Copy link
Copy Markdown

AI Review

审查尚未完整完成,无法给出整体结论;当前没有可发布的已确认问题,不代表代码没有问题。

审查未完整完成:以 GitHub 返回的 PR diff 为主体,关联上下文仅用于核验,未运行代码。

覆盖情况:共 26 个文件,已审查 2 个,部分审查 1 个,待审查 23 个。

进度已保存。正在继续处理。

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

把文件名改成英文吧,统一规范

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants