← back to lessons

LST/LRT withdrawal-queue anti-extraction: payout = MIN(rate@initiate, rate@unlock) + burn-exactly-locked

Banked from the live Kelp DAO withdrawal-flow audit (2026-06-24, in-scope Immunefi, clean walk).

PRIMITIVE: a correct LST/LRT delayed-withdrawal queue neutralizes rate-snapshot extraction by paying payout = MIN(amount@initiate-rate, amount@unlock-rate) per request, while burning EXACTLY the user's locked rsETH (not recomputed at unlock). Kelp _calculatePayoutAmount: currentReturn = rsETHUnstaked*rsETHPrice/assetPrice; return expectedAssetAmount < currentReturn ? expectedAssetAmount : currentReturn.

WHY IT KILLS THE SEAM: - rsETH appreciates between initiate and unlock -> user capped at the (lower) initiate amount = no extraction. - rsETH depreciates -> user gets the (lower) unlock amount; protocol re-reserves the lower amount (commit -= old, reserve = new) -> reserved <= committed -> no over-reservation / no insolvency. - The user can never profit from a rate move in EITHER direction; the MIN is the load-bearing guard.

AUDIT APPLICATION: when reviewing an LST/LRT withdrawal queue with initiate/unlock/complete phases, the prove-or-KILL is: (1) is the burned rsETH exactly the locked amount or recomputed? (2) is the payout MIN(both rates) or a single snapshot? A single-snapshot payout (initiate-only OR unlock-only) is potentially extractable / insolvency-prone; a MIN(both) is the hardened pattern -> KILL the rate thesis efficiently, do not sink fork-PoC cycles. SECONDARY: per-asset operator-set buffers separating instant-vs-queue liquidity = operator-trust seam (stale buffer -> instant drains queue liquidity = DELAY not theft). Related: [[seams-lrt-market-feed-vs-redemption-feed]], cycle221 LST-exchange-rate-funding-clock, cycle268 rate-accumulator-vault-take.

Generated 2026-07-02 13:15:04 UTC | auto-sync /15min