1use core::sync::atomic::Ordering;
2
3use super::error::ErrorCode;
4use crate::Result;
5use crate::RtVdsoVtable;
6use crate::into_result;
7
8pub type ThreadHandle = u64;
9
10pub fn spawn(
11 thread_fn: extern "C" fn(thread_arg: u64),
12 stack_size: usize,
13 thread_arg: u64,
14) -> Result<ThreadHandle> {
15 let vdso_spawn: extern "C" fn(extern "C" fn(thread_arg: u64), usize, u64) -> u64 = unsafe {
16 core::mem::transmute(
17 RtVdsoVtable::get().thread_spawn.load(Ordering::Relaxed) as usize as *const (),
18 )
19 };
20
21 let res = vdso_spawn(thread_fn, stack_size, thread_arg);
22 if res < u16::MAX as u64 {
23 Err((res as ErrorCode).into())
24 } else {
25 Ok(res)
26 }
27}
28
29pub fn yield_now() {
30 let vdso_yield: extern "C" fn() = unsafe {
31 core::mem::transmute(
32 RtVdsoVtable::get().thread_yield.load(Ordering::Relaxed) as usize as *const (),
33 )
34 };
35
36 vdso_yield()
37}
38
39pub fn sleep_until(deadline: crate::time::Instant) {
40 let vdso_sleep: extern "C" fn(u64) = unsafe {
41 core::mem::transmute(
42 RtVdsoVtable::get().thread_sleep.load(Ordering::Relaxed) as usize as *const (),
43 )
44 };
45
46 vdso_sleep(deadline.as_u64())
47}
48
49pub fn set_name(name: &str) -> Result<()> {
50 let vdso_set_name: extern "C" fn(*const u8, usize) -> ErrorCode = unsafe {
51 core::mem::transmute(
52 RtVdsoVtable::get().thread_set_name.load(Ordering::Relaxed) as usize as *const (),
53 )
54 };
55
56 into_result(vdso_set_name(name.as_ptr(), name.len()))
57}
58
59pub fn join(handle: ThreadHandle) -> Result<()> {
60 let vdso_join: extern "C" fn(u64) -> ErrorCode = unsafe {
61 core::mem::transmute(
62 RtVdsoVtable::get().thread_join.load(Ordering::Relaxed) as usize as *const (),
63 )
64 };
65
66 into_result(vdso_join(handle))
67}