Serac  0.1
Serac is an implicit thermal strucural mechanics simulation code.
odes.hpp
Go to the documentation of this file.
1 // Copyright (c) 2019-2023, Lawrence Livermore National Security, LLC and
2 // other Serac Project Developers. See the top-level LICENSE file for
3 // details.
4 //
5 // SPDX-License-Identifier: (BSD-3-Clause)
6 
13 #pragma once
14 
15 #include <functional>
16 
17 #include "mfem.hpp"
18 
21 
22 namespace serac::mfem_ext {
23 
34 class SecondOrderODE : public mfem::SecondOrderTimeDependentOperator {
35 public:
45  static constexpr double epsilon = 0.0001;
46 
51  struct State {
55  double& time;
56 
60  double& c0;
61 
65  double& c1;
66 
70  mfem::Vector& u;
71 
75  mfem::Vector& du_dt;
76 
80  mfem::Vector& d2u_dt2;
81  };
82 
102  SecondOrderODE(int n, State&& state, const EquationSolver& solver, const BoundaryConditionManager& bcs);
103 
111  void Mult(const mfem::Vector& u, const mfem::Vector& du_dt, mfem::Vector& d2u_dt2) const override
112  {
113  Solve(t, 0.0, 0.0, u, du_dt, d2u_dt2);
114  }
115 
125  void ImplicitSolve(const double c0, const double c1, const mfem::Vector& u, const mfem::Vector& du_dt,
126  mfem::Vector& d2u_dt2) override
127  {
128  Solve(t, c0, c1, u, du_dt, d2u_dt2);
129  }
130 
134  void ImplicitSolve(const double dt, const mfem::Vector& u, mfem::Vector& du_dt) override;
135 
140  void SetEnforcementMethod(const DirichletEnforcementMethod method) { enforcement_method_ = method; }
141 
147  void SetTimestepper(const serac::TimestepMethod timestepper);
148 
159  void Step(mfem::Vector& x, mfem::Vector& dxdt, double& time, double& dt);
160 
164  const State& GetState() { return state_; }
165 
171  TimestepMethod GetTimestepper() { return timestepper_; }
172 
173 private:
185  void Solve(const double time, const double c0, const double c1, const mfem::Vector& u, const mfem::Vector& du_dt,
186  mfem::Vector& d2u_dt2) const;
187 
191  State state_;
199  const EquationSolver& solver_;
203  std::unique_ptr<mfem::SecondOrderODESolver> second_order_ode_solver_;
204 
208  std::unique_ptr<mfem::ODESolver> first_order_system_ode_solver_;
209 
213  const BoundaryConditionManager& bcs_;
214  mfem::Vector zero_;
215 
219  mutable mfem::Vector U_minus_;
220  mutable mfem::Vector U_;
221  mutable mfem::Vector U_plus_;
222  mutable mfem::Vector dU_dt_;
223  mutable mfem::Vector d2U_dt2_;
224 
225  serac::TimestepMethod timestepper_;
226 };
227 
238 class FirstOrderODE : public mfem::TimeDependentOperator {
239 public:
249  static constexpr double epsilon = 0.000001;
250 
255  struct State {
259  double& time;
260 
264  mfem::Vector& u;
265 
269  double& dt;
270 
274  mfem::Vector& du_dt;
275 
279  double& previous_dt;
280  };
281 
300  FirstOrderODE(int n, FirstOrderODE::State&& state, const EquationSolver& solver, const BoundaryConditionManager& bcs);
301 
308  void Mult(const mfem::Vector& u, mfem::Vector& du_dt) const { Solve(t, 0.0, u, du_dt); }
309 
317  void ImplicitSolve(const double dt, const mfem::Vector& u, mfem::Vector& du_dt) { Solve(t, dt, u, du_dt); }
318 
323  void SetEnforcementMethod(const DirichletEnforcementMethod method) { enforcement_method_ = method; }
324 
330  void SetTimestepper(const serac::TimestepMethod timestepper);
331 
341  void Step(mfem::Vector& x, double& time, double& dt)
342  {
343  if (ode_solver_) {
344  ode_solver_->Step(x, time, dt);
345  } else {
346  SLIC_ERROR("ode_solver_ unspecified");
347  }
348  }
349 
355  TimestepMethod GetTimestepper() { return timestepper_; }
356 
357 private:
365  virtual void Solve(const double time, const double dt, const mfem::Vector& u, mfem::Vector& du_dt) const;
366 
370  FirstOrderODE::State state_;
371 
379  const EquationSolver& solver_;
383  std::unique_ptr<mfem::ODESolver> ode_solver_;
387  const BoundaryConditionManager& bcs_;
388  mfem::Vector zero_;
389 
393  mutable mfem::Vector U_minus_;
394  mutable mfem::Vector U_;
395  mutable mfem::Vector U_plus_;
396  mutable mfem::Vector dU_dt_;
397 
398  TimestepMethod timestepper_;
399 };
400 
401 } // namespace serac::mfem_ext
This file contains the declaration of the boundary condition manager class.
A container for the boundary condition information relating to a specific physics module.
This class manages the objects typically required to solve a nonlinear set of equations arising from ...
FirstOrderODE is a class wrapping mfem::TimeDependentOperator so that the user can use std::function ...
Definition: odes.hpp:238
void ImplicitSolve(const double dt, const mfem::Vector &u, mfem::Vector &du_dt)
Solves the equation du_dt = f(u + dt * du_dt, t)
Definition: odes.hpp:317
TimestepMethod GetTimestepper()
Query the timestep method for the ode solver.
Definition: odes.hpp:355
void SetTimestepper(const serac::TimestepMethod timestepper)
Set the time integration method.
Definition: odes.cpp:261
FirstOrderODE(int n, FirstOrderODE::State &&state, const EquationSolver &solver, const BoundaryConditionManager &bcs)
Constructor defining the size and specific system of ordinary differential equations to be solved.
Definition: odes.cpp:250
void Mult(const mfem::Vector &u, mfem::Vector &du_dt) const
Solves the equation du_dt = f(u, t)
Definition: odes.hpp:308
static constexpr double epsilon
a small number used to compute finite difference approximations to time derivatives of boundary condi...
Definition: odes.hpp:249
void SetEnforcementMethod(const DirichletEnforcementMethod method)
Configures the Dirichlet enforcement method to use.
Definition: odes.hpp:323
void Step(mfem::Vector &x, double &time, double &dt)
Performs a time step.
Definition: odes.hpp:341
SecondOrderODE is a class wrapping mfem::SecondOrderTimeDependentOperator so that the user can use st...
Definition: odes.hpp:34
void Step(mfem::Vector &x, mfem::Vector &dxdt, double &time, double &dt)
Performs a time step.
Definition: odes.cpp:77
const State & GetState()
Get a reference to the current state.
Definition: odes.hpp:164
void ImplicitSolve(const double c0, const double c1, const mfem::Vector &u, const mfem::Vector &du_dt, mfem::Vector &d2u_dt2) override
Solves the equation d2u_dt2 = f(u + c0 * d2u_dt2, du_dt + c1 * d2u_dt2, t)
Definition: odes.hpp:125
void Mult(const mfem::Vector &u, const mfem::Vector &du_dt, mfem::Vector &d2u_dt2) const override
Solves the equation d2u_dt2 = f(u, du_dt, t)
Definition: odes.hpp:111
static constexpr double epsilon
a small number used to compute finite difference approximations to time derivatives of boundary condi...
Definition: odes.hpp:45
void SetEnforcementMethod(const DirichletEnforcementMethod method)
Configures the Dirichlet enforcement method to use.
Definition: odes.hpp:140
void SetTimestepper(const serac::TimestepMethod timestepper)
Set the time integration method.
Definition: odes.cpp:22
SecondOrderODE(int n, State &&state, const EquationSolver &solver, const BoundaryConditionManager &bcs)
Constructor defining the size and specific system of ordinary differential equations to be solved.
Definition: odes.cpp:11
TimestepMethod GetTimestepper()
Query the timestep method for the ode solver.
Definition: odes.hpp:171
This file contains the declaration of an equation solver wrapper.
DirichletEnforcementMethod
this enum describes which way to enforce the time-varying constraint u(t) == U(t)
TimestepMethod
Timestep method of a solver.
A set of references to physics-module-owned variables used by the residual operator.
Definition: odes.hpp:255
double & dt
Current time step.
Definition: odes.hpp:269
mfem::Vector & u
Predicted true DOFs.
Definition: odes.hpp:264
double & time
Time value at which the ODE solver wants to compute a residual.
Definition: odes.hpp:259
mfem::Vector & du_dt
Previous value of du_dt.
Definition: odes.hpp:274
double & previous_dt
Previous value of dt.
Definition: odes.hpp:279
A set of references to physics-module-owned variables used by the residual operator.
Definition: odes.hpp:51
double & time
Time value at which the ODE solver wants to compute a residual.
Definition: odes.hpp:55
double & c0
coefficient used to calculate updated displacement: u_{n + 1} := u + c0 * d2u_dt2
Definition: odes.hpp:60
mfem::Vector & du_dt
Predicted du_dt.
Definition: odes.hpp:75
double & c1
coefficient used to calculate updated velocity: du_dt_{n+1} := du_dt + c1 * d2u_dt2
Definition: odes.hpp:65
mfem::Vector & u
Predicted true DOFs.
Definition: odes.hpp:70
mfem::Vector & d2u_dt2
Previous value of d^2u_dt^2.
Definition: odes.hpp:80