Skip to content

Commit 601a6fe

Browse files
test(recipe): allow DETERMINISM_ENV_VARS as a shared recipe env constant
Restore the DETERMINISM_ENV_VARS spread in the Moonlight H100 and DSv3 GB300 recipes. The two recipe-environment tests now accept that spread next to the common-default constants and merge its values when checking invariants, and docs/recipe-usage.md documents it as a third shared constant. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com> Signed-off-by: Zhiyu Li <zhiyul@nvidia.com>
1 parent 218e24f commit 601a6fe

5 files changed

Lines changed: 19 additions & 21 deletions

File tree

‎docs/recipe-usage.md‎

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -326,6 +326,8 @@ Flat performance and hardware-specific model recipes keep their baseline environ
326326

327327
Every flat performance recipe builder assigns `cfg.env_vars` directly before returning its config. `COMMON_PERF_ENV_VARS` contains only `TORCH_NCCL_HIGH_PRIORITY=1`, the one value shared by every workload; all GPU-, topology-, precision-, CUDA graph-, and model-specific values are written inline with comments in the owning recipe. This is intentionally verbose so a recipe user can see the exact benchmark environment without following a decorator or global derivation rules.
328328

329+
Deterministic recipes additionally spread `DETERMINISM_ENV_VARS` (from `megatron.bridge.recipes.utils.environment_utils`), a third shared constant, next to the two common-default ones, holding the process settings required for bit-exact reproducibility, such as `CUBLAS_WORKSPACE_CONFIG` and `NCCL_ALGO`. It is the only other constant a recipe may spread, and it is spread after `apply_determinism_overrides` because the recipe reassigns `cfg.env_vars`.
330+
329331
Hardware recipe builders follow the same explicit pattern. `COMMON_RECIPE_ENV_VARS` contains only the seven settings that are identical across every supported recipe; each of the 245 supported builders assigns `cfg.env_vars` directly before returning and writes any HybridEP or model-specific additions inline. There is no recipe decorator or generic launcher-side environment recomposition. Because the compatibility catalog currently reuses H100 builders on other targets, the recipe entry point adapts HybridEP topology after overrides and preserves legacy coupling for an explicit argparse `--nccl_ub`; explicit `env_vars` remain final. The nemo-ci executors under `scripts/performance` do not provide fallback values for recipe-owned process settings.
330332

331333
Cluster fabric and orchestration settings do not belong in recipes. Keep credentials, cache/offline policy, scheduler metadata, W&B state, and cluster-specific NCCL network tuning in the launcher or executor. In particular, settings such as `NCCL_NET_GDR_LEVEL`, `NCCL_NET_GDR_C2C`, and `NCCL_IB_QPS_PER_CONNECTION` must remain deployment-owned.

‎src/megatron/bridge/perf_recipes/deepseek/gb300/deepseek_v3.py‎

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
)
2828
from megatron.bridge.perf_recipes.environment import COMMON_PERF_ENV_VARS
2929
from megatron.bridge.recipes.utils.determinism_utils import apply_determinism_overrides
30+
from megatron.bridge.recipes.utils.environment_utils import DETERMINISM_ENV_VARS
3031

3132

