machines/stellio: deprecate withdrawn DHCPv6-PD prefixes (interim copy of cnx-network fa11327)
After the reboot vlan-lan got its /64 at boot, but IPv6 still failed for clients: the first PPPoE session lands on another AIS BNG, is torn down minutes later, and the reconnect brings a different /64 (07:53 2405:9800:b911:91e3 -> 07:57 b910:1f5d). networkd announces the new prefix at once but never deprecates the old one (systemd#29651), so clients keep it preferred for up to 30 minutes and source selection sends every connection from a dead address. router-radv-deprecate.service watches vlan-* for networkd removing a dynamic address and sends RAs with that /64 at preferred lifetime 0 via a short-lived radvd (SIGKILLed: no shutdown RA). Identical script to the upstream commit; drop once the cnx-network input is bumped past it. Verified on stellio: the stale prefix flipped to deprecated on the client at the first RA and pings resumed; a synthetic dynamic address removed from vlan-lan produced the same RA end to end.
This commit is contained in:
1 parent
b5077983ea
commit
31ebf2d081
1 file changed
+59
@@ -108,6 +108,65 @@
|
|||||||
systemd.network.networks."40-vlan-lan".dhcpPrefixDelegationConfig.SubnetId = lib.mkForce "0x0";
|
systemd.network.networks."40-vlan-lan".dhcpPrefixDelegationConfig.SubnetId = lib.mkForce "0x0";
|
||||||
systemd.network.networks."40-vlan-mgmt".dhcpPrefixDelegationConfig.SubnetId = lib.mkForce "0x1";
|
systemd.network.networks."40-vlan-mgmt".dhcpPrefixDelegationConfig.SubnetId = lib.mkForce "0x1";
|
||||||
|
|
||||||
|
# Interim copy of cnx-network-clan fa11327 (router/ipv6: deprecate
|
||||||
|
# withdrawn DHCPv6-PD prefixes); drop when the input is bumped past it.
|
||||||
|
# networkd never deprecates a prefix it stops announcing (systemd#29651):
|
||||||
|
# on every reboot the first PPPoE session lands on another AIS BNG, is
|
||||||
|
# torn down minutes later, and the reconnect brings a different /64.
|
||||||
|
# networkd announces the new prefix at once but clients keep the old
|
||||||
|
# one preferred for the rest of its 1800 s lifetime, so RFC 6724 source
|
||||||
|
# selection picks the dead prefix and every v6 connection fails for up
|
||||||
|
# to 30 minutes (2026-10-08 07:57). Watch vlan-* for networkd removing a
|
||||||
|
# dynamic (PD) address and send a few RAs with that /64 at preferred
|
||||||
|
# lifetime 0; radvd is only the packet generator, killed hard after ~7 s
|
||||||
|
# so it sends no shutdown RA (router lifetime 0) and does not keep
|
||||||
|
# deprecating a prefix the ISP re-delegates on reconnect.
|
||||||
|
systemd.services.router-radv-deprecate = {
|
||||||
|
description = "Deprecate withdrawn DHCPv6-PD prefixes on the VLANs";
|
||||||
|
wantedBy = [ "multi-user.target" ];
|
||||||
|
after = [ "systemd-networkd.service" ];
|
||||||
|
path = [
|
||||||
|
pkgs.iproute2
|
||||||
|
pkgs.ipcalc
|
||||||
|
pkgs.radvd
|
||||||
|
];
|
||||||
|
serviceConfig = {
|
||||||
|
Restart = "always";
|
||||||
|
RestartSec = 2;
|
||||||
|
RuntimeDirectory = "router-radv-deprecate";
|
||||||
|
};
|
||||||
|
script = ''
|
||||||
|
conf=$RUNTIME_DIRECTORY/radvd.conf
|
||||||
|
pid=$RUNTIME_DIRECTORY/radvd.pid
|
||||||
|
# "Deleted 4: vlan-lan inet6 2001:db8::1/64 scope global dynamic mngtmpaddr \ valid_lft ..."
|
||||||
|
ip -o -6 monitor address | while read -r event _ dev _ addr _ scope rest; do
|
||||||
|
[[ $event == Deleted && $dev == vlan-* && $scope == global && $rest == *dynamic* ]] || continue
|
||||||
|
prefix="$(ipcalc --no-decorate -n "$addr")/''${addr##*/}"
|
||||||
|
echo "$dev: deprecating withdrawn prefix $prefix"
|
||||||
|
cat > "$conf" <<EOF
|
||||||
|
interface $dev {
|
||||||
|
AdvSendAdvert on;
|
||||||
|
MinRtrAdvInterval 3;
|
||||||
|
MaxRtrAdvInterval 4;
|
||||||
|
AdvDefaultLifetime 1800;
|
||||||
|
AdvCurHopLimit 0;
|
||||||
|
prefix $prefix {
|
||||||
|
AdvOnLink on;
|
||||||
|
AdvAutonomous on;
|
||||||
|
AdvPreferredLifetime 0;
|
||||||
|
AdvValidLifetime 7200;
|
||||||
|
};
|
||||||
|
};
|
||||||
|
EOF
|
||||||
|
rm -f "$pid"
|
||||||
|
radvd -C "$conf" -p "$pid" -n -m stderr &
|
||||||
|
sleep 7
|
||||||
|
kill -KILL $! 2>/dev/null || true
|
||||||
|
wait $! || true
|
||||||
|
done
|
||||||
|
'';
|
||||||
|
};
|
||||||
|
|
||||||
systemd.services.heartbeat-push = {
|
systemd.services.heartbeat-push = {
|
||||||
description = "Heartbeat push to uptime monitor";
|
description = "Heartbeat push to uptime monitor";
|
||||||
serviceConfig = {
|
serviceConfig = {
|
||||||
|
|||||||
Reference in new issue
Block a user