summaryrefslogtreecommitdiff
path: root/src/user
diff options
context:
space:
mode:
authordzwdz2022-07-20 17:26:25 +0200
committerdzwdz2022-07-20 17:26:25 +0200
commitbc49ea97bb61bbe55af3e847a88a649d04a93777 (patch)
tree858fb9ed3427477405b0461241d6dcafd70a5892 /src/user
parentbdb25024a3fe0c8630fd68d9ba618df595effa36 (diff)
user/elf: free memory not belonging to the elf when jumping to it
Diffstat (limited to 'src/user')
-rw-r--r--src/user/lib/elfload.c17
1 files changed, 11 insertions, 6 deletions
diff --git a/src/user/lib/elfload.c b/src/user/lib/elfload.c
index 565dfa2..c32232e 100644
--- a/src/user/lib/elfload.c
+++ b/src/user/lib/elfload.c
@@ -62,6 +62,16 @@ static size_t elf_spread(const void *elf) {
return high - low;
}
+/* frees memory outside of [low; high] and jumps to *entry */
+static void freejmp(void *entry, void *low, void *high) {
+ uint64_t buf[] = {
+ EXECBUF_SYSCALL, _SYSCALL_MEMFLAG, 0, (uintptr_t)low, 0, 0,
+ EXECBUF_SYSCALL, _SYSCALL_MEMFLAG, (uintptr_t)high, ~0 - 0xF000 - (uintptr_t)high, 0, 0,
+ EXECBUF_JMP, (uintptr_t)entry,
+ };
+ _syscall_execbuf(buf, sizeof buf);
+}
+
void elf_exec(void *base) {
struct Elf64_Ehdr *ehdr = base;
void *exebase;
@@ -86,11 +96,6 @@ void elf_exec(void *base) {
return;
}
- uint64_t buf[] = {
- // TODO free lower memory
- //EXECBUF_SYSCALL, _SYSCALL_MEMFLAG, exebase + spread, ~0 - 0xF0000, 0, 0, // free upper memory
- EXECBUF_JMP, (uintptr_t)exebase + ehdr->e_entry,
- };
- _syscall_execbuf(buf, sizeof buf);
+ freejmp(exebase + ehdr->e_entry, exebase, exebase + spread + 0x1000);
printf("elf: execbuf failed?");
}