2

For private use I only want to use a simple peer-to-peer openVPN connection without maintaining a complete Public Key Infrastructure. I have heard it can be simplified by using static keys, but how can I set this up using Raspberry Pi?

2 Answers 2

2

You can generate static secret keys and just preshare them to the devices using openVPN. Then this keys are used for authentication. There is no need to generate private/public keys and maintain them in an infrastructure with a certification authority.

For reference I use Raspbian Stretch Lite 2019-04-08 updated with sudo update && sudo full-upgrade && sudo reboot on 2019-05-01.

Example for this setup:

 10.8.0.1 10.8.0.2 / vpn tunnel ┌──────────┐ \ peer1 ╔════════════════╗ ╔=═══════════════════════════════════ peer2 RPi(eth0) <-----------> router <-------------> │ INTERNET │ \ wired / \ wan │ │ 192.168.50.2 192.168.50.1 172.217.18.174 └──────────┘ (public ip) 

I assume you have a working internet connection.
On the openvpn peer1 install openvpn:

rpi ~$ sudo -Es rpi ~# apt update rpi ~# apt full-upgrade rpi ~# apt install openvpn rpi ~# systemctl disable --now openvpn.service 

If you use systemd-networkd then install also

rpi ~# apt install openvpn-systemd-resolved 

Then generate a static secret key:

rpi ~# openvpn --genkey --secret /etc/openvpn/static.key 

Create a peer1 config file:

rpi ~# cat > /etc/openvpn/peer1.conf <<EOF dev tun ifconfig 10.8.0.1 10.8.0.2 secret static.key cipher AES-256-CBC EOF 

Start the openvpn peer1:

rpi ~# systemctl enable --now [email protected] rpi ~# exit rpi ~$ 

On the openvpn peer2 also install openvpn as shown above with that 5 or 6 commands. Don't generate a new static key, instead copy that one you have made on the openvpn peer1 to /etc/openvpn/ with same permission (sudo chmod 600 /etc/openvpn/static.key). Create a peer2 config file:

mngmt ~# cat > /etc/openvpn/peer2.conf <<EOF remote 192.168.50.3 dev tun ifconfig 10.8.0.2 10.8.0.1 secret static.key cipher AES-256-CBC EOF 

This config file is made to test the vpn tunnel on your local network first. Now start the peer2 with:

mngmt ~# exit mngmt ~$ sudo systemctl start [email protected] 

Now you should be able to ping the peer1:

mngmt ~$ ping 10.8.0.1 

If it works we can test to connect from the internet. To be sure not conflicting with local setup we have to use a complete different path to connect to the internet. For this I use my android cell phone with USB tethering to the management computer where I have disabled wifi on the phone to be sure only using 4G data uplink. I also disabled wifi on the management computer and pulled out its ethernet cord. The default port of openvpn is 1194 so you have to forward this port on your router to the local openvpn peer1 192.168.50.2 port 1194 (192.168.50.2:1194). It is important to use protocol udp not tcp. Look at the router what it's current public ip address is, in my example 172.217.18.174. Then change the line remote 192.168.50.3 in /etc/openvpn/peer2.conf to remote 172.217.18.174 and
reboot.

Then enable USB tethering on your mobile phone and start peer2. You can check if port forwarding is set on the remote router with:

