Throwing an error if any procedure interface is not explicitly defined, or in a module in Fortran 90+

fortran, fortran90

Solution

For gfortran there is the compile option `-Wimplicit-interface`:

-Wimplicit-procedure Warn if a procedure is called that has neither an explicit interface nor has been declared as EXTERNAL.

This can be coupled with `-Werror` to treat this as an error.

On compiling this (with gfortran 4.8.2)

  call heffalump(1)
end

one sees

call heffalump(1) 1 Warning: Procedure 'heffalump' called with an implicit interface at (1)

Do note, however, that although this can be a useful test for "silly mistakes" in newly developed modern code, things can be quite correct and still fail this test. See also Vladimir F's comment to this answer.

Of course, a compiler in most circumstances can't tell whether the procedure requires an explicit interface. See this answer for options to allow the compiler to do a little extra work in that regard.

Problem

In the article Mistakes in Fortran 90 Programs That Might Surprise You There is this following section, Danger of calling Fortran 90 style routines ``` program main real, dimension(5) :: x x = 0. ! THIS IS WRONG call incb(x) print *, x end program main subroutine incb(a) ! this is a fortran90 style subroutine real, dimension(:) :: a a = a + 1. end subroutine incb ``` Explanation The subroutine incb uses a Fortran 90 style assumed shape array (containing dimension(:)). Such routines must either be in a module, or have an explicit interface wherever they are used. In this example, neither one was true. One correct way to call such procedures is to use an explicit interface as follows: ``` program main real, dimension(5) :: x ! THIS IS THE RIGHT WAY interface subroutine incb(a) real, dimension(:) :: a end subroutine incb end interface x = 0. call incb(x) print *, x end program main subroutine incb(a) ! this is a fortran90 style subroutine real, dimension(:) :: a a = a + 1. end subroutine incb ``` If the routine is in a module interfaces are generated automatically and do not need to be explicitly written. ``` ! THIS IS ANOTHER RIGHT WAY module inc contains subroutine incb(a) ! this is a fortran90 style subroutine real, dimension(:) :: a a = a + 1. end subroutine incb end module inc program main use inc real, dimension(5) :: x x = 0. call incb(x) print *, x end program main ``` If interfaces are used, the interface MUST match the actual function. So continuing my question, is there an option in `gfortran` or other compilers to prevent compilation if there is a call to a procedure whose interface is not explicity defined (or defined in a module)? If not, shouldn't it be a feature?

Original source