【问题标题】:Compaq Visual Fortran 6.6, Dynamic-Link Library (DLL) and ModuleCompaq Visual Fortran 6.6、动态链接库 (DLL) 和模块
【发布时间】:2019-05-29 15:40:27
【问题描述】:

我需要为使用 Compaq Visual Fortran 6.6 的 Fortran 应用程序创建和使用动态链接库 (DLL)。以下代码可以正常工作:

PROGRAM AMAIN1
IMPLICIT NONE
REAL(8):: A,B,S
A = 1D0
B = 2D0
CALL SUBRO1(A,B,S)
PRINT*, 'S = ', S
END PROGRAM AMAIN1

SUBROUTINE SUBRO1(A,B,S)
!DEC$ ATTRIBUTES DLLEXPORT :: SUBRO1
IMPLICIT NONE
REAL(8):: A,B,S
S = A + B
RETURN
END SUBROUTINE SUBRO1

结果正确: S = 3.00000000000000 按任意键继续

但是,如果我使用该模块实现相同的算法,我会得到不一致的结果(即零):

PROGRAM AMAIN2
USE MODUL2
A = 1D0
B = 2D0
CALL SUBRO2
PRINT*, 'S = ', S
END PROGRAM AMAIN2

MODULE MODUL2
IMPLICIT NONE
REAL(8):: A,B,S
END MODULE MODUL2

SUBROUTINE SUBRO2
!DEC$ ATTRIBUTES DLLEXPORT :: SUBRO2
USE MODUL2
S = A + B
RETURN
END SUBROUTINE SUBRO2

结果不正确: S = 0.000000000000000E+000 按任意键继续

如上所示,DLL 在两种情况下都只包含子程序(分别为 SUBRO1 和 SUBRO2)。我已经从可视化开发环境构建了 DLL 和 LIB 文件。第二种情况(使用模块)代表我的大型源代码的结构,所以我需要解决这个问题。任何建议将不胜感激。

顺便说一句,不使用 DLL 的相同算法效果很好并且给出了正确的结果:

PROGRAM AMAIN3
USE MODUL3
A = 1D0
B = 2D0
CALL SUBRO3
PRINT*, 'S = ', S
END PROGRAM AMAIN3

MODULE MODUL3
IMPLICIT NONE
REAL(8):: A,B,S
END MODULE MODUL3

SUBROUTINE SUBRO3
USE MODUL3
S = A + B
RETURN
END SUBROUTINE SUBRO3

结果正确: S = 3.00000000000000 按任意键继续

【问题讨论】:

    标签: dll module fortran fortran90


    【解决方案1】:

    你需要添加:

    !DEC$ ATTRIBUTES DLLEXPORT :: A,B,S

    到模块,以便主程序可以从DLL中看到模块变量。否则 A、B 和 S 是局部变量。

    编辑:2019 年 1 月 16 日

    我能够登录到 Bakhbergen 的 PC 并最终找出问题所在。

    在 CVF 6.6C(和后来的 Intel 编译器)中,当您使用具有 DLLEXPORT 指令的模块时,它会变成 DLLIMPORT,因此我的建议在上面。但并不总是这样,他拥有的版本没有这种行为。在该更改之前(我的记忆说我游说),您必须提供一个单独编译的 .mod,其中源具有 DLLIMPORT 而不是 DLLEXPORT。当我这样做时,该程序起作用了。我不记得确切的更新是哪个更新了。

    所以他需要做的是拥有两个版本的MODUL2.f90,一个带有DLLEXPORT,一个带有DLLIMPORT。 DLLEXPORT 版本被内置到 DLL 中。 DLLIMPORT 版本只会被编译 (/c),并且在链接主程序时只使用 .mod,而不是 ,obj。凌乱,我知道,这就是我们改变它的原因。

    【讨论】:

    • 非常感谢您的建议,Lionel 博士,但它不起作用。我希望我理解你并正确实施它。你在 CVF 6.6 上运行过这个吗?
    • 不,但我确实在 Intel Fortran 19.0.1 上运行过它。 CVF 6.6 已经超过 15 年了,我已经没有副本了。不过,我原以为它会起作用,因为当我还是一名 CVF 开发人员时,这是我尝试过多次的事情。您需要在之后添加该行:REAL(8):: A,B,S 然后重建 DLL 和主程序。附言我不是真正的医生,我只在网络上玩过。
    • 我希望我所做的一切都是正确的,但我仍然是零。 :-) 感谢您抽出宝贵时间帮助我。我看到你在帮助很多人,所以对我来说,你不仅仅是一名医生。以防万一,如果您有机会在 CVF 中运行此代码,请告诉我。
    • 我无法再访问 CVF。我建议将您的问题发布到software.intel.com/en-us/forums/… - 我认为那里仍有一些 CVF 用户。
    • 查看我修改后的答案。
    猜你喜欢
    • 1970-01-01
    • 2013-04-12
    • 2014-07-28
    • 2018-11-05
    • 1970-01-01
    • 2011-08-31
    • 2016-05-20
    • 2013-07-07
    • 1970-01-01
    相关资源
    最近更新 更多