Last Updated on August 10, 2022 by Thiago Crepaldi
Many of us have more than one pfSense (maybe connecting our home and office, our home and our parents, etc) which would benefit with a direct connection between them. In this post I will describe how to create a routed tunnel that connects both ends, in a way that Site A can directly access Site B and vice-versa.
I have found several post which assume that either assumes 1) that both sites have static IPs or 2) at most 1 site has dynamic IP. Here we will go beyond that and setup a tunnel with both ends using DDNS!
The nice thing about IPSec is that no additional software is needed in both sites, you can enforce specific firewall rules for the traffic, and only the traffic to the other site goes through the tunnel (as opposed to all traffic coming out of your router), it is safe and have low overhead!
Prerequisites
- Both sites must be using pfSense and properly working on their own LAN
- Not an IPSec requirement, but limits the scope of this post
- Both sites cannot use the same subnet (e.g. 192.168.1.0/24)
- This is not an IPSec limitation, but a networking one.
- If that is your case, change the subnet in one of the sites to a different subnet (e.g. 192.168.2.0/24)
- Both pfSense appliances must be the default gateway on the LAN where they are installed. There are workarounds using static routes, but for simplicity I will ignore this edge case
- You must have control of both sites, because we will need to configure both of them
- You cannot use Gateway groups as WAN interface as the other end expects a specific IP to close the connection
- DDNS must be configured in both sites
- This is not needed if you have static IPs
Configuring the VPN tunnel
The key to have a successful connection is to make sure both sites have matching settings. There are a few exceptions which I will explicitly highlight! Before start, make sure both sites have DDNS working and take note of their network info. For this post, we will use the following assumption:
WAN FQDN | LAN subnet | Gateway | |
Site A | a.domain.com | 10.0.0.0/24 | 10.0.0.1 |
Site B | b.domain.com | 10.100.0.0/24 | 10.100.0.1 |
IPsec tunnels have two phases: Phase 1 defines the remote peer and how the tunnel is authenticated. Phase 2 defines how traffic is carried across the tunnel. To get started, go to VPN >> IPSec >> Tunnels.
Site A
We need to configure both Site A and B!
Phase 1
To create a phase 1, click on Add P1 and do as follows:
- General Information
- Disabled: unchecked
- Description: IPSec Site A to Site B – Phase 1
- IKE Endpoint Configuration
- Key exchange version: IKEv2
- Internet protocol: IPv4
- Interface: WAN
- Remote gateway: b.domain.com
- This is the first difference between Site A and Site B. Site A will refer to Site B’s FQDN as remote gateway while Site B will use Site A’s FQDN as remote gateway!
- Phase 1 Proposal (Authentication)
- Authentication method: Mutual PSK
- My identifier: (this is the second difference)
- Dynamic DNS
- a.domain.com
- Peer identifier:
- IP address
- 0.0.0.0
- Pre-shared key: You either generate your super long key here or hit the Generate new pre-shared key button
- Take note of this PSK as it will be used in the other site too!
- Phase 1 Proposal (Encryption Algorithm)
- These settings are kind of hardware specific, so you may have to tune them later for more security/speed
- Encryption algorithm:
- Algorithm: AES128-GCM
- Key length: 128
- Hash: SHA256
- DH Group: 19 (nist ecp256)
- Lifetime (Seconds): 28800
- Advanced Options
- Disable rekey: unchecked
- Margintime (Seconds): empty
- Disable Reauth: empty
- Responder Only: unchecked
- Only one of the sites needs this checked. The one who has IPs changing more often should have this checked
- Child SA Close Action: Default
- NAT Traversal: Auto
- MOBIKE: Enable
- This is important to support Dynamic IPs!
- Split connections: unchecked
- Dead Peer Detection: checked
- Delay: 10
- Max failures: 5
Click Save and Apply changes and Phase 1 for site A is good!
Phase 2
At the Tunnel list table, the recently create Phase 1 tunnel must be listed. Click on Show Phase 2 entries (0) button, followed by a click on Add P2 button:
- General Information
- Disabled: unchecked
- Mode: Routed VTI
- Local network:
- This is another difference between sites A and B
- Type: Address
- Address: 192.168.99.1
- It can be any other subnet not used by neither sites!
- Remote Network:
- This is another difference between sites A and B
- Type: Address
- Address: 192.168.99.2
- Description: IPSec Site A to Site B – Phase 2
- Phase 2 Proposal (SA/Key Exchange)
- This is also hardware-specific and I am using this for compatibility
- Protocol: ESP
- Encryption Algorithms:
- AES128-GCM
- 128 bits
- Hash Algorithms: SHA256
- PFS key group: 19 (nist-ecp256)
- Lifetime: 3600
- Advanced Configuration
- Automatically ping host: 10.100.0.1
- Yup, another site specific setting!
- Automatically ping host: 10.100.0.1
As usual, click Save and Apply changes to complete this configuration!
Pre-Shared Keys
As we are working with dynamic IPs in both ends, we need to go an extra step and create another record for the Pre-Shared Key we used before. This record will associate the DDNS FQDN to the PSK! Go to Pre-Shared Keys tab and click on Add:
- Edit Pre-Shared-Secret
- Identifier: b.domain.com
- Yet another site specific setting
- Secret type: PSK
- Pre-Shared Key: The same used during Phase 1
- Identifier type: User fully qualified domain name
- Virtual Address Pool: empty
- DNS Server: empty
- Identifier: b.domain.com
Click on Save and Apply changes!
Assigning Interfaces to the IPSec
Because we have chosen Routed VTI as Phase 2 mode, we need to assign an interface to our tunnel. Go to Interfaces >> Assignments >> Interface Assignments and in the bottom of the list you should see something like Available network ports: ipsec1000 (name of your tunnel). Click on Add, followed by a click on the newly created interface:
- General Configuration
- Enabled: checked
- Description: IPSEC_SITES_A_B
Leave the rest as is and click on Save and Apply changes!
Creating static route to the other site
Now that we have an interface which represents the other site, we can create a new route to it by navigating to System >> Routing >> Static Routes and clicking on Add:
- Edit Route Entry
- Destination network: 10.100.0.0
- Gateway: Select the Interface you just assigned to the IPSec tunnel
- Disabled: unchecked
- Description: IPSec Route to Site B
The usual Save and Apply changes completes configuration on site A.
Configuring DNS domain override
Each site will be able to resolve names on their side, but not on the other. A quick fix for this is to create a domain override entry on DNS Resolver. Go to Services >> DNS Resolver >> Domain overrides, click on Add and do as follow:
- Domains to Override with Custom Lookup Servers
- Domain: lan.domain.com (or whatever domain name of site B)
- IP Address: 10.100.0.1
- TLS Queries: unchecked
- TLS Hostname: empty
- Description: Domain override for IPSec tunnel Site A – Site B
Press Save and Apply changes.
Site B
Site B should use the same settings, so repeat the process as before. Below I will only highlight the differences!
Phase 1
- General Information
- Remote gateway: a.domain.com
- Description: IPSec Site B to Site A – Phase 1
- Phase 1 Proposal (Authentication)
- My identifier:
- Dynamic DNS
- b.domain.com
- Pre-shared key: Copy and paste the PSK used on Site A
- My identifier:
- Advanced Options
- Responder Only: checked
Click Save and Apply changes and Phase 1 for site B is good!
Phase 2
At the Tunnel list table, the recently create Phase 1 tunnel must be listed. Click on Show Phase 2 entries (0) button, followed by a click on Add P2 button:
- General Information
- Local network:
- Type: Address
- Address: 192.168.99.2
- Remote Network:
- Type: Address
- Address: 192.168.99.1
- Description: IPSec Site B to Site A – Phase 2
- Local network:
- Advanced Configuration
- Automatically ping host: 10.0.0.1
As usual, click Save and Apply changes to complete this configuration!
Pre-Shared Keys
Similarly to Site A, go to Pre-Shared Keys tab and click on Add:
- Edit Pre-Shared-Secret
- Identifier: a.domain.com
One last time for site B, click on Save and Apply changes!
Assigning Interfaces to the IPSec
Similarly to Site A, go to Interfaces >> Assignment >> Interface Assignments page and Add on the available IPSec port, followed by a click on its name:
- General Configuration
- Enabled: checked
- Description: IPSEC_SITES_B_A
Leave the rest as is and click on Save and Apply changes!
Creating static route to the other site
Now that we have an interface which represents the other site, we can create a new route to it by navigating to System >> Routing >> Static Routes and clicking on Add:
- Edit Route Entry
- Destination network: 10.0.0.0
- Gateway: Select the Interface you just assigned to the IPSec tunnel
- Disabled: unchecked
- Description: IPSec Route to Site A
The usual Save and Apply changes completes configuration on site B.
Configuring DNS domain override
- Domains to Override with Custom Lookup Servers
- Domain: lan.domain.com (or whatever domain name of site B)
- IP Address: 10.0.0.1
- TLS Queries: unchecked
- TLS Hostname: empty
- Description: Domain override for IPSec tunnel Site A – Site B
Press Save and Apply changes.
Check tunnel status
In order to verify everything was done right, we have to go to Status >> IPSec >> Overview on the Site B (assuming you check Responder only to Site A). There will be a table with your tunnel. If the Status is ESTABLISHED, awesome. If not, try clicking on Connect VPN to get it started. If it never gets established, check all settings one by one. You probably missed something!
Add Firewall Rules
I am pretty sure that as soon as you saw the ESTABLISHED status, the first thing you tried was pinging the other site… Been there, done that! For your surprise, it didn’t work. That is expected as the although your pfSense knows about the existence of the tunnel, it didn’t get firewall rules to allow traffic…yet
In both sites, go to Firewall >> Rules >> IPsec and create an allow all rule by clicking on Add:
- Edit Firewall Rule
- Action: Pass
- Disabled: unchecked
- Interface: IPsec
- Address Family: IPv4
- Protocol: Any
- Source
- Source: Any
- Destination
- Destination: Any
- Extra Options
- Log: unchecked
- Description: Default allow all rule
Finish off by hitting Save and Apply changes!
That said, more restrictive rules are better to enforce proper network security protocols!
Check traffic is coming through
As soon as you have added the firewall rules in both sites and the tunnel is established, then you can try to ping the other end and they should reply back!
Optional: Adding Dashboard widget
This has nothing to do with getting IPSec working.. However, adding a widget to the dashboard can help you monitoring whether something is wrong. Or maybe it just looks nicer 🙂
On your pfSense dashboard, click on the + at the Status / Dashboard section. A list of widgets will show up and you just have to click on + IPSec to get it added. That is it!
Hello, I was able to establish a connection but wasn’t able to ping and reach the other server. I already allowed rules to both firewalls, anything that I might miss?
It seems you didn’t create static routes in each end