-
Notifications
You must be signed in to change notification settings - Fork 583
Quantize activations before EP all gather #4812
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
Shuwen-Fang
wants to merge
11
commits into
main
Choose a base branch
from
quantize_sort_2
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
Show all changes
11 commits
Select commit
Hold shift + click to select a range
1fb67bf
Rebase quantize_sort_2 onto latest main
Shuwen-Fang eb1b787
Tighten scope: keep use_single_sparsecore, drop unrelated capacity fixes
Shuwen-Fang 595d36f
Restore PR #4735's static-LHS-scaling mechanism, layered alongside ours
Shuwen-Fang 59a7acb
Use qwix's should_quantize() for the "already quantized" check in ops.py
Shuwen-Fang f438e64
moe.py: dedup ring_ragged_sort call sites, drop redundant/unsafe quan…
Shuwen-Fang 09dc56e
Add quantize_before_ep_all_gather flag; use qpl.get_current_rule in r…
Shuwen-Fang 207b943
Add test_quantize_before_ep_all_gather_equivalence
Shuwen-Fang 76f2097
update test
Shuwen-Fang 5728eac
validate
Shuwen-Fang b1ed0f0
simplify
Shuwen-Fang 1ed8bb5
fix
Shuwen-Fang File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,152 @@ | ||
| #!/bin/bash | ||
| set -e | ||
|
|
||
| # Activate Python virtual environment | ||
| source /home/shuwenf_google_com/venv-maxtext/bin/activate | ||
|
|
||
| # --- Environment Variables --- | ||
| export PROJECT_ID="tpu-prod-env-one-vm" | ||
| export CLUSTER_NAME="bodaborg-v6e-256-lcscld-c" | ||
| export ZONE="southamerica-west1-a" | ||
|
|
||
| # --- Configuration & Automated Image Build --- | ||
| TIMESTAMP=$(date +%m%d%H%M%S) | ||
| export WORKLOAD_IMAGE="gcr.io/tpu-prod-env-one-vm/param3_21jul:shuwenf_${TIMESTAMP}" | ||
| export WORKLOAD_NAME="shuwenf-qn80b-${TIMESTAMP}" | ||
| export DEVICE_TYPE="v6e-256" | ||
| export NUM_SLICES=1 | ||
| export PRIORITY="very-high" | ||
| export NUM_STEPS=15 | ||
| export MAX_RESTARTS=${MAX_RESTARTS:-0} | ||
| export MODEL_NAME="qwen3-next-80b-a3b" | ||
| export BASE_OUTPUT_DIR="gs://shuwenf-hlo-dumps/qwen3-next-80b-profiles/run-${TIMESTAMP}" | ||
|
|
||
| echo "========================================================================" | ||
| echo "Building and uploading Docker runner image for full 15-step execution..." | ||
| echo "Target Image: ${WORKLOAD_IMAGE}" | ||
| echo "========================================================================" | ||
|
|
||
| ( | ||
| cd /home/shuwenf_google_com/maxtext && sudo CLOUD_IMAGE_NAME="${WORKLOAD_IMAGE}" BASE_IMAGE="gcr.io/tpu-prod-env-one-vm/param3_21jul:latest" bash src/dependencies/scripts/docker_upload_runner.sh | ||
| ) | ||
|
|
||
| echo "Docker image upload complete: ${WORKLOAD_IMAGE}" | ||
|
|
||
| # --- XLA Flags --- | ||
| XLA_FLAGS_ARRAY=( | ||
| "--xla_tpu_scheduler_percent_shared_memory_limit=35" | ||
| "--xla_msa_enable_sync_slice_replacement=false" | ||
| "--xla_tpu_enable_sparse_core_collective_offload_2d_all_gather=true" | ||
| "--xla_msa_enable_sync_copy_replacement=false" | ||
| "--xla_tpu_scoped_vmem_limit_kib=81000" | ||
| "--xla_tpu_enable_sparse_core_collective_offload_all_gather=true" | ||
| "--xla_tpu_enable_sparse_core_collective_offload_all_reduce=true" | ||
| "--xla_tpu_offload_gather_to_sparsecore=true" | ||
| "--xla_tpu_dvfs_p_state=7" | ||
| "--xla_tpu_disable_sparse_core_collective_offload_remover=true" | ||
| "--xla_tpu_enable_async_collective_fusion=true" | ||
| "--xla_tpu_overlap_compute_collective_tc=true" | ||
| "--xla_tpu_enable_async_collective_fusion_multiple_steps=true" | ||
| "--xla_tpu_enable_latency_hiding_scheduler=true" | ||
| "--xla_latency_hiding_scheduler_rerun=10" | ||
| "--xla_tpu_all_gather_collective_matmul_mode=post_spmd_conservative" | ||
| "--xla_tpu_reduce_scatter_collective_matmul_mode=post_spmd_conservative" | ||
| "--xla_latency_hiding_scheduler_enable_selective_resources=true" | ||
| "--xla_tpu_enable_ilp_latency_hiding_scheduler=true" | ||
| "--xla_tpu_enable_all_experimental_scheduler_features=true" | ||
| "--xla_tpu_enable_scheduler_memory_pressure_tracking=true" | ||
| "--xla_tpu_host_transfer_overlap_limit=24" | ||
| "--xla_tpu_aggressive_opt_barrier_removal=ENABLED" | ||
| "--xla_lhs_prioritize_async_depth_over_stall=DISABLED" | ||
| "--xla_tpu_enable_ag_backward_pipelining=true" | ||
| "--xla_should_allow_loop_variant_parameter_in_chain=ENABLED" | ||
| "--xla_should_add_loop_invariant_op_in_chain=ENABLED" | ||
| "--xla_max_concurrent_host_send_recv=100" | ||
| ) | ||
| export XLA_FLAGS="${XLA_FLAGS_ARRAY[*]}" | ||
|
|
||
| # --- MaxText Workload Overrides --- | ||
| MAXTEXT_ARGS_ARRAY=( | ||
| "model_name=${MODEL_NAME}" | ||
| "base_output_directory=${BASE_OUTPUT_DIR}" | ||
| "run_name=param-3" | ||
| "dataset_type=synthetic" | ||
| "dataset_name=synthetic" | ||
| "dtype=bfloat16" | ||
| "allow_split_physical_axes=True" | ||
| "ici_expert_parallelism=4" | ||
| "use_ring_of_experts=True" | ||
| "custom_mesh=hybrid_ring_64x4" | ||
| "use_ragged_sort=True" | ||
| "use_random_routing=True" | ||
| "per_device_batch_size=4" | ||
| "opt_type=muon" | ||
| "muon_consistent_rms=0.2" | ||
| "muon_weight_decay=0.1" | ||
| "learning_rate=1e-5" | ||
| "max_target_length=2048" | ||
| "ragged_buffer_factor=1.5" | ||
| "remat_policy=full" | ||
| "reuse_example_batch=1" | ||
| "decoder_layer_input=offload" | ||
| "context=device" | ||
| "ici_fsdp_parallelism=-1" | ||
| "steps=15" | ||
| "shard_exp_on_fsdp=True" | ||
| "sharding_tolerance=0.5" | ||
| "sa_q_layout=SEQ_MINOR" | ||
| "sa_k_layout=HEAD_DIM_MINOR" | ||
| "sa_v_layout=HEAD_DIM_MINOR" | ||
| "sa_block_q=2048" | ||
| "sa_block_kv=2048" | ||
| "sa_block_kv_compute=1024" | ||
| "sa_block_q_dkv=2048" | ||
| "sa_block_kv_dkv=2048" | ||
| "sa_block_kv_dkv_compute=1024" | ||
| "hardware=tpu" | ||
| "skip_jax_distributed_system=False" | ||
| "attention=flash" | ||
| "use_tokamax_splash=True" | ||
| "sa_use_fused_bwd_kernel=True" | ||
| "use_tokamax_gmm=True" | ||
| "use_gmm_v2=True" | ||
| "sparse_matmul=True" | ||
| "megablox=True" | ||
| "optimizer_memory_host_offload=True" | ||
| "parameter_memory_host_offload=False" | ||
| "enable_checkpointing=False" | ||
| "async_checkpointing=False" | ||
| "tokenizer_type=tiktoken" | ||
| "tokenizer_path=tokenizer_74B/" | ||
| "override_model_config=true" | ||
| "mhc_expansion_rate=4" | ||
| "profiler=xplane" | ||
| "profiler_steps=5" | ||
| "skip_first_n_steps_for_profiler=2" | ||
| "enable_tpu_profiling_options=True" | ||
| "upload_all_profiler_results=true" | ||
| ) | ||
| MAXTEXT_ARGS="${MAXTEXT_ARGS_ARRAY[*]}" | ||
|
|
||
| # Clean container temporary log setup safely | ||
| RUN_COMMAND="set -e && rm -rf /tmp/tpu_logs/* 2>/dev/null || true; mkdir -p /tmp/tpu_logs && export LIBTPU_INIT_ARGS=\"${XLA_FLAGS}\" && export JAX_PLATFORMS='tpu,cpu' && export ENABLE_PJRT_COMPATIBILITY='true' && export JAX_DISTRIBUTED_INITIALIZE_TIMEOUT=1800 && export PYTHONPATH=/deps:/deps/src:/deps/src/maxtext/src && python3 src/maxtext/trainers/pre_train/train.py src/maxtext/configs/base.yml ${MAXTEXT_ARGS}" | ||
|
|
||
| # --- XPK Workload Creation --- | ||
| echo "Creating XPK workload: ${WORKLOAD_NAME} on cluster: ${CLUSTER_NAME}" | ||
|
|
||
| python3 -m xpk.main workload create --cluster="${CLUSTER_NAME}" --project="${PROJECT_ID}" --zone="${ZONE}" --priority="${PRIORITY}" --max-restarts="${MAX_RESTARTS}" --device-type="${DEVICE_TYPE}" --num-slices="${NUM_SLICES}" --docker-image="${WORKLOAD_IMAGE}" --enable-debug-logs --workload="${WORKLOAD_NAME}" --command="${RUN_COMMAND}" | ||
|
|
||
| LOGS_URL="https://console.cloud.google.com/logs/query;query=resource.type%3D%22k8s_container%22%0Aresource.labels.project_id%3D%22${PROJECT_ID}%22%0Aresource.labels.location%3D%22southamerica-west1%22%0Aresource.labels.cluster_name%3D%22${CLUSTER_NAME}%22%0Aresource.labels.namespace_name%3D%22default%22%0Aresource.labels.pod_name%3A%22${WORKLOAD_NAME}-slice-job-0-0-%22%0Aseverity%3E%3DDEFAULT;storageScope=project;duration=P1D?project=${PROJECT_ID}" | ||
| GKE_URL="https://console.cloud.google.com/kubernetes/service/southamerica-west1/${CLUSTER_NAME}/default/${WORKLOAD_NAME}/details?project=${PROJECT_ID}" | ||
| TB_URL="https://tensorboard.corp.google.com/?logdir=${BASE_OUTPUT_DIR}/param-3/tensorboard" | ||
|
|
||
| echo "========================================================================" | ||
| echo "📋 Pantheon Cloud Logging (Worker 0 Logs):" | ||
| echo "${LOGS_URL}" | ||
| echo "" | ||
| echo "☸️ GKE Workload Details:" | ||
| echo "${GKE_URL}" | ||
| echo "" | ||
| echo "📊 GCS TensorBoard Link:" | ||
| echo "${TB_URL}" | ||
| echo "========================================================================" |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change | ||||||||
|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -525,7 +525,12 @@ def _matmul(is_first_k_step: bool, is_last_k_step: bool): | |||||||||
| # Perform lhs quantization. Note that for every block_lhs, | ||||||||||
| # same computation will be performed tiles_n//mxu_size times. | ||||||||||
| # But we can let compiler perform CSE and avoid recomputation. | ||||||||||
| if should_use_external_scale: | ||||||||||
| if tiled_lhs.dtype == lhs_q_dtype: | ||||||||||
| # lhs block already arrives quantized, the real dequant | ||||||||||
| # scale is applied externally, so just pass an identity scale here. Comparing against lhs_q_dtype | ||||||||||
| block_lhs_q = block_lhs | ||||||||||
| block_scale = jnp.array(1.0, dtype=acc_ref.dtype) | ||||||||||
| elif should_use_external_scale: | ||||||||||
| assert lhs_scale is not None | ||||||||||
| assert lhs_scale_inv is not None | ||||||||||
| block_lhs_q = jnp.clip(block_lhs * lhs_scale_inv, -dtype_max, dtype_max).astype(lhs_q_dtype) | ||||||||||
|
|
@@ -1206,7 +1211,11 @@ def make_gmm_configs( | |||||||||
| ) | ||||||||||
|
|
||||||||||
| lhs_q_dtype = None | ||||||||||
| if maybe_quantize_lhs and rhs_cfgs.should_dequantize_after_matmul: | ||||||||||
| if jnp.issubdtype(lhs.dtype, jnp.integer) or jnp.issubdtype(lhs.dtype, jnp.float8_e4m3fn): | ||||||||||
| # lhs arrives already quantized (e.g. pre-quantized ahead-of-time by the | ||||||||||
| # caller): use its dtype as-is, no in-kernel quantization/scale needed. | ||||||||||
| lhs_q_dtype = lhs.dtype | ||||||||||
| elif maybe_quantize_lhs and rhs_cfgs.should_dequantize_after_matmul: | ||||||||||
| # Choose lhs quantization dtype based on TPU hardware support. | ||||||||||
| is_rhs_float = jnp.issubdtype(rhs_quant_dtype, jnp.floating) # pyrefly: ignore[bad-argument-type] | ||||||||||
| tpu_info = pltpu.get_tpu_info() | ||||||||||
|
|
@@ -1241,8 +1250,12 @@ def make_gmm_configs( | |||||||||
| has_scale=has_lhs_scale, | ||||||||||
| ) | ||||||||||
|
|
||||||||||
| if out_dtype is None: | ||||||||||
| out_dtype = lhs.dtype | ||||||||||
| if out_dtype is None or jnp.issubdtype(out_dtype, jnp.float8_e4m3fn): | ||||||||||
| # The raw quantized-domain matmul output isn't yet rescaled -- writing it | ||||||||||
| # directly as fp8 would lose precision before the scale multiply happens | ||||||||||
| # (either inside this kernel via lhs_scale/block_scale, or externally by | ||||||||||
| # the caller for a pre-quantized lhs). Floor to bf16 as a safe intermediate. | ||||||||||
| out_dtype = jnp.bfloat16.dtype | ||||||||||
|
Comment on lines
+1253
to
+1258
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. In standard JAX/NumPy,
Suggested change
|
||||||||||
|
|
||||||||||
| if acc_dtype is None: | ||||||||||
| if lhs_cfgs.quant_dtype is None: | ||||||||||
|
|
||||||||||
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Importing from a private module
qwix._src.core.qarrayis a maintainability risk as these internal APIs are unstable and can change without notice. Since bothoutandlhs_scaleare standard JAX arrays, standard JAX/NumPy broadcasting (e.g.,out * lhs_scale) is fully supported and should be preferred.