# Dutch auctions can fail to settle if any other collateral in the basket behaves unexpectedly

Reserve's Dutch auction settlement chains rebalance() in a try-catch meant for OOG; an empty revert from a collateral token's approve() aborts settlement.

- Payout: Audit contest
- Severity: medium
- Program: Reserve
- Found by: RadiantLabs
- Disclosed: 2024-10-03
- Write-up quality: 6/10
- Original: https://code4rena.com/reports/2024-07-reserve#m-04
- Library page: https://bugbountylibrary.com/r/c4%3A2024-07-reserve%3AM-04
- Tags: domain:web3 impact:dos kind:contest platform:code4rena sev:medium tech:evm tech:solidity technique:source-review vuln:business-logic vuln:dos

**Target:** BackingManager.settleTrade / rebalance() try-catch in RToken backing manager
**Root cause:** settleTrade() chains rebalance() in a try-catch that treats empty revert data as out-of-gas, but empty reverts also come from external token calls (e.g. approve() on USDT/BNB-style tokens), causing settlement to revert.
**Steps:**
1. Dutch auction for rebalancing collateral is initiated.
2. Bidder submits a fair-value bid; trade contract calls BackingManager.settleTrade().
3. settleTrade() invokes rebalance() inside a try-catch intended to catch OOG.
4. rebalance() reaches tryTrade() -> AllowanceLib.safeApproveFallbackToMax() -> token.approve().
5. A collateral ERC20 whose approve() reverts with empty data (e.g. USDT/BNB style) returns no error data.
6. Catch block interprets empty data as OOG and reverts the whole settlement.
**How found:** Code review of the try-catch OOG pattern in settleTrade(); noted empty revert data is not unique to OOG and traced external token interactions (refPerTok, approve) that can produce empty reverts.
**Exploitation:** Not an attack; a misbehaving/upgraded collateral token causes legitimate auction bids to fail settlement, leaving the auction unable to settle at fair price.
**Insight:** Empty revert data is not a reliable OOG signal; audit every try-catch that assumes it, and check whether external token calls (approve, balanceOf) inside the guarded block can revert empty on real tokens like USDT/BNB.
