Worked example · 2020-06
Bancor v0.6 upgrade pool-drain exploit — Ethereum — 2020-06-18
Summary
Bancor is a decentralised automated-market-maker (AMM) protocol on Ethereum that pre-dates Uniswap and pioneered the "liquidity pool with a reserve-based pricing formula" model. In June 2020, Bancor deployed a v0.6 upgrade to its smart contracts, replacing the existing BancorConverter contract with new code that introduced additional features, including a new fee model and an expanded set of conversion functions.
A security researcher (acting as a white-hat) discovered a logic error in the v0.6 BancorConverter contract within hours of deployment. The bug was in the reserve-balance accounting logic: under specific conditions, the contract's internal reserve-tracking state could diverge from the actual token balances held by the contract, allowing a caller to craft a conversion path that would transfer more tokens out of the pool than the conversion's input amount should have permitted — effectively draining the pool's USDT and ETH reserves.
The researcher demonstrated the vulnerability by extracting approximately 12.5 ETH and ~229K USDT from the USDT pool, then promptly reported the bug to the Bancor team. The extraction was a white-hat action — the researcher held the funds temporarily to prove impact and prevent a malicious actor from discovering and exploiting the same vulnerability. After Bancor confirmed the bug and deployed a fix (v0.6.1), the researcher returned all extracted funds.
The affected pool was the only pool using the v0.6 BancorConverter contract at the time; all other Bancor pools remained on v0.5, which was not vulnerable. Bancor's rapid response — pausing the v0.6 converter, fixing the reserve-accounting logic, and deploying the patched v0.6.1 contract — limited the exposure to the USDT pool only. The incident drew a sharp contrast with the July 2018 Bancor hot-wallet compromise (~$12.5M in ETH, BNT, and other tokens via a compromised operator endpoint — a T11.001 case), demonstrating the two structurally distinct attack surfaces at Bancor: custody-layer (2018) vs. smart-contract-upgrade-layer (2020).
Timeline (UTC)
| When | Event | OAK ref |
|---|---|---|
| 2020-06-18 ~08:00 | Bancor deploys v0.6 BancorConverter contract upgrade; USDT pool migrated to the new converter | T16.006 (timelock-free upgrade deployment) |
| 2020-06-18 ~12:00 | White-hat researcher discovers reserve-accounting logic bug in v0.6 converter; extracts ~12.5 ETH + ~229K USDT to demonstrate impact | T9.004 (access-control / reserve-validation failure) |
| 2020-06-18 ~12:30 | Researcher reports vulnerability to Bancor; Bancor team pauses v0.6 converter | (defender response) |
| 2020-06-18 ~18:00 | Bancor confirms root cause: reserve-balance state divergence under crafted conversion-path calls | (forensic analysis) |
| 2020-06-19 | Bancor deploys patched v0.6.1 contract; researcher returns all extracted funds | (remediation + fund return) |
| 2020-06-20 | Bancor publishes post-mortem; all funds returned and accounted for | (post-mortem) |
Realised extraction
Zero net loss. Approximately $460K was temporarily extracted by the white-hat researcher as a proof-of-impact demonstration; all funds were returned within 24 hours after the vulnerability was patched.
Distinction from 2018-07 Bancor exchange compromise
The July 2018 Bancor incident (~$12.5M via a compromised operator hot-wallet endpoint) is documented at examples/2018-07-bancor.md and is classified under OAK-T11.001 (Third-Party Signing-Vendor Compromise / Operator-Signing-Infrastructure Compromise): the attacker compromised Bancor's hot-wallet signing surface and drained the exchange's custody wallets. The June 2020 upgrade vulnerability is a structurally distinct event: it targeted the smart-contract layer (a logic bug in a production upgrade of the AMM converter), not the custody layer. The two Bancor incidents illustrate the dual-attack-surface shape that protocols with both custody operations and on-chain smart contracts must defend against.
T9.004 classification
The v0.6 BancorConverter vulnerability is classified under OAK-T9.004 (Access-Control Misconfiguration) because the core failure mode was a missing invariance check: the contract's withdraw or convert path did not validate that the caller's claimed output amount was bounded by the pool's actual reserve balance as tracked by the contract's internal accounting. The access-control failure is not a missing onlyOwner guard but a state-consistency failure — the contract permitted a state transition (token outflow) that violated the invariant the contract was designed to enforce (outflow <= caller's pro-rata reserve share). This is the same T9.004 structural sub-shape as the Uranium Finance migration-bug drain (April 2021, BSC) and the Concentric Finance multisig-signer-device compromise (January 2024, Arbitrum), all of which share the property that the contract believed it was in a valid state but an external caller could induce an inconsistent one.
T16.006 cross-classification
The upgrade from v0.5 to v0.6 was deployed by the Bancor contract owner without a governance timelock — the production pool was migrated to the new converter contract immediately upon deployment. The absence of a timelock meant that external researchers, auditors, and the community had no window to review the new converter's reserve-accounting logic before the pool's funds were exposed. The structural T16.006 pre-condition — a single-owner upgrade deployed directly to production without a mandatory delay — is the enabling context for the T9.004 reserve-accounting bug. This classification aligns Bancor June 2020 with the 2020-2021 DeFi timelock-free-upgrade cohort (documented at examples/2020-2021-defi-timelock-free-upgrade-cohort.md).
Public references
- Bancor, "Bancor Post-Mortem — June 2020 v0.6 Upgrade Vulnerability," June 20, 2020
- PeckShield, "Bancor v0.6 Converter Vulnerability Analysis," June 18, 2020
- The Block, "Bancor Smart Contract Bug Exposes User Funds," June 18, 2020
- Bancor v0.6 contract changelog and v0.6.1 patch notes (bancor.network)