Open c4-bot-2 opened 11 months ago
hansfriese marked the issue as primary issue
fez-init (sponsor) confirmed
After discussing internally with the sponsor/warden, we've confirmed the issue. Here is a part of the discussion.
when it frontruns the liquidation with 1 share, it removes 1 share and 2 debt
when it calculates the amount again in the following liquidation, the shares will be worth 1 less
and it reverts
As a mitigation, we can update extraInfo.totalInterest
only when debtAmtCurrent > extraInfo.lastDebtAmt.
High is appropriate as the main invariant might be broken temporarily while repaying.
hansfriese marked the issue as satisfactory
hansfriese marked the issue as selected for report
Lines of code
https://github.com/code-423n4/2023-12-initcapital/blob/main/contracts/core/PosManager.sol#L175
Vulnerability details
Impact
Users can avoid being liquidated if they frontrun liquidation calls with a liquidate call with 1 wei. Or, they may do a partial liquidation and avoid being liquidated before the interest reaches the value of the debt pre liquidation. The total interest stored in
__posBorrInfos[_posId].borrExtraInfos[_pool].totalInterest
would also be wrong.Proof of Concept
The
POS_MANAGER
stores the total interest in__posBorrInfos[_posId].borrExtraInfos[_pool].totalInterest
. FunctionupdatePosDebtShares()
assumes thatILendingPool(_pool).debtShareToAmtCurrent(currDebtShares)
is always increasing, but this is not the case, as a liquidation may happen that reduces the current debt amount. This leads to calls toupdatePosDebtShares()
reverting.The most relevant is when liquidating, such that users could liquidate themselves for small amounts (1) and prevent liqudiations in the same block. This is because the debt accrual happens over time, so if the block.timestamp is the same, no debt accrual will happen. Thus, if a liquidate call with 1 amount frontruns a liquidate call with any amount, the second call will revert.
A user could still stop liquidations for as long as the accrued interest doesn't reach the last debt value before liquidation, if the user liquidated a bigger part of the debt.
Add the following test to
TestInitCore.sol
:Tools Used
Vscode, Foundry
Recommended Mitigation Steps
Update the user's last debt position
__posBorrInfos[_posId].borrExtraInfos[_pool].totalInterest
on_repay()
.Assessed type
Under/Overflow