From f1152a90051e5c068b5033a8a606034cbfdea4e3 Mon Sep 17 00:00:00 2001 From: Carmine Scarpitta Date: Wed, 22 Feb 2023 10:27:15 +0100 Subject: [PATCH] isisd: Extend SPF algo to process SRv6 locator Extend SPF algorithm to process SRv6 locator. Signed-off-by: Carmine Scarpitta --- isisd/isis_spf.c | 45 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/isisd/isis_spf.c b/isisd/isis_spf.c index e114467e07..a2230cd009 100644 --- a/isisd/isis_spf.c +++ b/isisd/isis_spf.c @@ -837,6 +837,7 @@ static int isis_spf_process_lsp(struct isis_spftree *spftree, struct isis_mt_router_info *mt_router_info = NULL; struct prefix_pair ip_info; bool has_valid_psid; + bool loc_is_in_ipv6_reach = false; if (isis_lfa_excise_node_check(spftree, lsp->hdr.lsp_id)) { if (IS_DEBUG_LFA) @@ -1128,6 +1129,50 @@ lspfragloop: process_N(spftree, vtype, &ip_info, dist, depth + 1, NULL, parent); } + + /* Process SRv6 Locator TLVs */ + + struct isis_item_list *srv6_locators = isis_lookup_mt_items( + &lsp->tlvs->srv6_locator, spftree->mtid); + + struct isis_srv6_locator_tlv *loc; + for (loc = srv6_locators ? (struct isis_srv6_locator_tlv *) + srv6_locators->head + : NULL; + loc; loc = loc->next) { + + if (loc->algorithm != SR_ALGORITHM_SPF) + continue; + + dist = cost + loc->metric; + vtype = VTYPE_IP6REACH_INTERNAL; + memset(&ip_info, 0, sizeof(ip_info)); + ip_info.dest.family = AF_INET6; + ip_info.dest.u.prefix6 = loc->prefix.prefix; + ip_info.dest.prefixlen = loc->prefix.prefixlen; + + /* An SRv6 Locator can be received in both a Prefix + Reachability TLV and an SRv6 Locator TLV (as per RFC + 9352 section #5). We go through the Prefix Reachability + TLVs and check if the SRv6 Locator is present in some of + them. If we find the SRv6 Locator in some Prefix + Reachbility TLV then it means that we have already + processed it before and we can skip it. */ + for (r = ipv6_reachs ? (struct isis_ipv6_reach *) + ipv6_reachs->head + : NULL; + r; r = r->next) { + if (prefix_same((struct prefix *)&r->prefix, + (struct prefix *)&loc->prefix)) + loc_is_in_ipv6_reach = true; + } + + /* SRv6 locator not present in Prefix Reachability TLV, + * let's process it */ + if (!loc_is_in_ipv6_reach) + process_N(spftree, vtype, &ip_info, dist, + depth + 1, NULL, parent); + } } end: -- 2.39.5