When /etc/hosts stops working after enabling systemd‑resolved: a step‑by‑step fix

Enabling systemd‑resolved is the go‑to way to get modern DNS features on recent distributions, but it can bite you when you forget a tiny detail.
The most common symptom: the entries in /etc/hosts no longer resolve, or worse, the system starts hitting a public DNS server that ignores the file entirely.
Usually it’s a mis‑configured NSS order, a stale symlink, or a permission slip.
Below is a practical, hands‑on walk‑through that covers the most common causes, shows how to diagnose each one, and gives you a clean fix that keeps your system secure and predictable.


Why /etc/hosts might break after enabling systemd‑resolved

systemd‑resolved acts as a local DNS stub resolver.
When it’s active, it listens on 127.0.0.53 and forwards queries to upstream servers.
The NSS library (libnss_systemd) decides whether a hostname should be looked up in /etc/hosts, in the local DNS cache, or sent to the network.
If the NSS order is wrong, or if systemd‑resolved is mis‑configured, the lookup path can skip /etc/hosts entirely.

Typical symptoms:

SymptomLikely cause
ping foo.local fails even though /etc/hosts contains 127.0.0.1 foo.localNSS order wrong, or /etc/hosts unreadable
dig foo.local returns an IP from a public DNS serversystemd‑resolved is not using /etc/hosts
systemd-resolve --status shows DNS Servers: 8.8.8.8 but you expect local resolutionsystemd‑resolved is configured to ignore /etc/hosts

Quick sanity check: DNS resolution path

Before diving into configuration files, confirm the current resolution path:

# Show the NSS order
cat /etc/nsswitch.conf | grep hosts

# Verify systemd‑resolved status
systemctl status systemd-resolved.service

The hosts line should look like:

hosts: files systemd mdns

If files is missing, /etc/hosts will never be consulted.
If systemd appears before files, the stub resolver will handle the query first and may ignore /etc/hosts depending on its own configuration.


Step 1: Verify systemd‑resolved status

systemctl is-enabled systemd-resolved
systemctl is-active systemd-resolved

If the service is disabled or inactive, /etc/hosts will work normally.
If it is enabled and active, proceed.

# Quick check that the stub listener is up
ss -ltnp | grep 127.0.0.53

You should see a line similar to:

LISTEN 0 128 127.0.0.53:53 0.0.0.0:* users:(systemd-resolve(1234))

If the listener is missing, the service is mis‑configured or crashed.
Restart it:

sudo systemctl restart systemd-resolved

Step 2: Check /etc/nsswitch.conf

Open the file:

sudo nano /etc/nsswitch.conf

The hosts line must contain files before systemd.
A typical line looks like:

hosts: files systemd mdns

If you see:

hosts: systemd files mdns

or files is omitted, edit it accordingly.
After editing, test:

getent hosts foo.local

If it still returns nothing, move on.


Step 3: Inspect /etc/systemd/resolved.conf

systemd‑resolved can be instructed to ignore /etc/hosts via the Cache=yes and DNSStubListener=yes options, but the critical flag is Domains= and LLMNR=.
Open the config:

sudo nano /etc/systemd/resolved.conf

Typical defaults:

[Resolve]
#DNS=
#FallbackDNS=
#Domains=
#LLMNR=no
#MulticastDNS=no
#DNSSEC=no
#Cache=yes
#DNSStubListener=yes

If you have uncommented Domains= with a value that excludes the local domain, or set LLMNR=no, the stub resolver may bypass /etc/hosts.
Comment out any custom lines or set them to default values.
After changes, reload:

sudo systemctl restart systemd-resolved

Step 4: Examine /etc/hosts content and permissions

The file must be readable by all users (0644) and owned by root.
Check:

ls -l /etc/hosts

Expected output:

-rw-r--r-- 1 root root  123 /etc/hosts

If permissions are wrong, fix them:

sudo chmod 644 /etc/hosts
sudo chown root:root /etc/hosts

Now verify the file contains the expected entries:

cat /etc/hosts

A minimal example:

127.0.0.1   localhost
127.0.1.1   my-hostname
192.168.1.10  myapp.local

If you added a line for a hostname that is also in /etc/hostname, ensure there is no conflict.


Step 5: Test with dig, nslookup, host

Use dig to see where the query is going:

dig @127.0.0.53 myapp.local +short

If you get 192.168.1.10, /etc/hosts is being used.
If you get an IP from an external DNS server, the stub resolver is ignoring the file.

nslookup can also show the server used:

nslookup myapp.local

The output should mention Server: 127.0.0.53.
If it shows a public IP, your system is bypassing systemd‑resolved.


Step 6: Reconfigure systemd‑resolved to respect /etc/hosts

If the stub resolver is still ignoring the file, force it to use /etc/hosts by editing the systemd-resolved service unit.

sudo systemctl edit systemd-resolved.service

Add the following override:

[Service]
ExecStart=
ExecStart=/lib/systemd/systemd-resolved --no-pager --no-

See also