Wireguard as default gw

Hi, I'm struggling to make this work:

Peer1 (ISP1's router has port forwarding configured for wireguard):
clients ↔ OpenWrt router with NAT ↔ ISP1 router with NAT ↔ Internet
192.168.17.0/24 ↔ 192.168.17.1 | 192.168.1.254 ↔ 192.168.1.1|DSL ↔ Internet

Peer2
RaspPi with WG ↔ ISP2 router with NAT ↔ Internet
192.168.2.2/24 ↔ 192.168.2.1/24|DSL ↔ Internet

I want clients to connect to internet through ISP2
clients ↔ OpenWrt ↔ [(10.10.10.1) wg tunnel (10.10.10.2)] ↔ RaspPi ↔ ISP2 router ↔ Internet

The scenario is similar to this one, but I want to use wireguard instead of openvpn.

With this configuration I get the tunnel up and I can ping both rpi and ISP2' router from openwrt.
But tracert 8.8.8.8 is routed through ISP1.

/etc/config/network

config interface 'loopback'
	option device 'lo'
	option proto 'static'
	option ipaddr '127.0.0.1'
	option netmask '255.0.0.0'

config globals 'globals'
	option ula_prefix '<ula_prefix>'

config device
	option name 'br-lan'
	option type 'bridge'
	list ports 'eth0.1'

config interface 'lan'
	option device 'br-lan'
	option proto 'static'
	option netmask '255.255.255.0'
	option ip6assign '60'
	option ipaddr '192.168.17.1'

config device
	option name 'eth0.2'
	option macaddr '00:18:84:88:13:25'

config interface 'wan'
	option device 'eth0.2'
	option proto 'static'
	option ipaddr '192.168.1.254'
	option netmask '255.255.255.0'
	option broadcast '192.168.1.255'
	option gateway '192.168.1.1'

config interface 'wan6'
	option device 'eth0.2'
	option proto 'dhcpv6'

config switch
	option name 'switch0'
	option reset '1'
	option enable_vlan '1'

config switch_vlan
	option device 'switch0'
	option vlan '1'
	option ports '0 1 2 3 6t'

config switch_vlan
	option device 'switch0'
	option vlan '2'
	option ports '4 6t'

config interface 'wg0'
	option proto 'wireguard'
	option private_key '<private_key>'
	option listen_port '51820'
	option force_link '1'
	list addresses '10.10.10.1/24'

config wireguard_wg0
	option description 'rpi'
	option public_key '<public_key>'
	option route_allowed_ips '1'
	option persistent_keepalive '25'
	list allowed_ips '10.10.10.2/32'
	list allowed_ips '192.168.2.0/24'

If for the peer configuration in openwrt I change the above to this:
Allowed IPs: 0.0.0.0/0
Then I don't even get the handshake

config wireguard_wg0
	option description 'rpi'
	option public_key '<public_key>'
	option route_allowed_ips '1'
	option persistent_keepalive '25'
	list allowed_ips '0.0.0.0/0'

but I guess I need 0.0.0.0/0 for the final end to end.

What am I doing wrong? Any help will be much appreciated.

/etc/config/firewall is the other file that I believe will be needed.
As you can see everything is enabled for now. lan -> wg is accepted, and masq is being used for wg:

config defaults
	option input 'ACCEPT'
	option output 'ACCEPT'
	option forward 'REJECT'
	option synflood_protect '1'

config zone
	option name 'lan'
	option input 'ACCEPT'
	option output 'ACCEPT'
	option forward 'ACCEPT'
	list network 'lan'

config zone
	option name 'wan'
	option output 'ACCEPT'
	option mtu_fix '1'
	list network 'wan'
	list network 'wan6'
	option input 'ACCEPT'
	option forward 'ACCEPT'

config rule
	option name 'Allow-DHCP-Renew'
	option src 'wan'
	option proto 'udp'
	option dest_port '68'
	option target 'ACCEPT'
	option family 'ipv4'

config rule
	option name 'Allow-Ping'
	option src 'wan'
	option proto 'icmp'
	option icmp_type 'echo-request'
	option family 'ipv4'
	option target 'ACCEPT'

config rule
	option name 'Allow-IPSec-ESP'
	option src 'wan'
	option dest 'lan'
	option proto 'esp'
	option target 'ACCEPT'

config rule
	option name 'Allow-ISAKMP'
	option src 'wan'
	option dest 'lan'
	option dest_port '500'
	option proto 'udp'
	option target 'ACCEPT'

config rule
	option name 'Support-UDP-Traceroute'
	option src 'wan'
	option dest_port '33434:33689'
	option proto 'udp'
	option family 'ipv4'
	option target 'REJECT'
	option enabled 'false'

config include
	option path '/etc/firewall.user'

config zone
	option name 'wgzone'
	option output 'ACCEPT'
	list network 'wg0'
	option input 'ACCEPT'
	option forward 'ACCEPT'
	option masq '1'

config forwarding
	option src 'lan'
	option dest 'wgzone'

The configuration for peer2 is as follows:

[Interface]
Address = 10.10.10.2/24
PrivateKey = <PrivateKey>

[Peer]
# openwrt
Endpoint = public.net:51820
AllowedIPs = 10.10.10.1/32, 192.168.17.0/24
PublicKey = <PublicKey>
PersistentKeepalive = 25

[Peer]
# different tunnel that works fine
Endpoint = public.net:51821
AllowedIPs = 10.10.10.3/32, 192.168.1.0/24
PublicKey = <PublicKey>
PersistentKeepalive = 25

Try changing the allowed IPs to 0.0.0.0/0 and the interface address to a /32.

config interface 'wg0'
	option proto 'wireguard'
	option private_key '<private_key>'
	option listen_port '51820'
	option force_link '1'
	list addresses '10.10.10.1/32'

config wireguard_wg0
	option description 'rpi'
	option public_key '<public_key>'
	option route_allowed_ips '1'
	option persistent_keepalive '25'
	list allowed_ips '0.0.0.0'

Report back on the status...
If you don't get a handshake, try changing the peer config section allowed_ips back to what it was and test again.

Hi, thanks for the fast response.

I first applied suggested changes, but still no joy

image

Also if I try to ping from openwrt the other end of the 10.10.10.2 tunnel I guet timeouts.

Then I changed back the allowed_ips leaving it like this:

config interface 'wg0'
	option proto 'wireguard'
	option private_key '<private_key>'
	option listen_port '51820'
	option force_link '1'
	list addresses '10.10.10.1/32'

config wireguard_wg0
	option description 'rpi'
	option public_key '<public_key>'
	option route_allowed_ips '1'
	option persistent_keepalive '25'
	list allowed_ips '10.10.10.2/32'
	list allowed_ips '192.168.2.0/24'

But I do not think this makes it any different. As I can ping from wrt both 10.10.10.2 and 192.168.2.2, and even the gw 192.168.2.1, but when I ping an internet IP 8.8.8.8 it gets routed through ISP1, just as before.

I get similar results from a "client"

$ ping 10.10.10.1
PING 10.10.10.1 (10.10.10.1) 56(84) bytes of data.
64 bytes from 10.10.10.1: icmp_seq=1 ttl=64 time=1.19 ms
64 bytes from 10.10.10.1: icmp_seq=2 ttl=64 time=1.14 ms

$ ping 10.10.10.2
PING 10.10.10.2 (10.10.10.2) 56(84) bytes of data.
64 bytes from 10.10.10.2: icmp_seq=1 ttl=63 time=69.9 ms
64 bytes from 10.10.10.2: icmp_seq=2 ttl=63 time=66.3 ms

$ ping 8.8.8.8
PING 8.8.8.8 (8.8.8.8) 56(84) bytes of data.
From 192.168.17.1 icmp_seq=2 Destination Port Unreachable
From 192.168.17.1 icmp_seq=4 Destination Port Unreachable

What does the other peer (that works) look like?

^^^ can you show us the other side of this peer?

The other end is another RPi that sits in 192.168.1.0/24.
ISP1's router has antother port forwardind for it.

[Interface]
Address = 10.10.10.3/24
ListenPort = 51821
PrivateKey = <PrivateKey>

PostUp   = iptables -A FORWARD -i %i -j ACCEPT; iptables -A FORWARD -o %i -j ACCEPT; iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
PostDown = iptables -D FORWARD -i %i -j ACCEPT; iptables -D FORWARD -o %i -j ACCEPT; iptables -t nat -D POSTROUTING -o eth0 -j MASQUERADE

[Peer]
AllowedIPs = 10.10.10.2/32
PublicKey = <PrivateKey>

Would you be willing to try 'reversing' your connection...

currently, the OpenWrt router is listening for the connection from the Pi. If you did it the other way, it might work better.

Unfortunately, I cannot do that because of the ISP's routers.
I can manage (open ports) only ISP1's...

Ok... understood.

Let me think about this some more. I'm not sure why it would fail to handshake with the allowed IPs set to 0.0.0.0/0.

What happens if you turn on masquerading on your OpenWrt wan zone? Is there a specific reason why you currently have that disabled?

(do this in conduction with setting the allowed IPs to 0.0.0.0/0)

I know, it has me puzzle too.

I first thought it might be something with the openwrt router (although it has just been flashed and upgraded to OpenWrt 21.02.2 r16495-bf0c965af0 recently...) and started playing with another old dsl modem I had around, also flashed to openwrt, but this second one does not have wan port and it had to be set up differently, I guess. It is a Comtrend AR-5387 un.

But I have a feeling it might be related to the default gw 0.0.0.0 may be clashing with the port forward needed to start the tunnel??.

I haven't turn masquerading on WAN only because I want 100% of the traffic sent through the VPN, and therefore masquerading behind 10.10.10.1.

That's possible... but actually it really only should affect outbound traffic.

You can safely turn on masquerading on the WAN... once the tunnel is up, everything will (nominally) go through the tunnel as long as the allowed IPs = 0.0.0.0/0. Try the masquerading and see if it works.

I just gave it a go, and the tests give me the very same results I got without enabling masq on wan.

Bummer. Ok. I’ll continue thinking.

1 Like

I always suggest to recheck the routes (while allowed ips - 0.0.0.0/0 should assure they are injected with the right priority) so just post ip ro to check.

Next step is always to check if the package is leaving the interface tcpdump -n -i wireguard_wg0

If package is not leaving the interface it means that either routing is wrong or package is blocked by firewall (for that enable logging on the firewall).

Good point,

This is the routing table out of my last test.
The default route is obvioulsly not what I want

# ip r
default via 192.168.1.1 dev eth0.2 
10.10.10.1 dev wg0 scope link 
192.168.2.0/24 dev wg0 scope link 
192.168.17.0/24 dev br-lan scope link  src 192.168.17.1 
192.168.1.0/24 dev eth0.2 scope link  src 192.168.1.254

An this is the routing table when I revert back to list allowed_ips '0.0.0.0/0'

# ip r
default dev wg0 scope link 
192.168.17.0/24 dev br-lan scope link  src 192.168.17.1 
192.168.1.0/24 dev eth0.2 scope link  src 192.168.1.254

The routing table looks better to me, but no Handshake now.
tcpdump from openwrt shows c

# tcpdump -n -i wg0
tcpdump: verbose output suppressed, use -v or -vv for full protocol decode
listening on wg0, link-type RAW (Raw IP), capture size 262144 bytes
09:33:37.148097 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 92
09:33:42.268465 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 92
09:33:48.028253 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 92
09:33:53.147997 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 92
09:33:58.190346 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 92

And when I ping the other end of the tunnel 10.10.10.2 from a different ssh session

# ping 10.10.10.2
PING 10.10.10.2 (10.10.10.2): 56 data bytes

I wet this in tcpdump

...
09:33:58.190346 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 92
09:33:58.190346 IP 10.23.5.6.50123 > 80.161.179.178.59682: UDP, length 92
09:34:03.388300 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 92
09:34:06.345844 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 0, length 64
09:34:07.347342 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 1, length 64
09:34:08.348883 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 2, length 64
09:34:09.350355 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 3, length 64
09:34:09.361950 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 148
09:34:10.350792 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 4, length 64
09:34:11.351213 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 5, length 64
09:34:12.351637 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 6, length 64
09:34:13.352054 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 7, length 64
09:34:14.352472 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 8, length 64
09:34:14.888157 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 148
09:34:15.352959 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 9, length 64
09:34:16.353388 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 10, length 64
09:34:17.353808 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 11, length 64
09:34:18.354234 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 12, length 64
09:34:19.354656 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 13, length 64
09:34:20.264331 IP 10.10.10.1.51820 > some_public_ip.59682: UDP, length 148
09:34:20.355077 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 14, length 64
09:34:21.355504 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 15, length 64
09:34:22.355939 IP 10.10.10.1 > 10.10.10.2: ICMP echo request, id 16585, seq 16, length 64

And I end up canceling the ping command

# ping 10.10.10.2
PING 10.10.10.2 (10.10.10.2): 56 data bytes
^C

Ok, looks like that you also loose the route to the other side to establish the tunnel.
So you would need a fixed route to the public IP of the WG peer and point it to your WAN GW
There are several ways of doing that, suggest to search forum. Here is one solution

Thanks, @faser
Makes sense, but wouldn't this situation be the case in any full (0.0.0.0/0) tunnel, wether openwrt is part of the equation or not?
Another problem is that the other end does not have a predictable IP, that's why I forward ports in ISP1's router.
The route you are suggesting would have to be dynamic and based on destination port being udp/51820 and source IP not in 10.10.10.1/24 range, wouldn't it?

It would be, therefore a script (e.g. wg-quick) add respective routes/rules to make the vpn server still reachable.
https://manpages.debian.org/unstable/wireguard-tools/wg-quick.8.en.html

Yes therefore it might be easier to work with firewall rules and multiple GWs easier.