Skip to content

Commit 76397e8

Browse files
Lishin1215CohenArthur
authored andcommitted
gccrs: Emit drops for function parameters
Add function parameters to the function scope drop list after the function body block is created. This makes parameters drop after local variables on normal function exit. gcc/rust/ChangeLog: * backend/rust-compile-base.cc (HIRCompileBase::compile_function): Track droppable function parameters in the function scope. gcc/testsuite/ChangeLog: * rust/execute/drop-function-params.rs: New test. Signed-off-by: Lishin <lishin1008@gmail.com>
1 parent 1337bc7 commit 76397e8

2 files changed

Lines changed: 64 additions & 1 deletion

File tree

gcc/rust/backend/rust-compile-base.cc

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#include "rust-compile-stmt.h"
2222
#include "rust-compile-expr.h"
2323
#include "rust-compile-drop.h"
24+
#include "rust-compile-drop-builder.h"
2425
#include "rust-compile-fnparam.h"
2526
#include "rust-compile-var-decl.h"
2627
#include "rust-compile-type.h"
@@ -739,7 +740,7 @@ HIRCompileBase::compile_function_body (tree fndecl,
739740
// just add the stmt expression
740741
ctx->add_statement (return_value);
741742

742-
CompileDrop::emit_current_scope_drop_calls (ctx);
743+
CompileDrop (ctx).emit_current_scope_drop_calls ();
743744

744745
// now just return unit expression
745746
tree unit_expr = unit_expression (locus);
@@ -845,6 +846,7 @@ HIRCompileBase::compile_function (
845846
// setup the params
846847
TyTy::BaseType *tyret = fntype->get_return_type ();
847848
std::vector<Bvariable *> param_vars;
849+
std::vector<DropCandidate> param_drop_candidates;
848850
if (self_param)
849851
{
850852
rust_assert (fntype->is_method ());
@@ -880,6 +882,11 @@ HIRCompileBase::compile_function (
880882
const HIR::Pattern &param_pattern = referenced_param.get_param_name ();
881883
ctx->insert_var_decl (param_pattern.get_mappings ().get_hirid (),
882884
compiled_param_var);
885+
886+
if (CompileDrop (ctx).type_has_drop_impl (param_tyty))
887+
param_drop_candidates.emplace_back (
888+
param_pattern.get_mappings ().get_hirid (),
889+
param_pattern.get_locus ());
883890
}
884891

885892
if (!Backend::function_set_parameters (fndecl, param_vars))
@@ -893,6 +900,10 @@ HIRCompileBase::compile_function (
893900
start_location, end_location);
894901
ctx->push_block (code_block);
895902

903+
DropBuilder drop_builder (*ctx);
904+
for (auto &candidate : param_drop_candidates)
905+
drop_builder.note_simple_drop_candidate (candidate.hirid, candidate.locus);
906+
896907
Bvariable *return_address = nullptr;
897908
tree return_type = TyTyResolveCompile::compile (ctx, tyret);
898909

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
// { dg-output "l\r*\np\r*\nl\r*\np\r*\n" }
2+
// { dg-additional-options "-w" }
3+
#![feature(no_core)]
4+
#![feature(lang_items)]
5+
#![no_core]
6+
7+
extern "C" {
8+
fn printf(s: *const i8, ...);
9+
}
10+
11+
#[lang = "sized"]
12+
pub trait Sized {}
13+
14+
#[lang = "drop"]
15+
pub trait Drop {
16+
fn drop(&mut self);
17+
}
18+
19+
struct ParamDroppable;
20+
struct LocalDroppable;
21+
22+
impl Drop for ParamDroppable {
23+
fn drop(&mut self) {
24+
let msg = "p\n\0" as *const str as *const i8;
25+
unsafe {
26+
printf(msg);
27+
}
28+
}
29+
}
30+
31+
impl Drop for LocalDroppable {
32+
fn drop(&mut self) {
33+
let msg = "l\n\0" as *const str as *const i8;
34+
unsafe {
35+
printf(msg);
36+
}
37+
}
38+
}
39+
40+
fn named_param(_p: ParamDroppable) {
41+
let _l = LocalDroppable;
42+
}
43+
44+
fn wildcard_param(_: ParamDroppable) {
45+
let _l = LocalDroppable;
46+
}
47+
48+
fn main() -> i32 {
49+
named_param(ParamDroppable);
50+
wildcard_param(ParamDroppable);
51+
0
52+
}

0 commit comments

Comments
 (0)