-
您的位置:首页 → 精文荟萃 → 破解文章 → 浅谈利用 TEB 实现的反跟踪
浅谈利用 TEB 实现的反跟踪
时间:2004/10/15 0:58:00来源:本站整理作者:蓝点我要评论(0)
-
首先声明一下,本文所讲的内容已经是老掉牙的东西了,而且本文所涉及的代码似乎只能在 NT 内核下正常发挥作用,如有不对的地方,请各位高手给我指点,谢谢。 :)
我们先来看看本文中最重要的概念—— TEB 。
TEB(Thread Environment Block) 在 Windows 9x 系列中被称为 TIB(Thread Information Block),它记录了线程的重要信息,而且每一个线程都会对应一个 TEB 结构。 Matt Pietrek 大牛已经给我们列出了它的结构,我就不多说啦,见下:(摘自 Matt Pietrek 的 Under The Hood - MSJ 1996)
//===========================================================
// file: TIB.H
// Author: Matt Pietrek
// From: Microsoft Systems Journal "Under the Hood", May 1996
//===========================================================
#pragma pack(1)
typedef struct _EXCEPTION_REGISTRATION_RECORD
{
struct _EXCEPTION_REGISTRATION_RECORD * pNext;
FARPROC pfnHandler;
} EXCEPTION_REGISTRATION_RECORD, *PEXCEPTION_REGISTRATION_RECORD;
typedef struct _TIB
{
PEXCEPTION_REGISTRATION_RECORD pvExcept; // 00h Head of exception record list
PVOID pvStackUserTop; // 04h Top of user stack
PVOID pvStackUserBase; // 08h Base of user stack
union // 0Ch (NT/Win95 differences)
{
struct // Win95 fields
{
WORD pvTDB; // 0Ch TDB
WORD pvThunkSS; // 0Eh SS selector used for thunking to 16 bits
DWORD unknown1; // 10h
} WIN95;
struct // WinNT fields
{
PVOID SubSystemTib; // 0Ch
ULONG FiberData; // 10h
} WINNT;
} TIB_UNION1;
PVOID pvArbitrary; // 14h Available for application use
struct _tib *ptibSelf; // 18h Linear address of TIB structure
union // 1Ch (NT/Win95 differences)
{
struct // Win95 fields
{
WORD TIBFlags; // 1Ch
WORD Win16MutexCount; // 1Eh
DWORD DebugContext; // 20h
DWORD pCurrentPriority; // 24h
DWORD pvQueue; // 28h Message Queue selector
} WIN95;
struct // WinNT fields
{
DWORD unknown1; // 1Ch
DWORD processID; // 20h
DWORD threadID; // 24h
DWORD unknown2; // 28h
} WINNT;
} TIB_UNION2;
PVOID* pvTLSArray; // 2Ch Thread Local Storage array
union // 30h (NT/Win95 differences)
{
struct // Win95 fields
{
PVOID* pProcess; // 30h Pointer to owning process database
} WIN95;
} TIB_UNION3;
} TIB, *PTIB;
#pragma pack()
呵呵,看到那么多的结构,是不是有点头晕了?不要紧,我来给大家找出最重要的部分加以解释。
在 MASM/TASM 下编写过 SEH 代码的朋友,一定会对这三句代码非常熟悉:
push offset _SEH_Handler
push fs:[0]
mov fs:[0], esp
这是标准的 SEH 异常处理函数的注册方法,可是各位朋友有没有想过为什么是 fs:[0] 呢?
让我们抬头看看上面的 Matt Pietrek 的代码,其中有这么一行:
PEXCEPTION_REGISTRATION_RECORD pvExcept; // 00h Head of exception record list
注意到 PEXCEPTION_REGISTRATION_RECORD 这个定义,它表示 pvExcept 这个变量正是 exception record list 的入口,这个入口位于整个结构的 0 偏移处。同时,在 M$ 的 Intel i386 Windows NT/2K/XP 内核中,每当创建一个线程, OS 均会为每个线程分配 TEB ,而且 TEB 永远放在 fs 段选择器指定的数据段的 0 偏移处。
这样一来,你就明白了 SEH 注册的偏移为什么是在 fs:[0] 了吧?
事实上 Windows 系统都是通过这种方法来为应用程序提供信息的,比如有这样的例子:
struct _tib *ptibSelf; // 18h Linear address of TIB structure
DWORD threadID; // 24h
Windows 提供了一个 API :GetCurrentThreadID(),它的内部工作原理其实是这样的:(利用了上面的这两个地址)
mov eax, fs:[18h] ;因为 18h 偏移处是 TIB 结构的线性偏移地址
mov eax, [eax + 24h] ;因为 24h 偏移处是 threadID 的地址
ret ;把 eax 中储存的 threadID 地址返回
明白了上面的例子,就可以继续往下看了(罗罗嗦嗦讲了一大堆真不好意思……但是上面所说的其实并不是废话,因为这是理论基础)。
OK,接下来让我们看看 30h 处的偏移:
PVOID* pProcess; // 30h Pointer to owning process database
这个偏移地址处的内容非常有用,它指向本线程的拥有者的 PDB(Process Database) 的线性地址。听起来好像挺高深的,又是“拥有者”,又是“PDB”什么的……等等,聪明的你是不是已经想到了——“拥有者”意味着什么?
当你用动态调试器,例如 OllyDbg 的时候,调试器是把调试的对象作为一个子线程进行跟踪的,在这种情况下,被调试的对象的“拥有者”就是调试器本身,也就是说,它的 TEB 的 30h 处的偏移指向的内容肯定不为 0 ,这样,我们就可以利用这一点,判断 30h 偏移指向的内容,来判断是否有调试器跟踪。
原理就说到这里了,本文只是抛砖引玉,其实 TEB 的内容非常丰富,可以利用的地方还有不少!相信聪明的你一定能对它进行更为深入的挖掘,不过一旦有了什么研究心得,记得要告诉小弟一声啊! :)
最后给出一个 Anti-Debug 的例子程序,用 MASM 编译完成后,请用 OllyDbg 来加载调试一下,看看与正常的运行结果有什么不同。 :)
;*********************************************************
;程序名称:演示利用 TEB 结构进行 Anti-Debug
; 请用 OllyDbg 进行调试
;适用OS:Windows NT/2K/XP
;作者:罗聪
;日期:2003-2-9
;出处http://www.LuoCong.com(老罗的缤纷天地)
;注意事项:如欲转载,请保持本程序的完整,并注明:
;转载自“老罗的缤纷天地”http://www.LuoCong.com)
;*********************************************************
.386
.model flat, stdcall
option casemap:none
include \masm32\include\windows.inc
include \masm32\include\kernel32.inc
include \masm32\include\user32.inc
includelib \masm32\lib\kernel32.lib
includelib \masm32\lib\user32.lib
.data
szCaption db "Anti-Debug Demo by LC, 2003-2-9", 0
szDebugged db "Hah, let me guess... U r dEBUGGINg me! :)", 0
szFine db "Good boy, no dEBUGGEr detected!", 0
.code
main:
assume fs:nothing
mov eax, fs:[30h] ;指向 PDB(Process Database)
movzx eax, byte ptr [eax + 2h]
or al, al
jz _Fine
_Debugged:
push MB_OK or MB_ICONHAND
push offset szCaption
push offset szDebugged
jmp _Output
_Fine:
push MB_OK or MB_ICONINformATION
push offset szCaption
push offset szFine
_Output:
push NULL
call MessageBoxA
invoke ExitProcess, 0
end main
老罗
|
相关阅读
Windows错误代码大全 Windows错误代码查询激活windows有什么用Mac QQ和Windows QQ聊天记录怎么合并 Mac QQ和Windows QQ聊天记录Windows 10自动更新怎么关闭 如何关闭Windows 10自动更新windows 10 rs4快速预览版17017下载错误问题Win10秋季创意者更新16291更新了什么 win10 16291更新内容windows10秋季创意者更新时间 windows10秋季创意者更新内容kb3150513补丁更新了什么 Windows 10补丁kb3150513是什么
-
热门文章
去除winrar注册框方法
最新文章
比特币病毒怎么破解 比去除winrar注册框方法
华为无线路由器HG522-C破解教程(附超级密码JEB格式文件京东电子书下载和阅读限制破解教UltraISO注册码全集(最新)通过Access破解MSSQL获得数据
人气排行
华为无线路由器HG522-C破解教程(附超级密码JEB格式文件京东电子书下载和阅读限制破解教UltraISO注册码全集(最新)qq相册密码破解方法去除winrar注册框方法(适应任何版本)怎么用手机破解收费游戏华为无线猫HG522破解如何给软件脱壳基础教程
查看所有0条评论>>