Чистое завершение процесса
Чтобы завершить процесс корректно, сначала необходимо отправить сигнал закрытия:
Как завершить приложение «Чисто» в Win32.
Если вам абсолютно необходимо остановить процесс, выполните следующие действия:
Разместите WM_CLOSE во всех окнах верхнего уровня, принадлежащих процессу, который вы хотите завершить. Многие приложения Windows отвечают на это сообщение выключением.
ПРИМЕЧАНИЕ. Ответ консольного приложения на WM_CLOSE зависит от того, установлен ли на нем обработчик элемента управления.
Используйте EnumWindows (), чтобы найти дескрипторы ваших окон назначения. В вашей функции обратного вызова проверьте, соответствует ли идентификатор процесса Windows процессу, который вы хотите завершить. Вы можете сделать это, вызвав GetWindowThreadProcessId (). Как только вы установили совпадение, используйте PostMessage () или SendMessageTimeout (), чтобы отправить сообщение WM_CLOSE в окно.
Используйте WaitForSingleObject () для ожидания дескриптора процесса. Обязательно дождитесь значения тайм-аута, поскольку во многих ситуациях WM_CLOSE не закрывает приложение. Не забудьте сократить время ожидания (либо с помощью WaitForSingleObject (), либо с помощью SendMessageTimeout ()), чтобы пользователь мог отвечать на любые диалоговые окна, созданные в ответ на сообщение WM_CLOSE.
Если возвращаемое значение - WAIT_OBJECT_0, то приложение полностью закрылось. Если возвращаемое значение WAIT_TIMEOUT, то вы должны использовать TerminateProcess (), чтобы закрыть приложение.
ПРИМЕЧАНИЕ. Если вы получаете возвращаемое значение из WaitForSingleObject (), отличного от WAIT_OBJECT_0 или WAIT_TIMEOUT, используйте GetLastError () для определения причины.
Выполняя эти шаги, вы даете приложению наилучшую возможность аккуратно завершить работу (кроме IPC или вмешательства пользователя).
См. Этот ответ для кода.
Завершение процесса
Если вы не заботитесь о чистом отключении, вы можете использовать TerminateProcess()
. Тем не менее, важно отметить, что TerminateProcess()
является асинхронным; он инициирует прекращение и немедленно возвращается. Если вам необходимо убедиться, что процесс завершен, вызовите функцию WaitForSingleObject()
с дескриптором процесса.
TerminateProcess(pi.hProcess, 0);
// 500 ms timeout; use INFINITE for no timeout
const DWORD result = WaitForSingleObject(pi.hProcess, 500);
if (result == WAIT_OBJECT_0) {
// Success
}
else {
// Timed out or an error occurred
}
CloseHandle(pi.hProcess);
CloseHandle(pi.hThread);
Не закрывается, просто подождите, пока закончите
Если процесс завершится сам по себе, вместо завершения вы можете подождать, пока он не завершится.
WaitForSingleObject(pi.hProcess, INFINITE);
CloseHandle(pi.hProcess);
CloseHandle(pi.hThread);