How to Install Wireguard VPN on Rocky Linux 9
On this page
- Enable Wireguard Kernel Module
- Generating Server and Client Key Pair
- Configuring Wireguard Server
- Setting up Port Forwarding
- Setting up Firewalld
- Starting Wireguard Server
- Setting up Client and Connecting to Wireguard Server
Wireguard is an open-source VPN protocol alternative to IPSec, IKEv2, and OpenVPN. Wiruguard is designed for Linux and Unix operating systems, it runs on Linux kernel space, which makes the Wireguard faster and more reliable. Wireguard is used to create secure tunnel connections between two computers or more.
Wireguard aims to replace VPN protocols such as IPSec, IKEv2, and OpenVPN. Wireguard is lighter, faster, easy to set up, and more efficient. And at the same time, Wiregurad did not sacrifice the security aspect of the VPN protocol. Wireguard supports modern cryptography like the Noise protocol framework, Curve25519, ChaCha20, Poly1305, BLAKE2, SipHash24, HKDF, and secure trusted constructions.
Compared to other VPN protocols such as OpenVPN, IPSec, and IKEv2, wireguard is a new VPN protocol. Wireguard is released in 2015 by Jason A. Donenfeld as an alternative VPN protocol, It was merged to the Linux kernel v5.6 by Linus Torvalds in 2020 and the same year, also ported to FreeBSD 13.
This guide teaches you how to install and set up Wirgeuard Server on a Rocky Linux 9 server. You'll also learn how to set up a client machine to connect to the Wireguard server.
You can use any Linux distribution as a client machine in this example. But this guide will use the Rocky Linux client machine, one of the RHEL9-based distributions.
To start with this guide, you must ensure that you have the following requirements:
- A Rocky Linux 9 server - This example uses a Rocky Linux with hostname 'wireguard-rocky'.
- A non-root user with sudo/root administrator privileges.
- An SELinux is running in permissive mode.
Now with the prerequisites ready, you can now start installing and configuring the Wireguard server.
Enable Wireguard Kernel Module
The latest version of Rocky Linux 9 shipped with default Linux kernel 5.14, which is by default the 'wireguard' kernel module embedded on top of it. In this step, you'll enable the Wirguard kernel module and install the 'wireguard-tools' on your Rocky Linux server.
Run the below modprobe command to enable the 'wireguard' kernel module. Then, verify the list of enabled kernel modules via the 'lsmod' command.
sudo modprobe wireguard
lsmod | grep wireguard
If the 'wireguard' kernel module is enabled, you should receive an output similar to the following:
To load the wireguard module permanently, you can run the below command to add the new config file to '/etc/modules-load.d/' directory. This will load the wireguard kernel module permanently at system boot.
sudo echo wireguard > /etc/modules-load.d/wireguard.conf
After the 'wireguard' kernel module is enabled, you must install the 'wireguard-tools' package to manage the Wireguard server. This includes generating keys, starting the Wireguard server, and many more.
Run the dnf command below to install 'wireguard-tools'. When prompted for confirmation, input y and press ENTER to proceed.
sudo dnf install wireguard-tools
Now the 'wireguard-tools' installation should begin.
Your Rocky Linux server now has the 'wireguard' kernel module enabled and the 'wireguard-tools' installed. Next, you'll go over how to generate key pairs for both the Wireguard server and client via the wireguard-tools.
Generating Server and Client Key Pair
The wireguard-tools provide a user-space command line for managing Wireguard deployment. Two major utilities provided by wireguard-tools:
- wg - a command line utility that can be used to set up the wireguard tunnel interface. With this utility, you can generate key pairs, verify the current wireguard runtime and interface, and set up the Wireguard tunnel interface.
- wg-quick - a simple command line that can manage the Wireguard interface. You can start, stop, and restart any wireguard interfaces via the wg-quick command.
The first step after enabling the wireguard kernel module and installing wireguard-tools is generating key pairs for both the Wireguard server and client. And this can be done via the 'wg' command utility.
Generating Server Key Pair
Run the below 'wg genkey' command to generate the server private key '/etc/wireguard/server.key'. Then, change the default permission to '0400' to disable write and execute from others and groups.
wg genkey | sudo tee /etc/wireguard/server.key
sudo chmod 0400 /etc/wireguard/server.key
After that, run the below command to generate the public key for the wireguard server '/etc/wireguard/server.pub'. The wireguard public key is derived from the wireguard private key '/etc/wireguard/server.key'.
sudo cat /etc/wireguard/server.key | wg pubkey | sudo tee /etc/wireguard/server.pub
Next, verify both the wireguard server's public and private keys via the cat command below.
You may have a different key for both public and private keys, but the output is similar to this:
Generating Client Key Pair
After generating the wireguard server key pair, you'll generate a new one for the client. In this example, you'll generate a new key pair with the name 'client1'.
Run the below command to create a new directory '/etc/wireguard/clients'. This directory will be used to store client key pairs.
mkdir -p /etc/wireguard/clients
Next, run the below 'wg genkey' command to generate the client private key '/etc/wireguard/clients/client1.key'. Then, generate the client public key '/etc/wireguard/clients/client1.pub' via the 'wg pubkey' command.
wg genkey | tee /etc/wireguard/clients/client1.key
cat /etc/wireguard/clients/client1.key | wg pubkey | tee /etc/wireguard/clients/client1.pub
Now verify both client's public and private keys using the cat command below.
The key should be similar for both the wireguard server and client key pair, which is a base64-like key.
Configuring Wireguard Server
In this step, you'll create a new config file for the wireguard server, set up the wireguard interface, and set up peer connection for client connections. This includes the configuration of the wireguard VPN subnet, the IP address from the wireguard server, and the IP address for the peer client.
To start, Create a new wireguard server config file '/etc/wireguard/wg0.conf' using the below nano editor command.
sudo nano /etc/wireguard/wg0.conf
Add the following lines to the file and be sure to change the 'PrivateKey' with the Wirguard server private key 'server.key'. With this, you'll also set up the Wireguard server interface to be run at IP address '10.8.0.1'. And for client connection, you'll be using the UDP port 51820. And lastly, you'll also enable the SaveConfig parameter that will ensure any changes are saved to the wireguard configuration file, even when the Wireguard interface is off.
# Wireguard Server private key - server.key
PrivateKey = iHaI5bkEbW8wqTQDbU/KITGhxtKoiezWVohVZsKwj3w=
# Wireguard interface will be run at 10.8.0.1
Address = 10.8.0.1/24
# Clients will connect to UDP port 51820
ListenPort = 51820
# Ensure any changes will be saved to the Wireguard config file
SaveConfig = true
Next, add the following lines to define the client peer connection. Be sure to change the 'PublicKey' parameter with the client public key 'client1.pub'. With the 'AllowedIPs' parameter, you can specify which Wireguard client that allowed to access this peer. In this example, only clients with IP '10.8.0.8' will be allowed to access this peer connection. Additionally, you can also allow the range of internal network subnets such as '172.16.100.0/24' to access the wireguard peer.
# Wireguard client public key - client1.pub
PublicKey = iWskvxyj+QK4185xO6Z2Fb0XYo1jGyiyI3iKbyGTkT8=
# clients' VPN IP addresses you allow to connect
# possible to specify subnet ⇒ [172.16.100.0/24]
AllowedIPs = 10.8.0.8/24
Save and exit the file when finished.
With this, you've now created the basic configuration for the Wreguard server. Also, you've defined peer connection for the client using the client public key 'client1.pub'. In the next step, set up the port forwarding on the wireguard server and set up the firewalld rules for traffic routing.
Setting up Port Forwarding
To set up any VPN server, you must enable port forwarding on your deployment server. In this step, you'll enable port forwarding on your Rocky Linux server via the '/etc/sysctl.conf' file.
Open the config file '/etc/sysctl.conf' using the nano editor below.
sudo nano /etc/sysctl.conf
Add the following lines to the bottom of the line. These lines will enable port forwarding for both IPv4 and IPv6. Whether you need IPv6 or not, you can disable it by putting a comment '#' at the start of the line.
# Port Forwarding for IPv4
# Port forwarding for IPv6
Save the file and exit the editor when finished.
Now run the below 'sysctl' command to apply the changes on the '/etc/sysctl.conf' file.
sudo sysctl -p
And you'll receive an output similar to this:
With Port-Forwarding enabled, you'll next set up a firewalld that will be used to route traffics from clients to the specific network interface on the wireguard server.
Setting up Firewalld
You'll set up the firewalld on the Wireguard server in this step. You'll route client traffics to the specific network interface on the wireguard server via firewalld. And this can be done by adding new rules to firewalld permanently, or by using the wireguard 'PostUp' and 'PostDown' parameters in the Wireguard configuration file.
Before you start, run the below ip command to check the default network interface that is used for internet access on the wireguard server.
ip route show default
You'll receive an output similar to this - In this example, the wireguard server used interface eth0 for internet access. You may have different names of network interfaces on your server.
Next, open the wireguard server config file '/etc/wireguard/wg0.conf' using the below nano editor command.
sudo nano /etc/wireguard/wg0.conf
Add the following lines to the '[Interface]' section.
PostUp = firewall-cmd --zone=public --add-masquerade
PostUp = firewall-cmd --direct --add-rule ipv4 filter FORWARD 0 -i wg -o eth0 -j ACCEPT
PostUp = firewall-cmd --direct --add-rule ipv4 nat POSTROUTING 0 -o eth0 -j MASQUERADE
PostDown = firewall-cmd --zone=public --remove-masquerade
PostDown = firewall-cmd --direct --remove-rule ipv4 filter FORWARD 0 -i wg -o eth0 -j ACCEPT
PostDown = firewall-cmd --direct --remove-rule ipv4 nat POSTROUTING 0 -o eth0 -j MASQUERADE
Save and exit the file.
- The 'PostUp' parameter will be executed whenever the Wirguard server starts the VPN tunnel.
- The 'PostDown' parameter will be executed whenever the Wireguard server stops the VPN tunnel.
- The command 'firewall-cmd --zone=public --add-masquerade' will enable masquerade on firewalld.
- The command 'firewall-cmd --direct --add-rule ipv4 filter FORWARD 0 -i wg -o eth0 -j ACCEPT' will add firewalld rich-rule for traffics from the wireguard interface to eth0.
- The command 'firewall-cmd --direct --add-rule ipv4 nat POSTROUTING 0 -o eth0 -j MASQUERADE' will enable NAT through the eth0 interface.
- In the 'PostDown' parameter, all of these commands are used to revert the changes on firewalld by removing rules that were applied during commands on the 'PostUp' parameter executed.
Next, run the below firewall-cmd command to open the UDP port 51820 that will be used for wirguard clients. Then, reload the firewalld to apply the changes.
sudo firewall-cmd --add-port=51820/udp --permanent
sudo firewall-cmd --reload
Lastly, verify firewalld rules via the below firewall-cmd command.
sudo firewall-cmd --list-all
You should receive an output like this - The wireguard client port 51820/udp added to the firewalld.
With this, you've now enabled port forwarding on the wireguard server and configured the firewalld to route traffic from the wireguard interface to the specific network interface. You're now ready to start the wireguard server.
Starting Wireguard Server
In this step, you'll start and enable the Wireguard server. You'll also verify the Wireguard server and verify the wg0 interface that will be created by the Wireguard service.
Run the below systemctl command utility to start and enabled the wireguard server. This will start the wireguard service and create a new wireguard interface 'wg0'.
sudo systemctl start [email protected]
sudo systemctl enable [email protected]
Verify the wireguard server using the below systemctl command. This will ensure that the wireguard server is running.
sudo systemctl status [email protected]
And you'll receive output similar to this - The wireguard server is now enabled and will be run automatically upon the bootup. And the status of the wireguard server is running.
You can also verify the interface 'wg0' that is created by the wireguard server via the ip command below.
ip a show wg0
You'll receive the detailed interface of wg0, which is matched with the wireguard server config file '/etc/wireguard/wg0.conf'. The wg0 interface should have an IP address '10.8.0.1' as described in the wireguard config file '/etc/wireguard/wg0.conf'.
Another method that can be used to start the wireguard server is by using the 'wg-quick' command utility that provides by wireguard-tools.
Run the 'wg-quick up' to start the wireguard server and the 'wg-quick down' to stop the wireguard server. Also, be sure to specify the full path of your wireguard server config file '/etc/wireguard/wg0.conf'.
sudo wg-quick up /etc/wireguard/wg0.conf
sudo wg-quick down /etc/wireguard/wg0.conf
At this point, the wireguard server is running on the Rocky Linux server. In the next step, you'll set up a client machine and connect it to the wireguard server.
Setting up Client and Connecting to Wireguard Server
In this step, you'll set up a wireguard on a Linux client machine, then connect the client machine to the wireguard server. This example uses a Rocky Linux with the hostname 'client1' as a client machine, but you can also use any Linux distribution.
Log in to the client machine and run the below dnf command to install the wireguard-tools package to your client. This operation also installs the dependency 'systemd-resolved' that will be used by wireguard-tools for managing the DNS resolver.
sudo dnf install wireguard-tools
Input y when prompted and press ENTER to proceed.
During the 'wireguard-tools' installation, the systemd-resolved package is also installed as a dependency.
Run the below command to start and enable the 'systemd-resolved' service.
sudo systemctl start systemd-resolved
sudo systemctl enable systemd-resolved
With the wireguard-tools installed and the systemd-resolved running, you'll next set up the NetworkManager to use the 'systemd-resolved' as the DNS backend.
Open the NetworkManager config file '/etc/NetworkManager/NetworkManager.conf' using the below nano editor command.
sudo nano /etc/NetworkManager/NetworkManager.conf
Add the 'dns' parameter to the '[main]' section as below.
Save the file and exit the editor.
Next, run the below command to remove the '/etc/resolv.conf' file and create a new symlink file of the 'resolv.conf' file managed by systemd-resolved.
rm -f /etc/resolv.conf
sudo ln -s /usr/lib/systemd/resolv.conf /etc/resolv.conf
Now restart the NetworkManager service to apply the changes.
sudo systemctl restart NetworkManager
Now that the NetworkManager is configured, you are now ready to set up the wireguard client.
Create a new file '/etc/wireguard/wg-client1.conf' using the below nano editor.
sudo nano /etc/wireguard/wg-client1.conf
Add the following lines to the file.
# Define the IP address for the client - must be matched with wg0 on Wireguard Server
Address = 10.8.0.8/24
# Private key for the client - client1.key
PrivateKey = 4FsCdtKr9GrLiX7zpNEYeqodMa5oSeHwH/m9hsNNfEs=
# Run resolvectl command
PostUp = resolvectl dns %i 184.108.40.206 220.127.116.11; resolvectl domain %i ~.
PreDown = resolvectl revert %i
# Public key of the Wireguard server - server.pub
PublicKey = aK+MQ48PVopb8j1Vjs8Fvgz5ZIG2k6pmVZs8iVsgr1E=
# Allow all traffic to be routed via Wireguard VPN
AllowedIPs = 0.0.0.0/0
# Public IP address of the Wireguard Server
Endpoint = 192.168.5.59:51820
# Sending Keepalive every 25 sec
PersistentKeepalive = 25
Save the file and exit the editor when finished.
In the '[Interface]' section, you must define the following:
- The IP address of the client must be matched with the subnet of the Wireguard server. The Wireguard client will get the IP address '10.8.0.8' in this example.
- Specify the DNS server for the client via the resolvectl command.
- Change the 'PrivateKey' parameter with the client private key that you've generated 'client1.key'.
In the '[Peer]' section, you must add the following:
- Wireguard server public key 'server.pub' to the PublicKey parameter.
- Specify 'AllowedIPs' to restrict access on the VPN peer, you can specify subnets of networks or you can just put 0.0.0.0/0 to tunnel all traffic over VPN.
- Specify the Endpoint parameter with the public IP address of the Wireguard server or you can also use a domain name.
With the wireguard client config file created, you can run wireguard on the client machine via the 'wg-quick up' command below.
wg-quick up wg-client1
You'll receive an output similar to this - The new wireguard interface 'wg-client1' is created and get an IP address '10.8.0.8'.
Now verify the 'wg-client1' interface via the ip command below.
ip a show wg-client1
Below is a similar output that will be printed to your terminal.
You can also verify the DNS resolver on the wg-client1 interface via the 'resolvectl' command below.
resolvectl status wg-client1
Below is the output you'll receive on your terminal - The wireguard interface wg-client1 used a DNS resolver defined via the 'PostUp' parameter, which is using the 'systemd-resolved'.
In addition to that, you can also verify the Wireguard connection via the 'wg show' command.
Run the 'wg show' command on the wireguard client machine and you will receive an output like the below screenshot.
The wireguard server IP address should be shown in the 'endpoint' section. Also, you can see the wireguard server public key 'server.pub'.
Back to the wireguard server and run the 'wg show' command below.
Below is the similar output you'll receive on your terminal - On the endpoint section, you'll see the client's public IP address and on the peer section you'll see the client public key 'client1.pub'.
Lastly, run the below command to ensure that the client machine can access the internet or access the internal network subnet of the Wireguard VPN.
ping -c5 10.8.0.1
ping -c5 18.104.22.168
ping -c5 duckduckgo.com
Below is the output you should receive:
The client machine can connect to the Wireguard server that has an IP address '10.8.0.1'.
The client machine can access the internet. All traffic is routed via the Wireguard server's public IP address.
Now you've configured the wireguard VPN on the client machine. You've also verified the connection between the client machine to the wireguard server.
In this guide, you have installed and configured the wireguard VPN server on Rocky Linux 9. You've also learned how to set up the Rocky Linux client machine to connect to the wireguard server. Along with this, you have also learned how to enable port forwarding and set up NAT via firewalld.
Lastly, you've learned basic usages of the 'wg' command utility for generating public and private key pairs and verifying wireguard VPN connections. Then, you've also learned how to use the 'wg-quick' command to start and stop the wireguard connection.
If you want to learn more about WireGuard, visit the WireGuard documentation. Also, you can visit GitHub topics related to Wireguard to find automation deployment for WireGuard VPN Server.