Skip to main content
RunBook Academy

← All runbooks in VyOS

high riskservice affecting~90 min

Runbook: Configure IPsec

1 · Prerequisites

Confirm every item is in place before any state change.

2 · Pre-checks

Read-only diagnostic commands. If any of these don't match expected output, stop and investigate further.

  • · The two ends have an AGREED parameter sheet before anyone touches a router: IKE version, encryption, hash, PRF, DH group and lifetime on the IKE side; encryption, hash, PFS, mode and lifetime on the ESP side; and the identities each end will present. The VyOS documentation lists exactly these as the values that must match, and both ends configuring independently from intent is how "no proposal chosen" happens.
  • · Which end initiates is decided and written down. One peer gets connection-type initiate, the other connection-type none. The VyOS documentation recommends that pairing explicitly, and warns that initiate on its own never restarts the connection after a disconnection — so the initiating end also needs dead-peer-detection or close-action.
  • · Whether this router already terminates other IPsec peers is established with show vpn ipsec connections. If it does, this is NOT an additive change — see the two global options below.
  • · set vpn ipsec interface is checked against the current configuration. When it is absent, IPsec policies apply to ALL interfaces; adding it for the first time RESTRICTS them to the interfaces you name, for every peer on the router and not just the new one.
  • · set vpn ipsec options disable-route-autoinstall is checked. For route-based (VTI) peers it is required, because a VTI negotiates 0.0.0.0/0 selectors and strongSwan would otherwise install a default route via the VTI peer address. Setting it on a router that already has policy-based peers relying on auto-installed routes will remove those routes.
  • · The path is confirmed open in both directions before any tunnel configuration exists: UDP 500 (IKE), UDP 4500 (NAT-T) and IP protocol 50 (ESP) between the two public addresses, in the firewall on BOTH ends and in anything between them.
  • · Whether either end sits behind NAT is established. If so, ESP cannot traverse it and the tunnel depends on UDP 4500 encapsulation being permitted end to end. Where a middlebox blocks plain ESP without NAT being detected, force-udp-encapsulation on the peer is the documented lever.
  • · The PSK or certificate material is handled as a credential: generated out of band, never pasted into a ticket, and understood to be readable by anyone who can read the running configuration, any configuration backup taken afterwards, or the operational command show vpn ike secrets.
  • · The pre-change configuration is saved to a file you can load back: save /config/pre-change-TICKET.conf, and out-of-band console access is confirmed by using it.

3 · Procedure

Execute each step in order. Verify the expected output of a step before moving to the next.

  1. 1Confirm the path first, before configuring anything: from each end, prove UDP 500 and UDP 4500 reach the other public address and that the firewall permits ESP. A blocked port here makes every later proposal question unanswerable.
  2. 2Capture the pre-change state: show vpn ipsec connections, show vpn ike sa, show vpn ipsec sa, show system commit, then save /config/pre-change-TICKET.conf.
  3. 3Bind the daemon to the WAN interface if it is not already bound: set vpn ipsec interface eth0. Treat this as narrowing IPsec policy installation for every peer on the router, not just the new one.
  4. 4Define the IKE group from the agreed sheet: key-exchange ikev2, proposal N encryption/hash/dh-group/prf, lifetime, close-action, and dead-peer-detection action plus interval. Note that dead-peer-detection timeout is IKEv1 only — on IKEv2 the retransmission schedule decides when a peer is declared down.
  5. 5Define the ESP group from the agreed sheet: proposal N encryption/hash, pfs, mode tunnel, lifetime.
  6. 6Install the pre-shared key under set vpn ipsec authentication psk NAME, with an id for each end that matches the identity that end will actually present, and the secret.
  7. 7Define the peer: authentication mode pre-shared-secret, local-id and remote-id matching the psk ids, ike-group, default-esp-group, local-address, remote-address, and the agreed connection-type.
  8. 8For route-based: create the VTI with set interfaces vti vti0 address, bind it with set vpn ipsec site-to-site peer PEER vti bind vti0, and set set vpn ipsec options disable-route-autoinstall. For policy-based instead: tunnel 0 local prefix and tunnel 0 remote prefix.
  9. 9Set the tunnel MTU and MSS clamp on the VTI before you hand it to users: set interfaces vti vti0 mtu 1400 and set interfaces vti vti0 ip adjust-mss clamp-mss-to-pmtu. A VTI defaults to MTU 1500, which is the exact condition that produces a tunnel that pings and cannot carry a file.
  10. 10Run compare, read the diff against the agreed sheet, and apply with commit-confirm 10 rather than a bare commit.
  11. 11Verify in order: IKE SA established, child SA present with bytes in BOTH directions, VTI up, route present via the VTI, then a large do-not-fragment ping across the tunnel.
  12. 12Only after all five verifications pass, confirm, then save, then add the static or dynamic routing that puts real traffic on the tunnel.

