1 use core::{ 2 fmt::Debug, 3 intrinsics::unlikely, 4 sync::atomic::{compiler_fence, AtomicBool, AtomicU64, Ordering}, 5 }; 6 7 use alloc::{ 8 boxed::Box, 9 collections::LinkedList, 10 sync::{Arc, Weak}, 11 }; 12 13 use crate::{ 14 arch::{sched::sched, CurrentIrqArch}, 15 exception::{ 16 softirq::{softirq_vectors, SoftirqNumber, SoftirqVec}, 17 InterruptArch, 18 }, 19 kdebug, kerror, kinfo, 20 libs::spinlock::SpinLock, 21 process::{ProcessControlBlock, ProcessManager}, 22 syscall::SystemError, 23 }; 24 25 use super::timekeeping::update_wall_time; 26 27 const MAX_TIMEOUT: i64 = i64::MAX; 28 const TIMER_RUN_CYCLE_THRESHOLD: usize = 20; 29 static TIMER_JIFFIES: AtomicU64 = AtomicU64::new(0); 30 31 lazy_static! { 32 pub static ref TIMER_LIST: SpinLock<LinkedList<Arc<Timer>>> = SpinLock::new(LinkedList::new()); 33 } 34 35 /// 定时器要执行的函数的特征 36 pub trait TimerFunction: Send + Sync + Debug { 37 fn run(&mut self) -> Result<(), SystemError>; 38 } 39 40 #[derive(Debug)] 41 /// WakeUpHelper函数对应的结构体 42 pub struct WakeUpHelper { 43 pcb: Arc<ProcessControlBlock>, 44 } 45 46 impl WakeUpHelper { 47 pub fn new(pcb: Arc<ProcessControlBlock>) -> Box<WakeUpHelper> { 48 return Box::new(WakeUpHelper { pcb }); 49 } 50 } 51 52 impl TimerFunction for WakeUpHelper { 53 fn run(&mut self) -> Result<(), SystemError> { 54 ProcessManager::wakeup(&self.pcb).ok(); 55 return Ok(()); 56 } 57 } 58 59 #[derive(Debug)] 60 pub struct Timer(SpinLock<InnerTimer>); 61 62 impl Timer { 63 /// @brief 创建一个定时器(单位:ms) 64 /// 65 /// @param timer_func 定时器需要执行的函数对应的结构体 66 /// 67 /// @param expire_jiffies 定时器结束时刻 68 /// 69 /// @return 定时器结构体 70 pub fn new(timer_func: Box<dyn TimerFunction>, expire_jiffies: u64) -> Arc<Self> { 71 let result: Arc<Timer> = Arc::new(Timer(SpinLock::new(InnerTimer { 72 expire_jiffies, 73 timer_func, 74 self_ref: Weak::default(), 75 }))); 76 77 result.0.lock().self_ref = Arc::downgrade(&result); 78 79 return result; 80 } 81 82 /// @brief 将定时器插入到定时器链表中 83 pub fn activate(&self) { 84 let inner_guard = self.0.lock(); 85 let timer_list = &mut TIMER_LIST.lock(); 86 87 // 链表为空,则直接插入 88 if timer_list.is_empty() { 89 // FIXME push_timer 90 91 timer_list.push_back(inner_guard.self_ref.upgrade().unwrap()); 92 93 drop(inner_guard); 94 drop(timer_list); 95 compiler_fence(Ordering::SeqCst); 96 97 return; 98 } 99 let mut split_pos: usize = 0; 100 for (pos, elt) in timer_list.iter().enumerate() { 101 if elt.0.lock().expire_jiffies > inner_guard.expire_jiffies { 102 split_pos = pos; 103 break; 104 } 105 } 106 let mut temp_list: LinkedList<Arc<Timer>> = timer_list.split_off(split_pos); 107 timer_list.push_back(inner_guard.self_ref.upgrade().unwrap()); 108 timer_list.append(&mut temp_list); 109 drop(inner_guard); 110 drop(timer_list); 111 } 112 113 #[inline] 114 fn run(&self) { 115 let r = self.0.lock().timer_func.run(); 116 if unlikely(r.is_err()) { 117 kerror!( 118 "Failed to run timer function: {self:?} {:?}", 119 r.err().unwrap() 120 ); 121 } 122 } 123 } 124 125 /// 定时器类型 126 #[derive(Debug)] 127 pub struct InnerTimer { 128 /// 定时器结束时刻 129 pub expire_jiffies: u64, 130 /// 定时器需要执行的函数结构体 131 pub timer_func: Box<dyn TimerFunction>, 132 /// self_ref 133 self_ref: Weak<Timer>, 134 } 135 136 #[derive(Debug)] 137 pub struct DoTimerSoftirq { 138 running: AtomicBool, 139 } 140 141 impl DoTimerSoftirq { 142 pub fn new() -> Self { 143 return DoTimerSoftirq { 144 running: AtomicBool::new(false), 145 }; 146 } 147 148 fn set_run(&self) -> bool { 149 let x = self 150 .running 151 .compare_exchange(false, true, Ordering::Acquire, Ordering::Relaxed); 152 if x.is_ok() { 153 return true; 154 } else { 155 return false; 156 } 157 } 158 159 fn clear_run(&self) { 160 self.running.store(false, Ordering::Release); 161 } 162 } 163 impl SoftirqVec for DoTimerSoftirq { 164 fn run(&self) { 165 if self.set_run() == false { 166 return; 167 } 168 // 最多只处理TIMER_RUN_CYCLE_THRESHOLD个计时器 169 for _ in 0..TIMER_RUN_CYCLE_THRESHOLD { 170 // kdebug!("DoTimerSoftirq run"); 171 let timer_list = TIMER_LIST.try_lock(); 172 if timer_list.is_err() { 173 continue; 174 } 175 let mut timer_list = timer_list.unwrap(); 176 177 if timer_list.is_empty() { 178 break; 179 } 180 181 let timer_list_front = timer_list.pop_front().unwrap(); 182 // kdebug!("to lock timer_list_front"); 183 let mut timer_list_front_guard = None; 184 for _ in 0..10 { 185 let x = timer_list_front.0.try_lock(); 186 if x.is_err() { 187 continue; 188 } 189 timer_list_front_guard = Some(x.unwrap()); 190 } 191 if timer_list_front_guard.is_none() { 192 continue; 193 } 194 let timer_list_front_guard = timer_list_front_guard.unwrap(); 195 if timer_list_front_guard.expire_jiffies > TIMER_JIFFIES.load(Ordering::SeqCst) { 196 drop(timer_list_front_guard); 197 timer_list.push_front(timer_list_front); 198 break; 199 } 200 drop(timer_list_front_guard); 201 drop(timer_list); 202 timer_list_front.run(); 203 } 204 205 self.clear_run(); 206 } 207 } 208 209 /// @brief 初始化timer模块 210 pub fn timer_init() { 211 // FIXME 调用register_trap 212 let do_timer_softirq = Arc::new(DoTimerSoftirq::new()); 213 softirq_vectors() 214 .register_softirq(SoftirqNumber::TIMER, do_timer_softirq) 215 .expect("Failed to register timer softirq"); 216 kinfo!("timer initialized successfully"); 217 } 218 219 /// 计算接下来n毫秒对应的定时器时间片 220 pub fn next_n_ms_timer_jiffies(expire_ms: u64) -> u64 { 221 return TIMER_JIFFIES.load(Ordering::SeqCst) + 1000 * (expire_ms); 222 } 223 /// 计算接下来n微秒对应的定时器时间片 224 pub fn next_n_us_timer_jiffies(expire_us: u64) -> u64 { 225 return TIMER_JIFFIES.load(Ordering::SeqCst) + (expire_us); 226 } 227 228 /// @brief 让pcb休眠timeout个jiffies 229 /// 230 /// @param timeout 需要休眠的时间(单位:jiffies) 231 /// 232 /// @return Ok(i64) 剩余需要休眠的时间(单位:jiffies) 233 /// 234 /// @return Err(SystemError) 错误码 235 pub fn schedule_timeout(mut timeout: i64) -> Result<i64, SystemError> { 236 // kdebug!("schedule_timeout"); 237 if timeout == MAX_TIMEOUT { 238 sched(); 239 return Ok(MAX_TIMEOUT); 240 } else if timeout < 0 { 241 kerror!("timeout can't less than 0"); 242 return Err(SystemError::EINVAL); 243 } else { 244 // 禁用中断,防止在这段期间发生调度,造成死锁 245 let irq_guard = unsafe { CurrentIrqArch::save_and_disable_irq() }; 246 247 timeout += TIMER_JIFFIES.load(Ordering::SeqCst) as i64; 248 let timer = Timer::new( 249 WakeUpHelper::new(ProcessManager::current_pcb()), 250 timeout as u64, 251 ); 252 ProcessManager::mark_sleep(true).ok(); 253 timer.activate(); 254 255 drop(irq_guard); 256 257 sched(); 258 let time_remaining: i64 = timeout - TIMER_JIFFIES.load(Ordering::SeqCst) as i64; 259 if time_remaining >= 0 { 260 // 被提前唤醒,返回剩余时间 261 return Ok(time_remaining); 262 } else { 263 return Ok(0); 264 } 265 } 266 } 267 268 pub fn timer_get_first_expire() -> Result<u64, SystemError> { 269 // FIXME 270 // kdebug!("rs_timer_get_first_expire,timer_jif = {:?}", TIMER_JIFFIES); 271 for _ in 0..10 { 272 match TIMER_LIST.try_lock() { 273 Ok(timer_list) => { 274 // kdebug!("rs_timer_get_first_expire TIMER_LIST lock successfully"); 275 if timer_list.is_empty() { 276 // kdebug!("timer_list is empty"); 277 return Ok(0); 278 } else { 279 // kdebug!("timer_list not empty"); 280 return Ok(timer_list.front().unwrap().0.lock().expire_jiffies); 281 } 282 } 283 // 加锁失败返回啥?? 284 Err(_) => continue, 285 } 286 } 287 return Err(SystemError::EAGAIN_OR_EWOULDBLOCK); 288 } 289 290 pub fn update_timer_jiffies(add_jiffies: u64) -> u64 { 291 let prev = TIMER_JIFFIES.fetch_add(add_jiffies, Ordering::SeqCst); 292 compiler_fence(Ordering::SeqCst); 293 update_wall_time(); 294 295 compiler_fence(Ordering::SeqCst); 296 return prev + add_jiffies; 297 } 298 299 pub fn clock() -> u64 { 300 return TIMER_JIFFIES.load(Ordering::SeqCst); 301 } 302 // ====== 重构完成后请删掉extern C ====== 303 #[no_mangle] 304 pub extern "C" fn rs_clock() -> u64 { 305 clock() 306 } 307 308 // ====== 以下为给C提供的接口 ====== 309 #[no_mangle] 310 pub extern "C" fn rs_schedule_timeout(timeout: i64) -> i64 { 311 match schedule_timeout(timeout) { 312 Ok(v) => { 313 return v; 314 } 315 Err(e) => { 316 kdebug!("rs_schedule_timeout run failed"); 317 return e.to_posix_errno() as i64; 318 } 319 } 320 } 321 322 #[no_mangle] 323 pub extern "C" fn rs_timer_init() { 324 timer_init(); 325 } 326 327 #[no_mangle] 328 pub extern "C" fn rs_timer_next_n_ms_jiffies(expire_ms: u64) -> u64 { 329 return next_n_ms_timer_jiffies(expire_ms); 330 } 331 332 #[no_mangle] 333 pub extern "C" fn rs_timer_next_n_us_jiffies(expire_us: u64) -> u64 { 334 return next_n_us_timer_jiffies(expire_us); 335 } 336 337 #[no_mangle] 338 pub extern "C" fn rs_timer_get_first_expire() -> i64 { 339 match timer_get_first_expire() { 340 Ok(v) => return v as i64, 341 Err(_) => return 0, 342 } 343 } 344 345 #[no_mangle] 346 pub extern "C" fn rs_update_timer_jiffies(add_jiffies: u64) -> u64 { 347 return update_timer_jiffies(add_jiffies); 348 } 349