Project

General

Profile

Actions

Feature #11354

closed

WireGuard should respond from the address used by peer

Added by Jim Pingle about 3 years ago. Updated about 3 years ago.

Status:
Resolved
Priority:
Low
Assignee:
Category:
WireGuard
Target version:
Start date:
02/01/2021
Due date:
% Done:

100%

Estimated time:
Plus Target Version:
Release Notes:

Description

When a WireGuard peer contacts the firewall, the firewall always responds from the address it deems closest to the client, determined by the routing table. If there are multiple addresses on an interface, this means that the kernel may respond to a WireGuard packet from an address the remote peer doesn't expect. In some cases, this can operate OK, but others fail. Ideally responses should be sourced using the same address a client used, and not the closest address. Not sure how viable this is, but some features like HA and certain Multi-WAN use cases require it to function properly.

For example, in an HA configuration, the primary node may have an address like 198.51.100.12, but a CARP VIP of 198.51.100.11. Remote peers should always contact the CARP VIP for proper failover, but when they do, packets come to the firewall on 198.51.100.11 and replies are sourced from 198.51.100.12.

Example: HA node with 198.51.100.12 on interface, VIP of 198.51.100.11, and remote peer of 198.51.100.140. Remote peer is configured for an endpoint of 198.51.100.11:51821, but when the peer sends a packet:

12:59:00.174199 IP 198.51.100.140.51783 > 198.51.100.11.51821: UDP, length 148
12:59:00.177233 IP 198.51.100.12.51821 > 198.51.100.140.51783: UDP, length 92

The internal roaming feature of WireGuard allows that to work for some cases but it isn't ideal. If the primary node fails the peer will still keep trying to contact it directly since it keeps its last known peer endpoint, rather than using the original CARP VIP endpoint address which should move to a secondary node. The remote peer end may need to manually be restarted in this case to reset its knowledge of the last known peer address.

Also if an administrator wishes to run WireGuard on an alternate WAN that isn't the default route, responses would be sent out using the wrong address and path back to the peer. In some cases that can be worked around, like for static peers using a static route, but that also isn't ideal.

If responses were sourced using the same address the client used, all of this would work automatically.

Additional Notes:

  • We can't work around this with outbound NAT when initiating locally because when failover is triggered, the existing state can't match. The source on the existing NAT state is the interface address on the primary node, which won't work when the secondary node has MASTER status on the CARP VIP. The state would need to be manually cleared.
  • Can't work around it with port forwards because the responses never match the port forward states as they come from the default WAN address.
  • Outbound NAT also fails for cases of remote initiation (e.g. Remote Access clients) as inbound states already exist for the exact ports needed, so NAT fails to create a new state. Using NAT rules without static port ends up back at the first point above. Works at first, but doesn't work when failing over.

Files

if_wg.ko.carp (339 KB) if_wg.ko.carp Peter Grehan, 02/04/2021 06:02 AM
pfsense_wg_reflect_addrs.diff (2 KB) pfsense_wg_reflect_addrs.diff Peter Grehan, 02/04/2021 06:03 AM

Related issues

Related to Feature #11302: WireGuard XMLRPC syncNew01/23/2021

Actions
Actions

Also available in: Atom PDF