]> git.proxmox.com Git - mirror_frr.git/commitdiff
zebra: Re-work zebra_nhg_*_valid APIs
authorStephen Worley <sworley@cumulusnetworks.com>
Wed, 23 Oct 2019 20:49:07 +0000 (16:49 -0400)
committerStephen Worley <sworley@cumulusnetworks.com>
Fri, 25 Oct 2019 15:13:44 +0000 (11:13 -0400)
Re-work the validity setting and checking APIs
for nhg_hash_entry's to make them clearer.

Further, they were originally only beings set
on ifdown and install. Extended their use into
releasing entries and to account for setting
the validity of a recursive dependent.

Signed-off-by: Stephen Worley <sworley@cumulusnetworks.com>
zebra/interface.c
zebra/zebra_nhg.c
zebra/zebra_nhg.h

index 76d5d2a2463a33b565ce4f5af78074c6bffbb7b1..daa93e36d1c4cbc612506170b77f6fa167e20408 100644 (file)
@@ -189,17 +189,31 @@ static int if_zebra_new_hook(struct interface *ifp)
        return 0;
 }
 
-static void if_nhg_dependents_release(struct interface *ifp)
+static void if_nhg_dependents_check_valid(struct nhg_hash_entry *nhe)
 {
-       if (!if_nhg_dependents_is_empty(ifp)) {
-               struct nhg_connected *rb_node_dep = NULL;
-               struct zebra_if *zif = (struct zebra_if *)ifp->info;
+       zebra_nhg_check_valid(nhe);
+       if (!CHECK_FLAG(nhe->flags, NEXTHOP_GROUP_VALID))
+               /* Assuming uninstalled as well here */
+               UNSET_FLAG(nhe->flags, NEXTHOP_GROUP_INSTALLED);
+}
 
-               frr_each(nhg_connected_tree, &zif->nhg_dependents,
-                         rb_node_dep) {
-                       rb_node_dep->nhe->ifp = NULL;
-                       zebra_nhg_set_invalid(rb_node_dep->nhe);
-               }
+static void if_down_nhg_dependents(const struct interface *ifp)
+{
+       struct nhg_connected *rb_node_dep = NULL;
+       struct zebra_if *zif = (struct zebra_if *)ifp->info;
+
+       frr_each(nhg_connected_tree, &zif->nhg_dependents, rb_node_dep)
+               if_nhg_dependents_check_valid(rb_node_dep->nhe);
+}
+
+static void if_nhg_dependents_release(const struct interface *ifp)
+{
+       struct nhg_connected *rb_node_dep = NULL;
+       struct zebra_if *zif = (struct zebra_if *)ifp->info;
+
+       frr_each(nhg_connected_tree, &zif->nhg_dependents, rb_node_dep) {
+               rb_node_dep->nhe->ifp = NULL; /* Null it out */
+               if_nhg_dependents_check_valid(rb_node_dep->nhe);
        }
 }
 
@@ -998,19 +1012,6 @@ bool if_nhg_dependents_is_empty(const struct interface *ifp)
        return false;
 }
 
-static void if_down_nhg_dependents(const struct interface *ifp)
-{
-       if (!if_nhg_dependents_is_empty(ifp)) {
-               struct nhg_connected *rb_node_dep = NULL;
-               struct zebra_if *zif = (struct zebra_if *)ifp->info;
-
-               frr_each(nhg_connected_tree, &zif->nhg_dependents,
-                         rb_node_dep) {
-                       zebra_nhg_set_invalid(rb_node_dep->nhe);
-               }
-       }
-}
-
 /* Interface is up. */
 void if_up(struct interface *ifp)
 {
index 418c1102bdb0f9f2f47b6725e65e2ab6ca231f79..3ec764c5d390403435d3b0367321f30c2a6304d2 100644 (file)
@@ -246,13 +246,12 @@ void zebra_nhg_dependents_init(struct nhg_hash_entry *nhe)
 /* Release this nhe from anything depending on it */
 static void zebra_nhg_dependents_release(struct nhg_hash_entry *nhe)
 {
-       if (!zebra_nhg_dependents_is_empty(nhe)) {
-               struct nhg_connected *rb_node_dep = NULL;
+       struct nhg_connected *rb_node_dep = NULL;
 
-               frr_each_safe(nhg_connected_tree, &nhe->nhg_dependents,
-                              rb_node_dep) {
-                       zebra_nhg_depends_del(rb_node_dep->nhe, nhe);
-               }
+       frr_each_safe(nhg_connected_tree, &nhe->nhg_dependents, rb_node_dep) {
+               zebra_nhg_depends_del(rb_node_dep->nhe, nhe);
+               /* recheck validity of the dependent */
+               zebra_nhg_check_valid(rb_node_dep->nhe);
        }
 }
 
@@ -687,6 +686,48 @@ static void zebra_nhg_set_unhashable(struct nhg_hash_entry *nhe)
                nhe->id);
 }
 
