]> git.puffer.fish Git - mirror/frr.git/commitdiff
ospf: suppress delete using replacement
authorAyan Banerjee <ayan@cumulusnetworks.com>
Mon, 3 Dec 2012 18:48:46 +0000 (10:48 -0800)
committerScott Feldman <sfeldma@cumulusnetworks.com>
Mon, 7 Jan 2013 17:59:40 +0000 (09:59 -0800)
After a SPF run, OSPF deletes routes that have changed in terms of any
metric, type, and/or next-hops and re-adds them. Given that the Zebra-RIB
already support replacement semantics, we suppress deletes for routes
that will be added back again.

This has the following advantages. It reduces the number of IPC messages
between OSPF/Zebra. Also, in the current flow, a batch of route deletes
were followed by a batch of adds even for say a metric change.

With the change, routes are sent as "add" when they are modified. Zebra
already implicitly deletes older routes.

Signed-off-by: Ayan Banerjee <ayan@cumulusnetworks.com>
Reviewed-by: Scott Feldman <sfeldma@cumulusnetworks.com>
Reviewed-by: Dinesh Dutt <ddutt@cumulusnetworks.com>
Signed-off-by: Scott Feldman <sfeldma@cumulusnetworks.com>
ospfd/ospf_route.c

index c3acba348d01e1f3e9656cb8e75fbcf43ecca981..eb7829acdf1bd160914d219974f0e2719c82f76e 100644 (file)
@@ -126,6 +126,31 @@ ospf_route_table_free (struct route_table *rt)
    route_table_finish (rt);
 }
 
+/* If a prefix exists in the new routing table, then return 1,
+   otherwise return 0. Since the ZEBRA-RIB does an implicit
+   withdraw, it is not necessary to send a delete, an add later
+   will act like an implicit delete. */
+static int
+ospf_route_exist_new_table (struct route_table *rt, struct prefix_ipv4 *prefix)
+{
+  struct route_node *rn;
+
+  assert (rt);
+  assert (prefix);
+
+  rn = route_node_lookup (rt, (struct prefix *) prefix);
+  if (!rn) {
+    return 0;
+  }
+  route_unlock_node (rn);
+
+  if (!rn->info) {
+    return 0;
+  }
+
+  return 1;
+}
+
 /* If a prefix and a nexthop match any route in the routing table,
    then return 1, otherwise return 0. */
 int
@@ -223,13 +248,13 @@ ospf_route_delete_uniq (struct route_table *rt, struct route_table *cmprt)
        {
          if (or->type == OSPF_DESTINATION_NETWORK)
            {
-             if (! ospf_route_match_same (cmprt, 
-                                          (struct prefix_ipv4 *) &rn->p, or))
+             if (! ospf_route_exist_new_table (cmprt,
+                                          (struct prefix_ipv4 *) &rn->p))
                ospf_zebra_delete ((struct prefix_ipv4 *) &rn->p, or);
            }
          else if (or->type == OSPF_DESTINATION_DISCARD)
-           if (! ospf_route_match_same (cmprt,
-                                        (struct prefix_ipv4 *) &rn->p, or))
+           if (! ospf_route_exist_new_table (cmprt,
+                                        (struct prefix_ipv4 *) &rn->p))
              ospf_zebra_delete_discard ((struct prefix_ipv4 *) &rn->p);
        }
 }