Unconditional insertion of EMC entries results in EMC thrashing at high numbers of parallel flows. When this occurs, the performance of the EMC often falls below that of the dpcls classifier, rendering the EMC practically useless.
Instead of unconditionally inserting entries into the EMC when a miss occurs, use a 1% probability of insertion. This ensures that the most frequent flows have the highest chance of creating an entry in the EMC, and the probability of thrashing the EMC is also greatly reduced. Signed-off-by: Ciara Loftus <[email protected]> Signed-off-by: Georg Schmuecking <[email protected]> Co-authored-by: Georg Schmuecking <[email protected]> --- lib/dpif-netdev.c | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/lib/dpif-netdev.c b/lib/dpif-netdev.c index 546a1e9..8d55ba2 100644 --- a/lib/dpif-netdev.c +++ b/lib/dpif-netdev.c @@ -144,6 +144,9 @@ struct netdev_flow_key { #define EM_FLOW_HASH_MASK (EM_FLOW_HASH_ENTRIES - 1) #define EM_FLOW_HASH_SEGS 2 +#define EM_FLOW_INSERT_PROB 100 +#define EM_FLOW_INSERT_MIN (UINT32_MAX / EM_FLOW_INSERT_PROB) + struct emc_entry { struct dp_netdev_flow *flow; struct netdev_flow_key key; /* key.hash used for emc hash value. */ @@ -1994,6 +1997,19 @@ emc_insert(struct emc_cache *cache, const struct netdev_flow_key *key, emc_change_entry(to_be_replaced, flow, key); } +static inline void +emc_probabilistic_insert(struct dp_netdev_pmd_thread *pmd, + struct emc_cache *cache, + const struct netdev_flow_key *key, + struct dp_netdev_flow *flow) +{ + /* One in every EM_FLOW_INSERT_PROB packets are inserted to reduce + * thrashing */ + if ((key->hash ^ (uint32_t)pmd->last_cycles) <= EM_FLOW_INSERT_MIN) { + emc_insert(cache, key, flow); + } +} + static inline struct dp_netdev_flow * emc_lookup(struct emc_cache *cache, const struct netdev_flow_key *key) { @@ -4092,7 +4108,7 @@ handle_packet_upcall(struct dp_netdev_pmd_thread *pmd, struct dp_packet *packet, } ovs_mutex_unlock(&pmd->flow_mutex); - emc_insert(&pmd->flow_cache, key, netdev_flow); + emc_probabilistic_insert(pmd, &pmd->flow_cache, key, netdev_flow); } } @@ -4187,7 +4203,7 @@ fast_path_processing(struct dp_netdev_pmd_thread *pmd, flow = dp_netdev_flow_cast(rules[i]); - emc_insert(flow_cache, &keys[i], flow); + emc_probabilistic_insert(pmd, flow_cache, &keys[i], flow); dp_netdev_queue_batches(packet, flow, &keys[i].mf, batches, n_batches); } -- 2.4.3 _______________________________________________ dev mailing list [email protected] https://mail.openvswitch.org/mailman/listinfo/ovs-dev
