]> git.proxmox.com Git - mirror_frr.git/commitdiff
Merge pull request #984 from donaldsharp/debugging
authorDavid Lamparter <equinox@diac24.net>
Wed, 16 Aug 2017 17:18:31 +0000 (19:18 +0200)
committerGitHub <noreply@github.com>
Wed, 16 Aug 2017 17:18:31 +0000 (19:18 +0200)
Some Small Pim Issues

eigrpd/eigrp_const.h
eigrpd/eigrp_fsm.c
eigrpd/eigrp_topology.c
eigrpd/eigrp_topology.h
ospfd/ospf_spf.c
pimd/pim_bfd.c
pimd/pim_cmd.c
pimd/pim_ifchannel.c
tests/lib/cli/test_cli.c
tests/ospf6d/test_lsdb.c
vtysh/vtysh.c

index a6282665e4521df5f94919fdcc6a54f3905690e3..a008891a51be6cb8ff7ffc9377429ca570824a0d 100644 (file)
 #define EIGRP_MULTICAST_ADDRESS            0xe000000A /*224.0.0.10*/
 
 #define EIGRP_MAX_METRIC                   0xffffffffU    /*4294967295*/
+enum metric_change {
+       METRIC_DECREASE,
+       METRIC_SAME,
+       METRIC_INCREASE
+};
 
 #define DEFAULT_ROUTE               ZEBRA_ROUTE_MAX
 #define DEFAULT_ROUTE_TYPE(T) ((T) == DEFAULT_ROUTE)
index 852362e1921c76c5364f4fde22834130b7a6094c..8e2a26447eca0b97b84f26a766b3f3c4c84a7ddc 100644 (file)
@@ -185,6 +185,7 @@ int eigrp_get_fsm_event(struct eigrp_fsm_action_message *msg)
        struct eigrp_prefix_entry *prefix = msg->prefix;
        struct eigrp_neighbor_entry *entry = msg->entry;
        u_char actual_state = prefix->state;
+       enum metric_change change;
 
        if (entry == NULL) {
                entry = eigrp_neighbor_entry_new();
@@ -194,19 +195,18 @@ int eigrp_get_fsm_event(struct eigrp_fsm_action_message *msg)
                msg->entry = entry;
        }
 
