Closed howlbot-integration[bot] closed 3 months ago
alcueca marked the issue as duplicate of #326
alcueca marked the issue as satisfactory
@alcueca The root cause of #326 is the pricing of withdrawals on withdraw
instead of on the delayed claim
(e.g. here and here). Note my other issue #239 which is correctly duplicated to #326 on this basis.
This issue (#424), on the other hand, is not based on either the pricing on withdraw
instead of claim
, nor the delay, nor on sandwiching an oracle update. Rather, it is a static issue that arises when tokenizing a sum of price feeds. It can only be mitigated by a pessimistic valuation, effectively charging a fee on withdrawal.
The originary report of this kind of issue might be helpful (note however that it also deals with the additional complication that it was not possible to freely choose which asset to deposit or withdraw).
alcueca marked the issue as not a duplicate
@jatinj615, please review. You might consider this expected behaviour, but same as #13 arbitrage opportunities of this kind should be avoided. I also see fees on withdrawals as a more elegant and doable solution to prevent MEV and arbitrage than pricing withdrawals upon claiming.
alcueca marked the issue as primary issue
@alcueca , thanks for pointing out the arbitrage issue. Some pointers which needs to be considered at the current state of the protocol from our side -
Only stETH collateral uses the exchange rate feed while wbETH uses the true exchange rate
from the contract. through WBETHShim contract. Hence, only stETH oracle feed is volatile.
while stETH exchange rate can potentially open up an arbitrage opportunity. There are few factors which I would like to highlight -
While I understand fee on withdrawals seems like a doable solution, it impacts the user's APY which is not favourable for protocol users. Instead we think a long term solution can be implemented by utilising the true price and exchange rate price of stETH. i.e. consider lowest of both at time of deposit and highest of both at withdraw.
Acknowledging for now.
alcueca marked the issue as selected for report
alcueca marked the issue as duplicate of #13
alcueca marked the issue as not selected for report
Given that the root cause is the use of market rates for stEth, this becomes a uplicate of #13
alcueca changed the severity to 2 (Med Risk)
@alcueca Why was this lowered to Medium and duplicated to #13 (/deselected as best)?
I'm not sure if this has been properly understood, but #424 has nothing to do with frontrunning an oracle update. #429 is only based on frontrunning an oracle update, and #13 is only based on frontrunning an update of an stETH depeg.
The root cause of #424 is not the use of the market rate; rather, being able to use the true market rate would completely eliminate the arbitrage discussed in #424.
stETH -> ezETH
, price change
, ezETH -> stETH
, just as reported by #429. The second part seems to be essentially the same thing: ETH -> ezETH
, price change
, ezETH -> stETH
. Only by invoking a second asset could it be connected to #424, in which case it has to be interpreted that "stETH market depegs" is not reflected in the oracle price feed. This information is missing, however.It turns out the price change in ezETH can only effectively happen if it is based on more than a single underlying asset, otherwise the price of ezETH would just be a fictitious conversion factor (as long as the vault is otherwise fairly implemented). However, #13 and #429 make no mention of, nor seem to be aware, this fact; they simply seem to be based on the idea of the price's changing and to exploit this as a possibility to predict the "future" for a winning trade.
All these issues are quite similar in that there is an arbitrage opportunity in the way that ezETH is minted based on oracle prices, which invariably deviate from the true value of ezETH, whatever that might be.
All these cases are mitigated, at least partially, by locking in the withdrawals queue the LSTs without producing yield for the cooldown period. All these cases would be mitigated by applying deposit or withdrawal fees. Several other mitigations, like delays on deposits, or pricing withdrawals at the time of claim, would likely address all of these findings equally.
Based on this, and how all the findings seem to draw from the same past contests and protocols, I'm inclined to consider them a group.
I also have the impression that the sponsor was not unaware of these issues, but that probably didn't consider them to be serious enough to warrant more serious defensive measures. None of these issues has proven beyond doubt that they would have a serious impact on the protocol. Based on that, I think that a Medium severity is fair.
Lines of code
https://github.com/code-423n4/2024-04-renzo/blob/519e518f2d8dec9acf6482b84a181e403070d22d/contracts/RestakeManager.sol#L507 https://github.com/code-423n4/2024-04-renzo/blob/519e518f2d8dec9acf6482b84a181e403070d22d/contracts/Withdraw/WithdrawQueue.sol#L229
Vulnerability details
Impact
A discrepancy in oracle price deviation between two assets can be exploited for arbitrage; one can deposit the relatively overvalued asset and withdraw for the relatively undervalued asset.
Proof of Concept
The price of ezETH is based on a sum of oracle prices of multiple assets. The oracles will be slightly inaccurate; in the case of the Chainlink stETH/ETH feed the deviation threshold is 0.5%, which means that it may be up to 0.5% more or less than the true price. The deposit is valued according to the oracle price, and so is the amount of tokens received on withdrawal.
Suppose
2000
ezETH has been minted against1000
tokA and1000
tokB, and that the current true prices of tokA and tokB are1
. However, suppose the oracle returns a price of tokA as1.005
and of tokB as0.997
. This means that ezETH will be priced at(1005 + 997) / 2000 = 1.001
An attacker can exploit this by depositing tokA and withdrawing tokB. Suppose the attacker buys100
tokA for100
ETH (according to its true price) and deposits this. This will be valued as100 * 1.005 = 100.5
ETH by the oracle and he will get100.5 / 1.001 ≈ 100.4
ezETH. (This does not change the price of ezETH.) If he then immediately withdraws the ezETH, but now for tokB, he will get a value of100.4 * 1.001 = 100.5
ETH, which in tokB is–according to the oracle–100.5 / 0.997 ≈ 100.8
tokB, which is also truly worth100.8
ETH. The attacker was thus able to acquire100.8
ETH worth of tokB by depositing only100
ETH worth of tokA.Recommended Mitigation Steps
Note that this attack depends on a differential deviation between assets. It would not work if there was only one asset, or if they deviate identically. The maximum extractable value in percentage is the maximum possible deviation between any two assets. Consider eliminating the profitability of this attack by taking exactly this percentage as a fee on either deposit of withdrawal, e.g. if the deviation threshold of tokA is 0.5% and of tokB is 0.3% then charge a 0.8% fee. This fee might either be taken by the protocol or just implemented as a reduced amount of ezETH minted or tokens withdrawn, effectively returning it to other holders.
Assessed type
MEV