<!-- canonical: https://0xsimao.com/findings/autonomint-fees-reduced-withdraw-stuck -->

# `totalCdsDepositedAmountWithOptionFees` is incorrectly reduced in `CDSLib::withdrawUser()`, leading to stuck option fees

Crit/High · Sherlock · Hedged stablecoin · 4th December 2024

Finding H-33 of the Autonomint competition.

- Protocol: https://audits.sherlock.xyz/contests/569
- Report: /reports/autonomint
- Codebase: https://github.com/0xsimao/2024-11-autonomint/tree/0d324e04d4c0ca306e1ae4d4c65f0cb9d681751b
- Source: https://github.com/sherlock-audit/2024-11-autonomint-judging/issues/1019

---

### Summary

`totalCdsDepositedAmountWithOptionFees` in `CDSLib::withdrawUser()` is [reduced](https://github.com/sherlock-audit/2024-11-autonomint/blob/main/Blockchain/Blockchian/contracts/lib/CDSLib.sol#L731) by:
```solidity
totalCdsDepositedAmountWithOptionFees -= (params.cdsDepositDetails.depositedAmount - params.cdsDepositDetails.liquidationAmount + params.optionsFeesToGetFromOtherChain);
```
This is incorrect as the correct amount to reduce in option fees is `params.optionFees - params.optionsFeesToGetFromOtherChain`, not `optionsFeesToGetFromOtherChain` in this chain. As such, depending on the cds amounts of each chain, it will lead to too many/little option fees registered in the local chain, which will lead to stuck option fees.### 

### Root Cause

In `CDSLib.sol:731`, `totalCdsDepositedAmountWithOptionFees` is reduced by the incorrect amount.

### Internal pre-conditions

None.

### External pre-conditions

None.

### Attack Path

1. Cds depositor withdraws, having option fees, in which `params.optionsFeesToGetFromOtherChain` is null. Suppose a liquidation happened of 500, deposited amount is 1000 and options fees are 50, the resulting `totalCdsDepositedAmountWithOptionFees` is :
```solidity
totalCdsDepositedAmountWithOptionFees -= (params.cdsDepositDetails.depositedAmount - params.cdsDepositDetails.liquidationAmount + params.optionsFeesToGetFromOtherChain); = 550 - (1000 - 500 + 0) = 50
```
Note: for simplicity, it was assumed that the liquidation that happened reduced `totalCdsDepositedAmountWithOptionFees` by 500, which is not precise but it's an okay approximation for this example.
The user withdraws the option fees, but the CDS contract still has the 50 option fees stored in `totalCdsDepositedAmountWithOptionFees`, even though it is not actually backed.


### Impact

As `totalCdsDepositedAmountWithOptionFees` is 50, but the global `totalCdsDepositedAmountWithOptionFees` is null (it was correctly decreased), it will lead to incorrect calculations when getting the option fees [proportions](https://github.com/sherlock-audit/2024-11-autonomint/blob/main/Blockchain/Blockchian/contracts/lib/CDSLib.sol#L62). For example, if someone deposits 1000 cds and another user deposits borrows (suppose it pays more 50 USD), it will add option fees on deposit. Then, when the borrower withdraws and the cds depositor withdraws, `getOptionsFeesProportions()` will calculate `totalOptionFeesInOtherChain` as `1050 - 1100`, which underflows.

### PoC

See above.

### Mitigation

The correct code is:
```solidity
totalCdsDepositedAmountWithOptionFees -= (params.cdsDepositDetails.depositedAmount - params.cdsDepositDetails.liquidationAmount + (params.optionFees - params.optionsFeesToGetFromOtherChain));
```

---

Related findings:

- [`tower.gameETHForWithdraw` should be reduced pro-rata when there is not enough `ETH`](https://0xsimao.com/findings/codeup-tower-eth-withdraw-rata): CODEUP
- [`VaultPoolLib::reserve()` will store the `Pa` not attributed to user withdrawals incorrectly and leave in untracked once it expires again](https://0xsimao.com/findings/cork-protocol-attributed-withdrawals-untracked-expires): Cork Protocol
- [Mismatch between yield amount deposited in shares calculation and getAccountYieldBalance()](https://0xsimao.com/findings/benddao-mismatch-yield-deposited-shares): BendDAO
- [Admin new issuance or user calling `Vault::redeemExpiredLv()` after `Psm::redeemWithCt()` will lead to stuck funds when trying to withdraw](https://0xsimao.com/findings/cork-protocol-issuance-redeem-stuck-withdraw): Cork Protocol
