libutils_log/
iterators.rs1use super::Log;
7
8use core::{
10 slice::Iter,
11 mem::ManuallyDrop,
12 alloc::{
13 Layout,
14 Allocator
15 }
16};
17
18use libutils_pointer::Pointer;
20
21use alloc::alloc::Global;
23
24
25pub struct Iterable<Type> {
31 pointer: Pointer<Type>,
32 length: usize,
33 index: usize,
34 layout: Layout
35} impl<Type> Iterator for Iterable<Type> {
36 type Item = Type;
37 #[inline]
38 fn next(&mut self) -> Option<Self::Item> {
39 let value = if self.index < self.length {
40 Some(unsafe {self.pointer.add(self.index).read()?})
41 } else {None};
42 self.index += 1;
43 return value;
44 }
45} impl<Type> Drop for Iterable<Type> {
46 fn drop(&mut self) {
47 while let Some(_) = self.next() {}
48 if let Some(pointer) = self.pointer.take() {
49 unsafe {Global.deallocate(pointer.cast(), self.layout)}
50 }
51 }
52}
53
54impl<Type> FromIterator<Type> for Log<Type> {
56 fn from_iter<T: IntoIterator<Item = Type>>(iter: T) -> Self {
57 let mut log = Log::new();
58 log.extend(iter);
59 return log;
60 }
61}
62
63const impl<Type> IntoIterator for Log<Type> {
65 type Item = Type;
66 type IntoIter = Iterable<Type>;
67 fn into_iter(self) -> Self::IntoIter {
68 let instance = ManuallyDrop::new(self);
69 return Iterable {
70 pointer: instance.pointer,
71 length: instance.length,
72 index: 0,
73 layout: unsafe {Layout::from_size_align(instance.capacity * size_of::<Type>(), align_of::<Type>()).unwrap_unchecked()}
74 }
75 }
76}
77
78const impl<'valid, Type> IntoIterator for &'valid Log<Type> {
80 type Item = &'valid Type;
81 type IntoIter = Iter<'valid, Type>;
82 fn into_iter(self) -> Self::IntoIter {self.iter()}
83}