ObpReferenceProcessObjectByHandle 学习

NTSTATUS
ObpReferenceProcessObjectByHandle (
    IN HANDLE Handle,
    ......        OUT PVOID *Object,
    ......    
    )    {
     //获取当前线程
    Thread = PsGetCurrentThread ();
    *Object = NULL;
      // HANDLE为负数 说明才是内核使用句柄?        if ((LONG)(ULONG_PTR) Handle < 0) {
        //句柄就是当前进程  直接获取进程的对象头 增加引用计数并返回PROCESS即可
             if (Handle == NtCurrentProcess()) {            GrantedAccess = Process->GrantedAccess;            ObjectHeader = OBJECT_TO_OBJECT_HEADER(Process);            HandleInformation->GrantedAccess = GrantedAccess;
            HandleInformation->HandleAttributes = 0;            *AuditMask = 0;            ObpIncrPointerCount(ObjectHeader);
            *Object = Process;            ASSERT( *Object != NULL );            Status = STATUS_SUCCESS;            return Status;        //如果句柄是当前线程 也是增加引用计数和返回线程即可
           } else if (Handle == NtCurrentThread()) {            GrantedAccess = Thread->GrantedAccess;            ObjectHeader = OBJECT_TO_OBJECT_HEADER(Thread);            HandleInformation->GrantedAccess = GrantedAccess;
            HandleInformation->HandleAttributes = 0;            *AuditMask = 0;            ObpIncrPointerCount(ObjectHeader);
            *Object = Thread;            ASSERT( *Object != NULL );            Status = STATUS_SUCCESS;            return Status;        } else if (AccessMode == KernelMode) {
            //
            //  除开上述两种情况 如果是在内核模式下调用此函数的话            //            Handle = DecodeKernelHandle( Handle );            // 解析内核句柄            // #define EncodeKernelHandle(H) (HANDLE)(KERNEL_HANDLE_MASK | (ULONG_PTR)(H))            // #define DecodeKernelHandle(H) (HANDLE)(KERNEL_HANDLE_MASK ^ (ULONG_PTR)(H))
            // 句柄表是内核句柄表 即SYSTEM句柄表              HandleTable = ObpKernelHandleTable;
        } else {        ......        }
    //
    // 之后进入线程的EnterCriticalRegion    //    //  Translate the specified handle to an object table index.
    //   将句柄翻译成句柄表项  ExMapHandleToPointer 是此函数重点    ObjectTableEntry = ExMapHandleToPointer ( HandleTable, Handle );    // 有了句柄表项就获取对象头 增加引用计数和文件头BODY部分复制到OBJECT参数传出。       ........
    return Status;
}  NTKERNELAPI
PHANDLE_TABLE_ENTRY
ExMapHandleToPointer (    )主要  通过句柄索引在句柄表中查找句柄表项    HandleTableEntry = ExpLookupHandleTableEntry( HandleTable,
                                                  LocalHandle ); PHANDLE_TABLE_ENTRY
ExpLookupHandleTableEntry (
    IN PHANDLE_TABLE HandleTable,
    IN EXHANDLE tHandle
    ){   CapturedTable = *(volatile ULONG_PTR *) &HandleTable->TableCode;
    TableLevel = (ULONG)(CapturedTable & LEVEL_CODE_MASK);    // 这样就可以知道句柄表是1层表 还是2层表 还是3层表    //下面是SWITCH CASE结构来根据几层表来计算其在稀疏数组的偏移,返回我们需要的句柄表项    //句柄表内存分配是按页面大小4K来分配 一个句柄表项是8B 所以每申请一个页面来存放句柄表项就是增加512个句柄表项
    //} ObpReferenceProcessObjectByHandle 整个流程就是分析给出句柄是否是当前的进程或者线程 然后直接返回CURRENTTHREAD或者CURRENTPROCESS ,否则获取句柄表进行查询,通过句柄与对象的对应关系返回对应对象指针。注意此函数增加了引用计数,所以还需要解引用。(省略权限检测等过程) 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值