[https://nvbugs/6248757][fix] Avoid running all reduce in aux stream#14917
Conversation
📝 WalkthroughWalkthroughThis PR extends the multi-stream MoE transform to correctly handle shared-expert branches with trailing all-reduce collectives. It detects collective operations, constrains aux-stream work to the non-collective portion, and inserts synchronization barriers between auxiliary and main streams. A previously-waived integration test is unwaived to validate the fix. ChangesCollective-aware multi-stream MoE transform
Sequence DiagramsequenceDiagram
participant MainStream
participant AuxStream
participant Collective as shared_output<br/>(all-reduce)
participant Merge as merge_output
AuxStream->>AuxStream: compute on aux-stream<br/>(non-collective nodes)
AuxStream->>AuxStream: end_aux_stream_passthrough
MainStream->>MainStream: route + compute
MainStream->>Collective: wait_aux_stream_passthrough<br/>(sync before collective)
Collective->>Collective: all-reduce collective<br/>(executes on main stream)
Collective->>Merge: collective output
MainStream->>Merge: routed output
Merge->>Merge: merge result
Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes Possibly related PRs
Suggested reviewers
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
|
can we add a multi-gpu unit test that checks all_reduce is always placed on the main stream @tcherckez-nvidia |
|
Add tests, use this file as reference |
4bd1ee1 to
6fcddfc
Compare
|
/bot run --stage-list "DGX_B200-8_GPUs-AutoDeploy-Post-Merge-1" |
|
PR_Github #52556 [ run ] triggered by Bot. Commit: |
|
PR_Github #52556 [ run ] completed with state |
|
/bot run |
|
PR_Github #52565 [ run ] triggered by Bot. Commit: |
|
PR_Github #52565 [ run ] completed with state
|
|
/bot run --reuse-test |
|
added tests dont pass, see root cause:
|
1e5386b to
a8ffede
Compare
|
/bot run --reuse-test |
|
PR_Github #52657 [ run ] triggered by Bot. Commit: |
|
PR_Github #52657 [ run ] completed with state
|
a8ffede to
ae181df
Compare
|
/bot run |
|
PR_Github #52715 [ run ] triggered by Bot. Commit: |
|
PR_Github #52715 [ run ] completed with state
|
… multi_stream_moe The multi_stream_moe transform moved the entire shared-expert subgraph, including its trailing row-parallel all-reduce, onto the auxiliary CUDA stream. At TP=8 on SM100 the shared-expert symm-mem MULTIMEM all-reduce then ran concurrently with the routed-expert all-reduce on the main stream; under monolithic (decode) CUDA-graph replay the two collectives interleaved across ranks and silently corrupted the output, causing the flaky GSM8K accuracy failure. TP=4 was unaffected because MULTIMEM is disabled for world_size 4 on SM100, and MMLU passed because prefill does not use the monolithic CUDA graph. Overlap only the shared-expert GEMMs on the aux stream and run the trailing all-reduce on the main stream, so no two collectives execute on different streams concurrently. Non-collective shared branches keep the previous behavior. Signed-off-by: tensorrt-cicd <90828364+tensorrt-cicd@users.noreply.github.com>
…stream Add a regression suite to test_multi_stream_moe.py covering the multi_stream_moe placement fix: - test_shared_expert_all_reduce_stays_on_main_stream: a trailing shared-expert all-reduce is rewired after end_aux/wait_aux so the collective runs on the main stream and consumes the synced aux output, never landing inside the aux-stream region. - test_mid_branch_all_reduce_skips_transform: a collective in the middle of the shared-expert branch cannot be split off, so the transform must skip the node rather than move a collective to the aux stream. Signed-off-by: tensorrt-cicd <90828364+tensorrt-cicd@users.noreply.github.com>
Address review feedback (@tcherckez-nvidia) by adding the regression tests from the reviewer's reference patch: - New multi-GPU suite tests/.../multigpu/custom_ops/test_multi_stream_moe_trailing_allreduce.py covering the real distributed path: a structural MPI check, an NCCL correctness check under CUDA-graph replay, and a SYMM_MEM corruption demo that builds the pre-fix (buggy) graph with the collective on the aux stream and shows it diverges from the fixed graph (skipped when SYMM_MEM/MULTIMEM is unavailable). - Nemotron Ultra V3 single-GPU suite appended to tests/.../singlegpu/custom_ops/test_multi_stream_moe.py covering the fuse_rmsnorm_quant_nvfp4 topology (shared expert ending in a trailing all-reduce): graph-structure invariant, numerical correctness, CUDA-graph replay, and multi-layer stacking. These complement the existing single-GPU placement tests and exercise the fix on the multi-rank collective path it actually targets. Signed-off-by: tensorrt-cicd <90828364+tensorrt-cicd@users.noreply.github.com>
…lone mode The new shared-expert all-reduce gating in _execute_shared_expert_in_aux_stream calls all_reduce_ops(), which referenced torch.ops.auto_deploy.trtllm_dist_all_reduce unconditionally. In the standalone llmc package the trtllm_dist module fails to import (no tensorrt_llm available) and the op is never registered, so the attribute access raises AttributeError and breaks every test that runs the multi-stream-MoE transform (test_deepseek_glm4_*, test_nemotron_h_*, test_fused_merge_*, test_tuple_fork_*). Use the existing _auto_deploy_op helper to look up each op by name and silently drop entries that did not register. Behavior is unchanged when both backends register; in standalone mode only the torch_dist variant is included, which matches what is actually available. Signed-off-by: tensorrt-cicd <90828364+tensorrt-cicd@users.noreply.github.com>
The trailing-all-reduce multi-GPU test imported AllReduce / AllReduceStrategy from tensorrt_llm.functional, but functional.py only exposes the strategy enums (AllReduceStrategy / AllReduceFusionOp / AllReduceParams). The runtime class AllReduce lives in tensorrt_llm._torch.distributed; importing it from the wrong module raises ImportError at collection time and skips every test case in the file. Switch to the canonical import path used elsewhere in the test tree (tests/unittest/_torch/multi_gpu/test_allreduce.py et al.). Signed-off-by: tensorrt-cicd <90828364+tensorrt-cicd@users.noreply.github.com>
ae181df to
d3f0009
Compare
|
/bot run |
|
PR_Github #52779 [ run ] triggered by Bot. Commit: |
|
PR_Github #52779 [ run ] completed with state |
Summary
all_reduce_ops()); when present, overlap only the shared-expert GEMMs on the aux stream and emitend_aux/wait_auxbefore the collective so the all-reduce runs on the main stream. No two collectives ever run on different streams concurrently. If a collective appears mid-branch (cannot be split off), the node is skipped with a warning. Non-collective shared branches retain the original behavior. Verified at TP=8 with the feature ON (matches=48/rank): MMLU 86.891, GSM8K 94.141 (≥ 81.517), 1 passed. Waiverwaives.txtline for nvbugs/6248757 removed.Test plan
Links
Summary by CodeRabbit
Bug Fixes
Tests