mngmt ~$ sudo nmap -Pn -sU -p1194 172.217.18.174 Starting Nmap 7.70 ( https://nmap.org ) at 2019-08-03 16:20 BST Nmap scan report for p57A8602E.dip0.t-ipconnect.de (172.217.18.174) Host is up. PORT STATE SERVICE 1194/udp open|filtered openvpn Nmap done: 1 IP address (1 host up) scanned in 2.31 seconds 

This only checks if the port forwarding is active on the router. It does not check if the openvpn peer behind is active. This you can finally check with ping:

mngmt ~$ sudo systemctl start [email protected] mngmt ~$ ping 10.8.0.1 PING 10.8.0.1 (10.8.0.1) 56(84) bytes of data. 64 bytes from 10.8.0.1: icmp_seq=1 ttl=64 time=743 ms 64 bytes from 10.8.0.1: icmp_seq=2 ttl=64 time=504 ms 64 bytes from 10.8.0.1: icmp_seq=3 ttl=64 time=403 ms 

If this works then you have a running vpn tunnel through the internet to your local RasPi. If you want to connect in the other direction then just comment remote <ip address> in /etc/openvpn/peer2.conf and set it in /etc/openvpn/peer1.conf.

With this simple setup with a pre shared secret key you can ensure that the environment is working (port forwarding, routing etc.). Now you can improve the setup of openvpn step by step with all its nice features like TLS public key authentication, connecting whole subnets, not only one RasPi, using tap interfaces instead of tun interfaces to remotely play games that need broadcasts and so on. But this isn't subject of this site.


References:
[1] openvpn - Static Key Mini-HOWTO
[2] man openvpn

0

For peer-to-peer with static keys I would use tinc-vpn available as the apt package tinc.

It is simpler to manage than OVPN and much lighter, It is peer-to-peer with automatic routing and network forwarding and highly configurable.

It is flexible enough to be run out of a docker image for containerized VPN configurations (just mount the private key!)

  1. apt-get install tinc
  2. Follow the instructions to generate and share the keys

There are many tutorials on-line for this, and tinc supports many systems with the same configuration, for the official examples/tutorials that demonstrate the flexibility look at https://www.tinc-vpn.org/examples/

Mesh VPN topologies are also supported.

Setup

You need to create

  1. config file
  2. network up/down script
  3. host configuration
  4. Generate host keys

There are optional scripts that do thinks like host/segment available/unavailable (for logging or emailing for example if partner is offline)

Create the network config

myvpn is the name of the network and can be anything you like (it will become the name of the tunnel interface)

as root:

# Create the config directory cd /etc/tinc && mkdir myvpn && cd myvpn ` # Create a config file (https://www.tinc-vpn.org/documentation/tinc.conf.5) cat > tinc.conf <<-EOF Name = host1 AddressFamily = ipv4 Interface = myvpn ConnectTo = host2 EOF # create a network up script cat > tinc-up <<-EOF #!/bin/sh ifconfig $INTERFACE 192.168.240.10 netmask 255.255.255.0 EOF && chmod u+x tinc-up; # create a network down script cat > tinc-down <<-EOF #!/bin/sh ifconfig $INTERFACE down EOF chmod u+x tinc-down # create the host config mkdir hosts cat > hosts/host1 <<-EOF # External Address Address = my.external.ip # VPN Network segment served Subnet = 192.168.240.10/32 EOF # Generate the public/private key pair tincd -n myvpn -K # this creates a private key and places the public key into hosts/host1 cat hosts/host1 

Repeat the process on host 2 and exchange the host configuration file myvpn/hosts/host1 and myvpn/hosts/host2

Note: Only 1 host needs to be publically routable

afterwards start the network on each one tincd -n myvpn

you can enable automatic start at boot by adding echo myvpn >> /etc/tinc/nets.boot

2
  • How is that easier to manage than openvpn? Seems like same amount of configuration and having to know things. Openvpn static key is a very simple config as well. Commented Mar 8, 2021 at 8:28
  • @Cray, I agree, OpenVPN config is not difficult. But, the implementation is defined by a large config set, most of which is never touched by a user. In my experience, this tends to make "infrastructure as code" approach to system engineering more difficult than tools which leave fewer "black boxes". Contrast, a tinc deployment is defined by the configs in this answer, which are also scripted as heredocs. This approach, in my experience, improves the scalability of a system, and is more appropriate for applications requiring no configuration, like distributed pi clusters. Commented Mar 9, 2021 at 1:48

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.