API Hook基本原理和实现

API Hook基本原理和实现[图文]关键字:API Hook,消息,拦截API,钩子,wskjuf作者:wskjuf 更新:2007-12-23 08:18:25 浏览:18142注:本文主要为解决论坛上/forum/forum_posts.asp?TID=7281的提问而写的。

我搜索了一下互联网,将网络上几篇有代表性的api hook文章的精华进行了浓缩和适当简化,写成这篇介绍性文章。

另外也希望初学者能够认真思考本文采用的循序渐进的分析思路,如何解决了一个未知的问题。

文中借鉴的文献资料列于文末附录一节。

hook是什么?windows系统下的编程,消息message的传递是贯穿其始终的。

这个消息我们可以简单理解为一个有特定意义的整数,正如我们看过的老故事片中的“长江长江,我是黄河”一个含义。

windows中定义的消息给初学者的印象似乎是“不计其数”的,常见的一部分消息在winuser.h头文件中定义。

hook与消息有着非常密切的联系,它的中文含义是“钩子”,这样理解起来我们不难得出“hook是消息处理中的一个环节,用于监控消息在系统中的传递,并在这些消息到达最终的消息处理过程前,处理某些特定的消息”。

这也是hook分为不同种类的原因。

hook的这个本领,使它能够将自身的代码“融入”被hook住的程序的进程中,成为目标进程的一个部分。

我们也知道,在windows2000以后的系统中,普通用户程序的进程空间都是独立的,程序的运行彼此间都不受干扰。

这就使我们希望通过一个程序改变其他程序的某些行为的想法不能直接实现,但是hook的出现给我们开拓了解决此类问题的道路。

api hook是什么?在windows系统下编程,应该会接触到api函数的使用,常用的api函数大概有2000个左右。

今天随着控件,stl等高效编程技术的出现,api的使用概率在普通的用户程序上就变得越来越小了。

当诸如控件这些现成的手段不能实现的功能时,我们还需要借助api。

最初有些人对某些api函数的功能不太满意,就产生了如何修改这些api,使之更好的服务于程序的想法,这样api hook就自然而然的出现了。

我们可以通过api hook,改变一个系统api的原有功能。

基本的方法就是通过hook“接触”到需要修改的api函数入口点,改变它的地址指向新的自定义的函数。

api hook并不属于msdn上介绍的13类hook中的任何一种。

所以说,api hook并不是什么特别不同的hook,它也需要通过基本的hook提高自己的权限,跨越不同进程间访问的限制,达到修改api函数地址的目的。

对于自身进程空间下使用到的api函数地址的修改,是不需要用到api hook技术就可以实现的。

api hook和pe格式的关系api hook技术的难点,并不在于hook技术,初学者借助于资料“照葫芦画瓢”能够很容易就掌握hook的基本使用技术。

但是如何修改api函数的入口地址?这就需要学习pe可执行文件(.exe,.dll等)如何被系统映射到进程空间中,这就需要学习pe格式的基本知识。

windows已经提供了很多数据结构struct帮助我们访问pe格式,借助它们,我们就不要自己计算格式的具体字节位置这些繁琐的细节。

但是从api hook的实现来看,pe格式的访问部分仍然是整个编程实现中最复杂的一部分,对于经常crack的朋友不在此列。

假设我们已经了解了pe格式,那么我们在哪里修改api的函数入口点比较合适呢?这个就是输入符号表imported symbols table(间接)指向的输入符号地址。

下面对于pe格式的介绍这一部分,对于没有接触过pe格式学习的朋友应该是看不太明白的,但我已经把精华部分提取出来了,学习了pe格式后再看这些就很容易了。

pe格式的基本组成+-------------------+| DOS-stub | --DOS-头+-------------------+| file-header | --文件头+-------------------+| optional header | --可选头|- - - - - - - - - -|| || data directories | --(可选头尾的)数据目录| |+-------------------+| || section headers | --节头| |+-------------------+| || section 1 | --节1| |+-------------------+| || section 2 | --节2| |+-------------------+| || ... || |+-------------------+| || section n | --节n| |+-------------------+在上图中,我们需要从“可选头”尾的“数据目录”数组中的第二个元素——输入符号表的位置,它是一个IMAGE_DATA_DIRECTORY结构,从它中的VirtualAddress地址,“顺藤摸瓜”找到api函数的入口地点。

