Skip to content

Experiment with MiniMax-M2.7 EAGLE on B200 / 在 B200 上实验 MiniMax-M2.7 EAGLE#2289

Open
cquil11 wants to merge 10 commits into
mainfrom
agent/experimental-minimax-m2.7-eagle
Open

Experiment with MiniMax-M2.7 EAGLE on B200 / 在 B200 上实验 MiniMax-M2.7 EAGLE#2289
cquil11 wants to merge 10 commits into
mainfrom
agent/experimental-minimax-m2.7-eagle

Conversation

@cquil11

@cquil11 cquil11 commented Jul 20, 2026

Copy link
Copy Markdown
Collaborator

Summary

  • benchmark the public MiniMax-M2.7 NVFP4 checkpoint with a public full-vocabulary EAGLE3 draft on B200
  • cover TP4 and TP8 for 8K/1K and AgentX with chat templates enabled
  • pin both model revisions and use the latest stable upstream SGLang image

Validation

  • bash -n on the launcher and both benchmark entrypoints
  • python -m pytest utils/matrix_logic/ -v (224 passed)
  • generated the focused 8K/1K and AgentX matrices locally

中文说明

  • 在 B200 上使用公开的 MiniMax-M2.7 NVFP4 检查点和公开的全词表 EAGLE3 草稿模型进行基准测试
  • 覆盖 TP4、TP8 的 8K/1K 与 AgentX 场景,并启用聊天模板
  • 固定两个模型的版本,并使用最新稳定版上游 SGLang 镜像

验证

  • 对启动器和两个基准测试入口执行 bash -n
  • 执行 python -m pytest utils/matrix_logic/ -v(224 项通过)
  • 在本地生成并核对聚焦的 8K/1K 与 AgentX 扫描矩阵

Add pinned public NVFP4 target and full-vocabulary EAGLE3 draft staging, TP4/TP8 8K/1K and AgentX matrices, and shared SGLang launch logic with chat templates.\n\n中文:新增固定版本的公开 NVFP4 目标模型与全词表 EAGLE3 草稿模型暂存逻辑、TP4/TP8 的 8K/1K 与 AgentX 扫描矩阵,以及启用聊天模板的共享 SGLang 启动逻辑。
@github-actions

Copy link
Copy Markdown
Contributor

Thanks for the contribution! Please reach out to respective companies' CODEOWNER to fill in the latest PR_REVIEW_CHECKLIST.md before pinging core maintainer on Slack for review. In order for the signoff PR check bot to trigger, you must follow the PR_REVIEW_CHECKLIST.md template correctly, including the phrase As a PR reviewer and CODEOWNER, I have reviewed this and have.

For PR verification, add the full-sweep-fail-fast label (strongly recommended) to this PR — the benchmark sweep only runs on labeled PRs. Use full-sweep-enabled only if you need matrix jobs to keep running past a failure.

PR authors are responsible for ensuring that after merging, all GitHub Action jobs fully pass. A lot of the time, failures are just flakes and simply re-running the failed jobs will fix it. See GitHub's docs on re-running failed jobs


感谢你的贡献!请联系相应公司的 CODEOWNER 填写最新的 PR_REVIEW_CHECKLIST.md,然后再在 Slack 上联系核心维护者进行审阅。为了触发 signoff PR 检查机器人,你必须正确遵循 PR_REVIEW_CHECKLIST.md 模板,包括保留英文语句 As a PR reviewer and CODEOWNER, I have reviewed this and have

如需进行 PR 验证,请为此 PR 添加 full-sweep-fail-fast 标签(强烈推荐)— 基准测试 sweep 仅在带有标签的 PR 上运行。仅当需要矩阵任务在失败后继续运行时才使用 full-sweep-enabled

PR 作者有责任确保合并后所有 GitHub Action 任务完全通过。 很多时候失败只是偶发抖动(flake),重新运行失败的任务即可解决。参见 GitHub 关于重新运行失败任务的文档

