The StabilityPool::liquidateBorrower()
function incorrectly scales the user's debt twice, leading to an inflated balance check and approval amount. This causes legitimate liquidations to fail due to insufficient balance checks, even when the StabilityPool has enough funds to cover the actual debt.
In StabilityPool.sol
line 453:
The LendingPool::getUserDebt()
function already returns a scaled debt value (multiplied by the normalized debt index). However, the StabilityPool
then scales this value again by multiplying it with getNormalizedDebt()
. This results in the debt being scaled twice, making scaledUserDebt
much larger than it should be.
For example:
If a user has 100 tokens of raw debt
And the normalized debt index is 1.1
getUserDebt()
will return 110 tokens (100 * 1.1)
The StabilityPool then multiplies 110 * 1.1 again
Resulting in 121 tokens of debt instead of the correct 110
When a liquidation is attempted through the StabilityPool, the function checks if the pool has enough crvUSD to cover the incorrectly scaled debt amount (if (crvUSDBalance < scaledUserDebt) revert InsufficientBalance()
). Due to the double scaling, this check requires the pool to have more crvUSD than actually needed, causing legitimate liquidations to fail even when the pool has enough funds to cover the real debt amount. Additionally, the function approves an unnecessarily high amount of crvUSD to the LendingPool.
The likelihood is HIGH because it affects every liquidation through the StabilityPool
when the normalized debt index is not exactly 1, which is almost always due to interest accrual.
The impact is HIGH because it prevents the protocol from executing legitimate liquidations, potentially leaving the protocol with bad debt that should have been liquidated.
Manual review
Remove the additional scaling operation. Simply use the scaledUserDebt
already returned from getUserDebt()
, which is the correct value directly as it's already properly scaled by the LendingPool
:
The contest is live. Earn rewards by submitting a finding.
This is your time to appeal against judgements on your submissions.
Appeals are being carefully reviewed by our judges.