Wireguard VPN setup in Ubuntu 20 & Ubuntu 22

Ubuntu 20.04 focal fossaUbuntu 22.04 jammy jellyfish
Compatibility table for this guide. Let me know if you find otherwise.

Install the necessary software. Run everything as root.

mkdir -p /etc/wireguard
apt update
apt install wireguard

Make sure IP forwarding is enabled. Set a setting called net.ipv4.ip_forward to be 1 in /etc/sysctl.conf. Either uncomment, modify or create this line.

net.ipv4.ip_forward = 1

Let the system know of the new setting by running sysctl.

sysctl -p

Create the server key pair, a private key and a public key. You can delete the files afterwards, but remember the values.

wg genkey | tee /etc/wireguard/private.key
cat /etc/wireguard/private.key | wg pubkey | tee /etc/wireguard/public.key
rm -f /etc/wireguard/private.key /etc/wireguard/public.key

Here are mine.

mFUyHRVxrkDp3uij0JcJ6O+hAIR1SVaTRTAdWB2JUXA= <- server private key
QypmYvMDzvJ9enBPTcQEAC5incyjhe/WkLZjRAt+JTc= <- server public key

Do the above again, as we need to generate another pair for the client.

aPlilXQB+qf+e5wOsy7A+DfMnEj4LjTMZDuXk/m2Skk= <- client private key
CsSHI5n403i9eEER35rPg1fcYyBkNsT5CJq+4UDa014= <- client public key

Create this file /etc/wireguard/wg0.conf, change the key values accordingly. I arbitrarily choose a network 10.8.0.0/24 and 10.8.0.1 as the server IP address and 10.8.0.2 as the client IP address.

[Interface]
PrivateKey = mFUyHRVxrkDp3uij0JcJ6O+hAIR1SVaTRTAdWB2JUXA= <- server private key
Address = 10.0.0.1/8
ListenPort = 51280
PostUp = ufw route allow in on wg0 out on eth0
PostUp = iptables -t nat -I POSTROUTING -o eth0 -j MASQUERADE
PostUp = ip6tables -t nat -I POSTROUTING -o eth0 -j MASQUERADE
PreDown = ufw route delete allow in on wg0 out on eth0
PreDown = iptables -t nat -D POSTROUTING -o eth0 -j MASQUERADE
PreDown = ip6tables -t nat -D POSTROUTING -o eth0 -j MASQUERADE

[Peer]
PublicKey = CsSHI5n403i9eEER35rPg1fcYyBkNsT5CJq+4UDa014= <- client public key
AllowedIPs = 10.0.8.1/32

On some servers, the network interface is named differently than eth0, so you need to change it accordingly. To find out, use

ip addr

For example

root@ip-172-31-19-161:/home/ubuntu# ip addr
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: ens5: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 9001 qdisc mq state UP group default qlen 1000
    link/ether 02:40:b1:2b:d1:42 brd ff:ff:ff:ff:ff:ff
    altname enp0s5
    inet 172.31.19.161/20 metric 100 brd 172.31.31.255 scope global dynamic ens5
       valid_lft 2075sec preferred_lft 2075sec
    inet6 fe80::40:b1ff:fe2b:d142/64 scope link
       valid_lft forever preferred_lft forever

This the above case, then you have to change eth0 to ens5

To start the Wireguard server, run

systemctl start wg-quick@wg0

At this stage, you should see an interface called wg0 created.

# ip addr
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: ens5: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 9001 qdisc mq state UP group default qlen 1000
    link/ether 02:40:b1:2b:d1:42 brd ff:ff:ff:ff:ff:ff
    altname enp0s5
    inet 172.31.19.161/20 metric 100 brd 172.31.31.255 scope global dynamic ens5
       valid_lft 1855sec preferred_lft 1855sec
    inet6 fe80::40:b1ff:fe2b:d142/64 scope link
       valid_lft forever preferred_lft forever
3: wg0: <POINTOPOINT,NOARP,UP,LOWER_UP> mtu 8921 qdisc noqueue state UNKNOWN group default qlen 1000
    link/none
    inet 10.8.0.1/24 scope global wg0
       valid_lft forever preferred_lft forever

If you make any changes to your wg0.conf file, you might want to delete that interface before you do a systemctl start wg-quick@wg0. Delete using this command

ip link delete wg0

Make sure the server is running and listing on UDP port 51280 as specified in our wg0.conf. Make sure also your instance is open on UDP port 51280 (for instance, if you are using AWS, make sure your security group allows inbound traffic on UDP port 51280).

# netstat -nutap|grep 51280
udp        0      0 0.0.0.0:51280           0.0.0.0:*                           -
udp6       0      0 :::51280        

I have tested connecting to the server using Windows 10 as the client and using Android as the client. Download the client installer for Windows and Android from https://www.wireguard.com.

The client configuration is this, change the values accordingly.

[Interface]
PrivateKey = aPlilXQB+qf+e5wOsy7A+DfMnEj4LjTMZDuXk/m2Skk= <- client private key
Address = 10.0.8.1/32
DNS = 1.1.1.1

[Peer]
PublicKey = QypmYvMDzvJ9enBPTcQEAC5incyjhe/WkLZjRAt+JTc= <- server public key
AllowedIPs = 0.0.0.0/0
Endpoint = 18.143.164.202:51280 <- server IP address

In the client Wireguard application, on the tunnel is activated, you should expect to see something like this. Note the transfer values should be immediately increasing for both received and sent.

If your received value is slow, it means something wrong with the tunnel. Check the log. What I found if in the log it is stuck at sending handshake or sending keepalive packet, there is something wrong with the 2 key pairs. I was able to resolve this issue by regenerating.

To check if the tunnel is running. Do a search on the internet “What is my IP address”. On Google, it should show your server’s IP address.

On Android, it is also possible to scan a QR code containing the client configuration.
Do this a Linux instance, where wg-client.conf is the client configuration.

apt install qrencode
qrencode -t ansiutf8 -r wg-client.conf

You can then scan this QR code using your Android Wireguard client.

Leave a Reply

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