Applied patch from Mark Armstrong <marka@availsolutions.com>
This patch fixes two problems. The first is a race condition during a thread exit and a join. The second is condition where a thread can hang during msg/event processing. git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/trunk@16031 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
@@ -965,8 +965,30 @@ wxThreadError wxThread::Delete(ExitCode *pRc)
|
|||||||
|
|
||||||
HANDLE hThread = m_internal->GetHandle();
|
HANDLE hThread = m_internal->GetHandle();
|
||||||
|
|
||||||
// does is still run?
|
// Check if thread is really still running. There is a
|
||||||
if ( isRunning || IsRunning() )
|
// race condition in WinThreadStart between the time the
|
||||||
|
// m_internal->m_state is set to STATE_EXITED and the win32
|
||||||
|
// thread actually exits. It can be flagged as STATE_EXITED
|
||||||
|
// and then we don't wait for it to exit. This will cause
|
||||||
|
// GetExitCodeThread to return STILL_ACTIVE.
|
||||||
|
if ( !isRunning )
|
||||||
|
{
|
||||||
|
if ( !IsRunning() )
|
||||||
|
{
|
||||||
|
if ( ::GetExitCodeThread(hThread, (LPDWORD)&rc) )
|
||||||
|
{
|
||||||
|
if ((DWORD)rc == STILL_ACTIVE)
|
||||||
|
isRunning = TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
isRunning = TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// does it still run?
|
||||||
|
if ( isRunning )
|
||||||
{
|
{
|
||||||
if ( IsMain() )
|
if ( IsMain() )
|
||||||
{
|
{
|
||||||
@@ -1022,13 +1044,24 @@ wxThreadError wxThread::Delete(ExitCode *pRc)
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case WAIT_OBJECT_0 + 1:
|
case WAIT_OBJECT_0 + 1:
|
||||||
// new message arrived, process it
|
|
||||||
if ( !wxTheApp->DoMessage() )
|
|
||||||
{
|
{
|
||||||
// WM_QUIT received: kill the thread
|
MSG peekMsg;
|
||||||
Kill();
|
// Check if a new message has really arrived.
|
||||||
|
// MsgWaitForMultipleObjects can indicate that a message
|
||||||
return wxTHREAD_KILLED;
|
// is ready for processing, but this message may be sucked
|
||||||
|
// up by GetMessage and then GetMessage will hang and not
|
||||||
|
// allow us to process the actual thread exit event.
|
||||||
|
if (::PeekMessage(&peekMsg, (HWND) NULL, 0, 0, PM_NOREMOVE))
|
||||||
|
{
|
||||||
|
// new message arrived, process it
|
||||||
|
if ( !wxTheApp->DoMessage() )
|
||||||
|
{
|
||||||
|
// WM_QUIT received: kill the thread
|
||||||
|
Kill();
|
||||||
|
|
||||||
|
return wxTHREAD_KILLED;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user