Dump routes (VPP-500)
[vpp.git] / vnet / vnet / fib / fib_entry.c
index 5429da2..da2656e 100644 (file)
@@ -393,6 +393,7 @@ fib_entry_back_walk_notify (fib_node_t *node,
 
     if (FIB_NODE_BW_REASON_FLAG_EVALUATE & ctx->fnbw_reason        ||
         FIB_NODE_BW_REASON_FLAG_ADJ_UPDATE & ctx->fnbw_reason      ||
+        FIB_NODE_BW_REASON_FLAG_ADJ_DOWN & ctx->fnbw_reason        ||
        FIB_NODE_BW_REASON_FLAG_INTERFACE_UP & ctx->fnbw_reason    ||
        FIB_NODE_BW_REASON_FLAG_INTERFACE_DOWN & ctx->fnbw_reason  ||
        FIB_NODE_BW_REASON_FLAG_INTERFACE_DELETE & ctx->fnbw_reason)
@@ -402,35 +403,26 @@ fib_entry_back_walk_notify (fib_node_t *node,
                                             fib_entry_get_index(fib_entry)));
     }
 
-    if (FIB_NODE_BW_REASON_FLAG_ADJ_UPDATE & ctx->fnbw_reason)
-    {
-        /*
-         * ADJ updates (complete<->incomplete) do not need to propagate to
-         * recursive entries.
-         * The only reason its needed as far back as here, is that the adj
-         * and the incomplete adj are a different DPO type, so the LBs need
-         * to re-stack.
-         */
-        return (FIB_NODE_BACK_WALK_CONTINUE);
-    }
-    else
-    {
-        /*
-         * all other walk types can be reclassifed to a re-evaluate to
-         * all recursive dependents.
-         * By reclassifying we ensure that should any of these walk types meet
-         * they can be merged.
-         */
-        ctx->fnbw_reason = FIB_NODE_BW_REASON_FLAG_EVALUATE;
-
-        /*
-         * propagate the backwalk further if we haven't already reached the
-         * maximum depth.
-         */
-        fib_walk_sync(FIB_NODE_TYPE_ENTRY,
-                      fib_entry_get_index(fib_entry),
-                      ctx);
-    }
+    /*
+     * all other walk types can be reclassifed to a re-evaluate to
+     * all recursive dependents.
+     * By reclassifying we ensure that should any of these walk types meet
+     * they can be merged.
+     */
+    ctx->fnbw_reason = FIB_NODE_BW_REASON_FLAG_EVALUATE;
+
+    /*
+     * ... and nothing is forced sync from now on.
+     */
+    ctx->fnbw_flags &= ~FIB_NODE_BW_FLAG_FORCE_SYNC;
+
+    /*
+     * propagate the backwalk further if we haven't already reached the
+     * maximum depth.
+     */
+    fib_walk_sync(FIB_NODE_TYPE_ENTRY,
+                 fib_entry_get_index(fib_entry),
+                 ctx);
 
     return (FIB_NODE_BACK_WALK_CONTINUE);
 }
@@ -767,39 +759,26 @@ fib_entry_post_update_actions (fib_entry_t *fib_entry,
     fib_entry_post_install_actions(fib_entry, source, old_flags);
 }
 
