【问题标题】:stdcall required on import function?导入功能需要stdcall吗?
【发布时间】:2014-12-10 18:26:16
【问题描述】:

我很好奇这个:

当我从使用 stdcall 调用约定导出的动态链接库导入函数时,是否必须在 external 之前添加 stdcall Delphi 从版本 7 开始?

即

LIBNAME int __stdcall Foo(void);

作为

function Foo: Integer; stdcall; external 'libname.dll';

或者我可以侥幸逃脱

function Foo: Integer; external 'libname.dll';

默认情况下,IIRC 会使用 stdcall,但我不能 100% 确定这一点,需要您的意见。

编辑:

这个问题与 32 位库有关,Arnaud Bouchez 提出了一个很好的观点,即对于 64 位,调用约定没有考虑在内,因为只有一个。

【问题讨论】:

  • 您可以“摆脱”忽略该函数的调用约定,因为当有一个简单的返回类型且没有参数时,stdcall 和 register 的行为相同。
  • @RobKennedy 该死的例子!你说得对,实际上除了我导入的一个函数之外,所有函数都有 1 个或多个参数,谢谢你的提醒 Rob! (:

标签: delphi delphi-7


【解决方案1】:

如果您省略 stdcall,则将使用默认调用约定 register。所以你必须包含stdcall。

您使用external 的事实不会改变任何事情。默认调用约定是register,即使对于外部导入也是如此。

当然,这只在为 32 位编译时才重要。在 x64 Windows 上,ABI 中指定了一个调用约定。在 x64 Windows 上,代码中指定的所有调用约定都将被忽略,所有函数调用都使用 Windows x64 调用约定。

【讨论】:

  • +1 并接受,谢谢大卫,不确定,这是否适用于所有 delphi 版本?
  • @David 在构建 64 位应用程序时对 Delphi XE2 不是强制性的:在这种情况下只有一个调用约定。添加 stdcall 不会改变任何东西。
  • @ArnaudBouchez 没错!对于 64 位,调用约定被忽略,但在我的情况下,我使用的是 32 位 dll,我会更新问题。
  • @DavidHeffernan:我总是听说默认调用约定称为“fastcall”(它仍然在 C++ Builder 的“选项”对话框和自动生成的头文件中。)不过 Delphi documentation definitely uses 'register'。首选名称是否在过去某个时候发生了变化,还是我只是感到困惑?
  • @DavidM 在 Delphi 中一直被称为寄存器。它也被称为 Borland fastcall,因为它与 MS fastcall 相似但又略有不同。
猜你喜欢
  • 1970-01-01
  • 2017-10-23
  • 2015-05-06
  • 1970-01-01
  • 2017-02-25
  • 1970-01-01
  • 2019-02-02
  • 1970-01-01
相关资源
最近更新 更多