@@ -214,6 +214,43 @@ fn local_decls_for_sig<'tcx>(
214
214
. collect ( )
215
215
}
216
216
217
+ fn dropee_emit_retag < ' tcx > (
218
+ tcx : TyCtxt < ' tcx > ,
219
+ body : & mut Body < ' tcx > ,
220
+ dropee_ptr : Place < ' tcx > ,
221
+ span : Span ,
222
+ ) -> Place < ' tcx > {
223
+ let mut dropee_ptr = dropee_ptr;
224
+ if tcx. sess . opts . unstable_opts . mir_emit_retag {
225
+ let source_info = SourceInfo :: outermost ( span) ;
226
+ // We want to treat the function argument as if it was passed by `&mut`. As such, we
227
+ // generate
228
+ // ```
229
+ // temp = &mut *arg;
230
+ // Retag(temp, FnEntry)
231
+ // ```
232
+ // It's important that we do this first, before anything that depends on `dropee_ptr`
233
+ // has been put into the body.
234
+ let reborrow = Rvalue :: Ref (
235
+ tcx. lifetimes . re_erased ,
236
+ BorrowKind :: Mut { kind : MutBorrowKind :: Default } ,
237
+ tcx. mk_place_deref ( dropee_ptr) ,
238
+ ) ;
239
+ let ref_ty = reborrow. ty ( body. local_decls ( ) , tcx) ;
240
+ dropee_ptr = body. local_decls . push ( LocalDecl :: new ( ref_ty, span) ) . into ( ) ;
241
+ let new_statements = [
242
+ StatementKind :: Assign ( Box :: new ( ( dropee_ptr, reborrow) ) ) ,
243
+ StatementKind :: Retag ( RetagKind :: FnEntry , Box :: new ( dropee_ptr) ) ,
244
+ ] ;
245
+ for s in new_statements {
246
+ body. basic_blocks_mut ( ) [ START_BLOCK ]
247
+ . statements
248
+ . push ( Statement { source_info, kind : s } ) ;
249
+ }
250
+ }
251
+ dropee_ptr
252
+ }
253
+
217
254
fn build_drop_shim < ' tcx > ( tcx : TyCtxt < ' tcx > , def_id : DefId , ty : Option < Ty < ' tcx > > ) -> Body < ' tcx > {
218
255
debug ! ( "build_drop_shim(def_id={:?}, ty={:?})" , def_id, ty) ;
219
256
@@ -248,32 +285,7 @@ fn build_drop_shim<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId, ty: Option<Ty<'tcx>>)
248
285
249
286
// The first argument (index 0), but add 1 for the return value.
250
287
let mut dropee_ptr = Place :: from ( Local :: new ( 1 + 0 ) ) ;
251
- if tcx. sess . opts . unstable_opts . mir_emit_retag {
252
- // We want to treat the function argument as if it was passed by `&mut`. As such, we
253
- // generate
254
- // ```
255
- // temp = &mut *arg;
256
- // Retag(temp, FnEntry)
257
- // ```
258
- // It's important that we do this first, before anything that depends on `dropee_ptr`
259
- // has been put into the body.
260
- let reborrow = Rvalue :: Ref (
261
- tcx. lifetimes . re_erased ,
262
- BorrowKind :: Mut { kind : MutBorrowKind :: Default } ,
263
- tcx. mk_place_deref ( dropee_ptr) ,
264
- ) ;
265
- let ref_ty = reborrow. ty ( body. local_decls ( ) , tcx) ;
266
- dropee_ptr = body. local_decls . push ( LocalDecl :: new ( ref_ty, span) ) . into ( ) ;
267
- let new_statements = [
268
- StatementKind :: Assign ( Box :: new ( ( dropee_ptr, reborrow) ) ) ,
269
- StatementKind :: Retag ( RetagKind :: FnEntry , Box :: new ( dropee_ptr) ) ,
270
- ] ;
271
- for s in new_statements {
272
- body. basic_blocks_mut ( ) [ START_BLOCK ]
273
- . statements
274
- . push ( Statement { source_info, kind : s } ) ;
275
- }
276
- }
288
+ dropee_ptr = dropee_emit_retag ( tcx, & mut body, dropee_ptr, span) ;
277
289
278
290
if ty. is_some ( ) {
279
291
let patch = {
0 commit comments