From: Amelia Coutard Date: Thu, 13 Oct 2022 14:47:08 +0000 (+0200) Subject: Made ftl_to_userspace jump to a loaded module at linear address 0x1000, instead of... X-Git-Url: https://git.ameliathe1st.gay/?a=commitdiff_plain;h=aab73ccaa51c082e412aeaf66a4bfe5091494da7;p=voyage-au-centre-des-fichiers.git Made ftl_to_userspace jump to a loaded module at linear address 0x1000, instead of a function in the higher-half --- diff --git a/grub.cfg b/grub.cfg index 8eccea2..11f6906 100644 --- a/grub.cfg +++ b/grub.cfg @@ -1,3 +1,4 @@ menuentry "Amycros" { multiboot2 /boot/kernel.elf64 + module2 /boot/test-module test-module } diff --git a/src/boot.S b/src/boot.S index fe2f52f..cd329af 100644 --- a/src/boot.S +++ b/src/boot.S @@ -17,6 +17,11 @@ multiboot_header_start: .int 0 .int 0 .int 32 + /* Modules alignment tag: */ + .align 8 + .short 6 + .short 0 + .int 8 /* End tag: */ .align 8 .short 0 diff --git a/src/kernel.cpp b/src/kernel.cpp index 76d5167..c48b654 100644 --- a/src/kernel.cpp +++ b/src/kernel.cpp @@ -20,6 +20,10 @@ extern "C" void kmain(unsigned long magic, os::phys_ptr start_address = nullptr; + os::phys_ptr end_address = nullptr; + } test_module; { struct { os::phys_ptr start_address = nullptr; @@ -45,17 +49,27 @@ extern "C" void kmain(unsigned long magic, os::phys_ptr"); + os::print(multiboot2::modules_mod_end(it) / 0x1000 * 0x1000); + os::print(": "); + os::print(multiboot2::modules_string(it)); + os::printc('\n'); + test_module.start_address = os::phys_ptr(multiboot2::modules_mod_start(it) / 0x1000 * 0x1000); + test_module.end_address = os::phys_ptr(multiboot2::modules_mod_end(it) / 0x1000 * 0x1000); // [s,e], not [s,e[ + break; default: break; } } // kernel_start and kernel_end are aligned to 4K by the linker script. - const os::phys_ptr s = ([]() { + const os::phys_ptr kernel_s = ([]() { os::phys_ptr ptr = nullptr; asm("mov $_kernel_phys_start,%0" : "=ri"(ptr)); return ptr; })(); - const os::phys_ptr e = ([]() { + const os::phys_ptr kernel_e = ([]() { os::phys_ptr ptr = nullptr; asm("mov $_kernel_phys_end,%0" : "=ri"(ptr)); return ptr - 1; // [s, e], not [s, e[ @@ -63,20 +77,41 @@ extern "C" void kmain(unsigned long magic, os::phys_ptrcontents[0].page.P = false; - get_base_address(PML4T.contents[0])->contents[1].page.P = false; + // Unmap low RAM, and free corresponding page. PML4T.contents[0].P = false; + os::paging::page_allocator.deallocate({.ptr = os::phys_ptr(get_base_address(PML4T.contents[0]).get_phys_addr()), .size = 1}); + os::paging::page_allocator.print_all(); + // Map test_module to virtual address 0x0000'0000'0000'1000. + { + os::phys_ptr PT {os::paging::page_allocator.allocate(1).ptr.get_phys_addr()}; + os::phys_ptr PDT {os::paging::page_allocator.allocate(1).ptr.get_phys_addr()}; + os::phys_ptr PDPT{os::paging::page_allocator.allocate(1).ptr.get_phys_addr()}; + PML4T.contents[0] = { .P = 1, .R_W = 0, .U_S = 1, .PWT = 0, .PCD = 0, .base_address = 0, .NX = 0}; + PDPT->contents[0] = {.non_page = {.P = 1, .R_W = 0, .U_S = 1, .PWT = 0, .PCD = 0, .base_address = 0, .NX = 0}}; + PDT->contents[0] = {.non_page = {.P = 1, .R_W = 0, .U_S = 1, .PWT = 0, .PCD = 0, .base_address = 0, .NX = 0}}; + PT->contents[1] = { .P = 1, .R_W = 0, .U_S = 1, .PWT = 0, .PCD = 0, .PAT = 0, .G = 0, .base_address = 0, .NX = 0}; + set_base_address(PML4T.contents[0], PDPT); + set_base_address(PDPT->contents[0], PDT); + set_base_address(PDT->contents[0], PT); + set_page_base_address(PT->contents[1], test_module.start_address); + } + asm volatile("invlpg (%0)" ::"r" (0x1000) : "memory"); + + os::paging::on_all_pages(PML4T, [](os::paging::page* virt, os::phys_ptr phys, std::size_t size) { + if (std::uint64_t(virt) >= 0xFFFF'8000'0000'0000) { + return; + } + os::print(std::uint64_t(virt)); + os::print("->"); + os::print(std::uint64_t(phys.get_phys_addr())); + os::print(" ("); + os::print(size); + os::print(")\n"); + }); // Allow userspaaaaaaaaace in ring 3. Otherwise, we just immediately page fault. // Will make it a module soon-ish. @@ -152,13 +215,3 @@ extern "C" void kmain(unsigned long magic, os::phys_ptr ptr, std::size_t index) { return *reinterpret_cast(&ptr->rest[8 + memory_map_entry_size(ptr) * index + 16]); } + + inline std::uint32_t modules_mod_start(os::phys_ptr ptr) { + return *reinterpret_cast(&ptr->rest[0]); + } + inline std::uint32_t modules_mod_end(os::phys_ptr ptr) { + return *reinterpret_cast(&ptr->rest[4]); + } + inline const char* modules_string(os::phys_ptr ptr) { + return reinterpret_cast(&ptr->rest[8]); + } #endif // __cplusplus #ifdef __cplusplus diff --git a/src/ring3.S b/src/ring3.S index 3e21c2e..48bf822 100644 --- a/src/ring3.S +++ b/src/ring3.S @@ -2,7 +2,7 @@ .globl ftl_to_userspace ftl_to_userspace: - mov $userspaaaaaaaaace, %rcx + mov $0x1000, %rcx mov $0x202, %r11 # EFLAGS sysretq @@ -19,9 +19,3 @@ load_tss: mov $GDT.TSS, %ax ltr %ax ret - -.globl syscall -syscall: - mov %rcx, %r10 - syscall - ret