Summary
Reclaim orphaned per-swap VoteRound rent and add a reaper instruction to close vote rounds that no terminal path will ever close. Not urgent — the going-forward leak is already stopped by #549. This is a cleanup + a safety net for multi-validator.
Background
VoteRound PDAs come in two shapes:
- per-swap — CONFIRM (
REQ_CONFIRM=6) / TIMEOUT (REQ_TIMEOUT=7), seeded by swap_key. Unique per swap, never reused.
- per-miner / global — INITIATE / ACTIVATE / DEACTIVATE (seeded by miner) and SET_WEIGHTS (singleton). Reused across swaps.
Before #549, the terminal quorum branch in confirm_swap / timeout_swap called reset_round(...) — it zeroed created_at but left the account funded and alive. Every completed per-swap round leaked its rent (~0.004823 SOL each). #549 (Part 1) replaced that with vote_round.close(validator) in the same terminal branch as swap.close(...), so new swaps no longer orphan rent.
Verified live on mainnet (6JVBEj5w27J2SVjERmv2c7wXgFee9nSSBKUJevHehyBD):
- deployed bytecode == fixed build (sha256
8a57ed4b…)
- confirm-tx rent math: validator net-refunds full swap rent (+0.006523 SOL), i.e. the round is created + closed in the same tx — not parked
- 0 open per-swap rounds; our 4 post-deploy spot-check swaps orphaned nothing
The residual (what this issue tracks)
The fix does not retroactively clean rounds orphaned before it. On mainnet right now:
- 35 leftover per-swap
VoteRound accounts, all with created_at == 0 (the pre-fix reset_round signature) — pure debris.
- ~0.169 SOL of reclaimable rent parked across them (35 × 0.004823).
There is currently no instruction that can close these — the only closers are the terminal confirm/timeout branches, and those swaps are long gone (their Swap PDAs are closed), so the rounds are unreachable and stranded forever.
Why it can wait
- Bounded, non-growing: the going-forward leak is fixed, so this set does not increase.
- Small: ~0.169 SOL, and it's our own validator's rent.
- No correctness impact: stranded rounds don't affect swaps, crown, or scoring.
Proposed fix (Part 2 — reaper)
Add a permissioned close_orphaned_round instruction (validator/admin-signed) that closes a VoteRound whose bound swap no longer exists (or whose created_at == 0 and has aged out), refunding rent to the caller. One-time sweep of the current 35, and it becomes the safety net for multi-validator, where straggler/never-quorum rounds become a real ongoing possibility rather than a testing artifact.
Target milestone: multi-validator (roadmap, ~month(s) out). Fold the sweep of the current 35 into that same change.
Refs #549.
Summary
Reclaim orphaned per-swap
VoteRoundrent and add a reaper instruction to close vote rounds that no terminal path will ever close. Not urgent — the going-forward leak is already stopped by #549. This is a cleanup + a safety net for multi-validator.Background
VoteRoundPDAs come in two shapes:REQ_CONFIRM=6) / TIMEOUT (REQ_TIMEOUT=7), seeded byswap_key. Unique per swap, never reused.Before #549, the terminal quorum branch in
confirm_swap/timeout_swapcalledreset_round(...)— it zeroedcreated_atbut left the account funded and alive. Every completed per-swap round leaked its rent (~0.004823 SOL each). #549 (Part 1) replaced that withvote_round.close(validator)in the same terminal branch asswap.close(...), so new swaps no longer orphan rent.Verified live on mainnet (
6JVBEj5w27J2SVjERmv2c7wXgFee9nSSBKUJevHehyBD):8a57ed4b…)The residual (what this issue tracks)
The fix does not retroactively clean rounds orphaned before it. On mainnet right now:
VoteRoundaccounts, all withcreated_at == 0(the pre-fixreset_roundsignature) — pure debris.There is currently no instruction that can close these — the only closers are the terminal confirm/timeout branches, and those swaps are long gone (their
SwapPDAs are closed), so the rounds are unreachable and stranded forever.Why it can wait
Proposed fix (Part 2 — reaper)
Add a permissioned
close_orphaned_roundinstruction (validator/admin-signed) that closes aVoteRoundwhose bound swap no longer exists (or whosecreated_at == 0and has aged out), refunding rent to the caller. One-time sweep of the current 35, and it becomes the safety net for multi-validator, where straggler/never-quorum rounds become a real ongoing possibility rather than a testing artifact.Target milestone: multi-validator (roadmap, ~month(s) out). Fold the sweep of the current 35 into that same change.
Refs #549.