rune_alloc/vec/
spec_from_elem.rs
1#[cfg(rune_nightly)]
2use core::ptr;
3
4use crate::alloc::Allocator;
5use crate::clone::TryClone;
6use crate::error::Error;
7#[cfg(rune_nightly)]
8use crate::raw_vec::RawVec;
9
10#[cfg(rune_nightly)]
11use super::IsZero;
12use super::Vec;
13
14pub(super) trait SpecFromElem: Sized {
16 fn from_elem<A: Allocator>(elem: Self, n: usize, alloc: A) -> Result<Vec<Self, A>, Error>;
17}
18
19impl<T> SpecFromElem for T
20where
21 T: TryClone,
22{
23 default_fn! {
24 fn from_elem<A: Allocator>(elem: Self, n: usize, alloc: A) -> Result<Vec<Self, A>, Error> {
25 let mut v = Vec::try_with_capacity_in(n, alloc)?;
26 v.try_extend_with(n, elem)?;
27 Ok(v)
28 }
29 }
30}
31
32#[cfg(rune_nightly)]
33impl<T> SpecFromElem for T
34where
35 T: TryClone + IsZero,
36{
37 #[inline]
38 default fn from_elem<A: Allocator>(elem: T, n: usize, alloc: A) -> Result<Vec<T, A>, Error> {
39 if elem.is_zero() {
40 return Ok(Vec {
41 buf: RawVec::try_with_capacity_zeroed_in(n, alloc)?,
42 len: n,
43 });
44 }
45
46 let mut v = Vec::try_with_capacity_in(n, alloc)?;
47 v.try_extend_with(n, elem)?;
48 Ok(v)
49 }
50}
51
52#[cfg(rune_nightly)]
53impl SpecFromElem for i8 {
54 #[inline]
55 fn from_elem<A: Allocator>(elem: i8, n: usize, alloc: A) -> Result<Vec<i8, A>, Error> {
56 if elem == 0 {
57 return Ok(Vec {
58 buf: RawVec::try_with_capacity_zeroed_in(n, alloc)?,
59 len: n,
60 });
61 }
62
63 unsafe {
64 let mut v = Vec::try_with_capacity_in(n, alloc)?;
65 ptr::write_bytes(v.as_mut_ptr(), elem as u8, n);
66 v.set_len(n);
67 Ok(v)
68 }
69 }
70}
71
72#[cfg(rune_nightly)]
73impl SpecFromElem for u8 {
74 #[inline]
75 fn from_elem<A: Allocator>(elem: u8, n: usize, alloc: A) -> Result<Vec<u8, A>, Error> {
76 if elem == 0 {
77 return Ok(Vec {
78 buf: RawVec::try_with_capacity_zeroed_in(n, alloc)?,
79 len: n,
80 });
81 }
82
83 unsafe {
84 let mut v = Vec::try_with_capacity_in(n, alloc)?;
85 ptr::write_bytes(v.as_mut_ptr(), elem, n);
86 v.set_len(n);
87 Ok(v)
88 }
89 }
90}