Skip to content
Quantix Security Labs

Threat analysis

Analysed incidents and threat signals from Quantix investigations, written up the way an analyst briefs a protocol team: what happened, why it worked, how it was detected and what would have changed the outcome.
Analysed incidents
6
Critical
5
Median time to contain
55 min
Open signals
2
Illustration: briefing cards along a brass timeline, each with a severity edge

Response

Detection was fast. Containment was not always.

Every incident raised an alert at its first malicious action. What varied was how long it took someone with authority to act: a pause, a cancel, a registry update.
Time from the first malicious action to the first containment step, logarithmic scale.

Analysed incidents

Six incidents, newest first.

Each analysis is tied to the security events it produced and, where funds moved, to a forensic case file. Times are UTC.

6 of 6 incidents

CriticalOpen

2 Oct 2026, 13:05 UTC · Kestrelle Launchpad

BNB Chain

Attack class
Privileged parameter abuse (rug pull)
Events recorded
7
Alerts raised
7 (2 critical)
First alert
At the first malicious action
Contained
+55 min
Pool liquidity removed
96%
GLF supply minted by owner
40%
Sale claims
Paused

Liquidity lock shortened and drained on a launchpad sale

An owner-only setter moved a liquidity unlock date forward by six months; the pool was drained four minutes later.

Kestrelle’s LiquidityLocker let the platform owner reassign any lock and let a lock owner change its unlock time without a lower bound. The GLF project lock was reassigned to the project deployer, its unlock date moved from April 2027 to three minutes ahead, and 96% of pool liquidity was withdrawn. The deployer then minted 40% of GLF supply through a mint function the sale page described as disabled and sold it into what remained of the pool.

Root cause

Lock guarantees depended on two privileged setters: transferLockOwnership (platform owner) and setUnlockTime (lock owner), neither timelocked or restricted to extending a lock. The GLF token kept an owner-only mint function. Users relied on a promise that the code did not enforce.

Detection

R-02 fired on the lock owner change at 13:05, and R-09 at critical severity on the unlock-date change two minutes later. Both alerts arrived before the liquidity was withdrawn, but nobody outside the platform owner could act on them: the locker had no guardian or pause.

Timeline

  1. Preparation20 Sept 2026, 09:12 UTC

    Deployer funded from an exchange

    The GLF deployer received 3 BNB from deposit cluster EX-19 eight days before the sale closed.

  2. Preparation28 Sept 2026, 16:00 UTC

    Sale finalised and liquidity locked

    Sale proceeds seeded the GLF/WBNB pool and the LP tokens were locked until 1 April 2027.

  3. Execution2 Oct 2026, 13:05 UTC

    Lock reassigned to the deployer

    The platform owner transferred lock 2217 to the deployer address.

    Events EV-1601

  4. Execution2 Oct 2026, 13:07 UTC

    Unlock date moved forward

    setUnlockTime moved the unlock to 13:10 the same day.

    Events EV-1602

  5. Execution2 Oct 2026, 13:11 UTC

    Liquidity withdrawn

    96% of LP tokens were redeemed for the underlying WBNB and GLF.

    Events EV-1603

  6. Execution2 Oct 2026, 13:12 UTC

    Owner mint

    40% of supply minted to the deployer through a function described as disabled.

    Events EV-1604

  7. Execution2 Oct 2026, 13:15 UTC

    Minted tokens sold

    Sold into the remaining 4% of reserves.

    Events EV-1605

  8. Containment2 Oct 2026, 14:00 UTC

    Claims paused

    The platform owner paused GLF sale claims.

    Events EV-1606

  9. Post-incident3 Oct 2026, 10:00 UTC

    Platform ownership transferred

    Ownership of the sale factory moved to an address with no history. The investigation remains open.

    Events EV-1607

Behavioural indicators

  • Lock owner change followed by an unlock-time change within minutes
  • Owner mint on a token whose sale page states minting is disabled
  • Liquidity removal above 90% of reserves in a single transaction

What to change

  • Lock contracts should only allow extensions; shortening a lock should be impossible rather than permissioned.
  • Token contracts listed by a launchpad should be checked for retained mint, blacklist and fee setters before a sale opens.
  • An alert is only useful when someone independent of the alerted role can act on it.

Further reading: Detecting suspicious on-chain behaviour before the exploit transaction · Upgradeable proxy security: storage, selectors and the upgrade path

