Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix bug of sys_rt_sigaction, sys_poll, add sys_clock_nanosleep, sys_g… #139

Merged
merged 1 commit into from
Sep 19, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions api/ruxos_posix_api/build.rs
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,9 @@ typedef struct {{
let allow_vars = [
"O_.*",
"AF_.*",
"SO_.*",
"SOCK_.*",
"SOL_.*",
"IPPROTO_.*",
"FD_.*",
"F_.*",
Expand Down
4 changes: 4 additions & 0 deletions api/ruxos_posix_api/src/imp/io_mpx/poll.rs
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,10 @@ pub unsafe fn sys_poll(fds: *mut ctypes::pollfd, nfds: ctypes::nfds_t, timeout:
let fds = core::slice::from_raw_parts_mut(fds, nfds as usize);
let deadline = (!timeout.is_negative())
.then(|| current_time() + Duration::from_millis(timeout as u64));
for pollfd_item in fds.iter_mut() {
let revents = &mut pollfd_item.revents;
*revents &= 0;
}
loop {
#[cfg(feature = "net")]
ruxnet::poll_interfaces();
Expand Down
68 changes: 68 additions & 0 deletions api/ruxos_posix_api/src/imp/net.rs
Original file line number Diff line number Diff line change
Expand Up @@ -601,6 +601,74 @@ pub unsafe fn sys_getsockname(
})
}

/// get socket option
///
/// TODO: some options not impl, just return 0, like SO_RCVBUF SO_SNDBUF
pub fn sys_getsockopt(
socket_fd: c_int,
level: c_int,
optname: c_int,
optval: *mut c_void,
optlen: *mut ctypes::socklen_t,
) -> c_int {
unsafe {
info!(
"sys_getsockopt <= fd: {}, level: {}, optname: {}, optlen: {}, IGNORED",
socket_fd,
level,
optname,
core::ptr::read(optlen as *mut usize)
);
}
syscall_body!(sys_getsockopt, {
return Ok(0);
if optval.is_null() {
return Err(LinuxError::EFAULT);
}
let socket = Socket::from_fd(socket_fd)?;
match level as u32 {
ctypes::SOL_SOCKET => {
let val = match optname as u32 {
ctypes::SO_ACCEPTCONN => match &*socket {
Socket::Udp(_) => 0,
Socket::Tcp(tcpsocket) => {
if tcpsocket.lock().is_listening() {
1
} else {
0
}
}
},
ctypes::SO_TYPE => match &*socket {
Socket::Udp(_) => ctypes::SOCK_DGRAM,
Socket::Tcp(_) => ctypes::SOCK_STREAM,
},
ctypes::SO_RCVLOWAT | ctypes::SO_SNDLOWAT | ctypes::SO_BROADCAST => 1,
ctypes::SO_ERROR
| ctypes::SO_DONTROUTE
| ctypes::SO_KEEPALIVE
| ctypes::SO_LINGER
| ctypes::SO_OOBINLINE
| ctypes::SO_RCVBUF
| ctypes::SO_RCVTIMEO
| ctypes::SO_REUSEADDR
| ctypes::SO_SNDBUF
| ctypes::SO_SNDTIMEO => 0,
_ => return Err(LinuxError::ENOPROTOOPT),
};

unsafe {
core::ptr::write(optlen as *mut usize, core::mem::size_of::<i32>());
core::ptr::write(optval as *mut i32, val as i32);
}

Ok(0)
}
_ => Err(LinuxError::ENOSYS),
}
})
}

/// Get peer address to which the socket sockfd is connected.
pub unsafe fn sys_getpeername(
sock_fd: c_int,
Expand Down
18 changes: 12 additions & 6 deletions api/ruxos_posix_api/src/imp/rt_sig.rs
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,8 @@ pub fn sys_rt_sigprocmask(
}

/// sigaction syscall for A64 musl
///
/// TODO: if sa is 0, return now action
pub unsafe fn sys_rt_sigaction(
sig: c_int,
sa: *const ctypes::sigaction,
Expand All @@ -95,12 +97,16 @@ pub unsafe fn sys_rt_sigaction(
) -> c_int {
debug!("sys_rt_sigaction <= sig: {}", sig);
syscall_body!(sys_rt_sigaction, {
let sa = unsafe { *sa };
let old = unsafe { *old };
let sa = k_sigaction::from(sa);
let mut old_sa = k_sigaction::from(old);
sys_sigaction(sig as _, Some(&sa), Some(&mut old_sa));
Ok(0)
if sa as u64 == 0 || old as u64 == 0 {
Err(LinuxError::EFAULT)
} else {
let sa = unsafe { *sa };
let old = unsafe { *old };
let sa = k_sigaction::from(sa);
let mut old_sa = k_sigaction::from(old);
sys_sigaction(sig as _, Some(&sa), Some(&mut old_sa));
Ok(0)
}
})
}

Expand Down
49 changes: 48 additions & 1 deletion api/ruxos_posix_api/src/imp/time.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,9 @@ use crate::ctypes;

use axerrno::LinuxError;

// nanoseconds per a second
const NANO_PER_SECOND: i64 = 1000000000;

impl From<ctypes::timespec> for Duration {
fn from(ts: ctypes::timespec) -> Self {
Duration::new(ts.tv_sec as u64, ts.tv_nsec as u32)
Expand Down Expand Up @@ -74,13 +77,57 @@ pub unsafe fn sys_clock_settime(_clk: ctypes::clockid_t, ts: *const ctypes::time
})
}

/// Sleep until some nanoseconds
///
/// TODO: should be woken by signals, and set errno
/// TODO: deal with flags
pub unsafe fn sys_clock_nanosleep(
which_clock: ctypes::clockid_t,
flags: c_int,
req: *const ctypes::timespec,
rem: *mut ctypes::timespec,
) -> c_int {
syscall_body!(sys_clock_nanosleep, {
unsafe {
if req.is_null() || (*req).tv_nsec < 0 || (*req).tv_nsec >= NANO_PER_SECOND {
return Err(LinuxError::EINVAL);
}
}

let deadline = unsafe { Duration::from(*req) };

let now = ruxhal::time::current_time();

if now >= deadline {
return Ok(0);
}

#[cfg(feature = "multitask")]
ruxtask::sleep_until(deadline);
#[cfg(not(feature = "multitask"))]
ruxhal::time::busy_wait_until(deadline);

let after = ruxhal::time::current_time();
let actual = after - now;
let due = deadline - now;

if let Some(diff) = due.checked_sub(actual) {
if !rem.is_null() {
unsafe { (*rem) = diff.into() };
}
return Err(LinuxError::EINTR);
}
Ok(0)
})
}

/// Sleep some nanoseconds
///
/// TODO: should be woken by signals, and set errno
pub unsafe fn sys_nanosleep(req: *const ctypes::timespec, rem: *mut ctypes::timespec) -> c_int {
syscall_body!(sys_nanosleep, {
unsafe {
if req.is_null() || (*req).tv_nsec < 0 || (*req).tv_nsec > 999999999 {
if req.is_null() || (*req).tv_nsec < 0 || (*req).tv_nsec >= NANO_PER_SECOND {
return Err(LinuxError::EINVAL);
}
}
Expand Down
7 changes: 4 additions & 3 deletions api/ruxos_posix_api/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,8 @@ pub use imp::sys::{sys_sysinfo, sys_uname};
pub use imp::sys_invalid;
pub use imp::task::{sys_exit, sys_getpid, sys_getppid, sys_gettid, sys_sched_yield};
pub use imp::time::{
sys_clock_gettime, sys_clock_settime, sys_gettimeofday, sys_nanosleep, sys_times,
sys_clock_gettime, sys_clock_nanosleep, sys_clock_settime, sys_gettimeofday, sys_nanosleep,
sys_times,
};

#[cfg(all(feature = "fd", feature = "musl"))]
Expand All @@ -85,8 +86,8 @@ pub use imp::mmap::{sys_madvise, sys_mmap, sys_mprotect, sys_mremap, sys_msync,
#[cfg(feature = "net")]
pub use imp::net::{
sys_accept, sys_bind, sys_connect, sys_freeaddrinfo, sys_getaddrinfo, sys_getpeername,
sys_getsockname, sys_listen, sys_recv, sys_recvfrom, sys_send, sys_sendmsg, sys_sendto,
sys_setsockopt, sys_shutdown, sys_socket,
sys_getsockname, sys_getsockopt, sys_listen, sys_recv, sys_recvfrom, sys_send, sys_sendmsg,
sys_sendto, sys_setsockopt, sys_shutdown, sys_socket,
};
#[cfg(feature = "pipe")]
pub use imp::pipe::{sys_pipe, sys_pipe2};
Expand Down
6 changes: 6 additions & 0 deletions modules/ruxnet/src/lwip_impl/tcp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,12 @@ impl TcpSocket {
}
}

/// Returens if this socket is listening
#[inline]
pub fn is_listening(&self) -> bool {
unsafe { (*self.pcb.get()).state == tcp_state_LISTEN }
}

/// Returns whether this socket is in nonblocking mode.
#[inline]
pub fn is_nonblocking(&self) -> bool {
Expand Down
11 changes: 6 additions & 5 deletions modules/ruxnet/src/smoltcp_impl/tcp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,12 @@ impl TcpSocket {
}
}

/// Returens if this socket is listening
#[inline]
pub fn is_listening(&self) -> bool {
self.get_state() == STATE_LISTENING
}

/// Returns whether this socket is in nonblocking mode.
#[inline]
pub fn is_nonblocking(&self) -> bool {
Expand Down Expand Up @@ -423,11 +429,6 @@ impl TcpSocket {
self.get_state() == STATE_CONNECTED
}

#[inline]
fn is_listening(&self) -> bool {
self.get_state() == STATE_LISTENING
}

fn bound_endpoint(&self) -> AxResult<IpListenEndpoint> {
// SAFETY: no other threads can read or write `self.local_addr`.
let local_addr = unsafe { self.local_addr.get().read() };
Expand Down
15 changes: 14 additions & 1 deletion ulib/ruxlibc/src/time.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
*/

use core::ffi::c_int;
use ruxos_posix_api::{sys_clock_gettime, sys_clock_settime, sys_nanosleep};
use ruxos_posix_api::{sys_clock_gettime, sys_clock_nanosleep, sys_clock_settime, sys_nanosleep};
#[cfg(feature = "signal")]
use ruxos_posix_api::{sys_getitimer, sys_setitimer};

Expand All @@ -26,6 +26,19 @@ pub unsafe extern "C" fn clock_settime(clk: ctypes::clockid_t, ts: *mut ctypes::
e(sys_clock_settime(clk, ts))
}

/// Sleep until some nanoseconds
///
/// TODO: should be woken by signals, and set errno
#[no_mangle]
pub unsafe extern "C" fn clock_nanosleep(
which_clock: ctypes::clockid_t,
flags: c_int,
req: *const ctypes::timespec,
rem: *mut ctypes::timespec,
) -> c_int {
e(sys_clock_nanosleep(which_clock, flags, req, rem))
}

/// Sleep some nanoseconds
///
/// TODO: should be woken by signals, and set errno
Expand Down
14 changes: 14 additions & 0 deletions ulib/ruxmusl/src/aarch64/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -224,6 +224,12 @@ pub fn syscall(syscall_id: SyscallId, args: [usize; 6]) -> isize {
args[0] as ctypes::clockid_t,
args[1] as *mut ctypes::timespec,
) as _,
SyscallId::CLOCK_NANOSLEEP => ruxos_posix_api::sys_clock_nanosleep(
args[0] as ctypes::clockid_t,
args[1] as c_int,
args[2] as *const ctypes::timespec,
args[3] as *mut ctypes::timespec,
) as _,
SyscallId::SCHED_YIELD => ruxos_posix_api::sys_sched_yield() as _,
#[cfg(feature = "signal")]
SyscallId::KILL => ruxos_posix_api::sys_kill(args[0] as pid_t, args[1] as c_int) as _,
Expand Down Expand Up @@ -338,6 +344,14 @@ pub fn syscall(syscall_id: SyscallId, args: [usize; 6]) -> isize {
args[4] as ctypes::socklen_t,
) as _,
#[cfg(feature = "net")]
SyscallId::GETSOCKOPT => ruxos_posix_api::sys_getsockopt(
args[0] as c_int,
args[1] as c_int,
args[2] as c_int,
args[3] as *mut core::ffi::c_void,
args[4] as *mut ctypes::socklen_t,
) as _,
#[cfg(feature = "net")]
SyscallId::SHUTDOWN => {
ruxos_posix_api::sys_shutdown(args[0] as c_int, args[1] as c_int) as _
}
Expand Down
3 changes: 3 additions & 0 deletions ulib/ruxmusl/src/aarch64/syscall_id.rs
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,7 @@ pub enum SyscallId {
NANO_SLEEP = 101,
CLOCK_SETTIME = 112,
CLOCK_GETTIME = 113,
CLOCK_NANOSLEEP = 115,
SCHED_YIELD = 124,
#[cfg(feature = "signal")]
KILL = 129,
Expand Down Expand Up @@ -130,6 +131,8 @@ pub enum SyscallId {
#[cfg(feature = "net")]
SETSOCKOPT = 208,
#[cfg(feature = "net")]
GETSOCKOPT = 209,
#[cfg(feature = "net")]
SHUTDOWN = 210,
#[cfg(feature = "net")]
SENDMSG = 211,
Expand Down
14 changes: 14 additions & 0 deletions ulib/ruxmusl/src/riscv64/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -191,6 +191,12 @@ pub fn syscall(syscall_id: SyscallId, args: [usize; 6]) -> isize {
args[0] as ctypes::clockid_t,
args[1] as *mut ctypes::timespec,
) as _,
SyscallId::CLOCK_NANOSLEEP => ruxos_posix_api::sys_clock_nanosleep(
args[0] as ctypes::clockid_t,
args[1] as c_int,
args[2] as *const ctypes::timespec,
args[3] as *mut ctypes::timespec,
) as _,
SyscallId::SCHED_YIELD => ruxos_posix_api::sys_sched_yield() as _,
#[cfg(feature = "signal")]
SyscallId::SIGALTSTACK => ruxos_posix_api::sys_sigaltstack(
Expand Down Expand Up @@ -292,6 +298,14 @@ pub fn syscall(syscall_id: SyscallId, args: [usize; 6]) -> isize {
args[4] as ctypes::socklen_t,
) as _,
#[cfg(feature = "net")]
SyscallId::GETSOCKOPT => ruxos_posix_api::sys_getsockopt(
args[0] as c_int,
args[1] as c_int,
args[2] as c_int,
args[3] as *mut core::ffi::c_void,
args[4] as *mut ctypes::socklen_t,
) as _,
#[cfg(feature = "net")]
SyscallId::SHUTDOWN => {
ruxos_posix_api::sys_shutdown(args[0] as c_int, args[1] as c_int) as _
}
Expand Down
3 changes: 3 additions & 0 deletions ulib/ruxmusl/src/riscv64/syscall_id.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ pub enum SyscallId {
NANO_SLEEP = 101,
CLOCK_SETTIME = 112,
CLOCK_GETTIME = 113,
CLOCK_NANOSLEEP = 115,
SCHED_YIELD = 124,
#[cfg(feature = "signal")]
SIGALTSTACK = 132,
Expand Down Expand Up @@ -106,6 +107,8 @@ pub enum SyscallId {
#[cfg(feature = "net")]
SETSOCKOPT = 208,
#[cfg(feature = "net")]
GETSOCKOPT = 209,
#[cfg(feature = "net")]
SHUTDOWN = 210,
#[cfg(feature = "net")]
SENDMSG = 211,
Expand Down
Loading
Loading