以下是我项目的目录结构:
expt-main
---------
Makefile_main
/ \
subdir-1 subdir-2
-------- --------
Makefile_1 Makefile_2
mod_codeA.f90 mod_code1.f90
mod_codeB.f90 mod_code2.f90
mod_codeC.f90 mod_code3.f90
Makefile_main:
export
SHELL = /bin/sh
F90 = mpxlf95
SRCDIRS = $(subdir-1) $(subdir-2)
all:
@for DIR in ${SRCDIRS} ;
do \
back=`pwd`; \
cd $$DIR ;\
$(MAKE) ; status=$$? ; \
if [ $$status != 0 ] ; then \
echo "Exit status fro make was $$status" ; exit $$status ; \
fi ; \
cd $$back ; \
done
-------------------------------------------------------------------------------
Makefile-1:
%.o: %.f90
$(F90) $(F90FLAGS) -I$(subdir-2) -c $<
mod_codeA.o: mod_codeC.o $(subdir-2)/mod_code2.o
-------------------------------------------------------------------------------
Makefile-2:
PROG = $(exec)
subdir-1_objs = $(subdir-1)/mod_codeA.o mod_codeB.o mod_codeC.o
all: $(PROG)
$(PROG): $(subdir-2_objs) $(subdir-1_objs) -o $@ $(subdir-2_objs) $(subdir-1_objs)
---------------------------------------------------------------------------------
-
我编写了Makefile_main,它首先编译subdir-1中的代码(模块),然后编译subdir-2中的代码(模块),最后生成可执行文件。问题:subdir-1中的模块使用来自subdir-2的模块,并且以类似的方式,subdir-2中的模块使用subdir-1中的模块。我的make失败了,因为正在使用的模块在其他目录中。如何编写一个makefile来处理这个问题,即在编译subdir-1中的模块时,每当遇到来自subdir-2的对象文件的需要时,它应该切换到subdir-2编译必要的模块并返回回到subdir-1进行进一步的行动?
答案 0 :(得分:2)
如果你说的不同子目录中的模块彼此需要,那么这不是一个很好的使用递归Make。
取消Makefile-1
和Makefile-2
,让Makefile_main
完成所有工作。 (我不能具体告诉你如何更改Makefile-main
,因为我不做Fortran,我不理解Makefile-2
,我没有看到subdir-2中模块的依赖性在子目录-1)中。
答案 1 :(得分:1)
如果你想坚持这个目录布局并且仍然保留三个独立的Makefile,那么你可以使用编译器标志来指示FORTRAN编译器将模块文件放入你选择的公共目录中。
例如使用:
$ gfortran --version
GNU Fortran (Ubuntu/Linaro 4.6.3-1ubuntu5) 4.6.3
Copyright (C) 2011 Free Software Foundation, Inc.
您可以使用-I
和-J
标志来指示编译器:
那就是说我认为Beta加入Makefiles的建议很有意义。要了解您应该这样做的一些原因,请阅读this paper。
最后,由于您的项目在此阶段似乎不是很大,我还建议将CMake作为构建系统考虑,因为它可能提供了一种更方便的方法来指定目标之间的依赖关系(如以及许多其他事情。)