code-423n4 / 2024-03-abracadabra-money-findings

9 stars 7 forks source link

No access control on init() in BlastCauldronV4 contract #216

Closed c4-bot-4 closed 5 months ago

c4-bot-4 commented 6 months ago

Lines of code

https://github.com/code-423n4/2024-03-abracadabra-money/blob/main/src/blast/BlastWrappers.sol#L59

Vulnerability details

Impact

The BlastCauldronV4.init() function initializes the contract after deployment, However there is no access control for the public function, making any user to be able to initialize the contract with arbitrary input to set the state variables for collateral, oracle, oracleData, accrueInfo.INTEREST_PER_SECOND, LIQUIDATION_MULTIPLIER, COLLATERIZATION_RATE, BORROW_OPENING_FEE

Additionally, the function can be front-runned since there is no access control.

Proof of Concept

A direct or frontrunned call to https://github.com/code-423n4/2024-03-abracadabra-money/blob/main/src/blast/BlastWrappers.sol#L59-L72

function init(bytes calldata data) public payable override {
        if (_governor == address(this)) {
            revert ErrInvalidGovernorAddress();
        }

        _setupBlacklist();

        super.init(data);
        BlastYields.configureDefaultClaimables(_governor);
    }

    function _setupBlacklist() private {
        blacklistedCallees[address(BlastYields.BLAST_YIELD_PRECOMPILE)] = true;
    }

BlastCauldronV4.init() would set the collateral, oracle, oracleData, accrueInfo.INTEREST_PER_SECOND, LIQUIDATION_MULTIPLIER, COLLATERIZATION_RATE, BORROW_OPENING_FEE state variables in

https://github.com/code-423n4/2024-03-abracadabra-money/blob/1f4693fdbf33e9ad28132643e2d6f7635834c6c6/src/cauldrons/CauldronV4.sol#L137-L152

 require(address(collateral) == address(0), "Cauldron: already initialized");
        (collateral, oracle, oracleData, accrueInfo.INTEREST_PER_SECOND, LIQUIDATION_MULTIPLIER, COLLATERIZATION_RATE, BORROW_OPENING_FEE) = abi.decode(data, (IERC20, IOracle, bytes, uint64, uint256, uint256, uint256));
        borrowLimit = BorrowCap(type(uint128).max, type(uint128).max);
        require(address(collateral) != address(0), "Cauldron: bad pair");

        magicInternetMoney.approve(address(bentoBox), type(uint256).max);

        blacklistedCallees[address(bentoBox)] = true;
        blacklistedCallees[address(this)] = true;
        blacklistedCallees[Owned(address(bentoBox)).owner()] = true;

        (, exchangeRate) = oracle.get(oracleData);

Tools Used

Manual Review

Recommended Mitigation Steps

  1. Apply access controls to functions that should be called by authorized entities.
  2. Contract can also be initialized during deployment if access control is not considered.

Assessed type

Access Control

0xm3rlin commented 6 months ago

init is called with BoringFactory, this is a no factor

c4-pre-sort commented 6 months ago

141345 marked the issue as primary issue

c4-pre-sort commented 6 months ago

141345 marked the issue as sufficient quality report

0xCalibur commented 6 months ago

no factor

c4-sponsor commented 5 months ago

0xCalibur (sponsor) disputed

thereksfour commented 5 months ago

Invalid, relies on admin error, i.e. admin does not initialize it on deployment

c4-judge commented 5 months ago

thereksfour marked the issue as unsatisfactory: Invalid