Rock Paper Scissors

First Flight #38
Beginner FriendlySolidity
100 EXP
View results
Submission Details
Severity: high
Valid

Unchecked transfer in `joinGameWithToken` causing games to start without properly transferring tokens from the player

Summary

The joinGameWithToken function performs an unsafe ERC20 token transfer that does not validate the success of the operation. This could allow games to start without properly transferring tokens from the player, leading to inconsistent protocol states and potential loss of funds.

Vulnerability Details

Affected Code:

function joinGameWithToken(uint256 _gameId) external {
// ...validations...
winningToken.transferFrom(msg.sender, address(this), 1); // No success check
game.playerB = msg.sender; // State updated even if transfer failed
}

Root Cause:
The transferFrom function returns a boolean indicating success, but this value is never checked. If the token transfer fails (e.g., insufficient allowance/balance), the function:

  1. Proceeds as if the transfer succeeded

  2. Updates the game state (playerB)

  3. Allows the game to start with invalid token custody

Impact

Severity: High
Likelihood: Medium (Depends on token implementation)
Consequences:

  • Games starting without token collateral

  • Players participating without staking tokens

  • Protocol accounting inconsistencies

Tools Used

  1. Manual Review: Identified unchecked transferFrom call

  2. Slither: Flagged unchecked return value (Detector ID: unchecked-transfer)

Recommendations

Add explicit success checks for token transfers:

function joinGameWithToken(uint256 _gameId) external {
// ...validations...
bool success = winningToken.transferFrom(msg.sender, address(this), 1);
require(success, "Token transfer failed"); // Critical check
game.playerB = msg.sender; // Safe state update
}
Updates

Appeal created

m3dython Lead Judge about 1 month ago
Submission Judgement Published
Validated
Assigned finding tags:

Game Staking Inconsistency

joinGameWithEth function lacks a check to verify the game was created with ETH

Support

FAQs

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