cquil11 added 8 commits July 20, 2026 12:53
Record the draft PR URL in the append-only performance changelog before starting benchmark jobs.\n\n中文:在启动基准测试任务前,将草稿 PR 链接记录到仅追加的性能变更日志中。
Partition checkpoint prefetching across tensor-parallel ranks to avoid redundant network reads during repeated B200 engine startups.\n\n中文:在张量并行 rank 之间划分检查点预取,避免 B200 推理引擎重复启动时产生冗余网络读取。
Reduce the SGLang static memory fraction from 0.90 to 0.85 after TP4 and TP8 smoke runs OOMed while capturing the 16K prefill CUDA graph.\n\n中文:TP4 和 TP8 冒烟测试在捕获 16K 预填充 CUDA Graph 时显存溢出,因此将 SGLang 静态显存比例从 0.90 降至 0.85,为 EAGLE 图捕获预留空间。
Select gpu-1 only for the MiniMax-M2.7 experiment after confirming all ten nodes are healthy and idle while gpu-2 is saturated. Other B200 benchmark families keep their existing partition.\n\n中文:确认 gpu-1 的十个节点均健康且空闲、gpu-2 已满载后,仅将 MiniMax-M2.7 实验调度到 gpu-1;其他 B200 基准测试仍使用原分区。
Keep benchmark jobs on gpu-2 after Slurm association inspection confirmed sa-shared has only gpu-2_qos; gpu-1 rejects submissions despite idle nodes.\n\n中文:检查 Slurm 关联后确认 sa-shared 仅拥有 gpu-2_qos,因此继续在 gpu-2 上运行基准测试;gpu-1 即使有空闲节点也会拒绝提交。
Use a 150-minute model-scoped Slurm limit instead of the launcher-wide eight-hour default, retaining setup, warmup, and one-hour AgentX headroom while permitting backfill.\n\n中文:为该模型使用 150 分钟的 Slurm 时限,替代启动器默认的八小时;既覆盖准备、预热和一小时 AgentX 测量,也允许调度器进行回填。
Bind the AgentX replay limit to the 196608-token SGLang server window so oversized Weka trajectory turns are excluded before they become deterministic HTTP 400 failures.

中文:将 AgentX 重放上限绑定到 SGLang 的 196608 token 上下文窗口,使超长 Weka 轨迹轮次在发送前被排除,避免确定性的 HTTP 400 失败。
Allow up to 30 minutes for AgentX requests admitted during the measurement window to finish. TP4 was healthy and decoding when the 30-second AIPerf default grace cancelled its only smoke profile request.

中文:允许在测量窗口内已接收的 AgentX 请求最多用 30 分钟完成。TP4 服务保持健康并持续解码,但 AIPerf 默认的 30 秒宽限期取消了冒烟测试中唯一的测量请求。
@cquil11
cquil11 marked this pull request as ready for review July 22, 2026 18:23
@cquil11
cquil11 requested a review from a team July 22, 2026 18:23
同步最新 main,并解决配置与性能变更日志冲突;保留 MiniMax 实验条目为追加项。
Comment on lines +63 to +87
flock -u 8
else
hf download "$TARGET_MODEL" --revision "$TARGET_REVISION"
hf download "$DRAFT_MODEL" --revision "$DRAFT_REVISION"
DRAFT_MODEL_PATH="$DRAFT_MODEL"
fi

python3 - "$TARGET_MODEL_PATH" "$DRAFT_MODEL_PATH" <<'PY'
import json
import sys
from pathlib import Path

