sherlock-audit / 2024-06-magicsea-judging

8 stars 5 forks source link

zarkk01 - A malicious user can execute a Denial of Service (DoS) attack on the registration of legitimate ```BribeRewarder``` contracts in the ```Voter``` contract by registering 5 worthless ```BribeRewarder``` contracts in each ```VotingPeriod```. #670

Closed sherlock-admin3 closed 3 months ago

sherlock-admin3 commented 3 months ago

zarkk01

High

A malicious user can execute a Denial of Service (DoS) attack on the registration of legitimate BribeRewarder contracts in the Voter contract by registering 5 worthless BribeRewarder contracts in each VotingPeriod.

Summary

A malicious user can execute a Denial of Service (DoS) attack on the registration of legitimate BribeRewarder contracts in the Voter contract by registering 5 worthless BribeRewarder contracts in each VotingPeriod.

Vulnerability Detail

When a user wants to create a BribeRewarder, they must call the bribe function in the BribeRewarder contract and specify the VotingPeriod for the bribe activation. However, the Voter contract checks if the number of registered BribeRewarder contracts for the specified period is not above 5. If this limit is reached, no further BribeRewarder can be registered for that VotingPeriod. This limitation allows a malicious user to create and register worthless BribeRewarder contracts that distribute negligible amounts (e.g., 1 wei of ETH) to voters, thereby blocking the registration of legitimate BribeRewarder contracts. The relevant check during registration is shown below:

    function _bribe(uint256 startId, uint256 lastId, uint256 amountPerPeriod) internal {
        _checkAlreadyInitialized();
        if (lastId < startId) revert BribeRewarder__WrongEndId();
@>        if (amountPerPeriod == 0) revert BribeRewarder__ZeroReward();

        IVoter voter = IVoter(_caller);

        // ...
    }

By exploiting this check, a malicious user can create numerous BribeRewarder contracts that distribute trivial amounts, effectively preventing the registration of legitimate BribeRewarder contracts.

Impact

This vulnerability allows a malicious user to completely disrupt the Bribes system, making it impossible for legitimate BribeRewarder contracts to be registered and function as intended. The attack can be executed at minimal cost (e.g., 5 wei for each pair for each VotingPeriod), causing significant disruption to the voting and bribe distribution processes.

Code Snippet

https://github.com/sherlock-audit/2024-06-magicsea/blob/main/magicsea-staking/src/Voter.sol#L141

Tool used

Manual Review

Recommendation

To mitigate this vulnerability, consider implementing a minimum reward threshold that a BribeRewarder must meet before being accepted. This will ensure that only BribeRewarder contracts distributing meaningful rewards can be registered, preventing the registration of worthless BribeRewarder contracts.

    function _bribe(uint256 startId, uint256 lastId, uint256 amountPerPeriod) internal {
        _checkAlreadyInitialized();
        if (lastId < startId) revert BribeRewarder__WrongEndId();
        if (amountPerPeriod == 0) revert BribeRewarder__ZeroReward();
+       if (amountPerPeriod < MINIMUM_REWARD) revert BribeRewarder__InsufficientReward();

        IVoter voter = IVoter(_caller);

        // ...
    }

Define MINIMUM_REWARD based on the desired minimum amount to ensure the effectiveness of bribe distribution.

Duplicate of #190