带有 MinGW 的 Fortran 模块与 MSVC 一起使用会导致无法解析的符号“__exmod_MOD_value”
Fortran module with MinGW used with MSVC causes unresolved symbol "__exmod_MOD_value"
我想在 Windows 上使用 Fortran 库,它包含许多模块。因此我需要用 MinGW 编译这个库。为了使用 MSVC 编译器,我需要使用这两个链接中提到的外部链接来编译库:
https://groups.google.com/forum/#!topic/comp.lang.fortran/s8CiQnNmO14
https://blog.kitware.com/fortran-for-cc-developers-made-easier-with-cmake/
只要我不使用模块,这似乎就可以工作。
这是一个最小的例子:
Fortran 代码:
!-------------------------------------------------------------------------!
! !
! MODULE EXMOD !
! !
!-------------------------------------------------------------------------!
MODULE EXMOD
INTEGER :: VALUE
CONTAINS
!-------------------------------------------------------------------------!
! !
! INITOPTMOD !
! !
!-------------------------------------------------------------------------!
SUBROUTINE INITOPTMOD(VALUE_IN)
IMPLICIT NONE
INTEGER, INTENT(IN) :: VALUE_IN
VALUE = VALUE_IN
WRITE(*,*) 'The Value is: ', VALUE
RETURN
END SUBROUTINE INITOPTMOD
END MODULE EXMOD
!-------------------------------------------------------------------------!
!-------------------------------------------------------------------------!
! !
! EXTERN CALLER !
! !
!-------------------------------------------------------------------------!
SUBROUTINE FORTCALL( VALUE_ )
USE EXMOD
INTEGER, INTENT(IN) :: VALUE_
CALL INITOPTMOD(VALUE_)
END SUBROUTINE FORTCALL
!-------------------------------------------------------------------------!
我编译了这个:
gfortran forfunc.f90 -c
gfortran -o libfortfunc.dll forfunc.o -shared -Wl,--output-def,libfortfunc.def
lib /MACHINE:x64 /def:libfortfunc.def /out:libfortfunc.lib
编译库后,我尝试用 MSVC 编译 main.cpp:
main.cpp:
extern "C" {
void fortcall_( int *value );
}
int main()
{
int value = 12;
fortcall_( &value );
return 0;
}
我尝试用以下方法编译:
cl main.cpp libfortfunc.exp libfortfunc.lib
如果没有模块,这工作正常,但由于 fortran 代码包含一个,出现以下错误:
/out:main.exe
main.obj
libfortfunc.exp
libfortfunc.lib
libfortfunc.exp : error LNK2001: Nicht aufgelöstes externes Symbol "__exmod_MOD_value".
main.exe : fatal error LNK1120: 1 nicht aufgelöste Externe
我可以做些什么来解决这个问题吗?
至少我找到了避免这个错误的方法。
我查看了文件 libfortfunc.def:
EXPORTS
__exmod_MOD_initoptmod @1
__exmod_MOD_value @2 DATA
fortcall_ @3
因为我不想使用我的 C++ 代码中的模块,所以我只是删除了模块中的所有导出。之后我 运行 命令:
lib /MACHINE:x64 /def:libfortfunc.def /out:libfortfunc.lib
cl main.cpp libfortfunc.exp libfortfunc.lib
工作正常,main.exe 文件 returns 正确的值。
由于这感觉不是正确的方法,因此剩下的问题是:
如何告诉 gfortran 它不能导出模块?
为什么导出模块会出现问题?
我想在 Windows 上使用 Fortran 库,它包含许多模块。因此我需要用 MinGW 编译这个库。为了使用 MSVC 编译器,我需要使用这两个链接中提到的外部链接来编译库:
https://groups.google.com/forum/#!topic/comp.lang.fortran/s8CiQnNmO14 https://blog.kitware.com/fortran-for-cc-developers-made-easier-with-cmake/
只要我不使用模块,这似乎就可以工作。
这是一个最小的例子:
Fortran 代码:
!-------------------------------------------------------------------------!
! !
! MODULE EXMOD !
! !
!-------------------------------------------------------------------------!
MODULE EXMOD
INTEGER :: VALUE
CONTAINS
!-------------------------------------------------------------------------!
! !
! INITOPTMOD !
! !
!-------------------------------------------------------------------------!
SUBROUTINE INITOPTMOD(VALUE_IN)
IMPLICIT NONE
INTEGER, INTENT(IN) :: VALUE_IN
VALUE = VALUE_IN
WRITE(*,*) 'The Value is: ', VALUE
RETURN
END SUBROUTINE INITOPTMOD
END MODULE EXMOD
!-------------------------------------------------------------------------!
!-------------------------------------------------------------------------!
! !
! EXTERN CALLER !
! !
!-------------------------------------------------------------------------!
SUBROUTINE FORTCALL( VALUE_ )
USE EXMOD
INTEGER, INTENT(IN) :: VALUE_
CALL INITOPTMOD(VALUE_)
END SUBROUTINE FORTCALL
!-------------------------------------------------------------------------!
我编译了这个:
gfortran forfunc.f90 -c
gfortran -o libfortfunc.dll forfunc.o -shared -Wl,--output-def,libfortfunc.def
lib /MACHINE:x64 /def:libfortfunc.def /out:libfortfunc.lib
编译库后,我尝试用 MSVC 编译 main.cpp:
main.cpp:
extern "C" {
void fortcall_( int *value );
}
int main()
{
int value = 12;
fortcall_( &value );
return 0;
}
我尝试用以下方法编译:
cl main.cpp libfortfunc.exp libfortfunc.lib
如果没有模块,这工作正常,但由于 fortran 代码包含一个,出现以下错误:
/out:main.exe
main.obj
libfortfunc.exp
libfortfunc.lib
libfortfunc.exp : error LNK2001: Nicht aufgelöstes externes Symbol "__exmod_MOD_value".
main.exe : fatal error LNK1120: 1 nicht aufgelöste Externe
我可以做些什么来解决这个问题吗?
至少我找到了避免这个错误的方法。 我查看了文件 libfortfunc.def:
EXPORTS
__exmod_MOD_initoptmod @1
__exmod_MOD_value @2 DATA
fortcall_ @3
因为我不想使用我的 C++ 代码中的模块,所以我只是删除了模块中的所有导出。之后我 运行 命令:
lib /MACHINE:x64 /def:libfortfunc.def /out:libfortfunc.lib
cl main.cpp libfortfunc.exp libfortfunc.lib
工作正常,main.exe 文件 returns 正确的值。 由于这感觉不是正确的方法,因此剩下的问题是:
如何告诉 gfortran 它不能导出模块?
为什么导出模块会出现问题?