summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDonald Sharp <sharpd@cumulusnetworks.com>2020-04-17 01:39:14 +0200
committerGitHub <noreply@github.com>2020-04-17 01:39:14 +0200
commita83014ccd66477fa624ee54eb97e0a2a30a5a106 (patch)
tree3d7faaad38c74b74409785cc54c0a58b8f72a23a
parentMerge pull request #6135 from opensourcerouting/cli-node-cleanup (diff)
parentlib: suppress formatting on yang.c module array (diff)
downloadfrr-a83014ccd66477fa624ee54eb97e0a2a30a5a106.tar.xz
frr-a83014ccd66477fa624ee54eb97e0a2a30a5a106.zip
Merge pull request #6247 from FRRouting/nb_conversions
Merge nb_converions branch to master
-rw-r--r--babeld/babel_main.c8
-rw-r--r--bfdd/bfdd.c1
-rw-r--r--bgpd/bgp_main.c1
-rw-r--r--eigrpd/eigrp_main.c1
-rw-r--r--isisd/isis_main.c1
-rw-r--r--ldpd/ldpd.c1
-rw-r--r--lib/if.c139
-rw-r--r--lib/if.h18
-rw-r--r--lib/subdir.am5
-rw-r--r--lib/vrf.c180
-rw-r--r--lib/vrf.h2
-rw-r--r--lib/yang.c4
-rw-r--r--lib/yang.h2
-rw-r--r--lib/yang_wrappers.c50
-rw-r--r--lib/yang_wrappers.h10
-rw-r--r--ospf6d/ospf6_main.c1
-rw-r--r--ospfd/ospf_main.c1
-rw-r--r--pimd/pim_main.c1
-rw-r--r--ripd/rip_main.c1
-rw-r--r--ripngd/ripng_main.c1
-rw-r--r--sharpd/sharp_main.c1
-rw-r--r--staticd/static_main.c1
-rw-r--r--yang/frr-igmp.yang147
-rw-r--r--yang/frr-interface.yang260
-rw-r--r--yang/frr-nexthop.yang153
-rw-r--r--yang/frr-routing.yang135
-rw-r--r--yang/frr-staticd.yang86
-rw-r--r--yang/frr-vrf.yang60
-rw-r--r--yang/frr-zebra.yang284
-rw-r--r--yang/ietf/ietf-interfaces.yang1123
-rw-r--r--yang/subdir.am13
-rw-r--r--zebra/interface.c302
-rw-r--r--zebra/interface.h11
-rw-r--r--zebra/main.c2
-rw-r--r--zebra/subdir.am7
-rw-r--r--zebra/zebra_nb.c692
-rw-r--r--zebra/zebra_nb.h488
-rw-r--r--zebra/zebra_nb_config.c1672
-rw-r--r--zebra/zebra_nb_rpcs.c212
-rw-r--r--zebra/zebra_nb_state.c637
-rw-r--r--zebra/zebra_northbound.c2212
-rw-r--r--zebra/zebra_vty.c48
-rw-r--r--zebra/zebra_vxlan.c92
-rw-r--r--zebra/zebra_vxlan.h13
44 files changed, 6650 insertions, 2429 deletions
diff --git a/babeld/babel_main.c b/babeld/babel_main.c
index 6f4b905c1..e7ba29ed0 100644
--- a/babeld/babel_main.c
+++ b/babeld/babel_main.c
@@ -136,10 +136,10 @@ struct option longopts[] =
{ 0 }
};
-static const struct frr_yang_module_info *const babeld_yang_modules[] =
- {
- &frr_interface_info,
- };
+static const struct frr_yang_module_info *const babeld_yang_modules[] = {
+ &frr_interface_info,
+ &frr_vrf_info,
+};
FRR_DAEMON_INFO(babeld, BABELD,
.vty_port = BABEL_VTY_PORT,
diff --git a/bfdd/bfdd.c b/bfdd/bfdd.c
index e8e213c74..39d51eb64 100644
--- a/bfdd/bfdd.c
+++ b/bfdd/bfdd.c
@@ -113,6 +113,7 @@ static struct quagga_signal_t bfd_signals[] = {
static const struct frr_yang_module_info *const bfdd_yang_modules[] = {
&frr_interface_info,
&frr_bfdd_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(bfdd, BFD, .vty_port = 2617,
diff --git a/bgpd/bgp_main.c b/bgpd/bgp_main.c
index 8f0ccca74..04be8d83e 100644
--- a/bgpd/bgp_main.c
+++ b/bgpd/bgp_main.c
@@ -361,6 +361,7 @@ static void bgp_vrf_terminate(void)
static const struct frr_yang_module_info *const bgpd_yang_modules[] = {
&frr_interface_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(bgpd, BGP, .vty_port = BGP_VTY_PORT,
diff --git a/eigrpd/eigrp_main.c b/eigrpd/eigrp_main.c
index add758fa2..cdf1c6acd 100644
--- a/eigrpd/eigrp_main.c
+++ b/eigrpd/eigrp_main.c
@@ -141,6 +141,7 @@ static const struct frr_yang_module_info *const eigrpd_yang_modules[] = {
&frr_eigrpd_info,
&frr_interface_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(eigrpd, EIGRP, .vty_port = EIGRP_VTY_PORT,
diff --git a/isisd/isis_main.c b/isisd/isis_main.c
index f7fe089b9..4c841dffe 100644
--- a/isisd/isis_main.c
+++ b/isisd/isis_main.c
@@ -168,6 +168,7 @@ static const struct frr_yang_module_info *const isisd_yang_modules[] = {
&frr_isisd_info,
#endif /* ifndef FABRICD */
&frr_route_map_info,
+ &frr_vrf_info,
};
#ifdef FABRICD
diff --git a/ldpd/ldpd.c b/ldpd/ldpd.c
index a355b4a82..8e546be93 100644
--- a/ldpd/ldpd.c
+++ b/ldpd/ldpd.c
@@ -180,6 +180,7 @@ static struct quagga_signal_t ldp_signals[] =
};
static const struct frr_yang_module_info *const ldpd_yang_modules[] = {
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(ldpd, LDP,
diff --git a/lib/if.c b/lib/if.c
index cc964106d..c887bb626 100644
--- a/lib/if.c
+++ b/lib/if.c
@@ -1667,8 +1667,97 @@ static int lib_interface_description_destroy(enum nb_event event,
return NB_OK;
}
-/* clang-format off */
+/*
+ * XPath: /frr-interface:lib/interface/state/if-index
+ */
+struct yang_data *lib_interface_state_if_index_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+
+ return yang_data_new_int32(xpath, ifp->ifindex);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/state/mtu
+ */
+struct yang_data *lib_interface_state_mtu_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+
+ return yang_data_new_uint16(xpath, ifp->mtu);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/state/mtu6
+ */
+struct yang_data *lib_interface_state_mtu6_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+
+ return yang_data_new_uint32(xpath, ifp->mtu6);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/state/speed
+ */
+struct yang_data *lib_interface_state_speed_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+
+ return yang_data_new_uint32(xpath, ifp->speed);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/state/metric
+ */
+struct yang_data *lib_interface_state_metric_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+
+ return yang_data_new_uint32(xpath, ifp->metric);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/state/flags
+ */
+struct yang_data *lib_interface_state_flags_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/state/type
+ */
+struct yang_data *lib_interface_state_type_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/state/phy-address
+ */
+struct yang_data *
+lib_interface_state_phy_address_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+ struct ethaddr macaddr;
+
+ memcpy(&macaddr.octet, ifp->hw_addr, ETH_ALEN);
+
+ return yang_data_new_mac(xpath, &macaddr);
+}
+/* clang-format off */
const struct frr_yang_module_info frr_interface_info = {
.name = "frr-interface",
.nodes = {
@@ -1692,6 +1781,54 @@ const struct frr_yang_module_info frr_interface_info = {
},
},
{
+ .xpath = "/frr-interface:lib/interface/state/if-index",
+ .cbs = {
+ .get_elem = lib_interface_state_if_index_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/state/mtu",
+ .cbs = {
+ .get_elem = lib_interface_state_mtu_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/state/mtu6",
+ .cbs = {
+ .get_elem = lib_interface_state_mtu6_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/state/speed",
+ .cbs = {
+ .get_elem = lib_interface_state_speed_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/state/metric",
+ .cbs = {
+ .get_elem = lib_interface_state_metric_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/state/flags",
+ .cbs = {
+ .get_elem = lib_interface_state_flags_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/state/type",
+ .cbs = {
+ .get_elem = lib_interface_state_type_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/state/phy-address",
+ .cbs = {
+ .get_elem = lib_interface_state_phy_address_get_elem,
+ }
+ },
+ {
.xpath = NULL,
},
}
diff --git a/lib/if.h b/lib/if.h
index ac8d8e70b..9afbb5acc 100644
--- a/lib/if.h
+++ b/lib/if.h
@@ -602,6 +602,24 @@ extern void if_destroy_via_zapi(struct interface *ifp);
extern const struct frr_yang_module_info frr_interface_info;
+struct yang_data *lib_interface_state_if_index_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_interface_state_mtu_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_interface_state_mtu6_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_interface_state_speed_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_interface_state_metric_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_interface_state_flags_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_interface_state_type_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_state_phy_address_get_elem(const char *xpath,
+ const void *list_entry);
+
#ifdef __cplusplus
}
#endif
diff --git a/lib/subdir.am b/lib/subdir.am
index a01909e90..ed6cf31b3 100644
--- a/lib/subdir.am
+++ b/lib/subdir.am
@@ -113,8 +113,13 @@ nodist_lib_libfrr_la_SOURCES = \
yang/frr-interface.yang.c \
yang/frr-route-map.yang.c \
yang/frr-route-types.yang.c \
+ yang/frr-vrf.yang.c \
+ yang/frr-routing.yang.c \
yang/ietf/ietf-routing-types.yang.c \
+ yang/ietf/ietf-interfaces.yang.c \
yang/frr-module-translator.yang.c \
+ yang/frr-nexthop.yang.c \
+ yang/frr-igmp.yang.c \
# end
vtysh_scan += \
diff --git a/lib/vrf.c b/lib/vrf.c
index 0f57c602b..79195453e 100644
--- a/lib/vrf.c
+++ b/lib/vrf.c
@@ -36,6 +36,8 @@
#include "privs.h"
#include "nexthop_group.h"
#include "lib_errors.h"
+#include "northbound.h"
+#include "northbound_cli.h"
/* default VRF ID value used when VRF backend is not NETNS */
#define VRF_DEFAULT_INTERNAL 0
@@ -612,6 +614,8 @@ int vrf_handler_create(struct vty *vty, const char *vrfname,
struct vrf **vrf)
{
struct vrf *vrfp;
+ char xpath_list[XPATH_MAXLEN];
+ int ret;
if (strlen(vrfname) > VRF_NAMSIZ) {
if (vty)
@@ -626,13 +630,24 @@ int vrf_handler_create(struct vty *vty, const char *vrfname,
return CMD_WARNING_CONFIG_FAILED;
}
- vrfp = vrf_get(VRF_UNKNOWN, vrfname);
-
- if (vty)
- VTY_PUSH_CONTEXT(VRF_NODE, vrfp);
+ if (vty) {
+ snprintf(xpath_list, sizeof(xpath_list),
+ "/frr-vrf:lib/vrf[name='%s']", vrfname);
+
+ nb_cli_enqueue_change(vty, xpath_list, NB_OP_CREATE, NULL);
+ ret = nb_cli_apply_changes(vty, xpath_list);
+ if (ret == CMD_SUCCESS) {
+ VTY_PUSH_XPATH(VRF_NODE, xpath_list);
+ vrfp = vrf_lookup_by_name(vrfname);
+ if (vrfp)
+ VTY_PUSH_CONTEXT(VRF_NODE, vrfp);
+ }
+ } else {
+ vrfp = vrf_get(VRF_UNKNOWN, vrfname);
- if (vrf)
- *vrf = vrfp;
+ if (vrf)
+ *vrf = vrfp;
+ }
return CMD_SUCCESS;
}
@@ -735,6 +750,7 @@ DEFUN (no_vrf,
"VRF's name\n")
{
const char *vrfname = argv[2]->arg;
+ char xpath_list[XPATH_MAXLEN];
struct vrf *vrfp;
@@ -750,11 +766,11 @@ DEFUN (no_vrf,
return CMD_WARNING_CONFIG_FAILED;
}
- /* Clear configured flag and invoke delete. */
- UNSET_FLAG(vrfp->status, VRF_CONFIGURED);
- vrf_delete(vrfp);
+ snprintf(xpath_list, sizeof(xpath_list), "/frr-vrf:lib/vrf[name='%s']",
+ vrfname);
- return CMD_SUCCESS;
+ nb_cli_enqueue_change(vty, xpath_list, NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, xpath_list);
}
@@ -1031,3 +1047,147 @@ vrf_id_t vrf_generate_id(void)
return ++vrf_id_local;
}
+
+/* ------- Northbound callbacks ------- */
+
+/*
+ * XPath: /frr-vrf:lib/vrf
+ */
+static int lib_vrf_create(enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ const char *vrfname;
+ struct vrf *vrfp;
+
+ vrfname = yang_dnode_get_string(dnode, "./name");
+
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ vrfp = vrf_get(VRF_UNKNOWN, vrfname);
+
+ nb_running_set_entry(dnode, vrfp);
+
+ return NB_OK;
+}
+
+static int lib_vrf_destroy(enum nb_event event, const struct lyd_node *dnode)
+{
+ struct vrf *vrfp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ vrfp = nb_running_get_entry(dnode, NULL, true);
+ if (CHECK_FLAG(vrfp->status, VRF_ACTIVE)) {
+ zlog_debug("%s Only inactive VRFs can be deleted",
+ __func__);
+ return NB_ERR_VALIDATION;
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ vrfp = nb_running_unset_entry(dnode);
+
+ /* Clear configured flag and invoke delete. */
+ UNSET_FLAG(vrfp->status, VRF_CONFIGURED);
+ vrf_delete(vrfp);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static const void *lib_vrf_get_next(const void *parent_list_entry,
+ const void *list_entry)
+{
+ struct vrf *vrfp = (struct vrf *)list_entry;
+
+ if (list_entry == NULL) {
+ vrfp = RB_MIN(vrf_name_head, &vrfs_by_name);
+ } else {
+ vrfp = RB_NEXT(vrf_name_head, vrfp);
+ }
+
+ return vrfp;
+}
+
+static int lib_vrf_get_keys(const void *list_entry, struct yang_list_keys *keys)
+{
+ struct vrf *vrfp = (struct vrf *)list_entry;
+
+ keys->num = 1;
+ strlcpy(keys->key[0], vrfp->name, sizeof(keys->key[0]));
+
+ return NB_OK;
+}
+
+static const void *lib_vrf_lookup_entry(const void *parent_list_entry,
+ const struct yang_list_keys *keys)
+{
+ const char *vrfname = keys->key[0];
+
+ struct vrf *vrf = vrf_lookup_by_name(vrfname);
+
+ return vrf;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/id
+ */
+static struct yang_data *lib_vrf_state_id_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ struct vrf *vrfp = (struct vrf *)list_entry;
+
+ return yang_data_new_uint32(xpath, vrfp->vrf_id);
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/active
+ */
+static struct yang_data *lib_vrf_state_active_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ struct vrf *vrfp = (struct vrf *)list_entry;
+
+ if (vrfp->status == VRF_ACTIVE)
+ return yang_data_new_bool(
+ xpath, vrfp->status == VRF_ACTIVE ? true : false);
+
+ return NULL;
+}
+
+/* clang-format off */
+const struct frr_yang_module_info frr_vrf_info = {
+ .name = "frr-vrf",
+ .nodes = {
+ {
+ .xpath = "/frr-vrf:lib/vrf",
+ .cbs = {
+ .create = lib_vrf_create,
+ .destroy = lib_vrf_destroy,
+ .get_next = lib_vrf_get_next,
+ .get_keys = lib_vrf_get_keys,
+ .lookup_entry = lib_vrf_lookup_entry,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/state/id",
+ .cbs = {
+ .get_elem = lib_vrf_state_id_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/state/active",
+ .cbs = {
+ .get_elem = lib_vrf_state_active_get_elem,
+ }
+ },
+ {
+ .xpath = NULL,
+ },
+ }
+};
+
diff --git a/lib/vrf.h b/lib/vrf.h
index 2dc264883..83ed16b48 100644
--- a/lib/vrf.h
+++ b/lib/vrf.h
@@ -325,6 +325,8 @@ extern int vrf_enable(struct vrf *vrf);
extern void vrf_delete(struct vrf *vrf);
extern vrf_id_t vrf_generate_id(void);
+extern const struct frr_yang_module_info frr_vrf_info;
+
#ifdef __cplusplus
}
#endif
diff --git a/lib/yang.c b/lib/yang.c
index 0502d4952..c80bf2030 100644
--- a/lib/yang.c
+++ b/lib/yang.c
@@ -72,13 +72,17 @@ static const char *yang_module_imp_clb(const char *mod_name,
return NULL;
}
+/* clang-format off */
static const char *const frr_native_modules[] = {
"frr-interface",
+ "frr-vrf",
"frr-ripd",
"frr-ripngd",
"frr-isisd",
"frr-vrrpd",
+ "frr-zebra",
};
+/* clang-format on */
/* Generate the yang_modules tree. */
static inline int yang_module_compare(const struct yang_module *a,
diff --git a/lib/yang.h b/lib/yang.h
index 8af440d3e..126521707 100644
--- a/lib/yang.h
+++ b/lib/yang.h
@@ -34,7 +34,7 @@ extern "C" {
#endif
/* Maximum XPath length. */
-#define XPATH_MAXLEN 256
+#define XPATH_MAXLEN 512
/* Maximum list key length. */
#define LIST_MAXKEYS 8
diff --git a/lib/yang_wrappers.c b/lib/yang_wrappers.c
index 2b502d635..7d94a2f74 100644
--- a/lib/yang_wrappers.c
+++ b/lib/yang_wrappers.c
@@ -23,6 +23,7 @@
#include "lib_errors.h"
#include "northbound.h"
#include "printfrr.h"
+#include "nexthop.h"
static const char *yang_get_default_value(const char *xpath)
{
@@ -783,6 +784,14 @@ void yang_get_default_string_buf(char *buf, size_t size, const char *xpath_fmt,
}
/*
+ * Primitive type: empty.
+ */
+struct yang_data *yang_data_new_empty(const char *xpath)
+{
+ return yang_data_new(xpath, NULL);
+}
+
+/*
* Derived type: IP prefix.
*/
void yang_str2prefix(const char *value, union prefixptr prefix)
@@ -1114,3 +1123,44 @@ void yang_get_default_ip(struct ipaddr *var, const char *xpath_fmt, ...)
value = yang_get_default_value(xpath);
yang_str2ip(value, var);
}
+
+struct yang_data *yang_data_new_mac(const char *xpath,
+ const struct ethaddr *mac)
+{
+ char value_str[ETHER_ADDR_STRLEN];
+
+ prefix_mac2str(mac, value_str, sizeof(value_str));
+ return yang_data_new(xpath, value_str);
+}
+
+void yang_str2mac(const char *value, struct ethaddr *mac)
+{
+ (void)prefix_str2mac(value, mac);
+}
+
+const char *yang_nexthop_type2str(uint32_t ntype)
+{
+ switch (ntype) {
+ case NEXTHOP_TYPE_IFINDEX:
+ return "ifindex";
+ break;
+ case NEXTHOP_TYPE_IPV4:
+ return "ip4";
+ break;
+ case NEXTHOP_TYPE_IPV4_IFINDEX:
+ return "ip4-ifindex";
+ break;
+ case NEXTHOP_TYPE_IPV6:
+ return "ip6";
+ break;
+ case NEXTHOP_TYPE_IPV6_IFINDEX:
+ return "ip6-ifindex";
+ break;
+ case NEXTHOP_TYPE_BLACKHOLE:
+ return "blackhole";
+ break;
+ default:
+ return "unknown";
+ break;
+ }
+}
diff --git a/lib/yang_wrappers.h b/lib/yang_wrappers.h
index 10d1ea314..d853b61ae 100644
--- a/lib/yang_wrappers.h
+++ b/lib/yang_wrappers.h
@@ -114,6 +114,9 @@ extern const char *yang_get_default_string(const char *xpath_fmt, ...);
extern void yang_get_default_string_buf(char *buf, size_t size,
const char *xpath_fmt, ...);
+/* empty */
+extern struct yang_data *yang_data_new_empty(const char *xpath);
+
/* ip prefix */
extern void yang_str2prefix(const char *value, union prefixptr prefix);
extern struct yang_data *yang_data_new_prefix(const char *xpath,
@@ -172,4 +175,11 @@ extern void yang_dnode_get_ip(struct ipaddr *addr, const struct lyd_node *dnode,
const char *xpath_fmt, ...);
extern void yang_get_default_ip(struct ipaddr *var, const char *xpath_fmt, ...);
+/* mac */
+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 const char *yang_nexthop_type2str(uint32_t ntype);
+
#endif /* _FRR_NORTHBOUND_WRAPPERS_H_ */
diff --git a/ospf6d/ospf6_main.c b/ospf6d/ospf6_main.c
index e4bed7a79..4dbe5ca32 100644
--- a/ospf6d/ospf6_main.c
+++ b/ospf6d/ospf6_main.c
@@ -168,6 +168,7 @@ struct quagga_signal_t ospf6_signals[] = {
static const struct frr_yang_module_info *const ospf6d_yang_modules[] = {
&frr_interface_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(ospf6d, OSPF6, .vty_port = OSPF6_VTY_PORT,
diff --git a/ospfd/ospf_main.c b/ospfd/ospf_main.c
index 4d6ebb40e..6a3ba9902 100644
--- a/ospfd/ospf_main.c
+++ b/ospfd/ospf_main.c
@@ -128,6 +128,7 @@ struct quagga_signal_t ospf_signals[] = {
static const struct frr_yang_module_info *const ospfd_yang_modules[] = {
&frr_interface_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(ospfd, OSPF, .vty_port = OSPF_VTY_PORT,
diff --git a/pimd/pim_main.c b/pimd/pim_main.c
index 93b561ba0..5c4c7151a 100644
--- a/pimd/pim_main.c
+++ b/pimd/pim_main.c
@@ -75,6 +75,7 @@ struct zebra_privs_t pimd_privs = {
static const struct frr_yang_module_info *const pimd_yang_modules[] = {
&frr_interface_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(pimd, PIM, .vty_port = PIMD_VTY_PORT,
diff --git a/ripd/rip_main.c b/ripd/rip_main.c
index 73e94deef..9ec32a53e 100644
--- a/ripd/rip_main.c
+++ b/ripd/rip_main.c
@@ -117,6 +117,7 @@ static const struct frr_yang_module_info *const ripd_yang_modules[] = {
&frr_interface_info,
&frr_ripd_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(ripd, RIP, .vty_port = RIP_VTY_PORT,
diff --git a/ripngd/ripng_main.c b/ripngd/ripng_main.c
index 99adb2cba..fbac750db 100644
--- a/ripngd/ripng_main.c
+++ b/ripngd/ripng_main.c
@@ -117,6 +117,7 @@ static const struct frr_yang_module_info *const ripngd_yang_modules[] = {
&frr_interface_info,
&frr_ripngd_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(ripngd, RIPNG, .vty_port = RIPNG_VTY_PORT,
diff --git a/sharpd/sharp_main.c b/sharpd/sharp_main.c
index 5133523f0..120d70491 100644
--- a/sharpd/sharp_main.c
+++ b/sharpd/sharp_main.c
@@ -114,6 +114,7 @@ struct quagga_signal_t sharp_signals[] = {
static const struct frr_yang_module_info *const sharpd_yang_modules[] = {
&frr_interface_info,
&frr_route_map_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(sharpd, SHARP, .vty_port = SHARP_VTY_PORT,
diff --git a/staticd/static_main.c b/staticd/static_main.c
index 3aa8a8db3..c77a99f28 100644
--- a/staticd/static_main.c
+++ b/staticd/static_main.c
@@ -104,6 +104,7 @@ struct quagga_signal_t static_signals[] = {
};
static const struct frr_yang_module_info *const staticd_yang_modules[] = {
+ &frr_vrf_info,
};
#define STATIC_VTY_PORT 2616
diff --git a/yang/frr-igmp.yang b/yang/frr-igmp.yang
new file mode 100644
index 000000000..7f750dcf3
--- /dev/null
+++ b/yang/frr-igmp.yang
@@ -0,0 +1,147 @@
+module frr-igmp {
+ yang-version "1.1";
+ namespace "http://frrouting.org/yang/igmp";
+
+ prefix frr-igmp;
+
+ import frr-routing {
+ prefix "frr-rt";
+ }
+
+ import ietf-routing-types {
+ prefix "rt-types";
+ }
+
+ import ietf-inet-types {
+ prefix "inet";
+ }
+
+ import frr-interface {
+ prefix frr-interface;
+ }
+
+ organization
+ "Free Range Routing";
+
+ contact
+ "FRR Users List: <mailto:frog@lists.frrouting.org>
+ FRR Development List: <mailto:dev@lists.frrouting.org>";
+
+ description
+ "This module defines a model for managing FRR pimd daemon.";
+
+ revision 2019-11-06 {
+ description
+ "Initial revision.";
+ reference
+ "RFC 2236: IGMP v2.
+ RFC 3376: IGMP v3.";
+ }
+
+ grouping interface-config-attributes {
+ description
+ "Configuration attributes applied to the interface level.";
+
+ leaf igmp-enable {
+ type boolean;
+ default "false";
+ description
+ "Enable IGMP protocol on the interface.";
+ }
+
+ leaf version {
+ type uint8 {
+ range "2..3";
+ }
+ default "3";
+ description
+ "IGMP version.";
+ }
+
+ leaf query-interval {
+ type uint16 {
+ range "1..1800";
+ }
+ units seconds;
+ default "125";
+ description
+ "The Query Interval is the interval between General Queries
+ sent by the Querier.";
+ }
+
+ leaf query-max-response-time {
+ type uint8 {
+ range "10..250";
+ }
+ units deciseconds;
+ default "100";
+ description
+ "Query maximum response time specifies the maximum time
+ allowed before sending a responding report.";
+ }
+
+ leaf last-member-query-interval {
+ type uint8 {
+ range "1..255";
+ }
+ units deciseconds;
+ default "10";
+ description
+ "Last Member Query Interval, which may be tuned to modify
+ the leave latency of the network.";
+ }
+
+ leaf robustness-variable {
+ type uint8 {
+ range "1..7";
+ }
+ default "2";
+ description
+ "Querier's Robustness Variable allows tuning for the
+ expected packet loss on a network.";
+ }
+ }
+
+ grouping per-af-interface-config-attributes {
+ description
+ "Configuration attributes applied to the interface level per address family.";
+
+ list static-group {
+ key "group-addr source-addr";
+ description
+ "A static multicast route, (*,G) or (S,G).
+ The version of IGMP must be 3 to support (S,G).";
+
+ leaf group-addr {
+ type rt-types:ip-multicast-group-address;
+ description
+ "Multicast group address.";
+ }
+ leaf source-addr {
+ type inet:ip-address;
+ description
+ "Multicast source address.";
+ }
+ }
+
+ } // per-af-interface-config-attributes
+
+ /*
+ * Per-interface configuration data
+ */
+ augment "/frr-interface:lib/frr-interface:interface" {
+ container igmp {
+ description
+ "IGMP interface parameters.";
+ uses interface-config-attributes;
+ list address-family {
+ key "address-family";
+ description
+ "Each list entry for one address family.";
+ uses frr-rt:address-family;
+ uses per-af-interface-config-attributes;
+
+ } //address-family
+ }
+ }
+}
diff --git a/yang/frr-interface.yang b/yang/frr-interface.yang
index 1f3eebb2a..7ebba935a 100644
--- a/yang/frr-interface.yang
+++ b/yang/frr-interface.yang
@@ -3,6 +3,18 @@ module frr-interface {
namespace "http://frrouting.org/yang/interface";
prefix frr-interface;
+ import frr-vrf {
+ prefix frr-vrf;
+ }
+
+ import ietf-interfaces {
+ prefix ietf-if;
+ }
+
+ import ietf-yang-types {
+ prefix yang;
+ }
+
organization
"FRRouting";
contact
@@ -11,6 +23,10 @@ module frr-interface {
description
"This module defines a model for managing FRR interfaces.";
+ revision 2020-02-05 {
+ description
+ "Added operational data";
+ }
revision 2019-09-09 {
description
"Added interface-ref typedef";
@@ -20,12 +36,236 @@ module frr-interface {
"Initial revision.";
}
+ identity other {
+ base ietf-if:interface-type;
+ description
+ "Other type";
+ }
+
+ identity unknown {
+ base ietf-if:interface-type;
+ description
+ "Unknown type";
+ }
+
+ identity ethernet {
+ base ietf-if:interface-type;
+ description
+ "Ethernet type";
+ }
+
+ identity exper-ethernet {
+ base ietf-if:interface-type;
+ description
+ "Experimental Ethernet type";
+ }
+
+ identity loopback {
+ base ietf-if:interface-type;
+ description
+ "Loopback type";
+ }
+
+ identity pimreg {
+ base ietf-if:interface-type;
+ description
+ "PIMSM Registration.";
+ }
+
+ identity ipip {
+ base ietf-if:interface-type;
+ description
+ "IPIP Tunnel.";
+ }
+
+ identity ipip6 {
+ base ietf-if:interface-type;
+ description
+ "IPIP6 Tunnel.";
+ }
+
+ identity ipgre {
+ base ietf-if:interface-type;
+ description
+ "GRE over IP.";
+ }
+
+ typedef interface-ref {
+ type leafref {
+ path "/frr-interface:lib/frr-interface:interface/frr-interface:name";
+ require-instance false;
+ }
+ description
+ "Reference to an interface";
+ }
+
+ typedef if-flags-type {
+ type enumeration {
+ enum "up" {
+ value 1;
+ description
+ "Active and ready to transfer packets.";
+ }
+ enum "broadcast" {
+ value 2;
+ description
+ "Broadcast enabled.";
+ }
+ enum "debug" {
+ value 3;
+ description
+ "Debug mode.";
+ }
+ enum "loopback" {
+ value 4;
+ description
+ "Loopback interface.";
+ }
+ enum "point-to-point" {
+ value 5;
+ description
+ "Point-to-Point link.";
+ }
+ enum "notrailers" {
+ value 6;
+ description
+ "This flag is unused in Linux, but it exists for BSD compatibility.
+ Avoid use of trailers";
+ }
+ enum "running" {
+ value 7;
+ description
+ "Up and Running.";
+ }
+ enum "noarp" {
+ value 8;
+ description
+ "Can't perform address resolution protocol.";
+ }
+ enum "promisc" {
+ value 9;
+ description
+ "Promiscuous mode. Receive all packets.";
+ }
+ enum "allmulti" {
+ value 10;
+ description
+ "Receive all multicast packets.";
+ }
+ enum "simplex" {
+ value 11;
+ description
+ "Does not Rx or Tx at the sametime.";
+ }
+ enum "link0" {
+ value 12;
+ description
+ "Link0.";
+ }
+ enum "link1" {
+ value 13;
+ description
+ "Link1.";
+ }
+ enum "link2" {
+ value 14;
+ description
+ "Link2.";
+ }
+ enum "multicast" {
+ value 15;
+ description
+ "Supports multicast transmission.";
+ }
+ enum "notransmit" {
+ value 16;
+ description
+ "Interface is no transmit mode.";
+ }
+ enum "nortexch" {
+ value 17;
+ description
+ "No routing info exchange.";
+ }
+ enum "virtual" {
+ value 18;
+ description
+ "Virtual interface.";
+ }
+ enum "ipv4" {
+ value 19;
+ description
+ "IPv4 enabled.";
+ }
+ enum "ipv6" {
+ value 20;
+ description
+ "IPv6 enabled.";
+ }
+ }
+ }
+
+ grouping if-common-operational {
+ leaf if-index {
+ type int32 {
+ range "0..2147483647";
+ }
+ description
+ "Interface index.";
+ }
+
+ leaf mtu {
+ type uint16;
+ description
+ "The size of the largest IPV4 packet that the interface
+ will send and receive.";
+ }
+
+ leaf mtu6 {
+ type uint32;
+ description
+ "The size of the largest IPV6 packet that the interface
+ will send and receive.";
+ }
+
+ leaf speed {
+ type uint32;
+ description
+ "Interface speed.";
+ }
+
+ leaf metric {
+ type uint32;
+ description
+ "Interface metric.";
+ }
+
+ leaf flags {
+ type if-flags-type;
+ description
+ "Interface flags.";
+ }
+
+ leaf type {
+ type identityref {
+ base ietf-if:interface-type;
+ }
+ description
+ "The link type of the interface.";
+ }
+
+ leaf phy-address {
+ type yang:mac-address;
+ description
+ "The interface's MAC address.";
+ }
+ }
+
container lib {
list interface {
key "name vrf";
description
"Interface.";
-
leaf name {
type string {
length "1..16";
@@ -33,27 +273,27 @@ module frr-interface {
description
"Interface name.";
}
+
leaf vrf {
type string {
- length "1..36";
+ length "1..16";
}
+ /* yang version 0.16 having issue accessing leafref. */
+ /* type frr-vrf:vrf-ref;*/
description
"VRF this interface is associated with.";
}
+
leaf description {
type string;
description
"Interface description.";
}
- }
- }
- typedef interface-ref {
- type leafref {
- require-instance false;
- path "/frr-interface:lib/frr-interface:interface/frr-interface:name";
+ container state {
+ config false;
+ uses if-common-operational;
+ }
}
- description
- "Reference to an interface";
}
}
diff --git a/yang/frr-nexthop.yang b/yang/frr-nexthop.yang
index 3657ecbd7..07e15eb77 100644
--- a/yang/frr-nexthop.yang
+++ b/yang/frr-nexthop.yang
@@ -10,10 +10,15 @@ module frr-nexthop {
import ietf-routing-types {
prefix rt-types;
}
+
import frr-interface {
prefix frr-interface;
}
+ import frr-vrf {
+ prefix frr-vrf;
+ }
+
organization
"FRRouting";
contact
@@ -27,10 +32,18 @@ module frr-nexthop {
"Initial revision.";
}
- typedef gateway-address {
- type inet:ip-address;
+ typedef optional-ip-address {
+ type union {
+ type inet:ip-address;
+ type string {
+ pattern '';
+ }
+ }
}
+ /*
+ * Nexthop types.
+ */
typedef nexthop-type {
type enumeration {
enum "ifindex" {
@@ -68,6 +81,9 @@ module frr-nexthop {
"Nexthop types.";
}
+ /*
+ * Blockhole nexthop type.
+ */
typedef blackhole-type {
type enumeration {
enum "unspec" {
@@ -97,113 +113,148 @@ module frr-nexthop {
}
/*
- * Nexthop object
+ * Common nexthop attributes grouping.
*/
-
- grouping frr-nexthop {
+ grouping frr-nexthop-attributes {
leaf nh-type {
type nexthop-type;
mandatory true;
description
"The nexthop type.";
}
-
- leaf gateway {
- type gateway-address;
- description
- "The nexthop gateway address.";
- }
-
leaf vrf {
- type string {
- length "1..36";
- }
+ type frr-vrf:vrf-ref;
description
"The nexthop vrf name, if different from the route.";
}
-
+ leaf gateway {
+ type frr-nexthop:optional-ip-address;
+ description
+ "The nexthop gateway address.";
+ }
leaf interface {
type frr-interface:interface-ref;
description
"The nexthop egress interface.";
}
-
leaf bh-type {
+ when "../nh-type = 'blackhole'";
type blackhole-type;
description
"A blackhole sub-type, if the nexthop is a blackhole type.";
}
-
- leaf flags {
- type uint32;
+ leaf onlink {
+ when "../nh-type = 'ip4-ifindex' or
+ ../nh-type = 'ip6-ifindex'";
+ type boolean;
+ default "false";
description
- "The nexthop's raw flags value.";
+ "Nexthop is directly connected.";
}
- leaf is-duplicate {
- type empty;
+ uses rt-types:mpls-label-stack {
description
- "Duplicate nexthop; will be ignored.";
+ "Nexthop's MPLS label stack.";
}
+ }
- leaf is-recursive {
+ /*
+ * operational common attributes for nexthop
+ */
+ grouping frr-nexthop-operational {
+ leaf duplicate {
type empty;
+ config false;
description
- "Nexthop must be resolved through another gateway.";
+ "Duplicate nexthop";
}
- leaf is-onlink {
+ leaf recursive {
type empty;
+ config false;
description
- "Nexthop is directly connected.";
+ "Nexthop resolved through another gateway.";
}
- leaf is-active {
+ leaf active {
type empty;
+ config false;
description
"Nexthop is active.";
}
- uses rt-types:mpls-label-stack {
+ leaf fib {
+ type empty;
+ config false;
description
- "Nexthop's MPLS label stack.";
+ "Nexthop is installed in fib.";
}
- leaf mtu {
- type uint32;
+ leaf weight {
+ type uint8;
+ config false;
description
- "The nexthop's specific MTU.";
+ "Weight to be used by the nexthop for purposes of ECMP";
}
}
- // End of nexthop
/*
- * Nexthop-group container
+ * Single nexthop grouping.
*/
-
- grouping frr-nexthop-group {
- description
- "A nexthop-group, represented as a list of nexthop objects.";
- leaf name {
- type string;
+ grouping frr-nexthop {
+ container frr-nexthops {
description
- "The nexthop-group name.";
+ "FRR nexthop object.";
+ list nexthop {
+ key "nh-type gateway interface";
+ description
+ "A list of nexthop objects.";
+ uses frr-nexthop-attributes;
+ }
}
+ }
+
- list entry {
- key "id";
+ /*
+ * Container for FRR nexthop group.
+ */
+ grouping frr-nexthop-grouping {
+ list nexthop-group {
+ key "name";
description
- "A list of nexthop objects.";
- leaf id {
- type uint32;
+ "A group of nexthops.";
+
+ leaf name {
+ type string;
description
- "Identifies a nexthop within a nexthop group; the entries
- are ordered by id value, and the value has no other meaning.";
+ "The nexthop-group name.";
}
uses frr-nexthop;
}
}
- // End of frr-nexthop-group
+ container frr-nexthop-group {
+ description
+ "A nexthop-group, represented as a list of nexthop objects.";
+ uses frr-nexthop-grouping;
+ }
+
+ typedef nexthop-group-ref {
+ type leafref {
+ require-instance false;
+ path "/frr-nexthop:frr-nexthop-group/frr-nexthop:nexthop-group/frr-nexthop:name";
+ }
+ }
+
+ /*
+ * Augment weight attributes to nexthop group.
+ */
+ augment "/frr-nexthop-group/nexthop-group/frr-nexthops/nexthop" {
+ leaf weight {
+ type uint8;
+ description
+ "Weight to be used by the nexthop for purposes of ECMP";
+ }
+ }
}
diff --git a/yang/frr-routing.yang b/yang/frr-routing.yang
new file mode 100644
index 000000000..615a81c72
--- /dev/null
+++ b/yang/frr-routing.yang
@@ -0,0 +1,135 @@
+module frr-routing {
+ yang-version "1.1";
+ namespace "http://frrouting.org/yang/routing";
+ prefix "rt";
+
+ import ietf-yang-types {
+ prefix "yang";
+ }
+
+ import frr-vrf {
+ prefix frr-vrf;
+ }
+
+ organization
+ "Free Range Routing";
+
+ contact
+ "FRR Users List: <mailto:frog@lists.frrouting.org>
+ FRR Development List: <mailto:dev@lists.frrouting.org>";
+
+ description
+ "This YANG module defines essential components for the management
+ of a routing subsystem.";
+
+ revision 2019-08-15 {
+ description
+ "Initial revision.";
+ }
+
+ /* Identities */
+
+ identity address-family {
+ description
+ "Base identity from which identities describing address
+ families are derived.";
+ }
+
+ identity ipv4 {
+ base address-family;
+ description
+ "This identity represents an IPv4 address family.";
+ }
+
+ identity ipv6 {
+ base address-family;
+ description
+ "This identity represents an IPv6 address family.";
+ }
+
+ identity control-plane-protocol {
+ description
+ "Base identity from which control-plane protocol identities are
+ derived.";
+ }
+
+ identity routing-protocol {
+ base control-plane-protocol;
+ description
+ "Identity from which Layer 3 routing protocol identities are
+ derived.";
+ }
+
+ /* Type Definitions */
+
+ typedef administrative-distance {
+ type uint8 {
+ range "1..255";
+ }
+ description
+ "Admin distance associated with the route.";
+ }
+
+ /* Groupings */
+
+ grouping address-family {
+ description
+ "This grouping provides a leaf identifying an address
+ family.";
+ leaf address-family {
+ type identityref {
+ base address-family;
+ }
+ mandatory true;
+ description
+ "Address family.";
+ }
+ }
+
+ grouping router-id {
+ description
+ "This grouping provides a router ID.";
+ 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.";
+ reference
+ "RFC 2328: OSPF Version 2";
+ }
+ }
+
+ /* Data nodes */
+
+ container routing {
+ description
+ "Configuration parameters for the routing subsystem.";
+ container control-plane-protocols {
+ description
+ "Support for control-plane protocol instances.";
+ list control-plane-protocol {
+ key "type name vrf";
+ description
+ "Each entry contains a control-plane protocol instance.";
+ leaf type {
+ type identityref {
+ base control-plane-protocol;
+ }
+ description
+ "Type of the control-plane protocol";
+ }
+ leaf name {
+ type string;
+ description
+ "An arbitrary name of the control-plane protocol
+ instance.";
+ }
+ leaf vrf {
+ type frr-vrf:vrf-ref;
+ description
+ "vrf for control-plane protocol";
+ }
+ }
+ }
+ }
+}
diff --git a/yang/frr-staticd.yang b/yang/frr-staticd.yang
new file mode 100644
index 000000000..58933c904
--- /dev/null
+++ b/yang/frr-staticd.yang
@@ -0,0 +1,86 @@
+module frr-staticd {
+ yang-version "1.1";
+ namespace "http://frrouting.org/yang/staticd";
+
+ prefix frr-staticd;
+
+ import frr-routing {
+ prefix "frr-rt";
+ }
+
+ import frr-nexthop {
+ prefix frr-nexthop;
+ }
+
+ import ietf-inet-types {
+ prefix inet;
+ }
+
+ organization
+ "Free Range Routing";
+
+ contact
+ "FRR Users List: <mailto:frog@lists.frrouting.org>
+ FRR Development List: <mailto:dev@lists.frrouting.org>";
+
+ description
+ "This module defines a model for managing FRR staticd information.
+ This YANG module augments the ietf-routing with additional
+ nexthop information";
+
+ revision 2019-12-03 {
+ description
+ "Initial revision.";
+ }
+
+ identity static {
+ base frr-rt:routing-protocol;
+ description
+ "'Static' routing pseudo-protocol.";
+ }
+
+ augment "/frr-rt:routing/frr-rt:control-plane-protocols/"
+ + "frr-rt:control-plane-protocol" {
+ container staticd {
+ when "../frr-rt:type = 'frr-staticd:static'" {
+ description
+ "This container is only valid for the 'static' routing
+ protocol.";
+ }
+ description
+ "Support for a 'static' pseudo-protocol instance
+ consists of a list of routes.";
+
+ list prefix-list {
+ key "destination-prefix";
+ description
+ "List of static IP routes.";
+
+ leaf destination-prefix {
+ type inet:ip-address;
+ description
+ "IP destination prefix.";
+ }
+
+ leaf distance {
+ type frr-rt:administrative-distance;
+ description
+ "Admin distance associated with this route.";
+ }
+
+ leaf tag {
+ type uint32 {
+ range "1..4294967295";
+ }
+ description
+ "Route tag";
+ }
+ container frr-staticd-next-hop {
+ description
+ "Augment static route configuration 'nexthop-list'.";
+ uses frr-nexthop:frr-nexthop;
+ }
+ }
+ }
+ }
+}
diff --git a/yang/frr-vrf.yang b/yang/frr-vrf.yang
new file mode 100644
index 000000000..4924a86e8
--- /dev/null
+++ b/yang/frr-vrf.yang
@@ -0,0 +1,60 @@
+module frr-vrf {
+ yang-version 1.1;
+ namespace "http://frrouting.org/yang/vrf";
+ prefix frr-vrf;
+
+ organization
+ "Free Range Routing";
+ contact
+ "FRR Users List: <mailto:frog@lists.frrouting.org>
+ FRR Development List: <mailto:dev@lists.frrouting.org>";
+ description
+ "This module defines a model for managing FRR VRF.";
+
+ revision 2019-12-06 {
+ description
+ "Initial revision.";
+ }
+
+ typedef vrf-ref {
+ type leafref {
+ path "/frr-vrf:lib/frr-vrf:vrf/frr-vrf:name";
+ require-instance false;
+ }
+ description
+ "Reference to a VRF";
+ }
+
+ container lib {
+ list vrf {
+ key "name";
+ description
+ "VRF.";
+ leaf name {
+ type string {
+ length "1..36";
+ }
+ description
+ "VRF name.";
+ }
+
+ container state {
+ config false;
+ leaf id {
+ type uint32 {
+ range "0..4294967295";
+ }
+ description
+ "VRF Id.";
+ }
+
+ leaf active {
+ type boolean;
+ default "false";
+ description
+ "VRF active in kernel.";
+ }
+ }
+ }
+ }
+}
diff --git a/yang/frr-zebra.yang b/yang/frr-zebra.yang
index 736bbc2c8..26e30b5fa 100644
--- a/yang/frr-zebra.yang
+++ b/yang/frr-zebra.yang
@@ -27,10 +27,18 @@ module frr-zebra {
prefix frr-nh;
}
+ import frr-routing {
+ prefix frr-rt;
+ }
+
import frr-interface {
prefix frr-interface;
}
+ import frr-vrf {
+ prefix frr-vrf;
+ }
+
organization
"FRRouting";
contact
@@ -44,6 +52,35 @@ module frr-zebra {
"Initial revision.";
}
+ identity afi-safi-type {
+ description
+ "Base identity type (AFI,SAFI) tuples for RIB";
+ }
+
+ identity ipv4-unicast {
+ base afi-safi-type;
+ description
+ "This identity represents the IPv4 unicast address family.";
+ }
+
+ identity ipv6-unicast {
+ base afi-safi-type;
+ description
+ "This identity represents the IPv6 unicast address family.";
+ }
+
+ identity ipv4-multicast {
+ base afi-safi-type;
+ description
+ "This identity represents the IPv4 multicast address family.";
+ }
+
+ identity ipv6-multicast {
+ base afi-safi-type;
+ description
+ "This identity represents the IPv6 multicast address family.";
+ }
+
typedef unix-timestamp {
type uint32;
units "seconds";
@@ -51,6 +88,65 @@ module frr-zebra {
"An absolute time in seconds since the unix epoch.";
}
+ identity zebra-interface-type {
+ description
+ "zebra interface type.";
+ }
+
+ identity zif-other {
+ base zebra-interface-type;
+ description
+ "Zebra interface type other.";
+ }
+
+ identity zif-bridge {
+ base zebra-interface-type;
+ description
+ "Zebra interface type bridge.";
+ }
+
+ identity zif-vlan {
+ base zebra-interface-type;
+ description
+ "Zebra interface type vlan.";
+ }
+
+ identity zif-vxlan {
+ base zebra-interface-type;
+ description
+ "Zebra interface type vxlan.";
+ }
+
+ identity zif-vrf {
+ base zebra-interface-type;
+ description
+ "Zebra interface type vrf.";
+ }
+
+ identity zif-veth {
+ base zebra-interface-type;
+ description
+ "Zebra interface type veth.";
+ }
+
+ identity zif-bond {
+ base zebra-interface-type;
+ description
+ "Zebra interface type bond.";
+ }
+
+ identity zif-bond-slave {
+ base zebra-interface-type;
+ description
+ "Zebra interface type bond slave.";
+ }
+
+ identity zif-macvlan {
+ base zebra-interface-type;
+ description
+ "Zebra interface type macvlan.";
+ }
+
/*
* Multicast RPF mode configurable type
*/
@@ -132,13 +228,6 @@ module frr-zebra {
grouping route-common {
description
"Common information about a route.";
- leaf vrf {
- type string {
- length "1..36";
- }
- description
- "The route's vrf name.";
- }
leaf distance {
type uint8;
@@ -160,25 +249,25 @@ module frr-zebra {
"Route tag value.";
}
- leaf is-selected {
+ leaf selected {
type empty;
description
"Route is the selected or preferred route for the prefix.";
}
- leaf is-installed {
+ leaf installed {
type empty;
description
"Route is installed in the FIB.";
}
- leaf is-failed {
+ leaf failed {
type empty;
description
"Route installation in FIB has failed.";
}
- leaf is-queued {
+ leaf queued {
type empty;
description
"Route has a pending FIB operation that has not completed.";
@@ -197,17 +286,12 @@ module frr-zebra {
}
leaf uptime {
- type uint32;
- units "seconds";
+ type yang:date-and-time;
description
"Uptime for the route.";
}
- container nexthop-group {
- description
- "Nexthop information for the route.";
- uses frr-nh:frr-nexthop-group;
- }
+ uses frr-nh:frr-nexthop-grouping;
}
// End of route-common
@@ -257,6 +341,7 @@ module frr-zebra {
uses route-common;
}
+ // End of ip6-route
/*
* Information about EVPN VNIs
@@ -343,7 +428,7 @@ module frr-zebra {
"The gateway MAC-IP is being advertised.";
}
- leaf mcase-group {
+ leaf mcast-group {
type rt-types:ipv4-multicast-group-address;
description
"The VNI multicast group for BUM traffic.";
@@ -442,6 +527,7 @@ module frr-zebra {
description
"Debug kernel messages sent.";
}
+
leaf debug-kernel-msg-recv {
type boolean;
description
@@ -515,6 +601,58 @@ module frr-zebra {
}
}
+ grouping ribs {
+ container ribs {
+ description
+ "RIBs supported by FRR.";
+ list rib {
+ key "afi-safi-name table-id";
+ leaf table-id {
+ type uint32;
+ description
+ "Routing Table id (default id - 254).";
+ }
+
+ leaf afi-safi-name {
+ type identityref {
+ base afi-safi-type;
+ }
+ mandatory true;
+ description
+ "AFI, SAFI name.";
+ }
+
+ list route {
+ key "prefix";
+ config false;
+ leaf prefix {
+ type inet:ip-prefix;
+ description
+ "The route's prefix.";
+ }
+ list route-entry {
+ key "protocol";
+ leaf protocol {
+ type frr-route-types:frr-route-types-v4;
+ //TODO: Use unified route types done in PR 5183 when it is merged.
+ //type frr-route-types:frr-route-types;
+ description
+ "The protocol owning the route.";
+ }
+
+ leaf instance {
+ type uint16;
+ must "../protocol = \"ospf\"";
+ description
+ "Retrieve routes from a specific OSPF instance.";
+ }
+ uses route-common;
+ }
+ }
+ }
+ }
+ }
+
// End of zebra container
/*
* RPCs
@@ -532,6 +670,7 @@ module frr-zebra {
description
"Retrieve IPv4 routes.";
}
+
leaf prefix-v4 {
type inet:ipv4-prefix;
description
@@ -605,7 +744,7 @@ module frr-zebra {
type uint32 {
range "1..65535";
}
- must '../protocol = "ospf"';
+ must "../protocol = \"ospf\"";
description
"Retrieve routes from a specific OSPF instance.";
}
@@ -1790,39 +1929,32 @@ module frr-zebra {
description
"Extends interface model with Zebra-related parameters.";
container zebra {
- list ip4-addr-list {
- key "ip4-prefix";
+ list ip-addrs {
+ key "address-family ip-prefix";
description
- "IPv4 prefixes for an interface.";
- leaf ip4-prefix {
- type inet:ipv4-prefix;
+ "IP prefixes for an interface.";
+ uses frr-rt:address-family {
description
- "IPv4 address prefix.";
+ "Address family of the RIB.";
}
- leaf ip4-peer {
- type inet:ipv4-prefix;
+
+ leaf ip-prefix {
+ type inet:ip-prefix;
description
- "Peer prefix, for peer-to-peer interfaces.";
+ "IP address prefix.";
}
+
leaf label {
type string;
description
"Optional string label for the address.";
}
- }
- list ip6-addr-list {
- key "ip6-prefix";
- description
- "IPv6 prefixes for an interface.";
- leaf ip6-prefix {
- type inet:ipv6-prefix;
- description
- "IPv6 address prefix.";
- }
- leaf label {
- type string;
+
+ leaf ip4-peer {
+ when "derived-from-or-self(../address-family, 'ipv4')";
+ type inet:ipv4-prefix;
description
- "Optional string label for the address.";
+ "Peer prefix, for peer-to-peer interfaces.";
}
}
@@ -1831,16 +1963,19 @@ module frr-zebra {
description
"Multicast flag for the interface.";
}
+
leaf link-detect {
type boolean;
description
"Link-detection for the interface.";
}
+
leaf shutdown {
type boolean;
description
"Interface admin status.";
}
+
leaf bandwidth {
type uint32 {
range "1..100000";
@@ -1849,9 +1984,74 @@ module frr-zebra {
"Link bandwidth informational parameter, in megabits.";
}
// TODO -- link-params for (experimental/partial TE use in IGP extensions)
+ container state {
+ config false;
+ description
+ "Operational data.";
+ leaf up-count {
+ type uint16;
+ description
+ "Interface Up count.";
+ }
+
+ leaf down-count {
+ type uint16;
+ description
+ "Interface Down count.";
+ }
+
+ leaf zif-type {
+ type identityref {
+ base zebra-interface-type;
+ }
+ description
+ "zebra interface type.";
+ }
+
+ leaf ptm-status {
+ type string;
+ default "disabled";
+ description
+ "Interface PTM status.";
+ }
+
+ leaf vlan-id {
+ type uint16 {
+ range "1..4094";
+ }
+ description
+ "A VLAN id.";
+ }
+
+ leaf vni-id {
+ type vni-id-type;
+ }
+
+ leaf remote-vtep {
+ type inet:ipv4-address;
+ description
+ "The remote VTEP IP address.";
+ }
+
+ leaf mcast-group {
+ type rt-types:ipv4-multicast-group-address;
+ description
+ "The VNI multicast group for BUM traffic.";
+ }
+ }
}
}
+ augment "/frr-vrf:lib/frr-vrf:vrf" {
+ description
+ "Extends VRF model with Zebra-related parameters.";
+ uses ribs;
+ }
+
+ augment "/frr-vrf:lib/frr-vrf:vrf/ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop" {
+ uses frr-nh:frr-nexthop-operational;
+ }
+
/*
* Main zebra container
*/
diff --git a/yang/ietf/ietf-interfaces.yang b/yang/ietf/ietf-interfaces.yang
new file mode 100644
index 000000000..f66c205ce
--- /dev/null
+++ b/yang/ietf/ietf-interfaces.yang
@@ -0,0 +1,1123 @@
+module ietf-interfaces {
+ yang-version 1.1;
+ namespace "urn:ietf:params:xml:ns:yang:ietf-interfaces";
+ prefix if;
+
+ import ietf-yang-types {
+ prefix yang;
+ }
+
+ organization
+ "IETF NETMOD (Network Modeling) Working Group";
+
+ contact
+ "WG Web: <https://datatracker.ietf.org/wg/netmod/>
+ WG List: <mailto:netmod@ietf.org>
+
+ Editor: Martin Bjorklund
+ <mailto:mbj@tail-f.com>";
+
+ description
+ "This module contains a collection of YANG definitions for
+ managing network interfaces.
+
+ Copyright (c) 2018 IETF Trust and the persons identified as
+ authors of the code. All rights reserved.
+
+ Redistribution and use in source and binary forms, with or
+ without modification, is permitted pursuant to, and subject
+ to the license terms contained in, the Simplified BSD License
+ set forth in Section 4.c of the IETF Trust's Legal Provisions
+ Relating to IETF Documents
+ (https://trustee.ietf.org/license-info).
+
+ This version of this YANG module is part of RFC 8343; see
+ the RFC itself for full legal notices.";
+
+ revision 2018-02-20 {
+ description
+ "Updated to support NMDA.";
+ reference
+ "RFC 8343: A YANG Data Model for Interface Management";
+ }
+
+ revision 2014-05-08 {
+ description
+ "Initial revision.";
+ reference
+ "RFC 7223: A YANG Data Model for Interface Management";
+ }
+
+ /*
+ * Typedefs
+ */
+
+ typedef interface-ref {
+ type leafref {
+ path "/if:interfaces/if:interface/if:name";
+ }
+ description
+ "This type is used by data models that need to reference
+ interfaces.";
+ }
+
+ /*
+ * Identities
+ */
+
+ identity interface-type {
+ description
+ "Base identity from which specific interface types are
+ derived.";
+ }
+
+ /*
+ * Features
+ */
+
+ feature arbitrary-names {
+ description
+ "This feature indicates that the device allows user-controlled
+ interfaces to be named arbitrarily.";
+ }
+ feature pre-provisioning {
+ description
+ "This feature indicates that the device supports
+ pre-provisioning of interface configuration, i.e., it is
+ possible to configure an interface whose physical interface
+ hardware is not present on the device.";
+ }
+ feature if-mib {
+ description
+ "This feature indicates that the device implements
+ the IF-MIB.";
+ reference
+ "RFC 2863: The Interfaces Group MIB";
+ }
+
+ /*
+ * Data nodes
+ */
+
+ container interfaces {
+ description
+ "Interface parameters.";
+
+ list interface {
+ key "name";
+
+ description
+ "The list of interfaces on the device.
+
+ The status of an interface is available in this list in the
+ operational state. If the configuration of a
+ system-controlled interface cannot be used by the system
+ (e.g., the interface hardware present does not match the
+ interface type), then the configuration is not applied to
+ the system-controlled interface shown in the operational
+ state. If the configuration of a user-controlled interface
+ cannot be used by the system, the configured interface is
+ not instantiated in the operational state.
+
+ System-controlled interfaces created by the system are
+ always present in this list in the operational state,
+ whether or not they are configured.";
+
+ leaf name {
+ type string;
+ description
+ "The name of the interface.
+
+ A device MAY restrict the allowed values for this leaf,
+ possibly depending on the type of the interface.
+ For system-controlled interfaces, this leaf is the
+ device-specific name of the interface.
+
+ If a client tries to create configuration for a
+ system-controlled interface that is not present in the
+ operational state, the server MAY reject the request if
+ the implementation does not support pre-provisioning of
+ interfaces or if the name refers to an interface that can
+ never exist in the system. A Network Configuration
+ Protocol (NETCONF) server MUST reply with an rpc-error
+ with the error-tag 'invalid-value' in this case.
+
+ If the device supports pre-provisioning of interface
+ configuration, the 'pre-provisioning' feature is
+ advertised.
+
+ If the device allows arbitrarily named user-controlled
+ interfaces, the 'arbitrary-names' feature is advertised.
+
+ When a configured user-controlled interface is created by
+ the system, it is instantiated with the same name in the
+ operational state.
+
+ A server implementation MAY map this leaf to the ifName
+ MIB object. Such an implementation needs to use some
+ mechanism to handle the differences in size and characters
+ allowed between this leaf and ifName. The definition of
+ such a mechanism is outside the scope of this document.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifName";
+ }
+
+ leaf description {
+ type string;
+ description
+ "A textual description of the interface.
+
+ A server implementation MAY map this leaf to the ifAlias
+ MIB object. Such an implementation needs to use some
+ mechanism to handle the differences in size and characters
+ allowed between this leaf and ifAlias. The definition of
+ such a mechanism is outside the scope of this document.
+
+ Since ifAlias is defined to be stored in non-volatile
+ storage, the MIB implementation MUST map ifAlias to the
+ value of 'description' in the persistently stored
+ configuration.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifAlias";
+ }
+
+ leaf type {
+ type identityref {
+ base interface-type;
+ }
+ mandatory true;
+ description
+ "The type of the interface.
+
+ When an interface entry is created, a server MAY
+ initialize the type leaf with a valid value, e.g., if it
+ is possible to derive the type from the name of the
+ interface.
+
+ If a client tries to set the type of an interface to a
+ value that can never be used by the system, e.g., if the
+ type is not supported or if the type does not match the
+ name of the interface, the server MUST reject the request.
+ A NETCONF server MUST reply with an rpc-error with the
+ error-tag 'invalid-value' in this case.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifType";
+ }
+
+ leaf enabled {
+ type boolean;
+ default "true";
+ description
+ "This leaf contains the configured, desired state of the
+ interface.
+
+ Systems that implement the IF-MIB use the value of this
+ leaf in the intended configuration to set
+ IF-MIB.ifAdminStatus to 'up' or 'down' after an ifEntry
+ has been initialized, as described in RFC 2863.
+
+ Changes in this leaf in the intended configuration are
+ reflected in ifAdminStatus.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifAdminStatus";
+ }
+
+ leaf link-up-down-trap-enable {
+ if-feature if-mib;
+ type enumeration {
+ enum enabled {
+ value 1;
+ description
+ "The device will generate linkUp/linkDown SNMP
+ notifications for this interface.";
+ }
+ enum disabled {
+ value 2;
+ description
+ "The device will not generate linkUp/linkDown SNMP
+ notifications for this interface.";
+ }
+ }
+ description
+ "Controls whether linkUp/linkDown SNMP notifications
+ should be generated for this interface.
+
+ If this node is not configured, the value 'enabled' is
+ operationally used by the server for interfaces that do
+ not operate on top of any other interface (i.e., there are
+ no 'lower-layer-if' entries), and 'disabled' otherwise.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifLinkUpDownTrapEnable";
+ }
+
+ leaf admin-status {
+ if-feature if-mib;
+ type enumeration {
+ enum up {
+ value 1;
+ description
+ "Ready to pass packets.";
+ }
+ enum down {
+ value 2;
+ description
+ "Not ready to pass packets and not in some test mode.";
+ }
+ enum testing {
+ value 3;
+ description
+ "In some test mode.";
+ }
+ }
+ config false;
+ mandatory true;
+ description
+ "The desired state of the interface.
+
+ This leaf has the same read semantics as ifAdminStatus.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifAdminStatus";
+ }
+
+ leaf oper-status {
+ type enumeration {
+ enum up {
+ value 1;
+ description
+ "Ready to pass packets.";
+ }
+ enum down {
+ value 2;
+
+ description
+ "The interface does not pass any packets.";
+ }
+ enum testing {
+ value 3;
+ description
+ "In some test mode. No operational packets can
+ be passed.";
+ }
+ enum unknown {
+ value 4;
+ description
+ "Status cannot be determined for some reason.";
+ }
+ enum dormant {
+ value 5;
+ description
+ "Waiting for some external event.";
+ }
+ enum not-present {
+ value 6;
+ description
+ "Some component (typically hardware) is missing.";
+ }
+ enum lower-layer-down {
+ value 7;
+ description
+ "Down due to state of lower-layer interface(s).";
+ }
+ }
+ config false;
+ mandatory true;
+ description
+ "The current operational state of the interface.
+
+ This leaf has the same semantics as ifOperStatus.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifOperStatus";
+ }
+
+ leaf last-change {
+ type yang:date-and-time;
+ config false;
+ description
+ "The time the interface entered its current operational
+ state. If the current state was entered prior to the
+ last re-initialization of the local network management
+ subsystem, then this node is not present.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifLastChange";
+ }
+
+ leaf if-index {
+ if-feature if-mib;
+ type int32 {
+ range "1..2147483647";
+ }
+ config false;
+ mandatory true;
+ description
+ "The ifIndex value for the ifEntry represented by this
+ interface.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifIndex";
+ }
+
+ leaf phys-address {
+ type yang:phys-address;
+ config false;
+ description
+ "The interface's address at its protocol sub-layer. For
+ example, for an 802.x interface, this object normally
+ contains a Media Access Control (MAC) address. The
+ interface's media-specific modules must define the bit
+ and byte ordering and the format of the value of this
+ object. For interfaces that do not have such an address
+ (e.g., a serial line), this node is not present.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifPhysAddress";
+ }
+
+ leaf-list higher-layer-if {
+ type interface-ref;
+ config false;
+ description
+ "A list of references to interfaces layered on top of this
+ interface.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifStackTable";
+ }
+
+ leaf-list lower-layer-if {
+ type interface-ref;
+ config false;
+
+ description
+ "A list of references to interfaces layered underneath this
+ interface.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifStackTable";
+ }
+
+ leaf speed {
+ type yang:gauge64;
+ units "bits/second";
+ config false;
+ description
+ "An estimate of the interface's current bandwidth in bits
+ per second. For interfaces that do not vary in
+ bandwidth or for those where no accurate estimation can
+ be made, this node should contain the nominal bandwidth.
+ For interfaces that have no concept of bandwidth, this
+ node is not present.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifSpeed, ifHighSpeed";
+ }
+
+ container statistics {
+ config false;
+ description
+ "A collection of interface-related statistics objects.";
+
+ leaf discontinuity-time {
+ type yang:date-and-time;
+ mandatory true;
+ description
+ "The time on the most recent occasion at which any one or
+ more of this interface's counters suffered a
+ discontinuity. If no such discontinuities have occurred
+ since the last re-initialization of the local management
+ subsystem, then this node contains the time the local
+ management subsystem re-initialized itself.";
+ }
+
+ leaf in-octets {
+ type yang:counter64;
+ description
+ "The total number of octets received on the interface,
+ including framing characters.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCInOctets";
+ }
+
+ leaf in-unicast-pkts {
+ type yang:counter64;
+ description
+ "The number of packets, delivered by this sub-layer to a
+ higher (sub-)layer, that were not addressed to a
+ multicast or broadcast address at this sub-layer.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCInUcastPkts";
+ }
+
+ leaf in-broadcast-pkts {
+ type yang:counter64;
+ description
+ "The number of packets, delivered by this sub-layer to a
+ higher (sub-)layer, that were addressed to a broadcast
+ address at this sub-layer.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCInBroadcastPkts";
+ }
+
+ leaf in-multicast-pkts {
+ type yang:counter64;
+ description
+ "The number of packets, delivered by this sub-layer to a
+ higher (sub-)layer, that were addressed to a multicast
+ address at this sub-layer. For a MAC-layer protocol,
+ this includes both Group and Functional addresses.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCInMulticastPkts";
+ }
+
+ leaf in-discards {
+ type yang:counter32;
+ description
+ "The number of inbound packets that were chosen to be
+ discarded even though no errors had been detected to
+ prevent their being deliverable to a higher-layer
+ protocol. One possible reason for discarding such a
+ packet could be to free up buffer space.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifInDiscards";
+ }
+
+ leaf in-errors {
+ type yang:counter32;
+ description
+ "For packet-oriented interfaces, the number of inbound
+ packets that contained errors preventing them from being
+ deliverable to a higher-layer protocol. For character-
+ oriented or fixed-length interfaces, the number of
+ inbound transmission units that contained errors
+ preventing them from being deliverable to a higher-layer
+ protocol.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifInErrors";
+ }
+
+ leaf in-unknown-protos {
+ type yang:counter32;
+
+ description
+ "For packet-oriented interfaces, the number of packets
+ received via the interface that were discarded because
+ of an unknown or unsupported protocol. For
+ character-oriented or fixed-length interfaces that
+ support protocol multiplexing, the number of
+ transmission units received via the interface that were
+ discarded because of an unknown or unsupported protocol.
+ For any interface that does not support protocol
+ multiplexing, this counter is not present.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifInUnknownProtos";
+ }
+
+ leaf out-octets {
+ type yang:counter64;
+ description
+ "The total number of octets transmitted out of the
+ interface, including framing characters.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCOutOctets";
+ }
+
+ leaf out-unicast-pkts {
+ type yang:counter64;
+ description
+ "The total number of packets that higher-level protocols
+ requested be transmitted and that were not addressed
+ to a multicast or broadcast address at this sub-layer,
+ including those that were discarded or not sent.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCOutUcastPkts";
+ }
+
+ leaf out-broadcast-pkts {
+ type yang:counter64;
+ description
+ "The total number of packets that higher-level protocols
+ requested be transmitted and that were addressed to a
+ broadcast address at this sub-layer, including those
+ that were discarded or not sent.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCOutBroadcastPkts";
+ }
+
+ leaf out-multicast-pkts {
+ type yang:counter64;
+ description
+ "The total number of packets that higher-level protocols
+ requested be transmitted and that were addressed to a
+ multicast address at this sub-layer, including those
+ that were discarded or not sent. For a MAC-layer
+ protocol, this includes both Group and Functional
+ addresses.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCOutMulticastPkts";
+ }
+
+ leaf out-discards {
+ type yang:counter32;
+ description
+ "The number of outbound packets that were chosen to be
+ discarded even though no errors had been detected to
+ prevent their being transmitted. One possible reason
+ for discarding such a packet could be to free up buffer
+ space.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifOutDiscards";
+ }
+
+ leaf out-errors {
+ type yang:counter32;
+ description
+ "For packet-oriented interfaces, the number of outbound
+ packets that could not be transmitted because of errors.
+ For character-oriented or fixed-length interfaces, the
+ number of outbound transmission units that could not be
+ transmitted because of errors.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifOutErrors";
+ }
+ }
+
+ }
+ }
+
+ /*
+ * Legacy typedefs
+ */
+
+ typedef interface-state-ref {
+ type leafref {
+ path "/if:interfaces-state/if:interface/if:name";
+ }
+ status deprecated;
+ description
+ "This type is used by data models that need to reference
+ the operationally present interfaces.";
+ }
+
+ /*
+ * Legacy operational state data nodes
+ */
+
+ container interfaces-state {
+ config false;
+ status deprecated;
+ description
+ "Data nodes for the operational state of interfaces.";
+
+ list interface {
+ key "name";
+ status deprecated;
+
+ description
+ "The list of interfaces on the device.
+
+ System-controlled interfaces created by the system are
+ always present in this list, whether or not they are
+ configured.";
+
+ leaf name {
+ type string;
+ status deprecated;
+ description
+ "The name of the interface.
+
+ A server implementation MAY map this leaf to the ifName
+ MIB object. Such an implementation needs to use some
+ mechanism to handle the differences in size and characters
+ allowed between this leaf and ifName. The definition of
+ such a mechanism is outside the scope of this document.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifName";
+ }
+
+ leaf type {
+ type identityref {
+ base interface-type;
+ }
+ mandatory true;
+ status deprecated;
+ description
+ "The type of the interface.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifType";
+ }
+
+ leaf admin-status {
+ if-feature if-mib;
+ type enumeration {
+ enum up {
+ value 1;
+ description
+ "Ready to pass packets.";
+ }
+ enum down {
+ value 2;
+ description
+ "Not ready to pass packets and not in some test mode.";
+ }
+ enum testing {
+ value 3;
+ description
+ "In some test mode.";
+ }
+ }
+ mandatory true;
+ status deprecated;
+ description
+ "The desired state of the interface.
+
+ This leaf has the same read semantics as ifAdminStatus.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifAdminStatus";
+ }
+
+ leaf oper-status {
+ type enumeration {
+ enum up {
+ value 1;
+ description
+ "Ready to pass packets.";
+ }
+ enum down {
+ value 2;
+ description
+ "The interface does not pass any packets.";
+ }
+ enum testing {
+ value 3;
+ description
+ "In some test mode. No operational packets can
+ be passed.";
+ }
+ enum unknown {
+ value 4;
+ description
+ "Status cannot be determined for some reason.";
+ }
+ enum dormant {
+ value 5;
+ description
+ "Waiting for some external event.";
+ }
+ enum not-present {
+ value 6;
+ description
+ "Some component (typically hardware) is missing.";
+ }
+ enum lower-layer-down {
+ value 7;
+ description
+ "Down due to state of lower-layer interface(s).";
+ }
+ }
+ mandatory true;
+ status deprecated;
+ description
+ "The current operational state of the interface.
+
+ This leaf has the same semantics as ifOperStatus.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifOperStatus";
+ }
+
+ leaf last-change {
+ type yang:date-and-time;
+ status deprecated;
+ description
+ "The time the interface entered its current operational
+ state. If the current state was entered prior to the
+ last re-initialization of the local network management
+ subsystem, then this node is not present.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifLastChange";
+ }
+
+ leaf if-index {
+ if-feature if-mib;
+ type int32 {
+ range "1..2147483647";
+ }
+ mandatory true;
+ status deprecated;
+ description
+ "The ifIndex value for the ifEntry represented by this
+ interface.";
+
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifIndex";
+ }
+
+ leaf phys-address {
+ type yang:phys-address;
+ status deprecated;
+ description
+ "The interface's address at its protocol sub-layer. For
+ example, for an 802.x interface, this object normally
+ contains a Media Access Control (MAC) address. The
+ interface's media-specific modules must define the bit
+ and byte ordering and the format of the value of this
+ object. For interfaces that do not have such an address
+ (e.g., a serial line), this node is not present.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifPhysAddress";
+ }
+
+ leaf-list higher-layer-if {
+ type interface-state-ref;
+ status deprecated;
+ description
+ "A list of references to interfaces layered on top of this
+ interface.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifStackTable";
+ }
+
+ leaf-list lower-layer-if {
+ type interface-state-ref;
+ status deprecated;
+ description
+ "A list of references to interfaces layered underneath this
+ interface.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifStackTable";
+ }
+
+ leaf speed {
+ type yang:gauge64;
+ units "bits/second";
+ status deprecated;
+ description
+ "An estimate of the interface's current bandwidth in bits
+ per second. For interfaces that do not vary in
+ bandwidth or for those where no accurate estimation can
+
+ be made, this node should contain the nominal bandwidth.
+ For interfaces that have no concept of bandwidth, this
+ node is not present.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifSpeed, ifHighSpeed";
+ }
+
+ container statistics {
+ status deprecated;
+ description
+ "A collection of interface-related statistics objects.";
+
+ leaf discontinuity-time {
+ type yang:date-and-time;
+ mandatory true;
+ status deprecated;
+ description
+ "The time on the most recent occasion at which any one or
+ more of this interface's counters suffered a
+ discontinuity. If no such discontinuities have occurred
+ since the last re-initialization of the local management
+ subsystem, then this node contains the time the local
+ management subsystem re-initialized itself.";
+ }
+
+ leaf in-octets {
+ type yang:counter64;
+ status deprecated;
+ description
+ "The total number of octets received on the interface,
+ including framing characters.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCInOctets";
+ }
+
+ leaf in-unicast-pkts {
+ type yang:counter64;
+ status deprecated;
+ description
+ "The number of packets, delivered by this sub-layer to a
+ higher (sub-)layer, that were not addressed to a
+ multicast or broadcast address at this sub-layer.
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCInUcastPkts";
+ }
+
+ leaf in-broadcast-pkts {
+ type yang:counter64;
+ status deprecated;
+ description
+ "The number of packets, delivered by this sub-layer to a
+ higher (sub-)layer, that were addressed to a broadcast
+ address at this sub-layer.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCInBroadcastPkts";
+ }
+
+ leaf in-multicast-pkts {
+ type yang:counter64;
+ status deprecated;
+ description
+ "The number of packets, delivered by this sub-layer to a
+ higher (sub-)layer, that were addressed to a multicast
+ address at this sub-layer. For a MAC-layer protocol,
+ this includes both Group and Functional addresses.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCInMulticastPkts";
+ }
+
+ leaf in-discards {
+ type yang:counter32;
+ status deprecated;
+
+ description
+ "The number of inbound packets that were chosen to be
+ discarded even though no errors had been detected to
+ prevent their being deliverable to a higher-layer
+ protocol. One possible reason for discarding such a
+ packet could be to free up buffer space.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifInDiscards";
+ }
+
+ leaf in-errors {
+ type yang:counter32;
+ status deprecated;
+ description
+ "For packet-oriented interfaces, the number of inbound
+ packets that contained errors preventing them from being
+ deliverable to a higher-layer protocol. For character-
+ oriented or fixed-length interfaces, the number of
+ inbound transmission units that contained errors
+ preventing them from being deliverable to a higher-layer
+ protocol.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifInErrors";
+ }
+
+ leaf in-unknown-protos {
+ type yang:counter32;
+ status deprecated;
+ description
+ "For packet-oriented interfaces, the number of packets
+ received via the interface that were discarded because
+ of an unknown or unsupported protocol. For
+ character-oriented or fixed-length interfaces that
+ support protocol multiplexing, the number of
+ transmission units received via the interface that were
+ discarded because of an unknown or unsupported protocol.
+ For any interface that does not support protocol
+ multiplexing, this counter is not present.
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifInUnknownProtos";
+ }
+
+ leaf out-octets {
+ type yang:counter64;
+ status deprecated;
+ description
+ "The total number of octets transmitted out of the
+ interface, including framing characters.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCOutOctets";
+ }
+
+ leaf out-unicast-pkts {
+ type yang:counter64;
+ status deprecated;
+ description
+ "The total number of packets that higher-level protocols
+ requested be transmitted and that were not addressed
+ to a multicast or broadcast address at this sub-layer,
+ including those that were discarded or not sent.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifHCOutUcastPkts";
+ }
+
+ leaf out-broadcast-pkts {
+ type yang:counter64;
+ status deprecated;
+
+ description
+ "The total number of packets that higher-level protocols
+ requested be transmitted and that were addressed to a
+ broadcast address at this sub-layer, including those
+ that were discarded or not sent.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCOutBroadcastPkts";
+ }
+
+ leaf out-multicast-pkts {
+ type yang:counter64;
+ status deprecated;
+ description
+ "The total number of packets that higher-level protocols
+ requested be transmitted and that were addressed to a
+ multicast address at this sub-layer, including those
+ that were discarded or not sent. For a MAC-layer
+ protocol, this includes both Group and Functional
+ addresses.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB -
+ ifHCOutMulticastPkts";
+ }
+
+ leaf out-discards {
+ type yang:counter32;
+ status deprecated;
+ description
+ "The number of outbound packets that were chosen to be
+ discarded even though no errors had been detected to
+ prevent their being transmitted. One possible reason
+ for discarding such a packet could be to free up buffer
+ space.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifOutDiscards";
+ }
+
+ leaf out-errors {
+ type yang:counter32;
+ status deprecated;
+ description
+ "For packet-oriented interfaces, the number of outbound
+ packets that could not be transmitted because of errors.
+ For character-oriented or fixed-length interfaces, the
+ number of outbound transmission units that could not be
+ transmitted because of errors.
+
+ Discontinuities in the value of this counter can occur
+ at re-initialization of the management system and at
+ other times as indicated by the value of
+ 'discontinuity-time'.";
+ reference
+ "RFC 2863: The Interfaces Group MIB - ifOutErrors";
+ }
+ }
+ }
+ }
+}
diff --git a/yang/subdir.am b/yang/subdir.am
index 0e124c5ab..5393781d2 100644
--- a/yang/subdir.am
+++ b/yang/subdir.am
@@ -25,9 +25,12 @@ dist_yangmodels_DATA += yang/frr-nexthop.yang
dist_yangmodels_DATA += yang/frr-test-module.yang
dist_yangmodels_DATA += yang/frr-interface.yang
dist_yangmodels_DATA += yang/frr-route-map.yang
+dist_yangmodels_DATA += yang/frr-vrf.yang
dist_yangmodels_DATA += yang/frr-route-types.yang
-dist_yangmodels_DATA += yang/frr-zebra.yang
+dist_yangmodels_DATA += yang/frr-routing.yang
dist_yangmodels_DATA += yang/ietf/ietf-routing-types.yang
+dist_yangmodels_DATA += yang/frr-igmp.yang
+dist_yangmodels_DATA += yang/ietf/ietf-interfaces.yang
if BFDD
dist_yangmodels_DATA += yang/frr-bfdd.yang
@@ -52,3 +55,11 @@ endif
if VRRPD
dist_yangmodels_DATA += yang/frr-vrrpd.yang
endif
+
+if STATICD
+dist_yangmodels_DATA += yang/frr-staticd.yang
+endif
+
+if ZEBRA
+dist_yangmodels_DATA += yang/frr-zebra.yang
+endif
diff --git a/zebra/interface.c b/zebra/interface.c
index cad382ff0..586a59bb1 100644
--- a/zebra/interface.c
+++ b/zebra/interface.c
@@ -500,7 +500,7 @@ void if_flags_update(struct interface *ifp, uint64_t newflags)
/* Wake up configured address if it is not in current kernel
address. */
-static void if_addr_wakeup(struct interface *ifp)
+void if_addr_wakeup(struct interface *ifp)
{
struct listnode *node, *nnode;
struct connected *ifc;
@@ -1888,6 +1888,24 @@ DEFUN (show_interface_desc_vrf_all,
return CMD_SUCCESS;
}
+int if_multicast_set(struct interface *ifp)
+{
+ struct zebra_if *if_data;
+
+ if (CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
+ if (if_set_flags(ifp, IFF_MULTICAST) < 0) {
+ zlog_debug("Can't set multicast flag on interface %s",
+ ifp->name);
+ return -1;
+ }
+ if_refresh(ifp);
+ }
+ if_data = ifp->info;
+ if_data->multicast = IF_ZEBRA_MULTICAST_ON;
+
+ return 0;
+}
+
DEFUN (multicast,
multicast_cmd,
"multicast",
@@ -1911,6 +1929,24 @@ DEFUN (multicast,
return CMD_SUCCESS;
}
+int if_multicast_unset(struct interface *ifp)
+{
+ struct zebra_if *if_data;
+
+ if (CHECK_FLAG(ifp->status, ZEBRA_INTERFACE_ACTIVE)) {
+ if (if_unset_flags(ifp, IFF_MULTICAST) < 0) {
+ zlog_debug("Can't unset multicast flag on interface %s",
+ ifp->name);
+ return -1;
+ }
+ if_refresh(ifp);
+ }
+ if_data = ifp->info;
+ if_data->multicast = IF_ZEBRA_MULTICAST_OFF;
+
+ return 0;
+}
+
DEFUN (no_multicast,
no_multicast_cmd,
"no multicast",
@@ -1935,23 +1971,35 @@ DEFUN (no_multicast,
return CMD_SUCCESS;
}
-DEFUN (linkdetect,
- linkdetect_cmd,
- "link-detect",
- "Enable link detection on interface\n")
+int if_linkdetect(struct interface *ifp, bool detect)
{
- VTY_DECLVAR_CONTEXT(interface, ifp);
int if_was_operative;
if_was_operative = if_is_no_ptm_operative(ifp);
- SET_FLAG(ifp->status, ZEBRA_INTERFACE_LINKDETECTION);
+ if (detect) {
+ SET_FLAG(ifp->status, ZEBRA_INTERFACE_LINKDETECTION);
- /* When linkdetection is enabled, if might come down */
- if (!if_is_no_ptm_operative(ifp) && if_was_operative)
- if_down(ifp);
+ /* When linkdetection is enabled, if might come down */
+ if (!if_is_no_ptm_operative(ifp) && if_was_operative)
+ if_down(ifp);
+ } else {
+ UNSET_FLAG(ifp->status, ZEBRA_INTERFACE_LINKDETECTION);
+ /* Interface may come up after disabling link detection */
+ if (if_is_operative(ifp) && !if_was_operative)
+ if_up(ifp);
+ }
/* FIXME: Will defer status change forwarding if interface
does not come down! */
+ 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;
}
@@ -1964,18 +2012,29 @@ DEFUN (no_linkdetect,
"Disable link detection on interface\n")
{
VTY_DECLVAR_CONTEXT(interface, ifp);
- int if_was_operative;
- if_was_operative = if_is_no_ptm_operative(ifp);
- UNSET_FLAG(ifp->status, ZEBRA_INTERFACE_LINKDETECTION);
+ if_linkdetect(ifp, false);
+
+ return CMD_SUCCESS;
+}
- /* Interface may come up after disabling link detection */
- if (if_is_operative(ifp) && !if_was_operative)
- if_up(ifp);
+int if_shutdown(struct interface *ifp)
+{
+ struct zebra_if *if_data;
- /* FIXME: see linkdetect_cmd */
+ if (ifp->ifindex != IFINDEX_INTERNAL) {
+ /* send RA lifetime of 0 before stopping. rfc4861/6.2.5 */
+ rtadv_stop_ra(ifp);
+ if (if_unset_flags(ifp, IFF_UP) < 0) {
+ zlog_debug("Can't shutdown interface %s", ifp->name);
+ return -1;
+ }
+ if_refresh(ifp);
+ }
+ if_data = ifp->info;
+ if_data->shutdown = IF_ZEBRA_SHUTDOWN_ON;
- return CMD_SUCCESS;
+ return 0;
}
DEFUN (shutdown_if,
@@ -2003,6 +2062,30 @@ DEFUN (shutdown_if,
return CMD_SUCCESS;
}
+int if_no_shutdown(struct interface *ifp)
+{
+ struct zebra_if *if_data;
+
+ if (ifp->ifindex != IFINDEX_INTERNAL) {
+ if (if_set_flags(ifp, IFF_UP | IFF_RUNNING) < 0) {
+ zlog_debug("Can't up interface %s", ifp->name);
+ return -1;
+ }
+ 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_SHUTDOWN_OFF;
+
+ return 0;
+}
+
DEFUN (no_shutdown_if,
no_shutdown_if_cmd,
"no shutdown",
@@ -2758,6 +2841,79 @@ DEFUN (no_link_params_use_bw,
return CMD_SUCCESS;
}
+int 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);
+ if (!ifc) {
+ ifc = connected_new();
+ ifc->ifp = ifp;
+
+ /* Address. */
+ p = prefix_ipv4_new();
+ *p = lp;
+ ifc->address = (struct prefix *)p;
+
+ if (pp) {
+ SET_FLAG(ifc->flags, ZEBRA_IFA_PEER);
+ p = prefix_ipv4_new();
+ *p = *(struct prefix_ipv4 *)pp;
+ ifc->destination = (struct prefix *)p;
+ }
+
+ /* Label. */
+ if (label)
+ ifc->label = XSTRDUP(MTYPE_CONNECTED_LABEL, label);
+
+ /* Add to linked list. */
+ listnode_add(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_SHUTDOWN_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.\n",
+ 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.
+ * 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)
@@ -2852,6 +3008,51 @@ static int ip_address_install(struct vty *vty, struct interface *ifp,
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\n",
+ 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\n", ifp->name);
+ return -1;
+ }
+ 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)) {
+ listnode_delete(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) {
+ zlog_debug("Can't unset interface IP address: %s.\n",
+ 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)
@@ -3005,6 +3206,71 @@ DEFUN (no_ip_address_label,
}
#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. */
+ listnode_add(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_SHUTDOWN_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.\n",
+ 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)
diff --git a/zebra/interface.h b/zebra/interface.h
index b7e90a0c3..80799b58a 100644
--- a/zebra/interface.h
+++ b/zebra/interface.h
@@ -440,6 +440,17 @@ extern void zebra_if_update_link(struct interface *ifp, ifindex_t link_ifindex,
ns_id_t ns_id);
extern void zebra_if_update_all_links(void);
extern void zebra_if_set_protodown(struct interface *ifp, bool down);
+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 int if_shutdown(struct interface *ifp);
+extern int if_no_shutdown(struct interface *ifp);
+extern int if_multicast_set(struct interface *ifp);
+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);
/* Nexthop group connected functions */
extern void if_nhg_dependents_add(struct interface *ifp,
diff --git a/zebra/main.c b/zebra/main.c
index fb7e926c5..e230a744f 100644
--- a/zebra/main.c
+++ b/zebra/main.c
@@ -54,6 +54,7 @@
#include "zebra/zebra_pbr.h"
#include "zebra/zebra_vxlan.h"
#include "zebra/zebra_routemap.h"
+#include "zebra/zebra_nb.h"
#if defined(HANDLE_NETLINK_FUZZING)
#include "zebra/kernel_netlink.h"
@@ -247,6 +248,7 @@ static const struct frr_yang_module_info *const zebra_yang_modules[] = {
&frr_interface_info,
&frr_route_map_info,
&frr_zebra_info,
+ &frr_vrf_info,
};
FRR_DAEMON_INFO(
diff --git a/zebra/subdir.am b/zebra/subdir.am
index 71094cb52..ca1bc3662 100644
--- a/zebra/subdir.am
+++ b/zebra/subdir.am
@@ -75,7 +75,6 @@ zebra_zebra_SOURCES = \
zebra/zebra_mlag.c \
zebra/zebra_mlag_vty.c \
zebra/zebra_l2.c \
- zebra/zebra_northbound.c \
zebra/zebra_memory.c \
zebra/zebra_dplane.c \
zebra/zebra_mpls.c \
@@ -102,6 +101,10 @@ zebra_zebra_SOURCES = \
zebra/zebra_netns_notify.c \
zebra/table_manager.c \
zebra/zapi_msg.c \
+ zebra/zebra_nb.c \
+ zebra/zebra_nb_config.c \
+ zebra/zebra_nb_rpcs.c \
+ zebra/zebra_nb_state.c \
zebra/zebra_errors.c \
zebra/zebra_gr.c \
# end
@@ -165,6 +168,7 @@ noinst_HEADERS += \
zebra/zebra_netns_notify.h \
zebra/table_manager.h \
zebra/zapi_msg.h \
+ zebra/zebra_nb.h \
zebra/zebra_errors.h \
# end
@@ -193,7 +197,6 @@ endif
endif
nodist_zebra_zebra_SOURCES = \
- yang/frr-nexthop.yang.c \
yang/frr-zebra.yang.c \
# end
diff --git a/zebra/zebra_nb.c b/zebra/zebra_nb.c
new file mode 100644
index 000000000..1f3468d6d
--- /dev/null
+++ b/zebra/zebra_nb.c
@@ -0,0 +1,692 @@
+/*
+ * Copyright (C) 2020 Cumulus Networks, Inc.
+ * Chirag Shah
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; see the file COPYING; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#include <zebra.h>
+#include "northbound.h"
+#include "libfrr.h"
+#include "zebra_nb.h"
+
+/* clang-format off */
+const struct frr_yang_module_info frr_zebra_info = {
+ .name = "frr-zebra",
+ .nodes = {
+ {
+ .xpath = "/frr-zebra:zebra/mcast-rpf-lookup",
+ .cbs = {
+ .modify = zebra_mcast_rpf_lookup_modify,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/ip-forwarding",
+ .cbs = {
+ .modify = zebra_ip_forwarding_modify,
+ .destroy = zebra_ip_forwarding_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/ipv6-forwarding",
+ .cbs = {
+ .modify = zebra_ipv6_forwarding_modify,
+ .destroy = zebra_ipv6_forwarding_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/workqueue-hold-timer",
+ .cbs = {
+ .modify = zebra_workqueue_hold_timer_modify,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/zapi-packets",
+ .cbs = {
+ .modify = zebra_zapi_packets_modify,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/import-kernel-table/table-id",
+ .cbs = {
+ .modify = zebra_import_kernel_table_table_id_modify,
+ .destroy = zebra_import_kernel_table_table_id_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/import-kernel-table/distance",
+ .cbs = {
+ .modify = zebra_import_kernel_table_distance_modify,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/import-kernel-table/route-map",
+ .cbs = {
+ .modify = zebra_import_kernel_table_route_map_modify,
+ .destroy = zebra_import_kernel_table_route_map_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/allow-external-route-update",
+ .cbs = {
+ .create = zebra_allow_external_route_update_create,
+ .destroy = zebra_allow_external_route_update_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/dplane-queue-limit",
+ .cbs = {
+ .modify = zebra_dplane_queue_limit_modify,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/vrf-vni-mapping",
+ .cbs = {
+ .create = zebra_vrf_vni_mapping_create,
+ .destroy = zebra_vrf_vni_mapping_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/vrf-vni-mapping/vni-id",
+ .cbs = {
+ .modify = zebra_vrf_vni_mapping_vni_id_modify,
+ .destroy = zebra_vrf_vni_mapping_vni_id_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/vrf-vni-mapping/prefix-only",
+ .cbs = {
+ .create = zebra_vrf_vni_mapping_prefix_only_create,
+ .destroy = zebra_vrf_vni_mapping_prefix_only_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-events",
+ .cbs = {
+ .modify = zebra_debugs_debug_events_modify,
+ .destroy = zebra_debugs_debug_events_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-zapi-send",
+ .cbs = {
+ .modify = zebra_debugs_debug_zapi_send_modify,
+ .destroy = zebra_debugs_debug_zapi_send_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-zapi-recv",
+ .cbs = {
+ .modify = zebra_debugs_debug_zapi_recv_modify,
+ .destroy = zebra_debugs_debug_zapi_recv_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-zapi-detail",
+ .cbs = {
+ .modify = zebra_debugs_debug_zapi_detail_modify,
+ .destroy = zebra_debugs_debug_zapi_detail_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-kernel",
+ .cbs = {
+ .modify = zebra_debugs_debug_kernel_modify,
+ .destroy = zebra_debugs_debug_kernel_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-kernel-msg-send",
+ .cbs = {
+ .modify = zebra_debugs_debug_kernel_msg_send_modify,
+ .destroy = zebra_debugs_debug_kernel_msg_send_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-kernel-msg-recv",
+ .cbs = {
+ .modify = zebra_debugs_debug_kernel_msg_recv_modify,
+ .destroy = zebra_debugs_debug_kernel_msg_recv_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-rib",
+ .cbs = {
+ .modify = zebra_debugs_debug_rib_modify,
+ .destroy = zebra_debugs_debug_rib_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-rib-detail",
+ .cbs = {
+ .modify = zebra_debugs_debug_rib_detail_modify,
+ .destroy = zebra_debugs_debug_rib_detail_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-fpm",
+ .cbs = {
+ .modify = zebra_debugs_debug_fpm_modify,
+ .destroy = zebra_debugs_debug_fpm_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-nht",
+ .cbs = {
+ .modify = zebra_debugs_debug_nht_modify,
+ .destroy = zebra_debugs_debug_nht_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-nht-detail",
+ .cbs = {
+ .modify = zebra_debugs_debug_nht_detail_modify,
+ .destroy = zebra_debugs_debug_nht_detail_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-mpls",
+ .cbs = {
+ .modify = zebra_debugs_debug_mpls_modify,
+ .destroy = zebra_debugs_debug_mpls_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-vxlan",
+ .cbs = {
+ .modify = zebra_debugs_debug_vxlan_modify,
+ .destroy = zebra_debugs_debug_vxlan_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-pw",
+ .cbs = {
+ .modify = zebra_debugs_debug_pw_modify,
+ .destroy = zebra_debugs_debug_pw_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-dplane",
+ .cbs = {
+ .modify = zebra_debugs_debug_dplane_modify,
+ .destroy = zebra_debugs_debug_dplane_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-dplane-detail",
+ .cbs = {
+ .modify = zebra_debugs_debug_dplane_detail_modify,
+ .destroy = zebra_debugs_debug_dplane_detail_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:zebra/debugs/debug-mlag",
+ .cbs = {
+ .modify = zebra_debugs_debug_mlag_modify,
+ .destroy = zebra_debugs_debug_mlag_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-route-information",
+ .cbs = {
+ .rpc = get_route_information_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-v6-mroute-info",
+ .cbs = {
+ .rpc = get_v6_mroute_info_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-vrf-info",
+ .cbs = {
+ .rpc = get_vrf_info_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-vrf-vni-info",
+ .cbs = {
+ .rpc = get_vrf_vni_info_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-evpn-info",
+ .cbs = {
+ .rpc = get_evpn_info_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-vni-info",
+ .cbs = {
+ .rpc = get_vni_info_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-evpn-vni-rmac",
+ .cbs = {
+ .rpc = get_evpn_vni_rmac_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-evpn-vni-nexthops",
+ .cbs = {
+ .rpc = get_evpn_vni_nexthops_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:clear-evpn-dup-addr",
+ .cbs = {
+ .rpc = clear_evpn_dup_addr_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-evpn-macs",
+ .cbs = {
+ .rpc = get_evpn_macs_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-evpn-arp-cache",
+ .cbs = {
+ .rpc = get_evpn_arp_cache_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-pbr-ipset",
+ .cbs = {
+ .rpc = get_pbr_ipset_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-pbr-iptable",
+ .cbs = {
+ .rpc = get_pbr_iptable_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-zebra:get-debugs",
+ .cbs = {
+ .rpc = get_debugs_rpc,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip-addrs",
+ .cbs = {
+ .create = lib_interface_zebra_ip_addrs_create,
+ .destroy = lib_interface_zebra_ip_addrs_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/label",
+ .cbs = {
+ .modify = lib_interface_zebra_ip_addrs_label_modify,
+ .destroy = lib_interface_zebra_ip_addrs_label_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/ip4-peer",
+ .cbs = {
+ .modify = lib_interface_zebra_ip_addrs_ip4_peer_modify,
+ .destroy = lib_interface_zebra_ip_addrs_ip4_peer_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/multicast",
+ .cbs = {
+ .modify = lib_interface_zebra_multicast_modify,
+ .destroy = lib_interface_zebra_multicast_destroy,
+ }
+ },
+ {
+ .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",
+ .cbs = {
+ .modify = lib_interface_zebra_shutdown_modify,
+ .destroy = lib_interface_zebra_shutdown_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/bandwidth",
+ .cbs = {
+ .modify = lib_interface_zebra_bandwidth_modify,
+ .destroy = lib_interface_zebra_bandwidth_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/up-count",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_up_count_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/down-count",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_down_count_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/zif-type",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_zif_type_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/ptm-status",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_ptm_status_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/vlan-id",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_vlan_id_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/vni-id",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_vni_id_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/remote-vtep",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_remote_vtep_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/state/mcast-group",
+ .cbs = {
+ .get_elem = lib_interface_zebra_state_mcast_group_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib",
+ .cbs = {
+ .create = lib_vrf_ribs_rib_create,
+ .destroy = lib_vrf_ribs_rib_destroy,
+ .get_next = lib_vrf_ribs_rib_get_next,
+ .get_keys = lib_vrf_ribs_rib_get_keys,
+ .lookup_entry = lib_vrf_ribs_rib_lookup_entry,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route",
+ .cbs = {
+ .get_next = lib_vrf_ribs_rib_route_get_next,
+ .get_keys = lib_vrf_ribs_rib_route_get_keys,
+ .lookup_entry = lib_vrf_ribs_rib_route_lookup_entry,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/prefix",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_prefix_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry",
+ .cbs = {
+ .get_next = lib_vrf_ribs_rib_route_route_entry_get_next,
+ .get_keys = lib_vrf_ribs_rib_route_route_entry_get_keys,
+ .lookup_entry = lib_vrf_ribs_rib_route_route_entry_lookup_entry,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/protocol",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_protocol_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/instance",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_instance_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/distance",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_distance_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/metric",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_metric_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/tag",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_tag_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/selected",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_selected_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/installed",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_installed_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/failed",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_failed_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/queued",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_queued_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/internal-flags",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_internal_flags_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/internal-status",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_internal_status_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/uptime",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_uptime_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group",
+ .cbs = {
+ .get_next = lib_vrf_ribs_rib_route_route_entry_nexthop_group_get_next,
+ .get_keys = lib_vrf_ribs_rib_route_route_entry_nexthop_group_get_keys,
+ .lookup_entry = lib_vrf_ribs_rib_route_route_entry_nexthop_group_lookup_entry,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/name",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_name_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop",
+ .cbs = {
+ .get_next = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_get_next,
+ .get_keys = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_get_keys,
+ .lookup_entry = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_lookup_entry,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/nh-type",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_nh_type_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/vrf",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_vrf_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/gateway",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_gateway_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/interface",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_interface_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/bh-type",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_bh_type_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/onlink",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_onlink_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry",
+ .cbs = {
+ .get_next = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_get_next,
+ .get_keys = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_get_keys,
+ .lookup_entry = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_lookup_entry,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/id",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_id_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/label",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_label_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/ttl",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_ttl_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/traffic-class",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_traffic_class_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/duplicate",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_duplicate_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/recursive",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_recursive_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/active",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_active_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/fib",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_fib_get_elem,
+ }
+ },
+ {
+ .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv4-prefix-length",
+ .cbs = {
+ .modify = lib_route_map_entry_match_condition_ipv4_prefix_length_modify,
+ .destroy = lib_route_map_entry_match_condition_ipv4_prefix_length_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv6-prefix-length",
+ .cbs = {
+ .modify = lib_route_map_entry_match_condition_ipv6_prefix_length_modify,
+ .destroy = lib_route_map_entry_match_condition_ipv6_prefix_length_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-protocol",
+ .cbs = {
+ .modify = lib_route_map_entry_match_condition_source_protocol_modify,
+ .destroy = lib_route_map_entry_match_condition_source_protocol_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-instance",
+ .cbs = {
+ .modify = lib_route_map_entry_match_condition_source_instance_modify,
+ .destroy = lib_route_map_entry_match_condition_source_instance_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v4",
+ .cbs = {
+ .modify = lib_route_map_entry_set_action_source_v4_modify,
+ .destroy = lib_route_map_entry_set_action_source_v4_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v6",
+ .cbs = {
+ .modify = lib_route_map_entry_set_action_source_v6_modify,
+ .destroy = lib_route_map_entry_set_action_source_v6_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/weight",
+ .cbs = {
+ .get_elem = lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_weight_get_elem,
+ }
+ },
+ {
+ .xpath = NULL,
+ },
+ }
+};
diff --git a/zebra/zebra_nb.h b/zebra/zebra_nb.h
new file mode 100644
index 000000000..01a44e552
--- /dev/null
+++ b/zebra/zebra_nb.h
@@ -0,0 +1,488 @@
+/*
+ * Copyright (C) 2020 Cumulus Networks, Inc.
+ * Chirag Shah
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; see the file COPYING; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#ifndef ZEBRA_ZEBRA_NB_H_
+#define ZEBRA_ZEBRA_NB_H_
+
+extern const struct frr_yang_module_info frr_zebra_info;
+
+/* prototypes */
+int get_route_information_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_v6_mroute_info_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_vrf_info_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_vrf_vni_info_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_evpn_info_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_vni_info_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_evpn_vni_rmac_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_evpn_vni_nexthops_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int clear_evpn_dup_addr_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_evpn_macs_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_evpn_arp_cache_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_pbr_ipset_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_pbr_iptable_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int get_debugs_rpc(const char *xpath, const struct list *input,
+ struct list *output);
+int zebra_mcast_rpf_lookup_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_ip_forwarding_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_ip_forwarding_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_ipv6_forwarding_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_ipv6_forwarding_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_workqueue_hold_timer_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_zapi_packets_modify(enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_import_kernel_table_table_id_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_import_kernel_table_table_id_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_import_kernel_table_distance_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_import_kernel_table_route_map_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_import_kernel_table_route_map_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_allow_external_route_update_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_allow_external_route_update_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_dplane_queue_limit_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_vrf_vni_mapping_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_vrf_vni_mapping_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_vrf_vni_mapping_vni_id_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_vrf_vni_mapping_vni_id_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_vrf_vni_mapping_prefix_only_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_vrf_vni_mapping_prefix_only_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_events_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_events_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_zapi_send_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_zapi_send_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_zapi_recv_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_zapi_recv_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_zapi_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_zapi_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_kernel_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_kernel_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_kernel_msg_send_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_kernel_msg_send_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_kernel_msg_recv_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_kernel_msg_recv_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_rib_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_rib_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_rib_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_rib_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_fpm_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_fpm_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_nht_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_nht_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_nht_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_nht_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_mpls_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_mpls_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_vxlan_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_vxlan_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_pw_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_pw_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_dplane_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_dplane_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_dplane_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_dplane_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int zebra_debugs_debug_mlag_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int zebra_debugs_debug_mlag_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_interface_zebra_ip_addrs_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_interface_zebra_ip_addrs_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_interface_zebra_ip_addrs_label_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_interface_zebra_ip_addrs_label_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_interface_zebra_ip_addrs_ip4_peer_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_interface_zebra_ip_addrs_ip4_peer_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_interface_zebra_multicast_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_interface_zebra_multicast_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_interface_zebra_link_detect_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_interface_zebra_link_detect_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_interface_zebra_shutdown_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_interface_zebra_shutdown_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_interface_zebra_bandwidth_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_interface_zebra_bandwidth_destroy(enum nb_event event,
+ const struct lyd_node *dnode);
+int lib_route_map_entry_match_condition_ipv4_prefix_length_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_route_map_entry_match_condition_ipv4_prefix_length_destroy(
+ enum nb_event event, const struct lyd_node *dnode);
+int lib_route_map_entry_match_condition_ipv6_prefix_length_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_route_map_entry_match_condition_ipv6_prefix_length_destroy(
+ enum nb_event event, const struct lyd_node *dnode);
+int lib_route_map_entry_match_condition_source_protocol_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_route_map_entry_match_condition_source_protocol_destroy(
+ enum nb_event event, const struct lyd_node *dnode);
+int lib_route_map_entry_match_condition_source_instance_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_route_map_entry_match_condition_source_instance_destroy(
+ enum nb_event event, const struct lyd_node *dnode);
+int lib_route_map_entry_set_action_source_v4_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_route_map_entry_set_action_source_v4_destroy(
+ enum nb_event event, const struct lyd_node *dnode);
+int lib_route_map_entry_set_action_source_v6_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_route_map_entry_set_action_source_v6_destroy(
+ enum nb_event event, const struct lyd_node *dnode);
+struct yang_data *
+lib_interface_zebra_state_up_count_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_zebra_state_down_count_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_zebra_state_zif_type_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_zebra_state_ptm_status_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_zebra_state_vlan_id_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_zebra_state_vni_id_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_zebra_state_remote_vtep_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_interface_zebra_state_mcast_group_get_elem(const char *xpath,
+ const void *list_entry);
+int lib_vrf_ribs_rib_create(enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_vrf_ribs_rib_destroy(enum nb_event event, const struct lyd_node *dnode);
+const void *lib_vrf_ribs_rib_get_next(const void *parent_list_entry,
+ const void *list_entry);
+int lib_vrf_ribs_rib_get_keys(const void *list_entry,
+ struct yang_list_keys *keys);
+const void *lib_vrf_ribs_rib_lookup_entry(const void *parent_list_entry,
+ const struct yang_list_keys *keys);
+const void *lib_vrf_ribs_rib_route_get_next(const void *parent_list_entry,
+ const void *list_entry);
+int lib_vrf_ribs_rib_route_get_keys(const void *list_entry,
+ struct yang_list_keys *keys);
+const void *
+lib_vrf_ribs_rib_route_lookup_entry(const void *parent_list_entry,
+ const struct yang_list_keys *keys);
+struct yang_data *
+lib_vrf_ribs_rib_route_prefix_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_protocol_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_protocol_v6_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_vrf_ribs_rib_route_vrf_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_distance_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_metric_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_vrf_ribs_rib_route_tag_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_selected_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_installed_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_failed_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_queued_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_internal_flags_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_internal_status_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_uptime_get_elem(const char *xpath,
+ const void *list_entry);
+const void *
+lib_vrf_ribs_rib_route_nexthop_group_get_next(const void *parent_list_entry,
+ const void *list_entry);
+int lib_vrf_ribs_rib_route_nexthop_group_get_keys(const void *list_entry,
+ struct yang_list_keys *keys);
+const void *lib_vrf_ribs_rib_route_nexthop_group_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys);
+struct yang_data *
+lib_vrf_ribs_rib_route_nexthop_group_name_get_elem(const char *xpath,
+ const void *list_entry);
+const void *lib_vrf_ribs_rib_route_nexthop_group_frr_nexthops_nexthop_get_next(
+ const void *parent_list_entry, const void *list_entry);
+int lib_vrf_ribs_rib_route_nexthop_group_frr_nexthops_nexthop_get_keys(
+ const void *list_entry, struct yang_list_keys *keys);
+int lib_vrf_ribs_rib_create(enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource);
+int lib_vrf_ribs_rib_destroy(enum nb_event event, const struct lyd_node *dnode);
+const void *lib_vrf_ribs_rib_get_next(const void *parent_list_entry,
+ const void *list_entry);
+int lib_vrf_ribs_rib_get_keys(const void *list_entry,
+ struct yang_list_keys *keys);
+const void *lib_vrf_ribs_rib_lookup_entry(const void *parent_list_entry,
+ const struct yang_list_keys *keys);
+const void *lib_vrf_ribs_rib_route_get_next(const void *parent_list_entry,
+ const void *list_entry);
+int lib_vrf_ribs_rib_route_get_keys(const void *list_entry,
+ struct yang_list_keys *keys);
+const void *
+lib_vrf_ribs_rib_route_lookup_entry(const void *parent_list_entry,
+ const struct yang_list_keys *keys);
+struct yang_data *
+lib_vrf_ribs_rib_route_prefix_get_elem(const char *xpath,
+ const void *list_entry);
+const void *
+lib_vrf_ribs_rib_route_route_entry_get_next(const void *parent_list_entry,
+ const void *list_entry);
+int lib_vrf_ribs_rib_route_route_entry_get_keys(const void *list_entry,
+ struct yang_list_keys *keys);
+const void *lib_vrf_ribs_rib_route_route_entry_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_protocol_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_instance_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_distance_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_metric_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_tag_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_selected_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_installed_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_failed_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_queued_get_elem(const char *xpath,
+ const void *list_entry);
+struct yang_data *lib_vrf_ribs_rib_route_route_entry_internal_flags_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *lib_vrf_ribs_rib_route_route_entry_internal_status_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_uptime_get_elem(const char *xpath,
+ const void *list_entry);
+const void *lib_vrf_ribs_rib_route_route_entry_nexthop_group_get_next(
+ const void *parent_list_entry, const void *list_entry);
+int lib_vrf_ribs_rib_route_route_entry_nexthop_group_get_keys(
+ const void *list_entry, struct yang_list_keys *keys);
+const void *lib_vrf_ribs_rib_route_route_entry_nexthop_group_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_name_get_elem(
+ const char *xpath, const void *list_entry);
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_get_next(
+ const void *parent_list_entry, const void *list_entry);
+int lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_get_keys(
+ const void *list_entry, struct yang_list_keys *keys);
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_nh_type_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_vrf_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_gateway_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_interface_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_bh_type_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_onlink_get_elem(
+ const char *xpath, const void *list_entry);
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_get_next(
+ const void *parent_list_entry, const void *list_entry);
+int lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_get_keys(
+ const void *list_entry, struct yang_list_keys *keys);
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_id_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_label_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_ttl_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_traffic_class_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_duplicate_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_recursive_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_active_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_fib_get_elem(
+ const char *xpath, const void *list_entry);
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_weight_get_elem(
+ const char *xpath, const void *list_entry);
+
+#endif
diff --git a/zebra/zebra_nb_config.c b/zebra/zebra_nb_config.c
new file mode 100644
index 000000000..311922f2e
--- /dev/null
+++ b/zebra/zebra_nb_config.c
@@ -0,0 +1,1672 @@
+/*
+ * Copyright (C) 2019 Cumulus Networks, Inc.
+ * Chirag Shah
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; see the file COPYING; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#include <zebra.h>
+
+#include "lib/log.h"
+#include "lib/northbound.h"
+#include "libfrr.h"
+#include "lib/command.h"
+#include "lib/routemap.h"
+#include "zebra/zebra_nb.h"
+#include "zebra/rib.h"
+#include "zebra_nb.h"
+#include "zebra/interface.h"
+#include "zebra/connected.h"
+
+/*
+ * XPath: /frr-zebra:zebra/mcast-rpf-lookup
+ */
+int zebra_mcast_rpf_lookup_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/ip-forwarding
+ */
+int zebra_ip_forwarding_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_ip_forwarding_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/ipv6-forwarding
+ */
+int zebra_ipv6_forwarding_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_ipv6_forwarding_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/workqueue-hold-timer
+ */
+int zebra_workqueue_hold_timer_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/zapi-packets
+ */
+int zebra_zapi_packets_modify(enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/import-kernel-table/table-id
+ */
+int zebra_import_kernel_table_table_id_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_import_kernel_table_table_id_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/import-kernel-table/distance
+ */
+int zebra_import_kernel_table_distance_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/import-kernel-table/route-map
+ */
+int zebra_import_kernel_table_route_map_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_import_kernel_table_route_map_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/allow-external-route-update
+ */
+int zebra_allow_external_route_update_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_allow_external_route_update_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/dplane-queue-limit
+ */
+int zebra_dplane_queue_limit_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/vrf-vni-mapping
+ */
+int zebra_vrf_vni_mapping_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_vrf_vni_mapping_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/vrf-vni-mapping/vni-id
+ */
+int zebra_vrf_vni_mapping_vni_id_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_vrf_vni_mapping_vni_id_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/vrf-vni-mapping/prefix-only
+ */
+int zebra_vrf_vni_mapping_prefix_only_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_vrf_vni_mapping_prefix_only_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-events
+ */
+int zebra_debugs_debug_events_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_events_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-zapi-send
+ */
+int zebra_debugs_debug_zapi_send_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_zapi_send_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-zapi-recv
+ */
+int zebra_debugs_debug_zapi_recv_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_zapi_recv_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-zapi-detail
+ */
+int zebra_debugs_debug_zapi_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_zapi_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-kernel
+ */
+int zebra_debugs_debug_kernel_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_kernel_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-kernel-msg-send
+ */
+int zebra_debugs_debug_kernel_msg_send_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_kernel_msg_send_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-kernel-msg-recv
+ */
+int zebra_debugs_debug_kernel_msg_recv_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_kernel_msg_recv_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-rib
+ */
+int zebra_debugs_debug_rib_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_rib_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-rib-detail
+ */
+int zebra_debugs_debug_rib_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_rib_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-fpm
+ */
+int zebra_debugs_debug_fpm_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_fpm_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-nht
+ */
+int zebra_debugs_debug_nht_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_nht_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-nht-detail
+ */
+int zebra_debugs_debug_nht_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_nht_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-mpls
+ */
+int zebra_debugs_debug_mpls_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_mpls_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-vxlan
+ */
+int zebra_debugs_debug_vxlan_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_vxlan_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-pw
+ */
+int zebra_debugs_debug_pw_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_pw_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-dplane
+ */
+int zebra_debugs_debug_dplane_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_dplane_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-dplane-detail
+ */
+int zebra_debugs_debug_dplane_detail_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_dplane_detail_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-zebra:zebra/debugs/debug-mlag
+ */
+int zebra_debugs_debug_mlag_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int zebra_debugs_debug_mlag_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip-addrs
+ */
+int lib_interface_zebra_ip_addrs_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct interface *ifp;
+ struct prefix prefix;
+ char buf[PREFIX_STRLEN] = {0};
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ // addr_family = yang_dnode_get_enum(dnode, "./address-family");
+ yang_dnode_get_prefix(&prefix, dnode, "./ip-prefix");
+ apply_mask(&prefix);
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ if (prefix.family == AF_INET
+ && ipv4_martian(&prefix.u.prefix4)) {
+ zlog_debug("invalid address %s",
+ prefix2str(&prefix, buf, sizeof(buf)));
+ return NB_ERR_VALIDATION;
+ } else if (prefix.family == AF_INET6
+ && ipv6_martian(&prefix.u.prefix6)) {
+ zlog_debug("invalid address %s",
+ prefix2str(&prefix, buf, sizeof(buf)));
+ return NB_ERR_VALIDATION;
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ 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);
+
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_ip_addrs_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct interface *ifp;
+ struct prefix prefix;
+ struct connected *ifc;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ yang_dnode_get_prefix(&prefix, dnode, "./ip-prefix");
+ apply_mask(&prefix);
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ 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\n",
+ ifp->name);
+ return NB_ERR_VALIDATION;
+ }
+ } else if (prefix.family == AF_INET6) {
+ /* Check current interface address. */
+ ifc = connected_check(ifp, &prefix);
+ if (!ifc) {
+ zlog_debug("interface can't find address %s",
+ ifp->name);
+ return NB_ERR_VALIDATION;
+ }
+ } else
+ return NB_ERR_VALIDATION;
+
+ /* This is not configured address. */
+ if (!CHECK_FLAG(ifc->conf, ZEBRA_IFC_CONFIGURED)) {
+ zlog_debug("interface %s not configured", ifp->name);
+ return NB_ERR_VALIDATION;
+ }
+
+ /* 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)) {
+ listnode_delete(ifp->connected, ifc);
+ connected_free(&ifc);
+ return NB_ERR_VALIDATION;
+ }
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ break;
+ case NB_EV_APPLY:
+ if_ip_address_uinstall(ifp, &prefix);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/label
+ */
+int lib_interface_zebra_ip_addrs_label_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ 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(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip-addrs/ip4-peer
+ */
+int lib_interface_zebra_ip_addrs_ip4_peer_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ 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_ip4_peer_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/multicast
+ */
+int lib_interface_zebra_multicast_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ struct interface *ifp;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+
+ if_multicast_set(ifp);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_multicast_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ struct interface *ifp;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+
+ if_multicast_unset(ifp);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-detect
+ */
+int lib_interface_zebra_link_detect_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ struct interface *ifp;
+ bool link_detect;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ link_detect = yang_dnode_get_bool(dnode, "./link-detect");
+
+ if_linkdetect(ifp, link_detect);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_link_detect_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ struct interface *ifp;
+ bool link_detect;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ link_detect = yang_dnode_get_bool(dnode, "./link-detect");
+
+ if_linkdetect(ifp, link_detect);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/shutdown
+ */
+int lib_interface_zebra_shutdown_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct interface *ifp;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+
+ if_shutdown(ifp);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_shutdown_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct interface *ifp;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+
+ if_no_shutdown(ifp);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/bandwidth
+ */
+int lib_interface_zebra_bandwidth_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ struct interface *ifp;
+ uint32_t bandwidth;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ bandwidth = yang_dnode_get_uint32(dnode, "./bandwidth");
+
+ ifp->bandwidth = bandwidth;
+
+ /* force protocols to recalculate routes due to cost change */
+ if (if_is_operative(ifp))
+ zebra_interface_up_update(ifp);
+
+ return NB_OK;
+}
+
+int lib_interface_zebra_bandwidth_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ struct interface *ifp;
+
+ ifp = nb_running_get_entry(dnode, NULL, true);
+
+ ifp->bandwidth = 0;
+
+ /* force protocols to recalculate routes due to cost change */
+ if (if_is_operative(ifp))
+ zebra_interface_up_update(ifp);
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib
+ */
+int lib_vrf_ribs_rib_create(enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+int lib_vrf_ribs_rib_destroy(enum nb_event event, const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* TODO: implement me. */
+ break;
+ }
+
+ return NB_OK;
+}
+
+
+/*
+ * XPath:
+ * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv4-prefix-length
+ */
+int lib_route_map_entry_match_condition_ipv4_prefix_length_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct routemap_hook_context *rhc;
+ const char *length;
+ int condition, rv;
+
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ /* Add configuration. */
+ rhc = nb_running_get_entry(dnode, NULL, true);
+ length = yang_dnode_get_string(dnode, NULL);
+ condition = yang_dnode_get_enum(dnode, "../frr-route-map:condition");
+
+ /* Set destroy information. */
+ switch (condition) {
+ case 100: /* ipv4-prefix-length */
+ rhc->rhc_rule = "ip address prefix-len";
+ break;
+
+ case 102: /* ipv4-next-hop-prefix-length */
+ rhc->rhc_rule = "ip next-hop prefix-len";
+ break;
+ }
+ rhc->rhc_mhook = generic_match_delete;
+ rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
+
+ rv = generic_match_add(NULL, rhc->rhc_rmi, rhc->rhc_rule, length,
+ RMAP_EVENT_MATCH_ADDED);
+ if (rv != CMD_SUCCESS) {
+ rhc->rhc_mhook = NULL;
+ return NB_ERR_INCONSISTENCY;
+ }
+
+ return NB_OK;
+}
+
+int lib_route_map_entry_match_condition_ipv4_prefix_length_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ return lib_route_map_entry_match_destroy(event, dnode);
+}
+
+/*
+ * XPath:
+ * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv6-prefix-length
+ */
+int lib_route_map_entry_match_condition_ipv6_prefix_length_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct routemap_hook_context *rhc;
+ const char *length;
+ int rv;
+
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ /* Add configuration. */
+ rhc = nb_running_get_entry(dnode, NULL, true);
+ length = yang_dnode_get_string(dnode, NULL);
+
+ /* Set destroy information. */
+ rhc->rhc_mhook = generic_match_delete;
+ rhc->rhc_rule = "ipv6 address prefix-len";
+ rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
+
+ rv = generic_match_add(NULL, rhc->rhc_rmi, "ipv6 address prefix-len",
+ length, RMAP_EVENT_MATCH_ADDED);
+ if (rv != CMD_SUCCESS) {
+ rhc->rhc_mhook = NULL;
+ return NB_ERR_INCONSISTENCY;
+ }
+
+ return NB_OK;
+}
+
+int lib_route_map_entry_match_condition_ipv6_prefix_length_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ return lib_route_map_entry_match_destroy(event, dnode);
+}
+
+/*
+ * XPath:
+ * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-protocol
+ */
+int lib_route_map_entry_match_condition_source_protocol_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct routemap_hook_context *rhc;
+ const char *type;
+ int rv;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ type = yang_dnode_get_string(dnode, NULL);
+ if (proto_name2num(type) == -1) {
+ zlog_warn("%s: invalid protocol: %s", __func__, type);
+ return NB_ERR_VALIDATION;
+ }
+ return NB_OK;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ return NB_OK;
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ /* Add configuration. */
+ rhc = nb_running_get_entry(dnode, NULL, true);
+ type = yang_dnode_get_string(dnode, NULL);
+
+ /* Set destroy information. */
+ rhc->rhc_mhook = generic_match_delete;
+ rhc->rhc_rule = "source-protocol";
+ rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
+
+ rv = generic_match_add(NULL, rhc->rhc_rmi, "source-protocol", type,
+ RMAP_EVENT_MATCH_ADDED);
+ if (rv != CMD_SUCCESS) {
+ rhc->rhc_mhook = NULL;
+ return NB_ERR_INCONSISTENCY;
+ }
+
+ return NB_OK;
+}
+
+int lib_route_map_entry_match_condition_source_protocol_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ return lib_route_map_entry_match_destroy(event, dnode);
+}
+
+/*
+ * XPath:
+ * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-instance
+ */
+int lib_route_map_entry_match_condition_source_instance_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct routemap_hook_context *rhc;
+ const char *type;
+ int rv;
+
+ if (event != NB_EV_APPLY)
+ return NB_OK;
+
+ /* Add configuration. */
+ rhc = nb_running_get_entry(dnode, NULL, true);
+ type = yang_dnode_get_string(dnode, NULL);
+
+ /* Set destroy information. */
+ rhc->rhc_mhook = generic_match_delete;
+ rhc->rhc_rule = "source-instance";
+ rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
+
+ rv = generic_match_add(NULL, rhc->rhc_rmi, "source-instance", type,
+ RMAP_EVENT_MATCH_ADDED);
+ if (rv != CMD_SUCCESS) {
+ rhc->rhc_mhook = NULL;
+ return NB_ERR_INCONSISTENCY;
+ }
+
+ return NB_OK;
+}
+
+int lib_route_map_entry_match_condition_source_instance_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ return lib_route_map_entry_match_destroy(event, dnode);
+}
+
+/*
+ * XPath: /frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v4
+ */
+int lib_route_map_entry_set_action_source_v4_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct routemap_hook_context *rhc;
+ struct interface *pif = NULL;
+ const char *source;
+ struct vrf *vrf;
+ struct prefix p;
+ int rv;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ memset(&p, 0, sizeof(p));
+ yang_dnode_get_ipv4p(&p, dnode, NULL);
+ if (zebra_check_addr(&p) == 0) {
+ zlog_warn("%s: invalid IPv4 address: %s", __func__,
+ yang_dnode_get_string(dnode, NULL));
+ return NB_ERR_VALIDATION;
+ }
+
+ RB_FOREACH (vrf, vrf_id_head, &vrfs_by_id) {
+ pif = if_lookup_exact_address(&p.u.prefix4, AF_INET,
+ vrf->vrf_id);
+ if (pif != NULL)
+ break;
+ }
+ if (pif == NULL) {
+ zlog_warn("%s: is not a local adddress: %s", __func__,
+ yang_dnode_get_string(dnode, NULL));
+ return NB_ERR_VALIDATION;
+ }
+ return NB_OK;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ return NB_OK;
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ /* Add configuration. */
+ rhc = nb_running_get_entry(dnode, NULL, true);
+ source = yang_dnode_get_string(dnode, NULL);
+
+ /* Set destroy information. */
+ rhc->rhc_shook = generic_set_delete;
+ rhc->rhc_rule = "src";
+
+ rv = generic_set_add(NULL, rhc->rhc_rmi, "src", source);
+ if (rv != CMD_SUCCESS) {
+ rhc->rhc_shook = NULL;
+ return NB_ERR_INCONSISTENCY;
+ }
+
+ return NB_OK;
+}
+
+int lib_route_map_entry_set_action_source_v4_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ return lib_route_map_entry_set_destroy(event, dnode);
+}
+
+/*
+ * XPath: /frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v6
+ */
+int lib_route_map_entry_set_action_source_v6_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct routemap_hook_context *rhc;
+ struct interface *pif = NULL;
+ const char *source;
+ struct vrf *vrf;
+ struct prefix p;
+ int rv;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ memset(&p, 0, sizeof(p));
+ yang_dnode_get_ipv6p(&p, dnode, NULL);
+ if (zebra_check_addr(&p) == 0) {
+ zlog_warn("%s: invalid IPv6 address: %s", __func__,
+ yang_dnode_get_string(dnode, NULL));
+ return NB_ERR_VALIDATION;
+ }
+
+ RB_FOREACH (vrf, vrf_id_head, &vrfs_by_id) {
+ pif = if_lookup_exact_address(&p.u.prefix6, AF_INET6,
+ vrf->vrf_id);
+ if (pif != NULL)
+ break;
+ }
+ if (pif == NULL) {
+ zlog_warn("%s: is not a local adddress: %s", __func__,
+ yang_dnode_get_string(dnode, NULL));
+ return NB_ERR_VALIDATION;
+ }
+ return NB_OK;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ return NB_OK;
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ /* Add configuration. */
+ rhc = nb_running_get_entry(dnode, NULL, true);
+ source = yang_dnode_get_string(dnode, NULL);
+
+ /* Set destroy information. */
+ rhc->rhc_shook = generic_set_delete;
+ rhc->rhc_rule = "src";
+
+ rv = generic_set_add(NULL, rhc->rhc_rmi, "src", source);
+ if (rv != CMD_SUCCESS) {
+ rhc->rhc_shook = NULL;
+ return NB_ERR_INCONSISTENCY;
+ }
+
+ return NB_OK;
+}
+
+int lib_route_map_entry_set_action_source_v6_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ return lib_route_map_entry_set_destroy(event, dnode);
+}
diff --git a/zebra/zebra_nb_rpcs.c b/zebra/zebra_nb_rpcs.c
new file mode 100644
index 000000000..cf8efe40a
--- /dev/null
+++ b/zebra/zebra_nb_rpcs.c
@@ -0,0 +1,212 @@
+/*
+ * Copyright (C) 2020 Cumulus Networks, Inc.
+ * Chirag Shah
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; see the file COPYING; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#include <zebra.h>
+#include "northbound.h"
+#include "libfrr.h"
+
+#include "zebra/zebra_nb.h"
+#include "zebra/zebra_router.h"
+#include "zebra/zebra_vrf.h"
+#include "zebra/zebra_vxlan.h"
+
+/*
+ * XPath: /frr-zebra:clear-evpn-dup-addr
+ */
+int clear_evpn_dup_addr_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ struct zebra_vrf *zvrf;
+ int ret = NB_OK;
+ struct yang_data *yang_dup_choice = NULL, *yang_dup_vni = NULL,
+ *yang_dup_ip = NULL, *yang_dup_mac = NULL;
+
+ yang_dup_choice = yang_data_list_find(input, "%s/%s", xpath,
+ "input/clear-dup-choice");
+
+ zvrf = zebra_vrf_get_evpn();
+
+ if (yang_dup_choice
+ && strcmp(yang_dup_choice->value, "all-case") == 0) {
+ zebra_vxlan_clear_dup_detect_vni_all(zvrf);
+ } else {
+ vni_t vni;
+ struct ipaddr host_ip = {.ipa_type = IPADDR_NONE};
+ struct ethaddr mac;
+
+ yang_dup_vni = yang_data_list_find(
+ input, "%s/%s", xpath,
+ "input/clear-dup-choice/single-case/vni-id");
+ if (yang_dup_vni) {
+ vni = yang_str2uint32(yang_dup_vni->value);
+
+ yang_dup_mac = yang_data_list_find(
+ input, "%s/%s", xpath,
+ "input/clear-dup-choice/single-case/vni-id/mac-addr");
+ yang_dup_ip = yang_data_list_find(
+ input, "%s/%s", xpath,
+ "input/clear-dup-choice/single-case/vni-id/vni-ipaddr");
+
+ if (yang_dup_mac) {
+ yang_str2mac(yang_dup_mac->value, &mac);
+ ret = zebra_vxlan_clear_dup_detect_vni_mac(
+ zvrf, vni, &mac);
+ } else if (yang_dup_ip) {
+ yang_str2ip(yang_dup_ip->value, &host_ip);
+ ret = zebra_vxlan_clear_dup_detect_vni_ip(
+ zvrf, vni, &host_ip);
+ } else
+ ret = zebra_vxlan_clear_dup_detect_vni(zvrf,
+ vni);
+ }
+ }
+ ret = (ret != CMD_SUCCESS) ? NB_ERR : NB_OK;
+
+ return ret;
+}
+
+/*
+ * XPath: /frr-zebra:get-route-information
+ */
+int get_route_information_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-v6-mroute-info
+ */
+int get_v6_mroute_info_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-vrf-info
+ */
+int get_vrf_info_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-vrf-vni-info
+ */
+int get_vrf_vni_info_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-evpn-info
+ */
+int get_evpn_info_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-vni-info
+ */
+int get_vni_info_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-evpn-vni-rmac
+ */
+int get_evpn_vni_rmac_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-evpn-vni-nexthops
+ */
+int get_evpn_vni_nexthops_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-evpn-macs
+ */
+int get_evpn_macs_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-evpn-arp-cache
+ */
+int get_evpn_arp_cache_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-pbr-ipset
+ */
+int get_pbr_ipset_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-pbr-iptable
+ */
+int get_pbr_iptable_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
+
+/*
+ * XPath: /frr-zebra:get-debugs
+ */
+int get_debugs_rpc(const char *xpath, const struct list *input,
+ struct list *output)
+{
+ /* TODO: implement me. */
+ return NB_ERR_NOT_FOUND;
+}
diff --git a/zebra/zebra_nb_state.c b/zebra/zebra_nb_state.c
new file mode 100644
index 000000000..9036bdf0f
--- /dev/null
+++ b/zebra/zebra_nb_state.c
@@ -0,0 +1,637 @@
+/*
+ * Copyright (C) 2020 Cumulus Networks, Inc.
+ * Chirag Shah
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
+ * any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; see the file COPYING; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+#include <zebra.h>
+#include "northbound.h"
+#include "libfrr.h"
+#include "zebra_nb.h"
+#include "zebra/interface.h"
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/up-count
+ */
+struct yang_data *
+lib_interface_zebra_state_up_count_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+ struct zebra_if *zebra_if;
+
+ zebra_if = ifp->info;
+
+ return yang_data_new_uint16(xpath, zebra_if->up_count);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/down-count
+ */
+struct yang_data *
+lib_interface_zebra_state_down_count_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+ struct zebra_if *zebra_if;
+
+ zebra_if = ifp->info;
+
+ return yang_data_new_uint16(xpath, zebra_if->down_count);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/zif-type
+ */
+struct yang_data *
+lib_interface_zebra_state_zif_type_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/ptm-status
+ */
+struct yang_data *
+lib_interface_zebra_state_ptm_status_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/vlan-id
+ */
+struct yang_data *
+lib_interface_zebra_state_vlan_id_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+ struct zebra_if *zebra_if;
+ struct zebra_l2info_vlan *vlan_info;
+
+ if (!IS_ZEBRA_IF_VLAN(ifp))
+ return NULL;
+
+ zebra_if = ifp->info;
+ vlan_info = &zebra_if->l2info.vl;
+
+ return yang_data_new_uint16(xpath, vlan_info->vid);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/vni-id
+ */
+struct yang_data *
+lib_interface_zebra_state_vni_id_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+ struct zebra_if *zebra_if;
+ struct zebra_l2info_vxlan *vxlan_info;
+
+ if (!IS_ZEBRA_IF_VXLAN(ifp))
+ return NULL;
+
+ zebra_if = ifp->info;
+ vxlan_info = &zebra_if->l2info.vxl;
+
+ return yang_data_new_uint32(xpath, vxlan_info->vni);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/remote-vtep
+ */
+struct yang_data *
+lib_interface_zebra_state_remote_vtep_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+ struct zebra_if *zebra_if;
+ struct zebra_l2info_vxlan *vxlan_info;
+
+ if (!IS_ZEBRA_IF_VXLAN(ifp))
+ return NULL;
+
+ zebra_if = ifp->info;
+ vxlan_info = &zebra_if->l2info.vxl;
+
+ return yang_data_new_ipv4(xpath, &vxlan_info->vtep_ip);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-zebra:zebra/state/mcast-group
+ */
+struct yang_data *
+lib_interface_zebra_state_mcast_group_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ const struct interface *ifp = list_entry;
+ struct zebra_if *zebra_if;
+ struct zebra_l2info_vxlan *vxlan_info;
+
+ if (!IS_ZEBRA_IF_VXLAN(ifp))
+ return NULL;
+
+ zebra_if = ifp->info;
+ vxlan_info = &zebra_if->l2info.vxl;
+
+ return yang_data_new_ipv4(xpath, &vxlan_info->mcast_grp);
+}
+
+const void *lib_vrf_ribs_rib_get_next(const void *parent_list_entry,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+int lib_vrf_ribs_rib_get_keys(const void *list_entry,
+ struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NB_OK;
+}
+
+const void *lib_vrf_ribs_rib_lookup_entry(const void *parent_list_entry,
+ const struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route
+ */
+const void *lib_vrf_ribs_rib_route_get_next(const void *parent_list_entry,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+int lib_vrf_ribs_rib_route_get_keys(const void *list_entry,
+ struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NB_OK;
+}
+
+const void *
+lib_vrf_ribs_rib_route_lookup_entry(const void *parent_list_entry,
+ const struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/prefix
+ */
+struct yang_data *lib_vrf_ribs_rib_route_prefix_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry
+ */
+const void *
+lib_vrf_ribs_rib_route_route_entry_get_next(const void *parent_list_entry,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+int lib_vrf_ribs_rib_route_route_entry_get_keys(const void *list_entry,
+ struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NB_OK;
+}
+
+const void *lib_vrf_ribs_rib_route_route_entry_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/protocol
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_protocol_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/instance
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_instance_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/distance
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_distance_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/metric
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_metric_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/tag
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_tag_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/selected
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_selected_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/installed
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_installed_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/failed
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_failed_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/queued
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_queued_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/internal-flags
+ */
+struct yang_data *lib_vrf_ribs_rib_route_route_entry_internal_flags_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/internal-status
+ */
+struct yang_data *lib_vrf_ribs_rib_route_route_entry_internal_status_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/uptime
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_uptime_get_elem(const char *xpath,
+ const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath: /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group
+ */
+const void *lib_vrf_ribs_rib_route_route_entry_nexthop_group_get_next(
+ const void *parent_list_entry, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+int lib_vrf_ribs_rib_route_route_entry_nexthop_group_get_keys(
+ const void *list_entry, struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NB_OK;
+}
+
+const void *lib_vrf_ribs_rib_route_route_entry_nexthop_group_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/name
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_name_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop
+ */
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_get_next(
+ const void *parent_list_entry, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+int lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_get_keys(
+ const void *list_entry, struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NB_OK;
+}
+
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/nh-type
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_nh_type_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/vrf
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_vrf_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/gateway
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_gateway_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/interface
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_interface_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/bh-type
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_bh_type_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/onlink
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_onlink_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry
+ */
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_get_next(
+ const void *parent_list_entry, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+int lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_get_keys(
+ const void *list_entry, struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NB_OK;
+}
+
+const void *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_lookup_entry(
+ const void *parent_list_entry, const struct yang_list_keys *keys)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/id
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_id_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/label
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_label_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/ttl
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_ttl_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/mpls-label-stack/entry/traffic-class
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_mpls_label_stack_entry_traffic_class_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/duplicate
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_duplicate_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/recursive
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_recursive_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/active
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_active_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/fib
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_fib_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
+
+/*
+ * XPath:
+ * /frr-vrf:lib/vrf/frr-zebra:ribs/rib/route/route-entry/nexthop-group/frr-nexthops/nexthop/weight
+ */
+struct yang_data *
+lib_vrf_ribs_rib_route_route_entry_nexthop_group_frr_nexthops_nexthop_weight_get_elem(
+ const char *xpath, const void *list_entry)
+{
+ /* TODO: implement me. */
+ return NULL;
+}
diff --git a/zebra/zebra_northbound.c b/zebra/zebra_northbound.c
deleted file mode 100644
index 9f6514e12..000000000
--- a/zebra/zebra_northbound.c
+++ /dev/null
@@ -1,2212 +0,0 @@
-/*
- * Zebra northbound implementation.
- *
- * Copyright (C) 2019 Network Device Education Foundation, Inc. ("NetDEF")
- * Rafael Zalamena
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
- * 02110-1301 USA.
- */
-
-#include <zebra.h>
-
-#include "lib/command.h"
-#include "lib/log.h"
-#include "lib/northbound.h"
-#include "lib/routemap.h"
-
-#include "zebra/rib.h"
-
-/*
- * XPath: /frr-zebra:zebra/mcast-rpf-lookup
- */
-static int zebra_mcast_rpf_lookup_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/ip-forwarding
- */
-static int zebra_ip_forwarding_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_ip_forwarding_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/ipv6-forwarding
- */
-static int zebra_ipv6_forwarding_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_ipv6_forwarding_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/workqueue-hold-timer
- */
-static int zebra_workqueue_hold_timer_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/zapi-packets
- */
-static int zebra_zapi_packets_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/import-kernel-table/table-id
- */
-static int
-zebra_import_kernel_table_table_id_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-zebra_import_kernel_table_table_id_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/import-kernel-table/distance
- */
-static int
-zebra_import_kernel_table_distance_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/import-kernel-table/route-map
- */
-static int
-zebra_import_kernel_table_route_map_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-zebra_import_kernel_table_route_map_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/allow-external-route-update
- */
-static int
-zebra_allow_external_route_update_create(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-zebra_allow_external_route_update_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/dplane-queue-limit
- */
-static int zebra_dplane_queue_limit_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/vrf-vni-mapping
- */
-static int zebra_vrf_vni_mapping_create(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_vrf_vni_mapping_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/vrf-vni-mapping/vni-id
- */
-static int zebra_vrf_vni_mapping_vni_id_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_vrf_vni_mapping_vni_id_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/vrf-vni-mapping/prefix-only
- */
-static int
-zebra_vrf_vni_mapping_prefix_only_create(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-zebra_vrf_vni_mapping_prefix_only_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-events
- */
-static int zebra_debugs_debug_events_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_events_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-zapi-send
- */
-static int zebra_debugs_debug_zapi_send_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_zapi_send_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-zapi-recv
- */
-static int zebra_debugs_debug_zapi_recv_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_zapi_recv_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-zapi-detail
- */
-static int zebra_debugs_debug_zapi_detail_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_zapi_detail_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-kernel
- */
-static int zebra_debugs_debug_kernel_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_kernel_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-kernel-msg-send
- */
-static int
-zebra_debugs_debug_kernel_msg_send_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-zebra_debugs_debug_kernel_msg_send_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-kernel-msg-recv
- */
-static int
-zebra_debugs_debug_kernel_msg_recv_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-zebra_debugs_debug_kernel_msg_recv_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-rib
- */
-static int zebra_debugs_debug_rib_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_rib_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-rib-detail
- */
-static int zebra_debugs_debug_rib_detail_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_rib_detail_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-fpm
- */
-static int zebra_debugs_debug_fpm_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_fpm_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-nht
- */
-static int zebra_debugs_debug_nht_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_nht_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-nht-detail
- */
-static int zebra_debugs_debug_nht_detail_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_nht_detail_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-mpls
- */
-static int zebra_debugs_debug_mpls_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_mpls_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-vxlan
- */
-static int zebra_debugs_debug_vxlan_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_vxlan_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-pw
- */
-static int zebra_debugs_debug_pw_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_pw_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-dplane
- */
-static int zebra_debugs_debug_dplane_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_dplane_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-dplane-detail
- */
-static int zebra_debugs_debug_dplane_detail_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-zebra_debugs_debug_dplane_detail_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:zebra/debugs/debug-mlag
- */
-static int zebra_debugs_debug_mlag_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int zebra_debugs_debug_mlag_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-route-information
- */
-static int get_route_information_rpc(const char *xpath,
- const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-v6-mroute-info
- */
-static int get_v6_mroute_info_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-vrf-info
- */
-static int get_vrf_info_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-vrf-vni-info
- */
-static int get_vrf_vni_info_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-evpn-info
- */
-static int get_evpn_info_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-vni-info
- */
-static int get_vni_info_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-evpn-vni-rmac
- */
-static int get_evpn_vni_rmac_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-evpn-vni-nexthops
- */
-static int get_evpn_vni_nexthops_rpc(const char *xpath,
- const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:clear-evpn-dup-addr
- */
-static int clear_evpn_dup_addr_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-evpn-macs
- */
-static int get_evpn_macs_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-evpn-arp-cache
- */
-static int get_evpn_arp_cache_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-pbr-ipset
- */
-static int get_pbr_ipset_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-pbr-iptable
- */
-static int get_pbr_iptable_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-zebra:get-debugs
- */
-static int get_debugs_rpc(const char *xpath, const struct list *input,
- struct list *output)
-{
- /* TODO: implement me. */
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip4-addr-list
- */
-static int
-lib_interface_zebra_ip4_addr_list_create(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-lib_interface_zebra_ip4_addr_list_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip4-addr-list/ip4-peer
- */
-static int
-lib_interface_zebra_ip4_addr_list_ip4_peer_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-lib_interface_zebra_ip4_addr_list_ip4_peer_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip4-addr-list/label
- */
-static int
-lib_interface_zebra_ip4_addr_list_label_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-lib_interface_zebra_ip4_addr_list_label_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip6-addr-list
- */
-static int
-lib_interface_zebra_ip6_addr_list_create(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-lib_interface_zebra_ip6_addr_list_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/ip6-addr-list/label
- */
-static int
-lib_interface_zebra_ip6_addr_list_label_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int
-lib_interface_zebra_ip6_addr_list_label_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/multicast
- */
-static int lib_interface_zebra_multicast_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int lib_interface_zebra_multicast_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/link-detect
- */
-static int lib_interface_zebra_link_detect_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int lib_interface_zebra_link_detect_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/shutdown
- */
-static int lib_interface_zebra_shutdown_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int lib_interface_zebra_shutdown_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath: /frr-interface:lib/interface/frr-zebra:zebra/bandwidth
- */
-static int lib_interface_zebra_bandwidth_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-static int lib_interface_zebra_bandwidth_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- switch (event) {
- case NB_EV_VALIDATE:
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- case NB_EV_APPLY:
- /* TODO: implement me. */
- break;
- }
-
- return NB_ERR_NOT_FOUND;
-}
-
-/*
- * XPath:
- * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv4-prefix-length
- */
-static int lib_route_map_entry_match_condition_ipv4_prefix_length_modify(
- enum nb_event event, const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- struct routemap_hook_context *rhc;
- const char *length;
- int condition, rv;
-
- if (event != NB_EV_APPLY)
- return NB_OK;
-
- /* Add configuration. */
- rhc = nb_running_get_entry(dnode, NULL, true);
- length = yang_dnode_get_string(dnode, NULL);
- condition = yang_dnode_get_enum(dnode, "../frr-route-map:condition");
-
- /* Set destroy information. */
- switch (condition) {
- case 100: /* ipv4-prefix-length */
- rhc->rhc_rule = "ip address prefix-len";
- break;
-
- case 102: /* ipv4-next-hop-prefix-length */
- rhc->rhc_rule = "ip next-hop prefix-len";
- break;
- }
- rhc->rhc_mhook = generic_match_delete;
- rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
-
- rv = generic_match_add(NULL, rhc->rhc_rmi, rhc->rhc_rule, length,
- RMAP_EVENT_MATCH_ADDED);
- if (rv != CMD_SUCCESS) {
- rhc->rhc_mhook = NULL;
- return NB_ERR_INCONSISTENCY;
- }
-
- return NB_OK;
-}
-
-static int lib_route_map_entry_match_condition_ipv4_prefix_length_destroy(
- enum nb_event event, const struct lyd_node *dnode)
-{
- return lib_route_map_entry_match_destroy(event, dnode);
-}
-
-/*
- * XPath:
- * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv6-prefix-length
- */
-static int lib_route_map_entry_match_condition_ipv6_prefix_length_modify(
- enum nb_event event, const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- struct routemap_hook_context *rhc;
- const char *length;
- int rv;
-
- if (event != NB_EV_APPLY)
- return NB_OK;
-
- /* Add configuration. */
- rhc = nb_running_get_entry(dnode, NULL, true);
- length = yang_dnode_get_string(dnode, NULL);
-
- /* Set destroy information. */
- rhc->rhc_mhook = generic_match_delete;
- rhc->rhc_rule = "ipv6 address prefix-len";
- rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
-
- rv = generic_match_add(NULL, rhc->rhc_rmi, "ipv6 address prefix-len",
- length, RMAP_EVENT_MATCH_ADDED);
- if (rv != CMD_SUCCESS) {
- rhc->rhc_mhook = NULL;
- return NB_ERR_INCONSISTENCY;
- }
-
- return NB_OK;
-}
-
-static int lib_route_map_entry_match_condition_ipv6_prefix_length_destroy(
- enum nb_event event, const struct lyd_node *dnode)
-{
- return lib_route_map_entry_match_destroy(event, dnode);
-}
-
-/*
- * XPath:
- * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-protocol
- */
-static int lib_route_map_entry_match_condition_source_protocol_modify(
- enum nb_event event, const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- struct routemap_hook_context *rhc;
- const char *type;
- int rv;
-
- switch (event) {
- case NB_EV_VALIDATE:
- type = yang_dnode_get_string(dnode, NULL);
- if (proto_name2num(type) == -1) {
- zlog_warn("%s: invalid protocol: %s", __func__, type);
- return NB_ERR_VALIDATION;
- }
- return NB_OK;
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- return NB_OK;
- case NB_EV_APPLY:
- /* NOTHING */
- break;
- }
-
- /* Add configuration. */
- rhc = nb_running_get_entry(dnode, NULL, true);
- type = yang_dnode_get_string(dnode, NULL);
-
- /* Set destroy information. */
- rhc->rhc_mhook = generic_match_delete;
- rhc->rhc_rule = "source-protocol";
- rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
-
- rv = generic_match_add(NULL, rhc->rhc_rmi, "source-protocol", type,
- RMAP_EVENT_MATCH_ADDED);
- if (rv != CMD_SUCCESS) {
- rhc->rhc_mhook = NULL;
- return NB_ERR_INCONSISTENCY;
- }
-
- return NB_OK;
-}
-
-static int lib_route_map_entry_match_condition_source_protocol_destroy(
- enum nb_event event, const struct lyd_node *dnode)
-{
- return lib_route_map_entry_match_destroy(event, dnode);
-}
-
-/*
- * XPath:
- * /frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-instance
- */
-static int lib_route_map_entry_match_condition_source_instance_modify(
- enum nb_event event, const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- struct routemap_hook_context *rhc;
- const char *type;
- int rv;
-
- if (event != NB_EV_APPLY)
- return NB_OK;
-
- /* Add configuration. */
- rhc = nb_running_get_entry(dnode, NULL, true);
- type = yang_dnode_get_string(dnode, NULL);
-
- /* Set destroy information. */
- rhc->rhc_mhook = generic_match_delete;
- rhc->rhc_rule = "source-instance";
- rhc->rhc_event = RMAP_EVENT_MATCH_DELETED;
-
- rv = generic_match_add(NULL, rhc->rhc_rmi, "source-instance", type,
- RMAP_EVENT_MATCH_ADDED);
- if (rv != CMD_SUCCESS) {
- rhc->rhc_mhook = NULL;
- return NB_ERR_INCONSISTENCY;
- }
-
- return NB_OK;
-}
-
-static int lib_route_map_entry_match_condition_source_instance_destroy(
- enum nb_event event, const struct lyd_node *dnode)
-{
- return lib_route_map_entry_match_destroy(event, dnode);
-}
-
-/*
- * XPath: /frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v4
- */
-static int
-lib_route_map_entry_set_action_source_v4_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- struct routemap_hook_context *rhc;
- struct interface *pif = NULL;
- const char *source;
- struct vrf *vrf;
- struct prefix p;
- int rv;
-
- switch (event) {
- case NB_EV_VALIDATE:
- memset(&p, 0, sizeof(p));
- yang_dnode_get_ipv4p(&p, dnode, NULL);
- if (zebra_check_addr(&p) == 0) {
- zlog_warn("%s: invalid IPv4 address: %s", __func__,
- yang_dnode_get_string(dnode, NULL));
- return NB_ERR_VALIDATION;
- }
-
- RB_FOREACH(vrf, vrf_id_head, &vrfs_by_id) {
- pif = if_lookup_exact_address(&p.u.prefix4, AF_INET,
- vrf->vrf_id);
- if (pif != NULL)
- break;
- }
- if (pif == NULL) {
- zlog_warn("%s: is not a local adddress: %s", __func__,
- yang_dnode_get_string(dnode, NULL));
- return NB_ERR_VALIDATION;
- }
- return NB_OK;
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- return NB_OK;
- case NB_EV_APPLY:
- /* NOTHING */
- break;
- }
-
- /* Add configuration. */
- rhc = nb_running_get_entry(dnode, NULL, true);
- source = yang_dnode_get_string(dnode, NULL);
-
- /* Set destroy information. */
- rhc->rhc_shook = generic_set_delete;
- rhc->rhc_rule = "src";
-
- rv = generic_set_add(NULL, rhc->rhc_rmi, "src", source);
- if (rv != CMD_SUCCESS) {
- rhc->rhc_shook = NULL;
- return NB_ERR_INCONSISTENCY;
- }
-
- return NB_OK;
-}
-
-static int
-lib_route_map_entry_set_action_source_v4_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- return lib_route_map_entry_set_destroy(event, dnode);
-}
-
-/*
- * XPath: /frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v6
- */
-static int
-lib_route_map_entry_set_action_source_v6_modify(enum nb_event event,
- const struct lyd_node *dnode,
- union nb_resource *resource)
-{
- struct routemap_hook_context *rhc;
- struct interface *pif = NULL;
- const char *source;
- struct vrf *vrf;
- struct prefix p;
- int rv;
-
- switch (event) {
- case NB_EV_VALIDATE:
- memset(&p, 0, sizeof(p));
- yang_dnode_get_ipv6p(&p, dnode, NULL);
- if (zebra_check_addr(&p) == 0) {
- zlog_warn("%s: invalid IPv6 address: %s", __func__,
- yang_dnode_get_string(dnode, NULL));
- return NB_ERR_VALIDATION;
- }
-
- RB_FOREACH(vrf, vrf_id_head, &vrfs_by_id) {
- pif = if_lookup_exact_address(&p.u.prefix6, AF_INET6,
- vrf->vrf_id);
- if (pif != NULL)
- break;
- }
- if (pif == NULL) {
- zlog_warn("%s: is not a local adddress: %s", __func__,
- yang_dnode_get_string(dnode, NULL));
- return NB_ERR_VALIDATION;
- }
- return NB_OK;
- case NB_EV_PREPARE:
- case NB_EV_ABORT:
- return NB_OK;
- case NB_EV_APPLY:
- /* NOTHING */
- break;
- }
-
- /* Add configuration. */
- rhc = nb_running_get_entry(dnode, NULL, true);
- source = yang_dnode_get_string(dnode, NULL);
-
- /* Set destroy information. */
- rhc->rhc_shook = generic_set_delete;
- rhc->rhc_rule = "src";
-
- rv = generic_set_add(NULL, rhc->rhc_rmi, "src", source);
- if (rv != CMD_SUCCESS) {
- rhc->rhc_shook = NULL;
- return NB_ERR_INCONSISTENCY;
- }
-
- return NB_OK;
-}
-
-static int
-lib_route_map_entry_set_action_source_v6_destroy(enum nb_event event,
- const struct lyd_node *dnode)
-{
- return lib_route_map_entry_set_destroy(event, dnode);
-}
-
-/* clang-format off */
-const struct frr_yang_module_info frr_zebra_info = {
- .name = "frr-zebra",
- .nodes = {
- {
- .xpath = "/frr-zebra:zebra/mcast-rpf-lookup",
- .cbs = {
- .modify = zebra_mcast_rpf_lookup_modify,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/ip-forwarding",
- .cbs = {
- .modify = zebra_ip_forwarding_modify,
- .destroy = zebra_ip_forwarding_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/ipv6-forwarding",
- .cbs = {
- .modify = zebra_ipv6_forwarding_modify,
- .destroy = zebra_ipv6_forwarding_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/workqueue-hold-timer",
- .cbs = {
- .modify = zebra_workqueue_hold_timer_modify,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/zapi-packets",
- .cbs = {
- .modify = zebra_zapi_packets_modify,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/import-kernel-table/table-id",
- .cbs = {
- .modify = zebra_import_kernel_table_table_id_modify,
- .destroy = zebra_import_kernel_table_table_id_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/import-kernel-table/distance",
- .cbs = {
- .modify = zebra_import_kernel_table_distance_modify,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/import-kernel-table/route-map",
- .cbs = {
- .modify = zebra_import_kernel_table_route_map_modify,
- .destroy = zebra_import_kernel_table_route_map_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/allow-external-route-update",
- .cbs = {
- .create = zebra_allow_external_route_update_create,
- .destroy = zebra_allow_external_route_update_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/dplane-queue-limit",
- .cbs = {
- .modify = zebra_dplane_queue_limit_modify,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/vrf-vni-mapping",
- .cbs = {
- .create = zebra_vrf_vni_mapping_create,
- .destroy = zebra_vrf_vni_mapping_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/vrf-vni-mapping/vni-id",
- .cbs = {
- .modify = zebra_vrf_vni_mapping_vni_id_modify,
- .destroy = zebra_vrf_vni_mapping_vni_id_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/vrf-vni-mapping/prefix-only",
- .cbs = {
- .create = zebra_vrf_vni_mapping_prefix_only_create,
- .destroy = zebra_vrf_vni_mapping_prefix_only_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-events",
- .cbs = {
- .modify = zebra_debugs_debug_events_modify,
- .destroy = zebra_debugs_debug_events_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-zapi-send",
- .cbs = {
- .modify = zebra_debugs_debug_zapi_send_modify,
- .destroy = zebra_debugs_debug_zapi_send_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-zapi-recv",
- .cbs = {
- .modify = zebra_debugs_debug_zapi_recv_modify,
- .destroy = zebra_debugs_debug_zapi_recv_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-zapi-detail",
- .cbs = {
- .modify = zebra_debugs_debug_zapi_detail_modify,
- .destroy = zebra_debugs_debug_zapi_detail_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-kernel",
- .cbs = {
- .modify = zebra_debugs_debug_kernel_modify,
- .destroy = zebra_debugs_debug_kernel_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-kernel-msg-send",
- .cbs = {
- .modify = zebra_debugs_debug_kernel_msg_send_modify,
- .destroy = zebra_debugs_debug_kernel_msg_send_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-kernel-msg-recv",
- .cbs = {
- .modify = zebra_debugs_debug_kernel_msg_recv_modify,
- .destroy = zebra_debugs_debug_kernel_msg_recv_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-rib",
- .cbs = {
- .modify = zebra_debugs_debug_rib_modify,
- .destroy = zebra_debugs_debug_rib_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-rib-detail",
- .cbs = {
- .modify = zebra_debugs_debug_rib_detail_modify,
- .destroy = zebra_debugs_debug_rib_detail_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-fpm",
- .cbs = {
- .modify = zebra_debugs_debug_fpm_modify,
- .destroy = zebra_debugs_debug_fpm_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-nht",
- .cbs = {
- .modify = zebra_debugs_debug_nht_modify,
- .destroy = zebra_debugs_debug_nht_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-nht-detail",
- .cbs = {
- .modify = zebra_debugs_debug_nht_detail_modify,
- .destroy = zebra_debugs_debug_nht_detail_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-mpls",
- .cbs = {
- .modify = zebra_debugs_debug_mpls_modify,
- .destroy = zebra_debugs_debug_mpls_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-vxlan",
- .cbs = {
- .modify = zebra_debugs_debug_vxlan_modify,
- .destroy = zebra_debugs_debug_vxlan_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-pw",
- .cbs = {
- .modify = zebra_debugs_debug_pw_modify,
- .destroy = zebra_debugs_debug_pw_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-dplane",
- .cbs = {
- .modify = zebra_debugs_debug_dplane_modify,
- .destroy = zebra_debugs_debug_dplane_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-dplane-detail",
- .cbs = {
- .modify = zebra_debugs_debug_dplane_detail_modify,
- .destroy = zebra_debugs_debug_dplane_detail_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:zebra/debugs/debug-mlag",
- .cbs = {
- .modify = zebra_debugs_debug_mlag_modify,
- .destroy = zebra_debugs_debug_mlag_destroy,
- }
- },
- {
- .xpath = "/frr-zebra:get-route-information",
- .cbs = {
- .rpc = get_route_information_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-v6-mroute-info",
- .cbs = {
- .rpc = get_v6_mroute_info_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-vrf-info",
- .cbs = {
- .rpc = get_vrf_info_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-vrf-vni-info",
- .cbs = {
- .rpc = get_vrf_vni_info_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-evpn-info",
- .cbs = {
- .rpc = get_evpn_info_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-vni-info",
- .cbs = {
- .rpc = get_vni_info_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-evpn-vni-rmac",
- .cbs = {
- .rpc = get_evpn_vni_rmac_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-evpn-vni-nexthops",
- .cbs = {
- .rpc = get_evpn_vni_nexthops_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:clear-evpn-dup-addr",
- .cbs = {
- .rpc = clear_evpn_dup_addr_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-evpn-macs",
- .cbs = {
- .rpc = get_evpn_macs_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-evpn-arp-cache",
- .cbs = {
- .rpc = get_evpn_arp_cache_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-pbr-ipset",
- .cbs = {
- .rpc = get_pbr_ipset_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-pbr-iptable",
- .cbs = {
- .rpc = get_pbr_iptable_rpc,
- }
- },
- {
- .xpath = "/frr-zebra:get-debugs",
- .cbs = {
- .rpc = get_debugs_rpc,
- }
- },
- {
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip4-addr-list",
- .cbs = {
- .create = lib_interface_zebra_ip4_addr_list_create,
- .destroy = lib_interface_zebra_ip4_addr_list_destroy,
- }
- },
- {
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip4-addr-list/ip4-peer",
- .cbs = {
- .modify = lib_interface_zebra_ip4_addr_list_ip4_peer_modify,
- .destroy = lib_interface_zebra_ip4_addr_list_ip4_peer_destroy,
- }
- },
- {
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip4-addr-list/label",
- .cbs = {
- .modify = lib_interface_zebra_ip4_addr_list_label_modify,
- .destroy = lib_interface_zebra_ip4_addr_list_label_destroy,
- }
- },
- {
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip6-addr-list",
- .cbs = {
- .create = lib_interface_zebra_ip6_addr_list_create,
- .destroy = lib_interface_zebra_ip6_addr_list_destroy,
- }
- },
- {
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/ip6-addr-list/label",
- .cbs = {
- .modify = lib_interface_zebra_ip6_addr_list_label_modify,
- .destroy = lib_interface_zebra_ip6_addr_list_label_destroy,
- }
- },
- {
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/multicast",
- .cbs = {
- .modify = lib_interface_zebra_multicast_modify,
- .destroy = lib_interface_zebra_multicast_destroy,
- }
- },
- {
- .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",
- .cbs = {
- .modify = lib_interface_zebra_shutdown_modify,
- .destroy = lib_interface_zebra_shutdown_destroy,
- }
- },
- {
- .xpath = "/frr-interface:lib/interface/frr-zebra:zebra/bandwidth",
- .cbs = {
- .modify = lib_interface_zebra_bandwidth_modify,
- .destroy = lib_interface_zebra_bandwidth_destroy,
- }
- },
- {
- .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv4-prefix-length",
- .cbs = {
- .modify = lib_route_map_entry_match_condition_ipv4_prefix_length_modify,
- .destroy = lib_route_map_entry_match_condition_ipv4_prefix_length_destroy,
- }
- },
- {
- .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:ipv6-prefix-length",
- .cbs = {
- .modify = lib_route_map_entry_match_condition_ipv6_prefix_length_modify,
- .destroy = lib_route_map_entry_match_condition_ipv6_prefix_length_destroy,
- }
- },
- {
- .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-protocol",
- .cbs = {
- .modify = lib_route_map_entry_match_condition_source_protocol_modify,
- .destroy = lib_route_map_entry_match_condition_source_protocol_destroy,
- }
- },
- {
- .xpath = "/frr-route-map:lib/route-map/entry/match-condition/frr-zebra:source-instance",
- .cbs = {
- .modify = lib_route_map_entry_match_condition_source_instance_modify,
- .destroy = lib_route_map_entry_match_condition_source_instance_destroy,
- }
- },
- {
- .xpath = "/frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v4",
- .cbs = {
- .modify = lib_route_map_entry_set_action_source_v4_modify,
- .destroy = lib_route_map_entry_set_action_source_v4_destroy,
- }
- },
- {
- .xpath = "/frr-route-map:lib/route-map/entry/set-action/frr-zebra:source-v6",
- .cbs = {
- .modify = lib_route_map_entry_set_action_source_v6_modify,
- .destroy = lib_route_map_entry_set_action_source_v6_destroy,
- }
- },
- {
- .xpath = NULL,
- },
- }
-};
diff --git a/zebra/zebra_vty.c b/zebra/zebra_vty.c
index 8042264ca..8024db4ca 100644
--- a/zebra/zebra_vty.c
+++ b/zebra/zebra_vty.c
@@ -54,6 +54,7 @@
#include "zebra/zebra_pbr.h"
#include "zebra/zebra_nhg.h"
#include "zebra/interface.h"
+#include "northbound_cli.h"
extern int allow_delete;
@@ -2934,17 +2935,29 @@ DEFPY (clear_evpn_dup_addr,
"IPv4 address\n"
"IPv6 address\n")
{
- struct zebra_vrf *zvrf;
struct ipaddr host_ip = {.ipa_type = IPADDR_NONE };
int ret = CMD_SUCCESS;
+ struct list *input;
+ struct yang_data *yang_dup = NULL, *yang_dup_ip = NULL,
+ *yang_dup_mac = NULL;
- zvrf = zebra_vrf_get_evpn();
- if (vni_str) {
+ input = list_new();
+
+ if (!vni_str) {
+ yang_dup = yang_data_new(
+ "/frr-zebra:clear-evpn-dup-addr/input/clear-dup-choice",
+ "all-case");
+ } else {
+ yang_dup = yang_data_new_uint32(
+ "/frr-zebra:clear-evpn-dup-addr/input/clear-dup-choice/single-case/vni-id",
+ vni);
if (!is_zero_mac(&mac->eth_addr)) {
- ret = zebra_vxlan_clear_dup_detect_vni_mac(vty, zvrf,
- vni,
- &mac->eth_addr);
- } else if (ip) {
+ yang_dup_mac = yang_data_new_mac(
+ "/frr-zebra:clear-evpn-dup-addr/input/clear-dup-choice/single-case/vni-id/mac-addr",
+ &mac->eth_addr);
+ if (yang_dup_mac)
+ listnode_add(input, yang_dup_mac);
+ } else if (ip) {
if (sockunion_family(ip) == AF_INET) {
host_ip.ipa_type = IPADDR_V4;
host_ip.ipaddr_v4.s_addr = sockunion2ip(ip);
@@ -2953,16 +2966,23 @@ DEFPY (clear_evpn_dup_addr,
memcpy(&host_ip.ipaddr_v6, &ip->sin6.sin6_addr,
sizeof(struct in6_addr));
}
- ret = zebra_vxlan_clear_dup_detect_vni_ip(vty, zvrf,
- vni,
- &host_ip);
- } else
- ret = zebra_vxlan_clear_dup_detect_vni(vty, zvrf, vni);
- } else {
- ret = zebra_vxlan_clear_dup_detect_vni_all(vty, zvrf);
+ yang_dup_ip = yang_data_new_ip(
+ "/frr-zebra:clear-evpn-dup-addr/input/clear-dup-choice/single-case/vni-id/vni-ipaddr",
+ &host_ip);
+
+ if (yang_dup_ip)
+ listnode_add(input, yang_dup_ip);
+ }
}
+ if (yang_dup) {
+ listnode_add(input, yang_dup);
+ ret = nb_cli_rpc("/frr-zebra:clear-evpn-dup-addr", input, NULL);
+ }
+
+ list_delete(&input);
+
return ret;
}
diff --git a/zebra/zebra_vxlan.c b/zebra/zebra_vxlan.c
index 24050d803..d23cdfccd 100644
--- a/zebra/zebra_vxlan.c
+++ b/zebra/zebra_vxlan.c
@@ -6853,9 +6853,8 @@ void zebra_vxlan_print_macs_vni_dad(struct vty *vty,
}
-int zebra_vxlan_clear_dup_detect_vni_mac(struct vty *vty,
- struct zebra_vrf *zvrf,
- vni_t vni, struct ethaddr *macaddr)
+int zebra_vxlan_clear_dup_detect_vni_mac(struct zebra_vrf *zvrf, vni_t vni,
+ struct ethaddr *macaddr)
{
zebra_vni_t *zvni;
zebra_mac_t *mac;
@@ -6863,24 +6862,23 @@ int zebra_vxlan_clear_dup_detect_vni_mac(struct vty *vty,
zebra_neigh_t *nbr = NULL;
if (!is_evpn_enabled())
- return CMD_SUCCESS;
+ return 0;
zvni = zvni_lookup(vni);
if (!zvni) {
- vty_out(vty, "%% VNI %u does not exist\n", vni);
- return CMD_WARNING;
+ zlog_warn("VNI %u does not exist\n", vni);
+ return -1;
}
mac = zvni_mac_lookup(zvni, macaddr);
if (!mac) {
- vty_out(vty, "%% Requested MAC does not exist in VNI %u\n",
- vni);
- return CMD_WARNING;
+ zlog_warn("Requested MAC does not exist in VNI %u\n", vni);
+ return -1;
}
if (!CHECK_FLAG(mac->flags, ZEBRA_MAC_DUPLICATE)) {
- vty_out(vty, "%% Requested MAC is not duplicate detected\n");
- return CMD_WARNING;
+ zlog_warn("Requested MAC is not duplicate detected\n");
+ return -1;
}
/* Remove all IPs as duplicate associcated with this MAC */
@@ -6915,7 +6913,7 @@ int zebra_vxlan_clear_dup_detect_vni_mac(struct vty *vty,
/* warn-only action return */
if (!zvrf->dad_freeze)
- return CMD_SUCCESS;
+ return 0;
/* Local: Notify Peer VTEPs, Remote: Install the entry */
if (CHECK_FLAG(mac->flags, ZEBRA_MAC_LOCAL)) {
@@ -6924,7 +6922,7 @@ int zebra_vxlan_clear_dup_detect_vni_mac(struct vty *vty,
&mac->macaddr,
mac->flags,
mac->loc_seq))
- return CMD_SUCCESS;
+ return 0;
/* Process all neighbors associated with this MAC. */
zvni_process_neigh_on_local_mac_change(zvni, mac, 0);
@@ -6936,12 +6934,11 @@ int zebra_vxlan_clear_dup_detect_vni_mac(struct vty *vty,
zvni_mac_install(zvni, mac);
}
- return CMD_SUCCESS;
+ return 0;
}
-int zebra_vxlan_clear_dup_detect_vni_ip(struct vty *vty,
- struct zebra_vrf *zvrf,
- vni_t vni, struct ipaddr *ip)
+int zebra_vxlan_clear_dup_detect_vni_ip(struct zebra_vrf *zvrf, vni_t vni,
+ struct ipaddr *ip)
{
zebra_vni_t *zvni;
zebra_neigh_t *nbr;
@@ -6950,38 +6947,35 @@ int zebra_vxlan_clear_dup_detect_vni_ip(struct vty *vty,
char buf2[ETHER_ADDR_STRLEN];
if (!is_evpn_enabled())
- return CMD_SUCCESS;
+ return 0;
zvni = zvni_lookup(vni);
if (!zvni) {
- vty_out(vty, "%% VNI %u does not exist\n", vni);
- return CMD_WARNING;
+ zlog_debug("VNI %u does not exist\n", vni);
+ return -1;
}
nbr = zvni_neigh_lookup(zvni, ip);
if (!nbr) {
- vty_out(vty,
- "%% Requested host IP does not exist in VNI %u\n",
- vni);
- return CMD_WARNING;
+ zlog_warn("Requested host IP does not exist in VNI %u\n", vni);
+ return -1;
}
ipaddr2str(&nbr->ip, buf, sizeof(buf));
if (!CHECK_FLAG(nbr->flags, ZEBRA_NEIGH_DUPLICATE)) {
- vty_out(vty,
- "%% Requested host IP %s is not duplicate detected\n",
- buf);
- return CMD_WARNING;
+ zlog_warn("Requested host IP %s is not duplicate detected\n",
+ buf);
+ return -1;
}
mac = zvni_mac_lookup(zvni, &nbr->emac);
if (CHECK_FLAG(mac->flags, ZEBRA_MAC_DUPLICATE)) {
- vty_out(vty,
- "%% Requested IP's associated MAC %s is still in duplicate state\n",
+ zlog_warn(
+ "Requested IP's associated MAC %s is still in duplicate state\n",
prefix_mac2str(&nbr->emac, buf2, sizeof(buf2)));
- return CMD_WARNING_CONFIG_FAILED;
+ return -1;
}
if (IS_ZEBRA_DEBUG_VXLAN)
@@ -7003,7 +6997,7 @@ int zebra_vxlan_clear_dup_detect_vni_ip(struct vty *vty,
zvni_neigh_install(zvni, nbr);
}
- return CMD_SUCCESS;
+ return 0;
}
static void zvni_clear_dup_mac_hash(struct hash_bucket *bucket, void *ctxt)
@@ -7102,7 +7096,6 @@ static void zvni_clear_dup_neigh_hash(struct hash_bucket *bucket, void *ctxt)
static void zvni_clear_dup_detect_hash_vni_all(struct hash_bucket *bucket,
void **args)
{
- struct vty *vty;
zebra_vni_t *zvni;
struct zebra_vrf *zvrf;
struct mac_walk_ctx m_wctx;
@@ -7112,12 +7105,10 @@ static void zvni_clear_dup_detect_hash_vni_all(struct hash_bucket *bucket,
if (!zvni)
return;
- vty = (struct vty *)args[0];
- zvrf = (struct zebra_vrf *)args[1];
+ zvrf = (struct zebra_vrf *)args[0];
if (hashcount(zvni->neigh_table)) {
memset(&n_wctx, 0, sizeof(struct neigh_walk_ctx));
- n_wctx.vty = vty;
n_wctx.zvni = zvni;
n_wctx.zvrf = zvrf;
hash_iterate(zvni->neigh_table, zvni_clear_dup_neigh_hash,
@@ -7127,51 +7118,45 @@ static void zvni_clear_dup_detect_hash_vni_all(struct hash_bucket *bucket,
if (num_valid_macs(zvni)) {
memset(&m_wctx, 0, sizeof(struct mac_walk_ctx));
m_wctx.zvni = zvni;
- m_wctx.vty = vty;
m_wctx.zvrf = zvrf;
hash_iterate(zvni->mac_table, zvni_clear_dup_mac_hash, &m_wctx);
}
}
-int zebra_vxlan_clear_dup_detect_vni_all(struct vty *vty,
- struct zebra_vrf *zvrf)
+int zebra_vxlan_clear_dup_detect_vni_all(struct zebra_vrf *zvrf)
{
- void *args[2];
+ void *args[1];
if (!is_evpn_enabled())
- return CMD_SUCCESS;
+ return 0;
- args[0] = vty;
- args[1] = zvrf;
+ args[0] = zvrf;
hash_iterate(zvrf->vni_table,
(void (*)(struct hash_bucket *, void *))
zvni_clear_dup_detect_hash_vni_all, args);
- return CMD_SUCCESS;
+ return 0;
}
-int zebra_vxlan_clear_dup_detect_vni(struct vty *vty,
- struct zebra_vrf *zvrf,
- vni_t vni)
+int zebra_vxlan_clear_dup_detect_vni(struct zebra_vrf *zvrf, vni_t vni)
{
zebra_vni_t *zvni;
struct mac_walk_ctx m_wctx;
struct neigh_walk_ctx n_wctx;
if (!is_evpn_enabled())
- return CMD_SUCCESS;
+ return 0;
zvni = zvni_lookup(vni);
if (!zvni) {
- vty_out(vty, "%% VNI %u does not exist\n", vni);
- return CMD_WARNING;
+ zlog_warn("VNI %u does not exist\n", vni);
+ return -1;
}
if (hashcount(zvni->neigh_table)) {
memset(&n_wctx, 0, sizeof(struct neigh_walk_ctx));
- n_wctx.vty = vty;
n_wctx.zvni = zvni;
n_wctx.zvrf = zvrf;
hash_iterate(zvni->neigh_table, zvni_clear_dup_neigh_hash,
@@ -7181,12 +7166,11 @@ int zebra_vxlan_clear_dup_detect_vni(struct vty *vty,
if (num_valid_macs(zvni)) {
memset(&m_wctx, 0, sizeof(struct mac_walk_ctx));
m_wctx.zvni = zvni;
- m_wctx.vty = vty;
m_wctx.zvrf = zvrf;
hash_iterate(zvni->mac_table, zvni_clear_dup_mac_hash, &m_wctx);
}
- return CMD_SUCCESS;
+ return 0;
}
/*
@@ -7417,7 +7401,7 @@ void zebra_vxlan_dup_addr_detection(ZAPI_HANDLER_ARGS)
* clear all duplicate detected addresses.
*/
if (zvrf->dup_addr_detect && !dup_addr_detect)
- zebra_vxlan_clear_dup_detect_vni_all(NULL, zvrf);
+ zebra_vxlan_clear_dup_detect_vni_all(zvrf);
zvrf->dup_addr_detect = dup_addr_detect;
zvrf->dad_time = time;
diff --git a/zebra/zebra_vxlan.h b/zebra/zebra_vxlan.h
index a5c13a59e..064dda6cd 100644
--- a/zebra/zebra_vxlan.h
+++ b/zebra/zebra_vxlan.h
@@ -205,18 +205,13 @@ extern void zebra_vxlan_evpn_vrf_route_add(vrf_id_t vrf_id,
extern void zebra_vxlan_evpn_vrf_route_del(vrf_id_t vrf_id,
struct ipaddr *vtep_ip,
struct prefix *host_prefix);
-extern int zebra_vxlan_clear_dup_detect_vni_mac(struct vty *vty,
- struct zebra_vrf *zvrf,
+extern int zebra_vxlan_clear_dup_detect_vni_mac(struct zebra_vrf *zvrf,
vni_t vni,
struct ethaddr *macaddr);
-extern int zebra_vxlan_clear_dup_detect_vni_ip(struct vty *vty,
- struct zebra_vrf *zvrf,
+extern int zebra_vxlan_clear_dup_detect_vni_ip(struct zebra_vrf *zvrf,
vni_t vni, struct ipaddr *ip);
-extern int zebra_vxlan_clear_dup_detect_vni_all(struct vty *vty,
- struct zebra_vrf *zvrf);
-extern int zebra_vxlan_clear_dup_detect_vni(struct vty *vty,
- struct zebra_vrf *zvrf,
- vni_t vni);
+extern int zebra_vxlan_clear_dup_detect_vni_all(struct zebra_vrf *zvrf);
+extern int zebra_vxlan_clear_dup_detect_vni(struct zebra_vrf *zvrf, vni_t vni);
extern void zebra_vxlan_handle_result(struct zebra_dplane_ctx *ctx);
extern void zebra_evpn_init(void);