openscad-cpp-evaluator 0.13.4__tar.gz → 0.13.7__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/PKG-INFO +1 -1
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/bytecode.hpp +240 -52
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/bytecode_vm.hpp +37 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/pyproject.toml +1 -1
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/builtins.hpp +17 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/extrude.cpp +51 -13
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/roof.cpp +21 -4
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/bytecode_compiler.cpp +153 -18
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/bytecode_vm.cpp +145 -1
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_bytecode_compiler.cpp +260 -11
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/.github/workflows/ci.yml +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/.github/workflows/wheels.yml +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/.gitignore +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/.gitmodules +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/CLAUDE.md +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/LICENSE +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/README.md +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/bindings/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/bindings/module.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/cmake/embed_font.cmake +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/examples/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/examples/eval_perf_benchmark.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/examples/manifold_cache_reuse.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/examples/minimal_debugger.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/.github/workflows/ci.yml +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/.gitignore +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/CLAUDE.md +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/README.md +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/api.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast/ast_node.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast/comments.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast/declarations.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast/expression.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast/module_instantiation.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast/scope_builder.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast/vector_element.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/ast.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/comments.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/position.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/pretty_print.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/scope.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/serialization.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/include/openscad_cpp_parser/source_map.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/api.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/ast/ast_node.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/ast/declarations.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/ast/expression.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/ast/format_utils.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/ast/module_instantiation.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/ast/scope_builder.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/ast/vector_element.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/comment_attach_internal.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/comments.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/grammar/driver.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/grammar/driver.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/grammar/lexer.l +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/grammar/lexer_api.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/grammar/oscad_location.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/grammar/parser.y +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/inline_comment_attach.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/position.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/pretty_print.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/scope.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/serialization/json_io.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/serialization/yaml_io.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/src/source_map.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_assignments.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_ast_generation.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_comments_and_files.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_const_borrow.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_control.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_expressions.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_functions.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_helpers.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_inline_comments.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_lexical.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_modules.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_node_str.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_pretty_print.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_scope.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_serialization.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_smoke.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_source_map.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_use_include.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tests/test_vectors.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tools/cli/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/external/openscad_cpp_parser/tools/cli/main.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/bound_args.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/bytecode_compiler.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/call_args.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/colored_body.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/csg_node.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/css_colors.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/debug_hooks.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/debug_repl.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/dispatch.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/dxf_svg_import.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/eval_context.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/eval_error.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/eval_use.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/evaluator.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/export.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/font_provider.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/function_builtins.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/import_builtin.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/manifold_cache.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/mesh_import.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/osc_range.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/profile.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/scope_trail.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/segments.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/stb_font_provider.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/surface_load.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/text_metrics.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/value.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/include/openscad_cpp_evaluator/zip_stored.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/python/openscad_cpp_evaluator/__init__.py +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/resources/fonts/LICENSE +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/resources/fonts/LiberationSans-Regular.ttf +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/booleans.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/call_args.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/color.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/control.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/function_builtins.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/import.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/modifiers.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/primitives_2d.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/primitives_3d.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/registry.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/segments.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/surface.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/text.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/topology.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/builtins/transforms.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/colored_body.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/csg_generate.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/csg_resolve.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/css_colors.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/debug/debug_repl.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/debug_profile.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/eval_context.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/eval_error.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/eval_use.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/export.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/expr_eval.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/import/dxf_import.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/import/mesh_import.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/import/surface_load.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/import/svg_import.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/manifold_cache.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/stmt_eval.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/text/stb_font_provider.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/text/text_metrics.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/user_calls.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/value.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/src/zip_stored.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_booleans.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_cli.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_control_flow.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_csg_tree.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_debug_hooks.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_dxf_svg_import.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_eval_context.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_export.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_expr_eval.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_extrude_roof.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_function_builtins.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_helpers.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_import_export.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_manifold_cache.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_multi_color_merge.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_primitives.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_profiling.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_python_bindings.py +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_scope_trail.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_scoping.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_surface.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_tail_calls.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_text.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_transforms.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_use.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_value.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_viewport_params.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tests/test_zip_stored.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tools/cli/CMakeLists.txt +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tools/cli/cli_lib.cpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tools/cli/cli_lib.hpp +0 -0
- {openscad_cpp_evaluator-0.13.4 → openscad_cpp_evaluator-0.13.7}/tools/cli/main.cpp +0 -0
|
@@ -261,7 +261,9 @@ enum class Op {
|
|
|
261
261
|
CallModule,
|
|
262
262
|
|
|
263
263
|
// -- Builtin-wrap compilation (closes the "NativeStatement gap" for ----
|
|
264
|
-
// -- translate/rotate/scale/mirror/multmatrix/resize/color
|
|
264
|
+
// -- translate/rotate/scale/mirror/multmatrix/resize/color/#/%/!, ------
|
|
265
|
+
// -- hull/minkowski/render/linear_extrude/rotate_extrude/projection/ ---
|
|
266
|
+
// -- offset/roof) --------------------------------------------------------
|
|
265
267
|
// A builtin-with-children statement that isn't a "call" the way
|
|
266
268
|
// Op::CallModule's target is (no callStack_/profiling participation,
|
|
267
269
|
// no named scope with upvalue semantics -- see CompiledChunk::
|
|
@@ -284,31 +286,41 @@ enum class Op {
|
|
|
284
286
|
// (mirrors Evaluator::buildTreeNode's own ordering exactly -- doing
|
|
285
287
|
// this AFTER would silently drop uncacheable/ManifoldCache taint
|
|
286
288
|
// tracking for a rands() call embedded in the wrapper's own
|
|
287
|
-
// arguments), computes this site's own params
|
|
288
|
-
//
|
|
289
|
-
//
|
|
290
|
-
//
|
|
291
|
-
//
|
|
292
|
-
//
|
|
293
|
-
//
|
|
294
|
-
//
|
|
295
|
-
//
|
|
296
|
-
//
|
|
297
|
-
//
|
|
298
|
-
//
|
|
299
|
-
//
|
|
300
|
-
//
|
|
301
|
-
//
|
|
289
|
+
// arguments), computes this site's own params for every kind except
|
|
290
|
+
// Modifier (empty, no ctx push) and Roof (deferred to Pop -- see
|
|
291
|
+
// BuiltinWrapSite's own doc comment) via that kind's own native
|
|
292
|
+
// compute function (computeTransformParams/computeColorParams/etc.,
|
|
293
|
+
// builtins.hpp) -- always a possibly-$-scoped child EvalContext,
|
|
294
|
+
// pushed onto f.ctxChain unconditionally for every non-Modifier kind
|
|
295
|
+
// (Roof pushes it too, params or not) -- pushes a fresh ev.treeStack_
|
|
296
|
+
// frame, and stashes {params, randsBefore, siteIdx, (Roof only)
|
|
297
|
+
// deferredArgs} onto VmFrame::builtinWrapStack (a real per-frame LIFO
|
|
298
|
+
// stack, not a single slot: Push/PopBuiltinWrap pairs can nest or
|
|
299
|
+
// sequence within one frame's own instruction stream, e.g.
|
|
300
|
+
// `translate(a) translate(b) recur();`). The compiler always emits a
|
|
301
|
+
// plain Op::CheckDebugStatement immediately before this (see
|
|
302
|
+
// emitBuiltinWrap, bytecode_compiler.cpp), mirroring ModularEcho/
|
|
303
|
+
// ModularAssert's own pattern -- NOT skipped the way Op::CallModule's
|
|
304
|
+
// own call site skips one: this is a genuine statement doing real
|
|
305
|
+
// work here, unlike a module call (which transfers control to a
|
|
306
|
+
// declaration whose OWN body statements each get their own check
|
|
307
|
+
// instead).
|
|
302
308
|
PushBuiltinWrap,
|
|
303
309
|
|
|
304
310
|
// Closes the matching Op::PushBuiltinWrap bracket: pops
|
|
305
311
|
// VmFrame::builtinWrapStack's own top entry FIRST (before anything
|
|
306
312
|
// that can itself throw, e.g. Evaluator::setTreeDepthOrThrow below --
|
|
307
313
|
// so the exception-teardown path's own pending count is already
|
|
308
|
-
// correct if THIS throws)
|
|
309
|
-
//
|
|
310
|
-
//
|
|
311
|
-
//
|
|
314
|
+
// correct if THIS throws); for Roof only, computes `pending.params`
|
|
315
|
+
// HERE via computeRoofParams(ev, pending.deferredArgs, ctx) -- the one
|
|
316
|
+
// kind whose params computation has an observable side effect
|
|
317
|
+
// (ev.warn()) that must stay ordered AFTER children, unlike every
|
|
318
|
+
// other kind's params (computed at Push, before children, since
|
|
319
|
+
// nothing else in this group has an order-sensitive side effect); pops
|
|
320
|
+
// the ctx Push made (every kind except Modifier); pops ev.treeStack_
|
|
321
|
+
// to retrieve the children this bracket's own body produced, and
|
|
322
|
+
// builds the tagged CSGNode exactly like Evaluator::buildTreeNode's
|
|
323
|
+
// own post-resolveBody() half does
|
|
312
324
|
// (kind/node/isBuiltin=true/children/params/uncacheable/
|
|
313
325
|
// setTreeDepthOrThrow), pushing it onto the new top of treeStack_. a
|
|
314
326
|
// = index into CompiledChunk::builtinWrapSites (same site Push used).
|
|
@@ -325,6 +337,112 @@ enum class Op {
|
|
|
325
337
|
// same seam, now a counter).
|
|
326
338
|
PopBuiltinWrap,
|
|
327
339
|
|
|
340
|
+
// -- CSG-wrap compilation (closes the LAST native-reentry source in ----
|
|
341
|
+
// -- the original NativeStatement gap: union()/difference()/ -
|
|
342
|
+
// -- intersection()/intersection_for) -----------------------------------
|
|
343
|
+
// union()/difference()/intersection() weren't covered by the original
|
|
344
|
+
// Op::PushBuiltinWrap (see that op's own doc comment) because they need
|
|
345
|
+
// bespoke bookkeeping PushBuiltinWrap's single all-children bracket
|
|
346
|
+
// doesn't do: Evaluator's own resolveCsg (booleans.cpp) evaluates each
|
|
347
|
+
// TOP-LEVEL child statement of the block SEPARATELY and records how
|
|
348
|
+
// many CSGNodes it individually contributed ("group_sizes") -- e.g.
|
|
349
|
+
// `difference(){ A; B; C; }` = A - (B u C), preserving A's own group
|
|
350
|
+
// even when A itself expands to more than one body (an attachable()-
|
|
351
|
+
// style call returning parent+children as one operand). A flat
|
|
352
|
+
// all-children bracket the way Transform/Color/Modifier use would lose
|
|
353
|
+
// that grouping entirely. This op pair (PushCsgWrap/PopCsgWrap) plus
|
|
354
|
+
// Op::CsgGroupStart/CsgGroupEnd (below) replicate resolveCsg's exact
|
|
355
|
+
// two-pass shape (all assignments first, THEN one evalChildren-per-
|
|
356
|
+
// geometry-statement) as inline compiled bytecode instead, exactly as
|
|
357
|
+
// PushBuiltinWrap already did for translate/rotate/scale/mirror/
|
|
358
|
+
// multmatrix/resize/color/#/%/! -- same rationale (a recursive
|
|
359
|
+
// union()/difference()/intersection()-wrapped module chain was still a
|
|
360
|
+
// real Windows native-reentry depth risk, just never independently
|
|
361
|
+
// fixed when PushBuiltinWrap's own set was).
|
|
362
|
+
//
|
|
363
|
+
// a = index into CompiledChunk::csgWrapSites. Runtime handler: captures
|
|
364
|
+
// ev.randsCallCount() BEFORE argument resolution (same rands-in-args
|
|
365
|
+
// taint reasoning as PushBuiltinWrap); for a `hasArgs` site (union/
|
|
366
|
+
// difference/intersection) resolves the (rare, $-only) arguments via
|
|
367
|
+
// resolveCallArgs exactly like resolveCsg itself does (discarding the
|
|
368
|
+
// positional/named result -- these take no real parameters -- keeping
|
|
369
|
+
// only the possibly-$-scoped child ctx) and pushes that ctx onto
|
|
370
|
+
// f.ctxChain unconditionally (mirrors Transform/Color's own
|
|
371
|
+
// unconditional push -- a bare `union() {...}` with no `$fn=...`
|
|
372
|
+
// override still pushes a ctx that's merely a copy, cheap and uniform
|
|
373
|
+
// rather than a special-cased branch); intersection_for (`hasArgs`
|
|
374
|
+
// false -- it isn't a call, has no `.arguments`) skips both entirely,
|
|
375
|
+
// matching resolveIntersectionFor's own use of its caller's ctx
|
|
376
|
+
// unchanged (its per-ITERATION child ctxs are a completely separate
|
|
377
|
+
// concern, handled by the compiled cartesian loop's own Op::
|
|
378
|
+
// ForIterNext, not by this bracket). Either way: pushes a fresh
|
|
379
|
+
// ev.treeStack_ frame (every child statement's/iteration's own
|
|
380
|
+
// CSGNode(s) land flat in this ONE frame -- mirrors Evaluator::
|
|
381
|
+
// buildTreeNode/evalModularCall's own single treeStack_.emplace_back()
|
|
382
|
+
// around the whole call, not one per group), and stashes {op,
|
|
383
|
+
// randsBefore, siteIdx, empty groupSizes} onto VmFrame::csgWrapStack (a
|
|
384
|
+
// real per-frame LIFO, same reasoning as builtinWrapStack: nested/
|
|
385
|
+
// sequenced CSG wraps within one frame's own instruction stream, e.g.
|
|
386
|
+
// `union() { difference() {...} }`). The compiler always emits a plain
|
|
387
|
+
// Op::CheckDebugStatement immediately before this (see emitCsgWrap/
|
|
388
|
+
// compileIntersectionForLoop, bytecode_compiler.cpp), mirroring
|
|
389
|
+
// emitBuiltinWrap's own pattern -- this is a genuine statement doing
|
|
390
|
+
// real work here, not a call transferring control to a declaration.
|
|
391
|
+
PushCsgWrap,
|
|
392
|
+
|
|
393
|
+
// Opens one "group" within an already-open Op::PushCsgWrap bracket --
|
|
394
|
+
// emitted immediately before each top-level GEOMETRY child statement's
|
|
395
|
+
// own inline-compiled bytecode (compileStatementList of exactly that
|
|
396
|
+
// one statement). Records ev.treeStack_.back().size() into
|
|
397
|
+
// csgWrapStack.back().groupStartSize -- always operates on the
|
|
398
|
+
// TOPMOST (innermost still-open) csgWrapStack entry, matching
|
|
399
|
+
// PopBuiltinWrap's own back()-is-always-mine LIFO discipline, so no
|
|
400
|
+
// operand is needed. Assignments among the block's children are
|
|
401
|
+
// compiled separately, BEFORE any CsgGroupStart/End pair at all (see
|
|
402
|
+
// emitCsgWrap) -- mirrors resolveCsg's own two-pass split exactly
|
|
403
|
+
// (Evaluator::evalChildren(assignNodes, effCtx) always runs to
|
|
404
|
+
// completion before the per-geoNode loop starts).
|
|
405
|
+
CsgGroupStart,
|
|
406
|
+
|
|
407
|
+
// Closes the matching Op::CsgGroupStart: computes
|
|
408
|
+
// ev.treeStack_.back().size() - csgWrapStack.back().groupStartSize
|
|
409
|
+
// (how many CSGNodes THIS one top-level statement just contributed,
|
|
410
|
+
// however many that turned out to be -- 0 for a statement whose own
|
|
411
|
+
// evaluation spliced nothing, e.g. a no-op unknown-module warning; >1
|
|
412
|
+
// for an attachable()-style multi-body operand) and appends it, as a
|
|
413
|
+
// Value, onto csgWrapStack.back().groupSizes -- exactly one entry per
|
|
414
|
+
// top-level geometry statement, in source order, mirroring resolveCsg's
|
|
415
|
+
// own `groupSizes.push_back(Value{...})` loop.
|
|
416
|
+
CsgGroupEnd,
|
|
417
|
+
|
|
418
|
+
// Closes the matching Op::PushCsgWrap bracket: pops
|
|
419
|
+
// VmFrame::csgWrapStack's own top entry FIRST (before anything that can
|
|
420
|
+
// itself throw, e.g. setTreeDepthOrThrow below -- same "exception-
|
|
421
|
+
// teardown's own pending count must already be right" reasoning as
|
|
422
|
+
// PopBuiltinWrap), pops the ctx Push pushed (only when `hasArgs`),
|
|
423
|
+
// pops ev.treeStack_ to retrieve every group's own CSGNode(s) (flat,
|
|
424
|
+
// exactly like resolveCsg's own `children` result -- group boundaries
|
|
425
|
+
// live only in group_sizes, never in the CSGNode list's own shape), and
|
|
426
|
+
// builds the tagged CSGNode exactly like Evaluator::buildTreeNode's own
|
|
427
|
+
// post-resolveBody() half does, with params = {"group_sizes":
|
|
428
|
+
// ValueList(pending.groupSizes)} plus, only when `includeOpParam`,
|
|
429
|
+
// "op": site.op -- byte-for-byte what native resolveCsg returns for
|
|
430
|
+
// union/difference/intersection (generateCsg needs "op" to
|
|
431
|
+
// disambiguate the ONE function it shares across all 3) and what
|
|
432
|
+
// native resolveIntersectionFor returns (no "op" key at all --
|
|
433
|
+
// generateIntersectionFor is its own dedicated, separately-registered
|
|
434
|
+
// function, never needs one) -- pushing the result onto the new top of
|
|
435
|
+
// treeStack_. a = index into CompiledChunk::csgWrapSites (same site
|
|
436
|
+
// Push used).
|
|
437
|
+
//
|
|
438
|
+
// teardownVmCallStackDownTo's own exception path (bytecode_vm.cpp) pops
|
|
439
|
+
// frame->csgWrapStack.size() additional treeStack_ entries per
|
|
440
|
+
// torn-down frame, alongside its existing builtinWrapStack/
|
|
441
|
+
// ownsModuleSplice accounting -- same reasoning as PopBuiltinWrap's own
|
|
442
|
+
// doc comment: an exception can leave N of these brackets open in one
|
|
443
|
+
// frame.
|
|
444
|
+
PopCsgWrap,
|
|
445
|
+
|
|
328
446
|
// A `children()` / `children(N)` statement -- the runtime-varying
|
|
329
447
|
// sibling of Op::CallModule/Op::PushBuiltinWrap, closing the LAST
|
|
330
448
|
// dominant native-reentry source (BOSL2's attachable() calls
|
|
@@ -367,38 +485,58 @@ enum class Op {
|
|
|
367
485
|
// no separate site table needed).
|
|
368
486
|
CallChildren,
|
|
369
487
|
|
|
370
|
-
// A single "native passthrough" statement --
|
|
371
|
-
//
|
|
372
|
-
//
|
|
373
|
-
//
|
|
374
|
-
//
|
|
375
|
-
//
|
|
376
|
-
//
|
|
377
|
-
//
|
|
378
|
-
//
|
|
379
|
-
//
|
|
380
|
-
//
|
|
381
|
-
//
|
|
382
|
-
//
|
|
383
|
-
//
|
|
384
|
-
//
|
|
385
|
-
//
|
|
386
|
-
//
|
|
387
|
-
//
|
|
388
|
-
//
|
|
389
|
-
//
|
|
390
|
-
//
|
|
391
|
-
//
|
|
488
|
+
// A single "native passthrough" statement -- every builtin module call
|
|
489
|
+
// not covered by Op::PushBuiltinWrap/Op::PushCsgWrap (see those ops'
|
|
490
|
+
// own doc comments for exactly which builtins ARE covered -- cube/
|
|
491
|
+
// sphere/import/text/surface/etc., the true LEAVES that never take a
|
|
492
|
+
// `children` block at all, so wrapping a recursive call inside one
|
|
493
|
+
// isn't even syntactically possible), the `*` modifier's own no-op
|
|
494
|
+
// case, or a user-module call that didn't resolve at compile time
|
|
495
|
+
// (shadowed, forward-declared, or otherwise not statically known) --
|
|
496
|
+
// anything compileStatementList doesn't give its own real bytecode.
|
|
497
|
+
// (Assignment/ModularEcho/ModularAssert/ModularLet used to fall here
|
|
498
|
+
// too; they now have their own real bytecode -- Op::StoreModuleVar/
|
|
499
|
+
// Op::Echo/Op::AssertStatement/Op::OpenLetScope+StoreLetVar -- purely
|
|
500
|
+
// a throughput change, since none of these were ever the recursion-
|
|
501
|
+
// depth risk this compiler targets. `#`/`%`/`!` modifiers and
|
|
502
|
+
// translate/rotate/scale/mirror/multmatrix/resize/color used to fall
|
|
503
|
+
// here too, for the SAME throughput reasoning -- WRONG in that one
|
|
504
|
+
// specific case: a recursive module call wrapped in one of these is
|
|
505
|
+
// exactly the pattern that made this op's own native reentry a
|
|
506
|
+
// genuine Windows crash risk in practice, not just a missed
|
|
507
|
+
// optimization. See Op::PushBuiltinWrap's own doc comment for the
|
|
508
|
+
// real story and the fix. children() fell here too, and was the LAST
|
|
509
|
+
// and largest such reentry source once PushBuiltinWrap's own set was
|
|
510
|
+
// covered -- it now has Op::CallChildren, above. union()/difference()/
|
|
511
|
+
// intersection() fell here too, and were the last remaining REAL
|
|
512
|
+
// native-reentry risk among ModularCall-shaped statements (bespoke
|
|
513
|
+
// group_sizes bookkeeping meant they couldn't just reuse
|
|
514
|
+
// PushBuiltinWrap's own bracket) -- they now have Op::PushCsgWrap,
|
|
515
|
+
// above. hull()/minkowski()/render()/linear_extrude()/rotate_extrude()/
|
|
516
|
+
// projection()/offset()/roof() fell here too, closing out every
|
|
517
|
+
// remaining non-leaf builtin whose OWN children can wrap a recursive
|
|
518
|
+
// call in an idiomatic script (a rounded-hull chain, a recursive
|
|
519
|
+
// extrude, etc.) -- they now share Op::PushBuiltinWrap's own bracket
|
|
520
|
+
// via 6 new Kind values (Passthrough/LinearExtrude/RotateExtrude/
|
|
521
|
+
// Projection/Offset/Roof), reusing the exact same mechanism rather
|
|
522
|
+
// than inventing another. intersection_for -- NOT a ModularCall at
|
|
523
|
+
// all, its own NodeKind -- fell here too and was the true LAST
|
|
524
|
+
// native-reentry gap; it now shares Op::PushCsgWrap's own bracket
|
|
525
|
+
// (CsgWrapSite::hasArgs/includeOpParam both false for it) wrapped
|
|
526
|
+
// around a compiled cartesian-product loop reusing Op::ForIterNext/
|
|
527
|
+
// ForIterEnd/NativeIterMaterialize verbatim (see
|
|
528
|
+
// compileIntersectionForLoop, bytecode_compiler.cpp) -- one Op::
|
|
529
|
+
// CsgGroupStart/CsgGroupEnd pair per full iteration instead of per
|
|
530
|
+
// source statement. Every non-leaf builtin construct is covered now.)
|
|
392
531
|
// a = index into CompiledChunk::nativeStatements. Runtime just does
|
|
393
532
|
// what Evaluator::evalChildren's own per-statement loop already does
|
|
394
533
|
// for one node: derive childCtx via ctx.withScope(...), checkDebug,
|
|
395
534
|
// evalStatement. These are still "leaf-shaped" for what's left here
|
|
396
|
-
//
|
|
397
|
-
// recursion safety for a recursive module
|
|
398
|
-
// CallModule/PushBuiltinWrap/
|
|
399
|
-
// flow, not by how many of
|
|
400
|
-
//
|
|
401
|
-
// (translate()-wrapped recursion) has its own real bytecode instead.
|
|
535
|
+
// now that Op::PushBuiltinWrap/Op::PushCsgWrap have peeled off every
|
|
536
|
+
// proven-risky construct: real recursion safety for a recursive module
|
|
537
|
+
// chain is covered by CallModule/PushBuiltinWrap/PushCsgWrap/
|
|
538
|
+
// ForIterNext/the Jump-based if/for control flow, not by how many of
|
|
539
|
+
// THESE sit alongside them in the same body.
|
|
402
540
|
NativeStatement,
|
|
403
541
|
|
|
404
542
|
// If/if-else's own condition, evaluated NATIVELY (Evaluator::
|
|
@@ -714,8 +852,8 @@ struct CompiledChunk {
|
|
|
714
852
|
// replay the native param-resolution step and rebuild the tagged
|
|
715
853
|
// CSGNode at Pop time.
|
|
716
854
|
//
|
|
717
|
-
// `node`'s concrete type depends on `kind`:
|
|
718
|
-
// genuine `ModularCall`
|
|
855
|
+
// `node`'s concrete type depends on `kind`: every kind except Modifier
|
|
856
|
+
// is a genuine `ModularCall` (down-cast to read `.name`/`.arguments`/
|
|
719
857
|
// `.children`); Modifier sites are the wrapper node itself
|
|
720
858
|
// (`ModularModifierHighlight`/`Background`/`ShowOnly` -- `!`/`#`/`%`;
|
|
721
859
|
// `*`/Disable never reaches here, its child never evaluates at all,
|
|
@@ -727,10 +865,59 @@ struct CompiledChunk {
|
|
|
727
865
|
// union of concrete pointers) because that's all Op::PopBuiltinWrap
|
|
728
866
|
// itself ever needs `node` for: the resulting CSGNode's own
|
|
729
867
|
// `node`/error-position field.
|
|
868
|
+
//
|
|
869
|
+
// Passthrough/LinearExtrude/RotateExtrude/Projection/Offset/Roof
|
|
870
|
+
// (added for hull()/minkowski()/render()/linear_extrude()/
|
|
871
|
+
// rotate_extrude()/projection()/offset()/roof()) share Transform/
|
|
872
|
+
// Color's exact push-time-computed-params shape, just via a different
|
|
873
|
+
// native compute function each (Op::PushBuiltinWrap's own runtime
|
|
874
|
+
// handler switches on `kind` to pick it) -- see that op's own doc
|
|
875
|
+
// comment for the one exception (Roof, whose params computation has
|
|
876
|
+
// to run at POP time instead, after children, to preserve an
|
|
877
|
+
// observable warn() ordering).
|
|
730
878
|
struct BuiltinWrapSite {
|
|
731
|
-
enum class Kind {
|
|
879
|
+
enum class Kind {
|
|
880
|
+
Transform,
|
|
881
|
+
Color,
|
|
882
|
+
Modifier,
|
|
883
|
+
Passthrough, // hull()/minkowski()/render() -- empty params, no compute function needed
|
|
884
|
+
LinearExtrude,
|
|
885
|
+
RotateExtrude,
|
|
886
|
+
Projection,
|
|
887
|
+
Offset,
|
|
888
|
+
Roof, // computed at POP time, not PUSH -- see this struct's own doc comment
|
|
889
|
+
};
|
|
732
890
|
Kind kind;
|
|
733
|
-
std::string tagName; // "translate"/"rotate"/.../"color"/"highlight"/"background"/"show_only"
|
|
891
|
+
std::string tagName; // "translate"/"rotate"/.../"color"/"highlight"/"background"/"show_only"/"hull"/...
|
|
892
|
+
const oscad::ASTNode* node = nullptr;
|
|
893
|
+
};
|
|
894
|
+
|
|
895
|
+
// One Op::PushCsgWrap/PopCsgWrap site pair -- see those ops' own doc
|
|
896
|
+
// comments for the full "why union/difference/intersection need
|
|
897
|
+
// bespoke group_sizes bookkeeping instead of just reusing
|
|
898
|
+
// BuiltinWrapSite" rationale. `op` is "union"/"difference"/
|
|
899
|
+
// "intersection" (the 3 names resolveDispatch() maps to resolveCsg,
|
|
900
|
+
// always a genuine ModularCall) OR "intersection_for" (NOT a
|
|
901
|
+
// ModularCall -- a distinct NodeKind/ModuleInstantiation subtype with
|
|
902
|
+
// its own `.assignments`/`.body`, see compileIntersectionForLoop,
|
|
903
|
+
// bytecode_compiler.cpp) -- `node` is therefore the generic ASTNode*
|
|
904
|
+
// BuiltinWrapSite's own Modifier kind already established this pattern
|
|
905
|
+
// for, down-cast to ModularCall only when `hasArgs` is true.
|
|
906
|
+
//
|
|
907
|
+
// `hasArgs`/`includeOpParam` are both true for union/difference/
|
|
908
|
+
// intersection, both false for intersection_for: it isn't a call at
|
|
909
|
+
// all (no `.arguments`, so Op::PushCsgWrap's handler must skip
|
|
910
|
+
// resolveCallArgs/the ctx push entirely -- matches native
|
|
911
|
+
// resolveIntersectionFor, which uses the SAME ctx its caller passed in
|
|
912
|
+
// unchanged, never a $-scoped child of its own), and its own
|
|
913
|
+
// CSGParams has no "op" key at all (generateIntersectionFor is a
|
|
914
|
+
// dedicated, separately-registered generate function, unlike
|
|
915
|
+
// generateCsg which needs "op" in params to disambiguate union/
|
|
916
|
+
// difference/intersection from ONE shared function).
|
|
917
|
+
struct CsgWrapSite {
|
|
918
|
+
std::string op;
|
|
919
|
+
bool hasArgs = true;
|
|
920
|
+
bool includeOpParam = true;
|
|
734
921
|
const oscad::ASTNode* node = nullptr;
|
|
735
922
|
};
|
|
736
923
|
|
|
@@ -796,6 +983,7 @@ struct CompiledChunk {
|
|
|
796
983
|
// own doc comments, above) -- always empty for a function chunk.
|
|
797
984
|
std::vector<ModuleCallSite> moduleCallSites;
|
|
798
985
|
std::vector<BuiltinWrapSite> builtinWrapSites;
|
|
986
|
+
std::vector<CsgWrapSite> csgWrapSites;
|
|
799
987
|
std::vector<AssertSite> assertSites;
|
|
800
988
|
std::vector<const oscad::Expression*> nativeExprs;
|
|
801
989
|
std::vector<const oscad::ASTNode*> nativeStatements;
|
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
#include "openscad_cpp_evaluator/bound_args.hpp"
|
|
4
4
|
#include "openscad_cpp_evaluator/bytecode.hpp"
|
|
5
|
+
#include "openscad_cpp_evaluator/call_args.hpp"
|
|
5
6
|
#include "openscad_cpp_evaluator/csg_node.hpp"
|
|
6
7
|
#include "openscad_cpp_evaluator/eval_context.hpp"
|
|
7
8
|
#include "openscad_cpp_evaluator/value.hpp"
|
|
@@ -28,6 +29,33 @@ struct PendingBuiltinWrap {
|
|
|
28
29
|
CSGParams params;
|
|
29
30
|
std::uint64_t randsBefore = 0;
|
|
30
31
|
int siteIdx = -1;
|
|
32
|
+
// Only populated for BuiltinWrapSite::Kind::Roof -- the already-
|
|
33
|
+
// resolved call arguments, retained across the whole bracket so
|
|
34
|
+
// Op::PopBuiltinWrap's handler can compute roof()'s own params AFTER
|
|
35
|
+
// children finish (computeRoofParams needs them; re-running
|
|
36
|
+
// resolveCallArgs at Pop time instead would re-evaluate every argument
|
|
37
|
+
// expression a second time -- double rands()/side effects). Every
|
|
38
|
+
// other kind computes its params at Push time and leaves this default-
|
|
39
|
+
// empty.
|
|
40
|
+
CallArgs deferredArgs;
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
// One still-open Op::PushCsgWrap bracket's own state -- see that op's own
|
|
44
|
+
// doc comment (bytecode.hpp) for the full contract. `groupSizes` is built
|
|
45
|
+
// up incrementally, one entry per Op::CsgGroupStart/CsgGroupEnd pair (one
|
|
46
|
+
// per top-level GEOMETRY child statement); `groupStartSize` is scratch
|
|
47
|
+
// space for the CURRENTLY OPEN group only (set by CsgGroupStart, consumed
|
|
48
|
+
// by the matching CsgGroupEnd) -- safe as a single scalar, not a stack of
|
|
49
|
+
// its own, because groups within one CSG wrap are siblings in sequence,
|
|
50
|
+
// never nested (unlike PushCsgWrap brackets themselves, which CAN nest,
|
|
51
|
+
// e.g. `union() { difference() {...} }` -- that's what makes
|
|
52
|
+
// VmFrame::csgWrapStack itself a real LIFO, below).
|
|
53
|
+
struct PendingCsgWrap {
|
|
54
|
+
std::string op;
|
|
55
|
+
std::uint64_t randsBefore = 0;
|
|
56
|
+
int siteIdx = -1;
|
|
57
|
+
std::vector<Value> groupSizes;
|
|
58
|
+
size_t groupStartSize = 0;
|
|
31
59
|
};
|
|
32
60
|
|
|
33
61
|
// One ListCompFor/statement-for assignment's own materialized iteration
|
|
@@ -127,6 +155,15 @@ struct VmFrame {
|
|
|
127
155
|
// existing invariant ("whoever pops this frame drains its own open
|
|
128
156
|
// brackets first") already covers it.
|
|
129
157
|
std::vector<PendingBuiltinWrap> builtinWrapStack;
|
|
158
|
+
// Op::PushCsgWrap's own per-frame LIFO -- same role/lifetime/teardown
|
|
159
|
+
// discipline as builtinWrapStack, just for union()/difference()/
|
|
160
|
+
// intersection() (see PendingCsgWrap's own doc comment, above, and
|
|
161
|
+
// Op::PushCsgWrap's, bytecode.hpp). Not explicitly cleared in
|
|
162
|
+
// releaseVmFrame, same as builtinWrapStack/accumStack/ctxChain -- the
|
|
163
|
+
// existing invariant ("whoever pops this frame drains its own open
|
|
164
|
+
// brackets first", normally via matched Push/Pop, or via
|
|
165
|
+
// teardownVmCallStackDownTo on the exception path) already covers it.
|
|
166
|
+
std::vector<PendingCsgWrap> csgWrapStack;
|
|
130
167
|
// The ORIGINAL callee name at push time, used by
|
|
131
168
|
// Evaluator::exitUserCallSuccess's own returnHook call when this frame
|
|
132
169
|
// carries a bracket -- deliberately NOT updated by a later tail hop
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
#pragma once
|
|
2
2
|
|
|
3
|
+
#include "openscad_cpp_evaluator/call_args.hpp"
|
|
3
4
|
#include "openscad_cpp_evaluator/dispatch.hpp"
|
|
4
5
|
|
|
5
6
|
#include <optional>
|
|
@@ -153,21 +154,30 @@ std::vector<ColoredBody> generateMinkowski(Evaluator& ev, const CSGParams& param
|
|
|
153
154
|
const oscad::ASTNode& node);
|
|
154
155
|
|
|
155
156
|
// linear_extrude()/rotate_extrude()/projection() -- extrude.cpp.
|
|
157
|
+
// computeXParams: the pure "resolve args, build params" half, split out
|
|
158
|
+
// like computeTransformParams/computeColorParams so Op::PushBuiltinWrap's
|
|
159
|
+
// own runtime handler can call it directly (bytecode_vm.cpp) instead of
|
|
160
|
+
// through the whole resolve function, whose OTHER half (evalChildren) is
|
|
161
|
+
// exactly the native reentry that split exists to avoid.
|
|
162
|
+
BuiltinWrapParams computeLinearExtrudeParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
156
163
|
CSGParams resolveLinearExtrude(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
157
164
|
std::vector<ColoredBody> generateLinearExtrude(Evaluator& ev, const CSGParams& params,
|
|
158
165
|
const std::vector<std::unique_ptr<CSGNode>>& children,
|
|
159
166
|
const oscad::ASTNode& node);
|
|
160
167
|
|
|
168
|
+
BuiltinWrapParams computeRotateExtrudeParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
161
169
|
CSGParams resolveRotateExtrude(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
162
170
|
std::vector<ColoredBody> generateRotateExtrude(Evaluator& ev, const CSGParams& params,
|
|
163
171
|
const std::vector<std::unique_ptr<CSGNode>>& children,
|
|
164
172
|
const oscad::ASTNode& node);
|
|
165
173
|
|
|
174
|
+
BuiltinWrapParams computeProjectionParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
166
175
|
CSGParams resolveProjection(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
167
176
|
std::vector<ColoredBody> generateProjection(Evaluator& ev, const CSGParams& params,
|
|
168
177
|
const std::vector<std::unique_ptr<CSGNode>>& children,
|
|
169
178
|
const oscad::ASTNode& node);
|
|
170
179
|
|
|
180
|
+
BuiltinWrapParams computeOffsetParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
171
181
|
CSGParams resolveOffset(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
172
182
|
std::vector<ColoredBody> generateOffset(Evaluator& ev, const CSGParams& params,
|
|
173
183
|
const std::vector<std::unique_ptr<CSGNode>>& children, const oscad::ASTNode& node);
|
|
@@ -176,6 +186,13 @@ std::vector<ColoredBody> generateOffset(Evaluator& ev, const CSGParams& params,
|
|
|
176
186
|
// contour polygons) + Tier 3 (SDF/level-set fallback) only, per the plan --
|
|
177
187
|
// Tier 2 (general multi-contour/hole straight skeleton) is a named,
|
|
178
188
|
// documented follow-up, not silently dropped (see CLAUDE.md).
|
|
189
|
+
// computeRoofParams: UNLIKE computeLinearExtrudeParams and friends above,
|
|
190
|
+
// this is the params-computation half taken from AFTER evalChildren (it
|
|
191
|
+
// calls ev.warn(), an observable side effect that must stay ordered after
|
|
192
|
+
// any child's own echo/warn output) -- takes already-resolved CallArgs,
|
|
193
|
+
// not a raw node+ctx, since Op::PushBuiltinWrap's own runtime handler
|
|
194
|
+
// calls this at POP time. See its own doc comment (roof.cpp).
|
|
195
|
+
CSGParams computeRoofParams(Evaluator& ev, const CallArgs& args, EvalContext& effCtx);
|
|
179
196
|
CSGParams resolveRoof(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx);
|
|
180
197
|
std::vector<ColoredBody> generateRoof(Evaluator& ev, const CSGParams& params,
|
|
181
198
|
const std::vector<std::unique_ptr<CSGNode>>& children, const oscad::ASTNode& node);
|
|
@@ -13,10 +13,21 @@ namespace oscadeval {
|
|
|
13
13
|
// mirrors _resolve_linear_extrude/_generate_linear_extrude. `scale` is
|
|
14
14
|
// either a single number (applied to both X/Y) or a [x,y] pair for the top
|
|
15
15
|
// face; the bottom face is always full-size.
|
|
16
|
-
|
|
17
|
-
|
|
16
|
+
//
|
|
17
|
+
// Split into computeLinearExtrudeParams (pure, no children-evaluation side
|
|
18
|
+
// effect) + resolveLinearExtrude (adds the evalChildren call) so Op::
|
|
19
|
+
// PushBuiltinWrap's own runtime handler (bytecode_vm.cpp) can call the pure
|
|
20
|
+
// half directly instead of going through the whole resolve function --
|
|
21
|
+
// exactly the same split computeTransformParams/computeColorParams already
|
|
22
|
+
// use, extended to this builtin. Params computation here has no observable
|
|
23
|
+
// side effect of its own (no warn()/echo()/rands() call), so moving it
|
|
24
|
+
// before evalChildren (unlike this function's own former single-body
|
|
25
|
+
// shape, which computed params AFTER children like every other builtin
|
|
26
|
+
// still not covered by PushBuiltinWrap) is behaviorally unobservable --
|
|
27
|
+
// see computeRoofParams's own doc comment (roof.cpp) for the one builtin
|
|
28
|
+
// in this group where that ISN'T true and a different split was needed.
|
|
29
|
+
BuiltinWrapParams computeLinearExtrudeParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
18
30
|
auto [args, effCtx] = resolveCallArgs(ev, node.arguments, ctx);
|
|
19
|
-
ev.evalChildren(node.children, effCtx);
|
|
20
31
|
|
|
21
32
|
const double height = toDoubleLenient(getArg(args, 0, "height", Value{1.0}));
|
|
22
33
|
const bool center = truthy(getArg(args, std::nullopt, "center", Value{false}));
|
|
@@ -40,7 +51,13 @@ CSGParams resolveLinearExtrude(Evaluator& ev, const oscad::ModularCall& node, Ev
|
|
|
40
51
|
params["scale_x"] = Value{scaleX};
|
|
41
52
|
params["scale_y"] = Value{scaleY};
|
|
42
53
|
params["color"] = colorToValue(effCtx.color);
|
|
43
|
-
return params;
|
|
54
|
+
return BuiltinWrapParams{std::move(params), std::move(effCtx)};
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
CSGParams resolveLinearExtrude(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
58
|
+
BuiltinWrapParams result = computeLinearExtrudeParams(ev, node, ctx);
|
|
59
|
+
ev.evalChildren(node.children, result.ctx);
|
|
60
|
+
return std::move(result.params);
|
|
44
61
|
}
|
|
45
62
|
|
|
46
63
|
std::vector<ColoredBody> generateLinearExtrude(Evaluator& ev, const CSGParams& params,
|
|
@@ -65,9 +82,10 @@ std::vector<ColoredBody> generateLinearExtrude(Evaluator& ev, const CSGParams& p
|
|
|
65
82
|
// so resolve only caches $fn/$fa/$fs for generate to call fnSegments()
|
|
66
83
|
// with once the real max-x bound exists.
|
|
67
84
|
|
|
68
|
-
|
|
85
|
+
// Split the same way as computeLinearExtrudeParams, above -- see its own
|
|
86
|
+
// doc comment.
|
|
87
|
+
BuiltinWrapParams computeRotateExtrudeParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
69
88
|
auto [args, effCtx] = resolveCallArgs(ev, node.arguments, ctx);
|
|
70
|
-
ev.evalChildren(node.children, effCtx);
|
|
71
89
|
|
|
72
90
|
const double angle = toDoubleLenient(getArg(args, 0, "angle", Value{360.0}));
|
|
73
91
|
|
|
@@ -84,7 +102,13 @@ CSGParams resolveRotateExtrude(Evaluator& ev, const oscad::ModularCall& node, Ev
|
|
|
84
102
|
params["fa"] = Value{dynOr("$fa", 12.0)};
|
|
85
103
|
params["fs"] = Value{dynOr("$fs", 2.0)};
|
|
86
104
|
params["color"] = colorToValue(effCtx.color);
|
|
87
|
-
return params;
|
|
105
|
+
return BuiltinWrapParams{std::move(params), std::move(effCtx)};
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
CSGParams resolveRotateExtrude(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
109
|
+
BuiltinWrapParams result = computeRotateExtrudeParams(ev, node, ctx);
|
|
110
|
+
ev.evalChildren(node.children, result.ctx);
|
|
111
|
+
return std::move(result.params);
|
|
88
112
|
}
|
|
89
113
|
|
|
90
114
|
std::vector<ColoredBody> generateRotateExtrude(Evaluator& ev, const CSGParams& params,
|
|
@@ -108,12 +132,19 @@ std::vector<ColoredBody> generateRotateExtrude(Evaluator& ev, const CSGParams& p
|
|
|
108
132
|
// FillRule::Positive to clean up self-intersections Manifold's own
|
|
109
133
|
// Project() can produce.
|
|
110
134
|
|
|
111
|
-
|
|
135
|
+
// Split the same way as computeLinearExtrudeParams, above -- see its own
|
|
136
|
+
// doc comment.
|
|
137
|
+
BuiltinWrapParams computeProjectionParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
112
138
|
auto [args, effCtx] = resolveCallArgs(ev, node.arguments, ctx);
|
|
113
|
-
ev.evalChildren(node.children, effCtx);
|
|
114
139
|
CSGParams params;
|
|
115
140
|
params["cut"] = Value{truthy(getArg(args, std::nullopt, "cut", Value{false}))};
|
|
116
|
-
return params;
|
|
141
|
+
return BuiltinWrapParams{std::move(params), std::move(effCtx)};
|
|
142
|
+
}
|
|
143
|
+
|
|
144
|
+
CSGParams resolveProjection(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
145
|
+
BuiltinWrapParams result = computeProjectionParams(ev, node, ctx);
|
|
146
|
+
ev.evalChildren(node.children, result.ctx);
|
|
147
|
+
return std::move(result.params);
|
|
117
148
|
}
|
|
118
149
|
|
|
119
150
|
std::vector<ColoredBody> generateProjection(Evaluator&, const CSGParams& params,
|
|
@@ -145,9 +176,10 @@ std::vector<ColoredBody> generateProjection(Evaluator&, const CSGParams& params,
|
|
|
145
176
|
// (JoinType::Square, or Miter if chamfer=true) are mutually exclusive;
|
|
146
177
|
// neither given passes the first child through unchanged.
|
|
147
178
|
|
|
148
|
-
|
|
179
|
+
// Split the same way as computeLinearExtrudeParams, above -- see its own
|
|
180
|
+
// doc comment.
|
|
181
|
+
BuiltinWrapParams computeOffsetParams(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
149
182
|
auto [args, effCtx] = resolveCallArgs(ev, node.arguments, ctx);
|
|
150
|
-
ev.evalChildren(node.children, effCtx);
|
|
151
183
|
|
|
152
184
|
const Value rArg = getArg(args, std::nullopt, "r", Value{});
|
|
153
185
|
const Value deltaArg = getArg(args, std::nullopt, "delta", Value{});
|
|
@@ -161,7 +193,13 @@ CSGParams resolveOffset(Evaluator& ev, const oscad::ModularCall& node, EvalConte
|
|
|
161
193
|
params["segs"] = Value{static_cast<double>(fnSegmentsFromCtx(effCtx, std::fabs(toDoubleLenient(rArg))))};
|
|
162
194
|
}
|
|
163
195
|
params["color"] = colorToValue(effCtx.color);
|
|
164
|
-
return params;
|
|
196
|
+
return BuiltinWrapParams{std::move(params), std::move(effCtx)};
|
|
197
|
+
}
|
|
198
|
+
|
|
199
|
+
CSGParams resolveOffset(Evaluator& ev, const oscad::ModularCall& node, EvalContext& ctx) {
|
|
200
|
+
BuiltinWrapParams result = computeOffsetParams(ev, node, ctx);
|
|
201
|
+
ev.evalChildren(node.children, result.ctx);
|
|
202
|
+
return std::move(result.params);
|
|
165
203
|
}
|
|
166
204
|
|
|
167
205
|
std::vector<ColoredBody> generateOffset(Evaluator&, const CSGParams& params, const std::vector<std::unique_ptr<CSGNode>>& children,
|