0

I have two network interfaces: wg0 and wg1 (wireguard). Via both of these, it is possible to reach (ipv6) address fc00:77ee::4, but wg1 can only reach the address if it is in a local network. the route via wg0 is going via a peer with the address fc00:77ee::1.

i want the route over wg1 to be chosen when available because it has lower latency. i am doing this by setting a lower metric for the route via wg1 than via wg0. but this makes contacting fc00:77ee::4 timeout when not in the local network. it refuses to use the other route when there is a timeout.

i made this script

ping -c 1 -W 2 fc00:77ee::4 -I wg1 &>/dev/null if [ $? -ne 0 ]; then sudo ip route del fc00:77ee::4 dev wg1 sudo ip route add fc00:77ee::4 metric 257 dev wg1 else ip route get fc00:77ee::4 dev wg1 | grep 'metric 255' if [ $? -ne 0 ]; then sudo ip route del fc00:77ee::4 dev wg1 sudo ip route add fc00:77ee::4 metric 255 dev wg1 fi fi 

to change the metric to prefer the route via wg0 if the route via wg1 timeouts and this works quite well.

but is there any better way to do this? i.e. choose route via wg0 if route via wg1 timeouts and otherwise choose route via wg1? …because pinging the address every few seconds seems like a bad solution with a bunch of overhead.

am i missing something? is doing this via metric not the way?

is there some way to choose the least latency route via wireguard itself? i tried only having one wireguard interface with both peers and setting the endpoint of both, i.e. the peer with the address fc00:77ee::4 has an endpoint that is a local address, but this broke the connection to fc00:77ee::4 when not in the local network and did not result in it going via the other peer.

3
  • Why do you need separate tunnels? WG supports roaming, e.g. remote peer changing IP. Commented Jun 11 at 21:53
  • why would i want the remote peer to change its IP? then i would have to change all other configs to the new IP again, everytime it changes. and how would i know the new IP? Commented Jun 11 at 22:46
  • Why do you have two tunnels to the same destination then? Commented Jun 12 at 4:46

1 Answer 1

0

Routes don't care about TCP level timeouts. They work under TCP and deliver individual packets, not whole connections.

This would perhaps work if it were an Ethernet tunnel (VPN that provides L2 "TAP" interface), as then there would be ARP (and ICMPv6 Neighbor Discovery) involved as part of the routing procedure – which allows Dead Gateway Detection, a built-in part of IPv6, so in theory if your route specified a nexthop/gateway, then a lack of ARP or ND response from the gateway would let the kernel know that the route is unusable.

But there's no such thing with L3 tunnels like WireGuard (nor other TUN-based VPNs); the packet just goes out to "the other end" of the tunnel without any indication from the other side. If WireGuard couldn't deliver it, routing doesn't know about that. (And if WireGuard did deliver it but the remote gateway dropped it, routing doesn't know or care about that.)

(And of course with WireGuard insisting on being mediocre for all use cases, it won't indicate "no-carrier" when the remote peers can't be handshaked with, so you can't make use of of ignore_routes_on_link_down, either...)

What you could do is run an actual routing protocol such as OSPF or Babel between all three systems, with the ability to set costs for each path, but in the end, these too involve periodic probes to determine whether the remote gateway is still available (e.g. OSPF exchanges periodic 'Hello's) so they're not much of an improvement in your case.

You must log in to answer this question.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.