Je suis Charlie

Autres trucs

Accueil

Seulement les RFC

Seulement les fiches de lecture

Mon livre « Cyberstructure »

Ève

IPv6 chez OVH, c'est bizarre

Première rédaction de cet article le 17 mars 2023


Si vous avez déjà créé/géré une machine virtuelle chez OVH, vous avez sans doute noté la bizarrerie de la configuration IPv6. En fait, la configuration automatiquement installée lorsque vous créez votre machine est incorrecte. Voici pourquoi, et comment la réparer.

Créons d'abord un serveur (j'ai utilisé l'API OpenStack mais le problème existait déjà avant).


%    ip -6 addr show
...
2: ens3: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 state UP qlen 1000
    inet6 2001:41d0:801:1000::233c/56 scope global 
       valid_lft forever preferred_lft forever
    inet6 fe80::f816:3eff:fe10:748f/64 scope link 
       valid_lft forever preferred_lft forever

  

La machine a une adresse IPv6, 2001:41d0:801:1000::233c, dans un préfixe de longueur 56. Chic, je me dis, je vais pouvoir parler directement (sans passer par le routeur) avec les autres machines dans ce même préfixe. La table de routage va d'ailleurs en ce sens :

%    ip -6 route show
...
2001:41d0:801:1000::/56 dev ens3 proto kernel metric 256 pref medium
default via 2001:41d0:801:1000::1 dev ens3 metric 1 pref medium
  

Elle nous dit que tout le /56 est joignable sans intermédiaire (pas de via). Essayons depuis la 2001:41d0:801:1000::23b2 :

%  ping -c 3 2001:41d0:801:1000::233c
PING 2001:41d0:801:1000::233c(2011:41d0:801:1000::233c) 56 data bytes
From 2001:41d0:801:1000::23b2 icmp_seq=1 Destination unreachable: Address unreachable
...
--- 2001:41d0:801:1000::233c ping statistics ---
3 packets transmitted, 0 received, 100% packet loss, time 2030ms
  

Aïe, c'est raté, alors que les deux machines sont bien dans le même préfixe de longueur 56. Pourquoi ? Parce que les machines ne sont pas réellement sur un réseau local dont le préfixe ferait 56 bits. Elles doivent en fait toujours passer par le routeur, comme si elles étaient sur une liaison point-à-point avec ce routeur. (Pour la même raison, un tcpdump ne montrera pas de trafic, à part avec le routeur, par exemple du trafic NTP.)

Pour que cela marche, il faut renoncer à parler directement avec les machines proches, et corriger la configuration. Ce sont des Debian, on va éditer le fichier /etc/network/interfaces.d/50-cloud-init et remplacer la longueur incorrecte (56) par la bonne (128). Et on n'oublie pas de rajouter une route vers le routeur avant de définir la route par défaut. On redémarre et ça marche :

% ping -c 3 2001:41d0:801:1000::233c
PING 2001:41d0:801:1000::233c(2001:41d0:801:1000::233c) 56 data bytes
64 bytes from 2001:41d0:801:1000::233c: icmp_seq=1 ttl=57 time=0.810 ms
64 bytes from 2001:41d0:801:1000::233c: icmp_seq=2 ttl=57 time=0.746 ms
64 bytes from 2001:41d0:801:1000::233c: icmp_seq=3 ttl=57 time=0.764 ms

--- 2001:41d0:801:1000::233c ping statistics ---
3 packets transmitted, 3 received, 0% packet loss, time 2037ms
rtt min/avg/max/mdev = 0.746/0.773/0.810/0.026 ms

Et la table de routage nous montre que tout va passer par le routeur :

% ip -6 route show
...
2001:41d0:801:1000::1 dev ens3 metric 1 onlink pref medium
2001:41d0:801:1000::233c dev ens3 proto kernel metric 256 pref medium
default via 2001:41d0:801:1000::1 dev ens3 metric 1 pref medium

Il est dommage qu'on ne puisse pas parler directement aux autres machines du même préfixe. Peut-être est-ce pour des raisons de sécurité, ces machines pouvant appartenir à des organisations différentes ? C'est en effet la même chose en IPv4 mais, cette fois, avec une configuration par défaut qui est correcte (un préfixe de longueur 32).

Si vous créez beaucoup de machines virtuelles et qu'on vous n'avez pas envie de tout corriger à la main, et que, comme moi, vous utilisez Ansible, voici un playbook qui fait les choses plus ou moins proprement :


---
- hosts: coursipv6
  become: yes
  become_method: sudo
  tasks:
    - name: Broken IPv6 config at OVH
      lineinfile: 
        path: /etc/network/interfaces.d/50-cloud-init
        regexp: 'address {{ ipv6_address }}/56$' 
        line: 'address {{ ipv6_address }}/128'
        backrefs: yes

    - name: Broken IPv6 routing at OVH
      lineinfile: 
        path: /etc/network/interfaces.d/50-cloud-init
        regexp: 'route add -A inet6 default gw {{ ipv6_gateway }} || true$'
        line: '\tpost-up ip -6 route add {{ ipv6_gateway }} dev ens3 && route add -A inet6 default gw {{ ipv6_gateway }} || true'
        backrefs: yes

Version PDF de cette page (mais vous pouvez aussi imprimer depuis votre navigateur, il y a une feuille de style prévue pour cela)

Source XML de cette page (cette page est distribuée sous les termes de la licence GFDL)