--- /dev/null
+/*
+ * EIGRP daemon CLI 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_cli.h"
+
+#include "eigrp_structs.h"
+#include "eigrpd.h"
+#include "eigrp_zebra.h"
+
+#ifndef VTYSH_EXTRACT_PL
+#include "eigrpd/eigrp_cli_clippy.c"
+#endif /* VTYSH_EXTRACT_PL */
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance
+ */
+DEFPY_NOSH(
+ router_eigrp,
+ router_eigrp_cmd,
+ "router eigrp (1-65535)$as",
+ ROUTER_STR
+ EIGRP_STR
+ AS_STR)
+{
+ char xpath[XPATH_MAXLEN];
+ int rv;
+
+ snprintf(xpath, sizeof(xpath),
+ "/frr-eigrpd:eigrpd/instance[asn='%s'][vrf='']",
+ as_str);
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ rv = nb_cli_apply_changes(vty, NULL);
+ if (rv == CMD_SUCCESS)
+ VTY_PUSH_XPATH(EIGRP_NODE, xpath);
+
+ return rv;
+}
+
+DEFPY_NOSH(
+ no_router_eigrp,
+ no_router_eigrp_cmd,
+ "no router eigrp (1-65535)$as",
+ NO_STR
+ ROUTER_STR
+ EIGRP_STR
+ AS_STR)
+{
+ char xpath[XPATH_MAXLEN];
+
+ snprintf(xpath, sizeof(xpath),
+ "/frr-eigrpd:eigrpd/instance[asn='%s'][vrf='']",
+ as_str);
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_header(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *asn = yang_dnode_get_string(dnode, "./asn");
+
+ vty_out(vty, "router eigrp %s\n", asn);
+}
+
+void eigrp_cli_show_end_header(struct vty *vty, struct lyd_node *dnode)
+{
+ vty_out(vty, "!\n");
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/router-id
+ */
+DEFPY(
+ eigrp_router_id,
+ eigrp_router_id_cmd,
+ "eigrp router-id A.B.C.D$addr",
+ EIGRP_STR
+ "Router ID for this EIGRP process\n"
+ "EIGRP Router-ID in IP address format\n")
+{
+ nb_cli_enqueue_change(vty, "./router-id", NB_OP_MODIFY, addr_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_router_id,
+ no_eigrp_router_id_cmd,
+ "no eigrp router-id [A.B.C.D]",
+ NO_STR
+ EIGRP_STR
+ "Router ID for this EIGRP process\n"
+ "EIGRP Router-ID in IP address format\n")
+{
+ nb_cli_enqueue_change(vty, "./router-id", NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_router_id(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *router_id = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " eigrp router-id %s\n", router_id);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/passive-interface
+ */
+DEFPY(
+ eigrp_passive_interface,
+ eigrp_passive_interface_cmd,
+ "[no] passive-interface IFNAME",
+ NO_STR
+ "Suppress routing updates on an interface\n"
+ "Interface to suppress on\n")
+{
+ if (no)
+ nb_cli_enqueue_change(vty, "./passive-interface",
+ NB_OP_DESTROY, ifname);
+ else
+ nb_cli_enqueue_change(vty, "./passive-interface",
+ NB_OP_CREATE, ifname);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_passive_interface(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *ifname = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " passive-interface %s\n", ifname);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/active-time
+ */
+DEFPY(
+ eigrp_timers_active,
+ eigrp_timers_active_cmd,
+ "timers active-time <(1-65535)$timer|disabled$disabled>",
+ "Adjust routing timers\n"
+ "Time limit for active state\n"
+ "Active state time limit in seconds\n"
+ "Disable time limit for active state\n")
+{
+ if (disabled)
+ nb_cli_enqueue_change(vty, "./active-time", NB_OP_MODIFY, "0");
+ else
+ nb_cli_enqueue_change(vty, "./active-time",
+ NB_OP_MODIFY, timer_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_timers_active,
+ no_eigrp_timers_active_cmd,
+ "no timers active-time [<(1-65535)|disabled>]",
+ NO_STR
+ "Adjust routing timers\n"
+ "Time limit for active state\n"
+ "Active state time limit in seconds\n"
+ "Disable time limit for active state\n")
+{
+ nb_cli_enqueue_change(vty, "./active-time", NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_active_time(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *timer = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " timers active-time %s\n", timer);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/variance
+ */
+DEFPY(
+ eigrp_variance,
+ eigrp_variance_cmd,
+ "variance (1-128)$variance",
+ "Control load balancing variance\n"
+ "Metric variance multiplier\n")
+{
+ nb_cli_enqueue_change(vty, "./variance", NB_OP_MODIFY, variance_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_variance,
+ no_eigrp_variance_cmd,
+ "no variance [(1-128)]",
+ NO_STR
+ "Control load balancing variance\n"
+ "Metric variance multiplier\n")
+{
+ nb_cli_enqueue_change(vty, "./variance", NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_variance(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *variance = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " variance %s\n", variance);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/maximum-paths
+ */
+DEFPY(
+ eigrp_maximum_paths,
+ eigrp_maximum_paths_cmd,
+ "maximum-paths (1-32)$maximum_paths",
+ "Forward packets over multiple paths\n"
+ "Number of paths\n")
+{
+ nb_cli_enqueue_change(vty, "./maximum-paths", NB_OP_MODIFY,
+ maximum_paths_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_maximum_paths,
+ no_eigrp_maximum_paths_cmd,
+ "no maximum-paths [(1-32)]",
+ NO_STR
+ "Forward packets over multiple paths\n"
+ "Number of paths\n")
+{
+ nb_cli_enqueue_change(vty, "./maximum-paths", NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_maximum_paths(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *maximum_paths = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " maximum-paths %s\n", maximum_paths);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K1
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K2
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K3
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K4
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K5
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K6
+ */
+DEFPY(
+ eigrp_metric_weights,
+ eigrp_metric_weights_cmd,
+ "metric weights (0-255)$k1 (0-255)$k2 (0-255)$k3 (0-255)$k4 (0-255)$k5 [(0-255)$k6]",
+ "Modify metrics and parameters for advertisement\n"
+ "Modify metric coefficients\n"
+ "K1\n"
+ "K2\n"
+ "K3\n"
+ "K4\n"
+ "K5\n"
+ "K6\n")
+{
+ nb_cli_enqueue_change(vty, "./metric-weights/K1", NB_OP_MODIFY, k1_str);
+ nb_cli_enqueue_change(vty, "./metric-weights/K2", NB_OP_MODIFY, k2_str);
+ nb_cli_enqueue_change(vty, "./metric-weights/K3", NB_OP_MODIFY, k3_str);
+ nb_cli_enqueue_change(vty, "./metric-weights/K4", NB_OP_MODIFY, k4_str);
+ nb_cli_enqueue_change(vty, "./metric-weights/K5", NB_OP_MODIFY, k5_str);
+ if (k6)
+ nb_cli_enqueue_change(vty, "./metric-weights/K6",
+ NB_OP_MODIFY, k6_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_metric_weights,
+ no_eigrp_metric_weights_cmd,
+ "no metric weights [(0-255) (0-255) (0-255) (0-255) (0-255) (0-255)]",
+ NO_STR
+ "Modify metrics and parameters for advertisement\n"
+ "Modify metric coefficients\n"
+ "K1\n"
+ "K2\n"
+ "K3\n"
+ "K4\n"
+ "K5\n"
+ "K6\n")
+{
+ nb_cli_enqueue_change(vty, "./metric-weights/K1", NB_OP_DESTROY, NULL);
+ nb_cli_enqueue_change(vty, "./metric-weights/K2", NB_OP_DESTROY, NULL);
+ nb_cli_enqueue_change(vty, "./metric-weights/K3", NB_OP_DESTROY, NULL);
+ nb_cli_enqueue_change(vty, "./metric-weights/K4", NB_OP_DESTROY, NULL);
+ nb_cli_enqueue_change(vty, "./metric-weights/K5", NB_OP_DESTROY, NULL);
+ nb_cli_enqueue_change(vty, "./metric-weights/K6", NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_metrics(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *k1, *k2, *k3, *k4, *k5, *k6;
+
+ k1 = yang_dnode_exists(dnode, "./K1") ?
+ yang_dnode_get_string(dnode, "./K1") : "0";
+ k2 = yang_dnode_exists(dnode, "./K2") ?
+ yang_dnode_get_string(dnode, "./K2") : "0";
+ k3 = yang_dnode_exists(dnode, "./K3") ?
+ yang_dnode_get_string(dnode, "./K3") : "0";
+ k4 = yang_dnode_exists(dnode, "./K4") ?
+ yang_dnode_get_string(dnode, "./K4") : "0";
+ k5 = yang_dnode_exists(dnode, "./K5") ?
+ yang_dnode_get_string(dnode, "./K5") : "0";
+ k6 = yang_dnode_exists(dnode, "./K6") ?
+ yang_dnode_get_string(dnode, "./K6") : "0";
+
+ vty_out(vty, " metric weights %s %s %s %s %s",
+ k1, k2, k3, k4, k5);
+ if (k6)
+ vty_out(vty, " %s", k6);
+ vty_out(vty, "\n");
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/network
+ */
+DEFPY(
+ eigrp_network,
+ eigrp_network_cmd,
+ "[no] network A.B.C.D/M$prefix",
+ NO_STR
+ "Enable routing on an IP network\n"
+ "EIGRP network prefix\n")
+{
+ if (no)
+ nb_cli_enqueue_change(vty, "./network", NB_OP_DESTROY,
+ prefix_str);
+ else
+ nb_cli_enqueue_change(vty, "./network", NB_OP_CREATE,
+ prefix_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_network(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *prefix = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " network %s\n", prefix);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/neighbor
+ */
+DEFPY(
+ eigrp_neighbor,
+ eigrp_neighbor_cmd,
+ "[no] neighbor A.B.C.D$addr",
+ NO_STR
+ "Specify a neighbor router\n"
+ "Neighbor address\n")
+{
+ if (no)
+ nb_cli_enqueue_change(vty, "./neighbor", NB_OP_DESTROY,
+ addr_str);
+ else
+ nb_cli_enqueue_change(vty, "./neighbor", NB_OP_CREATE,
+ addr_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_neighbor(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *prefix = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " neighbor %s\n", prefix);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/route-map
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/bandwidth
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/delay
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/reliability
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/load
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/mtu
+ */
+DEFPY(
+ eigrp_redistribute_source_metric,
+ eigrp_redistribute_source_metric_cmd,
+ "[no] redistribute " FRR_REDIST_STR_EIGRPD
+ "$proto [metric (1-4294967295)$bw (0-4294967295)$delay (0-255)$rlbt (1-255)$load (1-65535)$mtu]",
+ NO_STR
+ REDIST_STR
+ FRR_REDIST_HELP_STR_EIGRPD
+ "Metric for redistributed routes\n"
+ "Bandwidth metric in Kbits per second\n"
+ "EIGRP delay metric, in 10 microsecond units\n"
+ "EIGRP reliability metric where 255 is 100% reliable2 ?\n"
+ "EIGRP Effective bandwidth metric (Loading) where 255 is 100% loaded\n"
+ "EIGRP MTU of the path\n")
+{
+ char xpath[XPATH_MAXLEN], xpath_metric[XPATH_MAXLEN + 64];
+
+ snprintf(xpath, sizeof(xpath), "./redistribute[protocol='%s']", proto);
+
+ if (no) {
+ nb_cli_enqueue_change(vty, xpath, NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+ }
+
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+ if (bw == 0 || delay == 0 || rlbt == 0 || load == 0 || mtu == 0)
+ return nb_cli_apply_changes(vty, NULL);
+
+ snprintf(xpath_metric, sizeof(xpath_metric), "%s/metrics/bandwidth",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_metric, NB_OP_MODIFY, bw_str);
+ snprintf(xpath_metric, sizeof(xpath_metric), "%s/metrics/delay", xpath);
+ nb_cli_enqueue_change(vty, xpath_metric, NB_OP_MODIFY, delay_str);
+ snprintf(xpath_metric, sizeof(xpath_metric), "%s/metrics/reliability",
+ xpath);
+ nb_cli_enqueue_change(vty, xpath_metric, NB_OP_MODIFY, rlbt_str);
+ snprintf(xpath_metric, sizeof(xpath_metric), "%s/metrics/load", xpath);
+ nb_cli_enqueue_change(vty, xpath_metric, NB_OP_MODIFY, load_str);
+ snprintf(xpath_metric, sizeof(xpath_metric), "%s/metrics/mtu", xpath);
+ nb_cli_enqueue_change(vty, xpath_metric, NB_OP_MODIFY, mtu_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_redistribute(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *proto = yang_dnode_get_string(dnode, "./protocol");
+ const char *bw, *delay, *load, *mtu, *rlbt;
+
+ bw = yang_dnode_exists(dnode, "./metrics/bandwidth") ?
+ yang_dnode_get_string(dnode, "./metrics/bandwidth") : NULL;
+ delay = yang_dnode_exists(dnode, "./metrics/delay") ?
+ yang_dnode_get_string(dnode, "./metrics/delay") : NULL;
+ rlbt = yang_dnode_exists(dnode, "./metrics/reliability") ?
+ yang_dnode_get_string(dnode, "./metrics/reliability") : NULL;
+ load = yang_dnode_exists(dnode, "./metrics/load") ?
+ yang_dnode_get_string(dnode, "./metrics/load") : NULL;
+ mtu = yang_dnode_exists(dnode, "./metrics/mtu") ?
+ yang_dnode_get_string(dnode, "./metrics/mtu") : NULL;
+
+ vty_out(vty, " redistribute %s", proto);
+ if (bw || rlbt || delay || load || mtu)
+ vty_out(vty, " metric %s %s %s %s %s", bw, delay, rlbt, load,
+ mtu);
+ vty_out(vty, "\n");
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/delay
+ */
+DEFPY(
+ eigrp_if_delay,
+ eigrp_if_delay_cmd,
+ "delay (1-16777215)$delay",
+ "Specify interface throughput delay\n"
+ "Throughput delay (tens of microseconds)\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/delay",
+ NB_OP_MODIFY, delay_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_if_delay,
+ no_eigrp_if_delay_cmd,
+ "no delay [(1-16777215)]",
+ NO_STR
+ "Specify interface throughput delay\n"
+ "Throughput delay (tens of microseconds)\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/delay",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_delay(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *delay = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " delay %s\n", delay);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/bandwidth
+ */
+DEFPY(
+ eigrp_if_bandwidth,
+ eigrp_if_bandwidth_cmd,
+ "eigrp bandwidth (1-10000000)$bw",
+ EIGRP_STR
+ "Set bandwidth informational parameter\n"
+ "Bandwidth in kilobits\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/bandwidth",
+ NB_OP_MODIFY, bw_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_if_bandwidth,
+ no_eigrp_if_bandwidth_cmd,
+ "no eigrp bandwidth [(1-10000000)]",
+ NO_STR
+ EIGRP_STR
+ "Set bandwidth informational parameter\n"
+ "Bandwidth in kilobits\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/bandwidth",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_bandwidth(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *bandwidth = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " eigrp bandwidth %s\n", bandwidth);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/hello-interval
+ */
+DEFPY(
+ eigrp_if_ip_hellointerval,
+ eigrp_if_ip_hellointerval_cmd,
+ "ip hello-interval eigrp (1-65535)$hello",
+ "Interface Internet Protocol config commands\n"
+ "Configures EIGRP hello interval\n"
+ EIGRP_STR
+ "Seconds between hello transmissions\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/hello-interval",
+ NB_OP_MODIFY, hello_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_if_ip_hellointerval,
+ no_eigrp_if_ip_hellointerval_cmd,
+ "no ip hello-interval eigrp [(1-65535)]",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Configures EIGRP hello interval\n"
+ EIGRP_STR
+ "Seconds between hello transmissions\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/hello-interval",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+
+void eigrp_cli_show_hello_interval(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *hello = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " ip hello-interval eigrp %s\n", hello);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/hold-time
+ */
+DEFPY(
+ eigrp_if_ip_holdinterval,
+ eigrp_if_ip_holdinterval_cmd,
+ "ip hold-time eigrp (1-65535)$hold",
+ "Interface Internet Protocol config commands\n"
+ "Configures EIGRP IPv4 hold time\n"
+ EIGRP_STR
+ "Seconds before neighbor is considered down\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/hold-time",
+ NB_OP_MODIFY, hold_str);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_if_ip_holdinterval,
+ no_eigrp_if_ip_holdinterval_cmd,
+ "no ip hold-time eigrp [(1-65535)]",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Configures EIGRP IPv4 hold time\n"
+ EIGRP_STR
+ "Seconds before neighbor is considered down\n")
+{
+ nb_cli_enqueue_change(vty, "./frr-eigrpd:eigrp/hold-time",
+ NB_OP_DESTROY, NULL);
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_hold_time(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const char *holdtime = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " ip hold-time eigrp %s\n", holdtime);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/split-horizon
+ */
+/* NOT implemented. */
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/summarize-addresses
+ */
+DEFPY(
+ eigrp_ip_summary_address,
+ eigrp_ip_summary_address_cmd,
+ "ip summary-address eigrp (1-65535)$as A.B.C.D/M$prefix",
+ "Interface Internet Protocol config commands\n"
+ "Perform address summarization\n"
+ EIGRP_STR
+ AS_STR
+ "Summary <network>/<length>, e.g. 192.168.0.0/16\n")
+{
+ char xpath[XPATH_MAXLEN], xpath_auth[XPATH_MAXLEN + 64];
+
+ snprintf(xpath, sizeof(xpath), "./frr-eigrpd:eigrp/instance[asn='%s']",
+ as_str);
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+
+ snprintf(xpath_auth, sizeof(xpath_auth), "%s/summarize-address", xpath);
+ nb_cli_enqueue_change(vty, xpath_auth, NB_OP_CREATE, prefix_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_ip_summary_address,
+ no_eigrp_ip_summary_address_cmd,
+ "no ip summary-address eigrp (1-65535)$as A.B.C.D/M$prefix",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Perform address summarization\n"
+ EIGRP_STR
+ AS_STR
+ "Summary <network>/<length>, e.g. 192.168.0.0/16\n")
+{
+ char xpath[XPATH_MAXLEN], xpath_auth[XPATH_MAXLEN + 64];
+
+ snprintf(xpath, sizeof(xpath), "./frr-eigrpd:eigrp/instance[asn='%s']",
+ as_str);
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+
+ snprintf(xpath_auth, sizeof(xpath_auth), "%s/summarize-address", xpath);
+ nb_cli_enqueue_change(vty, xpath_auth, NB_OP_DESTROY, prefix_str);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_summarize_address(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const struct eigrp_interface *eif = nb_running_get_entry(dnode, NULL,
+ true);
+ const char *summarize_address = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " ip summary-address eigrp %d %s\n",
+ eif->eigrp->AS, summarize_address);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/authentication
+ */
+DEFPY(
+ eigrp_authentication_mode,
+ eigrp_authentication_mode_cmd,
+ "ip authentication mode eigrp (1-65535)$as <md5|hmac-sha-256>$crypt",
+ "Interface Internet Protocol config commands\n"
+ "Authentication subcommands\n"
+ "Mode\n"
+ EIGRP_STR
+ AS_STR
+ "Keyed message digest\n"
+ "HMAC SHA256 algorithm \n")
+{
+ char xpath[XPATH_MAXLEN], xpath_auth[XPATH_MAXLEN + 64];
+
+ snprintf(xpath, sizeof(xpath), "./frr-eigrpd:eigrp/instance[asn='%s']",
+ as_str);
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+
+ snprintf(xpath_auth, sizeof(xpath_auth), "%s/authentication", xpath);
+ nb_cli_enqueue_change(vty, xpath_auth, NB_OP_MODIFY, crypt);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_authentication_mode,
+ no_eigrp_authentication_mode_cmd,
+ "no ip authentication mode eigrp (1-65535)$as [<md5|hmac-sha-256>]",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Authentication subcommands\n"
+ "Mode\n"
+ EIGRP_STR
+ AS_STR
+ "Keyed message digest\n"
+ "HMAC SHA256 algorithm \n")
+{
+ char xpath[XPATH_MAXLEN], xpath_auth[XPATH_MAXLEN + 64];
+
+ snprintf(xpath, sizeof(xpath), "./frr-eigrpd:eigrp/instance[asn='%s']",
+ as_str);
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+
+ snprintf(xpath_auth, sizeof(xpath_auth), "%s/authentication", xpath);
+ nb_cli_enqueue_change(vty, xpath_auth, NB_OP_MODIFY, "none");
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_authentication(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const struct eigrp_interface *eif = nb_running_get_entry(dnode, NULL,
+ true);
+ const char *crypt = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " ip authentication mode eigrp %d %s\n",
+ eif->eigrp->AS, crypt);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/keychain
+ */
+DEFPY(
+ eigrp_authentication_keychain,
+ eigrp_authentication_keychain_cmd,
+ "ip authentication key-chain eigrp (1-65535)$as WORD$name",
+ "Interface Internet Protocol config commands\n"
+ "Authentication subcommands\n"
+ "Key-chain\n"
+ EIGRP_STR
+ AS_STR
+ "Name of key-chain\n")
+{
+ char xpath[XPATH_MAXLEN], xpath_auth[XPATH_MAXLEN + 64];
+
+ snprintf(xpath, sizeof(xpath), "./frr-eigrpd:eigrp/instance[asn='%s']",
+ as_str);
+ nb_cli_enqueue_change(vty, xpath, NB_OP_CREATE, NULL);
+
+ snprintf(xpath_auth, sizeof(xpath_auth), "%s/keychain", xpath);
+ nb_cli_enqueue_change(vty, xpath_auth, NB_OP_MODIFY, name);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+DEFPY(
+ no_eigrp_authentication_keychain,
+ no_eigrp_authentication_keychain_cmd,
+ "no ip authentication key-chain eigrp (1-65535)$as [WORD]",
+ NO_STR
+ "Interface Internet Protocol config commands\n"
+ "Authentication subcommands\n"
+ "Key-chain\n"
+ EIGRP_STR
+ AS_STR
+ "Name of key-chain\n")
+{
+ char xpath[XPATH_MAXLEN], xpath_auth[XPATH_MAXLEN + 64];
+
+ snprintf(xpath, sizeof(xpath), "./frr-eigrpd:eigrp/instance[asn='%s']",
+ as_str);
+ snprintf(xpath_auth, sizeof(xpath_auth), "%s/keychain", xpath);
+ nb_cli_enqueue_change(vty, xpath_auth, NB_OP_DESTROY, NULL);
+
+ return nb_cli_apply_changes(vty, NULL);
+}
+
+void eigrp_cli_show_keychain(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults)
+{
+ const struct eigrp_interface *eif = nb_running_get_entry(dnode, NULL,
+ true);
+ const char *keychain = yang_dnode_get_string(dnode, NULL);
+
+ vty_out(vty, " ip authentication key-chain eigrp %d %s\n",
+ eif->eigrp->AS, keychain);
+}
+
+
+/*
+ * CLI installation procedures.
+ */
+static struct cmd_node eigrp_node = {EIGRP_NODE, "%s(config-router)# ", 1};
+
+static int eigrp_config_write(struct vty *vty)
+{
+ struct lyd_node *dnode;
+ int written = 0;
+
+ dnode = yang_dnode_get(running_config->dnode, "/frr-eigrpd:eigrpd");
+ if (dnode) {
+ nb_cli_show_dnode_cmds(vty, dnode, false);
+ written = 1;
+ }
+
+ return written;
+}
+
+static struct cmd_node eigrp_interface_node = {INTERFACE_NODE,
+ "%s(config-if)# ", 1};
+
+
+static int eigrp_write_interface(struct vty *vty)
+{
+ struct lyd_node *dnode;
+ struct interface *ifp;
+ struct vrf *vrf;
+ int written = 0;
+
+ RB_FOREACH(vrf, vrf_name_head, &vrfs_by_name) {
+ FOR_ALL_INTERFACES(vrf, ifp) {
+ dnode = yang_dnode_get(
+ running_config->dnode,
+ "/frr-interface:lib/interface[name='%s'][vrf='%s']",
+ ifp->name, vrf->name);
+ if (dnode == NULL)
+ continue;
+
+ written = 1;
+ nb_cli_show_dnode_cmds(vty, dnode, false);
+ }
+ }
+
+ return written;
+}
+
+void
+eigrp_cli_init(void)
+{
+ install_element(CONFIG_NODE, &router_eigrp_cmd);
+ install_element(CONFIG_NODE, &no_router_eigrp_cmd);
+
+ install_node(&eigrp_node, eigrp_config_write);
+ install_default(EIGRP_NODE);
+
+ install_element(EIGRP_NODE, &eigrp_router_id_cmd);
+ install_element(EIGRP_NODE, &no_eigrp_router_id_cmd);
+ install_element(EIGRP_NODE, &eigrp_passive_interface_cmd);
+ install_element(EIGRP_NODE, &eigrp_timers_active_cmd);
+ install_element(EIGRP_NODE, &no_eigrp_timers_active_cmd);
+ install_element(EIGRP_NODE, &eigrp_variance_cmd);
+ install_element(EIGRP_NODE, &no_eigrp_variance_cmd);
+ install_element(EIGRP_NODE, &eigrp_maximum_paths_cmd);
+ install_element(EIGRP_NODE, &no_eigrp_maximum_paths_cmd);
+ install_element(EIGRP_NODE, &eigrp_metric_weights_cmd);
+ install_element(EIGRP_NODE, &no_eigrp_metric_weights_cmd);
+ install_element(EIGRP_NODE, &eigrp_network_cmd);
+ install_element(EIGRP_NODE, &eigrp_neighbor_cmd);
+ install_element(EIGRP_NODE, &eigrp_redistribute_source_metric_cmd);
+
+ install_node(&eigrp_interface_node, eigrp_write_interface);
+ if_cmd_init();
+
+ install_element(INTERFACE_NODE, &eigrp_if_delay_cmd);
+ install_element(INTERFACE_NODE, &no_eigrp_if_delay_cmd);
+ install_element(INTERFACE_NODE, &eigrp_if_bandwidth_cmd);
+ install_element(INTERFACE_NODE, &no_eigrp_if_bandwidth_cmd);
+ install_element(INTERFACE_NODE, &eigrp_if_ip_hellointerval_cmd);
+ install_element(INTERFACE_NODE, &no_eigrp_if_ip_hellointerval_cmd);
+ install_element(INTERFACE_NODE, &eigrp_if_ip_holdinterval_cmd);
+ install_element(INTERFACE_NODE, &no_eigrp_if_ip_holdinterval_cmd);
+ install_element(INTERFACE_NODE, &eigrp_ip_summary_address_cmd);
+ install_element(INTERFACE_NODE, &no_eigrp_ip_summary_address_cmd);
+ install_element(INTERFACE_NODE, &eigrp_authentication_mode_cmd);
+ install_element(INTERFACE_NODE, &no_eigrp_authentication_mode_cmd);
+ install_element(INTERFACE_NODE, &eigrp_authentication_keychain_cmd);
+ install_element(INTERFACE_NODE, &no_eigrp_authentication_keychain_cmd);
+}
};
static const struct frr_yang_module_info *eigrpd_yang_modules[] = {
+ &frr_eigrpd_info,
&frr_interface_info,
};
eigrp_vty_init();
keychain_init();
eigrp_vty_show_init();
- eigrp_vty_if_init();
+ eigrp_cli_init();
#ifdef HAVE_SNMP
eigrp_snmp_init();
--- /dev/null
+/*
+ * EIGRP daemon 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/keychain.h"
+#include "lib/log.h"
+#include "lib/northbound.h"
+#include "lib/table.h"
+#include "lib/vrf.h"
+#include "lib/zclient.h"
+
+#include "eigrp_structs.h"
+#include "eigrpd.h"
+#include "eigrp_interface.h"
+#include "eigrp_network.h"
+#include "eigrp_zebra.h"
+
+/* Helper functions. */
+static void redistribute_get_metrics(const struct lyd_node *dnode,
+ struct eigrp_metrics *em)
+{
+ memset(em, 0, sizeof(*em));
+
+ if (yang_dnode_exists(dnode, "./bandwidth"))
+ em->bandwidth = yang_dnode_get_uint32(dnode, "./bandwidth");
+ if (yang_dnode_exists(dnode, "./delay"))
+ em->delay = yang_dnode_get_uint32(dnode, "./delay");
+#if 0 /* TODO: How does MTU work? */
+ if (yang_dnode_exists(dnode, "./mtu"))
+ em->mtu[0] = yang_dnode_get_uint32(dnode, "./mtu");
+#endif
+ if (yang_dnode_exists(dnode, "./load"))
+ em->load = yang_dnode_get_uint32(dnode, "./load");
+ if (yang_dnode_exists(dnode, "./reliability"))
+ em->reliability = yang_dnode_get_uint32(dnode, "./reliability");
+}
+
+static struct eigrp_interface *eigrp_interface_lookup(const struct eigrp *eigrp,
+ const char *ifname)
+{
+ struct eigrp_interface *eif;
+ struct listnode *ln;
+
+ for (ALL_LIST_ELEMENTS_RO(eigrp->eiflist, ln, eif)) {
+ if (strcmp(ifname, eif->ifp->name))
+ continue;
+
+ return eif;
+ }
+
+ return NULL;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance
+ */
+static int eigrpd_instance_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* NOTHING */
+ break;
+ case NB_EV_PREPARE:
+ eigrp = eigrp_get(yang_dnode_get_string(dnode, "./asn"));
+ resource->ptr = eigrp;
+ break;
+ case NB_EV_ABORT:
+ eigrp_finish_final(resource->ptr);
+ break;
+ case NB_EV_APPLY:
+ nb_running_set_entry(dnode, resource->ptr);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_unset_entry(dnode);
+ eigrp_finish_final(eigrp);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/router-id
+ */
+static int eigrpd_instance_router_id_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ yang_dnode_get_ipv4(&eigrp->router_id_static, dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_router_id_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->router_id_static.s_addr = 0;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/passive-interface
+ */
+static int
+eigrpd_instance_passive_interface_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp_interface *eif;
+ struct eigrp *eigrp;
+ const char *ifname;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ eigrp = nb_running_get_entry(dnode, NULL, false);
+ if (eigrp == NULL) {
+ /*
+ * XXX: we can't verify if the interface exists
+ * and is active until EIGRP is up.
+ */
+ break;
+ }
+
+ ifname = yang_dnode_get_string(dnode, NULL);
+ eif = eigrp_interface_lookup(eigrp, ifname);
+ if (eif == NULL)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ ifname = yang_dnode_get_string(dnode, NULL);
+ eif = eigrp_interface_lookup(eigrp, ifname);
+ if (eif == NULL)
+ return NB_ERR_INCONSISTENCY;
+
+ eif->params.passive_interface = EIGRP_IF_PASSIVE;
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_passive_interface_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp_interface *eif;
+ struct eigrp *eigrp;
+ const char *ifname;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ ifname = yang_dnode_get_string(dnode, NULL);
+ eif = eigrp_interface_lookup(eigrp, ifname);
+ if (eif == NULL)
+ break;
+
+ eif->params.passive_interface = EIGRP_IF_ACTIVE;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/active-time
+ */
+static int eigrpd_instance_active_time_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/variance
+ */
+static int eigrpd_instance_variance_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->variance = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_variance_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->variance = EIGRP_VARIANCE_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/maximum-paths
+ */
+static int eigrpd_instance_maximum_paths_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->max_paths = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_maximum_paths_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->max_paths = EIGRP_MAX_PATHS_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K1
+ */
+static int
+eigrpd_instance_metric_weights_K1_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[0] = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_metric_weights_K1_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[0] = EIGRP_K1_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K2
+ */
+static int
+eigrpd_instance_metric_weights_K2_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[1] = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_metric_weights_K2_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[1] = EIGRP_K2_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K3
+ */
+static int
+eigrpd_instance_metric_weights_K3_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[2] = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_metric_weights_K3_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[2] = EIGRP_K3_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K4
+ */
+static int
+eigrpd_instance_metric_weights_K4_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[3] = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_metric_weights_K4_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[3] = EIGRP_K4_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K5
+ */
+static int
+eigrpd_instance_metric_weights_K5_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[4] = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_metric_weights_K5_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[4] = EIGRP_K5_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/metric-weights/K6
+ */
+static int
+eigrpd_instance_metric_weights_K6_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[5] = yang_dnode_get_uint8(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_metric_weights_K6_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp->k_values[5] = EIGRP_K6_DEFAULT;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/network
+ */
+static int eigrpd_instance_network_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct route_node *rnode;
+ struct prefix prefix;
+ struct eigrp *eigrp;
+ int exists;
+
+ yang_dnode_get_ipv4p(&prefix, dnode, NULL);
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ eigrp = nb_running_get_entry(dnode, NULL, false);
+ /* If entry doesn't exist it means the list is empty. */
+ if (eigrp == NULL)
+ break;
+
+ rnode = route_node_get(eigrp->networks, &prefix);
+ exists = (rnode->info != NULL);
+ route_unlock_node(rnode);
+ if (exists)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ if (eigrp_network_set(eigrp, &prefix) == 0)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_network_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct route_node *rnode;
+ struct prefix prefix;
+ struct eigrp *eigrp;
+ int exists = 0;
+
+ yang_dnode_get_ipv4p(&prefix, dnode, NULL);
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ eigrp = nb_running_get_entry(dnode, NULL, false);
+ /* If entry doesn't exist it means the list is empty. */
+ if (eigrp == NULL)
+ break;
+
+ rnode = route_node_get(eigrp->networks, &prefix);
+ exists = (rnode->info != NULL);
+ route_unlock_node(rnode);
+ if (exists == 0)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ eigrp_network_unset(eigrp, &prefix);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/neighbor
+ */
+static int eigrpd_instance_neighbor_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_neighbor_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute
+ */
+static int eigrpd_instance_redistribute_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp_metrics metrics;
+ struct eigrp *eigrp;
+ uint32_t proto;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ proto = yang_dnode_get_enum(dnode, "./protocol");
+ if (vrf_bitmap_check(zclient->redist[AFI_IP][proto],
+ VRF_DEFAULT))
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ proto = yang_dnode_get_enum(dnode, "./protocol");
+ redistribute_get_metrics(dnode, &metrics);
+ eigrp_redistribute_set(eigrp, proto, metrics);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_redistribute_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp *eigrp;
+ uint32_t proto;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ proto = yang_dnode_get_enum(dnode, "./protocol");
+ eigrp_redistribute_unset(eigrp, proto);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/route-map
+ */
+static int
+eigrpd_instance_redistribute_route_map_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+eigrpd_instance_redistribute_route_map_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/bandwidth
+ */
+static int eigrpd_instance_redistribute_metrics_bandwidth_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp_metrics metrics;
+ struct eigrp *eigrp;
+ uint32_t proto;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ proto = yang_dnode_get_enum(dnode, "../../protocol");
+ redistribute_get_metrics(dnode, &metrics);
+ eigrp_redistribute_set(eigrp, proto, metrics);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int eigrpd_instance_redistribute_metrics_bandwidth_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ struct eigrp_metrics metrics;
+ struct eigrp *eigrp;
+ uint32_t proto;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eigrp = nb_running_get_entry(dnode, NULL, true);
+ proto = yang_dnode_get_enum(dnode, "../../protocol");
+ redistribute_get_metrics(dnode, &metrics);
+ eigrp_redistribute_set(eigrp, proto, metrics);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/delay
+ */
+static int
+eigrpd_instance_redistribute_metrics_delay_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_modify(event,
+ dnode,
+ resource);
+}
+
+static int
+eigrpd_instance_redistribute_metrics_delay_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_destroy(event,
+ dnode);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/reliability
+ */
+static int eigrpd_instance_redistribute_metrics_reliability_modify(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_modify(event,
+ dnode,
+ resource);
+}
+
+static int eigrpd_instance_redistribute_metrics_reliability_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_destroy(event,
+ dnode);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/load
+ */
+static int
+eigrpd_instance_redistribute_metrics_load_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_modify(event,
+ dnode,
+ resource);
+}
+
+static int
+eigrpd_instance_redistribute_metrics_load_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_destroy(event,
+ dnode);
+}
+
+/*
+ * XPath: /frr-eigrpd:eigrpd/instance/redistribute/metrics/mtu
+ */
+static int
+eigrpd_instance_redistribute_metrics_mtu_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_modify(event,
+ dnode,
+ resource);
+}
+
+static int
+eigrpd_instance_redistribute_metrics_mtu_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ return eigrpd_instance_redistribute_metrics_bandwidth_destroy(event,
+ dnode);
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/delay
+ */
+static int lib_interface_eigrp_delay_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp_interface *ei;
+ struct interface *ifp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ ifp = nb_running_get_entry(dnode, NULL, false);
+ if (ifp == NULL) {
+ /*
+ * XXX: we can't verify if the interface exists
+ * and is active until EIGRP is up.
+ */
+ break;
+ }
+
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+
+ ei->params.delay = yang_dnode_get_uint32(dnode, NULL);
+ eigrp_if_reset(ifp);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/bandwidth
+ */
+static int lib_interface_eigrp_bandwidth_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct interface *ifp;
+ struct eigrp_interface *ei;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ ifp = nb_running_get_entry(dnode, NULL, false);
+ if (ifp == NULL) {
+ /*
+ * XXX: we can't verify if the interface exists
+ * and is active until EIGRP is up.
+ */
+ break;
+ }
+
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+
+ ei->params.bandwidth = yang_dnode_get_uint32(dnode, NULL);
+ eigrp_if_reset(ifp);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/hello-interval
+ */
+static int
+lib_interface_eigrp_hello_interval_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct interface *ifp;
+ struct eigrp_interface *ei;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ ifp = nb_running_get_entry(dnode, NULL, false);
+ if (ifp == NULL) {
+ /*
+ * XXX: we can't verify if the interface exists
+ * and is active until EIGRP is up.
+ */
+ break;
+ }
+
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+
+ ei->params.v_hello = yang_dnode_get_uint16(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/hold-time
+ */
+static int lib_interface_eigrp_hold_time_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct interface *ifp;
+ struct eigrp_interface *ei;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ ifp = nb_running_get_entry(dnode, NULL, false);
+ if (ifp == NULL) {
+ /*
+ * XXX: we can't verify if the interface exists
+ * and is active until EIGRP is up.
+ */
+ break;
+ }
+
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ ei = ifp->info;
+ if (ei == NULL)
+ return NB_ERR_INCONSISTENCY;
+
+ ei->params.v_wait = yang_dnode_get_uint16(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/split-horizon
+ */
+static int
+lib_interface_eigrp_split_horizon_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance
+ */
+static int lib_interface_eigrp_instance_create(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp_interface *eif;
+ struct interface *ifp;
+ struct eigrp *eigrp;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ ifp = nb_running_get_entry(dnode, NULL, false);
+ if (ifp == NULL) {
+ /*
+ * XXX: we can't verify if the interface exists
+ * and is active until EIGRP is up.
+ */
+ break;
+ }
+
+ eigrp = eigrp_get(yang_dnode_get_string(dnode, "./asn"));
+ eif = eigrp_interface_lookup(eigrp, ifp->name);
+ if (eif == NULL)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ ifp = nb_running_get_entry(dnode, NULL, true);
+ eigrp = eigrp_get(yang_dnode_get_string(dnode, "./asn"));
+ eif = eigrp_interface_lookup(eigrp, ifp->name);
+ if (eif == NULL)
+ return NB_ERR_INCONSISTENCY;
+
+ nb_running_set_entry(dnode, eif);
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int lib_interface_eigrp_instance_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ nb_running_unset_entry(dnode);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath:
+ * /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/summarize-addresses
+ */
+static int lib_interface_eigrp_instance_summarize_addresses_create(
+ enum nb_event event, const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int lib_interface_eigrp_instance_summarize_addresses_destroy(
+ enum nb_event event, const struct lyd_node *dnode)
+{
+ switch (event) {
+ case NB_EV_VALIDATE:
+ /* TODO: Not implemented. */
+ return NB_ERR_INCONSISTENCY;
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ case NB_EV_APPLY:
+ /* NOTHING */
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/authentication
+ */
+static int
+lib_interface_eigrp_instance_authentication_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp_interface *eif;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eif = nb_running_get_entry(dnode, NULL, true);
+ eif->params.auth_type = yang_dnode_get_enum(dnode, NULL);
+ break;
+ }
+
+ return NB_OK;
+}
+
+/*
+ * XPath: /frr-interface:lib/interface/frr-eigrpd:eigrp/instance/keychain
+ */
+static int
+lib_interface_eigrp_instance_keychain_modify(enum nb_event event,
+ const struct lyd_node *dnode,
+ union nb_resource *resource)
+{
+ struct eigrp_interface *eif;
+ struct keychain *keychain;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ keychain = keychain_lookup(yang_dnode_get_string(dnode, NULL));
+ if (keychain == NULL)
+ return NB_ERR_INCONSISTENCY;
+ break;
+ case NB_EV_PREPARE:
+ resource->ptr = strdup(yang_dnode_get_string(dnode, NULL));
+ if (resource->ptr == NULL)
+ return NB_ERR_RESOURCE;
+ break;
+ case NB_EV_ABORT:
+ free(resource->ptr);
+ resource->ptr = NULL;
+ break;
+ case NB_EV_APPLY:
+ eif = nb_running_get_entry(dnode, NULL, true);
+ if (eif->params.auth_keychain)
+ free(eif->params.auth_keychain);
+
+ eif->params.auth_keychain = resource->ptr;
+ break;
+ }
+
+ return NB_OK;
+}
+
+static int
+lib_interface_eigrp_instance_keychain_destroy(enum nb_event event,
+ const struct lyd_node *dnode)
+{
+ struct eigrp_interface *eif;
+
+ switch (event) {
+ case NB_EV_VALIDATE:
+ case NB_EV_PREPARE:
+ case NB_EV_ABORT:
+ /* NOTHING */
+ break;
+ case NB_EV_APPLY:
+ eif = nb_running_get_entry(dnode, NULL, true);
+ if (eif->params.auth_keychain)
+ free(eif->params.auth_keychain);
+
+ eif->params.auth_keychain = NULL;
+ break;
+ }
+
+ return NB_OK;
+}
+
+/* clang-format off */
+const struct frr_yang_module_info frr_eigrpd_info = {
+ .name = "frr-eigrpd",
+ .nodes = {
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance",
+ .cbs = {
+ .create = eigrpd_instance_create,
+ .destroy = eigrpd_instance_destroy,
+ .cli_show = eigrp_cli_show_header,
+ .cli_show_end = eigrp_cli_show_end_header,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/router-id",
+ .cbs = {
+ .modify = eigrpd_instance_router_id_modify,
+ .destroy = eigrpd_instance_router_id_destroy,
+ .cli_show = eigrp_cli_show_router_id,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/passive-interface",
+ .cbs = {
+ .create = eigrpd_instance_passive_interface_create,
+ .destroy = eigrpd_instance_passive_interface_destroy,
+ .cli_show = eigrp_cli_show_passive_interface,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/active-time",
+ .cbs = {
+ .modify = eigrpd_instance_active_time_modify,
+ .cli_show = eigrp_cli_show_active_time,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/variance",
+ .cbs = {
+ .modify = eigrpd_instance_variance_modify,
+ .destroy = eigrpd_instance_variance_destroy,
+ .cli_show = eigrp_cli_show_variance,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/maximum-paths",
+ .cbs = {
+ .modify = eigrpd_instance_maximum_paths_modify,
+ .destroy = eigrpd_instance_maximum_paths_destroy,
+ .cli_show = eigrp_cli_show_maximum_paths,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights",
+ .cbs = {
+ .cli_show = eigrp_cli_show_metrics,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K1",
+ .cbs = {
+ .modify = eigrpd_instance_metric_weights_K1_modify,
+ .destroy = eigrpd_instance_metric_weights_K1_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K2",
+ .cbs = {
+ .modify = eigrpd_instance_metric_weights_K2_modify,
+ .destroy = eigrpd_instance_metric_weights_K2_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K3",
+ .cbs = {
+ .modify = eigrpd_instance_metric_weights_K3_modify,
+ .destroy = eigrpd_instance_metric_weights_K3_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K4",
+ .cbs = {
+ .modify = eigrpd_instance_metric_weights_K4_modify,
+ .destroy = eigrpd_instance_metric_weights_K4_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K5",
+ .cbs = {
+ .modify = eigrpd_instance_metric_weights_K5_modify,
+ .destroy = eigrpd_instance_metric_weights_K5_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/metric-weights/K6",
+ .cbs = {
+ .modify = eigrpd_instance_metric_weights_K6_modify,
+ .destroy = eigrpd_instance_metric_weights_K6_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/network",
+ .cbs = {
+ .create = eigrpd_instance_network_create,
+ .destroy = eigrpd_instance_network_destroy,
+ .cli_show = eigrp_cli_show_network,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/neighbor",
+ .cbs = {
+ .create = eigrpd_instance_neighbor_create,
+ .destroy = eigrpd_instance_neighbor_destroy,
+ .cli_show = eigrp_cli_show_neighbor,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/redistribute",
+ .cbs = {
+ .create = eigrpd_instance_redistribute_create,
+ .destroy = eigrpd_instance_redistribute_destroy,
+ .cli_show = eigrp_cli_show_redistribute,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/route-map",
+ .cbs = {
+ .modify = eigrpd_instance_redistribute_route_map_modify,
+ .destroy = eigrpd_instance_redistribute_route_map_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/bandwidth",
+ .cbs = {
+ .modify = eigrpd_instance_redistribute_metrics_bandwidth_modify,
+ .destroy = eigrpd_instance_redistribute_metrics_bandwidth_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/delay",
+ .cbs = {
+ .modify = eigrpd_instance_redistribute_metrics_delay_modify,
+ .destroy = eigrpd_instance_redistribute_metrics_delay_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/reliability",
+ .cbs = {
+ .modify = eigrpd_instance_redistribute_metrics_reliability_modify,
+ .destroy = eigrpd_instance_redistribute_metrics_reliability_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/load",
+ .cbs = {
+ .modify = eigrpd_instance_redistribute_metrics_load_modify,
+ .destroy = eigrpd_instance_redistribute_metrics_load_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-eigrpd:eigrpd/instance/redistribute/metrics/mtu",
+ .cbs = {
+ .modify = eigrpd_instance_redistribute_metrics_mtu_modify,
+ .destroy = eigrpd_instance_redistribute_metrics_mtu_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/delay",
+ .cbs = {
+ .modify = lib_interface_eigrp_delay_modify,
+ .cli_show = eigrp_cli_show_delay,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/bandwidth",
+ .cbs = {
+ .modify = lib_interface_eigrp_bandwidth_modify,
+ .cli_show = eigrp_cli_show_bandwidth,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/hello-interval",
+ .cbs = {
+ .modify = lib_interface_eigrp_hello_interval_modify,
+ .cli_show = eigrp_cli_show_hello_interval,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/hold-time",
+ .cbs = {
+ .modify = lib_interface_eigrp_hold_time_modify,
+ .cli_show = eigrp_cli_show_hold_time,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/split-horizon",
+ .cbs = {
+ .modify = lib_interface_eigrp_split_horizon_modify,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance",
+ .cbs = {
+ .create = lib_interface_eigrp_instance_create,
+ .destroy = lib_interface_eigrp_instance_destroy,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance/summarize-addresses",
+ .cbs = {
+ .create = lib_interface_eigrp_instance_summarize_addresses_create,
+ .destroy = lib_interface_eigrp_instance_summarize_addresses_destroy,
+ .cli_show = eigrp_cli_show_summarize_address,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance/authentication",
+ .cbs = {
+ .modify = lib_interface_eigrp_instance_authentication_modify,
+ .cli_show = eigrp_cli_show_authentication,
+ }
+ },
+ {
+ .xpath = "/frr-interface:lib/interface/frr-eigrpd:eigrp/instance/keychain",
+ .cbs = {
+ .modify = lib_interface_eigrp_instance_keychain_modify,
+ .destroy = lib_interface_eigrp_instance_keychain_destroy,
+ .cli_show = eigrp_cli_show_keychain,
+ }
+ },
+ {
+ .xpath = NULL,
+ },
+ }
+};
#include "eigrpd/eigrp_vty_clippy.c"
#endif
-static int config_write_network(struct vty *vty, struct eigrp *eigrp)
-{
- struct route_node *rn;
- int i;
-
- /* `network area' print. */
- for (rn = route_top(eigrp->networks); rn; rn = route_next(rn))
- if (rn->info) {
- /* Network print. */
- vty_out(vty, " network %s/%d \n",
- inet_ntoa(rn->p.u.prefix4), rn->p.prefixlen);
- }
-
- if (eigrp->max_paths != EIGRP_MAX_PATHS_DEFAULT)
- vty_out(vty, " maximum-paths %d\n", eigrp->max_paths);
-
- if (eigrp->variance != EIGRP_VARIANCE_DEFAULT)
- vty_out(vty, " variance %d\n", eigrp->variance);
-
- for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
- if (i != zclient->redist_default
- && vrf_bitmap_check(zclient->redist[AFI_IP][i],
- VRF_DEFAULT))
- vty_out(vty, " redistribute %s\n",
- zebra_route_string(i));
-
- /*Separate EIGRP configuration from the rest of the config*/
- vty_out(vty, "!\n");
-
- return 0;
-}
-
-static int config_write_interfaces(struct vty *vty, struct eigrp *eigrp)
-{
- struct eigrp_interface *ei;
- struct listnode *node;
-
- for (ALL_LIST_ELEMENTS_RO(eigrp->eiflist, node, ei)) {
- vty_frame(vty, "interface %s\n", ei->ifp->name);
-
- if (ei->params.auth_type == EIGRP_AUTH_TYPE_MD5) {
- vty_out(vty, " ip authentication mode eigrp %d md5\n",
- eigrp->AS);
- }
-
- if (ei->params.auth_type == EIGRP_AUTH_TYPE_SHA256) {
- vty_out(vty,
- " ip authentication mode eigrp %d hmac-sha-256\n",
- eigrp->AS);
- }
-
- if (ei->params.auth_keychain) {
- vty_out(vty,
- " ip authentication key-chain eigrp %d %s\n",
- eigrp->AS, ei->params.auth_keychain);
- }
-
- if (ei->params.v_hello != EIGRP_HELLO_INTERVAL_DEFAULT) {
- vty_out(vty, " ip hello-interval eigrp %d\n",
- ei->params.v_hello);
- }
-
- if (ei->params.v_wait != EIGRP_HOLD_INTERVAL_DEFAULT) {
- vty_out(vty, " ip hold-time eigrp %d\n",
- ei->params.v_wait);
- }
-
- /*Separate this EIGRP interface configuration from the others*/
- vty_endframe(vty, "!\n");
- }
-
- return 0;
-}
-
-static int eigrp_write_interface(struct vty *vty)
-{
- struct vrf *vrf = vrf_lookup_by_id(VRF_DEFAULT);
- struct interface *ifp;
- struct eigrp_interface *ei;
-
- FOR_ALL_INTERFACES (vrf, ifp) {
- ei = ifp->info;
- if (!ei)
- continue;
-
- vty_frame(vty, "interface %s\n", ifp->name);
-
- if (ifp->desc)
- vty_out(vty, " description %s\n", ifp->desc);
-
- if (ei->params.bandwidth != EIGRP_BANDWIDTH_DEFAULT)
- vty_out(vty, " bandwidth %u\n", ei->params.bandwidth);
- if (ei->params.delay != EIGRP_DELAY_DEFAULT)
- vty_out(vty, " delay %u\n", ei->params.delay);
- if (ei->params.v_hello != EIGRP_HELLO_INTERVAL_DEFAULT)
- vty_out(vty, " ip hello-interval eigrp %u\n",
- ei->params.v_hello);
- if (ei->params.v_wait != EIGRP_HOLD_INTERVAL_DEFAULT)
- vty_out(vty, " ip hold-time eigrp %u\n",
- ei->params.v_wait);
-
- vty_endframe(vty, "!\n");
- }
-
- return 0;
-}
-
-/**
- * Writes distribute lists to config
- */
-static int config_write_eigrp_distribute(struct vty *vty, struct eigrp *eigrp)
-{
- int write = 0;
-
- /* Distribute configuration. */
- write += config_write_distribute(vty, eigrp->distribute_ctx);
-
- return write;
-}
-
-/**
- * Writes 'router eigrp' section to config
- */
-static int config_write_eigrp_router(struct vty *vty, struct eigrp *eigrp)
-{
- int write = 0;
-
- /* `router eigrp' print. */
- vty_out(vty, "router eigrp %d\n", eigrp->AS);
-
- write++;
-
- /* Router ID print. */
- if (eigrp->router_id_static.s_addr != 0) {
- vty_out(vty, " eigrp router-id %s\n",
- inet_ntoa(eigrp->router_id_static));
- }
-
- /* Network area print. */
- config_write_network(vty, eigrp);
-
- /* Distribute-list and default-information print. */
- config_write_eigrp_distribute(vty, eigrp);
-
- /*Separate EIGRP configuration from the rest of the config*/
- vty_out(vty, "!\n");
-
- return write;
-}
-
-DEFUN_NOSH (router_eigrp,
- router_eigrp_cmd,
- "router eigrp (1-65535)",
- "Enable a routing process\n"
- "Start EIGRP configuration\n"
- "AS Number to use\n")
-{
- struct eigrp *eigrp = eigrp_get(argv[2]->arg);
- VTY_PUSH_CONTEXT(EIGRP_NODE, eigrp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_router_eigrp,
- no_router_eigrp_cmd,
- "no router eigrp (1-65535)",
- NO_STR
- "Routing process\n"
- "EIGRP configuration\n"
- "AS number to use\n")
-{
- vty->node = CONFIG_NODE;
-
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (eigrp->AS != atoi(argv[3]->arg)) {
- vty_out(vty, "%% Attempting to deconfigure non-existent AS\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- eigrp_finish_final(eigrp);
-
- return CMD_SUCCESS;
-}
-
-DEFPY (eigrp_router_id,
- eigrp_router_id_cmd,
- "eigrp router-id A.B.C.D$addr",
- "EIGRP specific commands\n"
- "Router ID for this EIGRP process\n"
- "EIGRP Router-ID in IP address format\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
-
- eigrp->router_id_static = addr;
-
- return CMD_SUCCESS;
-}
-
-DEFPY (no_eigrp_router_id,
- no_eigrp_router_id_cmd,
- "no eigrp router-id [A.B.C.D$addr]",
- NO_STR
- "EIGRP specific commands\n"
- "Router ID for this EIGRP process\n"
- "EIGRP Router-ID in IP address format\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
-
- eigrp->router_id_static.s_addr = 0;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_passive_interface,
- eigrp_passive_interface_cmd,
- "passive-interface IFNAME",
- "Suppress routing updates on an interface\n"
- "Interface to suppress on\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
- struct eigrp_interface *ei;
- struct listnode *node;
- char *ifname = argv[1]->arg;
-
- for (ALL_LIST_ELEMENTS_RO(eigrp->eiflist, node, ei)) {
- if (strcmp(ifname, ei->ifp->name) == 0) {
- ei->params.passive_interface = EIGRP_IF_PASSIVE;
- return CMD_SUCCESS;
- }
- }
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_passive_interface,
- no_eigrp_passive_interface_cmd,
- "no passive-interface IFNAME",
- NO_STR
- "Suppress routing updates on an interface\n"
- "Interface to suppress on\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
- struct eigrp_interface *ei;
- struct listnode *node;
- char *ifname = argv[2]->arg;
-
- for (ALL_LIST_ELEMENTS_RO(eigrp->eiflist, node, ei)) {
- if (strcmp(ifname, ei->ifp->name) == 0) {
- ei->params.passive_interface = EIGRP_IF_ACTIVE;
- return CMD_SUCCESS;
- }
- }
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_timers_active,
- eigrp_timers_active_cmd,
- "timers active-time <(1-65535)|disabled>",
- "Adjust routing timers\n"
- "Time limit for active state\n"
- "Active state time limit in seconds\n"
- "Disable time limit for active state\n")
-{
- // struct eigrp *eigrp = vty->index;
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_timers_active,
- no_eigrp_timers_active_cmd,
- "no timers active-time <(1-65535)|disabled>",
- NO_STR
- "Adjust routing timers\n"
- "Time limit for active state\n"
- "Active state time limit in seconds\n"
- "Disable time limit for active state\n")
-{
- // struct eigrp *eigrp = vty->index;
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-
-DEFUN (eigrp_metric_weights,
- eigrp_metric_weights_cmd,
- "metric weights (0-255) (0-255) (0-255) (0-255) (0-255) ",
- "Modify metrics and parameters for advertisement\n"
- "Modify metric coefficients\n"
- "K1\n"
- "K2\n"
- "K3\n"
- "K4\n"
- "K5\n")
-{
- // struct eigrp *eigrp = vty->index;
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_metric_weights,
- no_eigrp_metric_weights_cmd,
- "no metric weights (0-255) (0-255) (0-255) (0-255) (0-255)",
- NO_STR
- "Modify metrics and parameters for advertisement\n"
- "Modify metric coefficients\n"
- "K1\n"
- "K2\n"
- "K3\n"
- "K4\n"
- "K5\n")
-{
- // struct eigrp *eigrp = vty->index;
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-
-DEFUN (eigrp_network,
- eigrp_network_cmd,
- "network A.B.C.D/M",
- "Enable routing on an IP network\n"
- "EIGRP network prefix\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
- struct prefix p;
- int ret;
-
- (void)str2prefix(argv[1]->arg, &p);
-
- ret = eigrp_network_set(eigrp, &p);
-
- if (ret == 0) {
- vty_out(vty, "There is already same network statement.\n");
- return CMD_WARNING;
- }
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_network,
- no_eigrp_network_cmd,
- "no network A.B.C.D/M",
- NO_STR
- "Disable routing on an IP network\n"
- "EIGRP network prefix\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
- struct prefix p;
- int ret;
-
- (void)str2prefix(argv[2]->arg, &p);
-
- ret = eigrp_network_unset(eigrp, &p);
-
- if (ret == 0) {
- vty_out(vty, "Can't find specified network configuration.\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_neighbor,
- eigrp_neighbor_cmd,
- "neighbor A.B.C.D",
- "Specify a neighbor router\n"
- "Neighbor address\n")
-{
- // struct eigrp *eigrp = vty->index;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_neighbor,
- no_eigrp_neighbor_cmd,
- "no neighbor A.B.C.D",
- NO_STR
- "Specify a neighbor router\n"
- "Neighbor address\n")
-{
- // struct eigrp *eigrp = vty->index;
-
- return CMD_SUCCESS;
-}
-
static void eigrp_vty_display_prefix_entry(struct vty *vty,
struct eigrp *eigrp,
struct eigrp_prefix_entry *pe,
return CMD_SUCCESS;
}
-DEFUN (eigrp_if_delay,
- eigrp_if_delay_cmd,
- "delay (1-16777215)",
- "Specify interface throughput delay\n"
- "Throughput delay (tens of microseconds)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
- uint32_t delay;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
-
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
- delay = atoi(argv[1]->arg);
-
- ei->params.delay = delay;
- eigrp_if_reset(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_if_delay,
- no_eigrp_if_delay_cmd,
- "no delay (1-16777215)",
- NO_STR
- "Specify interface throughput delay\n"
- "Throughput delay (tens of microseconds)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
-
- return CMD_SUCCESS;
- }
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- ei->params.delay = EIGRP_DELAY_DEFAULT;
- eigrp_if_reset(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFPY (eigrp_if_bandwidth,
- eigrp_if_bandwidth_cmd,
- "eigrp bandwidth (1-10000000)$bw",
- "EIGRP specific commands\n"
- "Set bandwidth informational parameter\n"
- "Bandwidth in kilobits\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- ei->params.bandwidth = bw;
- eigrp_if_reset(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_if_bandwidth,
- no_eigrp_if_bandwidth_cmd,
- "no eigrp bandwidth [(1-10000000)]",
- NO_STR
- "EIGRP specific commands\n"
- "Set bandwidth informational parameter\n"
- "Bandwidth in kilobits\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- ei->params.bandwidth = EIGRP_BANDWIDTH_DEFAULT;
- eigrp_if_reset(ifp);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_if_ip_hellointerval,
- eigrp_if_ip_hellointerval_cmd,
- "ip hello-interval eigrp (1-65535)",
- "Interface Internet Protocol config commands\n"
- "Configures EIGRP hello interval\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "Seconds between hello transmissions\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- uint32_t hello;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- hello = atoi(argv[3]->arg);
-
- ei->params.v_hello = hello;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_if_ip_hellointerval,
- no_eigrp_if_ip_hellointerval_cmd,
- "no ip hello-interval eigrp [(1-65535)]",
- NO_STR
- "Interface Internet Protocol config commands\n"
- "Configures EIGRP hello interval\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "Seconds between hello transmissions\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- ei->params.v_hello = EIGRP_HELLO_INTERVAL_DEFAULT;
-
- THREAD_TIMER_OFF(ei->t_hello);
- thread_add_timer(master, eigrp_hello_timer, ei, 1, &ei->t_hello);
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_if_ip_holdinterval,
- eigrp_if_ip_holdinterval_cmd,
- "ip hold-time eigrp (1-65535)",
- "Interface Internet Protocol config commands\n"
- "Configures EIGRP IPv4 hold time\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "Seconds before neighbor is considered down\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- uint32_t hold;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- hold = atoi(argv[3]->arg);
-
- ei->params.v_wait = hold;
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_ip_summary_address,
- eigrp_ip_summary_address_cmd,
- "ip summary-address eigrp (1-65535) A.B.C.D/M",
- "Interface Internet Protocol config commands\n"
- "Perform address summarization\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "AS number\n"
- "Summary <network>/<length>, e.g. 192.168.0.0/16\n")
-{
- // VTY_DECLVAR_CONTEXT(interface, ifp);
- // uint32_t AS;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- // AS = atoi (argv[3]->arg);
-
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_ip_summary_address,
- no_eigrp_ip_summary_address_cmd,
- "no ip summary-address eigrp (1-65535) A.B.C.D/M",
- NO_STR
- "Interface Internet Protocol config commands\n"
- "Perform address summarization\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "AS number\n"
- "Summary <network>/<length>, e.g. 192.168.0.0/16\n")
-{
- // VTY_DECLVAR_CONTEXT(interface, ifp);
- // uint32_t AS;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- // AS = atoi (argv[4]->arg);
-
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_if_ip_holdinterval,
- no_eigrp_if_ip_holdinterval_cmd,
- "no ip hold-time eigrp",
- NO_STR
- "Interface Internet Protocol config commands\n"
- "Configures EIGRP hello interval\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- ei->params.v_wait = EIGRP_HOLD_INTERVAL_DEFAULT;
-
- return CMD_SUCCESS;
-}
-
-static int str2auth_type(const char *str, struct eigrp_interface *ei)
-{
- /* Sanity check. */
- if (str == NULL)
- return CMD_WARNING_CONFIG_FAILED;
-
- if (strncmp(str, "md5", 3) == 0) {
- ei->params.auth_type = EIGRP_AUTH_TYPE_MD5;
- return CMD_SUCCESS;
- } else if (strncmp(str, "hmac-sha-256", 12) == 0) {
- ei->params.auth_type = EIGRP_AUTH_TYPE_SHA256;
- return CMD_SUCCESS;
- }
-
- return CMD_WARNING_CONFIG_FAILED;
-}
-
-DEFUN (eigrp_authentication_mode,
- eigrp_authentication_mode_cmd,
- "ip authentication mode eigrp (1-65535) <md5|hmac-sha-256>",
- "Interface Internet Protocol config commands\n"
- "Authentication subcommands\n"
- "Mode\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "Autonomous system number\n"
- "Keyed message digest\n"
- "HMAC SHA256 algorithm \n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- // if(strncmp(argv[2], "md5",3))
- // IF_DEF_PARAMS (ifp)->auth_type = EIGRP_AUTH_TYPE_MD5;
- // else if(strncmp(argv[2], "hmac-sha-256",12))
- // IF_DEF_PARAMS (ifp)->auth_type = EIGRP_AUTH_TYPE_SHA256;
-
- return str2auth_type(argv[5]->arg, ei);
-}
-
-DEFUN (no_eigrp_authentication_mode,
- no_eigrp_authentication_mode_cmd,
- "no ip authentication mode eigrp (1-65535) <md5|hmac-sha-256>",
- "Disable\n"
- "Interface Internet Protocol config commands\n"
- "Authentication subcommands\n"
- "Mode\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "Autonomous system number\n"
- "Keyed message digest\n"
- "HMAC SHA256 algorithm \n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, " EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- ei->params.auth_type = EIGRP_AUTH_TYPE_NONE;
-
- return CMD_SUCCESS;
-}
-
-DEFPY (eigrp_authentication_keychain,
- eigrp_authentication_keychain_cmd,
- "[no] ip authentication key-chain eigrp (1-65535)$as WORD$name",
- NO_STR
- "Interface Internet Protocol config commands\n"
- "Authentication subcommands\n"
- "Key-chain\n"
- "Enhanced Interior Gateway Routing Protocol (EIGRP)\n"
- "Autonomous system number\n"
- "Name of key-chain\n")
-{
- VTY_DECLVAR_CONTEXT(interface, ifp);
- struct eigrp_interface *ei = ifp->info;
- struct eigrp *eigrp;
- struct keychain *keychain;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, "EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- if (!ei) {
- vty_out(vty, " EIGRP not configured on this interface\n");
- return CMD_SUCCESS;
- }
-
- if (no) {
- if ((ei->params.auth_keychain != NULL)
- && (strcmp(ei->params.auth_keychain, name) == 0)) {
- free(ei->params.auth_keychain);
- ei->params.auth_keychain = NULL;
- } else
- vty_out(vty,
- "Key chain with specified name not configured on interface\n");
- return CMD_SUCCESS;
- }
-
- keychain = keychain_lookup(name);
- if (keychain != NULL) {
- if (ei->params.auth_keychain) {
- free(ei->params.auth_keychain);
- ei->params.auth_keychain = strdup(keychain->name);
- } else
- ei->params.auth_keychain = strdup(keychain->name);
- } else {
- vty_out(vty,
- "Key chain with specified name not found\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_redistribute_source_metric,
- eigrp_redistribute_source_metric_cmd,
- "redistribute " FRR_REDIST_STR_EIGRPD
- " [metric (1-4294967295) (0-4294967295) (0-255) (1-255) (1-65535)]",
- REDIST_STR
- FRR_REDIST_HELP_STR_EIGRPD
- "Metric for redistributed routes\n"
- "Bandwidth metric in Kbits per second\n"
- "EIGRP delay metric, in 10 microsecond units\n"
- "EIGRP reliability metric where 255 is 100% reliable2 ?\n"
- "EIGRP Effective bandwidth metric (Loading) where 255 is 100% loaded\n"
- "EIGRP MTU of the path\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
- struct eigrp_metrics metrics_from_command = {0};
- int source;
- int idx = 0;
-
- /* Get distribute source. */
- argv_find(argv, argc, "redistribute", &idx);
- source = proto_redistnum(AFI_IP, argv[idx + 1]->text);
- if (source < 0) {
- vty_out(vty, "%% Invalid route type\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Get metrics values */
-
- return eigrp_redistribute_set(eigrp, source, metrics_from_command);
-}
-
-DEFUN (no_eigrp_redistribute_source_metric,
- no_eigrp_redistribute_source_metric_cmd,
- "no redistribute " FRR_REDIST_STR_EIGRPD
- " [metric (1-4294967295) (0-4294967295) (0-255) (1-255) (1-65535)]",
- "Disable\n"
- REDIST_STR
- FRR_REDIST_HELP_STR_EIGRPD
- "Metric for redistributed routes\n"
- "Bandwidth metric in Kbits per second\n"
- "EIGRP delay metric, in 10 microsecond units\n"
- "EIGRP reliability metric where 255 is 100% reliable2 ?\n"
- "EIGRP Effective bandwidth metric (Loading) where 255 is 100% loaded\n"
- "EIGRP MTU of the path\n")
-{
- VTY_DECLVAR_CONTEXT(eigrp, eigrp);
- int source;
- int idx = 0;
-
- /* Get distribute source. */
- argv_find(argv, argc, "redistribute", &idx);
- source = proto_redistnum(AFI_IP, argv[idx + 1]->text);
- if (source < 0) {
- vty_out(vty, "%% Invalid route type\n");
- return CMD_WARNING_CONFIG_FAILED;
- }
-
- /* Get metrics values */
-
- return eigrp_redistribute_unset(eigrp, source);
-}
-
-DEFUN (eigrp_variance,
- eigrp_variance_cmd,
- "variance (1-128)",
- "Control load balancing variance\n"
- "Metric variance multiplier\n")
-{
- struct eigrp *eigrp;
- uint8_t variance;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, "EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
- variance = atoi(argv[1]->arg);
-
- eigrp->variance = variance;
-
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_variance,
- no_eigrp_variance_cmd,
- "no variance (1-128)",
- "Disable\n"
- "Control load balancing variance\n"
- "Metric variance multiplier\n")
-{
- struct eigrp *eigrp;
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, "EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- eigrp->variance = EIGRP_VARIANCE_DEFAULT;
-
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (eigrp_maximum_paths,
- eigrp_maximum_paths_cmd,
- "maximum-paths (1-32)",
- "Forward packets over multiple paths\n"
- "Number of paths\n")
-{
- struct eigrp *eigrp;
- uint8_t max;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, "EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- max = atoi(argv[1]->arg);
-
- eigrp->max_paths = max;
-
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
-DEFUN (no_eigrp_maximum_paths,
- no_eigrp_maximum_paths_cmd,
- "no maximum-paths (1-32)",
- NO_STR
- "Forward packets over multiple paths\n"
- "Number of paths\n")
-{
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp == NULL) {
- vty_out(vty, "EIGRP Routing Process not enabled\n");
- return CMD_SUCCESS;
- }
-
- eigrp->max_paths = EIGRP_MAX_PATHS_DEFAULT;
-
- /*TODO: */
-
- return CMD_SUCCESS;
-}
-
/*
* Execute hard restart for all neighbors
*/
return CMD_SUCCESS;
}
-static struct cmd_node eigrp_node = {EIGRP_NODE, "%s(config-router)# ", 1};
-
-/* Save EIGRP configuration */
-static int eigrp_config_write(struct vty *vty)
-{
- struct eigrp *eigrp;
-
- eigrp = eigrp_lookup();
- if (eigrp != NULL) {
- /* Writes 'router eigrp' section to config */
- config_write_eigrp_router(vty, eigrp);
-
- /* Interface config print */
- config_write_interfaces(vty, eigrp);
- //
- // /* static neighbor print. */
- // config_write_eigrp_nbr_nbma (vty, eigrp);
- //
- // /* Virtual-Link print. */
- // config_write_virtual_link (vty, eigrp);
- //
- // /* Default metric configuration. */
- // config_write_eigrp_default_metric (vty, eigrp);
- //
- // /* Distribute-list and default-information print. */
- // config_write_eigrp_distribute (vty, eigrp);
- //
- // /* Distance configuration. */
- // config_write_eigrp_distance (vty, eigrp)
- }
-
- return 0;
-}
-
void eigrp_vty_show_init(void)
{
install_element(VIEW_NODE, &show_ip_eigrp_interfaces_cmd);
install_element(VIEW_NODE, &show_ip_eigrp_topology_all_cmd);
}
-/* eigrpd's interface node. */
-static struct cmd_node eigrp_interface_node = {INTERFACE_NODE,
- "%s(config-if)# ", 1};
-
-void eigrp_vty_if_init(void)
-{
- install_node(&eigrp_interface_node, eigrp_write_interface);
- if_cmd_init();
-
- /* Delay and bandwidth configuration commands*/
- install_element(INTERFACE_NODE, &eigrp_if_delay_cmd);
- install_element(INTERFACE_NODE, &no_eigrp_if_delay_cmd);
- install_element(INTERFACE_NODE, &eigrp_if_bandwidth_cmd);
- install_element(INTERFACE_NODE, &no_eigrp_if_bandwidth_cmd);
-
- /*Hello-interval and hold-time interval configuration commands*/
- install_element(INTERFACE_NODE, &eigrp_if_ip_holdinterval_cmd);
- install_element(INTERFACE_NODE, &no_eigrp_if_ip_holdinterval_cmd);
- install_element(INTERFACE_NODE, &eigrp_if_ip_hellointerval_cmd);
- install_element(INTERFACE_NODE, &no_eigrp_if_ip_hellointerval_cmd);
-
- /* "Authentication configuration commands */
- install_element(INTERFACE_NODE, &eigrp_authentication_mode_cmd);
- install_element(INTERFACE_NODE, &no_eigrp_authentication_mode_cmd);
- install_element(INTERFACE_NODE, &eigrp_authentication_keychain_cmd);
-
- /*EIGRP Summarization commands*/
- install_element(INTERFACE_NODE, &eigrp_ip_summary_address_cmd);
- install_element(INTERFACE_NODE, &no_eigrp_ip_summary_address_cmd);
-}
-
-static void eigrp_vty_zebra_init(void)
-{
- install_element(EIGRP_NODE, &eigrp_redistribute_source_metric_cmd);
- install_element(EIGRP_NODE, &no_eigrp_redistribute_source_metric_cmd);
-}
-
/* Install EIGRP related vty commands. */
void eigrp_vty_init(void)
{
- install_node(&eigrp_node, eigrp_config_write);
-
- install_default(EIGRP_NODE);
-
- install_element(CONFIG_NODE, &router_eigrp_cmd);
- install_element(CONFIG_NODE, &no_router_eigrp_cmd);
- install_element(EIGRP_NODE, &eigrp_network_cmd);
- install_element(EIGRP_NODE, &no_eigrp_network_cmd);
- install_element(EIGRP_NODE, &eigrp_variance_cmd);
- install_element(EIGRP_NODE, &no_eigrp_variance_cmd);
- install_element(EIGRP_NODE, &eigrp_router_id_cmd);
- install_element(EIGRP_NODE, &no_eigrp_router_id_cmd);
- install_element(EIGRP_NODE, &eigrp_passive_interface_cmd);
- install_element(EIGRP_NODE, &no_eigrp_passive_interface_cmd);
- install_element(EIGRP_NODE, &eigrp_timers_active_cmd);
- install_element(EIGRP_NODE, &no_eigrp_timers_active_cmd);
- install_element(EIGRP_NODE, &eigrp_metric_weights_cmd);
- install_element(EIGRP_NODE, &no_eigrp_metric_weights_cmd);
- install_element(EIGRP_NODE, &eigrp_maximum_paths_cmd);
- install_element(EIGRP_NODE, &no_eigrp_maximum_paths_cmd);
- install_element(EIGRP_NODE, &eigrp_neighbor_cmd);
- install_element(EIGRP_NODE, &no_eigrp_neighbor_cmd);
-
/* commands for manual hard restart */
install_element(ENABLE_NODE, &clear_ip_eigrp_neighbors_cmd);
install_element(ENABLE_NODE, &clear_ip_eigrp_neighbors_int_cmd);
install_element(ENABLE_NODE, &clear_ip_eigrp_neighbors_soft_cmd);
install_element(ENABLE_NODE, &clear_ip_eigrp_neighbors_int_soft_cmd);
install_element(ENABLE_NODE, &clear_ip_eigrp_neighbors_IP_soft_cmd);
-
- eigrp_vty_zebra_init();
}
/* Prototypes. */
extern void eigrp_vty_init(void);
extern void eigrp_vty_show_init(void);
-extern void eigrp_vty_if_init(void);
#endif /* _Quagga_EIGRP_VTY_H_ */
extern struct eigrp *eigrp_lookup(void);
extern void eigrp_router_id_update(struct eigrp *);
+/* eigrp_cli.c */
+extern void eigrp_cli_show_header(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_end_header(struct vty *vty, struct lyd_node *dnode);
+extern void eigrp_cli_show_router_id(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_passive_interface(struct vty *vty,
+ struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_active_time(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_variance(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_maximum_paths(struct vty *vty,
+ struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_metrics(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_network(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_neighbor(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_redistribute(struct vty *vty,
+ struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_delay(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_bandwidth(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_hello_interval(struct vty *vty,
+ struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_hold_time(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_summarize_address(struct vty *vty,
+ struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_authentication(struct vty *vty,
+ struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_show_keychain(struct vty *vty, struct lyd_node *dnode,
+ bool show_defaults);
+extern void eigrp_cli_init(void);
+
+/* eigrp_northbound.c */
+extern const struct frr_yang_module_info frr_eigrpd_info;
+
#endif /* _ZEBRA_EIGRPD_H */
sbin_PROGRAMS += eigrpd/eigrpd
dist_examples_DATA += eigrpd/eigrpd.conf.sample
vtysh_scan += \
+ $(top_srcdir)/eigrpd/eigrp_cli.c \
$(top_srcdir)/eigrpd/eigrp_dump.c \
$(top_srcdir)/eigrpd/eigrp_vty.c \
# end
endif
eigrpd_libeigrp_a_SOURCES = \
+ eigrpd/eigrp_cli.c \
eigrpd/eigrp_dump.c \
eigrpd/eigrp_errors.c \
eigrpd/eigrp_filter.c \
eigrpd/eigrp_memory.c \
eigrpd/eigrp_neighbor.c \
eigrpd/eigrp_network.c \
+ eigrpd/eigrp_northbound.c \
eigrpd/eigrp_packet.c \
eigrpd/eigrp_query.c \
eigrpd/eigrp_reply.c \
eigrpd/eigrp_vty_clippy.c: $(CLIPPY_DEPS)
eigrpd/eigrp_vty.$(OBJEXT): eigrpd/eigrp_vty_clippy.c
+eigrpd/eigrp_cli_clippy.c: $(CLIPPY_DEPS)
+eigrpd/eigrp_cli.$(OBJEXT): eigrpd/eigrp_cli_clippy.c
+
noinst_HEADERS += \
eigrpd/eigrp_const.h \
eigrpd/eigrp_errors.h \
eigrpd/eigrp_zebra.h \
# end
+nodist_eigrpd_eigrpd_SOURCES = \
+ yang/frr-eigrpd.yang.c \
+ # end
+
eigrpd_eigrpd_SOURCES = eigrpd/eigrp_main.c
eigrpd_eigrpd_LDADD = eigrpd/libeigrp.a lib/libfrr.la $(LIBCAP)
dist_yangmodels_DATA += yang/frr-bfdd.yang
endif
+if EIGRPD
+dist_yangmodels_DATA += yang/frr-eigrpd.yang
+endif
+
if RIPD
dist_yangmodels_DATA += yang/frr-ripd.yang
endif