Configurer un VPN Wireguard

Publié le 29/07/2023 et écrit par Vincent Finance, dans la catégorie : #infra

Contexte de cet article

En plus de mes machines locales, je possède plusieurs serveurs virtuels (ou VPS), afin d'assurer une bonne redondance pour mes DNS et mes serveurs mails en cas de panne réseau. Pour autant, cela me demande d'effectuer de la surveillance sur ces machines et je n'avais pas envie d'exposer mes sondes directement sur Internet. J'ai donc choisi de mettre en place un VPN entre mes machines extérieures et mon routeur, afin que seul le trafic interne passe par une interface sécurisée. La technologie que j'ai retenue est Wireguard, par sa simplicité d'utilisation, sa compatibilité avec l'ensemble de mes systèmes et sa robustesse.
Je vais également en profiter pour me créer un deuxième accès VPN qui sera utilisé par plusieurs machines lors de mes déplacements, en l'occurrence mon PC portable et mon iPhone.

Réseaux à mettre en place

Ici, je vais mettre en place deux interfaces de VPN :

Vu le nombre de machines à connecter, un serveur DHCP ne sera pas nécessaire et les IP des clients seront définies à la main.

Prérequis

Pour cette installation, voici les éléments nécessaires :

Mise en place du serveur

Mikrotik fournit nativement un module pour utiliser Wireguard sous RouterOS. Il est activé par défaut et il peut se configurer via l'interface graphique ou via la console. Ici, nous allons nous concentrer sur l'usage de la console pour des raisons de simplicité.

On commence par créer deux interfaces réseaux dédiées à Wireguard et ajouter deux adresses IP pour définir les futurs préfixes de nos clients :

/interface wireguard add name=wg0 listen-port=60002
/interface wireguard add name=wg1 listen-port=60001

/ip address add address=172.16.0.1/24 interface=wg0
/ip address add address=172.16.10.1/24 interface=wg1

On affiche ensuite les informations des interfaces avec la commande print pour récupérer la clé publique du serveur. Cela nous servira par la suite pour préparer la configuration de nos clients :

[vinishor@mikrotik] /interface/wireguard> /interface/wireguard print
Flags: X - disabled; R - running
 0  R name="wg0" mtu=1492 listen-port=60002 private-key="cleprivee="
      public-key="masuperclepublique="

 1  R name="wg1" mtu=1492 listen-port=60001 private-key="cleprivee2e="
      public-key="ma2esuperclepublique="

On passe maintenant à la partie pare-feu. Le but est alors d'ouvrir les ports dédiés à Wireguard et autoriser le passage du trafic du VPN. Je vais aussi en profiter pour autoriser le VLAN 10, réservé à mes serveurs maison, à aller vers les machines du VPN d'infrastructure, pour que la machine de monitoring puisse aller interroger les sondes de surveillance.
Les adresses IP des serveurs externes étant fixes, on peut aussi mettre en place une liste pour limiter l'accès au VPN d'infra à ces seules adresses.

Cela donne donc les commandes suivantes :

/ip/firewall/address-list
add list=wg-infra address=172.16.10.0/24
add list=wireguard address=172.16.0.0/24
add list=allowed-servers address=45.xx.xx.xx/32
add list=allowed-servers address=46.xx.xx.xx/32
add list=allowed-servers address=89.xx.xx.xx/32
add list=allowed-servers address=46.yy.yy.yy/32

/ip/firewall/filter
add chain=input action=accept protocol=udp dst-port=60001 src-address-list=allowed-servers
add chain=input action=accept protocol=udp dst-port=60002
add chain=forward action=accept src-address-list=wg-infra
add chain=forward action=accept src-address-list=vlan10 dst-address-list=wg-infra
add chain=forward action=accept src-address-list=wireguard

Ajouter un client sur l'interface du serveur (peer)

Le protocole de Wireguard impose d'ajouter des deux côtés les machines qui souhaitent communiquer entre elles. Cela évite ainsi d'échanger des mots de passe ou tout autre donnée en clair sur le réseau. Dans cette section, je vais donc vous donner les instructions pour ajouter un client sur l'interface voulue. Il est possible de jouer la commande plusieurs fois, en fonction du nombre de clients à rajouter.

