LCOV - code coverage report
Current view: top level - src/kernels - KernelScalarBase.C (source / functions) Hit Total Coverage
Test: idaholab/moose framework: 2bf808 Lines: 90 131 68.7 %
Date: 2025-07-17 01:28:37 Functions: 9 11 81.8 %
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 "KernelScalarBase.h"
      11             : 
      12             : #include "Assembly.h"
      13             : #include "SubProblem.h"
      14             : #include "SystemBase.h"
      15             : #include "MooseVariableFE.h"
      16             : #include "MooseVariableScalar.h"
      17             : 
      18             : #include "libmesh/quadrature.h"
      19             : 
      20             : InputParameters
      21       28615 : KernelScalarBase::validParams()
      22             : {
      23       28615 :   InputParameters params = Kernel::validParams();
      24             :   // This parameter can get renamed in derived class to a more relevant variable name
      25       28615 :   params.addCoupledVar("scalar_variable", "Primary coupled scalar variable");
      26       28615 :   params.addParam<bool>("compute_scalar_residuals", true, "Whether to compute scalar residuals");
      27       85845 :   params.addParam<bool>(
      28       57230 :       "compute_field_residuals", true, "Whether to compute residuals for the field variable.");
      29       28615 :   return params;
      30           0 : }
      31             : 
      32          45 : KernelScalarBase::KernelScalarBase(const InputParameters & parameters)
      33             :   : Kernel(parameters),
      34          45 :     _use_scalar(isParamValid("scalar_variable") ? true : false),
      35          45 :     _compute_scalar_residuals(!_use_scalar ? false : getParam<bool>("compute_scalar_residuals")),
      36          45 :     _compute_field_residuals(getParam<bool>("compute_field_residuals")),
      37          45 :     _kappa_var_ptr(_use_scalar ? getScalarVar("scalar_variable", 0) : nullptr),
      38          45 :     _kappa_var(_use_scalar ? _kappa_var_ptr->number() : 0),
      39          45 :     _k_order(_use_scalar ? _kappa_var_ptr->order() : 0),
      40          90 :     _kappa(_use_scalar ? (_is_implicit ? _kappa_var_ptr->sln() : _kappa_var_ptr->slnOld()) : _zero)
      41             : {
      42          45 : }
      43             : 
      44             : void
      45         195 : KernelScalarBase::computeResidual()
      46             : {
      47         195 :   if (_compute_field_residuals)
      48         195 :     Kernel::computeResidual(); // compute and assemble regular variable contributions
      49             : 
      50         195 :   if (_compute_scalar_residuals)
      51         131 :     computeScalarResidual();
      52         192 : }
      53             : 
      54             : void
      55         131 : KernelScalarBase::computeScalarResidual()
      56             : {
      57         131 :   std::vector<Real> scalar_residuals(_k_order);
      58             : 
      59        1283 :   for (_qp = 0; _qp < _qrule->n_points(); _qp++)
      60             :   {
      61        1155 :     initScalarQpResidual();
      62        2307 :     for (_h = 0; _h < _k_order; _h++)
      63        1155 :       scalar_residuals[_h] += _JxW[_qp] * _coord[_qp] * computeScalarQpResidual();
      64             :   }
      65             : 
      66         128 :   addResiduals(
      67         128 :       _assembly, scalar_residuals, _kappa_var_ptr->dofIndices(), _kappa_var_ptr->scalingFactor());
      68         128 : }
      69             : 
      70             : void
      71           0 : KernelScalarBase::computeJacobian()
      72             : {
      73           0 :   if (_compute_field_residuals)
      74           0 :     Kernel::computeJacobian();
      75             : 
      76           0 :   if (_compute_scalar_residuals)
      77           0 :     computeScalarJacobian();
      78           0 : }
      79             : 
      80             : void
      81          64 : KernelScalarBase::computeScalarJacobian()
      82             : {
      83          64 :   _local_ke.resize(_k_order, _k_order);
      84             : 
      85         640 :   for (_qp = 0; _qp < _qrule->n_points(); _qp++)
      86             :   {
      87         576 :     initScalarQpJacobian(_kappa_var);
      88        1152 :     for (_h = 0; _h < _k_order; _h++)
      89        1152 :       for (_l = 0; _l < _k_order; _l++)
      90         576 :         _local_ke(_h, _l) += _JxW[_qp] * _coord[_qp] * computeScalarQpJacobian();
      91             :   }
      92             : 
      93         256 :   addJacobian(_assembly,
      94          64 :               _local_ke,
      95          64 :               _kappa_var_ptr->dofIndices(),
      96          64 :               _kappa_var_ptr->dofIndices(),
      97          64 :               _kappa_var_ptr->scalingFactor());
      98          64 : }
      99             : 
     100             : void
     101          96 : KernelScalarBase::computeOffDiagJacobian(const unsigned int jvar_num)
     102             : {
     103          96 :   if (_use_scalar)
     104             :   {
     105          64 :     if (jvar_num == variable().number()) // column for this kernel's variable
     106             :     {
     107          64 :       if (_compute_field_residuals)
     108          64 :         Kernel::computeJacobian(); // d-_var-residual / d-_var
     109          64 :       if (_compute_scalar_residuals)
     110          64 :         computeScalarOffDiagJacobian(jvar_num); // d-_kappa-residual / d-_var
     111             :     }
     112           0 :     else if (jvar_num == _kappa_var) // column for this kernel's scalar variable
     113             :       // handle these in computeOffDiagJacobianScalar
     114           0 :       return;
     115             :     else // some other column for regular variable
     116             :     {
     117           0 :       if (_compute_field_residuals)
     118           0 :         Kernel::computeOffDiagJacobian(jvar_num); // d-_var-residual / d-jvar
     119           0 :       if (_compute_scalar_residuals)
     120           0 :         computeScalarOffDiagJacobian(jvar_num); // d-_kappa-residual / d-jvar
     121             :     }
     122             :   }
     123             :   else
     124             :   {
     125          32 :     if (jvar_num == variable().number()) // column for this kernel's variable
     126             :     {
     127          32 :       if (_compute_field_residuals)
     128          32 :         Kernel::computeJacobian(); // d-_var-residual / d-_var
     129             :     }
     130             :     else // some other column for regular variable
     131             :     {
     132           0 :       if (_compute_field_residuals)
     133           0 :         Kernel::computeOffDiagJacobian(jvar_num); // d-_var-residual / d-jvar
     134             :     }
     135             :   }
     136             : }
     137             : 
     138             : void
     139          64 : KernelScalarBase::computeScalarOffDiagJacobian(const unsigned int jvar_num)
     140             : {
     141          64 :   const auto & jvar = getVariable(jvar_num);
     142          64 :   if (jvar.fieldType() == Moose::VarFieldType::VAR_FIELD_STANDARD)
     143             :   {
     144             :     // Get dofs and order of this variable; at least one will be _var
     145             :     // const auto & jv0 = static_cast<const MooseVariable &>(jvar);
     146             :     // const auto & loc_phi = jv0.phi();
     147          64 :     const auto jvar_size = jvar.phiSize();
     148          64 :     _local_ke.resize(_k_order, jvar_size);
     149             : 
     150         640 :     for (_qp = 0; _qp < _qrule->n_points(); _qp++)
     151             :     {
     152         576 :       initScalarQpOffDiagJacobian(jvar);
     153        1152 :       for (_h = 0; _h < _k_order; _h++)
     154        5760 :         for (_j = 0; _j < jvar_size; _j++)
     155        5184 :           _local_ke(_h, _j) += _JxW[_qp] * _coord[_qp] * computeScalarQpOffDiagJacobian(jvar_num);
     156             :     }
     157             :   }
     158           0 :   else if (jvar.fieldType() == Moose::VarFieldType::VAR_FIELD_ARRAY)
     159           0 :     mooseError("Array variable cannot be coupled into Kernel Scalar currently");
     160             :   else
     161           0 :     mooseError("Vector variable cannot be coupled into Kernel Scalar currently");
     162             : 
     163         256 :   addJacobian(_assembly,
     164          64 :               _local_ke,
     165          64 :               _kappa_var_ptr->dofIndices(),
     166          64 :               jvar.dofIndices(),
     167          64 :               _kappa_var_ptr->scalingFactor());
     168          64 : }
     169             : 
     170             : void
     171          64 : KernelScalarBase::computeOffDiagJacobianScalarLocal(const unsigned int svar_num)
     172             : {
     173             :   // Get dofs and order of this scalar; at least one will be _kappa_var
     174          64 :   const auto & svar = _sys.getScalarVariable(_tid, svar_num);
     175          64 :   const unsigned int s_order = svar.order();
     176          64 :   _local_ke.resize(_test.size(), s_order);
     177             : 
     178         640 :   for (_qp = 0; _qp < _qrule->n_points(); _qp++)
     179             :   {
     180         576 :     initScalarQpJacobian(svar_num);
     181        5760 :     for (_i = 0; _i < _test.size(); _i++)
     182       10368 :       for (_l = 0; _l < s_order; _l++)
     183        5184 :         _local_ke(_i, _l) += _JxW[_qp] * _coord[_qp] * computeQpOffDiagJacobianScalar(svar_num);
     184             :   }
     185             : 
     186          64 :   addJacobian(_assembly, _local_ke, _var.dofIndices(), svar.dofIndices(), _var.scalingFactor());
     187          64 : }
     188             : 
     189             : void
     190          64 : KernelScalarBase::computeOffDiagJacobianScalar(const unsigned int svar_num)
     191             : {
     192          64 :   precalculateOffDiagJacobianScalar(svar_num);
     193          64 :   if (_use_scalar)
     194             :   {
     195          64 :     if (svar_num == variable().number()) // column for this kernel's variable
     196             :       // this kernel's variable is not a scalar
     197           0 :       return;
     198          64 :     else if (svar_num == _kappa_var) // column for this kernel's scalar variable
     199             :     {
     200             :       // Perform assembly using method in Kernel; works for simple cases but not general
     201             :       // Kernel::computeOffDiagJacobianScalar(svar_num); // d-_var-residual / d-_kappa
     202             :       // Perform assembly using local_ke like d-_kappa_var-residual / d-_var
     203          64 :       if (_compute_field_residuals)
     204          64 :         computeOffDiagJacobianScalarLocal(svar_num); // d-_var-residual / d-_kappa
     205          64 :       if (_compute_scalar_residuals)
     206          64 :         computeScalarJacobian(); // d-_kappa-residual / d-_kappa
     207             :     }
     208             :     else // some other column for scalar variable
     209             :     {
     210             :       // Perform assembly using method in Kernel; works for simple cases but not general
     211             :       // Kernel::computeOffDiagJacobianScalar(svar_num); // d-_var-residual / d-jvar
     212             :       // Perform assembly using local_ke like d-_kappa_var-residual / d-_var
     213           0 :       if (_compute_field_residuals)
     214           0 :         computeOffDiagJacobianScalarLocal(svar_num); // d-_var-residual / d-svar
     215           0 :       if (_compute_scalar_residuals)
     216           0 :         computeScalarOffDiagJacobianScalar(svar_num); // d-_kappa-residual / d-svar
     217             :     }
     218             :   }
     219           0 :   else if (_compute_field_residuals)
     220           0 :     Kernel::computeOffDiagJacobianScalar(svar_num); // d-_var-residual / d-svar
     221             : }
     222             : 
     223             : void
     224           0 : KernelScalarBase::computeScalarOffDiagJacobianScalar(const unsigned int svar_num)
     225             : {
     226             :   // Get dofs and order of this scalar; at least one will be _kappa_var
     227           0 :   const auto & svar = _sys.getScalarVariable(_tid, svar_num);
     228           0 :   const unsigned int s_order = svar.order();
     229           0 :   _local_ke.resize(_k_order, s_order);
     230             : 
     231           0 :   for (_qp = 0; _qp < _qrule->n_points(); _qp++)
     232             :   {
     233           0 :     initScalarQpJacobian(svar_num);
     234           0 :     for (_h = 0; _h < _k_order; _h++)
     235           0 :       for (_l = 0; _l < s_order; _l++)
     236           0 :         _local_ke(_h, _l) +=
     237           0 :             _JxW[_qp] * _coord[_qp] * computeScalarQpOffDiagJacobianScalar(svar_num);
     238             :   }
     239             : 
     240           0 :   addJacobian(_assembly,
     241           0 :               _local_ke,
     242           0 :               _kappa_var_ptr->dofIndices(),
     243           0 :               svar.dofIndices(),
     244           0 :               _kappa_var_ptr->scalingFactor());
     245           0 : }

Generated by: LCOV version 1.14