-
Notifications
You must be signed in to change notification settings - Fork 14
seeques - Collateral sent during borrowing is lost due to not accounting for borrowingCollateral in borrowing.DailyRateCollateralBalance #67
Comments
The borrowingCollateral is the margin deposit which is included in the borrowedAmount, therefore, it is only lost when the price moves in an unfavourable direction. In other cases, upon closing, after liquidity is restored, the remaining balance of borrowedAmount (including borrowed collateral) is returned to the trader (borrower). |
Escalate As the code suggests, both At first I thought that |
You've created a valid escalation! To remove the escalation from consideration: Delete your comment. You may delete or edit your escalation comment anytime before the 48-hour escalation window closes. After that, the escalation becomes final. |
@cvetanovv @fann95 what do you think? |
This is incorrect. holdTokenBalance - these are the tokens received during liquidity extraction (including the result of the swap). |
Hi @fann95 |
It should not be added, it is part of borrowedAmount. That is, this is what you actually received. borrowedAmount.will be more than holdTokenBalance or equal if the position is outside the current tick and swap will not occur |
If the position is outside, that is correct. But if the position is inside the current tick range, which would be in 90% of the cases, and the swap will occur, these swapped tokens are just sent to the Vault, where they would be stuck and lost as they are not represented anywhere in the system, which is a loss of liquidity for LPs. |
No, these exchanged tokens are part of the borrowedAmount . Because if the position is inside a tick, the result of extracted+swaped tokens will be less than the borrowedAmount. extracted+swaped+marginDeposit=borrowedAmount (which is stored) |
// Calculate borrowed amount
borrowedAmount += _getSingleSideRoundUpBorrowedAmount(
zeroForSaleToken,
tickLower,
tickUpper,
liquidity borrowedAmount = (
zeroForSaleToken
? LiquidityAmounts.getAmount1ForLiquidity(
TickMath.getSqrtRatioAtTick(tickLower),
TickMath.getSqrtRatioAtTick(tickUpper),
liquidity
)
: LiquidityAmounts.getAmount0ForLiquidity(
TickMath.getSqrtRatioAtTick(tickLower),
TickMath.getSqrtRatioAtTick(tickUpper),
liquidity
)
); But both amount0 and amount1 are borrowed from LP's position during liquidity extraction if the position is in the current tick range. Hence my reasoning that those tokens are not part of the |
Probably such a fantastic case is possible with positive slippage when the extracted+swaped tokens will be slightly more than the borrowedAmount, but in this case this dust will remain on the contract and it will be taken by the first one who calls the repay. We did not process these cases because they are unlikely and we wouldn't want to complicate the code and waste extra gas. The number of tokens in the single-side position will be more than on the current tick even if you exchange the second token.The price of a token will be worse in single positions.That is why borrowedAmount is calculated at the worst price that can be. I accepted #86 problem since it was possible to get DOS simply by sending a small number of tokens to the contract. |
Yes, I agree. I would argue though that any dust would not remain in the contract, but as a part of holdTokenBalance would be transferred to the Vault. And upon repayment this dust would not be taken as it would not be tranferred back to the contract from the Vault. |
@seeques does it mean that this behavior doesn't present a high/medium severity issue? |
It does not. I misinterpreted initially amounts calculation, but now I can see where my problem was. |
Great that consensus has been achieved. Will be rejecting the escalation and keeping the issue invalid. |
Result: |
Escalations have been resolved successfully! Escalation status:
|
seeques
high
Collateral sent during borrowing is lost due to not accounting for borrowingCollateral in borrowing.DailyRateCollateralBalance
Summary
During borrowing, a borrower has to pay some collateral in holdToken plus deposit for holding a position for 24 hours, which is a product of the
borrowedAmount
and thecurrentDailyRate
. The latter is added to the collateral balance of the borrower, while the former is not. This makes the collateral stuck in the Vault.Vulnerability Detail
In the
borrow()
function only thedailyRateCollateral
is added to theborrowing.DailyRateCollateralBalance
, while bothdailyRateCollateral
andborrowingCollateral
are transferred to the system.borrowing.DailyRateCollateralBalance
is the collateral balance before fees accrual and it is used to determine if a loan is liquidatable or not by calculating the actual collateral balance of the loan (that is, collateral balance minus the fees accrued).The only way of retrieving collateral from the Vault is calling the
repay()
function which can be called is case of liquidation or closing a position by the borrower.In case of liquidation (i.e., when
borrowing.DailyRateCollateralBalance
minus the fees < 0), theborrowing.DailyRateCollateralBalance
is added to borrowing.feesOwed after which tokens are transferred from the Vault and liquidity is being restored in uniswap position in the call to_restoreLiquidity()
, during which fees owed to a position owner is also transferred from the Vault.In case of closing position by the borrower the same happens, only his
borrowing.DailyRateCollateralBalance
is applied not to borrowing.feesOwed, but to the liquidationBonus which he receives at the end of the call.There is a 3rd case of emergency closure by the uniswap position owner but it is the same in a sense that no more tokens are drawn from the Vault that are borrowed and owed.
This means that the
borrowingCollateral
which is transferred upon borrowing is lost in the system.Impact
Loss of funds.
Code Snippet
https://github.com/sherlock-audit/2023-10-real-wagmi/blob/main/wagmi-leverage/contracts/LiquidityBorrowingManager.sol#L488-L490
https://github.com/sherlock-audit/2023-10-real-wagmi/blob/main/wagmi-leverage/contracts/LiquidityBorrowingManager.sol#L492-L503
https://github.com/sherlock-audit/2023-10-real-wagmi/blob/main/wagmi-leverage/contracts/LiquidityBorrowingManager.sol#L552-L557
https://github.com/sherlock-audit/2023-10-real-wagmi/blob/main/wagmi-leverage/contracts/abstract/DailyRateAndCollateral.sol#L103-L118
Tool used
Manual Review
Recommendation
Add borrowing collateral to the collateral balance
The text was updated successfully, but these errors were encountered: