Closed c4-submissions closed 9 months ago
One part of this issue (slippage in depositRewards()
) is a duplicate of #39 and the implementation of ISafEth(SAF_ETH_ADDRESS).stake()
does not allow for any form of sandwich attack as far as I can see but will leave as primary for the sponsor to confirm. Keep in mind, there is no provided POC to showcase how this might be exploited in the case of the SAF_ETH_ADDRESS
contract.
0xleastwood marked the issue as primary issue
0xleastwood marked the issue as satisfactory
0xleastwood marked the issue as selected for report
0xleastwood removed the grade
One part of this issue (slippage in
depositRewards()
) is a duplicate of #39 and the implementation ofISafEth(SAF_ETH_ADDRESS).stake()
does not allow for any form of sandwich attack as far as I can see but will leave as primary for the sponsor to confirm. Keep in mind, there is no provided POC to showcase how this might be exploited in the case of theSAF_ETH_ADDRESS
contract.
I believe our solution for #39 (https://github.com/asymmetryfinance/afeth/pull/169) should solve this but please let us know if you see any way this can still be exploited
elmutt (sponsor) confirmed
Technically this will fix the issue, but I guess I wanted to confirm if it is possible to sandwich attack the ISafEth(SAF_ETH_ADDRESS).stake{value: amount}(0)
call in the first place? @elmutt
Technically this will fix the issue, but I guess I wanted to confirm if it is possible to sandwich attack the
ISafEth(SAF_ETH_ADDRESS).stake{value: amount}(0)
call in the first place? @elmutt
When you call stake() on safEth its buying 6 different LSD derivatives (reth, lido, ankr, swell, stafi, ankr) and will revert if the price paid for any of them is 1% or higher from the oracle price. You can see the revert in finalChecks() in derivativeBase.sol here: https://etherscan.io/address/0xb3e64c481f0fc82344a7045592284fddb9905b8b#code
Im not really an expert on sandwich attacks, would this mean it could be sandwiched for up to 1% if no minout is passed?
Right, I see. You need some tolerance for slippage to allow for a trade to execute in the first place. I think this function is being restricted anyway, so no way to sandwich attack. But it seems possible to extract value still.
0xleastwood marked the issue as duplicate of #23
0xleastwood changed the severity to 3 (High Risk)
0xleastwood marked the issue as not selected for report
0xleastwood marked the issue as satisfactory
Lines of code
https://github.com/code-423n4/2023-09-asymmetry/blob/main/contracts/AfEth.sol#L272-L293
Vulnerability details
Summary
Deposits to SafEth and VotiumStrategy coming from rewards lack slippage control, making them susceptible to sandwich attacks by MEV bots, which can result in a loss of funds for the protocol.
Impact
Rewards coming from the VotiumStrategy contract are compounded and deposited back to the protocol using the
depositRewards()
function:https://github.com/code-423n4/2023-09-asymmetry/blob/main/contracts/AfEth.sol#L272-L293
As we can see in lines 289 and 291, depending on the current TVL ratio between both collaterals, rewards will be either staked in SafEth or deposited back to VotiumStrategy.
Both scenarios experience the same lack of slippage control. The call to
stake()
sets zero as the_minOut
argument in SafEth. Similarly, in thedepositRewards()
function of VotiumStrategy, the process involves using a Curve Pool to exchange ETH for CVX tokens with a hardcodedmin_dy
parameter set to zero.In any case, the reward compounding transaction could be sandwiched by a MEV bot, causing less output received and a loss of funds to the protocol in general.
Recommendation
Add slippage control to the deposit rewards flow in order to allow the rewarded role to specify a minimum output of assets when rewards are either staked in SafEth, or swapped for CVX in VotiumStrategy.
Assessed type
MEV