bgpd: make bgp_info_cmp and multiple-path decision logic more regular
* bgp_route.c: (bgp_info_cmp) This function is supposed to return a
preference between the given paths, and does so as binary either or. When
mpath was added, the binary return value was left as is and instead an out
parameter 'paths_eq' was added to indicate the mpath-equality case. It's
a bit odd, as is the resulting logic in the caller.
Regularise things again by making the function return a strcmp like
trinary return value of -1,0,1. Get rid of the mpath specific arguments,
but pass in afi/safi as part of the general context - that plus the
(struct bgp *) is enough to access configuration.
Update the return values.
The mpath check was testing the IGP metric for equality, even though
previous to the mpath changes (and consistent with the behaviour of all
the other tests bar the end), equality results in continuing through to
the next comparison. Just go back to the previous way - each test finds a
preference to return, or continues on to let further tests have a go.
(bgp_best_selection) Get rid of the (struct bgp_maxpaths_cfg *) arg, we
can't add state for every optional feature to the argument list - they
have to look it up as needed. Do pass through the very general afi/safi
context though (saves several lookups through the route_node).
Adjust for the new trinary bgp_info_cmp return value and updated args.
Do the mpath clearing/accumulation in one place, in each loop.
Call to bgp_info_mpath_update similarly gets updated, as there's no cfg to
pass.
(bgp_process_{rsclient,main}) match bgp_best_selection changes.
* bgp_mpath.c: (bgp_mpath_is_configured_sort) Helper for whether mpath is
enabled by peer sort.
(bgp_mpath_is_configured) ditto, generally.
(bgp_info_mpath_update) caller no longer has the cfg to pass in, look it
up.
* bgp_mpath.h: Export the above and Match .c changes.
Requires commit:
"bgpd: bgp_scan shouldn't queue up route_nodes with no routes for processing"
Signed-off-by: Donald Sharp <sharpd@cumulusnetworks.com>
diff --git a/tests/bgp_mpath_test.c b/tests/bgp_mpath_test.c
index ed54d9c..dbbf0dd 100644
--- a/tests/bgp_mpath_test.c
+++ b/tests/bgp_mpath_test.c
@@ -194,12 +194,15 @@
/*=========================================================
* Testcase for bgp_mp_list
*/
+
+struct bgp test_mp_bgp;
+
struct peer test_mp_list_peer[] = {
- { .local_as = 1, .as = 2 },
- { .local_as = 1, .as = 2 },
- { .local_as = 1, .as = 2 },
- { .local_as = 1, .as = 2 },
- { .local_as = 1, .as = 2 },
+ { .local_as = 1, .as = 2, .bgp = &test_mp_bgp },
+ { .local_as = 1, .as = 2, .bgp = &test_mp_bgp },
+ { .local_as = 1, .as = 2, .bgp = &test_mp_bgp },
+ { .local_as = 1, .as = 2, .bgp = &test_mp_bgp },
+ { .local_as = 1, .as = 2, .bgp = &test_mp_bgp },
};
int test_mp_list_peer_count = sizeof (test_mp_list_peer)/ sizeof (struct peer);
struct attr test_mp_list_attr[4];
@@ -305,7 +308,10 @@
{
struct bgp_info *new_best, *old_best, *mpath;
struct list mp_list;
- struct bgp_maxpaths_cfg mp_cfg = { 3, 3 };
+
+ test_mp_bgp.maxpaths[AFI_IP][SAFI_UNICAST].maxpaths_ebgp = 3;
+ test_mp_bgp.maxpaths[AFI_IP][SAFI_UNICAST].maxpaths_ibgp = 3;
+
int test_result = TEST_PASSED;
bgp_mp_list_init (&mp_list);
bgp_mp_list_add (&mp_list, &test_mp_list_info[4]);
@@ -314,7 +320,7 @@
bgp_mp_list_add (&mp_list, &test_mp_list_info[1]);
new_best = &test_mp_list_info[3];
old_best = NULL;
- bgp_info_mpath_update (&test_rn, new_best, old_best, &mp_list, &mp_cfg);
+ bgp_info_mpath_update (&test_rn, new_best, old_best, &mp_list, AFI_IP, SAFI_UNICAST);
bgp_mp_list_clear (&mp_list);
EXPECT_TRUE (bgp_info_mpath_count (new_best) == 2, test_result);
mpath = bgp_info_mpath_first (new_best);
@@ -328,7 +334,7 @@
bgp_mp_list_add (&mp_list, &test_mp_list_info[1]);
new_best = &test_mp_list_info[0];
old_best = &test_mp_list_info[3];
- bgp_info_mpath_update (&test_rn, new_best, old_best, &mp_list, &mp_cfg);
+ bgp_info_mpath_update (&test_rn, new_best, old_best, &mp_list, AFI_IP, SAFI_UNICAST);
bgp_mp_list_clear (&mp_list);
EXPECT_TRUE (bgp_info_mpath_count (new_best) == 1, test_result);
mpath = bgp_info_mpath_first (new_best);