Skip to content

Commit

Permalink
zebra: Delay some processing until after startup is finished
Browse files Browse the repository at this point in the history
Currently zebra starts the graceful restart timer as well as
allows connections from clients before all data is read in
from the kernel as well as the possiblity of allowing client
connections before this happens as well.

Let's move the graceful restart timer start till after this is
done as well as not allowing client connections till then as well.

Signed-off-by: Donald Sharp <[email protected]>
  • Loading branch information
donaldsharp committed Oct 4, 2024
1 parent 842009f commit d40a014
Show file tree
Hide file tree
Showing 3 changed files with 47 additions and 30 deletions.
64 changes: 34 additions & 30 deletions zebra/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@

#define ZEBRA_PTM_SUPPORT

char *zserv_path;

/* process id. */
pid_t pid;

Expand Down Expand Up @@ -312,17 +314,48 @@ FRR_DAEMON_INFO(zebra, ZEBRA,
);
/* clang-format on */

void zebra_main_router_started(void)
{
/* After we have successfully acquired the pidfile, we can be sure
* about being the only copy of zebra process, which is submitting
* changes to the FIB.
* Clean up zebra-originated routes. The requests will be sent to OS
* immediately, so originating PID in notifications from kernel
* will be equal to the current getpid(). To know about such routes,
* we have to have route_read() called before.
* If FRR is gracefully restarting, we either wait for clients
* (e.g., BGP) to signal GR is complete else we wait for specified
* duration.
*/
zrouter.startup_time = monotime(NULL);
zrouter.rib_sweep_time = 0;
zrouter.graceful_restart = zebra_di.graceful_restart;
if (!zrouter.graceful_restart)
event_add_timer(zrouter.master, rib_sweep_route, NULL, 0, NULL);
else {
int gr_cleanup_time;

gr_cleanup_time = zebra_di.gr_cleanup_time ? zebra_di.gr_cleanup_time
: ZEBRA_GR_DEFAULT_RIB_SWEEP_TIME;
event_add_timer(zrouter.master, rib_sweep_route, NULL, gr_cleanup_time,
&zrouter.t_rib_sweep);
}

zserv_start(zserv_path);
}

/* Main startup routine. */
int main(int argc, char **argv)
{
// int batch_mode = 0;
char *zserv_path = NULL;
struct sockaddr_storage dummy;
socklen_t dummylen;
bool asic_offload = false;
bool v6_with_v4_nexthop = false;
bool notify_on_ack = true;

zserv_path = NULL;

vrf_configure_backend(VRF_BACKEND_VRF_LITE);

frr_preinit(&zebra_di, argc, argv);
Expand Down Expand Up @@ -473,32 +506,6 @@ int main(int argc, char **argv)
*/
frr_config_fork();

/* After we have successfully acquired the pidfile, we can be sure
* about being the only copy of zebra process, which is submitting
* changes to the FIB.
* Clean up zebra-originated routes. The requests will be sent to OS
* immediately, so originating PID in notifications from kernel
* will be equal to the current getpid(). To know about such routes,
* we have to have route_read() called before.
* If FRR is gracefully restarting, we either wait for clients
* (e.g., BGP) to signal GR is complete else we wait for specified
* duration.
*/
zrouter.startup_time = monotime(NULL);
zrouter.rib_sweep_time = 0;
zrouter.graceful_restart = zebra_di.graceful_restart;
if (!zrouter.graceful_restart)
event_add_timer(zrouter.master, rib_sweep_route, NULL, 0, NULL);
else {
int gr_cleanup_time;

gr_cleanup_time = zebra_di.gr_cleanup_time
? zebra_di.gr_cleanup_time
: ZEBRA_GR_DEFAULT_RIB_SWEEP_TIME;
event_add_timer(zrouter.master, rib_sweep_route, NULL,
gr_cleanup_time, &zrouter.t_rib_sweep);
}

/* Needed for BSD routing socket. */
pid = getpid();

Expand All @@ -508,9 +515,6 @@ int main(int argc, char **argv)
/* Start the ted module, before zserv */
zebra_opaque_start();

/* Start Zebra API server */
zserv_start(zserv_path);

/* Init label manager */
label_manager_init();

Expand Down
2 changes: 2 additions & 0 deletions zebra/rib.h
Original file line number Diff line number Diff line change
Expand Up @@ -637,6 +637,8 @@ extern pid_t pid;

extern uint32_t rt_table_main_id;

extern void zebra_main_router_started(void);

/* Name of hook calls */
#define ZEBRA_ON_RIB_PROCESS_HOOK_CALL "on_rib_process_dplane_results"

Expand Down
11 changes: 11 additions & 0 deletions zebra/zebra_ns.c
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,17 @@ void zebra_ns_startup_continue(struct zebra_dplane_ctx *ctx)
vlan_read(zns);
kernel_read_pbr_rules(zns);
kernel_read_tc_qdisc(zns);

/*
* At this point FRR has requested and read a bunch
* of data from the dplane about initial state of
* the system. Zebra now needs to initialize
* the gr subsystem ( or the route sweeping
* subsystem ) to allow that to properly work.
* This must be done *immediately* after the
* load of all data from the underlying dplane.
*/
zebra_main_router_started();
break;
}
}
Expand Down

0 comments on commit d40a014

Please sign in to comment.