]> git.puffer.fish Git - mirror/frr.git/commitdiff
eigrpd: Fix eigrp crash on shut of a interface 3072/head
authorDonald Sharp <sharpd@cumulusnetworks.com>
Sat, 22 Sep 2018 16:43:32 +0000 (12:43 -0400)
committerDonald Sharp <sharpd@cumulusnetworks.com>
Sat, 22 Sep 2018 16:43:32 +0000 (12:43 -0400)
The eigrp interface structure was storing a pointer to the
connected interface structure and on shutdown of an interface
this would cause zebra to call eigrp back with a shutdown of
that interface, as part of that operation the connected interface
structure is being deleted, but eigrp was keeping a pointer to
the connected structure.  At the same time we were keeping the address
of the connected structure and this is all we need, so keep a copy
of that data and use that instead.

Signed-off-by: Donald Sharp <sharpd@cumulusnetworks.com>
eigrpd/eigrp_interface.c
eigrpd/eigrp_network.c
eigrpd/eigrp_structs.h

index cd62811fdfdadf34da3698590019f8974155b998..913db684c1c3cc15e3ae2394293918a2fba4adeb 100644 (file)
@@ -183,9 +183,7 @@ int eigrp_if_up(struct eigrp_interface *ei)
 
        struct prefix dest_addr;
 
-       dest_addr.family = AF_INET;
-       dest_addr.u.prefix4 = ei->connected->address->u.prefix4;
-       dest_addr.prefixlen = ei->connected->address->prefixlen;
+       dest_addr = *ei->address;
        apply_mask(&dest_addr);
        pe = eigrp_topology_table_lookup_ipv4(eigrp->topology_table,
                                              &dest_addr);
@@ -344,7 +342,7 @@ void eigrp_if_free(struct eigrp_interface *ei, int source)
                eigrp_hello_send(ei, EIGRP_HELLO_GRACEFUL_SHUTDOWN, NULL);
        }
 
-       dest_addr = *ei->connected->address;
+       dest_addr = *ei->address;
        apply_mask(&dest_addr);
        pe = eigrp_topology_table_lookup_ipv4(eigrp->topology_table,
                                              &dest_addr);
index 8eaf1e82a31ed55d7f87971d30c1358734c4da38..35b45288b80f2bedebcbd90cbc03e641dc2a56ee 100644 (file)
@@ -48,8 +48,8 @@
 #include "eigrpd/eigrp_vty.h"
 #include "eigrpd/eigrp_network.h"
 
-static int eigrp_network_match_iface(const struct connected *,
-                                    const struct prefix *);
+static int eigrp_network_match_iface(const struct prefix *connected_prefix,
+                                    const struct prefix *prefix);
 static void eigrp_network_run_interface(struct eigrp *, struct prefix *,
                                        struct interface *);
 
@@ -241,11 +241,11 @@ int eigrp_network_set(struct eigrp *eigrp, struct prefix *p)
 /* Check whether interface matches given network
  * returns: 1, true. 0, false
  */
-static int eigrp_network_match_iface(const struct connected *co,
+static int eigrp_network_match_iface(const struct prefix *co_prefix,
                                     const struct prefix *net)
 {
        /* new approach: more elegant and conceptually clean */
-       return prefix_match_network_statement(net, CONNECTED_PREFIX(co));
+       return prefix_match_network_statement(net, co_prefix);
 }
 
 static void eigrp_network_run_interface(struct eigrp *eigrp, struct prefix *p,
@@ -263,10 +263,9 @@ static void eigrp_network_run_interface(struct eigrp *eigrp, struct prefix *p,
                        continue;
 
                if (p->family == co->address->family && !ifp->info
-                   && eigrp_network_match_iface(co, p)) {
+                   && eigrp_network_match_iface(co->address, p)) {
 
                        ei = eigrp_if_new(eigrp, ifp, co->address);
-                       ei->connected = co;
 
                        /* Relate eigrp interface to eigrp instance. */
                        ei->eigrp = eigrp;
@@ -328,21 +327,20 @@ int eigrp_network_unset(struct eigrp *eigrp, struct prefix *p)
 
        /* Find interfaces that not configured already.  */
        for (ALL_LIST_ELEMENTS(eigrp->eiflist, node, nnode, ei)) {
-               int found = 0;
-               struct connected *co = ei->connected;
+               bool found = false;
 
                for (rn = route_top(eigrp->networks); rn; rn = route_next(rn)) {
                        if (rn->info == NULL)
                                continue;
 
-                       if (eigrp_network_match_iface(co, &rn->p)) {
-                               found = 1;
+                       if (eigrp_network_match_iface(ei->address, &rn->p)) {
+                               found = true;
                                route_unlock_node(rn);
                                break;
                        }
                }
 
-               if (found == 0) {
+               if (!found) {
                        eigrp_if_free(ei, INTERFACE_DOWN_BY_VTY);
                }
        }
index 95bcfe50e72e0f13089835f200d6989f02be8d61..ce03a21fbaeb7a4e796c731cabf9b75df6641138 100644 (file)
@@ -178,7 +178,6 @@ struct eigrp_interface {
        uint8_t type;
 
        struct prefix *address;      /* Interface prefix */
-       struct connected *connected; /* Pointer to connected */
 
        /* Neighbor information. */
        struct list *nbrs; /* EIGRP Neighbor List */