]> git.proxmox.com Git - mirror_frr.git/commitdiff
bgpd: set/unset bgpd no-rib option at runtime
authorDavid Schweizer <dschweizer@opensourcerouting.org>
Wed, 2 Sep 2020 16:20:08 +0000 (18:20 +0200)
committerDavid Schweizer <dschweizer@opensourcerouting.org>
Wed, 2 Sep 2020 16:20:08 +0000 (18:20 +0200)
* Added vtysh cli commands and functions to set/unset bgp daemons no-rib
  option during runtime and withdraw/announce routes in bgp instances
  RIB from/to Zebra.

Signed-off-by: David Schweizer <dschweizer@opensourcerouting.org>
bgpd/bgp_vty.c
bgpd/bgp_zebra.c
bgpd/bgp_zebra.h
bgpd/bgpd.c
bgpd/bgpd.h

index 005fad1409409aadee60e9e117e7c54a265ef465..795a4adfc7f5185d19264899d2a782dbcf9047f8 100644 (file)
@@ -1411,6 +1411,41 @@ DEFUN (no_bgp_cluster_id,
        return CMD_SUCCESS;
 }
 
+DEFPY (bgp_norib,
+       bgp_norib_cmd,
+       "bgp no-rib",
+       BGP_STR
+       "Disable BGP route installation to RIB (Zebra)\n")
+{
+       if (bgp_option_check(BGP_OPT_NO_FIB)) {
+               vty_out(vty,
+                       "%% No-RIB option is already set, nothing to do here.\n");
+               return CMD_SUCCESS;
+       }
+
+       bgp_option_norib_set_runtime();
+
+       return CMD_SUCCESS;
+}
+
+DEFPY (no_bgp_norib,
+       no_bgp_norib_cmd,
+       "no bgp no-rib",
+       NO_STR
+       BGP_STR
+       "Disable BGP route installation to RIB (Zebra)\n")
+{
+       if (!bgp_option_check(BGP_OPT_NO_FIB)) {
+               vty_out(vty,
+                       "%% No-RIB option is not set, nothing to do here.\n");
+               return CMD_SUCCESS;
+       }
+
+       bgp_option_norib_unset_runtime();
+
+       return CMD_SUCCESS;
+}
+
 DEFUN (bgp_confederation_identifier,
        bgp_confederation_identifier_cmd,
        "bgp confederation identifier (1-4294967295)",
@@ -15607,6 +15642,10 @@ int bgp_config_write(struct vty *vty)
        if (CHECK_FLAG(bm->flags, BM_FLAG_GRACEFUL_SHUTDOWN))
                vty_out(vty, "bgp graceful-shutdown\n");
 
+       /* No-RIB (Zebra) option flag configuration */
+       if (bgp_option_check(BGP_OPT_NO_FIB))
+               vty_out(vty, "bgp no-rib\n");
+
        /* BGP configuration. */
        for (ALL_LIST_ELEMENTS(bm->bgp, mnode, mnnode, bgp)) {
 
@@ -16151,6 +16190,10 @@ void bgp_vty_init(void)
        install_element(BGP_NODE, &bgp_cluster_id_cmd);
        install_element(BGP_NODE, &no_bgp_cluster_id_cmd);
 
+       /* "bgp no-rib" commands. */
+       install_element(CONFIG_NODE, &bgp_norib_cmd);
+       install_element(CONFIG_NODE, &no_bgp_norib_cmd);
+
        /* "bgp confederation" commands. */
        install_element(BGP_NODE, &bgp_confederation_identifier_cmd);
        install_element(BGP_NODE, &no_bgp_confederation_identifier_cmd);
index b20323852009da328ac8a3fe7f6f64c1d03aa3d2..a32e47f446364c348a11e334b2010cb73332218f 100644 (file)
@@ -1543,6 +1543,30 @@ void bgp_zebra_announce_table(struct bgp *bgp, afi_t afi, safi_t safi)
                                                   pi, bgp, afi, safi);
 }
 
