From 8d881ee3a36ed9a81fc55aef9e47048ad96ef6d6 Mon Sep 17 00:00:00 2001 From: David McFarland Date: Sat, 15 Nov 2025 15:07:50 -0400 Subject: [PATCH] nix_api_expr: ensure destructors are called for builder/state I found this because of a test failure on cygwin in nix_api_expr_test.nix_eval_state_lookup_path: 'std::filesystem::__cxx11::filesystem_error' what(): filesystem error: cannot remove all: Device or resource busy [...] [.../my_state/db/db.sqlite] LocalState was never getting destroyed due to a reference leak. These _free functions use an 'operator delete' which doesn't call the destructor for the type. Fixes: 309d55807c088ec3172f35d576522329972a1904 --- src/libexpr-c/nix_api_expr.cc | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/libexpr-c/nix_api_expr.cc b/src/libexpr-c/nix_api_expr.cc index db11dd40d..76f3b6486 100644 --- a/src/libexpr-c/nix_api_expr.cc +++ b/src/libexpr-c/nix_api_expr.cc @@ -137,6 +137,8 @@ nix_eval_state_builder * nix_eval_state_builder_new(nix_c_context * context, Sto void nix_eval_state_builder_free(nix_eval_state_builder * builder) { + if (builder) + builder->~nix_eval_state_builder(); operator delete(builder, static_cast(alignof(nix_eval_state_builder))); } @@ -203,6 +205,8 @@ EvalState * nix_state_create(nix_c_context * context, const char ** lookupPath_c void nix_state_free(EvalState * state) { + if (state) + state->~EvalState(); operator delete(state, static_cast(alignof(EvalState))); }