+static void zebra_nhg_set_valid(struct nhg_hash_entry *nhe)
+{
+       struct nhg_connected *rb_node_dep;
+
+       SET_FLAG(nhe->flags, NEXTHOP_GROUP_VALID);
+
+       frr_each(nhg_connected_tree, &nhe->nhg_dependents, rb_node_dep)
+               zebra_nhg_set_valid(rb_node_dep->nhe);
+}
+
+static void zebra_nhg_set_invalid(struct nhg_hash_entry *nhe)
+{
+       struct nhg_connected *rb_node_dep;
+
+       UNSET_FLAG(nhe->flags, NEXTHOP_GROUP_VALID);
+
+       /* Update validity of nexthops depending on it */
+       frr_each(nhg_connected_tree, &nhe->nhg_dependents, rb_node_dep)
+               zebra_nhg_check_valid(rb_node_dep->nhe);
+}
+
+void zebra_nhg_check_valid(struct nhg_hash_entry *nhe)
+{
+       struct nhg_connected *rb_node_dep = NULL;
+       bool valid = false;
+
+       /* If anthing else in the group is valid, the group is valid */
+       frr_each(nhg_connected_tree, &nhe->nhg_depends, rb_node_dep) {
+               if (CHECK_FLAG(rb_node_dep->nhe->flags, NEXTHOP_GROUP_VALID)) {
+                       valid = true;
+                       goto done;
+               }
+       }
+
+done:
+       if (valid)
+               zebra_nhg_set_valid(nhe);
+       else
+               zebra_nhg_set_invalid(nhe);
+}
+
+
 static void zebra_nhg_release(struct nhg_hash_entry *nhe)
 {
        /* Remove it from any lists it may be on */
@@ -711,6 +752,15 @@ static void zebra_nhg_handle_uninstall(struct nhg_hash_entry *nhe)
        zebra_nhg_free(nhe);
 }
 
+static void zebra_nhg_handle_install(struct nhg_hash_entry *nhe)
+{
+       /* Update validity of groups depending on it */
+       struct nhg_connected *rb_node_dep;
+
+       frr_each_safe(nhg_connected_tree, &nhe->nhg_dependents, rb_node_dep)
+               zebra_nhg_set_valid(rb_node_dep->nhe);
+}
+
 /*
  * The kernel/other program has changed the state of a nexthop object we are
  * using.
@@ -1083,34 +1133,6 @@ void zebra_nhg_increment_ref(struct nhg_hash_entry *nhe)
                nhg_connected_tree_increment_ref(&nhe->nhg_depends);
 }
 
-void zebra_nhg_set_invalid(struct nhg_hash_entry *nhe)
-{
-       if (!zebra_nhg_depends_is_empty(nhe)
-           && !CHECK_FLAG(nhe->flags, NEXTHOP_GROUP_RECURSIVE)) {
-               struct nhg_connected *rb_node_dep = NULL;
-
-               /* If anthing else in the group is valid, the group is valid */
-               frr_each(nhg_connected_tree, &nhe->nhg_depends, rb_node_dep) {
-                       if (CHECK_FLAG(rb_node_dep->nhe->flags,
-                                      NEXTHOP_GROUP_VALID))
-                               return;
-               }
-       }
-
-       UNSET_FLAG(nhe->flags, NEXTHOP_GROUP_VALID);
-       /* Assuming uninstalled as well here */
-       UNSET_FLAG(nhe->flags, NEXTHOP_GROUP_INSTALLED);
-
-       if (!zebra_nhg_dependents_is_empty(nhe)) {
-               struct nhg_connected *rb_node_dep = NULL;
-
-               frr_each(nhg_connected_tree, &nhe->nhg_dependents,
-                         rb_node_dep) {
-                       zebra_nhg_set_invalid(rb_node_dep->nhe);
-               }
-       }
-}
-
 void zebra_nhg_set_if(struct nhg_hash_entry *nhe, struct interface *ifp)
 {
        nhe->ifp = ifp;
@@ -1799,6 +1821,7 @@ void zebra_nhg_install_kernel(struct nhg_hash_entry *nhe)
                        break;
                case ZEBRA_DPLANE_REQUEST_SUCCESS:
                        SET_FLAG(nhe->flags, NEXTHOP_GROUP_INSTALLED);
+                       zebra_nhg_handle_install(nhe);
                        break;
                }
        }
@@ -1870,6 +1893,7 @@ void zebra_nhg_dplane_result(struct zebra_dplane_ctx *ctx)
                if (status == ZEBRA_DPLANE_REQUEST_SUCCESS) {
                        SET_FLAG(nhe->flags, NEXTHOP_GROUP_VALID);
                        SET_FLAG(nhe->flags, NEXTHOP_GROUP_INSTALLED);
+                       zebra_nhg_handle_install(nhe);
                } else
                        flog_err(
                                EC_ZEBRA_DP_INSTALL_FAIL,
index 82f54a3a63f3674a261b810fb277083f36f9abce..e636c0f2d2ea4ace34098f2974ee87db4cdeb979 100644 (file)
@@ -249,7 +249,7 @@ void zebra_nhg_free(void *arg);
 void zebra_nhg_decrement_ref(struct nhg_hash_entry *nhe);
 void zebra_nhg_increment_ref(struct nhg_hash_entry *nhe);
 
-void zebra_nhg_set_invalid(struct nhg_hash_entry *nhe);
+void zebra_nhg_check_valid(struct nhg_hash_entry *nhe);
 void zebra_nhg_set_if(struct nhg_hash_entry *nhe, struct interface *ifp);
 
 extern int nexthop_active_update(struct route_node *rn, struct route_entry *re);