summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/user/zebra.rst22
-rw-r--r--lib/affinitymap.h4
-rw-r--r--lib/affinitymap_cli.c40
-rw-r--r--lib/affinitymap_northbound.c1
-rw-r--r--lib/command.h8
-rw-r--r--lib/defun_lex.l1
-rw-r--r--lib/if.c2
-rw-r--r--lib/if.h2
-rw-r--r--lib/mgmt_be_client.c4
-rw-r--r--lib/northbound.c3
-rw-r--r--lib/northbound.h8
-rw-r--r--lib/vrf.c21
-rw-r--r--lib/vty.c14
-rw-r--r--lib/yang.c14
-rw-r--r--lib/yang.h8
-rw-r--r--lib/yang_wrappers.c27
-rw-r--r--lib/yang_wrappers.h7
-rw-r--r--mgmtd/mgmt_be_adapter.c25
-rw-r--r--mgmtd/mgmt_main.c20
-rw-r--r--mgmtd/mgmt_vty.c4
-rw-r--r--mgmtd/subdir.am4
-rw-r--r--python/xref2vtysh.py10
-rw-r--r--staticd/static_vty.c4
-rw-r--r--tests/isisd/test_isis_spf.c2
-rw-r--r--tests/topotests/bgp_recursive_route_ebgp_multi_hop/test_bgp_recursive_route_ebgp_multi_hop.py4
-rw-r--r--tests/topotests/mgmt_oper/simple-results/result-intf-eth0-only-config.json10
-rw-r--r--tests/topotests/mgmt_oper/simple-results/result-intf-eth0-with-config.json6
-rw-r--r--tools/gen_northbound_callbacks.c2
-rw-r--r--tools/gen_yang_deviations.c2
-rw-r--r--vtysh/vtysh.c18
-rw-r--r--vtysh/vtysh.h8
-rw-r--r--yang/frr-zebra.yang780
-rw-r--r--zebra/interface.c1724
-rw-r--r--zebra/interface.h21
-rw-r--r--zebra/irdp_interface.c1
-rw-r--r--zebra/main.c2
-rw-r--r--zebra/router-id.c270
-rw-r--r--zebra/router-id.h2
-rw-r--r--zebra/rtadv.c1250
-rw-r--r--zebra/rtadv.h24
-rw-r--r--zebra/subdir.am4
-rw-r--r--zebra/table_manager.c64
-rw-r--r--zebra/table_manager.h20
-rw-r--r--zebra/zebra_cli.c2969
-rw-r--r--zebra/zebra_cli.h10
-rw-r--r--zebra/zebra_evpn_mh.c359
-rw-r--r--zebra/zebra_evpn_mh.h17
-rw-r--r--zebra/zebra_nb.c471
-rw-r--r--zebra/zebra_nb.h201
-rw-r--r--zebra/zebra_nb_config.c2682
-rw-r--r--zebra/zebra_ns.c7
-rw-r--r--zebra/zebra_ns.h1
-rw-r--r--zebra/zebra_ptm.c70
-rw-r--r--zebra/zebra_ptm.h9
-rw-r--r--zebra/zebra_routemap.c668
-rw-r--r--zebra/zebra_routemap.h12
-rw-r--r--zebra/zebra_vrf.c143
-rw-r--r--zebra/zebra_vty.c264
-rw-r--r--zebra/zebra_vxlan.c39
-rw-r--r--zebra/zebra_vxlan.h5
60 files changed, 7323 insertions, 5071 deletions
diff --git a/doc/user/zebra.rst b/doc/user/zebra.rst
index 8f4c9e1d45..9199404f3e 100644
--- a/doc/user/zebra.rst
+++ b/doc/user/zebra.rst
@@ -178,7 +178,7 @@ Standard Commands
work on non-linux systems at all. 'enable' and 'disable' will respectively turn
on and off mpls on the given interface.
-.. clicmd:: multicast
+.. clicmd:: multicast <enable|disable>
Enable or disable multicast flag for the interface.
@@ -214,20 +214,14 @@ Link Parameters Commands
.. clicmd:: link-params
+ Enter into the link parameters sub node. This command activates the link
+ parameters and allows to configure routing information that could be used
+ as part of Traffic Engineering on this interface. MPLS-TE must be enabled at
+ the OSPF (:ref:`ospf-traffic-engineering`) or ISIS
+ (:ref:`isis-traffic-engineering`) router level in complement to this. To
+ disable link parameters, use the ``no`` version of this command.
- Enter into the link parameters sub node. At least 'enable' must be
- set to activate the link parameters, and consequently routing
- information that could be used as part of Traffic Engineering on
- this interface. MPLS-TE must be enable at the OSPF
- (:ref:`ospf-traffic-engineering`) or ISIS
- (:ref:`isis-traffic-engineering`) router level in complement to
- this.
-
- Under link parameter statement, the following commands set the different TE values:
-
-.. clicmd:: enable
-
- Enable link parameters for this interface.
+Under link parameter statement, the following commands set the different TE values:
.. clicmd:: metric (0-4294967295)
diff --git a/lib/affinitymap.h b/lib/affinitymap.h
index f5924ca3ef..ebe2659bf7 100644
--- a/lib/affinitymap.h
+++ b/lib/affinitymap.h
@@ -58,6 +58,7 @@ struct affinity_maps {
DECLARE_QOBJ_TYPE(affinity_maps);
extern const struct frr_yang_module_info frr_affinity_map_info;
+extern const struct frr_yang_module_info frr_affinity_map_cli_info;
void affinity_map_set(const char *name, int pos);
void affinity_map_unset(const char *name);
@@ -69,9 +70,6 @@ void affinity_map_set_update_hook(void (*func)(const char *affmap_name,
uint16_t old_pos,
uint16_t new_pos));
-void cli_show_affinity_map(struct vty *vty, const struct lyd_node *dnode,
- bool show_defaults);
-
void affinity_map_init(void);
diff --git a/lib/affinitymap_cli.c b/lib/affinitymap_cli.c
index d417ae1951..73b91e775b 100644
--- a/lib/affinitymap_cli.c
+++ b/lib/affinitymap_cli.c
@@ -30,15 +30,6 @@
#include "lib/affinitymap.h"
#include "lib/affinitymap_cli_clippy.c"
-/* Route map node structure. */
-static int affinity_map_config_write(struct vty *vty);
-static struct cmd_node affinitymap_node = {
- .name = "affinity-map",
- .node = AFFMAP_NODE,
- .prompt = "",
- .config_write = affinity_map_config_write,
-};
-
/* max value is EXT_ADMIN_GROUP_MAX_POSITIONS - 1 */
DEFPY_YANG_NOSH(affinity_map, affinity_map_cmd,
"affinity-map NAME$name bit-position (0-1023)$position",
@@ -75,21 +66,7 @@ DEFPY_YANG_NOSH(no_affinity_map, no_affinity_map_cmd,
return nb_cli_apply_changes(vty, NULL);
}
-static int affinity_map_config_write(struct vty *vty)
-{
- const struct lyd_node *dnode;
- int written = 0;
-
- dnode = yang_dnode_get(running_config->dnode, "/frr-affinity-map:lib");
- if (dnode) {
- nb_cli_show_dnode_cmds(vty, dnode, false);
- written = 1;
- }
-
- return written;
-}
-
-void cli_show_affinity_map(struct vty *vty, const struct lyd_node *dnode,
+static void cli_show_affinity_map(struct vty *vty, const struct lyd_node *dnode,
bool show_defaults __attribute__((__unused__)))
{
vty_out(vty, "affinity-map %s bit-position %u\n",
@@ -97,11 +74,24 @@ void cli_show_affinity_map(struct vty *vty, const struct lyd_node *dnode,
yang_dnode_get_uint16(dnode, "value"));
}
+const struct frr_yang_module_info frr_affinity_map_cli_info = {
+ .name = "frr-affinity-map",
+ .ignore_cfg_cbs = true,
+ .nodes = {
+ {
+ .xpath = "/frr-affinity-map:lib/affinity-maps/affinity-map",
+ .cbs.cli_show = cli_show_affinity_map,
+ },
+ {
+ .xpath = NULL,
+ },
+ }
+};
+
/* Initialization of affinity map vector. */
void affinity_map_init(void)
{
/* CLI commands. */
- install_node(&affinitymap_node);
install_element(CONFIG_NODE, &affinity_map_cmd);
install_element(CONFIG_NODE, &no_affinity_map_cmd);
}
diff --git a/lib/affinitymap_northbound.c b/lib/affinitymap_northbound.c
index 9daccc2800..8e84d36f2f 100644
--- a/lib/affinitymap_northbound.c
+++ b/lib/affinitymap_northbound.c
@@ -94,7 +94,6 @@ const struct frr_yang_module_info frr_affinity_map_info = {
.cbs = {
.create = lib_affinity_map_create,
.destroy = lib_affinity_map_destroy,
- .cli_show = cli_show_affinity_map,
}
},
{
diff --git a/lib/command.h b/lib/command.h
index 4886b4bc47..04c66adb26 100644
--- a/lib/command.h
+++ b/lib/command.h
@@ -291,6 +291,10 @@ struct cmd_node {
#define DEFPY_YANG(funcname, cmdname, cmdstr, helpstr) \
DEFPY_ATTR(funcname, cmdname, cmdstr, helpstr, CMD_ATTR_YANG)
+#define DEFPY_YANG_HIDDEN(funcname, cmdname, cmdstr, helpstr) \
+ DEFPY_ATTR(funcname, cmdname, cmdstr, helpstr, \
+ CMD_ATTR_YANG | CMD_ATTR_HIDDEN)
+
#define DEFPY_YANG_NOSH(funcname, cmdname, cmdstr, helpstr) \
DEFPY_ATTR(funcname, cmdname, cmdstr, helpstr, \
CMD_ATTR_YANG | CMD_ATTR_NOSH)
@@ -315,6 +319,10 @@ struct cmd_node {
#define DEFUN_NOSH(funcname, cmdname, cmdstr, helpstr) \
DEFUN_ATTR(funcname, cmdname, cmdstr, helpstr, CMD_ATTR_NOSH)
+#define DEFUN_YANG_HIDDEN(funcname, cmdname, cmdstr, helpstr) \
+ DEFUN_ATTR(funcname, cmdname, cmdstr, helpstr, \
+ CMD_ATTR_YANG | CMD_ATTR_HIDDEN)
+
#define DEFUN_YANG_NOSH(funcname, cmdname, cmdstr, helpstr) \
DEFUN_ATTR(funcname, cmdname, cmdstr, helpstr, \
CMD_ATTR_YANG | CMD_ATTR_NOSH)
diff --git a/lib/defun_lex.l b/lib/defun_lex.l
index 124f864166..3104e48063 100644
--- a/lib/defun_lex.l
+++ b/lib/defun_lex.l
@@ -140,6 +140,7 @@ SPECIAL [(),]
"DEFPY_ATTR" value = strdup(yytext); return DEFUNNY;
"DEFPY_HIDDEN" value = strdup(yytext); return DEFUNNY;
"DEFPY_YANG" value = strdup(yytext); return DEFUNNY;
+"DEFPY_YANG_HIDDEN" value = strdup(yytext); return DEFUNNY;
"DEFPY_YANG_NOSH" value = strdup(yytext); return DEFUNNY;
"ALIAS" value = strdup(yytext); return DEFUNNY;
"ALIAS_HIDDEN" value = strdup(yytext); return DEFUNNY;
diff --git a/lib/if.c b/lib/if.c
index 1a8195de67..1328e21874 100644
--- a/lib/if.c
+++ b/lib/if.c
@@ -1135,7 +1135,7 @@ struct if_link_params *if_link_params_enable(struct interface *ifp)
iflp->unrsv_bw[i] = iflp->default_bw;
/* Update Link parameters status */
- iflp->lp_status = LP_MAX_BW | LP_MAX_RSV_BW | LP_UNRSV_BW | LP_EXTEND_ADM_GRP;
+ iflp->lp_status = LP_MAX_BW | LP_MAX_RSV_BW | LP_UNRSV_BW;
/* Set TE metric equal to standard metric only if it is set */
if (ifp->metric != 0) {
diff --git a/lib/if.h b/lib/if.h
index fd5f6f7502..548a91b948 100644
--- a/lib/if.h
+++ b/lib/if.h
@@ -195,7 +195,7 @@ struct if_link_params {
uint32_t min_delay; /* Link Min Delay */
uint32_t max_delay; /* Link Max Delay */
uint32_t delay_var; /* Link Delay Variation */
- float pkt_loss; /* Link Packet Loss */
+ uint32_t pkt_loss; /* Link Packet Loss */
float res_bw; /* Residual Bandwidth */
float ava_bw; /* Available Bandwidth */
float use_bw; /* Utilized Bandwidth */
diff --git a/lib/mgmt_be_client.c b/lib/mgmt_be_client.c
index 458623844a..463aefdf25 100644
--- a/lib/mgmt_be_client.c
+++ b/lib/mgmt_be_client.c
@@ -19,6 +19,7 @@
#include "northbound.h"
#include "stream.h"
#include "sockopt.h"
+#include "northbound_cli.h"
#include "lib/mgmt_be_client_clippy.c"
@@ -1068,7 +1069,7 @@ struct mgmt_be_client *mgmt_be_client_create(const char *client_name,
client->name = XSTRDUP(MTYPE_MGMTD_BE_CLIENT_NAME, client_name);
client->running_config = running_config;
- client->candidate_config = nb_config_new(NULL);
+ client->candidate_config = vty_shared_candidate_config;
if (cbs)
client->cbs = *cbs;
mgmt_be_txns_init(&client->txn_head);
@@ -1107,7 +1108,6 @@ void mgmt_be_client_destroy(struct mgmt_be_client *client)
msg_client_cleanup(&client->client);
mgmt_be_cleanup_all_txns(client);
mgmt_be_txns_fini(&client->txn_head);
- nb_config_free(client->candidate_config);
XFREE(MTYPE_MGMTD_BE_CLIENT_NAME, client->name);
XFREE(MTYPE_MGMTD_BE_CLIENT, client);
diff --git a/lib/northbound.c b/lib/northbound.c
index 949218332a..b1da3315d0 100644
--- a/lib/northbound.c
+++ b/lib/northbound.c
@@ -2384,7 +2384,8 @@ void nb_init(struct event_loop *tm,
for (size_t i = 0; i < nmodules; i++) {
DEBUGD(&nb_dbg_events, "northbound: loading %s.yang",
modules[i]->name);
- *loadedp++ = yang_module_load(modules[i]->name);
+ *loadedp++ = yang_module_load(modules[i]->name,
+ modules[i]->features);
}
if (explicit_compile)
diff --git a/lib/northbound.h b/lib/northbound.h
index 493e5ce703..2d9643e7b4 100644
--- a/lib/northbound.h
+++ b/lib/northbound.h
@@ -628,6 +628,14 @@ struct frr_yang_module_info {
*/
bool ignore_cfg_cbs;
+ /*
+ * The NULL-terminated list of supported features.
+ * Features are defined with "feature" statements in the YANG model.
+ * Use ["*", NULL] to enable all features.
+ * Use NULL to disable all features.
+ */
+ const char **features;
+
/* Northbound callbacks. */
const struct {
/* Data path of this YANG node. */
diff --git a/lib/vrf.c b/lib/vrf.c
index 48071f2bd6..65721445ab 100644
--- a/lib/vrf.c
+++ b/lib/vrf.c
@@ -956,6 +956,25 @@ static int lib_vrf_destroy(struct nb_cb_destroy_args *args)
return NB_OK;
}
+static void lib_vrf_cli_write(struct vty *vty, const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *name = yang_dnode_get_string(dnode, "name");
+
+ if (strcmp(name, VRF_DEFAULT_NAME)) {
+ vty_out(vty, "!\n");
+ vty_out(vty, "vrf %s\n", name);
+ }
+}
+
+static void lib_vrf_cli_write_end(struct vty *vty, const struct lyd_node *dnode)
+{
+ const char *name = yang_dnode_get_string(dnode, "name");
+
+ if (strcmp(name, VRF_DEFAULT_NAME))
+ vty_out(vty, "exit-vrf\n");
+}
+
static const void *lib_vrf_get_next(struct nb_cb_get_next_args *args)
{
struct vrf *vrfp = (struct vrf *)args->list_entry;
@@ -1035,6 +1054,8 @@ const struct frr_yang_module_info frr_vrf_info = {
.cbs = {
.create = lib_vrf_create,
.destroy = lib_vrf_destroy,
+ .cli_show = lib_vrf_cli_write,
+ .cli_show_end = lib_vrf_cli_write_end,
.get_next = lib_vrf_get_next,
.get_keys = lib_vrf_get_keys,
.lookup_entry = lib_vrf_lookup_entry,
diff --git a/lib/vty.c b/lib/vty.c
index a6b4de579a..ea35c541ee 100644
--- a/lib/vty.c
+++ b/lib/vty.c
@@ -126,6 +126,7 @@ bool vty_log_commands;
static bool vty_log_commands_perm;
char const *const mgmt_daemons[] = {
+ "zebra",
#ifdef HAVE_RIPD
"ripd",
#endif
@@ -2264,19 +2265,6 @@ bool mgmt_vty_read_configs(void)
snprintf(path, sizeof(path), "%s/mgmtd.conf", frr_sysconfdir);
confp = vty_open_config(path, config_default);
- if (!confp) {
- char *orig;
-
- snprintf(path, sizeof(path), "%s/zebra.conf", frr_sysconfdir);
- orig = XSTRDUP(MTYPE_TMP, host_config_get());
-
- zlog_info("mgmtd: trying backup config file: %s", path);
- confp = vty_open_config(path, config_default);
-
- host_config_set(path);
- XFREE(MTYPE_TMP, orig);
- }
-
if (confp) {
zlog_info("mgmtd: reading config file: %s", path);
diff --git a/lib/yang.c b/lib/yang.c
index b6884619d9..3dd2513a4b 100644
--- a/lib/yang.c
+++ b/lib/yang.c
@@ -100,13 +100,14 @@ RB_GENERATE(yang_modules, yang_module, entry, yang_module_compare)
struct yang_modules yang_modules = RB_INITIALIZER(&yang_modules);
-struct yang_module *yang_module_load(const char *module_name)
+struct yang_module *yang_module_load(const char *module_name,
+ const char **features)
{
struct yang_module *module;
const struct lys_module *module_info;
- module_info =
- ly_ctx_load_module(ly_native_ctx, module_name, NULL, NULL);
+ module_info = ly_ctx_load_module(ly_native_ctx, module_name, NULL,
+ features);
if (!module_info) {
flog_err(EC_LIB_YANG_MODULE_LOAD,
"%s: failed to load data model: %s", __func__,
@@ -130,8 +131,10 @@ struct yang_module *yang_module_load(const char *module_name)
void yang_module_load_all(void)
{
+ static const char * const all_features[] = { "*", NULL };
+
for (size_t i = 0; i < array_size(frr_native_modules); i++)
- yang_module_load(frr_native_modules[i]);
+ yang_module_load(frr_native_modules[i], (const char **)all_features);
}
struct yang_module *yang_module_find(const char *module_name)
@@ -625,7 +628,8 @@ struct lyd_node *yang_dnode_dup(const struct lyd_node *dnode)
{
struct lyd_node *dup = NULL;
LY_ERR err;
- err = lyd_dup_siblings(dnode, NULL, LYD_DUP_RECURSIVE, &dup);
+ err = lyd_dup_siblings(dnode, NULL,
+ LYD_DUP_RECURSIVE | LYD_DUP_WITH_FLAGS, &dup);
assert(!err);
return dup;
}
diff --git a/lib/yang.h b/lib/yang.h
index 1235125f26..431b2eee48 100644
--- a/lib/yang.h
+++ b/lib/yang.h
@@ -112,10 +112,16 @@ extern struct yang_modules yang_modules;
* module_name
* Name of the YANG module.
*
+ * features
+ * NULL-terminated array of feature names to enable.
+ * If NULL, all features are disabled.
+ * To enable all features, use ["*", NULL].
+ *
* Returns:
* Pointer to newly created YANG module.
*/
-extern struct yang_module *yang_module_load(const char *module_name);
+extern struct yang_module *yang_module_load(const char *module_name,
+ const char **features);
/*
* Load all FRR native YANG models.
diff --git a/lib/yang_wrappers.c b/lib/yang_wrappers.c
index dc049a374a..a0133954c3 100644
--- a/lib/yang_wrappers.c
+++ b/lib/yang_wrappers.c
@@ -168,10 +168,9 @@ struct yang_data *yang_data_new_dec64(const char *xpath, double value)
double yang_dnode_get_dec64(const struct lyd_node *dnode, const char *xpath_fmt,
...)
{
- const double denom[19] = {1e0, 1e-1, 1e-2, 1e-3, 1e-4,
- 1e-5, 1e-6, 1e-7, 1e-8, 1e-9,
- 1e-10, 1e-11, 1e-12, 1e-13, 1e-14,
- 1e-15, 1e-16, 1e-17, 1e-18};
+ const double denom[19] = { 1e0, 1e1, 1e2, 1e3, 1e4, 1e5, 1e6,
+ 1e7, 1e8, 1e9, 1e10, 1e11, 1e12, 1e13,
+ 1e14, 1e15, 1e16, 1e17, 1e18 };
const struct lysc_type_dec *dectype;
const struct lyd_value *dvalue;
@@ -179,7 +178,7 @@ double yang_dnode_get_dec64(const struct lyd_node *dnode, const char *xpath_fmt,
dectype = (const struct lysc_type_dec *)dvalue->realtype;
assert(dectype->basetype == LY_TYPE_DEC64);
assert(dectype->fraction_digits < sizeof(denom) / sizeof(*denom));
- return (double)dvalue->dec64 * denom[dectype->fraction_digits];
+ return (double)dvalue->dec64 / denom[dectype->fraction_digits];
}
double yang_get_default_dec64(const char *xpath_fmt, ...)
@@ -1020,6 +1019,13 @@ void yang_str2mac(const char *value, struct ethaddr *mac)
(void)prefix_str2mac(value, mac);
}
+void yang_dnode_get_mac(struct ethaddr *mac, const struct lyd_node *dnode,
+ const char *xpath_fmt, ...)
+{
+ const char *canon = YANG_DNODE_XPATH_GET_CANON(dnode, xpath_fmt);
+ (void)prefix_str2mac(canon, mac);
+}
+
struct yang_data *yang_data_new_date_and_time(const char *xpath, time_t time)
{
struct tm tm;
@@ -1046,6 +1052,17 @@ struct yang_data *yang_data_new_date_and_time(const char *xpath, time_t time)
return yang_data_new(xpath, timebuf);
}
+float yang_dnode_get_bandwidth_ieee_float32(const struct lyd_node *dnode,
+ const char *xpath_fmt, ...)
+{
+ const char *canon = YANG_DNODE_XPATH_GET_CANON(dnode, xpath_fmt);
+ float value;
+
+ assert(sscanf(canon, "%a", &value) == 1);
+
+ return value;
+}
+
const char *yang_nexthop_type2str(uint32_t ntype)
{
switch (ntype) {
diff --git a/lib/yang_wrappers.h b/lib/yang_wrappers.h
index 06e05872e3..59b5b13acd 100644
--- a/lib/yang_wrappers.h
+++ b/lib/yang_wrappers.h
@@ -195,11 +195,18 @@ extern void yang_get_default_ip(struct ipaddr *var, const char *xpath_fmt, ...)
extern struct yang_data *yang_data_new_mac(const char *xpath,
const struct ethaddr *mac);
extern void yang_str2mac(const char *value, struct ethaddr *mac);
+extern void yang_dnode_get_mac(struct ethaddr *mac, const struct lyd_node *dnode,
+ const char *xpath_fmt, ...) PRINTFRR(3, 4);
/*data-and-time */
extern struct yang_data *yang_data_new_date_and_time(const char *xpath,
time_t time);
+/* rt-types:bandwidth-ieee-float32 */
+extern float yang_dnode_get_bandwidth_ieee_float32(const struct lyd_node *dnode,
+ const char *xpath_fmt, ...)
+ PRINTFRR(2, 3);
+
/* nexthop enum2str */
extern const char *yang_nexthop_type2str(uint32_t ntype);
diff --git a/mgmtd/mgmt_be_adapter.c b/mgmtd/mgmt_be_adapter.c
index 6754657500..8d7ae88555 100644
--- a/mgmtd/mgmt_be_adapter.c
+++ b/mgmtd/mgmt_be_adapter.c
@@ -65,6 +65,23 @@ struct mgmt_be_xpath_map {
* above map as well.
*/
+static const char *const zebra_config_xpaths[] = {
+ "/frr-affinity-map:lib",
+ "/frr-filter:lib",
+ "/frr-route-map:lib",
+ "/frr-zebra:zebra",
+ "/frr-interface:lib",
+ "/frr-vrf:lib",
+ NULL,
+};
+
+static const char *const zebra_oper_xpaths[] = {
+ "/frr-interface:lib/interface",
+ "/frr-vrf:lib/vrf/frr-zebra:zebra",
+ "/frr-zebra:zebra",
+ NULL,
+};
+
#if HAVE_RIPD
static const char *const ripd_config_xpaths[] = {
"/frr-filter:lib",
@@ -105,6 +122,7 @@ static const char *const staticd_config_xpaths[] = {
#endif
static const char *const *be_client_config_xpaths[MGMTD_BE_CLIENT_ID_MAX] = {
+ [MGMTD_BE_CLIENT_ID_ZEBRA] = zebra_config_xpaths,
#ifdef HAVE_RIPD
[MGMTD_BE_CLIENT_ID_RIPD] = ripd_config_xpaths,
#endif
@@ -116,13 +134,6 @@ static const char *const *be_client_config_xpaths[MGMTD_BE_CLIENT_ID_MAX] = {
#endif
};
-static const char *const zebra_oper_xpaths[] = {
- "/frr-interface:lib/interface",
- "/frr-vrf:lib/vrf/frr-zebra:zebra",
- "/frr-zebra:zebra",
- NULL,
-};
-
static const char *const *be_client_oper_xpaths[MGMTD_BE_CLIENT_ID_MAX] = {
#ifdef HAVE_RIPD
[MGMTD_BE_CLIENT_ID_RIPD] = ripd_oper_xpaths,
diff --git a/mgmtd/mgmt_main.c b/mgmtd/mgmt_main.c
index 100f574b34..6dbd1f2e52 100644
--- a/mgmtd/mgmt_main.c
+++ b/mgmtd/mgmt_main.c
@@ -17,7 +17,8 @@
#include "ripd/rip_nb.h"
#include "ripngd/ripng_nb.h"
#include "routing_nb.h"
-
+#include "affinitymap.h"
+#include "zebra/zebra_cli.h"
/* mgmt options, we use GNU getopt library. */
static const struct option longopts[] = {
@@ -143,24 +144,11 @@ static struct frr_signal_t mgmt_signals[] = {
extern const struct frr_yang_module_info frr_staticd_cli_info;
#endif
-
/*
* These are stub info structs that are used to load the modules used by backend
* clients into mgmtd. The modules are used by libyang in order to support
* parsing binary data returns from the backend.
*/
-const struct frr_yang_module_info zebra_info = {
- .name = "frr-zebra",
- .ignore_cfg_cbs = true,
- .nodes = { { .xpath = NULL } },
-};
-
-const struct frr_yang_module_info affinity_map_info = {
- .name = "frr-affinity-map",
- .ignore_cfg_cbs = true,
- .nodes = { { .xpath = NULL } },
-};
-
const struct frr_yang_module_info zebra_route_map_info = {
.name = "frr-zebra-route-map",
.ignore_cfg_cbs = true,
@@ -177,13 +165,13 @@ static const struct frr_yang_module_info *const mgmt_yang_modules[] = {
&frr_route_map_cli_info,
&frr_routing_info,
&frr_vrf_info,
+ &frr_affinity_map_cli_info,
/*
* YANG module info used by backend clients get added here.
*/
- &zebra_info,
- &affinity_map_info,
+ &frr_zebra_cli_info,
&zebra_route_map_info,
#ifdef HAVE_RIPD
diff --git a/mgmtd/mgmt_vty.c b/mgmtd/mgmt_vty.c
index 194af13f1e..7135bc5547 100644
--- a/mgmtd/mgmt_vty.c
+++ b/mgmtd/mgmt_vty.c
@@ -8,6 +8,7 @@
#include <zebra.h>
+#include "affinitymap.h"
#include "command.h"
#include "filter.h"
#include "json.h"
@@ -25,6 +26,7 @@
#include "ripd/rip_nb.h"
#include "ripngd/ripng_nb.h"
#include "staticd/static_vty.h"
+#include "zebra/zebra_cli.h"
extern struct frr_daemon_info *mgmt_daemon_info;
@@ -570,6 +572,7 @@ void mgmt_vty_init(void)
*/
filter_cli_init();
route_map_cli_init();
+ affinity_map_init();
/*
* Initialize command handling from VTYSH connection.
@@ -577,6 +580,7 @@ void mgmt_vty_init(void)
* backend components that are moved to new MGMTD infra
* here one by one.
*/
+ zebra_cli_init();
#if HAVE_RIPD
rip_cli_init();
#endif
diff --git a/mgmtd/subdir.am b/mgmtd/subdir.am
index 3d1dafabd4..a3955925ed 100644
--- a/mgmtd/subdir.am
+++ b/mgmtd/subdir.am
@@ -16,8 +16,10 @@ clippy_scan += \
lib_LTLIBRARIES += mgmtd/libmgmt_be_nb.la
mgmtd_libmgmt_be_nb_la_SOURCES = \
+ zebra/zebra_cli.c \
# end
nodist_mgmtd_libmgmt_be_nb_la_SOURCES = \
+ lib/affinitymap_cli.c \
# end
mgmtd_libmgmt_be_nb_la_CFLAGS = $(AM_CFLAGS) -DINCLUDE_MGMTD_CMDDEFS_ONLY
mgmtd_libmgmt_be_nb_la_CPPFLAGS = $(AM_CPPFLAGS) -DINCLUDE_MGMTD_CMDDEFS_ONLY
@@ -43,6 +45,7 @@ noinst_HEADERS += \
mgmtd/mgmt_history.h \
mgmtd/mgmt_memory.h \
mgmtd/mgmt_txn.h \
+ zebra/zebra_cli.h \
# end
sbin_PROGRAMS += mgmtd/mgmtd
@@ -51,6 +54,7 @@ mgmtd_mgmtd_SOURCES = \
mgmtd/mgmt_main.c \
# end
nodist_mgmtd_mgmtd_SOURCES = \
+ yang/frr-zebra.yang.c \
# nothing
mgmtd_mgmtd_CFLAGS = $(AM_CFLAGS) -I ./
mgmtd_mgmtd_LDADD = mgmtd/libmgmtd.a lib/libfrr.la $(LIBCAP) $(LIBM) $(LIBYANG_LIBS) $(UST_LIBS)
diff --git a/python/xref2vtysh.py b/python/xref2vtysh.py
index 1760588ca8..91ccba64f0 100644
--- a/python/xref2vtysh.py
+++ b/python/xref2vtysh.py
@@ -324,17 +324,7 @@ class CommandEntry:
def load(cls, xref):
nodes = NodeDict()
- mgmtname = "mgmtd/libmgmt_be_nb.la"
for cmd_name, origins in xref.get("cli", {}).items():
- # If mgmtd has a yang version of a CLI command, make it the only daemon
- # to handle it. For now, daemons can still be compiling their cmds into the
- # binaries to allow for running standalone with CLI config files. When they
- # do this they will also be present in the xref file, but we want to ignore
- # those in vtysh.
- if "yang" in origins.get(mgmtname, {}).get("attrs", []):
- CommandEntry.process(nodes, cmd_name, mgmtname, origins[mgmtname])
- continue
-
for origin, spec in origins.items():
CommandEntry.process(nodes, cmd_name, origin, spec)
return nodes
diff --git a/staticd/static_vty.c b/staticd/static_vty.c
index 95f79564af..05f23f54d1 100644
--- a/staticd/static_vty.c
+++ b/staticd/static_vty.c
@@ -1696,8 +1696,7 @@ void static_vty_init(void)
install_element(CONFIG_NODE, &debug_staticd_cmd);
install_element(ENABLE_NODE, &show_debugging_static_cmd);
install_element(ENABLE_NODE, &staticd_show_bfd_routes_cmd);
-#endif /* ifndef INCLUDE_MGMTD_CMDDEFS_ONLY */
-
+#else /* else INCLUDE_MGMTD_CMDDEFS_ONLY */
install_element(CONFIG_NODE, &ip_mroute_dist_cmd);
install_element(CONFIG_NODE, &ip_route_blackhole_cmd);
@@ -1713,6 +1712,7 @@ void static_vty_init(void)
install_element(VRF_NODE, &ipv6_route_address_interface_vrf_cmd);
install_element(CONFIG_NODE, &ipv6_route_cmd);
install_element(VRF_NODE, &ipv6_route_vrf_cmd);
+#endif /* ifndef INCLUDE_MGMTD_CMDDEFS_ONLY */
#ifndef INCLUDE_MGMTD_CMDDEFS_ONLY
mgmt_be_client_lib_vty_init();
diff --git a/tests/isisd/test_isis_spf.c b/tests/isisd/test_isis_spf.c
index 95f045c90d..4ea28cda2f 100644
--- a/tests/isisd/test_isis_spf.c
+++ b/tests/isisd/test_isis_spf.c
@@ -540,7 +540,7 @@ int main(int argc, char **argv)
zlog_aux_init("NONE: ", ZLOG_DISABLED);
/* IS-IS inits. */
- yang_module_load("frr-isisd");
+ yang_module_load("frr-isisd", NULL);
SET_FLAG(im->options, F_ISIS_UNIT_TEST);
debug_spf_events |= DEBUG_SPF_EVENTS;
debug_lfa |= DEBUG_LFA;
diff --git a/tests/topotests/bgp_recursive_route_ebgp_multi_hop/test_bgp_recursive_route_ebgp_multi_hop.py b/tests/topotests/bgp_recursive_route_ebgp_multi_hop/test_bgp_recursive_route_ebgp_multi_hop.py
index 35459f6f68..88251fae60 100644
--- a/tests/topotests/bgp_recursive_route_ebgp_multi_hop/test_bgp_recursive_route_ebgp_multi_hop.py
+++ b/tests/topotests/bgp_recursive_route_ebgp_multi_hop/test_bgp_recursive_route_ebgp_multi_hop.py
@@ -257,10 +257,10 @@ def test_recursive_routes_iBGP_peer_p1(request):
)
dut = "r2"
create_interface_in_kernel(
- tgen, dut, "lo", "40.40.40.50", netmask="255.255.255.0", create=True
+ tgen, dut, "lo10", "40.40.40.50", netmask="255.255.255.0", create=True
)
create_interface_in_kernel(
- tgen, dut, "lo", "40:40::40:50", netmask="120", create=True
+ tgen, dut, "lo10", "40:40::40:50", netmask="120", create=True
)
for addr_type in ADDR_TYPES:
input_dict_3 = {
diff --git a/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-only-config.json b/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-only-config.json
index adcf99053f..9289759274 100644
--- a/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-only-config.json
+++ b/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-only-config.json
@@ -3,7 +3,15 @@
"interface": [
{
"name": "r1-eth0",
- "description": "r1-eth0-desc"
+ "description": "r1-eth0-desc",
+ "frr-zebra:zebra": {
+ "ipv4-addrs": [
+ {
+ "ip": "1.1.1.1",
+ "prefix-length": 24
+ }
+ ]
+ }
}
]
}
diff --git a/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-with-config.json b/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-with-config.json
index 47c9686252..ef9e005619 100644
--- a/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-with-config.json
+++ b/tests/topotests/mgmt_oper/simple-results/result-intf-eth0-with-config.json
@@ -14,6 +14,12 @@
"phy-address": "rubout"
},
"frr-zebra:zebra": {
+ "ipv4-addrs": [
+ {
+ "ip": "1.1.1.1",
+ "prefix-length": 24
+ }
+ ],
"state": {
"up-count": 0,
"down-count": 0
diff --git a/tools/gen_northbound_callbacks.c b/tools/gen_northbound_callbacks.c
index 550058bfec..6188559010 100644
--- a/tools/gen_northbound_callbacks.c
+++ b/tools/gen_northbound_callbacks.c
@@ -350,7 +350,7 @@ int main(int argc, char *argv[])
module = yang_module_find(argv[0]);
if (!module)
/* Non-native FRR module (e.g. modules from unit tests). */
- module = yang_module_load(argv[0]);
+ module = yang_module_load(argv[0], NULL);
yang_init_loading_complete();
diff --git a/tools/gen_yang_deviations.c b/tools/gen_yang_deviations.c
index fc9f55bcbc..251643c69e 100644
--- a/tools/gen_yang_deviations.c
+++ b/tools/gen_yang_deviations.c
@@ -55,7 +55,7 @@ int main(int argc, char *argv[])
yang_init(false, false);
/* Load YANG module. */
- module = yang_module_load(argv[0]);
+ module = yang_module_load(argv[0], NULL);
/* Generate deviations. */
yang_snodes_iterate(module->info, generate_yang_deviation, 0, NULL);
diff --git a/vtysh/vtysh.c b/vtysh/vtysh.c
index b1a53965cd..940b63b0e1 100644
--- a/vtysh/vtysh.c
+++ b/vtysh/vtysh.c
@@ -1615,7 +1615,6 @@ struct cmd_node link_params_node = {
.node = LINK_PARAMS_NODE,
.parent_node = INTERFACE_NODE,
.prompt = "%s(config-link-params)# ",
- .no_xpath = true,
};
#ifdef HAVE_BGPD
@@ -3008,14 +3007,22 @@ DEFUN (vtysh_show_work_queues_daemon,
return show_one_daemon(vty, argv, argc - 1, argv[argc - 1]->text);
}
-DEFUNSH(VTYSH_ZEBRA, vtysh_link_params, vtysh_link_params_cmd, "link-params",
+DEFUNSH(VTYSH_MGMTD, vtysh_link_params, vtysh_link_params_cmd, "link-params",
LINK_PARAMS_STR)
{
vty->node = LINK_PARAMS_NODE;
return CMD_SUCCESS;
}
-DEFUNSH(VTYSH_ZEBRA, exit_link_params, exit_link_params_cmd, "exit-link-params",
+DEFUNSH_HIDDEN(VTYSH_MGMTD, no_link_params_enable, no_link_params_enable_cmd,
+ "no enable", NO_STR "Disable link parameters on this interface\n")
+{
+ if (vty->node == LINK_PARAMS_NODE)
+ vty->node = INTERFACE_NODE;
+ return CMD_SUCCESS;
+}
+
+DEFUNSH(VTYSH_MGMTD, exit_link_params, exit_link_params_cmd, "exit-link-params",
"Exit from Link Params configuration node\n")
{
if (vty->node == LINK_PARAMS_NODE)
@@ -3023,7 +3030,7 @@ DEFUNSH(VTYSH_ZEBRA, exit_link_params, exit_link_params_cmd, "exit-link-params",
return CMD_SUCCESS;
}
-DEFUNSH(VTYSH_ZEBRA, vtysh_exit_link_params, vtysh_exit_link_params_cmd, "exit",
+DEFUNSH(VTYSH_MGMTD, vtysh_exit_link_params, vtysh_exit_link_params_cmd, "exit",
"Exit current mode and down to previous mode\n")
{
if (vty->node == LINK_PARAMS_NODE)
@@ -3031,7 +3038,7 @@ DEFUNSH(VTYSH_ZEBRA, vtysh_exit_link_params, vtysh_exit_link_params_cmd, "exit",
return CMD_SUCCESS;
}
-DEFUNSH(VTYSH_ZEBRA, vtysh_quit_link_params, vtysh_quit_link_params_cmd, "quit",
+DEFUNSH(VTYSH_MGMTD, vtysh_quit_link_params, vtysh_quit_link_params_cmd, "quit",
"Exit current mode and down to previous mode\n")
{
return vtysh_exit_link_params(self, vty, argc, argv);
@@ -5064,6 +5071,7 @@ void vtysh_init_vty(void)
install_node(&link_params_node);
install_element(INTERFACE_NODE, &vtysh_link_params_cmd);
+ install_element(LINK_PARAMS_NODE, &no_link_params_enable_cmd);
install_element(LINK_PARAMS_NODE, &exit_link_params_cmd);
install_element(LINK_PARAMS_NODE, &vtysh_end_all_cmd);
install_element(LINK_PARAMS_NODE, &vtysh_exit_link_params_cmd);
diff --git a/vtysh/vtysh.h b/vtysh/vtysh.h
index b1e914ebf7..7758ceaea5 100644
--- a/vtysh/vtysh.h
+++ b/vtysh/vtysh.h
@@ -53,23 +53,23 @@ extern struct event_loop *master;
VTYSH_BFDD | VTYSH_BABELD | VTYSH_BGPD | VTYSH_EIGRPD | VTYSH_ISISD | \
VTYSH_FABRICD | VTYSH_LDPD | VTYSH_NHRPD | VTYSH_OSPF6D | \
VTYSH_OSPFD | VTYSH_PBRD | VTYSH_PIMD | VTYSH_PIM6D | \
- VTYSH_VRRPD | VTYSH_ZEBRA | VTYSH_MGMTD
+ VTYSH_VRRPD | VTYSH_MGMTD
#define VTYSH_ACL_SHOW \
VTYSH_BFDD | VTYSH_BABELD | VTYSH_BGPD | VTYSH_EIGRPD | VTYSH_ISISD | \
VTYSH_FABRICD | VTYSH_LDPD | VTYSH_NHRPD | VTYSH_OSPF6D | \
VTYSH_OSPFD | VTYSH_PBRD | VTYSH_PIMD | VTYSH_PIM6D | \
VTYSH_RIPD | VTYSH_RIPNGD | VTYSH_VRRPD | VTYSH_ZEBRA
-#define VTYSH_AFFMAP VTYSH_ZEBRA | VTYSH_ISISD
+#define VTYSH_AFFMAP VTYSH_ISISD | VTYSH_MGMTD
#define VTYSH_RMAP_CONFIG \
- VTYSH_ZEBRA | VTYSH_OSPFD | VTYSH_OSPF6D | VTYSH_BGPD | VTYSH_ISISD | \
+ VTYSH_OSPFD | VTYSH_OSPF6D | VTYSH_BGPD | VTYSH_ISISD | \
VTYSH_PIMD | VTYSH_EIGRPD | VTYSH_FABRICD | VTYSH_MGMTD
#define VTYSH_RMAP_SHOW \
VTYSH_ZEBRA | VTYSH_RIPD | VTYSH_RIPNGD | VTYSH_OSPFD | VTYSH_OSPF6D | \
VTYSH_BGPD | VTYSH_ISISD | VTYSH_PIMD | VTYSH_EIGRPD | \
VTYSH_FABRICD
#define VTYSH_INTERFACE_SUBSET \
- VTYSH_ZEBRA | VTYSH_OSPFD | VTYSH_OSPF6D | \
+ VTYSH_OSPFD | VTYSH_OSPF6D | \
VTYSH_ISISD | VTYSH_PIMD | VTYSH_PIM6D | VTYSH_NHRPD | \
VTYSH_EIGRPD | VTYSH_BABELD | VTYSH_PBRD | VTYSH_FABRICD | \
VTYSH_VRRPD | VTYSH_MGMTD
diff --git a/yang/frr-zebra.yang b/yang/frr-zebra.yang
index 1168f05f40..564617103b 100644
--- a/yang/frr-zebra.yang
+++ b/yang/frr-zebra.yang
@@ -81,6 +81,16 @@ module frr-zebra {
"Initial revision.";
}
+ feature ipv6-router-advertisements {
+ description
+ "Support for IPv6 Router Advertisements.";
+ }
+
+ feature ptm-bfd {
+ description
+ "Using an external PTM daemon that implements BFD.";
+ }
+
typedef unix-timestamp {
type uint32;
units "seconds";
@@ -1935,19 +1945,23 @@ module frr-zebra {
description
"Extends interface model with Zebra-related parameters.";
container zebra {
- list ip-addrs {
- key "address-family ip-prefix";
+ list ipv4-addrs {
+ key "ip prefix-length";
description
- "IP prefixes for an interface.";
- uses frr-rt:address-family {
+ "The list of configured IPv4 addresses on the interface.";
+
+ leaf ip {
+ type inet:ipv4-address-no-zone;
description
- "Address family of the RIB.";
+ "The IPv4 address on the interface.";
}
- leaf ip-prefix {
- type inet:ip-prefix;
+ leaf prefix-length {
+ type uint8 {
+ range "0..32";
+ }
description
- "IP address prefix.";
+ "The length of the subnet prefix.";
}
leaf label {
@@ -1955,12 +1969,57 @@ module frr-zebra {
description
"Optional string label for the address.";
}
+ }
+
+ list ipv4-p2p-addrs {
+ key "ip peer-ip peer-prefix-length";
+ description
+ "The list of configured peer-to-peer IPv4 addresses on the interface.";
+
+ leaf ip {
+ type inet:ipv4-address-no-zone;
+ description
+ "The IPv4 address on the interface.";
+ }
+
+ leaf peer-ip {
+ type inet:ipv4-address-no-zone;
+ description
+ "Peer address.";
+ }
+
+ leaf peer-prefix-length {
+ type uint8 {
+ range "0..32";
+ }
+ description
+ "The length of the peer subnet prefix.";
+ }
- leaf ip4-peer {
- when "derived-from-or-self(../address-family, 'frr-rt:ipv4')";
- type inet:ipv4-prefix;
+ leaf label {
+ type string;
description
- "Peer prefix, for peer-to-peer interfaces.";
+ "Optional string label for the address.";
+ }
+ }
+
+ list ipv6-addrs {
+ key "ip prefix-length";
+ description
+ "The list of configured IPv6 addresses on the interface.";
+
+ leaf ip {
+ type inet:ipv6-address-no-zone;
+ description
+ "The IPv6 address on the interface.";
+ }
+
+ leaf prefix-length {
+ type uint8 {
+ range "0..128";
+ }
+ description
+ "The length of the subnet prefix.";
}
}
@@ -1972,11 +2031,12 @@ module frr-zebra {
leaf link-detect {
type boolean;
+ default "true";
description
"Link-detection for the interface.";
}
- leaf shutdown {
+ leaf enabled {
type boolean;
description
"Interface admin status.";
@@ -1992,12 +2052,67 @@ module frr-zebra {
type uint32 {
range "1..100000";
}
+ units "megabits/sec";
description
"Link bandwidth informational parameter, in megabits.";
}
container link-params {
+ presence "Activates link parameters on this interface.";
description
"link-params for Traffic-Engineering (TE) use in IGP extensions.";
+ leaf metric {
+ type uint32;
+ description
+ "Link metric for MPLS-TE purpose.";
+ }
+ leaf max-bandwidth {
+ type rt-types:bandwidth-ieee-float32;
+ description
+ "Maximum bandwidth.";
+ }
+ leaf max-reservable-bandwidth {
+ type rt-types:bandwidth-ieee-float32;
+ description
+ "Maximum reservable bandwidth.";
+ }
+ container unreserved-bandwidths {
+ description
+ "All unreserved bandwidths.";
+ list unreserved-bandwidth {
+ key "priority";
+ leaf priority {
+ type uint8 {
+ range "0 .. 7";
+ }
+ description
+ "Priority from 0 to 7.";
+ }
+ leaf unreserved-bandwidth {
+ type rt-types:bandwidth-ieee-float32;
+ mandatory true;
+ description
+ "Unreserved bandwidth.";
+ }
+ description
+ "List of unreserved bandwidths for different
+ priorities.";
+ }
+ }
+ leaf residual-bandwidth {
+ type rt-types:bandwidth-ieee-float32;
+ description
+ "Unidirectional residual bandwidth.";
+ }
+ leaf available-bandwidth {
+ type rt-types:bandwidth-ieee-float32;
+ description
+ "Unidirectional available bandwidth.";
+ }
+ leaf utilized-bandwidth {
+ type rt-types:bandwidth-ieee-float32;
+ description
+ "Unidirectional utilized bandwidth.";
+ }
choice admin-group-mode {
description "Admin-group mode";
case legacy {
@@ -2044,9 +2159,526 @@ module frr-zebra {
}
}
}
+ container neighbor {
+ description "Remote ASBR information (RFC 5316 & RFC 5392)";
+ presence "Activates neighbor information on this interface.";
+ leaf remote-as {
+ type inet:as-number;
+ mandatory true;
+ description
+ "Remote AS Number (RFC 5316 & RFC 5392)";
+ }
+ leaf ipv4-remote-id {
+ type inet:ipv4-address;
+ mandatory true;
+ description
+ "IPv4 Remote ASBR ID (RFC 5316 & RFC 5392)";
+ }
+ }
+ leaf delay {
+ type uint32 {
+ range "0..16777215";
+ }
+ description
+ "Average Unidirectional Link Delay";
+ }
+ container min-max-delay {
+ description
+ "Min/Max Unidirectional Link Delay";
+ presence "Activates min/max delay.";
+ leaf delay-min {
+ type uint32 {
+ range "0..16777215";
+ }
+ must '. <= ../../delay' {
+ error-message "Min delay must be less than or equal to delay";
+ }
+ mandatory true;
+ description
+ "Min Delay";
+ }
+ leaf delay-max {
+ type uint32 {
+ range "0..16777215";
+ }
+ must '. >= ../../delay' {
+ error-message "Max delay must be greater than or equal to delay";
+ }
+ mandatory true;
+ description
+ "Max Delay";
+ }
+ }
+ leaf delay-variation {
+ type uint32 {
+ range "0..16777215";
+ }
+ description
+ "Unidirectional Delay Variation";
+ }
+ leaf packet-loss {
+ type decimal64 {
+ fraction-digits 6;
+ range "0..50.331642";
+ }
+ description
+ "Unidirectional Link Packet Loss";
+ }
// TODO -- other link-params options
// for (experimental/partial TE use in IGP extensions)
}
+ container evpn-mh {
+ description "EVPN multihoming configuration";
+ choice esi-choice {
+ description "ESI type";
+ container type-0 {
+ leaf esi {
+ type yang:hex-string {
+ length "29";
+ }
+ description
+ "10-octet ESI.";
+ }
+ }
+ container type-3 {
+ leaf system-mac {
+ type yang:mac-address;
+ description
+ "System MAC address.";
+ }
+ leaf local-discriminator {
+ type uint32 {
+ range "1..16777215";
+ }
+ description
+ "Local discriminator.";
+ }
+ }
+ }
+ leaf df-preference {
+ type uint16;
+ default "32767";
+ description
+ "Preference value used for DF election.";
+ }
+ leaf bypass {
+ type boolean;
+ default "false";
+ description
+ "Bypass mode.";
+ }
+ leaf uplink {
+ type boolean;
+ default "false";
+ description
+ "Uplink to the VxLAN core.";
+ }
+ }
+ container ipv6-router-advertisements {
+ if-feature "ipv6-router-advertisements";
+ description
+ "Support for IPv6 Router Advertisements.";
+ leaf send-advertisements {
+ type boolean;
+ default "false";
+ description
+ "A flag indicating whether or not the router sends
+ periodic Router Advertisements and responds to
+ Router Solicitations.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvSendAdvertisements";
+ }
+ leaf max-rtr-adv-interval {
+ type uint32 {
+ range "70..1800000";
+ }
+ units "milliseconds";
+ default "600000";
+ description
+ "The maximum time allowed between sending unsolicited
+ multicast Router Advertisements from the interface.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - MaxRtrAdvInterval
+ RFC 6275: Mobility Support in IPv6";
+ }
+ // Setting this value is not yet supported by the actual code.
+ /*
+ leaf min-rtr-adv-interval {
+ type uint32 {
+ range "30..1350000";
+ }
+ units "milliseconds";
+ must ". <= 0.75 * ../max-rtr-adv-interval" {
+ description
+ "The value MUST NOT be greater than 75% of
+ 'max-rtr-adv-interval'.";
+ }
+ description
+ "The minimum time allowed between sending unsolicited
+ multicast Router Advertisements from the interface.
+
+ The default value to be used operationally if this
+ leaf is not configured is determined as follows:
+
+ - if max-rtr-adv-interval >= 9 seconds, the default
+ value is 0.33 * max-rtr-adv-interval;
+
+ - otherwise, it is 0.75 * max-rtr-adv-interval.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - MaxRtrAdvInterval
+ RFC 6275: Mobility Support in IPv6";
+ }
+ */
+ leaf managed-flag {
+ type boolean;
+ default "false";
+ description
+ "The value to be placed in the 'Managed address
+ configuration' flag field in the Router
+ Advertisement.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvManagedFlag";
+ }
+ leaf other-config-flag {
+ type boolean;
+ default "false";
+ description
+ "The value to be placed in the 'Other configuration'
+ flag field in the Router Advertisement.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvOtherConfigFlag";
+ }
+ leaf home-agent-flag {
+ type boolean;
+ default "false";
+ description
+ "The value to be placed in the 'Home Agent'
+ flag field in the Router Advertisement.";
+ reference
+ "RFC 6275: Mobility Support in IPv6";
+ }
+ leaf link-mtu {
+ type uint32;
+ default "0";
+ description
+ "The value to be placed in MTU options sent by the
+ router. A value of zero indicates that no MTU options
+ are sent.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvLinkMTU";
+ }
+ leaf reachable-time {
+ type uint32 {
+ range "0..3600000";
+ }
+ units "milliseconds";
+ default "0";
+ description
+ "The value to be placed in the Reachable Time field in
+ the Router Advertisement messages sent by the router.
+ A value of zero means unspecified (by this router).";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvReachableTime";
+ }
+ leaf retrans-timer {
+ type uint32;
+ units "milliseconds";
+ default "0";
+ description
+ "The value to be placed in the Retrans Timer field in
+ the Router Advertisement messages sent by the router.
+ A value of zero means unspecified (by this router).";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvRetransTimer";
+ }
+ leaf cur-hop-limit {
+ type uint8;
+ description
+ "The value to be placed in the Cur Hop Limit field in
+ the Router Advertisement messages sent by the router.
+ A value of zero means unspecified (by this router).
+
+ If this parameter is not configured, the device SHOULD
+ use the IANA-specified value for the default IPv4
+ Time to Live (TTL) parameter that was in effect at the
+ time of implementation.";
+ reference
+ "RFC 3232: Assigned Numbers: RFC 1700 is Replaced by
+ an On-line Database
+ RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvCurHopLimit
+ IANA: IP Parameters
+ (https://www.iana.org/assignments/ip-parameters)";
+ }
+ leaf default-lifetime {
+ type uint16 {
+ range "0..9000";
+ }
+ units "seconds";
+ must ". = 0 or . * 1000 >= ../max-rtr-adv-interval" {
+ description
+ "The value MUST NOT be less than max-rtr-adv-interval.";
+ }
+ description
+ "The value to be placed in the Router Lifetime field of
+ Router Advertisements sent from the interface, in
+ seconds. It MUST be either zero or between
+ max-rtr-adv-interval and 9000 seconds. A value of zero
+ indicates that the router is not to be used as a
+ default router. These limits may be overridden by
+ specific documents that describe how IPv6 operates over
+ different link layers.
+
+ If this parameter is not configured, the device SHOULD
+ use a value of 3 * max-rtr-adv-interval.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvDefaultLifetime";
+ }
+ leaf fast-retransmit {
+ type boolean;
+ default "true";
+ description
+ "Allow sending unsolicited multicast Router Advertisements
+ more frequently than once every 3 seconds as required by
+ RFC 4861.";
+ }
+ leaf advertisement-interval-option {
+ type boolean;
+ default "false";
+ description
+ "Enable sending the Advertisement Interval Option in
+ Router Advertisements.";
+ reference
+ "RFC 6275: Mobility Support in IPv6";
+ }
+ leaf home-agent-preference {
+ type uint16;
+ description
+ "The value to be placed in the Home Agent Preference
+ field in the Router Advertisement messages sent by the
+ router.";
+ reference
+ "RFC 6275: Mobility Support in IPv6";
+ }
+ leaf home-agent-lifetime {
+ type uint16;
+ description
+ "The value to be placed in the Home Agent Lifetime
+ field in the Router Advertisement messages sent by the
+ router.";
+ reference
+ "RFC 6275: Mobility Support in IPv6";
+ }
+ leaf default-router-preference {
+ type enumeration {
+ enum high {
+ value 1; /* 01 */
+ description
+ "High preference.";
+ }
+ enum medium {
+ value 0; /* 00 */
+ description
+ "Medium preference.";
+ }
+ enum low {
+ value 3; /* 11 */
+ description
+ "Low preference.";
+ }
+ }
+ default "medium";
+ description
+ "The value to be placed in the Default Router
+ Preference field in the Router Advertisement messages
+ sent by the router.";
+ reference
+ "RFC 4191: Default Router Preferences and More-Specific
+ Routes";
+ }
+ container prefix-list {
+ description
+ "Support for prefixes to be placed in Prefix
+ Information options in Router Advertisement messages
+ sent from the interface.
+
+ Prefixes that are advertised by default but do not
+ have their entries in the child 'prefix' list are
+ advertised with the default values of all parameters.
+
+ The link-local prefix SHOULD NOT be included in the
+ list of advertised prefixes.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6 (IPv6)
+ - AdvPrefixList";
+ list prefix {
+ key "prefix-spec";
+ description
+ "Support for an advertised prefix entry.";
+ leaf prefix-spec {
+ type inet:ipv6-prefix;
+ description
+ "IPv6 address prefix.";
+ }
+ // FRR doesn't support 'no-advertise'. Keeping the code
+ // here for future reference.
+ /*
+ choice control-adv-prefixes {
+ default "advertise";
+ description
+ "Either (1) the prefix is explicitly removed from the
+ set of advertised prefixes or (2) the parameters with
+ which the prefix is advertised are specified (default
+ case).";
+ leaf no-advertise {
+ type empty;
+ description
+ "The prefix will not be advertised.
+
+ This can be used for removing the prefix from
+ the default set of advertised prefixes.";
+ }
+ case advertise {
+ */
+ leaf valid-lifetime {
+ type uint32;
+ units "seconds";
+ default "2592000";
+ description
+ "The value to be placed in the Valid Lifetime
+ in the Prefix Information option. The
+ designated value of all 1's (0xffffffff)
+ represents infinity.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6
+ (IPv6) - AdvValidLifetime";
+ }
+ leaf on-link-flag {
+ type boolean;
+ default "true";
+ description
+ "The value to be placed in the on-link flag
+ ('L-bit') field in the Prefix Information
+ option.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6
+ (IPv6) - AdvOnLinkFlag";
+ }
+ leaf preferred-lifetime {
+ type uint32;
+ units "seconds";
+ must ". <= ../valid-lifetime" {
+ description
+ "This value MUST NOT be greater than
+ valid-lifetime.";
+ }
+ default "604800";
+ description
+ "The value to be placed in the Preferred
+ Lifetime in the Prefix Information option.
+ The designated value of all 1's (0xffffffff)
+ represents infinity.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6
+ (IPv6) - AdvPreferredLifetime";
+ }
+ leaf autonomous-flag {
+ type boolean;
+ default "true";
+ description
+ "The value to be placed in the Autonomous Flag
+ field in the Prefix Information option.";
+ reference
+ "RFC 4861: Neighbor Discovery for IP version 6
+ (IPv6) - AdvAutonomousFlag";
+ }
+ leaf router-address-flag {
+ type boolean;
+ default "false";
+ description
+ "The value to be placed in the Router Address
+ flag field in the Prefix Information option.";
+ reference
+ "RFC 6275: Mobility Support in IPv6";
+ }
+ /*
+ }
+ }
+ */
+ // This is closing brackets for `case advertise` and
+ // `choice control-adv-prefixes`.
+ }
+ }
+ container rdnss {
+ description
+ "A list of recursive DNS server addresses that are placed
+ in Recursive DNS Server (RDNSS) options in Router
+ Advertisement messages sent from the interface.";
+ reference
+ "RFC 8106: IPv6 Router Advertisement Options for DNS
+ Configuration";
+ list rdnss-address {
+ key "address";
+ description
+ "Recursive DNS server address.";
+ leaf address {
+ type inet:ipv6-address;
+ description
+ "IPv6 address of a recursive DNS server.";
+ }
+ leaf lifetime {
+ type uint32;
+ units "seconds";
+ description
+ "The value that is placed in the Lifetime field in the
+ RDNSS option. The designated value of all 1's
+ (0xffffffff) represents infinity.";
+ }
+ }
+ }
+ container dnssl {
+ description
+ "A list of domain names that are placed in DNS Search List (DNSSL)
+ options in Router Advertisement messages sent from the interface.";
+ reference
+ "RFC 8106: IPv6 Router Advertisement Options for DNS
+ Configuration";
+ list dnssl-domain {
+ key "domain";
+ description
+ "Domain name for the search list.";
+ leaf domain {
+ type inet:domain-name;
+ description
+ "Domain name for the search list.";
+ }
+ leaf lifetime {
+ type uint32;
+ units "seconds";
+ description
+ "The value that is placed in the Lifetime field in the
+ DNSSL option. The designated value of all 1's
+ (0xffffffff) represents infinity.";
+ }
+ }
+ }
+ }
+ leaf ptm-enable {
+ if-feature ptm-bfd;
+ type boolean;
+ default "true";
+ description
+ "Enable PTM on the interface.";
+ }
container state {
config false;
description
@@ -2111,6 +2743,112 @@ module frr-zebra {
container zebra {
description
"Zebra's vrf specific configuration and operational model.";
+
+ leaf router-id {
+ type yang:dotted-quad;
+ description
+ "A 32-bit number in the form of a dotted quad that is used by
+ some routing protocols identifying a router.";
+ }
+
+ leaf ipv6-router-id {
+ type inet:ipv6-address-no-zone;
+ description
+ "A 128-bit number in the form of an IPv6 address that is used by
+ some routing protocols identifying a router.";
+ }
+
+ list filter-protocol {
+ key "afi-safi protocol";
+ description
+ "Filter routing info exchanged between zebra and protocol.";
+ leaf afi-safi {
+ type identityref {
+ base frr-rt:afi-safi-type;
+ }
+ description
+ "AFI-SAFI type.";
+ }
+ leaf protocol {
+ // This should be identityref to frr-rt:control-plane-protocol someday
+ type string;
+ description
+ "The protocol to filter.";
+ }
+ leaf route-map {
+ type frr-route-map:route-map-ref;
+ mandatory true;
+ description
+ "A route-map to filter routes.";
+ }
+ }
+
+ list filter-nht {
+ key "afi-safi protocol";
+ description
+ "Filter next hop tracking route resolution.";
+ leaf afi-safi {
+ type identityref {
+ base frr-rt:afi-safi-type;
+ }
+ description
+ "AFI-SAFI type.";
+ }
+ leaf protocol {
+ // This should be identityref to frr-rt:control-plane-protocol someday
+ type string;
+ description
+ "The protocol to filter.";
+ }
+ leaf route-map {
+ type frr-route-map:route-map-ref;
+ mandatory true;
+ description
+ "A route-map to filter nexthops.";
+ }
+ }
+
+ leaf resolve-via-default {
+ type boolean;
+ description
+ "Resolve IPv4 nexthops via the default route. This is true by default
+ for traditional profile and false by default for datacenter profile.
+ Removing the leaf sets it back to the default value for the profile.";
+ }
+
+ leaf ipv6-resolve-via-default {
+ type boolean;
+ description
+ "Resolve IPv4 nexthops via the default route. This is true by default
+ for traditional profile and false by default for datacenter profile.
+ Removing the leaf sets it back to the default value for the profile.";
+ }
+
+ container netns {
+ description
+ "Configuration for netns VRF backend.";
+ container table-range {
+ presence "Activates table-range configuration.";
+ description
+ "The range of tables to use for this netns.";
+ leaf start {
+ type uint32;
+ mandatory true;
+ description
+ "The first table to use.";
+ }
+ leaf end {
+ type uint32;
+ mandatory true;
+ must ". >= ../start" {
+ error-message "End table must be greater than or equal to start table";
+ }
+ description
+ "The last table to use.";
+ }
+ }
+ }
+
uses ribs;
uses vrf-vni-mapping;
@@ -2216,6 +2954,22 @@ module frr-zebra {
description
"Limit on the number of updates queued to the dataplane subsystem.";
}
+ leaf ptm-enable {
+ if-feature ptm-bfd;
+ type boolean;
+ default "false";
+ description
+ "Enable PTM globally.";
+ }
+ leaf route-map-delay {
+ type uint32 {
+ range "0..600";
+ }
+ units "seconds";
+ default "5";
+ description
+ "Time to wait before route-map updates are processed.";
+ }
/*
* Debug options
*/
diff --git a/zebra/interface.c b/zebra/interface.c
index f864b91822..6e33d7ec7d 100644
--- a/zebra/interface.c
+++ b/zebra/interface.c
@@ -18,7 +18,6 @@
#include "log.h"
#include "zclient.h"
#include "vrf.h"
-#include "lib/northbound_cli.h"
#include "zebra/rtadv.h"
#include "zebra_ns.h"
@@ -44,8 +43,6 @@ DEFINE_MTYPE_STATIC(ZEBRA, ZINFO, "Zebra Interface Information");
DEFINE_HOOK(zebra_if_extra_info, (struct vty * vty, struct interface *ifp),
(vty, ifp));
-DEFINE_HOOK(zebra_if_config_wr, (struct vty * vty, struct interface *ifp),
- (vty, ifp));
DEFINE_MTYPE(ZEBRA, ZIF_DESC, "Intf desc");
@@ -136,7 +133,7 @@ static int if_zebra_new_hook(struct interface *ifp)
zebra_if->multicast = IF_ZEBRA_DATA_UNSPEC;
zebra_if->mpls_config = IF_ZEBRA_DATA_UNSPEC;
- zebra_if->shutdown = IF_ZEBRA_DATA_OFF;
+ zebra_if->shutdown = IF_ZEBRA_DATA_UNSPEC;
zebra_if->link_nsid = NS_UNKNOWN;
@@ -148,6 +145,8 @@ static int if_zebra_new_hook(struct interface *ifp)
rtadv_if_init(zebra_if);
+ zebra_evpn_mh_if_init(zebra_if);
+
memset(&zebra_if->neigh_mac[0], 0, 6);
/* Initialize installed address chains tree. */
@@ -2877,8 +2876,8 @@ static void if_dump_vty(struct vty *vty, struct interface *ifp)
" Link Delay Variation %u (micro-sec.)\n",
iflp->delay_var);
if (IS_PARAM_SET(iflp, LP_PKT_LOSS))
- vty_out(vty, " Link Packet Loss %g (in %%)\n",
- iflp->pkt_loss);
+ vty_out(vty, " Link Packet Loss %f (in %%)\n",
+ (double)iflp->pkt_loss * LOSS_PRECISION);
if (IS_PARAM_SET(iflp, LP_AVA_BW))
vty_out(vty, " Available Bandwidth %g (Byte/s)\n",
iflp->ava_bw);
@@ -3278,7 +3277,8 @@ static void if_dump_vty_json(struct vty *vty, struct interface *ifp,
iflp->delay_var);
if (IS_PARAM_SET(iflp, LP_PKT_LOSS))
json_object_double_add(json_te, "linkPacketLoss",
- iflp->pkt_loss);
+ (double)iflp->pkt_loss *
+ LOSS_PRECISION);
if (IS_PARAM_SET(iflp, LP_AVA_BW))
json_object_double_add(json_te, "availableBandwidth",
iflp->ava_bw);
@@ -3701,47 +3701,6 @@ int if_multicast_set(struct interface *ifp)
return 0;
}
-DEFUN (multicast,
- multicast_cmd,
- "multicast",
- "Set multicast flag to interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- int ret;
- struct zebra_if *if_data;
-
- if (CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
- ret = if_set_flags(ifp, IFF_MULTICAST);
- if (ret < 0) {
- vty_out(vty, "Can't set multicast flag\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if_refresh(ifp);
- }
- if_data = ifp->info;
- if_data->multicast = IF_ZEBRA_DATA_ON;
-
- return CMD_SUCCESS;
-}
-
-DEFPY (mpls,
- mpls_cmd,
- "[no] mpls <enable$on|disable$off>",
- NO_STR
- MPLS_STR
- "Set mpls to be on for the interface\n"
- "Set mpls to be off for the interface\n")
-{
- if (!no)
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra/mpls",
- NB_OP_CREATE, on ? "true" : "false");
- else
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra/mpls",
- NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
int if_multicast_unset(struct interface *ifp)
{
struct zebra_if *if_data;
@@ -3760,30 +3719,6 @@ int if_multicast_unset(struct interface *ifp)
return 0;
}
-DEFUN (no_multicast,
- no_multicast_cmd,
- "no multicast",
- NO_STR
- "Unset multicast flag to interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- int ret;
- struct zebra_if *if_data;
-
- if (CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
- ret = if_unset_flags(ifp, IFF_MULTICAST);
- if (ret < 0) {
- vty_out(vty, "Can't unset multicast flag\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if_refresh(ifp);
- }
- if_data = ifp->info;
- if_data->multicast = IF_ZEBRA_DATA_OFF;
-
- return CMD_SUCCESS;
-}
-
int if_linkdetect(struct interface *ifp, bool detect)
{
int if_was_operative;
@@ -3807,30 +3742,6 @@ int if_linkdetect(struct interface *ifp, bool detect)
return 0;
}
-DEFUN(linkdetect, linkdetect_cmd, "link-detect",
- "Enable link detection on interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- if_linkdetect(ifp, true);
-
- return CMD_SUCCESS;
-}
-
-
-DEFUN (no_linkdetect,
- no_linkdetect_cmd,
- "no link-detect",
- NO_STR
- "Disable link detection on interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- if_linkdetect(ifp, false);
-
- return CMD_SUCCESS;
-}
-
int if_shutdown(struct interface *ifp)
{
struct zebra_if *if_data;
@@ -3850,31 +3761,6 @@ int if_shutdown(struct interface *ifp)
return 0;
}
-DEFUN (shutdown_if,
- shutdown_if_cmd,
- "shutdown",
- "Shutdown the selected interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- int ret;
- struct zebra_if *if_data;
-
- if (ifp->ifindex != IFINDEX_INTERNAL) {
- /* send RA lifetime of 0 before stopping. rfc4861/6.2.5 */
- rtadv_stop_ra(ifp);
- ret = if_unset_flags(ifp, IFF_UP);
- if (ret < 0) {
- vty_out(vty, "Can't shutdown interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if_refresh(ifp);
- }
- if_data = ifp->info;
- if_data->shutdown = IF_ZEBRA_DATA_ON;
-
- return CMD_SUCCESS;
-}
-
int if_no_shutdown(struct interface *ifp)
{
struct zebra_if *if_data;
@@ -3899,961 +3785,56 @@ int if_no_shutdown(struct interface *ifp)
return 0;
}
-DEFUN (no_shutdown_if,
- no_shutdown_if_cmd,
- "no shutdown",
- NO_STR
- "Shutdown the selected interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- int ret;
- struct zebra_if *if_data;
-
- if (ifp->ifindex != IFINDEX_INTERNAL) {
- ret = if_set_flags(ifp, IFF_UP | IFF_RUNNING);
- if (ret < 0) {
- vty_out(vty, "Can't up interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if_refresh(ifp);
-
- /* Some addresses (in particular, IPv6 addresses on Linux) get
- * removed when the interface goes down. They need to be
- * readded.
- */
- if_addr_wakeup(ifp);
- }
-
- if_data = ifp->info;
- if_data->shutdown = IF_ZEBRA_DATA_OFF;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (bandwidth_if,
- bandwidth_if_cmd,
- "bandwidth (1-100000)",
- "Set bandwidth informational parameter\n"
- "Bandwidth in megabits\n")
-{
- int idx_number = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- unsigned int bandwidth;
-
- bandwidth = strtol(argv[idx_number]->arg, NULL, 10);
-
- /* bandwidth range is <1-100000> */
- if (bandwidth < 1 || bandwidth > 100000) {
- vty_out(vty, "Bandwidth is invalid\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ifp->bandwidth = bandwidth;
-
- /* force protocols to recalculate routes due to cost change */
- if (if_is_operative(ifp))
- zebra_interface_up_update(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_bandwidth_if,
- no_bandwidth_if_cmd,
- "no bandwidth [(1-100000)]",
- NO_STR
- "Set bandwidth informational parameter\n"
- "Bandwidth in megabits\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- ifp->bandwidth = 0;
-
- /* force protocols to recalculate routes due to cost change */
- if (if_is_operative(ifp))
- zebra_interface_up_update(ifp);
-
- return CMD_SUCCESS;
-}
-
-
-struct cmd_node link_params_node = {
- .name = "link-params",
- .node = LINK_PARAMS_NODE,
- .parent_node = INTERFACE_NODE,
- .prompt = "%s(config-link-params)# ",
- .no_xpath = true,
-};
-
-static void link_param_cmd_set_uint32(struct interface *ifp, uint32_t *field,
- uint32_t type, uint32_t value)
+void link_param_cmd_set_uint32(struct interface *ifp, uint32_t *field,
+ uint32_t type, uint32_t value)
{
/* Update field as needed */
if (IS_PARAM_UNSET(ifp->link_params, type) || *field != value) {
*field = value;
SET_PARAM(ifp->link_params, type);
-
- /* force protocols to update LINK STATE due to parameters change
- */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
}
}
-static void link_param_cmd_set_float(struct interface *ifp, float *field,
- uint32_t type, float value)
-{
+void link_param_cmd_set_float(struct interface *ifp, float *field,
+ uint32_t type, float value)
+{
/* Update field as needed */
if (IS_PARAM_UNSET(ifp->link_params, type) || *field != value) {
*field = value;
SET_PARAM(ifp->link_params, type);
-
- /* force protocols to update LINK STATE due to parameters change
- */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
}
}
-static void link_param_cmd_unset(struct interface *ifp, uint32_t type)
+void link_param_cmd_unset(struct interface *ifp, uint32_t type)
{
if (ifp->link_params == NULL)
return;
/* Unset field */
UNSET_PARAM(ifp->link_params, type);
-
- /* force protocols to update LINK STATE due to parameters change */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
-}
-
-DEFUN_NOSH (link_params,
- link_params_cmd,
- "link-params",
- LINK_PARAMS_STR)
-{
- /* vty->qobj_index stays the same @ interface pointer */
- vty->node = LINK_PARAMS_NODE;
-
- return CMD_SUCCESS;
}
-DEFUN_NOSH (exit_link_params,
- exit_link_params_cmd,
- "exit-link-params",
- "Exit from Link Params configuration mode\n")
-{
- if (vty->node == LINK_PARAMS_NODE)
- vty->node = INTERFACE_NODE;
- return CMD_SUCCESS;
-}
-
-/* Specific Traffic Engineering parameters commands */
-DEFUN (link_params_enable,
- link_params_enable_cmd,
- "enable",
- "Activate link parameters on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- /* This command could be issue at startup, when activate MPLS TE */
- /* on a new interface or after a ON / OFF / ON toggle */
- /* In all case, TE parameters are reset to their default factory */
- if (IS_ZEBRA_DEBUG_EVENT || IS_ZEBRA_DEBUG_MPLS)
- zlog_debug(
- "Link-params: enable TE link parameters on interface %s",
- ifp->name);
-
- if (!if_link_params_get(ifp))
- if_link_params_enable(ifp);
-
- /* force protocols to update LINK STATE due to parameters change */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_enable,
- no_link_params_enable_cmd,
- "no enable",
- NO_STR
- "Disable link parameters on this interface\n")
-{
- char xpath[XPATH_MAXLEN];
- int ret;
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- if (IS_ZEBRA_DEBUG_EVENT || IS_ZEBRA_DEBUG_MPLS)
- zlog_debug("MPLS-TE: disable TE link parameters on interface %s",
- ifp->name);
-
- if_link_params_free(ifp);
-
- snprintf(
- xpath, sizeof(xpath),
- "/frr-interface:lib/interface[name='%s']/frr-zebra:zebra/link-params/affinities",
- ifp->name);
- if (yang_dnode_exists(running_config->dnode, xpath))
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- ret = nb_cli_apply_changes(vty, NULL);
-
- if (ret != CMD_SUCCESS)
- return ret;
-
- /* force protocols to update LINK STATE due to parameters change */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
-
- return CMD_SUCCESS;
-}
-
-/* STANDARD TE metrics */
-DEFUN (link_params_metric,
- link_params_metric_cmd,
- "metric (0-4294967295)",
- "Link metric for MPLS-TE purpose\n"
- "Metric value in decimal\n")
-{
- int idx_number = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- uint32_t metric;
-
- metric = strtoul(argv[idx_number]->arg, NULL, 10);
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update TE metric if needed */
- link_param_cmd_set_uint32(ifp, &iflp->te_metric, LP_TE_METRIC, metric);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_metric,
- no_link_params_metric_cmd,
- "no metric",
- NO_STR
- "Disable Link Metric on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- /* Unset TE Metric */
- link_param_cmd_unset(ifp, LP_TE_METRIC);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_maxbw,
- link_params_maxbw_cmd,
- "max-bw BANDWIDTH",
- "Maximum bandwidth that can be used\n"
- "Bytes/second (IEEE floating point format)\n")
-{
- int idx_bandwidth = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
-
- float bw;
-
- if (sscanf(argv[idx_bandwidth]->arg, "%g", &bw) != 1) {
- vty_out(vty, "link_params_maxbw: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Check that Maximum bandwidth is not lower than other bandwidth
- * parameters */
- if (iflp && ((bw <= iflp->max_rsv_bw) || (bw <= iflp->unrsv_bw[0]) ||
- (bw <= iflp->unrsv_bw[1]) || (bw <= iflp->unrsv_bw[2]) ||
- (bw <= iflp->unrsv_bw[3]) || (bw <= iflp->unrsv_bw[4]) ||
- (bw <= iflp->unrsv_bw[5]) || (bw <= iflp->unrsv_bw[6]) ||
- (bw <= iflp->unrsv_bw[7]) || (bw <= iflp->ava_bw) ||
- (bw <= iflp->res_bw) || (bw <= iflp->use_bw))) {
- vty_out(vty,
- "Maximum Bandwidth could not be lower than others bandwidth\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Maximum Bandwidth if needed */
- link_param_cmd_set_float(ifp, &iflp->max_bw, LP_MAX_BW, bw);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_max_rsv_bw,
- link_params_max_rsv_bw_cmd,
- "max-rsv-bw BANDWIDTH",
- "Maximum bandwidth that may be reserved\n"
- "Bytes/second (IEEE floating point format)\n")
-{
- int idx_bandwidth = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- float bw;
-
- if (sscanf(argv[idx_bandwidth]->arg, "%g", &bw) != 1) {
- vty_out(vty, "link_params_max_rsv_bw: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Check that bandwidth is not greater than maximum bandwidth parameter
- */
- if (iflp && bw > iflp->max_bw) {
- vty_out(vty,
- "Maximum Reservable Bandwidth could not be greater than Maximum Bandwidth (%g)\n",
- iflp->max_bw);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Maximum Reservable Bandwidth if needed */
- link_param_cmd_set_float(ifp, &iflp->max_rsv_bw, LP_MAX_RSV_BW, bw);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_unrsv_bw,
- link_params_unrsv_bw_cmd,
- "unrsv-bw (0-7) BANDWIDTH",
- "Unreserved bandwidth at each priority level\n"
- "Priority\n"
- "Bytes/second (IEEE floating point format)\n")
-{
- int idx_number = 1;
- int idx_bandwidth = 2;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- int priority;
- float bw;
-
- /* We don't have to consider about range check here. */
- if (sscanf(argv[idx_number]->arg, "%d", &priority) != 1) {
- vty_out(vty, "link_params_unrsv_bw: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (sscanf(argv[idx_bandwidth]->arg, "%g", &bw) != 1) {
- vty_out(vty, "link_params_unrsv_bw: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Check that bandwidth is not greater than maximum bandwidth parameter
- */
- if (iflp && bw > iflp->max_bw) {
- vty_out(vty,
- "UnReserved Bandwidth could not be greater than Maximum Bandwidth (%g)\n",
- iflp->max_bw);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Unreserved Bandwidth if needed */
- link_param_cmd_set_float(ifp, &iflp->unrsv_bw[priority], LP_UNRSV_BW,
- bw);
-
- return CMD_SUCCESS;
-}
-
-DEFPY_YANG(link_params_admin_grp, link_params_admin_grp_cmd,
- "admin-grp BITPATTERN",
- "Administrative group membership\n"
- "32-bit Hexadecimal value (e.g. 0xa1)\n")
-{
- int idx_bitpattern = 1;
- unsigned long value;
- char value_str[11];
-
- if (sscanf(argv[idx_bitpattern]->arg, "0x%lx", &value) != 1) {
- vty_out(vty, "link_params_admin_grp: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (value > 0xFFFFFFFF) {
- vty_out(vty, "value must be not be superior to 0xFFFFFFFF\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- snprintf(value_str, sizeof(value_str), "%ld", value);
-
- nb_cli_enqueue_change(
- vty, "./frr-zebra:zebra/link-params/legacy-admin-group",
- NB_OP_MODIFY, value_str);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(no_link_params_admin_grp, no_link_params_admin_grp_cmd,
- "no admin-grp",
- NO_STR "Disable Administrative group membership on this interface\n")
-{
- nb_cli_enqueue_change(
- vty, "./frr-zebra:zebra/link-params/legacy-admin-group",
- NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-/* RFC5392 & RFC5316: INTER-AS */
-DEFUN (link_params_inter_as,
- link_params_inter_as_cmd,
- "neighbor A.B.C.D as (1-4294967295)",
- "Configure remote ASBR information (Neighbor IP address and AS number)\n"
- "Remote IP address in dot decimal A.B.C.D\n"
- "Remote AS number\n"
- "AS number in the range <1-4294967295>\n")
-{
- int idx_ipv4 = 1;
- int idx_number = 3;
-
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- struct in_addr addr;
- uint32_t as;
-
- if (!inet_aton(argv[idx_ipv4]->arg, &addr)) {
- vty_out(vty, "Please specify Router-Addr by A.B.C.D\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- as = strtoul(argv[idx_number]->arg, NULL, 10);
-
- /* Update Remote IP and Remote AS fields if needed */
- if (IS_PARAM_UNSET(iflp, LP_RMT_AS) || iflp->rmt_as != as
- || iflp->rmt_ip.s_addr != addr.s_addr) {
-
- iflp->rmt_as = as;
- iflp->rmt_ip.s_addr = addr.s_addr;
- SET_PARAM(iflp, LP_RMT_AS);
-
- /* force protocols to update LINK STATE due to parameters change
- */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
- }
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_inter_as,
- no_link_params_inter_as_cmd,
- "no neighbor",
- NO_STR
- "Remove Neighbor IP address and AS number for Inter-AS TE\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
-
- if (!iflp)
- return CMD_SUCCESS;
-
- /* Reset Remote IP and AS neighbor */
- iflp->rmt_as = 0;
- iflp->rmt_ip.s_addr = 0;
- UNSET_PARAM(iflp, LP_RMT_AS);
-
- /* force protocols to update LINK STATE due to parameters change */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
-
- return CMD_SUCCESS;
-}
-
-/* RFC7471: OSPF Traffic Engineering (TE) Metric extensions &
- * draft-ietf-isis-metric-extensions-07.txt */
-DEFUN (link_params_delay,
- link_params_delay_cmd,
- "delay (0-16777215) [min (0-16777215) max (0-16777215)]",
- "Unidirectional Average Link Delay\n"
- "Average delay in micro-second as decimal (0...16777215)\n"
- "Minimum delay\n"
- "Minimum delay in micro-second as decimal (0...16777215)\n"
- "Maximum delay\n"
- "Maximum delay in micro-second as decimal (0...16777215)\n")
-{
- /* Get and Check new delay values */
- uint32_t delay = 0, low = 0, high = 0;
- delay = strtoul(argv[1]->arg, NULL, 10);
- if (argc == 6) {
- low = strtoul(argv[3]->arg, NULL, 10);
- high = strtoul(argv[5]->arg, NULL, 10);
- }
-
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- uint8_t update = 0;
-
- if (argc == 2) {
- /*
- * Check new delay value against old Min and Max delays if set
- *
- * RFC 7471 Section 4.2.7:
- * It is possible for min delay and max delay to be
- * the same value.
- *
- * Therefore, it is also allowed that the average
- * delay be equal to the min delay or max delay.
- */
- if (iflp && IS_PARAM_SET(iflp, LP_MM_DELAY) &&
- (delay < iflp->min_delay || delay > iflp->max_delay)) {
- vty_out(vty,
- "Average delay should be in range Min (%d) - Max (%d) delay\n",
- iflp->min_delay, iflp->max_delay);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update delay if value is not set or change */
- if (IS_PARAM_UNSET(iflp, LP_DELAY) || iflp->av_delay != delay) {
- iflp->av_delay = delay;
- SET_PARAM(iflp, LP_DELAY);
- update = 1;
- }
- /* Unset Min and Max delays if already set */
- if (IS_PARAM_SET(iflp, LP_MM_DELAY)) {
- iflp->min_delay = 0;
- iflp->max_delay = 0;
- UNSET_PARAM(iflp, LP_MM_DELAY);
- update = 1;
- }
- } else {
- /*
- * Check new delays value coherency. See above note
- * regarding average delay equal to min/max allowed
- */
- if (delay < low || delay > high) {
- vty_out(vty,
- "Average delay should be in range Min (%d) - Max (%d) delay\n",
- low, high);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Delays if needed */
- if (IS_PARAM_UNSET(iflp, LP_DELAY)
- || IS_PARAM_UNSET(iflp, LP_MM_DELAY)
- || iflp->av_delay != delay || iflp->min_delay != low
- || iflp->max_delay != high) {
- iflp->av_delay = delay;
- SET_PARAM(iflp, LP_DELAY);
- iflp->min_delay = low;
- iflp->max_delay = high;
- SET_PARAM(iflp, LP_MM_DELAY);
- update = 1;
- }
- }
-
- /* force protocols to update LINK STATE due to parameters change */
- if (update == 1 && if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_delay,
- no_link_params_delay_cmd,
- "no delay",
- NO_STR
- "Disable Unidirectional Average, Min & Max Link Delay on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
-
- if (!iflp)
- return CMD_SUCCESS;
-
- /* Unset Delays */
- iflp->av_delay = 0;
- UNSET_PARAM(iflp, LP_DELAY);
- iflp->min_delay = 0;
- iflp->max_delay = 0;
- UNSET_PARAM(iflp, LP_MM_DELAY);
-
- /* force protocols to update LINK STATE due to parameters change */
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_delay_var,
- link_params_delay_var_cmd,
- "delay-variation (0-16777215)",
- "Unidirectional Link Delay Variation\n"
- "delay variation in micro-second as decimal (0...16777215)\n")
-{
- int idx_number = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- uint32_t value;
-
- value = strtoul(argv[idx_number]->arg, NULL, 10);
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Delay Variation if needed */
- link_param_cmd_set_uint32(ifp, &iflp->delay_var, LP_DELAY_VAR, value);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_delay_var,
- no_link_params_delay_var_cmd,
- "no delay-variation",
- NO_STR
- "Disable Unidirectional Delay Variation on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- /* Unset Delay Variation */
- link_param_cmd_unset(ifp, LP_DELAY_VAR);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_pkt_loss,
- link_params_pkt_loss_cmd,
- "packet-loss PERCENTAGE",
- "Unidirectional Link Packet Loss\n"
- "percentage of total traffic by 0.000003% step and less than 50.331642%\n")
-{
- int idx_percentage = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- float fval;
-
- if (sscanf(argv[idx_percentage]->arg, "%g", &fval) != 1) {
- vty_out(vty, "link_params_pkt_loss: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (fval > MAX_PKT_LOSS)
- fval = MAX_PKT_LOSS;
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Packet Loss if needed */
- link_param_cmd_set_float(ifp, &iflp->pkt_loss, LP_PKT_LOSS, fval);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_pkt_loss,
- no_link_params_pkt_loss_cmd,
- "no packet-loss",
- NO_STR
- "Disable Unidirectional Link Packet Loss on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- /* Unset Packet Loss */
- link_param_cmd_unset(ifp, LP_PKT_LOSS);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_res_bw,
- link_params_res_bw_cmd,
- "res-bw BANDWIDTH",
- "Unidirectional Residual Bandwidth\n"
- "Bytes/second (IEEE floating point format)\n")
-{
- int idx_bandwidth = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- float bw;
-
- if (sscanf(argv[idx_bandwidth]->arg, "%g", &bw) != 1) {
- vty_out(vty, "link_params_res_bw: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Check that bandwidth is not greater than maximum bandwidth parameter
- */
- if (iflp && bw > iflp->max_bw) {
- vty_out(vty,
- "Residual Bandwidth could not be greater than Maximum Bandwidth (%g)\n",
- iflp->max_bw);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Residual Bandwidth if needed */
- link_param_cmd_set_float(ifp, &iflp->res_bw, LP_RES_BW, bw);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_res_bw,
- no_link_params_res_bw_cmd,
- "no res-bw",
- NO_STR
- "Disable Unidirectional Residual Bandwidth on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- /* Unset Residual Bandwidth */
- link_param_cmd_unset(ifp, LP_RES_BW);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_ava_bw,
- link_params_ava_bw_cmd,
- "ava-bw BANDWIDTH",
- "Unidirectional Available Bandwidth\n"
- "Bytes/second (IEEE floating point format)\n")
-{
- int idx_bandwidth = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- float bw;
-
- if (sscanf(argv[idx_bandwidth]->arg, "%g", &bw) != 1) {
- vty_out(vty, "link_params_ava_bw: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Check that bandwidth is not greater than maximum bandwidth parameter
- */
- if (iflp && bw > iflp->max_bw) {
- vty_out(vty,
- "Available Bandwidth could not be greater than Maximum Bandwidth (%g)\n",
- iflp->max_bw);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Residual Bandwidth if needed */
- link_param_cmd_set_float(ifp, &iflp->ava_bw, LP_AVA_BW, bw);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_ava_bw,
- no_link_params_ava_bw_cmd,
- "no ava-bw",
- NO_STR
- "Disable Unidirectional Available Bandwidth on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- /* Unset Available Bandwidth */
- link_param_cmd_unset(ifp, LP_AVA_BW);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (link_params_use_bw,
- link_params_use_bw_cmd,
- "use-bw BANDWIDTH",
- "Unidirectional Utilised Bandwidth\n"
- "Bytes/second (IEEE floating point format)\n")
-{
- int idx_bandwidth = 1;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct if_link_params *iflp = if_link_params_get(ifp);
- float bw;
-
- if (sscanf(argv[idx_bandwidth]->arg, "%g", &bw) != 1) {
- vty_out(vty, "link_params_use_bw: fscanf: %s\n",
- safe_strerror(errno));
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Check that bandwidth is not greater than maximum bandwidth parameter
- */
- if (iflp && bw > iflp->max_bw) {
- vty_out(vty,
- "Utilised Bandwidth could not be greater than Maximum Bandwidth (%g)\n",
- iflp->max_bw);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!iflp)
- iflp = if_link_params_enable(ifp);
-
- /* Update Utilized Bandwidth if needed */
- link_param_cmd_set_float(ifp, &iflp->use_bw, LP_USE_BW, bw);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_link_params_use_bw,
- no_link_params_use_bw_cmd,
- "no use-bw",
- NO_STR
- "Disable Unidirectional Utilised Bandwidth on this interface\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
-
- /* Unset Utilised Bandwidth */
- link_param_cmd_unset(ifp, LP_USE_BW);
-
- return CMD_SUCCESS;
-}
-
-static int ag_change(struct vty *vty, int argc, struct cmd_token **argv,
- const char *xpath_base, bool no, int start_idx)
-{
- char xpath[XPATH_MAXLEN];
-
- for (int i = start_idx; i < argc; i++) {
- snprintf(xpath, XPATH_MAXLEN, "%s[.='%s']", xpath_base,
- argv[i]->arg);
- nb_cli_enqueue_change(vty, xpath,
- no ? NB_OP_DESTROY : NB_OP_CREATE, NULL);
- }
- return nb_cli_apply_changes(vty, NULL);
-}
-
-/*
- * XPath:
- * /frr-interface:lib/interface/frr-zebra:zebra/link-params/affinities/affinity
- */
-DEFPY_YANG(link_params_affinity, link_params_affinity_cmd,
- "[no] affinity NAME...",
- NO_STR
- "Interface affinities\n"
- "Affinity names\n")
-{
- return ag_change(vty, argc, argv,
- "./frr-zebra:zebra/link-params/affinities/affinity",
- no, no ? 2 : 1);
-}
-
-
-/*
- * XPath:
- * /frr-interface:lib/interface/frr-zebra:zebra/link-params/affinities/affinity-mode
- */
-DEFPY_YANG(link_params_affinity_mode, link_params_affinity_mode_cmd,
- "affinity-mode <standard|extended|both>$affmode",
- "Interface affinity mode\n"
- "Standard Admin-Group only RFC3630,5305,5329\n"
- "Extended Admin-Group only RFC7308 (default)\n"
- "Standard and extended Admin-Group format\n")
-{
- const char *xpath = "./frr-zebra:zebra/link-params/affinity-mode";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_MODIFY, affmode);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(no_link_params_affinity_mode, no_link_params_affinity_mode_cmd,
- "no affinity-mode [<standard|extended|both>]",
- NO_STR
- "Interface affinity mode\n"
- "Standard Admin-Group only RFC3630,5305,5329\n"
- "Extended Admin-Group only RFC7308 (default)\n"
- "Standard and extended Admin-Group format\n")
-{
- const char *xpath = "./frr-zebra:zebra/link-params/affinity-mode";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_MODIFY, "extended");
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-static int ag_iter_cb(const struct lyd_node *dnode, void *arg)
-{
- struct vty *vty = (struct vty *)arg;
-
- vty_out(vty, " %s", yang_dnode_get_string(dnode, "."));
- return YANG_ITER_CONTINUE;
-}
-
-void cli_show_legacy_admin_group(struct vty *vty, const struct lyd_node *dnode,
- bool show_defaults)
-{
- vty_out(vty, " admin-grp 0x%x\n",
- yang_dnode_get_uint32(dnode, NULL));
-}
-
-void cli_show_affinity_mode(struct vty *vty, const struct lyd_node *dnode,
- bool show_defaults)
-{
- enum affinity_mode affinity_mode = yang_dnode_get_enum(dnode, ".");
-
- if (affinity_mode == AFFINITY_MODE_STANDARD)
- vty_out(vty, " affinity-mode standard\n");
- else if (affinity_mode == AFFINITY_MODE_BOTH)
- vty_out(vty, " affinity-mode both\n");
- else if (affinity_mode == AFFINITY_MODE_EXTENDED && show_defaults)
- vty_out(vty, " affinity-mode extended\n");
-}
-
-void cli_show_affinity(struct vty *vty, const struct lyd_node *dnode,
- bool show_defaults)
-{
- if (!yang_dnode_exists(dnode, "affinity"))
- return;
-
- vty_out(vty, " affinity");
- yang_dnode_iterate(ag_iter_cb, vty, dnode, "affinity");
- vty_out(vty, "\n");
-}
-
-int if_ip_address_install(struct interface *ifp, struct prefix *prefix,
- const char *label, struct prefix *pp)
+void if_ip_address_install(struct interface *ifp, struct prefix *prefix,
+ const char *label, struct prefix *pp)
{
struct zebra_if *if_data;
- struct prefix_ipv4 lp;
- struct prefix_ipv4 *p;
struct connected *ifc;
- enum zebra_dplane_result dplane_res;
if_data = ifp->info;
- lp.family = prefix->family;
- lp.prefix = prefix->u.prefix4;
- lp.prefixlen = prefix->prefixlen;
- apply_mask_ipv4(&lp);
-
- ifc = connected_check_ptp(ifp, &lp, pp ? pp : NULL);
+ ifc = connected_check_ptp(ifp, prefix, pp);
if (!ifc) {
ifc = connected_new();
ifc->ifp = ifp;
/* Address. */
- p = prefix_ipv4_new();
- *p = lp;
- ifc->address = (struct prefix *)p;
+ ifc->address = prefix_new();
+ prefix_copy(ifc->address, prefix);
if (pp) {
SET_FLAG(ifc->flags, ZEBRA_IFA_PEER);
- p = prefix_ipv4_new();
- *p = *(struct prefix_ipv4 *)pp;
- ifc->destination = (struct prefix *)p;
+ ifc->destination = prefix_new();
+ prefix_copy(ifc->destination, pp);
}
/* Label. */
@@ -4878,13 +3859,7 @@ int if_ip_address_install(struct interface *ifp, struct prefix *prefix,
if_refresh(ifp);
}
- dplane_res = dplane_intf_addr_set(ifp, ifc);
- if (dplane_res == ZEBRA_DPLANE_REQUEST_FAILURE) {
- zlog_debug(
- "dplane can't set interface IP address: %s.",
- dplane_res2str(dplane_res));
- return NB_ERR;
- }
+ dplane_intf_addr_set(ifp, ifc);
SET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED);
/* The address will be advertised to zebra clients when the
@@ -4892,127 +3867,16 @@ int if_ip_address_install(struct interface *ifp, struct prefix *prefix,
* from the kernel has been received.
* It will also be added to the subnet chain list, then. */
}
-
- return 0;
}
-static int ip_address_install(struct vty *vty, struct interface *ifp,
- const char *addr_str, const char *peer_str,
- const char *label)
+void if_ip_address_uninstall(struct interface *ifp, struct prefix *prefix,
+ struct prefix *pp)
{
- struct zebra_if *if_data;
- struct prefix_ipv4 lp, pp;
struct connected *ifc;
- struct prefix_ipv4 *p;
- int ret;
- enum zebra_dplane_result dplane_res;
-
- if_data = ifp->info;
-
- ret = str2prefix_ipv4(addr_str, &lp);
- if (ret <= 0) {
- vty_out(vty, "%% Malformed address \n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if (ipv4_martian(&lp.prefix)) {
- vty_out(vty, "%% Invalid address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (peer_str) {
- if (lp.prefixlen != IPV4_MAX_BITLEN) {
- vty_out(vty,
- "%% Local prefix length for P-t-P address must be /32\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = str2prefix_ipv4(peer_str, &pp);
- if (ret <= 0) {
- vty_out(vty, "%% Malformed peer address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- }
-
- ifc = connected_check_ptp(ifp, &lp, peer_str ? &pp : NULL);
- if (!ifc) {
- ifc = connected_new();
- ifc->ifp = ifp;
-
- /* Address. */
- p = prefix_ipv4_new();
- *p = lp;
- ifc->address = (struct prefix *)p;
-
- if (peer_str) {
- SET_FLAG(ifc->flags, ZEBRA_IFA_PEER);
- p = prefix_ipv4_new();
- *p = pp;
- ifc->destination = (struct prefix *)p;
- }
-
- /* Label. */
- if (label)
- ifc->label = XSTRDUP(MTYPE_CONNECTED_LABEL, label);
-
- /* Add to linked list. */
- if_connected_add_tail(ifp->connected, ifc);
- }
-
- /* This address is configured from zebra. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED))
- SET_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED);
-
- /* In case of this route need to install kernel. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_QUEUED) &&
- CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE) &&
- !(if_data && if_data->shutdown == IF_ZEBRA_DATA_ON)) {
- /* Some system need to up the interface to set IP address. */
- if (!if_is_up(ifp)) {
- if_set_flags(ifp, IFF_UP | IFF_RUNNING);
- if_refresh(ifp);
- }
-
- dplane_res = dplane_intf_addr_set(ifp, ifc);
- if (dplane_res == ZEBRA_DPLANE_REQUEST_FAILURE) {
- vty_out(vty, "%% Can't set interface IP address: %s.\n",
- dplane_res2str(dplane_res));
- return CMD_WARNING_CONFIG_FAILED;
- }
+ ifc = connected_check_ptp(ifp, prefix, pp);
+ assert(ifc);
- SET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED);
- /* The address will be advertised to zebra clients when the
- * notification
- * from the kernel has been received.
- * It will also be added to the subnet chain list, then. */
- }
-
- return CMD_SUCCESS;
-}
-
-int if_ip_address_uinstall(struct interface *ifp, struct prefix *prefix)
-{
- struct connected *ifc = NULL;
- enum zebra_dplane_result dplane_res;
-
- if (prefix->family == AF_INET) {
- /* Check current interface address. */
- ifc = connected_check_ptp(ifp, prefix, NULL);
- if (!ifc) {
- zlog_debug("interface %s Can't find address",
- ifp->name);
- return -1;
- }
-
- } else if (prefix->family == AF_INET6) {
- /* Check current interface address. */
- ifc = connected_check(ifp, prefix);
- }
-
- if (!ifc) {
- zlog_debug("interface %s Can't find address", ifp->name);
- return -1;
- }
UNSET_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED);
/* This is not real address or interface is not active. */
@@ -5020,276 +3884,30 @@ int if_ip_address_uinstall(struct interface *ifp, struct prefix *prefix)
|| !CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
if_connected_del(ifp->connected, ifc);
connected_free(&ifc);
- return CMD_WARNING_CONFIG_FAILED;
+ return;
}
/* This is real route. */
- dplane_res = dplane_intf_addr_unset(ifp, ifc);
- if (dplane_res == ZEBRA_DPLANE_REQUEST_FAILURE) {
- zlog_debug("Can't unset interface IP address: %s.",
- dplane_res2str(dplane_res));
- return -1;
- }
- UNSET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED);
-
- return 0;
-}
-
-static int ip_address_uninstall(struct vty *vty, struct interface *ifp,
- const char *addr_str, const char *peer_str,
- const char *label)
-{
- struct prefix_ipv4 lp, pp;
- struct connected *ifc;
- int ret;
- enum zebra_dplane_result dplane_res;
-
- /* Convert to prefix structure. */
- ret = str2prefix_ipv4(addr_str, &lp);
- if (ret <= 0) {
- vty_out(vty, "%% Malformed address \n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (peer_str) {
- if (lp.prefixlen != IPV4_MAX_BITLEN) {
- vty_out(vty,
- "%% Local prefix length for P-t-P address must be /32\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
+ dplane_intf_addr_unset(ifp, ifc);
- ret = str2prefix_ipv4(peer_str, &pp);
- if (ret <= 0) {
- vty_out(vty, "%% Malformed peer address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- }
-
- /* Check current interface address. */
- ifc = connected_check_ptp(ifp, &lp, peer_str ? &pp : NULL);
- if (!ifc) {
- vty_out(vty, "%% Can't find address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* This is not configured address. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED))
- return CMD_WARNING_CONFIG_FAILED;
-
- UNSET_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED);
-
- /* This is not real address or interface is not active. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_QUEUED)
- || !CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
- if_connected_del(ifp->connected, ifc);
- connected_free(&ifc);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* This is real route. */
- dplane_res = dplane_intf_addr_unset(ifp, ifc);
- if (dplane_res == ZEBRA_DPLANE_REQUEST_FAILURE) {
- vty_out(vty, "%% Can't unset interface IP address: %s.\n",
- dplane_res2str(dplane_res));
- return CMD_WARNING_CONFIG_FAILED;
- }
UNSET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED);
- /* we will receive a kernel notification about this route being removed.
- * this will trigger its removal from the connected list. */
- return CMD_SUCCESS;
-}
-
-DEFUN (ip_address,
- ip_address_cmd,
- "ip address A.B.C.D/M",
- "Interface Internet Protocol config commands\n"
- "Set the IP address of an interface\n"
- "IP address (e.g. 10.0.0.1/8)\n")
-{
- int idx_ipv4_prefixlen = 2;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ip_address_install(vty, ifp, argv[idx_ipv4_prefixlen]->arg, NULL,
- NULL);
-}
-
-DEFUN (no_ip_address,
- no_ip_address_cmd,
- "no ip address A.B.C.D/M",
- NO_STR
- "Interface Internet Protocol config commands\n"
- "Set the IP address of an interface\n"
- "IP Address (e.g. 10.0.0.1/8)\n")
-{
- int idx_ipv4_prefixlen = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ip_address_uninstall(vty, ifp, argv[idx_ipv4_prefixlen]->arg,
- NULL, NULL);
-}
-
-DEFUN(ip_address_peer,
- ip_address_peer_cmd,
- "ip address A.B.C.D peer A.B.C.D/M",
- "Interface Internet Protocol config commands\n"
- "Set the IP address of an interface\n"
- "Local IP (e.g. 10.0.0.1) for P-t-P address\n"
- "Specify P-t-P address\n"
- "Peer IP address (e.g. 10.0.0.1/8)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ip_address_install(vty, ifp, argv[2]->arg, argv[4]->arg, NULL);
-}
-
-DEFUN(no_ip_address_peer,
- no_ip_address_peer_cmd,
- "no ip address A.B.C.D peer A.B.C.D/M",
- NO_STR
- "Interface Internet Protocol config commands\n"
- "Set the IP address of an interface\n"
- "Local IP (e.g. 10.0.0.1) for P-t-P address\n"
- "Specify P-t-P address\n"
- "Peer IP address (e.g. 10.0.0.1/8)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ip_address_uninstall(vty, ifp, argv[3]->arg, argv[5]->arg, NULL);
-}
-
-#ifdef HAVE_NETLINK
-DEFUN (ip_address_label,
- ip_address_label_cmd,
- "ip address A.B.C.D/M label LINE",
- "Interface Internet Protocol config commands\n"
- "Set the IP address of an interface\n"
- "IP address (e.g. 10.0.0.1/8)\n"
- "Label of this address\n"
- "Label\n")
-{
- int idx_ipv4_prefixlen = 2;
- int idx_line = 4;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ip_address_install(vty, ifp, argv[idx_ipv4_prefixlen]->arg, NULL,
- argv[idx_line]->arg);
-}
-
-DEFUN (no_ip_address_label,
- no_ip_address_label_cmd,
- "no ip address A.B.C.D/M label LINE",
- NO_STR
- "Interface Internet Protocol config commands\n"
- "Set the IP address of an interface\n"
- "IP address (e.g. 10.0.0.1/8)\n"
- "Label of this address\n"
- "Label\n")
-{
- int idx_ipv4_prefixlen = 3;
- int idx_line = 5;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ip_address_uninstall(vty, ifp, argv[idx_ipv4_prefixlen]->arg,
- NULL, argv[idx_line]->arg);
-}
-#endif /* HAVE_NETLINK */
-
-int if_ipv6_address_install(struct interface *ifp, struct prefix *prefix,
- const char *label)
-{
- struct zebra_if *if_data;
- struct prefix_ipv6 cp;
- struct connected *ifc;
- struct prefix_ipv6 *p;
- enum zebra_dplane_result dplane_res;
-
- if_data = ifp->info;
-
- cp.family = prefix->family;
- cp.prefixlen = prefix->prefixlen;
- cp.prefix = prefix->u.prefix6;
- apply_mask_ipv6(&cp);
-
- ifc = connected_check(ifp, (struct prefix *)&cp);
- if (!ifc) {
- ifc = connected_new();
- ifc->ifp = ifp;
-
- /* Address. */
- p = prefix_ipv6_new();
- *p = cp;
- ifc->address = (struct prefix *)p;
-
- /* Label. */
- if (label)
- ifc->label = XSTRDUP(MTYPE_CONNECTED_LABEL, label);
-
- /* Add to linked list. */
- if_connected_add_tail(ifp->connected, ifc);
- }
-
- /* This address is configured from zebra. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED))
- SET_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED);
-
- /* In case of this route need to install kernel. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_QUEUED) &&
- CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE) &&
- !(if_data && if_data->shutdown == IF_ZEBRA_DATA_ON)) {
- /* Some system need to up the interface to set IP address. */
- if (!if_is_up(ifp)) {
- if_set_flags(ifp, IFF_UP | IFF_RUNNING);
- if_refresh(ifp);
- }
-
- dplane_res = dplane_intf_addr_set(ifp, ifc);
- if (dplane_res == ZEBRA_DPLANE_REQUEST_FAILURE) {
- zlog_debug(
- "dplane can't set interface IP address: %s.",
- dplane_res2str(dplane_res));
- return NB_ERR;
- }
-
- SET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED);
- /* The address will be advertised to zebra clients when the
- * notification
- * from the kernel has been received. */
- }
-
- return 0;
}
-static int ipv6_address_install(struct vty *vty, struct interface *ifp,
- const char *addr_str, const char *peer_str,
- const char *label)
+void if_ipv6_address_install(struct interface *ifp, struct prefix *prefix)
{
struct zebra_if *if_data;
- struct prefix_ipv6 cp;
struct connected *ifc;
- struct prefix_ipv6 *p;
- int ret;
- enum zebra_dplane_result dplane_res;
if_data = ifp->info;
- ret = str2prefix_ipv6(addr_str, &cp);
- if (ret <= 0) {
- vty_out(vty, "%% Malformed address \n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (ipv6_martian(&cp.prefix)) {
- vty_out(vty, "%% Invalid address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ifc = connected_check(ifp, (struct prefix *)&cp);
+ ifc = connected_check(ifp, prefix);
if (!ifc) {
ifc = connected_new();
ifc->ifp = ifp;
/* Address. */
- p = prefix_ipv6_new();
- *p = cp;
- ifc->address = (struct prefix *)p;
-
- /* Label. */
- if (label)
- ifc->label = XSTRDUP(MTYPE_CONNECTED_LABEL, label);
+ ifc->address = prefix_new();
+ prefix_copy(ifc->address, prefix);
/* Add to linked list. */
if_connected_add_tail(ifp->connected, ifc);
@@ -5309,48 +3927,21 @@ static int ipv6_address_install(struct vty *vty, struct interface *ifp,
if_refresh(ifp);
}
- dplane_res = dplane_intf_addr_set(ifp, ifc);
- if (dplane_res == ZEBRA_DPLANE_REQUEST_FAILURE) {
- vty_out(vty, "%% Can't set interface IP address: %s.\n",
- dplane_res2str(dplane_res));
- return CMD_WARNING_CONFIG_FAILED;
- }
+ dplane_intf_addr_set(ifp, ifc);
SET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED);
/* The address will be advertised to zebra clients when the
* notification
* from the kernel has been received. */
}
-
- return CMD_SUCCESS;
}
-static int ipv6_address_uninstall(struct vty *vty, struct interface *ifp,
- const char *addr_str, const char *peer_str,
- const char *label)
+void if_ipv6_address_uninstall(struct interface *ifp, struct prefix *prefix)
{
- struct prefix_ipv6 cp;
struct connected *ifc;
- int ret;
- enum zebra_dplane_result dplane_res;
-
- /* Convert to prefix structure. */
- ret = str2prefix_ipv6(addr_str, &cp);
- if (ret <= 0) {
- vty_out(vty, "%% Malformed address \n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- /* Check current interface address. */
- ifc = connected_check(ifp, (struct prefix *)&cp);
- if (!ifc) {
- vty_out(vty, "%% Can't find address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* This is not configured address. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED))
- return CMD_WARNING_CONFIG_FAILED;
+ ifc = connected_check(ifp, prefix);
+ assert(ifc);
UNSET_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED);
@@ -5359,199 +3950,13 @@ static int ipv6_address_uninstall(struct vty *vty, struct interface *ifp,
|| !CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
if_connected_del(ifp->connected, ifc);
connected_free(&ifc);
- return CMD_WARNING_CONFIG_FAILED;
+ return;
}
/* This is real route. */
- dplane_res = dplane_intf_addr_unset(ifp, ifc);
- if (dplane_res == ZEBRA_DPLANE_REQUEST_FAILURE) {
- vty_out(vty, "%% Can't unset interface IP address: %s.\n",
- dplane_res2str(dplane_res));
- return CMD_WARNING_CONFIG_FAILED;
- }
+ dplane_intf_addr_unset(ifp, ifc);
UNSET_FLAG(ifc->conf, ZEBRA_IFC_QUEUED);
- /* This information will be propagated to the zclients when the
- * kernel notification is received. */
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_address,
- ipv6_address_cmd,
- "ipv6 address X:X::X:X/M",
- "Interface IPv6 config commands\n"
- "Set the IP address of an interface\n"
- "IPv6 address (e.g. 3ffe:506::1/48)\n")
-{
- int idx_ipv6_prefixlen = 2;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ipv6_address_install(vty, ifp, argv[idx_ipv6_prefixlen]->arg,
- NULL, NULL);
-}
-
-DEFUN (no_ipv6_address,
- no_ipv6_address_cmd,
- "no ipv6 address X:X::X:X/M",
- NO_STR
- "Interface IPv6 config commands\n"
- "Set the IP address of an interface\n"
- "IPv6 address (e.g. 3ffe:506::1/48)\n")
-{
- int idx_ipv6_prefixlen = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- return ipv6_address_uninstall(vty, ifp, argv[idx_ipv6_prefixlen]->arg,
- NULL, NULL);
-}
-
-static int link_params_config_write(struct vty *vty, struct interface *ifp)
-{
- const struct lyd_node *dnode;
- char xpath[XPATH_MAXLEN];
- int i;
-
- if ((ifp == NULL) || !HAS_LINK_PARAMS(ifp))
- return -1;
-
- struct if_link_params *iflp = ifp->link_params;
-
- vty_out(vty, " link-params\n");
- vty_out(vty, " enable\n");
- if (IS_PARAM_SET(iflp, LP_TE_METRIC) && iflp->te_metric != ifp->metric)
- vty_out(vty, " metric %u\n", iflp->te_metric);
- if (IS_PARAM_SET(iflp, LP_MAX_BW) && iflp->max_bw != iflp->default_bw)
- vty_out(vty, " max-bw %g\n", iflp->max_bw);
- if (IS_PARAM_SET(iflp, LP_MAX_RSV_BW)
- && iflp->max_rsv_bw != iflp->default_bw)
- vty_out(vty, " max-rsv-bw %g\n", iflp->max_rsv_bw);
- if (IS_PARAM_SET(iflp, LP_UNRSV_BW)) {
- for (i = 0; i < 8; i++)
- if (iflp->unrsv_bw[i] != iflp->default_bw)
- vty_out(vty, " unrsv-bw %d %g\n", i,
- iflp->unrsv_bw[i]);
- }
-
- snprintf(
- xpath, sizeof(xpath),
- "/frr-interface:lib/interface[name='%s']/frr-zebra:zebra/link-params",
- ifp->name);
- dnode = yang_dnode_get(running_config->dnode, xpath);
- if (dnode)
- nb_cli_show_dnode_cmds(vty, dnode, false);
-
- if (IS_PARAM_SET(iflp, LP_DELAY)) {
- vty_out(vty, " delay %u", iflp->av_delay);
- if (IS_PARAM_SET(iflp, LP_MM_DELAY)) {
- vty_out(vty, " min %u", iflp->min_delay);
- vty_out(vty, " max %u", iflp->max_delay);
- }
- vty_out(vty, "\n");
- }
- if (IS_PARAM_SET(iflp, LP_DELAY_VAR))
- vty_out(vty, " delay-variation %u\n", iflp->delay_var);
- if (IS_PARAM_SET(iflp, LP_PKT_LOSS))
- vty_out(vty, " packet-loss %g\n", iflp->pkt_loss);
- if (IS_PARAM_SET(iflp, LP_AVA_BW))
- vty_out(vty, " ava-bw %g\n", iflp->ava_bw);
- if (IS_PARAM_SET(iflp, LP_RES_BW))
- vty_out(vty, " res-bw %g\n", iflp->res_bw);
- if (IS_PARAM_SET(iflp, LP_USE_BW))
- vty_out(vty, " use-bw %g\n", iflp->use_bw);
- if (IS_PARAM_SET(iflp, LP_RMT_AS))
- vty_out(vty, " neighbor %pI4 as %u\n", &iflp->rmt_ip,
- iflp->rmt_as);
-
- vty_out(vty, " exit-link-params\n");
- return 0;
-}
-
-static int if_config_write(struct vty *vty)
-{
- struct vrf *vrf;
- struct interface *ifp;
-
- zebra_ptm_write(vty);
-
- RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name)
- FOR_ALL_INTERFACES (vrf, ifp) {
- struct zebra_if *if_data;
- struct connected *ifc;
- struct prefix *p;
-
- if_data = ifp->info;
-
- if_vty_config_start(vty, ifp);
-
- if (if_data) {
- if (if_data->shutdown == IF_ZEBRA_DATA_ON)
- vty_out(vty, " shutdown\n");
-
- zebra_ptm_if_write(vty, if_data);
- }
-
- if (ifp->desc)
- vty_out(vty, " description %s\n", ifp->desc);
-
- /* Assign bandwidth here to avoid unnecessary interface
- flap
- while processing config script */
- if (ifp->bandwidth != 0)
- vty_out(vty, " bandwidth %u\n", ifp->bandwidth);
-
- if (!CHECK_FLAG(ifp->status,
- ZEBRA_INTERFACE_LINKDETECTION))
- vty_out(vty, " no link-detect\n");
-
- frr_each (if_connected, ifp->connected, ifc) {
- if (CHECK_FLAG(ifc->conf,
- ZEBRA_IFC_CONFIGURED)) {
- char buf[INET6_ADDRSTRLEN];
- p = ifc->address;
- vty_out(vty, " ip%s address %s",
- p->family == AF_INET ? ""
- : "v6",
- inet_ntop(p->family,
- &p->u.prefix, buf,
- sizeof(buf)));
- if (CONNECTED_PEER(ifc)) {
- p = ifc->destination;
- vty_out(vty, " peer %s",
- inet_ntop(p->family,
- &p->u.prefix,
- buf,
- sizeof(buf)));
- }
- vty_out(vty, "/%d", p->prefixlen);
-
- if (ifc->label)
- vty_out(vty, " label %s",
- ifc->label);
-
- vty_out(vty, "\n");
- }
- }
-
- if (if_data) {
- if (if_data->multicast != IF_ZEBRA_DATA_UNSPEC)
- vty_out(vty, " %smulticast\n",
- if_data->multicast ==
- IF_ZEBRA_DATA_ON
- ? ""
- : "no ");
-
- if (if_data->mpls_config == IF_ZEBRA_DATA_ON)
- vty_out(vty, " mpls enable\n");
- else if (if_data->mpls_config ==
- IF_ZEBRA_DATA_OFF)
- vty_out(vty, " mpls disable\n");
- }
-
- hook_call(zebra_if_config_wr, vty, ifp);
- zebra_evpn_mh_if_write(vty, ifp);
- link_params_config_write(vty, ifp);
-
- if_vty_config_end(vty);
- }
- return 0;
}
/* Allocate and initialize interface vector. */
@@ -5561,10 +3966,6 @@ void zebra_if_init(void)
hook_register_prio(if_add, 0, if_zebra_new_hook);
hook_register_prio(if_del, 0, if_zebra_delete_hook);
- /* Install configuration write function. */
- if_cmd_init(if_config_write);
- install_node(&link_params_node);
-
install_element(VIEW_NODE, &show_interface_cmd);
install_element(VIEW_NODE, &show_interface_vrf_all_cmd);
install_element(VIEW_NODE, &show_interface_name_vrf_cmd);
@@ -5572,55 +3973,4 @@ void zebra_if_init(void)
install_element(ENABLE_NODE, &show_interface_desc_cmd);
install_element(ENABLE_NODE, &show_interface_desc_vrf_all_cmd);
- install_element(INTERFACE_NODE, &multicast_cmd);
- install_element(INTERFACE_NODE, &no_multicast_cmd);
- install_element(INTERFACE_NODE, &mpls_cmd);
- install_element(INTERFACE_NODE, &linkdetect_cmd);
- install_element(INTERFACE_NODE, &no_linkdetect_cmd);
- install_element(INTERFACE_NODE, &shutdown_if_cmd);
- install_element(INTERFACE_NODE, &no_shutdown_if_cmd);
- install_element(INTERFACE_NODE, &bandwidth_if_cmd);
- install_element(INTERFACE_NODE, &no_bandwidth_if_cmd);
- install_element(INTERFACE_NODE, &ip_address_cmd);
- install_element(INTERFACE_NODE, &no_ip_address_cmd);
- install_element(INTERFACE_NODE, &ip_address_peer_cmd);
- install_element(INTERFACE_NODE, &no_ip_address_peer_cmd);
- install_element(INTERFACE_NODE, &ipv6_address_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_address_cmd);
-#ifdef HAVE_NETLINK
- install_element(INTERFACE_NODE, &ip_address_label_cmd);
- install_element(INTERFACE_NODE, &no_ip_address_label_cmd);
-#endif /* HAVE_NETLINK */
- install_element(INTERFACE_NODE, &link_params_cmd);
- install_default(LINK_PARAMS_NODE);
- install_element(LINK_PARAMS_NODE, &link_params_enable_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_enable_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_metric_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_metric_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_maxbw_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_max_rsv_bw_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_unrsv_bw_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_admin_grp_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_admin_grp_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_inter_as_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_inter_as_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_delay_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_delay_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_delay_var_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_delay_var_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_pkt_loss_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_pkt_loss_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_ava_bw_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_ava_bw_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_res_bw_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_res_bw_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_use_bw_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_use_bw_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_affinity_cmd);
- install_element(LINK_PARAMS_NODE, &link_params_affinity_mode_cmd);
- install_element(LINK_PARAMS_NODE, &no_link_params_affinity_mode_cmd);
- install_element(LINK_PARAMS_NODE, &exit_link_params_cmd);
-
- /* setup EVPN MH elements */
- zebra_evpn_interface_init();
}
diff --git a/zebra/interface.h b/zebra/interface.h
index a96f2ec718..fc6850e80e 100644
--- a/zebra/interface.h
+++ b/zebra/interface.h
@@ -218,8 +218,6 @@ struct zebra_if {
DECLARE_HOOK(zebra_if_extra_info, (struct vty * vty, struct interface *ifp),
(vty, ifp));
-DECLARE_HOOK(zebra_if_config_wr, (struct vty * vty, struct interface *ifp),
- (vty, ifp));
#define IS_ZEBRA_IF_VRF(ifp) \
(((struct zebra_if *)(ifp->info))->zif_type == ZEBRA_IF_VRF)
@@ -307,11 +305,14 @@ extern void cli_show_affinity(struct vty *vty, const struct lyd_node *dnode,
*/
extern int zebra_if_set_protodown(struct interface *ifp, bool down,
enum protodown_reasons new_reason);
-extern int if_ip_address_install(struct interface *ifp, struct prefix *prefix,
- const char *label, struct prefix *pp);
-extern int if_ipv6_address_install(struct interface *ifp, struct prefix *prefix,
- const char *label);
-extern int if_ip_address_uinstall(struct interface *ifp, struct prefix *prefix);
+extern void if_ip_address_install(struct interface *ifp, struct prefix *prefix,
+ const char *label, struct prefix *pp);
+extern void if_ip_address_uninstall(struct interface *ifp,
+ struct prefix *prefix, struct prefix *pp);
+extern void if_ipv6_address_install(struct interface *ifp,
+ struct prefix *prefix);
+extern void if_ipv6_address_uninstall(struct interface *ifp,
+ struct prefix *prefix);
extern int if_shutdown(struct interface *ifp);
extern int if_no_shutdown(struct interface *ifp);
extern void if_arp(struct interface *ifp, bool enable);
@@ -320,6 +321,12 @@ extern int if_multicast_unset(struct interface *ifp);
extern int if_linkdetect(struct interface *ifp, bool detect);
extern void if_addr_wakeup(struct interface *ifp);
+void link_param_cmd_set_uint32(struct interface *ifp, uint32_t *field,
+ uint32_t type, uint32_t value);
+void link_param_cmd_set_float(struct interface *ifp, float *field,
+ uint32_t type, float value);
+void link_param_cmd_unset(struct interface *ifp, uint32_t type);
+
/* Nexthop group connected functions */
extern void if_nhg_dependents_add(struct interface *ifp,
struct nhg_hash_entry *nhe);
diff --git a/zebra/irdp_interface.c b/zebra/irdp_interface.c
index 591236d680..70f3f57ae0 100644
--- a/zebra/irdp_interface.c
+++ b/zebra/irdp_interface.c
@@ -694,7 +694,6 @@ DEFUN (ip_irdp_debug_disable,
void irdp_if_init(void)
{
- hook_register(zebra_if_config_wr, irdp_config_write);
hook_register(if_del, irdp_if_delete);
install_element(INTERFACE_NODE, &ip_irdp_broadcast_cmd);
diff --git a/zebra/main.c b/zebra/main.c
index 47aef46cac..606ecc7279 100644
--- a/zebra/main.c
+++ b/zebra/main.c
@@ -442,7 +442,7 @@ int main(int argc, char **argv)
zebra_vty_init();
mgmt_be_client = mgmt_be_client_create("zebra", NULL, 0,
zrouter.master);
- access_list_init();
+ access_list_init_new(true);
prefix_list_init();
rtadv_init();
diff --git a/zebra/router-id.c b/zebra/router-id.c
index ef87d924fe..2f251a79e5 100644
--- a/zebra/router-id.c
+++ b/zebra/router-id.c
@@ -109,7 +109,7 @@ int router_id_get(afi_t afi, struct prefix *p, struct zebra_vrf *zvrf)
assert(!"Reached end of function we should never hit");
}
-static int router_id_set(afi_t afi, struct prefix *p, struct zebra_vrf *zvrf)
+int router_id_set(afi_t afi, struct prefix *p, struct zebra_vrf *zvrf)
{
struct prefix after, before;
struct listnode *node;
@@ -241,256 +241,6 @@ void router_id_del_address(struct connected *ifc)
zsend_router_id_update(client, afi, &after, zvrf_id(zvrf));
}
-void router_id_write(struct vty *vty, struct zebra_vrf *zvrf)
-{
- char space[2];
-
- memset(space, 0, sizeof(space));
-
- if (zvrf_id(zvrf) != VRF_DEFAULT)
- snprintf(space, sizeof(space), "%s", " ");
-
- if (zvrf->rid_user_assigned.u.prefix4.s_addr != INADDR_ANY) {
- vty_out(vty, "%sip router-id %pI4\n", space,
- &zvrf->rid_user_assigned.u.prefix4);
- }
- if (!router_id_v6_is_any(&zvrf->rid6_user_assigned)) {
- vty_out(vty, "%sipv6 router-id %pI6\n", space,
- &zvrf->rid_user_assigned.u.prefix6);
- }
-}
-
-DEFUN (ip_router_id,
- ip_router_id_cmd,
- "ip router-id A.B.C.D vrf NAME",
- IP_STR
- "Manually set the router-id\n"
- "IP address to use for router-id\n"
- VRF_CMD_HELP_STR)
-{
- int idx = 0;
- struct prefix rid;
- vrf_id_t vrf_id;
- struct zebra_vrf *zvrf;
-
- argv_find(argv, argc, "A.B.C.D", &idx);
-
- if (!inet_pton(AF_INET, argv[idx]->arg, &rid.u.prefix4))
- return CMD_WARNING_CONFIG_FAILED;
-
- rid.prefixlen = IPV4_MAX_BITLEN;
- rid.family = AF_INET;
-
- argv_find(argv, argc, "NAME", &idx);
- VRF_GET_ID(vrf_id, argv[idx]->arg, false);
-
- zvrf = zebra_vrf_lookup_by_id(vrf_id);
- router_id_set(AFI_IP, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
-ALIAS (ip_router_id,
- router_id_cmd,
- "router-id A.B.C.D vrf NAME",
- "Manually set the router-id\n"
- "IP address to use for router-id\n"
- VRF_CMD_HELP_STR);
-
-DEFUN (ipv6_router_id,
- ipv6_router_id_cmd,
- "ipv6 router-id X:X::X:X vrf NAME",
- IPV6_STR
- "Manually set the router-id\n"
- "IPv6 address to use for router-id\n"
- VRF_CMD_HELP_STR)
-{
- int idx = 0;
- struct prefix rid;
- vrf_id_t vrf_id;
- struct zebra_vrf *zvrf;
-
- argv_find(argv, argc, "X:X::X:X", &idx);
-
- if (!inet_pton(AF_INET6, argv[idx]->arg, &rid.u.prefix6))
- return CMD_WARNING_CONFIG_FAILED;
-
- rid.prefixlen = IPV6_MAX_BITLEN;
- rid.family = AF_INET6;
-
- argv_find(argv, argc, "NAME", &idx);
- VRF_GET_ID(vrf_id, argv[idx]->arg, false);
-
- zvrf = zebra_vrf_lookup_by_id(vrf_id);
- router_id_set(AFI_IP6, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
-
-DEFUN (ip_router_id_in_vrf,
- ip_router_id_in_vrf_cmd,
- "ip router-id A.B.C.D",
- IP_STR
- "Manually set the router-id\n"
- "IP address to use for router-id\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
- int idx = 0;
- struct prefix rid;
-
- argv_find(argv, argc, "A.B.C.D", &idx);
-
- if (!inet_pton(AF_INET, argv[idx]->arg, &rid.u.prefix4))
- return CMD_WARNING_CONFIG_FAILED;
-
- rid.prefixlen = IPV4_MAX_BITLEN;
- rid.family = AF_INET;
-
- router_id_set(AFI_IP, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
-ALIAS (ip_router_id_in_vrf,
- router_id_in_vrf_cmd,
- "router-id A.B.C.D",
- "Manually set the router-id\n"
- "IP address to use for router-id\n");
-
-DEFUN (ipv6_router_id_in_vrf,
- ipv6_router_id_in_vrf_cmd,
- "ipv6 router-id X:X::X:X",
- IP6_STR
- "Manually set the IPv6 router-id\n"
- "IPV6 address to use for router-id\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
- int idx = 0;
- struct prefix rid;
-
- argv_find(argv, argc, "X:X::X:X", &idx);
-
- if (!inet_pton(AF_INET6, argv[idx]->arg, &rid.u.prefix6))
- return CMD_WARNING_CONFIG_FAILED;
-
- rid.prefixlen = IPV6_MAX_BITLEN;
- rid.family = AF_INET6;
-
- router_id_set(AFI_IP6, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ip_router_id,
- no_ip_router_id_cmd,
- "no ip router-id [A.B.C.D vrf NAME]",
- NO_STR
- IP_STR
- "Remove the manually configured router-id\n"
- "IP address to use for router-id\n"
- VRF_CMD_HELP_STR)
-{
- int idx = 0;
- struct prefix rid;
- vrf_id_t vrf_id = VRF_DEFAULT;
- struct zebra_vrf *zvrf;
-
- rid.u.prefix4.s_addr = 0;
- rid.prefixlen = 0;
- rid.family = AF_INET;
-
- if (argv_find(argv, argc, "NAME", &idx))
- VRF_GET_ID(vrf_id, argv[idx]->arg, false);
-
- zvrf = zebra_vrf_lookup_by_id(vrf_id);
- router_id_set(AFI_IP, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
-ALIAS (no_ip_router_id,
- no_router_id_cmd,
- "no router-id [A.B.C.D vrf NAME]",
- NO_STR
- "Remove the manually configured router-id\n"
- "IP address to use for router-id\n"
- VRF_CMD_HELP_STR);
-
-DEFUN (no_ipv6_router_id,
- no_ipv6_router_id_cmd,
- "no ipv6 router-id [X:X::X:X vrf NAME]",
- NO_STR
- IPV6_STR
- "Remove the manually configured IPv6 router-id\n"
- "IPv6 address to use for router-id\n"
- VRF_CMD_HELP_STR)
-{
- int idx = 0;
- struct prefix rid;
- vrf_id_t vrf_id = VRF_DEFAULT;
- struct zebra_vrf *zvrf;
-
- memset(&rid, 0, sizeof(rid));
- rid.family = AF_INET;
-
- if (argv_find(argv, argc, "NAME", &idx))
- VRF_GET_ID(vrf_id, argv[idx]->arg, false);
-
- zvrf = zebra_vrf_lookup_by_id(vrf_id);
- router_id_set(AFI_IP6, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ip_router_id_in_vrf,
- no_ip_router_id_in_vrf_cmd,
- "no ip router-id [A.B.C.D]",
- NO_STR
- IP_STR
- "Remove the manually configured router-id\n"
- "IP address to use for router-id\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- struct prefix rid;
-
- rid.u.prefix4.s_addr = 0;
- rid.prefixlen = 0;
- rid.family = AF_INET;
-
- router_id_set(AFI_IP, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
-ALIAS (no_ip_router_id_in_vrf,
- no_router_id_in_vrf_cmd,
- "no router-id [A.B.C.D]",
- NO_STR
- "Remove the manually configured router-id\n"
- "IP address to use for router-id\n");
-
-DEFUN (no_ipv6_router_id_in_vrf,
- no_ipv6_router_id_in_vrf_cmd,
- "no ipv6 router-id [X:X::X:X]",
- NO_STR
- IP6_STR
- "Remove the manually configured IPv6 router-id\n"
- "IPv6 address to use for router-id\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- struct prefix rid;
-
- memset(&rid, 0, sizeof(rid));
- rid.family = AF_INET;
-
- router_id_set(AFI_IP6, &rid, zvrf);
-
- return CMD_SUCCESS;
-}
-
DEFUN (show_ip_router_id,
show_ip_router_id_cmd,
"show [ip|ipv6] router-id [vrf NAME]",
@@ -557,24 +307,6 @@ static int router_id_v6_cmp(void *a, void *b)
void router_id_cmd_init(void)
{
- install_element(CONFIG_NODE, &ip_router_id_cmd);
- install_element(CONFIG_NODE, &router_id_cmd);
- install_element(CONFIG_NODE, &ipv6_router_id_cmd);
- install_element(CONFIG_NODE, &no_ip_router_id_cmd);
- install_element(CONFIG_NODE, &no_router_id_cmd);
- install_element(CONFIG_NODE, &ip_router_id_in_vrf_cmd);
- install_element(VRF_NODE, &ip_router_id_in_vrf_cmd);
- install_element(CONFIG_NODE, &router_id_in_vrf_cmd);
- install_element(VRF_NODE, &router_id_in_vrf_cmd);
- install_element(CONFIG_NODE, &ipv6_router_id_in_vrf_cmd);
- install_element(VRF_NODE, &ipv6_router_id_in_vrf_cmd);
- install_element(CONFIG_NODE, &no_ipv6_router_id_cmd);
- install_element(CONFIG_NODE, &no_ip_router_id_in_vrf_cmd);
- install_element(VRF_NODE, &no_ip_router_id_in_vrf_cmd);
- install_element(CONFIG_NODE, &no_router_id_in_vrf_cmd);
- install_element(VRF_NODE, &no_router_id_in_vrf_cmd);
- install_element(CONFIG_NODE, &no_ipv6_router_id_in_vrf_cmd);
- install_element(VRF_NODE, &no_ipv6_router_id_in_vrf_cmd);
install_element(VIEW_NODE, &show_ip_router_id_cmd);
}
diff --git a/zebra/router-id.h b/zebra/router-id.h
index 45860d8b7b..09ad4ec65e 100644
--- a/zebra/router-id.h
+++ b/zebra/router-id.h
@@ -25,8 +25,8 @@ extern void router_id_add_address(struct connected *c);
extern void router_id_del_address(struct connected *c);
extern void router_id_init(struct zebra_vrf *zvrf);
extern void router_id_cmd_init(void);
-extern void router_id_write(struct vty *vty, struct zebra_vrf *zvrf);
extern int router_id_get(afi_t afi, struct prefix *p, struct zebra_vrf *zvrf);
+extern int router_id_set(afi_t afi, struct prefix *p, struct zebra_vrf *zvrf);
#ifdef __cplusplus
}
diff --git a/zebra/rtadv.c b/zebra/rtadv.c
index 00f018d192..6aca643bd8 100644
--- a/zebra/rtadv.c
+++ b/zebra/rtadv.c
@@ -1134,7 +1134,8 @@ static void rtadv_prefix_set_defaults(struct rtadv_prefix *rp)
rp->AdvValidLifetime = RTADV_VALID_LIFETIME;
}
-static void rtadv_prefix_set(struct zebra_if *zif, struct rtadv_prefix *rp)
+static struct rtadv_prefix *rtadv_prefix_set(struct zebra_if *zif,
+ struct rtadv_prefix *rp)
{
struct rtadv_prefix *rprefix;
@@ -1167,13 +1168,16 @@ static void rtadv_prefix_set(struct zebra_if *zif, struct rtadv_prefix *rp)
rtadv_prefix_set_defaults(rprefix);
}
}
+
+ return rprefix;
}
-static int rtadv_prefix_reset(struct zebra_if *zif, struct rtadv_prefix *rp)
+static void rtadv_prefix_reset(struct zebra_if *zif, struct rtadv_prefix *rp,
+ struct rtadv_prefix *rprefix)
{
- struct rtadv_prefix *rprefix;
+ if (!rprefix)
+ rprefix = rtadv_prefixes_find(zif->rtadv.prefixes, rp);
- rprefix = rtadv_prefixes_find(zif->rtadv.prefixes, rp);
if (rprefix != NULL) {
/*
@@ -1187,20 +1191,35 @@ static int rtadv_prefix_reset(struct zebra_if *zif, struct rtadv_prefix *rp)
if (rprefix->AdvPrefixCreate == PREFIX_SRC_BOTH) {
rprefix->AdvPrefixCreate = PREFIX_SRC_AUTO;
rtadv_prefix_set_defaults(rprefix);
- return 1;
+ return;
}
} else if (rp->AdvPrefixCreate == PREFIX_SRC_AUTO) {
if (rprefix->AdvPrefixCreate == PREFIX_SRC_BOTH) {
rprefix->AdvPrefixCreate = PREFIX_SRC_MANUAL;
- return 1;
+ return;
}
}
rtadv_prefixes_del(zif->rtadv.prefixes, rprefix);
rtadv_prefix_free(rprefix);
- return 1;
- } else
- return 0;
+ }
+}
+
+struct rtadv_prefix *rtadv_add_prefix_manual(struct zebra_if *zif,
+ struct rtadv_prefix *rp)
+{
+ rp->AdvPrefixCreate = PREFIX_SRC_MANUAL;
+ return rtadv_prefix_set(zif, rp);
+}
+
+void rtadv_delete_prefix_manual(struct zebra_if *zif,
+ struct rtadv_prefix *rprefix)
+{
+ struct rtadv_prefix rp;
+
+ rp.AdvPrefixCreate = PREFIX_SRC_MANUAL;
+
+ rtadv_prefix_reset(zif, &rp, rprefix);
}
/* Add IPv6 prefixes learned from the kernel to the RA prefix list */
@@ -1222,7 +1241,7 @@ void rtadv_delete_prefix(struct zebra_if *zif, const struct prefix *p)
rp.prefix = *((struct prefix_ipv6 *)p);
apply_mask_ipv6(&rp.prefix);
rp.AdvPrefixCreate = PREFIX_SRC_AUTO;
- rtadv_prefix_reset(zif, &rp);
+ rtadv_prefix_reset(zif, &rp, NULL);
}
static void rtadv_start_interface_events(struct zebra_vrf *zvrf,
@@ -1248,8 +1267,8 @@ static void rtadv_start_interface_events(struct zebra_vrf *zvrf,
rtadv_event(zvrf, RTADV_START, 0);
}
-static void ipv6_nd_suppress_ra_set(struct interface *ifp,
- enum ipv6_nd_suppress_ra_status status)
+void ipv6_nd_suppress_ra_set(struct interface *ifp,
+ enum ipv6_nd_suppress_ra_status status)
{
struct zebra_if *zif;
struct zebra_vrf *zvrf;
@@ -1297,6 +1316,36 @@ static void ipv6_nd_suppress_ra_set(struct interface *ifp,
}
}
+void ipv6_nd_interval_set(struct interface *ifp, uint32_t interval)
+{
+ struct zebra_if *zif = ifp->info;
+ struct zebra_vrf *zvrf = rtadv_interface_get_zvrf(ifp);
+ struct adv_if *adv_if;
+
+ if (zif->rtadv.MaxRtrAdvInterval % 1000) {
+ adv_if = adv_msec_if_del(zvrf, ifp->name);
+ if (adv_if != NULL)
+ adv_if_free(adv_if);
+ }
+
+ if (interval % 1000)
+ (void)adv_msec_if_add(zvrf, ifp->name);
+
+ zif->rtadv.MaxRtrAdvInterval = interval;
+ zif->rtadv.MinRtrAdvInterval = 0.33 * interval;
+
+ if (interval != RTADV_MAX_RTR_ADV_INTERVAL) {
+ SET_FLAG(zif->rtadv.ra_configured, VTY_RA_INTERVAL_CONFIGURED);
+ zif->rtadv.AdvIntervalTimer = 0;
+ } else {
+ if (CHECK_FLAG(zif->rtadv.ra_configured, BGP_RA_CONFIGURED))
+ zif->rtadv.MaxRtrAdvInterval = 10000;
+
+ UNSET_FLAG(zif->rtadv.ra_configured, VTY_RA_INTERVAL_CONFIGURED);
+ zif->rtadv.AdvIntervalTimer = zif->rtadv.MaxRtrAdvInterval;
+ }
+}
+
/*
* Handle client (BGP) message to enable or disable IPv6 RA on an interface.
* Note that while the client could request RA on an interface on which the
@@ -1414,7 +1463,7 @@ void rtadv_stop_ra_all(void)
frr_each_safe (rtadv_prefixes, zif->rtadv.prefixes,
rprefix)
- rtadv_prefix_reset(zif, rprefix);
+ rtadv_prefix_reset(zif, rprefix, rprefix);
rtadv_stop_ra(ifp);
}
@@ -1499,777 +1548,6 @@ DEFPY(show_ipv6_nd_ra_if, show_ipv6_nd_ra_if_cmd,
return CMD_SUCCESS;
}
-DEFUN (ipv6_nd_ra_fast_retrans,
- ipv6_nd_ra_fast_retrans_cmd,
- "ipv6 nd ra-fast-retrans",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Fast retransmit of RA packets\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot configure IPv6 Router Advertisements on this interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- zif->rtadv.UseFastRexmit = true;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_ra_fast_retrans,
- no_ipv6_nd_ra_fast_retrans_cmd,
- "no ipv6 nd ra-fast-retrans",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Fast retransmit of RA packets\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot configure IPv6 Router Advertisements on this interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- zif->rtadv.UseFastRexmit = false;
-
- return CMD_SUCCESS;
-}
-
-DEFPY (ipv6_nd_ra_hop_limit,
- ipv6_nd_ra_hop_limit_cmd,
- "ipv6 nd ra-hop-limit (0-255)$hopcount",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertisement Hop Limit\n"
- "Advertisement Hop Limit in hops (default:64)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot configure IPv6 Router Advertisements on this interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- zif->rtadv.AdvCurHopLimit = hopcount;
-
- return CMD_SUCCESS;
-}
-
-DEFPY (no_ipv6_nd_ra_hop_limit,
- no_ipv6_nd_ra_hop_limit_cmd,
- "no ipv6 nd ra-hop-limit [(0-255)]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertisement Hop Limit\n"
- "Advertisement Hop Limit in hops\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot configure IPv6 Router Advertisements on this interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- zif->rtadv.AdvCurHopLimit = RTADV_DEFAULT_HOPLIMIT;
-
- return CMD_SUCCESS;
-}
-
-DEFPY (ipv6_nd_ra_retrans_interval,
- ipv6_nd_ra_retrans_interval_cmd,
- "ipv6 nd ra-retrans-interval (0-4294967295)$interval",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertisement Retransmit Interval\n"
- "Advertisement Retransmit Interval in msec\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot configure IPv6 Router Advertisements on loopback interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- zif->rtadv.AdvRetransTimer = interval;
-
- return CMD_SUCCESS;
-}
-
-DEFPY (no_ipv6_nd_ra_retrans_interval,
- no_ipv6_nd_ra_retrans_interval_cmd,
- "no ipv6 nd ra-retrans-interval [(0-4294967295)]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertisement Retransmit Interval\n"
- "Advertisement Retransmit Interval in msec\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot remove IPv6 Router Advertisements on loopback interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- zif->rtadv.AdvRetransTimer = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_suppress_ra,
- ipv6_nd_suppress_ra_cmd,
- "ipv6 nd suppress-ra",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Suppress Router Advertisement\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot configure IPv6 Router Advertisements on this interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (!CHECK_FLAG(zif->rtadv.ra_configured, BGP_RA_CONFIGURED))
- ipv6_nd_suppress_ra_set(ifp, RA_SUPPRESS);
-
- UNSET_FLAG(zif->rtadv.ra_configured, VTY_RA_CONFIGURED);
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_suppress_ra,
- no_ipv6_nd_suppress_ra_cmd,
- "no ipv6 nd suppress-ra",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Suppress Router Advertisement\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- if (if_is_loopback(ifp)) {
- vty_out(vty,
- "Cannot configure IPv6 Router Advertisements on this interface\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ipv6_nd_suppress_ra_set(ifp, RA_ENABLE);
- SET_FLAG(zif->rtadv.ra_configured, VTY_RA_CONFIGURED);
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_ra_interval_msec,
- ipv6_nd_ra_interval_msec_cmd,
- "ipv6 nd ra-interval msec (70-1800000)",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Router Advertisement interval\n"
- "Router Advertisement interval in milliseconds\n"
- "Router Advertisement interval in milliseconds\n")
-{
- int idx_number = 4;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- unsigned interval;
- struct zebra_if *zif = ifp->info;
- struct zebra_vrf *zvrf;
- struct adv_if *adv_if;
-
- zvrf = rtadv_interface_get_zvrf(ifp);
-
- interval = strtoul(argv[idx_number]->arg, NULL, 10);
- if ((zif->rtadv.AdvDefaultLifetime != -1
- && interval > (unsigned)zif->rtadv.AdvDefaultLifetime * 1000)) {
- vty_out(vty,
- "This ra-interval would conflict with configured ra-lifetime!\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (zif->rtadv.MaxRtrAdvInterval % 1000) {
- adv_if = adv_msec_if_del(zvrf, ifp->name);
- if (adv_if != NULL)
- adv_if_free(adv_if);
- }
-
- if (interval % 1000)
- (void)adv_msec_if_add(zvrf, ifp->name);
-
- SET_FLAG(zif->rtadv.ra_configured, VTY_RA_INTERVAL_CONFIGURED);
- zif->rtadv.MaxRtrAdvInterval = interval;
- zif->rtadv.MinRtrAdvInterval = 0.33 * interval;
- zif->rtadv.AdvIntervalTimer = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_ra_interval,
- ipv6_nd_ra_interval_cmd,
- "ipv6 nd ra-interval (1-1800)",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Router Advertisement interval\n"
- "Router Advertisement interval in seconds\n")
-{
- int idx_number = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- unsigned interval;
- struct zebra_if *zif = ifp->info;
- struct zebra_vrf *zvrf;
- struct adv_if *adv_if;
-
- zvrf = rtadv_interface_get_zvrf(ifp);
-
- interval = strtoul(argv[idx_number]->arg, NULL, 10);
- if ((zif->rtadv.AdvDefaultLifetime != -1
- && interval > (unsigned)zif->rtadv.AdvDefaultLifetime)) {
- vty_out(vty,
- "This ra-interval would conflict with configured ra-lifetime!\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- if (zif->rtadv.MaxRtrAdvInterval % 1000) {
- adv_if = adv_msec_if_del(zvrf, ifp->name);
- if (adv_if != NULL)
- adv_if_free(adv_if);
- }
-
- /* convert to milliseconds */
- interval = interval * 1000;
-
- SET_FLAG(zif->rtadv.ra_configured, VTY_RA_INTERVAL_CONFIGURED);
- zif->rtadv.MaxRtrAdvInterval = interval;
- zif->rtadv.MinRtrAdvInterval = 0.33 * interval;
- zif->rtadv.AdvIntervalTimer = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_ra_interval,
- no_ipv6_nd_ra_interval_cmd,
- "no ipv6 nd ra-interval [<(1-1800)|msec (1-1800000)>]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Router Advertisement interval\n"
- "Router Advertisement interval in seconds\n"
- "Specify millisecond router advertisement interval\n"
- "Router Advertisement interval in milliseconds\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- struct zebra_vrf *zvrf = NULL;
- struct adv_if *adv_if;
-
- zvrf = rtadv_interface_get_zvrf(ifp);
-
- if (zif->rtadv.MaxRtrAdvInterval % 1000) {
- adv_if = adv_msec_if_del(zvrf, ifp->name);
- if (adv_if != NULL)
- adv_if_free(adv_if);
- }
-
- UNSET_FLAG(zif->rtadv.ra_configured, VTY_RA_INTERVAL_CONFIGURED);
-
- if (CHECK_FLAG(zif->rtadv.ra_configured, BGP_RA_CONFIGURED))
- zif->rtadv.MaxRtrAdvInterval = 10000;
- else
- zif->rtadv.MaxRtrAdvInterval = RTADV_MAX_RTR_ADV_INTERVAL;
-
- zif->rtadv.AdvIntervalTimer = zif->rtadv.MaxRtrAdvInterval;
- zif->rtadv.MinRtrAdvInterval = RTADV_MIN_RTR_ADV_INTERVAL;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_ra_lifetime,
- ipv6_nd_ra_lifetime_cmd,
- "ipv6 nd ra-lifetime (0-9000)",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Router lifetime\n"
- "Router lifetime in seconds (0 stands for a non-default gw)\n")
-{
- int idx_number = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- int lifetime;
-
- lifetime = strtoul(argv[idx_number]->arg, NULL, 10);
-
- /* The value to be placed in the Router Lifetime field
- * of Router Advertisements sent from the interface,
- * in seconds. MUST be either zero or between
- * MaxRtrAdvInterval and 9000 seconds. -- RFC4861, 6.2.1 */
- if ((lifetime != 0 && lifetime * 1000 < zif->rtadv.MaxRtrAdvInterval)) {
- vty_out(vty,
- "This ra-lifetime would conflict with configured ra-interval\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- zif->rtadv.AdvDefaultLifetime = lifetime;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_ra_lifetime,
- no_ipv6_nd_ra_lifetime_cmd,
- "no ipv6 nd ra-lifetime [(0-9000)]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Router lifetime\n"
- "Router lifetime in seconds (0 stands for a non-default gw)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvDefaultLifetime = -1;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_reachable_time,
- ipv6_nd_reachable_time_cmd,
- "ipv6 nd reachable-time (1-3600000)",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Reachable time\n"
- "Reachable time in milliseconds\n")
-{
- int idx_number = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- zif->rtadv.AdvReachableTime = strtoul(argv[idx_number]->arg, NULL, 10);
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_reachable_time,
- no_ipv6_nd_reachable_time_cmd,
- "no ipv6 nd reachable-time [(1-3600000)]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Reachable time\n"
- "Reachable time in milliseconds\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvReachableTime = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_homeagent_preference,
- ipv6_nd_homeagent_preference_cmd,
- "ipv6 nd home-agent-preference (0-65535)",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Home Agent preference\n"
- "preference value (default is 0, least preferred)\n")
-{
- int idx_number = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- zif->rtadv.HomeAgentPreference =
- strtoul(argv[idx_number]->arg, NULL, 10);
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_homeagent_preference,
- no_ipv6_nd_homeagent_preference_cmd,
- "no ipv6 nd home-agent-preference [(0-65535)]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Home Agent preference\n"
- "preference value (default is 0, least preferred)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.HomeAgentPreference = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_homeagent_lifetime,
- ipv6_nd_homeagent_lifetime_cmd,
- "ipv6 nd home-agent-lifetime (0-65520)",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Home Agent lifetime\n"
- "Home Agent lifetime in seconds (0 to track ra-lifetime)\n")
-{
- int idx_number = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- zif->rtadv.HomeAgentLifetime = strtoul(argv[idx_number]->arg, NULL, 10);
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_homeagent_lifetime,
- no_ipv6_nd_homeagent_lifetime_cmd,
- "no ipv6 nd home-agent-lifetime [(0-65520)]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Home Agent lifetime\n"
- "Home Agent lifetime in seconds (0 to track ra-lifetime)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.HomeAgentLifetime = -1;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_managed_config_flag,
- ipv6_nd_managed_config_flag_cmd,
- "ipv6 nd managed-config-flag",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Managed address configuration flag\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvManagedFlag = 1;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_managed_config_flag,
- no_ipv6_nd_managed_config_flag_cmd,
- "no ipv6 nd managed-config-flag",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Managed address configuration flag\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvManagedFlag = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_homeagent_config_flag,
- ipv6_nd_homeagent_config_flag_cmd,
- "ipv6 nd home-agent-config-flag",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Home Agent configuration flag\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvHomeAgentFlag = 1;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_homeagent_config_flag,
- no_ipv6_nd_homeagent_config_flag_cmd,
- "no ipv6 nd home-agent-config-flag",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Home Agent configuration flag\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvHomeAgentFlag = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_adv_interval_config_option,
- ipv6_nd_adv_interval_config_option_cmd,
- "ipv6 nd adv-interval-option",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertisement Interval Option\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvIntervalOption = 1;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_adv_interval_config_option,
- no_ipv6_nd_adv_interval_config_option_cmd,
- "no ipv6 nd adv-interval-option",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertisement Interval Option\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvIntervalOption = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_other_config_flag,
- ipv6_nd_other_config_flag_cmd,
- "ipv6 nd other-config-flag",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Other statefull configuration flag\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvOtherConfigFlag = 1;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_other_config_flag,
- no_ipv6_nd_other_config_flag_cmd,
- "no ipv6 nd other-config-flag",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Other statefull configuration flag\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.AdvOtherConfigFlag = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_prefix,
- ipv6_nd_prefix_cmd,
- "ipv6 nd prefix X:X::X:X/M [<(0-4294967295)|infinite> <(0-4294967295)|infinite>] [<router-address|off-link [no-autoconfig]|no-autoconfig [off-link]>]",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Prefix information\n"
- "IPv6 prefix\n"
- "Valid lifetime in seconds\n"
- "Infinite valid lifetime\n"
- "Preferred lifetime in seconds\n"
- "Infinite preferred lifetime\n"
- "Set Router Address flag\n"
- "Do not use prefix for onlink determination\n"
- "Do not use prefix for autoconfiguration\n"
- "Do not use prefix for autoconfiguration\n"
- "Do not use prefix for onlink determination\n")
-{
- /* prelude */
- char *prefix = argv[3]->arg;
- int lifetimes = (argc > 4) && (argv[4]->type == RANGE_TKN
- || strmatch(argv[4]->text, "infinite"));
- int routeropts = lifetimes ? argc > 6 : argc > 4;
-
- int idx_routeropts = routeropts ? (lifetimes ? 6 : 4) : 0;
-
- char *lifetime = NULL, *preflifetime = NULL;
- int routeraddr = 0, offlink = 0, noautoconf = 0;
- if (lifetimes) {
- lifetime = argv[4]->type == RANGE_TKN ? argv[4]->arg
- : argv[4]->text;
- preflifetime = argv[5]->type == RANGE_TKN ? argv[5]->arg
- : argv[5]->text;
- }
- if (routeropts) {
- routeraddr =
- strmatch(argv[idx_routeropts]->text, "router-address");
- if (!routeraddr) {
- offlink = (argc > idx_routeropts + 1
- || strmatch(argv[idx_routeropts]->text,
- "off-link"));
- noautoconf = (argc > idx_routeropts + 1
- || strmatch(argv[idx_routeropts]->text,
- "no-autoconfig"));
- }
- }
-
- /* business */
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zebra_if = ifp->info;
- int ret;
- struct rtadv_prefix rp;
-
- ret = str2prefix_ipv6(prefix, &rp.prefix);
- if (!ret) {
- vty_out(vty, "Malformed IPv6 prefix\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- apply_mask_ipv6(&rp.prefix); /* RFC4861 4.6.2 */
- rp.AdvOnLinkFlag = !offlink;
- rp.AdvAutonomousFlag = !noautoconf;
- rp.AdvRouterAddressFlag = routeraddr;
- rp.AdvValidLifetime = RTADV_VALID_LIFETIME;
- rp.AdvPreferredLifetime = RTADV_PREFERRED_LIFETIME;
- rp.AdvPrefixCreate = PREFIX_SRC_MANUAL;
-
- if (lifetimes) {
- rp.AdvValidLifetime = strmatch(lifetime, "infinite")
- ? UINT32_MAX
- : strtoll(lifetime, NULL, 10);
- rp.AdvPreferredLifetime =
- strmatch(preflifetime, "infinite")
- ? UINT32_MAX
- : strtoll(preflifetime, NULL, 10);
- if (rp.AdvPreferredLifetime > rp.AdvValidLifetime) {
- vty_out(vty, "Invalid preferred lifetime\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- }
-
- rtadv_prefix_set(zebra_if, &rp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_prefix,
- no_ipv6_nd_prefix_cmd,
- "no ipv6 nd prefix X:X::X:X/M [<(0-4294967295)|infinite> <(0-4294967295)|infinite>] [<router-address|off-link [no-autoconfig]|no-autoconfig [off-link]>]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Prefix information\n"
- "IPv6 prefix\n"
- "Valid lifetime in seconds\n"
- "Infinite valid lifetime\n"
- "Preferred lifetime in seconds\n"
- "Infinite preferred lifetime\n"
- "Set Router Address flag\n"
- "Do not use prefix for onlink determination\n"
- "Do not use prefix for autoconfiguration\n"
- "Do not use prefix for autoconfiguration\n"
- "Do not use prefix for onlink determination\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zebra_if = ifp->info;
- int ret;
- struct rtadv_prefix rp;
- char *prefix = argv[4]->arg;
-
- ret = str2prefix_ipv6(prefix, &rp.prefix);
- if (!ret) {
- vty_out(vty, "Malformed IPv6 prefix\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- apply_mask_ipv6(&rp.prefix); /* RFC4861 4.6.2 */
- rp.AdvPrefixCreate = PREFIX_SRC_MANUAL;
-
- ret = rtadv_prefix_reset(zebra_if, &rp);
- if (!ret) {
- vty_out(vty, "Non-existant IPv6 prefix\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_router_preference,
- ipv6_nd_router_preference_cmd,
- "ipv6 nd router-preference <high|medium|low>",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Default router preference\n"
- "High default router preference\n"
- "Medium default router preference (default)\n"
- "Low default router preference\n")
-{
- int idx_high_medium_low = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- int i = 0;
-
- while (0 != rtadv_pref_strs[i]) {
- if (strncmp(argv[idx_high_medium_low]->arg, rtadv_pref_strs[i],
- 1)
- == 0) {
- zif->rtadv.DefaultPreference = i;
- return CMD_SUCCESS;
- }
- i++;
- }
-
- return CMD_ERR_NO_MATCH;
-}
-
-DEFUN (no_ipv6_nd_router_preference,
- no_ipv6_nd_router_preference_cmd,
- "no ipv6 nd router-preference [<high|medium|low>]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Default router preference\n"
- "High default router preference\n"
- "Medium default router preference (default)\n"
- "Low default router preference\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
-
- zif->rtadv.DefaultPreference =
- RTADV_PREF_MEDIUM; /* Default per RFC4191. */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nd_mtu,
- ipv6_nd_mtu_cmd,
- "ipv6 nd mtu (1-65535)",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertised MTU\n"
- "MTU in bytes\n")
-{
- int idx_number = 3;
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- zif->rtadv.AdvLinkMTU = strtoul(argv[idx_number]->arg, NULL, 10);
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nd_mtu,
- no_ipv6_nd_mtu_cmd,
- "no ipv6 nd mtu [(1-65535)]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Advertised MTU\n"
- "MTU in bytes\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- zif->rtadv.AdvLinkMTU = 0;
- return CMD_SUCCESS;
-}
-
static struct rtadv_rdnss *rtadv_rdnss_new(void)
{
return XCALLOC(MTYPE_RTADV_RDNSS, sizeof(struct rtadv_rdnss));
@@ -2280,55 +1558,22 @@ static void rtadv_rdnss_free(struct rtadv_rdnss *rdnss)
XFREE(MTYPE_RTADV_RDNSS, rdnss);
}
-static struct rtadv_rdnss *rtadv_rdnss_lookup(struct list *list,
- struct rtadv_rdnss *rdnss)
-{
- struct listnode *node;
- struct rtadv_rdnss *p;
-
- for (ALL_LIST_ELEMENTS_RO(list, node, p))
- if (IPV6_ADDR_SAME(&p->addr, &rdnss->addr))
- return p;
- return NULL;
-}
-
-static struct rtadv_rdnss *rtadv_rdnss_get(struct list *list,
- struct rtadv_rdnss *rdnss)
+struct rtadv_rdnss *rtadv_rdnss_set(struct zebra_if *zif,
+ struct rtadv_rdnss *rdnss)
{
struct rtadv_rdnss *p;
- p = rtadv_rdnss_lookup(list, rdnss);
- if (p)
- return p;
-
p = rtadv_rdnss_new();
memcpy(p, rdnss, sizeof(struct rtadv_rdnss));
- listnode_add(list, p);
+ listnode_add(zif->rtadv.AdvRDNSSList, p);
return p;
}
-static void rtadv_rdnss_set(struct zebra_if *zif, struct rtadv_rdnss *rdnss)
+void rtadv_rdnss_reset(struct zebra_if *zif, struct rtadv_rdnss *p)
{
- struct rtadv_rdnss *p;
-
- p = rtadv_rdnss_get(zif->rtadv.AdvRDNSSList, rdnss);
- p->lifetime = rdnss->lifetime;
- p->lifetime_set = rdnss->lifetime_set;
-}
-
-static int rtadv_rdnss_reset(struct zebra_if *zif, struct rtadv_rdnss *rdnss)
-{
- struct rtadv_rdnss *p;
-
- p = rtadv_rdnss_lookup(zif->rtadv.AdvRDNSSList, rdnss);
- if (p) {
- listnode_delete(zif->rtadv.AdvRDNSSList, p);
- rtadv_rdnss_free(p);
- return 1;
- }
-
- return 0;
+ listnode_delete(zif->rtadv.AdvRDNSSList, p);
+ rtadv_rdnss_free(p);
}
static struct rtadv_dnssl *rtadv_dnssl_new(void)
@@ -2341,54 +1586,22 @@ static void rtadv_dnssl_free(struct rtadv_dnssl *dnssl)
XFREE(MTYPE_RTADV_DNSSL, dnssl);
}
-static struct rtadv_dnssl *rtadv_dnssl_lookup(struct list *list,
- struct rtadv_dnssl *dnssl)
+struct rtadv_dnssl *rtadv_dnssl_set(struct zebra_if *zif,
+ struct rtadv_dnssl *dnssl)
{
- struct listnode *node;
struct rtadv_dnssl *p;
- for (ALL_LIST_ELEMENTS_RO(list, node, p))
- if (!strcasecmp(p->name, dnssl->name))
- return p;
- return NULL;
-}
-
-static struct rtadv_dnssl *rtadv_dnssl_get(struct list *list,
- struct rtadv_dnssl *dnssl)
-{
- struct rtadv_dnssl *p;
-
- p = rtadv_dnssl_lookup(list, dnssl);
- if (p)
- return p;
-
p = rtadv_dnssl_new();
memcpy(p, dnssl, sizeof(struct rtadv_dnssl));
- listnode_add(list, p);
+ listnode_add(zif->rtadv.AdvDNSSLList, p);
return p;
}
-static void rtadv_dnssl_set(struct zebra_if *zif, struct rtadv_dnssl *dnssl)
+void rtadv_dnssl_reset(struct zebra_if *zif, struct rtadv_dnssl *p)
{
- struct rtadv_dnssl *p;
-
- p = rtadv_dnssl_get(zif->rtadv.AdvDNSSLList, dnssl);
- memcpy(p, dnssl, sizeof(struct rtadv_dnssl));
-}
-
-static int rtadv_dnssl_reset(struct zebra_if *zif, struct rtadv_dnssl *dnssl)
-{
- struct rtadv_dnssl *p;
-
- p = rtadv_dnssl_lookup(zif->rtadv.AdvDNSSLList, dnssl);
- if (p) {
- listnode_delete(zif->rtadv.AdvDNSSLList, p);
- rtadv_dnssl_free(p);
- return 1;
- }
-
- return 0;
+ listnode_delete(zif->rtadv.AdvDNSSLList, p);
+ rtadv_dnssl_free(p);
}
/*
@@ -2399,7 +1612,7 @@ static int rtadv_dnssl_reset(struct zebra_if *zif, struct rtadv_dnssl *dnssl)
* Returns the number of octets written to out or -1 if in does not constitute
* a valid domain name.
*/
-static int rtadv_dnssl_encode(uint8_t *out, const char *in)
+int rtadv_dnssl_encode(uint8_t *out, const char *in)
{
const char *label_start, *label_end;
size_t outp;
@@ -2430,148 +1643,6 @@ static int rtadv_dnssl_encode(uint8_t *out, const char *in)
return outp;
}
-DEFUN(ipv6_nd_rdnss,
- ipv6_nd_rdnss_cmd,
- "ipv6 nd rdnss X:X::X:X [<(0-4294967295)|infinite>]",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Recursive DNS server information\n"
- "IPv6 address\n"
- "Valid lifetime in seconds\n"
- "Infinite valid lifetime\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- struct rtadv_rdnss rdnss = {};
-
- if (inet_pton(AF_INET6, argv[3]->arg, &rdnss.addr) != 1) {
- vty_out(vty, "Malformed IPv6 address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if (argc > 4) {
- char *lifetime = argv[4]->type == RANGE_TKN ? argv[4]->arg
- : argv[4]->text;
- rdnss.lifetime = strmatch(lifetime, "infinite")
- ? UINT32_MAX
- : strtoll(lifetime, NULL, 10);
- rdnss.lifetime_set = 1;
- }
-
- rtadv_rdnss_set(zif, &rdnss);
-
- return CMD_SUCCESS;
-}
-
-DEFUN(no_ipv6_nd_rdnss,
- no_ipv6_nd_rdnss_cmd,
- "no ipv6 nd rdnss X:X::X:X [<(0-4294967295)|infinite>]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "Recursive DNS server information\n"
- "IPv6 address\n"
- "Valid lifetime in seconds\n"
- "Infinite valid lifetime\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- struct rtadv_rdnss rdnss = {};
-
- if (inet_pton(AF_INET6, argv[4]->arg, &rdnss.addr) != 1) {
- vty_out(vty, "Malformed IPv6 address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if (rtadv_rdnss_reset(zif, &rdnss) != 1) {
- vty_out(vty, "Non-existant RDNSS address\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- return CMD_SUCCESS;
-}
-
-DEFUN(ipv6_nd_dnssl,
- ipv6_nd_dnssl_cmd,
- "ipv6 nd dnssl SUFFIX [<(0-4294967295)|infinite>]",
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "DNS search list information\n"
- "Domain name suffix\n"
- "Valid lifetime in seconds\n"
- "Infinite valid lifetime\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- struct rtadv_dnssl dnssl = {};
- size_t len;
- int ret;
-
- len = strlcpy(dnssl.name, argv[3]->arg, sizeof(dnssl.name));
- if (len == 0 || len >= sizeof(dnssl.name)) {
- vty_out(vty, "Malformed DNS search domain\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if (dnssl.name[len - 1] == '.') {
- /*
- * Allow, but don't require, a trailing dot signifying the root
- * zone. Canonicalize by cutting it off if present.
- */
- dnssl.name[len - 1] = '\0';
- len--;
- }
- if (argc > 4) {
- char *lifetime = argv[4]->type == RANGE_TKN ? argv[4]->arg
- : argv[4]->text;
- dnssl.lifetime = strmatch(lifetime, "infinite")
- ? UINT32_MAX
- : strtoll(lifetime, NULL, 10);
- dnssl.lifetime_set = 1;
- }
-
- ret = rtadv_dnssl_encode(dnssl.encoded_name, dnssl.name);
- if (ret < 0) {
- vty_out(vty, "Malformed DNS search domain\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- dnssl.encoded_len = ret;
- rtadv_dnssl_set(zif, &dnssl);
-
- return CMD_SUCCESS;
-}
-
-DEFUN(no_ipv6_nd_dnssl,
- no_ipv6_nd_dnssl_cmd,
- "no ipv6 nd dnssl SUFFIX [<(0-4294967295)|infinite>]",
- NO_STR
- "Interface IPv6 config commands\n"
- "Neighbor discovery\n"
- "DNS search list information\n"
- "Domain name suffix\n"
- "Valid lifetime in seconds\n"
- "Infinite valid lifetime\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif = ifp->info;
- struct rtadv_dnssl dnssl = {};
- size_t len;
-
- len = strlcpy(dnssl.name, argv[4]->arg, sizeof(dnssl.name));
- if (len == 0 || len >= sizeof(dnssl.name)) {
- vty_out(vty, "Malformed DNS search domain\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if (dnssl.name[len - 1] == '.') {
- dnssl.name[len - 1] = '\0';
- len--;
- }
- if (rtadv_dnssl_reset(zif, &dnssl) != 1) {
- vty_out(vty, "Non-existant DNS search domain\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- return CMD_SUCCESS;
-}
-
-
/* Dump interface ND information to vty. */
static int nd_dump_vty(struct vty *vty, struct interface *ifp)
{
@@ -2642,136 +1713,6 @@ static int nd_dump_vty(struct vty *vty, struct interface *ifp)
return 0;
}
-
-/* Write configuration about router advertisement. */
-static int rtadv_config_write(struct vty *vty, struct interface *ifp)
-{
- struct zebra_if *zif;
- struct listnode *node;
- struct rtadv_prefix *rprefix;
- struct rtadv_rdnss *rdnss;
- struct rtadv_dnssl *dnssl;
- int interval;
-
- zif = ifp->info;
-
- if (!if_is_loopback(ifp)) {
- if (zif->rtadv.AdvSendAdvertisements
- && CHECK_FLAG(zif->rtadv.ra_configured, VTY_RA_CONFIGURED))
- vty_out(vty, " no ipv6 nd suppress-ra\n");
- }
-
- interval = zif->rtadv.MaxRtrAdvInterval;
- if (CHECK_FLAG(zif->rtadv.ra_configured, VTY_RA_INTERVAL_CONFIGURED)) {
- if (interval % 1000)
- vty_out(vty, " ipv6 nd ra-interval msec %d\n",
- interval);
- else if (interval != RTADV_MAX_RTR_ADV_INTERVAL)
- vty_out(vty, " ipv6 nd ra-interval %d\n",
- interval / 1000);
- }
-
- if (zif->rtadv.AdvIntervalOption)
- vty_out(vty, " ipv6 nd adv-interval-option\n");
-
- if (!zif->rtadv.UseFastRexmit)
- vty_out(vty, " no ipv6 nd ra-fast-retrans\n");
-
- if (zif->rtadv.AdvRetransTimer != 0)
- vty_out(vty, " ipv6 nd ra-retrans-interval %u\n",
- zif->rtadv.AdvRetransTimer);
-
- if (zif->rtadv.AdvCurHopLimit != RTADV_DEFAULT_HOPLIMIT)
- vty_out(vty, " ipv6 nd ra-hop-limit %d\n",
- zif->rtadv.AdvCurHopLimit);
-
- if (zif->rtadv.AdvDefaultLifetime != -1)
- vty_out(vty, " ipv6 nd ra-lifetime %d\n",
- zif->rtadv.AdvDefaultLifetime);
-
- if (zif->rtadv.HomeAgentPreference)
- vty_out(vty, " ipv6 nd home-agent-preference %u\n",
- zif->rtadv.HomeAgentPreference);
-
- if (zif->rtadv.HomeAgentLifetime != -1)
- vty_out(vty, " ipv6 nd home-agent-lifetime %u\n",
- zif->rtadv.HomeAgentLifetime);
-
- if (zif->rtadv.AdvHomeAgentFlag)
- vty_out(vty, " ipv6 nd home-agent-config-flag\n");
-
- if (zif->rtadv.AdvReachableTime)
- vty_out(vty, " ipv6 nd reachable-time %d\n",
- zif->rtadv.AdvReachableTime);
-
- if (zif->rtadv.AdvManagedFlag)
- vty_out(vty, " ipv6 nd managed-config-flag\n");
-
- if (zif->rtadv.AdvOtherConfigFlag)
- vty_out(vty, " ipv6 nd other-config-flag\n");
-
- if (zif->rtadv.DefaultPreference != RTADV_PREF_MEDIUM)
- vty_out(vty, " ipv6 nd router-preference %s\n",
- rtadv_pref_strs[zif->rtadv.DefaultPreference]);
-
- if (zif->rtadv.AdvLinkMTU)
- vty_out(vty, " ipv6 nd mtu %d\n", zif->rtadv.AdvLinkMTU);
-
- frr_each (rtadv_prefixes, zif->rtadv.prefixes, rprefix) {
- if ((rprefix->AdvPrefixCreate == PREFIX_SRC_MANUAL)
- || (rprefix->AdvPrefixCreate == PREFIX_SRC_BOTH)) {
- vty_out(vty, " ipv6 nd prefix %pFX", &rprefix->prefix);
- if ((rprefix->AdvValidLifetime != RTADV_VALID_LIFETIME)
- || (rprefix->AdvPreferredLifetime
- != RTADV_PREFERRED_LIFETIME)) {
- if (rprefix->AdvValidLifetime == UINT32_MAX)
- vty_out(vty, " infinite");
- else
- vty_out(vty, " %u",
- rprefix->AdvValidLifetime);
- if (rprefix->AdvPreferredLifetime == UINT32_MAX)
- vty_out(vty, " infinite");
- else
- vty_out(vty, " %u",
- rprefix->AdvPreferredLifetime);
- }
- if (!rprefix->AdvOnLinkFlag)
- vty_out(vty, " off-link");
- if (!rprefix->AdvAutonomousFlag)
- vty_out(vty, " no-autoconfig");
- if (rprefix->AdvRouterAddressFlag)
- vty_out(vty, " router-address");
- vty_out(vty, "\n");
- }
- }
-
- for (ALL_LIST_ELEMENTS_RO(zif->rtadv.AdvRDNSSList, node, rdnss)) {
- char buf[INET6_ADDRSTRLEN];
-
- vty_out(vty, " ipv6 nd rdnss %s",
- inet_ntop(AF_INET6, &rdnss->addr, buf, sizeof(buf)));
- if (rdnss->lifetime_set) {
- if (rdnss->lifetime == UINT32_MAX)
- vty_out(vty, " infinite");
- else
- vty_out(vty, " %u", rdnss->lifetime);
- }
- vty_out(vty, "\n");
- }
- for (ALL_LIST_ELEMENTS_RO(zif->rtadv.AdvDNSSLList, node, dnssl)) {
- vty_out(vty, " ipv6 nd dnssl %s", dnssl->name);
- if (dnssl->lifetime_set) {
- if (dnssl->lifetime == UINT32_MAX)
- vty_out(vty, " infinite");
- else
- vty_out(vty, " %u", dnssl->lifetime);
- }
- vty_out(vty, "\n");
- }
- return 0;
-}
-
-
static void rtadv_event(struct zebra_vrf *zvrf, enum rtadv_event event, int val)
{
struct rtadv *rtadv;
@@ -2917,49 +1858,8 @@ void rtadv_cmd_init(void)
interfaces_configured_for_ra_from_bgp = 0;
hook_register(zebra_if_extra_info, nd_dump_vty);
- hook_register(zebra_if_config_wr, rtadv_config_write);
install_element(VIEW_NODE, &show_ipv6_nd_ra_if_cmd);
-
- install_element(INTERFACE_NODE, &ipv6_nd_ra_fast_retrans_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_ra_fast_retrans_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_ra_retrans_interval_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_ra_retrans_interval_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_ra_hop_limit_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_ra_hop_limit_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_suppress_ra_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_suppress_ra_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_ra_interval_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_ra_interval_msec_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_ra_interval_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_ra_lifetime_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_ra_lifetime_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_reachable_time_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_reachable_time_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_managed_config_flag_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_managed_config_flag_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_other_config_flag_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_other_config_flag_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_homeagent_config_flag_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_homeagent_config_flag_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_homeagent_preference_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_homeagent_preference_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_homeagent_lifetime_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_homeagent_lifetime_cmd);
- install_element(INTERFACE_NODE,
- &ipv6_nd_adv_interval_config_option_cmd);
- install_element(INTERFACE_NODE,
- &no_ipv6_nd_adv_interval_config_option_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_prefix_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_prefix_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_router_preference_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_router_preference_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_mtu_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_mtu_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_rdnss_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_rdnss_cmd);
- install_element(INTERFACE_NODE, &ipv6_nd_dnssl_cmd);
- install_element(INTERFACE_NODE, &no_ipv6_nd_dnssl_cmd);
}
static int if_join_all_router(int sock, struct interface *ifp)
diff --git a/zebra/rtadv.h b/zebra/rtadv.h
index 9d358d4b0d..0983ea578f 100644
--- a/zebra/rtadv.h
+++ b/zebra/rtadv.h
@@ -385,6 +385,30 @@ extern void rtadv_if_fini(struct zebra_if *zif);
extern void rtadv_add_prefix(struct zebra_if *zif, const struct prefix_ipv6 *p);
extern void rtadv_delete_prefix(struct zebra_if *zif, const struct prefix *p);
+/* returns created prefix */
+struct rtadv_prefix *rtadv_add_prefix_manual(struct zebra_if *zif,
+ struct rtadv_prefix *rp);
+/* rprefix must be the one returned by rtadv_add_prefix_manual */
+void rtadv_delete_prefix_manual(struct zebra_if *zif,
+ struct rtadv_prefix *rprefix);
+
+/* returns created address */
+struct rtadv_rdnss *rtadv_rdnss_set(struct zebra_if *zif,
+ struct rtadv_rdnss *rdnss);
+/* p must be the one returned by rtadv_rdnss_set */
+void rtadv_rdnss_reset(struct zebra_if *zif, struct rtadv_rdnss *p);
+
+/* returns created domain */
+struct rtadv_dnssl *rtadv_dnssl_set(struct zebra_if *zif,
+ struct rtadv_dnssl *dnssl);
+/* p must be the one returned by rtadv_dnssl_set */
+void rtadv_dnssl_reset(struct zebra_if *zif, struct rtadv_dnssl *p);
+int rtadv_dnssl_encode(uint8_t *out, const char *in);
+
+void ipv6_nd_suppress_ra_set(struct interface *ifp,
+ enum ipv6_nd_suppress_ra_status status);
+void ipv6_nd_interval_set(struct interface *ifp, uint32_t interval);
+
#else /* !HAVE_RTADV */
struct rtadv {
/* empty structs aren't valid ISO C */
diff --git a/zebra/subdir.am b/zebra/subdir.am
index a59515d3a8..d9c8d9045e 100644
--- a/zebra/subdir.am
+++ b/zebra/subdir.am
@@ -28,7 +28,7 @@ man8 += $(MANBUILD)/frr-zebra.8
## endif ZEBRA
endif
-zebra_zebra_LDADD = lib/libfrr.la $(LIBCAP) $(UST_LIBS)
+zebra_zebra_LDADD = lib/libfrr.la $(LIBCAP) $(LIBYANG_LIBS) $(UST_LIBS)
if HAVE_PROTOBUF3
zebra_zebra_LDADD += mlag/libmlag_pb.la $(PROTOBUF_C_LIBS)
zebra/zebra_mlag.$(OBJEXT): mlag/mlag.pb-c.h
@@ -118,7 +118,6 @@ clippy_scan += \
zebra/debug.c \
zebra/interface.c \
zebra/rtadv.c \
- zebra/zebra_evpn_mh.c \
zebra/zebra_mlag_vty.c \
zebra/zebra_routemap.c \
zebra/zebra_vty.c \
@@ -126,6 +125,7 @@ clippy_scan += \
zebra/zebra_vrf.c \
zebra/dpdk/zebra_dplane_dpdk_vty.c \
zebra/label_manager.c \
+ zebra/zebra_cli.c \
# end
noinst_HEADERS += \
diff --git a/zebra/table_manager.c b/zebra/table_manager.c
index 512508b79f..8417a22114 100644
--- a/zebra/table_manager.c
+++ b/zebra/table_manager.c
@@ -24,21 +24,6 @@
#include "zebra/table_manager.h"
#include "zebra/zebra_errors.h"
-/* routing table identifiers
- *
- */
-#if !defined(GNU_LINUX)
-/* BSD systems
- */
-#else
-/* Linux Systems
- */
-#define RT_TABLE_ID_LOCAL 255
-#define RT_TABLE_ID_MAIN 254
-#define RT_TABLE_ID_DEFAULT 253
-#define RT_TABLE_ID_COMPAT 252
-#define RT_TABLE_ID_UNSPEC 0
-#endif /* !def(GNU_LINUX) */
#define RT_TABLE_ID_UNRESERVED_MIN 1
#define RT_TABLE_ID_UNRESERVED_MAX 0xffffffff
@@ -279,52 +264,11 @@ void table_manager_disable(struct zebra_vrf *zvrf)
zvrf->tbl_mgr = NULL;
}
-int table_manager_range(struct vty *vty, bool add, struct zebra_vrf *zvrf,
- const char *start_table_str, const char *end_table_str)
+void table_manager_range(bool add, struct zebra_vrf *zvrf, uint32_t start,
+ uint32_t end)
{
- uint32_t start;
- uint32_t end;
-
- if (add) {
- if (!start_table_str || !end_table_str) {
- vty_out(vty, "%% Labels not specified\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- start = atoi(start_table_str);
- end = atoi(end_table_str);
- if (end < start) {
- vty_out(vty, "%% End table is less than Start table\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
-#if !defined(GNU_LINUX)
-/* BSD systems
- */
-#else
- /* Linux Systems
- */
- if ((start >= RT_TABLE_ID_COMPAT && start <= RT_TABLE_ID_LOCAL)
- || (end >= RT_TABLE_ID_COMPAT
- && end <= RT_TABLE_ID_LOCAL)) {
- vty_out(vty, "%% Values forbidden in range [%u;%u]\n",
- RT_TABLE_ID_COMPAT, RT_TABLE_ID_LOCAL);
- return CMD_WARNING_CONFIG_FAILED;
- }
- if (start < RT_TABLE_ID_COMPAT && end > RT_TABLE_ID_LOCAL) {
- vty_out(vty,
- "%% Range overlaps range [%u;%u] forbidden\n",
- RT_TABLE_ID_COMPAT, RT_TABLE_ID_LOCAL);
- return CMD_WARNING_CONFIG_FAILED;
- }
-#endif
- if (zvrf->tbl_mgr
- && ((zvrf->tbl_mgr->start && zvrf->tbl_mgr->start != start)
- || (zvrf->tbl_mgr->end && zvrf->tbl_mgr->end != end))) {
- vty_out(vty,
- "%% New range will be taken into account at restart\n");
- }
+ if (add)
table_range_add(zvrf, start, end);
- } else
+ else
table_range_add(zvrf, 0, 0);
- return CMD_SUCCESS;
}
diff --git a/zebra/table_manager.h b/zebra/table_manager.h
index f8e99a357d..21691994cb 100644
--- a/zebra/table_manager.h
+++ b/zebra/table_manager.h
@@ -18,6 +18,22 @@
extern "C" {
#endif
+/* routing table identifiers
+ *
+ */
+#if !defined(GNU_LINUX)
+/* BSD systems
+ */
+#else
+/* Linux Systems
+ */
+#define RT_TABLE_ID_LOCAL 255
+#define RT_TABLE_ID_MAIN 254
+#define RT_TABLE_ID_DEFAULT 253
+#define RT_TABLE_ID_COMPAT 252
+#define RT_TABLE_ID_UNSPEC 0
+#endif /* !def(GNU_LINUX) */
+
/*
* Table chunk struct
* Client daemon which the chunk belongs to can be identified by either
@@ -56,8 +72,8 @@ int release_table_chunk(uint8_t proto, uint16_t instance, uint32_t start,
uint32_t end, struct zebra_vrf *zvrf);
int release_daemon_table_chunks(struct zserv *client);
void table_manager_disable(struct zebra_vrf *zvrf);
-int table_manager_range(struct vty *vty, bool add, struct zebra_vrf *zvrf,
- const char *min, const char *max);
+void table_manager_range(bool add, struct zebra_vrf *zvrf, uint32_t start,
+ uint32_t end);
#ifdef __cplusplus
}
diff --git a/zebra/zebra_cli.c b/zebra/zebra_cli.c
new file mode 100644
index 0000000000..76b2df157e
--- /dev/null
+++ b/zebra/zebra_cli.c
@@ -0,0 +1,2969 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+
+#ifdef HAVE_CONFIG_H
+#include "config.h"
+#endif
+
+#include "command.h"
+#include "defaults.h"
+#include "northbound_cli.h"
+#include "vrf.h"
+
+#include "zebra_cli.h"
+#include "zebra/zebra_cli_clippy.c"
+
+#define EVPN_MH_VTY_STR "Multihoming\n"
+
+FRR_CFG_DEFAULT_BOOL(ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT,
+ { .val_bool = true, .match_profile = "traditional", },
+ { .val_bool = false },
+);
+
+#if HAVE_BFDD == 0
+DEFPY_YANG (zebra_ptm_enable,
+ zebra_ptm_enable_cmd,
+ "[no] ptm-enable",
+ NO_STR
+ "Enable neighbor check with specified topology\n")
+{
+ nb_cli_enqueue_change(vty, "/frr-zebra:zebra/ptm-enable", NB_OP_MODIFY,
+ no ? "false" : "true");
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void zebra_ptm_enable_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ bool enable = yang_dnode_get_bool(dnode, NULL);
+
+ if (enable)
+ vty_out(vty, "ptm-enable\n");
+ else if (show_defaults)
+ vty_out(vty, "no ptm-enable\n");
+}
+#endif
+
+DEFPY_YANG (zebra_route_map_timer,
+ zebra_route_map_timer_cmd,
+ "[no] zebra route-map delay-timer ![(0-600)$delay]",
+ NO_STR
+ ZEBRA_STR
+ "Set route-map parameters\n"
+ "Time to wait before route-map updates are processed\n"
+ "0 means route-map changes are run immediately instead of delaying\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "/frr-zebra:zebra/route-map-delay",
+ NB_OP_MODIFY, delay_str);
+ else
+ nb_cli_enqueue_change(vty, "/frr-zebra:zebra/route-map-delay",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void zebra_route_map_delay_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ uint32_t delay = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, "zebra route-map delay-timer %u\n", delay);
+}
+
+DEFPY_YANG (multicast_new,
+ multicast_new_cmd,
+ "[no] multicast <enable$on|disable$off>",
+ NO_STR
+ "Control multicast flag on interface\n"
+ "Set multicast flag on interface\n"
+ "Unset multicast flag on interface\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/multicast",
+ NB_OP_CREATE, on ? "true" : "false");
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/multicast",
+ NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_multicast_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ bool multicast = yang_dnode_get_bool(dnode, NULL);
+
+ if (multicast)
+ vty_out(vty, " multicast enable\n");
+ else
+ vty_out(vty, " multicast disable\n");
+}
+
+/* Deprecated multicast commands */
+
+DEFPY_YANG_HIDDEN (multicast,
+ multicast_cmd,
+ "[no] multicast",
+ NO_STR
+ "Set multicast flag to interface\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/multicast",
+ NB_OP_CREATE, no ? "false" : "true");
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG (mpls,
+ mpls_cmd,
+ "[no] mpls <enable$on|disable$off>",
+ NO_STR
+ MPLS_STR
+ "Set mpls to be on for the interface\n"
+ "Set mpls to be off for the interface\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/mpls",
+ NB_OP_CREATE, on ? "true" : "false");
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/mpls",
+ NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_mpls_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ bool mpls = yang_dnode_get_bool(dnode, NULL);
+
+ if (mpls)
+ vty_out(vty, " mpls enable\n");
+ else
+ vty_out(vty, " mpls disable\n");
+}
+
+DEFPY_YANG (linkdetect,
+ linkdetect_cmd,
+ "[no] link-detect",
+ NO_STR
+ "Enable link detection on interface\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/link-detect",
+ NB_OP_CREATE, no ? "false" : "true");
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_detect_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool link_detect = yang_dnode_get_bool(dnode, NULL);
+
+ if (!link_detect)
+ vty_out(vty, " no link-detect\n");
+ else if (show_defaults)
+ vty_out(vty, " link-detect\n");
+}
+
+DEFPY_YANG (shutdown_if,
+ shutdown_if_cmd,
+ "[no] shutdown",
+ NO_STR
+ "Shutdown the selected interface\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/enabled", NB_OP_CREATE,
+ no ? "true" : "false");
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_enabled_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ bool enabled = yang_dnode_get_bool(dnode, NULL);
+
+ if (!enabled)
+ vty_out(vty, " shutdown\n");
+ else if (show_defaults)
+ vty_out(vty, " no shutdown\n");
+}
+
+DEFPY_YANG (bandwidth_if,
+ bandwidth_if_cmd,
+ "[no] bandwidth ![(1-100000)]$bw",
+ NO_STR
+ "Set bandwidth informational parameter\n"
+ "Bandwidth in megabits\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/bandwidth",
+ NB_OP_CREATE, bw_str);
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/bandwidth",
+ NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_bandwidth_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ uint32_t bandwidth = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " bandwidth %u\n", bandwidth);
+}
+
+DEFUN_YANG_NOSH (link_params,
+ link_params_cmd,
+ "link-params",
+ LINK_PARAMS_STR)
+{
+ int ret;
+
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/link-params",
+ NB_OP_CREATE, NULL);
+
+ ret = nb_cli_apply_changes(vty, NULL);
+ if (ret == CMD_SUCCESS) {
+ char *xpath;
+
+ xpath = asprintfrr(MTYPE_TMP, "%s/frr-zebra:zebra/link-params",
+ VTY_CURR_XPATH);
+ VTY_PUSH_XPATH(LINK_PARAMS_NODE, xpath);
+ XFREE(MTYPE_TMP, xpath);
+ }
+
+ return ret;
+}
+
+DEFUN_NOSH (exit_link_params,
+ exit_link_params_cmd,
+ "exit-link-params",
+ "Exit from Link Params configuration mode\n")
+{
+ cmd_exit(vty);
+ return CMD_SUCCESS;
+}
+
+static void lib_interface_zebra_link_params_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ vty_out(vty, " link-params\n");
+}
+
+static void
+lib_interface_zebra_link_params_cli_write_end(struct vty *vty,
+ const struct lyd_node *dnode)
+{
+ vty_out(vty, " exit-link-params\n");
+}
+
+DEFUN_YANG (no_link_params,
+ no_link_params_cmd,
+ "no link-params",
+ NO_STR
+ LINK_PARAMS_STR)
+{
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/link-params", NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+/* [no] enable is deprecated, link-params is enabled when entering the node. */
+
+DEFUN_YANG_HIDDEN (link_params_enable,
+ link_params_enable_cmd,
+ "enable",
+ "Activate link parameters on this interface\n")
+{
+ vty_out(vty, "This command is deprecated. Link parameters are activated when \"link-params\" node is entered.\n");
+
+ return CMD_SUCCESS;
+}
+
+DEFUN_YANG_NOSH (no_link_params_enable,
+ no_link_params_enable_cmd,
+ "no enable",
+ NO_STR
+ "Disable link parameters on this interface\n")
+{
+ int ret;
+
+ vty_out(vty, "This command is deprecated. To disable link parameters use \"no link-params\" in the interface node.\n");
+
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+
+ ret = nb_cli_apply_changes(vty, NULL);
+ if (ret == CMD_SUCCESS)
+ cmd_exit(vty);
+
+ return ret;
+}
+
+DEFPY_YANG (link_params_metric,
+ link_params_metric_cmd,
+ "[no] metric ![(0-4294967295)]$metric",
+ NO_STR
+ "Link metric for MPLS-TE purpose\n"
+ "Metric value in decimal\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./metric", NB_OP_MODIFY, metric_str);
+ else
+ nb_cli_enqueue_change(vty, "./metric", NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_metric_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t metric = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " metric %u\n", metric);
+}
+
+DEFPY_YANG (link_params_maxbw,
+ link_params_maxbw_cmd,
+ "max-bw BANDWIDTH",
+ "Maximum bandwidth that can be used\n"
+ "Bytes/second (IEEE floating point format)\n")
+{
+ char value[YANG_VALUE_MAXLEN];
+ float bw;
+
+ if (sscanf(bandwidth, "%g", &bw) != 1) {
+ vty_out(vty, "Invalid bandwidth value\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ snprintf(value, sizeof(value), "%a", bw);
+
+ nb_cli_enqueue_change(vty, "./max-bandwidth", NB_OP_MODIFY, value);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_max_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ float max_bandwidth = yang_dnode_get_bandwidth_ieee_float32(dnode, NULL);
+
+ vty_out(vty, " max-bw %g\n", max_bandwidth);
+}
+
+DEFPY_YANG (link_params_max_rsv_bw,
+ link_params_max_rsv_bw_cmd,
+ "max-rsv-bw BANDWIDTH",
+ "Maximum bandwidth that may be reserved\n"
+ "Bytes/second (IEEE floating point format)\n")
+{
+ char value[YANG_VALUE_MAXLEN];
+ float bw;
+
+ if (sscanf(bandwidth, "%g", &bw) != 1) {
+ vty_out(vty, "Invalid bandwidth value\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ snprintf(value, sizeof(value), "%a", bw);
+
+ nb_cli_enqueue_change(vty, "./max-reservable-bandwidth", NB_OP_MODIFY,
+ value);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_max_reservable_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ float max_reservable_bandwidth =
+ yang_dnode_get_bandwidth_ieee_float32(dnode, NULL);
+
+ vty_out(vty, " max-rsv-bw %g\n", max_reservable_bandwidth);
+}
+
+DEFPY_YANG (link_params_unrsv_bw,
+ link_params_unrsv_bw_cmd,
+ "unrsv-bw (0-7)$priority BANDWIDTH",
+ "Unreserved bandwidth at each priority level\n"
+ "Priority\n"
+ "Bytes/second (IEEE floating point format)\n")
+{
+ char xpath[XPATH_MAXLEN];
+ char value[YANG_VALUE_MAXLEN];
+ float bw;
+
+ if (sscanf(bandwidth, "%g", &bw) != 1) {
+ vty_out(vty, "Invalid bandwidth value\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ snprintf(xpath, sizeof(xpath),
+ "./unreserved-bandwidths/unreserved-bandwidth[priority='%s']/unreserved-bandwidth",
+ priority_str);
+ snprintf(value, sizeof(value), "%a", bw);
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_MODIFY, value);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint8_t priority = yang_dnode_get_uint8(dnode, "priority");
+ float unreserved_bandwidth =
+ yang_dnode_get_bandwidth_ieee_float32(dnode,
+ "unreserved-bandwidth");
+
+ vty_out(vty, " unrsv-bw %u %g\n", priority, unreserved_bandwidth);
+}
+
+DEFPY_YANG (link_params_admin_grp,
+ link_params_admin_grp_cmd,
+ "[no] admin-grp ![BITPATTERN]",
+ NO_STR
+ "Administrative group membership\n"
+ "32-bit Hexadecimal value (e.g. 0xa1)\n")
+{
+ uint32_t value;
+ char value_str[YANG_VALUE_MAXLEN];
+
+ if (!no) {
+ if (bitpattern[0] != '0' || bitpattern[1] != 'x' ||
+ strlen(bitpattern) > 10) {
+ vty_out(vty, "Invalid bitpattern value\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ sscanf(bitpattern, "%x", &value);
+ snprintf(value_str, sizeof(value_str), "%u", value);
+
+ nb_cli_enqueue_change(vty, "./legacy-admin-group", NB_OP_MODIFY,
+ value_str);
+ } else {
+ nb_cli_enqueue_change(vty, "./legacy-admin-group",
+ NB_OP_DESTROY, NULL);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_legacy_admin_group_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ vty_out(vty, " admin-grp %#x\n", yang_dnode_get_uint32(dnode, NULL));
+}
+
+/* RFC5392 & RFC5316: INTER-AS */
+DEFPY_YANG (link_params_inter_as,
+ link_params_inter_as_cmd,
+ "[no] neighbor ![A.B.C.D$ip as (1-4294967295)$as]",
+ NO_STR
+ "Configure remote ASBR information (Neighbor IP address and AS number)\n"
+ "Remote IP address in dot decimal A.B.C.D\n"
+ "Remote AS number\n"
+ "AS number in the range <1-4294967295>\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, "./neighbor", NB_OP_CREATE, NULL);
+ nb_cli_enqueue_change(vty, "./neighbor/remote-as", NB_OP_MODIFY,
+ as_str);
+ nb_cli_enqueue_change(vty, "./neighbor/ipv4-remote-id",
+ NB_OP_MODIFY, ip_str);
+ } else {
+ nb_cli_enqueue_change(vty, "./neighbor", NB_OP_DESTROY, NULL);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_neighbor_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t remote_as = yang_dnode_get_uint32(dnode, "remote-as");
+ const char *ipv4_remote_id = yang_dnode_get_string(dnode,
+ "ipv4-remote-id");
+
+ vty_out(vty, " neighbor %s as %u\n", ipv4_remote_id, remote_as);
+}
+
+/* RFC7471 & RFC8570 */
+DEFPY_YANG (link_params_delay,
+ link_params_delay_cmd,
+ "[no] delay ![(0-16777215)$delay [min (0-16777215)$min max (0-16777215)$max]]",
+ NO_STR
+ "Unidirectional Average Link Delay\n"
+ "Average delay in micro-second as decimal (0...16777215)\n"
+ "Minimum delay\n"
+ "Minimum delay in micro-second as decimal (0...16777215)\n"
+ "Maximum delay\n"
+ "Maximum delay in micro-second as decimal (0...16777215)\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, "./delay", NB_OP_MODIFY, delay_str);
+ if (min_str && max_str) {
+ nb_cli_enqueue_change(vty, "./min-max-delay",
+ NB_OP_CREATE, NULL);
+ nb_cli_enqueue_change(vty, "./min-max-delay/delay-min",
+ NB_OP_MODIFY, min_str);
+ nb_cli_enqueue_change(vty, "./min-max-delay/delay-max",
+ NB_OP_MODIFY, max_str);
+ } else {
+ nb_cli_enqueue_change(vty, "./min-max-delay",
+ NB_OP_DESTROY, NULL);
+ }
+ } else {
+ nb_cli_enqueue_change(vty, "./delay", NB_OP_DESTROY, NULL);
+ nb_cli_enqueue_change(vty, "./min-max-delay", NB_OP_DESTROY,
+ NULL);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_delay_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t delay = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " delay %u", delay);
+
+ if (yang_dnode_exists(dnode, "../min-max-delay")) {
+ uint32_t delay_min =
+ yang_dnode_get_uint32(dnode,
+ "../min-max-delay/delay-min");
+ uint32_t delay_max =
+ yang_dnode_get_uint32(dnode,
+ "../min-max-delay/delay-max");
+
+ vty_out(vty, " min %u max %u", delay_min, delay_max);
+ }
+
+ vty_out(vty, "\n");
+}
+
+DEFPY_YANG (link_params_delay_var,
+ link_params_delay_var_cmd,
+ "[no] delay-variation ![(0-16777215)$delay_var]",
+ NO_STR
+ "Unidirectional Link Delay Variation\n"
+ "delay variation in micro-second as decimal (0...16777215)\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./delay-variation", NB_OP_MODIFY,
+ delay_var_str);
+ else
+ nb_cli_enqueue_change(vty, "./delay-variation", NB_OP_DESTROY,
+ NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_delay_variation_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t delay_variation = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " delay-variation %u\n", delay_variation);
+}
+
+DEFPY_YANG(
+ link_params_pkt_loss, link_params_pkt_loss_cmd,
+ "[no] packet-loss ![PERCENTAGE]",
+ NO_STR
+ "Unidirectional Link Packet Loss\n"
+ "percentage of total traffic by 0.000003% step and less than 50.331642%\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./packet-loss", NB_OP_MODIFY,
+ percentage);
+ else
+ nb_cli_enqueue_change(vty, "./packet-loss", NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_packet_loss_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ double packet_loss = yang_dnode_get_dec64(dnode, NULL);
+
+ vty_out(vty, " packet-loss %lf\n", packet_loss);
+}
+
+DEFPY_YANG (link_params_res_bw,
+ link_params_res_bw_cmd,
+ "[no] res-bw ![BANDWIDTH]",
+ NO_STR
+ "Unidirectional Residual Bandwidth\n"
+ "Bytes/second (IEEE floating point format)\n")
+{
+ char value[YANG_VALUE_MAXLEN];
+ float bw;
+
+ if (!no) {
+ if (sscanf(bandwidth, "%g", &bw) != 1) {
+ vty_out(vty, "Invalid bandwidth value\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ snprintf(value, sizeof(value), "%a", bw);
+
+ nb_cli_enqueue_change(vty, "./residual-bandwidth", NB_OP_MODIFY,
+ value);
+ } else {
+ nb_cli_enqueue_change(vty, "./residual-bandwidth",
+ NB_OP_DESTROY, NULL);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_residual_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ float residual_bandwidth = yang_dnode_get_bandwidth_ieee_float32(dnode,
+ NULL);
+
+ vty_out(vty, " res-bw %g\n", residual_bandwidth);
+}
+
+DEFPY_YANG (link_params_ava_bw,
+ link_params_ava_bw_cmd,
+ "[no] ava-bw ![BANDWIDTH]",
+ NO_STR
+ "Unidirectional Available Bandwidth\n"
+ "Bytes/second (IEEE floating point format)\n")
+{
+ char value[YANG_VALUE_MAXLEN];
+ float bw;
+
+ if (!no) {
+ if (sscanf(bandwidth, "%g", &bw) != 1) {
+ vty_out(vty, "Invalid bandwidth value\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ snprintf(value, sizeof(value), "%a", bw);
+
+ nb_cli_enqueue_change(vty, "./available-bandwidth",
+ NB_OP_MODIFY, value);
+ } else {
+ nb_cli_enqueue_change(vty, "./available-bandwidth",
+ NB_OP_DESTROY, NULL);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_available_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ float available_bandwidth = yang_dnode_get_bandwidth_ieee_float32(dnode,
+ NULL);
+
+ vty_out(vty, " ava-bw %g\n", available_bandwidth);
+}
+
+DEFPY_YANG (link_params_use_bw,
+ link_params_use_bw_cmd,
+ "[no] use-bw ![BANDWIDTH]",
+ NO_STR
+ "Unidirectional Utilised Bandwidth\n"
+ "Bytes/second (IEEE floating point format)\n")
+{
+ char value[YANG_VALUE_MAXLEN];
+ float bw;
+
+ if (!no) {
+ if (sscanf(bandwidth, "%g", &bw) != 1) {
+ vty_out(vty, "Invalid bandwidth value\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ snprintf(value, sizeof(value), "%a", bw);
+
+ nb_cli_enqueue_change(vty, "./utilized-bandwidth", NB_OP_MODIFY,
+ value);
+ } else {
+ nb_cli_enqueue_change(vty, "./utilized-bandwidth",
+ NB_OP_DESTROY, NULL);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_utilized_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ float utilized_bandwidth = yang_dnode_get_bandwidth_ieee_float32(dnode,
+ NULL);
+
+ vty_out(vty, " use-bw %g\n", utilized_bandwidth);
+}
+
+DEFPY_YANG (link_params_affinity,
+ link_params_affinity_cmd,
+ "[no] affinity NAME...",
+ NO_STR
+ "Interface affinities\n"
+ "Affinity names\n")
+{
+ char xpath[XPATH_MAXLEN];
+ int i;
+
+ for (i = no ? 2 : 1; i < argc; i++) {
+ snprintf(xpath, XPATH_MAXLEN, "./affinities/affinity[.='%s']",
+ argv[i]->arg);
+ nb_cli_enqueue_change(vty, xpath,
+ no ? NB_OP_DESTROY : NB_OP_CREATE, NULL);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static int ag_iter_cb(const struct lyd_node *dnode, void *arg)
+{
+ struct vty *vty = arg;
+
+ vty_out(vty, " %s", yang_dnode_get_string(dnode, NULL));
+ return YANG_ITER_CONTINUE;
+}
+
+static void lib_interface_zebra_link_params_affinities_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ vty_out(vty, " affinity");
+ yang_dnode_iterate(ag_iter_cb, vty, dnode, "affinity");
+ vty_out(vty, "\n");
+}
+
+DEFPY_YANG (link_params_affinity_mode,
+ link_params_affinity_mode_cmd,
+ "[no] affinity-mode ![<standard|extended|both>$mode]",
+ NO_STR
+ "Interface affinity mode\n"
+ "Standard Admin-Group only RFC3630,5305,5329\n"
+ "Extended Admin-Group only RFC7308 (default)\n"
+ "Standard and extended Admin-Group format\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./affinity-mode", NB_OP_MODIFY,
+ mode);
+ else
+ nb_cli_enqueue_change(vty, "./affinity-mode", NB_OP_DESTROY,
+ NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_link_params_affinity_mode_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ enum affinity_mode affinity_mode = yang_dnode_get_enum(dnode, NULL);
+
+ if (affinity_mode == AFFINITY_MODE_STANDARD)
+ vty_out(vty, " affinity-mode standard\n");
+ else if (affinity_mode == AFFINITY_MODE_BOTH)
+ vty_out(vty, " affinity-mode both\n");
+ else if (affinity_mode == AFFINITY_MODE_EXTENDED && show_defaults)
+ vty_out(vty, " affinity-mode extended\n");
+}
+
+#ifdef HAVE_NETLINK
+DEFPY_YANG (ip_address,
+ ip_address_cmd,
+ "[no] ip address A.B.C.D/M [label LINE$label]",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Set the IP address of an interface\n"
+ "IP address (e.g. 10.0.0.1/8)\n"
+ "Label of this address\n"
+ "Label\n")
+#else
+DEFPY_YANG (ip_address,
+ ip_address_cmd,
+ "[no] ip address A.B.C.D/M",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Set the IP address of an interface\n"
+ "IP address (e.g. 10.0.0.1/8)\n")
+#endif
+{
+ char ip[INET_ADDRSTRLEN + 3];
+ char *mask;
+
+ if (no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+#ifdef HAVE_NETLINK
+ if (label)
+ nb_cli_enqueue_change(vty, "./label", NB_OP_MODIFY,
+ label);
+ else
+ nb_cli_enqueue_change(vty, "./label", NB_OP_DESTROY,
+ NULL);
+#endif
+ }
+
+ strlcpy(ip, address_str, sizeof(ip));
+
+ mask = strchr(ip, '/');
+ *mask = 0;
+ mask++;
+
+ return nb_cli_apply_changes(vty,
+ "./frr-zebra:zebra/ipv4-addrs[ip='%s'][prefix-length='%s']",
+ ip, mask);
+}
+
+static void lib_interface_zebra_ipv4_addrs_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *ip = yang_dnode_get_string(dnode, "ip");
+ uint8_t prefix_length = yang_dnode_get_uint8(dnode, "prefix-length");
+
+ vty_out(vty, " ip address %s/%u", ip, prefix_length);
+
+ if (yang_dnode_exists(dnode, "label")) {
+ const char *label = yang_dnode_get_string(dnode, "label");
+
+ vty_out(vty, " label %s", label);
+ }
+
+ vty_out(vty, "\n");
+}
+
+#ifdef HAVE_NETLINK
+DEFPY_YANG (ip_address_peer,
+ ip_address_peer_cmd,
+ "[no] ip address A.B.C.D peer A.B.C.D/M [label LINE$label]",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Set the IP address of an interface\n"
+ "Local IP (e.g. 10.0.0.1) for P-t-P address\n"
+ "Specify P-t-P address\n"
+ "Peer IP address (e.g. 10.0.0.1/8)\n"
+ "Label of this address\n"
+ "Label\n")
+#else
+DEFPY_YANG (ip_address_peer,
+ ip_address_peer_cmd,
+ "[no] ip address A.B.C.D peer A.B.C.D/M",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Set the IP address of an interface\n"
+ "Local IP (e.g. 10.0.0.1) for P-t-P address\n"
+ "Specify P-t-P address\n"
+ "Peer IP address (e.g. 10.0.0.1/8)\n")
+#endif
+{
+ char peer_ip[INET_ADDRSTRLEN + 3];
+ char *peer_mask;
+
+ if (no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+#ifdef HAVE_NETLINK
+ if (label)
+ nb_cli_enqueue_change(vty, "./label", NB_OP_MODIFY,
+ label);
+ else
+ nb_cli_enqueue_change(vty, "./label", NB_OP_DESTROY,
+ NULL);
+#endif
+ }
+
+ strlcpy(peer_ip, peer_str, sizeof(peer_ip));
+
+ peer_mask = strchr(peer_ip, '/');
+ *peer_mask = 0;
+ peer_mask++;
+
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/ipv4-p2p-addrs[ip='%s'][peer-ip='%s'][peer-prefix-length='%s']",
+ address_str, peer_ip, peer_mask);
+}
+
+static void lib_interface_zebra_ipv4_p2p_addrs_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *ip = yang_dnode_get_string(dnode, "ip");
+ const char *peer_ip = yang_dnode_get_string(dnode, "peer-ip");
+ uint8_t peer_prefix_length = yang_dnode_get_uint8(dnode,
+ "peer-prefix-length");
+
+ vty_out(vty, " ip address %s peer %s/%u", ip, peer_ip,
+ peer_prefix_length);
+
+ if (yang_dnode_exists(dnode, "label")) {
+ const char *label = yang_dnode_get_string(dnode, "label");
+
+ vty_out(vty, " label %s", label);
+ }
+
+ vty_out(vty, "\n");
+}
+
+DEFPY_YANG (ipv6_address,
+ ipv6_address_cmd,
+ "[no] ipv6 address X:X::X:X/M",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Set the IP address of an interface\n"
+ "IPv6 address (e.g. 3ffe:506::1/48)\n")
+{
+ char ip[INET6_ADDRSTRLEN + 4];
+ char *mask;
+
+ if (no)
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ else
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+
+ strlcpy(ip, address_str, sizeof(ip));
+
+ mask = strchr(ip, '/');
+ *mask = 0;
+ mask++;
+
+ return nb_cli_apply_changes(vty,
+ "./frr-zebra:zebra/ipv6-addrs[ip='%s'][prefix-length='%s']",
+ ip, mask);
+}
+
+static void lib_interface_zebra_ipv6_addrs_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *ip = yang_dnode_get_string(dnode, "ip");
+ uint8_t prefix_length = yang_dnode_get_uint8(dnode, "prefix-length");
+
+ vty_out(vty, " ipv6 address %s/%u\n", ip, prefix_length);
+}
+
+/* CLI for setting an ES in bypass mode */
+DEFPY_YANG_HIDDEN (zebra_evpn_es_bypass,
+ zebra_evpn_es_bypass_cmd,
+ "[no] evpn mh bypass",
+ NO_STR
+ "EVPN\n"
+ EVPN_MH_VTY_STR
+ "Set bypass mode\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/evpn-mh/bypass",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/evpn-mh/bypass",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_evpn_mh_bypass_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool bypass = yang_dnode_get_bool(dnode, NULL);
+
+ if (bypass)
+ vty_out(vty, " evpn mh bypass\n");
+ else if (show_defaults)
+ vty_out(vty, " no evpn mh bypass\n");
+}
+
+/* CLI for configuring DF preference part for an ES */
+DEFPY_YANG (zebra_evpn_es_pref,
+ zebra_evpn_es_pref_cmd,
+ "[no$no] evpn mh es-df-pref ![(1-65535)$df_pref]",
+ NO_STR
+ "EVPN\n"
+ EVPN_MH_VTY_STR
+ "Preference value used for DF election\n"
+ "Preference\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/df-preference",
+ NB_OP_MODIFY, df_pref_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/df-preference",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_evpn_mh_df_preference_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint16_t df_pref = yang_dnode_get_uint16(dnode, NULL);
+
+ vty_out(vty, " evpn mh es-df-pref %u\n", df_pref);
+}
+
+/* CLI for setting up sysmac part of ESI on an access port */
+DEFPY_YANG (zebra_evpn_es_sys_mac,
+ zebra_evpn_es_sys_mac_cmd,
+ "[no$no] evpn mh es-sys-mac ![X:X:X:X:X:X$mac]",
+ NO_STR
+ "EVPN\n"
+ EVPN_MH_VTY_STR
+ "Ethernet segment system MAC\n"
+ MAC_STR)
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/type-3/system-mac",
+ NB_OP_MODIFY, mac_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/type-3/system-mac",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_evpn_mh_type_3_system_mac_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ char buf[ETHER_ADDR_STRLEN];
+ struct ethaddr mac;
+
+ yang_dnode_get_mac(&mac, dnode, NULL);
+
+ vty_out(vty, " evpn mh es-sys-mac %s\n",
+ prefix_mac2str(&mac, buf, sizeof(buf)));
+}
+
+/* CLI for setting up local-ID part of ESI on an access port */
+DEFPY_YANG (zebra_evpn_es_id,
+ zebra_evpn_es_id_cmd,
+ "[no$no] evpn mh es-id ![(1-16777215)$es_lid | NAME$esi_str]",
+ NO_STR
+ "EVPN\n"
+ EVPN_MH_VTY_STR
+ "Ethernet segment identifier\n"
+ "local discriminator\n"
+ "10-byte ID - 00:AA:BB:CC:DD:EE:FF:GG:HH:II\n")
+{
+ if (no) {
+ /* We don't know which one is configured, so detroy both types. */
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/type-0/esi",
+ NB_OP_DESTROY, NULL);
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/type-3/local-discriminator",
+ NB_OP_DESTROY, NULL);
+ } else {
+ if (esi_str)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/type-0/esi",
+ NB_OP_MODIFY, esi_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/evpn-mh/type-3/local-discriminator",
+ NB_OP_MODIFY, es_lid_str);
+ }
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_evpn_mh_type_0_esi_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *esi_str = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " evpn mh es-id %s\n", esi_str);
+}
+
+static void lib_interface_zebra_evpn_mh_type_3_local_discriminator_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t es_lid = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " evpn mh es-id %u\n", es_lid);
+}
+
+/* CLI for tagging an interface as an uplink */
+DEFPY_YANG (zebra_evpn_mh_uplink,
+ zebra_evpn_mh_uplink_cmd,
+ "[no] evpn mh uplink",
+ NO_STR
+ "EVPN\n"
+ EVPN_MH_VTY_STR
+ "Uplink to the VxLAN core\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/evpn-mh/uplink",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/evpn-mh/uplink",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_evpn_mh_uplink_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool uplink = yang_dnode_get_bool(dnode, NULL);
+
+ if (uplink)
+ vty_out(vty, " evpn mh uplink\n");
+ else if (show_defaults)
+ vty_out(vty, " no evpn mh uplink\n");
+}
+
+#if defined(HAVE_RTADV)
+DEFPY_YANG (ipv6_nd_ra_fast_retrans,
+ ipv6_nd_ra_fast_retrans_cmd,
+ "[no] ipv6 nd ra-fast-retrans",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Fast retransmit of RA packets\n")
+{
+ if (no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/fast-retransmit",
+ NB_OP_MODIFY, "false");
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/fast-retransmit",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_fast_retransmit_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool fast_retransmit = yang_dnode_get_bool(dnode, NULL);
+
+ if (!fast_retransmit)
+ vty_out(vty, " no ipv6 nd ra-fast-retrans\n");
+ else if (show_defaults)
+ vty_out(vty, " ipv6 nd ra-fast-retrans\n");
+}
+
+DEFPY_YANG (ipv6_nd_ra_hop_limit,
+ ipv6_nd_ra_hop_limit_cmd,
+ "[no] ipv6 nd ra-hop-limit ![(0-255)$hopcount]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Advertisement Hop Limit\n"
+ "Advertisement Hop Limit in hops (default:64)\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/cur-hop-limit",
+ NB_OP_MODIFY, hopcount_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/cur-hop-limit",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint8_t hop_limit = yang_dnode_get_uint8(dnode, NULL);
+
+ vty_out(vty, " ipv6 nd ra-hop-limit %u\n", hop_limit);
+}
+
+DEFPY_YANG (ipv6_nd_ra_retrans_interval,
+ ipv6_nd_ra_retrans_interval_cmd,
+ "[no] ipv6 nd ra-retrans-interval ![(0-4294967295)$interval]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Advertisement Retransmit Interval\n"
+ "Advertisement Retransmit Interval in msec\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/retrans-timer",
+ NB_OP_MODIFY, interval_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/retrans-timer",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_retrans_timer_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t retrans_timer = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " ipv6 nd ra-retrans-interval %u\n", retrans_timer);
+}
+
+DEFPY_YANG (ipv6_nd_suppress_ra,
+ ipv6_nd_suppress_ra_cmd,
+ "[no] ipv6 nd suppress-ra",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Suppress Router Advertisement\n")
+{
+ if (no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/send-advertisements",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/send-advertisements",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_send_advertisements_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool send_advertisements = yang_dnode_get_bool(dnode, NULL);
+
+ if (send_advertisements)
+ vty_out(vty, " no ipv6 nd suppress-ra\n");
+ else if (show_defaults)
+ vty_out(vty, " ipv6 nd suppress-ra\n");
+}
+
+DEFPY_YANG (ipv6_nd_ra_interval,
+ ipv6_nd_ra_interval_cmd,
+ "[no] ipv6 nd ra-interval ![<(1-1800)$sec|msec (70-1800000)$msec>]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Router Advertisement interval\n"
+ "Router Advertisement interval in seconds\n"
+ "Router Advertisement interval in milliseconds\n"
+ "Router Advertisement interval in milliseconds\n")
+{
+ char value[YANG_VALUE_MAXLEN];
+
+ if (!no) {
+ if (sec)
+ snprintf(value, sizeof(value), "%lu", sec * 1000);
+ else
+ snprintf(value, sizeof(value), "%lu", msec);
+
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/max-rtr-adv-interval",
+ NB_OP_MODIFY, value);
+ } else {
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/max-rtr-adv-interval",
+ NB_OP_DESTROY, NULL);
+ }
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_max_rtr_adv_interval_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t max_rtr_adv_interval = yang_dnode_get_uint32(dnode, NULL);
+
+ if (max_rtr_adv_interval % 1000)
+ vty_out(vty, " ipv6 nd ra-interval msec %u\n",
+ max_rtr_adv_interval);
+ else
+ vty_out(vty, " ipv6 nd ra-interval %u\n",
+ max_rtr_adv_interval / 1000);
+}
+
+DEFPY_YANG (ipv6_nd_ra_lifetime,
+ ipv6_nd_ra_lifetime_cmd,
+ "[no] ipv6 nd ra-lifetime ![(0-9000)$lifetime]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Router lifetime\n"
+ "Router lifetime in seconds (0 stands for a non-default gw)\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/default-lifetime",
+ NB_OP_MODIFY, lifetime_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/default-lifetime",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_default_lifetime_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint16_t default_lifetime = yang_dnode_get_uint16(dnode, NULL);
+
+ vty_out(vty, " ipv6 nd ra-lifetime %u\n", default_lifetime);
+}
+
+DEFPY_YANG (ipv6_nd_reachable_time,
+ ipv6_nd_reachable_time_cmd,
+ "[no] ipv6 nd reachable-time ![(1-3600000)$msec]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Reachable time\n"
+ "Reachable time in milliseconds\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/reachable-time",
+ NB_OP_MODIFY, msec_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/reachable-time",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_reachable_time_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t reachable_time = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " ipv6 nd reachable-time %u\n", reachable_time);
+}
+
+DEFPY_YANG (ipv6_nd_homeagent_preference,
+ ipv6_nd_homeagent_preference_cmd,
+ "[no] ipv6 nd home-agent-preference ![(0-65535)$pref]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Home Agent preference\n"
+ "preference value (default is 0, least preferred)\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/home-agent-preference",
+ NB_OP_MODIFY, pref_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/home-agent-preference",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint16_t home_agent_preference = yang_dnode_get_uint16(dnode, NULL);
+
+ vty_out(vty, " ipv6 nd home-agent-preference %u\n",
+ home_agent_preference);
+}
+
+DEFPY_YANG (ipv6_nd_homeagent_lifetime,
+ ipv6_nd_homeagent_lifetime_cmd,
+ "[no] ipv6 nd home-agent-lifetime ![(1-65520)$lifetime]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Home Agent lifetime\n"
+ "Home Agent lifetime in seconds\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/home-agent-lifetime",
+ NB_OP_MODIFY, lifetime_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/home-agent-lifetime",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint16_t home_agent_lifetime = yang_dnode_get_uint16(dnode, NULL);
+
+ vty_out(vty, " ipv6 nd home-agent-lifetime %u\n", home_agent_lifetime);
+}
+
+DEFPY_YANG (ipv6_nd_managed_config_flag,
+ ipv6_nd_managed_config_flag_cmd,
+ "[no] ipv6 nd managed-config-flag",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Managed address configuration flag\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/managed-flag",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/managed-flag",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_ipv6_router_advertisements_managed_flag_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool managed_flag = yang_dnode_get_bool(dnode, NULL);
+
+ if (managed_flag)
+ vty_out(vty, " ipv6 nd managed-config-flag\n");
+ else if (show_defaults)
+ vty_out(vty, " no ipv6 nd managed-config-flag\n");
+}
+
+DEFPY_YANG (ipv6_nd_homeagent_config_flag,
+ ipv6_nd_homeagent_config_flag_cmd,
+ "[no] ipv6 nd home-agent-config-flag",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Home Agent configuration flag\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/home-agent-flag",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/home-agent-flag",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_home_agent_flag_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool home_agent_flag = yang_dnode_get_bool(dnode, NULL);
+
+ if (home_agent_flag)
+ vty_out(vty, " ipv6 nd home-agent-config-flag\n");
+ else if (show_defaults)
+ vty_out(vty, " no ipv6 nd home-agent-config-flag\n");
+}
+
+DEFPY_YANG (ipv6_nd_adv_interval_config_option,
+ ipv6_nd_adv_interval_config_option_cmd,
+ "[no] ipv6 nd adv-interval-option",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Advertisement Interval Option\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/advertisement-interval-option",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/advertisement-interval-option",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_advertisement_interval_option_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool advertisement_interval_option = yang_dnode_get_bool(dnode, NULL);
+
+ if (advertisement_interval_option)
+ vty_out(vty, " ipv6 nd adv-interval-option\n");
+ else if (show_defaults)
+ vty_out(vty, " no ipv6 nd adv-interval-option\n");
+}
+
+DEFPY_YANG (ipv6_nd_other_config_flag,
+ ipv6_nd_other_config_flag_cmd,
+ "[no] ipv6 nd other-config-flag",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Other statefull configuration flag\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/other-config-flag",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/other-config-flag",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_other_config_flag_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool other_config_flag = yang_dnode_get_bool(dnode, NULL);
+
+ if (other_config_flag)
+ vty_out(vty, " ipv6 nd other-config-flag\n");
+ else if (show_defaults)
+ vty_out(vty, " no ipv6 nd other-config-flag\n");
+}
+
+DEFPY_YANG (ipv6_nd_prefix,
+ ipv6_nd_prefix_cmd,
+ "[no] ipv6 nd prefix X:X::X:X/M$prefix [<(0-4294967295)|infinite>$valid <(0-4294967295)|infinite>$preferred] [{router-address$routeraddr|off-link$offlink|no-autoconfig$noautoconf}]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Prefix information\n"
+ "IPv6 prefix\n"
+ "Valid lifetime in seconds\n"
+ "Infinite valid lifetime\n"
+ "Preferred lifetime in seconds\n"
+ "Infinite preferred lifetime\n"
+ "Set Router Address flag\n"
+ "Do not use prefix for onlink determination\n"
+ "Do not use prefix for autoconfiguration\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+ if (valid) {
+ if (strmatch(valid, "infinite"))
+ valid = "4294967295";
+ nb_cli_enqueue_change(vty, "./valid-lifetime",
+ NB_OP_MODIFY, valid);
+ } else {
+ nb_cli_enqueue_change(vty, "./valid-lifetime",
+ NB_OP_DESTROY, NULL);
+ }
+ if (preferred) {
+ if (strmatch(preferred, "infinite"))
+ preferred = "4294967295";
+ nb_cli_enqueue_change(vty, "./preferred-lifetime",
+ NB_OP_MODIFY, preferred);
+ } else {
+ nb_cli_enqueue_change(vty, "./preferred-lifetime",
+ NB_OP_DESTROY, NULL);
+ }
+ if (routeraddr)
+ nb_cli_enqueue_change(vty, "./router-address-flag",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty, "./router-address-flag",
+ NB_OP_DESTROY, NULL);
+ if (offlink)
+ nb_cli_enqueue_change(vty, "./on-link-flag",
+ NB_OP_MODIFY, "false");
+ else
+ nb_cli_enqueue_change(vty, "./on-link-flag",
+ NB_OP_DESTROY, NULL);
+ if (noautoconf)
+ nb_cli_enqueue_change(vty, "./autonomous-flag",
+ NB_OP_MODIFY, "false");
+ else
+ nb_cli_enqueue_change(vty, "./autonomous-flag",
+ NB_OP_DESTROY, NULL);
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ }
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix[prefix-spec='%s']",
+ prefix_str);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *prefix = yang_dnode_get_string(dnode, "prefix-spec");
+ struct lyd_node *valid = yang_dnode_get(dnode, "valid-lifetime");
+ struct lyd_node *preferred = yang_dnode_get(dnode, "preferred-lifetime");
+ bool router_address_flag = yang_dnode_get_bool(dnode,
+ "router-address-flag");
+ bool on_link_flag = yang_dnode_get_bool(dnode, "on-link-flag");
+ bool autonomous_flag = yang_dnode_get_bool(dnode, "autonomous-flag");
+
+ vty_out(vty, " ipv6 nd prefix %s", prefix);
+
+ if (!yang_dnode_is_default(valid, NULL) ||
+ !yang_dnode_is_default(preferred, NULL) || show_defaults) {
+ uint32_t valid_lifetime = yang_dnode_get_uint32(valid, NULL);
+ uint32_t preferred_lifetime = yang_dnode_get_uint32(preferred,
+ NULL);
+
+ if (valid_lifetime == UINT32_MAX)
+ vty_out(vty, " infinite");
+ else
+ vty_out(vty, " %u", valid_lifetime);
+ if (preferred_lifetime == UINT32_MAX)
+ vty_out(vty, " infinite");
+ else
+ vty_out(vty, " %u", preferred_lifetime);
+ }
+
+ if (!on_link_flag)
+ vty_out(vty, " off-link");
+
+ if (!autonomous_flag)
+ vty_out(vty, " no-autoconfig");
+
+ if (router_address_flag)
+ vty_out(vty, " router-address");
+
+ vty_out(vty, "\n");
+}
+
+DEFPY_YANG (ipv6_nd_router_preference,
+ ipv6_nd_router_preference_cmd,
+ "[no] ipv6 nd router-preference ![<high|medium|low>$pref]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Default router preference\n"
+ "High default router preference\n"
+ "Medium default router preference (default)\n"
+ "Low default router preference\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/default-router-preference",
+ NB_OP_MODIFY, pref);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/default-router-preference",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_default_router_preference_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *default_router_preference = yang_dnode_get_string(dnode,
+ NULL);
+
+ vty_out(vty, " ipv6 nd router-preference %s\n",
+ default_router_preference);
+}
+
+DEFPY_YANG (ipv6_nd_mtu,
+ ipv6_nd_mtu_cmd,
+ "[no] ipv6 nd mtu ![(1-65535)]",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Advertised MTU\n"
+ "MTU in bytes\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/link-mtu",
+ NB_OP_MODIFY, mtu_str);
+ else
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/link-mtu",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_ipv6_router_advertisements_link_mtu_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint16_t link_mtu = yang_dnode_get_uint32(dnode, NULL);
+
+ vty_out(vty, " ipv6 nd mtu %u\n", link_mtu);
+}
+
+DEFPY_YANG (ipv6_nd_rdnss,
+ ipv6_nd_rdnss_cmd,
+ "[no] ipv6 nd rdnss X:X::X:X$addr [<(0-4294967295)|infinite>]$lifetime",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "Recursive DNS server information\n"
+ "IPv6 address\n"
+ "Valid lifetime in seconds\n"
+ "Infinite valid lifetime\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+ if (lifetime) {
+ if (strmatch(lifetime, "infinite"))
+ lifetime = "4294967295";
+ nb_cli_enqueue_change(vty, "./lifetime", NB_OP_MODIFY,
+ lifetime);
+ } else {
+ nb_cli_enqueue_change(vty, "./lifetime", NB_OP_DESTROY,
+ NULL);
+ }
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ }
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/rdnss/rdnss-address[address='%s']",
+ addr_str);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *address = yang_dnode_get_string(dnode, "address");
+
+ vty_out(vty, " ipv6 nd rdnss %s", address);
+
+ if (yang_dnode_exists(dnode, "lifetime")) {
+ uint32_t lifetime = yang_dnode_get_uint32(dnode, "lifetime");
+
+ if (lifetime == UINT32_MAX)
+ vty_out(vty, " infinite");
+ else
+ vty_out(vty, " %u", lifetime);
+ }
+
+ vty_out(vty, "\n");
+}
+
+DEFPY_YANG (ipv6_nd_dnssl,
+ ipv6_nd_dnssl_cmd,
+ "[no] ipv6 nd dnssl SUFFIX [<(0-4294967295)|infinite>]$lifetime",
+ NO_STR
+ "Interface IPv6 config commands\n"
+ "Neighbor discovery\n"
+ "DNS search list information\n"
+ "Domain name suffix\n"
+ "Valid lifetime in seconds\n"
+ "Infinite valid lifetime\n")
+{
+ char domain[254];
+ size_t len;
+
+ len = strlcpy(domain, suffix, sizeof(domain));
+ if (len == 0 || len >= sizeof(domain)) {
+ vty_out(vty, "Malformed DNS search domain\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+ if (domain[len - 1] == '.') {
+ /*
+ * Allow, but don't require, a trailing dot signifying the root
+ * zone. Canonicalize by cutting it off if present.
+ */
+ domain[len - 1] = '\0';
+ len--;
+ }
+
+ if (!no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+ if (lifetime) {
+ if (strmatch(lifetime, "infinite"))
+ lifetime = "4294967295";
+ nb_cli_enqueue_change(vty, "./lifetime", NB_OP_MODIFY,
+ lifetime);
+ } else {
+ nb_cli_enqueue_change(vty, "./lifetime", NB_OP_DESTROY,
+ NULL);
+ }
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ }
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/ipv6-router-advertisements/dnssl/dnssl-domain[domain='%s']",
+ domain);
+}
+
+static void
+lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ const char *domain = yang_dnode_get_string(dnode, "domain");
+
+ vty_out(vty, " ipv6 nd dnssl %s", domain);
+
+ if (yang_dnode_exists(dnode, "lifetime")) {
+ uint32_t lifetime = yang_dnode_get_uint32(dnode, "lifetime");
+
+ if (lifetime == UINT32_MAX)
+ vty_out(vty, " infinite");
+ else
+ vty_out(vty, " %u", lifetime);
+ }
+
+ vty_out(vty, "\n");
+}
+#endif /* HAVE_RTADV */
+
+#if HAVE_BFDD == 0
+DEFPY_YANG (zebra_ptm_enable_if,
+ zebra_ptm_enable_if_cmd,
+ "[no] ptm-enable",
+ NO_STR
+ "Enable neighbor check with specified topology\n")
+{
+ if (no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/ptm-enable",
+ NB_OP_MODIFY, "false");
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/ptm-enable",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_interface_zebra_ptm_enable_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool enable = yang_dnode_get_bool(dnode, NULL);
+
+ if (!enable)
+ vty_out(vty, " no ptm-enable\n");
+ else if (show_defaults)
+ vty_out(vty, " ptm-enable\n");
+}
+#endif /* HAVE_BFDD == 0 */
+
+/*
+ * VRF commands
+ */
+
+static void zebra_vrf_indent_cli_write(struct vty *vty,
+ const struct lyd_node *dnode)
+{
+ const struct lyd_node *vrf = yang_dnode_get_parent(dnode, "vrf");
+
+ if (vrf && strcmp(yang_dnode_get_string(vrf, "name"), VRF_DEFAULT_NAME))
+ vty_out(vty, " ");
+}
+
+DEFPY_YANG (ip_router_id,
+ ip_router_id_cmd,
+ "[no] ip router-id A.B.C.D$id vrf NAME",
+ NO_STR
+ IP_STR
+ "Manually set the router-id\n"
+ "IP address to use for router-id\n"
+ VRF_CMD_HELP_STR)
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/router-id", NB_OP_MODIFY,
+ id_str);
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/router-id", NB_OP_DESTROY,
+ NULL);
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']", vrf);
+}
+
+ALIAS_YANG (ip_router_id,
+ router_id_cmd,
+ "[no] router-id A.B.C.D$id vrf NAME",
+ NO_STR
+ "Manually set the router-id\n"
+ "IP address to use for router-id\n"
+ VRF_CMD_HELP_STR);
+
+DEFPY_YANG (ipv6_router_id,
+ ipv6_router_id_cmd,
+ "[no] ipv6 router-id X:X::X:X$id vrf NAME",
+ NO_STR
+ IPV6_STR
+ "Manually set the router-id\n"
+ "IPv6 address to use for router-id\n"
+ VRF_CMD_HELP_STR)
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/ipv6-router-id",
+ NB_OP_MODIFY, id_str);
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/ipv6-router-id",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']", vrf);
+}
+
+DEFPY_YANG (ip_router_id_in_vrf,
+ ip_router_id_in_vrf_cmd,
+ "[no] ip router-id ![A.B.C.D$id]",
+ NO_STR
+ IP_STR
+ "Manually set the router-id\n"
+ "IP address to use for router-id\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/router-id", NB_OP_MODIFY,
+ id_str);
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/router-id", NB_OP_DESTROY,
+ NULL);
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']",
+ VRF_DEFAULT_NAME);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+ALIAS_YANG (ip_router_id_in_vrf,
+ router_id_in_vrf_cmd,
+ "[no] router-id ![A.B.C.D$id]",
+ NO_STR
+ "Manually set the router-id\n"
+ "IP address to use for router-id\n");
+
+DEFPY_YANG (ipv6_router_id_in_vrf,
+ ipv6_router_id_in_vrf_cmd,
+ "[no] ipv6 router-id ![X:X::X:X$id]",
+ NO_STR
+ IP6_STR
+ "Manually set the IPv6 router-id\n"
+ "IPV6 address to use for router-id\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/ipv6-router-id",
+ NB_OP_MODIFY, id_str);
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/ipv6-router-id",
+ NB_OP_DESTROY, NULL);
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']",
+ VRF_DEFAULT_NAME);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_vrf_zebra_router_id_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *id = yang_dnode_get_string(dnode, NULL);
+
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ vty_out(vty, "ip router-id %s\n", id);
+}
+
+static void lib_vrf_zebra_ipv6_router_id_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *id = yang_dnode_get_string(dnode, NULL);
+
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ vty_out(vty, "ipv6 router-id %s\n", id);
+}
+
+DEFPY_YANG (ip_protocol,
+ ip_protocol_cmd,
+ "[no] ip protocol " FRR_IP_PROTOCOL_MAP_STR_ZEBRA
+ " $proto ![route-map ROUTE-MAP$rmap]",
+ NO_STR
+ IP_STR
+ "Filter routing info exchanged between zebra and protocol\n"
+ FRR_IP_PROTOCOL_MAP_HELP_STR_ZEBRA
+ "Specify route-map\n"
+ "Route map name\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+ nb_cli_enqueue_change(vty, "./route-map", NB_OP_MODIFY, rmap);
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ }
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(
+ vty,
+ "/frr-vrf:lib/vrf[name='%s']/frr-zebra:zebra/filter-protocol[afi-safi='%s'][protocol='%s']",
+ VRF_DEFAULT_NAME,
+ yang_afi_safi_value2identity(AFI_IP, SAFI_UNICAST),
+ proto);
+
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/filter-protocol[afi-safi='%s'][protocol='%s']",
+ yang_afi_safi_value2identity(AFI_IP, SAFI_UNICAST), proto);
+}
+
+DEFPY_YANG (ipv6_protocol,
+ ipv6_protocol_cmd,
+ "[no] ipv6 protocol " FRR_IP6_PROTOCOL_MAP_STR_ZEBRA
+ " $proto ![route-map ROUTE-MAP$rmap]",
+ NO_STR
+ IP6_STR
+ "Filter IPv6 routing info exchanged between zebra and protocol\n"
+ FRR_IP6_PROTOCOL_MAP_HELP_STR_ZEBRA
+ "Specify route-map\n"
+ "Route map name\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+ nb_cli_enqueue_change(vty, "./route-map", NB_OP_MODIFY, rmap);
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ }
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(
+ vty,
+ "/frr-vrf:lib/vrf[name='%s']/frr-zebra:zebra/filter-protocol[afi-safi='%s'][protocol='%s']",
+ VRF_DEFAULT_NAME,
+ yang_afi_safi_value2identity(AFI_IP6, SAFI_UNICAST),
+ proto);
+
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/filter-protocol[afi-safi='%s'][protocol='%s']",
+ yang_afi_safi_value2identity(AFI_IP6, SAFI_UNICAST), proto);
+}
+
+static void lib_vrf_zebra_filter_protocol_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *afi_safi = yang_dnode_get_string(dnode, "afi-safi");
+ const char *proto = yang_dnode_get_string(dnode, "protocol");
+ const char *rmap = yang_dnode_get_string(dnode, "route-map");
+ afi_t afi;
+ safi_t safi;
+
+ yang_afi_safi_identity2value(afi_safi, &afi, &safi);
+
+ if (safi != SAFI_UNICAST)
+ return;
+
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ if (afi == AFI_IP)
+ vty_out(vty, "ip protocol %s route-map %s\n", proto, rmap);
+ else
+ vty_out(vty, "ipv6 protocol %s route-map %s\n", proto, rmap);
+}
+
+DEFPY_YANG (ip_protocol_nht_rmap,
+ ip_protocol_nht_rmap_cmd,
+ "[no] ip nht " FRR_IP_PROTOCOL_MAP_STR_ZEBRA
+ " $proto ![route-map ROUTE-MAP$rmap]",
+ NO_STR
+ IP_STR
+ "Filter Next Hop tracking route resolution\n"
+ FRR_IP_PROTOCOL_MAP_HELP_STR_ZEBRA
+ "Specify route map\n"
+ "Route map name\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+ nb_cli_enqueue_change(vty, "./route-map", NB_OP_MODIFY, rmap);
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ }
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(
+ vty,
+ "/frr-vrf:lib/vrf[name='%s']/frr-zebra:zebra/filter-nht[afi-safi='%s'][protocol='%s']",
+ VRF_DEFAULT_NAME,
+ yang_afi_safi_value2identity(AFI_IP, SAFI_UNICAST),
+ proto);
+
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/filter-nht[afi-safi='%s'][protocol='%s']",
+ yang_afi_safi_value2identity(AFI_IP, SAFI_UNICAST), proto);
+}
+
+DEFPY_YANG (ipv6_protocol_nht_rmap,
+ ipv6_protocol_nht_rmap_cmd,
+ "[no] ipv6 nht " FRR_IP6_PROTOCOL_MAP_STR_ZEBRA
+ " $proto ![route-map ROUTE-MAP$rmap]",
+ NO_STR
+ IP6_STR
+ "Filter Next Hop tracking route resolution\n"
+ FRR_IP6_PROTOCOL_MAP_HELP_STR_ZEBRA
+ "Specify route map\n"
+ "Route map name\n")
+{
+ if (!no) {
+ nb_cli_enqueue_change(vty, ".", NB_OP_CREATE, NULL);
+ nb_cli_enqueue_change(vty, "./route-map", NB_OP_MODIFY, rmap);
+ } else {
+ nb_cli_enqueue_change(vty, ".", NB_OP_DESTROY, NULL);
+ }
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(
+ vty,
+ "/frr-vrf:lib/vrf[name='%s']/frr-zebra:zebra/filter-nht[afi-safi='%s'][protocol='%s']",
+ VRF_DEFAULT_NAME,
+ yang_afi_safi_value2identity(AFI_IP6, SAFI_UNICAST),
+ proto);
+
+ return nb_cli_apply_changes(
+ vty,
+ "./frr-zebra:zebra/filter-nht[afi-safi='%s'][protocol='%s']",
+ yang_afi_safi_value2identity(AFI_IP6, SAFI_UNICAST), proto);
+}
+
+static void lib_vrf_zebra_filter_nht_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *afi_safi = yang_dnode_get_string(dnode, "afi-safi");
+ const char *proto = yang_dnode_get_string(dnode, "protocol");
+ const char *rmap = yang_dnode_get_string(dnode, "route-map");
+ afi_t afi;
+ safi_t safi;
+
+ yang_afi_safi_identity2value(afi_safi, &afi, &safi);
+
+ if (safi != SAFI_UNICAST)
+ return;
+
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ if (afi == AFI_IP)
+ vty_out(vty, "ip nht %s route-map %s\n", proto, rmap);
+ else
+ vty_out(vty, "ipv6 nht %s route-map %s\n", proto, rmap);
+}
+
+DEFPY_YANG (ip_nht_default_route,
+ ip_nht_default_route_cmd,
+ "[no] ip nht resolve-via-default",
+ NO_STR
+ IP_STR
+ "Filter Next Hop tracking route resolution\n"
+ "Resolve via default route\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/resolve-via-default",
+ NB_OP_MODIFY, no ? "false" : "true");
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']",
+ VRF_DEFAULT_NAME);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_vrf_zebra_resolve_via_default_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool resolve_via_default = yang_dnode_get_bool(dnode, NULL);
+
+ if (resolve_via_default != SAVE_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT ||
+ show_defaults) {
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ vty_out(vty, "%sip nht resolve-via-default\n",
+ resolve_via_default ? "" : "no ");
+ }
+}
+
+DEFPY_YANG (ipv6_nht_default_route,
+ ipv6_nht_default_route_cmd,
+ "[no] ipv6 nht resolve-via-default",
+ NO_STR
+ IP6_STR
+ "Filter Next Hop tracking route resolution\n"
+ "Resolve via default route\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/ipv6-resolve-via-default",
+ NB_OP_MODIFY, no ? "false" : "true");
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']",
+ VRF_DEFAULT_NAME);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_vrf_zebra_ipv6_resolve_via_default_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ bool resolve_via_default = yang_dnode_get_bool(dnode, NULL);
+
+ if (resolve_via_default != SAVE_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT ||
+ show_defaults) {
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ vty_out(vty, "%sipv6 nht resolve-via-default\n",
+ resolve_via_default ? "" : "no ");
+ }
+}
+
+DEFPY_YANG (vrf_netns,
+ vrf_netns_cmd,
+ "[no] netns ![NAME$netns_name]",
+ NO_STR
+ "Attach VRF to a Namespace\n"
+ "The file name in " NS_RUN_DIR ", or a full pathname\n")
+{
+ vty_out(vty, "%% This command doesn't do anything.\n");
+ vty_out(vty,
+ "%% VRF is linked to a netns automatically based on its name.\n");
+ return CMD_WARNING;
+}
+
+DEFPY_YANG (ip_table_range, ip_table_range_cmd,
+ "[no] ip table range ![(1-4294967295)$start (1-4294967295)$end]",
+ NO_STR IP_STR
+ "table configuration\n"
+ "Configure table range\n"
+ "Start Routing Table\n"
+ "End Routing Table\n")
+{
+ if (!no) {
+ const struct lyd_node *start_node;
+ const struct lyd_node *end_node;
+
+ if (vty->node == CONFIG_NODE) {
+ start_node =
+ yang_dnode_getf(vty->candidate_config->dnode,
+ "/frr-vrf:lib/vrf[name='%s']/frr-zebra:zebra/netns/table-range/start",
+ VRF_DEFAULT_NAME);
+ end_node =
+ yang_dnode_getf(vty->candidate_config->dnode,
+ "/frr-vrf:lib/vrf[name='%s']/frr-zebra:zebra/netns/table-range/end",
+ VRF_DEFAULT_NAME);
+ } else {
+ start_node =
+ yang_dnode_getf(vty->candidate_config->dnode,
+ "%s/frr-zebra:zebra/netns/table-range/start",
+ VTY_CURR_XPATH);
+ end_node =
+ yang_dnode_getf(vty->candidate_config->dnode,
+ "%s/frr-zebra:zebra/netns/table-range/end",
+ VTY_CURR_XPATH);
+ }
+
+ if (start_node && end_node) {
+ if (yang_dnode_get_uint32(start_node, NULL) !=
+ (uint32_t)start ||
+ yang_dnode_get_uint32(end_node, NULL) !=
+ (uint32_t)end) {
+ vty_out(vty,
+ "%% New range will be taken into account at restart.\n");
+ vty_out(vty,
+ "%% Don't forget to save your configuration.\n");
+ }
+ }
+
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/netns/table-range",
+ NB_OP_CREATE, NULL);
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/netns/table-range/start",
+ NB_OP_MODIFY, start_str);
+ nb_cli_enqueue_change(vty,
+ "./frr-zebra:zebra/netns/table-range/end",
+ NB_OP_MODIFY, end_str);
+ } else {
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/netns/table-range",
+ NB_OP_DESTROY, NULL);
+ }
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']",
+ VRF_DEFAULT_NAME);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_vrf_zebra_netns_table_range_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults)
+{
+ uint32_t start = yang_dnode_get_uint32(dnode, "start");
+ uint32_t end = yang_dnode_get_uint32(dnode, "end");
+
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ vty_out(vty, "ip table range %u %u\n", start, end);
+}
+
+DEFPY_YANG (vni_mapping,
+ vni_mapping_cmd,
+ "[no] vni ![" CMD_VNI_RANGE "[prefix-routes-only$filter]]",
+ NO_STR
+ "VNI corresponding to tenant VRF\n"
+ "VNI-ID\n"
+ "prefix-routes-only\n")
+{
+ if (!no)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/l3vni-id", NB_OP_MODIFY,
+ vni_str);
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/l3vni-id", NB_OP_DESTROY,
+ NULL);
+
+ if (filter)
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/prefix-only",
+ NB_OP_MODIFY, "true");
+ else
+ nb_cli_enqueue_change(vty, "./frr-zebra:zebra/prefix-only",
+ NB_OP_DESTROY, NULL);
+
+ if (vty->node == CONFIG_NODE)
+ return nb_cli_apply_changes(vty, "/frr-vrf:lib/vrf[name='%s']",
+ VRF_DEFAULT_NAME);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+static void lib_vrf_zebra_l3vni_id_cli_write(struct vty *vty,
+ const struct lyd_node *dnode,
+ bool show_defaults)
+{
+ vni_t vni = yang_dnode_get_uint32(dnode, NULL);
+ bool prefix_only = yang_dnode_get_bool(dnode, "../prefix-only");
+
+ zebra_vrf_indent_cli_write(vty, dnode);
+
+ vty_out(vty, "vni %u", vni);
+
+ if (prefix_only)
+ vty_out(vty, " prefix-routes-only");
+
+ vty_out(vty, "\n");
+}
+
+DEFPY_YANG(
+ match_ip_address_prefix_len, match_ip_address_prefix_len_cmd,
+ "match ip address prefix-len (0-32)$length",
+ MATCH_STR
+ IP_STR
+ "Match prefix length of IP address\n"
+ "Match prefix length of IP address\n"
+ "Prefix length\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:ipv4-prefix-length']";
+ char xpath_value[XPATH_MAXLEN];
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ snprintf(
+ xpath_value, sizeof(xpath_value),
+ "%s/rmap-match-condition/frr-zebra-route-map:ipv4-prefix-length",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, length_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ no_match_ip_address_prefix_len, no_match_ip_address_prefix_len_cmd,
+ "no match ip address prefix-len [(0-32)]",
+ NO_STR
+ MATCH_STR
+ IP_STR
+ "Match prefix length of IP address\n"
+ "Match prefix length of IP address\n"
+ "Prefix length\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:ipv4-prefix-length']";
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ match_ipv6_address_prefix_len, match_ipv6_address_prefix_len_cmd,
+ "match ipv6 address prefix-len (0-128)$length",
+ MATCH_STR
+ IPV6_STR
+ "Match prefix length of IPv6 address\n"
+ "Match prefix length of IPv6 address\n"
+ "Prefix length\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:ipv6-prefix-length']";
+ char xpath_value[XPATH_MAXLEN];
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ snprintf(
+ xpath_value, sizeof(xpath_value),
+ "%s/rmap-match-condition/frr-zebra-route-map:ipv6-prefix-length",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, length_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ no_match_ipv6_address_prefix_len, no_match_ipv6_address_prefix_len_cmd,
+ "no match ipv6 address prefix-len [(0-128)]",
+ NO_STR
+ MATCH_STR
+ IPV6_STR
+ "Match prefix length of IPv6 address\n"
+ "Match prefix length of IPv6 address\n"
+ "Prefix length\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:ipv6-prefix-length']";
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ match_ip_nexthop_prefix_len, match_ip_nexthop_prefix_len_cmd,
+ "match ip next-hop prefix-len (0-32)$length",
+ MATCH_STR
+ IP_STR
+ "Match prefixlen of nexthop IP address\n"
+ "Match prefixlen of given nexthop\n"
+ "Prefix length\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:ipv4-next-hop-prefix-length']";
+ char xpath_value[XPATH_MAXLEN];
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ snprintf(
+ xpath_value, sizeof(xpath_value),
+ "%s/rmap-match-condition/frr-zebra-route-map:ipv4-prefix-length",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, length_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ no_match_ip_nexthop_prefix_len, no_match_ip_nexthop_prefix_len_cmd,
+ "no match ip next-hop prefix-len [(0-32)]",
+ NO_STR
+ MATCH_STR
+ IP_STR
+ "Match prefixlen of nexthop IP address\n"
+ "Match prefix length of nexthop\n"
+ "Prefix length\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:ipv4-next-hop-prefix-length']";
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ match_source_protocol, match_source_protocol_cmd,
+ "match source-protocol " FRR_REDIST_STR_ZEBRA "$proto",
+ MATCH_STR
+ "Match protocol via which the route was learnt\n"
+ FRR_REDIST_HELP_STR_ZEBRA)
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:source-protocol']";
+ char xpath_value[XPATH_MAXLEN];
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ snprintf(xpath_value, sizeof(xpath_value),
+ "%s/rmap-match-condition/frr-zebra-route-map:source-protocol",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, proto);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ no_match_source_protocol, no_match_source_protocol_cmd,
+ "no match source-protocol [" FRR_REDIST_STR_ZEBRA "]",
+ NO_STR
+ MATCH_STR
+ "Match protocol via which the route was learnt\n"
+ FRR_REDIST_HELP_STR_ZEBRA)
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:source-protocol']";
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ match_source_instance, match_source_instance_cmd,
+ "match source-instance (0-255)$instance",
+ MATCH_STR
+ "Match the protocol's instance number\n"
+ "The instance number\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:source-instance']";
+ char xpath_value[XPATH_MAXLEN];
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ snprintf(xpath_value, sizeof(xpath_value),
+ "%s/rmap-match-condition/frr-zebra-route-map:source-instance",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, instance_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ no_match_source_instance, no_match_source_instance_cmd,
+ "no match source-instance [(0-255)]",
+ NO_STR MATCH_STR
+ "Match the protocol's instance number\n"
+ "The instance number\n")
+{
+ const char *xpath =
+ "./match-condition[condition='frr-zebra-route-map:source-instance']";
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+/* set functions */
+
+DEFPY_YANG(
+ set_src, set_src_cmd,
+ "set src <A.B.C.D$addrv4|X:X::X:X$addrv6>",
+ SET_STR
+ "src address for route\n"
+ "IPv4 src address\n"
+ "IPv6 src address\n")
+{
+ const char *xpath =
+ "./set-action[action='frr-zebra-route-map:src-address']";
+ char xpath_value[XPATH_MAXLEN];
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ if (addrv4_str) {
+ snprintf(
+ xpath_value, sizeof(xpath_value),
+ "%s/rmap-set-action/frr-zebra-route-map:ipv4-src-address",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY,
+ addrv4_str);
+ } else {
+ snprintf(
+ xpath_value, sizeof(xpath_value),
+ "%s/rmap-set-action/frr-zebra-route-map:ipv6-src-address",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY,
+ addrv6_str);
+ }
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY_YANG(
+ no_set_src, no_set_src_cmd,
+ "no set src [<A.B.C.D|X:X::X:X>]",
+ NO_STR
+ SET_STR
+ "Source address for route\n"
+ "IPv4 address\n"
+ "IPv6 address\n")
+{
+ const char *xpath =
+ "./set-action[action='frr-zebra-route-map:src-address']";
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+const char *features[] = {
+#if HAVE_BFDD == 0
+ "ptm-bfd",
+#endif
+#if defined(HAVE_RTADV)
+ "ipv6-router-advertisements",
+#endif
+ NULL
+};
+
+/* clang-format off */
+const struct frr_yang_module_info frr_zebra_cli_info = {
+ .name = "frr-zebra",
+ .ignore_cfg_cbs = true,
+ .features = features,
+ .nodes = {
+#if HAVE_BFDD == 0
+ {
+ .xpath = "/frr-zebra:zebra/ptm-enable",
+ .cbs.cli_show = zebra_ptm_enable_cli_write,
+ },
+#endif
+ {
+ .xpath = "/frr-zebra:zebra/route-map-delay",
+ .cbs.cli_show = zebra_route_map_delay_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv4-addrs",
+ .cbs.cli_show = lib_interface_zebra_ipv4_addrs_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv4-p2p-addrs",
+ .cbs.cli_show = lib_interface_zebra_ipv4_p2p_addrs_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-addrs",
+ .cbs.cli_show = lib_interface_zebra_ipv6_addrs_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/multicast",
+ .cbs.cli_show = lib_interface_zebra_multicast_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-detect",
+ .cbs.cli_show = lib_interface_zebra_link_detect_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/enabled",
+ .cbs.cli_show = lib_interface_zebra_enabled_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/bandwidth",
+ .cbs.cli_show = lib_interface_zebra_bandwidth_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/mpls",
+ .cbs.cli_show = lib_interface_zebra_mpls_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params",
+ .cbs.cli_show = lib_interface_zebra_link_params_cli_write,
+ .cbs.cli_show_end = lib_interface_zebra_link_params_cli_write_end,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/metric",
+ .cbs.cli_show = lib_interface_zebra_link_params_metric_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/max-bandwidth",
+ .cbs.cli_show = lib_interface_zebra_link_params_max_bandwidth_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/max-reservable-bandwidth",
+ .cbs.cli_show = lib_interface_zebra_link_params_max_reservable_bandwidth_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/unreserved-bandwidths/unreserved-bandwidth",
+ .cbs.cli_show = lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/residual-bandwidth",
+ .cbs.cli_show = lib_interface_zebra_link_params_residual_bandwidth_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/available-bandwidth",
+ .cbs.cli_show = lib_interface_zebra_link_params_available_bandwidth_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/utilized-bandwidth",
+ .cbs.cli_show = lib_interface_zebra_link_params_utilized_bandwidth_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/legacy-admin-group",
+ .cbs.cli_show = lib_interface_zebra_link_params_legacy_admin_group_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/affinities",
+ .cbs.cli_show = lib_interface_zebra_link_params_affinities_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/affinity-mode",
+ .cbs.cli_show = lib_interface_zebra_link_params_affinity_mode_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/neighbor",
+ .cbs.cli_show = lib_interface_zebra_link_params_neighbor_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/delay",
+ .cbs.cli_show = lib_interface_zebra_link_params_delay_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/delay-variation",
+ .cbs.cli_show = lib_interface_zebra_link_params_delay_variation_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/packet-loss",
+ .cbs.cli_show = lib_interface_zebra_link_params_packet_loss_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-0/esi",
+ .cbs.cli_show = lib_interface_zebra_evpn_mh_type_0_esi_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-3/system-mac",
+ .cbs.cli_show = lib_interface_zebra_evpn_mh_type_3_system_mac_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-3/local-discriminator",
+ .cbs.cli_show = lib_interface_zebra_evpn_mh_type_3_local_discriminator_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/df-preference",
+ .cbs.cli_show = lib_interface_zebra_evpn_mh_df_preference_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/bypass",
+ .cbs.cli_show = lib_interface_zebra_evpn_mh_bypass_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/uplink",
+ .cbs.cli_show = lib_interface_zebra_evpn_mh_uplink_cli_write,
+ },
+#if defined(HAVE_RTADV)
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/send-advertisements",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_send_advertisements_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/max-rtr-adv-interval",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_max_rtr_adv_interval_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/managed-flag",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_managed_flag_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/other-config-flag",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_other_config_flag_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-flag",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_home_agent_flag_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/link-mtu",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_link_mtu_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/reachable-time",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_reachable_time_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/retrans-timer",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_retrans_timer_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/cur-hop-limit",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/default-lifetime",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_default_lifetime_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/fast-retransmit",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_fast_retransmit_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/advertisement-interval-option",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_advertisement_interval_option_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-preference",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-lifetime",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/default-router-preference",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_default_router_preference_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/dnssl/dnssl-domain",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_cli_write,
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/rdnss/rdnss-address",
+ .cbs.cli_show = lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_cli_write,
+ },
+#endif /* defined(HAVE_RTADV) */
+#if HAVE_BFDD == 0
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ptm-enable",
+ .cbs.cli_show = lib_interface_zebra_ptm_enable_cli_write,
+ },
+#endif
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/router-id",
+ .cbs.cli_show = lib_vrf_zebra_router_id_cli_write,
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/ipv6-router-id",
+ .cbs.cli_show = lib_vrf_zebra_ipv6_router_id_cli_write,
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/filter-protocol",
+ .cbs.cli_show = lib_vrf_zebra_filter_protocol_cli_write,
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/filter-nht",
+ .cbs.cli_show = lib_vrf_zebra_filter_nht_cli_write,
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/resolve-via-default",
+ .cbs.cli_show = lib_vrf_zebra_resolve_via_default_cli_write,
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/ipv6-resolve-via-default",
+ .cbs.cli_show = lib_vrf_zebra_ipv6_resolve_via_default_cli_write,
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/netns/table-range",
+ .cbs.cli_show = lib_vrf_zebra_netns_table_range_cli_write,
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/l3vni-id",
+ .cbs.cli_show = lib_vrf_zebra_l3vni_id_cli_write,
+ },
+ {
+ .xpath = NULL,
+ },
+ }
+};
+
+struct cmd_node link_params_node = {
+ .name = "link-params",
+ .node = LINK_PARAMS_NODE,
+ .parent_node = INTERFACE_NODE,
+ .prompt = "%s(config-link-params)# ",
+};
+
+void zebra_cli_init(void)
+{
+ install_node(&link_params_node);
+
+ install_element(INTERFACE_NODE, &multicast_new_cmd);
+ install_element(INTERFACE_NODE, &multicast_cmd);
+ install_element(INTERFACE_NODE, &mpls_cmd);
+ install_element(INTERFACE_NODE, &linkdetect_cmd);
+ install_element(INTERFACE_NODE, &shutdown_if_cmd);
+ install_element(INTERFACE_NODE, &bandwidth_if_cmd);
+ install_element(INTERFACE_NODE, &ip_address_cmd);
+ install_element(INTERFACE_NODE, &ip_address_peer_cmd);
+ install_element(INTERFACE_NODE, &ipv6_address_cmd);
+ install_element(INTERFACE_NODE, &link_params_cmd);
+ install_element(INTERFACE_NODE, &no_link_params_cmd);
+ install_default(LINK_PARAMS_NODE);
+ install_element(LINK_PARAMS_NODE, &link_params_enable_cmd);
+ install_element(LINK_PARAMS_NODE, &no_link_params_enable_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_metric_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_maxbw_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_max_rsv_bw_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_unrsv_bw_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_admin_grp_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_inter_as_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_delay_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_delay_var_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_pkt_loss_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_ava_bw_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_res_bw_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_use_bw_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_affinity_cmd);
+ install_element(LINK_PARAMS_NODE, &link_params_affinity_mode_cmd);
+ install_element(LINK_PARAMS_NODE, &exit_link_params_cmd);
+
+ install_element(INTERFACE_NODE, &zebra_evpn_es_id_cmd);
+ install_element(INTERFACE_NODE, &zebra_evpn_es_sys_mac_cmd);
+ install_element(INTERFACE_NODE, &zebra_evpn_es_pref_cmd);
+ install_element(INTERFACE_NODE, &zebra_evpn_es_bypass_cmd);
+ install_element(INTERFACE_NODE, &zebra_evpn_mh_uplink_cmd);
+
+#if defined(HAVE_RTADV)
+ install_element(INTERFACE_NODE, &ipv6_nd_ra_fast_retrans_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_ra_retrans_interval_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_ra_hop_limit_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_suppress_ra_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_ra_interval_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_ra_lifetime_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_reachable_time_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_managed_config_flag_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_other_config_flag_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_homeagent_config_flag_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_homeagent_preference_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_homeagent_lifetime_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_adv_interval_config_option_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_prefix_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_router_preference_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_mtu_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_rdnss_cmd);
+ install_element(INTERFACE_NODE, &ipv6_nd_dnssl_cmd);
+#endif
+#if HAVE_BFDD == 0
+ install_element(INTERFACE_NODE, &zebra_ptm_enable_if_cmd);
+#endif
+
+ install_element(CONFIG_NODE, &ip_router_id_cmd);
+ install_element(CONFIG_NODE, &router_id_cmd);
+ install_element(CONFIG_NODE, &ipv6_router_id_cmd);
+ install_element(CONFIG_NODE, &ip_router_id_in_vrf_cmd);
+ install_element(CONFIG_NODE, &router_id_in_vrf_cmd);
+ install_element(CONFIG_NODE, &ipv6_router_id_in_vrf_cmd);
+ install_element(VRF_NODE, &ip_router_id_in_vrf_cmd);
+ install_element(VRF_NODE, &router_id_in_vrf_cmd);
+ install_element(VRF_NODE, &ipv6_router_id_in_vrf_cmd);
+
+ install_element(CONFIG_NODE, &ip_protocol_cmd);
+ install_element(VRF_NODE, &ip_protocol_cmd);
+ install_element(CONFIG_NODE, &ipv6_protocol_cmd);
+ install_element(VRF_NODE, &ipv6_protocol_cmd);
+ install_element(CONFIG_NODE, &ip_protocol_nht_rmap_cmd);
+ install_element(VRF_NODE, &ip_protocol_nht_rmap_cmd);
+ install_element(CONFIG_NODE, &ipv6_protocol_nht_rmap_cmd);
+ install_element(VRF_NODE, &ipv6_protocol_nht_rmap_cmd);
+ install_element(CONFIG_NODE, &zebra_route_map_timer_cmd);
+
+ install_element(CONFIG_NODE, &ip_nht_default_route_cmd);
+ install_element(CONFIG_NODE, &ipv6_nht_default_route_cmd);
+ install_element(VRF_NODE, &ip_nht_default_route_cmd);
+ install_element(VRF_NODE, &ipv6_nht_default_route_cmd);
+
+ install_element(CONFIG_NODE, &vni_mapping_cmd);
+ install_element(VRF_NODE, &vni_mapping_cmd);
+
+ if (vrf_is_backend_netns())
+ install_element(VRF_NODE, &vrf_netns_cmd);
+
+ install_element(CONFIG_NODE, &ip_table_range_cmd);
+ install_element(VRF_NODE, &ip_table_range_cmd);
+#if HAVE_BFDD == 0
+ install_element(CONFIG_NODE, &zebra_ptm_enable_cmd);
+#endif
+ install_element(RMAP_NODE, &match_ip_nexthop_prefix_len_cmd);
+ install_element(RMAP_NODE, &no_match_ip_nexthop_prefix_len_cmd);
+ install_element(RMAP_NODE, &match_ip_address_prefix_len_cmd);
+ install_element(RMAP_NODE, &match_ipv6_address_prefix_len_cmd);
+ install_element(RMAP_NODE, &no_match_ipv6_address_prefix_len_cmd);
+ install_element(RMAP_NODE, &no_match_ip_address_prefix_len_cmd);
+ install_element(RMAP_NODE, &match_source_protocol_cmd);
+ install_element(RMAP_NODE, &no_match_source_protocol_cmd);
+ install_element(RMAP_NODE, &match_source_instance_cmd);
+ install_element(RMAP_NODE, &no_match_source_instance_cmd);
+
+ install_element(RMAP_NODE, &set_src_cmd);
+ install_element(RMAP_NODE, &no_set_src_cmd);
+}
diff --git a/zebra/zebra_cli.h b/zebra/zebra_cli.h
new file mode 100644
index 0000000000..01931a47ab
--- /dev/null
+++ b/zebra/zebra_cli.h
@@ -0,0 +1,10 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+
+#ifndef _ZEBRA_CLI_H
+#define _ZEBRA_CLI_H 1
+
+extern const struct frr_yang_module_info frr_zebra_cli_info;
+
+void zebra_cli_init(void);
+
+#endif
diff --git a/zebra/zebra_evpn_mh.c b/zebra/zebra_evpn_mh.c
index a5092c629a..35d5027fb8 100644
--- a/zebra/zebra_evpn_mh.c
+++ b/zebra/zebra_evpn_mh.c
@@ -52,10 +52,9 @@ static void zebra_evpn_es_get_one_base_evpn(void);
static int zebra_evpn_es_evi_send_to_client(struct zebra_evpn_es *es,
struct zebra_evpn *zevpn, bool add);
static void zebra_evpn_local_es_del(struct zebra_evpn_es **esp);
-static int zebra_evpn_local_es_update(struct zebra_if *zif, esi_t *esi);
+static void zebra_evpn_local_es_update(struct zebra_if *zif);
static bool zebra_evpn_es_br_port_dplane_update(struct zebra_evpn_es *es,
const char *caller);
-static void zebra_evpn_mh_uplink_cfg_update(struct zebra_if *zif, bool set);
static void zebra_evpn_mh_update_protodown_es(struct zebra_evpn_es *es,
bool resync_dplane);
static void zebra_evpn_mh_clear_protodown_es(struct zebra_evpn_es *es);
@@ -1139,7 +1138,7 @@ void zebra_evpn_if_init(struct zebra_if *zif)
/* if an es_id and sysmac are already present against the interface
* activate it
*/
- zebra_evpn_local_es_update(zif, &zif->es_info.esi);
+ zebra_evpn_local_es_update(zif);
}
/* handle deletion of an access port by removing it from all associated
@@ -2250,8 +2249,7 @@ static void zebra_evpn_es_local_info_set(struct zebra_evpn_es *es,
/* attach es to interface */
zif->es_info.es = es;
- es->df_pref = zif->es_info.df_pref ? zif->es_info.df_pref
- : EVPN_MH_DF_PREF_DEFAULT;
+ es->df_pref = zif->es_info.df_pref;
/* attach interface to es */
es->zif = zif;
@@ -2402,73 +2400,63 @@ static void zebra_evpn_es_remote_info_re_eval(struct zebra_evpn_es **esp)
}
}
+void zebra_build_type3_esi(uint32_t lid, struct ethaddr *mac, esi_t *esi)
+{
+ int offset = 0;
+ int field_bytes = 0;
+
+ /* build 10-byte type-3-ESI -
+ * Type(1-byte), MAC(6-bytes), ES-LID (3-bytes)
+ */
+ field_bytes = 1;
+ esi->val[offset] = ESI_TYPE_MAC;
+ offset += field_bytes;
+
+ field_bytes = ETH_ALEN;
+ memcpy(&esi->val[offset], (uint8_t *)mac, field_bytes);
+ offset += field_bytes;
+
+ esi->val[offset++] = (uint8_t)(lid >> 16);
+ esi->val[offset++] = (uint8_t)(lid >> 8);
+ esi->val[offset++] = (uint8_t)lid;
+}
+
/* A new local es is created when a local-es-id and sysmac is configured
* against an interface.
*/
-static int zebra_evpn_local_es_update(struct zebra_if *zif, esi_t *esi)
+static void zebra_evpn_local_es_update(struct zebra_if *zif)
{
struct zebra_evpn_es *old_es = zif->es_info.es;
struct zebra_evpn_es *es;
+ esi_t _esi, *esi;
+
+ if (!zebra_evpn_is_if_es_capable(zif))
+ return;
+
+ if (memcmp(&zif->es_info.esi, zero_esi, sizeof(*zero_esi))) {
+ esi = &zif->es_info.esi;
+ } else if (zif->es_info.lid && !is_zero_mac(&zif->es_info.sysmac)) {
+ zebra_build_type3_esi(zif->es_info.lid, &zif->es_info.sysmac,
+ &_esi);
+ esi = &_esi;
+ } else {
+ esi = zero_esi;
+ }
if (old_es && !memcmp(&old_es->esi, esi, sizeof(*esi)))
/* dup - nothing to be done */
- return 0;
+ return;
/* release the old_es against the zif */
if (old_es)
zebra_evpn_local_es_del(&old_es);
es = zebra_evpn_es_find(esi);
- if (es) {
- /* if it exists against another interface flag an error */
- if (es->zif && es->zif != zif)
- return -1;
- } else {
- /* create new es */
+ if (!es)
es = zebra_evpn_es_new(esi);
- }
- memcpy(&zif->es_info.esi, esi, sizeof(*esi));
if (es)
zebra_evpn_es_local_info_set(es, zif);
-
- return 0;
-}
-
-static int zebra_evpn_type3_esi_update(struct zebra_if *zif, uint32_t lid,
- struct ethaddr *sysmac)
-{
- struct zebra_evpn_es *old_es = zif->es_info.es;
- esi_t esi;
- int offset = 0;
- int field_bytes = 0;
-
- /* Complete config of the ES-ID bootstraps the ES */
- if (!lid || is_zero_mac(sysmac)) {
- /* clear old esi */
- memset(&zif->es_info.esi, 0, sizeof(zif->es_info.esi));
- /* if in ES is attached to zif delete it */
- if (old_es)
- zebra_evpn_local_es_del(&old_es);
- return 0;
- }
-
- /* build 10-byte type-3-ESI -
- * Type(1-byte), MAC(6-bytes), ES-LID (3-bytes)
- */
- field_bytes = 1;
- esi.val[offset] = ESI_TYPE_MAC;
- offset += field_bytes;
-
- field_bytes = ETH_ALEN;
- memcpy(&esi.val[offset], (uint8_t *)sysmac, field_bytes);
- offset += field_bytes;
-
- esi.val[offset++] = (uint8_t)(lid >> 16);
- esi.val[offset++] = (uint8_t)(lid >> 8);
- esi.val[offset++] = (uint8_t)lid;
-
- return zebra_evpn_local_es_update(zif, &esi);
}
int zebra_evpn_remote_es_del(const esi_t *esi, struct in_addr vtep_ip)
@@ -2673,44 +2661,33 @@ static int zebra_evpn_es_evi_send_to_client(struct zebra_evpn_es *es,
}
/* sysmac part of a local ESI has changed */
-static int zebra_evpn_es_sys_mac_update(struct zebra_if *zif,
- struct ethaddr *sysmac)
+void zebra_evpn_es_sys_mac_update(struct zebra_if *zif, struct ethaddr *sysmac)
{
- int rv;
-
- rv = zebra_evpn_type3_esi_update(zif, zif->es_info.lid, sysmac);
- if (!rv)
+ if (sysmac)
memcpy(&zif->es_info.sysmac, sysmac, sizeof(struct ethaddr));
+ else
+ memset(&zif->es_info.sysmac, 0, sizeof(struct ethaddr));
- return rv;
+ zebra_evpn_local_es_update(zif);
}
/* local-ID part of ESI has changed */
-static int zebra_evpn_es_lid_update(struct zebra_if *zif, uint32_t lid)
+void zebra_evpn_es_lid_update(struct zebra_if *zif, uint32_t lid)
{
- int rv;
-
- rv = zebra_evpn_type3_esi_update(zif, lid, &zif->es_info.sysmac);
- if (!rv)
- zif->es_info.lid = lid;
+ zif->es_info.lid = lid;
- return rv;
+ zebra_evpn_local_es_update(zif);
}
/* type-0 esi has changed */
-static int zebra_evpn_es_type0_esi_update(struct zebra_if *zif, esi_t *esi)
+void zebra_evpn_es_type0_esi_update(struct zebra_if *zif, esi_t *esi)
{
- int rv;
-
- rv = zebra_evpn_local_es_update(zif, esi);
-
- /* clear the old es_lid, es_sysmac - type-0 is being set so old
- * type-3 params need to be flushed
- */
- memset(&zif->es_info.sysmac, 0, sizeof(struct ethaddr));
- zif->es_info.lid = 0;
+ if (esi)
+ memcpy(&zif->es_info.esi, esi, sizeof(*esi));
+ else
+ memset(&zif->es_info.esi, 0, sizeof(*esi));
- return rv;
+ zebra_evpn_local_es_update(zif);
}
void zebra_evpn_es_cleanup(void)
@@ -2726,10 +2703,9 @@ void zebra_evpn_es_cleanup(void)
}
}
-static void zebra_evpn_es_df_pref_update(struct zebra_if *zif, uint16_t df_pref)
+void zebra_evpn_es_df_pref_update(struct zebra_if *zif, uint16_t df_pref)
{
struct zebra_evpn_es *es;
- uint16_t tmp_pref;
if (zif->es_info.df_pref == df_pref)
return;
@@ -2740,13 +2716,10 @@ static void zebra_evpn_es_df_pref_update(struct zebra_if *zif, uint16_t df_pref)
if (!es)
return;
- tmp_pref = zif->es_info.df_pref ? zif->es_info.df_pref
- : EVPN_MH_DF_PREF_DEFAULT;
-
- if (es->df_pref == tmp_pref)
+ if (es->df_pref == zif->es_info.df_pref)
return;
- es->df_pref = tmp_pref;
+ es->df_pref = zif->es_info.df_pref;
/* run df election */
zebra_evpn_es_run_df_election(es, __func__);
/* notify bgp */
@@ -2833,7 +2806,7 @@ void zebra_evpn_es_bypass_update(struct zebra_evpn_es *es,
zebra_evpn_es_br_port_dplane_update(es, __func__);
}
-static void zebra_evpn_es_bypass_cfg_update(struct zebra_if *zif, bool bypass)
+void zebra_evpn_es_bypass_cfg_update(struct zebra_if *zif, bool bypass)
{
bool old_bypass = !!(zif->es_info.flags & ZIF_CFG_ES_FLAG_BYPASS);
@@ -3326,208 +3299,9 @@ void zebra_evpn_es_show_esi(struct vty *vty, bool uj, esi_t *esi)
vty_json(vty, json);
}
-int zebra_evpn_mh_if_write(struct vty *vty, struct interface *ifp)
+void zebra_evpn_mh_if_init(struct zebra_if *zif)
{
- struct zebra_if *zif = ifp->info;
- char buf[ETHER_ADDR_STRLEN];
- bool type_3_esi = false;
- char esi_buf[ESI_STR_LEN];
-
- if (zif->es_info.lid) {
- vty_out(vty, " evpn mh es-id %u\n", zif->es_info.lid);
- type_3_esi = true;
- }
-
- if (!is_zero_mac(&zif->es_info.sysmac)) {
- vty_out(vty, " evpn mh es-sys-mac %s\n",
- prefix_mac2str(&zif->es_info.sysmac,
- buf, sizeof(buf)));
- type_3_esi = true;
- }
-
- if (!type_3_esi
- && memcmp(&zif->es_info.esi, zero_esi, sizeof(*zero_esi)))
- vty_out(vty, " evpn mh es-id %s\n",
- esi_to_str(&zif->es_info.esi, esi_buf, sizeof(esi_buf)));
-
- if (zif->es_info.df_pref)
- vty_out(vty, " evpn mh es-df-pref %u\n", zif->es_info.df_pref);
-
- if (zif->flags & ZIF_FLAG_EVPN_MH_UPLINK)
- vty_out(vty, " evpn mh uplink\n");
-
- return 0;
-}
-
-#include "zebra/zebra_evpn_mh_clippy.c"
-/* CLI for setting an ES in bypass mode */
-DEFPY_HIDDEN(zebra_evpn_es_bypass, zebra_evpn_es_bypass_cmd,
- "[no] evpn mh bypass",
- NO_STR "EVPN\n" EVPN_MH_VTY_STR "set bypass mode\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif;
-
- zif = ifp->info;
-
- if (no) {
- zebra_evpn_es_bypass_cfg_update(zif, false);
- } else {
- if (!zebra_evpn_is_if_es_capable(zif)) {
- vty_out(vty,
- "%% DF bypass cannot be associated with this interface type\n");
- return CMD_WARNING;
- }
- zebra_evpn_es_bypass_cfg_update(zif, true);
- }
- return CMD_SUCCESS;
-}
-
-/* CLI for configuring DF preference part for an ES */
-DEFPY(zebra_evpn_es_pref, zebra_evpn_es_pref_cmd,
- "[no$no] evpn mh es-df-pref [(1-65535)$df_pref]",
- NO_STR "EVPN\n" EVPN_MH_VTY_STR
- "preference value used for DF election\n"
- "pref\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif;
-
- zif = ifp->info;
-
- if (no) {
- zebra_evpn_es_df_pref_update(zif, 0);
- } else {
- if (!zebra_evpn_is_if_es_capable(zif)) {
- vty_out(vty,
- "%% DF preference cannot be associated with this interface type\n");
- return CMD_WARNING;
- }
- zebra_evpn_es_df_pref_update(zif, df_pref);
- }
- return CMD_SUCCESS;
-}
-
-/* CLI for setting up sysmac part of ESI on an access port */
-DEFPY(zebra_evpn_es_sys_mac,
- zebra_evpn_es_sys_mac_cmd,
- "[no$no] evpn mh es-sys-mac [X:X:X:X:X:X$mac]",
- NO_STR
- "EVPN\n"
- EVPN_MH_VTY_STR
- "Ethernet segment system MAC\n"
- MAC_STR
-)
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif;
- int ret = 0;
-
- zif = ifp->info;
-
- if (no) {
- static struct ethaddr zero_mac;
-
- ret = zebra_evpn_es_sys_mac_update(zif, &zero_mac);
- if (ret == -1) {
- vty_out(vty, "%% Failed to clear ES sysmac\n");
- return CMD_WARNING;
- }
- } else {
-
- if (!zebra_evpn_is_if_es_capable(zif)) {
- vty_out(vty,
- "%% ESI cannot be associated with this interface type\n");
- return CMD_WARNING;
- }
-
- if (!mac || is_zero_mac(&mac->eth_addr)) {
- vty_out(vty, "%% ES sysmac value is invalid\n");
- return CMD_WARNING;
- }
-
- ret = zebra_evpn_es_sys_mac_update(zif, &mac->eth_addr);
- if (ret == -1) {
- vty_out(vty,
- "%% ESI already exists on a different interface\n");
- return CMD_WARNING;
- }
- }
- return CMD_SUCCESS;
-}
-
-/* CLI for setting up local-ID part of ESI on an access port */
-DEFPY(zebra_evpn_es_id,
- zebra_evpn_es_id_cmd,
- "[no$no] evpn mh es-id [(1-16777215)$es_lid | NAME$esi_str]",
- NO_STR
- "EVPN\n"
- EVPN_MH_VTY_STR
- "Ethernet segment identifier\n"
- "local discriminator\n"
- "10-byte ID - 00:AA:BB:CC:DD:EE:FF:GG:HH:II\n"
-)
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif;
- int ret = 0;
- esi_t esi;
-
- zif = ifp->info;
-
- if (no) {
- if (zif->es_info.lid)
- ret = zebra_evpn_es_lid_update(zif, 0);
- else if (memcmp(&zif->es_info.esi, zero_esi, sizeof(*zero_esi)))
- ret = zebra_evpn_es_type0_esi_update(zif, zero_esi);
-
- if (ret == -1) {
- vty_out(vty,
- "%% Failed to clear ES local id or ESI name\n");
- return CMD_WARNING;
- }
- } else {
- if (!zebra_evpn_is_if_es_capable(zif)) {
- vty_out(vty,
- "%% ESI cannot be associated with this interface type\n");
- return CMD_WARNING;
- }
-
- if (esi_str) {
- if (!str_to_esi(esi_str, &esi)) {
- vty_out(vty, "%% Malformed ESI name\n");
- return CMD_WARNING;
- }
- ret = zebra_evpn_es_type0_esi_update(zif, &esi);
- } else {
- if (!es_lid) {
- vty_out(vty,
- "%% Specify ES local id or ESI name\n");
- return CMD_WARNING;
- }
- ret = zebra_evpn_es_lid_update(zif, es_lid);
- }
-
- if (ret == -1) {
- vty_out(vty,
- "%% ESI already exists on a different interface\n");
- return CMD_WARNING;
- }
- }
- return CMD_SUCCESS;
-}
-
-/* CLI for tagging an interface as an uplink */
-DEFPY(zebra_evpn_mh_uplink, zebra_evpn_mh_uplink_cmd, "[no] evpn mh uplink",
- NO_STR "EVPN\n" EVPN_MH_VTY_STR "uplink to the VxLAN core\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct zebra_if *zif;
-
- zif = ifp->info;
- zebra_evpn_mh_uplink_cfg_update(zif, no ? false : true);
-
- return CMD_SUCCESS;
+ zif->es_info.df_pref = EVPN_MH_DF_PREF_DEFAULT;
}
void zebra_evpn_mh_json(json_object *json)
@@ -3864,7 +3638,7 @@ static void zebra_evpn_mh_uplink_oper_flags_update(struct zebra_if *zif,
}
}
-static void zebra_evpn_mh_uplink_cfg_update(struct zebra_if *zif, bool set)
+void zebra_evpn_mh_uplink_cfg_update(struct zebra_if *zif, bool set)
{
bool old_protodown = zebra_evpn_mh_is_all_uplinks_down();
bool new_protodown;
@@ -4087,15 +3861,6 @@ int zebra_evpn_mh_redirect_off(struct vty *vty, bool redirect_off)
return 0;
}
-void zebra_evpn_interface_init(void)
-{
- install_element(INTERFACE_NODE, &zebra_evpn_es_id_cmd);
- install_element(INTERFACE_NODE, &zebra_evpn_es_sys_mac_cmd);
- install_element(INTERFACE_NODE, &zebra_evpn_es_pref_cmd);
- install_element(INTERFACE_NODE, &zebra_evpn_es_bypass_cmd);
- install_element(INTERFACE_NODE, &zebra_evpn_mh_uplink_cmd);
-}
-
void zebra_evpn_mh_init(void)
{
zrouter.mh_info = XCALLOC(MTYPE_ZMH_INFO, sizeof(*zrouter.mh_info));
diff --git a/zebra/zebra_evpn_mh.h b/zebra/zebra_evpn_mh.h
index 59a41d0606..6080048976 100644
--- a/zebra/zebra_evpn_mh.h
+++ b/zebra/zebra_evpn_mh.h
@@ -17,8 +17,7 @@
#include "zebra_vxlan.h"
#include "zebra_vxlan_private.h"
#include "zebra_nhg.h"
-
-#define EVPN_MH_VTY_STR "Multihoming\n"
+#include "zebra_nb.h"
/* Ethernet Segment entry -
* - Local and remote ESs are maintained in a global RB tree,
@@ -336,8 +335,6 @@ extern bool zebra_evpn_es_mac_ref_entry(struct zebra_mac *mac,
struct zebra_evpn_es *es);
extern bool zebra_evpn_es_mac_ref(struct zebra_mac *mac, const esi_t *esi);
extern struct zebra_evpn_es *zebra_evpn_es_find(const esi_t *esi);
-extern void zebra_evpn_interface_init(void);
-extern int zebra_evpn_mh_if_write(struct vty *vty, struct interface *ifp);
extern void zebra_evpn_acc_vl_show(struct vty *vty, bool uj);
extern void zebra_evpn_acc_vl_show_detail(struct vty *vty, bool uj);
extern void zebra_evpn_if_es_print(struct vty *vty, json_object *json,
@@ -382,4 +379,16 @@ extern void zebra_evpn_proc_remote_nh(ZAPI_HANDLER_ARGS);
extern struct zebra_evpn_es_evi *
zebra_evpn_es_evi_find(struct zebra_evpn_es *es, struct zebra_evpn *zevpn);
+void zebra_build_type3_esi(uint32_t lid, struct ethaddr *mac, esi_t *esi);
+
+void zebra_evpn_es_sys_mac_update(struct zebra_if *zif, struct ethaddr *sysmac);
+void zebra_evpn_es_lid_update(struct zebra_if *zif, uint32_t lid);
+void zebra_evpn_es_type0_esi_update(struct zebra_if *zif, esi_t *esi);
+
+void zebra_evpn_es_df_pref_update(struct zebra_if *zif, uint16_t df_pref);
+void zebra_evpn_es_bypass_cfg_update(struct zebra_if *zif, bool bypass);
+void zebra_evpn_mh_uplink_cfg_update(struct zebra_if *zif, bool set);
+
+void zebra_evpn_mh_if_init(struct zebra_if *zif);
+
#endif /* _ZEBRA_EVPN_MH_H */
diff --git a/zebra/zebra_nb.c b/zebra/zebra_nb.c
index 7cdcaedd7e..7e1c43c204 100644
--- a/zebra/zebra_nb.c
+++ b/zebra/zebra_nb.c
@@ -10,9 +10,20 @@
#include "libfrr.h"
#include "zebra_nb.h"
+const char *features[] = {
+#if HAVE_BFDD == 0
+ "ptm-bfd",
+#endif
+#if defined(HAVE_RTADV)
+ "ipv6-router-advertisements",
+#endif
+ NULL
+};
+
/* clang-format off */
const struct frr_yang_module_info frr_zebra_info = {
.name = "frr-zebra",
+ .features = features,
.nodes = {
{
.xpath = "/frr-zebra:zebra/mcast-rpf-lookup",
@@ -79,6 +90,20 @@ const struct frr_yang_module_info frr_zebra_info = {
.modify = zebra_dplane_queue_limit_modify,
}
},
+#if HAVE_BFDD == 0
+ {
+ .xpath = "/frr-zebra:zebra/ptm-enable",
+ .cbs = {
+ .modify = zebra_ptm_enable_modify,
+ }
+ },
+#endif
+ {
+ .xpath = "/frr-zebra:zebra/route-map-delay",
+ .cbs = {
+ .modify = zebra_route_map_delay_modify,
+ }
+ },
{
.xpath = "/frr-zebra:zebra/debugs/debug-events",
.cbs = {
@@ -290,24 +315,38 @@ const struct frr_yang_module_info frr_zebra_info = {
}
},
{
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip-addrs",
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv4-addrs",
+ .cbs = {
+ .create = lib_interface_zebra_ipv4_addrs_create,
+ .destroy = lib_interface_zebra_ipv4_addrs_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv4-addrs/label",
.cbs = {
- .create = lib_interface_zebra_ip_addrs_create,
- .destroy = lib_interface_zebra_ip_addrs_destroy,
+ .modify = lib_interface_zebra_ipv4_addrs_label_modify,
+ .destroy = lib_interface_zebra_ipv4_addrs_label_destroy,
}
},
{
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/label",
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv4-p2p-addrs",
.cbs = {
- .modify = lib_interface_zebra_ip_addrs_label_modify,
- .destroy = lib_interface_zebra_ip_addrs_label_destroy,
+ .create = lib_interface_zebra_ipv4_p2p_addrs_create,
+ .destroy = lib_interface_zebra_ipv4_p2p_addrs_destroy,
}
},
{
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/ip4-peer",
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv4-p2p-addrs/label",
.cbs = {
- .modify = lib_interface_zebra_ip_addrs_ip4_peer_modify,
- .destroy = lib_interface_zebra_ip_addrs_ip4_peer_destroy,
+ .modify = lib_interface_zebra_ipv4_p2p_addrs_label_modify,
+ .destroy = lib_interface_zebra_ipv4_p2p_addrs_label_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-addrs",
+ .cbs = {
+ .create = lib_interface_zebra_ipv6_addrs_create,
+ .destroy = lib_interface_zebra_ipv6_addrs_destroy,
}
},
{
@@ -321,14 +360,13 @@ const struct frr_yang_module_info frr_zebra_info = {
.xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-detect",
.cbs = {
.modify = lib_interface_zebra_link_detect_modify,
- .destroy = lib_interface_zebra_link_detect_destroy,
}
},
{
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/shutdown",
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/enabled",
.cbs = {
- .modify = lib_interface_zebra_shutdown_modify,
- .destroy = lib_interface_zebra_shutdown_destroy,
+ .modify = lib_interface_zebra_enabled_modify,
+ .destroy = lib_interface_zebra_enabled_destroy,
}
},
{
@@ -346,10 +384,66 @@ const struct frr_yang_module_info frr_zebra_info = {
}
},
{
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/bandwidth",
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params",
.cbs = {
- .modify = lib_interface_zebra_bandwidth_modify,
- .destroy = lib_interface_zebra_bandwidth_destroy,
+ .create = lib_interface_zebra_link_params_create,
+ .destroy = lib_interface_zebra_link_params_destroy,
+ .apply_finish = lib_interface_zebra_link_params_apply_finish,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/metric",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_metric_modify,
+ .destroy = lib_interface_zebra_link_params_metric_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/max-bandwidth",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_max_bandwidth_modify,
+ .destroy = lib_interface_zebra_link_params_max_bandwidth_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/max-reservable-bandwidth",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_max_reservable_bandwidth_modify,
+ .destroy = lib_interface_zebra_link_params_max_reservable_bandwidth_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/unreserved-bandwidths/unreserved-bandwidth",
+ .cbs = {
+ .create = lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_create,
+ .destroy = lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/unreserved-bandwidths/unreserved-bandwidth/unreserved-bandwidth",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_unreserved_bandwidth_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/residual-bandwidth",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_residual_bandwidth_modify,
+ .destroy = lib_interface_zebra_link_params_residual_bandwidth_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/available-bandwidth",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_available_bandwidth_modify,
+ .destroy = lib_interface_zebra_link_params_available_bandwidth_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/utilized-bandwidth",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_utilized_bandwidth_modify,
+ .destroy = lib_interface_zebra_link_params_utilized_bandwidth_destroy,
}
},
{
@@ -357,13 +451,11 @@ const struct frr_yang_module_info frr_zebra_info = {
.cbs = {
.modify = lib_interface_zebra_legacy_admin_group_modify,
.destroy = lib_interface_zebra_legacy_admin_group_destroy,
- .cli_show = cli_show_legacy_admin_group,
},
},
{
.xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/affinities",
.cbs = {
- .cli_show = cli_show_affinity,
},
},
{
@@ -377,10 +469,276 @@ const struct frr_yang_module_info frr_zebra_info = {
.xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/affinity-mode",
.cbs = {
.modify = lib_interface_zebra_affinity_mode_modify,
- .cli_show = cli_show_affinity_mode,
},
},
{
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/neighbor",
+ .cbs = {
+ .create = lib_interface_zebra_link_params_neighbor_create,
+ .destroy = lib_interface_zebra_link_params_neighbor_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/neighbor/remote-as",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_neighbor_remote_as_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/neighbor/ipv4-remote-id",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_neighbor_ipv4_remote_id_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/delay",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_delay_modify,
+ .destroy = lib_interface_zebra_link_params_delay_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/min-max-delay",
+ .cbs = {
+ .create = lib_interface_zebra_link_params_min_max_delay_create,
+ .destroy = lib_interface_zebra_link_params_min_max_delay_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/min-max-delay/delay-min",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_min_max_delay_delay_min_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/min-max-delay/delay-max",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_min_max_delay_delay_max_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/delay-variation",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_delay_variation_modify,
+ .destroy = lib_interface_zebra_link_params_delay_variation_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/link-params/packet-loss",
+ .cbs = {
+ .modify = lib_interface_zebra_link_params_packet_loss_modify,
+ .destroy = lib_interface_zebra_link_params_packet_loss_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-0/esi",
+ .cbs = {
+ .modify = lib_interface_zebra_evpn_mh_type_0_esi_modify,
+ .destroy = lib_interface_zebra_evpn_mh_type_0_esi_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-3/system-mac",
+ .cbs = {
+ .modify = lib_interface_zebra_evpn_mh_type_3_system_mac_modify,
+ .destroy = lib_interface_zebra_evpn_mh_type_3_system_mac_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-3/local-discriminator",
+ .cbs = {
+ .modify = lib_interface_zebra_evpn_mh_type_3_local_discriminator_modify,
+ .destroy = lib_interface_zebra_evpn_mh_type_3_local_discriminator_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/df-preference",
+ .cbs = {
+ .modify = lib_interface_zebra_evpn_mh_df_preference_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/bypass",
+ .cbs = {
+ .modify = lib_interface_zebra_evpn_mh_bypass_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/uplink",
+ .cbs = {
+ .modify = lib_interface_zebra_evpn_mh_uplink_modify,
+ }
+ },
+#if defined(HAVE_RTADV)
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/send-advertisements",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_send_advertisements_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/max-rtr-adv-interval",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_max_rtr_adv_interval_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/managed-flag",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_managed_flag_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/other-config-flag",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_other_config_flag_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-flag",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_home_agent_flag_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/link-mtu",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_link_mtu_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/reachable-time",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_reachable_time_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/retrans-timer",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_retrans_timer_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/cur-hop-limit",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_modify,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/default-lifetime",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_default_lifetime_modify,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_default_lifetime_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/fast-retransmit",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_fast_retransmit_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/advertisement-interval-option",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_advertisement_interval_option_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-preference",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_modify,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-lifetime",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_modify,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/default-router-preference",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_default_router_preference_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix",
+ .cbs = {
+ .create = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_create,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/dnssl/dnssl-domain",
+ .cbs = {
+ .create = lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_create,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/dnssl/dnssl-domain/lifetime",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_lifetime_modify,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_lifetime_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/valid-lifetime",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_valid_lifetime_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/on-link-flag",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_on_link_flag_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/preferred-lifetime",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_preferred_lifetime_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/autonomous-flag",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_autonomous_flag_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/router-address-flag",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_router_address_flag_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/rdnss/rdnss-address",
+ .cbs = {
+ .create = lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_create,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/rdnss/rdnss-address/lifetime",
+ .cbs = {
+ .modify = lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_lifetime_modify,
+ .destroy = lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_lifetime_destroy,
+ }
+ },
+#endif /* defined(HAVE_RTADV) */
+#if HAVE_BFDD == 0
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ptm-enable",
+ .cbs = {
+ .modify = lib_interface_zebra_ptm_enable_modify,
+ }
+ },
+#endif
+ {
.xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/up-count",
.cbs = {
.get_elem = lib_interface_zebra_state_up_count_get_elem,
@@ -429,6 +787,81 @@ const struct frr_yang_module_info frr_zebra_info = {
}
},
{
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/router-id",
+ .cbs = {
+ .modify = lib_vrf_zebra_router_id_modify,
+ .destroy = lib_vrf_zebra_router_id_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/ipv6-router-id",
+ .cbs = {
+ .modify = lib_vrf_zebra_ipv6_router_id_modify,
+ .destroy = lib_vrf_zebra_ipv6_router_id_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/filter-protocol",
+ .cbs = {
+ .create = lib_vrf_zebra_filter_protocol_create,
+ .destroy = lib_vrf_zebra_filter_protocol_destroy,
+ .apply_finish = lib_vrf_zebra_filter_protocol_apply_finish,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/filter-protocol/route-map",
+ .cbs = {
+ .modify = lib_vrf_zebra_filter_protocol_route_map_modify,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/filter-nht",
+ .cbs = {
+ .create = lib_vrf_zebra_filter_nht_create,
+ .destroy = lib_vrf_zebra_filter_nht_destroy,
+ .apply_finish = lib_vrf_zebra_filter_nht_apply_finish,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/filter-nht/route-map",
+ .cbs = {
+ .modify = lib_vrf_zebra_filter_nht_route_map_modify,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/resolve-via-default",
+ .cbs = {
+ .modify = lib_vrf_zebra_resolve_via_default_modify,
+ .destroy = lib_vrf_zebra_resolve_via_default_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/ipv6-resolve-via-default",
+ .cbs = {
+ .modify = lib_vrf_zebra_ipv6_resolve_via_default_modify,
+ .destroy = lib_vrf_zebra_ipv6_resolve_via_default_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/netns/table-range",
+ .cbs = {
+ .create = lib_vrf_zebra_netns_table_range_create,
+ .destroy = lib_vrf_zebra_netns_table_range_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/netns/table-range/start",
+ .cbs = {
+ .modify = lib_vrf_zebra_netns_table_range_start_modify,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/netns/table-range/end",
+ .cbs = {
+ .modify = lib_vrf_zebra_netns_table_range_end_modify,
+ }
+ },
+ {
.xpath = "/frr-vrf:lib/vrf/frr-zebra:zebra/ribs/rib",
.cbs = {
.get_next = lib_vrf_zebra_ribs_rib_get_next,
diff --git a/zebra/zebra_nb.h b/zebra/zebra_nb.h
index 6762ebd314..97979ef962 100644
--- a/zebra/zebra_nb.h
+++ b/zebra/zebra_nb.h
@@ -44,6 +44,10 @@ int zebra_import_kernel_table_route_map_destroy(
int zebra_allow_external_route_update_create(struct nb_cb_create_args *args);
int zebra_allow_external_route_update_destroy(struct nb_cb_destroy_args *args);
int zebra_dplane_queue_limit_modify(struct nb_cb_modify_args *args);
+#if HAVE_BFDD == 0
+int zebra_ptm_enable_modify(struct nb_cb_modify_args *args);
+#endif
+int zebra_route_map_delay_modify(struct nb_cb_modify_args *args);
int zebra_debugs_debug_events_modify(struct nb_cb_modify_args *args);
int zebra_debugs_debug_events_destroy(struct nb_cb_destroy_args *args);
int zebra_debugs_debug_zapi_send_modify(struct nb_cb_modify_args *args);
@@ -80,31 +84,185 @@ int zebra_debugs_debug_dplane_detail_modify(struct nb_cb_modify_args *args);
int zebra_debugs_debug_dplane_detail_destroy(struct nb_cb_destroy_args *args);
int zebra_debugs_debug_mlag_modify(struct nb_cb_modify_args *args);
int zebra_debugs_debug_mlag_destroy(struct nb_cb_destroy_args *args);
-int lib_interface_zebra_ip_addrs_create(struct nb_cb_create_args *args);
-int lib_interface_zebra_ip_addrs_destroy(struct nb_cb_destroy_args *args);
-int lib_interface_zebra_ip_addrs_label_modify(struct nb_cb_modify_args *args);
-int lib_interface_zebra_ip_addrs_label_destroy(struct nb_cb_destroy_args *args);
-int lib_interface_zebra_ip_addrs_ip4_peer_modify(
+int lib_interface_zebra_ipv4_addrs_create(struct nb_cb_create_args *args);
+int lib_interface_zebra_ipv4_addrs_destroy(struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv4_addrs_label_modify(struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv4_addrs_label_destroy(struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv4_p2p_addrs_create(struct nb_cb_create_args *args);
+int lib_interface_zebra_ipv4_p2p_addrs_destroy(struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv4_p2p_addrs_label_modify(
struct nb_cb_modify_args *args);
-int lib_interface_zebra_ip_addrs_ip4_peer_destroy(
+int lib_interface_zebra_ipv4_p2p_addrs_label_destroy(
struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_addrs_create(struct nb_cb_create_args *args);
+int lib_interface_zebra_ipv6_addrs_destroy(struct nb_cb_destroy_args *args);
int lib_interface_zebra_multicast_modify(struct nb_cb_modify_args *args);
int lib_interface_zebra_multicast_destroy(struct nb_cb_destroy_args *args);
int lib_interface_zebra_link_detect_modify(struct nb_cb_modify_args *args);
-int lib_interface_zebra_link_detect_destroy(struct nb_cb_destroy_args *args);
-int lib_interface_zebra_shutdown_modify(struct nb_cb_modify_args *args);
-int lib_interface_zebra_shutdown_destroy(struct nb_cb_destroy_args *args);
+int lib_interface_zebra_enabled_modify(struct nb_cb_modify_args *args);
+int lib_interface_zebra_enabled_destroy(struct nb_cb_destroy_args *args);
int lib_interface_zebra_bandwidth_modify(struct nb_cb_modify_args *args);
int lib_interface_zebra_bandwidth_destroy(struct nb_cb_destroy_args *args);
int lib_interface_zebra_mpls_modify(struct nb_cb_modify_args *args);
int lib_interface_zebra_mpls_destroy(struct nb_cb_destroy_args *args);
-int lib_interface_zebra_legacy_admin_group_modify(
+int lib_interface_zebra_link_params_create(struct nb_cb_create_args *args);
+int lib_interface_zebra_link_params_destroy(struct nb_cb_destroy_args *args);
+void lib_interface_zebra_link_params_apply_finish(
+ struct nb_cb_apply_finish_args *args);
+int lib_interface_zebra_link_params_metric_modify(struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_metric_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_max_bandwidth_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_max_bandwidth_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_max_reservable_bandwidth_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_max_reservable_bandwidth_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_create(
+ struct nb_cb_create_args *args);
+void lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults);
+int lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_unreserved_bandwidth_modify(
+ struct nb_cb_modify_args *args);
+void lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_unreserved_bandwidth_cli_write(
+ struct vty *vty, const struct lyd_node *dnode, bool show_defaults);
+int lib_interface_zebra_link_params_residual_bandwidth_modify(
struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_residual_bandwidth_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_available_bandwidth_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_available_bandwidth_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_utilized_bandwidth_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_utilized_bandwidth_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_legacy_admin_group_modify(struct nb_cb_modify_args *args);
int lib_interface_zebra_legacy_admin_group_destroy(
struct nb_cb_destroy_args *args);
int lib_interface_zebra_affinity_create(struct nb_cb_create_args *args);
int lib_interface_zebra_affinity_destroy(struct nb_cb_destroy_args *args);
int lib_interface_zebra_affinity_mode_modify(struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_neighbor_create(
+ struct nb_cb_create_args *args);
+int lib_interface_zebra_link_params_neighbor_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_neighbor_remote_as_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_neighbor_ipv4_remote_id_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_delay_modify(struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_delay_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_min_max_delay_create(
+ struct nb_cb_create_args *args);
+int lib_interface_zebra_link_params_min_max_delay_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_min_max_delay_delay_min_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_min_max_delay_delay_max_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_delay_variation_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_delay_variation_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_link_params_packet_loss_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_link_params_packet_loss_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_evpn_mh_type_0_esi_modify(struct nb_cb_modify_args *args);
+int lib_interface_zebra_evpn_mh_type_0_esi_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_evpn_mh_type_3_system_mac_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_evpn_mh_type_3_system_mac_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_evpn_mh_type_3_local_discriminator_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_evpn_mh_type_3_local_discriminator_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_evpn_mh_df_preference_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_evpn_mh_bypass_modify(struct nb_cb_modify_args *args);
+int lib_interface_zebra_evpn_mh_uplink_modify(struct nb_cb_modify_args *args);
+#if defined(HAVE_RTADV)
+int lib_interface_zebra_ipv6_router_advertisements_send_advertisements_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_max_rtr_adv_interval_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_managed_flag_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_other_config_flag_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_flag_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_link_mtu_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_reachable_time_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_retrans_timer_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_default_lifetime_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_default_lifetime_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_fast_retransmit_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_advertisement_interval_option_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_default_router_preference_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_create(
+ struct nb_cb_create_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_valid_lifetime_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_on_link_flag_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_preferred_lifetime_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_autonomous_flag_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_router_address_flag_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_create(
+ struct nb_cb_create_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_lifetime_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_lifetime_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_create(
+ struct nb_cb_create_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_lifetime_modify(
+ struct nb_cb_modify_args *args);
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_lifetime_destroy(
+ struct nb_cb_destroy_args *args);
+#endif /* defined(HAVE_RTADV) */
+#if HAVE_BFDD == 0
+int lib_interface_zebra_ptm_enable_modify(struct nb_cb_modify_args *args);
+#endif
struct yang_data *
lib_interface_zebra_state_up_count_get_elem(struct nb_cb_get_elem_args *args);
struct yang_data *
@@ -121,6 +279,29 @@ struct yang_data *lib_interface_zebra_state_remote_vtep_get_elem(
struct nb_cb_get_elem_args *args);
struct yang_data *lib_interface_zebra_state_mcast_group_get_elem(
struct nb_cb_get_elem_args *args);
+int lib_vrf_zebra_router_id_modify(struct nb_cb_modify_args *args);
+int lib_vrf_zebra_router_id_destroy(struct nb_cb_destroy_args *args);
+int lib_vrf_zebra_ipv6_router_id_modify(struct nb_cb_modify_args *args);
+int lib_vrf_zebra_ipv6_router_id_destroy(struct nb_cb_destroy_args *args);
+int lib_vrf_zebra_filter_protocol_create(struct nb_cb_create_args *args);
+int lib_vrf_zebra_filter_protocol_destroy(struct nb_cb_destroy_args *args);
+void lib_vrf_zebra_filter_protocol_apply_finish(
+ struct nb_cb_apply_finish_args *args);
+int lib_vrf_zebra_filter_protocol_route_map_modify(
+ struct nb_cb_modify_args *args);
+int lib_vrf_zebra_filter_nht_create(struct nb_cb_create_args *args);
+int lib_vrf_zebra_filter_nht_destroy(struct nb_cb_destroy_args *args);
+void lib_vrf_zebra_filter_nht_apply_finish(struct nb_cb_apply_finish_args *args);
+int lib_vrf_zebra_filter_nht_route_map_modify(struct nb_cb_modify_args *args);
+int lib_vrf_zebra_resolve_via_default_modify(struct nb_cb_modify_args *args);
+int lib_vrf_zebra_resolve_via_default_destroy(struct nb_cb_destroy_args *args);
+int lib_vrf_zebra_ipv6_resolve_via_default_modify(struct nb_cb_modify_args *args);
+int lib_vrf_zebra_ipv6_resolve_via_default_destroy(
+ struct nb_cb_destroy_args *args);
+int lib_vrf_zebra_netns_table_range_create(struct nb_cb_create_args *args);
+int lib_vrf_zebra_netns_table_range_destroy(struct nb_cb_destroy_args *args);
+int lib_vrf_zebra_netns_table_range_start_modify(struct nb_cb_modify_args *args);
+int lib_vrf_zebra_netns_table_range_end_modify(struct nb_cb_modify_args *args);
const void *lib_vrf_zebra_ribs_rib_get_next(struct nb_cb_get_next_args *args);
int lib_vrf_zebra_ribs_rib_get_keys(struct nb_cb_get_keys_args *args);
const void *
diff --git a/zebra/zebra_nb_config.c b/zebra/zebra_nb_config.c
index 98c241b2a1..f24af16a2e 100644
--- a/zebra/zebra_nb_config.c
+++ b/zebra/zebra_nb_config.c
@@ -23,6 +23,12 @@
#include "zebra/debug.h"
#include "zebra/zebra_vxlan_private.h"
#include "zebra/zebra_vxlan.h"
+#include "zebra/zebra_evpn_mh.h"
+#include "zebra/zebra_ptm.h"
+#include "zebra/router-id.h"
+#include "zebra/zebra_routemap.h"
+#include "zebra/zebra_rnh.h"
+#include "zebra/table_manager.h"
/*
* XPath: /frr-zebra:zebra/mcast-rpf-lookup
@@ -264,6 +270,43 @@ int zebra_dplane_queue_limit_modify(struct nb_cb_modify_args *args)
return NB_OK;
}
+#if HAVE_BFDD == 0
+/*
+ * XPath: /frr-zebra:zebra/ptm-enable
+ */
+int zebra_ptm_enable_modify(struct nb_cb_modify_args *args)
+{
+ bool ptm;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ptm = yang_dnode_get_bool(args->dnode, NULL);
+
+ if (ptm)
+ zebra_global_ptm_enable();
+ else
+ zebra_global_ptm_disable();
+
+ return NB_OK;
+}
+#endif
+
+/*
+ * XPath: /frr-zebra:zebra/route-map-delay
+ */
+int zebra_route_map_delay_modify(struct nb_cb_modify_args *args)
+{
+ uint32_t delay = yang_dnode_get_uint32(args->dnode, NULL);
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ zebra_route_map_set_delay_timer(delay);
+
+ return NB_OK;
+}
+
/*
* XPath: /frr-zebra:zebra/debugs/debug-events
*/
@@ -823,28 +866,26 @@ int zebra_debugs_debug_mlag_destroy(struct nb_cb_destroy_args *args)
}
/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip-addrs
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv4-addrs
*/
-int lib_interface_zebra_ip_addrs_create(struct nb_cb_create_args *args)
+int lib_interface_zebra_ipv4_addrs_create(struct nb_cb_create_args *args)
{
struct interface *ifp;
- struct prefix prefix;
+ struct prefix p;
+ const char *label = NULL;
- // addr_family = yang_dnode_get_enum(dnode, "address-family");
- yang_dnode_get_prefix(&prefix, args->dnode, "ip-prefix");
- apply_mask(&prefix);
+ p.family = AF_INET;
+ yang_dnode_get_ipv4(&p.u.prefix4, args->dnode, "ip");
+ p.prefixlen = yang_dnode_get_uint8(args->dnode, "prefix-length");
+
+ if (yang_dnode_exists(args->dnode, "label"))
+ label = yang_dnode_get_string(args->dnode, "label");
switch (args->event) {
case NB_EV_VALIDATE:
- if (prefix.family == AF_INET
- && ipv4_martian(&prefix.u.prefix4)) {
- snprintfrr(args->errmsg, args->errmsg_len,
- "invalid address %pFX", &prefix);
- return NB_ERR_VALIDATION;
- } else if (prefix.family == AF_INET6
- && ipv6_martian(&prefix.u.prefix6)) {
+ if (ipv4_martian(&p.u.prefix4)) {
snprintfrr(args->errmsg, args->errmsg_len,
- "invalid address %pFX", &prefix);
+ "invalid address %pFX", &p);
return NB_ERR_VALIDATION;
}
break;
@@ -853,65 +894,105 @@ int lib_interface_zebra_ip_addrs_create(struct nb_cb_create_args *args)
break;
case NB_EV_APPLY:
ifp = nb_running_get_entry(args->dnode, NULL, true);
- if (prefix.family == AF_INET)
- if_ip_address_install(ifp, &prefix, NULL, NULL);
- else if (prefix.family == AF_INET6)
- if_ipv6_address_install(ifp, &prefix, NULL);
+ if_ip_address_install(ifp, &p, label, NULL);
+ /* set something for checking on label modify */
+ nb_running_set_entry(args->dnode, (void *)0x1);
break;
}
return NB_OK;
}
-int lib_interface_zebra_ip_addrs_destroy(struct nb_cb_destroy_args *args)
+int lib_interface_zebra_ipv4_addrs_destroy(struct nb_cb_destroy_args *args)
{
struct interface *ifp;
- struct prefix prefix;
- struct connected *ifc;
+ struct prefix p;
- yang_dnode_get_prefix(&prefix, args->dnode, "ip-prefix");
- apply_mask(&prefix);
+ p.family = AF_INET;
+ yang_dnode_get_ipv4(&p.u.prefix4, args->dnode, "ip");
+ p.prefixlen = yang_dnode_get_uint8(args->dnode, "prefix-length");
switch (args->event) {
case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ nb_running_unset_entry(args->dnode);
+
ifp = nb_running_get_entry(args->dnode, NULL, false);
- if (!ifp)
- return NB_OK;
-
- if (prefix.family == AF_INET) {
- /* Check current interface address. */
- ifc = connected_check_ptp(ifp, &prefix, NULL);
- if (!ifc) {
- snprintf(args->errmsg, args->errmsg_len,
- "interface %s Can't find address\n",
- ifp->name);
- return NB_ERR_VALIDATION;
- }
- } else if (prefix.family == AF_INET6) {
- /* Check current interface address. */
- ifc = connected_check(ifp, &prefix);
- if (!ifc) {
- snprintf(args->errmsg, args->errmsg_len,
- "interface can't find address %s",
- ifp->name);
- return NB_ERR_VALIDATION;
- }
- } else
- return NB_ERR_VALIDATION;
+ if_ip_address_uninstall(ifp, &p, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
- /* This is not configured address. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED)) {
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv4-addrs/label
+ */
+int lib_interface_zebra_ipv4_addrs_label_modify(struct nb_cb_modify_args *args)
+{
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (nb_running_get_entry_non_rec(lyd_parent(args->dnode), NULL,
+ false)) {
snprintf(args->errmsg, args->errmsg_len,
- "interface %s not configured", ifp->name);
+ "Changing label is not allowed");
return NB_ERR_VALIDATION;
}
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ break;
+ }
- /* This is not real address or interface is not active. */
- if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_QUEUED)
- || !CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
- if_connected_del(ifp->connected, ifc);
- connected_free(&ifc);
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv4_addrs_label_destroy(struct nb_cb_destroy_args *args)
+{
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ snprintf(args->errmsg, args->errmsg_len,
+ "Removing label is not allowed");
+ return NB_ERR_VALIDATION;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv4-p2p-addrs
+ */
+int lib_interface_zebra_ipv4_p2p_addrs_create(struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+ struct prefix p, pp;
+ const char *label = NULL;
+
+ p.family = AF_INET;
+ yang_dnode_get_ipv4(&p.u.prefix4, args->dnode, "ip");
+ p.prefixlen = 32;
+
+ pp.family = AF_INET;
+ yang_dnode_get_ipv4(&pp.u.prefix4, args->dnode, "peer-ip");
+ pp.prefixlen = yang_dnode_get_uint8(args->dnode, "peer-prefix-length");
+
+ if (yang_dnode_exists(args->dnode, "label"))
+ label = yang_dnode_get_string(args->dnode, "label");
+
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (ipv4_martian(&p.u.prefix4)) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "invalid address %pFX", &p);
return NB_ERR_VALIDATION;
}
break;
@@ -920,7 +1001,39 @@ int lib_interface_zebra_ip_addrs_destroy(struct nb_cb_destroy_args *args)
break;
case NB_EV_APPLY:
ifp = nb_running_get_entry(args->dnode, NULL, true);
- if_ip_address_uinstall(ifp, &prefix);
+ if_ip_address_install(ifp, &p, label, &pp);
+
+ /* set something for checking on label modify */
+ nb_running_set_entry(args->dnode, (void *)0x1);
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv4_p2p_addrs_destroy(struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct prefix p, pp;
+
+ p.family = AF_INET;
+ yang_dnode_get_ipv4(&p.u.prefix4, args->dnode, "ip");
+ p.prefixlen = 32;
+
+ pp.family = AF_INET;
+ yang_dnode_get_ipv4(&pp.u.prefix4, args->dnode, "peer-ip");
+ pp.prefixlen = yang_dnode_get_uint8(args->dnode, "peer-prefix-length");
+
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ nb_running_unset_entry(args->dnode);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, false);
+ if_ip_address_uninstall(ifp, &p, &pp);
break;
}
@@ -928,30 +1041,39 @@ int lib_interface_zebra_ip_addrs_destroy(struct nb_cb_destroy_args *args)
}
/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/label
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv4-p2p-addrs/label
*/
-int lib_interface_zebra_ip_addrs_label_modify(struct nb_cb_modify_args *args)
+int lib_interface_zebra_ipv4_p2p_addrs_label_modify(struct nb_cb_modify_args *args)
{
switch (args->event) {
case NB_EV_VALIDATE:
+ if (nb_running_get_entry_non_rec(lyd_parent(args->dnode), NULL,
+ false)) {
+ snprintf(args->errmsg, args->errmsg_len,
+ "Changing label is not allowed");
+ return NB_ERR_VALIDATION;
+ }
+ break;
case NB_EV_PREPARE:
case NB_EV_ABORT:
case NB_EV_APPLY:
- /* TODO: implement me. */
break;
}
return NB_OK;
}
-int lib_interface_zebra_ip_addrs_label_destroy(struct nb_cb_destroy_args *args)
+int lib_interface_zebra_ipv4_p2p_addrs_label_destroy(
+ struct nb_cb_destroy_args *args)
{
switch (args->event) {
case NB_EV_VALIDATE:
+ snprintf(args->errmsg, args->errmsg_len,
+ "Removing label is not allowed");
+ return NB_ERR_VALIDATION;
case NB_EV_PREPARE:
case NB_EV_ABORT:
case NB_EV_APPLY:
- /* TODO: implement me. */
break;
}
@@ -959,31 +1081,54 @@ int lib_interface_zebra_ip_addrs_label_destroy(struct nb_cb_destroy_args *args)
}
/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/ip4-peer
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-addrs
*/
-int lib_interface_zebra_ip_addrs_ip4_peer_modify(struct nb_cb_modify_args *args)
+int lib_interface_zebra_ipv6_addrs_create(struct nb_cb_create_args *args)
{
+ struct interface *ifp;
+ struct prefix p;
+
+ p.family = AF_INET6;
+ yang_dnode_get_ipv6(&p.u.prefix6, args->dnode, "ip");
+ p.prefixlen = yang_dnode_get_uint8(args->dnode, "prefix-length");
+
switch (args->event) {
case NB_EV_VALIDATE:
+ if (ipv6_martian(&p.u.prefix6)) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "invalid address %pFX", &p);
+ return NB_ERR_VALIDATION;
+ }
+ break;
case NB_EV_PREPARE:
case NB_EV_ABORT:
+ break;
case NB_EV_APPLY:
- /* TODO: implement me. */
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ if_ipv6_address_install(ifp, &p);
break;
}
return NB_OK;
}
-int lib_interface_zebra_ip_addrs_ip4_peer_destroy(
- struct nb_cb_destroy_args *args)
+int lib_interface_zebra_ipv6_addrs_destroy(struct nb_cb_destroy_args *args)
{
+ struct interface *ifp;
+ struct prefix p;
+
+ p.family = AF_INET6;
+ yang_dnode_get_ipv6(&p.u.prefix6, args->dnode, "ip");
+ p.prefixlen = yang_dnode_get_uint8(args->dnode, "prefix-length");
+
switch (args->event) {
case NB_EV_VALIDATE:
case NB_EV_PREPARE:
case NB_EV_ABORT:
+ break;
case NB_EV_APPLY:
- /* TODO: implement me. */
+ ifp = nb_running_get_entry(args->dnode, NULL, false);
+ if_ipv6_address_uninstall(ifp, &p);
break;
}
@@ -999,10 +1144,14 @@ int lib_interface_zebra_multicast_modify(struct nb_cb_modify_args *args)
return NB_OK;
struct interface *ifp;
+ bool multicast = yang_dnode_get_bool(args->dnode, NULL);
ifp = nb_running_get_entry(args->dnode, NULL, true);
- if_multicast_set(ifp);
+ if (multicast)
+ if_multicast_set(ifp);
+ else
+ if_multicast_unset(ifp);
return NB_OK;
}
@@ -1013,10 +1162,12 @@ int lib_interface_zebra_multicast_destroy(struct nb_cb_destroy_args *args)
return NB_OK;
struct interface *ifp;
+ struct zebra_if *zif;
ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
- if_multicast_unset(ifp);
+ zif->multicast = IF_ZEBRA_DATA_UNSPEC;
return NB_OK;
}
@@ -1033,23 +1184,7 @@ int lib_interface_zebra_link_detect_modify(struct nb_cb_modify_args *args)
bool link_detect;
ifp = nb_running_get_entry(args->dnode, NULL, true);
- link_detect = yang_dnode_get_bool(args->dnode, "link-detect");
-
- if_linkdetect(ifp, link_detect);
-
- return NB_OK;
-}
-
-int lib_interface_zebra_link_detect_destroy(struct nb_cb_destroy_args *args)
-{
- if (args->event != NB_EV_APPLY)
- return NB_OK;
-
- struct interface *ifp;
- bool link_detect;
-
- ifp = nb_running_get_entry(args->dnode, NULL, true);
- link_detect = yang_dnode_get_bool(args->dnode, "link-detect");
+ link_detect = yang_dnode_get_bool(args->dnode, NULL);
if_linkdetect(ifp, link_detect);
@@ -1057,32 +1192,39 @@ int lib_interface_zebra_link_detect_destroy(struct nb_cb_destroy_args *args)
}
/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/shutdown
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/enabled
*/
-int lib_interface_zebra_shutdown_modify(struct nb_cb_modify_args *args)
+int lib_interface_zebra_enabled_modify(struct nb_cb_modify_args *args)
{
if (args->event != NB_EV_APPLY)
return NB_OK;
struct interface *ifp;
+ bool enabled;
ifp = nb_running_get_entry(args->dnode, NULL, true);
+ enabled = yang_dnode_get_bool(args->dnode, NULL);
- if_shutdown(ifp);
+ if (enabled)
+ if_no_shutdown(ifp);
+ else
+ if_shutdown(ifp);
return NB_OK;
}
-int lib_interface_zebra_shutdown_destroy(struct nb_cb_destroy_args *args)
+int lib_interface_zebra_enabled_destroy(struct nb_cb_destroy_args *args)
{
if (args->event != NB_EV_APPLY)
return NB_OK;
struct interface *ifp;
+ struct zebra_if *zif;
ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
- if_no_shutdown(ifp);
+ zif->shutdown = IF_ZEBRA_DATA_UNSPEC;
return NB_OK;
}
@@ -1143,7 +1285,7 @@ int lib_interface_zebra_bandwidth_modify(struct nb_cb_modify_args *args)
uint32_t bandwidth;
ifp = nb_running_get_entry(args->dnode, NULL, true);
- bandwidth = yang_dnode_get_uint32(args->dnode, "bandwidth");
+ bandwidth = yang_dnode_get_uint32(args->dnode, NULL);
ifp->bandwidth = bandwidth;
@@ -1173,6 +1315,414 @@ int lib_interface_zebra_bandwidth_destroy(struct nb_cb_destroy_args *args)
}
/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params
+ */
+int lib_interface_zebra_link_params_create(struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ if_link_params_enable(ifp);
+
+ /*
+ * The interface is updated in the apply_finish callback after all
+ * parameters are set in the corresponding callbacks.
+ */
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_destroy(struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ if_link_params_free(ifp);
+ if (if_is_operative(ifp))
+ zebra_interface_parameters_update(ifp);
+
+ return NB_OK;
+}
+
+void lib_interface_zebra_link_params_apply_finish(
+ struct nb_cb_apply_finish_args *args)
+{
+ struct interface *ifp;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ if (if_is_operative(ifp))
+ zebra_interface_parameters_update(ifp);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/metric
+ */
+int lib_interface_zebra_link_params_metric_modify(struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint32_t metric;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ metric = yang_dnode_get_uint32(args->dnode, NULL);
+
+ link_param_cmd_set_uint32(ifp, &iflp->te_metric, LP_TE_METRIC, metric);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_metric_destroy(struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ link_param_cmd_unset(ifp, LP_TE_METRIC);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/max-bandwidth
+ */
+int lib_interface_zebra_link_params_max_bandwidth_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ float max_bw, res_bw, ava_bw, use_bw;
+
+ max_bw = yang_dnode_get_bandwidth_ieee_float32(args->dnode, NULL);
+
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (yang_dnode_exists(args->dnode, "../residual-bandwidth")) {
+ res_bw = yang_dnode_get_bandwidth_ieee_float32(
+ args->dnode, "../residual-bandwidth");
+ if (max_bw < res_bw) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "max-bandwidth %f is less than residual-bandwidth %f",
+ max_bw, res_bw);
+ return NB_ERR_VALIDATION;
+ }
+ }
+ if (yang_dnode_exists(args->dnode, "../available-bandwidth")) {
+ ava_bw = yang_dnode_get_bandwidth_ieee_float32(
+ args->dnode, "../available-bandwidth");
+ if (max_bw < ava_bw) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "max-bandwidth %f is less than available-bandwidth %f",
+ max_bw, ava_bw);
+ return NB_ERR_VALIDATION;
+ }
+ }
+ if (yang_dnode_exists(args->dnode, "../utilized-bandwidth")) {
+ use_bw = yang_dnode_get_bandwidth_ieee_float32(
+ args->dnode, "../utilized-bandwidth");
+ if (max_bw < use_bw) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "max-bandwidth %f is less than utilized-bandwidth %f",
+ max_bw, use_bw);
+ return NB_ERR_VALIDATION;
+ }
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ link_param_cmd_set_float(ifp, &iflp->max_bw, LP_MAX_BW, max_bw);
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_max_bandwidth_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ if (args->event == NB_EV_VALIDATE) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "Removing max-bandwidth is not allowed");
+ return NB_ERR_VALIDATION;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/max-reservable-bandwidth
+ */
+int lib_interface_zebra_link_params_max_reservable_bandwidth_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ float max_rsv_bw;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ max_rsv_bw = yang_dnode_get_bandwidth_ieee_float32(args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ link_param_cmd_set_float(ifp, &iflp->max_rsv_bw, LP_MAX_RSV_BW,
+ max_rsv_bw);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_max_reservable_bandwidth_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ if (args->event == NB_EV_VALIDATE) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "Removing max-reservable-bandwidth is not allowed");
+ return NB_ERR_VALIDATION;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/unreserved-bandwidths/unreserved-bandwidth
+ */
+int lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_create(
+ struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint8_t priority;
+ float unrsv_bw;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ priority = yang_dnode_get_uint8(args->dnode, "priority");
+ unrsv_bw = yang_dnode_get_bandwidth_ieee_float32(args->dnode,
+ "unreserved-bandwidth");
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ link_param_cmd_set_float(ifp, &iflp->unrsv_bw[priority], LP_UNRSV_BW,
+ unrsv_bw);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ if (args->event == NB_EV_VALIDATE) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "Removing unreserved-bandwidth is not allowed");
+ return NB_ERR_VALIDATION;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/unreserved-bandwidths/unreserved-bandwidth/unreserved-bandwidth
+ */
+int lib_interface_zebra_link_params_unreserved_bandwidths_unreserved_bandwidth_unreserved_bandwidth_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint8_t priority;
+ float unrsv_bw;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ priority = yang_dnode_get_uint8(args->dnode, "../priority");
+ unrsv_bw = yang_dnode_get_bandwidth_ieee_float32(args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ link_param_cmd_set_float(ifp, &iflp->unrsv_bw[priority], LP_UNRSV_BW,
+ unrsv_bw);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/residual-bandwidth
+ */
+int lib_interface_zebra_link_params_residual_bandwidth_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ float max_bw, res_bw;
+
+ res_bw = yang_dnode_get_bandwidth_ieee_float32(args->dnode, NULL);
+
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (yang_dnode_exists(args->dnode, "../max-bandwidth")) {
+ max_bw =
+ yang_dnode_get_bandwidth_ieee_float32(args->dnode,
+ "../max-bandwidth");
+ if (max_bw < res_bw) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "max-bandwidth %f is less than residual-bandwidth %f",
+ max_bw, res_bw);
+ return NB_ERR_VALIDATION;
+ }
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ link_param_cmd_set_float(ifp, &iflp->res_bw, LP_RES_BW, res_bw);
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_residual_bandwidth_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ link_param_cmd_unset(ifp, LP_RES_BW);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/available-bandwidth
+ */
+int lib_interface_zebra_link_params_available_bandwidth_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ float max_bw, ava_bw;
+
+ ava_bw = yang_dnode_get_bandwidth_ieee_float32(args->dnode, NULL);
+
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (yang_dnode_exists(args->dnode, "../max-bandwidth")) {
+ max_bw =
+ yang_dnode_get_bandwidth_ieee_float32(args->dnode,
+ "../max-bandwidth");
+ if (max_bw < ava_bw) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "max-bandwidth %f is less than available-bandwidth %f",
+ max_bw, ava_bw);
+ return NB_ERR_VALIDATION;
+ }
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ link_param_cmd_set_float(ifp, &iflp->ava_bw, LP_AVA_BW, ava_bw);
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_available_bandwidth_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ link_param_cmd_unset(ifp, LP_AVA_BW);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/utilized-bandwidth
+ */
+int lib_interface_zebra_link_params_utilized_bandwidth_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ float max_bw, use_bw;
+
+ use_bw = yang_dnode_get_bandwidth_ieee_float32(args->dnode, NULL);
+
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (yang_dnode_exists(args->dnode, "../max-bandwidth")) {
+ max_bw =
+ yang_dnode_get_bandwidth_ieee_float32(args->dnode,
+ "../max-bandwidth");
+ if (max_bw < use_bw) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "max-bandwidth %f is less than utilized-bandwidth %f",
+ max_bw, use_bw);
+ return NB_ERR_VALIDATION;
+ }
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ link_param_cmd_set_float(ifp, &iflp->use_bw, LP_USE_BW, use_bw);
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_utilized_bandwidth_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ link_param_cmd_unset(ifp, LP_USE_BW);
+
+ return NB_OK;
+}
+
+/*
* XPath:
* /frr-interface:lib/interface/frr-zebra:zebra/link-params/legacy-admin-group
*/
@@ -1183,31 +1733,22 @@ int lib_interface_zebra_legacy_admin_group_modify(
struct if_link_params *iflp;
uint32_t admin_group_value;
- ifp = nb_running_get_entry(args->dnode, NULL, true);
admin_group_value = yang_dnode_get_uint32(args->dnode, ".");
- if (!ifp)
- return NB_ERR_RESOURCE;
-
- iflp = if_link_params_get(ifp);
-
switch (args->event) {
case NB_EV_VALIDATE:
case NB_EV_PREPARE:
case NB_EV_ABORT:
break;
case NB_EV_APPLY:
- if (!iflp)
- iflp = if_link_params_enable(ifp);
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
iflp->admin_grp = admin_group_value;
SET_PARAM(iflp, LP_ADM_GRP);
admin_group_clear(&iflp->ext_admin_grp);
UNSET_PARAM(iflp, LP_EXTEND_ADM_GRP);
-
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
break;
}
return NB_OK;
@@ -1219,27 +1760,17 @@ int lib_interface_zebra_legacy_admin_group_destroy(
struct interface *ifp;
struct if_link_params *iflp;
- ifp = nb_running_get_entry(args->dnode, NULL, true);
-
- if (!ifp)
- return NB_ERR_RESOURCE;
-
- iflp = if_link_params_get(ifp);
-
switch (args->event) {
case NB_EV_VALIDATE:
case NB_EV_PREPARE:
case NB_EV_ABORT:
break;
case NB_EV_APPLY:
- if (!iflp)
- iflp = if_link_params_enable(ifp);
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
iflp->admin_grp = 0;
UNSET_PARAM(iflp, LP_ADM_GRP);
-
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
break;
}
return NB_OK;
@@ -1257,25 +1788,18 @@ int lib_interface_zebra_affinity_create(struct nb_cb_create_args *args)
struct affinity_map *affmap;
enum affinity_mode affinity_mode;
-
- ifp = nb_running_get_entry(args->dnode, NULL, true);
affname = yang_dnode_get_string(args->dnode, ".");
affinity_mode = yang_dnode_get_enum(args->dnode, "../../affinity-mode");
- if (!ifp)
- return NB_ERR_RESOURCE;
-
- affmap = affinity_map_get(affname);
- iflp = if_link_params_get(ifp);
-
switch (args->event) {
case NB_EV_VALIDATE:
case NB_EV_PREPARE:
case NB_EV_ABORT:
break;
case NB_EV_APPLY:
- if (!iflp)
- iflp = if_link_params_enable(ifp);
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ affmap = affinity_map_get(affname);
if (affmap->bit_position < 32 &&
(affinity_mode == AFFINITY_MODE_STANDARD ||
@@ -1289,9 +1813,6 @@ int lib_interface_zebra_affinity_create(struct nb_cb_create_args *args)
affmap->bit_position);
SET_PARAM(iflp, LP_EXTEND_ADM_GRP);
}
-
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
break;
}
return NB_OK;
@@ -1305,24 +1826,19 @@ int lib_interface_zebra_affinity_destroy(struct nb_cb_destroy_args *args)
struct affinity_map *affmap;
enum affinity_mode affinity_mode;
- ifp = nb_running_get_entry(args->dnode, NULL, true);
affname = yang_dnode_get_string(args->dnode, ".");
affinity_mode = yang_dnode_get_enum(args->dnode, "../../affinity-mode");
- if (!ifp)
- return NB_ERR_RESOURCE;
-
- affmap = affinity_map_get(affname);
- iflp = if_link_params_get(ifp);
-
switch (args->event) {
case NB_EV_VALIDATE:
case NB_EV_PREPARE:
case NB_EV_ABORT:
break;
case NB_EV_APPLY:
- if (!iflp)
- return NB_OK;
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+ affmap = affinity_map_get(affname);
+
if (affmap->bit_position < 32 &&
(affinity_mode == AFFINITY_MODE_STANDARD ||
affinity_mode == AFFINITY_MODE_BOTH)) {
@@ -1337,9 +1853,6 @@ int lib_interface_zebra_affinity_destroy(struct nb_cb_destroy_args *args)
if (admin_group_zero(&iflp->ext_admin_grp))
UNSET_PARAM(iflp, LP_EXTEND_ADM_GRP);
}
-
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
break;
}
return NB_OK;
@@ -1355,23 +1868,17 @@ int lib_interface_zebra_affinity_mode_modify(struct nb_cb_modify_args *args)
struct if_link_params *iflp;
enum affinity_mode affinity_mode;
-
- ifp = nb_running_get_entry(args->dnode, NULL, true);
affinity_mode = yang_dnode_get_enum(args->dnode, ".");
- if (!ifp)
- return NB_ERR_RESOURCE;
-
- iflp = if_link_params_get(ifp);
-
switch (args->event) {
case NB_EV_VALIDATE:
case NB_EV_PREPARE:
case NB_EV_ABORT:
break;
case NB_EV_APPLY:
- if (!iflp)
- iflp = if_link_params_enable(ifp);
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
if (affinity_mode == AFFINITY_MODE_STANDARD) {
if (!IS_PARAM_SET(iflp, LP_ADM_GRP) &&
IS_PARAM_SET(iflp, LP_EXTEND_ADM_GRP)) {
@@ -1405,84 +1912,1835 @@ int lib_interface_zebra_affinity_mode_modify(struct nb_cb_modify_args *args)
SET_PARAM(iflp, LP_ADM_GRP);
}
}
+ break;
+ }
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/neighbor
+ */
+int lib_interface_zebra_link_params_neighbor_create(struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ struct in_addr ip;
+ uint32_t as;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ as = yang_dnode_get_uint32(args->dnode, "remote-as");
+ yang_dnode_get_ipv4(&ip, args->dnode, "ipv4-remote-id");
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->rmt_as = as;
+ iflp->rmt_ip = ip;
+ SET_PARAM(iflp, LP_RMT_AS);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_neighbor_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->rmt_as = 0;
+ iflp->rmt_ip.s_addr = 0;
+ UNSET_PARAM(iflp, LP_RMT_AS);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/neighbor/remote-as
+ */
+int lib_interface_zebra_link_params_neighbor_remote_as_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint32_t as;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ as = yang_dnode_get_uint32(args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->rmt_as = as;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/neighbor/ipv4-remote-id
+ */
+int lib_interface_zebra_link_params_neighbor_ipv4_remote_id_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ struct in_addr ip;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ yang_dnode_get_ipv4(&ip, args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->rmt_ip = ip;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/delay
+ */
+int lib_interface_zebra_link_params_delay_modify(struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint32_t delay;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ delay = yang_dnode_get_uint32(args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ link_param_cmd_set_uint32(ifp, &iflp->av_delay, LP_DELAY, delay);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_delay_destroy(struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->av_delay = 0;
+ link_param_cmd_unset(ifp, LP_DELAY);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/min-max-delay
+ */
+int lib_interface_zebra_link_params_min_max_delay_create(
+ struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint32_t delay_min, delay_max;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ delay_min = yang_dnode_get_uint32(args->dnode, "delay-min");
+ delay_max = yang_dnode_get_uint32(args->dnode, "delay-max");
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->min_delay = delay_min;
+ iflp->max_delay = delay_max;
+ SET_PARAM(iflp, LP_MM_DELAY);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_min_max_delay_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->min_delay = 0;
+ iflp->max_delay = 0;
+ UNSET_PARAM(iflp, LP_MM_DELAY);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/min-max-delay/delay-min
+ */
+int lib_interface_zebra_link_params_min_max_delay_delay_min_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint32_t delay_min;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ delay_min = yang_dnode_get_uint32(args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->min_delay = delay_min;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/min-max-delay/delay-max
+ */
+int lib_interface_zebra_link_params_min_max_delay_delay_max_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint32_t delay_max;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ delay_max = yang_dnode_get_uint32(args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ iflp->max_delay = delay_max;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/delay-variation
+ */
+int lib_interface_zebra_link_params_delay_variation_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ uint32_t delay_var;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ delay_var = yang_dnode_get_uint32(args->dnode, NULL);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
- if (if_is_operative(ifp))
- zebra_interface_parameters_update(ifp);
+ link_param_cmd_set_uint32(ifp, &iflp->delay_var, LP_DELAY_VAR,
+ delay_var);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_delay_variation_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ link_param_cmd_unset(ifp, LP_DELAY_VAR);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-params/packet-loss
+ */
+int lib_interface_zebra_link_params_packet_loss_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct if_link_params *iflp;
+ double packet_loss;
+ uint32_t value;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ packet_loss = yang_dnode_get_dec64(args->dnode, NULL);
+ value = (uint32_t)(packet_loss / LOSS_PRECISION);
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ iflp = if_link_params_get(ifp);
+
+ link_param_cmd_set_uint32(ifp, &iflp->pkt_loss, LP_PKT_LOSS, value);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_params_packet_loss_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ link_param_cmd_unset(ifp, LP_PKT_LOSS);
+
+ return NB_OK;
+}
+
+static bool evpn_mh_dnode_to_esi(const struct lyd_node *dnode, esi_t *esi)
+{
+ if (yang_dnode_exists(dnode, "type-0/esi")) {
+ str_to_esi(yang_dnode_get_string(dnode, "type-0/esi"), esi);
+ } else if (yang_dnode_exists(dnode, "type-3/system-mac") &&
+ yang_dnode_exists(dnode, "type-3/local-discriminator")) {
+ struct ethaddr mac;
+ uint32_t lid;
+
+ yang_dnode_get_mac(&mac, dnode, "type-3/system-mac");
+ lid = yang_dnode_get_uint32(dnode, "type-3/local-discriminator");
+
+ zebra_build_type3_esi(lid, &mac, esi);
+ } else {
+ return false;
+ }
+
+ return true;
+}
+
+struct esi_cmp_iter_arg {
+ struct lyd_node *dnode;
+ esi_t esi;
+ bool exists;
+};
+
+static int esi_cmp_iter_cb(const struct lyd_node *dnode, void *arg)
+{
+ struct esi_cmp_iter_arg *iter = arg;
+ esi_t esi;
+
+ if (dnode == iter->dnode)
+ return YANG_ITER_CONTINUE;
+
+ if (!evpn_mh_dnode_to_esi(dnode, &esi))
+ return YANG_ITER_CONTINUE;
+
+ if (!memcmp(&esi, &iter->esi, ESI_BYTES)) {
+ iter->exists = true;
+ return YANG_ITER_STOP;
+ }
+
+ return YANG_ITER_CONTINUE;
+}
+
+/* evpn-mh should be passed to this function */
+static bool esi_unique(struct lyd_node *dnode)
+{
+ struct esi_cmp_iter_arg iter;
+
+ iter.dnode = dnode;
+ evpn_mh_dnode_to_esi(dnode, &iter.esi);
+ iter.exists = false;
+
+ yang_dnode_iterate(esi_cmp_iter_cb, &iter, dnode,
+ "/frr-interface:lib/interface/frr-zebra:zebra/evpn-mh");
+
+ if (iter.exists)
+ return false;
+
+ return true;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-0/esi
+ */
+int lib_interface_zebra_evpn_mh_type_0_esi_modify(struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ esi_t esi;
+
+ switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (!esi_unique(lyd_parent(lyd_parent(args->dnode)))) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "ESI already exists on a different interface");
+ return NB_ERR_VALIDATION;
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ str_to_esi(yang_dnode_get_string(args->dnode, NULL), &esi);
+ zebra_evpn_es_type0_esi_update(ifp->info, &esi);
break;
}
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_evpn_mh_type_0_esi_destroy(struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zebra_evpn_es_type0_esi_update(ifp->info, NULL);
+
return NB_OK;
}
/*
- * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/l3vni-id
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-3/system-mac
*/
-int lib_vrf_zebra_l3vni_id_modify(struct nb_cb_modify_args *args)
+int lib_interface_zebra_evpn_mh_type_3_system_mac_modify(
+ struct nb_cb_modify_args *args)
{
- struct vrf *vrf;
- struct zebra_vrf *zvrf;
- vni_t vni = 0;
- struct zebra_l3vni *zl3vni = NULL;
- char err[ERR_STR_SZ];
- bool pfx_only = false;
- const struct lyd_node *pn_dnode;
- const char *vrfname;
+ struct interface *ifp;
+ struct ethaddr mac;
+
+ yang_dnode_get_mac(&mac, args->dnode, NULL);
switch (args->event) {
+ case NB_EV_VALIDATE:
+ if (is_zero_mac(&mac)) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "MAC cannot be all-zeroes");
+ return NB_ERR_VALIDATION;
+ }
+ if (!esi_unique(lyd_parent(lyd_parent(args->dnode)))) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "ESI already exists on a different interface");
+ return NB_ERR_VALIDATION;
+ }
+ break;
case NB_EV_PREPARE:
case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zebra_evpn_es_sys_mac_update(ifp->info, &mac);
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_evpn_mh_type_3_system_mac_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zebra_evpn_es_sys_mac_update(ifp->info, NULL);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/type-3/local-discriminator
+ */
+int lib_interface_zebra_evpn_mh_type_3_local_discriminator_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ uint32_t lid;
+
+ switch (args->event) {
case NB_EV_VALIDATE:
- vni = yang_dnode_get_uint32(args->dnode, NULL);
- /* Get vrf info from parent node, reject configuration
- * if zebra vrf already mapped to different vni id.
- */
- pn_dnode = yang_dnode_get_parent(args->dnode, "vrf");
- vrfname = yang_dnode_get_string(pn_dnode, "name");
- zvrf = zebra_vrf_lookup_by_name(vrfname);
- if (!zvrf) {
- snprintf(args->errmsg, args->errmsg_len,
- "zebra vrf info not found for vrf:%s.",
- vrfname);
+ if (!esi_unique(lyd_parent(lyd_parent(args->dnode)))) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "ESI already exists on a different interface");
+ return NB_ERR_VALIDATION;
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ lid = yang_dnode_get_uint32(args->dnode, NULL);
+ zebra_evpn_es_lid_update(ifp->info, lid);
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_evpn_mh_type_3_local_discriminator_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zebra_evpn_es_lid_update(ifp->info, 0);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/df-preference
+ */
+int lib_interface_zebra_evpn_mh_df_preference_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ uint16_t df_pref;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ df_pref = yang_dnode_get_uint16(args->dnode, NULL);
+ zebra_evpn_es_df_pref_update(ifp->info, df_pref);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/bypass
+ */
+int lib_interface_zebra_evpn_mh_bypass_modify(struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ bool bypass;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ bypass = yang_dnode_get_bool(args->dnode, NULL);
+ zebra_evpn_es_bypass_cfg_update(ifp->info, bypass);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/evpn-mh/uplink
+ */
+int lib_interface_zebra_evpn_mh_uplink_modify(struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ bool uplink;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ uplink = yang_dnode_get_bool(args->dnode, NULL);
+ zebra_evpn_mh_uplink_cfg_update(ifp->info, uplink);
+
+ return NB_OK;
+}
+
+#if defined(HAVE_RTADV)
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/send-advertisements
+ */
+int lib_interface_zebra_ipv6_router_advertisements_send_advertisements_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ bool send_adv;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ send_adv = yang_dnode_get_bool(args->dnode, NULL);
+
+ if (send_adv) {
+ ipv6_nd_suppress_ra_set(ifp, RA_ENABLE);
+ SET_FLAG(zif->rtadv.ra_configured, VTY_RA_CONFIGURED);
+ } else {
+ if (!CHECK_FLAG(zif->rtadv.ra_configured, BGP_RA_CONFIGURED))
+ ipv6_nd_suppress_ra_set(ifp, RA_SUPPRESS);
+ UNSET_FLAG(zif->rtadv.ra_configured, VTY_RA_CONFIGURED);
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/max-rtr-adv-interval
+ */
+int lib_interface_zebra_ipv6_router_advertisements_max_rtr_adv_interval_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ uint32_t interval;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ interval = yang_dnode_get_uint32(args->dnode, NULL);
+
+ ipv6_nd_interval_set(ifp, interval);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/managed-flag
+ */
+int lib_interface_zebra_ipv6_router_advertisements_managed_flag_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ bool managed_flag;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ managed_flag = yang_dnode_get_bool(args->dnode, NULL);
+
+ zif->rtadv.AdvManagedFlag = managed_flag;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/other-config-flag
+ */
+int lib_interface_zebra_ipv6_router_advertisements_other_config_flag_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ bool other_config_flag;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ other_config_flag = yang_dnode_get_bool(args->dnode, NULL);
+
+ zif->rtadv.AdvOtherConfigFlag = other_config_flag;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-flag
+ */
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_flag_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ bool home_agent_flag;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ home_agent_flag = yang_dnode_get_bool(args->dnode, NULL);
+
+ zif->rtadv.AdvHomeAgentFlag = home_agent_flag;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/link-mtu
+ */
+int lib_interface_zebra_ipv6_router_advertisements_link_mtu_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ uint32_t mtu;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ mtu = yang_dnode_get_uint32(args->dnode, NULL);
+
+ zif->rtadv.AdvLinkMTU = mtu;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/reachable-time
+ */
+int lib_interface_zebra_ipv6_router_advertisements_reachable_time_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ uint32_t time;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+ time = yang_dnode_get_uint32(args->dnode, NULL);
+
+ zif->rtadv.AdvReachableTime = time;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/retrans-timer
+ */
+int lib_interface_zebra_ipv6_router_advertisements_retrans_timer_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ uint32_t timer;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+ timer = yang_dnode_get_uint32(args->dnode, NULL);
+
+ zif->rtadv.AdvRetransTimer = timer;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/cur-hop-limit
+ */
+int lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ uint8_t limit;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+ limit = yang_dnode_get_uint8(args->dnode, NULL);
+
+ zif->rtadv.AdvCurHopLimit = limit;
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_cur_hop_limit_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ zif->rtadv.AdvCurHopLimit = RTADV_DEFAULT_HOPLIMIT;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/default-lifetime
+ */
+int lib_interface_zebra_ipv6_router_advertisements_default_lifetime_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ uint16_t lifetime;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ lifetime = yang_dnode_get_uint16(args->dnode, NULL);
+
+ zif->rtadv.AdvDefaultLifetime = lifetime;
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_default_lifetime_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ zif->rtadv.AdvDefaultLifetime = -1;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/fast-retransmit
+ */
+int lib_interface_zebra_ipv6_router_advertisements_fast_retransmit_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ bool fast_retransmit;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ fast_retransmit = yang_dnode_get_bool(args->dnode, NULL);
+
+ zif->rtadv.UseFastRexmit = fast_retransmit;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/advertisement-interval-option
+ */
+int lib_interface_zebra_ipv6_router_advertisements_advertisement_interval_option_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ bool option;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ option = yang_dnode_get_bool(args->dnode, NULL);
+
+ zif->rtadv.AdvIntervalOption = option;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-preference
+ */
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ uint16_t preference;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ preference = yang_dnode_get_uint16(args->dnode, NULL);
+
+ zif->rtadv.HomeAgentPreference = preference;
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_preference_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ zif->rtadv.HomeAgentPreference = 0;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/home-agent-lifetime
+ */
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ uint16_t lifetime;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ lifetime = yang_dnode_get_uint16(args->dnode, NULL);
+
+ zif->rtadv.HomeAgentLifetime = lifetime;
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_home_agent_lifetime_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ zif->rtadv.HomeAgentLifetime = -1;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/default-router-preference
+ */
+int lib_interface_zebra_ipv6_router_advertisements_default_router_preference_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ struct zebra_if *zif;
+ int preference;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+ zif = ifp->info;
+
+ preference = yang_dnode_get_enum(args->dnode, NULL);
+
+ zif->rtadv.DefaultPreference = preference;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix
+ */
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_create(
+ struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+ struct rtadv_prefix rp, *prefix;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ yang_dnode_get_ipv6p(&rp.prefix, args->dnode, "prefix-spec");
+ rp.AdvOnLinkFlag = yang_dnode_get_bool(args->dnode, "on-link-flag");
+ rp.AdvAutonomousFlag = yang_dnode_get_bool(args->dnode,
+ "autonomous-flag");
+ rp.AdvRouterAddressFlag = yang_dnode_get_bool(args->dnode,
+ "router-address-flag");
+ rp.AdvValidLifetime = yang_dnode_get_uint32(args->dnode,
+ "valid-lifetime");
+ rp.AdvPreferredLifetime = yang_dnode_get_uint32(args->dnode,
+ "preferred-lifetime");
+
+ prefix = rtadv_add_prefix_manual(ifp->info, &rp);
+ nb_running_set_entry(args->dnode, prefix);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct rtadv_prefix *prefix;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ prefix = nb_running_unset_entry(args->dnode);
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ rtadv_delete_prefix_manual(ifp->info, prefix);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/valid-lifetime
+ */
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_valid_lifetime_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct rtadv_prefix *prefix;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ prefix = nb_running_get_entry(args->dnode, NULL, true);
+
+ prefix->AdvValidLifetime = yang_dnode_get_uint32(args->dnode, NULL);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/on-link-flag
+ */
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_on_link_flag_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct rtadv_prefix *prefix;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ prefix = nb_running_get_entry(args->dnode, NULL, true);
+
+ prefix->AdvOnLinkFlag = yang_dnode_get_bool(args->dnode, NULL);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/preferred-lifetime
+ */
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_preferred_lifetime_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct rtadv_prefix *prefix;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ prefix = nb_running_get_entry(args->dnode, NULL, true);
+
+ prefix->AdvPreferredLifetime = yang_dnode_get_uint32(args->dnode, NULL);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/autonomous-flag
+ */
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_autonomous_flag_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct rtadv_prefix *prefix;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ prefix = nb_running_get_entry(args->dnode, NULL, true);
+
+ prefix->AdvAutonomousFlag = yang_dnode_get_bool(args->dnode, NULL);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/prefix-list/prefix/router-address-flag
+ */
+int lib_interface_zebra_ipv6_router_advertisements_prefix_list_prefix_router_address_flag_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct rtadv_prefix *prefix;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ prefix = nb_running_get_entry(args->dnode, NULL, true);
+
+ prefix->AdvRouterAddressFlag = yang_dnode_get_bool(args->dnode, NULL);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/rdnss/rdnss-address
+ */
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_create(
+ struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+ struct rtadv_rdnss rdnss, *p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ yang_dnode_get_ipv6(&rdnss.addr, args->dnode, "address");
+ if (yang_dnode_exists(args->dnode, "lifetime")) {
+ rdnss.lifetime = yang_dnode_get_uint32(args->dnode, "lifetime");
+ rdnss.lifetime_set = 1;
+ } else {
+ rdnss.lifetime_set = 0;
+ }
+
+ p = rtadv_rdnss_set(ifp->info, &rdnss);
+ nb_running_set_entry(args->dnode, p);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct rtadv_rdnss *p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ p = nb_running_unset_entry(args->dnode);
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ rtadv_rdnss_reset(ifp->info, p);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/rdnss/rdnss-address/lifetime
+ */
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_lifetime_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct rtadv_rdnss *p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ p = nb_running_get_entry(args->dnode, NULL, true);
+
+ p->lifetime = yang_dnode_get_uint32(args->dnode, NULL);
+ p->lifetime_set = 1;
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_rdnss_rdnss_address_lifetime_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct rtadv_rdnss *p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ p = nb_running_get_entry(args->dnode, NULL, true);
+
+ p->lifetime_set = 0;
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/dnssl/dnssl-domain
+ */
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_create(
+ struct nb_cb_create_args *args)
+{
+ struct interface *ifp;
+ struct rtadv_dnssl dnssl, *p;
+ int ret;
+
+ strlcpy(dnssl.name, yang_dnode_get_string(args->dnode, "domain"),
+ sizeof(dnssl.name));
+ ret = rtadv_dnssl_encode(dnssl.encoded_name, dnssl.name);
+
+ if (args->event == NB_EV_VALIDATE) {
+ if (ret < 0) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "Malformed DNS search domain");
return NB_ERR_VALIDATION;
}
- if (zvrf->l3vni && zvrf->l3vni != vni) {
- snprintf(
- args->errmsg, args->errmsg_len,
- "vni %u cannot be configured as vni %u is already configured under the vrf",
- vni, zvrf->l3vni);
+ }
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ if (yang_dnode_exists(args->dnode, "lifetime")) {
+ dnssl.lifetime = yang_dnode_get_uint32(args->dnode, "lifetime");
+ dnssl.lifetime_set = 1;
+ } else {
+ dnssl.lifetime_set = 0;
+ }
+
+ p = rtadv_dnssl_set(ifp->info, &dnssl);
+ nb_running_set_entry(args->dnode, p);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct interface *ifp;
+ struct rtadv_dnssl *p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ p = nb_running_unset_entry(args->dnode);
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ rtadv_dnssl_reset(ifp->info, p);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ipv6-router-advertisements/dnssl/dnssl-domain/lifetime
+ */
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_lifetime_modify(
+ struct nb_cb_modify_args *args)
+{
+ struct rtadv_dnssl *p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ p = nb_running_get_entry(args->dnode, NULL, true);
+
+ p->lifetime = yang_dnode_get_uint32(args->dnode, NULL);
+ p->lifetime_set = 1;
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ipv6_router_advertisements_dnssl_dnssl_domain_lifetime_destroy(
+ struct nb_cb_destroy_args *args)
+{
+ struct rtadv_dnssl *p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ p = nb_running_get_entry(args->dnode, NULL, true);
+
+ p->lifetime_set = 0;
+
+ return NB_OK;
+}
+#endif /* defined(HAVE_RTADV) */
+
+#if HAVE_BFDD == 0
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ptm-enable
+ */
+int lib_interface_zebra_ptm_enable_modify(struct nb_cb_modify_args *args)
+{
+ struct interface *ifp;
+ bool ptm;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ ifp = nb_running_get_entry(args->dnode, NULL, true);
+
+ ptm = yang_dnode_get_bool(args->dnode, NULL);
+ if (ptm)
+ zebra_if_ptm_enable(ifp);
+ else
+ zebra_if_ptm_disable(ifp);
+
+ return NB_OK;
+}
+#endif
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/router-id
+ */
+int lib_vrf_zebra_router_id_modify(struct nb_cb_modify_args *args)
+{
+ struct vrf *vrf;
+ struct prefix p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ yang_dnode_get_ipv4p(&p, args->dnode, NULL);
+
+ router_id_set(AFI_IP, &p, vrf->info);
+
+ return NB_OK;
+}
+
+int lib_vrf_zebra_router_id_destroy(struct nb_cb_destroy_args *args)
+{
+ struct vrf *vrf;
+ struct prefix p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ memset(&p, 0, sizeof(p));
+ p.family = AF_INET;
+
+ router_id_set(AFI_IP, &p, vrf->info);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/ipv6-router-id
+ */
+int lib_vrf_zebra_ipv6_router_id_modify(struct nb_cb_modify_args *args)
+{
+ struct vrf *vrf;
+ struct prefix p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ yang_dnode_get_ipv6p(&p, args->dnode, NULL);
+
+ router_id_set(AFI_IP6, &p, vrf->info);
+
+ return NB_OK;
+}
+
+int lib_vrf_zebra_ipv6_router_id_destroy(struct nb_cb_destroy_args *args)
+{
+ struct vrf *vrf;
+ struct prefix p;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ memset(&p, 0, sizeof(p));
+ p.family = AF_INET6;
+
+ router_id_set(AFI_IP6, &p, vrf->info);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/filter-protocol
+ */
+int lib_vrf_zebra_filter_protocol_create(struct nb_cb_create_args *args)
+{
+ const char *proto = yang_dnode_get_string(args->dnode, "protocol");
+ int rtype;
+
+ if (strcasecmp(proto, "any") == 0)
+ rtype = ZEBRA_ROUTE_MAX;
+ else
+ rtype = proto_name2num(proto);
+
+ if (args->event == NB_EV_VALIDATE)
+ if (rtype < 0) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "invalid protocol name \"%s\"", proto);
return NB_ERR_VALIDATION;
}
- /* Check if this VNI is already present in the system */
- zl3vni = zl3vni_lookup(vni);
- if (zl3vni) {
- snprintf(args->errmsg, args->errmsg_len,
- "VNI %u is already configured as L3-VNI", vni);
+ /* the creation finishes in the apply_finish callback */
+
+ return NB_OK;
+}
+
+int lib_vrf_zebra_filter_protocol_destroy(struct nb_cb_destroy_args *args)
+{
+ struct vrf *vrf;
+ const char *afi_safi = yang_dnode_get_string(args->dnode, "afi-safi");
+ const char *proto = yang_dnode_get_string(args->dnode, "protocol");
+ const char *rmap = yang_dnode_get_string(args->dnode, "route-map");
+ afi_t afi;
+ safi_t safi;
+ int rtype;
+
+ yang_afi_safi_identity2value(afi_safi, &afi, &safi);
+
+ if (strcasecmp(proto, "any") == 0)
+ rtype = ZEBRA_ROUTE_MAX;
+ else
+ rtype = proto_name2num(proto);
+
+ /* deleting an existing entry, it can't be invalid */
+ assert(rtype >= 0);
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ ip_protocol_rm_del(vrf->info, rmap, rtype, afi, safi);
+
+ return NB_OK;
+}
+
+void lib_vrf_zebra_filter_protocol_apply_finish(
+ struct nb_cb_apply_finish_args *args)
+{
+ struct vrf *vrf;
+ const char *afi_safi = yang_dnode_get_string(args->dnode, "afi-safi");
+ const char *proto = yang_dnode_get_string(args->dnode, "protocol");
+ const char *rmap = yang_dnode_get_string(args->dnode, "route-map");
+ afi_t afi;
+ safi_t safi;
+ int rtype;
+
+ yang_afi_safi_identity2value(afi_safi, &afi, &safi);
+
+ if (strcasecmp(proto, "any") == 0)
+ rtype = ZEBRA_ROUTE_MAX;
+ else
+ rtype = proto_name2num(proto);
+
+ /* finishing apply for a validated entry, it can't be invalid */
+ assert(rtype >= 0);
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ ip_protocol_rm_add(vrf->info, rmap, rtype, afi, safi);
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/filter-protocol/route-map
+ */
+int lib_vrf_zebra_filter_protocol_route_map_modify(struct nb_cb_modify_args *args)
+{
+ /* the update is done in the apply_finish callback */
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/filter-nht
+ */
+int lib_vrf_zebra_filter_nht_create(struct nb_cb_create_args *args)
+{
+ const char *afi_safi = yang_dnode_get_string(args->dnode, "afi-safi");
+ const char *proto = yang_dnode_get_string(args->dnode, "protocol");
+ afi_t afi;
+ safi_t safi;
+ int rtype;
+
+ yang_afi_safi_identity2value(afi_safi, &afi, &safi);
+
+ if (strcasecmp(proto, "any") == 0)
+ rtype = ZEBRA_ROUTE_MAX;
+ else
+ rtype = proto_name2num(proto);
+
+ if (args->event == NB_EV_VALIDATE) {
+ if (rtype < 0) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "invalid protocol name \"%s\"", proto);
+ return NB_ERR_VALIDATION;
+ }
+ if (safi != SAFI_UNICAST) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "only SAFI unicast is supported");
+ return NB_ERR_VALIDATION;
+ }
+ }
+
+ /* the creation finishes in the apply_finish callback */
+
+ return NB_OK;
+}
+
+int lib_vrf_zebra_filter_nht_destroy(struct nb_cb_destroy_args *args)
+{
+ struct vrf *vrf;
+ const char *afi_safi = yang_dnode_get_string(args->dnode, "afi-safi");
+ const char *proto = yang_dnode_get_string(args->dnode, "protocol");
+ const char *rmap = yang_dnode_get_string(args->dnode, "route-map");
+ afi_t afi;
+ safi_t safi;
+ int rtype;
+
+ yang_afi_safi_identity2value(afi_safi, &afi, &safi);
+
+ if (strcasecmp(proto, "any") == 0)
+ rtype = ZEBRA_ROUTE_MAX;
+ else
+ rtype = proto_name2num(proto);
+
+ /* deleting an existing entry, it can't be invalid */
+ assert(rtype >= 0);
+ assert(safi == SAFI_UNICAST);
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ ip_nht_rm_del(vrf->info, rmap, rtype, afi);
+
+ return NB_OK;
+}
+
+void lib_vrf_zebra_filter_nht_apply_finish(struct nb_cb_apply_finish_args *args)
+{
+ struct vrf *vrf;
+ const char *afi_safi = yang_dnode_get_string(args->dnode, "afi-safi");
+ const char *proto = yang_dnode_get_string(args->dnode, "protocol");
+ const char *rmap = yang_dnode_get_string(args->dnode, "route-map");
+ afi_t afi;
+ safi_t safi;
+ int rtype;
+
+ yang_afi_safi_identity2value(afi_safi, &afi, &safi);
+
+ if (strcasecmp(proto, "any") == 0)
+ rtype = ZEBRA_ROUTE_MAX;
+ else
+ rtype = proto_name2num(proto);
+
+ /* finishing apply for an existing entry, it can't be invalid */
+ assert(rtype >= 0);
+ assert(safi == SAFI_UNICAST);
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ ip_nht_rm_add(vrf->info, rmap, rtype, afi);
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/filter-nht/route-map
+ */
+int lib_vrf_zebra_filter_nht_route_map_modify(struct nb_cb_modify_args *args)
+{
+ /* the update is done in the apply_finish callback */
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/resolve-via-default
+ */
+int lib_vrf_zebra_resolve_via_default_modify(struct nb_cb_modify_args *args)
+{
+ struct vrf *vrf;
+ struct zebra_vrf *zvrf;
+ bool resolve_via_default;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+ zvrf = vrf->info;
+
+ resolve_via_default = yang_dnode_get_bool(args->dnode, NULL);
+
+ if (zvrf->zebra_rnh_ip_default_route == resolve_via_default)
+ return NB_OK;
+
+ zvrf->zebra_rnh_ip_default_route = resolve_via_default;
+
+ zebra_evaluate_rnh(zvrf, AFI_IP, 0, NULL, SAFI_UNICAST);
+
+ return NB_OK;
+}
+
+int lib_vrf_zebra_resolve_via_default_destroy(struct nb_cb_destroy_args *args)
+{
+ struct vrf *vrf;
+ struct zebra_vrf *zvrf;
+ bool resolve_via_default;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+ zvrf = vrf->info;
+
+ resolve_via_default = DFLT_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT;
+
+ if (zvrf->zebra_rnh_ip_default_route == resolve_via_default)
+ return NB_OK;
+
+ zvrf->zebra_rnh_ip_default_route = resolve_via_default;
+
+ zebra_evaluate_rnh(zvrf, AFI_IP, 0, NULL, SAFI_UNICAST);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/ipv6-resolve-via-default
+ */
+int lib_vrf_zebra_ipv6_resolve_via_default_modify(struct nb_cb_modify_args *args)
+{
+ struct vrf *vrf;
+ struct zebra_vrf *zvrf;
+ bool resolve_via_default;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+ zvrf = vrf->info;
+
+ resolve_via_default = yang_dnode_get_bool(args->dnode, NULL);
+
+ if (zvrf->zebra_rnh_ipv6_default_route == resolve_via_default)
+ return NB_OK;
+
+ zvrf->zebra_rnh_ipv6_default_route = resolve_via_default;
+
+ zebra_evaluate_rnh(zvrf, AFI_IP6, 0, NULL, SAFI_UNICAST);
+
+ return NB_OK;
+}
+
+int lib_vrf_zebra_ipv6_resolve_via_default_destroy(struct nb_cb_destroy_args *args)
+{
+ struct vrf *vrf;
+ struct zebra_vrf *zvrf;
+ bool resolve_via_default;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+ zvrf = vrf->info;
+
+ resolve_via_default = DFLT_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT;
+
+ if (zvrf->zebra_rnh_ipv6_default_route == resolve_via_default)
+ return NB_OK;
+
+ zvrf->zebra_rnh_ipv6_default_route = resolve_via_default;
+
+ zebra_evaluate_rnh(zvrf, AFI_IP6, 0, NULL, SAFI_UNICAST);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/netns/table-range
+ */
+static int table_range_validate(uint32_t start, uint32_t end, char *errmsg,
+ size_t errmsg_len)
+{
+#if defined(GNU_LINUX)
+ if ((start >= RT_TABLE_ID_COMPAT && start <= RT_TABLE_ID_LOCAL) ||
+ (end >= RT_TABLE_ID_COMPAT && end <= RT_TABLE_ID_LOCAL)) {
+ snprintfrr(errmsg, errmsg_len,
+ "Values forbidden in range [%u;%u]",
+ RT_TABLE_ID_COMPAT, RT_TABLE_ID_LOCAL);
+ return NB_ERR_VALIDATION;
+ }
+ if (start < RT_TABLE_ID_COMPAT && end > RT_TABLE_ID_LOCAL) {
+ snprintfrr(errmsg, errmsg_len,
+ "Range overlaps range [%u;%u] forbidden",
+ RT_TABLE_ID_COMPAT, RT_TABLE_ID_LOCAL);
+ return NB_ERR_VALIDATION;
+ }
+#endif
+ return NB_OK;
+}
+
+int lib_vrf_zebra_netns_table_range_create(struct nb_cb_create_args *args)
+{
+ struct vrf *vrf;
+ uint32_t start, end;
+ const char *vrf_name;
+
+ start = yang_dnode_get_uint32(args->dnode, "start");
+ end = yang_dnode_get_uint32(args->dnode, "end");
+
+ if (args->event == NB_EV_VALIDATE) {
+ vrf_name = yang_dnode_get_string(args->dnode, "../../../name");
+ if (!vrf_is_backend_netns() &&
+ strcmp(vrf_name, VRF_DEFAULT_NAME)) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "Configuration is not available in non-default VRFs when using VRF-lite backend.");
return NB_ERR_VALIDATION;
}
+ return table_range_validate(start, end, args->errmsg,
+ args->errmsg_len);
+ }
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ table_manager_range(true, vrf->info, start, end);
+
+ return NB_OK;
+}
+
+int lib_vrf_zebra_netns_table_range_destroy(struct nb_cb_destroy_args *args)
+{
+ struct vrf *vrf;
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ table_manager_range(false, vrf->info, 0, 0);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/netns/table-range/start
+ */
+int lib_vrf_zebra_netns_table_range_start_modify(struct nb_cb_modify_args *args)
+{
+ struct vrf *vrf;
+ uint32_t start, end;
+
+ start = yang_dnode_get_uint32(args->dnode, NULL);
+ end = yang_dnode_get_uint32(args->dnode, "../end");
+ if (args->event == NB_EV_VALIDATE)
+ return table_range_validate(start, end, args->errmsg,
+ args->errmsg_len);
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ table_manager_range(true, vrf->info, start, end);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/netns/table-range/end
+ */
+int lib_vrf_zebra_netns_table_range_end_modify(struct nb_cb_modify_args *args)
+{
+ struct vrf *vrf;
+ uint32_t start, end;
+
+ start = yang_dnode_get_uint32(args->dnode, "../start");
+ end = yang_dnode_get_uint32(args->dnode, NULL);
+
+ if (args->event == NB_EV_VALIDATE)
+ return table_range_validate(start, end, args->errmsg,
+ args->errmsg_len);
+
+ if (args->event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrf = nb_running_get_entry(args->dnode, NULL, true);
+
+ table_manager_range(true, vrf->info, start, end);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:zebra/l3vni-id
+ */
+int lib_vrf_zebra_l3vni_id_modify(struct nb_cb_modify_args *args)
+{
+ struct vrf *vrf;
+ vni_t vni = 0;
+ bool pfx_only = false;
+ uint32_t count;
+
+ vni = yang_dnode_get_uint32(args->dnode, NULL);
+
+ switch (args->event) {
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ return NB_OK;
+ case NB_EV_VALIDATE:
+ count = yang_dnode_count(args->dnode,
+ "/frr-vrf:lib/vrf/frr-zebra:zebra[l3vni-id='%u']",
+ vni);
+ if (count > 1) {
+ snprintfrr(args->errmsg, args->errmsg_len,
+ "vni %u is already mapped to another vrf",
+ vni);
+ return NB_ERR_VALIDATION;
+ }
break;
case NB_EV_APPLY:
-
vrf = nb_running_get_entry(args->dnode, NULL, true);
- zvrf = zebra_vrf_lookup_by_name(vrf->name);
- vni = yang_dnode_get_uint32(args->dnode, NULL);
- /* Note: This covers lib_vrf_zebra_prefix_only_modify() config
- * along with l3vni config
- */
pfx_only = yang_dnode_get_bool(args->dnode, "../prefix-only");
- if (zebra_vxlan_process_vrf_vni_cmd(zvrf, vni, err, ERR_STR_SZ,
- pfx_only ? 1 : 0, 1)
- != 0) {
- if (IS_ZEBRA_DEBUG_VXLAN)
- snprintf(
- args->errmsg, args->errmsg_len,
- "vrf vni %u mapping failed with error: %s",
- vni, err);
- return NB_ERR;
- }
-
+ zebra_vxlan_process_vrf_vni_cmd(vrf->info, vni,
+ pfx_only ? 1 : 0, 1);
break;
}
@@ -1492,10 +3750,7 @@ int lib_vrf_zebra_l3vni_id_modify(struct nb_cb_modify_args *args)
int lib_vrf_zebra_l3vni_id_destroy(struct nb_cb_destroy_args *args)
{
struct vrf *vrf;
- struct zebra_vrf *zvrf;
vni_t vni = 0;
- char err[ERR_STR_SZ];
- uint8_t filter = 0;
switch (args->event) {
case NB_EV_PREPARE:
@@ -1504,32 +3759,9 @@ int lib_vrf_zebra_l3vni_id_destroy(struct nb_cb_destroy_args *args)
return NB_OK;
case NB_EV_APPLY:
vrf = nb_running_get_entry(args->dnode, NULL, true);
- zvrf = zebra_vrf_lookup_by_name(vrf->name);
vni = yang_dnode_get_uint32(args->dnode, NULL);
- if (!zl3vni_lookup(vni))
- return NB_OK;
-
- if (zvrf->l3vni != vni) {
- snprintf(args->errmsg, args->errmsg_len,
- "vrf %s has different vni %u mapped",
- vrf->name, zvrf->l3vni);
- return NB_ERR;
- }
-
- if (is_l3vni_for_prefix_routes_only(zvrf->l3vni))
- filter = 1;
-
- if (zebra_vxlan_process_vrf_vni_cmd(zvrf, vni, err, ERR_STR_SZ,
- filter, 0)
- != 0) {
- if (IS_ZEBRA_DEBUG_VXLAN)
- zlog_debug(
- "vrf vni %u unmapping failed with error: %s",
- vni, err);
- return NB_ERR;
- }
-
+ zebra_vxlan_process_vrf_vni_cmd(vrf->info, vni, 0, 0);
break;
}
diff --git a/zebra/zebra_ns.c b/zebra/zebra_ns.c
index f74b30a6ce..803d8f0034 100644
--- a/zebra/zebra_ns.c
+++ b/zebra/zebra_ns.c
@@ -238,10 +238,3 @@ int zebra_ns_init(void)
return 0;
}
-
-int zebra_ns_config_write(struct vty *vty, struct ns *ns)
-{
- if (ns && ns->name != NULL)
- vty_out(vty, " netns %s\n", ns->name);
- return 0;
-}
diff --git a/zebra/zebra_ns.h b/zebra/zebra_ns.h
index 55cbb95528..8d988c3f82 100644
--- a/zebra/zebra_ns.h
+++ b/zebra/zebra_ns.h
@@ -70,7 +70,6 @@ int zebra_ns_early_shutdown(struct ns *ns,
int zebra_ns_final_shutdown(struct ns *ns,
void *param_in __attribute__((unused)),
void **param_out __attribute__((unused)));
-int zebra_ns_config_write(struct vty *vty, struct ns *ns);
void zebra_ns_startup_continue(struct zebra_dplane_ctx *ctx);
diff --git a/zebra/zebra_ptm.c b/zebra/zebra_ptm.c
index 40630d7890..d7d752f01e 100644
--- a/zebra/zebra_ptm.c
+++ b/zebra/zebra_ptm.c
@@ -86,7 +86,6 @@ struct zebra_ptm_cb ptm_cb;
static int zebra_ptm_socket_init(void);
void zebra_ptm_sock_read(struct event *thread);
-static void zebra_ptm_install_commands(void);
static int zebra_ptm_handle_msg_cb(void *arg, void *in_ctxt);
void zebra_bfd_peer_replay_req(void);
void zebra_ptm_send_status_req(void);
@@ -115,7 +114,6 @@ void zebra_ptm_init(void)
}
ptm_cb.pid = getpid();
- zebra_ptm_install_commands();
snprintf(buf, sizeof(buf), "%s", FRR_PTM_NAME);
ptm_hdl = ptm_lib_register(buf, NULL, zebra_ptm_handle_msg_cb,
@@ -240,10 +238,7 @@ void zebra_ptm_connect(struct event *t)
}
}
-DEFUN (zebra_ptm_enable,
- zebra_ptm_enable_cmd,
- "ptm-enable",
- "Enable neighbor check with specified topology\n")
+void zebra_global_ptm_enable(void)
{
struct vrf *vrf;
struct interface *ifp;
@@ -266,27 +261,16 @@ DEFUN (zebra_ptm_enable,
}
zebra_ptm_connect(NULL);
-
- return CMD_SUCCESS;
}
-DEFUN (no_zebra_ptm_enable,
- no_zebra_ptm_enable_cmd,
- "no ptm-enable",
- NO_STR
- "Enable neighbor check with specified topology\n")
+void zebra_global_ptm_disable(void)
{
ptm_cb.ptm_enable = ZEBRA_IF_PTM_ENABLE_OFF;
zebra_ptm_reset_status(1);
- return CMD_SUCCESS;
}
-DEFUN (zebra_ptm_enable_if,
- zebra_ptm_enable_if_cmd,
- "ptm-enable",
- "Enable neighbor check with specified topology\n")
+void zebra_if_ptm_enable(struct interface *ifp)
{
- VTY_DECLVAR_CONTEXT(interface, ifp);
struct zebra_if *if_data;
int old_ptm_enable;
int send_linkdown = 0;
@@ -295,7 +279,7 @@ DEFUN (zebra_ptm_enable_if,
if_data->ptm_enable = ZEBRA_IF_PTM_ENABLE_UNSPEC;
if (ifp->ifindex == IFINDEX_INTERNAL) {
- return CMD_SUCCESS;
+ return;
}
old_ptm_enable = ifp->ptm_enable;
@@ -312,19 +296,12 @@ DEFUN (zebra_ptm_enable_if,
if_down(ifp);
}
}
-
- return CMD_SUCCESS;
}
-DEFUN (no_zebra_ptm_enable_if,
- no_zebra_ptm_enable_if_cmd,
- "no ptm-enable",
- NO_STR
- "Enable neighbor check with specified topology\n")
+void zebra_if_ptm_disable(struct interface *ifp)
{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- int send_linkup = 0;
struct zebra_if *if_data;
+ int send_linkup = 0;
if ((ifp->ifindex != IFINDEX_INTERNAL) && (ifp->ptm_enable)) {
if (!if_is_operative(ifp))
@@ -341,17 +318,6 @@ DEFUN (no_zebra_ptm_enable_if,
if_data = ifp->info;
if_data->ptm_enable = ZEBRA_IF_PTM_ENABLE_OFF;
-
- return CMD_SUCCESS;
-}
-
-
-void zebra_ptm_write(struct vty *vty)
-{
- if (ptm_cb.ptm_enable)
- vty_out(vty, "ptm-enable\n");
-
- return;
}
static int zebra_ptm_socket_init(void)
@@ -394,14 +360,6 @@ static int zebra_ptm_socket_init(void)
return sock;
}
-static void zebra_ptm_install_commands(void)
-{
- install_element(CONFIG_NODE, &zebra_ptm_enable_cmd);
- install_element(CONFIG_NODE, &no_zebra_ptm_enable_cmd);
- install_element(INTERFACE_NODE, &zebra_ptm_enable_if_cmd);
- install_element(INTERFACE_NODE, &no_zebra_ptm_enable_if_cmd);
-}
-
/* BFD session goes down, send message to the protocols. */
static void if_bfd_session_update(struct interface *ifp, struct prefix *dp,
struct prefix *sp, int status,
@@ -1165,12 +1123,6 @@ void zebra_ptm_if_set_ptm_state(struct interface *ifp,
ifp->ptm_enable = zebra_ifp->ptm_enable;
}
-void zebra_ptm_if_write(struct vty *vty, struct zebra_if *zebra_ifp)
-{
- if (zebra_ifp->ptm_enable == ZEBRA_IF_PTM_ENABLE_OFF)
- vty_out(vty, " no ptm-enable\n");
-}
-
#else /* HAVE_BFDD */
/*
@@ -1533,16 +1485,6 @@ void zebra_ptm_show_status(struct vty *vty __attribute__((__unused__)),
/* NOTHING */
}
-void zebra_ptm_write(struct vty *vty __attribute__((__unused__)))
-{
- /* NOTHING */
-}
-
-void zebra_ptm_if_write(struct vty *vty __attribute__((__unused__)),
- struct zebra_if *zifp __attribute__((__unused__)))
-{
- /* NOTHING */
-}
void zebra_ptm_if_set_ptm_state(struct interface *i __attribute__((__unused__)),
struct zebra_if *zi __attribute__((__unused__)))
{
diff --git a/zebra/zebra_ptm.h b/zebra/zebra_ptm.h
index 4d09474b7f..20a53e2fea 100644
--- a/zebra/zebra_ptm.h
+++ b/zebra/zebra_ptm.h
@@ -58,9 +58,15 @@ struct zebra_ptm_cb {
void zebra_ptm_init(void);
void zebra_ptm_finish(void);
void zebra_ptm_connect(struct event *t);
-void zebra_ptm_write(struct vty *vty);
int zebra_ptm_get_enable_state(void);
+#if HAVE_BFDD == 0
+void zebra_global_ptm_enable(void);
+void zebra_global_ptm_disable(void);
+void zebra_if_ptm_enable(struct interface *ifp);
+void zebra_if_ptm_disable(struct interface *ifp);
+#endif
+
/* ZAPI message handlers */
void zebra_ptm_bfd_dst_register(ZAPI_HANDLER_ARGS);
void zebra_ptm_bfd_dst_deregister(ZAPI_HANDLER_ARGS);
@@ -74,7 +80,6 @@ void zebra_ptm_show_status(struct vty *vty, json_object *json,
void zebra_ptm_if_init(struct zebra_if *zebra_ifp);
void zebra_ptm_if_set_ptm_state(struct interface *ifp,
struct zebra_if *zebra_ifp);
-void zebra_ptm_if_write(struct vty *vty, struct zebra_if *zebra_ifp);
#ifdef __cplusplus
}
diff --git a/zebra/zebra_routemap.c b/zebra/zebra_routemap.c
index 21aaf1d066..95da789108 100644
--- a/zebra/zebra_routemap.c
+++ b/zebra/zebra_routemap.c
@@ -14,7 +14,6 @@
#include "filter.h"
#include "plist.h"
#include "nexthop.h"
-#include "northbound_cli.h"
#include "lib/route_types.h"
#include "vrf.h"
#include "frrstr.h"
@@ -24,6 +23,7 @@
#include "zebra/debug.h"
#include "zebra/zebra_rnh.h"
#include "zebra/zebra_routemap.h"
+#include "zebra/zebra_vrf.h"
#include "zebra/zebra_routemap_clippy.c"
@@ -36,8 +36,6 @@ struct zebra_rmap_obj {
struct route_entry *re;
};
-static void zebra_route_map_set_delay_timer(uint32_t value);
-
/* 'match tag TAG'
* Match function return 1 if match is success else return 0
*/
@@ -284,8 +282,8 @@ static const struct route_map_rule_cmd route_match_interface_cmd = {
route_match_interface_free
};
-static int ip_protocol_rm_add(struct zebra_vrf *zvrf, const char *rmap,
- int rtype, afi_t afi, safi_t safi)
+int ip_protocol_rm_add(struct zebra_vrf *zvrf, const char *rmap, int rtype,
+ afi_t afi, safi_t safi)
{
struct route_table *table;
@@ -317,8 +315,8 @@ static int ip_protocol_rm_add(struct zebra_vrf *zvrf, const char *rmap,
return CMD_SUCCESS;
}
-static int ip_protocol_rm_del(struct zebra_vrf *zvrf, const char *rmap,
- int rtype, afi_t afi, safi_t safi)
+int ip_protocol_rm_del(struct zebra_vrf *zvrf, const char *rmap, int rtype,
+ afi_t afi, safi_t safi)
{
struct route_table *table;
@@ -346,8 +344,7 @@ static int ip_protocol_rm_del(struct zebra_vrf *zvrf, const char *rmap,
return CMD_SUCCESS;
}
-static int ip_nht_rm_add(struct zebra_vrf *zvrf, const char *rmap, int rtype,
- int afi)
+int ip_nht_rm_add(struct zebra_vrf *zvrf, const char *rmap, int rtype, int afi)
{
if (NHT_RM_NAME(zvrf, afi, rtype)) {
@@ -368,8 +365,7 @@ static int ip_nht_rm_add(struct zebra_vrf *zvrf, const char *rmap, int rtype,
return CMD_SUCCESS;
}
-static int ip_nht_rm_del(struct zebra_vrf *zvrf, const char *rmap, int rtype,
- int afi)
+int ip_nht_rm_del(struct zebra_vrf *zvrf, const char *rmap, int rtype, int afi)
{
if (!NHT_RM_NAME(zvrf, afi, rtype))
@@ -391,351 +387,7 @@ static int ip_nht_rm_del(struct zebra_vrf *zvrf, const char *rmap, int rtype,
return CMD_SUCCESS;
}
-DEFPY_YANG(
- match_ip_address_prefix_len, match_ip_address_prefix_len_cmd,
- "match ip address prefix-len (0-32)$length",
- MATCH_STR
- IP_STR
- "Match prefix length of IP address\n"
- "Match prefix length of IP address\n"
- "Prefix length\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:ipv4-prefix-length']";
- char xpath_value[XPATH_MAXLEN];
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
- snprintf(
- xpath_value, sizeof(xpath_value),
- "%s/rmap-match-condition/frr-zebra-route-map:ipv4-prefix-length",
- xpath);
- nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, length_str);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- no_match_ip_address_prefix_len, no_match_ip_address_prefix_len_cmd,
- "no match ip address prefix-len [(0-32)]",
- NO_STR
- MATCH_STR
- IP_STR
- "Match prefix length of IP address\n"
- "Match prefix length of IP address\n"
- "Prefix length\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:ipv4-prefix-length']";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- match_ipv6_address_prefix_len, match_ipv6_address_prefix_len_cmd,
- "match ipv6 address prefix-len (0-128)$length",
- MATCH_STR
- IPV6_STR
- "Match prefix length of IPv6 address\n"
- "Match prefix length of IPv6 address\n"
- "Prefix length\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:ipv6-prefix-length']";
- char xpath_value[XPATH_MAXLEN];
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
- snprintf(
- xpath_value, sizeof(xpath_value),
- "%s/rmap-match-condition/frr-zebra-route-map:ipv6-prefix-length",
- xpath);
- nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, length_str);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- no_match_ipv6_address_prefix_len, no_match_ipv6_address_prefix_len_cmd,
- "no match ipv6 address prefix-len [(0-128)]",
- NO_STR
- MATCH_STR
- IPV6_STR
- "Match prefix length of IPv6 address\n"
- "Match prefix length of IPv6 address\n"
- "Prefix length\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:ipv6-prefix-length']";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- match_ip_nexthop_prefix_len, match_ip_nexthop_prefix_len_cmd,
- "match ip next-hop prefix-len (0-32)$length",
- MATCH_STR
- IP_STR
- "Match prefixlen of nexthop IP address\n"
- "Match prefixlen of given nexthop\n"
- "Prefix length\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:ipv4-next-hop-prefix-length']";
- char xpath_value[XPATH_MAXLEN];
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
- snprintf(
- xpath_value, sizeof(xpath_value),
- "%s/rmap-match-condition/frr-zebra-route-map:ipv4-prefix-length",
- xpath);
- nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, length_str);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- no_match_ip_nexthop_prefix_len, no_match_ip_nexthop_prefix_len_cmd,
- "no match ip next-hop prefix-len [(0-32)]",
- NO_STR
- MATCH_STR
- IP_STR
- "Match prefixlen of nexthop IP address\n"
- "Match prefix length of nexthop\n"
- "Prefix length\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:ipv4-next-hop-prefix-length']";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- match_source_protocol, match_source_protocol_cmd,
- "match source-protocol " FRR_REDIST_STR_ZEBRA "$proto",
- MATCH_STR
- "Match protocol via which the route was learnt\n"
- FRR_REDIST_HELP_STR_ZEBRA)
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:source-protocol']";
- char xpath_value[XPATH_MAXLEN];
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
- snprintf(xpath_value, sizeof(xpath_value),
- "%s/rmap-match-condition/frr-zebra-route-map:source-protocol",
- xpath);
- nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, proto);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- no_match_source_protocol, no_match_source_protocol_cmd,
- "no match source-protocol [" FRR_REDIST_STR_ZEBRA "]",
- NO_STR
- MATCH_STR
- "Match protocol via which the route was learnt\n"
- FRR_REDIST_HELP_STR_ZEBRA)
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:source-protocol']";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- match_source_instance, match_source_instance_cmd,
- "match source-instance (0-255)$instance",
- MATCH_STR
- "Match the protocol's instance number\n"
- "The instance number\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:source-instance']";
- char xpath_value[XPATH_MAXLEN];
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
- snprintf(xpath_value, sizeof(xpath_value),
- "%s/rmap-match-condition/frr-zebra-route-map:source-instance",
- xpath);
- nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY, instance_str);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- no_match_source_instance, no_match_source_instance_cmd,
- "no match source-instance [(0-255)]",
- NO_STR MATCH_STR
- "Match the protocol's instance number\n"
- "The instance number\n")
-{
- const char *xpath =
- "./match-condition[condition='frr-zebra-route-map:source-instance']";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-/* set functions */
-
-DEFPY_YANG(
- set_src, set_src_cmd,
- "set src <A.B.C.D$addrv4|X:X::X:X$addrv6>",
- SET_STR
- "src address for route\n"
- "IPv4 src address\n"
- "IPv6 src address\n")
-{
- const char *xpath =
- "./set-action[action='frr-zebra-route-map:src-address']";
- char xpath_value[XPATH_MAXLEN];
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
- if (addrv4_str) {
- snprintf(
- xpath_value, sizeof(xpath_value),
- "%s/rmap-set-action/frr-zebra-route-map:ipv4-src-address",
- xpath);
- nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY,
- addrv4_str);
- } else {
- snprintf(
- xpath_value, sizeof(xpath_value),
- "%s/rmap-set-action/frr-zebra-route-map:ipv6-src-address",
- xpath);
- nb_cli_enqueue_change(vty, xpath_value, NB_OP_MODIFY,
- addrv6_str);
- }
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFPY_YANG(
- no_set_src, no_set_src_cmd,
- "no set src [<A.B.C.D|X:X::X:X>]",
- NO_STR
- SET_STR
- "Source address for route\n"
- "IPv4 address\n"
- "IPv6 address\n")
-{
- const char *xpath =
- "./set-action[action='frr-zebra-route-map:src-address']";
-
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFUN_YANG (zebra_route_map_timer,
- zebra_route_map_timer_cmd,
- "zebra route-map delay-timer (0-600)",
- ZEBRA_STR
- "Set route-map parameters\n"
- "Time to wait before route-map updates are processed\n"
- "0 means route-map changes are run immediately instead of delaying\n")
-{
- int idx_number = 3;
- uint32_t rmap_delay_timer;
-
- rmap_delay_timer = strtoul(argv[idx_number]->arg, NULL, 10);
- zebra_route_map_set_delay_timer(rmap_delay_timer);
-
- return (CMD_SUCCESS);
-}
-
-DEFUN_YANG (no_zebra_route_map_timer,
- no_zebra_route_map_timer_cmd,
- "no zebra route-map delay-timer [(0-600)]",
- NO_STR
- ZEBRA_STR
- "Set route-map parameters\n"
- "Reset delay-timer to default value, 30 secs\n"
- "0 means route-map changes are run immediately instead of delaying\n")
-{
- zebra_route_map_set_delay_timer(ZEBRA_RMAP_DEFAULT_UPDATE_TIMER);
-
- return (CMD_SUCCESS);
-}
-
-DEFPY_YANG (ip_protocol,
- ip_protocol_cmd,
- "ip protocol " FRR_IP_PROTOCOL_MAP_STR_ZEBRA
- " $proto route-map ROUTE-MAP$rmap",
- IP_STR
- "Filter routing info exchanged between zebra and protocol\n"
- FRR_IP_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route-map\n"
- "Route map name\n")
-{
- int ret, rtype;
-
- assert(proto);
- assert(rmap);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_protocol_rm_add(zvrf, rmap, rtype, AFI_IP, SAFI_UNICAST);
-
- return ret;
-}
-
-DEFPY_YANG (no_ip_protocol,
- no_ip_protocol_cmd,
- "no ip protocol " FRR_IP_PROTOCOL_MAP_STR_ZEBRA
- " $proto [route-map ROUTE-MAP$rmap]",
- NO_STR
- IP_STR
- "Stop filtering routing info between zebra and protocol\n"
- FRR_IP_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route-map\n"
- "Route map name\n")
-{
- int ret, rtype;
-
- assert(proto);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_protocol_rm_del(zvrf, rmap, rtype, AFI_IP, SAFI_UNICAST);
-
- return ret;
-}
-
-DEFPY_YANG (show_ip_protocol,
+DEFPY (show_ip_protocol,
show_ip_protocol_cmd,
"show ip protocol [vrf <NAME$vrf_name|all$vrf_all>]",
SHOW_STR
@@ -748,75 +400,7 @@ DEFPY_YANG (show_ip_protocol,
return ret;
}
-DEFPY_YANG (ipv6_protocol,
- ipv6_protocol_cmd,
- "ipv6 protocol " FRR_IP6_PROTOCOL_MAP_STR_ZEBRA
- " $proto route-map ROUTE-MAP$rmap",
- IP6_STR
- "Filter IPv6 routing info exchanged between zebra and protocol\n"
- FRR_IP6_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route-map\n"
- "Route map name\n")
-{
- int ret, rtype;
-
- assert(rmap);
- assert(proto);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_protocol_rm_add(zvrf, rmap, rtype, AFI_IP6, SAFI_UNICAST);
-
- return ret;
-}
-
-DEFPY_YANG (no_ipv6_protocol,
- no_ipv6_protocol_cmd,
- "no ipv6 protocol " FRR_IP6_PROTOCOL_MAP_STR_ZEBRA
- " $proto [route-map ROUTE-MAP$rmap]",
- NO_STR
- IP6_STR
- "Stop filtering IPv6 routing info between zebra and protocol\n"
- FRR_IP6_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route-map\n"
- "Route map name\n")
-{
- int ret, rtype;
-
- assert(proto);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_protocol_rm_del(zvrf, rmap, rtype, AFI_IP6, SAFI_UNICAST);
-
- return ret;
-}
-
-DEFPY_YANG (show_ipv6_protocol,
+DEFPY (show_ipv6_protocol,
show_ipv6_protocol_cmd,
"show ipv6 protocol [vrf <NAME$vrf_name|all$vrf_all>]",
SHOW_STR
@@ -829,76 +413,7 @@ DEFPY_YANG (show_ipv6_protocol,
return ret;
}
-DEFPY_YANG (ip_protocol_nht_rmap,
- ip_protocol_nht_rmap_cmd,
- "ip nht " FRR_IP_PROTOCOL_MAP_STR_ZEBRA
- " $proto route-map ROUTE-MAP$rmap",
- IP_STR
- "Filter Next Hop tracking route resolution\n"
- FRR_IP_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route map\n"
- "Route map name\n")
-{
-
- int ret, rtype;
-
- assert(proto);
- assert(rmap);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_nht_rm_add(zvrf, rmap, rtype, AFI_IP);
-
- return ret;
-}
-
-DEFPY_YANG (no_ip_protocol_nht_rmap,
- no_ip_protocol_nht_rmap_cmd,
- "no ip nht " FRR_IP_PROTOCOL_MAP_STR_ZEBRA
- " $proto route-map [ROUTE-MAP$rmap]",
- NO_STR
- IP_STR
- "Filter Next Hop tracking route resolution\n"
- FRR_IP_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route map\n"
- "Route map name\n")
-{
- int ret, rtype;
-
- assert(proto);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_nht_rm_del(zvrf, rmap, rtype, AFI_IP);
-
- return ret;
-}
-
-DEFPY_YANG (show_ip_protocol_nht,
+DEFPY (show_ip_protocol_nht,
show_ip_protocol_nht_cmd,
"show ip nht route-map [vrf <NAME$vrf_name|all$vrf_all>] [json]",
SHOW_STR
@@ -917,75 +432,7 @@ DEFPY_YANG (show_ip_protocol_nht,
return ret;
}
-DEFPY_YANG (ipv6_protocol_nht_rmap,
- ipv6_protocol_nht_rmap_cmd,
- "ipv6 nht " FRR_IP6_PROTOCOL_MAP_STR_ZEBRA
- " $proto route-map ROUTE-MAP$rmap",
- IP6_STR
- "Filter Next Hop tracking route resolution\n"
- FRR_IP6_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route map\n"
- "Route map name\n")
-{
- int ret, rtype;
-
- assert(rmap);
- assert(proto);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_nht_rm_add(zvrf, rmap, rtype, AFI_IP6);
-
- return ret;
-}
-
-DEFPY_YANG (no_ipv6_protocol_nht_rmap,
- no_ipv6_protocol_nht_rmap_cmd,
- "no ipv6 nht " FRR_IP6_PROTOCOL_MAP_STR_ZEBRA
- " $proto [route-map ROUTE-MAP$rmap]",
- NO_STR
- IP6_STR
- "Filter Next Hop tracking route resolution\n"
- FRR_IP6_PROTOCOL_MAP_HELP_STR_ZEBRA
- "Specify route map\n"
- "Route map name\n")
-{
- int ret, rtype;
-
- assert(proto);
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (strcasecmp(proto, "any") == 0)
- rtype = ZEBRA_ROUTE_MAX;
- else
- rtype = proto_name2num(proto);
- if (rtype < 0) {
- vty_out(vty, "invalid protocol name \"%s\"\n", proto);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ret = ip_nht_rm_del(zvrf, rmap, rtype, AFI_IP6);
-
- return ret;
-}
-
-DEFPY_YANG (show_ipv6_protocol_nht,
+DEFPY (show_ipv6_protocol_nht,
show_ipv6_protocol_nht_cmd,
"show ipv6 nht route-map [vrf <NAME$vrf_name|all$vrf_all>] [json]",
SHOW_STR
@@ -1736,7 +1183,7 @@ static void zebra_route_map_update_timer(struct event *thread)
*/
}
-static void zebra_route_map_set_delay_timer(uint32_t value)
+void zebra_route_map_set_delay_timer(uint32_t value)
{
zebra_rmap_update_timer = value;
if (!value && zebra_t_rmap_update) {
@@ -1903,88 +1350,14 @@ void zebra_routemap_vrf_delete(struct zebra_vrf *zvrf)
}
}
-/* ip protocol configuration write function */
-void zebra_routemap_config_write_protocol(struct vty *vty,
- struct zebra_vrf *zvrf)
-{
- int i;
- char space[2];
-
- memset(space, 0, sizeof(space));
-
- if (zvrf_id(zvrf) != VRF_DEFAULT)
- snprintf(space, sizeof(space), "%s", " ");
-
- for (i = 0; i < ZEBRA_ROUTE_MAX; i++) {
- if (PROTO_RM_NAME(zvrf, AFI_IP, i))
- vty_out(vty, "%sip protocol %s route-map %s\n", space,
- zebra_route_string(i),
- PROTO_RM_NAME(zvrf, AFI_IP, i));
-
- if (PROTO_RM_NAME(zvrf, AFI_IP6, i))
- vty_out(vty, "%sipv6 protocol %s route-map %s\n", space,
- zebra_route_string(i),
- PROTO_RM_NAME(zvrf, AFI_IP6, i));
-
- if (NHT_RM_NAME(zvrf, AFI_IP, i))
- vty_out(vty, "%sip nht %s route-map %s\n", space,
- zebra_route_string(i),
- NHT_RM_NAME(zvrf, AFI_IP, i));
-
- if (NHT_RM_NAME(zvrf, AFI_IP6, i))
- vty_out(vty, "%sipv6 nht %s route-map %s\n", space,
- zebra_route_string(i),
- NHT_RM_NAME(zvrf, AFI_IP6, i));
- }
-
- if (PROTO_RM_NAME(zvrf, AFI_IP, ZEBRA_ROUTE_MAX))
- vty_out(vty, "%sip protocol %s route-map %s\n", space, "any",
- PROTO_RM_NAME(zvrf, AFI_IP, ZEBRA_ROUTE_MAX));
-
- if (PROTO_RM_NAME(zvrf, AFI_IP6, ZEBRA_ROUTE_MAX))
- vty_out(vty, "%sipv6 protocol %s route-map %s\n", space, "any",
- PROTO_RM_NAME(zvrf, AFI_IP6, ZEBRA_ROUTE_MAX));
-
- if (NHT_RM_NAME(zvrf, AFI_IP, ZEBRA_ROUTE_MAX))
- vty_out(vty, "%sip nht %s route-map %s\n", space, "any",
- NHT_RM_NAME(zvrf, AFI_IP, ZEBRA_ROUTE_MAX));
-
- if (NHT_RM_NAME(zvrf, AFI_IP6, ZEBRA_ROUTE_MAX))
- vty_out(vty, "%sipv6 nht %s route-map %s\n", space, "any",
- NHT_RM_NAME(zvrf, AFI_IP6, ZEBRA_ROUTE_MAX));
-
- if (zvrf_id(zvrf) == VRF_DEFAULT
- && zebra_rmap_update_timer != ZEBRA_RMAP_DEFAULT_UPDATE_TIMER)
- vty_out(vty, "zebra route-map delay-timer %d\n",
- zebra_rmap_update_timer);
-}
-
void zebra_route_map_init(void)
{
- install_element(CONFIG_NODE, &ip_protocol_cmd);
- install_element(CONFIG_NODE, &no_ip_protocol_cmd);
- install_element(VRF_NODE, &ip_protocol_cmd);
- install_element(VRF_NODE, &no_ip_protocol_cmd);
install_element(VIEW_NODE, &show_ip_protocol_cmd);
- install_element(CONFIG_NODE, &ipv6_protocol_cmd);
- install_element(CONFIG_NODE, &no_ipv6_protocol_cmd);
- install_element(VRF_NODE, &ipv6_protocol_cmd);
- install_element(VRF_NODE, &no_ipv6_protocol_cmd);
install_element(VIEW_NODE, &show_ipv6_protocol_cmd);
- install_element(CONFIG_NODE, &ip_protocol_nht_rmap_cmd);
- install_element(CONFIG_NODE, &no_ip_protocol_nht_rmap_cmd);
- install_element(VRF_NODE, &ip_protocol_nht_rmap_cmd);
- install_element(VRF_NODE, &no_ip_protocol_nht_rmap_cmd);
install_element(VIEW_NODE, &show_ip_protocol_nht_cmd);
- install_element(CONFIG_NODE, &ipv6_protocol_nht_rmap_cmd);
- install_element(CONFIG_NODE, &no_ipv6_protocol_nht_rmap_cmd);
- install_element(VRF_NODE, &ipv6_protocol_nht_rmap_cmd);
- install_element(VRF_NODE, &no_ipv6_protocol_nht_rmap_cmd);
install_element(VIEW_NODE, &show_ipv6_protocol_nht_cmd);
- install_element(CONFIG_NODE, &zebra_route_map_timer_cmd);
- install_element(CONFIG_NODE, &no_zebra_route_map_timer_cmd);
- route_map_init();
+ route_map_init_new(true);
route_map_add_hook(zebra_route_map_add);
route_map_delete_hook(zebra_route_map_delete);
@@ -2038,19 +1411,4 @@ void zebra_route_map_init(void)
/* */
route_map_install_set(&route_set_src_cmd);
- /* */
- install_element(RMAP_NODE, &match_ip_nexthop_prefix_len_cmd);
- install_element(RMAP_NODE, &no_match_ip_nexthop_prefix_len_cmd);
- install_element(RMAP_NODE, &match_ip_address_prefix_len_cmd);
- install_element(RMAP_NODE, &match_ipv6_address_prefix_len_cmd);
- install_element(RMAP_NODE, &no_match_ipv6_address_prefix_len_cmd);
- install_element(RMAP_NODE, &no_match_ip_address_prefix_len_cmd);
- install_element(RMAP_NODE, &match_source_protocol_cmd);
- install_element(RMAP_NODE, &no_match_source_protocol_cmd);
- install_element(RMAP_NODE, &match_source_instance_cmd);
- install_element(RMAP_NODE, &no_match_source_instance_cmd);
-
- /* */
- install_element(RMAP_NODE, &set_src_cmd);
- install_element(RMAP_NODE, &no_set_src_cmd);
}
diff --git a/zebra/zebra_routemap.h b/zebra/zebra_routemap.h
index fceb53c841..2039e80e3a 100644
--- a/zebra/zebra_routemap.h
+++ b/zebra/zebra_routemap.h
@@ -14,8 +14,6 @@ extern "C" {
#endif
extern void zebra_route_map_init(void);
-extern void zebra_routemap_config_write_protocol(struct vty *vty,
- struct zebra_vrf *vrf);
extern char *zebra_get_import_table_route_map(afi_t afi, uint32_t table);
extern void zebra_add_import_table_route_map(afi_t afi, const char *rmap_name,
uint32_t table);
@@ -35,6 +33,16 @@ extern route_map_result_t zebra_nht_route_map_check(afi_t afi, int client_proto,
struct route_entry *re,
struct nexthop *nexthop);
+extern void zebra_route_map_set_delay_timer(uint32_t value);
+extern int ip_protocol_rm_add(struct zebra_vrf *zvrf, const char *rmap,
+ int rtype, afi_t afi, safi_t safi);
+extern int ip_protocol_rm_del(struct zebra_vrf *zvrf, const char *rmap,
+ int rtype, afi_t afi, safi_t safi);
+extern int ip_nht_rm_add(struct zebra_vrf *zvrf, const char *rmap, int rtype,
+ int afi);
+extern int ip_nht_rm_del(struct zebra_vrf *zvrf, const char *rmap, int rtype,
+ int afi);
+
extern void zebra_routemap_vrf_delete(struct zebra_vrf *zvrf);
#ifdef __cplusplus
diff --git a/zebra/zebra_vrf.c b/zebra/zebra_vrf.c
index 92982f25c8..e464e47b1f 100644
--- a/zebra/zebra_vrf.c
+++ b/zebra/zebra_vrf.c
@@ -450,141 +450,6 @@ struct route_table *zebra_vrf_table(afi_t afi, safi_t safi, vrf_id_t vrf_id)
return zvrf->table[afi][safi];
}
-static int vrf_config_write(struct vty *vty)
-{
- struct vrf *vrf;
- struct zebra_vrf *zvrf;
-
- RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
- zvrf = vrf->info;
-
- if (!zvrf)
- continue;
-
- if (zvrf_id(zvrf) == VRF_DEFAULT) {
- if (zvrf->l3vni)
- vty_out(vty, "vni %u%s\n", zvrf->l3vni,
- is_l3vni_for_prefix_routes_only(
- zvrf->l3vni)
- ? " prefix-routes-only"
- : "");
-
- if (zvrf->zebra_rnh_ip_default_route !=
- SAVE_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT)
- vty_out(vty, "%sip nht resolve-via-default\n",
- zvrf->zebra_rnh_ip_default_route
- ? ""
- : "no ");
-
- if (zvrf->zebra_rnh_ipv6_default_route !=
- SAVE_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT)
- vty_out(vty, "%sipv6 nht resolve-via-default\n",
- zvrf->zebra_rnh_ipv6_default_route
- ? ""
- : "no ");
-
- if (zvrf->tbl_mgr
- && (zvrf->tbl_mgr->start || zvrf->tbl_mgr->end))
- vty_out(vty, "ip table range %u %u\n",
- zvrf->tbl_mgr->start,
- zvrf->tbl_mgr->end);
- } else {
- vty_frame(vty, "vrf %s\n", zvrf_name(zvrf));
- if (zvrf->l3vni)
- vty_out(vty, " vni %u%s\n", zvrf->l3vni,
- is_l3vni_for_prefix_routes_only(
- zvrf->l3vni)
- ? " prefix-routes-only"
- : "");
- zebra_ns_config_write(vty, (struct ns *)vrf->ns_ctxt);
- if (zvrf->zebra_rnh_ip_default_route !=
- SAVE_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT)
- vty_out(vty, " %sip nht resolve-via-default\n",
- zvrf->zebra_rnh_ip_default_route
- ? ""
- : "no ");
-
- if (zvrf->zebra_rnh_ipv6_default_route !=
- SAVE_ZEBRA_IP_NHT_RESOLVE_VIA_DEFAULT)
- vty_out(vty, " %sipv6 nht resolve-via-default\n",
- zvrf->zebra_rnh_ipv6_default_route
- ? ""
- : "no ");
-
- if (zvrf->tbl_mgr && vrf_is_backend_netns()
- && (zvrf->tbl_mgr->start || zvrf->tbl_mgr->end))
- vty_out(vty, " ip table range %u %u\n",
- zvrf->tbl_mgr->start,
- zvrf->tbl_mgr->end);
- }
-
-
- zebra_routemap_config_write_protocol(vty, zvrf);
- router_id_write(vty, zvrf);
-
- if (zvrf_id(zvrf) != VRF_DEFAULT)
- vty_endframe(vty, "exit-vrf\n!\n");
- else
- vty_out(vty, "!\n");
- }
- return 0;
-}
-
-DEFPY (vrf_netns,
- vrf_netns_cmd,
- "netns NAME$netns_name",
- "Attach VRF to a Namespace\n"
- "The file name in " NS_RUN_DIR ", or a full pathname\n")
-{
- char *pathname = ns_netns_pathname(vty, netns_name);
- int ret;
-
- VTY_DECLVAR_CONTEXT(vrf, vrf);
-
- if (!pathname)
- return CMD_WARNING_CONFIG_FAILED;
-
- frr_with_privs(&zserv_privs) {
- ret = zebra_vrf_netns_handler_create(
- vty, vrf, pathname, NS_UNKNOWN, NS_UNKNOWN, NS_UNKNOWN);
- }
-
- return ret;
-}
-
-DEFUN (no_vrf_netns,
- no_vrf_netns_cmd,
- "no netns [NAME]",
- NO_STR
- "Detach VRF from a Namespace\n"
- "The file name in " NS_RUN_DIR ", or a full pathname\n")
-{
- struct ns *ns = NULL;
-
- VTY_DECLVAR_CONTEXT(vrf, vrf);
-
- if (!vrf_is_backend_netns()) {
- vty_out(vty, "VRF backend is not Netns. Aborting\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
- if (!vrf->ns_ctxt) {
- vty_out(vty, "VRF %s(%u) is not configured with NetNS\n",
- vrf->name, vrf->vrf_id);
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- ns = (struct ns *)vrf->ns_ctxt;
-
- ns->vrf_ctxt = NULL;
- vrf_disable(vrf);
- /* vrf ID from VRF is necessary for Zebra
- * so that propagate to other clients is done
- */
- ns_delete(ns);
- vrf->ns_ctxt = NULL;
- return CMD_SUCCESS;
-}
-
/* if ns_id is different and not VRF_UNKNOWN,
* then update vrf identifier, and enable VRF
*/
@@ -683,12 +548,4 @@ void zebra_vrf_init(void)
zebra_vrf_delete);
hook_register(zserv_client_close, release_daemon_table_chunks);
-
- vrf_cmd_init(vrf_config_write);
-
- if (vrf_is_backend_netns() && ns_have_netns()) {
- /* Install NS commands. */
- install_element(VRF_NODE, &vrf_netns_cmd);
- install_element(VRF_NODE, &no_vrf_netns_cmd);
- }
}
diff --git a/zebra/zebra_vty.c b/zebra/zebra_vty.c
index b778b39508..70b71fe707 100644
--- a/zebra/zebra_vty.c
+++ b/zebra/zebra_vty.c
@@ -51,6 +51,7 @@
#include "zebra/zebra_script.h"
#include "zebra/rtadv.h"
#include "zebra/zebra_neigh.h"
+#include "zebra/zebra_ptm.h"
/* context to manage dumps in multiple tables or vrfs */
struct route_show_ctx {
@@ -1163,27 +1164,6 @@ DEFPY (show_ip_nht,
return CMD_SUCCESS;
}
-DEFUN (ip_nht_default_route,
- ip_nht_default_route_cmd,
- "ip nht resolve-via-default",
- IP_STR
- "Filter Next Hop tracking route resolution\n"
- "Resolve via default route\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (zvrf->zebra_rnh_ip_default_route)
- return CMD_SUCCESS;
-
- zvrf->zebra_rnh_ip_default_route = true;
-
- zebra_evaluate_rnh(zvrf, AFI_IP, 0, NULL, SAFI_UNICAST);
- return CMD_SUCCESS;
-}
-
static void show_nexthop_group_out(struct vty *vty, struct nhg_hash_entry *nhe,
json_object *json_nhe_hdr)
{
@@ -1682,68 +1662,6 @@ DEFPY_HIDDEN(backup_nexthop_recursive_use_enable,
return CMD_SUCCESS;
}
-DEFUN (no_ip_nht_default_route,
- no_ip_nht_default_route_cmd,
- "no ip nht resolve-via-default",
- NO_STR
- IP_STR
- "Filter Next Hop tracking route resolution\n"
- "Resolve via default route\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (!zvrf->zebra_rnh_ip_default_route)
- return CMD_SUCCESS;
-
- zvrf->zebra_rnh_ip_default_route = false;
- zebra_evaluate_rnh(zvrf, AFI_IP, 0, NULL, SAFI_UNICAST);
- return CMD_SUCCESS;
-}
-
-DEFUN (ipv6_nht_default_route,
- ipv6_nht_default_route_cmd,
- "ipv6 nht resolve-via-default",
- IP6_STR
- "Filter Next Hop tracking route resolution\n"
- "Resolve via default route\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (zvrf->zebra_rnh_ipv6_default_route)
- return CMD_SUCCESS;
-
- zvrf->zebra_rnh_ipv6_default_route = true;
- zebra_evaluate_rnh(zvrf, AFI_IP6, 0, NULL, SAFI_UNICAST);
- return CMD_SUCCESS;
-}
-
-DEFUN (no_ipv6_nht_default_route,
- no_ipv6_nht_default_route_cmd,
- "no ipv6 nht resolve-via-default",
- NO_STR
- IP6_STR
- "Filter Next Hop tracking route resolution\n"
- "Resolve via default route\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (!zvrf->zebra_rnh_ipv6_default_route)
- return CMD_SUCCESS;
-
- zvrf->zebra_rnh_ipv6_default_route = false;
- zebra_evaluate_rnh(zvrf, AFI_IP6, 0, NULL, SAFI_UNICAST);
- return CMD_SUCCESS;
-}
-
DEFPY_HIDDEN(rnh_hide_backups, rnh_hide_backups_cmd,
"[no] ip nht hide-backup-events",
NO_STR
@@ -2727,146 +2645,6 @@ DEFPY(evpn_mh_redirect_off, evpn_mh_redirect_off_cmd,
return zebra_evpn_mh_redirect_off(vty, redirect_off);
}
-DEFUN (default_vrf_vni_mapping,
- default_vrf_vni_mapping_cmd,
- "vni " CMD_VNI_RANGE "[prefix-routes-only]",
- "VNI corresponding to the DEFAULT VRF\n"
- "VNI-ID\n"
- "Prefix routes only \n")
-{
- char xpath[XPATH_MAXLEN];
- int filter = 0;
-
- if (argc == 3)
- filter = 1;
-
- snprintf(xpath, sizeof(xpath), FRR_VRF_KEY_XPATH "/frr-zebra:zebra",
- VRF_DEFAULT_NAME);
- nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
-
- snprintf(xpath, sizeof(xpath),
- FRR_VRF_KEY_XPATH "/frr-zebra:zebra/l3vni-id",
- VRF_DEFAULT_NAME);
- nb_cli_enqueue_change(vty, xpath, NB_OP_MODIFY, argv[1]->arg);
-
- if (filter) {
- snprintf(xpath, sizeof(xpath),
- FRR_VRF_KEY_XPATH "/frr-zebra:zebra/prefix-only",
- VRF_DEFAULT_NAME);
- nb_cli_enqueue_change(vty, xpath, NB_OP_MODIFY, "true");
- }
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFUN (no_default_vrf_vni_mapping,
- no_default_vrf_vni_mapping_cmd,
- "no vni " CMD_VNI_RANGE "[prefix-routes-only]",
- NO_STR
- "VNI corresponding to DEFAULT VRF\n"
- "VNI-ID\n"
- "Prefix routes only \n")
-{
- char xpath[XPATH_MAXLEN];
- int filter = 0;
- vni_t vni = strtoul(argv[2]->arg, NULL, 10);
- struct zebra_vrf *zvrf = NULL;
-
- zvrf = zebra_vrf_lookup_by_id(VRF_DEFAULT);
-
- if (argc == 4)
- filter = 1;
-
- if (zvrf->l3vni != vni) {
- vty_out(vty, "VNI %d doesn't exist in VRF: %s \n", vni,
- zvrf->vrf->name);
- return CMD_WARNING;
- }
-
- snprintf(xpath, sizeof(xpath),
- FRR_VRF_KEY_XPATH "/frr-zebra:zebra/l3vni-id",
- VRF_DEFAULT_NAME);
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, argv[2]->arg);
-
- if (filter) {
- snprintf(xpath, sizeof(xpath),
- FRR_VRF_KEY_XPATH "/frr-zebra:zebra/prefix-only",
- VRF_DEFAULT_NAME);
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, "true");
- }
-
- snprintf(xpath, sizeof(xpath), FRR_VRF_KEY_XPATH "/frr-zebra:zebra",
- VRF_DEFAULT_NAME);
- nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFUN (vrf_vni_mapping,
- vrf_vni_mapping_cmd,
- "vni " CMD_VNI_RANGE "[prefix-routes-only]",
- "VNI corresponding to tenant VRF\n"
- "VNI-ID\n"
- "prefix-routes-only\n")
-{
- int filter = 0;
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- assert(vrf);
- assert(zvrf);
-
- if (argc == 3)
- filter = 1;
-
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra", NB_OP_CREATE, NULL);
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra/l3vni-id", NB_OP_MODIFY,
- argv[1]->arg);
-
- if (filter)
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra/prefix-only",
- NB_OP_MODIFY, "true");
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
-DEFUN (no_vrf_vni_mapping,
- no_vrf_vni_mapping_cmd,
- "no vni " CMD_VNI_RANGE "[prefix-routes-only]",
- NO_STR
- "VNI corresponding to tenant VRF\n"
- "VNI-ID\n"
- "prefix-routes-only\n")
-{
- int filter = 0;
-
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
- vni_t vni = strtoul(argv[2]->arg, NULL, 10);
-
- assert(vrf);
- assert(zvrf);
-
- if (argc == 4)
- filter = 1;
-
- if (zvrf->l3vni != vni) {
- vty_out(vty, "VNI %d doesn't exist in VRF: %s \n", vni,
- zvrf->vrf->name);
- return CMD_WARNING;
- }
-
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra/l3vni-id", NB_OP_DESTROY,
- argv[2]->arg);
-
- if (filter)
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra/prefix-only",
- NB_OP_DESTROY, "true");
-
- nb_cli_enqueue_change(vty, "./frr-zebra:zebra", NB_OP_DESTROY, NULL);
-
- return nb_cli_apply_changes(vty, NULL);
-}
-
/* show vrf */
DEFPY (show_vrf_vni,
show_vrf_vni_cmd,
@@ -4498,31 +4276,6 @@ DEFPY (no_zebra_protodown_bit,
#endif /* HAVE_NETLINK */
-DEFUN(ip_table_range, ip_table_range_cmd,
- "[no] ip table range (1-4294967295) (1-4294967295)",
- NO_STR IP_STR
- "table configuration\n"
- "Configure table range\n"
- "Start Routing Table\n"
- "End Routing Table\n")
-{
- ZEBRA_DECLVAR_CONTEXT_VRF(vrf, zvrf);
-
- if (!zvrf)
- return CMD_WARNING;
-
- if (zvrf_id(zvrf) != VRF_DEFAULT && !vrf_is_backend_netns()) {
- vty_out(vty,
- "VRF subcommand does not make any sense in l3mdev based vrf's\n");
- return CMD_WARNING;
- }
-
- if (strmatch(argv[0]->text, "no"))
- return table_manager_range(vty, false, zvrf, NULL, NULL);
-
- return table_manager_range(vty, true, zvrf, argv[3]->arg, argv[4]->arg);
-}
-
#ifdef HAVE_SCRIPTING
DEFUN(zebra_on_rib_process_script, zebra_on_rib_process_script_cmd,
@@ -4634,14 +4387,6 @@ void zebra_vty_init(void)
install_element(VIEW_NODE, &show_ip_rpf_addr_cmd);
install_element(VIEW_NODE, &show_ipv6_rpf_addr_cmd);
- install_element(CONFIG_NODE, &ip_nht_default_route_cmd);
- install_element(CONFIG_NODE, &no_ip_nht_default_route_cmd);
- install_element(CONFIG_NODE, &ipv6_nht_default_route_cmd);
- install_element(CONFIG_NODE, &no_ipv6_nht_default_route_cmd);
- install_element(VRF_NODE, &ip_nht_default_route_cmd);
- install_element(VRF_NODE, &no_ip_nht_default_route_cmd);
- install_element(VRF_NODE, &ipv6_nht_default_route_cmd);
- install_element(VRF_NODE, &no_ipv6_nht_default_route_cmd);
install_element(CONFIG_NODE, &rnh_hide_backups_cmd);
install_element(VIEW_NODE, &show_frr_cmd);
@@ -4693,19 +4438,12 @@ void zebra_vty_init(void)
install_element(CONFIG_NODE, &evpn_mh_neigh_holdtime_cmd);
install_element(CONFIG_NODE, &evpn_mh_startup_delay_cmd);
install_element(CONFIG_NODE, &evpn_mh_redirect_off_cmd);
- install_element(CONFIG_NODE, &default_vrf_vni_mapping_cmd);
- install_element(CONFIG_NODE, &no_default_vrf_vni_mapping_cmd);
- install_element(VRF_NODE, &vrf_vni_mapping_cmd);
- install_element(VRF_NODE, &no_vrf_vni_mapping_cmd);
install_element(VIEW_NODE, &show_dataplane_cmd);
install_element(VIEW_NODE, &show_dataplane_providers_cmd);
install_element(CONFIG_NODE, &zebra_dplane_queue_limit_cmd);
install_element(CONFIG_NODE, &no_zebra_dplane_queue_limit_cmd);
- install_element(CONFIG_NODE, &ip_table_range_cmd);
- install_element(VRF_NODE, &ip_table_range_cmd);
-
#ifdef HAVE_NETLINK
install_element(CONFIG_NODE, &zebra_kernel_netlink_batch_tx_buf_cmd);
install_element(CONFIG_NODE, &no_zebra_kernel_netlink_batch_tx_buf_cmd);
diff --git a/zebra/zebra_vxlan.c b/zebra/zebra_vxlan.c
index 7d0c82a437..f0401d02a5 100644
--- a/zebra/zebra_vxlan.c
+++ b/zebra/zebra_vxlan.c
@@ -5174,9 +5174,8 @@ void zebra_vxlan_macvlan_up(struct interface *ifp)
}
}
-int zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
- char *err, int err_str_sz, int filter,
- int add)
+void zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
+ int filter, int add)
{
struct zebra_l3vni *zl3vni = NULL;
struct zebra_vrf *zvrf_evpn = NULL;
@@ -5188,21 +5187,6 @@ int zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
add ? "ADD" : "DEL");
if (add) {
- /* check if the vni is already present under zvrf */
- if (zvrf->l3vni) {
- snprintf(err, err_str_sz,
- "VNI is already configured under the vrf");
- return -1;
- }
-
- /* check if this VNI is already present in the system */
- zl3vni = zl3vni_lookup(vni);
- if (zl3vni) {
- snprintf(err, err_str_sz,
- "VNI is already configured as L3-VNI");
- return -1;
- }
-
/* Remove L2VNI if present */
zebra_vxlan_handle_vni_transition(zvrf, vni, add);
@@ -5248,23 +5232,7 @@ int zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
} else {
zl3vni = zl3vni_lookup(vni);
- if (!zl3vni) {
- snprintf(err, err_str_sz, "VNI doesn't exist");
- return -1;
- }
-
- if (zvrf->l3vni != vni) {
- snprintf(err, err_str_sz,
- "VNI %d doesn't exist in VRF: %s",
- vni, zvrf->vrf->name);
- return -1;
- }
-
- if (filter && !CHECK_FLAG(zl3vni->filter, PREFIX_ROUTES_ONLY)) {
- snprintf(err, ERR_STR_SZ,
- "prefix-routes-only is not set for the vni");
- return -1;
- }
+ assert(zl3vni);
zebra_vxlan_process_l3vni_oper_down(zl3vni);
@@ -5282,7 +5250,6 @@ int zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
/* Add L2VNI for this VNI */
zebra_vxlan_handle_vni_transition(zvrf, vni, add);
}
- return 0;
}
int zebra_vxlan_vrf_enable(struct zebra_vrf *zvrf)
diff --git a/zebra/zebra_vxlan.h b/zebra/zebra_vxlan.h
index 5785e0b3c3..eb02de6f7b 100644
--- a/zebra/zebra_vxlan.h
+++ b/zebra/zebra_vxlan.h
@@ -178,9 +178,8 @@ extern int zebra_vxlan_if_add(struct interface *ifp);
extern int zebra_vxlan_if_update(struct interface *ifp,
struct zebra_vxlan_if_update_ctx *ctx);
extern int zebra_vxlan_if_del(struct interface *ifp);
-extern int zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
- char *err, int err_str_sz,
- int filter, int add);
+extern void zebra_vxlan_process_vrf_vni_cmd(struct zebra_vrf *zvrf, vni_t vni,
+ int filter, int add);
extern void zebra_vxlan_init_tables(struct zebra_vrf *zvrf);
extern void zebra_vxlan_close_tables(struct zebra_vrf *);
extern void zebra_vxlan_cleanup_tables(struct zebra_vrf *);