Intel® Fortran Compiler
Build applications that can scale for the future with optimized code designed for Intel® Xeon® and compatible processors.

how to tell make to monitor changes in files accessed via "include"

may_ka
Beginner
645 Views

Hi there,

fortrans module feature can become quite clumsy even when routines are moved to submodules. Parent-child-grandchild-etc definitions and routine interfaces can occupy several thousand lines of code.

For code readability I am thinking about moving type definitions and related interface blocks to files accessed via "include". With a small test example I noticed that "make" is not detecting changes in these files since it only checks the host file (that with the include statement) for changes.

Is there any way of telling make to monitor these files as well such that the host files gets recompiled in case an included files has changed??

Thanks

 

0 Kudos
11 Replies
Steve_Lionel
Honored Contributor III
645 Views

Usually you add the include file as a dependency in the makefile. make doesn't try reading your sources. I don't understand your comment about modules and submodules, though. Submodules help avoid compilation cascades, though you do need to accurately describe them in the makefile.

0 Kudos
mecej4
Honored Contributor III
645 Views

Depending on the contents of an INCLUDEd file, the host file, as you call it, may or may not need recompilation. As Steve pointed out, make does not read and interpret source code. Therefore, you cannot put in an implicit rule in the makefile to cover the include files in your project. 

You are left with adding explicit rules such as

        sub1.o: inc3.inc inc5.inc mod4.mod

and

        mod4.mod: sub4.f mod3.mod

to your makefile. Modifying and maintaining explicit rules in a makefile by hand for a large project can become quite error prone, as you may have already seen.

Utilities such as Wester's makemakehttps://www.fortran.com/makemake.perl , can assist.

0 Kudos
may_ka
Beginner
645 Views

My comment regarding submodules was just an "intro" that even submodules sometimes aren't a sufficient tool for keeping modules "small", at least if the whole inheritance path must sit in one module.

I am aware that make doesn't read the content.

Thanks for the hint to the additional dependency. Works.

Cheers

0 Kudos
may_ka
Beginner
645 Views

Hy mecej4,

I am aiming for this structure:

Submoudle file (submod.f90):

Submodule(test) rout
contains
  Module Procedure Subs1
    write(*,*) "hello"
  end procedure
end Submodule rout

Module file (mod.f90):
 

Module test
  Implicit None
  private
  include "tt_include.f90"
end Module test

included file (tt_include.f90):

  Type, public :: tt
  contains
    procedure, pass :: s1=> subs1
  end type tt
  interface
    Module Subroutine subs1(this)
      class(tt), intent(inout) :: this
    end Subroutine
  end interface

source file for make (Moduls.mk):

SRC += mod.f90\
submod.f90

make file itself:

SRC :=

.SUFFIXES:
.SUFFIXES: .f90

include Moduls.mk

OBJS = $(subst .f90,.o,$(SRC))
%.o:%.f90 *include.f90
	ifort -c $< -o $@

all: $(OBJS)

clean:
	-rm *.mod
	-rm *.o
	-rm *.smod

Because of the final application (+1000 files), I cannot write the rules by hand. As this is just a mickey mouse trial, I don't know whether it will eventually work okish.

0 Kudos
jimdempseyatthecove
Honored Contributor III
645 Views

Maybe mecej4 can answer this better, it appears that if mod.f90 gets edited, that submod.f90 will not be compiled.

Note, submod.f90 contains neither INCLUDE mod.f90, nor #include mod.f90

I do not know if the makemake pearl script addresses submodules properly.

Jim Dempsey

0 Kudos
Steve_Lionel
Honored Contributor III
645 Views

You're going to have to write the rules for each source file. ifort has a -gen-dep option that may be of help here. For submodules, the submodule sources depend on the parent module and the regular sources depend on the parent module, not the submodule(s). That way if you modify the implementation (in the submodule), neither the module nor sources that use the module have to be recompiled. Of course, if you modify the interface (which must be done in the module), then all users of the module get recompiled.

0 Kudos
FortranFan
Honored Contributor II
645 Views

Many coders will find INCLUDE files only make sense when the INCLUDEd code snippet applies to more than one program component, a classic example being the use of a same COMMON block in different subprograms and perhaps the main program also.  OP does not appear to have such a need, at least from what is shown in this thread - it's difficult to fathom how the "tt_include.f90" statement will need to be present anywhere besides the module named Test.  All the INCLUDE statement statement appears to be achieving is shorten the amount of text in the module; such an aim is better achieved by other means - see below - note though nothing is perfect.

So what OP may want to consider is

  1. improved code design based on better OO and other programming paradigms - this is based on the comments such as "Parent-child-grandchild-etc definitions and routine interfaces can occupy several thousand lines of code." and "My comment regarding submodules was just an "intro" that even submodules sometimes aren't a sufficient tool for keeping modules "small"".  This is so that "the whole inheritance path" need not "sit in one module"
  2. Better code editor(s) that continue to advance further at a rapid frequency (e.g., Microsoft Visual Studio editor on Windows for C# and C++ languages) their existing quality code folding capabilities with good shortcuts and macros, etc.  Large files can then be handled more efficiently.  https://en.wikipedia.org/wiki/Code_folding

 

0 Kudos
mecej4
Honored Contributor III
645 Views

Apart from all the comments made so far, if include files are used I suggest that they be given a suffix other than .f or .f90. Doing so will avoid causing make and other utilities attempt to compile or parse those include files as independent Fortran source files, which we know in advance will fail.

Utilities such as makemake.pl were created in the days before submodules were added to Fortran. I do not know if any of them have been updated to know about submodules.

0 Kudos
may_ka
Beginner
645 Views

FortranFan wrote:

All the INCLUDE statement statement appears to be achieving is shorten the amount of text in the module ......................

Spot on.

FortranFan wrote:

improved code design based on better OO and other programming paradigms

I think this forum has seen discussion about the short-commings of oop in fortran several times, and I think the general consensus was that they are there. Also, there are applications, and I think I have once elaborated on one example, where "one type one module" approaches simply do not work which will eventually lead to very large modules. However, without knowing application specifities you are free to believe that everything can be solved via better design ....................... even in oo fortran.

FortranFan wrote:

Better code editor(s) that continue to advance further at a rapid frequency (e.g., Microsoft Visual Studio editor on Windows for C# and C++ languages) their existing quality code folding capabilities with good shortcuts and macros, etc.  Large files can then be handled more efficiently.

You may have noticed that this is the Linux/Mac forum. There a plenty of ides in linux for c++ and c (e.g. eclipse), but to my knowledge fortran supporting ides are very limited to absent in linux (maybe photran in eclipse) .................. most likely due to the limited use of this language in large projects. Code folding in emacs might be an option, but one would have to fix the plugin first to cope with different programming styles which lead to the same code.

0 Kudos
Steve_Lionel
Honored Contributor III
645 Views

Code:Blocks is also available on Linux and I have read of people using it for Fortran.

0 Kudos
may_ka
Beginner
645 Views

Steve Lionel (Ret.) wrote:

Code:Blocks is also available on Linux and I have read of people using it for Fortran.

Thanks Steve. I'll give that a try.

Cheers

0 Kudos
Reply