CentOS 8 set up WireGuard VPN server

How do I install and set up WireGuard VPN server on a CentOS 8 Linux? How can I configure CentOS 8 as the WireGuard VPN server?

WireGuard is a free, open-source modern and fast VPN with state-of-the-art cryptography. It is quicker and simpler as compared to IPSec and OpenVPN. Originally, released for the Linux kernel, but it is getting cross-platform support for other operating systems too. This page explains how to install and set up WireGuard VPN on CentOS 8 Linux.

Procedure: CentOS 8 set up WireGuard VPN server

Our sample setup includes a simple peer connection between a cloud server running CentOS 8 server, and a CentOS/Ubuntu Linux desktop client:

The steps are as follows for installing and configuring WireGuard on CentOS Linux as a VPN server.

Please note that {vivek@centos8:~ }$ is my shell prompt and is not part of actual commands. In other words, you need to copy and paste command after my shell prompt.

Step 1 – Update your system

Run the dnf command or yum command to install CentOS 8 security updates:
{vivek@centos8:~ }$ sudo dnf updateOR
{vivek@centos8:~ }$ sudo yum update

Step 2 – Enable and install EPEL repo

We need to install a package named wireguard-tools from EPEL repo that provides the wg binary for controlling the WireGuard server. Let us enable and install EPEL repo on CentOS 8, run:
{vivek@centos8:~ }$ sudo yum install epel-release

Make sure you enable the PowerTools repository since EPEL packages may depend on packages from it:
{vivek@centos8:~ }$ sudo yum install 'dnf-command(config-manager)'
{vivek@centos8:~ }$ sudo yum config-manager --set-enabled PowerTools

Step 3 – Set up wireguard repo

Before we can install the wireguard Linux kernel module, turn on the official wireguard repo. Execute the following command:
{vivek@centos8:~ }$ sudo yum copr enable jdoss/wireguard

Step 4 – Installing a WireGuard VPN server on CentOS 8

Now we got everything set up. It is time for setting up a WireGuard VPN server on CentOS 8 box. Run:
{vivek@centos8:~ }$ sudo yum install wireguard-dkms wireguard-tools

The above will also install the GNU GCC compiler collection to compile and build the required Linux kernel modules. So it would be best if you waited some time to complete the procedure.

Step 5 – Configuring WireGuard server

First, we are going to create an empty WireGuard server config file with proper permissions. Use the mkdir command as follows:
{vivek@centos8:~ }$ sudo mkdir -v /etc/wireguard/
mkdir: created directory '/etc/wireguard/'
{vivek@centos8:~ }$ sudo sh -c 'umask 077; touch /etc/wireguard/wg0.conf'
{vivek@centos8:~ }$ sudo ls -l /etc/wireguard/wg0.conf
-rw-------. 1 root root 0 Mar 13 09:13 /etc/wireguard/wg0.conf

Create a private and public key pair for the WireGuard server

We need to run the following commands in /etc/wireguard/ directory. Use the cd command:
{vivek@centos8:~ }$ cd /etc/wireguard/
Run the following command:
{vivek@centos8:~ }$ sudo sh -c 'umask 077; wg genkey | tee privatekey | wg pubkey > publickey'
To view keys use the cat command and ls command:
{vivek@centos8:~ }$ ls -l privatekey publickey
{vivek@centos8:~ }$ sudo cat privatekey
#### Note down the privatekey ####
{vivek@centos8:~ }$ sudo cat publickey

Configure WireGuard server

Edit the /etc/wireguard/wg0.conf file:
{vivek@centos8:~ }$ sudo vi /etc/wireguard/wg0.conf
Append the following directives:

[Interface]
## VPN server private IP address ##
Address = 192.168.5.1/24
 
## VPN server port ##
ListenPort = 31194
 
## VPN server's private key i.e. /etc/wireguard/privatekey ##
PrivateKey = cBRd8MhXckz5ZnNRvk8F+r0558sfJlI0YdJ7ZQfWqUM=
 
## Save and update this config file when a new peer (vpn client) added ##
SaveConfig = true

Save and close the file.

Set up firewalld rules

We have set up a firewall using FirewallD on our CentOS 8 server. Hence, we need to open UDP port 31194 by creating wireguard service:
{vivek@centos8:~ }$ sudo vi /etc/firewalld/services/wireguard.xml

<?xml version="1.0" encoding="utf-8"?>
<service>
  <short>wireguard</short>
  <description>WireGuard open UDP port 31194 for client connections</description>
  <port protocol="udp" port="31194"/>
