進(jìn)程只是提供了一段地址空間和內(nèi)核對(duì)象,其運(yùn)行時(shí)通過在其地址空間內(nèi)的主線程來體現(xiàn)的。當(dāng)主線程的進(jìn)入點(diǎn)函數(shù)返回時(shí),進(jìn)程也就隨之結(jié)束。這種進(jìn)程的終止方式是進(jìn)程的正常退出,進(jìn)程中的所有線程資源都能夠得到正確的清除。除了這種進(jìn)程的正常退出方式外,有時(shí)還需要在程序中通過代碼來強(qiáng)制結(jié)束本進(jìn)程或其他進(jìn)程的運(yùn)行。ExitProcess()函數(shù)的原型為:
void ExitProcess(UINT uExitCode); 其參數(shù)uExitCode為進(jìn)程設(shè)置了退出代碼。該函數(shù)具有強(qiáng)制性,在執(zhí)行完畢后進(jìn)程即被結(jié)束,因此位于其后的任何代碼將不能被執(zhí)行。雖然ExitProcess()函數(shù)可以在結(jié)束進(jìn)程的同時(shí)通知與其關(guān)聯(lián)的動(dòng)態(tài)鏈接庫,但是由于它的這種執(zhí)行的強(qiáng)制性,使得ExitProcess()函數(shù)在使用上將存在有安全隱患。例如,如果在程序調(diào)用ExitProcess()函數(shù)之前曾用new操作符申請(qǐng)過一段空間,那么將會(huì)由于ExitProcess()函數(shù)的強(qiáng)制性而無法通過delete操作符將其釋放,從而造成內(nèi)存泄露。有鑒于ExitProcess()函數(shù)的強(qiáng)制性和不安全性,在使用時(shí)一定要引起注意。 2.使用TerminateProcess()結(jié)束進(jìn)程 ExitProcess()只能強(qiáng)制執(zhí)行本進(jìn)程的退出,如果要在一個(gè)進(jìn)程中強(qiáng)制結(jié)束其他進(jìn)程就要用TerminateProcess()來實(shí)現(xiàn)。與ExitProcess()不同,TerminateProcess()函數(shù)執(zhí)行后,被終止的進(jìn)程是不會(huì)的到任何關(guān)于程序退出的通知的。也就是說,被終止的進(jìn)程是無法在結(jié)束運(yùn)行前進(jìn)行退出前的收尾工作的。所以,通常只有在其他任何方法都無法迫使進(jìn)程退出時(shí)才會(huì)考慮使用TerminateProcess()去強(qiáng)制結(jié)束進(jìn)程。下面給出TerminateProcess()的函數(shù)原型: BOOL TerminateProcess(HANDLE hProcess,UINT uExitCode); 參數(shù)hProcess和uExitCode分別為進(jìn)程句柄和退出代碼。如果被結(jié)束的是本進(jìn)程,可以通過GetCurrentProcess()獲取到句柄。TerminateProcess()是異步執(zhí)行的,在調(diào)用返回后并不能確定被終止進(jìn)程是否已經(jīng)真的退出,如果調(diào)用TerminateProcess()的進(jìn)程對(duì)此細(xì)節(jié)關(guān)心,可以通過WaitForSingleObject()來等待進(jìn)程的真正結(jié)束。 在VC程序中如何結(jié)束系統(tǒng)正在運(yùn)行的其他進(jìn)程(該進(jìn)程必須有窗口界面),其實(shí)很簡單,按如下步驟進(jìn)行即可: 1.取得進(jìn)程的句柄(利用FindWindow函數(shù)得到); 2.獲取進(jìn)程ID號(hào)(用GetWindowThreadProcessId函數(shù)獲取); 3.打開進(jìn)程,OpenProcess函數(shù)中的第一個(gè)參數(shù)設(shè)為PROCESS_TERMINATE,就可以獲取處理該進(jìn)程的句柄; 4.利用TerminateProcess函數(shù)結(jié)束進(jìn)程,將該函數(shù)的第二個(gè)參數(shù)設(shè)為4。 代碼如下: //結(jié)束進(jìn)程 int CStaticFunc::KillProcess(LPCSTR pszClassName, LPCSTR pszWindowTitle) { HANDLE hProcessHandle; ULONG nProcessID; HWND TheWindow; TheWindow = ::FindWindow( NULL, pszWindowTitle ); ::GetWindowThreadProcessId( TheWindow, &nProcessID ); hProcessHandle = ::OpenProcess( PROCESS_TERMINATE, FALSE, nProcessID ); return ::TerminateProcess( hProcessHandle, 4 ); } 而啟動(dòng)進(jìn)程則只需要CreateProcess函數(shù)就可完成,需要注意的是這個(gè)函數(shù)的幾個(gè)輸入?yún)?shù),第一個(gè)參數(shù)是 //啟動(dòng)新進(jìn)程 int CStaticFunc::CreateNewProcess(LPCSTR pszExeName) { PROCESS_INFORMATION piProcInfoGPS; STARTUPINFO siStartupInfo; SECURITY_ATTRIBUTES saProcess, saThread; ZeroMemory( &siStartupInfo, sizeof(siStartupInfo) ); siStartupInfo.cb = sizeof(siStartupInfo); saProcess.nLength = sizeof(saProcess); saProcess.lpSecurityDescriptor = NULL; saProcess.bInheritHandle = true; saThread.nLength = sizeof(saThread); saThread.lpSecurityDescriptor = NULL; saThread.bInheritHandle = true; return ::CreateProcess( NULL, (LPTSTR)pszExeName, &saProcess, &saThread, false, Create_DEFAULT_ERROR_MODE, NULL, NULL, &siStartupInfo, &piProcInfoGPS ); |
|