Skip to content

Commit

Permalink
#1 enhance fmu constructor for moi environment
Browse files Browse the repository at this point in the history
  • Loading branch information
prudhomm committed Dec 2, 2023
1 parent ff36203 commit 292ee75
Show file tree
Hide file tree
Showing 4 changed files with 90 additions and 28 deletions.
2 changes: 1 addition & 1 deletion include/fmi4cpp/fmi2/fmu.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ class fmu : public virtual fmu_provider<model_description, cs_fmu, me_fmu>
std::shared_ptr<const fmi4cpp::fmi2::model_description> modelDescription_;

public:
explicit fmu(const fs::path& fmuPath);
explicit fmu(const fs::path& fmuPath, bool unzipFmu = true);

[[nodiscard]] std::string get_model_description_xml() const;
[[nodiscard]] std::shared_ptr<const fmi4cpp::fmi2::model_description> get_model_description() const override;
Expand Down
56 changes: 30 additions & 26 deletions src/fmi4cpp/fmi2/fmu.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -11,34 +11,38 @@
using namespace fmi4cpp;
using namespace fmi4cpp::fmi2;

fmu::fmu(const fs::path& fmuPath)
fmu::fmu(const fs::path& fmuPath, bool unzipFmu)
{

if (!exists(fmuPath)) {
const auto err = "No such file '" + absolute(fmuPath).string() + "'!";
MLOG_FATAL(err);
throw std::runtime_error(err);
}

const std::string fmuName = fmuPath.stem().string();
fs::path tmpPath(fs::temp_directory_path() /= fs::path("fmi4cpp_" + fmuName + "_" + generate_simple_id(8)));

if (!create_directories(tmpPath)) {
const auto err = "Failed to create temporary directory '" + tmpPath.string() + "' !";
MLOG_FATAL(err);
throw std::runtime_error(err);
if (unzipFmu) {
if (!exists(fmuPath)) {
const auto err = "No such file '" + absolute(fmuPath).string() + "'!";
MLOG_FATAL(err);
throw std::runtime_error(err);
}

const std::string fmuName = fmuPath.stem().string();
fs::path tmpPath(fs::temp_directory_path() /= fs::path("fmi4cpp_" + fmuName + "_" + generate_simple_id(8)));

if (!create_directories(tmpPath)) {
const auto err = "Failed to create temporary directory '" + tmpPath.string() + "' !";
MLOG_FATAL(err);
throw std::runtime_error(err);
}

MLOG_DEBUG("Created temporary directory '" << tmpPath.string());

if (!unzip(fmuPath, tmpPath.string())) {
const auto err = "Failed to extract FMU '" + absolute(fmuPath).string() + "'!";
MLOG_FATAL(err);
throw std::runtime_error(err);
}

resource_ = std::make_shared<fmu_resource>(tmpPath);
modelDescription_ = std::move(parse_model_description(resource_->model_description_path()));
} else {
resource_ = std::make_shared<fmu_resource>(fmuPath);
modelDescription_ = std::move(parse_model_description(resource_->model_description_path()));
}

MLOG_DEBUG("Created temporary directory '" << tmpPath.string());

if (!unzip(fmuPath, tmpPath.string())) {
const auto err = "Failed to extract FMU '" + absolute(fmuPath).string() + "'!";
MLOG_FATAL(err);
throw std::runtime_error(err);
}

resource_ = std::make_shared<fmu_resource>(tmpPath);
modelDescription_ = std::move(parse_model_description(resource_->model_description_path()));
}

std::string fmu::get_model_description_xml() const
Expand Down
3 changes: 2 additions & 1 deletion tests/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@

add_executable(test_controlled_temperature test_controlled_temperature.cpp)
target_link_libraries(test_controlled_temperature PRIVATE fmi4cpp::fmi4cpp Catch2::Catch2)
target_link_libraries(test_controlled_temperature PRIVATE fmi4cpp::fmi4cpp Catch2::Catch2 libzip::libzip)
add_test(NAME test_controlled_temperature COMMAND test_controlled_temperature)
target_include_directories(test_controlled_temperature PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/../src)

add_executable(test_model_description1 test_modeldescription1.cpp)
target_link_libraries(test_model_description1 PRIVATE fmi4cpp::fmi4cpp Catch2::Catch2)
Expand Down
57 changes: 57 additions & 0 deletions tests/test_controlled_temperature.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@

#include <fmi4cpp/fmi2/fmi2.hpp>
#include <fmi4cpp/fs_portability.hpp>
#include <fmi4cpp/mlog.hpp>
#include <fmi4cpp/tools/os_util.hpp>
#include <fmi4cpp/tools/simple_id.hpp>
#include <fmi4cpp/tools/unzipper.hpp>

#define CATCH_CONFIG_MAIN
#include <catch2/catch.hpp>
Expand Down Expand Up @@ -37,5 +42,57 @@ TEST_CASE("ControlledTemperature_test1")

CHECK(298.15 == Approx(ref));

CHECK(slave->terminate());
}


TEST_CASE("ControlledTemperature_test2")
{
const std::string fmu_path = "../resources/fmus/2.0/cs/20sim/4.6.4.8004/"
"ControlledTemperature/ControlledTemperature.fmu";
namespace fs = std::filesystem;
if (!fs::exists(fmu_path)) {
const auto err = "No such file '" + fs::absolute(fmu_path).string() + "'!";
MLOG_FATAL(err);
throw std::runtime_error(err);
}

const std::string fmuName = fs::path(fmu_path).stem().string();
fs::path tmpPath(fs::temp_directory_path() /= fs::path("fmi4cpp_" + fmuName + "_" + generate_simple_id(8)));

if (!fs::create_directories(tmpPath)) {
const auto err = "Failed to create temporary directory '" + tmpPath.string() + "' !";
MLOG_FATAL(err);
throw std::runtime_error(err);
}

MLOG_DEBUG("Created temporary directory '" << tmpPath.string());

if (!unzip(fmu_path, tmpPath.string())) {
const auto err = "Failed to extract FMU '" + fs::absolute(fs::path(fmu_path)).string() + "'!";
MLOG_FATAL(err);
throw std::runtime_error(err);
}
auto fmu = fmi2::fmu(tmpPath,false).as_cs_fmu();

size_t numOutputs = 0;
for (const auto& v : *fmu->get_model_description()->model_variables) {
if (v.causality == fmi2::causality::output) {
numOutputs++;
}
}
CHECK(2 == numOutputs);

auto slave = fmu->new_instance();
CHECK(slave->setup_experiment());
CHECK(slave->enter_initialization_mode());
CHECK(slave->exit_initialization_mode());

double ref;
CHECK(slave->step(step_size));
CHECK(slave->read_real(vr, ref));

CHECK(298.15 == Approx(ref));

CHECK(slave->terminate());
}

0 comments on commit 292ee75

Please sign in to comment.