五月综合缴情婷婷六月,色94色欧美sute亚洲线路二,日韩制服国产精品一区,色噜噜一区二区三区,香港三级午夜理伦三级三

您現(xiàn)在的位置: 365建站網(wǎng) > 365文章 > exit(0) ExitProcess和TerminateProcess的結(jié)束進(jìn)程的用法和區(qū)別

exit(0) ExitProcess和TerminateProcess的結(jié)束進(jìn)程的用法和區(qū)別

文章來(lái)源:365jz.com     點(diǎn)擊數(shù):757    更新時(shí)間:2018-06-07 10:04   參與評(píng)論

每個(gè)應(yīng)用程序都有個(gè)主函數(shù),在WINDOWS下,只支持兩種類型的應(yīng)用程序——CUI(控制臺(tái)應(yīng)用程序)和GUI(圖形界面應(yīng)用程序),相應(yīng)的,其主函數(shù)類型不同。來(lái)看下這幾個(gè)入口函數(shù)

int WINAPI WinMain(HINSTANCE hinstExe, HINSTANCE,PSTR pszCmdLine, int nCmdShow);  
int WINAPT wWinMain(HINSTANCE hinstExe,HINSTANCE,PWSTR pszCmdLine,int nCmdShow);  
int __cdecl main(int argc,char *argv[],char *envp[]);  
int _cdecl wmain(int argc, wchar_t *argv[],wchar_t *envp[]);


前兩個(gè)為GUI的入口函數(shù),后兩個(gè)為CUI的入口函數(shù);事實(shí)上,在一個(gè)進(jìn)程開始運(yùn)行時(shí),WINDOWS OS并不直接從主函數(shù)開始執(zhí)行,而是從另外
一個(gè)比較大的運(yùn)行期啟動(dòng)函數(shù)開始執(zhí)行,不同的入口函數(shù)對(duì)應(yīng)的啟動(dòng)函數(shù)不同:

應(yīng)用程序類型進(jìn)入點(diǎn)嵌入可執(zhí)行文件的啟動(dòng)函數(shù)
需要ANSI字符和字符串的GUI應(yīng)用程序WinMainWinMainCRTStartup
需要Unicode字符和字符串的GUI應(yīng)用程序wWinMainwWinMainCRTStartup
需要ANSI字符和字符串的CUI應(yīng)用程序mainmainCRTStartup
需要Unicode字符和字符串的CUI應(yīng)用程序wmainwmainCRTStartup
啟動(dòng)函數(shù)負(fù)責(zé)對(duì)應(yīng)用程序運(yùn)行前期的初始化,如全局變量的內(nèi)存分配等。如果編寫了一個(gè)wWinMain()函數(shù),以下就是它的調(diào)用過(guò)程:
GetStartupInfo(&StartupInfo);
int nMainRetVal = wWinMain(GetMjduleHandle(NULL),
   NULL, pszCommandLineUnicode,
   (StartupInfo.dwFlags & STARTF_USESHOWWINDOW) ? 
   StartupInfo.wShowWindow:SW_SHOWDEFAULT);

......

exit(0)

當(dāng)入口函數(shù)(主函數(shù))返回時(shí),運(yùn)行期啟動(dòng)函數(shù)就執(zhí)行EXIT函數(shù),此函數(shù)主要完成全局對(duì)象和變量的內(nèi)存釋放任務(wù),之后:再調(diào)用ExitProcess

函數(shù)進(jìn)行撤銷進(jìn)程。即:exit()函數(shù)內(nèi)部調(diào)用了ExitProcess函數(shù)。通常來(lái)說(shuō),這是最完美的進(jìn)程執(zhí)行過(guò)程。由此可以看出exit()函數(shù)原型:進(jìn)行

全局變量和對(duì)象的析構(gòu),然后調(diào)用ExitProcess函數(shù)。注意:它只析構(gòu)全局對(duì)象和變量,而不析構(gòu)局部變量,后面我會(huì)列出具體事例程序來(lái)說(shuō)明。

ExitProcess()函數(shù)實(shí)際上只是用來(lái)進(jìn)行結(jié)束進(jìn)程,如果其后面還有我們預(yù)期要執(zhí)行的代碼,實(shí)際上全未執(zhí)行,這個(gè)性質(zhì)暴露出ExitProcess函數(shù)

的缺陷:可能導(dǎo)致已經(jīng)創(chuàng)建的對(duì)象沒(méi)有析構(gòu)而退出,從而導(dǎo)致內(nèi)存泄露。

