mirror of
https://github.com/OPM/opm-simulators.git
synced 2025-02-25 18:55:30 -06:00
Merge pull request #870 from totto82/frankenstein_cache_reuse_fix
Frankenstein: InvalidateCache when restaring the timestep
This commit is contained in:
@@ -170,6 +170,7 @@ namespace Opm {
|
|||||||
, current_relaxation_(1.0)
|
, current_relaxation_(1.0)
|
||||||
, dx_old_(AutoDiffGrid::numCells(grid_))
|
, dx_old_(AutoDiffGrid::numCells(grid_))
|
||||||
, isBeginReportStep_(false)
|
, isBeginReportStep_(false)
|
||||||
|
, isRestart_(false)
|
||||||
{
|
{
|
||||||
const double gravity = detail::getGravity(geo_.gravity(), UgGridHelpers::dimensions(grid_));
|
const double gravity = detail::getGravity(geo_.gravity(), UgGridHelpers::dimensions(grid_));
|
||||||
const std::vector<double> pv(geo_.poreVolume().data(), geo_.poreVolume().data() + geo_.poreVolume().size());
|
const std::vector<double> pv(geo_.poreVolume().data(), geo_.poreVolume().data() + geo_.poreVolume().size());
|
||||||
@@ -220,7 +221,11 @@ namespace Opm {
|
|||||||
std::vector<double> residual_norms;
|
std::vector<double> residual_norms;
|
||||||
const bool converged = getConvergence(timer, iteration,residual_norms);
|
const bool converged = getConvergence(timer, iteration,residual_norms);
|
||||||
residual_norms_history_.push_back(residual_norms);
|
residual_norms_history_.push_back(residual_norms);
|
||||||
const bool must_solve = (iteration < nonlinear_solver.minIter()) || (!converged);
|
bool must_solve = (iteration < nonlinear_solver.minIter()) || (!converged);
|
||||||
|
// is first set to true if a linear solve is needed, but then it is set to false if the solver succeed.
|
||||||
|
isRestart_ = must_solve && (iteration == nonlinear_solver.maxIter());
|
||||||
|
// don't solve if we have reached the maximum number of iteration.
|
||||||
|
must_solve = must_solve && (iteration < nonlinear_solver.maxIter());
|
||||||
Dune::InverseOperatorResult result;
|
Dune::InverseOperatorResult result;
|
||||||
if (must_solve) {
|
if (must_solve) {
|
||||||
// enable single precision for solvers when dt is smaller then 20 days
|
// enable single precision for solvers when dt is smaller then 20 days
|
||||||
@@ -256,6 +261,9 @@ namespace Opm {
|
|||||||
// since the solution was changed, the cache for the intensive quantities
|
// since the solution was changed, the cache for the intensive quantities
|
||||||
// are invalid
|
// are invalid
|
||||||
ebosSimulator_.model().invalidateIntensiveQuantitiesCache(/*timeIdx=*/0);
|
ebosSimulator_.model().invalidateIntensiveQuantitiesCache(/*timeIdx=*/0);
|
||||||
|
|
||||||
|
// solver has succeed i.e. no need for restart.
|
||||||
|
isRestart_ = false;
|
||||||
}
|
}
|
||||||
const bool failed = false; // Not needed in this model.
|
const bool failed = false; // Not needed in this model.
|
||||||
const int linear_iters = must_solve ? result.iterations : 0;
|
const int linear_iters = must_solve ? result.iterations : 0;
|
||||||
@@ -303,7 +311,8 @@ namespace Opm {
|
|||||||
}
|
}
|
||||||
catch ( const Dune::FMatrixError& e )
|
catch ( const Dune::FMatrixError& e )
|
||||||
{
|
{
|
||||||
OPM_THROW(Opm::NumericalProblem,"no convergence");
|
isRestart_ = true;
|
||||||
|
OPM_THROW(Opm::NumericalProblem,"Well equation did not converge");
|
||||||
}
|
}
|
||||||
|
|
||||||
return iter_report;
|
return iter_report;
|
||||||
@@ -744,11 +753,13 @@ namespace Opm {
|
|||||||
if (std::isnan(mass_balance_residual[phaseIdx])
|
if (std::isnan(mass_balance_residual[phaseIdx])
|
||||||
|| std::isnan(CNV[phaseIdx])
|
|| std::isnan(CNV[phaseIdx])
|
||||||
|| (phaseIdx < np && std::isnan(well_flux_residual[phaseIdx]))) {
|
|| (phaseIdx < np && std::isnan(well_flux_residual[phaseIdx]))) {
|
||||||
|
isRestart_ = true;
|
||||||
OPM_THROW(Opm::NumericalProblem, "NaN residual for phase " << phaseName);
|
OPM_THROW(Opm::NumericalProblem, "NaN residual for phase " << phaseName);
|
||||||
}
|
}
|
||||||
if (mass_balance_residual[phaseIdx] > maxResidualAllowed()
|
if (mass_balance_residual[phaseIdx] > maxResidualAllowed()
|
||||||
|| CNV[phaseIdx] > maxResidualAllowed()
|
|| CNV[phaseIdx] > maxResidualAllowed()
|
||||||
|| (phaseIdx < np && well_flux_residual[phaseIdx] > maxResidualAllowed())) {
|
|| (phaseIdx < np && well_flux_residual[phaseIdx] > maxResidualAllowed())) {
|
||||||
|
isRestart_ = true;
|
||||||
OPM_THROW(Opm::NumericalProblem, "Too large residual for phase " << phaseName);
|
OPM_THROW(Opm::NumericalProblem, "Too large residual for phase " << phaseName);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1039,6 +1050,10 @@ namespace Opm {
|
|||||||
{
|
{
|
||||||
ebosSimulator_.problem().beginTimeStep();
|
ebosSimulator_.problem().beginTimeStep();
|
||||||
}
|
}
|
||||||
|
// if the last step failed we want to recalculate the IntesiveQuantities.
|
||||||
|
if (isRestart_) {
|
||||||
|
ebosSimulator_.model().invalidateIntensiveQuantitiesCache(/*timeIdx=*/0);
|
||||||
|
}
|
||||||
|
|
||||||
ebosSimulator_.problem().beginIteration();
|
ebosSimulator_.problem().beginIteration();
|
||||||
ebosSimulator_.model().linearizer().linearize();
|
ebosSimulator_.model().linearizer().linearize();
|
||||||
@@ -1065,6 +1080,7 @@ namespace Opm {
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
bool isBeginReportStep_;
|
bool isBeginReportStep_;
|
||||||
|
bool isRestart_;
|
||||||
|
|
||||||
};
|
};
|
||||||
} // namespace Opm
|
} // namespace Opm
|
||||||
|
|||||||
Reference in New Issue
Block a user