Line data Source code
1 0 : // Distributed under the MIT License.
2 : // See LICENSE.txt for details.
3 :
4 : #pragma once
5 :
6 : #include <cstdint>
7 : #include <pup.h>
8 : #include <pup_stl.h>
9 : #include <string>
10 : #include <type_traits>
11 : #include <utility>
12 : #include <vector>
13 :
14 : #include "IO/Observer/Helpers.hpp"
15 : #include "IO/Observer/ObservationId.hpp"
16 : #include "IO/Observer/ObserverComponent.hpp"
17 : #include "IO/Observer/ReductionActions.hpp"
18 : #include "IO/Observer/TypeOfObservation.hpp"
19 : #include "Options/String.hpp"
20 : #include "Parallel/ArrayComponentId.hpp"
21 : #include "Parallel/ArrayIndex.hpp"
22 : #include "Parallel/GlobalCache.hpp"
23 : #include "Parallel/Invoke.hpp"
24 : #include "Parallel/Local.hpp"
25 : #include "Parallel/Reduction.hpp"
26 : #include "ParallelAlgorithms/EventsAndTriggers/Event.hpp"
27 : #include "Time/AdaptiveSteppingDiagnostics.hpp"
28 : #include "Utilities/Functional.hpp"
29 : #include "Utilities/Serialization/CharmPupable.hpp"
30 : #include "Utilities/TMPL.hpp"
31 :
32 : /// \cond
33 : namespace Tags {
34 : struct AdaptiveSteppingDiagnostics;
35 : } // namespace Tags
36 : /// \endcond
37 :
38 : namespace Events {
39 : /*!
40 : * \brief %Observe diagnostics about adaptive time-stepping
41 : *
42 : * Writes reduction quantities:
43 : * - `%Time`
44 : * - `Number of slabs`
45 : * - `Number of slab size changes`
46 : * - `Total steps on all elements`
47 : * - `Number of LTS step changes`
48 : * - `Number of step rejections`
49 : *
50 : * The slab information is the same on all elements. The step
51 : * information is summed over the elements.
52 : */
53 1 : class ObserveAdaptiveSteppingDiagnostics : public Event {
54 : private:
55 0 : using ReductionData = Parallel::ReductionData<
56 : Parallel::ReductionDatum<double, funcl::AssertEqual<>>,
57 : Parallel::ReductionDatum<uint64_t, funcl::AssertEqual<>>,
58 : Parallel::ReductionDatum<uint64_t, funcl::AssertEqual<>>,
59 : Parallel::ReductionDatum<uint64_t, funcl::Plus<>>,
60 : Parallel::ReductionDatum<uint64_t, funcl::Plus<>>,
61 : Parallel::ReductionDatum<uint64_t, funcl::Plus<>>>;
62 :
63 : public:
64 : /// The name of the subfile inside the HDF5 file
65 1 : struct SubfileName {
66 0 : using type = std::string;
67 0 : static constexpr Options::String help = {
68 : "The name of the subfile inside the HDF5 file without an extension and "
69 : "without a preceding '/'."};
70 : };
71 :
72 : /// \cond
73 : explicit ObserveAdaptiveSteppingDiagnostics(CkMigrateMessage* /*unused*/) {}
74 : using PUP::able::register_constructor;
75 : WRAPPED_PUPable_decl_template(ObserveAdaptiveSteppingDiagnostics); // NOLINT
76 : /// \endcond
77 :
78 0 : using options = tmpl::list<SubfileName>;
79 0 : static constexpr Options::String help =
80 : "Observe diagnostics about adaptive time-stepping\n"
81 : "\n"
82 : "Writes reduction quantities:\n"
83 : " - Time\n"
84 : " - Number of slabs\n"
85 : " - Number of slab size changes\n"
86 : " - Total steps on all elements\n"
87 : " - Number of LTS step changes\n"
88 : " - Number of step rejections\n"
89 : "\n"
90 : "The slab information is the same on all elements. The step\n"
91 : "information is summed over the elements.";
92 :
93 0 : ObserveAdaptiveSteppingDiagnostics() = default;
94 0 : explicit ObserveAdaptiveSteppingDiagnostics(const std::string& subfile_name)
95 : : subfile_path_("/" + subfile_name) {}
96 :
97 0 : using observed_reduction_data_tags =
98 : observers::make_reduction_data_tags<tmpl::list<ReductionData>>;
99 :
100 0 : using compute_tags_for_observation_box = tmpl::list<>;
101 :
102 0 : using return_tags = tmpl::list<>;
103 0 : using argument_tags = tmpl::list<::Tags::AdaptiveSteppingDiagnostics>;
104 :
105 : template <typename ArrayIndex, typename ParallelComponent,
106 : typename Metavariables>
107 0 : void operator()(const AdaptiveSteppingDiagnostics& diags,
108 : Parallel::GlobalCache<Metavariables>& cache,
109 : const ArrayIndex& array_index,
110 : const ParallelComponent* const /*meta*/,
111 : const ObservationValue& observation_value) const {
112 : auto& local_observer = *Parallel::local_branch(
113 : Parallel::get_parallel_component<observers::Observer<Metavariables>>(
114 : cache));
115 : Parallel::simple_action<observers::Actions::ContributeReductionData>(
116 : local_observer,
117 : observers::ObservationId(observation_value.value,
118 : subfile_path_ + ".dat"),
119 : Parallel::make_array_component_id<ParallelComponent>(array_index),
120 : subfile_path_,
121 : std::vector<std::string>{
122 : observation_value.name, "Number of slabs",
123 : "Number of slab size changes", "Total steps on all elements",
124 : "Number of LTS step changes", "Number of step rejections"},
125 : ReductionData{observation_value.value, diags.number_of_slabs,
126 : diags.number_of_slab_size_changes, diags.number_of_steps,
127 : diags.number_of_step_fraction_changes,
128 : diags.number_of_step_rejections});
129 : }
130 :
131 0 : using observation_registration_tags = tmpl::list<>;
132 : std::pair<observers::TypeOfObservation, observers::ObservationKey>
133 0 : get_observation_type_and_key_for_registration() const {
134 : return {observers::TypeOfObservation::Reduction,
135 : observers::ObservationKey(subfile_path_ + ".dat")};
136 : }
137 :
138 0 : using is_ready_argument_tags = tmpl::list<>;
139 :
140 : template <typename Metavariables, typename ArrayIndex, typename Component>
141 0 : bool is_ready(Parallel::GlobalCache<Metavariables>& /*cache*/,
142 : const ArrayIndex& /*array_index*/,
143 : const Component* const /*meta*/) const {
144 : return true;
145 : }
146 :
147 1 : bool needs_evolved_variables() const override { return false; }
148 :
149 : // NOLINTNEXTLINE(google-runtime-references)
150 0 : void pup(PUP::er& p) override {
151 : Event::pup(p);
152 : p | subfile_path_;
153 : }
154 :
155 : private:
156 0 : std::string subfile_path_;
157 : };
158 : } // namespace Events
|