mirror of
https://github.com/DragonOS-Community/DragonOS.git
synced 2025-06-09 02:46:47 +00:00
riscv: 进程管理初始化 (#654)
This commit is contained in:
parent
6046f77591
commit
401699735b
@ -71,7 +71,12 @@ fn print_node(node: FdtNode<'_, '_>, n_spaces: usize) {
|
|||||||
println!("{}/", node.name);
|
println!("{}/", node.name);
|
||||||
node.properties().for_each(|p| {
|
node.properties().for_each(|p| {
|
||||||
(0..n_spaces + 4).for_each(|_| print!(" "));
|
(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() {
|
for child in node.children() {
|
||||||
|
@ -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 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;
|
use super::interrupt::TrapFrame;
|
||||||
|
|
||||||
@ -28,7 +38,7 @@ pub unsafe fn arch_switch_to_user(path: String, argv: Vec<String>, envp: Vec<Str
|
|||||||
|
|
||||||
impl ProcessManager {
|
impl ProcessManager {
|
||||||
pub fn arch_init() {
|
pub fn arch_init() {
|
||||||
unimplemented!("ProcessManager::arch_init")
|
// do nothing
|
||||||
}
|
}
|
||||||
|
|
||||||
/// fork的过程中复制线程
|
/// fork的过程中复制线程
|
||||||
@ -50,6 +60,7 @@ impl ProcessManager {
|
|||||||
/// - `prev`:上一个进程的pcb
|
/// - `prev`:上一个进程的pcb
|
||||||
/// - `next`:下一个进程的pcb
|
/// - `next`:下一个进程的pcb
|
||||||
pub unsafe fn switch_process(prev: Arc<ProcessControlBlock>, next: Arc<ProcessControlBlock>) {
|
pub unsafe fn switch_process(prev: Arc<ProcessControlBlock>, next: Arc<ProcessControlBlock>) {
|
||||||
|
// todo: https://code.dragonos.org.cn/xref/linux-6.6.21/arch/riscv/include/asm/switch_to.h#76
|
||||||
unimplemented!("ProcessManager::switch_process")
|
unimplemented!("ProcessManager::switch_process")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -57,7 +68,27 @@ impl ProcessManager {
|
|||||||
impl ProcessControlBlock {
|
impl ProcessControlBlock {
|
||||||
/// 获取当前进程的pcb
|
/// 获取当前进程的pcb
|
||||||
pub fn arch_current_pcb() -> Arc<Self> {
|
pub fn arch_current_pcb() -> Arc<Self> {
|
||||||
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<Weak<ProcessControlBlock>> =
|
||||||
|
ManuallyDrop::new(Weak::from_raw(*p));
|
||||||
|
|
||||||
|
let new_arc: Arc<ProcessControlBlock> = weak_wrapper.upgrade().unwrap();
|
||||||
|
return new_arc;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -80,7 +111,7 @@ impl ArchPCBInfo {
|
|||||||
///
|
///
|
||||||
/// 返回一个新的ArchPCBInfo
|
/// 返回一个新的ArchPCBInfo
|
||||||
pub fn new(kstack: &KernelStack) -> Self {
|
pub fn new(kstack: &KernelStack) -> Self {
|
||||||
unimplemented!("ArchPCBInfo::new")
|
Self {}
|
||||||
}
|
}
|
||||||
// ### 从另一个ArchPCBInfo处clone,但是保留部分字段不变
|
// ### 从另一个ArchPCBInfo处clone,但是保留部分字段不变
|
||||||
pub fn clone_from(&mut self, from: &Self) {
|
pub fn clone_from(&mut self, from: &Self) {
|
||||||
|
@ -1,8 +1,11 @@
|
|||||||
use system_error::SystemError;
|
use system_error::SystemError;
|
||||||
|
|
||||||
use crate::smp::{
|
use crate::{
|
||||||
cpu::{CpuHpCpuState, ProcessorId},
|
kwarn,
|
||||||
SMPArch,
|
smp::{
|
||||||
|
cpu::{CpuHpCpuState, ProcessorId},
|
||||||
|
SMPArch,
|
||||||
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
pub struct RiscV64SMPArch;
|
pub struct RiscV64SMPArch;
|
||||||
@ -10,10 +13,12 @@ pub struct RiscV64SMPArch;
|
|||||||
impl SMPArch for RiscV64SMPArch {
|
impl SMPArch for RiscV64SMPArch {
|
||||||
#[inline(never)]
|
#[inline(never)]
|
||||||
fn prepare_cpus() -> Result<(), SystemError> {
|
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> {
|
fn start_cpu(cpu_id: ProcessorId, hp_state: &CpuHpCpuState) -> Result<(), SystemError> {
|
||||||
todo!()
|
kwarn!("RiscV64SMPArch::start_cpu() is not implemented");
|
||||||
|
Ok(())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -8,7 +8,7 @@ use super::{interrupt::TrapFrame, CurrentIrqArch};
|
|||||||
|
|
||||||
/// 系统调用初始化
|
/// 系统调用初始化
|
||||||
pub fn arch_syscall_init() -> Result<(), SystemError> {
|
pub fn arch_syscall_init() -> Result<(), SystemError> {
|
||||||
unimplemented!("arch_syscall_init")
|
return Ok(());
|
||||||
}
|
}
|
||||||
|
|
||||||
#[no_mangle]
|
#[no_mangle]
|
||||||
|
@ -20,14 +20,10 @@ use crate::{
|
|||||||
exception::InterruptArch,
|
exception::InterruptArch,
|
||||||
kerror, kwarn,
|
kerror, kwarn,
|
||||||
libs::spinlock::SpinLockGuard,
|
libs::spinlock::SpinLockGuard,
|
||||||
mm::{
|
mm::VirtAddr,
|
||||||
percpu::{PerCpu, PerCpuVar},
|
|
||||||
VirtAddr,
|
|
||||||
},
|
|
||||||
process::{
|
process::{
|
||||||
fork::{CloneFlags, KernelCloneArgs},
|
fork::{CloneFlags, KernelCloneArgs},
|
||||||
KernelStack, ProcessControlBlock, ProcessFlags, ProcessManager, SwitchResult,
|
KernelStack, ProcessControlBlock, ProcessFlags, ProcessManager, PROCESS_SWITCH_RESULT,
|
||||||
SWITCH_RESULT,
|
|
||||||
},
|
},
|
||||||
syscall::Syscall,
|
syscall::Syscall,
|
||||||
};
|
};
|
||||||
@ -299,16 +295,7 @@ impl ProcessControlBlock {
|
|||||||
|
|
||||||
impl ProcessManager {
|
impl ProcessManager {
|
||||||
pub fn arch_init() {
|
pub fn arch_init() {
|
||||||
{
|
// do nothing
|
||||||
// 初始化进程切换结果 per cpu变量
|
|
||||||
let mut switch_res_vec: Vec<SwitchResult> = 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());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
/// fork的过程中复制线程
|
/// fork的过程中复制线程
|
||||||
///
|
///
|
||||||
@ -421,8 +408,8 @@ impl ProcessManager {
|
|||||||
x86::Ring::Ring0,
|
x86::Ring::Ring0,
|
||||||
next.kernel_stack().stack_max_address().data() as u64,
|
next.kernel_stack().stack_max_address().data() as u64,
|
||||||
);
|
);
|
||||||
SWITCH_RESULT.as_mut().unwrap().get_mut().prev_pcb = Some(prev);
|
PROCESS_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().next_pcb = Some(next);
|
||||||
// kdebug!("switch tss ok");
|
// kdebug!("switch tss ok");
|
||||||
compiler_fence(Ordering::SeqCst);
|
compiler_fence(Ordering::SeqCst);
|
||||||
// 正式切换上下文
|
// 正式切换上下文
|
||||||
|
@ -74,7 +74,13 @@ impl ProcessManager {
|
|||||||
return VirtAddr::new(x86::current::registers::rsp() as usize);
|
return VirtAddr::new(x86::current::registers::rsp() as usize);
|
||||||
|
|
||||||
#[cfg(target_arch = "riscv64")]
|
#[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进程数组的引用
|
/// 获取idle进程数组的引用
|
||||||
|
@ -41,7 +41,12 @@ use crate::{
|
|||||||
spinlock::{SpinLock, SpinLockGuard},
|
spinlock::{SpinLock, SpinLockGuard},
|
||||||
wait_queue::WaitQueue,
|
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,
|
net::socket::SocketInode,
|
||||||
sched::{
|
sched::{
|
||||||
completion::Completion,
|
completion::Completion,
|
||||||
@ -73,7 +78,7 @@ pub mod utils;
|
|||||||
/// 系统中所有进程的pcb
|
/// 系统中所有进程的pcb
|
||||||
static ALL_PROCESS: SpinLock<Option<HashMap<Pid, Arc<ProcessControlBlock>>>> = SpinLock::new(None);
|
static ALL_PROCESS: SpinLock<Option<HashMap<Pid, Arc<ProcessControlBlock>>>> = SpinLock::new(None);
|
||||||
|
|
||||||
pub static mut SWITCH_RESULT: Option<PerCpuVar<SwitchResult>> = None;
|
pub static mut PROCESS_SWITCH_RESULT: Option<PerCpuVar<SwitchResult>> = None;
|
||||||
|
|
||||||
/// 一个只改变1次的全局变量,标志进程管理器是否已经初始化完成
|
/// 一个只改变1次的全局变量,标志进程管理器是否已经初始化完成
|
||||||
static mut __PROCESS_MANAGEMENT_INIT_DONE: bool = false;
|
static mut __PROCESS_MANAGEMENT_INIT_DONE: bool = false;
|
||||||
@ -118,6 +123,7 @@ impl ProcessManager {
|
|||||||
};
|
};
|
||||||
|
|
||||||
ALL_PROCESS.lock_irqsave().replace(HashMap::new());
|
ALL_PROCESS.lock_irqsave().replace(HashMap::new());
|
||||||
|
Self::init_switch_result();
|
||||||
Self::arch_init();
|
Self::arch_init();
|
||||||
kdebug!("process arch init done.");
|
kdebug!("process arch init done.");
|
||||||
Self::init_idle();
|
Self::init_idle();
|
||||||
@ -127,6 +133,16 @@ impl ProcessManager {
|
|||||||
kinfo!("Process Manager initialized.");
|
kinfo!("Process Manager initialized.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn init_switch_result() {
|
||||||
|
let mut switch_res_vec: Vec<SwitchResult> = 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 {
|
pub fn initialized() -> bool {
|
||||||
unsafe { __PROCESS_MANAGEMENT_INIT_DONE }
|
unsafe { __PROCESS_MANAGEMENT_INIT_DONE }
|
||||||
@ -399,14 +415,14 @@ impl ProcessManager {
|
|||||||
/// 上下文切换完成后的钩子函数
|
/// 上下文切换完成后的钩子函数
|
||||||
unsafe fn switch_finish_hook() {
|
unsafe fn switch_finish_hook() {
|
||||||
// kdebug!("switch_finish_hook");
|
// kdebug!("switch_finish_hook");
|
||||||
let prev_pcb = SWITCH_RESULT
|
let prev_pcb = PROCESS_SWITCH_RESULT
|
||||||
.as_mut()
|
.as_mut()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.get_mut()
|
.get_mut()
|
||||||
.prev_pcb
|
.prev_pcb
|
||||||
.take()
|
.take()
|
||||||
.expect("prev_pcb is None");
|
.expect("prev_pcb is None");
|
||||||
let next_pcb = SWITCH_RESULT
|
let next_pcb = PROCESS_SWITCH_RESULT
|
||||||
.as_mut()
|
.as_mut()
|
||||||
.unwrap()
|
.unwrap()
|
||||||
.get_mut()
|
.get_mut()
|
||||||
|
Loading…
x
Reference in New Issue
Block a user