下图的简单说明如下:OriginalFirstThunk 指向IMAGE_THUNK_DATA结构数组,为方便只画了数组的一个元素,AddressOfData 指向IMAGE_IMPORT_BY_NAME结构。

IMAGE_IMPORT_DESCRIPTOR数组:每个引入的dll文件都对应数组中的一个元素,以全0的元素(20个bytes的0)表示数组的结束IMAGE_THUNK_DATA32数组:同一组的以全0的元素(4个bytes的0)表示数组的结束,每个元素对应一个IMAGE_IMPORT_BY_NAME结构IMAGE_IMPORT_BY_NAME:如..@Consts@initialization$qqrv. 表示Unmangled Borland C++ Function: qualified function __fastcall Consts::initialization()为了减少这个图的大小,不得已将汇编和c++的结构都用上了。

这个图是输入符号表初始化的情形,此时两个IMAGE_THUNK_DATA结构数组的对应元素都指向同一个IMAGE_IMPORT_BY_NAME结构。

程序加载到进程空间后,两个IMAGE_THUNK_DATA结构数组指向有所不同了。

看下图:// 本文转自 C++Builder研究 -/article.asp?i=1036&d=cf6de2始化的,“两个结构都指向同一个IMAGE_IMPORT_BY_NAME”,此时还没有api 函数地址当PE文件准备执行时,前图已转换成上图。

一个结构指向不变,另一个出现api 函数地址如果PE文件从kernel32.dll中引入10个函数,那么IMAGE_IMPORT_DESCRIPTOR 结构的 Name1域包含指向字符串"kernel32.dll"的RVA,同时每个IMAGE_THUNK_DATA 数组有10个元素。

(RVA是指相对地址,每一个可执行文件在加载到内存空间前,都以一个基址作为起点,其他地址以基址为准,均以相对地址表示。

这样系统加载程序到不同的内存空间时,都可以方便的算出地址) 上述这些结构可以在winnt.h头文件里查到。

具体编程实现我将手上的vc示例代码进行了适当修正,修改了一些资源泄漏的小问题,移植到c++builder6 & update4上,经过测试已经可以完成基本的api hook功能。

有几个知识点说明一下:1、 dll中共享内存变量的实现正常编译下的dll,它的变量使用到的内存是独立的。

比如你同时运行两个调用了某个dll的用户程序,试图对某一个在dll中定义的全局变量修改赋值的时候,两个程序里的变量值仍然是不同的。

共享的方法为:在.cpp文件(.h文件里如此设置会提示编译错误)的头部写上如上两行:#pragma option -zRSHSEG // 改变缺省数据段名#pragma option -zTSHCLASS // 改变缺省数据类名HINSTANCE hdll = NULL; // 用来保存该动态连接库的句柄HHOOK hApiHook = NULL; // 钩子句柄HHOOK hWndProc = NULL; // 窗口过程钩子用来拦截SendMessageint threadId = 0;另外建立一个与dll同名,不同后缀的def文件,如HookDll.def文件,写上:LIBRARY HookDll.dllEXPORTS;...SEGMENTSSHSEG CLASS 'SHCLASS' SHARED;end这样设置后在.cpp文件中定义的变量,如果进行了初始化,将进入“SHCLASS”共享内存段(如果不初始化,将不改变其默认段属性)。

上述的共享对于本示例代码并不是必须的,只是稍微演示了一下。

2、 api hook修改api函数入口点地址的时机很显然,我们必须通过hook进入目标进程的地址空间后,再在位于该地址空间里的hook消息处理过程里修改输入符号表“指向”的api函数入口点地址,退出hook前也必须在这个消息处理过程里恢复原来的地址。

只要我们牢记修改的过程发生在目标进程的地址空间中,就不会发生访问违例的错误了。

示例代码使用了WH_GETMESSAGE、WH_CALLWNDPROC两中hook来演示如何hook api,但WH_GETMESSAGE实际上并没有完成具体的功能。

为了让初学者尽快的掌握重点,我将代码进行了简化,是一个不健壮、不灵活的演示示例。

3、函数的内外部表现形式例如api函数MessageBox,这个形式是我们通常用到的,但到了dll里,它的名字很可能出现了两个形式,一个是MessageBoxA,另一个是MessageBoxW,这是因为系统需要适应Ansi和Unicode编码的两种形式,我们不在函数尾端添加“A”或“W”,是不能hook到需要的函数的。

4、辅助pe格式查看工具PE Explorer是一个非常好的查看pe资源的工具,通过它可以验证自己手工计算的pe地址,可以更快的掌握pe格式。

调试器ollydbg也是非常好的辅助工具,例如查看输入符号表中的api函数。

5、程序文件列表dll基本文件:Hook.h,Hook.cpp,HookDll.defclient验证方基本文件:HookTest.h,HookTest.cpp,ApiHookTest.cpp6、实现的功能对记事本的MessageBoxW函数进行了hook,先执行自定义的int WINAPI MyMessageBoxW(HWND hWnd, LPCWSTR M1, LPCWSTR M2, UINT M3) {return oldMessageBoxW(hWnd, M1, L"my api hook", M3);}从这里可以看到,由于目标进程空间中的执行线程并不知道你已经改变了api函数的实际入口地址,它在调用时仍旧将参数一成不变的压入堆栈(这个说法是汇编代码时看到的等价情形),事实上你已经提前接收到了函数调用的所有参数。

合集下载

APIHOOK的实现原理

APIHOOK的实现原理

APIHOOK的实现原理API Hooking(API挂钩)是一种常见的软件技术,用于修改或者扩展应用程序的行为,它通过“操纵”应用程序的API调用过程来实现这一目标。

API Hooking通常用于各种目的,例如:监视应用程序的行为、修复漏洞、收集数据等。

本文将介绍API Hook的实现原理及其相关概念。

1. API Hook概述API Hooking通过劫持和修改应用程序对动态链接库(DLL)中导出函数的调用来实现目标功能。

在Windows操作系统中,每个可执行文件都会使用一些API函数,这些函数由系统提供并存储在动态链接库中。

当应用程序调用这些函数时,操作系统会在库文件中查找并执行相应的函数代码。

API Hooking就是在应用程序和DLL之间插入一个中间层,通过改变函数调用的目标,来控制和改变应用程序的行为。

API Hooking的实现原理可以归纳为以下几个步骤:(1)定位目标函数:首先,需要确定要Hook的目标函数。

可以通过静态分析程序源代码、反汇编可执行文件、监视应用程序行为等方法来获取目标函数的地址或名称。

(2)获取目标函数的原始地址:通过动态链接库(DLL)中的导入表,可以获取到目标函数的原始地址。

导入表中保存了DLL中导出函数地址的引用。

(3)Hook目标函数:Hook目标函数的方式有多种,这里介绍两种常见的方式。

a. 钩子函数(Hook Function):通过将Hook函数替换为目标函数的调用,可以劫持目标函数的执行。

Hook函数在执行之前、中间或者之后可以执行额外的逻辑操作,并返回结果给应用程序。

b. IAT Hooking(Import Address Table Hooking):IAT是动态链接库中的导入表,包含了动态链接库中导出函数的地址。

通过修改IAT中目标函数的地址,将其指向Hook函数,即可实现Hook效果。

(4)重定向函数调用:Hook目标函数后,需要将应用程序中对目标函数的调用重定向到Hook函数。

跨进程API Hook

跨进程API Hook

跨进程API Hook(初稿)detrox什么是“跨进程API Hook”?众所周知Windows应用程序的各种系统功能是通过调用API函数来实现。

API Hook就是给系统的API附加上一段小程序,它能监视甚至控制应用程序对API函数的调用。

所谓跨进程也就是让自己的程序来控制别人程序的API调用了。

API Hook 理论通过对Win32 PE文件的分析(如果你还不熟悉PE文件格式,可以看看Iczelion的PE教程或者LUEVELSMEYER的<<The PE File Format>>)。

我们知道在PE文件中的IMPORT TABLE内存储着API函数的很多信息。

其中包括API的函数名,调用地址等等。

而操作系统在执行PE文件时会先将其映射到内存中。

在映射的同时还会把当前版本操作系统中API函数的入口地址写入IMPORT TABLE中一组与API调用相关的结构体内,用于该应用程序的API调用。

当应用程序调用API时,他会在自己内存映像里寻找API的入口地址,然后执行CALL指令。

如此一来,我们通过修改应用程序内存映像的IMPORT TABLE中API函数的入口地址,就可以达到重定向API 的目的。

