Add support for mapping new pages
This commit is contained in:
parent
15d14ed67f
commit
e51b3a53e7
21
src/main.rs
21
src/main.rs
|
@ -29,7 +29,6 @@ fn init() {
|
|||
#[no_mangle]
|
||||
pub extern "C" fn _start(boot_info: &'static BootInfo) {
|
||||
use crate::vga_buffer::{change_color, Color};
|
||||
use x86_64::{VirtAddr, structures::paging::Translate};
|
||||
|
||||
init();
|
||||
print!("[ ");
|
||||
|
@ -38,26 +37,6 @@ pub extern "C" fn _start(boot_info: &'static BootInfo) {
|
|||
change_color(Color::White, Color::Black);
|
||||
println!(" ] Initialized GDT and interrupts");
|
||||
|
||||
let phys_mem_offset = VirtAddr::new(boot_info.physical_memory_offset);
|
||||
let mapper = unsafe { memory::init(phys_mem_offset) };
|
||||
|
||||
let addresses = [
|
||||
// the identity-mapped vga buffer page
|
||||
0xb8000,
|
||||
// some code page
|
||||
0x201008,
|
||||
// some stack page
|
||||
0x0100_0020_1a10,
|
||||
// virtual address mapped to physical address 0
|
||||
boot_info.physical_memory_offset,
|
||||
];
|
||||
|
||||
for &address in &addresses {
|
||||
let virt = VirtAddr::new(address);
|
||||
let phys = mapper.translate_addr(virt);
|
||||
println!("{:?} -> {:?}", virt, phys);
|
||||
}
|
||||
|
||||
print!("Welcome to ");
|
||||
change_color(Color::Blue, Color::Black);
|
||||
println!("KarxOS!");
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
use x86_64::{VirtAddr, structures::paging::{PageTable, OffsetPageTable}};
|
||||
use x86_64::{PhysAddr, VirtAddr, structures::paging::{FrameAllocator, Mapper, OffsetPageTable, Page, PageTable, PhysFrame, Size4KiB}};
|
||||
use bootloader::bootinfo::{MemoryMap, MemoryRegionType};
|
||||
|
||||
pub unsafe fn init(physical_memory_offset: VirtAddr) -> OffsetPageTable<'static> {
|
||||
let level_4_table = active_level_4_table(physical_memory_offset);
|
||||
|
@ -16,3 +17,33 @@ unsafe fn active_level_4_table(physical_memory_offset: VirtAddr) -> &'static mut
|
|||
|
||||
&mut *page_table_ptr
|
||||
}
|
||||
|
||||
pub struct BootInfoFrameAllocator {
|
||||
memory_map: &'static MemoryMap,
|
||||
next: usize,
|
||||
}
|
||||
|
||||
impl BootInfoFrameAllocator {
|
||||
pub unsafe fn init(memory_map: &'static MemoryMap) -> Self {
|
||||
BootInfoFrameAllocator {
|
||||
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_ranges = usable_regions.map(|r| r.range.start_addr()..r.range.end_addr());
|
||||
let frame_addresses = addr_ranges.flat_map(|r| r.step_by(4096));
|
||||
frame_addresses.map(|addr| PhysFrame::containing_address(PhysAddr::new(addr)))
|
||||
}
|
||||
}
|
||||
|
||||
unsafe impl FrameAllocator<Size4KiB> for BootInfoFrameAllocator {
|
||||
fn allocate_frame(&mut self) -> Option<PhysFrame> {
|
||||
let frame = self.usable_frames().nth(self.next);
|
||||
self.next += 1;
|
||||
frame
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue