1
- use rustc:: mir;
1
+ use rustc:: mir:: BasicBlock ;
2
2
use rustc:: ty:: { self , Ty } ;
3
3
use syntax:: codemap:: Span ;
4
4
5
- use interpret:: { EvalResult , EvalContext , StackPopCleanup , Lvalue , LvalueExtra , PrimVal , Value ,
5
+ use interpret:: { EvalResult , EvalContext , Lvalue , LvalueExtra , PrimVal , Value ,
6
6
Machine , ValTy } ;
7
7
8
8
impl < ' a , ' tcx , M : Machine < ' tcx > > EvalContext < ' a , ' tcx , M > {
@@ -12,6 +12,7 @@ impl<'a, 'tcx, M: Machine<'tcx>> EvalContext<'a, 'tcx, M> {
12
12
instance : ty:: Instance < ' tcx > ,
13
13
ty : Ty < ' tcx > ,
14
14
span : Span ,
15
+ target : BasicBlock ,
15
16
) -> EvalResult < ' tcx > {
16
17
trace ! ( "drop_lvalue: {:#?}" , lval) ;
17
18
// We take the address of the object. This may well be unaligned, which is fine for us here.
@@ -32,57 +33,51 @@ impl<'a, 'tcx, M: Machine<'tcx>> EvalContext<'a, 'tcx, M> {
32
33
} => ptr. ptr . to_value ( ) ,
33
34
_ => bug ! ( "force_allocation broken" ) ,
34
35
} ;
35
- self . drop ( val, instance, ty, span)
36
+ self . drop ( val, instance, ty, span, target )
36
37
}
37
- pub ( crate ) fn drop (
38
+
39
+ fn drop (
38
40
& mut self ,
39
41
arg : Value ,
40
- mut instance : ty:: Instance < ' tcx > ,
42
+ instance : ty:: Instance < ' tcx > ,
41
43
ty : Ty < ' tcx > ,
42
44
span : Span ,
45
+ target : BasicBlock ,
43
46
) -> EvalResult < ' tcx > {
44
47
trace ! ( "drop: {:#?}, {:?}, {:?}" , arg, ty. sty, instance. def) ;
45
48
46
- if let ty:: InstanceDef :: DropGlue ( _, None ) = instance. def {
47
- trace ! ( "nothing to do, aborting" ) ;
48
- // we don't actually need to drop anything
49
- return Ok ( ( ) ) ;
50
- }
51
- let mir = match ty. sty {
49
+ let instance = match ty. sty {
52
50
ty:: TyDynamic ( ..) => {
53
51
let vtable = match arg {
54
52
Value :: ByValPair ( _, PrimVal :: Ptr ( vtable) ) => vtable,
55
53
_ => bug ! ( "expected fat ptr, got {:?}" , arg) ,
56
54
} ;
57
55
match self . read_drop_type_from_vtable ( vtable) ? {
58
- Some ( func) => {
59
- instance = func;
60
- self . load_mir ( func. def ) ?
61
- }
56
+ Some ( func) => func,
62
57
// no drop fn -> bail out
63
- None => return Ok ( ( ) ) ,
58
+ None => {
59
+ self . goto_block ( target) ;
60
+ return Ok ( ( ) )
61
+ } ,
64
62
}
65
63
}
66
- _ => self . load_mir ( instance. def ) ? ,
64
+ _ => instance,
67
65
} ;
68
66
69
- self . push_stack_frame (
70
- instance,
71
- span,
72
- mir,
73
- Lvalue :: undef ( ) ,
74
- StackPopCleanup :: None ,
75
- ) ?;
76
-
77
- let mut arg_locals = self . frame ( ) . mir . args_iter ( ) ;
78
- assert_eq ! ( self . frame( ) . mir. arg_count, 1 ) ;
79
- let arg_local = arg_locals. next ( ) . unwrap ( ) ;
80
- let dest = self . eval_lvalue ( & mir:: Lvalue :: Local ( arg_local) ) ?;
81
- let arg_ty = self . tcx . mk_mut_ptr ( ty) ;
67
+ // the drop function expects a reference to the value
82
68
let valty = ValTy {
83
69
value : arg,
84
- ty : arg_ty ,
70
+ ty : self . tcx . mk_mut_ptr ( ty ) ,
85
71
} ;
86
- self . write_value ( valty, dest)
72
+
73
+ let fn_sig = self . tcx . fn_sig ( instance. def_id ( ) ) . skip_binder ( ) . clone ( ) ;
74
+
75
+ self . eval_fn_call (
76
+ instance,
77
+ Some ( ( Lvalue :: undef ( ) , target) ) ,
78
+ & vec ! [ valty] ,
79
+ span,
80
+ fn_sig,
81
+ )
87
82
}
88
83
}
0 commit comments