diff --git a/dumux/decoupled/common/impetproblem.hh b/dumux/decoupled/common/impetproblem.hh index e09466ca209f4e4ea41d45436d0f1b840526697a..073b5a52c3d7195ba2e4dc45c2af749fbac8caa9 100644 --- a/dumux/decoupled/common/impetproblem.hh +++ b/dumux/decoupled/common/impetproblem.hh @@ -735,7 +735,7 @@ public: Restarter res; res.serializeBegin(asImp_()); - std::cerr << "Serialize to file " << res.fileName() << "\n"; + std::cout << "Serialize to file " << res.fileName() << "\n"; timeManager().serialize(res); resultWriter().serialize(res); @@ -748,7 +748,7 @@ public: if (adaptiveGrid) { - AdaptiveGridRestart<Grid, dim>::serializeGrid(asImp_()); + AdaptiveGridRestart<Grid>::serializeGrid(asImp_()); } } @@ -763,7 +763,7 @@ public: { if (adaptiveGrid) { - AdaptiveGridRestart<Grid, dim>::restartGrid(asImp_()); + AdaptiveGridRestart<Grid>::restartGrid(asImp_()); variables().initialize(); model().initialize(); } @@ -772,7 +772,7 @@ public: Restarter res; res.deserializeBegin(asImp_(), tRestart); - std::cerr << "Deserialize from file " << res.fileName() << "\n"; + std::cout << "Deserialize from file " << res.fileName() << "\n"; timeManager().deserialize(res); diff --git a/dumux/decoupled/common/onemodelproblem.hh b/dumux/decoupled/common/onemodelproblem.hh index 81081ad382fd7baea52b5676ac07843bc2dd3fd7..040e2808f452c43cd0adfdf299ad0c271b594bdb 100644 --- a/dumux/decoupled/common/onemodelproblem.hh +++ b/dumux/decoupled/common/onemodelproblem.hh @@ -591,7 +591,7 @@ public: Restarter res; res.serializeBegin(asImp_()); - std::cerr << "Serialize to file " << res.fileName() << "\n"; + std::cout << "Serialize to file " << res.fileName() << "\n"; timeManager().serialize(res); resultWriter().serialize(res); @@ -612,7 +612,7 @@ public: Restarter res; res.deserializeBegin(asImp_(), tRestart); - std::cerr << "Deserialize from file " << res.fileName() << "\n"; + std::cout << "Deserialize from file " << res.fileName() << "\n"; timeManager().deserialize(res); resultWriter().deserialize(res); diff --git a/dumux/io/adaptivegridrestart.hh b/dumux/io/adaptivegridrestart.hh index 52f364c1db2b3e8b68579d80ff52c6ec7e60b0c4..36787d840909083fd3b8e07686a8e8c2ac637f83 100644 --- a/dumux/io/adaptivegridrestart.hh +++ b/dumux/io/adaptivegridrestart.hh @@ -25,17 +25,12 @@ #include <dune/common/deprecated.hh> -#include <dune/grid/yaspgrid.hh> -#include <dune/grid/sgrid.hh> #if HAVE_ALUGRID #include <dune/grid/alugrid/2d/alugrid.hh> #include <dune/grid/alugrid/3d/alugrid.hh> #elif HAVE_DUNE_ALUGRID #include <dune/alugrid/grid.hh> #endif -#if HAVE_UG -#include <dune/grid/uggrid.hh> -#endif #if HAVE_ALBERTA #include <dune/grid/albertagrid/agrid.hh> #endif @@ -43,6 +38,8 @@ #include <dune/grid/common/backuprestore.hh> #include <dune/grid/utility/grapedataioformattypes.hh> +#include <dumux/common/basicproperties.hh> + namespace Dumux { /*! @@ -50,58 +47,24 @@ namespace Dumux */ //! \cond \private -template<class Grid, int dim> +template<class Grid> struct GridRestartCheck { static const bool allowRestart = false; }; -template<int dim> -struct GridRestartCheck<Dune::YaspGrid<dim>, dim> -{ - static const bool allowRestart = false; -}; - -template<int dim> -struct -DUNE_DEPRECATED_MSG("SGrid is deprecated in Dune 2.4, use YaspGrid instead.") -GridRestartCheck<Dune::SGrid<dim, dim>, dim> -{ - static const bool allowRestart = false; -}; - +// the specializations for grid managers that support restart #if HAVE_ALUGRID || HAVE_DUNE_ALUGRID -template<int dim> -struct GridRestartCheck<Dune::ALUGrid<dim, dim, Dune::cube, Dune::nonconforming>, dim> -{ -#if HAVE_ALUGRID - static const bool allowRestart = true; -#else - static const bool allowRestart = false; -#endif -}; - -template<int dim> -struct GridRestartCheck<Dune::ALUGrid<dim, dim, Dune::simplex, Dune::conforming>, dim> +template<int dim, int dimworld, Dune::ALUGridElementType elType, Dune::ALUGridRefinementType refinementType> +struct GridRestartCheck<Dune::ALUGrid<dim, dimworld, elType, refinementType> > { -#if HAVE_ALUGRID static const bool allowRestart = true; -#else - static const bool allowRestart = false; -#endif }; #endif -#if HAVE_UG -template<int dim> -struct GridRestartCheck<Dune::UGGrid<dim>, dim> -{ - static const bool allowRestart = false; -}; -#endif #if HAVE_ALBERTA -template<int dim> -struct GridRestartCheck<Dune::AlbertaGrid< dim, dim>, dim> +template<int dim, int dimworld> +struct GridRestartCheck<Dune::AlbertaGrid<dim, dimworld> > { static const bool allowRestart = true; }; @@ -112,7 +75,7 @@ struct GridRestartCheck<Dune::AlbertaGrid< dim, dim>, dim> /*! * \brief Default class for restart functionality for non-adaptive grids */ -template <class Grid, int dim, bool allowGridRestart = GridRestartCheck<Grid, dim>::allowRestart > +template <class Grid, bool allowGridRestart = GridRestartCheck<Grid>::allowRestart > class AdaptiveGridRestart { public: @@ -123,7 +86,7 @@ public: static void serializeGrid(Problem& problem) { DUNE_THROW(Dune::NotImplemented, - "Adaptive restart functionality currently only works for ALUGrid (not dune-alugrid)."); + "Adaptive restart functionality currently only works for ALUGrid / dune-alugrid."); } /*! @@ -133,15 +96,15 @@ public: static void restartGrid(Problem& problem) { DUNE_THROW(Dune::NotImplemented, - "Adaptive restart functionality currently only works for ALUGrid (not dune-alugrid)."); + "Adaptive restart functionality currently only works for ALUGrid / dune-alugrid."); } }; /*! * \brief Provides a restart functionality for adaptive grids */ -template <class Grid, int dim> -class AdaptiveGridRestart<Grid, dim, true> +template <class Grid> +class AdaptiveGridRestart<Grid, true> { public: /*! @@ -151,11 +114,12 @@ public: static void serializeGrid(Problem& problem) { std::string gridName = restartGridFileName_(problem); +#if HAVE_DUNE_ALUGRID + Dune::BackupRestoreFacility<Grid>::backup(problem.grid(), gridName); +#else double time = problem.timeManager().time(); - problem.grid().template writeGrid<Dune::xdr> (gridName, time); - // TODO use the BackupRestoreFacility with dune-alugrid, see FS#237 - //Dune::BackupRestoreFacility<Grid>::backup( - // problem.grid(), restartGridFileName_(problem)); + problem.grid().template writeGrid<Dune::xdr>(gridName, time); +#endif } /*! @@ -164,12 +128,11 @@ public: template<class Problem> static void restartGrid(Problem& problem) { +#if HAVE_ALUGRID std::string gridName = restartGridFileName_(problem); double time = problem.timeManager().time(); - problem.grid().template readGrid<Dune::xdr> (gridName, time); - // TODO use the BackupRestoreFacility with dune-alugrid, see FS#237 - //problem.setGrid(*Dune::BackupRestoreFacility<Grid>::restore( - // restartGridFileName_(problem))); + problem.grid().template readGrid<Dune::xdr>(gridName, time); +#endif } private: @@ -179,7 +142,18 @@ private: { int rank = problem.gridView().comm().rank(); std::ostringstream oss; - oss << problem.name()<<"_time="<<problem.timeManager().time()<<"_rank="<<rank<<".grs"; + try { + std::string name = GET_RUNTIME_PARAM_FROM_GROUP(TTAG(NumericModel), std::string, Problem, Name); + oss << name; + } + catch (Dumux::ParameterException &e) + { + std::cerr << e.what() << std::endl; + std::cerr << "Taking name from problem.name(): " << problem.name() << std::endl; + std::cerr << "Be sure to provide a parameter Problem.Name if you want to restart." << std::endl; + oss << problem.name(); + } + oss << "_time=" << problem.timeManager().time() << "_rank=" << rank << ".grs"; return oss.str(); } }; diff --git a/dumux/io/gridcreator.hh b/dumux/io/gridcreator.hh index 5af01dcdaddba938e7f2e6844ac7473c87517610..f40a2af908d2ecd46aafcf0c53b08937c834e03a 100644 --- a/dumux/io/gridcreator.hh +++ b/dumux/io/gridcreator.hh @@ -85,6 +85,8 @@ namespace Properties // poperty forward declarations NEW_PROP_TAG(Grid); NEW_PROP_TAG(GridParameterGroup); +NEW_PROP_TAG(AdaptiveGrid); +NEW_PROP_TAG(Scalar); } @@ -815,7 +817,40 @@ public: */ static void makeGrid() { - // First try to create it from a DGF or msh file in GridParameterGroup.File +#if HAVE_DUNE_ALUGRID + // First check if a restart for an adaptive grid is required + try { + if (GET_PROP_VALUE(TypeTag, AdaptiveGrid)) + { + typedef typename GET_PROP_TYPE(TypeTag, Scalar) Scalar; + Scalar restartTime = GET_RUNTIME_PARAM_FROM_GROUP(TypeTag, Scalar, TimeManager, Restart); + // we came until here so the restart key was found. Restore the grid. + int rank = 0; +#if HAVE_MPI + MPI_Comm_rank(Dune::MPIHelper::getCommunicator(), &rank); +#endif + try { + std::string name = GET_RUNTIME_PARAM_FROM_GROUP(TypeTag, std::string, Problem, Name); + std::ostringstream oss; + oss << name << "_time=" << restartTime << "_rank=" << rank << ".grs"; + std::cout << "Restoring an ALUGrid from " << oss.str() << std::endl; + ParentType::gridPtr() = std::shared_ptr<Grid>(Dune::BackupRestoreFacility<Grid>::restore(oss.str())); + return; + } + catch (Dumux::ParameterException &e) + { + std::cerr << e.what() << std::endl; + std::cerr << "Restart functionality for an adaptive grid requested, but failed." << std::endl; + std::cerr << "Did you forget to provide Problem.Name in your .input file?" << std::endl; + throw; + } + } + } + catch (Dumux::ParameterException &e) {} + catch (...) { throw; } +#endif + + // Then try to create it from a DGF or msh file in GridParameterGroup.File try { const std::string fileName = GET_RUNTIME_PARAM_FROM_GROUP_CSTRING(TypeTag, std::string, GET_PROP_VALUE(TypeTag, GridParameterGroup).c_str(), File); ParentType::makeGridFromFile(fileName, "ALUGrid"); diff --git a/dumux/multidomain/common/multidomainproblem.hh b/dumux/multidomain/common/multidomainproblem.hh index 65a535301b394f0c3d46eaff5c15d7c36274140a..2c0741b96cfc8af2159fb96ff748ec1525083cf3 100644 --- a/dumux/multidomain/common/multidomainproblem.hh +++ b/dumux/multidomain/common/multidomainproblem.hh @@ -138,7 +138,7 @@ public: typedef Dumux::Restart Restarter; Restarter res; res.serializeBegin(this->asImp_()); - std::cerr << "Serialize to file '" << res.fileName() << "'\n"; + std::cout << "Serialize to file '" << res.fileName() << "'\n"; this->timeManager().serialize(res); this->asImp_().serialize(res); res.serializeEnd(); diff --git a/test/decoupled/2p/CMakeLists.txt b/test/decoupled/2p/CMakeLists.txt index da571faf3862872297e5cb53791c66385253ecf4..4033a9678c2c442260ba89402a1a0d465fcd80a1 100644 --- a/test/decoupled/2p/CMakeLists.txt +++ b/test/decoupled/2p/CMakeLists.txt @@ -14,6 +14,16 @@ add_dumux_test(test_impesadaptive test_impesadaptive test_impesadaptive.cc ${CMAKE_CURRENT_BINARY_DIR}/test_2padaptive-00007.vtu --command "${CMAKE_CURRENT_BINARY_DIR}/test_impesadaptive") +add_dumux_test(test_impesadaptiverestart test_impesadaptiverestart test_impesadaptiverestart.cc + python ${CMAKE_SOURCE_DIR}/bin/runtest.py + --script fuzzy + --files ${CMAKE_SOURCE_DIR}/test/references/test_2padaptive-reference.vtu + ${CMAKE_CURRENT_BINARY_DIR}/test_2padaptive-00007.vtu + --command "${CMAKE_CURRENT_BINARY_DIR}/test_impesadaptiverestart") + +# the restart test has to run after the test that produces the restart file +set_tests_properties(test_impesadaptiverestart PROPERTIES DEPENDS test_impesadaptive) + if(MPI_FOUND) add_dumux_test(test_impeswithamg test_impeswithamg test_impeswithamg.cc python ${CMAKE_SOURCE_DIR}/bin/runtest.py @@ -99,4 +109,3 @@ add_dumux_test(test_3d2pmpfaladaptive test_3d2pmpfaladaptive test_3d2p.cc --files ${CMAKE_SOURCE_DIR}/test/references/test_3d2pmpfaladaptive-reference.vtu ${CMAKE_CURRENT_BINARY_DIR}/test_3d2pmpfaladaptive-00012.vtu --command "${CMAKE_CURRENT_BINARY_DIR}/test_3d2pmpfaladaptive -ParameterFile ${CMAKE_CURRENT_SOURCE_DIR}/test_3d2p.input -Problem.OutputName test_3d2pmpfaladaptive -ModelType MPFALAdaptive") - diff --git a/test/decoupled/2p/test_impesadaptive.cc b/test/decoupled/2p/test_impesadaptive.cc index 993eb575b802f66250d15555b8336cc551e8a0fe..03c5ceedab8ba8e30088f7e89010e0b847c5f230 100644 --- a/test/decoupled/2p/test_impesadaptive.cc +++ b/test/decoupled/2p/test_impesadaptive.cc @@ -45,7 +45,9 @@ void usage(const char *progName, const std::string &errorMsg) "\t-Grid.NumberOfCellsX Resolution in x-direction [-]\n" "\t-Grid.NumberOfCellsY Resolution in y-direction [-]\n" "\t-Grid.UpperRightX Length of the domain [m]\n" - "\t-Grid.UpperRightY Height of the domain [m]\n"; + "\t-Grid.UpperRightY Height of the domain [m]\n" + "\t-Problem.Name Name passed to the output routines \n" +; std::cout << errorMessageOut << "\n"; } diff --git a/test/decoupled/2p/test_impesadaptive.input b/test/decoupled/2p/test_impesadaptive.input index 586f6e9b31d5f6d74eb19226287ee333d64e6baf..bfe28a5b423450a9f1b8fb68f444391417da1462 100644 --- a/test/decoupled/2p/test_impesadaptive.input +++ b/test/decoupled/2p/test_impesadaptive.input @@ -2,6 +2,9 @@ TEnd = 2e7 # [s] DtInitial = 0 # [s] +[Problem] +Name = test_2padaptive # name passed to the output routines + [Grid] NumberOfCellsX = 2 # [-] level 0 resolution in x-direction NumberOfCellsY = 1 # [-] level 0 resolution in y-direction diff --git a/test/decoupled/2p/test_impesadaptiveproblem.hh b/test/decoupled/2p/test_impesadaptiveproblem.hh index 804a983a428826d18c53eecd6420cd37587de41e..3b9723b8024631d1e18ac0c877526e7fffeeabf1 100644 --- a/test/decoupled/2p/test_impesadaptiveproblem.hh +++ b/test/decoupled/2p/test_impesadaptiveproblem.hh @@ -56,6 +56,7 @@ class TestIMPESAdaptiveProblem; namespace Properties { NEW_TYPE_TAG(TestIMPESAdaptiveProblem, INHERITS_FROM(FVPressureTwoPAdaptive, FVTransportTwoP, IMPESTwoPAdaptive, TestIMPESAdaptiveSpatialParams)); +NEW_TYPE_TAG(TestIMPESAdaptiveRestartProblem, INHERITS_FROM(TestIMPESAdaptiveProblem)); // Set the grid type #if HAVE_ALUGRID || HAVE_DUNE_ALUGRID @@ -65,6 +66,11 @@ SET_TYPE_PROP(TestIMPESAdaptiveProblem, Grid, Dune::ALUGrid<2, 2, Dune::cube, Du // set the GridCreator property SET_TYPE_PROP(TestIMPESAdaptiveProblem, GridCreator, CubeGridCreator<TypeTag>); +#if HAVE_DUNE_ALUGRID +// reset the GridCreator to the standard one for testing the restart functionality +SET_TYPE_PROP(TestIMPESAdaptiveRestartProblem, GridCreator, GridCreator<TypeTag>); +#endif + // Set the problem property SET_TYPE_PROP(TestIMPESAdaptiveProblem, Problem, Dumux::TestIMPESAdaptiveProblem<TypeTag>); @@ -150,7 +156,16 @@ public: TestIMPESAdaptiveProblem(TimeManager &timeManager, const GridView &gridView) : ParentType(timeManager, gridView), eps_(1e-6) { - GridCreator::grid().globalRefine(GET_PARAM_FROM_GROUP(TypeTag, int, GridAdapt, MaxLevel)); + name_ = GET_RUNTIME_PARAM_FROM_GROUP(TypeTag, std::string, Problem, Name); + + // Refine the grid provided that no restart occurs. Otherwise, an + // already refined grid will be read. + typedef typename GET_PROP(TypeTag, ParameterTree) ParameterTree; + if (!(ParameterTree::tree().hasKey("Restart") + || ParameterTree::tree().hasKey("TimeManager.Restart"))) + { + GridCreator::grid().globalRefine(GET_PARAM_FROM_GROUP(TypeTag, int, GridAdapt, MaxLevel)); + } this->setGrid(GridCreator::grid()); this->setOutputInterval(10); @@ -167,12 +182,12 @@ public: */ const char *name() const { - return "test_2padaptive"; + return name_.c_str(); } bool shouldWriteRestartFile() const { - return false; + return true; } /*! @@ -267,6 +282,7 @@ public: private: const Scalar eps_; + std::string name_; }; } //end namespace diff --git a/test/decoupled/2p/test_impesadaptiverestart.cc b/test/decoupled/2p/test_impesadaptiverestart.cc new file mode 100644 index 0000000000000000000000000000000000000000..379809d0835014cbfef4acbc9974e58216e9d7ca --- /dev/null +++ b/test/decoupled/2p/test_impesadaptiverestart.cc @@ -0,0 +1,73 @@ +// -*- mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- +// vi: set et ts=4 sw=4 sts=4: +/***************************************************************************** + * See the file COPYING for full copying permissions. * + * * + * This program 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 2 of the License, or * + * (at your option) any later version. * + * * + * 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 License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program. If not, see <http://www.gnu.org/licenses/>. * + *****************************************************************************/ +/*! + * \file + * + * \ingroup IMPETtests + * \brief test for the sequential 2p model + */ +#include "config.h" + +#if HAVE_ALUGRID || HAVE_DUNE_ALUGRID + +#include "test_impesadaptiveproblem.hh" +#include <dumux/common/start.hh> + +//////////////////////// +// the main function +//////////////////////// +void usage(const char *progName, const std::string &errorMsg) +{ + if (errorMsg.size() > 0) { + std::string errorMessageOut = "\nUsage: "; + errorMessageOut += progName; + errorMessageOut += " [options]\n"; + errorMessageOut += errorMsg; + errorMessageOut += "\n\nThe list of mandatory options for this program is:\n" + "\t-TimeManager.TEnd End of the simulation [s] \n" + "\t-TimeManager.DtInitial Initial timestep size [s] \n" +#if HAVE_ALUGRID + "\t-Grid.NumberOfCellsX Resolution in x-direction [-]\n" + "\t-Grid.NumberOfCellsY Resolution in y-direction [-]\n" + "\t-Grid.UpperRightX Length of the domain [m]\n" + "\t-Grid.UpperRightY Height of the domain [m]\n" +#endif + "\t-Problem.Name Name passed to the output routines \n" + "\t-Restart Restart time [s] \n"; + std::cout << errorMessageOut + << "\n"; + } +} + +int main(int argc, char** argv) +{ + typedef TTAG(TestIMPESAdaptiveRestartProblem) ProblemTypeTag; + return Dumux::start<ProblemTypeTag>(argc, argv, usage); +} +#else + +#include <iostream> + +int main() +{ +#warning You need to have dune-ALUGrid installed to run this test + std::cerr << "You need to have dune-ALUGrid installed to run this test\n"; + return 77; +} +#endif // HAVE_ALUGRID || HAVE_DUNE_ALUGRID diff --git a/test/decoupled/2p/test_impesadaptiverestart.input b/test/decoupled/2p/test_impesadaptiverestart.input new file mode 100644 index 0000000000000000000000000000000000000000..df9fb7972944b0b6004a5cc64f0c4d14e462e69a --- /dev/null +++ b/test/decoupled/2p/test_impesadaptiverestart.input @@ -0,0 +1,20 @@ +[TimeManager] +TEnd = 2e7 # [s] +DtInitial = 0 # [s] +Restart = 1.02418e+07 # [s] the restart time + +[Grid] +NumberOfCellsX = 2 # [-] level 0 resolution in x-direction +NumberOfCellsY = 1 # [-] level 0 resolution in y-direction + +UpperRightX = 300 # [m] length of the domain +UpperRightY = 100 # [m] height of the domain + +[GridAdapt] +MinLevel = 0 # [-] minimum level of refinement +MaxLevel = 5 # [-] maximum level of refinement +RefineTolerance = 0.05 # threshold for refinement criterion +CoarsenTolerance = 0.001 # threshold for coarsening criterion + +[Problem] +Name = test_2padaptive # name passed to the output routines