Line data Source code
1 : //* This file is part of the MOOSE framework
2 : //* https://mooseframework.inl.gov
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 : #include "AuxiliarySystem.h"
11 : #include "FEProblem.h"
12 : #include "Factory.h"
13 : #include "AuxKernel.h"
14 : #include "AuxScalarKernel.h"
15 : #include "MaterialData.h"
16 : #include "Assembly.h"
17 : #include "GeometricSearchData.h"
18 : #include "ComputeNodalAuxVarsThread.h"
19 : #include "ComputeNodalAuxBcsThread.h"
20 : #include "ComputeElemAuxVarsThread.h"
21 : #include "ComputeElemAuxBcsThread.h"
22 : #include "ComputeMortarNodalAuxBndThread.h"
23 : #include "Parser.h"
24 : #include "TimeIntegrator.h"
25 : #include "Conversion.h"
26 :
27 : #include "libmesh/quadrature_gauss.h"
28 : #include "libmesh/node_range.h"
29 : #include "libmesh/numeric_vector.h"
30 : #include "libmesh/default_coupling.h"
31 : #include "libmesh/string_to_enum.h"
32 : #include "libmesh/fe_interface.h"
33 :
34 : // C++
35 : #include <cstring> // for "Jacobian" exception test
36 :
37 : using namespace libMesh;
38 :
39 : // AuxiliarySystem ////////
40 :
41 61700 : AuxiliarySystem::AuxiliarySystem(FEProblemBase & subproblem, const std::string & name)
42 : : SystemBase(subproblem, subproblem, name, Moose::VAR_AUXILIARY),
43 61700 : PerfGraphInterface(subproblem.getMooseApp().perfGraph(), "AuxiliarySystem"),
44 : LinearFVGradientInterface(static_cast<SystemBase &>(*this)),
45 61700 : _sys(subproblem.es().add_system<System>(name)),
46 61700 : _current_solution(_sys.current_local_solution.get()),
47 61700 : _aux_scalar_storage(_app.getExecuteOnEnum()),
48 61700 : _nodal_aux_storage(_app.getExecuteOnEnum()),
49 61700 : _mortar_nodal_aux_storage(_app.getExecuteOnEnum()),
50 61700 : _elemental_aux_storage(_app.getExecuteOnEnum()),
51 61700 : _nodal_vec_aux_storage(_app.getExecuteOnEnum()),
52 61700 : _elemental_vec_aux_storage(_app.getExecuteOnEnum()),
53 61700 : _nodal_array_aux_storage(_app.getExecuteOnEnum()),
54 137030 : _elemental_array_aux_storage(_app.getExecuteOnEnum())
55 : #ifdef MOOSE_KOKKOS_ENABLED
56 : ,
57 46634 : _kokkos_nodal_aux_storage(_app.getExecuteOnEnum()),
58 279804 : _kokkos_elemental_aux_storage(_app.getExecuteOnEnum())
59 : #endif
60 : {
61 61700 : _nodal_vars.resize(libMesh::n_threads());
62 61700 : _elem_vars.resize(libMesh::n_threads());
63 :
64 61700 : if (!_fe_problem.defaultGhosting())
65 : {
66 61627 : auto & dof_map = _sys.get_dof_map();
67 61627 : dof_map.remove_algebraic_ghosting_functor(dof_map.default_algebraic_ghosting());
68 61627 : dof_map.set_implicit_neighbor_dofs(false);
69 : }
70 61700 : }
71 :
72 58620 : AuxiliarySystem::~AuxiliarySystem() = default;
73 :
74 : void
75 59172 : AuxiliarySystem::initialSetup()
76 : {
77 295860 : TIME_SECTION("initialSetup", 3, "Initializing Auxiliary System");
78 :
79 59172 : SystemBase::initialSetup();
80 59172 : _current_solution = _sys.current_local_solution.get();
81 59172 : LinearFVGradientInterface::rebuildLinearFVGradientStorage();
82 :
83 124225 : for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
84 : {
85 65059 : _aux_scalar_storage.sort(tid);
86 65059 : _aux_scalar_storage.initialSetup(tid);
87 :
88 65059 : _nodal_aux_storage.sort(tid);
89 65059 : _nodal_aux_storage.initialSetup(tid);
90 :
91 65056 : _mortar_nodal_aux_storage.sort(tid);
92 65056 : _mortar_nodal_aux_storage.initialSetup(tid);
93 :
94 65056 : _nodal_vec_aux_storage.sort(tid);
95 65056 : _nodal_vec_aux_storage.initialSetup(tid);
96 :
97 65056 : _nodal_array_aux_storage.sort(tid);
98 65056 : _nodal_array_aux_storage.initialSetup(tid);
99 :
100 65056 : _elemental_aux_storage.sort(tid);
101 65056 : _elemental_aux_storage.initialSetup(tid);
102 :
103 65053 : _elemental_vec_aux_storage.sort(tid);
104 65053 : _elemental_vec_aux_storage.initialSetup(tid);
105 :
106 65053 : _elemental_array_aux_storage.sort(tid);
107 65053 : _elemental_array_aux_storage.initialSetup(tid);
108 : }
109 :
110 : #ifdef MOOSE_KOKKOS_ENABLED
111 44780 : _kokkos_nodal_aux_storage.sort(/*tid=*/0);
112 44780 : _kokkos_nodal_aux_storage.initialSetup(/*tid=*/0);
113 :
114 44780 : _kokkos_elemental_aux_storage.sort(/*tid=*/0);
115 44780 : _kokkos_elemental_aux_storage.initialSetup(/*tid=*/0);
116 : #endif
117 59166 : }
118 :
119 : void
120 3510 : AuxiliarySystem::reinit()
121 : {
122 3510 : _current_solution = _sys.current_local_solution.get();
123 3510 : LinearFVGradientInterface::rebuildLinearFVGradientStorage();
124 3510 : }
125 :
126 : void
127 265154 : AuxiliarySystem::timestepSetup()
128 : {
129 265154 : SystemBase::timestepSetup();
130 :
131 556673 : for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
132 : {
133 291519 : _aux_scalar_storage.timestepSetup(tid);
134 291519 : _nodal_aux_storage.timestepSetup(tid);
135 291519 : _mortar_nodal_aux_storage.timestepSetup(tid);
136 291519 : _nodal_vec_aux_storage.timestepSetup(tid);
137 291519 : _nodal_array_aux_storage.timestepSetup(tid);
138 291519 : _elemental_aux_storage.timestepSetup(tid);
139 291519 : _elemental_vec_aux_storage.timestepSetup(tid);
140 291519 : _elemental_array_aux_storage.timestepSetup(tid);
141 : }
142 :
143 : #ifdef MOOSE_KOKKOS_ENABLED
144 194430 : _kokkos_nodal_aux_storage.timestepSetup(/*tid=*/0);
145 194430 : _kokkos_elemental_aux_storage.timestepSetup(/*tid=*/0);
146 : #endif
147 265154 : }
148 :
149 : void
150 1760570 : AuxiliarySystem::customSetup(const ExecFlagType & exec_type)
151 : {
152 1760570 : SystemBase::customSetup(exec_type);
153 :
154 3697459 : for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
155 : {
156 1936889 : _aux_scalar_storage.customSetup(exec_type, tid);
157 1936889 : _nodal_aux_storage.customSetup(exec_type, tid);
158 1936889 : _mortar_nodal_aux_storage.customSetup(exec_type, tid);
159 1936889 : _nodal_vec_aux_storage.customSetup(exec_type, tid);
160 1936889 : _nodal_array_aux_storage.customSetup(exec_type, tid);
161 1936889 : _elemental_aux_storage.customSetup(exec_type, tid);
162 1936889 : _elemental_vec_aux_storage.customSetup(exec_type, tid);
163 1936889 : _elemental_array_aux_storage.customSetup(exec_type, tid);
164 : }
165 :
166 : #ifdef MOOSE_KOKKOS_ENABLED
167 1289041 : _kokkos_nodal_aux_storage.customSetup(exec_type, /*tid=*/0);
168 1289041 : _kokkos_elemental_aux_storage.customSetup(exec_type, /*tid=*/0);
169 : #endif
170 1760570 : }
171 :
172 : void
173 0 : AuxiliarySystem::subdomainSetup()
174 : {
175 0 : SystemBase::subdomainSetup();
176 :
177 0 : for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
178 : {
179 0 : _aux_scalar_storage.subdomainSetup(tid);
180 0 : _nodal_aux_storage.subdomainSetup(tid);
181 0 : _mortar_nodal_aux_storage.subdomainSetup(tid);
182 0 : _nodal_vec_aux_storage.subdomainSetup(tid);
183 0 : _nodal_array_aux_storage.subdomainSetup(tid);
184 0 : _elemental_aux_storage.subdomainSetup(tid);
185 0 : _elemental_vec_aux_storage.subdomainSetup(tid);
186 0 : _elemental_array_aux_storage.subdomainSetup(tid);
187 : }
188 0 : }
189 :
190 : void
191 499234 : AuxiliarySystem::jacobianSetup()
192 : {
193 499234 : SystemBase::jacobianSetup();
194 :
195 1048427 : for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
196 : {
197 549193 : _aux_scalar_storage.jacobianSetup(tid);
198 549193 : _nodal_aux_storage.jacobianSetup(tid);
199 549193 : _mortar_nodal_aux_storage.jacobianSetup(tid);
200 549193 : _nodal_vec_aux_storage.jacobianSetup(tid);
201 549193 : _nodal_array_aux_storage.jacobianSetup(tid);
202 549193 : _elemental_aux_storage.jacobianSetup(tid);
203 549193 : _elemental_vec_aux_storage.jacobianSetup(tid);
204 549193 : _elemental_array_aux_storage.jacobianSetup(tid);
205 : }
206 :
207 : #ifdef MOOSE_KOKKOS_ENABLED
208 363123 : _kokkos_nodal_aux_storage.jacobianSetup(/*tid=*/0);
209 363123 : _kokkos_elemental_aux_storage.jacobianSetup(/*tid=*/0);
210 : #endif
211 499234 : }
212 :
213 : void
214 3046677 : AuxiliarySystem::residualSetup()
215 : {
216 3046677 : SystemBase::residualSetup();
217 :
218 6402075 : for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
219 : {
220 3355398 : _aux_scalar_storage.residualSetup(tid);
221 3355398 : _nodal_aux_storage.residualSetup(tid);
222 3355398 : _mortar_nodal_aux_storage.residualSetup(tid);
223 3355398 : _nodal_vec_aux_storage.residualSetup(tid);
224 3355398 : _nodal_array_aux_storage.residualSetup(tid);
225 3355398 : _elemental_aux_storage.residualSetup(tid);
226 3355398 : _elemental_vec_aux_storage.residualSetup(tid);
227 3355398 : _elemental_array_aux_storage.residualSetup(tid);
228 : }
229 :
230 : #ifdef MOOSE_KOKKOS_ENABLED
231 2218200 : _kokkos_nodal_aux_storage.residualSetup(/*tid=*/0);
232 2218200 : _kokkos_elemental_aux_storage.residualSetup(/*tid=*/0);
233 : #endif
234 3046677 : }
235 :
236 : void
237 341467 : AuxiliarySystem::updateActive(THREAD_ID tid)
238 : {
239 341467 : _aux_scalar_storage.updateActive(tid);
240 341467 : _nodal_aux_storage.updateActive(tid);
241 341467 : _mortar_nodal_aux_storage.updateActive(tid);
242 341467 : _nodal_vec_aux_storage.updateActive(tid);
243 341467 : _nodal_array_aux_storage.updateActive(tid);
244 341467 : _elemental_aux_storage.updateActive(tid);
245 341467 : _elemental_vec_aux_storage.updateActive(tid);
246 341467 : _elemental_array_aux_storage.updateActive(tid);
247 :
248 : #ifdef MOOSE_KOKKOS_ENABLED
249 257716 : if (tid == 0)
250 : {
251 227466 : _kokkos_nodal_aux_storage.updateActive(/*tid=*/0);
252 227466 : _kokkos_elemental_aux_storage.updateActive(/*tid=*/0);
253 : }
254 : #endif
255 341467 : }
256 :
257 : void
258 93816 : AuxiliarySystem::addVariable(const std::string & var_type,
259 : const std::string & name,
260 : InputParameters & parameters)
261 : {
262 93816 : SystemBase::addVariable(var_type, name, parameters);
263 :
264 187632 : auto fe_type = FEType(Utility::string_to_enum<Order>(parameters.get<MooseEnum>("order")),
265 281448 : Utility::string_to_enum<FEFamily>(parameters.get<MooseEnum>("family")));
266 :
267 93816 : if (var_type == "MooseVariableScalar")
268 1585 : return;
269 :
270 193972 : for (THREAD_ID tid = 0; tid < libMesh::n_threads(); tid++)
271 : {
272 101741 : if (FEInterface::field_type(fe_type) == TYPE_VECTOR)
273 : {
274 388 : auto * var = _vars[tid].getActualFieldVariable<RealVectorValue>(name);
275 388 : if (var)
276 : {
277 388 : if (var->feType().family == LAGRANGE_VEC)
278 130 : _nodal_vars[tid].push_back(var);
279 : else
280 258 : _elem_vars[tid].push_back(var);
281 : }
282 : }
283 :
284 : else
285 : {
286 101353 : MooseVariableBase * var_base = _vars[tid].getVariable(name);
287 :
288 101353 : auto * const var = dynamic_cast<MooseVariableField<Real> *>(var_base);
289 :
290 101353 : if (var)
291 : {
292 100271 : if (var->feType().family == LAGRANGE)
293 36439 : _nodal_vars[tid].push_back(var);
294 : else
295 63832 : _elem_vars[tid].push_back(var);
296 : }
297 :
298 101353 : auto * const avar = dynamic_cast<MooseVariableField<RealEigenVector> *>(var_base);
299 :
300 101353 : if (avar)
301 : {
302 1082 : if (avar->feType().family == LAGRANGE)
303 495 : _nodal_vars[tid].push_back(avar);
304 : else
305 587 : _elem_vars[tid].push_back(avar);
306 : }
307 : }
308 : }
309 : }
310 :
311 : void
312 64427 : AuxiliarySystem::addKernel(const std::string & kernel_name,
313 : const std::string & name,
314 : InputParameters & parameters)
315 : {
316 134875 : for (THREAD_ID tid = 0; tid < libMesh::n_threads(); tid++)
317 : {
318 70559 : const auto & base = parameters.getBase();
319 70559 : if (base == "AuxKernel" || base == "Bounds")
320 : {
321 : std::shared_ptr<AuxKernel> kernel =
322 70149 : _factory.create<AuxKernel>(kernel_name, name, parameters, tid);
323 70056 : if (kernel->isNodal())
324 : {
325 22528 : if (kernel->isMortar())
326 78 : _mortar_nodal_aux_storage.addObject(kernel, tid);
327 : else
328 22450 : _nodal_aux_storage.addObject(kernel, tid);
329 : }
330 : else
331 47528 : _elemental_aux_storage.addObject(kernel, tid);
332 70053 : }
333 :
334 410 : else if (base == "VectorAuxKernel")
335 : {
336 : std::shared_ptr<VectorAuxKernel> kernel =
337 228 : _factory.create<VectorAuxKernel>(kernel_name, name, parameters, tid);
338 228 : if (kernel->isNodal())
339 : {
340 52 : if (kernel->isMortar())
341 0 : mooseError("Vector mortar aux kernels not yet implemented");
342 52 : _nodal_vec_aux_storage.addObject(kernel, tid);
343 : }
344 : else
345 176 : _elemental_vec_aux_storage.addObject(kernel, tid);
346 228 : }
347 :
348 182 : else if (base == "ArrayAuxKernel")
349 : {
350 : std::shared_ptr<ArrayAuxKernel> kernel =
351 182 : _factory.create<ArrayAuxKernel>(kernel_name, name, parameters, tid);
352 167 : if (kernel->isNodal())
353 : {
354 102 : if (kernel->isMortar())
355 0 : mooseError("Vector mortar aux kernels not yet implemented");
356 102 : _nodal_array_aux_storage.addObject(kernel, tid);
357 : }
358 : else
359 65 : _elemental_array_aux_storage.addObject(kernel, tid);
360 167 : }
361 : else
362 : mooseAssert(false,
363 : "Attempting to add AuxKernel of type '" + kernel_name + "' and name '" + name +
364 : "' to the auxiliary system with invalid _moose_base: " + base);
365 : }
366 64316 : }
367 :
368 : void
369 475 : AuxiliarySystem::addScalarKernel(const std::string & kernel_name,
370 : const std::string & name,
371 : InputParameters & parameters)
372 : {
373 990 : for (THREAD_ID tid = 0; tid < libMesh::n_threads(); tid++)
374 : {
375 : std::shared_ptr<AuxScalarKernel> kernel =
376 518 : _factory.create<AuxScalarKernel>(kernel_name, name, parameters, tid);
377 515 : _aux_scalar_storage.addObject(kernel, tid);
378 515 : }
379 472 : }
380 :
381 : void
382 374199079 : AuxiliarySystem::reinitElem(const Elem * /*elem*/, THREAD_ID tid)
383 : {
384 518824395 : for (auto * var : _nodal_vars[tid])
385 144625316 : var->computeElemValues();
386 :
387 519981520 : for (auto * var : _elem_vars[tid])
388 : {
389 145782441 : var->reinitAux();
390 145782441 : var->computeElemValues();
391 : }
392 374199079 : }
393 :
394 : void
395 9010437 : AuxiliarySystem::reinitElemFace(const Elem * /*elem*/, unsigned int /*side*/, THREAD_ID tid)
396 : {
397 11311488 : for (auto * var : _nodal_vars[tid])
398 2301051 : var->computeElemValuesFace();
399 :
400 14433878 : for (auto * var : _elem_vars[tid])
401 : {
402 5423441 : var->reinitAux();
403 5423441 : var->reinitAuxNeighbor();
404 5423441 : var->computeElemValuesFace();
405 : }
406 9010437 : }
407 :
408 : void
409 2082 : AuxiliarySystem::serializeSolution()
410 : {
411 4164 : if (_serialized_solution.get() &&
412 2082 : _sys.n_dofs() > 0) // libMesh does not like serializing of empty vectors
413 : {
414 2082 : if (!_serialized_solution->initialized() || _serialized_solution->size() != _sys.n_dofs())
415 : {
416 58 : _serialized_solution->clear();
417 58 : _serialized_solution->init(_sys.n_dofs(), false, SERIAL);
418 : }
419 :
420 2082 : solution().localize(*_serialized_solution);
421 : }
422 2082 : }
423 :
424 : void
425 5820643 : AuxiliarySystem::compute(ExecFlagType type)
426 : {
427 : // avoid division by dt which might be zero.
428 5820643 : if (_fe_problem.dt() > 0.)
429 9948782 : for (auto & ti : _time_integrators)
430 4963008 : ti->preStep();
431 :
432 : // We need to compute time derivatives every time each kind of the variables is finished, because:
433 : //
434 : // a) the user might want to use the aux variable value somewhere, thus we need to provide the
435 : // up-to-date value
436 : // b) time integration system works with the whole vectors of solutions, thus we cannot update
437 : // only a part of the vector
438 : //
439 :
440 5820643 : if (_vars[0].scalars().size() > 0)
441 : {
442 47856 : computeScalarVars(type);
443 : // compute time derivatives of scalar aux variables _after_ the values were updated
444 47856 : if (_fe_problem.dt() > 0.)
445 73914 : for (auto & ti : _time_integrators)
446 36957 : ti->computeTimeDerivatives();
447 : }
448 :
449 5820643 : if (_vars[0].fieldVariables().size() > 0)
450 : {
451 2039446 : computeNodalArrayVars(type);
452 2039446 : computeNodalVecVars(type);
453 2039446 : computeNodalVars(type);
454 2039444 : computeMortarNodalVars(type);
455 2039444 : computeElementalArrayVars(type);
456 2039444 : computeElementalVecVars(type);
457 2039444 : computeElementalVars(type);
458 :
459 : #ifdef MOOSE_KOKKOS_ENABLED
460 1490550 : kokkosCompute(type);
461 : #endif
462 :
463 2039413 : if (!_raw_grad_container.empty())
464 : {
465 0 : solution().close();
466 0 : _sys.update();
467 0 : computeGradients();
468 : }
469 :
470 : // compute time derivatives of nodal aux variables _after_ the values were updated
471 2039413 : if (_fe_problem.dt() > 0.)
472 3502441 : for (auto & ti : _time_integrators)
473 1734535 : ti->computeTimeDerivatives();
474 : }
475 :
476 5820610 : if (_serialized_solution.get())
477 2082 : serializeSolution();
478 5820610 : }
479 :
480 : std::set<std::string>
481 2813036 : AuxiliarySystem::getDependObjects(ExecFlagType type)
482 : {
483 2813036 : std::set<std::string> depend_objects;
484 :
485 : // Elemental AuxKernels
486 : {
487 : const std::vector<std::shared_ptr<AuxKernel>> & auxs =
488 2813036 : _elemental_aux_storage[type].getActiveObjects();
489 2951363 : for (const auto & aux : auxs)
490 : {
491 138327 : const std::set<UserObjectName> & uo = aux->getDependObjects();
492 138327 : depend_objects.insert(uo.begin(), uo.end());
493 : }
494 : }
495 :
496 : // Elemental VectorAuxKernels
497 : {
498 : const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
499 2813036 : _elemental_vec_aux_storage[type].getActiveObjects();
500 2813587 : for (const auto & aux : auxs)
501 : {
502 551 : const std::set<UserObjectName> & uo = aux->getDependObjects();
503 551 : depend_objects.insert(uo.begin(), uo.end());
504 : }
505 : }
506 :
507 : // Elemental ArrayAuxKernels
508 : {
509 : const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
510 2813036 : _elemental_array_aux_storage[type].getActiveObjects();
511 2813204 : for (const auto & aux : auxs)
512 : {
513 168 : const std::set<UserObjectName> & uo = aux->getDependObjects();
514 168 : depend_objects.insert(uo.begin(), uo.end());
515 : }
516 : }
517 :
518 : // Nodal AuxKernels
519 : {
520 : const std::vector<std::shared_ptr<AuxKernel>> & auxs =
521 2813036 : _nodal_aux_storage[type].getActiveObjects();
522 2881485 : for (const auto & aux : auxs)
523 : {
524 68449 : const std::set<UserObjectName> & uo = aux->getDependObjects();
525 68449 : depend_objects.insert(uo.begin(), uo.end());
526 : }
527 : }
528 :
529 : // Mortar Nodal AuxKernels
530 : {
531 : const std::vector<std::shared_ptr<AuxKernel>> & auxs =
532 2813036 : _mortar_nodal_aux_storage[type].getActiveObjects();
533 2813288 : for (const auto & aux : auxs)
534 : {
535 252 : const std::set<UserObjectName> & uo = aux->getDependObjects();
536 252 : depend_objects.insert(uo.begin(), uo.end());
537 : }
538 : }
539 :
540 : // Nodal VectorAuxKernels
541 : {
542 : const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
543 2813036 : _nodal_vec_aux_storage[type].getActiveObjects();
544 2813183 : for (const auto & aux : auxs)
545 : {
546 147 : const std::set<UserObjectName> & uo = aux->getDependObjects();
547 147 : depend_objects.insert(uo.begin(), uo.end());
548 : }
549 : }
550 :
551 : // Nodal ArrayAuxKernels
552 : {
553 : const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
554 2813036 : _nodal_array_aux_storage[type].getActiveObjects();
555 2813322 : for (const auto & aux : auxs)
556 : {
557 286 : const std::set<UserObjectName> & uo = aux->getDependObjects();
558 286 : depend_objects.insert(uo.begin(), uo.end());
559 : }
560 : }
561 :
562 : #ifdef MOOSE_KOKKOS_ENABLED
563 : // Kokkos NodalAuxKernels
564 : {
565 : const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
566 2423318 : _kokkos_nodal_aux_storage[type].getActiveObjects();
567 2424444 : for (const auto & aux : auxs)
568 : {
569 1126 : const std::set<UserObjectName> & uo = aux->getDependObjects();
570 1126 : depend_objects.insert(uo.begin(), uo.end());
571 : }
572 : }
573 :
574 : // Kokkos ElementalAuxKernels
575 : {
576 : const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
577 2423318 : _kokkos_elemental_aux_storage[type].getActiveObjects();
578 2424306 : for (const auto & aux : auxs)
579 : {
580 988 : const std::set<UserObjectName> & uo = aux->getDependObjects();
581 988 : depend_objects.insert(uo.begin(), uo.end());
582 : }
583 : }
584 : #endif
585 :
586 2813036 : return depend_objects;
587 0 : }
588 :
589 : std::set<std::string>
590 59311 : AuxiliarySystem::getDependObjects()
591 : {
592 59311 : std::set<std::string> depend_objects;
593 :
594 : // Elemental AuxKernels
595 : {
596 : const std::vector<std::shared_ptr<AuxKernel>> & auxs =
597 59311 : _elemental_aux_storage.getActiveObjects();
598 101194 : for (const auto & aux : auxs)
599 : {
600 41883 : const std::set<UserObjectName> & uo = aux->getDependObjects();
601 41883 : depend_objects.insert(uo.begin(), uo.end());
602 : }
603 : }
604 :
605 : // Elemental VectorAuxKernels
606 : {
607 : const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
608 59311 : _elemental_vec_aux_storage.getActiveObjects();
609 59475 : for (const auto & aux : auxs)
610 : {
611 164 : const std::set<UserObjectName> & uo = aux->getDependObjects();
612 164 : depend_objects.insert(uo.begin(), uo.end());
613 : }
614 : }
615 :
616 : // Elemental ArrayAuxKernels
617 : {
618 : const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
619 59311 : _elemental_array_aux_storage.getActiveObjects();
620 59371 : for (const auto & aux : auxs)
621 : {
622 60 : const std::set<UserObjectName> & uo = aux->getDependObjects();
623 60 : depend_objects.insert(uo.begin(), uo.end());
624 : }
625 : }
626 :
627 : // Nodal AuxKernels
628 : {
629 59311 : const std::vector<std::shared_ptr<AuxKernel>> & auxs = _nodal_aux_storage.getActiveObjects();
630 79876 : for (const auto & aux : auxs)
631 : {
632 20565 : const std::set<UserObjectName> & uo = aux->getDependObjects();
633 20565 : depend_objects.insert(uo.begin(), uo.end());
634 : }
635 : }
636 :
637 : // Mortar Nodal AuxKernels
638 : {
639 : const std::vector<std::shared_ptr<AuxKernel>> & auxs =
640 59311 : _mortar_nodal_aux_storage.getActiveObjects();
641 59383 : for (const auto & aux : auxs)
642 : {
643 72 : const std::set<UserObjectName> & uo = aux->getDependObjects();
644 72 : depend_objects.insert(uo.begin(), uo.end());
645 : }
646 : }
647 :
648 : // Nodal VectorAuxKernels
649 : {
650 : const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
651 59311 : _nodal_vec_aux_storage.getActiveObjects();
652 59359 : for (const auto & aux : auxs)
653 : {
654 48 : const std::set<UserObjectName> & uo = aux->getDependObjects();
655 48 : depend_objects.insert(uo.begin(), uo.end());
656 : }
657 : }
658 :
659 : // Nodal ArrayAuxKernels
660 : {
661 : const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
662 59311 : _nodal_array_aux_storage.getActiveObjects();
663 59405 : for (const auto & aux : auxs)
664 : {
665 94 : const std::set<UserObjectName> & uo = aux->getDependObjects();
666 94 : depend_objects.insert(uo.begin(), uo.end());
667 : }
668 : }
669 :
670 : #ifdef MOOSE_KOKKOS_ENABLED
671 : // Nodal KokkosAuxKernels
672 : {
673 : const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
674 44877 : _kokkos_nodal_aux_storage.getActiveObjects();
675 45217 : for (const auto & aux : auxs)
676 : {
677 340 : const std::set<UserObjectName> & uo = aux->getDependObjects();
678 340 : depend_objects.insert(uo.begin(), uo.end());
679 : }
680 : }
681 :
682 : // Elemental KokkosAuxKernels
683 : {
684 : const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
685 44877 : _kokkos_elemental_aux_storage.getActiveObjects();
686 45154 : for (const auto & aux : auxs)
687 : {
688 277 : const std::set<UserObjectName> & uo = aux->getDependObjects();
689 277 : depend_objects.insert(uo.begin(), uo.end());
690 : }
691 : }
692 : #endif
693 :
694 59311 : return depend_objects;
695 0 : }
696 :
697 : void
698 47856 : AuxiliarySystem::setScalarVariableCoupleableTags(ExecFlagType type)
699 : {
700 47856 : const MooseObjectWarehouse<AuxScalarKernel> & storage = _aux_scalar_storage[type];
701 47856 : const std::vector<std::shared_ptr<AuxScalarKernel>> & objects = storage.getActiveObjects(0);
702 :
703 47856 : std::set<TagID> needed_sc_var_matrix_tags;
704 47856 : std::set<TagID> needed_sc_var_vector_tags;
705 64571 : for (const auto & obj : objects)
706 : {
707 16715 : auto & sc_var_coup_vtags = obj->getScalarVariableCoupleableVectorTags();
708 16715 : needed_sc_var_vector_tags.insert(sc_var_coup_vtags.begin(), sc_var_coup_vtags.end());
709 :
710 16715 : auto & sc_var_coup_mtags = obj->getScalarVariableCoupleableMatrixTags();
711 16715 : needed_sc_var_matrix_tags.insert(sc_var_coup_mtags.begin(), sc_var_coup_mtags.end());
712 : }
713 :
714 47856 : _fe_problem.setActiveScalarVariableCoupleableMatrixTags(needed_sc_var_matrix_tags, 0);
715 47856 : _fe_problem.setActiveScalarVariableCoupleableVectorTags(needed_sc_var_vector_tags, 0);
716 47856 : }
717 :
718 : void
719 47856 : AuxiliarySystem::clearScalarVariableCoupleableTags()
720 : {
721 47856 : _fe_problem.clearActiveScalarVariableCoupleableMatrixTags(0);
722 47856 : _fe_problem.clearActiveScalarVariableCoupleableVectorTags(0);
723 47856 : }
724 :
725 : void
726 47856 : AuxiliarySystem::computeScalarVars(ExecFlagType type)
727 : {
728 47856 : setScalarVariableCoupleableTags(type);
729 :
730 : // Reference to the current storage container
731 47856 : const MooseObjectWarehouse<AuxScalarKernel> & storage = _aux_scalar_storage[type];
732 :
733 47856 : if (storage.hasActiveObjects())
734 : {
735 45696 : TIME_SECTION("computeScalarVars", 1);
736 :
737 : PARALLEL_TRY
738 : {
739 : // FIXME: run multi-threaded
740 15232 : THREAD_ID tid = 0;
741 15232 : if (storage.hasActiveObjects())
742 : {
743 15232 : _fe_problem.reinitScalars(tid);
744 :
745 : const std::vector<std::shared_ptr<AuxScalarKernel>> & objects =
746 15232 : storage.getActiveObjects(tid);
747 :
748 : // Call compute() method on all active AuxScalarKernel objects
749 31947 : for (const auto & obj : objects)
750 16715 : obj->compute();
751 :
752 15232 : const std::vector<MooseVariableScalar *> & scalar_vars = getScalarVariables(tid);
753 44410 : for (const auto & var : scalar_vars)
754 29178 : var->insert(solution());
755 : }
756 : }
757 15232 : PARALLEL_CATCH;
758 :
759 15232 : solution().close();
760 15232 : _sys.update();
761 15232 : }
762 :
763 47856 : clearScalarVariableCoupleableTags();
764 47856 : }
765 :
766 : void
767 2039446 : AuxiliarySystem::computeNodalVars(ExecFlagType type)
768 : {
769 6118338 : TIME_SECTION("computeNodalVars", 3);
770 :
771 2039446 : const MooseObjectWarehouse<AuxKernel> & nodal = _nodal_aux_storage[type];
772 2039446 : computeNodalVarsHelper<AuxKernel>(nodal);
773 2039444 : }
774 :
775 : void
776 2039446 : AuxiliarySystem::computeNodalVecVars(ExecFlagType type)
777 : {
778 6118338 : TIME_SECTION("computeNodalVecVars", 3);
779 :
780 2039446 : const MooseObjectWarehouse<VectorAuxKernel> & nodal = _nodal_vec_aux_storage[type];
781 2039446 : computeNodalVarsHelper<VectorAuxKernel>(nodal);
782 2039446 : }
783 :
784 : void
785 2039446 : AuxiliarySystem::computeNodalArrayVars(ExecFlagType type)
786 : {
787 2039446 : const MooseObjectWarehouse<ArrayAuxKernel> & nodal = _nodal_array_aux_storage[type];
788 2039446 : computeNodalVarsHelper<ArrayAuxKernel>(nodal);
789 2039446 : }
790 :
791 : void
792 2039444 : AuxiliarySystem::computeMortarNodalVars(const ExecFlagType type)
793 : {
794 6118332 : TIME_SECTION("computeMortarNodalVars", 3);
795 :
796 2039444 : const MooseObjectWarehouse<AuxKernel> & mortar_nodal_warehouse = _mortar_nodal_aux_storage[type];
797 :
798 : mooseAssert(!mortar_nodal_warehouse.hasActiveBlockObjects(),
799 : "We don't allow creation of block restricted mortar nodal aux kernels.");
800 :
801 2039444 : if (mortar_nodal_warehouse.hasActiveBoundaryObjects())
802 : {
803 169 : ConstBndNodeRange & bnd_nodes = *_mesh.getBoundaryNodeRange();
804 338 : for (const auto & [bnd_id, mortar_nodal_auxes] :
805 507 : mortar_nodal_warehouse.getActiveBoundaryObjects())
806 338 : for (const auto index : index_range(mortar_nodal_auxes))
807 : {
808 : PARALLEL_TRY
809 : {
810 : try
811 : {
812 : ComputeMortarNodalAuxBndThread<AuxKernel> mnabt(
813 169 : _fe_problem, mortar_nodal_warehouse, bnd_id, index);
814 169 : Threads::parallel_reduce(bnd_nodes, mnabt);
815 169 : }
816 0 : catch (MooseException & e)
817 : {
818 0 : _fe_problem.setException("The following MooseException was raised during mortar nodal "
819 0 : "Auxiliary variable computation:\n" +
820 0 : std::string(e.what()));
821 0 : }
822 0 : catch (MetaPhysicL::LogicError & e)
823 : {
824 0 : moose::translateMetaPhysicLError(e);
825 0 : }
826 0 : catch (std::exception & e)
827 : {
828 : // Continue if we find a libMesh degenerate map exception, but
829 : // just re-throw for any real error
830 0 : if (!strstr(e.what(), "Jacobian") && !strstr(e.what(), "singular") &&
831 0 : !strstr(e.what(), "det != 0"))
832 0 : throw;
833 :
834 0 : _fe_problem.setException("We caught a libMesh degeneracy exception during mortar "
835 0 : "nodal Auxiliary variable computation:\n" +
836 0 : std::string(e.what()));
837 0 : }
838 : }
839 169 : PARALLEL_CATCH;
840 :
841 : // We need to make sure we propagate exceptions to all processes before trying to close
842 : // here, which is a parallel operation
843 169 : solution().close();
844 169 : _sys.update();
845 : }
846 : }
847 2039444 : }
848 :
849 : void
850 2039444 : AuxiliarySystem::computeElementalVars(ExecFlagType type)
851 : {
852 6118332 : TIME_SECTION("computeElementalVars", 3);
853 :
854 2039444 : const MooseObjectWarehouse<AuxKernel> & elemental = _elemental_aux_storage[type];
855 2039444 : computeElementalVarsHelper<AuxKernel>(elemental);
856 2039413 : }
857 :
858 : void
859 2039444 : AuxiliarySystem::computeElementalVecVars(ExecFlagType type)
860 : {
861 6118332 : TIME_SECTION("computeElementalVecVars", 3);
862 :
863 2039444 : const MooseObjectWarehouse<VectorAuxKernel> & elemental = _elemental_vec_aux_storage[type];
864 2039444 : computeElementalVarsHelper<VectorAuxKernel>(elemental);
865 2039444 : }
866 :
867 : void
868 2039444 : AuxiliarySystem::computeElementalArrayVars(ExecFlagType type)
869 : {
870 2039444 : const MooseObjectWarehouse<ArrayAuxKernel> & elemental = _elemental_array_aux_storage[type];
871 2039444 : computeElementalVarsHelper<ArrayAuxKernel>(elemental);
872 2039444 : }
873 :
874 : void
875 0 : AuxiliarySystem::augmentSparsity(SparsityPattern::Graph & /*sparsity*/,
876 : std::vector<dof_id_type> & /*n_nz*/,
877 : std::vector<dof_id_type> &
878 : /*n_oz*/)
879 : {
880 0 : }
881 :
882 : Order
883 66590 : AuxiliarySystem::getMinQuadratureOrder()
884 : {
885 66590 : Order order = CONSTANT;
886 66590 : std::vector<MooseVariableFEBase *> vars = _vars[0].fieldVariables();
887 148978 : for (const auto & var : vars)
888 : {
889 82388 : if (!var->isNodal()) // nodal aux variables do not need quadrature
890 : {
891 41754 : FEType fe_type = var->feType();
892 41754 : if (fe_type.default_quadrature_order() > order)
893 21414 : order = fe_type.default_quadrature_order();
894 : }
895 : }
896 :
897 66590 : return order;
898 66590 : }
899 :
900 : bool
901 29129 : AuxiliarySystem::needMaterialOnSide(BoundaryID bnd_id)
902 : {
903 57727 : return _elemental_aux_storage.hasActiveBoundaryObjects(bnd_id) ||
904 57727 : _elemental_vec_aux_storage.hasActiveBoundaryObjects(bnd_id);
905 : }
906 :
907 : void
908 503 : AuxiliarySystem::copyCurrentIntoPreviousNL()
909 : {
910 503 : if (solutionPreviousNewton())
911 503 : *solutionPreviousNewton() = *currentSolution();
912 503 : }
913 :
914 : template <typename AuxKernelType>
915 : void
916 6118332 : AuxiliarySystem::computeElementalVarsHelper(const MooseObjectWarehouse<AuxKernelType> & warehouse)
917 : {
918 6118332 : if (warehouse.hasActiveBlockObjects())
919 : {
920 : // Block Elemental AuxKernels
921 : PARALLEL_TRY
922 : {
923 70075 : ConstElemRange & range = *_mesh.getActiveLocalElementRange();
924 70075 : ComputeElemAuxVarsThread<AuxKernelType> eavt(_fe_problem, warehouse, true);
925 : try
926 : {
927 70075 : Threads::parallel_reduce(range, eavt);
928 : }
929 0 : catch (MooseException & e)
930 : {
931 0 : _fe_problem.setException("The following MooseException was raised during elemental "
932 : "Auxiliary variable computation:\n" +
933 0 : std::string(e.what()));
934 : }
935 70050 : }
936 70050 : PARALLEL_CATCH;
937 :
938 : // We need to make sure we propagate exceptions to all processes before trying to close
939 : // here, which is a parallel operation
940 70050 : solution().close();
941 70050 : _sys.update();
942 : }
943 :
944 : // Boundary Elemental AuxKernels
945 6118307 : if (warehouse.hasActiveBoundaryObjects())
946 : {
947 74628 : TIME_SECTION("computeElementalVecVars", 3);
948 :
949 : PARALLEL_TRY
950 : {
951 24876 : ConstBndElemRange & bnd_elems = *_mesh.getBoundaryElementRange();
952 24876 : ComputeElemAuxBcsThread<AuxKernelType> eabt(_fe_problem, warehouse, true);
953 : try
954 : {
955 24876 : Threads::parallel_reduce(bnd_elems, eabt);
956 : }
957 0 : catch (MooseException & e)
958 : {
959 0 : _fe_problem.setException("The following MooseException was raised during boundary "
960 : "elemental Auxiliary variable computation:\n" +
961 0 : std::string(e.what()));
962 : }
963 24870 : }
964 24870 : PARALLEL_CATCH;
965 :
966 : // We need to make sure we propagate exceptions to all processes before trying to close
967 : // here, which is a parallel operation
968 24870 : solution().close();
969 24870 : _sys.update();
970 24870 : }
971 6118301 : }
972 :
973 : template <typename AuxKernelType>
974 : void
975 6118338 : AuxiliarySystem::computeNodalVarsHelper(const MooseObjectWarehouse<AuxKernelType> & warehouse)
976 : {
977 6118338 : if (warehouse.hasActiveBlockObjects())
978 : {
979 : // Block Nodal AuxKernels
980 : PARALLEL_TRY
981 : {
982 136321 : ConstNodeRange & range = *_mesh.getLocalNodeRange();
983 136321 : ComputeNodalAuxVarsThread<AuxKernelType> navt(_fe_problem, warehouse);
984 136321 : Threads::parallel_reduce(range, navt);
985 :
986 136319 : solution().close();
987 136319 : _sys.update();
988 136319 : }
989 136319 : PARALLEL_CATCH;
990 : }
991 :
992 6118336 : if (warehouse.hasActiveBoundaryObjects())
993 : {
994 253413 : TIME_SECTION("computeBoundaryObjects", 3);
995 :
996 : // Boundary Nodal AuxKernels
997 : PARALLEL_TRY
998 : {
999 84471 : ConstBndNodeRange & bnd_nodes = *_mesh.getBoundaryNodeRange();
1000 84471 : ComputeNodalAuxBcsThread<AuxKernelType> nabt(_fe_problem, warehouse);
1001 84471 : Threads::parallel_reduce(bnd_nodes, nabt);
1002 :
1003 84471 : solution().close();
1004 84471 : _sys.update();
1005 84471 : }
1006 84471 : PARALLEL_CATCH;
1007 84471 : }
1008 6118336 : }
1009 :
1010 : void
1011 519 : AuxiliarySystem::variableWiseRelativeSolutionDifferenceNorm(
1012 : std::vector<Number> & rel_diff_norms) const
1013 : {
1014 519 : rel_diff_norms.resize(nVariables(), 0);
1015 : // Get dof map from system
1016 519 : const auto & dof_map = _sys.get_dof_map();
1017 :
1018 1545 : for (const auto n : make_range(nVariables()))
1019 : {
1020 : // Get local indices from dof map for each variable
1021 1026 : std::vector<dof_id_type> local_indices_n;
1022 1026 : dof_map.local_variable_indices(local_indices_n, _mesh, n);
1023 1026 : Number diff_norm_n = 0;
1024 1026 : Number norm_n = 0;
1025 : // Get values from system, update norm
1026 90342 : for (const auto local_index : local_indices_n)
1027 : {
1028 89316 : const Number & value = solution()(local_index);
1029 89316 : const Number & value_old = solutionOld()(local_index);
1030 89316 : diff_norm_n += Utility::pow<2, Number>(value - value_old);
1031 89316 : norm_n += Utility::pow<2, Number>(value);
1032 : }
1033 : // Aggregate norm over proceccors
1034 1026 : _communicator.sum(diff_norm_n);
1035 1026 : _communicator.sum(norm_n);
1036 1026 : diff_norm_n = sqrt(diff_norm_n);
1037 1026 : norm_n = sqrt(norm_n);
1038 1026 : rel_diff_norms[n] = diff_norm_n > 0 ? diff_norm_n / norm_n : 0.0;
1039 1026 : }
1040 519 : }
1041 :
1042 : template void
1043 : AuxiliarySystem::computeElementalVarsHelper<AuxKernel>(const MooseObjectWarehouse<AuxKernel> &);
1044 : template void AuxiliarySystem::computeElementalVarsHelper<VectorAuxKernel>(
1045 : const MooseObjectWarehouse<VectorAuxKernel> &);
1046 : template void
1047 : AuxiliarySystem::computeNodalVarsHelper<AuxKernel>(const MooseObjectWarehouse<AuxKernel> &);
1048 : template void AuxiliarySystem::computeNodalVarsHelper<VectorAuxKernel>(
1049 : const MooseObjectWarehouse<VectorAuxKernel> &);
|