diff --git a/programs/Hadrons/Application.cc b/programs/Hadrons/Application.cc index f0e6f6a4..c21dba5d 100644 --- a/programs/Hadrons/Application.cc +++ b/programs/Hadrons/Application.cc @@ -29,6 +29,8 @@ using namespace Hadrons; ******************************************************************************/ // constructor ///////////////////////////////////////////////////////////////// Application::Application(int argc, char *argv[]) +: env_(Environment::getInstance()) +, modFactory_(ModuleFactory::getInstance()) { if (argc < 2) { @@ -43,6 +45,12 @@ Application::Application(int argc, char *argv[]) HadronsLogMessage.Active(GridLogMessage.isActive()); HadronsLogDebug.Active(GridLogDebug.isActive()); LOG(Message) << "Grid initialized" << endl; + LOG(Message) << "Modules available:" << endl; + auto list = modFactory_.getModuleList(); + for (auto &m: list) + { + LOG(Message) << " " << m << endl; + } } // destructor ////////////////////////////////////////////////////////////////// @@ -57,15 +65,40 @@ void Application::run(void) { parseParameterFile(); schedule(); + configLoop(); } // parse parameter file //////////////////////////////////////////////////////// +class ModuleId: Serializable +{ +public: + GRID_SERIALIZABLE_CLASS_MEMBERS(ModuleId, + std::string, name, + std::string, type); +}; + void Application::parseParameterFile(void) { XmlReader reader(parameterFileName_); + ModuleId id; LOG(Message) << "Reading '" << parameterFileName_ << "'..." << endl; - read(reader, "parameters", parameters_); + read(reader, "parameters", par_); + push(reader, "modules"); + push(reader, "module"); + do + { + read(reader, "id", id); + module_[id.name] = modFactory_.create(id.type, id.name); + module_[id.name]->parseParameters(reader, "options"); + vector output = module_[id.name]->getOutput(); + for (auto &n: output) + { + associatedModule_[n] = id.name; + } + } while (reader.nextElement("module")); + pop(reader); + pop(reader); } // schedule computation //////////////////////////////////////////////////////// @@ -74,37 +107,63 @@ void Application::schedule(void) Graph moduleGraph; LOG(Message) << "Scheduling computation..." << endl; - for (auto &m: parameters_.modules) + + // create dependency graph + for (auto &m: module_) { - for (auto &p: m.in) + vector input = m.second->getInput(); + for (auto &n: input) { - moduleGraph.addEdge(p, m.name); + try + { + moduleGraph.addEdge(associatedModule_.at(n), m.first); + } + catch (out_of_range &) + { + HADRON_ERROR("unknown object '" + n + "'"); + } } } - vector> con = moduleGraph.getConnectedComponents(); + // topological sort + map> m; + unsigned int k = 0; + vector> con = moduleGraph.getConnectedComponents(); LOG(Message) << "Program:" << endl; - LOG(Message) << " #segments: " << con.size() << endl; for (unsigned int i = 0; i < con.size(); ++i) { vector> t = con[i].allTopoSort(); - auto m = makeDependencyMatrix(t); - - for (auto &v: t[0]) + + m = makeDependencyMatrix(t); + for (unsigned int j = 0; j < t[0].size(); ++j) { - cout << v << " "; + program_.push_back(t[0][j]); + LOG(Message) << setw(4) << right << k << ": " + << program_[k] << endl; + k++; } - cout << endl; - for (auto &v1: t[0]) - { - for (auto &v2: t[0]) - { - cout << m[v1][v2] << " "; - } - cout << endl; - } - - LOG(Message) << " segment " << i << ":" << endl; + } +} + +// program execution /////////////////////////////////////////////////////////// +void Application::configLoop(void) +{ + auto range = par_.configs.range; + + for (unsigned int t = range.start; t < range.end; t += range.step) + { + LOG(Message) << "Starting measurement for trajectory " << t << endl; + execute(); + } +} + +void Application::execute(void) +{ + for (unsigned int i = 0; i < program_.size(); ++i) + { + LOG(Message) << "Measurement step (" << i+1 << "/" << program_.size() + << ")" << endl; + (*module_[program_[i]])(env_); } } diff --git a/programs/Hadrons/Application.hpp b/programs/Hadrons/Application.hpp index 670c644e..71cc0a80 100644 --- a/programs/Hadrons/Application.hpp +++ b/programs/Hadrons/Application.hpp @@ -21,15 +21,47 @@ #define Hadrons_Application_hpp_ #include -#include +#include +#include + +namespace Grid { + GRID_SERIALIZABLE_ENUM(ConfigType, undef, load, 1, unit, 2, gen, 3); +} BEGIN_HADRONS_NAMESPACE +class TrajRange: Serializable +{ +public: + GRID_SERIALIZABLE_CLASS_MEMBERS(TrajRange, + unsigned int, start, + unsigned int, end, + unsigned int, step); +}; + +class ConfigPar: Serializable +{ +public: + GRID_SERIALIZABLE_CLASS_MEMBERS(ConfigPar, + std::string, ioStem, + TrajRange, range); +}; + +class GlobalPar: Serializable +{ +public: + GRID_SERIALIZABLE_CLASS_MEMBERS(GlobalPar, + std::vector, latticeSize, + ConfigPar, configs); +}; + /****************************************************************************** * Main program manager * ******************************************************************************/ class Application { +public: + public: // constructor Application(int argc, char *argv[]); @@ -42,9 +74,17 @@ private: void parseParameterFile(void); // schedule computation void schedule(void); + // program execution + void configLoop(void); + void execute(void); private: - std::string parameterFileName_; - Parameters parameters_; + std::string parameterFileName_; + GlobalPar par_; + Environment &env_; + ModuleFactory &modFactory_; + std::map> module_; + std::map associatedModule_; + std::vector program_; }; END_HADRONS_NAMESPACE diff --git a/programs/Hadrons/CMeson.cc b/programs/Hadrons/CMeson.cc new file mode 100644 index 00000000..d9fe3547 --- /dev/null +++ b/programs/Hadrons/CMeson.cc @@ -0,0 +1,65 @@ +/* + * CMeson.cc, part of Grid + * + * Copyright (C) 2015 Antonin Portelli + * + * Grid is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Grid 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 License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Grid. If not, see . + */ + +#include + +using namespace std; +using namespace Grid; +using namespace Hadrons; + +/****************************************************************************** + * CMeson implementation * + ******************************************************************************/ +// constructor ///////////////////////////////////////////////////////////////// +CMeson::CMeson(const string &name) +: Module(name) +{} + +// parse parameters //////////////////////////////////////////////////////////// +void CMeson::parseParameters(XmlReader &reader, const std::string &name) +{ + read(reader, name, par_); +} + +// dependency relation ///////////////////////////////////////////////////////// +vector CMeson::getInput(void) +{ + vector input = {par_.q1, par_.q2}; + + return input; +} + +vector CMeson::getOutput(void) +{ + vector output = {getName()}; + + return output; +} + +// memory footprint //////////////////////////////////////////////////////////// +double CMeson::nCreatedProp(void) +{ + return 0.; +} + +// execution /////////////////////////////////////////////////////////////////// +void CMeson::operator()(Environment &env) +{ + LOG(Message) << "computing meson contraction '" << getName() << "'" << endl; +} diff --git a/programs/Hadrons/CMeson.hpp b/programs/Hadrons/CMeson.hpp new file mode 100644 index 00000000..7f13ce9a --- /dev/null +++ b/programs/Hadrons/CMeson.hpp @@ -0,0 +1,65 @@ +/* + * CMeson.hpp, part of Grid + * + * Copyright (C) 2015 Antonin Portelli + * + * Grid is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Grid 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 License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Grid. If not, see . + */ + +#ifndef Hadrons_CMeson_hpp_ +#define Hadrons_CMeson_hpp_ + +#include +#include +#include + +BEGIN_HADRONS_NAMESPACE + +/****************************************************************************** + * CMeson * + ******************************************************************************/ +class CMeson: public Module +{ +public: + class Par: Serializable + { + public: + GRID_SERIALIZABLE_CLASS_MEMBERS(Par, + std::string, q1, + std::string, q2, + std::string, output); + }; +public: + // constructor + CMeson(const std::string &name); + // destructor + virtual ~CMeson(void) = default; + // parse parameters + virtual void parseParameters(XmlReader &reader, const std::string &name); + // dependency relation + virtual std::vector getInput(void); + virtual std::vector getOutput(void); + // memory footprint + virtual double nCreatedProp(void); + // execution + virtual void operator()(Environment &env); +private: + Par par_; +}; + +MODULE_REGISTER(CMeson); + +END_HADRONS_NAMESPACE + +#endif // Hadrons_CMeson_hpp_ diff --git a/programs/Hadrons/Environment.cc b/programs/Hadrons/Environment.cc index bf95b175..66dd540e 100644 --- a/programs/Hadrons/Environment.cc +++ b/programs/Hadrons/Environment.cc @@ -29,3 +29,4 @@ using namespace Hadrons; // constructor ///////////////////////////////////////////////////////////////// Environment::Environment(void) {} + diff --git a/programs/Hadrons/Environment.hpp b/programs/Hadrons/Environment.hpp index 205f0aa0..62da9839 100644 --- a/programs/Hadrons/Environment.hpp +++ b/programs/Hadrons/Environment.hpp @@ -21,21 +21,15 @@ #define Hadrons_Environment_hpp_ #include -#include BEGIN_HADRONS_NAMESPACE /****************************************************************************** * Global environment * ******************************************************************************/ -// TODO: make it a singleton class Environment { -public: - // constructor - Environment(void); - // destructor - virtual ~Environment(void) = default; + SINGLETON(Environment); }; END_HADRONS_NAMESPACE diff --git a/programs/Hadrons/Global.hpp b/programs/Hadrons/Global.hpp index 3b90b7ed..2294adef 100644 --- a/programs/Hadrons/Global.hpp +++ b/programs/Hadrons/Global.hpp @@ -49,6 +49,19 @@ extern HadronsLogger HadronsLogWarning; extern HadronsLogger HadronsLogMessage; extern HadronsLogger HadronsLogDebug; +// singleton pattern +#define SINGLETON(name)\ +public:\ + name(const name &e) = delete;\ + void operator=(const name &e) = delete;\ + static name & getInstance(void)\ + {\ + static name e;\ + return e;\ + }\ +private:\ + name(void); + END_HADRONS_NAMESPACE #endif // Hadrons_Global_hpp_ diff --git a/programs/Hadrons/MQuark.cc b/programs/Hadrons/MQuark.cc new file mode 100644 index 00000000..82c46c52 --- /dev/null +++ b/programs/Hadrons/MQuark.cc @@ -0,0 +1,63 @@ +/* + * MQuark.cc, part of Grid + * + * Copyright (C) 2015 Antonin Portelli + * + * Grid is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Grid 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 License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Grid. If not, see . + */ + +#include + +using namespace std; +using namespace Grid; +using namespace Hadrons; + +/****************************************************************************** + * MQuark implementation * + ******************************************************************************/ +// constructor ///////////////////////////////////////////////////////////////// +MQuark::MQuark(const std::string &name) +: Module(name) +{} + +// parse parameters +void MQuark::parseParameters(XmlReader &reader, const std::string &name) +{ + read(reader, name, par_); +} + +// dependency relation +vector MQuark::getInput(void) +{ + return vector(); +} + +vector MQuark::getOutput(void) +{ + vector out = {getName(), getName() + "_5d"}; + + return out; +} + +// memory footprint +double MQuark::nCreatedProp(void) +{ + return static_cast((par_.Ls > 1) ? par_.Ls + 1 : 1); +} + +// execution +void MQuark::operator()(Environment &env) +{ + LOG(Message) << "computing quark propagator '" << getName() << "'" << endl; +} diff --git a/programs/Hadrons/InputObjects.hpp b/programs/Hadrons/MQuark.hpp similarity index 52% rename from programs/Hadrons/InputObjects.hpp rename to programs/Hadrons/MQuark.hpp index d18615fa..ae1efa12 100644 --- a/programs/Hadrons/InputObjects.hpp +++ b/programs/Hadrons/MQuark.hpp @@ -1,5 +1,5 @@ /* - * InputObjects.hpp, part of Grid + * MQuark.hpp, part of Grid * * Copyright (C) 2015 Antonin Portelli * @@ -17,44 +17,46 @@ * along with Grid. If not, see . */ -#ifndef Hadrons_InputObjects_hpp_ -#define Hadrons_InputObjects_hpp_ +#ifndef Hadrons_MQuark_hpp_ +#define Hadrons_MQuark_hpp_ #include +#include +#include BEGIN_HADRONS_NAMESPACE /****************************************************************************** - * Serializable input classes * + * MQuark * ******************************************************************************/ -class Module: Serializable +class MQuark: public Module { +public: + class Par: Serializable + { + public: + GRID_SERIALIZABLE_CLASS_MEMBERS(Par, unsigned int, Ls); + }; public: // constructor - Module(void) = default; + MQuark(const std::string &name); // destructor - virtual ~Module(void) = default; - // serializable members - GRID_DECL_CLASS_MEMBERS(Module, - std::string , name, - std::vector, in - ); + virtual ~MQuark(void) = default; + // parse parameters + virtual void parseParameters(XmlReader &reader, const std::string &name); + // dependency relation + virtual std::vector getInput(void); + virtual std::vector getOutput(void); + // memory footprint + virtual double nCreatedProp(void); + // execution + virtual void operator()(Environment &env); +private: + Par par_; }; -class Parameters: Serializable -{ -public: - // constructor - Parameters(void) = default; - // destructor - virtual ~Parameters(void) = default; - // serializable members - GRID_DECL_CLASS_MEMBERS(Parameters, - std::vector, latticeSize, - std::vector , modules - ); -}; +MODULE_REGISTER(MQuark); END_HADRONS_NAMESPACE -#endif // Hadrons_InputObjects_hpp_ +#endif // Hadrons_MQuark_hpp_ diff --git a/programs/Hadrons/Makefile.am b/programs/Hadrons/Makefile.am index 870b0747..b907f8c8 100644 --- a/programs/Hadrons/Makefile.am +++ b/programs/Hadrons/Makefile.am @@ -5,9 +5,16 @@ bin_PROGRAMS = Hadrons Hadrons_SOURCES = \ Application.cc \ - Application.hpp \ - Global.hpp \ + Environment.cc \ Global.cc \ - Hadrons.cc + Hadrons.cc \ + Module.cc \ + ModuleFactory.cc + +Hadrons_SOURCES += \ + MQuark.cc + +Hadrons_SOURCES += \ + CMeson.cc Hadrons_LDADD = -lGrid diff --git a/programs/Hadrons/Module.cc b/programs/Hadrons/Module.cc new file mode 100644 index 00000000..be689867 --- /dev/null +++ b/programs/Hadrons/Module.cc @@ -0,0 +1,38 @@ +/* + * Module.cc, part of Grid + * + * Copyright (C) 2015 Antonin Portelli + * + * Grid is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Grid 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 License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Grid. If not, see . + */ + +#include + +using namespace std; +using namespace Grid; +using namespace Hadrons; + +/****************************************************************************** + * Module implementation * + ******************************************************************************/ +// constructor ///////////////////////////////////////////////////////////////// +Module::Module(const string &name) +: name_(name) +{} + +// access ////////////////////////////////////////////////////////////////////// +string Module::getName(void) const +{ + return name_; +} diff --git a/programs/Hadrons/Module.hpp b/programs/Hadrons/Module.hpp new file mode 100644 index 00000000..bf82a9e7 --- /dev/null +++ b/programs/Hadrons/Module.hpp @@ -0,0 +1,72 @@ +/* + * Module.hpp, part of Grid + * + * Copyright (C) 2015 Antonin Portelli + * + * Grid is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Grid 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 License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Grid. If not, see . + */ + +#ifndef Hadrons_Module_hpp_ +#define Hadrons_Module_hpp_ + +#include + +BEGIN_HADRONS_NAMESPACE + +// module registration macro +#define MODULE_REGISTER(mod)\ +class mod##Registrar\ +{\ +public:\ + mod##Registrar(void)\ + {\ + ModuleFactory &modFac = ModuleFactory::getInstance();\ + modFac.registerModule(#mod, [&](const std::string &name)\ + {\ + return std::unique_ptr(new mod(name));\ + });\ + }\ +};\ +static mod##Registrar mod##RegistrarInstance; + +/****************************************************************************** + * Module * + ******************************************************************************/ +class Environment; + +class Module +{ +public: + // constructor + Module(const std::string &name); + // destructor + virtual ~Module(void) = default; + // access + std::string getName(void) const; + // parse parameters + virtual void parseParameters(XmlReader &reader, const std::string &name) = 0; + // dependency relation + virtual std::vector getInput(void) = 0; + virtual std::vector getOutput(void) = 0; + // memory footprint + virtual double nCreatedProp(void) = 0; + // execution + virtual void operator()(Environment &env) = 0; +private: + std::string name_; +}; + +END_HADRONS_NAMESPACE + +#endif // Hadrons_Module_hpp_ diff --git a/programs/Hadrons/ModuleFactory.cc b/programs/Hadrons/ModuleFactory.cc new file mode 100644 index 00000000..2a87da3a --- /dev/null +++ b/programs/Hadrons/ModuleFactory.cc @@ -0,0 +1,70 @@ +/* + * ModuleFactory.cc, part of Grid + * + * Copyright (C) 2015 Antonin Portelli + * + * Grid is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Grid 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 License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Grid. If not, see . + */ + +#include + +using namespace std; +using namespace Grid; +using namespace Hadrons; + +/****************************************************************************** + * ModuleFactory implementation * + ******************************************************************************/ +// constructor ///////////////////////////////////////////////////////////////// +ModuleFactory::ModuleFactory(void) +{ +} + +// registration //////////////////////////////////////////////////////////////// +void ModuleFactory::registerModule(const std::string &type, + const FactoryFunc &f) +{ + factory_[type] = f; +} + +// get module list ///////////////////////////////////////////////////////////// +std::vector ModuleFactory::getModuleList(void) const +{ + std::vector list; + + for (auto &f: factory_) + { + list.push_back(f.first); + } + + return list; +} + +// factory ///////////////////////////////////////////////////////////////////// +unique_ptr ModuleFactory::create(const string &type, + const string &name) const +{ + FactoryFunc func; + + try + { + func = factory_.at(type); + } + catch (out_of_range) + { + HADRON_ERROR("module type '" + type + "' unknown"); + } + + return func(name); +} diff --git a/programs/Hadrons/ModuleFactory.hpp b/programs/Hadrons/ModuleFactory.hpp new file mode 100644 index 00000000..822dc8e7 --- /dev/null +++ b/programs/Hadrons/ModuleFactory.hpp @@ -0,0 +1,51 @@ +/* + * ModuleFactory.hpp, part of Grid + * + * Copyright (C) 2015 Antonin Portelli + * + * Grid is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Grid 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 License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Grid. If not, see . + */ + +#ifndef Hadrons_ModuleFactory_hpp_ +#define Hadrons_ModuleFactory_hpp_ + +#include +#include + +BEGIN_HADRONS_NAMESPACE + +/****************************************************************************** + * ModuleFactory * + ******************************************************************************/ +class ModuleFactory +{ + SINGLETON(ModuleFactory) +public: + typedef std::function(const std::string &)> + FactoryFunc; +public: + // registration + void registerModule(const std::string &type, const FactoryFunc &f); + // get module list + std::vector getModuleList(void) const; + // factory + std::unique_ptr create(const std::string &type, + const std::string &name) const; +private: + std::map factory_; +}; + +END_HADRONS_NAMESPACE + +#endif // Hadrons_ModuleFactory_hpp_