您的位置:首页 > 其它

Dll小结-->基础部分

2010-05-18 16:14 274 查看
DLL总结
1:Dll内存
比如system32下有Dll.dll一份A调用Dll.dll的时候物理内存中会有且只有一份该dll的内存映射

然后将dll的内存通过“虚拟地址到物理地址的一种映射机制”将他们映射到A的4G虚拟内存中的一部分内存中

当再有B调用该Dll.dll的时候仍然会将dll的内存映射到B的虚拟内存地址中不过这个时候需要注意的是AB共享代码区而数据区是不共享的B调用Dll的时候dll之前的数据区会产生一份拷贝然后来映射到B的虚拟内存这样A对数据区的数据产生修改时不会影响B中的结果

最后尤其需要注意的是Dll还可以创建共享区共享数据区不像数据区那样随着exe的调用会产生拷贝共享数据区不产生拷贝所有调用dll的exe都将映射该数据当A对其中的数据修改之后同样会影响B中的结果



语法:
共享数据区
#pragmadata_seg("Share_Name");


//-->Code


#pragmadata_seg();

#pragmacomment(linker,"/SECTON:Share_Name,RWS")


共享数据区初始化必须赋值






在调用Dll时出现ESP错误很可能是堆栈不平衡造成造成的原因很可能是


声明调用或定义的时候出现调用约定不一致造成




问:是否只有导出函数才可以调用?

解答:不是即使未导出的函数依然可以通过


比如DLL.dll中有导出函数voidShow()以及未导出函数voidNoShow()

Dll.dll
加载到exe虚拟内存后dll的模块句柄hModule是0x100000而Show的相对偏移是0x1005

我们来定义一个函数指针类型void(*FUNTYPE)()

这样我们通过TYPEFUNpFun=(TYPEFUN)GetProcAddress(hModule,"Show");

得到的pFun值就是0x101005而我们可以通过pFun()来调用该函数


这样是在动态调用dll的时候常规的方法

其实即使未导出的函数NoShow()在dll中也有个相对偏移我们假设其为0x2000

那么我们在LoadLibraydll之后可以直接通过TYPEFUNpFun=(TYPEFUN)0x102000然后pFun()来使用该函数


必须指出这是非常规使用方法一般都不会这样使用



关于
HMODULEGetModuleHandle(LPCTSTRlpModuleName//modulename);
1
Thereturnedhandleisnotglobalorinheritable.Itcannotbeduplicatedorusedbyanotherprocess.
2:在EXE中当lpModuleName==Null的时候返回值就是当前的exe模块句柄
而在dll中该返回值是调用该dll的模块的句柄

调用顺序
动态加载dll时
EXE全局构造à进入ExeMainàDll全局构造à进入DLLMain
EXE全局析构ß退出ExeMainßDll全局析构ß退出DllMain

静态加载Dll时
DLL全局构造à进入DllMainàEXE全局构造à进入ExeMain
DLL全局析构ß退出DllMainàEXE全局析构ß退出ExeMain
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: