feat(paging): map kernel using elf section flags
Signed-off-by: Julien CLEMENT <julien.clement@epita.fr>
This commit is contained in:
parent
5e994b9dff
commit
5ff8596233
17
src/lib.rs
17
src/lib.rs
@ -12,6 +12,8 @@ extern crate multiboot2;
|
|||||||
|
|
||||||
use core::panic::PanicInfo;
|
use core::panic::PanicInfo;
|
||||||
use vga::{Color, ColorCode};
|
use vga::{Color, ColorCode};
|
||||||
|
use memory::paging::{Size4KiB, FrameAllocator};
|
||||||
|
use multiboot2::BootInformation;
|
||||||
|
|
||||||
#[panic_handler]
|
#[panic_handler]
|
||||||
fn panic_handler(info: &PanicInfo) -> ! {
|
fn panic_handler(info: &PanicInfo) -> ! {
|
||||||
@ -26,14 +28,24 @@ pub fn hlt_loop() -> ! {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn init() {
|
pub fn init<A>(frame_allocator: &mut A, boot_info: &BootInformation)
|
||||||
|
where A: FrameAllocator<Size4KiB>
|
||||||
|
{
|
||||||
vga::change_color(ColorCode::new(Color::LightCyan, Color::Black));
|
vga::change_color(ColorCode::new(Color::LightCyan, Color::Black));
|
||||||
println!("Starting init");
|
println!("Starting init");
|
||||||
|
enable_nxe_bit();
|
||||||
|
memory::kernel_remap(frame_allocator, boot_info);
|
||||||
gdt::init_gdt();
|
gdt::init_gdt();
|
||||||
interrupts::init_idt();
|
interrupts::init_idt();
|
||||||
vga::change_color(ColorCode::new(Color::LightGreen, Color::Black));
|
vga::change_color(ColorCode::new(Color::LightGreen, Color::Black));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn enable_nxe_bit() {
|
||||||
|
println!("Enabling nxe bit");
|
||||||
|
use x86_64::registers::control::{Efer, EferFlags};
|
||||||
|
unsafe { Efer::update(|efer| *efer |= EferFlags::NO_EXECUTE_ENABLE) }
|
||||||
|
}
|
||||||
|
|
||||||
fn get_frame_allocator(multiboot_info_addr: usize) -> memory::AreaFrameAllocator {
|
fn get_frame_allocator(multiboot_info_addr: usize) -> memory::AreaFrameAllocator {
|
||||||
let boot_info = unsafe { multiboot2::load(multiboot_info_addr) };
|
let boot_info = unsafe { multiboot2::load(multiboot_info_addr) };
|
||||||
let memory_map_tag = boot_info.memory_map_tag().expect("Memory map tag required");
|
let memory_map_tag = boot_info.memory_map_tag().expect("Memory map tag required");
|
||||||
@ -62,9 +74,8 @@ pub extern "C" fn julios_main(multiboot_info_addr: usize) -> ! {
|
|||||||
|
|
||||||
let mut frame_allocator = get_frame_allocator(multiboot_info_addr);
|
let mut frame_allocator = get_frame_allocator(multiboot_info_addr);
|
||||||
|
|
||||||
memory::kernel_remap(&mut frame_allocator, boot_info);
|
|
||||||
|
|
||||||
init();
|
init(&mut frame_allocator, &boot_info);
|
||||||
println!("***JuliOS V0.1.0***");
|
println!("***JuliOS V0.1.0***");
|
||||||
serial_println!("Hello serial");
|
serial_println!("Hello serial");
|
||||||
memory::paging::test_paging(&mut frame_allocator);
|
memory::paging::test_paging(&mut frame_allocator);
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
use multiboot2::BootInformation;
|
use multiboot2::{BootInformation, ElfSection};
|
||||||
pub use x86_64::structures::paging::{FrameAllocator, Size4KiB, PageTable, RecursivePageTable, Page, PageTableFlags as Flags, Mapper, PhysFrame as Frame};
|
pub use x86_64::structures::paging::{FrameAllocator, Size4KiB, PageTable, RecursivePageTable, Page, PageTableFlags as Flags, Mapper, PhysFrame as Frame};
|
||||||
use crate::println;
|
use crate::println;
|
||||||
use x86_64::{VirtAddr, PhysAddr};
|
use x86_64::{VirtAddr, PhysAddr};
|
||||||
@ -10,9 +10,29 @@ mod temporary_page;
|
|||||||
|
|
||||||
pub const P4: *mut PageTable = 0o177777_777_777_777_777_0000 as *mut _;
|
pub const P4: *mut PageTable = 0o177777_777_777_777_777_0000 as *mut _;
|
||||||
|
|
||||||
|
fn get_flags_from_elf_section(section: &ElfSection) -> Flags {
|
||||||
|
use multiboot2::{ELF_SECTION_ALLOCATED, ELF_SECTION_WRITABLE,
|
||||||
|
ELF_SECTION_EXECUTABLE};
|
||||||
|
|
||||||
|
let mut flags = Flags::empty();
|
||||||
|
|
||||||
|
if section.flags().contains(ELF_SECTION_ALLOCATED) {
|
||||||
|
flags = flags | Flags::PRESENT;
|
||||||
|
}
|
||||||
|
if section.flags().contains(ELF_SECTION_WRITABLE) {
|
||||||
|
flags = flags | Flags::WRITABLE;
|
||||||
|
}
|
||||||
|
if !section.flags().contains(ELF_SECTION_EXECUTABLE) {
|
||||||
|
flags = flags | Flags::NO_EXECUTE;
|
||||||
|
}
|
||||||
|
|
||||||
|
flags
|
||||||
|
}
|
||||||
|
|
||||||
pub fn kernel_remap<A>(allocator: &mut A, boot_info: &BootInformation)
|
pub fn kernel_remap<A>(allocator: &mut A, boot_info: &BootInformation)
|
||||||
where A: FrameAllocator<Size4KiB>
|
where A: FrameAllocator<Size4KiB>
|
||||||
{
|
{
|
||||||
|
println!("Remapping kernel");
|
||||||
let mut temporary_page = TemporaryPage::new(Page::containing_address(VirtAddr::new(0xcafebabe)), allocator);
|
let mut temporary_page = TemporaryPage::new(Page::containing_address(VirtAddr::new(0xcafebabe)), allocator);
|
||||||
let mut active_table = get_active_page_table();
|
let mut active_table = get_active_page_table();
|
||||||
let mut new_table = {
|
let mut new_table = {
|
||||||
@ -33,7 +53,7 @@ pub fn kernel_remap<A>(allocator: &mut A, boot_info: &BootInformation)
|
|||||||
"sections need to be page aligned");
|
"sections need to be page aligned");
|
||||||
|
|
||||||
|
|
||||||
let flags = Flags::WRITABLE | Flags::PRESENT;
|
let flags = get_flags_from_elf_section(section);
|
||||||
|
|
||||||
let start_frame = Frame::<Size4KiB>::containing_address(PhysAddr::new(section.start_address() as u64));
|
let start_frame = Frame::<Size4KiB>::containing_address(PhysAddr::new(section.start_address() as u64));
|
||||||
let end_frame = Frame::containing_address(PhysAddr::new(section.end_address() as u64 - 1));
|
let end_frame = Frame::containing_address(PhysAddr::new(section.end_address() as u64 - 1));
|
||||||
@ -129,7 +149,5 @@ pub fn test_paging<A>(allocator: &mut A)
|
|||||||
let page_ptr: *mut u8 = page.start_address().as_mut_ptr();
|
let page_ptr: *mut u8 = page.start_address().as_mut_ptr();
|
||||||
let frame_ptr: *mut u8 = frame.start_address().as_u64() as *mut u8;
|
let frame_ptr: *mut u8 = frame.start_address().as_u64() as *mut u8;
|
||||||
|
|
||||||
unsafe {
|
|
||||||
println!("Page: {:#?}, Frame: {:#?}", page_ptr, frame_ptr);
|
println!("Page: {:#?}, Frame: {:#?}", page_ptr, frame_ptr);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
Loading…
Reference in New Issue
Block a user