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