MPI_Init_thread function was called before MPI_Init was invoked - fortran

I need an MPI_Init_Thread call example in fortran.
I tried it without MPI_Init before it and got the message:"MPI_Init_thread function was called before MPI_Init was invoked".
I called after MPI_init and got the message "Calling MPI_Init or MPI_Init_Thread twpce is erreneous." altough I had each called once.
I am confused.
Also are there three or 4 arguments? and what are they? I believe it is three and the second one I want is MPI_THREAD_MULTIPLE but program aborts.
It would be best if someone uses it with fortran could post an example call please.
For completeness I am posting a simple code I am tring to run in hybrid (MPI + OPENMP) mode.
My purpose is to run this job on two nodes , each with 32 threads by making use of openmp within each node.
program hello
Use mpi
integer ierr,np,pid,inull1,inul2,hug
call MPI_Init(ierr)
inull2=3
! call MPI_Init_thread(inull1,inull2,ierr)
call MPI_Comm_rank(MPI_COMM_WORLD, pid,ierr)
call MPI_Comm_size(MPI_COMM_WORLD, np, ierr)
write(6,*) 'inull2,MPI_THREAD_MULTIPLE',MPI_THREAD_MULTIPLE
hug=huge(inull1)
!$OMP PARALLEL SHARED(inull1,inull2,hug,MPI_THREAD_MULTIPLE,np) &
!$OMP PRIVATE(pid)
!$OMP DO SCEDULE (STATIC)
do i=1,hug
write(6,*) 'program hello_world i,np,pid,inull2,mtm',i,np,pid,inull2,MPI_THREAD_MULTIPLE
enddo
!$OMP END DO
!$OMP END PARALLEL
call MPI_Finalize(ierr)
end program hello
I compile it with
mpif90 -o hello_world_openmp.exe hello_world_openmp.f90
and run it with the following command (for now)
mpirun -hostfile hostfile -pernode -bind-to none hello_world_openmp.exe
Changing the code as
integer ierr,np,pid,inull1,inul2,hug
! call MPI_Init(ierr)
call MPI_Init_thread(MPI_THREAD_FUNNELLED,inull2,ierr)
also gives the following error:
*** The MPI_Init_thread() function was called before MPI_INIT was invoked.
*** This is disallowed by the MPI standard.
*** Your MPI job will now abort.

The error message you quite is strange. But it has been reported before (https://www.mail-archive.com/devel#lists.open-mpi.org/msg19978.html https://github.com/TRIQS/cthyb/issues/122)
It points to some incompatibility somewhere. In your case it points to an incorrect call to MPI_Init_thread. The main point is:
Always use IMPLICIT NONE!
This cannot be over-stressed. Even in a very short code you must use it. You declared inul2 instead of inull2 and you used MPI_THREAD_FUNNELLED instead of MPI_THREAD_FUNNELED. After correcting that, your codes runs correctly for me.
One calls MPI_Init_thread instead of MPI_Init, not after.
You call it like
call MPI_Init_thread(required, provided, ie)
where all arguments are integers, required is an input argument saying which threading level you need and provided is an output argument and says which threading level you got.
Be aware that for many MPI implementations MPI_THREAD_MULTIPLE is either not supported at all or is very slow. I suggest designing your programs without the need for MPI_THREAD_MULTIPLE.
The usage can be something like
integer :: ie
integer :: required, provided
required = MPI_THREAD_SERIALIZED
call MPI_Init_thread(required, provided, ie)
if (ie/=0) ... error
if (provided<required) then
... different error

Related

How can I change MPI error handler before MPI_init?

I have a Fortran code which is predominantly used for running large MPI calculations, but occasionally I want to run it on a machine which does not have MPI available for quick data processing tasks.
I have a logical variable which determines whether or not the program is being run in MPI mode or not, and when it is false the code will not call any MPI subroutines. The way I determine whether or not to run in MPI mode at the moment is by testing to see if a dummy file "NO_MPI" exists which I dislike due to its inelegance and the fact that I usually forget that I need to create this file when running in a non-MPI environment.
When the code is run in a non-MPI environment the MPI_init subroutine will fail and cause the program to crash. So what I would like to do is call it with the optional error output:
call MPI_init(ierr)
and then if an error is returned continue with the node in non-MPI mode.
The issue is that the default MPI error handler will abort the program without returning an error. For any other MPI subroutine the solution would be:
call MPI_Comm_set_errhandler(MPI_COMM_WORLD, MPI_ERRORS_RETURN)
to tell MPI not to abort and return the error code. However I cannot call this subroutine before MPI_init without getting the error
Attempting to use an MPI routine before initializing MPICH.
Is there any way to change the default error handler before calling MPI_init, perhaps specifying it with a compiler flag? I am using the IFORT compiler with MPICH.
I feel that there must be some way of testing the error code from MPI_init, otherwise what is the point of allowing MPI_init to accept the optional error return as an argument when the default behaviour is to abort without returning errors?

"No specific subroutine for the generic" error with MPI_SEND and MPI_RECV

I have installed OpenMPI and it works with a simple parallelized hello world program but it doesn't work when MPI_SEND() or MPI_RECV() is called. I am using gfortran 5.1 and OpenMPI 3.0.1rc4.
The error is
Error: There is no specific subroutine for the generic ‘mpi_recv’ at
(1)
It seems the compiler does not recognise basic subroutines such as MPI_RECV().
This is the test program that causes the error:
program main
use mpi
implicit none
integer :: ierr,np,myid,i,rbuf
integer, dimension(:,:), allocatable :: ista
CALL MPI_INIT(ierr)
CALL MPI_COMM_RANK(MPI_COMM_WORLD,myid,ierr)
CALL MPI_COMM_SIZE(MPI_COMM_WORLD,np,ierr)
allocate(ista(MPI_STATUS_SIZE,np))
if (myid==0) then
do i = 1, np-1
CALL MPI_RECV(rbuf,1,MPI_INTEGER4,i,i,MPI_COMM_WORLD,ista,ierr)
write(*,"('process ',i2,' sent:',i2)") i,rbuf
end do
else
i=10*myid
CALL MPI_SEND(i,1,MPI_INTEGER4,0,myid,MPI_COMM_WORLD,ierr)
end if
CALL MPI_FINALIZE(ierr)
end program main
The status argument is an INTEGER(MPI_STATUS_SIZE), and you pass ista which is declared as a 2D array, that is why the compiler is complaining.
Another option, perhaps closer to the original intent of your code, is to pass the appropriate subarray ista(:,i) of the array of all statuses
CALL MPI_RECV(rbuf,1,MPI_INTEGER4,i,i,MPI_COMM_WORLD,ista(:,i),ierr)
Or just use MPI_STATUS_IGNORE, I think it is the best here.

how to stop a fortran program abnormally

When an exception occurs I would like to terminate abnormally my program. Right now, when an exception happens a write statement with an explanatory sentence is called, and then a stop statement is called.
I am debugging the program with idb (intel debugger), when the exception happens I get the write statement, but idb treats the program as terminated normally. I would like that when the exception happens the program is terminated abnormally and so that I can look to the memory with backtrace in the place where the exception happened.
I have tried changing stop in stop 1, so that a non zero value is returned, but this doesn't work
EDIT:
I have implemented the solution in one of the answer:
interface
subroutine abort() bind(C, name="abort")
end subroutine
end interface
print *,1
call abort()
print *,2
end
with this solution I still do not get any backtrace when I am using ifort 13.0.1, but this works perfectly with ifort 14.0.2.
I have resorted to use idb instead of gdb, because often the latter cannot read the values of allocatable arrays in fortran.
There are non-standard extensions for this. Gfortran uses backtrace() to print a backtrace anywhere, for the Intel's equivalent see the wander95's answer https://stackoverflow.com/a/38905855/721644.
In ifort and gfortran you can call the abort() subroutine and you will get backtrace if you used the -traceback (Intel) or -g -fbacktrace (gfortran) compiler option.
You could also call the C abort() directly using the C interoperability. (also non-standard and may not work in all circumstances):
interface
subroutine abort() bind(C, name="abort")
end subroutine
end interface
print *,1
call abort()
print *,2
end
With Fortran 2008 the ERROR STOP statement has been introduced. It's mainly used for Coarray Fortran programs to initiate error termination on all images.
Found this old question by accident. If you want abnormal termination with the intel compiler, you can use the routine tracebackqq. The call sequence can be:
call TRACEBACKQQ(string=string,user_exit_code=user_exit_code)
To quote the manual:
Provides traceback information. Uses the Intel® Fortran run-time library traceback facility to generate a stack trace showing the program call stack as it appeared at the time of the call to TRACEBACKQQ( )
I've never used idb, I've only used gdb, so this might not work. I just put a read statement in at the error point, so that the program stops and waits for input. Then I can CTRL-C it, which causes gdb to pause execution, from which I can get a backtrace, move up and down the stack, look at variables, etc.

Where should I put MPI_INIT in a Fortran module?

I have a problem, and I don't know what it is. I have a test program with MPI_INIT and MPI_FINALIZE in its body. I have a module that contains 5 subroutines: 3 subroutines are dependent, and independent from 2 other subroutines. I want to put the MPI code in the test program into this module. I put MPI_INIT in the module where the variables are declared and before the subroutine. I obtain a series of errors with the same error message:
This statement must not appear in the specification part of a module
How does "MPI_INIT and MPI_FINALIZE should be called only once" affect Fortran program, modules, and subroutines? Where should I put MPI functions and variables if there are multiple, independent programs, each calling this module's subroutines multiple number of times?
You need to call MPI subroutine in subroutine part of the module.
Generally i define an init_mpi subroutine that do the call to MPI_INIT and eventually call to MPI_COMM_RANK and MPI_COMM_SIZE. You could also use MPI_INITIALIZED in this init_mpi subroutine to avoid multiple initialization.

Updated: Should I put MPI in a module or a module's subroutine?

Updated: I have a problem, and I don't know what it is. I have a test program with MPI_INIT and MPI_FINALIZE in its body. I have a module that contains 5 subroutines: 3 subroutines are dependent, and independent from 2 other subroutines. I want to put the MPI code in the test program into this module. I put MPI_INIT in the module where the variables are declared and before the subroutine. I obtain a series of errors with the same error message:
This statement must not appear in the specification part of a module
How does "MPI_INIT and MPI_FINALIZE should be called only once" affect Fortran program, modules, and subroutines? Where should I put MPI functions and variables if there are multiple, independent programs, each calling this module's subroutines multiple number of times?
~~~~~~~~~
I have a module that contains a series of subroutines, which contain do loops that I wish to parallelize. The subroutines are public that other programs use. Should I define MPI outside the subroutines:
module ...
call MPI_INIT
subroutine 1
... (MPI code)
subroutine 2
subroutine 3
MPI_GATHERV
call MPI_FINALIZE
module
or inside each subroutine?
module ...
subroutine 1
call MPI_INIT
... (MPI code)
MPI_GATHERV
call MPI_FINALIZE
subroutine 2
call MPI_INIT
... (MPI code)
MPI_GATHERV
call MPI_FINALIZE
subroutine 3
call MPI_INIT
... (MPI code)
MPI_GATHERV
call MPI_FINALIZE
module
I see the advantage of following the coarse grain principle for solution 1. If a program calls subroutine 1, will it also execute MPI codes outside the subroutine?
You should initialize and finalize MPI exactly once in your program. After calling MPI_Finalize you are not allowed to do further MPI actions. The standard says:
Once MPI_FINALIZE returns, no MPI routine (not even MPI_INIT) may be called, except for MPI_GET_VERSION, MPI_GET_LIBRARY_VERSION, MPI_INITIALIZED, MPI_FINALIZED, and any function with the prefix MPI_T_ (within the constraints for functions with this prefix listed in Section 14.3.4).
(MPI3, p361, l25) MPI3 PDF
Reply to the update:
You are not allowed to put executable statements into the declaration part of your code. The point, that there should be just one call to MPI_Init and MPI_Finalize in your execution means exactly that. Your application could read something like that:
program mini
use mpi
implicit none
integer :: iError
call mpi_init(iError)
call do_some_stuff()
call mpi_finalize(iError)
end program mini
If you have various initialization stuff you want to do in the beginning of the program, you can of course combine it in module subroutine and call mpi_init in there. If you use a test program for your module, use mpi_init and mpi_finalize there.
An example for the call of mpi_init and mpi_finalize in some subroutines can be found for example in the env_module of the treelm library which we use to set up very general stuff.
Where should I put MPI functions and variables if there are multiple, independent programs, each calling this module's subroutines multiple number of times?
Could you rephrase that? I don't get it. MPI functions and variables are supposed to be in the mpi module, if you have multiple independent programs calling them, they all have to "use" the mpi module. Independent programs are also fine to have the MPI_Init and MPI_Finalize each in itself. Maybe you could post a short code example, what you want to achieve and what your problem is.