arrayvec/
arrayvec_impl.rs

1use std::ptr;
2use std::slice;
3
4use crate::CapacityError;
5
6/// Implements basic arrayvec methods - based on a few required methods
7/// for length and element access.
8pub(crate) trait ArrayVecImpl {
9    type Item;
10    const CAPACITY: usize;
11
12    fn len(&self) -> usize;
13
14    unsafe fn set_len(&mut self, new_len: usize);
15
16    /// Return a slice containing all elements of the vector.
17    fn as_slice(&self) -> &[Self::Item] {
18        let len = self.len();
19        unsafe {
20            slice::from_raw_parts(self.as_ptr(), len)
21        }
22    }
23
24    /// Return a mutable slice containing all elements of the vector.
25    fn as_mut_slice(&mut self) -> &mut [Self::Item] {
26        let len = self.len();
27        unsafe {
28            std::slice::from_raw_parts_mut(self.as_mut_ptr(), len)
29        }
30    }
31
32    /// Return a raw pointer to the vector's buffer.
33    fn as_ptr(&self) -> *const Self::Item;
34
35    /// Return a raw mutable pointer to the vector's buffer.
36    fn as_mut_ptr(&mut self) -> *mut Self::Item;
37
38    #[track_caller]
39    fn push(&mut self, element: Self::Item) {
40        self.try_push(element).unwrap()
41    }
42
43    fn try_push(&mut self, element: Self::Item) -> Result<(), CapacityError<Self::Item>> {
44        if self.len() < Self::CAPACITY {
45            unsafe {
46                self.push_unchecked(element);
47            }
48            Ok(())
49        } else {
50            Err(CapacityError::new(element))
51        }
52    }
53
54    unsafe fn push_unchecked(&mut self, element: Self::Item) {
55        let len = self.len();
56        debug_assert!(len < Self::CAPACITY);
57        ptr::write(self.as_mut_ptr().add(len), element);
58        self.set_len(len + 1);
59    }
60
61    fn pop(&mut self) -> Option<Self::Item> {
62        if self.len() == 0 {
63            return None;
64        }
65        unsafe {
66            let new_len = self.len() - 1;
67            self.set_len(new_len);
68            Some(ptr::read(self.as_ptr().add(new_len)))
69        }
70    }
71
72    fn clear(&mut self) {
73        self.truncate(0)
74    }
75
76    fn truncate(&mut self, new_len: usize) {
77        unsafe {
78            let len = self.len();
79            if new_len < len {
80                self.set_len(new_len);
81                let tail = slice::from_raw_parts_mut(self.as_mut_ptr().add(new_len), len - new_len);
82                ptr::drop_in_place(tail);
83            }
84        }
85    }
86}
87