mirror of
https://github.com/Mathewnd/Astral.git
synced 2026-10-27 20:58:22 +00:00
+15
-4
@@ -153,6 +153,10 @@ int elf_load(vnode_t *vnode, void *base, void **entry, char **interpreter, auxv6
|
||||
if (headerok(&header) == false)
|
||||
return ENOEXEC;
|
||||
|
||||
if (!base && header.type == ELF_SHARED) {
|
||||
base = (void *)0x400000;
|
||||
}
|
||||
|
||||
auxv64->null.type = AT_NULL;
|
||||
auxv64->phdr.type = AT_PHDR;
|
||||
auxv64->phnum.type = AT_PHNUM;
|
||||
@@ -161,7 +165,7 @@ int elf_load(vnode_t *vnode, void *base, void **entry, char **interpreter, auxv6
|
||||
|
||||
auxv64->phnum.val = header.phcount;
|
||||
auxv64->phent.val = header.phsize;
|
||||
auxv64->entry.val = header.entry;
|
||||
auxv64->entry.val = header.entry + (uintptr_t)base;
|
||||
*entry = (void *)(header.entry + (uintptr_t)base);
|
||||
|
||||
__assert(header.phsize == sizeof(elfph64_t));
|
||||
@@ -215,11 +219,12 @@ int elf_load(vnode_t *vnode, void *base, void **entry, char **interpreter, auxv6
|
||||
#define STACK_SIZE (1024 * 1024 * 4)
|
||||
#define STACK_TOP_BUFFER 8
|
||||
|
||||
void *elf_preparestack(void *top, auxv64list_t *auxv64, char **argv, char **envp) {
|
||||
void *elf_preparestack(void *top, auxv64list_t *auxv64, char **argv, char **envp, char *path) {
|
||||
size_t argc;
|
||||
size_t envc;
|
||||
size_t argdatasize = 0;
|
||||
size_t envdatasize = 0;
|
||||
size_t pathsize = strlen(path) + 1;
|
||||
|
||||
for (argc = 0; argv[argc]; ++argc)
|
||||
argdatasize += strlen(argv[argc]) + 1;
|
||||
@@ -231,7 +236,7 @@ void *elf_preparestack(void *top, auxv64list_t *auxv64, char **argv, char **envp
|
||||
int alignment = ((argc + 1) + (envc + 1) + 1) & 1 ? 8 : 0;
|
||||
|
||||
// env data + arg data + pointers to arg and env data + argc + buffer at the top
|
||||
size_t initialsize = argdatasize + envdatasize + (argc + envc) * sizeof(char *) + sizeof(size_t) + sizeof(auxv64list_t) + alignment + STACK_TOP_BUFFER;
|
||||
size_t initialsize = argdatasize + envdatasize + pathsize + (argc + envc) * sizeof(char *) + sizeof(size_t) + sizeof(auxv64list_t) + alignment + STACK_TOP_BUFFER;
|
||||
|
||||
size_t initialsizeround = ROUND_UP(initialsize, PAGE_SIZE);
|
||||
void *initialpagebase = (void *)((uintptr_t)top - initialsizeround);
|
||||
@@ -247,7 +252,8 @@ void *elf_preparestack(void *top, auxv64list_t *auxv64, char **argv, char **envp
|
||||
|
||||
char *argdatastart = (char *)((uintptr_t)top - argdatasize);
|
||||
char *envdatastart = (char *)((uintptr_t)argdatastart - envdatasize);
|
||||
auxv64list_t *auxvstart = (auxv64list_t *)envdatastart - 1;
|
||||
char *pathdatastart = (char *)((uintptr_t)envdatastart - pathsize);
|
||||
auxv64list_t *auxvstart = (auxv64list_t *)pathdatastart - 1;
|
||||
|
||||
auxvstart = (auxv64list_t *)(((uintptr_t)auxvstart & ~(uintptr_t)0xf) - alignment);
|
||||
|
||||
@@ -256,6 +262,11 @@ void *elf_preparestack(void *top, auxv64list_t *auxv64, char **argv, char **envp
|
||||
char **argstart = (char **)envstart - argc - 1;
|
||||
size_t *argcptr = (size_t *)argstart - 1;
|
||||
|
||||
auxv64->execfn.type = AT_EXECFN;
|
||||
auxv64->execfn.val = (uint64_t)pathdatastart;
|
||||
|
||||
memcpy(pathdatastart, path, pathsize);
|
||||
|
||||
memcpy(auxvstart, auxv64, sizeof(auxv64list_t));
|
||||
|
||||
for (int i = 0; i < argc; ++i) {
|
||||
|
||||
@@ -361,7 +361,7 @@ void proc_run_init() {
|
||||
char *argv[] = {"/init", cmdline_get("initarg"), NULL};
|
||||
char *envp[] = {NULL};
|
||||
|
||||
void *stack = elf_preparestack(STACK_TOP, &auxv64, argv, envp);
|
||||
void *stack = elf_preparestack(STACK_TOP, &auxv64, argv, envp, "/init");
|
||||
__assert(stack);
|
||||
|
||||
// reenter kernel context
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
#include <kernel/vmm.h>
|
||||
|
||||
#define CLOCK_REALTIME 0
|
||||
#define CLOCK_MONOTONIC 1
|
||||
#define CLOCK_BOOTTIME 7
|
||||
|
||||
syscallret_t syscall_clockget(context_t *, int clockid, timespec_t *tp) {
|
||||
@@ -19,6 +20,7 @@ syscallret_t syscall_clockget(context_t *, int clockid, timespec_t *tp) {
|
||||
ret.errno = 0;
|
||||
break;
|
||||
}
|
||||
case CLOCK_MONOTONIC:
|
||||
case CLOCK_BOOTTIME: {
|
||||
timespec_t ts = timekeeper_timefromboot();
|
||||
usercopy_touser(tp, &ts, sizeof(timespec_t));
|
||||
|
||||
@@ -258,7 +258,7 @@ static syscallret_t execve(context_t *context, char *upath, char *uargv[], char
|
||||
VOP_RELEASE(interpnode);
|
||||
}
|
||||
|
||||
stack = elf_preparestack(STACK_TOP, &auxv64, argv, envp);
|
||||
stack = elf_preparestack(STACK_TOP, &auxv64, argv, envp, path);
|
||||
if (stack == NULL) {
|
||||
ret.errno = ENOMEM;
|
||||
goto error;
|
||||
|
||||
@@ -9,6 +9,8 @@
|
||||
#define F_SETFD 2
|
||||
#define F_GETFL 3
|
||||
#define F_SETFL 4
|
||||
#define F_SETLK64 6
|
||||
#define F_SETLKW64 7
|
||||
|
||||
#define FD_CLOEXEC 1
|
||||
|
||||
@@ -52,6 +54,11 @@ syscallret_t syscall_fcntl(context_t *, int fd, int cmd, uint64_t arg) {
|
||||
ret.errno = fd_getflags(fd, &flg);
|
||||
ret.ret = flg ? FD_CLOEXEC : 0;
|
||||
break;
|
||||
case F_SETLK64:
|
||||
case F_SETLKW64:
|
||||
ret.errno = 0;
|
||||
ret.ret = 0;
|
||||
break;
|
||||
default:
|
||||
ret.errno = EINVAL;
|
||||
goto cleanup;
|
||||
|
||||
@@ -13,9 +13,10 @@
|
||||
#define MAP_FIXED 0x10
|
||||
#define MAP_ANON 0x20
|
||||
#define MAP_ANONYMOUS MAP_ANON
|
||||
#define MAP_NORESERVE 0x4000
|
||||
|
||||
#define KNOWN_PROT (PROT_READ | PROT_WRITE | PROT_EXEC)
|
||||
#define KNOWN_FLAGS (MAP_SHARED | MAP_PRIVATE | MAP_FIXED | MAP_ANONYMOUS)
|
||||
#define KNOWN_FLAGS (MAP_SHARED | MAP_PRIVATE | MAP_FIXED | MAP_ANONYMOUS | MAP_NORESERVE)
|
||||
|
||||
syscallret_t syscall_mmap(context_t *context, void *hint, size_t len, int prot, int flags, int fd, off_t offset) {
|
||||
syscallret_t ret = {
|
||||
|
||||
@@ -67,7 +67,7 @@ syscallret_t syscall_seek(context_t *context, int fd, off_t offset, int whence)
|
||||
}
|
||||
break;
|
||||
case SEEK_END:
|
||||
newoffset = size;
|
||||
newoffset = size + offset;
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user