Normal behavior:
After the 90-day claim period has elapsed, the Pot should be closed once, where the manager takes a cut of the remaining rewards and the remainder is distributed, after which no further reward distribution should occur.
Issue:
The closePot() function does not update or lock the reward state after execution, allowing it to be called repeatedly and causing the same remaining rewards to be redistributed multiple times.
Likelihood:
Reason 1: Occurs every time closePot() is called after the 90-day claim period, as no state transition restricts repeated execution
Reason 2: Repeated calls reuse the same remainingRewards snapshot for reward calculation
Impact:
Impact 1: Rewards can be distributed multiple times, exceeding the intended totalRewards invariant
Impact 2: The contract’s token balance can be fully drained through repeated closePot() calls
Once the claim window has elapsed, calling closePot() performs reward distribution without modifying the remainingRewards state. Because no guard or state update exists, subsequent calls execute the same logic again using the same reward snapshot, causing repeated payouts.
This demonstrates that reward distribution is not a one-time operation, but can be executed an arbitrary number of times.
The contract should transition into a finalized state after closing the Pot. This can be achieved by either introducing an explicit closed flag or by updating remainingRewards to zero after the first execution, ensuring subsequent calls cannot redistribute rewards.
This ensures closePot() is idempotent and enforces the intended one-time reward distribution invariant.
The contest is live. Earn rewards by submitting a finding.
Submissions are being reviewed by our AI judge. Results will be available in a few minutes.
View all submissionsThe contest is complete and the rewards are being distributed.