Profile MPI (PMPI) and Fortran

Viewed 270

I am writing sample code for profiling MPI code with PMPI (Profile MPI interface). While an example in C works well, a Fortran similar simple code is not working.

Here is my C code:

#include "mpi.h"
#include <stdio.h>


int main (int argc, char *argv[]) {
   
   int size;
   int rank;
   char b[100];
   MPI_Status st;
   
   
   MPI_Init (&argc, &argv);
   
   MPI_Pcontrol(2);
   
   MPI_Comm_size(MPI_COMM_WORLD, &size);
   MPI_Comm_rank(MPI_COMM_WORLD, &rank);
   
   if (rank == 0) {
      
      MPI_Send(b, 100, MPI_CHAR, 1, 99, MPI_COMM_WORLD);
      
   } else {
      
      MPI_Recv(b, 100, MPI_CHAR, 0, 99, MPI_COMM_WORLD, &st);
      
   }
   
   MPI_Finalize();
   
   return 0;
}

And the profiling code capturing calls to MPI_Xxx functions:

#include "mpi.h"
#include <stdio.h>


static int totalBytes = 0;

int MPI_Init (int *argc, char ***argv) {

   int err = PMPI_Init(argc, argv);

   return err;
}


int MPI_Send(const void* buffer, int count, MPI_Datatype datatype,
             int dest, int tag, MPI_Comm comm) {

   int size;

   printf("Sending ...\n");
   
   int result = PMPI_Send(buffer, count, datatype, dest, tag, comm);

   MPI_Type_size(datatype, &size);
   totalBytes += count*size;
   
   return result;
}

int MPI_Finalize() {
   
   int rank;
   
   MPI_Comm_rank(MPI_COMM_WORLD, &rank);
   
   if (rank == 0) {
   
      printf("Total bytes: %d\n", totalBytes);
      
   }
   
   return PMPI_Finalize();
}

Compiling commands are:

$ mpicc -c example.c 
$ mpicc -c prof.c 
$ mpicc -o example prof.o example.o 
$ mpiexec --hostfile hfile --oversubscribe -np 2 ./example

The output, as expected, include the sentences:

Sending ...
Total bytes: 100

While in fortran, the code is:

PROGRAM send_recv_mpi
include 'mpif.h'

integer process_Rank, size_Of_Cluster, ierror, message_Item

call MPI_INIT(ierror)
call MPI_COMM_SIZE(MPI_COMM_WORLD, size_Of_Cluster, ierror)
call MPI_COMM_RANK(MPI_COMM_WORLD, process_Rank, ierror)

IF(process_Rank == 0) THEN
    message_Item = 42
    call MPI_SEND(message_Item, 1, MPI_INT, 1, 1, MPI_COMM_WORLD, ierror)
    print *, "Sending message containing: ", message_Item
ELSE IF(process_Rank == 1) THEN
    call MPI_RECV(message_Item, 1, MPI_INT, 0, 1, MPI_COMM_WORLD, MPI_STATUS_IGNORE, ierror)
    print *, "Received message containing: ", message_Item
END IF

call MPI_FINALIZE(ierror)
END PROGRAM

and compilation is:

$ mpicc -c prof.c 
$ mpif77 -c simple.f90 
$ mpif77 -o simple prof.o simple.o 
$ mpiexec --hostfile hfile --oversubscribe -np 2 ./simple

However, the Fortran execution does not show profiling messages. It seems that profiling code is not called.

Thanks a lot.

1 Answers

The Fortran program does not directly call any PMPI procedures or your intercepting C-provided functions. Whether the Fortran bindings indirectly call them is implementation dependent: your implementation does not.

As Gilles Gouaillardet comments, some implementations (notably MPICH) do allow the interception as developed in this question. However, for those implementations which do not the following reasoning applies.

Although you have a C-compiled object which is linked in to the executable with the Fortran main program, this does not affect the operation of the Fortran program: the Fortran program does not reference any symbols defined by that C object.

For example, the symbol MPI_Init defined by the C source file is not the same thing that the Fortran linker is looking for after the Fortran compiler sees MPI_INIT. It'll be looking for mpi_init_ (or some such: precise details will depend on your system).

To have the Fortran program use the user-defined C object you will need to use proper inter-language operation (for example using standardized C interoperability with Fortran, or manual name mangling). But you'll also need to address more complicated aspects of multi-language use of MPI.

Related