社区
进程/线程/DLL
帖子详情
VC如何动态调用DLL里的函数?
wenyongjie
2004-07-26 11:30:01
有例子最佳
...全文
1105
4
打赏
收藏
VC如何动态调用DLL里的函数?
有例子最佳
复制链接
扫一扫
分享
转发到动态
举报
AI
作业
写回复
配置赞助广告
用AI写文章
4 条
回复
切换为时间正序
请发表友善的回复…
发表回复
打赏红包
kpld8888
2004-07-27
打赏
举报
回复
我有,qq:101059899,email:kpld@163.com
qqhuangshen
2004-07-27
打赏
举报
回复
综合以上例子,有两种调用动态连接库中的函数的方法
1.通过引入库:
利用Visual C++提供的IMPLIB工具为动态连接库生成引入库,为引入库设计一个头文件:
#ifndef _MYMATH_H
#define _MYMATH_H
extern “C”
{
int Summary(int n);
int Factorial(int n);
}
#endif
将该头文件包含在使用动态连接库的源文件中,连接应用程序时会连接上该引入库。这样,应用程序就可以象使用静态连接库一样自由的使用动态连接库中的函数了。注意要把动态连接库拷贝到应用程序可执行文件所在的目录(\TEST\DEBUG)下。
这是一种常用的方法。实际上,应用程序就是通过这种方式访问Windows的API函数的。Windows为其内核动态连接库生成引入库并提供了头文件。应用程序在编译时将引入库的信息带入可执行文件中,在运行时通过引入库信息访问API函数。
2. 直接指定库和函数地址
这种方式适合于一些提供文件格式转换等服务的动态连接库。比如,一个程序带有多个动态连接库,分别用于访问JPG、BMP、GIF等多种图像文件格式,这些动态连接库提供了相同的库函数接口。此时,无法使用引入库方式指定库函数。可以采用下面的方法来解决这个问题。
HANDLE hLibrary;
FARPROC lpFunc;
int nFormat;
if(nFormat==JPEG)//如果是JPEG格式,装入JPEG动态连接库
{
hLibrary=LoadLibrary(“JPEG.DLL”);
}
else//是GIF格式
hLibrary= LoadLibrary(“GIF.DLL”);
if(hLibrary>=32)
{
lpFunc=GetProcAddress(hLibrary,”ReadImage”);
if(lpFunc!=(FARPROC)NULL)
(*lpFunc)((LPCTSTR)strFileName);
FreeLibrary(hLibrary);
}
LoadLibrary函数装入所需的动态连接库,并返回库的句柄。如果句柄小于32,则载入库失败,错误含义参见有关手册。GetProcAddress函数使用函数名字取得函数的地址。利用该函数地址,就可以访问动态连接库的函数了。
qqhuangshen
2004-07-27
打赏
举报
回复
现在,来使用刚才生成的动态连接库。。首先,把mymaths\debug目录下的mymaths.dll拷贝到test\debug目录下。test程序运行时,会在该目录下搜索动态连接库文件。然后修改testdlg.h,在其中加入一个函数LoadDLL()的声明,LoadDLL用于载入动态连接库。
class CTestDlg : public CDialog
{
// Construction
public:
CTestDlg(CWnd* pParent = NULL); // standard constructor
protected:
void LoadDLL();
//......
}
然后修改testdlg.cpp,修改后如清单9.5。
清单95. TestDlg.cpp文件
// TestDlg.cpp : implementation file
//
#include "stdafx.h"
#include "Test.h"
#include "TestDlg.h"
//#include "mymath.h" //注释掉mymath.h头文件
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
//The instance of the Mymaths.DLL library
HINSTANCE ghMathsDLL=NULL;
//declare the Summary() function from the Mymaths.DLL libray.
typedef int (*SUMMARY)(int);
SUMMARY Summary;
//declare the Factorial() function from
//the Mymaths.DLL library.
typedef int (*FACTORIAL)(int);
FACTORIAL Factorial;
/////////////////////////////////////////////////////////////////////////////
// CAboutDlg dialog used for App About
class CAboutDlg : public CDialog
{
//...
};
//CAboutDlg的一些成员函数定义
//CTestDlg的一些成员函数定义
void CTestDlg::OnSum()
{
// TODO: Add your control notification handler code here
LoadDLL();
int nSum=Summary(10);
CString sResult;
sResult.Format("Sum(10)=%d",nSum);
AfxMessageBox(sResult);
}
void CTestDlg::OnFactorial()
{
// TODO: Add your control notification handler code here
LoadDLL();
int nFact=Factorial(10);
CString sResult;
sResult.Format("10!=%d",nFact);
AfxMessageBox(sResult);
}
void CTestDlg::LoadDLL()
{
//如果DLL已经载入,则返回
if(ghMathsDLL!=NULL)
{
return;
}
//载入Mymaths.DLL文件.
ghMathsDLL=LoadLibrary("mymaths.DLL");
//如果载入DLL失败,提示用户
if(ghMathsDLL==NULL)
{
AfxMessageBox("Cannot load DLL file!");
}
//获得DLL中Summary函数的地址
Summary=(SUMMARY)GetProcAddress(ghMathsDLL,"Summary");
//获得DLL中Factorial函数的地址
Factorial=(FACTORIAL)GetProcAddress(ghMathsDLL,"Factorial");
}
在testdlg.cpp文件开头,加入:
//The instance of the Mymaths.DLL library
HINSTANCE ghMathsDLL=NULL;
//declare the Summary() function from the Mymaths.DLL libray.
typedef int (*SUMMARY)(int);
SUMMARY Summary;
//declare the Factorial() function from
//the Mymaths.DLL library.
typedef int (*FACTORIAL)(int);
FACTORIAL Factorial;
qqhuangshen
2004-07-27
打赏
举报
回复
譬如这样创建了如下DLL文件。最简单的求和函数和阶乘函数
文件1:mymaths.cpp
////////////////////////////
//mymaths.cpp
//
//a maths API DLL.
//
///////////////////////////
#include<windows.h>
//Declare the DLL functions prototypes
int Summary(int);
int Factorial(int);
//////////////////////////
//DllEntryPoint():The entry point of the DLL
//
/////////////////////////
BOOL WINAPI DLLEntryPoint(HINSTANCE hDLL,DWORD dwReason,
LPVOID Reserved)
{
switch(dwReason)
{
case DLL_PROCESS_ATTACH:
{
//一些初始化代码
break;
}
case DLL_PROCESS_DETACH:
{
//一些用于清理的代码
break;
}
}
return TRUE;
}
int Summary(int n)
{
int sum=0;
int i;
for(i=1;i<=n;i++)
{
sum+=i;
}
return sum;
}
int Factorial(int n)
{
int Fact=1;
int i;
for(i=1;i<=n;i++)
{
Fact=Fact*i;
}
return Fact;
}
文件2:mymaths.def
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;Mymaths.DEF
;
;The DEF file for the Mymaths.DLL DLL.
;
LIBRARY mymaths
CODE PRELOAD MOVEABLE DISCARDABLE
DATA PRELOAD SINGLE
EXPORTS
;The names of the DLL functions
Summary
Factorial
在文件mymaths.cpp开头,声明了动态连接库所包含的两个函数:Summary和Factorial。接着是DllEntryPoint()函数的定义。DllEntryPoint()顾名思义是动态连接库的入口,应用程序通过该入口访问动态连接库提供的服务。DllEntryPoint()主体是一个switch/case语句:
switch(dwReason)
{
case DLL_PROCESS_ATTACH:
{
//一些初始化代码
break;
}
case DLL_PROCESS_DETACH:
{
//一些用于清理的代码
break;
}
}
VC
中
调用
dll
函数
的两种方法
一、显式
调用
1、定义
函数
指针 typedef int (*
dll
_mul)(int a,int b); 2、加载
dll
,并获取其程序实例句柄 HINSTANCE h
dll
=loadlibrary("c:/cpp
Dll
.
dll
"); 3、从
dll
实例句柄中获取
函数
指针
dll
_mul mymul=(
dll
_mul)...
C++
动态
调用
dll
中的
函数
1.
dll
中的
函数
声明必须写上extern “C” __declspec(
dll
export),不然找不到该
函数
。2.
dll
文件和exe放在同一文件夹下。
VC
中如何
调用
DLL
中的
函数
VC
中如何
调用
DLL
中的
函数
调用
DLL
有两种方法:静态
调用
和
动态
调用
.(一).静态
调用
其步骤如下:1.把你的youApp.
DLL
拷到你目标工程(需
调用
youApp.
DLL
的工程)的Debug目录下;2.把你的youApp.lib拷到你目标工程(需
调用
youApp...
利用
vc
调用
dll
利用
vc
调用
dll
一时兴起,研究下关于
dll
的
调用
,算是作为我首次发表文章啦,怎么说也是我的处子作啊~~~好吧入正题啦 关于
dll
的
调用
,查了下资料,有两种——(一)静态
调用
(二)
动态
调用
,下面是分别的
调用
方法 ...
vc
调用
dll
静态
调用
和
动态
调用
.
VC
调用
DLL
调用
DLL
有两种方法:静态
调用
和
动态
调用
. (一).静态
调用
其步骤如下: 1.把你的youApp.
DLL
拷到你目标工程(需
调用
youApp.
DLL
的工程)的Debug目录下; 2.把你的youApp.lib拷到你目标工程(需
调用
youApp...
进程/线程/DLL
15,473
社区成员
49,171
社区内容
发帖
与我相关
我的任务
进程/线程/DLL
VC/MFC 进程/线程/DLL
复制链接
扫一扫
分享
社区描述
VC/MFC 进程/线程/DLL
社区管理员
加入社区
获取链接或二维码
近7日
近30日
至今
加载中
查看更多榜单
社区公告
暂无公告
试试用AI创作助手写篇文章吧
+ 用AI写文章