-
Notifications
You must be signed in to change notification settings - Fork 2.6k
[https://nvbugs/6442074][fix] Make one-model spec-dec attn-metadata save/restore exception-safe #16382
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
base: main
Are you sure you want to change the base?
[https://nvbugs/6442074][fix] Make one-model spec-dec attn-metadata save/restore exception-safe #16382
Changes from all commits
1d48a06
66bab0d
7859223
4e8053c
9df1b8b
f69a318
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -28,6 +28,7 @@ | |
| from tensorrt_llm.logger import logger | ||
|
|
||
| from ..._utils import get_sm_version, prefer_pinned | ||
| from ..attention_backend.interface import AttentionMetadata | ||
| from ..attention_backend.trtllm import (AttentionBackend, TrtllmAttention, | ||
| TrtllmAttentionMetadata) | ||
| from ..flashinfer_utils import IS_FLASHINFER_AVAILABLE | ||
|
|
@@ -925,6 +926,54 @@ def __init__(self, use_separate_draft_kv_cache: bool = False): | |
| self._force_accept_rng_pool: Optional[torch.Tensor] = None | ||
| self._force_accept_rng_counter: Optional[torch.Tensor] = None | ||
|
|
||
| def __init_subclass__(cls, **kwargs): | ||
| super().__init_subclass__(**kwargs) | ||
| if "forward" in cls.__dict__: | ||
| raise TypeError( | ||
| f"{cls.__name__} must not override SpecWorkerBase.forward; " | ||
| f"implement _forward_impl instead. SpecWorkerBase.forward " | ||
| f"guarantees spec-dec attn-metadata cleanup when a forward " | ||
| f"fails (https://nvbugs/6442074).") | ||
|
|
||
| def forward(self, *args, **kwargs): | ||
| """Run _forward_impl with guaranteed spec-dec metadata cleanup. | ||
|
|
||
| Tolerated forward failures (e.g. an OOM during the max-shape general | ||
| warmup, or an error-budget-tolerated serving exception) must not leak | ||
| the attn-metadata state saved by prepare_for_spec_dec: a stale save | ||
| fails every subsequent forward at the pairing assert. | ||
| https://nvbugs/6442074 | ||
| """ | ||
| attn_metadata = kwargs.get("attn_metadata") | ||
|
Collaborator
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. Could also do something like this: with prepare_for_spec_dec(attn_metata) as attn_metadata:
# Run forward implwhere the
Collaborator
Author
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. Hi Mike, thanks for the good suggestion! Some of the states are in subclasses, looks like putting them in a context manager requires additional work, and it's possible this will result in the code being a little bit more complicated. |
||
| spec_metadata = kwargs.get("spec_metadata") | ||
| if attn_metadata is None or spec_metadata is None: | ||
| for a in args: | ||
| if attn_metadata is None and isinstance(a, AttentionMetadata): | ||
| attn_metadata = a | ||
| elif spec_metadata is None and isinstance(a, SpecMetadata): | ||
| spec_metadata = a | ||
| try: | ||
| return self._forward_impl(*args, **kwargs) | ||
| finally: | ||
| self._ensure_spec_dec_state_restored(attn_metadata, spec_metadata) | ||
|
|
||
| @abstractmethod | ||
| def _forward_impl(self, *args, **kwargs): | ||
| """Worker-specific forward logic, called by SpecWorkerBase.forward.""" | ||
|
|
||
| def _ensure_spec_dec_state_restored(self, attn_metadata, spec_metadata): | ||
| """Restore attn-metadata spec-dec state if a failure skipped it. | ||
|
|
||
| No-op on the success path: workers restore at their preferred point | ||
| and this sees no saved state. Subclasses with extra transient state | ||
| (e.g. the deferred kv_lens rewind in PARD/DFlash) extend this. | ||
| """ | ||
| if attn_metadata is not None and attn_metadata.has_spec_dec_saved_state: | ||
| logger.warning( | ||
| "Spec-dec worker forward failed between prepare_for_spec_dec " | ||
| "and restore_from_spec_dec; restoring attn metadata state.") | ||
| self._restore_attn_metadata_from_spec_dec(attn_metadata) | ||
|
|
||
| @property | ||
| @abstractmethod | ||
| def max_draft_len(self) -> int: | ||
|
|
||
Uh oh!
There was an error while loading. Please reload this page.