TerminateProcess()函數(shù)的實(shí)際作用跟ExitProcess函數(shù)差不多,只不過(guò),此函數(shù)可用來(lái)終止當(dāng)前進(jìn)程之外的另外一個(gè)其它進(jìn)程,同樣的,它

也會(huì)導(dǎo)致和ExitProcess一樣的結(jié)果:內(nèi)存泄露。

如果我們?cè)诰帉憫?yīng)用程序時(shí),打算終止當(dāng)前進(jìn)程,我們?cè)撜{(diào)用哪個(gè)函數(shù)?答案是:三者其實(shí)都一樣! 因?yàn)槿叨伎赡軐?dǎo)致內(nèi)存泄露,但我們擔(dān)心

的過(guò)多了,因?yàn)檫M(jìn)程在結(jié)束時(shí),即使有ExitProcess,TerminateProcess,以及exit函數(shù)調(diào)用而導(dǎo)致的內(nèi)存泄露,OS也會(huì)進(jìn)行清理工作,能保證

我們泄露的內(nèi)存最終被還回到OS中去,而不必?fù)?dān)心當(dāng)前進(jìn)程已經(jīng)退出而導(dǎo)致內(nèi)存泄露,致使其它進(jìn)程無(wú)法使用該內(nèi)存塊。一個(gè)進(jìn)程無(wú)論在什么情

況下終止,都會(huì)進(jìn)行如下工作:

1) 進(jìn)程指定的所有用戶對(duì)象和G D I對(duì)象均被釋放,所有內(nèi)核對(duì)象均被關(guān)閉(如果沒(méi)有其他 進(jìn)程打開它們的句柄,那么這些內(nèi)核對(duì)象將被撤消。


但是,如果其他進(jìn)程打開了它們的句柄, 內(nèi)核對(duì)象將不會(huì)撤消)。 


2) 進(jìn)程的退出代碼將從S T I L L _ A C T I V E改為傳遞給E x i t P r o c e s s或Te r m i n a t e P r o c e s s的代碼。 


3) 進(jìn)程內(nèi)核對(duì)象的狀態(tài)變成收到通知的狀態(tài)(關(guān)于傳送通知的詳細(xì)說(shuō)明,參見(jiàn)第9章)。系 統(tǒng)中的其他線程可以掛起,直到進(jìn)程終止運(yùn)行。 


4) 進(jìn)程內(nèi)核對(duì)象的使用計(jì)數(shù)遞減1。


進(jìn)程只是提供了一段地址空間和內(nèi)核對(duì)象,其運(yùn)行時(shí)通過(guò)其他地址空間內(nèi)的主線程來(lái)體現(xiàn)的。當(dāng)主線程的進(jìn)入點(diǎn)函數(shù)返回時(shí),進(jìn)程也就隨之而技術(shù)。這種進(jìn)程的種植方式是進(jìn)程的正常退出。進(jìn)程中的所有縣城資源都能夠得到正確的清除。除了這種進(jìn)程的正常退出方式之外,優(yōu)勢(shì)還需要在程序中通過(guò)代碼來(lái)強(qiáng)制結(jié)束本進(jìn)程或其他進(jìn)程的運(yùn)行。

ExitProcess

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)鏈接庫(kù),但是由于他的這種強(qiáng)制性,使得ExitProcess()函數(shù)在使用上將存有安全隱患。例如,如果最親愛(ài)程序調(diào)用ExitProcess()函數(shù)之前曾用new操作,申請(qǐng)一段空間,那么敬愛(ài)那個(gè)會(huì)由于ExitProcess() 函數(shù)的強(qiáng)制性而無(wú)法通過(guò)delete操作符將其釋放,從而造成內(nèi)存泄露。

有鑒于ExitProcess()函數(shù)的強(qiáng)制性和安全性,在使用時(shí)一定要引起注意。

Terminateprocess()

ExitProcess 只能強(qiáng)制本進(jìn)程的推出,如果要在一個(gè)進(jìn)程中強(qiáng)制結(jié)束其他的進(jìn)程就需要用TerminateProcess()來(lái)實(shí)現(xiàn),與ExitProcess()不同,TerminateProcess()函數(shù)執(zhí)行后,被終止的進(jìn)程不會(huì)得到任何關(guān)于程序退出的通知。也就是說(shuō),被終止的進(jìn)程是無(wú)法再結(jié)束運(yùn)行前進(jìn)程推出前的收尾工作的。所以,通常只有在其他任何地方都無(wú)法迫使進(jìn)程退出時(shí)才會(huì)考慮使用TerminateProcess()去強(qiáng)制結(jié)束進(jìn)程。

BOOL TerminateProcess(HANDLE hProcess, UINT uExitCode);

