KomissarovShock.hpp
1 // Distributed under the MIT License.
2 // See LICENSE.txt for details.
3 
4 #pragma once
5 
6 #include <array>
7 #include <limits>
8 #include <string>
9 
11 #include "Options/Options.hpp"
12 #include "PointwiseFunctions/AnalyticSolutions/GeneralRelativity/Minkowski.hpp"
13 #include "PointwiseFunctions/Hydro/EquationsOfState/EquationOfState.hpp"
14 #include "PointwiseFunctions/Hydro/EquationsOfState/IdealFluid.hpp" // IWYU pragma: keep
15 #include "PointwiseFunctions/Hydro/Tags.hpp"
16 #include "Utilities/TMPL.hpp"
18 // IWYU pragma: no_include <pup.h>
19 
20 /// \cond
21 namespace PUP {
22 class er; // IWYU pragma: keep
23 } // namespace PUP
24 /// \endcond
25 
26 namespace grmhd {
27 namespace Solutions {
28 
29 /*!
30  * \brief A one-dimensional shock solution for an ideal fluid in Minkowski
31  * spacetime
32  *
33  * This solution consists of a left state for \f$x<0\f$ and a right state for
34  * \f$x\ge 0\f$, each with constant fluid variables. The interface between these
35  * states moves with the shock speed \f$\mu\f$ as described in
36  * \cite Komissarov1999.
37  *
38  * \note We do not currently support 1D RMHD, so this class provides a 3D
39  * solution with \f$x\f$-dependence only. Therefore the computational domain can
40  * be represented by a single element with periodic boundary conditions in the
41  * \f$y\f$ and \f$z\f$ directions.
42  */
44  public:
47 
48  struct AdiabaticIndex {
49  using type = double;
50  static constexpr OptionString help = {
51  "The adiabatic index of the ideal fluid"};
52  static type lower_bound() noexcept { return 1.0; }
53  };
55  using type = double;
56  static std::string name() noexcept { return "LeftDensity"; };
57  static constexpr OptionString help = {
58  "Fluid rest mass density in the left half-domain"};
59  static type lower_bound() noexcept { return 0.0; }
60  };
62  using type = double;
63  static std::string name() noexcept { return "RightDensity"; };
64  static constexpr OptionString help = {
65  "Fluid rest mass density in the right half-domain"};
66  static type lower_bound() noexcept { return 0.0; }
67  };
68  struct LeftPressure {
69  using type = double;
70  static constexpr OptionString help = {
71  "Fluid pressure in the left half-domain"};
72  static type lower_bound() noexcept { return 0.0; }
73  };
74  struct RightPressure {
75  using type = double;
76  static constexpr OptionString help = {
77  "Fluid pressure in the right half-domain"};
78  static type lower_bound() noexcept { return 0.0; }
79  };
82  static std::string name() noexcept { return "LeftVelocity"; };
83  static constexpr OptionString help = {
84  "Fluid spatial velocity in the left half-domain"};
85  };
88  static std::string name() noexcept { return "RightVelocity"; };
89  static constexpr OptionString help = {
90  "Fluid spatial velocity in the right half-domain"};
91  };
94  static constexpr OptionString help = {
95  "Magnetic field in the left half-domain"};
96  };
99  static constexpr OptionString help = {
100  "Magnetic field in the right half-domain"};
101  };
102  struct ShockSpeed {
103  using type = double;
104  static constexpr OptionString help = {"Propagation speed of the shock"};
105  };
106 
107  using options = tmpl::list<AdiabaticIndex, LeftRestMassDensity,
111 
112  static constexpr OptionString help = {
113  "Analytic initial data for a Komissarov shock test. The fluid variables "
114  "are set homogeneously on either half of the domain left and right of "
115  "x=0."};
116 
117  KomissarovShock() = default;
118  KomissarovShock(const KomissarovShock& /*rhs*/) = delete;
119  KomissarovShock& operator=(const KomissarovShock& /*rhs*/) = delete;
120  KomissarovShock(KomissarovShock&& /*rhs*/) noexcept = default;
121  KomissarovShock& operator=(KomissarovShock&& /*rhs*/) noexcept = default;
122  ~KomissarovShock() = default;
123 
124  KomissarovShock(AdiabaticIndex::type adiabatic_index,
125  LeftRestMassDensity::type left_rest_mass_density,
126  RightRestMassDensity::type right_rest_mass_density,
127  LeftPressure::type left_pressure,
128  RightPressure::type right_pressure,
129  LeftSpatialVelocity::type left_spatial_velocity,
130  RightSpatialVelocity::type right_spatial_velocity,
131  LeftMagneticField::type left_magnetic_field,
132  RightMagneticField::type right_magnetic_field,
133  ShockSpeed::type shock_speed) noexcept;
134 
135  explicit KomissarovShock(CkMigrateMessage* /*unused*/) noexcept {}
136 
137  // @{
138  /// Retrieve the GRMHD variables at a given position.
139  template <typename DataType>
140  auto variables(
141  const tnsr::I<DataType, 3>& x, double t,
142  tmpl::list<hydro::Tags::RestMassDensity<DataType>> /*meta*/) const
144 
145  template <typename DataType>
146  auto variables(
147  const tnsr::I<DataType, 3>& x, double t,
148  tmpl::list<hydro::Tags::SpecificInternalEnergy<DataType>> /*meta*/) const
149  noexcept
151 
152  template <typename DataType>
153  auto variables(const tnsr::I<DataType, 3>& x, double t,
154  tmpl::list<hydro::Tags::Pressure<DataType>> /*meta*/) const
156 
157  template <typename DataType>
158  auto variables(const tnsr::I<DataType, 3>& x, double t,
159  tmpl::list<hydro::Tags::SpatialVelocity<
160  DataType, 3, Frame::Inertial>> /*meta*/) const noexcept
163 
164  template <typename DataType>
165  auto variables(const tnsr::I<DataType, 3>& x, double t,
166  tmpl::list<hydro::Tags::MagneticField<
167  DataType, 3, Frame::Inertial>> /*meta*/) const noexcept
170 
171  template <typename DataType>
172  auto variables(
173  const tnsr::I<DataType, 3>& x, double t,
174  tmpl::list<hydro::Tags::DivergenceCleaningField<DataType>> /*meta*/) const
175  noexcept
177 
178  template <typename DataType>
179  auto variables(
180  const tnsr::I<DataType, 3>& x, double t,
181  tmpl::list<hydro::Tags::LorentzFactor<DataType>> /*meta*/) const noexcept
183 
184  template <typename DataType>
185  auto variables(
186  const tnsr::I<DataType, 3>& x, double t,
187  tmpl::list<hydro::Tags::SpecificEnthalpy<DataType>> /*meta*/) const
189  // @}
190 
191  /// Retrieve a collection of hydrodynamic variables at position x
192  template <typename DataType, typename... Tags>
194  const tnsr::I<DataType, 3, Frame::Inertial>& x, double t,
195  tmpl::list<Tags...> /*meta*/) const noexcept {
196  static_assert(sizeof...(Tags) > 1,
197  "The generic template will recurse infinitely if only one "
198  "tag is being retrieved.");
199  return {tuples::get<Tags>(variables(x, t, tmpl::list<Tags>{}))...};
200  }
201 
202  /// Retrieve the metric variables
203  template <typename DataType, typename Tag>
204  tuples::TaggedTuple<Tag> variables(const tnsr::I<DataType, 3>& x, double t,
205  tmpl::list<Tag> /*meta*/) const noexcept {
206  return background_spacetime_.variables(x, t, tmpl::list<Tag>{});
207  }
208 
209  const EquationsOfState::IdealFluid<true>& equation_of_state() const noexcept {
210  return equation_of_state_;
211  }
212 
213  // clang-tidy: no runtime references
214  void pup(PUP::er& /*p*/) noexcept; // NOLINT
215 
216  private:
217  EquationsOfState::IdealFluid<true> equation_of_state_{};
218  gr::Solutions::Minkowski<3> background_spacetime_{};
219 
220  AdiabaticIndex::type adiabatic_index_ =
222  LeftRestMassDensity::type left_rest_mass_density_ =
224  RightRestMassDensity::type right_rest_mass_density_ =
226  LeftPressure::type left_pressure_ =
228  RightPressure::type right_pressure_ =
230  LeftSpatialVelocity::type left_spatial_velocity_ =
234  RightSpatialVelocity::type right_spatial_velocity_ =
238  LeftMagneticField::type left_magnetic_field_ =
242  RightMagneticField::type right_magnetic_field_ =
246  ShockSpeed::type shock_speed_ = std::numeric_limits<double>::signaling_NaN();
247 
248  friend bool operator==(const KomissarovShock& lhs,
249  const KomissarovShock& rhs) noexcept;
250 
251  friend bool operator!=(const KomissarovShock& lhs,
252  const KomissarovShock& rhs) noexcept;
253 };
254 
255 } // namespace Solutions
256 } // namespace grmhd
Definition: Strahlkorper.hpp:14
Defines class tuples::TaggedTuple.
The spatial velocity .
Definition: Tags.hpp:144
The fluid pressure .
Definition: Tags.hpp:123
The specific internal energy .
Definition: Tags.hpp:176
T signaling_NaN(T... args)
Definition: KomissarovShock.hpp:102
Defines classes and functions for making classes creatable from input files.
Definition: KomissarovShock.hpp:68
The magnetic field measured by an Eulerian observer, where is the normal to the spatial hypersurfac...
Definition: Tags.hpp:80
The divergence-cleaning field .
Definition: Tags.hpp:47
tuples::TaggedTuple< Tags... > variables(const tnsr::I< DataType, 3, Frame::Inertial > &x, double t, tmpl::list< Tags... >) const noexcept
Retrieve a collection of hydrodynamic variables at position x.
Definition: KomissarovShock.hpp:193
Definition: KomissarovShock.hpp:74
const char *const OptionString
The string used in option structs.
Definition: Options.hpp:27
An associative container that is indexed by structs.
Definition: TaggedTuple.hpp:272
Definition: KomissarovShock.hpp:48
The Lorentz factor .
Definition: Tags.hpp:64
Definition: DataBoxTag.hpp:29
Defines a list of useful type aliases for tensors.
Wraps the template metaprogramming library used (brigand)
tuples::TaggedTuple< Tag > variables(const tnsr::I< DataType, 3 > &x, double t, tmpl::list< Tag >) const noexcept
Retrieve the metric variables.
Definition: KomissarovShock.hpp:204
auto variables(const tnsr::I< DataType, 3 > &x, double t, tmpl::list< hydro::Tags::RestMassDensity< DataType >>) const noexcept -> tuples::TaggedTuple< hydro::Tags::RestMassDensity< DataType >>
Retrieve the GRMHD variables at a given position.
The rest-mass density .
Definition: Tags.hpp:130
Definition: IndexType.hpp:44
The specific enthalpy .
Definition: Tags.hpp:169
Items related to general relativistic magnetohydrodynamics (GRMHD)
Definition: Characteristics.hpp:34
A one-dimensional shock solution for an ideal fluid in Minkowski spacetime.
Definition: KomissarovShock.hpp:43