xref: /DragonOS/kernel/src/libs/notifier.rs (revision b5b571e02693d91eb6918d3b7561e088c3e7ee81)
126887c63SLoGin #![allow(dead_code)]
206d5e247SLoGin use core::fmt::Debug;
306d5e247SLoGin 
4729a96efSXshine use crate::{
5729a96efSXshine     kwarn,
6729a96efSXshine     libs::{rwlock::RwLock, spinlock::SpinLock},
7729a96efSXshine };
8729a96efSXshine use alloc::{sync::Arc, vec::Vec};
991e9d4abSLoGin use system_error::SystemError;
10729a96efSXshine 
11729a96efSXshine /// @brief 通知链节点
1206d5e247SLoGin pub trait NotifierBlock<V: Clone + Copy, T>: Debug + Send + Sync {
13729a96efSXshine     /// @brief 通知链中注册的回调函数类型
1406d5e247SLoGin     fn notifier_call(&self, action: V, data: Option<&T>) -> i32;
15729a96efSXshine     /// @brief 通知链节点的优先级
16729a96efSXshine     fn priority(&self) -> i32;
17729a96efSXshine }
18729a96efSXshine 
19729a96efSXshine /// @brief 通知链
20729a96efSXshine // TODO: 考虑使用红黑树封装
2106d5e247SLoGin #[derive(Debug)]
2206d5e247SLoGin struct NotifierChain<V: Clone + Copy, T>(Vec<Arc<dyn NotifierBlock<V, T>>>);
23729a96efSXshine 
2406d5e247SLoGin impl<V: Clone + Copy, T> NotifierChain<V, T> {
25729a96efSXshine     pub fn new() -> Self {
26729a96efSXshine         Self(vec![])
27729a96efSXshine     }
28729a96efSXshine 
29729a96efSXshine     /// @brief 将节点注册到通知链
30729a96efSXshine     /// @param unique_priority 检查通知链中优先级的唯一性
31729a96efSXshine     pub fn register(
32729a96efSXshine         &mut self,
3306d5e247SLoGin         block: Arc<dyn NotifierBlock<V, T>>,
34729a96efSXshine         unique_priority: bool,
35729a96efSXshine     ) -> Result<(), SystemError> {
36729a96efSXshine         let mut index: usize = 0;
37729a96efSXshine 
38729a96efSXshine         // 在 notifier chain中寻找第一个优先级比要插入块低的块
39729a96efSXshine         for b in self.0.iter() {
40729a96efSXshine             // 判断之前是否已经注册过该节点
41*b5b571e0SLoGin             if Arc::ptr_eq(&block, b) {
42729a96efSXshine                 kwarn!(
43729a96efSXshine                     "notifier callback {:?} already registered",
44729a96efSXshine                     Arc::as_ptr(&block)
45729a96efSXshine                 );
46729a96efSXshine                 return Err(SystemError::EEXIST);
47729a96efSXshine             }
48729a96efSXshine 
49729a96efSXshine             if block.priority() > b.priority() {
50729a96efSXshine                 break;
51729a96efSXshine             }
52729a96efSXshine 
53729a96efSXshine             // 优先级唯一性检测
54729a96efSXshine             if block.priority() == b.priority() && unique_priority {
55729a96efSXshine                 return Err(SystemError::EBUSY);
56729a96efSXshine             }
57729a96efSXshine 
58729a96efSXshine             index += 1;
59729a96efSXshine         }
60729a96efSXshine 
61729a96efSXshine         // 插入 notifier chain
62729a96efSXshine         self.0.insert(index, block);
63729a96efSXshine         return Ok(());
64729a96efSXshine     }
65729a96efSXshine 
66729a96efSXshine     /// @brief 在通知链中取消注册节点
6706d5e247SLoGin     pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
68*b5b571e0SLoGin         let remove = self.0.extract_if(|b| Arc::ptr_eq(&block, b));
69729a96efSXshine         match remove.count() {
70729a96efSXshine             0 => return Err(SystemError::ENOENT),
71729a96efSXshine             _ => return Ok(()),
72729a96efSXshine         }
73729a96efSXshine     }
74729a96efSXshine 
7506d5e247SLoGin     /// 通知链进行事件通知
7606d5e247SLoGin     ///
7706d5e247SLoGin     /// ## 参数
7806d5e247SLoGin     ///
7906d5e247SLoGin     /// - nr_to_call 最大调用回调函数的数量,如果为None,则不限制次数
8006d5e247SLoGin     ///
8106d5e247SLoGin     /// ## 返回
8206d5e247SLoGin     ///
8306d5e247SLoGin     /// (最后一次回调函数的返回值,回调次数)
8406d5e247SLoGin     ///
8506d5e247SLoGin     /// TODO: 增加 NOTIFIER_STOP_MASK 相关功能
86729a96efSXshine     pub fn call_chain(
87729a96efSXshine         &self,
8806d5e247SLoGin         action: V,
89729a96efSXshine         data: Option<&T>,
90729a96efSXshine         nr_to_call: Option<usize>,
91729a96efSXshine     ) -> (i32, usize) {
92729a96efSXshine         let mut ret: i32 = 0;
93729a96efSXshine         let mut nr_calls: usize = 0;
94729a96efSXshine 
95729a96efSXshine         for b in self.0.iter() {
96729a96efSXshine             if nr_to_call.is_some_and(|x| nr_calls >= x) {
97729a96efSXshine                 break;
98729a96efSXshine             }
99729a96efSXshine             ret = b.notifier_call(action, data);
100729a96efSXshine             nr_calls += 1;
101729a96efSXshine         }
102729a96efSXshine         return (ret, nr_calls);
103729a96efSXshine     }
104729a96efSXshine }
105729a96efSXshine 
106729a96efSXshine /// @brief 原子的通知链,使用 SpinLock 进行同步
10706d5e247SLoGin #[derive(Debug)]
10806d5e247SLoGin pub struct AtomicNotifierChain<V: Clone + Copy, T>(SpinLock<NotifierChain<V, T>>);
109729a96efSXshine 
110*b5b571e0SLoGin impl<V: Clone + Copy, T> Default for AtomicNotifierChain<V, T> {
111*b5b571e0SLoGin     fn default() -> Self {
112*b5b571e0SLoGin         Self::new()
113*b5b571e0SLoGin     }
114*b5b571e0SLoGin }
115*b5b571e0SLoGin 
11606d5e247SLoGin impl<V: Clone + Copy, T> AtomicNotifierChain<V, T> {
117729a96efSXshine     pub fn new() -> Self {
11806d5e247SLoGin         Self(SpinLock::new(NotifierChain::<V, T>::new()))
119729a96efSXshine     }
120729a96efSXshine 
12106d5e247SLoGin     pub fn register(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
122729a96efSXshine         let mut notifier_chain_guard = self.0.lock();
123729a96efSXshine         return notifier_chain_guard.register(block, false);
124729a96efSXshine     }
125729a96efSXshine 
126729a96efSXshine     pub fn register_unique_prio(
127729a96efSXshine         &mut self,
12806d5e247SLoGin         block: Arc<dyn NotifierBlock<V, T>>,
129729a96efSXshine     ) -> Result<(), SystemError> {
130729a96efSXshine         let mut notifier_chain_guard = self.0.lock();
131729a96efSXshine         return notifier_chain_guard.register(block, true);
132729a96efSXshine     }
133729a96efSXshine 
13406d5e247SLoGin     pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
135729a96efSXshine         let mut notifier_chain_guard = self.0.lock();
136729a96efSXshine         return notifier_chain_guard.unregister(block);
137729a96efSXshine     }
138729a96efSXshine 
139729a96efSXshine     pub fn call_chain(
140729a96efSXshine         &self,
14106d5e247SLoGin         action: V,
142729a96efSXshine         data: Option<&T>,
143729a96efSXshine         nr_to_call: Option<usize>,
144729a96efSXshine     ) -> (i32, usize) {
145729a96efSXshine         let notifier_chain_guard = self.0.lock();
146729a96efSXshine         return notifier_chain_guard.call_chain(action, data, nr_to_call);
147729a96efSXshine     }
148729a96efSXshine }
149729a96efSXshine 
150729a96efSXshine /// @brief 可阻塞的通知链,使用 RwLock 进行同步
151729a96efSXshine // TODO: 使用 semaphore 封装
15206d5e247SLoGin #[derive(Debug)]
15306d5e247SLoGin pub struct BlockingNotifierChain<V: Clone + Copy, T>(RwLock<NotifierChain<V, T>>);
154729a96efSXshine 
15506d5e247SLoGin impl<V: Clone + Copy, T> BlockingNotifierChain<V, T> {
156729a96efSXshine     pub fn new() -> Self {
15706d5e247SLoGin         Self(RwLock::new(NotifierChain::<V, T>::new()))
158729a96efSXshine     }
159729a96efSXshine 
16006d5e247SLoGin     pub fn register(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
161729a96efSXshine         let mut notifier_chain_guard = self.0.write();
162729a96efSXshine         return notifier_chain_guard.register(block, false);
163729a96efSXshine     }
164729a96efSXshine 
165729a96efSXshine     pub fn register_unique_prio(
166729a96efSXshine         &mut self,
16706d5e247SLoGin         block: Arc<dyn NotifierBlock<V, T>>,
168729a96efSXshine     ) -> Result<(), SystemError> {
169729a96efSXshine         let mut notifier_chain_guard = self.0.write();
170729a96efSXshine         return notifier_chain_guard.register(block, true);
171729a96efSXshine     }
172729a96efSXshine 
17306d5e247SLoGin     pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
174729a96efSXshine         let mut notifier_chain_guard = self.0.write();
175729a96efSXshine         return notifier_chain_guard.unregister(block);
176729a96efSXshine     }
177729a96efSXshine 
178729a96efSXshine     pub fn call_chain(
179729a96efSXshine         &self,
18006d5e247SLoGin         action: V,
181729a96efSXshine         data: Option<&T>,
182729a96efSXshine         nr_to_call: Option<usize>,
183729a96efSXshine     ) -> (i32, usize) {
184729a96efSXshine         let notifier_chain_guard = self.0.read();
185729a96efSXshine         return notifier_chain_guard.call_chain(action, data, nr_to_call);
186729a96efSXshine     }
187729a96efSXshine }
188729a96efSXshine 
189729a96efSXshine /// @brief 原始的通知链,由调用者自行考虑同步
19006d5e247SLoGin pub struct RawNotifierChain<V: Clone + Copy, T>(NotifierChain<V, T>);
191729a96efSXshine 
19206d5e247SLoGin impl<V: Clone + Copy, T> RawNotifierChain<V, T> {
193729a96efSXshine     pub fn new() -> Self {
19406d5e247SLoGin         Self(NotifierChain::<V, T>::new())
195729a96efSXshine     }
196729a96efSXshine 
19706d5e247SLoGin     pub fn register(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
198729a96efSXshine         return self.0.register(block, false);
199729a96efSXshine     }
200729a96efSXshine 
20106d5e247SLoGin     pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
202729a96efSXshine         return self.0.unregister(block);
203729a96efSXshine     }
204729a96efSXshine 
205729a96efSXshine     pub fn call_chain(
206729a96efSXshine         &self,
20706d5e247SLoGin         action: V,
208729a96efSXshine         data: Option<&T>,
209729a96efSXshine         nr_to_call: Option<usize>,
210729a96efSXshine     ) -> (i32, usize) {
211729a96efSXshine         return self.0.call_chain(action, data, nr_to_call);
212729a96efSXshine     }
213729a96efSXshine }
214