Paging works :3

This commit is contained in:
elfein 2021-11-22 06:58:35 -08:00
parent f749c89cfc
commit 218f700b22
5 changed files with 39 additions and 5 deletions

View file

@ -3,7 +3,7 @@ target = "./json_targets/x86_64-ableos.json"
[unstable] [unstable]
build-std-features = ["compiler-builtins-mem"] build-std-features = ["compiler-builtins-mem"]
build-std = ["core", "compiler_builtins"] build-std = ["core", "compiler_builtins", "alloc"]
[target.'cfg(target_arch = "x86_64")'] [target.'cfg(target_arch = "x86_64")']

View file

@ -1,3 +1,4 @@
use bootloader::bootinfo::{MemoryMap, MemoryRegionType};
use x86_64::{ use x86_64::{
structures::paging::{ structures::paging::{
FrameAllocator, Mapper, OffsetPageTable, Page, PageTable, PhysFrame, Size4KiB, FrameAllocator, Mapper, OffsetPageTable, Page, PageTable, PhysFrame, Size4KiB,
@ -79,3 +80,33 @@ unsafe impl FrameAllocator<Size4KiB> for EmptyFrameAllocator {
None None
} }
} }
pub struct BootInfoFrameAllocator {
memory_map: &'static MemoryMap,
next: usize,
}
impl BootInfoFrameAllocator {
pub unsafe fn init(memory_map: &'static MemoryMap) -> Self {
Self {
memory_map,
next: 0,
}
}
fn usable_frames(&self) -> impl Iterator<Item = PhysFrame> {
let regions = self.memory_map.iter();
let usable_regions = regions.filter(|r| r.region_type == MemoryRegionType::Usable);
let addr_range = usable_regions.map(|r| r.range.start_addr()..r.range.end_addr());
let frame_address = addr_range.flat_map(|r| r.step_by(4096));
frame_address.map(|addr| PhysFrame::containing_address(PhysAddr::new(addr)))
}
}
unsafe impl FrameAllocator<Size4KiB> for BootInfoFrameAllocator {
fn allocate_frame(&mut self) -> Option<PhysFrame<Size4KiB>> {
let frame = self.usable_frames().nth(self.next);
self.next += 1;
frame
}
}

View file

@ -57,13 +57,15 @@ pub fn kernel_main(boot_info: &'static BootInfo) -> ! {
let phys_mem_offset = VirtAddr::new(boot_info.physical_memory_offset); let phys_mem_offset = VirtAddr::new(boot_info.physical_memory_offset);
let mut mapper = unsafe { memory::init(phys_mem_offset) }; let mut mapper = unsafe { memory::init(phys_mem_offset) };
let mut frame_allocator = memory::EmptyFrameAllocator; let mut frame_allocator = unsafe {
memory::BootInfoFrameAllocator::init(&boot_info.memory_map)
};
let page = Page::containing_address(VirtAddr::new(0)); let page = Page::containing_address(VirtAddr::new(0xdeadbeaf000));
memory::create_example_mapping(page, &mut mapper, &mut frame_allocator); memory::create_example_mapping(page, &mut mapper, &mut frame_allocator);
let page_ptr: *mut u64 = page.start_address().as_mut_ptr(); let page_ptr: *mut u64 = page.start_address().as_mut_ptr();
unsafe { page_ptr.offset(400).write_volatile(0xf021_f077_f065_f04e) }; unsafe { page_ptr.offset(400).write_volatile(0xf021_f077_f065_804e) };
// stack_overflow(); // stack_overflow();
// crate::arch::shutdown(); // crate::arch::shutdown();

View file

@ -45,3 +45,4 @@ pub const RELEASE_TYPE: &str = "debug";
#[cfg(not(debug_assertions))] #[cfg(not(debug_assertions))]
/// A constant to check if the kernel is in release mode /// A constant to check if the kernel is in release mode
pub const RELEASE_TYPE: &str = "release"; pub const RELEASE_TYPE: &str = "release";
extern crate alloc;