旬阳做网站,淘宝网网页版登录卖家中心,网站集约化建设做法,光明楼网站建设内核对象
基本概念
例如#xff0c;访问令牌#xff0c;事件对象#xff0c;文件对象#xff0c;文件映射对象#xff0c;I/O完成端口对象#xff0c;作业对象#xff0c;邮件槽对象#xff0c;互斥量对象#xff0c;管道#xff0c;进程对象#xff0c;信号量对象…内核对象
基本概念
例如访问令牌事件对象文件对象文件映射对象I/O完成端口对象作业对象邮件槽对象互斥量对象管道进程对象信号量对象线程对象可等待计时器对象线程池工厂
这些对象是通过不同名称的函数创建的
每个内核对象都是一个内存块成员维护着与对象相关的信息
内核对象只能由操作系统内核访问
利用Windows提供的一组函数这组函数会以最恰当的方式来操纵这些结构
句柄
调用一个会创建内核对象的函数后函数会返回一个句柄handle它标识了所创建的对象
可以把这个句柄想象成一个不透明opaque的值它可由进程中的任意线程使用
在32位Windows进程中句柄是一个32位值在64位Windows进程中句柄是64位值
句柄是与进程相关的将句柄传给另一个进程中的线程那么另一个进程用我们的进程的句柄值来发出调用时可能会失败
使用计数
指明多少个进程正在使用同一个内核对象
内核对象的安全性
内核对象可以用一个安全描述符security descriptorSD来保护描述了谁拥有对象 进程内核对象句柄表
一个进程在初始化时系统将为它分配一个句柄表这个句柄表仅供内核对象使用不适用于用户对象或GDI对象
每个结构都包含指向一个内核对象的指针一个访问掩码和一些标志
索引指向内核对象内存块的指针访问掩码包含标志位的一个DWORD标志10x???0x???0x???20x???0x???0x???............
创建一个内核对象
一个进程在初始化的时候其句柄表为空。当进程内的一个线程调用一个会创建内核对象的函数时内核将为这个对象分配并初始化一个内存块。然后内核扫描进程的句柄表查找一个空白的记录项对其进行初始化。
用于创建内核对象的任何函数都会返回一个与进程相关的句柄这个句柄可由同一个进程中运行的所有线程使用。创建内核对象的函数有CreateThreadCreateFileCreateFileMappingCreateSemaphore
调用一个函数时如果它接受一个内核对象句柄作为参数就必须把Create*函数的返回值传给它该函数会查找该进程的句柄表获得目标内核对象的地址然后以一种恰当的方式来操纵对象的数据结构。
关闭内核对象
无论以什么方式创建内核对象关闭内核对象的API为
BOOL CloseHandle(HANDLE hobject);
函数会验证传给函数的句柄值标识是进程有权访问的一个对象如果句柄有效系统就会获得内核对象的数据结构地址并将结合中的“使用记数”减一 跨进程边界共享内核对象
使用对象句柄继承
只有在进程之间有一个父—子关系的时候才可以使用对象句柄继承
父进程决定生成一个子进程并允许子进程访问父进程的内核对象。
执行步骤
1.父进程创建一个内核对象时父进程必须向系统指出他希望这个对象句柄是可以继承的父进程必须分配并初始化一个SECURITY_ATTRIBUTES并将这个结构的地址传给具体的Create函数
SECURITY_ATTRIBUTES sa;
sa.nLengthsizeof(sa);
sa.lpSecurityDescriptorNULL;
sa.bInheritHandleTRUE;HANDLE hMutexCreateMutex(sa,FALSE,NULL);
创建了一个SECURITY_ATTRIBUTES结构表明对象要用默认安全性来创建而且返回的句柄是可以继承的
此时句柄表中的是否可以继承的标志位被设置为1
2.创建子进程
使用CreateProcess函数来完成
将参数bInheritHandle设置为TRUE就会继承父进程中可继承的句柄
改变句柄的标志
父进程创建了一个内核对象得到了一个可继承的句柄然后生成了两个子进程。但是父进程只希望其中一个子进程继承内核对象的句柄。
使用SetHandleInformation函数来改变内核对象的继承标志。
BOOL SetHandleInformation(HANDLE hObject,DWORD dwMask,DWORD dwFlags);
dwMask告诉函数我们要更改哪个或者哪些标志
如果想把每个对象的标志一次性更改完毕可以对这两个标志执行一次按位或运算。
我么可以用GetHandleInformation来检查一下一个句柄是否可以被继承
DWORD dwFlags;
GetHandleInformation(hObj,dwFlags);
BOOL fHandleIsInheritable(0!(dwflagsHANDLE_FLAG_INHERIT);
为对象命名
许多内核对象都可以进行命名
HANDLE CreateMutex(PSECURITY_ATTRIBUTES psa,BOOL bInitialOwner,PCTSTR pszName);
很多函数最后一个参数都是pszName向此参数传入NULL相当于向系统表明我们要创建一个未命名的内核对象微软没有提供任何专门的机制来保证内核对象的名称是唯一的。