我来我网
https://5come5.cn
 
您尚未 登录  注册 | 菠菜 | 软件站 | 音乐站 | 邮箱1 | 邮箱2 | 风格选择 | 更多 » 
 

« 1 2» Pages: ( 1/2 total )
本页主题: 如何调用dll中定义的一个全局变量? 隐藏签名 | 打印 | 加为IE收藏 | 收藏主题 | 上一主题 | 下一主题

依然随意



性别: 帅哥 状态: 该用户目前不在线
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 5922
威望: 0
浮云: 760
在线等级:
注册时间: 2006-09-25
最后登陆: 2022-10-30

5come5帮你背单词 [ planet /'plænit/ n. 行星 ]


如何调用dll中定义的一个全局变量?

偶在dll中写了一个栈类,然后在其中实例化,并把它当作dll的输出变量,
请问在加载此dll后,怎样用这个变量?
顶端 Posted: 2007-06-13 10:59 | [楼 主]
依然随意



性别: 帅哥 状态: 该用户目前不在线
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 5922
威望: 0
浮云: 760
在线等级:
注册时间: 2006-09-25
最后登陆: 2022-10-30

5come5帮你背单词 [ film /film/ n. 影片,胶卷,薄层,薄膜,把…拍成电影 ]


没人回呀?
在线等!!!
顶端 Posted: 2007-06-13 11:08 | [1 楼]
huangmao



性别: 帅哥 状态: 该用户目前不在线
等级: 人见人爱
家族: ⊙JAY菊爱园⊙
发贴: 4141
威望: 0
浮云: 1107
在线等级:
注册时间: 2006-09-19
最后登陆: 2010-07-18

5come5帮你背单词 [ rope /rəup/ n. 绳索 ]


虫虫?我来顶你哈哈
顶端 Posted: 2007-06-13 11:23 | [2 楼]
依然随意



性别: 帅哥 状态: 该用户目前不在线
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 5922
威望: 0
浮云: 760
在线等级:
注册时间: 2006-09-25
最后登陆: 2022-10-30

5come5帮你背单词 [ fuse /fju:z/ n. 保险丝,保险,导火线,引信;v. 熔化,(电路)烧断,合并 ]


Quote:
引用第2楼huangmao于2007-06-13 11:23发表的:
虫虫?我来顶你哈哈

谢谢黄毛.
顶端 Posted: 2007-06-13 11:25 | [3 楼]
coolboy





性别: 保密 状态: 该用户目前不在线
等级: 品行端正
发贴: 252
威望: 0
浮云: 1107
在线等级:
注册时间: 2005-10-02
最后登陆: 2016-04-25

5come5帮你背单词 [ smile /smail/ n. 微笑,笑容;vt. 微笑,露出笑容 ]


你是如何加载的DLL的?
隐式加载定义外部变量即可。
显式加载则调用LoadLibrary() & GetProcAddress()获得该变量指针。注意你的符号名。
ps:建议楼主不要在dll中输出变量,而应该仅输出函数。
顶端 Posted: 2007-06-13 13:37 | [4 楼]
liunian



自信之戒 友爱之戒 勇敢之戒 真诚之戒
性别: 帅哥 状态: 该用户目前不在线
头衔: I laugh best and  last
等级: 人见人爱
家族: 菠韬汹勇
发贴: 3869
威望: 0
浮云: 1
在线等级:
注册时间: 2007-03-10
最后登陆: 2021-05-07

5come5帮你背单词 [ inaugurate /i'no:gjureit/ vt. 为…举行开幕(落成、成立)典礼,为…举行就职典礼,开创,开始 ]


帮顶哈~~我不知道怎么解决

这个世界只有一种失败,叫做不努力  
顶端 Posted: 2007-06-13 14:50 | [5 楼]
disneycheng



性别: 帅哥 状态: 该用户目前不在线
头衔: Piano Prince
等级: 荣誉会员
发贴: 1971
威望: 1
浮云: 413
在线等级:
注册时间: 2005-12-16
最后登陆: 2008-06-29

5come5帮你背单词 [ occupy /'okjupəai/ vt. 占,占用,占领,使忙碌 ]


.lib
Disney
顶端 Posted: 2007-06-13 23:13 | [6 楼]
vista





性别: 帅哥 状态: 该用户目前不在线
头衔: 不日成名
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 8138
威望: 0
浮云: 5
在线等级:
注册时间: 2006-09-30
最后登陆: 2018-06-14

5come5帮你背单词 [ fist /fist/ n. 拳头;vt. 用拳打,紧握 ]


Quote:
引用第4楼coolboy于2007-06-13 13:37发表的:
你是如何加载的DLL的?
隐式加载定义外部变量即可。
显式加载则调用LoadLibrary() & GetProcAddress()获得该变量指针。注意你的符号名。
ps:建议楼主不要在dll中输出变量,而应该仅输出函数。

是显式加的,如果想在dll中定义常用类.怎么在可执行模块中实例化这个类呀?
既然选择了远方,便只顾风雨兼程...
外网:https://5come5.cn/
顶端 Posted: 2007-06-15 09:13 | [7 楼]
coolboy





性别: 保密 状态: 该用户目前不在线
等级: 品行端正
发贴: 252
威望: 0
浮云: 1107
在线等级:
注册时间: 2005-10-02
最后登陆: 2016-04-25

5come5帮你背单词 [ penny /'peni/ n. 便士 ]


Quote:
引用第7楼vista于2007-06-15 09:13发表的:

是显式加的,如果想在dll中定义常用类.怎么在可执行模块中实例化这个类呀?

你的类到底是在dll中实例化的,还是在客户程序中实例化的?

显示加载只能加载函数和变量。你可以在dll中实例化一个对象,作为全局变量,然后通过GetProcAddress()的到变量的指针。显示加载不必包含库文件。

要在客户程序中实例化,则必须隐式加载。你需要在客户程序中将完整的类的声明放进来。并加上__declspec(dllimport)声明,以表明你的类是定义在外部。然后包含dll的库文件就可以了。
顶端 Posted: 2007-06-15 11:39 | [8 楼]
依然随意



性别: 帅哥 状态: 该用户目前不在线
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 5922
威望: 0
浮云: 760
在线等级:
注册时间: 2006-09-25
最后登陆: 2022-10-30

5come5帮你背单词 [ boundary /'baundəri/ n. 分界线,边界 ]


Quote:
引用第8楼coolboy于2007-06-15 11:39发表的:

你的类到底是在dll中实例化的,还是在客户程序中实例化的?

显示加载只能加载函数和变量。你可以在dll中实例化一个对象,作为全局变量,然后通过GetProcAddress()的到变量的指针。显示加载不必包含库文件。

.......

是想在可执行模块中实例化dll模块中的类,
还有,如果是dll模块中已经实例化的类,怎样在可执行模块中访问喃?那个GetProcAddress()还可以获取变量呀?
顶端 Posted: 2007-06-15 12:03 | [9 楼]
依然随意



性别: 帅哥 状态: 该用户目前不在线
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 5922
威望: 0
浮云: 760
在线等级:
注册时间: 2006-09-25
最后登陆: 2022-10-30

5come5帮你背单词 [ realistic /riə'listik/ a. 现实的,现实主义的,逼真的 ]


Quote:
引用第8楼coolboy于2007-06-15 11:39发表的:

你的类到底是在dll中实例化的,还是在客户程序中实例化的?

显示加载只能加载函数和变量。你可以在dll中实例化一个对象,作为全局变量,然后通过GetProcAddress()的到变量的指针。显示加载不必包含库文件。

.......

GetProcAddress()还可以获取变量地址呀?
顶端 Posted: 2007-06-15 12:19 | [10 楼]
coolboy





性别: 保密 状态: 该用户目前不在线
等级: 品行端正
发贴: 252
威望: 0
浮云: 1107
在线等级:
注册时间: 2005-10-02
最后登陆: 2016-04-25

5come5帮你背单词 [ inorganic /ino:'gænik/ a. 无机的,无生物的 ]


Quote:
引用第9楼依然随意于2007-06-15 12:03发表的:

是想在可执行模块中实例化dll模块中的类,
还有,如果是dll模块中已经实例化的类,怎样在可执行模块中访问喃?那个GetProcAddress()还可以获取变量呀?

你在dll中创建一个类指针,指向你实例化的那个对象,输出这个指针,就可以用GetProcAddress得这个到指针。
GetProcAddress()其实是通过符号名来获取地址的,用dumpbin查看dll的输出表,你就能看到你所属出的符号名了。
输出时建议遵循C调用约定,加上extern "C。
顶端 Posted: 2007-06-15 13:10 | [11 楼]
依然随意



性别: 帅哥 状态: 该用户目前不在线
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 5922
威望: 0
浮云: 760
在线等级:
注册时间: 2006-09-25
最后登陆: 2022-10-30

5come5帮你背单词 [ concentrate /'konsəntreit/ vt. 集中,浓缩;n. 浓缩物 ]


Quote:
引用第11楼coolboy于2007-06-15 13:10发表的:

你在dll中创建一个类指针,指向你实例化的那个对象,输出这个指针,就可以用GetProcAddress得这个到指针。
GetProcAddress()其实是通过符号名来获取地址的,用dumpbin查看dll的输出表,你就能看到你所属出的符号名了。
输出时建议遵循C调用约定,加上extern "C。

GetProcAdress()要两个参数,函数指针类型的一个实例,
如:typedef void (* pFunc)(int ,int);
  pFunc mfunc;
然后将mfunc传给它,但如果要将变量指针取出,调用主程序中怎么定义这个参数呀,
我开始传给它一个void*型的,但取回后,不能访问这个指针指向类的成员函数,
顶端 Posted: 2007-06-15 20:41 | [12 楼]
coolboy





性别: 保密 状态: 该用户目前不在线
等级: 品行端正
发贴: 252
威望: 0
浮云: 1107
在线等级:
注册时间: 2005-10-02
最后登陆: 2016-04-25

5come5帮你背单词 [ blunt /blΛnt/ a. (刀子)钝的,不锋利的,迟钝的,直率的,坦白的 ]


Quote:
引用第12楼依然随意于2007-06-15 20:41发表的:

GetProcAdress()要两个参数,函数指针类型的一个实例,
如:typedef void (* pFunc)(int ,int);
  pFunc mfunc;
然后将mfunc传给它,但如果要将变量指针取出,调用主程序中怎么定义这个参数呀,
.......

首先你要知道什么叫输出符号名,它就是GetProcAdress()的第二个参数,你可以用dumpbin -exports yourfile 查看你的dll的输出符号名。
比如我随便写的一个dll查看结果如下:

      1   0    00011410    ??0Cdll@@QAE@XZ
      2   1    00011375    ??0Point@@QAE@XZ
      3   2    000114E2    ??4Cdll@@QAEAAV0@ABV0@@Z
      4   3    000115CD    ??4Point@@QAEAAV0@ABV0@@Z
      5   4    000110AA    ?SetPoint@Point@@QAEXHH@Z
      6   5    00011389    ?fndll@@YAHXZ
      7   6    00037C40    ?ndll@@3HA
      8   7    00037C44    hello

其中最边上那列中那些酷似乱码一般的字符就是符号名,代表你所输出的变量或函数,而这个表实际是dll的输出表。GetProcAddree是怎么找到你输出的函数和变量的呢?很简单,他根据你给的符号名来查表,得到第三列中的偏移地址,然后做一些处理后返回给你,你就得到了函数或者变量的指针。所以你可以用dumpbin得到GetProcAdress()的第二个参数。

其次,你会注意到上面的表里最后一行似函数名乎比较规则,没有乱码,因为这个输出变量是按C调用约定(定义时加上extren "C"),其他的则是按C++调用约定。因为C++中出现了重载函数,函数名是一样的,所以为了区别这些函数,不得不加一些信息区别,这些函数名就看起来就比较乱。C中不允许函数同名,所以不需要加以区分。因此,你可以把你的变量按C约定输出,或者直接查看输出表,得到符号名。要注意,这里讨论的是显示链接,隐式链接不需要知道符号名,包含lib文件即可。

第三,你需要把得到的地址强制转换为原来的类型,是函数你就转换为函数指针,是变量你就转换为变量指针,是类你就转换为对象指针。注意你必须先声明这些类型,比如输出对象时你要先在客户程序中包含类的完整定义,但你不必实现它。同时,类中原本私有和保护的变量你依然无法访问。

另外,输出变量不是个好主意,因为这些变量必须是全局的,一旦你的dll被加载,这些变量就被创建了,比较浪费资源。我刚才试了一下,可以输出一个对象,但只能查看对象的属性,无法调用对象的方法,所以显示加载+输出全局对象是非常不好的一种做法。
顶端 Posted: 2007-06-15 22:39 | [13 楼]
依然随意



性别: 帅哥 状态: 该用户目前不在线
等级: 前途无量
家族: ⊙JAY菊爱园⊙
发贴: 5922
威望: 0
浮云: 760
在线等级:
注册时间: 2006-09-25
最后登陆: 2022-10-30

5come5帮你背单词 [ margin /'ma:d3in/ n. 页边,边缘,余地 ]


Quote:
引用第13楼coolboy于2007-06-15 22:39发表的:

首先你要知道什么叫输出符号名,它就是GetProcAdress()的第二个参数,你可以用dumpbin -exports yourfile 查看你的dll的输出符号名。
比如我随便写的一个dll查看结果如下:

      1   0   00011410   ??0Cdll@@QAE@XZ
.......

你没有回答我的问题,我的问题是如下:
dll模块中:
class example.................................................................//定义一个类
{
//something and some methods
}
example* GetExample()
{example* pExample=new example; ..........................//new一个类实例;
}
dll.def中
LIBRARY
EXPORTS
GetExample
主程序中:
#include some files                     //没有将dll中定义类的头文件包进去.
int main()
{
typedef void(*pFunc)();                   //若为Example则不能识别,只能选void
加载dll;
获取函数地址;
//以上成功了;
调用指向GetExample()的函数指针,获取了一个指向example 类的指针(但实际是void型),
以上也成功了;;



接下来问题出现了;
我不能通过这个返回的指针访问example的成员函数,或成员变量;
}
就是上面的问题,怎么办呀?
我的前提是#include中不包含example类的头文件,应为如果包含,我就不用费这么大劲了,就不用dll了.



顶端 Posted: 2007-06-16 00:45 | [14 楼]
« 1 2» Pages: ( 1/2 total )
我来我网·5come5 Forum » 程序员之家

Total 0.012067(s) query 5, Time now is:11-23 13:03, Gzip enabled
Powered by PHPWind v5.3, Localized by 5come5 Tech Team, 黔ICP备16009856号