1.多线程删除注册的事件,因为事件响应总是会调用回调的,因此,在这通过注册和删除回调函数来阐述
2.由于多线程环境去处理,那么需要注意事件增删的接口,会在任何地方调用,因此,需要处理好,即保证无递归产生死锁也要保证互斥性
3.代码是伪代码,处理流程参考了libevent,libevent对于event的删除就是这么做的
4.有可能描述不太清晰,具体可以去看libevent代码
class Base
{
//注册回调函数
attach(Proc fn);
//脱离注册的事件
detach(Proc fn)
{
//加锁
lock(mutex);
//判断当前执行的回调函数是否和要删除的回调是同一个,以及执行detach的线程是否和base在同一个线程
if( current_callback_fn == fn && owner_thread_id != pthread_self()){
++current_callback_fn_waiters
//如果等待条件广播
pthread_cond_wait(cond,mutex);
}
//从回调事件列表中删除注册的回调
remove(callback_fn_list,fn);
//出锁
unlock(mutex);
}
//base所在线程体执行process方法
process()
{
while(1){
//上锁,取就绪的回调函数
lock(mutex);
current_callback_fn = tail(callback_fn_list);
unlock(mutex);
//执行回调函数
current_callback_fn (args);
//查看是否有对当前回调的等待者
lock(mutex);
current_callback_fn = NULL;
if(current_callback_fn_waiters > 0){
current_callback_fn_waiters = 0;
//有等待的话,进行广播
pthread_broadcast_cond(cond);
}
unlock(mutex);
}
}
private:
//base所在线程的id
owner_thread_id;
//注册的回调函数列表
callback_fn_list;
//当前正在执行的回调函数
current_callback_fn;
//是否有对当前执行回调函数操作的等待者
current_callback_fn_waiters;
//互斥锁
mutex;
//条件变量
cond;
};线程1执行base的process方法,其他线程执行detach
这是如果注册了回调函数fn如下
fn(args)
{
if 出现某种状态变更
调用detach 删除回调事件
}
那么由于在base的process和detach所做的处理,多线程对注册的注册的事件,就可删除了,而不会导致死锁

10万+

被折叠的 条评论
为什么被折叠?



