Kernel export metric change can delete a route and leave a forwarding blackhole until the next kernel scan
水兵
jxshuibei at gmail.com
Tue May 12 08:24:19 CEST 2026
# Title
Kernel export metric change can delete a route and leave a forwarding
blackhole until the next kernel scan
# Description
When a kernel-exported route changes `krt_metric`, BIRD may perform the
update as delete-old plus add-new instead of an atomic replace. If the add
operation fails, BIRD's source route and export view still show the route
as exported, but the Linux FIB is missing the route until the next kernel
protocol scan repairs it.
This creates a transient RIB/FIB divergence and forwarding blackhole.
# Version
Reproduced with:
```text
BIRD 2.18+branch.master.f0f859c26cf9
```
# How to reproduce
1. Create a single-router Linux namespace or VM with one tested interface.
```text
10.100.0.1/24
+---------------+
| r1 |
| |
| eth0 |
+---------------+
```
2. Configure a BIRD static blackhole source route, then rewrite it in the
kernel export filter into a direct route with an interface, preferred
source, and metric:
```bird
protocol static static_src {
ipv4;
route 198.51.100.0/24 blackhole;
}
protocol kernel krt_export {
ipv4 {
export filter {
ifname = "eth0";
krt_prefsrc = 10.100.0.1;
krt_metric = 110;
accept;
};
};
scan time 2;
}
```
3. Confirm the route is installed in the Linux FIB:
```bash
ip route show 198.51.100.0/24
```
4. Remove address `10.100.0.1/24` so that a later route add using `krt_prefsrc
= 10.100.0.1` fails:
```bash
ip addr del 10.100.0.1/24 dev eth0
```
5. Reconfigure the export filter so that the route metric changes from `110`
to `210`, without otherwise changing the source route.
6. Observe BIRD's source route and export view, then inspect the Linux FIB
before the next kernel scan:
```bash
birdc show route for 198.51.100.0/24 all
birdc show route export krt_export for 198.51.100.0/24 all
ip route show 198.51.100.0/24
```
7. Restore the address and wait for the kernel scan to confirm that the
route is repaired later:
```bash
ip addr add 10.100.0.1/24 dev eth0
sleep 3
ip route show 198.51.100.0/24
```
# Expected behavior
BIRD should not leave the forwarding plane without the route while its
control-plane/export view says the route should be exported. If the
metric-changing update cannot be installed, BIRD should either preserve the
old route, retry immediately when possible, or otherwise keep the control
plane and FIB from diverging until the next periodic scan.
# Actual behavior
After the metric-changing reconfiguration, before the next kernel scan:
```text
bird_source_present=True
bird_export_present=True
bird_export_final_metric=True
bird_export_prefsrc=True
kernel_present=False
addr_present=False
```
The route is absent from the Linux FIB even though BIRD still reports that
it should be exported. After the address is restored and the kernel
protocol scan runs, BIRD installs the route again:
# Additional context
The suspected source path is in `sysdep/linux/netlink.c`. `
nl_allow_replace()` disallows an atomic replace when the old and new `
EA_KRT_METRIC` values differ under kernel protocol metric handling. `
krt_replace_rte()` then performs delete-old followed by add-new. If add-new
fails, BIRD clears synchronization state but does not immediately recover
the missing FIB route; recovery waits for the next kernel scan.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://trubka.network.cz/pipermail/bird-users/attachments/20260512/9777165c/attachment.htm>
More information about the Bird-users
mailing list