因为项目原因,需要处理socket连接超时资源释放问题
原来使用单个线程轮巡,效率较低,后改为TimerQueue,参考文档http://blog.csdn.net/querw/article/details/6600327
官方的帮助文档: http://msdn.microsoft.com/zh-cn/office/ms687003(v=vs.85)很简略
使用流程:
1. 创建TimerQueue, // Create the timer queue.
hTimerQueue = CreateTimerQueue();
2. 新建Timer,加入Queue并启动处理回调
// Set a timer to call the timer routine in 10 seconds.
CreateTimerQueueTimer( &hTimer, hTimerQueue, (WAITORTIMERCALLBACK)TimerRoutine, &arg , 10000, 0, 0)
//循环处理函数
static VOID CALLBACK TimerRoutine(PVOID lpParam, BOOLEAN TimerOrWaitFired)
{
// ToDO Something
}
3.资源释放
如果不再使用,删除单个Timer
DeleteTimerQueueTimer(Handle hTimer, Handle hTimerQueue,HANDLE CompletionEvent)
删除整个Queue
DeleteTimerQueue(hTimerQueue)
有几点需要注意:
1. 在单进程中要创建多个TimerQueue,windows2003及以下是不支持的,后来查了资料才搞明白,原因是
TimerQueue的依赖windows线程池。而2003及以前系统不支持单个进程中有多个线程池。
2. TimerRoutine函数最好为全局static函数。开始作为static方法放在类中,编译没有问题,但在2003下面有
崩溃现象,后续改为全局后,问题解决。原因待分析。
3.如果在TimerRoutine中有需要释放的资源,使用ChangeTimerQueueTimer,将DueTimer置为0,则会立
即执行回调函数,可以快速释放堆上的资源。
补充一下:
ChangeTimerQueueTimer(
__in_opt HANDLE TimerQueue,
__inout HANDLE Timer,
__in ULONG DueTime,
__in ULONG Period
);
这个方法挺好用,具体来说从某次操作完成后30秒无操作就清理,就设置DueTime=30,Period为0,
这样可将原来的轮训方式修改为定时器,到了设定时间(如30秒)就处理回调。
附参考文档:http://blog.csdn.net/woshinia/article/details/8585930