diff --git a/bgpd/bgp_route.c b/bgpd/bgp_route.c index 5feda7183739..e8f645406bb3 100644 --- a/bgpd/bgp_route.c +++ b/bgpd/bgp_route.c @@ -3007,7 +3007,8 @@ void bgp_best_selection(struct bgp *bgp, struct bgp_dest *dest, old_select = NULL; pi = bgp_dest_get_bgp_path_info(dest); - while (pi && CHECK_FLAG(pi->flags, BGP_PATH_UNSORTED)) { + while (pi && (CHECK_FLAG(pi->flags, BGP_PATH_UNSORTED) || + (pi->peer != bgp->peer_self && !peer_established(pi->peer->connection)))) { struct bgp_path_info *next = pi->next; if (CHECK_FLAG(pi->flags, BGP_PATH_SELECTED)) @@ -3101,6 +3102,28 @@ void bgp_best_selection(struct bgp *bgp, struct bgp_dest *dest, continue; } + if (first->peer != bgp->peer_self && !peer_established(first->peer->connection)) { + if (debug) + zlog_debug("%s: %pBD(%s) pi %p from %s is not in established state", + __func__, dest, bgp->name_pretty, first, + first->peer->host); + + /* + * Peer is not in established state we cannot sort this + * item yet. Let's wait, so hold this one to the side + */ + if (unsorted_holddown) { + first->next = unsorted_holddown; + unsorted_holddown->prev = first; + unsorted_holddown = first; + } else + unsorted_holddown = first; + + UNSET_FLAG(first->flags, BGP_PATH_UNSORTED); + + continue; + } + bgp_path_info_unset_flag(dest, first, BGP_PATH_DMED_CHECK); worse = NULL;