#37058 [SC-High] Theft of remuneration through claims processing loops.
Submitted on Nov 24th 2024 at 05:14:27 UTC by @innertia for Audit Comp | Celo
Report ID: #37058
Report Type: Smart Contract
Report severity: High
Target: https://github.com/celo-org/celo-monorepo/blob/release/core-contracts/12/packages/protocol/contracts-0.8/common/EpochManager.sol
Impacts:
Theft of unclaimed royalties
Description
Brief/Intro
In EpochManager, rewards are distributed by advancing the EpochProcess. However, if a group that has already received a reward loops through the process, it will be able to obtain as many rewards as it likes.
Vulnerability Details
In setToProcessGroups, rewards are assigned to the group corresponding to the electedAccounts.
processedGroups[group] = epochRewards == 0 ? type(uint256).max : epochRewards;https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L247
After that, rewards are distributed within the processGroup.
https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L288
At this point, processedGroups are deleted, but electedAccounts are not deleted.
https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L291
In other words, by starting setToProcessGroups again, rewards are assigned to the same groups corresponding to the electedAccounts again.
https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L236-L237
By repeating this, group can obtain as many rewards as they like. In the case of finishNextEpochProcess, where the same process is executed in batches, the electedAccounts are deleted each time the process is executed. This is not a problem.
https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L336-L337
This problem occurs because there is no such process in setToProcessGroups.
Impact Details
A selected group of people can receive unlimited rewards.
References
https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L247. https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L288. https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L291. https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L236-L237. https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts-0.8/common/EpochManager.sol#L336-L337.
Proof of Concept
First, as a preliminary preparation, modify the distributeEpochRewards of MockElection. In this mock, the value is simply assigned, but in the original function behaviour, the correct behaviour is to add. Therefore, modify it as follows.
https://github.com/celo-org/celo-monorepo/blob/4903cfa3744f4e03c5c042c3f881cc93d4807b21/packages/protocol/contracts/governance/test/MockElection.sol#L104-L106
With this modification, the existing test will not fail.
Now, we will begin the test of reward theft. As this is a repurposed version of an existing test, I have only written comments for the important parts. Please add the following contract to EpochManager.t.sol.
https://github.com/celo-org/celo-monorepo/blob/release/core-contracts/12/packages/protocol/test-sol/unit/common/EpochManager.t.sol
Last updated
Was this helpful?