mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-08-14 12:41:21 +00:00
isisd: update isis_tlvs_add_*_reach() with multi algorithm
isis_tlvs_add_extended_ip_reach adds IS-IS Extended IP reachability to the LSP. In this case, if the pcfg argument is not NULL, you can add IGP Prefix-SID as its sub tlv. Before this commit, only one Prefix-SID can be added. After this commit, the argument is not a single pointer but an array of pointers, and multiple Prefix-SIDs can be added. This feature is necessary because Flex-Algo requires multiple Prefix-SIDs for each Algorithm. Signed-off-by: Hiroki Shirokura <hiroki.shirokura@linecorp.com> Signed-off-by: Louis Scalbert <louis.scalbert@6wind.com>
This commit is contained in:
parent
e7948f8ce6
commit
0de7b43308
@ -904,14 +904,16 @@ static void lsp_build_ext_reach_ipv4(struct isis_lsp *lsp,
|
|||||||
isis_tlvs_add_oldstyle_ip_reach(lsp->tlvs, ipv4,
|
isis_tlvs_add_oldstyle_ip_reach(lsp->tlvs, ipv4,
|
||||||
metric);
|
metric);
|
||||||
if (area->newmetric) {
|
if (area->newmetric) {
|
||||||
struct sr_prefix_cfg *pcfg = NULL;
|
struct sr_prefix_cfg *pcfgs[SR_ALGORITHM_COUNT] = {
|
||||||
|
NULL};
|
||||||
|
|
||||||
if (area->srdb.enabled)
|
if (area->srdb.enabled)
|
||||||
pcfg = isis_sr_cfg_prefix_find(
|
for (int i = 0; i < SR_ALGORITHM_COUNT; i++)
|
||||||
area, ipv4, SR_ALGORITHM_SPF);
|
pcfgs[i] = isis_sr_cfg_prefix_find(
|
||||||
|
area, ipv4, i);
|
||||||
|
|
||||||
isis_tlvs_add_extended_ip_reach(lsp->tlvs, ipv4, metric,
|
isis_tlvs_add_extended_ip_reach(lsp->tlvs, ipv4, metric,
|
||||||
true, pcfg);
|
true, pcfgs);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -939,15 +941,17 @@ static void lsp_build_ext_reach_ipv6(struct isis_lsp *lsp,
|
|||||||
metric = MAX_WIDE_PATH_METRIC;
|
metric = MAX_WIDE_PATH_METRIC;
|
||||||
|
|
||||||
if (!src_p || !src_p->prefixlen) {
|
if (!src_p || !src_p->prefixlen) {
|
||||||
struct sr_prefix_cfg *pcfg = NULL;
|
struct sr_prefix_cfg *pcfgs[SR_ALGORITHM_COUNT] = {
|
||||||
|
NULL};
|
||||||
|
|
||||||
if (area->srdb.enabled)
|
if (area->srdb.enabled)
|
||||||
pcfg = isis_sr_cfg_prefix_find(
|
for (int i = 0; i < SR_ALGORITHM_COUNT; i++)
|
||||||
area, p, SR_ALGORITHM_SPF);
|
pcfgs[i] = isis_sr_cfg_prefix_find(
|
||||||
|
area, p, i);
|
||||||
|
|
||||||
isis_tlvs_add_ipv6_reach(lsp->tlvs,
|
isis_tlvs_add_ipv6_reach(lsp->tlvs,
|
||||||
isis_area_ipv6_topology(area),
|
isis_area_ipv6_topology(area),
|
||||||
p, metric, true, pcfg);
|
p, metric, true, pcfgs);
|
||||||
} else if (isis_area_ipv6_dstsrc_enabled(area)) {
|
} else if (isis_area_ipv6_dstsrc_enabled(area)) {
|
||||||
isis_tlvs_add_ipv6_dstsrc_reach(lsp->tlvs,
|
isis_tlvs_add_ipv6_dstsrc_reach(lsp->tlvs,
|
||||||
ISIS_MT_IPV6_DSTSRC,
|
ISIS_MT_IPV6_DSTSRC,
|
||||||
@ -1199,20 +1203,27 @@ static void lsp_build(struct isis_lsp *lsp, struct isis_area *area)
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (area->newmetric) {
|
if (area->newmetric) {
|
||||||
struct sr_prefix_cfg *pcfg = NULL;
|
struct sr_prefix_cfg
|
||||||
|
*pcfgs[SR_ALGORITHM_COUNT] = {
|
||||||
|
NULL};
|
||||||
|
|
||||||
lsp_debug(
|
lsp_debug(
|
||||||
"ISIS (%s): Adding te-style IP reachability for %pFX",
|
"ISIS (%s): Adding te-style IP reachability for %pFX",
|
||||||
area->area_tag, ipv4);
|
area->area_tag, ipv4);
|
||||||
|
|
||||||
if (area->srdb.enabled)
|
if (area->srdb.enabled)
|
||||||
pcfg = isis_sr_cfg_prefix_find(
|
for (int i = 0;
|
||||||
area, ipv4,
|
i < SR_ALGORITHM_COUNT;
|
||||||
SR_ALGORITHM_SPF);
|
i++)
|
||||||
|
pcfgs[i] =
|
||||||
|
isis_sr_cfg_prefix_find(
|
||||||
|
area,
|
||||||
|
ipv4,
|
||||||
|
i);
|
||||||
|
|
||||||
isis_tlvs_add_extended_ip_reach(
|
isis_tlvs_add_extended_ip_reach(
|
||||||
lsp->tlvs, ipv4, metric, false,
|
lsp->tlvs, ipv4, metric, false,
|
||||||
pcfg);
|
pcfgs);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1223,20 +1234,24 @@ static void lsp_build(struct isis_lsp *lsp, struct isis_area *area)
|
|||||||
|
|
||||||
for (ALL_LIST_ELEMENTS_RO(circuit->ipv6_non_link,
|
for (ALL_LIST_ELEMENTS_RO(circuit->ipv6_non_link,
|
||||||
ipnode, ipv6)) {
|
ipnode, ipv6)) {
|
||||||
struct sr_prefix_cfg *pcfg = NULL;
|
struct sr_prefix_cfg
|
||||||
|
*pcfgs[SR_ALGORITHM_COUNT] = {NULL};
|
||||||
|
|
||||||
lsp_debug(
|
lsp_debug(
|
||||||
"ISIS (%s): Adding IPv6 reachability for %pFX",
|
"ISIS (%s): Adding IPv6 reachability for %pFX",
|
||||||
area->area_tag, ipv6);
|
area->area_tag, ipv6);
|
||||||
|
|
||||||
if (area->srdb.enabled)
|
if (area->srdb.enabled)
|
||||||
pcfg = isis_sr_cfg_prefix_find(area,
|
for (int i = 0; i < SR_ALGORITHM_COUNT;
|
||||||
ipv6, 0);
|
i++)
|
||||||
|
pcfgs[i] =
|
||||||
|
isis_sr_cfg_prefix_find(
|
||||||
|
area, ipv6, i);
|
||||||
|
|
||||||
isis_tlvs_add_ipv6_reach(
|
isis_tlvs_add_ipv6_reach(
|
||||||
lsp->tlvs,
|
lsp->tlvs,
|
||||||
isis_area_ipv6_topology(area), ipv6,
|
isis_area_ipv6_topology(area), ipv6,
|
||||||
metric, false, pcfg);
|
metric, false, pcfgs);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5873,40 +5873,57 @@ void isis_tlvs_del_lan_adj_sid(struct isis_ext_subtlvs *exts,
|
|||||||
|
|
||||||
void isis_tlvs_add_extended_ip_reach(struct isis_tlvs *tlvs,
|
void isis_tlvs_add_extended_ip_reach(struct isis_tlvs *tlvs,
|
||||||
struct prefix_ipv4 *dest, uint32_t metric,
|
struct prefix_ipv4 *dest, uint32_t metric,
|
||||||
bool external, struct sr_prefix_cfg *pcfg)
|
bool external,
|
||||||
|
struct sr_prefix_cfg **pcfgs)
|
||||||
{
|
{
|
||||||
struct isis_extended_ip_reach *r = XCALLOC(MTYPE_ISIS_TLV, sizeof(*r));
|
struct isis_extended_ip_reach *r = XCALLOC(MTYPE_ISIS_TLV, sizeof(*r));
|
||||||
|
|
||||||
r->metric = metric;
|
r->metric = metric;
|
||||||
memcpy(&r->prefix, dest, sizeof(*dest));
|
memcpy(&r->prefix, dest, sizeof(*dest));
|
||||||
apply_mask_ipv4(&r->prefix);
|
apply_mask_ipv4(&r->prefix);
|
||||||
if (pcfg) {
|
|
||||||
struct isis_prefix_sid *psid =
|
|
||||||
XCALLOC(MTYPE_ISIS_SUBTLV, sizeof(*psid));
|
|
||||||
|
|
||||||
isis_sr_prefix_cfg2subtlv(pcfg, external, psid);
|
if (pcfgs) {
|
||||||
r->subtlvs = isis_alloc_subtlvs(ISIS_CONTEXT_SUBTLV_IP_REACH);
|
r->subtlvs = isis_alloc_subtlvs(ISIS_CONTEXT_SUBTLV_IP_REACH);
|
||||||
append_item(&r->subtlvs->prefix_sids, (struct isis_item *)psid);
|
for (int i = 0; i < SR_ALGORITHM_COUNT; i++) {
|
||||||
|
struct isis_prefix_sid *psid;
|
||||||
|
struct sr_prefix_cfg *pcfg = pcfgs[i];
|
||||||
|
|
||||||
|
if (!pcfg)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
psid = XCALLOC(MTYPE_ISIS_SUBTLV, sizeof(*psid));
|
||||||
|
isis_sr_prefix_cfg2subtlv(pcfg, external, psid);
|
||||||
|
append_item(&r->subtlvs->prefix_sids,
|
||||||
|
(struct isis_item *)psid);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
append_item(&tlvs->extended_ip_reach, (struct isis_item *)r);
|
append_item(&tlvs->extended_ip_reach, (struct isis_item *)r);
|
||||||
}
|
}
|
||||||
|
|
||||||
void isis_tlvs_add_ipv6_reach(struct isis_tlvs *tlvs, uint16_t mtid,
|
void isis_tlvs_add_ipv6_reach(struct isis_tlvs *tlvs, uint16_t mtid,
|
||||||
struct prefix_ipv6 *dest, uint32_t metric,
|
struct prefix_ipv6 *dest, uint32_t metric,
|
||||||
bool external, struct sr_prefix_cfg *pcfg)
|
bool external, struct sr_prefix_cfg **pcfgs)
|
||||||
{
|
{
|
||||||
struct isis_ipv6_reach *r = XCALLOC(MTYPE_ISIS_TLV, sizeof(*r));
|
struct isis_ipv6_reach *r = XCALLOC(MTYPE_ISIS_TLV, sizeof(*r));
|
||||||
|
|
||||||
r->metric = metric;
|
r->metric = metric;
|
||||||
memcpy(&r->prefix, dest, sizeof(*dest));
|
memcpy(&r->prefix, dest, sizeof(*dest));
|
||||||
apply_mask_ipv6(&r->prefix);
|
apply_mask_ipv6(&r->prefix);
|
||||||
if (pcfg) {
|
if (pcfgs) {
|
||||||
struct isis_prefix_sid *psid =
|
|
||||||
XCALLOC(MTYPE_ISIS_SUBTLV, sizeof(*psid));
|
|
||||||
|
|
||||||
isis_sr_prefix_cfg2subtlv(pcfg, external, psid);
|
|
||||||
r->subtlvs = isis_alloc_subtlvs(ISIS_CONTEXT_SUBTLV_IP_REACH);
|
r->subtlvs = isis_alloc_subtlvs(ISIS_CONTEXT_SUBTLV_IP_REACH);
|
||||||
append_item(&r->subtlvs->prefix_sids, (struct isis_item *)psid);
|
for (int i = 0; i < SR_ALGORITHM_COUNT; i++) {
|
||||||
|
struct isis_prefix_sid *psid;
|
||||||
|
struct sr_prefix_cfg *pcfg = pcfgs[i];
|
||||||
|
|
||||||
|
if (!pcfg)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
psid = XCALLOC(MTYPE_ISIS_SUBTLV, sizeof(*psid));
|
||||||
|
isis_sr_prefix_cfg2subtlv(pcfg, external, psid);
|
||||||
|
append_item(&r->subtlvs->prefix_sids,
|
||||||
|
(struct isis_item *)psid);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
struct isis_item_list *l;
|
struct isis_item_list *l;
|
||||||
|
@ -571,10 +571,11 @@ void isis_tlvs_add_oldstyle_ip_reach(struct isis_tlvs *tlvs,
|
|||||||
struct prefix_ipv4 *dest, uint8_t metric);
|
struct prefix_ipv4 *dest, uint8_t metric);
|
||||||
void isis_tlvs_add_extended_ip_reach(struct isis_tlvs *tlvs,
|
void isis_tlvs_add_extended_ip_reach(struct isis_tlvs *tlvs,
|
||||||
struct prefix_ipv4 *dest, uint32_t metric,
|
struct prefix_ipv4 *dest, uint32_t metric,
|
||||||
bool external, struct sr_prefix_cfg *pcfg);
|
bool external,
|
||||||
|
struct sr_prefix_cfg **pcfgs);
|
||||||
void isis_tlvs_add_ipv6_reach(struct isis_tlvs *tlvs, uint16_t mtid,
|
void isis_tlvs_add_ipv6_reach(struct isis_tlvs *tlvs, uint16_t mtid,
|
||||||
struct prefix_ipv6 *dest, uint32_t metric,
|
struct prefix_ipv6 *dest, uint32_t metric,
|
||||||
bool external, struct sr_prefix_cfg *pcfg);
|
bool external, struct sr_prefix_cfg **pcfgs);
|
||||||
void isis_tlvs_add_ipv6_dstsrc_reach(struct isis_tlvs *tlvs, uint16_t mtid,
|
void isis_tlvs_add_ipv6_dstsrc_reach(struct isis_tlvs *tlvs, uint16_t mtid,
|
||||||
struct prefix_ipv6 *dest,
|
struct prefix_ipv6 *dest,
|
||||||
struct prefix_ipv6 *src,
|
struct prefix_ipv6 *src,
|
||||||
|
@ -98,7 +98,7 @@ static void lsp_add_ip_reach(struct isis_lsp *lsp,
|
|||||||
{
|
{
|
||||||
struct prefix prefix;
|
struct prefix prefix;
|
||||||
struct sr_prefix_cfg pcfg = {};
|
struct sr_prefix_cfg pcfg = {};
|
||||||
struct sr_prefix_cfg *pcfg_p = NULL;
|
struct sr_prefix_cfg *pcfg_p[SR_ALGORITHM_COUNT] = {NULL};
|
||||||
|
|
||||||
if (str2prefix(prefix_str, &prefix) != 1) {
|
if (str2prefix(prefix_str, &prefix) != 1) {
|
||||||
zlog_debug("%s: invalid network: %s", __func__, prefix_str);
|
zlog_debug("%s: invalid network: %s", __func__, prefix_str);
|
||||||
@ -106,7 +106,7 @@ static void lsp_add_ip_reach(struct isis_lsp *lsp,
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (CHECK_FLAG(tnode->flags, F_ISIS_TEST_NODE_SR)) {
|
if (CHECK_FLAG(tnode->flags, F_ISIS_TEST_NODE_SR)) {
|
||||||
pcfg_p = &pcfg;
|
pcfg_p[SR_ALGORITHM_SPF] = &pcfg;
|
||||||
|
|
||||||
pcfg.sid = *next_sid_index;
|
pcfg.sid = *next_sid_index;
|
||||||
*next_sid_index = *next_sid_index + 1;
|
*next_sid_index = *next_sid_index + 1;
|
||||||
|
Loading…
Reference in New Issue
Block a user