WireGuard-Windows sets wrong gateway IP address in routes
Kilian Schauer
kilian at schauer.tech
Mon Dec 9 21:02:32 CET 2019
Hey all,
it appears I found a bug in the Windows implementation of the WireGuard client.
I'm not sure, because it seems to be a rather trivial one, but I guess you will tell me if it's not the case.
So: When you activate a configured tunnel, WG sets the very first IP address of a network as gateway, instead of the first usable address.
That means, if you have a VPN (sub)net like 10.0.10.0/24, where your server has 10.0.10.1 and the Windows machine 10.0.10.4,
the client tries to use 10.0.10.0 as gateway. This obviously doesn't work, because this address is reserved / not usable, and the gateway has a different IP.
The first usable address for hosts is 10.0.10.1, which the WireGuard client should set as gateway.
Same applies for IPv6.
The relevant code should be here: https://git.zx2c4.com/wireguard-windows/tree/tunnel/addressconfig.go#n74
The interface IP is masked with the subnet mask, which returns the very first address,
the network address (xxx.xxx.xxx.0 for a IPv4 /24) instead of the first usable address (xxx.xxx.xxx.1): https://golang.org/src/net/ip.go?s=946:960#L244
For reference, looking at TunSafe's implementation they _do_ increment the address by one:
https://github.com/TunSafe/TunSafe/blob/85a871c1d226956df7c1308a1e5527556fe35fe1/network_win32.cpp#L1147-L1152
Without knowing too much about what's going on behind the scenes, I think incrementing the returned address by one like TunSafe does it might be enough to fix this.
I didn't try it out yet though, don't have a WireGuard dev env set up. If you want me to, I can take a look and maybe send a patch if I get it to work.
I've attached my configuration + the output of 'route PRINT' before and after activating the tunnel (WG + TunSafe).
Thank you very much
Kilian
Example configuration:
Windows Client:
[Interface]
PrivateKey = [Redacted]
Address = 10.0.10.4/24, 2000:db8:bbbb:0:1000::4/80
[Peer]
PublicKey = [Redacted]
AllowedIPs = ::/0
Endpoint = vpn.example.com:51820
PersistentKeepalive = 25
Server:
[Interface]
PrivateKey = [Redacted]
Address = 10.0.10.1/24 2000:db8:bbbb:0:1000::1/80
ListenPort = 51820
[...]
[Peer]
# Windows Client
PublicKey = [Redacted]
AllowedIPs = 10.0.10.4/32, 2000:db8:bbbb:0:1000::4/128
And the routing table on the Windows client **before** activating the tunnel (rough translation. View with monospace font for proper alignment):
IPv4-Routingtable
===========================================================================
Active Routes:
Target Network Mask Gateway Interface Metric
0.0.0.0 0.0.0.0 192.168.0.1 192.168.1.150 25
127.0.0.0 255.0.0.0 On-link 127.0.0.1 331
127.0.0.1 255.255.255.255 On-link 127.0.0.1 331
127.255.255.255 255.255.255.255 On-link 127.0.0.1 331
192.168.0.0 255.255.254.0 On-link 192.168.1.150 281
192.168.1.150 255.255.255.255 On-link 192.168.1.150 281
192.168.1.255 255.255.255.255 On-link 192.168.1.150 281
224.0.0.0 240.0.0.0 On-link 127.0.0.1 331
224.0.0.0 240.0.0.0 On-link 192.168.1.150 281
255.255.255.255 255.255.255.255 On-link 127.0.0.1 331
255.255.255.255 255.255.255.255 On-link 192.168.1.150 281
===========================================================================
Static Routes:
None
IPv6-Routingtable
===========================================================================
Active Routes:
If Metric Target Network Gateway
4 281 ::/0 fe80::4244:b528:6295:8428
1 331 ::1/128 On-link
4 281 2000:db8:abcd::/64 On-link
4 281 2000:db8:abcd::150/128 On-link
4 281 fe80::/64 On-link
4 281 fe80::fc41:14c7:8c5b:e566/128 On-link
1 331 ff00::/8 On-link
4 281 ff00::/8 On-link
===========================================================================
Static Routes:
None
The routing table **after** activating the tunnel:
IPv4-Routingtable
===========================================================================
Active Routes:
Target Network Mask Gateway Interface Metric
0.0.0.0 0.0.0.0 192.168.0.1 192.168.1.150 25
0.0.0.0 128.0.0.0 10.0.10.0 10.0.10.4 5 <-----
128.0.0.0 128.0.0.0 10.0.10.0 10.0.10.4 5 <-----
10.0.10.0 255.255.255.0 10.0.10.0 10.0.10.4 5 <-----
10.0.10.4 255.255.255.255 On-link 10.0.10.4 261
127.0.0.0 255.0.0.0 On-link 127.0.0.1 331
127.0.0.1 255.255.255.255 On-link 127.0.0.1 331
127.255.255.255 255.255.255.255 On-link 127.0.0.1 331
192.168.0.0 255.255.254.0 On-link 192.168.1.150 281
192.168.1.150 255.255.255.255 On-link 192.168.1.150 281
192.168.1.255 255.255.255.255 On-link 192.168.1.150 281
224.0.0.0 240.0.0.0 On-link 127.0.0.1 331
224.0.0.0 240.0.0.0 On-link 192.168.1.150 281
255.255.255.255 255.255.255.255 On-link 127.0.0.1 331
255.255.255.255 255.255.255.255 On-link 192.168.1.150 281
===========================================================================
Static Routes:
None
IPv6-Routingtable
===========================================================================
Active Routes:
If Metric Target Network Gateway
4 281 ::/0 fe80::4244:b528:6295:8428
63 0 ::/0 2000:db8:bbbb:0:1000:: <-----
63 0 2000:db8:bbbb:0:1000::/80 2000:db8:bbbb:0:1000:: <-----
1 331 ::1/128 On-link
4 281 2000:db8:abcd::/64 On-link
4 281 2000:db8:abcd::150/128 On-link
63 256 2000:db8:bbbb:0:1000::4/128 On-link
4 281 fe80::/64 On-link
4 281 fe80::fc41:14c7:8c5b:e566/128 On-link
1 331 ff00::/8 On-link
4 281 ff00::/8 On-link
===========================================================================
Static Routes:
None
The routing table after activating the tunnel with the same config but using TunSafe as implementation:
IPv4-Routingtable
===========================================================================
Active Routes:
Target Network Mask Gateway Interface Metric
0.0.0.0 0.0.0.0 192.168.0.1 192.168.1.150 25
0.0.0.0 128.0.0.0 10.0.10.1 10.0.10.4 102 <-----
128.0.0.0 128.0.0.0 10.0.10.1 10.0.10.4 102 <-----
[vpn.example.com] 255.255.255.255 192.168.0.1 192.168.1.150 125
10.0.10.0 255.255.255.0 On-link 10.0.10.4 258
10.0.10.4 255.255.255.255 On-link 10.0.10.4 261
127.0.0.0 255.0.0.0 On-link 127.0.0.1 331
127.0.0.1 255.255.255.255 On-link 127.0.0.1 331
127.255.255.255 255.255.255.255 On-link 127.0.0.1 331
192.168.0.0 255.255.254.0 On-link 192.168.1.150 281
192.168.1.150 255.255.255.255 On-link 192.168.1.150 281
192.168.1.255 255.255.255.255 On-link 192.168.1.150 281
224.0.0.0 240.0.0.0 On-link 127.0.0.1 331
224.0.0.0 240.0.0.0 On-link 192.168.1.150 281
255.255.255.255 255.255.255.255 On-link 127.0.0.1 331
255.255.255.255 255.255.255.255 On-link 192.168.1.150 281
===========================================================================
Static Routes:
None
IPv6-Routingtable
===========================================================================
Active Routes:
If Metric Target Network Gateway
4 281 ::/0 fe80::4244:b528:6295:8428
63 0 ::/0 2000:db8:bbbb:0:1000::1 <-----
63 0 2000:db8:bbbb:0:1000::/80 On-link
1 331 ::1/128 On-link
4 281 2000:db8:abcd::/64 On-link
4 281 2000:db8:abcd::150/128 On-link
63 256 2000:db8:bbbb:0:1000::4/128 On-link
4 281 fe80::/64 On-link
4 281 fe80::fc41:14c7:8c5b:e566/128 On-link
1 331 ff00::/8 On-link
4 281 ff00::/8 On-link
===========================================================================
Static Routes:
None
More information about the WireGuard
mailing list