English version

Trucs et astuces pour /etc/resolv.conf sous GNU/Linux

Par défaut, la résolution DNS est faite en utilisant la couche transport UDP. J'ai cependant remarqué que sur un certain réseau avec connexion WiFi, cela aboutit souvent à un timeout de 5 secondes avant que la résolution soit automatiquement réessayée, quel que soit les serveurs DNS, y compris le serveur DNS fourni par le modem-routeur ADSL. J'obtenais parfois deux timeout à la suite, si bien que la résolution DNS pouvait prendre 10 secondes! Ce problème est aggravé par le fait que GNU/Linux n'utilise pas de cache DNS local par défaut.

J'ai donc voulu essayer le DNS avec la couche transport TCP. Pour cela, on peut utiliser l'option use-vc, non documentée. Cependant tous les serveurs DNS ne supportent pas TCP, et en particulier, cela ne marchait pas avec le serveur DNS du modem-routeur ou ceux du FAI. Heureusement, cela marche avec Google Public DNS. Voici le fichier /etc/resolv.conf correspondant:

options use-vc
nameserver 8.8.8.8
nameserver 8.8.4.4

Ensuite, on peut vouloir utiliser cette configuration (ou une autre) uniquement sur certains réseaux donnés. Alors que certains outils de gestion réseau permettent de spécifier les serveurs de noms pour des réseaux donnés, je n'ai pas vu de façon de donner des options comme use-vc. Il y a plusieurs solutions alternatives. Sauf mention contraire, on suppose que resolvconf n'est pas utilisé, sinon il peut y avoir des conflits. Même chose pour les caches DNS locaux.

Maintenant, pour DHCP (cas habituel), il y a un autre problème: le fichier /etc/resolv.conf est normalement réécrit quand le bail est renouvelé, ce qui signifie que la configuration de l'utilisateur faite ci-dessus est écrasée. Pour le client DHCP de l'Internet Software Consortium, une solution est d'empêcher ceci sur les réseaux concernés en redéfinissant la fonction shell make_resolv_conf dans un enter hook script pour RENEW.

Voici un exemple de hook script DHCP pour BOUND et RENEW (il est peut-être nécessaire d'ajouter d'autres raisons, mais elles ne se produisent pas chez moi, si bien que je n'ai pas pu les tester), à utiliser à la fois en tant qu'enter hook script et exit hook script. La fonction make_resolv_conf est exécutée par dhclient-script juste après les enter hook scripts; pour BOUND, quand ce script est exécuté en tant qu'exit hook script, on fait la même chose et on exécute cette fonction.

#!/bin/sh

if [ ! -L /etc/resolv.conf ]; then

  logger "$1 with reason=$reason"

  # the MAC address of the router
  mac=00:1f:33:89:73:4e

  case "$reason" in
    BOUND)
      # The ping has an effect to fill the ARP table "/proc/net/arp".
      # This trick is inspired by:
      #   https://www.debian-fr.org/serveur-dns-timout-resolv-conf-et-dhclient-t24401.html
      # In 2015-08, this was working as an enter hook, but in 2016-08,
      # the ping fails (ditto with arping, after trying various options).
      # So, this script should be used as an exit hook too.
      ping -n -c 1 -I "$interface" "$new_routers" > /dev/null
      if grep -i -q $mac /proc/net/arp; then
        logger "Google Public DNS with TCP to avoid recurrent timeout"
        make_resolv_conf()
        {
          logger "creating /etc/resolv.conf (Google Public DNS with TCP)"
          cat > /etc/resolv.conf <<EOF
options use-vc
nameserver 8.8.8.8
nameserver 8.8.4.4
EOF
        }
        case $1 in
          */dhclient-exit-hooks.d/*) make_resolv_conf;;
        esac
      fi
      ;;
    RENEW)
      case $1 in
        */dhclient-enter-hooks.d/*)
          if grep -i -q $mac /proc/net/arp; then
            logger "do not overwrite /etc/resolv.conf"
            make_resolv_conf() { : ; }
          fi;;
      esac
      ;;
  esac

fi

Note: pour le cas RENEW, au lieu de tester l'adresse MAC, on peut aussi tester la présence d'un certain texte dans le fichier /etc/resolv.conf, e.g. do not overwrite on lease renewal, si un tel texte a été écrit à la création du fichier.



webmaster@vinc17.org