summaryrefslogtreecommitdiff
path: root/src/init
diff options
context:
space:
mode:
Diffstat (limited to 'src/init')
-rw-r--r--src/init/fs/misc.c11
-rw-r--r--src/init/main.c6
-rw-r--r--src/init/shell.c2
-rw-r--r--src/init/syscalls.c8
-rw-r--r--src/init/tests/main.c32
5 files changed, 29 insertions, 30 deletions
diff --git a/src/init/fs/misc.c b/src/init/fs/misc.c
index ca3128d..f4965d5 100644
--- a/src/init/fs/misc.c
+++ b/src/init/fs/misc.c
@@ -6,9 +6,12 @@
#include <stdbool.h>
bool fork2_n_mount(const char *path) {
- handle_t h = _syscall_fs_fork2();
- if (h) _syscall_mount(h, path, strlen(path));
- return h;
+ handle_t h;
+ if (_syscall_fork(FORK_NEWFS, &h) > 0) { /* parent */
+ _syscall_mount(h, path, strlen(path));
+ return true;
+ }
+ return false;
}
static void fs_respond_delegate(struct fs_wait_response *res, handle_t delegate, const char *og_buf) {
@@ -53,7 +56,7 @@ static void fs_respond_delegate(struct fs_wait_response *res, handle_t delegate,
switch (res->op) {
case VFSOP_READ:
- if (_syscall_fork(FORK_NOREAP)) {
+ if (_syscall_fork(FORK_NOREAP, NULL)) {
// handle reads in a child
// this is a HORRIBLE workaround for making concurrent IO work without proper delegates
break;
diff --git a/src/init/main.c b/src/init/main.c
index a5323a3..06c267a 100644
--- a/src/init/main.c
+++ b/src/init/main.c
@@ -33,7 +33,7 @@ int main(void) {
file_close(&__stdout);
- if (_syscall_fork(0)) {
+ if (_syscall_fork(0, NULL)) {
/* (used to) expose a bug in the kernel
* the program will flow like this:
* 1. we launch the forked init
@@ -50,7 +50,7 @@ int main(void) {
_syscall_exit(1);
}
- if (!_syscall_fork(0)) {
+ if (!_syscall_fork(0, NULL)) {
if (file_open(&__stdout, "/com1") < 0 || file_open(&__stdin, "/com1") < 0)
_syscall_exit(1);
@@ -59,7 +59,7 @@ int main(void) {
}
- if (!_syscall_fork(0)) {
+ if (!_syscall_fork(0, NULL)) {
if (file_open(&__stdout, "/vga_tty") < 0)
_syscall_exit(1);
diff --git a/src/init/shell.c b/src/init/shell.c
index e7c836f..105231e 100644
--- a/src/init/shell.c
+++ b/src/init/shell.c
@@ -145,7 +145,7 @@ void shell_loop(void) {
} else if (!strcmp(cmd, "exit")) {
_syscall_exit(0);
} else if (!strcmp(cmd, "fork")) {
- if (_syscall_fork(0))
+ if (_syscall_fork(0, NULL))
_syscall_await();
else level++;
} else if (!strcmp(cmd, "run_tests")) {
diff --git a/src/init/syscalls.c b/src/init/syscalls.c
index daddde9..ed7420e 100644
--- a/src/init/syscalls.c
+++ b/src/init/syscalls.c
@@ -14,8 +14,8 @@ int _syscall_await(void) {
return _syscall(_SYSCALL_AWAIT, 0, 0, 0, 0);
}
-int _syscall_fork(int flags) {
- return _syscall(_SYSCALL_FORK, flags, 0, 0, 0);
+int _syscall_fork(int flags, handle_t __user *fs_front) {
+ return _syscall(_SYSCALL_FORK, flags, (int)fs_front, 0, 0);
}
handle_t _syscall_open(const char __user *path, int len) {
@@ -38,10 +38,6 @@ int _syscall_close(handle_t h) {
return _syscall(_SYSCALL_CLOSE, (int)h, 0, 0, 0);
}
-handle_t _syscall_fs_fork2(void) {
- return _syscall(_SYSCALL_FS_FORK2, 0, 0, 0, 0);
-}
-
int _syscall_fs_wait(char __user *buf, int max_len, struct fs_wait_response __user *res) {
return _syscall(_SYSCALL_FS_WAIT, (int)buf, max_len, (int)res, 0);
}
diff --git a/src/init/tests/main.c b/src/init/tests/main.c
index ac8874f..182c545 100644
--- a/src/init/tests/main.c
+++ b/src/init/tests/main.c
@@ -12,7 +12,7 @@
#define assert(cond) if (!(cond)) test_fail();
static void run_forked(void (*fn)()) {
- if (!_syscall_fork(0)) {
+ if (!_syscall_fork(0, NULL)) {
fn();
_syscall_exit(0);
} else {
@@ -31,7 +31,7 @@ static void test_await(void) {
int counts[16] = {0};
for (int i = 0; i < 16; i++)
- if (!_syscall_fork(0))
+ if (!_syscall_fork(0, NULL))
_syscall_exit(i);
while ((ret = _syscall_await()) != ~0) {
@@ -49,12 +49,12 @@ static void test_faults(void) {
* reap all its children */
int await_cnt = 0;
- if (!_syscall_fork(0)) { // invalid memory access
+ if (!_syscall_fork(0, NULL)) { // invalid memory access
asm volatile("movb $69, 0" ::: "memory");
printf("this shouldn't happen");
_syscall_exit(-1);
}
- if (!_syscall_fork(0)) { // #GP
+ if (!_syscall_fork(0, NULL)) { // #GP
asm volatile("hlt" ::: "memory");
printf("this shouldn't happen");
_syscall_exit(-1);
@@ -65,36 +65,36 @@ static void test_faults(void) {
}
static void test_interrupted_fs(void) {
- handle_t h = _syscall_fs_fork2();
- if (h) {
- _syscall_mount(h, "/", 1);
- int ret = _syscall_open("/", 1);
- // the handler quits while handling that call - but this syscall should return anyways
- _syscall_exit(ret < 0 ? 0 : -1);
- } else {
+ handle_t h;
+ if (_syscall_fork(FORK_NEWFS, &h)) { /* child */
// TODO make a similar test with all 0s passed to fs_wait
struct fs_wait_response res;
_syscall_fs_wait(NULL, 0, &res);
_syscall_exit(0);
+ } else { /* parent */
+ _syscall_mount(h, "/", 1);
+ int ret = _syscall_open("/", 1);
+ // the handler quits while handling that call - but this syscall should return anyways
+ _syscall_exit(ret < 0 ? 0 : -1);
}
}
static void test_orphaned_fs(void) {
- handle_t h = _syscall_fs_fork2();
- if (h) {
+ handle_t h;
+ if (_syscall_fork(FORK_NEWFS, &h)) { /* child */
+ _syscall_exit(0);
+ } else { /* parent */
_syscall_mount(h, "/", 1);
int ret = _syscall_open("/", 1);
// no handler will ever be available to handle this call - the syscall should instantly return
_syscall_exit(ret < 0 ? 0 : -1);
- } else {
- _syscall_exit(0);
}
}
static void stress_fork(void) {
/* run a lot of processes */
for (size_t i = 0; i < 2048; i++) {
- if (!_syscall_fork(0)) _syscall_exit(0);
+ if (!_syscall_fork(0, NULL)) _syscall_exit(0);
_syscall_await();
}
}