diff --git a/kernel/src/arch/riscv64/init/mod.rs b/kernel/src/arch/riscv64/init/mod.rs index a22d7530..25482915 100644 --- a/kernel/src/arch/riscv64/init/mod.rs +++ b/kernel/src/arch/riscv64/init/mod.rs @@ -71,7 +71,12 @@ fn print_node(node: FdtNode<'_, '_>, n_spaces: usize) { println!("{}/", node.name); node.properties().for_each(|p| { (0..n_spaces + 4).for_each(|_| print!(" ")); - println!("{}: {:?}", p.name, p.value); + + if p.name == "compatible" { + println!("{}: {:?}", p.name, p.as_str()); + } else { + println!("{}: {:?}", p.name, p.value); + } }); for child in node.children() { diff --git a/kernel/src/arch/riscv64/process/mod.rs b/kernel/src/arch/riscv64/process/mod.rs index fde3ae98..9988dc03 100644 --- a/kernel/src/arch/riscv64/process/mod.rs +++ b/kernel/src/arch/riscv64/process/mod.rs @@ -1,7 +1,17 @@ -use alloc::{string::String, sync::Arc, vec::Vec}; +use core::{arch::asm, mem::ManuallyDrop}; + +use alloc::{ + string::String, + sync::{Arc, Weak}, + vec::Vec, +}; use system_error::SystemError; -use crate::process::{fork::KernelCloneArgs, KernelStack, ProcessControlBlock, ProcessManager}; +use crate::{ + kerror, + mm::VirtAddr, + process::{fork::KernelCloneArgs, KernelStack, ProcessControlBlock, ProcessManager}, +}; use super::interrupt::TrapFrame; @@ -28,7 +38,7 @@ pub unsafe fn arch_switch_to_user(path: String, argv: Vec, envp: Vec, next: Arc) { + // todo: https://code.dragonos.org.cn/xref/linux-6.6.21/arch/riscv/include/asm/switch_to.h#76 unimplemented!("ProcessManager::switch_process") } } @@ -57,7 +68,27 @@ impl ProcessManager { impl ProcessControlBlock { /// 获取当前进程的pcb pub fn arch_current_pcb() -> Arc { - unimplemented!("ProcessControlBlock::arch_current_pcb") + // 获取栈指针 + let mut sp: usize; + unsafe { asm!("mv {}, sp", lateout(reg) sp, options(nostack)) }; + let ptr = VirtAddr::new(sp); + + let stack_base = VirtAddr::new(ptr.data() & (!(KernelStack::ALIGN - 1))); + + // 从内核栈的最低地址处取出pcb的地址 + let p = stack_base.data() as *const *const ProcessControlBlock; + if core::intrinsics::unlikely((unsafe { *p }).is_null()) { + kerror!("p={:p}", p); + panic!("current_pcb is null"); + } + unsafe { + // 为了防止内核栈的pcb weak 指针被释放,这里需要将其包装一下 + let weak_wrapper: ManuallyDrop> = + ManuallyDrop::new(Weak::from_raw(*p)); + + let new_arc: Arc = weak_wrapper.upgrade().unwrap(); + return new_arc; + } } } @@ -80,7 +111,7 @@ impl ArchPCBInfo { /// /// 返回一个新的ArchPCBInfo pub fn new(kstack: &KernelStack) -> Self { - unimplemented!("ArchPCBInfo::new") + Self {} } // ### 从另一个ArchPCBInfo处clone,但是保留部分字段不变 pub fn clone_from(&mut self, from: &Self) { diff --git a/kernel/src/arch/riscv64/smp/mod.rs b/kernel/src/arch/riscv64/smp/mod.rs index 42f75185..f0ed87b6 100644 --- a/kernel/src/arch/riscv64/smp/mod.rs +++ b/kernel/src/arch/riscv64/smp/mod.rs @@ -1,8 +1,11 @@ use system_error::SystemError; -use crate::smp::{ - cpu::{CpuHpCpuState, ProcessorId}, - SMPArch, +use crate::{ + kwarn, + smp::{ + cpu::{CpuHpCpuState, ProcessorId}, + SMPArch, + }, }; pub struct RiscV64SMPArch; @@ -10,10 +13,12 @@ pub struct RiscV64SMPArch; impl SMPArch for RiscV64SMPArch { #[inline(never)] fn prepare_cpus() -> Result<(), SystemError> { - todo!() + kwarn!("RiscV64SMPArch::prepare_cpus() is not implemented"); + Ok(()) } fn start_cpu(cpu_id: ProcessorId, hp_state: &CpuHpCpuState) -> Result<(), SystemError> { - todo!() + kwarn!("RiscV64SMPArch::start_cpu() is not implemented"); + Ok(()) } } diff --git a/kernel/src/arch/riscv64/syscall/mod.rs b/kernel/src/arch/riscv64/syscall/mod.rs index eb10a057..eb896d97 100644 --- a/kernel/src/arch/riscv64/syscall/mod.rs +++ b/kernel/src/arch/riscv64/syscall/mod.rs @@ -8,7 +8,7 @@ use super::{interrupt::TrapFrame, CurrentIrqArch}; /// 系统调用初始化 pub fn arch_syscall_init() -> Result<(), SystemError> { - unimplemented!("arch_syscall_init") + return Ok(()); } #[no_mangle] diff --git a/kernel/src/arch/x86_64/process/mod.rs b/kernel/src/arch/x86_64/process/mod.rs index d1e0dd56..32d50a99 100644 --- a/kernel/src/arch/x86_64/process/mod.rs +++ b/kernel/src/arch/x86_64/process/mod.rs @@ -20,14 +20,10 @@ use crate::{ exception::InterruptArch, kerror, kwarn, libs::spinlock::SpinLockGuard, - mm::{ - percpu::{PerCpu, PerCpuVar}, - VirtAddr, - }, + mm::VirtAddr, process::{ fork::{CloneFlags, KernelCloneArgs}, - KernelStack, ProcessControlBlock, ProcessFlags, ProcessManager, SwitchResult, - SWITCH_RESULT, + KernelStack, ProcessControlBlock, ProcessFlags, ProcessManager, PROCESS_SWITCH_RESULT, }, syscall::Syscall, }; @@ -299,16 +295,7 @@ impl ProcessControlBlock { impl ProcessManager { pub fn arch_init() { - { - // 初始化进程切换结果 per cpu变量 - let mut switch_res_vec: Vec = Vec::new(); - for _ in 0..PerCpu::MAX_CPU_NUM { - switch_res_vec.push(SwitchResult::new()); - } - unsafe { - SWITCH_RESULT = Some(PerCpuVar::new(switch_res_vec).unwrap()); - } - } + // do nothing } /// fork的过程中复制线程 /// @@ -421,8 +408,8 @@ impl ProcessManager { x86::Ring::Ring0, next.kernel_stack().stack_max_address().data() as u64, ); - SWITCH_RESULT.as_mut().unwrap().get_mut().prev_pcb = Some(prev); - SWITCH_RESULT.as_mut().unwrap().get_mut().next_pcb = Some(next); + PROCESS_SWITCH_RESULT.as_mut().unwrap().get_mut().prev_pcb = Some(prev); + PROCESS_SWITCH_RESULT.as_mut().unwrap().get_mut().next_pcb = Some(next); // kdebug!("switch tss ok"); compiler_fence(Ordering::SeqCst); // 正式切换上下文 diff --git a/kernel/src/process/idle.rs b/kernel/src/process/idle.rs index 70a0b3aa..bd4d3150 100644 --- a/kernel/src/process/idle.rs +++ b/kernel/src/process/idle.rs @@ -74,7 +74,13 @@ impl ProcessManager { return VirtAddr::new(x86::current::registers::rsp() as usize); #[cfg(target_arch = "riscv64")] - unimplemented!("stack_ptr() is not implemented on RISC-V") + { + let stack_ptr: usize; + unsafe { + core::arch::asm!("mv {}, sp", out(reg) stack_ptr); + } + return VirtAddr::new(stack_ptr); + } } /// 获取idle进程数组的引用 diff --git a/kernel/src/process/mod.rs b/kernel/src/process/mod.rs index 065b5a23..c7c502de 100644 --- a/kernel/src/process/mod.rs +++ b/kernel/src/process/mod.rs @@ -41,7 +41,12 @@ use crate::{ spinlock::{SpinLock, SpinLockGuard}, wait_queue::WaitQueue, }, - mm::{percpu::PerCpuVar, set_IDLE_PROCESS_ADDRESS_SPACE, ucontext::AddressSpace, VirtAddr}, + mm::{ + percpu::{PerCpu, PerCpuVar}, + set_IDLE_PROCESS_ADDRESS_SPACE, + ucontext::AddressSpace, + VirtAddr, + }, net::socket::SocketInode, sched::{ completion::Completion, @@ -73,7 +78,7 @@ pub mod utils; /// 系统中所有进程的pcb static ALL_PROCESS: SpinLock>>> = SpinLock::new(None); -pub static mut SWITCH_RESULT: Option> = None; +pub static mut PROCESS_SWITCH_RESULT: Option> = None; /// 一个只改变1次的全局变量,标志进程管理器是否已经初始化完成 static mut __PROCESS_MANAGEMENT_INIT_DONE: bool = false; @@ -118,6 +123,7 @@ impl ProcessManager { }; ALL_PROCESS.lock_irqsave().replace(HashMap::new()); + Self::init_switch_result(); Self::arch_init(); kdebug!("process arch init done."); Self::init_idle(); @@ -127,6 +133,16 @@ impl ProcessManager { kinfo!("Process Manager initialized."); } + fn init_switch_result() { + let mut switch_res_vec: Vec = Vec::new(); + for _ in 0..PerCpu::MAX_CPU_NUM { + switch_res_vec.push(SwitchResult::new()); + } + unsafe { + PROCESS_SWITCH_RESULT = Some(PerCpuVar::new(switch_res_vec).unwrap()); + } + } + /// 判断进程管理器是否已经初始化完成 pub fn initialized() -> bool { unsafe { __PROCESS_MANAGEMENT_INIT_DONE } @@ -399,14 +415,14 @@ impl ProcessManager { /// 上下文切换完成后的钩子函数 unsafe fn switch_finish_hook() { // kdebug!("switch_finish_hook"); - let prev_pcb = SWITCH_RESULT + let prev_pcb = PROCESS_SWITCH_RESULT .as_mut() .unwrap() .get_mut() .prev_pcb .take() .expect("prev_pcb is None"); - let next_pcb = SWITCH_RESULT + let next_pcb = PROCESS_SWITCH_RESULT .as_mut() .unwrap() .get_mut()