4 · Verification

Confirm the procedure actually fixed the problem.

  • show vpn ike sa shows the IKE SA up, and the NEGOTIATED values in its Encrypt, Hash and D-H Group columns are read from the output and compared against the agreed sheet — not assumed from what was typed. A tunnel can come up on a weaker proposal than intended.
  • show vpn ipsec sa shows a child SA for the peer with non-zero counters in BOTH halves of its Bytes In/Out column. Bytes in one direction only means the return path is broken — routing or firewall on the far end — and the tunnel is not usable even though it reads as up.
  • The child SA carries the name this deployment should produce: PEER-vti for a VTI binding, PEER-tunnel-N for each policy-based tunnel. A peer that shows a tunnel-0 child when you built a VTI means the wrong branch of step 4 was committed.
  • show vpn ipsec connections agrees with the configured peer and mode. For a VTI peer the Local TS and Remote TS columns read 0.0.0.0/0 (and ::/0) — that is correct and expected, not a misconfiguration.
  • show interfaces vti vti0 shows the interface up with its configured address (route-based deployments only).
  • The remote prefix appears in the routing table via the VTI or the expected next hop, and the route is the one the traffic will actually take.
  • A large do-not-fragment ping across the tunnel succeeds — ping 10.100.100.2 size 1372 do-not-fragment count 3. A default-size ping proves only that the SA exists; the do-not-fragment ping is what proves the MTU and MSS work is correct.
  • One real application flow is tested end to end, from a host behind one side to a host behind the other, not from router to router.
  • show log ipsec contains no repeating negotiation errors after the tunnel settles.
  • Existing tunnels on this router are re-checked with show vpn ipsec connections and are still established — proof the global options did not disturb them.

5 · Rollback

If verification fails, undo the procedure in reverse order.

  • Not yet committed: discard. Nothing has been applied and no daemon has been reloaded.
  • Committed under commit-confirm N and the tunnel is wrong: do nothing and let the window expire. The router reverts on its own. This matters more than usual here because a bad IPsec commit can disturb tunnels other than the one you were building.
  • Committed and confirmed: load /config/pre-change-TICKET.conf then commit. This restores the whole IPsec subtree, including the two global options, in one step.
  • To remove only the new peer, leaving everything else in place: delete vpn ipsec site-to-site peer PEER and, for route-based, delete interfaces vti vti0, then commit.
  • Do NOT revert with rollback N. The VyOS documentation states rollback applies the revision and triggers a system reboot; on a router terminating other tunnels that is an outage for all of them, not a revert of one.
  • If set vpn ipsec interface or disable-route-autoinstall was added and other peers exist, the rollback must remove those too — they are the parts of this change that reach beyond the new tunnel.
  • After any rollback, re-verify the OTHER tunnels, not just that the new one is gone. The pre-change capture of show vpn ipsec connections is the comparison.

6 · Escalation

When the runbook isn't enough, contact:

  • · Escalate to the peer-side owner as soon as the local evidence is complete and points outward: IKE reaching UDP 500 but no response, or a child SA with bytes leaving and none returning. Both are far-end conditions and no amount of local reconfiguration fixes them.
  • · Escalate to network engineering if adding this peer requires changing set vpn ipsec interface or disable-route-autoinstall on a router that already carries production tunnels — that is a change to the shared IPsec configuration and needs its own window and its own blast-radius review.
  • · Escalate to the security owner before deploying a proposal containing 3DES, DES, MD5, SHA-1, or DH group 1, 2 or 5, even when the far end demands it. Interoperating with weak crypto is a documented exception with an owner, not an operator decision made at 02:00 to make a tunnel come up.
  • · Escalate immediately if a pre-shared key has been sent through a ticket, chat or email. Treat it as disclosed, rotate it, and record the disclosure — a PSK is a symmetric credential and copies of it do not expire.
  • · Hold rather than proceed when the two ends have no agreed parameter sheet. Configuring from intent and negotiating by trial is how a window is spent producing "no proposal chosen" repeatedly. Record the hold with an owner and a date, and hand the window back.

An IPsec tunnel is not one thing that works or does not. It is five separate agreements plus a network path, and every one of them fails with the same sentence from the person who reported it: the tunnel is down.

  1. The path — UDP 500, UDP 4500 and IP protocol 50 reaching the far end.
  2. The IKE proposal — encryption, hash, PRF, DH group, IKE version.
  3. Authentication — the secret, and the identities it is filed under.
  4. The ESP proposal — encryption, hash, PFS, mode.
  5. The traffic selectors or VTI binding, and the routing that feeds them.

The whole procedure is ordered so each is proven separately, cheapest first. Confirming the path takes two minutes and invalidates half the possible causes; aligning proposals against a peer whose firewall was dropping UDP 500 the entire time takes an evening.

When this runbook applies

Use it to bring up a new site-to-site IPsec peer on a VyOS 1.5 router, or to rebuild one whose configuration has been removed.

Do not use it for:

  • A tunnel that was working and has stopped. That is a diagnosis. The parameters have not changed, so re-entering them proves nothing; go to the IPsec troubleshooting runbook and find what did change.
  • Remote-access (road-warrior) IPsec. Different subtree (vpn ipsec remote-access), different authentication model, an address pool and a client population to think about.
  • A crypto change on an existing tunnel. Rekeying a live peer to a new proposal is a coordinated two-ended change and drops traffic when the ends disagree even briefly.

Two things to confirm on your image before you paste anything

VyOS moves IPsec nodes between releases, and this course’s Part XLII lessons were written against an older generation. Two differences bite immediately.

SubjectWhat 1.5 acceptsWhy it matters
IKE versionike-group NAME key-exchange ikev2With key-exchange unset, VyOS initiates IKEv2 but responds to either version — so an unset value is not the same as a chosen one
Pre-shared keyvpn ipsec authentication psk NAME id ... secret ...The key is a separate node keyed by identity, not a value under the peer
ESP PFSesp-group NAME pfs enable (or pfs dh-group14)enable inherits the IKE group’s DH group; there is no dh-group node under an ESP proposal
Tunnel interfaceinterfaces vti vtiNThe interface name is constrained to vtiN; anything else is rejected at commit
Connection roleconnection-type initiate on one end, none on the otherThe third accepted value differs by release — confirm it with completion rather than copying it from anywhere, including here

Confirm each node with command completion on your image before pasting. On a configuration-tree OS a wrong node name is a rejected commit, which is the cheap failure. A node that exists and means something slightly different is the expensive one.

Step 0: prove the path before you configure anything

Read-only / Safeis the path even open?
monitor traffic interface eth0 filter 'udp port 500 or udp port 4500 or proto esp'

Run this BEFORE any tunnel configuration exists, while the far end is asked to initiate. monitor traffic is VyOS’s wrapper around tcpdump, so the output is tcpdump’s; press Ctrl-C to stop it.

Three outcomes, three different next actions:

  • Nothing at all, in either direction. Neither end is trying, or something upstream is dropping it. Check the local firewall permits the peer address on UDP 500/4500 and ESP, and ask the far end to confirm the same. Nothing else is worth doing yet.
  • Outbound packets only. Your side is initiating and nothing is coming back. This is a far-end or path condition. Escalate outward with the capture rather than changing local proposals.
  • Traffic both ways. The path is fine and the problem, when it comes, is a parameter problem. Proceed.

Step 1: the two global options that are not about your tunnel

Adding a peer looks additive. Two nodes in this procedure are not, and both are easy to type without noticing.

Service impact possibleglobal — affects every peer on this router
set vpn ipsec interface eth0
set vpn ipsec options disable-route-autoinstall

set vpn ipsec interface restricts outbound IPsec policies to the interfaces you name. The VyOS documentation is explicit about the default: when no interface is specified, IPsec policies apply to all interfaces. So this is not “switch IPsec on for eth0” — it is “switch IPsec off everywhere except eth0”. On a router whose existing peers terminate on a second WAN, a pppoe interface or a VRF-bound link, adding this line for your new peer is what removes theirs.

disable-route-autoinstall stops strongSwan installing its own routes for negotiated traffic selectors. Route-based (VTI) deployments require it, and the reason is specific rather than general: a VTI negotiates its selectors as 0.0.0.0/0, and forwarding decisions are made on netfilter marks rather than on those selectors. Left enabled, strongSwan reads 0.0.0.0/0 as “route everything” and installs a default route via the VTI peer address. But it is a global switch: on a router that already has policy-based peers quietly depending on auto-installed routes to their remote prefixes, turning it on removes their routing while leaving their tunnels up.

Step 2: proposals, from an agreed sheet

Both ends must offer at least one identical combination. The failure when they do not is NO_PROPOSAL_CHOSEN in the log, and the notify itself does not say which parameter disagrees — which is why the sheet is agreed before the window rather than discovered during it.

Configuration changeIKE and ESP groups
configure

set vpn ipsec ike-group IKE-GROUP key-exchange 'ikev2'
set vpn ipsec ike-group IKE-GROUP lifetime '28800'
set vpn ipsec ike-group IKE-GROUP proposal 10 encryption 'aes256'
set vpn ipsec ike-group IKE-GROUP proposal 10 hash 'sha256'
set vpn ipsec ike-group IKE-GROUP proposal 10 prf 'prfsha256'
set vpn ipsec ike-group IKE-GROUP proposal 10 dh-group '14'
set vpn ipsec ike-group IKE-GROUP close-action 'start'
set vpn ipsec ike-group IKE-GROUP dead-peer-detection action 'restart'
set vpn ipsec ike-group IKE-GROUP dead-peer-detection interval '30'

set vpn ipsec esp-group ESP-GROUP mode 'tunnel'
set vpn ipsec esp-group ESP-GROUP lifetime '3600'
set vpn ipsec esp-group ESP-GROUP pfs 'enable'
set vpn ipsec esp-group ESP-GROUP proposal 10 encryption 'aes256'
set vpn ipsec esp-group ESP-GROUP proposal 10 hash 'sha256'

prf is on the agreed-parameters list and is easy to leave out. It defaults in a way that usually matches, and when it does not, the failure is an ordinary proposal mismatch with one more column to compare.

pfs enable inherits the DH group from the IKE group rather than naming one. That is convenient and it is also a trap on a two-vendor tunnel: the far end almost certainly names a PFS group explicitly, and “inherit” only matches if the IKE group you inherit from is the group they named. Where the sheet says group 14, pfs dh-group14 says so in the configuration and survives someone later editing the IKE group.

Step 3: authentication, and the identity trap

On 1.5 the pre-shared key does not live under the peer. It lives in its own node, filed under the identities the two ends present:

Configuration changePSK is keyed by identity, not by peer name
set vpn ipsec authentication psk PSK-SITE-B id '198.51.100.1'
set vpn ipsec authentication psk PSK-SITE-B id '203.0.113.1'
set vpn ipsec authentication psk PSK-SITE-B secret 'REPLACE-WITH-A-GENERATED-SECRET'

set vpn ipsec site-to-site peer PEER-SITE-B authentication mode 'pre-shared-secret'
set vpn ipsec site-to-site peer PEER-SITE-B authentication local-id '198.51.100.1'
set vpn ipsec site-to-site peer PEER-SITE-B authentication remote-id '203.0.113.1'

