During the last Pihole-Update I went into a self-manufactured deadlock in DNS resolving. That was, because during the update of Pihole the DNS resolving by Pihole itself was interrupted, and the update script waited for DNS resolving to become available again, but that would not be the case until the update script was finished. So, this was a network design problem, because the Pihole gets its IP address and its DNS server from my router, als all other clients do too. But the router gives to all clients the Pihole as DNS resolver. For that reason, the Pihole was the DNS resolver for itself, what lead to the deadlock.

To solve this, I had to make some changes at the router, which is a barebone (Qotom Q330G4) running Ubuntu 24.04 server with iptabes and isc-dhcp-server.

First, I disabled the systemd-resolved mechanis as Kristof suggested in his blog:

# Create directory
sudo mkdir -p /etc/systemd/resolved.conf.d/
# Set permissions
sudo chmod 755 /etc/systemd/resolved.conf.d/
# Disable
printf "[Resolve]\nDNSStubListener=no\n" | sudo tee /etc/systemd/resolved.conf.d/noresolved.conf
# Restart systemd-resolved
sudo systemctl restart systemd-resolved.service

Then, I set up dnsmaq as DNS resolver with the following configuration:

# /etc/dnsmasq.conf
# Set up your local domain here    
domain=example.com

# Example: The option local=/localnet/ ensures that any domain name query which ends in .localnet will be answered if possible from /etc/hosts or DHCP, but never sent to an upstream server
# don't forward requests (andrewoberstar.com/blog/2012/12/30/raspberry-pi-as-server-dns-and-dhcp)
local=/example.com/

listen-address=192.0.2.254
resolv-file=/etc/dnsresolv.conf
log-facility=/var/log/dnsmasq.log
log-queries
no-negcache
#strict-order

# Use the hosts file on this machine
expand-hosts

Here, 192.0.2.254 is the IP adress of the router.
The resolv file reads

#/etc/dnsresolv.conf 
domain example.com
search example.com

#quad9
nameserver 9.9.9.10
# cloudflare
nameserver 1.1.1.1

With this configuration, the router can work as an auxiliary DNS resolver, i.e. for the Pihole itself - not to confuse with the upstream DNS resolver configured in Pihole, that are only used when Pihole is running! (It’s complicated, I know.)

But, to let the Pihole know that the router 192.0.2.254 is ready to serve it’s DNS requests, I had to configure the router’s DHCP setting accordingly:

#/etc/dhcp/dhcpd.conf
# LAN (Internal)
subnet 192.0.2.0 netmask 255.255.255.0 {
  interface enp2s0;
  option routers 192.0.2.254;
  option domain-name-servers 192.0.2.53;
  option broadcast-address 192.0.2.255;
  default-lease-time 43200;
  max-lease-time 43200;
}

[...]

host dns {
 hardware ethernet 00:53:af:ab:cd:ef;
 fixed-address 192.0.2.53;
 option domain-name-servers 192.0.2.254;
}

With this setup, the DNS resolver for queries coming from the Pihole machine (again, not to be confused with the upstream servers configured in Piholte itself) is the router’s dnsmasq, that in turn has i.e. Clouflare and quad9 configured as external upstream servers.

Thus, when Pihole is under update and needs DNS resolution during the process (or even during normal operation), the router will provide this.
Furthermore, the router can serve as a backup DNS resolver in case Pihole is not available for other reasons, only thing is to change option domain-name-serversfrom 192.0.2.53 to 192.0.2.254 in the router’s dhcpd configuration for the LAN subnet. There will be of course no DNS filtering then (except the upstram DNS server provides it), but the DNS resolving is always provided.