ax_task/sched/system/task_system/park_exit/
park.rs1use super::*;
4
5impl TaskSystem {
6 pub(crate) fn enter_rt_lock_wait(&self, core: &ThreadCore) -> Result<(), TaskError> {
7 let _sched = core.sched().lock();
8 core.enter_rt_lock_wait()
9 }
10
11 pub(crate) fn restore_rt_lock_wait(&self, core: &ThreadCore) -> Result<(), TaskError> {
12 let _sched = core.sched().lock();
13 core.restore_rt_lock_wait()
14 }
15
16 pub fn prepare_park(
18 &self,
19 cpu: Pin<&mut CpuLocal>,
20 current: &ThreadHandle,
21 ) -> Result<ParkPrepare, TaskError> {
22 self.ensure_owner_cpu_context(&cpu)?;
23 self.ensure_owner_cpu_online(&cpu)?;
24 let core = current.runtime_core_arc();
25 let placement = core.sched().placement();
26 if placement.queued_cpu() != Some(cpu.owner()) || placement.on_cpu() != Some(cpu.owner()) {
27 return Err(TaskError::StaleThreadId);
28 }
29 self.prepare_current_park(core)
30 }
31
32 pub(crate) fn prepare_current_park(
39 &self,
40 current: &ThreadCore,
41 ) -> Result<ParkPrepare, TaskError> {
42 let core = current;
43 let placement = core.sched().placement();
44 let queued_cpu = placement.queued_cpu();
45 if core.state() != ThreadState::Running
46 || queued_cpu.is_none()
47 || placement.on_cpu() != queued_cpu
48 {
49 return Err(TaskError::StaleThreadId);
50 }
51 if core.take_park_notification() {
52 return Ok(ParkPrepare::Notified);
53 }
54 let generation = core.next_park_generation()?;
55 core.transition_state(ThreadState::Parking)?;
56 Ok(ParkPrepare::Prepared(ParkTicket::new(
57 core.id(),
58 generation,
59 )))
60 }
61
62 pub fn cancel_park(
64 &self,
65 cpu: Pin<&mut CpuLocal>,
66 current: &ThreadHandle,
67 token: &mut ParkTicket,
68 ) -> Result<(), TaskError> {
69 self.cancel_current_park(cpu, current.runtime_core_arc(), token)
70 }
71
72 pub(crate) fn cancel_current_park(
73 &self,
74 cpu: Pin<&mut CpuLocal>,
75 current: &ThreadCore,
76 token: &mut ParkTicket,
77 ) -> Result<(), TaskError> {
78 self.ensure_owner_cpu_context(&cpu)?;
79 if token.is_resolved() || current.id() != token.thread() {
80 return Err(TaskError::StaleThreadId);
81 }
82 self.ensure_owner_cpu_online(&cpu)?;
83 let core = current;
84 if core.park_generation() != token.generation() {
85 return Err(TaskError::StaleThreadId);
86 }
87 let placement = core.sched().placement();
88 if core.state() != ThreadState::Parking
89 || placement.queued_cpu() != Some(cpu.owner())
90 || placement.on_cpu() != Some(cpu.owner())
91 {
92 return Err(TaskError::StaleThreadId);
93 }
94 core.transition_state(ThreadState::Running)?;
95 cpu.finish_park_preemption(true);
96 token.mark_resolved();
97 Ok(())
98 }
99}