LCOV - code coverage report
Current view: top level - include/kernels - CahnHilliardBase.h (source / functions) Hit Total Coverage
Test: idaholab/moose phase_field: #31761 (b7bd6c) with base 2acb41 Lines: 49 52 94.2 %
Date: 2025-10-28 02:30:14 Functions: 9 10 90.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             : #pragma once
      11             : 
      12             : #include "CHBulk.h"
      13             : 
      14             : /**
      15             :  * CahnHilliardBase implements the residual of the Cahn-Hilliard
      16             :  * equation in a general way that can be templated to a scalar or
      17             :  * tensor mobility.
      18             :  */
      19             : template <typename T>
      20             : class CahnHilliardBase : public CHBulk<T>
      21             : {
      22             : public:
      23             :   CahnHilliardBase(const InputParameters & parameters);
      24             : 
      25             :   static InputParameters validParams();
      26             :   virtual void initialSetup();
      27             : 
      28             : protected:
      29             :   typedef typename CHBulk<T>::PFFunctionType PFFunctionType;
      30             :   virtual RealGradient computeGradDFDCons(PFFunctionType type);
      31             :   virtual Real computeQpOffDiagJacobian(unsigned int jvar);
      32             : 
      33             :   // Explicitly declare the use of the following members of the parent class
      34             :   // https://isocpp.org/wiki/faq/templates#nondependent-name-lookup-members
      35             :   using CHBulk<T>::_M;
      36             :   using CHBulk<T>::_i;
      37             :   using CHBulk<T>::_j;
      38             :   using CHBulk<T>::_qp;
      39             :   using CHBulk<T>::_var;
      40             :   using CHBulk<T>::_phi;
      41             :   using CHBulk<T>::_grad_u;
      42             :   using CHBulk<T>::_grad_phi;
      43             :   using CHBulk<T>::_grad_test;
      44             :   using CHBulk<T>::_coupled_moose_vars;
      45             :   using CHBulk<T>::_subproblem;
      46             :   using CHBulk<T>::_tid;
      47             : 
      48             : private:
      49             :   const unsigned int _nvar;
      50             :   std::vector<const MaterialProperty<Real> *> _second_derivatives;
      51             :   std::vector<const MaterialProperty<Real> *> _third_derivatives;
      52             :   std::vector<std::vector<const MaterialProperty<Real> *>> _third_cross_derivatives;
      53             :   std::vector<const VariableGradient *> _grad_vars;
      54             : };
      55             : 
      56             : template <typename T>
      57             : InputParameters
      58         260 : CahnHilliardBase<T>::validParams()
      59             : {
      60         260 :   InputParameters params = CHBulk<Real>::validParams();
      61         260 :   params.addClassDescription("Cahn-Hilliard Kernel that uses a DerivativeMaterial Free Energy");
      62         520 :   params.addRequiredParam<MaterialPropertyName>(
      63             :       "f_name", "Base name of the free energy function F defined in a DerivativeParsedMaterial");
      64         520 :   params.addCoupledVar("displacement_gradients",
      65             :                        "Vector of displacement gradient variables (see "
      66             :                        "Modules/PhaseField/DisplacementGradients "
      67             :                        "action)");
      68         260 :   return params;
      69           0 : }
      70             : 
      71             : template <typename T>
      72         138 : CahnHilliardBase<T>::CahnHilliardBase(const InputParameters & parameters)
      73             :   : CHBulk<T>(parameters),
      74         138 :     _nvar(_coupled_moose_vars.size()),
      75         138 :     _second_derivatives(_nvar + 1),
      76         138 :     _third_derivatives(_nvar + 1),
      77         138 :     _third_cross_derivatives(_nvar),
      78         276 :     _grad_vars(_nvar + 1)
      79             : {
      80             :   // derivatives w.r.t. and gradients of the kernel variable
      81         138 :   _second_derivatives[0] =
      82         276 :       &this->template getMaterialPropertyDerivative<Real>("f_name", _var.name(), _var.name());
      83         138 :   _third_derivatives[0] = &this->template getMaterialPropertyDerivative<Real>(
      84         138 :       "f_name", _var.name(), _var.name(), _var.name());
      85         138 :   _grad_vars[0] = &(_grad_u);
      86             : 
      87             :   // Iterate over all coupled variables
      88         177 :   for (unsigned int i = 0; i < _nvar; ++i)
      89             :   {
      90          39 :     const VariableName iname = _coupled_moose_vars[i]->name();
      91          39 :     if (iname == _var.name())
      92           0 :       this->paramError("coupled_variables",
      93             :                        "The kernel variable should not be specified in the coupled "
      94             :                        "`coupled_variables` parameter.");
      95          39 :     _second_derivatives[i + 1] =
      96          78 :         &this->template getMaterialPropertyDerivative<Real>("f_name", _var.name(), iname);
      97          39 :     _third_derivatives[i + 1] = &this->template getMaterialPropertyDerivative<Real>(
      98          39 :         "f_name", _var.name(), _var.name(), iname);
      99             : 
     100          39 :     _third_cross_derivatives[i].resize(_nvar);
     101         132 :     for (unsigned int j = 0; j < _nvar; ++j)
     102             :     {
     103          93 :       VariableName jname = _coupled_moose_vars[j]->name();
     104          93 :       _third_cross_derivatives[i][j] =
     105         186 :           &this->template getMaterialPropertyDerivative<Real>("f_name", _var.name(), iname, jname);
     106             :     }
     107             : 
     108          39 :     _grad_vars[i + 1] = &_subproblem.getStandardVariable(_tid, iname).gradSln();
     109             :   }
     110         138 : }
     111             : 
     112             : template <typename T>
     113             : void
     114         120 : CahnHilliardBase<T>::initialSetup()
     115             : {
     116             :   /**
     117             :    * Check if both the non-linear as well as the auxiliary variables variables
     118             :    * are coupled. Derivatives with respect to both types of variables contribute
     119             :    * the residual.
     120             :    */
     121         480 :   this->template validateCoupling<Real>("f_name", _var.name());
     122         120 :   this->template validateDerivativeMaterialPropertyBase<Real>("f_name");
     123         120 : }
     124             : 
     125             : template <typename T>
     126             : RealGradient
     127    97486424 : CahnHilliardBase<T>::computeGradDFDCons(PFFunctionType type)
     128             : {
     129             :   RealGradient res = 0.0;
     130             : 
     131    97486424 :   switch (type)
     132             :   {
     133             :     case CHBulk<T>::Residual:
     134   149901264 :       for (unsigned int i = 0; i <= _nvar; ++i)
     135    87538536 :         res += (*_grad_vars[i])[_qp] * (*_second_derivatives[i])[_qp];
     136             :       return res;
     137             : 
     138    35123696 :     case CHBulk<T>::Jacobian:
     139    35123696 :       res = _grad_phi[_j][_qp] * (*_second_derivatives[0])[_qp];
     140    72296928 :       for (unsigned int i = 0; i <= _nvar; ++i)
     141    37173232 :         res += _phi[_j][_qp] * (*_grad_vars[i])[_qp] * (*_third_derivatives[i])[_qp];
     142             :       return res;
     143             :   }
     144             : 
     145           0 :   mooseError("Internal error");
     146             : }
     147             : 
     148             : template <typename T>
     149             : Real
     150    22962176 : CahnHilliardBase<T>::computeQpOffDiagJacobian(unsigned int jvar)
     151             : {
     152             :   // get the coupled variable jvar is referring to
     153             :   const unsigned int cvar = this->mapJvarToCvar(jvar);
     154             : 
     155    22962176 :   RealGradient J = _grad_u[_qp] * _phi[_j][_qp] * (*_third_derivatives[cvar + 1])[_qp] +
     156    22962176 :                    _grad_phi[_j][_qp] * (*_second_derivatives[cvar + 1])[_qp];
     157             : 
     158    45924352 :   for (unsigned int i = 0; i < _nvar; ++i)
     159    22962176 :     J += _phi[_j][_qp] * (*_grad_vars[i + 1])[_qp] * (*_third_cross_derivatives[i][cvar])[_qp];
     160             : 
     161    22962176 :   return CHBulk<T>::computeQpOffDiagJacobian(jvar) + _M[_qp] * _grad_test[_i][_qp] * J;
     162             : }

Generated by: LCOV version 1.14