SpECTRE Documentation Coverage Report
Current view: top level - Evolution/Systems/Cce - WorldtubeBufferUpdater.hpp Hit Total Coverage
Commit: 6e1258ccd353220e12442198913007fb6c170b6b Lines: 27 75 36.0 %
Date: 2024-10-23 19:54:13
Legend: Lines: hit not hit

          Line data    Source code
       1           0 : // Distributed under the MIT License.
       2             : // See LICENSE.txt for details.
       3             : 
       4             : #pragma once
       5             : 
       6             : #include <cstddef>
       7             : #include <memory>
       8             : #include <optional>
       9             : #include <string>
      10             : #include <utility>
      11             : 
      12             : #include "DataStructures/ComplexModalVector.hpp"
      13             : #include "DataStructures/DataBox/PrefixHelpers.hpp"
      14             : #include "DataStructures/DataBox/Prefixes.hpp"
      15             : #include "DataStructures/DataBox/Tag.hpp"
      16             : #include "DataStructures/DataBox/TagName.hpp"
      17             : #include "DataStructures/DataVector.hpp"
      18             : #include "DataStructures/Matrix.hpp"
      19             : #include "Evolution/Systems/Cce/Tags.hpp"
      20             : #include "IO/H5/Dat.hpp"
      21             : #include "IO/H5/File.hpp"
      22             : #include "IO/H5/Version.hpp"
      23             : #include "NumericalAlgorithms/SpinWeightedSphericalHarmonics/SwshTags.hpp"
      24             : #include "PointwiseFunctions/GeneralRelativity/Tags.hpp"
      25             : #include "Utilities/ErrorHandling/Assert.hpp"
      26             : #include "Utilities/Gsl.hpp"
      27             : #include "Utilities/Serialization/CharmPupable.hpp"
      28             : #include "Utilities/Serialization/PupStlCpp17.hpp"
      29             : #include "Utilities/TMPL.hpp"
      30             : #include "Utilities/TaggedTuple.hpp"
      31             : 
      32             : namespace Cce {
      33             : namespace Tags {
      34             : namespace detail {
      35             : // tags for use in the buffers for the modal input worldtube data management
      36             : // classes
      37             : using SpatialMetric = gr::Tags::SpatialMetric<ComplexModalVector, 3>;
      38             : using Shift = gr::Tags::Shift<ComplexModalVector, 3>;
      39             : using Lapse = gr::Tags::Lapse<ComplexModalVector>;
      40             : 
      41             : // radial derivative prefix tag to be used with the modal input worldtube data
      42             : template <typename Tag>
      43             : struct Dr : db::SimpleTag, db::PrefixTag {
      44             :   using type = typename Tag::type;
      45             :   using tag = Tag;
      46             : };
      47             : 
      48             : // tag for the string for accessing the quantity associated with `Tag` in
      49             : // worldtube h5 file
      50             : template <typename Tag>
      51             : struct InputDataSet : db::SimpleTag, db::PrefixTag {
      52             :   using type = std::string;
      53             :   using tag = Tag;
      54             : };
      55             : }  // namespace detail
      56             : }  // namespace Tags
      57             : 
      58             : namespace detail {
      59             : // generates the component dataset name in the worldtube file based on the
      60             : // tensor indices requested. For instance, if called with arguments ("/g", 0,1),
      61             : // it returns the dataset name "/gxy".
      62             : template <typename... T>
      63             : std::string dataset_name_for_component(std::string base_name,
      64             :                                        const T... indices) {  // NOLINT
      65             :   const auto add_index = [&base_name](size_t index) {
      66             :     ASSERT(index < 3, "The character-arithmetic index must be less than 3.");
      67             :     base_name += static_cast<char>('x' + index);
      68             :   };
      69             :   EXPAND_PACK_LEFT_TO_RIGHT(add_index(indices));
      70             :   // void cast so that compilers can tell it's used.
      71             :   (void)add_index;
      72             :   return base_name;
      73             : }
      74             : 
      75             : // creates a pair of indices such that the difference is `2 *
      76             : // interpolator_length + pad`, centered around `time`, and bounded by
      77             : // `lower_bound` and `upper_bound`. If it cannot be centered, it gives a span
      78             : // that is appropriately sized and bounded by the supplied bounds. If the bounds
      79             : // are too constraining for the necessary size, it gives a span that is the
      80             : // correct size starting at `lower bound`, but not constrained by `upper_bound`
      81             : std::pair<size_t, size_t> create_span_for_time_value(
      82             :     double time, size_t pad, size_t interpolator_length, size_t lower_bound,
      83             :     size_t upper_bound, const DataVector& time_buffer);
      84             : 
      85             : // retrieves time stamps and lmax the from the specified file.
      86             : void set_time_buffer_and_lmax(gsl::not_null<DataVector*> time_buffer,
      87             :                               size_t& l_max, const h5::Dat& data);
      88             : 
      89             : // retrieves modal data from Bondi or Klein-Gordon worldtube H5 file.
      90             : void update_buffer_with_modal_data(
      91             :     gsl::not_null<ComplexModalVector*> buffer_to_update,
      92             :     const h5::Dat& read_data, size_t computation_l_max, size_t l_max,
      93             :     size_t time_span_start, size_t time_span_end, bool is_real);
      94             : 
      95             : // updates `time_span_start` and `time_span_end` based on the provided `time`,
      96             : // and inserts the cooresponding modal data (for `InputTags`) from worldtube H5
      97             : // file into `buffers`. The function is used by Bondi and Klein-Gordon systems.
      98             : template <typename InputTags>
      99             : double update_buffers_for_time(
     100             :     gsl::not_null<Variables<InputTags>*> buffers,
     101             :     gsl::not_null<size_t*> time_span_start,
     102             :     gsl::not_null<size_t*> time_span_end, double time, size_t computation_l_max,
     103             :     size_t l_max, size_t interpolator_length, size_t buffer_depth,
     104             :     const DataVector& time_buffer,
     105             :     const tuples::tagged_tuple_from_typelist<
     106             :         db::wrap_tags_in<Tags::detail::InputDataSet, InputTags>>& dataset_names,
     107             :     const h5::H5File<h5::AccessType::ReadOnly>& cce_data_file);
     108             : }  // namespace detail
     109             : 
     110             : /// the full set of tensors to be extracted from the worldtube h5 file
     111           1 : using cce_metric_input_tags = tmpl::list<
     112             :     Tags::detail::SpatialMetric, Tags::detail::Dr<Tags::detail::SpatialMetric>,
     113             :     ::Tags::dt<Tags::detail::SpatialMetric>, Tags::detail::Shift,
     114             :     Tags::detail::Dr<Tags::detail::Shift>, ::Tags::dt<Tags::detail::Shift>,
     115             :     Tags::detail::Lapse, Tags::detail::Dr<Tags::detail::Lapse>,
     116             :     ::Tags::dt<Tags::detail::Lapse>>;
     117             : 
     118             : /// the full set of tensors to be extracted from the reduced form of the
     119             : /// worldtube h5 file
     120           1 : using cce_bondi_input_tags =
     121             :     tmpl::list<Spectral::Swsh::Tags::SwshTransform<Tags::BondiBeta>,
     122             :                Spectral::Swsh::Tags::SwshTransform<Tags::BondiU>,
     123             :                Spectral::Swsh::Tags::SwshTransform<Tags::BondiQ>,
     124             :                Spectral::Swsh::Tags::SwshTransform<Tags::BondiW>,
     125             :                Spectral::Swsh::Tags::SwshTransform<Tags::BondiJ>,
     126             :                Spectral::Swsh::Tags::SwshTransform<Tags::Dr<Tags::BondiJ>>,
     127             :                Spectral::Swsh::Tags::SwshTransform<Tags::Du<Tags::BondiJ>>,
     128             :                Spectral::Swsh::Tags::SwshTransform<Tags::BondiR>,
     129             :                Spectral::Swsh::Tags::SwshTransform<Tags::Du<Tags::BondiR>>>;
     130             : 
     131           0 : using klein_gordon_input_tags =
     132             :     tmpl::list<Spectral::Swsh::Tags::SwshTransform<Tags::KleinGordonPsi>,
     133             :                Spectral::Swsh::Tags::SwshTransform<Tags::KleinGordonPi>>;
     134             : 
     135             : /// \cond
     136             : class MetricWorldtubeH5BufferUpdater;
     137             : class BondiWorldtubeH5BufferUpdater;
     138             : class KleinGordonWorldtubeH5BufferUpdater;
     139             : /// \endcond
     140             : 
     141             : /*!
     142             :  *  \brief Abstract base class for utilities that are able to perform the buffer
     143             :  *  updating procedure needed by the `WorldtubeDataManager`.
     144             :  *
     145             :  *  \details The methods that are required to be overridden in the derived
     146             :  * classes are:
     147             :  *  - `WorldtubeBufferUpdater::update_buffers_for_time()`:
     148             :  *  updates the buffers passed by pointer and the `time_span_start` and
     149             :  *  `time_span_end` to be appropriate for the requested `time`,
     150             :  *  `interpolator_length`, and `buffer_depth`.
     151             :  *  - `WorldtubeBufferUpdater::get_clone()`
     152             :  *  clone function to obtain a `std::unique_ptr` of the base
     153             :  *  `WorldtubeBufferUpdater`, needed to pass around the factory-created
     154             :  *  object.
     155             :  *  - `WorldtubeBufferUpdater::time_is_outside_range()`
     156             :  *  the override should return `true` if the `time` could be used in a
     157             :  *  `update_buffers_for_time` call given the data available to the derived
     158             :  *  class, and `false` otherwise
     159             :  *  - `WorldtubeBufferUpdater::get_l_max()`
     160             :  *  The override should return the `l_max` it uses in the
     161             :  *  Goldberg modal data placed in the buffers.
     162             :  *  - `WorldtubeBufferUpdater::get_extraction_radius()`
     163             :  *  The override should return the coordinate radius associated with the modal
     164             :  *  worldtube data that it supplies in the buffer update function. This is
     165             :  *  currently assumed to be a single double, but may be generalized in future
     166             :  *  to be time-dependent.
     167             :  *  - `WorldtubeBufferUpdater::get_time_buffer`
     168             :  *  The override should return the vector of times that it can produce modal
     169             :  *  data at. For instance, if associated with a file input, this will be the
     170             :  *  times at each of the rows of the time-series data.
     171             :  */
     172             : template <typename BufferTags>
     173           1 : class WorldtubeBufferUpdater : public PUP::able {
     174             :  public:
     175           0 :   using creatable_classes =
     176             :       tmpl::list<MetricWorldtubeH5BufferUpdater, BondiWorldtubeH5BufferUpdater,
     177             :                  KleinGordonWorldtubeH5BufferUpdater>;
     178             : 
     179           0 :   WRAPPED_PUPable_abstract(WorldtubeBufferUpdater);  // NOLINT
     180             : 
     181           0 :   virtual double update_buffers_for_time(
     182             :       gsl::not_null<Variables<BufferTags>*> buffers,
     183             :       gsl::not_null<size_t*> time_span_start,
     184             :       gsl::not_null<size_t*> time_span_end, double time,
     185             :       size_t computation_l_max, size_t interpolator_length,
     186             :       size_t buffer_depth) const = 0;
     187             : 
     188           0 :   virtual std::unique_ptr<WorldtubeBufferUpdater> get_clone() const = 0;
     189             : 
     190           0 :   virtual bool time_is_outside_range(double time) const = 0;
     191             : 
     192           0 :   virtual size_t get_l_max() const = 0;
     193             : 
     194           0 :   virtual double get_extraction_radius() const = 0;
     195             : 
     196           0 :   virtual bool has_version_history() const = 0;
     197             : 
     198           0 :   virtual DataVector& get_time_buffer() = 0;
     199             : };
     200             : 
     201             : /// A `WorldtubeBufferUpdater` specialized to the CCE input worldtube  H5 file
     202             : /// produced by SpEC.
     203           1 : class MetricWorldtubeH5BufferUpdater
     204             :     : public WorldtubeBufferUpdater<cce_metric_input_tags> {
     205             :  public:
     206             :   // charm needs the empty constructor
     207           0 :   MetricWorldtubeH5BufferUpdater() = default;
     208             : 
     209             :   /// The constructor takes the filename of the SpEC h5 file that will be used
     210             :   /// for boundary data. The extraction radius can either be passed in directly,
     211             :   /// or if it takes the value `std::nullopt`, then the extraction radius is
     212             :   /// retrieved as an integer in the filename.
     213           1 :   explicit MetricWorldtubeH5BufferUpdater(
     214             :       const std::string& cce_data_filename,
     215             :       std::optional<double> extraction_radius = std::nullopt);
     216             : 
     217           0 :   WRAPPED_PUPable_decl_template(MetricWorldtubeH5BufferUpdater);  // NOLINT
     218             : 
     219           0 :   explicit MetricWorldtubeH5BufferUpdater(CkMigrateMessage* /*unused*/) {}
     220             : 
     221             :   /// update the `buffers`, `time_span_start`, and `time_span_end` with
     222             :   /// time-varies-fastest, Goldberg modal data and the start and end index in
     223             :   /// the member `time_buffer_` covered by the newly updated `buffers`. The
     224             :   /// function returns the next time at which a full update will occur. If
     225             :   /// called again at times earlier than the next full update time, it will
     226             :   /// leave the `buffers` unchanged and again return the next needed time.
     227           1 :   double update_buffers_for_time(
     228             :       gsl::not_null<Variables<cce_metric_input_tags>*> buffers,
     229             :       gsl::not_null<size_t*> time_span_start,
     230             :       gsl::not_null<size_t*> time_span_end, double time,
     231             :       size_t computation_l_max, size_t interpolator_length,
     232             :       size_t buffer_depth) const override;
     233             : 
     234           0 :   std::unique_ptr<WorldtubeBufferUpdater<cce_metric_input_tags>> get_clone()
     235             :       const override;
     236             : 
     237             :   /// The time can only be supported in the buffer update if it is between the
     238             :   /// first and last time of the input file.
     239           1 :   bool time_is_outside_range(double time) const override;
     240             : 
     241             :   /// retrieves the l_max of the input file
     242           1 :   size_t get_l_max() const override { return l_max_; }
     243             : 
     244             :   /// retrieves the extraction radius
     245           1 :   double get_extraction_radius() const override { return extraction_radius_; }
     246             : 
     247             :   /// The time buffer is supplied by non-const reference to allow views to
     248             :   /// easily point into the buffer.
     249             :   ///
     250             :   /// \warning Altering this buffer outside of the constructor of this class
     251             :   /// results in undefined behavior! This should be supplied by const reference
     252             :   /// once there is a convenient method of producing a const view of a vector
     253             :   /// type.
     254           1 :   DataVector& get_time_buffer() override { return time_buffer_; }
     255             : 
     256           0 :   bool has_version_history() const override { return has_version_history_; }
     257             : 
     258             :   /// Serialization for Charm++.
     259           1 :   void pup(PUP::er& p) override;
     260             : 
     261             :  private:
     262           0 :   void update_buffer(gsl::not_null<ComplexModalVector*> buffer_to_update,
     263             :                      const h5::Dat& read_data, size_t computation_l_max,
     264             :                      size_t time_span_start, size_t time_span_end) const;
     265             : 
     266           0 :   bool has_version_history_ = true;
     267           0 :   double extraction_radius_ = std::numeric_limits<double>::signaling_NaN();
     268           0 :   size_t l_max_ = 0;
     269             : 
     270           0 :   h5::H5File<h5::AccessType::ReadOnly> cce_data_file_;
     271           0 :   std::string filename_;
     272             : 
     273             :   tuples::tagged_tuple_from_typelist<
     274             :       db::wrap_tags_in<Tags::detail::InputDataSet, cce_metric_input_tags>>
     275           0 :       dataset_names_;
     276             : 
     277             :   // stores all the times in the input file
     278           0 :   DataVector time_buffer_;
     279             : };
     280             : 
     281             : /// A `WorldtubeBufferUpdater` specialized to the CCE input worldtube H5 file
     282             : /// produced by the reduced SpEC format.
     283           1 : class BondiWorldtubeH5BufferUpdater
     284             :     : public WorldtubeBufferUpdater<cce_bondi_input_tags> {
     285             :  public:
     286             :   // charm needs the empty constructor
     287           0 :   BondiWorldtubeH5BufferUpdater() = default;
     288             : 
     289             :   /// The constructor takes the filename of the SpEC h5 file that will be used
     290             :   /// for boundary data. The extraction radius can either be passed in directly,
     291             :   /// or if it takes the value `std::nullopt`, then the extraction radius is
     292             :   /// retrieved as an integer in the filename.
     293           1 :   explicit BondiWorldtubeH5BufferUpdater(
     294             :       const std::string& cce_data_filename,
     295             :       std::optional<double> extraction_radius = std::nullopt);
     296             : 
     297           0 :   WRAPPED_PUPable_decl_template(BondiWorldtubeH5BufferUpdater);  // NOLINT
     298             : 
     299           0 :   explicit BondiWorldtubeH5BufferUpdater(CkMigrateMessage* /*unused*/) {}
     300             : 
     301             :   /// update the `buffers`, `time_span_start`, and `time_span_end` with
     302             :   /// time-varies-fastest, Goldberg modal data and the start and end index in
     303             :   /// the member `time_buffer_` covered by the newly updated `buffers`.
     304           1 :   double update_buffers_for_time(
     305             :       gsl::not_null<Variables<cce_bondi_input_tags>*> buffers,
     306             :       gsl::not_null<size_t*> time_span_start,
     307             :       gsl::not_null<size_t*> time_span_end, double time,
     308             :       size_t computation_l_max, size_t interpolator_length,
     309             :       size_t buffer_depth) const override;
     310             : 
     311           0 :   std::unique_ptr<WorldtubeBufferUpdater<cce_bondi_input_tags>> get_clone()
     312             :       const override {
     313             :     return std::make_unique<BondiWorldtubeH5BufferUpdater>(filename_);
     314             :   }
     315             : 
     316             :   /// The time can only be supported in the buffer update if it is between the
     317             :   /// first and last time of the input file.
     318           1 :   bool time_is_outside_range(const double time) const override {
     319             :     return time < time_buffer_[0] or
     320             :            time > time_buffer_[time_buffer_.size() - 1];
     321             :   }
     322             : 
     323             :   /// retrieves the l_max of the input file
     324           1 :   size_t get_l_max() const override { return l_max_; }
     325             : 
     326             :   /// retrieves the extraction radius. In most normal circumstances, this will
     327             :   /// not be needed for Bondi data.
     328           1 :   double get_extraction_radius() const override {
     329             :     if (not extraction_radius_.has_value()) {
     330             :       ERROR(
     331             :           "Extraction radius has not been set, and was not successfully parsed "
     332             :           "from the filename. The extraction radius has been used, so must be "
     333             :           "set either by the input file or via the filename.");
     334             :     }
     335             :     return *extraction_radius_;
     336             :   }
     337             : 
     338             :   /// The time buffer is supplied by non-const reference to allow views to
     339             :   /// easily point into the buffer.
     340             :   ///
     341             :   /// \warning Altering this buffer outside of the constructor of this class
     342             :   /// results in undefined behavior! This should be supplied by const reference
     343             :   /// once there is a convenient method of producing a const view of a vector
     344             :   /// type.
     345           1 :   DataVector& get_time_buffer() override { return time_buffer_; }
     346             : 
     347           0 :   bool has_version_history() const override { return true; }
     348             : 
     349             :   /// Serialization for Charm++.
     350           1 :   void pup(PUP::er& p) override;
     351             : 
     352             :  private:
     353           0 :   void update_buffer(gsl::not_null<ComplexModalVector*> buffer_to_update,
     354             :                      const h5::Dat& read_data, size_t computation_l_max,
     355             :                      size_t time_span_start, size_t time_span_end,
     356             :                      bool is_real) const;
     357             : 
     358           0 :   std::optional<double> extraction_radius_ = std::nullopt;
     359           0 :   size_t l_max_ = 0;
     360             : 
     361           0 :   h5::H5File<h5::AccessType::ReadOnly> cce_data_file_;
     362           0 :   std::string filename_;
     363             : 
     364             :   tuples::tagged_tuple_from_typelist<
     365             :       db::wrap_tags_in<Tags::detail::InputDataSet, cce_bondi_input_tags>>
     366           0 :       dataset_names_;
     367             : 
     368             :   // stores all the times in the input file
     369           0 :   DataVector time_buffer_;
     370             : };
     371             : 
     372             : /// A `WorldtubeBufferUpdater` specialized to the Klein-Gordon input worldtube
     373             : /// H5 file produced by the SpEC format. We assume the scalar field is
     374             : /// real-valued.
     375           1 : class KleinGordonWorldtubeH5BufferUpdater
     376             :     : public WorldtubeBufferUpdater<klein_gordon_input_tags> {
     377             :  public:
     378             :   // charm needs the empty constructor
     379           0 :   KleinGordonWorldtubeH5BufferUpdater() = default;
     380             : 
     381             :   /// The constructor takes the filename of the SpEC h5 file that will be used
     382             :   /// for boundary data. The extraction radius can either be passed in directly,
     383             :   /// or if it takes the value `std::nullopt`, then the extraction radius is
     384             :   /// retrieved as an integer in the filename.
     385           1 :   explicit KleinGordonWorldtubeH5BufferUpdater(
     386             :       const std::string& cce_data_filename,
     387             :       std::optional<double> extraction_radius = std::nullopt);
     388             : 
     389           0 :   WRAPPED_PUPable_decl_template(KleinGordonWorldtubeH5BufferUpdater);  // NOLINT
     390             : 
     391           0 :   explicit KleinGordonWorldtubeH5BufferUpdater(CkMigrateMessage* /*unused*/) {}
     392             : 
     393             :   /// update the `buffers`, `time_span_start`, and `time_span_end` with
     394             :   /// time-varies-fastest, Goldberg modal data and the start and end index in
     395             :   /// the member `time_buffer_` covered by the newly updated `buffers`.
     396           1 :   double update_buffers_for_time(
     397             :       gsl::not_null<Variables<klein_gordon_input_tags>*> buffers,
     398             :       gsl::not_null<size_t*> time_span_start,
     399             :       gsl::not_null<size_t*> time_span_end, double time,
     400             :       size_t computation_l_max, size_t interpolator_length,
     401             :       size_t buffer_depth) const override;
     402             : 
     403           0 :   std::unique_ptr<WorldtubeBufferUpdater<klein_gordon_input_tags>> get_clone()
     404             :       const override {
     405             :     return std::make_unique<KleinGordonWorldtubeH5BufferUpdater>(filename_);
     406             :   }
     407             : 
     408             :   /// The time can only be supported in the buffer update if it is between the
     409             :   /// first and last time of the input file.
     410           1 :   bool time_is_outside_range(const double time) const override {
     411             :     return time < time_buffer_[0] or
     412             :            time > time_buffer_[time_buffer_.size() - 1];
     413             :   }
     414             : 
     415             :   /// retrieves the l_max of the input file
     416           1 :   size_t get_l_max() const override { return l_max_; }
     417             : 
     418             :   /// retrieves the extraction radius. In most normal circumstances, this will
     419             :   /// not be needed for Klein-Gordon data.
     420           1 :   double get_extraction_radius() const override {
     421             :     if (not static_cast<bool>(extraction_radius_)) {
     422             :       ERROR(
     423             :           "Extraction radius has not been set, and was not successfully parsed "
     424             :           "from the filename. The extraction radius has been used, so must be "
     425             :           "set either by the input file or via the filename.");
     426             :     }
     427             :     return *extraction_radius_;
     428             :   }
     429             : 
     430             :   /// The time buffer is supplied by non-const reference to allow views to
     431             :   /// easily point into the buffer.
     432             :   ///
     433             :   /// \warning Altering this buffer outside of the constructor of this class
     434             :   /// results in undefined behavior! This should be supplied by const reference
     435             :   /// once there is a convenient method of producing a const view of a vector
     436             :   /// type.
     437           1 :   DataVector& get_time_buffer() override { return time_buffer_; }
     438             : 
     439           0 :   bool has_version_history() const override { return true; }
     440             : 
     441             :   /// Serialization for Charm++.
     442           1 :   void pup(PUP::er& p) override;
     443             : 
     444             :  private:
     445             :   // The scalar field is assumed to be real-valued.
     446           0 :   void update_buffer(gsl::not_null<ComplexModalVector*> buffer_to_update,
     447             :                      const h5::Dat& read_data, size_t computation_l_max,
     448             :                      size_t time_span_start, size_t time_span_end) const;
     449             : 
     450           0 :   std::optional<double> extraction_radius_ = std::nullopt;
     451           0 :   size_t l_max_ = 0;
     452             : 
     453           0 :   h5::H5File<h5::AccessType::ReadOnly> cce_data_file_;
     454           0 :   std::string filename_;
     455             : 
     456             :   tuples::tagged_tuple_from_typelist<
     457             :       db::wrap_tags_in<Tags::detail::InputDataSet, klein_gordon_input_tags>>
     458           0 :       dataset_names_;
     459             : 
     460             :   // stores all the times in the input file
     461           0 :   DataVector time_buffer_;
     462             : };
     463             : }  // namespace Cce

Generated by: LCOV version 1.14