|
在本节的示例代码中,我会演示如何使用psapi.dll和imagehlp.dll完成如下任务:
l 枚举所有内核组件和驱动程序
l 枚举系统当前管理的所有进程
l 枚举加载到进程地址空间的所有模块(modules)
l 枚举一个给定组件的所有符号(如果其符号文件可用的话)
psapi.dll的接口并不像其设计的那样好。它提供了最小的功能集,尽管它曾试图增加一些便利性。虽然,它能从内核获取一些信息但却扔掉了其中的大多数,只留下很少一部分。
由于psapi.dll和imagehlp.dll的函数并不是标准Win32 API的一部分,它们所需的头文件和导入库不会自动包括在Visual C/C++工程中。因此,列表1-2中列出的四个指示符(directives)应该在你的原文件中出现。第一部分是所需的头文件,剩余部分用于和这两个DLL中的导出函数建立动态链接。
#include <imagehlp.h>
#include <psapi.h>
#pragma comment (linker,”/defaultlib:imagehlp.dll”)
#pragma comment (linker,”/defaultlib:psapi.dll”)
列表1-2 增加psapi.dll和imagehlp.dll到Visual C/C++工程
译注:
其实,也可以采用静态链接,如下:
#pragma comment(lib,”psapi.lib”)
#pragma comment(lib,”imagehlp.lib”)
这样,就不需要目标平台必须有这两个DLL了。
光盘中的示列代码
在本书的附带光盘中,有两个工程是构建与psapi.dll和imagehlp.dll之上。其中一个示例工程是w2k_sym.exe----一个Windows 2000符号浏览器,它可以从任意符号文件中提取符号名称(假如你已经安装了的话)。它输出的符号表可以按照名称、地址和大小来排序,同时接受一个采用通配符的过滤器。作为附送功能,w2k_sym.exe还可列出当前活动的系统模块/驱动程序的名称,运行的进程和每个进程加载的模块。另一个示例工程是调试支持库w2k_dbg.dll,这个库包含几个便于使用的针对psapi.dll和imagehlp.dll的外包函数。w2k_sym.exe完全依赖这个DLL。这些工程的源代码分别位于光盘的\src\w2k_dbg和\src\w2k_sym目录。
表1-2列出了w2k_dbg.dll用到的函数名称。A./W列表示对ANSI和Unicode的支持情况。稍早提示过,psapi.dll同时支持ANSI和Unicode。不幸的是,imagehlp.dll和dbghelp.dll没有这么聪明,其中几个函数只能接受ANSI字符串。这有些烦人,因为Windows 2000的调试程序通常不能运行在Windows 9x上,所以不该限制使用Unicode。若将imagehlp.dll假如你的工程中,你就必须选择是使用ANSI还是来回转化Unicode字符串。因为我很讨厌在一个可处理16位字符串的系统中使用8位的字符串,所以我选择后一种方法。w2k_dbg.dll导出的所有函数中涉及的字符串默认都是Unicode。所以,如果你在自己的Windows 2000工程中使用这个DLL不需要再关心字符大小问题。
另一方面,imagehlp.dll和dbghelp.dll有一个psapi.dll没有的特性:他们同样适用于Win64----让每个开发人员恐惧的64位Windows,这是因为没人知道将Win32程序移植到Win64有多困难。这些DLL导出了Win64 API函数,好吧----或许有一天我们会用到他们。
|
名称 |
A/W |
库 |
|
EnumDeviceDrivers |
|
psapi.dll |
|
EnumProcesses |
|
psapi.dll |
|
EnumProcessModules |
|
psapi.dll |
|
GetDeviceDriverFileName |
A/W |
psapi.dll |
|
GetModuleFileNameEx |
A/W |
psapi.dll |
|
GetModulelnformation |
|
psapi.dll |
|
ImageLoad |
A |
imagehlp.dll |
|
ImageUnload |
|
imagehlp.dll |
|
SymCleanup |
|
imagehlp.dll |
|
SymEnumerateSymbols |
A/W |
imagehlp.dll |
|
Symlnitialize |
A |
imagehlp.dll |
|
SymLoadModule |
A |
imagehlp.dll |
|
SymUnloadModule |
|
imagehlp.dll |
表1-2 w2k_dbg.dll使用的调试函数
我没有深入的探究psapi.dll和imagehlp.dll。本书的焦点在于未文档化的接口,而且在SDK中与这两个DLL的接口有关的文档还算不错。可是,我并不打算完全绕过它们,因为它们和Windows 2000 Native API(将在第2章讨论)紧密联系在一起。而且,psapi.dll是证明为什么未文档化的接口比文档化的那个更好的最佳实例。该DLL的接口不仅仅只是看上去的简单和笨拙---在某些地方它竟然会返回明显矛盾的数据。如果我不得不编写一个专业的调试工具来出售,我是不会指望这个DLL的。Windows 2000内核提供了强大、通用和更加合适的调试API函数。然而,这些几乎都没有文档化。幸运的是,微软提供的许多系统工具都广泛的使用了这些API,so it has undergone only slight changes across Windows NT versions。是的,如果你使用了这些API,每当发布了新版的NT,你就必须修订和小心的测试你的软件,但是它们带来的好处远大于这些障碍。
本章随后的大多数示例代码都来自w2k_dbg.dll,你可以在光盘的\src\w2k_dbg\w2k_dbg.c中发现它们。这个DLL封装了多个步骤,以返回更丰富的信息。数据会以合适的大小、链表(包括可选的索引值)返回,以便于对它们进行排序等操作。表1-3列出了w2k_dbg.dll导出的所有API函数。这些函数很多,详细讨论每个函数已经超出了本章的范围,因此我鼓励你去参考w2k_sym.exe的源代码(位于光盘\src\w2k_sym\x),来学习它们的典型用法。
上一页 [1] [2] [3] 下一页 |