</service>

Next, I am going to enable our WireGuard service in firewalld using the firewall-cmd command as follows:
{vivek@centos8:~ }$ sudo firewall-cmd --permanent --add-service=wireguard --zone=public
Turn on masquerading so all traffic coming and going out from 192.168.5.0/24 routed correctly via our public IP address 172.105.120.136/24:
{vivek@centos8:~ }$ sudo firewall-cmd --permanent --zone=public --add-masquerade
Finally reload the firewalld and list our configuration:
{vivek@centos8:~ }$ sudo firewall-cmd --reload
{vivek@centos8:~ }$ sudo firewall-cmd --list-all

Sample outputs:

public (active)
  target: default
  icmp-block-inversion: no
  interfaces: eth0
  sources: 
  services: wireguard ssh
  ports: 
  protocols: 
  masquerade: yes
  forward-ports: 
  source-ports: 
  icmp-blocks: 
  rich rules: 
Turn on IPv4/IPv6 forwarding

Edit the /etc/sysctl.d/99-custom.conf file
{vivek@centos8:~ }$ sudo vi /etc/sysctl.d/99-custom.conf
Append the following config options:

## Turn on bbr ##
net.core.default_qdisc = fq
net.ipv4.tcp_congestion_control = bbr
 
## for IPv4 ##
net.ipv4.ip_forward = 1
 
## Turn on basic protection/security ##
net.ipv4.conf.default.rp_filter = 1
net.ipv4.conf.all.rp_filter = 1
net.ipv4.tcp_syncookies = 1
 
## for IPv6 - uncomment the following line ##
#net.ipv6.conf.all.forwarding = 1

Reload changes using the sysctl command:
{vivek@centos8:~ }$ sudo sysctl -p /etc/sysctl.d/99-custom.conf
Above directives are explained in details in my previous tutorials:

Allow peer to peer connection

By default, firewalld will drop all communication between internal (wg0) and the public network (eth0). So we are going to add interface wg0 to the internal network and turn on masquerading as follows
{vivek@centos8:~ }$ sudo firewall-cmd --add-interface=wg0 --zone=internal
{vivek@centos8:~ }$ sudo firewall-cmd --permanent --zone=internal --add-masquerade

Step 5 – Enable and start WireGuard service

Now we installed and configured server correctly it is time to enable and start wireguard service using the systemctl command:
{vivek@centos8:~ }$ sudo systemctl enable wg-quick@wg0 #<-- turn it on
{vivek@centos8:~ }$ sudo systemctl start wg-quick@wg0 #<-- start it
{vivek@centos8:~ }$ sudo systemctl status wg-quick@wg0 #<-- get status

Verify that interface wg0 is up and running using the ip command:
{vivek@centos8:~ }$ sudo wg
{vivek@centos8:~ }$ sudo ip a show wg0

Please note down the public key when displayed:

Step 6 – Wireguard VPN client configuration

The procedure for installing and configuring a VPN client is the same as setting up the server. Let us install the client on a CentOS 8:
{vivek@centos8-vpn-client:~ }$ sudo yum install epel-release
{vivek@centos8-vpn-client:~ }$ sudo yum install 'dnf-command(config-manager)'
{vivek@centos8-vpn-client:~ }$ sudo yum config-manager --set-enabled PowerTools
{vivek@centos8-vpn-client:~ }$ sudo yum copr enable jdoss/wireguard
{vivek@centos8-vpn-client:~ }$ sudo yum install wireguard-dkms wireguard-tools

Here is how I installed it on my Ubuntu Linux laptop using the apt command:
{vivek@ubuntu19-10-vpn-client:~ }$ sudo apt install wireguard-dkms wireguard-tools wireguard
Let us create our VPN client config:
{vivek@centos8-vpn-client:~ }$ sudo mkdir -v /etc/wireguard/
{vivek@centos8-vpn-client:~ }$ sudo sh -c 'umask 077; touch /etc/wireguard/wg0.conf'
{vivek@centos8-vpn-client:~ }$ sudo ls -l /etc/wireguard/wg0.conf
{vivek@centos8-vpn-client:~ }$ cd /etc/wireguard/
{vivek@centos8-vpn-client:~ }$ sudo sh -c 'umask 077; wg genkey | tee privatekey | wg pubkey > publickey'
#### Note down the privatekey ####
{vivek@centos8-vpn-client:~ }$ sudo cat privatekey

Edit the /etc/wireguard/wg0.conf file:
{vivek@centos8-vpn-client:~ }$ sudo vi /etc/wireguard/wg0.conf
Append the following directives:

[Interface]
## client private key ##
PrivateKey = sKVVArGeo75fCkskltZc8WRIi9fPQ3SPLXmrr8uBp3M=
 
## client ip address ##
Address = 192.168.5.2/24
 
[Peer]
## CentOS 8 server public key ##
PublicKey = qdjdqh2+N3DEMDUDRob8K3b+9BZFJbT59f+rBrl99zM
 
## set ACL ##
AllowedIPs = 192.168.5.0/24
 
## Your CentOS 8 server's public IPv4/IPv6 address and port ##
Endpoint = 172.105.120.136:31194
 
##  Key connection alive ##
PersistentKeepalive = 15

Enable and start VPN client/peer, run:
{vivek@centos8-vpn-client:~ }$ sudo systemctl enable wg-quick@wg0
{vivek@centos8-vpn-client:~ }$ sudo systemctl start wg-quick@wg0
{vivek@centos8-vpn-client:~ }$ sudo systemctl status wg-quick@wg0

Allow client and server connection

We need to configure the server-side and allow a connection between the client and the server. Let us go back to our CentOS 8 server and edit wg0.conf file to add [Peer] (client) information as follows (type commands on the server):
{vivek@centos8:~ }$ sudo systemctl stop wg-quick@wg0
{vivek@centos8:~ }$ sudo vi /etc/wireguard/wg0.conf

Append the following config:

[Peer]
## client VPN public key ##
PublicKey = hM/J1IVUns1F4gWjA11pOPq6uDmlYsSq0o7JWCQ02C4=
 
## client VPN IP address (note /32 subnet) ##
AllowedIPs = 192.168.5.2/32

Save and close the file in vim. Next start the service again, run:
{vivek@centos8:~ }$ sudo systemctl start wg-quick@wg0

Verification

That is all. By now, both servers and clients must be connected securely using VPN. Let us test the connection. Type the following ping command on your client machine:
{vivek@centos8-vpn-client:~ }$ ping -c 4 192.168.5.1
{vivek@centos8-vpn-client:~ }$ sudo wg

Step 7 – Firewall configurations

Now we have set up and configured peer-to-peer VPN networking for our server and client. However, you may want to give access to the Internet for all VPN clients. For these purposes, we need to set up IPv4 and IPv6 firewall rules, including NAT and IP forwarding. See the following tutorial:

Conclusion

Congratulation! You just end up setting up a WireGuard VPN server on CentOS 8 and peer (client) on both Ubuntu/CentOS Linux desktop. See WireGuard project docs and other information here.

This entry is 2 of 6 in the WireGuard moden Linux/Unix/*BSD VPN Tutorial series. Keep reading the rest of the series:
  1. Ubuntu 20.04 set up WireGuard VPN server
  2. CentOS 8 set up WireGuard VPN server
  3. Debian 10 set up WireGuard VPN server
  4. WireGuard Firewall Rules in Linux
  5. Wireguard VPN client in a FreeBSD jail
  6. Alpine Linux set up WireGuard VPN server
🐧 If you liked this page, please support my work on Patreon or with a donation.
🐧 Get the latest tutorials on SysAdmin, Linux/Unix, Open Source/DevOps topics:
CategoryList of Unix and Linux commands
File Managementcat
FirewallAlpine Awall CentOS 8 OpenSUSE RHEL 8 Ubuntu 16.04 Ubuntu 18.04 Ubuntu 20.04
Network Utilitiesdig host ip nmap
OpenVPNCentOS 7 CentOS 8 Debian 10 Debian 8/9 Ubuntu 18.04 Ubuntu 20.04
Package Managerapk apt
Processes Managementbg chroot cron disown fg jobs killall kill pidof pstree pwdx time
Searchinggrep whereis which
User Informationgroups id lastcomm last lid/libuser-lid logname members users whoami who w
WireGuard VPNAlpine CentOS 8 Debian 10 Firewall Ubuntu 20.04
2 comments… add one
  • Pete Sep 2, 2020 @ 3:30

    This was a fantastic reference. Thank you very much.

Leave a Reply

Your email address will not be published. Required fields are marked *

Use HTML <pre>...</pre>, <code>...</code> and <kbd>...</kbd> for code samples.