VPN with CA and Certificates on PI

From Coolscript
Jump to navigation Jump to search



This is howto setup a OpenVPN connection from you mobile device to your Home-LAN in less than 20 Minutes.





Intro

This configuration example allows your mobile devices to connect and use the remote server to act as gateway for outbound connections and lets you access the Home-LAN securely.

The setup includes a Certificate Authority using EasyRSA and a certificate issued for client1 which can be used on your mobile device.

Requirements

  • Your Home LAN
  • Raspberry-PI or alternative another Linux Server within the Home-LAN for OpenVPN
  • The ISP Router of the Home-LAN must forward tcp 1194 to the above OpenVPN Server
  • Mobile device with the OpenVPN Client installed and connected to the Internet




Prepare

  • Install packages
apt install openvpn easy-rsa


Tune the system control parameters to use the BBR congestion control algorithm:

  • /etc/sysctl.conf
net.core.default_qdisc=fq
net.ipv4.tcp_congestion_control=bbr
#Enable ip forward
net.ipv4.ip_forward=1
  • Activate changes:
# sysctl -p


  • Create an OpenVPN user as a system user with no shell
# useradd -r -M -s /usr/sbin/nologin ovpnuser
  • Install packages
# apt install openvpn easy-rsa

Configure CA for OpenVPN

  • Copy the complete EasyRSA materials into a working area for OpenVPN, the default path is /etc/openvpn
# cp -r /usr/share/easy-rsa /etc/openvpn
# cd /etc/openvpn/easy-rsa
# cp vars.example vars
  • Edit the vars file in /etc/openvpn/easy-rsa/vars
set_var EASYRSA_ALGO ec
set_var EASYRSA_CURVE secp521r1
set_var EASYRSA_CA_EXPIRE 3650
set_var EASYRSA_CERT_EXPIRE 3650
set_var EASYRSA_CRL_DAYS 3650
set_var EASYRSA_DIGEST "sha512"


Initialize the public key infrastructure (PKI):

# cd /etc/openvpn/easy-rsa
# ./easyrsa init-pki


# touch /etc/openvpn/easy-rsa/pki/.rnd
# touch /etc/openvpn/easy-rsa/pki/index.txt.attr


  • Create Certification Authority (CA)
# cd /etc/openvpn/easy-rsa/
# ./easyrsa build-ca nopass


  • Create CSR for server0.
# cd /etc/openvpn/easy-rsa/
# ./easyrsa gen-req server0 nopass
  • Sign Cert for server0
# cd /etc/openvpn/easy-rsa/
# ./easyrsa sign-req server server0


  • Client CSR client1
# cd /etc/openvpn/easy-rsa/
# ./easyrsa gen-req client1 nopass
  • Sign client1
# cd /etc/openvpn/easy-rsa/
# ./easyrsa sign-req client client1


  • Copy Certs to the expected location:
/etc/openvpn/easy-rsa#
cp pki/ca.crt ..
cp pki/issued/server0.crt ../server
cp pki/private/server0.key ../server
cp pki/issued/client1.crt ../client
cp pki/private/client1.key ../client
  • Create static key
/etc/openvpn# openvpn --genkey --secret tls-crypt.key

OpenVPN Server Configuration

  • /etc/openvpn/server.conf
topology subnet
user ovpnuser
group ovpnuser
local 0.0.0.0
port 1194
proto tcp
dev tun
ca ca.crt
cert server/server0.crt
key server/server0.key
tls-crypt tls-crypt.key
dh none
ecdh-curve secp521r1
server 10.8.0.0 255.255.255.0
ifconfig-pool-persist /etc/openvpn/ipp.txt
push "redirect-gateway def1 bypass-dhcp"
push "dhcp-option DNS 1.1.1.1"
push "dhcp-option DNS 1.0.0.1"
keepalive 10 120
cipher AES-256-GCM
auth SHA512
tls-version-min 1.2
remote-cert-tls client
remote-cert-eku "TLS Web Client Authentication"
persist-key
persist-tun
status /var/log/openvpn-status.log
log /var/log/openvpn.log
verb 3

Apply the new configuration to systemctl

systemctl daemon-reload 

Restart OpenVPN

systemctl restart openvpn

Open VPN Client configuration

Save this file with including the file extension .ovpn to allow the import on foreign devices.

client
dev tun
proto tcp
remote x.x.x.x 1194
resolv-retry infinite
nobind
persist-key
persist-tun
tls-client
<ca>
-----BEGIN CERTIFICATE-----
MIIC...
-----END CERTIFICATE-----
</ca>
<cert>
-----BEGIN CERTIFICATE-----
MIIC...
-----END CERTIFICATE-----
</cert>
<key>
-----BEGIN PRIVATE KEY-----
MIHu...
-----END PRIVATE KEY-----
</key>
<tls-crypt>
-----BEGIN OpenVPN Static key V1-----
6160...
-----END OpenVPN Static key V1-----
</tls-crypt>
remote-cert-tls server
remote-cert-eku "TLS Web Server Authentication"
cipher AES-256-GCM
auth SHA512
block-outside-dns
verb 3

Nftables

If you run already use nft than add into the INPUT Chain:

iif tun0 accept comment "accept openvpn"
tcp dport 1194 counter accept comment "Allow OpenVPN"

An allow forwarding between the networks within the FORWARD Chain

iifname "tun0" oifname "eth0" counter accept comment "allow tun0 to eth0"
iifname "eth0" oifname "tun0" counter accept comment "allow eth0 to tun0"


  • full example of /etc/nftables.conf
table ip filter_v4 {
       chain INPUT {
               type filter hook input priority 0; policy drop;
               iif "lo" accept comment "accept loopback"
               tcp dport openvpn counter accept comment "Allow OpenVPN"
               ip protocol icmp accept comment "Allow ICMP"
               ct state { established, related } counter accept comment "accept related connections"
               counter jump my_drop
       }

       chain OUTPUT {
               type filter hook output priority 0; policy drop;
               ct state { established, related, new } counter accept comment "accept all local outbound connections"
       }


       chain FORWARD {
        type filter hook forward priority 0; policy drop;
        iifname "tun0" oifname "eth0" counter accept comment "allow tun0 to eth0"
        iifname "eth0" oifname "tun0" counter accept comment "allow eth0 to tun0"
        counter jump my_drop
       }

       chain my_drop {
               meta l4proto icmp counter log prefix "DROP-ICMP "
               meta l4proto tcp counter log prefix "DROP-TCP "
               meta l4proto udp counter log prefix "DROP-UDP "
               drop
       }
}
table ip nat {
       chain PREROUTING {
               type nat hook prerouting priority -100; policy accept;
       }

       chain POSTROUTING {
               type nat hook postrouting priority 100; policy accept;
               ip saddr 10.8.0.0/24 oif "eth0" counter masquerade comment "masq for vpn"
       }
}

Start/Stop/Enable Nftables

  • Run to manual start (apply) the script:
nft -f /etc/nftables.conf
  • Run to manual stop nft:
nft flush ruleset
  • To enable at system start run:
systemctl enable nftables


IPhone Screenshots

Import the openvpn configuration on your device to get connected

  • Swipe to connect
  • Showing Stats after connected sucessful