Skip to main content

bytes/
bytes.rs

1use core::mem::{self, ManuallyDrop};
2use core::ops::{Deref, RangeBounds};
3use core::ptr::NonNull;
4use core::{cmp, fmt, hash, ptr, slice};
5
6use alloc::{
7    alloc::{dealloc, Layout},
8    borrow::Borrow,
9    boxed::Box,
10    string::String,
11    vec::Vec,
12};
13
14use crate::buf::IntoIter;
15#[allow(unused)]
16use crate::loom::sync::atomic::AtomicMut;
17use crate::loom::sync::atomic::{AtomicPtr, AtomicUsize, Ordering};
18use crate::{Buf, BytesMut};
19
20/// A cheaply cloneable and sliceable chunk of contiguous memory.
21///
22/// `Bytes` is an efficient container for storing and operating on contiguous
23/// slices of memory. It is intended for use primarily in networking code, but
24/// could have applications elsewhere as well.
25///
26/// `Bytes` values facilitate zero-copy network programming by allowing multiple
27/// `Bytes` objects to point to the same underlying memory.
28///
29/// `Bytes` does not have a single implementation. It is an interface, whose
30/// exact behavior is implemented through dynamic dispatch in several underlying
31/// implementations of `Bytes`.
32///
33/// All `Bytes` implementations must fulfill the following requirements:
34/// - They are cheaply cloneable and thereby shareable between an unlimited amount
35///   of components, for example by modifying a reference count.
36/// - Instances can be sliced to refer to a subset of the original buffer.
37///
38/// ```
39/// use bytes::Bytes;
40///
41/// let mut mem = Bytes::from("Hello world");
42/// let a = mem.slice(0..5);
43///
44/// assert_eq!(a, "Hello");
45///
46/// let b = mem.split_to(6);
47///
48/// assert_eq!(mem, "world");
49/// assert_eq!(b, "Hello ");
50/// ```
51///
52/// # Memory layout
53///
54/// The `Bytes` struct itself is fairly small, limited to 4 `usize` fields used
55/// to track information about which segment of the underlying memory the
56/// `Bytes` handle has access to.
57///
58/// `Bytes` keeps both a pointer to the shared state containing the full memory
59/// slice and a pointer to the start of the region visible by the handle.
60/// `Bytes` also tracks the length of its view into the memory.
61///
62/// # Sharing
63///
64/// `Bytes` contains a vtable, which allows implementations of `Bytes` to define
65/// how sharing/cloning is implemented in detail.
66/// When `Bytes::clone()` is called, `Bytes` will call the vtable function for
67/// cloning the backing storage in order to share it behind multiple `Bytes`
68/// instances.
69///
70/// For `Bytes` implementations which refer to constant memory (e.g. created
71/// via `Bytes::from_static()`) the cloning implementation will be a no-op.
72///
73/// For `Bytes` implementations which point to a reference counted shared storage
74/// (e.g. an `Arc<[u8]>`), sharing will be implemented by increasing the
75/// reference count.
76///
77/// Due to this mechanism, multiple `Bytes` instances may point to the same
78/// shared memory region.
79/// Each `Bytes` instance can point to different sections within that
80/// memory region, and `Bytes` instances may or may not have overlapping views
81/// into the memory.
82///
83/// The following diagram visualizes a scenario where 2 `Bytes` instances make
84/// use of an `Arc`-based backing storage, and provide access to different views:
85///
86/// ```text
87///
88///    Arc ptrs                   ┌─────────┐
89///    ________________________ / │ Bytes 2 │
90///   /                           └─────────┘
91///  /          ┌───────────┐     |         |
92/// |_________/ │  Bytes 1  │     |         |
93/// |           └───────────┘     |         |
94/// |           |           | ___/ data     | tail
95/// |      data |      tail |/              |
96/// v           v           v               v
97/// ┌─────┬─────┬───────────┬───────────────┬─────┐
98/// │ Arc │     │           │               │     │
99/// └─────┴─────┴───────────┴───────────────┴─────┘
100/// ```
101pub struct Bytes {
102    ptr: *const u8,
103    len: usize,
104    // inlined "trait object"
105    data: AtomicPtr<()>,
106    vtable: &'static Vtable,
107}
108
109// `data` is passed by value (`*mut ()` instead of `&mut AtomicPtr<()>`)
110// when `&mut self` or `self` is consumed.
111// This allows the optimizer to see that the address of the `Bytes` is not
112// captured by the indirect call, enabling further optimizations.
113pub(crate) struct Vtable {
114    /// fn(data, ptr, len)
115    pub clone: unsafe fn(&AtomicPtr<()>, *const u8, usize) -> Bytes,
116    /// fn(data, ptr, len)
117    ///
118    /// `into_*` consumes the `Bytes`, returning the respective value.
119    pub into_vec: unsafe fn(*mut (), *const u8, usize) -> Vec<u8>,
120    pub into_mut: unsafe fn(*mut (), *const u8, usize) -> BytesMut,
121    /// fn(data)
122    pub is_unique: unsafe fn(&AtomicPtr<()>) -> bool,
123    /// fn(data, ptr, len)
124    pub drop: unsafe fn(*mut (), *const u8, usize),
125}
126
127impl Bytes {
128    /// Creates a new empty `Bytes`.
129    ///
130    /// This will not allocate and the returned `Bytes` handle will be empty.
131    ///
132    /// # Examples
133    ///
134    /// ```
135    /// use bytes::Bytes;
136    ///
137    /// let b = Bytes::new();
138    /// assert_eq!(&b[..], b"");
139    /// ```
140    #[inline]
141    #[cfg(not(all(loom, test)))]
142    pub const fn new() -> Self {
143        // Make it a named const to work around
144        // "unsizing casts are not allowed in const fn"
145        const EMPTY: &[u8] = &[];
146        Bytes::from_static(EMPTY)
147    }
148
149    /// Creates a new empty `Bytes`.
150    #[cfg(all(loom, test))]
151    pub fn new() -> Self {
152        const EMPTY: &[u8] = &[];
153        Bytes::from_static(EMPTY)
154    }
155
156    /// Creates a new `Bytes` from a static slice.
157    ///
158    /// The returned `Bytes` will point directly to the static slice. There is
159    /// no allocating or copying.
160    ///
161    /// # Examples
162    ///
163    /// ```
164    /// use bytes::Bytes;
165    ///
166    /// let b = Bytes::from_static(b"hello");
167    /// assert_eq!(&b[..], b"hello");
168    /// ```
169    #[inline]
170    #[cfg(not(all(loom, test)))]
171    pub const fn from_static(bytes: &'static [u8]) -> Self {
172        Bytes {
173            ptr: bytes.as_ptr(),
174            len: bytes.len(),
175            data: AtomicPtr::new(ptr::null_mut()),
176            vtable: &STATIC_VTABLE,
177        }
178    }
179
180    /// Creates a new `Bytes` from a static slice.
181    #[cfg(all(loom, test))]
182    pub fn from_static(bytes: &'static [u8]) -> Self {
183        Bytes {
184            ptr: bytes.as_ptr(),
185            len: bytes.len(),
186            data: AtomicPtr::new(ptr::null_mut()),
187            vtable: &STATIC_VTABLE,
188        }
189    }
190
191    /// Creates a new `Bytes` with length zero and the given pointer as the address.
192    fn new_empty_with_ptr(ptr: *const u8) -> Self {
193        debug_assert!(!ptr.is_null());
194
195        // Detach this pointer's provenance from whichever allocation it came from, and reattach it
196        // to the provenance of the fake ZST [u8;0] at the same address.
197        let ptr = without_provenance(ptr as usize);
198
199        Bytes {
200            ptr,
201            len: 0,
202            data: AtomicPtr::new(ptr::null_mut()),
203            vtable: &STATIC_VTABLE,
204        }
205    }
206
207    /// Create [Bytes] with a buffer whose lifetime is controlled
208    /// via an explicit owner.
209    ///
210    /// A common use case is to zero-copy construct from mapped memory.
211    ///
212    /// ```
213    /// # struct File;
214    /// #
215    /// # impl File {
216    /// #     pub fn open(_: &str) -> Result<Self, ()> {
217    /// #         Ok(Self)
218    /// #     }
219    /// # }
220    /// #
221    /// # mod memmap2 {
222    /// #     pub struct Mmap;
223    /// #
224    /// #     impl Mmap {
225    /// #         pub unsafe fn map(_file: &super::File) -> Result<Self, ()> {
226    /// #             Ok(Self)
227    /// #         }
228    /// #     }
229    /// #
230    /// #     impl AsRef<[u8]> for Mmap {
231    /// #         fn as_ref(&self) -> &[u8] {
232    /// #             b"buf"
233    /// #         }
234    /// #     }
235    /// # }
236    /// use bytes::Bytes;
237    /// use memmap2::Mmap;
238    ///
239    /// # fn main() -> Result<(), ()> {
240    /// let file = File::open("upload_bundle.tar.gz")?;
241    /// let mmap = unsafe { Mmap::map(&file) }?;
242    /// let b = Bytes::from_owner(mmap);
243    /// # Ok(())
244    /// # }
245    /// ```
246    ///
247    /// The `owner` will be transferred to the constructed [Bytes] object, which
248    /// will ensure it is dropped once all remaining clones of the constructed
249    /// object are dropped. The owner will then be responsible for dropping the
250    /// specified region of memory as part of its [Drop] implementation.
251    ///
252    /// Note that converting [Bytes] constructed from an owner into a [BytesMut]
253    /// will always create a deep copy of the buffer into newly allocated memory.
254    pub fn from_owner<T>(owner: T) -> Self
255    where
256        T: AsRef<[u8]> + Send + 'static,
257    {
258        // Safety & Miri:
259        // The ownership of `owner` is first transferred to the `Owned` wrapper and `Bytes` object.
260        // This ensures that the owner is pinned in memory, allowing us to call `.as_ref()` safely
261        // since the lifetime of the owner is controlled by the lifetime of the new `Bytes` object,
262        // and the lifetime of the resulting borrowed `&[u8]` matches that of the owner.
263        // Note that this remains safe so long as we only call `.as_ref()` once.
264        //
265        // There are some additional special considerations here:
266        //   * We rely on Bytes's Drop impl to clean up memory should `.as_ref()` panic.
267        //   * Setting the `ptr` and `len` on the bytes object last (after moving the owner to
268        //     Bytes) allows Miri checks to pass since it avoids obtaining the `&[u8]` slice
269        //     from a stack-owned Box.
270        // More details on this: https://github.com/tokio-rs/bytes/pull/742/#discussion_r1813375863
271        //                  and: https://github.com/tokio-rs/bytes/pull/742/#discussion_r1813316032
272
273        let owned = Box::into_raw(Box::new(Owned {
274            ref_cnt: AtomicUsize::new(1),
275            owner,
276        }));
277
278        let mut ret = Bytes {
279            ptr: NonNull::dangling().as_ptr(),
280            len: 0,
281            data: AtomicPtr::new(owned.cast()),
282            vtable: &Owned::<T>::VTABLE,
283        };
284
285        let buf = unsafe { &*owned }.owner.as_ref();
286        ret.ptr = buf.as_ptr();
287        ret.len = buf.len();
288
289        ret
290    }
291
292    /// Returns the number of bytes contained in this `Bytes`.
293    ///
294    /// # Examples
295    ///
296    /// ```
297    /// use bytes::Bytes;
298    ///
299    /// let b = Bytes::from(&b"hello"[..]);
300    /// assert_eq!(b.len(), 5);
301    /// ```
302    #[inline]
303    pub const fn len(&self) -> usize {
304        self.len
305    }
306
307    /// Returns true if the `Bytes` has a length of 0.
308    ///
309    /// # Examples
310    ///
311    /// ```
312    /// use bytes::Bytes;
313    ///
314    /// let b = Bytes::new();
315    /// assert!(b.is_empty());
316    /// ```
317    #[inline]
318    pub const fn is_empty(&self) -> bool {
319        self.len == 0
320    }
321
322    /// Returns true if this is the only reference to the data and
323    /// `Into<BytesMut>` would avoid cloning the underlying buffer.
324    ///
325    /// Always returns false if the data is backed by a [static slice](Bytes::from_static),
326    /// or an [owner](Bytes::from_owner).
327    ///
328    /// The result of this method may be invalidated immediately if another
329    /// thread clones this value while this is being called. Ensure you have
330    /// unique access to this value (`&mut Bytes`) first if you need to be
331    /// certain the result is valid (i.e. for safety reasons).
332    /// # Examples
333    ///
334    /// ```
335    /// use bytes::Bytes;
336    ///
337    /// let a = Bytes::from(vec![1, 2, 3]);
338    /// assert!(a.is_unique());
339    /// let b = a.clone();
340    /// assert!(!a.is_unique());
341    /// ```
342    pub fn is_unique(&self) -> bool {
343        unsafe { (self.vtable.is_unique)(&self.data) }
344    }
345
346    /// Creates `Bytes` instance from slice, by copying it.
347    pub fn copy_from_slice(data: &[u8]) -> Self {
348        data.to_vec().into()
349    }
350
351    /// Returns a slice of self for the provided range.
352    ///
353    /// This will increment the reference count for the underlying memory and
354    /// return a new `Bytes` handle set to the slice.
355    ///
356    /// This operation is `O(1)`.
357    ///
358    /// # Examples
359    ///
360    /// ```
361    /// use bytes::Bytes;
362    ///
363    /// let a = Bytes::from(&b"hello world"[..]);
364    /// let b = a.slice(2..5);
365    ///
366    /// assert_eq!(&b[..], b"llo");
367    /// ```
368    ///
369    /// # Panics
370    ///
371    /// Requires that `begin <= end` and `end <= self.len()`, otherwise slicing
372    /// will panic.
373    pub fn slice(&self, range: impl RangeBounds<usize>) -> Self {
374        let (begin, end) = crate::range(range, self.len());
375
376        if end == begin {
377            return Bytes::new_empty_with_ptr(self.ptr.wrapping_add(begin));
378        }
379
380        let mut ret = self.clone();
381
382        ret.len = end - begin;
383        ret.ptr = unsafe { ret.ptr.add(begin) };
384
385        ret
386    }
387
388    /// Returns a slice of self that is equivalent to the given `subset`.
389    ///
390    /// When processing a `Bytes` buffer with other tools, one often gets a
391    /// `&[u8]` which is in fact a slice of the `Bytes`, i.e. a subset of it.
392    /// This function turns that `&[u8]` into another `Bytes`, as if one had
393    /// called `self.slice()` with the offsets that correspond to `subset`.
394    ///
395    /// This operation is `O(1)`.
396    ///
397    /// # Examples
398    ///
399    /// ```
400    /// use bytes::Bytes;
401    ///
402    /// let bytes = Bytes::from(&b"012345678"[..]);
403    /// let as_slice = bytes.as_ref();
404    /// let subset = &as_slice[2..6];
405    /// let subslice = bytes.slice_ref(&subset);
406    /// assert_eq!(&subslice[..], b"2345");
407    /// ```
408    ///
409    /// # Panics
410    ///
411    /// Requires that the given `sub` slice is in fact contained within the
412    /// `Bytes` buffer; otherwise this function will panic.
413    pub fn slice_ref(&self, subset: &[u8]) -> Self {
414        // Empty slice and empty Bytes may have their pointers reset
415        // so explicitly allow empty slice to be a subslice of any slice.
416        if subset.is_empty() {
417            return Bytes::new();
418        }
419
420        let bytes_p = self.as_ptr() as usize;
421        let bytes_len = self.len();
422
423        let sub_p = subset.as_ptr() as usize;
424        let sub_len = subset.len();
425
426        assert!(
427            sub_p >= bytes_p,
428            "subset pointer ({:p}) is smaller than self pointer ({:p})",
429            subset.as_ptr(),
430            self.as_ptr(),
431        );
432        assert!(
433            sub_p + sub_len <= bytes_p + bytes_len,
434            "subset is out of bounds: self = ({:p}, {}), subset = ({:p}, {})",
435            self.as_ptr(),
436            bytes_len,
437            subset.as_ptr(),
438            sub_len,
439        );
440
441        let sub_offset = sub_p - bytes_p;
442
443        self.slice(sub_offset..(sub_offset + sub_len))
444    }
445
446    /// Splits the bytes into two at the given index.
447    ///
448    /// Afterwards `self` contains elements `[0, at)`, and the returned `Bytes`
449    /// contains elements `[at, len)`. It's guaranteed that the memory does not
450    /// move, that is, the address of `self` does not change, and the address of
451    /// the returned slice is `at` bytes after that.
452    ///
453    /// This is an `O(1)` operation that just increases the reference count and
454    /// sets a few indices.
455    ///
456    /// # Examples
457    ///
458    /// ```
459    /// use bytes::Bytes;
460    ///
461    /// let mut a = Bytes::from(&b"hello world"[..]);
462    /// let b = a.split_off(5);
463    ///
464    /// assert_eq!(&a[..], b"hello");
465    /// assert_eq!(&b[..], b" world");
466    /// ```
467    ///
468    /// # Panics
469    ///
470    /// Panics if `at > len`.
471    #[must_use = "consider Bytes::truncate if you don't need the other half"]
472    pub fn split_off(&mut self, at: usize) -> Self {
473        if at == self.len() {
474            return Bytes::new_empty_with_ptr(self.ptr.wrapping_add(at));
475        }
476
477        if at == 0 {
478            return mem::replace(self, Bytes::new_empty_with_ptr(self.ptr));
479        }
480
481        assert!(
482            at <= self.len(),
483            "split_off out of bounds: {:?} <= {:?}",
484            at,
485            self.len(),
486        );
487
488        let mut ret = self.clone();
489
490        self.len = at;
491
492        // SAFETY: `at` has been asserted to be <= `self.len()`, and the
493        // `at == self.len()` and `at == 0` cases were handled above.
494        unsafe { ret.inc_start(at) };
495
496        ret
497    }
498
499    /// Splits the bytes into two at the given index.
500    ///
501    /// Afterwards `self` contains elements `[at, len)`, and the returned
502    /// `Bytes` contains elements `[0, at)`.
503    ///
504    /// This is an `O(1)` operation that just increases the reference count and
505    /// sets a few indices.
506    ///
507    /// # Examples
508    ///
509    /// ```
510    /// use bytes::Bytes;
511    ///
512    /// let mut a = Bytes::from(&b"hello world"[..]);
513    /// let b = a.split_to(5);
514    ///
515    /// assert_eq!(&a[..], b" world");
516    /// assert_eq!(&b[..], b"hello");
517    /// ```
518    ///
519    /// # Panics
520    ///
521    /// Panics if `at > len`.
522    #[must_use = "consider Bytes::advance if you don't need the other half"]
523    pub fn split_to(&mut self, at: usize) -> Self {
524        if at == self.len() {
525            let end_ptr = self.ptr.wrapping_add(at);
526            return mem::replace(self, Bytes::new_empty_with_ptr(end_ptr));
527        }
528
529        if at == 0 {
530            return Bytes::new_empty_with_ptr(self.ptr);
531        }
532
533        assert!(
534            at <= self.len(),
535            "split_to out of bounds: {:?} <= {:?}",
536            at,
537            self.len(),
538        );
539
540        let mut ret = self.clone();
541
542        // SAFETY: `at` has been asserted to be <= `self.len()`, and the
543        // `at == self.len()` and `at == 0` cases were handled above.
544        unsafe { self.inc_start(at) };
545
546        ret.len = at;
547        ret
548    }
549
550    /// Shortens the buffer, keeping the first `len` bytes and dropping the
551    /// rest.
552    ///
553    /// If `len` is greater than the buffer's current length, this has no
554    /// effect.
555    ///
556    /// The [split_off](`Self::split_off()`) method can emulate `truncate`, but this causes the
557    /// excess bytes to be returned instead of dropped.
558    ///
559    /// # Examples
560    ///
561    /// ```
562    /// use bytes::Bytes;
563    ///
564    /// let mut buf = Bytes::from(&b"hello world"[..]);
565    /// buf.truncate(5);
566    /// assert_eq!(buf, b"hello"[..]);
567    /// ```
568    #[inline]
569    pub fn truncate(&mut self, len: usize) {
570        if len < self.len {
571            // The Vec "promotable" vtables do not store the capacity,
572            // so we cannot truncate while using this repr. We *have* to
573            // promote using `split_off` so the capacity can be stored.
574            if self.vtable as *const Vtable == &PROMOTABLE_EVEN_VTABLE
575                || self.vtable as *const Vtable == &PROMOTABLE_ODD_VTABLE
576            {
577                drop(self.split_off(len));
578            } else {
579                self.len = len;
580            }
581        }
582    }
583
584    /// Clears the buffer, removing all data.
585    ///
586    /// # Examples
587    ///
588    /// ```
589    /// use bytes::Bytes;
590    ///
591    /// let mut buf = Bytes::from(&b"hello world"[..]);
592    /// buf.clear();
593    /// assert!(buf.is_empty());
594    /// ```
595    #[inline]
596    pub fn clear(&mut self) {
597        self.truncate(0);
598    }
599
600    /// Try to convert self into `BytesMut`.
601    ///
602    /// If `self` is unique for the entire original buffer, this will succeed
603    /// and return a `BytesMut` with the contents of `self` without copying.
604    /// If `self` is not unique for the entire original buffer, this will fail
605    /// and return self.
606    ///
607    /// This will also always fail if the buffer was constructed via either
608    /// [from_owner](Bytes::from_owner) or [from_static](Bytes::from_static).
609    ///
610    /// # Examples
611    ///
612    /// ```
613    /// use bytes::{Bytes, BytesMut};
614    ///
615    /// let bytes = Bytes::from(b"hello".to_vec());
616    /// assert_eq!(bytes.try_into_mut(), Ok(BytesMut::from(&b"hello"[..])));
617    /// ```
618    pub fn try_into_mut(self) -> Result<BytesMut, Bytes> {
619        if self.is_unique() {
620            Ok(self.into())
621        } else {
622            Err(self)
623        }
624    }
625
626    #[inline]
627    pub(crate) unsafe fn with_vtable(
628        ptr: *const u8,
629        len: usize,
630        data: AtomicPtr<()>,
631        vtable: &'static Vtable,
632    ) -> Bytes {
633        Bytes {
634            ptr,
635            len,
636            data,
637            vtable,
638        }
639    }
640
641    // private
642
643    #[inline]
644    fn as_slice(&self) -> &[u8] {
645        unsafe { slice::from_raw_parts(self.ptr, self.len) }
646    }
647
648    #[inline]
649    unsafe fn inc_start(&mut self, by: usize) {
650        // should already be asserted, but debug assert for tests
651        debug_assert!(self.len >= by, "internal: inc_start out of bounds");
652        self.len -= by;
653        self.ptr = self.ptr.add(by);
654    }
655
656    #[inline]
657    fn data_mut(&mut self) -> *mut () {
658        self.data.with_mut(|p| *p)
659    }
660}
661
662// Vtable must enforce this behavior
663unsafe impl Send for Bytes {}
664unsafe impl Sync for Bytes {}
665
666impl Drop for Bytes {
667    #[inline]
668    fn drop(&mut self) {
669        let data = self.data_mut();
670        unsafe { (self.vtable.drop)(data, self.ptr, self.len) }
671    }
672}
673
674impl Clone for Bytes {
675    #[inline]
676    fn clone(&self) -> Bytes {
677        unsafe { (self.vtable.clone)(&self.data, self.ptr, self.len) }
678    }
679}
680
681impl Buf for Bytes {
682    #[inline]
683    fn remaining(&self) -> usize {
684        self.len()
685    }
686
687    #[inline]
688    fn chunk(&self) -> &[u8] {
689        self.as_slice()
690    }
691
692    #[inline]
693    fn advance(&mut self, cnt: usize) {
694        assert!(
695            cnt <= self.len(),
696            "cannot advance past `remaining`: {:?} <= {:?}",
697            cnt,
698            self.len(),
699        );
700
701        unsafe {
702            self.inc_start(cnt);
703        }
704    }
705
706    fn copy_to_bytes(&mut self, len: usize) -> Self {
707        self.split_to(len)
708    }
709}
710
711impl Deref for Bytes {
712    type Target = [u8];
713
714    #[inline]
715    fn deref(&self) -> &[u8] {
716        self.as_slice()
717    }
718}
719
720impl AsRef<[u8]> for Bytes {
721    #[inline]
722    fn as_ref(&self) -> &[u8] {
723        self.as_slice()
724    }
725}
726
727impl hash::Hash for Bytes {
728    fn hash<H>(&self, state: &mut H)
729    where
730        H: hash::Hasher,
731    {
732        self.as_slice().hash(state);
733    }
734}
735
736impl Borrow<[u8]> for Bytes {
737    fn borrow(&self) -> &[u8] {
738        self.as_slice()
739    }
740}
741
742impl IntoIterator for Bytes {
743    type Item = u8;
744    type IntoIter = IntoIter<Bytes>;
745
746    fn into_iter(self) -> Self::IntoIter {
747        IntoIter::new(self)
748    }
749}
750
751impl<'a> IntoIterator for &'a Bytes {
752    type Item = &'a u8;
753    type IntoIter = core::slice::Iter<'a, u8>;
754
755    fn into_iter(self) -> Self::IntoIter {
756        self.as_slice().iter()
757    }
758}
759
760impl FromIterator<u8> for Bytes {
761    fn from_iter<T: IntoIterator<Item = u8>>(into_iter: T) -> Self {
762        Vec::from_iter(into_iter).into()
763    }
764}
765
766// impl Eq
767
768impl PartialEq for Bytes {
769    fn eq(&self, other: &Bytes) -> bool {
770        self.as_slice() == other.as_slice()
771    }
772}
773
774impl PartialOrd for Bytes {
775    fn partial_cmp(&self, other: &Bytes) -> Option<cmp::Ordering> {
776        Some(self.cmp(other))
777    }
778}
779
780impl Ord for Bytes {
781    fn cmp(&self, other: &Bytes) -> cmp::Ordering {
782        self.as_slice().cmp(other.as_slice())
783    }
784}
785
786impl Eq for Bytes {}
787
788impl PartialEq<[u8]> for Bytes {
789    fn eq(&self, other: &[u8]) -> bool {
790        self.as_slice() == other
791    }
792}
793
794impl PartialOrd<[u8]> for Bytes {
795    fn partial_cmp(&self, other: &[u8]) -> Option<cmp::Ordering> {
796        self.as_slice().partial_cmp(other)
797    }
798}
799
800impl PartialEq<Bytes> for [u8] {
801    fn eq(&self, other: &Bytes) -> bool {
802        *other == *self
803    }
804}
805
806impl PartialOrd<Bytes> for [u8] {
807    fn partial_cmp(&self, other: &Bytes) -> Option<cmp::Ordering> {
808        <[u8] as PartialOrd<[u8]>>::partial_cmp(self, other)
809    }
810}
811
812impl PartialEq<str> for Bytes {
813    fn eq(&self, other: &str) -> bool {
814        self.as_slice() == other.as_bytes()
815    }
816}
817
818impl PartialOrd<str> for Bytes {
819    fn partial_cmp(&self, other: &str) -> Option<cmp::Ordering> {
820        self.as_slice().partial_cmp(other.as_bytes())
821    }
822}
823
824impl PartialEq<Bytes> for str {
825    fn eq(&self, other: &Bytes) -> bool {
826        *other == *self
827    }
828}
829
830impl PartialOrd<Bytes> for str {
831    fn partial_cmp(&self, other: &Bytes) -> Option<cmp::Ordering> {
832        <[u8] as PartialOrd<[u8]>>::partial_cmp(self.as_bytes(), other)
833    }
834}
835
836impl PartialEq<Vec<u8>> for Bytes {
837    fn eq(&self, other: &Vec<u8>) -> bool {
838        *self == other[..]
839    }
840}
841
842impl PartialOrd<Vec<u8>> for Bytes {
843    fn partial_cmp(&self, other: &Vec<u8>) -> Option<cmp::Ordering> {
844        self.as_slice().partial_cmp(&other[..])
845    }
846}
847
848impl PartialEq<Bytes> for Vec<u8> {
849    fn eq(&self, other: &Bytes) -> bool {
850        *other == *self
851    }
852}
853
854impl PartialOrd<Bytes> for Vec<u8> {
855    fn partial_cmp(&self, other: &Bytes) -> Option<cmp::Ordering> {
856        <[u8] as PartialOrd<[u8]>>::partial_cmp(self, other)
857    }
858}
859
860impl PartialEq<String> for Bytes {
861    fn eq(&self, other: &String) -> bool {
862        *self == other[..]
863    }
864}
865
866impl PartialOrd<String> for Bytes {
867    fn partial_cmp(&self, other: &String) -> Option<cmp::Ordering> {
868        self.as_slice().partial_cmp(other.as_bytes())
869    }
870}
871
872impl PartialEq<Bytes> for String {
873    fn eq(&self, other: &Bytes) -> bool {
874        *other == *self
875    }
876}
877
878impl PartialOrd<Bytes> for String {
879    fn partial_cmp(&self, other: &Bytes) -> Option<cmp::Ordering> {
880        <[u8] as PartialOrd<[u8]>>::partial_cmp(self.as_bytes(), other)
881    }
882}
883
884impl PartialEq<Bytes> for &[u8] {
885    fn eq(&self, other: &Bytes) -> bool {
886        *other == *self
887    }
888}
889
890impl PartialOrd<Bytes> for &[u8] {
891    fn partial_cmp(&self, other: &Bytes) -> Option<cmp::Ordering> {
892        <[u8] as PartialOrd<[u8]>>::partial_cmp(self, other)
893    }
894}
895
896impl PartialEq<Bytes> for &str {
897    fn eq(&self, other: &Bytes) -> bool {
898        *other == *self
899    }
900}
901
902impl PartialOrd<Bytes> for &str {
903    fn partial_cmp(&self, other: &Bytes) -> Option<cmp::Ordering> {
904        <[u8] as PartialOrd<[u8]>>::partial_cmp(self.as_bytes(), other)
905    }
906}
907
908impl<'a, T: ?Sized> PartialEq<&'a T> for Bytes
909where
910    Bytes: PartialEq<T>,
911{
912    fn eq(&self, other: &&'a T) -> bool {
913        *self == **other
914    }
915}
916
917impl<'a, T: ?Sized> PartialOrd<&'a T> for Bytes
918where
919    Bytes: PartialOrd<T>,
920{
921    fn partial_cmp(&self, other: &&'a T) -> Option<cmp::Ordering> {
922        self.partial_cmp(&**other)
923    }
924}
925
926// impl From
927
928impl Default for Bytes {
929    #[inline]
930    fn default() -> Bytes {
931        Bytes::new()
932    }
933}
934
935impl From<&'static [u8]> for Bytes {
936    fn from(slice: &'static [u8]) -> Bytes {
937        Bytes::from_static(slice)
938    }
939}
940
941impl From<&'static str> for Bytes {
942    fn from(slice: &'static str) -> Bytes {
943        Bytes::from_static(slice.as_bytes())
944    }
945}
946
947impl From<Vec<u8>> for Bytes {
948    fn from(vec: Vec<u8>) -> Bytes {
949        let mut vec = ManuallyDrop::new(vec);
950        let ptr = vec.as_mut_ptr();
951        let len = vec.len();
952        let cap = vec.capacity();
953
954        // Avoid an extra allocation if possible.
955        if len == cap {
956            let vec = ManuallyDrop::into_inner(vec);
957            return Bytes::from(vec.into_boxed_slice());
958        }
959
960        let shared = Box::new(Shared {
961            buf: ptr,
962            cap,
963            ref_cnt: AtomicUsize::new(1),
964        });
965
966        let shared = Box::into_raw(shared);
967        // The pointer should be aligned, so this assert should
968        // always succeed.
969        debug_assert!(
970            0 == (shared as usize & KIND_MASK),
971            "internal: Box<Shared> should have an aligned pointer",
972        );
973        Bytes {
974            ptr,
975            len,
976            data: AtomicPtr::new(shared as _),
977            vtable: &SHARED_VTABLE,
978        }
979    }
980}
981
982impl From<Box<[u8]>> for Bytes {
983    fn from(slice: Box<[u8]>) -> Bytes {
984        // Box<[u8]> doesn't contain a heap allocation for empty slices,
985        // so the pointer isn't aligned enough for the KIND_VEC stashing to
986        // work.
987        if slice.is_empty() {
988            return Bytes::new();
989        }
990
991        let len = slice.len();
992        let ptr = Box::into_raw(slice) as *mut u8;
993
994        if ptr as usize & 0x1 == 0 {
995            let data = ptr_map(ptr, |addr| addr | KIND_VEC);
996            Bytes {
997                ptr,
998                len,
999                data: AtomicPtr::new(data.cast()),
1000                vtable: &PROMOTABLE_EVEN_VTABLE,
1001            }
1002        } else {
1003            Bytes {
1004                ptr,
1005                len,
1006                data: AtomicPtr::new(ptr.cast()),
1007                vtable: &PROMOTABLE_ODD_VTABLE,
1008            }
1009        }
1010    }
1011}
1012
1013impl From<Bytes> for BytesMut {
1014    /// Convert self into `BytesMut`.
1015    ///
1016    /// If `bytes` is unique for the entire original buffer, this will return a
1017    /// `BytesMut` with the contents of `bytes` without copying.
1018    /// If `bytes` is not unique for the entire original buffer, this will make
1019    /// a copy of `bytes` subset of the original buffer in a new `BytesMut`.
1020    ///
1021    /// # Examples
1022    ///
1023    /// ```
1024    /// use bytes::{Bytes, BytesMut};
1025    ///
1026    /// let bytes = Bytes::from(b"hello".to_vec());
1027    /// assert_eq!(BytesMut::from(bytes), BytesMut::from(&b"hello"[..]));
1028    /// ```
1029    fn from(bytes: Bytes) -> Self {
1030        let mut bytes = ManuallyDrop::new(bytes);
1031        let data = bytes.data_mut();
1032        unsafe { (bytes.vtable.into_mut)(data, bytes.ptr, bytes.len) }
1033    }
1034}
1035
1036impl From<String> for Bytes {
1037    fn from(s: String) -> Bytes {
1038        Bytes::from(s.into_bytes())
1039    }
1040}
1041
1042impl From<Bytes> for Vec<u8> {
1043    fn from(bytes: Bytes) -> Vec<u8> {
1044        let mut bytes = ManuallyDrop::new(bytes);
1045        let data = bytes.data_mut();
1046        unsafe { (bytes.vtable.into_vec)(data, bytes.ptr, bytes.len) }
1047    }
1048}
1049
1050// ===== impl Vtable =====
1051
1052impl fmt::Debug for Vtable {
1053    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
1054        f.debug_struct("Vtable")
1055            .field("clone", &(self.clone as *const ()))
1056            .field("drop", &(self.drop as *const ()))
1057            .finish()
1058    }
1059}
1060
1061// ===== impl StaticVtable =====
1062
1063const STATIC_VTABLE: Vtable = Vtable {
1064    clone: static_clone,
1065    into_vec: static_to_vec,
1066    into_mut: static_to_mut,
1067    is_unique: static_is_unique,
1068    drop: static_drop,
1069};
1070
1071unsafe fn static_clone(_: &AtomicPtr<()>, ptr: *const u8, len: usize) -> Bytes {
1072    let slice = slice::from_raw_parts(ptr, len);
1073    Bytes::from_static(slice)
1074}
1075
1076unsafe fn static_to_vec(_: *mut (), ptr: *const u8, len: usize) -> Vec<u8> {
1077    let slice = slice::from_raw_parts(ptr, len);
1078    slice.to_vec()
1079}
1080
1081unsafe fn static_to_mut(_: *mut (), ptr: *const u8, len: usize) -> BytesMut {
1082    let slice = slice::from_raw_parts(ptr, len);
1083    BytesMut::from(slice)
1084}
1085
1086fn static_is_unique(_: &AtomicPtr<()>) -> bool {
1087    false
1088}
1089
1090unsafe fn static_drop(_: *mut (), _: *const u8, _: usize) {
1091    // nothing to drop for &'static [u8]
1092}
1093
1094// ===== impl OwnedVtable =====
1095
1096#[repr(C)]
1097struct Owned<T> {
1098    ref_cnt: AtomicUsize,
1099    owner: T,
1100}
1101
1102impl<T> Owned<T> {
1103    const VTABLE: Vtable = Vtable {
1104        clone: owned_clone::<T>,
1105        into_vec: owned_to_vec::<T>,
1106        into_mut: owned_to_mut::<T>,
1107        is_unique: owned_is_unique,
1108        drop: owned_drop::<T>,
1109    };
1110}
1111
1112unsafe fn owned_clone<T>(data: &AtomicPtr<()>, ptr: *const u8, len: usize) -> Bytes {
1113    let owned = data.load(Ordering::Relaxed);
1114    let old_cnt = (*owned.cast::<AtomicUsize>()).fetch_add(1, Ordering::Relaxed);
1115    if old_cnt > usize::MAX >> 1 {
1116        crate::abort();
1117    }
1118
1119    Bytes {
1120        ptr,
1121        len,
1122        data: AtomicPtr::new(owned as _),
1123        vtable: &Owned::<T>::VTABLE,
1124    }
1125}
1126
1127unsafe fn owned_to_vec<T>(owned: *mut (), ptr: *const u8, len: usize) -> Vec<u8> {
1128    let slice = slice::from_raw_parts(ptr, len);
1129    let vec = slice.to_vec();
1130    owned_drop_impl::<T>(owned);
1131    vec
1132}
1133
1134unsafe fn owned_to_mut<T>(owned: *mut (), ptr: *const u8, len: usize) -> BytesMut {
1135    BytesMut::from_vec(owned_to_vec::<T>(owned, ptr, len))
1136}
1137
1138unsafe fn owned_is_unique(_data: &AtomicPtr<()>) -> bool {
1139    false
1140}
1141
1142unsafe fn owned_drop_impl<T>(owned: *mut ()) {
1143    {
1144        let ref_cnt = &*owned.cast::<AtomicUsize>();
1145
1146        let old_cnt = ref_cnt.fetch_sub(1, Ordering::Release);
1147        debug_assert!(
1148            old_cnt > 0 && old_cnt <= usize::MAX >> 1,
1149            "expected non-zero refcount and no underflow"
1150        );
1151        if old_cnt != 1 {
1152            return;
1153        }
1154        ref_cnt.load(Ordering::Acquire);
1155    }
1156
1157    drop(Box::<Owned<T>>::from_raw(owned.cast()));
1158}
1159
1160unsafe fn owned_drop<T>(data: *mut (), _ptr: *const u8, _len: usize) {
1161    owned_drop_impl::<T>(data);
1162}
1163
1164// ===== impl PromotableVtable =====
1165
1166static PROMOTABLE_EVEN_VTABLE: Vtable = Vtable {
1167    clone: promotable_even_clone,
1168    into_vec: promotable_even_to_vec,
1169    into_mut: promotable_even_to_mut,
1170    is_unique: promotable_is_unique,
1171    drop: promotable_even_drop,
1172};
1173
1174static PROMOTABLE_ODD_VTABLE: Vtable = Vtable {
1175    clone: promotable_odd_clone,
1176    into_vec: promotable_odd_to_vec,
1177    into_mut: promotable_odd_to_mut,
1178    is_unique: promotable_is_unique,
1179    drop: promotable_odd_drop,
1180};
1181
1182unsafe fn promotable_even_clone(data: &AtomicPtr<()>, ptr: *const u8, len: usize) -> Bytes {
1183    let shared = data.load(Ordering::Acquire);
1184    let kind = shared as usize & KIND_MASK;
1185
1186    if kind == KIND_ARC {
1187        shallow_clone_arc(shared.cast(), ptr, len)
1188    } else {
1189        debug_assert_eq!(kind, KIND_VEC);
1190        let buf = ptr_map(shared.cast(), |addr| addr & !KIND_MASK);
1191        shallow_clone_vec(data, shared, buf, ptr, len)
1192    }
1193}
1194
1195unsafe fn promotable_to_vec(
1196    shared: *mut (),
1197    ptr: *const u8,
1198    len: usize,
1199    f: fn(*mut ()) -> *mut u8,
1200) -> Vec<u8> {
1201    let kind = shared as usize & KIND_MASK;
1202
1203    if kind == KIND_ARC {
1204        shared_to_vec_impl(shared.cast(), ptr, len)
1205    } else {
1206        // If Bytes holds a Vec, then the offset must be 0.
1207        debug_assert_eq!(kind, KIND_VEC);
1208
1209        let buf = f(shared);
1210
1211        let cap = ptr.offset_from(buf) as usize + len;
1212
1213        // Copy back buffer
1214        ptr::copy(ptr, buf, len);
1215
1216        Vec::from_raw_parts(buf, len, cap)
1217    }
1218}
1219
1220unsafe fn promotable_to_mut(
1221    shared: *mut (),
1222    ptr: *const u8,
1223    len: usize,
1224    f: fn(*mut ()) -> *mut u8,
1225) -> BytesMut {
1226    let kind = shared as usize & KIND_MASK;
1227
1228    if kind == KIND_ARC {
1229        shared_to_mut_impl(shared.cast(), ptr, len)
1230    } else {
1231        // KIND_VEC is a view of an underlying buffer at a certain offset.
1232        // The ptr + len always represents the end of that buffer.
1233        // Before truncating it, it is first promoted to KIND_ARC.
1234        // Thus, we can safely reconstruct a Vec from it without leaking memory.
1235        debug_assert_eq!(kind, KIND_VEC);
1236
1237        let buf = f(shared);
1238        let off = ptr.offset_from(buf) as usize;
1239        let cap = off + len;
1240        let v = Vec::from_raw_parts(buf, cap, cap);
1241
1242        let mut b = BytesMut::from_vec(v);
1243        b.advance_unchecked(off);
1244        b
1245    }
1246}
1247
1248unsafe fn promotable_even_to_vec(shared: *mut (), ptr: *const u8, len: usize) -> Vec<u8> {
1249    promotable_to_vec(shared, ptr, len, |shared| {
1250        ptr_map(shared.cast(), |addr| addr & !KIND_MASK)
1251    })
1252}
1253
1254unsafe fn promotable_even_to_mut(shared: *mut (), ptr: *const u8, len: usize) -> BytesMut {
1255    promotable_to_mut(shared, ptr, len, |shared| {
1256        ptr_map(shared.cast(), |addr| addr & !KIND_MASK)
1257    })
1258}
1259
1260unsafe fn promotable_even_drop(shared: *mut (), ptr: *const u8, len: usize) {
1261    let kind = shared as usize & KIND_MASK;
1262
1263    if kind == KIND_ARC {
1264        release_shared(shared.cast());
1265    } else {
1266        debug_assert_eq!(kind, KIND_VEC);
1267        let buf = ptr_map(shared.cast(), |addr| addr & !KIND_MASK);
1268        free_boxed_slice(buf, ptr, len);
1269    }
1270}
1271
1272unsafe fn promotable_odd_clone(data: &AtomicPtr<()>, ptr: *const u8, len: usize) -> Bytes {
1273    let shared = data.load(Ordering::Acquire);
1274    let kind = shared as usize & KIND_MASK;
1275
1276    if kind == KIND_ARC {
1277        shallow_clone_arc(shared as _, ptr, len)
1278    } else {
1279        debug_assert_eq!(kind, KIND_VEC);
1280        shallow_clone_vec(data, shared, shared.cast(), ptr, len)
1281    }
1282}
1283
1284unsafe fn promotable_odd_to_vec(shared: *mut (), ptr: *const u8, len: usize) -> Vec<u8> {
1285    promotable_to_vec(shared, ptr, len, |shared| shared.cast())
1286}
1287
1288unsafe fn promotable_odd_to_mut(shared: *mut (), ptr: *const u8, len: usize) -> BytesMut {
1289    promotable_to_mut(shared, ptr, len, |shared| shared.cast())
1290}
1291
1292unsafe fn promotable_odd_drop(shared: *mut (), ptr: *const u8, len: usize) {
1293    let kind = shared as usize & KIND_MASK;
1294
1295    if kind == KIND_ARC {
1296        release_shared(shared.cast());
1297    } else {
1298        debug_assert_eq!(kind, KIND_VEC);
1299
1300        free_boxed_slice(shared.cast(), ptr, len);
1301    }
1302}
1303
1304unsafe fn promotable_is_unique(data: &AtomicPtr<()>) -> bool {
1305    let shared = data.load(Ordering::Acquire);
1306    let kind = shared as usize & KIND_MASK;
1307
1308    if kind == KIND_ARC {
1309        let ref_cnt = (*shared.cast::<Shared>()).ref_cnt.load(Ordering::Relaxed);
1310        ref_cnt == 1
1311    } else {
1312        true
1313    }
1314}
1315
1316unsafe fn free_boxed_slice(buf: *mut u8, offset: *const u8, len: usize) {
1317    let cap = offset.offset_from(buf) as usize + len;
1318    dealloc(buf, Layout::from_size_align(cap, 1).unwrap())
1319}
1320
1321// ===== impl SharedVtable =====
1322
1323struct Shared {
1324    // Holds arguments to dealloc upon Drop, but otherwise doesn't use them
1325    buf: *mut u8,
1326    cap: usize,
1327    ref_cnt: AtomicUsize,
1328}
1329
1330impl Drop for Shared {
1331    fn drop(&mut self) {
1332        unsafe { dealloc(self.buf, Layout::from_size_align(self.cap, 1).unwrap()) }
1333    }
1334}
1335
1336// Assert that the alignment of `Shared` is divisible by 2.
1337// This is a necessary invariant since we depend on allocating `Shared` a
1338// shared object to implicitly carry the `KIND_ARC` flag in its pointer.
1339// This flag is set when the LSB is 0.
1340const _: [(); 0 - mem::align_of::<Shared>() % 2] = []; // Assert that the alignment of `Shared` is divisible by 2.
1341
1342static SHARED_VTABLE: Vtable = Vtable {
1343    clone: shared_clone,
1344    into_vec: shared_to_vec,
1345    into_mut: shared_to_mut,
1346    is_unique: shared_is_unique,
1347    drop: shared_drop,
1348};
1349
1350const KIND_ARC: usize = 0b0;
1351const KIND_VEC: usize = 0b1;
1352const KIND_MASK: usize = 0b1;
1353
1354unsafe fn shared_clone(data: &AtomicPtr<()>, ptr: *const u8, len: usize) -> Bytes {
1355    let shared = data.load(Ordering::Relaxed);
1356    shallow_clone_arc(shared as _, ptr, len)
1357}
1358
1359unsafe fn shared_to_vec_impl(shared: *mut Shared, ptr: *const u8, len: usize) -> Vec<u8> {
1360    // Check that the ref_cnt is 1 (unique).
1361    //
1362    // If it is unique, then it is set to 0 with AcqRel fence for the same
1363    // reason in release_shared.
1364    //
1365    // Otherwise, we take the other branch and call release_shared.
1366    if (*shared)
1367        .ref_cnt
1368        .compare_exchange(1, 0, Ordering::AcqRel, Ordering::Relaxed)
1369        .is_ok()
1370    {
1371        // Deallocate the `Shared` instance without running its destructor.
1372        let shared = *Box::from_raw(shared);
1373        let shared = ManuallyDrop::new(shared);
1374        let buf = shared.buf;
1375        let cap = shared.cap;
1376
1377        // Copy back buffer
1378        ptr::copy(ptr, buf, len);
1379
1380        Vec::from_raw_parts(buf, len, cap)
1381    } else {
1382        let v = slice::from_raw_parts(ptr, len).to_vec();
1383        release_shared(shared);
1384        v
1385    }
1386}
1387
1388unsafe fn shared_to_vec(shared: *mut (), ptr: *const u8, len: usize) -> Vec<u8> {
1389    shared_to_vec_impl(shared.cast(), ptr, len)
1390}
1391
1392unsafe fn shared_to_mut_impl(shared: *mut Shared, ptr: *const u8, len: usize) -> BytesMut {
1393    // The goal is to check if the current handle is the only handle
1394    // that currently has access to the buffer. This is done by
1395    // checking if the `ref_cnt` is currently 1.
1396    //
1397    // The `Acquire` ordering synchronizes with the `Release` as
1398    // part of the `fetch_sub` in `release_shared`. The `fetch_sub`
1399    // operation guarantees that any mutations done in other threads
1400    // are ordered before the `ref_cnt` is decremented. As such,
1401    // this `Acquire` will guarantee that those mutations are
1402    // visible to the current thread.
1403    //
1404    // Otherwise, we take the other branch, copy the data and call `release_shared`.
1405    if (*shared).ref_cnt.load(Ordering::Acquire) == 1 {
1406        // Deallocate the `Shared` instance without running its destructor.
1407        let shared = *Box::from_raw(shared);
1408        let shared = ManuallyDrop::new(shared);
1409        let buf = shared.buf;
1410        let cap = shared.cap;
1411
1412        // Rebuild Vec
1413        let off = ptr.offset_from(buf) as usize;
1414        let v = Vec::from_raw_parts(buf, len + off, cap);
1415
1416        let mut b = BytesMut::from_vec(v);
1417        b.advance_unchecked(off);
1418        b
1419    } else {
1420        // Copy the data from Shared in a new Vec, then release it
1421        let v = slice::from_raw_parts(ptr, len).to_vec();
1422        release_shared(shared);
1423        BytesMut::from_vec(v)
1424    }
1425}
1426
1427unsafe fn shared_to_mut(shared: *mut (), ptr: *const u8, len: usize) -> BytesMut {
1428    shared_to_mut_impl(shared.cast(), ptr, len)
1429}
1430
1431pub(crate) unsafe fn shared_is_unique(data: &AtomicPtr<()>) -> bool {
1432    let shared = data.load(Ordering::Acquire);
1433    let ref_cnt = (*shared.cast::<Shared>()).ref_cnt.load(Ordering::Relaxed);
1434    ref_cnt == 1
1435}
1436
1437unsafe fn shared_drop(shared: *mut (), _ptr: *const u8, _len: usize) {
1438    release_shared(shared.cast());
1439}
1440
1441unsafe fn shallow_clone_arc(shared: *mut Shared, ptr: *const u8, len: usize) -> Bytes {
1442    let old_size = (*shared).ref_cnt.fetch_add(1, Ordering::Relaxed);
1443
1444    if old_size > usize::MAX >> 1 {
1445        crate::abort();
1446    }
1447
1448    Bytes {
1449        ptr,
1450        len,
1451        data: AtomicPtr::new(shared as _),
1452        vtable: &SHARED_VTABLE,
1453    }
1454}
1455
1456#[cold]
1457unsafe fn shallow_clone_vec(
1458    atom: &AtomicPtr<()>,
1459    ptr: *const (),
1460    buf: *mut u8,
1461    offset: *const u8,
1462    len: usize,
1463) -> Bytes {
1464    // If the buffer is still tracked in a `Vec<u8>`. It is time to
1465    // promote the vec to an `Arc`. This could potentially be called
1466    // concurrently, so some care must be taken.
1467
1468    // First, allocate a new `Shared` instance containing the
1469    // `Vec` fields. It's important to note that `ptr`, `len`,
1470    // and `cap` cannot be mutated without having `&mut self`.
1471    // This means that these fields will not be concurrently
1472    // updated and since the buffer hasn't been promoted to an
1473    // `Arc`, those three fields still are the components of the
1474    // vector.
1475    let shared = Box::new(Shared {
1476        buf,
1477        cap: offset.offset_from(buf) as usize + len,
1478        // Initialize refcount to 2. One for this reference, and one
1479        // for the new clone that will be returned from
1480        // `shallow_clone`.
1481        ref_cnt: AtomicUsize::new(2),
1482    });
1483
1484    let shared = Box::into_raw(shared);
1485
1486    // The pointer should be aligned, so this assert should
1487    // always succeed.
1488    debug_assert!(
1489        0 == (shared as usize & KIND_MASK),
1490        "internal: Box<Shared> should have an aligned pointer",
1491    );
1492
1493    // Try compare & swapping the pointer into the `arc` field.
1494    // `Release` is used synchronize with other threads that
1495    // will load the `arc` field.
1496    //
1497    // If the `compare_exchange` fails, then the thread lost the
1498    // race to promote the buffer to shared. The `Acquire`
1499    // ordering will synchronize with the `compare_exchange`
1500    // that happened in the other thread and the `Shared`
1501    // pointed to by `actual` will be visible.
1502    match atom.compare_exchange(ptr as _, shared as _, Ordering::AcqRel, Ordering::Acquire) {
1503        Ok(actual) => {
1504            debug_assert!(core::ptr::eq(actual, ptr));
1505            // The upgrade was successful, the new handle can be
1506            // returned.
1507            Bytes {
1508                ptr: offset,
1509                len,
1510                data: AtomicPtr::new(shared as _),
1511                vtable: &SHARED_VTABLE,
1512            }
1513        }
1514        Err(actual) => {
1515            // The upgrade failed, a concurrent clone happened. Release
1516            // the allocation that was made in this thread, it will not
1517            // be needed.
1518            let shared = Box::from_raw(shared);
1519            mem::forget(*shared);
1520
1521            // Buffer already promoted to shared storage, so increment ref
1522            // count.
1523            shallow_clone_arc(actual as _, offset, len)
1524        }
1525    }
1526}
1527
1528unsafe fn release_shared(ptr: *mut Shared) {
1529    // `Shared` storage... follow the drop steps from Arc.
1530    if (*ptr).ref_cnt.fetch_sub(1, Ordering::Release) != 1 {
1531        return;
1532    }
1533
1534    // This fence is needed to prevent reordering of use of the data and
1535    // deletion of the data.  Because it is marked `Release`, the decreasing
1536    // of the reference count synchronizes with this `Acquire` fence. This
1537    // means that use of the data happens before decreasing the reference
1538    // count, which happens before this fence, which happens before the
1539    // deletion of the data.
1540    //
1541    // As explained in the [Boost documentation][1],
1542    //
1543    // > It is important to enforce any possible access to the object in one
1544    // > thread (through an existing reference) to *happen before* deleting
1545    // > the object in a different thread. This is achieved by a "release"
1546    // > operation after dropping a reference (any access to the object
1547    // > through this reference must obviously happened before), and an
1548    // > "acquire" operation before deleting the object.
1549    //
1550    // [1]: (www.boost.org/doc/libs/1_55_0/doc/html/atomic/usage_examples.html)
1551    //
1552    // Thread sanitizer does not support atomic fences. Use an atomic load
1553    // instead.
1554    (*ptr).ref_cnt.load(Ordering::Acquire);
1555
1556    // Drop the data
1557    drop(Box::from_raw(ptr));
1558}
1559
1560// Ideally we would always use this version of `ptr_map` since it is strict
1561// provenance compatible, but it results in worse codegen. We will however still
1562// use it on miri because it gives better diagnostics for people who test bytes
1563// code with miri.
1564//
1565// See https://github.com/tokio-rs/bytes/pull/545 for more info.
1566#[cfg(miri)]
1567fn ptr_map<F>(ptr: *mut u8, f: F) -> *mut u8
1568where
1569    F: FnOnce(usize) -> usize,
1570{
1571    let old_addr = ptr as usize;
1572    let new_addr = f(old_addr);
1573    let diff = new_addr.wrapping_sub(old_addr);
1574    ptr.wrapping_add(diff)
1575}
1576
1577#[cfg(not(miri))]
1578fn ptr_map<F>(ptr: *mut u8, f: F) -> *mut u8
1579where
1580    F: FnOnce(usize) -> usize,
1581{
1582    let old_addr = ptr as usize;
1583    let new_addr = f(old_addr);
1584    new_addr as *mut u8
1585}
1586
1587fn without_provenance(ptr: usize) -> *const u8 {
1588    core::ptr::null::<u8>().wrapping_add(ptr)
1589}
1590
1591// compile-fails
1592
1593/// ```compile_fail
1594/// use bytes::Bytes;
1595/// #[deny(unused_must_use)]
1596/// {
1597///     let mut b1 = Bytes::from("hello world");
1598///     b1.split_to(6);
1599/// }
1600/// ```
1601fn _split_to_must_use() {}
1602
1603/// ```compile_fail
1604/// use bytes::Bytes;
1605/// #[deny(unused_must_use)]
1606/// {
1607///     let mut b1 = Bytes::from("hello world");
1608///     b1.split_off(6);
1609/// }
1610/// ```
1611fn _split_off_must_use() {}
1612
1613// fuzz tests
1614#[cfg(all(test, loom))]
1615mod fuzz {
1616    use loom::sync::Arc;
1617    use loom::thread;
1618
1619    use super::Bytes;
1620    #[test]
1621    fn bytes_cloning_vec() {
1622        loom::model(|| {
1623            let a = Bytes::from(b"abcdefgh".to_vec());
1624            let addr = a.as_ptr() as usize;
1625
1626            // test the Bytes::clone is Sync by putting it in an Arc
1627            let a1 = Arc::new(a);
1628            let a2 = a1.clone();
1629
1630            let t1 = thread::spawn(move || {
1631                let b: Bytes = (*a1).clone();
1632                assert_eq!(b.as_ptr() as usize, addr);
1633            });
1634
1635            let t2 = thread::spawn(move || {
1636                let b: Bytes = (*a2).clone();
1637                assert_eq!(b.as_ptr() as usize, addr);
1638            });
1639
1640            t1.join().unwrap();
1641            t2.join().unwrap();
1642        });
1643    }
1644}