The id values on the psk node are how the daemon decides which secret applies to an incoming negotiation — the VyOS documentation states plainly that the peer selects its key according to the local-id / remote-id pair. If those ids do not match the identities the two ends actually present, the correct secret is never selected, and the log reads tried 1 shared key ... but MAC mismatched followed by AUTHENTICATION_FAILED — which is the same evidence you would get from two genuinely different keys. Two ends with the same PSK typed correctly and mismatched ids fail exactly like two ends with different PSKs.

Where the secret contains characters the CLI would rather not carry, VyOS accepts a base64 form: encode it, then set both secret 'BASE64VALUE' and secret-type base64 on the psk node. That is an encoding, not protection.

Step 4: peer, VTI and MTU

Configuration changeroute-based peer with a VTI
set vpn ipsec site-to-site peer PEER-SITE-B ike-group 'IKE-GROUP'
set vpn ipsec site-to-site peer PEER-SITE-B default-esp-group 'ESP-GROUP'
set vpn ipsec site-to-site peer PEER-SITE-B local-address '198.51.100.1'
set vpn ipsec site-to-site peer PEER-SITE-B remote-address '203.0.113.1'
set vpn ipsec site-to-site peer PEER-SITE-B connection-type 'initiate'
set vpn ipsec site-to-site peer PEER-SITE-B vti bind 'vti0'

set interfaces vti vti0 address '10.100.100.1/30'
set interfaces vti vti0 description 'IPsec to Site B'
set interfaces vti vti0 mtu '1400'
set interfaces vti vti0 ip adjust-mss 'clamp-mss-to-pmtu'

set protocols static route 192.0.2.0/24 next-hop 10.100.100.2

compare

connection-type is a two-ended decision. One peer is initiate; the other is none, meaning the connection is loaded and waits to be initiated from the far side. That is the pairing the VyOS documentation recommends for site-to-site, and it goes with the DPD and close-action split from step 2.

For a policy-based tunnel instead of a VTI, the VTI binding and the static route are replaced by traffic selectors on the peer:

set vpn ipsec site-to-site peer PEER-SITE-B tunnel 0 local prefix '198.51.100.0/24'
set vpn ipsec site-to-site peer PEER-SITE-B tunnel 0 remote prefix '192.0.2.0/24'

Route-based is the better default: adding a destination later is a route, not a renegotiation, and a routing protocol can run over the VTI. Choose policy-based when the far end can only do policy-based — and note that the VyOS documentation advises against running both styles to the same peer.

Step 5: apply with a timer, verify in order

Service impact possiblecommit-confirm, verify, then confirm
commit-confirm 10

run show vpn ike sa
run show vpn ipsec sa
run show vpn ipsec connections
run show interfaces vti vti0

# only when every check below has passed:
confirm
save

Verify in this order, and stop at the first one that fails.

IKE SA up — and on the proposal you meant. show vpn ike sa prints the negotiated values in columns: State, IKEVer, Encrypt, Hash, D-H Group, NAT-T, and the two timers A-Time (how long it has been established) and L-Time (how long until rekey). Read Encrypt, Hash and D-H Group out of the output rather than assuming them. Two ends offering several proposals can settle on the weakest one they share, and the tunnel comes up looking healthy.

Child SA with bytes in both directions. This is the check that catches the most and gets skipped the most. show vpn ipsec sa gives one row per child SA with a Bytes In/Out and a Packets In/Out column. A child SA present with bytes outbound and zero inbound is not a working tunnel — it means your side is encrypting and sending and nothing is coming back. The cause is on the far end or in the path, and it is invisible if you only look at whether an SA exists.

The child SA has the name this build should produce.

Read-only / Safethe connection name tells you which branch of step 4 committed
show vpn ipsec sa
show vpn ipsec connections
Connection         State    Uptime   Bytes In/Out   Packets In/Out   Remote address
-----------------  -------  -------  -------------  ---------------  --------------
PEER-SITE-B-vti    up       4m11s    18K/17K        142/139          203.0.113.1