-       // Dividing by actual state of prefix's FSM
+       /*
+        * Calculate resultant metrics and insert to correct position
+        * in entries list
+        */
+       change = eigrp_topology_update_distance(msg);
+
        switch (actual_state) {
        case EIGRP_FSM_STATE_PASSIVE: {
-               // Calculate resultant metrics and insert to correct position in
-               // entries list
-               eigrp_topology_update_distance(msg);
-
                struct eigrp_neighbor_entry *head =
                        (struct eigrp_neighbor_entry *)
                                entry->prefix->entries->head->data;
-               // zlog_info ("flag: %d rdist: %u dist: %u pfdist: %u pdist:
-               // %u", head->flags, head->reported_distance, head->distance,
-               // prefix->fdistance, prefix->distance);
+
                if (head->reported_distance < prefix->fdistance) {
                        return EIGRP_FSM_KEEP_STATE;
                }
@@ -215,34 +215,31 @@ int eigrp_get_fsm_event(struct eigrp_fsm_action_message *msg)
                 * move to active state
                 * dependently if it was query from successor
                 */
-               else {
-                       if (msg->packet_type == EIGRP_OPC_QUERY) {
-                               return EIGRP_FSM_EVENT_Q_FCN;
-                       } else {
-                               return EIGRP_FSM_EVENT_NQ_FCN;
-                       }
+               if (msg->packet_type == EIGRP_OPC_QUERY) {
+                       return EIGRP_FSM_EVENT_Q_FCN;
+               } else {
+                       return EIGRP_FSM_EVENT_NQ_FCN;
                }
 
                break;
        }
        case EIGRP_FSM_STATE_ACTIVE_0: {
-               eigrp_topology_update_distance(msg);
-
                if (msg->packet_type == EIGRP_OPC_REPLY) {
+                       struct eigrp_neighbor_entry *head =
+                               (struct eigrp_neighbor_entry *)
+                               entry->prefix->entries->head->data;
+
                        listnode_delete(prefix->rij, entry->adv_router);
-                       if (prefix->rij->count) {
+                       if (prefix->rij->count)
                                return EIGRP_FSM_KEEP_STATE;
-                       } else {
-                               zlog_info("All reply received\n");
-                               if (((struct eigrp_neighbor_entry *)
-                                            prefix->entries->head->data)
-                                           ->reported_distance
-                                   < prefix->fdistance) {
-                                       return EIGRP_FSM_EVENT_LR_FCS;
-                               }
 
-                               return EIGRP_FSM_EVENT_LR_FCN;
+                       zlog_info("All reply received\n");
+                       if (head->reported_distance
+                           < prefix->fdistance) {
+                               return EIGRP_FSM_EVENT_LR_FCS;
                        }
+
+                       return EIGRP_FSM_EVENT_LR_FCN;
                } else if (msg->packet_type == EIGRP_OPC_QUERY
                           && (entry->flags
                               & EIGRP_NEIGHBOR_ENTRY_SUCCESSOR_FLAG)) {
@@ -254,15 +251,13 @@ int eigrp_get_fsm_event(struct eigrp_fsm_action_message *msg)
                break;
        }
        case EIGRP_FSM_STATE_ACTIVE_1: {
-               int change = eigrp_topology_update_distance(msg);
-
                if (msg->packet_type == EIGRP_OPC_QUERY
                    && (entry->flags & EIGRP_NEIGHBOR_ENTRY_SUCCESSOR_FLAG)) {
                        return EIGRP_FSM_EVENT_QACT;
                } else if (msg->packet_type == EIGRP_OPC_REPLY) {
                        listnode_delete(prefix->rij, entry->adv_router);
 
-                       if (change == 1
+                       if (change == METRIC_INCREASE
                            && (entry->flags
                                & EIGRP_NEIGHBOR_ENTRY_SUCCESSOR_FLAG)) {
                                return EIGRP_FSM_EVENT_DINC;
@@ -282,17 +277,17 @@ int eigrp_get_fsm_event(struct eigrp_fsm_action_message *msg)
                break;
        }
        case EIGRP_FSM_STATE_ACTIVE_2: {
-               eigrp_topology_update_distance(msg);
-
                if (msg->packet_type == EIGRP_OPC_REPLY) {
+                       struct eigrp_neighbor_entry *head =
+                               (struct eigrp_neighbor_entry *)
+                               prefix->entries->head->data;
+
                        listnode_delete(prefix->rij, entry->adv_router);
                        if (prefix->rij->count) {
                                return EIGRP_FSM_KEEP_STATE;
                        } else {
                                zlog_info("All reply received\n");
-                               if (((struct eigrp_neighbor_entry *)
-                                            prefix->entries->head->data)
-                                           ->reported_distance
+                               if (head->reported_distance
                                    < prefix->fdistance) {
                                        return EIGRP_FSM_EVENT_LR_FCS;
                                }
@@ -305,12 +300,10 @@ int eigrp_get_fsm_event(struct eigrp_fsm_action_message *msg)
                break;
        }
        case EIGRP_FSM_STATE_ACTIVE_3: {
-               int change = eigrp_topology_update_distance(msg);
-
                if (msg->packet_type == EIGRP_OPC_REPLY) {
                        listnode_delete(prefix->rij, entry->adv_router);
 
-                       if (change == 1
+                       if (change == METRIC_INCREASE
                            && (entry->flags
                                & EIGRP_NEIGHBOR_ENTRY_SUCCESSOR_FLAG)) {
                                return EIGRP_FSM_EVENT_DINC;
index ae1396ebaf9580380c6829f9d9c4ca7e95baa020..50d83430a8e8cc2852507670e2e1dce4e09443b9 100644 (file)
@@ -374,42 +374,42 @@ struct list *eigrp_neighbor_prefixes_lookup(struct eigrp *eigrp,
        return prefixes;
 }
 
-int eigrp_topology_update_distance(struct eigrp_fsm_action_message *msg)
+enum metric_change eigrp_topology_update_distance(struct eigrp_fsm_action_message *msg)
 {
        struct eigrp *eigrp = msg->eigrp;
        struct eigrp_prefix_entry *prefix = msg->prefix;
        struct eigrp_neighbor_entry *entry = msg->entry;
-       int change = 0;
+       enum metric_change change = METRIC_SAME;
        assert(entry);
 
        struct TLV_IPv4_External_type *ext_data = NULL;
        struct TLV_IPv4_Internal_type *int_data = NULL;
        if (msg->data_type == EIGRP_TLV_IPv4_INT) {
+               u_int32_t new_reported_distance;
+
                int_data = msg->data.ipv4_int_type;
                if (eigrp_metrics_is_same(int_data->metric,
                                          entry->reported_metric)) {
-                       return 0; // No change
+                       return change; // No change
                }
-               change = entry->reported_distance
-                                        < eigrp_calculate_metrics(
-                                                  eigrp, int_data->metric)
-                                ? 1
-                                : entry->reported_distance
-                                                  > eigrp_calculate_metrics(
-                                                            eigrp,
-                                                            int_data->metric)
-                                          ? 2
-                                          : 3; // Increase : Decrease : No
-                                               // change
+
+               new_reported_distance = eigrp_calculate_metrics(eigrp,
+                                                               int_data->metric);
+
+               if (entry->reported_distance  < new_reported_distance)
+                       change = METRIC_INCREASE;
+               else
+                       change = METRIC_DECREASE;
+
                entry->reported_metric = int_data->metric;
-               entry->reported_distance =
+               entry->reported_distance = new_reported_distance;
                        eigrp_calculate_metrics(eigrp, int_data->metric);
                entry->distance = eigrp_calculate_total_metrics(eigrp, entry);
        } else {
                ext_data = msg->data.ipv4_ext_data;
                if (eigrp_metrics_is_same(ext_data->metric,
                                          entry->reported_metric))
-                       return 0;
+                       return change;
        }
        /*
         * Move to correct position in list according to new distance
index 1340c8210114e84645407d9bc984ec29a32b09bf..0c9b5c60c6a077c9d417a92bcff09bcf811d0efd 100644 (file)
@@ -60,7 +60,7 @@ extern struct list *eigrp_neighbor_prefixes_lookup(struct eigrp *,
                                                   struct eigrp_neighbor *);
 extern void eigrp_topology_update_all_node_flags(struct eigrp *);
 extern void eigrp_topology_update_node_flags(struct eigrp_prefix_entry *);
-extern int eigrp_topology_update_distance(struct eigrp_fsm_action_message *);
+extern enum metric_change eigrp_topology_update_distance(struct eigrp_fsm_action_message *);
 extern void eigrp_update_routing_table(struct eigrp_prefix_entry *);
 extern void eigrp_topology_neighbor_down(struct eigrp *,
                                         struct eigrp_neighbor *);
index 7437d26da31e40bb86781e37b1a158affbb5d66b..891088ecc2da46dd7ad5030fa772bc212f6379e8 100644 (file)
@@ -136,8 +136,10 @@ static void ospf_canonical_nexthops_free(struct vertex *root)
 
                /* Free child nexthops pointing back to this root vertex */
                for (ALL_LIST_ELEMENTS(child->parents, n2, nn2, vp))
-                       if (vp->parent == root && vp->nexthop)
+                       if (vp->parent == root && vp->nexthop) {
                                vertex_nexthop_free(vp->nexthop);
+                               vp->nexthop = NULL;
+                       }
        }
 }
 
@@ -401,8 +403,6 @@ static void ospf_spf_flush_parents(struct vertex *w)
        /* delete the existing nexthops */
        for (ALL_LIST_ELEMENTS(w->parents, ln, nn, vp)) {
                list_delete_node(w->parents, ln);
-               if (vp->nexthop)
-                       vertex_nexthop_free(vp->nexthop);
                vertex_parent_free(vp);
        }
 }
index 1dfb558f46de2bd27835dc0b64bc28834a002e99..bba26662bdab4b08b644162e65f8477ca28b4e88 100644 (file)
@@ -295,31 +295,39 @@ static int pim_bfd_nbr_replay(int command, struct zclient *zclient,
        struct listnode *node;
        struct listnode *neigh_node;
        struct listnode *neigh_nextnode;
+       struct vrf *vrf = NULL;
 
        /* Send the client registration */
        bfd_client_sendmsg(zclient, ZEBRA_BFD_CLIENT_REGISTER);
 
-       for (ALL_LIST_ELEMENTS_RO(vrf_iflist(VRF_DEFAULT), node, ifp)) {
-               pim_ifp = ifp->info;
+       RB_FOREACH(vrf, vrf_name_head, &vrfs_by_name) {
+               for (ALL_LIST_ELEMENTS_RO(vrf_iflist(vrf->vrf_id), node, ifp)) {
+                       pim_ifp = ifp->info;
 
-               if (!pim_ifp)
-                       continue;
-
-               if (pim_ifp->pim_sock_fd < 0)
-                       continue;
+                       if (!pim_ifp)
+                               continue;
 
-               for (ALL_LIST_ELEMENTS(pim_ifp->pim_neighbor_list, neigh_node,
-                                      neigh_nextnode, neigh)) {
-                       if (!neigh->bfd_info)
+                       if (pim_ifp->pim_sock_fd < 0)
                                continue;
-                       if (PIM_DEBUG_PIM_TRACE) {
-                               char str[INET_ADDRSTRLEN];
-                               pim_inet4_dump("<bfd_nbr?>", neigh->source_addr,
-                                              str, sizeof(str));
-                               zlog_debug("%s: Replaying Pim Neigh %s to BFD",
-                                          __PRETTY_FUNCTION__, str);
+
+                       for (ALL_LIST_ELEMENTS(pim_ifp->pim_neighbor_list,
+                                              neigh_node, neigh_nextnode,
+                                              neigh)) {
+                               if (!neigh->bfd_info)
+                                       continue;
+                               if (PIM_DEBUG_PIM_TRACE) {
+                                       char str[INET_ADDRSTRLEN];
+
+                                       pim_inet4_dump("<bfd_nbr?>",
+                                                      neigh->source_addr,
+                                                      str, sizeof(str));
+                                       zlog_debug("%s: Replaying Pim Neigh %s to BFD vrf_id %u",
+                                                  __PRETTY_FUNCTION__, str,
+                                                  vrf->vrf_id);
+                               }
+                               pim_bfd_reg_dereg_nbr(neigh,
+                                                     ZEBRA_BFD_DEST_UPDATE);
                        }
-                       pim_bfd_reg_dereg_nbr(neigh, ZEBRA_BFD_DEST_UPDATE);
                }
        }
        return 0;
index b65eeaba0119954660ff17059c1b45fcc4068875..db24aef423648c769fb5b47279c97b26b6c14861 100644 (file)
@@ -7329,8 +7329,14 @@ DEFUN (ip_pim_bfd,
        struct pim_interface *pim_ifp = ifp->info;
        struct bfd_info *bfd_info = NULL;
 
-       if (!pim_ifp)
-               return CMD_SUCCESS;
+       if (!pim_ifp) {
+               if (!pim_cmd_interface_add(ifp)) {
+                       vty_out(vty, "Could not enable PIM SM on interface\n");
+                       return CMD_WARNING;
+               }
+       }
+       pim_ifp = ifp->info;
+
        bfd_info = pim_ifp->bfd_info;
 
        if (!bfd_info || !CHECK_FLAG(bfd_info->flags, BFD_FLAG_PARAM_CFG))
@@ -7351,8 +7357,10 @@ DEFUN (no_ip_pim_bfd,
        VTY_DECLVAR_CONTEXT(interface, ifp);
        struct pim_interface *pim_ifp = ifp->info;
 
-       if (!pim_ifp)
-               return CMD_SUCCESS;
+       if (!pim_ifp) {
+               vty_out(vty, "Pim not enabled on this interface\n");
+               return CMD_WARNING;
+       }
 
        if (pim_ifp->bfd_info) {
                pim_bfd_reg_dereg_all_nbr(ifp, ZEBRA_BFD_DEST_DEREGISTER);
@@ -7380,7 +7388,14 @@ DEFUN (ip_pim_bfd_param,
        u_int32_t tx_val;
        u_int8_t dm_val;
        int ret;
+       struct pim_interface *pim_ifp = ifp->info;
 
+       if (!pim_ifp) {
+               if (!pim_cmd_interface_add(ifp)) {
+                       vty_out(vty, "Could not enable PIM SM on interface\n");
+                       return CMD_WARNING;
+               }
+       }
 
        if ((ret = bfd_validate_param(
                     vty, argv[idx_number]->arg, argv[idx_number_2]->arg,
index c91efbd8b624e3e685df440262b2d3b85d8e7fe8..39f5f2cc4bfd2e83c3887c5801d0b72b8ff6fbe4 100644 (file)
@@ -553,6 +553,9 @@ struct pim_ifchannel *pim_ifchannel_add(struct interface *ifp,
                        "%s: could not attach upstream (S,G)=%s on interface %s",
                        __PRETTY_FUNCTION__, pim_str_sg_dump(sg), ifp->name);
 
+               if (ch->parent)
+                       listnode_delete(ch->parent->sources, ch);
+
                pim_ifchannel_remove_children(ch);
                if (ch->sources)
                        list_delete(ch->sources);
index 8f062d8b5efdf916f3ae90160641bfc692f165d3..4cc15ba23fd8db5e466948071abdfe79c3108771 100644 (file)
@@ -41,7 +41,7 @@ DUMMY_DEFUN(cmd13, "alt a X:X::X:X");
 DUMMY_DEFUN(cmd14,
            "pat g {  foo A.B.C.D$foo|foo|bar   X:X::X:X$bar| baz } [final]");
 
-#include "tests/lib/cli/test_cli_clippy.c"
+#include "lib/cli/test_cli_clippy.c"
 
 DEFPY(magic_test, magic_test_cmd,
        "magic (0-100) {ipv4net A.B.C.D/M|X:X::X:X$ipv6}",
index 310c4a7323a82a218c6b5e9fc05e6455dec801e6..633e88e76980952b0a1bee22dade471bbe1ef170 100644 (file)
@@ -29,7 +29,7 @@
 #include "ospf6d/ospf6_lsdb.h"
 
 #include "tests/lib/cli/common_cli.h"
-#include "tests/ospf6d/test_lsdb_clippy.c"
+#include "ospf6d/test_lsdb_clippy.c"
 
 static struct ospf6_lsdb *lsdb;
 
index 6255726c471c142e27a742ae903c1391077d937f..f971c171bc328afcc5dfbab5b8bc2c033cf98570 100644 (file)
@@ -250,6 +250,13 @@ static int vtysh_client_execute(struct vtysh_client *head_client,
 
 static void vtysh_client_config(struct vtysh_client *head_client, char *line)
 {
+       /* watchfrr currently doesn't load any config, and has some hardcoded
+        * settings that show up in "show run".  skip it here (for now at
+        * least) so we don't get that mangled up in config-write.
+        */
+       if (head_client->flag == VTYSH_WATCHFRR)
+               return;
+
        vtysh_client_run_all(head_client, line, 1, NULL,
                             vtysh_config_parse_line, NULL);
 }