32#ifndef EWOMS_BLACK_OIL_EXTBO_MODULE_HH
33#define EWOMS_BLACK_OIL_EXTBO_MODULE_HH
35#include <dune/common/fvector.hh>
37#include <opm/common/utility/gpuDecorators.hpp>
62template <class TypeTag, bool enableExtboV = getPropValue<TypeTag, Properties::EnableExtbo>()>
77 using Toolbox = MathToolbox<Evaluation>;
79 static constexpr unsigned zFractionIdx = Indices::zFractionIdx;
80 static constexpr unsigned contiZfracEqIdx = Indices::contiZfracEqIdx;
81 static constexpr unsigned enableExtbo = enableExtboV;
82 static constexpr unsigned numEq = getPropValue<TypeTag, Properties::NumEq>();
83 static constexpr unsigned gasPhaseIdx = FluidSystem::gasPhaseIdx;
84 static constexpr unsigned oilPhaseIdx = FluidSystem::oilPhaseIdx;
85 static constexpr bool blackoilConserveSurfaceVolume = getPropValue<TypeTag, Properties::BlackoilConserveSurfaceVolume>();
109 if constexpr (enableExtbo) {
110 return pvIdx == zFractionIdx;
129 return static_cast<Scalar
>(1.0);
134 if constexpr (enableExtbo) {
135 return eqIdx == contiZfracEqIdx;
142 static std::string
eqName([[maybe_unused]]
unsigned eqIdx)
146 return "conti^solvent";
149 static Scalar
eqWeight([[maybe_unused]]
unsigned eqIdx)
154 return static_cast<Scalar
>(1.0);
157 template <
class StorageType>
159 const IntensiveQuantities& intQuants)
161 using LhsEval =
typename StorageType::value_type;
163 if constexpr (enableExtbo) {
164 if constexpr (blackoilConserveSurfaceVolume) {
165 storage[contiZfracEqIdx] =
166 Toolbox::template decay<LhsEval>(intQuants.porosity()) *
167 Toolbox::template decay<LhsEval>(intQuants.yVolume()) *
168 Toolbox::template decay<LhsEval>(intQuants.fluidState().saturation(gasPhaseIdx)) *
169 Toolbox::template decay<LhsEval>(intQuants.fluidState().invB(gasPhaseIdx));
170 if (FluidSystem::enableDissolvedGas()) {
171 storage[contiZfracEqIdx] +=
172 Toolbox::template decay<LhsEval>(intQuants.porosity()) *
173 Toolbox::template decay<LhsEval>(intQuants.xVolume()) *
174 Toolbox::template decay<LhsEval>(intQuants.fluidState().Rs()) *
175 Toolbox::template decay<LhsEval>(intQuants.fluidState().saturation(oilPhaseIdx)) *
176 Toolbox::template decay<LhsEval>(intQuants.fluidState().invB(oilPhaseIdx));
181 const Scalar regWghtFactor = 1.0e-6;
182 storage[contiZfracEqIdx] +=
183 regWghtFactor* (1.0 - Toolbox::template decay<LhsEval>(intQuants.zFraction())) +
184 regWghtFactor*Toolbox::template decay<LhsEval>(intQuants.porosity()) *
185 Toolbox::template decay<LhsEval>(intQuants.fluidState().saturation(gasPhaseIdx)) *
186 Toolbox::template decay<LhsEval>(intQuants.fluidState().invB(gasPhaseIdx));
187 storage[contiZfracEqIdx - 1] += regWghtFactor*Toolbox::template decay<LhsEval>(intQuants.zFraction());
190 throw std::runtime_error(
"Only component conservation in terms of surface volumes is implemented. ");
196 [[maybe_unused]]
const ElementContext& elemCtx,
197 [[maybe_unused]]
unsigned scvfIdx,
198 [[maybe_unused]]
unsigned timeIdx)
200 if constexpr (enableExtbo) {
201 const auto& extQuants = elemCtx.extensiveQuantities(scvfIdx, timeIdx);
203 if constexpr (blackoilConserveSurfaceVolume) {
204 const unsigned inIdx = extQuants.interiorIndex();
206 const unsigned upIdxGas =
static_cast<unsigned>(extQuants.upstreamIndex(gasPhaseIdx));
207 const auto& upGas = elemCtx.intensiveQuantities(upIdxGas, timeIdx);
208 const auto& fsGas = upGas.fluidState();
209 if (upIdxGas == inIdx) {
210 flux[contiZfracEqIdx] =
211 extQuants.volumeFlux(gasPhaseIdx) *
213 fsGas.invB(gasPhaseIdx);
216 flux[contiZfracEqIdx] =
217 extQuants.volumeFlux(gasPhaseIdx) *
218 decay<Scalar>(upGas.yVolume()) *
219 decay<Scalar>(fsGas.invB(gasPhaseIdx));
221 if (FluidSystem::enableDissolvedGas()) {
222 const unsigned upIdxOil =
static_cast<unsigned>(extQuants.upstreamIndex(oilPhaseIdx));
223 const auto& upOil = elemCtx.intensiveQuantities(upIdxOil, timeIdx);
224 const auto& fsOil = upOil.fluidState();
225 if (upIdxOil == inIdx) {
226 flux[contiZfracEqIdx] +=
227 extQuants.volumeFlux(oilPhaseIdx) *
230 fsOil.invB(oilPhaseIdx);
233 flux[contiZfracEqIdx] +=
234 extQuants.volumeFlux(oilPhaseIdx) *
235 decay<Scalar>(upOil.xVolume()) *
236 decay<Scalar>(fsOil.Rs()) *
237 decay<Scalar>(fsOil.invB(oilPhaseIdx));
242 throw std::runtime_error(
"Only component conservation in terms of surface volumes is implemented. ");
253 if constexpr (enableExtbo) {
254 priVars[zFractionIdx] = zFraction;
262 const PrimaryVariables& oldPv,
263 const EqVector& delta)
265 if constexpr (enableExtbo) {
267 newPv[zFractionIdx] = oldPv[zFractionIdx] - delta[zFractionIdx];
280 return static_cast<Scalar
>(0.0);
289 return std::abs(Toolbox::scalarValue(resid[contiZfracEqIdx]));
292 template <
class DofEntity>
293 static void serializeEntity(
const Model& model, std::ostream& outstream,
const DofEntity& dof)
295 if constexpr (enableExtbo) {
296 const unsigned dofIdx = model.dofMapper().index(dof);
298 const PrimaryVariables& priVars = model.solution(0)[dofIdx];
299 outstream << priVars[zFractionIdx];
303 template <
class DofEntity>
306 if constexpr (enableExtbo) {
307 const unsigned dofIdx = model.dofMapper().index(dof);
309 PrimaryVariables& priVars0 = model.solution(0)[dofIdx];
310 PrimaryVariables& priVars1 = model.solution(1)[dofIdx];
312 instream >> priVars0[zFractionIdx];
315 priVars1 = priVars0[zFractionIdx];
319 template <
typename Value>
320 static Value
xVolume(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
321 {
return params_.X_[pvtRegionIdx].eval(z, pressure,
true); }
323 template <
typename Value>
324 static Value
yVolume(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
325 {
return params_.Y_[pvtRegionIdx].eval(z, pressure,
true); }
327 template <
typename Value>
328 static Value
pbubRs(
unsigned pvtRegionIdx,
const Value& z,
const Value&
rs)
329 {
return params_.PBUB_RS_[pvtRegionIdx].eval(z,
rs,
true); }
331 template <
typename Value>
332 static Value
pbubRv(
unsigned pvtRegionIdx,
const Value& z,
const Value&
rv)
333 {
return params_.PBUB_RV_[pvtRegionIdx].eval(z,
rv,
true); }
335 template <
typename Value>
336 static Value
oilViscosity(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
337 {
return params_.VISCO_[pvtRegionIdx].eval(z, pressure,
true); }
339 template <
typename Value>
340 static Value
gasViscosity(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
341 {
return params_.VISCG_[pvtRegionIdx].eval(z, pressure,
true); }
343 template <
typename Value>
344 static Value
bo(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
345 {
return params_.BO_[pvtRegionIdx].eval(z, pressure,
true); }
347 template <
typename Value>
348 static Value
bg(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
349 {
return params_.BG_[pvtRegionIdx].eval(z, pressure,
true); }
351 template <
typename Value>
352 static Value
rs(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
353 {
return params_.RS_[pvtRegionIdx].eval(z, pressure,
true); }
355 template <
typename Value>
356 static Value
rv(
unsigned pvtRegionIdx,
const Value& pressure,
const Value& z)
357 {
return params_.RV_[pvtRegionIdx].eval(z, pressure,
true); }
360 {
return params_.zReferenceDensity_[regionIdx]; }
362 static Scalar
zLim(
unsigned regionIdx)
363 {
return params_.zLim_[regionIdx]; }
365 template <
typename Value>
366 static Value
oilCmp(
unsigned pvtRegionIdx,
const Value& z)
367 {
return params_.oilCmp_[pvtRegionIdx].eval(z,
true); }
369 template <
typename Value>
370 static Value
gasCmp(
unsigned pvtRegionIdx,
const Value& z)
371 {
return params_.gasCmp_[pvtRegionIdx].eval(z,
true); }
377template <
class TypeTag,
bool enableExtboV>
378BlackOilExtboParams<typename BlackOilExtboModule<TypeTag, enableExtboV>::Scalar>
379BlackOilExtboModule<TypeTag, enableExtboV>::params_;
381template <
class TypeTag,
bool enableExtboV>
391template <
class TypeTag>
405 static constexpr int zFractionIdx = Indices::zFractionIdx;
406 static constexpr int oilPhaseIdx = FluidSystem::oilPhaseIdx;
407 static constexpr int gasPhaseIdx = FluidSystem::gasPhaseIdx;
419 zFractionUpdate_(elemCtx.primaryVars(dofIdx, timeIdx), timeIdx);
430 const unsigned pvtRegionIdx = priVars.pvtRegionIndex();
431 const auto& fs = asImp_().fluidState_;
433 zFraction_ = priVars.makeEvaluation(zFractionIdx, timeIdx);
435 oilViscosity_ = ExtboModule::oilViscosity(pvtRegionIdx, fs.pressure(oilPhaseIdx), zFraction_);
436 gasViscosity_ = ExtboModule::gasViscosity(pvtRegionIdx, fs.pressure(gasPhaseIdx), zFraction_);
438 bo_ = ExtboModule::bo(pvtRegionIdx, fs.pressure(oilPhaseIdx), zFraction_);
439 bg_ = ExtboModule::bg(pvtRegionIdx, fs.pressure(gasPhaseIdx), zFraction_);
441 bz_ = ExtboModule::bg(pvtRegionIdx, fs.pressure(oilPhaseIdx), Evaluation{0.99});
443 if (FluidSystem::enableDissolvedGas()) {
444 rs_ = ExtboModule::rs(pvtRegionIdx, fs.pressure(oilPhaseIdx), zFraction_);
450 if (FluidSystem::enableVaporizedOil()) {
451 rv_ = ExtboModule::rv(pvtRegionIdx, fs.pressure(gasPhaseIdx), zFraction_);
457 xVolume_ = ExtboModule::xVolume(pvtRegionIdx, fs.pressure(oilPhaseIdx), zFraction_);
458 yVolume_ = ExtboModule::yVolume(pvtRegionIdx, fs.pressure(oilPhaseIdx), zFraction_);
460 Evaluation pbub = fs.pressure(oilPhaseIdx);
462 if (priVars.primaryVarsMeaningWater() == PrimaryVariables::WaterMeaning::Sw) {
463 static const Scalar thresholdWaterFilledCell = 1.0 - 1e-6;
464 Scalar sw = priVars.makeEvaluation(Indices::waterSwitchIdx, timeIdx).value();
465 if (sw >= thresholdWaterFilledCell) {
470 if (priVars.primaryVarsMeaningGas() == PrimaryVariables::GasMeaning::Rs) {
471 rs_ = priVars.makeEvaluation(Indices::compositionSwitchIdx, timeIdx);
472 const Evaluation zLim = ExtboModule::zLim(pvtRegionIdx);
473 if (zFraction_ > zLim) {
474 pbub = ExtboModule::pbubRs(pvtRegionIdx, zLim, rs_);
476 pbub = ExtboModule::pbubRs(pvtRegionIdx, zFraction_, rs_);
478 bo_ = ExtboModule::bo(pvtRegionIdx, pbub, zFraction_) +
479 ExtboModule::oilCmp(pvtRegionIdx, zFraction_) * (fs.pressure(oilPhaseIdx) - pbub);
481 xVolume_ = ExtboModule::xVolume(pvtRegionIdx, pbub, zFraction_);
484 if (priVars.primaryVarsMeaningGas() == PrimaryVariables::GasMeaning::Rv) {
485 rv_ = priVars.makeEvaluation(Indices::compositionSwitchIdx, timeIdx);
486 const Evaluation rvsat = ExtboModule::rv(pvtRegionIdx, pbub, zFraction_);
487 bg_ = ExtboModule::bg(pvtRegionIdx, pbub, zFraction_) +
488 ExtboModule::gasCmp(pvtRegionIdx, zFraction_) * (rv_ - rvsat);
490 yVolume_ = ExtboModule::yVolume(pvtRegionIdx, pbub, zFraction_);
501 const auto& iq = asImp_();
502 auto& fs = asImp_().fluidState_;
504 const unsigned pvtRegionIdx = iq.pvtRegionIndex();
505 zRefDensity_ = ExtboModule::referenceDensity(pvtRegionIdx);
507 fs.setInvB(oilPhaseIdx, 1.0 / bo_);
508 fs.setInvB(gasPhaseIdx, 1.0 / bg_);
510 fs.setDensity(oilPhaseIdx,
511 fs.invB(oilPhaseIdx) *
512 (FluidSystem::referenceDensity(oilPhaseIdx, pvtRegionIdx) +
513 (1.0 - xVolume_) * fs.Rs() * FluidSystem::referenceDensity(gasPhaseIdx, pvtRegionIdx) +
514 xVolume_ * fs.Rs() * zRefDensity_));
515 fs.setDensity(gasPhaseIdx,
516 fs.invB(gasPhaseIdx) *
517 (FluidSystem::referenceDensity(gasPhaseIdx, pvtRegionIdx) *
518 (1.0 - yVolume_) + yVolume_* zRefDensity_ +
519 FluidSystem::referenceDensity(oilPhaseIdx, pvtRegionIdx) * fs.Rv()));
523 {
return zFraction_; }
532 {
return oilViscosity_; }
535 {
return gasViscosity_; }
537 const Evaluation&
bo()
const
540 const Evaluation&
bg()
const
543 const Evaluation&
rs()
const
546 const Evaluation&
rv()
const
550 {
return 1.0 / bz_; }
553 {
return zRefDensity_; }
557 {
return *
static_cast<Implementation*
>(
this); }
581template <
class TypeTag>
598 {
throw std::runtime_error(
"xVolume() called but extbo is disabled"); }
601 {
throw std::runtime_error(
"yVolume() called but extbo is disabled"); }
604 {
throw std::runtime_error(
"oilViscosity() called but extbo is disabled"); }
607 {
throw std::runtime_error(
"gasViscosity() called but extbo is disabled"); }
609 const Evaluation&
rs()
const
610 {
throw std::runtime_error(
"rs() called but extbo is disabled"); }
612 const Evaluation&
rv()
const
613 {
throw std::runtime_error(
"rv() called but extbo is disabled"); }
616 {
throw std::runtime_error(
"zPureInvFormationVolumeFactor() called but extbo is disabled"); }
619 {
throw std::runtime_error(
"zFraction() called but extbo is disabled"); }
622 {
throw std::runtime_error(
"zInverseFormationVolumeFactor() called but extbo is disabled"); }
625 {
throw std::runtime_error(
"zRefDensity() called but extbo is disabled"); }
635template <class TypeTag, bool enableExtboV = getPropValue<TypeTag, Properties::EnableExtbo>()>
640 Implementation& asImp_()
641 {
return *
static_cast<Implementation*
>(
this); }
644template <
class TypeTag>
Defines a type tags and some fundamental properties all models.
Contains the parameters required to extend the black-oil model by solvent component....
Declares the properties required by the black oil model.
Provides the solvent specific extensive quantities to the generic black-oil module's extensive quanti...
Definition: blackoilextbomodules.hh:637
const Evaluation & xVolume() const
Definition: blackoilextbomodules.hh:597
const Evaluation & rs() const
Definition: blackoilextbomodules.hh:609
const Evaluation & zInverseFormationVolumeFactor() const
Definition: blackoilextbomodules.hh:621
const Evaluation & zPureInvFormationVolumeFactor() const
Definition: blackoilextbomodules.hh:615
const Evaluation & oilViscosity() const
Definition: blackoilextbomodules.hh:603
void zFractionUpdate_(const ElementContext &, unsigned, unsigned)
Definition: blackoilextbomodules.hh:592
const Evaluation & zFraction() const
Definition: blackoilextbomodules.hh:618
void zPvtUpdate_()
Definition: blackoilextbomodules.hh:589
const Evaluation & rv() const
Definition: blackoilextbomodules.hh:612
const Evaluation & gasViscosity() const
Definition: blackoilextbomodules.hh:606
const Evaluation & yVolume() const
Definition: blackoilextbomodules.hh:600
Scalar zRefDensity() const
Definition: blackoilextbomodules.hh:624
void zFractionUpdate_(const ElementContext &elemCtx, unsigned dofIdx, unsigned timeIdx)
Compute extended pvt properties from table lookups.
Definition: blackoilextbomodules.hh:415
Evaluation xVolume_
Definition: blackoilextbomodules.hh:565
Evaluation bo_
Definition: blackoilextbomodules.hh:571
void zPvtUpdate_()
Re-compute face densities to account for zFraction dependency.
Definition: blackoilextbomodules.hh:499
const Evaluation & oilViscosity() const
Definition: blackoilextbomodules.hh:531
const Evaluation & xVolume() const
Definition: blackoilextbomodules.hh:525
const Evaluation & zFraction() const
Definition: blackoilextbomodules.hh:522
Scalar zRefDensity_
Definition: blackoilextbomodules.hh:578
void zFractionUpdate_(const PrimaryVariables &priVars, unsigned timeIdx)
Compute extended pvt properties from table lookups.
Definition: blackoilextbomodules.hh:427
const Evaluation & gasViscosity() const
Definition: blackoilextbomodules.hh:534
const Evaluation & yVolume() const
Definition: blackoilextbomodules.hh:528
Evaluation oilViscosity_
Definition: blackoilextbomodules.hh:569
const Evaluation & rv() const
Definition: blackoilextbomodules.hh:546
Evaluation bg_
Definition: blackoilextbomodules.hh:572
Evaluation bz_
Definition: blackoilextbomodules.hh:577
const Evaluation & bg() const
Definition: blackoilextbomodules.hh:540
Evaluation yVolume_
Definition: blackoilextbomodules.hh:566
Evaluation gasViscosity_
Definition: blackoilextbomodules.hh:570
Scalar zRefDensity() const
Definition: blackoilextbomodules.hh:552
const Evaluation & rs() const
Definition: blackoilextbomodules.hh:543
const Evaluation zPureInvFormationVolumeFactor() const
Definition: blackoilextbomodules.hh:549
Evaluation rs_
Definition: blackoilextbomodules.hh:573
const Evaluation & bo() const
Definition: blackoilextbomodules.hh:537
Implementation & asImp_()
Definition: blackoilextbomodules.hh:556
Evaluation rv_
Definition: blackoilextbomodules.hh:574
Evaluation zFraction_
Definition: blackoilextbomodules.hh:562
Provides the volumetric quantities required for the equations needed by the solvents extension of the...
Definition: blackoilextbomodules.hh:382
Contains the high level supplements required to extend the black oil model.
Definition: blackoilextbomodules.hh:64
static bool primaryVarApplies(unsigned pvIdx)
Definition: blackoilextbomodules.hh:107
static Scalar zLim(unsigned regionIdx)
Definition: blackoilextbomodules.hh:362
static Scalar computeResidualError(const EqVector &resid)
Return how much a residual is considered an error.
Definition: blackoilextbomodules.hh:286
static Value yVolume(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:324
static void updatePrimaryVars(PrimaryVariables &newPv, const PrimaryVariables &oldPv, const EqVector &delta)
Do a Newton-Raphson update the primary variables of the solvents.
Definition: blackoilextbomodules.hh:261
static Value gasViscosity(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:340
static std::string eqName(unsigned eqIdx)
Definition: blackoilextbomodules.hh:142
static bool eqApplies(unsigned eqIdx)
Definition: blackoilextbomodules.hh:132
static Value pbubRv(unsigned pvtRegionIdx, const Value &z, const Value &rv)
Definition: blackoilextbomodules.hh:332
static Scalar primaryVarWeight(unsigned pvIdx)
Definition: blackoilextbomodules.hh:124
static Value rs(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:352
static void registerOutputModules(Model &, Simulator &)
Register all solvent specific VTK and ECL output modules.
Definition: blackoilextbomodules.hh:103
static Scalar computeUpdateError(const PrimaryVariables &, const EqVector &)
Return how much a Newton-Raphson update is considered an error.
Definition: blackoilextbomodules.hh:274
static Value xVolume(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:320
static void serializeEntity(const Model &model, std::ostream &outstream, const DofEntity &dof)
Definition: blackoilextbomodules.hh:293
static void computeFlux(RateVector &flux, const ElementContext &elemCtx, unsigned scvfIdx, unsigned timeIdx)
Definition: blackoilextbomodules.hh:195
static void registerParameters()
Register all run-time parameters for the black-oil solvent module.
Definition: blackoilextbomodules.hh:97
static void deserializeEntity(Model &model, std::istream &instream, const DofEntity &dof)
Definition: blackoilextbomodules.hh:304
static std::string primaryVarName(unsigned pvIdx)
Definition: blackoilextbomodules.hh:117
static Value rv(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:356
static void setParams(BlackOilExtboParams< Scalar > &¶ms)
Set parameters.
Definition: blackoilextbomodules.hh:89
static Value pbubRs(unsigned pvtRegionIdx, const Value &z, const Value &rs)
Definition: blackoilextbomodules.hh:328
static Value oilCmp(unsigned pvtRegionIdx, const Value &z)
Definition: blackoilextbomodules.hh:366
static Scalar referenceDensity(unsigned regionIdx)
Definition: blackoilextbomodules.hh:359
static OPM_HOST_DEVICE void addStorage(StorageType &storage, const IntensiveQuantities &intQuants)
Definition: blackoilextbomodules.hh:158
static Value bg(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:348
static Value oilViscosity(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:336
static void assignPrimaryVars(PrimaryVariables &priVars, Scalar zFraction)
Assign the solvent specific primary variables to a PrimaryVariables object.
Definition: blackoilextbomodules.hh:250
static Scalar eqWeight(unsigned eqIdx)
Definition: blackoilextbomodules.hh:149
static Value bo(unsigned pvtRegionIdx, const Value &pressure, const Value &z)
Definition: blackoilextbomodules.hh:344
static Value gasCmp(unsigned pvtRegionIdx, const Value &z)
Definition: blackoilextbomodules.hh:370
Declare the properties used by the infrastructure code of the finite volume discretizations.
Definition: blackoilbioeffectsmodules.hh:45
typename Properties::Detail::GetPropImpl< TypeTag, Property >::type::type GetPropType
get the type alias defined in the property (equivalent to old macro GET_PROP_TYPE(....
Definition: propertysystem.hh:233
Struct holding the parameters for the BlackoilExtboModule class.
Definition: blackoilextboparams.hpp:47