Skip to content
EIP-7702 drain replay

A valid signature is not an approved action.

Since EIP-7702, one signature can turn a wallet into a contract that empties itself. Binonce replays these drains on a real chain, starting with the largest so far: Binance, 29 October 2026. Watch each step, and see what stops it.

Real contracts and transactions on local anvil or Sepolia · test tokens only

The largest case: Binance, 29 Oct 2026other cases
$0.0B

left Binance hot wallets across about ten chains.

~0 min
for most of it to leave
$0.0B
from one wallet, in a single transaction
0
authorizations signed, 1 landed
0
approvals asked of the owner
live… delegate contracts in the public Blacklist on Arkiv

Sources: Blockaid, Fireblocks, TRM Labs, TechFlow. Figures vary slightly between them.

Cases

Binance was the biggest. It wasn’t the first.

EIP-7702 went live with Ethereum’s Pectra upgrade in May 2025. Since then wallets have been drained in two ways: with a leaked key and a sweeper contract, or by tricking the owner into signing a malicious batch. Binonce replays the first, because that is what happened to Binance.

Leaked key + sweeper. Someone has the key, delegates the wallet to a drainer contract, and calls it.
Phishing batch. The owner is tricked into signing one batch that hides the transfers.
  1. May 2025
    80%+

    Sweeper bots move in within weeks of Pectra

    Wintermute found that over 80% of EIP-7702 delegations pointed to copy-pasted versions of the same sweeper code, which it named CrimeEnjoyor: bots that delegate wallets with leaked keys and drain any ETH that arrives.

    Leaked key + sweeperReplayed in BinonceWintermute via The Block, Jun 2025
  2. 24 May 2025
    ~$146K

    A phishing batch through a delegated wallet

    A user whose wallet was already upgraded with EIP-7702 signed what looked like one action. It was a batch that moved their memecoins out in a single transaction. Scam Sniffer linked it to Inferno Drainer.

    Phishing batchDifferent pathScam Sniffer via Cryptorank
  3. Aug 2025
    ~$1M

    A fake Uniswap swap

    An investor signed a batch dressed up as Uniswap swaps. Five tokens left their wallet in one EIP-7702 transaction.

    Phishing batchDifferent pathScam Sniffer via CryptoSlate, Aug 2025
  4. 29 Oct 2026
    $6.3B

    Binance hot wallets

    One leaked key, 50 authorizations in one transaction, and Binance 14 became a sweeper. The pattern spread across about ten chains in twenty minutes.

    Leaked key + sweeperReplayed in BinonceThe four moments

Amounts are as reported by the linked sources and vary between outlets.

Binance · 29 October 2026

The biggest case, in four moments.

Fifty authorizations in one transaction

The attacker broadcasts a single type-4 transaction carrying 50 EIP-7702 authorizations, all signed with the key of Binance 14, one of the exchange’s largest Ethereum hot wallets, for nonces 18,914,775 to 18,914,824.

Sources: Blockaid, Fireblocks, TRM Labs, TechFlow. Figures vary slightly between them.Binance 14 on Etherscan

How the drain works

Four steps from a leaked key to an empty wallet.

EIP-7702 lets an ordinary account temporarily run a contract’s code. With the account’s key, an attacker can point it at a contract that sends everything away. Four steps, and the replay runs every one of them on-chain.

  1. 01 · Sign

    The stolen key signs 50 authorizations.

    Each one says “let this account run the sweeper’s code,” at consecutive nonces. These are only signatures: nothing touches the chain, no gas is spent, and no wallet shows a prompt.

  2. 02 · Broadcast

    A relayer sends them in one transaction.

    All 50 ride in a single type-4 transaction. The relayer pays the gas. The wallet’s owner never approves anything, because nothing asks them to.

  3. 03 · Hijack

    One authorization lands, and the wallet becomes the sweeper.

    Only the authorization at the account’s current nonce takes effect. The other 49 are spares in case the nonce moves. The wallet’s code is now 0xef0100 followed by the sweeper’s address, so it runs the attacker’s contract as its own.

  4. 04 · Drain

    One call empties it.

    The relayer calls the sweeper through the hijacked wallet. The contract reads its own balance and sends all of it to a hardcoded address, in a single on-chain call.

