Skip to main content

musli/alloc/
array_buffer.rs

1use core::mem::MaybeUninit;
2use core::ops::{Deref, DerefMut};
3
4use super::DEFAULT_ARRAY_BUFFER;
5
6/// An array that can conveniently be used as a buffer, by default this is
7/// [`DEFAULT_ARRAY_BUFFER`] bytes large.
8///
9/// This is aligned to 8 bytes, since that's an alignment which works with many
10/// common Rust types.
11///
12/// See the [module level documentation][super] for more information.
13#[repr(align(8))]
14pub struct ArrayBuffer<const N: usize = DEFAULT_ARRAY_BUFFER> {
15    data: [MaybeUninit<u8>; N],
16}
17
18impl ArrayBuffer {
19    /// Construct a new buffer with the default size of
20    /// [`DEFAULT_ARRAY_BUFFER`].
21    ///
22    /// # Examples
23    ///
24    /// ```
25    /// use musli::alloc::ArrayBuffer;
26    ///
27    /// let buffer = ArrayBuffer::new();
28    /// assert_eq!(buffer.len(), 4096);
29    /// ```
30    pub const fn new() -> Self {
31        Self::with_size()
32    }
33}
34
35impl Default for ArrayBuffer {
36    #[inline]
37    fn default() -> Self {
38        Self::new()
39    }
40}
41
42impl<const N: usize> ArrayBuffer<N> {
43    /// Construct a new buffer with a custom size.
44    ///
45    /// # Examples
46    ///
47    /// ```
48    /// use musli::alloc::ArrayBuffer;
49    ///
50    /// let buffer = ArrayBuffer::<1024>::with_size();
51    /// assert_eq!(buffer.len(), 1024);
52    /// ```
53    pub const fn with_size() -> Self {
54        Self {
55            // SAFETY: This is safe to initialize, since it's just an array of
56            // contiguous uninitialized memory.
57            data: unsafe { MaybeUninit::uninit().assume_init() },
58        }
59    }
60}
61
62impl<const N: usize> Deref for ArrayBuffer<N> {
63    type Target = [MaybeUninit<u8>];
64
65    #[inline]
66    fn deref(&self) -> &Self::Target {
67        &self.data
68    }
69}
70
71impl<const N: usize> DerefMut for ArrayBuffer<N> {
72    #[inline]
73    fn deref_mut(&mut self) -> &mut Self::Target {
74        &mut self.data
75    }
76}