blob: 3e064fb771be53143a39f28c490092ace3cb87e4 (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
|
#+TITLE: OpenBSD Wireguard VPN Gateway
#+DATE: 2023-12-29T16:35:36-05:00
#+DRAFT: true
#+DESCRIPTION:
#+TAGS[]: openbsd wireguard vpn
#+KEYWORDS[]: openbsd wireguard vpn
#+SLUG:
#+SUMMARY:
A couple of years ago I published a (link) blog post about creating an
OpenBSD VPN gateway using OpenVPN.
I've recently switched from an OpenVPN-based VPN provider to one that
uses Wireguard. As a result I've had to redo my VPN gateway.
One advantage this iteration has over my previous setup is that it no
longer requires third party software to be installed on the OpenBSD
router. Everything required comes as part of the base install.
The purpose of the VPN gateway is to allow any device on the network
to send its traffic through a VPN without installing anything. Instead
of installing one profile per device, the client just sets the VPN
Gateway as its default route.
Unlike the previous setup, in this version we're going to create a
separate routing table for the VPN. This lets us set the VPN as the
default route for the traffic we want to go through, while leaving the
rest of the system unaffected. It also lets us selectively send
traffic from the router through the VPN using the =route= command.
#+begin_src
route -T <rtable> exec <program>
#+end_src
Here's a diagram of what we're building.
The first step in the process is getting the VPN profile from the VPN
provider. It should look something like the following.
#+CAPTION: wireguard.conf
#+begin_src conf
[Interface]
PrivateKey = PRIVATEKEY
Address = XX.XX.XX.XX/32,YYYY:YYYY:YYYY:YYYY:YYYY:YYYY:YYYY/128
DNS = ZZ.ZZ.ZZ.ZZ
[Peer]
PublicKey = PUBLICKEY
AllowedIPs = 0.0.0.0/0,::0/0
Endpoint = ENDPOINT:51820
#+end_src
We then have to rewrite it into OpenBSD's =hostname.if(5)= format.
#+begin_src conf
inet XX.XX.XX.XX/32
inet6 YYYY:YYYY:YYYY:YYYY:YYYY:YYYY:YYYY/128
wgkey PRIVATEKEY
wgpeer PUBLICKEY wgaip 0.0.0.0/0 wgaip ::0/0 wgendpoint ENDPOINT 51820
#+end_src
#+begin_src conf
inet XX.XX.XX.XX/32
inet6 YYYY:YYYY:YYYY:YYYY:YYYY:YYYY:YYYY/128
wgkey PRIVATEKEY
wgpeer PUBLICKEY wgaip 0.0.0.0/0 wgaip ::0/0 wgendpoint ENDPOINT 51820
!route -T 1 add -inet default XX.XX.XX.XX
!route -T 1 add -inet6 default YYYY:YYYY:YYYY:YYYY:YYYY:YYYY:YYYY
#+end_src
#+begin_src conf
ext_if = "vio0"
vpn_if = "wg0"
pass in on $ext_if
pass in on $ext_if from $ext_if:network rtable 1
pass out on $ext_if from self # ($ext_if)
match out on $vpn_if from $ext_if:network to any nat-to $vpn_if
pass out on $vpn_if
#+end_src
sysctl thing
|