+/* Announce routes of any bgp subtype of a table to zebra */
+void bgp_zebra_announce_table_all_subtypes(struct bgp *bgp, afi_t afi,
+                                          safi_t safi)
+{
+       struct bgp_dest *dest;
+       struct bgp_table *table;
+       struct bgp_path_info *pi;
+
+       if (!bgp_install_info_to_zebra(bgp))
+               return;
+
+       table = bgp->rib[afi][safi];
+       if (!table)
+               return;
+
+       for (dest = bgp_table_top(table); dest; dest = bgp_route_next(dest))
+               for (pi = bgp_dest_get_bgp_path_info(dest); pi; pi = pi->next)
+                       if (CHECK_FLAG(pi->flags, BGP_PATH_SELECTED) &&
+                           pi->type == ZEBRA_ROUTE_BGP)
+                               bgp_zebra_announce(dest,
+                                                  bgp_dest_get_prefix(dest),
+                                                  pi, bgp, afi, safi);
+}
+
 void bgp_zebra_withdraw(const struct prefix *p, struct bgp_path_info *info,
                        struct bgp *bgp, safi_t safi)
 {
@@ -1586,6 +1610,30 @@ void bgp_zebra_withdraw(const struct prefix *p, struct bgp_path_info *info,
        zclient_route_send(ZEBRA_ROUTE_DELETE, zclient, &api);
 }
 
+/* Withdraw all entries in a BGP instances RIB table from Zebra */
+void bgp_zebra_withdraw_table_all_subtypes(struct bgp *bgp, afi_t afi, safi_t safi)
+{
+       struct bgp_dest *dest;
+       struct bgp_table *table;
+       struct bgp_path_info *pi;
+
+       if (!bgp_install_info_to_zebra(bgp))
+               return;
+
+       table = bgp->rib[afi][safi];
+       if (!table)
+               return;
+
+       for (dest = bgp_table_top(table); dest; dest = bgp_route_next(dest)) {
+               for (pi = bgp_dest_get_bgp_path_info(dest); pi; pi = pi->next) {
+                       if (CHECK_FLAG(pi->flags, BGP_PATH_SELECTED)
+                           && (pi->type == ZEBRA_ROUTE_BGP))
+                               bgp_zebra_withdraw(bgp_dest_get_prefix(dest),
+                                                  pi, bgp, safi);
+               }
+       }
+}
+
 struct bgp_redist *bgp_redist_lookup(struct bgp *bgp, afi_t afi, uint8_t type,
                                     unsigned short instance)
 {
index a068c03717007160a71ed1e8f8ad59e6ab0ded2d..4b357c380afcdeb07646e391ed73e642b7177e1a 100644 (file)
@@ -43,6 +43,14 @@ extern void bgp_zebra_withdraw(const struct prefix *p,
                               struct bgp_path_info *path, struct bgp *bgp,
                               safi_t safi);
 
+/* Announce routes of any bgp subtype of a table to zebra */
+extern void bgp_zebra_announce_table_all_subtypes(struct bgp *bgp, afi_t afi,
+                                                 safi_t safi);
+
+/* Withdraw all entries of any subtype in a BGP instances RIB table from Zebra */
+extern void bgp_zebra_withdraw_table_all_subtypes(struct bgp *bgp, afi_t afi,
+                                                 safi_t safi);
+
 extern void bgp_zebra_initiate_radv(struct bgp *bgp, struct peer *peer);
 extern void bgp_zebra_terminate_radv(struct bgp *bgp, struct peer *peer);
 
index b654e85206e24209782b6632a8608e32e9c070c2..84d4aeb1e64fdacb0d10b2f1e877af683f137b29 100644 (file)
@@ -202,6 +202,52 @@ int bgp_option_check(int flag)
        return CHECK_FLAG(bm->options, flag);
 }
 
+/* set the bgp no-rib option during runtime and remove installed routes */
+void bgp_option_norib_set_runtime(void)
+{
+       struct bgp *bgp;
+       struct listnode *node;
+       afi_t afi;
+       safi_t safi;
+
+       if (bgp_option_check(BGP_OPT_NO_FIB))
+               return;
+
+       bgp_option_set(BGP_OPT_NO_FIB);
+
+       zlog_info("Disabled BGP route installation to RIB (Zebra)");
+
+       for (ALL_LIST_ELEMENTS_RO(bm->bgp, node, bgp)) {
+               FOREACH_AFI_SAFI(afi, safi)
+                       bgp_zebra_withdraw_table_all_subtypes(bgp, afi, safi);
+       }
+
+       zlog_info("All routes have been withdrawn from RIB (Zebra)");
+}
+
+/* unset the bgp no-rib option during runtime and announce routes to Zebra */
+void bgp_option_norib_unset_runtime(void)
+{
+       struct bgp *bgp;
+       struct listnode *node;
+       afi_t afi;
+       safi_t safi;
+
+       if (!bgp_option_check(BGP_OPT_NO_FIB))
+               return;
+
+       bgp_option_unset(BGP_OPT_NO_FIB);
+
+       zlog_info("Enabled BGP route installation to RIB (Zebra)");
+
+       for (ALL_LIST_ELEMENTS_RO(bm->bgp, node, bgp)) {
+               FOREACH_AFI_SAFI(afi, safi)
+                       bgp_zebra_announce_table_all_subtypes(bgp, afi, safi);
+       }
+
+       zlog_info("All routes have been installed in RIB (Zebra)");
+}
+
 /* Internal function to set BGP structure configureation flag.  */
 static void bgp_config_set(struct bgp *bgp, int config)
 {
index e282e461dfeb6ce618a9861de4a1d24f8537c464..9f72a3e19e2a473a20f6db9a5506c1ab34bdc37a 100644 (file)
@@ -1807,6 +1807,12 @@ extern int bgp_option_set(int);
 extern int bgp_option_unset(int);
 extern int bgp_option_check(int);
 
+/* set the bgp no-rib option during runtime and remove installed routes */
+extern void bgp_option_norib_set_runtime(void);
+
+/* unset the bgp no-rib option during runtime and reset all peers */
+extern void bgp_option_norib_unset_runtime(void);
+
 extern int bgp_get(struct bgp **, as_t *, const char *, enum bgp_instance_type);
 extern void bgp_instance_up(struct bgp *);
 extern void bgp_instance_down(struct bgp *);