Aiguillage DNS

Pour notre travail connecté, une bonne configuration réseau est importante. La mobilité croissante nous rends plus sensibles aux bricolages qui ne marchent qu'une fois. Un point particulier est la résolution des noms de domaines.

C'est courant d'avoir un domaine privé pour nommer les services internes, ceux qui ne sont pas dans le cloud ! On se contente souvent d'utiliser le serveur DNS fourni par l'entreprise pour toutes les requêtes DNS. Ça devient lourd quand on est en VPN et qu'on dépends de la qualité du VPN pour résoudre un simple google.com. Et comment gérer d'autres domaines comme .docker ou .lxc ?

Je vous propose de comprendre les divers éléments techniques pour aboutir au graal de la configuration DNS de votre station de travail !

resolv.conf

Votre Linux stocke dans /etc/resolv.conf les IP des serveurs DNS à interroger pour résoudre un nom de domaine. Le système va interroger chaque serveur, l'un après l'autre, jusqu'à ce qu'il obtienne une réponse positive ou négative.

C'est important de comprendre que le système essaye la deuxième adresse uniquement si la première ne répond pas au bout de 5 secondes (par défaut). C'est un peu comme si Firefox vous présentait automatiquement la page de recherche de Qwant lorsque duckduckgo ne répond plus. Si Qwant retourne 404, alors Firefox s'arrête.

Exemple d'erreur de configuration:

nameserver 9.9.9.9     # DNS public
nameserver 10.0.0.254  # DNS privé pour résoudre lan.acme.fr

Dans ce cas, 10.0.0.254 ne sera interrogé que lorsque vous n'aurez plus internet... Si vous demandez wiki.lan.acme.net, 9.9.9.9 répondra NXDOMAIN (domaine inexistant) et le système ne tentera pas d'interroger 10.0.0.254.

Qui écrit dans /etc/resolv.conf ?

Beaucoup de monde !! Dans le cas courant, votre client DHCP écrit les serveurs DNS fournis avec votre connexion réseau. Le client VPN peut aussi écraser la configuration. Lorsque vous coupez le client VPN, il ne va pas remettre gentilment la valeur précedente.

L'outil resolvconf essaie de pacifier cela. Chacun déclare le serveur DNS qu'il apporte dans /run/resolvconf/interface/ dans un fichier <interface_reseau>.<logiciel>. Par exemple eth0.dhclient ou tun0.openvpn. Le fichier /etc/resolvconf/interface-order priorise les sources. Regardons ce qu'il dit:

...
tun*
tap*
...
@(br|eth)*([^.]).inet6
@(br|eth)*([^.]).ip6.@(dhclient|dhcpcd|pump|udhcpc)
@(br|eth)*([^.]).inet
@(br|eth)*([^.]).@(dhclient|dhcpcd|pump|udhcpc)
...

En bon français, les serveurs DNS de VPN (tun0, etc.) ont la priorité sur ceux fournis par le client DHCP. Là ou resolvconf devient vraiment pertinent, c'est lorsque le client VPN s'arrête, il met à jour la configuration avec serveur DNS du client DHCP.

Il suffit d'installer resolvconf et de relancer son client DHCP pour que tout cela fonctionne, la configuration par défaut est largement suffisante. resolvconf est souvent installé par défaut.

Aiguillage

Maintenant qu'on a résolu la guerre du /etc/resolv.conf, ça serait bien de demander au bon serveur. C'est ce que j'appelle l'aiguillage. Pour cela, nous allons utiliser la délégation de zone de dnsmasq.

dnsmasq est un serveur combiné DHCP et DNS. Il est notamment utile pour créer un réseau local pour ses machines virtuelles ou ses conteneurs LXC. En considérant le routage et le DNS comme les deux fonctionnalités essentielles d'un réseau, on comprend l'intérêt d'associer les deux services dans un seul serveur.

Par défaut, dnsmasq relaie simplement les requêtes DNS aux serveurs DNS publics renseignés dans resolvconf. L'option server permet de surcharger resolvconf. Exemple.

# Utiliser Quad9 plutôt que le serveur DNS du FAI à la maison, du réseau privé
# pro, du Wifi de l'hôtel, etc.
server=9.9.9.9

L'option server permet surtout d'associer un domaine à un serveur particulier. Voilà ce que nous cherchons !

# Pour lan.acme.net, utiliser l'IP du serveur DNS du LAN (éventuellement en VPN).
server=/lan.acme.net/10.0.140.254
# Sinon, demander à Quad9.
server=9.9.9.9

Et voilà. dnsmasq sert non seulement de cache, mais également d'aiguilleur de requêtes DNS. Maintenant, on peut facilement envisager d'ajouter les lignes server=/lxc/..., server=/docker/..., server=/guests/.... ! La prochaine étape est de disposer de ces serveurs résolvant les noms en .lxc, .docker, .guests, etc. À suivre !