[ovs-dev] [PATCH 3/6] revalidator: Refactor revalidation early exit.
Joe Stringer
joe at ovn.org
Wed Sep 21 01:47:32 UTC 2016
Shift the early-exit conditions for revalidation into a separate
function.
Signed-off-by: Joe Stringer <joe at ovn.org>
---
ofproto/ofproto-dpif-upcall.c | 136 ++++++++++++++++++++++++------------------
1 file changed, 78 insertions(+), 58 deletions(-)
diff --git a/ofproto/ofproto-dpif-upcall.c b/ofproto/ofproto-dpif-upcall.c
index 064f043b9eac..052e502de696 100644
--- a/ofproto/ofproto-dpif-upcall.c
+++ b/ofproto/ofproto-dpif-upcall.c
@@ -1793,6 +1793,11 @@ should_revalidate(const struct udpif *udpif, uint64_t packets,
{
long long int metric, now, duration;
+ if (!used) {
+ /* Always revalidate the first time a flow is dumped. */
+ return true;
+ }
+
if (udpif->dump_duration < 200) {
/* We are likely to handle full revalidation for the flows. */
return true;
@@ -1871,39 +1876,18 @@ xlate_ukey(struct udpif *udpif, const struct udpif_key *ukey,
return 0;
}
-
-/* Verifies that the datapath actions of 'ukey' are still correct, and pushes
- * 'stats' for it.
- *
- * Returns a recommended action for 'ukey', options include:
- * UKEY_DELETE The ukey should be deleted.
- * UKEY_KEEP The ukey is fine as is.
- * UKEY_MODIFY The ukey's actions should be changed but is otherwise
- * fine. Callers should change the actions to those found
- * in the caller supplied 'odp_actions' buffer. The
- * recirculation references can be found in 'recircs' and
- * must be handled by the caller.
- *
- * If the result is UKEY_MODIFY, then references to all recirc_ids used by the
- * new flow will be held within 'recircs' (which may be none).
- *
- * The caller is responsible for both initializing 'recircs' prior this call,
- * and ensuring any references are eventually freed.
- */
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)
+revalidate_ukey__(struct udpif *udpif, struct udpif_key *ukey,
+ const struct dpif_flow_stats *push,
+ struct ofpbuf *odp_actions, uint64_t reval_seq,
+ struct recirc_refs *recircs)
OVS_REQUIRES(ukey->mutex)
{
bool need_revalidate = (ukey->reval_seq != reval_seq);
struct xlate_out *xoutp;
struct netflow *netflow;
- struct dpif_flow_stats push;
struct flow_wildcards dp_mask, wc;
enum reval_result result;
- long long int last_used;
struct reval_context ctx = {
.odp_actions = odp_actions,
.netflow = &netflow,
@@ -1914,35 +1898,6 @@ revalidate_ukey(struct udpif *udpif, struct udpif_key *ukey,
xoutp = NULL;
netflow = NULL;
- ofpbuf_clear(odp_actions);
- last_used = ukey->stats.used;
- push.used = stats->used;
- push.tcp_flags = stats->tcp_flags;
- push.n_packets = (stats->n_packets > ukey->stats.n_packets
- ? stats->n_packets - ukey->stats.n_packets
- : 0);
- push.n_bytes = (stats->n_bytes > ukey->stats.n_bytes
- ? stats->n_bytes - ukey->stats.n_bytes
- : 0);
-
- if (need_revalidate && last_used
- && !should_revalidate(udpif, push.n_packets, last_used)) {
- goto exit;
- }
-
- /* We will push the stats, so update the ukey stats cache. */
- ukey->stats = *stats;
- if (!push.n_packets && !need_revalidate) {
- result = UKEY_KEEP;
- goto exit;
- }
-
- if (ukey->xcache && !need_revalidate) {
- xlate_push_stats(ukey->xcache, &push);
- result = UKEY_KEEP;
- goto exit;
- }
-
if (need_revalidate) {
xlate_cache_clear(ukey->xcache);
}
@@ -1950,7 +1905,7 @@ revalidate_ukey(struct udpif *udpif, struct udpif_key *ukey,
ukey->xcache = xlate_cache_new();
}
ctx.xcache = ukey->xcache;
- if (xlate_ukey(udpif, ukey, &push, &ctx)) {
+ if (xlate_ukey(udpif, ukey, push, &ctx)) {
goto exit;
}
xoutp = &ctx.xout;
@@ -1994,9 +1949,6 @@ revalidate_ukey(struct udpif *udpif, struct udpif_key *ukey,
result = UKEY_KEEP;
exit:
- if (result != UKEY_DELETE) {
- ukey->reval_seq = reval_seq;
- }
if (netflow && result == UKEY_DELETE) {
netflow_flow_clear(netflow, &ctx.flow);
}
@@ -2004,6 +1956,74 @@ exit:
return result;
}
+/* Verifies that the datapath actions of 'ukey' are still correct, and pushes
+ * 'stats' for it.
+ *
+ * Returns a recommended action for 'ukey', options include:
+ * UKEY_DELETE The ukey should be deleted.
+ * UKEY_KEEP The ukey is fine as is.
+ * UKEY_MODIFY The ukey's actions should be changed but is otherwise
+ * fine. Callers should change the actions to those found
+ * in the caller supplied 'odp_actions' buffer. The
+ * recirculation references can be found in 'recircs' and
+ * must be handled by the caller.
+ *
+ * If the result is UKEY_MODIFY, then references to all recirc_ids used by the
+ * new flow will be held within 'recircs' (which may be none).
+ *
+ * The caller is responsible for both initializing 'recircs' prior this call,
+ * and ensuring any references are eventually freed.
+ */
+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)
+ OVS_REQUIRES(ukey->mutex)
+{
+ bool need_revalidate = ukey->reval_seq != reval_seq;
+ enum reval_result result = UKEY_DELETE;
+ struct dpif_flow_stats push;
+
+ ofpbuf_clear(odp_actions);
+
+ push.used = stats->used;
+ push.tcp_flags = stats->tcp_flags;
+ push.n_packets = (stats->n_packets > ukey->stats.n_packets
+ ? stats->n_packets - ukey->stats.n_packets
+ : 0);
+ push.n_bytes = (stats->n_bytes > ukey->stats.n_bytes
+ ? stats->n_bytes - ukey->stats.n_bytes
+ : 0);
+
+ if (need_revalidate
+ && !should_revalidate(udpif, push.n_packets, ukey->stats.used)) {
+ goto exit;
+ }
+
+ /* We will push the stats, so update the ukey stats cache. */
+ ukey->stats = *stats;
+ if (!push.n_packets && !need_revalidate) {
+ result = UKEY_KEEP;
+ goto exit;
+ }
+
+ if (ukey->xcache && !need_revalidate) {
+ xlate_push_stats(ukey->xcache, &push);
+ result = UKEY_KEEP;
+ goto exit;
+ }
+
+ result = revalidate_ukey__(udpif, ukey, &push, odp_actions, reval_seq,
+ recircs);
+
+exit:
+ if (result != UKEY_DELETE) {
+ ukey->reval_seq = reval_seq;
+ }
+ return result;
+}
+
static void
delete_op_init__(struct udpif *udpif, struct ukey_op *op,
const struct dpif_flow *flow)
--
2.9.3
More information about the dev
mailing list