TinyDNS tinydns.org

How DNS resolves a name, and how the servers that do it are run.

Follow it down

What a resolver is really doing

Two adult engineers at a bench of network gear with a laptop between them
Each step of a lookup is answered by a machine that knows one thing: who to ask next.Photograph

The machine that holds the conversation

A recursive resolver is the piece of DNS infrastructure most operators never think about until it fails. Stub resolvers — the tiny client-side shims inside every operating system — do almost nothing: they hand a name to whatever address sits in /etc/resolv.conf and wait. The recursive resolver is the machine that actually does the work, and the work is more intricate than "look it up and return the answer."

The moment a query arrives, the resolver must decide whether it already holds a usable cached answer. If it does, TTL arithmetic governs: the record's original time-to-live, minus the seconds already spent, is the value a client receives. The countdown does not reset when a new query arrives; the countdown started the moment the resolver got the answer, and it runs whether anyone asks again or not. Under normal operation a record is never served once its TTL has run out, though some resolvers can be configured to serve expired records deliberately while they refresh them.

When the cache is cold, the resolver walks the delegation tree. It starts from a root hint — a locally configured set of root server addresses — and issues a query to one of the thirteen root addresses. The answer it gets back is not the record it wants but a referral: a list of TLD nameservers and, usually, glue records to reach them. The resolver follows the chain, one label at a time, until it reaches an authoritative server that either answers or issues an NXDOMAIN. Every referral response is itself cached at whatever TTL the parent zone specified for the delegation, which means a resolver working through a cold cache may make five or six separate UDP exchanges before it satisfies a single client query.

A patch panel with numbered ports and neatly combed fibre looms
Numbered ports are a name’s last hop. Everything above them is a chain of referrals that exists only as records in other people’s zones.Photograph

State, retries, and trust

What separates a resolver from a simple forwarder is that it keeps state across all of this. It tracks which servers it has already tried, notes which ones timed out, and implements retry logic independently of anything the client does. The client's stub typically has its own timeout — often a few seconds — but the resolver may be mid-walk when that clock expires; it will often continue the walk anyway, so the next client query for the same name arrives at a resolver already partway to the answer.

Resolver implementations differ meaningfully in how they handle failure. BIND, maintained by ISC ↗, uses a fetch-limits mechanism that deprioritises servers that have been slow or unresponsive, spreading load across a zone's nameserver set rather than hammering one. Unbound, developed at NLnet Labs, tracks RTT per server and selects the fastest known address first, a behaviour documented in its own design notes. These are operational choices with real consequences: a resolver that retries aggressively against a lame delegation can sustain high query rates against a misconfigured zone for as long as negative caching has not yet filled in.

Negative answers are cached too, under the parameters carried in the zone's SOA record — specifically the MINIMUM field, which RFC 2308 ↗ redefined in 1998 to govern negative TTL rather than the minimum TTL of all records. A resolver that has cached an NXDOMAIN will serve it to every subsequent client for the duration of that TTL, regardless of whether the zone has since been corrected. This is the mechanism behind the frustrating experience of "I added the record, why can't anyone see it?" — the answer is already cached, and the cache is working correctly.

Trust is the third dimension. A resolver that has validated DNSSEC signatures has cryptographic confirmation that each delegation step was authorised by the zone above it, and that the final answer was produced by the key the zone published. One that has not may be feeding clients data it received over UDP from an address it cannot verify. DNSSEC validation is a resolver-side decision: the authoritative servers publish the signatures, but it is the resolver that checks them and decides whether to set the AD bit in its response or return SERVFAIL.

A resolver, then, is not a lookup service. It is a state machine that walks a delegation tree, manages a cache with per-record lifetimes, implements retry and failover logic, and makes a trust decision for every answer it promotes from in-flight query to cached fact. Most of the interesting failure modes in DNS live here, not in the authoritative servers.

A resolver that has cached an NXDOMAIN will serve it to every subsequent client for the duration of that TTL, regardless of whether the zone has since been corrected.

A machine room seen down a cold aisle, one adult operator standing mid-row with an open laptop
A cold aisle holds the machines that answer. The walk described here crosses several rooms like this one, none of which knows what the others hold.Photograph

If it does, TTL arithmetic governs: the record's original time-to-live, minus the seconds already spent, is the value a client receives.

Read next, in this section