From 8bc8de2c155f33e1af273ed53dbf47c948a5c56e Mon Sep 17 00:00:00 2001 From: Donald Sharp Date: Thu, 21 Jun 2018 21:55:38 -0400 Subject: [PATCH] staticd: Allow daemon to have backup static routes Modify staticd to allow it to have backup static routes with higher admin distance. Signed-off-by: Donald Sharp --- staticd/static_nht.c | 8 ++++++-- staticd/static_routes.c | 28 +++++++++++++++------------- staticd/static_zebra.c | 34 ++++++++++++++++------------------ staticd/static_zebra.h | 5 +++-- 4 files changed, 40 insertions(+), 35 deletions(-) diff --git a/staticd/static_nht.c b/staticd/static_nht.c index aea175b19b..f9f937f905 100644 --- a/staticd/static_nht.c +++ b/staticd/static_nht.c @@ -70,8 +70,12 @@ void static_nht_update(struct prefix *p, uint32_t nh_num, if (orig != si->nh_valid) reinstall = true; + + if (reinstall) { + static_zebra_route_add(rn, si, vrf_id, + SAFI_UNICAST, true); + reinstall = false; + } } - if (reinstall) - static_zebra_route_add(rn, vrf_id, SAFI_UNICAST, true); } } diff --git a/staticd/static_routes.c b/staticd/static_routes.c index b7699ae3f3..9f4338f946 100644 --- a/staticd/static_routes.c +++ b/staticd/static_routes.c @@ -33,7 +33,8 @@ #include "static_zebra.h" /* Install static route into rib. */ -static void static_install_route(struct route_node *rn, safi_t safi) +static void static_install_route(struct route_node *rn, + struct static_route *si_changed, safi_t safi) { struct static_route *si; @@ -42,19 +43,20 @@ static void static_install_route(struct route_node *rn, safi_t safi) si = rn->info; if (si) - static_zebra_route_add(rn, si->vrf_id, safi, true); + static_zebra_route_add(rn, si_changed, si->vrf_id, safi, true); } /* Uninstall static route from RIB. */ static void static_uninstall_route(vrf_id_t vrf_id, safi_t safi, - struct route_node *rn) + struct route_node *rn, + struct static_route *si_changed) { if (rn->info) - static_zebra_route_add(rn, vrf_id, safi, true); + static_zebra_route_add(rn, si_changed, vrf_id, safi, true); else - static_zebra_route_add(rn, vrf_id, safi, false); + static_zebra_route_add(rn, si_changed, vrf_id, safi, false); } int static_add_route(afi_t afi, safi_t safi, uint8_t type, struct prefix *p, @@ -180,14 +182,14 @@ int static_add_route(afi_t afi, safi_t safi, uint8_t type, struct prefix *p, /* check whether interface exists in system & install if it does */ if (!ifname) - static_install_route(rn, safi); + static_install_route(rn, si, safi); else { struct interface *ifp; ifp = if_lookup_by_name(ifname, nh_svrf->vrf->vrf_id); if (ifp && ifp->ifindex != IFINDEX_INTERNAL) { si->ifindex = ifp->ifindex; - static_install_route(rn, safi); + static_install_route(rn, si, safi); } else zlog_warn("Static Route using %s interface not installed because the interface does not exist in specified vrf", ifname); @@ -253,7 +255,7 @@ int static_delete_route(afi_t afi, safi_t safi, uint8_t type, struct prefix *p, * If we have other si nodes then route replace * else delete the route */ - static_uninstall_route(si->vrf_id, safi, rn); + static_uninstall_route(si->vrf_id, safi, rn, si); route_unlock_node(rn); /* Free static route configuration. */ @@ -296,7 +298,7 @@ static void static_ifindex_update_af(struct interface *ifp, bool up, afi_t afi, } } - static_install_route(rn, safi); + static_install_route(rn, si, safi); } } } @@ -340,7 +342,7 @@ static void static_fixup_vrf(struct static_vrf *svrf, } if (install) - static_install_route(rn, safi); + static_install_route(rn, si, safi); } } @@ -379,7 +381,7 @@ static void static_enable_vrf(struct static_vrf *svrf, } if (install) - static_install_route(rn, safi); + static_install_route(rn, si, safi); } } @@ -441,7 +443,7 @@ static void static_cleanup_vrf(struct static_vrf *svrf, if (strcmp(svrf->vrf->name, si->nh_vrfname) != 0) continue; - static_uninstall_route(si->vrf_id, safi, rn); + static_uninstall_route(si->vrf_id, safi, rn, si); } } } @@ -462,7 +464,7 @@ static void static_disable_vrf(struct route_table *stable, for (rn = route_top(stable); rn; rn = route_next(rn)) for (si = rn->info; si; si = si->next) - static_uninstall_route(si->vrf_id, safi, rn); + static_uninstall_route(si->vrf_id, safi, rn, si); } /* diff --git a/staticd/static_zebra.c b/staticd/static_zebra.c index 9802aa548a..27e126e2a6 100644 --- a/staticd/static_zebra.c +++ b/staticd/static_zebra.c @@ -240,8 +240,9 @@ void static_zebra_nht_register(struct static_route *si, bool reg) si->nh_registered = reg; } -extern void static_zebra_route_add(struct route_node *rn, vrf_id_t vrf_id, - safi_t safi, bool install) +extern void static_zebra_route_add(struct route_node *rn, + struct static_route *si_changed, + vrf_id_t vrf_id, safi_t safi, bool install) { struct static_route *si = rn->info; const struct prefix *p, *src_pp; @@ -262,29 +263,26 @@ extern void static_zebra_route_add(struct route_node *rn, vrf_id_t vrf_id, SET_FLAG(api.message, ZAPI_MESSAGE_SRCPFX); memcpy(&api.src_prefix, src_pp, sizeof(api.src_prefix)); } - + SET_FLAG(api.flags, ZEBRA_FLAG_RR_USE_DISTANCE); SET_FLAG(api.message, ZAPI_MESSAGE_NEXTHOP); + if (si_changed->distance) { + SET_FLAG(api.message, ZAPI_MESSAGE_DISTANCE); + api.distance = si_changed->distance; + } + if (si_changed->tag) { + SET_FLAG(api.message, ZAPI_MESSAGE_TAG); + api.tag = si_changed->tag; + } + api.tableid = si_changed->table_id; + zlog_debug("Distance sent down: %d %d", si_changed->distance, install); for (/*loaded above*/; si; si = si->next) { api_nh = &api.nexthops[nh_num]; if (si->nh_vrf_id == VRF_UNKNOWN) continue; - /* - * If we create a ecmp static route the - * last distance and tag entered wins. Why because - * this cli choosen sucks - */ - if (si->distance) { - SET_FLAG(api.message, ZAPI_MESSAGE_DISTANCE); - api.distance = si->distance; - } - if (si->tag) { - SET_FLAG(api.message, ZAPI_MESSAGE_TAG); - api.tag = si->tag; - } - - api.tableid = si->table_id; + if (si->distance != si_changed->distance) + continue; api_nh->vrf_id = si->nh_vrf_id; switch (si->type) { diff --git a/staticd/static_zebra.h b/staticd/static_zebra.h index 6b73b0dd3d..a82eb162e1 100644 --- a/staticd/static_zebra.h +++ b/staticd/static_zebra.h @@ -23,7 +23,8 @@ extern struct thread_master *master; extern void static_zebra_nht_register(struct static_route *si, bool reg); -extern void static_zebra_route_add(struct route_node *rn, vrf_id_t vrf_id, - safi_t safi, bool install); +extern void static_zebra_route_add(struct route_node *rn, + struct static_route *si_changed, + vrf_id_t vrf_id, safi_t safi, bool install); extern void static_zebra_init(void); #endif -- 2.39.5