将API地址改为我们自己函数的地址,这样我们的函数就可以完成对API的监视和控制了。

API Hook 的实现/* 1 */HANDLE hCurrent = GetModuleHandle(NULL);/* 2 */IMAGE_DOS_HEADER *pidh;/* 3 */IMAGE_NT_HEADERS *pinh;/* 4 */IMAGE_DATA_DIRECTORY *pSymbolTable;/* 5 */IMAGE_IMPORT_DESCRIPTOR *piid;/* 6 */pidh = (IMAGE_DOS_HEADER *)hCurrent;/* 7 */pinh = (IMAGE_NT_HEADERS *)((DWORD)hCurrent + pidh->e_lfanew); /* 8 */pSymbolTable = &pinh->OptionalHeader.DataDirectory[1];/* 9 */piid =(IMAGE_IMPORT_DESCRIPTOR *)((DWORD)hCurrent + pSymbolTable->VirtualAddress);/*10 */do {/*11 */ IMAGE_THUNK_DATA *pitd,*pitd2;/*12 */ pitd = (IMAGE_THUNK_DATA *)((DWORD)hCurrent +piid->OriginalFirstThunk);/*13 */ pitd2 = (IMAGE_THUNK_DATA *)((DWORD)hCurrent +piid->FirstThunk);/*14 */ do {/*15 */ IMAGE_IMPORT_BY_NAME *piibn;/*16 */ piibn = (IMAGE_IMPORT_BY_NAME *)((DWORD)hCurrent + *((DWORD *)pitd));/*17 */ PROC *ppfn = (PROC *)(pitd2->u1.Function);/*18 */ if (!strcmp("MessageBoxW",(char *)piibn->Name)) {/*19 */ oldMsg = (MsgBoxType)(ppfn);/*20 */ DWORD addr = (DWORD)MyMessage;/*21 */ DWORD written = 0;/* 改变内存读写状态 *//*22 */ DWORD oldAccess;/*23 */VirtualProtect(&pitd2->u1.Function,sizeof(DWORD),PAGE_WRITECOPY,&oldA ccess);/*24 */ APIAddress = (DWORD)&pitd2->u1.Function;/* 向内存映像写入数据 *//*25 */WriteProcessMemory(GetCurrentProcess(),&pitd2->u1.Function,&addr,sizeof(DWORD), &written);/*26 */ }/*27 */ pitd++;pitd2++;/*28 */ } while (pitd->u1.Function);/*29 */ piid++;/*30 */} while (piid->FirstThunk + piid->Characteristics+ piid->ForwarderChain + piid->Name + piid->TimeDateStamp);寻觅IMPORT TALBE在/*1*/中我们使用GetModuleHandle(NULL)来返回当前进程在内存中映像的基地址。

API_HOOK讲解1

API_HOOK讲解1

第6章APIHOOKAPIHOOK始终是系统程序员关心的热门话题。

通过APIHOOK,可以对Win32API函数进行拦截,从而改变函数乃至程序的固有行为。

通过APIHOOK拦截可以解决十分棘手的难题。

本章主要介绍Win32API拦截、驱动程序服务函数的拦截、BrowserHelpObject实现、SPI接口的应用,并利用Detours库实现对DLL的绑定。

6.1 APIHOOK综述APIHOOK尽管能够提供非常强大的功能,但是遗憾的是,无论是DDK还是SDK都没有提供这方面的任何文档和例子。

使用APIHOOK前,用户首先应该弄清楚,究竟是拦截一个应用程序还是系统范围内的拦截。

系统的拦截往往需要实现对创建的新的进程进行监视。

对系统底层服务进行拦截,能够打破进程边界。

最简单的实现拦截的方法是实现一个代理的动态链接库。

这个动态链接库实现了目标拦截动态链接库的全部输出函数,但是它只是一个函数转发器,其函数功能还是通过间接地调用原来的目标动态链接库函数实现。

当程序或者系统调用目标动态链接库的时候,真正调用的是代理动态链接库。

代理动态链接库的输出函数会首先检查调用函数的入口参数,决定直接返回一个值,还是调用原来的函数。

可以把这个函数的返回结果作为返回值返回,也可以对调用结果进行二次处理。

