diff --git a/isisd/isis_route.c b/isisd/isis_route.c index 636a63e290..05394e0fe4 100644 --- a/isisd/isis_route.c +++ b/isisd/isis_route.c @@ -49,8 +49,16 @@ #include "isis_route.h" #include "isis_zebra.h" +DEFINE_HOOK(isis_route_update_hook, + (struct isis_area * area, struct prefix *prefix, + struct isis_route_info *route_info), + (area, prefix, route_info)) + static struct isis_nexthop *nexthoplookup(struct list *nexthops, int family, union g_addr *ip, ifindex_t ifindex); +static void isis_route_update(struct isis_area *area, struct prefix *prefix, + struct prefix_ipv6 *src_p, + struct isis_route_info *route_info); static struct isis_nexthop *isis_nexthop_create(int family, union g_addr *ip, ifindex_t ifindex) @@ -316,7 +324,7 @@ struct isis_route_info *isis_route_create(struct prefix *prefix, return route_info; } -static void isis_route_delete(struct route_node *rode, +static void isis_route_delete(struct isis_area *area, struct route_node *rode, struct route_table *table) { struct isis_route_info *rinfo; @@ -343,13 +351,37 @@ static void isis_route_delete(struct route_node *rode, UNSET_FLAG(rinfo->flag, ISIS_ROUTE_FLAG_ACTIVE); if (isis->debugs & DEBUG_RTE_EVENTS) zlog_debug("ISIS-Rte: route delete %s", buff); - isis_zebra_route_update(prefix, src_p, rinfo); + isis_route_update(area, prefix, src_p, rinfo); } isis_route_info_delete(rinfo); rode->info = NULL; route_unlock_node(rode); } +static void isis_route_update(struct isis_area *area, struct prefix *prefix, + struct prefix_ipv6 *src_p, + struct isis_route_info *route_info) +{ + if (CHECK_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ACTIVE)) { + if (CHECK_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED)) + return; + + isis_zebra_route_add_route(prefix, src_p, route_info); + hook_call(isis_route_update_hook, area, prefix, route_info); + + SET_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED); + UNSET_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_RESYNC); + } else { + if (!CHECK_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED)) + return; + + isis_zebra_route_del_route(prefix, src_p, route_info); + hook_call(isis_route_update_hook, area, prefix, route_info); + + UNSET_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED); + } +} + static void _isis_route_verify_table(struct isis_area *area, struct route_table *table, struct route_table **tables) @@ -390,7 +422,7 @@ static void _isis_route_verify_table(struct isis_area *area, buff); } - isis_zebra_route_update(dst_p, src_p, rinfo); + isis_route_update(area, dst_p, src_p, rinfo); if (CHECK_FLAG(rinfo->flag, ISIS_ROUTE_FLAG_ACTIVE)) continue; @@ -399,7 +431,7 @@ static void _isis_route_verify_table(struct isis_area *area, * directly for * validating => no problems with deleting routes. */ if (!tables) { - isis_route_delete(rnode, table); + isis_route_delete(area, rnode, table); continue; } @@ -422,7 +454,7 @@ static void _isis_route_verify_table(struct isis_area *area, route_unlock_node(drnode); } - isis_route_delete(rnode, table); + isis_route_delete(area, rnode, table); } } diff --git a/isisd/isis_route.h b/isisd/isis_route.h index a20a7e038f..2326bb8228 100644 --- a/isisd/isis_route.h +++ b/isisd/isis_route.h @@ -44,6 +44,11 @@ struct isis_route_info { struct list *nexthops; }; +DECLARE_HOOK(isis_route_update_hook, + (struct isis_area * area, struct prefix *prefix, + struct isis_route_info *route_info), + (area, prefix, route_info)) + struct isis_route_info *isis_route_create(struct prefix *prefix, struct prefix_ipv6 *src_p, uint32_t cost, diff --git a/isisd/isis_tlvs.c b/isisd/isis_tlvs.c index ee253c7a31..bdf00b64cc 100644 --- a/isisd/isis_tlvs.c +++ b/isisd/isis_tlvs.c @@ -186,10 +186,10 @@ static int unpack_item_prefix_sid(uint16_t mtid, uint8_t len, struct stream *s, } sid.flags = stream_getc(s); - if ((sid.flags & ISIS_PREFIX_SID_VALUE) - != (sid.flags & ISIS_PREFIX_SID_LOCAL)) { + if (!!(sid.flags & ISIS_PREFIX_SID_VALUE) + != !!(sid.flags & ISIS_PREFIX_SID_LOCAL)) { sbuf_push(log, indent, "Flags inplausible: Local Flag needs to match Value Flag\n"); - return 0; + return 1; } sid.algorithm = stream_getc(s); diff --git a/isisd/isis_zebra.c b/isisd/isis_zebra.c index e8481a558b..d1bc20ba5a 100644 --- a/isisd/isis_zebra.c +++ b/isisd/isis_zebra.c @@ -219,9 +219,9 @@ static int isis_zebra_link_params(ZAPI_CALLBACK_ARGS) return 0; } -static void isis_zebra_route_add_route(struct prefix *prefix, - struct prefix_ipv6 *src_p, - struct isis_route_info *route_info) +void isis_zebra_route_add_route(struct prefix *prefix, + struct prefix_ipv6 *src_p, + struct isis_route_info *route_info) { struct zapi_route api; struct zapi_nexthop *api_nh; @@ -229,7 +229,7 @@ static void isis_zebra_route_add_route(struct prefix *prefix, struct listnode *node; int count = 0; - if (CHECK_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED)) + if (zclient->sock < 0) return; memset(&api, 0, sizeof(api)); @@ -292,17 +292,15 @@ static void isis_zebra_route_add_route(struct prefix *prefix, api.nexthop_num = count; zclient_route_send(ZEBRA_ROUTE_ADD, zclient, &api); - SET_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED); - UNSET_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_RESYNC); } -static void isis_zebra_route_del_route(struct prefix *prefix, - struct prefix_ipv6 *src_p, - struct isis_route_info *route_info) +void isis_zebra_route_del_route(struct prefix *prefix, + struct prefix_ipv6 *src_p, + struct isis_route_info *route_info) { struct zapi_route api; - if (!CHECK_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED)) + if (zclient->sock < 0) return; memset(&api, 0, sizeof(api)); @@ -316,20 +314,6 @@ static void isis_zebra_route_del_route(struct prefix *prefix, } zclient_route_send(ZEBRA_ROUTE_DELETE, zclient, &api); - UNSET_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ZEBRA_SYNCED); -} - -void isis_zebra_route_update(struct prefix *prefix, - struct prefix_ipv6 *src_p, - struct isis_route_info *route_info) -{ - if (zclient->sock < 0) - return; - - if (CHECK_FLAG(route_info->flag, ISIS_ROUTE_FLAG_ACTIVE)) - isis_zebra_route_add_route(prefix, src_p, route_info); - else - isis_zebra_route_del_route(prefix, src_p, route_info); } static int isis_zebra_read(ZAPI_CALLBACK_ARGS) diff --git a/isisd/isis_zebra.h b/isisd/isis_zebra.h index 20c10d0b23..d00f348c8e 100644 --- a/isisd/isis_zebra.h +++ b/isisd/isis_zebra.h @@ -29,9 +29,12 @@ void isis_zebra_stop(void); struct isis_route_info; -void isis_zebra_route_update(struct prefix *prefix, - struct prefix_ipv6 *src_p, - struct isis_route_info *route_info); +void isis_zebra_route_add_route(struct prefix *prefix, + struct prefix_ipv6 *src_p, + struct isis_route_info *route_info); +void isis_zebra_route_del_route(struct prefix *prefix, + struct prefix_ipv6 *src_p, + struct isis_route_info *route_info); int isis_distribute_list_update(int routetype); void isis_zebra_redistribute_set(afi_t afi, int type); void isis_zebra_redistribute_unset(afi_t afi, int type); diff --git a/isisd/isisd.h b/isisd/isisd.h index 393b1d67c7..308f018c19 100644 --- a/isisd/isisd.h +++ b/isisd/isisd.h @@ -58,7 +58,6 @@ extern struct zebra_privs_t isisd_privs; /* uncomment if you are a developer in bug hunt */ /* #define EXTREME_DEBUG */ -/* #define EXTREME_DICT_DEBUG */ struct fabricd;