Deception CheckDeception Check← all research
Threat Research · Fleet Telemetry · Part 2 of 2

The Same Scanners Phone Home

In Part 1, 216 sources crossed the line between our IT and our OT decoys. Here we take the ones that hit the most decoys and ask a simpler question: who are they, and are they connected? Most of them turned out to be scanners — but the exposed databases they surfaced in are genuinely compromised.

Deception Check  |  July 2026  |  Fleet telemetry + Shodan + VirusTotal  |  9 addresses → all scanners  |  1,357 exposed Redis  |  Part 2 of 2
New here? This is the second of two parts. Part 1 shows how a single automated source crossed our IT and OT decoys, and why that boundary is an org chart rather than a control. Start with Part 1: One Source, Twenty Decoys →
The short version Part 1 ended with a single Amazon-hosted crosser that touched more than twenty of our decoys in one sweep. The non-obvious read came when we did the same lookup for the other top crossers. We took the addresses that hit the most of our decoys, dropped our own management traffic and a couple of research scanners, and looked each one up in Shodan and VirusTotal. Nine of them shared something striking: they all appeared in the client lists of the same compromised datastores. That looked like a single coherent operation running on cheap cloud hosting and coordinating through other organizations' exposed Redis and Apache ZooKeeper servers. It was not. We are not naming an operator. We are showing that you can take a handful of IPs your own sensors flagged and, using nothing but public data, fingerprint the shared infrastructure behind them. The through-line is a discipline we hold to: catching is not classifying, and a fleet that flags everything is only useful if it will say which hits are a botnet, which are research scanners, and which it honestly cannot tell apart.

How we did it

From Part 1 we had a ranked list of the sources that crossed the IT/OT line, ordered by how many distinct decoys each one touched. Before doing anything with it, we scrubbed it. First we removed our own internal artifacts, the fleet's management and self-test traffic, which is exactly the kind of thing that inflates a count if you do not catch it. Then we set aside two addresses on a single hosting block that belong to a legitimate internet-measurement company, plus one lone SSH box that did not match anything else.

The arithmetic is worth stating plainly. Of the 216 crossers, we worked from the most prolific by decoy count, which came to thirteen external addresses once our own artifacts were removed. Setting aside the two research scanners and the one outlier just described left ten. We looked each of the ten up in Shodan, to see what services it runs and what it connects to, and VirusTotal, for independent reputation. Every one of the ten is flagged malicious by multiple security vendors. Nine of them appeared to resolve into one operation. The tenth advertised itself as something else, and it turned out to be the key to re-reading the other nine; we come back to it below.

What we found: two compromised datastores, and a roster we could not read

The nine split across two cheap-hosting providers: four on Amazon's cloud in the US-East region, and five on Linode, now Akamai Connected Cloud. Both groups surfaced in the client lists of the same exposed datastores, which is what first made them look like one fleet. They are not one fleet.

The Amazon nodes speak Redis. Each shows up in the connected-clients list of a large population of exposed Redis servers, databases left open to the internet on port 6379 with no password. Those Redis servers share a common profile: they run on Windows, using the same widely-circulated unofficial Windows build. Redis has no official Windows port, so nearly everyone who runs it on Windows pulls the same prebuilt binary, which is why they carry an identical redis_build_id a4f7a6e86f2d60b3. That uniformity is expected rather than remarkable, and we do not lean on it as evidence. What it gives us is a clean way to size the pool: a Shodan search for that build returns more than thirteen hundred internet-exposed instances, concentrated in China, South Korea, the United States, Iran, and Vietnam. That is the botnet's hunting ground, not its membership.

World map of the internet-exposed Windows Redis population the botnet targets, concentrated in China
The internet-exposed Windows Redis population the botnet preys on: 1,357 servers, heavily concentrated in China, then South Korea, the US, Iran, and Vietnam. Compromised instances are a subset, marked by the c2 keys, not the whole population.

