Windows内核之进程的终⽌和⼦进程
1 进程终⽌的⽅法:
<1>主线程的进⼊点函数返回(最好使⽤这种⽅法)
<2>进程中的⼀个线程调⽤ExitProcesss函数(应该避免使⽤这样的⽅法)。
<3>还有⼀个进程中的线程调⽤TerminateProcess函数(应该避免使⽤这样的⽅法)。
<4>进程中的全部线程⾃⾏终⽌执⾏(这样的情况差点⼉从未发⽣)。
1.1 主线程进⼊点函数返回
始终都应该这样来设计应⽤程序。即仅仅有当主线程的进⼊点函数返回时,它的进程才终⽌执⾏。这是保证全部线程资源可以得到正确清除的唯⼀办法。
<1> C++对象将可以使⽤它们的析构函数得以释放
<2> 操作系统可以正确的释放该线程使⽤的堆栈内存
<3> 系统将进程的退出代码设置为进⼊点函数的返回值
waitforsingleobject函数
<4> 系统将内核对象的计数值减去1
1.2 调⽤ExitProcess函数
voidExitProcess(uExitCode)
跟主线程的进⼊点函数返回相⽐,它就不那么安全,不能保证资源被清理。
通过调⽤ExitProcess函数。C++/C执⾏期启动代码可以确保主线程从它的进⼊点函数返回时,进程便终⽌执⾏,⽽⽆论进程中是否还有其它线程在执⾏。
假设在进⼊点函数中调⽤ExitThread。那么主线程就会停⽌执⾏,可是假设进程中假设还有其它线程的话。进程便不会终⽌。
ExitProcess以及ExitThread能保证操作系统资源在函数调⽤时被清除,可是不能保证C/C++执⾏时资源被正确的清除。所以不妨不要调⽤这些资源。
在前⾯也介绍过当主线程的进⼊点函数返回的时候。C/C++执⾏时会调⽤执⾏时的exit函数。exit函数会完毕以下操作
<1>调⽤_onexit函数的调⽤⽽注冊的⼈不论什么函数
<2>为全部的全局和静态的C++对象调⽤析构函数
<3>调⽤系统的ExitProcess函数。将nMainRetVal传递给它。
使得操作系统可以撤销进程并设置它的exit代码。
1.3 调⽤TerminateProcess 函数
BOOL TerminateProcess(HANDLE hProcess,UINTnExitCode)
这个函数通知进程内全部线程终⽌。当全部线程终⽌时。进程也会终⽌了,可是它不会告诉进程内相关联的DLL这个进程将要被终⽌。它做的事情:
<1>全部打开的句柄被关闭
<2>全部的线程会被终⽌
<3>进程对象的状态变为终⽌的,满⾜全部等待进程结束的线程
<4>进程中全部线程对象的状态变为终⽌。满⾜全部等待线程结束的线程
<5>进程的终⽌状态由STILL_ACTIVE变为了进程的返回代码
这个函数是异步的。它告诉操作系统,你要终⽌某个进程。可是当函数返回的时候,你⽆法保证进程是否已经被杀死。假设想要确切知道进程是否被杀死,能够使⽤WaitForSingleObject函数。
2 进程终⽌时的情况
<1>进程中全部剩余线程将被终⽌
<2>进程中指定的⽤户对象,GDI对象被释放。内核对象被关闭
<3>内核对象的状态编程收到通知的状态
<4>进程的退出代码由STILL_ACTIVE 变为ExitProcess或者TerminateProcess传递的的退出代码
<5>进程内核对象计数减去1
能够通过函数 BOOLGetExitCodeProcess(HANDLE handle,LPDWORD lpExitCode)来查进程的退出代码。假设代码是STILL_ACTIVE表⽰的是进程还没终⽌。假设不是这个,就说明进程已经被终⽌。
3 ⼦进程
程序中要实现⼀段功能⼀共同拥有3种⽅法:
<1>调⽤函数
<2>开辟新线程
<3>开辟新进程
3.1 调⽤函数
调⽤函数时很常见的。可是它的缺点是由于在同⼀个线程中,所以必须等待此函数运⾏完成,才⼲运⾏后⾯的代码
3.2 开辟新线程
这样可以在新线程运⾏的时候,同⼀时候运⾏其它线程的代码,可是这种缺点是不同线程之间须要交流数据时候。会产⽣同步的问题。
3.3 开辟⼦进程
这样有点是既能够保护数据。能够同步运⾏,也能够等待新进程运⾏完成再去运⾏其它进程的代码。缺点是开辟新进程,会造成地址空间的浪费。
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论