From a758304f13cdc0f8a85a582f90a015a6f984a4f3 Mon Sep 17 00:00:00 2001
From: Open vSwitch CI
Date: Mar 16 2023 01:11:13 +0000
Subject: Import openvswitch2.17-2.17.0-72 from Fast DataPath
---
diff --git a/SOURCES/openvswitch-2.17.0.patch b/SOURCES/openvswitch-2.17.0.patch
index 4a6c88b..d98f087 100644
--- a/SOURCES/openvswitch-2.17.0.patch
+++ b/SOURCES/openvswitch-2.17.0.patch
@@ -59040,7 +59040,7 @@ index 78a54c715d..109940ad2a 100644
oftrace_node_destroy(node);
}
diff --git a/ofproto/ofproto-dpif-upcall.c b/ofproto/ofproto-dpif-upcall.c
-index 57f94df544..308876d38c 100644
+index 57f94df544..53b47073ad 100644
--- a/ofproto/ofproto-dpif-upcall.c
+++ b/ofproto/ofproto-dpif-upcall.c
@@ -47,17 +47,20 @@
@@ -59130,7 +59130,46 @@ index 57f94df544..308876d38c 100644
ovsrcu_postpone(ukey_delete__, old_ukey);
transition_ukey(old_ukey, UKEY_DELETED);
transition_ukey(new_ukey, UKEY_VISIBLE);
-@@ -2321,6 +2346,13 @@ revalidate_ukey(struct udpif *udpif, struct udpif_key *ukey,
+@@ -2074,10 +2099,12 @@ ukey_delete(struct umap *umap, struct udpif_key *ukey)
+ }
+
+ static bool
+-should_revalidate(const struct udpif *udpif, uint64_t packets,
+- long long int used)
++should_revalidate(const struct udpif *udpif, const struct udpif_key *ukey,
++ uint64_t packets)
++ OVS_REQUIRES(ukey->mutex)
+ {
+ long long int metric, now, duration;
++ long long int used = ukey->stats.used;
+
+ if (!used) {
+ /* Always revalidate the first time a flow is dumped. */
+@@ -2104,8 +2131,12 @@ should_revalidate(const struct udpif *udpif, uint64_t packets,
+ duration = now - used;
+ metric = duration / packets;
+
+- if (metric < 1000 / ofproto_min_revalidate_pps) {
+- /* The flow is receiving more than min-revalidate-pps, so keep it. */
++ if (metric < 1000 / ofproto_min_revalidate_pps ||
++ (ukey->offloaded && duration < ofproto_offloaded_stats_delay)) {
++ /* The flow is receiving more than min-revalidate-pps, so keep it.
++ * Or it's a hardware offloaded flow that might take up to X seconds
++ * to update its statistics. Until we are sure the statistics had a
++ * chance to be updated, also keep it. */
+ return true;
+ }
+ return false;
+@@ -2303,7 +2334,7 @@ static enum reval_result
+ revalidate_ukey(struct udpif *udpif, struct udpif_key *ukey,
+ const struct dpif_flow_stats *stats,
+ struct ofpbuf *odp_actions, uint64_t reval_seq,
+- struct recirc_refs *recircs, bool offloaded)
++ struct recirc_refs *recircs)
+ OVS_REQUIRES(ukey->mutex)
+ {
+ bool need_revalidate = ukey->reval_seq != reval_seq;
+@@ -2321,8 +2352,15 @@ revalidate_ukey(struct udpif *udpif, struct udpif_key *ukey,
? stats->n_bytes - ukey->stats.n_bytes
: 0);
@@ -59142,9 +59181,21 @@ index 57f94df544..308876d38c 100644
+ }
+
if (need_revalidate) {
- if (should_revalidate(udpif, push.n_packets, ukey->stats.used)) {
+- if (should_revalidate(udpif, push.n_packets, ukey->stats.used)) {
++ if (should_revalidate(udpif, ukey, push.n_packets)) {
if (!ukey->xcache) {
-@@ -2434,6 +2466,15 @@ push_dp_ops(struct udpif *udpif, struct ukey_op *ops, size_t n_ops)
+ ukey->xcache = xlate_cache_new();
+ } else {
+@@ -2338,7 +2376,7 @@ revalidate_ukey(struct udpif *udpif, struct udpif_key *ukey,
+
+ /* Stats for deleted flows will be attributed upon flow deletion. Skip. */
+ if (result != UKEY_DELETE) {
+- xlate_push_stats(ukey->xcache, &push, offloaded);
++ xlate_push_stats(ukey->xcache, &push, ukey->offloaded);
+ ukey->stats = *stats;
+ ukey->reval_seq = reval_seq;
+ }
+@@ -2434,6 +2472,15 @@ push_dp_ops(struct udpif *udpif, struct ukey_op *ops, size_t n_ops)
push->tcp_flags = stats->tcp_flags | op->ukey->stats.tcp_flags;
push->n_packets = stats->n_packets - op->ukey->stats.n_packets;
push->n_bytes = stats->n_bytes - op->ukey->stats.n_bytes;
@@ -59160,7 +59211,7 @@ index 57f94df544..308876d38c 100644
ovs_mutex_unlock(&op->ukey->mutex);
} else {
push = stats;
-@@ -2738,6 +2779,22 @@ revalidate(struct revalidator *revalidator)
+@@ -2738,6 +2785,22 @@ revalidate(struct revalidator *revalidator)
continue;
}
@@ -59183,16 +59234,29 @@ index 57f94df544..308876d38c 100644
already_dumped = ukey->dump_seq == dump_seq;
if (already_dumped) {
/* The flow has already been handled during this flow dump
-@@ -2853,7 +2910,7 @@ revalidator_sweep__(struct revalidator *revalidator, bool purge)
+@@ -2769,8 +2832,7 @@ revalidate(struct revalidator *revalidator)
+ result = UKEY_DELETE;
+ } else {
+ result = revalidate_ukey(udpif, ukey, &stats, &odp_actions,
+- reval_seq, &recircs,
+- f->attrs.offloaded);
++ reval_seq, &recircs);
+ }
+ ukey->dump_seq = dump_seq;
+
+@@ -2853,9 +2915,9 @@ revalidator_sweep__(struct revalidator *revalidator, bool purge)
} else {
struct dpif_flow_stats stats;
COVERAGE_INC(revalidate_missed_dp_flow);
- memset(&stats, 0, sizeof stats);
+ memcpy(&stats, &ukey->stats, sizeof stats);
result = revalidate_ukey(udpif, ukey, &stats, &odp_actions,
- reval_seq, &recircs, false);
+- reval_seq, &recircs, false);
++ reval_seq, &recircs);
}
-@@ -3099,6 +3156,31 @@ upcall_unixctl_purge(struct unixctl_conn *conn, int argc OVS_UNUSED,
+ if (result != UKEY_KEEP) {
+ /* Clears 'recircs' if filled by revalidate_ukey(). */
+@@ -3099,6 +3161,31 @@ upcall_unixctl_purge(struct unixctl_conn *conn, int argc OVS_UNUSED,
unixctl_command_reply(conn, "");
}
@@ -60015,7 +60079,7 @@ index 8143dd965f..b3e575bcd0 100644
static void
diff --git a/ofproto/ofproto-provider.h b/ofproto/ofproto-provider.h
-index 14b909973d..47e96e62e1 100644
+index 14b909973d..e64ca5b805 100644
--- a/ofproto/ofproto-provider.h
+++ b/ofproto/ofproto-provider.h
@@ -143,6 +143,8 @@ struct ofproto {
@@ -60027,11 +60091,31 @@ index 14b909973d..47e96e62e1 100644
};
void ofproto_init_tables(struct ofproto *, int n_tables);
+@@ -536,6 +538,11 @@ extern unsigned ofproto_max_revalidator;
+ * duration exceeds half of max-revalidator config variable. */
+ extern unsigned ofproto_min_revalidate_pps;
+
++/* Worst case delay (in ms) it might take before statistics of offloaded flows
++ * are updated. Offloaded flows younger than this delay will always be
++ * revalidated regardless of ofproto_min_revalidate_pps. */
++extern unsigned ofproto_offloaded_stats_delay;
++
+ /* Number of upcall handler and revalidator threads. Only affects the
+ * ofproto-dpif implementation. */
+ extern uint32_t n_handlers, n_revalidators;
diff --git a/ofproto/ofproto.c b/ofproto/ofproto.c
-index 56aeac7209..933f7de2dc 100644
+index 56aeac7209..8569ce94cb 100644
--- a/ofproto/ofproto.c
+++ b/ofproto/ofproto.c
-@@ -549,6 +549,7 @@ ofproto_create(const char *datapath_name, const char *datapath_type,
+@@ -310,6 +310,7 @@ unsigned ofproto_flow_limit = OFPROTO_FLOW_LIMIT_DEFAULT;
+ unsigned ofproto_max_idle = OFPROTO_MAX_IDLE_DEFAULT;
+ unsigned ofproto_max_revalidator = OFPROTO_MAX_REVALIDATOR_DEFAULT;
+ unsigned ofproto_min_revalidate_pps = OFPROTO_MIN_REVALIDATE_PPS_DEFAULT;
++unsigned ofproto_offloaded_stats_delay = OFPROTO_OFFLOADED_STATS_DELAY;
+
+ uint32_t n_handlers, n_revalidators;
+
+@@ -549,6 +550,7 @@ ofproto_create(const char *datapath_name, const char *datapath_type,
ovs_mutex_init(&ofproto->vl_mff_map.mutex);
cmap_init(&ofproto->vl_mff_map.cmap);
@@ -60039,7 +60123,23 @@ index 56aeac7209..933f7de2dc 100644
error = ofproto->ofproto_class->construct(ofproto);
if (error) {
-@@ -1695,9 +1696,33 @@ ofproto_destroy__(struct ofproto *ofproto)
+@@ -725,6 +727,15 @@ ofproto_set_min_revalidate_pps(unsigned min_revalidate_pps)
+ ofproto_min_revalidate_pps = min_revalidate_pps ? min_revalidate_pps : 1;
+ }
+
++/* Set worst case delay (in ms) it might take before statistics of offloaded
++ * flows are updated. Offloaded flows younger than this delay will always be
++ * revalidated regardless of ofproto_min_revalidate_pps. */
++void
++ofproto_set_offloaded_stats_delay(unsigned offloaded_stats_delay)
++{
++ ofproto_offloaded_stats_delay = offloaded_stats_delay;
++}
++
+ /* If forward_bpdu is true, the NORMAL action will forward frames with
+ * reserved (e.g. STP) destination Ethernet addresses. if forward_bpdu is false,
+ * the NORMAL action will drop these frames. */
+@@ -1695,9 +1706,33 @@ ofproto_destroy__(struct ofproto *ofproto)
ofproto->ofproto_class->dealloc(ofproto);
}
@@ -60076,7 +60176,7 @@ index 56aeac7209..933f7de2dc 100644
static void
ofproto_destroy_defer__(struct ofproto *ofproto)
OVS_EXCLUDED(ofproto_mutex)
-@@ -1705,11 +1730,31 @@ ofproto_destroy_defer__(struct ofproto *ofproto)
+@@ -1705,11 +1740,31 @@ ofproto_destroy_defer__(struct ofproto *ofproto)
ovsrcu_postpone(ofproto_destroy__, ofproto);
}
@@ -60109,7 +60209,7 @@ index 56aeac7209..933f7de2dc 100644
struct ofport_usage *usage;
if (!p) {
-@@ -1717,7 +1762,7 @@ ofproto_destroy(struct ofproto *p, bool del)
+@@ -1717,7 +1772,7 @@ ofproto_destroy(struct ofproto *p, bool del)
}
ofproto_flush__(p, del);
@@ -60118,7 +60218,7 @@ index 56aeac7209..933f7de2dc 100644
ofport_destroy(ofport, del);
}
-@@ -1736,8 +1781,7 @@ ofproto_destroy(struct ofproto *p, bool del)
+@@ -1736,8 +1791,7 @@ ofproto_destroy(struct ofproto *p, bool del)
p->connmgr = NULL;
ovs_mutex_unlock(&ofproto_mutex);
@@ -60128,7 +60228,7 @@ index 56aeac7209..933f7de2dc 100644
}
/* Destroys the datapath with the respective 'name' and 'type'. With the Linux
-@@ -2782,7 +2826,7 @@ init_ports(struct ofproto *p)
+@@ -2782,7 +2836,7 @@ init_ports(struct ofproto *p)
{
struct ofproto_port_dump dump;
struct ofproto_port ofproto_port;
@@ -60137,7 +60237,7 @@ index 56aeac7209..933f7de2dc 100644
OFPROTO_PORT_FOR_EACH (&ofproto_port, &dump, p) {
const char *name = ofproto_port.name;
-@@ -2813,7 +2857,7 @@ init_ports(struct ofproto *p)
+@@ -2813,7 +2867,7 @@ init_ports(struct ofproto *p)
}
}
@@ -60146,7 +60246,7 @@ index 56aeac7209..933f7de2dc 100644
struct iface_hint *iface_hint = node->data;
if (!strcmp(iface_hint->br_name, p->name)) {
-@@ -2929,6 +2973,9 @@ ofproto_rule_destroy__(struct rule *rule)
+@@ -2929,6 +2983,9 @@ ofproto_rule_destroy__(struct rule *rule)
cls_rule_destroy(CONST_CAST(struct cls_rule *, &rule->cr));
rule_actions_destroy(rule_get_actions(rule));
ovs_mutex_destroy(&rule->mutex);
@@ -60156,7 +60256,7 @@ index 56aeac7209..933f7de2dc 100644
rule->ofproto->ofproto_class->rule_dealloc(rule);
}
-@@ -3069,6 +3116,9 @@ group_destroy_cb(struct ofgroup *group)
+@@ -3069,6 +3126,9 @@ group_destroy_cb(struct ofgroup *group)
&group->props));
ofputil_bucket_list_destroy(CONST_CAST(struct ovs_list *,
&group->buckets));
@@ -60166,7 +60266,7 @@ index 56aeac7209..933f7de2dc 100644
group->ofproto->ofproto_class->group_dealloc(group);
}
-@@ -5271,10 +5321,15 @@ ofproto_rule_create(struct ofproto *ofproto, struct cls_rule *cr,
+@@ -5271,10 +5331,15 @@ ofproto_rule_create(struct ofproto *ofproto, struct cls_rule *cr,
struct rule *rule;
enum ofperr error;
@@ -60182,7 +60282,7 @@ index 56aeac7209..933f7de2dc 100644
VLOG_WARN_RL(&rl, "%s: failed to allocate a rule.", ofproto->name);
return OFPERR_OFPFMFC_UNKNOWN;
}
-@@ -6797,9 +6852,9 @@ static void
+@@ -6797,9 +6862,9 @@ static void
meter_delete_all(struct ofproto *ofproto)
OVS_REQUIRES(ofproto_mutex)
{
@@ -60194,7 +60294,7 @@ index 56aeac7209..933f7de2dc 100644
hmap_remove(&ofproto->meters, &meter->node);
meter_destroy(ofproto, meter);
}
-@@ -7339,8 +7394,13 @@ init_group(struct ofproto *ofproto, const struct ofputil_group_mod *gm,
+@@ -7339,8 +7404,13 @@ init_group(struct ofproto *ofproto, const struct ofputil_group_mod *gm,
return OFPERR_OFPGMFC_BAD_TYPE;
}
@@ -60208,7 +60308,7 @@ index 56aeac7209..933f7de2dc 100644
VLOG_WARN_RL(&rl, "%s: failed to allocate group", ofproto->name);
return OFPERR_OFPGMFC_OUT_OF_GROUPS;
}
-@@ -7377,6 +7437,7 @@ init_group(struct ofproto *ofproto, const struct ofputil_group_mod *gm,
+@@ -7377,6 +7447,7 @@ init_group(struct ofproto *ofproto, const struct ofputil_group_mod *gm,
&(*ofgroup)->props));
ofputil_bucket_list_destroy(CONST_CAST(struct ovs_list *,
&(*ofgroup)->buckets));
@@ -60216,7 +60316,7 @@ index 56aeac7209..933f7de2dc 100644
ofproto->ofproto_class->group_dealloc(*ofgroup);
}
return error;
-@@ -8902,7 +8963,7 @@ eviction_group_hash_rule(struct rule *rule)
+@@ -8902,7 +8973,7 @@ eviction_group_hash_rule(struct rule *rule)
hash = table->eviction_group_id_basis;
miniflow_expand(rule->cr.match.flow, &flow);
for (sf = table->eviction_fields;
@@ -60225,7 +60325,7 @@ index 56aeac7209..933f7de2dc 100644
sf++)
{
if (mf_are_prereqs_ok(sf->field, &flow, NULL)) {
-@@ -9138,8 +9199,8 @@ oftable_configure_eviction(struct oftable *table, unsigned int eviction,
+@@ -9138,8 +9209,8 @@ oftable_configure_eviction(struct oftable *table, unsigned int eviction,
/* Destroy existing eviction groups, then destroy and recreate data
* structures to recover memory. */
@@ -60237,10 +60337,26 @@ index 56aeac7209..933f7de2dc 100644
}
hmap_destroy(&table->eviction_groups_by_id);
diff --git a/ofproto/ofproto.h b/ofproto/ofproto.h
-index b0262da2df..4e15167ab7 100644
+index b0262da2df..fa7973ac72 100644
--- a/ofproto/ofproto.h
+++ b/ofproto/ofproto.h
-@@ -563,6 +563,10 @@ int ofproto_port_get_cfm_status(const struct ofproto *,
+@@ -311,6 +311,7 @@ int ofproto_port_dump_done(struct ofproto_port_dump *);
+ #define OFPROTO_MAX_IDLE_DEFAULT 10000 /* ms */
+ #define OFPROTO_MAX_REVALIDATOR_DEFAULT 500 /* ms */
+ #define OFPROTO_MIN_REVALIDATE_PPS_DEFAULT 5
++#define OFPROTO_OFFLOADED_STATS_DELAY 2000 /* ms */
+
+ const char *ofproto_port_open_type(const struct ofproto *,
+ const char *port_type);
+@@ -340,6 +341,7 @@ void ofproto_set_flow_limit(unsigned limit);
+ void ofproto_set_max_idle(unsigned max_idle);
+ void ofproto_set_max_revalidator(unsigned max_revalidator);
+ void ofproto_set_min_revalidate_pps(unsigned min_revalidate_pps);
++void ofproto_set_offloaded_stats_delay(unsigned offloaded_stats_delay);
+ void ofproto_set_forward_bpdu(struct ofproto *, bool forward_bpdu);
+ void ofproto_set_mac_table_config(struct ofproto *, unsigned idle_time,
+ size_t max_entries);
+@@ -563,6 +565,10 @@ int ofproto_port_get_cfm_status(const struct ofproto *,
enum ofputil_table_miss ofproto_table_get_miss_config(const struct ofproto *,
uint8_t table_id);
@@ -70157,7 +70273,7 @@ index 37cc72d401..1032089fc2 100644
if (fscset->bridge == br->br_cfg) {
ovsrec_flow_sample_collector_set_delete(fscset);
diff --git a/vswitchd/bridge.c b/vswitchd/bridge.c
-index 5223aa8970..793bad1243 100644
+index 5223aa8970..81f073b1cf 100644
--- a/vswitchd/bridge.c
+++ b/vswitchd/bridge.c
@@ -543,13 +543,13 @@ bridge_exit(bool delete_datapath)
@@ -70234,7 +70350,17 @@ index 5223aa8970..793bad1243 100644
int sflow_bridge_number;
size_t n_managers;
-@@ -875,7 +875,7 @@ bridge_reconfigure(const struct ovsrec_open_vswitch *ovs_cfg)
+@@ -832,6 +832,9 @@ bridge_reconfigure(const struct ovsrec_open_vswitch *ovs_cfg)
+ ofproto_set_min_revalidate_pps(
+ smap_get_uint(&ovs_cfg->other_config, "min-revalidate-pps",
+ OFPROTO_MIN_REVALIDATE_PPS_DEFAULT));
++ ofproto_set_offloaded_stats_delay(
++ smap_get_uint(&ovs_cfg->other_config, "offloaded-stats-delay",
++ OFPROTO_OFFLOADED_STATS_DELAY));
+ ofproto_set_vlan_limit(smap_get_int(&ovs_cfg->other_config, "vlan-limit",
+ LEGACY_MAX_VLAN_HEADERS));
+ ofproto_set_bundle_idle_timeout(smap_get_uint(&ovs_cfg->other_config,
+@@ -875,7 +878,7 @@ bridge_reconfigure(const struct ovsrec_open_vswitch *ovs_cfg)
* - Create ofprotos that are missing.
*
* - Add ports that are missing. */
@@ -70243,7 +70369,7 @@ index 5223aa8970..793bad1243 100644
if (!br->ofproto) {
int error;
-@@ -1020,7 +1020,7 @@ bridge_delete_or_reconfigure_ports(struct bridge *br)
+@@ -1020,7 +1023,7 @@ bridge_delete_or_reconfigure_ports(struct bridge *br)
struct ofproto_port_dump dump;
struct sset ofproto_ports;
@@ -70252,7 +70378,7 @@ index 5223aa8970..793bad1243 100644
/* List of "ofp_port"s to delete. We make a list instead of deleting them
* right away because ofproto implementations aren't necessarily able to
-@@ -1132,10 +1132,10 @@ bridge_delete_or_reconfigure_ports(struct bridge *br)
+@@ -1132,10 +1135,10 @@ bridge_delete_or_reconfigure_ports(struct bridge *br)
* device destroyed via "tunctl -d", a physical Ethernet device
* whose module was just unloaded via "rmmod", or a virtual NIC for a
* VM whose VM was just terminated. */
@@ -70266,7 +70392,7 @@ index 5223aa8970..793bad1243 100644
if (!sset_contains(&ofproto_ports, iface->name)) {
iface_destroy__(iface);
}
-@@ -1967,7 +1967,7 @@ port_is_bond_fake_iface(const struct port *port)
+@@ -1967,7 +1970,7 @@ port_is_bond_fake_iface(const struct port *port)
static void
add_del_bridges(const struct ovsrec_open_vswitch *cfg)
{
@@ -70275,7 +70401,7 @@ index 5223aa8970..793bad1243 100644
struct shash_node *node;
struct shash new_br;
size_t i;
-@@ -1993,7 +1993,7 @@ add_del_bridges(const struct ovsrec_open_vswitch *cfg)
+@@ -1993,7 +1996,7 @@ add_del_bridges(const struct ovsrec_open_vswitch *cfg)
/* Get rid of deleted bridges or those whose types have changed.
* Update 'cfg' of bridges that still exist. */
@@ -70284,7 +70410,7 @@ index 5223aa8970..793bad1243 100644
br->cfg = shash_find_data(&new_br, br->name);
if (!br->cfg || strcmp(br->type, ofproto_normalize_type(
br->cfg->datapath_type))) {
-@@ -2660,6 +2660,7 @@ iface_refresh_stats(struct iface *iface)
+@@ -2660,6 +2663,7 @@ iface_refresh_stats(struct iface *iface)
IFACE_STAT(tx_512_to_1023_packets, "tx_512_to_1023_packets") \
IFACE_STAT(tx_1024_to_1522_packets, "tx_1024_to_1522_packets") \
IFACE_STAT(tx_1523_to_max_packets, "tx_1523_to_max_packets") \
@@ -70292,7 +70418,7 @@ index 5223aa8970..793bad1243 100644
IFACE_STAT(tx_multicast_packets, "tx_multicast_packets") \
IFACE_STAT(rx_broadcast_packets, "rx_broadcast_packets") \
IFACE_STAT(tx_broadcast_packets, "tx_broadcast_packets") \
-@@ -3266,13 +3267,13 @@ bridge_run(void)
+@@ -3266,13 +3270,13 @@ bridge_run(void)
if (ovsdb_idl_is_lock_contended(idl)) {
static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(1, 1);
@@ -70308,7 +70434,7 @@ index 5223aa8970..793bad1243 100644
bridge_destroy(br, false);
}
/* Since we will not be running system_stats_run() in this process
-@@ -3594,13 +3595,13 @@ static void
+@@ -3594,13 +3598,13 @@ static void
bridge_destroy(struct bridge *br, bool del)
{
if (br) {
@@ -70326,7 +70452,7 @@ index 5223aa8970..793bad1243 100644
mirror_destroy(mirror);
}
-@@ -3746,11 +3747,11 @@ static void
+@@ -3746,11 +3750,11 @@ static void
bridge_del_ports(struct bridge *br, const struct shash *wanted_ports)
{
struct shash_node *port_node;
@@ -70340,7 +70466,7 @@ index 5223aa8970..793bad1243 100644
port->cfg = shash_find_data(wanted_ports, port->name);
if (!port->cfg) {
port_destroy(port);
-@@ -4211,7 +4212,7 @@ bridge_configure_aa(struct bridge *br)
+@@ -4211,7 +4215,7 @@ bridge_configure_aa(struct bridge *br)
const struct ovsdb_datum *mc;
struct ovsrec_autoattach *auto_attach = br->cfg->auto_attach;
struct aa_settings aa_s;
@@ -70349,7 +70475,7 @@ index 5223aa8970..793bad1243 100644
size_t i;
if (!auto_attach) {
-@@ -4227,7 +4228,7 @@ bridge_configure_aa(struct bridge *br)
+@@ -4227,7 +4231,7 @@ bridge_configure_aa(struct bridge *br)
mc = ovsrec_autoattach_get_mappings(auto_attach,
OVSDB_TYPE_INTEGER,
OVSDB_TYPE_INTEGER);
@@ -70358,7 +70484,7 @@ index 5223aa8970..793bad1243 100644
union ovsdb_atom atom;
atom.integer = m->isid;
-@@ -4341,12 +4342,12 @@ static void
+@@ -4341,12 +4345,12 @@ static void
bridge_aa_refresh_queued(struct bridge *br)
{
struct ovs_list *list = xmalloc(sizeof *list);
@@ -70373,7 +70499,7 @@ index 5223aa8970..793bad1243 100644
struct port *port;
VLOG_INFO("ifname=%s, vlan=%u, oper=%u", node->port_name, node->vlan,
-@@ -4387,7 +4388,7 @@ port_create(struct bridge *br, const struct ovsrec_port *cfg)
+@@ -4387,7 +4391,7 @@ port_create(struct bridge *br, const struct ovsrec_port *cfg)
static void
port_del_ifaces(struct port *port)
{
@@ -70382,7 +70508,7 @@ index 5223aa8970..793bad1243 100644
struct sset new_ifaces;
size_t i;
-@@ -4398,7 +4399,7 @@ port_del_ifaces(struct port *port)
+@@ -4398,7 +4402,7 @@ port_del_ifaces(struct port *port)
}
/* Get rid of deleted interfaces. */
@@ -70391,7 +70517,7 @@ index 5223aa8970..793bad1243 100644
if (!sset_contains(&new_ifaces, iface->name)) {
iface_destroy(iface);
}
-@@ -4412,13 +4413,13 @@ port_destroy(struct port *port)
+@@ -4412,13 +4416,13 @@ port_destroy(struct port *port)
{
if (port) {
struct bridge *br = port->bridge;
@@ -70407,7 +70533,7 @@ index 5223aa8970..793bad1243 100644
iface_destroy__(iface);
}
-@@ -5013,12 +5014,12 @@ bridge_configure_mirrors(struct bridge *br)
+@@ -5013,12 +5017,12 @@ bridge_configure_mirrors(struct bridge *br)
{
const struct ovsdb_datum *mc;
unsigned long *flood_vlans;
@@ -70423,10 +70549,30 @@ index 5223aa8970..793bad1243 100644
atom.uuid = m->uuid;
diff --git a/vswitchd/vswitch.xml b/vswitchd/vswitch.xml
-index 0c66326171..87d8f3e67a 100644
+index 0c66326171..0c8534f142 100644
--- a/vswitchd/vswitch.xml
+++ b/vswitchd/vswitch.xml
-@@ -2312,7 +2312,7 @@
+@@ -222,6 +222,19 @@
+
+
+
++
++
++ Set worst case delay (in ms) it might take before statistics of
++ offloaded flows are updated. Offloaded flows younger than this
++ delay will always be revalidated regardless of
++ .
++
++
++ The default is 2000.
++
++
++
+
+
+@@ -2312,7 +2325,7 @@
lowest port-id is elected as the root.
diff --git a/SPECS/openvswitch2.17.spec b/SPECS/openvswitch2.17.spec
index 23594eb..b7ce8e9 100644
--- a/SPECS/openvswitch2.17.spec
+++ b/SPECS/openvswitch2.17.spec
@@ -57,7 +57,7 @@ Summary: Open vSwitch
Group: System Environment/Daemons daemon/database/utilities
URL: http://www.openvswitch.org/
Version: 2.17.0
-Release: 71%{?dist}
+Release: 72%{?dist}
# Nearly all of openvswitch is ASL 2.0. The bugtool is LGPLv2+, and the
# lib/sflow*.[ch] files are SISSL
@@ -748,6 +748,12 @@ exit 0
%endif
%changelog
+* Wed Mar 15 2023 Open vSwitch CI - 2.17.0-72
+- Merging upstream branch-2.17 [RH git: aa069916b4]
+ Commit list:
+ 09e6e1de7a ofproto-dpif-upcall: Wait for valid hw flow stats before applying min-revalidate-pps.
+
+
* Tue Mar 14 2023 Open vSwitch CI - 2.17.0-71
- Merging upstream branch-2.17 [RH git: 0144f0fed7]
Commit list: