Revert PRs 81238 and 82967 (which made copy and copy_nonoverlapping intrinsics).
This is to address issue 84297.
This commit is contained in:
parent
cebfcd3256
commit
5f6016f125
4 changed files with 192 additions and 266 deletions
|
@ -1742,6 +1742,18 @@ extern "rust-intrinsic" {
|
|||
/// Allocate at compile time. Should not be called at runtime.
|
||||
#[rustc_const_unstable(feature = "const_heap", issue = "79597")]
|
||||
pub fn const_allocate(size: usize, align: usize) -> *mut u8;
|
||||
}
|
||||
|
||||
// Some functions are defined here because they accidentally got made
|
||||
// available in this module on stable. See <https://github.com/rust-lang/rust/issues/15702>.
|
||||
// (`transmute` also falls into this category, but it cannot be wrapped due to the
|
||||
// check that `T` and `U` have the same size.)
|
||||
|
||||
/// Checks whether `ptr` is properly aligned with respect to
|
||||
/// `align_of::<T>()`.
|
||||
pub(crate) fn is_aligned_and_not_null<T>(ptr: *const T) -> bool {
|
||||
!ptr.is_null() && ptr as usize % mem::align_of::<T>() == 0
|
||||
}
|
||||
|
||||
/// Copies `count * size_of::<T>()` bytes from `src` to `dst`. The source
|
||||
/// and destination must *not* overlap.
|
||||
|
@ -1826,8 +1838,28 @@ extern "rust-intrinsic" {
|
|||
/// [`Vec::append`]: ../../std/vec/struct.Vec.html#method.append
|
||||
#[doc(alias = "memcpy")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[rustc_const_unstable(feature = "const_intrinsic_copy", issue = "80697")]
|
||||
#[inline]
|
||||
pub const unsafe fn copy_nonoverlapping<T>(src: *const T, dst: *mut T, count: usize) {
|
||||
extern "rust-intrinsic" {
|
||||
#[rustc_const_unstable(feature = "const_intrinsic_copy", issue = "80697")]
|
||||
pub fn copy_nonoverlapping<T>(src: *const T, dst: *mut T, count: usize);
|
||||
}
|
||||
|
||||
// FIXME: Perform these checks only at run time
|
||||
/*if cfg!(debug_assertions)
|
||||
&& !(is_aligned_and_not_null(src)
|
||||
&& is_aligned_and_not_null(dst)
|
||||
&& is_nonoverlapping(src, dst, count))
|
||||
{
|
||||
// Not panicking to keep codegen impact smaller.
|
||||
abort();
|
||||
}*/
|
||||
|
||||
// SAFETY: the safety contract for `copy_nonoverlapping` must be
|
||||
// upheld by the caller.
|
||||
unsafe { copy_nonoverlapping(src, dst, count) }
|
||||
}
|
||||
|
||||
/// Copies `count * size_of::<T>()` bytes from `src` to `dst`. The source
|
||||
/// and destination may overlap.
|
||||
|
@ -1892,18 +1924,21 @@ extern "rust-intrinsic" {
|
|||
#[doc(alias = "memmove")]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
#[rustc_const_unstable(feature = "const_intrinsic_copy", issue = "80697")]
|
||||
pub fn copy<T>(src: *const T, dst: *mut T, count: usize);
|
||||
#[inline]
|
||||
pub const unsafe fn copy<T>(src: *const T, dst: *mut T, count: usize) {
|
||||
extern "rust-intrinsic" {
|
||||
#[rustc_const_unstable(feature = "const_intrinsic_copy", issue = "80697")]
|
||||
fn copy<T>(src: *const T, dst: *mut T, count: usize);
|
||||
}
|
||||
|
||||
// Some functions are defined here because they accidentally got made
|
||||
// available in this module on stable. See <https://github.com/rust-lang/rust/issues/15702>.
|
||||
// (`transmute` also falls into this category, but it cannot be wrapped due to the
|
||||
// check that `T` and `U` have the same size.)
|
||||
// FIXME: Perform these checks only at run time
|
||||
/*if cfg!(debug_assertions) && !(is_aligned_and_not_null(src) && is_aligned_and_not_null(dst)) {
|
||||
// Not panicking to keep codegen impact smaller.
|
||||
abort();
|
||||
}*/
|
||||
|
||||
/// Checks whether `ptr` is properly aligned with respect to
|
||||
/// `align_of::<T>()`.
|
||||
pub(crate) fn is_aligned_and_not_null<T>(ptr: *const T) -> bool {
|
||||
!ptr.is_null() && ptr as usize % mem::align_of::<T>() == 0
|
||||
// SAFETY: the safety contract for `copy` must be upheld by the caller.
|
||||
unsafe { copy(src, dst, count) }
|
||||
}
|
||||
|
||||
/// Sets `count * size_of::<T>()` bytes of memory starting at `dst` to
|
||||
|
|
|
@ -870,12 +870,17 @@ pub const unsafe fn read_unaligned<T>(src: *const T) -> T {
|
|||
#[inline]
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
pub unsafe fn write<T>(dst: *mut T, src: T) {
|
||||
// We are calling the intrinsics directly to avoid function calls in the generated code
|
||||
// as `intrinsics::copy_nonoverlapping` is a wrapper function.
|
||||
extern "rust-intrinsic" {
|
||||
fn copy_nonoverlapping<T>(src: *const T, dst: *mut T, count: usize);
|
||||
}
|
||||
|
||||
// SAFETY: the caller must guarantee that `dst` is valid for writes.
|
||||
// `dst` cannot overlap `src` because the caller has mutable access
|
||||
// to `dst` while `src` is owned by this function.
|
||||
unsafe {
|
||||
copy_nonoverlapping(&src as *const T, dst, 1);
|
||||
// We are calling the intrinsic directly to avoid function calls in the generated code.
|
||||
intrinsics::forget(src);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,45 +0,0 @@
|
|||
// ignore-tidy-linelength
|
||||
#![feature(const_mut_refs, const_intrinsic_copy, const_ptr_offset)]
|
||||
use std::{ptr, mem};
|
||||
|
||||
const COPY_ZERO: () = unsafe {
|
||||
// Since we are not copying anything, this should be allowed.
|
||||
let src = ();
|
||||
let mut dst = ();
|
||||
ptr::copy_nonoverlapping(&src as *const _ as *const i32, &mut dst as *mut _ as *mut i32, 0);
|
||||
};
|
||||
|
||||
const COPY_OOB_1: () = unsafe {
|
||||
let mut x = 0i32;
|
||||
let dangle = (&mut x as *mut i32).wrapping_add(10);
|
||||
// Even if the first ptr is an int ptr and this is a ZST copy, we should detect dangling 2nd ptrs.
|
||||
ptr::copy_nonoverlapping(0x100 as *const i32, dangle, 0); //~ ERROR any use of this value will cause an error
|
||||
//~| memory access failed: pointer must be in-bounds
|
||||
//~| previously accepted
|
||||
};
|
||||
const COPY_OOB_2: () = unsafe {
|
||||
let x = 0i32;
|
||||
let dangle = (&x as *const i32).wrapping_add(10);
|
||||
// Even if the second ptr is an int ptr and this is a ZST copy, we should detect dangling 1st ptrs.
|
||||
ptr::copy_nonoverlapping(dangle, 0x100 as *mut i32, 0); //~ ERROR any use of this value will cause an error
|
||||
//~| memory access failed: pointer must be in-bounds
|
||||
//~| previously accepted
|
||||
};
|
||||
|
||||
const COPY_SIZE_OVERFLOW: () = unsafe {
|
||||
let x = 0;
|
||||
let mut y = 0;
|
||||
ptr::copy(&x, &mut y, 1usize << (mem::size_of::<usize>() * 8 - 1)); //~ ERROR any use of this value will cause an error
|
||||
//~| overflow computing total size of `copy`
|
||||
//~| previously accepted
|
||||
};
|
||||
const COPY_NONOVERLAPPING_SIZE_OVERFLOW: () = unsafe {
|
||||
let x = 0;
|
||||
let mut y = 0;
|
||||
ptr::copy_nonoverlapping(&x, &mut y, 1usize << (mem::size_of::<usize>() * 8 - 1)); //~ ERROR any use of this value will cause an error
|
||||
//~| overflow computing total size of `copy_nonoverlapping`
|
||||
//~| previously accepted
|
||||
};
|
||||
|
||||
fn main() {
|
||||
}
|
|
@ -1,69 +0,0 @@
|
|||
error: any use of this value will cause an error
|
||||
--> $DIR/copy-intrinsic.rs:16:5
|
||||
|
|
||||
LL | / const COPY_OOB_1: () = unsafe {
|
||||
LL | | let mut x = 0i32;
|
||||
LL | | let dangle = (&mut x as *mut i32).wrapping_add(10);
|
||||
LL | | // Even if the first ptr is an int ptr and this is a ZST copy, we should detect dangling 2nd ptrs.
|
||||
LL | | ptr::copy_nonoverlapping(0x100 as *const i32, dangle, 0);
|
||||
| | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ memory access failed: pointer must be in-bounds at offset 40, but is outside bounds of alloc4 which has size 4
|
||||
LL | |
|
||||
LL | |
|
||||
LL | | };
|
||||
| |__-
|
||||
|
|
||||
= note: `#[deny(const_err)]` on by default
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #71800 <https://github.com/rust-lang/rust/issues/71800>
|
||||
|
||||
error: any use of this value will cause an error
|
||||
--> $DIR/copy-intrinsic.rs:24:5
|
||||
|
|
||||
LL | / const COPY_OOB_2: () = unsafe {
|
||||
LL | | let x = 0i32;
|
||||
LL | | let dangle = (&x as *const i32).wrapping_add(10);
|
||||
LL | | // Even if the second ptr is an int ptr and this is a ZST copy, we should detect dangling 1st ptrs.
|
||||
LL | | ptr::copy_nonoverlapping(dangle, 0x100 as *mut i32, 0);
|
||||
| | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ memory access failed: pointer must be in-bounds at offset 40, but is outside bounds of alloc6 which has size 4
|
||||
LL | |
|
||||
LL | |
|
||||
LL | | };
|
||||
| |__-
|
||||
|
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #71800 <https://github.com/rust-lang/rust/issues/71800>
|
||||
|
||||
error: any use of this value will cause an error
|
||||
--> $DIR/copy-intrinsic.rs:32:5
|
||||
|
|
||||
LL | / const COPY_SIZE_OVERFLOW: () = unsafe {
|
||||
LL | | let x = 0;
|
||||
LL | | let mut y = 0;
|
||||
LL | | ptr::copy(&x, &mut y, 1usize << (mem::size_of::<usize>() * 8 - 1));
|
||||
| | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ overflow computing total size of `copy`
|
||||
LL | |
|
||||
LL | |
|
||||
LL | | };
|
||||
| |__-
|
||||
|
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #71800 <https://github.com/rust-lang/rust/issues/71800>
|
||||
|
||||
error: any use of this value will cause an error
|
||||
--> $DIR/copy-intrinsic.rs:39:5
|
||||
|
|
||||
LL | / const COPY_NONOVERLAPPING_SIZE_OVERFLOW: () = unsafe {
|
||||
LL | | let x = 0;
|
||||
LL | | let mut y = 0;
|
||||
LL | | ptr::copy_nonoverlapping(&x, &mut y, 1usize << (mem::size_of::<usize>() * 8 - 1));
|
||||
| | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ overflow computing total size of `copy_nonoverlapping`
|
||||
LL | |
|
||||
LL | |
|
||||
LL | | };
|
||||
| |__-
|
||||
|
|
||||
= warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release!
|
||||
= note: for more information, see issue #71800 <https://github.com/rust-lang/rust/issues/71800>
|
||||
|
||||
error: aborting due to 4 previous errors
|
||||
|
Loading…
Add table
Add a link
Reference in a new issue