use core::ops::RangeInclusive;
#[cfg(feature = "alloc")]
use alloc::{ffi::CString, string::String};
use crate::prelude::*;
use crate::Int;
pub struct Source<'a, I: Iterator<Item = &'a u8>, E: EntropyScheme> {
pub(crate) iter: I,
scheme: E,
}
impl<'a, I: Iterator<Item = &'a u8>, E: EntropyScheme> Source<'a, I, E> {
#[inline]
pub fn new(iter: I) -> Self {
Self {
iter,
scheme: E::default(),
}
}
#[inline]
pub fn get_entropic<T: Entropic>(&mut self) -> Result<T, EntropicError> {
T::from_entropy_source(self)
}
#[inline]
pub fn get_uniform_range<T: Int>(
&mut self,
range: RangeInclusive<T>,
) -> Result<T, EntropicError> {
self.scheme.get_uniform_range(&mut self.iter, range)
}
#[inline]
pub fn get_uniform_ranges<T: Int, const L: usize>(
&mut self,
ranges: &[RangeInclusive<T>; L],
) -> Result<T, EntropicError> {
self.scheme.get_uniform_ranges(&mut self.iter, ranges)
}
#[inline]
pub fn get_bounded_len(
&mut self,
range: RangeInclusive<usize>,
) -> Result<usize, EntropicError> {
self.scheme.get_bounded_len(&mut self.iter, range)
}
#[inline]
pub fn get_unbounded_len(&mut self) -> Result<usize, EntropicError> {
self.scheme.get_unbounded_len(&mut self.iter)
}
#[inline]
pub fn get_bool(&mut self) -> Result<bool, EntropicError> {
self.scheme.get_bool(&mut self.iter)
}
#[inline]
pub fn get_char(&mut self) -> Result<char, EntropicError> {
self.scheme.get_char(&mut self.iter)
}
#[cfg(feature = "alloc")]
#[inline]
pub fn get_string(&mut self) -> Result<String, EntropicError> {
self.scheme.get_string(&mut self.iter)
}
#[cfg(feature = "alloc")]
#[inline]
pub fn get_cstring(&mut self) -> Result<CString, EntropicError> {
self.scheme.get_cstring(&mut self.iter)
}
#[inline]
pub fn get_byte(&mut self) -> Result<u8, EntropicError> {
self.scheme.get_byte(&mut self.iter)
}
#[inline]
pub fn get_slice(&mut self, slice: &mut [u8]) -> Result<(), EntropicError> {
self.scheme.get_slice(&mut self.iter, slice)
}
#[inline]
pub fn get_bytearray<const T: usize>(&mut self) -> Result<[u8; T], EntropicError> {
self.scheme.get_bytearray(&mut self.iter)
}
#[inline]
pub fn get_optional(&mut self) -> Result<bool, EntropicError> {
self.scheme.get_optional(&mut self.iter)
}
}
pub trait AsSource<'a> {
type I: Iterator<Item = &'a u8>;
fn to_source<E: EntropyScheme>(self) -> Source<'a, Self::I, E>;
}
impl<'a, T: IntoIterator<Item = &'a u8> + Clone> AsSource<'a> for T {
type I = T::IntoIter;
#[inline]
fn to_source<E: EntropyScheme>(self) -> Source<'a, Self::I, E> {
Source {
iter: self.into_iter(),
scheme: E::default(),
}
}
}