What is Permit2 and why does every dApp use it now
Permit2 is a smart contract Uniswap deployed in late 2022 at address 0x000000000022D473030F116dDEE9F6B43aC78BA3. Its job is to act as a single token-approval router for the entire Ethereum, Base, Arbitrum, Optimism, Polygon, and BNB ecosystems. Instead of every dApp asking the user to approve each ERC-20 token separately, Permit2 lets the user approve once, then any dApp can request a Permit2 signature that names a specific spender, amount, and deadline. Approving Permit2 itself is a normal on-chain transaction. Using Permit2 from then on is an off-chain signature.
The design solved a real problem. Token approvals used to require a gas-paying transaction for every new dApp the user wanted to use, which made user onboarding slow and expensive. Permit2 reduced that to one approval-of-Permit2 transaction plus cheap off-chain signatures forever after. Uniswap, 1inch, CoW Swap, ParaSwap, Matcha, and dozens of other major DeFi protocols adopted Permit2 within months. By 2024 it was the standard. By 2026 essentially every active wallet has approved Permit2 for at least USDC, USDT, WETH, and any token the user has swapped on a Permit2-enabled router.
That universal approval is exactly what attackers exploit.
What Permit2 actually signs
When a legitimate dApp asks for a Permit2 signature, the wallet shows a typed-data message that looks roughly like this:
PermitSingle { details: { token: 0xA0b8..., amount: 1000000000, expiration: 1716000000, nonce: 5 }, spender: 0x6A00..., sigDeadline: 1715900000 }
The user is signing a permission slip. The slip says: "I authorize the address at spender to move up to amount of token from my wallet, until expiration." If the user signs this, the spender contract gains the right to call permitTransferFrom any time before expiration and pull amount of the token out of the user's wallet. No further user interaction required.
For a real swap on Uniswap, this is fine. The spender is Uniswap's UniversalRouter at a publicly audited address. The amount matches the user's intended swap. The expiration is usually 30 days. The signature is consumed by the swap and the permission burns out as soon as the swap completes. Safe.
For a phishing site, every one of those fields is weaponized.
How the attacker constructs a malicious Permit2 signature
The drainer page generates a PermitSingle or PermitBatch payload with three modifications.
Modification 1: spender is the attacker. Instead of Uniswap's UniversalRouter, the spender field contains an EOA or contract controlled by the attacker. Once the user signs, that address can transfer the user's tokens at will.
Modification 2: amount is unlimited. Instead of the exact amount the user intends to swap, the field contains 2^160 - 1, which is the maximum value Permit2 supports. That number is so large it covers the user's entire wallet balance of that token and any future deposits.
Modification 3: expiration is far future. Instead of a 30-minute or 30-day window, the expiration is set to a value years or decades in the future. The signature stays valid forever in practical terms. The attacker can sit on it for weeks or months before executing.
The drainer page often uses PermitBatch to chain dozens of token permissions into a single signature. One signature gives the attacker permission to drain USDC, USDT, WETH, WBTC, LINK, AAVE, UNI, and any other ERC-20 the user holds, all at the same time.
Why this looks safe in the wallet UI
Wallet UIs distinguish between transactions and signatures. A transaction requires gas, a confirmation slider, and a clear "you are sending X to Y" message. A signature does not require gas. The popup is smaller. The wording is often "Sign this message to continue" or "Approve to proceed." Many wallets show only the contract name and a generic "permit" label, hiding the actual amount and spender behind a "View full details" link that most users do not click.
This UX asymmetry is the attack's leverage. The user is trained to read transactions carefully because gas costs and on-chain finality make the consequences obvious. The user is trained to dismiss signatures quickly because most signatures are cheap, casual confirmations like "sign in with wallet" or "agree to terms of service." A Permit2 signature looks like the second category but has the financial consequences of the first.
MetaMask, Rabby, Phantom, Rainbow, and other major wallets have all added signature simulation features that try to surface the financial impact of a typed-data message before the user signs. These simulators help. They are not perfect. A drainer payload that uses uncommon function selectors or unusual encoding can bypass simulation and render a generic "Permit signature" warning that the user interprets as harmless.
The waiting attack: why drainers do not pull funds immediately
Naive crypto scams drain wallets in the same block the user signs. The wallet shows a balance change within minutes. The user immediately notices, alerts their security circle, and word spreads. The same drainer URL gets reported, blocked, and burned within hours.
Permit2 changes this. A signature is just data the attacker holds. There is no on-chain footprint until the attacker executes permitTransferFrom. Sophisticated drainers wait days or weeks before pulling the trigger. By the time the user notices the drain, they have already forgotten the page that asked for the signature. The on-chain history shows their own wallet as the authorizing signer, with no obvious link back to the phishing source. Recovery becomes essentially impossible because the user cannot prove which interaction caused the loss.
Some drainer operations also batch-execute across hundreds of compromised wallets in a single multicall transaction, which obfuscates the attribution further. The attacker pulls $5 million from 800 wallets in one block, then disperses across mixers within the next ten blocks. By the time monitoring firms are tagging the addresses, the funds are already in their second or third hop.
How to revoke a Permit2 signature before the attacker executes
If you signed something on a suspicious page and the funds have not moved yet, there is a window to revoke. The window is measured in days or weeks for a far-future expiration. Act fast.
The cleanest tool is revoke.cash, which is a community-maintained dashboard that lists every active token approval and Permit2 allowance for a connected wallet. Connect your wallet (read-only is fine for the listing step), find the suspicious approval, and click revoke. Revoking is an on-chain transaction that costs gas, usually $1 to $5 depending on the chain. It is cheap insurance compared to the alternative.
For Permit2 specifically, look at the section labeled "Permit2 allowances." Each row shows a token, a spender address, an amount, and an expiration. Sort by expiration descending and look for any row with a far-future date (years out) combined with an unlimited amount. Those are the dangerous ones. Revoke them first.
If you signed a PermitBatch that covers multiple tokens, every token in the batch needs to be revoked separately. revoke.cash will show each token as its own row. Click through all of them.
If you cannot reach revoke.cash for some reason, you can also revoke directly by calling permit on the Permit2 contract with the same spender but an amount of zero and an expiration in the past. The Etherscan UI at etherscan.io/address/0x000000000022D473030F116dDEE9F6B43aC78BA3 exposes the approve function directly. This requires comfort with raw contract interaction.
How to recognize a malicious Permit2 request in your wallet popup
- The spender address is not a known router. Uniswap UniversalRouter is at
0x66a9893cC07D91D95644AEDD05D03f95e1dBA8Afon Ethereum. 1inch router is at0x1111111254EEB25477B68fb85Ed929f73A960582. CoW Settlement is at0x9008D19f58AAbD9eD0D60971565AA8510560ab41. If the spender does not match a known protocol address, treat it as malicious. - The amount is unusually large. A real Permit2 signature for a $100 swap usually specifies an amount close to $100 worth of tokens, not the entire balance and not
2^160 - 1. If you see a number with many leading 9s or scientific notation in the millions or higher, that is a drainer. - The expiration is far in the future. Legitimate swap signatures expire within minutes to hours. Permit2 router signatures expire within 30 days at most. An expiration set to 2030 or beyond is a drainer.
- The token list does not match what you are swapping. If you are swapping ETH for USDC and the Permit2 signature lists USDC, USDT, WETH, WBTC, and LINK, the page is harvesting permissions for tokens you did not consent to spend.
- The page asks you to sign without any visible swap UI. Legitimate DEX flows always show you the swap details first. If a page is asking for a signature before showing what you are about to do on-chain, the signature itself is the entire interaction. That is the attack.
The wallets that handle Permit2 safely (and the ones that do not)
Rabby Wallet has the best Permit2 signature simulation as of 2026. It explicitly highlights the spender address, compares it against a known-protocols list, and warns the user if the spender is unrecognized. The amount field is displayed in human-readable units rather than raw bigint. The expiration is shown as a date, not a Unix timestamp. Sign requests from suspicious spenders are rendered with a red banner.
MetaMask added Permit2 simulation in 2024 and improved it through 2025. The current version shows the spender address, the token, and an approximate USD value of the amount. It does not yet auto-flag unknown spenders, so users still have to recognize that 0xa1b2c3... is not a Uniswap or 1inch address. The blockaid.io security alerts plug into MetaMask and catch most known drainer addresses.
Phantom on Solana does not use Permit2 because Solana has a different token approval model. But Phantom's analog vulnerability is the SystemProgram.transfer blind sign, which presents the same trust pattern: a signature that moves funds, rendered in a small popup that the user is trained to dismiss quickly. Phantom added transaction simulation in 2024 that shows the destination address and amount, which catches most basic Solana drainers but not the more sophisticated ones using PDA derivation tricks.
Coinbase Wallet and Trust Wallet have improved their signature simulation but still trail Rabby on Permit2 specifically. Hardware wallets like Ledger and Trezor route the signature through their device screen, which is the best defense because the device screen cannot be spoofed by the dApp UI. The downside is that Ledger and Trezor screens are small and the typed-data display is truncated, so users often see a partial signature and assume the rest is fine.
How SafeBrowz detects Permit2 drainer pages
The SafeBrowz extension catches Permit2 drainer pages on three layers before the wallet popup even appears.
The local layer checks the URL pattern. Domains containing brand keywords like uniswap, 1inch, matcha, cowswap, paraswap, kyber on TLDs that are not the brand's official root (uniswap.org, 1inch.io, etc.) are flagged. A page on uniswap-claim.xyz or swap-uniswap.app never reaches the wallet popup.
The AI layer scans page content for the Permit2 invocation signature. When the page imports @uniswap/permit2-sdk or its derivatives, calls signTypedData with a PermitSingle or PermitBatch structure, and the spender field is set programmatically rather than from a known router list, the page is flagged as a likely drainer. The AI also looks at the on-page text. Pages that say "approve to claim airdrop" or "verify wallet to continue" while preparing a Permit2 request are flagged regardless of brand.
For Premium users, the JavaScript signature scanner catches the specific drainer libraries used to construct Permit2 payloads. Inferno Drainer, Angel Drainer, Pink Drainer, MS Drainer, and Atomic Drainer each have signature patterns in their Permit2 payload construction code. SafeBrowz Premium recognizes those signatures and shows a full-screen warning before the page can build the request.
The same detection is available as an API at api.safebrowz.com/v1/detect, so wallet apps that want to pre-check a URL before triggering the signature flow can integrate at 0.001 USDC per call via x402 on Solana or Base. Enterprise Bearer keys are available for wallet apps serving high-volume integrations.
What dApp builders should do
If you are building a DEX, an aggregator, or any dApp that uses Permit2, the cleanest practice is to bound the amount and expiration tightly. Sign for exactly the swap amount, not the unlimited max. Set expiration to the swap deadline, typically 5 to 30 minutes, not 30 days. These choices cost nothing technically and remove the long-tail liability of leaked signatures.
For the spender field, prefer the official router contract address as a constant, not a value passed in via dApp config. A misconfigured config that lets a Permit2 spender be set via URL parameter is a recipe for the next drainer to use your dApp as a delivery vehicle.
Add a "Show full signature details" button in your sign-in flow that exposes the spender, amount, and expiration in plain English before the user reaches the wallet popup. Educate users by name about Permit2 instead of hiding the mechanic behind a generic "approve" button. The pages that explain Permit2 transparently tend to also be the pages that real users learn to trust.
The bigger picture: signatures are the new transactions
For the first decade of Ethereum, the standard threat model treated transactions as the dangerous primitive and signatures as the safe one. Signatures cost no gas, did not appear on-chain, and were generally used for off-chain logins. That model is obsolete. EIP-712 typed-data signatures, Permit, Permit2, ERC-2612, and EIP-7702 delegations have all made signatures into commitments with full financial weight. The wallet UI has not caught up. The user training has not caught up. Drainer crews have caught up perfectly.
Going forward, the rule for crypto users is: treat every signature request the same way you treat a transaction request. Read the typed-data payload. Check the spender. Check the amount. Check the expiration. If anything is unclear, reject and verify on the protocol's official channel. The signature is the transaction now. The transaction simulator is your screen, your patience, and your willingness to walk away from a page when something does not add up.
Block Permit2 drainer pages before you sign
SafeBrowz is a free browser extension for Chrome, Firefox, and Edge that detects Permit2 drainer construction in real time and blocks fake DEX, fake airdrop, and fake claim pages before the signature popup appears. Premium adds wallet drainer JavaScript signature detection for the major drainer libraries (Inferno, Pink, Angel, MS, Atomic) at $14.99 per year. The core protection is free forever.