https://gcc.gnu.org/g:0a0bbb5e07487353b13f3787143f715839124675
commit r17-3095-g0a0bbb5e07487353b13f3787143f715839124675 Author: Lishin <[email protected]> Date: Thu Jul 2 16:14:39 2026 +0000 gccrs: Emit block scope drops through TRY_FINALLY_EXPR Add Context::pop_block_with_cleanup for blocks that need cleanup. Use it from CompileBlock so block-scope drops are emitted in a TRY_FINALLY_EXPR cleanup instead of at the end of the block body. gcc/rust/ChangeLog: * backend/rust-compile-block.cc (CompileBlock::visit): Build current scope drop cleanup and pass it when popping the block. * backend/rust-compile-context.h (Context::pop_block): Use pop_block_impl. (Context::pop_block_with_cleanup): New function for popping a block with cleanup code. (Context::pop_block_impl): New helper that adds the block statements directly, or wraps them in TRY_FINALLY_EXPR when cleanup is present. Signed-off-by: Lishin <[email protected]> Diff: --- gcc/rust/backend/rust-compile-block.cc | 4 +-- gcc/rust/backend/rust-compile-context.h | 45 +++++++++++++++++++++++---------- 2 files changed, 34 insertions(+), 15 deletions(-) diff --git a/gcc/rust/backend/rust-compile-block.cc b/gcc/rust/backend/rust-compile-block.cc index e35d02e52a06..ca69315c3b5d 100644 --- a/gcc/rust/backend/rust-compile-block.cc +++ b/gcc/rust/backend/rust-compile-block.cc @@ -85,9 +85,9 @@ CompileBlock::visit (HIR::BlockExpr &expr) expr.get_locus ()); ctx->add_statement (assignment); } - CompileDrop (ctx).emit_current_scope_drop_calls (); + tree cleanup = CompileDrop (ctx).build_current_scope_drop_cleanup (); - ctx->pop_block (); + ctx->pop_block_with_cleanup (cleanup, expr.get_locus ()); translated = new_block; } diff --git a/gcc/rust/backend/rust-compile-context.h b/gcc/rust/backend/rust-compile-context.h index 9fe39e5572d7..25a27ca96281 100644 --- a/gcc/rust/backend/rust-compile-context.h +++ b/gcc/rust/backend/rust-compile-context.h @@ -107,20 +107,11 @@ public: block_drop_candidates.emplace_back (); } - tree pop_block () - { - auto block = scope_stack.back (); - scope_stack.pop_back (); - - auto stmts = statements.back (); - statements.pop_back (); - - rust_assert (!block_drop_candidates.empty ()); - block_drop_candidates.pop_back (); + tree pop_block () { return pop_block_impl (NULL_TREE, UNKNOWN_LOCATION); } - Backend::block_add_statements (block, stmts); - - return block; + tree pop_block_with_cleanup (tree cleanup, location_t cleanup_locus) + { + return pop_block_impl (cleanup, cleanup_locus); } tree peek_enclosing_scope () @@ -429,6 +420,34 @@ private: friend class DropBuilder; Context (); + tree pop_block_impl (tree cleanup, location_t cleanup_locus) + { + auto block = scope_stack.back (); + scope_stack.pop_back (); + + auto stmts = statements.back (); + statements.pop_back (); + + rust_assert (!block_drop_candidates.empty ()); + block_drop_candidates.pop_back (); + + if (cleanup != NULL_TREE) + { + tree body = Backend::statement_list (stmts); + if (body == NULL_TREE) + body = build_empty_stmt (cleanup_locus); + + tree try_finally + = Backend::exception_handler_statement (body, NULL_TREE, cleanup, + cleanup_locus); + Backend::block_add_statements (block, {try_finally}); + } + else + Backend::block_add_statements (block, stmts); + + return block; + } + Resolver::TypeCheckContext *tyctx; Analysis::Mappings &mappings; Mangler mangler;
