FMpiBufferReader.hpp 4.07 KB
Newer Older
PIACIBELLO Cyrille's avatar
PIACIBELLO Cyrille committed
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
// ===================================================================================
// Copyright ScalFmm 2011 INRIA, Olivier Coulaud, Bérenger Bramas, Matthias Messner
// olivier.coulaud@inria.fr, berenger.bramas@inria.fr
// This software is a computer program whose purpose is to compute the FMM.
//
// This software is governed by the CeCILL-C and LGPL licenses and
// abiding by the rules of distribution of free software.  
// 
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public and CeCILL-C Licenses for more details.
// "http://www.cecill.info". 
// "http://www.gnu.org/licenses".
// ===================================================================================
#ifndef FMPIBUFFERREADER_HPP
#define FMPIBUFFERREADER_HPP

19
#include <memory>
PIACIBELLO Cyrille's avatar
PIACIBELLO Cyrille committed
20
#include "../Utils/FMpi.hpp"
21
#include "FAbstractBuffer.hpp"
PIACIBELLO Cyrille's avatar
PIACIBELLO Cyrille committed
22 23 24 25 26 27 28 29 30


/** @author Cyrille Piacibello
 * This class provide the same features as FBufferWriter using MPI_Pack system
 *
 * Put some data
 * then insert back if needed
 * finally use data pointer as you like
 */
31
class FMpiBufferReader : public FAbstractBufferReader {
BRAMAS Berenger's avatar
BRAMAS Berenger committed
32 33 34 35
    const MPI_Comm comm;            //< Communicator needed by MPI_Pack functions
    const int arrayCapacity;        //< Allocated space
    std::unique_ptr<char[]> array;  //< Allocated Array
    int currentIndex;
PIACIBELLO Cyrille's avatar
PIACIBELLO Cyrille committed
36 37

public :
BRAMAS Berenger's avatar
BRAMAS Berenger committed
38 39 40 41 42 43 44 45 46
    /*Constructor with a default arrayCapacity of 512 bytes */
    FMpiBufferReader(const MPI_Comm inComm, const int inCapacity = 512):
        comm(inComm),
        arrayCapacity(inCapacity),
        array(new char[inCapacity]),
        currentIndex(0)
    {}

    /** Destructor
PIACIBELLO Cyrille's avatar
PIACIBELLO Cyrille committed
47
   */
BRAMAS Berenger's avatar
BRAMAS Berenger committed
48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79
    virtual ~FMpiBufferReader(){
    }

    /** Get allocated memory pointer */
    char* data(){
        return array.get();
    }

    /** Get allocated memory pointer */
    const char* data() const {
        return array.get();
    }

    /** get the filled space */
    int getSize() const{
        return currentIndex;
    }

    /** Size of the memory initialized */
    int getCapacity() const{
        return arrayCapacity;
    }

    /** Move the read index to a position */
    void seek(const int inIndex){
        if(inIndex > arrayCapacity){
            printf("FMpiBufferReader :: Aborting :: Can't move index because buffer isn't long enough");
            exit(0);
        }
        else{
            currentIndex = inIndex;
        }
80
    }
BRAMAS Berenger's avatar
BRAMAS Berenger committed
81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127

    /** Get the read position */
    int tell() const {
        return currentIndex;
    }

    /** Get a value with memory cast */
    template <class ClassType>
    ClassType getValue(){
        ClassType value;
        int previousIndex = currentIndex;
        seek(int(sizeof(value) + previousIndex));
        MPI_Unpack(array.get(),arrayCapacity,&previousIndex,&value,1,FMpi::GetType(value),comm);
        return value;
    }

    /** Get a value with memory cast at a specified index */
    template <class ClassType>
    ClassType getValue(const int ind){
        ClassType value;
        int previousIndex = ind;
        seek(int(sizeof(value)+ind));
        MPI_Unpack(array.get(),arrayCapacity,&previousIndex,&value,1,FMpi::GetType(value),comm);
        return value;
    }

    /** Fill a value with memory cast */
    template <class ClassType>
    void fillValue(ClassType* const inValue){
        int previousIndex = currentIndex;
        seek(int(sizeof(ClassType) + previousIndex));
        MPI_Unpack(array.get(),arrayCapacity,&previousIndex,inValue,1,FMpi::GetType(*inValue),comm);
    }

    /** Fill one/many value(s) with memcpy */
    template <class ClassType>
    void fillArray(ClassType* const inArray, const int inSize){
        int previousIndex = currentIndex;
        seek(int(sizeof(ClassType) * inSize + previousIndex));
        MPI_Unpack(array.get(),arrayCapacity,&previousIndex,inArray,inSize,FMpi::GetType(*inArray),comm);
    }

    /** Same as fillValue */
    template <class ClassType>
    FMpiBufferReader& operator>>(ClassType& object){
        fillValue(&object);
        return *this;
128
    }
PIACIBELLO Cyrille's avatar
PIACIBELLO Cyrille committed
129 130 131 132

};
#endif