Serveur wireguard

De Le Wiki du Forum-Debian.fr
Aller à la navigation Aller à la recherche

VPN wireguard pour Debian Bullseye


par Petitchat


Introduction

Wireguard a été intégré dans le noyau Linux depuis mars 2020. C'est dire le succès de ce VPN. Fiable, rapide, bien sécurisé, facile à configurer...Cela devient évident de chiffrer ses données dans un tunnel pour rejoindre un réseau virtuel ou/et partager une adresse IP.

Prérequis et conventions pour le tuto

  • Une machine Debian en guise de serveur Wireguard avec les droits administrateurs
  • Pour les tests une machine connectée à Internet en dehors du réseau local, de n’importe quelle plate-forme, nécessaire comme client
  • Savoir mettre en place un routage NAT sur sa box
  • L'adresse IP publique de la box est 87.65.43.21
  • le serveur vpn est dans un réseau physique de classe C, par exemple ici le réseau 192.168.15.0/24 et on fixe son adresse à 192.168.15.2

Installation

On met à jour les dépots apt :

sudo apt update

On installe simplement :

apt install wireguard

Puis nous créons un espace de travail: sur le Bureau le dossier "wireguard" et dans le dossier wireguard les dossiers "serveur" et "utilisateurs".

cd Bureau

mkdir wireguard ; cd wireguard ; mkdir serveur; mkdir utilisateurs

Génération des clés du serveur

On se place dans le dossier "serveur"

cd serveur

Nous allons créer une clé privée. Comme il s'agit d'un fichier secret, la commande wg nous force à utiliser la commande umask afin de restreindre les droits en lecture pour ce fichier.

umask 077

sudo wg genkey > wg-private.key

créer une clé publique avec la clé privée

sudo wg pubkey < wg-private.key > wg-public.key

Paramétrage de l'interface virtuelle

Wireguard fonctionne avec une interface réseau virtuelle qu'il faut paramétrer en créant, avec les droits administrateur, un fichier configuration. Wireguard utilise un format de nommage particulier pour ce fichier: <nom_de_l'interface>.conf. Nous nommons le fichier "wg0.conf" ainsi le nom de l'interface virtuelle sera "wg0".

sudo nano /etc/wireguard/wg0.conf

Nous y collons ce paramétrage:

# define the WireGuard services
[Interface]
Address = 10.0.15.1/24

# contents of file wg-private.key that was recently created
PrivateKey = UKXwwKH+p2tNrZLzRI7TLyoAjoPUE2NC243lQVluBVU=

# UDP service port; 51820 is a common choice for WireGuard
ListenPort = 51820

PostUp = iptables -A FORWARD -i %i -j ACCEPT; iptables -t nat -A POSTROUTING -o <interface> -j MASQUERADE

PostDown = iptables -D FORWARD -i %i -j ACCEPT; iptables -t nat -D POSTROUTING -o <interface> -j MASQUERADE

Attention !!! il faut remplacer <interface> par le nom de l'interface physique. Pour connaître le nom de cette interface on peut utiliser la commande:

ip -o -4 route show to default | awk '{print $5}'

Dans mon cas l'interface s'appelle "ens33"

Explications des paramètres:

  • <Address>, ici il faut choisir un réseaux de classe C, dans cet exemple le réseau 10.0.15.0/24. Il faut aussi choisir l'adresse du serveur wireguard dans le réseau, dans cet exemple de digit 1. Ce qui donne 10.0.15.1/24. Il faut choisir un sous réseau différent de son réseau local usuel, elle pourront quand même atteindre les machines du réseau local (dans mon cas 192.168.15.0/24).
  • <PrivateKey>, précise la clef privée du serveur, c'est une donnée secrète.
  • <ListenPort>, précise le port d'écoute du serveur, si on passe par une box il faut faire un routage NAT vers ce port.
  • <PostUp>, ajoute une règle de routage lorsque l'interface virtuelle démarre. La règle de routage redirige le traffic de l'interface physique vers l'interface virtuelle du vpn.
  • <PostDown>, supprime la règle de routage losque l'interface est éteinte.

Paramétrages réseau

A propos de règles de routage, on a besoin d'iptables, si ce n'est pas déjà fait il faut l'installer:

apt install iptables

