The preference attribute in bird

In the bird routing daemon there is a hidden attribute: the preference attribute preference. “Hidden” because it is quite poorly documented. The documentation mentions it, but does not go into detail about how to use it, nor what the default values of this attribute are. Depending on how well you read through the documentation, reading this attribute can also be somewhat hidden.

What is the preference attribute and what is it used for?

The preference attribute is used for route selection. It is evaluated before the protocol-specific criteria (for example, metric for Babel, AS path length, and BGP Local Pref for BGP). The route with the highest preference is preferred. If there are two routes with the same preference, the protocol-specific selection procedure is used accordingly.

What is the default value?

In order to be able to manipulate routes with these preferences, it is useful to know their default values, but there is currently nothing about this in the documentation. However, you can quickly find the preferences in the source code. It can be found in line 748 to line 755 in the file nest/route.h.

The following are the default values:

Protocol Preference Note
Direct 240 Routes, from interfaces that are directly connected
Static 200 Static configured routes
OSPF 150 IGP; for OSPF intra-area, inter-area and type 1 external routes
Babel 130 IGP
RPKI 100  
“Inherited” 10 Routes inherited from other routing daemons

How to read it out?

Unless you have edited the preference attribute in the import filter, you can see it in the detailed log view:

$ birdc show protocol all kioubit
BIRD 2.0.12 ready.
Name       Proto      Table      State  Since         Info
kioubit    BGP        ---        up     2023-06-11    Established   
  BGP state:          Established
    Local capabilities
        AF announced: ipv6
    Neighbor capabilities
        AF announced: ipv4 ipv6
  Channel ipv6
    State:          UP
    Table:          dn42
    Preference:     100
    Input filter:   (unnamed)
    Output filter:  (unnamed)

With the line Preference: 100 you can see that all imported IPv6 routes from this protocol (if not manipulated in the filter) get a preference of 100.

If you want to read the preference not for a protocol but for a specific route, you can easily do this by reading the value in round brackets:

$ birdc show route protocol kioubit | head
BIRD 2.0.12 ready.
Table dn42:
fda7:3ae7:e04d::/48  unicast [kioubit 2023-06-11] (100) [AS4242422596i]
    via fe80::ade0 on kioubit
fd23:0:0:f00d::/64   unicast [kioubit 2023-06-11] (100) [AS4242422037i]
    via fe80::ade0 on kioubit
fd66:dca7:46f3::/48  unicast [kioubit 01:32:34.600] (100) [AS4242423772i]
    via fe80::ade0 on kioubit
fd5b:d2c1:2ecc::/48  unicast [kioubit 2023-06-11] (100) [AS4242421832i]
    via fe80::ade0 on kioubit

For example, here you can see that all four routes have a preference of 100.

When should you change the preference attribute?

The actual preference attributes are quite well chosen, but if you have special cases like mixing the protocols, it can make sense to change the preference - for example, if you want to talk BGP to some people and Babel to others as EGP and also have a Babel for IGP itself, the EGP Babel routes should of course have the same preference as the BGP routes and only the IGP Babel routes should be preferred.

How to change the preference attribute?

This is quite simple by setting the preference in the import filter accordingly:

filter egp_babel_import {
    preference = 100;

This code is based on the example above.

It should be said that one should not simply use Babel and BGP as EGP and mix them without informing oneself accordingly in advance. However, this is a real example from the CRXN/dn42 interconnection.


Since the topic is a bit obscure for me as well, I have rewritten the blog entry after new information from the mailing list. You can see the postings on the mailing list in the archive.