]> git.puffer.fish Git - mirror/frr.git/commitdiff
ripd: retrofit the 'neighbor' command to the new northbound model
authorRenato Westphal <renato@opensourcerouting.org>
Wed, 9 May 2018 04:34:59 +0000 (01:34 -0300)
committerRenato Westphal <renato@opensourcerouting.org>
Sat, 27 Oct 2018 18:16:12 +0000 (16:16 -0200)
Make rip_neighbor_add() and rip_neighbor_delete() return northbound
error codes since their return values are used as the return value of
some northbound callbacks.

These functions shouldn't fail in normal conditions because the northbound
layer guarantees it will never call the 'create' or 'delete' callback
more than once for the same object. Hence any failure in those functions
would indicate an internal inconsistency that needs to be investigated
(by returning NB_ERR the northbound will log a detailed error message
indicating the xpath of the object, the event and the callback where
the error happened).

Signed-off-by: Renato Westphal <renato@opensourcerouting.org>
ripd/rip_cli.c
ripd/rip_cli.h
ripd/rip_interface.c
ripd/rip_northbound.c
ripd/ripd.h

index 4f394bf19e25db8136ab29c2fcb994e7e5d7a318..1d94d02bd7b548bb22d8cae4646d80cc0b0f080e 100644 (file)
@@ -304,6 +304,33 @@ void cli_show_rip_distance_source(struct vty *vty, struct lyd_node *dnode,
        vty_out(vty, "\n");
 }
 
+/*
+ * XPath: /frr-ripd:ripd/instance/explicit-neighbor
+ */
+DEFPY (rip_neighbor,
+       rip_neighbor_cmd,
+       "[no] neighbor A.B.C.D",
+       NO_STR
+       "Specify a neighbor router\n"
+       "Neighbor address\n")
+{
+       struct cli_config_change changes[] = {
+               {
+                       .xpath = "./explicit-neighbor",
+                       .operation = no ? NB_OP_DELETE : NB_OP_CREATE,
+                       .value = neighbor_str,
+               },
+       };
+
+       return nb_cli_cfg_change(vty, NULL, changes, array_size(changes));
+}
+
+void cli_show_rip_neighbor(struct vty *vty, struct lyd_node *dnode,
+                          bool show_defaults)
+{
+       vty_out(vty, " neighbor %s\n", yang_dnode_get_string(dnode, NULL));
+}
+
 void rip_cli_init(void)
 {
        install_element(CONFIG_NODE, &router_rip_cmd);
@@ -317,4 +344,5 @@ void rip_cli_init(void)
        install_element(RIP_NODE, &no_rip_distance_cmd);
        install_element(RIP_NODE, &rip_distance_source_cmd);
        install_element(RIP_NODE, &no_rip_distance_source_cmd);
+       install_element(RIP_NODE, &rip_neighbor_cmd);
 }
index dd810fb70e500d38ae7ca2bb78e7f855a771a999..34cbd646fb9f6b9c24fc4ba3178fc806af456d14 100644 (file)
@@ -35,5 +35,7 @@ extern void cli_show_rip_distance(struct vty *vty, struct lyd_node *dnode,
 extern void cli_show_rip_distance_source(struct vty *vty,
                                         struct lyd_node *dnode,
                                         bool show_defaults);
+extern void cli_show_rip_neighbor(struct vty *vty, struct lyd_node *dnode,
+                                 bool show_defaults);
 
 #endif /* _FRR_RIP_CLI_H_ */
index bbac1a0a00a66f7957d1555275f655f486444141..4373484a293b22129018932b5549508ceb74343e 100644 (file)
@@ -35,6 +35,7 @@
 #include "sockopt.h"
 #include "privs.h"
 #include "lib_errors.h"
+#include "northbound_cli.h"
 
 #include "zebra/connected.h"
 
@@ -1011,29 +1012,29 @@ int rip_neighbor_lookup(struct sockaddr_in *from)
 }
 
 /* Add new RIP neighbor to the neighbor tree. */
-static int rip_neighbor_add(struct prefix_ipv4 *p)
+int rip_neighbor_add(struct prefix_ipv4 *p)
 {
        struct route_node *node;
 
        node = route_node_get(rip->neighbor, (struct prefix *)p);
 
        if (node->info)
-               return -1;
+               return NB_ERR_INCONSISTENCY;
 
        node->info = rip->neighbor;
 
-       return 0;
+       return NB_OK;
 }
 
 /* Delete RIP neighbor from the neighbor tree. */
-static int rip_neighbor_delete(struct prefix_ipv4 *p)
+int rip_neighbor_delete(struct prefix_ipv4 *p)
 {
        struct route_node *node;
 
        /* Lock for look up. */
        node = route_node_lookup(rip->neighbor, (struct prefix *)p);
        if (!node)
-               return -1;
+               return NB_ERR_INCONSISTENCY;
 
        node->info = NULL;
 
@@ -1043,7 +1044,7 @@ static int rip_neighbor_delete(struct prefix_ipv4 *p)
        /* Unlock real neighbor information lock. */
        route_unlock_node(node);
 
-       return 0;
+       return NB_OK;
 }
 
 /* Clear all network and neighbor configuration. */
