DeFiHardhat
21,000 USDC
View results
Submission Details
Severity: low
Invalid

Incorrect Reporting of Bean Distribution to Silo in Reward Event

Summary

The Reward event in the rewardBeans function of the Sun contract inaccurately reports the amount of Beans distributed to the Silo. This is as a result of the newSupply variable being decremented during the distribution to Fertilizer and the Field before being used in the event to represent the amount given to the Silo.

Vulnerability Details

The rewardBeans distributes newly minted Beans among three components: Fertilizer, the Field, and the Silo. The function first mints new Beans, then conditionally distributes parts of these Beans to Fertilizer and the Field, decrementing the newSupply variable each time. The remaining Beans are then allocated to the Silo. However, the Reward event uses the decremented newSupply to report the amount sent to the Silo, leading to incorrect emmission.

Here's the sequence of operations and see how this affects the accuracy of the event data:

  1. Initial Minting:

    C.bean().mint(address(this), newSupply);

    The function starts by minting newSupply amount of Beans to the contract itself. At this point, newSupply represents the total number of new Beans created.

  2. Distribution to Fertilizer:

    if (s.season.fertilizing) {
    newFertilized = rewardToFertilizer(newSupply);
    newSupply = newSupply.sub(newFertilized);
    }

    If fertilizing is active, a portion of the Beans (newFertilized) is distributed to Fertilizer. The newSupply is then reduced by the amount given to Fertilizer. After this step, newSupply no longer represents the total Beans but the remaining Beans after Fertilizer's allocation.

  3. Distribution to the Field:

    if (s.f.harvestable < s.f.pods) {
    newHarvestable = rewardToHarvestable(newSupply);
    newSupply = newSupply.sub(newHarvestable);
    }

    Next, Beans are allocated to the Field (newHarvestable). Again, newSupply is reduced by the amount allocated to the Field. Now, newSupply represents the Beans left after allocations to both Fertilizer and the Field.

  4. Distribution to the Silo:

    rewardToSilo(newSupply);

    The remaining Beans (newSupply) are then given to the Silo. At this point, newSupply should ideally represent the exact amount of Beans sent to the Silo.

  5. Emitting the Event:

    emit Reward(s.season.current, newHarvestable, newSupply, newFertilized);

    The Reward event is emitted with newSupply as one of the parameters, intended to represent the Beans distributed to the Silo. However, the issue arises because newSupply is used in the event after it has been decremented twice (for Fertilizer and the Field). This means the value of newSupply in the event does not accurately reflect the initial amount intended for the Silo but rather the leftover after other distributions.

Impact

Impact is Low. Users reviewing transaction logs or contract events for auditing or tracking purposes will receive incorrect data about the amount of Beans distributed to the Silo. This could lead to confusion and misinterpretation of the contract's operational outcomes.

Tools Used

Manual review

Recommendations

Consider introducing a new variable that captures the amount of Beans allocated to the Silo before any modifications to newSupply. This variable should then be used in the Reward event to accurately reflect the distribution.

uint256 toSilo = newSupply; // Capture the amount before passing to rewardToSilo
rewardToSilo(toSilo);
emit Reward(s.season.current, newHarvestable, toSilo, newFertilized);
Updates

Lead Judging Commences

giovannidisiena Lead Judge about 1 year ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.