mirror of
https://github.com/DragonOS-Community/DragonOS.git
synced 2025-06-18 16:26:31 +00:00
完善设备驱动模型,基于kset、kobj来维护对象之间的关系 (#401)
* 使用kobj和kset管理/sys文件夹下的对象 * 修改notifier,把action从u64换为泛型。 * 完善设备驱动模型,基于kset、kobj来维护对象之间的关系
This commit is contained in:
@ -1,4 +1,6 @@
|
||||
#![allow(dead_code)]
|
||||
use core::fmt::Debug;
|
||||
|
||||
use crate::{
|
||||
kwarn,
|
||||
libs::{rwlock::RwLock, spinlock::SpinLock},
|
||||
@ -7,18 +9,19 @@ use crate::{
|
||||
use alloc::{sync::Arc, vec::Vec};
|
||||
|
||||
/// @brief 通知链节点
|
||||
pub trait NotifierBlock<T> {
|
||||
pub trait NotifierBlock<V: Clone + Copy, T>: Debug + Send + Sync {
|
||||
/// @brief 通知链中注册的回调函数类型
|
||||
fn notifier_call(&self, action: u64, data: Option<&T>) -> i32;
|
||||
fn notifier_call(&self, action: V, data: Option<&T>) -> i32;
|
||||
/// @brief 通知链节点的优先级
|
||||
fn priority(&self) -> i32;
|
||||
}
|
||||
|
||||
/// @brief 通知链
|
||||
// TODO: 考虑使用红黑树封装
|
||||
struct NotifierChain<T>(Vec<Arc<dyn NotifierBlock<T>>>);
|
||||
#[derive(Debug)]
|
||||
struct NotifierChain<V: Clone + Copy, T>(Vec<Arc<dyn NotifierBlock<V, T>>>);
|
||||
|
||||
impl<T> NotifierChain<T> {
|
||||
impl<V: Clone + Copy, T> NotifierChain<V, T> {
|
||||
pub fn new() -> Self {
|
||||
Self(vec![])
|
||||
}
|
||||
@ -27,7 +30,7 @@ impl<T> NotifierChain<T> {
|
||||
/// @param unique_priority 检查通知链中优先级的唯一性
|
||||
pub fn register(
|
||||
&mut self,
|
||||
block: Arc<dyn NotifierBlock<T>>,
|
||||
block: Arc<dyn NotifierBlock<V, T>>,
|
||||
unique_priority: bool,
|
||||
) -> Result<(), SystemError> {
|
||||
let mut index: usize = 0;
|
||||
@ -61,7 +64,7 @@ impl<T> NotifierChain<T> {
|
||||
}
|
||||
|
||||
/// @brief 在通知链中取消注册节点
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<T>>) -> Result<(), SystemError> {
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
|
||||
let remove = self
|
||||
.0
|
||||
.drain_filter(|b| Arc::as_ptr(&block) == Arc::as_ptr(b));
|
||||
@ -71,13 +74,20 @@ impl<T> NotifierChain<T> {
|
||||
}
|
||||
}
|
||||
|
||||
/// @brief 通知链进行事件通知
|
||||
/// @param nr_to_call 回调函数次数
|
||||
/// @return (最后一次回调函数的返回值,回调次数)
|
||||
// TODO: 增加 NOTIFIER_STOP_MASK 相关功能
|
||||
/// 通知链进行事件通知
|
||||
///
|
||||
/// ## 参数
|
||||
///
|
||||
/// - nr_to_call 最大调用回调函数的数量,如果为None,则不限制次数
|
||||
///
|
||||
/// ## 返回
|
||||
///
|
||||
/// (最后一次回调函数的返回值,回调次数)
|
||||
///
|
||||
/// TODO: 增加 NOTIFIER_STOP_MASK 相关功能
|
||||
pub fn call_chain(
|
||||
&self,
|
||||
action: u64,
|
||||
action: V,
|
||||
data: Option<&T>,
|
||||
nr_to_call: Option<usize>,
|
||||
) -> (i32, usize) {
|
||||
@ -96,34 +106,35 @@ impl<T> NotifierChain<T> {
|
||||
}
|
||||
|
||||
/// @brief 原子的通知链,使用 SpinLock 进行同步
|
||||
pub struct AtomicNotifierChain<T>(SpinLock<NotifierChain<T>>);
|
||||
#[derive(Debug)]
|
||||
pub struct AtomicNotifierChain<V: Clone + Copy, T>(SpinLock<NotifierChain<V, T>>);
|
||||
|
||||
impl<T> AtomicNotifierChain<T> {
|
||||
impl<V: Clone + Copy, T> AtomicNotifierChain<V, T> {
|
||||
pub fn new() -> Self {
|
||||
Self(SpinLock::new(NotifierChain::<T>::new()))
|
||||
Self(SpinLock::new(NotifierChain::<V, T>::new()))
|
||||
}
|
||||
|
||||
pub fn register(&mut self, block: Arc<dyn NotifierBlock<T>>) -> Result<(), SystemError> {
|
||||
pub fn register(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
|
||||
let mut notifier_chain_guard = self.0.lock();
|
||||
return notifier_chain_guard.register(block, false);
|
||||
}
|
||||
|
||||
pub fn register_unique_prio(
|
||||
&mut self,
|
||||
block: Arc<dyn NotifierBlock<T>>,
|
||||
block: Arc<dyn NotifierBlock<V, T>>,
|
||||
) -> Result<(), SystemError> {
|
||||
let mut notifier_chain_guard = self.0.lock();
|
||||
return notifier_chain_guard.register(block, true);
|
||||
}
|
||||
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<T>>) -> Result<(), SystemError> {
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
|
||||
let mut notifier_chain_guard = self.0.lock();
|
||||
return notifier_chain_guard.unregister(block);
|
||||
}
|
||||
|
||||
pub fn call_chain(
|
||||
&self,
|
||||
action: u64,
|
||||
action: V,
|
||||
data: Option<&T>,
|
||||
nr_to_call: Option<usize>,
|
||||
) -> (i32, usize) {
|
||||
@ -134,34 +145,35 @@ impl<T> AtomicNotifierChain<T> {
|
||||
|
||||
/// @brief 可阻塞的通知链,使用 RwLock 进行同步
|
||||
// TODO: 使用 semaphore 封装
|
||||
pub struct BlockingNotifierChain<T>(RwLock<NotifierChain<T>>);
|
||||
#[derive(Debug)]
|
||||
pub struct BlockingNotifierChain<V: Clone + Copy, T>(RwLock<NotifierChain<V, T>>);
|
||||
|
||||
impl<T> BlockingNotifierChain<T> {
|
||||
impl<V: Clone + Copy, T> BlockingNotifierChain<V, T> {
|
||||
pub fn new() -> Self {
|
||||
Self(RwLock::new(NotifierChain::<T>::new()))
|
||||
Self(RwLock::new(NotifierChain::<V, T>::new()))
|
||||
}
|
||||
|
||||
pub fn register(&mut self, block: Arc<dyn NotifierBlock<T>>) -> Result<(), SystemError> {
|
||||
pub fn register(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
|
||||
let mut notifier_chain_guard = self.0.write();
|
||||
return notifier_chain_guard.register(block, false);
|
||||
}
|
||||
|
||||
pub fn register_unique_prio(
|
||||
&mut self,
|
||||
block: Arc<dyn NotifierBlock<T>>,
|
||||
block: Arc<dyn NotifierBlock<V, T>>,
|
||||
) -> Result<(), SystemError> {
|
||||
let mut notifier_chain_guard = self.0.write();
|
||||
return notifier_chain_guard.register(block, true);
|
||||
}
|
||||
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<T>>) -> Result<(), SystemError> {
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
|
||||
let mut notifier_chain_guard = self.0.write();
|
||||
return notifier_chain_guard.unregister(block);
|
||||
}
|
||||
|
||||
pub fn call_chain(
|
||||
&self,
|
||||
action: u64,
|
||||
action: V,
|
||||
data: Option<&T>,
|
||||
nr_to_call: Option<usize>,
|
||||
) -> (i32, usize) {
|
||||
@ -171,24 +183,24 @@ impl<T> BlockingNotifierChain<T> {
|
||||
}
|
||||
|
||||
/// @brief 原始的通知链,由调用者自行考虑同步
|
||||
pub struct RawNotifierChain<T>(NotifierChain<T>);
|
||||
pub struct RawNotifierChain<V: Clone + Copy, T>(NotifierChain<V, T>);
|
||||
|
||||
impl<T> RawNotifierChain<T> {
|
||||
impl<V: Clone + Copy, T> RawNotifierChain<V, T> {
|
||||
pub fn new() -> Self {
|
||||
Self(NotifierChain::<T>::new())
|
||||
Self(NotifierChain::<V, T>::new())
|
||||
}
|
||||
|
||||
pub fn register(&mut self, block: Arc<dyn NotifierBlock<T>>) -> Result<(), SystemError> {
|
||||
pub fn register(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
|
||||
return self.0.register(block, false);
|
||||
}
|
||||
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<T>>) -> Result<(), SystemError> {
|
||||
pub fn unregister(&mut self, block: Arc<dyn NotifierBlock<V, T>>) -> Result<(), SystemError> {
|
||||
return self.0.unregister(block);
|
||||
}
|
||||
|
||||
pub fn call_chain(
|
||||
&self,
|
||||
action: u64,
|
||||
action: V,
|
||||
data: Option<&T>,
|
||||
nr_to_call: Option<usize>,
|
||||
) -> (i32, usize) {
|
||||
|
Reference in New Issue
Block a user