summaryrefslogtreecommitdiffstats
path: root/src/plugins/gbp/gbp_bridge_domain.c
diff options
context:
space:
mode:
authorNeale Ranns <nranns@cisco.com>2019-07-05 00:53:45 -0700
committerNeale Ranns <nranns@cisco.com>2019-07-09 15:45:52 +0000
commite28c87cd00644205e9bebca054029a8e655ed015 (patch)
tree8e6e0bac3b6d269c00b569a3ebf60338237c8a29 /src/plugins/gbp/gbp_bridge_domain.c
parent777d2aee8054e77e6f265879e1dfe3776d90d758 (diff)
gbp: Ownership of dynamically created vxlan-gbp tunnels managed via gbp_itf
Type: fix This solves the ownership of vxlan-gbp tunnels. When the last reference of these goes away they need to be deleted. Currently there are two owners; gbp_itf via gef_itf and the lock held by the gbp_endpoint_location_t. The problem is that the loc removes its reference whilst the fwd still holds the gbp_itf, and things go wrong. This change moves the lifecycle management of the vxlan-gbp tunnel to the gbp_itf. When the last lock of the gbp_itf goes, so does the tunnel. now both the EP's loc and fwd can hold a lock on the gbp_itf and it's only removed when required. The other change is the management of the 'user' of the gbp_itf. Since each user can enable and disable different features, it's the job of the gbp_itf to apply the combined set. determining a unique 'uesr' from the caller was near impossible, so I moved that to the gbp_itf, and return the allocated user, hence the 'handle' that encodes both user and interface. The hash table maps from sw_if_index to pool index. Change-Id: I4c7bf4c0e5dcf33d1c545f262365e69151febcf4 Signed-off-by: Neale Ranns <nranns@cisco.com>
Diffstat (limited to 'src/plugins/gbp/gbp_bridge_domain.c')
-rw-r--r--src/plugins/gbp/gbp_bridge_domain.c107
1 files changed, 57 insertions, 50 deletions
diff --git a/src/plugins/gbp/gbp_bridge_domain.c b/src/plugins/gbp/gbp_bridge_domain.c
index 3e6d7ef66b6..f2a56d770b9 100644
--- a/src/plugins/gbp/gbp_bridge_domain.c
+++ b/src/plugins/gbp/gbp_bridge_domain.c
@@ -17,6 +17,7 @@
#include <plugins/gbp/gbp_route_domain.h>
#include <plugins/gbp/gbp_endpoint.h>
#include <plugins/gbp/gbp_learn.h>
+#include <plugins/gbp/gbp_itf.h>
#include <vnet/dpo/dvr_dpo.h>
#include <vnet/fib/fib_table.h>
@@ -149,13 +150,14 @@ format_gbp_bridge_domain_ptr (u8 * s, va_list * args)
vnet_main_t *vnm = vnet_get_main ();
if (NULL != gb)
- s = format (s, "[%d] bd:[%d,%d], bvi:%U uu-flood:%U flags:%U locks:%d",
- gb - gbp_bridge_domain_pool,
- gb->gb_bd_id,
- gb->gb_bd_index,
- format_vnet_sw_if_index_name, vnm, gb->gb_bvi_sw_if_index,
- format_vnet_sw_if_index_name, vnm, gb->gb_uu_fwd_sw_if_index,
- format_gbp_bridge_domain_flags, gb->gb_flags, gb->gb_locks);
+ s =
+ format (s,
+ "[%d] bd:[%d,%d], bvi:%U uu-flood:%U bm-flood:%U flags:%U locks:%d",
+ gb - gbp_bridge_domain_pool, gb->gb_bd_id, gb->gb_bd_index,
+ format_vnet_sw_if_index_name, vnm, gb->gb_bvi_sw_if_index,
+ format_vnet_sw_if_index_name, vnm, gb->gb_uu_fwd_sw_if_index,
+ format_gbp_itf_hdl, gb->gb_bm_flood_itf,
+ format_gbp_bridge_domain_flags, gb->gb_flags, gb->gb_locks);
else
s = format (s, "NULL");
@@ -174,28 +176,6 @@ format_gbp_bridge_domain (u8 * s, va_list * args)
return (s);
}
-void
-gbp_bridge_domain_itf_add (u32 sw_if_index, u32 bd_index,
- l2_bd_port_type_t type)
-{
- set_int_l2_mode (vlib_get_main (), vnet_get_main (), MODE_L2_BRIDGE,
- sw_if_index, bd_index, type, 0, 0);
- /*
- * adding an interface to the bridge enable learning on the
- * interface. Disable learning on the interface by default for gbp
- * interfaces
- */
- l2input_intf_bitmap_enable (sw_if_index, L2INPUT_FEAT_LEARN, 0);
-}
-
-void
-gbp_bridge_domain_itf_del (u32 sw_if_index, u32 bd_index,
- l2_bd_port_type_t type)
-{
- set_int_l2_mode (vlib_get_main (), vnet_get_main (), MODE_L3, sw_if_index,
- bd_index, type, 0, 0);
-}
-
int
gbp_bridge_domain_add_and_lock (u32 bd_id,
u32 rd_id,
@@ -228,11 +208,12 @@ gbp_bridge_domain_add_and_lock (u32 bd_id,
pool_get (gbp_bridge_domain_pool, gb);
memset (gb, 0, sizeof (*gb));
+ gbi = gb - gbp_bridge_domain_pool;
gb->gb_bd_id = bd_id;
gb->gb_bd_index = bd_index;
gb->gb_uu_fwd_sw_if_index = uu_fwd_sw_if_index;
gb->gb_bvi_sw_if_index = bvi_sw_if_index;
- gb->gb_bm_flood_sw_if_index = bm_flood_sw_if_index;
+ gbp_itf_hdl_reset (&gb->gb_bm_flood_itf);
gb->gb_locks = 1;
gb->gb_flags = flags;
gb->gb_rdi = gbp_route_domain_find_and_lock (rd_id);
@@ -247,20 +228,21 @@ gbp_bridge_domain_add_and_lock (u32 bd_id,
/*
* Set the BVI and uu-flood interfaces into the BD
*/
- gbp_bridge_domain_itf_add (gb->gb_bvi_sw_if_index, bd_index,
+ gbp_bridge_domain_itf_add (gbi, gb->gb_bvi_sw_if_index,
L2_BD_PORT_TYPE_BVI);
- if ((!(flags & GBP_BD_FLAG_UU_FWD_DROP)
- || (flags & GBP_BD_FLAG_UCAST_ARP))
- && ~0 != gb->gb_uu_fwd_sw_if_index)
- gbp_bridge_domain_itf_add (gb->gb_uu_fwd_sw_if_index, bd_index,
+ if ((!(flags & GBP_BD_FLAG_UU_FWD_DROP) ||
+ (flags & GBP_BD_FLAG_UCAST_ARP)) &&
+ ~0 != gb->gb_uu_fwd_sw_if_index)
+ gbp_bridge_domain_itf_add (gbi, gb->gb_uu_fwd_sw_if_index,
L2_BD_PORT_TYPE_UU_FWD);
- if (!(flags & GBP_BD_FLAG_MCAST_DROP)
- && ~0 != gb->gb_bm_flood_sw_if_index)
+
+ if (!(flags & GBP_BD_FLAG_MCAST_DROP) && ~0 != bm_flood_sw_if_index)
{
- gbp_bridge_domain_itf_add (gb->gb_bm_flood_sw_if_index, bd_index,
- L2_BD_PORT_TYPE_NORMAL);
- gbp_learn_enable (gb->gb_bm_flood_sw_if_index, GBP_LEARN_MODE_L2);
+ gb->gb_bm_flood_itf =
+ gbp_itf_l2_add_and_lock (bm_flood_sw_if_index, gbi);
+ gbp_itf_l2_set_input_feature (gb->gb_bm_flood_itf,
+ L2INPUT_FEAT_GBP_LEARN);
}
/*
@@ -297,11 +279,41 @@ gbp_bridge_domain_add_and_lock (u32 bd_id,
}
void
-gbp_bridge_domain_unlock (index_t index)
+gbp_bridge_domain_itf_add (index_t gbdi,
+ u32 sw_if_index, l2_bd_port_type_t type)
+{
+ gbp_bridge_domain_t *gb;
+
+ gb = gbp_bridge_domain_get (gbdi);
+
+ set_int_l2_mode (vlib_get_main (), vnet_get_main (), MODE_L2_BRIDGE,
+ sw_if_index, gb->gb_bd_index, type, 0, 0);
+ /*
+ * adding an interface to the bridge enables learning on the
+ * interface. Disable learning on the interface by default for gbp
+ * interfaces
+ */
+ l2input_intf_bitmap_enable (sw_if_index, L2INPUT_FEAT_LEARN, 0);
+}
+
+void
+gbp_bridge_domain_itf_del (index_t gbdi,
+ u32 sw_if_index, l2_bd_port_type_t type)
{
gbp_bridge_domain_t *gb;
- gb = gbp_bridge_domain_get (index);
+ gb = gbp_bridge_domain_get (gbdi);
+
+ set_int_l2_mode (vlib_get_main (), vnet_get_main (), MODE_L3, sw_if_index,
+ gb->gb_bd_index, type, 0, 0);
+}
+
+void
+gbp_bridge_domain_unlock (index_t gbdi)
+{
+ gbp_bridge_domain_t *gb;
+
+ gb = gbp_bridge_domain_get (gbdi);
gb->gb_locks--;
@@ -313,17 +325,12 @@ gbp_bridge_domain_unlock (index_t index)
(vnet_get_main (), gb->gb_bvi_sw_if_index),
gb->gb_bd_index, gb->gb_bvi_sw_if_index);
- gbp_bridge_domain_itf_del (gb->gb_bvi_sw_if_index, gb->gb_bd_index,
+ gbp_bridge_domain_itf_del (gbdi, gb->gb_bvi_sw_if_index,
L2_BD_PORT_TYPE_BVI);
if (~0 != gb->gb_uu_fwd_sw_if_index)
- gbp_bridge_domain_itf_del (gb->gb_uu_fwd_sw_if_index, gb->gb_bd_index,
+ gbp_bridge_domain_itf_del (gbdi, gb->gb_uu_fwd_sw_if_index,
L2_BD_PORT_TYPE_UU_FWD);
- if (~0 != gb->gb_bm_flood_sw_if_index)
- {
- gbp_bridge_domain_itf_del (gb->gb_bm_flood_sw_if_index,
- gb->gb_bd_index, L2_BD_PORT_TYPE_NORMAL);
- gbp_learn_enable (gb->gb_bm_flood_sw_if_index, GBP_LEARN_MODE_L2);
- }
+ gbp_itf_unlock (&gb->gb_bm_flood_itf);
gbp_bridge_domain_db_remove (gb);
gbp_route_domain_unlock (gb->gb_rdi);