]> git.puffer.fish Git - mirror/frr.git/commitdiff
ospfd: Assure OSPF AS External routes are installed after link flap 15593/head
authorAcee <aceelindem@gmail.com>
Wed, 20 Mar 2024 03:34:09 +0000 (23:34 -0400)
committerAcee <aceelindem@gmail.com>
Thu, 21 Mar 2024 20:18:59 +0000 (16:18 -0400)
OSPF intra/inter area routes were previously marked to assure they
are re-installed after a fast link flap in the commit:

commit effee18744ad3e1777614f58350d74fb718d3211
Author: Donald Sharp <sharpd@nvidia.com>
Date:   Mon May 24 13:45:29 2021 -0400

    ospfd: Fix quick interface down up event handling in ospf

This commit extends this fix to OSPF AS External routes as well.

Signed-off-by: Acee <aceelindem@gmail.com>
ospfd/ospf_ase.c
ospfd/ospf_interface.c

index 610b5fc08e92640856c78875f23b99e57f759032..9e26a2ac2ddbbcdbe75c60928861439504f4e586 100644 (file)
@@ -480,7 +480,7 @@ static int ospf_ase_route_match_same(struct route_table *rt,
 
        assert(or);
 
-       if (or->path_type != newor->path_type)
+       if (or->changed || (or->path_type != newor->path_type))
                return 0;
 
        switch (or->path_type) {
index 0969ae15bdec12b87367daf91619fca83a887c85..17426d261585519d7a6ca0a85fbfb701083b646e 100644 (file)
@@ -821,14 +821,41 @@ int ospf_if_up(struct ospf_interface *oi)
        return 1;
 }
 
-int ospf_if_down(struct ospf_interface *oi)
+/* This function will mark routes with next-hops matching the down
+ * OSPF interface as changed. It is used to assure routes that get
+ * removed from the zebra RIB when an interface goes down are
+ * reinstalled if the interface comes back up prior to an intervening
+ * SPF calculation.
+ */
+static void ospf_if_down_mark_routes_changed(struct route_table *table,
+                                            struct ospf_interface *oi)
 {
-       struct ospf *ospf;
        struct route_node *rn;
        struct ospf_route *or;
        struct listnode *nh;
        struct ospf_path *op;
 
+       for (rn = route_top(table); rn; rn = route_next(rn)) {
+               or = rn->info;
+
+               if (or == NULL)
+                       continue;
+
+               for (nh = listhead(or->paths); nh;
+                    nh = listnextnode_unchecked(nh)) {
+                       op = listgetdata(nh);
+                       if (op->ifindex == oi->ifp->ifindex) {
+                               or->changed = true;
+                               break;
+                       }
+               }
+       }
+}
+
+int ospf_if_down(struct ospf_interface *oi)
+{
+       struct ospf *ospf;
+
        if (oi == NULL)
                return 0;
 
@@ -864,23 +891,11 @@ int ospf_if_down(struct ospf_interface *oi)
        /* Shutdown packet reception and sending */
        ospf_if_stream_unset(oi);
 
-       if (!ospf->new_table)
-               return 1;
-       for (rn = route_top(ospf->new_table); rn; rn = route_next(rn)) {
-               or = rn->info;
-
-               if (!or)
-                       continue;
+       if (ospf->new_table)
+               ospf_if_down_mark_routes_changed(ospf->new_table, oi);
 
-               for (nh = listhead(or->paths); nh;
-                    nh = listnextnode_unchecked(nh)) {
-                       op = listgetdata(nh);
-                       if (op->ifindex == oi->ifp->ifindex) {
-                               or->changed = true;
-                               break;
-                       }
-               }
-       }
+       if (ospf->new_external_route)
+               ospf_if_down_mark_routes_changed(ospf->new_external_route, oi);
 
        return 1;
 }