Add syscall spawn

This commit is contained in:
Tate, Hongliang Tian 2018-09-22 14:20:13 +08:00
parent 7671dbf470
commit 637e15f6c6
23 changed files with 1318 additions and 75 deletions

@ -15,5 +15,6 @@ enclave {
untrusted { untrusted {
void ocall_print_string([in, string] const char* msg); void ocall_print_string([in, string] const char* msg);
int ocall_run_new_task(void);
}; };
}; };

160
src/libos/src/errno.h Normal file

@ -0,0 +1,160 @@
#ifndef __RUSGX_ERRNO_H_
#define __RUSGX_ERRNO_H_
/* Copied from glibc headers for x86-64 */
#define EPERM 1 /* Operation not permitted */
#define ENOENT 2 /* No such file or directory */
#define ESRCH 3 /* No such process */
#define EINTR 4 /* Interrupted system call */
#define EIO 5 /* I/O error */
#define ENXIO 6 /* No such device or address */
#define E2BIG 7 /* Argument list too long */
#define ENOEXEC 8 /* Exec format error */
#define EBADF 9 /* Bad file number */
#define ECHILD 10 /* No child processes */
#define EAGAIN 11 /* Try again */
#define ENOMEM 12 /* Out of memory */
#define EACCES 13 /* Permission denied */
#define EFAULT 14 /* Bad address */
#define ENOTBLK 15 /* Block device required */
#define EBUSY 16 /* Device or resource busy */
#define EEXIST 17 /* File exists */
#define EXDEV 18 /* Cross-device link */
#define ENODEV 19 /* No such device */
#define ENOTDIR 20 /* Not a directory */
#define EISDIR 21 /* Is a directory */
#define EINVAL 22 /* Invalid argument */
#define ENFILE 23 /* File table overflow */
#define EMFILE 24 /* Too many open files */
#define ENOTTY 25 /* Not a typewriter */
#define ETXTBSY 26 /* Text file busy */
#define EFBIG 27 /* File too large */
#define ENOSPC 28 /* No space left on device */
#define ESPIPE 29 /* Illegal seek */
#define EROFS 30 /* Read-only file system */
#define EMLINK 31 /* Too many links */
#define EPIPE 32 /* Broken pipe */
#define EDOM 33 /* Math argument out of domain of func */
#define ERANGE 34 /* Math result not representable */
#define EDEADLK 35 /* Resource deadlock would occur */
#define ENAMETOOLONG 36 /* File name too long */
#define ENOLCK 37 /* No record locks available */
#if 0
/*
* This error code is special: arch syscall entry code will return
* -ENOSYS if users try to call a syscall that doesn't exist. To keep
* failures of syscalls that really do exist distinguishable from
* failures due to attempts to use a nonexistent syscall, syscall
* implementations should refrain from returning -ENOSYS.
*/
#define ENOSYS 38 /* Invalid system call number */
#define ENOTEMPTY 39 /* Directory not empty */
#define ELOOP 40 /* Too many symbolic links encountered */
#define EWOULDBLOCK EAGAIN /* Operation would block */
#define ENOMSG 42 /* No message of desired type */
#define EIDRM 43 /* Identifier removed */
#define ECHRNG 44 /* Channel number out of range */
#define EL2NSYNC 45 /* Level 2 not synchronized */
#define EL3HLT 46 /* Level 3 halted */
#define EL3RST 47 /* Level 3 reset */
#define ELNRNG 48 /* Link number out of range */
#define EUNATCH 49 /* Protocol driver not attached */
#define ENOCSI 50 /* No CSI structure available */
#define EL2HLT 51 /* Level 2 halted */
#define EBADE 52 /* Invalid exchange */
#define EBADR 53 /* Invalid request descriptor */
#define EXFULL 54 /* Exchange full */
#define ENOANO 55 /* No anode */
#define EBADRQC 56 /* Invalid request code */
#define EBADSLT 57 /* Invalid slot */
#define EDEADLOCK EDEADLK
#define EBFONT 59 /* Bad font file format */
#define ENOSTR 60 /* Device not a stream */
#define ENODATA 61 /* No data available */
#define ETIME 62 /* Timer expired */
#define ENOSR 63 /* Out of streams resources */
#define ENONET 64 /* Machine is not on the network */
#define ENOPKG 65 /* Package not installed */
#define EREMOTE 66 /* Object is remote */
#define ENOLINK 67 /* Link has been severed */
#define EADV 68 /* Advertise error */
#define ESRMNT 69 /* Srmount error */
#define ECOMM 70 /* Communication error on send */
#define EPROTO 71 /* Protocol error */
#define EMULTIHOP 72 /* Multihop attempted */
#define EDOTDOT 73 /* RFS specific error */
#define EBADMSG 74 /* Not a data message */
#define EOVERFLOW 75 /* Value too large for defined data type */
#define ENOTUNIQ 76 /* Name not unique on network */
#define EBADFD 77 /* File descriptor in bad state */
#define EREMCHG 78 /* Remote address changed */
#define ELIBACC 79 /* Can not access a needed shared library */
#define ELIBBAD 80 /* Accessing a corrupted shared library */
#define ELIBSCN 81 /* .lib section in a.out corrupted */
#define ELIBMAX 82 /* Attempting to link in too many shared libraries */
#define ELIBEXEC 83 /* Cannot exec a shared library directly */
#define EILSEQ 84 /* Illegal byte sequence */
#define ERESTART 85 /* Interrupted system call should be restarted */
#define ESTRPIPE 86 /* Streams pipe error */
#define EUSERS 87 /* Too many users */
#define ENOTSOCK 88 /* Socket operation on non-socket */
#define EDESTADDRREQ 89 /* Destination address required */
#define EMSGSIZE 90 /* Message too long */
#define EPROTOTYPE 91 /* Protocol wrong type for socket */
#define ENOPROTOOPT 92 /* Protocol not available */
#define EPROTONOSUPPORT 93 /* Protocol not supported */
#define ESOCKTNOSUPPORT 94 /* Socket type not supported */
#define EOPNOTSUPP 95 /* Operation not supported on transport endpoint */
#define EPFNOSUPPORT 96 /* Protocol family not supported */
#define EAFNOSUPPORT 97 /* Address family not supported by protocol */
#define EADDRINUSE 98 /* Address already in use */
#define EADDRNOTAVAIL 99 /* Cannot assign requested address */
#define ENETDOWN 100 /* Network is down */
#define ENETUNREACH 101 /* Network is unreachable */
#define ENETRESET 102 /* Network dropped connection because of reset */
#define ECONNABORTED 103 /* Software caused connection abort */
#define ECONNRESET 104 /* Connection reset by peer */
#define ENOBUFS 105 /* No buffer space available */
#define EISCONN 106 /* Transport endpoint is already connected */
#define ENOTCONN 107 /* Transport endpoint is not connected */
#define ESHUTDOWN 108 /* Cannot send after transport endpoint shutdown */
#define ETOOMANYREFS 109 /* Too many references: cannot splice */
#define ETIMEDOUT 110 /* Connection timed out */
#define ECONNREFUSED 111 /* Connection refused */
#define EHOSTDOWN 112 /* Host is down */
#define EHOSTUNREACH 113 /* No route to host */
#define EALREADY 114 /* Operation already in progress */
#define EINPROGRESS 115 /* Operation now in progress */
#define ESTALE 116 /* Stale file handle */
#define EUCLEAN 117 /* Structure needs cleaning */
#define ENOTNAM 118 /* Not a XENIX named type file */
#define ENAVAIL 119 /* No XENIX semaphores available */
#define EISNAM 120 /* Is a named type file */
#define EREMOTEIO 121 /* Remote I/O error */
#define EDQUOT 122 /* Quota exceeded */
#define ENOMEDIUM 123 /* No medium found */
#define EMEDIUMTYPE 124 /* Wrong medium type */
#define ECANCELED 125 /* Operation Canceled */
#define ENOKEY 126 /* Required key not available */
#define EKEYEXPIRED 127 /* Key has expired */
#define EKEYREVOKED 128 /* Key has been revoked */
#define EKEYREJECTED 129 /* Key was rejected by service */
/* for robust mutexes */
#define EOWNERDEAD 130 /* Owner died */
#define ENOTRECOVERABLE 131 /* State not recoverable */
#define ERFKILL 132 /* Operation not possible due to RF-kill */
#define EHWPOISON 133 /* Memory page has hardware error */
#endif
#endif /* __RUSGX_ERRNO_H_ */

