From 3e0bde68b876de878e72f9f4faa017bbab36e06c Mon Sep 17 00:00:00 2001 From: "sijie.sun" Date: Sat, 13 Jun 2026 13:28:50 +0800 Subject: [PATCH] perf: bound shared nic flow eviction Replace full flow table clears with a small FIFO order queue so overflow evicts only older flow ownership hints. Keep lookup read-only on the packet hot path and prune stale queue entries when a shared member unregisters. --- .../instance/shared_virtual_nic/dispatcher.rs | 21 ++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) diff --git a/easytier/src/instance/shared_virtual_nic/dispatcher.rs b/easytier/src/instance/shared_virtual_nic/dispatcher.rs index 8c8c1233..ba8484b2 100644 --- a/easytier/src/instance/shared_virtual_nic/dispatcher.rs +++ b/easytier/src/instance/shared_virtual_nic/dispatcher.rs @@ -1,5 +1,5 @@ use std::{ - collections::{BTreeMap, HashMap}, + collections::{BTreeMap, HashMap, VecDeque}, pin::Pin, sync::{ Arc, Mutex as StdMutex, @@ -256,6 +256,7 @@ impl SharedVirtualNicFlowKey { #[derive(Default)] struct SharedVirtualNicFlowTable { owners: HashMap, + insert_order: VecDeque, } impl SharedVirtualNicFlowTable { @@ -265,8 +266,9 @@ impl SharedVirtualNicFlowTable { return; }; - if !self.owners.contains_key(&key) && self.owners.len() >= FLOW_OWNER_LIMIT { - self.owners.clear(); + if !self.owners.contains_key(&key) { + self.evict_before_insert(); + self.insert_order.push_back(key); } self.owners.insert(key, member_id); } @@ -278,10 +280,23 @@ impl SharedVirtualNicFlowTable { fn remove_owner(&mut self, member_id: SharedVirtualNicMemberId) { self.owners.retain(|_, owner| *owner != member_id); + self.insert_order + .retain(|key| self.owners.contains_key(key)); } fn clear(&mut self) { self.owners.clear(); + self.insert_order.clear(); + } + + fn evict_before_insert(&mut self) { + while self.owners.len() >= FLOW_OWNER_LIMIT { + let Some(key) = self.insert_order.pop_front() else { + self.owners.clear(); + return; + }; + self.owners.remove(&key); + } } }