top of page

We Had Megalodon's C2 Forty-Nine Days Before It Bit. Here Are The Three Detectors We Just Wired To Catch The Next One.

  • Writer: Patrick Duggan
    Patrick Duggan
  • 3 minutes ago
  • 4 min read

I published a blog yesterday about Megalodon, the mass GitHub Actions workflow-poisoning campaign that compromised 5,561 repositories in six hours on May 18, 2026. The headline I led with was that DugganUSA's IOC index carried the command-and-control endpoint at 216.126.225.129 before the campaign was publicly named by SafeDep, StepSecurity, OX, the Hacker News, and the rest. That was true. It was also a serious undercount of the actual receipt.


Tonight's deeper hunt against the corpus surfaced the real timeline. Our index first observed TeamPCP's blockchain-canister C2 at tdtqy-oyaaa-aaaae-af2dq-cai.raw.icp0.io on March 30, 2026, indexed via maltrail correlated with our daily github-hunt sweep. The Megalodon attack window opened on May 18 at 11:36 UTC and closed at 17:48 UTC the same day. The interval between the first indexed observation of the operator's persistent C2 and the operational use of that operator's most destructive campaign to date is forty-nine days. We watched the lighthouse for seven weeks without knowing what would eventually sail past it.



The structural lesson the longer interval forces


Four-day lead time before public naming is a competitive advantage. Forty-nine-day lead time before the attack itself is a different category of opportunity. The defender who acts on a four-day signal blocks the C2 after the operator has already exfiltrated. The defender who acts on a forty-nine-day signal blocks the C2 before the operator has chosen which campaign to fire from it. The asymmetry between those two states is the entire game.


What we did not have on March 30 was a detector that knew to elevate the observation. The blockchain-canister IOC sat in the corpus as one record among one-point-one-six million, classified as botnet_cc / Unknown malware from SSL Blacklist's certificate fingerprint correlator. It survived in the index because we do not delete data. It did not surface to anyone's attention because no precursor signal was wired to count "novel decentralized-compute C2 endpoints observed in the last thirty days" as an alerting condition. That is the gap. That is what tonight's deploy closes.



The three new precursor signals


The PreCog precursor aggregator is the hourly cron that scores eleven distinct signal axes and rolls them into a composite threat level. As of this evening's deploy, three new signals are live in the rotation.


The first is Decentralized C2 Emergence. The detector counts distinct untakedownable-C2 endpoints — Internet Computer Protocol canisters, IPFS gateways, web3.storage URIs, Arweave persistent objects — observed in the IOC index over the trailing thirty days. One new endpoint sets the score to 0.4, which is the elevation threshold. Two sets it to 0.6. Three or more sets it to 0.85, which is in approaching-critical territory. The lead time on this signal, calibrated against the Megalodon postmortem, is fourteen to forty-nine days.


The second is CI/CD Compromise Indicators. The detector queries the IOC index in the last twenty-four hours for tradecraft markers of GitHub Actions workflow poisoning — forged-bot author email TLDs like noreply.dev and automated.dev, identity strings like ci-bot and build-bot and pipeline-bot, file path references containing .github/workflows/, and the specific Megalodon payload-naming pattern. One indicator elevates. Three escalates. Five hits the high-confidence band. The lead time on this signal is zero to six hours, because by the time the indicator is in our index the campaign is firing or about to fire.


The third is Trycloudflare Staging Velocity. The detector counts distinct new *.trycloudflare.com tunnels in the last twenty-four hours whose paths look like phishing-loader or credential-harvest infrastructure — Windows shortcut extensions, double-extensioned PDFs, shipping-receipt naming conventions, login-pretender paths. Two new tunnels in twenty-four hours elevates. Five escalates. Ten hits the high band. Trycloudflare anonymity is the standard staging primitive across TeamPCP-class operators and the credential-harvester adjacency; velocity surfacing here precedes the campaign delivery window by one to fourteen days.


All three feed into the same composite threat-level calculation that drives the public status page and the customer-facing alerts. When any of the three transitions from non-elevated to elevated, a tier-one email fires to the operator inbox with the score, the lead-time band, the observed count, and a sample of the indicators. The first time the next Megalodon-class operator stages their C2 on a fresh blockchain canister, the inbox will know within an hour of our pipeline observing it.



What the live readings say tonight


Of the three new signals, Decentralized C2 Emergence already has two observations in the last thirty days — TeamPCP's tdtqy canister and the unattributed cjn37 canister from April 23. That places the new signal at score 0.6 at first run, which is in WARNING territory before it has even drawn its first new data point. The signal walks in already elevated. The threat-level composite will move when the aggregator next ticks at the top of the hour.


The CI/CD Compromise Indicators signal will start cold. The Trycloudflare Staging Velocity signal will start cold. Cold-start is the correct behavior for a detector; the surface area we want it to watch is operational tradecraft, not historical artifacts. The Megalodon-era markers are already in the corpus; they are older than the twenty-four-hour window and therefore do not count. The detector is for what comes next.



The shape that travels


This is the second time today that the strongest defender posture turned out to be the data we already had, surfaced by a detector we had not yet wired. The earlier example was PreCog itself — three months of precursor observations sitting in the Meilisearch index, invisible to our own search API because the multi-index handler silently dropped the sort parameter, fixed in revision 0000104 four hours ago. Tonight's example is the same shape one rung deeper. The receipt for the next campaign is already being deposited into our index. The job is to write the detector that surfaces it before the attacker decides what to fire.


Four-day lead time is a story. Forty-nine-day lead time is an operating model. The next Megalodon-class operator is staging their infrastructure right now, somewhere in the public web, getting it indexed by SSL Blacklist or URLhaus or maltrail or our github-hunt sweep, sitting in our corpus the way TeamPCP's canister sat for forty-nine days before March 30. The three signals that went live tonight are the difference between the operator's lighthouse being a passive record and the lighthouse triggering the watchman.


We are now configured to learn the same lesson once.




How do AI models see YOUR brand?

AIPM has audited 250+ domains. 15 seconds. Free while still in beta.


bottom of page