Add accessor functions to maintain WellState objects in well model

This commit is contained in:
Joakim Hove 2021-03-26 22:10:16 +01:00
parent ee20d1c1c1
commit 405b9d2244
4 changed files with 273 additions and 128 deletions

View File

@ -33,6 +33,7 @@
#include <opm/models/utils/propertysystem.hh> #include <opm/models/utils/propertysystem.hh>
#include <opm/models/utils/alignedallocator.hh> #include <opm/models/utils/alignedallocator.hh>
#include <opm/simulators/wells/WellStateFullyImplicitBlackoil.hpp>
#include <opm/material/fluidstates/CompositionalFluidState.hpp> #include <opm/material/fluidstates/CompositionalFluidState.hpp>
#include <opm/material/densead/Evaluation.hpp> #include <opm/material/densead/Evaluation.hpp>
#include <opm/material/densead/Math.hpp> #include <opm/material/densead/Math.hpp>
@ -1410,6 +1411,36 @@ protected:
/ rhoWaterSurface; / rhoWaterSurface;
} }
const WellStateFullyImplicitBlackoil& wellState() const
{
throw std::logic_error("wellState() method not implemented for class eclpeacemanwell");
}
WellStateFullyImplicitBlackoil& wellState()
{
throw std::logic_error("wellState() method not implemented for class eclpeacemanwell");
}
void commitWellState()
{
throw std::logic_error("commitWellState() method not implemented for class eclpeacemanwell");
}
void commitWellState(WellStateFullyImplicitBlackoil well_state)
{
throw std::logic_error("commitWellState() method not implemented for class eclpeacemanwell");
}
void resetWellState()
{
throw std::logic_error("resetWellState() method not implemented for class eclpeacemanwell");
}
void updateNupcolWellState()
{
throw std::logic_error("updateNupcolWellState() method not implemented for class eclpeacemanwell");
}
void void
updateEclWell(int, int) updateEclWell(int, int)
{ {

View File

@ -36,6 +36,7 @@
#include <opm/parser/eclipse/EclipseState/EclipseState.hpp> #include <opm/parser/eclipse/EclipseState/EclipseState.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/Schedule.hpp> #include <opm/parser/eclipse/EclipseState/Schedule/Schedule.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/Events.hpp> #include <opm/parser/eclipse/EclipseState/Schedule/Events.hpp>
#include <opm/simulators/wells/WellStateFullyImplicitBlackoil.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/Well/WellConnections.hpp> #include <opm/parser/eclipse/EclipseState/Schedule/Well/WellConnections.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/Well/Well.hpp> #include <opm/parser/eclipse/EclipseState/Schedule/Well/Well.hpp>
#include <opm/parser/eclipse/EclipseState/Schedule/TimeMap.hpp> #include <opm/parser/eclipse/EclipseState/Schedule/TimeMap.hpp>
@ -619,6 +620,35 @@ public:
// not implemented // not implemented
} }
const WellStateFullyImplicitBlackoil& wellState() const
{
throw std::logic_error("wellState() method not implemented for class eclwellmanager");
}
WellStateFullyImplicitBlackoil& wellState()
{
throw std::logic_error("wellState() method not implemented for class eclwellmanager");
}
void commitWellState()
{
throw std::logic_error("commitWellState() method not implemented for class eclwellmanager");
}
void commitWellState(WellStateFullyImplicitBlackoil well_state)
{
throw std::logic_error("commitWellState() method not implemented for class eclwellmanager");
}
void resetWellState()
{
throw std::logic_error("resetWellState() method not implemented for class eclwellmanager");
}
void updateNupcolWellState()
{
throw std::logic_error("updateNupcolWellState() method not implemented for class eclwellmanager");
}
void void
updateEclWell(int, int) updateEclWell(int, int)

View File

@ -215,14 +215,113 @@ namespace Opm {
return grp_nwrk_values; return grp_nwrk_values;
} }
/*
The dynamic state of the well model is maintained with an instance
of the WellStateFullyImplicitBlackoil class. Currently we have
three different wellstate instances:
1. The currently active wellstate is in the active_well_state_
member. That is the state which is mutated by the simulator.
2. In the case timestep fails to converge and we must go back and
try again with a smaller timestep we need to recover the last
valid wellstate. This is maintained with the
last_valid_well_state_ member and the functions
commitWellState() and resetWellState().
3. For the NUPCOL functionality we should either use the
currently active wellstate or a wellstate frozen at max
nupcol iterations. This is handled with the member
nupcol_well_state_ and the initNupcolWellState() function.
*/
/*
Immutable version of the currently active wellstate.
*/
const WellStateFullyImplicitBlackoil& wellState() const
{
return this->active_well_state_;
}
/*
Mutable version of the currently active wellstate.
*/
WellStateFullyImplicitBlackoil& wellState()
{
return this->active_well_state_;
}
/*
Will return the last good wellstate. This is typcially used when
initializing a new report step where the Schedule object might
have introduced new wells. The wellstate returned by
prevWellState() must have been stored with the commitWellState()
function first.
*/
const WellStateFullyImplicitBlackoil& prevWellState() const
{
return this->last_valid_well_state_;
}
/*
Will return the currently active nupcolWellState; must initialize
the internal nupcol wellstate with initNupcolWellState() first.
*/
const WellStateFullyImplicitBlackoil& nupcolWellState() const
{
return this->nupcol_well_state_;
}
/*
Will assign the internal member last_valid_well_state_ to the
current value of the this->active_well_state_. The state stored
with storeWellState() can then subsequently be recovered with the
resetWellState() method.
*/
void commitWellState()
{
this->last_valid_well_state_ = this->active_well_state_;
}
/*
Will store a copy of the input argument well_state in the
last_valid_well_state_ member, that state can then be recovered
with a subsequent call to resetWellState().
*/
void commitWellState(WellStateFullyImplicitBlackoil well_state)
{
this->last_valid_well_state_ = std::move(well_state);
}
/*
Will update the internal variable active_well_state_ to whatever
was stored in the last_valid_well_state_ member. This function
works in pair with commitWellState() which should be called first.
*/
void resetWellState()
{
this->active_well_state_ = this->last_valid_well_state_;
}
/*
Will store the current active wellstate in the nupcol_well_state_
member. This can then be subsequently retrieved with accessor
nupcolWellState().
*/
void updateNupcolWellState()
{
this->nupcol_well_state_ = this->active_well_state_;
}
Opm::data::Wells wellData() const Opm::data::Wells wellData() const
{ {
auto wsrpt = well_state_ auto wsrpt = this->wellState().report(phase_usage_, Opm::UgGridHelpers::globalCell(grid()),
.report(phase_usage_, Opm::UgGridHelpers::globalCell(grid()), [this](const int well_ndex) -> bool
[this](const int well_ndex) -> bool {
{ return this->wasDynamicallyShutThisTimeStep(well_ndex);
return this->wasDynamicallyShutThisTimeStep(well_ndex); });
});
this->assignWellGuideRates(wsrpt); this->assignWellGuideRates(wsrpt);
this->assignShutConnections(wsrpt); this->assignShutConnections(wsrpt);
@ -247,13 +346,6 @@ namespace Opm {
// Check if well equations is converged. // Check if well equations is converged.
ConvergenceReport getWellConvergence(const std::vector<Scalar>& B_avg, const bool checkGroupConvergence = false) const; ConvergenceReport getWellConvergence(const std::vector<Scalar>& B_avg, const bool checkGroupConvergence = false) const;
// return the internal well state, ignore the passed one.
// Used by the legacy code to make it compatible with the legacy well models.
const WellState& wellState(const WellState& well_state OPM_UNUSED) const;
// return the internal well state
const WellState& wellState() const;
const SimulatorReportSingle& lastReport() const; const SimulatorReportSingle& lastReport() const;
void addWellContributions(SparseMatrixAdapter& jacobian) const void addWellContributions(SparseMatrixAdapter& jacobian) const
@ -279,6 +371,8 @@ namespace Opm {
double wellPI(const int well_index) const; double wellPI(const int well_index) const;
double wellPI(const std::string& well_name) const; double wellPI(const std::string& well_name) const;
protected: protected:
Simulator& ebosSimulator_; Simulator& ebosSimulator_;
@ -323,9 +417,6 @@ namespace Opm {
WellInterfacePtr createWellForWellTest(const std::string& well_name, const int report_step, Opm::DeferredLogger& deferred_logger) const; WellInterfacePtr createWellForWellTest(const std::string& well_name, const int report_step, Opm::DeferredLogger& deferred_logger) const;
WellState well_state_;
WellState previous_well_state_;
WellState well_state_nupcol_;
const ModelParameters param_; const ModelParameters param_;
bool terminal_output_; bool terminal_output_;
@ -526,6 +617,16 @@ namespace Opm {
data::GroupData& gdata) const; data::GroupData& gdata) const;
void computeWellTemperature(); void computeWellTemperature();
private:
/*
The various wellState members should be accessed and modified
through the accessor functions wellState(), prevWellState(),
commitWellState(), resetWellState(), nupcolWellState() and
updateNupcolWellState().
*/
WellState active_well_state_;
WellState last_valid_well_state_;
WellState nupcol_well_state_;
}; };

View File

@ -268,11 +268,11 @@ namespace Opm {
// handling MS well related // handling MS well related
if (param_.use_multisegment_well_&& anyMSWellOpenLocal()) { // if we use MultisegmentWell model if (param_.use_multisegment_well_&& anyMSWellOpenLocal()) { // if we use MultisegmentWell model
well_state_.initWellStateMSWell(wells_ecl_, phase_usage_, &previous_well_state_); this->wellState().initWellStateMSWell(wells_ecl_, phase_usage_, &this->prevWellState());
} }
const Group& fieldGroup = schedule().getGroup("FIELD", timeStepIdx); const Group& fieldGroup = schedule().getGroup("FIELD", timeStepIdx);
WellGroupHelpers::setCmodeGroup(fieldGroup, schedule(), summaryState, timeStepIdx, well_state_); WellGroupHelpers::setCmodeGroup(fieldGroup, schedule(), summaryState, timeStepIdx, this->wellState());
// Compute reservoir volumes for RESV controls. // Compute reservoir volumes for RESV controls.
rateConverter_.reset(new RateConverterType (phase_usage_, rateConverter_.reset(new RateConverterType (phase_usage_,
@ -289,8 +289,8 @@ namespace Opm {
} }
} }
// update the previous well state. This is used to restart failed steps. // Store the current well state, to be able to recover in the case of failed iterations
previous_well_state_ = well_state_; this->commitWellState();
} }
@ -305,8 +305,8 @@ namespace Opm {
Opm::DeferredLogger local_deferredLogger; Opm::DeferredLogger local_deferredLogger;
well_state_ = previous_well_state_; this->resetWellState();
well_state_.disableGliftOptimization(); this->wellState().disableGliftOptimization();
updateAndCommunicateGroupData(); updateAndCommunicateGroupData();
const int reportStepIdx = ebosSimulator_.episodeIndex(); const int reportStepIdx = ebosSimulator_.episodeIndex();
const double simulationTime = ebosSimulator_.time(); const double simulationTime = ebosSimulator_.time();
@ -383,7 +383,7 @@ namespace Opm {
// nonzero phase anyway. // nonzero phase anyway.
for (auto& well : well_container_) { for (auto& well : well_container_) {
if (well->isProducer()) { if (well->isProducer()) {
well->updateWellStateRates(ebosSimulator_, well_state_, local_deferredLogger); well->updateWellStateRates(ebosSimulator_, this->wellState(), local_deferredLogger);
} }
} }
} }
@ -393,9 +393,9 @@ namespace Opm {
const auto& summaryState = ebosSimulator_.vanguard().summaryState(); const auto& summaryState = ebosSimulator_.vanguard().summaryState();
std::vector<double> pot(numPhases(), 0.0); std::vector<double> pot(numPhases(), 0.0);
const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx); const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx);
WellGroupHelpers::updateGuideRateForProductionGroups(fieldGroup, schedule(), phase_usage_, reportStepIdx, simulationTime, well_state_, comm, guideRate_.get(), pot); WellGroupHelpers::updateGuideRateForProductionGroups(fieldGroup, schedule(), phase_usage_, reportStepIdx, simulationTime, this->wellState(), comm, guideRate_.get(), pot);
WellGroupHelpers::updateGuideRatesForInjectionGroups(fieldGroup, schedule(), summaryState, phase_usage_, reportStepIdx, well_state_, guideRate_.get(), local_deferredLogger); WellGroupHelpers::updateGuideRatesForInjectionGroups(fieldGroup, schedule(), summaryState, phase_usage_, reportStepIdx, this->wellState(), guideRate_.get(), local_deferredLogger);
WellGroupHelpers::updateGuideRatesForWells(schedule(), phase_usage_, reportStepIdx, simulationTime, well_state_, comm, guideRate_.get()); WellGroupHelpers::updateGuideRatesForWells(schedule(), phase_usage_, reportStepIdx, simulationTime, this->wellState(), comm, guideRate_.get());
try { try {
// Compute initial well solution for new wells and injectors that change injection type i.e. WAG. // Compute initial well solution for new wells and injectors that change injection type i.e. WAG.
@ -408,8 +408,8 @@ namespace Opm {
const bool event = report_step_starts_ && events.hasEvent(well->name(), effective_events_mask); const bool event = report_step_starts_ && events.hasEvent(well->name(), effective_events_mask);
if (event) { if (event) {
try { try {
well->calculateExplicitQuantities(ebosSimulator_, well_state_, local_deferredLogger); well->calculateExplicitQuantities(ebosSimulator_, this->wellState(), local_deferredLogger);
well->solveWellEquation(ebosSimulator_, well_state_, local_deferredLogger); well->solveWellEquation(ebosSimulator_, this->wellState(), local_deferredLogger);
} catch (const std::exception& e) { } catch (const std::exception& e) {
const std::string msg = "Compute initial well solution for new well " + well->name() + " failed. Continue with zero initial rates"; const std::string msg = "Compute initial well solution for new well " + well->name() + " failed. Continue with zero initial rates";
local_deferredLogger.warning("WELL_INITIAL_SOLVE_FAILED", msg); local_deferredLogger.warning("WELL_INITIAL_SOLVE_FAILED", msg);
@ -483,7 +483,7 @@ namespace Opm {
const WellTestConfig::Reason testing_reason = testWell.second; const WellTestConfig::Reason testing_reason = testWell.second;
well->wellTesting(ebosSimulator_, simulationTime, timeStepIdx, well->wellTesting(ebosSimulator_, simulationTime, timeStepIdx,
testing_reason, well_state_, wellTestState_, deferred_logger); testing_reason, this->wellState(), wellTestState_, deferred_logger);
} }
} }
} }
@ -534,7 +534,7 @@ namespace Opm {
Opm::DeferredLogger local_deferredLogger; Opm::DeferredLogger local_deferredLogger;
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
if (getPropValue<TypeTag, Properties::EnablePolymerMW>() && well->isInjector()) { if (getPropValue<TypeTag, Properties::EnablePolymerMW>() && well->isInjector()) {
well->updateWaterThroughput(dt, well_state_); well->updateWaterThroughput(dt, this->wellState());
} }
} }
updateWellTestState(simulationTime, wellTestState_); updateWellTestState(simulationTime, wellTestState_);
@ -554,11 +554,11 @@ namespace Opm {
// check group sales limits at the end of the timestep // check group sales limits at the end of the timestep
const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx); const Group& fieldGroup = schedule().getGroup("FIELD", reportStepIdx);
checkGconsaleLimits(fieldGroup, well_state_, local_deferredLogger); checkGconsaleLimits(fieldGroup, this->wellState(), local_deferredLogger);
this->calculateProductivityIndexValues(local_deferredLogger); this->calculateProductivityIndexValues(local_deferredLogger);
previous_well_state_ = well_state_; this->commitWellState();
Opm::DeferredLogger global_deferredLogger = gatherDeferredLogger(local_deferredLogger); Opm::DeferredLogger global_deferredLogger = gatherDeferredLogger(local_deferredLogger);
if (terminal_output_) { if (terminal_output_) {
@ -629,12 +629,11 @@ namespace Opm {
const auto phaseUsage = phaseUsageFromDeck(eclState()); const auto phaseUsage = phaseUsageFromDeck(eclState());
const size_t numCells = Opm::UgGridHelpers::numCells(grid()); const size_t numCells = Opm::UgGridHelpers::numCells(grid());
const bool handle_ms_well = (param_.use_multisegment_well_ && anyMSWellOpenLocal()); const bool handle_ms_well = (param_.use_multisegment_well_ && anyMSWellOpenLocal());
well_state_.resize(wells_ecl_, local_parallel_well_info_, schedule(), handle_ms_well, numCells, phaseUsage, well_perf_data_, summaryState, globalNumWells); // Resize for restart step this->wellState().resize(wells_ecl_, local_parallel_well_info_, schedule(), handle_ms_well, numCells, phaseUsage, well_perf_data_, summaryState, globalNumWells); // Resize for restart step
wellsToState(restartValues.wells, restartValues.grp_nwrk, phaseUsage, handle_ms_well, well_state_); wellsToState(restartValues.wells, restartValues.grp_nwrk, phaseUsage, handle_ms_well, this->wellState());
} }
previous_well_state_ = well_state_; this->commitWellState();
initial_step_ = false; initial_step_ = false;
} }
@ -757,9 +756,9 @@ namespace Opm {
} }
} }
well_state_.init(cellPressures, schedule(), wells_ecl_, local_parallel_well_info_, timeStepIdx, this->wellState().init(cellPressures, schedule(), wells_ecl_, local_parallel_well_info_, timeStepIdx,
&previous_well_state_, phase_usage_, well_perf_data_, &this->prevWellState(), phase_usage_, well_perf_data_,
summaryState, globalNumWells); summaryState, globalNumWells);
} }
@ -792,7 +791,7 @@ namespace Opm {
// Due to ACTIONX the well might have been closed behind our back. // Due to ACTIONX the well might have been closed behind our back.
if (well_ecl.getStatus() != Well::Status::SHUT) { if (well_ecl.getStatus() != Well::Status::SHUT) {
this->closed_this_step_.insert(well_name); this->closed_this_step_.insert(well_name);
well_state_.shutWell(w); this->wellState().shutWell(w);
} }
continue; continue;
@ -802,13 +801,13 @@ namespace Opm {
if (this->wellTestState_.hasWellClosed(well_name)) { if (this->wellTestState_.hasWellClosed(well_name)) {
// TODO: more checking here, to make sure this standard more specific and complete // TODO: more checking here, to make sure this standard more specific and complete
// maybe there is some WCON keywords will not open the well // maybe there is some WCON keywords will not open the well
if (well_state_.effectiveEventsOccurred(w)) { if (this->wellState().effectiveEventsOccurred(w)) {
if (wellTestState_.lastTestTime(well_name) == ebosSimulator_.time()) { if (wellTestState_.lastTestTime(well_name) == ebosSimulator_.time()) {
// The well was shut this timestep, we are most likely retrying // The well was shut this timestep, we are most likely retrying
// a timestep without the well in question, after it caused // a timestep without the well in question, after it caused
// repeated timestep cuts. It should therefore not be opened, // repeated timestep cuts. It should therefore not be opened,
// even if it was new or received new targets this report step. // even if it was new or received new targets this report step.
well_state_.setEffectiveEventsOccurred(w, false); this->wellState().setEffectiveEventsOccurred(w, false);
} else { } else {
wellTestState_.openWell(well_name); wellTestState_.openWell(well_name);
} }
@ -823,11 +822,11 @@ namespace Opm {
{ {
if (well_ecl.getAutomaticShutIn()) { if (well_ecl.getAutomaticShutIn()) {
// shut wells are not added to the well container // shut wells are not added to the well container
well_state_.shutWell(w); this->wellState().shutWell(w);
continue; continue;
} else { } else {
// stopped wells are added to the container but marked as stopped // stopped wells are added to the container but marked as stopped
well_state_.stopWell(w); this->wellState().stopWell(w);
wellIsStopped = true; wellIsStopped = true;
} }
} }
@ -874,13 +873,13 @@ namespace Opm {
if (zero_rate_control) { if (zero_rate_control) {
// Treat as shut, do not add to container. // Treat as shut, do not add to container.
local_deferredLogger.info(" Well shut due to zero rate control and disallowing crossflow: " + well_ecl.name()); local_deferredLogger.info(" Well shut due to zero rate control and disallowing crossflow: " + well_ecl.name());
well_state_.shutWell(w); this->wellState().shutWell(w);
continue; continue;
} }
} }
if (well_status == Well::Status::STOP) { if (well_status == Well::Status::STOP) {
well_state_.stopWell(w); this->wellState().stopWell(w);
wellIsStopped = true; wellIsStopped = true;
} }
@ -948,7 +947,7 @@ namespace Opm {
this->numComponents(), this->numComponents(),
this->numPhases(), this->numPhases(),
wellID, wellID,
this->well_state_.firstPerfIndex()[wellID], this->wellState().firstPerfIndex()[wellID],
perf_data); perf_data);
} }
@ -1021,15 +1020,15 @@ namespace Opm {
if (param_.solve_welleq_initially_ && iterationIdx == 0) { if (param_.solve_welleq_initially_ && iterationIdx == 0) {
for (auto& well : well_container_) { for (auto& well : well_container_) {
well->solveWellEquation(ebosSimulator_, well_state_, local_deferredLogger); well->solveWellEquation(ebosSimulator_, this->wellState(), local_deferredLogger);
} }
updateWellControls(local_deferredLogger, /* check group controls */ false); updateWellControls(local_deferredLogger, /* check group controls */ false);
} }
gliftDebug("assemble() : running assembleWellEq()..", local_deferredLogger); gliftDebug("assemble() : running assembleWellEq()..", local_deferredLogger);
well_state_.enableGliftOptimization(); this->wellState().enableGliftOptimization();
assembleWellEq(dt, local_deferredLogger); assembleWellEq(dt, local_deferredLogger);
well_state_.disableGliftOptimization(); this->wellState().disableGliftOptimization();
} catch (const std::runtime_error& e) { } catch (const std::runtime_error& e) {
exc_type = ExceptionType::RUNTIME_ERROR; exc_type = ExceptionType::RUNTIME_ERROR;
exc_msg = e.what(); exc_msg = e.what();
@ -1054,9 +1053,8 @@ namespace Opm {
assembleWellEq(const double dt, Opm::DeferredLogger& deferred_logger) assembleWellEq(const double dt, Opm::DeferredLogger& deferred_logger)
{ {
for (auto& well : well_container_) { for (auto& well : well_container_) {
well->maybeDoGasLiftOptimization( well->maybeDoGasLiftOptimization(this->wellState(), ebosSimulator_, deferred_logger);
well_state_, ebosSimulator_, deferred_logger); well->assembleWellEq(ebosSimulator_, dt, this->wellState(), deferred_logger);
well->assembleWellEq(ebosSimulator_, dt, well_state_, deferred_logger);
} }
} }
@ -1167,7 +1165,7 @@ namespace Opm {
try { try {
if (localWellsActive()) { if (localWellsActive()) {
for (auto& well : well_container_) { for (auto& well : well_container_) {
well->recoverWellSolutionAndUpdateWellState(x, well_state_, local_deferredLogger); well->recoverWellSolutionAndUpdateWellState(x, this->wellState(), local_deferredLogger);
} }
} }
} catch (const std::runtime_error& e) { } catch (const std::runtime_error& e) {
@ -1251,7 +1249,7 @@ namespace Opm {
ConvergenceReport local_report; ConvergenceReport local_report;
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
if (well->isOperable() ) { if (well->isOperable() ) {
local_report += well->getWellConvergence(well_state_, B_avg, local_deferredLogger); local_report += well->getWellConvergence(this->wellState(), B_avg, local_deferredLogger);
} }
} }
Opm::DeferredLogger global_deferredLogger = gatherDeferredLogger(local_deferredLogger); Opm::DeferredLogger global_deferredLogger = gatherDeferredLogger(local_deferredLogger);
@ -1292,7 +1290,7 @@ namespace Opm {
{ {
// TODO: checking isOperable() ? // TODO: checking isOperable() ?
for (auto& well : well_container_) { for (auto& well : well_container_) {
well->calculateExplicitQuantities(ebosSimulator_, well_state_, deferred_logger); well->calculateExplicitQuantities(ebosSimulator_, this->wellState(), deferred_logger);
} }
} }
@ -1329,7 +1327,7 @@ namespace Opm {
// Check wells' group constraints and communicate. // Check wells' group constraints and communicate.
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Group; const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Group;
const bool changed = well->updateWellControl(ebosSimulator_, mode, well_state_, deferred_logger); const bool changed = well->updateWellControl(ebosSimulator_, mode, this->wellState(), deferred_logger);
if (changed) { if (changed) {
switched_wells.insert(well->name()); switched_wells.insert(well->name());
} }
@ -1343,7 +1341,7 @@ namespace Opm {
continue; continue;
} }
const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Individual; const auto mode = WellInterface<TypeTag>::IndividualOrGroup::Individual;
well->updateWellControl(ebosSimulator_, mode, well_state_, deferred_logger); well->updateWellControl(ebosSimulator_, mode, this->wellState(), deferred_logger);
} }
updateAndCommunicateGroupData(); updateAndCommunicateGroupData();
@ -1364,7 +1362,7 @@ namespace Opm {
return; return;
} }
node_pressures_ = WellGroupHelpers::computeNetworkPressures( node_pressures_ = WellGroupHelpers::computeNetworkPressures(
network, well_state_, *(vfp_properties_->getProd()), schedule(), reportStepIdx); network, this->wellState(), *(vfp_properties_->getProd()), schedule(), reportStepIdx);
// Set the thp limits of wells // Set the thp limits of wells
for (auto& well : well_container_) { for (auto& well : well_container_) {
@ -1398,42 +1396,44 @@ namespace Opm {
// This builds some necessary lookup structures, so it must be called // This builds some necessary lookup structures, so it must be called
// before we copy to well_state_nupcol_. // before we copy to well_state_nupcol_.
const auto& comm = ebosSimulator_.vanguard().grid().comm(); const auto& comm = ebosSimulator_.vanguard().grid().comm();
well_state_.updateGlobalIsGrup(schedule(), reportStepIdx, comm); this->wellState().updateGlobalIsGrup(schedule(), reportStepIdx, comm);
if (iterationIdx < nupcol) { if (iterationIdx < nupcol) {
well_state_nupcol_ = well_state_; this->updateNupcolWellState();
} }
auto& well_state = this->wellState();
const auto& well_state_nupcol = this->nupcolWellState();
const auto& summaryState = ebosSimulator_.vanguard().summaryState(); const auto& summaryState = ebosSimulator_.vanguard().summaryState();
// the group target reduction rates needs to be update since wells may have swicthed to/from GRUP control // the group target reduction rates needs to be update since wells may have swicthed to/from GRUP control
// Currently the group target reduction does not honor NUPCOL. TODO: is that true? // Currently the group target reduction does not honor NUPCOL. TODO: is that true?
std::vector<double> groupTargetReduction(numPhases(), 0.0); std::vector<double> groupTargetReduction(numPhases(), 0.0);
WellGroupHelpers::updateGroupTargetReduction(fieldGroup, schedule(), reportStepIdx, /*isInjector*/ false, phase_usage_, *guideRate_, well_state_nupcol_, well_state_, groupTargetReduction); WellGroupHelpers::updateGroupTargetReduction(fieldGroup, schedule(), reportStepIdx, /*isInjector*/ false, phase_usage_, *guideRate_, well_state_nupcol, well_state, groupTargetReduction);
std::vector<double> groupTargetReductionInj(numPhases(), 0.0); std::vector<double> groupTargetReductionInj(numPhases(), 0.0);
WellGroupHelpers::updateGroupTargetReduction(fieldGroup, schedule(), reportStepIdx, /*isInjector*/ true, phase_usage_, *guideRate_, well_state_nupcol_, well_state_, groupTargetReductionInj); WellGroupHelpers::updateGroupTargetReduction(fieldGroup, schedule(), reportStepIdx, /*isInjector*/ true, phase_usage_, *guideRate_, well_state_nupcol, well_state, groupTargetReductionInj);
WellGroupHelpers::updateREINForGroups(fieldGroup, schedule(), reportStepIdx, phase_usage_, summaryState, well_state_nupcol_, well_state_); WellGroupHelpers::updateREINForGroups(fieldGroup, schedule(), reportStepIdx, phase_usage_, summaryState, well_state_nupcol, well_state);
WellGroupHelpers::updateVREPForGroups(fieldGroup, schedule(), reportStepIdx, well_state_nupcol_, well_state_); WellGroupHelpers::updateVREPForGroups(fieldGroup, schedule(), reportStepIdx, well_state_nupcol, well_state);
WellGroupHelpers::updateReservoirRatesInjectionGroups(fieldGroup, schedule(), reportStepIdx, well_state_nupcol_, well_state_); WellGroupHelpers::updateReservoirRatesInjectionGroups(fieldGroup, schedule(), reportStepIdx, well_state_nupcol, well_state);
WellGroupHelpers::updateGroupProductionRates(fieldGroup, schedule(), reportStepIdx, well_state_nupcol_, well_state_); WellGroupHelpers::updateGroupProductionRates(fieldGroup, schedule(), reportStepIdx, well_state_nupcol, well_state);
// We use the rates from the privious time-step to reduce oscilations // We use the rates from the privious time-step to reduce oscilations
WellGroupHelpers::updateWellRates(fieldGroup, schedule(), reportStepIdx, previous_well_state_, well_state_); WellGroupHelpers::updateWellRates(fieldGroup, schedule(), reportStepIdx, this->prevWellState(), well_state);
// Set ALQ for off-process wells to zero // Set ALQ for off-process wells to zero
for (const auto& wname : schedule().wellNames(reportStepIdx)) { for (const auto& wname : schedule().wellNames(reportStepIdx)) {
const bool is_producer = schedule().getWell(wname, reportStepIdx).isProducer(); const bool is_producer = schedule().getWell(wname, reportStepIdx).isProducer();
const bool not_on_this_process = well_state_.wellMap().count(wname) == 0; const bool not_on_this_process = well_state.wellMap().count(wname) == 0;
if (is_producer && not_on_this_process) { if (is_producer && not_on_this_process) {
well_state_.setALQ(wname, 0.0); well_state.setALQ(wname, 0.0);
} }
} }
well_state_.communicateGroupRates(comm); well_state.communicateGroupRates(comm);
// compute wsolvent fraction for REIN wells // compute wsolvent fraction for REIN wells
updateWsolvent(fieldGroup, schedule(), reportStepIdx, well_state_nupcol_); updateWsolvent(fieldGroup, schedule(), reportStepIdx, well_state_nupcol);
} }
@ -1450,7 +1450,7 @@ namespace Opm {
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
const auto wasClosed = wellTestState.hasWellClosed(well->name()); const auto wasClosed = wellTestState.hasWellClosed(well->name());
well->updateWellTestState(well_state_, simulationTime, /*writeMessageToOPMLog=*/ true, wellTestState, local_deferredLogger); well->updateWellTestState(this->wellState(), simulationTime, /*writeMessageToOPMLog=*/ true, wellTestState, local_deferredLogger);
if (!wasClosed && wellTestState.hasWellClosed(well->name())) { if (!wasClosed && wellTestState.hasWellClosed(well->name())) {
this->closed_this_step_.insert(well->name()); this->closed_this_step_.insert(well->name());
@ -1475,7 +1475,7 @@ namespace Opm {
const int np = numPhases(); const int np = numPhases();
well_potentials.resize(nw * np, 0.0); well_potentials.resize(nw * np, 0.0);
auto well_state_copy = well_state_; auto well_state = this->wellState();
const Opm::SummaryConfig& summaryConfig = ebosSimulator_.vanguard().summaryConfig(); const Opm::SummaryConfig& summaryConfig = ebosSimulator_.vanguard().summaryConfig();
const bool write_restart_file = ebosSimulator_.vanguard().schedule().write_rst_file(reportStepIdx); const bool write_restart_file = ebosSimulator_.vanguard().schedule().write_rst_file(reportStepIdx);
@ -1494,7 +1494,7 @@ namespace Opm {
{ {
try { try {
std::vector<double> potentials; std::vector<double> potentials;
well->computeWellPotentials(ebosSimulator_, well_state_copy, potentials, deferred_logger); well->computeWellPotentials(ebosSimulator_, well_state, potentials, deferred_logger);
// putting the sucessfully calculated potentials to the well_potentials // putting the sucessfully calculated potentials to the well_potentials
for (int p = 0; p < np; ++p) { for (int p = 0; p < np; ++p) {
well_potentials[well->indexOfWell() * np + p] = std::abs(potentials[p]); well_potentials[well->indexOfWell() * np + p] = std::abs(potentials[p]);
@ -1519,7 +1519,7 @@ namespace Opm {
terminal_output_); terminal_output_);
// Store it in the well state // Store it in the well state
well_state_.wellPotentials() = well_potentials; this->wellState().wellPotentials() = well_potentials;
} }
@ -1540,7 +1540,7 @@ namespace Opm {
for (const auto& wellPtr : this->well_container_) { for (const auto& wellPtr : this->well_container_) {
wellPtr->updateProductivityIndex(this->ebosSimulator_, wellPtr->updateProductivityIndex(this->ebosSimulator_,
this->prod_index_calc_[wellPtr->indexOfWell()], this->prod_index_calc_[wellPtr->indexOfWell()],
this->well_state_, this->wellState(),
deferred_logger); deferred_logger);
} }
} }
@ -1558,15 +1558,15 @@ namespace Opm {
std::string exc_msg; std::string exc_msg;
try { try {
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
well->checkWellOperability(ebosSimulator_, well_state_, deferred_logger); well->checkWellOperability(ebosSimulator_, this->wellState(), deferred_logger);
} }
// since the controls are all updated, we should update well_state accordingly // since the controls are all updated, we should update well_state accordingly
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
const int w = well->indexOfWell(); const int w = well->indexOfWell();
if (!well->isOperable() ) continue; if (!well->isOperable() ) continue;
if (well_state_.effectiveEventsOccurred(w) ) { if (this->wellState().effectiveEventsOccurred(w) ) {
well->updateWellStateWithTarget(ebosSimulator_, well_state_, deferred_logger); well->updateWellStateWithTarget(ebosSimulator_, this->wellState(), deferred_logger);
} }
// there is no new well control change input within a report step, // there is no new well control change input within a report step,
@ -1575,8 +1575,8 @@ namespace Opm {
// we do not need to set it to false // we do not need to set it to false
// TODO: we should do this at the end of the time step in case we will need it within // TODO: we should do this at the end of the time step in case we will need it within
// this time step somewhere // this time step somewhere
if (well_state_.effectiveEventsOccurred(w) ) { if (this->wellState().effectiveEventsOccurred(w) ) {
well_state_.setEffectiveEventsOccurred(w, false); this->wellState().setEffectiveEventsOccurred(w, false);
} }
} // end of for (const auto& well : well_container_) } // end of for (const auto& well : well_container_)
updatePrimaryVariables(deferred_logger); updatePrimaryVariables(deferred_logger);
@ -1600,17 +1600,6 @@ namespace Opm {
template<typename TypeTag>
const typename BlackoilWellModel<TypeTag>::WellState&
BlackoilWellModel<TypeTag>::
wellState() const { return well_state_; }
template<typename TypeTag>
const typename BlackoilWellModel<TypeTag>::WellState&
BlackoilWellModel<TypeTag>::
wellState(const WellState& well_state OPM_UNUSED) const { return wellState(); }
template<typename TypeTag> template<typename TypeTag>
void void
BlackoilWellModel<TypeTag>:: BlackoilWellModel<TypeTag>::
@ -1726,7 +1715,7 @@ namespace Opm {
updatePrimaryVariables(Opm::DeferredLogger& deferred_logger) updatePrimaryVariables(Opm::DeferredLogger& deferred_logger)
{ {
for (const auto& well : well_container_) { for (const auto& well : well_container_) {
well->updatePrimaryVariables(well_state_, deferred_logger); well->updatePrimaryVariables(this->wellState(), deferred_logger);
} }
} }
@ -2103,7 +2092,7 @@ namespace Opm {
const int reportStepIdx = ebosSimulator_.episodeIndex(); const int reportStepIdx = ebosSimulator_.episodeIndex();
const auto& summaryState = ebosSimulator_.vanguard().summaryState(); const auto& summaryState = ebosSimulator_.vanguard().summaryState();
const auto& comm = ebosSimulator_.vanguard().grid().comm(); const auto& comm = ebosSimulator_.vanguard().grid().comm();
const auto& well_state = well_state_; const auto& well_state = this->wellState();
const auto controls = group.productionControls(summaryState); const auto controls = group.productionControls(summaryState);
const Group::ProductionCMode& currentControl = well_state.currentProductionGroupControl(group.name()); const Group::ProductionCMode& currentControl = well_state.currentProductionGroupControl(group.name());
@ -2209,7 +2198,7 @@ namespace Opm {
const int reportStepIdx = ebosSimulator_.episodeIndex(); const int reportStepIdx = ebosSimulator_.episodeIndex();
const auto& summaryState = ebosSimulator_.vanguard().summaryState(); const auto& summaryState = ebosSimulator_.vanguard().summaryState();
const auto& comm = ebosSimulator_.vanguard().grid().comm(); const auto& comm = ebosSimulator_.vanguard().grid().comm();
const auto& well_state = well_state_; const auto& well_state = this->wellState();
int phasePos; int phasePos;
if (phase == Phase::GAS && phase_usage_.phase_used[BlackoilPhases::Vapour] ) if (phase == Phase::GAS && phase_usage_.phase_used[BlackoilPhases::Vapour] )
@ -2429,7 +2418,7 @@ namespace Opm {
BlackoilWellModel<TypeTag>:: BlackoilWellModel<TypeTag>::
actionOnBrokenConstraints(const Group& group, const Group::ExceedAction& exceed_action, const Group::ProductionCMode& newControl, Opm::DeferredLogger& deferred_logger) { actionOnBrokenConstraints(const Group& group, const Group::ExceedAction& exceed_action, const Group::ProductionCMode& newControl, Opm::DeferredLogger& deferred_logger) {
auto& well_state = well_state_; auto& well_state = this->wellState();
const Group::ProductionCMode oldControl = well_state.currentProductionGroupControl(group.name()); const Group::ProductionCMode oldControl = well_state.currentProductionGroupControl(group.name());
std::ostringstream ss; std::ostringstream ss;
@ -2482,7 +2471,7 @@ namespace Opm {
void void
BlackoilWellModel<TypeTag>:: BlackoilWellModel<TypeTag>::
actionOnBrokenConstraints(const Group& group, const Group::InjectionCMode& newControl, const Phase& controlPhase, Opm::DeferredLogger& deferred_logger) { actionOnBrokenConstraints(const Group& group, const Group::InjectionCMode& newControl, const Phase& controlPhase, Opm::DeferredLogger& deferred_logger) {
auto& well_state = well_state_; auto& well_state = this->wellState();
const Group::InjectionCMode oldControl = well_state.currentInjectionGroupControl(controlPhase, group.name()); const Group::InjectionCMode oldControl = well_state.currentInjectionGroupControl(controlPhase, group.name());
std::ostringstream ss; std::ostringstream ss;
@ -2557,22 +2546,21 @@ namespace Opm {
if (!skip && group.isInjectionGroup()) { if (!skip && group.isInjectionGroup()) {
// Obtain rates for group. // Obtain rates for group.
for (int phasePos = 0; phasePos < phase_usage_.num_phases; ++phasePos) { for (int phasePos = 0; phasePos < phase_usage_.num_phases; ++phasePos) {
const double local_current_rate = WellGroupHelpers::sumWellRates( const double local_current_rate = WellGroupHelpers::sumWellRates(group, schedule(), this->wellState(), reportStepIdx, phasePos, /* isInjector */ true);
group, schedule(), well_state_, reportStepIdx, phasePos, /* isInjector */ true);
// Sum over all processes // Sum over all processes
rates[phasePos] = comm.sum(local_current_rate); rates[phasePos] = comm.sum(local_current_rate);
} }
const Phase all[] = { Phase::WATER, Phase::OIL, Phase::GAS }; const Phase all[] = { Phase::WATER, Phase::OIL, Phase::GAS };
for (Phase phase : all) { for (Phase phase : all) {
// Check higher up only if under individual (not FLD) control. // Check higher up only if under individual (not FLD) control.
const Group::InjectionCMode& currentControl = well_state_.currentInjectionGroupControl(phase, group.name()); const Group::InjectionCMode& currentControl = this->wellState().currentInjectionGroupControl(phase, group.name());
if (currentControl != Group::InjectionCMode::FLD) { if (currentControl != Group::InjectionCMode::FLD) {
const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx); const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx);
const std::pair<bool, double> changed = WellGroupHelpers::checkGroupConstraintsInj( const std::pair<bool, double> changed = WellGroupHelpers::checkGroupConstraintsInj(
group.name(), group.name(),
group.parent(), group.parent(),
parentGroup, parentGroup,
well_state_, this->wellState(),
reportStepIdx, reportStepIdx,
guideRate_.get(), guideRate_.get(),
rates.data(), rates.data(),
@ -2594,20 +2582,19 @@ namespace Opm {
if (!skip && group.isProductionGroup()) { if (!skip && group.isProductionGroup()) {
// Obtain rates for group. // Obtain rates for group.
for (int phasePos = 0; phasePos < phase_usage_.num_phases; ++phasePos) { for (int phasePos = 0; phasePos < phase_usage_.num_phases; ++phasePos) {
const double local_current_rate = WellGroupHelpers::sumWellRates( const double local_current_rate = WellGroupHelpers::sumWellRates(group, schedule(), this->wellState(), reportStepIdx, phasePos, /* isInjector */ false);
group, schedule(), well_state_, reportStepIdx, phasePos, /* isInjector */ false);
// Sum over all processes // Sum over all processes
rates[phasePos] = -comm.sum(local_current_rate); rates[phasePos] = -comm.sum(local_current_rate);
} }
// Check higher up only if under individual (not FLD) control. // Check higher up only if under individual (not FLD) control.
const Group::ProductionCMode& currentControl = well_state_.currentProductionGroupControl(group.name()); const Group::ProductionCMode& currentControl = this->wellState().currentProductionGroupControl(group.name());
if (currentControl != Group::ProductionCMode::FLD) { if (currentControl != Group::ProductionCMode::FLD) {
const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx); const Group& parentGroup = schedule().getGroup(group.parent(), reportStepIdx);
const std::pair<bool, double> changed = WellGroupHelpers::checkGroupConstraintsProd( const std::pair<bool, double> changed = WellGroupHelpers::checkGroupConstraintsProd(
group.name(), group.name(),
group.parent(), group.parent(),
parentGroup, parentGroup,
well_state_, this->wellState(),
reportStepIdx, reportStepIdx,
guideRate_.get(), guideRate_.get(),
rates.data(), rates.data(),
@ -2654,7 +2641,7 @@ namespace Opm {
} }
} }
this->well_state_.resetConnectionTransFactors(well_index, pd); this->wellState().resetConnectionTransFactors(well_index, pd);
this->prod_index_calc_[well_index].reInit(well); this->prod_index_calc_[well_index].reInit(well);
} }
@ -2691,7 +2678,7 @@ namespace Opm {
{ {
const auto& pu = this->phase_usage_; const auto& pu = this->phase_usage_;
const auto np = this->numPhases(); const auto np = this->numPhases();
const auto* pi = &this->well_state_.productivityIndex()[np*well_index + 0]; const auto* pi = &this->wellState().productivityIndex()[np*well_index + 0];
const auto preferred = this->wells_ecl_[well_index].getPreferredPhase(); const auto preferred = this->wells_ecl_[well_index].getPreferredPhase();
switch (preferred) { // Should really have LIQUID = OIL + WATER here too... switch (preferred) { // Should really have LIQUID = OIL + WATER here too...
@ -2789,8 +2776,8 @@ namespace Opm {
// Minimal well setup to compute PI/II values // Minimal well setup to compute PI/II values
{ {
auto saved_previous_well_state = this->previous_well_state_; auto saved_previous_well_state = this->prevWellState();
this->previous_well_state_ = this->well_state_; this->commitWellState();
well_container_ = createWellContainer(timeStepIdx); well_container_ = createWellContainer(timeStepIdx);
for (auto& well : well_container_) { for (auto& well : well_container_) {
@ -2803,7 +2790,7 @@ namespace Opm {
} }
this->calculateProductivityIndexValues(local_deferredLogger); this->calculateProductivityIndexValues(local_deferredLogger);
this->previous_well_state_ = std::move(saved_previous_well_state); this->commitWellState(std::move(saved_previous_well_state));
} }
const auto nw = this->numLocalWells(); const auto nw = this->numLocalWells();
@ -2998,7 +2985,7 @@ namespace Opm {
// group tree (FIELD group). // group tree (FIELD group).
for (const auto& wname : sched.wellNames(reportStepIdx)) { for (const auto& wname : sched.wellNames(reportStepIdx)) {
if (! (this->well_state_.hasWellRates(wname) && if (! (this->wellState().hasWellRates(wname) &&
this->guideRate_->has(wname))) this->guideRate_->has(wname)))
{ {
continue; continue;
@ -3080,22 +3067,19 @@ namespace Opm {
cgc.currentWaterInjectionConstraint = cgc.currentWaterInjectionConstraint =
::Opm::Group::InjectionCMode::NONE; ::Opm::Group::InjectionCMode::NONE;
if (this->well_state_.hasProductionGroupControl(gname)) { if (this->wellState().hasProductionGroupControl(gname)) {
cgc.currentProdConstraint = this->well_state_ cgc.currentProdConstraint = this->wellState().currentProductionGroupControl(gname);
.currentProductionGroupControl(gname);
} }
if ((grup_type == ::Opm::Group::GroupType::INJECTION) || if ((grup_type == ::Opm::Group::GroupType::INJECTION) ||
(grup_type == ::Opm::Group::GroupType::MIXED)) (grup_type == ::Opm::Group::GroupType::MIXED))
{ {
if (this->well_state_.hasInjectionGroupControl(::Opm::Phase::WATER, gname)) { if (this->wellState().hasInjectionGroupControl(::Opm::Phase::WATER, gname)) {
cgc.currentWaterInjectionConstraint = this->well_state_ cgc.currentWaterInjectionConstraint = this->wellState().currentInjectionGroupControl(::Opm::Phase::WATER, gname);
.currentInjectionGroupControl(::Opm::Phase::WATER, gname);
} }
if (this->well_state_.hasInjectionGroupControl(::Opm::Phase::GAS, gname)) { if (this->wellState().hasInjectionGroupControl(::Opm::Phase::GAS, gname)) {
cgc.currentGasInjectionConstraint = this->well_state_ cgc.currentGasInjectionConstraint = this->wellState().currentInjectionGroupControl(::Opm::Phase::GAS, gname);
.currentInjectionGroupControl(::Opm::Phase::GAS, gname);
} }
} }
} }
@ -3110,7 +3094,7 @@ namespace Opm {
assert (this->guideRate_ != nullptr); assert (this->guideRate_ != nullptr);
const auto& wname = well.name(); const auto& wname = well.name();
if (! this->well_state_.hasWellRates(wname)) { if (! this->wellState().hasWellRates(wname)) {
// No flow rates for 'wname' -- might be before well comes // No flow rates for 'wname' -- might be before well comes
// online (e.g., for the initial condition before simulation // online (e.g., for the initial condition before simulation
// starts). // starts).
@ -3123,7 +3107,7 @@ namespace Opm {
} }
const auto qs = WellGroupHelpers:: const auto qs = WellGroupHelpers::
getWellRateVector(this->well_state_, this->phase_usage_, wname); getWellRateVector(this->wellState(), this->phase_usage_, wname);
this->getGuideRateValues(qs, well.isInjector(), wname, grval); this->getGuideRateValues(qs, well.isInjector(), wname, grval);
@ -3161,7 +3145,7 @@ namespace Opm {
const auto& gname = group.name(); const auto& gname = group.name();
if ( ! this->well_state_.hasProductionGroupRates(gname)) { if ( ! this->wellState().hasProductionGroupRates(gname)) {
// No flow rates for production group 'gname' -- might be before group comes // No flow rates for production group 'gname' -- might be before group comes
// online (e.g., for the initial condition before simulation // online (e.g., for the initial condition before simulation
// starts). // starts).
@ -3173,8 +3157,7 @@ namespace Opm {
return grval; return grval;
} }
const auto qs = WellGroupHelpers:: const auto qs = WellGroupHelpers::getProductionGroupRateVector(this->wellState(), this->phase_usage_, gname);
getProductionGroupRateVector(this->well_state_, this->phase_usage_, gname);
const auto is_inj = false; // This procedure only applies to G*PGR. const auto is_inj = false; // This procedure only applies to G*PGR.
this->getGuideRateValues(qs, is_inj, gname, grval); this->getGuideRateValues(qs, is_inj, gname, grval);
@ -3273,7 +3256,7 @@ namespace Opm {
cellInternalEnergy = fs.enthalpy(phaseIdx).value() - fs.pressure(phaseIdx).value() / fs.density(phaseIdx).value(); cellInternalEnergy = fs.enthalpy(phaseIdx).value() - fs.pressure(phaseIdx).value() / fs.density(phaseIdx).value();
cellBinv = fs.invB(phaseIdx).value(); cellBinv = fs.invB(phaseIdx).value();
cellDensity = fs.density(phaseIdx).value(); cellDensity = fs.density(phaseIdx).value();
perfPhaseRate = well_state_.perfPhaseRates()[connpos + perf*np + phaseIdx ]; perfPhaseRate = this->wellState().perfPhaseRates()[connpos + perf*np + phaseIdx ];
weight_factor += cellDensity * perfPhaseRate/cellBinv * cellInternalEnergy/cellTemperatures; weight_factor += cellDensity * perfPhaseRate/cellBinv * cellInternalEnergy/cellTemperatures;
} }
total_weight += weight_factor; total_weight += weight_factor;
@ -3281,7 +3264,7 @@ namespace Opm {
} }
weighted_temperature = well_info.communication().sum(weighted_temperature); weighted_temperature = well_info.communication().sum(weighted_temperature);
total_weight = well_info.communication().sum(total_weight); total_weight = well_info.communication().sum(total_weight);
well_state_.temperature()[wellID] = weighted_temperature/total_weight; this->wellState().temperature()[wellID] = weighted_temperature/total_weight;
} }
} }
} // namespace Opm } // namespace Opm