https://mooseframework.inl.gov
Loading...
Searching...
No Matches
AuxiliarySystem.C
Go to the documentation of this file.
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"
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// AuxiliarySystem ////////
38
39AuxiliarySystem::AuxiliarySystem(FEProblemBase & subproblem, const std::string & name)
40 : SystemBase(subproblem, subproblem, name, Moose::VAR_AUXILIARY),
41 PerfGraphInterface(subproblem.getMooseApp().perfGraph(), "AuxiliarySystem"),
43 _sys(subproblem.es().add_system<System>(name)),
44 _current_solution(_sys.current_local_solution.get()),
45 _aux_scalar_storage(_app.getExecuteOnEnum()),
46 _nodal_aux_storage(_app.getExecuteOnEnum()),
47 _mortar_nodal_aux_storage(_app.getExecuteOnEnum()),
48 _elemental_aux_storage(_app.getExecuteOnEnum()),
49 _nodal_vec_aux_storage(_app.getExecuteOnEnum()),
50 _elemental_vec_aux_storage(_app.getExecuteOnEnum()),
51 _nodal_array_aux_storage(_app.getExecuteOnEnum()),
52 _elemental_array_aux_storage(_app.getExecuteOnEnum())
53#ifdef MOOSE_KOKKOS_ENABLED
54 ,
55 _kokkos_nodal_aux_storage(_app.getExecuteOnEnum()),
56 _kokkos_elemental_aux_storage(_app.getExecuteOnEnum())
57#endif
58{
59 _nodal_vars.resize(libMesh::n_threads());
60 _elem_vars.resize(libMesh::n_threads());
61
62 if (!_fe_problem.defaultGhosting())
63 {
64 auto & dof_map = _sys.get_dof_map();
65 dof_map.remove_algebraic_ghosting_functor(dof_map.default_algebraic_ghosting());
66 dof_map.set_implicit_neighbor_dofs(false);
67 }
68}
69
71
72void
74{
75 TIME_SECTION("initialSetup", 3, "Initializing Auxiliary System");
76
80
81 for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
82 {
85
86 _nodal_aux_storage.sort(tid);
87 _nodal_aux_storage.initialSetup(tid);
88
90 _mortar_nodal_aux_storage.initialSetup(tid);
91
92 _nodal_vec_aux_storage.sort(tid);
93 _nodal_vec_aux_storage.initialSetup(tid);
94
96 _nodal_array_aux_storage.initialSetup(tid);
97
98 _elemental_aux_storage.sort(tid);
99 _elemental_aux_storage.initialSetup(tid);
100
102 _elemental_vec_aux_storage.initialSetup(tid);
103
105 _elemental_array_aux_storage.initialSetup(tid);
106 }
107
108#ifdef MOOSE_KOKKOS_ENABLED
111
114#endif
115}
116
117void
123
124void
126{
128
129 for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
130 {
132 _nodal_aux_storage.timestepSetup(tid);
133 _mortar_nodal_aux_storage.timestepSetup(tid);
134 _nodal_vec_aux_storage.timestepSetup(tid);
135 _nodal_array_aux_storage.timestepSetup(tid);
136 _elemental_aux_storage.timestepSetup(tid);
137 _elemental_vec_aux_storage.timestepSetup(tid);
138 _elemental_array_aux_storage.timestepSetup(tid);
139 }
140
141#ifdef MOOSE_KOKKOS_ENABLED
144#endif
145}
146
147void
149{
150 SystemBase::customSetup(exec_type);
151
152 for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
153 {
154 _aux_scalar_storage.customSetup(exec_type, tid);
155 _nodal_aux_storage.customSetup(exec_type, tid);
156 _mortar_nodal_aux_storage.customSetup(exec_type, tid);
157 _nodal_vec_aux_storage.customSetup(exec_type, tid);
158 _nodal_array_aux_storage.customSetup(exec_type, tid);
159 _elemental_aux_storage.customSetup(exec_type, tid);
160 _elemental_vec_aux_storage.customSetup(exec_type, tid);
161 _elemental_array_aux_storage.customSetup(exec_type, tid);
162 }
163
164#ifdef MOOSE_KOKKOS_ENABLED
165 _kokkos_nodal_aux_storage.customSetup(exec_type, /*tid=*/0);
166 _kokkos_elemental_aux_storage.customSetup(exec_type, /*tid=*/0);
167#endif
168}
169
170void
172{
174
175 for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
176 {
178 _nodal_aux_storage.subdomainSetup(tid);
179 _mortar_nodal_aux_storage.subdomainSetup(tid);
180 _nodal_vec_aux_storage.subdomainSetup(tid);
181 _nodal_array_aux_storage.subdomainSetup(tid);
182 _elemental_aux_storage.subdomainSetup(tid);
183 _elemental_vec_aux_storage.subdomainSetup(tid);
184 _elemental_array_aux_storage.subdomainSetup(tid);
185 }
186}
187
188void
190{
192
193 for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
194 {
196 _nodal_aux_storage.jacobianSetup(tid);
197 _mortar_nodal_aux_storage.jacobianSetup(tid);
198 _nodal_vec_aux_storage.jacobianSetup(tid);
199 _nodal_array_aux_storage.jacobianSetup(tid);
200 _elemental_aux_storage.jacobianSetup(tid);
201 _elemental_vec_aux_storage.jacobianSetup(tid);
202 _elemental_array_aux_storage.jacobianSetup(tid);
203 }
204
205#ifdef MOOSE_KOKKOS_ENABLED
208#endif
209}
210
211void
213{
215
216 for (unsigned int tid = 0; tid < libMesh::n_threads(); tid++)
217 {
219 _nodal_aux_storage.residualSetup(tid);
220 _mortar_nodal_aux_storage.residualSetup(tid);
221 _nodal_vec_aux_storage.residualSetup(tid);
222 _nodal_array_aux_storage.residualSetup(tid);
223 _elemental_aux_storage.residualSetup(tid);
224 _elemental_vec_aux_storage.residualSetup(tid);
225 _elemental_array_aux_storage.residualSetup(tid);
226 }
227
228#ifdef MOOSE_KOKKOS_ENABLED
231#endif
232}
233
234void
236{
238 _nodal_aux_storage.updateActive(tid);
239 _mortar_nodal_aux_storage.updateActive(tid);
240 _nodal_vec_aux_storage.updateActive(tid);
241 _nodal_array_aux_storage.updateActive(tid);
242 _elemental_aux_storage.updateActive(tid);
243 _elemental_vec_aux_storage.updateActive(tid);
244 _elemental_array_aux_storage.updateActive(tid);
245
246#ifdef MOOSE_KOKKOS_ENABLED
247 if (tid == 0)
248 {
251 }
252#endif
253}
254
255void
256AuxiliarySystem::addVariable(const std::string & var_type,
257 const std::string & name,
258 InputParameters & parameters)
259{
260 SystemBase::addVariable(var_type, name, parameters);
261
262 auto fe_type = FEType(Utility::string_to_enum<Order>(parameters.get<MooseEnum>("order")),
263 Utility::string_to_enum<FEFamily>(parameters.get<MooseEnum>("family")));
264
265 if (var_type == "MooseVariableScalar")
266 return;
267
268 for (THREAD_ID tid = 0; tid < libMesh::n_threads(); tid++)
269 {
270 if (FEInterface::field_type(fe_type) == libMesh::TYPE_VECTOR)
271 {
272 auto * var = _vars[tid].getActualFieldVariable<RealVectorValue>(name);
273 if (var)
274 {
275 if (var->feType().family == LAGRANGE_VEC)
276 _nodal_vars[tid].push_back(var);
277 else
278 _elem_vars[tid].push_back(var);
279 }
280 }
281
282 else
283 {
284 MooseVariableBase * var_base = _vars[tid].getVariable(name);
285
286 auto * const var = dynamic_cast<MooseVariableField<Real> *>(var_base);
287
288 if (var)
289 {
290 if (var->feType().family == LAGRANGE)
291 _nodal_vars[tid].push_back(var);
292 else
293 _elem_vars[tid].push_back(var);
294 }
295
296 auto * const avar = dynamic_cast<MooseVariableField<RealEigenVector> *>(var_base);
297
298 if (avar)
299 {
300 if (avar->feType().family == LAGRANGE)
301 _nodal_vars[tid].push_back(avar);
302 else
303 _elem_vars[tid].push_back(avar);
304 }
305 }
306 }
307}
308
309void
310AuxiliarySystem::addKernel(const std::string & kernel_name,
311 const std::string & name,
312 InputParameters & parameters)
313{
314 for (THREAD_ID tid = 0; tid < libMesh::n_threads(); tid++)
315 {
316 const auto & base = parameters.getBase();
317 if (base == "AuxKernel" || base == "Bounds")
318 {
319 std::shared_ptr<AuxKernel> kernel =
320 _factory.create<AuxKernel>(kernel_name, name, parameters, tid);
321 if (kernel->isNodal())
322 {
323 if (kernel->isMortar())
324 _mortar_nodal_aux_storage.addObject(kernel, tid);
325 else
326 _nodal_aux_storage.addObject(kernel, tid);
327 }
328 else
329 _elemental_aux_storage.addObject(kernel, tid);
330 }
331
332 else if (base == "VectorAuxKernel")
333 {
334 std::shared_ptr<VectorAuxKernel> kernel =
335 _factory.create<VectorAuxKernel>(kernel_name, name, parameters, tid);
336 if (kernel->isNodal())
337 {
338 if (kernel->isMortar())
339 mooseError("Vector mortar aux kernels not yet implemented");
340 _nodal_vec_aux_storage.addObject(kernel, tid);
341 }
342 else
343 _elemental_vec_aux_storage.addObject(kernel, tid);
344 }
345
346 else if (base == "ArrayAuxKernel")
347 {
348 std::shared_ptr<ArrayAuxKernel> kernel =
349 _factory.create<ArrayAuxKernel>(kernel_name, name, parameters, tid);
350 if (kernel->isNodal())
351 {
352 if (kernel->isMortar())
353 mooseError("Vector mortar aux kernels not yet implemented");
354 _nodal_array_aux_storage.addObject(kernel, tid);
355 }
356 else
357 _elemental_array_aux_storage.addObject(kernel, tid);
358 }
359 else
360 mooseAssert(false,
361 "Attempting to add AuxKernel of type '" + kernel_name + "' and name '" + name +
362 "' to the auxiliary system with invalid _moose_base: " + base);
363 }
364}
365
366void
367AuxiliarySystem::addScalarKernel(const std::string & kernel_name,
368 const std::string & name,
369 InputParameters & parameters)
370{
371 for (THREAD_ID tid = 0; tid < libMesh::n_threads(); tid++)
372 {
373 std::shared_ptr<AuxScalarKernel> kernel =
374 _factory.create<AuxScalarKernel>(kernel_name, name, parameters, tid);
375 _aux_scalar_storage.addObject(kernel, tid);
376 }
377}
378
379void
380AuxiliarySystem::reinitElem(const Elem * /*elem*/, THREAD_ID tid)
381{
382 for (auto * var : _nodal_vars[tid])
383 var->computeElemValues();
384
385 for (auto * var : _elem_vars[tid])
386 {
387 var->reinitAux();
388 var->computeElemValues();
389 }
390}
391
392void
393AuxiliarySystem::reinitElemFace(const Elem * /*elem*/, unsigned int /*side*/, THREAD_ID tid)
394{
395 for (auto * var : _nodal_vars[tid])
396 var->computeElemValuesFace();
397
398 for (auto * var : _elem_vars[tid])
399 {
400 var->reinitAux();
401 var->reinitAuxNeighbor();
402 var->computeElemValuesFace();
403 }
404}
405
406void
408{
409 if (_serialized_solution.get() &&
410 _sys.n_dofs() > 0) // libMesh does not like serializing of empty vectors
411 {
412 if (!_serialized_solution->initialized() || _serialized_solution->size() != _sys.n_dofs())
413 {
414 _serialized_solution->clear();
415 _serialized_solution->init(_sys.n_dofs(), false, SERIAL);
416 }
417
419 }
420}
421
422void
424{
425 // avoid division by dt which might be zero.
426 if (_fe_problem.dt() > 0.)
427 for (auto & ti : _time_integrators)
428 ti->preStep();
429
430 // We need to compute time derivatives every time each kind of the variables is finished, because:
431 //
432 // a) the user might want to use the aux variable value somewhere, thus we need to provide the
433 // up-to-date value
434 // b) time integration system works with the whole vectors of solutions, thus we cannot update
435 // only a part of the vector
436 //
437
438 if (_vars[0].scalars().size() > 0)
439 {
440 computeScalarVars(type);
441 // compute time derivatives of scalar aux variables _after_ the values were updated
442 if (_fe_problem.dt() > 0.)
443 for (auto & ti : _time_integrators)
444 ti->computeTimeDerivatives();
445 }
446
447 if (_vars[0].fieldVariables().size() > 0)
448 {
451 computeNodalVars(type);
456
457#ifdef MOOSE_KOKKOS_ENABLED
458 kokkosCompute(type);
459#endif
460
462 {
463 solution().close();
464 _sys.update();
466 }
467
468 // compute time derivatives of nodal aux variables _after_ the values were updated
469 if (_fe_problem.dt() > 0.)
470 for (auto & ti : _time_integrators)
471 ti->computeTimeDerivatives();
472 }
473
474 if (_serialized_solution.get())
476}
477
478std::set<std::string>
480{
481 std::set<std::string> depend_objects;
482
483 // Elemental AuxKernels
484 {
485 const std::vector<std::shared_ptr<AuxKernel>> & auxs =
486 _elemental_aux_storage[type].getActiveObjects();
487 for (const auto & aux : auxs)
488 {
489 const std::set<UserObjectName> & uo = aux->getDependObjects();
490 depend_objects.insert(uo.begin(), uo.end());
491 }
492 }
493
494 // Elemental VectorAuxKernels
495 {
496 const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
497 _elemental_vec_aux_storage[type].getActiveObjects();
498 for (const auto & aux : auxs)
499 {
500 const std::set<UserObjectName> & uo = aux->getDependObjects();
501 depend_objects.insert(uo.begin(), uo.end());
502 }
503 }
504
505 // Elemental ArrayAuxKernels
506 {
507 const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
508 _elemental_array_aux_storage[type].getActiveObjects();
509 for (const auto & aux : auxs)
510 {
511 const std::set<UserObjectName> & uo = aux->getDependObjects();
512 depend_objects.insert(uo.begin(), uo.end());
513 }
514 }
515
516 // Nodal AuxKernels
517 {
518 const std::vector<std::shared_ptr<AuxKernel>> & auxs =
519 _nodal_aux_storage[type].getActiveObjects();
520 for (const auto & aux : auxs)
521 {
522 const std::set<UserObjectName> & uo = aux->getDependObjects();
523 depend_objects.insert(uo.begin(), uo.end());
524 }
525 }
526
527 // Mortar Nodal AuxKernels
528 {
529 const std::vector<std::shared_ptr<AuxKernel>> & auxs =
530 _mortar_nodal_aux_storage[type].getActiveObjects();
531 for (const auto & aux : auxs)
532 {
533 const std::set<UserObjectName> & uo = aux->getDependObjects();
534 depend_objects.insert(uo.begin(), uo.end());
535 }
536 }
537
538 // Nodal VectorAuxKernels
539 {
540 const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
541 _nodal_vec_aux_storage[type].getActiveObjects();
542 for (const auto & aux : auxs)
543 {
544 const std::set<UserObjectName> & uo = aux->getDependObjects();
545 depend_objects.insert(uo.begin(), uo.end());
546 }
547 }
548
549 // Nodal ArrayAuxKernels
550 {
551 const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
552 _nodal_array_aux_storage[type].getActiveObjects();
553 for (const auto & aux : auxs)
554 {
555 const std::set<UserObjectName> & uo = aux->getDependObjects();
556 depend_objects.insert(uo.begin(), uo.end());
557 }
558 }
559
560#ifdef MOOSE_KOKKOS_ENABLED
561 // Kokkos NodalAuxKernels
562 {
563 const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
565 for (const auto & aux : auxs)
566 {
567 const std::set<UserObjectName> & uo = aux->getDependObjects();
568 depend_objects.insert(uo.begin(), uo.end());
569 }
570 }
571
572 // Kokkos ElementalAuxKernels
573 {
574 const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
576 for (const auto & aux : auxs)
577 {
578 const std::set<UserObjectName> & uo = aux->getDependObjects();
579 depend_objects.insert(uo.begin(), uo.end());
580 }
581 }
582#endif
583
584 return depend_objects;
585}
586
587std::set<std::string>
589{
590 std::set<std::string> depend_objects;
591
592 // Elemental AuxKernels
593 {
594 const std::vector<std::shared_ptr<AuxKernel>> & auxs =
595 _elemental_aux_storage.getActiveObjects();
596 for (const auto & aux : auxs)
597 {
598 const std::set<UserObjectName> & uo = aux->getDependObjects();
599 depend_objects.insert(uo.begin(), uo.end());
600 }
601 }
602
603 // Elemental VectorAuxKernels
604 {
605 const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
606 _elemental_vec_aux_storage.getActiveObjects();
607 for (const auto & aux : auxs)
608 {
609 const std::set<UserObjectName> & uo = aux->getDependObjects();
610 depend_objects.insert(uo.begin(), uo.end());
611 }
612 }
613
614 // Elemental ArrayAuxKernels
615 {
616 const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
617 _elemental_array_aux_storage.getActiveObjects();
618 for (const auto & aux : auxs)
619 {
620 const std::set<UserObjectName> & uo = aux->getDependObjects();
621 depend_objects.insert(uo.begin(), uo.end());
622 }
623 }
624
625 // Nodal AuxKernels
626 {
627 const std::vector<std::shared_ptr<AuxKernel>> & auxs = _nodal_aux_storage.getActiveObjects();
628 for (const auto & aux : auxs)
629 {
630 const std::set<UserObjectName> & uo = aux->getDependObjects();
631 depend_objects.insert(uo.begin(), uo.end());
632 }
633 }
634
635 // Mortar Nodal AuxKernels
636 {
637 const std::vector<std::shared_ptr<AuxKernel>> & auxs =
638 _mortar_nodal_aux_storage.getActiveObjects();
639 for (const auto & aux : auxs)
640 {
641 const std::set<UserObjectName> & uo = aux->getDependObjects();
642 depend_objects.insert(uo.begin(), uo.end());
643 }
644 }
645
646 // Nodal VectorAuxKernels
647 {
648 const std::vector<std::shared_ptr<VectorAuxKernel>> & auxs =
649 _nodal_vec_aux_storage.getActiveObjects();
650 for (const auto & aux : auxs)
651 {
652 const std::set<UserObjectName> & uo = aux->getDependObjects();
653 depend_objects.insert(uo.begin(), uo.end());
654 }
655 }
656
657 // Nodal ArrayAuxKernels
658 {
659 const std::vector<std::shared_ptr<ArrayAuxKernel>> & auxs =
660 _nodal_array_aux_storage.getActiveObjects();
661 for (const auto & aux : auxs)
662 {
663 const std::set<UserObjectName> & uo = aux->getDependObjects();
664 depend_objects.insert(uo.begin(), uo.end());
665 }
666 }
667
668#ifdef MOOSE_KOKKOS_ENABLED
669 // Nodal KokkosAuxKernels
670 {
671 const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
673 for (const auto & aux : auxs)
674 {
675 const std::set<UserObjectName> & uo = aux->getDependObjects();
676 depend_objects.insert(uo.begin(), uo.end());
677 }
678 }
679
680 // Elemental KokkosAuxKernels
681 {
682 const std::vector<std::shared_ptr<AuxKernelBase>> & auxs =
684 for (const auto & aux : auxs)
685 {
686 const std::set<UserObjectName> & uo = aux->getDependObjects();
687 depend_objects.insert(uo.begin(), uo.end());
688 }
689 }
690#endif
691
692 return depend_objects;
693}
694
695void
697{
699 const std::vector<std::shared_ptr<AuxScalarKernel>> & objects = storage.getActiveObjects(0);
700
701 std::set<TagID> needed_sc_var_matrix_tags;
702 std::set<TagID> needed_sc_var_vector_tags;
703 for (const auto & obj : objects)
704 {
705 auto & sc_var_coup_vtags = obj->getScalarVariableCoupleableVectorTags();
706 needed_sc_var_vector_tags.insert(sc_var_coup_vtags.begin(), sc_var_coup_vtags.end());
707
708 auto & sc_var_coup_mtags = obj->getScalarVariableCoupleableMatrixTags();
709 needed_sc_var_matrix_tags.insert(sc_var_coup_mtags.begin(), sc_var_coup_mtags.end());
710 }
711
712 _fe_problem.setActiveScalarVariableCoupleableMatrixTags(needed_sc_var_matrix_tags, 0);
713 _fe_problem.setActiveScalarVariableCoupleableVectorTags(needed_sc_var_vector_tags, 0);
714}
715
716void
722
723void
725{
727
728 // Reference to the current storage container
730
731 if (storage.hasActiveObjects())
732 {
733 TIME_SECTION("computeScalarVars", 1);
734
735 PARALLEL_TRY
736 {
737 // FIXME: run multi-threaded
738 THREAD_ID tid = 0;
739 if (storage.hasActiveObjects())
740 {
742
743 const std::vector<std::shared_ptr<AuxScalarKernel>> & objects =
744 storage.getActiveObjects(tid);
745
746 // Call compute() method on all active AuxScalarKernel objects
747 for (const auto & obj : objects)
748 obj->compute();
749
750 const std::vector<MooseVariableScalar *> & scalar_vars = getScalarVariables(tid);
751 for (const auto & var : scalar_vars)
752 var->insert(solution());
753 }
754 }
755 PARALLEL_CATCH;
756
757 solution().close();
758 _sys.update();
759 }
760
762}
763
764void
766{
767 TIME_SECTION("computeNodalVars", 3);
768
770 computeNodalVarsHelper<AuxKernel>(nodal);
771}
772
773void
775{
776 TIME_SECTION("computeNodalVecVars", 3);
777
779 computeNodalVarsHelper<VectorAuxKernel>(nodal);
780}
781
782void
784{
786 computeNodalVarsHelper<ArrayAuxKernel>(nodal);
787}
788
789void
791{
792 TIME_SECTION("computeMortarNodalVars", 3);
793
794 const MooseObjectWarehouse<AuxKernel> & mortar_nodal_warehouse = _mortar_nodal_aux_storage[type];
795
796 mooseAssert(!mortar_nodal_warehouse.hasActiveBlockObjects(),
797 "We don't allow creation of block restricted mortar nodal aux kernels.");
798
799 if (mortar_nodal_warehouse.hasActiveBoundaryObjects())
800 {
802 for (const auto & [bnd_id, mortar_nodal_auxes] :
803 mortar_nodal_warehouse.getActiveBoundaryObjects())
804 for (const auto index : index_range(mortar_nodal_auxes))
805 {
806 PARALLEL_TRY
807 {
808 try
809 {
811 _fe_problem, mortar_nodal_warehouse, bnd_id, index);
812 Threads::parallel_reduce(bnd_nodes, mnabt);
813 }
814 catch (MooseException & e)
815 {
816 _fe_problem.setException("The following MooseException was raised during mortar nodal "
817 "Auxiliary variable computation:\n" +
818 std::string(e.what()));
819 }
820 catch (MetaPhysicL::LogicError & e)
821 {
823 }
824 catch (std::exception & e)
825 {
826 // Continue if we find a libMesh degenerate map exception, but
827 // just re-throw for any real error
828 if (!strstr(e.what(), "Jacobian") && !strstr(e.what(), "singular") &&
829 !strstr(e.what(), "det != 0"))
830 throw;
831
832 _fe_problem.setException("We caught a libMesh degeneracy exception during mortar "
833 "nodal Auxiliary variable computation:\n" +
834 std::string(e.what()));
835 }
836 }
837 PARALLEL_CATCH;
838
839 // We need to make sure we propagate exceptions to all processes before trying to close
840 // here, which is a parallel operation
841 solution().close();
842 _sys.update();
843 }
844 }
845}
846
847void
849{
850 TIME_SECTION("computeElementalVars", 3);
851
853 computeElementalVarsHelper<AuxKernel>(elemental);
854}
855
856void
858{
859 TIME_SECTION("computeElementalVecVars", 3);
860
862 computeElementalVarsHelper<VectorAuxKernel>(elemental);
863}
864
865void
867{
869 computeElementalVarsHelper<ArrayAuxKernel>(elemental);
870}
871
872void
874 std::vector<dof_id_type> & /*n_nz*/,
875 std::vector<dof_id_type> &
876 /*n_oz*/)
877{
878}
879
880Order
882{
883 Order order = CONSTANT;
884 std::vector<MooseVariableFEBase *> vars = _vars[0].fieldVariables();
885 for (const auto & var : vars)
886 {
887 if (!var->isNodal()) // nodal aux variables do not need quadrature
888 {
889 FEType fe_type = var->feType();
890 if (fe_type.default_quadrature_order() > order)
891 order = fe_type.default_quadrature_order();
892 }
893 }
894
895 return order;
896}
897
898bool
900{
901 return _elemental_aux_storage.hasActiveBoundaryObjects(bnd_id) ||
902 _elemental_vec_aux_storage.hasActiveBoundaryObjects(bnd_id);
903}
904
905void
911
912template <typename AuxKernelType>
913void
915{
916 if (warehouse.hasActiveBlockObjects())
917 {
918 // Block Elemental AuxKernels
919 PARALLEL_TRY
920 {
921 const ConstElemRange & range = *_mesh.getActiveLocalElementRange();
923 try
924 {
925 Threads::parallel_reduce(range, eavt);
926 }
927 catch (MooseException & e)
928 {
929 _fe_problem.setException("The following MooseException was raised during elemental "
930 "Auxiliary variable computation:\n" +
931 std::string(e.what()));
932 }
933 }
934 PARALLEL_CATCH;
935
936 // We need to make sure we propagate exceptions to all processes before trying to close
937 // here, which is a parallel operation
938 solution().close();
939 _sys.update();
940 }
941
942 // Boundary Elemental AuxKernels
943 if (warehouse.hasActiveBoundaryObjects())
944 {
945 TIME_SECTION("computeElementalVecVars", 3);
946
947 PARALLEL_TRY
948 {
951 try
952 {
953 Threads::parallel_reduce(bnd_elems, eabt);
954 }
955 catch (MooseException & e)
956 {
957 _fe_problem.setException("The following MooseException was raised during boundary "
958 "elemental Auxiliary variable computation:\n" +
959 std::string(e.what()));
960 }
961 }
962 PARALLEL_CATCH;
963
964 // We need to make sure we propagate exceptions to all processes before trying to close
965 // here, which is a parallel operation
966 solution().close();
967 _sys.update();
968 }
969}
970
971template <typename AuxKernelType>
972void
974{
975 if (warehouse.hasActiveBlockObjects())
976 {
977 // Block Nodal AuxKernels
978 PARALLEL_TRY
979 {
980 ConstNodeRange & range = *_mesh.getLocalNodeRange();
982 Threads::parallel_reduce(range, navt);
983
984 solution().close();
985 _sys.update();
986 }
987 PARALLEL_CATCH;
988 }
989
990 if (warehouse.hasActiveBoundaryObjects())
991 {
992 TIME_SECTION("computeBoundaryObjects", 3);
993
994 // Boundary Nodal AuxKernels
995 PARALLEL_TRY
996 {
999 Threads::parallel_reduce(bnd_nodes, nabt);
1000
1001 solution().close();
1002 _sys.update();
1003 }
1004 PARALLEL_CATCH;
1005 }
1006}
1007
1008void
1010 std::vector<Number> & rel_diff_norms) const
1011{
1012 rel_diff_norms.resize(nVariables(), 0);
1013 // Get dof map from system
1014 const auto & dof_map = _sys.get_dof_map();
1015
1016 for (const auto n : make_range(nVariables()))
1017 {
1018 // Get local indices from dof map for each variable
1019 std::vector<dof_id_type> local_indices_n;
1020 dof_map.local_variable_indices(local_indices_n, _mesh, n);
1021 Number diff_norm_n = 0;
1022 Number norm_n = 0;
1023 // Get values from system, update norm
1024 for (const auto local_index : local_indices_n)
1025 {
1026 const Number & value = solution()(local_index);
1027 const Number & value_old = solutionOld()(local_index);
1028 diff_norm_n += Utility::pow<2, Number>(value - value_old);
1029 norm_n += Utility::pow<2, Number>(value);
1030 }
1031 // Aggregate norm over proceccors
1032 _communicator.sum(diff_norm_n);
1033 _communicator.sum(norm_n);
1034 diff_norm_n = sqrt(diff_norm_n);
1035 norm_n = sqrt(norm_n);
1036 rel_diff_norms[n] = diff_norm_n > 0 ? diff_norm_n / norm_n : 0.0;
1037 }
1038}
1039
1040template void
1041AuxiliarySystem::computeElementalVarsHelper<AuxKernel>(const MooseObjectWarehouse<AuxKernel> &);
1042template void AuxiliarySystem::computeElementalVarsHelper<VectorAuxKernel>(
1044template void
1045AuxiliarySystem::computeNodalVarsHelper<AuxKernel>(const MooseObjectWarehouse<AuxKernel> &);
1046template void AuxiliarySystem::computeNodalVarsHelper<VectorAuxKernel>(
boundary_id_type BoundaryID
void mooseError(Args &&... args)
Emit an error message with the given stringified, concatenated args and terminate the application.
Definition MooseError.h:311
unsigned int THREAD_ID
Definition MooseTypes.h:237
char ** vars
Base class for making kernels that work on auxiliary scalar variables.
virtual void copyCurrentIntoPreviousNL()
Copies the current solution into the previous nonlinear iteration solution.
bool needMaterialOnSide(BoundaryID bnd_id)
Indicated whether this system needs material properties on boundaries.
virtual void jacobianSetup() override
virtual void residualSetup() override
void computeScalarVars(ExecFlagType type)
void addKernel(const std::string &kernel_name, const std::string &name, InputParameters &parameters)
Adds an auxiliary kernel.
ExecuteMooseObjectWarehouse< ArrayAuxKernel > _nodal_array_aux_storage
void clearScalarVariableCoupleableTags()
virtual void compute(ExecFlagType type) override
Compute auxiliary variables.
void kokkosCompute(ExecFlagType type)
void computeMortarNodalVars(ExecFlagType type)
void computeElementalVars(ExecFlagType type)
void computeElementalVarsHelper(const MooseObjectWarehouse< AuxKernelType > &warehouse)
const NumericVector< Number > * _current_solution
solution vector from nonlinear solver
virtual void subdomainSetup() override
ExecuteMooseObjectWarehouse< AuxKernelBase > _kokkos_elemental_aux_storage
virtual libMesh::Order getMinQuadratureOrder() override
Get the minimum quadrature order for evaluating elemental auxiliary variables.
ExecuteMooseObjectWarehouse< AuxKernel > _elemental_aux_storage
void computeNodalVecVars(ExecFlagType type)
void variableWiseRelativeSolutionDifferenceNorm(std::vector< Number > &var_diffs) const
Computes and stores ||current - old|| / ||current|| for each variable in the given vector.
void setScalarVariableCoupleableTags(ExecFlagType type)
std::set< std::string > getDependObjects()
virtual void customSetup(const ExecFlagType &exec_type) override
ExecuteMooseObjectWarehouse< ArrayAuxKernel > _elemental_array_aux_storage
ExecuteMooseObjectWarehouse< VectorAuxKernel > _elemental_vec_aux_storage
ExecuteMooseObjectWarehouse< AuxKernel > _nodal_aux_storage
void computeElementalVecVars(ExecFlagType type)
ExecuteMooseObjectWarehouse< VectorAuxKernel > _nodal_vec_aux_storage
void addScalarKernel(const std::string &kernel_name, const std::string &name, InputParameters &parameters)
Adds a scalar kernel.
AuxiliarySystem(FEProblemBase &subproblem, const std::string &name)
virtual void reinitElem(const Elem *elem, THREAD_ID tid) override
Reinit an element assembly info.
ExecuteMooseObjectWarehouse< AuxKernel > _mortar_nodal_aux_storage
virtual ~AuxiliarySystem()
virtual void addVariable(const std::string &var_type, const std::string &name, InputParameters &parameters) override
Canonical method for adding a variable.
ExecuteMooseObjectWarehouse< AuxKernelBase > _kokkos_nodal_aux_storage
const NumericVector< Number > *const & currentSolution() const override
The solution vector that is currently being operated on.
void computeElementalArrayVars(ExecFlagType type)
void computeNodalVars(ExecFlagType type)
virtual void initialSetup() override
Setup Functions.
virtual void updateActive(THREAD_ID tid)
virtual void augmentSparsity(libMesh::SparsityPattern::Graph &, std::vector< dof_id_type > &, std::vector< dof_id_type > &) override
Will modify the sparsity pattern to add logical geometric connections.
std::vector< std::vector< MooseVariableFieldBase * > > _elem_vars
Elemental variables.
std::vector< std::vector< MooseVariableFEBase * > > _nodal_vars
virtual void serializeSolution()
ExecuteMooseObjectWarehouse< AuxScalarKernel > _aux_scalar_storage
libMesh::System & _sys
virtual void reinitElemFace(const Elem *elem, unsigned int side, THREAD_ID tid) override
Reinit assembly info for a side of an element.
void computeNodalArrayVars(ExecFlagType type)
virtual void timestepSetup() override
virtual void reinit() override
Reinitialize the system when the degrees of freedom in this system have changed.
void computeNodalVarsHelper(const MooseObjectWarehouse< AuxKernelType > &warehouse)
This class evaluates a single mortar nodal aux kernel.
void jacobianSetup(THREAD_ID tid=0) const override
Convenience methods for calling object setup methods.
void updateActive(THREAD_ID tid=0) override
Updates the active objects storage.
void addObject(std::shared_ptr< T > object, THREAD_ID tid=0, bool recurse=true) override
Adds an object to the storage structure.
void residualSetup(THREAD_ID tid=0) const override
void sort(THREAD_ID tid=0)
Performs a sort using the DependencyResolver.
Specialization of SubProblem for solving nonlinear equations plus auxiliary equations.
virtual void setActiveScalarVariableCoupleableVectorTags(std::set< TagID > &vtags, const THREAD_ID tid) override
virtual void reinitScalars(const THREAD_ID tid, bool reinit_for_derivative_reordering=false) override
fills the VariableValue arrays for scalar variables from the solution vector
virtual void setException(const std::string &message)
Set an exception, which is stored at this point by toggling a member variable in this class,...
virtual Real & dt() const
virtual void setActiveScalarVariableCoupleableMatrixTags(std::set< TagID > &mtags, const THREAD_ID tid) override
virtual void clearActiveScalarVariableCoupleableMatrixTags(const THREAD_ID tid) override
virtual void clearActiveScalarVariableCoupleableVectorTags(const THREAD_ID tid) override
std::shared_ptr< MooseObject > create(const std::string &obj_name, const std::string &name, const InputParameters &parameters, THREAD_ID tid=0, bool print_deprecated=true)
Definition Factory.C:142
The main MOOSE class responsible for handling user-defined parameters in almost every MOOSE system.
std::vector< std::pair< R1, R2 > > get(const std::string &param1, const std::string &param2) const
Combine two vector parameters into a single vector of pairs.
const std::string & getBase() const
Registration, update, and allocation logic for linear finite-volume cell gradients.
void rebuildLinearFVGradientStorage()
Rebuild cached gradient values and reusable scratch storage after mesh/DOF changes.
bool hasLinearFVGradients() const
Whether any linear finite-volume gradient fields have been registered to this object.
void computeGradients()
Compute and finalize all registered linear FV gradient fields.
Class for containing MooseEnum item information.
This is a "smart" enum class intended to replace many of the shortcomings in the C++ enum type It sho...
Definition MooseEnum.h:55
Provides a way for users to bail out of the current solve.
virtual const char * what() const
Get out the error message.
libMesh::ConstNodeRange * getLocalNodeRange()
Definition MooseMesh.C:1274
libMesh::StoredRange< MooseMesh::const_bnd_node_iterator, const BndNode * > * getBoundaryNodeRange()
Definition MooseMesh.C:1288
const libMesh::ConstElemRange * getActiveLocalElementRange()
Return pointers to range objects for various types of ranges (local nodes, boundary elems,...
Definition MooseMesh.C:1245
libMesh::StoredRange< MooseMesh::const_bnd_elem_iterator, const BndElement * > * getBoundaryElementRange()
Definition MooseMesh.C:1301
bool hasActiveObjects(THREAD_ID tid=0) const
const std::map< BoundaryID, std::vector< std::shared_ptr< T > > > & getActiveBoundaryObjects(THREAD_ID tid=0) const
bool hasActiveBlockObjects(THREAD_ID tid=0) const
bool hasActiveBoundaryObjects(THREAD_ID tid=0) const
const std::vector< std::shared_ptr< T > > & getActiveObjects(THREAD_ID tid=0) const
Retrieve complete vector to the active all/block/boundary restricted objects for a given thread.
A storage container for MooseObjects that inherit from SetupInterface.
virtual void timestepSetup(THREAD_ID tid=0) const
virtual void customSetup(const ExecFlagType &exec_type, THREAD_ID tid=0) const
virtual void subdomainSetup(THREAD_ID tid=0) const
virtual void initialSetup(THREAD_ID tid=0) const
Convenience methods for calling object setup methods.
Base variable class.
Class for stuff related to variables.
Interface for objects interacting with the PerfGraph.
Base class for a system (of equations)
Definition SystemBase.h:87
std::unique_ptr< NumericVector< Number > > _serialized_solution
Serialized version of the solution vector, or nullptr if a serialized solution is not needed.
FEProblemBase & _fe_problem
the governing finite element/volume problem
virtual void subdomainSetup()
std::vector< std::shared_ptr< TimeIntegrator > > _time_integrators
Time integrator.
virtual unsigned int nVariables() const
Get the number of variables in this system.
Definition SystemBase.C:890
Factory & _factory
virtual void addVariable(const std::string &var_type, const std::string &var_name, InputParameters &parameters)
Canonical method for adding a variable.
Definition SystemBase.C:717
virtual void customSetup(const ExecFlagType &exec_type)
NumericVector< Number > & solutionOld()
Definition SystemBase.h:204
virtual void initialSetup()
Setup Functions.
virtual void timestepSetup()
virtual void jacobianSetup()
virtual void residualSetup()
std::vector< VariableWarehouse > _vars
Variable warehouses (one for each thread)
virtual const NumericVector< Number > * solutionPreviousNewton() const
virtual const std::string & name() const
NumericVector< Number > & solution()
Definition SystemBase.h:203
const std::vector< MooseVariableScalar * > & getScalarVariables(THREAD_ID tid)
Definition SystemBase.h:777
MooseMesh & _mesh
void local_variable_indices(T &idx, const MeshBase &mesh, unsigned int var_num) const
virtual void close()=0
virtual void localize(std::vector< T > &v_local) const=0
const Parallel::Communicator & _communicator
std::unique_ptr< NumericVector< Number > > current_local_solution
dof_id_type n_dofs() const
virtual void update()
const DofMap & get_dof_map() const
MOOSE now contains C++17 code, so give a reasonable error message stating what the user can do to add...
@ VAR_AUXILIARY
Definition MooseTypes.h:771
std::string name(const ElemQuality q)
const Elem & get(const ElemType type_in)
void parallel_reduce(const Range &range, Body &body, unsigned int n_threads=libMesh::n_threads())
Tnew cast_ref(Told &oldvar)
unsigned int n_threads()
void translateMetaPhysicLError(const MetaPhysicL::LogicError &)
emit a relatively clear error message when we catch a MetaPhysicL logic error
Definition MooseError.C:153