Skip to main content

fidl_next_codec/
copy_optimization.rs

1// Copyright 2025 The Fuchsia Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5use core::marker::PhantomData;
6
7/// An optimization hint about whether the conversion from `T` to `U` is equivalent to copying the
8/// raw bytes of `T`.
9pub struct CopyOptimization<T: ?Sized, U: ?Sized>(bool, PhantomData<(*mut T, *mut U)>);
10
11impl<T: ?Sized, U: ?Sized> CopyOptimization<T, U> {
12    /// Returns a `CopyOptimization` hint with the optimization enabled.
13    ///
14    /// # Safety
15    ///
16    /// `T` and `U` must be the same size and must not have any uninit bytes (e.g. padding).
17    pub const unsafe fn enable() -> Self {
18        Self(true, PhantomData)
19    }
20
21    /// Returns a `CopyOptimization` hint with the optimization enabled if `value` is `true`.
22    ///
23    /// # Safety
24    ///
25    /// `T` and `U` must be the same size and must not have any uninit bytes (e.g. padding) if
26    /// `value` is `true`.
27    pub const unsafe fn enable_if(value: bool) -> Self {
28        Self(value, PhantomData)
29    }
30
31    /// Returns a `CopyOptimization` hint with the optimization disabled.
32    pub const fn disable() -> Self {
33        Self(false, PhantomData)
34    }
35
36    /// Returns whether the optimization is enabled.
37    pub const fn is_enabled(&self) -> bool {
38        self.0
39    }
40
41    /// Infers whether the conversion from `[T; N]` to `[U; N]` is copy-optimizable based on the
42    /// conversion from `T` to `U`.
43    pub const fn infer_array<const N: usize>(&self) -> CopyOptimization<[T; N], [U; N]>
44    where
45        T: Sized,
46        U: Sized,
47    {
48        unsafe { CopyOptimization::enable_if(self.is_enabled()) }
49    }
50
51    /// Infers whether the conversion from `[T]` to `[U]` is copy-optimizable based on the
52    /// conversion from `T` to `U`.
53    pub const fn infer_slice(&self) -> CopyOptimization<[T], [U]>
54    where
55        T: Sized,
56        U: Sized,
57    {
58        unsafe { CopyOptimization::enable_if(self.is_enabled()) }
59    }
60}
61
62impl<T: ?Sized> CopyOptimization<T, T> {
63    /// Returns an enabled `CopyOptimization`, as copy optimization is always enabled from a type to
64    /// itself.
65    pub const fn identity() -> Self {
66        unsafe { Self::enable() }
67    }
68}