diff --git a/libmaxsi/include/unistd.h b/libmaxsi/include/unistd.h index 49f2c160..527edd41 100644 --- a/libmaxsi/include/unistd.h +++ b/libmaxsi/include/unistd.h @@ -32,6 +32,14 @@ #include #include +/* BSD compatibility: The problem with RFMEM is that isn't default to share, but + default to make a copy. However, Sortix rforks wants to make sharing default + and forking only happens if you ask for it. The Sortix RFFMEM extension + reverses this logic. */ +#if defined(RFMEM) && !defined(_BSD_SOURCE) && !defined(_WANT_RFMEM) +#undef RFMEM +#endif + #define _SORTIX_ALWAYS_SBRK __BEGIN_DECLS @@ -51,8 +59,6 @@ __BEGIN_DECLS @include(NULL.h) -/* TODO: F_OK, R_OK, W_OK, X_OK is missing here. */ - /* TODO: _CS_* is missing here. */ /* TODO: F_* is missing here. */ @@ -184,6 +190,7 @@ size_t pwriteall(int fd, const void* buf, size_t count, off_t off); size_t pwriteleast(int fd, const void* buf, size_t least, size_t max, off_t off); size_t readall(int fd, void* buf, size_t count); size_t readleast(int fd, void* buf, size_t least, size_t max); +pid_t rfork(int flags); int uptime(uintmax_t* usecssinceboot); size_t writeall(int fd, const void* buf, size_t count); size_t writeleast(int fd, const void* buf, size_t least, size_t max); diff --git a/libmaxsi/process.cpp b/libmaxsi/process.cpp index 284e0e60..ab624d41 100644 --- a/libmaxsi/process.cpp +++ b/libmaxsi/process.cpp @@ -35,6 +35,7 @@ namespace Maxsi DEFN_SYSCALL1_VOID(SysExit, SYSCALL_EXIT, int); DEFN_SYSCALL3(int, SysExecVE, SYSCALL_EXEC, const char*, char* const*, char* const*); DEFN_SYSCALL0(pid_t, SysFork, SYSCALL_FORK); + DEFN_SYSCALL1(pid_t, SysRFork, SYSCALL_RFORK, int); DEFN_SYSCALL0(pid_t, SysGetPID, SYSCALL_GETPID); DEFN_SYSCALL0(pid_t, SysGetParentPID, SYSCALL_GETPPID); DEFN_SYSCALL3(pid_t, SysWait, SYSCALL_WAIT, pid_t, int*, int); @@ -77,6 +78,11 @@ namespace Maxsi return SysFork(); } + extern "C" int rfork(int flags) + { + return SysRFork(flags); + } + DUAL_FUNCTION(pid_t, getpid, GetPID, ()) { return SysGetPID(); diff --git a/sortix/include/sortix/syscallnum.h b/sortix/include/sortix/syscallnum.h index f88e4e1d..b5b0ccf5 100644 --- a/sortix/include/sortix/syscallnum.h +++ b/sortix/include/sortix/syscallnum.h @@ -74,7 +74,8 @@ #define SYSCALL_KERNELINFO 48 #define SYSCALL_PREAD 49 #define SYSCALL_PWRITE 50 -#define SYSCALL_MAX_NUM 51 /* index of highest constant + 1 */ +#define SYSCALL_RFORK 51 +#define SYSCALL_MAX_NUM 52 /* index of highest constant + 1 */ #endif diff --git a/sortix/include/sortix/unistd.h b/sortix/include/sortix/unistd.h index a163fcaf..443b0003 100644 --- a/sortix/include/sortix/unistd.h +++ b/sortix/include/sortix/unistd.h @@ -34,6 +34,17 @@ __BEGIN_DECLS #define X_OK 1 /* Test for execute permission. */ #define F_OK 0 /* Test for existence. */ +#define RFCLONE (1<<0) /* Creates child, otherwise affect current process. */ +#define RFPID (1<<1) /* Allocates new PID. */ +#define RFFDG (1<<2) /* Fork file descriptor table. */ +#define RFMEM (1<<3) /* Shares address space. */ +#define RFFMEM (1<<4) /* Forks address space. */ +#define RFCWD (1<<5) /* Forks current directory pointer. */ +#define RFNS (1<<6) /* Forks namespace. */ + +#define RFPROC (RFCLONE | RFPID | RFFMEM | RFCWD) /* Create new process. */ +#define RFFORK (RFPROC | RFFDG) /* Traditional fork(2) behavior. */ + __END_DECLS #endif diff --git a/sortix/process.cpp b/sortix/process.cpp index b79061b5..64100138 100644 --- a/sortix/process.cpp +++ b/sortix/process.cpp @@ -23,6 +23,7 @@ ******************************************************************************/ #include +#include #include #include #include @@ -431,8 +432,11 @@ namespace Sortix return SysExevVEStage2(state); } - pid_t SysFork() + pid_t SysRFork(int flags) { + // TODO: Properly support rfork(2). + if ( flags != RFFORK ) { Error::Set(ENOSYS); return -1; } + // Prepare the state of the clone. Syscall::SyscallRegs()->result = 0; CurrentThread()->SaveRegisters(Syscall::InterruptRegs()); @@ -443,6 +447,11 @@ namespace Sortix return clone->pid; } + pid_t SysFork() + { + return SysRFork(RFFORK); + } + pid_t SysGetPID() { return CurrentProcess()->pid; @@ -746,6 +755,7 @@ namespace Sortix { Syscall::Register(SYSCALL_EXEC, (void*) SysExecVE); Syscall::Register(SYSCALL_FORK, (void*) SysFork); + Syscall::Register(SYSCALL_RFORK, (void*) SysRFork); Syscall::Register(SYSCALL_GETPID, (void*) SysGetPID); Syscall::Register(SYSCALL_GETPPID, (void*) SysGetParentPID); Syscall::Register(SYSCALL_EXIT, (void*) SysExit);