arc_slice/
slice_mut.rs

1use alloc::{string::String, vec::Vec};
2use core::{
3    any::Any,
4    borrow::{Borrow, BorrowMut},
5    cmp,
6    convert::Infallible,
7    fmt,
8    hash::{Hash, Hasher},
9    marker::PhantomData,
10    mem,
11    mem::{ManuallyDrop, MaybeUninit},
12    ops::{Deref, DerefMut},
13    ptr::NonNull,
14    slice,
15};
16
17#[cfg(not(feature = "oom-handling"))]
18use crate::layout::{ArcLayout, CloneNoAllocLayout, VecLayout};
19#[allow(unused_imports)]
20use crate::msrv::{NonNullExt, OptionExt, StrictProvenance};
21use crate::{
22    arc::Arc,
23    buffer::{
24        BorrowMetadata, BufferExt, BufferMut, BufferWithMetadata, Concatenable, DynBuffer,
25        Emptyable, Extendable, Slice, SliceExt, Zeroable,
26    },
27    error::{AllocError, AllocErrorImpl, TryReserveError},
28    layout::{AnyBufferLayout, DefaultLayoutMut, FromLayout, Layout, LayoutMut},
29    macros::{assume, is},
30    msrv::{ptr, NonZero},
31    slice::ArcSliceLayout,
32    utils::{
33        debug_slice, lower_hex, min_non_zero_cap, panic_out_of_range, transmute_checked,
34        try_transmute, upper_hex, UnwrapChecked, UnwrapInfallible,
35    },
36    ArcSlice,
37};
38#[cfg(feature = "serde")]
39use crate::{buffer::Buffer, utils::assert_checked};
40
41mod arc;
42mod vec;
43
44#[derive(Debug, Clone, Copy, PartialEq, Eq)]
45pub struct Data(NonNull<()>);
46
47impl Data {
48    fn addr(&self) -> NonZero<usize> {
49        self.0.addr().into()
50    }
51
52    fn into_arc<S: Slice + ?Sized, const ANY_BUFFER: bool>(
53        self,
54    ) -> ManuallyDrop<Arc<S, ANY_BUFFER>> {
55        ManuallyDrop::new(unsafe { Arc::from_raw(self.0) })
56    }
57}
58
59impl From<NonNull<()>> for Data {
60    fn from(value: NonNull<()>) -> Self {
61        Self(value)
62    }
63}
64
65impl<S: Slice + ?Sized, const ANY_BUFFER: bool> From<Arc<S, ANY_BUFFER>> for Data {
66    fn from(value: Arc<S, ANY_BUFFER>) -> Self {
67        Self(value.into_raw())
68    }
69}
70
71pub(crate) type TryReserveResult<T> = (Result<usize, TryReserveError>, NonNull<T>);
72
73#[allow(clippy::missing_safety_doc)]
74pub unsafe trait ArcSliceMutLayout {
75    const ANY_BUFFER: bool;
76    fn try_data_from_arc<S: Slice + ?Sized, const ANY_BUFFER: bool>(
77        arc: ManuallyDrop<Arc<S, ANY_BUFFER>>,
78    ) -> Option<Data> {
79        Some(ManuallyDrop::into_inner(arc).into())
80    }
81    unsafe fn data_from_vec<S: Slice + ?Sized, E: AllocErrorImpl>(
82        vec: S::Vec,
83        offset: usize,
84    ) -> Result<Data, (E, S::Vec)>;
85    fn clone<S: Slice + ?Sized, E: AllocErrorImpl>(
86        start: NonNull<S::Item>,
87        length: usize,
88        capacity: usize,
89        data: &mut Data,
90    ) -> Result<(), E>;
91    unsafe fn drop<S: Slice + ?Sized, const UNIQUE: bool>(
92        start: NonNull<S::Item>,
93        length: usize,
94        capacity: usize,
95        data: Data,
96    );
97    fn advance<S: Slice + ?Sized>(_data: Option<&mut Data>, _offset: usize) {}
98    fn truncate<S: Slice + ?Sized>(
99        _start: NonNull<S::Item>,
100        _length: usize,
101        _capacity: usize,
102        _data: &mut Data,
103    ) {
104    }
105    fn get_metadata<S: Slice + ?Sized, M: Any>(data: &Data) -> Option<&M>;
106    unsafe fn take_buffer<S: Slice + ?Sized, B: BufferMut<S>, const UNIQUE: bool>(
107        start: NonNull<S::Item>,
108        length: usize,
109        capacity: usize,
110        data: Data,
111    ) -> Option<B>;
112    unsafe fn take_array<T: Send + Sync + 'static, const N: usize, const UNIQUE: bool>(
113        start: NonNull<T>,
114        length: usize,
115        data: Data,
116    ) -> Option<[T; N]>;
117    fn is_unique<S: Slice + ?Sized>(data: Data) -> bool;
118    fn try_reserve<S: Slice + ?Sized, const UNIQUE: bool>(
119        start: NonNull<S::Item>,
120        length: usize,
121        capacity: usize,
122        data: &mut Data,
123        additional: usize,
124        allocate: bool,
125    ) -> TryReserveResult<S::Item>;
126    fn frozen_data<S: Slice + ?Sized, L: ArcSliceLayout, E: AllocErrorImpl>(
127        start: NonNull<S::Item>,
128        length: usize,
129        capacity: usize,
130        data: Data,
131    ) -> Option<L::Data>;
132    fn update_layout<S: Slice + ?Sized, L: ArcSliceMutLayout, E: AllocErrorImpl>(
133        start: NonNull<S::Item>,
134        length: usize,
135        capacity: usize,
136        data: Data,
137    ) -> Option<Data>;
138}
139
140/// A thread-safe, mutable and growable container.
141///
142/// `ArcSliceMut` has a smaller choice of [layout] than [`ArcSlice`], but can also wrap arbitrary
143/// buffers such as`Vec`, memory-mapped files, etc. Arbitrary metadata can also be attached to the
144/// buffer for contextual or domain-specific needs.
145///
146/// With `UNIQUE=true`, `ArcSliceMut` is roughly equivalent to a `Vec`. Additional capacity
147/// can be reserved and the slice can be extended. With `UNIQUE=false`, the slice may be shared,
148/// meaning that multiple `ArcSliceMut` may reference non-intersecting portions of the underlying
149/// buffer. In that case, capacity reservation might fail, but the slice will never be implicitly
150/// reallocated and copied. In any case, `ArcSliceMut` is cheaply convertible to [`ArcSlice`].
151///
152/// It is mainly intended to manipulate `[u8]`/`str` byte slices, to facilitate zero-copy
153/// operations in network programming, hence the aliases [`ArcBytesMut`]/[`ArcStrMut`]. But it can
154/// actually handle any type of slices, from strings with specific invariants to primitive slices
155/// with droppable items.
156///
157/// # Examples
158///
159/// ```rust
160/// use arc_slice::{ArcSlice, ArcSliceMut};
161///
162/// let mut s = ArcSliceMut::<[u8]>::with_capacity(64);
163/// s.push(b'h');
164/// s.extend_from_slice(b"ello");
165/// assert_eq!(s, b"hello");
166///
167/// let mut s = s.into_shared();
168/// let mut s2 = s.split_off(3);
169/// s.copy_from_slice(b"bye");
170/// s2.copy_from_slice(b"!!");
171/// s.try_unsplit(s2).unwrap();
172/// assert_eq!(s, b"bye!!");
173///
174/// let frozen: ArcSlice<[u8]> = s.freeze();
175/// assert_eq!(frozen, b"bye!!");
176/// ```
177///
178/// With shared memory:
179/// ```rust
180/// use std::{
181///     fs::File,
182///     path::{Path, PathBuf},
183/// };
184///
185/// use arc_slice::{buffer::AsMutBuffer, error::TryReserveError, layout::ArcLayout, ArcSliceMut};
186/// use memmap2::MmapMut;
187///
188/// # fn main() -> std::io::Result<()> {
189/// let path = Path::new("README.md").to_owned();
190/// # #[cfg(not(miri))]
191/// let file = File::options().read(true).write(true).open(&path)?;
192/// # #[cfg(not(miri))]
193/// let mmap = unsafe { MmapMut::map_mut(&file)? };
194/// # #[cfg(miri)]
195/// # let mmap = b"# arc-slice".to_vec();
196///
197/// let buffer = unsafe { AsMutBuffer::new(mmap) };
198/// let mut bytes: ArcSliceMut<[u8], ArcLayout<true>> =
199///     ArcSliceMut::from_buffer_with_metadata(buffer, path);
200/// bytes[..11].copy_from_slice(b"# arc-slice");
201/// assert!(bytes.starts_with(b"# arc-slice"));
202/// assert_eq!(bytes.metadata::<PathBuf>().unwrap(), Path::new("README.md"));
203/// # Ok(())
204/// # }
205/// ```
206///
207/// [layout]: crate::layout
208/// [`ArcBytesMut`]: crate::ArcBytesMut
209/// [`ArcStrMut`]: crate::ArcStrMut
210pub struct ArcSliceMut<
211    S: Slice + ?Sized,
212    L: LayoutMut = DefaultLayoutMut,
213    const UNIQUE: bool = true,
214> {
215    start: NonNull<S::Item>,
216    length: usize,
217    capacity: usize,
218    data: Option<Data>,
219    _phantom: PhantomData<L>,
220}
221
222impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> ArcSliceMut<S, L, UNIQUE> {
223    /// Returns the number of items in the slice.
224    ///
225    /// # Examples
226    ///
227    /// ```rust
228    /// use arc_slice::ArcSliceMut;
229    ///
230    /// let s = ArcSliceMut::<[u8]>::from(&[0, 1, 2]);
231    /// assert_eq!(s.len(), 3);
232    /// ```
233    pub const fn len(&self) -> usize {
234        self.length
235    }
236
237    /// Returns `true` if the slice contains no items.
238    ///
239    /// # Examples
240    ///
241    /// ```rust
242    /// use arc_slice::ArcSliceMut;
243    ///
244    /// let s = ArcSliceMut::<[u8]>::from(&[0, 1, 2]);
245    /// assert!(!s.is_empty());
246    ///
247    /// let s = ArcSliceMut::<[u8]>::from(&[]);
248    /// assert!(s.is_empty());
249    /// ```
250    pub const fn is_empty(&self) -> bool {
251        self.len() == 0
252    }
253
254    /// Returns a raw pointer to the slice's first item.
255    ///
256    /// See [`slice::as_ptr`].
257    pub const fn as_ptr(&self) -> *const S::Item {
258        self.start.as_ptr()
259    }
260
261    /// Returns a mutable raw pointer to the slice's first item.
262    ///
263    /// See [`slice::as_mut_ptr`].
264    pub fn as_mut_ptr(&mut self) -> *mut S::Item {
265        self.start.as_ptr()
266    }
267
268    /// Returns a reference to the underlying slice.
269    ///
270    /// Equivalent to `&self[..]`.
271    ///
272    /// # Examples
273    ///
274    /// ```rust
275    /// use arc_slice::ArcSliceMut;
276    ///
277    /// let s = ArcSliceMut::<[u8]>::from(b"hello world");
278    /// assert_eq!(s.as_slice(), b"hello world");
279    /// ```
280    pub fn as_slice(&self) -> &S {
281        unsafe { S::from_raw_parts(self.start, self.len()) }
282    }
283
284    /// Returns a mutable reference to the underlying slice.
285    ///
286    /// Equivalent to `&mut self[..]`.
287    ///
288    /// # Examples
289    ///
290    /// ```rust
291    /// use arc_slice::ArcSliceMut;
292    ///
293    /// let mut s = ArcSliceMut::<[u8]>::from(b"hello world");
294    /// assert_eq!(s.as_mut_slice(), b"hello world");
295    /// ```
296    pub fn as_mut_slice(&mut self) -> &mut S {
297        unsafe { S::from_raw_parts_mut(self.start, self.len()) }
298    }
299
300    /// Returns the total number of items the slice can hold without reallocating.
301    ///
302    /// ```rust
303    /// use arc_slice::ArcSliceMut;
304    ///
305    /// let mut s = ArcSliceMut::<[u8]>::with_capacity(64);
306    /// s.push(0);
307    /// assert_eq!(s.capacity(), 64);
308    /// ```
309    pub const fn capacity(&self) -> usize {
310        self.capacity
311    }
312
313    fn spare_capacity(&self) -> usize {
314        self.capacity - self.length
315    }
316
317    /// Returns the remaining spare capacity of the slice.
318    ///
319    /// The returned slice can be used to fill the slice with items before marking the data as
320    /// initialized using the [`set_len`](Self::set_len) method.
321    ///
322    /// # Safety
323    ///
324    /// Writing uninitialized memory may be unsound if the underlying buffer doesn't support it.
325    ///
326    /// # Examples
327    ///
328    /// ```rust
329    /// use arc_slice::ArcSliceMut;
330    /// let mut s = ArcSliceMut::<[u8]>::with_capacity(10);
331    ///
332    /// // SAFETY: no uninit bytes are written
333    /// let uninit = unsafe { s.spare_capacity_mut() };
334    /// uninit[0].write(0);
335    /// uninit[1].write(1);
336    /// uninit[2].write(2);
337    /// // SAFETY: the first 3 bytes are initialized
338    /// unsafe { s.set_len(3) }
339    ///
340    /// assert_eq!(s, [0, 1, 2]);
341    /// ```
342    pub unsafe fn spare_capacity_mut(&mut self) -> &mut [MaybeUninit<S::Item>]
343    where
344        S: Extendable,
345    {
346        unsafe {
347            let end = self.start.as_ptr().add(self.length).cast();
348            slice::from_raw_parts_mut(end, self.spare_capacity())
349        }
350    }
351
352    /// Forces the length of the slice to `new_len`.
353    ///
354    /// # Safety
355    ///
356    /// First `len` items of the slice must be initialized.
357    ///
358    /// # Examples
359    ///
360    /// ```rust
361    /// use arc_slice::ArcSliceMut;
362    /// let mut s = ArcSliceMut::<[u8]>::with_capacity(10);
363    ///
364    /// // SAFETY: `s.capacity()` >= 3
365    /// unsafe { std::ptr::copy_nonoverlapping([0, 1, 2].as_ptr(), s.as_mut_ptr(), 3) };
366    ///
367    /// // SAFETY: the first 3 bytes are initialized
368    /// unsafe { s.set_len(3) }
369    ///
370    /// assert_eq!(s, [0, 1, 2]);
371    /// ```
372    pub unsafe fn set_len(&mut self, new_len: usize)
373    where
374        S: Extendable,
375    {
376        self.length = new_len;
377    }
378
379    /// Tries appending an element to the end of the slice, returning an error if the capacity
380    /// reservation fails.
381    ///
382    /// The buffer might have to reserve additional capacity to do the appending.
383    ///
384    /// The default arc-slice buffer supports amortized reservation, doubling the capacity each
385    /// time.
386    ///
387    /// # Examples
388    ///
389    /// ```rust
390    /// use arc_slice::ArcSliceMut;
391    ///
392    /// # fn main() -> Result<(), arc_slice::error::TryReserveError> {
393    /// let mut s = ArcSliceMut::<[u8]>::new();
394    /// s.try_push(42)?;
395    /// assert_eq!(s, [42]);
396    /// # Ok(())
397    /// # }
398    /// ```
399    pub fn try_push(&mut self, item: S::Item) -> Result<(), TryReserveError>
400    where
401        S: Extendable,
402    {
403        self.try_reserve(1)?;
404        unsafe { self.start.as_ptr().add(self.length).write(item) };
405        self.length += 1;
406        Ok(())
407    }
408
409    /// Tries reclaiming additional capacity for at least `additional` more items without
410    /// reallocating the buffer, returning `true` if it succeeds.
411    ///
412    /// Does nothing if the spare capacity is greater than the requested one.
413    ///
414    /// Reclaiming means shifting the current slice to the front of the buffer. It is only possible
415    /// when the `ArcSliceMut` is unique, and when the slice doesn't overlap with the spare
416    /// capacity at the buffer front.
417    ///
418    /// The reclaimed capacity might be greater than the requested one.
419    ///
420    /// # Examples
421    ///
422    /// ```rust
423    /// use arc_slice::ArcSliceMut;
424    ///
425    /// let mut s = ArcSliceMut::<[u8]>::from_iter(0..64);
426    /// let ptr = s.as_ptr();
427    /// s.advance(60);
428    /// assert_eq!(s.capacity(), 4);
429    /// assert_eq!(s, [60, 61, 62, 63]);
430    ///
431    /// // Reclamation of less than 60 bytes succeeds, bringing back the full capacity.
432    /// assert!(s.try_reclaim(16));
433    /// assert_eq!(s.capacity(), 64);
434    /// assert_eq!(s, [60, 61, 62, 63]);
435    /// assert_eq!(s.as_ptr(), ptr);
436    /// // Trying reclaiming more capacity fails.
437    /// assert!(!s.try_reclaim(100));
438    /// ```
439    pub fn try_reclaim(&mut self, additional: usize) -> bool {
440        self.try_reserve_impl(additional, false).is_ok()
441    }
442
443    /// Tries reserving capacity for at least `additional` more items, returning an error if the
444    /// operation fails.
445    ///
446    /// Does nothing if the spare capacity is greater than the requested one.
447    ///
448    /// Reserving is only possible when the `ArcSliceMut` is unique, and when it is supported by
449    /// the underlying buffer. It always attempts to [reclaim](Self::try_reclaim) first, and
450    /// reallocates the buffer if that fails.
451    ///
452    /// The default arc-slice buffer supports amortized reservation, doubling the capacity each
453    /// time. The reserved capacity might be greater than the requested one.
454    ///
455    /// # Examples
456    ///
457    /// ```rust
458    /// use arc_slice::ArcSliceMut;
459    ///
460    /// # fn main() -> Result<(), arc_slice::error::TryReserveError> {
461    /// let mut s = ArcSliceMut::<[u8]>::new();
462    /// s.try_reserve(3)?;
463    /// assert!(s.capacity() >= 3);
464    /// s.extend_from_slice(&[0, 1, 2]);
465    /// assert_eq!(s, [0, 1, 2]);
466    /// # Ok(())
467    /// # }
468    /// ```
469    pub fn try_reserve(&mut self, additional: usize) -> Result<(), TryReserveError> {
470        self.try_reserve_impl(additional, true)
471    }
472
473    fn try_reserve_impl(
474        &mut self,
475        additional: usize,
476        allocate: bool,
477    ) -> Result<(), TryReserveError> {
478        if additional <= self.spare_capacity() {
479            return Ok(());
480        }
481        let res = self.try_reserve_cold(additional, allocate);
482        unsafe { assume!(res.is_err() || self.spare_capacity() >= additional) };
483        res
484    }
485
486    #[cold]
487    fn try_reserve_cold(
488        &mut self,
489        additional: usize,
490        allocate: bool,
491    ) -> Result<(), TryReserveError> {
492        let (capacity, start) = match &mut self.data {
493            Some(data) => L::try_reserve::<S, UNIQUE>(
494                self.start,
495                self.length,
496                self.capacity,
497                data,
498                additional,
499                allocate,
500            ),
501            None if allocate => {
502                let capacity = cmp::max(min_non_zero_cap::<S::Item>(), additional);
503                let (arc, start) = Arc::<S>::with_capacity::<AllocError, false>(capacity)?;
504                self.data = Some(arc.into());
505                (Ok(capacity), start)
506            }
507            None => return Err(TryReserveError::Unsupported),
508        };
509        self.start = start;
510        self.capacity = capacity?;
511        Ok(())
512    }
513
514    /// Tries appending a slice to the end of slice, returning an error if the capacity
515    /// reservation fails.
516    ///
517    /// The buffer might have to reserve additional capacity to do the appending.
518    ///
519    /// The default arc-slice buffer supports amortized reservation, doubling the capacity each
520    /// time.
521    ///
522    /// ```rust
523    /// use arc_slice::ArcSliceMut;
524    ///
525    /// # fn main() -> Result<(), arc_slice::error::TryReserveError> {
526    /// let mut s = ArcSliceMut::<[u8]>::new();
527    /// s.try_extend_from_slice(b"hello world")?;
528    /// assert_eq!(s, b"hello world");
529    /// # Ok(())
530    /// # }
531    /// ```
532    pub fn try_extend_from_slice(&mut self, slice: &S) -> Result<(), TryReserveError>
533    where
534        S: Concatenable,
535        S::Item: Copy,
536    {
537        self.try_reserve(slice.len())?;
538        unsafe { self.extend_from_slice_unchecked(slice.to_slice()) };
539        Ok(())
540    }
541
542    unsafe fn extend_from_slice_unchecked(&mut self, slice: &[S::Item])
543    where
544        S: Concatenable,
545        S::Item: Copy,
546    {
547        unsafe {
548            let end = self.start.as_ptr().add(self.length);
549            ptr::copy_nonoverlapping(slice.as_ptr(), end, slice.len());
550            self.length += slice.len();
551        }
552    }
553
554    /// Advances the start of the slice by `offset` items.
555    ///
556    /// This operation does not touch the underlying buffer.
557    ///
558    /// # Panics
559    ///
560    /// Panics if `offset > self.len()`.
561    ///
562    /// # Examples
563    ///
564    /// ```rust
565    /// use arc_slice::ArcSliceMut;
566    ///
567    /// let mut s = ArcSliceMut::<[u8]>::from(b"hello world");
568    /// s.advance(6);
569    /// assert_eq!(s, b"world");
570    /// ```
571    pub fn advance(&mut self, offset: usize) {
572        if offset > self.length {
573            panic_out_of_range();
574        }
575        L::advance::<S>(self.data.as_mut(), offset);
576        self.start = unsafe { self.start.add(offset) };
577        self.length -= offset;
578        self.capacity -= offset;
579    }
580
581    /// Truncate the slice to the first `len` items.
582    ///
583    /// If `len` is greater than the slice length, this has no effect.
584    ///
585    /// ```rust
586    /// use arc_slice::ArcSliceMut;
587    ///
588    /// let mut s = ArcSliceMut::<[u8]>::from(b"hello world");
589    /// s.truncate(5);
590    /// assert_eq!(s, b"hello");
591    /// ```
592    pub fn truncate(&mut self, len: usize) {
593        if len >= self.length {
594            return;
595        }
596        if S::needs_drop() {
597            let truncate = <L as ArcSliceMutLayout>::truncate::<S>;
598            let data = unsafe { self.data.as_mut().unwrap_unchecked() };
599            truncate(self.start, self.length, self.capacity, data);
600            // shorten capacity to avoid overwriting droppable items
601            self.capacity = len;
602        }
603        self.length = len;
604    }
605
606    /// Accesses the metadata of the underlying buffer if it can be successfully downcast.
607    ///
608    /// # Examples
609    ///
610    /// ```rust
611    /// use arc_slice::{layout::ArcLayout, ArcSliceMut};
612    ///
613    /// let metadata = "metadata".to_string();
614    /// let s =
615    ///     ArcSliceMut::<[u8], ArcLayout<true>>::from_buffer_with_metadata(vec![0, 1, 2], metadata);
616    /// assert_eq!(s.metadata::<String>().unwrap(), "metadata");
617    /// ```
618    pub fn metadata<M: Any>(&self) -> Option<&M> {
619        <L as ArcSliceMutLayout>::get_metadata::<S, M>(self.data.as_ref()?)
620    }
621
622    /// Tries downcasting the `ArcSliceMut` to its underlying buffer.
623    ///
624    /// # Examples
625    ///
626    /// ```rust
627    /// use arc_slice::{layout::ArcLayout, ArcSliceMut};
628    ///
629    /// let s = ArcSliceMut::<[u8], ArcLayout<true>>::from(vec![0, 1, 2]);
630    /// assert_eq!(s.try_into_buffer::<Vec<u8>>().unwrap(), [0, 1, 2]);
631    /// ```
632    pub fn try_into_buffer<B: BufferMut<S>>(self) -> Result<B, Self> {
633        // MSRV 1.65 let-else
634        let data = match self.data {
635            Some(data) => data,
636            None => return Err(self),
637        };
638        let this = ManuallyDrop::new(self);
639        let take_buffer = <L as ArcSliceMutLayout>::take_buffer::<S, B, UNIQUE>;
640        unsafe { take_buffer(this.start, this.length, this.capacity, data) }
641            .ok_or_else(|| ManuallyDrop::into_inner(this))
642    }
643
644    /// Tries turning the shared `ArcSliceMut` into a unique one.
645    ///
646    /// # Examples
647    ///
648    /// ```rust
649    /// use arc_slice::ArcSliceMut;
650    ///
651    /// let mut a = ArcSliceMut::<[u8]>::from(b"hello world").into_shared();
652    /// let b = a.split_to(5);
653    /// assert!(a.try_into_unique().is_err());
654    /// // a has been dropped
655    /// assert!(b.try_into_unique().is_ok());
656    /// ```
657    #[inline(always)]
658    pub fn try_into_unique(self) -> Result<ArcSliceMut<S, L, true>, Self> {
659        let is_unique = <L as ArcSliceMutLayout>::is_unique::<S>;
660        if !UNIQUE && !self.data.is_some_and(is_unique) {
661            return Err(self);
662        }
663        Ok(unsafe { mem::transmute::<Self, ArcSliceMut<S, L, true>>(self) })
664    }
665
666    /// Turns the unique `ArcSliceMut` into a shared one.
667    ///
668    /// Shared `ArcSliceMut` can be split.
669    ///
670    /// # Examples
671    ///
672    /// ```rust
673    /// use arc_slice::ArcSliceMut;
674    ///
675    /// let mut a = ArcSliceMut::<[u8]>::from(b"hello world").into_shared();
676    /// let b = a.split_to(5);
677    /// ```
678    #[inline(always)]
679    pub fn into_shared(self) -> ArcSliceMut<S, L, false> {
680        unsafe { mem::transmute::<Self, ArcSliceMut<S, L, false>>(self) }
681    }
682
683    fn freeze_impl<L2: Layout, E: AllocErrorImpl>(self) -> Result<ArcSlice<S, L2>, Self> {
684        let mut this = ManuallyDrop::new(self);
685        let data = match this.data {
686            Some(data) => L::frozen_data::<S, L2, E>(this.start, this.length, this.capacity, data),
687            None if L2::STATIC_DATA.is_some() || L2::ANY_BUFFER => {
688                L2::data_from_static::<_, E>(unsafe { S::from_raw_parts(this.start, this.length) })
689                    .ok()
690            }
691            None => match Arc::new_array::<E, 0>([]) {
692                Ok((arc, start)) => {
693                    this.start = start;
694                    Some(L2::data_from_arc_slice::<S>(arc))
695                }
696                Err(_) => None,
697            },
698        };
699        match data {
700            Some(data) => Ok(ArcSlice::init(this.start, this.length, data)),
701            None => Err(ManuallyDrop::into_inner(this)),
702        }
703    }
704
705    /// Tries freezing the slice, returning an immutable [`ArcSlice`].
706    ///
707    /// If the mutable slice was split into several parts, only the current one is frozen.
708    ///
709    /// The conversion may allocate depending on the given [layouts](crate::layout), but allocation
710    /// errors are caught and the original slice is returned in this case.
711    ///
712    /// # Examples
713    ///
714    /// ```rust
715    /// use arc_slice::{layout::DefaultLayoutMut, ArcSlice, ArcSliceMut};
716    ///
717    /// let mut s = ArcSliceMut::<[u8]>::with_capacity(16);
718    /// s.extend_from_slice(b"hello world");
719    ///
720    /// let frozen: ArcSlice<[u8]> = s.try_freeze().unwrap();
721    /// ```
722    pub fn try_freeze<L2: Layout>(self) -> Result<ArcSlice<S, L2>, Self> {
723        self.freeze_impl::<L2, AllocError>()
724    }
725
726    fn with_layout_impl<L2: LayoutMut, E: AllocErrorImpl>(
727        self,
728    ) -> Result<ArcSliceMut<S, L2, UNIQUE>, Self> {
729        let this = ManuallyDrop::new(self);
730        let update_layout = <L as ArcSliceMutLayout>::update_layout::<S, L2, E>;
731        Ok(ArcSliceMut {
732            start: this.start,
733            length: this.length,
734            capacity: this.capacity,
735            data: this
736                .data
737                .map(|data| update_layout(this.start, this.length, this.capacity, data).ok_or(()))
738                .transpose()
739                .map_err(|_| ManuallyDrop::into_inner(this))?,
740            _phantom: PhantomData,
741        })
742    }
743
744    /// Tries to replace the layout of the `ArcSliceMut`, returning the original slice if it fails.
745    ///
746    /// The [layouts](crate::layout) must be compatible for the conversion to succeed, see
747    /// [`FromLayout`].
748    ///
749    /// The conversion may allocate depending on the given [layouts](crate::layout), but allocation
750    /// errors are caught and the original slice is also returned in this case.
751    ///
752    /// # Examples
753    /// ```rust
754    /// use arc_slice::{
755    ///     layout::{ArcLayout, BoxedSliceLayout, VecLayout},
756    ///     ArcSliceMut,
757    /// };
758    ///
759    /// let a = ArcSliceMut::<[u8], VecLayout>::from(vec![0, 1, 2]);
760    ///
761    /// let b = a.try_with_layout::<ArcLayout<true>>().unwrap();
762    /// assert!(b.try_with_layout::<ArcLayout<false>>().is_err());
763    /// ```
764    pub fn try_with_layout<L2: LayoutMut>(self) -> Result<ArcSliceMut<S, L2, UNIQUE>, Self> {
765        self.with_layout_impl::<L2, AllocError>()
766    }
767
768    /// Converts an `ArcSliceMut` into a primitive `ArcSliceMut`.
769    ///
770    /// # Examples
771    ///
772    /// ```rust
773    /// use arc_slice::ArcSliceMut;
774    ///
775    /// let s = ArcSliceMut::<str>::from("hello world");
776    /// let bytes: ArcSliceMut<[u8]> = s.into_arc_slice_mut();
777    /// assert_eq!(bytes, b"hello world");
778    /// ```
779    pub fn into_arc_slice_mut(self) -> ArcSliceMut<[S::Item], L, UNIQUE> {
780        let this = ManuallyDrop::new(self);
781        ArcSliceMut {
782            start: this.start,
783            length: this.length,
784            capacity: this.capacity,
785            data: this.data,
786            _phantom: PhantomData,
787        }
788    }
789
790    /// Tries converting an item slice into the given `ArcSliceMut`.
791    ///
792    /// The conversion uses [`Slice::try_from_slice_mut`].
793    ///
794    /// # Examples
795    ///
796    /// ```rust
797    /// use arc_slice::ArcSliceMut;
798    ///
799    /// let utf8 = ArcSliceMut::<[u8]>::from(b"hello world");
800    /// let not_utf8 = ArcSliceMut::<[u8]>::from(b"\x80\x81");
801    ///
802    /// assert!(ArcSliceMut::<str>::try_from_arc_slice_mut(utf8).is_ok());
803    /// assert!(ArcSliceMut::<str>::try_from_arc_slice_mut(not_utf8).is_err());
804    /// ```
805    #[allow(clippy::type_complexity)]
806    pub fn try_from_arc_slice_mut(
807        mut slice: ArcSliceMut<[S::Item], L, UNIQUE>,
808    ) -> Result<Self, (S::TryFromSliceError, ArcSliceMut<[S::Item], L, UNIQUE>)> {
809        match S::try_from_slice_mut(&mut slice) {
810            Ok(_) => Ok(unsafe { Self::from_arc_slice_mut_unchecked(slice) }),
811            Err(error) => Err((error, slice)),
812        }
813    }
814
815    /// Converts an item slice into the given `ArcSliceMut`, without checking the slice validity.
816    ///
817    /// # Safety
818    ///
819    /// The operation has the same contract as [`Slice::from_slice_mut_unchecked`].
820    ///
821    /// # Examples
822    ///
823    /// ```rust
824    /// use arc_slice::ArcSliceMut;
825    ///
826    /// let utf8 = ArcSliceMut::<[u8]>::from(b"hello world");
827    ///
828    /// // SAFETY: `utf8` is a valid utf8 string
829    /// let s = unsafe { ArcSliceMut::<str>::from_arc_slice_mut_unchecked(utf8) };
830    /// assert_eq!(s, "hello world");
831    /// ```
832    pub unsafe fn from_arc_slice_mut_unchecked(
833        mut slice: ArcSliceMut<[S::Item], L, UNIQUE>,
834    ) -> Self {
835        debug_assert!(S::try_from_slice_mut(&mut slice).is_ok());
836        let slice = ManuallyDrop::new(slice);
837        Self {
838            start: slice.start,
839            length: slice.length,
840            capacity: slice.capacity,
841            data: slice.data,
842            _phantom: slice._phantom,
843        }
844    }
845}
846
847#[cfg(feature = "oom-handling")]
848impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> ArcSliceMut<S, L, UNIQUE> {
849    /// Freeze the slice, returning an immutable [`ArcSlice`].
850    ///
851    /// If the mutable slice was split into several parts, only the current one is frozen.
852    ///
853    /// # Examples
854    ///
855    /// ```rust
856    /// use arc_slice::{layout::DefaultLayoutMut, ArcSlice, ArcSliceMut};
857    ///
858    /// let mut s = ArcSliceMut::<[u8]>::with_capacity(16);
859    /// s.extend_from_slice(b"hello world");
860    ///
861    /// let frozen: ArcSlice<[u8]> = s.freeze();
862    /// ```
863    pub fn freeze<L2: FromLayout<L>>(self) -> ArcSlice<S, L2> {
864        self.freeze_impl::<L2, Infallible>().unwrap_checked()
865    }
866
867    /// Replace the layout of the `ArcSliceMut`.
868    ///
869    /// The [layouts](crate::layout) must be compatible, see [`FromLayout`].
870    ///
871    /// # Examples
872    /// ```rust
873    /// use arc_slice::{
874    ///     layout::{ArcLayout, BoxedSliceLayout, VecLayout},
875    ///     ArcSliceMut,
876    /// };
877    ///
878    /// let a = ArcSliceMut::<[u8]>::from(b"hello world");
879    ///
880    /// let b = a.with_layout::<VecLayout>();
881    /// ```
882    pub fn with_layout<L2: LayoutMut + FromLayout<L>>(self) -> ArcSliceMut<S, L2, UNIQUE> {
883        self.with_layout_impl::<L2, Infallible>().unwrap_checked()
884    }
885}
886
887#[cfg(not(feature = "oom-handling"))]
888impl<S: Slice + ?Sized, const ANY_BUFFER: bool, const STATIC: bool, const UNIQUE: bool>
889    ArcSliceMut<S, ArcLayout<ANY_BUFFER, STATIC>, UNIQUE>
890{
891    /// Freeze the slice, returning an immutable [`ArcSlice`].
892    ///
893    /// If the mutable slice was split into several parts, only the current one is frozen.
894    ///
895    /// # Examples
896    ///
897    /// ```rust
898    /// use arc_slice::{layout::DefaultLayoutMut, ArcSlice, ArcSliceMut};
899    ///
900    /// let mut s = ArcSliceMut::<[u8]>::with_capacity(16);
901    /// s.extend_from_slice(b"hello world");
902    ///
903    /// let frozen: ArcSlice<[u8]> = s.freeze();
904    /// ```
905    pub fn freeze<L2: FromLayout<ArcLayout<ANY_BUFFER, STATIC>>>(self) -> ArcSlice<S, L2> {
906        self.freeze_impl::<L2, Infallible>().unwrap_checked()
907    }
908
909    /// Replace the layout of the `ArcSliceMut`.
910    ///
911    /// The [layouts](crate::layout) must be compatible, see [`FromLayout`].
912    ///
913    /// # Examples
914    /// ```rust
915    /// use arc_slice::{
916    ///     layout::{ArcLayout, BoxedSliceLayout, VecLayout},
917    ///     ArcSliceMut,
918    /// };
919    ///
920    /// let a = ArcSliceMut::<[u8]>::from(b"hello world");
921    ///
922    /// let b = a.with_layout::<VecLayout>();
923    /// ```
924    pub fn with_layout<L2: LayoutMut + FromLayout<ArcLayout<ANY_BUFFER, STATIC>>>(
925        self,
926    ) -> ArcSliceMut<S, L2, UNIQUE> {
927        self.with_layout_impl::<L2, Infallible>().unwrap_checked()
928    }
929}
930
931impl<S: Slice + ?Sized, L: LayoutMut> ArcSliceMut<S, L> {
932    pub(crate) const fn init(
933        start: NonNull<S::Item>,
934        length: usize,
935        capacity: usize,
936        data: Option<Data>,
937    ) -> Self {
938        Self {
939            start,
940            length,
941            capacity,
942            data,
943            _phantom: PhantomData,
944        }
945    }
946
947    /// # Safety
948    ///
949    /// Empty slice must be valid (see [`Emptyable`])
950    const unsafe fn empty() -> Self {
951        Self::init(NonNull::dangling(), 0, 0, None)
952    }
953
954    /// Creates a new empty `ArcSliceMut`.
955    ///
956    /// This operation doesn't allocate.
957    ///
958    /// # Examples
959    ///
960    /// ```rust
961    /// use arc_slice::{layout::ArcLayout, ArcSliceMut};
962    ///
963    /// let s = ArcSliceMut::<[u8]>::new();
964    /// assert_eq!(s, []);
965    /// ```
966    pub const fn new() -> Self
967    where
968        S: Emptyable,
969    {
970        unsafe { Self::empty() }
971    }
972
973    pub(crate) fn from_slice_impl<E: AllocErrorImpl>(slice: &S) -> Result<Self, E>
974    where
975        S::Item: Copy,
976    {
977        if slice.is_empty() {
978            return Ok(unsafe { Self::empty() });
979        }
980        let (arc, start) = Arc::<S, false>::new::<E>(slice)?;
981        Ok(Self::init(
982            start,
983            slice.len(),
984            slice.len(),
985            Some(arc.into()),
986        ))
987    }
988
989    /// Creates a new `ArcSliceMut` by copying the given slice.
990    ///
991    /// # Panics
992    ///
993    /// Panics if the new capacity exceeds `isize::MAX - size_of::<usize>()` bytes.
994    ///
995    /// # Examples
996    ///
997    /// ```rust
998    /// use arc_slice::ArcSliceMut;
999    ///
1000    /// let s = ArcSliceMut::<[u8]>::from_slice(b"hello world");
1001    /// assert_eq!(s, b"hello world");
1002    /// ```
1003    #[cfg(feature = "oom-handling")]
1004    pub fn from_slice(slice: &S) -> Self
1005    where
1006        S::Item: Copy,
1007    {
1008        Self::from_slice_impl::<Infallible>(slice).unwrap_infallible()
1009    }
1010
1011    /// Tries creating a new `ArcSliceMut` by copying the given slice, returning an error if the
1012    /// allocation fails.
1013    ///
1014    /// # Examples
1015    ///
1016    /// ```rust
1017    /// use arc_slice::ArcSliceMut;
1018    ///
1019    /// # fn main() -> Result<(), arc_slice::error::AllocError> {
1020    /// let s = ArcSliceMut::<[u8]>::try_from_slice(b"hello world")?;
1021    /// assert_eq!(s, b"hello world");
1022    /// # Ok(())
1023    /// # }
1024    /// ```
1025    pub fn try_from_slice(slice: &S) -> Result<Self, AllocError>
1026    where
1027        S::Item: Copy,
1028    {
1029        Self::from_slice_impl::<AllocError>(slice)
1030    }
1031
1032    #[cfg(feature = "serde")]
1033    pub(crate) fn new_bytes(slice: &S) -> Self {
1034        assert_checked(is!(S::Item, u8));
1035        let (arc, start) = unsafe {
1036            Arc::<S, false>::new_unchecked::<Infallible>(slice.to_slice()).unwrap_infallible()
1037        };
1038        Self::init(start, slice.len(), slice.len(), Some(arc.into()))
1039    }
1040
1041    #[cfg(feature = "serde")]
1042    pub(crate) fn new_byte_vec(vec: S::Vec) -> Self {
1043        assert_checked(is!(S::Item, u8));
1044        if !<L as ArcSliceMutLayout>::ANY_BUFFER {
1045            return Self::new_bytes(ManuallyDrop::new(vec).as_slice());
1046        }
1047        Self::from_vec(vec)
1048    }
1049
1050    pub(crate) fn from_vec_impl<E: AllocErrorImpl>(mut vec: S::Vec) -> Result<Self, (E, S::Vec)> {
1051        let capacity = vec.capacity();
1052        if capacity == 0 {
1053            return Ok(unsafe { Self::empty() });
1054        }
1055        let start = S::vec_start(&mut vec);
1056        let length = vec.len();
1057        let data = unsafe { <L as ArcSliceMutLayout>::data_from_vec::<S, E>(vec, 0)? };
1058        Ok(Self::init(start, length, capacity, Some(data)))
1059    }
1060
1061    pub(crate) fn from_vec(vec: S::Vec) -> Self {
1062        Self::from_vec_impl::<Infallible>(vec).unwrap_infallible()
1063    }
1064
1065    fn with_capacity_impl<E: AllocErrorImpl, const ZEROED: bool>(
1066        capacity: usize,
1067    ) -> Result<Self, E> {
1068        if capacity == 0 {
1069            return Ok(unsafe { Self::empty() });
1070        }
1071        let (arc, start) = Arc::<S>::with_capacity::<E, ZEROED>(capacity)?;
1072        let length = if ZEROED { capacity } else { 0 };
1073        Ok(Self::init(start, length, capacity, Some(arc.into())))
1074    }
1075
1076    /// Creates a new `ArcSliceMut` with the given capacity.
1077    ///
1078    /// This operation allocates if `capacity > 0`.
1079    ///
1080    /// # Panics
1081    ///
1082    /// Panics if the new capacity exceeds `isize::MAX - size_of::<usize>()` bytes.
1083    ///
1084    /// # Examples
1085    ///
1086    /// ```rust
1087    /// use arc_slice::ArcSliceMut;
1088    ///
1089    /// let s = ArcSliceMut::<[u8]>::with_capacity(64);
1090    /// assert_eq!(s, []);
1091    /// assert_eq!(s.capacity(), 64);
1092    /// ```
1093    #[cfg(feature = "oom-handling")]
1094    pub fn with_capacity(capacity: usize) -> Self
1095    where
1096        S: Emptyable,
1097    {
1098        Self::with_capacity_impl::<Infallible, false>(capacity).unwrap_infallible()
1099    }
1100
1101    /// Tries creating a new `ArcSliceMut` with the given capacity, returning an error if an
1102    /// allocation fails.
1103    ///
1104    /// This operation allocates if `capacity > 0`.
1105    ///
1106    /// # Panics
1107    ///
1108    /// Panics if the new capacity exceeds `isize::MAX - size_of::<usize>()` bytes.
1109    ///
1110    /// # Examples
1111    ///
1112    /// ```rust
1113    /// use arc_slice::ArcSliceMut;
1114    ///
1115    /// # fn main() -> Result<(), arc_slice::error::AllocError> {
1116    /// let s = ArcSliceMut::<[u8]>::try_with_capacity(64)?;
1117    /// assert_eq!(s, []);
1118    /// assert_eq!(s.capacity(), 64);
1119    /// # Ok(())
1120    /// # }
1121    /// ```
1122    #[cfg(feature = "oom-handling")]
1123    pub fn try_with_capacity(capacity: usize) -> Result<Self, AllocError>
1124    where
1125        S: Emptyable,
1126    {
1127        Self::with_capacity_impl::<AllocError, false>(capacity)
1128    }
1129
1130    /// Creates a new zeroed `ArcSliceMut` with the given capacity.
1131    ///
1132    /// This operation allocates if `capacity > 0`. All the items are initialized to `0`.
1133    ///
1134    /// # Panics
1135    ///
1136    /// Panics if the new capacity exceeds `isize::MAX - size_of::<usize>()` bytes.
1137    ///
1138    /// # Examples
1139    ///
1140    /// ```rust
1141    /// use arc_slice::ArcSliceMut;
1142    ///
1143    /// let s = ArcSliceMut::<[u8]>::zeroed(4);
1144    /// assert_eq!(s, [0, 0, 0, 0]);
1145    /// assert_eq!(s.capacity(), 4);
1146    /// ```
1147    #[cfg(feature = "oom-handling")]
1148    pub fn zeroed(length: usize) -> Self
1149    where
1150        S: Zeroable,
1151    {
1152        Self::with_capacity_impl::<Infallible, true>(length).unwrap_infallible()
1153    }
1154
1155    /// Tries creating a new zeroed `ArcSliceMut` with the given capacity.
1156    ///
1157    /// This operation allocates if `capacity > 0`. All the items are initialized to `0`.
1158    ///
1159    /// # Panics
1160    ///
1161    /// Panics if the new capacity exceeds `isize::MAX - size_of::<usize>()` bytes.
1162    ///
1163    /// # Examples
1164    ///
1165    /// ```rust
1166    /// use arc_slice::ArcSliceMut;
1167    ///
1168    /// let s = ArcSliceMut::<[u8]>::zeroed(4);
1169    /// assert_eq!(s, [0, 0, 0, 0]);
1170    /// assert_eq!(s.capacity(), 4);
1171    /// ```
1172    pub fn try_zeroed(length: usize) -> Result<Self, AllocError>
1173    where
1174        S: Zeroable,
1175    {
1176        Self::with_capacity_impl::<AllocError, true>(length)
1177    }
1178
1179    /// Reserve capacity for at least `additional` more items.
1180    ///
1181    /// Does nothing if the spare capacity is greater than the requested one.
1182    ///
1183    /// Reserving always attempts to [reclaim](Self::try_reclaim) first, and
1184    /// reallocates the buffer if that fails.
1185    ///
1186    /// The default arc-slice buffer supports amortized reservation, doubling the capacity each
1187    /// time. The reserved capacity might be greater than the requested one.
1188    ///
1189    /// # Panics
1190    ///
1191    /// Panics if the new capacity exceeds isize::MAX bytes, or if the underlying buffer doesn't
1192    /// support additional capacity reservation.
1193    ///
1194    /// # Examples
1195    ///
1196    /// ```rust
1197    /// use arc_slice::ArcSliceMut;
1198    ///
1199    /// let mut s = ArcSliceMut::<[u8]>::new();
1200    /// s.reserve(3);
1201    /// assert!(s.capacity() >= 3);
1202    /// s.extend_from_slice(&[0, 1, 2]);
1203    /// assert_eq!(s, [0, 1, 2]);
1204    /// ```
1205    #[cfg(feature = "oom-handling")]
1206    pub fn reserve(&mut self, additional: usize) {
1207        if let Err(err) = self.try_reserve(additional) {
1208            #[cold]
1209            fn panic_reserve(err: TryReserveError) -> ! {
1210                match err {
1211                    TryReserveError::AllocError => {
1212                        alloc::alloc::handle_alloc_error(core::alloc::Layout::new::<()>())
1213                    }
1214                    err => panic!("{err:?}"),
1215                }
1216            }
1217            panic_reserve(err);
1218        }
1219    }
1220
1221    /// Appends an element to the end of the slice.
1222    ///
1223    /// The buffer might have to reserve additional capacity to do the appending.
1224    ///
1225    /// The default arc-slice buffer supports amortized reservation, doubling the capacity each
1226    /// time.
1227    ///
1228    /// # Panics
1229    ///
1230    /// See [reserve](Self::reserve).
1231    ///
1232    /// # Examples
1233    ///
1234    /// ```rust
1235    /// use arc_slice::ArcSliceMut;
1236    ///
1237    /// let mut s = ArcSliceMut::<[u8]>::new();
1238    /// s.push(42);
1239    /// assert_eq!(s, [42]);
1240    /// ```
1241    #[cfg(feature = "oom-handling")]
1242    pub fn push(&mut self, item: S::Item)
1243    where
1244        S: Extendable,
1245    {
1246        self.reserve(1);
1247        unsafe { self.start.as_ptr().add(self.length).write(item) };
1248        self.length += 1;
1249    }
1250
1251    /// Appends a slice to the end of slice.
1252    ///
1253    /// The buffer might have to reserve additional capacity to do the appending.
1254    ///
1255    /// The default arc-slice buffer supports amortized reservation, doubling the capacity each
1256    /// time.
1257    ///
1258    /// # Panics
1259    ///
1260    /// See [reserve](Self::reserve).
1261    ///
1262    /// ```rust
1263    /// use arc_slice::ArcSliceMut;
1264    ///
1265    /// let mut s = ArcSliceMut::<[u8]>::new();
1266    /// s.extend_from_slice(b"hello world");
1267    /// assert_eq!(s, b"hello world");
1268    /// ```
1269    #[cfg(feature = "oom-handling")]
1270    pub fn extend_from_slice(&mut self, slice: &S)
1271    where
1272        S: Concatenable,
1273        S::Item: Copy,
1274    {
1275        self.reserve(slice.len());
1276        unsafe { self.extend_from_slice_unchecked(slice.to_slice()) }
1277    }
1278}
1279
1280impl<T: Send + Sync + 'static, L: LayoutMut> ArcSliceMut<[T], L> {
1281    pub(crate) fn from_array_impl<E: AllocErrorImpl, const N: usize>(
1282        array: [T; N],
1283    ) -> Result<Self, (E, [T; N])> {
1284        if N == 0 {
1285            return Ok(Self::new());
1286        }
1287        let (arc, start) = Arc::<[T], false>::new_array::<E, N>(array)?;
1288        Ok(Self::init(start, N, N, Some(arc.into())))
1289    }
1290
1291    /// Creates a new `ArcSliceMut` by moving the given array.
1292    ///
1293    /// # Panics
1294    ///
1295    /// Panics if the new capacity exceeds `isize::MAX - size_of::<usize>()` bytes.
1296    ///
1297    /// # Examples
1298    ///
1299    /// ```rust
1300    /// use arc_slice::ArcSliceMut;
1301    ///
1302    /// let s = ArcSliceMut::<[u8]>::from_array([0, 1, 2]);
1303    /// assert_eq!(s, [0, 1, 2]);
1304    /// ```
1305    #[cfg(feature = "oom-handling")]
1306    pub fn from_array<const N: usize>(array: [T; N]) -> Self {
1307        Self::from_array_impl::<Infallible, N>(array).unwrap_infallible()
1308    }
1309
1310    /// Tries creating a new `ArcSliceMut` by moving the given array,
1311    /// returning it if an allocation fails.
1312    ///
1313    /// # Examples
1314    ///
1315    /// ```rust
1316    /// use arc_slice::ArcSliceMut;
1317    ///
1318    /// let s = ArcSliceMut::<[u8]>::try_from_array([0, 1, 2]).unwrap();
1319    /// assert_eq!(s, [0, 1, 2]);
1320    /// ```
1321    pub fn try_from_array<const N: usize>(array: [T; N]) -> Result<Self, [T; N]> {
1322        Self::from_array_impl::<AllocError, N>(array).map_err(|(_, array)| array)
1323    }
1324}
1325
1326impl<S: Slice + ?Sized, L: LayoutMut> ArcSliceMut<S, L, false> {
1327    unsafe fn clone_impl<E: AllocErrorImpl>(&mut self) -> Result<Self, E> {
1328        if let Some(data) = &mut self.data {
1329            <L as ArcSliceMutLayout>::clone::<S, E>(self.start, self.length, self.capacity, data)?;
1330        }
1331        Ok(Self {
1332            start: self.start,
1333            length: self.length,
1334            capacity: self.capacity,
1335            data: self.data,
1336            _phantom: self._phantom,
1337        })
1338    }
1339
1340    fn split_off_impl<E: AllocErrorImpl>(&mut self, at: usize) -> Result<Self, E> {
1341        if at > self.capacity {
1342            panic_out_of_range();
1343        }
1344        let mut clone = unsafe { self.clone_impl()? };
1345        clone.start = unsafe { clone.start.add(at) };
1346        clone.capacity -= at;
1347        self.capacity = at;
1348        if at > self.length {
1349            clone.length = 0;
1350        } else {
1351            self.length = at;
1352            clone.length -= at;
1353        }
1354        Ok(clone)
1355    }
1356
1357    /// Tries splitting the slice into two at the given index, returning an error if an allocation
1358    /// fails.
1359    ///
1360    /// Afterwards `self` contains elements `[0, at)`, and the returned `ArcSliceMut`
1361    /// contains elements `[at, len)`. This operation does not touch the underlying buffer.
1362    ///
1363    /// The operation may allocate. See [`CloneNoAllocLayout`](crate::layout::CloneNoAllocLayout)
1364    /// documentation for cases where it does not.
1365    ///
1366    /// # Panics
1367    ///
1368    /// Panics if `at > self.len()`.
1369    ///
1370    /// # Examples
1371    ///
1372    /// ```rust
1373    /// use arc_slice::ArcSliceMut;
1374    ///
1375    /// # fn main() -> Result<(), arc_slice::error::AllocError> {
1376    /// let mut a = ArcSliceMut::<[u8]>::from(b"hello world").into_shared();
1377    /// let b = a.try_split_off(5)?;
1378    ///
1379    /// assert_eq!(a, b"hello");
1380    /// assert_eq!(b, b" world");
1381    /// # Ok(())
1382    /// # }
1383    /// ```
1384    pub fn try_split_off(&mut self, at: usize) -> Result<Self, AllocError> {
1385        self.split_off_impl::<AllocError>(at)
1386    }
1387
1388    fn split_to_impl<E: AllocErrorImpl>(&mut self, at: usize) -> Result<Self, E> {
1389        if at > self.length {
1390            panic_out_of_range();
1391        }
1392        let mut clone = unsafe { self.clone_impl()? };
1393        clone.capacity = at;
1394        clone.length = at;
1395        self.start = unsafe { self.start.add(at) };
1396        self.capacity -= at;
1397        self.length -= at;
1398        Ok(clone)
1399    }
1400
1401    /// Tries splitting the slice into two at the given index, returning an error if an allocation
1402    /// fails.
1403    ///
1404    /// Afterwards `self` contains elements `[at, len)`, and the returned `ArcSliceMut`
1405    /// contains elements `[0, at)`. This operation does not touch the underlying buffer.
1406    ///
1407    /// The operation may allocate. See [`CloneNoAllocLayout`](crate::layout::CloneNoAllocLayout)
1408    /// documentation for cases where it does not.
1409    ///
1410    /// # Panics
1411    ///
1412    /// Panics if `at > self.len()`.
1413    ///
1414    /// # Examples
1415    ///
1416    /// ```rust
1417    /// use arc_slice::ArcSliceMut;
1418    ///
1419    /// # fn main() -> Result<(), arc_slice::error::AllocError> {
1420    /// let mut a = ArcSliceMut::<[u8]>::from(b"hello world").into_shared();
1421    /// let b = a.try_split_to(5)?;
1422    ///
1423    /// assert_eq!(a, b" world");
1424    /// assert_eq!(b, b"hello");
1425    /// # Ok(())
1426    /// # }
1427    /// ```
1428    pub fn try_split_to(&mut self, at: usize) -> Result<Self, AllocError> {
1429        self.split_to_impl::<AllocError>(at)
1430    }
1431
1432    /// Tries unsplitting two parts of a previously split slice.
1433    ///
1434    /// # Examples
1435    ///
1436    /// ```rust
1437    /// use arc_slice::ArcSliceMut;
1438    ///
1439    /// let mut a = ArcSliceMut::<[u8]>::from(b"hello world").into_shared();
1440    ///
1441    /// let b = a.split_off(5);
1442    /// assert_eq!(a, b"hello");
1443    /// assert_eq!(b, b" world");
1444    /// a.try_unsplit(b).unwrap();
1445    /// assert_eq!(a, b"hello world");
1446    ///
1447    /// assert!(a
1448    ///     .try_unsplit(ArcSliceMut::from(b"other").into_shared())
1449    ///     .is_err());
1450    /// ```
1451    pub fn try_unsplit(
1452        &mut self,
1453        other: ArcSliceMut<S, L, false>,
1454    ) -> Result<(), ArcSliceMut<S, L, false>> {
1455        let end = unsafe { self.start.add(self.capacity) };
1456        if self.length == self.capacity && self.data == other.data && end == other.start {
1457            self.length += other.length;
1458            self.capacity += other.capacity;
1459            return Ok(());
1460        }
1461        Err(other)
1462    }
1463}
1464
1465impl<
1466        S: Slice + ?Sized,
1467        #[cfg(feature = "oom-handling")] L: LayoutMut,
1468        #[cfg(not(feature = "oom-handling"))] L: LayoutMut + CloneNoAllocLayout,
1469    > ArcSliceMut<S, L, false>
1470{
1471    /// Splits the slice into two at the given index.
1472    ///
1473    /// Afterwards `self` contains elements `[0, at)`, and the returned `ArcSliceMut`
1474    /// contains elements `[at, len)`. This operation does not touch the underlying buffer.
1475    ///
1476    /// # Panics
1477    ///
1478    /// Panics if `at > self.capacity()`.
1479    ///
1480    /// # Examples
1481    ///
1482    /// ```rust
1483    /// use arc_slice::ArcSliceMut;
1484    ///
1485    /// let mut a = ArcSliceMut::<[u8]>::from(b"hello world").into_shared();
1486    /// let b = a.split_off(5);
1487    ///
1488    /// assert_eq!(a, b"hello");
1489    /// assert_eq!(b, b" world");
1490    /// ```
1491    #[must_use = "consider `ArcSliceMut::truncate` if you don't need the other half"]
1492    pub fn split_off(&mut self, at: usize) -> Self {
1493        self.split_off_impl::<Infallible>(at).unwrap_infallible()
1494    }
1495
1496    /// Splits the slice into two at the given index.
1497    ///
1498    /// Afterwards `self` contains elements `[at, len)`, and the returned `ArcSliceMut`
1499    /// contains elements `[0, at)`. This operation does not touch the underlying buffer.
1500    ///
1501    /// # Panics
1502    ///
1503    /// Panics if `at > self.len()`.
1504    ///
1505    /// # Examples
1506    ///
1507    /// ```rust
1508    /// use arc_slice::ArcSliceMut;
1509    ///
1510    /// let mut a = ArcSliceMut::<[u8]>::from(b"hello world").into_shared();
1511    /// let b = a.split_to(5);
1512    ///
1513    /// assert_eq!(a, b" world");
1514    /// assert_eq!(b, b"hello");
1515    /// ```
1516    #[must_use = "consider `ArcSliceMut::advance` if you don't need the other half"]
1517    pub fn split_to(&mut self, at: usize) -> Self {
1518        self.split_to_impl::<Infallible>(at).unwrap_infallible()
1519    }
1520}
1521
1522impl<S: Slice + ?Sized, L: AnyBufferLayout + LayoutMut> ArcSliceMut<S, L> {
1523    pub(crate) fn from_dyn_buffer_impl<B: DynBuffer + BufferMut<S>, E: AllocErrorImpl>(
1524        buffer: B,
1525    ) -> Result<Self, (E, B)> {
1526        let (arc, start, length, capacity) = Arc::new_buffer_mut::<_, E>(buffer)?;
1527        Ok(Self::init(start, length, capacity, Some(arc.into())))
1528    }
1529
1530    fn from_buffer_impl<B: BufferMut<S>, E: AllocErrorImpl>(mut buffer: B) -> Result<Self, (E, B)> {
1531        match try_transmute::<B, S::Vec>(buffer) {
1532            Ok(vec) => {
1533                return Self::from_vec_impl::<E>(vec)
1534                    .map_err(|(err, v)| (err, transmute_checked(v)))
1535            }
1536            Err(b) => buffer = b,
1537        }
1538        Self::from_dyn_buffer_impl::<_, E>(BufferWithMetadata::new(buffer, ()))
1539            .map_err(|(err, b)| (err, b.buffer()))
1540    }
1541    /// Creates a new `ArcSliceMut` with the given underlying buffer.
1542    ///
1543    /// The buffer can be extracted back using [`try_into_buffer`](Self::try_into_buffer).
1544    ///
1545    /// # Examples
1546    ///
1547    /// ```rust
1548    /// use arc_slice::{layout::ArcLayout, ArcSliceMut};
1549    ///
1550    /// let s = ArcSliceMut::<[u8], ArcLayout<true>>::from_buffer(vec![0, 1, 2]);
1551    /// assert_eq!(s, [0, 1, 2]);
1552    /// assert_eq!(s.try_into_buffer::<Vec<u8>>().unwrap(), vec![0, 1, 2]);
1553    /// ```
1554    #[cfg(feature = "oom-handling")]
1555    pub fn from_buffer<B: BufferMut<S>>(buffer: B) -> Self {
1556        Self::from_buffer_impl::<_, Infallible>(buffer).unwrap_infallible()
1557    }
1558
1559    /// Tries creating a new `ArcSliceMut` with the given underlying buffer, returning it if an
1560    /// allocation fails.
1561    ///
1562    /// The buffer can be extracted back using [`try_into_buffer`](Self::try_into_buffer).
1563    ///
1564    /// Having an Arc allocation depends on the [layout](crate::layout) and the buffer type,
1565    /// e.g. there will be no allocation for a `Vec` with [`VecLayout`](crate::layout::VecLayout).
1566    ///
1567    /// # Examples
1568    ///
1569    /// ```rust
1570    /// use arc_slice::{layout::ArcLayout, ArcSliceMut};
1571    ///
1572    /// let s = ArcSliceMut::<[u8], ArcLayout<true>>::try_from_buffer(vec![0, 1, 2]).unwrap();
1573    /// assert_eq!(s, [0, 1, 2]);
1574    /// assert_eq!(s.try_into_buffer::<Vec<u8>>().unwrap(), vec![0, 1, 2]);
1575    /// ```
1576    pub fn try_from_buffer<B: BufferMut<S>>(buffer: B) -> Result<Self, B> {
1577        Self::from_buffer_impl::<_, AllocError>(buffer).map_err(|(_, buffer)| buffer)
1578    }
1579
1580    fn from_buffer_with_metadata_impl<
1581        B: BufferMut<S>,
1582        M: Send + Sync + 'static,
1583        E: AllocErrorImpl,
1584    >(
1585        buffer: B,
1586        metadata: M,
1587    ) -> Result<Self, (E, (B, M))> {
1588        if is!(M, ()) {
1589            return Self::from_buffer_impl::<_, E>(buffer).map_err(|(err, b)| (err, (b, metadata)));
1590        }
1591        Self::from_dyn_buffer_impl::<_, E>(BufferWithMetadata::new(buffer, metadata))
1592            .map_err(|(err, b)| (err, b.into_tuple()))
1593    }
1594
1595    /// Creates a new `ArcSliceMut` with the given underlying buffer and its associated metadata.
1596    ///
1597    /// The buffer can be extracted back using [`try_into_buffer`](Self::try_into_buffer);
1598    /// metadata can be retrieved with [`metadata`](Self::metadata).
1599    ///
1600    /// # Examples
1601    ///
1602    /// ```rust
1603    /// use arc_slice::{layout::ArcLayout, ArcSliceMut};
1604    ///
1605    /// let metadata = "metadata".to_string();
1606    /// let s =
1607    ///     ArcSliceMut::<[u8], ArcLayout<true>>::from_buffer_with_metadata(vec![0, 1, 2], metadata);
1608    /// assert_eq!(s, [0, 1, 2]);
1609    /// assert_eq!(s.metadata::<String>().unwrap(), "metadata");
1610    /// assert_eq!(s.try_into_buffer::<Vec<u8>>().unwrap(), vec![0, 1, 2]);
1611    /// ```
1612    #[cfg(feature = "oom-handling")]
1613    #[cfg(feature = "oom-handling")]
1614    pub fn from_buffer_with_metadata<B: BufferMut<S>, M: Send + Sync + 'static>(
1615        buffer: B,
1616        metadata: M,
1617    ) -> Self {
1618        Self::from_buffer_with_metadata_impl::<_, _, Infallible>(buffer, metadata)
1619            .unwrap_infallible()
1620    }
1621
1622    /// Tries creates a new `ArcSliceMut` with the given underlying buffer and its associated metadata,
1623    /// returning them if an allocation fails.
1624    ///
1625    /// The buffer can be extracted back using [`try_into_buffer`](Self::try_into_buffer);
1626    /// metadata can be retrieved with [`metadata`](Self::metadata).
1627    ///
1628    /// Having an Arc allocation depends on the [layout](crate::layout) and the buffer type,
1629    /// e.g. there will be no allocation for a `Vec` with [`VecLayout`](crate::layout::VecLayout).
1630    ///
1631    /// # Examples
1632    ///
1633    /// ```rust
1634    /// use arc_slice::{layout::ArcLayout, ArcSliceMut};
1635    ///
1636    /// let metadata = "metadata".to_string();
1637    /// let s = ArcSliceMut::<[u8], ArcLayout<true>>::try_from_buffer_with_metadata(
1638    ///     vec![0, 1, 2],
1639    ///     metadata,
1640    /// )
1641    /// .unwrap();
1642    /// assert_eq!(s, [0, 1, 2]);
1643    /// assert_eq!(s.metadata::<String>().unwrap(), "metadata");
1644    /// assert_eq!(s.try_into_buffer::<Vec<u8>>().unwrap(), vec![0, 1, 2]);
1645    /// ```
1646    pub fn try_from_buffer_with_metadata<B: BufferMut<S>, M: Send + Sync + 'static>(
1647        buffer: B,
1648        metadata: M,
1649    ) -> Result<Self, (B, M)> {
1650        Self::from_buffer_with_metadata_impl::<_, _, AllocError>(buffer, metadata)
1651            .map_err(|(_, bm)| bm)
1652    }
1653
1654    /// Creates a new `ArcSliceMut` with the given underlying buffer with borrowed metadata.
1655    ///
1656    /// The buffer can be extracted back using [`try_into_buffer`](Self::try_into_buffer);
1657    /// metadata can be retrieved with [`metadata`](Self::metadata).
1658    ///
1659    /// # Examples
1660    ///
1661    /// ```rust
1662    /// use arc_slice::{
1663    ///     buffer::{BorrowMetadata, Buffer, BufferMut},
1664    ///     error::TryReserveError,
1665    ///     layout::ArcLayout,
1666    ///     ArcSliceMut,
1667    /// };
1668    ///
1669    /// #[derive(Debug, PartialEq, Eq)]
1670    /// struct MyBuffer(Vec<u8>);
1671    /// impl Buffer<[u8]> for MyBuffer {
1672    ///     fn as_slice(&self) -> &[u8] {
1673    ///         &self.0
1674    ///     }
1675    /// }
1676    /// #[derive(Debug, PartialEq, Eq)]
1677    /// struct MyMetadata;
1678    /// impl BorrowMetadata for MyBuffer {
1679    ///     type Metadata = MyMetadata;
1680    ///     fn borrow_metadata(&self) -> &Self::Metadata {
1681    ///         &MyMetadata
1682    ///     }
1683    /// }
1684    /// // SAFETY: `MyBuffer` delegates to `Vec<u8>`, which upholds the invariant
1685    /// unsafe impl BufferMut<[u8]> for MyBuffer {
1686    ///     fn as_mut_slice(&mut self) -> &mut [u8] {
1687    ///         &mut self.0
1688    ///     }
1689    ///     fn capacity(&self) -> usize {
1690    ///         self.0.capacity()
1691    ///     }
1692    ///     unsafe fn set_len(&mut self, len: usize) -> bool {
1693    ///         // SAFETY: same function contract
1694    ///         unsafe { self.0.set_len(len) };
1695    ///         true
1696    ///     }
1697    ///     fn try_reserve(&mut self, additional: usize) -> Result<(), TryReserveError> {
1698    ///         BufferMut::try_reserve(&mut self.0, additional)
1699    ///     }
1700    /// }
1701    /// let buffer = MyBuffer(vec![0, 1, 2]);
1702    /// let s = ArcSliceMut::<[u8], ArcLayout<true>>::from_buffer_with_borrowed_metadata(buffer);
1703    /// assert_eq!(s, [0, 1, 2]);
1704    /// assert_eq!(s.metadata::<MyMetadata>().unwrap(), &MyMetadata);
1705    /// assert_eq!(
1706    ///     s.try_into_buffer::<MyBuffer>().unwrap(),
1707    ///     MyBuffer(vec![0, 1, 2])
1708    /// );
1709    /// ```
1710    #[cfg(feature = "oom-handling")]
1711    pub fn from_buffer_with_borrowed_metadata<B: BufferMut<S> + BorrowMetadata>(buffer: B) -> Self {
1712        Self::from_dyn_buffer_impl::<_, Infallible>(buffer).unwrap_infallible()
1713    }
1714
1715    /// Tries creating a new `ArcSliceMut` with the given underlying buffer with borrowed metadata,
1716    /// returning it if an allocation fails.
1717    ///
1718    /// The buffer can be extracted back using [`try_into_buffer`](Self::try_into_buffer);
1719    /// metadata can be retrieved with [`metadata`](Self::metadata).
1720    ///
1721    /// Having an Arc allocation depends on the [layout](crate::layout) and the buffer type,
1722    /// e.g. there will be no allocation for a `Vec` with [`VecLayout`](crate::layout::VecLayout).
1723    ///
1724    /// # Examples
1725    ///
1726    /// ```rust
1727    /// use arc_slice::{
1728    ///     buffer::{BorrowMetadata, Buffer, BufferMut},
1729    ///     error::TryReserveError,
1730    ///     layout::ArcLayout,
1731    ///     ArcSliceMut,
1732    /// };
1733    ///
1734    /// #[derive(Debug, PartialEq, Eq)]
1735    /// struct MyBuffer(Vec<u8>);
1736    /// impl Buffer<[u8]> for MyBuffer {
1737    ///     fn as_slice(&self) -> &[u8] {
1738    ///         &self.0
1739    ///     }
1740    /// }
1741    /// // SAFETY: `MyBuffer` delegates to `Vec<u8>`, which upholds the invariant
1742    /// unsafe impl BufferMut<[u8]> for MyBuffer {
1743    ///     fn as_mut_slice(&mut self) -> &mut [u8] {
1744    ///         &mut self.0
1745    ///     }
1746    ///     fn capacity(&self) -> usize {
1747    ///         self.0.capacity()
1748    ///     }
1749    ///     unsafe fn set_len(&mut self, len: usize) -> bool {
1750    ///         // SAFETY: same function contract
1751    ///         unsafe { self.0.set_len(len) };
1752    ///         true
1753    ///     }
1754    ///     fn try_reserve(&mut self, additional: usize) -> Result<(), TryReserveError> {
1755    ///         BufferMut::try_reserve(&mut self.0, additional)
1756    ///     }
1757    /// }
1758    /// #[derive(Debug, PartialEq, Eq)]
1759    /// struct MyMetadata;
1760    /// impl BorrowMetadata for MyBuffer {
1761    ///     type Metadata = MyMetadata;
1762    ///     fn borrow_metadata(&self) -> &Self::Metadata {
1763    ///         &MyMetadata
1764    ///     }
1765    /// }
1766    /// let buffer = MyBuffer(vec![0, 1, 2]);
1767    /// let s = ArcSliceMut::<[u8], ArcLayout<true>>::try_from_buffer_with_borrowed_metadata(buffer)
1768    ///     .unwrap();
1769    /// assert_eq!(s, [0, 1, 2]);
1770    /// assert_eq!(s.metadata::<MyMetadata>().unwrap(), &MyMetadata);
1771    /// assert_eq!(
1772    ///     s.try_into_buffer::<MyBuffer>().unwrap(),
1773    ///     MyBuffer(vec![0, 1, 2])
1774    /// );
1775    /// ```
1776    pub fn try_from_buffer_with_borrowed_metadata<B: BufferMut<S> + BorrowMetadata>(
1777        buffer: B,
1778    ) -> Result<Self, B> {
1779        Self::from_dyn_buffer_impl::<_, AllocError>(buffer).map_err(|(_, buffer)| buffer)
1780    }
1781}
1782
1783unsafe impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> Send
1784    for ArcSliceMut<S, L, UNIQUE>
1785{
1786}
1787unsafe impl<S: Slice + ?Sized, L: AnyBufferLayout + LayoutMut, const UNIQUE: bool> Sync
1788    for ArcSliceMut<S, L, UNIQUE>
1789{
1790}
1791
1792impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> Drop for ArcSliceMut<S, L, UNIQUE> {
1793    fn drop(&mut self) {
1794        if let Some(data) = self.data {
1795            let drop = <L as ArcSliceMutLayout>::drop::<S, UNIQUE>;
1796            unsafe { drop(self.start, self.length, self.capacity, data) };
1797        }
1798    }
1799}
1800
1801impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> Deref for ArcSliceMut<S, L, UNIQUE> {
1802    type Target = S;
1803
1804    fn deref(&self) -> &Self::Target {
1805        self.as_slice()
1806    }
1807}
1808
1809impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> DerefMut for ArcSliceMut<S, L, UNIQUE> {
1810    fn deref_mut(&mut self) -> &mut Self::Target {
1811        self.as_mut_slice()
1812    }
1813}
1814
1815impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> AsRef<S> for ArcSliceMut<S, L, UNIQUE> {
1816    fn as_ref(&self) -> &S {
1817        self
1818    }
1819}
1820
1821impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> AsMut<S> for ArcSliceMut<S, L, UNIQUE> {
1822    fn as_mut(&mut self) -> &mut S {
1823        self
1824    }
1825}
1826
1827impl<S: Hash + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> Hash
1828    for ArcSliceMut<S, L, UNIQUE>
1829{
1830    fn hash<H>(&self, state: &mut H)
1831    where
1832        H: Hasher,
1833    {
1834        self.as_slice().hash(state);
1835    }
1836}
1837
1838impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> Borrow<S> for ArcSliceMut<S, L, UNIQUE> {
1839    fn borrow(&self) -> &S {
1840        self
1841    }
1842}
1843
1844impl<S: Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> BorrowMut<S>
1845    for ArcSliceMut<S, L, UNIQUE>
1846{
1847    fn borrow_mut(&mut self) -> &mut S {
1848        self
1849    }
1850}
1851
1852impl<S: Emptyable + ?Sized, L: LayoutMut> Default for ArcSliceMut<S, L> {
1853    fn default() -> Self {
1854        Self::new()
1855    }
1856}
1857
1858impl<S: fmt::Debug + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> fmt::Debug
1859    for ArcSliceMut<S, L, UNIQUE>
1860{
1861    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1862        debug_slice(self.as_slice(), f)
1863    }
1864}
1865
1866impl<S: fmt::Display + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> fmt::Display
1867    for ArcSliceMut<S, L, UNIQUE>
1868{
1869    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1870        self.as_slice().fmt(f)
1871    }
1872}
1873
1874impl<S: Slice<Item = u8> + ?Sized, L: LayoutMut, const UNIQUE: bool> fmt::LowerHex
1875    for ArcSliceMut<S, L, UNIQUE>
1876{
1877    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1878        lower_hex(self.to_slice(), f)
1879    }
1880}
1881
1882impl<S: Slice<Item = u8> + ?Sized, L: LayoutMut, const UNIQUE: bool> fmt::UpperHex
1883    for ArcSliceMut<S, L, UNIQUE>
1884{
1885    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1886        upper_hex(self.to_slice(), f)
1887    }
1888}
1889
1890impl<S: PartialEq + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> PartialEq
1891    for ArcSliceMut<S, L, UNIQUE>
1892{
1893    fn eq(&self, other: &ArcSliceMut<S, L, UNIQUE>) -> bool {
1894        self.as_slice() == other.as_slice()
1895    }
1896}
1897
1898impl<S: PartialEq + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> Eq
1899    for ArcSliceMut<S, L, UNIQUE>
1900{
1901}
1902
1903impl<S: PartialOrd + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> PartialOrd
1904    for ArcSliceMut<S, L, UNIQUE>
1905{
1906    fn partial_cmp(&self, other: &ArcSliceMut<S, L, UNIQUE>) -> Option<cmp::Ordering> {
1907        self.as_slice().partial_cmp(other.as_slice())
1908    }
1909}
1910
1911impl<S: Ord + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> Ord for ArcSliceMut<S, L, UNIQUE> {
1912    fn cmp(&self, other: &ArcSliceMut<S, L, UNIQUE>) -> cmp::Ordering {
1913        self.as_slice().cmp(other.as_slice())
1914    }
1915}
1916
1917impl<S: PartialEq + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> PartialEq<S>
1918    for ArcSliceMut<S, L, UNIQUE>
1919{
1920    fn eq(&self, other: &S) -> bool {
1921        self.as_slice() == other
1922    }
1923}
1924
1925impl<'a, S: PartialEq + Slice + ?Sized, L: LayoutMut, const UNIQUE: bool> PartialEq<&'a S>
1926    for ArcSliceMut<S, L, UNIQUE>
1927{
1928    fn eq(&self, other: &&'a S) -> bool {
1929        self.as_slice() == *other
1930    }
1931}
1932
1933impl<T: PartialEq + Send + Sync + 'static, L: LayoutMut, const UNIQUE: bool, const N: usize>
1934    PartialEq<[T; N]> for ArcSliceMut<[T], L, UNIQUE>
1935{
1936    fn eq(&self, other: &[T; N]) -> bool {
1937        *other == **self
1938    }
1939}
1940
1941impl<
1942        'a,
1943        T: PartialEq + Send + Sync + 'static,
1944        L: LayoutMut,
1945        const UNIQUE: bool,
1946        const N: usize,
1947    > PartialEq<&'a [T; N]> for ArcSliceMut<[T], L, UNIQUE>
1948{
1949    fn eq(&self, other: &&'a [T; N]) -> bool {
1950        **other == **self
1951    }
1952}
1953
1954impl<T: PartialEq + Send + Sync + 'static, L: LayoutMut, const UNIQUE: bool, const N: usize>
1955    PartialEq<ArcSliceMut<[T], L, UNIQUE>> for [T; N]
1956{
1957    fn eq(&self, other: &ArcSliceMut<[T], L, UNIQUE>) -> bool {
1958        **other == *self
1959    }
1960}
1961
1962impl<T: PartialEq + Send + Sync + 'static, L: LayoutMut, const UNIQUE: bool>
1963    PartialEq<ArcSliceMut<[T], L, UNIQUE>> for [T]
1964{
1965    fn eq(&self, other: &ArcSliceMut<[T], L, UNIQUE>) -> bool {
1966        **other == *self
1967    }
1968}
1969
1970impl<L: LayoutMut, const UNIQUE: bool> PartialEq<ArcSliceMut<str, L, UNIQUE>> for str {
1971    fn eq(&self, other: &ArcSliceMut<str, L, UNIQUE>) -> bool {
1972        **other == *self
1973    }
1974}
1975
1976impl<T: PartialEq + Send + Sync + 'static, L: LayoutMut, const UNIQUE: bool> PartialEq<Vec<T>>
1977    for ArcSliceMut<[T], L, UNIQUE>
1978{
1979    fn eq(&self, other: &Vec<T>) -> bool {
1980        **self == **other
1981    }
1982}
1983
1984impl<T: PartialEq + Send + Sync + 'static, L: LayoutMut, const UNIQUE: bool>
1985    PartialEq<ArcSliceMut<[T], L, UNIQUE>> for Vec<T>
1986{
1987    fn eq(&self, other: &ArcSliceMut<[T], L, UNIQUE>) -> bool {
1988        **self == **other
1989    }
1990}
1991
1992impl<L: LayoutMut, const UNIQUE: bool> PartialEq<String> for ArcSliceMut<str, L, UNIQUE> {
1993    fn eq(&self, other: &String) -> bool {
1994        **self == **other
1995    }
1996}
1997
1998impl<L: LayoutMut, const UNIQUE: bool> PartialEq<ArcSliceMut<str, L, UNIQUE>> for String {
1999    fn eq(&self, other: &ArcSliceMut<str, L, UNIQUE>) -> bool {
2000        **self == **other
2001    }
2002}
2003
2004#[cfg(feature = "oom-handling")]
2005impl<S: Slice + ?Sized, L: LayoutMut> From<&S> for ArcSliceMut<S, L>
2006where
2007    S::Item: Copy,
2008{
2009    fn from(value: &S) -> Self {
2010        Self::from_slice(value)
2011    }
2012}
2013
2014#[cfg(feature = "oom-handling")]
2015impl<T: Copy + Send + Sync + 'static, L: LayoutMut, const N: usize> From<&[T; N]>
2016    for ArcSliceMut<[T], L>
2017{
2018    fn from(value: &[T; N]) -> Self {
2019        Self::from_slice(value)
2020    }
2021}
2022
2023#[cfg(feature = "oom-handling")]
2024impl<T: Send + Sync + 'static, L: LayoutMut, const N: usize> From<[T; N]> for ArcSliceMut<[T], L> {
2025    fn from(value: [T; N]) -> Self {
2026        Self::from_array(value)
2027    }
2028}
2029
2030#[cfg(feature = "oom-handling")]
2031impl<T: Send + Sync + 'static, L: AnyBufferLayout + LayoutMut> From<Vec<T>>
2032    for ArcSliceMut<[T], L>
2033{
2034    fn from(value: Vec<T>) -> Self {
2035        Self::from_vec(value)
2036    }
2037}
2038
2039#[cfg(not(feature = "oom-handling"))]
2040impl<T: Send + Sync + 'static> From<Vec<T>> for ArcSliceMut<[T], VecLayout> {
2041    fn from(value: Vec<T>) -> Self {
2042        Self::from_vec(value)
2043    }
2044}
2045
2046impl<T: Send + Sync + 'static, L: LayoutMut, const N: usize, const UNIQUE: bool>
2047    TryFrom<ArcSliceMut<[T], L, UNIQUE>> for [T; N]
2048{
2049    type Error = ArcSliceMut<[T], L, UNIQUE>;
2050    fn try_from(value: ArcSliceMut<[T], L, UNIQUE>) -> Result<Self, Self::Error> {
2051        let data = match value.data {
2052            Some(data) => data,
2053            None if N == 0 => return Ok(transmute_checked::<[T; 0], _>([])),
2054            None => return Err(value),
2055        };
2056        let this = ManuallyDrop::new(value);
2057        let take_array = <L as ArcSliceMutLayout>::take_array::<T, N, UNIQUE>;
2058        unsafe { take_array(this.start, this.length, data) }
2059            .ok_or_else(|| ManuallyDrop::into_inner(this))
2060    }
2061}
2062
2063#[cfg(feature = "oom-handling")]
2064impl<S: Emptyable + Extendable + ?Sized, L: LayoutMut> Extend<S::Item> for ArcSliceMut<S, L> {
2065    fn extend<I: IntoIterator<Item = S::Item>>(&mut self, iter: I) {
2066        let iter = iter.into_iter();
2067        self.reserve(iter.size_hint().0);
2068        for item in iter {
2069            self.push(item);
2070        }
2071    }
2072}
2073
2074#[cfg(feature = "oom-handling")]
2075impl<S: Emptyable + Extendable + ?Sized, L: LayoutMut> FromIterator<S::Item> for ArcSliceMut<S, L> {
2076    fn from_iter<T: IntoIterator<Item = S::Item>>(iter: T) -> Self {
2077        let mut this = Self::new();
2078        this.extend(iter);
2079        this
2080    }
2081}
2082
2083#[cfg(feature = "oom-handling")]
2084impl<L: LayoutMut> core::str::FromStr for ArcSliceMut<str, L> {
2085    type Err = Infallible;
2086
2087    fn from_str(s: &str) -> Result<Self, Self::Err> {
2088        Ok(s.into())
2089    }
2090}
2091
2092impl<S: Slice<Item = u8> + Extendable + ?Sized, L: LayoutMut, const UNIQUE: bool> fmt::Write
2093    for ArcSliceMut<S, L, UNIQUE>
2094{
2095    fn write_str(&mut self, s: &str) -> fmt::Result {
2096        self.try_reserve(s.len()).map_err(|_| fmt::Error)?;
2097        unsafe { self.extend_from_slice_unchecked(s.as_bytes()) };
2098        Ok(())
2099    }
2100
2101    fn write_fmt(&mut self, args: fmt::Arguments<'_>) -> fmt::Result {
2102        fmt::write(self, args)
2103    }
2104}
2105
2106impl<L: LayoutMut, const UNIQUE: bool> fmt::Write for ArcSliceMut<str, L, UNIQUE> {
2107    fn write_str(&mut self, s: &str) -> fmt::Result {
2108        self.try_extend_from_slice(s).map_err(|_| fmt::Error)
2109    }
2110
2111    fn write_fmt(&mut self, args: fmt::Arguments<'_>) -> fmt::Result {
2112        fmt::write(self, args)
2113    }
2114}
2115
2116#[cfg(feature = "std")]
2117const _: () = {
2118    extern crate std;
2119
2120    impl<L: LayoutMut, const UNIQUE: bool> std::io::Read for ArcSliceMut<[u8], L, UNIQUE> {
2121        fn read(&mut self, buf: &mut [u8]) -> std::io::Result<usize> {
2122            let n = cmp::min(self.len(), buf.len());
2123            buf[..n].copy_from_slice(&self[..n]);
2124            Ok(n)
2125        }
2126    }
2127
2128    impl<L: LayoutMut, const UNIQUE: bool> std::io::Write for ArcSliceMut<[u8], L, UNIQUE> {
2129        fn write(&mut self, buf: &[u8]) -> std::io::Result<usize> {
2130            let n = cmp::min(self.spare_capacity(), buf.len());
2131            unsafe { self.extend_from_slice_unchecked(&buf[..n]) };
2132            Ok(n)
2133        }
2134
2135        fn flush(&mut self) -> std::io::Result<()> {
2136            Ok(())
2137        }
2138    }
2139};