Nexus7, Android 4.2 and OpenVPN 2

2012.11.18
I needed a way to get "road-warrior" remote access to my network resources and SSH wasn't doing everything I needed, it was time to setup a VPN. It's a common problem and there is a common solution. During my VPN configuration I was all over the Internet pulling in parts of the solution so I thought I'd wrap it all up in one place. This is a solution for my problem, yours may be different.

First a bit of context...
I actually have two networks, one wireless and the other wireline. There is no connection between the two, they are autonomous. The wireless network exists for convenience and no servers run on it, just clients ... tablets, laptops, PS3 etc. The wireline network has desktop/laptop clients and servers (print/NAS/etc) - this is what I need remote access to. When I travel, one or more laptops come with me. This is what my wireline network looks like:
NetworkDiagram.png
My DNS/DHCP server is not on my gateway router. This can cause problems, especially if your router doesn't support static routes.

I am using an Alix.2C3 to provide infrastructure services; DNS, DHCP and now OpenVPN. DNS & DHCP services are provided by dnsmasq and are outside the scope of this post. OpenVPN 2.1 provides the VPN server endpoint.

The Android client is OpenVPN Android Client 1.1.4 (build 21).

My linux clients are OpenVPN 2.2.1 x86_64-linux-gnu.

Items in RED are values from my equipment - you'll need to substitute values for your equipment.

Items in Green are commands to be entered.

Items in Grey are system prompts or responses.

Setting up a road warrior OpenVPN has the following steps:
1. Install OpenVPN on Server and Clients.
2. Create PKI infrastructure and generate keys
3. Configure the Server
4. Configure the Client(s)
5. Distribute client keys
6. Testing

1. Install OpenVPN on Server and Clients.
I'm not going to cover installation - it varies by server OS/Distribution and frankly it's usually pretty easy. OpenVPN.net has a great overview which I was able to use for my installation.

2. Create PKI infrastructure and generate keys
This is straightforward. Read up on this at OpenVPN.net. Just remember to create one client certificate & key for each device you wish to connect to the VPN ... sharing one key among devices is not recommended.

3. Configure the Server
My VPN is configured to use the private network 10.12.34.x/24 ... adjust accordingly if you'd rather use something else. The endpoint is on 192.168.1.x.
There is a great walk-through at OpenVPN.net or you can start with what I did:
port 1194
proto udp
dev tun
ca keys/ca.crt
cert keys/server.crt
key keys/server.key # This file should be kept secret
dh keys/dh1024.pem
server 10.12.34.0 255.255.255.0
ifconfig-pool-persist ipp.txt
push "route 192.168.1.0 255.255.255.0"
push "redirect-gateway"
keepalive 10 120
cipher BF-CBC # Blowfish (default)
comp-lzo
max-clients 5
user nobody
group nogroup
persist-key
persist-tun
status openvpn-status.log
verb 4
mute 20

I need to NAT the VPN streams in my network so that other devices in the network, including the default gateway router, will know where to send traffic.
As root:

  1. Execute this to update your iptables:
    • iptables -t nat -A POSTROUTING -s 10.12.34.0/24 -o eth0 -j MASQUERADE
  2. Save the iptables configuration:
    • iptables-save > /etc/firewall.conf
  3. Update Startup scripts to restore the saved iptables config:
    • vi /etc/network/if-up.d/iptables
      #!/bin/sh
      /sbin/iptables-restore < /etc/firewall.conf

4. Configure the Client(s)
There are two client types I need to configure for; Android tablet(s) and everything else.

4.1 Android OpenVPN configuration
client
remote a.b.c.d
dev tun
proto udp
resolv-retry infinite
nobind
persist-key
persist-tun
remote-cert-tls server
cipher BF-CBC
comp-lzo
verb 5
auth-user-pass

4.2 Generic OpenVPN configuration file:
client
dev tun
proto udp
remote a.b.c.d
float
resolv-retry infinite
nobind
user nobody
group nogroup
persist-key
persist-tun
mute-replay-warnings
ca ca.crt
cert client.crt
key client.key
cipher BF-CBC
comp-lzo
verb 3
remote-cert-tls server

a.b.c.d is the IP or hostname of your OpenVPN server. This file has 3 additional entries in it ... the ca.crt, client cert and client key. The android example had these combined into a single .p12 file and imported but they are normally broken out as seen here.

5. Distribute client keys
You need to provide each client with a VPN certificate & key. Each client should have their own key - if you ever need to revoke a certificate this will make it a bit easier.
5.1 Android Credentials
On your PKI server (from step 2) do:
cd .../easy-rsa
. ./vars
cd keys
openssl pkcs12 -export -in android.crt -inkey android.key -certfile ca.crt -name android -out android.p12

android.p12 now contains the embedded client private key so it should be kept secret and transported securely to your android device.
I copied my android OpenVPN configuration file to:
"/sdcard/OpenVPN/android.ovpn"
I copied my android.p12 credentials file to:
"/sdcard/OpenVPN/android.p12"
5.2 Generic Credential usage
Nothing special is needed beyond making sure that the certificates and key file locations are specified correctly in the configuration file.

6. Testing
You can now import both files into OpenVPN Connect...
Start the OpenVPN app.
1
Tap the menu
2
Select Import
3
Select Import PKCS#12 from SD card
4
Tap the android.p12 entry
5
Tap the Select button
6
Enter the certificate password
7
Accept the default name of certificate ... you can change it if you want, this is the user visible label.
8
Go back to the menu, Tap Import and this time select Import Profile from SD card
9
Tap the android.ovpn entry and then Tap Select
10
Enter the certificate username (android) and password, then Tap the Connect button. I've blurred out my IP address in this screen shot.
11
You should now be connected to your OpenVPN server.