CriticalClosed

14 Sept 2026, 01:56 UTC · Obsidian Rollup

Ethereum

Attack class
Key compromise of an upgrade administrator
Events recorded
8
Alerts raised
6 (1 critical)
First alert
At the first malicious action
Contained
+1 h 6 min
Funds lost
None
Withdrawal finalisation paused
37 h
Scheduled upgrade
Cancelled

Compromised upgrade signers schedule a malicious Portal upgrade

Two of three upgrade-multisig keys were taken from a CI-connected signing host; the timelock gave responders 48 hours and they needed three.

An attacker with access to the signing service used by Obsidian’s release pipeline obtained two of the three upgrade-multisig keys. They deployed a Portal implementation that would let them finalise arbitrary withdrawals and scheduled the upgrade through the 48-hour UpgradeTimelock. Detection on the unapproved implementation hash led the guardian to pause finalisation and the security council to cancel the operation inside the delay.

Root cause

Two upgrade keys lived on the same CI-connected host, so one host compromise met the 2-of-3 threshold. The timelock was the control that worked: a direct upgrade path would have executed immediately.

Detection

R-01 compares every scheduled implementation with the approved-release list. It fired at 02:14:09, eighteen seconds after scheduling. Earlier, R-16 had flagged the fresh deployer, and R-02 flagged multisig activity outside the change window.

Timeline

  1. Preparation14 Sept 2026, 01:56 UTC

    Malicious implementation deployed

    A fresh, single-use deployer created a Portal-sized contract matching no release.

    Events EV-1501

  2. Execution14 Sept 2026, 02:13 UTC

    Multisig transaction signed

    Two owners signed outside the change window.

    Events EV-1502

  3. Detection14 Sept 2026, 02:14 UTC

    Unapproved upgrade scheduled

    The UpgradeTimelock received an operation pointing the Portal proxy at the new contract.

    Events EV-1503

  4. Containment14 Sept 2026, 03:02 UTC

    Finalisation paused

    The guardian paused withdrawal finalisation as a precaution.

    Events EV-1504

  5. Containment14 Sept 2026, 05:40 UTC

    Operation cancelled

    The 4-of-7 security council cancelled the scheduled operation.

    Events EV-1505

  6. Recovery14 Sept 2026, 09:25 UTC

    Owners rotated

    Both exposed owners replaced with hardware-backed keys held by separate people; threshold raised to 3 of 5.

    Events EV-1506

  7. Recovery15 Sept 2026, 16:00 UTC

    Finalisation resumed

    State roots for the affected period re-verified before unpausing.

    Events EV-1507

  8. Post-incident16 Sept 2026, 12:00 UTC

    Upgrade delay raised to 8 days

    Longer than the 7-day withdrawal window, so users can exit before any upgrade takes effect.

    Events EV-1508

Behavioural indicators

  • Implementation deployed by an address funded less than an hour earlier
  • Upgrade-multisig execution outside the agreed change window
  • Scheduled implementation hash absent from the release allowlist

What to change

  • Signer keys for a threshold must not share infrastructure; one host should never hold enough keys to meet the threshold.
  • Timelock delays on withdrawal-path contracts should exceed the time needed to convene the cancelling party.
  • Implementation-hash allowlists make upgrade alerts specific enough to act on at 2 a.m.

Further reading: Upgradeable proxy security: storage, selectors and the upgrade path · Initializers, proxies and the contract nobody owns

CriticalMonitoring

30 Aug 2026, 03:12 UTC · Tallowmere CDP

Solana · Ethereum · Arbitrum

Attack class
Oracle manipulation
Events recorded
10
Alerts raised
8 (3 critical)
First alert
At the first malicious action
Contained
+28 min
tUSD minted
3,180,000
Uncovered bad debt
2,364,000 tUSD
Lowest tUSD price
0.87

Spot-price oracle manipulation mints unbacked tUSD

A flash-loan funded trade moved a thin pool 8.1×; the CDP valued collateral at that price and minted 6.4% of tUSD supply.

Tallowmere’s oracle adapter priced TLW collateral from a single spot-price account on a thin Corvid AMM pool. In one transaction an exploit program borrowed SOL from a flash liquidity program, bought TLW and pushed its price to 8.1× the reference, deposited the TLW and minted 3,180,000 tUSD against it, swapped the tUSD to USDC and repaid the loan. Proceeds were split, bridged to Ethereum and Arbitrum, swapped to WETH and partly passed through a mixing service before reaching exchange deposit addresses.

