How to install OpenVPN with hardened configuration

In this guide I use my previous OpenSSL 1.1.1m build as a library for OpenVPN 2.5.5.

Let’s begin.
1. Install the prerequisites.
yum -y install lzo-devel pam-devel systemd-devel
2. Download the latest version of OpenVPN.
cd /opt
wget https://swupdate.openvpn.org/community/releases/openvpn-2.5.5.tar.gz

3. Extract the downloaded tarball and delete the tarball after extracted (Optional).
tar -xvzf openvpn-2.5.5.tar.gz
rm -f openvpn-2.5.5.tar.gz

4. Configure the installation.
cd openvpn-2.5.5
./configure –enable-x509-alt-username –enable-pkcs11 –enable-iproute2 –enable-selinux –enable-systemd

5. Compile the configured installation.
make
6. Check the compiled installation
make check
make sure the results are passed.

7. Install the OpenVPN.
make install
8. Export the binary’s path. (Optional)
export PATH=$PATH:/usr/local/sbin
source /root/.bashrc

9. Verify the OpenVPN is installed and using OpenSSL 1.1.1m library.
openvpn –version

10. Delete the configuration folder. (Optional)
cd /opt
rm -rf openvpn-2.5.5

11. Install the COPR plugin.
yum -y install yum-plugin-copr
12. Enable COPR dsommers’s repo and reload all repos’ cache.
yum -y copr enable dsommers/openvpn-release
yum clean all; yum makecache
13. Install Easy-RSA.
yum -y install easy-rsa
14. Disable CPOR dsommers’s repo and reload all repos’ cache. (Optional)
yum -y copr disable dsommers/openvpn-release
yum clean all; yum makecache
15. Create OpenVPN user.
useradd openvpn
passwd openvpn

16. Give root’s privileges to OpenVPN user.
usermod -aG wheel openvpn
17. Log in with OpenVPN user.
su – openvpn
18. Create OpenVPN and Easy-RSA working directories.
sudo mkdir -p /etc/openvpn/server
mkdir /home/openvpn/easy-rsa

19. Link Easy-RSA contents to working directory.
ln -s /usr/share/easy-rsa/3.0.8/* /home/openvpn/easy-rsa
20. Set Easy-RSA working directory privileges.
chmod 700 /home/openvpn/easy-rsa
21. Initialize Easy-RSA working directory.
cd /home/openvpn/easy-rsa
./easyrsa init-pki

22. Set Easy-RSA settings
vi vars
with the following configuration.
set_var EASYRSA_DN “org”
set_var EASYRSA_REQ_COUNTRY “ID”
set_var EASYRSA_REQ_PROVINCE “DKI Jakarta”
set_var EASYRSA_REQ_CITY “Jakarta Pusat”
set_var EASYRSA_REQ_ORG “destrianetworks”
set_var EASYRSA_REQ_EMAIL “tlsvpn@destrianetworks.id”
set_var EASYRSA_REQ_OU “Private”
set_var EASYRSA_ALGO “ec”
set_var EASYRSA_CURVE “x25519”
set_var EASYRSA_CA_EXPIRE “3650”
set_var EASYRSA_CERT_EXPIRE “3650”
set_var EASYRSA_CRL_DAYS “3650”
set_var EASYRSA_CERT_RENEW “30”
set_var EASYRSA_REQ_CN “tlsvpn”
set_var EASYRSA_DIGEST “sha384”

Note: Please use your own identity for every “EASYRSA_REQ_XXX” variables.
23. Generate CA for OpenVPN
./easyrsa build-ca nopass
with the Common Name same as EASYRSA_REQ_CN in Easy-RSA settings. (In this scenario it would be tlsvpn)

24. Copy the generated CA to Trusted CA directory and then update.
sudo cp /home/openvpn/easy-rsa/pki/ca.crt /etc/pki/ca-trust/source/anchors
sudo update-ca-trust

25. Generate certificate for OpenVPN server
./easyrsa gen-req tlsvpn nopass
with the Common Name same as EASYRSA_REQ_CN in Easy-RSA settings. (In this scenario it would be tlsvpn)

26. Copy the generated OpenVPN server key to OpenVPN working directory.
sudo cp /home/openvpn/easy-rsa/pki/private/tlsvpn.key /etc/openvpn/server
27. Sign the generated OpenVPN server certificate (In this scenario it would be tlsvpn)
./easyrsa sign-req server tlsvpn
answer yes to confirm.

28. Copy the OpenVPN server signed certificate and generated CA to OpenVPN working directory.
sudo cp /home/openvpn/easy-rsa/pki/issued/tlsvpn.crt /etc/openvpn/server
sudo cp /home/openvpn/easy-rsa/pki/ca.crt /etc/openvpn/server

29. Generate OpenVPN static key and then copy it to OpenVPN working directory.
openvpn –genkey secret ta.key
sudo cp ta.key /etc/openvpn/server

30. Create OpenVPN client working directory.
mkdir -p /home/openvpn/client-configs/keys
31. Set OpenVPN client working directory privileges.
chmod -R 700 /home/openvpn/client-configs
32. Generate certificate for OpenVPN client
./easyrsa gen-req someuser nopass
fill the Common Name with username. (In this scenario it would be someuser)

33. Copy the generated OpenVPN client key to OpenVPN client working directory.
cp /home/openvpn/easy-rsa/pki/private/someuser.key /home/openvpn/client-configs/keys
34. Sign the generated OpenVPN client certificate (In this scenario it would be someuser)
./easyrsa sign-req client someuser
answer yes to confirm.

35. Copy the OpenVPN client signed certificate to OpenVPN client working directory.
cp /home/openvpn/easy-rsa/pki/issued/someuser.crt /home/openvpn/client-configs/keys
36. Create OpenVPN client configuration directory.
sudo mkdir /etc/openvpn/server/ccd
37. Set OpenVPN client network configuration (In this scenario it would be someuser)
sudo vi /etc/openvpn/server/ccd/someuser
with the following configuration.
ifconfig-push 172.16.172.101 255.255.255.0
push “route 10.0.2.0 255.255.255.0”

Note: Please use your own configuration for “ifconfig-push” and “push“.
38. Copy the OpenVPN static key and generated CA to OpenVPN client working directory.
cp ta.key /home/openvpn/client-configs/keys
sudo cp /etc/openvpn/server/ca.crt /home/openvpn/client-configs/keys

39. Set OpenVPN client working directory contents ownership.
sudo chown openvpn:openvpn /home/openvpn/client-configs/keys/*
40. Generate CRL.
./easyrsa gen-crl

41. Copy the generated CRL to OpenVPN working directory.
sudo cp /home/openvpn/easy-rsa/pki/crl.pem /etc/openvpn/server
42. Configure OpenVPN server
sudo vi /etc/openvpn/server/server.conf
with the following configuration.
local 172.20.20.101
port 8443
proto udp
dev tun
ca ca.crt
cert tlsvpn.crt
key tlsvpn.key
crl-verify crl.pem
remote-cert-tls client
tls-cert-profile preferred
verify-client-cert require
tls-version-min 1.2
tls-version-max 1.3
tls-crypt ta.key
dh none
cipher AES-256-GCM
auth SHA384
key-direction 0
tls-ciphersuites TLS_CHACHA20_POLY1305_SHA256:TLS_AES_256_GCM_SHA384:TLS_AES_128_GCM_SHA256
tls-cipher TLS-ECDHE-ECDSA-WITH-CHACHA20-POLY1305-SHA256:TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384:TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256
tls-cipher TLS-ECDHE-RSA-WITH-CHACHA20-POLY1305-SHA256:TLS-ECDHE-RSA-WITH-AES-256-GCM-SHA384:TLS-ECDHE-RSA-WITH-AES-128-GCM-SHA256
tls-groups x25519:x448:secp521r1:secp384r1:secp256r1
tls-server
max-clients 100
topology subnet
server 172.16.172.0 255.255.255.0
client-config-dir ccd
ifconfig-pool-persist ipp.txt
client-to-client
keepalive 15 180
float
user nobody
group nobody
persist-key
persist-tun
verb 3
log openvpn.log
status openvpn-status.log
explicit-exit-notify 1

Note: Please use your own configuration for “local“, “port“, “cert“, “key“, and “server“.
43. Set OpenVPN server configuration privileges.
sudo chmod 600 /etc/openvpn/server/server.conf
44. Set sysctl configuration for OpenVPN
sudo vi /usr/lib/sysctl.d/50-default.conf
sudo vi /etc/sysctl.d/99-sysctl.conf

insert the following configuration on bottom.
# OpenVPN requirements
net.ipv4.ip_forward = 1
net.ipv4.conf.tun0.route_localnet = 1

45. Create a directory for the output of OpenVPN client generator.
mkdir /home/openvpn/client-configs/files
46. Configure OpenVPN client
vi /home/openvpn/client-configs/client.conf
with the following configuration.
client
remote 172.20.20.101
port 8443
proto udp
dev tun
nobind
resolv-retry infinite
remote-cert-tls server
verify-x509-name tlsvpn name
tls-version-min 1.2
tls-version-max 1.3
cipher AES-256-GCM
auth SHA384
key-direction 1
tls-ciphersuites TLS_CHACHA20_POLY1305_SHA256:TLS_AES_256_GCM_SHA384:TLS_AES_128_GCM_SHA256
tls-cipher TLS-ECDHE-ECDSA-WITH-CHACHA20-POLY1305-SHA256:TLS-ECDHE-ECDSA-WITH-AES-256-GCM-SHA384:TLS-ECDHE-ECDSA-WITH-AES-128-GCM-SHA256
tls-cipher TLS-ECDHE-RSA-WITH-CHACHA20-POLY1305-SHA256:TLS-ECDHE-RSA-WITH-AES-256-GCM-SHA384:TLS-ECDHE-RSA-WITH-AES-128-GCM-SHA256
tls-groups x25519:x448:secp521r1:secp384r1:secp256r1
tls-client
user nobody
group nobody
persist-key
persist-tun
verb 3

Note: Please use your own configuration for “remote” and “port“.
47. Set OpenVPN client configuration ownerships and its privilege.
sudo chown openvpn:openvpn /home/openvpn/client-configs/client.conf
sudo chmod 600 /home/openvpn/client-configs/client.conf
48. Create a script for OpenVPN client generator. (The script origins is here)
vi /home/openvpn/client-configs/make_config.sh
with the following codes.
#!/bin/bash

CLIENT=${1}
KEY_DIR=~/client-configs/keys
OUTPUT_DIR=~/client-configs/files
BASE_CONFIG=~/client-configs/client.conf

cat ${BASE_CONFIG} \
<(echo -e ‘<ca>’) \
${KEY_DIR}/ca.crt \
<(echo -e ‘</ca>\n<cert>’) \
${KEY_DIR}/${CLIENT}.crt \
<(echo -e ‘</cert>\n</key>’) \
${KEY_DIR}/${CLIENT}.key \
<(echo -e ‘</key>\n<tls-crypt>’) \
${KEY_DIR}/ta.key \

> ${OUTPUT_DIR}/${CLIENT}.ovpn

49. Set OpenVPN client generator privileges.
chmod 700 /home/openvpn/client-configs/make_config.sh
50. Generate OpenVPN client configuration file. (In this scenario it would be someuser)
/home/openvpn/client-configs/./make_config.sh someuser
51. Start OpenVPN service
sudo systemctl start openvpn-server@server.service
then check OpenVPN status
sudo systemctl status openvpn-server@server.service

and start OpenVPN service after boot.
sudo systemctl -f enable openvpn-server@server.service
52. Download the generated OpenVPN client configuration file in /home/openvpn/client-configs/files (In this scenario it would be someuser.ovpn) to client’s PC and then connect.

53. Verify the OpenVPN client’s connectivity logs.
sudo tail -f -n 0 /etc/openvpn/server/openvpn.log

54. Verify the connectivity by ping to VPN gateway and the network behind the OpenVPN server. (In this scenario it would be 172.16.172.1 and 10.0.2.15)

55. OpenVPN is ready to use.

The following guide is a summary about generate OpenVPN clients.
56. Generate certificate for OpenVPN client
cd /home/openvpn/easy-rsa
./easyrsa gen-req someone nopass
fill the Common Name with username. (In this scenario it would be someone)

57. Copy the generated OpenVPN client key to OpenVPN client working directory.
cp /home/openvpn/easy-rsa/pki/private/someone.key /home/openvpn/client-configs/keys
58. Sign the generated OpenVPN client certificate (In this scenario it would be someone)
./easyrsa sign-req client someone
answer yes to confirm.

59. Copy the OpenVPN client signed certificate to OpenVPN client working directory.
cp /home/openvpn/easy-rsa/pki/issued/someone.crt /home/openvpn/client-configs/keys
60. Set OpenVPN client network configuration (In this scenario it would be someone)
sudo vi /etc/openvpn/server/ccd/someone
with the following configuration.
ifconfig-push 172.16.172.102 255.255.255.0
push “route 10.0.2.0 255.255.255.0”

Note: Please use your own configuration for “ifconfig-push” and “push“.
61. Generate OpenVPN client configuration file. (In this scenario it would be someone)
/home/openvpn/client-configs/./make_config.sh someone
62. Download the generated OpenVPN client configuration file in /home/openvpn/client-configs/files (In this scenario it would be someone.ovpn) to client’s PC and then connect.

63. Verify the OpenVPN client’s connectivity logs.
sudo tail -f -n 0 /etc/openvpn/server/openvpn.log

The following guide is about to revoke OpenVPN clients.
64. Revoke an OpenVPN client certificate (In this scenario it would be someone)
cd /home/openvpn/easy-rsa
./easyrsa revoke someone

answer yes to confirm.

65. Re-generate CRL.
./easyrsa gen-crl

66. Copy the re-generated CRL to OpenVPN working directory.
sudo cp /home/openvpn/easy-rsa/pki/crl.pem /etc/openvpn/server
67. Restart OpenVPN service.
sudo systemctl restart openvpn-server@server.service
68. Verify the OpenVPN client is unable to establish VPN connection.

69. Verify the OpenVPN client’s connectivity logs.
sudo tail -f -n 0 /etc/openvpn/server/openvpn.log | grep revoked

70. The OpenVPN client is revoked.

Ade Destrianto
Just tryna git gud.

Leave a Reply

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