@@ -1208,53 +1209,6 @@ DEFUN (no_rip_network,
        return CMD_SUCCESS;
 }
 
-/* RIP neighbor configuration set. */
-DEFUN (rip_neighbor,
-       rip_neighbor_cmd,
-       "neighbor A.B.C.D",
-       "Specify a neighbor router\n"
-       "Neighbor address\n")
-{
-       int idx_ipv4 = 1;
-       int ret;
-       struct prefix_ipv4 p;
-
-       ret = str2prefix_ipv4(argv[idx_ipv4]->arg, &p);
-
-       if (ret <= 0) {
-               vty_out(vty, "Please specify address by A.B.C.D\n");
-               return CMD_WARNING_CONFIG_FAILED;
-       }
-
-       rip_neighbor_add(&p);
-
-       return CMD_SUCCESS;
-}
-
-/* RIP neighbor configuration unset. */
-DEFUN (no_rip_neighbor,
-       no_rip_neighbor_cmd,
-       "no neighbor A.B.C.D",
-       NO_STR
-       "Specify a neighbor router\n"
-       "Neighbor address\n")
-{
-       int idx_ipv4 = 2;
-       int ret;
-       struct prefix_ipv4 p;
-
-       ret = str2prefix_ipv4(argv[idx_ipv4]->arg, &p);
-
-       if (ret <= 0) {
-               vty_out(vty, "Please specify address by A.B.C.D\n");
-               return CMD_WARNING_CONFIG_FAILED;
-       }
-
-       rip_neighbor_delete(&p);
-
-       return CMD_SUCCESS;
-}
-
 DEFUN (ip_rip_receive_version,
        ip_rip_receive_version_cmd,
        "ip rip receive version <(1-2)|none>",
@@ -1896,8 +1850,6 @@ void rip_if_init(void)
        /* Install commands. */
        install_element(RIP_NODE, &rip_network_cmd);
        install_element(RIP_NODE, &no_rip_network_cmd);
-       install_element(RIP_NODE, &rip_neighbor_cmd);
-       install_element(RIP_NODE, &no_rip_neighbor_cmd);
 
        install_element(RIP_NODE, &rip_passive_interface_cmd);
        install_element(RIP_NODE, &no_rip_passive_interface_cmd);
index 25c279a773b6d0d1a1187dd948244ae044819b0a..fdb19a3c14f552fa12728ad222931524a284b8de 100644 (file)
@@ -276,15 +276,31 @@ static int ripd_instance_explicit_neighbor_create(enum nb_event event,
                                                  const struct lyd_node *dnode,
                                                  union nb_resource *resource)
 {
-       /* TODO: implement me. */
-       return NB_OK;
+       struct prefix_ipv4 p;
+
+       if (event != NB_EV_APPLY)
+               return NB_OK;
+
+       p.family = AF_INET;
+       p.prefixlen = IPV4_MAX_BITLEN;
+       yang_dnode_get_ipv4(&p.prefix, dnode, NULL);
+
+       return rip_neighbor_add(&p);
 }
 
 static int ripd_instance_explicit_neighbor_delete(enum nb_event event,
                                                  const struct lyd_node *dnode)
 {
-       /* TODO: implement me. */
-       return NB_OK;
+       struct prefix_ipv4 p;
+
+       if (event != NB_EV_APPLY)
+               return NB_OK;
+
+       p.family = AF_INET;
+       p.prefixlen = IPV4_MAX_BITLEN;
+       yang_dnode_get_ipv4(&p.prefix, dnode, NULL);
+
+       return rip_neighbor_delete(&p);
 }
 
 /*
@@ -858,6 +874,7 @@ const struct frr_yang_module_info frr_ripd_info = {
                        .xpath = "/frr-ripd:ripd/instance/explicit-neighbor",
                        .cbs.create = ripd_instance_explicit_neighbor_create,
                        .cbs.delete = ripd_instance_explicit_neighbor_delete,
+                       .cbs.cli_show = cli_show_rip_neighbor,
                },
                {
                        .xpath = "/frr-ripd:ripd/instance/network",
index 31697264a0aeca53fc2469fa5a101031acae4ee1..fd8762904f17d1c8b2d266b04debf30f84369928 100644 (file)
@@ -389,6 +389,8 @@ extern int rip_create(int socket);
 extern int rip_request_send(struct sockaddr_in *, struct interface *, uint8_t,
                            struct connected *);
 extern int rip_neighbor_lookup(struct sockaddr_in *);
+extern int rip_neighbor_add(struct prefix_ipv4 *p);
+extern int rip_neighbor_delete(struct prefix_ipv4 *p);
 
 extern void rip_ecmp_disable(void);