Skip to content

Gateway Backup Links

When the box goes down, the gateway switches by itself to a backup link : a free ethernet port, a phone’s connection sharing over wifi… The zone stays on Internet in degraded mode, then goes back to the box as soon as it responds.

Every Internet link (the WAN, then the backups) carries its own default route. The lowest metric wins.

LinkMetric
WAN (the box)100
Backup link200 + 10 × priority (300 by default)
Return link, in probationmetric + 10000
Link without Internetmetric + 20000

Three situations are covered :

SituationDetectionEffect
Unplugged cable, box powered off, no DHCP lease anymorethe WAN route disappearsthe kernel takes the next route
Box powered on but Internet cut offthe dnf-uplink-monitor probe fails 3 times (about 40 seconds)the WAN goes to 20100, the backup takes over
Internet back on the box6 successful probesswitch back to the WAN
Unplugged or changed cable, box restarted, 3 rounds without a routeloss of carrier or of routethe link returns to probation (10100), then finds its place back after 6 successful probes

The probe sends a ping through each link (1.1.1.1 and 9.9.9.9, every 10 seconds). It does not depend on DNS : it targets IP addresses.

The two link types do not wait the same way :

TypeWhile waitingWake-up
ethernetconnected, without traffic (the metric keeps everything on the box)immediate
wifiradio off (rfkill) : no connection to the sharingas soon as no preferred link reaches the Internet
  1. Identify the interface on the gateway :

    Fenêtre de terminal
    ip -br link

    It must be free : neither the WAN, nor a LAN port, nor a wifi access point’s radio.

  2. Declare the link in the host’s file :

    usr/machines/gw/configuration.nix
    darkone.host.gateway.backupLinks = {
    phone = {
    type = "wifi";
    interface = "wlp4s0";
    };
    voisin = {
    type = "ethernet";
    interface = "enp3s0";
    priority = 20;
    };
    };
    OptionRole
    typeethernet (DHCP client) or wifi (WPA2/WPA3 client)
    interfaceinterface that carries the link
    priority1 to 99, the lowest is preferred among the backups
  3. For a wifi link, enter the SSID and the passphrase in sops with just sops :

    usr/secrets/secrets.yaml
    backup-link:
    phone:
    ssid: "Partage du téléphone"
    psk: "passphrase-du-partage"

    The SSID and the passphrase never go through the Nix store.

  4. Deploy :

    Fenêtre de terminal
    just apply gw
Fenêtre de terminal
networkctl list # the link is “routable” when it is active
ip -4 route show default # the first line is the link in use
rfkill # backup wifi radio “blocked” in standby
journalctl -u dnf-uplink-monitor -f # radio switches and wake-ups, live

With the box down and the phone sharing its connection :

default via 192.168.1.254 dev enp1s0 proto dhcp src 192.168.1.10 metric 20100
default via 192.168.43.1 dev wlp4s0 proto dhcp src 192.168.43.20 metric 300
OptionDefaultRole
darkone.host.gateway.linkCheck.targets1.1.1.1, 9.9.9.9pinged addresses, a single reply is enough
darkone.host.gateway.linkCheck.interval10seconds between two rounds
darkone.host.gateway.linkCheck.failAfter3failures before penalizing a link
darkone.host.gateway.linkCheck.recoverAfter6successes before restoring it

The probe publishes three metrics for Prometheus :

MetricValue
dnf_gateway_link_up1 if the link has a route and reaches the Internet
dnf_gateway_link_active1 on the link carrying the default route
dnf_gateway_link_standby1 on a backup wifi radio turned off and waiting

The GatewayOnBackupLink alert (warning) triggers after 2 minutes on a backup link.

LimitDetail
Streams cut on switchoverin-progress connections restart over the new link (call or download to relaunch)
Subnet in conflicta link that hands out addresses from the zone network (e.g. 10.0.0.0/16) breaks routing; a phone’s connection sharing uses a small, distinct network (/24), so no conflict in practice
SSID and passphrasewithout double quotes (")
Remote LUKS unlockover the WAN or the LAN only
Removed linksa running penalty stays until reboot : delete /run/systemd/network/*.network.d/90-dnf-penalty.conf, then networkctl reload