et il faut l'activer iptables avec cette commande:

systemctl enable iptables

A ce stade on peut tester la configuration avec la commande

sudo wg-quick up wg0

Si la configuration de wg0.conf ne contient pas d'erreur on devrait obtenir ceci:

[#] ip link add wg0 type wireguard
[#] wg setconf wg0 /dev/fd/63
[#] ip -4 address add 10.0.15.1/24 dev wg0
[#] ip link set mtu 1420 up dev wg0
[#] iptables -A FORWARD -i wg0 -j ACCEPT; iptables -t nat -A POSTROUTING -o ens33 -j MASQUERADE

on peut maintenant voir l'interface, un

sudo wg show wg0

donne ceci:

interface: wg0
  public key: kjuD10RMEyU8eNYVnQNrBXx6StrokXg9fUKt4rDI4RU=
  private key: (hidden)
  listening port: 51820

On ferme l'interface proprement ainsi:

sudo wg-quick down wg0

L'activation du routage IPv4 se fait également dans le fichier /etc/sysctl.conf qu'il faut éditer et vérifier que cette directive est activée:

net.ipv4.ip_forward = 1

On peut vérifier que le changement est pris en compte avec la commande:

cat /proc/sys/net/ipv4/ip_forward

qui renvoie "1" si elle est activée.

désactiver networking.service sinon il rentre en conflit avec wg-quick qui le remplace:

sudo systemctl disable networking.service

Les utilisateurs du parefeu UFW pourront entrer cette règle:

sudo ufw allow 51820/udp

Retour à l'interface réseau

Debian reconnaît aussi un service qui permet de contrôler l'interface virtuelle. Il s'agit de wg-quick@<nom_interface>.service, donc pour nous wg-quick@wg0.service. Nour allons maintenant rendre les changements permanents au démarrage:

sudo systemctl enable wg-quick@wg0.service

On peut lancer le service ainsi:

sudo systemctl start wg-quick@wg.service

ce qui démarre l'interface virtuelle mais sans les messages.

On peut arrêter le service avec la commande:

sudo systemctl stop wg-quick@wg0.service

Et s'il y a lieu, le redémarrer:

sudo systemctl restart wg-quick@wg0.service

Pour surveiller l'état du service on pourra utiliser la commende « status » :

sudo systemctl status wg-quick@wg0.service

Il est également possible de voir l’historique de la création de l'interface en consultant le journal:

journalctl -u wg-quick@wg0.service

Malheureusement ces commandes ne donnent pas d'information sur les connexions des pairs. Pour cela il faut paramétrer un système de journalisation plus poussé.

La dernière étape du paramétrage réseau consiste à établir un routage NAT du port 51820 vers notre serveur wireguard d'adresse IP privée 192.168.15.1.

Coté client

Dans cette exemple nous allons créer manuellement une connexion pour l'utilisateur Sigmund. On lui créé un dossier dans le répertoire /wireguard/utilisateur et on se place dans ce dossier.

cd utilisateur

sudo mkdir sigmund

cd sigmund

Comme pour le serveur nous allons générer une paire de clés publique/privée.

D'abord la clé privée:

umask 077

sudo wg genkey > wg-sigmund-private.key

Puis une clée publique avec la clée privée:

sudo wg pubkey < wg-sigmund-private.key > wg-sigmund-public.key

Ceci fait nous allons créer le fichier configuration du client Sigmund. Editons le fichier "wgsigmund.conf":

sudo nano wgsigmund.conf

on y ajoute le paramétrage suivant:

[Interface]
PrivateKey = <clef privée de sigmund>
Address = 10.0.15.2/32

[Peer]
PublicKey = <clef publique du serveur>
AllowedIPs = 10.0.15.0/24, 192.168.15.0/24
Endpoint = 87.65.43.21:51820
PersistentKeepalive = 25

Explication des paramétres:

Le fichier contient deux sections:

La section [Interface]

  • <PrivateKey>, ici il faut reporter la clé privée du client. Pour le faire il est pratique d'ouvrir une deuxième console, de se placer dans le dossier "sigmund" et de lancer la commande:

sudo cat wg-sigmund-private.key

  • <Address>, l'adresse de l'interface client dans le sous réseau du vpn. 10.0.15.1 est prise par le serveur, on peut prendre l'adresse suivante qui est 10.0.15.2. "/32" est la notation cidr pouor une adresse IP.

La section [Peer]

  • <PublicKey>, il faut reporter ici la clée publique du serveur (de la même façon qu'on a reporter plus haut la clé privée du client)
  • <AllowedIPs>, ce paramètre corresponds aux réseaux que pourra atteindre le client. 10.0.15.0/24 est le sous réseau du vpn, le client pourra joindre les autres machines de ce sous réseau. 192.168.15.0/24 correspond au réseau local physique dans lequel se trouve le serveur wireguard, les clients pourront aussi joindre les machines de ce réseau. Enfin, dans ce champs, si l'on remplace ces réseaux par les réseaux 0.0.0.0/1 et 128.0.0.0/1 alors tout le trafic est redirigé vers le vpn, le client passe par le serveur vpn pour ses requêtes Internet. Bref, avec ce réglage, le client partage l'adresse IP publique du serveur.
  • <Endpoint>, il s'agit de l'adresse IP publique du serveur ainsi que le port, soit dans notre exemple 87.65.43.21:51820
  • <PersistentKeepalive>, ce paramètre indique, en seconde, le délai entre deux paquets keepalive. Ces paquets servent à maintenir la connexion active. On peut mettre cette valeur à 25.

Lorsque ceci est fait on enregistre le fichier et on quitte l'éditeur (Ctrl+X). Remarque: les fichiers configurations des clients contiennent leur clef privée qui est une donnée confidentielle, donc il faut gérer les droits des fichiers en conséquence.

Ajout du client coté serveur

Le serveur wireguard ne se connecte qu'aux machines dont il connaît à minima la clé publique. Il faut donc enregistrer celle-ci. Il existe une méthode rapide qui consiste en cette ligne de commande:

wg set wg0 peer CLIENT_PUBLIC_KEY allowed-ips 10.0.15.0/24, 192.168.15.0/24

Cette méthode rapide souffre de ne pas être persistante, de ne pas résister à un redémarrage. Heureusement il existe une autre méthode pour pérenniser les enregistrements des utilisateurs. Pour cela il faut d'abord éditer le fichier /etc/wireguard/wg0.conf avec les droits administrateurs:

sudo nano /etc/wireguard/wg0.conf

Nous allons enregistrer le client sigmund en ajoutant ces lignes en toute fin de fichier:

[Peer]
#sigmund
PublicKey = <clef publique de sigmund>
AllowedIPs = 10.0.15.2/32
PersistentKeepalive = 25

Puis enregistrons les changements et quittons l'éditeur. Pour prendre en compte le nouveau client il faut redémarrer le service wg-quick:

sudo systemctl restart wg-quick@wg0.service

S'il n'y a pas d'erreur la commande:

sudo wg show wg0 (ou seulement sudo wg show)

affiche la configuration du serveur et les dernières lignes affichent les pairs.

Si l'on veut ajouter un autre pair, alors il faut rajouter les 5 lignes de paramètres en commençant pas [Peer].

Configurations sur la machine de test

Wireguard client existe pour la plupart des systèmes d'exploitation. On trouve le logiciel client sur cette page https://www.wireguard.com/install/ , dans l'appstore, l'applestore etc... On l'installe. Tout à l'heure nous avons créé un fichier de configuration pour l'utilisateur Sigmund qui s'appelle wgsigmund.conf, c'est le moment de le transférer sur notre machine cliente. Puis:

  • connecter la machine cliente à Internet en la laissant déconnectée du réseau local
  • lancer wiregard
  • choisir "ajouter tunnel"
  • choisir le fichier wgsigmund.conf; si tout se passe bien wiregard charge la configuration

Test du client

Le moment de vérité.

  • pour le test désactiver le pare-feu du client s'il y a lieu. On réglera le pare-feu quand déjà ça marchera sans.
  • dans wireguard, lancer la connexion

La connexion est établie lorsque wireguard indique un transfert d'octets entre le client et le serveur.

Pour être sûr, si l'on peut, on lance un

ping 10.0.15.1

qui devrait répondre, de même qu'un

ping 192.168.15.2

étant donné que le réseau 192.168.15.0/24 est normalement accessible via le vpn depuis Internet.

Le MTU

MTU est le sigle pour l'anglais "maximum transmission unit". C'est une valeur dont l'unité est l'octet. Du point de vu IP, couche réseau (couche 3) du modèle OSI, les interfaces serveur et cliente communiquent via des paquet IP qui contiennent entre autre les données à échanger entre les postes. Le MTU désigne la taille maximale des paquets IP qui circulent dans le VPN. En d'autres termes Wireguard fragmente l'information en paquets dont la taille est égale ou inférieure au MTU. Pour acheminer les données, les paquets IP sont aussi constitués, outre les données, d'une en-tête IP de 20 octet et d'une en-tête UDP de 8 octets qui sont autant d'information d'acheminement. Pour simplifier la problématique du MTU: plus il est élevé et plus le débit est rapide mais perd en fiabilité, ou, dit à contrario, plus le MTU est bas, plus le transfert est fiable mais lent. Dans Wireguard, le MTU du serveur et du client est fixée à 1420 octets ce qui est déjà un bon compromis. C'est pourquoi nous laissons cette valeur par défaut. Il est toutefois possible de la modifier aussi bien pour le serveur que pour le client. Il faut pour cela éditer le fichier de configuration et ajouter dans la section [Interface] la ligne:

MTU = <valeur>

Jouer en LAN avec Wireguard

Nous avons essayer divers jeux windows via un serveur Debian 11 et Wireguard. Certains jeux fonctionnent en LAN facilement et d'autre non; en particulier certains jeux ne permettent pas de se connecter nominativement à une adresse IP précise et utilisent impérativement le broadcast qui justement ne passe pas dans le VPN. Certains jeux, alors que les joueurs sont dans le même réseau local virtuel, nécessitent la configuration "0.0.0.0/0" ou "0.0.0.0/1, 128.0.0.0/1" dans les AllowedIPS du client pour fonctionner, c'est le cas d'Age of Mythology par exemple.

Script de création de compte pour Wireguard

Générer les clefs du client, son fichier configuration, enregistrer le client dans le fichier configuration du serveur, relancer le service, tout cela multiplier par le nombre d'utilisateur : la tâche peut s'avérer fastidieuse et répétitive à la longue. C'est pourquoi je vous fais don d'un script de création de compte que j'ai écrit.

Installation du script

  • Il faut placer ce script dans le dossier « […]/Bureau/wireguard » qu'on a créer précédemment, dossier qui contient les sous dossier « serveur » et « utilisateurs »
  • Dans le dossier « utilisateur » il faut créer le fichier « nextip ». Ce fichier ne contient qu'un nombre entier qui correspond au prochain digit qu'on utilisera pour créer un utilisateur. Si pour l'instant on n'a créé uniquement l'utilisateur Sigmund, alors : « 10.0.15.1 » et prise par le serveur, « 10.0.15.2 » est prise par Sigmund mais « 10.0.15.3 » est libre. On peut alors fixer « nextip » à 3 de cette façon, en se plaçant dans le dossier « utilisateurs » :

echo 3 > nextip

Cette commande créer le fichier « nextip » s'il n'existe pas et lui attribue la valeur « 3 ».

Puis nous créons le fichier du script à proprement parlé :

sudo nano wgadduser

On y colle se code abondamment commenté :

 
#!/bin/bash
# wgadduser "utilisateur" ajoute un utilisateur à wireguard
declare -i digit ;
clear ;
#teste si le nom de l'utilisateur a été précisé
if [[ -z "$1" ]]; then
echo "syntaxe: ./wgadduser <utilisateur> " ;
exit 0 ;
fi

#récupération de la clé publique du serveur
pbkeysrv=$(head ./serveur/wg-public.key) ;

#changement de dossier courant
cd utilisateurs ;

#récupération de nextIP
digit=$(head nextip) ;

#création du dossier utilisateur
#faire commencer le nom du dossier par $digit permet de lister
#les dossiers dans  l ordre de création et d adresse ip
mkdir $digit.$1 ;
cd $digit.$1 ;

#génération et récupération de la clé privée
nmprkey=wg-"$1"-private.key ;
umask 077 ;
wg genkey > $nmprkey ;
prkey=$(head $nmprkey) ;

#génération et récupération de la clé publique
nmpbkey=wg-"$1"-public.key ;
wg pubkey < $nmprkey > $nmpbkey ;
pbkey=$(head $nmpbkey) ;

#génération du fichier wg-utlisateur.conf
confile=wg"$1".conf ;
echo "[Interface]" > $confile ;
echo "PrivateKey = "$prkey >> $confile ;
echo "Address = 10.0.15."$digit"/32">> $confile ;
echo "MTU = 1384" >> $confile ;
echo "" >> $confile ;
echo "[Peer]" >> $confile ;
echo "PublicKey = "$pbkeysrv >> $confile ;
echo "AllowedIPs = 10.0.15.0/24, 192.168.15.0/24" >> $confile ;
echo "Endpoint = 82.65.96.172:51820" >> $confile ;
echo "PersistentKeepalive = 25" >> $confile ;

#affichage du fichier
cat $confile;

#choix de validation ou d'annulation
while true ; do
	read -p "Valider l'enregistrement ? y/n" choix
	case $choix in
		[YyOo]* ) break ;;
		[Nn]* ) cd ..; rm -R $1; exit 0 ;;
		* ) echo "Répondre oui (o) ou non (n)" ;;
	esac
done
clear ;

#ajout de l'utilisateur à /etc/wireguard/wg0.conf
config="/etc/wireguard/wg0.conf" ;
echo "" >> $config ;
echo "[Peer]" >> $config ;
echo "#"$1 >> $config ;
echo "PublicKey = "$pbkey >> $config ;
echo "AllowedIPs = 10.0.15."$digit"/32" >> $config ;
echo "PersistentKeepalive = 25" >> $config ;
#incrémentation de nextip
digit=$((digit+1)) ;
cd .. ;
echo $digit > nextip ;

#proposition de redémarrage du service
echo "L\'utilistaeur "$1" a bien été enregistré" ;
while true ; do
	read -p "Faut-il redémarrer l'interface pour prendre en compte les changements ? (O)ui ou (N)on" choix1 ;
	case $choix1 in
		[YyOo]* ) break;;
		[Nn]* ) exit 0 ;;
		* ) echo "Répondre oui (o) ou non (n)" ;;
	esac
