diff options
| author | Jakob Degen <jakob.e.degen@gmail.com> | 2022-12-06 01:18:24 -0800 |
|---|---|---|
| committer | Jakob Degen <jakob.e.degen@gmail.com> | 2022-12-21 14:59:55 -0800 |
| commit | c359ab0b5d0dbaab1a995d7aa9fb9c6512bb837b (patch) | |
| tree | a91cdcddc1574428355322b1869fbde9f50d837d | |
| parent | 102040ce76d588c0605e29577cdf8307acb4bb10 (diff) | |
| download | rust-c359ab0b5d0dbaab1a995d7aa9fb9c6512bb837b.tar.gz rust-c359ab0b5d0dbaab1a995d7aa9fb9c6512bb837b.zip | |
Retag argument to `drop_in_place` unconditionally
6 files changed, 34 insertions, 47 deletions
diff --git a/compiler/rustc_mir_transform/src/shim.rs b/compiler/rustc_mir_transform/src/shim.rs index aa89ff00381..dace540fa29 100644 --- a/compiler/rustc_mir_transform/src/shim.rs +++ b/compiler/rustc_mir_transform/src/shim.rs @@ -174,35 +174,36 @@ fn build_drop_shim<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId, ty: Option<Ty<'tcx>>) let mut body = new_body(source, blocks, local_decls_for_sig(&sig, span), sig.inputs().len(), span); - if ty.is_some() { - // The first argument (index 0), but add 1 for the return value. - let mut dropee_ptr = Place::from(Local::new(1 + 0)); - if tcx.sess.opts.unstable_opts.mir_emit_retag { - // We want to treat the function argument as if it was passed by `&mut`. As such, we - // generate - // ``` - // temp = &mut *arg; - // Retag(temp, FnEntry) - // ``` - // It's important that we do this first, before anything that depends on `dropee_ptr` - // has been put into the body. - let reborrow = Rvalue::Ref( - tcx.lifetimes.re_erased, - BorrowKind::Mut { allow_two_phase_borrow: false }, - tcx.mk_place_deref(dropee_ptr), - ); - let ref_ty = reborrow.ty(body.local_decls(), tcx); - dropee_ptr = body.local_decls.push(LocalDecl::new(ref_ty, span)).into(); - let new_statements = [ - StatementKind::Assign(Box::new((dropee_ptr, reborrow))), - StatementKind::Retag(RetagKind::FnEntry, Box::new(dropee_ptr)), - ]; - for s in new_statements { - body.basic_blocks_mut()[START_BLOCK] - .statements - .push(Statement { source_info, kind: s }); - } + // The first argument (index 0), but add 1 for the return value. + let mut dropee_ptr = Place::from(Local::new(1 + 0)); + if tcx.sess.opts.unstable_opts.mir_emit_retag { + // We want to treat the function argument as if it was passed by `&mut`. As such, we + // generate + // ``` + // temp = &mut *arg; + // Retag(temp, FnEntry) + // ``` + // It's important that we do this first, before anything that depends on `dropee_ptr` + // has been put into the body. + let reborrow = Rvalue::Ref( + tcx.lifetimes.re_erased, + BorrowKind::Mut { allow_two_phase_borrow: false }, + tcx.mk_place_deref(dropee_ptr), + ); + let ref_ty = reborrow.ty(body.local_decls(), tcx); + dropee_ptr = body.local_decls.push(LocalDecl::new(ref_ty, span)).into(); + let new_statements = [ + StatementKind::Assign(Box::new((dropee_ptr, reborrow))), + StatementKind::Retag(RetagKind::FnEntry, Box::new(dropee_ptr)), + ]; + for s in new_statements { + body.basic_blocks_mut()[START_BLOCK] + .statements + .push(Statement { source_info, kind: s }); } + } + + if ty.is_some() { let patch = { let param_env = tcx.param_env_reveal_all_normalized(def_id); let mut elaborator = diff --git a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.rs b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.rs index 883361d05fc..8cf63ee700b 100644 --- a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.rs +++ b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.rs @@ -10,7 +10,7 @@ impl Drop for HasDrop { fn drop(&mut self) { unsafe { let _val = *P; - //~^ ERROR: /not granting access .* because that would remove .* which is protected/ + //~^ ERROR: /not granting access .* because that would remove .* which is strongly protected/ } } } diff --git a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.stderr b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.stderr index 6d122ade477..8b1740cd81b 100644 --- a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.stderr +++ b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_protector.stderr @@ -1,8 +1,8 @@ -error: Undefined Behavior: not granting access to tag <TAG> because that would remove [Unique for <TAG>] which is protected because it is an argument of call ID +error: Undefined Behavior: not granting access to tag <TAG> because that would remove [Unique for <TAG>] which is strongly protected because it is an argument of call ID --> $DIR/drop_in_place_protector.rs:LL:CC | LL | let _val = *P; - | ^^ not granting access to tag <TAG> because that would remove [Unique for <TAG>] which is protected because it is an argument of call ID + | ^^ not granting access to tag <TAG> because that would remove [Unique for <TAG>] which is strongly protected because it is an argument of call ID | = help: this indicates a potential bug in the program: it performed an invalid operation, but the Stacked Borrows rules it violated are still experimental = help: see https://github.com/rust-lang/unsafe-code-guidelines/blob/master/wip/stacked-borrows.md for further information diff --git a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.rs b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.rs index 4cb870f1d97..e7d256b686d 100644 --- a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.rs +++ b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.rs @@ -3,16 +3,9 @@ //@error-pattern: /retag .* for Unique permission .* only grants SharedReadOnly permission/ -#[repr(transparent)] -struct HasDrop; - -impl Drop for HasDrop { - fn drop(&mut self) {} -} - fn main() { unsafe { - let x = (0u8, HasDrop); + let x = 0u8; let x = core::ptr::addr_of!(x); core::ptr::drop_in_place(x.cast_mut()); } diff --git a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.stderr b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.stderr index 022b27d69b2..05648e44be9 100644 --- a/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.stderr +++ b/src/tools/miri/tests/fail/stacked_borrows/drop_in_place_retag.stderr @@ -15,7 +15,7 @@ help: <TAG> was created by a SharedReadOnly retag at offsets [0x0..0x1] LL | let x = core::ptr::addr_of!(x); | ^^^^^^^^^^^^^^^^^^^^^^ = note: BACKTRACE: - = note: inside `std::ptr::drop_in_place::<(u8, HasDrop)> - shim(Some((u8, HasDrop)))` at RUSTLIB/core/src/ptr/mod.rs:LL:CC + = note: inside `std::ptr::drop_in_place::<u8> - shim(None)` at RUSTLIB/core/src/ptr/mod.rs:LL:CC note: inside `main` at $DIR/drop_in_place_retag.rs:LL:CC --> $DIR/drop_in_place_retag.rs:LL:CC | diff --git a/src/tools/miri/tests/pass/drop_in_place_null.rs b/src/tools/miri/tests/pass/drop_in_place_null.rs deleted file mode 100644 index aab070b6975..00000000000 --- a/src/tools/miri/tests/pass/drop_in_place_null.rs +++ /dev/null @@ -1,7 +0,0 @@ -// Make sure that dropping types with no drop glue is DB even for invalid pointers. - -fn main() { - unsafe { - core::ptr::drop_in_place::<u8>(core::ptr::null_mut()); - } -} |
