use moa_uapi::{
channel::ChanHandle,
error::{ERR_INVAL, ERR_NO_RESOURCE, ERR_NOT_FOUND, ERR_PERM},
sysnr::{
SYSNR_TIMER_BIND, SYSNR_TIMER_CLOSE, SYSNR_TIMER_CREATE, SYSNR_TIMER_SET,
SYSNR_TIMER_UNBIND,
},
timer::{ClockId, TimerFlags, TimerHandle},
};
pub type Result<T> = core::result::Result<T, TimerError>;
define_syscall_error! {
pub enum TimerError {
Perm = ERR_PERM,
NotFound = ERR_NOT_FOUND,
Inval = ERR_INVAL,
NoResource = ERR_NO_RESOURCE,
}
}
#[allow(clippy::cast_possible_truncation, clippy::cast_sign_loss)]
pub fn timer_create(clock_id: ClockId) -> Result<TimerHandle> {
let ret = unsafe { super::arch::syscall1(SYSNR_TIMER_CREATE, clock_id as usize) };
if ret < 0 { Err(TimerError::from_raw(ret)) } else { Ok(TimerHandle::from_raw(ret as u32)) }
}
pub fn timer_bind(timer: TimerHandle, chan: ChanHandle) -> Result<()> {
let ret = unsafe {
super::arch::syscall2(SYSNR_TIMER_BIND, timer.raw() as usize, chan.raw() as usize)
};
if ret < 0 { Err(TimerError::from_raw(ret)) } else { Ok(()) }
}
pub fn timer_unbind(timer: TimerHandle) -> Result<()> {
let ret = unsafe { super::arch::syscall1(SYSNR_TIMER_UNBIND, timer.raw() as usize) };
if ret < 0 { Err(TimerError::from_raw(ret)) } else { Ok(()) }
}
#[allow(clippy::cast_possible_truncation)]
pub fn timer_set(timer: TimerHandle, flags: TimerFlags, initial: u64, interval: u64) -> Result<()> {
let ret = unsafe {
super::arch::syscall4(
SYSNR_TIMER_SET,
timer.raw() as usize,
flags.bits() as usize,
initial as usize,
interval as usize,
)
};
if ret < 0 { Err(TimerError::from_raw(ret)) } else { Ok(()) }
}
pub fn timer_close(timer: TimerHandle) -> Result<()> {
let ret = unsafe { super::arch::syscall1(SYSNR_TIMER_CLOSE, timer.raw() as usize) };
if ret < 0 { Err(TimerError::from_raw(ret)) } else { Ok(()) }
}