Why sign 50?

An authorization only works at the wallet’s exact current nonce. The wallet keeps sending its own transactions, so the attacker can’t know which nonce it will be at. Drag to move it.

The wallet didn’t move. Authorization n lands, the first one. In the replay this is what happens.

Read the 23 bytes

Ask any node for an account’s code with eth_getCode. A delegated account returns exactly this shape. Hover the bytes, or paste your own result.

ef01005fbdb2315678afecb367f032d93f642f64180aa3
Delegated. This account now runs the code at 0x5fbdb2315678afecb367f032d93f642f64180aa3.
Inside the replay

What the owner sees, next to what the chain records.

The replay page puts the two side by side. The wallet stays calm until the money is gone; the trace shows every signature, transaction and block as it happens.

What the owner sees
Balance
2,500,000.00 tUSD

A funded hot wallet. Nothing to see.

What the chain records
  1. 01Victim balance before attack: 2,500,000 tUSD

In the live replay each line links to its transaction and block.

Defense

A key alone should not be enough to move money.

Spotting a bad signature doesn’t work, because a forged one looks exactly like a real one. The fix is to stop treating a signature as permission. Binonce frames that as three layers around the same wallet.

Same stolen key, two places to keep the money
  1. 01Attacker signs with the stolen keySignatures are valid
  2. 027702 delegation landsWallet code becomes the sweeper
  3. 03Call to move the fundsExecutes: nothing checks the caller
  4. 04Balance afterwards0 · everything went to the attacker
  1. Keeps the door shut

    The Lock

    with Chainwall

    Treasury funds sit in a governed vault instead of a bare key. Money moves only through interactions the policy already approved, so a stolen signature has nothing it is allowed to do.

    The walkthrough UI is built; its on-chain run is being rewired. The engine checks every signer first. If the signer’s account has become delegated code, the call reverts with ActorDelegated before any signature is even looked at.

  2. Knows who the thieves are

    The Blacklist

    with Arkiv

    Every sweeper the replay uses, plus delegate contracts scanned from Ethereum mainnet, goes into a public, wallet-signed registry. Anyone can query it without asking us.

    Labels come from bytecode and reuse heuristics, recorded with their evidence. Nothing is called a thief on a guess.

    Live on Arkiv testnetHow entries are labelled
  3. Spots the break-in

    The Alarm

    with Chainlink CRE

    A workflow that watches treasury keys for new 0xef0100 code, checks the delegate against the Blacklist, and raises an alert on-chain so the key gets rotated.

    Designed in the project docs; not built yet.

    Planned

The Lock runs on OKcontract’s Chainwall. Binonce built the attack replay, the Blacklist and the walkthroughs around it.

The Blacklist

A public list of contracts that drain wallets.

Every delegate contract Binonce sees goes to Arkiv, a database on its own chain. Entries are signed by our writer wallet and stamped with a block, anyone can read them without asking us, and a flag can only change through a public transaction. Labels come from fixed rules on the bytecode, not guesses.

Try the classifier
127
3
Labelsuspicious

105 bytes, not a proxy: too small for owner checks. Typically forwards the whole balance to one address.

confirmed-thief never comes from these rules. It is added by hand, with a published source.

query.ts
const { entities } = await pub
  .select({ $key: true, address: true, label: true, delegatorCount: true })
  .from(Delegate)            // schema "chainwall.delegate"
  .ownedBy("0x7264fB117ce777888B1bD2eF66ED0CF4CA14B4a9")
  .fetch();
Runs against the live registry with your own free Arkiv access key. The full script is in the README.
Writer wallet
0x7264fB…14B4a9
Network
Arkiv Rabdi · 7794095
Sources
Mainnet 7702 scan + every replay
License
Data CC0 · code MIT
Run it yourself

Run the drain on your own machine.

Each run tops the test wallet back up to 2,500,000 tUSD, so you can replay it as often as you like. Locally it runs in seconds; on Sepolia it waits for real blocks.

Terminal
  1. npm install# dependencies
  2. npm run chain# anvil on the Prague hardfork
  3. npm run setup# deploys the contracts, writes .env
  4. npm run dev# open /attack, press Launch attack

Needs Node 18+ and Foundry’s anvil. No faucet, no gas, no wallet.