1 #![allow(dead_code)] 2 use system_error::SystemError; 3 4 use crate::{ 5 libs::{spinlock::SpinLock, wait_queue::WaitQueue}, 6 time::timer::schedule_timeout, 7 }; 8 9 const COMPLETE_ALL: u32 = core::u32::MAX; 10 const MAX_TIMEOUT: i64 = core::i64::MAX; 11 12 #[derive(Debug)] 13 pub struct Completion { 14 inner: SpinLock<InnerCompletion>, 15 } 16 17 impl Completion { new() -> Self18 pub const fn new() -> Self { 19 Self { 20 inner: SpinLock::new(InnerCompletion::new()), 21 } 22 } 23 24 /// @brief 基本函数:通用的处理wait命令的函数(即所有wait_for_completion函数最核心部分在这里) 25 /// 26 /// @param timeout 非负整数 27 /// @param interuptible 设置进程是否能被打断 28 /// @return 返回剩余时间或者SystemError do_wait_for_common(&self, mut timeout: i64, interuptible: bool) -> Result<i64, SystemError>29 fn do_wait_for_common(&self, mut timeout: i64, interuptible: bool) -> Result<i64, SystemError> { 30 let mut inner = self.inner.lock_irqsave(); 31 32 if inner.done == 0 { 33 //loop break 类似 do while 保证进行一次信号检测 34 loop { 35 //检查当前线程是否有未处理的信号 36 // if (signal_pending_state(state, current)) { 37 // timeout = -ERESTARTSYS; 38 // break; 39 //} 40 41 if interuptible { 42 unsafe { inner.wait_queue.sleep_without_schedule() }; 43 } else { 44 unsafe { inner.wait_queue.sleep_without_schedule_uninterruptible() }; 45 } 46 drop(inner); 47 timeout = schedule_timeout(timeout)?; 48 inner = self.inner.lock_irqsave(); 49 if inner.done != 0 || timeout <= 0 { 50 break; 51 } 52 } 53 inner.wait_queue.wakeup(None); 54 if inner.done == 0 { 55 drop(inner); 56 return Ok(timeout); 57 } 58 } 59 if inner.done != COMPLETE_ALL { 60 inner.done -= 1; 61 } 62 drop(inner); 63 return Ok(if timeout > 0 { timeout } else { 1 }); 64 } 65 66 /// @brief 等待指定时间,超时后就返回, 同时设置pcb state为uninteruptible. 67 /// @param timeout 非负整数,等待指定时间,超时后就返回/或者提前done wait_for_completion_timeout(&self, timeout: i64) -> Result<i64, SystemError>68 pub fn wait_for_completion_timeout(&self, timeout: i64) -> Result<i64, SystemError> { 69 self.do_wait_for_common(timeout, false) 70 } 71 72 /// @brief 等待completion命令唤醒进程, 同时设置pcb state 为uninteruptible. wait_for_completion(&self) -> Result<i64, SystemError>73 pub fn wait_for_completion(&self) -> Result<i64, SystemError> { 74 self.do_wait_for_common(MAX_TIMEOUT, false) 75 } 76 77 /// @brief @brief 等待completion的完成,但是可以被中断 wait_for_completion_interruptible(&self) -> Result<i64, SystemError>78 pub fn wait_for_completion_interruptible(&self) -> Result<i64, SystemError> { 79 self.do_wait_for_common(MAX_TIMEOUT, true) 80 } 81 wait_for_completion_interruptible_timeout( &mut self, timeout: i64, ) -> Result<i64, SystemError>82 pub fn wait_for_completion_interruptible_timeout( 83 &mut self, 84 timeout: i64, 85 ) -> Result<i64, SystemError> { 86 assert!(timeout >= 0); 87 self.do_wait_for_common(timeout, true) 88 } 89 90 /// @brief 唤醒一个wait_queue中的节点 complete(&self)91 pub fn complete(&self) { 92 let mut inner = self.inner.lock_irqsave(); 93 if inner.done != COMPLETE_ALL { 94 inner.done += 1; 95 } 96 inner.wait_queue.wakeup(None); 97 // 脱离生命周期,自动释放guard 98 } 99 100 /// @brief 永久标记done为Complete_All,并从wait_queue中删除所有节点 complete_all(&self)101 pub fn complete_all(&self) { 102 let mut inner = self.inner.lock_irqsave(); 103 inner.done = COMPLETE_ALL; 104 inner.wait_queue.wakeup_all(None); 105 // 脱离生命周期,自动释放guard 106 } 107 108 /// @brief @brief 尝试获取completion的一个done!如果您在wait之前加上这个函数作为判断,说不定会加快运行速度。 109 /// 110 /// @return true - 表示不需要wait_for_completion,并且已经获取到了一个completion(即返回true意味着done已经被 减1 ) 111 /// @return false - 表示当前done=0,您需要进入等待,即wait_for_completion try_wait_for_completion(&mut self) -> bool112 pub fn try_wait_for_completion(&mut self) -> bool { 113 let mut inner = self.inner.lock_irqsave(); 114 if inner.done == 0 { 115 return false; 116 } 117 118 if inner.done != 0 { 119 return false; 120 } else if inner.done != COMPLETE_ALL { 121 inner.done -= 1; 122 } 123 return true; 124 // 脱离生命周期,自动释放guard 125 } 126 127 // @brief 测试一个completion是否有waiter。(即done是不是等于0) completion_done(&self) -> bool128 pub fn completion_done(&self) -> bool { 129 let inner = self.inner.lock_irqsave(); 130 if inner.done == 0 { 131 return false; 132 } 133 134 if inner.done == 0 { 135 return false; 136 } 137 return true; 138 // 脱离生命周期,自动释放guard 139 } 140 } 141 #[derive(Debug)] 142 pub struct InnerCompletion { 143 done: u32, 144 wait_queue: WaitQueue, 145 } 146 147 impl InnerCompletion { new() -> Self148 pub const fn new() -> Self { 149 Self { 150 done: 0, 151 wait_queue: WaitQueue::INIT, 152 } 153 } 154 } 155