104
src/libos/src/errno.rs Normal file

@ -0,0 +1,104 @@
use std;
use std::fmt;
#[derive(Clone, Copy, Debug)]
enum Errno {
OK = 0,
EPERM = 1,
ENOENT = 2,
ESRCH = 3,
EINTR = 4,
EIO = 5,
ENXIO = 6,
E2BIG = 7,
ENOEXEC = 8,
EBADF = 9,
ECHILD = 10,
EAGAIN = 11,
ENOMEM = 12,
EACCES = 13,
EFAULT = 14,
ENOTBLK = 15,
EBUSY = 16,
EEXIST = 17,
EXDEV = 18,
ENODEV = 19,
ENOTDIR = 20,
EISDIR = 21,
EINVAL = 22,
ENFILE = 23,
EMFILE = 24,
ENOTTY = 25,
ETXTBSY = 26,
EFBIG = 27,
ENOSPC = 28,
ESPIPE = 29,
EROFS = 30,
EMLINK = 31,
EPIPE = 32,
EDOM = 33,
ERANGE = 34,
EDEADLK = 35,
ENAMETOOLONG = 36,
ENOLCK = 37,
}
impl Errno {
fn as_retval(&self) -> i32 {
*self as i32
}
}
impl Default for Errno {
fn default() -> Errno {
Errno::OK
}
}
impl fmt::Display for Errno {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "{} ({})",
*self as i32,
match *self {
Errno::OK => "Ok",
Errno::EPERM => "Operation not permitted",
Errno::ENOENT => "No such file or directory",
Errno::ESRCH => "No such process",
Errno::EINTR => "Interrupted system call",
Errno::EIO => "I/O error",
Errno::ENXIO => "No such device or address",
Errno::E2BIG => "Argument list too long",
Errno::ENOEXEC => "Exec format error",
Errno::EBADF => "Bad file number",
Errno::ECHILD => "No child processes",
Errno::EAGAIN => "Try again",
Errno::ENOMEM => "Out of memory",
Errno::EACCES => "Permission denied",
Errno::EFAULT => "Bad address",
Errno::ENOTBLK => "Block device required",
Errno::EBUSY => "Device or resource busy",
Errno::EEXIST => "File exists",
Errno::EXDEV => "Cross-device link",
Errno::ENODEV => "No such device",
Errno::ENOTDIR => "Not a directory",
Errno::EISDIR => "Is a directory",
Errno::EINVAL => "Invalid argument",
Errno::ENFILE => "File table overflow",
Errno::EMFILE => "Too many open files",
Errno::ENOTTY => "Not a typewriter",
Errno::ETXTBSY => "Text file busy",
Errno::EFBIG => "File too large",
Errno::ENOSPC => "No space left on device",
Errno::ESPIPE => "Illegal seek",
Errno::EROFS => "Read-only file system",
Errno::EMLINK => "Too many links",
Errno::EPIPE => "Broken pipe",
Errno::EDOM => "Math argument out of domain of func",
Errno::ERANGE => "Math result not representable",
Errno::EDEADLK => "Resource deadlock would occur",
Errno::ENAMETOOLONG => "File name too long",
Errno::ENOLCK => "No record locks available",
_ => "Unknown",
})
}
}

@ -29,12 +29,13 @@ mod process;
mod syscall; mod syscall;
mod elf_helper; mod elf_helper;
mod mm; mod mm;
mod errno;
use process::spawn_process; use process::spawn_process;
use process::run_task; use process::run_task;
/// Export system calls /// Export system calls
pub use syscall::{rusgx_write}; pub use syscall::*;
#[no_mangle] #[no_mangle]
pub extern "C" fn libos_boot(path_buf: *const i8) -> i32 { pub extern "C" fn libos_boot(path_buf: *const i8) -> i32 {

@ -36,7 +36,7 @@ pub fn spawn_process<P: AsRef<Path>>(elf_path: &P) -> Result<(), &'static str> {
elf_helper::print_pltrel_section(&elf_file)?; elf_helper::print_pltrel_section(&elf_file)?;
*/ */
let new_process = Process::new(&elf_file)?; let new_process = Process::new(&elf_file)?;
println!("new_process: {:#x?}", &new_process); //println!("new_process: {:#x?}", &new_process);
let new_task = Task::from(&new_process); let new_task = Task::from(&new_process);
process_table.lock().unwrap() process_table.lock().unwrap()
@ -44,11 +44,18 @@ pub fn spawn_process<P: AsRef<Path>>(elf_path: &P) -> Result<(), &'static str> {
new_task_queue.lock().unwrap() new_task_queue.lock().unwrap()
.push_back(new_task); .push_back(new_task);
let mut ret = 0;
let ocall_status = unsafe { ocall_run_new_task(&mut ret) };
if ocall_status != sgx_status_t::SGX_SUCCESS || ret != 0 {
return Err("ocall_run_new_task failed");
}
Ok(()) Ok(())
} }
pub fn run_task() -> Result<(), &'static str> { pub fn run_task() -> Result<(), &'static str> {
if let Some(new_task) = new_task_queue.lock().unwrap().pop_front() { if let Some(new_task) = pop_new_task() {
println!("Run task: {:#x?}", &new_task); println!("Run task: {:#x?}", &new_task);
println!("do_run_task() begin: {}", do_run_task as *const () as usize); println!("do_run_task() begin: {}", do_run_task as *const () as usize);
unsafe { do_run_task(&new_task as *const Task); } unsafe { do_run_task(&new_task as *const Task); }
@ -176,7 +183,13 @@ lazy_static! {
}; };
} }
fn pop_new_task() -> Option<Task> {
new_task_queue.lock().unwrap().pop_front()
}
extern { extern {
fn ocall_run_new_task(ret: *mut i32) -> sgx_status_t;
fn do_run_task(task: *const Task) -> i32; fn do_run_task(task: *const Task) -> i32;
fn rusgx_syscall(num: i32, arg0: u64, arg1: u64, arg2: u64, arg3: u64, arg4: u64) -> i64; fn rusgx_syscall(num: i32, arg0: u64, arg1: u64, arg2: u64, arg3: u64, arg4: u64) -> i64;
} }

@ -2,15 +2,17 @@
#define __RUSGX_SYSCALL_H__ #define __RUSGX_SYSCALL_H__
#include <sys/types.h> #include <sys/types.h>
#include "syscall_nr.h"
#define SYS_exit 60
#define SYS_write 1
#ifdef __cplusplus #ifdef __cplusplus
extern "C" { extern "C" {
#endif #endif
extern ssize_t rusgx_write(int fd, const void* buf, size_t size); extern ssize_t rusgx_write(int fd, const void* buf, size_t size);
extern int rusgx_spawn(int* child_pid, const char* path,
const char** argv,
const char** envp);
extern int rusgx_wait4(int child_pid, int* status, int options/*, struct rusage* rusage*/);
#ifdef __cplusplus #ifdef __cplusplus
} }

@ -1,5 +1,7 @@
use sgx_types::*; use sgx_types::*;
use process;
use std::ffi::CStr; // a borrowed C string
use std::collections::HashMap; use std::collections::HashMap;
// Use the internal syscall wrappers from sgx_tstd // Use the internal syscall wrappers from sgx_tstd
//use std::libc_fs as fs; //use std::libc_fs as fs;
@ -24,7 +26,30 @@ pub unsafe extern "C" fn sys_read(fd: c_int, buf: * mut c_void, size: size_t) ->
#[no_mangle] #[no_mangle]
pub extern fn rusgx_write(fd: c_int, buf: * const c_void, size: size_t) -> ssize_t { pub extern fn rusgx_write(fd: c_int, buf: * const c_void, size: size_t) -> ssize_t {
println!("Hello World!"); let str_from_c = unsafe {
CStr::from_ptr(buf as * const i8).to_string_lossy().into_owned()
};
println!("rusgx_write: {}", str_from_c);
size as ssize_t size as ssize_t
} }
#[no_mangle]
pub extern "C" fn rusgx_spawn(child_pid: *mut c_int, path: *const c_char,
argv: *const *const c_char, envp: *const *const c_char) -> c_int
{
let mut ret = 0;
let path_str = unsafe {
CStr::from_ptr(path as * const i8).to_string_lossy().into_owned()
};
if process::spawn_process(&path_str) != Ok(()) {
ret = -1;
}
ret
}
#[no_mangle]
pub extern "C" fn rusgx_wait4(child_pid: c_int, status: *mut c_int,
options: c_int/*, rusage: *mut Rusage*/) -> c_int
{
0
}

