fortran - Autotools 和 Fortran 模块
问题描述
我在编写 Makefile.am 时遇到问题,它将使 autotools 以正确的顺序编译文件。
我的最小示例是一些test.f90
使用模块中的例程的示例mod.f90
。我手动执行以下操作。
gfortran -c mod.f90
gfortran -c test.f90
gfortran -o test test.o mod.o
这工作正常。现在,我已经读到 autotools 不处理 Fortran 模块依赖项,根据这篇文章(automake with fortran: order of file),应该手动将依赖项放入 Makefile.am 中。
我的看起来像下面这样。
AUTOMAKE_OPTIONS = foreign
bin_PROGRAMS = test
test_SOURCES = mod.f90 test.f90
test: test.f90 mod.o
mod.o: mod.f90
虽然每次运行时都会生成模块的 .mod 文件./configure && make
,但它显然不是在所有其他文件之前生成的,即我仍然收到错误消息Fatal Error: Cannot open module file ‘mod.mod’ for reading at (1): No such file or directory
。
连续运行./configure && make
两次可以编译程序,但这当然不是一个真正令人满意的解决方案。有没有一些标准的方法来处理这个?我可以以某种方式强制mod.o
之前编译test.o
吗?
解决方案
鉴于第一行,这两行中的第二行是多余的:
test_SOURCES = mod.f90 test.f90 test: test.f90 mod.o
这个是不需要的,因为 Automake (和 GNU make
)已经知道它传达的信息:
mod.o: mod.f90
这实际上让你只剩下这个:
AUTOMAKE_OPTIONS = foreign
bin_PROGRAMS = test
test_SOURCES = mod.f90 test.f90
就目前而言,这没问题,但它没有表达任何与mod.mod
文件相关的依赖信息,因此构建可能会失败。要解决这个问题,您需要添加一个或多个规则来表达额外的依赖关系以及如何满足它们。
真正的依赖是test.o
依赖于mod.mod
,你可以编写一个仅依赖的规则来表达:
# INSUFFICIENT
test.o: mod.mod
但这给你留下了一个问题:make
不知道这mod.mod
是编译的输出mod.f90
。实际上,通过一次配方运行创建多个目标的情况很难描述make
(和 Automake)。Automake 手册用其中一个较长的部分来讨论这个问题。最强大的构建系统将使用该部分描述的方法来表达如何构建mod.o
和mod.mod
,但这将使您的大小增加三倍Makefile.am
,并且您需要为每个 Fortran 模块提供类似的额外代码。
您可以通过告诉 Automake 这test.o
取决于mod.o
:
# Better
test.o: mod.o
这将产生从头开始的成功构建,并且在大多数正常的开发环境下,但它确实表达了不正确的依赖关系。因此,它很容易通过例如构建项目,然后删除mod.mod
(留mod.o
在原地)和更新来构建破坏test.f90
。在随后的构建中,make
将看到它mod.o
是最新的,因此它不会重新生成缺失的mod.mod
. 一个干净的构建可以解决这个问题,作为开发人员,为了简单起见,我可能准备接受这种情况Makefile.am
。
说到干净的构建,您还应该添加mod.mod
到make clean
应该删除的文件列表中:
CLEANFILES = mod.mod
总的来说,那么,最终的结果是:
AUTOMAKE_OPTIONS = foreign
bin_PROGRAMS = test
test_SOURCES = mod.f90 test.f90
# A fib -- the real dependency is test.o: mod.mod
test.o: mod.o
CLEANFILES = mod.mod
推荐阅读
- angular - Angular 10 - 在订阅中调度 NGXS 动作导致无限循环
- r - 如何使用 Get_Labels 在 R 中正确标记图表上的条形?
- typescript - Using private properties with Module Augmentation in Typescript
- ios - 在 iOS (Flutter) 上调用 Agora RTC SDK 时如何获取麦克风输入流?
- docker - 从 pod 访问 CIFS 文件
- passport.js - 如何解决护照 saml 策略的问题
- express - 在 Nodejs 中使用 Multer 上传图像时出错
- ios - 录音点击开始
- git - 在 Visual Studio 2019 中添加 git 中的所有文件
- use-ref - useRef、useLayoutEffect、Element.scrollTo 每次都不工作