Skip to content

fix(inference): AUT-2539 reply to a KV handoff import that fails before admission - #8255

Open
svcnemo-autobot wants to merge 3 commits into
NVIDIA:mainfrom
svcnemo-autobot:fix/inference-handoff-failed-import-reply
Open

svcnemo-autobot wants to merge 3 commits into
NVIDIA:mainfrom
svcnemo-autobot:fix/inference-handoff-failed-import-reply

Conversation

@svcnemo-autobot

@svcnemo-autobot svcnemo-autobot commented Oct 15, 2026 •

Copy link
Copy Markdown
Collaborator

Background

A review of recent inference changes on main found a hang in disaggregated decode. The decode side imports a request's KV cache before it admits the request. An import can fail before _finalize_kv_handoff_import() runs, either because a peer failed or because the local transfer raised. The request then never reaches add_request().

_admit_pending_kv_imports() releases or quarantines the blocks and fails the import future, but the engine dispatch drops that future. So no ENGINE_REPLY is ever sent. The coordinator frees a request's routing entry and pending count only on ENGINE_REPLY, so the client request hangs forever.

What changed

  • inference_state_handoff.py: in the except branch, an import that is not in self.requests now calls _fail_submission(). This is the same FAILED-placeholder path already used for rejected submissions. Every MP rank applies the same broadcast completion decision to mirrored state, so all ranks register the same placeholder. Only the MP coordinator sends the reply.
  • dynamic_engine.py: the _fail_submission docstring now names this caller.
  • test_disagg_handoff_lifecycle.py:
    • The peer-failure quarantine test now asserts exactly one failed submission.
    • The submission-failure test now runs the engine's real _fail_submission, _handle_failed_request and _complete_request, with only the coordinator socket mocked. It asserts exactly one FAILED reply for the request.

Details

Release-once and quarantine behavior are unchanged. A failure after add_request() still goes through the existing request path. There are no dependency or lock changes.

The branch was based on main at a54dd737 and now merges main at ee6baa2e. CI on the previous head (which merged main at 3914483f, run 38816895124) timed out in an NCCL barrier in test_checkpointing.py::test_checkpoint_load_without_microbatch_calculator (torch_dist cases). ee6baa2e is #8263, "test(checkpointing): seed CPU initialization in checkpoint load test". Against main at ee6baa2e, this branch still changes only the three files above.

Tested

  • black, isort, pylint and ruff are clean on the three changed files.
  • unit:tests/unit_tests/inference/**/*.py on 1×8 H100 at 49fcf50f (before the merges), CI image for a54dd737 (sha256:5c82eeb5…): 3674 passed, 37 skipped, 9 deselected, 0 failed, exit code 0. All 37 tests in test_disagg_handoff_lifecycle.py passed, including the two changed failure tests.
  • Full tests/unit_tests/**/*.py bucket on 8×H100, on this head merged with the main tip (28d5dd15), image megatron-lm@sha256:7b4e22a3…: 3424 passed, 142 skipped, 0 failed; then 24 of 24 passed in the second session; exit code 0. All 16 test_checkpoint_load_without_microbatch_calculator cases passed, including every torch_dist case.
  • No functional rows were run: no functional test case covers disaggregation.
  • GitHub CI on this head is pending.

A decode-side KV handoff import that fails (peer failure or local transfer error) before _finalize_kv_handoff_import() never reaches add_request(). The except branch in _admit_pending_kv_imports() released or quarantined its blocks and failed the future, but the engine dispatch drops that future, so no ENGINE_REPLY was sent. The coordinator frees routing and pending counts only on ENGINE_REPLY, so the request hung forever.

When the failed import is not in self.requests, register the same FAILED placeholder _fail_submission() uses for rejected submissions. Every MP rank applies the broadcast completion decision to mirrored state, and only the MP coordinator sends the reply. Release-once and quarantine behavior are unchanged.

Signed-off-by: svcnemo-autobot <svcnemo-autobot@nvidia.com>
@svcnemo-autobot
svcnemo-autobot requested review from a team as code owners October 15, 2026 14:37
@copy-pr-bot

copy-pr-bot Bot commented Oct 15, 2026

Copy link
Copy Markdown

This pull request requires additional validation before any workflows can run on NVIDIA's runners.

Pull request vetters can view their responsibilities here.

Contributors can view more details about this message here.

@svcnvidia-nemo-ci
svcnvidia-nemo-ci marked this pull request as draft October 15, 2026 14:38
@github-actions

Copy link
Copy Markdown
Contributor

This PR has been automatically converted to draft because all PRs must start as drafts.

When you are ready for review, click Ready for Review to begin the review process. This will:

  1. Add the oncall reviewer (optional reviewer)
  2. Add required review teams based on your changes

See the contribution guide for more details.

@svcnvidia-nemo-ci

Copy link
Copy Markdown
Contributor

/ok to test 49fcf50

Bring in main 3914483 so CI's main-based Testmon baseline matches the branch base.

Signed-off-by: svcnemo-autobot <svcnemo-autobot@nvidia.com>
@svcnvidia-nemo-ci

Copy link
Copy Markdown
Contributor

/ok to test ba41ebb

Signed-off-by: svcnemo-autobot <svcnemo-autobot@nvidia.com>
@svcnvidia-nemo-ci

Copy link
Copy Markdown
Contributor

/ok to test 9dc92d4

@ko3n1g

ko3n1g commented Oct 16, 2026

Copy link
Copy Markdown
Contributor

/review

@svcnvidia-nemo-ci svcnvidia-nemo-ci left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM. The pre-admission import failure now reaches the existing immediate failure-reply path. The regression assertions cover exactly one FAILED reply and retain the release/quarantine checks. Static review only; tests were not executed.

Note: formal approval is not available for this request, so this review is posted as a comment only.

Review generated by codex

This branch was successfully deployed

2 active deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants