Beatland Festival

First Flight #44
Beginner FriendlyFoundrySolidityNFT
100 EXP
View results
Submission Details
Impact: low
Likelihood: low
Invalid

No Recovery Mechanism for Mistakenly Sent Tokens or ETH

Root + Impact

Description

  • Normal Behavior:
    It is common for users or other contracts to mistakenly send ETH or non-BEAT ERC20 tokens to the BeatToken contract address. In well-designed contracts, the owner is able to recover such assets to prevent permanent loss.

    Issue:
    The BeatToken contract does not provide any function for the owner to recover ETH or tokens sent to the contract by mistake. As a result, any ETH or non-BEAT tokens sent to this contract are permanently locked and unrecoverable.

// No function exists to withdraw ETH or recover ERC20 tokens sent to this contract.

Risk

Likelihood:

  • While not frequent, it is a common user or integration mistake, especially for high-profile tokens.

Impact:

  • Funds sent by mistake are permanently lost, which can be significant for users or integrators.

Proof of Concept

If a user or contract mistakenly sends ETH or another ERC20 token to the BeatToken contract, there is no way for the owner to recover these funds:

// User sends ETH directly to the contract address
(bool sent, ) = address(beatToken).call{value: 1 ether}("");
require(sent, "ETH transfer failed");
// Or sends an ERC20 token
otherToken.transfer(address(beatToken), 1000);
// There is no way for the owner to recover these funds.

Recommended Mitigation

Add functions to allow the owner to recover ETH and any ERC20 tokens sent to the contract by mistake. This is a standard best practice for ERC20 contracts.

// Allow the owner to withdraw ETH
+ function recoverETH(address to) external onlyOwner {
+ require(to != address(0), "Cannot send to zero address");
+ payable(to).transfer(address(this).balance);
+ }
// Allow the owner to recover any ERC20 token
+ function recoverERC20(address token, address to, uint256 amount) external onlyOwner {
+ require(to != address(0), "Cannot send to zero address");
+ require(token != address(this), "Cannot recover BEAT tokens");
+ IERC20(token).transfer(to, amount);
+ }
Updates

Lead Judging Commences

inallhonesty Lead Judge 4 months ago
Submission Judgement Published
Invalidated
Reason: Non-acceptable severity

Support

FAQs

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