# Cream Finance: yUSD price manipulation inflates crYUSD collateral

Cream Finance crYUSD/crETH collateral was priced off manipulable yUSD Curve pool, letting attacker inflate collateral and borrow ~$130M.

- Payout: Real-world hack
- Severity: critical
- Program: CreamFinance
- Analysis by: DeFiHackLabs
- Disclosed: 2021-10-27
- Write-up quality: 7/10
- Original: https://github.com/SunWeb3Sec/DeFiHackLabs/blob/main/src/test/2021-10/Cream_2_exp.sol
- Library page: http://bugbountylibrary.com/r/dhl%3A20211027-cream-2
- Tags: area:web3 domain:web3 impact:funds-loss kind:incident platform:defihacklabs sev:critical tech:evm tech:solidity technique:chained vuln:accounting-error vuln:flash-loan vuln:oracle-manipulation

**Target:** Compound-fork lending market (crYUSD/crETH) with yUSD Curve/Yearn price oracle
**Root cause:** Cream's crYUSD collateral valuation depended on yUSD price derived from a Curve y-pool that the attacker could imbalance via large add/remove_liquidity, so collateral value was inflated far beyond real backing.
**Steps:**
1. Flash loan 500M DAI from MakerDAO (`DaiFlash.flashLoan(address(this), DAI, 500_000_000 * 1e18, "")`)
2. Convert DAI to yUSD and mint crYUSD in Cream, enter market as collateral
3. Second contract takes Aave flash loan of 524_102 WETH (`AaveFlash.flashLoan(...524_102*1e18...)`)
4. Send 6000 WETH to first contract; withdraw 518_102 WETH to ETH and `ICether(crETH).mint{value: 518_102 ether}()`, enter crETH market
5. Recursively `ICrToken(crYUSD).borrow(yUSD balance)` then `mint` and transfer crYUSD to first contract to stack collateral
6. Borrow remaining yUSD and transfer to first contract, then call `doIt()` on first contract
7. First contract withdraws yUSD into Curve 4-pool (`remove_liquidity_imbalance`/`remove_liquidity_one_coin`) to double crYUSD price
8. Borrow against inflated ~$3B collateral, repay Aave 524k WETH and MakerDAO 500M DAI flash loans
**How found:** Attacker recognized Cream's crYUSD pricing relied on a thin Curve y-pool that could be imbalanced with a large single-sided withdrawal, and that recursive mint/borrow could concentrate collateral to amplify the skew.
**Exploitation:** Attacker used two nested flash loans (MakerDAO 500M DAI, Aave 524k WETH) to seed crYUSD and crETH collateral, then recursively borrowed/minted crYUSD to concentrate collateral in one contract. By withdrawing yUSD into the Curve y-pool they skewed the yUSD price used to value crYUSD, roughly doubling collateral value, then borrowed against it to repay both flash loans and keep the residual.
**Escalation:** Recursive borrow-mint-transfer loop amplified crYUSD collateral before the price skew, maximizing borrowable amount against the manipulated valuation.
**Insight:** For Compound-fork markets, check whether cToken exchange rate or underlying price depends on a Curve/Yearn pool whose spot can be moved by add/remove_liquidity within one tx; recursive borrow-mint loops let you stack collateral cheaply before the skew.

## Proof of concept (copied exactly from the original report)

**Foundry exploit test with flashloans and yUSD manipulation**

```
function testExploit() public {
        SecondContract exploitContract = new SecondContract();
        secondContract = address(exploitContract);
        console.log("[1. Beigin]");
        console.log("------------Acquire Capital------------");
        console.log("[2. MakerDao FlashLoan 500_000_000 DAI]");
        DaiFlash.flashLoan(address(this), address(DAI), 500_000_000 * 1e18, "");

        console.log("[17. End]");
        console.log("------------Proift------------");
```

