Skip to content
Open
34 changes: 18 additions & 16 deletions include/bout/options_io.hxx
Original file line number Diff line number Diff line change
@@ -1,3 +1,17 @@
#pragma once

#ifndef OPTIONS_IO_H
#define OPTIONS_IO_H

#include "bout/build_defines.hxx"
#include "bout/generic_factory.hxx"
#include "bout/options.hxx"

#include <memory>
#include <string>

namespace bout {

/// Parent class for IO to binary files and streams
///
///
Expand Down Expand Up @@ -29,29 +43,14 @@
/// auto file = OptionsIO::create("some_file.nc");
///
///

#pragma once

#ifndef OPTIONS_IO_H
#define OPTIONS_IO_H

#include "bout/build_config.hxx"
#include "bout/generic_factory.hxx"
#include "bout/options.hxx"

#include <memory>
#include <string>

namespace bout {

class OptionsIO {
public:
/// No default constructor, as settings are required
OptionsIO() = delete;

/// Constructor specifies the kind of file, and options to control
/// the name of file, mode of operation etc.
OptionsIO(Options&) {}
OptionsIO(Options& /*unused*/) {}

virtual ~OptionsIO() = default;

Expand All @@ -73,6 +72,9 @@ public:
/// ADIOS: Indicate completion of an output step.
virtual void verifyTimesteps() const = 0;

/// NetCDF: Flush file to disk
virtual void flush() {}

/// Create an OptionsIO for I/O to the given file.
/// This uses the default file type and default options.
static std::unique_ptr<OptionsIO> create(const std::string& file);
Expand Down
7 changes: 7 additions & 0 deletions include/bout/physicsmodel.hxx
Original file line number Diff line number Diff line change
Expand Up @@ -376,6 +376,9 @@ protected:
PhysicsModel* model;
};

/// Set timestep counter for flushing file
void setFlushCounter(std::size_t iteration) { flush_counter = iteration; }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

warning: no header providing "std::size_t" is directly included [misc-include-cleaner]

include/bout/physicsmodel.hxx:34:

- class PhysicsModel;
+ #include <cstddef>
+ class PhysicsModel;


private:
/// State for outputs
Options output_options;
Expand All @@ -399,6 +402,10 @@ private:
bool initialised{false};
/// write restarts and pass outputMonitor method inside a Monitor subclass
PhysicsModelMonitor modelMonitor{this};
/// How often to flush to disk
std::size_t flush_frequency{1};
/// Current timestep counter
std::size_t flush_counter{0};
};

/*!
Expand Down
24 changes: 17 additions & 7 deletions src/physics/physicsmodel.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -33,12 +33,14 @@
#undef BOUT_NO_USING_NAMESPACE_BOUTGLOBALS

#include <bout/mesh.hxx>
#include <bout/options.hxx>
#include <bout/sys/timer.hxx>
#include <bout/vector2d.hxx>
#include <bout/vector3d.hxx>

#include <fmt/core.h>

#include <cstddef>
#include <string>
using namespace std::literals;

Expand Down Expand Up @@ -66,9 +68,10 @@ PhysicsModel::PhysicsModel()
.withDefault(true)),
restart_enabled(Options::root()["restart_files"]["enabled"]
.doc("Write restart files")
.withDefault(true))

{
.withDefault(true)),
flush_frequency(Options::root()["output"]["flush_frequency"]
.doc("How often to flush to disk")
.withDefault<std::size_t>(1)) {
if (output_enabled) {
output_file = bout::OptionsIOFactory::getInstance().createOutput();
}
Expand Down Expand Up @@ -216,9 +219,7 @@ void PhysicsModel::writeRestartFile() {
void PhysicsModel::writeOutputFile() { writeOutputFile(output_options); }

void PhysicsModel::writeOutputFile(const Options& options) {
if (output_enabled) {
output_file->write(options, "t");
}
writeOutputFile(options, "t");
}

void PhysicsModel::writeOutputFile(const Options& options,
Expand All @@ -229,13 +230,19 @@ void PhysicsModel::writeOutputFile(const Options& options,
}

void PhysicsModel::finishOutputTimestep() const {
if (output_enabled) {
Timer timer("io");

if (output_enabled and (flush_counter % flush_frequency == 0)) {
output_file->flush();
output_file->verifyTimesteps();
}
}

int PhysicsModel::PhysicsModelMonitor::call(Solver* solver, BoutReal simtime,
int iteration, int nout) {

model->setFlushCounter(static_cast<std::size_t>(iteration));

// Restart file variables
solver->outputVars(model->restart_options, false);
model->restartVars(model->restart_options);
Expand All @@ -250,6 +257,9 @@ int PhysicsModel::PhysicsModelMonitor::call(Solver* solver, BoutReal simtime,
model->outputVars(model->output_options);
model->writeOutputFile();

// Reset output options, this avoids rewriting time-independent data
model->output_options = Options{};

// Call user output monitor
return model->outputMonitor(simtime, iteration, nout);
}
3 changes: 1 addition & 2 deletions src/sys/options/options_adios.hxx
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,7 @@
#ifndef OPTIONS_ADIOS_H
#define OPTIONS_ADIOS_H

#include "bout/build_config.hxx"
#include "bout/options.hxx"
#include "bout/build_defines.hxx"
#include "bout/options_io.hxx"

#if !BOUT_HAS_ADIOS2
Expand Down
4 changes: 2 additions & 2 deletions src/sys/options/options_netcdf.cxx
Original file line number Diff line number Diff line change
Expand Up @@ -698,10 +698,10 @@ void OptionsNetCDF::write(const Options& options, const std::string& time_dim) {
}

writeGroup(options, *data_file, time_dim);

data_file->sync();
}

void OptionsNetCDF::flush() { data_file->sync(); }

} // namespace bout

#endif // BOUT_HAS_NETCDF
16 changes: 9 additions & 7 deletions src/sys/options/options_netcdf.hxx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
#ifndef OPTIONS_NETCDF_H
#define OPTIONS_NETCDF_H

#include "bout/build_config.hxx"
#include "bout/build_defines.hxx"

#include "bout/options.hxx"
#include "bout/options_io.hxx"
Expand Down Expand Up @@ -39,24 +39,26 @@ public:
/// - "append" File mode, default is false
OptionsNetCDF(Options& options);

~OptionsNetCDF() {}
~OptionsNetCDF() override = default;

OptionsNetCDF(const OptionsNetCDF&) = delete;
OptionsNetCDF(OptionsNetCDF&&) noexcept = default;
OptionsNetCDF& operator=(const OptionsNetCDF&) = delete;
OptionsNetCDF& operator=(OptionsNetCDF&&) noexcept = default;

/// Read options from file
Options read();
Options read() override;

/// Write options to file
void write(const Options& options) { write(options, "t"); }
void write(const Options& options, const std::string& time_dim);
void write(const Options& options, const std::string& time_dim) override;

/// Check that all variables with the same time dimension have the
/// same size in that dimension. Throws BoutException if there are
/// any differences, otherwise is silent
void verifyTimesteps() const;
void verifyTimesteps() const override;

/// Flush file to disk
void flush() override;

private:
enum class FileMode {
Expand All @@ -74,7 +76,7 @@ private:
};

namespace {
RegisterOptionsIO<OptionsNetCDF> registeroptionsnetcdf("netcdf");
const RegisterOptionsIO<OptionsNetCDF> registeroptionsnetcdf("netcdf");
}

} // namespace bout
Expand Down
Loading