Skip to content
Snippets Groups Projects
tensormatrix_mpi.cpp 4.99 KiB
Newer Older
  • Learn to ignore specific revisions
  • Camille Coti's avatar
    Camille Coti committed
    #include <iostream>
    #include <cstdlib>
    #include <ginac/ginac.h>
    #include <fstream> // debug?
    #include <signal.h> // necessaire ?
    #include <sys/wait.h> // necessaire ?
    #include <mpi.h>
    
    #include <unistd.h> // debug
    
    
    Camille Coti's avatar
    Camille Coti committed
    #include "tensormatrix.h"
    #include "utils.h"
    
    Camille Coti's avatar
    Camille Coti committed
    
    
    #ifdef TAUPROF
    #include <TAU.h>
    #endif
    
    
    Camille Coti's avatar
    Camille Coti committed
    #define DEBUG 0
    
    Camille Coti's avatar
    Camille Coti committed
    
    namespace gi = GiNaC;
    
    /*
      libginac-dev ginac-tools
      mpic++ -O3 -g -Wall -o tensormatrix_mpi tensormatrix_mpi.cpp -lginac  -Wno-unused-variable
    */
    
    
    /* Arguments:
       tensormatrix_mpi [N] [Function name] [Nb of foremen]
       Function names being: 
       - M/m: Master-Worker -> multiply_1level_mw
       - A/a: Master-Worker, addition on a slave -> multiply_1level_mw_addslave
       - H/h: Hierarchical master-worker -> multiply_1level_mw_hierarch
    
       - C/c: Combined -> multiply_combined
    
    Camille Coti's avatar
    Camille Coti committed
    /* Sequentiel sur Minimum
    real	3m31,034s
    */
    
    
    /*******************************************************************************
     *                          Global variables                                   *
     *******************************************************************************/
    
    
    Camille Coti's avatar
    Camille Coti committed
    MPI_Datatype DT_PARAMETERS;
    
    MPI_Datatype DT_PARAMETERS_2;
    
    Camille Coti's avatar
    Camille Coti committed
    
    
    Camille Coti's avatar
    Camille Coti committed
    unsigned int nbforemen = NBFOREMEN;     /* Number of foremen to use with the hierarchical M/W */
    unsigned int maxresult = MAXRESULT;     /* Maximum results in the result queue, addslave version */
    
    Camille Coti's avatar
    Camille Coti committed
    /*******************************************************************************
     *                               Main function                                 *
     *******************************************************************************/
    
    int main( int argc, char** argv ){
    
        tensor3D_t T;
        matrix_int_t J;
    
        int N = DEFAULTN;
        char tostart = DEFAULTFUNCTION;
    
    Camille Coti's avatar
    Camille Coti committed
        
        gi::ex Tpara = 0;
        gi::ex Tseq = 0;
    
        double tv_start, tv_para, tv_seq;
        int rank;
    
        
    #ifdef TAUPROF
        TAU_INIT(&argc, &argv);
        TAU_PROFILE_SET_NODE(0);
    #endif
        
    
    Camille Coti's avatar
    Camille Coti committed
        MPI_Init( &argc, &argv );
        MPI_Comm_rank( MPI_COMM_WORLD, &rank );
        //    std::cout << "Process " << rank << " has pid " << getpid() << std::endl;
    
    
        /* Parse the command line */
    
        if( argc >= 2 ) {
            if( argv[1][0] == 'h' ) {
                if( 0 == rank ) help();
                MPI_Finalize();
                return EXIT_SUCCESS;
            }
            N = atoi( argv[1] );
            if( argc >= 3 ) {
                switch( argv[2][0] ) {
                case 'M':
                case 'm':
                    tostart = 'm';
                    break;
                case 'A':
                case 'a':
                    tostart = 'a';
                    break;
                case 'H':
                case 'h':
                    tostart = 'h';
                    break;
    
                case 'C':
                case 'c':
                    tostart = 'c';
                    break;
    
    Camille Coti's avatar
    Camille Coti committed
                case 'S':
                case 's':
                    tostart = 's';
                    break;
                case '1':
                case '2':
                    tostart = argv[2][0];
                    break;
    
                default:
                    std::cout << "Wrong function name. Using " << tostart << std::endl;
                    break;
                }
                if( argc >= 4 ) {
    
                    nbforemen = atoi( argv[3] );  /* these two variables are obtained from the same CI parameter but since they are */
                    maxresult = atoi( argv[3] );  /* used in two functions for two purposes, use two different names                */
    
    Camille Coti's avatar
    Camille Coti committed
        /* Initialize the tensor with symbolic values */
        
        create_tensor_3D( T, N, N, N );
    
        /* Initialize the simplectic matrix */
    
        init_simplectic( J, N, N );
    
        /* Compute it in parallel */
        
        tv_start = getTime();
    
        switch( tostart ){
        case 'm':
    
            Tpara = multiply_1level_mw( T, N );
    
            break;
    
        case 'a':
            Tpara = multiply_1level_mw_addslave( T, N );
    
            break;
    
            Tpara = multiply_1level_mw_hierarch( T, J, N );
            break;
    
        case 'c':
            Tpara = multiply_combined( T, J, N );
    
        case 's':
            Tpara = multiply_seq( T, J, N );
            break;
        case '1':
            Tpara = multiply_1level( T, J, N );
            break;
        default:
            std::cerr << "Wrong function called" << std::endl;
        }
    
    Camille Coti's avatar
    Camille Coti committed
        tv_para = getTime();
    
        /* Local verification */
        
        if( 0 == rank ) {
    #if DEBUG
            Tseq = multiply_1level( T, J, N );
            tv_seq = getTime();
            
            std::cout << "Tpara3=" << Tpara << ";" << std::endl;
            std::cout << "Tseq=" << Tseq << ";" << std::endl;
    #endif
    
            std::cout.precision( 4 );
    
    Camille Coti's avatar
    Camille Coti committed
            std::cout << "Time: ";
            std::cout << "parallel    " << ( tv_para - tv_start ) / 1e6 << "   ";
    #if DEBUG
            std::cout << "sequential  " << ( tv_seq - tv_para ) / 1e6 << "   ";
            /* this verification does not work, the manual one (copy-paste in ginsh) works */
            std::cout << "Equal? " << ( Tseq.is_equal( Tpara )  ? "yes" : "no" ) << std::endl;
    #endif
            std::cout << std::endl;
    
            //        std::cout << "Difference? " << ( Tseq -= Tpara  ) << std::endl;
        }
    
        MPI_Finalize();
        return EXIT_SUCCESS;
    }
    
    
    Camille Coti's avatar
    Camille Coti committed