Steadefi

Steadefi
DeFiHardhatFoundryOracle
35,000 USDC
View results
Submission Details
Severity: medium
Valid

Swaps can be sandwiched

Vulnerability Details

In processDepositFailureLiquidityWithdrawal() when one of the token amount is not enough to repay the borrowed debt, the entire amount of the other token is used to obtain the remaining token amount. These token amounts can differ very much from the market price causing the user to loose funds to sandwich attacks and the protocol to be in bad debt.

function processDepositFailureLiquidityWithdrawal(
GMXTypes.Store storage self
) public {
....... more code
(
bool _swapNeeded,
address _tokenFrom,
address _tokenTo,
uint256 _tokenToAmt
) = GMXManager.calcSwapForRepay(self, _rp);
if (_swapNeeded) {
ISwap.SwapParams memory _sp;
_sp.tokenIn = _tokenFrom;
_sp.tokenOut = _tokenTo;
_sp.amountIn = IERC20(_tokenFrom).balanceOf(address(this)); // @audit the entire amount is used
_sp.amountOut = _tokenToAmt;
_sp.slippage = self.minSlippage;
_sp.deadline = block.timestamp;
GMXManager.swapTokensForExactTokens(self, _sp);
}

https://github.com/Cyfrin/2023-10-SteadeFi/blob/0f909e2f0917cb9ad02986f631d622376510abec/contracts/strategy/gmx/GMXDeposit.sol#L282-L318

Example Scenario

  • The vault is 3x leveraged delta neutral vault with token weights 50%-50%.

  • User attempts deposit with 1usd value. Since 3x leverage, 1.5usd worth long token and 0.5usd worth short token is borrowed.

  • Due to the amount of vault share tokens getting minted being less than what user specified, the processDeposit function reverts and the status of the vault is now Deposit_Failed

  • Keeper calls processDepositFailure and GMX vault returns 1.4usd worth long token and 1.5usd worth short token. The loss of 0.1usd worth of long token is considered acceptable by the slippage.

  • Keeper calls processDepositFailureLiquidityWithdrawal. Since extra 0.1usd worth long token is required to repay the debt, a swap is attempted with amountIn = 1.5usd worth short token and amountOut = 0.1usd worth long token.

  • An attacker sees the opportunity and sandwiches the swap causing a loss of 1.4usd worth of funds.

Impact

User's may loose funds and protocol may incur bad debt.

Recommendations

The calcSwapForRepay function blindly assumes that it will be possible to repay both tokens after swap. Instead attempting to swap with only excess amounts of a token and choosing to revert or proceed if certain percentage of the other token amount has been reached seems to be better at handling this situation.

Updates

Lead Judging Commences

hans Lead Judge over 1 year ago
Submission Judgement Published
Invalidated
Reason: Out of scope
Assigned finding tags:

OOS: No slippage control on swap

Impact: High Likelihood: Low Note that the submission assumes the feasibility of price manipulation on exchanges. Also swaps are out of scope. Because it seems like slippage control does not exist in the codebase, leaving this for now for sponsor's review.

hash Submitter
over 1 year ago
hans Auditor
over 1 year ago
hash Submitter
over 1 year ago
hans Auditor
over 1 year ago
hash Submitter
over 1 year ago
ElHaj Auditor
over 1 year ago
hans Auditor
over 1 year ago
hans Lead Judge over 1 year ago
Submission Judgement Published
Validated
Assigned finding tags:

Missing slippage protection on swaps

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.