fix(mtp): generalize context parallelism across MTP models - #3570
fix(mtp): generalize context parallelism across MTP models#3570HuiyingLi wants to merge 36 commits into
Conversation
Signed-off-by: SlyneD <slyned@nvidia.com>
Signed-off-by: SlyneD <slyned@nvidia.com>
Signed-off-by: SlyneD <slyned@nvidia.com>
Signed-off-by: SlyneD <slyned@nvidia.com>
Signed-off-by: SlyneD <slyned@nvidia.com>
Signed-off-by: SlyneD <slyned@nvidia.com>
Signed-off-by: SlyneD <slyned@nvidia.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
|
/claude review |
|
Light review — context-parallel MTP support across DeepSeek V4, Step3.7, MiniMax M3, and Qwen3.5, plus the new Overall the distributed logic reads correctly and is well-tested:
Findings (2, both non-blocking, same root cause):
The common |
| position_ids: torch.LongTensor | None = None, | ||
| position_ids_per_depth: tuple[torch.LongTensor, ...] | list[torch.LongTensor] | None = None, | ||
| **block_kwargs, | ||
| ) -> list[torch.Tensor]: |
There was a problem hiding this comment.
DeepseekV4MTPModule.forward gained new tensor parameters (input_ids_per_depth, position_ids_per_depth) and materially changed its tensor-handling body, but has no docstring documenting any tensor layouts. Per the tensor-contract rule, add a Google-style Args/Returns section documenting the semantic shapes, e.g.:
Args:
hidden_states: Tensor of shape [batch, sequence, hidden].
input_ids: Optional token IDs of shape [batch, sequence]; rolled per depth.
input_ids_per_depth: Optional tuple of ``num_depths`` tensors, each [batch, sequence],
holding the pre-shifted future-token IDs for the corresponding depth (CP path).
position_ids: Optional [batch, sequence] positions applied at every depth.
position_ids_per_depth: Optional tuple of ``num_depths`` tensors, each [batch, sequence],
overriding per-depth positions (CP path).
Returns:
List of ``num_depths`` prediction-hidden tensors, each [batch, sequence, hidden].
The input_ids_per_depth/position_ids_per_depth local-vs-global (per-rank CP shard) semantics are non-obvious and should be stated explicitly.
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
Signed-off-by: HuiyingLi <willwin.lee@gmail.com>
|
/ok to test f64478c |
What changed
Why
The existing recipe support handled MTP+CP around a specific input convention. Other MTP models can use different position semantics or embedding paths, so they need one common global-input contract while retaining model-owned preparation where their layout differs. The CP sharder then performs the actual local tensor placement.
This PR intentionally keeps MiniMax's missing-MTP-checkpoint compatibility out of scope.
Impact
Models explicitly advertising MTP+CP support can use the shared recipe path without duplicating CP index calculations. Models without that capability keep their existing behavior and fail early if MTP+CP is requested.
Validation
50-step MTP+CP parity
num_label_tokens; the mean absolute loss difference was 0.000164 and the maximum was 0.0006. CP1 pipeline, CP2 pipeline. The parity probe used sequence length 1024 because the full 16K recipe exceeded H100 memory.num_label_tokens; the mean absolute loss difference was 0.0114 and the maximum was 0.0469 (2.2% maximum relative difference). CP1 pipeline, CP8 pipeline.Qwen/Qwen3.5-4Bwith one MTP depth, sequence length 1024, GBS2, LBS1, and LR0. Raw MTP loss was isolated with paired MTP-on (weight 1.0) and MTP-off runs; a directcalculate_mtp_lossprobe confirmed that the subtraction gives the returned raw MTP loss. Every step used identicalnum_label_tokensandnum_tokens_per_step. Mean raw MTP loss was 2.361566 for CP1 and 2.361717 for CP2 (0.0064% difference); the mean per-step relative difference was 0.42% and the maximum was 1.41%, within the base-loss CP variation. CP1 MTP-on pipeline, CP1 MTP-off pipeline, CP2 MTP-on pipeline, CP2 MTP-off pipeline.