Root cause

The adapter read an instantaneous pool price with no time-weighting, deviation bound or liquidity check. Manipulating that price cost less than the tUSD it allowed to be minted.

Detection

R-06 (flash-loan sized round trip), R-05 (oracle deviation) and R-11 (mint above schedule) all fired on the exploit transaction itself. Detection was immediate; containment took 28 minutes because pausing required the admin multisig.

Timeline

  1. Preparation27 Aug 2026, 14:22 UTC

    Funding wallet created

    A new wallet received 412 SOL from deposit cluster EX-03.

  2. Preparation29 Aug 2026, 22:40 UTC

    Exploiter funded

    410 SOL moved to the wallet that would deploy the exploit program.

  3. Preparation30 Aug 2026, 02:58 UTC

    Program deployed and simulated

    The exploit program was deployed and read the TLW price account in simulation.

    Events EV-1401

  4. Execution30 Aug 2026, 03:12 UTC

    Flash-loan funded manipulation

    4,500 SOL borrowed; 4,200 SOL bought 640,000 TLW, moving the pool to 8.1× the reference price.

    Events EV-1402, EV-1403

  5. Execution30 Aug 2026, 03:12 UTC

    Unbacked mint

    3,180,000 tUSD minted against 640,000 TLW in the same transaction.

    Events EV-1404

  6. Execution30 Aug 2026, 03:14 UTC

    Proceeds withdrawn

    tUSD swapped to USDC; the loan repaid; 2,329,200 USDC sent to the exploiter.

    Events EV-1405

  7. Detection30 Aug 2026, 03:20 UTC

    Vault liquidated

    Keepers liquidated the attacker vault after the price reverted; the collateral covered about a fifth of the debt.

    Events EV-1406

  8. Containment30 Aug 2026, 03:41 UTC

    Minting paused

    The admin multisig halted new mints.

    Events EV-1407

  9. Containment30 Aug 2026, 04:10 UTC

    tUSD depeg

    tUSD traded at 0.87 as holders exited.

    Events EV-1408

  10. Recovery30 Aug 2026, 06:30 UTC

    Oracle replaced

    TLW delisted; every feed moved to a bounded 30-minute TWAP.

    Events EV-1409

  11. Recovery31 Aug 2026, 12:00 UTC

    Insurance fund draw

    210,000 tUSD of bad debt covered from the insurance fund.

    Events EV-1410

  12. Post-incident13 Sept 2026, 11:40 UTC

    Funds traced to exchange deposits

    Forensics follows proceeds through two bridge routes, a mixing service and into two exchange deposit clusters.

Behavioural indicators

  • Program deployed minutes before reading a price account it later manipulates
  • Borrow, swap and repay inside one transaction sized against pool depth
  • Proceeds split into near-equal amounts and bridged within the hour

What to change

  • Collateral prices must come from manipulation-resistant sources: time-weighted, bounded, and checked against liquidity depth.
  • The cost of manipulating a price should be compared with the value a protocol lets you extract at that price.
  • Mint caps per block or per collateral type limit the damage of any single pricing failure.

Further reading: Understanding oracle manipulation: designs and their failure modes · What it costs to move a price: reasoning about oracle manipulation · Solana program security: every account is an input

CriticalClosed

22 Jul 2026, 11:02 UTC · Axeline Bridge

Optimism · Avalanche · Arbitrum

Attack class
Cross-chain message replay
Events recorded
8
Alerts raised
6 (2 critical)
First alert
At the first malicious action
Contained
+6 min
axUSD credited twice
412,000
Replay attempts blocked
14
Arbitrum delivery paused
22 h

Cross-chain message replayed on a second destination

Verifier v1 digests did not commit to the destination chain, so two Avalanche deliveries were accepted again on Arbitrum.

An attacker sent two 206,000 axUSD transfers from Optimism to their own address on Avalanche. Because the v1 attestation digest covered source chain, nonce and payload but not the destination chain, the same attestations were valid on every Axeline endpoint. The attacker relayed both to Arbitrum and was credited a second time. Fourteen further replay attempts failed after the Arbitrum executor was paused.

Root cause

