Skip to content

Commit 475e57d

Browse files
committed
Add a few ops needed to use this in iroh-quinn
1 parent 513f89c commit 475e57d

File tree

1 file changed

+38
-8
lines changed

1 file changed

+38
-8
lines changed

src/lib.rs

Lines changed: 38 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -22,10 +22,10 @@
2222
///
2323
/// Access is O(1). Insertion and removal is usually O(1), but will occasionally
2424
/// move contents around to resize the buffer, which is O(n). Moving will only
25-
/// happem every O(n.next_power_of_two()) operations, so amortized complexity is
25+
/// happen every O(n.next_power_of_two()) operations, so amortized complexity is
2626
/// still O(1).
27-
#[derive(Debug)]
28-
pub struct PacketBuffer<T> {
27+
#[derive(Debug, Clone)]
28+
pub struct PacketBuf<T> {
2929
/// The underlying data buffer. Size is a power of two, 2 "pages".
3030
data: Vec<Option<T>>,
3131
/// The minimum valid index (inclusive).
@@ -34,13 +34,13 @@ pub struct PacketBuffer<T> {
3434
max: u64,
3535
}
3636

37-
impl<T> Default for PacketBuffer<T> {
37+
impl<T> Default for PacketBuf<T> {
3838
fn default() -> Self {
3939
Self::new()
4040
}
4141
}
4242

43-
impl<T> PacketBuffer<T> {
43+
impl<T> PacketBuf<T> {
4444
/// Create a new PacketBuffer with the given initial capacity.
4545
pub fn with_capacity(capacity: usize) -> Self {
4646
let data = Vec::with_capacity(capacity);
@@ -89,6 +89,17 @@ impl<T> PacketBuffer<T> {
8989
.filter_map(|slot| slot.as_ref())
9090
}
9191

92+
/// Iterate over all values in the given index range in ascending order of their keys.
93+
pub fn values_range_mut<R: std::ops::RangeBounds<u64>>(
94+
&mut self,
95+
range: R,
96+
) -> impl DoubleEndedIterator<Item = &mut T> + '_ {
97+
let (buf_start, buf_end, _) = self.resolve_range(range);
98+
self.data[buf_start..buf_end]
99+
.iter_mut()
100+
.filter_map(|slot| slot.as_mut())
101+
}
102+
92103
/// Iterate over all (index, value) pairs in the given index range in ascending order of their keys.
93104
pub fn iter_range<R: std::ops::RangeBounds<u64>>(
94105
&self,
@@ -132,15 +143,31 @@ impl<T> PacketBuffer<T> {
132143
self.values_range(..)
133144
}
134145

146+
/// Iterate over all values in the buffer in ascending order of their keys.
147+
pub fn values_mut(&mut self) -> impl DoubleEndedIterator<Item = &mut T> + '_ {
148+
self.values_range_mut(..)
149+
}
150+
135151
/// Iterate over all (index, value) pairs in the buffer in ascending order of their keys.
136152
///
137153
/// Values are returned by reference.
138154
pub fn iter(&self) -> impl DoubleEndedIterator<Item = (u64, &T)> + '_ {
139155
self.iter_range(..)
140156
}
141157

158+
/// Turn into an iterator over all (index, value) pairs in the buffer in ascending order of their keys.
159+
pub fn into_iter(self) -> impl DoubleEndedIterator<Item = (u64, T)> {
160+
let base = base(self.min, self.max);
161+
self.data
162+
.into_iter()
163+
.enumerate()
164+
.filter_map(move |(i, slot)| slot.map(|v| (base + i as u64, v)))
165+
}
166+
142167
/// Convert range bounds into an inclusive start and exclusive end, clipped to the current
143168
/// bounds.
169+
///
170+
/// The resulting range may be empty, which has to be handled by the caller.
144171
#[inline]
145172
fn clip_bounds<R: std::ops::RangeBounds<u64>>(&self, range: R) -> (u64, u64) {
146173
use std::ops::Bound;
@@ -161,6 +188,9 @@ impl<T> PacketBuffer<T> {
161188
#[inline]
162189
fn resolve_range<R: std::ops::RangeBounds<u64>>(&self, range: R) -> (usize, usize, u64) {
163190
let (start, end) = self.clip_bounds(range);
191+
if start >= end {
192+
return (0, 0, start);
193+
}
164194
let base = base(self.min, self.max);
165195
let buf_start = (start - base) as usize;
166196
let buf_end = (end - base) as usize;
@@ -393,7 +423,7 @@ mod tests {
393423
fn test_usage() {
394424
let elements = lag_permute(0..10000, 100).collect::<Vec<_>>();
395425
let mut reference = BTreeMap::<u64, u64>::new();
396-
let mut pb = PacketBuffer::<u64>::default();
426+
let mut pb = PacketBuf::<u64>::default();
397427
let d = 100;
398428
let add = elements
399429
.iter()
@@ -419,7 +449,7 @@ mod tests {
419449

420450
#[test]
421451
fn test_range_iterators() {
422-
let mut pb = PacketBuffer::default();
452+
let mut pb = PacketBuf::default();
423453
for i in 0..100 {
424454
pb.insert(i, i * 10);
425455
}
@@ -443,7 +473,7 @@ mod tests {
443473

444474
#[test]
445475
fn test_retain_range() {
446-
let mut pb = PacketBuffer::default();
476+
let mut pb = PacketBuf::default();
447477
for i in 0..100 {
448478
pb.insert(i, i * 10);
449479
}

0 commit comments

Comments
 (0)