Exclusive UPSafeCell: A RefCell wrapper
This commit is contained in:
parent
fd00e8de3a
commit
93ea7f9d4d
3 changed files with 26 additions and 20 deletions
|
@ -27,12 +27,12 @@ lazy_static! {
|
|||
let mut tasks = [
|
||||
TaskControlBlock {
|
||||
task_cx: TaskContext::zero_init(),
|
||||
task_status: TaskStatus::UnInit
|
||||
task_status: TaskStatus::UnInit
|
||||
};
|
||||
MAX_APP_NUM
|
||||
];
|
||||
for i in 0..num_app {
|
||||
tasks[i].task_cx = TaskContext::goto_restore(init_app_cx(i));
|
||||
tasks[i].task_cx = TaskContext::goto_restore(init_app_cx(i));
|
||||
tasks[i].task_status = TaskStatus::Ready;
|
||||
}
|
||||
TaskManager {
|
||||
|
@ -46,33 +46,37 @@ lazy_static! {
|
|||
}
|
||||
|
||||
impl TaskManager {
|
||||
fn run_first_task(&self) {
|
||||
let task0 = &mut self.inner.upsafe_access().tasks[0];
|
||||
fn run_first_task(&self) -> ! {
|
||||
let mut inner = self.inner.exclusive_access();
|
||||
let task0 = &mut inner.tasks[0];
|
||||
task0.task_status = TaskStatus::Running;
|
||||
let next_task_cx_ptr = &task0.task_cx as *const TaskContext;
|
||||
let next_task_cx_ptr = &task0.task_cx as *const TaskContext;
|
||||
drop(inner);
|
||||
let mut _unused = TaskContext::zero_init();
|
||||
// before this, we should drop local variables that must be dropped manually
|
||||
unsafe {
|
||||
__switch(
|
||||
&mut _unused as *mut TaskContext,
|
||||
next_task_cx_ptr,
|
||||
);
|
||||
}
|
||||
panic!("unreachable in run_first_task!");
|
||||
}
|
||||
|
||||
fn mark_current_suspended(&self) {
|
||||
let mut inner = self.inner.upsafe_access();
|
||||
let mut inner = self.inner.exclusive_access();
|
||||
let current = inner.current_task;
|
||||
inner.tasks[current].task_status = TaskStatus::Ready;
|
||||
}
|
||||
|
||||
fn mark_current_exited(&self) {
|
||||
let mut inner = self.inner.upsafe_access();
|
||||
let mut inner = self.inner.exclusive_access();
|
||||
let current = inner.current_task;
|
||||
inner.tasks[current].task_status = TaskStatus::Exited;
|
||||
}
|
||||
|
||||
fn find_next_task(&self) -> Option<usize> {
|
||||
let inner = self.inner.upsafe_access();
|
||||
let inner = self.inner.exclusive_access();
|
||||
let current = inner.current_task;
|
||||
(current + 1..current + self.num_app + 1)
|
||||
.map(|id| id % self.num_app)
|
||||
|
@ -83,19 +87,21 @@ impl TaskManager {
|
|||
|
||||
fn run_next_task(&self) {
|
||||
if let Some(next) = self.find_next_task() {
|
||||
let mut inner = self.inner.upsafe_access();
|
||||
let mut inner = self.inner.exclusive_access();
|
||||
let current = inner.current_task;
|
||||
inner.tasks[next].task_status = TaskStatus::Running;
|
||||
inner.current_task = next;
|
||||
let current_task_cx_ptr = &mut inner.tasks[current].task_cx as *mut TaskContext;
|
||||
let next_task_cx_ptr = &inner.tasks[next].task_cx as *const TaskContext;
|
||||
drop(inner);
|
||||
// before this, we should drop local variables that must be dropped manually
|
||||
unsafe {
|
||||
__switch(
|
||||
current_task_cx_ptr,
|
||||
next_task_cx_ptr,
|
||||
);
|
||||
}
|
||||
// go back to user mode
|
||||
} else {
|
||||
panic!("All applications completed!");
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue