Root Cause
Harmony Protocol contained two compounding vulnerabilities in its cross-shard consensus layer:
Vulnerability 1: Cross-Shard Receipt Replay
Harmony's inter-shard messaging protocol failed to enforce single-use semantics on cross-shard receipts. Once a receipt was validated on the receiving shard, it could be submitted again—and re-executed—without triggering a duplicate-detection error. Each successful replay minted fresh ONE tokens on the destination shard without debiting any balance elsewhere.
Vulnerability 2: Quorum Signature Check Bypass
Harmony's consensus quorum verification counted every public key listed in the BLS signature bitmask as a valid signer, rather than counting only keys whose actual cryptographic signatures passed verification. An attacker could craft a consensus message that listed many public keys in the mask but carried zero valid signatures—yet the quorum threshold check would still pass because it counted mask entries, not verified signers.
// Pseudocode illustrating the broken quorum check:
func isQuorumMet(msg ConsensusMsg, validators []PubKey) bool {
count := 0
for _, key := range validators {
if msg.SigMask.Has(key) { // ← counts mask entries, not verified sigs
count++
}
}
return count >= quorumThreshold // BUG: signatures never actually verified
}
Combined, these two flaws let the attacker: (a) forge a cross-shard receipt carrying zero real signatures that passed the quorum check, and (b) replay it hundreds of times to continuously mint tokens.
Attack Steps
| Step | Action | Result |
|---|---|---|
| 1 | Attacker crafts forged cross-shard receipts using zero signatures + zeroed/dead-address keys | Bypasses quorum check due to mask-counting bug |
| 2 | Submits 534 fraudulent transfers of 5 billion ONE each within a 106-second window | 477 succeed due to replay flaw |
| 3 | 2.385 trillion ONE minted; later analysis raises total to ~3.01 trillion | ~26% supply inflation in minutes |
| 4 | totalSupply() endpoint masked the new tokens (supply reporting bug) | 97% of fraudulent tokens reach exchanges before freeze |
| 5 | Attacker sells into exchange liquidity | ONE falls 37–40%; USDC/USDT extracted |
| 6 | Network patched (Mainnet v2026.1.1 at 14:30 UTC+8 on Aug 13) | Vulnerability closed |
| 7 | Full rollback executed (Aug 17): Shard 0 → block 92,730,034; Shard 1 → block 94,978,278 | Forged token history erased |
Impact
- Forged supply: ~3.01 trillion ONE tokens (≈20% of pre-attack circulating supply)
- Token price drop: ONE fell 37–40% at peak before partial recovery
- Exchange exposure: 97% of forged tokens reached exchange deposit addresses before the network could freeze them
- Network action: Harmony executed a hard rollback erasing all blocks after the fork point, discarding all post-attack transactions in both Shard 0 and Shard 1
- Decentralization concern: The rollback decision, made by a small set of validators on a short timeline, drew criticism about the practical limits of blockchain immutability under emergency conditions
- Financial loss: Difficult to quantify post-rollback; exchanges that honored withdrawals of forged ONE before the freeze absorbed real losses
Lessons for Auditors
- Cross-shard/cross-chain receipt uniqueness must be enforced on-chain: Every cross-shard or cross-chain message must carry a globally unique nonce and a consumed-nonce set checked atomically on execution. Relying on off-chain monitoring to detect replays is insufficient.
- Verify signatures, not masks: BLS aggregate signature verification must iterate over and cryptographically verify each included signer, not merely count bits in a participation mask. Separate the parsing of "who claimed to sign" from "whose signature verified."
- Supply reporting endpoints must be derived from the live state: Any view function that reports
totalSupplymust read from the same authoritative state root as transfer logic—cached or indexed values can lag and mask exploits. - Fuzz cross-shard message flows: Consensus-layer bugs that require specific timing (106-second window, 534 rapid transactions) are hard to catch with unit tests. Property-based fuzzing over message sequencing and state transitions is essential.
- Immutability vs. emergency response: Chains with validator rollback capabilities should have pre-defined, on-chain governance processes for invoking them—ad-hoc rollbacks erode trust even when technically necessary.