target_path, draft_path = map(Path, sys.argv[1:])
target = json.loads((target_path / "config.json").read_text())
draft = json.loads((draft_path / "config.json").read_text())
quant = target.get("quantization_config", {})
if quant.get("quant_algo") != "NVFP4" or quant.get("quant_method") != "modelopt":
raise SystemExit(f"Unexpected NVFP4 target configuration: {quant}")
if target.get("vocab_size") != 200064:
raise SystemExit(f"Unexpected target vocabulary: {target.get('vocab_size')}")
if draft.get("architectures") != ["LlamaForCausalLMEagle3"]:
raise SystemExit(f"Unexpected EAGLE3 architecture: {draft.get('architectures')}")
if draft.get("vocab_size") != 200064 or draft.get("num_hidden_layers") != 1:
raise SystemExit(
f"Unexpected EAGLE3 draft contract: vocab={draft.get('vocab_size')} "

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.

🟡 In the hub-cache fallback branch (no --local-dir), TARGET_MODEL_PATH/DRAFT_MODEL_PATH are left as bare HF repo IDs (e.g. nvidia/MiniMax-M2.7-NVFP4) instead of resolved filesystem paths, so the Python preflight's (target_path / "config.json").read_text() raises FileNotFoundError before the server starts. This is a real defect in the documented hub-cache/local-invocation mode, but it's not exercised in CI since launch_b200-dgxc.sh always exports an absolute MODEL_PATH for this recipe (routing through the --local-dir branch instead); fix by capturing the resolved snapshot dir from hf download (or passing --local-dir) in that branch too.

Extended reasoning...

The new benchmark entrypoint minimaxm2.7_fp4_b200_sglang_mtp.sh supports two model-resolution modes: an absolute-path branch (used when MODEL_PATH is set or MODEL is already an absolute path) that passes --local-dir to hf download and correctly sets TARGET_MODEL_PATH/DRAFT_MODEL_PATH to real directories, and an else branch (lines 63-67) intended for hub-cache/local invocation where MODEL is the bare HF id and MODEL_PATH is unset.

In that else branch, hf download "$TARGET_MODEL" --revision "$TARGET_REVISION" is called without --local-dir, which places the downloaded files under the HF hub cache (e.g. ~/.cache/huggingface/hub/models--nvidia--MiniMax-M2.7-NVFP4/snapshots/<rev>/...), not in a directory literally named nvidia/MiniMax-M2.7-NVFP4 relative to $PWD. Despite this, the script sets TARGET_MODEL_PATH="$TARGET_MODEL" (i.e. the bare repo id string) and DRAFT_MODEL_PATH="$DRAFT_MODEL" (the bare draft repo id) rather than capturing the resolved snapshot path.

Those two variables are then fed straight into the inline Python preflight:

target_path, draft_path = map(Path, sys.argv[1:])
target = json.loads((target_path / "config.json").read_text())

With target_path = Path("nvidia/MiniMax-M2.7-NVFP4"), this resolves to the nonexistent relative path ./nvidia/MiniMax-M2.7-NVFP4/config.json, and read_text() raises FileNotFoundError. Because the script runs under set -Eeuo pipefail, this immediately aborts the run — sglang.launch_server is never even invoked, even though sglang itself would have tolerated the bare repo id and resolved it via the HF cache fine. So the preflight validation step, not the actual model loading, is what breaks this mode.

Step-by-step proof:

  1. Run the script locally/manually with MODEL=nvidia/MiniMax-M2.7-NVFP4 and MODEL_PATH unset (exactly the "local validation" scenario the PR description references).
  2. TARGET_MODEL_PATH is set to the string "nvidia/MiniMax-M2.7-NVFP4" (line ~65-67), not a filesystem path.
  3. hf download nvidia/MiniMax-M2.7-NVFP4 --revision ... (no --local-dir) populates ~/.cache/huggingface/hub/...; no ./nvidia/MiniMax-M2.7-NVFP4 directory is created in $PWD.
  4. The Python preflight executes Path("nvidia/MiniMax-M2.7-NVFP4") / "config.json", which does not exist relative to $PWD.
  5. read_text() raises FileNotFoundError, the script exits nonzero under set -e, and the server never starts.

Why this doesn't block the current CI sweep: runners/launch_b200-dgxc.sh hardcodes MODEL_PATH="/lustre/fsw/gharunners/models/MiniMax-M2.7-NVFP4" for MODEL_PREFIX=minimaxm2.7/fp4 and then does export MODEL="$MODEL_PATH", so in the actual GitHub Actions sweep TARGET_MODEL_PATH is always an absolute path and the --local-dir branch is taken instead — this else branch is dead code from CI's perspective. The PR's own validation (bash -n plus matrix generation) doesn't execute the script, so it wouldn't have caught this either. All three independent verifiers reached the same conclusion and rated it nit severity for this reason.

Suggested fix: capture the resolved snapshot directory that hf download prints/returns (or, simpler, always pass --local-dir "$TARGET_MODEL_PATH"/"$DRAFT_MODEL_PATH" pointing at a real staging directory even in the hub-cache branch, mirroring the absolute-path branch's behavior) so the preflight always receives real filesystem paths.

@github-actions

Copy link
Copy Markdown
Contributor

3 similar comments
@github-actions

Copy link
Copy Markdown
Contributor

@github-actions

Copy link
Copy Markdown
Contributor

@github-actions

Copy link
Copy Markdown
Contributor

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

Projects

Status: No status

Development

Successfully merging this pull request may close these issues.

1 participant