From 3ba21d4c99b499dde16d23377e405d992d31a673 Mon Sep 17 00:00:00 2001 From: Levi Morrison Date: Tue, 8 Apr 2025 11:01:55 -0600 Subject: [PATCH 1/4] chore(ddtelemetry): migrate from RawTable to HashTable API Update the QueueHashMap implementation to use the newer, more stable HashTable API from hashbrown. This change maintains the same functionality while using the recommended API. --- ddtelemetry/src/worker/store.rs | 34 ++++++++++++++++----------------- 1 file changed, 16 insertions(+), 18 deletions(-) diff --git a/ddtelemetry/src/worker/store.rs b/ddtelemetry/src/worker/store.rs index 5619f6b359..bab5862c17 100644 --- a/ddtelemetry/src/worker/store.rs +++ b/ddtelemetry/src/worker/store.rs @@ -4,14 +4,14 @@ use std::{collections::VecDeque, hash::Hash}; mod queuehasmpap { - use hashbrown::{hash_map::DefaultHashBuilder, raw::RawTable}; + use hashbrown::{hash_map::DefaultHashBuilder, hash_table::HashTable}; use std::{ collections::VecDeque, hash::{BuildHasher, Hash}, }; pub struct QueueHashMap { - table: RawTable, + table: HashTable, hash_builder: DefaultHashBuilder, items: VecDeque<(K, V)>, popped: usize, @@ -41,8 +41,9 @@ mod queuehasmpap { pub fn pop_front(&mut self) -> Option<(K, V)> { let (k, v) = self.items.pop_front()?; let hash = make_hash(&self.hash_builder, &k); - let found = self.table.remove_entry(hash, |other| *other == self.popped); - debug_assert!(found.is_some()); + if let Ok(entry) = self.table.find_entry(hash, |&other| other == self.popped) { + entry.remove(); + } debug_assert!(self.items.len() == self.table.len()); self.popped += 1; Some((k, v)) @@ -52,8 +53,8 @@ mod queuehasmpap { let hash = make_hash(&self.hash_builder, k); let idx = self .table - .get(hash, |other| &self.items[other - self.popped].0 == k)?; - Some(&self.items[idx - self.popped].1) + .find(hash, |other| &self.items[other - self.popped].0 == k)?; + Some(&self.items[*idx - self.popped].1) } pub fn get_idx(&self, idx: usize) -> Option<&(K, V)> { @@ -62,11 +63,11 @@ mod queuehasmpap { pub fn get_mut_or_insert(&mut self, key: K, default: V) -> (&mut V, bool) { let hash = make_hash(&self.hash_builder, &key); - if let Some(&idx) = self + if let Some(idx) = self .table - .get(hash, |other| self.items[other - self.popped].0 == key) + .find(hash, |other| self.items[other - self.popped].0 == key) { - return (&mut self.items[idx - self.popped].1, false); + return (&mut self.items[*idx - self.popped].1, false); } self.insert_nocheck(hash, key, default); @@ -74,17 +75,14 @@ mod queuehasmpap { (&mut self.items.back_mut().unwrap().1, true) } - // Insert a new item at the back if the queue if it doesn't yet exist. - // - // If the key already exists, replace the previous value pub fn insert(&mut self, key: K, value: V) -> (usize, bool) { let hash = make_hash(&self.hash_builder, &key); - if let Some(&idx) = self + if let Some(idx) = self .table - .get(hash, |other| self.items[other - self.popped].0 == key) + .find(hash, |other| self.items[other - self.popped].0 == key) { - self.items[idx - self.popped].1 = value; - (idx, false) + self.items[*idx - self.popped].1 = value; + (*idx, false) } else { (self.insert_nocheck(hash, key, value), true) } @@ -108,7 +106,7 @@ mod queuehasmpap { hash_builder, .. } = self; - table.insert(hash, item_index, |i| { + table.insert_unique(hash, item_index, |i| { make_hash(hash_builder, &items[i - *popped].0) }); self.items.push_back((key, value)); @@ -119,7 +117,7 @@ mod queuehasmpap { impl Default for QueueHashMap { fn default() -> Self { Self { - table: RawTable::new(), + table: HashTable::new(), hash_builder: DefaultHashBuilder::default(), items: VecDeque::new(), popped: 0, From a07dde202da416348d5867c4624032a0289ea75f Mon Sep 17 00:00:00 2001 From: Levi Morrison Date: Tue, 8 Apr 2025 11:07:56 -0600 Subject: [PATCH 2/4] chore(ddtelemetry): update hashbrown to v0.15 Update hashbrown dependency to v0.15 and fix DefaultHashBuilder import path. The raw feature is no longer needed since we migrated to the hash_table module. --- Cargo.lock | 13 ++++++++++++- LICENSE-3rdparty.yml | 26 ++++++++++++++++++++++++++ ddtelemetry/Cargo.toml | 2 +- ddtelemetry/src/worker/store.rs | 2 +- 4 files changed, 40 insertions(+), 3 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 92642ab076..097e49864e 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1918,7 +1918,7 @@ dependencies = [ "datadog-ddsketch", "ddcommon", "futures", - "hashbrown 0.14.5", + "hashbrown 0.15.1", "http 1.1.0", "http-body-util", "hyper 1.6.0", @@ -2307,6 +2307,12 @@ version = "1.0.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" +[[package]] +name = "foldhash" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d9c4f5dac5e15c24eb999c26181a6ca40b39fe946cbe4c263c7209467bc83af2" + [[package]] name = "form_urlencoded" version = "1.2.1" @@ -2618,6 +2624,11 @@ name = "hashbrown" version = "0.15.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3a9bfc1af68b1726ea47d3d5109de126281def866b33970e10fbab11b5dafab3" +dependencies = [ + "allocator-api2", + "equivalent", + "foldhash", +] [[package]] name = "hdrhistogram" diff --git a/LICENSE-3rdparty.yml b/LICENSE-3rdparty.yml index 8a9a343cf7..83fbb12e93 100644 --- a/LICENSE-3rdparty.yml +++ b/LICENSE-3rdparty.yml @@ -11924,6 +11924,32 @@ third_party_libraries: OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +- package_name: foldhash + package_version: 0.1.5 + repository: https://github.com/orlp/foldhash + license: Zlib + licenses: + - license: Zlib + text: |- + Copyright (c) 2024 Orson Peters + + This software is provided 'as-is', without any express or implied warranty. In + no event will the authors be held liable for any damages arising from the use of + this software. + + Permission is granted to anyone to use this software for any purpose, including + commercial applications, and to alter it and redistribute it freely, subject to + the following restrictions: + + 1. The origin of this software must not be misrepresented; you must not claim + that you wrote the original software. If you use this software in a product, + an acknowledgment in the product documentation would be appreciated but is + not required. + + 2. Altered source versions must be plainly marked as such, and must not be + misrepresented as being the original software. + + 3. This notice may not be removed or altered from any source distribution. - package_name: form_urlencoded package_version: 1.2.1 repository: https://github.com/servo/rust-url diff --git a/ddtelemetry/Cargo.toml b/ddtelemetry/Cargo.toml index c62e254e2c..f8bf1ecbc1 100644 --- a/ddtelemetry/Cargo.toml +++ b/ddtelemetry/Cargo.toml @@ -32,7 +32,7 @@ tokio-util = { version = "0.7", features = ["codec"] } tracing = { version = "0.1", default-features = false } uuid = { version = "1.3", features = ["v4"] } -hashbrown = { version = "0.14", features = ["raw"] } +hashbrown = "0.15" [dev-dependencies] tracing-subscriber = "0.3.18" diff --git a/ddtelemetry/src/worker/store.rs b/ddtelemetry/src/worker/store.rs index bab5862c17..78967b588f 100644 --- a/ddtelemetry/src/worker/store.rs +++ b/ddtelemetry/src/worker/store.rs @@ -4,7 +4,7 @@ use std::{collections::VecDeque, hash::Hash}; mod queuehasmpap { - use hashbrown::{hash_map::DefaultHashBuilder, hash_table::HashTable}; + use hashbrown::{hash_table::HashTable, DefaultHashBuilder}; use std::{ collections::VecDeque, hash::{BuildHasher, Hash}, From 47422fd8cc3763ccd1cba28dbbcdfa02bead7eec Mon Sep 17 00:00:00 2001 From: Levi Morrison Date: Tue, 8 Apr 2025 11:23:29 -0600 Subject: [PATCH 3/4] style(ddtelemetry): fix typos in module name --- ddtelemetry/src/worker/store.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/ddtelemetry/src/worker/store.rs b/ddtelemetry/src/worker/store.rs index 78967b588f..81ab261745 100644 --- a/ddtelemetry/src/worker/store.rs +++ b/ddtelemetry/src/worker/store.rs @@ -3,7 +3,7 @@ use std::{collections::VecDeque, hash::Hash}; -mod queuehasmpap { +mod queuehashmap { use hashbrown::{hash_table::HashTable, DefaultHashBuilder}; use std::{ collections::VecDeque, @@ -130,7 +130,7 @@ mod queuehasmpap { } } -pub use queuehasmpap::QueueHashMap; +pub use queuehashmap::QueueHashMap; #[derive(Default)] /// Stores telemetry data item, like dependencies and integrations From 3f154f9df6ad2c9d34f634f2d04f2027766ded93 Mon Sep 17 00:00:00 2001 From: Levi Morrison Date: Tue, 8 Apr 2025 11:52:23 -0600 Subject: [PATCH 4/4] docs(ddtelemetry): restore deleted comment --- ddtelemetry/src/worker/store.rs | 3 +++ 1 file changed, 3 insertions(+) diff --git a/ddtelemetry/src/worker/store.rs b/ddtelemetry/src/worker/store.rs index 81ab261745..8bcf9ca2cd 100644 --- a/ddtelemetry/src/worker/store.rs +++ b/ddtelemetry/src/worker/store.rs @@ -75,6 +75,9 @@ mod queuehashmap { (&mut self.items.back_mut().unwrap().1, true) } + // Insert a new item at the back if the queue if it doesn't yet exist. + // + // If the key already exists, replace the previous value pub fn insert(&mut self, key: K, value: V) -> (usize, bool) { let hash = make_hash(&self.hash_builder, &key); if let Some(idx) = self