RunByCoffee

@runbycoffee

IT guy with an interest in security, privacy, OSINT, dreams, and coffee.

2,856 words

Thank Guestbook
You'll only receive email when RunByCoffee publishes a new post

VPN on pfSense with "Killswitch"

A VPN is a great solution for privacy, and at times, a great solution for security too. Many people run VPN's using software installed on their PC's - this is absolutely better than nothing, but can still give room for error if the connection disconnects and the software contains no killswitch, or, the software's killswitch doesn't work as designed.

Additionally, you may accidentally forget to turn your VPN on, or, if your PC is booting up, you may inadvertently leak personal information prior to the VPN turning on. The solution to this is a VPN at the network level - this way, it is device-agnostic, and always on.

I utilise pfSense for this, and NordVPN as my provider. This guide will cover such a setup - however, the same overall process will work with any VPN provider (it will just require some tweaks to work with your provider).

The Process

Set up Static IP mappings

For every machine you will have connecting through the VPN, you'll want to create a static address mapping in DHCP. This will ensure that the firewall rules you will create (which will apply to IP addresses) will remaing effective due to the consistency of the addresses assigned.

I'm assuming you're fairly familiar with the pfSense interface, but if not, go to Services > DHCP Server > DHCP Static Mappings and click the Add button. You'll just need the MAC address, and an IP outside of your DHCP scope.

Create a Firewall Alias Group

To make rule creation simpler, we'll create a firewall alias, and use that for all the rules. Then, later on, adding a new device to the VPN is as simple as adding it into the firewall alias. To do this, go Firewall > Aliases, then click Add and give it a name. In my example, I've named it VPNClientsDoubleVPN so it's easy for me to distinguish later. Make sure to click Save when you're done.

Firewall Alias

If you have IPv6 enabled on your network, be mindful of needing to add those addresses too (otherwise you may have some leakage).

Import the CA Cert

Go to the NordVPN Tools Page and pick a server that relates to you. I'm picking one of the DoubleVPN servers in this part. Download the OpenVPN config - generally you'd pick the UDP one. In that file, there's a certificate - it'll start at -----BEGIN CERTIFICATE---- and go through to ----END CERTIFICATE---- - copy this, including those lines.

Then, go to System > Certificate Manager > CA's > Add. Give it a descriptive name like Nord_TW_HK3. Change the Method to Import an existing Certificate Authority. Then, paste your copied certificate in the Certificate Data field and click Save.

CA Import

Set up the VPN connection

At this stage, we'll just set up the connection to the VPN; routes and NAT etc will be done futher down.

In pfSense, navigate to VPN > OpenVPN > Clients. The settings you require are below:

Setting Name Setting Value
Disabled Unticked
Server Mode Peer to Peer (SSL/TLS)
Protocol UDP on IPv4 Only (in my case, for Double VPN, this will be TCP)
Device mode tun - Layer 3 tunnel mode
Interface Your outgoing interface (WAN, for me)
Local port Can be left blank
Server host or address VPN endpoint - tw-hk3.nordvpn.com in my case
Server port Generally, 1194 if UDP - for me, 443
Description Something that makes sense - NordVPN_TW-HK3 is what I used
Username Your NordVPN user
Password Your NordVPN password
TLS Configuration Tick Use a TLS Key
Automatically generate a TLS key Untick this
TLS Key Copy and paste the OpenVPN Static Key from the config file you downloaded into this field. You'll find it toward the end of the config file - copy from the BEGIN line to the END line inclusive.
TLS Key Usage Mode TLS Authentication
Peer Certificate Authority The CA cert we imported earlier - Nord_TW-HK3
Client Certificate None
Encryption Algorithm AES-256-GCM
Enable NCP Checked
NCP Algorithms AES-256-GCM and AES-256-CBC (You'll need to click the existing entry to remove it)
Auth Digest Algorithm SHA512 (512-bit)
Hardware Crypto Select one if you have a hardware crypto module
Tunnel Compression No LZO Compression [Legacy style,comp-lzo no]
Topology Subnet – One IP address per client in a common subnet
Don't pull routes Tick this
Custom options See block below
Gateway Creation IPv4 only

Click save.

tls-client;
remote-random;
tun-mtu 1500;
tun-mtu-extra 32;
mssfix 1450;
persist-key;
persist-tun;
reneg-sec 0;
remote-cert-tls server;

Assign the Interface

Go to Interfaces > Assignments. Under Available Network Ports, click the drop down and choose your newly created VPN interface, then click Add. After that, click Save.

Once done, you may wish to rename the interface from OPT1 or similar to another better named interface. Just click on the interface name in the list, and change the Description - you'll also need to tick Enable interface. I also check Block Private Networks and Block Bogon Networks.

Once saved, click Apply the changes.

Set up NAT

We'll need to add some NAT rules for our traffic to get through. You may already be doing this manually, or you may have gone the lazy route and just had fully auto. I've gone the combo - the "Hybrid" route so that the system subnets have auto created rules (so that they are auto added if any new ones are added), but I can still add my manual rules.

Click to Add a new rule, then choose the Interface you just made above. Address family should be IPv4, Protocol as Any, Soure Network will be the Internal subnet of whatever network you are NAT'ing for - in my case, 10.15.15.0/24, and Destination will be Any. Translation address will be Interface Address. Give it a description and click save.

Once saved, click Apply. Create one of these for each of your network ranges you wish to NAT for/use with the VPN.

Set up Firewall Rules

We'll set up a our rules in Firewall > Rules on your LAN interface (I'm presuming you know how to do this if you already have a functioning pfSense). If you don't use secure + private DNS servers on your pfSense already, you may wish to create a rule which blocks all queries to the LAN DNS server from any client in the VPN Alias group. If you do this, make sure that your DHCP Static Mappings are set to issue your VPN's DNS server to these clients for direct querying.

You may also wish to block all IPv6 from any client in that alias, if you don't already drop all IPv6 at the Firewall level (as I currently do). The main rule you'll want is the one that sends all traffic out the VPN. Add a rule like so:

Setting Name Setting Value
Action Pass
Interface Your LAN Interface
Address Family IPv4
Protocol Any
Source Single host or alias: Enter your Firewall Alias name here
Destination Any, or, if you need to access other internal networks, create an alias of all local subnets, and invert the match to that (therefore tunneling out everything but your local networks)
Advanced options Show advanced
Tag VPN_NO_WAN_EGRESS (this is the tag we'll use to make killswitch)
Gateway Your VPN interface

Then click Save and Apply.

Finally, add a rule to your Floating interface to block any outgoing from IP.

Setting Name Setting Value
Action Block (or Reject)
Quick Ticked
Interface WAN (or your main outgoing)
Direction Any
Address Family IPv4+IPv6
Protocol Any
Source Any
Destination Any
Description Something useful
Show Advanced Click it
Tagged VPN_NO_WAN_EGRESS (the tag we made earlier - this is used to match the block rule to this traffic)

Save and Apply. After doing this, I've also found I need to Stop then Start the OpenVPN clients. Status > OpenVPN, then click the "Stop" icon and then the "Start" icon next to Client Instance Statistics. You may also want to enable Services > Service Watchdog to auto bring the service back up if it crashes.

Testing

Test your client - check it is accessing via VPN. Then, disable VPN - make sure the client cannot get to the net. Finally, re-enable VPN and make sure you can connect once more. Thata should be it!

My Privacy and Security Tools

In my quest for privacy and security, I've made use of a great many different tools. It seemed wise to document these for others, to save time and provide options that may not have been considered before.

  • 2 Factor Auth - YubiKey has been my staple for 2FA for a long time now. Initially I started off using it just for TOTP, but have progress to FIDO2 as services have supported it. Additionally, my Yubi is compatible for many of the services I list below (including BitWarden, GNU Pass, dm-crypt, etc). I now use my YubiKey for GPG also, as it holds my private keys (which were generated + stored offline), and for doors at work (thanks to RFID) as well as any operations on my phone via NFC.
  • Signing Security, Identity Management, Email/File Encryption - I also use the YubiKey, as mentioned above, for holding my GPG keys. I generated these on an offline PC, and moved the secret keys over to the YubiKey. Now I use those keys for git code signing, file encryption, etc as the keys are secured to the highest possible level whilst remaining functional still (i.e. signing everything on the offline PC would likely be the only more secure option than this - however, having a device that supports write-only for the secure element is secure enough for my risk profile). This works well with OpenKeychain for encryption and decryption on the mobile, and ties in with the standard Linux GPG utilities via the SmartCard service.
  • Password Manager - BitWarden. I'd considered and tried a few different password managers, including LastPass in the past, one 1Password more recently. I was never particularly please with LastPass from both a functionality and security perspective, but 1Password did rate highly in my tests. However, the ability to self-host BitWarden, as well as support for most of the features I loved about 1Password (notes, family accounts, icons) drove me to BitWarden (and I haven't looked back). I also previously used GNU Pass with git for a good many years, however, I wanted just a little more "functionality" with a similar level of security (and by self-hosting, the only downside is symmetric key vs. asymmetric - i.e one password/key unlocks the lot, vs. GNU Pass where every item is individually decrypted; this is an acceptable risk for my risk profile)
  • Encryption - dm-crypt with CryptSetup for Linux, VeraCrypt for Windows. Whilst I'm predominantly running on Linux, I do occasionally need to access encrypted space on Windows. I used to use TrueCrypt for this, and did stick on the known good 7.1a version for a time - however, since VeraCrypt completed an audit, and some time has passed, I have switched over to them. I'd love for dm-crypt to support password and keyfile requirement, instead of just one or the other. However, the ability to use YubiKey with my Full Disk Encryption (via the mkinitcpio-ykfde project) has been a positive. Shoutout to the Tomb wrapper script here as well.
  • Git - Gitea. I've found self hosting my Git server the most effective way to keep my code private, and secured (in the sense of being able to guarantee it's backed up effectively and consistently). I did previously utilise Gitlab, however, for a more personal service, I decided on Gitea (much lighter on resources) after having also tried Gogs.
  • Backups - restic and duplicacy. I used restic for a long time, and there's a lot I like about it - however, I recently moved to duplicacy, and will be sticking with it. Restic does a lot right - the ability to mount your backups locally and browse as a fuse system, the ability to take backups of whatever file you want on-the-fly just be specifying it, etc. However, it's just not quite fast enough for my liking - duplicacy performs far quicker (especially on subsequent backups) as well as properly supporting multiple machines to a single repo, and compression (which restic doesn't yet support). I have also tried duplicati, borg, duplicity, bup, obnam, and rdiff-backup. I use minio for local file storage, and Backblaze B2 for a low cost cloud storage destination.
  • VPN and Firewall - NordVPN and pfSense Community. I have a pfSense firewall at the edge of my network (on a dedicated box) which I use for protecting all of my devices. I push all my traffic out through NordVPN, and also have the mobile client for when I'm out and about. I've found Nord to be most affordable, with one of the better privacy policies out there, and great performance (and selection of servers). The pfSense is configured with a "kill switch" so that if my service goes down, no traffic escapes my network. I used to use Private Internet Access as well, settled on Nord as they had a few more supported protocols at the time.
  • Chat - Signal and Wire. I've used and appreciated both of these - I like the fact that Wire doesn't require a phone number, and is therefore slightly more private; however, I find the Signal client to be much better designed (and easier to get friends and family on board with, which was important to me in order to make this actually feasible). For public group chats, I like what the Matrix protocol offers, but the default "Synapse Server" memory usage was too high, so I settled on Mattermost community edition for chat rooms (private, but not encrypted).
  • Contacts, Calendars, and Tasks - EteSync. Massive shout out to the work EteSync have done here - drop in replacement for your Google Account (or similar), syncs seamlessly, has a change journal (so you can revert any mistakes), and supports vCard 4.0 . Highly recommended - can be self hosted, but I use the hosted version to support the project devs. I use my phones built-in Calendar and Contacts app with this, but use OpenTasks for the Task support.
  • Notes - StandardNotes. Simple, private, and secure note taking app. Free for basic, but extended offers many features worth paying for. I've opted for the 5 year plan (again, a project worth supporting), and use it extensively.
  • Mail - ProtonMail, Mailcow, and Tutanota. I use (and have used) each of these at various times for various reasons. Would highly recommend them all - especially ProtonMail and Tutanota if their encryption + privacy manifesto's are to be believe. Mailcow is a plus if you want self hosted - it makes it incredibly easy.
  • CryptoCurrency - Monero and Ledger. Monero has been one of the most private crypto's I've come across, and the Ledger is a great device to securely store your private keys. I use both extensively.
  • Operating System - ArchLinux. I've opted for Linux over Windows or Mac, due to the level of control you get over your privacy. I used to use Ubuntu, but opted for a "rolling release" distribution. I've not noticed any of the oft-toted issues of updates breaking things; in fact, it's been more stable for me than Ubuntu ever was. Additionally the package structure makes sense to me, which has enabled me to contribute to the AUR ecosystem in ways I never would have with Ubuntu's equivalents. Would strongly recommend.

I'll update this list as I add new tools (or remember ones that I've forgotten to add in here). Please feel free to contact me (perhaps via the Guestbook) if you've got any suggestoins!

Kicking off the Blog

Greetings!

I've taken a leap into the world of self-publishing my writing! I'll likely have musings about Linux, IT Security, coding, coffee, infosec, OSINT, and other related matters in these posts, as these are things that are significant interests for me. If anything here is relatable for you, please don't hesitate to join in the conversation. Thanks for reading!

Yum