static uint64_t start(struct tar_file *file, char const **argv) { int32_t pid; pid = fork(); if (pid < 0) { execiv(file->start, file->size, argv); abort(); } mwait(PORT_CHILD, pid); return RP_CONS(pid, 1); }
static uint64_t start(struct tar_file *file, char const **argv) { int32_t pid; pid = fork(); setenv("NAME", "unknown"); if (pid < 0) { execiv(file->start, file->size, argv); for(;;); } setenv("NAME", "init"); mwait(PORT_CHILD, RP_CONS(pid, 0)); return RP_CONS(pid, 0); }
int execv(const char *path, char const **argv) { void *image; image = load_exec(path); return execiv(image, msize(image), argv); }
int execi(uint8_t *image, size_t size) { return execiv(image, size, NULL); }
int main() { struct tar_file *boot_image, *file; char const **argv; uint64_t temp, temp1, temp2; argv = malloc(sizeof(char*) * 4); /* Boot Image */ boot_image = tar_parse((void*) BOOT_IMAGE); /* Dynamic Linker */ file = tar_find(boot_image, "lib/dl.so"); dl_load(file->start); /* Initial Root Filesystem / Device Filesystem / System Filesystem (tmpfs) */ argv[0] = "tmpfs"; argv[1] = NULL; file = tar_find(boot_image, "sbin/tmpfs"); fs_root = start(file, argv); io_cons("/dev", RP_TYPE_DIR); io_cons("/sys", RP_TYPE_DIR); /* Logfile */ io_cons("/dev/stderr", RP_TYPE_FILE); /* Init control file */ io_link("/sys/init", RP_CONS(getpid(), 1)); /* Keyboard Driver */ argv[0] = "kbd"; argv[1] = NULL; file = tar_find(boot_image, "sbin/kbd"); temp = start(file, argv); /* Terminal Driver */ argv[0] = "tty"; argv[1] = NULL; file = tar_find(boot_image, "sbin/tty"); temp = start(file, argv); io_link("/dev/tty", temp); /* Splash */ stdin = stderr = stdout = fopen("/dev/tty", "w"); printf(splash); /* Initrd */ initrd_init(); io_link("/dev/initrd", RP_CONS(getpid(), 0)); /* Root filesystem (tarfs) */ argv[0] = "tarfs"; argv[1] = "/dev/initrd"; argv[2] = NULL; file = tar_find(boot_image, "sbin/tarfs"); temp = start(file, argv); /* Link /dev and /sys and change root */ temp1 = io_find("/dev"); temp2 = io_find("/sys"); fs_root = temp; io_link("/dev", temp1); io_link("/sys", temp2); /* Temporary filesystem */ argv[0] = "tmpfs"; argv[1] = NULL; file = tar_find(boot_image, "sbin/tmpfs"); io_link("/tmp", start(file, argv)); /* Time Driver */ argv[0] = "time"; argv[1] = NULL; file = tar_find(boot_image, "sbin/time"); io_link("/dev/time", start(file, argv)); /* Serial Driver */ argv[0] = "serial"; argv[1] = NULL; file = tar_find(boot_image, "sbin/serial"); io_link("/dev/serial", start(file, argv)); /* Path */ setenv("PATH", "/bin"); /* Flux Init Shell */ argv[0] = "fish"; argv[1] = NULL; file = tar_find(boot_image, "bin/fish"); if (!file) { printf("critical error: no init shell found\n"); for(;;); } if (fork() < 0) { // setcuser(1); execiv(file->start, file->size, argv); } setenv("NAME", "init"); mwait(PORT_CHILD, 0); printf("INIT PANIC: system daemon died\n"); for(;;); return 0; }