WIN2000内部加载模块
 

作者:陆麟
转载请征得作者同意.
2002.2.11



WIN2000在内部管理模块时, 有一些基本函数, 例如, 通常,加载DRIVER用的ZwLoadDrier. 但是, 我们要加载一个USER MODE DLL到KERNEL MODE确比较麻烦. 因为DLLENTRY的接口不同. USER MODE的接口是3个参数, 而KERNEL MODE的结构是2个参数. 真够要命. 我们在USER MODE开发的库如果要在KERNEL MODE用, 就有麻烦了.  通常情况下是自己加载该DLL. 完成DLL->内存的映射. 自己解决IMPORTS/EXPORTS. 我自己也实现了该功能. 但是, 从OS内部来看, OS一定有一个函数, 加载DLL却不CALL DLLMAIN. 这个函数的确存在, 名字叫MmLoadSystemImage. 该函数没有公开, 没有EXPORT, 只在OS CORE中作为内部例程被调用. 令人更加感兴趣的是该函数的返回值, 该函数返回3个值, 其中一个返回值是个数据结构, 该结构里面东西很多东西都是我们所感兴趣的. 但是限于时间和能力, 我仅揭开了该结构头上一部分, 公开如下.
typedef struct tagModuleEntryNode{
 struct tagModuleEntryNode *prev;
 struct tagModuleEntryNode *next;
 ULONG    UnKnown1[4];
 PVOID    ModuleBaseAddr;
 PVOID    EntryPoint;
 ULONG    UnKnown2;
 UNICODE_STRING  ModuleFullPath;
 UNICODE_STRING  ModuleName;
 //the rest unknown
}MODULEENTRYNODE,*PMODULEENTRYNODE;

WIN2000下MmLoadSystemImage的原型如下. NT4的原型和自己的DRIVER中如何使用, 我不打算公开了. :) 使用和探索可是相辅相成的.:D
//
//Undocumented/Unexported MmLoadSystemImage for load DLL into memory
//
typedef NTSTATUS (__stdcall *PMmLoadSystemImage)(PUNICODE_STRING imageName,ULONG,ULONG,ULONG,PMODULEENTRYNODE *ModuleEntryStru,PVOID *ModuleBase);