From d25dc4e795b13e2cd26db7485a56c8fb1a574f01 Mon Sep 17 00:00:00 2001 From: Tor Harald Sandve Date: Fri, 9 Sep 2022 14:23:20 +0200 Subject: [PATCH] check controls in getWellConvergence --- opm/simulators/flow/BlackoilModelEbos.hpp | 2 +- opm/simulators/wells/BlackoilWellModel.hpp | 6 +- .../wells/BlackoilWellModel_impl.hpp | 76 ++++++++++++++----- opm/simulators/wells/WellInterface_impl.hpp | 2 +- tests/test_glift1.cpp | 2 +- 5 files changed, 67 insertions(+), 21 deletions(-) diff --git a/opm/simulators/flow/BlackoilModelEbos.hpp b/opm/simulators/flow/BlackoilModelEbos.hpp index 4a732ebb9..93faa6e78 100644 --- a/opm/simulators/flow/BlackoilModelEbos.hpp +++ b/opm/simulators/flow/BlackoilModelEbos.hpp @@ -982,7 +982,7 @@ namespace Opm { // Get convergence reports for reservoir and wells. std::vector B_avg(numEq, 0.0); auto report = getReservoirConvergence(timer.currentStepLength(), iteration, B_avg, residual_norms); - report += wellModel().getWellConvergence(B_avg); + report += wellModel().getWellConvergence(B_avg, /*checkWellGroupControls*/report.converged()); return report; } diff --git a/opm/simulators/wells/BlackoilWellModel.hpp b/opm/simulators/wells/BlackoilWellModel.hpp index c23ff4b67..300285fd3 100644 --- a/opm/simulators/wells/BlackoilWellModel.hpp +++ b/opm/simulators/wells/BlackoilWellModel.hpp @@ -260,7 +260,7 @@ namespace Opm { void applyScaleAdd(const Scalar alpha, const BVector& x, BVector& Ax) const; // Check if well equations is converged. - ConvergenceReport getWellConvergence(const std::vector& B_avg, const bool checkGroupConvergence = false) const; + ConvergenceReport getWellConvergence(const std::vector& B_avg, const bool checkWellGroupControls = false); const SimulatorReportSingle& lastReport() const; @@ -280,8 +280,12 @@ namespace Opm { // at the beginning of each time step (Not report step) void prepareTimeStep(DeferredLogger& deferred_logger); void initPrimaryVariablesEvaluation() const; +<<<<<<< HEAD bool shouldBalanceNetwork(const int reportStepIndex, const int iterationIdx) const; std::pair updateWellControls(DeferredLogger& deferred_logger, const bool checkGroupControls); +======= + bool updateWellControls(DeferredLogger& deferred_logger); +>>>>>>> check controls in getWellConvergence void updateAndCommunicate(const int reportStepIdx, const int iterationIdx, diff --git a/opm/simulators/wells/BlackoilWellModel_impl.hpp b/opm/simulators/wells/BlackoilWellModel_impl.hpp index 2e9057e46..a82da9d24 100644 --- a/opm/simulators/wells/BlackoilWellModel_impl.hpp +++ b/opm/simulators/wells/BlackoilWellModel_impl.hpp @@ -899,7 +899,7 @@ namespace Opm { DeferredLogger& local_deferredLogger) { - const auto [network_changed, network_imbalance] = updateWellControls(local_deferredLogger, /* check group controls */ true); + const auto [network_changed, network_imbalance] = updateWellControls(local_deferredLogger); bool alq_updated = false; OPM_BEGIN_PARALLEL_TRY_CATCH(); @@ -1389,7 +1389,7 @@ namespace Opm { template ConvergenceReport BlackoilWellModel:: - getWellConvergence(const std::vector& B_avg, bool checkGroupConvergence) const + getWellConvergence(const std::vector& B_avg, bool checkWellGroupControls) { DeferredLogger local_deferredLogger; @@ -1406,7 +1406,7 @@ namespace Opm { local_report += report; } } - + const Opm::Parallel::Communication comm = grid().comm(); DeferredLogger global_deferredLogger = gatherDeferredLogger(local_deferredLogger, comm); if (terminal_output_) { @@ -1415,6 +1415,10 @@ namespace Opm { ConvergenceReport report = gatherConvergenceReport(local_report, comm); + if (report.converged() && checkWellGroupControls) { + bool violated = updateWellControls(local_deferredLogger); + report.setGroupConverged(!violated); + } // Log debug messages for NaN or too large residuals. if (terminal_output_) { for (const auto& f : report.wellFailures()) { @@ -1425,15 +1429,6 @@ namespace Opm { } } } - - if (checkGroupConvergence) { - const int reportStepIdx = ebosSimulator_.episodeIndex(); - const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx); - bool violated = checkGroupConstraints(fieldGroup, - ebosSimulator_.episodeIndex(), - global_deferredLogger); - report.setGroupConverged(!violated); - } return report; } @@ -1458,6 +1453,7 @@ namespace Opm { template bool +<<<<<<< HEAD BlackoilWellModel:: shouldBalanceNetwork(const int reportStepIdx, const int iterationIdx) const { @@ -1482,13 +1478,19 @@ namespace Opm { template std::pair +======= +>>>>>>> check controls in getWellConvergence BlackoilWellModel:: - updateWellControls(DeferredLogger& deferred_logger, const bool checkGroupControls) + updateWellControls(DeferredLogger& deferred_logger) { // Even if there are no wells active locally, we cannot // return as the DeferredLogger uses global communication. // For no well active globally we simply return. +<<<<<<< HEAD if( !wellsActive() ) return { false, 0.0 }; +======= + if( !wellsActive() ) return false ; +>>>>>>> check controls in getWellConvergence const int episodeIdx = ebosSimulator_.episodeIndex(); const int iterationIdx = ebosSimulator_.model().newtonMethod().numIterations(); @@ -1502,6 +1504,7 @@ namespace Opm { const double network_imbalance = comm.max(local_network_imbalance); std::set switched_wells; +<<<<<<< HEAD if (checkGroupControls) { @@ -1522,10 +1525,42 @@ namespace Opm { switched_wells.insert(well->name()); changed_well_group = changed_well || changed_well_group; } +======= + bool changed = false; + // Check group individual constraints. + bool changed_individual = updateGroupIndividualControls(deferred_logger, + episodeIdx, iterationIdx); + + if (changed_individual) { + updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); + changed = true; + } + + // Check group's constraints from higher levels. + bool changed_higher = updateGroupHigherControls(deferred_logger, + episodeIdx); + + if (changed_higher) { + updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); + changed = true; + } + + + // Check wells' group constraints and communicate. + bool changed_well_group = false; + for (const auto& well : well_container_) { + const auto mode = WellInterface::IndividualOrGroup::Group; + const bool changed_well = well->updateWellControl(ebosSimulator_, mode, this->wellState(), this->groupState(), deferred_logger); + if (changed_well) { + switched_wells.insert(well->name()); + changed_well_group = changed_well || changed_well_group; +>>>>>>> check controls in getWellConvergence } - changed_well_group = comm.sum(changed_well_group); - if (changed_well_group) - updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); + } + changed_well_group = comm.sum(changed_well_group); + if (changed_well_group) { + updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); + changed = true; } // Check individual well constraints and communicate. @@ -1541,14 +1576,21 @@ namespace Opm { } } changed_well_individual = comm.sum(changed_well_individual); - if (changed_well_individual) + if (changed_well_individual) { updateAndCommunicate(episodeIdx, iterationIdx, deferred_logger); + changed = true; + } + // update wsolvent fraction for REIN wells const Group& fieldGroup = schedule().getGroup("FIELD", episodeIdx); updateWsolvent(fieldGroup, episodeIdx, this->nupcolWellState()); +<<<<<<< HEAD return { network_changed, network_imbalance }; +======= + return changed; +>>>>>>> check controls in getWellConvergence } diff --git a/opm/simulators/wells/WellInterface_impl.hpp b/opm/simulators/wells/WellInterface_impl.hpp index be68647c5..10a8fcf89 100644 --- a/opm/simulators/wells/WellInterface_impl.hpp +++ b/opm/simulators/wells/WellInterface_impl.hpp @@ -230,7 +230,7 @@ namespace Opm const GroupState& group_state, DeferredLogger& deferred_logger) /* const */ { - if (this->wellIsStopped()) { + if (!this->isOperableAndSolvable() || this->wellIsStopped()) { return false; } diff --git a/tests/test_glift1.cpp b/tests/test_glift1.cpp index 7f3735cfa..bc59097a6 100644 --- a/tests/test_glift1.cpp +++ b/tests/test_glift1.cpp @@ -146,7 +146,7 @@ BOOST_AUTO_TEST_CASE(G1) Opm::DeferredLogger deferred_logger; well_model.calculateExplicitQuantities(deferred_logger); well_model.prepareTimeStep(deferred_logger); - well_model.updateWellControls(deferred_logger, /* check group controls */ true); + well_model.updateWellControls(deferred_logger); well_model.initPrimaryVariablesEvaluation(); Opm::WellInterface *well_ptr = well_model.getWell("B-1H").get(); StdWell *std_well = dynamic_cast(well_ptr);