#ifndef Hadrons_MSource_Convolution_hpp_ #define Hadrons_MSource_Convolution_hpp_ #include #include #include BEGIN_HADRONS_NAMESPACE /****************************************************************************** * Convolution * ******************************************************************************/ BEGIN_MODULE_NAMESPACE(MSource) class ConvolutionPar: Serializable { public: GRID_SERIALIZABLE_CLASS_MEMBERS(ConvolutionPar, std::string, field, std::string, filter, std::string, mom); }; template class TConvolution: public Module { public: FERM_TYPE_ALIASES(FImpl,); public: // constructor TConvolution(const std::string name); // destructor virtual ~TConvolution(void) {}; // dependency relation virtual std::vector getInput(void); virtual std::vector getOutput(void); // setup virtual void setup(void); // execution virtual void execute(void); private: std::vector mom_; }; MODULE_REGISTER_TMP(Convolution, TConvolution, MSource); /****************************************************************************** * TConvolution implementation * ******************************************************************************/ // constructor ///////////////////////////////////////////////////////////////// template TConvolution::TConvolution(const std::string name) : Module(name) {} // dependencies/products /////////////////////////////////////////////////////// template std::vector TConvolution::getInput(void) { std::vector in = {par().field, par().filter}; return in; } template std::vector TConvolution::getOutput(void) { std::vector out = {getName()}; return out; } // setup /////////////////////////////////////////////////////////////////////// template void TConvolution::setup(void) { mom_ = strToVec(par().mom); if(mom_.size() != env().getNd()) { HADRONS_ERROR(Size, std::string("momentum has ") + std::to_string(mom_.size()) + " instead of " + std::to_string(env().getNd()) + " components"); } envCreateLat(PropagatorField, getName()); envTmpLat(ComplexField, "momfield"); envTmp(FFT, "fft", 1, env().getGrid()); } // execution /////////////////////////////////////////////////////////////////// template void TConvolution::execute(void) { auto &filter = envGet(ComplexField, par().filter); auto &field = envGet(PropagatorField, par().field); auto &out = envGet(PropagatorField, getName()); envGetTmp(ComplexField, momfield); envGetTmp(FFT, fft); std::vector mask(env().getNd(), 1); mask.back()=0; //transform only the spatial dimensions startTimer("Fourier transform"); fft.FFT_dim_mask(momfield, filter, mask, FFT::forward); fft.FFT_dim_mask(out, field, mask, FFT::forward); stopTimer("Fourier transform"); startTimer("momentum-space multiplication"); out=momfield*out; stopTimer("momentum-space multiplication"); startTimer("inserting momentum"); for(int mu=0; mu