Skip to main content

rustix/backend/libc/pipe/
types.rs

1#[cfg(linux_kernel)]
2use crate::ffi;
3#[cfg(linux_kernel)]
4use core::marker::PhantomData;
5#[cfg(not(any(apple, target_os = "wasi")))]
6use {crate::backend::c, bitflags::bitflags};
7
8#[cfg(not(any(apple, target_os = "wasi")))]
9bitflags! {
10    /// `O_*` constants for use with [`pipe_with`].
11    ///
12    /// [`pipe_with`]: crate::pipe::pipe_with
13    #[repr(transparent)]
14    #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
15    pub struct PipeFlags: u32 {
16        /// `O_CLOEXEC`
17        const CLOEXEC = bitcast!(c::O_CLOEXEC);
18        /// `O_DIRECT`
19        #[cfg(not(any(
20            solarish,
21            target_os = "espidf",
22            target_os = "haiku",
23            target_os = "horizon",
24            target_os = "hurd",
25            target_os = "nto",
26            target_os = "openbsd",
27            target_os = "redox",
28            target_os = "vita",
29        )))]
30        const DIRECT = bitcast!(c::O_DIRECT);
31        /// `O_NONBLOCK`
32        const NONBLOCK = bitcast!(c::O_NONBLOCK);
33
34        /// <https://docs.rs/bitflags/*/bitflags/#externally-defined-flags>
35        const _ = !0;
36    }
37}
38
39#[cfg(linux_kernel)]
40bitflags! {
41    /// `SPLICE_F_*` constants for use with [`splice`], [`vmsplice`], and
42    /// [`tee`].
43    ///
44    /// [`splice`]: crate::pipe::splice
45    /// [`vmsplice`]: crate::pipe::splice
46    /// [`tee`]: crate::pipe::tee
47    #[repr(transparent)]
48    #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
49    pub struct SpliceFlags: ffi::c_uint {
50        /// `SPLICE_F_MOVE`
51        const MOVE = c::SPLICE_F_MOVE;
52        /// `SPLICE_F_NONBLOCK`
53        const NONBLOCK = c::SPLICE_F_NONBLOCK;
54        /// `SPLICE_F_MORE`
55        const MORE = c::SPLICE_F_MORE;
56        /// `SPLICE_F_GIFT`
57        const GIFT = c::SPLICE_F_GIFT;
58
59        /// <https://docs.rs/bitflags/*/bitflags/#externally-defined-flags>
60        const _ = !0;
61    }
62}
63
64/// A buffer type for use with [`vmsplice`].
65///
66/// It is guaranteed to be ABI compatible with the iovec type on Unix platforms
67/// and `WSABUF` on Windows. Unlike `IoSlice` and `IoSliceMut` it is
68/// semantically like a raw pointer, and therefore can be shared or mutated as
69/// needed.
70///
71/// [`vmsplice`]: crate::pipe::vmsplice
72#[cfg(linux_kernel)]
73#[repr(transparent)]
74pub struct IoSliceRaw<'a> {
75    _buf: c::iovec,
76    _lifetime: PhantomData<&'a ()>,
77}
78
79#[cfg(linux_kernel)]
80impl<'a> IoSliceRaw<'a> {
81    /// Creates a new `IoSlice` wrapping a byte slice.
82    pub fn from_slice(buf: &'a [u8]) -> Self {
83        IoSliceRaw {
84            _buf: c::iovec {
85                iov_base: (buf.as_ptr() as *mut u8).cast::<c::c_void>(),
86                iov_len: buf.len() as _,
87            },
88            _lifetime: PhantomData,
89        }
90    }
91
92    /// Creates a new `IoSlice` wrapping a mutable byte slice.
93    pub fn from_slice_mut(buf: &'a mut [u8]) -> Self {
94        IoSliceRaw {
95            _buf: c::iovec {
96                iov_base: buf.as_mut_ptr().cast::<c::c_void>(),
97                iov_len: buf.len() as _,
98            },
99            _lifetime: PhantomData,
100        }
101    }
102}
103
104#[cfg(test)]
105mod tests {
106    #[allow(unused_imports)]
107    use super::*;
108
109    #[cfg(not(any(apple, target_os = "wasi")))]
110    #[test]
111    fn test_types() {
112        assert_eq_size!(PipeFlags, c::c_int);
113
114        #[cfg(linux_kernel)]
115        assert_eq_size!(SpliceFlags, c::c_int);
116    }
117}