Skip to content

fix(train): hand off to the engine before an off-cadence final eval - #3615

Merged
guapisolo merged 1 commit into
mainfrom
jiajun/fix-final-eval-handoff
Sep 23, 2026
Merged

guapisolo merged 1 commit into
mainfrom
jiajun/fix-final-eval-handoff

Conversation

@guapisolo

Copy link
Copy Markdown
Collaborator

Summary

Runs the last rollout's engine handoff whenever a final eval follows, including off-cadence.

Symptom & Reproduction

Root Cause

  1. train.py handoff guard calls should_run_periodic_action without args.num_rollout.
  2. should_run_periodic_action forces the last rollout only when num_rollout is passed.
  3. At --num-rollout 3 --eval-interval 20, the guard is false on rollout 2; the handoff is skipped.
  4. The eval gate passes args.num_rollout, so the final eval still dispatches.
  5. release_memory_occupation leaves the colocated engine released; eval requests crash its scheduler.

Fix

train() computes eval_due once and uses it for both the handoff guard and the eval gate, so the two cannot disagree. The last rollout still skips the handoff when no final eval follows, which is #3182's intent. Every earlier rollout is unchanged. Without colocation the old code did not crash, but its final eval scored the previous rollout's weights; that also changes.

Verification

  • tests/fast/test_train.py, tests/fast/test_train_async.py: 16 passed locally (CPU). The new off-cadence test fails on main (8cdf3794d9) and passes here; test_the_last_rollout_skips_the_handoff_without_an_eval passes on both.
  • The two GPU e2e tests were not rerun; they need run-ci-fsdp.

Review Focus

  • eval_due in train.py: the handoff must run for every rollout whose eval runs, and only then on the last one.

🤖 Generated with Claude Code

#3182 skips the last rollout's engine handoff (weight onload,
update_weights, KV onload) unless a final eval follows, but its guard called
should_run_periodic_action without args.num_rollout. That helper only treats
the last rollout as due when num_rollout is passed, so whenever num_rollout is
not a multiple of eval_interval the guard skipped the handoff while the eval
gate below, which does pass num_rollout, still ran the final eval.

With --colocate the eval then reached an engine left in the released state:
the 2026-09-22 nightly lost test_qwen3_vl_4B_fsdp and
test_qwen3_4B_fsdp_true_on_policy (--num-rollout 3 --eval-interval 20) to
"Pointer argument cannot be accessed from Triton (cpu tensor?)" in
write_req_to_token_pool_triton. Without colocation the final eval would score
the previous rollout's weights.

Compute eval_due once and use it for both the handoff guard and the eval
gate, so the handoff runs exactly when a final eval needs it.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

@claude claude Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Claude Code Review

This repository is configured for manual code reviews. Comment @claude review for a one-time review, or @claude review always to subscribe this PR to a review on every future push.

Tip: disable this comment in your organization's Code Review settings.

@guapisolo

Copy link
Copy Markdown
Collaborator Author

@claude review always

@guapisolo

Copy link
Copy Markdown
Collaborator Author

/rerun-test tests/e2e/fsdp/test_qwen3_vl_4B_fsdp.py

@guapisolo

Copy link
Copy Markdown
Collaborator Author

/rerun-test tests/e2e/fsdp/test_qwen3_4B_fsdp_true_on_policy.py

@claude claude Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Code review found no issues

No high-confidence issues detected in this change.

@github-actions

github-actions Bot commented Sep 23, 2026 •

Copy link
Copy Markdown
Contributor

✅ tests/e2e/fsdp/test_qwen3_4B_fsdp_true_on_policy.py passed on stage-c-2-gpu-h200 in 17m02s — workflow run

@github-actions

github-actions Bot commented Sep 23, 2026 •

Copy link
Copy Markdown
Contributor

✅ tests/e2e/fsdp/test_qwen3_vl_4B_fsdp.py passed on stage-c-2-gpu-h200 in 17m31s — workflow run

@guapisolo
guapisolo merged commit e89b45f into main Sep 23, 2026
25 checks passed
@guapisolo
guapisolo deleted the jiajun/fix-final-eval-handoff branch September 23, 2026 03:47
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants