A hard-coded command server is a fixed target. Block the domain, pull the host, or seize the name, and every endpoint that had only that one address to phone home to is cut off.
A domain generation algorithm (DGA) replaces or supplements that fixed name with a shared rule. The endpoint calculates candidate domain names on demand, the operator calculates the same names independently, and DNS becomes the meeting point between two systems that don’t need a permanent domain written into the malware. It’s a good example of why attackers use DNS. The advantage comes from ordinary lookups, not from breaking DNS itself.
The algorithm replaces a static domain list
A DGA is logic that produces domain-name candidates from a few inputs, such as a date, a fixed seed, configuration data, or values unique to a malware family or sample. Both sides share enough of those inputs to arrive at the same names. The malware generates candidates and tries to resolve them, while the operator predicts the same sequence and registers or controls a few of them.
That shared rule turns locating infrastructure into a synchronization problem. The durable part is the generation logic and its inputs, and the resilience comes from the size of the changing candidate space more than from secrecy (the algorithm is often recovered later anyway). A DGA can emit far more candidates than the operator ever intends to register:
q7m4p2.example
k9v8d1.example
n3r6t5.example
b2x7c4.example
The endpoint knows the rule but not which candidate the operator actually made reachable, so it works through candidates, all of them or a sampled subset, until one resolves the way it expects. The operator, knowing the sequence in advance, only has to stand up a few.
To DNS, none of this is special. Each generated domain is just another name to look up, and the resolver has no idea a scheme exists.
Time gives both sides a changing schedule
Many DGAs feed the current date or time interval into the generator, so the candidate set rotates without pushing new configuration to every endpoint. Both sides calculate from the same date and seed and land on the same names for that window, and the next day or hour produces a different set. Conficker is the textbook case, deriving its domains in part from the current UTC date, and other families use monthly schedules, daily keys, or additional seed material.
Time also introduces failure modes that are the malware’s problem to solve. Endpoint clocks drift, so an implementation may query a window of dates or carry a fallback path to recover synchronization when the clock is wrong.
Generated names don’t have to look random
Some DGAs build labels character by character, producing strings that look like keyboard noise. Others concatenate dictionary words into names that read as almost plausible. That difference can decide whether a detector catches the family. High character entropy flags the gibberish generators, but a wordlist DGA scores far more like ordinary text under a character-entropy test and slips past it. Catching those takes word- and sequence-aware features instead.
A detector that treats “DGA” as a synonym for “random-looking” misses every family built around pronounceable strings or word combinations. The generation method matters more than whether the output looks like gibberish.
The NXDOMAIN flood is a side effect
When malware generates hundreds of candidates and the operator registers a handful, most lookups fail, and a burst of NXDOMAIN responses becomes a genuinely useful DGA signal in some environments. But the failures depend on how the operator deploys the algorithm. A candidate the operator actually stood up resolves normally. A defender’s sinkhole makes a generated name resolve too. A frugal implementation may query only a few candidates and never produce the tell-tale flood.
Negative caching does little against this. It suppresses repeat queries for the same nonexistent name, but a DGA mostly asks for distinct names, so each candidate is a fresh question the cache has never seen and the failures keep reaching the resolver. The exception is malware that retries the same daily set on a schedule, where negative caching does absorb the repeats.
Resolution itself is the discovery step
The endpoint needs no separate directory telling it which candidate is live. An unused candidate usually returns NXDOMAIN (though NODATA, SERVFAIL, or a timeout are possible too), a candidate the operator has set up returns an address or other data the malware recognizes, and whatever command channel follows may run over HTTPS, another protocol, or DNS.
That’s the usual line between a DGA and DNS tunneling. A DGA calculates candidate names and uses DNS to find which one is live, while tunneling uses DNS queries and answers as the data channel itself. The same malware can do both, so neither implies the other, and a DGA says nothing about how the later traffic travels.
Prediction, sinkholes, and what the evidence becomes
Recover a DGA’s logic and inputs and you can often compute future candidates before the endpoints query them, which opens the door to pre-emptive blocking, monitoring, registration, or sinkholing. None of that is guaranteed. A seed may be unknown, values may differ per sample, the generator may depend on data fetched elsewhere, and operators ship new versions. The practical question is whether the process can be reproduced reliably enough to get ahead of the next lookup set.
Sinkholing then changes the very evidence defenders were reading. A sinkhole is infrastructure under defender control, so a selected malicious domain resolves toward an observation or containment system instead of the operator’s. A generated name that used to return NXDOMAIN starts returning an address (sometimes through resolver policy rather than public DNS), and any detector leaning on failure rates loses one of its best signals at the exact moment defenders take control of part of the domain set. Response codes are evidence, not verdicts.
Reading the search in DNS telemetry
DGA activity leaves several traces, each with an innocent twin:
- An endpoint querying many domains rarely or never seen elsewhere
- Many candidates failing to resolve in a short span
- Labels sharing lexical or statistical fingerprints of one generator
- Queries arriving on a daily, hourly, or otherwise repeating schedule
- A few generated names resolving, then followed by connections from the same process
Browsers, endpoint agents, telemetry systems, content platforms, typo traffic, and service discovery all produce strange names or failed lookups, so no single signal convicts. MITRE’s DGA detection guidance combines domain structure, failed lookups, query rate, and process context rather than trusting an entropy threshold or an NXDOMAIN count.
A resolver can show that an endpoint tried hundreds of candidates before one resolved, and passive DNS can show when a candidate was first observed in its dataset and whether related names have been showing up elsewhere. That exposes the shape of a rendezvous strategy, sometimes before anyone has recovered the algorithm. What DNS can’t do alone is name the software that generated the candidates or prove why the endpoint connected to the one that resolved. That takes endpoint telemetry, malware analysis, and registration data joined to the DNS record.
Summary
A domain generation algorithm swaps a fixed rendezvous domain for a reproducible sequence of candidates. Malware and operator compute the same names from shared inputs, and DNS tells the endpoint which candidate currently leads somewhere useful.
The durable signal is the repeated search for infrastructure through generated names, not any particular flood of NXDOMAIN failures. The search shows up in DNS telemetry, but understanding who ran it and why almost always needs evidence from beyond DNS.