Hello, since there are a lot of howtos how to make OpenVPN work with a tun device in routing mode here I want to share how to make OpenVPN work with a tap device in bridged mode in an iocage jail. I hope I did not forget a step.
openvpn in a FreeBSD iocage jail
voilá, your clients should now be able to connect to your network.
If you have any feedback for improvements, please do so.
openvpn in a FreeBSD iocage jail
- prepare your jail
This was done with FreeNAS 11.1-U1
iocage jail was created on the shell using FreeBSD 11.1-RELEASE
I work with ports and use portmaster and portsnap.
jail options I am using are
Code:allow_mount_devfs:1 allow_raw_sockets:1 allow_set_hostname:1 allow_sysvipc:1 vnet:on ip4_addr:vnet0|192.168.1.XXX/24 # give it a vaild IP address defaultrouter:192.168.1.1 # set to your standard gateway
- install openvpn
portmaster security/openvpn
add ovpn to /etc/rc.conf
sysrc openvpn_enable="YES"
sysrc openvpn_if="tap"
- create keys
I used parts of the following howto https://ramsdenj.com/2016/07/25/openvpn-on-freebsd-10_3.html
open the easyrsa config file
nano /usr/local/etc/openvpn/easy-rsa/vars
and edit anything you like to accomodate your needs; i did change:
Code:set_var EASYRSA_REQ_COUNTRY "XX" set_var EASYRSA_REQ_PROVINCE "yourprovince" set_var EASYRSA_REQ_CITY "yourcity" set_var EASYRSA_REQ_ORG "yourorganisation" set_var EASYRSA_REQ_EMAIL "admin@youremail.com" set_var EASYRSA_REQ_OU "IT" set_var EASYRSA_KEY_SIZE 2048 set_var EASYRSA_CA_EXPIRE 3650 set_var EASYRSA_CERT_EXPIRE 3650
change to the bourne shell (`sh`) to make the easyrsa script work.
you can see all commands with
./easyrsa.real help
./easyrsa.real help COMMAND
./easyrsa.real help options
initialize key infrastructure
./easyrsa.real init-pki
build certificate authority
./easyrsa.real build-ca
build server certificate
./easyrsa.real build-server-full openvpn-server nopass
check if successful
./easyrsa.real show-cert openvpn-server
generate diffie hellman parameters
./easyrsa.real gen-dh
build client certificate
./easyrsa.real build-client-full <name>
# I use as name the device I want to use it with, so I can revoke it if I loose it.
- move keys
With the files created, move the key’s to their destination.
The files of importance are:
In pki/:
dh.pem - Diffie Hellman parameters. Needed by server.
ca.crt - Root CA certificate. Needed by server and all clients.
In pki/issued/:
openvpn-server.crt - Server certificate. Needed by server.
<name>.crt - Client certificate. Needed by client.
In pki/private/ [These are secret]:
openvpn-server.key - Server key. Needed by server.
<name>.key - Client key. Needed by client.
ca.key - Root CA key. Needed by key signing machine.
So the following keys should be moved to the server:
pki/dh.pem
pki/ca.crt
pki/issued/openvpn-server.crt
pki/private/openvpn-server.key
Make a directory for the keys in the openvpn directory:
mkdir /usr/local/etc/openvpn/keys
copy the server keys:
cp pki/dh.pem \
pki/ca.crt \
pki/issued/openvpn-server.crt \
pki/private/openvpn-server.key \
/usr/local/etc/openvpn/keys
since openvpn 2.4 you also need a ta.key inside the keys directory (and inside the .ovpn profile)
openvpn --genkey --secret /usr/local/etc/openvpn/keys/ta.key
and from the following create the ovpn profile:
pki/ca.crt
pki/issued/<name>.crt
pki/private/<name>.key
/usr/local/etc/openvpn/keys/ta.key
I just made a new folder to store my *.ovpn profile files, but it does not matter, since those will be moved to the clients later.
nano /usr/local/etc/openvpn/keys/ovpn/<name>.ovpn
Code:client remote <here.comes.your.domain.name> 1194 proto udp dev tap persist-key persist-tun resolv-retry infinite nobind compress lz4-v2 verb 3 cipher AES-256-CBC tun-mtu 1500 key-direction 1 remote-cert-tls server auth-nocache mssfix 1400 <tls-auth> insert ta.key here (same for all clients) </tls-auth> <ca> insert ca.crt here (same for all clients) </ca> <cert> insert client cert </cert> <key> insert client key (protected by passphrase) </key>
move the ovpn profile to your device that should connect and import it into the client application (which is the openvpn gui on windows in my case)
for iOS devices, you might need to encode the keys in another way.
on OSX i had to remove compress lz4-v2 and cipher AES-256-CBC to make it work in Tunnelblick
- create up and downscript for handling creation of bridge
this will raise a bridge when starting the ovpn server with the correct interfaces. ${dev} will automatically be replaced by the device ovpn creates.
cd /usr/local/etc/openvpn/
nano up.sh
Code:#!/bin/sh # Setup Ethernet bridge ifconfig bridge0 create ifconfig bridge0 addm vnet0 #this has to be the name of the virtual device and can differ. epair0b is also possible, check with ifconfig ifconfig bridge0 addm ${dev} ifconfig bridge0 inet 192.168.1.14/24 # the IP of your ovpn jail! ifconfig ${dev} up ifconfig bridge0 up
nano down.sh
Code:#!/bin/sh ifconfig bridge0 destroy
- edit openvpn config
nano /usr/local/etc/openvpn/openvpn.conf
I adjusted following values, be sure to modify the server-bridge parameter to your network and pick a IP-range that is not in your DHCP range to avoid IP address collisions:
Code:port 1194 proto udp dev tap ca /usr/local/etc/openvpn/keys/ca.crt cert /usr/local/etc/openvpn/keys/openvpn-server.crt dh /usr/local/etc/openvpn/keys/dh.pem ifconfig-pool-persist ipp.txt # first is the gateway (the same as the vnet interface has; netmask; IP-range start; IP-range stop) server-bridge 192.168.1.1 255.255.255.0 192.168.1.230 192.168.1.248 client-to-client keepalive 10 120 tls-auth /usr/local/etc/openvpn/keys/ta.key 0 cipher AES-256-CBC compress lz4-v2 push "compress lz4-v2" user nobody group nobody persist-key persist-tun status openvpn-status.log log /var/log/openvpn.log verb 3 explicit-exit-notify 1 up /usr/local/etc/openvpn/up.sh down /usr/local/etc/openvpn/down.sh # script-security so the scripts can be started script-security 2 tun-mtu 1500 mssfix 1400 remote-cert-tls client
well, then let's start this thing up
service openvpn start
when I started the service the first time up first none, then on second try 256 tap devices where created. I had to restart FreeNAS to reset all tap devices and on the second try everything worked (also consistently after reboots).
- configure router/firewall
check that traffic on UDP 1194 is allowed and forwarded to your ovpn jail.
voilá, your clients should now be able to connect to your network.
If you have any feedback for improvements, please do so.