The tell that a given box has actually been conscripted is not the shared build, it is the two keys sitting in its keyspace that have no business in a cache: c2_startup and c2_ssh_key. That pattern is consistent with the long-known open-Redis takeover technique, where an attacker connects to an unauthenticated Redis instance and uses it to write an SSH key onto the host, turning the database into a foothold and a staging point. The scanners are not just probing these boxes, they are wiring them into a back end. Everything we describe about these servers, the build, the keys, and the connected-client lists, comes from Shodan's published banner data; we did not connect to any of them ourselves.

The Linode nodes speak ZooKeeper. Alongside Redis, the Linode cluster appears as clients in exposed Apache ZooKeeper instances on port 2181. ZooKeeper is a coordination service, the kind of thing a distributed system uses to keep its nodes in sync, and an internet-exposed one with no authentication is both a target and a ready-made control channel. The same handful of Linode addresses recur across ZooKeeper servers on Google Cloud, Aliyun, DigitalOcean, and others.

Why the two halves looked like one operation. The apparent tell was the overlap: the Linode nodes appear in both the Redis and the ZooKeeper client lists. A node that connects to the botnet's Redis staging boxes and to its ZooKeeper coordination boxes looked like more than coincidence. What that reasoning missed is that a scanner sweeping port 6379 and port 2181 produces exactly the same overlap, for entirely mundane reasons. The overlap is real; the conclusion we drew from it was not. The shared Redis build fingerprint across the victim population is still a genuine signature — but it describes the pool being preyed on, not the parties doing it.

Bigger than we caught

Here is the part that pays off Part 1's argument. Our decoys caught nine addresses that all turned up in the client lists of the same compromised datastores. Checked against our own sensor logs, every single one announces itself as a scanner: four send the user-agent visionheight.com/scan, five send zgrab. The compromised servers are real and the exposure is real. The membership list is the part a client list cannot give you.

Nine caught addresses appear in the client lists of exposed Redis on 6379 and exposed ZooKeeper on 2181; the servers are compromised, the client lists are not a roster
The nine addresses our decoys caught all appear in the client lists of other people's exposed Redis and ZooKeeper servers. Those servers are genuinely compromised. The client lists, however, record every host that connected to them — and scanners connect to everything, which is why we no longer read these lists as a roster.

The numbers make the point. Each exposed ZooKeeper server we looked at was showing dozens of connected clients at once. We pulled the client lists from just two of them and counted the distinct source addresses: fifty-four. Of those fifty-four, exactly five are nodes our own decoys had flagged as crossers. The other forty-nine never touched a single one of our sensors, and we cannot say what they are. They may be fleet nodes, other scanners, or researchers — a client list does not distinguish them. There are hundreds more exposed ZooKeeper and Redis instances carrying the same client fingerprints.

Scale: 9 addresses caught by our sensors, against a population of 1,357 internet-exposed Redis servers
One fleet of sensors sees a sliver. The exposed infrastructure reveals the staging ground, even when it cannot reveal the roster.

So the honeypots gave us nine addresses and a direction. The exposed infrastructure gave us the staging ground.

The gray zone: scanners you cannot tell from bots

The honest counterweight is that not everything crossing our IT/OT line is a botnet, and the hard part is telling the difference. The clearest case was easy. Two addresses sharing one hosting block belong to an internet-measurement company. They show up not in Redis or ZooKeeper but in the recent-connections of NTP servers around the world, which is what wide-area research scanning looks like. Their traffic reached our decoys the same way an attacker's would, but calling them botnet nodes would have been wrong, so we set them aside.

The genuinely difficult case is the tenth address, the one that advertised itself as something else. It was, in Part 1, the single widest crosser on our whole fleet. Its scanning hosts share a reverse-DNS suffix that ties them to a single operator, a self-described "ethical internet scanning" program whose public site says it collects only banners, TLS certificates, and protocol versions, with no authentication attempts and no exploitation. Taken at face value, that is a research scanner like Censys or Shodan.

Three things sit uneasily with the face value. It carries tens of thousands of abuse reports from over a thousand independent sources and is flagged malicious by multiple VirusTotal vendors. Defenders log it in the same breath as Censys and Shadowserver, but also alongside pure nuisance scanners. And on our own fleet it did not behave like a banner-grabber: it spoke Modbus and other industrial protocols to our OT decoys, and it appears in the connected-client lists of the very same exposed-Redis population the botnet uses.

