Add signal facilities

This commit is contained in:
Mark Poliakov 2023-07-25 16:15:00 +03:00
parent e0774b4d39
commit fb4586c48f
2 changed files with 52 additions and 8 deletions

View File

@ -1,6 +1,3 @@
//! Process management data types
pub use abi::process::{SpawnOption, SpawnOptions};
/// Status code returned when a process terminates
pub type ExitStatus = i32;
pub use abi::process::{ExitCode, Signal, SignalEntryData, SpawnOption, SpawnOptions};

View File

@ -7,14 +7,14 @@ use abi::{
DirectoryEntry, FileAttr, FileMode, MountOptions, OpenOptions, RawFd, SeekFrom,
UnmountOptions,
},
process::SpawnOptions,
process::{ExitCode, Signal, SpawnOptions},
syscall::SyscallFunction,
};
macro_rules! syscall {
($num:expr) => {{
let mut res: usize;
core::arch::asm!("svc #0", lateout("x0") res, in("x8") $num.repr());
core::arch::asm!("svc #0", lateout("x0") res, in("x8") usize::from($num));
res
}};
($num:expr, $a0:expr) => {{
@ -123,7 +123,8 @@ pub unsafe fn nanosleep(duration: Duration) {
/// # Safety
///
/// Unsafe: direct system call.
pub unsafe fn exit(code: i32) -> ! {
pub unsafe fn exit(code: ExitCode) -> ! {
let code = i32::from(code);
syscall!(SyscallFunction::Exit, argn!(code));
panic!();
}
@ -318,16 +319,62 @@ pub unsafe fn seek(fd: RawFd, pos: SeekFrom) -> Result<u64, Error> {
u64::from_syscall_result(syscall!(SyscallFunction::Seek, argn!(fd.0), argn!(u64::from(pos))))
}
/// System call: create a new process.
///
/// # Safety
///
/// Unsafe: direct system call.
pub unsafe fn spawn(options: &SpawnOptions<'_>) -> Result<u32, Error> {
u32::from_syscall_result(syscall!(SyscallFunction::Spawn, argp!(options as *const _)))
}
/// System call: wait for a process to finish
///
pub unsafe fn wait_process(pid: u32, status: &mut i32) -> Result<(), Error> {
/// # Safety
///
/// Unsafe: direct system call.
pub unsafe fn wait_process(pid: u32, status: &mut ExitCode) -> Result<(), Error> {
<()>::from_syscall_result(syscall!(
SyscallFunction::WaitProcess,
argn!(pid),
argp!(status as *mut _)
))
}
/// System call: send a signal to the target process.
///
/// # Safety
///
/// Unsafe: direct system call.
pub unsafe fn send_signal(pid: u32, signal: Signal) -> Result<(), Error> {
let signal = u32::from(signal);
<()>::from_syscall_result(syscall!(SyscallFunction::SendSignal, argn!(pid), argn!(signal)))
}
/// System call: set the process signal handler information.
///
/// # Safety
///
/// Unsafe: direct system call.
pub unsafe fn set_signal_entry(entry: usize, sp: usize) {
syscall!(SyscallFunction::SetSignalEntry, argn!(entry), argn!(sp));
}
/// System call: return from a signal handler.
///
/// # Safety
///
/// Unsafe: direct system call.
pub unsafe fn exit_signal() -> ! {
syscall!(SyscallFunction::ExitSignal);
panic!("Cannot return here");
}
/// System call: get the caller process ID.
///
/// # Safety
///
/// Unsafe: direct system call.
pub unsafe fn get_pid() -> u32 {
syscall!(SyscallFunction::GetPid) as _
}