mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-07-03 09:38:49 +00:00
isisd: Prepare IS-IS for Link State support
In order to provide Link State Traffic Engineering features to IS-IS, this patch adds some modifications to base IS-IS: - Solve bug in lsp iterate function to avoid infinite loop in isis_lsp.c by adding condition to recurse call - Add new trigger event to parse LSP in isis_lsp.c - Add new TE debug flag to track Traffic Engineering events in isisd.[c,h] - Correct small bug in isis_tlvs.c where delay and min/max delay are not correctly handle - Handle Opaque LSA Traffic Engineering Zebra API in isis_zebra.[c,h] Signed-off-by: Olivier Dugeon <olivier.dugeon@orange.com>
This commit is contained in:
parent
8693b4d66e
commit
d9884a758c
@ -124,6 +124,8 @@ static void lsp_destroy(struct isis_lsp *lsp)
|
||||
|
||||
ISIS_FLAGS_CLEAR_ALL(lsp->SSNflags);
|
||||
|
||||
isis_te_lsp_event(lsp, LSP_DEL);
|
||||
|
||||
lsp_clear_data(lsp);
|
||||
|
||||
if (!LSP_FRAGMENT(lsp->hdr.lsp_id)) {
|
||||
@ -335,6 +337,7 @@ void lsp_inc_seqno(struct isis_lsp *lsp, uint32_t seqno)
|
||||
|
||||
lsp_pack_pdu(lsp);
|
||||
isis_spf_schedule(lsp->area, lsp->level);
|
||||
isis_te_lsp_event(lsp, LSP_INC);
|
||||
}
|
||||
|
||||
static void lsp_purge_add_poi(struct isis_lsp *lsp,
|
||||
@ -570,8 +573,10 @@ void lsp_update(struct isis_lsp *lsp, struct isis_lsp_hdr *hdr,
|
||||
lsp_link_fragment(lsp, lsp0);
|
||||
}
|
||||
|
||||
if (lsp->hdr.seqno)
|
||||
if (lsp->hdr.seqno) {
|
||||
isis_spf_schedule(lsp->area, lsp->level);
|
||||
isis_te_lsp_event(lsp, LSP_UPD);
|
||||
}
|
||||
}
|
||||
|
||||
/* creation of LSP directly from what we received */
|
||||
@ -636,8 +641,10 @@ struct isis_lsp *lsp_new(struct isis_area *area, uint8_t *lsp_id,
|
||||
void lsp_insert(struct lspdb_head *head, struct isis_lsp *lsp)
|
||||
{
|
||||
lspdb_add(head, lsp);
|
||||
if (lsp->hdr.seqno)
|
||||
if (lsp->hdr.seqno) {
|
||||
isis_spf_schedule(lsp->area, lsp->level);
|
||||
isis_te_lsp_event(lsp, LSP_ADD);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1030,6 +1037,10 @@ static void lsp_build(struct isis_lsp *lsp, struct isis_area *area)
|
||||
cap.srlb.lower_bound = srdb->config.srlb_lower_bound;
|
||||
/* And finally MSD */
|
||||
cap.msd = srdb->config.msd;
|
||||
} else {
|
||||
/* Disable SR Algorithm */
|
||||
cap.algo[0] = SR_ALGORITHM_UNSET;
|
||||
cap.algo[1] = SR_ALGORITHM_UNSET;
|
||||
}
|
||||
|
||||
isis_tlvs_set_router_capability(lsp->tlvs, &cap);
|
||||
@ -2012,6 +2023,7 @@ int lsp_tick(struct thread *thread)
|
||||
/* 7.3.16.4 c) record the time to purge
|
||||
* FIXME */
|
||||
isis_spf_schedule(lsp->area, lsp->level);
|
||||
isis_te_lsp_event(lsp, LSP_TICK);
|
||||
}
|
||||
|
||||
if (lsp->age_out == 0) {
|
||||
@ -2166,7 +2178,7 @@ int isis_lsp_iterate_ip_reach(struct isis_lsp *lsp, int family, uint16_t mtid,
|
||||
if (lsp->hdr.seqno == 0 || lsp->hdr.rem_lifetime == 0)
|
||||
return LSP_ITER_CONTINUE;
|
||||
|
||||
/* Parse main LSP. */
|
||||
/* Parse LSP */
|
||||
if (lsp->tlvs) {
|
||||
if (!fabricd && !pseudo_lsp && family == AF_INET
|
||||
&& mtid == ISIS_MT_IPV4_UNICAST) {
|
||||
@ -2236,12 +2248,16 @@ int isis_lsp_iterate_ip_reach(struct isis_lsp *lsp, int family, uint16_t mtid,
|
||||
}
|
||||
}
|
||||
|
||||
/* Parse LSP fragments. */
|
||||
/* Parse LSP fragments if it is not a fragment itself */
|
||||
if (!LSP_FRAGMENT(lsp->hdr.lsp_id))
|
||||
for (ALL_LIST_ELEMENTS_RO(lsp->lspu.frags, node, frag)) {
|
||||
if (!frag->tlvs)
|
||||
continue;
|
||||
|
||||
isis_lsp_iterate_ip_reach(frag, family, mtid, cb, arg);
|
||||
if (isis_lsp_iterate_ip_reach(frag, family, mtid, cb,
|
||||
arg)
|
||||
== LSP_ITER_STOP)
|
||||
return LSP_ITER_STOP;
|
||||
}
|
||||
|
||||
return LSP_ITER_CONTINUE;
|
||||
@ -2263,7 +2279,7 @@ int isis_lsp_iterate_is_reach(struct isis_lsp *lsp, uint16_t mtid,
|
||||
if (lsp->hdr.seqno == 0 || lsp->hdr.rem_lifetime == 0)
|
||||
return LSP_ITER_CONTINUE;
|
||||
|
||||
/* Parse main LSP. */
|
||||
/* Parse LSP */
|
||||
if (lsp->tlvs) {
|
||||
if (pseudo_lsp || mtid == ISIS_MT_IPV4_UNICAST) {
|
||||
head = lsp->tlvs->oldstyle_reach.head;
|
||||
@ -2295,12 +2311,15 @@ int isis_lsp_iterate_is_reach(struct isis_lsp *lsp, uint16_t mtid,
|
||||
}
|
||||
}
|
||||
|
||||
/* Parse LSP fragments. */
|
||||
/* Parse LSP fragments if it not a fragment itself. */
|
||||
if (!LSP_FRAGMENT(lsp->hdr.lsp_id))
|
||||
for (ALL_LIST_ELEMENTS_RO(lsp->lspu.frags, node, frag)) {
|
||||
if (!frag->tlvs)
|
||||
continue;
|
||||
|
||||
isis_lsp_iterate_is_reach(frag, mtid, cb, arg);
|
||||
if (isis_lsp_iterate_is_reach(frag, mtid, cb, arg)
|
||||
== LSP_ITER_STOP)
|
||||
return LSP_ITER_STOP;
|
||||
}
|
||||
|
||||
return LSP_ITER_CONTINUE;
|
||||
|
@ -38,6 +38,7 @@
|
||||
#include "vrf.h"
|
||||
#include "libfrr.h"
|
||||
#include "bfd.h"
|
||||
#include "link_state.h"
|
||||
|
||||
#include "isisd/isis_constants.h"
|
||||
#include "isisd/isis_common.h"
|
||||
@ -747,6 +748,25 @@ static void isis_zebra_connected(struct zclient *zclient)
|
||||
bfd_client_sendmsg(zclient, ZEBRA_BFD_CLIENT_REGISTER, VRF_DEFAULT);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register / unregister Link State ZAPI Opaque Message
|
||||
*
|
||||
* @param up True to register, false to unregister
|
||||
*
|
||||
* @return 0 if success, -1 otherwise
|
||||
*/
|
||||
int isis_zebra_ls_register(bool up)
|
||||
{
|
||||
int rc;
|
||||
|
||||
if (up)
|
||||
rc = ls_register(zclient, true);
|
||||
else
|
||||
rc = ls_unregister(zclient, true);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
/*
|
||||
* opaque messages between processes
|
||||
*/
|
||||
@ -754,6 +774,7 @@ static int isis_opaque_msg_handler(ZAPI_CALLBACK_ARGS)
|
||||
{
|
||||
struct stream *s;
|
||||
struct zapi_opaque_msg info;
|
||||
struct zapi_opaque_reg_info dst;
|
||||
struct ldp_igp_sync_if_state state;
|
||||
struct ldp_igp_sync_announce announce;
|
||||
struct zapi_rlfa_response rlfa;
|
||||
@ -764,6 +785,13 @@ static int isis_opaque_msg_handler(ZAPI_CALLBACK_ARGS)
|
||||
return -1;
|
||||
|
||||
switch (info.type) {
|
||||
case LINK_STATE_SYNC:
|
||||
STREAM_GETC(s, dst.proto);
|
||||
STREAM_GETW(s, dst.instance);
|
||||
STREAM_GETL(s, dst.session_id);
|
||||
dst.type = LINK_STATE_SYNC;
|
||||
ret = isis_te_sync_ted(dst);
|
||||
break;
|
||||
case LDP_IGP_SYNC_IF_STATE_UPDATE:
|
||||
STREAM_GET(&state, s, sizeof(state));
|
||||
ret = isis_ldp_sync_state_update(state);
|
||||
|
@ -67,5 +67,6 @@ int isis_zebra_request_label_range(uint32_t base, uint32_t chunk_size);
|
||||
int isis_zebra_release_label_range(uint32_t start, uint32_t end);
|
||||
void isis_zebra_vrf_register(struct isis *isis);
|
||||
void isis_zebra_vrf_deregister(struct isis *isis);
|
||||
int isis_zebra_ls_register(bool up);
|
||||
|
||||
#endif /* _ZEBRA_ISIS_ZEBRA_H */
|
||||
|
@ -81,6 +81,7 @@ unsigned long debug_tx_queue;
|
||||
unsigned long debug_sr;
|
||||
unsigned long debug_ldp_sync;
|
||||
unsigned long debug_lfa;
|
||||
unsigned long debug_te;
|
||||
|
||||
DEFINE_MGROUP(ISISD, "isisd");
|
||||
|
||||
@ -1419,6 +1420,10 @@ void print_debug(struct vty *vty, int flags, int onoff)
|
||||
if (flags & DEBUG_SR)
|
||||
vty_out(vty, "IS-IS Segment Routing events debugging is %s\n",
|
||||
onoffs);
|
||||
if (flags & DEBUG_TE)
|
||||
vty_out(vty,
|
||||
"IS-IS Traffic Engineering events debugging is %s\n",
|
||||
onoffs);
|
||||
if (flags & DEBUG_LFA)
|
||||
vty_out(vty, "IS-IS LFA events debugging is %s\n", onoffs);
|
||||
if (flags & DEBUG_UPDATE_PACKETS)
|
||||
@ -1461,6 +1466,8 @@ DEFUN_NOSH (show_debugging,
|
||||
print_debug(vty, DEBUG_SPF_EVENTS, 1);
|
||||
if (IS_DEBUG_SR)
|
||||
print_debug(vty, DEBUG_SR, 1);
|
||||
if (IS_DEBUG_TE)
|
||||
print_debug(vty, DEBUG_TE, 1);
|
||||
if (IS_DEBUG_UPDATE_PACKETS)
|
||||
print_debug(vty, DEBUG_UPDATE_PACKETS, 1);
|
||||
if (IS_DEBUG_RTE_EVENTS)
|
||||
@ -1518,6 +1525,10 @@ static int config_write_debug(struct vty *vty)
|
||||
vty_out(vty, "debug " PROTO_NAME " sr-events\n");
|
||||
write++;
|
||||
}
|
||||
if (IS_DEBUG_TE) {
|
||||
vty_out(vty, "debug " PROTO_NAME " te-events\n");
|
||||
write++;
|
||||
}
|
||||
if (IS_DEBUG_LFA) {
|
||||
vty_out(vty, "debug " PROTO_NAME " lfa\n");
|
||||
write++;
|
||||
@ -1752,6 +1763,33 @@ DEFUN (no_debug_isis_srevents,
|
||||
return CMD_SUCCESS;
|
||||
}
|
||||
|
||||
DEFUN (debug_isis_teevents,
|
||||
debug_isis_teevents_cmd,
|
||||
"debug " PROTO_NAME " te-events",
|
||||
DEBUG_STR
|
||||
PROTO_HELP
|
||||
"IS-IS Traffic Engineering Events\n")
|
||||
{
|
||||
debug_te |= DEBUG_TE;
|
||||
print_debug(vty, DEBUG_TE, 1);
|
||||
|
||||
return CMD_SUCCESS;
|
||||
}
|
||||
|
||||
DEFUN (no_debug_isis_teevents,
|
||||
no_debug_isis_teevents_cmd,
|
||||
"no debug " PROTO_NAME " te-events",
|
||||
NO_STR
|
||||
UNDEBUG_STR
|
||||
PROTO_HELP
|
||||
"IS-IS Traffic Engineering Events\n")
|
||||
{
|
||||
debug_te &= ~DEBUG_TE;
|
||||
print_debug(vty, DEBUG_TE, 0);
|
||||
|
||||
return CMD_SUCCESS;
|
||||
}
|
||||
|
||||
DEFUN (debug_isis_lfa,
|
||||
debug_isis_lfa_cmd,
|
||||
"debug " PROTO_NAME " lfa",
|
||||
@ -3140,6 +3178,8 @@ void isis_init(void)
|
||||
install_element(ENABLE_NODE, &no_debug_isis_spfevents_cmd);
|
||||
install_element(ENABLE_NODE, &debug_isis_srevents_cmd);
|
||||
install_element(ENABLE_NODE, &no_debug_isis_srevents_cmd);
|
||||
install_element(ENABLE_NODE, &debug_isis_teevents_cmd);
|
||||
install_element(ENABLE_NODE, &no_debug_isis_teevents_cmd);
|
||||
install_element(ENABLE_NODE, &debug_isis_lfa_cmd);
|
||||
install_element(ENABLE_NODE, &no_debug_isis_lfa_cmd);
|
||||
install_element(ENABLE_NODE, &debug_isis_rtevents_cmd);
|
||||
@ -3171,6 +3211,8 @@ void isis_init(void)
|
||||
install_element(CONFIG_NODE, &no_debug_isis_spfevents_cmd);
|
||||
install_element(CONFIG_NODE, &debug_isis_srevents_cmd);
|
||||
install_element(CONFIG_NODE, &no_debug_isis_srevents_cmd);
|
||||
install_element(CONFIG_NODE, &debug_isis_teevents_cmd);
|
||||
install_element(CONFIG_NODE, &no_debug_isis_teevents_cmd);
|
||||
install_element(CONFIG_NODE, &debug_isis_lfa_cmd);
|
||||
install_element(CONFIG_NODE, &no_debug_isis_lfa_cmd);
|
||||
install_element(CONFIG_NODE, &debug_isis_rtevents_cmd);
|
||||
|
@ -331,6 +331,7 @@ extern unsigned long debug_tx_queue;
|
||||
extern unsigned long debug_sr;
|
||||
extern unsigned long debug_ldp_sync;
|
||||
extern unsigned long debug_lfa;
|
||||
extern unsigned long debug_te;
|
||||
|
||||
#define DEBUG_ADJ_PACKETS (1<<0)
|
||||
#define DEBUG_SNP_PACKETS (1<<1)
|
||||
@ -347,6 +348,7 @@ extern unsigned long debug_lfa;
|
||||
#define DEBUG_SR (1<<12)
|
||||
#define DEBUG_LDP_SYNC (1<<13)
|
||||
#define DEBUG_LFA (1<<14)
|
||||
#define DEBUG_TE (1<<15)
|
||||
|
||||
/* Debug related macro. */
|
||||
#define IS_DEBUG_ADJ_PACKETS (debug_adj_pkt & DEBUG_ADJ_PACKETS)
|
||||
@ -364,6 +366,7 @@ extern unsigned long debug_lfa;
|
||||
#define IS_DEBUG_SR (debug_sr & DEBUG_SR)
|
||||
#define IS_DEBUG_LDP_SYNC (debug_ldp_sync & DEBUG_LDP_SYNC)
|
||||
#define IS_DEBUG_LFA (debug_lfa & DEBUG_LFA)
|
||||
#define IS_DEBUG_TE (debug_te & DEBUG_TE)
|
||||
|
||||
#define lsp_debug(...) \
|
||||
do { \
|
||||
@ -383,6 +386,10 @@ extern unsigned long debug_lfa;
|
||||
zlog_debug(__VA_ARGS__); \
|
||||
} while (0)
|
||||
|
||||
#define DEBUG_TE DEBUG_LSP_GEN
|
||||
#define te_debug(...) \
|
||||
do { \
|
||||
if (IS_DEBUG_TE) \
|
||||
zlog_debug(__VA_ARGS__); \
|
||||
} while (0)
|
||||
|
||||
#endif /* ISISD_H */
|
||||
|
Loading…
Reference in New Issue
Block a user