-
November 12th, 2008, 02:15 AM
#1
Question for worker threads
Hi all,
I created three worker threads to work for two simultaneous runs at each time and one control (main) thread. The main thread is waiting while two (sub) thread are processing. Then,once the main get any finish signal from those two, it check if it needs to create another run or to stop. The user specify the limit count to stop. I don't want to stop the loop in the main thread unless both two threads finished their runs. Therefore, I made the main thread 'while' loop to go on til both finish.
I don't know it is right to do for running 2 threads at the same time. (actually 3 including main thread).
The problem is it works well sometimes and it doesn't.
For example of problem, the user set 4 runs. Run1 and Run2 start together. Run1 finish first but Run2 stil running. Run1 needs to do 'third' process by creating new thread from main thread. It doesn't do that process and stops. Run2 keeps on running till the current process finishes and go on with third process.
Finally, run2 finish running til the end (forth run) and the loop in main thread never gets out. Meaning that the whole process "hanging" there. After I check the 'while' loop is going on and on. Why is it that way?
I think the logical variables are not stable or something is very wrong. Sometimes, it goes very smoothly.
Pls help me. Thanks in advance.
The codes are as following:
Code:
CEvent Run1, Run2, EContinue;
UINT SubThread1(LPVOID param)
{
//run the process 1
//........
Run1.SetEvent();
return 0;
}
UINT SubThread2(LPVOID param)
{
//run the process 2
//........
Run2.SetEvent();
return 0;
}
UINT MainThread(LPVOID param)
{
BOOL bRestart1 = FALSE;
BOOL bRestart2 = FALSE;
BOOL Continue = FALSE;
BOOL bRunOn;
HANDLE hSub1, hSub2;
CWinThread *pSub1 = NULL;
CWinThread *pSub2 = NULL;
do
{
if( (!Continue) && (!bRestart1) )
{
Run1.ResetEvent();
pSub1 = ::AfxBeginThread(SubThread1, param, THREAD_PRIORITY_NORMAL,
0, CREATE_SUSPENDED);
hSub1 = pSub1->m_hThread;
bRestart1 = TRUE;
::ResumeThread (hSub1);
}
::Sleep(100);
if( (!Continue) && (!bRestart2) )
{
Run2.ResetEvent();
pSub2 = ::AfxBeginThread(SubThread2, param, THREAD_PRIORITY_NORMAL,
0, CREATE_SUSPENDED);
hSub2 = pSub2->m_hThread;
bRestart2 = TRUE;
::ResumeThread (hSub2);
}
::Sleep(100);
if(bRestart1)
{
DWORD run1 = ::WaitForSingleObject( Run1.m_hObject, 0 );
if(run1 == WAIT_OBJECT_0)
{
CloseHandle(hSub1);
pSub1 = NULL;
bRestart1 = FALSE;
::Sleep(100);
}
}
::Sleep(100);
if(bRestart2)
{
DWORD run2 = ::WaitForSingleObject( Run2.m_hObject, 0 );
if(run2 == WAIT_OBJECT_0)
{
CloseHandle(hSub2);
pSub2 = NULL;
bRestart2 = FALSE;
::Sleep(100);
}
}
::Sleep(100);
if ( (!bRestart1) || (!bRestart2) )
{
::PostMessage((HWND)param, WM_ACONTINUE, 0, 0);
//go to the 'acontinue' function to monitor counts.
::Sleep(2000);
DWORD StopLoop = ::WaitForSingleObject(EContinue.m_hObject, 0);
//set the event when the limit is hit
if(StopLoop == WAIT_OBJECT_0)
{
Continue = TRUE;
::Sleep(100);
}
else Continue = FALSE;
}
::Sleep(100);
if(!Continue)
{
bRunOn = TRUE;
}
else
{
if(bRestart1 || bRestart2) bRunOn = TRUE;
else
{
bRunOn = FALSE;
::Sleep(1000);
}
}
::Sleep(100);
}
while(bRunOn);//to signal to continue
return 0;
}
LRESULT MyDlg::AContinue(WPARAM wParam, LPARAM lParam)
{
//count is initialise when start running
if(count == limit) EContinue.SetEvent();
count++;
return 0;
}
void MyDlg::ClickButton()
{
HWND hWnd = GetSafeHwnd();
AfxBeginThread(MainThread, hWnd, THREAD_PRIORITY_ABOVE_NORMAL);
}
Last edited by nankyu; November 12th, 2008 at 02:26 AM.
-
November 12th, 2008, 07:29 AM
#2
Re: Question for worker threads
Hard to say, but CloseHandle is not needed with CWinThread - it is closed automatically if you use autodelete.
And your use of events is superfluous. You can wait directly on the thread handle instead, but then you have to turn off autodelete.
Code:
pSub1 = ::AfxBeginThread(SubThread1, param, THREAD_PRIORITY_NORMAL,
0, CREATE_SUSPENDED);
pSub1->m_bAutoDelete=FALSE;
...
pSub1->ResumeThread();
...
WaitForSingleObject(pSub1->m_hThread, 0);
...
delete pSub1;
Nobody cares how it works as long as it works
-
November 12th, 2008, 08:00 PM
#3
Re: Question for worker threads
Originally Posted by zerver
Hard to say, but CloseHandle is not needed with CWinThread - it is closed automatically if you use autodelete.
And your use of events is superfluous. You can wait directly on the thread handle instead, but then you have to turn off autodelete.
Thanks for your reply. zerver. Yes, I used many events and I think may be they are causing me this problem. I will try as you told me and post my outcomes and question if any.
nankyu
Last edited by nankyu; November 12th, 2008 at 08:04 PM.
-
November 13th, 2008, 07:51 PM
#4
Re: Question for worker threads
Hi,
Zerver, your post helped me to solve the problem. Thanks alot.
Since I used many events and I checked its object's status to control the loop. Now I used few events and no problem occurs.
I think after 'SetEvent()' call for a event, I can see that its object equals to 'WAIT_OBJECT_0'. But as it was looping and called for 'SetEvent()' certain times, its object changed and not equal to 'WAIT_OBJECT_0' anymore (I think that is a problem).
nankyu
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|