Domain separation was incomplete: the signed digest omitted the destination chain ID and endpoint address, and receivers kept per-destination nonce records that could not see deliveries elsewhere.

Detection

R-13 maintains a digest index across destinations and fired on the first replay. R-14 confirmed the outflow exceeded the window limit, which was configured to alert rather than block.

Timeline

  1. Preparation21 Jul 2026, 19:40 UTC

    Original delivery on Avalanche

    The attacker’s second 206,000 axUSD message (nonce 48211) was delivered normally.

    Events EV-1301

  2. Execution22 Jul 2026, 11:02 UTC

    First replay on Arbitrum

    Message 48211’s attestation accepted by the Arbitrum endpoint.

    Events EV-1302

  3. Execution22 Jul 2026, 11:04 UTC

    Second replay

    Message 48202 replayed the same way.

    Events EV-1303

  4. Detection22 Jul 2026, 11:05 UTC

    Window limit exceeded

    Outflow reached 118% of the window limit.

    Events EV-1304

  5. Containment22 Jul 2026, 11:09 UTC

    Executor paused

    Operations paused Arbitrum delivery seven minutes after the first alert.

    Events EV-1305

  6. Containment22 Jul 2026, 12:40 UTC

    Further attempts rejected

    Fourteen replays of other Avalanche deliveries reverted.

    Events EV-1306

  7. Recovery22 Jul 2026, 14:30 UTC

    Verifier v2 made default

    v2 digests commit to source, destination, endpoint and nonce.

    Events EV-1307

  8. Post-incident23 Jul 2026, 09:00 UTC

    Delivery resumed

    Arbitrum executor unpaused after all receivers moved to v2.

    Events EV-1308

Behavioural indicators

  • The same attestation digest presented on more than one destination
  • Relayer gas funded by the message recipient minutes before relaying
  • Sender and recipient are the same externally owned account on different chains

What to change

  • Every signed cross-chain message must commit to source and destination chain IDs, endpoint addresses and nonce.
  • Rate limits that only alert are monitoring, not a control; at least one limit should block.
  • Replay detection needs a view across all destinations, not just the receiving chain.

Further reading: Anatomy of cross-chain bridge exploits · Signature replay across EVM chains

CriticalClosed

9 Jun 2026, 23:55 UTC · Thessaly Governance

Optimism

Attack class
Governance takeover with borrowed votes
Events recorded
8
Alerts raised
6 (1 critical)
First alert
At the first malicious action
Contained
+9 h 34 min
Treasury moved
None
Borrowed voting power
96% of proposer votes
Proposal 41
Cancelled

Borrowed voting power proposes removing the timelock

A one-block voting delay let borrowed tokens count; the payload would have zeroed the timelock and emptied the treasury.

An attacker borrowed 1.9M THS (4.2% of supply) from a lending market, delegated it to a new address and created Proposal 41 six minutes later. With a voting delay of one block the snapshot captured the borrowed balance. The payload set the timelock delay to zero and transferred the whole treasury to the proposer. The guardian cancelled the proposal before voting closed.

Root cause

Voting power was measured one block after proposal creation, so tokens borrowed for minutes counted in full. The Timelock accepted updateDelay(0) from governance, so a proposal could remove the delay it was itself subject to.

Detection

R-07 flagged that 96% of the proposer’s votes were acquired within 50 blocks; R-17 classified the payload as high risk because it called a privileged setter and moved treasury funds. Both fired in the creation block.

Timeline

  1. Preparation9 Jun 2026, 23:55 UTC

    Votes borrowed and delegated

    1.9M THS delegated to an address created 40 minutes earlier.

    Events EV-1201

  2. Execution10 Jun 2026, 00:01 UTC

    Proposal 41 created

    Threshold met only with recently acquired votes; payload zeroes the delay and moves the treasury.

    Events EV-1202, EV-1203

  3. Detection10 Jun 2026, 00:03 UTC

    Snapshot taken

    The borrowed balance was captured one block later.

    Events EV-1204

  4. Execution10 Jun 2026, 01:20 UTC

    Tokens returned

    The loan was repaid after the snapshot.

    Events EV-1205

  5. Containment10 Jun 2026, 09:30 UTC

    Guardian cancel

    Proposal 41 cancelled before voting closed.

    Events EV-1206

  6. Post-incident11 Jun 2026, 15:00 UTC

    Delay and floor raised

    Voting delay set to 43,200 blocks; Timelock minimum delay fixed at 48 hours.

    Events EV-1207, EV-1208

