Linux kernel IPv4 and IPv6 route lookup illustration

Network engineer Vincent Bernat, whose earlier deep dives into the Linux routing subsystem are widely cited, published on November 9, 2026 a new benchmark of IPv4 and IPv6 route lookup performance across Linux 4.14 to 7.3. IPv6 lookups improved and are now stable, IPv4 has slowly regressed, and the largest single cost came not from routing code but from CPU vulnerability mitigations.

Linux route lookup performance in 30 seconds

  • IPv6 lookups got faster through kernel changes in 4.15, 4.18 and 5.9.
  • From 6.5, the SRSO mitigation on AMD CPUs added about 200 ns per IPv6 lookup and about 30 ns per IPv4 lookup.
  • A 5.11 commit cost IPv4 about 5 cycles per lookup; Bernat’s fix lands in Linux 7.5.
  • Newer CPUs, selective mitigations, XDP or NIC offload are the ways to claw back performance.

The post continues a series Bernat started in 2017, when he explained how Linux stores routes (an LC-trie for IPv4, a radix tree for IPv6), and followed in 2018 with performance measurements up to 4.16 and 4.18, including the Meltdown and Spectre mitigations. This time he also tracked down the commits behind the regressions.

Test setup

The benchmarks ran on an AMD EPYC 8024P (Zen 4c) rented from Scaleway, pinned at 2.4 GHz with boost disabled. Every kernel was built with GCC 10.2, old enough to compile the oldest kernels and recent enough for the newest. On kernels that got the SRSO mitigation as a backport (5.10, 5.15, 6.1 and 6.4), it was turned off with spec_rstack_overflow=off to keep results comparable. Results are in CPU cycles, at roughly 0.42 ns per cycle.

IPv6 was tested with a current full view (about 260,000 prefixes), the 2017 full view (about 40,000), 40,000 /48 prefixes and 40,000 random /128 prefixes. IPv4 used a current full view of more than one million prefixes, a 500,000-prefix 2017 subset and 500,000 contiguous /32 routes.

IPv6 gains, an IPv4 regression and its fix

Three changes made IPv6 faster: in 4.15 Wei Wang replaced a read-write lock with RCU and a spinlock; in 4.18 David Ahern split the FIB structures used for lookups from those used for management; and in 5.9 Brian Vazquez removed costly indirect calls from fib6_rule_lookup.

IPv4 has drifted slightly slower over the years. One regression was Bernat’s own: commit c0c5a60f0f13 in 5.11 fixed ignore_routes_with_linkdown but added about 5 cycles per lookup, because ip_ignore_linkdown() chases three pointers and ran before the cheaper link-down flag check. His patch 5fe3653f13b9, now in net-next, reorders the conditions and brings the median from 132 to 126 cycles and the 95th percentile from 134 to 128. He expects Linux 7.5 to be the first stable release with the fix.

CPU mitigations dominate the cost

The biggest drop arrives in Linux 6.5 with the SRSO (Speculative Return Stack Overflow) mitigation for AMD CPUs, which adds about 20 cycles to every function return. An IPv6 lookup goes through about 25 calls, so it loses roughly 200 ns and all the earlier gains; an IPv4 lookup, with about four calls, loses around 30 ns. On a 2020 Xeon W-2295, by contrast, mitigations cost only a few cycles for IPv4 and under 3% for IPv6.

Bernat’s options for operators who need routing performance: move to newer CPUs such as AMD Zen 5, 4th-gen Xeon or ARM Neoverse V2; disable all mitigations (mitigations=off), only SRSO (spec_rstack_overflow=off), or keep protection only for selected attack vectors with mitigations=auto,no_user_kernel, available since 6.17; bypass the kernel path with XDP/eBPF, noting that bpf_fib_lookup() uses the same kernel lookup and pays the same price; or offload routing to the NIC.

Turning mitigations off is a security decision, not just a tuning knob. It may be reasonable on a dedicated router that runs no untrusted code, but on shared servers or hypervisors it reopens the attacks those mitigations were built to stop.

FAQ

Which data structures does Linux use for route lookups?

An LC-trie for IPv4 and a radix tree for IPv6.

Why did route lookups get slower in Linux 6.5?

The SRSO mitigation for AMD CPUs adds about 20 cycles per function return. IPv6 is hit harder because a lookup chains about 25 calls.

Does XDP avoid the cost?

Only if you do not use bpf_fib_lookup(), which calls the same kernel lookup and pays the same cost.

Sources:

Scroll to Top