Ensure that rows created for deleted port binding and multicast group rows are cleared when doing full processing.
Signed-off-by: Ryan Moats <rmo...@us.ibm.com> --- ovn/controller/physical.c | 39 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) diff --git a/ovn/controller/physical.c b/ovn/controller/physical.c index 2e9fb73..9e9343d 100644 --- a/ovn/controller/physical.c +++ b/ovn/controller/physical.c @@ -58,6 +58,10 @@ static struct simap localvif_to_ofport = SIMAP_INITIALIZER(&localvif_to_ofport); static struct hmap tunnels = HMAP_INITIALIZER(&tunnels); +static struct sset port_binding_uuids = SSET_INITIALIZER(&port_binding_uuids); +static struct sset multicast_group_uuids = + SSET_INITIALIZER(&multicast_group_uuids); + /* UUID to identify OF flows not associated with ovsdb rows. */ static struct uuid *hc_uuid = NULL; static bool full_binding_processing = false; @@ -594,6 +598,27 @@ consider_mc_group(enum mf_field_id mff_ovn_geneve, sset_destroy(&remote_chassis); } +static void +rationalize_ssets_and_delete_flows(struct sset *old, struct sset *new) +{ + const char *uuid_s, *next_uuid; + SSET_FOR_EACH_SAFE (uuid_s, next_uuid, old) { + if (!sset_find(new, uuid_s)) { + struct uuid uuid; + if (uuid_from_string(&uuid, uuid_s)) { + ofctrl_remove_flows(&uuid); + } + sset_find_and_delete(old, uuid_s); + } + } + SSET_FOR_EACH_SAFE (uuid_s, next_uuid, new) { + if (!sset_find(old, uuid_s)) { + sset_add(old, uuid_s); + } + sset_find_and_delete(new, uuid_s); + } +} + void physical_run(struct controller_ctx *ctx, enum mf_field_id mff_ovn_geneve, const struct ovsrec_bridge *br_int, const char *this_chassis_id, @@ -750,6 +775,8 @@ physical_run(struct controller_ctx *ctx, enum mf_field_id mff_ovn_geneve, * 64 for logical-to-physical translation. */ const struct sbrec_port_binding *binding; if (full_binding_processing) { + struct sset new_port_binding_uuids = + SSET_INITIALIZER(&new_port_binding_uuids); SBREC_PORT_BINDING_FOR_EACH (binding, ctx->ovnsb_idl) { /* Because it is possible in the above code to enter this * for loop without having cleared the flow table first, we @@ -757,7 +784,12 @@ physical_run(struct controller_ctx *ctx, enum mf_field_id mff_ovn_geneve, ofctrl_remove_flows(&binding->header_.uuid); consider_port_binding(mff_ovn_geneve, ct_zones, local_datapaths, patched_datapaths, binding, &ofpacts); + sset_add(&new_port_binding_uuids, + xasprintf(UUID_FMT, UUID_ARGS(&binding->header_.uuid))); } + rationalize_ssets_and_delete_flows(&port_binding_uuids, + &new_port_binding_uuids); + sset_destroy(&new_port_binding_uuids); full_binding_processing = false; } else { SBREC_PORT_BINDING_FOR_EACH_TRACKED (binding, ctx->ovnsb_idl) { @@ -777,6 +809,8 @@ physical_run(struct controller_ctx *ctx, enum mf_field_id mff_ovn_geneve, const struct sbrec_multicast_group *mc; struct ofpbuf remote_ofpacts; ofpbuf_init(&remote_ofpacts, 0); + struct sset new_multicast_group_uuids = + SSET_INITIALIZER(&new_multicast_group_uuids); SBREC_MULTICAST_GROUP_FOR_EACH (mc, ctx->ovnsb_idl) { /* As multicast groups are always reprocessed each time, * the first step is to clean the old flows for the group @@ -784,7 +818,12 @@ physical_run(struct controller_ctx *ctx, enum mf_field_id mff_ovn_geneve, ofctrl_remove_flows(&mc->header_.uuid); consider_mc_group(mff_ovn_geneve, ct_zones, local_datapaths, mc, &ofpacts, &remote_ofpacts); + sset_add(&new_multicast_group_uuids, + xasprintf(UUID_FMT, UUID_ARGS(&mc->header_.uuid))); } + rationalize_ssets_and_delete_flows(&multicast_group_uuids, + &new_multicast_group_uuids); + sset_destroy(&new_multicast_group_uuids); ofpbuf_uninit(&remote_ofpacts); -- 1.9.1 _______________________________________________ dev mailing list dev@openvswitch.org http://openvswitch.org/mailman/listinfo/dev