由于这种方法需要对所有的函数进行处理,这个过程十分繁琐,而且并非所有的函数都提供了足够的文档,因此这种方法在某些情况下几乎是无法实现的。

这方面应用的例子有关于WinInet实现的程序,发表在1994年12月份的MSJ杂志上,网址是/MSJ/0997/hood0997.htm。

对API函数的拦截不外乎两种方式,要么在磁盘文件上实现,要么在内存中实现。

前者拦截在可执行程序加载以前,后者则是在程序加载之后。

两种方法基本上都是通过打补丁的方法实现的。

如果用户以前曾经研究过APIHOOK,也许听说过导入地址表补丁的概念。

它的很多优点使得这种WindowsAPIHOOK的方法成为最体面、最常见的方法之一。

hook技术原理

hook技术原理

Hook技术是一种用于拦截API函数调用的技术,它通过修改系统API函数的内存地址,从而拦截系统函数的调用,实现对系统API函数的拦截和修改。

Hook技术的基本原理是将系统API函数的内存地址指向一个用户定义的函数,而不是指向实际的API函数。

当调用系统API函数时,系统将调用用户定义的函数,而不是原来的函数。

这样就可以实现对系统API函数的拦截和修改。

Hook技术的实现步骤如下:
1、首先,程序员需要查找和定位需要拦截的API函数的内存地址。

2、然后,程序员需要编写用户定义的函数,用来拦截和修改系统API函数的调用。

3、接着,程序员需要将系统API函数的内存地址指向用户定义的函数,从而实现API函数的拦截。

4、最后,程序员需要将系统API函数的原始内存地址保存起来,以便在不再需要拦截时,可以恢复原来的API函数调用行为。

Hook技术是一种强大的技术,可以用来实现各种功能,比如拦截软件的调用,拦截软件的输入输出,拦截系统函数的调用等。

Hook技术也可以用来实现防病毒,反垃圾邮件,防恶意程序,实现软件保护以及实现自定义控件等功能。

陷阱式APIHook的原理及其在截取串口数据中的应用

陷阱式APIHook的原理及其在截取串口数据中的应用

