25 #ifndef FLOW_PROBLEM_TPSA_HPP 26 #define FLOW_PROBLEM_TPSA_HPP 28 #include <dune/common/fvector.hh> 30 #include <dune/grid/common/rangegenerators.hh> 32 #include <opm/common/OpmLog/OpmLog.hpp> 34 #include <opm/input/eclipse/EclipseState/Grid/FaceDir.hpp> 36 #include <opm/material/common/MathToolbox.hpp> 37 #include <opm/material/materialstates/MaterialStateTPSA.hpp> 39 #include <opm/models/io/vtktpsamodule.hpp> 40 #include <opm/models/tpsa/tpsabaseproperties.hpp> 41 #include <opm/models/tpsa/tpsamodel.hpp> 44 #include <opm/simulators/flow/FacePropertiesTPSA.hpp> 53 #include <fmt/format.h> 61 template <
class TypeTag>
79 enum { dimWorld = GridView::dimensionworld };
80 enum { enableMech = getPropValue<TypeTag, Properties::EnableMech>() };
81 enum { historySize = getPropValue<TypeTag, Properties::SolutionHistorySizeTPSA>() };
82 enum { numEq = getPropValue<TypeTag, Properties::NumEqTPSA>() };
83 enum { numPhases = FluidSystem::numPhases };
85 enum { contiRotEqIdx = Indices::contiRotEqIdx };
86 enum { contiSolidPresEqIdx = Indices::contiSolidPresEqIdx };
87 enum { solidPres0Idx = Indices::solidPres0Idx };
90 using DimVector = Dune::FieldVector<Scalar, dimWorld>;
92 using InitialMaterialState = MaterialStateTPSA<Scalar>;
93 using Toolbox = MathToolbox<Evaluation>;
104 : ParentType(simulator)
105 , faceProps_(simulator.vanguard().eclState(),
106 simulator.vanguard().gridView(),
107 simulator.vanguard().cartesianIndexMapper(),
108 simulator.vanguard().grid(),
109 simulator.vanguard().cellCentroids())
110 , geoMechModel_(simulator)
112 if constexpr(enableMech) {
117 const auto& mechSolver = simulator.vanguard().eclState().runspec().mechSolver();
118 if (!mechSolver.tpsa()) {
119 std::string msg =
"Simulator with Tpsa-geomechanics enabled compile time, but deck does not contain " 122 throw std::runtime_error(msg);
126 if (simulator.vanguard().eclState().aquifer().active()) {
127 OpmLog::warning(
"TPSA geomechanics does not handle numerical or analytical " 128 "aquifers, hence results may be inaccurate!");
133 const auto& mechSolver = simulator.vanguard().eclState().runspec().mechSolver();
134 if (mechSolver.tpsa()) {
135 std::string msg =
"TPSA keyword in deck, but Tpsa-geomechanics disabled compile-time!";
137 throw std::runtime_error(msg);
151 GeomechModel::registerParameters();
175 geoMechModel_.finishInit();
189 auto& uCur = geoMechModel_.solution(0);
193 ElementContext elemCtx(this->simulator());
194 for (
const auto& elem : elements(this->gridView())) {
196 if (elem.partitionType() != Dune::InteriorEntity) {
201 elemCtx.updateStencil(elem);
202 for (
unsigned dofIdx = 0; dofIdx < elemCtx.numPrimaryDof(0); ++dofIdx) {
203 const unsigned globalIdx = elemCtx.globalSpaceIndex(dofIdx, 0);
204 auto& priVars = uCur[globalIdx];
205 priVars.assignNaive(initialMaterialState_[globalIdx]);
206 priVars.checkDefined();
211 geoMechModel_.syncOverlap();
214 for (
unsigned timeIdx = 1; timeIdx < historySize; ++timeIdx) {
215 geoMechModel_.solution(timeIdx) = geoMechModel_.solution(0);
219 geoMechModel_.updateMaterialState(0);
228 Scalar avgSmodulus = 0.0;
229 const auto& gridView = this->gridView();
230 ElementContext elemCtx(this->simulator());
231 for(
const auto& elem: elements(gridView, Dune::Partitions::interior)) {
232 elemCtx.updatePrimaryStencil(elem);
233 int elemIdx = elemCtx.globalSpaceIndex(0, 0);
236 std::size_t numDof = this->model().numGridDof();
237 const auto& comm = this->simulator().vanguard().grid().comm();
238 avgSmodulus = comm.sum(avgSmodulus);
239 Scalar numTotalDof = comm.sum(numDof);
240 avgSmodulus /= numTotalDof;
241 avgSmodulus = std::sqrt(avgSmodulus);
243 for (
unsigned eqIdx = 0; eqIdx < numEq; ++eqIdx) {
244 if (eqIdx < contiRotEqIdx) {
245 geoMechModel_.setEqWeight(eqIdx, 1 / avgSmodulus);
248 geoMechModel_.setEqWeight(eqIdx, avgSmodulus);
263 if (this->nonTrivialBoundaryConditions()) {
264 geoMechModel_.linearizer().updateBoundaryConditionData();
280 std::pair<BCMECHType, Dune::FieldVector<Evaluation, 3>>
284 if (!this->nonTrivialBoundaryConditions()) {
285 return { BCMECHType::NONE, Dune::FieldVector<Evaluation, 3>{0.0, 0.0, 0.0} };
289 FaceDir::DirEnum dir = FaceDir::FromIntersectionIndex(directionId);
290 const auto& schedule = this->simulator().vanguard().schedule();
291 if (this->bcindex_(dir)[globalSpaceIdx] == 0 || schedule[this->episodeIndex()].bcprop.size() == 0) {
292 return { BCMECHType::NONE, Dune::FieldVector<Evaluation, 3>{0.0, 0.0, 0.0} };
296 const auto& bc = schedule[this->episodeIndex()].bcprop[this->bcindex_(dir)[globalSpaceIdx]];
297 if (bc.bcmechtype == BCMECHType::FREE) {
298 return { BCMECHType::FREE, Dune::FieldVector<Evaluation, 3>{0.0, 0.0, 0.0} };
301 return { bc.bcmechtype, Dune::FieldVector<Evaluation, 3>{0.0, 0.0, 0.0} };
314 void tpsaSource(Dune::FieldVector<Evaluation, numEq>& sourceTerm,
315 unsigned globalSpaceIdx,
321 const auto biot = this->
biotCoeff(globalSpaceIdx);
322 const auto lameParam = this->
lame(globalSpaceIdx);
324 const auto& iq = this->model().intensiveQuantities(globalSpaceIdx, timeIdx);
325 const auto& fs = iq.fluidState();
326 const auto pres = decay<Scalar>(fs.pressure(this->refPressurePhaseIdx_()));
327 const auto initPres = this->initialFluidState(globalSpaceIdx).pressure(this->refPressurePhaseIdx_());
329 auto sourceFromFlow = -biot / lameParam * (pres - initPres);
330 sourceTerm[contiSolidPresEqIdx] += sourceFromFlow;
345 assert (timeIdx <= historySize);
346 const auto solidPres = (timeIdx == 0) ?
347 decay<Scalar>( geoMechModel_.materialState(elementIdx, timeIdx).solidPressure()) :
348 geoMechModel_.solution(timeIdx)[elementIdx][solidPres0Idx];
349 const auto biot = this->
biotCoeff(elementIdx);
350 const auto lameParam = this->
lame(elementIdx);
352 return biot / lameParam * solidPres;
367 return faceProps_.
weightAverage(globalElemIdxIn, globalElemIdxOut);
389 Scalar
weightProduct(
unsigned globalElemIdxIn,
unsigned globalElemIdxOut)
const 391 return faceProps_.
weightProduct(globalElemIdxIn, globalElemIdxOut);
403 return faceProps_.
normalDistance(globalElemIdxIn, globalElemIdxOut);
427 return faceProps_.
cellFaceNormal(globalElemIdxIn, globalElemIdxOut);
460 const auto& mechSolver = this->simulator().vanguard().eclState().runspec().mechSolver();
461 return mechSolver.laggedScheme();
471 const auto& mechSolver = this->simulator().vanguard().eclState().runspec().mechSolver();
472 return mechSolver.fixedStressScheme();
482 return geoMechModel_;
492 return geoMechModel_;
502 const auto& mechSolver = this->simulator().vanguard().eclState().runspec().mechSolver();
503 return std::make_pair(mechSolver.fixedStressMinIter(), mechSolver.fixedStressMaxIter());
520 std::size_t numDof = this->model().numGridDof();
521 initialMaterialState_.resize(numDof);
522 for (std::size_t dofIdx = 0; dofIdx < numDof; ++dofIdx) {
523 auto& dofMaterialState = initialMaterialState_[dofIdx];
524 for (
unsigned dirIdx = 0; dirIdx < 3; ++dirIdx) {
525 dofMaterialState.setDisplacement(dirIdx, 0.0);
526 dofMaterialState.setRotation(dirIdx, 0.0);
528 dofMaterialState.setSolidPressure(0.0);
533 FaceProperties faceProps_;
534 GeomechModel geoMechModel_;
536 std::vector<Scalar> biotcoeff_;
537 std::vector<InitialMaterialState> initialMaterialState_;
Scalar weightAverage(unsigned globalElemIdxIn, unsigned globalElemIdxOut)
Direct access to average (half-)weight at interface between two elements.
Definition: FlowProblemTPSA.hpp:365
This problem simulates an input file given in the data format used by the commercial ECLiPSE simulato...
Definition: FlowProblemBlackoil.hpp:86
VTK output module for TPSA quantities.
Definition: vtktpsamodule.hpp:48
Scalar weightProduct(unsigned elemIdx1, unsigned elemIdx2) const
Product of weights at interface between two elements.
Definition: FacePropertiesTPSA_impl.hpp:343
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
bool laggedScheme() const
Flow-TPSA lagged coupling scheme activated?
Definition: FlowProblemTPSA.hpp:458
bool fixedStressScheme() const
Flow-TPSA fixed-stress coupling scheme activated?
Definition: FlowProblemTPSA.hpp:469
const DimVector & cellFaceNormalBoundary(unsigned globalElemIdxIn, unsigned boundaryFaceIdx) const
Direct access to face normal at the boundary.
Definition: FlowProblemTPSA.hpp:437
const Scalar shearModulus(unsigned elemIdx) const
Return shear modulus of an element.
Definition: FacePropertiesTPSA.hpp:77
Scalar shearModulus(unsigned globalElemIdx) const
Direct access to shear modulus in an element.
Definition: FlowProblemTPSA.hpp:448
void readInitalConditionsTPSA_()
Read initial conditions and generate material state for TPSA model.
Definition: FlowProblemTPSA.hpp:513
Cell face properties needed in TPSA equation calculations.
Definition: FacePropertiesTPSA.hpp:48
This file provides the infrastructure to retrieve run-time parameters.
void beginTimeStep() override
Called by the simulator before each time integration.
Definition: FlowProblemBlackoil.hpp:315
Scalar weightProduct(unsigned globalElemIdxIn, unsigned globalElemIdxOut) const
Direct access to product of weights at interface between two elements.
Definition: FlowProblemTPSA.hpp:389
std::pair< BCMECHType, Dune::FieldVector< Evaluation, 3 > > mechBoundaryCondition(const unsigned int globalSpaceIdx, const int directionId)
Organize mechanics boundary conditions.
Definition: FlowProblemTPSA.hpp:281
FlowProblemTPSA(Simulator &simulator)
Constructor.
Definition: FlowProblemTPSA.hpp:103
static void registerParameters()
Register runtime parameters.
Definition: vtktpsamodule.hpp:88
Scalar weightAverageBoundary(unsigned elemIdx1, unsigned boundaryFaceIdx) const
Average (half-)weight at boundary interface.
Definition: FacePropertiesTPSA_impl.hpp:329
Structs needed for tpfalinearizer and its gpuparams struct extracted to be defined in one place that ...
Definition: blackoilbioeffectsmodules.hh:45
void tpsaSource(Dune::FieldVector< Evaluation, numEq > &sourceTerm, unsigned globalSpaceIdx, unsigned timeIdx)
Set mechanics source term, in particular coupling terms.
Definition: FlowProblemTPSA.hpp:314
static void registerParameters()
Register runtime parameters.
Definition: FlowProblemTPSA.hpp:145
void finishInit()
Called by the Opm::Simulator in order to initialize the problem.
Definition: FlowProblemBlackoil.hpp:324
This problem simulates an input file given in the data format used by the commercial ECLiPSE simulato...
DimVector cellFaceNormal(unsigned elemIdx1, unsigned elemIdx2)
Cell face normal at interface between two elements.
Definition: FacePropertiesTPSA_impl.hpp:402
Scalar biotCoeff(const Context &context, unsigned spaceIdx, unsigned timeIdx) const
Definition: FlowProblem.hpp:765
GeomechModel & geoMechModel()
Get TPSA model.
Definition: FlowProblemTPSA.hpp:490
static void registerParameters()
Registers all available parameters for the problem and the model.
Definition: FlowProblemBlackoil.hpp:175
void beginTimeStep() override
Called by the simulator before each time integration.
Definition: FlowProblemTPSA.hpp:256
std::pair< int, int > fixedStressParameters() const
Get fixed-stress iteration parameters.
Definition: FlowProblemTPSA.hpp:500
Problem for Flow-TPSA coupled simulations.
Definition: FlowProblemTPSA.hpp:62
Scalar normalDistance(unsigned globalElemIdxIn, unsigned globalElemIdxOut) const
Direct access to normal distance between two elements.
Definition: FlowProblemTPSA.hpp:401
void initialSolutionApplied() override
Set initial solution for the problem.
Definition: FlowProblemTPSA.hpp:183
DimVector cellFaceNormal(unsigned globalElemIdxIn, unsigned globalElemIdxOut)
Direct access to face normal between two elements.
Definition: FlowProblemTPSA.hpp:425
Scalar weightAverage(unsigned elemIdx1, unsigned elemIdx2) const
Average (half-)weight at interface between two elements.
Definition: FacePropertiesTPSA_impl.hpp:304
void initialSolutionApplied() override
Callback used by the model to indicate that the initial solution has been determined for all degrees ...
Definition: FlowProblemBlackoil.hpp:635
Scalar normalDistanceBoundary(unsigned elemIdx1, unsigned boundaryFaceIdx) const
Distance to boundary interface.
Definition: FacePropertiesTPSA_impl.hpp:385
Scalar normalDistanceBoundary(unsigned globalElemIdxIn, unsigned boundaryFaceIdx) const
Direct access to normal distance at the boundary.
Definition: FlowProblemTPSA.hpp:413
Scalar lame(const Context &context, unsigned spaceIdx, unsigned timeIdx) const
Definition: FlowProblem.hpp:755
void finishInit()
Initialize the problem.
Definition: FlowProblemTPSA.hpp:160
Definition: CollectDataOnIORank.hpp:50
Scalar rockMechPoroChange(unsigned elementIdx, unsigned timeIdx) const
Pore volume change due to geomechanics.
Definition: FlowProblemTPSA.hpp:342
const GeomechModel & geoMechModel() const
Get TPSA model.
Definition: FlowProblemTPSA.hpp:480
Scalar weightAverageBoundary(unsigned globalElemIdxIn, unsigned boundaryFaceIdx) const
Direct access to normal distance at the boundary.
Definition: FlowProblemTPSA.hpp:377
Scalar normalDistance(unsigned elemIdx1, unsigned elemIdx2) const
Distance between two elements.
Definition: FacePropertiesTPSA_impl.hpp:371
void computeAndSetEqWeights_()
Compute weights to rescale the TPSA equations.
Definition: FlowProblemTPSA.hpp:225
void finishInit()
Compute TPSA face properties.
Definition: FacePropertiesTPSA_impl.hpp:96
const DimVector & cellFaceNormalBoundary(unsigned elemIdx1, unsigned boundaryFaceIdx) const
Cell face normal of boundary interface.
Definition: FacePropertiesTPSA_impl.hpp:424