1 // SPDX-License-Identifier: MIT
3 Copyright 2011 by Matthieu Boutier and Juliusz Chroboczek
11 #include "distribute.h"
15 #include "lib_errors.h"
19 #include "babel_main.h"
24 #include "babel_interface.h"
25 #include "neighbour.h"
29 #include "babel_filter.h"
30 #include "babel_zebra.h"
31 #include "babel_errors.h"
33 #ifndef VTYSH_EXTRACT_PL
34 #include "babeld/babeld_clippy.c"
37 DEFINE_MGROUP(BABELD
, "babeld");
38 DEFINE_MTYPE_STATIC(BABELD
, BABEL
, "Babel Structure");
40 static void babel_init_routing_process(struct thread
*thread
);
41 static void babel_get_myid(void);
42 static void babel_initial_noise(void);
43 static void babel_read_protocol(struct thread
*thread
);
44 static void babel_main_loop(struct thread
*thread
);
45 static void babel_set_timer(struct timeval
*timeout
);
46 static void babel_fill_with_next_timeout(struct timeval
*tv
);
48 babel_distribute_update (struct distribute_ctx
*ctx
, struct distribute
*dist
);
50 /* Informations relative to the babel running daemon. */
51 static struct babel
*babel_routing_process
= NULL
;
52 static unsigned char *receive_buffer
= NULL
;
53 static int receive_buffer_size
= 0;
56 struct timeval check_neighbours_timeout
;
57 static time_t expiry_time
;
58 static time_t source_expiry_time
;
60 /* Babel node structure. */
61 static int babel_config_write (struct vty
*vty
);
62 static struct cmd_node cmd_babel_node
=
66 .parent_node
= CONFIG_NODE
,
67 .prompt
= "%s(config-router)# ",
68 .config_write
= babel_config_write
,
71 /* print current babel configuration on vty */
73 babel_config_write (struct vty
*vty
)
79 /* list enabled debug modes */
80 lines
+= debug_babel_config_write (vty
);
82 if (!babel_routing_process
)
84 vty_out (vty
, "router babel\n");
85 if (diversity_kind
!= DIVERSITY_NONE
)
87 vty_out (vty
, " babel diversity\n");
90 if (diversity_factor
!= BABEL_DEFAULT_DIVERSITY_FACTOR
)
92 vty_out (vty
, " babel diversity-factor %d\n",diversity_factor
);
95 if (resend_delay
!= BABEL_DEFAULT_RESEND_DELAY
)
97 vty_out (vty
, " babel resend-delay %u\n", resend_delay
);
100 if (smoothing_half_life
!= BABEL_DEFAULT_SMOOTHING_HALF_LIFE
)
102 vty_out (vty
, " babel smoothing-half-life %u\n",
103 smoothing_half_life
);
106 /* list enabled interfaces */
107 lines
= 1 + babel_enable_if_config_write (vty
);
108 /* list redistributed protocols */
109 for (afi
= AFI_IP
; afi
<= AFI_IP6
; afi
++) {
110 for (i
= 0; i
< ZEBRA_ROUTE_MAX
; i
++) {
111 if (i
!= zclient
->redist_default
&&
112 vrf_bitmap_check (zclient
->redist
[afi
][i
], VRF_DEFAULT
)) {
113 vty_out (vty
, " redistribute %s %s\n",
114 (afi
== AFI_IP
) ? "ipv4" : "ipv6",
115 zebra_route_string(i
));
121 lines
+= config_write_distribute (vty
, babel_routing_process
->distribute_ctx
);
123 vty_out (vty
, "exit\n");
130 babel_create_routing_process (void)
132 assert (babel_routing_process
== NULL
);
134 /* Allocaste Babel instance. */
135 babel_routing_process
= XCALLOC(MTYPE_BABEL
, sizeof(struct babel
));
137 /* Initialize timeouts */
139 expiry_time
= babel_now
.tv_sec
+ roughly(30);
140 source_expiry_time
= babel_now
.tv_sec
+ roughly(300);
142 /* Make socket for Babel protocol. */
143 protocol_socket
= babel_socket(protocol_port
);
144 if (protocol_socket
< 0) {
145 flog_err_sys(EC_LIB_SOCKET
, "Couldn't create link local socket: %s",
146 safe_strerror(errno
));
151 thread_add_read(master
, babel_read_protocol
, NULL
, protocol_socket
, &babel_routing_process
->t_read
);
152 /* wait a little: zebra will announce interfaces, addresses, routes... */
153 thread_add_timer_msec(master
, babel_init_routing_process
, NULL
, 200L, &babel_routing_process
->t_update
);
155 /* Distribute list install. */
156 babel_routing_process
->distribute_ctx
= distribute_list_ctx_create (vrf_lookup_by_id(VRF_DEFAULT
));
157 distribute_list_add_hook (babel_routing_process
->distribute_ctx
, babel_distribute_update
);
158 distribute_list_delete_hook (babel_routing_process
->distribute_ctx
, babel_distribute_update
);
161 XFREE(MTYPE_BABEL
, babel_routing_process
);
165 /* thread reading entries form others babel daemons */
166 static void babel_read_protocol(struct thread
*thread
)
169 struct vrf
*vrf
= vrf_lookup_by_id(VRF_DEFAULT
);
170 struct interface
*ifp
= NULL
;
171 struct sockaddr_in6 sin6
;
173 assert(babel_routing_process
!= NULL
);
174 assert(protocol_socket
>= 0);
176 rc
= babel_recv(protocol_socket
,
177 receive_buffer
, receive_buffer_size
,
178 (struct sockaddr
*)&sin6
, sizeof(sin6
));
180 if(errno
!= EAGAIN
&& errno
!= EINTR
) {
181 flog_err_sys(EC_LIB_SOCKET
, "recv: %s", safe_strerror(errno
));
184 FOR_ALL_INTERFACES(vrf
, ifp
) {
187 if(ifp
->ifindex
== (ifindex_t
)sin6
.sin6_scope_id
) {
188 parse_packet((unsigned char*)&sin6
.sin6_addr
, ifp
,
196 thread_add_read(master
, &babel_read_protocol
, NULL
, protocol_socket
, &babel_routing_process
->t_read
);
199 /* Zebra will give some information, especially about interfaces. This function
200 must be call with a litte timeout wich may give zebra the time to do his job,
201 making these inits have sense. */
202 static void babel_init_routing_process(struct thread
*thread
)
204 myseqno
= (frr_weak_random() & 0xFFFF);
206 babel_load_state_file();
207 debugf(BABEL_DEBUG_COMMON
, "My ID is : %s.", format_eui64(myid
));
208 babel_initial_noise();
209 babel_main_loop(thread
);/* this function self-add to the t_update thread */
212 /* fill "myid" with an unique id (only if myid != {0}). */
216 struct vrf
*vrf
= vrf_lookup_by_id(VRF_DEFAULT
);
217 struct interface
*ifp
= NULL
;
221 /* if we already have an id (from state file), we return. */
222 if (memcmp(myid
, zeroes
, 8) != 0) {
226 FOR_ALL_INTERFACES(vrf
, ifp
) {
227 /* ifp->ifindex is not necessarily valid at this point */
228 int ifindex
= if_nametoindex(ifp
->name
);
230 unsigned char eui
[8];
231 rc
= if_eui64(ifindex
, eui
);
234 memcpy(myid
, eui
, 8);
239 /* We failed to get a global EUI64 from the interfaces we were given.
240 Let's try to find an interface with a MAC address. */
241 for(i
= 1; i
< 256; i
++) {
242 char buf
[INTERFACE_NAMSIZ
], *ifname
;
243 unsigned char eui
[8];
244 ifname
= if_indextoname(i
, buf
);
247 rc
= if_eui64(i
, eui
);
250 memcpy(myid
, eui
, 8);
254 flog_err(EC_BABEL_CONFIG
, "Couldn't find router id -- using random value.");
256 rc
= read_random_bytes(myid
, 8);
258 flog_err(EC_BABEL_CONFIG
, "read(random): %s (cannot assign an ID)",
259 safe_strerror(errno
));
262 /* Clear group and global bits */
263 UNSET_FLAG (myid
[0], 3);
266 /* Make some noise so that others notice us, and send retractions in
267 case we were restarted recently */
269 babel_initial_noise(void)
271 struct vrf
*vrf
= vrf_lookup_by_id(VRF_DEFAULT
);
272 struct interface
*ifp
= NULL
;
274 FOR_ALL_INTERFACES(vrf
, ifp
) {
277 /* Apply jitter before we send the first message. */
278 usleep(roughly(10000));
281 send_wildcard_retraction(ifp
);
284 FOR_ALL_INTERFACES(vrf
, ifp
) {
287 usleep(roughly(10000));
290 send_wildcard_retraction(ifp
);
291 send_self_update(ifp
);
292 send_request(ifp
, NULL
, 0);
298 /* Delete all the added babel routes, make babeld only speak to zebra. */
300 babel_clean_routing_process(void)
303 babel_interface_close_all();
306 thread_cancel(&babel_routing_process
->t_read
);
307 thread_cancel(&babel_routing_process
->t_update
);
309 distribute_list_delete(&babel_routing_process
->distribute_ctx
);
310 XFREE(MTYPE_BABEL
, babel_routing_process
);
313 /* Function used with timeout. */
314 static void babel_main_loop(struct thread
*thread
)
317 struct vrf
*vrf
= vrf_lookup_by_id(VRF_DEFAULT
);
318 struct interface
*ifp
= NULL
;
323 /* timeouts --------------------------------------------------------- */
324 /* get the next timeout */
325 babel_fill_with_next_timeout(&tv
);
326 /* if there is no timeout, we must wait. */
327 if(timeval_compare(&tv
, &babel_now
) > 0) {
328 timeval_minus(&tv
, &tv
, &babel_now
);
329 debugf(BABEL_DEBUG_TIMEOUT
, "babel main loop : timeout: %lld msecs",
330 (long long)tv
.tv_sec
* 1000 + tv
.tv_usec
/ 1000);
331 /* it happens often to have less than 1 ms, it's bad. */
332 timeval_add_msec(&tv
, &tv
, 300);
333 babel_set_timer(&tv
);
339 /* update database -------------------------------------------------- */
340 if(timeval_compare(&check_neighbours_timeout
, &babel_now
) < 0) {
342 msecs
= check_neighbours();
343 /* Multiply by 3/2 to allow neighbours to expire. */
344 msecs
= MAX(3 * msecs
/ 2, 10);
345 schedule_neighbours_check(msecs
, 1);
348 if(babel_now
.tv_sec
>= expiry_time
) {
351 expiry_time
= babel_now
.tv_sec
+ roughly(30);
354 if(babel_now
.tv_sec
>= source_expiry_time
) {
356 source_expiry_time
= babel_now
.tv_sec
+ roughly(300);
359 FOR_ALL_INTERFACES(vrf
, ifp
) {
360 babel_interface_nfo
*babel_ifp
= NULL
;
363 babel_ifp
= babel_get_if_nfo(ifp
);
364 if(timeval_compare(&babel_now
, &babel_ifp
->hello_timeout
) >= 0)
366 if(timeval_compare(&babel_now
, &babel_ifp
->update_timeout
) >= 0)
367 send_update(ifp
, 0, NULL
, 0);
368 if(timeval_compare(&babel_now
,
369 &babel_ifp
->update_flush_timeout
) >= 0)
373 if(resend_time
.tv_sec
!= 0) {
374 if(timeval_compare(&babel_now
, &resend_time
) >= 0)
378 if(unicast_flush_timeout
.tv_sec
!= 0) {
379 if(timeval_compare(&babel_now
, &unicast_flush_timeout
) >= 0)
383 FOR_ALL_INTERFACES(vrf
, ifp
) {
384 babel_interface_nfo
*babel_ifp
= NULL
;
387 babel_ifp
= babel_get_if_nfo(ifp
);
388 if(babel_ifp
->flush_timeout
.tv_sec
!= 0) {
389 if(timeval_compare(&babel_now
, &babel_ifp
->flush_timeout
) >= 0)
395 assert(0); /* this line should never be reach */
399 printIfMin(struct timeval
*tv
, int cmd
, const char *tag
, const char *ifname
)
401 static struct timeval curr_tv
;
402 static char buffer
[200];
403 static const char *curr_tag
= NULL
;
406 case 0: /* reset timeval */
409 snprintf(buffer
, 200L, "interface: %s; %s", ifname
, tag
);
415 case 1: /* take the min */
416 if (tv
->tv_sec
== 0 && tv
->tv_usec
== 0) { /* if (tv == ∞) */
419 if (tv
->tv_sec
< curr_tv
.tv_sec
||(tv
->tv_sec
== curr_tv
.tv_sec
&&
420 tv
->tv_usec
< curr_tv
.tv_usec
)) {
423 snprintf(buffer
, 200L, "interface: %s; %s", ifname
, tag
);
430 case 2: /* print message */
431 debugf(BABEL_DEBUG_TIMEOUT
, "next timeout due to: %s", curr_tag
);
439 babel_fill_with_next_timeout(struct timeval
*tv
)
441 #if (defined NO_DEBUG)
442 #define printIfMin(a,b,c,d)
444 #define printIfMin(a,b,c,d) \
445 if (UNLIKELY(debug & BABEL_DEBUG_TIMEOUT)) {printIfMin(a,b,c,d);}
447 struct vrf
*vrf
= vrf_lookup_by_id(VRF_DEFAULT
);
448 struct interface
*ifp
= NULL
;
450 *tv
= check_neighbours_timeout
;
451 printIfMin(tv
, 0, "check_neighbours_timeout", NULL
);
452 timeval_min_sec(tv
, expiry_time
);
453 printIfMin(tv
, 1, "expiry_time", NULL
);
454 timeval_min_sec(tv
, source_expiry_time
);
455 printIfMin(tv
, 1, "source_expiry_time", NULL
);
456 timeval_min(tv
, &resend_time
);
457 printIfMin(tv
, 1, "resend_time", NULL
);
458 FOR_ALL_INTERFACES(vrf
, ifp
) {
459 babel_interface_nfo
*babel_ifp
= NULL
;
462 babel_ifp
= babel_get_if_nfo(ifp
);
463 timeval_min(tv
, &babel_ifp
->flush_timeout
);
464 printIfMin(tv
, 1, "flush_timeout", ifp
->name
);
465 timeval_min(tv
, &babel_ifp
->hello_timeout
);
466 printIfMin(tv
, 1, "hello_timeout", ifp
->name
);
467 timeval_min(tv
, &babel_ifp
->update_timeout
);
468 printIfMin(tv
, 1, "update_timeout", ifp
->name
);
469 timeval_min(tv
, &babel_ifp
->update_flush_timeout
);
470 printIfMin(tv
, 1, "update_flush_timeout",ifp
->name
);
472 timeval_min(tv
, &unicast_flush_timeout
);
473 printIfMin(tv
, 1, "unicast_flush_timeout", NULL
);
474 printIfMin(tv
, 2, NULL
, NULL
);
479 /* set the t_update thread of the babel routing process to be launch in
480 'timeout' (approximate at the milisecond) */
482 babel_set_timer(struct timeval
*timeout
)
484 long msecs
= timeout
->tv_sec
* 1000 + timeout
->tv_usec
/ 1000;
485 thread_cancel(&(babel_routing_process
->t_update
));
486 thread_add_timer_msec(master
, babel_main_loop
, NULL
, msecs
, &babel_routing_process
->t_update
);
490 schedule_neighbours_check(int msecs
, int override
)
492 struct timeval timeout
;
494 timeval_add_msec(&timeout
, &babel_now
, msecs
);
496 check_neighbours_timeout
= timeout
;
498 timeval_min(&check_neighbours_timeout
, &timeout
);
502 resize_receive_buffer(int size
)
504 if(size
<= receive_buffer_size
)
507 if(receive_buffer
== NULL
) {
508 receive_buffer
= malloc(size
);
509 if(receive_buffer
== NULL
) {
510 flog_err(EC_BABEL_MEMORY
, "malloc(receive_buffer): %s",
511 safe_strerror(errno
));
514 receive_buffer_size
= size
;
517 new = realloc(receive_buffer
, size
);
519 flog_err(EC_BABEL_MEMORY
, "realloc(receive_buffer): %s",
520 safe_strerror(errno
));
523 receive_buffer
= new;
524 receive_buffer_size
= size
;
530 babel_distribute_update (struct distribute_ctx
*ctx
, struct distribute
*dist
)
532 struct interface
*ifp
;
533 babel_interface_nfo
*babel_ifp
;
540 ifp
= if_lookup_by_name (dist
->ifname
, VRF_DEFAULT
);
544 babel_ifp
= babel_get_if_nfo(ifp
);
546 for (type
= 0; type
< DISTRIBUTE_MAX
; type
++) {
547 family
= type
== DISTRIBUTE_V4_IN
|| type
== DISTRIBUTE_V4_OUT
?
549 if (dist
->list
[type
])
550 babel_ifp
->list
[type
] = access_list_lookup (family
,
553 babel_ifp
->list
[type
] = NULL
;
554 if (dist
->prefix
[type
])
555 babel_ifp
->prefix
[type
] = prefix_list_lookup (family
,
558 babel_ifp
->prefix
[type
] = NULL
;
563 babel_distribute_update_interface (struct interface
*ifp
)
565 struct distribute
*dist
= NULL
;
567 if (babel_routing_process
)
568 dist
= distribute_lookup(babel_routing_process
->distribute_ctx
, ifp
->name
);
570 babel_distribute_update (babel_routing_process
->distribute_ctx
, dist
);
573 /* Update all interface's distribute list. */
575 babel_distribute_update_all (struct prefix_list
*notused
)
577 struct vrf
*vrf
= vrf_lookup_by_id(VRF_DEFAULT
);
578 struct interface
*ifp
;
580 FOR_ALL_INTERFACES (vrf
, ifp
)
581 babel_distribute_update_interface (ifp
);
585 babel_distribute_update_all_wrapper (struct access_list
*notused
)
587 babel_distribute_update_all(NULL
);
592 DEFUN_NOSH (router_babel
,
595 "Enable a routing process\n"
596 "Make Babel instance command\n")
600 vty
->node
= BABEL_NODE
;
602 if (!babel_routing_process
) {
603 ret
= babel_create_routing_process ();
605 /* Notice to user we couldn't create Babel. */
607 zlog_warn ("can't create Babel");
616 DEFUN (no_router_babel
,
620 "Disable a routing process\n"
621 "Remove Babel instance command\n")
623 if(babel_routing_process
)
624 babel_clean_routing_process();
628 /* [Babel Command] */
629 DEFUN (babel_diversity
,
633 "Enable diversity-aware routing.\n")
635 diversity_kind
= DIVERSITY_CHANNEL
;
639 /* [Babel Command] */
640 DEFUN (no_babel_diversity
,
641 no_babel_diversity_cmd
,
642 "no babel diversity",
645 "Disable diversity-aware routing.\n")
647 diversity_kind
= DIVERSITY_NONE
;
651 /* [Babel Command] */
652 DEFPY (babel_diversity_factor
,
653 babel_diversity_factor_cmd
,
654 "[no] babel diversity-factor (1-256)$factor",
657 "Set the diversity factor.\n"
658 "Factor in units of 1/256.\n")
660 diversity_factor
= no
? BABEL_DEFAULT_DIVERSITY_FACTOR
: factor
;
664 /* [Babel Command] */
665 DEFPY (babel_set_resend_delay
,
666 babel_set_resend_delay_cmd
,
667 "[no] babel resend-delay (20-655340)$delay",
670 "Time before resending a message\n"
673 resend_delay
= no
? BABEL_DEFAULT_RESEND_DELAY
: delay
;
677 /* [Babel Command] */
678 DEFPY (babel_set_smoothing_half_life
,
679 babel_set_smoothing_half_life_cmd
,
680 "[no] babel smoothing-half-life (0-65534)$seconds",
683 "Smoothing half-life\n"
684 "Seconds (0 to disable)\n")
686 change_smoothing_half_life(no
? BABEL_DEFAULT_SMOOTHING_HALF_LIFE
691 DEFUN (babel_distribute_list
,
692 babel_distribute_list_cmd
,
693 "distribute-list [prefix] ACCESSLIST4_NAME <in|out> [WORD]",
694 "Filter networks in routing updates\n"
697 "Filter incoming routing updates\n"
698 "Filter outgoing routing updates\n"
701 const char *ifname
= NULL
;
702 int prefix
= (argv
[1]->type
== WORD_TKN
) ? 1 : 0;
704 if (argv
[argc
- 1]->type
== VARIABLE_TKN
)
705 ifname
= argv
[argc
- 1]->arg
;
707 return distribute_list_parser(prefix
, true, argv
[2 + prefix
]->text
,
708 argv
[1 + prefix
]->arg
, ifname
);
711 DEFUN (babel_no_distribute_list
,
712 babel_no_distribute_list_cmd
,
713 "no distribute-list [prefix] ACCESSLIST4_NAME <in|out> [WORD]",
715 "Filter networks in routing updates\n"
718 "Filter incoming routing updates\n"
719 "Filter outgoing routing updates\n"
722 const char *ifname
= NULL
;
723 int prefix
= (argv
[2]->type
== WORD_TKN
) ? 1 : 0;
725 if (argv
[argc
- 1]->type
== VARIABLE_TKN
)
726 ifname
= argv
[argc
- 1]->arg
;
728 return distribute_list_no_parser(vty
, prefix
, true,
729 argv
[3 + prefix
]->text
,
730 argv
[2 + prefix
]->arg
, ifname
);
733 DEFUN (babel_ipv6_distribute_list
,
734 babel_ipv6_distribute_list_cmd
,
735 "ipv6 distribute-list [prefix] ACCESSLIST6_NAME <in|out> [WORD]",
737 "Filter networks in routing updates\n"
740 "Filter incoming routing updates\n"
741 "Filter outgoing routing updates\n"
744 const char *ifname
= NULL
;
745 int prefix
= (argv
[2]->type
== WORD_TKN
) ? 1 : 0;
747 if (argv
[argc
- 1]->type
== VARIABLE_TKN
)
748 ifname
= argv
[argc
- 1]->arg
;
750 return distribute_list_parser(prefix
, false, argv
[3 + prefix
]->text
,
751 argv
[2 + prefix
]->arg
, ifname
);
754 DEFUN (babel_no_ipv6_distribute_list
,
755 babel_no_ipv6_distribute_list_cmd
,
756 "no ipv6 distribute-list [prefix] ACCESSLIST6_NAME <in|out> [WORD]",
759 "Filter networks in routing updates\n"
762 "Filter incoming routing updates\n"
763 "Filter outgoing routing updates\n"
766 const char *ifname
= NULL
;
767 int prefix
= (argv
[3]->type
== WORD_TKN
) ? 1 : 0;
769 if (argv
[argc
- 1]->type
== VARIABLE_TKN
)
770 ifname
= argv
[argc
- 1]->arg
;
772 return distribute_list_no_parser(vty
, prefix
, false,
773 argv
[4 + prefix
]->text
,
774 argv
[3 + prefix
]->arg
, ifname
);
778 babeld_quagga_init(void)
781 install_node(&cmd_babel_node
);
783 install_element(CONFIG_NODE
, &router_babel_cmd
);
784 install_element(CONFIG_NODE
, &no_router_babel_cmd
);
786 install_default(BABEL_NODE
);
787 install_element(BABEL_NODE
, &babel_diversity_cmd
);
788 install_element(BABEL_NODE
, &no_babel_diversity_cmd
);
789 install_element(BABEL_NODE
, &babel_diversity_factor_cmd
);
790 install_element(BABEL_NODE
, &babel_set_resend_delay_cmd
);
791 install_element(BABEL_NODE
, &babel_set_smoothing_half_life_cmd
);
793 install_element(BABEL_NODE
, &babel_distribute_list_cmd
);
794 install_element(BABEL_NODE
, &babel_no_distribute_list_cmd
);
795 install_element(BABEL_NODE
, &babel_ipv6_distribute_list_cmd
);
796 install_element(BABEL_NODE
, &babel_no_ipv6_distribute_list_cmd
);
802 /* Access list install. */
804 access_list_add_hook (babel_distribute_update_all_wrapper
);
805 access_list_delete_hook (babel_distribute_update_all_wrapper
);
807 /* Prefix list initialize.*/
809 prefix_list_add_hook (babel_distribute_update_all
);
810 prefix_list_delete_hook (babel_distribute_update_all
);
813 /* Stubs to adapt Babel's filtering calls to Quagga's infrastructure. */
816 input_filter(const unsigned char *id
,
817 const unsigned char *prefix
, unsigned short plen
,
818 const unsigned char *neigh
, unsigned int ifindex
)
820 return babel_filter(0, prefix
, plen
, ifindex
);
824 output_filter(const unsigned char *id
, const unsigned char *prefix
,
825 unsigned short plen
, unsigned int ifindex
)
827 return babel_filter(1, prefix
, plen
, ifindex
);
830 /* There's no redistribute filter in Quagga -- the zebra daemon does its
833 redistribute_filter(const unsigned char *prefix
, unsigned short plen
,
834 unsigned int ifindex
, int proto
)
839 struct babel
*babel_lookup(void)
841 return babel_routing_process
;