refactor(kernel): extract MockPlatform and test helpers into separate modules
This commit is contained in:
100
crates/kernel/src/tests/helpers.rs
Normal file
100
crates/kernel/src/tests/helpers.rs
Normal file
@@ -0,0 +1,100 @@
|
||||
use domain::memory::page_pool::PagePool;
|
||||
use domain::resource::Resource;
|
||||
use domain::scheduler::Scheduler;
|
||||
use domain::thread::ThreadState;
|
||||
use platform::Platform;
|
||||
use types::{
|
||||
address::PhysicalAddress,
|
||||
bounded::{CapSlot, Priority},
|
||||
id::{EndpointId, IrqId, ProcessId, ThreadId},
|
||||
permission::PermissionSet,
|
||||
time::TimeSlice,
|
||||
};
|
||||
|
||||
use crate::Kernel;
|
||||
use super::mock_platform::MockPlatform;
|
||||
|
||||
pub fn test_kernel() -> Kernel<MockPlatform> {
|
||||
let mock = MockPlatform::new(1);
|
||||
let pool = PagePool::new(PhysicalAddress::from_raw(0x8000_0000), 1024);
|
||||
Kernel::new(mock, pool)
|
||||
}
|
||||
|
||||
pub fn kernel_with_process() -> (Kernel<MockPlatform>, ProcessId) {
|
||||
let mut kernel = test_kernel();
|
||||
let (pid, _tid) = kernel
|
||||
.boot(Priority::new(16).unwrap(), TimeSlice::new(100))
|
||||
.unwrap();
|
||||
(kernel, pid)
|
||||
}
|
||||
|
||||
impl Kernel<MockPlatform> {
|
||||
pub fn spawn_thread_for_test(
|
||||
&mut self,
|
||||
pid: ProcessId,
|
||||
priority: Priority,
|
||||
time_slice: TimeSlice,
|
||||
) -> ThreadId {
|
||||
let tid = self.threads.spawn(pid, priority, time_slice, None).expect("spawn");
|
||||
let _ = self.processes.get_mut(pid).map(|p| p.add_thread(tid));
|
||||
let core = self.platform.core_id();
|
||||
self.scheduler.add(tid, priority, core);
|
||||
tid
|
||||
}
|
||||
|
||||
pub fn register_irq_for_test(&mut self, irq: IrqId, thread: ThreadId) {
|
||||
let _ = self.irqs.register(irq, thread);
|
||||
}
|
||||
|
||||
pub fn block_thread_for_test(
|
||||
&mut self,
|
||||
tid: ThreadId,
|
||||
reason: domain::thread::BlockReason,
|
||||
) {
|
||||
let core = self.platform.core_id();
|
||||
if let Ok(t) = self.threads.get_mut(tid) {
|
||||
if matches!(t.state(), ThreadState::Ready) {
|
||||
let _ = t.set_running(core);
|
||||
}
|
||||
let _ = t.block(reason);
|
||||
}
|
||||
self.scheduler.remove(tid);
|
||||
}
|
||||
|
||||
pub fn switch_to_thread_for_test(&mut self, tid: ThreadId) {
|
||||
let core = self.platform.core_id();
|
||||
|
||||
if let Some(current) = self.scheduler.current(core) {
|
||||
if current == tid {
|
||||
return;
|
||||
}
|
||||
if let Ok(t) = self.threads.get_mut(current) {
|
||||
if matches!(t.state(), ThreadState::Running(_)) {
|
||||
let priority = t.priority();
|
||||
let _ = t.preempt();
|
||||
self.scheduler.add(current, priority, core);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if let Ok(t) = self.threads.get(tid) {
|
||||
if matches!(t.state(), ThreadState::Ready) {
|
||||
self.scheduler.next(core);
|
||||
let _ = self.threads.get_mut(tid).map(|t| t.set_running(core));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn create_endpoint_for_test(&mut self) -> EndpointId {
|
||||
self.endpoints.create().expect("create endpoint")
|
||||
}
|
||||
|
||||
pub fn grant_cap_for_test(
|
||||
&mut self,
|
||||
pid: ProcessId,
|
||||
resource: Resource,
|
||||
permissions: PermissionSet,
|
||||
) -> CapSlot {
|
||||
self.grant_cap(pid, resource, permissions).expect("grant cap")
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user