MFEM v4.9.0
Finite element discretization library
Loading...
Searching...
No Matches
mtop_solvers.hpp
Go to the documentation of this file.
1// Copyright (c) 2010-2025, Lawrence Livermore National Security, LLC. Produced
2// at the Lawrence Livermore National Laboratory. All Rights reserved. See files
3// LICENSE and NOTICE for details. LLNL-CODE-806117.
4//
5// This file is part of the MFEM library. For more information and source code
6// availability visit https://mfem.org.
7//
8// MFEM is free software; you can redistribute it and/or modify it under the
9// terms of the BSD-3 license. We welcome feedback and contributions, see file
10// CONTRIBUTING.md for details.
11#pragma once
12
13#include <memory>
14
15#include "mfem.hpp"
16
18
19///////////////////////////////////////////////////////////////////////////////
20/// \brief The IsoElasticyLambdaCoeff class converts E modulus of elasticity
21/// and Poisson's ratio to Lame's lambda coefficient
23{
24 mfem::Coefficient *E, *nu;
25
26public:
27 /// Constructor - takes as inputs E modulus and Poisson's ratio
31
32 /// Evaluates the Lame's lambda coefficient
34 const mfem::IntegrationPoint &ip) override
35 {
36 const real_t EE = E->Eval(T, ip);
37 const real_t nn = nu->Eval(T, ip);
38 constexpr auto Lambda = [](const real_t E, const real_t nu)
39 {
40 return E * nu / (1.0 + nu) / (1.0 - 2.0 * nu);
41 };
42 return Lambda(EE, nn);
43 }
44};
45
46///////////////////////////////////////////////////////////////////////////////
47/// \brief The IsoElasticySchearCoeff class converts E modulus of elasticity
48/// and Poisson's ratio to Shear coefficient
49///
51{
52 mfem::Coefficient *E, *nu;
53
54public:
55 /// Constructor - takes as inputs E modulus and Poisson's ratio
58
59 /// Evaluates the shear coefficient coefficient
61 const mfem::IntegrationPoint &ip) override
62 {
63 const real_t EE = E->Eval(T, ip);
64 const real_t nn = nu->Eval(T, ip);
65 constexpr auto Schear = [](const real_t E, const real_t nu)
66 {
67 return E / (2.0 * (1.0 + nu));
68 };
69 return Schear(EE, nn);
70 }
71};
72
73///////////////////////////////////////////////////////////////////////////////
74/// \brief The IsoLinElasticSolver class provides a solver for
75/// linear isotropic elasticity. The solver provides options for
76/// partial assembly, dFEM based integrators, and full assembly.
77/// The preconditioners are based on block LOR approximations.
79{
80public:
81 /// Construct the solver for a given mesh and discretization
82 /// order. The parameters pa and dfem define the utilization of
83 /// partial assembly or dFEM based integrators.
84 IsoLinElasticSolver(mfem::ParMesh *mesh, int vorder = 1,
85 bool pa = false, bool dfem = false);
86
87 /// Destructor of the solver.
89
90 /// Sets the linear solver relative tolerance (rtol),
91 /// absolute tolerance (atol) and maximum number of
92 /// iterations miter.
93 void SetLinearSolver(real_t rtol = 1e-8,
94 real_t atol = 1e-12,
95 int miter = 200);
96
97 /// Solves the forward problem.
98 void FSolve();
99
100 /// Adds displacement BC in direction 0(x), 1(y), 2(z), or -1(all).
101 void AddDispBC(int id, int dir, real_t val);
102
103 /// Adds displacement BC in direction 0(x), 1(y), 2(z), or -1(all).
104 void AddDispBC(int id, int dir, mfem::Coefficient &val);
105
106 /// Clear all displacement BC
107 void DelDispBC();
108
109 /// Set the values of the volumetric force.
110 void SetVolForce(real_t fx, real_t fy, real_t fz = 0.0);
111
112 /// Add surface load.
113 void AddSurfLoad(int id, real_t fx, real_t fy, real_t fz = 0.0)
114 {
115 mfem::Vector vec;
116 vec.SetSize(spaceDim);
117 vec[0] = fx;
118 vec[1] = fy;
119 if (spaceDim == 3) { vec[2] = fz; }
120 auto *vc = new mfem::VectorConstantCoefficient(vec);
121 if (load_coeff.find(id) != load_coeff.end()) { delete load_coeff[id]; }
122 load_coeff[id] = vc;
123 }
124
125 /// Add surface load
127 {
128 surf_loads[id] = &ff;
129 }
130
131 /// Associates coefficient to the volumetric force.
133
134 /// Returns the displacements.
136 {
137 fdisp.SetFromTrueDofs(sol);
138 return fdisp;
139 }
140
141 /// Returns the adjoint displacements.
143 {
144 adisp.SetFromTrueDofs(adj);
145 return adisp;
146 }
147
148 /// Returns the solution vector.
150
151 /// Returns the adjoint solution vector.
153
154 /// Returns the displacements.
156 {
157 sgf.SetSpace(vfes);
158 sgf.SetFromTrueDofs(sol);
159 }
160
161 /// Returns the adjoint displacements.
163 {
164 agf.SetSpace(vfes);
165 agf.SetFromTrueDofs(adj);
166 }
167
168 /// Sets BC dofs, bilinear form, preconditioner and solver.
169 /// Should be called before calling Mult of MultTranspose
170 virtual void Assemble();
171
172 /// Forward solve with given RHS. x is the RHS vector.
173 void Mult(const mfem::Vector &x, mfem::Vector &y) const override;
174
175 /// Adjoint solve with given RHS. x is the RHS vector.
176 /// The essential BCs are set to zero.
177 void MultTranspose(const mfem::Vector &x, mfem::Vector &y) const override;
178
179 /// Set material
181 {
182 E = &E_;
183 nu = &nu_;
184
185 delete lambda;
186 delete mu;
187 delete bf; bf=nullptr;
188 dop.release();
189
190 lambda = new IsoElasticyLambdaCoeff(E, nu);
191 mu = new IsoElasticySchearCoeff(E, nu);
192 }
193
196 {
197 public:
199 const mfem::IntegrationRule &ir,
200 int vdim) :
201 mfem::future::UniformParameterSpace(mesh, ir, vdim, false)
202 {
203 dtq.nqpt = ir.GetNPoints();
204 }
205 };
206
207 // creates a list with essential dofs
208 // sets the values in the bsol vector
209 // the list is written in ess_dofs
210 // The 'nvcc' compiler needs these SetEssTDofs functions to be public.
211 void SetEssTDofs(mfem::Vector &bsol, mfem::Array<int> &ess_dofs);
212 void SetEssTDofs(const int j, mfem::ParFiniteElementSpace& scalar_space,
213 mfem::Array<int> &ess_dofs);
214private:
215 mfem::ParMesh *pmesh;
216 const bool pa, dfem; // partial assembly, dFEM operator
217 const int dim, spaceDim;
218
219 // finite element collection for linear elasticity
221
222 // finite element space for linear elasticity
224
225 // solution true vector
226 mutable mfem::Vector sol;
227 // adjoint true vector
228 mutable mfem::Vector adj;
229 // RHS
230 mutable mfem::Vector rhs;
231
232 // forward solution
234 // adjoint solution
236
237 // Linear solver parameters
238 real_t linear_rtol;
239 real_t linear_atol;
240 int linear_iter;
241
242 mfem::HypreBoomerAMG *prec; // preconditioner
243 mfem::CGSolver *ls; // linear solver
244
245 // PA LOR preconditioner
246 mfem::Array<int> lor_block_offsets;
247 std::unique_ptr<mfem::Solver> lor_pa_prec;
248 std::unique_ptr<mfem::ParLORDiscretization> lor_disc;
249 std::unique_ptr<mfem::ElasticityIntegrator> lor_integrator;
250 std::unique_ptr<mfem::ParFiniteElementSpace> lor_scalar_fespace;
251 std::unique_ptr<mfem::BlockDiagonalPreconditioner> lor_blockDiag;
252 std::vector<std::unique_ptr<mfem::ParBilinearForm>> lor_bilinear_forms;
253 std::vector<std::unique_ptr<mfem::HypreParMatrix>> lor_block;
254 std::vector<std::unique_ptr<mfem::HypreBoomerAMG>> lor_amg_blocks;
255
256 /// Volumetric force created by the solver.
258 /// Volumetric force coefficient can point to the one
259 /// created by the solver or to external vector coefficient.
260 mfem::VectorCoefficient *volforce;
261
262 // surface loads
263 using VectorCoefficientPtrMap = std::map<int, mfem::VectorCoefficient *>;
264 VectorCoefficientPtrMap load_coeff; // internaly generated load
265 VectorCoefficientPtrMap surf_loads; // external vector coeeficients
266
267 class SurfaceLoad;
268 std::unique_ptr<SurfaceLoad> lcsurf_load; // localy generated surface loads
269 std::unique_ptr<SurfaceLoad> glsurf_load; // global surface loads
270
271 // boundary conditions for x,y, and z directions
272 using ConstantCoefficientMap = std::map<int, mfem::ConstantCoefficient>;
273 ConstantCoefficientMap bcx, bcy, bcz;
274
275 // holds BC in coefficient form
276 using CoefficientPtrMap = std::map<int, mfem::Coefficient*>;
277 CoefficientPtrMap bccx, bccy, bccz;
278
279 // holds the displacement contrained DOFs
280 mfem::Array<int> ess_tdofv;
281
282 mfem::Coefficient *E, *nu;
283 mfem::Coefficient *lambda, *mu;
284
287 std::unique_ptr<mfem::OperatorHandle> Kh;
288 std::unique_ptr<mfem::HypreParMatrix> K, Ke;
289
290 // begining of dFEM defintions
291 // U - displacements, Coords - nodal coordinates
292 // E modulud sampled on integration points
293 // Nu Poisson's ratio sampled on integration points
294 static constexpr int U = 0, Coords = 1, LCoeff = 2, MuCoeff = 3;
295 const mfem::FiniteElement *fe;
298 mfem::Array<int> domain_attributes;
299 const mfem::IntegrationRule &ir;
301 NqptUniformParameterSpace Lambda_ps, Mu_ps;
302 std::unique_ptr<mfem::CoefficientVector> Lambda_cv, Mu_cv;
303 std::unique_ptr<mfem::future::DifferentiableOperator> dop;
304 // end of dFEM definitions
305
307
308 class SurfaceLoad: public mfem::VectorCoefficient
309 {
310 VectorCoefficientPtrMap *map;
311 public:
312 SurfaceLoad(int dim, VectorCoefficientPtrMap &cmap):
314 {
315 map = &cmap;
316 }
318
320 const mfem::IntegrationPoint &ip) override
321 {
322 V.SetSize(GetVDim());
323 V = 0.0;
324 auto it = map->find(T.Attribute);
325 if (it != map->end()) { it->second->Eval(V, T, ip); }
326 }
327 };
328};
The IsoElasticyLambdaCoeff class converts E modulus of elasticity and Poisson's ratio to Lame's lambd...
real_t Eval(mfem::ElementTransformation &T, const mfem::IntegrationPoint &ip) override
Evaluates the Lame's lambda coefficient.
IsoElasticyLambdaCoeff(mfem::Coefficient *E, mfem::Coefficient *nu)
Constructor - takes as inputs E modulus and Poisson's ratio.
The IsoElasticySchearCoeff class converts E modulus of elasticity and Poisson's ratio to Shear coeffi...
real_t Eval(mfem::ElementTransformation &T, const mfem::IntegrationPoint &ip) override
Evaluates the shear coefficient coefficient.
IsoElasticySchearCoeff(mfem::Coefficient *E_, mfem::Coefficient *nu_)
Constructor - takes as inputs E modulus and Poisson's ratio.
NqptUniformParameterSpace(mfem::ParMesh &mesh, const mfem::IntegrationRule &ir, int vdim)
The IsoLinElasticSolver class provides a solver for linear isotropic elasticity. The solver provides ...
void SetEssTDofs(mfem::Vector &bsol, mfem::Array< int > &ess_dofs)
void AddDispBC(int id, int dir, real_t val)
Adds displacement BC in direction 0(x), 1(y), 2(z), or -1(all).
mfem::Vector & GetAdjointSolutionVector()
Returns the adjoint solution vector.
void FSolve()
Solves the forward problem.
void SetVolForce(real_t fx, real_t fy, real_t fz=0.0)
Set the values of the volumetric force.
void Mult(const mfem::Vector &x, mfem::Vector &y) const override
Forward solve with given RHS. x is the RHS vector.
void SetMaterial(mfem::Coefficient &E_, mfem::Coefficient &nu_)
Set material.
void GetAdj(mfem::ParGridFunction &agf)
Returns the adjoint displacements.
mfem::ParGridFunction & GetDisplacements()
Returns the displacements.
void GetSol(mfem::ParGridFunction &sgf)
Returns the displacements.
void SetLinearSolver(real_t rtol=1e-8, real_t atol=1e-12, int miter=200)
void AddSurfLoad(int id, real_t fx, real_t fy, real_t fz=0.0)
Add surface load.
IsoLinElasticSolver(mfem::ParMesh *mesh, int vorder=1, bool pa=false, bool dfem=false)
mfem::Vector & GetSolutionVector()
Returns the solution vector.
~IsoLinElasticSolver()
Destructor of the solver.
mfem::ParGridFunction & GetADisplacements()
Returns the adjoint displacements.
void AddSurfLoad(int id, mfem::VectorCoefficient &ff)
Add surface load.
virtual void Assemble()
void MultTranspose(const mfem::Vector &x, mfem::Vector &y) const override
void DelDispBC()
Clear all displacement BC.
Conjugate gradient method.
Definition solvers.hpp:627
Base class Coefficients that optionally depend on space and time. These are used by the BilinearFormI...
virtual real_t Eval(ElementTransformation &T, const IntegrationPoint &ip)=0
Evaluate the coefficient in the element described by T at the point ip.
Square Operator for imposing essential boundary conditions using only the action, Mult(),...
int nqpt
Number of quadrature points. When mode is TENSOR, this is the 1D number.
Definition fe_base.hpp:182
Collection of finite elements from the same family in multiple dimensions. This class is used to matc...
Definition fe_coll.hpp:27
Abstract class for all finite elements.
Definition fe_base.hpp:247
The BoomerAMG solver in hypre.
Definition hypre.hpp:1737
Class for integration point with weight.
Definition intrules.hpp:35
Class for an integration rule - an Array of IntegrationPoint.
Definition intrules.hpp:100
int GetNPoints() const
Returns the number of the points in the integration rule.
Definition intrules.hpp:256
Abstract operator.
Definition operator.hpp:25
Class for parallel bilinear form.
Abstract parallel finite element space.
Definition pfespace.hpp:31
Class for parallel grid function.
Definition pgridfunc.hpp:50
void SetFromTrueDofs(const Vector &tv) override
Set the GridFunction from the given true-dof vector.
void SetSpace(FiniteElementSpace *f) override
Associate a new FiniteElementSpace with the ParGridFunction.
Definition pgridfunc.cpp:91
Class for parallel linear form.
Class for parallel meshes.
Definition pmesh.hpp:34
Class representing the storage layout of a QuadratureFunction.
Definition qspace.hpp:164
Base class for vector Coefficients that optionally depend on time and space.
int GetVDim()
Returns dimension of the vector.
VectorCoefficient(int vd)
Initialize the VectorCoefficient with vector dimension vd.
virtual void Eval(Vector &V, ElementTransformation &T, const IntegrationPoint &ip)=0
Evaluate the vector coefficient in the element described by T at the point ip, storing the result in ...
Vector coefficient that is constant in space and time.
Vector data type.
Definition vector.hpp:82
void SetSize(int s)
Resize the vector to size s.
Definition vector.hpp:584
UniformParameterSpace(Mesh &mesh, const IntegrationRule &ir, int vdim, bool used_in_tensor_product=true)
Constructor for a uniform parameter space.
int dim
Definition ex24.cpp:53
real_t mu
Definition ex25.cpp:140
mfem::real_t real_t
float real_t
Definition config.hpp:46
std::array< int, NCMesh::MaxFaceNodes > nodes