https://mooseframework.inl.gov
AbaqusUserElement.C
Go to the documentation of this file.
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 "AbaqusUserElement.h"
11 #include "SystemBase.h"
12 #include "UELThread.h"
13 
14 #define QUOTE(macro) stringifyName(macro)
15 
16 registerMooseObject("SolidMechanicsApp", AbaqusUserElement);
17 
20 {
21  auto params = GeneralUserObject::validParams();
24  params.addClassDescription("Coupling UserObject to use Abaqus UEL plugins in MOOSE");
25 
26  // execute during residual and Jacobian evaluation
27  ExecFlagEnum & exec_enum = params.set<ExecFlagEnum>("execute_on", true);
29  exec_enum = {EXEC_PRE_KERNELS, EXEC_TIMESTEP_END};
30  params.suppressParameter<ExecFlagEnum>("execute_on");
31 
32  // Avoid uninitialized residual objects
33  params.suppressParameter<bool>("force_preic");
34 
35  // coupled variables
36  params.addParam<std::vector<NonlinearVariableName>>("variables", "Nonlinear coupled variables");
37  // auxiliary variables (including temperature)
38  params.addParam<std::vector<AuxVariableName>>(
39  "external_fields",
40  {},
41  "Auxiliary field variables (or 'predifined field variables') passed to the UEL plugin. Some "
42  "plugins may assume that the first field is temperature when there are multiple external "
43  "fields.");
44 
45  // UEL plugin file
46  params.addRequiredParam<FileName>("plugin", "UEL plugin file");
47 
48  params.addRequiredParam<std::vector<Real>>(
49  "constant_properties", "Constant mechanical and thermal material properties (PROPS)");
50  params.addRequiredParam<unsigned int>("num_state_vars",
51  "The number of state variables this UMAT is going to use");
52 
53  params.addParam<int>("jtype", 0, "Abaqus element type integer");
54 
55  return params;
56 }
57 
59  : GeneralUserObject(params),
60  BlockRestrictable(this),
61  TaggingInterface(this),
62  _plugin(getParam<FileName>("plugin")),
63  _library(_plugin + std::string("-") + QUOTE(METHOD) + ".plugin"),
64  _uel(_library.getFunction<uel_t>("uel_")),
65  _moose_mesh(UserObject::_subproblem.mesh()),
66  _mesh(_moose_mesh.getMesh()),
67  _dim(_moose_mesh.dimension()),
68  _variable_names(getParam<std::vector<NonlinearVariableName>>("variables")),
69  _aux_variable_names(getParam<std::vector<AuxVariableName>>("external_fields")),
70  _sub_ids(blockRestricted() ? blockIDs() : _moose_mesh.meshSubdomains()),
71  _props(getParam<std::vector<Real>>("constant_properties")),
72  _nprops(_props.size()),
73  _nstatev(getParam<unsigned int>("num_state_vars")),
74  _statev_index_current(0),
75  _statev_index_old(1),
76  _jtype(getParam<int>("jtype"))
77 {
78  // coupled variables must be nonlinear scalar fields
79  for (const auto & variable_name : _variable_names)
80  {
81  const auto * var = &UserObject::_subproblem.getVariable(
82  0, variable_name, Moose::VarKindType::VAR_SOLVER, Moose::VarFieldType::VAR_FIELD_STANDARD);
83  _variables.push_back(var);
84 
85  // check block restriction
86  if (!var->hasBlocks(blockIDs()))
87  paramError("variables", "must be defined on all blocks the UEL is operating on.");
88  }
89 
90  for (const auto & aux_variable_name : _aux_variable_names)
91  {
92  MooseVariableFEBase * aux_var =
94  aux_variable_name,
95  Moose::VarKindType::VAR_AUXILIARY,
96  Moose::VarFieldType::VAR_FIELD_STANDARD);
97  _aux_variables.push_back(aux_var);
98  aux_var->sys().addVariableToZeroOnResidual(aux_variable_name);
99 
100  // check block restriction
101  if (!aux_var->hasBlocks(blockIDs()))
102  paramError("aux_variables", "must be defined on all blocks the UEL is operating on.");
103  }
104 }
105 
106 void
108 {
109  setupElemRange();
110 }
111 
112 void
114 {
115  setupElemRange();
116 }
117 
118 void
120 {
121 }
122 
123 void
125 {
126  // swap the current and old state data at the end of a converged timestep
128  {
130  return;
131  }
132 
133  PARALLEL_TRY
134  {
135  UELThread ut(_fe_problem, *this);
136  Threads::parallel_reduce(*_elem_range, ut);
137  }
138  PARALLEL_CATCH;
139 }
140 
141 void
143 {
144  _elem_range =
145  std::make_unique<ConstElemRange>(_mesh.active_local_subdomain_set_elements_begin(_sub_ids),
146  _mesh.active_local_subdomain_set_elements_end(_sub_ids));
147 
148  // prepopulate the statev map outside of a threaded region
149  if (_nstatev > 0)
150  for (const auto & elem : *_elem_range)
151  {
152  _statev[0][elem->id()].resize(_nstatev);
153  _statev[1][elem->id()].resize(_nstatev);
154  }
155 }
std::array< std::map< dof_id_type, std::vector< Real > >, 2 > _statev
T & getMesh(MooseMesh &mesh)
function to cast mesh
Definition: SCM.h:35
static InputParameters validParams()
std::vector< NonlinearVariableName > _variable_names
coupled variables to provide the DOF values
const ExecFlagType & getCurrentExecuteOnFlag() const
virtual void initialSetup() override
int _nstatev
stateful data
virtual void execute() override
const libMesh::MeshBase & _mesh
The libMesh mesh that this object acts on.
MeshBase & mesh
void addAvailableFlags(const ExecFlagType &flag, Args... flags)
const ExecFlagType EXEC_TIMESTEP_END
virtual const std::set< SubdomainID > & blockIDs() const
virtual void initialize() override final
static InputParameters validParams()
SubProblem & _subproblem
virtual void meshChanged() override
std::size_t _statev_index_current
std::unique_ptr< ConstElemRange > _elem_range
All the active and elements local to this process that exist on this object&#39;s subdomains.
std::vector< AuxVariableName > _aux_variable_names
Auxiliary variable names.
const std::set< SubdomainID > _sub_ids
The subdomain ids this object operates on.
void paramError(const std::string &param, Args... args) const
AbaqusUserElement(const InputParameters &params)
virtual const MooseVariableFieldBase & getVariable(const THREAD_ID tid, const std::string &var_name, Moose::VarKindType expected_var_type=Moose::VarKindType::VAR_ANY, Moose::VarFieldType expected_var_field_type=Moose::VarFieldType::VAR_FIELD_ANY) const=0
This user-object is a testbed for implementing a custom element.
DIE A HORRIBLE DEATH HERE typedef LIBMESH_DEFAULT_SCALAR_TYPE Real
registerMooseObject("SolidMechanicsApp", AbaqusUserElement)
virtual void addVariableToZeroOnResidual(std::string var_name)
FEProblemBase & _fe_problem
void setupElemRange()
setup the range of elements this object operates on
static InputParameters validParams()
const ExecFlagType EXEC_PRE_KERNELS
std::size_t _statev_index_old
bool hasBlocks(const SubdomainName &name) const
static InputParameters validParams()
SystemBase & sys()
void ErrorVector unsigned int
std::vector< const MooseVariableFieldBase * > _variables
pointers to the variable objects
std::vector< const MooseVariableFieldBase * > _aux_variables
pointers to the auxiliary variable objects