diff --git a/kernel/.cargo/config.toml b/kernel/.cargo/config.toml index 98ee5ed..712c292 100644 --- a/kernel/.cargo/config.toml +++ b/kernel/.cargo/config.toml @@ -1,3 +1,3 @@ [build] target = "x86_64-unknown-none" -rustflags = ["-C", "link-arg=link.ld"] +rustflags = ["-C", "link-arg=link.ld", "-C", "link-arg=-no-pie"] diff --git a/kernel/Cargo.lock b/kernel/Cargo.lock index 97c0833..9db4e13 100644 --- a/kernel/Cargo.lock +++ b/kernel/Cargo.lock @@ -2,6 +2,74 @@ # It is not intended for manual editing. version = 3 +[[package]] +name = "bit_field" +version = "0.10.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dc827186963e592360843fb5ba4b973e145841266c1357f7180c43526f2e5b61" + +[[package]] +name = "bitflags" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" + +[[package]] +name = "com_logger" +version = "0.1.1" +source = "git+https://git.strypsteen.com/mathieu/com_logger#2dc5c9d0fd04e3e9102f0dbed25187761cf07525" +dependencies = [ + "log", + "uart_16550", +] + [[package]] name = "kernel" version = "0.0.1" +dependencies = [ + "com_logger", + "log", +] + +[[package]] +name = "log" +version = "0.4.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a7a70ba024b9dc04c27ea2f0c0548feb474ec5c54bba33a7f72f873a39d07b24" + +[[package]] +name = "raw-cpuid" +version = "10.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c297679cb867470fa8c9f67dbba74a78d78e3e98d7cf2b08d6d71540f797332" +dependencies = [ + "bitflags", +] + +[[package]] +name = "rustversion" +version = "1.0.17" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "955d28af4278de8121b7ebeb796b6a45735dc01436d898801014aced2773a3d6" + +[[package]] +name = "uart_16550" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6dc00444796f6c71f47c85397a35e9c4dbf9901902ac02386940d178e2b78687" +dependencies = [ + "bitflags", + "rustversion", + "x86", +] + +[[package]] +name = "x86" +version = "0.52.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2781db97787217ad2a2845c396a5efe286f87467a5810836db6d74926e94a385" +dependencies = [ + "bit_field", + "bitflags", + "raw-cpuid", +] diff --git a/kernel/Cargo.toml b/kernel/Cargo.toml index 831a26b..c00bf4e 100644 --- a/kernel/Cargo.toml +++ b/kernel/Cargo.toml @@ -4,3 +4,5 @@ version = "0.0.1" edition = "2021" [dependencies] +com_logger = { git = "https://git.strypsteen.com/mathieu/com_logger", version = "0.1.1" } +log = "0.4.22" diff --git a/kernel/src/main.rs b/kernel/src/main.rs index 3289e15..f1f2bd1 100644 --- a/kernel/src/main.rs +++ b/kernel/src/main.rs @@ -1,14 +1,26 @@ #![no_std] #![no_main] -use core::panic::PanicInfo; +use core::{arch::asm, panic::PanicInfo}; + +use log::{error, info}; + +static mut STACK: [u8; 8 * 1024] = [0; 8 * 1024]; #[no_mangle] -fn _start() { +fn _start() -> ! { + unsafe { + asm!("mov rsp, {}", in(reg) STACK.as_ptr().add(STACK.len())); + } + main(); +} +fn main() -> ! { + com_logger::init(); + info!("Starting kernel..."); loop {} } - #[panic_handler] -fn panic(_info: &PanicInfo) -> ! { +fn panic(info: &PanicInfo) -> ! { + error!("{}", info); loop {} } diff --git a/loader/src/elf.rs b/loader/src/elf.rs index c608257..165eb8c 100644 --- a/loader/src/elf.rs +++ b/loader/src/elf.rs @@ -6,9 +6,9 @@ use uefi::table::{ Boot, SystemTable, }; -const KERNEL_VIRT_START: u64 = 0xffffffff80000000; +pub const KERNEL_VIRT_START: u64 = 0xffffffff80000000; -pub fn load_kernel(kernel: &[u8], system_table: &SystemTable) { +pub fn load_kernel(kernel: &[u8], system_table: &SystemTable) -> (u64, usize, u64) { let file: ElfBytes = ElfBytes::minimal_parse(kernel).unwrap(); let mut kernel_size = 0; for i in file.segments().unwrap() { @@ -37,4 +37,5 @@ pub fn load_kernel(kernel: &[u8], system_table: &SystemTable) { ptr::copy(kernel[i.p_offset.try_into().unwrap()..].as_ptr(), start_addr as *mut u8, i.p_filesz.try_into().unwrap()); } } + (phys_start, kernel_size as usize, file.ehdr.e_entry) } diff --git a/loader/src/main.rs b/loader/src/main.rs index 787753e..bf9d49b 100644 --- a/loader/src/main.rs +++ b/loader/src/main.rs @@ -3,7 +3,7 @@ extern crate alloc; -use core::panic::PanicInfo; +use core::{mem, panic::PanicInfo}; use elf::load_kernel; use log::{error, info}; @@ -28,9 +28,13 @@ fn main(image_handle: Handle, mut system_table: SystemTable) -> Status { com_logger::init(); info!("Starting bootloader..."); uefi::helpers::init(&mut system_table).unwrap(); - load_kernel(KERNEL, &system_table); + let (kernel_start, kernel_size, kernel_entry) = load_kernel(KERNEL, &system_table); let memory_map = system_table.exit_boot_services(MemoryType::LOADER_DATA).1; - setup_paging(&memory_map); + setup_paging(&memory_map, kernel_start, kernel_size); + info!("Jumping to kernel..."); + unsafe { + (mem::transmute::<_, fn()>(kernel_entry))(); + } loop {} } #[panic_handler] diff --git a/loader/src/paging.rs b/loader/src/paging.rs index 0ed0daf..644201a 100644 --- a/loader/src/paging.rs +++ b/loader/src/paging.rs @@ -8,6 +8,8 @@ use x86_64::{ PhysAddr, }; +use crate::elf; + fn get_table_entry(table: &mut PageTable, i: usize) -> &mut PageTable { if table[i].is_unused() { let layout = Layout::new::().align_to(0x1000).unwrap(); @@ -35,7 +37,7 @@ fn map(pml4: &mut PageTable, mut virt: usize, phys: usize) { let phys_addr = PhysAddr::new(phys as u64); table[table_i].set_addr(phys_addr, PageTableFlags::PRESENT | PageTableFlags::WRITABLE) } -pub fn setup_paging(memory_map: &MemoryMap) { +pub fn setup_paging(memory_map: &MemoryMap, kernel_start: u64, kernel_size: usize) { let pml4; let layout = Layout::new::().align_to(0x1000).unwrap(); unsafe { @@ -55,6 +57,11 @@ pub fn setup_paging(memory_map: &MemoryMap) { } } } + for i in 0..((kernel_size + 0xfff) / 0x1000) { + let virt = elf::KERNEL_VIRT_START as usize + i * 0x1000; + let phys = kernel_start as usize + i * 0x1000; + map(pml4, virt, phys); + } let pml4_addr = PhysAddr::new(pml4 as *const PageTable as u64); let frame = PhysFrame::from_start_address(pml4_addr).unwrap(); unsafe {