Merge pull request #4347 from atgeirr/afr_well_assemble_separate

Implement functionality to add well source terms to the residual separately
This commit is contained in:
Bård Skaflestad 2023-03-31 11:10:01 +02:00 committed by GitHub
commit c52ab4ccd5
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 47 additions and 0 deletions

View File

@ -1784,6 +1784,7 @@ public:
OPM_TIMEBLOCK_LOCAL(eclProblemSource);
rate = 0.0;
// Add well contribution to source here.
wellModel_.computeTotalRatesForDof(rate, globalDofIdx);
// convert the source term from the total mass rate of the
@ -1795,6 +1796,14 @@ public:
assert(isfinite(rate[eqIdx]));
}
// Add non-well sources.
addToSourceDense(rate, globalDofIdx, timeIdx);
}
void addToSourceDense(RateVector& rate,
unsigned globalDofIdx,
unsigned timeIdx) const
{
if (enableAquifers_)
aquiferModel_.addToSource(rate, globalDofIdx, timeIdx);

View File

@ -274,6 +274,10 @@ namespace Opm {
void addWellContributions(SparseMatrixAdapter& jacobian) const;
// add source from wells to the reservoir matrix
void addReservoirSourceTerms(GlobalEqVector& residual,
std::vector<typename SparseMatrixAdapter::MatrixBlock*>& diagMatAddress) const;
// called at the beginning of a report step
void beginReportStep(const int time_step);

View File

@ -1249,6 +1249,35 @@ namespace Opm {
}
}
template <typename TypeTag>
void BlackoilWellModel<TypeTag>::
addReservoirSourceTerms(GlobalEqVector& residual,
std::vector<typename SparseMatrixAdapter::MatrixBlock*>& diagMatAddress) const
{
// NB this loop may write multiple times to the same element
// if a cell is perforated by more than one well, so it should
// not be OpenMP-parallelized.
for (const auto& well : well_container_) {
if (!well->isOperableAndSolvable() && !well->wellIsStopped()) {
continue;
}
const auto& cells = well->cells();
const auto& rates = well->connectionRates();
for (unsigned perfIdx = 0; perfIdx < rates.size(); ++perfIdx) {
unsigned cellIdx = cells[perfIdx];
auto rate = rates[perfIdx];
rate *= -1.0;
VectorBlockType res(0.0);
using MatrixBlockType = typename SparseMatrixAdapter::MatrixBlock;
MatrixBlockType bMat(0.0);
ebosSimulator_.model().linearizer().setResAndJacobi(res, bMat, rate);
residual[cellIdx] += res;
*diagMatAddress[cellIdx] += bMat;
}
}
}
template<typename TypeTag>
int
BlackoilWellModel<TypeTag>::

View File

@ -294,6 +294,11 @@ public:
const GroupState& group_state,
DeferredLogger& deferred_logger);
const std::vector<RateVector>& connectionRates() const
{
return connectionRates_;
}
protected:
// simulation parameters