分享
 
 
 

Win32调试API学习心得(二)

王朝delphi·作者佚名  2006-01-08
窄屏简体版  字體: |||超大  

上一章讲解了如何用调试API来打开一个被调试程序,并给出了一个简单的例子,这一章将祥细

讲解调试消息包含的内容.

类似于消息处理中的消息结构TMessage一样,调试事件也有自己特定的事件结构,那就是TDeb

ugEvent, TDebugEvent在Delphi中的定义为:

TDebugEvent = _DEBUG_EVENT;

_DEBUG_EVENT = record

dwDebugEventCode: DWORD;

dwProcessId: DWORD;

dwThreadId: DWORD;

case Integer of

0: (Exception: TExceptionDebugInfo);

1: (CreateThread: TCreateThreadDebugInfo);

2: (CreateProcessInfo: TCreateProcessDebugInfo);

3: (ExitThread: TExitThreadDebugInfo);

4: (ExitProcess: TExitThreadDebugInfo);

5: (LoadDll: TLoadDLLDebugInfo);

6: (UnloadDll: TUnloadDLLDebugInfo);

7: (DebugString: TOutputDebugStringInfo);

8: (RipInfo: TRIPInfo);

end;

这个结构很复杂,包含了三个基本类型和一个联合类型的数据.dwProcessId和dwThreadId指明

了产生调试事件的进程和线程的ID,dwDebugEventCode指明了产生了何种调试事件,可能的取值

如下表(摘自<<Win32汇编程序设计>>):

1.CREATE_PROCESS_DEBUG_EVENT:进程被创建.当被调试进程刚被创建(还未运行) 或我们的程

序刚以DebugActiveProcess捆绑到一个运行中的进程时该事件发生. 这是我们的程序应该获得

的第一个事件.

2.EXIT_PROCESS_DEBUG_EVENT:被调试进程退出时产生此消息.

3.CREATE_THEAD_DEBUG_EVENT:当一个新线程在被调试进程中创建或我们的程序首次捆绑到运

行中的进程时该事件发生.要注意的是当被调试进程的主线程被创建时不会收到该通知.

4.EXIT_THREAD_DEBUG_EVENT:被调试进程中的线程退出时事件发生.被调试进程的主线程退出

时不会收到该通知.我们可以认为被调试进程的主线程与被调试进程是同义词. 因此, 当我们

的程序看到CREATE_PROCESS_DEBUG_EVENT标志时,对主线程来说,就是CREATE_THREAD_DEBUG_E

VENT标志.

5.LOAD_DLL_DEBUG_EVENT:被调试进程装入一个DLL.当PE装载器第一次分解指向DLL的链接时

,我们将收到这一事件. (当调用CreateProcess装入 被调试进程时)并且当被调试进程调用Lo

adLibrary时也会发生.

6.UNLOAD_DLL_DEBUG_EVENT:一个DLL从被调试进程中卸载时此事件发生.

7.EXCEPTION_DEBUG_EVENT:在被调试进程中发生异常时事件发生.异常实际上是一个调试中断

(int 3h).如果想恢复被调试进程事,以 DBG_CONTINUE 标志调用ContinueDebugEvent 函数.

不要使用DBG_EXCEPTION_NOT_HANDLED 标志否则被调试进程会在NT下拒绝运行(Win98下运行得

很好).

8.OUTPUT_DEBUG_STRING_EVENT:当被调试进程调用DebugOutputString函数向我们的程序发送

消息字符串时该事件发生.

9.RIP_EVENT:系统调试发生错误.

根据dwDebugEventCode的不同,应调用联合中相应的结构来获得相关的调试信息.例如我们有

个名为Debug的TDebguEvent的结构,在调用WaitForDebugEvent(Debug, INFINITE)后接收到调

试信息时,并且dwDebugEventCode的值为CREATE_PROCESS_DEBUG_EVENT,我们就可以通过仿问D

ebug.CreateProcessInfo.hProcess来获得刚创建的被调试进程的进程句柄.

下面将祥细讲解TDebugEvent结构中可能包括的每个结构的含义.因为没有相关的祥细资料,大

部分结果是靠测试所得,如有错漏敬请指正.

一.CreateProcessInfo结构: 对应的调试消息CREATE_PROCESS_DEBUG_EVENT.

CreateProcessInfo.hFile:被调试进程的EXE文件被映射到内存中的内存文件映射句柄,可以

