At 20:20:59 UTC on October 29, a Binance hot wallet began executing code it had never run before. Three minutes and 24 seconds later, the wallet had been drained.
The drain was not a phishing success or a withdrawal-policy bypass. Attackers reached the component that produces signatures and asked it directly. The signing service answered.
The transaction moved 167,464 ETH, 1.62 billion USDT and dozens of other tokens to an address now tagged “Binance Hot Wallet Exploiter 2.”
The usual explanations do not fit. No private key was stolen. No withdrawal request was forged. No human approved a transfer. According to Binance’s November 3 initial findings, the attacker “exploited unauthorized access to an internal wallet signing service to initiate transactions outside the normal withdrawal process” and “submitted 50 signing transactions to manipulate the account nonce and establish malicious delegation authorizations.”
That is the whole finding. The control that failed was not custody, policy or human review. It was the trust boundary around the thing that signs.
In this article
Why this matters
Because the same failure is sitting in most organizations that sign anything.
The attacker did not steal a private key. They used a stolen deployment token to reach a service that was trusted to sign, and the service signed a message type it was never designed to evaluate. Replace “signing service” with payment API, CI/CD deploy token, OAuth token issuer, cloud IAM role, HSM, or approval bot, and the pattern repeats.
Most teams protect the key and the policy. Fewer protect the trust boundary around the signer. If the signer authenticates the caller by network position or a bearer token, and signs payloads it cannot classify, the policy above it is decorative.
The incident also exposes the response gap. Fifty signing requests in minutes should be an alert. A delegation installed on a treasury wallet should be treated like a withdrawal. Revocation should be a tested button, not a four-hour engineering project. If your runbook has never practised revoking a delegation or disabling a signing path, you will learn during the incident.
And the money is not the only cost. Roughly US$2.8 billion was frozen only because stablecoin issuers and a chain council could act. More than US$1 billion in native ETH was beyond any issuer’s reach. If your treasury holds assets on chains without a freeze mechanism, your recovery plan cannot depend on someone else’s blacklist.
This is a design review you can run this week: list every component that signs, ask what it authenticates, what it parses, what it can authorize, and whether revocation is pre-built.
The 50 signatures
A signing service that signs what it is given, without understanding what it is signing, is not a control. It is an oracle.
Binance’s own wording points at this. The attacker did not push a fraudulent withdrawal through the normal pipeline. They reached the signer and asked it to authorize a set of EIP-7702 delegation messages. The service produced 50 signatures in minutes. Whatever withdrawal policy existed lived above that layer, and the attacker walked around it.
Halborn’s reading is the simplest one that fits the facts: the signer either received raw digests it could not parse, or received typed requests without a rule set that treated a delegation authorization as a different kind of action from a transfer. Binance has not said which. That distinction decides whether the fix is a parser or a policy engine.
The road in
The campaign did not begin on October 29. It began in June, with a developer.
Engineer A searched for a popular AI coding tool, found a tampered Homebrew installation and ran it. Binance detected the anomaly, replaced the device and rotated every related credential. The response was correct. It also did not end the campaign. The attacker left with Engineer A’s role and the names of colleagues on the wallet infrastructure team.
In September, Engineer B was approached on a legitimate job platform by a supposed project director. A first-round video interview with an HR representative using a personal social account built trust. A second round in a chat app involved the CEO of a company that does not exist. The closing “assignment” was a code repository to download onto a work computer. The setup script replaced the pyenv shim under Homebrew with a malicious file of 3,414 bytes against an original 3,344 bytes, deleted the binary link, created a new one, and spawned a shell that phoned home. Every later pyenv invocation ran attacker code. Endpoint protection did not detect it, and the malware removed its own traces.
On October 20, from Engineer B’s machine, the attacker used an internal AI tool to take control of Engineer A and a third wallet engineer, C. On Engineer A’s computer the attacker found a container deployment token. Binance has since rebuilt the internal AI tool with new access controls, but it has not said what the tool was or how it granted that reach.
On October 29, the attacker logged onto Engineer C’s computer, used Engineer A’s token to deploy a container, and triggered a script from inside it. The script talked to the internal wallet signing service. The first XRP left at 20:05 UTC.
Why EIP-7702 made it worse
EIP-7702 lets an externally owned account set code by attaching authorization tuples formatted as [chain_id, address, nonce, y_parity, r, s]. For each tuple, a delegation indicator 0xef0100 || address is written to the authorizing account’s code, and code-executing operations then load and execute the code pointed to by that delegation.
Two details matter operationally.
First, the authorization list is processed before the execution portion of the transaction begins. Second, if transaction execution fails, the processed delegation indicators are not rolled back. A failed transaction can still leave a delegation installed.
That is how a hot wallet becomes an attacker-controlled sweeper without a key ever leaving the building.
Revocation is defined by the same specification. If the address in the authorization tuple is the zero address, the delegation indicator is not written and the account’s code hash is reset to the empty code. Binance says that because Binance 14 uses multi-party computation there was no single private key with which to sign a revocation, and the team “developed and executed a specialized procedure” to produce the authorization to the zero address.
The asymmetry is the story. The attacker obtained 50 delegation signatures in minutes. The owner needed close to four hours to obtain one, because the tooling had never been built to sign anything but withdrawals. Halborn’s framing is blunt: half of Binance’s paragraph is true and half is an excuse. The correct reading is that revocation is a first-class wallet operation and must be pre-built, pre-tested and pre-authorized.
The delegation also carries a cross-chain blast radius. EIP-7702 authorization tuples include a chain ID, and chain ID 0 is the chain-agnostic mode. Academic analysis identifies that mode as a replay-like compromise surface across independent networks, with user-driven, attacker-driven and protocol-triggered paths to full account takeover. ERC-4337’s EntryPoint pipeline can make reactivation remote and repeatable.
The freeze race
The freeze response was fast, partial and uneven.
700 million USDT left the attacker’s address before any freeze, partly through Uniswap’s USDT pools. Tether froze the main Ethereum address at 21:01:35, 37 minutes after the drain. Circle froze US$823 million of USDC at 21:04:59, 41 minutes after. Tether’s Avalanche and Tron addresses and Tether Gold followed within minutes.
At 21:43, Binance moved 200 million USDT into Binance 14. The attacker’s code pulled it out about a minute later into a frozen address. Halborn independently flags that replenishment as unexplained in Binance’s report. Suspending withdrawals did not stop the pipeline from feeding the compromised wallet.
Avalanche and Polygon were hit at 23:05, after withdrawals were suspended. The last Ethereum transfer, 2,961.9 ETH, had been broadcast earlier and sat pending. Binance 14 revoked the delegation at 00:10:35, roughly 3 hours 46 minutes after the drain. Arbitrum’s Security Council moved 74.6 million ARB and 8,426 ETH into a frozen wallet at 00:18:20, 3 hours 54 minutes after.
Roughly US$2.8 billion was frozen across Ethereum, Tron, Avalanche and Polygon. About 460,000 ETH, worth more than US$1 billion, remained in 17 Ethereum wallets that no issuer could freeze. The attacker moved fastest where the brake arrived last. Native ETH on Ethereum, Avalanche and Polygon was never freezable at all.
What defenders should change
Rebuild the signer as a policy-enforcing component. Authenticate callers with workload identity, not network position or a bearer token. Parse what is being signed. Reject EIP-7702 authorization tuples unless a separate, higher-authority approval path authorizes them. A signer that accepts raw digests cannot enforce destination, amount or message-type policy.
Pre-build revocation. Ship a tested, runbook-exercised procedure that produces an authorization to the zero address. For MPC wallets, make it part of the standard signing product, not a bespoke procedure developed under incident pressure. Run it on every chain the wallet can authorize, including chain ID 0, and verify that a delegated account cannot be reactivated through ERC-4337 without fresh owner consent.
Treat the developer endpoint as the perimeter. Enforce provenance and integrity on Homebrew and language-version-manager shims. Alert on near-duplicate file sizes and replaced symlinks. Require code signing or hash pinning for toolchains. The pyenv replacement here differed from the original by 70 bytes and evaded endpoint protection entirely.
Constrain container deployment tokens. A single engineer token that can deploy workloads into a network segment containing the signing service is a single point of compromise for the entire treasury. Scope tokens to namespaces, shorten their lifetime, and enforce admission policy that blocks workloads from reaching signing endpoints without explicit identity.
Detect delegation as a first-class event. Alert on EIP-7702 authorization activity on every hot-wallet address. Treat a delegation indicator as equivalent to a withdrawal instruction. The 50 signing transactions were visible to the signer and should have been visible to monitoring.
Kill the replenishment path. Any incident response that pauses withdrawals must also pause automated treasury replenishment to any address with an active delegation.
What the record does not prove
Attribution is not established. Binance describes a North Korean-style tradecraft profile and says it detected and prevented 57 suspected North Korea-linked cases during 2026, but it does not tie the June intrusion to that count. The tradecraft is attributable. The operator is not. That distinction matters, because the technique is reusable by any actor with the same patience and the same access to a developer endpoint.
Several other questions remain open:
- Whether the signer received raw 32-byte digests or typed requests.
- Whether the service authenticated callers at all.
- When signing access was actually cut, given the late Avalanche and Polygon movements.
- Why 200 million USDT was moved into a wallet with an active delegation.
- What the internal AI tool was, and what privilege scope it had.
- Whether the bitcoin addresses attributed to the attacker can be independently traced. The US$1.5 billion bitcoin component currently rests on a single attribution.
Method and sources
This is an analysis of the public record, not an independent on-chain investigation. It draws on Halborn’s analysis of Binance’s November 3 findings, the EIP-7702 specification, the arXiv paper on EIP-7702 phishing, and OnChain Benchmark’s second-by-second reconstruction of the freeze race. Where the record is incomplete, I have said so rather than filling the gap.