summaryrefslogtreecommitdiff
path: root/vendor/rustix/src/backend/libc/net
diff options
context:
space:
mode:
authormo khan <mo@mokhan.ca>2025-07-15 16:37:08 -0600
committermo khan <mo@mokhan.ca>2025-07-17 16:30:22 -0600
commit45df4d0d9b577fecee798d672695fe24ff57fb1b (patch)
tree1b99bf645035b58e0d6db08c7a83521f41f7a75b /vendor/rustix/src/backend/libc/net
parentf94f79608393d4ab127db63cc41668445ef6b243 (diff)
feat: migrate from Cedar to SpiceDB authorization system
This is a major architectural change that replaces the Cedar policy-based authorization system with SpiceDB's relation-based authorization. Key changes: - Migrate from Rust to Go implementation - Replace Cedar policies with SpiceDB schema and relationships - Switch from envoy `ext_authz` with Cedar to SpiceDB permission checks - Update build system and dependencies for Go ecosystem - Maintain Envoy integration for external authorization This change enables more flexible permission modeling through SpiceDB's Google Zanzibar inspired relation-based system, supporting complex hierarchical permissions that were difficult to express in Cedar. Breaking change: Existing Cedar policies and Rust-based configuration will no longer work and need to be migrated to SpiceDB schema.
Diffstat (limited to 'vendor/rustix/src/backend/libc/net')
-rw-r--r--vendor/rustix/src/backend/libc/net/addr.rs390
-rw-r--r--vendor/rustix/src/backend/libc/net/ext.rs137
-rw-r--r--vendor/rustix/src/backend/libc/net/mod.rs17
-rw-r--r--vendor/rustix/src/backend/libc/net/msghdr.rs188
-rw-r--r--vendor/rustix/src/backend/libc/net/netdevice.rs55
-rw-r--r--vendor/rustix/src/backend/libc/net/read_sockaddr.rs264
-rw-r--r--vendor/rustix/src/backend/libc/net/send_recv.rs153
-rw-r--r--vendor/rustix/src/backend/libc/net/sockopt.rs1339
-rw-r--r--vendor/rustix/src/backend/libc/net/syscalls.rs438
-rw-r--r--vendor/rustix/src/backend/libc/net/write_sockaddr.rs72
10 files changed, 0 insertions, 3053 deletions
diff --git a/vendor/rustix/src/backend/libc/net/addr.rs b/vendor/rustix/src/backend/libc/net/addr.rs
deleted file mode 100644
index 1699ffa9..00000000
--- a/vendor/rustix/src/backend/libc/net/addr.rs
+++ /dev/null
@@ -1,390 +0,0 @@
-//! Socket address utilities.
-
-use crate::backend::c;
-use crate::net::AddressFamily;
-#[cfg(unix)]
-use {
- crate::ffi::CStr,
- crate::io,
- crate::net::addr::SocketAddrLen,
- crate::path,
- core::cmp::Ordering,
- core::fmt,
- core::hash::{Hash, Hasher},
- core::slice,
-};
-#[cfg(all(unix, feature = "alloc"))]
-use {crate::ffi::CString, alloc::borrow::Cow, alloc::vec::Vec};
-
-/// `struct sockaddr_un`
-#[cfg(unix)]
-#[derive(Clone)]
-#[doc(alias = "sockaddr_un")]
-pub struct SocketAddrUnix {
- pub(crate) unix: c::sockaddr_un,
- #[cfg(not(any(bsd, target_os = "haiku")))]
- len: c::socklen_t,
-}
-
-#[cfg(unix)]
-impl SocketAddrUnix {
- /// Construct a new Unix-domain address from a filesystem path.
- #[inline]
- pub fn new<P: path::Arg>(path: P) -> io::Result<Self> {
- path.into_with_c_str(Self::_new)
- }
-
- #[inline]
- fn _new(path: &CStr) -> io::Result<Self> {
- let mut unix = Self::init();
- let mut bytes = path.to_bytes_with_nul();
- if bytes.len() > unix.sun_path.len() {
- bytes = path.to_bytes(); // without NUL
- if bytes.len() > unix.sun_path.len() {
- return Err(io::Errno::NAMETOOLONG);
- }
- }
- for (i, b) in bytes.iter().enumerate() {
- unix.sun_path[i] = *b as c::c_char;
- }
-
- #[cfg(any(bsd, target_os = "haiku"))]
- {
- unix.sun_len = (offsetof_sun_path() + bytes.len()).try_into().unwrap();
- }
-
- Ok(Self {
- unix,
- #[cfg(not(any(bsd, target_os = "haiku")))]
- len: (offsetof_sun_path() + bytes.len()).try_into().unwrap(),
- })
- }
-
- /// Construct a new abstract Unix-domain address from a byte slice.
- #[cfg(linux_kernel)]
- #[inline]
- pub fn new_abstract_name(name: &[u8]) -> io::Result<Self> {
- let mut unix = Self::init();
- if 1 + name.len() > unix.sun_path.len() {
- return Err(io::Errno::NAMETOOLONG);
- }
- unix.sun_path[0] = 0;
- for (i, b) in name.iter().enumerate() {
- unix.sun_path[1 + i] = *b as c::c_char;
- }
- let len = offsetof_sun_path() + 1 + name.len();
- let len = len.try_into().unwrap();
- Ok(Self {
- unix,
- #[cfg(not(any(bsd, target_os = "haiku")))]
- len,
- })
- }
-
- /// Construct a new unnamed address.
- ///
- /// The kernel will assign an abstract Unix-domain address to the socket
- /// when you call [`bind`][crate::net::bind]. You can inspect the assigned
- /// name with [`getsockname`][crate::net::getsockname].
- ///
- /// # References
- /// - [Linux]
- ///
- /// [Linux]: https://www.man7.org/linux/man-pages/man7/unix.7.html
- #[cfg(linux_kernel)]
- #[inline]
- pub fn new_unnamed() -> Self {
- Self {
- unix: Self::init(),
- #[cfg(not(any(bsd, target_os = "haiku")))]
- len: offsetof_sun_path() as c::socklen_t,
- }
- }
-
- const fn init() -> c::sockaddr_un {
- c::sockaddr_un {
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto",
- target_os = "hurd",
- ))]
- sun_len: 0,
- #[cfg(target_os = "vita")]
- ss_len: 0,
- sun_family: c::AF_UNIX as _,
- #[cfg(any(bsd, target_os = "horizon", target_os = "nto"))]
- sun_path: [0; 104],
- #[cfg(not(any(
- bsd,
- target_os = "aix",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto"
- )))]
- sun_path: [0; 108],
- #[cfg(target_os = "haiku")]
- sun_path: [0; 126],
- #[cfg(target_os = "aix")]
- sun_path: [0; 1023],
- }
- }
-
- /// For a filesystem path address, return the path.
- #[inline]
- #[cfg(feature = "alloc")]
- #[cfg_attr(docsrs, doc(cfg(feature = "alloc")))]
- pub fn path(&self) -> Option<Cow<'_, CStr>> {
- let bytes = self.bytes()?;
- if !bytes.is_empty() && bytes[0] != 0 {
- if self.unix.sun_path.len() == bytes.len() {
- // SAFETY: There are no NULs contained in bytes.
- unsafe { Self::path_with_termination(bytes) }
- } else {
- // SAFETY: `from_bytes_with_nul_unchecked` since the string is
- // NUL-terminated.
- Some(unsafe { CStr::from_bytes_with_nul_unchecked(bytes) }.into())
- }
- } else {
- None
- }
- }
-
- /// If the `sun_path` field is not NUL-terminated, terminate it.
- ///
- /// SAFETY: The input `bytes` must not contain any NULs.
- #[cfg(feature = "alloc")]
- #[cold]
- unsafe fn path_with_termination(bytes: &[u8]) -> Option<Cow<'_, CStr>> {
- let mut owned = Vec::with_capacity(bytes.len() + 1);
- owned.extend_from_slice(bytes);
- owned.push(b'\0');
- // SAFETY: `from_vec_with_nul_unchecked` since the string is
- // NUL-terminated and `bytes` does not contain any NULs.
- Some(Cow::Owned(
- CString::from_vec_with_nul_unchecked(owned).into(),
- ))
- }
-
- /// For a filesystem path address, return the path as a byte sequence,
- /// excluding the NUL terminator.
- #[inline]
- pub fn path_bytes(&self) -> Option<&[u8]> {
- let bytes = self.bytes()?;
- if !bytes.is_empty() && bytes[0] != 0 {
- if self.unix.sun_path.len() == self.len() - offsetof_sun_path() {
- // There is no NUL terminator.
- Some(bytes)
- } else {
- // Remove the NUL terminator.
- Some(&bytes[..bytes.len() - 1])
- }
- } else {
- None
- }
- }
-
- /// For an abstract address, return the identifier.
- #[cfg(linux_kernel)]
- #[inline]
- pub fn abstract_name(&self) -> Option<&[u8]> {
- if let [0, bytes @ ..] = self.bytes()? {
- Some(bytes)
- } else {
- None
- }
- }
-
- /// `true` if the socket address is unnamed.
- #[cfg(linux_kernel)]
- #[inline]
- pub fn is_unnamed(&self) -> bool {
- self.bytes() == Some(&[])
- }
-
- #[inline]
- pub(crate) fn addr_len(&self) -> SocketAddrLen {
- #[cfg(not(any(bsd, target_os = "haiku")))]
- {
- bitcast!(self.len)
- }
- #[cfg(any(bsd, target_os = "haiku"))]
- {
- bitcast!(c::socklen_t::from(self.unix.sun_len))
- }
- }
-
- #[inline]
- pub(crate) fn len(&self) -> usize {
- self.addr_len() as usize
- }
-
- #[inline]
- fn bytes(&self) -> Option<&[u8]> {
- let len = self.len();
- if len != 0 {
- let bytes = &self.unix.sun_path[..len - offsetof_sun_path()];
- // SAFETY: `from_raw_parts` to convert from `&[c_char]` to `&[u8]`.
- Some(unsafe { slice::from_raw_parts(bytes.as_ptr().cast(), bytes.len()) })
- } else {
- None
- }
- }
-}
-
-#[cfg(unix)]
-impl PartialEq for SocketAddrUnix {
- #[inline]
- fn eq(&self, other: &Self) -> bool {
- let self_len = self.len() - offsetof_sun_path();
- let other_len = other.len() - offsetof_sun_path();
- self.unix.sun_path[..self_len].eq(&other.unix.sun_path[..other_len])
- }
-}
-
-#[cfg(unix)]
-impl Eq for SocketAddrUnix {}
-
-#[cfg(unix)]
-impl PartialOrd for SocketAddrUnix {
- #[inline]
- fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
- Some(self.cmp(other))
- }
-}
-
-#[cfg(unix)]
-impl Ord for SocketAddrUnix {
- #[inline]
- fn cmp(&self, other: &Self) -> Ordering {
- let self_len = self.len() - offsetof_sun_path();
- let other_len = other.len() - offsetof_sun_path();
- self.unix.sun_path[..self_len].cmp(&other.unix.sun_path[..other_len])
- }
-}
-
-#[cfg(unix)]
-impl Hash for SocketAddrUnix {
- #[inline]
- fn hash<H: Hasher>(&self, state: &mut H) {
- let self_len = self.len() - offsetof_sun_path();
- self.unix.sun_path[..self_len].hash(state)
- }
-}
-
-#[cfg(unix)]
-impl fmt::Debug for SocketAddrUnix {
- fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
- #[cfg(feature = "alloc")]
- if let Some(path) = self.path() {
- return path.fmt(f);
- }
- if let Some(bytes) = self.path_bytes() {
- if let Ok(s) = core::str::from_utf8(bytes) {
- return s.fmt(f);
- }
- return bytes.fmt(f);
- }
- #[cfg(linux_kernel)]
- if let Some(name) = self.abstract_name() {
- return name.fmt(f);
- }
- "(unnamed)".fmt(f)
- }
-}
-
-/// `struct sockaddr_storage`
-///
-/// This type is guaranteed to be large enough to hold any encoded socket
-/// address.
-#[repr(transparent)]
-#[derive(Copy, Clone)]
-#[doc(alias = "sockaddr_storage")]
-pub struct SocketAddrStorage(c::sockaddr_storage);
-
-impl SocketAddrStorage {
- /// Return a socket addr storage initialized to all zero bytes. The
- /// `sa_family` is set to [`AddressFamily::UNSPEC`].
- pub fn zeroed() -> Self {
- assert_eq!(c::AF_UNSPEC, 0);
- // SAFETY: `sockaddr_storage` is meant to be zero-initializable.
- unsafe { core::mem::zeroed() }
- }
-
- /// Return the `sa_family` of this socket address.
- pub fn family(&self) -> AddressFamily {
- // SAFETY: `self.0` is a `sockaddr_storage` so it has enough space.
- unsafe {
- AddressFamily::from_raw(crate::backend::net::read_sockaddr::read_sa_family(
- crate::utils::as_ptr(&self.0).cast::<c::sockaddr>(),
- ))
- }
- }
-
- /// Clear the `sa_family` of this socket address to
- /// [`AddressFamily::UNSPEC`].
- pub fn clear_family(&mut self) {
- // SAFETY: `self.0` is a `sockaddr_storage` so it has enough space.
- unsafe {
- crate::backend::net::read_sockaddr::initialize_family_to_unspec(
- crate::utils::as_mut_ptr(&mut self.0).cast::<c::sockaddr>(),
- )
- }
- }
-}
-
-/// Return the offset of the `sun_path` field of `sockaddr_un`.
-#[cfg(not(windows))]
-#[inline]
-pub(crate) fn offsetof_sun_path() -> usize {
- let z = c::sockaddr_un {
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "hurd",
- target_os = "nto",
- ))]
- sun_len: 0_u8,
- #[cfg(target_os = "vita")]
- ss_len: 0,
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- ))]
- sun_family: 0_u8,
- #[cfg(not(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- )))]
- sun_family: 0_u16,
- #[cfg(any(bsd, target_os = "horizon", target_os = "nto"))]
- sun_path: [0; 104],
- #[cfg(not(any(
- bsd,
- target_os = "aix",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto"
- )))]
- sun_path: [0; 108],
- #[cfg(target_os = "haiku")]
- sun_path: [0; 126],
- #[cfg(target_os = "aix")]
- sun_path: [0; 1023],
- };
- (crate::utils::as_ptr(&z.sun_path) as usize) - (crate::utils::as_ptr(&z) as usize)
-}
diff --git a/vendor/rustix/src/backend/libc/net/ext.rs b/vendor/rustix/src/backend/libc/net/ext.rs
deleted file mode 100644
index efd2b31c..00000000
--- a/vendor/rustix/src/backend/libc/net/ext.rs
+++ /dev/null
@@ -1,137 +0,0 @@
-use crate::backend::c;
-
-/// The windows `sockaddr_in6` type is a union with accessor functions which
-/// are not `const fn`. Define our own layout-compatible version so that we
-/// can transmute in and out of it.
-#[cfg(windows)]
-#[repr(C)]
-struct sockaddr_in6 {
- sin6_family: u16,
- sin6_port: u16,
- sin6_flowinfo: u32,
- sin6_addr: c::in6_addr,
- sin6_scope_id: u32,
-}
-
-#[cfg(not(windows))]
-#[inline]
-pub(crate) const fn in_addr_s_addr(addr: c::in_addr) -> u32 {
- addr.s_addr
-}
-
-#[cfg(windows)]
-#[inline]
-pub(crate) const fn in_addr_s_addr(addr: c::in_addr) -> u32 {
- // This should be `*addr.S_un.S_addr()`, except that isn't a `const fn`.
- unsafe { core::mem::transmute(addr) }
-}
-
-#[cfg(not(windows))]
-#[inline]
-pub(crate) const fn in_addr_new(s_addr: u32) -> c::in_addr {
- c::in_addr { s_addr }
-}
-
-#[cfg(windows)]
-#[inline]
-pub(crate) const fn in_addr_new(s_addr: u32) -> c::in_addr {
- unsafe { core::mem::transmute(s_addr) }
-}
-
-#[cfg(not(windows))]
-#[inline]
-pub(crate) const fn in6_addr_s6_addr(addr: c::in6_addr) -> [u8; 16] {
- addr.s6_addr
-}
-
-#[cfg(windows)]
-#[inline]
-pub(crate) const fn in6_addr_s6_addr(addr: c::in6_addr) -> [u8; 16] {
- unsafe { core::mem::transmute(addr) }
-}
-
-#[cfg(not(windows))]
-#[inline]
-pub(crate) const fn in6_addr_new(s6_addr: [u8; 16]) -> c::in6_addr {
- c::in6_addr { s6_addr }
-}
-
-#[cfg(windows)]
-#[inline]
-pub(crate) const fn in6_addr_new(s6_addr: [u8; 16]) -> c::in6_addr {
- unsafe { core::mem::transmute(s6_addr) }
-}
-
-#[cfg(not(windows))]
-#[inline]
-pub(crate) const fn sockaddr_in6_sin6_scope_id(addr: &c::sockaddr_in6) -> u32 {
- addr.sin6_scope_id
-}
-
-#[cfg(windows)]
-#[inline]
-pub(crate) const fn sockaddr_in6_sin6_scope_id(addr: &c::sockaddr_in6) -> u32 {
- let addr: &sockaddr_in6 = unsafe { core::mem::transmute(addr) };
- addr.sin6_scope_id
-}
-
-#[cfg(not(windows))]
-#[inline]
-pub(crate) const fn sockaddr_in6_new(
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- ))]
- sin6_len: u8,
- sin6_family: c::sa_family_t,
- sin6_port: u16,
- sin6_flowinfo: u32,
- sin6_addr: c::in6_addr,
- sin6_scope_id: u32,
-) -> c::sockaddr_in6 {
- c::sockaddr_in6 {
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- ))]
- sin6_len,
- sin6_family,
- sin6_port,
- sin6_flowinfo,
- sin6_addr,
- sin6_scope_id,
- #[cfg(solarish)]
- __sin6_src_id: 0,
- #[cfg(target_os = "vita")]
- sin6_vport: 0,
- }
-}
-
-#[cfg(windows)]
-#[inline]
-pub(crate) const fn sockaddr_in6_new(
- sin6_family: u16,
- sin6_port: u16,
- sin6_flowinfo: u32,
- sin6_addr: c::in6_addr,
- sin6_scope_id: u32,
-) -> c::sockaddr_in6 {
- let addr = sockaddr_in6 {
- sin6_family,
- sin6_port,
- sin6_flowinfo,
- sin6_addr,
- sin6_scope_id,
- };
- unsafe { core::mem::transmute(addr) }
-}
diff --git a/vendor/rustix/src/backend/libc/net/mod.rs b/vendor/rustix/src/backend/libc/net/mod.rs
deleted file mode 100644
index da7e1df8..00000000
--- a/vendor/rustix/src/backend/libc/net/mod.rs
+++ /dev/null
@@ -1,17 +0,0 @@
-pub(crate) mod addr;
-pub(crate) mod ext;
-#[cfg(not(any(
- windows,
- target_os = "espidf",
- target_os = "horizon",
- target_os = "redox",
- target_os = "vita"
-)))]
-pub(crate) mod msghdr;
-#[cfg(linux_kernel)]
-pub(crate) mod netdevice;
-pub(crate) mod read_sockaddr;
-pub(crate) mod send_recv;
-pub(crate) mod sockopt;
-pub(crate) mod syscalls;
-pub(crate) mod write_sockaddr;
diff --git a/vendor/rustix/src/backend/libc/net/msghdr.rs b/vendor/rustix/src/backend/libc/net/msghdr.rs
deleted file mode 100644
index fe5471b9..00000000
--- a/vendor/rustix/src/backend/libc/net/msghdr.rs
+++ /dev/null
@@ -1,188 +0,0 @@
-//! Utilities for dealing with message headers.
-//!
-//! These take closures rather than returning a `c::msghdr` directly because
-//! the message headers may reference stack-local data.
-
-use crate::backend::c;
-
-use crate::io::{self, IoSlice, IoSliceMut};
-use crate::net::addr::SocketAddrArg;
-use crate::net::{RecvAncillaryBuffer, SendAncillaryBuffer, SocketAddrBuf};
-
-use core::mem::zeroed;
-
-/// Convert the value to the `msg_iovlen` field of a `msghdr` struct.
-#[cfg(all(
- not(any(windows, target_os = "espidf", target_os = "wasi")),
- any(
- target_os = "android",
- all(
- target_os = "linux",
- not(target_env = "musl"),
- not(all(target_env = "uclibc", any(target_arch = "arm", target_arch = "mips")))
- )
- )
-))]
-#[inline]
-fn msg_iov_len(len: usize) -> c::size_t {
- len
-}
-
-/// Convert the value to the `msg_iovlen` field of a `msghdr` struct.
-#[cfg(all(
- not(any(
- windows,
- target_os = "espidf",
- target_os = "redox",
- target_os = "vita",
- target_os = "wasi"
- )),
- not(any(
- target_os = "android",
- all(
- target_os = "linux",
- not(target_env = "musl"),
- not(all(target_env = "uclibc", any(target_arch = "arm", target_arch = "mips")))
- )
- ))
-))]
-#[inline]
-fn msg_iov_len(len: usize) -> c::c_int {
- len.try_into().unwrap_or(c::c_int::MAX)
-}
-
-/// Convert the value to a `socklen_t`.
-#[cfg(any(
- bsd,
- solarish,
- target_env = "musl",
- target_os = "aix",
- target_os = "cygwin",
- target_os = "emscripten",
- target_os = "fuchsia",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
-))]
-#[inline]
-fn msg_control_len(len: usize) -> c::socklen_t {
- len.try_into().unwrap_or(c::socklen_t::MAX)
-}
-
-/// Convert the value to a `size_t`.
-#[cfg(not(any(
- bsd,
- solarish,
- windows,
- target_env = "musl",
- target_os = "aix",
- target_os = "cygwin",
- target_os = "emscripten",
- target_os = "espidf",
- target_os = "fuchsia",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
- target_os = "wasi",
-)))]
-#[inline]
-fn msg_control_len(len: usize) -> c::size_t {
- len
-}
-
-/// Create a message header intended to receive a datagram.
-///
-/// # Safety
-///
-/// If `f` dereferences the pointers in the `msghdr`, it must do so only within
-/// the bounds indicated by the associated lengths in the `msghdr`.
-///
-/// And, if `f` returns `Ok`, it must have updated the `msg_controllen` field
-/// of the `msghdr` to indicate how many bytes it initialized.
-pub(crate) unsafe fn with_recv_msghdr<R>(
- name: &mut SocketAddrBuf,
- iov: &mut [IoSliceMut<'_>],
- control: &mut RecvAncillaryBuffer<'_>,
- f: impl FnOnce(&mut c::msghdr) -> io::Result<R>,
-) -> io::Result<R> {
- control.clear();
-
- let mut msghdr = zero_msghdr();
- msghdr.msg_name = name.storage.as_mut_ptr().cast();
- msghdr.msg_namelen = name.len;
- msghdr.msg_iov = iov.as_mut_ptr().cast();
- msghdr.msg_iovlen = msg_iov_len(iov.len());
- msghdr.msg_control = control.as_control_ptr().cast();
- msghdr.msg_controllen = msg_control_len(control.control_len());
-
- let res = f(&mut msghdr);
-
- // Reset the control length.
- if res.is_ok() {
- // SAFETY: `f` returned `Ok`, so our safety condition requires `f` to
- // have initialized `msg_controllen` bytes.
- control.set_control_len(msghdr.msg_controllen as usize);
- }
-
- name.len = msghdr.msg_namelen;
-
- res
-}
-
-/// Create a message header intended to send without an address.
-///
-/// The returned `msghdr` will contain raw pointers to the memory
-/// referenced by `iov` and `control`.
-pub(crate) fn noaddr_msghdr(
- iov: &[IoSlice<'_>],
- control: &mut SendAncillaryBuffer<'_, '_, '_>,
-) -> c::msghdr {
- let mut h = zero_msghdr();
- h.msg_iov = iov.as_ptr() as _;
- h.msg_iovlen = msg_iov_len(iov.len());
- h.msg_control = control.as_control_ptr().cast();
- h.msg_controllen = msg_control_len(control.control_len());
- h
-}
-
-/// Create a message header intended to send with the specified address.
-///
-/// This creates a `c::msghdr` and calls a function `f` on it. The `msghdr`'s
-/// raw pointers may point to temporaries, so this function should avoid
-/// storing the pointers anywhere that would outlive the function call.
-///
-/// # Safety
-///
-/// If `f` dereferences the pointers in the `msghdr`, it must do so only within
-/// the bounds indicated by the associated lengths in the `msghdr`.
-pub(crate) unsafe fn with_msghdr<R>(
- addr: &impl SocketAddrArg,
- iov: &[IoSlice<'_>],
- control: &mut SendAncillaryBuffer<'_, '_, '_>,
- f: impl FnOnce(&c::msghdr) -> R,
-) -> R {
- addr.with_sockaddr(|addr_ptr, addr_len| {
- let mut h = zero_msghdr();
- h.msg_name = addr_ptr as *mut _;
- h.msg_namelen = bitcast!(addr_len);
- h.msg_iov = iov.as_ptr() as _;
- h.msg_iovlen = msg_iov_len(iov.len());
- h.msg_control = control.as_control_ptr().cast();
- h.msg_controllen = msg_control_len(control.control_len());
- // Pass a reference to the `c::msghdr` instead of passing it by value
- // because it may contain pointers to temporary objects that won't
- // live beyond the call to `with_sockaddr`.
- f(&h)
- })
-}
-
-/// Create a zero-initialized message header struct value.
-#[cfg(all(unix, not(target_os = "redox")))]
-pub(crate) fn zero_msghdr() -> c::msghdr {
- // SAFETY: We can't initialize all the fields by value because on some
- // platforms the `msghdr` struct in the libc crate contains private padding
- // fields. But it is still a C type that's meant to be zero-initializable.
- unsafe { zeroed() }
-}
diff --git a/vendor/rustix/src/backend/libc/net/netdevice.rs b/vendor/rustix/src/backend/libc/net/netdevice.rs
deleted file mode 100644
index 887f768d..00000000
--- a/vendor/rustix/src/backend/libc/net/netdevice.rs
+++ /dev/null
@@ -1,55 +0,0 @@
-//! Wrappers for netdevice ioctls.
-
-#![allow(unsafe_code)]
-
-#[cfg(feature = "alloc")]
-use crate::alloc::string::String;
-use crate::backend::c;
-use crate::backend::io::syscalls::ioctl;
-use crate::fd::BorrowedFd;
-use crate::io;
-#[cfg(feature = "alloc")]
-use c::SIOCGIFNAME;
-use c::{__c_anonymous_ifr_ifru, c_char, ifreq, IFNAMSIZ, SIOCGIFINDEX};
-
-pub(crate) fn name_to_index(fd: BorrowedFd<'_>, if_name: &str) -> io::Result<u32> {
- let if_name_bytes = if_name.as_bytes();
- if if_name_bytes.len() >= IFNAMSIZ as usize {
- return Err(io::Errno::NODEV);
- }
-
- let mut ifreq = ifreq {
- ifr_name: [0; 16],
- ifr_ifru: __c_anonymous_ifr_ifru { ifru_ifindex: 0 },
- };
-
- let mut if_name_c_char_iter = if_name_bytes.iter().map(|byte| *byte as c_char);
- ifreq.ifr_name[..if_name_bytes.len()].fill_with(|| if_name_c_char_iter.next().unwrap());
-
- unsafe { ioctl(fd, SIOCGIFINDEX as _, &mut ifreq as *mut ifreq as _) }?;
- let index = unsafe { ifreq.ifr_ifru.ifru_ifindex };
- Ok(index as u32)
-}
-
-#[cfg(feature = "alloc")]
-pub(crate) fn index_to_name(fd: BorrowedFd<'_>, index: u32) -> io::Result<String> {
- let mut ifreq = ifreq {
- ifr_name: [0; 16],
- ifr_ifru: __c_anonymous_ifr_ifru {
- ifru_ifindex: index as _,
- },
- };
-
- unsafe { ioctl(fd, SIOCGIFNAME as _, &mut ifreq as *mut ifreq as _) }?;
-
- if let Some(nul_byte) = ifreq.ifr_name.iter().position(|char| *char == 0) {
- let name: String = ifreq.ifr_name[..nul_byte]
- .iter()
- .map(|v| *v as u8 as char)
- .collect();
-
- Ok(name)
- } else {
- Err(io::Errno::INVAL)
- }
-}
diff --git a/vendor/rustix/src/backend/libc/net/read_sockaddr.rs b/vendor/rustix/src/backend/libc/net/read_sockaddr.rs
deleted file mode 100644
index 5f8c48ec..00000000
--- a/vendor/rustix/src/backend/libc/net/read_sockaddr.rs
+++ /dev/null
@@ -1,264 +0,0 @@
-//! The BSD sockets API requires us to read the `sa_family` field before we can
-//! interpret the rest of a `sockaddr` produced by the kernel.
-
-#[cfg(unix)]
-use super::addr::SocketAddrUnix;
-use super::ext::{in6_addr_s6_addr, in_addr_s_addr, sockaddr_in6_sin6_scope_id};
-use crate::backend::c;
-#[cfg(not(windows))]
-use crate::ffi::CStr;
-use crate::io::Errno;
-use crate::net::addr::SocketAddrLen;
-#[cfg(linux_kernel)]
-use crate::net::netlink::SocketAddrNetlink;
-#[cfg(target_os = "linux")]
-use crate::net::xdp::{SocketAddrXdp, SocketAddrXdpFlags};
-use crate::net::{AddressFamily, Ipv4Addr, Ipv6Addr, SocketAddrAny, SocketAddrV4, SocketAddrV6};
-use core::mem::size_of;
-
-// This must match the header of `sockaddr`.
-#[repr(C)]
-pub(crate) struct sockaddr_header {
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "nto",
- target_os = "vita"
- ))]
- sa_len: u8,
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "nto",
- target_os = "vita"
- ))]
- sa_family: u8,
- #[cfg(not(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "nto",
- target_os = "vita"
- )))]
- sa_family: u16,
-}
-
-/// Read the `sa_family` field from a socket address returned from the OS.
-///
-/// # Safety
-///
-/// `storage` must point to a valid socket address returned from the OS.
-#[inline]
-pub(crate) unsafe fn read_sa_family(storage: *const c::sockaddr) -> u16 {
- // Assert that we know the layout of `sockaddr`.
- let _ = c::sockaddr {
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- ))]
- sa_len: 0_u8,
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- ))]
- sa_family: 0_u8,
- #[cfg(not(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- )))]
- sa_family: 0_u16,
- #[cfg(not(any(target_os = "haiku", target_os = "horizon")))]
- sa_data: [0; 14],
- #[cfg(target_os = "horizon")]
- sa_data: [0; 26],
- #[cfg(target_os = "haiku")]
- sa_data: [0; 30],
- };
-
- (*storage.cast::<sockaddr_header>()).sa_family.into()
-}
-
-/// Read the first byte of the `sun_path` field, assuming we have an `AF_UNIX`
-/// socket address.
-#[cfg(apple)]
-#[inline]
-unsafe fn read_sun_path0(storage: *const c::sockaddr) -> u8 {
- // In `read_sa_family` we assert that we know the layout of `sockaddr`.
- storage
- .cast::<u8>()
- .add(super::addr::offsetof_sun_path())
- .read()
-}
-
-/// Check if a socket address returned from the OS is considered non-empty.
-///
-/// # Safety
-///
-/// `storage` must point to a least an initialized `sockaddr_header`.
-#[inline]
-pub(crate) unsafe fn sockaddr_nonempty(storage: *const c::sockaddr, len: SocketAddrLen) -> bool {
- if len == 0 {
- return false;
- }
-
- assert!(len as usize >= size_of::<c::sa_family_t>());
- let family: c::c_int = read_sa_family(storage.cast::<c::sockaddr>()).into();
- if family == c::AF_UNSPEC {
- return false;
- }
-
- // On macOS, if we get an `AF_UNIX` with an empty path, treat it as an
- // absent address.
- #[cfg(apple)]
- if family == c::AF_UNIX && read_sun_path0(storage) == 0 {
- return false;
- }
-
- true
-}
-
-/// Set the `sa_family` field of a socket address to `AF_UNSPEC`, so that we
-/// can test for `AF_UNSPEC` to test whether it was stored to.
-///
-/// # Safety
-///
-/// `storage` must point to a least an initialized `sockaddr_header`.
-pub(crate) unsafe fn initialize_family_to_unspec(storage: *mut c::sockaddr) {
- (*storage.cast::<sockaddr_header>()).sa_family = c::AF_UNSPEC as _;
-}
-
-#[inline]
-pub(crate) fn read_sockaddr_v4(addr: &SocketAddrAny) -> Result<SocketAddrV4, Errno> {
- if addr.address_family() != AddressFamily::INET {
- return Err(Errno::AFNOSUPPORT);
- }
- assert!(addr.addr_len() as usize >= size_of::<c::sockaddr_in>());
- let decode = unsafe { &*addr.as_ptr().cast::<c::sockaddr_in>() };
- Ok(SocketAddrV4::new(
- Ipv4Addr::from(u32::from_be(in_addr_s_addr(decode.sin_addr))),
- u16::from_be(decode.sin_port),
- ))
-}
-
-#[inline]
-pub(crate) fn read_sockaddr_v6(addr: &SocketAddrAny) -> Result<SocketAddrV6, Errno> {
- if addr.address_family() != AddressFamily::INET6 {
- return Err(Errno::AFNOSUPPORT);
- }
- assert!(addr.addr_len() as usize >= size_of::<c::sockaddr_in6>());
- let decode = unsafe { &*addr.as_ptr().cast::<c::sockaddr_in6>() };
- Ok(SocketAddrV6::new(
- Ipv6Addr::from(in6_addr_s6_addr(decode.sin6_addr)),
- u16::from_be(decode.sin6_port),
- u32::from_be(decode.sin6_flowinfo),
- sockaddr_in6_sin6_scope_id(decode),
- ))
-}
-
-#[cfg(unix)]
-#[inline]
-pub(crate) fn read_sockaddr_unix(addr: &SocketAddrAny) -> Result<SocketAddrUnix, Errno> {
- if addr.address_family() != AddressFamily::UNIX {
- return Err(Errno::AFNOSUPPORT);
- }
-
- let offsetof_sun_path = super::addr::offsetof_sun_path();
- let len = addr.addr_len() as usize;
-
- assert!(len >= offsetof_sun_path);
-
- if len == offsetof_sun_path {
- SocketAddrUnix::new(&[][..])
- } else {
- let decode = unsafe { &*addr.as_ptr().cast::<c::sockaddr_un>() };
-
- // On Linux check for Linux's [abstract namespace].
- //
- // [abstract namespace]: https://man7.org/linux/man-pages/man7/unix.7.html
- #[cfg(linux_kernel)]
- if decode.sun_path[0] == 0 {
- let name = &decode.sun_path[1..len - offsetof_sun_path];
- let name = unsafe { core::mem::transmute::<&[c::c_char], &[u8]>(name) };
- return SocketAddrUnix::new_abstract_name(name);
- }
-
- // Otherwise we expect a NUL-terminated filesystem path.
-
- // Trim off unused bytes from the end of `path_bytes`.
- let path_bytes = if cfg!(any(solarish, target_os = "freebsd")) {
- // FreeBSD and illumos sometimes set the length to longer
- // than the length of the NUL-terminated string. Find the
- // NUL and truncate the string accordingly.
- &decode.sun_path[..decode
- .sun_path
- .iter()
- .position(|b| *b == 0)
- .ok_or(Errno::INVAL)?]
- } else {
- // Otherwise, use the provided length.
- let provided_len = len - 1 - offsetof_sun_path;
- if decode.sun_path[provided_len] != 0 {
- return Err(Errno::INVAL);
- }
- debug_assert_eq!(
- unsafe { CStr::from_ptr(decode.sun_path.as_ptr().cast()) }
- .to_bytes()
- .len(),
- provided_len
- );
- &decode.sun_path[..provided_len]
- };
-
- SocketAddrUnix::new(unsafe { core::mem::transmute::<&[c::c_char], &[u8]>(path_bytes) })
- }
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn read_sockaddr_xdp(addr: &SocketAddrAny) -> Result<SocketAddrXdp, Errno> {
- if addr.address_family() != AddressFamily::XDP {
- return Err(Errno::AFNOSUPPORT);
- }
- assert!(addr.addr_len() as usize >= size_of::<c::sockaddr_xdp>());
- let decode = unsafe { &*addr.as_ptr().cast::<c::sockaddr_xdp>() };
-
- // This ignores the `sxdp_shared_umem_fd` field, which is only expected to
- // be significant in `bind` calls, and not returned from `acceptfrom` or
- // `recvmsg` or similar.
- Ok(SocketAddrXdp::new(
- SocketAddrXdpFlags::from_bits_retain(decode.sxdp_flags),
- u32::from_be(decode.sxdp_ifindex),
- u32::from_be(decode.sxdp_queue_id),
- ))
-}
-
-#[cfg(linux_kernel)]
-#[inline]
-pub(crate) fn read_sockaddr_netlink(addr: &SocketAddrAny) -> Result<SocketAddrNetlink, Errno> {
- if addr.address_family() != AddressFamily::NETLINK {
- return Err(Errno::AFNOSUPPORT);
- }
- assert!(addr.addr_len() as usize >= size_of::<c::sockaddr_nl>());
- let decode = unsafe { &*addr.as_ptr().cast::<c::sockaddr_nl>() };
- Ok(SocketAddrNetlink::new(decode.nl_pid, decode.nl_groups))
-}
diff --git a/vendor/rustix/src/backend/libc/net/send_recv.rs b/vendor/rustix/src/backend/libc/net/send_recv.rs
deleted file mode 100644
index 4b67f2c5..00000000
--- a/vendor/rustix/src/backend/libc/net/send_recv.rs
+++ /dev/null
@@ -1,153 +0,0 @@
-use crate::backend::c;
-use bitflags::bitflags;
-
-bitflags! {
- /// `MSG_*` flags for use with [`send`], [`sendto`], and related
- /// functions.
- ///
- /// [`send`]: crate::net::send
- /// [`sendto`]: crate::net::sendto
- #[repr(transparent)]
- #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
- pub struct SendFlags: u32 {
- /// `MSG_CONFIRM`
- #[cfg(not(any(
- bsd,
- solarish,
- windows,
- target_os = "aix",
- target_os = "cygwin",
- target_os = "espidf",
- target_os = "nto",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "hurd",
- target_os = "redox",
- target_os = "vita",
- )))]
- const CONFIRM = bitcast!(c::MSG_CONFIRM);
- /// `MSG_DONTROUTE`
- const DONTROUTE = bitcast!(c::MSG_DONTROUTE);
- /// `MSG_DONTWAIT`
- #[cfg(not(windows))]
- const DONTWAIT = bitcast!(c::MSG_DONTWAIT);
- /// `MSG_EOR`
- #[cfg(not(any(windows, target_os = "horizon")))]
- const EOR = bitcast!(c::MSG_EOR);
- /// `MSG_MORE`
- #[cfg(not(any(
- bsd,
- solarish,
- windows,
- target_os = "aix",
- target_os = "cygwin",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
- )))]
- const MORE = bitcast!(c::MSG_MORE);
- #[cfg(not(any(apple, windows, target_os = "redox", target_os = "vita")))]
- /// `MSG_NOSIGNAL`
- const NOSIGNAL = bitcast!(c::MSG_NOSIGNAL);
- /// `MSG_OOB`
- const OOB = bitcast!(c::MSG_OOB);
-
- /// <https://docs.rs/bitflags/*/bitflags/#externally-defined-flags>
- const _ = !0;
- }
-}
-
-bitflags! {
- /// `MSG_*` flags for use with [`recv`], [`recvfrom`], and related
- /// functions.
- ///
- /// [`recv`]: crate::net::recv
- /// [`recvfrom`]: crate::net::recvfrom
- #[repr(transparent)]
- #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
- pub struct RecvFlags: u32 {
- /// `MSG_CMSG_CLOEXEC`
- #[cfg(not(any(
- apple,
- solarish,
- windows,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
- )))]
- const CMSG_CLOEXEC = bitcast!(c::MSG_CMSG_CLOEXEC);
- /// `MSG_DONTWAIT`
- #[cfg(not(windows))]
- const DONTWAIT = bitcast!(c::MSG_DONTWAIT);
- /// `MSG_ERRQUEUE`
- #[cfg(not(any(
- bsd,
- solarish,
- windows,
- target_os = "aix",
- target_os = "cygwin",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "hurd",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
- )))]
- const ERRQUEUE = bitcast!(c::MSG_ERRQUEUE);
- /// `MSG_OOB`
- const OOB = bitcast!(c::MSG_OOB);
- /// `MSG_PEEK`
- const PEEK = bitcast!(c::MSG_PEEK);
- /// `MSG_TRUNC`
- // Apple, illumos, and NetBSD have `MSG_TRUNC` but it's not documented
- // for use with `recv` and friends, and in practice appears to be
- // ignored.
- #[cfg(not(any(apple, solarish, target_os = "horizon", target_os = "netbsd")))]
- const TRUNC = bitcast!(c::MSG_TRUNC);
- /// `MSG_WAITALL`
- const WAITALL = bitcast!(c::MSG_WAITALL);
-
- /// <https://docs.rs/bitflags/*/bitflags/#externally-defined-flags>
- const _ = !0;
- }
-}
-
-bitflags! {
- /// `MSG_*` flags returned from [`recvmsg`], in the `flags` field of
- /// [`RecvMsg`]
- ///
- /// [`recvmsg`]: crate::net::recvmsg
- /// [`RecvMsg`]: crate::net::RecvMsg
- #[repr(transparent)]
- #[derive(Copy, Clone, Eq, PartialEq, Hash, Debug)]
- pub struct ReturnFlags: u32 {
- /// `MSG_OOB`
- const OOB = bitcast!(c::MSG_OOB);
- /// `MSG_EOR`
- #[cfg(not(any(windows, target_os = "horizon")))]
- const EOR = bitcast!(c::MSG_EOR);
- /// `MSG_TRUNC`
- #[cfg(not(target_os = "horizon"))]
- const TRUNC = bitcast!(c::MSG_TRUNC);
- /// `MSG_CTRUNC`
- #[cfg(not(target_os = "horizon"))]
- const CTRUNC = bitcast!(c::MSG_CTRUNC);
-
- /// `MSG_CMSG_CLOEXEC`
- #[cfg(linux_kernel)]
- const CMSG_CLOEXEC = bitcast!(c::MSG_CMSG_CLOEXEC);
- /// `MSG_ERRQUEUE`
- #[cfg(linux_kernel)]
- const ERRQUEUE = bitcast!(c::MSG_ERRQUEUE);
-
- /// <https://docs.rs/bitflags/*/bitflags/#externally-defined-flags>
- const _ = !0;
- }
-}
diff --git a/vendor/rustix/src/backend/libc/net/sockopt.rs b/vendor/rustix/src/backend/libc/net/sockopt.rs
deleted file mode 100644
index 132ebe75..00000000
--- a/vendor/rustix/src/backend/libc/net/sockopt.rs
+++ /dev/null
@@ -1,1339 +0,0 @@
-//! libc syscalls supporting `rustix::net::sockopt`.
-
-use super::ext::{in6_addr_new, in_addr_new};
-use crate::backend::c;
-use crate::backend::conv::{borrowed_fd, ret};
-use crate::fd::BorrowedFd;
-#[cfg(feature = "alloc")]
-#[cfg(any(
- linux_like,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "illumos"
-))]
-use crate::ffi::CStr;
-use crate::io;
-use crate::net::sockopt::Timeout;
-#[cfg(target_os = "linux")]
-use crate::net::xdp::{XdpMmapOffsets, XdpOptionsFlags, XdpRingOffset, XdpStatistics, XdpUmemReg};
-#[cfg(not(any(
- apple,
- windows,
- target_os = "aix",
- target_os = "cygwin",
- target_os = "dragonfly",
- target_os = "emscripten",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "netbsd",
- target_os = "nto",
- target_os = "vita",
-)))]
-use crate::net::AddressFamily;
-#[cfg(any(
- linux_kernel,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "openbsd",
- target_os = "redox",
- target_env = "newlib"
-))]
-use crate::net::Protocol;
-#[cfg(any(
- linux_kernel,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "openbsd",
- target_os = "redox",
- target_env = "newlib"
-))]
-use crate::net::RawProtocol;
-#[cfg(any(linux_kernel, target_os = "fuchsia"))]
-use crate::net::SocketAddrV4;
-use crate::net::{Ipv4Addr, Ipv6Addr, SocketType};
-#[cfg(linux_kernel)]
-use crate::net::{SocketAddrV6, UCred};
-use crate::utils::as_mut_ptr;
-#[cfg(feature = "alloc")]
-#[cfg(any(
- linux_like,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "illumos"
-))]
-use alloc::borrow::ToOwned as _;
-#[cfg(feature = "alloc")]
-#[cfg(any(
- linux_like,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "illumos"
-))]
-use alloc::string::String;
-#[cfg(apple)]
-use c::TCP_KEEPALIVE as TCP_KEEPIDLE;
-#[cfg(not(any(apple, target_os = "haiku", target_os = "nto", target_os = "openbsd")))]
-use c::TCP_KEEPIDLE;
-use core::mem::{size_of, MaybeUninit};
-use core::time::Duration;
-#[cfg(target_os = "linux")]
-use linux_raw_sys::xdp::{xdp_mmap_offsets, xdp_statistics, xdp_statistics_v1};
-#[cfg(windows)]
-use windows_sys::Win32::Foundation::BOOL;
-
-#[inline]
-fn getsockopt<T: Copy>(fd: BorrowedFd<'_>, level: i32, optname: i32) -> io::Result<T> {
- let mut optlen = size_of::<T>().try_into().unwrap();
- debug_assert!(
- optlen as usize >= size_of::<c::c_int>(),
- "Socket APIs don't ever use `bool` directly"
- );
-
- let mut value = MaybeUninit::<T>::zeroed();
- getsockopt_raw(fd, level, optname, &mut value, &mut optlen)?;
-
- // On Windows at least, `getsockopt` has been observed writing 1
- // byte on at least (`IPPROTO_TCP`, `TCP_NODELAY`), even though
- // Windows' documentation says that should write a 4-byte `BOOL`.
- // So, we initialize the memory to zeros above, and just assert
- // that `getsockopt` doesn't write too many bytes here.
- assert!(
- optlen as usize <= size_of::<T>(),
- "unexpected getsockopt size"
- );
-
- unsafe { Ok(value.assume_init()) }
-}
-
-#[inline]
-fn getsockopt_raw<T>(
- fd: BorrowedFd<'_>,
- level: i32,
- optname: i32,
- value: &mut MaybeUninit<T>,
- optlen: &mut c::socklen_t,
-) -> io::Result<()> {
- unsafe {
- ret(c::getsockopt(
- borrowed_fd(fd),
- level,
- optname,
- as_mut_ptr(value).cast(),
- optlen,
- ))
- }
-}
-
-#[inline]
-fn setsockopt<T: Copy>(fd: BorrowedFd<'_>, level: i32, optname: i32, value: T) -> io::Result<()> {
- let optlen = size_of::<T>().try_into().unwrap();
- debug_assert!(
- optlen as usize >= size_of::<c::c_int>(),
- "Socket APIs don't ever use `bool` directly"
- );
- setsockopt_raw(fd, level, optname, &value, optlen)
-}
-
-#[inline]
-fn setsockopt_raw<T>(
- fd: BorrowedFd<'_>,
- level: i32,
- optname: i32,
- ptr: *const T,
- optlen: c::socklen_t,
-) -> io::Result<()> {
- unsafe {
- ret(c::setsockopt(
- borrowed_fd(fd),
- level,
- optname,
- ptr.cast(),
- optlen,
- ))
- }
-}
-
-#[inline]
-pub(crate) fn socket_type(fd: BorrowedFd<'_>) -> io::Result<SocketType> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_TYPE)
-}
-
-#[inline]
-pub(crate) fn set_socket_reuseaddr(fd: BorrowedFd<'_>, reuseaddr: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_REUSEADDR, from_bool(reuseaddr))
-}
-
-#[inline]
-pub(crate) fn socket_reuseaddr(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_REUSEADDR).map(to_bool)
-}
-
-#[inline]
-pub(crate) fn set_socket_broadcast(fd: BorrowedFd<'_>, broadcast: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_BROADCAST, from_bool(broadcast))
-}
-
-#[inline]
-pub(crate) fn socket_broadcast(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_BROADCAST).map(to_bool)
-}
-
-#[inline]
-pub(crate) fn set_socket_linger(fd: BorrowedFd<'_>, linger: Option<Duration>) -> io::Result<()> {
- // Convert `linger` to seconds, rounding up.
- let l_linger = if let Some(linger) = linger {
- duration_to_secs(linger)?
- } else {
- 0
- };
- let linger = c::linger {
- l_onoff: linger.is_some().into(),
- l_linger,
- };
- setsockopt(fd, c::SOL_SOCKET, c::SO_LINGER, linger)
-}
-
-#[inline]
-pub(crate) fn socket_linger(fd: BorrowedFd<'_>) -> io::Result<Option<Duration>> {
- let linger: c::linger = getsockopt(fd, c::SOL_SOCKET, c::SO_LINGER)?;
- Ok((linger.l_onoff != 0).then(|| Duration::from_secs(linger.l_linger as u64)))
-}
-
-#[cfg(linux_kernel)]
-#[inline]
-pub(crate) fn set_socket_passcred(fd: BorrowedFd<'_>, passcred: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_PASSCRED, from_bool(passcred))
-}
-
-#[cfg(linux_kernel)]
-#[inline]
-pub(crate) fn socket_passcred(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_PASSCRED).map(to_bool)
-}
-
-#[inline]
-pub(crate) fn set_socket_timeout(
- fd: BorrowedFd<'_>,
- id: Timeout,
- timeout: Option<Duration>,
-) -> io::Result<()> {
- let optname = match id {
- Timeout::Recv => c::SO_RCVTIMEO,
- Timeout::Send => c::SO_SNDTIMEO,
- };
-
- #[cfg(not(windows))]
- let timeout = match timeout {
- Some(timeout) => {
- if timeout == Duration::ZERO {
- return Err(io::Errno::INVAL);
- }
-
- // Rust's musl libc bindings deprecated `time_t` while they
- // transition to 64-bit `time_t`. What we want here is just
- // “whatever type `timeval`'s `tv_sec` is”, so we're ok using
- // the deprecated type.
- #[allow(deprecated)]
- let tv_sec = timeout.as_secs().try_into().unwrap_or(c::time_t::MAX);
-
- // `subsec_micros` rounds down, so we use `subsec_nanos` and
- // manually round up.
- let mut timeout = c::timeval {
- tv_sec,
- tv_usec: ((timeout.subsec_nanos() + 999) / 1000) as _,
- };
- if timeout.tv_sec == 0 && timeout.tv_usec == 0 {
- timeout.tv_usec = 1;
- }
- timeout
- }
- None => c::timeval {
- tv_sec: 0,
- tv_usec: 0,
- },
- };
-
- #[cfg(windows)]
- let timeout: u32 = match timeout {
- Some(timeout) => {
- if timeout == Duration::ZERO {
- return Err(io::Errno::INVAL);
- }
-
- // `as_millis` rounds down, so we use `as_nanos` and
- // manually round up.
- let mut timeout: u32 = ((timeout.as_nanos() + 999_999) / 1_000_000)
- .try_into()
- .map_err(|_convert_err| io::Errno::INVAL)?;
- if timeout == 0 {
- timeout = 1;
- }
- timeout
- }
- None => 0,
- };
-
- setsockopt(fd, c::SOL_SOCKET, optname, timeout)
-}
-
-#[inline]
-pub(crate) fn socket_timeout(fd: BorrowedFd<'_>, id: Timeout) -> io::Result<Option<Duration>> {
- let optname = match id {
- Timeout::Recv => c::SO_RCVTIMEO,
- Timeout::Send => c::SO_SNDTIMEO,
- };
-
- #[cfg(not(windows))]
- {
- let timeout: c::timeval = getsockopt(fd, c::SOL_SOCKET, optname)?;
- if timeout.tv_sec == 0 && timeout.tv_usec == 0 {
- Ok(None)
- } else {
- Ok(Some(
- Duration::from_secs(timeout.tv_sec as u64)
- + Duration::from_micros(timeout.tv_usec as u64),
- ))
- }
- }
-
- #[cfg(windows)]
- {
- let timeout: u32 = getsockopt(fd, c::SOL_SOCKET, optname)?;
- if timeout == 0 {
- Ok(None)
- } else {
- Ok(Some(Duration::from_millis(timeout as u64)))
- }
- }
-}
-
-#[cfg(any(apple, freebsdlike, target_os = "netbsd"))]
-#[inline]
-pub(crate) fn socket_nosigpipe(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_NOSIGPIPE).map(to_bool)
-}
-
-#[cfg(any(apple, freebsdlike, target_os = "netbsd"))]
-#[inline]
-pub(crate) fn set_socket_nosigpipe(fd: BorrowedFd<'_>, val: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_NOSIGPIPE, from_bool(val))
-}
-
-#[inline]
-pub(crate) fn socket_error(fd: BorrowedFd<'_>) -> io::Result<Result<(), io::Errno>> {
- let err: c::c_int = getsockopt(fd, c::SOL_SOCKET, c::SO_ERROR)?;
- Ok(if err == 0 {
- Ok(())
- } else {
- Err(io::Errno::from_raw_os_error(err))
- })
-}
-
-#[inline]
-pub(crate) fn set_socket_keepalive(fd: BorrowedFd<'_>, keepalive: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_KEEPALIVE, from_bool(keepalive))
-}
-
-#[inline]
-pub(crate) fn socket_keepalive(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_KEEPALIVE).map(to_bool)
-}
-
-#[inline]
-pub(crate) fn set_socket_recv_buffer_size(fd: BorrowedFd<'_>, size: usize) -> io::Result<()> {
- let size: c::c_int = size.try_into().map_err(|_| io::Errno::INVAL)?;
- setsockopt(fd, c::SOL_SOCKET, c::SO_RCVBUF, size)
-}
-
-#[cfg(any(linux_kernel, target_os = "fuchsia", target_os = "redox"))]
-#[inline]
-pub(crate) fn set_socket_recv_buffer_size_force(fd: BorrowedFd<'_>, size: usize) -> io::Result<()> {
- let size: c::c_int = size.try_into().map_err(|_| io::Errno::INVAL)?;
- setsockopt(fd, c::SOL_SOCKET, c::SO_RCVBUFFORCE, size)
-}
-
-#[inline]
-pub(crate) fn socket_recv_buffer_size(fd: BorrowedFd<'_>) -> io::Result<usize> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_RCVBUF).map(|size: u32| size as usize)
-}
-
-#[inline]
-pub(crate) fn set_socket_send_buffer_size(fd: BorrowedFd<'_>, size: usize) -> io::Result<()> {
- let size: c::c_int = size.try_into().map_err(|_| io::Errno::INVAL)?;
- setsockopt(fd, c::SOL_SOCKET, c::SO_SNDBUF, size)
-}
-
-#[cfg(any(linux_kernel, target_os = "fuchsia", target_os = "redox"))]
-#[inline]
-pub(crate) fn set_socket_send_buffer_size_force(fd: BorrowedFd<'_>, size: usize) -> io::Result<()> {
- let size: c::c_int = size.try_into().map_err(|_| io::Errno::INVAL)?;
- setsockopt(fd, c::SOL_SOCKET, c::SO_SNDBUFFORCE, size)
-}
-
-#[inline]
-pub(crate) fn socket_send_buffer_size(fd: BorrowedFd<'_>) -> io::Result<usize> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_SNDBUF).map(|size: u32| size as usize)
-}
-
-#[inline]
-#[cfg(not(any(
- apple,
- windows,
- target_os = "aix",
- target_os = "cygwin",
- target_os = "dragonfly",
- target_os = "emscripten",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "hurd",
- target_os = "netbsd",
- target_os = "nto",
- target_os = "vita",
-)))]
-pub(crate) fn socket_domain(fd: BorrowedFd<'_>) -> io::Result<AddressFamily> {
- let domain: c::c_int = getsockopt(fd, c::SOL_SOCKET, c::SO_DOMAIN)?;
- Ok(AddressFamily(
- domain.try_into().map_err(|_| io::Errno::OPNOTSUPP)?,
- ))
-}
-
-#[inline]
-#[cfg(not(apple))] // Apple platforms declare the constant, but do not actually implement it.
-pub(crate) fn socket_acceptconn(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_ACCEPTCONN).map(to_bool)
-}
-
-#[inline]
-pub(crate) fn set_socket_oobinline(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_OOBINLINE, from_bool(value))
-}
-
-#[inline]
-pub(crate) fn socket_oobinline(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_OOBINLINE).map(to_bool)
-}
-
-#[cfg(not(any(solarish, windows, target_os = "cygwin")))]
-#[inline]
-pub(crate) fn set_socket_reuseport(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_REUSEPORT, from_bool(value))
-}
-
-#[cfg(not(any(solarish, windows, target_os = "cygwin")))]
-#[inline]
-pub(crate) fn socket_reuseport(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_REUSEPORT).map(to_bool)
-}
-
-#[cfg(target_os = "freebsd")]
-#[inline]
-pub(crate) fn set_socket_reuseport_lb(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_REUSEPORT_LB, from_bool(value))
-}
-
-#[cfg(target_os = "freebsd")]
-#[inline]
-pub(crate) fn socket_reuseport_lb(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_REUSEPORT_LB).map(to_bool)
-}
-
-#[cfg(any(
- linux_kernel,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "openbsd",
- target_os = "redox",
- target_env = "newlib"
-))]
-#[inline]
-pub(crate) fn socket_protocol(fd: BorrowedFd<'_>) -> io::Result<Option<Protocol>> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_PROTOCOL)
- .map(|raw| RawProtocol::new(raw).map(Protocol::from_raw))
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn socket_cookie(fd: BorrowedFd<'_>) -> io::Result<u64> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_COOKIE)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn socket_incoming_cpu(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_INCOMING_CPU)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn set_socket_incoming_cpu(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::SOL_SOCKET, c::SO_INCOMING_CPU, value)
-}
-
-#[inline]
-pub(crate) fn set_ip_ttl(fd: BorrowedFd<'_>, ttl: u32) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IP, c::IP_TTL, ttl)
-}
-
-#[inline]
-pub(crate) fn ip_ttl(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_IP, c::IP_TTL)
-}
-
-#[inline]
-pub(crate) fn set_ipv6_v6only(fd: BorrowedFd<'_>, only_v6: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IPV6, c::IPV6_V6ONLY, from_bool(only_v6))
-}
-
-#[inline]
-pub(crate) fn ipv6_v6only(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_V6ONLY).map(to_bool)
-}
-
-#[cfg(any(linux_kernel, target_os = "cygwin"))]
-#[inline]
-pub(crate) fn ip_mtu(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_IP, c::IP_MTU)
-}
-
-#[cfg(any(linux_kernel, target_os = "cygwin"))]
-#[inline]
-pub(crate) fn ipv6_mtu(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_MTU)
-}
-
-#[inline]
-pub(crate) fn set_ip_multicast_if(fd: BorrowedFd<'_>, value: &Ipv4Addr) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IP, c::IP_MULTICAST_IF, to_imr_addr(value))
-}
-
-#[inline]
-pub(crate) fn ip_multicast_if(fd: BorrowedFd<'_>) -> io::Result<Ipv4Addr> {
- getsockopt(fd, c::IPPROTO_IP, c::IP_MULTICAST_IF).map(from_in_addr)
-}
-
-#[cfg(any(
- apple,
- freebsdlike,
- linux_like,
- target_os = "fuchsia",
- target_os = "openbsd"
-))]
-#[inline]
-pub(crate) fn set_ip_multicast_if_with_ifindex(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv4Addr,
- address: &Ipv4Addr,
- ifindex: u32,
-) -> io::Result<()> {
- let mreqn = to_ip_mreqn(multiaddr, address, ifindex as i32);
- setsockopt(fd, c::IPPROTO_IP, c::IP_MULTICAST_IF, mreqn)
-}
-
-#[inline]
-pub(crate) fn set_ipv6_multicast_if(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IPV6, c::IPV6_MULTICAST_IF, value as c::c_int)
-}
-
-#[inline]
-pub(crate) fn ipv6_multicast_if(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_MULTICAST_IF)
-}
-
-#[inline]
-pub(crate) fn set_ip_multicast_loop(fd: BorrowedFd<'_>, multicast_loop: bool) -> io::Result<()> {
- setsockopt(
- fd,
- c::IPPROTO_IP,
- c::IP_MULTICAST_LOOP,
- from_bool(multicast_loop),
- )
-}
-
-#[inline]
-pub(crate) fn ip_multicast_loop(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_IP, c::IP_MULTICAST_LOOP).map(to_bool)
-}
-
-#[inline]
-pub(crate) fn set_ip_multicast_ttl(fd: BorrowedFd<'_>, multicast_ttl: u32) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IP, c::IP_MULTICAST_TTL, multicast_ttl)
-}
-
-#[inline]
-pub(crate) fn ip_multicast_ttl(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_IP, c::IP_MULTICAST_TTL)
-}
-
-#[inline]
-pub(crate) fn set_ipv6_multicast_loop(fd: BorrowedFd<'_>, multicast_loop: bool) -> io::Result<()> {
- setsockopt(
- fd,
- c::IPPROTO_IPV6,
- c::IPV6_MULTICAST_LOOP,
- from_bool(multicast_loop),
- )
-}
-
-#[inline]
-pub(crate) fn ipv6_multicast_loop(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_MULTICAST_LOOP).map(to_bool)
-}
-
-#[inline]
-pub(crate) fn set_ipv6_multicast_hops(fd: BorrowedFd<'_>, multicast_hops: u32) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IP, c::IPV6_MULTICAST_HOPS, multicast_hops)
-}
-
-#[inline]
-pub(crate) fn ipv6_multicast_hops(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_IP, c::IPV6_MULTICAST_HOPS)
-}
-
-#[inline]
-pub(crate) fn set_ip_add_membership(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv4Addr,
- interface: &Ipv4Addr,
-) -> io::Result<()> {
- let mreq = to_ip_mreq(multiaddr, interface);
- setsockopt(fd, c::IPPROTO_IP, c::IP_ADD_MEMBERSHIP, mreq)
-}
-
-#[cfg(any(
- apple,
- freebsdlike,
- linux_like,
- target_os = "fuchsia",
- target_os = "openbsd"
-))]
-#[inline]
-pub(crate) fn set_ip_add_membership_with_ifindex(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv4Addr,
- address: &Ipv4Addr,
- ifindex: u32,
-) -> io::Result<()> {
- let mreqn = to_ip_mreqn(multiaddr, address, ifindex as i32);
- setsockopt(fd, c::IPPROTO_IP, c::IP_ADD_MEMBERSHIP, mreqn)
-}
-
-#[cfg(any(apple, freebsdlike, linux_like, solarish, target_os = "aix"))]
-#[inline]
-pub(crate) fn set_ip_add_source_membership(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv4Addr,
- interface: &Ipv4Addr,
- sourceaddr: &Ipv4Addr,
-) -> io::Result<()> {
- let mreq_source = to_imr_source(multiaddr, interface, sourceaddr);
- setsockopt(fd, c::IPPROTO_IP, c::IP_ADD_SOURCE_MEMBERSHIP, mreq_source)
-}
-
-#[cfg(any(apple, freebsdlike, linux_like, solarish, target_os = "aix"))]
-#[inline]
-pub(crate) fn set_ip_drop_source_membership(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv4Addr,
- interface: &Ipv4Addr,
- sourceaddr: &Ipv4Addr,
-) -> io::Result<()> {
- let mreq_source = to_imr_source(multiaddr, interface, sourceaddr);
- setsockopt(fd, c::IPPROTO_IP, c::IP_DROP_SOURCE_MEMBERSHIP, mreq_source)
-}
-
-#[inline]
-pub(crate) fn set_ipv6_add_membership(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv6Addr,
- interface: u32,
-) -> io::Result<()> {
- #[cfg(not(any(
- bsd,
- solarish,
- target_os = "haiku",
- target_os = "l4re",
- target_os = "nto"
- )))]
- use c::IPV6_ADD_MEMBERSHIP;
- #[cfg(any(
- bsd,
- solarish,
- target_os = "haiku",
- target_os = "l4re",
- target_os = "nto"
- ))]
- use c::IPV6_JOIN_GROUP as IPV6_ADD_MEMBERSHIP;
-
- let mreq = to_ipv6mr(multiaddr, interface);
- setsockopt(fd, c::IPPROTO_IPV6, IPV6_ADD_MEMBERSHIP, mreq)
-}
-
-#[inline]
-pub(crate) fn set_ip_drop_membership(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv4Addr,
- interface: &Ipv4Addr,
-) -> io::Result<()> {
- let mreq = to_ip_mreq(multiaddr, interface);
- setsockopt(fd, c::IPPROTO_IP, c::IP_DROP_MEMBERSHIP, mreq)
-}
-
-#[cfg(any(
- apple,
- freebsdlike,
- linux_like,
- target_os = "fuchsia",
- target_os = "openbsd"
-))]
-#[inline]
-pub(crate) fn set_ip_drop_membership_with_ifindex(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv4Addr,
- address: &Ipv4Addr,
- ifindex: u32,
-) -> io::Result<()> {
- let mreqn = to_ip_mreqn(multiaddr, address, ifindex as i32);
- setsockopt(fd, c::IPPROTO_IP, c::IP_DROP_MEMBERSHIP, mreqn)
-}
-
-#[inline]
-pub(crate) fn set_ipv6_drop_membership(
- fd: BorrowedFd<'_>,
- multiaddr: &Ipv6Addr,
- interface: u32,
-) -> io::Result<()> {
- #[cfg(not(any(
- bsd,
- solarish,
- target_os = "haiku",
- target_os = "l4re",
- target_os = "nto"
- )))]
- use c::IPV6_DROP_MEMBERSHIP;
- #[cfg(any(
- bsd,
- solarish,
- target_os = "haiku",
- target_os = "l4re",
- target_os = "nto"
- ))]
- use c::IPV6_LEAVE_GROUP as IPV6_DROP_MEMBERSHIP;
-
- let mreq = to_ipv6mr(multiaddr, interface);
- setsockopt(fd, c::IPPROTO_IPV6, IPV6_DROP_MEMBERSHIP, mreq)
-}
-
-#[inline]
-pub(crate) fn ipv6_unicast_hops(fd: BorrowedFd<'_>) -> io::Result<u8> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_UNICAST_HOPS).map(|hops: c::c_int| hops as u8)
-}
-
-#[inline]
-pub(crate) fn set_ipv6_unicast_hops(fd: BorrowedFd<'_>, hops: Option<u8>) -> io::Result<()> {
- let hops = match hops {
- Some(hops) => hops as c::c_int,
- None => -1,
- };
- setsockopt(fd, c::IPPROTO_IPV6, c::IPV6_UNICAST_HOPS, hops)
-}
-
-#[cfg(any(
- bsd,
- linux_like,
- target_os = "aix",
- target_os = "fuchsia",
- target_os = "haiku",
- target_os = "nto",
- target_env = "newlib"
-))]
-#[inline]
-pub(crate) fn set_ip_tos(fd: BorrowedFd<'_>, value: u8) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IP, c::IP_TOS, i32::from(value))
-}
-
-#[cfg(any(
- bsd,
- linux_like,
- target_os = "aix",
- target_os = "fuchsia",
- target_os = "haiku",
- target_os = "nto",
- target_env = "newlib"
-))]
-#[inline]
-pub(crate) fn ip_tos(fd: BorrowedFd<'_>) -> io::Result<u8> {
- let value: i32 = getsockopt(fd, c::IPPROTO_IP, c::IP_TOS)?;
- Ok(value as u8)
-}
-
-#[cfg(any(
- apple,
- linux_like,
- target_os = "cygwin",
- target_os = "freebsd",
- target_os = "fuchsia",
-))]
-#[inline]
-pub(crate) fn set_ip_recvtos(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IP, c::IP_RECVTOS, from_bool(value))
-}
-
-#[cfg(any(
- apple,
- linux_like,
- target_os = "cygwin",
- target_os = "freebsd",
- target_os = "fuchsia",
-))]
-#[inline]
-pub(crate) fn ip_recvtos(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_IP, c::IP_RECVTOS).map(to_bool)
-}
-
-#[cfg(any(
- bsd,
- linux_like,
- target_os = "aix",
- target_os = "fuchsia",
- target_os = "nto"
-))]
-#[inline]
-pub(crate) fn set_ipv6_recvtclass(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IPV6, c::IPV6_RECVTCLASS, from_bool(value))
-}
-
-#[cfg(any(
- bsd,
- linux_like,
- target_os = "aix",
- target_os = "fuchsia",
- target_os = "nto"
-))]
-#[inline]
-pub(crate) fn ipv6_recvtclass(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_RECVTCLASS).map(to_bool)
-}
-
-#[cfg(any(linux_kernel, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn set_ip_freebind(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IP, c::IP_FREEBIND, from_bool(value))
-}
-
-#[cfg(any(linux_kernel, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn ip_freebind(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_IP, c::IP_FREEBIND).map(to_bool)
-}
-
-#[cfg(linux_kernel)]
-#[inline]
-pub(crate) fn set_ipv6_freebind(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IPV6, c::IPV6_FREEBIND, from_bool(value))
-}
-
-#[cfg(linux_kernel)]
-#[inline]
-pub(crate) fn ipv6_freebind(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_FREEBIND).map(to_bool)
-}
-
-#[cfg(any(linux_kernel, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn ip_original_dst(fd: BorrowedFd<'_>) -> io::Result<SocketAddrV4> {
- let level = c::IPPROTO_IP;
- let optname = c::SO_ORIGINAL_DST;
-
- let mut addr = crate::net::SocketAddrBuf::new();
- getsockopt_raw(fd, level, optname, &mut addr.storage, &mut addr.len)?;
- Ok(unsafe { addr.into_any() }.try_into().unwrap())
-}
-
-#[cfg(linux_kernel)]
-#[inline]
-pub(crate) fn ipv6_original_dst(fd: BorrowedFd<'_>) -> io::Result<SocketAddrV6> {
- let level = c::IPPROTO_IPV6;
- let optname = c::IP6T_SO_ORIGINAL_DST;
-
- let mut addr = crate::net::SocketAddrBuf::new();
- getsockopt_raw(fd, level, optname, &mut addr.storage, &mut addr.len)?;
- Ok(unsafe { addr.into_any() }.try_into().unwrap())
-}
-
-#[cfg(not(any(
- solarish,
- windows,
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "redox",
- target_os = "vita"
-)))]
-#[inline]
-pub(crate) fn set_ipv6_tclass(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_IPV6, c::IPV6_TCLASS, value)
-}
-
-#[cfg(not(any(
- solarish,
- windows,
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "redox",
- target_os = "vita"
-)))]
-#[inline]
-pub(crate) fn ipv6_tclass(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_IPV6, c::IPV6_TCLASS)
-}
-
-#[inline]
-pub(crate) fn set_tcp_nodelay(fd: BorrowedFd<'_>, nodelay: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_TCP, c::TCP_NODELAY, from_bool(nodelay))
-}
-
-#[inline]
-pub(crate) fn tcp_nodelay(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_TCP, c::TCP_NODELAY).map(to_bool)
-}
-
-#[inline]
-#[cfg(not(any(
- target_os = "haiku",
- target_os = "nto",
- target_os = "openbsd",
- target_os = "redox"
-)))]
-pub(crate) fn set_tcp_keepcnt(fd: BorrowedFd<'_>, count: u32) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_TCP, c::TCP_KEEPCNT, count)
-}
-
-#[inline]
-#[cfg(not(any(
- target_os = "haiku",
- target_os = "nto",
- target_os = "openbsd",
- target_os = "redox"
-)))]
-pub(crate) fn tcp_keepcnt(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_TCP, c::TCP_KEEPCNT)
-}
-
-#[inline]
-#[cfg(not(any(target_os = "haiku", target_os = "nto", target_os = "openbsd")))]
-pub(crate) fn set_tcp_keepidle(fd: BorrowedFd<'_>, duration: Duration) -> io::Result<()> {
- let secs: c::c_uint = duration_to_secs(duration)?;
- setsockopt(fd, c::IPPROTO_TCP, TCP_KEEPIDLE, secs)
-}
-
-#[inline]
-#[cfg(not(any(target_os = "haiku", target_os = "nto", target_os = "openbsd")))]
-pub(crate) fn tcp_keepidle(fd: BorrowedFd<'_>) -> io::Result<Duration> {
- let secs: c::c_uint = getsockopt(fd, c::IPPROTO_TCP, TCP_KEEPIDLE)?;
- Ok(Duration::from_secs(secs as u64))
-}
-
-#[inline]
-#[cfg(not(any(
- target_os = "haiku",
- target_os = "nto",
- target_os = "openbsd",
- target_os = "redox"
-)))]
-pub(crate) fn set_tcp_keepintvl(fd: BorrowedFd<'_>, duration: Duration) -> io::Result<()> {
- let secs: c::c_uint = duration_to_secs(duration)?;
- setsockopt(fd, c::IPPROTO_TCP, c::TCP_KEEPINTVL, secs)
-}
-
-#[inline]
-#[cfg(not(any(
- target_os = "haiku",
- target_os = "nto",
- target_os = "openbsd",
- target_os = "redox"
-)))]
-pub(crate) fn tcp_keepintvl(fd: BorrowedFd<'_>) -> io::Result<Duration> {
- let secs: c::c_uint = getsockopt(fd, c::IPPROTO_TCP, c::TCP_KEEPINTVL)?;
- Ok(Duration::from_secs(secs as u64))
-}
-
-#[inline]
-#[cfg(any(linux_like, target_os = "fuchsia"))]
-pub(crate) fn set_tcp_user_timeout(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_TCP, c::TCP_USER_TIMEOUT, value)
-}
-
-#[inline]
-#[cfg(any(linux_like, target_os = "fuchsia"))]
-pub(crate) fn tcp_user_timeout(fd: BorrowedFd<'_>) -> io::Result<u32> {
- getsockopt(fd, c::IPPROTO_TCP, c::TCP_USER_TIMEOUT)
-}
-
-#[cfg(any(linux_like, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn set_tcp_quickack(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_TCP, c::TCP_QUICKACK, from_bool(value))
-}
-
-#[cfg(any(linux_like, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn tcp_quickack(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_TCP, c::TCP_QUICKACK).map(to_bool)
-}
-
-#[cfg(any(
- linux_like,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "illumos"
-))]
-#[inline]
-pub(crate) fn set_tcp_congestion(fd: BorrowedFd<'_>, value: &str) -> io::Result<()> {
- let level = c::IPPROTO_TCP;
- let optname = c::TCP_CONGESTION;
- let optlen = value.len().try_into().unwrap();
- setsockopt_raw(fd, level, optname, value.as_ptr(), optlen)
-}
-
-#[cfg(feature = "alloc")]
-#[cfg(any(
- linux_like,
- target_os = "freebsd",
- target_os = "fuchsia",
- target_os = "illumos"
-))]
-#[inline]
-pub(crate) fn tcp_congestion(fd: BorrowedFd<'_>) -> io::Result<String> {
- const OPTLEN: c::socklen_t = 16;
-
- let level = c::IPPROTO_TCP;
- let optname = c::TCP_CONGESTION;
- let mut value = MaybeUninit::<[MaybeUninit<u8>; OPTLEN as usize]>::uninit();
- let mut optlen = OPTLEN;
- getsockopt_raw(fd, level, optname, &mut value, &mut optlen)?;
- unsafe {
- let value = value.assume_init();
- let slice: &[u8] = core::mem::transmute(&value[..optlen as usize]);
- assert!(slice.contains(&b'\0'));
- Ok(
- core::str::from_utf8(CStr::from_ptr(slice.as_ptr().cast()).to_bytes())
- .unwrap()
- .to_owned(),
- )
- }
-}
-
-#[cfg(any(linux_like, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn set_tcp_thin_linear_timeouts(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(
- fd,
- c::IPPROTO_TCP,
- c::TCP_THIN_LINEAR_TIMEOUTS,
- from_bool(value),
- )
-}
-
-#[cfg(any(linux_like, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn tcp_thin_linear_timeouts(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_TCP, c::TCP_THIN_LINEAR_TIMEOUTS).map(to_bool)
-}
-
-#[cfg(any(linux_like, solarish, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn set_tcp_cork(fd: BorrowedFd<'_>, value: bool) -> io::Result<()> {
- setsockopt(fd, c::IPPROTO_TCP, c::TCP_CORK, from_bool(value))
-}
-
-#[cfg(any(linux_like, solarish, target_os = "fuchsia"))]
-#[inline]
-pub(crate) fn tcp_cork(fd: BorrowedFd<'_>) -> io::Result<bool> {
- getsockopt(fd, c::IPPROTO_TCP, c::TCP_CORK).map(to_bool)
-}
-
-#[cfg(linux_kernel)]
-#[inline]
-pub(crate) fn socket_peercred(fd: BorrowedFd<'_>) -> io::Result<UCred> {
- getsockopt(fd, c::SOL_SOCKET, c::SO_PEERCRED)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn set_xdp_umem_reg(fd: BorrowedFd<'_>, value: XdpUmemReg) -> io::Result<()> {
- setsockopt(fd, c::SOL_XDP, c::XDP_UMEM_REG, value)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn set_xdp_umem_fill_ring_size(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::SOL_XDP, c::XDP_UMEM_FILL_RING, value)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn set_xdp_umem_completion_ring_size(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::SOL_XDP, c::XDP_UMEM_COMPLETION_RING, value)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn set_xdp_tx_ring_size(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::SOL_XDP, c::XDP_TX_RING, value)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn set_xdp_rx_ring_size(fd: BorrowedFd<'_>, value: u32) -> io::Result<()> {
- setsockopt(fd, c::SOL_XDP, c::XDP_RX_RING, value)
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn xdp_mmap_offsets(fd: BorrowedFd<'_>) -> io::Result<XdpMmapOffsets> {
- // The kernel will write `xdp_mmap_offsets` or `xdp_mmap_offsets_v1` to the
- // supplied pointer, depending on the kernel version. Both structs only
- // contain u64 values. By using the larger of both as the parameter, we can
- // shuffle the values to the non-v1 version returned by
- // `get_xdp_mmap_offsets` while keeping the return type unaffected by the
- // kernel version. This works because C will layout all struct members one
- // after the other.
-
- let mut optlen = size_of::<xdp_mmap_offsets>().try_into().unwrap();
- debug_assert!(
- optlen as usize >= size_of::<c::c_int>(),
- "Socket APIs don't ever use `bool` directly"
- );
- let mut value = MaybeUninit::<xdp_mmap_offsets>::zeroed();
- getsockopt_raw(fd, c::SOL_XDP, c::XDP_MMAP_OFFSETS, &mut value, &mut optlen)?;
-
- if optlen as usize == size_of::<c::xdp_mmap_offsets_v1>() {
- // SAFETY: All members of xdp_mmap_offsets are `u64` and thus are
- // correctly initialized by `MaybeUninit::<xdp_statistics>::zeroed()`.
- let xpd_mmap_offsets = unsafe { value.assume_init() };
- Ok(XdpMmapOffsets {
- rx: XdpRingOffset {
- producer: xpd_mmap_offsets.rx.producer,
- consumer: xpd_mmap_offsets.rx.consumer,
- desc: xpd_mmap_offsets.rx.desc,
- flags: None,
- },
- tx: XdpRingOffset {
- producer: xpd_mmap_offsets.rx.flags,
- consumer: xpd_mmap_offsets.tx.producer,
- desc: xpd_mmap_offsets.tx.consumer,
- flags: None,
- },
- fr: XdpRingOffset {
- producer: xpd_mmap_offsets.tx.desc,
- consumer: xpd_mmap_offsets.tx.flags,
- desc: xpd_mmap_offsets.fr.producer,
- flags: None,
- },
- cr: XdpRingOffset {
- producer: xpd_mmap_offsets.fr.consumer,
- consumer: xpd_mmap_offsets.fr.desc,
- desc: xpd_mmap_offsets.fr.flags,
- flags: None,
- },
- })
- } else {
- assert_eq!(
- optlen as usize,
- size_of::<xdp_mmap_offsets>(),
- "unexpected getsockopt size"
- );
- // SAFETY: All members of xdp_mmap_offsets are `u64` and thus are
- // correctly initialized by `MaybeUninit::<xdp_statistics>::zeroed()`
- let xpd_mmap_offsets = unsafe { value.assume_init() };
- Ok(XdpMmapOffsets {
- rx: XdpRingOffset {
- producer: xpd_mmap_offsets.rx.producer,
- consumer: xpd_mmap_offsets.rx.consumer,
- desc: xpd_mmap_offsets.rx.desc,
- flags: Some(xpd_mmap_offsets.rx.flags),
- },
- tx: XdpRingOffset {
- producer: xpd_mmap_offsets.tx.producer,
- consumer: xpd_mmap_offsets.tx.consumer,
- desc: xpd_mmap_offsets.tx.desc,
- flags: Some(xpd_mmap_offsets.tx.flags),
- },
- fr: XdpRingOffset {
- producer: xpd_mmap_offsets.fr.producer,
- consumer: xpd_mmap_offsets.fr.consumer,
- desc: xpd_mmap_offsets.fr.desc,
- flags: Some(xpd_mmap_offsets.fr.flags),
- },
- cr: XdpRingOffset {
- producer: xpd_mmap_offsets.cr.producer,
- consumer: xpd_mmap_offsets.cr.consumer,
- desc: xpd_mmap_offsets.cr.desc,
- flags: Some(xpd_mmap_offsets.cr.flags),
- },
- })
- }
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn xdp_statistics(fd: BorrowedFd<'_>) -> io::Result<XdpStatistics> {
- let mut optlen = size_of::<xdp_statistics>().try_into().unwrap();
- debug_assert!(
- optlen as usize >= size_of::<c::c_int>(),
- "Socket APIs don't ever use `bool` directly"
- );
- let mut value = MaybeUninit::<xdp_statistics>::zeroed();
- getsockopt_raw(fd, c::SOL_XDP, c::XDP_STATISTICS, &mut value, &mut optlen)?;
-
- if optlen as usize == size_of::<xdp_statistics_v1>() {
- // SAFETY: All members of xdp_statistics are `u64` and thus are
- // correctly initialized by `MaybeUninit::<xdp_statistics>::zeroed()`.
- let xdp_statistics = unsafe { value.assume_init() };
- Ok(XdpStatistics {
- rx_dropped: xdp_statistics.rx_dropped,
- rx_invalid_descs: xdp_statistics.rx_dropped,
- tx_invalid_descs: xdp_statistics.rx_dropped,
- rx_ring_full: None,
- rx_fill_ring_empty_descs: None,
- tx_ring_empty_descs: None,
- })
- } else {
- assert_eq!(
- optlen as usize,
- size_of::<xdp_statistics>(),
- "unexpected getsockopt size"
- );
- // SAFETY: All members of xdp_statistics are `u64` and thus are
- // correctly initialized by `MaybeUninit::<xdp_statistics>::zeroed()`.
- let xdp_statistics = unsafe { value.assume_init() };
- Ok(XdpStatistics {
- rx_dropped: xdp_statistics.rx_dropped,
- rx_invalid_descs: xdp_statistics.rx_invalid_descs,
- tx_invalid_descs: xdp_statistics.tx_invalid_descs,
- rx_ring_full: Some(xdp_statistics.rx_ring_full),
- rx_fill_ring_empty_descs: Some(xdp_statistics.rx_fill_ring_empty_descs),
- tx_ring_empty_descs: Some(xdp_statistics.tx_ring_empty_descs),
- })
- }
-}
-
-#[cfg(target_os = "linux")]
-#[inline]
-pub(crate) fn xdp_options(fd: BorrowedFd<'_>) -> io::Result<XdpOptionsFlags> {
- getsockopt(fd, c::SOL_XDP, c::XDP_OPTIONS)
-}
-
-#[inline]
-fn to_ip_mreq(multiaddr: &Ipv4Addr, interface: &Ipv4Addr) -> c::ip_mreq {
- c::ip_mreq {
- imr_multiaddr: to_imr_addr(multiaddr),
- imr_interface: to_imr_addr(interface),
- }
-}
-
-#[cfg(not(windows))]
-#[inline]
-fn from_in_addr(in_addr: c::in_addr) -> Ipv4Addr {
- Ipv4Addr::from(in_addr.s_addr.to_ne_bytes())
-}
-
-#[cfg(windows)]
-fn from_in_addr(in_addr: c::in_addr) -> Ipv4Addr {
- Ipv4Addr::from(unsafe { in_addr.S_un.S_addr.to_ne_bytes() })
-}
-
-#[cfg(any(
- apple,
- freebsdlike,
- linux_like,
- target_os = "fuchsia",
- target_os = "openbsd"
-))]
-#[inline]
-fn to_ip_mreqn(multiaddr: &Ipv4Addr, address: &Ipv4Addr, ifindex: i32) -> c::ip_mreqn {
- c::ip_mreqn {
- imr_multiaddr: to_imr_addr(multiaddr),
- imr_address: to_imr_addr(address),
- imr_ifindex: ifindex,
- }
-}
-
-#[cfg(any(apple, freebsdlike, linux_like, solarish, target_os = "aix"))]
-#[inline]
-fn to_imr_source(
- multiaddr: &Ipv4Addr,
- interface: &Ipv4Addr,
- sourceaddr: &Ipv4Addr,
-) -> c::ip_mreq_source {
- c::ip_mreq_source {
- imr_multiaddr: to_imr_addr(multiaddr),
- imr_interface: to_imr_addr(interface),
- imr_sourceaddr: to_imr_addr(sourceaddr),
- }
-}
-
-#[inline]
-fn to_imr_addr(addr: &Ipv4Addr) -> c::in_addr {
- in_addr_new(u32::from_ne_bytes(addr.octets()))
-}
-
-#[inline]
-fn to_ipv6mr(multiaddr: &Ipv6Addr, interface: u32) -> c::ipv6_mreq {
- c::ipv6_mreq {
- ipv6mr_multiaddr: to_ipv6mr_multiaddr(multiaddr),
- ipv6mr_interface: to_ipv6mr_interface(interface),
- }
-}
-
-#[inline]
-fn to_ipv6mr_multiaddr(multiaddr: &Ipv6Addr) -> c::in6_addr {
- in6_addr_new(multiaddr.octets())
-}
-
-#[cfg(target_os = "android")]
-#[inline]
-fn to_ipv6mr_interface(interface: u32) -> c::c_int {
- interface as c::c_int
-}
-
-#[cfg(not(target_os = "android"))]
-#[inline]
-fn to_ipv6mr_interface(interface: u32) -> c::c_uint {
- interface as c::c_uint
-}
-
-// `getsockopt` and `setsockopt` represent boolean values as integers.
-#[cfg(not(windows))]
-type RawSocketBool = c::c_int;
-#[cfg(windows)]
-type RawSocketBool = BOOL;
-
-// Wrap `RawSocketBool` in a newtype to discourage misuse.
-#[repr(transparent)]
-#[derive(Copy, Clone)]
-struct SocketBool(RawSocketBool);
-
-// Convert from a `bool` to a `SocketBool`.
-#[inline]
-fn from_bool(value: bool) -> SocketBool {
- SocketBool(value.into())
-}
-
-// Convert from a `SocketBool` to a `bool`.
-#[inline]
-fn to_bool(value: SocketBool) -> bool {
- value.0 != 0
-}
-
-/// Convert to seconds, rounding up if necessary.
-#[inline]
-fn duration_to_secs<T: TryFrom<u64>>(duration: Duration) -> io::Result<T> {
- let mut secs = duration.as_secs();
- if duration.subsec_nanos() != 0 {
- secs = secs.checked_add(1).ok_or(io::Errno::INVAL)?;
- }
- T::try_from(secs).map_err(|_e| io::Errno::INVAL)
-}
diff --git a/vendor/rustix/src/backend/libc/net/syscalls.rs b/vendor/rustix/src/backend/libc/net/syscalls.rs
deleted file mode 100644
index aafea002..00000000
--- a/vendor/rustix/src/backend/libc/net/syscalls.rs
+++ /dev/null
@@ -1,438 +0,0 @@
-//! libc syscalls supporting `rustix::net`.
-
-use super::read_sockaddr::initialize_family_to_unspec;
-use super::send_recv::{RecvFlags, SendFlags};
-use crate::backend::c;
-#[cfg(target_os = "linux")]
-use crate::backend::conv::ret_u32;
-use crate::backend::conv::{borrowed_fd, ret, ret_owned_fd, ret_send_recv, send_recv_len};
-use crate::fd::{BorrowedFd, OwnedFd};
-use crate::io;
-use crate::net::addr::SocketAddrArg;
-#[cfg(target_os = "linux")]
-use crate::net::MMsgHdr;
-use crate::net::{
- AddressFamily, Protocol, Shutdown, SocketAddrAny, SocketAddrBuf, SocketFlags, SocketType,
-};
-use crate::utils::as_ptr;
-use core::mem::{size_of, MaybeUninit};
-use core::ptr::null_mut;
-#[cfg(not(any(
- windows,
- target_os = "espidf",
- target_os = "horizon",
- target_os = "redox",
- target_os = "vita"
-)))]
-use {
- super::msghdr::{noaddr_msghdr, with_msghdr, with_recv_msghdr},
- super::send_recv::ReturnFlags,
- crate::io::{IoSlice, IoSliceMut},
- crate::net::{RecvAncillaryBuffer, RecvMsg, SendAncillaryBuffer},
-};
-
-pub(crate) unsafe fn recv(
- fd: BorrowedFd<'_>,
- buf: (*mut u8, usize),
- flags: RecvFlags,
-) -> io::Result<usize> {
- ret_send_recv(c::recv(
- borrowed_fd(fd),
- buf.0.cast(),
- send_recv_len(buf.1),
- bitflags_bits!(flags),
- ))
-}
-
-pub(crate) fn send(fd: BorrowedFd<'_>, buf: &[u8], flags: SendFlags) -> io::Result<usize> {
- unsafe {
- ret_send_recv(c::send(
- borrowed_fd(fd),
- buf.as_ptr().cast(),
- send_recv_len(buf.len()),
- bitflags_bits!(flags),
- ))
- }
-}
-
-pub(crate) unsafe fn recvfrom(
- fd: BorrowedFd<'_>,
- buf: (*mut u8, usize),
- flags: RecvFlags,
-) -> io::Result<(usize, Option<SocketAddrAny>)> {
- let mut addr = SocketAddrBuf::new();
-
- // `recvfrom` does not write to the storage if the socket is
- // connection-oriented sockets, so we initialize the family field to
- // `AF_UNSPEC` so that we can detect this case.
- initialize_family_to_unspec(addr.storage.as_mut_ptr().cast::<c::sockaddr>());
-
- let nread = ret_send_recv(c::recvfrom(
- borrowed_fd(fd),
- buf.0.cast(),
- send_recv_len(buf.1),
- bitflags_bits!(flags),
- addr.storage.as_mut_ptr().cast::<c::sockaddr>(),
- &mut addr.len,
- ))?;
-
- Ok((nread, addr.into_any_option()))
-}
-
-pub(crate) fn sendto(
- fd: BorrowedFd<'_>,
- buf: &[u8],
- flags: SendFlags,
- addr: &impl SocketAddrArg,
-) -> io::Result<usize> {
- unsafe {
- addr.with_sockaddr(|addr_ptr, addr_len| {
- ret_send_recv(c::sendto(
- borrowed_fd(fd),
- buf.as_ptr().cast(),
- send_recv_len(buf.len()),
- bitflags_bits!(flags),
- addr_ptr.cast(),
- bitcast!(addr_len),
- ))
- })
- }
-}
-
-pub(crate) fn socket(
- domain: AddressFamily,
- type_: SocketType,
- protocol: Option<Protocol>,
-) -> io::Result<OwnedFd> {
- let raw_protocol = match protocol {
- Some(p) => p.0.get(),
- None => 0,
- };
- unsafe {
- ret_owned_fd(c::socket(
- domain.0 as c::c_int,
- type_.0 as c::c_int,
- raw_protocol as c::c_int,
- ))
- }
-}
-
-pub(crate) fn socket_with(
- domain: AddressFamily,
- type_: SocketType,
- flags: SocketFlags,
- protocol: Option<Protocol>,
-) -> io::Result<OwnedFd> {
- let raw_protocol = match protocol {
- Some(p) => p.0.get(),
- None => 0,
- };
- unsafe {
- ret_owned_fd(c::socket(
- domain.0 as c::c_int,
- (type_.0 | flags.bits()) as c::c_int,
- raw_protocol as c::c_int,
- ))
- }
-}
-
-pub(crate) fn bind(sockfd: BorrowedFd<'_>, addr: &impl SocketAddrArg) -> io::Result<()> {
- unsafe {
- addr.with_sockaddr(|addr_ptr, addr_len| {
- ret(c::bind(
- borrowed_fd(sockfd),
- addr_ptr.cast(),
- bitcast!(addr_len),
- ))
- })
- }
-}
-
-pub(crate) fn connect(sockfd: BorrowedFd<'_>, addr: &impl SocketAddrArg) -> io::Result<()> {
- unsafe {
- addr.with_sockaddr(|addr_ptr, addr_len| {
- ret(c::connect(
- borrowed_fd(sockfd),
- addr_ptr.cast(),
- bitcast!(addr_len),
- ))
- })
- }
-}
-
-pub(crate) fn connect_unspec(sockfd: BorrowedFd<'_>) -> io::Result<()> {
- debug_assert_eq!(c::AF_UNSPEC, 0);
- let addr = MaybeUninit::<c::sockaddr_storage>::zeroed();
- unsafe {
- ret(c::connect(
- borrowed_fd(sockfd),
- as_ptr(&addr).cast(),
- size_of::<c::sockaddr_storage>() as c::socklen_t,
- ))
- }
-}
-
-pub(crate) fn listen(sockfd: BorrowedFd<'_>, backlog: c::c_int) -> io::Result<()> {
- unsafe { ret(c::listen(borrowed_fd(sockfd), backlog)) }
-}
-
-pub(crate) fn accept(sockfd: BorrowedFd<'_>) -> io::Result<OwnedFd> {
- unsafe {
- let owned_fd = ret_owned_fd(c::accept(borrowed_fd(sockfd), null_mut(), null_mut()))?;
- Ok(owned_fd)
- }
-}
-
-#[cfg(not(any(
- windows,
- target_os = "espidf",
- target_os = "horizon",
- target_os = "redox",
- target_os = "vita"
-)))]
-pub(crate) fn recvmsg(
- sockfd: BorrowedFd<'_>,
- iov: &mut [IoSliceMut<'_>],
- control: &mut RecvAncillaryBuffer<'_>,
- msg_flags: RecvFlags,
-) -> io::Result<RecvMsg> {
- let mut addr = SocketAddrBuf::new();
-
- // SAFETY: This passes the `msghdr` reference to the OS which reads the
- // buffers only within the designated bounds.
- let (bytes, flags) = unsafe {
- with_recv_msghdr(&mut addr, iov, control, |msghdr| {
- let bytes = ret_send_recv(c::recvmsg(
- borrowed_fd(sockfd),
- msghdr,
- bitflags_bits!(msg_flags),
- ))?;
- Ok((bytes, msghdr.msg_flags))
- })?
- };
-
- Ok(RecvMsg {
- bytes,
- address: unsafe { addr.into_any_option() },
- flags: ReturnFlags::from_bits_retain(bitcast!(flags)),
- })
-}
-
-#[cfg(not(any(
- windows,
- target_os = "espidf",
- target_os = "horizon",
- target_os = "redox",
- target_os = "vita"
-)))]
-pub(crate) fn sendmsg(
- sockfd: BorrowedFd<'_>,
- iov: &[IoSlice<'_>],
- control: &mut SendAncillaryBuffer<'_, '_, '_>,
- msg_flags: SendFlags,
-) -> io::Result<usize> {
- let msghdr = noaddr_msghdr(iov, control);
- unsafe {
- ret_send_recv(c::sendmsg(
- borrowed_fd(sockfd),
- &msghdr,
- bitflags_bits!(msg_flags),
- ))
- }
-}
-
-#[cfg(not(any(
- windows,
- target_os = "espidf",
- target_os = "horizon",
- target_os = "redox",
- target_os = "vita"
-)))]
-pub(crate) fn sendmsg_addr(
- sockfd: BorrowedFd<'_>,
- addr: &impl SocketAddrArg,
- iov: &[IoSlice<'_>],
- control: &mut SendAncillaryBuffer<'_, '_, '_>,
- msg_flags: SendFlags,
-) -> io::Result<usize> {
- // SAFETY: This passes the `msghdr` reference to the OS which reads the
- // buffers only within the designated bounds.
- unsafe {
- with_msghdr(addr, iov, control, |msghdr| {
- ret_send_recv(c::sendmsg(
- borrowed_fd(sockfd),
- msghdr,
- bitflags_bits!(msg_flags),
- ))
- })
- }
-}
-
-#[cfg(target_os = "linux")]
-pub(crate) fn sendmmsg(
- sockfd: BorrowedFd<'_>,
- msgs: &mut [MMsgHdr<'_>],
- flags: SendFlags,
-) -> io::Result<usize> {
- unsafe {
- ret_u32(c::sendmmsg(
- borrowed_fd(sockfd),
- msgs.as_mut_ptr() as _,
- msgs.len().try_into().unwrap_or(c::c_uint::MAX),
- bitflags_bits!(flags),
- ))
- .map(|ret| ret as usize)
- }
-}
-
-#[cfg(not(any(
- apple,
- windows,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
-)))]
-pub(crate) fn accept_with(sockfd: BorrowedFd<'_>, flags: SocketFlags) -> io::Result<OwnedFd> {
- unsafe {
- let owned_fd = ret_owned_fd(c::accept4(
- borrowed_fd(sockfd),
- null_mut(),
- null_mut(),
- flags.bits() as c::c_int,
- ))?;
- Ok(owned_fd)
- }
-}
-
-pub(crate) fn acceptfrom(sockfd: BorrowedFd<'_>) -> io::Result<(OwnedFd, Option<SocketAddrAny>)> {
- unsafe {
- let mut addr = SocketAddrBuf::new();
- let owned_fd = ret_owned_fd(c::accept(
- borrowed_fd(sockfd),
- addr.storage.as_mut_ptr().cast::<c::sockaddr>(),
- &mut addr.len,
- ))?;
- Ok((owned_fd, addr.into_any_option()))
- }
-}
-
-#[cfg(not(any(
- apple,
- windows,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
-)))]
-pub(crate) fn acceptfrom_with(
- sockfd: BorrowedFd<'_>,
- flags: SocketFlags,
-) -> io::Result<(OwnedFd, Option<SocketAddrAny>)> {
- unsafe {
- let mut addr = SocketAddrBuf::new();
- let owned_fd = ret_owned_fd(c::accept4(
- borrowed_fd(sockfd),
- addr.storage.as_mut_ptr().cast::<c::sockaddr>(),
- &mut addr.len,
- flags.bits() as c::c_int,
- ))?;
- Ok((owned_fd, addr.into_any_option()))
- }
-}
-
-/// Darwin lacks `accept4`, but does have `accept`. We define `SocketFlags` to
-/// have no flags, so we can discard it here.
-#[cfg(any(
- apple,
- windows,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
-))]
-pub(crate) fn accept_with(sockfd: BorrowedFd<'_>, _flags: SocketFlags) -> io::Result<OwnedFd> {
- accept(sockfd)
-}
-
-/// Darwin lacks `accept4`, but does have `accept`. We define `SocketFlags` to
-/// have no flags, so we can discard it here.
-#[cfg(any(
- apple,
- windows,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "horizon",
- target_os = "nto",
- target_os = "redox",
- target_os = "vita",
-))]
-pub(crate) fn acceptfrom_with(
- sockfd: BorrowedFd<'_>,
- _flags: SocketFlags,
-) -> io::Result<(OwnedFd, Option<SocketAddrAny>)> {
- acceptfrom(sockfd)
-}
-
-pub(crate) fn shutdown(sockfd: BorrowedFd<'_>, how: Shutdown) -> io::Result<()> {
- unsafe { ret(c::shutdown(borrowed_fd(sockfd), how as c::c_int)) }
-}
-
-pub(crate) fn getsockname(sockfd: BorrowedFd<'_>) -> io::Result<SocketAddrAny> {
- unsafe {
- let mut addr = SocketAddrBuf::new();
- ret(c::getsockname(
- borrowed_fd(sockfd),
- addr.storage.as_mut_ptr().cast::<c::sockaddr>(),
- &mut addr.len,
- ))?;
- Ok(addr.into_any())
- }
-}
-
-pub(crate) fn getpeername(sockfd: BorrowedFd<'_>) -> io::Result<Option<SocketAddrAny>> {
- unsafe {
- let mut addr = SocketAddrBuf::new();
- ret(c::getpeername(
- borrowed_fd(sockfd),
- addr.storage.as_mut_ptr().cast::<c::sockaddr>(),
- &mut addr.len,
- ))?;
- Ok(addr.into_any_option())
- }
-}
-
-#[cfg(not(windows))]
-pub(crate) fn socketpair(
- domain: AddressFamily,
- type_: SocketType,
- flags: SocketFlags,
- protocol: Option<Protocol>,
-) -> io::Result<(OwnedFd, OwnedFd)> {
- let raw_protocol = match protocol {
- Some(p) => p.0.get(),
- None => 0,
- };
- unsafe {
- let mut fds = MaybeUninit::<[OwnedFd; 2]>::uninit();
- ret(c::socketpair(
- c::c_int::from(domain.0),
- (type_.0 | flags.bits()) as c::c_int,
- raw_protocol as c::c_int,
- fds.as_mut_ptr().cast::<c::c_int>(),
- ))?;
-
- let [fd0, fd1] = fds.assume_init();
- Ok((fd0, fd1))
- }
-}
diff --git a/vendor/rustix/src/backend/libc/net/write_sockaddr.rs b/vendor/rustix/src/backend/libc/net/write_sockaddr.rs
deleted file mode 100644
index 08f04646..00000000
--- a/vendor/rustix/src/backend/libc/net/write_sockaddr.rs
+++ /dev/null
@@ -1,72 +0,0 @@
-//! The BSD sockets API requires us to read the `sa_family` field before we can
-//! interpret the rest of a `sockaddr` produced by the kernel.
-
-use super::ext::{in6_addr_new, in_addr_new, sockaddr_in6_new};
-use crate::backend::c;
-use crate::net::{SocketAddrV4, SocketAddrV6};
-
-pub(crate) fn encode_sockaddr_v4(v4: &SocketAddrV4) -> c::sockaddr_in {
- c::sockaddr_in {
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita",
- ))]
- sin_len: core::mem::size_of::<c::sockaddr_in>() as _,
- sin_family: c::AF_INET as _,
- sin_port: u16::to_be(v4.port()),
- sin_addr: in_addr_new(u32::from_ne_bytes(v4.ip().octets())),
- #[cfg(not(any(target_os = "haiku", target_os = "vita")))]
- sin_zero: [0; 8_usize],
- #[cfg(target_os = "haiku")]
- sin_zero: [0; 24_usize],
- #[cfg(target_os = "vita")]
- sin_zero: [0; 6_usize],
- #[cfg(target_os = "vita")]
- sin_vport: 0,
- }
-}
-
-pub(crate) fn encode_sockaddr_v6(v6: &SocketAddrV6) -> c::sockaddr_in6 {
- #[cfg(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- ))]
- {
- sockaddr_in6_new(
- core::mem::size_of::<c::sockaddr_in6>() as _,
- c::AF_INET6 as _,
- u16::to_be(v6.port()),
- u32::to_be(v6.flowinfo()),
- in6_addr_new(v6.ip().octets()),
- v6.scope_id(),
- )
- }
- #[cfg(not(any(
- bsd,
- target_os = "aix",
- target_os = "espidf",
- target_os = "haiku",
- target_os = "hurd",
- target_os = "nto",
- target_os = "vita"
- )))]
- {
- sockaddr_in6_new(
- c::AF_INET6 as _,
- u16::to_be(v6.port()),
- u32::to_be(v6.flowinfo()),
- in6_addr_new(v6.ip().octets()),
- v6.scope_id(),
- )
- }
-}