aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorNeale Ranns <nranns@cisco.com>2019-12-04 06:11:00 +0000
committerOle Trøan <otroan@employees.org>2019-12-04 22:47:12 +0000
commit3bab8f9c5396a7bf1115b93a9e0691a76a9ed14c (patch)
tree0212708b47f042ac393848e0471669f837788278
parent5f8f6173328f8d77feea5fd100e150c3094c11f0 (diff)
fib: Decouple source from priority and behaviour
Type: feature the fib_source_t enum alone no longer defines the priority and behaviour, instead each source must be allocated these attributes. This allows the creation of other sources by the plugins (and soon over the API). Signed-off-by: Neale Ranns <nranns@cisco.com> Change-Id: I890ee820fbc16079ee417ea1fbc163192806e853
-rw-r--r--src/plugins/gbp/gbp_endpoint.c21
-rw-r--r--src/plugins/gbp/gbp_route_domain.c9
-rw-r--r--src/plugins/gbp/gbp_subnet.c13
-rw-r--r--src/plugins/ila/ila.c13
-rw-r--r--src/plugins/lb/lb.c12
-rw-r--r--src/plugins/nat/dslite.c10
-rwxr-xr-xsrc/plugins/nat/nat.c44
-rw-r--r--src/plugins/nat/nat.h4
-rw-r--r--src/plugins/nat/nat64.c9
-rw-r--r--src/plugins/nat/nat64_cli.c9
-rw-r--r--src/plugins/nat/nat66.c5
-rw-r--r--src/plugins/pppoe/pppoe.c10
-rw-r--r--src/plugins/svs/svs.c16
-rw-r--r--src/plugins/unittest/fib_test.c7
-rw-r--r--src/vnet/CMakeLists.txt14
-rw-r--r--src/vnet/fib/fib.c1
-rw-r--r--src/vnet/fib/fib_entry.c60
-rw-r--r--src/vnet/fib/fib_entry.h171
-rw-r--r--src/vnet/fib/fib_entry_src.c27
-rw-r--r--src/vnet/fib/fib_entry_src.h8
-rw-r--r--src/vnet/fib/fib_entry_src_adj.c2
-rw-r--r--src/vnet/fib/fib_entry_src_api.c10
-rw-r--r--src/vnet/fib/fib_entry_src_default.c7
-rw-r--r--src/vnet/fib/fib_entry_src_drop.c (renamed from src/vnet/fib/fib_entry_src_default_route.c)19
-rw-r--r--src/vnet/fib/fib_entry_src_interface.c3
-rw-r--r--src/vnet/fib/fib_entry_src_interpose.c15
-rw-r--r--src/vnet/fib/fib_entry_src_lisp.c5
-rw-r--r--src/vnet/fib/fib_entry_src_mpls.c2
-rwxr-xr-xsrc/vnet/fib/fib_entry_src_rr.c3
-rw-r--r--src/vnet/fib/fib_entry_src_simple.c77
-rw-r--r--src/vnet/fib/fib_entry_src_special.c82
-rw-r--r--src/vnet/fib/fib_source.c222
-rw-r--r--src/vnet/fib/fib_source.h302
-rw-r--r--src/vnet/fib/fib_table.c68
-rw-r--r--src/vnet/fib/fib_table.h11
-rw-r--r--src/vnet/fib/ip4_fib.c9
-rw-r--r--src/vnet/fib/ip6_fib.c7
-rw-r--r--src/vnet/fib/mpls_fib.c3
-rw-r--r--src/vnet/ip/ip6_ll_table.c2
-rw-r--r--test/test_fib.py18
40 files changed, 889 insertions, 441 deletions
diff --git a/src/plugins/gbp/gbp_endpoint.c b/src/plugins/gbp/gbp_endpoint.c
index 12865461d18..bef67770fd9 100644
--- a/src/plugins/gbp/gbp_endpoint.c
+++ b/src/plugins/gbp/gbp_endpoint.c
@@ -41,9 +41,10 @@ static const char *gbp_endpoint_attr_names[] = GBP_ENDPOINT_ATTR_NAMES;
*/
gbp_ep_db_t gbp_ep_db;
-fib_node_type_t gbp_endpoint_fib_type;
-
-vlib_log_class_t gbp_ep_logger;
+static fib_source_t gbp_fib_source_hi;
+static fib_source_t gbp_fib_source_low;
+static fib_node_type_t gbp_endpoint_fib_type;
+static vlib_log_class_t gbp_ep_logger;
#define GBP_ENDPOINT_DBG(...) \
vlib_log_debug (gbp_ep_logger, __VA_ARGS__);
@@ -588,10 +589,10 @@ gbb_endpoint_fwd_reset (gbp_endpoint_t * ge)
*/
if (gbp_endpoint_is_remote (ge))
{
- fib_table_entry_special_remove (fib_index, pfx, FIB_SOURCE_PLUGIN_HI);
+ fib_table_entry_special_remove (fib_index, pfx, gbp_fib_source_hi);
}
- fib_table_entry_delete (fib_index, pfx, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_entry_delete (fib_index, pfx, gbp_fib_source_low);
}
vec_foreach (ai, gef->gef_adjs)
{
@@ -726,7 +727,7 @@ gbb_endpoint_fwd_recalc (gbp_endpoint_t * ge)
}
fib_table_entry_path_add (fib_index, pfx,
- FIB_SOURCE_PLUGIN_LOW,
+ gbp_fib_source_low,
FIB_ENTRY_FLAG_NONE,
fib_proto_to_dpo (pfx->fp_proto),
&pfx->fp_addr, ip_sw_if_index,
@@ -759,7 +760,7 @@ gbb_endpoint_fwd_recalc (gbp_endpoint_t * ge)
gg->gg_sclass, ~0, &policy_dpo);
fib_table_entry_special_dpo_add (fib_index, pfx,
- FIB_SOURCE_PLUGIN_HI,
+ gbp_fib_source_hi,
FIB_ENTRY_FLAG_INTERPOSE,
&policy_dpo);
dpo_reset (&policy_dpo);
@@ -1576,6 +1577,12 @@ gbp_endpoint_init (vlib_main_t * vm)
gbp_ep_logger = vlib_log_register_class ("gbp", "ep");
gbp_endpoint_fib_type = fib_node_register_new_type (&gbp_endpoint_vft);
+ gbp_fib_source_hi = fib_source_allocate ("gbp-endpoint-hi",
+ FIB_SOURCE_PRIORITY_HI,
+ FIB_SOURCE_BH_SIMPLE);
+ gbp_fib_source_low = fib_source_allocate ("gbp-endpoint-low",
+ FIB_SOURCE_PRIORITY_LOW,
+ FIB_SOURCE_BH_SIMPLE);
return (NULL);
}
diff --git a/src/plugins/gbp/gbp_route_domain.c b/src/plugins/gbp/gbp_route_domain.c
index ab998591982..f0aa694d44a 100644
--- a/src/plugins/gbp/gbp_route_domain.c
+++ b/src/plugins/gbp/gbp_route_domain.c
@@ -53,6 +53,7 @@ typedef struct gbp_route_domain_db_t
} gbp_route_domain_db_t;
static gbp_route_domain_db_t gbp_route_domain_db;
+static fib_source_t gbp_fib_source;
/**
* logger
@@ -154,7 +155,7 @@ gbp_route_domain_add_and_lock (u32 rd_id,
grd->grd_fib_index[fproto] =
fib_table_find_or_create_and_lock (fproto,
grd->grd_table_id[fproto],
- FIB_SOURCE_PLUGIN_HI);
+ gbp_fib_source);
if (~0 != grd->grd_uu_sw_if_index[fproto])
{
@@ -221,8 +222,7 @@ gbp_route_domain_unlock (index_t index)
FOR_EACH_FIB_IP_PROTOCOL (fproto)
{
- fib_table_unlock (grd->grd_fib_index[fproto],
- fproto, FIB_SOURCE_PLUGIN_HI);
+ fib_table_unlock (grd->grd_fib_index[fproto], fproto, gbp_fib_source);
if (INDEX_INVALID != grd->grd_adj[fproto])
adj_unlock (grd->grd_adj[fproto]);
}
@@ -430,6 +430,9 @@ static clib_error_t *
gbp_route_domain_init (vlib_main_t * vm)
{
grd_logger = vlib_log_register_class ("gbp", "rd");
+ gbp_fib_source = fib_source_allocate ("gbp-rd",
+ FIB_SOURCE_PRIORITY_HI,
+ FIB_SOURCE_BH_DROP);
return (NULL);
}
diff --git a/src/plugins/gbp/gbp_subnet.c b/src/plugins/gbp/gbp_subnet.c
index bb069ffe892..2ef3fcfd534 100644
--- a/src/plugins/gbp/gbp_subnet.c
+++ b/src/plugins/gbp/gbp_subnet.c
@@ -65,6 +65,8 @@ uword *gbp_subnet_db;
*/
gbp_subnet_t *gbp_subnet_pool;
+static fib_source_t gbp_fib_source;
+
static index_t
gbp_subnet_db_find (u32 fib_index, const fib_prefix_t * pfx)
{
@@ -122,7 +124,7 @@ gbp_subnet_transport_add (gbp_subnet_t * gs)
gs->gs_fei = fib_table_entry_update_one_path (gs->gs_key->gsk_fib_index,
&gs->gs_key->gsk_pfx,
- FIB_SOURCE_PLUGIN_HI,
+ gbp_fib_source,
FIB_ENTRY_FLAG_NONE,
fib_proto_to_dpo (fproto),
&ADJ_BCAST_ADDR,
@@ -145,7 +147,7 @@ gbp_subnet_internal_add (gbp_subnet_t * gs)
gs->gs_fei = fib_table_entry_special_dpo_update (gs->gs_key->gsk_fib_index,
&gs->gs_key->gsk_pfx,
- FIB_SOURCE_PLUGIN_HI,
+ gbp_fib_source,
FIB_ENTRY_FLAG_EXCLUSIVE,
&gfd);
@@ -169,7 +171,7 @@ gbp_subnet_external_add (gbp_subnet_t * gs, u32 sw_if_index, sclass_t sclass)
gs->gs_fei = fib_table_entry_special_dpo_update (gs->gs_key->gsk_fib_index,
&gs->gs_key->gsk_pfx,
- FIB_SOURCE_PLUGIN_HI,
+ gbp_fib_source,
(FIB_ENTRY_FLAG_EXCLUSIVE |
FIB_ENTRY_FLAG_LOOSE_URPF_EXEMPT),
&gpd);
@@ -216,7 +218,7 @@ gbp_subnet_del_i (index_t gsi)
(GBP_SUBNET_L3_OUT == gs->gs_type
|| GBP_SUBNET_ANON_L3_OUT ==
gs->gs_type) ? FIB_SOURCE_SPECIAL :
- FIB_SOURCE_PLUGIN_HI);
+ gbp_fib_source);
gbp_subnet_db_del (gs);
gbp_route_domain_unlock (gs->gs_rd);
@@ -578,6 +580,9 @@ gbp_subnet_init (vlib_main_t * vm)
{
gbp_subnet_db = hash_create_mem (0,
sizeof (gbp_subnet_key_t), sizeof (u32));
+ gbp_fib_source = fib_source_allocate ("gbp-subnet",
+ FIB_SOURCE_PRIORITY_HI,
+ FIB_SOURCE_BH_SIMPLE);
return (NULL);
}
diff --git a/src/plugins/ila/ila.c b/src/plugins/ila/ila.c
index bac76151c28..162d417d772 100644
--- a/src/plugins/ila/ila.c
+++ b/src/plugins/ila/ila.c
@@ -68,6 +68,11 @@ static dpo_type_t ila_dpo_type;
*/
static fib_node_type_t ila_fib_node_type;
+/**
+ * FIB source for adding entries
+ */
+static fib_source_t ila_fib_src;
+
u8 *
format_half_ip6_address (u8 * s, va_list * va)
{
@@ -758,7 +763,7 @@ ila_add_del_entry (ila_add_del_entry_args_t * args)
fib_table_entry_special_dpo_add(0,
&pfx,
- FIB_SOURCE_PLUGIN_HI,
+ ila_fib_src,
FIB_ENTRY_FLAG_EXCLUSIVE,
&dpo);
dpo_reset(&dpo);
@@ -794,7 +799,7 @@ ila_add_del_entry (ila_add_del_entry_args_t * args)
.fp_proto = FIB_PROTOCOL_IP6,
};
- fib_table_entry_special_remove(0, &pfx, FIB_SOURCE_PLUGIN_HI);
+ fib_table_entry_special_remove(0, &pfx, ila_fib_src);
/*
* remove this ILA entry as child of the FIB netry for the next-hop
*/
@@ -935,7 +940,9 @@ ila_init (vlib_main_t * vm)
ila_dpo_type = dpo_register_new_type(&ila_vft, ila_nodes);
ila_fib_node_type = fib_node_register_new_type(&ila_fib_node_vft);
-
+ ila_fib_src = fib_source_allocate("ila",
+ FIB_SOURCE_PRIORITY_HI,
+ FIB_SOURCE_BH_SIMPLE);
return NULL;
}
diff --git a/src/plugins/lb/lb.c b/src/plugins/lb/lb.c
index b1e0b237478..4dbf134cc4f 100644
--- a/src/plugins/lb/lb.c
+++ b/src/plugins/lb/lb.c
@@ -26,6 +26,9 @@
//After so many seconds. It is assumed that inter-core race condition will not occur.
#define LB_CONCURRENCY_TIMEOUT 10
+// FIB source for adding routes
+static fib_source_t lb_fib_src;
+
lb_main_t lb_main;
#define lb_get_writer_lock() clib_spinlock_lock (&lb_main.writer_lock)
@@ -948,7 +951,7 @@ static void lb_vip_add_adjacency(lb_main_t *lbm, lb_vip_t *vip,
dpo_set(&dpo, dpo_type, proto, *vip_prefix_index);
fib_table_entry_special_dpo_add(0,
&pfx,
- FIB_SOURCE_PLUGIN_HI,
+ lb_fib_src,
FIB_ENTRY_FLAG_EXCLUSIVE,
&dpo);
dpo_reset(&dpo);
@@ -1037,7 +1040,7 @@ static void lb_vip_del_adjacency(lb_main_t *lbm, lb_vip_t *vip)
pfx.fp_len = vip->plen;
pfx.fp_proto = FIB_PROTOCOL_IP6;
}
- fib_table_entry_special_remove(0, &pfx, FIB_SOURCE_PLUGIN_HI);
+ fib_table_entry_special_remove(0, &pfx, lb_fib_src);
}
int lb_vip_add(lb_vip_add_args_t args, u32 *vip_index)
@@ -1445,6 +1448,11 @@ lb_init (vlib_main_t * vm)
#define _(a,b,c) lbm->vip_counters[c].name = b;
lb_foreach_vip_counter
#undef _
+
+ lb_fib_src = fib_source_allocate("lb",
+ FIB_SOURCE_PRIORITY_HI,
+ FIB_SOURCE_BH_SIMPLE);
+
return NULL;
}
diff --git a/src/plugins/nat/dslite.c b/src/plugins/nat/dslite.c
index 339c12c5656..d9a17293fac 100644
--- a/src/plugins/nat/dslite.c
+++ b/src/plugins/nat/dslite.c
@@ -109,7 +109,7 @@ dslite_set_aftr_ip6_addr (dslite_main_t * dm, ip6_address_t * addr)
.fp_len = 0,
.fp_addr.ip4.as_u32 = 0,
};
- fib_table_entry_special_dpo_add (0, &pfx, FIB_SOURCE_PLUGIN_HI,
+ fib_table_entry_special_dpo_add (0, &pfx, nat_fib_src_hi,
FIB_ENTRY_FLAG_EXCLUSIVE, &dpo);
}
else
@@ -121,7 +121,7 @@ dslite_set_aftr_ip6_addr (dslite_main_t * dm, ip6_address_t * addr)
.fp_addr.ip6.as_u64[0] = addr->as_u64[0],
.fp_addr.ip6.as_u64[1] = addr->as_u64[1],
};
- fib_table_entry_special_dpo_add (0, &pfx, FIB_SOURCE_PLUGIN_HI,
+ fib_table_entry_special_dpo_add (0, &pfx, nat_fib_src_hi,
FIB_ENTRY_FLAG_EXCLUSIVE, &dpo);
}
@@ -153,7 +153,7 @@ dslite_set_b4_ip6_addr (dslite_main_t * dm, ip6_address_t * addr)
.fp_addr.ip6.as_u64[0] = addr->as_u64[0],
.fp_addr.ip6.as_u64[1] = addr->as_u64[1],
};
- fib_table_entry_special_dpo_add (0, &pfx, FIB_SOURCE_PLUGIN_HI,
+ fib_table_entry_special_dpo_add (0, &pfx, nat_fib_src_hi,
FIB_ENTRY_FLAG_EXCLUSIVE, &dpo);
dpo_reset (&dpo);
@@ -218,7 +218,7 @@ dslite_add_del_pool_addr (dslite_main_t * dm, ip4_address_t * addr, u8 is_add)
foreach_snat_protocol
#undef _
dslite_dpo_create (DPO_PROTO_IP4, 0, &dpo_v4);
- fib_table_entry_special_dpo_add (0, &pfx, FIB_SOURCE_PLUGIN_HI,
+ fib_table_entry_special_dpo_add (0, &pfx, nat_fib_src_hi,
FIB_ENTRY_FLAG_EXCLUSIVE, &dpo_v4);
dpo_reset (&dpo_v4);
}
@@ -231,7 +231,7 @@ dslite_add_del_pool_addr (dslite_main_t * dm, ip4_address_t * addr, u8 is_add)
vec_free (a->busy_##n##_ports_per_thread);
foreach_snat_protocol
#undef _
- fib_table_entry_special_remove (0, &pfx, FIB_SOURCE_PLUGIN_HI);
+ fib_table_entry_special_remove (0, &pfx, nat_fib_src_hi);
vec_del1 (dm->addr_pool, i);
}
return 0;
diff --git a/src/plugins/nat/nat.c b/src/plugins/nat/nat.c
index 0a30caf0f21..d7133684b32 100755
--- a/src/plugins/nat/nat.c
+++ b/src/plugins/nat/nat.c
@@ -38,6 +38,9 @@
snat_main_t snat_main;
+fib_source_t nat_fib_src_hi;
+fib_source_t nat_fib_src_low;
+
/* *INDENT-OFF* */
/* Hook up input features */
VNET_FEATURE_INIT (nat_pre_in2out, static) = {
@@ -536,7 +539,7 @@ snat_add_del_addr_to_fib (ip4_address_t * addr, u8 p_len, u32 sw_if_index,
if (is_add)
fib_table_entry_update_one_path (fib_index,
&prefix,
- FIB_SOURCE_PLUGIN_LOW,
+ nat_fib_src_low,
(FIB_ENTRY_FLAG_CONNECTED |
FIB_ENTRY_FLAG_LOCAL |
FIB_ENTRY_FLAG_EXCLUSIVE),
@@ -545,7 +548,7 @@ snat_add_del_addr_to_fib (ip4_address_t * addr, u8 p_len, u32 sw_if_index,
sw_if_index,
~0, 1, NULL, FIB_ROUTE_PATH_FLAG_NONE);
else
- fib_table_entry_delete (fib_index, &prefix, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_entry_delete (fib_index, &prefix, nat_fib_src_low);
}
int
@@ -577,7 +580,7 @@ snat_add_address (snat_main_t * sm, ip4_address_t * addr, u32 vrf_id,
if (vrf_id != ~0)
ap->fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP4, vrf_id,
- FIB_SOURCE_PLUGIN_LOW);
+ nat_fib_src_low);
else
ap->fib_index = ~0;
#define _(N, i, n, s) \
@@ -813,7 +816,7 @@ snat_add_static_mapping (ip4_address_t l_addr, ip4_address_t e_addr,
local->vrf_id = vrf_id;
local->fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP4, vrf_id,
- FIB_SOURCE_PLUGIN_LOW);
+ nat_fib_src_low);
m_key.addr = m->local_addr;
m_key.port = m->local_port;
m_key.protocol = m->proto;
@@ -834,13 +837,13 @@ snat_add_static_mapping (ip4_address_t l_addr, ip4_address_t e_addr,
if (vrf_id != ~0)
fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP4, vrf_id,
- FIB_SOURCE_PLUGIN_LOW);
+ nat_fib_src_low);
/* If not specified use inside VRF id from SNAT plugin startup config */
else
{
fib_index = sm->inside_fib_index;
vrf_id = sm->inside_vrf_id;
- fib_table_lock (fib_index, FIB_PROTOCOL_IP4, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_lock (fib_index, FIB_PROTOCOL_IP4, nat_fib_src_low);
}
if (!(out2in_only || identity_nat))
@@ -1133,7 +1136,7 @@ snat_add_static_mapping (ip4_address_t l_addr, ip4_address_t e_addr,
}
}
- fib_table_unlock (fib_index, FIB_PROTOCOL_IP4, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_unlock (fib_index, FIB_PROTOCOL_IP4, nat_fib_src_low);
if (pool_elts (m->locals))
return 0;
@@ -1291,7 +1294,7 @@ nat44_add_del_lb_static_mapping (ip4_address_t e_addr, u16 e_port,
locals[i].fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP4,
locals[i].vrf_id,
- FIB_SOURCE_PLUGIN_LOW);
+ nat_fib_src_low);
m_key.addr = locals[i].addr;
m_key.fib_index = locals[i].fib_index;
if (!out2in_only)
@@ -1381,7 +1384,7 @@ nat44_add_del_lb_static_mapping (ip4_address_t e_addr, u16 e_port,
pool_foreach (local, m->locals,
({
fib_table_unlock (local->fib_index, FIB_PROTOCOL_IP4,
- FIB_SOURCE_PLUGIN_LOW);
+ nat_fib_src_low);
m_key.addr = local->addr;
if (!out2in_only)
{
@@ -1514,7 +1517,7 @@ nat44_lb_static_mapping_add_del_local (ip4_address_t e_addr, u16 e_port,
local->vrf_id = vrf_id;
local->fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP4, vrf_id,
- FIB_SOURCE_PLUGIN_LOW);
+ nat_fib_src_low);
if (!is_out2in_only_static_mapping (m))
{
@@ -1536,7 +1539,7 @@ nat44_lb_static_mapping_add_del_local (ip4_address_t e_addr, u16 e_port,
return VNET_API_ERROR_UNSPECIFIED;
fib_table_unlock (match_local->fib_index, FIB_PROTOCOL_IP4,
- FIB_SOURCE_PLUGIN_LOW);
+ nat_fib_src_low);
if (!is_out2in_only_static_mapping (m))
{
@@ -1687,7 +1690,7 @@ snat_del_address (snat_main_t * sm, ip4_address_t addr, u8 delete_sm,
}
if (a->fib_index != ~0)
- fib_table_unlock (a->fib_index, FIB_PROTOCOL_IP4, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_unlock (a->fib_index, FIB_PROTOCOL_IP4, nat_fib_src_low);
/* Delete sessions using address */
if (a->busy_tcp_ports || a->busy_udp_ports || a->busy_icmp_ports)
@@ -2464,6 +2467,13 @@ snat_init (vlib_main_t * vm)
};
vec_add1 (ip4_main.table_bind_callbacks, cbt4);
+ nat_fib_src_hi = fib_source_allocate ("nat-hi",
+ FIB_SOURCE_PRIORITY_HI,
+ FIB_SOURCE_BH_SIMPLE);
+ nat_fib_src_low = fib_source_allocate ("nat-low",
+ FIB_SOURCE_PRIORITY_LOW,
+ FIB_SOURCE_BH_SIMPLE);
+
/* Init virtual fragmenentation reassembly */
return nat_reass_init (vm);
}
@@ -2915,13 +2925,13 @@ nat44_add_del_address_dpo (ip4_address_t addr, u8 is_add)
if (is_add)
{
nat_dpo_create (DPO_PROTO_IP4, 0, &dpo_v4);
- fib_table_entry_special_dpo_add (0, &pfx, FIB_SOURCE_PLUGIN_HI,
+ fib_table_entry_special_dpo_add (0, &pfx, nat_fib_src_hi,
FIB_ENTRY_FLAG_EXCLUSIVE, &dpo_v4);
dpo_reset (&dpo_v4);
}
else
{
- fib_table_entry_special_remove (0, &pfx, FIB_SOURCE_PLUGIN_HI);
+ fib_table_entry_special_remove (0, &pfx, nat_fib_src_hi);
}
}
@@ -3836,15 +3846,15 @@ snat_config (vlib_main_t * vm, unformat_input_t * input)
sm->outside_vrf_id = outside_vrf_id;
sm->outside_fib_index = fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP4,
outside_vrf_id,
- FIB_SOURCE_PLUGIN_HI);
+ nat_fib_src_hi);
nm->outside_vrf_id = outside_ip6_vrf_id;
nm->outside_fib_index = fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP6,
outside_ip6_vrf_id,
- FIB_SOURCE_PLUGIN_HI);
+ nat_fib_src_hi);
sm->inside_vrf_id = inside_vrf_id;
sm->inside_fib_index = fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP4,
inside_vrf_id,
- FIB_SOURCE_PLUGIN_HI);
+ nat_fib_src_hi);
sm->static_mapping_only = static_mapping_only;
sm->static_mapping_connection_tracking = static_mapping_connection_tracking;
diff --git a/src/plugins/nat/nat.h b/src/plugins/nat/nat.h
index b65ad1b676f..ee712f4748f 100644
--- a/src/plugins/nat/nat.h
+++ b/src/plugins/nat/nat.h
@@ -23,6 +23,7 @@
#include <vnet/ethernet/ethernet.h>
#include <vnet/ip/icmp46_packet.h>
#include <vnet/api_errno.h>
+#include <vnet/fib/fib_source.h>
#include <vppinfra/elog.h>
#include <vppinfra/bihash_8_8.h>
#include <vppinfra/bihash_16_8.h>
@@ -742,6 +743,9 @@ extern vlib_node_registration_t nat44_ed_in2out_worker_handoff_node;
extern vlib_node_registration_t nat44_ed_in2out_output_worker_handoff_node;
extern vlib_node_registration_t nat44_ed_out2in_worker_handoff_node;
+extern fib_source_t nat_fib_src_hi;
+extern fib_source_t nat_fib_src_low;
+
/* format functions */
format_function_t format_snat_user;
format_function_t format_snat_static_mapping;
diff --git a/src/plugins/nat/nat64.c b/src/plugins/nat/nat64.c
index 0fe29800420..e1afea6510e 100644
--- a/src/plugins/nat/nat64.c
+++ b/src/plugins/nat/nat64.c
@@ -343,7 +343,7 @@ nat64_add_del_pool_addr (u32 thread_index,
if (vrf_id != ~0)
a->fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP6, vrf_id,
- FIB_SOURCE_PLUGIN_HI);
+ nat_fib_src_hi);
#define _(N, id, n, s) \
clib_bitmap_alloc (a->busy_##n##_port_bitmap, 65535); \
a->busy_##n##_ports = 0; \
@@ -357,8 +357,7 @@ nat64_add_del_pool_addr (u32 thread_index,
return VNET_API_ERROR_NO_SUCH_ENTRY;
if (a->fib_index != ~0)
- fib_table_unlock (a->fib_index, FIB_PROTOCOL_IP6,
- FIB_SOURCE_PLUGIN_HI);
+ fib_table_unlock (a->fib_index, FIB_PROTOCOL_IP6, nat_fib_src_hi);
/* Delete sessions using address */
/* *INDENT-OFF* */
vec_foreach (db, nm->db)
@@ -688,7 +687,7 @@ nat64_add_del_static_bib_entry (ip6_address_t * in_addr,
nat64_main_t *nm = &nat64_main;
nat64_db_bib_entry_t *bibe;
u32 fib_index = fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP6, vrf_id,
- FIB_SOURCE_PLUGIN_HI);
+ nat_fib_src_hi);
snat_protocol_t p = ip_proto_to_snat_proto (proto);
ip46_address_t addr;
int i;
@@ -1027,7 +1026,7 @@ nat64_add_del_prefix (ip6_address_t * prefix, u8 plen, u32 vrf_id, u8 is_add)
vec_add2 (nm->pref64, p, 1);
p->fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP6, vrf_id,
- FIB_SOURCE_PLUGIN_HI);
+ nat_fib_src_hi);
p->vrf_id = vrf_id;
}
diff --git a/src/plugins/nat/nat64_cli.c b/src/plugins/nat/nat64_cli.c
index 53152f11996..be468df1753 100644
--- a/src/plugins/nat/nat64_cli.c
+++ b/src/plugins/nat/nat64_cli.c
@@ -633,9 +633,9 @@ nat64_add_del_prefix_command_fn (vlib_main_t * vm, unformat_input_t * input,
{
fib_index =
fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP6,
- vrf_id, FIB_SOURCE_PLUGIN_HI);
+ vrf_id, nat_fib_src_hi);
fib_table_entry_update_one_path (fib_index, &fibpfx,
- FIB_SOURCE_PLUGIN_HI,
+ nat_fib_src_hi,
FIB_ENTRY_FLAG_NONE,
DPO_PROTO_IP6, NULL,
sw_if_index, ~0, 0,
@@ -645,12 +645,11 @@ nat64_add_del_prefix_command_fn (vlib_main_t * vm, unformat_input_t * input,
{
fib_index = fib_table_find (FIB_PROTOCOL_IP6, vrf_id);
fib_table_entry_path_remove (fib_index, &fibpfx,
- FIB_SOURCE_PLUGIN_HI,
+ nat_fib_src_hi,
DPO_PROTO_IP6, NULL,
sw_if_index, ~0, 1,
FIB_ROUTE_PATH_INTF_RX);
- fib_table_unlock (fib_index, FIB_PROTOCOL_IP6,
- FIB_SOURCE_PLUGIN_HI);
+ fib_table_unlock (fib_index, FIB_PROTOCOL_IP6, nat_fib_src_hi);
}
}
diff --git a/src/plugins/nat/nat66.c b/src/plugins/nat/nat66.c
index 2caefab6480..e5e783b31f7 100644
--- a/src/plugins/nat/nat66.c
+++ b/src/plugins/nat/nat66.c
@@ -170,7 +170,7 @@ nat66_static_mapping_add_del (ip6_address_t * l_addr, ip6_address_t * e_addr,
return VNET_API_ERROR_VALUE_EXIST;
fib_index = fib_table_find_or_create_and_lock (FIB_PROTOCOL_IP6, vrf_id,
- FIB_SOURCE_PLUGIN_HI);
+ nat_fib_src_hi);
pool_get (nm->sm, sm);
clib_memset (sm, 0, sizeof (*sm));
sm->l_addr.as_u64[0] = l_addr->as_u64[0];
@@ -214,8 +214,7 @@ nat66_static_mapping_add_del (ip6_address_t * l_addr, ip6_address_t * e_addr,
kv.key[2] = sm_key.as_u64[2];
if (clib_bihash_add_del_24_8 (&nm->sm_e, &kv, 0))
nat_elog_warn ("nat66-static-map-by-external delete key failed");
- fib_table_unlock (sm->fib_index, FIB_PROTOCOL_IP6,
- FIB_SOURCE_PLUGIN_HI);
+ fib_table_unlock (sm->fib_index, FIB_PROTOCOL_IP6, nat_fib_src_hi);
pool_put (nm->sm, sm);
}
diff --git a/src/plugins/pppoe/pppoe.c b/src/plugins/pppoe/pppoe.c
index 2d63b3e8674..1f8a7288aeb 100644
--- a/src/plugins/pppoe/pppoe.c
+++ b/src/plugins/pppoe/pppoe.c
@@ -37,6 +37,8 @@
pppoe_main_t pppoe_main;
+static fib_source_t pppoe_fib_src;
+
u8 *
format_pppoe_session (u8 * s, va_list * args)
{
@@ -376,7 +378,7 @@ int vnet_pppoe_add_del_session
/* add reverse route for client ip */
fib_table_entry_path_add (a->decap_fib_index, &pfx,
- FIB_SOURCE_PLUGIN_HI, FIB_ENTRY_FLAG_NONE,
+ pppoe_fib_src, FIB_ENTRY_FLAG_NONE,
fib_proto_to_dpo (pfx.fp_proto),
&pfx.fp_addr, sw_if_index, ~0,
1, NULL, FIB_ROUTE_PATH_FLAG_NONE);
@@ -408,7 +410,7 @@ int vnet_pppoe_add_del_session
/* delete reverse route for client ip */
fib_table_entry_path_remove (a->decap_fib_index, &pfx,
- FIB_SOURCE_PLUGIN_HI,
+ pppoe_fib_src,
fib_proto_to_dpo (pfx.fp_proto),
&pfx.fp_addr,
sw_if_index, ~0, 1,
@@ -721,6 +723,10 @@ pppoe_init (vlib_main_t * vm)
ethernet_register_input_type (vm, ETHERNET_TYPE_PPPOE_DISCOVERY,
pppoe_cp_dispatch_node.index);
+ pppoe_fib_src = fib_source_allocate ("pppoe",
+ FIB_SOURCE_PRIORITY_HI,
+ FIB_SOURCE_BH_API);
+
return 0;
}
diff --git a/src/plugins/svs/svs.c b/src/plugins/svs/svs.c
index 8c1487c6ebc..555283397ff 100644
--- a/src/plugins/svs/svs.c
+++ b/src/plugins/svs/svs.c
@@ -26,10 +26,12 @@
u32 *svs_itf_db[FIB_PROTOCOL_IP_MAX];
+static fib_source_t svs_fib_src;
+
int
svs_table_add (fib_protocol_t fproto, u32 table_id)
{
- fib_table_find_or_create_and_lock (fproto, table_id, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_find_or_create_and_lock (fproto, table_id, svs_fib_src);
return (0);
}
@@ -50,7 +52,7 @@ svs_table_delete (fib_protocol_t fproto, u32 table_id)
if (~0 == fib_index)
return VNET_API_ERROR_NO_SUCH_FIB;
- fib_table_unlock (fib_index, fproto, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_unlock (fib_index, fproto, svs_fib_src);
return (0);
}
@@ -68,7 +70,7 @@ svs_route_add_i (u32 fib_index, const fib_prefix_t * pfx, u32 src_fib_index)
LOOKUP_TABLE_FROM_CONFIG, &dpo);
fib_table_entry_special_dpo_add (fib_index, pfx,
- FIB_SOURCE_PLUGIN_LOW,
+ svs_fib_src,
FIB_ENTRY_FLAG_EXCLUSIVE, &dpo);
dpo_unlock (&dpo);
@@ -107,7 +109,7 @@ svs_route_delete (u32 table_id, const fib_prefix_t * pfx)
if (~0 == fib_index)
return VNET_API_ERROR_NO_SUCH_FIB;
- fib_table_entry_special_remove (fib_index, pfx, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_entry_special_remove (fib_index, pfx, svs_fib_src);
return (0);
}
@@ -214,7 +216,7 @@ svs_disable (fib_protocol_t fproto, u32 table_id, u32 sw_if_index)
"svs-ip4" :
"svs-ip6"), sw_if_index, 0, NULL, 0);
- fib_table_entry_special_remove (fib_index, &pfx, FIB_SOURCE_PLUGIN_LOW);
+ fib_table_entry_special_remove (fib_index, &pfx, svs_fib_src);
return (0);
}
@@ -607,6 +609,10 @@ svs_init (vlib_main_t * vm)
};
vec_add1 (ip4_main.table_bind_callbacks, cbt4);
+ svs_fib_src = fib_source_allocate ("svs",
+ FIB_SOURCE_PRIORITY_LOW,
+ FIB_SOURCE_BH_SIMPLE);
+
return (NULL);
}
diff --git a/src/plugins/unittest/fib_test.c b/src/plugins/unittest/fib_test.c
index f220eb0d358..2d75f28a8ca 100644
--- a/src/plugins/unittest/fib_test.c
+++ b/src/plugins/unittest/fib_test.c
@@ -9310,13 +9310,16 @@ fib_test_inherit (void)
"%U via 10.10.10.2",
format_fib_prefix, &pfx_10_10_10_0_s_24);
+ fib_source_t hi_src = fib_source_allocate("test", 0x50,
+ FIB_SOURCE_BH_SIMPLE);
+
/*
* add the source that replaces inherited state.
* inheriting source is not the best, so it doesn't push state.
*/
fib_table_entry_update_one_path(0,
&pfx_10_10_10_0_s_24,
- FIB_SOURCE_PLUGIN_HI,
+ hi_src,
FIB_ENTRY_FLAG_NONE,
DPO_PROTO_IP4,
&nh_10_10_10_1,
@@ -9354,7 +9357,7 @@ fib_test_inherit (void)
* withdraw the higher priority source and expect the inherited to return
* throughout the sub-tree
*/
- fib_table_entry_delete(0, &pfx_10_10_10_0_s_24, FIB_SOURCE_PLUGIN_HI);
+ fib_table_entry_delete(0, &pfx_10_10_10_0_s_24, hi_src);
fei = fib_table_lookup_exact_match(0, &pfx_10_10_10_21_s_32);
FIB_TEST(!fib_test_validate_entry(fei,
diff --git a/src/vnet/CMakeLists.txt b/src/vnet/CMakeLists.txt
index 11827734a60..21653ab7c7a 100644
--- a/src/vnet/CMakeLists.txt
+++ b/src/vnet/CMakeLists.txt
@@ -1248,21 +1248,22 @@ list(APPEND VNET_SOURCES
fib/fib_node_list.c
fib/fib_entry.c
fib/fib_entry_src.c
- fib/fib_entry_src_rr.c
+ fib/fib_entry_src_adj.c
+ fib/fib_entry_src_api.c
+ fib/fib_entry_src_drop.c
fib/fib_entry_src_interface.c
fib/fib_entry_src_interpose.c
- fib/fib_entry_src_default_route.c
- fib/fib_entry_src_special.c
- fib/fib_entry_src_api.c
- fib/fib_entry_src_adj.c
- fib/fib_entry_src_mpls.c
fib/fib_entry_src_lisp.c
+ fib/fib_entry_src_mpls.c
+ fib/fib_entry_src_simple.c
+ fib/fib_entry_src_rr.c
fib/fib_entry_cover.c
fib/fib_entry_delegate.c
fib/fib_entry_track.c
fib/fib_path_list.c
fib/fib_path.c
fib/fib_path_ext.c
+ fib/fib_source.c
fib/fib_urpf_list.c
fib/fib_attached_export.c
fib/fib_api.c
@@ -1280,6 +1281,7 @@ list(APPEND VNET_HEADERS
fib/fib_node_list.h
fib/fib_entry.h
fib/fib_entry_delegate.h
+ fib/fib_source.h
)
list(APPEND VNET_API_FILES fib/fib_types.api)
diff --git a/src/vnet/fib/fib.c b/src/vnet/fib/fib.c
index 28e18dded23..ddfa830bb0f 100644
--- a/src/vnet/fib/fib.c
+++ b/src/vnet/fib/fib.c
@@ -22,6 +22,7 @@
static clib_error_t *
fib_module_init (vlib_main_t * vm)
{
+ fib_source_module_init();
fib_entry_module_init();
fib_entry_src_module_init();
fib_path_module_init();
diff --git a/src/vnet/fib/fib_entry.c b/src/vnet/fib/fib_entry.c
index fd69db989f2..0e5482840bf 100644
--- a/src/vnet/fib/fib_entry.c
+++ b/src/vnet/fib/fib_entry.c
@@ -34,7 +34,6 @@
/*
* Array of strings/names for the FIB sources
*/
-static const char *fib_source_names[] = FIB_SOURCES;
static const char *fib_attribute_names[] = FIB_ENTRY_ATTRIBUTES;
static const char *fib_src_attribute_names[] = FIB_ENTRY_SRC_ATTRIBUTES;
@@ -98,16 +97,6 @@ fib_entry_get_default_chain_type (const fib_entry_t *fib_entry)
}
u8 *
-format_fib_source (u8 * s, va_list * args)
-{
- fib_source_t source = va_arg (*args, int);
-
- s = format (s, "src:%s", fib_source_names[source]);
-
- return (s);
-}
-
-u8 *
format_fib_entry_flags (u8 *s, va_list *args)
{
fib_entry_attribute_t attr;
@@ -285,7 +274,7 @@ fib_entry_src_get_source (const fib_entry_src_t *esrc)
{
return (esrc->fes_src);
}
- return (FIB_SOURCE_MAX);
+ return (FIB_SOURCE_INVALID);
}
static fib_entry_flag_t
@@ -836,16 +825,17 @@ fib_entry_source_change_w_flags (fib_entry_t *fib_entry,
fib_entry_flag_t old_flags,
fib_source_t new_source)
{
- if (new_source < old_source)
+ switch (fib_source_cmp(new_source, old_source))
{
+ case FIB_SOURCE_CMP_BETTER:
/*
* we have a new winning source.
*/
fib_entry_src_action_deactivate(fib_entry, old_source);
fib_entry_src_action_activate(fib_entry, new_source);
- }
- else if (new_source > old_source)
- {
+ break;
+
+ case FIB_SOURCE_CMP_WORSE:
/*
* the new source loses. Re-activate the winning sources
* in case it is an interposer and hence relied on the losing
@@ -853,15 +843,15 @@ fib_entry_source_change_w_flags (fib_entry_t *fib_entry,
*/
fib_entry_src_action_reactivate(fib_entry, old_source);
return;
- }
- else
- {
+
+ case FIB_SOURCE_CMP_EQUAL:
/*
* the new source is one this entry already has.
* But the path-list was updated, which will contribute new forwarding,
* so install it.
*/
fib_entry_src_action_reactivate(fib_entry, new_source);
+ break;
}
fib_entry_post_update_actions(fib_entry, new_source, old_flags);
@@ -984,7 +974,7 @@ fib_entry_source_removed (fib_entry_t *fib_entry,
bsrc = fib_entry_get_best_src_i(fib_entry);
best_source = fib_entry_src_get_source(bsrc);
- if (FIB_SOURCE_MAX == best_source)
+ if (FIB_SOURCE_INVALID == best_source)
{
/*
* no more sources left. this entry is toast.
@@ -1040,16 +1030,16 @@ fib_entry_path_remove (fib_node_index_t fib_entry_index,
* then we need to create a new one. else we are updating
* an existing.
*/
- if (source < best_source)
+ switch (fib_source_cmp(source, best_source))
{
+ case FIB_SOURCE_CMP_BETTER:
/*
* Que! removing a path from a source that is better than the
* one this entry is using.
*/
ASSERT(0);
- }
- else if (source > best_source )
- {
+ break;
+ case FIB_SOURCE_CMP_WORSE:
/*
* the source is not the best. no need to update forwarding
*/
@@ -1067,10 +1057,9 @@ fib_entry_path_remove (fib_node_index_t fib_entry_index,
* that remain are non-inherited
*/
return (fib_entry_src_burn_only_inherited(fib_entry));
- }
- }
- else
- {
+ }
+ break;
+ case FIB_SOURCE_CMP_EQUAL:
/*
* removing a path from the path-list we were using.
*/
@@ -1089,6 +1078,7 @@ fib_entry_path_remove (fib_node_index_t fib_entry_index,
*/
fib_entry_src_action_reactivate(fib_entry, source);
}
+ break;
}
fib_entry_post_update_actions(fib_entry, source, bflags);
@@ -1131,16 +1121,17 @@ fib_entry_special_remove (fib_node_index_t fib_entry_index,
* then we need to create a new one. else we are updating
* an existing.
*/
- if (source < best_source )
+ switch (fib_source_cmp(source, best_source))
{
+ case FIB_SOURCE_CMP_BETTER:
/*
* Que! removing a path from a source that is better than the
* one this entry is using. This can only mean it is a source
* this prefix does not have.
*/
return (FIB_ENTRY_SRC_FLAG_ADDED);
- }
- else if (source > best_source ) {
+
+ case FIB_SOURCE_CMP_WORSE:
/*
* the source is not the best. no need to update forwarding
*/
@@ -1174,9 +1165,9 @@ fib_entry_special_remove (fib_node_index_t fib_entry_index,
return (FIB_ENTRY_SRC_FLAG_ADDED);
}
- }
- else
- {
+ break;
+
+ case FIB_SOURCE_CMP_EQUAL:
if (!(FIB_ENTRY_SRC_FLAG_ADDED & sflag))
{
/*
@@ -1191,6 +1182,7 @@ fib_entry_special_remove (fib_node_index_t fib_entry_index,
*/
fib_entry_src_action_reactivate(fib_entry, source);
}
+ break;
}
fib_entry_post_update_actions(fib_entry, source, bflags);
diff --git a/src/vnet/fib/fib_entry.h b/src/vnet/fib/fib_entry.h
index f0e6e8d8aae..b97c80fd8bf 100644
--- a/src/vnet/fib/fib_entry.h
+++ b/src/vnet/fib/fib_entry.h
@@ -17,6 +17,7 @@
#define __FIB_ENTRY_H__
#include <vnet/fib/fib_node.h>
+#include <vnet/fib/fib_source.h>
#include <vnet/adj/adj.h>
#include <vnet/ip/ip.h>
#include <vnet/dpo/dpo.h>
@@ -26,176 +27,6 @@
* The sources are defined here with their relative priority order.
* The lower the value the higher the priority
*/
-typedef enum fib_source_t_ {
- /**
- * An invalid source
- * This is not a real source, so don't use it to source a prefix.
- * It exists here to provide a value for inexistant/uninitialized source
- */
- FIB_SOURCE_INVALID = 0,
- /**
- * Marker. Add new values after this one.
- */
- FIB_SOURCE_FIRST,
- /**
- * Special sources. These are for entries that are added to all
- * FIBs by default, and should never be over-ridden (hence they
- * are the highest priority)
- */
- FIB_SOURCE_SPECIAL = FIB_SOURCE_FIRST,
- /**
- * Classify. A route that links directly to a classify adj
- */
- FIB_SOURCE_CLASSIFY,
- /**
- * A route the is being 'proxied' on behalf of another device
- */
- FIB_SOURCE_PROXY,
- /**
- * Route added as a result of interface configuration.
- * this will also come from the API/CLI, but the distinction is
- * that is from confiiguration on an interface, not a 'ip route' command
- */
- FIB_SOURCE_INTERFACE,
- /**
- * SRv6 and SR-MPLS
- */
- FIB_SOURCE_SR,
- /**
- * A high priority source a plugin can use
- */
- FIB_SOURCE_PLUGIN_HI,
- /**
- * From the BIER subsystem
- */
- FIB_SOURCE_BIER,
- /**
- * From 6RD.
- */
- FIB_SOURCE_6RD,
- /**
- * From the control plane API
- */
- FIB_SOURCE_API,
- /**
- * From the CLI.
- */
- FIB_SOURCE_CLI,
- /**
- * A low (below routing) priority source a plugin can use
- */
- FIB_SOURCE_PLUGIN_LOW,
- /**
- * LISP
- */
- FIB_SOURCE_LISP,
- /**
- * IPv[46] Mapping
- */
- FIB_SOURCE_MAP,
- /**
- * DHCP
- */
- FIB_SOURCE_DHCP,
- /**
- * IPv6 Proxy ND
- */
- FIB_SOURCE_IP6_ND_PROXY,
- /**
- * IPv6 ND (seen in the link-local tables)
- */
- FIB_SOURCE_IP6_ND,
- /**
- * Adjacency source.
- * routes created as a result of ARP/ND entries. This is lower priority
- * then the API/CLI. This is on purpose. trust me.
- */
- FIB_SOURCE_ADJ,
- /**
- * MPLS label. The prefix has been assigned a local label. This source
- * never provides forwarding information, instead it acts as a place-holder
- * so the association of label to prefix can be maintained
- */
- FIB_SOURCE_MPLS,
- /**
- * Attached Export source.
- * routes created as a result of attahced export. routes thus sourced
- * will be present in the export tables
- */
- FIB_SOURCE_AE,
- /**
- * Recursive resolution source.
- * Used to install an entry that is the resolution traget of another.
- */
- FIB_SOURCE_RR,
- /**
- * uRPF bypass/exemption.
- * Used to install an entry that is exempt from the loose uRPF check
- */
- FIB_SOURCE_URPF_EXEMPT,
- /**
- * The default route source.
- * The default route is always added to the FIB table (like the
- * special sources) but we need to be able to over-ride it with
- * 'ip route' sources when provided
- */
- FIB_SOURCE_DEFAULT_ROUTE,
- /**
- * The interpose source.
- * This is not a real source, so don't use it to source a prefix.
- * It exists here to provide a value against which to register to the
- * VFT for providing the interpose actions to a real source.
- */
- FIB_SOURCE_INTERPOSE,
- /**
- * Marker. add new entries before this one.
- */
- FIB_SOURCE_LAST = FIB_SOURCE_INTERPOSE,
-} __attribute__ ((packed)) fib_source_t;
-
-STATIC_ASSERT (sizeof(fib_source_t) == 1,
- "FIB too many sources");
-
-/**
- * The maximum number of sources
- */
-#define FIB_SOURCE_MAX (FIB_SOURCE_LAST+1)
-
-#define FIB_SOURCES { \
- [FIB_SOURCE_INVALID] = "invalid", \
- [FIB_SOURCE_SPECIAL] = "special", \
- [FIB_SOURCE_INTERFACE] = "interface", \
- [FIB_SOURCE_PROXY] = "proxy", \
- [FIB_SOURCE_BIER] = "BIER", \
- [FIB_SOURCE_6RD] = "6RD", \
- [FIB_SOURCE_API] = "API", \
- [FIB_SOURCE_CLI] = "CLI", \
- [FIB_SOURCE_ADJ] = "adjacency", \
- [FIB_SOURCE_MAP] = "MAP", \
- [FIB_SOURCE_SR] = "SR", \
- [FIB_SOURCE_LISP] = "LISP", \
- [FIB_SOURCE_CLASSIFY] = "classify", \
- [FIB_SOURCE_DHCP] = "DHCP", \
- [FIB_SOURCE_IP6_ND_PROXY] = "IPv6-proxy-nd", \
- [FIB_SOURCE_IP6_ND] = "IPv6-nd", \
- [FIB_SOURCE_RR] = "recursive-resolution", \
- [FIB_SOURCE_AE] = "attached_export", \
- [FIB_SOURCE_MPLS] = "mpls", \
- [FIB_SOURCE_URPF_EXEMPT] = "urpf-exempt", \
- [FIB_SOURCE_DEFAULT_ROUTE] = "default-route", \
- [FIB_SOURCE_PLUGIN_HI] = "plugin-hi", \
- [FIB_SOURCE_PLUGIN_LOW] = "plugin-low", \
- [FIB_SOURCE_INTERPOSE] = "interpose", \
-}
-
-#define FOR_EACH_FIB_SOURCE(_item) \
- for (_item = FIB_SOURCE_FIRST; _item < FIB_SOURCE_MAX; _item++)
-
-/**
- * The different sources that can create a route.
- * The sources are defined here with their relative priority order.
- * The lower the value the higher the priority
- */
typedef enum fib_entry_attribute_t_ {
/**
* Marker. Add new values after this one.
diff --git a/src/vnet/fib/fib_entry_src.c b/src/vnet/fib/fib_entry_src.c
index 176818abc0a..d534135d330 100644
--- a/src/vnet/fib/fib_entry_src.c
+++ b/src/vnet/fib/fib_entry_src.c
@@ -28,7 +28,7 @@
/*
* per-source type vft
*/
-static fib_entry_src_vft_t fib_entry_src_vft[FIB_SOURCE_MAX];
+static fib_entry_src_vft_t fib_entry_src_bh_vft[FIB_SOURCE_BH_MAX];
/**
* Get the VFT for a given source. This is a combination of the source
@@ -37,12 +37,16 @@ static fib_entry_src_vft_t fib_entry_src_vft[FIB_SOURCE_MAX];
const fib_entry_src_vft_t*
fib_entry_src_get_vft (const fib_entry_src_t *esrc)
{
+ fib_source_behaviour_t bh;
+
+ bh = fib_source_get_behaviour(esrc->fes_src);
+
if (esrc->fes_entry_flags & FIB_ENTRY_FLAG_INTERPOSE)
{
- return (&fib_entry_src_vft[FIB_SOURCE_INTERPOSE]);
+ return (&fib_entry_src_bh_vft[FIB_SOURCE_BH_INTERPOSE]);
}
- return (&fib_entry_src_vft[esrc->fes_src]);
+ return (&fib_entry_src_bh_vft[bh]);
}
static void
@@ -54,14 +58,14 @@ fib_entry_src_copy_default (const fib_entry_src_t *orig_src,
}
void
-fib_entry_src_register (fib_source_t source,
- const fib_entry_src_vft_t *vft)
+fib_entry_src_behaviour_register (fib_source_behaviour_t bh,
+ const fib_entry_src_vft_t *vft)
{
- fib_entry_src_vft[source] = *vft;
+ fib_entry_src_bh_vft[bh] = *vft;
- if (NULL == fib_entry_src_vft[source].fesv_copy)
+ if (NULL == fib_entry_src_bh_vft[bh].fesv_copy)
{
- fib_entry_src_vft[source].fesv_copy = fib_entry_src_copy_default;
+ fib_entry_src_bh_vft[bh].fesv_copy = fib_entry_src_copy_default;
}
}
@@ -71,7 +75,8 @@ fib_entry_src_cmp_for_sort (void * v1,
{
fib_entry_src_t *esrc1 = v1, *esrc2 = v2;
- return (esrc1->fes_src - esrc2->fes_src);
+ return (fib_source_get_prio(esrc1->fes_src) -
+ fib_source_get_prio(esrc2->fes_src));
}
static void
@@ -1925,8 +1930,8 @@ fib_entry_src_module_init (void)
fib_entry_src_rr_register();
fib_entry_src_interface_register();
fib_entry_src_interpose_register();
- fib_entry_src_default_route_register();
- fib_entry_src_special_register();
+ fib_entry_src_drop_register();
+ fib_entry_src_simple_register();
fib_entry_src_api_register();
fib_entry_src_adj_register();
fib_entry_src_mpls_register();
diff --git a/src/vnet/fib/fib_entry_src.h b/src/vnet/fib/fib_entry_src.h
index 8f13ae894bb..308005777a0 100644
--- a/src/vnet/fib/fib_entry_src.h
+++ b/src/vnet/fib/fib_entry_src.h
@@ -260,8 +260,8 @@ extern u8* fib_entry_src_format(fib_entry_t *entry,
fib_source_t source,
u8* s);
-extern void fib_entry_src_register(fib_source_t source,
- const fib_entry_src_vft_t *vft);
+extern void fib_entry_src_behaviour_register (fib_source_behaviour_t source,
+ const fib_entry_src_vft_t *vft);
extern fib_entry_src_cover_res_t fib_entry_src_action_cover_change(
fib_entry_t *entry,
@@ -348,8 +348,8 @@ extern void fib_entry_src_default_register(void);
extern void fib_entry_src_rr_register(void);
extern void fib_entry_src_interface_register(void);
extern void fib_entry_src_interpose_register(void);
-extern void fib_entry_src_default_route_register(void);
-extern void fib_entry_src_special_register(void);
+extern void fib_entry_src_drop_register(void);
+extern void fib_entry_src_simple_register(void);
extern void fib_entry_src_api_register(void);
extern void fib_entry_src_adj_register(void);
extern void fib_entry_src_mpls_register(void);
diff --git a/src/vnet/fib/fib_entry_src_adj.c b/src/vnet/fib/fib_entry_src_adj.c
index 2a5b46a2c91..ec80a867d49 100644
--- a/src/vnet/fib/fib_entry_src_adj.c
+++ b/src/vnet/fib/fib_entry_src_adj.c
@@ -411,5 +411,5 @@ const static fib_entry_src_vft_t adj_src_vft = {
void
fib_entry_src_adj_register (void)
{
- fib_entry_src_register(FIB_SOURCE_ADJ, &adj_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_ADJ, &adj_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_api.c b/src/vnet/fib/fib_entry_src_api.c
index be93cc23c36..69102a15030 100644
--- a/src/vnet/fib/fib_entry_src_api.c
+++ b/src/vnet/fib/fib_entry_src_api.c
@@ -162,13 +162,5 @@ const static fib_entry_src_vft_t api_src_vft = {
void
fib_entry_src_api_register (void)
{
- fib_entry_src_register(FIB_SOURCE_PLUGIN_HI, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_PLUGIN_LOW, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_API, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_CLI, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_6RD, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_DHCP, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_IP6_ND_PROXY, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_IP6_ND, &api_src_vft);
- fib_entry_src_register(FIB_SOURCE_SR, &api_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_API, &api_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_default.c b/src/vnet/fib/fib_entry_src_default.c
index 18a039afbd6..534a28ca6f8 100644
--- a/src/vnet/fib/fib_entry_src_default.c
+++ b/src/vnet/fib/fib_entry_src_default.c
@@ -113,9 +113,6 @@ const static fib_entry_src_vft_t default_src_vft = {
void
fib_entry_src_default_register (void)
{
- fib_source_t source;
-
- FOR_EACH_FIB_SOURCE(source) {
- fib_entry_src_register(source, &default_src_vft);
- }
+ fib_entry_src_behaviour_register (FIB_SOURCE_BH_DROP,
+ &default_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_default_route.c b/src/vnet/fib/fib_entry_src_drop.c
index 431abb66d17..886977100f4 100644
--- a/src/vnet/fib/fib_entry_src_default_route.c
+++ b/src/vnet/fib/fib_entry_src_drop.c
@@ -20,19 +20,19 @@
* Source initialisation Function
*/
static void
-fib_entry_src_default_route_init (fib_entry_src_t *src)
+fib_entry_src_drop_init (fib_entry_src_t *src)
{
src->fes_flags = FIB_ENTRY_SRC_FLAG_NONE;
}
static void
-fib_entry_src_default_route_remove (fib_entry_src_t *src)
+fib_entry_src_drop_remove (fib_entry_src_t *src)
{
src->fes_pl = FIB_NODE_INDEX_INVALID;
}
static void
-fib_entry_src_default_route_add (fib_entry_src_t *src,
+fib_entry_src_drop_add (fib_entry_src_t *src,
const fib_entry_t *entry,
fib_entry_flag_t flags,
dpo_proto_t proto,
@@ -43,16 +43,17 @@ fib_entry_src_default_route_add (fib_entry_src_t *src,
dpo);
}
-const static fib_entry_src_vft_t interface_src_vft = {
- .fesv_init = fib_entry_src_default_route_init,
- .fesv_add = fib_entry_src_default_route_add,
- .fesv_remove = fib_entry_src_default_route_remove,
+const static fib_entry_src_vft_t drop_src_vft = {
+ .fesv_init = fib_entry_src_drop_init,
+ .fesv_add = fib_entry_src_drop_add,
+ .fesv_remove = fib_entry_src_drop_remove,
};
void
-fib_entry_src_default_route_register (void)
+fib_entry_src_drop_register (void)
{
- fib_entry_src_register(FIB_SOURCE_DEFAULT_ROUTE, &interface_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_DROP,
+ &drop_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_interface.c b/src/vnet/fib/fib_entry_src_interface.c
index 5d609c5857a..140036012b9 100644
--- a/src/vnet/fib/fib_entry_src_interface.c
+++ b/src/vnet/fib/fib_entry_src_interface.c
@@ -213,5 +213,6 @@ const static fib_entry_src_vft_t interface_src_vft = {
void
fib_entry_src_interface_register (void)
{
- fib_entry_src_register(FIB_SOURCE_INTERFACE, &interface_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_INTERFACE,
+ &interface_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_interpose.c b/src/vnet/fib/fib_entry_src_interpose.c
index 2220fa4debd..02db3911dfc 100644
--- a/src/vnet/fib/fib_entry_src_interpose.c
+++ b/src/vnet/fib/fib_entry_src_interpose.c
@@ -61,17 +61,17 @@ fib_entry_src_rr_get_next_best (const fib_entry_src_t *src,
/*
* skip to the next best source after this one
*/
- if (source <= src->fes_src)
+ switch (fib_source_cmp(source, src->fes_src))
{
+ case FIB_SOURCE_CMP_BETTER:
+ case FIB_SOURCE_CMP_EQUAL:
continue;
- }
- else
- {
+ case FIB_SOURCE_CMP_WORSE:
best_src = next_src;
- break;
+ goto out;
}
}));
-
+ out:
return (best_src);
}
@@ -366,5 +366,6 @@ const static fib_entry_src_vft_t interpose_src_vft = {
void
fib_entry_src_interpose_register (void)
{
- fib_entry_src_register(FIB_SOURCE_INTERPOSE, &interpose_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_INTERPOSE,
+ &interpose_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_lisp.c b/src/vnet/fib/fib_entry_src_lisp.c
index ec8c467d1cf..2fc9c924e6b 100644
--- a/src/vnet/fib/fib_entry_src_lisp.c
+++ b/src/vnet/fib/fib_entry_src_lisp.c
@@ -114,7 +114,7 @@ fib_entry_src_lisp_get_data (fib_entry_src_t *src,
return (&(src->u.lisp.fesl_fib_index));
}
-const static fib_entry_src_vft_t api_src_vft = {
+const static fib_entry_src_vft_t lisp_src_vft = {
.fesv_init = fib_entry_src_lisp_init,
.fesv_deinit = fib_entry_src_lisp_deinit,
.fesv_add = fib_entry_src_lisp_add,
@@ -129,5 +129,6 @@ const static fib_entry_src_vft_t api_src_vft = {
void
fib_entry_src_lisp_register (void)
{
- fib_entry_src_register(FIB_SOURCE_LISP, &api_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_LISP,
+ &lisp_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_mpls.c b/src/vnet/fib/fib_entry_src_mpls.c
index f3d1dc0bd50..7bbe34d0566 100644
--- a/src/vnet/fib/fib_entry_src_mpls.c
+++ b/src/vnet/fib/fib_entry_src_mpls.c
@@ -193,5 +193,5 @@ const static fib_entry_src_vft_t mpls_src_vft = {
void
fib_entry_src_mpls_register (void)
{
- fib_entry_src_register(FIB_SOURCE_MPLS, &mpls_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_MPLS, &mpls_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_rr.c b/src/vnet/fib/fib_entry_src_rr.c
index 9f4f68d88f5..d0256b9f24b 100755
--- a/src/vnet/fib/fib_entry_src_rr.c
+++ b/src/vnet/fib/fib_entry_src_rr.c
@@ -306,6 +306,5 @@ const static fib_entry_src_vft_t rr_src_vft = {
void
fib_entry_src_rr_register (void)
{
- fib_entry_src_register(FIB_SOURCE_RR, &rr_src_vft);
- fib_entry_src_register(FIB_SOURCE_URPF_EXEMPT, &rr_src_vft);
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_RR, &rr_src_vft);
}
diff --git a/src/vnet/fib/fib_entry_src_simple.c b/src/vnet/fib/fib_entry_src_simple.c
new file mode 100644
index 00000000000..2caa4fcc1e1
--- /dev/null
+++ b/src/vnet/fib/fib_entry_src_simple.c
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2016 Cisco and/or its affiliates.
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "fib_entry.h"
+#include "fib_entry_src.h"
+
+/**
+ * Source initialisation Function
+ */
+static void
+fib_entry_src_simple_init (fib_entry_src_t *src)
+{
+ src->fes_flags = FIB_ENTRY_SRC_FLAG_NONE;
+}
+
+/**
+ * Source deinitialisation Function
+ */
+static void
+fib_entry_src_simple_deinit (fib_entry_src_t *src)
+{
+}
+
+static void
+fib_entry_src_simple_remove (fib_entry_src_t *src)
+{
+ src->fes_pl = FIB_NODE_INDEX_INVALID;
+}
+
+static void
+fib_entry_src_simple_add (fib_entry_src_t *src,
+ const fib_entry_t *entry,
+ fib_entry_flag_t flags,
+ dpo_proto_t proto,
+ const dpo_id_t *dpo)
+{
+ src->fes_pl =
+ fib_path_list_create_special(proto,
+ fib_entry_src_flags_2_path_list_flags(flags),
+ dpo);
+}
+
+static void
+fib_entry_src_simple_path_swap (fib_entry_src_t *src,
+ const fib_entry_t *entry,
+ fib_path_list_flags_t pl_flags,
+ const fib_route_path_t *rpaths)
+{
+ src->fes_pl = fib_path_list_create((FIB_PATH_LIST_FLAG_SHARED | pl_flags),
+ rpaths);
+}
+
+const static fib_entry_src_vft_t simple_src_vft = {
+ .fesv_init = fib_entry_src_simple_init,
+ .fesv_deinit = fib_entry_src_simple_deinit,
+ .fesv_add = fib_entry_src_simple_add,
+ .fesv_remove = fib_entry_src_simple_remove,
+ .fesv_path_swap = fib_entry_src_simple_path_swap,
+};
+
+void
+fib_entry_src_simple_register (void)
+{
+ fib_entry_src_behaviour_register(FIB_SOURCE_BH_SIMPLE, &simple_src_vft);
+}
diff --git a/src/vnet/fib/fib_entry_src_special.c b/src/vnet/fib/fib_entry_src_special.c
deleted file mode 100644
index c976da9327a..00000000000
--- a/src/vnet/fib/fib_entry_src_special.c
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright (c) 2016 Cisco and/or its affiliates.
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "fib_entry.h"
-#include "fib_entry_src.h"
-
-/**
- * Source initialisation Function
- */
-static void
-fib_entry_src_special_init (fib_entry_src_t *src)
-{
- src->fes_flags = FIB_ENTRY_SRC_FLAG_NONE;
-}
-
-/**
- * Source deinitialisation Function
- */
-static void
-fib_entry_src_special_deinit (fib_entry_src_t *src)
-{
-}
-
-static void
-fib_entry_src_special_remove (fib_entry_src_t *src)
-{
- src->fes_pl = FIB_NODE_INDEX_INVALID;
-}
-
-static void
-fib_entry_src_special_add (fib_entry_src_t *src,
- const fib_entry_t *entry,
- fib_entry_flag_t flags,
- dpo_proto_t proto,
- const dpo_id_t *dpo)
-{
- src->fes_pl =
- fib_path_list_create_special(proto,
- fib_entry_src_flags_2_path_list_flags(flags),
- dpo);
-}
-
-static void
-fib_entry_src_special_path_swap (fib_entry_src_t *src,
- const fib_entry_t *entry,
- fib_path_list_flags_t pl_flags,
- const fib_route_path_t *rpaths)
-{
- src->fes_pl = fib_path_list_create((FIB_PATH_LIST_FLAG_SHARED | pl_flags),
- rpaths);
-}
-
-const static fib_entry_src_vft_t special_src_vft = {
- .fesv_init = fib_entry_src_special_init,
- .fesv_deinit = fib_entry_src_special_deinit,
- .fesv_add = fib_entry_src_special_add,
- .fesv_remove = fib_entry_src_special_remove,
- .fesv_path_swap = fib_entry_src_special_path_swap,
-};
-
-void
-fib_entry_src_special_register (void)
-{
- fib_entry_src_register(FIB_SOURCE_SPECIAL, &special_src_vft);
- fib_entry_src_register(FIB_SOURCE_MAP, &special_src_vft);
- fib_entry_src_register(FIB_SOURCE_CLASSIFY, &special_src_vft);
- fib_entry_src_register(FIB_SOURCE_AE, &special_src_vft);
- fib_entry_src_register(FIB_SOURCE_PROXY, &special_src_vft);
- fib_entry_src_register(FIB_SOURCE_BIER, &special_src_vft);
-}
diff --git a/src/vnet/fib/fib_source.c b/src/vnet/fib/fib_source.c
new file mode 100644
index 00000000000..0aeecae545f
--- /dev/null
+++ b/src/vnet/fib/fib_source.c
@@ -0,0 +1,222 @@
+/*
+ * Copyright (c) 2016 Cisco and/or its affiliates.
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <vnet/fib/fib_source.h>
+
+static const char *fib_source_names[] = FIB_SOURCES;
+static const char *fib_source_behaviour_names[] = FIB_SOURCE_BEHAVIOURS;
+
+static fib_source_t fib_source_id = FIB_SOURCE_LAST+1;
+
+typedef struct fib_source_prio_t_
+{
+ fib_source_priority_t fsp_class;
+ fib_source_priority_t fsp_slot;
+} fib_source_prio_t;
+
+/**
+ * for each client requested priority count the number pf uses of
+ * that prio so we can asign is usage a slot number, and therefore
+ * each request will have a unique value.
+ */
+STATIC_ASSERT_SIZEOF(fib_source_priority_t, 1);
+static fib_source_priority_t fib_source_prio_by_class[0x100];
+
+typedef struct fib_source_reg_t_
+{
+ fib_source_t fsr_source;
+ const char *fsr_name;
+ fib_source_behaviour_t fsr_behaviour;
+ fib_source_prio_t fsr_prio;
+} fib_source_reg_t;
+
+static fib_source_reg_t *fib_source_regs;
+
+
+u16
+fib_source_get_prio (fib_source_t src)
+{
+ ASSERT(vec_len(fib_source_regs) > src);
+
+ return (((u16)fib_source_regs[src].fsr_prio.fsp_class << 8) |
+ fib_source_regs[src].fsr_prio.fsp_slot);
+}
+
+fib_source_behaviour_t
+fib_source_get_behaviour (fib_source_t src)
+{
+ ASSERT(vec_len(fib_source_regs) > src);
+
+ return (fib_source_regs[src].fsr_behaviour);
+}
+
+u8 *
+format_fib_source (u8 *s, va_list *a)
+{
+ fib_source_t src = va_arg(*a, int);
+
+ ASSERT(vec_len(fib_source_regs) > src);
+
+ return (format(s, "%s", fib_source_regs[src].fsr_name));
+}
+
+fib_source_priority_cmp_t
+fib_source_cmp (fib_source_t s1,
+ fib_source_t s2)
+{
+ if (fib_source_get_prio(s1) <
+ fib_source_get_prio(s2))
+ {
+ return (FIB_SOURCE_CMP_BETTER);
+ }
+ else if (fib_source_get_prio(s1) >
+ fib_source_get_prio(s2))
+ {
+ return (FIB_SOURCE_CMP_WORSE);
+ }
+ return (FIB_SOURCE_CMP_EQUAL);
+}
+
+static void
+fib_source_reg_init (fib_source_t src,
+ const char *name,
+ fib_source_priority_t prio,
+ fib_source_behaviour_t bh)
+{
+ fib_source_priority_t slot;
+ fib_source_reg_t *fsr;
+
+ /*
+ * ensure we assign a unique priority to each request
+ * otherwise different source will be treated like ECMP
+ */
+ slot = fib_source_prio_by_class[prio]++;
+
+ vec_validate(fib_source_regs, src);
+
+ fsr = &fib_source_regs[src];
+ fsr->fsr_source = src;
+ fsr->fsr_name = strdup(name);
+ fsr->fsr_prio.fsp_class = prio;
+ fsr->fsr_prio.fsp_slot = slot;
+ fsr->fsr_behaviour = bh;
+}
+
+fib_source_t
+fib_source_allocate (const char *name,
+ fib_source_priority_t prio,
+ fib_source_behaviour_t bh)
+{
+ fib_source_t src;
+
+ // max value range
+ ASSERT(fib_source_id < 255);
+ if (fib_source_id == 255)
+ return (FIB_SOURCE_INVALID);
+
+ src = fib_source_id++;
+
+ fib_source_reg_init(src, name, prio, bh);
+
+ return (src);
+}
+
+void
+fib_source_register (fib_source_t src,
+ fib_source_priority_t prio,
+ fib_source_behaviour_t bh)
+{
+ fib_source_reg_init(src, fib_source_names[src], prio, bh);
+}
+
+static u8 *
+format_fib_source_reg (u8 *s, va_list *a)
+{
+ fib_source_reg_t *fsr = va_arg(*a, fib_source_reg_t*);
+
+ s = format(s, "[%d] %U prio:%d.%d behaviour:%s",
+ fsr->fsr_source,
+ format_fib_source, fsr->fsr_source,
+ fsr->fsr_prio.fsp_class, fsr->fsr_prio.fsp_slot,
+ fib_source_behaviour_names[fsr->fsr_behaviour]);
+
+ return (s);
+}
+
+static int
+fib_source_reg_cmp_for_sort (void * v1,
+ void * v2)
+{
+ fib_source_reg_t *fsr1 = v1, *fsr2 = v2;
+
+ return (fib_source_get_prio(fsr1->fsr_source) -
+ fib_source_get_prio(fsr2->fsr_source));
+}
+
+void
+fib_source_walk (fib_source_walk_t fn,
+ void *ctx)
+{
+ fib_source_reg_t *fsr;
+
+ vec_foreach(fsr, fib_source_regs)
+ {
+ if (WALK_STOP == fn(fsr->fsr_source,
+ fsr->fsr_name,
+ fsr->fsr_prio.fsp_class,
+ fsr->fsr_behaviour,
+ ctx))
+ break;
+ }
+}
+
+static clib_error_t *
+fib_source_show (vlib_main_t * vm,
+ unformat_input_t * input,
+ vlib_cli_command_t * cmd)
+{
+ fib_source_reg_t *fsr, *fsrs;
+
+ fsrs = vec_dup(fib_source_regs);
+
+ while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
+ {
+ if (unformat (input, "prio") ||
+ unformat (input, "priority"))
+ vec_sort_with_function(fsrs, fib_source_reg_cmp_for_sort);
+ }
+ vec_foreach(fsr, fsrs)
+ {
+ vlib_cli_output(vm, "%U", format_fib_source_reg, fsr);
+ }
+ vec_free(fsrs);
+
+ return (NULL);
+}
+
+VLIB_CLI_COMMAND (show_fib_sources, static) = {
+ .path = "show fib source",
+ .function = fib_source_show,
+ .short_help = "show fib source [prio]",
+};
+
+
+void
+fib_source_module_init (void)
+{
+#define _(s,p,b) fib_source_register(s,p,b);
+ foreach_fib_source
+#undef _
+}
diff --git a/src/vnet/fib/fib_source.h b/src/vnet/fib/fib_source.h
new file mode 100644
index 00000000000..198ef194e2b
--- /dev/null
+++ b/src/vnet/fib/fib_source.h
@@ -0,0 +1,302 @@
+/*
+ * Copyright (c) 2016 Cisco and/or its affiliates.
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __FIB_SOURCE_H__
+#define __FIB_SOURCE_H__
+
+#include <vnet/vnet.h>
+
+/**
+ * The different sources that can create a route.
+ * The sources are defined here with their relative priority order.
+ * The lower the value the higher the priority
+ */
+typedef enum fib_source_t_ {
+ /**
+ * An invalid source
+ * This is not a real source, so don't use it to source a prefix.
+ * It exists here to provide a value for inexistant/uninitialized source
+ */
+ FIB_SOURCE_INVALID = 0,
+ /**
+ * Marker. Add new values after this one.
+ */
+ FIB_SOURCE_FIRST,
+ /**
+ * Special sources. These are for entries that are added to all
+ * FIBs by default, and should never be over-ridden (hence they
+ * are the highest priority)
+ */
+ FIB_SOURCE_SPECIAL = FIB_SOURCE_FIRST,
+ /**
+ * Classify. A route that links directly to a classify adj
+ */
+ FIB_SOURCE_CLASSIFY,
+ /**
+ * A route the is being 'proxied' on behalf of another device
+ */
+ FIB_SOURCE_PROXY,
+ /**
+ * Route added as a result of interface configuration.
+ * this will also come from the API/CLI, but the distinction is
+ * that is from confiiguration on an interface, not a 'ip route' command
+ */
+ FIB_SOURCE_INTERFACE,
+ /**
+ * SRv6 and SR-MPLS
+ */
+ FIB_SOURCE_SR,
+ /**
+ * From the BIER subsystem
+ */
+ FIB_SOURCE_BIER,
+ /**
+ * From 6RD.
+ */
+ FIB_SOURCE_6RD,
+ /**
+ * From the control plane API
+ */
+ FIB_SOURCE_API,
+ /**
+ * From the CLI.
+ */
+ FIB_SOURCE_CLI,
+ /**
+ * LISP
+ */
+ FIB_SOURCE_LISP,
+ /**
+ * IPv[46] Mapping
+ */
+ FIB_SOURCE_MAP,
+ /**
+ * DHCP
+ */
+ FIB_SOURCE_DHCP,
+ /**
+ * IPv6 Proxy ND
+ */
+ FIB_SOURCE_IP6_ND_PROXY,
+ /**
+ * IPv6 ND (seen in the link-local tables)
+ */
+ FIB_SOURCE_IP6_ND,
+ /**
+ * Adjacency source.
+ * routes created as a result of ARP/ND entries. This is lower priority
+ * then the API/CLI. This is on purpose. trust me.
+ */
+ FIB_SOURCE_ADJ,
+ /**
+ * MPLS label. The prefix has been assigned a local label. This source
+ * never provides forwarding information, instead it acts as a place-holder
+ * so the association of label to prefix can be maintained
+ */
+ FIB_SOURCE_MPLS,
+ /**
+ * Attached Export source.
+ * routes created as a result of attahced export. routes thus sourced
+ * will be present in the export tables
+ */
+ FIB_SOURCE_AE,
+ /**
+ * Recursive resolution source.
+ * Used to install an entry that is the resolution traget of another.
+ */
+ FIB_SOURCE_RR,
+ /**
+ * uRPF bypass/exemption.
+ * Used to install an entry that is exempt from the loose uRPF check
+ */
+ FIB_SOURCE_URPF_EXEMPT,
+ /**
+ * The default route source.
+ * The default route is always added to the FIB table (like the
+ * special sources) but we need to be able to over-ride it with
+ * 'ip route' sources when provided
+ */
+ FIB_SOURCE_DEFAULT_ROUTE,
+ /**
+ * The interpose source.
+ * This is not a real source, so don't use it to source a prefix.
+ * It exists here to provide a value against which to register to the
+ * VFT for providing the interpose actions to a real source.
+ */
+ FIB_SOURCE_INTERPOSE,
+ /**
+ * Marker. add new entries before this one.
+ */
+ FIB_SOURCE_LAST = FIB_SOURCE_INTERPOSE,
+} __attribute__ ((packed)) fib_source_t;
+
+STATIC_ASSERT (sizeof(fib_source_t) == 1,
+ "FIB too many sources");
+
+#define FIB_SOURCES { \
+ [FIB_SOURCE_INVALID] = "invalid", \
+ [FIB_SOURCE_SPECIAL] = "special", \
+ [FIB_SOURCE_INTERFACE] = "interface", \
+ [FIB_SOURCE_PROXY] = "proxy", \
+ [FIB_SOURCE_BIER] = "BIER", \
+ [FIB_SOURCE_6RD] = "6RD", \
+ [FIB_SOURCE_API] = "API", \
+ [FIB_SOURCE_CLI] = "CLI", \
+ [FIB_SOURCE_ADJ] = "adjacency", \
+ [FIB_SOURCE_MAP] = "MAP", \
+ [FIB_SOURCE_SR] = "SR", \
+ [FIB_SOURCE_LISP] = "LISP", \
+ [FIB_SOURCE_CLASSIFY] = "classify", \
+ [FIB_SOURCE_DHCP] = "DHCP", \
+ [FIB_SOURCE_IP6_ND_PROXY] = "IPv6-proxy-nd", \
+ [FIB_SOURCE_IP6_ND] = "IPv6-nd", \
+ [FIB_SOURCE_RR] = "recursive-resolution", \
+ [FIB_SOURCE_AE] = "attached_export", \
+ [FIB_SOURCE_MPLS] = "mpls", \
+ [FIB_SOURCE_URPF_EXEMPT] = "urpf-exempt", \
+ [FIB_SOURCE_DEFAULT_ROUTE] = "default-route", \
+ [FIB_SOURCE_INTERPOSE] = "interpose", \
+}
+
+/**
+ * Each source is assigned a priority. lower priority is beeter.
+ * the source with the best source with have its contribution added
+ * to forwarding. the lesser sources will be 'remembered' by FIB and
+ * added to forwarding should the best source be removed.
+ */
+typedef u8 fib_source_priority_t;
+
+/**
+ * source comparison
+ */
+typedef enum fib_source_priority_cmp_t_
+{
+ FIB_SOURCE_CMP_BETTER,
+ FIB_SOURCE_CMP_WORSE,
+ FIB_SOURCE_CMP_EQUAL,
+} fib_source_priority_cmp_t;
+
+/**
+ * Each source has a defined behaviour that controls how entries
+ * behave that have that source
+ */
+typedef enum fib_source_behaviour_t_
+{
+ /**
+ * If your adding a new source from a plugin pick one of these
+ */
+ /** Default behaviour - always install a drop */
+ FIB_SOURCE_BH_DROP,
+ /** add paths with [mpls] path extensions */
+ FIB_SOURCE_BH_API,
+ /** add paths without path extensions */
+ FIB_SOURCE_BH_SIMPLE,
+
+ /**
+ * If your adding a new source from a plugin
+ * these are probably not the behaviour you're lokking for.
+ */
+ /** recursive resolution w/ cover tracking*/
+ FIB_SOURCE_BH_RR,
+ /** associated label stored in private data */
+ FIB_SOURCE_BH_MPLS,
+ /** cover tracking w/ glean management */
+ FIB_SOURCE_BH_INTERFACE,
+ /** interpose */
+ FIB_SOURCE_BH_INTERPOSE,
+ /** simple + source fib tracking */
+ FIB_SOURCE_BH_LISP,
+ /** adj w/ cover tracking + refinement */
+ FIB_SOURCE_BH_ADJ,
+} fib_source_behaviour_t;
+
+#define FIB_SOURCE_BH_MAX (FIB_SOURCE_BH_ADJ+1)
+
+#define FIB_SOURCE_BEHAVIOURS { \
+ [FIB_SOURCE_BH_DROP] = "drop", \
+ [FIB_SOURCE_BH_RR] = "rr", \
+ [FIB_SOURCE_BH_MPLS] = "mpls", \
+ [FIB_SOURCE_BH_INTERFACE] = "interface", \
+ [FIB_SOURCE_BH_INTERPOSE] = "interpose", \
+ [FIB_SOURCE_BH_LISP] = "lisp", \
+ [FIB_SOURCE_BH_ADJ] = "adjacency", \
+ [FIB_SOURCE_BH_API] = "api", \
+ [FIB_SOURCE_BH_SIMPLE] = "simple", \
+}
+
+/**
+ * The fixed source to priority mappings.
+ * Declared here so those adding new sources can better determine their respective
+ * priority values.
+ */
+#define foreach_fib_source \
+ /** you can't do better then the special source */ \
+ _(FIB_SOURCE_SPECIAL, 0x00, FIB_SOURCE_BH_SIMPLE) \
+ _(FIB_SOURCE_CLASSIFY, 0x01, FIB_SOURCE_BH_SIMPLE) \
+ _(FIB_SOURCE_PROXY, 0x02, FIB_SOURCE_BH_SIMPLE) \
+ _(FIB_SOURCE_INTERFACE, 0x03, FIB_SOURCE_BH_INTERFACE) \
+ _(FIB_SOURCE_SR, 0x10, FIB_SOURCE_BH_API) \
+ _(FIB_SOURCE_BIER, 0x20, FIB_SOURCE_BH_SIMPLE) \
+ _(FIB_SOURCE_6RD, 0x30, FIB_SOURCE_BH_API) \
+ _(FIB_SOURCE_API, 0x80, FIB_SOURCE_BH_API) \
+ _(FIB_SOURCE_CLI, 0x81, FIB_SOURCE_BH_API) \
+ _(FIB_SOURCE_LISP, 0x90, FIB_SOURCE_BH_LISP) \
+ _(FIB_SOURCE_MAP, 0xa0, FIB_SOURCE_BH_SIMPLE) \
+ _(FIB_SOURCE_DHCP, 0xb0, FIB_SOURCE_BH_API) \
+ _(FIB_SOURCE_IP6_ND_PROXY, 0xc0, FIB_SOURCE_BH_API) \
+ _(FIB_SOURCE_IP6_ND, 0xc1, FIB_SOURCE_BH_API) \
+ _(FIB_SOURCE_ADJ, 0xd0, FIB_SOURCE_BH_ADJ) \
+ _(FIB_SOURCE_MPLS, 0xe0, FIB_SOURCE_BH_MPLS) \
+ _(FIB_SOURCE_AE, 0xf0, FIB_SOURCE_BH_SIMPLE) \
+ _(FIB_SOURCE_RR, 0xfb, FIB_SOURCE_BH_RR) \
+ _(FIB_SOURCE_URPF_EXEMPT, 0xfc, FIB_SOURCE_BH_RR) \
+ _(FIB_SOURCE_DEFAULT_ROUTE, 0xfd, FIB_SOURCE_BH_DROP) \
+ _(FIB_SOURCE_INTERPOSE, 0xfe, FIB_SOURCE_BH_INTERPOSE) \
+ _(FIB_SOURCE_INVALID, 0xff, FIB_SOURCE_BH_DROP)
+
+/**
+ * Some priority values that plugins might use when they are not to concerned
+ * where in the list they'll go.
+ */
+#define FIB_SOURCE_PRIORITY_HI 0x10
+#define FIB_SOURCE_PRIORITY_LOW 0xd0
+
+
+extern u16 fib_source_get_prio(fib_source_t src);
+extern fib_source_behaviour_t fib_source_get_behaviour(fib_source_t src);
+extern fib_source_priority_cmp_t fib_source_cmp(fib_source_t s1,
+ fib_source_t s2);
+
+extern u8 *format_fib_source(u8 *s, va_list *a);
+
+extern fib_source_t fib_source_allocate(const char *name,
+ fib_source_priority_t prio,
+ fib_source_behaviour_t bh);
+
+extern void fib_source_register(fib_source_t src,
+ fib_source_priority_t prio,
+ fib_source_behaviour_t bh);
+
+typedef walk_rc_t (*fib_source_walk_t)(fib_source_t id,
+ const char *name,
+ fib_source_priority_t prio,
+ fib_source_behaviour_t bh,
+ void *ctx);
+extern void fib_source_walk(fib_source_walk_t fn,
+ void *ctx);
+
+extern void fib_source_module_init(void);
+
+#endif
diff --git a/src/vnet/fib/fib_table.c b/src/vnet/fib/fib_table.c
index d3cf5dc88b1..6766028762d 100644
--- a/src/vnet/fib/fib_table.c
+++ b/src/vnet/fib/fib_table.c
@@ -304,6 +304,21 @@ fib_table_fwding_dpo_remove (u32 fib_index,
}
}
+static void
+fib_table_source_count_inc (fib_table_t *fib_table,
+ fib_source_t source)
+{
+ vec_validate (fib_table->ft_src_route_counts, source);
+ fib_table->ft_src_route_counts[source]++;
+}
+
+static void
+fib_table_source_count_dec (fib_table_t *fib_table,
+ fib_source_t source)
+{
+ vec_validate (fib_table->ft_src_route_counts, source);
+ fib_table->ft_src_route_counts[source]--;
+}
fib_node_index_t
fib_table_entry_special_dpo_add (u32 fib_index,
@@ -325,7 +340,7 @@ fib_table_entry_special_dpo_add (u32 fib_index,
dpo);
fib_table_entry_insert(fib_table, prefix, fib_entry_index);
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
else
{
@@ -336,7 +351,7 @@ fib_table_entry_special_dpo_add (u32 fib_index,
if (was_sourced != fib_entry_is_sourced(fib_entry_index, source))
{
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
}
@@ -364,7 +379,7 @@ fib_table_entry_special_dpo_update (u32 fib_index,
dpo);
fib_table_entry_insert(fib_table, prefix, fib_entry_index);
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
else
{
@@ -379,7 +394,7 @@ fib_table_entry_special_dpo_update (u32 fib_index,
if (was_sourced != fib_entry_is_sourced(fib_entry_index, source))
{
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
}
@@ -461,7 +476,7 @@ fib_table_entry_special_remove (u32 fib_index,
*/
if (was_sourced != fib_entry_is_sourced(fib_entry_index, source))
{
- fib_table->ft_src_route_counts[source]--;
+ fib_table_source_count_dec(fib_table, source);
}
fib_entry_unlock(fib_entry_index);
@@ -591,7 +606,7 @@ fib_table_entry_path_add2 (u32 fib_index,
rpaths);
fib_table_entry_insert(fib_table, prefix, fib_entry_index);
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
else
{
@@ -602,7 +617,7 @@ fib_table_entry_path_add2 (u32 fib_index,
if (was_sourced != fib_entry_is_sourced(fib_entry_index, source))
{
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
}
@@ -684,7 +699,7 @@ fib_table_entry_path_remove2 (u32 fib_index,
*/
if (was_sourced != fib_entry_is_sourced(fib_entry_index, source))
{
- fib_table->ft_src_route_counts[source]--;
+ fib_table_source_count_dec(fib_table, source);
}
fib_entry_unlock(fib_entry_index);
@@ -763,7 +778,7 @@ fib_table_entry_update (u32 fib_index,
paths);
fib_table_entry_insert(fib_table, prefix, fib_entry_index);
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
else
{
@@ -774,7 +789,7 @@ fib_table_entry_update (u32 fib_index,
if (was_sourced != fib_entry_is_sourced(fib_entry_index, source))
{
- fib_table->ft_src_route_counts[source]++;
+ fib_table_source_count_inc(fib_table, source);
}
}
@@ -856,7 +871,7 @@ fib_table_entry_delete_i (u32 fib_index,
*/
if (was_sourced != fib_entry_is_sourced(fib_entry_index, source))
{
- fib_table->ft_src_route_counts[source]--;
+ fib_table_source_count_dec(fib_table, source);
}
fib_entry_unlock(fib_entry_index);
@@ -1246,6 +1261,27 @@ fib_table_sub_tree_walk (u32 fib_index,
}
}
+static void
+fib_table_lock_dec (fib_table_t *fib_table,
+ fib_source_t source)
+{
+ vec_validate(fib_table->ft_locks, source);
+
+ fib_table->ft_locks[source]--;
+ fib_table->ft_total_locks--;
+}
+
+static void
+fib_table_lock_inc (fib_table_t *fib_table,
+ fib_source_t source)
+{
+ vec_validate(fib_table->ft_locks, source);
+
+ ASSERT(fib_table->ft_locks[source] < (0xffff - 1));
+ fib_table->ft_locks[source]++;
+ fib_table->ft_total_locks++;
+}
+
void
fib_table_unlock (u32 fib_index,
fib_protocol_t proto,
@@ -1254,10 +1290,9 @@ fib_table_unlock (u32 fib_index,
fib_table_t *fib_table;
fib_table = fib_table_get(fib_index, proto);
- fib_table->ft_locks[source]--;
- fib_table->ft_locks[FIB_TABLE_TOTAL_LOCKS]--;
+ fib_table_lock_dec(fib_table, source);
- if (0 == fib_table->ft_locks[FIB_TABLE_TOTAL_LOCKS])
+ if (0 == fib_table->ft_total_locks)
{
/*
* no more locak from any source - kill it
@@ -1275,10 +1310,7 @@ fib_table_lock (u32 fib_index,
fib_table = fib_table_get(fib_index, proto);
- ASSERT(fib_table->ft_locks[source] < (0xffff - 1));
-
- fib_table->ft_locks[source]++;
- fib_table->ft_locks[FIB_TABLE_TOTAL_LOCKS]++;
+ fib_table_lock_inc(fib_table, source);
}
u32
diff --git a/src/vnet/fib/fib_table.h b/src/vnet/fib/fib_table.h
index 74be63d326a..59ebb0b0161 100644
--- a/src/vnet/fib/fib_table.h
+++ b/src/vnet/fib/fib_table.h
@@ -23,12 +23,6 @@
#include <vnet/mpls/packet.h>
/**
- * Keep a lock per-source and a total
- */
-#define FIB_TABLE_N_LOCKS (FIB_SOURCE_MAX+1)
-#define FIB_TABLE_TOTAL_LOCKS FIB_SOURCE_MAX
-
-/**
* Flags for the source data
*/
typedef enum fib_table_attribute_t_ {
@@ -89,7 +83,8 @@ typedef struct fib_table_t_
/**
* per-source number of locks on the table
*/
- u16 ft_locks[FIB_TABLE_N_LOCKS];
+ u16 *ft_locks;
+ u32 ft_total_locks;
/**
* Table ID (hash key) for this FIB.
@@ -109,7 +104,7 @@ typedef struct fib_table_t_
/**
* Per-source route counters
*/
- u32 ft_src_route_counts[FIB_SOURCE_MAX];
+ u32 *ft_src_route_counts;
/**
* Total route counters
diff --git a/src/vnet/fib/ip4_fib.c b/src/vnet/fib/ip4_fib.c
index 02348af87d8..e4ff1bf77cc 100644
--- a/src/vnet/fib/ip4_fib.c
+++ b/src/vnet/fib/ip4_fib.c
@@ -160,6 +160,7 @@ ip4_fib_table_destroy (u32 fib_index)
{
fib_table_t *fib_table = pool_elt_at_index(ip4_main.fibs, fib_index);
ip4_fib_t *v4_fib = pool_elt_at_index(ip4_main.v4_fibs, fib_index);
+ u32 *n_locks;
int ii;
/*
@@ -182,9 +183,10 @@ ip4_fib_table_destroy (u32 fib_index)
* validate no more routes.
*/
ASSERT(0 == fib_table->ft_total_route_counts);
- FOR_EACH_FIB_SOURCE(ii)
+
+ vec_foreach(n_locks, fib_table->ft_src_route_counts)
{
- ASSERT(0 == fib_table->ft_src_route_counts[ii]);
+ ASSERT(0 == *n_locks);
}
if (~0 != fib_table->ft_table_id)
@@ -192,6 +194,7 @@ ip4_fib_table_destroy (u32 fib_index)
hash_unset (ip4_main.fib_index_by_table_id, fib_table->ft_table_id);
}
+ vec_free(fib_table->ft_src_route_counts);
ip4_mtrie_free(&v4_fib->mtrie);
pool_put(ip4_main.v4_fibs, v4_fib);
@@ -679,7 +682,7 @@ ip4_show_fib (vlib_main_t * vm,
fib_table->ft_flow_hash_config,
fib_table->ft_epoch,
format_fib_table_flags, fib_table->ft_flags);
- FOR_EACH_FIB_SOURCE(source)
+ vec_foreach_index(source, fib_table->ft_locks)
{
if (0 != fib_table->ft_locks[source])
{
diff --git a/src/vnet/fib/ip6_fib.c b/src/vnet/fib/ip6_fib.c
index 991fbc1151b..6d0eca4c8d7 100644
--- a/src/vnet/fib/ip6_fib.c
+++ b/src/vnet/fib/ip6_fib.c
@@ -151,11 +151,11 @@ ip6_fib_table_destroy (u32 fib_index)
fib_table_t *fib_table = fib_table_get(fib_index, FIB_PROTOCOL_IP6);
fib_source_t source;
- /*
+ /*
* validate no more routes.
*/
ASSERT(0 == fib_table->ft_total_route_counts);
- FOR_EACH_FIB_SOURCE(source)
+ vec_foreach_index(source, fib_table->ft_src_route_counts)
{
ASSERT(0 == fib_table->ft_src_route_counts[source]);
}
@@ -164,6 +164,7 @@ ip6_fib_table_destroy (u32 fib_index)
{
hash_unset (ip6_main.fib_index_by_table_id, fib_table->ft_table_id);
}
+ vec_free(fib_table->ft_src_route_counts);
pool_put_index(ip6_main.v6_fibs, fib_table->ft_index);
pool_put(ip6_main.fibs, fib_table);
}
@@ -688,7 +689,7 @@ ip6_show_fib (vlib_main_t * vm,
fib_table->ft_epoch,
format_fib_table_flags, fib_table->ft_flags);
- FOR_EACH_FIB_SOURCE(source)
+ vec_foreach_index(source, fib_table->ft_locks)
{
if (0 != fib_table->ft_locks[source])
{
diff --git a/src/vnet/fib/mpls_fib.c b/src/vnet/fib/mpls_fib.c
index 6f59eb3ee44..9ec32d2fea6 100644
--- a/src/vnet/fib/mpls_fib.c
+++ b/src/vnet/fib/mpls_fib.c
@@ -275,6 +275,7 @@ mpls_fib_table_destroy (u32 fib_index)
}
hash_free(mf->mf_entries);
+ vec_free(fib_table->ft_src_route_counts);
pool_put(mpls_main.mpls_fibs, mf);
pool_put(mpls_main.fibs, fib_table);
}
@@ -450,7 +451,7 @@ mpls_fib_show (vlib_main_t * vm,
s = format (s, "%v, fib_index:%d locks:[",
fib_table->ft_desc, mpls_main.fibs - fib_table);
- FOR_EACH_FIB_SOURCE(source)
+ vec_foreach_index(source, fib_table->ft_locks)
{
if (0 != fib_table->ft_locks[source])
{
diff --git a/src/vnet/ip/ip6_ll_table.c b/src/vnet/ip/ip6_ll_table.c
index a7440ea543c..3672b635c87 100644
--- a/src/vnet/ip/ip6_ll_table.c
+++ b/src/vnet/ip/ip6_ll_table.c
@@ -283,7 +283,7 @@ ip6_ll_show_fib (vlib_main_t * vm,
s = format (s, "%U, fib_index:%d, locks:[",
format_fib_table_name, fib_index,
FIB_PROTOCOL_IP6, fib_index);
- FOR_EACH_FIB_SOURCE (source)
+ vec_foreach_index (source, fib_table->ft_locks)
{
if (0 != fib_table->ft_locks[source])
{
diff --git a/test/test_fib.py b/test/test_fib.py
index faafdad15b0..0eefcdf8b80 100644
--- a/test/test_fib.py
+++ b/test/test_fib.py
@@ -20,6 +20,24 @@ class TestFIB(VppTestCase):
""" FIB Unit Tests """
error = self.vapi.cli("test fib")
+ # shameless test of CLIs to bump lcov results...
+ # no i mean to ensure they don't crash
+ self.logger.info(self.vapi.cli("sh fib source"))
+ self.logger.info(self.vapi.cli("sh fib source prio"))
+ self.logger.info(self.vapi.cli("sh fib memory"))
+ self.logger.info(self.vapi.cli("sh fib entry"))
+ self.logger.info(self.vapi.cli("sh fib entry 0"))
+ self.logger.info(self.vapi.cli("sh fib entry 10000"))
+ self.logger.info(self.vapi.cli("sh fib entry-delegate"))
+ self.logger.info(self.vapi.cli("sh fib paths"))
+ self.logger.info(self.vapi.cli("sh fib paths 0"))
+ self.logger.info(self.vapi.cli("sh fib paths 10000"))
+ self.logger.info(self.vapi.cli("sh fib path-list"))
+ self.logger.info(self.vapi.cli("sh fib path-list 0"))
+ self.logger.info(self.vapi.cli("sh fib path-list 10000"))
+ self.logger.info(self.vapi.cli("sh fib walk"))
+ self.logger.info(self.vapi.cli("sh fib uRPF"))
+
if error:
self.logger.critical(error)
self.assertNotIn("Failed", error)