通过打开这个句柄(用OpenFileMapping和MapViewOfFile)来读取此EXE文件的相关信息.如引入

引出表等.

CreateProcessInfo.hProcess:被调试进程的进程句柄,如果要使用ReadProcessMemory和Wri

teProcessMemory等函数来修改被调试进程,就需要用到这个句柄,可以用一个变量保存起来供

以后使用.

CreateProcessInfo.hThread:主线程句柄.

CreateProcessInfo.lpBaseOfImage:可执行文件被装载到虚似地址空间中的基址.

CreateProcessInfo.dwDebugInfoFileOffset:调试信息在可执行文件中的偏移地址(一般为0

,即没有调试信息).

CreateProcessInfo.nDebugInfoSize:调试信息的长度.

CreateProcessInfo.lpThreadLocalBase:主线程基址.

CreateProcessInfo.lpStartAddress:主线程的线程函数地址.

CreateProcessInfo.lpImageName:文件映像名,注意这是一个RVA地址(相对虚拟地址).

CreateProcessInfo.fUnicode:如果此值大于0,则lpImageName指向的文件名为UNICODE码.

二.ExitProcess结构: 对应的调试消息EXIT_PROCESS_DEBUG_EVENT.

ExitProcess.dwExitCode:即被调试程序调用ExitProcess函数时传入的退出代码.

三.CreateThread结构: 对应的调试消息CREATE_THEAD_DEBUG_EVENT.

CreateThread.hThread:新建线程的句柄.线程句柄,如果以后会涉及到对线程的操作,如挂起

线程等,则可以用一个TList来保存进程ID(TDebugEvent.dwThreadId)和相对应的句柄.再在其

它调试事件发生时,根据dwThreadId得到线程句柄.

CreateThread.lpThreadLocalBase:新线程的基址.

CreateThread.lpStartAddress:新线程的线程函数地址.

四.ExitThread结构: 对应的调试消息EXIT_THREAD_DEBUG_EVENT.

ExitThread.dwExitCode:即退出的线程调用ExitThread函数时传入的退出代码.

五.LoadDll结构: 对应的调试消息LOAD_DLL_DEBUG_EVENT.

LoadDll.hFile:被加载的DLL文件映射到内存中的内存文件映射句柄,可以通过打开这个句柄

来读取此DLL文件的相关信息.

LoadDll.lpBaseOfDll:DLL文件被装载到虚似地址空间中的基址.这个地址加上DLL文件引出的

函数的地址,就是这个函数在内存中的地址.

LoadDll.dwDebugInfoFileOffset:调试信息在DLL文件中的偏移地址.

LoadDll.nDebugInfoSize:调试信息的长度.

LoadDll.lpImageName:DLL文件名的地址,是一个RVA地.

LoadDll.fUnicode:如果此值大于0,则lpImageName指向的文件名为UNICODE码.

六.UnLoadDll结构: 对应的调试消息UNLOAD_DLL_DEBUG_EVENT.

UnloadDll.lpBaseOfDll:卸载的DLL文件的基址,可以通过在处理LOAD_DLL_DEBUG_EVENT消息

中保存DLL信息和对应的基址的方法,来得到卸载的DLL信息.

七.Exception结构: 对应的调试消息EXCEPTION_DEBUG_EVENT.

Exception.ExceptionRecord: 这是一个TExceptionRecord结构,里面包含了被调试程序产生

的中断或异常的代码,产生的中断或异常的地址等信息.

八.DebugString结构: 对应的调试消息OUTPUT_DEBUG_STRING_EVENT.

DebugString.lpDebugStringData:被调试进程调用DebugOutputString函数发送的消息字符串

的地址.

DebugString.nDebugStringLength:被调试进程调用DebugOutputString函数发送的消息字符

串的长度.

DebugString.fUnicode:如果此值大于0,则消息字符串为UNICODE码.

九.RipInfo结构: 对应的调试消息RIP_EVENT.

RipInfo.dwError:错误代码.

RipInfo.dwType:错误类型.

了解了以上的知识,我们就可以在调试器中监视这些调试消息,并获得我们感兴趣的信息.但这

仅仅实现了对被调试调试程序的监视.下一章将讲解如何修改被调试程序.

附:一个监视目标程序启动,加载DLL,退出的例子,并演示了如何读取RVA地址,获得加载的DLL

文件名的方法.请到下面的地址下载.

http://qxccccc.8u8.com/debug.rar

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有