-void
-fib_entry_special_add (fib_node_index_t fib_entry_index,
-                      fib_source_t source,
-                      fib_entry_flag_t flags,
-                      const dpo_id_t *dpo)
+static void
+fib_entry_source_change (fib_entry_t *fib_entry,
+                        fib_source_t best_source,
+                        fib_source_t new_source,
+                        fib_entry_flag_t old_flags)
 {
-    fib_source_t best_source;
-    fib_entry_flag_t bflags;
-    fib_entry_t *fib_entry;
-    fib_entry_src_t *bsrc;
-
-    fib_entry = fib_entry_get(fib_entry_index);
-
-    bsrc = fib_entry_get_best_src_i(fib_entry);
-    best_source = fib_entry_src_get_source(bsrc);
-    bflags = fib_entry_src_get_flags(bsrc);
-
-    fib_entry = fib_entry_src_action_add(fib_entry, source, flags, dpo);
-
     /*
      * if the path list for the source passed is invalid,
      * then we need to create a new one. else we are updating
      * an existing.
      */
-    if (source < best_source)
+    if (new_source < best_source)
     {
        /*
         * we have a new winning source.
         */
        fib_entry_src_action_deactivate(fib_entry, best_source);
-       fib_entry_src_action_activate(fib_entry, source);
+       fib_entry_src_action_activate(fib_entry, new_source);
     }
-    else if (source > best_source)
+    else if (new_source > best_source)
     {
        /*
         * the new source loses. nothing to do here.
@@ -814,13 +793,56 @@ fib_entry_special_add (fib_node_index_t fib_entry_index,
         * But the path-list was updated, which will contribute new forwarding,
         * so install it.
         */
-       fib_entry_src_action_deactivate(fib_entry, source);
-       fib_entry_src_action_activate(fib_entry, source);
+       fib_entry_src_action_deactivate(fib_entry, new_source);
+       fib_entry_src_action_activate(fib_entry, new_source);
     }
 
-    fib_entry_post_update_actions(fib_entry, source, bflags);
+    fib_entry_post_update_actions(fib_entry, new_source, old_flags);
+}
+
+void
+fib_entry_special_add (fib_node_index_t fib_entry_index,
+                      fib_source_t source,
+                      fib_entry_flag_t flags,
+                      const dpo_id_t *dpo)
+{
+    fib_source_t best_source;
+    fib_entry_flag_t bflags;
+    fib_entry_t *fib_entry;
+    fib_entry_src_t *bsrc;
+
+    fib_entry = fib_entry_get(fib_entry_index);
+
+    bsrc = fib_entry_get_best_src_i(fib_entry);
+    best_source = fib_entry_src_get_source(bsrc);
+    bflags = fib_entry_src_get_flags(bsrc);
+
+    fib_entry = fib_entry_src_action_add(fib_entry, source, flags, dpo);
+    fib_entry_source_change(fib_entry, best_source, source, bflags);
+}
+
+void
+fib_entry_special_update (fib_node_index_t fib_entry_index,
+                         fib_source_t source,
+                         fib_entry_flag_t flags,
+                         const dpo_id_t *dpo)
+{
+    fib_source_t best_source;
+    fib_entry_flag_t bflags;
+    fib_entry_t *fib_entry;
+    fib_entry_src_t *bsrc;
+
+    fib_entry = fib_entry_get(fib_entry_index);
+
+    bsrc = fib_entry_get_best_src_i(fib_entry);
+    best_source = fib_entry_src_get_source(bsrc);
+    bflags = fib_entry_src_get_flags(bsrc);
+
+    fib_entry = fib_entry_src_action_update(fib_entry, source, flags, dpo);
+    fib_entry_source_change(fib_entry, best_source, source, bflags);
 }
 
+
 void
 fib_entry_path_add (fib_node_index_t fib_entry_index,
                    fib_source_t source,
@@ -1456,6 +1478,16 @@ fib_entry_module_init (void)
     fib_node_register_type (FIB_NODE_TYPE_ENTRY, &fib_entry_vft);
 }
 
+void
+fib_entry_encode (fib_node_index_t fib_entry_index,
+                 fib_route_path_encode_t **api_rpaths)
+{
+    fib_entry_t *fib_entry;
+
+    fib_entry = fib_entry_get(fib_entry_index);
+    fib_path_list_walk(fib_entry->fe_parent, fib_path_encode, api_rpaths);
+}
+
 void
 fib_entry_get_prefix (fib_node_index_t fib_entry_index,
                      fib_prefix_t *pfx)