Behavioural indicators

  • Delegation from a lending-market borrower to a fresh address shortly before a proposal
  • Proposal payload that modifies the timelock it will execute through
  • Voting power repaid immediately after the snapshot block

What to change

  • Voting delay should make borrowed votes expensive: at least a day of interest at market rates.
  • Timelocks need a minimum delay that governance itself cannot lower.
  • A guardian cancel right is a backstop worth keeping until governance participation is broad.

Further reading: Governance attacks in DeFi

HighClosed

18 May 2026, 08:20 UTC · Larkspur Wallet SDK

Cosmos

Attack class
Signature phishing (delegated authorisation)
Events recorded
6
Alerts raised
3 (0 critical)
First alert
At the first malicious action
Contained
+2 h 9 min
Grants signed
37
Balances moved
22
Grant revocations after advisory
88

Look-alike dApp collects unlimited authz grants

Thirty-seven users granted a single grantee open-ended send authority through a cloned front end; 22 balances were moved within the hour.

A look-alike front end copied an integrator’s name and icon and paired with wallets built on the Larkspur SDK. It asked users to sign a MsgGrant giving one grantee GenericAuthorization for MsgSend with no expiry, presented as a session approval. The grantee then used MsgExec to move balances. The SDK showed the raw message type but not what it allowed.

Root cause

The signing view did not decode authz grants into plain language or flag GenericAuthorization without expiry, and the pairing relay could not verify that dApp metadata came from the claimed origin.

Detection

R-12 counts grants to the same grantee per hour and fired at 37. R-18 followed with the MsgExec burst. The pairing mismatch was found by correlating session origins with the alerting grantee.

Timeline

  1. Execution18 May 2026, 08:20 UTC

    Grants collected

    37 MsgGrant signatures to one grantee in an hour.

    Events EV-1101

  2. Execution18 May 2026, 08:41 UTC

    Balances moved

    22 MsgSend executions under authz to a collection address.

    Events EV-1102

  3. Detection18 May 2026, 09:05 UTC

    Cloned metadata found

    Pairing sessions traced to a look-alike origin.

    Events EV-1103

  4. Containment18 May 2026, 10:30 UTC

    Grantee flagged

    Registry update made SDK clients block grants to the address.

    Events EV-1104

  5. Recovery19 May 2026, 14:00 UTC

    SDK 2.4 released

    Grants decoded in plain language; GenericAuthorization requires an expiry.

    Events EV-1105

  6. Post-incident20 May 2026, 09:00 UTC

    Revocations

    Users revoked outstanding grants at 2.1× the usual rate.

    Events EV-1106

Behavioural indicators

  • Many grantors authorising one grantee within an hour
  • GenericAuthorization for MsgSend without an expiry
  • Pairing metadata that matches a known integrator but not its origin

What to change

  • Wallets should decode delegated-authority messages and warn on unlimited scope or missing expiry.
  • Pairing metadata is a claim, not an identity; origin verification belongs in the protocol.
  • Revocation should be one click from the warning, not a separate tool.

Further reading: Off-chain signatures, on-chain losses: the anatomy of approval phishing · Detecting suspicious on-chain behaviour before the exploit transaction

Signals

High-severity alerts outside the incidents.

Alerts at high or critical severity that are not part of an analysed incident, newest first, from recorded monitoring through 24 Oct 2026, 09:00 UTC.
  • 23 Oct 2026, 22:41CriticalFlash-loan sized round trip through a GLF poolMerivale Markets · Router · BNB Chain · R-06 Flash-loan sized round tripOpen
  • 24 Jun 2026, 06:40HighPrice deviation of 2.3% after sequencer restartVeyra Finance · PriceOracle · Base · R-05 Oracle deviation from referenceResolved
  • 6 May 2026, 02:11HighInsurance fund outflow of 3.1% in one hourVantor Perpetuals · Insurance fund · Solana · R-03 Treasury outflow above thresholdResolved
  • 26 Mar 2026, 08:31HighFee operator transferred to an externally owned accountMerivale Markets · FeeController · BNB Chain · R-02 Privileged role changeAcknowledged

Open these events in the monitoring console

Threat intelligence tied to your architecture.

Technique tracking, indicator development and exposure mapping for the components you actually run.