LCOV - code coverage report
Current view: top level - src/splits - ContactSplit.C (source / functions) Hit Total Coverage
Test: idaholab/moose contact: 8601ad Lines: 45 52 86.5 %
Date: 2025-07-18 13:27:36 Functions: 3 3 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 "ContactSplit.h"
      11             : #include "InputParameters.h"
      12             : #include "FEProblem.h"
      13             : #include "Conversion.h"
      14             : 
      15             : registerMooseObject("ContactApp", ContactSplit);
      16             : 
      17             : InputParameters
      18          72 : ContactSplit::validParams()
      19             : {
      20          72 :   InputParameters params = Split::validParams();
      21         144 :   params.addParam<std::vector<BoundaryName>>("contact_primary",
      22             :                                              "Primary surface list for included contacts");
      23         144 :   params.addParam<std::vector<BoundaryName>>("contact_secondary",
      24             :                                              "Secondary surface list for included contacts");
      25         144 :   params.addParam<std::vector<int>>(
      26             :       "contact_displaced",
      27             :       {},
      28             :       "List of indicators whether displaced mesh is used to define included contact");
      29         144 :   params.addParam<std::vector<BoundaryName>>("uncontact_primary",
      30             :                                              "Primary surface list for excluded contacts");
      31         144 :   params.addParam<std::vector<BoundaryName>>("uncontact_secondary",
      32             :                                              "Secondary surface list for excluded contacts");
      33         144 :   params.addParam<std::vector<int>>(
      34             :       "uncontact_displaced",
      35             :       {},
      36             :       "List of indicators whether displaced mesh is used to define excluded contact");
      37         144 :   params.addRequiredParam<bool>("include_all_contact_nodes",
      38             :                                 "Whether to include all nodes on the contact surfaces");
      39          72 :   params.addClassDescription("Split-based preconditioner that partitions the domain into DOFs "
      40             :                              "directly involved in contact (on contact surfaces) and those "
      41             :                              "that are not");
      42          72 :   return params;
      43           0 : }
      44             : 
      45          36 : ContactSplit::ContactSplit(const InputParameters & params)
      46             :   : Split(params),
      47          72 :     _contact_pairs(getParam<BoundaryName, BoundaryName>("contact_primary", "contact_secondary")),
      48          72 :     _contact_displaced(getParam<std::vector<int>>("contact_displaced")),
      49          72 :     _uncontact_pairs(
      50             :         getParam<BoundaryName, BoundaryName>("uncontact_primary", "uncontact_secondary")),
      51          72 :     _uncontact_displaced(getParam<std::vector<int>>("uncontact_displaced")),
      52         108 :     _include_all_contact_nodes(getParam<bool>("include_all_contact_nodes"))
      53             : {
      54          36 :   if (!_contact_displaced.empty() && _contact_pairs.size() != _contact_displaced.size())
      55           0 :     mooseError("Primary and displaced contact lists must have matching sizes: ",
      56           0 :                _contact_pairs.size(),
      57             :                " != ",
      58           0 :                _contact_displaced.size());
      59             : 
      60          36 :   if (_contact_displaced.empty())
      61          18 :     _contact_displaced.resize(_contact_pairs.size());
      62             : 
      63          36 :   if (!_uncontact_displaced.empty() && _uncontact_pairs.size() != _uncontact_displaced.size())
      64           0 :     mooseError("Primary and displaced uncontact lists must have matching sizes: ",
      65           0 :                _uncontact_pairs.size(),
      66             :                " != ",
      67           0 :                _uncontact_displaced.size());
      68             : 
      69          36 :   if (!_uncontact_displaced.size())
      70          18 :     _uncontact_displaced.resize(_uncontact_pairs.size());
      71          36 : }
      72             : 
      73             : void
      74          36 : ContactSplit::setup(NonlinearSystemBase & nl, const std::string & prefix)
      75             : {
      76             :   // A reference to the PetscOptions
      77          36 :   Moose::PetscSupport::PetscOptions & po = _fe_problem.getPetscOptions();
      78             :   // prefix
      79          36 :   const std::string dmprefix = prefix + "dm_moose_";
      80             : 
      81             :   // contacts options
      82          36 :   if (!_contact_pairs.empty())
      83             :   {
      84             :     // append PETSc options
      85          36 :     po.pairs.emplace_back(dmprefix + "ncontacts", Moose::stringify(_contact_pairs.size()));
      86             : 
      87          36 :     for (std::size_t j = 0; j < _contact_pairs.size(); ++j)
      88             :     {
      89          36 :       auto opt = dmprefix + "contact_" + Moose::stringify(j);
      90          36 :       po.pairs.emplace_back(opt, Moose::stringify(_contact_pairs[j], ","));
      91             : 
      92          18 :       if (_contact_displaced[j])
      93          36 :         po.pairs.emplace_back(opt + "_displaced", "yes");
      94             :     }
      95             :   }
      96             : 
      97             :   // uncontacts options
      98          36 :   if (!_uncontact_pairs.empty())
      99             :   {
     100          36 :     po.pairs.emplace_back(dmprefix + "nuncontacts", Moose::stringify(_uncontact_pairs.size()));
     101             : 
     102          36 :     for (std::size_t j = 0; j < _uncontact_pairs.size(); ++j)
     103             :     {
     104          36 :       auto opt = dmprefix + "uncontact_" + Moose::stringify(j);
     105          36 :       po.pairs.emplace_back(opt, Moose::stringify(_uncontact_pairs[j], ","));
     106             : 
     107          18 :       if (_uncontact_displaced[j])
     108          36 :         po.pairs.emplace_back(opt + "_displaced", "yes");
     109             :     }
     110             :   }
     111             : 
     112             :   // Whether to include all nodes on the contact surfaces
     113             :   // into the contact subsolver
     114          36 :   po.pairs.emplace_back(dmprefix + "includeAllContactNodes",
     115          36 :                         _include_all_contact_nodes ? "yes" : "no");
     116          36 :   Split::setup(nl, prefix);
     117          36 : }

Generated by: LCOV version 1.14