Il est aussi nécessaire de connaître la clé publique du client pour l'ajouter correctement (je vous expliquerai par la suite comment faire pour la générer).

Pour ajouter un client sur l'interface wireguard, on entre la commande suivante :

/interface/wireguard/peers
add allowed-address=172.16.10.2/32 endpoint-port=60001 interface=wg1 public-key="zzzzzzzzzzzz"
# Si on l'ajoute sur la deuxième interface
add allowed-address=172.16.0.6/32 interface=wg0 public-key="uuuuuuuuuuuuuuuuuuuuuuuu"

L'option endpoint-port permet de choisir le port dédié à wireguard sur le client. Cela peut être pratique sur un serveur, afin d'ouvrir le strict nécessaire au niveau du pare-feu. On peut aussi spécifier une adresse précise en rajoutant l'option endpoint-address.
Dans le cas de mon VPN de gestion, je ne spécifie ni le port, ni l'adresse, car les smartphones utilisent souvent des adresses provenant d'un CG-NAT et leur pare-feu n'est pas facilement contrôlable. C'est bien le couple de clés que l'on indique dans la configuration qui permet l'authentification de l'accès et qui assure la sécurité.

Mise en place des clients

Maintenant que le serveur est en place, nous allons connecter nos machines clientes, afin que celles-ci puissent communiquer entre elles et avec les autres machines situées sur mon réseau à la maison.

Exemples pour un serveur à surveiller

Sous Debian GNU/Linux

Installer Wireguard avec l'aide de apt :

$ sudo apt install wireguard-tools

Générer les clés privée et publique du client pour pouvoir se connecter par la suite :

$ sudo -i
# mkdir /etc/wireguard && cd /etc/wireguard
# wg genkey | tee privatekey | wg pubkey > publickey

Créer un fichier de configuration pour l'interface dédiée à Wireguard en ajoutant les paramètres pour se connecter au serveur :

# cat << EOF > /etc/wireguard/wg0.conf
[Interface]
Address = 172.16.10.2/24
SaveConfig = true
ListenPort = 60001
PrivateKey = xxxxxxxxxxxxxx # cat privatekey

[Peer]
PublicKey = yyyyyyyyyy # clé publique du serveur Wireguard (obtenue avec /interface/wireguard print)
AllowedIPs = 172.16.10.0/24,10.10.10.0/24
Endpoint = x.x.x.x:60001 # Adresse publique du routeur
EOF

Importer la configuration en utilisant l'utilitaire wg-quick, vu que l'option SaveConfig sauvegardera cette dernière pour les prochains redémarrages de la machine :

# wg-quick up wg0

La commande rajoute alors une nouvelle interface réseau et initie la connexion avec le routeur Mikrotik pour monter le VPN. Pour vérifier que tout fonctionne, on peut lister les interfaces réseaux et essayer de faire un ping vers une machine située sur le réseau local :

$ ip -c a show
...
8: wg0: <POINTOPOINT,NOARP,UP,LOWER_UP> mtu 1420 qdisc noqueue state UNKNOWN group default qlen 1000
    link/none 
    inet 172.16.10.5/24 scope global wg0
       valid_lft forever preferred_lft forever


$ ping -c 1 10.10.10.10
PING 10.10.10.10 (10.10.10.10) 56(84) bytes of data.
64 bytes from 10.10.10.10: icmp_seq=1 ttl=63 time=18.6 ms

--- 10.10.10.10 ping statistics ---
1 packets transmitted, 1 received, 0% packet loss, time 0ms
rtt min/avg/max/mdev = 18.629/18.629/18.629/0.000 ms

Sous OpenBSD

Installer Wireguard avec l'aide de pkg_add :

$ doas pkg_add wireguard-tools

Générer les clés privée et publique pour pouvoir se connecter par la suite :

$ su
# mkdir /etc/wireguard && cd /etc/wireguard
# wg genkey | tee privatekey | wg pubkey > publickey

Créer un fichier de configuration dédié à Wireguard en ajoutant les paramètres pour se connecter au serveur :

# cat << EOF > /etc/wireguard/wg0.conf
[Interface]
ListenPort = 60001
PrivateKey = xxxxxxxxxxxxxx # cat privatekey

