dll相关知识备忘

来源:互联网 发布:mac口红圣诞限量2017 编辑:程序博客网 时间:2024/05/06 00:40

非转载,只为了别误导了大家,读的人少一点。

生成dll:

 此主要是原来研究hook机制的时候需要写dll测试而去看了一下如何生成dll,原来一直没怎么关注过。
 我在windows下使用vs2008编译器,它可以通过项目配置类型来配置是生成dll还是exe,还是lib文件。
 简单如下:
 dllhello.h:
  #ifdef HELLO_EXPORTS
#define HELLO_API __declspec(dllexport)
#else
#define HELLO_API __declspec(dllimport)
#endif

extern "C"{
HELLO_API void HelloWorld();
}
上面如果用户定义HELLO_EXPORTS宏,那么定义HELLO_API为导出,反之为导入。通过这种方式库的提供者通过定义HELLO_EXPORTS,将想要导出的函数定义为导出,而库的使用者也就什么都不用定义,因为不定义就意味着导入。使用者可以任意使用了,毕竟这样可以避免限制使用者必须定义某些宏开关。
这声明要导出的函数为C函数,前面要加上HELLO_API的声明。

dllhello.cpp:
HELLO_API void HelloWorld()
{
printf("HelloWorld\n");
}
这就是一个简单的HelloWorld实现,同样加上了HELLO_API,表明当前为导出。

dllmain.cpp:
BOOL APIENTRY DllMain( HMODULE hModule,
                       DWORD  ul_reason_for_call,
                       LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
printf("DLL_PROCESS_ATTACH, dllhello.dll\n");
break;
case DLL_THREAD_ATTACH:
printf("DLL_THREAD_ATTACH, dllhello.dll\n");
break;
case DLL_THREAD_DETACH:
printf("DLL_THREAD_DETACH, dllhello.dll\n");
break;
case DLL_PROCESS_DETACH:
printf("DLL_PROCESS_DETACH, dllhello.dll\n");
break;
}
return TRUE;
}
此文件主要是当dll载入的时候可以做一些初始化操作,dll卸载的时候可以做一些清理操作。

以上三个文件就可以做一个简单的dll了。通过配置工程选项为dll方式。就会在生成目录中生成一个dllhello.lib,dllhello.dll.这个lib仅仅是函数描述文件,不带任何实现文件,它是用来描述dllhello.dll的。
要在自己的程序载入dll,有两种方式一种是编译的时候加上dllhello.h,dllhello.lib文件,在自己的代码中就跟使用普通的源代码一样使用它,然后在生成的exe目录下加上dllhello.dll。这样执行的时候就自动在的当前目录下搜索这个dll,然后执行函数。另外一种是完全摒弃了头文件和lib文件,直接通过GetProcAddress方式获取到函数的地址,调用执行。

函数库分类:
静态库: 在编译过程中将库函数代码直接加入到生成的可执行程序中,这样生成的目标程序会比较大,而且可能会有多份copy,程序运行过程中不需要此lib文件,因为在链接阶段静态库被复制到了程序中。#pragma comment(lib, "dllhello.lib")或者工程配置中设置
动态库: 编译时,只是在生成的可执行程序中简单指定需要使用的库函数信息,即lib函数描述文件,程序运行过程中需要利用此dll库。链接阶段不会被复制到程序中,在运行时由系统动态加载到内存中供程序调用,一次载入。#pragma comment(lib, "dllhello.lib")或者工程配置中设置,或者通过LoadLibrary方式。
原创粉丝点击