delphi调用vc写的DLL,为什么不能成功?接口该如何定义?

thief21cn 2002-01-31 07:43:18
用VC写的一个函数如下,
extern "C" __declspec(dllexport) void __cdecl snmpget(
char *ipaddress, char *oid, char *Value, int *ValueLength, int *state, int version = 1, char * Community = "public")
想用Delphi调用,我以为接口函数应该定义成这样, procedure snmpget(var ipaddress : Pchar; var oid : Pchar;var Value : Pchar; var ValueLength : Integer; var State:Integer; VERSION : Integer = 1; var Community : String = 'public'); stdcall; external 'snmp_pp.dll' name 'snmpget';
可是编译没法通过,说Default parameter 'Community' must be by-value or const
,请大侠指点一二。
...全文
168 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
greenspan 2002-02-05
  • 打赏
  • 举报
回复
ok,我看看,Greenzpan@163.net
thief21cn 2002-02-05
  • 打赏
  • 举报
回复
非常感谢各位的帮助,终于搞定了.
函数是这样定义的:
type
PInteger = ^Integer;


procedure snmpget(ipaddress : Pchar; oid : Pchar; Value : Pchar; ValueLength : PInteger; State:PInteger; VERSION : Integer; const Community : PChar); cdecl; external 'snmp_pp.dll' name 'snmpget';

procedure TForm1.Button1Click(Sender: TObject);
var
ipaddress,oid,Value: array[0..999] of char;
ValueLength,State:PInteger;
begin
ipaddress := '172.24.224.10';
oid := '.1.3.6.1.2.1.1.1.0';
Value := '';
New(ValueLength);
ValueLength^ := 0;
New(State);
State^ := 0;

snmpget(ipaddress,oid,Value,ValueLength,State,1,'public');

if (State^ = 0) then
ShowMessage(Value);

Dispose(ValueLength);
Dispose(State);
end;
thief21cn 2002-02-03
  • 打赏
  • 举报
回复
to GreensPan
非常感谢你的帮助,我也怀疑是你说的这个原因,没有分配足够的空间。
可是,我按照你说的修改以后,编译时候居然出来这个错误Write Error
on 'H:\Delphi\SNMP\Unit1.dcu',注释掉snmpget函数调用那一句就没有
这个错误,怎么回事?

如果你不忙的话,我把那个Dll发给你,还有VC下的函数接口,你帮我看看?
greenspan 2002-02-01
  • 打赏
  • 举报
回复
procedure TForm1.Button1Click(Sender: TObject);
var
ipaddress,oid,Value,Community : String;
ValueLength,Version,State:PInteger;
begin
ipaddress := '172.24.224.10';//如果长度是传进去的长度就不用用SetLength分配空间了
oid := '.1.3.6.1.2.1.1.1.0';//如果长度是传进去的长度就不用用SetLength分配空间了
SetLength(Value,足够大的空间{比如255,看你所传的值});//Value := '';
ValueLength^ := 0;
State^ := 0;
Version^ := 1;
SetLength(Community,足够大的空间{比如255,看你所传的值});
snmpget(PChar(ipaddress),PChar(oid),PChar(Value),ValueLength,State,Version,PChar(Community));
SetLength(Value,StrLen(Value));SetLength(Community,StrLen(Community));
//
end;



greenspan 2002-02-01
  • 打赏
  • 举报
回复
procedure TForm1.Button1Click(Sender: TObject);
var
ipaddress,oid,Value,Community : Pchar;
ValueLength,Version,State:Integer;
begin
ipaddress := '172.24.224.10';
oid := '.1.3.6.1.2.1.1.1.0';
Value := '';
ValueLength := 0;
State := 0;
Version := 1;
Community := 'public';

snmpget(ipaddress,oid,Value,ValueLength,State,Version,Community);
end;

在我看来,你传入的指针有的没有初始化足够的空间,比如Value你初始化成'',dll就没有空间
存放数据了,qkl的声明应该是对的,我是用stdcall的!
所以我建议你这样调用:
procedure TForm1.Button1Click(Sender: TObject);
var
ipaddress,oid,Value,Community : String;
ValueLength,Version,State:Integer;
begin
ipaddress := '172.24.224.10';
oid := '.1.3.6.1.2.1.1.1.0';
SetLength(Value,足够大的空间{比如255,看你所传的值});
ValueLength := 0;
State := 0;
Version := 1;
Community := 'public';

snmpget(ipaddress,oid,PChar(Value),ValueLength,State,Version,Community);
SetLength(Value,StrLen(Value));
//
end;



qkl 2002-02-01
  • 打赏
  • 举报
回复
不只把 stdcall 改成 cdecl,还有其他改动,注意了没有。

我现在经常要调用 vc 写的 DLL(没问题) ,调用方式一般是 cdecl ,但我不敢肯定(不过不难),但你的参数是错了。
thief21cn 2002-01-31
  • 打赏
  • 举报
回复
照你说的该了,把stdcall 改成 cdecl, 编译运行,当执行到那一句时,还是有Access violation错误。

:(
qkl 2002-01-31
  • 打赏
  • 举报
回复
不,不应该是
type
PInt = ^Integer;
procedure snmpget(ipaddress : Pchar; oid : Pchar; Value : Pchar; ValueLength:
PInt; state: PInt; version: integer; Community: pchar); cdecl; external
'snmp_pp.dll' name 'snmpget';
qkl 2002-01-31
  • 打赏
  • 举报
回复
应该是:
procedure snmpget(var ipaddress : Pchar; var oid : Pchar;var Value : Pchar;
var ValueLength : Integer; var State:Integer; var VERSION : Integer; var
Community : Pchar); cdecl; external 'snmp_pp.dll' name 'snmpget';
~~~~~
qkl 2002-01-31
  • 打赏
  • 举报
回复
应该是:
procedure snmpget(var ipaddress : Pchar; var oid : Pchar;var Value : Pchar; var ValueLength : Integer; var State:Integer; var VERSION : Integer; var Community : Pchar); cdecl; external 'snmp_pp.dll' name 'snmpget';
~~~~~
thief21cn 2002-01-31
  • 打赏
  • 举报
回复
我把接口函数改成这样,
procedure snmpget(var ipaddress : Pchar; var oid : Pchar;var Value : Pchar; var ValueLength : Integer; var State:Integer; var VERSION : Integer; var Community : Pchar); stdcall; external 'snmp_pp.dll' name 'snmpget';
然后程序里这样写:
procedure TForm1.Button1Click(Sender: TObject);
var
ipaddress,oid,Value,Community : Pchar;
ValueLength,Version,State:Integer;
begin
ipaddress := '172.24.224.10';
oid := '.1.3.6.1.2.1.1.1.0';
Value := '';
ValueLength := 0;
State := 0;
Version := 1;
Community := 'public';

snmpget(ipaddress,oid,Value,ValueLength,State,Version,Community);
end;

当程序执行玩snmpget这句以后,就出来Access violation错误。所以我觉的函数的调用方式已经没有问题了,只是两边的参数不对应,所以才出来这个错误。可是有不知该如何解决。
VSaber 2002-01-31
  • 打赏
  • 举报
回复
应该改用stdcall调用约定吧!
qkl 2002-01-31
  • 打赏
  • 举报
回复
改用 cdecl 调用约定就行.

5,388

社区成员

发帖
与我相关
我的任务
社区描述
Delphi 开发及应用
社区管理员
  • VCL组件开发及应用社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