GEOS
StatisticsKernel.hpp
Go to the documentation of this file.
1 /*
2  * ------------------------------------------------------------------------------------------------------------
3  * SPDX-License-Identifier: LGPL-2.1-only
4  *
5  * Copyright (c) 2016-2024 Lawrence Livermore National Security LLC
6  * Copyright (c) 2018-2024 Total, S.A
7  * Copyright (c) 2018-2024 The Board of Trustees of the Leland Stanford Junior University
8  * Copyright (c) 2023-2024 Chevron
9  * Copyright (c) 2019- GEOS/GEOSX Contributors
10  * All rights reserved
11  *
12  * See top level LICENSE, COPYRIGHT, CONTRIBUTORS, NOTICE, and ACKNOWLEDGEMENTS files for details.
13  * ------------------------------------------------------------------------------------------------------------
14  */
15 
20 #ifndef GEOS_PHYSICSSOLVERS_FLUIDFLOW_COMPOSITIONAL_STATISTICSKERNEL_HPP
21 #define GEOS_PHYSICSSOLVERS_FLUIDFLOW_COMPOSITIONAL_STATISTICSKERNEL_HPP
22 
23 #include "common/DataLayouts.hpp"
24 #include "common/DataTypes.hpp"
25 #include "common/GEOS_RAJA_Interface.hpp"
26 #include "constitutive/relativePermeability/layouts.hpp"
27 
28 
29 namespace geos
30 {
31 
32 namespace isothermalCompositionalMultiphaseBaseKernels
33 {
34 
35 /******************************** StatisticsKernel ********************************/
36 
38 {
39  template< typename POLICY >
40  static void
41  saveDeltaPressure( localIndex const size,
42  arrayView1d< real64 const > const & pres,
43  arrayView1d< real64 const > const & initPres,
44  arrayView1d< real64 > const & deltaPres )
45  {
46  forAll< parallelDevicePolicy<> >( size, [=] GEOS_HOST_DEVICE ( localIndex const ei )
47  {
48  deltaPres[ei] = pres[ei] - initPres[ei];
49  } );
50  }
51 
52  template< typename POLICY >
53  static void
54  launch( localIndex const size,
55  integer const numComps,
56  integer const numPhases,
57  real64 const relpermThreshold,
58  arrayView1d< integer const > const & elemGhostRank,
59  arrayView1d< real64 const > const & volume,
60  arrayView1d< real64 const > const & pres,
61  arrayView1d< real64 const > const & deltaPres,
62  arrayView1d< real64 const > const & temp,
63  arrayView1d< real64 const > const & refPorosity,
64  arrayView2d< real64 const > const & porosity,
70  real64 & minPres,
71  real64 & avgPresNumerator,
72  real64 & maxPres,
73  real64 & minDeltaPres,
74  real64 & maxDeltaPres,
75  real64 & minTemp,
76  real64 & avgTempNumerator,
77  real64 & maxTemp,
78  real64 & totalUncompactedPoreVol,
79  arrayView1d< real64 > const & phaseDynamicPoreVol,
80  arrayView1d< real64 > const & phaseMass,
81  arrayView1d< real64 > const & trappedPhaseMass,
82  arrayView1d< real64 > const & immobilePhaseMass,
83  arrayView2d< real64 > const & dissolvedComponentMass )
84  {
85  RAJA::ReduceMin< parallelDeviceReduce, real64 > subRegionMinPres( LvArray::NumericLimits< real64 >::max );
86  RAJA::ReduceSum< parallelDeviceReduce, real64 > subRegionAvgPresNumerator( 0.0 );
87  RAJA::ReduceMax< parallelDeviceReduce, real64 > subRegionMaxPres( -LvArray::NumericLimits< real64 >::max );
88  RAJA::ReduceMin< parallelDeviceReduce, real64 > subRegionMinDeltaPres( LvArray::NumericLimits< real64 >::max );
89  RAJA::ReduceMax< parallelDeviceReduce, real64 > subRegionMaxDeltaPres( -LvArray::NumericLimits< real64 >::max );
90  RAJA::ReduceMin< parallelDeviceReduce, real64 > subRegionMinTemp( LvArray::NumericLimits< real64 >::max );
91  RAJA::ReduceSum< parallelDeviceReduce, real64 > subRegionAvgTempNumerator( 0.0 );
92  RAJA::ReduceMax< parallelDeviceReduce, real64 > subRegionMaxTemp( 0.0 );
93  RAJA::ReduceSum< parallelDeviceReduce, real64 > subRegionTotalUncompactedPoreVol( 0.0 );
94 
95  // For this arrays phaseDynamicPoreVol, phaseMass, dissolvedComponentMass,
96  // using an array of ReduceSum leads to a formal parameter overflow in CUDA.
97  // As a workaround, we use a slice with RAJA::atomicAdd instead
98 
99  forAll< parallelDevicePolicy<> >( size, [numComps,
100  numPhases,
101  relpermThreshold,
102  elemGhostRank,
103  volume,
104  refPorosity,
105  porosity,
106  pres,
107  deltaPres,
108  temp,
109  phaseDensity,
110  phaseVolFrac,
111  phaseTrappedVolFrac,
112  phaseRelperm,
113  phaseCompFraction,
114  subRegionMinPres,
115  subRegionAvgPresNumerator,
116  subRegionMaxPres,
117  subRegionMinDeltaPres,
118  subRegionMaxDeltaPres,
119  subRegionMinTemp,
120  subRegionAvgTempNumerator,
121  subRegionMaxTemp,
122  subRegionTotalUncompactedPoreVol,
123  phaseDynamicPoreVol,
124  phaseMass,
125  trappedPhaseMass,
126  immobilePhaseMass,
127  dissolvedComponentMass] GEOS_HOST_DEVICE ( localIndex const ei )
128  {
129  if( elemGhostRank[ei] >= 0 )
130  {
131  return;
132  }
133 
134  // To match our "reference", we have to use reference porosity here, not the actual porosity when we compute averages
135  real64 const uncompactedPoreVol = volume[ei] * refPorosity[ei];
136  real64 const dynamicPoreVol = volume[ei] * porosity[ei][0];
137 
138  subRegionMinPres.min( pres[ei] );
139  subRegionAvgPresNumerator += uncompactedPoreVol * pres[ei];
140  subRegionMaxPres.max( pres[ei] );
141 
142  subRegionMaxDeltaPres.max( deltaPres[ei] );
143  subRegionMinDeltaPres.min( deltaPres[ei] );
144 
145  subRegionMinTemp.min( temp[ei] );
146  subRegionAvgTempNumerator += uncompactedPoreVol * temp[ei];
147  subRegionMaxTemp.max( temp[ei] );
148  subRegionTotalUncompactedPoreVol += uncompactedPoreVol;
149  for( integer ip = 0; ip < numPhases; ++ip )
150  {
151  real64 const elemPhaseVolume = dynamicPoreVol * phaseVolFrac[ei][ip];
152  real64 const elemPhaseMass = phaseDensity[ei][0][ip] * elemPhaseVolume;
153  real64 const elemTrappedPhaseMass = phaseDensity[ei][0][ip] * dynamicPoreVol * phaseTrappedVolFrac[ei][0][ip];
154  // RAJA::atomicAdd used here because we do not use ReduceSum here (for the reason explained above)
155  RAJA::atomicAdd( parallelDeviceAtomic{}, &phaseDynamicPoreVol[ip], elemPhaseVolume );
156  RAJA::atomicAdd( parallelDeviceAtomic{}, &phaseMass[ip], elemPhaseMass );
157  RAJA::atomicAdd( parallelDeviceAtomic{}, &trappedPhaseMass[ip], elemTrappedPhaseMass );
158  if( phaseRelperm[ei][0][ip] < relpermThreshold )
159  {
160  RAJA::atomicAdd( parallelDeviceAtomic{}, &immobilePhaseMass[ip], elemPhaseMass );
161  }
162  for( integer ic = 0; ic < numComps; ++ic )
163  {
164  // RAJA::atomicAdd used here because we do not use ReduceSum here (for the reason explained above)
165  RAJA::atomicAdd( parallelDeviceAtomic{}, &dissolvedComponentMass[ip][ic], phaseCompFraction[ei][0][ip][ic] * elemPhaseMass );
166  }
167  }
168 
169  } );
170 
171  minPres = subRegionMinPres.get();
172  avgPresNumerator = subRegionAvgPresNumerator.get();
173  maxPres = subRegionMaxPres.get();
174  minDeltaPres = subRegionMinDeltaPres.get();
175  maxDeltaPres = subRegionMaxDeltaPres.get();
176  minTemp = subRegionMinTemp.get();
177  avgTempNumerator = subRegionAvgTempNumerator.get();
178  maxTemp = subRegionMaxTemp.get();
179  totalUncompactedPoreVol = subRegionTotalUncompactedPoreVol.get();
180 
181  // dummy loop to bring data back to the CPU
182  forAll< serialPolicy >( 1, [phaseDynamicPoreVol, phaseMass, trappedPhaseMass, immobilePhaseMass, dissolvedComponentMass] ( localIndex const )
183  {
184  GEOS_UNUSED_VAR( phaseDynamicPoreVol, phaseMass, trappedPhaseMass, immobilePhaseMass, dissolvedComponentMass );
185  } );
186  }
187 };
188 
189 } // namespace isothermalCompositionalMultiphaseBaseKernels
190 
191 } // namespace geos
192 
193 
194 #endif //GEOS_PHYSICSSOLVERS_FLUIDFLOW_COMPOSITIONAL_STATISTICSKERNEL_HPP
#define GEOS_HOST_DEVICE
Marks a host-device function.
Definition: GeosxMacros.hpp:49
#define GEOS_UNUSED_VAR(...)
Mark an unused variable and silence compiler warnings.
Definition: GeosxMacros.hpp:84
ArrayView< T, 1 > arrayView1d
Alias for 1D array view.
Definition: DataTypes.hpp:180
double real64
64-bit floating point type.
Definition: DataTypes.hpp:99
GEOS_LOCALINDEX_TYPE localIndex
Local index type (for indexing objects within an MPI partition).
Definition: DataTypes.hpp:85
std::int32_t integer
Signed integer type.
Definition: DataTypes.hpp:82
ArrayView< T, 4, USD > arrayView4d
Alias for 4D array view.
Definition: DataTypes.hpp:228
ArrayView< T, 2, USD > arrayView2d
Alias for 2D array view.
Definition: DataTypes.hpp:196
ArrayView< T, 3, USD > arrayView3d
Alias for 3D array view.
Definition: DataTypes.hpp:212