LCOV - code coverage report
Current view: top level - src/variables - MooseVariableDataBase.C (source / functions) Hit Total Coverage
Test: idaholab/moose framework: #33390 (250e9c) with base 846a5c Lines: 335 411 81.5 %
Date: 2026-07-31 18:15:22 Functions: 85 109 78.0 %
Legend: Lines: hit not hit

          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 "MooseVariableDataBase.h"
      11             : #include "MooseError.h"
      12             : #include "MooseTypes.h"
      13             : #include "SystemBase.h"
      14             : #include "SubProblem.h"
      15             : #include "MooseVariableField.h"
      16             : 
      17             : template <typename OutputType>
      18      541528 : MooseVariableDataBase<OutputType>::MooseVariableDataBase(const MooseVariableField<OutputType> & var,
      19             :                                                          SystemBase & sys,
      20             :                                                          THREAD_ID tid)
      21      541528 :   : _sys(sys),
      22     1083056 :     _subproblem(_sys.subproblem()),
      23      541528 :     _tid(tid),
      24      541528 :     _dof_map(_sys.dofMap()),
      25      541528 :     _count(var.count()),
      26      541528 :     _has_dof_values(false),
      27      541528 :     _max_state(0),
      28      541528 :     _solution_tag(_subproblem.getVectorTagID(Moose::SOLUTION_TAG)),
      29      541528 :     _old_solution_tag(Moose::INVALID_TAG_ID),
      30      541528 :     _older_solution_tag(Moose::INVALID_TAG_ID),
      31      541528 :     _previous_nl_solution_tag(Moose::INVALID_TAG_ID),
      32      541528 :     _need_u_dot(false),
      33      541528 :     _need_u_dotdot(false),
      34      541528 :     _need_u_dot_old(false),
      35      541528 :     _need_u_dotdot_old(false),
      36      541528 :     _need_du_dot_du(false),
      37      541528 :     _need_du_dotdot_du(false),
      38      541528 :     _need_grad_dot(false),
      39      541528 :     _need_grad_dotdot(false),
      40      541528 :     _need_dof_values_dot(false),
      41      541528 :     _need_dof_values_dotdot(false),
      42      541528 :     _need_dof_values_dot_old(false),
      43      541528 :     _need_dof_values_dotdot_old(false),
      44      541528 :     _need_dof_du_dot_du(false),
      45      541528 :     _need_dof_du_dotdot_du(false),
      46     1083056 :     _var(var)
      47             : {
      48      541528 :   auto num_vector_tags = _subproblem.numVectorTags();
      49             :   // Additional solution tags corresponding to older-than-current solution states may be requested
      50             :   // on-the-fly by consumer objects after variable construction. To accomodate this we should
      51             :   // reserve the possibly requisite memory. As of now we only support old and older solution states
      52             :   // but this could potentially increase in the future
      53      541528 :   const auto max_future_num_vector_tags = num_vector_tags + 2;
      54             : 
      55      541528 :   _vector_tags_dof_u.reserve(max_future_num_vector_tags);
      56      541528 :   _vector_tags_dof_u.resize(num_vector_tags);
      57      541528 :   _need_vector_tag_dof_u.reserve(max_future_num_vector_tags);
      58      541528 :   _need_vector_tag_dof_u.resize(num_vector_tags, false);
      59             : 
      60      541528 :   _need_vector_tag_u.reserve(max_future_num_vector_tags);
      61      541528 :   _need_vector_tag_u.resize(num_vector_tags, false);
      62      541528 :   _vector_tag_u.reserve(max_future_num_vector_tags);
      63      541528 :   _vector_tag_u.resize(num_vector_tags);
      64             : 
      65      541528 :   _need_vector_tag_grad.reserve(max_future_num_vector_tags);
      66      541528 :   _need_vector_tag_grad.resize(num_vector_tags, false);
      67      541528 :   _vector_tag_grad.reserve(max_future_num_vector_tags);
      68      541528 :   _vector_tag_grad.resize(num_vector_tags);
      69             : 
      70             :   // Always fetch the dof values for the solution tag
      71      541528 :   const auto soln_tag = _subproblem.getVectorTagID(Moose::SOLUTION_TAG);
      72      541528 :   _need_vector_tag_dof_u[soln_tag] = true;
      73      541528 :   _need_vector_tag_u[soln_tag] = true;
      74      541528 :   insertSolutionTag(soln_tag);
      75             : 
      76             :   // These MooseArray objects are used by AuxKernelBase for nodal AuxKernel objects, hence the size
      77             :   // size is always 1 (i.e, nodal kernels work with _qp=0 only).
      78      541528 :   _nodal_value_array.resize(1);
      79      541528 :   _nodal_value_old_array.resize(1);
      80      541528 :   _nodal_value_older_array.resize(1);
      81      541528 : }
      82             : 
      83             : template <typename OutputType>
      84             : void
      85      391921 : MooseVariableDataBase<OutputType>::sizeMatrixTagData()
      86             : {
      87      391921 :   auto num_matrix_tags = _subproblem.numMatrixTags();
      88             : 
      89      391921 :   _matrix_tags_dof_u.resize(num_matrix_tags);
      90      391921 :   _need_matrix_tag_dof_u.resize(num_matrix_tags, false);
      91             : 
      92      391921 :   _need_matrix_tag_u.resize(num_matrix_tags, false);
      93      391921 :   _matrix_tag_u.resize(num_matrix_tags);
      94      391921 : }
      95             : 
      96             : template <typename OutputType>
      97             : const typename MooseVariableDataBase<OutputType>::DofValues &
      98         433 : MooseVariableDataBase<OutputType>::nodalVectorTagValue(TagID tag) const
      99             : {
     100         433 :   if (isNodal())
     101             :   {
     102         433 :     if (tag >= _need_vector_tag_dof_u.size())
     103           0 :       const_cast<MooseVariableDataBase<OutputType> *>(this)->resizeVectorTagData(tag);
     104             : 
     105         433 :     _need_vector_tag_dof_u[tag] = true;
     106             : 
     107         433 :     if (_sys.hasVector(tag))
     108         433 :       return _vector_tags_dof_u[tag];
     109             :     else
     110           0 :       mooseError(
     111           0 :           "Tag ", tag, " is not associated with any vector for nodal variable ", _var.name());
     112             :   }
     113             :   else
     114           0 :     mooseError("Nodal values can be requested only on nodal variables, variable '",
     115           0 :                _var.name(),
     116             :                "' is not nodal.");
     117             : }
     118             : 
     119             : template <typename OutputType>
     120             : const typename MooseVariableDataBase<OutputType>::DofValues &
     121         225 : MooseVariableDataBase<OutputType>::nodalMatrixTagValue(TagID tag) const
     122             : {
     123         225 :   if (isNodal())
     124             :   {
     125         225 :     if (tag >= _matrix_tags_dof_u.size())
     126             :     {
     127           0 :       _need_matrix_tag_dof_u.resize(tag + 1, false);
     128           0 :       const_cast<MooseVariableDataBase<OutputType> *>(this)->_matrix_tags_dof_u.resize(tag + 1);
     129             :     }
     130             : 
     131         225 :     _need_matrix_tag_dof_u[tag] = true;
     132             : 
     133         225 :     if (_sys.hasMatrix(tag))
     134         225 :       return _matrix_tags_dof_u[tag];
     135             :     else
     136           0 :       mooseError(
     137           0 :           "Tag ", tag, " is not associated with any matrix for nodal variable ", _var.name());
     138             :   }
     139             :   else
     140           0 :     mooseError("Nodal values can be requested only on nodal variables, variable '",
     141           0 :                _var.name(),
     142             :                "' is not nodal.");
     143             : }
     144             : 
     145             : template <typename OutputType>
     146             : void
     147         490 : MooseVariableDataBase<OutputType>::resizeVectorTagData(TagID tag)
     148             : {
     149             :   mooseAssert(_need_vector_tag_dof_u.size() == _need_vector_tag_u.size() &&
     150             :                   _need_vector_tag_dof_u.size() == _need_vector_tag_grad.size() &&
     151             :                   _need_vector_tag_dof_u.size() == _vector_tags_dof_u.size() &&
     152             :                   _need_vector_tag_dof_u.size() == _vector_tag_u.size() &&
     153             :                   _need_vector_tag_dof_u.size() == _vector_tag_grad.size(),
     154             :               "These sizes should be in sync.");
     155             : 
     156        6370 :   auto check_capacity = [tag](const auto & vector_to_check)
     157             :   {
     158        2940 :     if (tag + 1 > vector_to_check.capacity())
     159           0 :       mooseError("New size greater than tag capacity. This will cause reallocation which will "
     160             :                  "invalidate any stored references.");
     161             :   };
     162         490 :   check_capacity(_need_vector_tag_dof_u);
     163         490 :   check_capacity(_need_vector_tag_u);
     164         490 :   check_capacity(_need_vector_tag_grad);
     165         490 :   check_capacity(_vector_tags_dof_u);
     166         490 :   check_capacity(_vector_tag_u);
     167         490 :   check_capacity(_vector_tag_grad);
     168             : 
     169         490 :   _need_vector_tag_dof_u.resize(tag + 1, false);
     170         490 :   _need_vector_tag_u.resize(tag + 1, false);
     171         490 :   _need_vector_tag_grad.resize(tag + 1, false);
     172         490 :   _vector_tags_dof_u.resize(tag + 1);
     173         490 :   _vector_tag_u.resize(tag + 1);
     174         490 :   _vector_tag_grad.resize(tag + 1);
     175         490 : }
     176             : 
     177             : template <typename OutputType>
     178             : const typename MooseVariableDataBase<OutputType>::FieldVariableValue &
     179      294140 : MooseVariableDataBase<OutputType>::vectorTagValue(TagID tag) const
     180             : {
     181      294140 :   if (tag >= _need_vector_tag_u.size())
     182         117 :     const_cast<MooseVariableDataBase<OutputType> *>(this)->resizeVectorTagData(tag);
     183             : 
     184      294140 :   _var.requireQpComputations();
     185             : 
     186      294140 :   _need_vector_tag_u[tag] = true;
     187             : 
     188      294140 :   if (_sys.hasVector(tag))
     189      294140 :     return _vector_tag_u[tag];
     190             :   else
     191           0 :     mooseError("Tag ", tag, " is not associated with any vector for variable ", _var.name());
     192             : }
     193             : 
     194             : template <typename OutputType>
     195             : const typename MooseVariableDataBase<OutputType>::DofValues &
     196      917261 : MooseVariableDataBase<OutputType>::vectorTagDofValue(TagID tag) const
     197             : {
     198      917261 :   if (tag >= _need_vector_tag_dof_u.size())
     199         156 :     const_cast<MooseVariableDataBase<OutputType> *>(this)->resizeVectorTagData(tag);
     200             : 
     201      917261 :   _var.requireQpComputations();
     202             : 
     203      917261 :   _need_vector_tag_dof_u[tag] = true;
     204             : 
     205      917261 :   if (_sys.hasVector(tag))
     206      917261 :     return _vector_tags_dof_u[tag];
     207             :   else
     208           0 :     mooseError("Tag ", tag, " is not associated with any vector for variable ", _var.name());
     209             : }
     210             : 
     211             : template <typename OutputType>
     212             : const typename MooseVariableDataBase<OutputType>::FieldVariableGradient &
     213      129123 : MooseVariableDataBase<OutputType>::vectorTagGradient(TagID tag) const
     214             : {
     215      129123 :   if (tag >= _need_vector_tag_grad.size())
     216          13 :     const_cast<MooseVariableDataBase<OutputType> *>(this)->resizeVectorTagData(tag);
     217             : 
     218      129123 :   _var.requireQpComputations();
     219             : 
     220      129123 :   _need_vector_tag_grad[tag] = true;
     221             : 
     222      129123 :   if (_sys.hasVector(tag))
     223      129123 :     return _vector_tag_grad[tag];
     224             :   else
     225           0 :     mooseError("Tag ", tag, " is not associated with any vector for variable ", _var.name());
     226             : }
     227             : 
     228             : template <typename OutputType>
     229             : const typename MooseVariableDataBase<OutputType>::FieldVariableValue &
     230          48 : MooseVariableDataBase<OutputType>::matrixTagValue(TagID tag) const
     231             : {
     232          48 :   if (tag >= _matrix_tag_u.size())
     233             :   {
     234           0 :     _need_matrix_tag_u.resize(tag + 1, false);
     235           0 :     const_cast<MooseVariableDataBase<OutputType> *>(this)->_matrix_tag_u.resize(tag + 1);
     236             :   }
     237             : 
     238          48 :   _var.requireQpComputations();
     239             : 
     240          48 :   _need_matrix_tag_u[tag] = true;
     241             : 
     242          48 :   if (_sys.hasMatrix(tag))
     243          48 :     return _matrix_tag_u[tag];
     244             :   else
     245           0 :     mooseError("Tag ", tag, " is not associated with any matrix for variable ", _var.name());
     246             : }
     247             : 
     248             : template <typename OutputType>
     249             : unsigned int
     250   441126066 : MooseVariableDataBase<OutputType>::oldestSolutionStateRequested() const
     251             : {
     252   441126066 :   return _max_state;
     253             : }
     254             : 
     255             : template <typename OutputType>
     256             : void
     257       35944 : MooseVariableDataBase<OutputType>::needSolutionState(const unsigned int state)
     258             : {
     259       35944 :   if (state > _max_state)
     260             :   {
     261       15750 :     _sys.needSolutionState(state);
     262       15750 :     _max_state = state;
     263             :   }
     264       35944 : }
     265             : 
     266             : template <typename OutputType>
     267             : template <typename ReturnType, typename Functor>
     268             : const ReturnType &
     269     1339658 : MooseVariableDataBase<OutputType>::stateToTagHelper(const Moose::SolutionState state,
     270             :                                                     Functor functor)
     271             : {
     272     1339658 :   if (state > 0)
     273             :   {
     274             :     // We need to request all states that are between current and the requested state
     275       35944 :     stateToTagHelper<ReturnType>(Moose::SolutionState(static_cast<int>(state) - 1), functor);
     276       35944 :     needSolutionState(cast_int<unsigned int>(state));
     277             :   }
     278             : 
     279     1339658 :   switch (state)
     280             :   {
     281     1303638 :     case Moose::Current:
     282     1303638 :       return functor(_subproblem.getVectorTagID(Moose::SOLUTION_TAG));
     283             : 
     284       24777 :     case Moose::Old:
     285             :     {
     286       24777 :       _old_solution_tag = _subproblem.getVectorTagID(Moose::OLD_SOLUTION_TAG);
     287       24777 :       insertSolutionTag(_old_solution_tag);
     288       24777 :       return functor(_old_solution_tag);
     289             :     }
     290             : 
     291       11167 :     case Moose::Older:
     292             :     {
     293       11167 :       _older_solution_tag = _subproblem.getVectorTagID(Moose::OLDER_SOLUTION_TAG);
     294       11167 :       insertSolutionTag(_older_solution_tag);
     295       11167 :       return functor(_older_solution_tag);
     296             :     }
     297             : 
     298          76 :     case Moose::PreviousNL:
     299             :     {
     300          76 :       _previous_nl_solution_tag = _subproblem.getVectorTagID(Moose::PREVIOUS_NL_SOLUTION_TAG);
     301          76 :       insertSolutionTag(_previous_nl_solution_tag);
     302          76 :       return functor(_previous_nl_solution_tag);
     303             :     }
     304             : 
     305           0 :     default:
     306             :       // We should never get here but gcc requires that we have a default. See
     307             :       // htpps://stackoverflow.com/questions/18680378/after-defining-case-for-all-enum-values-compiler-still-says-control-reaches-e
     308           0 :       mooseError("Unknown SolutionState!");
     309             :   }
     310             : }
     311             : 
     312             : template <typename OutputType>
     313             : const typename MooseVariableDataBase<OutputType>::FieldVariableValue &
     314      258805 : MooseVariableDataBase<OutputType>::sln(Moose::SolutionState state) const
     315             : {
     316      552236 :   auto functor = [this](TagID tag_id) -> const FieldVariableValue &
     317      293431 :   { return vectorTagValue(tag_id); };
     318             : 
     319      258805 :   _var.requireQpComputations();
     320             : 
     321             :   return const_cast<MooseVariableDataBase<OutputType> *>(this)
     322      517610 :       ->stateToTagHelper<FieldVariableValue>(state, functor);
     323             : }
     324             : 
     325             : template <typename OutputType>
     326             : const typename MooseVariableDataBase<OutputType>::FieldVariableGradient &
     327      128167 : MooseVariableDataBase<OutputType>::gradSln(Moose::SolutionState state) const
     328             : {
     329      257264 :   auto functor = [this](TagID tag_id) -> const FieldVariableGradient &
     330      129097 :   { return vectorTagGradient(tag_id); };
     331             : 
     332      128167 :   _var.requireQpComputations();
     333             : 
     334             :   return const_cast<MooseVariableDataBase<OutputType> *>(this)
     335      256334 :       ->stateToTagHelper<FieldVariableGradient>(state, functor);
     336             : }
     337             : 
     338             : template <typename OutputType>
     339             : const typename MooseVariableDataBase<OutputType>::DofValues &
     340      916742 : MooseVariableDataBase<OutputType>::vectorTagDofValue(Moose::SolutionState state) const
     341             : {
     342     1833872 :   auto functor = [this](TagID tag_id) -> const DofValues & { return vectorTagDofValue(tag_id); };
     343             : 
     344      916742 :   _var.requireQpComputations();
     345             : 
     346      916742 :   return const_cast<MooseVariableDataBase<OutputType> *>(this)->stateToTagHelper<DofValues>(
     347     1833484 :       state, functor);
     348             : }
     349             : 
     350             : template <typename OutputType>
     351             : const typename MooseVariableDataBase<OutputType>::DofValues &
     352      892101 : MooseVariableDataBase<OutputType>::dofValues() const
     353             : {
     354      892101 :   return vectorTagDofValue(Moose::Current);
     355             : }
     356             : 
     357             : template <typename OutputType>
     358             : const typename MooseVariableDataBase<OutputType>::DofValues &
     359         128 : MooseVariableDataBase<OutputType>::dofValuesOld() const
     360             : {
     361         128 :   return vectorTagDofValue(Moose::Old);
     362             : }
     363             : 
     364             : template <typename OutputType>
     365             : const typename MooseVariableDataBase<OutputType>::DofValues &
     366          52 : MooseVariableDataBase<OutputType>::dofValuesOlder() const
     367             : {
     368          52 :   return vectorTagDofValue(Moose::Older);
     369             : }
     370             : 
     371             : template <typename OutputType>
     372             : const typename MooseVariableDataBase<OutputType>::DofValues &
     373           0 : MooseVariableDataBase<OutputType>::dofValuesPreviousNL() const
     374             : {
     375           0 :   return vectorTagDofValue(Moose::PreviousNL);
     376             : }
     377             : 
     378             : template <typename OutputType>
     379             : void
     380    46038132 : MooseVariableDataBase<OutputType>::setNodalValue(const OutputType & value, unsigned int idx)
     381             : {
     382    46038132 :   auto & dof_values = _vector_tags_dof_u[_solution_tag];
     383             :   mooseAssert(idx < dof_values.size(), "idx is out of the bounds of degree of freedom values");
     384    46038132 :   dof_values[idx] = value; // update variable nodal value
     385    46038132 :   _has_dof_values = true;
     386    46038132 :   _nodal_value = value;
     387             : 
     388             :   // Update the qp values as well
     389    46038132 :   auto & u = _vector_tag_u[_solution_tag];
     390   229010636 :   for (unsigned int qp = 0; qp < u.size(); qp++)
     391   182972504 :     u[qp] = value;
     392    46038132 : }
     393             : 
     394             : template <>
     395             : void
     396        8315 : MooseVariableDataBase<RealVectorValue>::setNodalValue(const RealVectorValue & value,
     397             :                                                       unsigned int idx)
     398             : {
     399        8315 :   auto & dof_values = _vector_tags_dof_u[_solution_tag];
     400       28449 :   for (decltype(idx) i = 0; i < dof_values.size(); ++i, ++idx)
     401       20134 :     dof_values[idx] = value(i);
     402             : 
     403        8315 :   _has_dof_values = true;
     404        8315 :   _nodal_value = value;
     405        8315 : }
     406             : 
     407             : template <typename OutputType>
     408             : void
     409    49785303 : MooseVariableDataBase<OutputType>::insert(NumericVector<Number> & residual)
     410             : {
     411    49785303 :   if (_has_dof_values)
     412             :   {
     413    48678340 :     const auto & dof_values = _vector_tags_dof_u[_solution_tag];
     414             :     mooseAssert(dof_values.size() == _dof_indices.size(),
     415             :                 "Degree of freedom values size and degree of freedom indices sizes must match.");
     416    48678340 :     residual.insert(&dof_values[0], _dof_indices);
     417             :   }
     418    49785303 : }
     419             : 
     420             : template <>
     421             : void
     422      635442 : MooseVariableDataBase<RealEigenVector>::insert(NumericVector<Number> & residual)
     423             : {
     424      635442 :   if (_has_dof_values)
     425             :   {
     426      635442 :     const auto & dof_values = _vector_tags_dof_u[_solution_tag];
     427             :     mooseAssert(_dof_indices.size() % _count == 0,
     428             :                 "Dof indices should be cleanly divisible by the variable count");
     429      635442 :     const auto n_shapes = _dof_indices.size() / _count;
     430     2467820 :     for (const auto indx : index_range(_dof_indices))
     431             :     {
     432     1832378 :       const auto i = indx % n_shapes;
     433     1832378 :       const auto j = indx / n_shapes;
     434     1832378 :       residual.set(_dof_indices[indx], dof_values[i](j));
     435             :     }
     436             :   }
     437      635442 : }
     438             : 
     439             : template <typename OutputType>
     440             : void
     441     1959703 : MooseVariableDataBase<OutputType>::add(NumericVector<Number> & residual)
     442             : {
     443     1959703 :   if (_has_dof_values)
     444             :   {
     445       33256 :     const auto & dof_values = _vector_tags_dof_u[_solution_tag];
     446       33256 :     residual.add_vector(&dof_values[0], _dof_indices);
     447             :   }
     448     1959703 : }
     449             : 
     450             : template <>
     451             : void
     452           0 : MooseVariableDataBase<RealEigenVector>::add(NumericVector<Number> & residual)
     453             : {
     454           0 :   if (_has_dof_values)
     455             :   {
     456           0 :     const auto & dof_values = _vector_tags_dof_u[_solution_tag];
     457             :     mooseAssert(_dof_indices.size() % _count == 0,
     458             :                 "Dof indices should be cleanly divisible by the variable count");
     459           0 :     const auto n_shapes = _dof_indices.size() / _count;
     460           0 :     for (const auto indx : index_range(_dof_indices))
     461             :     {
     462           0 :       const auto i = indx % n_shapes;
     463           0 :       const auto j = indx / n_shapes;
     464           0 :       residual.add(_dof_indices[indx], dof_values[i](j));
     465             :     }
     466             :   }
     467           0 : }
     468             : 
     469             : template <typename OutputType>
     470             : const OutputType &
     471        1239 : MooseVariableDataBase<OutputType>::nodalValue(Moose::SolutionState state) const
     472             : {
     473        1239 :   if (isNodal())
     474             :   {
     475             :     // Request the correct solution states and data members
     476        1239 :     vectorTagDofValue(state);
     477        1239 :     switch (state)
     478             :     {
     479        1239 :       case Moose::Current:
     480        1239 :         return _nodal_value;
     481             : 
     482           0 :       case Moose::Old:
     483           0 :         return _nodal_value_old;
     484             : 
     485           0 :       case Moose::Older:
     486           0 :         return _nodal_value_older;
     487             : 
     488           0 :       case Moose::PreviousNL:
     489           0 :         return _nodal_value_previous_nl;
     490             : 
     491           0 :       default:
     492             :         // We should never get here but gcc requires that we have a default. See
     493             :         // htpps://stackoverflow.com/questions/18680378/after-defining-case-for-all-enum-values-compiler-still-says-control-reaches-e
     494           0 :         mooseError("Unknown SolutionState!");
     495             :     }
     496             :   }
     497             :   else
     498           0 :     mooseError("Nodal values can be requested only on nodal variables, variable '",
     499           0 :                _var.name(),
     500             :                "' is not nodal.");
     501             : }
     502             : 
     503             : template <typename OutputType>
     504             : const MooseArray<OutputType> &
     505       23222 : MooseVariableDataBase<OutputType>::nodalValueArray(Moose::SolutionState state) const
     506             : {
     507       23222 :   if (isNodal())
     508             :   {
     509             :     // Request the correct solution states and data members
     510       23222 :     vectorTagDofValue(state);
     511       23222 :     switch (state)
     512             :     {
     513       23079 :       case Moose::Current:
     514       23079 :         return _nodal_value_array;
     515             : 
     516         130 :       case Moose::Old:
     517         130 :         return _nodal_value_old_array;
     518             : 
     519          13 :       case Moose::Older:
     520          13 :         return _nodal_value_older_array;
     521             : 
     522           0 :       default:
     523           0 :         mooseError("No current support for PreviousNL for nodal value array");
     524             :     }
     525             :   }
     526             :   else
     527           0 :     mooseError("Nodal values can be requested only on nodal variables, variable '",
     528           0 :                _var.name(),
     529             :                "' is not nodal.");
     530             : }
     531             : 
     532             : template <typename OutputType>
     533             : void
     534  1042343390 : MooseVariableDataBase<OutputType>::fetchDofValues()
     535             : {
     536  1042343390 :   bool is_transient = _subproblem.isTransient();
     537             : 
     538  1042343390 :   auto n = _dof_indices.size();
     539             :   libmesh_assert(n);
     540             : 
     541  1042343390 :   if (is_transient)
     542             :   {
     543   823107020 :     if (_need_u_dot || _need_grad_dot || _need_dof_values_dot)
     544             :     {
     545             :       libmesh_assert(_sys.solutionUDot());
     546   305779312 :       _dof_values_dot.resize(n);
     547   305779312 :       _sys.solutionUDot()->get(_dof_indices, &_dof_values_dot[0]);
     548             :     }
     549   823107020 :     if (_need_u_dotdot || _need_grad_dotdot || _need_dof_values_dotdot)
     550             :     {
     551             :       libmesh_assert(_sys.solutionUDotDot());
     552       13246 :       _dof_values_dotdot.resize(n);
     553       13246 :       _sys.solutionUDotDot()->get(_dof_indices, &_dof_values_dotdot[0]);
     554             :     }
     555   823107020 :     if (_need_u_dot_old || _need_dof_values_dot_old)
     556             :     {
     557             :       libmesh_assert(_sys.solutionUDotOld());
     558           0 :       _dof_values_dot_old.resize(n);
     559           0 :       _sys.solutionUDotOld()->get(_dof_indices, &_dof_values_dot_old[0]);
     560             :     }
     561   823107020 :     if (_need_u_dotdot_old || _need_dof_values_dotdot_old)
     562             :     {
     563             :       libmesh_assert(_sys.solutionUDotDotOld());
     564           0 :       _dof_values_dotdot_old.resize(n);
     565           0 :       _sys.solutionUDotDotOld()->get(_dof_indices, &_dof_values_dotdot_old[0]);
     566             :     }
     567             :   }
     568             : 
     569  2096854369 :   for (auto tag : _required_vector_tags)
     570  1054510979 :     if (_need_vector_tag_u[tag] || _need_vector_tag_grad[tag] || _need_vector_tag_dof_u[tag])
     571  1054008780 :       if ((_subproblem.vectorTagType(tag) == Moose::VECTOR_TAG_RESIDUAL &&
     572  2107938031 :            _subproblem.safeAccessTaggedVectors()) ||
     573  1053929251 :           _subproblem.vectorTagType(tag) == Moose::VECTOR_TAG_SOLUTION)
     574             :       {
     575             :         // tag is defined on problem but may not be used by a system
     576             :         // the grain tracker requires being able to read from solution vectors that we are also in
     577             :         // the process of writing :-/
     578             :         // Note: the extra vector tags are also still not closed when a TagVectorAux uses them
     579  1054008780 :         if (_sys.hasVector(tag) /* && _sys.getVector(tag).closed()*/)
     580             :         {
     581  1054008780 :           auto & vec = _sys.getVector(tag);
     582  1054008780 :           _vector_tags_dof_u[tag].resize(n);
     583  1054008780 :           vec.get(_dof_indices, &_vector_tags_dof_u[tag][0]);
     584             :         }
     585             :       }
     586             : 
     587  1042343390 :   if (_subproblem.safeAccessTaggedMatrices())
     588             :   {
     589             :     auto & active_coupleable_matrix_tags =
     590   831573807 :         _subproblem.getActiveFEVariableCoupleableMatrixTags(_tid);
     591             : 
     592   831849434 :     for (auto tag : active_coupleable_matrix_tags)
     593             :     {
     594      275627 :       _matrix_tags_dof_u[tag].resize(n);
     595      275627 :       if (_need_matrix_tag_dof_u[tag] || _need_matrix_tag_u[tag])
     596       69085 :         if (_sys.hasMatrix(tag) && _sys.matrixTagActive(tag))
     597             :         {
     598             :           mooseAssert(_sys.getMatrix(tag).closed(),
     599             :                       "Matrix with tag '" + std::to_string(tag) + "' should be closed");
     600       69085 :           auto & mat = _sys.getMatrix(tag);
     601      138426 :           for (unsigned i = 0; i < n; i++)
     602       69341 :             _matrix_tags_dof_u[tag][i] = mat(_dof_indices[i], _dof_indices[i]);
     603             :         }
     604             :     }
     605             :   }
     606             : 
     607  1042343390 :   if (_need_du_dot_du || _need_dof_du_dot_du)
     608             :   {
     609   305773800 :     _dof_du_dot_du.resize(n);
     610  1408902486 :     for (decltype(n) i = 0; i < n; ++i)
     611  1103128686 :       _dof_du_dot_du[i] = _sys.duDotDu(_var.number());
     612             :   }
     613  1042343390 :   if (_need_du_dotdot_du || _need_dof_du_dotdot_du)
     614             :   {
     615        9646 :     _dof_du_dotdot_du.resize(n);
     616       56942 :     for (decltype(n) i = 0; i < n; ++i)
     617       47296 :       _dof_du_dotdot_du[i] = _sys.duDotDotDu();
     618             :   }
     619  1042343390 : }
     620             : 
     621             : template <typename OutputType>
     622             : void
     623     7620558 : MooseVariableDataBase<OutputType>::getArrayDofValues(const NumericVector<Number> & sol,
     624             :                                                      const unsigned int nshapes,
     625             :                                                      MooseArray<RealEigenVector> & dof_values) const
     626             : {
     627     7620558 :   dof_values.resize(nshapes);
     628    31344158 :   for (const auto i : make_range(nshapes))
     629             :   {
     630    23723600 :     dof_values[i].resize(_count);
     631    72811877 :     for (const auto j : make_range(_count))
     632    49088277 :       dof_values[i](j) = sol(_dof_indices[j * nshapes + i]);
     633             :   }
     634     7620558 : }
     635             : 
     636             : template <>
     637             : void
     638     5351604 : MooseVariableDataBase<RealEigenVector>::fetchDofValues()
     639             : {
     640     5351604 :   bool is_transient = _subproblem.isTransient();
     641             : 
     642     5351604 :   auto n = _dof_indices.size() / _count;
     643             :   libmesh_assert(n);
     644             : 
     645     5351604 :   if (is_transient)
     646             :   {
     647     4998738 :     if (_need_u_dot || _need_grad_dot || _need_dof_values_dot)
     648             :     {
     649             :       libmesh_assert(_sys.solutionUDot());
     650     2268376 :       getArrayDofValues(*_sys.solutionUDot(), n, _dof_values_dot);
     651             :     }
     652     4998738 :     if (_need_u_dotdot || _need_grad_dotdot || _need_dof_values_dotdot)
     653             :     {
     654             :       libmesh_assert(_sys.solutionUDotDot());
     655           0 :       getArrayDofValues(*_sys.solutionUDot(), n, _dof_values_dotdot);
     656             :     }
     657     4998738 :     if (_need_u_dot_old || _need_dof_values_dot_old)
     658             :     {
     659             :       libmesh_assert(_sys.solutionUDotOld());
     660           0 :       getArrayDofValues(*_sys.solutionUDotOld(), n, _dof_values_dot_old);
     661             :     }
     662     4998738 :     if (_need_u_dotdot_old || _need_dof_values_dotdot_old)
     663             :     {
     664             :       libmesh_assert(_sys.solutionUDotDotOld());
     665           0 :       getArrayDofValues(*_sys.solutionUDotDotOld(), n, _dof_values_dotdot_old);
     666             :     }
     667             :   }
     668             : 
     669    10704748 :   for (auto tag : _required_vector_tags)
     670     5353144 :     if ((_subproblem.vectorTagType(tag) == Moose::VECTOR_TAG_RESIDUAL &&
     671    10704748 :          _subproblem.safeAccessTaggedVectors()) ||
     672     5351604 :         _subproblem.vectorTagType(tag) == Moose::VECTOR_TAG_SOLUTION)
     673             :       // tag is defined on problem but may not be used by a system
     674     5353144 :       if (_sys.hasVector(tag))
     675             :       {
     676             :         mooseAssert(_sys.getVector(tag).closed(),
     677             :                     "Vector with tag '" + std::to_string(tag) + "' should be closed");
     678     5352182 :         getArrayDofValues(_sys.getVector(tag), n, _vector_tags_dof_u[tag]);
     679             :       }
     680             : 
     681     5351604 :   if (_subproblem.safeAccessTaggedMatrices())
     682             :   {
     683             :     auto & active_coupleable_matrix_tags =
     684     4631461 :         _subproblem.getActiveFEVariableCoupleableMatrixTags(_tid);
     685     4631461 :     for (auto tag : active_coupleable_matrix_tags)
     686             :     {
     687           0 :       _matrix_tags_dof_u[tag].resize(n);
     688           0 :       if (_need_matrix_tag_dof_u[tag] || _need_matrix_tag_u[tag])
     689           0 :         if (_sys.hasMatrix(tag) && _sys.matrixTagActive(tag))
     690             :         {
     691             :           mooseAssert(_sys.getMatrix(tag).closed(),
     692             :                       "Matrix with tag '" + std::to_string(tag) + "' should be closed");
     693           0 :           auto & mat = _sys.getMatrix(tag);
     694           0 :           for (unsigned i = 0; i < n; i++)
     695           0 :             for (unsigned j = 0; j < _count; j++)
     696           0 :               _matrix_tags_dof_u[tag][i](j) = mat(_dof_indices[i] + j, _dof_indices[i] + j);
     697             :         }
     698             :     }
     699             :   }
     700             : 
     701     5351604 :   if (_need_du_dot_du || _need_dof_du_dot_du)
     702             :   {
     703     2268376 :     _dof_du_dot_du.resize(n);
     704    10061977 :     for (decltype(n) i = 0; i < n; ++i)
     705     7793601 :       _dof_du_dot_du[i] = _sys.duDotDu(_var.number());
     706             :   }
     707     5351604 :   if (_need_du_dotdot_du || _need_dof_du_dotdot_du)
     708             :   {
     709           0 :     _dof_du_dotdot_du.resize(n);
     710           0 :     for (decltype(n) i = 0; i < n; ++i)
     711           0 :       _dof_du_dotdot_du[i] = _sys.duDotDotDu();
     712             :   }
     713     5351604 : }
     714             : 
     715             : template <typename OutputType>
     716             : void
     717         204 : MooseVariableDataBase<OutputType>::zeroSizeDofValues()
     718             : {
     719         204 :   if (_subproblem.isTransient())
     720             :   {
     721         168 :     _dof_values_dot.resize(0);
     722         168 :     _dof_values_dotdot.resize(0);
     723         168 :     _dof_values_dot_old.resize(0);
     724         168 :     _dof_values_dotdot_old.resize(0);
     725         168 :     _dof_du_dot_du.resize(0);
     726         168 :     _dof_du_dotdot_du.resize(0);
     727             :   }
     728             : 
     729        1488 :   for (auto & dof_values : _vector_tags_dof_u)
     730        1284 :     dof_values.resize(0);
     731             : 
     732         204 :   _has_dof_values = false;
     733         204 : }
     734             : 
     735             : template <typename OutputType>
     736             : void
     737   246466848 : MooseVariableDataBase<OutputType>::assignNodalValue()
     738             : {
     739   246466848 :   bool is_transient = _subproblem.isTransient();
     740             :   libmesh_assert(_dof_indices.size());
     741             : 
     742   246466848 :   auto & dof_values = _vector_tags_dof_u[_solution_tag];
     743   246466848 :   _nodal_value = dof_values[0];
     744   246466848 :   _nodal_value_array[0] = _nodal_value;
     745             : 
     746   246466848 :   if (is_transient)
     747             :   {
     748   220080450 :     if (oldestSolutionStateRequested() >= 1)
     749             :     {
     750     4582330 :       _nodal_value_old = _vector_tags_dof_u[_old_solution_tag][0];
     751     4582330 :       _nodal_value_old_array[0] = _nodal_value_old;
     752             :     }
     753   220080450 :     if (oldestSolutionStateRequested() >= 2)
     754             :     {
     755     1606903 :       _nodal_value_older = _vector_tags_dof_u[_older_solution_tag][0];
     756     1606903 :       _nodal_value_older_array[0] = _nodal_value_older;
     757             :     }
     758   220080450 :     if (_need_dof_values_dot)
     759     1406446 :       _nodal_value_dot = _dof_values_dot[0];
     760   220080450 :     if (_need_dof_values_dotdot)
     761           0 :       _nodal_value_dotdot = _dof_values_dotdot[0];
     762   220080450 :     if (_need_dof_values_dot_old)
     763           0 :       _nodal_value_dot_old = _dof_values_dot_old[0];
     764   220080450 :     if (_need_dof_values_dotdot_old)
     765           0 :       _nodal_value_dotdot_old = _dof_values_dotdot_old[0];
     766             :   }
     767   246466848 :   if (_previous_nl_solution_tag != Moose::INVALID_TAG_ID)
     768       47014 :     _nodal_value_previous_nl = _vector_tags_dof_u[_previous_nl_solution_tag][0];
     769   246466848 : }
     770             : 
     771             : template <>
     772             : void
     773      467911 : MooseVariableDataBase<RealVectorValue>::assignNodalValue()
     774             : {
     775      467911 :   bool is_transient = _subproblem.isTransient();
     776             : 
     777      467911 :   auto n = _dof_indices.size();
     778             :   libmesh_assert(n);
     779             : 
     780      467911 :   auto & dof_values = _vector_tags_dof_u[_solution_tag];
     781     1535513 :   for (decltype(n) i = 0; i < n; ++i)
     782     1067602 :     _nodal_value(i) = dof_values[i];
     783      467911 :   _nodal_value_array[0] = _nodal_value;
     784             : 
     785      467911 :   if (is_transient)
     786             :   {
     787      242945 :     if (oldestSolutionStateRequested() >= 1)
     788             :     {
     789       42537 :       auto & dof_values_old = _vector_tags_dof_u[_old_solution_tag];
     790      167123 :       for (decltype(n) i = 0; i < n; ++i)
     791      124586 :         _nodal_value_old(i) = dof_values_old[i];
     792       42537 :       _nodal_value_old_array[0] = _nodal_value_old;
     793             :     }
     794      242945 :     if (oldestSolutionStateRequested() >= 2)
     795             :     {
     796        3025 :       auto & dof_values_older = _vector_tags_dof_u[_older_solution_tag];
     797        9075 :       for (decltype(n) i = 0; i < n; ++i)
     798        6050 :         _nodal_value_older(i) = dof_values_older[i];
     799        3025 :       _nodal_value_older_array[0] = _nodal_value_older;
     800             :     }
     801      242945 :     if (_need_dof_values_dot)
     802           0 :       for (decltype(n) i = 0; i < n; ++i)
     803           0 :         _nodal_value_dot(i) = _dof_values_dot[i];
     804      242945 :     if (_need_dof_values_dotdot)
     805           0 :       for (decltype(n) i = 0; i < n; ++i)
     806           0 :         _nodal_value_dotdot(i) = _dof_values_dotdot[i];
     807      242945 :     if (_need_dof_values_dot_old)
     808           0 :       for (decltype(n) i = 0; i < n; ++i)
     809           0 :         _nodal_value_dot_old(i) = _dof_values_dot_old[i];
     810      242945 :     if (_need_dof_values_dotdot_old)
     811           0 :       for (decltype(n) i = 0; i < n; ++i)
     812           0 :         _nodal_value_dotdot_old(i) = _dof_values_dotdot_old[i];
     813             :   }
     814      467911 :   if (_previous_nl_solution_tag != Moose::INVALID_TAG_ID)
     815             :   {
     816           0 :     auto & dof_values_previous_nl = _vector_tags_dof_u[_previous_nl_solution_tag];
     817           0 :     for (decltype(n) i = 0; i < n; ++i)
     818           0 :       _nodal_value_previous_nl(i) = dof_values_previous_nl[i];
     819             :   }
     820      467911 : }
     821             : 
     822             : template class MooseVariableDataBase<Real>;
     823             : template class MooseVariableDataBase<RealVectorValue>;
     824             : template class MooseVariableDataBase<RealEigenVector>;

Generated by: LCOV version 1.14