# Incorrect loss calculation

VaultV2.realizeLoss miscomputes adapter loss because cap[id].allocation excludes accrued interest, leaving _totalAssets inflated and mispricing deposits/withdrawals.

- Payout: Contest reward
- Severity: medium
- Program: Morpho
- Credited: Audittens
- Disclosed: 2025-11-05
- Write-up quality: 7/10
- Original: https://cdn.cantina.xyz/reports/cantina_competition_morpho_jul2025.pdf#3.1.2
- Library page: https://bugbountylibrary.com/r/cantina%3Amorpho_jul2025%3A3.1.2
- Tags: domain:web3 impact:funds-loss kind:contest platform:cantina sev:medium tech:evm tech:solidity technique:source-review vuln:accounting-error vuln:business-logic vuln:precision-loss

**Target:** VaultV2.sol realizeLoss / MorphoVaultV1Adapter
**Root cause:** cap[id].allocation only updates on allocate/deallocate, while _totalAssets accrues interest continuously; realizeLoss computes loss as allocation() - previewRedeem(shares), ignoring accrued interest A, so loss is understated or the call reverts.
**Steps:**
1. Note _totalAssets is bumped in accrueInterest on nearly every vault interaction, but cap[id].allocation only changes on allocate/deallocate.
2. Call realizeLoss on a MorphoVaultV1Adapter after interest accrued but before any allocate/deallocate.
3. Adapter computes `loss = allocation() - IERC4626(morphoVaultV1).previewRedeem(shares)` where previewRedeem = allocation() + A - L.
4. If A > L, subtraction underflows and realizeLoss reverts, blocking loss reporting.
5. If A <= L, reported loss = L - A, so _totalAssets drops by only L - A instead of L.
**How found:** Code review comparing update cadence of _totalAssets (accrueInterest) versus cap[id].allocation (allocate/deallocate), then algebraically modeling interest A and loss L in the adapter's realizeLoss formula.
**Exploitation:** No direct theft; stale _totalAssets lets late withdrawers over-redeem and new depositors receive too few shares after a loss is realized.
**Insight:** When auditing vault accounting, compare the update frequency of aggregate state (_totalAssets) against per-adapter cached allocations; any path that derives loss/profit from a stale cache will diverge from true NAV.
