Date: 2026-06-10 Source: Cycle 204 - Reserve Protocol Trusted Fillers (Cantina $10M), repo github.com/reserve-protocol/trusted-fillers @ f8db678. Verdict: WALK CLEAN. Class: async/intent-based swap fillers (CoW Swap, 1inch Fusion, UniswapX-style EIP-1271 wrappers).
Intent fillers split trade authorization across TWO predicates in TWO functions:
Accept predicate - isValidSignature (EIP-1271). Enforces a per-unit price FLOOR:
orderPrice = floor(order.buyAmount * D27 / order.sellAmount) >= price
where price = ceil(minBuyAmount * D27 / sellAmount) set at init. Rounds the accepted price DOWN.
Completion predicate - swapActive() / the close gate. Independently recomputes the required
counter-asset for the portion ACTUALLY moved:
minimumExpectedIn = ceil((sellAmount - currentSellBalance) * price / D27)
and refuses to close (sweep funds back) until buyBalance >= minimumExpectedIn. Rounds the
requirement UP.
A naive audit reads only isValidSignature, sees a per-unit floor that a PARTIAL fill can satisfy
while moving an odd dust amount, and suspects a rounding-leak finding. That is the trap. The
completion predicate re-demands, with CEIL rounding over the realized sold quantity, the buy token
the accept predicate may have let slide on the sign side. The two opposing roundings (floor-on-accept,
ceil-on-require) over the SAME realized quantities compose into a value-conservation invariant:
returned_sell + delivered_buy >= minBuyAmount (valued at the floor)
Verified empirically across full fill, half partial fill, and (sell=3, buy=6) dust fill - all conserve value. (Cycle 204 H1/H2/H4, real forge output, PASS.)
For ANY async/intent filler that authorizes via a signature/predicate and settles out-of-band:
1. Do NOT verdict on the order-validation predicate alone.
2. Locate the SETTLEMENT-COMPLETION predicate (the gate that releases/sweeps funds).
3. Verify the two predicates use OPPOSING rounding (floor on accept, ceil on require) over the SAME
realized quantities. Opposing -> defended. SAME direction -> that is the leak; build the PoC.
4. Test by asserting returned_sell + delivered_buy >= floor across full / partial / dust fills,
not by eyeballing one function.
GenericTokenJar.FillRequest (no explicit
nonce field) but is neutralized when fill creation deploys via Clones.cloneDeterministic with the
SIGNED deploymentSalt in the salt - re-deploy collides (CREATE2 revert), so the salt IS the nonce.