于无声处

人生三恨:鲥鱼多剌,海棠无香,需求常变

狗尾续貂:利用引用计数在多线程中安全释放资源
原文标题:IOCP中的socket错误和资源释放处理方法
原文作者:sodme
原文地址:http://blog.csdn.net/sodme/archive/2006/04/17/666062.aspx
原作者声明:本文可以不经作者同意任意转载、复制、传播,但任何对本文的引用均须保留本文的作者、出处及本行声明信息!谢谢!
本文是观大宝SODME的BLOG中文章有感,原文中提到了两种方法(对数据缓冲区使用引用计数机制、在clientsock的对象设计机制上使释放操作线性化),但只讨论了第2种方法的实现。其实在多线程程序里,要让一个释放操作线性化,并不是一件容易的事情,这不仅仅是多个IOCP工作线程的问题(一般来说,我们会为每个CPU设立两个IOCP工作线程),还涉及到其他业务逻辑线程的问题。
比方说,我们通常(就象文中也提到的)会将ClientSocket与接收缓冲区绑定到一个会话对象中(为简化起见,发送数据往往没有用overlapped机制,而是直接用一个异步send,也就不需要发送缓冲区),而这个对象可能被除IOCP工作线程以外的其他线程也用到,比方说一个事件队列的处理线程(我们会在收到数据的时候生成事件对象置入队例中,以类似于Command模式的方法来处理,而这些事件对象会引用到会话对象),或者,也许有某个容器会存放这些会话对象的一个引用,用于定时发送心跳包、会话计数、检索等等,这个时候,会话对象的销毁就不是那么简单的了,换句话说,仅靠“将销毁工作统一到执行GetQueuedCompletionStatus的函数里“是不够的。
在这种情况下,文中提到的第1种“采用引用计数”的方法就比较优雅了,在我的很多实际应用中,都是将会话对象设计为“可引用计数”的,不暴露它的析构函数,而是当引用计数减到0的时候,自动销毁,这样就保证“仅当没有任何人使用它的时候才会释放它”。
利用C++的模板,可以十分方便地模拟出自动引用计数的安全指针:
 



_REFCOUNTED_INCLUDED_
_REFCOUNTED_INCLUDED_


_MT



RefCountable


_MT
refCount_

refCount_




r
_MT
refCount_

refCount_

r
r

r


refCount_



refCount_


_MT




refCount_
RefCountable
RefCountable RefCountable


T
RefCountedPtr


T ptr ptr
ptr_
ptr_

RefCountedPtrT sour sourptr_
ptr_
ptr_

RefCountedPtr RefCountedPtrT right
right
ptr_
ptr_
ptr_ rightptr_
ptr_
ptr_




ptr_
ptr_


T ptr_
T

RefCountedPtrT left RefCountedPtrT right
leftptr_ rightptr_

RefCountedPtrT left RefCountedPtrT right
leftptr_ rightptr_

RefCountedPtrT left RefCountedPtrT right
leftptr_ rightptr_

RefCountedPtrT left RefCountedPtrT right
leftptr_ rightptr_

RefCountedPtrT left RefCountedPtrT right
leftptr_ rightptr_

RefCountedPtrT left RefCountedPtrT right
leftptr_ rightptr_


ptr_
ptr_


T ptr_


T ptr
ptr
ptr
ptr_
ptr_
ptr_ ptr



T ptr_


阅读更多
个人分类: C++
想对作者说点什么? 我来说一句

没有更多推荐了,返回首页

不良信息举报

狗尾续貂:利用引用计数在多线程中安全释放资源

最多只允许输入30个字

加入CSDN,享受更精准的内容推荐,与500万程序员共同成长!
关闭
关闭