diff --git a/.gitignore b/.gitignore index 170fcf24..9014aaa6 100644 --- a/.gitignore +++ b/.gitignore @@ -7,3 +7,4 @@ tests/data *.code-workspace PolySolveOptions.cmake .vs +src/polysolve/autogen diff --git a/CMakeLists.txt b/CMakeLists.txt index 91826934..77b47733 100755 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -183,6 +183,34 @@ target_compile_definitions(polysolve_linear PRIVATE POLYSOLVE_LINEAR_SPEC="${PRO target_compile_definitions(polysolve PRIVATE POLYSOLVE_NON_LINEAR_SPEC="${PROJECT_SOURCE_DIR}/nonlinear-solver-spec.json") target_compile_definitions(polysolve_linear PUBLIC POLYSOLVE_JSON_SPEC_DIR="${PROJECT_SOURCE_DIR}") +function(embed_resource resource_file_name source_file_name variable_name) + + if(EXISTS "${source_file_name}") + if("${source_file_name}" IS_NEWER_THAN "${resource_file_name}") + return() + endif() + endif() + + file(READ "${resource_file_name}" hex_content HEX) + + string(REPEAT "[0-9a-f]" 32 pattern) + string(REGEX REPLACE "(${pattern})" "\\1\n" content "${hex_content}") + + string(REGEX REPLACE "([0-9a-f][0-9a-f])" "0x\\1, " content "${content}") + + string(REGEX REPLACE ", $" "" content "${content}") + + set(array_definition "static const unsigned char ${variable_name}[] =\n{\n${content}\n};") + + set(source "// Auto generated file.\n${array_definition}\n") + + file(WRITE "${source_file_name}" "${source}") + +endfunction() + +embed_resource("${PROJECT_SOURCE_DIR}/linear-solver-spec.json" "${PROJECT_SOURCE_DIR}/src/polysolve/autogen/linear-solver-spec.cpp" "LINEAR_SOLVER_SPEC") +embed_resource("${PROJECT_SOURCE_DIR}/nonlinear-solver-spec.json" "${PROJECT_SOURCE_DIR}/src/polysolve/autogen/nonlinear-solver-spec.cpp" "NONLINEAR_SOLVER_SPEC") + ################################################################################ # Dependencies diff --git a/src/polysolve/linear/Solver.cpp b/src/polysolve/linear/Solver.cpp index e7c0c259..16ca06ae 100644 --- a/src/polysolve/linear/Solver.cpp +++ b/src/polysolve/linear/Solver.cpp @@ -10,6 +10,8 @@ #include +#include + // ----------------------------------------------------------------------------- // // Subsequent macros assume a single template parameter and SparseQR fails due to requiring 2 parameters. this is because the OrderingType is not filled in. @@ -137,17 +139,10 @@ namespace polysolve::linear { json params = params_in; // mutable copy - json rules; jse::JSE jse; jse.strict = strict_validation; - const std::string input_spec = POLYSOLVE_LINEAR_SPEC; - std::ifstream file(input_spec); - - if (file.is_open()) - file >> rules; - else - log_and_throw_error(logger, "unable to open {} rules", input_spec); + json rules = json::parse(LINEAR_SOLVER_SPEC); apply_default_solver(rules); select_valid_solver(params, logger); diff --git a/src/polysolve/nonlinear/BoxConstraintSolver.cpp b/src/polysolve/nonlinear/BoxConstraintSolver.cpp index 707bb7d7..3cb46c8f 100644 --- a/src/polysolve/nonlinear/BoxConstraintSolver.cpp +++ b/src/polysolve/nonlinear/BoxConstraintSolver.cpp @@ -8,6 +8,8 @@ #include +#include + namespace polysolve::nonlinear { @@ -21,18 +23,10 @@ namespace polysolve::nonlinear { json solver_params = solver_params_in; // mutable copy - json rules; jse::JSE jse; jse.strict = strict_validation; - const std::string input_spec = POLYSOLVE_NON_LINEAR_SPEC; - std::ifstream file(input_spec); - - if (file.is_open()) - file >> rules; - else - log_and_throw_error(logger, "unable to open {} rules", input_spec); - + json rules = json::parse(NONLINEAR_SOLVER_SPEC); const bool valid_input = jse.verify_json(solver_params, rules); if (!valid_input) diff --git a/src/polysolve/nonlinear/Solver.cpp b/src/polysolve/nonlinear/Solver.cpp index 1b98faa1..fc6706be 100644 --- a/src/polysolve/nonlinear/Solver.cpp +++ b/src/polysolve/nonlinear/Solver.cpp @@ -26,6 +26,8 @@ #include #include +#include + namespace polysolve::nonlinear { namespace @@ -121,18 +123,10 @@ namespace polysolve::nonlinear { json solver_params = solver_params_in; // mutable copy - json rules; jse::JSE jse; jse.strict = strict_validation; - const std::string input_spec = POLYSOLVE_NON_LINEAR_SPEC; - std::ifstream file(input_spec); - - if (file.is_open()) - file >> rules; - else - log_and_throw_error(logger, "unable to open {} rules", input_spec); - + json rules = json::parse(NONLINEAR_SOLVER_SPEC); const bool valid_input = jse.verify_json(solver_params, rules); if (!valid_input)