fix: scheduler: head node will never be scheduled, add a dummy head node

This commit is contained in:
Paul Pan 2024-06-16 00:11:17 +08:00
parent 6565beef4c
commit 797652c2b8
3 changed files with 16 additions and 14 deletions

View File

@ -1,4 +1,4 @@
pub const TIMER_TICKS: u64 = 100_000; // 100ms
pub const TIMER_TICKS: u64 = 100_000;
// devices
pub const UART0_BASE: usize = 0x1000_0000;

View File

@ -2,7 +2,7 @@ use crate::plat::console::{set_console, ConsoleDevice, ConsoleDriver, CONSOLE};
use crate::plat::lowlevel::{Hardware, LowLevel};
use crate::plat::timer::{Timer, TimerOps};
use crate::plat::trap::{Trap, TrapOps};
use crate::scheduler::SCHEDULER;
use crate::scheduler::{IDLE_THREAD, SCHEDULER};
use core::cell::Cell;
use core::sync::atomic::{AtomicUsize, Ordering};
use fdt::Fdt;
@ -35,6 +35,9 @@ pub fn rust_main() -> ! {
Trap::init();
Timer::init();
SCHEDULER.init();
SCHEDULER.add(&IDLE_THREAD);
SCHEDULER.schedule();
loop {

View File

@ -1,18 +1,18 @@
use crate::objects::*;
use core::ptr::NonNull;
use log::{error, trace};
use log::error;
use spin::lazy::Lazy;
use utils::linked_list::Link;
use utils::{container_of, linked_list::Link};
#[thread_local]
static IDLE_THREAD: Lazy<TcbObject> = Lazy::new(|| {
pub static IDLE_THREAD: Lazy<TcbObject> = Lazy::new(|| {
let mut idle_thread = TcbObject::new();
idle_thread.configure_idle_thread();
idle_thread
});
#[thread_local]
pub static SCHEDULER: Lazy<Scheduler> = Lazy::new(|| Scheduler::new(&IDLE_THREAD));
pub static SCHEDULER: Scheduler = Scheduler::new();
// TODO: add a shared buffer to transfer TCB between cores
@ -24,14 +24,14 @@ pub struct Scheduler {
}
impl Scheduler {
pub fn new(idle_thread: &TcbObject) -> Self {
// link idle_thread
idle_thread.link.set_prev(Some(NonNull::from(idle_thread)));
idle_thread.link.set_next(Some(NonNull::from(idle_thread)));
pub const fn new() -> Self {
Self { head: Link::new() }
}
Self {
head: idle_thread.link.clone(),
}
pub fn init(&self) {
let head = unsafe { Some(NonNull::from(&*container_of!(&self.head, TcbObject, link))) };
self.head.set_next(head);
self.head.set_prev(head);
}
pub fn add(&self, tcb: &TcbObject) {
@ -41,7 +41,6 @@ impl Scheduler {
pub fn schedule(&self) {
while let Some(next) = self.head.next_mut() {
if next.timetick() > 0 && next.schedulable() {
trace!("[Scheduler] Switch to {}, tick: {}", next.tid(), next.timetick());
next.activate();
} else if next.timetick() == 0 {
next.set_timetick(TIME_SLICE);