LCOV - code coverage report
Current view: top level - src/kernels - CoupledSwitchingTimeDerivative.C (source / functions) Hit Total Coverage
Test: idaholab/moose phase_field: #31761 (b7bd6c) with base 2acb41 Lines: 67 69 97.1 %
Date: 2025-10-28 02:30:14 Functions: 12 12 100.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 "CoupledSwitchingTimeDerivative.h"
      11             : 
      12             : registerMooseObject("PhaseFieldApp", CoupledSwitchingTimeDerivative);
      13             : registerMooseObject("PhaseFieldApp", ADCoupledSwitchingTimeDerivative);
      14             : 
      15             : template <bool is_ad>
      16             : InputParameters
      17         543 : CoupledSwitchingTimeDerivativeTempl<is_ad>::validParams()
      18             : {
      19         543 :   InputParameters params = CoupledSwitchingTimeDerivativeBase<is_ad>::validParams();
      20         543 :   params.addClassDescription(
      21             :       "Coupled time derivative Kernel that multiplies the time derivative by "
      22             :       "$\\frac{dh_\\alpha}{d\\eta_i} F_\\alpha + \\frac{dh_\\beta}{d\\eta_i} F_\\beta + \\dots$");
      23        1086 :   params.addRequiredParam<std::vector<MaterialPropertyName>>(
      24             :       "Fj_names", "List of functions for each phase. Place in same order as hj_names!");
      25        1086 :   params.addRequiredParam<std::vector<MaterialPropertyName>>(
      26             :       "hj_names", "Switching Function Materials that provide h. Place in same order as Fj_names!");
      27        1086 :   params.addCoupledVar("coupled_variables", "Vector of variable arguments of Fj and hj");
      28         543 :   return params;
      29           0 : }
      30             : template <bool is_ad>
      31         285 : CoupledSwitchingTimeDerivativeTempl<is_ad>::CoupledSwitchingTimeDerivativeTempl(
      32             :     const InputParameters & parameters)
      33             :   : DerivativeMaterialInterface<JvarMapKernelInterface<CoupledSwitchingTimeDerivativeBase<is_ad>>>(
      34             :         parameters),
      35         285 :     _v_name(this->coupledName("v", 0)),
      36         855 :     _Fj_names(this->template getParam<std::vector<MaterialPropertyName>>("Fj_names")),
      37         285 :     _num_j(_Fj_names.size()),
      38         285 :     _prop_Fj(_num_j),
      39         570 :     _hj_names(this->template getParam<std::vector<MaterialPropertyName>>("hj_names")),
      40         570 :     _prop_dhjdetai(_num_j)
      41             : {
      42             :   // check passed in parameter vectors
      43         285 :   if (_num_j != _hj_names.size())
      44           0 :     this->paramError("hj_names", "Need to pass in as many hj_names as Fj_names");
      45             : 
      46             :   // reserve space and set phase material properties
      47         909 :   for (unsigned int n = 0; n < _num_j; ++n)
      48             :   {
      49             :     // get phase free energy
      50         624 :     _prop_Fj[n] = &this->template getGenericMaterialProperty<Real, is_ad>(_Fj_names[n]);
      51             : 
      52             :     // get switching function derivatives wrt eta_i, the nonlinear variable
      53         624 :     _prop_dhjdetai[n] =
      54        1248 :         &this->template getMaterialPropertyDerivative<Real, is_ad>(_hj_names[n], _v_name);
      55             :   }
      56         285 : }
      57             : 
      58         207 : CoupledSwitchingTimeDerivative::CoupledSwitchingTimeDerivative(const InputParameters & parameters)
      59             :   : CoupledSwitchingTimeDerivativeTempl<false>(parameters),
      60         414 :     _prop_dFjdv(_num_j),
      61         207 :     _prop_dFjdarg(_num_j),
      62         207 :     _prop_d2hjdetai2(_num_j),
      63         414 :     _prop_d2hjdetaidarg(_num_j)
      64             : {
      65             :   // reserve space and set phase material properties
      66         648 :   for (unsigned int n = 0; n < _num_j; ++n)
      67             :   {
      68             :     // get phase free energy and derivatives
      69         441 :     _prop_dFjdv[n] = &getMaterialPropertyDerivative<Real>(_Fj_names[n], _var.name());
      70         441 :     _prop_dFjdarg[n].resize(_n_args);
      71             : 
      72             :     // get switching function and derivatives wrt eta_i, the nonlinear variable
      73         441 :     _prop_d2hjdetai2[n] = &getMaterialPropertyDerivative<Real>(_hj_names[n], _v_name, _v_name);
      74         441 :     _prop_d2hjdetaidarg[n].resize(_n_args);
      75             : 
      76        2397 :     for (unsigned int i = 0; i < _n_args; ++i)
      77             :     {
      78             :       // Get derivatives of all Fj wrt all coupled variables
      79        1956 :       _prop_dFjdarg[n][i] = &getMaterialPropertyDerivative<Real>(_Fj_names[n], i);
      80             : 
      81             :       // Get second derivatives of all hj wrt eta_i and all coupled variables
      82        1956 :       _prop_d2hjdetaidarg[n][i] = &getMaterialPropertyDerivative<Real>(_hj_names[n], _v_name, i);
      83             :     }
      84             :   }
      85         207 : }
      86             : 
      87             : template <bool is_ad>
      88             : void
      89         231 : CoupledSwitchingTimeDerivativeTempl<is_ad>::initialSetup()
      90             : {
      91         693 :   for (unsigned int n = 0; n < _num_j; ++n)
      92        1386 :     this->template validateNonlinearCoupling<GenericReal<is_ad>>(_hj_names[n]);
      93         231 : }
      94             : 
      95             : void
      96         180 : CoupledSwitchingTimeDerivative::initialSetup()
      97             : {
      98         180 :   CoupledSwitchingTimeDerivativeTempl<false>::initialSetup();
      99         540 :   for (unsigned int n = 0; n < _num_j; ++n)
     100        1080 :     validateNonlinearCoupling<Real>(_Fj_names[n]);
     101         180 : }
     102             : 
     103             : Real
     104     8392800 : CoupledSwitchingTimeDerivative::computeQpResidual()
     105             : {
     106             :   Real sum = 0.0;
     107    25178400 :   for (unsigned int n = 0; n < _num_j; ++n)
     108    16785600 :     sum += (*_prop_dhjdetai[n])[_qp] * (*_prop_Fj[n])[_qp];
     109             : 
     110     8392800 :   return CoupledTimeDerivative::computeQpResidual() * sum;
     111             : }
     112             : 
     113             : ADReal
     114      503220 : ADCoupledSwitchingTimeDerivative::precomputeQpResidual()
     115             : {
     116      503220 :   ADReal sum = 0.0;
     117     1509660 :   for (unsigned int n = 0; n < _num_j; ++n)
     118     2012880 :     sum += (*_prop_dhjdetai[n])[_qp] * (*_prop_Fj[n])[_qp];
     119             : 
     120     1006440 :   return _v_dot[_qp] * sum;
     121             : }
     122             : 
     123             : Real
     124     7337600 : CoupledSwitchingTimeDerivative::computeQpJacobian()
     125             : {
     126             :   Real sum = 0.0;
     127    22012800 :   for (unsigned int n = 0; n < _num_j; ++n)
     128    14675200 :     sum += (*_prop_dhjdetai[n])[_qp] * (*_prop_dFjdv[n])[_qp];
     129             : 
     130     7337600 :   return CoupledTimeDerivative::computeQpResidual() * sum * _phi[_j][_qp];
     131             : }
     132             : 
     133             : Real
     134    19206400 : CoupledSwitchingTimeDerivative::computeQpOffDiagJacobian(unsigned int jvar)
     135             : {
     136             :   // get the coupled variable jvar is referring to
     137             :   const unsigned int cvar = mapJvarToCvar(jvar);
     138             : 
     139    19206400 :   if (jvar == _v_var)
     140             :   {
     141             :     Real sum = 0.0;
     142             : 
     143    21091200 :     for (unsigned int n = 0; n < _num_j; ++n)
     144    14060800 :       sum +=
     145    14060800 :           ((*_prop_d2hjdetai2[n])[_qp] * _v_dot[_qp] + (*_prop_dhjdetai[n])[_qp] * _dv_dot[_qp]) *
     146    14060800 :           (*_prop_Fj[n])[_qp];
     147             : 
     148     7030400 :     return _phi[_j][_qp] * sum * _test[_i][_qp];
     149             :   }
     150             : 
     151             :   Real sum = 0.0;
     152    36528000 :   for (unsigned int n = 0; n < _num_j; ++n)
     153    24352000 :     sum += (*_prop_d2hjdetaidarg[n][cvar])[_qp] * (*_prop_Fj[n])[_qp] +
     154    24352000 :            (*_prop_dhjdetai[n])[_qp] * (*_prop_dFjdarg[n][cvar])[_qp];
     155             : 
     156    12176000 :   return CoupledTimeDerivative::computeQpResidual() * sum * _phi[_j][_qp];
     157             : }
     158             : 
     159             : template class CoupledSwitchingTimeDerivativeTempl<false>;
     160             : template class CoupledSwitchingTimeDerivativeTempl<true>;

Generated by: LCOV version 1.14