VPN
Wireguard
To use Wireguard inside of a LXC container the host has to have Wireguard installed since LXC guests are run with the kernel of the host system. Additionally you'll want the wireguard-tools
package in the LXC guest.
Route Subnet Through Wireguard Interface
Funneling all traffic from an Ethernet interface through a Wireguard interface is relatively easy once you're familar with how packets flow through Linux. You'll mostly just need to modify your Wireguard *.conf
file to add the Table
, PostUp
, and PreDown
parameters.
You also need to setup IP masquerading of outgoing traffic on your Wireguard interface. See below for instructions.
[Interface]
PrivateKey = ****
Address = 192.168.0.5/28
Table = 9
PostUp = ip rule add iif eth1.9 lookup 9
PreDown = ip rule del iif eth1.9 lookup 9
[Peer]
AllowedIPs = 0.0.0.0/0
...
Line 4: All rules/routes should be applied to a custom route table 9
. If you want to name your custom route table you could do echo "9 warp" > /etc/iproute2/rt_tables
and then say Table = warp
for improved readability.
Line 5: Add a rule that all traffic coming in interface eth1.9
should use custom route table 9
. Because you defined a peer with AllowedIPs = 0.0.0.0/0
a default route will be setup on custom route table 9
that redirects all traffic to the Wireguard interface. If you named your custom route like shown above you can say lookup warp
inplace of lookup 9
.
Line 6: Just the inverse of line 5 to clean up after ourselves when taking down the Wireguard interface.
Setup IP Masquerading
IP Masquerading is a technique that hides an entire IP address space, usually consisting of private IP addresses, behind a single IP address in another, usually public address space.
Source: Wikipedia
How To
The easiest way to set this up are to append some netfilter rules to the PostUp
and PreDown
parameters.
...
PostUp = ...; iptables -t nat -A POSTROUTING -o wg0 -j MASQUERADE
PreDown = ...; iptables -t nat -D POSTROUTING -o wg0 -j MASQUERADE
[Peer]
...
Although this works you risk the iptables/netfilter rules getting squashed by Shorewall when if it is restarted while the Wireguard interface exists. It is best to have Shorewall setup the masquerading by making a simple declaration in /etc/shorewall/snat
. I've included the other shorewall configuration files that would be necessary to make this setup work.
This tells Shorwall to masquerade all IPs going out on WG_IF
…
# /etc/shorewall/snat
#ACTION SOURCE DEST
+ MASQUERADE 0.0.0.0/0 WG_IF
Then we define WG_IF
…
# /etc/shorewall/interfaces
#ZONE INTERFACE OPTIONS
warp WARP_IF tcpflags,nosmurfs,routefilter=2,logmartians,physical=eth1.9
+ wg WG_IF physical=wg0
Then we define the wg
zone…
# /etc/shorewall/zones
#ZONE TYPE OPTIONS IN OUT
# OPTIONS OPTIONS
warp ipv4
+ wg ipv4
Then we allow the warp
zone to send packets to the wg
zone.
# /etc/shorewall/policy
#SOURCE DEST POLICY LOGLEVEL RATE CONNLIMIT
- warp $FW ACCEPT $LOG_LEVEL
+ warp $FW,wg ACCEPT $LOG_LEVEL