done
systemctl restart wg-quick@wg0 ;
echo "service relancé, fin du script, merci !" ;
exit 0 ;

Enfin on rend le script executable avec la commande:

sudo chmod +x wgadduser

Fonctionnement du script

la syntaxe du script est

./wgadduser <utilistateur>

par exemple

./wgadduser donald

va créer l'utilisateur donald automatiquement. Le script est commenté de façon à comprendre ce qu'il fait au fur et à mesure. Une fois la commande lancée le script affiche les informations avec lesquelles il va procéder à l'enregistrement, il est possible d'annuler la création à ce moment. Si on valide le choix de création, alors :

  • Dans le dossier « utilisateurs» est créé un nouveau dossier. Son nom respecte la syntaxe <dernier_digit>.<utilisateur>. Ainsi, avec un simple

ls -al

On aura une correspondance entre utilisateurs et adresses IP dans le VPN ce qui s’avérera fort pratique à l'usage pour identifier les connections.

  • Dans ce dossier le script génère la paire de clés nécessaire au chiffrement.
  • Toujours dans ce dossier le script génère un fichier de configuration pour l'utilisateur client. Le fichier s'appelle wg<utilisateur>.conf.
  • Le script ajoute au fichier de configuration wg0.conf une nouvelle section [Peer] en fin de fichier correspondant à l'enregistrement du nouvel utilisateur.
  • Pour finir le script propose de redémarrer le service Wireguard, ce qui permet de ne redémarrer qu'une fois tous les enregistrements faits.

Conclusion

Il est encore possible d'aller plus loin dans la configuration, par exemple ajouter un serveur DNS ou installer le paquet qrencode, ce paquet génère un Qrcode de configuration pour les smartphones. Pour l'heure avec ce tuto on a un serveur wireguard fonctionnel, un script de création des comptes, c'est une bonne mise à l'étrier.


Remerciements

Ont contribué à tester mes vpn Wireguard et à ce tutoriel : Nour, Rico, Watts, Anonimix ; je les remercie particulièrement pour leur patience.

Copyleft Petitchat MMXXII