#![allow(clippy::redundant_pub_crate)]
#[cfg(not(feature = "safe-map"))]
use core::mem::MaybeUninit;
use crate::dim::{Dim, MAX_DIMS};
#[cfg(not(feature = "safe-map"))]
#[derive(Debug)]
pub(crate) struct FixedMap {
slots: [MaybeUninit<u64>; MAX_DIMS],
present: [bool; MAX_DIMS],
}
#[cfg(not(feature = "safe-map"))]
impl FixedMap {
pub(crate) const fn new() -> Self {
Self {
slots: [MaybeUninit::uninit(); MAX_DIMS],
present: [false; MAX_DIMS],
}
}
pub(crate) fn get(&self, dim: Dim) -> Option<u64> {
let idx = dim.index();
#[allow(clippy::indexing_slicing)]
if self.present[idx] {
#[allow(clippy::indexing_slicing)]
Some(unsafe { self.slots[idx].assume_init() })
} else {
None
}
}
pub(crate) fn insert(&mut self, dim: Dim, value: u64) -> Option<u64> {
let idx = dim.index();
#[allow(clippy::indexing_slicing)]
let prev = if self.present[idx] {
#[allow(clippy::indexing_slicing)]
Some(unsafe { self.slots[idx].assume_init() })
} else {
None
};
#[allow(clippy::indexing_slicing)]
{
self.slots[idx] = MaybeUninit::new(value);
self.present[idx] = true;
}
prev
}
pub(crate) fn get_or(&self, dim: Dim, default: u64) -> u64 {
self.get(dim).unwrap_or(default)
}
pub(crate) fn contains(&self, dim: Dim) -> bool {
self.present.get(dim.index()).copied().unwrap_or(false)
}
pub(crate) fn is_empty(&self) -> bool {
!self.present.iter().any(|&p| p)
}
}
#[cfg(feature = "safe-map")]
#[derive(Debug)]
pub(crate) struct FixedMap {
slots: [u64; MAX_DIMS],
present: [bool; MAX_DIMS],
}
#[cfg(feature = "safe-map")]
impl FixedMap {
pub(crate) const fn new() -> Self {
Self {
slots: [0u64; MAX_DIMS],
present: [false; MAX_DIMS],
}
}
pub(crate) fn get(&self, dim: Dim) -> Option<u64> {
let idx = dim.index();
if self.present.get(idx).copied().unwrap_or(false) {
self.slots.get(idx).copied()
} else {
None
}
}
pub(crate) fn insert(&mut self, dim: Dim, value: u64) -> Option<u64> {
let idx = dim.index();
let prev = if self.present.get(idx).copied().unwrap_or(false) {
self.slots.get(idx).copied()
} else {
None
};
if let Some(slot) = self.slots.get_mut(idx) {
*slot = value;
}
if let Some(flag) = self.present.get_mut(idx) {
*flag = true;
}
prev
}
pub(crate) fn get_or(&self, dim: Dim, default: u64) -> u64 {
self.get(dim).unwrap_or(default)
}
pub(crate) fn contains(&self, dim: Dim) -> bool {
self.present.get(dim.index()).copied().unwrap_or(false)
}
pub(crate) fn is_empty(&self) -> bool {
!self.present.iter().any(|&p| p)
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::dim::Dim;
fn present_count(map: &FixedMap) -> usize {
Dim::ALL
.into_iter()
.filter(|&dim| map.contains(dim))
.count()
}
#[test]
fn new_map_is_empty() {
let m = FixedMap::new();
assert!(m.is_empty());
for dim in Dim::ALL {
assert!(!m.contains(dim));
assert!(m.get(dim).is_none());
}
}
#[test]
fn insert_and_get_roundtrip() {
let mut m = FixedMap::new();
assert!(m.insert(Dim::Tokens, 42).is_none());
assert_eq!(m.get(Dim::Tokens), Some(42));
assert!(m.contains(Dim::Tokens));
}
#[test]
fn insert_returns_previous_value() {
let mut m = FixedMap::new();
m.insert(Dim::Tokens, 10);
let prev = m.insert(Dim::Tokens, 20);
assert_eq!(prev, Some(10));
assert_eq!(m.get(Dim::Tokens), Some(20));
}
#[test]
fn get_or_returns_default_when_absent() {
let m = FixedMap::new();
assert_eq!(m.get_or(Dim::Millis, 99), 99);
}
#[test]
fn get_or_returns_stored_value_when_present() {
let mut m = FixedMap::new();
m.insert(Dim::Millis, 7);
assert_eq!(m.get_or(Dim::Millis, 99), 7);
}
#[test]
fn present_count_tracks_distinct_dimensions() {
let mut m = FixedMap::new();
assert_eq!(present_count(&m), 0);
m.insert(Dim::Tokens, 1);
assert_eq!(present_count(&m), 1);
m.insert(Dim::Bytes, 2);
assert_eq!(present_count(&m), 2);
m.insert(Dim::Tokens, 3);
assert_eq!(present_count(&m), 2);
}
#[test]
fn is_empty_tracks_insertions() {
let mut m = FixedMap::new();
assert!(m.is_empty());
let _ = m.insert(Dim::Tokens, 1);
assert!(!m.is_empty());
}
#[test]
fn dimensions_are_independent() {
let mut m = FixedMap::new();
m.insert(Dim::Tokens, 100);
m.insert(Dim::Bytes, 200);
assert_eq!(m.get(Dim::Tokens), Some(100));
assert_eq!(m.get(Dim::Bytes), Some(200));
assert!(m.get(Dim::Millis).is_none());
}
#[test]
fn all_dims_can_be_inserted_and_read() {
let mut m = FixedMap::new();
for (i, dim) in Dim::ALL.iter().enumerate() {
m.insert(*dim, i as u64);
}
assert_eq!(present_count(&m), MAX_DIMS);
for (i, dim) in Dim::ALL.iter().enumerate() {
assert_eq!(m.get(*dim), Some(i as u64));
}
}
#[test]
fn insert_overwrites_without_growing_present_count() {
let mut m = FixedMap::new();
m.insert(Dim::Calls, 1);
m.insert(Dim::Calls, 2);
m.insert(Dim::Calls, 3);
assert_eq!(present_count(&m), 1);
assert_eq!(m.get(Dim::Calls), Some(3));
}
}