Skip to content

Commit

Permalink
feat(net): add get_socket_option on Socket
Browse files Browse the repository at this point in the history
  • Loading branch information
AsakuraMizu committed Jul 31, 2024
1 parent 5fdea90 commit b200fc1
Show file tree
Hide file tree
Showing 2 changed files with 49 additions and 1 deletion.
45 changes: 44 additions & 1 deletion compio-net/src/socket.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,8 @@
use std::{future::Future, io, mem::ManuallyDrop};
use std::{
future::Future,
io,
mem::{ManuallyDrop, MaybeUninit},
};

use compio_buf::{BufResult, IntoInner, IoBuf, IoBufMut, IoVectoredBuf, IoVectoredBufMut};
#[cfg(unix)]
Expand Down Expand Up @@ -319,6 +323,45 @@ impl Socket {
compio_runtime::submit(op).await.into_inner()
}

#[cfg(unix)]
pub fn get_socket_option<T>(&self, level: i32, name: i32) -> io::Result<T> {
let mut value: MaybeUninit<T> = MaybeUninit::uninit();
let mut len = size_of::<T>() as libc::socklen_t;
syscall!(libc::getsockopt(
self.socket.as_raw_fd(),
level,
name,
value.as_mut_ptr() as _,
&mut len
))
.map(|_| {
debug_assert_eq!(len as usize, size_of::<T>());
// SAFETY: The value is initialized by `getsockopt`.
unsafe { value.assume_init() }
})
}

#[cfg(windows)]
pub fn get_socket_option<T>(&self, level: i32, name: i32) -> io::Result<T> {
let mut value: MaybeUninit<T> = MaybeUninit::uninit();
let mut len = size_of::<T>() as i32;
syscall!(
SOCKET,
windows_sys::Win32::Networking::WinSock::getsockopt(
self.socket.as_raw_fd() as _,
level,
name,
value.as_mut_ptr() as _,
&mut len
)
)
.map(|_| {
debug_assert_eq!(len as usize, size_of::<T>());
// SAFETY: The value is initialized by `getsockopt`.
unsafe { value.assume_init() }
})
}

#[cfg(unix)]
pub fn set_socket_option<T>(&self, level: i32, name: i32, value: &T) -> io::Result<()> {
syscall!(libc::setsockopt(
Expand Down
5 changes: 5 additions & 0 deletions compio-net/src/udp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -316,6 +316,11 @@ impl UdpSocket {
.await
}

/// Gets a socket option.
pub fn get_socket_option<T>(&self, level: i32, name: i32) -> io::Result<T> {
self.inner.get_socket_option(level, name)
}

/// Sets a socket option.
pub fn set_socket_option<T>(&self, level: i32, name: i32, value: &T) -> io::Result<()> {
self.inner.set_socket_option(level, name, value)
Expand Down

0 comments on commit b200fc1

Please sign in to comment.