perf(router): negotiation-first ordering cuts the CM5 route 113min → 14min#680
Merged
Conversation
… 14min The greedy phase paid for its unrouted tail twice. Every connection the speculative batch search missed got the full sequential rescue arsenal (flow escape, coupled-pair phantom, true shove) inline in the batch loop, and the GPU negotiator — which resolves the same tail in seconds — only ran afterwards. Then rip-up rounds re-solved it a third time at ~45 minutes each, routinely ending with fewer connections placed than they started (536 -> 511) and being discarded wholesale by keep-best. Reorder the layer-rich regime around the negotiator: - route_batch runs search-only when negotiation goes first; failures fall straight through to the negotiator, and the arsenal fires once afterwards over its leftovers (`arsenal_sweep`). Measured on the full CM5: negotiation takes pending 37 -> 11 in 4.9s, the sweep 11 -> 10 in 48s. - Skip the greedy phase's rip-up rounds once negotiation has run first. Both measured rounds in this regime regressed and were thrown away (536 -> 511 full board, 382 -> 380 on the 250-net subset). - Stop the negotiation loop after round 0 in this regime. Round 0 is already a negotiated pass carrying the arsenal and the last-round fine-retry, and every incremental CPU round measured here ended below it and was discarded (335s + 183s full board, 231s + 130s subset). - Make the surviving budgets binding. They were checked between connections only, but one connection's victim re-route is itself a whole batch, so a 92s budget measured 231s. route_batch now takes an optional deadline; over it, the remaining queue is reported unrouted — which every caller already handles (a stuck connection stays pending, a ripped victim gets its original copper restored), so it costs attempts, never legality. The >= 4 copper layer gate is preserved and now lives in one place (`negotiate_first_regime`): thin boards keep arsenal-first, the full rip-up ladder and all four negotiation rounds, because their scarce corridors are spent more carefully by the arsenal (the VESC lost 4 points to negotiation-first). Boards without the gpu feature or with VCAD_GPU_NEGOTIATE unset are untouched. Benchmarks (same machine, load ~5, VCAD_GPU_BATCH=1 VCAD_GPU_NEGOTIATE=1): board before after CM5 ~113 min 0.985 14.4 min 0.981 VESC ~26 s 0.79 22.9 s 0.787 moteus 80-124 s 0.87 107.6 s 0.891 Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Choji has used up today's reviewsYour team has reached the free plan's limit of 5 reviews per day, so Choji stepped aside on this pull request. That's a plan limit, not a reflection of the change itself. Your free reviews reset tomorrow. To have Choji review every push without waiting, upgrade to Pro for unlimited reviews. You're on the free plan · 5 reviews/day. |
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
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
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.
What
The greedy phase paid for its unrouted tail three times over.
Measured on the full CM5, the baseline spends 82% of its 113 minutes on three rounds that all end below where they started and are then discarded wholesale by keep-best:
route_batch(greedy + inline arsenal)This reorders the layer-rich regime around the negotiator and lets the arsenal work only what negotiation leaves behind.
Changes
route_batchruns search-only when negotiation goes first. Failures fall straight through to the negotiator; the arsenal fires once afterwards over its leftovers (newarsenal_sweep). On the full CM5 negotiation takes pending 37 → 11 in 4.9s, the sweep 11 → 10 in 48s. Dropping the inline arsenal also cuts the greedy batch itself from 680.5s to 470.9s for identical output (191 committed, 37 unrouted).route_batchnow takes an optional deadline; past it the remaining queue is reported unrouted, which every caller already handles (a stuck connection stays pending, a ripped victim gets its original copper restored). It costs attempts, never legality.Board-regime rule preserved
The
>= 4 copper layersgate is unchanged and now lives in one place (negotiate_first_regime). Thin boards keep arsenal-first ordering, the full rip-up ladder, and all four negotiation rounds — their scarce corridors are spent more carefully by the arsenal (the VESC lost 4 points of routability to negotiation-first). Boards built without thegpufeature, or run withoutVCAD_GPU_NEGOTIATE=1, are untouched.Benchmarks
Same machine, same session, background load ~5,
VCAD_GPU_BATCH=1 VCAD_GPU_NEGOTIATE=1. CM5 before/after are both measured here, not quoted:Where the CM5's 14.4 min goes now:
route_batch470.9s, GPU negotiation 4.9s, arsenal sweep 48.4s, post-loop repair and plane stitching the rest.Routability trade: 0.985 → 0.981, i.e. 2 connections of 544, against 99 minutes. It is above the 0.98 bar but worth naming: in the old order the inline arsenal commits its rescues during the batch, so the board those rescues leave behind lets negotiation reach pending 8 where the new order reaches 10. Recovering them would mean running the sweep over all 37 failures before negotiation rather than over its 11 leftovers — roughly +2 minutes — if those two connections are worth it.
Verification
cargo test -p vcad-ecad-pcb— 248 passedcargo clippy -p vcad-ecad-pcb --features gpu -- -D warnings— clean (also clean without the feature)🤖 Generated with Claude Code