TTR Networks

Intermediate · BFD on VyOS: fast failover for quiet failures · section 3 of 7

BFD for OSPF

✓ Lab-tested 21 October 2026 on VyOS 2026.10.16-0024-rolling, FRR 10.2.1

How BFD works

A BFD session runs between two neighbours that already know each other, usually because a routing protocol asked for one. Each side sends tiny UDP packets (port 3784) at an agreed interval. If no packet arrives for interval × multiplier, the session goes down, and BFD tells the protocols that use it. They react at once, as if the link had failed.

  • Transmit and receive intervals: how often each side wants to send, and how often it's willing to receive. The two sides negotiate, and the slower one wins.
  • Multiplier: how many packets in a row may be missed. With 300 ms and 3, the detection time is 900 ms.
  • BFD is designed to be light enough to run in the forwarding path, or in a dedicated daemon (bfdd in FRR), independent of how busy the routing protocol is.

Profiles

VyOS groups timers into named profiles, so every session that should behave the same way says so by name. The lab's profile FAST is 300 ms × 3. OSPF interfaces then ask for BFD with bfd profile FAST. R2 does the same in FRR syntax. FRR doesn't even print the timers in its saved configuration, because 300 ms × 3 is its default.

show bfd peers lists both sessions, with the negotiated timers, the actual interval with jitter (BFD varies it slightly so sessions don't synchronise), and the 900 ms detection timeout. Peer Type: dynamic means OSPF created the session, not the BFD configuration.

The same failure, with BFD

Link A was cut at 08:37:53, and OSPF dropped the neighbour at 08:37:54. h1 lost 9 pings: under a second. The log still says InactivityTimer: when BFD reports the neighbour down, FRR's OSPF expires the dead timer immediately rather than waiting for it.

While the link was down, the session for link A wasn't shown as down: it had gone, because OSPF had removed the neighbour that asked for it. The route to LAN2 had already moved to link B.

R1: a BFD profile, used by both OSPF interfaces
set protocols bfd profile FAST interval transmit '300'
set protocols bfd profile FAST interval receive '300'
set protocols bfd profile FAST interval multiplier '3'
set protocols ospf interface eth0 bfd profile 'FAST'
set protocols ospf interface eth1 bfd profile 'FAST'
  • Lines 1–3: 300 ms intervals, three missed packets: 900 ms to detect a failure.
  • Lines 4–5: OSPF asks BFD to watch each neighbour.
R2 (FRR): OSPF with BFD
frr version 10.2.1_git
frr defaults traditional
hostname R2
no ipv6 forwarding
service integrated-vtysh-config
!
interface eth0
 description link A to R1
 ip address 10.0.12.2/30
 ip ospf bfd
 ip ospf bfd profile FAST
 ip ospf cost 10
 ip ospf network point-to-point
exit
!
interface eth1
 description link B to R1 (backup)
 ip address 10.0.12.6/30
 ip ospf bfd
 ip ospf bfd profile FAST
 ip ospf cost 100
 ip ospf network point-to-point
exit
!
interface eth2
 description LAN2
 ip address 198.51.100.129/25
 ip ospf passive
exit
!
interface lo
 ip address 192.0.2.2/32
exit
!
router ospf
 ospf router-id 192.0.2.2
 network 10.0.12.0/30 area 0
 network 10.0.12.4/30 area 0
 network 192.0.2.2/32 area 0
 network 198.51.100.128/25 area 0
exit
!
bfd
 profile FAST
 exit
 !
exit
!
  • Lines 10–11: The same on R2, interface by interface.
  • Lines 43–47: The FAST profile: empty, because 300 ms × 3 is FRR's default and isn't saved.
The BFD sessions (real output)
vyos@R1:~$ show bfd peers brief
Session count: 2
SessionId  LocalAddress                             PeerAddress                             Status          Profile
=========  ============                             ===========                             ======          =======
3012387602 10.0.12.5                                10.0.12.6                               up              FAST
2108029913 10.0.12.1                                10.0.12.2                               up              FAST
vyos@R1:~$ show bfd peer 10.0.12.2
	peer 10.0.12.2 local-address 10.0.12.1 vrf default interface eth0
		ID: 2108029913
		Remote ID: 47564980
		Active mode
		Status: up
		Uptime: 11 second(s)
		Diagnostics: ok
		Remote diagnostics: ok
		Peer Type: dynamic
		RTT min/avg/max: 0/0/0 usec
		Profile: FAST
		Local timers:
			Detect-multiplier: 3
			Receive interval: 300ms
			Transmission interval: 300ms
			Transmission interval (actual with jitter): 297ms
			Detection timeout: 900ms
			Echo receive interval: 50ms
			Echo transmission interval: disabled
		Remote timers:
			Detect-multiplier: 3
			Receive interval: 300ms
			Transmission interval: 300ms
			Echo receive interval: 50ms
  • Lines 5–6: One session per link, both up, both using FAST.
  • Line 16: dynamic: created because OSPF asked for it.
  • Lines 20–24: Negotiated timers, the jittered actual interval, and the 900 ms detection time.
  • Lines 27–31: What R2 asked for: the same.
The same cut, with BFD (real output)
root@r1-container:~# date +%T; ip link set eth0 nomaster   # cut link A in the middle; carrier stays up
08:37:53

root@h1:~# ping -i 0.1 -w 20 -q 198.51.100.130   # started 5 s before the cut
PING 198.51.100.130 (198.51.100.130) 56(84) bytes of data.
--- 198.51.100.130 ping statistics ---
190 packets transmitted, 181 received, 4.73684% packet loss, time 19919ms
rtt min/avg/max/mdev = 0.422/1.511/4.657/0.786 ms
  • Lines 1–2: The cut: link A is detached in the middle, so both routers keep carrier on their interfaces.
  • Line 4: Ten pings a second from h1 to h2, started 5 seconds earlier.
  • Line 7: 9 pings lost: under a second.
When OSPF noticed this time (real output)
vyos@R1:~$ show log | match "AdjChg" | tail -1
Oct 21 08:37:54 ospfd[1284]: AdjChg: Nbr 192.0.2.2, NbrIP 10.0.12.2 (default) on eth0:10.0.12.1: Full -> Deleted (InactivityTimer)
  • Line 2: One second after the cut at 08:37:53. BFD made OSPF expire its dead timer at once.
During the outage (real output)
vyos@R1:~$ show bfd peers brief
Session count: 1
SessionId  LocalAddress                             PeerAddress                             Status          Profile
=========  ============                             ===========                             ======          =======
3012387602 10.0.12.5                                10.0.12.6                               up              FAST
vyos@R1:~$ show bfd peer 10.0.12.2
vyos@R1:~$ show ip route 198.51.100.128/25
Routing entry for 198.51.100.128/25
  Known via "ospf", distance 110, metric 110, best
  Last update 00:00:04 ago
  Flags: Selected
  Status: Installed
  * 10.0.12.6, via eth1, weight 1
  • Lines 1–5: Only link B's session is left: link A's was removed along with the OSPF neighbour.
  • Lines 7–13: Traffic to LAN2 already goes over link B (metric 110: link B's cost plus the LAN).

Check your understanding

With transmit and receive intervals of 300 ms and a multiplier of 3, how long can a path be silent before BFD declares it down?

  • 900 ms
  • 300 ms
  • 3 seconds
  • 40 seconds