Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Who owns CWinThread after it was created by AfxBeginThread?

Tags:

c++

mfc

I am starting a thread by using AfxBeginThread. This returns a pointer to a new CWinThread object.

MSDN states that this pointer is NULL and it will deallocate everything if thread creation fails. However as soon as the thread exits after starting regularly the CWinThread object still exists. I am not sure if I should delete the CWinThread object or if this is done by MFC itself (though it does not seem so).

FYI it is not likely that the thread exits, since it should run until the application ends. However since I use it to be part of a thread pool, I do not want the CWinThread to hang aorund for ever.

like image 226
Alex Avatar asked Mar 15 '12 16:03

Alex


3 Answers

The responsibility for cleaning up the CWinThread object depends on it's m_bAutoDelete value. The default is to delete itself. For fire and forget short running threads this is fine. It will clean up after itself.

If your thread is long running and needs to be told it's time to quit or otherwise interacted with, you will want that CWinThread handle to remain valid and not point to a self-deleted object.

If you set m_bAutoDelete to FALSE, you claim responsibility for deleting it. To play it safe with the returned pointer you should create suspended and set it to FALSE before resuming as suggested by Joseph Newcomer in his Using Worker Threads article.

   thread = AfxBeginThread(proc, this, 
                       THREAD_PRIORITY_NORMAL, // default: use it
                       0,     // default stack size 
                       CREATE_SUSPENDED); // let us set auto delete
   if(thread) { // protect against that rare NULL return
       thread->m_bAutoDelete = FALSE;
       thread->ResumeThread();
   }
like image 179
jla Avatar answered Oct 24 '22 09:10

jla


I never trusted CWinThread to clean up after itself. I usually create threads and I tell MFC that I'll do the clean up, specially when the program is closing:

CWinThread *thread = AfxBeginThread(...); 
thread->m_bAutoDelete = FALSE;

You will, however, have to save the thread pointer otherwise you'll have memory leaks.

like image 4
Eddie Paz Avatar answered Oct 24 '22 09:10

Eddie Paz


If your thread is still running, you shouldn't delete it. Once it has stopped, just use operator delete on the pointer returned by AfxBeginThread in order to free the memory used by the thread:

CWinThread *thread = AfxBeginThread(...);
/* ... */
// now wait for it to terminate
WaitForSingleObject(thread->m_hThread, INFINITE); 
delete thread;

You should store the CWinThread pointers until your thread/application ends, so that you can free the memory allocated for them. Otherwise, you'll have a memory leak.

like image 2
mfontanini Avatar answered Oct 24 '22 10:10

mfontanini