// #include "mpi_test_incl.h"
#include <mpi.h>
#include <stdlib.h>

void mainInit(int* procRank)
{
    MPI::Init_thread(MPI_THREAD_MULTIPLE);
    MPI_Errhandler_set(MPI_COMM_WORLD, MPI_ERRORS_RETURN); // return an exception instead of Fatal Error, which finishes execution of all processes.
    MPI_Comm_rank(MPI_COMM_WORLD, procRank);
}

int main(int argc, char *argv[])
{
    int rank = 0, buf;
    mainInit(&rank);

    int retErr  = MPI_SUCCESS;
    if(rank == 0){
        MPI_Request request;
        MPI_Status  status;
        for (int i=1; i<10; ++i) {
            retErr = MPI_Irecv(&buf, 1, MPI::INT, 1, 0, MPI_COMM_WORLD, &request);
            if (retErr != MPI_SUCCESS) {
                printf("Error in initiating irecv !!! \n");
            }
            retErr = MPI_Wait(&request, &status);
            if (retErr != MPI_SUCCESS) {
                printf("Error with sender !!! \n");
            }
            else {
                printf("Got %d \n", buf);
            }
        }
    }
    else {
        MPI_Status status;
        for (int i=1; i<10; ++i) {
            buf = i * 1000;
            retErr = MPI_Send(&buf, 1, MPI::INT, 0, 0, MPI_COMM_WORLD);
            if (i==5) {
                printf("Calling abort\n");
                abort();
            }
        }
    }

    retErr = MPI_Finalize();
    return 0;
}
