Abstract

This article presents a brief, step-by-step guide of setting up an VPN server which relays all your Internet traffic in a secure way so that you can surf the Internet as if you are at your server's location, with transmission between you and the server encrypted.

Recipe

Ingredients

  • A server running Ubuntu Server 14.04 LTS, which can be rent from a cloud service provider. Root access is required.
  • Understanding private IP address range: 192.168.0.0/16, 10.0.0.0/8, etc.
  • Knowing that a '#' before a Linux command indicates running under root privilege, contrast to '$'.

Instructions on the server side

Logging into the server

The typical way of administering remote server is through SSH. If you are running Windows on your own computer, PuTTY is one of the choice of SSH client. Note that you should download the Windows Installer on the PuTTY Download Page. After starting PuTTY, fill your host's IP address (or domain name if you have one) and click 'Open'.

PuTTY GUI

PuTTY GUI

Or if you are running Linux, just run ssh from your command line:

$ ssh <yourusername>@<yourserverIP>

Then you will be asked for password. Note that when you type the password, no feedback will show on your screen. This is a security feature of Linux. If there is a '$' precedes the cursor, type this to obtain root privilege:

$ sudo -s
[sudo] password for <yourusername> 
# <cursor>

Logging in public/private key pair is not covered in this article.

Obtaining software

We will run OpenVPN on both client and server. As Ubuntu provides fairly old versions of OpenVPN, it's better to add OpenVPN's official repository to system:

# wget -O - https://swupdate.openvpn.net/repos/repo-public.gpg|apt-key add -
# echo "deb http://swupdate.openvpn.net/apt trusty main" > /etc/apt/sources.list.d/swupdate.openvpn.net.list

And install OpenVPN:

# apt-get update && apt-get install openvpn

Setting up PKI

PKI refers to public key infrastructure, which is responsible for authenticating both your computer and your VPN server, and encrypting the traffic between them. Easy RSA provides a simple way to set up PKI.

Download Easy RSA from GitHub and extract files:

:~# wget https://github.com/OpenVPN/easy-rsa/releases/download/3.0.1/EasyRSA-3.0.1.tgz
:~# tar -xzvf EasyRSA-3.0.1.tgz
:~# cd EasyRSA-3.0.1
:~/EasyRSA-3.0.1# <cursor>

Rename vars.example to vars and edit using nano:

:~/EasyRSA-3.0.1# mv vars.example vars
:~/EasyRSA-3.0.1# nano vars

Find the line (use arrow keys on keyboard to move)

#set_var EASYRSA        "$PWD"

and modify it to (or add this line below)

set_var EASYRSA "/usr/local/etc/easy-rsa"

Type Ctrl+O to save and Ctrl+X to exit nano.

Then copy some files to /usr/local/etc/easy-rsa:

:~/EasyRSA-3.0.1# mkdir -p /usr/local/etc/easy-rsa
:~/EasyRSA-3.0.1# cp openssl-1.0.cnf /usr/local/etc/easy-rsa/
:~/EasyRSA-3.0.1# cp -R x509-types /usr/local/etc/easy-rsa/

Next, we will initialize PKI, build the CA, generate the CRL, create certificates for the server and your computer (i.e. the client):

:~/EasyRSA-3.0.1# ./easyrsa init-pki
:~/EasyRSA-3.0.1# ./easyrsa build-ca nopass
:~/EasyRSA-3.0.1# ./easyrsa gen-crl
:~/EasyRSA-3.0.1# ./easyrsa build-server-full myvpn-server nopass
:~/EasyRSA-3.0.1# ./easyrsa build-client-full myvpn-client1 nopass

Note that after running ./easyrsa build-ca nopass, you will be asked for Common Name of your CA. Type MyVPN or whatever you like. Special care should be taken to protect the .key files.

Write OpenVPN server configuration file

Copy the PKI files for the server to OpenVPN working directory:

:~/EasyRSA-3.0.1# cd /etc/openvpn
:/etc/openvpn# cp -a /usr/local/etc/easy-rsa/pki/ca.crt ca.crt
:/etc/openvpn# cp -a /usr/local/etc/easy-rsa/pki/issued/myvpn-server.crt myvpn-server.crt
:/etc/openvpn# cp -a /usr/local/etc/easy-rsa/pki/private/myvpn-server.key myvpn-server.key

Generate a Diffie-Hellman parameter:

:/etc/openvpn# openssl dhparam -out dh2048.pem 2048

Generate a tls-auth key:

:/etc/openvpn# openvpn --genkey --secret /etc/openvpn/ta.key

Create a client configuration file for all clients:

:/etc/openvpn# mkdir clients
:/etc/openvpn# cd clients
:/etc/openvpn/clients# nano DEFAULT

Edit DEFAULT as follows:

push "redirect-gateway def1 bypass-dhcp"
push "route-metric 0"
push "dhcp-option DNS 8.8.8.8"

iroute 10.0.0.0 255.0.0.0
iroute 192.168.0.0 255.255.0.0

Create vpnserver.ovpn at /etc/openvpn/:

:/etc/openvpn/clients# cd ..
:/etc/openvpn# nano vpnserver.ovpn

Save it as follows:

proto udp
port 1194
dev tun
server 10.245.63.0 255.255.255.0
topology subnet
persist-key
persist-tun
keepalive 10 60

remote-cert-tls client
tls-auth /etc/openvpn/ta.key 0
dh /etc/openvpn/dh2048.pem
ca /etc/openvpn/ca.crt
cert /etc/openvpn/myvpn-server.crt
key /etc/openvpn/myvpn-server.key

user nobody
group nogroup

verb 3
daemon
log-append /var/log/openvpn.log

client-config-dir /etc/openvpn/clients

Finally we are able to run the server side instance:

:/etc/openvpn# openvpn vpnserver.ovpn

We had set the OpenVPN to run in daemon mode, so no output will be shown in the terminal. Use tail command to check log:

:/etc/openvpn# tail -f /var/log/openvpn.log

If the log finishes with the following line, it means that the VPN server is successfully launched.

Fri Jan 15 14:31:27 2016 Initialization Sequence Completed

Configure packet forwarding

You will find that connecting to an OpenVPN server is like connecting to a WiFi router: You are assigned an private IP address and your requests/responses are passed through NAT. A 'router' will do this automatically while you must explicitly tell your server to forward your traffic.

:/etc/openvpn# sysctl -w net.ipv4.ip_forward=1
:/etc/openvpn# iptables -t nat -I POSTROUTING -o eth0 -s 10.245.63.0/24 -j MASQUERADE

Generate client configuration file

Switch to your home directory and create client configuration template:

:/etc/openvpn# cd ~
:~# nano client-config-template.ovpn

Then edit client-config-template.ovpn as follows, remember to replace <yourserverIP> with your server's IP address or domain name.

client
dev tun
nobind
float

remote <yourserverIP> 1194 udp

remote-cert-tls server
key-direction 1
reneg-sec 0

# Uncomment these lines if using Linux and experiencing DNS cache poisoning
# Make sure the script update-resolv-conf exists
;script-security 2
;up /etc/openvpn/update-resolv-conf
;down /etc/openvpn/update-resolv-conf

Finally append key files to the client configuration file:

:~# cat client-config-template.ovpn > myvpn-client1.ovpn
:~# echo -e '\n<cert>' >> myvpn-client1.ovpn
:~# cat /usr/local/etc/easy-rsa/pki/issued/myvpn-client1.crt >> myvpn-client1.ovpn
:~# echo -e '</cert>\n' >> myvpn-client1.ovpn 
:~# echo -e '<key>' >> myvpn-client1.ovpn
:~# cat /usr/local/etc/easy-rsa/pki/private/myvpn-client1.key >> myvpn-client1.ovpn
:~# echo -e '</key>\n' >> myvpn-client1.ovpn
:~# echo -e '<ca>' >> myvpn-client1.ovpn
:~# cat /usr/local/etc/easy-rsa/pki/ca.crt >> myvpn-client1.ovpn
:~# echo -e '</ca>\n' >> myvpn-client1.ovpn
:~# echo -e '<tls-auth>' >> myvpn-client1.ovpn
:~# cat /etc/openvpn/ta.key >> myvpn-client1.ovpn
:~# echo -e '</tls-auth>' >> myvpn-client1.ovpn

Instructions on your computer

The first step is to download myvpn-client1.ovpn from the server. The simplest way is showing content of the file using nano and copy-paste it into your local text editor, save. Filezilla supports downloading via SSH by changing the port from 21 to 22. If you are running Linux on your computer, it's recommended to use scp:

:~$ scp <yourusername>@<yourserverIP>:~/myvpn-client1.ovpn myvpn-client1.ovpn

Windows

  • Go to OpenVPN Download Page and download an installer, install.
  • Save your myvpn-client1.ovpn to %PROGRAM%\OpenVPN\config\
  • Run OpenVPN GUI as Administrator
  • Right-click the OpenVPN icon on the system tray, choose myvpn-client1 and click 'Connect'.

Linux

  • Install OpenVPN just like installing on the server.
  • Save your myvpn-client1.ovpn to wherever you like.
  • Type sudo openvpn myvpn-client1.ovpn to launch VPN client.

References

https://community.openvpn.net/openvpn/wiki/OpenvpnSoftwareRepos
Crist, Eric F., and Jan Just Keijser. Mastering OpenVPN. Packt Publishing Ltd, 2015.