Connection         State    Type     Remote address   Local TS    Remote TS
-----------------  -------  ------   ---------------  ----------  ----------
PEER-SITE-B        up       IKEv2    203.0.113.1      -           -
PEER-SITE-B-vti    up       IPsec    203.0.113.1      0.0.0.0/0   0.0.0.0/0

Illustrative output

A VTI binding produces a child SA named PEER-vti. Each policy-based tunnel produces PEER-tunnel-N. If you built a VTI and the table shows PEER-SITE-B-tunnel-0, a tunnel 0 node survived from an earlier attempt and the peer is running policy-based whatever the VTI configuration says. The 0.0.0.0/0 in the Local TS and Remote TS columns is the VTI signature from step 4, not a fault.

VTI up, route present, and the route is the one traffic will take. show interfaces vti vti0 for the interface, show ip route 192.0.2.0/24 for the route.

A large do-not-fragment ping crosses. The check that proves step 4.

Read-only / Safethe MTU proof — a default-size ping does not do this
ping 10.100.100.2 size 1372 do-not-fragment count 3

ping 10.100.100.2 count 3

size is the ICMP payload, not the packet: 1372 plus 20 bytes of IP header and 8 of ICMP header is 1400, the VTI MTU set in step 4. Run the small case afterwards so that a failure above means “too big” rather than “no path at all”.

Finish by testing one real application flow from a host behind one side to a host behind the other. Router-to-router across the VTI proves the tunnel; only host-to-host proves the routing, the firewall and the MSS clamp together.

What each step costs if it is wrong

StepCost of getting it wrong
Skipping the step-0 path checkAn evening spent aligning proposals that were always compatible, against a firewall rule nobody looked at.
set vpn ipsec interface on a shared routerRestricts IPsec policy installation to that interface for every existing peer, during a window booked for one new one.
disable-route-autoinstall with policy-based peers presentRemoves routing those peers depend on. The tunnels stay up; the traffic stops.
Omitting disable-route-autoinstall on a VTI buildstrongSwan installs a default route via the VTI peer address, from the tunnel’s own 0.0.0.0/0 selectors.
Both ends connection-type initiateDuplicate child SAs, periodic renegotiation, a tunnel that “flaps for no reason”.
connection-type initiate with no DPD and no close-actionThe tunnel comes up once and never comes back after the first drop.
dead-peer-detection timeout in an IKEv2 groupA failover expectation sized from a value that is not in effect.
PSK id not matching the presented identityAuthentication failure that looks like a wrong secret, with the correct secret configured on both ends.
Leaving the VTI at its default MTU 1500Ping works, applications hang. Diagnosed as an application fault, often for days.
Reading VTI selectors as a faultTime spent “fixing” 0.0.0.0/0, which is the correct value for a VTI.
Verifying on “SA exists” instead of bidirectional bytesA one-way tunnel signed off as working.
rollback N used as the undoReboot — and every other tunnel on the router goes with it.

Escalation and the option to hold

Escalate outward as soon as local evidence points outward. A capture showing IKE leaving and nothing returning, or a child SA with bytes in one direction, is complete evidence of a far-end condition; continuing to change local parameters against it just adds variables to someone else’s problem.

Hold rather than proceed when there is no agreed parameter sheet. Two ends configuring from intent and negotiating by trial will spend the window producing NO_PROPOSAL_CHOSEN, and the result at the end of it is a tunnel whose actual crypto nobody chose. Record the hold with an owner and a date.

References

  1. VyOS documentation — IPsec site-to-site VPN (peer tree, connection types, op-mode commands, worked route-based example)
  2. VyOS documentation — IPsec general information (ike-group, esp-group, log, options, IKEv2 retransmission)
  3. VyOS documentation — VTI interfaces, and why route autoinstall must be disabled
  4. VyOS documentation — troubleshooting site-to-site IPsec (op-mode output shapes and charon log lines)
  5. VyOS documentation — CLI, commit-confirm, compare, load and rollback
  6. RFC 7296 — Internet Key Exchange Protocol Version 2 (IKEv2)
  7. RFC 3948 — UDP Encapsulation of IPsec ESP Packets (NAT-T)