GivingThanks

First Flight #28
Beginner FriendlyFoundry
100 EXP
View results
Submission Details
Severity: low
Valid

Zero Donation Allowed in GivingThanks.sol

Summary

The donate function in GivingThanks.sol allows any caller to mint an NFT without donating any ETH. This is due to the absence of a minimum donation amount requirement. As a result, users can mint NFTs by donating 0 ETH, circumventing the intended charitable donation functionality and potentially undermining the integrity of the platform.

Vulnerability Details

Function: donate(address charity)

In the current implementation of the donate function, any caller can mint an NFT without actually contributing funds to a verified charity. This occurs because there is no minimum amount of ETH (msg.value) enforced within the function. The relevant code is as follows:

// Minting the NFT
_mint(msg.sender, tokenCounter);
// Creating and setting the token URI
string memory uri = _createTokenURI(msg.sender, block.timestamp, msg.value);
_setTokenURI(tokenCounter, uri);
tokenCounter += 1

Issue Analysis:

  1. Lack of Minimum Donation Requirement: The donate function does not include a check to ensure msg.value > 0. This allows any caller to send 0 ETH and still proceed through the function, effectively donating no funds while still receiving an NFT.

  2. Minting NFT Without Donation: The _mint function is called after a successful charity.call{value: msg.value}(""), even if msg.value is 0. The absence of a minimum donation requirement enables a malicious user to exploit the system by minting NFTs at no cost, diminishing the intended charitable purpose of the function.

Impact

  • Unauthorized NFT Minting: Users can mint NFTs without contributing to a charity, resulting in a potential flood of illegitimate NFTs that do not represent genuine charitable contributions.

  • Loss of Charitable Funds: Verified charities do not receive the intended donations, leading to an unfulfilled primary goal of the contract.

  • Reputational Damage: The absence of a donation requirement undermines the credibility of the project and the contract’s intended charitable purpose.

This vulnerability, therefore, escalates to a critical severity as it directly enables users to bypass the fundamental function of the platform.

Tools Used

Manual code review.

Recommendations

Add a Minimum Donation Requirement: Modify the donate function to enforce a minimum ETH donation threshold. This ensures users cannot mint NFTs without contributing a minimum amount to a verified charity.

Define a Minimum Donation Amount: Set a MIN_DONATION_AMOUNT constant to the minimum ETH required for an NFT to be minted, e.g., 0.01 ether.

  • Enforce Minimum Donation in donate Function: Use require to check msg.value against MIN_DONATION_AMOUNT before proceeding with the transaction.

Add a check to validate msg.value before allowing the transaction to proceed:

uint256 constant MIN_DONATION_AMOUNT = 0.01 ether; // Set a minimum donation threshold
function donate(address charity) public payable {
require(msg.value >= MIN_DONATION_AMOUNT, "Donation must be at least the minimum amount");
require(registry.isVerified(charity), "Charity not verified");
(bool sent, ) = charity.call{value: msg.value}("");
require(sent, "Failed to send Ether");
_mint(msg.sender, tokenCounter);
string memory uri = _createTokenURI(msg.sender, block.timestamp, msg.value);
_setTokenURI(tokenCounter, uri);
tokenCounter += 1;
}
Updates

Lead Judging Commences

n0kto Lead Judge 12 months ago
Submission Judgement Published
Validated
Assigned finding tags:

finding-0-donation-mint-an-NFT

Likelyhood: Low, anyone can mint an NFT with 0 amount. No reason to do it. Impact: Informational/Very Low, NFT are minted to a false donator. An NFT with 0 in the amount section would be useless. Since that's a bad design and not expected, I'll consider it Low but in a real contest, it could be informational because there is no real impact.

Support

FAQs

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