Line data Source code
1 0 : // Distributed under the MIT License.
2 : // See LICENSE.txt for details.
3 :
4 : #pragma once
5 :
6 : #include <array>
7 : #include <cstddef>
8 : #include <memory>
9 : #include <optional>
10 : #include <tuple>
11 : #include <utility>
12 : #include <vector>
13 :
14 : #include "ControlSystem/Tags/FunctionsOfTimeInitialize.hpp"
15 : #include "DataStructures/DataBox/DataBox.hpp"
16 : #include "DataStructures/Tensor/IndexType.hpp"
17 : #include "Domain/CoordinateMaps/CoordinateMap.hpp"
18 : #include "Domain/CoordinateMaps/Identity.hpp"
19 : #include "Domain/CoordinateMaps/Tags.hpp"
20 : #include "Domain/CreateInitialElement.hpp"
21 : #include "Domain/Creators/Tags/Domain.hpp"
22 : #include "Domain/Creators/Tags/FunctionsOfTime.hpp"
23 : #include "Domain/Creators/Tags/InitialExtents.hpp"
24 : #include "Domain/Creators/Tags/InitialRefinementLevels.hpp"
25 : #include "Domain/Domain.hpp"
26 : #include "Domain/ElementMap.hpp"
27 : #include "Domain/MinimumGridSpacing.hpp"
28 : #include "Domain/Structure/CreateInitialMesh.hpp"
29 : #include "Domain/Structure/Direction.hpp"
30 : #include "Domain/Structure/Element.hpp"
31 : #include "Domain/Structure/ElementId.hpp"
32 : #include "Domain/Tags.hpp"
33 : #include "Domain/Tags/NeighborMesh.hpp"
34 : #include "Domain/TagsTimeDependent.hpp"
35 : #include "Evolution/DiscontinuousGalerkin/Initialization/QuadratureTag.hpp"
36 : #include "Evolution/TagsDomain.hpp"
37 : #include "NumericalAlgorithms/Spectral/LogicalCoordinates.hpp"
38 : #include "NumericalAlgorithms/Spectral/Mesh.hpp"
39 : #include "NumericalAlgorithms/Spectral/Quadrature.hpp"
40 : #include "Parallel/AlgorithmExecution.hpp"
41 : #include "Parallel/GlobalCache.hpp"
42 : #include "Parallel/Tags/ArrayIndex.hpp"
43 : #include "ParallelAlgorithms/Amr/Protocols/Projector.hpp"
44 : #include "ParallelAlgorithms/Initialization/MutateAssign.hpp"
45 : #include "Utilities/Gsl.hpp"
46 : #include "Utilities/Requires.hpp"
47 : #include "Utilities/TMPL.hpp"
48 : #include "Utilities/TaggedTuple.hpp"
49 :
50 : /// \cond
51 : namespace Frame {
52 : struct Inertial;
53 : } // namespace Frame
54 : /// \endcond
55 :
56 : namespace evolution::dg::Initialization {
57 :
58 : /// \ingroup InitializationGroup
59 : /// \brief Initialize items related to the basic structure of the element
60 : ///
61 : /// \details See the type aliases defined below for what items are added to the
62 : /// GlobalCache and DataBox and how they are initialized
63 :
64 : template <size_t Dim, bool UseControlSystems = false>
65 1 : struct Domain {
66 : /// Tags for constant items added to the GlobalCache. These items are
67 : /// initialized from input file options.
68 1 : using const_global_cache_tags = tmpl::list<::domain::Tags::Domain<Dim>>;
69 :
70 : /// Tags for mutable items added to the GlobalCache. These items are
71 : /// initialized from input file options.
72 1 : using mutable_global_cache_tags = tmpl::list<tmpl::conditional_t<
73 : UseControlSystems, ::control_system::Tags::FunctionsOfTimeInitialize,
74 : ::domain::Tags::FunctionsOfTimeInitialize>>;
75 :
76 : /// Tags for simple DataBox items that are initialized from input file options
77 1 : using simple_tags_from_options =
78 : tmpl::list<::domain::Tags::InitialExtents<Dim>,
79 : ::domain::Tags::InitialRefinementLevels<Dim>,
80 : evolution::dg::Tags::Quadrature>;
81 :
82 : /// Tags for simple DataBox items that are default initialized.
83 1 : using default_initialized_simple_tags =
84 : tmpl::list<::domain::Tags::NeighborMesh<Dim>>;
85 :
86 : /// Tags for items fetched by the DataBox and passed to the apply function
87 1 : using argument_tags =
88 : tmpl::append<const_global_cache_tags, simple_tags_from_options,
89 : tmpl::list<::Parallel::Tags::ArrayIndex>>;
90 :
91 : /// Tags for items in the DataBox that are mutated by the apply function
92 1 : using return_tags =
93 : tmpl::list<::domain::Tags::Mesh<Dim>, ::domain::Tags::Element<Dim>,
94 : ::domain::Tags::ElementMap<Dim, Frame::Grid>,
95 : ::domain::CoordinateMaps::Tags::CoordinateMap<
96 : Dim, Frame::Grid, Frame::Inertial>>;
97 :
98 : /// Tags for mutable DataBox items that are either default initialized or
99 : /// initialized by the apply function
100 1 : using simple_tags =
101 : tmpl::append<default_initialized_simple_tags, return_tags>;
102 :
103 : /// Tags for immutable DataBox items (compute items or reference items) added
104 : /// to the DataBox.
105 1 : using compute_tags = tmpl::list<
106 : ::domain::Tags::LogicalCoordinates<Dim>,
107 : // Compute tags for Frame::Grid quantities
108 : ::domain::Tags::MappedCoordinates<
109 : ::domain::Tags::ElementMap<Dim, Frame::Grid>,
110 : ::domain::Tags::Coordinates<Dim, Frame::ElementLogical>>,
111 : ::domain::Tags::InverseJacobianCompute<
112 : ::domain::Tags::ElementMap<Dim, Frame::Grid>,
113 : ::domain::Tags::Coordinates<Dim, Frame::ElementLogical>>,
114 : // Compute tag to retrieve functions of time from global cache.
115 : Parallel::Tags::FromGlobalCache<tmpl::conditional_t<
116 : UseControlSystems, ::control_system::Tags::FunctionsOfTimeInitialize,
117 : ::domain::Tags::FunctionsOfTimeInitialize>>,
118 : // Compute tags for Frame::Inertial quantities
119 : ::domain::Tags::CoordinatesMeshVelocityAndJacobiansCompute<
120 : ::domain::CoordinateMaps::Tags::CoordinateMap<Dim, Frame::Grid,
121 : Frame::Inertial>>,
122 :
123 : ::domain::Tags::InertialFromGridCoordinatesCompute<Dim>,
124 : ::domain::Tags::ElementToInertialInverseJacobian<Dim>,
125 : ::domain::Tags::DetInvJacobianCompute<Dim, Frame::ElementLogical,
126 : Frame::Inertial>,
127 : ::domain::Tags::InertialMeshVelocityCompute<Dim>,
128 : evolution::domain::Tags::DivMeshVelocityCompute<Dim>,
129 : // Compute tags for other mesh quantities
130 : ::domain::Tags::MinimumGridSpacingCompute<Dim, Frame::Inertial>>;
131 :
132 : /// Given the items fetched from a DataBox by the argument_tags, mutate
133 : /// the items in the DataBox corresponding to return_tags
134 1 : static void apply(
135 : const gsl::not_null<Mesh<Dim>*> mesh,
136 : const gsl::not_null<Element<Dim>*> element,
137 : const gsl::not_null<ElementMap<Dim, Frame::Grid>*> element_map,
138 : const gsl::not_null<std::unique_ptr<
139 : ::domain::CoordinateMapBase<Frame::Grid, Frame::Inertial, Dim>>*>
140 : grid_to_inertial_map,
141 : const ::Domain<Dim>& domain,
142 : const std::vector<std::array<size_t, Dim>>& initial_extents,
143 : const std::vector<std::array<size_t, Dim>>& initial_refinement,
144 : const Spectral::Quadrature& quadrature,
145 : const ElementId<Dim>& element_id) {
146 : const auto& my_block = domain.blocks()[element_id.block_id()];
147 : *mesh = ::domain::Initialization::create_initial_mesh(
148 : initial_extents, element_id, quadrature);
149 : *element = ::domain::Initialization::create_initial_element(
150 : element_id, my_block, initial_refinement);
151 : *element_map = ElementMap<Dim, Frame::Grid>{element_id, my_block};
152 :
153 : if (my_block.is_time_dependent()) {
154 : *grid_to_inertial_map =
155 : my_block.moving_mesh_grid_to_inertial_map().get_clone();
156 : } else {
157 : *grid_to_inertial_map =
158 : ::domain::make_coordinate_map_base<Frame::Grid, Frame::Inertial>(
159 : ::domain::CoordinateMaps::Identity<Dim>{});
160 : }
161 : }
162 : };
163 :
164 : /// \brief Initialize/update items related to coordinate maps after an AMR
165 : /// change
166 : template <size_t Dim>
167 1 : struct ProjectDomain : tt::ConformsTo<amr::protocols::Projector> {
168 0 : using return_tags = tmpl::list<::domain::Tags::ElementMap<Dim, Frame::Grid>,
169 : ::domain::CoordinateMaps::Tags::CoordinateMap<
170 : Dim, Frame::Grid, Frame::Inertial>>;
171 0 : using argument_tags =
172 : tmpl::list<::domain::Tags::Domain<Dim>, ::domain::Tags::Element<Dim>>;
173 :
174 0 : static void apply(
175 : const gsl::not_null<ElementMap<Dim, Frame::Grid>*> /*element_map*/,
176 : const gsl::not_null<std::unique_ptr<
177 : ::domain::CoordinateMapBase<Frame::Grid, Frame::Inertial, Dim>>*>
178 : /*grid_to_inertial_map*/,
179 : const ::Domain<Dim>& /*domain*/, const Element<Dim>& /*element*/,
180 : const std::pair<Mesh<Dim>, Element<Dim>>& /*old_mesh_and_element*/) {
181 : // Do not change anything for p-refinement
182 : }
183 :
184 : template <typename ParentOrChildrenItemsType>
185 0 : static void apply(
186 : const gsl::not_null<ElementMap<Dim, Frame::Grid>*> element_map,
187 : const gsl::not_null<std::unique_ptr<
188 : ::domain::CoordinateMapBase<Frame::Grid, Frame::Inertial, Dim>>*>
189 : grid_to_inertial_map,
190 : const ::Domain<Dim>& domain, const Element<Dim>& element,
191 : const ParentOrChildrenItemsType& /*parent_or_children_items*/) {
192 : const ElementId<Dim>& element_id = element.id();
193 : const auto& my_block = domain.blocks()[element_id.block_id()];
194 : *element_map = ElementMap<Dim, Frame::Grid>{element_id, my_block};
195 : if (my_block.is_time_dependent()) {
196 : *grid_to_inertial_map =
197 : my_block.moving_mesh_grid_to_inertial_map().get_clone();
198 : } else {
199 : *grid_to_inertial_map =
200 : ::domain::make_coordinate_map_base<Frame::Grid, Frame::Inertial>(
201 : ::domain::CoordinateMaps::Identity<Dim>{});
202 : }
203 : }
204 : };
205 : } // namespace evolution::dg::Initialization
|