LCOV - code coverage report
Current view: top level - src/userobjects - LMWeightedGapUserObject.C (source / functions) Hit Total Coverage
Test: idaholab/moose contact: #31730 (e8b711) with base e0c998 Lines: 38 46 82.6 %
Date: 2025-10-29 16:50:33 Functions: 9 9 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 "LMWeightedGapUserObject.h"
      11             : #include "MooseVariableFE.h"
      12             : #include "SystemBase.h"
      13             : 
      14             : registerMooseObject("ContactApp", LMWeightedGapUserObject);
      15             : 
      16             : InputParameters
      17        1752 : LMWeightedGapUserObject::newParams()
      18             : {
      19        1752 :   auto params = emptyInputParameters();
      20        3504 :   params.addRequiredCoupledVar(
      21             :       "lm_variable", "The Lagrange multiplier variable representing the contact pressure.");
      22        3504 :   params.addParam<bool>(
      23        3504 :       "use_petrov_galerkin", false, "Whether to use the Petrov-Galerkin approach.");
      24        3504 :   params.addCoupledVar("aux_lm",
      25             :                        "Auxiliary Lagrange multiplier variable that is utilized together with the "
      26             :                        "Petrov-Galerkin approach.");
      27        1752 :   return params;
      28           0 : }
      29             : 
      30             : InputParameters
      31         982 : LMWeightedGapUserObject::validParams()
      32             : {
      33         982 :   InputParameters params = WeightedGapUserObject::validParams();
      34         982 :   params.addClassDescription(
      35             :       "Provides the mortar normal Lagrange multiplier for constraint enforcement.");
      36         982 :   params += LMWeightedGapUserObject::newParams();
      37         982 :   return params;
      38           0 : }
      39             : 
      40         876 : LMWeightedGapUserObject::LMWeightedGapUserObject(const InputParameters & parameters)
      41             :   : WeightedGapUserObject(parameters),
      42         876 :     _lm_var(getVar("lm_variable", 0)),
      43        1752 :     _use_petrov_galerkin(getParam<bool>("use_petrov_galerkin")),
      44        1806 :     _aux_lm_var(isCoupled("aux_lm") ? getVar("aux_lm", 0) : nullptr)
      45             : {
      46         876 :   checkInput(_lm_var, "lm_variable");
      47         876 :   verifyLagrange(*_lm_var, "lm_variable");
      48             : 
      49         984 :   if (_use_petrov_galerkin && ((!isParamValid("aux_lm")) || _aux_lm_var == nullptr))
      50           0 :     paramError("use_petrov_galerkin",
      51             :                "We need to specify an auxiliary variable `aux_lm` while using the Petrov-Galerkin "
      52             :                "approach");
      53             : 
      54         876 :   if (_use_petrov_galerkin && _aux_lm_var->useDual())
      55           0 :     paramError("aux_lm",
      56             :                "Auxiliary LM variable needs to use standard shape function, i.e., set `use_dual = "
      57             :                "false`.");
      58         876 : }
      59             : 
      60             : void
      61        1356 : LMWeightedGapUserObject::checkInput(const MooseVariable * const var,
      62             :                                     const std::string & var_param_name) const
      63             : {
      64        1356 :   if (isCoupledConstant(var_param_name))
      65           0 :     paramError(var_param_name,
      66             :                "The Lagrange multiplier variable must be an actual variable and not a constant.");
      67        1356 :   else if (!var)
      68           0 :     paramError(var_param_name,
      69             :                "The Lagrange multiplier variables must be provided and be actual variables.");
      70        1356 : }
      71             : 
      72             : void
      73        1356 : LMWeightedGapUserObject::verifyLagrange(const MooseVariable & var,
      74             :                                         const std::string & var_param_name) const
      75             : {
      76        1356 :   if (var.feType().family != LAGRANGE)
      77           0 :     paramError(var_param_name, "The Lagrange multiplier variables must be of Lagrange type");
      78        1356 : }
      79             : 
      80             : const VariableTestValue &
      81         860 : LMWeightedGapUserObject::test() const
      82             : {
      83         860 :   return _use_petrov_galerkin ? _aux_lm_var->phiLower() : _lm_var->phiLower();
      84             : }
      85             : 
      86             : const ADVariableValue &
      87   190279072 : LMWeightedGapUserObject::contactPressure() const
      88             : {
      89   190279072 :   return _lm_var->adSlnLower();
      90             : }
      91             : 
      92             : Real
      93       14359 : LMWeightedGapUserObject::getNormalContactPressure(const Node * const node) const
      94             : {
      95       14359 :   const auto sys_num = _lm_var->sys().number();
      96       14359 :   const auto var_num = _lm_var->number();
      97       14359 :   if (!node->n_dofs(sys_num, var_num))
      98           0 :     mooseError("No degrees of freedom for the Lagrange multiplier at the node. If this is being "
      99             :                "called from an aux kernel make sure that your aux variable has the same order as "
     100             :                "your Lagrange multiplier");
     101             : 
     102       14359 :   const auto dof_number = node->dof_number(sys_num, var_num, /*component=*/0);
     103       14359 :   return (*_lm_var->sys().currentSolution())(dof_number);
     104             : }

Generated by: LCOV version 1.14