參數(shù)hProcess和uExitCode分別為進(jìn)城句柄和退出代碼。如果被結(jié)束的是本進(jìn)程,可以通過(guò)GetCurrentProcess()獲取到句柄。 TerminateProcess()是異步執(zhí)行的,在調(diào)用后返回并不能確定被終止進(jìn)程是否已經(jīng)真的退出,如果調(diào)用TerminateProcess() 的進(jìn)程對(duì)此細(xì)節(jié)關(guān)心,可以通過(guò)WaitForSingleObject()來(lái)等待進(jìn)程的真正結(jié)束。

在VC中如何結(jié)束系統(tǒng)正在運(yùn)行的其他進(jìn)程(該進(jìn)程必須有窗口界面),其實(shí)很簡(jiǎn)單,按照如下步驟進(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 );
}


下面來(lái)看下如下很簡(jiǎn)單的示例程序:


// exitprocess_text.cpp : 定義控制臺(tái)應(yīng)用程序的入口點(diǎn)。  
//  
  
#include "stdafx.h"  
#include "windows.h"  
#include "iostream"  
  
class Example  
{  
public:  
  
    Example()  
    {  
        std::cout<<"struction"<<std::endl;  
  
    }  
  
    ~Example()  
    {  
        std::cout<<"construction"<<std::endl;  
    }  
};  
  
Example ex1;  
  
int _tmain(int argc, _TCHAR* argv[])  
{  
      
    Example ex2;  
      
    return 0;  
}

 


程序這樣執(zhí)行時(shí)最完美的,其輸出結(jié)果如下:

 

structionstructionconstructionconstruction

 

局部對(duì)象ex1和全局對(duì)象ex2都被正常析構(gòu),而如果將主函數(shù)該為如下:


int _tmain(int argc, _TCHAR* argv[])  
{  
      
    Example ex2;  
  
    ::ExitProcess(0);  
      
    return 0;  
}


程序此時(shí)執(zhí)行結(jié)果為:

 

structionstruction

 

局部對(duì)象和全局對(duì)象都沒(méi)被析構(gòu),因?yàn)檎{(diào)用了ExitProcess進(jìn)程直接結(jié)束,而沒(méi)有調(diào)用啟動(dòng)函數(shù)中的exit函數(shù),所以全局對(duì)象也沒(méi)被析構(gòu)。

而如果將主函數(shù)再改為如下:


int _tmain(int argc, _TCHAR* argv[])  
{  
      
    Example ex2;  
  
    exit(0);  
      
    return 0;  
}

 程序此時(shí)執(zhí)行結(jié)果為:


 

structionstructionconstruction

 

可以看到只析構(gòu)了一個(gè)對(duì)象,而另外一個(gè)未被析構(gòu),其實(shí)沒(méi)被析構(gòu)的對(duì)象是局部對(duì)象,前面提到exit函數(shù)主要任務(wù)就是負(fù)責(zé)析構(gòu)全局對(duì)象和變

量,而不負(fù)責(zé)局部對(duì)象的析構(gòu)。為了說(shuō)明析構(gòu)的是全局變量,將主函數(shù)再做如下處理:

int _tmain(int argc, _TCHAR* argv[])  
{  
      
    exit(0);  
      
    return 0;  
}

 


 

代碼的執(zhí)行結(jié)果是:

 

structionconstruction

 

由此證明析構(gòu)的是全局變量;如果你認(rèn)為還不給力的話,試著把全局對(duì)象刪掉,局部對(duì)象留下,其執(zhí)行結(jié)果是:

 

struction

 

局部變量會(huì)被證明沒(méi)被析構(gòu),這絕度沒(méi)有任何含糊。


如對(duì)本文有疑問(wèn),請(qǐng)?zhí)峤坏浇涣髡搲?,廣大熱心網(wǎng)友會(huì)為你解答!! 點(diǎn)擊進(jìn)入論壇

發(fā)表評(píng)論 (757人查看0條評(píng)論)
請(qǐng)自覺(jué)遵守互聯(lián)網(wǎng)相關(guān)的政策法規(guī),嚴(yán)禁發(fā)布色情、暴力、反動(dòng)的言論。
昵稱:
最新評(píng)論
------分隔線----------------------------

其它欄目

· 建站教程
· 365學(xué)習(xí)

業(yè)務(wù)咨詢

· 技術(shù)支持
· 服務(wù)時(shí)間:9:00-18:00
365建站網(wǎng)二維碼

Powered by 365建站網(wǎng) RSS地圖 HTML地圖

copyright © 2013-2024 版權(quán)所有 鄂ICP備17013400號(hào)