2024/9/29
8
NewCreateFile(文件名){ 还原CreateFile; Handle = CreateFile(文件名); 修改CreateFile; if(文件名==“COM2”) 保存Handle到共享内存变量ComHandle中
}
2024/9/29
9
NewWriteFile(文件句柄,数据){ if(文件句柄=ComHandle) 修改“数据”
GetMsgProc(){ }
2
目的进程载入 DLPSLIB.dll
(寄生程序)
同步修改ReadFile跳
转到NewReadFile
NewReadFile(){ }
2024/9/29
DLPSLIB.dll
目的进程载入dll时, dll就已经成为其一
部分了
SetDIPSHook{ SetWindowsHookEx(…)
2024/9/29
6
……
调用 Call ReadFile
1
……
4
自定义函数
NewReadFile(){ 还原ReadFile 调用ReadFile 修改ReadFile
ret
}
被劫持函数 ReadFile(){
……
2
ret
3
}
2024/9/29
……
调用 Call ReadFile
1
……
9
自定义函数 NewReadFile(){
1
……
9
自定义函数 NewReadFile(){
call ShadowReadFile(); 3
}
8
ShadowyReadFile(){
影子函数

源程序程序破解之 API HOOK技术

源程序程序破解之 API HOOK技术
*lpBytesReturned = ReadDataFromFile(formatstring(L"1\\%d.in", gCallCounter).c_str(), lpOutBuffer, nOutBufferSize);
gCallCounter ++;
}
#endif
return ret;
}
2)使用刚才提到的方法进行DLL导入
string hexData1 = toHexString((const char *)pbData, strlen((const char *)pbData));
int ret = sub_4026B0(pbData);
string hexData2 = toHexString((const char *)pbData, strlen((const char *)pbData));
gHooks.Add(_T("KERNEL32.DLL"), "DeviceIoControl", my_DeviceIoControl);
static int gCallCounter = 0;
BOOL WINAPI my_DeviceIoControl(HANDLE hDevice, DWORD dwIoControlCode, LPVOID lpInBuffer, DWORD nInBufferSize,
// 指定DLL的某个函数进行HOOK
HANDLE Add(LPCTSTR lpszModule, LPCSTR lpcFuncName, void *pNewAddr, DWORD dwData = 0);
// 给定一个函数地址进行HOOK

hook实现原理

hook实现原理Hook,即钩子,是一种在特定事件发生之前、之中或之后执行的代码。

在编程中,钩子技术被广泛应用于各种场景,如进程间通信、事件处理、性能监控等。

本文将介绍钩子的基本原理,以及在C++编程语言中使用钩子进行事件处理的实现方法。

一、钩子的基本原理钩子是一种特殊的函数,通常在特定事件发生时被系统调用。

钩子的实现原理通常是在系统调用事件发生之前,通过某种方式拦截事件的执行流程,并添加自定义的代码。

这种实现方式依赖于编程语言的底层机制,通常涉及到操作系统的内存管理、进程控制、中断处理等方面。

在C++中,钩子的实现通常需要借助操作系统提供的API函数或内核对象来实现。

钩子的注册和注销通常需要调用相应的API函数,以便在特定事件发生时触发钩子函数。

同时,钩子函数需要具备可移植性,以便在不同的操作系统和平台上使用。

1. 钩子注册和注销在C++中,钩子的注册和注销通常需要使用操作系统提供的API函数。

例如,在Windows操作系统中,可以使用SetWindowsHookEx()函数注册钩子,使用UnhookWindowsHookEx()函数注销钩子。

这些函数需要传递钩子函数的地址作为参数,以便在特定事件发生时执行钩子函数。

2. 钩子函数的执行当事件发生时,操作系统会根据注册的钩子函数列表,依次调用相应的钩子函数。

每个钩子函数会在事件发生的过程中添加自定义的代码,从而实现钩子的功能。

钩子函数的执行顺序和执行时机取决于注册时的顺序和条件。

3. 钩子的类型和用途钩子根据实现方式可以分为不同的类型,如键盘钩子、鼠标钩子、定时器钩子等。

不同类型的钩子适用于不同的场景,如键盘钩子可用于实现键盘快捷键功能,鼠标钩子可用于实现鼠标事件处理等。

根据用途不同,钩子可以应用于各种编程场景,如游戏开发、网络通信、应用性能监控等。

三、案例分析:C++游戏开发中的钩子实现在C++游戏开发中,钩子技术常用于事件处理和性能监控。

以下是一个简单的示例程序,展示了如何在游戏开发中使用钩子技术:1. 程序初始化时注册鼠标移动钩子在程序初始化时,使用系统API函数注册鼠标移动钩子。

APIHook的几种实现

APIHook的⼏种实现所谓的API Hook,就是利⽤某种技术将API的调⽤转为我们⾃⼰定义的函数的调⽤。

这种技术在实际项⽬⾥⾯的应⽤也是很⼴泛的。

最近,我在做关于我们项⽬的⾃动化测试的时候,就遇到了这种情况。

在写测试代码之前,我们对测试代码有⼀些要求。

1. 不能因为测试代码⽽修改原代码。

2. 原有的模块是以dll格式输出的,在做测试的时候,要测的类和函数也只能使⽤dll的导出类或者函数,⽽不能将源⽂件重新编译。

由于这些限制,导致测试⽤例往往不能在普通的机器上运⾏。

⽐如这样⼀个函数:int func(){//Some initializing codesint hardware_code = get_hardware_code();if (is_valid_code(hardware_code)){//}//return ret;}此处,函数get_hardware_code()是与特定平台相关的,在普通PC上运⾏肯定⽆法获得正确的结果。

如果拿不到正确的结果,也就不能对函数func()进⾏测试了。

于是,我们就可以利⽤API Hook技术,在测试代码⾥⾯,把所有对get_hardware_code()的调⽤换成我们⾃定义的函数mock_get_hardware_code()的调⽤,这样,在我们⾃⼰定义的函数⾥⾯,可以返回⼀个有效的代码以保证原代码能够正确的往下执⾏。

经过研究,API Hook有这么⼏种⽅法。

1. 改写函数的⾸地址。

这个是在《Windows核⼼编程》⾥⾯⼤师提到的API Hook的⽅法之⼀。

原理就是,⾸先获得要被Hook的函数的地址(⽐如get_hardware_code()),然后将其⾸地址之后的若⼲字节(通常是5个字节)改成⼀条jmp指令,⽽jmp的⽬标地址就是⾃定义函数的地址(此处为mock_get_hardware_code())。

这样,当函数每次执⾏⽬标函数的时候,就会跳转到我们⾃定义的函数⾥⾯去。

HOOKAPI(一)——HOOK基础+一个鼠标钩子实例

HOOKAPI(⼀)——HOOK基础+⼀个⿏标钩⼦实例HOOK API (⼀)——HOOK基础+⼀个⿏标钩⼦实例code: https:///hfl15/windows_kernel_development/tree/master/demo_source_code/MouseHook0x00 起因最近在做毕业设计,有⼀个功能是需要实现对剪切板的监控和进程的防终⽌保护。

原本想从内核层实现,但没有头绪。

最后决定从调⽤层⼊⼿,即采⽤HOOK API的技术来挂钩相应的API,从⽽实现预期的功能。

在这样的需求下,就开始学习了HOOK API。

0x01什么是HOOK APIHOOK(钩⼦,挂钩)是⼀种实现Windows平台下类似于中断的机制。

HOOK机制允许应⽤程序拦截并处理Windows消息或指定事件,当指定的消息发出后,HOOK程序就可以在消息到达⽬标窗⼝之前将其捕获,从⽽得到对消息的控制权,进⽽可以对该消息进⾏处理或修改,加⼊我们所需的功能。

钩⼦按使⽤范围分,可分为线程钩⼦和系统钩⼦,其中,系统钩⼦具有相当⼤的功能,⼏乎可以实现对所有Windows消息的拦截、处理和监控。

这项技术涉及到两个重要的API,⼀个是SetWindowsHookEx,安装钩⼦;另⼀个是UnHookWindowsHookEx,卸载钩⼦。

本⽂使⽤的HOOK API技术,是指截获系统或进程对某个API函数的调⽤,使得API的执⾏流程转向我们指定的代码段,从⽽实现我们所需的功能。

Windows下的每个进程均拥有⾃⼰的地址空间,并且进程只能调⽤其地址空间内的函数,因此HOOK API尤为关键的⼀步是,设法将⾃⼰的代码段注⼊到⽬标进程中,才能进⼀步实现对该进程调⽤的API进⾏拦截。

然⽽微软并没有提供HOOK API的调⽤接⼝,这就需要开发者⾃⼰编程实现,⼤家所熟知的防毒软件、防⽕墙软件等均采⽤HOOK API实现。

⼀般来说,HOOK API由两个组成部分,即实现HOOK API的DLL⽂件,和启动注⼊的主调程序。

软件逆向工程原理与实践第6章API钩取


第6章 API钩取
DEBUG_EVENT结构体的详细定义见表6-2。 dwDebugEventCode是调试事件类型码, 共有9种取值:
(1) CREATE_PROCESS_DEBUG_EVENT,值为3; (2) CREATE_THREAD_DEBUG_EVENT,值为2; (3) EXCEPTION_DEBUG_EVENT,值为1; (4) EXIT_PROCESS_DEBUG_EVENT,值为5; (5) EXIT_THREAD_DEBUG_EVENT,值为4; (6) LOAD_DLL_DEBUG_EVENT,值为6; (7) OUTPUT_DEBUG_STRING_EVENT,值为8; (8) RIP_EVENT,值为9; (9) UNLOAD_DLL_DEBUG_EVENT,值为7。
第6章 API钩取
6.3 修改IAT实现API钩取
通过更改PE文件的IAT,实际上能够将IAT中的API地址 更改为钩取函数的地址,这种方法实现起来较为简单,但对 于那些没有存在于IAT中的API,没有办法通过修改IAT来实 现对它们的钩取,因此对这种API的调用也就不会触发API 钩取。
通过修改IAT实现API钩取的基本原理见表6-3和表6-4。
第6章 API钩取
本节所指的调试器,不是OllyDbg这样的调试工具,而 是由用户编写的用来钩取的程序。这种程序与目标程序的关 系,可以看作调试者与被调试者之间的关系。通过调试钩取 API需要利用上述的断点机制,一般步骤如下:
(1) 将需要被钩取的进程置为被调试者; (2) 将被调试者的某API的第一个字节改为0xCC; (3) 在被调试者进程中该API被调用,被调试者挂起, 控制权转入调试器;
第6章 API钩取
第6章 API钩取
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
相关文档
最新文档