Skip to content

Commit e40c500

Browse files
negvetvthumbe1503
andauthored
[PyTorch] Optimize GroupedLinear validation (#3405)
* Optimize GroupedLinear validation Signed-off-by: Evgeny <etsykunov@nvidia.com> * CI fix Signed-off-by: Evgeny <etsykunov@nvidia.com> --------- Signed-off-by: Evgeny <etsykunov@nvidia.com> Co-authored-by: vthumbe1503 <vthumbe@nvidia.com>
1 parent 0a2ebe9 commit e40c500

2 files changed

Lines changed: 27 additions & 2 deletions

File tree

‎tests/pytorch/test_hybrid_quantization.py‎

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4825,6 +4825,13 @@ def unexpected_validation(*_args, **_kwargs):
48254825
model(tensor, m_splits)
48264826
assert model._custom_quantizer_cache == {}
48274827

4828+
def unexpected_grad_mode_query():
4829+
pytest.fail("built-in recipe validation must not query grad mode")
4830+
4831+
with monkeypatch.context() as context:
4832+
context.setattr(torch, "is_grad_enabled", unexpected_grad_mode_query)
4833+
model._validate_custom_recipe_quantizers(False, recipe.DelayedScaling())
4834+
48284835
def unexpected_custom_validation(*_args, **_kwargs):
48294836
pytest.fail("built-in recipes must not validate custom quantizers per forward")
48304837

@@ -4869,12 +4876,29 @@ def tracked_validate(quantizers, *, operand_name="operand"):
48694876
first_call_count = len(validation_calls)
48704877
first_generation = model._custom_quantizer_cache["scaling_fwd"]
48714878
assert first_call_count > 0
4879+
assert "scaling_bwd" not in model._custom_quantizer_cache
48724880

48734881
with torch.no_grad(), autocast(enabled=True, recipe=original_recipe):
48744882
model(tensor, m_splits)
48754883
assert len(validation_calls) == first_call_count
48764884
assert model._custom_quantizer_cache["scaling_fwd"] is first_generation
48774885

4886+
# Backward quantizers are validated the first time quantizers are selected
4887+
# with gradients enabled. Do not run a full forward here: this validation
4888+
# test intentionally uses a columnwise-only configuration that is not
4889+
# supported by the split-quantization kernel.
4890+
with torch.enable_grad(), autocast(enabled=True, recipe=original_recipe):
4891+
model._get_quantizers()
4892+
assert len(validation_calls) == first_call_count + 1
4893+
assert model._custom_quantizer_cache["scaling_bwd"] is model.quantizers["scaling_bwd"]
4894+
4895+
def unexpected_grad_mode_query():
4896+
pytest.fail("cached validation must not query grad mode")
4897+
4898+
with monkeypatch.context() as context:
4899+
context.setattr(torch, "is_grad_enabled", unexpected_grad_mode_query)
4900+
model._validate_custom_recipe_quantizers(False, original_recipe)
4901+
48784902
rebuilt_recipe = recipe.CustomRecipe(qfactory=make_qfactory("rowwise_dequantized"))
48794903
with torch.no_grad(), autocast(enabled=True, recipe=rebuilt_recipe):
48804904
model(tensor, m_splits)

‎transformer_engine/pytorch/module/grouped_linear.py‎

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1810,6 +1810,8 @@ def _validate_custom_recipe_quantizers(self, fwd: bool, recipe: Recipe) -> None:
18101810
return
18111811
if self._custom_quantizer_cache.get(meta_key) is generation:
18121812
return
1813+
if not fwd and not torch.is_grad_enabled():
1814+
return
18131815

18141816
if fwd:
18151817
stride = self._num_fp8_tensors_per_gemm["fwd"]
@@ -2455,8 +2457,7 @@ def _get_quantizers(self):
24552457
# a failed generation remains installed when the caller catches the error.
24562458
recipe = FP8GlobalStateManager.get_fp8_recipe()
24572459
self._validate_custom_recipe_quantizers(True, recipe)
2458-
if torch.is_grad_enabled():
2459-
self._validate_custom_recipe_quantizers(False, recipe)
2460+
self._validate_custom_recipe_quantizers(False, recipe)
24602461

24612462
weight_quantizers = self._get_weight_quantizers()
24622463
input_quantizers, output_quantizers = (

0 commit comments

Comments
 (0)