Ordered rows of blue and violet circles fractured by a pink-red stream entering a dark void.

The Huff router approval incident

A calldata parsing bug in the Huff router let callers spend ERC-20 approvals granted to it by other addresses. Approximately $1.43M was taken from 31 addresses on May 5, 2026.

On May 5, 2026, a calldata parsing bug in HuffRouter was used to spend ERC-20 approvals that other addresses had granted to the router. Approximately $1.43M was taken.

This is a summary. The full post-mortem has the technical detail, the transaction-level analysis and the raw data.

Affected contracts

ChainEkubo versionRouter
EthereumV20x8f52903d17e2d8d6c77d1a1de0cc975b6b5a0d15
EthereumV20x8ccb1ffd5c2aa6bd926473425dea4c8c15de60fd
EthereumV30x4f168f17923435c999f5c8565acab52c2218edf2
ArbitrumV30xc93c4ad185ca48d66fefe80f906a67ef859fc47d

The flaw was in shared callback parsing logic, so routers for both Ekubo versions were affected. All four deployments are immutable and remain vulnerable.

What was taken

31 addresses, across 34 address-token combinations, totalling approximately $1,419,543 at the prices used in the analysis.

TokenAmount
WBTC17.0158
USDC20,550.01
EKUBO5,813.55
gEKUBO-26Q215.81
cbBTC0.3439
USDT92.38
LINK0.5503

Losses are concentrated. One address accounts for about 98% of the total: 17.0148 WBTC (≈$1,368,068) and 0.3439 cbBTC (≈$27,715). The other 30 addresses account for roughly $24,000 between them. Twenty-eight of the 31 were affected in a single token.

On Arbitrum the exploit was found once, for 5 USDC.

Per-address data is in the report, and the analysis can be re-run against any mainnet RPC supporting trace_*.

Cause

The router located its own settlement data by counting forward from the logical end of the decoded route rather than from the actual end of the calldata. A caller could append bytes after the route that the route parser never read, and those bytes were then interpreted during settlement as values the router had set itself — including the address tokens are pulled from.

That address is normally the caller. With appended bytes it could be any address that had approved the router.

The fix anchors those reads to the end of calldata. Regression tests reproducing the attack shape are in the repository.

Cost of discovery

The router is written in Huff and its source was not published. Finding this bug by hand means identifying the contract as a target, decompiling it, reconstructing its calldata format, producing a working exploit and selecting a moment to use it — substantial work for a person, against an uncertain return.

Automated tooling now performs that sequence at a fraction of the cost, which changes the economics of attacking a small, obscure, closed-source contract. That capability arrived quickly enough that it was not reflected in the risk assessment made before deployment.

Approval exposure

The router was not in the scope of an independent audit. It was written for use with an allowance fixed to the amount being spent, granted and consumed together, which bounds exposure to the size of a single swap.

Two things produced allowances outside that pattern:

  • The EVM fix-price page. An internal tool for correcting the price of a pool, reached by direct URL rather than from the app’s navigation, requested an unlimited allowance.
  • Wallets without batching. EIP-5792 allows an approval and the transaction that consumes it to be sent atomically. Wallets without it require the approval as a separate transaction, which stands until the swap lands, and makes an unlimited approval the more convenient option.

ERC-20 approvals do not expire and are commonly granted without limit, so an approval remains usable indefinitely after the transaction that motivated it.

Status

  • The parsing bug is fixed in the repository. The deployed routers cannot be patched.
  • The Ekubo interface no longer routes through the affected contracts.
  • Finite approvals were whitehatted out of the affected contracts. Remaining exposure is limited to infinite approvals.
  • Addresses with an outstanding approval see a warning in the interface.

Infinite approvals to the four contracts above should be revoked. revoke.cash has a page for them, and the report lists the infinite approvals still outstanding. The Ekubo interface is the only known source of approvals to these routers.

Recovery fund

The report includes a plan for distributing recovery funds to affected addresses, using a single per-address cap applied regardless of approval size or origin. Distributions would be made in kind, in the affected token, and where an address was affected in multiple tokens the cap would be filled starting from the largest balance by USD value. The plan is subject to legal review and to a DAO vote to fund it.

Update, August 10, 2026. On June 15, 2026 the DAO voted to contribute 300,000 USDC to a recovery fund, funded from its Ethereum USDC-USDT position, and the proposal executed. See Upgrades, bugs and a recovery fund. The fund is $300,000 against approximately $1.42M of identified losses, so a per-address cap applies.

Changes to audit scope

Routers are now included in the scope of contract audits, and Ekubo has increased its use of AI tooling for auditing alongside independent review.

The interface routes through a Yul router audited under that scope. Approvals to it are always limited to the amount being spent, regardless of the approval preference set in the interface, so standalone approvals are offered again for wallets that cannot batch an approval with the transaction that consumes it.

Separately, Ekubo published ERC-8255: Expiring Token Approvals, a draft standard giving approvals a bounded lifetime so they stop being usable after a set period rather than persisting indefinitely. Adoption is up to token implementers.