use crate::raw::PulseMapRaw;
use crate::{PulseKey, PulseValue, SlotState};
pub struct RawIter<'a> {
map: &'a PulseMapRaw,
bucket_idx: usize,
slot_idx: u8,
}
impl<'a> RawIter<'a> {
pub fn new(map: &'a PulseMapRaw) -> Self {
Self {
map,
bucket_idx: 0,
slot_idx: 0,
}
}
}
impl<'a> Iterator for RawIter<'a> {
type Item = (&'a [u8], &'a [u8]);
fn next(&mut self) -> Option<Self::Item> {
let num_buckets = self.map.num_buckets();
while self.bucket_idx < num_buckets {
let bucket = &self.map.buckets[self.bucket_idx];
while self.slot_idx < 4 {
let idx = self.slot_idx;
self.slot_idx += 1;
if bucket.meta.get_state(idx) == SlotState::Full {
let slot = &bucket.slots[idx as usize];
let key = if slot.get_mode() == 0 {
slot.inline_key()
} else {
slot.slab_key(&self.map.slab_pool)
};
let value = slot.get_value(&self.map.slab_pool);
return Some((key, value));
}
}
self.bucket_idx += 1;
self.slot_idx = 0;
}
None
}
}
pub struct TypedIter<'a, K: PulseKey, V: PulseValue> {
raw_iter: RawIter<'a>,
_marker: core::marker::PhantomData<(K, V)>,
}
impl<'a, K: PulseKey, V: PulseValue> TypedIter<'a, K, V> {
pub fn new(map: &'a PulseMapRaw) -> Self {
Self {
raw_iter: RawIter::new(map),
_marker: core::marker::PhantomData,
}
}
}
impl<'a, K: PulseKey, V: PulseValue> Iterator for TypedIter<'a, K, V> {
type Item = (K, V);
fn next(&mut self) -> Option<Self::Item> {
loop {
let (kb, vb) = self.raw_iter.next()?;
if let (Some(k), Some(v)) = (K::from_bytes(kb), V::from_bytes(vb)) {
return Some((k, v));
}
}
}
}