Fortran编译的DLL和C编译的DLL应该能够互换导入吗?(x86目标)



前提:我正在编写一个符合行业标准接口/函数签名的插件DLL。这将在我公司内部使用的至少两个不同的软件包中使用,这两个软件包都有这个特定接口的一些示例骨架代码或空壳。一家供应商用C/C++编写了他们的示例,另一家则用Fortran编写。

理想情况下,我只想用一种语言编写和维护这个库代码,而不是复制它(尤其是我刚刚对各种风格的C语言有了一些熟悉,但还没有接触Fortran)。

我已经给我们的两个供应商发了电子邮件,看看他们的求解器在导入这个DLL时是否需要什么特定的东西,但这让我在更基本的层面上感到好奇。如果我用C和Fortran中公开的方法void foo(int bar)编译DLL。。。到了x86机器指令的时候,程序"X"调用该方法的方式有什么不同吗?到目前为止,我已经了解到,如果我要使用C++,我需要extern "C"位来避免"损坏"——还有什么我应该注意的吗?

这很重要。导出的函数必须使用特定的调用约定,在32位代码中有几种不兼容的约定。调用约定规定了函数参数的存储位置、传递顺序以及如何再次删除。以及函数返回值的传递方式。

函数的名称很重要,导出的函数名称通常用额外的字符装饰。这就是extern "C"的全部内容,它抑制了C++编译器用来防止重载函数具有相同导出名称的名称篡改。因此,这个名称是C编译器的链接器可以识别的名称。

如果您与用其他语言编写的代码进行互操作,那么C编译器进行函数调用的方式几乎是标准的。任何现代Fortran编译器都支持声明,使它们与C程序兼容。当然,无论与您合作的软件供应商提供用Fortran编写的附加组件,都已经使用了这种软件。反过来说,只要你提供了C编译器可以使用的函数,Fortran程序员就很有可能调用它

是的,这里已经讨论过很多次了。研究此标签中的答案和问题https://stackoverflow.com/questions/tagged/fortran-iso-c-binding。

在fortran中extern "C"的等价物是bind(C)。使用内部模块iso_c_binding来实现数据类型的等效性。

还要确保使用相同的调用约定。如果不手动指定任何内容,则两者的默认值通常相同。在Linux上,这不是问题。

extern"C"用于C++代码中。因此,如果DLL是用C++编写的,就不能传递任何C++对象(类)。

如果您坚持使用C类型,则需要确保函数以单一方式传递参数,例如使用C的默认_cdecl。不确定Fortran使用了什么。

最新更新