Building an IPSec Hub and Spoke

Sort of a continuation of the last post. This still uses FreeBSD , pfSense , Juniper SRX but it could fairly easily be adapted to OpnSense (fork/clone of pfSense ), and other network vendor appliances.

Versions used:

Software Version
Junos 12.3X48-D105.4
FreeBSD 12.2
StrongSwan 5.9.2
pfSense 2.4

Note If you are using Junos 15.1X49 >D100, you can use IKEv2 with the traffic selectors. If not, you have to either use IKEv1, or use proxy-identity and create multiple phase2, 1 for each subnet you want to pass traffic to/from.

Requirements

  • route-based tunnel on Junos, policy-based tunnel on StrongSwan (VTI may be an option in the future).
  • Suite-B(ish) crypto: JunOS requires certificates for Suite-B on phase-1, I’m not doing that. I am still using SHA256, AES-128-CBC for phase1, and SHA256 and AES-128-GCM (Suite-B) for phase2.

JunOS config

Interface:

1louisk@srx.cmhome> show configuration interfaces st0
2unit 0 {
3    apply-groups ipsec_interfaces;
4    description "DO Tunnel";
5    family inet;
6    family inet6;
7}
8
9louisk@srx.cmhome>

IKE (phase 1):

 1louisk@srx.cmhome> show configuration security ike
 2inactive: traceoptions {
 3    file ike-debug size 10m files 2;
 4    flag all;
 5    level 10;
 6}
 7proposal ike-proposal-digital-ocean {
 8    authentication-method pre-shared-keys;
 9    dh-group group19;
10    authentication-algorithm sha-256;
11    encryption-algorithm aes-128-cbc;
12    lifetime-seconds 28800;
13}
14policy ike-policy-digital-ocean {
15    mode main;
16    proposals ike-proposal-digital-ocean;
17    pre-shared-key ascii-text "insert secret here";
18}
19gateway ike-gate-digital-ocean {
20    ike-policy ike-policy-digital-ocean;
21    address 172.16.143.91;
22    dead-peer-detection {
23        optimized;
24        interval 10;
25        threshold 5;
26    }
27    local-identity hostname srx.cmhome;
28    remote-identity inet 172.16.143.91;
29    external-interface fe-0/0/7;
30    version v1-only;
31}
32
33louisk@srx.cmhome>

IPSec (phase 2):

 1louisk@srx.cmhome> show configuration security ipsec
 2inactive: traceoptions {
 3    flag all;
 4}
 5vpn-monitor-options {
 6    interval 10;
 7    threshold 10;
 8}
 9proposal ipsec-proposal-digital-ocean {
10    protocol esp;
11    authentication-algorithm hmac-sha1-96;
12    encryption-algorithm aes-128-cbc;
13}
14policy ipsec-policy-digital-ocean {
15    perfect-forward-secrecy {
16        keys group19;
17    }
18    proposal-set suiteb-gcm-128;
19}
20vpn ipsec-vpn-digital-ocean {
21    bind-interface st0.0;
22    ike {
23        gateway ike-gate-digital-ocean;
24        ipsec-policy ipsec-policy-digital-ocean;
25    }
26    traffic-selector t1 {
27        local-ip 192.168.0.0/20;
28        remote-ip 10.10.2.0/24;
29    }
30    traffic-selector t2 {
31        local-ip 192.168.0.0/20;
32        remote-ip 192.168.17.0/24;
33    }
34    establish-tunnels immediately;
35}
36
37louisk@srx.cmhome>

The traffic-selector (proxy-identity if you’re using IKEv2 before Junos 15.1X49-D100) parts are required if the other side is policy-based (StrongSwan).

Security policies:

 1louisk@srx.cmhome> show configuration security policies from-zone trust to-zone site-2-site
 2policy trust-site-2-site {
 3    match {
 4        source-address net-192.168_0_0_m20;
 5        destination-address [ net-192.168_17_0_m24 net-10_10_2_20_m32 ];
 6        application any;
 7    }
 8    then {
 9        permit;
10        count;
11    }
12}
13
14louisk@srx.cmhome> show configuration security policies from-zone site-2-site to-zone trust
15policy site-2-site-trust {
16    match {
17        source-address [ net-192.168_17_0_m24 net-10_10_2_20_m32 ];
18        destination-address net-192.168_0_0_m20;
19        application junos-icmp-ping;
20    }
21    then {
22        permit;
23        count;
24    }
25}
26
27louisk@srx.cmhome>

If you want to be more granular about what kind of traffic you allow through, You would want to create more policy statements, and/or provide a list of applications, ports, and protocols that you wish to allow.

Security zones:

1louisk@srx.cmhome> show configuration security zones security-zone site-2-site
2interfaces {
3    st0.0;
4}
5
6louisk@srx.cmhome>

Addressbook:

 1louisk@srx.cmhome> show configuration security address-book
 2global {
 3    address net-192.168_0_0_m20 {
 4        description CMHome;
 5        192.168.0.0/20;
 6    }
 7    address net-192.168_17_0_m24 {
 8        description "Office";
 9        192.168.17.0/24;
10    }
11    address net-10_10_2_20_m32 {
12        description "DO IPSec Hub";
13        10.10.2.20/32;
14    }
15}
16
17louisk@srx.cmhome>

StrongSwan config

Most of this is pretty straight forward. I did find that nothing wanted to work until I changed the strongswan_interface variable to stroke. It currently defaults to vici (new configs from scratch should probably be done this way, but getting the existing configs working was faster this time).

rc.conf

1strongswan_enable="YES"
2strongswan_interface="stroke"
3gateway_enable="YES"
4ipv6_gateway_enable="YES"

ipsec.conf

 1# ipsec.conf - strongSwan IPsec configuration file
 2
 3# basic configuration
 4
 5config setup
 6	uniqueids=yes
 7	# strictcrlpolicy=yes
 8
 9# Add connections here.
10conn %default
11	ikelifetime=28800s
12	keylife=3600s
13	rekeymargin=3m
14	keyingtries=1
15	authby=secret
16	keyexchange=ikev2
17	mobike=no
18	rekey=yes
19
20conn to-office
21	fragmentation=yes
22	reauth=yes
23	forceencaps=no
24	mobike=yes
25
26	installpolicy=yes
27	type=tunnel
28	dpddelay=10s
29	dpdtimeout=60s
30	dpdaction=restart
31	auto=add
32	authby=secret
33	ike=aes128-sha256-ecp256!
34	esp=aes128gcm128-sha256-ecp256,aes128gcm96-sha256-ecp256,aes128gcm64-sha256-ecp256!
35
36	leftauth=psk
37	leftsubnet=10.10.2.20/24,192.168.0.0/20
38	left=172.16.143.91
39	leftid=172.16.143.91
40
41	rightauth=psk
42	rightsubnet=192.168.17.0/24
43	right=%any
44	rightid=@office
45
46conn to-cmhome
47	keyexchange=ikev1
48	fragmentation=yes
49	reauth=yes
50	forceencaps=no
51	mobike=yes
52
53	installpolicy=yes
54	type=tunnel
55	dpddelay=10s
56	dpdtimeout=60s
57	dpdaction=restart
58	auto=add
59	authby=secret
60	ike=aes128-sha256-ecp256!
61	esp=aes128gcm128-sha256-ecp256,aes128gcm96-sha256-ecp256,aes128gcm64-sha256-ecp256!
62
63	leftauth=psk
64	leftsubnet=10.10.2.20/24,192.168.17.0/24
65	left=172.16.143.91
66	leftid=172.16.143.91
67
68	rightauth=psk
69	rightsubnet=192.168.0.0/20
70	right=%any
71	rightid=@srx.cmhome

You can provide a comma separated list of prefixes for the left/right subnet instead of having to define new stanzas for each P2. That was nice.

Because all of the spokes in this configuration have dynamic addresses, the right needs to be set to %any. Make sure you set your identifier the same on both sides or it won’t connect.

ipsec.secrets

1@srx.cmhome : PSK "insert password here"
2@office : PSK "insert other password here"

You can use certs instead of PSK if you like them better. You can find examples here .

pfSense config

Overview: SHA256, AES128 CBC/GCM

Phase 1: 2 screenshots because its too long for 1

Phase 2: 2 screenshots because its too long for 1

NOTE: Ensure you allow traffic in/out the IPSec interface. With out this, you won’t get traffic to go where you want.

You can be granular, or not, up to you. Probably best to use the same applications, ports, and protocols that were defined in the SRX policy, just to keep things from being more confusing when it comes time to debug things.

Verification and testing

Tunnel is up:

 1louisk@srx.cmhome> show security ike sa
 2Index   State  Initiator cookie  Responder cookie  Mode           Remote Address
 34286058 UP     4e4839c9f5cf00e7  5b4197e463eefd51  Main           172.16.143.91
 4
 5louisk@srx.cmhome> show security ipsec sa
 6  Total active tunnels: 2
 7  ID    Algorithm       SPI      Life:sec/kb  Mon lsys Port  Gateway
 8  <67108865 ESP:aes-gcm-128/None e36683fb 1626/ unlim - root 500 172.16.143.91
 9  >67108865 ESP:aes-gcm-128/None c7e91c4f 1626/ unlim - root 500 172.16.143.91
10  <67108866 ESP:aes-gcm-128/None c5880593 1726/ unlim - root 500 172.16.143.91
11  >67108866 ESP:aes-gcm-128/None c233855f 1726/ unlim - root 500 172.16.143.91
12
13louisk@srx.cmhome> ping count 1 192.168.17.6
14PING 192.168.17.6 (192.168.17.6): 56 data bytes
1564 bytes from 192.168.17.6: icmp_seq=0 ttl=63 time=131.445 ms
16
17--- 192.168.17.6 ping statistics ---
181 packets transmitted, 1 packets received, 0% packet loss
19round-trip min/avg/max/stddev = 131.445/131.445/131.445/0.000 ms
20
21louisk@srx.cmhome>

Showing policy counters/statistics after the tunnel has been up for a little bit. You should see numbers > 0 for almost everything here.

 1louisk@srx.cmhome> show security policies from-zone trust to-zone site-2-site detail
 2Policy: trust-site-2-site, action-type: permit, State: enabled, Index: 13, Scope Policy: 0
 3  Policy Type: Configured
 4  Sequence number: 1
 5  From zone: trust, To zone: site-2-site
 6  Source addresses:
 7    net-192.168_0_0_m20(global): 192.168.0.0/20
 8  Destination addresses:
 9    net-10_10_2_20_m32(global): 10.10.2.20/32
10    net-192.168_17_0_m24(global): 192.168.17.0/24
11  Application: any
12    IP protocol: 0, ALG: 0, Inactivity timeout: 0
13      Source port range: [0-0]
14      Destination port range: [0-0]
15  Per policy TCP Options: SYN check: No, SEQ check: No
16  Policy statistics:
17    Input  bytes       :              9794924                   29 bps
18      Initial direction:              1933478                   14 bps
19      Reply direction  :              7861446                   14 bps
20    Output bytes       :              9795478                   29 bps
21      Initial direction:              1932016                   14 bps
22      Reply direction  :              7863462                   14 bps
23    Input  packets     :                24114                    0 pps
24      Initial direction:                11438                    0 pps
25      Reply direction  :                12676                    0 pps
26    Output packets     :                24149                    0 pps
27      Initial direction:                11437                    0 pps
28      Reply direction  :                12712                    0 pps
29    Session rate       :                 3155                    0 sps
30    Active sessions    :                    1
31    Session deletions  :                 3154
32    Policy lookups     :                 3167
33
34louisk@srx.cmhome>
 1[louisk@hub louisk 125 ]$ ipsec statusall
 2Status of IKE charon daemon (strongSwan 5.9.2, FreeBSD 12.2-RELEASE-p6, amd64):
 3  uptime: 3 hours, since Apr 24 19:25:50 2021
 4  worker threads: 11 of 16 idle, 5/0/0/0 working, job queue: 0/0/0/0, scheduled: 6
 5  loaded plugins: charon aes des blowfish rc2 sha2 sha1 md4 md5 random nonce x509 revocation constraints pubkey pkcs1 pkcs7 pkcs8 pkcs12 pgp dnskey sshkey pem openssl fips-prf curve25519 xcbc cmac hmac gcm drbg curl attr kernel-pfkey kernel-pfroute resolve socket-default stroke vici updown eap-identity eap-md5 eap-mschapv2 eap-tls eap-ttls eap-peap xauth-generic whitelist addrblock counters
 6Listening IP addresses:
 7  172.16.143.91
 8Connections:
 9       to-office:  172.16.143.91...%any  IKEv2, dpddelay=10s
