# External PT redeem functions can be reentered to double count the received underlying funds

Reentrancy in Illuminate Redeemer's Sense redeem lets attacker re-enter multi-PT redeem, double-counting underlying in holdings and draining funds.

- Payout: Contest reward
- Severity: high
- Program: Illuminate
- Credited: Jeiwan
- Disclosed: 2022-10-15
- Write-up quality: 8/10
- Original: https://github.com/sherlock-audit/2022-10-illuminate-judging/issues/236
- Library page: https://bugbountylibrary.com/r/sherlock%3A2022-10-illuminate%3AH-2
- Tags: domain:web3 impact:funds-loss kind:contest platform:sherlock sev:high tech:solidity technique:chained vuln:accounting-error vuln:business-logic vuln:reentrancy

**Target:** Redeemer.sol redeem() functions (multi-PT and Sense)
**Root cause:** Both redeem() functions compute redeemed underlying as balance difference (balanceOf - starting) without a reentrancy guard; Sense redeem calls a user-supplied adapter mid-snapshot, allowing reentry into the multi-PT redeem which also credits holdings.
**Steps:**
1. Lend 1 block before maturity, wait 1 block.
2. Deploy wrapper contract 'a' implementing ISenseAdapter; its divider()/target() return valid values but it first calls Redeemer.redeem(p,u,m) for all non-Sense PTs held by lender.
3. Call Redeemer.redeem(Sense, u, m, s, a) with elevated gas.
4. Inner multi-PT redeem credits holdings[u][m] += redeemed for each PT.
5. Outer Sense redeem's balance-diff snapshot also captures those same underlying funds, crediting holdings again (double count).
6. Be first to redeem Illuminate PTs to withdraw up to double the underlying, leaving contract insolvent.
**How found:** Code review: noticed both redeem() functions measure received underlying via balanceOf difference and that Sense redeem invokes a user-supplied adapter between the starting and ending balance snapshots, creating a reentrancy window that double-counts funds.
**Exploitation:** Attacker supplies malicious Sense adapter that reenters multi-PT redeem for all other PT types before performing the real Sense redeem; the same underlying received is counted twice in holdings, letting attacker redeem Illuminate PTs for up to double funds and drain the contract.
**Insight:** When a function measures value received via balance-difference and calls an attacker-controlled contract mid-measurement, reentering any sibling function that also credits the same accounting variable double-counts funds; check every external call between balance snapshots.
