Review my BGP configuration
Hello I have just put my first bird router up in production. Everything is working fine, but I wonder if there are any modifications that I can do to my configuration to optimize it and/or adhere best practicess. My prefix is, in the configuration bellow, a.b.0.0/23, but I want to export it as two separate /24 prefixes, a.b.0.0/24 and a.b.1.0/24. Aditional information: Router ID: x.y.z.w Local AS: 1234 Neighbor ID: w.z.y.x Neighbor AS: 4321 The neighbor router is not directly connected to my router, so I'm using multihop. The part that is bugging me about this configuration is the need for a kernel protocol black list filter. Is there a cleaner way to do this? Bellow is my bird.conf: # Protocol kernel: the black list is so that the routes for # the two /24 reject routes from the static protocol are not # added to the kernel routing table. This kinda smells fishy. # Is there a way around this? filter kernel_filter prefix set KERNEL_BLACKLIST; { KERNEL_BLACKLIST = [ a.b.0.0/24, a.b.1.0/24 ]; if net ~ KERNEL_BLACKLIST then { reject; } accept; } protocol kernel { scan time 20; export filter kernel_filter; } protocol device { scan time 10; } # Prefixes to be exported to BGP, plus a route to the BGP neighbor: protocol static mynetwork { route a.b.0.0/24 reject; route a.b.1.0/24 reject; route w.z.y.x/32 via w.z.y.1; } # The file below contains a single definition: define BGP_MED=200. # This is used when, due to failover, the iBGP peer becomes the # preferred router. A script is executed changing the MED value to # 100 and bird is reloaded. The iBGP peer (which has MED 100) will # analogously be modified to 200, and thus become the preferred # router from my provider's router's point of view. include "/etc/bird-med.conf" # BGP export filter: export my prefixes. filter ebgp_out prefix set EXPORT_WHITELIST; { EXPORT_WHITELIST = [ a.b.c.0/23, a.b.c.0/24, a.b.c.1/24 ]; if net ~ EXPORT_WHITELIST then { bgp_med = BGP_MED; accept; } reject; } # BGP import filters: reject RFC1918 stuff. filter ebgp_in prefix set IMPORT_BLACKLIST; { IMPORT_BLACKLIST = [...]; if net ~ IMPORT_BLACKLIST then { printn "Discarding received route to "; print net; reject; } accept; } # # BGP sessions # protocol bgp eBGP { description "eBGP"; local as 1234; source address x.y.z.w; neighbor w.z.y.x as 4321; multihop 2; default bgp_local_pref 200; export filter ebgp_out; import filter ebgp_in; } protocol bgp iBGP { description "iBGP"; local as 1234; source address x.y.z.w; neighbor x.y.z.k as 262672; next hop self; gateway direct; default bgp_local_pref 100; } Thanks in advance, Andre
Hi Andre, On 03/02/2013 10:40 PM, Andre Nathan wrote:
I have just put my first bird router up in production. Everything is working fine, but I wonder if there are any modifications that I can do to my configuration to optimize it and/or adhere best practicess.
Congratulations! :)
My prefix is, in the configuration bellow, a.b.0.0/23, but I want to export it as two separate /24 prefixes, a.b.0.0/24 and a.b.1.0/24.
[...]
The part that is bugging me about this configuration is the need for a kernel protocol black list filter. Is there a cleaner way to do this?
In this case, you can take advantage of the fact that you can create as many internal extra routing tables in bird for your own administration as you like, eliminating the 'bugging' extra filters you need when putting all in a single table. Using 'pipe' protocols you can import/export routes between the custom defined tables. As an example, here's how I'm doing this, adjusted to your config: +--------+ | master | +--------+ ^ | | | p_bgp_to_master | v +--------+ ---> | t_bgp | <--- iBGP +--------+ ^ | | | p_wzyx_to_bgp | v +--------+ ---> | t_wzyx | <--- eBGP to wzyx +--------+ ^ | originate_to_wzyx | bgp routes we want to announce The extra route tables used here are a table per eBGP peer, in which we can keep a 'local' administration of what happens to/from this peer, and a t_bgp table, in which all external learned bgp routes are imported, and which can be used to export those routes to iBGP peers so they know where to go outside of our local network. Here's a diff on your config which implements this: --- bird-nathan.orig 2013-03-02 23:47:08.963808563 +0100 +++ bird-nathan 2013-03-03 00:12:03.128925412 +0100 @@ -1,36 +1,30 @@ -# Protocol kernel: the black list is so that the routes for -# the two /24 reject routes from the static protocol are not -# added to the kernel routing table. This kinda smells fishy. -# Is there a way around this? -filter kernel_filter -prefix set KERNEL_BLACKLIST; -{ - KERNEL_BLACKLIST = [ - a.b.0.0/24, - a.b.1.0/24 - ]; - if net ~ KERNEL_BLACKLIST then { - reject; - } - accept; -} - protocol kernel { scan time 20; - export filter kernel_filter; + export all; } protocol device { scan time 10; } -# Prefixes to be exported to BGP, plus a route to the BGP neighbor: +# A route to the BGP neighbor: protocol static mynetwork { - route a.b.0.0/24 reject; - route a.b.1.0/24 reject; route w.z.y.x/32 via w.z.y.1; } +# Use this routing table to gather external routes received via BGP +# which we want to push to the kernel via our master table and to +# other routers in our AS via iBGP or even to other routers outside +# our AS again (transit), which can be connected here or to a router +# elsewhere on the border of our AS. +table t_bgp; + +protocol pipe p_master_to_bgp { + table master; + peer table t_bgp; + import all; # default + export none; # default +} + # The file below contains a single definition: define BGP_MED=200. # This is used when, due to failover, the iBGP peer becomes the # preferred router. A script is executed changing the MED value to @@ -72,7 +66,21 @@ # BGP sessions # +# simply create an extra internal routing table per external peer, +# which helps keeping the route administration separate from the +# master table. e.g. injecting routes we want to originate to an eBGP +# peer happens here +table t_wzyx; + +protocol static originate_to_wzyx { + table t_wzyx; + import all; # originate here + route a.b.0.0/24 reject; + route a.b.1.0/24 reject; +} + protocol bgp eBGP { + table t_wzyx; + igp table master; description "eBGP"; local as 1234; source address x.y.z.w; @@ -82,7 +90,18 @@ export filter ebgp_out; import filter ebgp_in; } + +protocol pipe p_bgp_to_wzyx { + table t_bgp; + peer table t_wzyx; + # put all learned routes into central bgp table + import where proto = "eBGP"; + export none; # no transit please +} + protocol bgp iBGP { + table t_bgp; + igp table master; description "iBGP"; local as 1234; source address x.y.z.w; @@ -90,4 +109,7 @@ next hop self; gateway direct; default bgp_local_pref 100; + # share all bgp routes with our ibgp peer + import all; + export all; } This approach is similar to the example of a route server in the bird examples section, in fact it's where I got the ideas to do this: https://redmine.labs.nic.cz/projects/bird/wiki/Route_server_with_community_b... Defining transit is as simple as re-exporting routes that were learned from eBGP peer X from the t_bgp table to the dedicated table for peer y again. :) -- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
Hi Hans On Sun, 03 Mar 2013, Hans van Kranenburg wrote:
In this case, you can take advantage of the fact that you can create as many internal extra routing tables in bird for your own administration as you like, eliminating the 'bugging' extra filters you need when putting all in a single table. Using 'pipe' protocols you can import/export routes between the custom defined tables.
I'll have to study your suggested configuration and the pipe protocol before trying to apply it in production, but it sure looks nice :) Earlier today I had the following idea. Instead of specifying all static routes in the same protocol, as I did before, couldn't I define two instances and then filter based on the protocol name? # Prefixes to be exported to BGP procol static mynetworks { route a.b.c.0/24; route a.b.c.1/24; } # Route to the BGP peer protocol static bgp_peer_route { route w.z.y.x/32 via w.z.y.1; } protocol kernel { scan time 20; export where proto = "bgp_peer_route"; } This should work, right? Thanks a lot, Andre
On 03/04/2013 06:19 PM, Andre Nathan wrote:
# Prefixes to be exported to BGP procol static mynetworks { route a.b.c.0/24; route a.b.c.1/24; }
# Route to the BGP peer protocol static bgp_peer_route { route w.z.y.x/32 via w.z.y.1; }
protocol kernel { scan time 20; export where proto = "bgp_peer_route"; }
This should work, right?
Yes, it's almost the opposite way of doing the same: What do you want to happen when x.y.z.w loses its connection to the outside world? (i.e. bgp to w.z.y.x goes down) You might have learned an alternative route to the outside world from your iBGP peer, but you're not making it active in the os kernel now. -- Hans van Kranenburg - System / Network Engineer +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
On 03/04/2013 07:09 PM, Hans van Kranenburg wrote:
On 03/04/2013 06:19 PM, Andre Nathan wrote:
# Prefixes to be exported to BGP procol static mynetworks { route a.b.c.0/24; route a.b.c.1/24; }
# Route to the BGP peer protocol static bgp_peer_route { route w.z.y.x/32 via w.z.y.1; }
protocol kernel { scan time 20; export where proto = "bgp_peer_route"; }
This should work, right?
Yes, it's almost the opposite way of doing the same: What do you want to happen when x.y.z.w loses its connection to the outside world? (i.e. bgp to w.z.y.x goes down) You might have learned an alternative route to the outside world from your iBGP peer, but you're not making it active in the os kernel now.
Oh, I was reading a bit too quick. When you only export proto = "bgp_peer_route", you're not doing anything with any route that bird learns from your bgp peers, is that what you want? -- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
On Mon, 04 Mar 2013, Hans van Kranenburg wrote:
Oh, I was reading a bit too quick. When you only export proto = "bgp_peer_route", you're not doing anything with any route that bird learns from your bgp peers, is that what you want?
No, my idea is indeed wrong. I was trying to eliminate the kernel black list from my original configuration but this, as you said, would avoid any routes coming from BGP to be sent to the kernel. Thanks, Andre
Hi again, Hans I tried your suggested configuration. It worked almost perfectly, but I had one problem. My router's network interfaces are configured as follows: eth0: interface connected to a.b.0.0/23 network eth1: interface for eBGP and iBGP sessions What happened was that my IP block is a.b.0.0/23, and therefore my router has an IP address with a /23 netmask in eth0 (say, a.b.0.1/23). However, I export two /24 blocks, a.b.0.0/24 and a.b.0.1/24. The router learns these routes from the iBGP session, and since they are more specific than the eth0 interface route, they'll be preferred when compared to the eth0 interface route. So I ended up with a route to the /23 via eth0 and two routes to the /24 blocks via eth1, with the iBGP peer as the gateway. My first thought is that I need another static protocol block in my configuration: protocol static { route a.b.0.0/24 via "eth0"; route a.b.0.1/24 via "eth0"; } Is that a solution to this situation? What's weird to me is that my other router (the iBGP peer of the Bird router) is still running Quagga, and it learns the same two /24 routes via iBGP but does not add them to the kernel routing table. I'm wondering if Quagga is doing some kind of filtering here behind the scenes that isn't done by default in Bird... Thanks, Andre
On Wed, 06 Mar 2013, Andre Nathan wrote:
Is that a solution to this situation? What's weird to me is that my other router (the iBGP peer of the Bird router) is still running Quagga, and it learns the same two /24 routes via iBGP but does not add them to the kernel routing table. I'm wondering if Quagga is doing some kind of filtering here behind the scenes that isn't done by default in Bird...
Actually I mispoke here. Quagga detects the /24 blocks as local and doesn't seem to learn them from iBGP: # show ip bgp ... Network Next Hop Metric LocPrf Weight Path ... *> a.b.0.0/24 0.0.0.0 0 32768 i *> a.b.0.1/24 0.0.0.0 0 32768 i ... # show ip bgp a.b.0.0/24 BGP routing table entry for a.b.0.0/24 Paths: (1 available, best #1, table Default-IP-Routing-Table) Advertised to non peer-group peers: w.z.y.x x.y.z.1 Local 0.0.0.0 from 0.0.0.0 (x.y.z.2) Origin IGP, metric 0, localpref 100, weight 32768, valid, sourced, local, best Last update: Sat Mar 2 17:18:25 2013 BGP routing table entry for a.b.1.0/24 Paths: (1 available, best #1, table Default-IP-Routing-Table) Advertised to non peer-group peers: w.z.y.x x.y.z.1 Local 0.0.0.0 from 0.0.0.0 (x.y.z.2) Origin IGP, metric 0, localpref 100, weight 32768, valid, sourced, local, best Last update: Sat Mar 2 17:18:25 2013 However, just as in the Bird configuration, I have no filters configured in the iBGP session, so I don't understand why Bird added the two /24 iBGP routes to the kernel routing table, while Quagga didn't. Thanks again, Andre
On 03/06/2013 02:28 PM, Andre Nathan wrote:
My router's network interfaces are configured as follows:
eth0: interface connected to a.b.0.0/23 network eth1: interface for eBGP and iBGP sessions
What happened was that my IP block is a.b.0.0/23, and therefore my router has an IP address with a /23 netmask in eth0 (say, a.b.0.1/23). However, I export two /24 blocks, a.b.0.0/24 and a.b.0.1/24.
I assume you mean to say a.b.1.0/24 instead of a.b.0.1/24?
The router learns these routes from the iBGP session, and since they are more specific than the eth0 interface route, they'll be preferred when compared to the eth0 interface route.
If there a specific need for advertising the routes you want to send to your eBGP peer also via iBGP?
So I ended up with a route to the /23 via eth0 and two routes to the /24 blocks via eth1, with the iBGP peer as the gateway.
I think you do not want to put the /24 routes in iBGP, because if you'd do that on both sides, you'd be creating a loop, because afaik traffic will bounce between them indefinitely and never reach the network on eth0. :)
My first thought is that I need another static protocol block in my configuration:
protocol static { route a.b.0.0/24 via "eth0"; route a.b.0.1/24 via "eth0"; }
Is that a solution to this situation? What's weird to me is that my other router (the iBGP peer of the Bird router) is still running Quagga, and it learns the same two /24 routes via iBGP but does not add them to the kernel routing table. I'm wondering if Quagga is doing some kind of filtering here behind the scenes that isn't done by default in Bird...
I'd suggest only using the /24 routes when talking to the peers outside your network, and use iBGP to only distribute information about routes originating from outside your AS. -- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
Hi Hans On Wed, 06 Mar 2013, Hans van Kranenburg wrote:
I assume you mean to say a.b.1.0/24 instead of a.b.0.1/24?
Yes, sorry.
If there a specific need for advertising the routes you want to send to your eBGP peer also via iBGP?
There's no need to send them via iBGP, but since the iBGP session learns from the central BGP table (t_bgp), it ends up learning them. Is the best solution to create an import filter in the iBGP session, ignoring those prefixes? I was wondering about the behavior difference vs Quagga, where I don't have any iBGP filters but those routes are not learned in the iBGP session. Could this be a consequence of using "gateway direct;" in the iBGP session? Thanks a lot, Andre
On 03/07/2013 01:58 PM, Andre Nathan wrote:
On Wed, 06 Mar 2013, Hans van Kranenburg wrote:
If there a specific need for advertising the routes you want to send to your eBGP peer also via iBGP?
There's no need to send them via iBGP, but since the iBGP session learns from the central BGP table (t_bgp), it ends up learning them.
And how do they end up in your t_bgp table? Via p_bgp_to_wzyx pipe, or learned from quagga via iBGP?
Is the best solution to create an import filter in the iBGP session, ignoring those prefixes? I was wondering about the behavior difference vs Quagga, where I don't have any iBGP filters but those routes are not learned in the iBGP session.
I don't know exactly about quagga, I do know I got very frustrated with it and switched to bird. :)
Could this be a consequence of using "gateway direct;" in the iBGP session?
I don't think so. -- Hans van Kranenburg - System / Network Engineer +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
On Fri, 08 Mar 2013, Hans van Kranenburg wrote:
And how do they end up in your t_bgp table? Via p_bgp_to_wzyx pipe, or learned from quagga via iBGP?
The come from quagga via iBGP: bird> show route for a.b.0.0/24 table t_bgp a.b.0.0/24 via x.y.z.2 on eth1 [iBGP Mar05] * (100) [i] bird> show route for a.b.1.0/24 table t_bgp a.b.1.0/24 via x.y.z.2 on eth1 [iBGP Mar05] * (100) [i] From the p_bgp_to_wzyx pipe I get this (as expected): bird> show route for a.b.0.0/24 table t_wzyx a.b.0.0/24 unreachable [originate_to_wzyx Mar05] * (200) bird> show route for a.b.1.0/24 table t_wzyx a.b.1.0/24 unreachable [originate_to_wzyx Mar05] * (200)
I don't know exactly about quagga, I do know I got very frustrated with it and switched to bird. :)
Tell me about it :) That's why I'm switching to bird. But I want to get everything right in the first router before reinstalling the second one. Thanks, Andre
On 03/08/2013 12:43 PM, Andre Nathan wrote:
On Fri, 08 Mar 2013, Hans van Kranenburg wrote:
And how do they end up in your t_bgp table? Via p_bgp_to_wzyx pipe, or learned from quagga via iBGP?
The come from quagga via iBGP:
bird> show route for a.b.0.0/24 table t_bgp a.b.0.0/24 via x.y.z.2 on eth1 [iBGP Mar05] * (100) [i] bird> show route for a.b.1.0/24 table t_bgp a.b.1.0/24 via x.y.z.2 on eth1 [iBGP Mar05] * (100) [i]
From the p_bgp_to_wzyx pipe I get this (as expected):
bird> show route for a.b.0.0/24 table t_wzyx a.b.0.0/24 unreachable [originate_to_wzyx Mar05] * (200) bird> show route for a.b.1.0/24 table t_wzyx a.b.1.0/24 unreachable [originate_to_wzyx Mar05] * (200)
Ok, well I think it's best then not to try fix quagga, but create a temporary import filter that only allows what you want to accept.
I don't know exactly about quagga, I do know I got very frustrated with it and switched to bird. :)
Tell me about it :) That's why I'm switching to bird. But I want to get everything right in the first router before reinstalling the second one.
-- Hans van Kranenburg - System / Network Engineer +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
On Fri, 08 Mar 2013, Hans van Kranenburg wrote:
Ok, well I think it's best then not to try fix quagga, but create a temporary import filter that only allows what you want to accept.
Oh, I see. When I migrate the other router to Bird, the /24 prefixes will be exported with the "reject" option and therefore not be added to the kernel routing table, so no filter will be needed then. Thanks! Andre
On 03/08/2013 01:41 PM, Andre Nathan wrote:
On Fri, 08 Mar 2013, Hans van Kranenburg wrote:
Ok, well I think it's best then not to try fix quagga, but create a temporary import filter that only allows what you want to accept.
Oh, I see. When I migrate the other router to Bird, the /24 prefixes will be exported with the "reject" option and therefore not be added to the kernel routing table, so no filter will be needed then.
When converting the other router to bird, you can also configure it to just use the /24 ranges in the context of talking to the ebgp peer, and never let them come near the t_bgp or even master table, so you don't need the additional filters to keep them out again. Why would a route with target 'reject' not be added to the kernel table if you export the route to it? -- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
On Fri, 08 Mar 2013, Hans van Kranenburg wrote:
When converting the other router to bird, you can also configure it to just use the /24 ranges in the context of talking to the ebgp peer, and never let them come near the t_bgp or even master table, so you don't need the additional filters to keep them out again.
Borrowing your routing table scheme from your first reply: +--------+ | master | +--------+ ^ | | | p_bgp_to_master | v +--------+ ---> | t_bgp | <--- iBGP +--------+ ^ | | | p_wzyx_to_bgp | v +--------+ ---> | t_wzyx | <--- eBGP to wzyx +--------+ ^ | originate_to_wzyx | bgp routes we want to announce In the eBGP session I have an input filter that rejects routes matching my /24. What happens here is that despite the filter, those routes still end up being added to t_bgp because they were added to t_wzyx via originate_to_wzyx. Is that correct? If so, the solution is see is to change p_wzyx_to_bgp so that instead of 'import where proto = "eBGP"' a more complex filter is used, something like if proto = "eBGP" && ! (net ~ [a.b.0.0/24, a.b.1.0/24]) then { accept; } reject; Looks good?
Why would a route with target 'reject' not be added to the kernel table if you export the route to it?
Please ignore that, it was a brain malfunction. Thank you, Andre
On 03/08/2013 07:28 PM, Andre Nathan wrote:
On Fri, 08 Mar 2013, Hans van Kranenburg wrote:
When converting the other router to bird, you can also configure it to just use the /24 ranges in the context of talking to the ebgp peer, and never let them come near the t_bgp or even master table, so you don't need the additional filters to keep them out again.
Borrowing your routing table scheme from your first reply:
Whoops, the drawing does not entirely match the config, p_bgp_to_master should be p_master_to_bgp and p_wzyx_to_bgp should be p_bgp_to_wxyz, like in the diff I sent in the first post. This does not alter any of the behaviour by the way. So: kernel ^ : | : | v +--------+ | master | +--------+ ^ : | : p_master_to_bgp | v ,---> +--------+ | ,-- | t_bgp | ---------------------. | : +--------+ <-----------------. | | : ^ : | v | : | : p_bgp_to_wxyz iBGP peers | v | v +--------+ +--------+ | t_uiop | | t_wzyx | - - - - - -. +--------+ +--------+ <--------. | ^ | ^ | | v | | | | originate_to_wzyx | v | v eBGP peers Arrows pointing up then mean import (pointing closer to bird), and pointing down mean export (further away from bird).
In the eBGP session I have an input filter that rejects routes matching my /24.
That's a filter for sanity purposes I guess, an eBGP peer should never send you your own routes?
What happens here is that despite the filter, those routes still end up being added to t_bgp because they were added to t_wzyx via originate_to_wzyx. Is that correct?
No, because if you do import where proto = "eBGP" only the routes that were learned in protocol bgp eBGP would match. the /24's would match when you say where proto = "originate_to_wzyx" Using the commands in the interactive console, birdc, you could try to debug what's going on exactly, and where those routes come from... show route all table t_wzyx and... show route protocol eBGP table t_wzyx (imported routes) show route export eBGP table t_wzyx (exported routes) etc...
If so, the solution is see is to change p_wzyx_to_bgp so that instead of 'import where proto = "eBGP"' a more complex filter is used, something like
if proto = "eBGP" && ! (net ~ [a.b.0.0/24, a.b.1.0/24]) then { accept; } reject;
Looks good?
-- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
On 03/08/2013 09:25 PM, Hans van Kranenburg wrote:
So:
kernel ^ : | : | v +--------+ | master | +--------+ ^ : | : p_master_to_bgp | v ,---> +--------+ | ,-- | t_bgp | ---------------------. | : +--------+ <-----------------. | | : ^ : | v | : | : p_bgp_to_wxyz iBGP peers | v | v +--------+ +--------+ | t_uiop | | t_wzyx | - - - - - -. +--------+ +--------+ <--------. | ^ | ^ | | v | | | | originate_to_wzyx | v | v
eBGP peers
Arrows pointing up then mean import (pointing closer to bird), and pointing down mean export (further away from bird).
Meh, except for the kernel arrows, of course... :| -- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
Hello Hans Sorry for the delay to reply you message. I figured it was best to just reinstall the second router with Bird and get Quagga out of the scenario, and now all is working fine, and the routes to my two /24 prefixes are not being added to the t_bgp table. There's just one weird thing I'm seeing in the logs: configuration error: tried to export prefix w.z.y.x/32 configuration error: tried to export prefix 77.74.252.0/22 ... The first line is the address of my eBGP peer, and there are a handful of lines like the second one for prefixes that don't show up anywhere in my configuration. The log message comes from a sanity-check export filter that I created which only allows me to export my own prefixes. I tried to simplify your drawing from your last message, removing all the arrows where there's no route flow in the pipes: filter proto = +--------+ +-------+ "wzyx" +--------+ kernel <-> | master | <- | t_bgp | <----- | t_wzyx | <- export_to_wzyx +--------+ +-------+ +--------+ ^ | ^ | | | filter | | filter | | wzyx_in | | wzyx_out | v | v iBGP wzyx eBGP session session From that I can't see how the static route to w.z.y.x/32 would ever reach filter wzyx_out, which is where the log message comes from... and neither do I understand how the other routes reach that filter (and why only a handful of routes...?) bird> show route for w.z.y.x/32 all w.z.y.x/32 via w.z.y.1 on eth1 [wzyx_bgp_neighbor Mar14] * (200) Type: static unicast univ bird> show route for 77.74.252.0/22 all 77.74.248.0/21 via w.z.y.1 on eth1 [wzyx 04:56 from w.z.y.x] * (100) [AS42860i] Type: BGP unicast univ BGP.origin: IGP BGP.as_path: 4321 7162 3549 31042 42860 BGP.next_hop: w.z.y.x BGP.local_pref: 200 via x.y.z.k on eth1 [iBGP 04:57] (100) [AS42860i] Type: BGP unicast univ BGP.origin: IGP BGP.as_path: 4321 7162 3549 31042 42860 BGP.next_hop: x.y.z.k BGP.local_pref: 200 I'm pasting the new configuration below just in case. log syslog { info, warning, error, auth, fatal, bug }; router id x.y.z.w; # The order in which the files are loaded is important. # This table contains routes learnt via BGP. table t_bgp; # Send routes learnt via BGP to the kernel through the master table. protocol pipe bgp_into_master { table master; peer table t_bgp; import all; # from table t_bgp into table master export none; # from table master into table t_bgp } include "/etc/bird-med.conf"; # # wzyx BGP session # # Static route to wzyx's router. protocol static wzyx_bgp_neighbor { route w.z.y.x/32 via w.z.y.1; } # This table contains routes exported to and imported from wzyx. table t_wzyx; # Prefixes we want to export to wzyx. protocol static export_to_wzyx { table t_wzyx; route a.b.0.0/24 reject; route a.b.1.0/24 reject; route a.b.0.0/23 reject; import all; # send routes to table t_wzyx. } # Import filters. filter wzyx_in prefix set my_prefixes; { my_prefixes = [ a.b.0.0/23+, ]; if net ~ my_prefixes then accept; reject "prefix cannot be imported"; } # Export filters. filter wzyx_out prefix set my_prefixes; { my_prefixes = [ a.b.0.0/24, a.b.1.0/24, a.b.0.0/23 ]; if net ~ my_prefixes then { bgp_med = BGP_MED; # defined in bird-med.conf accept; } printn "configuration error: tried to export prefix "; print net; reject; } # The BGP session. protocol bgp wzyx { description "wzyx"; table t_wzyx; igp table master; local as 1234; source address x.y.z.w; neighbor w.z.y.x as 4321; multihop 2; default bgp_local_pref 200; import filter wzyx_in; export filter wzyx_out; } # Send all routes learnt in the BGP session above to the central bgp table. protocol pipe wzyx_into_bgp { table t_bgp; peer table t_wzyx; import where proto = "wzyx"; export none; } # # iBGP session # protocol bgp iBGP { description "iBGP"; table t_bgp; igp table master; local as 1234; source address x.y.z.w; neighbor x.y.z.k as 1234; next hop self; gateway direct; default bgp_local_pref 100; import all; export all; } protocol kernel { export all; scan time 20; } protocol device { scan time 10; } Thanks again, Andre
Hi Andre, On 03/15/2013 04:37 PM, Andre Nathan wrote:
Sorry for the delay to reply you message. I figured it was best to just reinstall the second router with Bird and get Quagga out of the scenario, and now all is working fine, and the routes to my two /24 prefixes are not being added to the t_bgp table.
Yay!
There's just one weird thing I'm seeing in the logs:
configuration error: tried to export prefix w.z.y.x/32 configuration error: tried to export prefix 77.74.252.0/22 ...
Cool, I didn't use print statements yet myself, but this shows they're very useful for detection of spurious route announcements, misconfiguration etc. With custom messages this is easy to detect in the logs.
The first line is the address of my eBGP peer, and there are a handful of lines like the second one for prefixes that don't show up anywhere in my configuration.
The log message comes from a sanity-check export filter that I created which only allows me to export my own prefixes.
I tried to simplify your drawing from your last message, removing all the arrows where there's no route flow in the pipes:
filter proto = +--------+ +-------+ "wzyx" +--------+ kernel <-> | master | <- | t_bgp | <----- | t_wzyx | <- export_to_wzyx +--------+ +-------+ +--------+ ^ | ^ | | | filter | | filter | | wzyx_in | | wzyx_out | v | v iBGP wzyx eBGP session session
Yes!
From that I can't see how the static route to w.z.y.x/32 would ever reach filter wzyx_out, which is where the log message comes from...
I second that.
and neither do I understand how the other routes reach that filter (and why only a handful of routes...?)
Well...
bird> show route for w.z.y.x/32 all w.z.y.x/32 via w.z.y.1 on eth1 [wzyx_bgp_neighbor Mar14] * (200) Type: static unicast univ
This one says it's coming from 'wzyx_bgp_neighbor'. It does not say to which table the route did make it. What does e.g. show route table t_wzyx show route all table t_wzyx show route export bgp_wzyx table t_wzyx show route preexport bgp_wzyx table t_wzyx say?
bird> show route for 77.74.252.0/22 all 77.74.248.0/21 via w.z.y.1 on eth1 [wzyx 04:56 from w.z.y.x] * (100) [AS42860i] Type: BGP unicast univ BGP.origin: IGP BGP.as_path: 4321 7162 3549 31042 42860 BGP.next_hop: w.z.y.x BGP.local_pref: 200 via x.y.z.k on eth1 [iBGP 04:57] (100) [AS42860i] Type: BGP unicast univ BGP.origin: IGP BGP.as_path: 4321 7162 3549 31042 42860 BGP.next_hop: x.y.z.k BGP.local_pref: 200
This looks like an external route that was learned from wzyx by you and by the other bird, who provides you with a backup-path, when your own eBGP session might go down. But, aha... hold on.
I'm pasting the new configuration below just in case.
log syslog { info, warning, error, auth, fatal, bug };
I'm using debug protocols { states, routes, filters, interfaces } here. I don't know if it shows the same information as your log settings, but for me, it shows just enough detailed information I'm interested in, especially about which routes go where. This might appear in your syslog file: bird: bgp_example > added [best] 10.1.0.0/19 via 10.1.19.37 on example bird: bgp_example < rejected by protocol 10.10.0.0/19 via 10.1.19.37 on example because... protocol bgp bgp_example { table t_example; import all; export all; [...] } What happens here is that bird itself understands that it's useless to echo routes back the same way they came from in the same protocol definition. That implicit behaviour is quite useful, so we don't have to write nonsense filters. Another example is filtering of routes that are learned from an iBGP peer to another iBGP peer, which is never done, regardless of your configuration. What I expect you're seeing here is your print statement gets run *before* bird itself would filter the route. Maybe someone else can comment on this, if I'm right here, or not. I didn't build a test setup to validate this, but it sounds like an explanation for what you see.
router id x.y.z.w;
I've looked at your config over and over again, but I cannot see any way in it how the /32 route from static wzyx_bgp_neighbor would end up in table t_wzyx. Nice and clear config by the way. -- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
Hi Hans On Sat, 16 Mar 2013, Hans van Kranenburg wrote:
There's just one weird thing I'm seeing in the logs:
configuration error: tried to export prefix w.z.y.x/32 configuration error: tried to export prefix 77.74.252.0/22 ...
Cool, I didn't use print statements yet myself, but this shows they're very useful for detection of spurious route announcements, misconfiguration etc. With custom messages this is easy to detect in the logs.
So, I scheduled a full restart of bird on both routers this weekend, and this time the "configuration error" messages didn't show up. I guess after a number of "configure soft" commands that I did until I finally finished the configuration, my routing tables weren't in the state they were supposed to be. Anyway, a clean restart solved the issue :) Thanks for all your help with this. Best, Andre
Hi, On 03/25/2013 02:35 PM, Andre Nathan wrote:
On Sat, 16 Mar 2013, Hans van Kranenburg wrote:
There's just one weird thing I'm seeing in the logs:
configuration error: tried to export prefix w.z.y.x/32 configuration error: tried to export prefix 77.74.252.0/22 ...
Cool, I didn't use print statements yet myself, but this shows they're very useful for detection of spurious route announcements, misconfiguration etc. With custom messages this is easy to detect in the logs.
So, I scheduled a full restart of bird on both routers this weekend, and this time the "configuration error" messages didn't show up. I guess after a number of "configure soft" commands that I did until I finally finished the configuration, my routing tables weren't in the state they were supposed to be.
Ah, that sounds like a plausible cause of the behaviour yes. Bird does a lot of effort to find out how configuration changed and adapt to it, which is an awesome feature, but especially when using soft, it tries to do its best, but will not re-evaluate changed filters to remove routes.
Anyway, a clean restart solved the issue :)
Great! Happy to hear that. -- Hans van Kranenburg - System / Network Engineer T +31 (0)10 2760434 | hans.van.kranenburg@mendix.com | www.mendix.com
On Sat, Mar 02, 2013 at 06:40:05PM -0300, Andre Nathan wrote:
The part that is bugging me about this configuration is the need for a kernel protocol black list filter. Is there a cleaner way to do this?
Bellow is my bird.conf:
# Protocol kernel: the black list is so that the routes for # the two /24 reject routes from the static protocol are not # added to the kernel routing table. This kinda smells fishy. # Is there a way around this?
Well, you already use reject/unreachable for these two routes so i don't see the reason to filter these routes out. I would just export it to the kernel, assuming that there are more specific routes to handle real traffic. If you use default route, it has additional advantages that traffic to your unhandled IPs does not ping-pong between you and your uplink. -- Elen sila lumenn' omentielvo Ondrej 'SanTiago' Zajicek (email: santiago@crfreenet.org) OpenPGP encrypted e-mails preferred (KeyID 0x11DEADC3, wwwkeys.pgp.net) "To err is human -- to blame it on a computer is even more so."
Hi Ondrej On Sun, 03 Mar 2013, Ondrej Zajicek wrote:
Well, you already use reject/unreachable for these two routes so i don't see the reason to filter these routes out. I would just export it to the kernel, assuming that there are more specific routes to handle real traffic.
In my case the existing route has a /23 netmask, so I ended up with two /24 reject routes (shown with a "!" by the route command), which blocked all traffic into my AS. Thanks, Andre
participants (3)
-
Andre Nathan -
Hans van Kranenburg -
Ondrej Zajicek