fidl_next_codec/wire/
mod.rs

1// Copyright 2024 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
5mod boxed;
6mod envelope;
7mod ptr;
8mod result;
9mod string;
10mod table;
11mod union;
12mod vec;
13
14pub use self::boxed::*;
15pub use self::envelope::*;
16pub use self::ptr::*;
17pub use self::result::*;
18pub use self::string::*;
19pub use self::table::*;
20pub use self::union::*;
21pub use self::vec::*;
22
23use core::mem::MaybeUninit;
24
25use crate::{WireF32, WireF64, WireI16, WireI32, WireI64, WireU16, WireU32, WireU64};
26
27/// A FIDL wire type.
28///
29/// # Safety
30///
31/// - References to decoded data yielded by `Self::Decoded<'de>` must not outlive `'de`.
32/// - `zero_padding` must write zeroes to (at least) the padding bytes of `out`.
33pub unsafe trait Wire: 'static + Sized {
34    /// The decoded wire type, restricted to the `'de` lifetime.
35    type Decoded<'de>: 'de;
36
37    /// Writes zeroes to the padding for this type, if any.
38    fn zero_padding(out: &mut MaybeUninit<Self>);
39}
40
41macro_rules! impl_primitive {
42    ($ty:ty) => {
43        unsafe impl Wire for $ty {
44            type Decoded<'de> = Self;
45
46            #[inline]
47            fn zero_padding(_: &mut MaybeUninit<Self>) {}
48        }
49    };
50}
51
52macro_rules! impl_primitives {
53    ($($ty:ty),* $(,)?) => {
54        $(
55            impl_primitive!($ty);
56        )*
57    }
58}
59
60impl_primitives! {
61    (),
62    bool,
63    i8, WireI16, WireI32, WireI64,
64    u8, WireU16, WireU32, WireU64,
65    WireF32, WireF64,
66}
67
68unsafe impl<T: Wire, const N: usize> Wire for [T; N] {
69    type Decoded<'de> = [T::Decoded<'de>; N];
70
71    #[inline]
72    fn zero_padding(out: &mut MaybeUninit<Self>) {
73        for i in 0..N {
74            let out_i = unsafe { &mut *out.as_mut_ptr().cast::<MaybeUninit<T>>().add(i) };
75            T::zero_padding(out_i);
76        }
77    }
78}