sherlock-audit / 2024-05-sophon-judging

7 stars 6 forks source link

hunter_w3b - Protocol supports `eETH` but doesn't consider its also a rebase token like `stETH` #186

Closed sherlock-admin2 closed 4 months ago

sherlock-admin2 commented 4 months ago

hunter_w3b

high

Protocol supports eETH but doesn't consider its also a rebase token like stETH

Summary

eETH is also a rebasing token like stETH it should check it's value before and after the transfer

Vulnerability Detail

eETH is also a rebasing token like stETH it should check it's value before and after the transfer

Docs for eETH

eETH launched on November 15th, 2023

eETH, brought to you by ether.fi, is a Liquid Restaking Token that allows users to stake their ETH to accrue staking rewards and automatically restake their ETH in EigenLayer.

@>> weETH is the wrapped non rebasing version of eETH that can be used throughout the DeFI ecosystem. ether.fi will >be working with DeFi partners to create utility for weETH including Balancer, Gravita, Pendle, Aura, Maverick, and many >more, as well as other layer two protocols proceeding the launch date.

Rebasing tokens, such as eETH, have a dynamic supply that can complicate their integration with DeFi platforms.

    function depositStEth(uint256 _amount, uint256 _boostAmount) external {
        IERC20(stETH).safeTransferFrom(
            msg.sender,
            address(this),
            _amount
        );

        _depositPredefinedAsset(_amount, _amount, _boostAmount, PredefinedPool.wstETH);
    }

    function depositeEth(uint256 _amount, uint256 _boostAmount) external {
        IERC20(eETH).safeTransferFrom(
            msg.sender,
            address(this),
            _amount
        );

        _depositPredefinedAsset(_amount, _amount, _boostAmount, PredefinedPool.weETH);
    }

    function _depositPredefinedAsset(uint256 _amount, uint256 _initalAmount, uint256 _boostAmount, PredefinedPool _predefinedPool) internal {

        uint256 _finalAmount;

        if (_predefinedPool == PredefinedPool.sDAI) {
            _finalAmount = _daiTOsDai(_amount);
        } else if (_predefinedPool == PredefinedPool.wstETH) {
            _finalAmount = _stEthTOwstEth(_amount);
        } else if (_predefinedPool == PredefinedPool.weETH) {
            _finalAmount = _eethTOweEth(_amount);
        } else {
            revert InvalidDeposit();
        }

        // adjust boostAmount for the new asset
        _boostAmount = _boostAmount * _finalAmount / _initalAmount;

        _deposit(typeToId[_predefinedPool], _finalAmount, _boostAmount);
    }

    function _ethTOstEth(uint256 _amount) internal returns (uint256) {
        // submit function does not return exact amount of stETH so we need to check balances
        uint256 balanceBefore = IERC20(stETH).balanceOf(address(this));
        IstETH(stETH).submit{value: _amount}(address(this));
        return (IERC20(stETH).balanceOf(address(this)) - balanceBefore);
    }

    function _stEthTOwstEth(uint256 _amount) internal returns (uint256) {
        // wrap returns exact amount of wstETH
        return IwstETH(wstETH).wrap(_amount);
    }

    function _ethTOeEth(uint256 _amount) internal returns (uint256) {
        // deposit returns exact amount of eETH
@>>        return IeETHLiquidityPool(eETHLiquidityPool).deposit{value: _amount}(address(this));
    }

Impact

Code Snippet

https://github.com/sherlock-audit/2024-05-sophon/blob/main/farming-contracts/contracts/farm/SophonFarming.sol#L832-L836

Tool used

Manual Review

Recommendation


    function _ethTOeEth(uint256 _amount) internal returns (uint256) {
          // deposit returns exact amount of eETH
+         uint256 balanceBefore = IERC20(eETH).balanceOf(address(this));
+         IeETHLiquidityPool(eETHLiquidityPool).deposit{value: _amount}(address(this));
+         return (IERC20(eETH).balanceOf(address(this)) - balanceBefore);
    }

Duplicate of #4

sherlock-admin2 commented 4 months ago

1 comment(s) were left on this issue during the judging contest.

0xmystery commented:

valid because it's the shares that matter

sherlock-admin2 commented 4 months ago

The protocol team fixed this issue in the following PRs/commits: https://github.com/sophon-org/farming-contracts/commit/73adb6759b899e1a192fb5e28a5cd6202b5c3ff2

sherlock-admin2 commented 4 months ago

The Lead Senior Watson signed off on the fix.