VPN tunnel between Cisco and VyOS behind NAT
![thumbnail for this post](https://dosztal.com/blog/vpn-cisco-vyos-nat/cover.jpg)
As a follow up to the VPN tunnel between Cisco and VyOS routers using VTIs post, let’s see a different scenario where the VyOS router is on a private network behind a firewall that provides NAT; for example hosted a cloud network.
Topology
We have three networks:
- 10.0.0.0/24 is the local site (GW: 10.0.0.1)
- 209.2.3.0/24 represents the internet
- 192.168.1.0/24 is the private network at the cloud provider (GW: 192.168.1.1)
The hosts are configured to have the .10 IP address.
![Topology](topo.png)
Base config
R1 is empty. R2 has its IP addresses set and translates the 209.2.3.2 address to 192.168.1.2:
interface Ethernet0/0
ip address 192.168.1.1 255.255.255.0
ip nat inside
no shut
interface Ethernet0/1
ip address 209.2.3.1 255.255.255.0
ip nat outside
no shut
ip nat inside source static 192.168.1.2 209.2.3.2
R3 also has its interfaces configured:
interface Ethernet0/0
ip address 10.0.0.1 255.255.255.0
interface Ethernet0/1
ip address 209.2.3.3 255.255.255.0
Solution
First we create basic connectivity between R1 and R3, then set up the VPN tunnels, followed by some basic OSPF routing through the tunnel. I’ll only explain the differences to the previous post.
1. Configure basic connectivity
Since R2 already does the NAT for us, the job on R1 is quite easy:
set interfaces ethernet eth0 address 192.168.1.2/24
set protocols static route 0.0.0.0/0 next-hop 192.168.1.1
Ping check:
vyos@vyos:~$ ping 209.2.3.3 count 3
PING 209.2.3.3 (209.2.3.3) 56(84) bytes of data.
64 bytes from 209.2.3.3: icmp_req=1 ttl=254 time=1.74 ms
64 bytes from 209.2.3.3: icmp_req=2 ttl=254 time=0.647 ms
64 bytes from 209.2.3.3: icmp_req=3 ttl=254 time=0.637 ms
--- 209.2.3.3 ping statistics ---
3 packets transmitted, 3 received, 0% packet loss, time 2003ms
rtt min/avg/max/mdev = 0.637/1.010/1.748/0.522 ms
2. Create the VPN tunnels
That’s the tricky part. Obviously we can’t set 192.168.1.2 as the tunnel destination because R3 doesn’t know how to connect to that IP. On the other hand, if we set 209.2.3.2 as the destination, the ESP packets will be translated to R1 but R1 won’t know anything about that public IP.
How to resolve this conflict? Change the “authentication id” parameter to the public IP on VyOS:
set vpn ipsec esp-group ESP_to_Cisco lifetime 3600
set vpn ipsec esp-group ESP_to_Cisco mode tunnel
set vpn ipsec esp-group ESP_to_Cisco pfs enable
set vpn ipsec esp-group ESP_to_Cisco proposal 1 encryption aes256
set vpn ipsec esp-group ESP_to_Cisco proposal 1 hash sha1
set vpn ipsec ike-group IKE_to_Cisco key-exchange ikev1
set vpn ipsec ike-group IKE_to_Cisco lifetime 86400
set vpn ipsec ike-group IKE_to_Cisco proposal 1 dh-group 14
set vpn ipsec ike-group IKE_to_Cisco proposal 1 encryption aes256
set vpn ipsec ike-group IKE_to_Cisco proposal 1 hash sha256
set vpn ipsec ipsec-interfaces interface eth0
set vpn ipsec site-to-site peer 209.2.3.3 authentication id 209.2.3.2
set vpn ipsec site-to-site peer 209.2.3.3 authentication mode pre-shared-secret
set vpn ipsec site-to-site peer 209.2.3.3 authentication pre-shared-secret PSK_tahp_secret
set vpn ipsec site-to-site peer 209.2.3.3 authentication remote-id 209.2.3.3
set vpn ipsec site-to-site peer 209.2.3.3 connection-type initiate
set vpn ipsec site-to-site peer 209.2.3.3 default-esp-group ESP_to_Cisco
set vpn ipsec site-to-site peer 209.2.3.3 ike-group IKE_to_Cisco
set vpn ipsec site-to-site peer 209.2.3.3 ikev2-reauth inherit
set vpn ipsec site-to-site peer 209.2.3.3 local-address 192.168.1.2
set vpn ipsec site-to-site peer 209.2.3.3 vti bind vti0
set vpn ipsec site-to-site peer 209.2.3.3 vti esp-group ESP_to_Cisco
set interfaces vti vti0 address 10.255.255.1/24
On R3, we create the tunnel to R2’s public address:
crypto isakmp policy 1
encr aes 256
hash sha256
authentication pre-share
group 14
crypto isakmp key PSK_tahp_secret address 0.0.0.0
crypto ipsec transform-set VyOS_Tset esp-aes 256 esp-sha-hmac
mode tunnel
crypto ipsec profile VyOS
set transform-set VyOS_Tset
interface Tunnel0
ip address 10.255.255.2 255.255.255.0
ip ospf mtu-ignore
tunnel source 209.2.3.3
tunnel mode ipsec ipv4
tunnel destination 209.2.3.2
tunnel protection ipsec profile VyOS
3. Set up routing
Just as in the previous post, we’re creating two loopback addresses, use them as router-id, and advertise the connected networks through the tunnel.
R3:
interface Loopback0
ip address 3.3.3.3 255.255.255.255
router ospf 1
router-id 3.3.3.3
network 3.3.3.3 0.0.0.0 area 0
network 10.0.0.0 0.0.0.255 area 0
network 10.255.255.0 0.0.0.255 area 0
R1:
set interfaces loopback lo address 1.1.1.1/32
set interfaces vti vti0 ip ospf mtu-ignore
set protocols ospf area 0 network 1.1.1.1/32
set protocols ospf area 0 network 192.168.1.0/24
set protocols ospf area 0 network 10.255.255.0/24
set protocols ospf parameters router-id 1.1.1.1
One remark about PC1 (hosts in the cloud network). Though you can set R1 as the default gateway, it is not recommended because it only needs to forward traffic to the remote network. I suggest setting up static routes, e.g.:
ip route add 10.0.0.0/24 via 192.168.1.2 dev ethx
-- OR --
route add -net 10.0.0.0 netmask 255.255.255.0 gw 192.168.1.2 dev ethx
4. Testing
OSPF neighbor on R3 is up:
R3#sh ip ospf neighbor
Neighbor ID Pri State Dead Time Address Interface
1.1.1.1 0 FULL/ - 00:00:36 10.255.255.1 Tunnel0
Routes are installed:
R3#sh ip route ospf
[...]
1.0.0.0/32 is subnetted, 1 subnets
O 1.1.1.1 [110/1010] via 10.255.255.1, 01:23:36, Tunnel0
O 192.168.1.0/24 [110/1010] via 10.255.255.1, 01:23:36, Tunnel0
PC1 can ping PC2:
PC1> ping 10.0.0.10
84 bytes from 10.0.0.10 icmp_seq=1 ttl=62 time=2.167 ms
84 bytes from 10.0.0.10 icmp_seq=2 ttl=62 time=5.052 ms
84 bytes from 10.0.0.10 icmp_seq=3 ttl=62 time=5.053 ms
84 bytes from 10.0.0.10 icmp_seq=4 ttl=62 time=4.939 ms
84 bytes from 10.0.0.10 icmp_seq=5 ttl=62 time=5.227 ms