First you have to start the thread in a way so MFC doesn't delete the thread object when it's finished, the default setting for MFC thread is to delete itself so you want to turn that off.
m_thread = AfxBeginThread(ThreadProc, this, THREAD_PRIORITY_NORMAL ,CREATE_SUSPENDED);
m_thread->m_bAutoDelete = FALSE;
Now in the thread, you want a mechanism that the caller thread can send it a signal to end itself. There are multiple ways, one is the
WaitForSingleObject to check the status of the signal or another way is to simply send this thread a message to end itself. This is graceful ending rather killing it.
While this thread is ending itself (= exiting the thread function, cleaning up), you can have the main thread wait on it to finish before it exits.
int wait = 2000 // seconds ( I am waiting for 2 seconds for worker to finish)
int dwRes = WaitForSingleObject( m_thread->m_hThread, wait);
TRACE( _T("worker thread just finished") ); break;
TRACE( _T("timed out, worker thread is still busy") ); break;
m_bAutoDelete = FALSE above made it possible we still have a valid handle when thread finishes so we can wait on it. The last thing you want to do now is delete the CWinThread object to free its memory (since we took the responsibility to do that).