claimSnowman()
is static — it only includes the user address and amount. This allows re-use of a previously signed message, leading to replay attacks if other checks (like nonce or timestamp) aren't added.A user signs an EIP-712 message and submits it on-chain to claim their Snowman NFT.
Since the hash doesn't include a nonce or unique identifier, a malicious actor can reuse the signed message on another chain, deployment, or after cloning wallets. The logic assumes a single claim will stop replays, but it doesn't account for external factors or signature leaks.
Likelihood:
Anyone who captures a valid signature can reuse it later (e.g., from logs, frontend memory, phishing).
Replayable across testnets, forks, and other contracts using same logic.
Impact:
NFT claimed multiple times.
Undeserved mints or DoS to legitimate claims.
Vulnerability persists even if hasClaimed
is updated, as signature itself remains valid without expiration or nonce.
The claim function of the Snowman Airdrop contract doesn't check that a recipient has already claimed a Snowman. This poses no significant risk as is as farming period must have been long concluded before snapshot, creation of merkle script, and finally claiming.
The contest is live. Earn rewards by submitting a finding.
This is your time to appeal against judgements on your submissions.
View preliminary resultsAppeals are being carefully reviewed by our judges.
The contest is complete and the rewards are being distributed.