1 use fdt::node::FdtNode; 2 use system_error::SystemError; 3 4 use crate::{ 5 arch::{driver::sbi::SbiDriver, mm::init::mm_early_init}, 6 driver::{ 7 firmware::efi::init::efi_init, irqchip::riscv_intc::riscv_intc_init, 8 open_firmware::fdt::open_firmware_fdt_driver, 9 }, 10 init::{boot_params, init::start_kernel}, 11 kdebug, kinfo, 12 mm::{memblock::mem_block_manager, PhysAddr, VirtAddr}, 13 print, println, 14 smp::cpu::ProcessorId, 15 }; 16 17 use super::{cpu::init_local_context, driver::sbi::console_putstr}; 18 19 #[derive(Debug)] 20 pub struct ArchBootParams { 21 /// 启动时的fdt物理地址 22 pub fdt_paddr: PhysAddr, 23 pub fdt_vaddr: Option<VirtAddr>, 24 25 pub boot_hartid: ProcessorId, 26 } 27 28 impl ArchBootParams { 29 pub const DEFAULT: Self = ArchBootParams { 30 fdt_paddr: PhysAddr::new(0), 31 fdt_vaddr: None, 32 boot_hartid: ProcessorId::new(0), 33 }; 34 35 pub fn arch_fdt(&self) -> VirtAddr { 36 // 如果fdt_vaddr为None,则说明还没有进行内核虚拟地址空间的映射,此时返回物理地址 37 if self.fdt_vaddr.is_none() { 38 return VirtAddr::new(self.fdt_paddr.data()); 39 } 40 self.fdt_vaddr.unwrap() 41 } 42 } 43 44 static mut BOOT_HARTID: u32 = 0; 45 static mut BOOT_FDT_PADDR: PhysAddr = PhysAddr::new(0); 46 47 #[no_mangle] 48 unsafe extern "C" fn kernel_main(hartid: usize, fdt_paddr: usize) -> ! { 49 let fdt_paddr = PhysAddr::new(fdt_paddr); 50 51 unsafe { 52 BOOT_HARTID = hartid as u32; 53 BOOT_FDT_PADDR = fdt_paddr; 54 } 55 56 start_kernel(); 57 } 58 59 #[inline(never)] 60 fn print_node(node: FdtNode<'_, '_>, n_spaces: usize) { 61 (0..n_spaces).for_each(|_| print!(" ")); 62 println!("{}/", node.name); 63 node.properties().for_each(|p| { 64 (0..n_spaces + 4).for_each(|_| print!(" ")); 65 println!("{}: {:?}", p.name, p.value); 66 }); 67 68 for child in node.children() { 69 print_node(child, n_spaces + 4); 70 } 71 } 72 73 /// 解析fdt,获取内核启动参数 74 #[inline(never)] 75 unsafe fn parse_dtb() { 76 let fdt_paddr = boot_params().read().arch.fdt_paddr; 77 if fdt_paddr.is_null() { 78 panic!("Failed to get fdt address!"); 79 } 80 81 open_firmware_fdt_driver() 82 .early_scan_device_tree() 83 .expect("Failed to scan device tree at boottime."); 84 } 85 86 #[inline(never)] 87 pub fn early_setup_arch() -> Result<(), SystemError> { 88 SbiDriver::early_init(); 89 let hartid = unsafe { BOOT_HARTID }; 90 let fdt_paddr = unsafe { BOOT_FDT_PADDR }; 91 92 let mut arch_boot_params_guard = boot_params().write(); 93 arch_boot_params_guard.arch.fdt_paddr = fdt_paddr; 94 arch_boot_params_guard.arch.boot_hartid = ProcessorId::new(hartid); 95 96 drop(arch_boot_params_guard); 97 98 kinfo!( 99 "DragonOS kernel is running on hart {}, fdt address:{:?}", 100 hartid, 101 fdt_paddr 102 ); 103 mm_early_init(); 104 105 let fdt = 106 unsafe { fdt::Fdt::from_ptr(fdt_paddr.data() as *const u8).expect("Failed to parse fdt!") }; 107 print_node(fdt.find_node("/").unwrap(), 0); 108 109 unsafe { parse_dtb() }; 110 111 for x in mem_block_manager().to_iter() { 112 kdebug!("before efi: {x:?}"); 113 } 114 115 efi_init(); 116 117 open_firmware_fdt_driver().early_init_fdt_scan_reserved_mem(); 118 119 return Ok(()); 120 } 121 122 #[inline(never)] 123 pub fn setup_arch() -> Result<(), SystemError> { 124 init_local_context(); 125 return Ok(()); 126 } 127 128 #[inline(never)] 129 pub fn setup_arch_post() -> Result<(), SystemError> { 130 // todo 131 return Ok(()); 132 } 133