Line data Source code
1 : //* This file is part of the MOOSE framework
2 : //* https://www.mooseframework.org
3 : //*
4 : //* All rights reserved, see COPYRIGHT for full restrictions
5 : //* https://github.com/idaholab/moose/blob/master/COPYRIGHT
6 : //*
7 : //* Licensed under LGPL 2.1, please see LICENSE for details
8 : //* https://www.gnu.org/licenses/lgpl-2.1.html
9 :
10 : #pragma once
11 :
12 : // initQpStatefulProperties() and computeQpProperties() are intentionally hidden
13 : // but some compilers generate ugly warnings
14 :
15 : #if defined(__clang__)
16 : #pragma clang diagnostic push
17 : #pragma clang diagnostic ignored "-Woverloaded-virtual"
18 : #elif defined(__GNUC__) || defined(__GNUG__)
19 : #pragma GCC diagnostic push
20 : #pragma GCC diagnostic ignored "-Woverloaded-virtual"
21 : #endif
22 :
23 : #include "KokkosMaterialBase.h"
24 : #include "KokkosDatum.h"
25 :
26 : #include "Coupleable.h"
27 : #include "MaterialPropertyInterface.h"
28 :
29 : namespace Moose::Kokkos
30 : {
31 :
32 : /**
33 : * The base class for a user to derive their own Kokkos materials.
34 : *
35 : * The user should define initQpStatefulProperties() and computeQpProperties() as inlined public
36 : * methods in their derived class (not virtual override). The signature of computeQpProperties()
37 : * expected to be defined in the derived class is as follows:
38 : *
39 : * @tparam Derived The object type
40 : * @param qp The local quadrature point index
41 : * @param datum The Datum object of the current thread
42 : *
43 : * template <typename Derived>
44 : * KOKKOS_FUNCTION void computeQpProperties(const unsigned int qp, Datum & datum) const;
45 : *
46 : * The signature of initQpStatefulProperties() can be found in the code below, and its definition in
47 : * the derived class is optional. If it is defined in the derived class, it will hide the default
48 : * definition in the base class.
49 : */
50 : class Material : public MaterialBase, public Coupleable, public MaterialPropertyInterface
51 : {
52 : public:
53 : static InputParameters validParams();
54 :
55 : /**
56 : * Constructor
57 : */
58 : Material(const InputParameters & parameters);
59 :
60 : /**
61 : * Copy constructor for parallel dispatch
62 : */
63 : Material(const Material & object);
64 :
65 : /**
66 : * Dispatch stateful material property initialization
67 : */
68 : virtual void initStatefulProperties(unsigned int) override;
69 : /**
70 : * Dispatch material property evaluation
71 : */
72 : virtual void computeProperties() override;
73 :
74 : /**
75 : * Default methods to prevent compile errors even when these methods were not defined in the
76 : * derived class
77 : */
78 : ///@{
79 : /**
80 : * Initialize stateful material properties on a quadrature point
81 : * @tparam Derived The object type
82 : * @param qp The local quadrature point index
83 : * @param datum The Datum object of the current thread
84 : */
85 : template <typename Derived>
86 0 : KOKKOS_FUNCTION void initQpStatefulProperties(const unsigned int /* qp */,
87 : Datum & /* datum */) const
88 : {
89 0 : ::Kokkos::abort(
90 : "Default initQpStatefulProperties() should never be called. Make sure you properly "
91 : "redefined this method in your class without typos.");
92 : }
93 : ///@}
94 :
95 : /**
96 : * Functions used to check if users have overriden the hook methods, whose calculations can be
97 : * skipped when not overriden
98 : * @returns The function pointer of the default hook method
99 : */
100 : ///@{
101 : template <typename Derived>
102 2056980 : static auto defaultInitStateful()
103 : {
104 2056980 : return &Material::initQpStatefulProperties<Derived>;
105 : }
106 : ///@}
107 :
108 : /**
109 : * The parallel computation entry functions called by Kokkos
110 : */
111 : ///@{
112 : template <typename Derived>
113 : KOKKOS_FUNCTION void operator()(ElementInit, const ThreadID tid, const Derived & material) const;
114 : template <typename Derived>
115 : KOKKOS_FUNCTION void operator()(SideInit, const ThreadID tid, const Derived & material) const;
116 : template <typename Derived>
117 : KOKKOS_FUNCTION void operator()(NeighborInit, const ThreadID tid, const Derived & material) const;
118 : template <typename Derived>
119 : KOKKOS_FUNCTION void
120 : operator()(ElementCompute, const ThreadID tid, const Derived & material) const;
121 : template <typename Derived>
122 : KOKKOS_FUNCTION void operator()(SideCompute, const ThreadID tid, const Derived & material) const;
123 : template <typename Derived>
124 : KOKKOS_FUNCTION void
125 : operator()(NeighborCompute, const ThreadID tid, const Derived & material) const;
126 : ///@}
127 :
128 : protected:
129 : /**
130 : * Override of the MaterialPropertyInterface function to perform additional checks and add
131 : * dependencies
132 : */
133 : void getKokkosMaterialPropertyHook(const std::string & prop_name_in,
134 : const unsigned int state) override final;
135 :
136 1085 : virtual void checkMaterialProperty(const std::string & name, const unsigned int state) override
137 : {
138 : // Avoid performing duplicate checks for triple block/face/neighbor materials
139 1085 : if (boundaryRestricted() || !_bnd)
140 373 : MaterialPropertyInterface::checkMaterialProperty(name, state);
141 1085 : }
142 :
143 2996 : virtual bool isBoundaryMaterial() const override { return _bnd; }
144 :
145 33745 : virtual const std::unordered_set<unsigned int> & getMatPropDependencies() const override
146 : {
147 33745 : return MaterialPropertyInterface::getMatPropDependencies();
148 : }
149 :
150 4724 : virtual const MaterialData & materialData() const override { return _material_data; }
151 5984 : virtual MaterialData & materialData() override { return _material_data; }
152 2642 : virtual MaterialDataType materialDataType() override { return _material_data_type; }
153 :
154 : /**
155 : * Flag whether the material is on faces
156 : */
157 : const bool _bnd;
158 : /**
159 : * Flag whether the material is on neighbor faces
160 : */
161 : const bool _neighbor;
162 :
163 : private:
164 : /**
165 : * Dummy members unused for Kokkos materials
166 : */
167 : ///@{
168 : const QBase * const & _qrule;
169 0 : virtual const QBase & qRule() const override { return *_qrule; }
170 : ///@}
171 : };
172 :
173 : template <typename Derived>
174 : KOKKOS_FUNCTION void
175 16504 : Material::operator()(ElementInit, const ThreadID tid, const Derived & material) const
176 : {
177 : // When constant option is subdomain, elem is an arbitrary element in each subdomain, and thus
178 : // datum is invalid
179 16504 : auto elem = kokkosElementID(tid);
180 :
181 16504 : Datum datum(elem, libMesh::invalid_uint, kokkosAssembly(), kokkosSystems());
182 :
183 16504 : const unsigned int num_qps = _constant_option == PropertyConstantOption::NONE ? datum.n_qps() : 1;
184 :
185 106236 : for (unsigned int qp = 0; qp < num_qps; ++qp)
186 89732 : material.template initQpStatefulProperties<Derived>(qp, datum);
187 16504 : }
188 :
189 : template <typename Derived>
190 : KOKKOS_FUNCTION void
191 410 : Material::operator()(SideInit, const ThreadID tid, const Derived & material) const
192 : {
193 410 : auto [elem, side] = kokkosElementSideID(tid);
194 :
195 410 : Datum datum(elem, side, kokkosAssembly(), kokkosSystems());
196 :
197 410 : const unsigned int num_qps = _constant_option == PropertyConstantOption::NONE ? datum.n_qps() : 1;
198 :
199 1520 : for (unsigned int qp = 0; qp < num_qps; ++qp)
200 1110 : material.template initQpStatefulProperties<Derived>(qp, datum);
201 410 : }
202 :
203 : template <typename Derived>
204 : KOKKOS_FUNCTION void
205 290 : Material::operator()(NeighborInit, const ThreadID tid, const Derived & material) const
206 : {
207 290 : auto [elem, side] = kokkosElementSideID(tid);
208 :
209 290 : Datum datum(elem, side, kokkosAssembly(), kokkosSystems());
210 :
211 290 : const unsigned int num_qps = _constant_option == PropertyConstantOption::NONE ? datum.n_qps() : 1;
212 :
213 1160 : for (unsigned int qp = 0; qp < num_qps; ++qp)
214 870 : material.template initQpStatefulProperties<Derived>(qp, datum);
215 290 : }
216 :
217 : template <typename Derived>
218 : KOKKOS_FUNCTION void
219 1248811 : Material::operator()(ElementCompute, const ThreadID tid, const Derived & material) const
220 : {
221 : // When constant option is subdomain, elem is an arbitrary element in each subdomain, and thus
222 : // datum is invalid
223 1248811 : auto elem = kokkosElementID(tid);
224 :
225 1248811 : Datum datum(elem, libMesh::invalid_uint, kokkosAssembly(), kokkosSystems());
226 :
227 1248811 : const unsigned int num_qps = _constant_option == PropertyConstantOption::NONE ? datum.n_qps() : 1;
228 :
229 7582068 : for (unsigned int qp = 0; qp < num_qps; ++qp)
230 6333257 : material.template computeQpProperties<Derived>(qp, datum);
231 1248811 : }
232 :
233 : template <typename Derived>
234 : KOKKOS_FUNCTION void
235 51400 : Material::operator()(SideCompute, const ThreadID tid, const Derived & material) const
236 : {
237 51400 : auto [elem, side] = kokkosElementSideID(tid);
238 :
239 51400 : Datum datum(elem, side, kokkosAssembly(), kokkosSystems());
240 :
241 51400 : const unsigned int num_qps = _constant_option == PropertyConstantOption::NONE ? datum.n_qps() : 1;
242 :
243 184490 : for (unsigned int qp = 0; qp < num_qps; ++qp)
244 133090 : material.template computeQpProperties<Derived>(qp, datum);
245 51400 : }
246 :
247 : template <typename Derived>
248 : KOKKOS_FUNCTION void
249 46220 : Material::operator()(NeighborCompute, const ThreadID tid, const Derived & material) const
250 : {
251 46220 : auto [elem, side] = kokkosElementSideID(tid);
252 :
253 46220 : Datum datum(elem, side, kokkosAssembly(), kokkosSystems());
254 :
255 46220 : const unsigned int num_qps = _constant_option == PropertyConstantOption::NONE ? datum.n_qps() : 1;
256 :
257 168950 : for (unsigned int qp = 0; qp < num_qps; ++qp)
258 122730 : material.template computeQpProperties<Derived>(qp, datum);
259 46220 : }
260 :
261 : } // namespace Moose::Kokkos
|