[Peer]
PublicKey = yyyyyyyyyy # clé publique du serveur Wireguard (obtenue avec /interface/wireguard print)
AllowedIPs = 172.16.10.0/24,10.10.10.0/24
Endpoint = x.x.x.x:60001 # Adresse publique du routeur
EOF

Créer un fichier de configuration pour l'interface réseau en indiquant le chemin du fichier de configuration de Wireguard et en ajoutant la route réseau nécessaire pour le préfixe du VLAN 10 :

# vi /etc/hostname.wg0
inet 172.16.10.3 255.255.255.0
up
!/usr/local/bin/wg setconf wg0 /etc/wireguard/wg0.conf
!/sbin/route add 10.10.10.0/24 172.16.10.3

Initialiser l'interface réseau :

# sh /etc/netstart wg0

La commande rajoute alors une nouvelle interface réseau et initie la connexion avec le routeur Mikrotik pour monter le VPN. Pour vérifier que tout fonctionne, on peut lister les interfaces réseaux et essayer de faire un ping vers une machine située sur le réseau local :

$ ifconfig
...
wg0: flags=80c3<UP,BROADCAST,RUNNING,NOARP,MULTICAST> mtu 1420
        index 6 priority 0 llprio 3
        wgport 60001
        groups: wg
        inet 172.16.10.3 netmask 0xffffff00 broadcast 172.16.10.255


$ ping -c 1 10.10.10.10
PING 10.10.10.10 (10.10.10.10): 56 data bytes
64 bytes from 10.10.10.10: icmp_seq=0 ttl=64 time=21.077 ms

--- 10.10.10.10 ping statistics ---
1 packets transmitted, 1 packets received, 0.0% packet loss
round-trip min/avg/max/std-dev = 21.077/21.077/21.077/0.000 ms

Exemple pour un client "classique"

iPhone

Dans cet exemple, je vais relier mon smartphone à mon réseau local, afin d'avoir accès à mes machines internes et toute autre ressource non exposée sur Internet. Pour mettre en place la configuration sur le smartphone, je vais générer un fichier de configuration sur un ordinateur et le convertir en code QR pour l'utiliser sur le téléphone.

Étant sous Fedora Linux, je peux utiliser les outils de Wireguard pour générer un fichier :

$ mkdir wireguard && cd wireguard # dans mon $HOME
$ wg genkey | tee privatekey | wg pubkey > publickey
$ cat << EOF > wg-iphone.conf
[Interface]
PrivateKey = xxxxxxxxxxxxxx # cat privatekey
Address = 172.16.0.2/24

[Peer]
PublicKey = yyyyyyyyyy # clé publique du serveur Wireguard (obtenue avec /interface/wireguard print)
AllowedIPs = 172.16.0.0/24,10.10.10.0/24
Endpoint = x.x.x.x:60002 # Adresse publique du routeur
EOF

Une fois le fichier prêt, on peut utiliser le programme qrencode pour générer un code QR contenant la configuration du VPN pour notre iPhone :

$ sudo dnf install qrencode
$ qrencode --type=UTF8 --read-from=wg-iphone.conf

Installer ensuite l'application officielle via l'App Store d'Apple sur l'iPhone et ouvrir l'application. Appuyer sur le bouton Ajouter un tunnel et choisir l'option Créer à partir d'un QR code. Confirmer l'autorisation pour la caméra et scanner le code QR affiché dans le terminal. Nommer le tunnel et appuyer sur Sauvegarder en validant l'autorisation pour ajouter un VPN.

Le VPN est maintenant prêt à être utilisé. En tapant sur le bouton dans l'application, la connexion s'active et une petite icône VPN s'affiche tout en haut de l'écran de l'iPhone. On a désormais accès aux ressources locales !

Conclusion

Simplicité et rapidité de mise en place sont les deux grands avantages de Wireguard. J'ai pu ainsi mettre en place un système complet pour accéder à mon réseau local en déplacement et avoir un bon système de monitoring sans tout exposer directement sur Internet.

Le prochain article en lien avec celui-ci traitera justement de la mise en place de ma solution de monitoring à base de Netdata, de Prometheus et de Grafana.


Sources pour la rédaction de cet article :


Un commentaire à ajouter ?

Pour ajouter votre commentaire, envoyez directement un mail ici