uint16_t psnp_interval[2]; /* psnp-interval in seconds */
uint8_t metric[2];
uint32_t te_metric[2];
- struct mpls_te_circuit *mtc; /* MPLS-TE parameters */
+ struct mpls_te_circuit
+ *mtc; /* Support for MPLS-TE parameters - see isis_te.[c,h] */
int ip_router; /* Route IP ? */
int is_passive; /* Is Passive ? */
struct list *mt_settings; /* IS-IS MT Settings */
}
/*
- * XPath: /frr-isisd:isis/instance/mpls-te
+ * XPath: /frr-isisd:isis/mpls-te
*/
DEFPY(isis_mpls_te_on, isis_mpls_te_on_cmd, "mpls-te on",
MPLS_TE_STR "Enable the MPLS-TE functionality\n")
{
- nb_cli_enqueue_change(vty, "./mpls-te", NB_OP_CREATE,
+ nb_cli_enqueue_change(vty, "/frr-isisd:isis/mpls-te", NB_OP_CREATE,
NULL);
return nb_cli_apply_changes(vty, NULL);
DEFPY(no_isis_mpls_te_on, no_isis_mpls_te_on_cmd, "no mpls-te [on]",
NO_STR
"Disable the MPLS-TE functionality\n"
- "Disable the MPLS-TE functionality\n")
+ "Enable the MPLS-TE functionality\n")
{
- nb_cli_enqueue_change(vty, "./mpls-te", NB_OP_DESTROY,
+ nb_cli_enqueue_change(vty, "/frr-isisd:isis/mpls-te", NB_OP_DESTROY,
NULL);
return nb_cli_apply_changes(vty, NULL);
}
/*
- * XPath: /frr-isisd:isis/instance/mpls-te/router-address
+ * XPath: /frr-isisd:isis/mpls-te/router-address
*/
DEFPY(isis_mpls_te_router_addr, isis_mpls_te_router_addr_cmd,
"mpls-te router-address A.B.C.D",
"Stable IP address of the advertising router\n"
"MPLS-TE router address in IPv4 address format\n")
{
- nb_cli_enqueue_change(vty, "./mpls-te/router-address",
+ nb_cli_enqueue_change(vty, "/frr-isisd:isis/mpls-te/router-address",
NB_OP_MODIFY, router_address_str);
return nb_cli_apply_changes(vty, NULL);
}
-DEFPY(no_isis_mpls_te_router_addr, no_isis_mpls_te_router_addr_cmd,
- "no mpls-te router-address [A.B.C.D]",
- NO_STR MPLS_TE_STR
- "Delete IP address of the advertising router\n"
- "MPLS-TE router address in IPv4 address format\n")
-{
- nb_cli_enqueue_change(vty, "./mpls-te/router-address",
- NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
void cli_show_isis_mpls_te_router_addr(struct vty *vty, struct lyd_node *dnode,
bool show_defaults)
{
"AREA native mode self originate INTER-AS LSP with L1 and L2 flooding scope\n"
"AS native mode self originate INTER-AS LSP with L2 only flooding scope\n")
{
- vty_out(vty, "MPLS-TE Inter-AS is not yet supported\n");
+ vty_out(vty, "MPLS-TE Inter-AS is not yet supported.");
return CMD_SUCCESS;
}
install_element(ISIS_NODE, &isis_mpls_te_on_cmd);
install_element(ISIS_NODE, &no_isis_mpls_te_on_cmd);
install_element(ISIS_NODE, &isis_mpls_te_router_addr_cmd);
- install_element(ISIS_NODE, &no_isis_mpls_te_router_addr_cmd);
install_element(ISIS_NODE, &isis_mpls_te_inter_as_cmd);
install_element(ISIS_NODE, &isis_default_originate_cmd);
uint8_t subtlvs[256];
uint8_t subtlv_len;
- if (IS_MPLS_TE(area->mta)
+ if (IS_MPLS_TE(isisMplsTE)
&& circuit->interface
&& HAS_LINK_PARAMS(
circuit->interface))
uint8_t subtlvs[256];
uint8_t subtlv_len;
- if (IS_MPLS_TE(area->mta)
+ if (IS_MPLS_TE(isisMplsTE)
&& circuit->interface != NULL
&& HAS_LINK_PARAMS(
circuit->interface))
}
/*
- * XPath: /frr-isisd:isis/instance/mpls-te
+ * XPath: /frr-isisd:isis/mpls-te
*/
-static int isis_instance_mpls_te_create(enum nb_event event,
+static int isis_mpls_te_create(enum nb_event event,
const struct lyd_node *dnode,
union nb_resource *resource)
{
struct listnode *node;
- struct isis_area *area;
struct isis_circuit *circuit;
if (event != NB_EV_APPLY)
return NB_OK;
- area = yang_dnode_get_entry(dnode, true);
- if (area->mta == NULL) {
-
- struct mpls_te_area *new;
-
- zlog_debug("ISIS MPLS-TE: Initialize area %s",
- area->area_tag);
-
- new = XCALLOC(MTYPE_ISIS_MPLS_TE, sizeof(struct mpls_te_area));
-
- /* Initialize MPLS_TE structure */
- new->status = enable;
- new->level = 0;
- new->inter_as = off;
- new->interas_areaid.s_addr = 0;
- new->router_id.s_addr = 0;
-
- area->mta = new;
- } else {
- area->mta->status = enable;
- }
+ isisMplsTE.status = enable;
/*
* Following code is intended to handle two cases;
* MPLS_TE flag
* 2) MPLS-TE was once enabled then disabled, and now enabled again.
*/
- for (ALL_LIST_ELEMENTS_RO(area->circuit_list, node, circuit)) {
+ for (ALL_LIST_ELEMENTS_RO(isisMplsTE.cir_list, node, circuit)) {
if (circuit->mtc == NULL || IS_FLOOD_AS(circuit->mtc->type))
continue;
- if (!IS_MPLS_TE(circuit->mtc)
+ if ((circuit->mtc->status == disable)
&& HAS_LINK_PARAMS(circuit->interface))
circuit->mtc->status = enable;
else
return NB_OK;
}
-static int isis_instance_mpls_te_destroy(enum nb_event event,
+static int isis_mpls_te_destroy(enum nb_event event,
const struct lyd_node *dnode)
{
struct listnode *node;
- struct isis_area *area;
struct isis_circuit *circuit;
if (event != NB_EV_APPLY)
return NB_OK;
- area = yang_dnode_get_entry(dnode, true);
- if (IS_MPLS_TE(area->mta))
- area->mta->status = disable;
- else
- return NB_OK;
+ isisMplsTE.status = disable;
/* Flush LSP if circuit engage */
- for (ALL_LIST_ELEMENTS_RO(area->circuit_list, node, circuit)) {
+ for (ALL_LIST_ELEMENTS_RO(isisMplsTE.cir_list, node, circuit)) {
if (circuit->mtc == NULL || (circuit->mtc->status == disable))
continue;
}
/*
- * XPath: /frr-isisd:isis/instance/mpls-te/router-address
+ * XPath: /frr-isisd:isis/mpls-te/router-address
*/
-static int isis_instance_mpls_te_router_address_modify(enum nb_event event,
+static int isis_mpls_te_router_address_modify(enum nb_event event,
const struct lyd_node *dnode,
union nb_resource *resource)
{
struct in_addr value;
+ struct listnode *node;
struct isis_area *area;
if (event != NB_EV_APPLY)
return NB_OK;
- area = yang_dnode_get_entry(dnode, true);
+ yang_dnode_get_ipv4(&value, dnode, NULL);
+ isisMplsTE.router_id.s_addr = value.s_addr;
/* only proceed if MPLS-TE is enabled */
- if (!IS_MPLS_TE(area->mta))
+ if (isisMplsTE.status == disable)
return NB_OK;
- /* Update Area Router ID */
- yang_dnode_get_ipv4(&value, dnode, NULL);
- area->mta->router_id.s_addr = value.s_addr;
-
+ /* Update main Router ID in isis global structure */
+ isis->router_id = value.s_addr;
/* And re-schedule LSP update */
- if (listcount(area->area_addrs) > 0)
- lsp_regenerate_schedule(area, area->is_type, 0);
+ for (ALL_LIST_ELEMENTS_RO(isis->area_list, node, area))
+ if (listcount(area->area_addrs) > 0)
+ lsp_regenerate_schedule(area, area->is_type, 0);
return NB_OK;
}
-static int isis_instance_mpls_te_router_address_destroy(enum nb_event event,
+static int isis_mpls_te_router_address_destroy(enum nb_event event,
const struct lyd_node *dnode)
{
+ struct listnode *node;
struct isis_area *area;
if (event != NB_EV_APPLY)
return NB_OK;
- area = yang_dnode_get_entry(dnode, true);
+ isisMplsTE.router_id.s_addr = INADDR_ANY;
/* only proceed if MPLS-TE is enabled */
- if (!IS_MPLS_TE(area->mta))
+ if (isisMplsTE.status == disable)
return NB_OK;
- /* Reset Area Router ID */
- area->mta->router_id.s_addr = INADDR_ANY;
-
+ /* Update main Router ID in isis global structure */
+ isis->router_id = 0;
/* And re-schedule LSP update */
- if (listcount(area->area_addrs) > 0)
- lsp_regenerate_schedule(area, area->is_type, 0);
+ for (ALL_LIST_ELEMENTS_RO(isis->area_list, node, area))
+ if (listcount(area->area_addrs) > 0)
+ lsp_regenerate_schedule(area, area->is_type, 0);
return NB_OK;
}
.cbs.cli_show = cli_show_isis_log_adjacency,
},
{
- .xpath = "/frr-isisd:isis/instance/mpls-te",
- .cbs.create = isis_instance_mpls_te_create,
- .cbs.destroy = isis_instance_mpls_te_destroy,
+ .xpath = "/frr-isisd:isis/mpls-te",
+ .cbs.create = isis_mpls_te_create,
+ .cbs.destroy = isis_mpls_te_destroy,
.cbs.cli_show = cli_show_isis_mpls_te,
},
{
- .xpath = "/frr-isisd:isis/instance/mpls-te/router-address",
- .cbs.modify = isis_instance_mpls_te_router_address_modify,
- .cbs.destroy = isis_instance_mpls_te_router_address_destroy,
+ .xpath = "/frr-isisd:isis/mpls-te/router-address",
+ .cbs.modify = isis_mpls_te_router_address_modify,
+ .cbs.destroy = isis_mpls_te_router_address_destroy,
.cbs.cli_show = cli_show_isis_mpls_te_router_addr,
},
{
adj);
/* Update MPLS TE Remote IP address parameter if possible */
- if (adj->ipv4_address_count && iih->circuit->area
- && IS_MPLS_TE(iih->circuit->area->mta)
- && IS_MPLS_TE(iih->circuit->mtc))
+ if (IS_MPLS_TE(isisMplsTE) && iih->circuit->mtc
+ && IS_CIRCUIT_TE(iih->circuit->mtc) && adj->ipv4_address_count)
set_circuitparams_rmt_ipaddr(iih->circuit->mtc,
adj->ipv4_addresses[0]);
#include "isisd/isis_spf.h"
#include "isisd/isis_te.h"
+/* Global varial for MPLS TE management */
+struct isis_mpls_te isisMplsTE;
+
const char *mode2text[] = {"Disable", "Area", "AS", "Emulate"};
/*------------------------------------------------------------------------*
/* Finally Update LSP */
#if 0
- if (circuit->area && IS_MPLS_TE(circuit->area->mta))
+ if (IS_MPLS_TE(isisMplsTE) && circuit->area)
lsp_regenerate_schedule (circuit->area, circuit->is_type, 0);
#endif
return;
isis_link_params_update(circuit, ifp);
/* ... and LSP */
- if (circuit->area && IS_MPLS_TE(circuit->area->mta))
+ if (IS_MPLS_TE(isisMplsTE) && circuit->area)
lsp_regenerate_schedule(circuit->area, circuit->is_type, 0);
return;
return;
}
+/* Specific MPLS TE router parameters write function */
+void isis_mpls_te_config_write_router(struct vty *vty)
+{
+ if (IS_MPLS_TE(isisMplsTE)) {
+ vty_out(vty, " mpls-te on\n");
+ vty_out(vty, " mpls-te router-address %s\n",
+ inet_ntoa(isisMplsTE.router_id));
+ }
+
+ return;
+}
+
+
/*------------------------------------------------------------------------*
* Followings are vty command functions.
*------------------------------------------------------------------------*/
#ifndef FABRICD
+/* Search MPLS TE Circuit context from Interface */
+static struct mpls_te_circuit *lookup_mpls_params_by_ifp(struct interface *ifp)
+{
+ struct isis_circuit *circuit;
+
+ if ((circuit = circuit_scan_by_ifp(ifp)) == NULL)
+ return NULL;
+
+ return circuit->mtc;
+}
+
DEFUN (show_isis_mpls_te_router,
show_isis_mpls_te_router_cmd,
"show " PROTO_NAME " mpls-te router",
MPLS_TE_STR
"Router information\n")
{
+ if (IS_MPLS_TE(isisMplsTE)) {
+ vty_out(vty, "--- MPLS-TE router parameters ---\n");
- struct listnode *anode;
- struct isis_area *area;
-
- if (!isis) {
- vty_out(vty, "IS-IS Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- for (ALL_LIST_ELEMENTS_RO(isis->area_list, anode, area)) {
-
- if (!IS_MPLS_TE(area->mta))
- continue;
-
- vty_out(vty, "Area %s:\n", area->area_tag);
- if (ntohs(area->mta->router_id.s_addr) != 0)
- vty_out(vty, " MPLS-TE Router-Address: %s\n",
- inet_ntoa(area->mta->router_id));
+ if (ntohs(isisMplsTE.router_id.s_addr) != 0)
+ vty_out(vty, " Router-Address: %s\n",
+ inet_ntoa(isisMplsTE.router_id));
else
vty_out(vty, " N/A\n");
- }
+ } else
+ vty_out(vty, " MPLS-TE is disable on this router\n");
return CMD_SUCCESS;
}
-static void show_mpls_te_sub(struct vty *vty, char *name,
- struct mpls_te_circuit *mtc)
+static void show_mpls_te_sub(struct vty *vty, struct interface *ifp)
{
+ struct mpls_te_circuit *mtc;
struct sbuf buf;
sbuf_init(&buf, NULL, 0);
- if (mtc->status != enable)
- return;
+ if ((IS_MPLS_TE(isisMplsTE))
+ && ((mtc = lookup_mpls_params_by_ifp(ifp)) != NULL)) {
+ /* Continue only if interface is not passive or support Inter-AS
+ * TEv2 */
+ if (mtc->status != enable) {
+ if (IS_INTER_AS(mtc->type)) {
+ vty_out(vty,
+ "-- Inter-AS TEv2 link parameters for %s --\n",
+ ifp->name);
+ } else {
+ /* MPLS-TE is not activate on this interface */
+ /* or this interface is passive and Inter-AS
+ * TEv2 is not activate */
+ vty_out(vty,
+ " %s: MPLS-TE is disabled on this interface\n",
+ ifp->name);
+ return;
+ }
+ } else {
+ vty_out(vty, "-- MPLS-TE link parameters for %s --\n",
+ ifp->name);
+ }
- vty_out(vty, "-- MPLS-TE link parameters for %s --\n", name);
+ sbuf_reset(&buf);
+ print_subtlv_admin_grp(&buf, 4, &mtc->admin_grp);
- sbuf_reset(&buf);
- print_subtlv_admin_grp(&buf, 4, &mtc->admin_grp);
+ if (SUBTLV_TYPE(mtc->local_ipaddr) != 0)
+ print_subtlv_local_ipaddr(&buf, 4, &mtc->local_ipaddr);
+ if (SUBTLV_TYPE(mtc->rmt_ipaddr) != 0)
+ print_subtlv_rmt_ipaddr(&buf, 4, &mtc->rmt_ipaddr);
- if (SUBTLV_TYPE(mtc->local_ipaddr) != 0)
- print_subtlv_local_ipaddr(&buf, 4, &mtc->local_ipaddr);
- if (SUBTLV_TYPE(mtc->rmt_ipaddr) != 0)
- print_subtlv_rmt_ipaddr(&buf, 4, &mtc->rmt_ipaddr);
-
- print_subtlv_max_bw(&buf, 4, &mtc->max_bw);
- print_subtlv_max_rsv_bw(&buf, 4, &mtc->max_rsv_bw);
- print_subtlv_unrsv_bw(&buf, 4, &mtc->unrsv_bw);
- print_subtlv_te_metric(&buf, 4, &mtc->te_metric);
-
- if (IS_INTER_AS(mtc->type)) {
- if (SUBTLV_TYPE(mtc->ras) != 0)
- print_subtlv_ras(&buf, 4, &mtc->ras);
- if (SUBTLV_TYPE(mtc->rip) != 0)
- print_subtlv_rip(&buf, 4, &mtc->rip);
- }
+ print_subtlv_max_bw(&buf, 4, &mtc->max_bw);
+ print_subtlv_max_rsv_bw(&buf, 4, &mtc->max_rsv_bw);
+ print_subtlv_unrsv_bw(&buf, 4, &mtc->unrsv_bw);
+ print_subtlv_te_metric(&buf, 4, &mtc->te_metric);
- print_subtlv_av_delay(&buf, 4, &mtc->av_delay);
- print_subtlv_mm_delay(&buf, 4, &mtc->mm_delay);
- print_subtlv_delay_var(&buf, 4, &mtc->delay_var);
- print_subtlv_pkt_loss(&buf, 4, &mtc->pkt_loss);
- print_subtlv_res_bw(&buf, 4, &mtc->res_bw);
- print_subtlv_ava_bw(&buf, 4, &mtc->ava_bw);
- print_subtlv_use_bw(&buf, 4, &mtc->use_bw);
+ if (IS_INTER_AS(mtc->type)) {
+ if (SUBTLV_TYPE(mtc->ras) != 0)
+ print_subtlv_ras(&buf, 4, &mtc->ras);
+ if (SUBTLV_TYPE(mtc->rip) != 0)
+ print_subtlv_rip(&buf, 4, &mtc->rip);
+ }
+
+ print_subtlv_av_delay(&buf, 4, &mtc->av_delay);
+ print_subtlv_mm_delay(&buf, 4, &mtc->mm_delay);
+ print_subtlv_delay_var(&buf, 4, &mtc->delay_var);
+ print_subtlv_pkt_loss(&buf, 4, &mtc->pkt_loss);
+ print_subtlv_res_bw(&buf, 4, &mtc->res_bw);
+ print_subtlv_ava_bw(&buf, 4, &mtc->ava_bw);
+ print_subtlv_use_bw(&buf, 4, &mtc->use_bw);
- vty_multiline(vty, "", "%s", sbuf_buf(&buf));
- vty_out(vty, "---------------\n\n");
+ vty_multiline(vty, "", "%s", sbuf_buf(&buf));
+ vty_out(vty, "---------------\n\n");
+ } else {
+ vty_out(vty, " %s: MPLS-TE is disabled on this interface\n",
+ ifp->name);
+ }
sbuf_free(&buf);
return;
"Interface information\n"
"Interface name\n")
{
- struct listnode *anode, *cnode;
- struct isis_area *area;
- struct isis_circuit *circuit;
- struct interface *ifp;
+ struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
int idx_interface = 4;
+ struct interface *ifp;
- if (!isis) {
- vty_out(vty, "IS-IS Routing Process not enabled\n");
- return CMD_SUCCESS;
+ /* Show All Interfaces. */
+ if (argc == 4) {
+ FOR_ALL_INTERFACES (vrf, ifp)
+ show_mpls_te_sub(vty, ifp);
}
-
- if (argc == idx_interface) {
- /* Show All Interfaces. */
- for (ALL_LIST_ELEMENTS_RO(isis->area_list, anode, area)) {
-
- if (!IS_MPLS_TE(area->mta))
- continue;
-
- vty_out(vty, "Area %s:\n", area->area_tag);
-
- for (ALL_LIST_ELEMENTS_RO(area->circuit_list, cnode,
- circuit))
- show_mpls_te_sub(vty, circuit->interface->name,
- circuit->mtc);
- }
- } else {
- /* Interface name is specified. */
- ifp = if_lookup_by_name(argv[idx_interface]->arg, VRF_DEFAULT);
- if (ifp == NULL)
+ /* Interface name is specified. */
+ else {
+ if ((ifp = if_lookup_by_name(argv[idx_interface]->arg,
+ VRF_DEFAULT))
+ == NULL)
vty_out(vty, "No such interface name\n");
- else {
- circuit = circuit_scan_by_ifp(ifp);
- if (!circuit)
- vty_out(vty,
- "ISIS is not enabled on circuit %s\n",
- ifp->name);
- else
- show_mpls_te_sub(vty, ifp->name, circuit->mtc);
- }
+ else
+ show_mpls_te_sub(vty, ifp);
}
return CMD_SUCCESS;
void isis_mpls_te_init(void)
{
+ zlog_debug("ISIS MPLS-TE: Initialize");
+
+ /* Initialize MPLS_TE structure */
+ isisMplsTE.status = disable;
+ isisMplsTE.level = 0;
+ isisMplsTE.inter_as = off;
+ isisMplsTE.interas_areaid.s_addr = 0;
+ isisMplsTE.cir_list = list_new();
+ isisMplsTE.router_id.s_addr = 0;
+
#ifndef FABRICD
/* Register new VTY commands */
install_element(VIEW_NODE, &show_isis_mpls_te_router_cmd);
/* Mode for Inter-AS LSP */ /* TODO: Check how if LSP is flooded in RFC5316 */
typedef enum _interas_mode_t { off, region, as, emulate } interas_mode_t;
-#define IS_MPLS_TE(m) (m && m->status == enable)
+#define IS_MPLS_TE(m) (m.status == enable)
+#define IS_CIRCUIT_TE(c) (c->status == enable)
-/* Per area MPLS-TE parameters */
-struct mpls_te_area {
+/* Following structure are internal use only. */
+struct isis_mpls_te {
/* Status of MPLS-TE: enable or disable */
status_t status;
interas_mode_t inter_as;
struct in_addr interas_areaid;
+ /* Circuit list on which TE are enable */
+ struct list *cir_list;
+
/* MPLS_TE router ID */
struct in_addr router_id;
};
-/* Per Circuit MPLS-TE parameters */
+extern struct isis_mpls_te isisMplsTE;
+
struct mpls_te_circuit {
/* Status of MPLS-TE on this interface */
uint8_t build_te_subtlvs(uint8_t *, struct isis_circuit *);
void isis_link_params_update(struct isis_circuit *, struct interface *);
void isis_mpls_te_update(struct interface *);
+void isis_mpls_te_config_write_router(struct vty *);
#endif /* _ZEBRA_ISIS_MPLS_TE_H */
struct listnode *node;
struct prefix router_id;
+ /*
+ * If ISIS TE is enable, TE Router ID is set through specific command.
+ * See mpls_te_router_addr() command in isis_te.c
+ */
+ if (IS_MPLS_TE(isisMplsTE))
+ return 0;
+
zebra_router_id_update_read(zclient->ibuf, &router_id);
if (isis->router_id == router_id.u.prefix4.s_addr)
return 0;
* uncomment the next line for full debugs
*/
/* isis->debugs = 0xFFFF; */
+ isisMplsTE.status = disable; /* Only support TE metric */
QOBJ_REG(isis, isis);
}
if (fabricd)
fabricd_finish(area->fabricd);
- /* Disable MPLS if necessary before flooding LSP */
- if (IS_MPLS_TE(area->mta))
- area->mta->status = disable;
-
if (area->circuit_list) {
for (ALL_LIST_ELEMENTS(area->circuit_list, node, nnode,
circuit)) {
write += area_write_mt_settings(area, vty);
write += fabricd_write_settings(area, vty);
}
+ isis_mpls_te_config_write_router(vty);
}
return write;
uint8_t log_adj_changes;
/* multi topology settings */
struct list *mt_settings;
- /* MPLS-TE settings */
- struct mpls_te_area *mta;
int ipv6_circuits;
bool purge_originator;
/* Counters */
description
"Log changes to the IS-IS adjacencies in this area.";
}
+ }
- container mpls-te {
- presence "Present if MPLS-TE is enabled.";
+ container mpls-te {
+ presence "Present if MPLS-TE is enabled.";
+ description
+ "Enable MPLS-TE functionality.";
+ leaf router-address {
+ type inet:ipv4-address;
description
- "Enable MPLS-TE functionality.";
- leaf router-address {
- type inet:ipv4-address;
- description
- "Stable IP address of the advertising router.";
- }
+ "Stable IP address of the advertising router.";
}
}
}