3233
def _build_deepseek_v3_gb300_bf16() -> ConfigContainer:
@@ -212,13 +213,7 @@ def deepseek_v3_pretrain_256gpu_gb300_fp8mx_deterministic_config() -> ConfigCont
212213
# Keep process settings next to the recipe so users can see the exact benchmark environment.
213214
cfg.env_vars = {
214215
**COMMON_PERF_ENV_VARS,
215-
# ---- Determinism (same values as apply_determinism_overrides) ----
216-
"CUBLAS_WORKSPACE_CONFIG": ":4096:8",
217-
"NCCL_ALGO": "Ring",
218-
"NCCL_EP_HT_EM_AG_SCAN_MODE": "1",
219-
"NVTE_ALLOW_NONDETERMINISTIC_ALGO": "0",
220-
"MAMBA_DETERMINISTIC": "1",
221-
"CAUSAL_CONV1D_DETERMINISTIC": "1",
216+
**DETERMINISM_ENV_VARS,
222217
# ---- Others ----
223218
# CUDA stream scheduling for this model and parallel layout.
224219
"CUDA_DEVICE_MAX_CONNECTIONS": 32,

‎src/megatron/bridge/recipes/moonlight/h100/moonlight_16b.py‎

Lines changed: 2 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
from megatron.bridge.recipes.common import _peft_common, _pretrain_common, _sft_common
2222
from megatron.bridge.recipes.utils.dataset_utils import default_peft_config
2323
from megatron.bridge.recipes.utils.determinism_utils import apply_determinism_overrides
24-
from megatron.bridge.recipes.utils.environment_utils import COMMON_RECIPE_ENV_VARS
24+
from megatron.bridge.recipes.utils.environment_utils import COMMON_RECIPE_ENV_VARS, DETERMINISM_ENV_VARS
2525
from megatron.bridge.training.comm_overlap import CommOverlapConfig
2626
from megatron.bridge.training.config import ConfigContainer
2727
from megatron.bridge.training.mixed_precision import MixedPrecisionConfig
@@ -403,13 +403,7 @@ def moonlight_16b_pretrain_16gpu_h100_bf16_deterministic_config() -> ConfigConta
403403
# Keep the complete process environment visible on the recipe.
404404
cfg.env_vars = {
405405
**COMMON_RECIPE_ENV_VARS,
406-
# Determinism (same values as apply_determinism_overrides).
407-
"CUBLAS_WORKSPACE_CONFIG": ":4096:8",
408-
"NCCL_ALGO": "Ring",
409-
"NCCL_EP_HT_EM_AG_SCAN_MODE": "1",
410-
"NVTE_ALLOW_NONDETERMINISTIC_ALGO": "0",
411-
"MAMBA_DETERMINISTIC": "1",
412-
"CAUSAL_CONV1D_DETERMINISTIC": "1",
406+
**DETERMINISM_ENV_VARS,
413407
"CUDA_DEVICE_MAX_CONNECTIONS": 32,
414408
"NUM_OF_HYBRID_EP_RANKS_PER_NVLINK_DOMAIN": 8,
415409
"NUM_OF_TOKENS_PER_CHUNK_COMBINE_API": 128,

‎tests/unit_tests/recipes/test_perf_recipe_environment.py‎

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@
2323

2424
from megatron.bridge.perf_recipes._common import _benchmark_common
2525
from megatron.bridge.perf_recipes.environment import COMMON_PERF_ENV_VARS
26+
from megatron.bridge.recipes.utils.environment_utils import DETERMINISM_ENV_VARS
2627

2728

2829
_CANONICAL_RECIPE_NAME = re.compile(
@@ -101,8 +102,11 @@ def _explicit_environment(path: Path, function_name: str) -> dict[str, str | int
101102
common_expansions = 0
102103
for key, value in zip(mapping.keys, mapping.values):
103104
if key is None:
104-
assert isinstance(value, ast.Name) and value.id == "COMMON_PERF_ENV_VARS"
105-
common_expansions += 1
105+
assert isinstance(value, ast.Name) and value.id in {"COMMON_PERF_ENV_VARS", "DETERMINISM_ENV_VARS"}
106+
if value.id == "COMMON_PERF_ENV_VARS":
107+
common_expansions += 1
108+
else:
109+
result.update(DETERMINISM_ENV_VARS)
106110
continue
107111
if isinstance(value, ast.Name):
108112
assert value.id in local_constants

‎tests/unit_tests/recipes/test_recipe_environment_defaults.py‎

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020

2121
import pytest
2222

23-
from megatron.bridge.recipes.utils.environment_utils import COMMON_RECIPE_ENV_VARS
23+
from megatron.bridge.recipes.utils.environment_utils import COMMON_RECIPE_ENV_VARS, DETERMINISM_ENV_VARS
2424

2525

2626
_CANONICAL_RECIPE_NAME = re.compile(
@@ -67,9 +67,12 @@ def _explicit_environment(path: Path, function_name: str) -> dict[str, str | int
6767
common_expansions = 0
6868
for index, (key, value) in enumerate(zip(mapping.keys, mapping.values)):
6969
if key is None:
70-
assert index == 0
71-
assert isinstance(value, ast.Name) and value.id == "COMMON_RECIPE_ENV_VARS"
72-
common_expansions += 1
70+
assert isinstance(value, ast.Name) and value.id in {"COMMON_RECIPE_ENV_VARS", "DETERMINISM_ENV_VARS"}
71+
if value.id == "COMMON_RECIPE_ENV_VARS":
72+
assert index == 0
73+
common_expansions += 1
74+
else:
75+
result.update(DETERMINISM_ENV_VARS)
7376
continue
7477
result[ast.literal_eval(key)] = ast.literal_eval(value)
7578
assert common_expansions == 1

0 commit comments

Comments
 (0)