The _beforeSwap function tracks swap amounts and cooldowns using the sender parameter. However, in Uniswap V4's architecture, sender is the address that called PoolManager.swap(), which is typically a SwapRouter contract, NOT the end user.
Vulnerable Code (lines 171-172):
Call flow for typical swaps:
This means:
ALL users using the same SwapRouter share the same tracking limits
Individual per-user limits are completely bypassed
Bots can trivially bypass all limits by deploying their own router contracts
Complete bypass of anti-bot protection:
Shared Limits Problem:
Alice swaps 0.5% through SwapRouter
Bob swaps 0.6% through same SwapRouter
Bob gets PENALIZED even though his individual limit isn't hit
Because: Router's tracked amount (0.5%) + Bob's swap (0.6%) > 1% limit
Bot Bypass Attack:
Bot deploys custom router contracts (cheap via CREATE2)
Routes each swap through a fresh router address
Each router starts with 0 tracked amount
Bot can swap unlimited amounts with NO penalties
Severity: HIGH/CRITICAL
Complete bypass of the hook's core anti-bot functionality
Legitimate users unfairly penalized when sharing routers
Bots can trivially circumvent all protections
Option 1: Encode actual user in hookData
Option 2: Track by tx.origin (has other security tradeoffs)
Option 3: Require users to interact directly (poor UX)
The contest is live. Earn rewards by submitting a finding.
This is your time to appeal against judgements on your submissions.
Appeals are being carefully reviewed by our judges.
The contest is complete and the rewards are being distributed.