Line data Source code
1 0 : // Distributed under the MIT License.
2 : // See LICENSE.txt for details.
3 :
4 : #pragma once
5 :
6 : #include <memory>
7 : #include <optional>
8 : #include <pup.h>
9 : #include <string>
10 : #include <type_traits>
11 :
12 : #include "DataStructures/DataBox/Prefixes.hpp"
13 : #include "DataStructures/DataVector.hpp"
14 : #include "DataStructures/Tensor/Tensor.hpp"
15 : #include "DataStructures/Variables.hpp"
16 : #include "Evolution/BoundaryConditions/Type.hpp"
17 : #include "Evolution/Systems/RelativisticEuler/Valencia/BoundaryConditions/BoundaryCondition.hpp"
18 : #include "Evolution/Systems/RelativisticEuler/Valencia/ConservativeFromPrimitive.hpp"
19 : #include "Evolution/Systems/RelativisticEuler/Valencia/Fluxes.hpp"
20 : #include "Evolution/Systems/RelativisticEuler/Valencia/Tags.hpp"
21 : #include "Options/String.hpp"
22 : #include "PointwiseFunctions/AnalyticData/Tags.hpp"
23 : #include "PointwiseFunctions/AnalyticSolutions/AnalyticSolution.hpp"
24 : #include "Utilities/Gsl.hpp"
25 : #include "Utilities/Serialization/CharmPupable.hpp"
26 : #include "Utilities/TMPL.hpp"
27 :
28 : /// \cond
29 : namespace Tags {
30 : struct Time;
31 : } // namespace Tags
32 : namespace domain::Tags {
33 : template <size_t Dim, typename Frame>
34 : struct Coordinates;
35 : } // namespace domain::Tags
36 : /// \endcond
37 :
38 : namespace RelativisticEuler::Valencia::BoundaryConditions {
39 : /*!
40 : * \brief Sets Dirichlet boundary conditions using the analytic solution or
41 : * analytic data.
42 : */
43 : template <size_t Dim>
44 1 : class DirichletAnalytic final : public BoundaryCondition<Dim> {
45 : public:
46 0 : using options = tmpl::list<>;
47 0 : static constexpr Options::String help{
48 : "DirichletAnalytic boundary conditions using either analytic solution or "
49 : "analytic data."};
50 :
51 0 : DirichletAnalytic() = default;
52 0 : DirichletAnalytic(DirichletAnalytic&&) = default;
53 0 : DirichletAnalytic& operator=(DirichletAnalytic&&) = default;
54 0 : DirichletAnalytic(const DirichletAnalytic&) = default;
55 0 : DirichletAnalytic& operator=(const DirichletAnalytic&) = default;
56 0 : ~DirichletAnalytic() override = default;
57 :
58 0 : explicit DirichletAnalytic(CkMigrateMessage* msg);
59 :
60 0 : WRAPPED_PUPable_decl_base_template(
61 : domain::BoundaryConditions::BoundaryCondition, DirichletAnalytic);
62 :
63 0 : auto get_clone() const -> std::unique_ptr<
64 : domain::BoundaryConditions::BoundaryCondition> override;
65 :
66 0 : static constexpr evolution::BoundaryConditions::Type bc_type =
67 : evolution::BoundaryConditions::Type::Ghost;
68 :
69 0 : void pup(PUP::er& p) override;
70 :
71 0 : using dg_interior_evolved_variables_tags = tmpl::list<>;
72 0 : using dg_interior_temporary_tags =
73 : tmpl::list<domain::Tags::Coordinates<Dim, Frame::Inertial>>;
74 0 : using dg_interior_primitive_variables_tags = tmpl::list<>;
75 0 : using dg_gridless_tags =
76 : tmpl::list<::Tags::Time, ::Tags::AnalyticSolutionOrData>;
77 :
78 : template <typename AnalyticSolutionOrData>
79 0 : std::optional<std::string> dg_ghost(
80 : const gsl::not_null<Scalar<DataVector>*> tilde_d,
81 : const gsl::not_null<Scalar<DataVector>*> tilde_tau,
82 : const gsl::not_null<tnsr::i<DataVector, Dim, Frame::Inertial>*> tilde_s,
83 :
84 : const gsl::not_null<tnsr::I<DataVector, Dim, Frame::Inertial>*>
85 : flux_tilde_d,
86 : const gsl::not_null<tnsr::I<DataVector, Dim, Frame::Inertial>*>
87 : flux_tilde_tau,
88 : const gsl::not_null<tnsr::Ij<DataVector, Dim, Frame::Inertial>*>
89 : flux_tilde_s,
90 :
91 : const gsl::not_null<Scalar<DataVector>*> lapse,
92 : const gsl::not_null<tnsr::I<DataVector, Dim, Frame::Inertial>*> shift,
93 : const gsl::not_null<tnsr::ii<DataVector, Dim, Frame::Inertial>*>
94 : spatial_metric,
95 : const gsl::not_null<Scalar<DataVector>*> rest_mass_density,
96 : const gsl::not_null<Scalar<DataVector>*> specific_internal_energy,
97 : const gsl::not_null<Scalar<DataVector>*> specific_enthalpy,
98 : const gsl::not_null<tnsr::I<DataVector, Dim, Frame::Inertial>*>
99 : spatial_velocity,
100 : const gsl::not_null<tnsr::II<DataVector, Dim, Frame::Inertial>*>
101 : inv_spatial_metric,
102 :
103 : const std::optional<
104 : tnsr::I<DataVector, Dim, Frame::Inertial>>& /*face_mesh_velocity*/,
105 : const tnsr::i<DataVector, Dim, Frame::Inertial>& /*normal_covector*/,
106 : const tnsr::I<DataVector, Dim, Frame::Inertial>& /*normal_vector*/,
107 : const tnsr::I<DataVector, Dim, Frame::Inertial>& coords,
108 : const double time,
109 : const AnalyticSolutionOrData& analytic_solution_or_data) const {
110 : auto boundary_values = [&analytic_solution_or_data, &coords, &time]() {
111 : if constexpr (is_analytic_solution_v<AnalyticSolutionOrData>) {
112 : return analytic_solution_or_data.variables(
113 : coords, time,
114 : tmpl::list<hydro::Tags::RestMassDensity<DataVector>,
115 : hydro::Tags::SpecificInternalEnergy<DataVector>,
116 : hydro::Tags::SpecificEnthalpy<DataVector>,
117 : hydro::Tags::Pressure<DataVector>,
118 : hydro::Tags::SpatialVelocity<DataVector, Dim>,
119 : hydro::Tags::LorentzFactor<DataVector>,
120 : gr::Tags::SqrtDetSpatialMetric<DataVector>,
121 : gr::Tags::Lapse<DataVector>,
122 : gr::Tags::Shift<DataVector, Dim>,
123 : gr::Tags::SpatialMetric<DataVector, Dim>,
124 : gr::Tags::InverseSpatialMetric<DataVector, Dim>>{});
125 : } else {
126 : (void)time;
127 : return analytic_solution_or_data.variables(
128 : coords,
129 : tmpl::list<hydro::Tags::RestMassDensity<DataVector>,
130 : hydro::Tags::SpecificInternalEnergy<DataVector>,
131 : hydro::Tags::SpecificEnthalpy<DataVector>,
132 : hydro::Tags::Pressure<DataVector>,
133 : hydro::Tags::SpatialVelocity<DataVector, Dim>,
134 : hydro::Tags::LorentzFactor<DataVector>,
135 : gr::Tags::SqrtDetSpatialMetric<DataVector>,
136 : gr::Tags::Lapse<DataVector>,
137 : gr::Tags::Shift<DataVector, Dim>,
138 : gr::Tags::SpatialMetric<DataVector, Dim>,
139 : gr::Tags::InverseSpatialMetric<DataVector, Dim>>{});
140 : }
141 : }();
142 :
143 : *lapse = get<gr::Tags::Lapse<DataVector>>(boundary_values);
144 : *shift = get<gr::Tags::Shift<DataVector, Dim>>(boundary_values);
145 : *spatial_metric =
146 : get<gr::Tags::SpatialMetric<DataVector, Dim>>(boundary_values);
147 : *inv_spatial_metric =
148 : get<gr::Tags::InverseSpatialMetric<DataVector, Dim>>(boundary_values);
149 : *rest_mass_density =
150 : get<hydro::Tags::RestMassDensity<DataVector>>(boundary_values);
151 : *specific_internal_energy =
152 : get<hydro::Tags::SpecificInternalEnergy<DataVector>>(boundary_values);
153 : *specific_enthalpy =
154 : get<hydro::Tags::SpecificEnthalpy<DataVector>>(boundary_values);
155 : *spatial_velocity =
156 : get<hydro::Tags::SpatialVelocity<DataVector, Dim>>(boundary_values);
157 :
158 : const auto& pressure =
159 : get<hydro::Tags::Pressure<DataVector>>(boundary_values);
160 : const auto& lorentz_factor =
161 : get<hydro::Tags::LorentzFactor<DataVector>>(boundary_values);
162 : const auto& sqrt_det_spatial_metric =
163 : get<gr::Tags::SqrtDetSpatialMetric<DataVector>>(boundary_values);
164 :
165 : ConservativeFromPrimitive<Dim>::apply(
166 : tilde_d, tilde_tau, tilde_s, *rest_mass_density,
167 : *specific_internal_energy, *specific_enthalpy, pressure,
168 : *spatial_velocity, lorentz_factor, sqrt_det_spatial_metric,
169 : *spatial_metric);
170 : ComputeFluxes<Dim>::apply(flux_tilde_d, flux_tilde_tau, flux_tilde_s,
171 : *tilde_d, *tilde_tau, *tilde_s, *lapse, *shift,
172 : sqrt_det_spatial_metric, pressure,
173 : *spatial_velocity);
174 :
175 : return {};
176 : }
177 : };
178 : } // namespace RelativisticEuler::Valencia::BoundaryConditions
|