@ -1,16 +1,41 @@
#include "syscall.h" #include "syscall.h"
#include "task.h" #include "task.h"
#define DECL_SYSCALL_ARG(_type, _name, _arg) \
_type _name = (_type) (_arg)
long dispatch_syscall(int num, long arg0, long arg1, long arg2, long arg3, long arg4) { long dispatch_syscall(int num, long arg0, long arg1, long arg2, long arg3, long arg4) {
long ret = 0; long ret = 0;
switch (num) { switch (num) {
case SYS_exit: case SYS_exit: {
do_exit_task((int)arg0); DECL_SYSCALL_ARG(int, exit_code, arg0);
do_exit_task(exit_code);
break; break;
case SYS_write: }
ret = (long) rusgx_write((int)arg0, (const void*)arg1, (size_t)arg2); case SYS_write: {
DECL_SYSCALL_ARG(int, fd, arg0);
DECL_SYSCALL_ARG(const void*, buf, arg1);
DECL_SYSCALL_ARG(size_t, buf_size, arg2);
ret = rusgx_write(fd, buf, buf_size);
break; break;
}
case SYS_spawn: {
DECL_SYSCALL_ARG(int*, child_pid, arg0);
DECL_SYSCALL_ARG(const char*, path, arg1);
DECL_SYSCALL_ARG(const char**, argv, arg2);
DECL_SYSCALL_ARG(const char**, envp, arg3);
ret = rusgx_spawn(child_pid, path, argv, envp);
break;
}
case SYS_wait4: {
DECL_SYSCALL_ARG(int, child_pid, arg0);
DECL_SYSCALL_ARG(int*, status, arg1);
DECL_SYSCALL_ARG(int, options, arg2);
//DECL_SYSCALL_ARG(struct rusage*, rusage, arg3);
ret = rusgx_wait4(child_pid, status, options/*, rusage*/);
break;
}
default: default:
ret = -1; ret = -1;
break; break;

716
src/libos/src/syscall_nr.h Normal file

@ -0,0 +1,716 @@
#ifndef __RUSGX_SYSCALL_NR_H__
#define __RUSGX_SYSCALL_NR_H__
/* Macros are copied from glibc headers for x86-64 */
#define SYS__llseek __NR__llseek
#define SYS__newselect __NR__newselect
#define SYS__sysctl __NR__sysctl
#define SYS_accept4 __NR_accept4
#define SYS_access __NR_access
#define SYS_acct __NR_acct
#define SYS_add_key __NR_add_key
#define SYS_adjtimex __NR_adjtimex
#define SYS_afs_syscall __NR_afs_syscall
#define SYS_alarm __NR_alarm
#define SYS_bdflush __NR_bdflush
#define SYS_bind __NR_bind
#define SYS_bpf __NR_bpf
#define SYS_break __NR_break
#define SYS_brk __NR_brk
#define SYS_capget __NR_capget
#define SYS_capset __NR_capset
#define SYS_chdir __NR_chdir
#define SYS_chmod __NR_chmod
#define SYS_chown __NR_chown
#define SYS_chown32 __NR_chown32
#define SYS_chroot __NR_chroot
#define SYS_clock_adjtime __NR_clock_adjtime
#define SYS_clock_getres __NR_clock_getres
#define SYS_clock_gettime __NR_clock_gettime
#define SYS_clock_nanosleep __NR_clock_nanosleep
#define SYS_clock_settime __NR_clock_settime
#define SYS_clone __NR_clone
#define SYS_close __NR_close
#define SYS_connect __NR_connect
#define SYS_creat __NR_creat
#define SYS_create_module __NR_create_module
#define SYS_delete_module __NR_delete_module
#define SYS_dup __NR_dup
#define SYS_dup2 __NR_dup2
#define SYS_dup3 __NR_dup3
#define SYS_epoll_create __NR_epoll_create
#define SYS_epoll_create1 __NR_epoll_create1
#define SYS_epoll_ctl __NR_epoll_ctl
#define SYS_epoll_pwait __NR_epoll_pwait
#define SYS_epoll_wait __NR_epoll_wait
#define SYS_eventfd __NR_eventfd
#define SYS_eventfd2 __NR_eventfd2
#define SYS_execve __NR_execve
#define SYS_execveat __NR_execveat
#define SYS_exit __NR_exit
#define SYS_exit_group __NR_exit_group
#define SYS_faccessat __NR_faccessat
#define SYS_fadvise64 __NR_fadvise64
#define SYS_fadvise64_64 __NR_fadvise64_64
#define SYS_fallocate __NR_fallocate
#define SYS_fanotify_init __NR_fanotify_init
#define SYS_fanotify_mark __NR_fanotify_mark
#define SYS_fchdir __NR_fchdir
#define SYS_fchmod __NR_fchmod
#define SYS_fchmodat __NR_fchmodat
#define SYS_fchown __NR_fchown
#define SYS_fchown32 __NR_fchown32
#define SYS_fchownat __NR_fchownat
#define SYS_fcntl __NR_fcntl
#define SYS_fcntl64 __NR_fcntl64
#define SYS_fdatasync __NR_fdatasync
#define SYS_fgetxattr __NR_fgetxattr
#define SYS_finit_module __NR_finit_module
#define SYS_flistxattr __NR_flistxattr
#define SYS_flock __NR_flock
#define SYS_fork __NR_fork
#define SYS_fremovexattr __NR_fremovexattr
#define SYS_fsetxattr __NR_fsetxattr
#define SYS_fstat __NR_fstat
#define SYS_fstat64 __NR_fstat64
#define SYS_fstatat64 __NR_fstatat64
#define SYS_fstatfs __NR_fstatfs
#define SYS_fstatfs64 __NR_fstatfs64
#define SYS_fsync __NR_fsync
#define SYS_ftime __NR_ftime
#define SYS_ftruncate __NR_ftruncate
#define SYS_ftruncate64 __NR_ftruncate64
#define SYS_futex __NR_futex
#define SYS_futimesat __NR_futimesat
#define SYS_get_kernel_syms __NR_get_kernel_syms
#define SYS_get_mempolicy __NR_get_mempolicy
#define SYS_get_robust_list __NR_get_robust_list
#define SYS_get_thread_area __NR_get_thread_area
#define SYS_getcpu __NR_getcpu
#define SYS_getcwd __NR_getcwd
#define SYS_getdents __NR_getdents
#define SYS_getdents64 __NR_getdents64
#define SYS_getegid __NR_getegid
#define SYS_getegid32 __NR_getegid32
#define SYS_geteuid __NR_geteuid
#define SYS_geteuid32 __NR_geteuid32
#define SYS_getgid __NR_getgid
#define SYS_getgid32 __NR_getgid32
#define SYS_getgroups __NR_getgroups
#define SYS_getgroups32 __NR_getgroups32
#define SYS_getitimer __NR_getitimer
#define SYS_getpeername __NR_getpeername
#define SYS_getpgid __NR_getpgid
#define SYS_getpgrp __NR_getpgrp
#define SYS_getpid __NR_getpid
#define SYS_getpmsg __NR_getpmsg
#define SYS_getppid __NR_getppid
#define SYS_getpriority __NR_getpriority
#define SYS_getrandom __NR_getrandom
#define SYS_getresgid __NR_getresgid
#define SYS_getresgid32 __NR_getresgid32
#define SYS_getresuid __NR_getresuid
#define SYS_getresuid32 __NR_getresuid32
#define SYS_getrlimit __NR_getrlimit
#define SYS_getrusage __NR_getrusage
#define SYS_getsid __NR_getsid
#define SYS_getsockname __NR_getsockname
#define SYS_getsockopt __NR_getsockopt
#define SYS_gettid __NR_gettid
#define SYS_gettimeofday __NR_gettimeofday
#define SYS_getuid __NR_getuid
#define SYS_getuid32 __NR_getuid32
#define SYS_getxattr __NR_getxattr
#define SYS_gtty __NR_gtty
#define SYS_idle __NR_idle
#define SYS_init_module __NR_init_module
#define SYS_inotify_add_watch __NR_inotify_add_watch
#define SYS_inotify_init __NR_inotify_init
#define SYS_inotify_init1 __NR_inotify_init1
#define SYS_inotify_rm_watch __NR_inotify_rm_watch
#define SYS_io_cancel __NR_io_cancel
#define SYS_io_destroy __NR_io_destroy
#define SYS_io_getevents __NR_io_getevents
#define SYS_io_setup __NR_io_setup
#define SYS_io_submit __NR_io_submit
#define SYS_ioctl __NR_ioctl
#define SYS_ioperm __NR_ioperm
#define SYS_iopl __NR_iopl
#define SYS_ioprio_get __NR_ioprio_get
#define SYS_ioprio_set __NR_ioprio_set
#define SYS_ipc __NR_ipc
#define SYS_kcmp __NR_kcmp
#define SYS_kexec_load __NR_kexec_load
#define SYS_keyctl __NR_keyctl
#define SYS_kill __NR_kill
#define SYS_lchown __NR_lchown
#define SYS_lchown32 __NR_lchown32
#define SYS_lgetxattr __NR_lgetxattr
#define SYS_link __NR_link
#define SYS_linkat __NR_linkat
#define SYS_listen __NR_listen
#define SYS_listxattr __NR_listxattr
#define SYS_llistxattr __NR_llistxattr
#define SYS_lock __NR_lock
#define SYS_lookup_dcookie __NR_lookup_dcookie
#define SYS_lremovexattr __NR_lremovexattr
#define SYS_lseek __NR_lseek
#define SYS_lsetxattr __NR_lsetxattr
#define SYS_lstat __NR_lstat
#define SYS_lstat64 __NR_lstat64
#define SYS_madvise __NR_madvise
#define SYS_mbind __NR_mbind
#define SYS_membarrier __NR_membarrier
#define SYS_memfd_create __NR_memfd_create
#define SYS_migrate_pages __NR_migrate_pages
#define SYS_mincore __NR_mincore
#define SYS_mkdir __NR_mkdir
#define SYS_mkdirat __NR_mkdirat
#define SYS_mknod __NR_mknod
#define SYS_mknodat __NR_mknodat
#define SYS_mlock __NR_mlock
#define SYS_mlock2 __NR_mlock2
#define SYS_mlockall __NR_mlockall
#define SYS_mmap __NR_mmap
#define SYS_mmap2 __NR_mmap2
#define SYS_modify_ldt __NR_modify_ldt
#define SYS_mount __NR_mount
#define SYS_move_pages __NR_move_pages
#define SYS_mprotect __NR_mprotect
#define SYS_mpx __NR_mpx
#define SYS_mq_getsetattr __NR_mq_getsetattr
#define SYS_mq_notify __NR_mq_notify
#define SYS_mq_open __NR_mq_open
#define SYS_mq_timedreceive __NR_mq_timedreceive
#define SYS_mq_timedsend __NR_mq_timedsend
#define SYS_mq_unlink __NR_mq_unlink
#define SYS_mremap __NR_mremap
#define SYS_msync __NR_msync
#define SYS_munlock __NR_munlock
#define SYS_munlockall __NR_munlockall
#define SYS_munmap __NR_munmap
#define SYS_name_to_handle_at __NR_name_to_handle_at
#define SYS_nanosleep __NR_nanosleep
#define SYS_nfsservctl __NR_nfsservctl
#define SYS_nice __NR_nice
#define SYS_oldfstat __NR_oldfstat
#define SYS_oldlstat __NR_oldlstat
#define SYS_oldolduname __NR_oldolduname
#define SYS_oldstat __NR_oldstat
#define SYS_olduname __NR_olduname
#define SYS_open __NR_open
#define SYS_open_by_handle_at __NR_open_by_handle_at
#define SYS_openat __NR_openat
#define SYS_pause __NR_pause
#define SYS_perf_event_open __NR_perf_event_open
#define SYS_personality __NR_personality
#define SYS_pipe __NR_pipe
#define SYS_pipe2 __NR_pipe2
#define SYS_pivot_root __NR_pivot_root
#define SYS_poll __NR_poll
#define SYS_ppoll __NR_ppoll
#define SYS_prctl __NR_prctl
#define SYS_pread64 __NR_pread64
#define SYS_preadv __NR_preadv
#define SYS_prlimit64 __NR_prlimit64
#define SYS_process_vm_readv __NR_process_vm_readv
#define SYS_process_vm_writev __NR_process_vm_writev
#define SYS_prof __NR_prof
#define SYS_profil __NR_profil
#define SYS_pselect6 __NR_pselect6
#define SYS_ptrace __NR_ptrace
#define SYS_putpmsg __NR_putpmsg
#define SYS_pwrite64 __NR_pwrite64
#define SYS_pwritev __NR_pwritev
#define SYS_query_module __NR_query_module
#define SYS_quotactl __NR_quotactl
#define SYS_read __NR_read
#define SYS_readahead __NR_readahead
#define SYS_readdir __NR_readdir
#define SYS_readlink __NR_readlink
#define SYS_readlinkat __NR_readlinkat
#define SYS_readv __NR_readv
#define SYS_reboot __NR_reboot
#define SYS_recvfrom __NR_recvfrom
#define SYS_recvmmsg __NR_recvmmsg
#define SYS_recvmsg __NR_recvmsg
#define SYS_remap_file_pages __NR_remap_file_pages
#define SYS_removexattr __NR_removexattr
#define SYS_rename __NR_rename
#define SYS_renameat __NR_renameat
#define SYS_renameat2 __NR_renameat2
#define SYS_request_key __NR_request_key
#define SYS_restart_syscall __NR_restart_syscall
#define SYS_rmdir __NR_rmdir
#define SYS_rt_sigaction __NR_rt_sigaction
#define SYS_rt_sigpending __NR_rt_sigpending
#define SYS_rt_sigprocmask __NR_rt_sigprocmask
#define SYS_rt_sigqueueinfo __NR_rt_sigqueueinfo
#define SYS_rt_sigreturn __NR_rt_sigreturn
#define SYS_rt_sigsuspend __NR_rt_sigsuspend
#define SYS_rt_sigtimedwait __NR_rt_sigtimedwait
#define SYS_rt_tgsigqueueinfo __NR_rt_tgsigqueueinfo
#define SYS_sched_get_priority_max __NR_sched_get_priority_max
#define SYS_sched_get_priority_min __NR_sched_get_priority_min
#define SYS_sched_getaffinity __NR_sched_getaffinity
#define SYS_sched_getattr __NR_sched_getattr
#define SYS_sched_getparam __NR_sched_getparam
#define SYS_sched_getscheduler __NR_sched_getscheduler
#define SYS_sched_rr_get_interval __NR_sched_rr_get_interval
#define SYS_sched_setaffinity __NR_sched_setaffinity
#define SYS_sched_setattr __NR_sched_setattr
#define SYS_sched_setparam __NR_sched_setparam
#define SYS_sched_setscheduler __NR_sched_setscheduler
#define SYS_sched_yield __NR_sched_yield
#define SYS_seccomp __NR_seccomp
#define SYS_select __NR_select
#define SYS_sendfile __NR_sendfile
#define SYS_sendfile64 __NR_sendfile64
#define SYS_sendmmsg __NR_sendmmsg
#define SYS_sendmsg __NR_sendmsg
#define SYS_sendto __NR_sendto
#define SYS_set_mempolicy __NR_set_mempolicy
#define SYS_set_robust_list __NR_set_robust_list
#define SYS_set_thread_area __NR_set_thread_area
#define SYS_set_tid_address __NR_set_tid_address
#define SYS_setdomainname __NR_setdomainname
#define SYS_setfsgid __NR_setfsgid
#define SYS_setfsgid32 __NR_setfsgid32
#define SYS_setfsuid __NR_setfsuid
#define SYS_setfsuid32 __NR_setfsuid32
#define SYS_setgid __NR_setgid
#define SYS_setgid32 __NR_setgid32
#define SYS_setgroups __NR_setgroups
#define SYS_setgroups32 __NR_setgroups32
#define SYS_sethostname __NR_sethostname
#define SYS_setitimer __NR_setitimer
#define SYS_setns __NR_setns
#define SYS_setpgid __NR_setpgid
#define SYS_setpriority __NR_setpriority
#define SYS_setregid __NR_setregid
#define SYS_setregid32 __NR_setregid32
#define SYS_setresgid __NR_setresgid
#define SYS_setresgid32 __NR_setresgid32
#define SYS_setresuid __NR_setresuid
#define SYS_setresuid32 __NR_setresuid32
#define SYS_setreuid __NR_setreuid
#define SYS_setreuid32 __NR_setreuid32
#define SYS_setrlimit __NR_setrlimit
#define SYS_setsid __NR_setsid
#define SYS_setsockopt __NR_setsockopt
#define SYS_settimeofday __NR_settimeofday
#define SYS_setuid __NR_setuid
#define SYS_setuid32 __NR_setuid32
#define SYS_setxattr __NR_setxattr
#define SYS_sgetmask __NR_sgetmask
#define SYS_shutdown __NR_shutdown
#define SYS_sigaction __NR_sigaction
#define SYS_sigaltstack __NR_sigaltstack
#define SYS_signal __NR_signal
#define SYS_signalfd __NR_signalfd
#define SYS_signalfd4 __NR_signalfd4
#define SYS_sigpending __NR_sigpending
#define SYS_sigprocmask __NR_sigprocmask
#define SYS_sigreturn __NR_sigreturn
#define SYS_sigsuspend __NR_sigsuspend
#define SYS_socket __NR_socket
#define SYS_socketcall __NR_socketcall
#define SYS_socketpair __NR_socketpair
#define SYS_splice __NR_splice
#define SYS_ssetmask __NR_ssetmask
#define SYS_stat __NR_stat
#define SYS_stat64 __NR_stat64
#define SYS_statfs __NR_statfs
#define SYS_statfs64 __NR_statfs64
#define SYS_stime __NR_stime
#define SYS_stty __NR_stty
#define SYS_swapoff __NR_swapoff
#define SYS_swapon __NR_swapon
#define SYS_symlink __NR_symlink
#define SYS_symlinkat __NR_symlinkat
#define SYS_sync __NR_sync
#define SYS_sync_file_range __NR_sync_file_range
#define SYS_syncfs __NR_syncfs
#define SYS_sysfs __NR_sysfs
#define SYS_sysinfo __NR_sysinfo
#define SYS_syslog __NR_syslog
#define SYS_tee __NR_tee
#define SYS_tgkill __NR_tgkill
#define SYS_time __NR_time
#define SYS_timer_create __NR_timer_create
#define SYS_timer_delete __NR_timer_delete
#define SYS_timer_getoverrun __NR_timer_getoverrun
#define SYS_timer_gettime __NR_timer_gettime
#define SYS_timer_settime __NR_timer_settime
#define SYS_timerfd_create __NR_timerfd_create
#define SYS_timerfd_gettime __NR_timerfd_gettime
#define SYS_timerfd_settime __NR_timerfd_settime
#define SYS_times __NR_times
#define SYS_tkill __NR_tkill
#define SYS_truncate __NR_truncate
#define SYS_truncate64 __NR_truncate64
#define SYS_ugetrlimit __NR_ugetrlimit
#define SYS_ulimit __NR_ulimit
#define SYS_umask __NR_umask
#define SYS_umount __NR_umount
#define SYS_umount2 __NR_umount2
#define SYS_uname __NR_uname
#define SYS_unlink __NR_unlink
#define SYS_unlinkat __NR_unlinkat
#define SYS_unshare __NR_unshare
#define SYS_uselib __NR_uselib
#define SYS_userfaultfd __NR_userfaultfd
#define SYS_ustat __NR_ustat
#define SYS_utime __NR_utime
#define SYS_utimensat __NR_utimensat
#define SYS_utimes __NR_utimes
#define SYS_vfork __NR_vfork
#define SYS_vhangup __NR_vhangup
#define SYS_vm86 __NR_vm86
#define SYS_vm86old __NR_vm86old
#define SYS_vmsplice __NR_vmsplice
#define SYS_vserver __NR_vserver
#define SYS_wait4 __NR_wait4
#define SYS_waitid __NR_waitid
#define SYS_waitpid __NR_waitpid
#define SYS_write __NR_write
#define SYS_writev __NR_writev
#define SYS_spawn __NR_spawn
#endif /* _SYSCALL_H */
#ifndef _ASM_X86_UNISTD_64_H
#define _ASM_X86_UNISTD_64_H 1
#define __NR_read 0
#define __NR_write 1
#define __NR_open 2
#define __NR_close 3
#define __NR_stat 4
#define __NR_fstat 5
#define __NR_lstat 6
#define __NR_poll 7
#define __NR_lseek 8
#define __NR_mmap 9
#define __NR_mprotect 10
#define __NR_munmap 11
#define __NR_brk 12
#define __NR_rt_sigaction 13
#define __NR_rt_sigprocmask 14
#define __NR_rt_sigreturn 15
#define __NR_ioctl 16
#define __NR_pread64 17
#define __NR_pwrite64 18
#define __NR_readv 19
#define __NR_writev 20
#define __NR_access 21
#define __NR_pipe 22
#define __NR_select 23
#define __NR_sched_yield 24
#define __NR_mremap 25
#define __NR_msync 26
#define __NR_mincore 27
#define __NR_madvise 28
#define __NR_shmget 29
#define __NR_shmat 30
#define __NR_shmctl 31
#define __NR_dup 32
#define __NR_dup2 33
#define __NR_pause 34
#define __NR_nanosleep 35
#define __NR_getitimer 36
#define __NR_alarm 37
#define __NR_setitimer 38
#define __NR_getpid 39
#define __NR_sendfile 40
#define __NR_socket 41
#define __NR_connect 42
#define __NR_accept 43
#define __NR_sendto 44
#define __NR_recvfrom 45
#define __NR_sendmsg 46
#define __NR_recvmsg 47
#define __NR_shutdown 48
#define __NR_bind 49
#define __NR_listen 50
#define __NR_getsockname 51
#define __NR_getpeername 52
#define __NR_socketpair 53
#define __NR_setsockopt 54
#define __NR_getsockopt 55
#define __NR_clone 56
#define __NR_fork 57
#define __NR_vfork 58
#define __NR_execve 59
#define __NR_exit 60
#define __NR_wait4 61
#define __NR_kill 62
#define __NR_uname 63
#define __NR_semget 64
#define __NR_semop 65
#define __NR_semctl 66
#define __NR_shmdt 67
#define __NR_msgget 68
#define __NR_msgsnd 69
#define __NR_msgrcv 70
#define __NR_msgctl 71
#define __NR_fcntl 72
#define __NR_flock 73
#define __NR_fsync 74
#define __NR_fdatasync 75
#define __NR_truncate 76
#define __NR_ftruncate 77
#define __NR_getdents 78
#define __NR_getcwd 79
#define __NR_chdir 80
#define __NR_fchdir 81
#define __NR_rename 82
#define __NR_mkdir 83
#define __NR_rmdir 84
#define __NR_creat 85
#define __NR_link 86
#define __NR_unlink 87
#define __NR_symlink 88
#define __NR_readlink 89
#define __NR_chmod 90
#define __NR_fchmod 91
#define __NR_chown 92
#define __NR_fchown 93
#define __NR_lchown 94
#define __NR_umask 95
#define __NR_gettimeofday 96
#define __NR_getrlimit 97
#define __NR_getrusage 98
#define __NR_sysinfo 99
#define __NR_times 100
#define __NR_ptrace 101
#define __NR_getuid 102
#define __NR_syslog 103
#define __NR_getgid 104
#define __NR_setuid 105
#define __NR_setgid 106
#define __NR_geteuid 107
#define __NR_getegid 108
#define __NR_setpgid 109
#define __NR_getppid 110
#define __NR_getpgrp 111
#define __NR_setsid 112
#define __NR_setreuid 113
#define __NR_setregid 114
#define __NR_getgroups 115
#define __NR_setgroups 116
#define __NR_setresuid 117
#define __NR_getresuid 118
#define __NR_setresgid 119
#define __NR_getresgid 120
#define __NR_getpgid 121
#define __NR_setfsuid 122
#define __NR_setfsgid 123
#define __NR_getsid 124
#define __NR_capget 125
#define __NR_capset 126
#define __NR_rt_sigpending 127
#define __NR_rt_sigtimedwait 128
#define __NR_rt_sigqueueinfo 129
#define __NR_rt_sigsuspend 130
#define __NR_sigaltstack 131
#define __NR_utime 132
#define __NR_mknod 133
#define __NR_uselib 134
#define __NR_personality 135
#define __NR_ustat 136
#define __NR_statfs 137
#define __NR_fstatfs 138
#define __NR_sysfs 139
#define __NR_getpriority 140
#define __NR_setpriority 141
#define __NR_sched_setparam 142
#define __NR_sched_getparam 143
#define __NR_sched_setscheduler 144
#define __NR_sched_getscheduler 145
#define __NR_sched_get_priority_max 146
#define __NR_sched_get_priority_min 147
#define __NR_sched_rr_get_interval 148
#define __NR_mlock 149
#define __NR_munlock 150
#define __NR_mlockall 151
#define __NR_munlockall 152
#define __NR_vhangup 153
#define __NR_modify_ldt 154
#define __NR_pivot_root 155
#define __NR__sysctl 156
#define __NR_prctl 157
#define __NR_arch_prctl 158
#define __NR_adjtimex 159
#define __NR_setrlimit 160
#define __NR_chroot 161
#define __NR_sync 162
#define __NR_acct 163
#define __NR_settimeofday 164
#define __NR_mount 165
#define __NR_umount2 166
#define __NR_swapon 167
#define __NR_swapoff 168
#define __NR_reboot 169
#define __NR_sethostname 170
#define __NR_setdomainname 171
#define __NR_iopl 172
#define __NR_ioperm 173
#define __NR_create_module 174
#define __NR_init_module 175
#define __NR_delete_module 176
#define __NR_get_kernel_syms 177
#define __NR_query_module 178
#define __NR_quotactl 179
#define __NR_nfsservctl 180
#define __NR_getpmsg 181
#define __NR_putpmsg 182
#define __NR_afs_syscall 183
#define __NR_tuxcall 184
#define __NR_security 185
#define __NR_gettid 186
#define __NR_readahead 187
#define __NR_setxattr 188
#define __NR_lsetxattr 189
#define __NR_fsetxattr 190
#define __NR_getxattr 191
#define __NR_lgetxattr 192
#define __NR_fgetxattr 193
#define __NR_listxattr 194
#define __NR_llistxattr 195
#define __NR_flistxattr 196
#define __NR_removexattr 197
#define __NR_lremovexattr 198
#define __NR_fremovexattr 199
#define __NR_tkill 200
#define __NR_time 201
#define __NR_futex 202
#define __NR_sched_setaffinity 203
#define __NR_sched_getaffinity 204
#define __NR_set_thread_area 205
#define __NR_io_setup 206
#define __NR_io_destroy 207
#define __NR_io_getevents 208
#define __NR_io_submit 209
#define __NR_io_cancel 210
#define __NR_get_thread_area 211
#define __NR_lookup_dcookie 212
#define __NR_epoll_create 213
#define __NR_epoll_ctl_old 214
#define __NR_epoll_wait_old 215
#define __NR_remap_file_pages 216
#define __NR_getdents64 217
#define __NR_set_tid_address 218
#define __NR_restart_syscall 219
#define __NR_semtimedop 220
#define __NR_fadvise64 221
#define __NR_timer_create 222
#define __NR_timer_settime 223
#define __NR_timer_gettime 224
#define __NR_timer_getoverrun 225
#define __NR_timer_delete 226
#define __NR_clock_settime 227
#define __NR_clock_gettime 228
#define __NR_clock_getres 229
#define __NR_clock_nanosleep 230
#define __NR_exit_group 231
#define __NR_epoll_wait 232
#define __NR_epoll_ctl 233
#define __NR_tgkill 234
#define __NR_utimes 235
#define __NR_vserver 236
#define __NR_mbind 237
#define __NR_set_mempolicy 238
#define __NR_get_mempolicy 239
#define __NR_mq_open 240
#define __NR_mq_unlink 241
#define __NR_mq_timedsend 242
#define __NR_mq_timedreceive 243
#define __NR_mq_notify 244
#define __NR_mq_getsetattr 245
#define __NR_kexec_load 246
#define __NR_waitid 247
#define __NR_add_key 248
#define __NR_request_key 249
#define __NR_keyctl 250
#define __NR_ioprio_set 251
#define __NR_ioprio_get 252
#define __NR_inotify_init 253
#define __NR_inotify_add_watch 254
#define __NR_inotify_rm_watch 255
#define __NR_migrate_pages 256
#define __NR_openat 257
#define __NR_mkdirat 258
#define __NR_mknodat 259
#define __NR_fchownat 260
#define __NR_futimesat 261
#define __NR_newfstatat 262
#define __NR_unlinkat 263
#define __NR_renameat 264
#define __NR_linkat 265
#define __NR_symlinkat 266
#define __NR_readlinkat 267
#define __NR_fchmodat 268
#define __NR_faccessat 269
#define __NR_pselect6 270
#define __NR_ppoll 271
#define __NR_unshare 272
#define __NR_set_robust_list 273
#define __NR_get_robust_list 274
#define __NR_splice 275
#define __NR_tee 276
#define __NR_sync_file_range 277
#define __NR_vmsplice 278
#define __NR_move_pages 279
#define __NR_utimensat 280
#define __NR_epoll_pwait 281
#define __NR_signalfd 282
#define __NR_timerfd_create 283
#define __NR_eventfd 284
#define __NR_fallocate 285
#define __NR_timerfd_settime 286
#define __NR_timerfd_gettime 287
#define __NR_accept4 288
#define __NR_signalfd4 289
#define __NR_eventfd2 290
#define __NR_epoll_create1 291
#define __NR_dup3 292
#define __NR_pipe2 293
#define __NR_inotify_init1 294
#define __NR_preadv 295
#define __NR_pwritev 296
#define __NR_rt_tgsigqueueinfo 297
#define __NR_perf_event_open 298
#define __NR_recvmmsg 299
#define __NR_fanotify_init 300
#define __NR_fanotify_mark 301
#define __NR_prlimit64 302
#define __NR_name_to_handle_at 303
#define __NR_open_by_handle_at 304
#define __NR_clock_adjtime 305
#define __NR_syncfs 306
#define __NR_sendmmsg 307
#define __NR_setns 308
#define __NR_getcpu 309
#define __NR_process_vm_readv 310
#define __NR_process_vm_writev 311
#define __NR_kcmp 312
#define __NR_finit_module 313
#define __NR_sched_setattr 314
#define __NR_sched_getattr 315
#define __NR_renameat2 316
#define __NR_seccomp 317
#define __NR_getrandom 318
#define __NR_memfd_create 319
#define __NR_kexec_file_load 320
#define __NR_bpf 321
#define __NR_execveat 322
#define __NR_userfaultfd 323
#define __NR_membarrier 324
#define __NR_mlock2 325
#define __NR_spawn 360
#endif /* __RUSGX_SYSCALL_NR_H__ */

12
src/pal/atomic.h Normal file

@ -0,0 +1,12 @@
#ifndef __ATOMIC_H_
#define __ATOMIC_H_
static inline int a_load(int* n) {
return *(volatile int*)n;
}
static inline int a_fetch_and_add(int* n, int a) {
return __sync_fetch_and_add(n, a);
}
#endif /* __ATOMIC_H_ */

32
src/pal/futex.c Normal file

@ -0,0 +1,32 @@
#include <stddef.h>
#include <sys/time.h>
#include <sys/syscall.h>
#include <limits.h>
#include <linux/futex.h>
static inline long __syscall6(long n, long a1, long a2, long a3, long a4, long a5, long a6)
{
unsigned long ret;
register long r10 __asm__("r10") = a4;
register long r8 __asm__("r8") = a5;
register long r9 __asm__("r9") = a6;
__asm__ __volatile__ ("syscall" : "=a"(ret) : "a"(n), "D"(a1), "S"(a2),
"d"(a3), "r"(r10), "r"(r8), "r"(r9) : "rcx", "r11", "memory");
return ret;
}
#define syscall(num, a1, a2, a3, a4, a5, a6) \
__syscall6((num), (long)(a1), (long)(a2), (long)(a3), (long)(a4), (long)(a5), (long)(a6))
static inline int futex(void *addr1, int op, int val1, struct timespec *timeout,
void *addr2, int val3) {
return (int) syscall(SYS_futex, addr1, op, val1, timeout, addr2, val3);
}
int futex_wait(int* uaddr, int val) {
return futex(uaddr, FUTEX_WAIT, val, NULL, NULL, 0);
}
int futex_wakeup(int* uaddr) {
return futex(uaddr, FUTEX_WAKE, INT_MAX, NULL, NULL, 0);
}

9
src/pal/futex.h Normal file

@ -0,0 +1,9 @@
#ifndef __FUTEX_H_
#define __FUTEX_H_
#include <sys/time.h>
int futex_wait(int* uaddr, int val);
int futex_wakeup(int* uaddr);
#endif /* __ATOMIC_H_ */

@ -4,13 +4,14 @@
#include <unistd.h> #include <unistd.h>
#include <pwd.h> #include <pwd.h>
#define MAX_PATH FILENAME_MAX #define MAX_PATH FILENAME_MAX
#include "sgx_urts.h" #include "sgx_urts.h"
#include "pal.h" #include "pal.h"
#include "task.h"
#include "Enclave_u.h" #include "Enclave_u.h"
sgx_enclave_id_t global_eid = 0; sgx_enclave_id_t global_eid = 0;
typedef struct _sgx_errlist_t { typedef struct _sgx_errlist_t {
@ -192,11 +193,17 @@ void ocall_print_string(const char* msg) {
printf("%s", msg); printf("%s", msg);
} }
int ocall_run_new_task(void) {
int ret = run_new_task(global_eid);
return ret;
}
/* Application entry */ /* Application entry */
int SGX_CDECL main(int argc, char *argv[]) int SGX_CDECL main(int argc, char *argv[])
{ {
sgx_status_t sgx_ret = SGX_SUCCESS; sgx_status_t sgx_ret = SGX_SUCCESS;
int exitcode = 0; int status = 0;
uint32_t sealed_log_size = 1024; uint32_t sealed_log_size = 1024;
uint8_t sealed_log[1024] = {0}; uint8_t sealed_log[1024] = {0};
@ -215,25 +222,16 @@ int SGX_CDECL main(int argc, char *argv[])
return -1; return -1;
} }
sgx_ret = libos_boot(global_eid, &exitcode, executable_path); sgx_ret = libos_boot(global_eid, &status, executable_path);
if(sgx_ret != SGX_SUCCESS) { if(sgx_ret != SGX_SUCCESS) {
print_error_message(sgx_ret); print_error_message(sgx_ret);
return -1; return -1;
} }
sgx_ret = libos_run(global_eid, &exitcode); status = wait_all_tasks();
if(sgx_ret != SGX_SUCCESS) {
print_error_message(sgx_ret);
return -1;
}
if(exitcode) {
printf("Program exits with error code %d...\n", exitcode);
return -1;
}
/* Destroy the enclave */ /* Destroy the enclave */
sgx_destroy_enclave(global_eid); sgx_destroy_enclave(global_eid);
return 0; return status;
} }

68
src/pal/task.c Normal file

@ -0,0 +1,68 @@
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include "atomic.h"
#include "futex.h"
#include "sgx_urts.h"
#include "Enclave_u.h"
static int num_tasks = 0;
static int main_task_status = 0;
static int BEGIN_TASK(void) {
return a_fetch_and_add(&num_tasks, 1) == 0;
}
static void END_TASK(void) {
if (a_fetch_and_add(&num_tasks, -1) == 1) {
futex_wakeup(&num_tasks);
}
}
struct task_thread_data {
int is_main_task;
sgx_enclave_id_t eid;
};
static void* __run_task_thread(void* _data) {
int status = 0;
struct task_thread_data* data = _data;
sgx_status_t sgx_ret = libos_run(data->eid, &status);
if(sgx_ret != SGX_SUCCESS) {
// TODO: deal with ECALL error
printf("ERROR: ECall libos_run failed\n");
}
if (data->is_main_task) main_task_status = status;
free(data);
END_TASK();
return NULL;
}
int run_new_task(sgx_enclave_id_t eid) {
int ret = 0;
pthread_t thread;
struct task_thread_data* data = malloc(sizeof(*data));
data->is_main_task = BEGIN_TASK();
data->eid = eid;
if ((ret = pthread_create(&thread, NULL, __run_task_thread, data)) < 0) {
free(data);
END_TASK();
return ret;
}
pthread_detach(thread);
return 0;
}
int wait_all_tasks(void) {
int cur_num_tasks;
while ((cur_num_tasks = a_load(&num_tasks)) != 0) {
futex_wait(&num_tasks, cur_num_tasks);
}
return main_task_status;
}

7
src/pal/task.h Normal file

@ -0,0 +1,7 @@
#ifndef __TASK_H_
#define __TASK_H_
int run_new_task(sgx_enclave_id_t eid);
int wait_all_tasks(void);
#endif /* __TASK_H_ */

@ -1,19 +1,49 @@
.PHONY: all build_rusgx_stub build_src clean test CUR_DIR := $(shell dirname $(realpath $(lastword $(MAKEFILE_LIST))))
PROJECT_DIR := $(realpath $(CUR_DIR)/../)
all: build_rusgx_stub build_src TEST_SUITES := hello_world_raw spawn_and_wait4_raw
BUILD_TEST_SUITES := $(TEST_SUITES:%=%)
RUN_TEST_SUITES := $(TEST_SUITES:%=run-%)
CLEAN_TEST_SUITES := $(TEST_SUITES:%=clean-%)
build_src: build_rusgx_stub .PHONY: all build test clean $(BUILD_TEST_SUITES) $(RUN_TEST_SUITES) $(CLEAN_TEST_SUITES)
@$(MAKE) -C src
#############################################################################
# Build tests
#############################################################################
all: build
build: build_rusgx_stub $(BUILD_TEST_SUITES)
build_rusgx_stub: build_rusgx_stub:
@$(MAKE) -C rusgx_stub @$(MAKE) -C rusgx_stub
test: all $(BUILD_TEST_SUITES): %:
@$(MAKE) -C src test @$(MAKE) -C $@
test-without-rusgx: all #############################################################################
@$(MAKE) -C src test-without-rusgx # Run tests
#############################################################################
clean: run: build $(RUN_TEST_SUITES)
pal: $(PROJECT_DIR)/src/pal/pal
cp $< pal
librusgx.signed.so: $(PROJECT_DIR)/src/libos/librusgx.signed.so
cp $< librusgx.signed.so
$(RUN_TEST_SUITES): run-%: % pal librusgx.signed.so
@$(MAKE) -C $< run
#############################################################################
# Misc
#############################################################################
clean: $(CLEAN_TEST_SUITES)
@$(MAKE) -C rusgx_stub clean @$(MAKE) -C rusgx_stub clean
@$(MAKE) -C src clean @$(RM) -f pal librusgx.signed.so
$(CLEAN_TEST_SUITES): clean-%:
@$(MAKE) -C $(patsubst clean-%,%,$@) clean

@ -0,0 +1,4 @@
include ../test_common.mk
EXTRA_C_FLAGS := -fno-builtin
EXTRA_LINK_FLAGS := -nostdlib

@ -20,17 +20,39 @@
* host syscalls provided by the default implementation of this library. * host syscalls provided by the default implementation of this library.
*/ */
#define SYS_exit 60
#define SYS_write 1 #define SYS_write 1
#define SYS_exit 60
#define SYS_wait4 61
#define SYS_spawn 360
long rusgx_syscall(int num, long arg0, long arg1, long arg2, long arg3, long arg4); long rusgx_syscall(int num, long arg0, long arg1, long arg2, long arg3, long arg4);
#define RUSGX_SYSCALL1(num, arg0) \
rusgx_syscall((num), (long)(arg0), (long)0, (long)0, (long)0, (long)0)
#define RUSGX_SYSCALL2(num, arg0, arg1) \
rusgx_syscall((num), (long)(arg0), (long)(arg1), (long)0, (long)0, (long)0)
#define RUSGX_SYSCALL3(num, arg0, arg1, arg2) \
rusgx_syscall((num), (long)(arg0), (long)(arg1), (long)(arg2), (long)0, (long)0)
#define RUSGX_SYSCALL4(num, arg0, arg1, arg2, arg3) \
rusgx_syscall((num), (long)(arg0), (long)(arg1), (long)(arg2), (long)(arg3), (long)0)
#define RUSGX_SYSCALL5(num, arg0, arg1, arg2, arg3, arg4) \
rusgx_syscall((num), (long)(arg0), (long)(arg1), (long)(arg2), (long)(arg3), (long)(arg4))
static inline ssize_t __rusgx_write(int fd, const void* buf, unsigned long size) { static inline ssize_t __rusgx_write(int fd, const void* buf, unsigned long size) {
return (ssize_t) rusgx_syscall(SYS_write, (long)fd, (long)buf, (long)size, (long)0, (long)0); return (ssize_t) RUSGX_SYSCALL3(SYS_write, fd, buf, size);
} }
static inline void __rusgx_exit(int status) { static inline void __rusgx_exit(int status) {
rusgx_syscall(SYS_exit, (long)status, (long)0, (long)0, (long)0, (long)0); RUSGX_SYSCALL1(SYS_exit, status);
}
static inline int __rusgx_spawn(int* child_pid, const char* path,
const char** argv, const char** envp) {
return (int) RUSGX_SYSCALL4(SYS_spawn, child_pid, path, argv, envp);
}
static inline int __rusgx_wait4(int child_pid, int* status, int options/*, struct rusage* rusage*/) {
return (int) RUSGX_SYSCALL3(SYS_wait4, child_pid, status, options);
} }
#endif /* __RUSGX_STUB__ */ #endif /* __RUSGX_STUB__ */

@ -0,0 +1,4 @@
include ../test_common.mk
EXTRA_C_FLAGS := -fno-builtin
EXTRA_LINK_FLAGS := -nostdlib

@ -0,0 +1,24 @@
#include "rusgx_stub.h"
static char success_str_buf[] = "A child process starts and exits!\n";
static unsigned long success_str_size = sizeof(success_str_buf);
static void print_ok(void) {
__rusgx_write(1, success_str_buf, success_str_size);
}
void _start(void) {
int ret = 0;
int pid = 0;
ret = __rusgx_spawn(&pid, "hello_world_raw/bin.encrypted", NULL, NULL);
if (ret < 0) { __rusgx_exit(0); }
/*
int status;
ret = __rusgx_wait4(pid, &status, 0);
if (ret < 0) { __rusgx_exit(0); }
*/
print_ok();
__rusgx_exit(0);
}

@ -1,13 +0,0 @@
#!/bin/bash
if [ $# -ne 1 ]; then
echo "ERROR: the number of given arguments is incorrect!"
echo
echo "./use_fs <assembly_file>"
exit -1
fi
S_FILE=$1
sed -i \
-e 's/str_size@GOTPCREL/%fs:&/g' \
-e 's/str_buf@GOTPCREL/%fs:&/g' \
${S_FILE}

@ -1,4 +1,6 @@
CUR_DIR := $(shell dirname $(realpath $(lastword $(MAKEFILE_LIST)))) MAIN_MAKEFILE := $(firstword $(MAKEFILE_LIST))
INCLUDE_MAKEFILE := $(lastword $(MAKEFILE_LIST))
CUR_DIR := $(shell dirname $(realpath $(MAIN_MAKEFILE)))
PROJECT_DIR := $(realpath $(CUR_DIR)/../../) PROJECT_DIR := $(realpath $(CUR_DIR)/../../)
C_SRCS := $(wildcard *.c) C_SRCS := $(wildcard *.c)
@ -9,18 +11,27 @@ BIN_ENC_NAME := bin.encrypted
OBJDUMP_FILE := bin.objdump OBJDUMP_FILE := bin.objdump
READELF_FILE := bin.readelf READELF_FILE := bin.readelf
C_FLAGS := -Wall -fno-builtin -fno-stack-protector -fverbose-asm -fpic C_FLAGS = -Wall -fno-stack-protector -fverbose-asm -fpic \
C_FLAGS += -I../include -L../rusgx_stub -lrusgx_stub -I../include -L../rusgx_stub -lrusgx_stub \
C_FLAGS += -O0 -O0 \
LINK_FLAGS := -pie -nostdlib -L../rusgx_stub -lrusgx_stub $(EXTRA_C_FLAGS)
LINK_FLAGS = -pie -L../rusgx_stub -lrusgx_stub \
$(EXTRA_LINK_FLAGS)
.PHONY: all clean test test-without-rusgx .PHONY: all run run-without-rusgx debug clean
############################################################################# #############################################################################
# Build # Build
############################################################################# #############################################################################
all: $(BIN_NAME) $(OBJDUMP_FILE) $(READELF_FILE) all: $(BIN_ENC_NAME)
$(BIN_ENC_NAME): $(BIN_NAME)
$(RM) -f $(BIN_ENC_NAME)
cd $(PROJECT_DIR)/deps/sgx_protect_file/ && \
./sgx_protect_file encrypt -i $(CUR_DIR)/$(BIN_NAME) -o $(CUR_DIR)/$(BIN_ENC_NAME) -k 123
debug: $(OBJDUMP_FILE) $(READELF_FILE)
$(OBJDUMP_FILE): $(BIN_NAME) $(OBJDUMP_FILE): $(BIN_NAME)
objdump -d $(BIN_NAME) > $(OBJDUMP_FILE) objdump -d $(BIN_NAME) > $(OBJDUMP_FILE)
@ -36,32 +47,20 @@ $(C_OBJS): %.o: %.S
$(S_FILES): %.S: %.c $(S_FILES): %.S: %.c
$(CC) $(C_FLAGS) -S $< -o $@ $(CC) $(C_FLAGS) -S $< -o $@
# ./override_ds_with_fs.sh $@
############################################################################# #############################################################################
# Test # Test
############################################################################# #############################################################################
test: pal librusgx.signed.so $(BIN_ENC_NAME) run: $(BIN_ENC_NAME)
RUST_BACKTRACE=1 ./pal ./bin.encrypted cd ../ && RUST_BACKTRACE=1 ./pal $(CUR_DIR)/$(BIN_ENC_NAME)
pal: run-without-rusgx:
cp $(PROJECT_DIR)/src/pal/pal pal cd ../ && LD_LIBRARY_PATH=./rusgx_stub/ ./$(BIN_NAME)
librusgx.signed.so:
cp $(PROJECT_DIR)/src/libos/librusgx.signed.so librusgx.signed.so
$(BIN_ENC_NAME): $(BIN_NAME)
$(RM) -f $(BIN_ENC_NAME)
cd $(PROJECT_DIR)/deps/sgx_protect_file/ && \
./sgx_protect_file encrypt -i $(CUR_DIR)/$(BIN_NAME) -o $(CUR_DIR)/$(BIN_ENC_NAME) -k 123
test-without-rusgx: $(BIN_ENC_NAME)
LD_LIBRARY_PATH=../rusgx_stub/ ./$(BIN_NAME)
############################################################################# #############################################################################
# Misc # Misc
############################################################################# #############################################################################
clean: clean:
$(RM) -f *.o *.S $(BIN_NAME) $(BIN_ENC_NAME) $(OBJDUMP_FILE) $(READELF_FILE) pal librusgx.signed.so $(RM) -f *.o *.S $(BIN_NAME) $(BIN_ENC_NAME) $(OBJDUMP_FILE) $(READELF_FILE)