Line data Source code
1 0 : // Distributed under the MIT License.
2 : // See LICENSE.txt for details.
3 :
4 : #pragma once
5 :
6 : #include <type_traits>
7 :
8 : #include "Parallel/Protocols/ElementRegistrar.hpp"
9 : #include "Parallel/Protocols/RegistrationMetavariables.hpp"
10 : #include "Utilities/ErrorHandling/Error.hpp"
11 : #include "Utilities/ProtocolHelpers.hpp"
12 : #include "Utilities/TMPL.hpp"
13 : #include "Utilities/TypeTraits/CreateHasTypeAlias.hpp"
14 :
15 : /// \cond
16 : namespace db {
17 : template <typename DbTagList>
18 : class DataBox;
19 : } // namespace db
20 : namespace Parallel {
21 : template <typename Metavariables>
22 : class GlobalCache;
23 : } // namespace Parallel
24 : /// \endcond
25 :
26 : namespace Parallel {
27 : namespace detail {
28 : CREATE_HAS_TYPE_ALIAS(registration)
29 : CREATE_HAS_TYPE_ALIAS_V(registration)
30 : } // namespace detail
31 :
32 : /// @{
33 : /// \brief (De)register an array element for specified actions
34 : ///
35 : /// \details Array elements are (de)registered with actions on components that
36 : /// need to know which elements are contributing data before the action can be
37 : /// executed. If array elements are migrated (e.g. during load balancing),
38 : /// or are created/destroyed (e.g. during adaptive mesh refinement), these
39 : /// functions must be called in order to (un)register (old) new elements.
40 : /// The list of registration actions is obtained from
41 : /// `Metavariables::registration::element_registrars`.
42 : ///
43 : /// \see Parallel::protocols::RegistrationMetavariables
44 : /// \see Parallel::protocols::ElementRegistrar
45 : template <typename ParallelComponent, typename DbTagList,
46 : typename Metavariables, typename ArrayIndex>
47 1 : void deregister_element(db::DataBox<DbTagList>& box,
48 : Parallel::GlobalCache<Metavariables>& cache,
49 : const ArrayIndex& array_index) {
50 : if constexpr (detail::has_registration_v<Metavariables>) {
51 : static_assert(tt::assert_conforms_to_v<
52 : typename Metavariables::registration,
53 : Parallel::protocols::RegistrationMetavariables>);
54 : using element_registrars =
55 : typename Metavariables::registration::element_registrars;
56 : if constexpr (tmpl::has_key<element_registrars, ParallelComponent>::value) {
57 : tmpl::for_each<tmpl::at<element_registrars, ParallelComponent>>(
58 : [&box, &cache, &array_index](auto registration_v) {
59 : using registration = typename decltype(registration_v)::type;
60 : static_assert(tt::assert_conforms_to_v<
61 : registration, Parallel::protocols::ElementRegistrar>);
62 : registration::template perform_deregistration<ParallelComponent>(
63 : box, cache, array_index);
64 : });
65 : }
66 : }
67 : }
68 :
69 : template <typename ParallelComponent, typename DbTagList,
70 : typename Metavariables, typename ArrayIndex>
71 1 : void register_element(db::DataBox<DbTagList>& box,
72 : Parallel::GlobalCache<Metavariables>& cache,
73 : const ArrayIndex& array_index) {
74 : if constexpr (detail::has_registration_v<Metavariables>) {
75 : static_assert(tt::assert_conforms_to_v<
76 : typename Metavariables::registration,
77 : Parallel::protocols::RegistrationMetavariables>);
78 : using element_registrars =
79 : typename Metavariables::registration::element_registrars;
80 : if constexpr (tmpl::has_key<element_registrars, ParallelComponent>::value) {
81 : tmpl::for_each<tmpl::at<element_registrars, ParallelComponent>>(
82 : [&box, &cache, &array_index](auto registration_v) {
83 : using registration = typename decltype(registration_v)::type;
84 : static_assert(tt::assert_conforms_to_v<
85 : registration, Parallel::protocols::ElementRegistrar>);
86 : registration::template perform_registration<ParallelComponent>(
87 : box, cache, array_index);
88 : });
89 : }
90 : }
91 : }
92 : /// @}
93 : } // namespace Parallel
|