]> git.puffer.fish Git - matthieu/frr.git/commitdiff
bgpd: ensure that the node gets unlocked in all cases
authorCarl Baldwin <carl@ecbaldwin.net>
Wed, 29 Dec 2021 21:32:33 +0000 (14:32 -0700)
committerMergify <37929162+mergify[bot]@users.noreply.github.com>
Thu, 28 Apr 2022 13:50:28 +0000 (13:50 +0000)
The logic to unlock dest if iteration completed without iterating the
entire node was flawed. Specifically, if iteration terminated due to
`gr_deferred == 0` then the node would not get unlocked.

This change takes into account the fact that dest will be NULL only in
the case when the entire table was iterated and all nodes were already
unlocked. In any other case, it needs to be unlocked.

Signed-off-by: Carl Baldwin <carl@ecbaldwin.net>
(cherry picked from commit 067ea16598a444b1ecfda5012f96acb038ba041e)

bgpd/bgp_route.c

index 1edb10ea4c126862f6dc1ea22adddf0f2bd07bed..e81fcc07107e9fa2fdb30f220ec6982e5114158f 100644 (file)
@@ -3165,7 +3165,8 @@ int bgp_best_path_select_defer(struct bgp *bgp, afi_t afi, safi_t safi)
 
        /* Process the route list */
        for (dest = bgp_table_top(bgp->rib[afi][safi]);
-            dest && bgp->gr_info[afi][safi].gr_deferred != 0;
+            dest && bgp->gr_info[afi][safi].gr_deferred != 0 &&
+            cnt < BGP_MAX_BEST_ROUTE_SELECT;
             dest = bgp_route_next(dest)) {
                if (!CHECK_FLAG(dest->flags, BGP_NODE_SELECT_DEFER))
                        continue;
@@ -3174,10 +3175,13 @@ int bgp_best_path_select_defer(struct bgp *bgp, afi_t afi, safi_t safi)
                bgp->gr_info[afi][safi].gr_deferred--;
                bgp_process_main_one(bgp, dest, afi, safi);
                cnt++;
-               if (cnt >= BGP_MAX_BEST_ROUTE_SELECT) {
-                       bgp_dest_unlock_node(dest);
-                       break;
-               }
+       }
+       /* If iteration stopped before the entire table was traversed then the
+        * node needs to be unlocked.
+        */
+       if (dest) {
+               bgp_dest_unlock_node(dest);
+               dest = NULL;
        }
 
        /* Send EOR message when all routes are processed */