/*win32 静/动态库制作与使用*/
chinanetboy
.dll 和.lib 都是程序集合,便于代码重用。都是二进制的文件。 .
dll 也叫动态链接库,与程序链接的方式为运行时链接(run-time linked ),为PE (portable executable )格式,也就是程完整的程序。.
exe 、.dll 、.fon 、.mod 、.drv 、.ocx 等等都是动态链接库。如.exe 为系统调用的函数集合。.
dll 不存在同名引用,且有导出表,与导入表。
.lib 也叫静态链接库,在编译时与程序链接(link-time linked ),将“嵌入”到程序中。
会有冗余(程序文件代码的冗余和运行时内存存储的冗余),当两个lib 相链接时地址会重新建立同。
在使用.lib 之前,要在程序源代码中引用lib 对应的头文件.h ,这些头文件告诉编译器.lib 中有什么。
在生成.dll 时,通常会生成一个.lib 。这个.lib 将被编译到程序文件中,在程序运行的时候,告诉操作系统将要加载的.dll 。
这个.lib 包括对应.dll 的文件名、顺序表(ordinal table 包含.dll 暴露出的函数的进入点),在程序运行的时候,通过顺序表实现函数的跳转。
如果不想使用或者找不到该.lib ,可以用LoadLibrary () Win32 API 和GetLibrary () Win32 API 。
VC IDE 为了实现程序调试,会生成.PDB (程序数据库,二进制),里面包含源文件调用的文件信息和行信息。这样就可以逐行调试了。
打开.lib ,查看其ascii 码,可以看到如@@My_Function1123 的函数名,这些名称在编译时被编译器运用mangling mechanism 进行了名称的mangling 。
在程序的编译过程中,如果出现如下错误“unresolved symbol 通常是因为找不到引用过的外部函数对应的.lib 文件,或者是.c 、.cpp 源文件。
如果在c++ 工程中使用用c 编写的.lib 文件,需要做如下引用:
extern “C ” { #include “headfile.h ” }
dll---com 组件dll ,__ 常规dll___win32 dll ,___mfc dll ,___extended dll (所有dll 不参与编译)
lib | 与obj 文件类似的未编译过符号文件,与obj 文件区别是声明了转入转出函数
****************************************************************************************************
chinanetboy say:
谈发布lib,dll 的区别
发布lib 库时,我们通常也要把这个库对应的头文件也一起发布,以方便别人使用你的LIB ,在wind32 汇编程序,
MS 把所有的API 函数是放在几个大的*.LIB 中,另外还提供一对应的几个*.inc ,实际上它如同*.h 头文件,起到声明API 函数的目的
发布DLL 库时,我们要公开这库里面所有的导入导出函数的函数声明原形,以方便别人使用你的DLL ,
目前WINDOW 实现的就是以一些DLL 文件方式提供出来的,网上很多开源软件也是有用到大量的自己量身定制的DLL 文件
****************************************************************************************************
VC 实现建立LIB 静态链接库的过程
做lib 库文件在windows 汇编是一个重要主题
就谈一下在VC 里面如何实现用C 做一个静态文件库*.lib
然后用程序去调用lib 库里的函数的例子
****************************************************************************************************
1. 用VC 建立一个lib.h 文件
///lib.h file
#ifndef LIB_H
#define LIB_H
extern "C" int add(int x,int y);
extern "C" int sub(int x,int y);
extern "C" int mul(int x,int y);
extern "C" int div(int x,int y);
extern "C" int mod(int x,int y);
#endif
2. 用VC 建立一个lib.cpp 文件
// lib.cpp
#include "lib.h"
int add(int x,int y){return x + y;}
int sub(int x,int y){return x - y;}
int mul(int x,int y){return x * y;}
int div(int x,int y){return x / y;}
int mod(int x,int y){return x % y;}
3. 用VC 新建立一个工作区,再新建立一个工程文件lib,
工程类型选择win32 static library ,下一步为空工程,
在工程中把上面的lib.h,lib.cpp 添加到工程中,编译后
系统就会生在一个lib.lib 的静态链接库文件,到止为止已经建立OK
4. 调用一个静态链接库文件列子
// main.cpp : use this lib.lib
#include <stdio.h>
#include "lib.h" // 让程序知道库中的函数原型
#pragma comment(lib,"lib.lib") // 把这函数的实现库lib.lib 导入代码中,编译器就会自动加载
int main(int argc, char* argv[]){
printf("13 + 6 = %d /n",add(3,6));
printf("12 - 5 = %d /n",sub(12,5));
printf("13 * 6 = %d /n",mul(3,6));
printf("15 / 5 = %d /n",div(15,5));
printf("12 %% 5 = %d /n",mod(12,5));
return 0;
}
运行结果为是
13 + 6 = 18
12 - 5 = 7
13 * 6 = 78
15 / 5 = 3
12 % 5 = 2
****************************************************************************************************
VC 实现DLL(Win32 Dynamic-link library) 库的过程
它是WIN32 下的DLL ,而不是MFC 的DLL
只要在头文件指出声明那些函数将会支持被导出
关键字是:__declspec(dllexport) ,常用于直接加在函数前面
如:extern "C" int __declspec(dllexport)add(int x, int y);
****************************************************************************************************
1. 建立头文件
// 1.demodll.h
#ifndef LIB_H
#define LIB_H
extern "C" int __declspec(dllexport)add(int x,int y);
extern "C" int __declspec(dllexport)sub(int x,int y);
extern "C" int __declspec(dllexport)mul(int x,int y);
extern "C" int __declspec(dllexport)div(int x,int y);
extern "C" int __declspec(dllexport)mod(int x,int y);
#endif
2. 建立实现文件
//demodll.cpp
#include "demodll.h"
int add(int x,int y)
{ return x + y;}
int sub(int x,int y)
{ return x - y;}
int mul(int x,int y)
{ return x * y;}
int div(int x,int y)
{ return x / y;}
int mod(int x,int y)
{ return x % y;}
3. 用VC 新建立一个工作区,再新建立一个工程文件demodll,
工程类型选择win32 dynamic-link library ,下一步为空工程,
在工程中把上面的demodll.h,demodll.cpp 添加到工程中,编译后
系统就会生在一个demodll.DLL 的静态链接库文件,到止为止已经建立OK
4. 调用DLL 中的函数功能的例子
建立一个全新的win32 application 应用程序,
userdll.cpp 代码如下
#include <stdio.h>
#include <windows.h>
typedef int(*lpAddFun)(int, int); // 宏定义函数指标类型
int main(int argc, char *argv[])
{
HINSTANCE hDll; //DLL 控制码
lpAddFun addFun; // 函数指针
hDll = LoadLibrary("demodll.dll");
if (hDll != NULL)
{
addFun = (lpAddFun)GetProcAddress(hDll, "add");
if (addFun != NULL)
{
int result = addFun(3,15);
printf("addFun(3,15)=%d/n", result);
}
FreeLibrary(hDll);
}
return 0;
}
运行结果是addFun(3,15)=18 ,结果OK
转自点击打开链接