10       to-office:   local:  [172.16.143.91] uses pre-shared key authentication
11       to-office:   remote: [office] uses pre-shared key authentication
12       to-office:   child:  10.10.2.0/24 192.168.0.0/20 === 192.168.17.0/24 TUNNEL, dpdaction=restart
13   to-cmhome:  172.16.143.91...%any  IKEv1, dpddelay=10s
14   to-cmhome:   local:  [172.16.143.91] uses pre-shared key authentication
15   to-cmhome:   remote: [srx.cmhome] uses pre-shared key authentication
16   to-cmhome:   child:  10.10.2.0/24 192.168.17.0/24 === 192.168.0.0/20 TUNNEL, dpdaction=restart
17Security Associations (2 up, 0 connecting):
18   to-cmhome[3]: ESTABLISHED 3 hours ago, 172.16.143.91[172.16.143.91]...98.198.238.127[srx.cmhome]
19   to-cmhome[3]: IKEv1 SPIs: 4e4839c9f5cf00e7_i 5b4197e463eefd51_r*, pre-shared key reauthentication in 4 hours
20   to-cmhome[3]: IKE proposal: AES_CBC_128/HMAC_SHA2_256_128/PRF_HMAC_SHA2_256/ECP_256
21   to-cmhome{11}:  INSTALLED, TUNNEL, reqid 2, ESP SPIs: c7e91c4f_i e36683fb_o
22   to-cmhome{11}:  AES_GCM_16_128/ECP_256, 9108 bytes_i (207 pkts, 2s ago), 20700 bytes_o (207 pkts, 2s ago), rekeying in 19 minutes
23   to-cmhome{11}:   10.10.2.0/24 === 192.168.0.0/20
24   to-cmhome{12}:  INSTALLED, TUNNEL, reqid 3, ESP SPIs: c233855f_i c5880593_o
25   to-cmhome{12}:  AES_GCM_16_128/ECP_256, 31888 bytes_i (692 pkts, 3s ago), 305548 bytes_o (2670 pkts, 1s ago), rekeying in 23 minutes
26   to-cmhome{12}:   192.168.17.0/24 === 192.168.0.0/20
27       to-office[1]: ESTABLISHED 3 hours ago, 172.16.143.91[172.16.143.91]...66.220.110.60[office]
28       to-office[1]: IKEv2 SPIs: 77f55c79c761bb62_i 855552af159b5132_r*, pre-shared key reauthentication in 4 hours
29       to-office[1]: IKE proposal: AES_CBC_128/HMAC_SHA2_256_128/PRF_HMAC_SHA2_256/ECP_256
30       to-office{10}:  INSTALLED, TUNNEL, reqid 1, ESP SPIs: c12588fa_i cc7b0f52_o
31       to-office{10}:  AES_GCM_16_128/ECP_256, 248788 bytes_i (4327 pkts, 1s ago), 134880 bytes_o (1328 pkts, 2s ago), rekeying in 4 minutes
32       to-office{10}:   10.10.2.0/24 192.168.0.0/20 === 192.168.17.0/24
33[louisk@hub louisk 126 ]$

pfSense ICMP test:

pfSense should also show traffic flowing across the tunnel

Footnotes and References

Copyright

Comments