Alexander Cska
Alexander Cska

Reputation: 818

Call MPI_RECV after certain signal was obtained from the master

I am using a code which runs a loop and accumulates some mean value. At a particular moment in time I would like to send this mean value and receive it on all slaves. This should be done only once. At first glance I taught that this should be fairly easy to do. So I used an internal variable (the loop count) to do the following

! on the master
if( i == 55 ) 
do mt = 1, tasks
call MPI_SEND(A,size,MPI_DOUBLE_PRECISION,mt,5,MPI_COMM_WORLD,status,ierror)
end do

! on the slaves
if(i==55) then
call MPI_RECV(a,size,MPI_DOUBLE_PRECISION,0,5, MPI_COMM_WORLD,status,ierror)
endif

Running this caused segmentation fault, at the line where the MPI_RECV is called. In general this would work if I was communicating continuously, i.e. sending and receiving data during the entire loop.

The most natural thing would be to assume that the variable I am using for triggering the communication is not synchronized between the master and the slaves. Therefore, I decided to send an integer value to the slaves, and use it as a singnal for calling MPI_RECV. Unfortunately this caused a communication deadlock. I did something like:

! on the master
sig = 0
if ( i == 55) then 
sig = 1
call MPI_SEND(sig,1,MPI_INTEGER,mt,10,MPI_COMM_WORLD,status,ierror)
endif

if(i==55) then
do mt =1,tasks
call MPI_SEND(A,size,MPI_DOUBLE_PRECISION,mt,5,MPI_COMM_WORLD,status,ierror)
end do
endif 

! on the slaves
call MPI_RECV(sig,1,MPI_INTEGER,mt,10,MPI_COM_WORLD,status,ierror)
if ( sig == 1) Call MPI_RECV(a,size,MPI_DOUBLE_PRECISION,0,5,   MPI_COMM_WORLD,status,ierror)

I am not able to figure out what is going on wrong myself.

I would appreciate any ideas.

Upvotes: 0

Views: 135

Answers (1)

Wesley Bland
Wesley Bland

Reputation: 9072

If you're trying to send data from one MPI process to all other MPI processes, using MPI_SEND and MPI_RECV is horribly inefficient. Take a look at the function MPI_BCAST. The prototype for this function looks like this:

MPI_BCAST(BUFFER, COUNT, DATATYPE, ROOT, COMM, IERROR)
<type>    BUFFER(*)
INTEGER    COUNT, DATATYPE, ROOT, COMM, IERROR

At the root process (the master process in your case), you pass the value that you want to send to everyone else in as the BUFFER. I assume you're only intending to send one value as the mean so your COUNT will be 1. The DATATYPE is whatever you want (MPI_DOUBLE_PRECISION), the ROOT is your master rank (I assume 0) and your COMM is MPI_COMM_WORLD.

Something important to remember with MPI_BCAST (and all other functions like it called "collective functions") is that every process must make this call together. Until everyone has entered the call, no one will be able to leave it. So make sure that everyone is on the same iteration.

Upvotes: 1

Related Questions