我是靠谱客的博主 光亮烧鹅,最近开发中收集的这篇文章主要介绍28.探秘_OBJECT_TYPE结构,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

首先,每个进程/线程对象上面都有个_OBJECT_HEADER结构,而句柄结构在这个结构的后面,64位下这个结构大小为0X30
以进程结构体举例:

nt!_OBJECT_HEADER
   +0x000 PointerCount     : Int8B
   +0x008 HandleCount      : Int8B
   +0x008 NextToFree       : Ptr64 Void
   +0x010 Lock             : _EX_PUSH_LOCK
   +0x018 TypeIndex        : UChar
   +0x019 TraceFlags       : UChar
   +0x019 DbgRefTrace      : Pos 0, 1 Bit
   +0x019 DbgTracePermanent : Pos 1, 1 Bit
   +0x01a InfoMask         : UChar
   +0x01b Flags            : UChar		 		flags = 0x71; //进程退出,修改后再改句柄表隐藏
   +0x01b NewObject        : Pos 0, 1 Bit
   +0x01b KernelObject     : Pos 1, 1 Bit
   +0x01b KernelOnlyAccess : Pos 2, 1 Bit
   +0x01b ExclusiveObject  : Pos 3, 1 Bit
   +0x01b PermanentObject  : Pos 4, 1 Bit
   +0x01b DefaultSecurityQuota : Pos 5, 1 Bit
   +0x01b SingleHandleEntry : Pos 6, 1 Bit
   +0x01b DeletedInline    : Pos 7, 1 Bit
   +0x01c Reserved         : Uint4B
   +0x020 ObjectCreateInfo : Ptr64 _OBJECT_CREATE_INFORMATION
   +0x020 QuotaBlockCharged : Ptr64 Void
   +0x028 SecurityDescriptor : Ptr64 Void
   +0x030 Body             : _QUAD            //进程/线程对象在这个位置
这里开始就是
 _EPROCESS / _ETHREAD 结构

2.微软提供了一个未文档化函数可以返回结构体头部
NTKERNELAPI POBJECT_TYPE ObGetObjectType(PVOID Object);

//ObGetObjectType可以通过进程对象取到_OBJECT_TYPE结构体头地址

0: kd> dt _OBJECT_TYPE
ntdll!_OBJECT_TYPE
   +0x000 TypeList         : _LIST_ENTRY
   +0x010 Name             : _UNICODE_STRING    //进程就是 process  线程就是Thread
   +0x020 DefaultObject    : Ptr64 Void
   +0x028 Index            : UChar       //句柄类型ID process 是 7 ;Thread是8
   +0x02c TotalNumberOfObjects : Uint4B
   +0x030 TotalNumberOfHandles : Uint4B
   +0x034 HighWaterNumberOfObjects : Uint4B
   +0x038 HighWaterNumberOfHandles : Uint4B
   +0x040 TypeInfo         : _OBJECT_TYPE_INITIALIZER
   +0x0b0 TypeLock         : _EX_PUSH_LOCK
   +0x0b8 Key              : Uint4B
   +0x0c0 CallbackList     : _LIST_ENTRY

那么手动如何得到_OBJECT_TYPE的地址呢,逆向下win7(WIN8.1)内核模块

PAGE:0000000140330B54                 public ObGetObjectType
PAGE:0000000140330B54 ObGetObjectType proc near               ; CODE XREF: CMFCheckAccess:loc_14033123E↓p
PAGE:0000000140330B54                                         ; PnpHandleProcessWalkWorker+15↓p ...
PAGE:0000000140330B54                 movzx   eax, byte ptr [rcx-18h]
PAGE:0000000140330B58                 lea     rcx, ObTypeIndexTable
PAGE:0000000140330B5F                 mov     rax, [rcx+rax*8] 
PAGE:0000000140330B63                 retn


得知:ObTypeIndexTable + [对象-0x18] *8 = _OBJECT_TYPE头部

win7虚拟机找个进程测试下
在这里插入图片描述

WIN10开始就换了个解密方法,真蛋疼

PAGE:00000001404C65A8                 public ObGetObjectType
PAGE:00000001404C65A8 ObGetObjectType proc near               ; DATA XREF: .pdata:00000001403AA730↑o
PAGE:00000001404C65A8                 lea     rax, [rcx-30h]  ; ffffd18dccb7f050
PAGE:00000001404C65AC                 movzx   ecx, byte ptr [rcx-18h] ; 0x7c  注意:movzx会填充整个x64寄存器为0再赋值
PAGE:00000001404C65B0                 shr     rax, 8          ;  FFD18DCCB7F0
PAGE:00000001404C65B4                 movzx   eax, al         ; F0
PAGE:00000001404C65B7                 xor     rax, rcx        ; f0 xor 7c=8C
PAGE:00000001404C65BA                 movzx   ecx, byte ptr cs:ObHeaderCookie ; 8b
PAGE:00000001404C65C1                 xor     rax, rcx        ; xor   8c,8b =7
PAGE:00000001404C65C4                 lea     rcx, ObTypeIndexTable
PAGE:00000001404C65CB                 mov     rax, [rcx+rax*8]
PAGE:00000001404C65CF                 retn
PAGE:00000001404C65CF ObGetObjectType endp

解密出来公式大概这样:
[ObTypeIndexTable+((((object - 0x30) >> 8 ) &0xFF^ *(pchar)(object-0x18))^*(pchar)ObHeaderCookie))*8] = _OBJECT_TYPE头

[ObTypeIndexTable+((0xf0^ 0x7c)^0x8b)8]
[fffff800`6b911e10+7
8]

在这里插入图片描述

至此,解密完成,当然代码还是用微软提供的函数吧 ObGetObjectType,有现成的干嘛不用呢

最后

以上就是光亮烧鹅为你收集整理的28.探秘_OBJECT_TYPE结构的全部内容,希望文章能够帮你解决28.探秘_OBJECT_TYPE结构所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(52)

评论列表共有 0 条评论

立即
投稿
返回
顶部