фон:Почему win32 поток не выходит автоматически?
В моем приложении, написанном в C++, я создаю рабочий поток, который, в свою очередь создает два потока с помощью CreateThread()
. Два потока, которые создает рабочий поток, общаются с WCF-службой через клиента, который реализован с использованием Windows Web Services API, который предлагает интерфейс программирования приложений C/C++ (API) для создания веб-сервисов и клиентов на основе SOAP. Мое приложение реализует только только клиентом, использующим этот API.
Проблема:
Проблема я столкнулся в том, что все остальные потоки выхода из грациозно, кроме рабочего потока, как вы можете видеть себя в изображении ниже, что WorkerThreadProc
не использует циклов центрального процессора пока он Безразлично Выход. Есть также несколько других потоков, которые не созданы мной, а временем выполнения.
нить состояния следующим образом (по данным ProcessExplorer):
WorkerThreadProc
в Wait: WrUserRequest состояние.wWinMainCRTStartup
находится в Подождите: UserRequest состояние.- Все
TpCallbackIndependent
находятся в Подождите: WrQueue состояние.
Что они ожидают? Какие могут быть возможные причины, по которым мне нужно заглянуть? Кроме того, в чем разница между WrUserRequest и UserRequest? А что означает WrQueue? Я абсолютно не знаю, что здесь происходит.
Вот мой WorkerThreadProc код. Я удалил все операторы лесозаготовительных за исключением последнего в нижней части функции:
DWORD WINAPI WorkerThreadProc(PVOID pVoid)
{
//Initialize GDI+
GdiplusStartupInput gdiplusStartupInput;
ULONG_PTR gdiplusToken;
Status status = GdiplusStartup(&gdiplusToken, &gdiplusStartupInput, NULL);
if (status != Status::Ok)
{
return 1;
}
GuiThreadData *pGuiData = (GuiThreadData*)pVoid;
auto patternIdRequestQueue= new PatternIdRequestQueue();
auto resultQueue = new ResultQueue();
auto patternManager = new PatternManager(patternIdRequestQueue);
LocalScheduler *pScheduler = new LocalScheduler(resultQueue, patternManager);
bool bInitializationDone = pScheduler->Initialize(pGuiData->m_lpCmdLine);
if (!bInitializationDone)
{
return 0;
}
//PatternIdThread
PatternIdThread patternIdThread(patternIdRequestQueue);
DWORD dwPatternIdThreadId;
HANDLE hPatternIdThread = CreateThread(NULL, 0, PatternIdThreadProc, &patternIdThread, 0, &dwPatternIdThreadId);
ResultPersistence resultPersistence(resultQueue);
DWORD dwResultPersistenceThreadId;
HANDLE hResultPersistenceThread = CreateThread(NULL, 0, ResultPersistenceThreadProc, &resultPersistence, 0, &dwResultPersistenceThreadId);
pScheduler->ScheduleWork(pGuiData->m_hWnd, pGuiData->m_hInstance, ss.str());
pScheduler->WaitTillDone();
patternIdThread.Close();
resultPersistence.Close();
delete pScheduler;
//Uninitialize GDI+
GdiplusShutdown(gdiplusToken);
dwRet = WaitForSingleObject(hPatternIdThread, INFINITE);
CloseHandle(hPatternIdThread);
dwRet = WaitForSingleObject(hResultPersistenceThread,INFINITE);
CloseHandle(hResultPersistenceThread);
SendMessage(pGuiData->m_hWnd, WM_CLOSE, 0, 0);
//IMPORTANT : this verbose message is getting logged!
T_VERBOSE(EvtSrcInsightAnalysis, 0, 0, "After sending message to destroy window");
delete patternManager;
delete patternIdRequestQueue;
delete resultQueue;
return 0;
}
Пожалуйста, смотрите T_VERBOSE
макросъемки используется для входа подробного сообщения. Я вижу, что сообщение регистрируется, но поток не выходит!
EDIT:
Я просто заметил следующую строку по моему WorkerThreadProc
, то рабочий поток выходит изящно!
SendMessage(pGuiData->m_hWnd, WM_CLOSE, 0, 0);
Означает ли это, что SendMessage
является виновником? Почему он блокирует поток вызывающим потоком?
Вы звоните CloseHandle() на ручке потока после его выхода? Вы должны использовать WaitForSingleObject(), чтобы дождаться окончания потока. –
@ infact: Конечно, да! И да, я использую 'WaitForSingleObject', чтобы дождаться окончания потока! – Nawaz
Почему бы вам не использовать абстракции, такие как 'boost :: thread', которые, как доказано, работают нормально (и даже переносимы)? – PlasmaHH