Skip to content
This repository was archived by the owner on Mar 25, 2025. It is now read-only.
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 2 additions & 3 deletions src/codegen/codegen_coreneuron_cpp_visitor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@
#include "config/config.h"
#include "lexer/token_mapping.hpp"
#include "parser/c11_driver.hpp"
#include "solver/solver.hpp"
#include "utils/logger.hpp"
#include "utils/string_utils.hpp"
#include "visitors/defuse_analyze_visitor.hpp"
Expand Down Expand Up @@ -1005,7 +1004,7 @@ void CodegenCoreneuronCppVisitor::print_coreneuron_includes() {
#include <coreneuron/utils/randoms/nrnran123.h>
)CODE");
if (info.eigen_newton_solver_exist) {
printer->add_multi_line(nmodl::solvers::newton_hpp);
printer->add_line("#include \"solver/newton.hpp\"");
}
if (info.eigen_linear_solver_exist) {
if (std::accumulate(info.state_vars.begin(),
Expand All @@ -1014,7 +1013,7 @@ void CodegenCoreneuronCppVisitor::print_coreneuron_includes() {
[](int l, const SymbolType& variable) {
return l += variable->get_length();
}) > 4) {
printer->add_multi_line(nmodl::solvers::crout_hpp);
printer->add_line("#include \"solver/crout.hpp\"");
} else {
printer->add_line("#include <Eigen/Dense>");
printer->add_line("#include <Eigen/LU>");
Expand Down
3 changes: 1 addition & 2 deletions src/codegen/codegen_neuron_cpp_visitor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@
#include "codegen/codegen_utils.hpp"
#include "codegen_naming.hpp"
#include "config/config.h"
#include "solver/solver.hpp"
#include "utils/string_utils.hpp"
#include "visitors/rename_visitor.hpp"
#include "visitors/var_usage_visitor.hpp"
Expand Down Expand Up @@ -754,7 +753,7 @@ void CodegenNeuronCppVisitor::print_standard_includes() {
#include <vector>
)CODE");
if (info.eigen_newton_solver_exist) {
printer->add_multi_line(nmodl::solvers::newton_hpp);
printer->add_line("#include \"solver/newton.hpp\"");
}
}

Expand Down
35 changes: 34 additions & 1 deletion src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,12 @@
* SPDX-License-Identifier: Apache-2.0
*/

#include <filesystem>
#include <fstream>
#include <string>
#include <vector>

#include <CLI/CLI.hpp>
#include <filesystem>

#include "ast/program.hpp"
#include "codegen/codegen_acc_visitor.hpp"
Expand All @@ -20,6 +21,7 @@
#include "config/config.h"
#include "parser/nmodl_driver.hpp"
#include "pybind/pyembed.hpp"
#include "solver/solver.hpp"
#include "utils/common_utils.hpp"
#include "utils/logger.hpp"
#include "visitors/after_cvode_to_cnexp_visitor.hpp"
Expand Down Expand Up @@ -60,6 +62,26 @@ using namespace codegen;
using namespace visitor;
using nmodl::parser::NmodlDriver;

fs::path get_solver_path(const fs::path& directory, const std::string& solver) {
auto path = directory / "solver" / solver;
path += ".hpp";
return path;
}

void write_shared_headers(const std::string& directory,
const std::vector<std::string>& solvers = nmodl::solver::get_names()) {
fs::path output(directory);

for (const auto& solver: solvers) {
const auto& path = get_solver_path(directory, solver);
fs::create_directories(path.parent_path());

std::ofstream fout(path);
fout << nmodl::solver::get_hpp(solver);
logger->info("Generated {}", path.string());
}
}

// NOLINTNEXTLINE(readability-function-cognitive-complexity)
int main(int argc, const char* argv[]) {
CLI::App app{fmt::format("NMODL : Source-to-Source Code Generation Framework [{}]",
Expand Down Expand Up @@ -180,6 +202,17 @@ int main(int argc, const char* argv[]) {
app.add_option("-o,--output", output_dir, "Directory for backend code output")
->capture_default_str()
->ignore_case();

app.add_option_function<std::vector<std::string>>(
"--write-shared-headers",
[&](const std::vector<std::string>& solvers) {
write_shared_headers(output_dir, solvers);
exit(0);
},
"Create solver headers in directory and exit")
->expected(1, 2)
->check(CLI::IsMember(nmodl::solver::get_names()));

app.add_option("--scratch", scratch_dir, "Directory for intermediate code output")
->capture_default_str()
->ignore_case();
Expand Down
12 changes: 4 additions & 8 deletions src/solver/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,15 +1,11 @@
# Read headers, remove everything up to and including "#pragma once", then remove header includes.
file(READ ${CMAKE_CURRENT_SOURCE_DIR}/crout/crout.hpp NMODL_CROUT_HPP_RAW)
string(REGEX REPLACE ".*#pragma once[ \t\r\n]*" "" NMODL_CROUT_HPP "${NMODL_CROUT_HPP_RAW}")
file(READ ${CMAKE_CURRENT_SOURCE_DIR}/newton/newton.hpp NMODL_NEWTON_HPP_RAW)
string(REGEX REPLACE ".*#pragma once[ \t\r\n]*" "" NMODL_NEWTON_HPP_TMP "${NMODL_NEWTON_HPP_RAW}")
string(REGEX REPLACE "#include <crout/crout.hpp>[ \t\r\n]*" "" NMODL_NEWTON_HPP
"${NMODL_NEWTON_HPP_TMP}")
file(READ ${CMAKE_CURRENT_SOURCE_DIR}/crout.hpp NMODL_CROUT_HPP)
file(READ ${CMAKE_CURRENT_SOURCE_DIR}/newton.hpp NMODL_NEWTON_HPP)
set_property(
DIRECTORY
APPEND
PROPERTY CMAKE_CONFIGURE_DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/crout/crout.hpp
${CMAKE_CURRENT_SOURCE_DIR}/newton/newton.hpp)
PROPERTY CMAKE_CONFIGURE_DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/crout.hpp
${CMAKE_CURRENT_SOURCE_DIR}/newton.hpp)
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/solver.hpp.inc ${CMAKE_CURRENT_BINARY_DIR}/solver.hpp)

add_custom_target(nmodl_copy_solver_files ALL DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/solver.hpp")
File renamed without changes.
2 changes: 1 addition & 1 deletion src/solver/newton/newton.hpp → src/solver/newton.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
* \brief Implementation of Newton method for solving system of non-linear equations
*/

#include <crout/crout.hpp>
#include "crout.hpp"

#include <Eigen/Dense>
#include <Eigen/LU>
Expand Down
23 changes: 15 additions & 8 deletions src/solver/solver.hpp.inc
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
#include <string>
#include <vector>

// This file is generated from `crout/crout.hpp` and `newton/newton.hpp`.
//
Expand All @@ -8,13 +9,19 @@
// However, because we want to be able to test the headers separately we can't
// move them here.

namespace nmodl::solvers {
const std::string crout_hpp = R"jiowi(
@NMODL_CROUT_HPP@
)jiowi";
const std::string newton_hpp = R"jiowi(
@NMODL_CROUT_HPP@
@NMODL_NEWTON_HPP@
)jiowi";
namespace nmodl::solver {
const std::vector<std::string> get_names() {
return {"crout", "newton"};
}

const std::string get_hpp(const std::string& solver) {
if (solver == "crout") {
return R"jiowi(@NMODL_CROUT_HPP@)jiowi";
} else if (solver == "newton") {
return R"jiowi(@NMODL_NEWTON_HPP@)jiowi";
} else {
throw std::runtime_error("unknown solver '" + solver + "'");
}
};

}
2 changes: 1 addition & 1 deletion test/unit/crout/crout.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
* SPDX-License-Identifier: Apache-2.0
*/

#include "crout/crout.hpp"
#include "crout.hpp"

#include <catch2/catch_test_macros.hpp>

Expand Down
2 changes: 1 addition & 1 deletion test/unit/newton/newton.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
* SPDX-License-Identifier: Apache-2.0
*/

#include "newton/newton.hpp"
#include "newton.hpp"

#include <catch2/catch_test_macros.hpp>
#include <catch2/matchers/catch_matchers_floating_point.hpp>
Expand Down