From the packets alone, a gray-area scanner and a botnet node are the same thing. The only difference is a claimed intent, published on a website, that the traffic cannot confirm.

That is why we set it aside rather than counting it as hostile: not because its behavior was cleaner than the others, but because it asserts a research purpose we can neither verify nor disprove. And that ambiguity is itself a finding. A growing class of self-described "ethical" scanners now sweep the entire internet, industrial and OT services included, from cloud IP space, rack up heavy abuse records, and are operationally indistinguishable from the botnets they claim to be studying. When intent does not travel in the packets, "aggressive research" and "reconnaissance for a campaign" look identical on your sensors. One last address, a lone SSH-only box on a US host, matched none of the clusters, and we left it as an honest outlier rather than force it into the story.

This is the point of classification. Deception catches everything that touches a decoy, which is its strength, but "touched a decoy" is not the same as "is malicious," and a fleet that cannot separate a coordinated C2 client from a research scanner, or admit when it cannot tell them apart, is not producing intelligence, it is producing noise.

The map

Source addresses grouped by the infrastructure they phone home to; reputation from VirusTotal; our own nodes and exact decoy names generalized.
GroupAddresses we caughtHostingPhones home toIndependent verdict
Gray-zone scanner5Amazon, US-EastExposed Redis (6379) client lists; self-describes as "ethical" scanningSends visionheight.com/scan to our sensors; heavily abuse-reported; intent unverifiable
Measurement scanner5Linode / Akamai Connected CloudExposed ZooKeeper (2181) and Redis client listsSends zgrab to our sensors; wide-area enumeration
Research scanner2One hosting /24 (measurement firm)NTP servers worldwideBenign scanning, set aside
Outlier1US host, SSH onlyNothing matchingUnexplained, left out

Indicators

Indicators of compromise: exposed-datastore abuse, observed July 2026
# Behavioral indicators (the durable ones, and the only ones we publish)
Redis build id    a4f7a6e86f2d60b3   (the common unofficial Windows Redis build)
Redis keys        c2_startup, c2_ssh_key
Ports             6379/tcp Redis (staging)   2181/tcp Apache ZooKeeper (coordination)

# Notes
Source addresses are deliberately not published. Every address we caught resolved to a scanner;
see the correction note at the end of this post.
Exposed Redis and ZooKeeper servers are third-party victims and are deliberately not listed here.
Presence in a compromised server's client list is not evidence of operating it.

What defenders should take from this

Honest framing and limits

We are fingerprinting infrastructure by behavior, not attributing it to a named actor, and we are deliberately not publishing our own node identities or exact decoy names. Shodan is a point-in-time view, so the specific exposed servers and client lists will drift. The Redis c2_* keys and the shared build fingerprint are strong signals of a single coordinated operation, but "one operation" is an inference from correlation, not a claim about who runs it. The exposed Redis and ZooKeeper servers described here in aggregate are victims, not the attacker, and they are already visible to anyone with a Shodan account.

Sources & notes

Deception Check honeypot fleet, July 2026 (first-party): the crosser ranking and IT/OT correlation from Part 1, scrubbed of our own management and self-test traffic before analysis. Third-party enrichment (public OSINT, July 2026): Shodan host and search data for services, connected-client lists, and build fingerprints; VirusTotal for independent reputation. Source addresses are not published at all; only behavioral indicators appear in the box above. Exposed-server populations are described in aggregate and their addresses are not published, since those hosts are victims rather than attackers.

Correction — 28 July 2026

This post originally published a list of nine source addresses under the heading “confirmed botnet nodes,” and described them as a rented fleet. That attribution was wrong and the list has been removed.

The compromised datastores are real. What we could not do is name the operator from their client lists — because those lists are full of scanners. Of the nine addresses we initially flagged, every one turned out to announce itself as a scanner on our own sensors: four as visionheight.com/scan, five as zgrab. The lesson generalises: co-presence in a victim’s client list is not membership in the operation.

The behavioral indicators are unaffected and remain the recommended detection surface. We are leaving this note in place rather than editing silently, because the original list was public for a day and may have been copied.