您的位置:首页 > 移动开发 > Objective-C

在主线程中慎用WaitForSingleObject (WaitForMultipleObjects)

2015-06-12 09:41 549 查看
下面的代码我调试了将近一个星期,你能够看出什么地方出了问题吗?

线程函数:

DWORD WINAPI ThreadProc(

while(!bTerminate)

{

// 从一个链表中读取信息并且插入到CListCtrl中

// CListCtrl的句柄是通过线程参数传递进来的

for(;;)

{

ReadInfoFromList();

InsertToCListCtrl();

}

}

}

主线程中使用CreateThread启动线程。

当想终止子线程时,在主线程中:

bTerminate = TRUE;

WaitForSingleObject(threadHandle, INFINITE);

可是,以运行到WaitForSingleObject,子线程就Crash了。

为什么呢?

问题原因:

后来我终于在InsertItem的反汇编中发现了如下的代码

call dword ptr [__imp__SendMessageA@16 (7C141B54h)]

可见,InsertItem是必须借助消息循环来完成任务的。如果我们在主线程中WaitForSingleObject了,必然导致主线程阻塞,也就导致了消息循环的阻塞,最终导致工作线程Crash掉了*_*

解决方案:

为了解决在主线程中Wait的问题,微软专门设计了一个函数MsgWaitForMultipleObjects,这个函数即可以等待信号(thread,event,mutex等等),也可以等待消息(MSG)。即不论有信号被激发或者有消息到来,此函数都可以返回。呵呵,那么我的解决办法也就出来了。

将上面的WaitForSingleObject用下面的代码替换:

while(TRUE)

{

DWORD result ;

MSG msg ;

result = MsgWaitForMultipleObjects(1, &readThreadHandle,

FALSE, INFINITE, QS_ALLINPUT);

if (result == (WAIT_OBJECT_0))

{

break;

}

else

{

PeekMessage(&msg, NULL, 0, 0, PM_REMOVE);

DispatchMessage(&msg);

}

}

总结:

如果在工作线程中有可能涉及到了消息驱动的API,那么不能在主线程中使用WaitForSingleObject一类函数,而必须使用上述的方案。

本文转载自:
http://www.cnblogs.com/zhangzhifeng/archive/2011/08/23/2150147.html
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: