mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-25 08:13:41 +00:00
rename expose_addr
to expose_provenance
This commit is contained in:
parent
99c42d2340
commit
989660c3e6
@ -2261,7 +2261,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
CastKind::PointerExposeAddress => {
|
||||
CastKind::PointerExposeProvenance => {
|
||||
let ty_from = op.ty(body, tcx);
|
||||
let cast_ty_from = CastTy::from_ty(ty_from);
|
||||
let cast_ty_to = CastTy::from_ty(*ty);
|
||||
@ -2271,7 +2271,7 @@ impl<'a, 'tcx> TypeChecker<'a, 'tcx> {
|
||||
span_mirbug!(
|
||||
self,
|
||||
rvalue,
|
||||
"Invalid PointerExposeAddress cast {:?} -> {:?}",
|
||||
"Invalid PointerExposeProvenance cast {:?} -> {:?}",
|
||||
ty_from,
|
||||
ty
|
||||
)
|
||||
|
@ -649,7 +649,7 @@ fn codegen_stmt<'tcx>(
|
||||
| CastKind::IntToFloat
|
||||
| CastKind::FnPtrToPtr
|
||||
| CastKind::PtrToPtr
|
||||
| CastKind::PointerExposeAddress
|
||||
| CastKind::PointerExposeProvenance
|
||||
| CastKind::PointerWithExposedProvenance,
|
||||
ref operand,
|
||||
to_ty,
|
||||
|
@ -965,7 +965,7 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>(
|
||||
});
|
||||
}
|
||||
|
||||
sym::simd_expose_addr | sym::simd_with_exposed_provenance | sym::simd_cast_ptr => {
|
||||
sym::simd_expose_provenance | sym::simd_with_exposed_provenance | sym::simd_cast_ptr => {
|
||||
intrinsic_args!(fx, args => (arg); intrinsic);
|
||||
ret.write_cvalue_transmute(fx, arg);
|
||||
}
|
||||
|
@ -2111,7 +2111,7 @@ fn generic_simd_intrinsic<'ll, 'tcx>(
|
||||
return Ok(args[0].immediate());
|
||||
}
|
||||
|
||||
if name == sym::simd_expose_addr {
|
||||
if name == sym::simd_expose_provenance {
|
||||
let (out_len, out_elem) = require_simd!(ret_ty, SimdReturn);
|
||||
require!(
|
||||
in_len == out_len,
|
||||
|
@ -405,7 +405,7 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
|
||||
let cast = bx.cx().layout_of(self.monomorphize(mir_cast_ty));
|
||||
|
||||
let val = match *kind {
|
||||
mir::CastKind::PointerExposeAddress => {
|
||||
mir::CastKind::PointerExposeProvenance => {
|
||||
assert!(bx.cx().is_backend_immediate(cast));
|
||||
let llptr = operand.immediate();
|
||||
let llcast_ty = bx.cx().immediate_backend_type(cast);
|
||||
|
@ -34,9 +34,9 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
|
||||
self.unsize_into(src, cast_layout, dest)?;
|
||||
}
|
||||
|
||||
CastKind::PointerExposeAddress => {
|
||||
CastKind::PointerExposeProvenance => {
|
||||
let src = self.read_immediate(src)?;
|
||||
let res = self.pointer_expose_address_cast(&src, cast_layout)?;
|
||||
let res = self.pointer_expose_provenance_cast(&src, cast_layout)?;
|
||||
self.write_immediate(*res, dest)?;
|
||||
}
|
||||
|
||||
@ -225,7 +225,7 @@ impl<'mir, 'tcx: 'mir, M: Machine<'mir, 'tcx>> InterpCx<'mir, 'tcx, M> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn pointer_expose_address_cast(
|
||||
pub fn pointer_expose_provenance_cast(
|
||||
&mut self,
|
||||
src: &ImmTy<'tcx, M::Provenance>,
|
||||
cast_to: TyAndLayout<'tcx>,
|
||||
|
@ -544,7 +544,7 @@ impl<'tcx> Visitor<'tcx> for Checker<'_, 'tcx> {
|
||||
// Unsizing is implemented for CTFE.
|
||||
}
|
||||
|
||||
Rvalue::Cast(CastKind::PointerExposeAddress, _, _) => {
|
||||
Rvalue::Cast(CastKind::PointerExposeProvenance, _, _) => {
|
||||
self.check_op(ops::RawPtrToIntCast);
|
||||
}
|
||||
Rvalue::Cast(CastKind::PointerWithExposedProvenance, _, _) => {
|
||||
|
@ -1077,7 +1077,7 @@ impl<'a, 'tcx> Visitor<'tcx> for TypeChecker<'a, 'tcx> {
|
||||
}
|
||||
// FIXME: Add Checks for these
|
||||
CastKind::PointerWithExposedProvenance
|
||||
| CastKind::PointerExposeAddress
|
||||
| CastKind::PointerExposeProvenance
|
||||
| CastKind::PointerCoercion(_) => {}
|
||||
CastKind::IntToInt | CastKind::IntToFloat => {
|
||||
let input_valid = op_ty.is_integral() || op_ty.is_char() || op_ty.is_bool();
|
||||
|
@ -627,7 +627,7 @@ pub fn check_intrinsic_type(
|
||||
sym::simd_cast
|
||||
| sym::simd_as
|
||||
| sym::simd_cast_ptr
|
||||
| sym::simd_expose_addr
|
||||
| sym::simd_expose_provenance
|
||||
| sym::simd_with_exposed_provenance => (2, 0, vec![param(0)], param(1)),
|
||||
sym::simd_bitmask => (2, 0, vec![param(0)], param(1)),
|
||||
sym::simd_select | sym::simd_select_bitmask => {
|
||||
|
@ -91,7 +91,7 @@ hir_typeck_lossy_provenance_int2ptr =
|
||||
hir_typeck_lossy_provenance_ptr2int =
|
||||
under strict provenance it is considered bad style to cast pointer `{$expr_ty}` to integer `{$cast_ty}`
|
||||
.suggestion = use `.addr()` to obtain the address of a pointer
|
||||
.help = if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_addr()` instead
|
||||
.help = if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_provenance()` instead
|
||||
|
||||
hir_typeck_method_call_on_unknown_raw_pointee =
|
||||
cannot call a method on a raw pointer with an unknown pointee type
|
||||
|
@ -2797,17 +2797,17 @@ declare_lint! {
|
||||
/// Since this cast is lossy, it is considered good style to use the
|
||||
/// [`ptr::addr`] method instead, which has a similar effect, but doesn't
|
||||
/// "expose" the pointer provenance. This improves optimisation potential.
|
||||
/// See the docs of [`ptr::addr`] and [`ptr::expose_addr`] for more information
|
||||
/// See the docs of [`ptr::addr`] and [`ptr::expose_provenance`] for more information
|
||||
/// about exposing pointer provenance.
|
||||
///
|
||||
/// If your code can't comply with strict provenance and needs to expose
|
||||
/// the provenance, then there is [`ptr::expose_addr`] as an escape hatch,
|
||||
/// the provenance, then there is [`ptr::expose_provenance`] as an escape hatch,
|
||||
/// which preserves the behaviour of `as usize` casts while being explicit
|
||||
/// about the semantics.
|
||||
///
|
||||
/// [issue #95228]: https://github.com/rust-lang/rust/issues/95228
|
||||
/// [`ptr::addr`]: https://doc.rust-lang.org/core/primitive.pointer.html#method.addr
|
||||
/// [`ptr::expose_addr`]: https://doc.rust-lang.org/core/primitive.pointer.html#method.expose_addr
|
||||
/// [`ptr::expose_provenance`]: https://doc.rust-lang.org/core/primitive.pointer.html#method.expose_provenance
|
||||
pub LOSSY_PROVENANCE_CASTS,
|
||||
Allow,
|
||||
"a lossy pointer to integer cast is used",
|
||||
|
@ -409,7 +409,7 @@ impl<'tcx> Rvalue<'tcx> {
|
||||
// Pointer to int casts may be side-effects due to exposing the provenance.
|
||||
// While the model is undecided, we should be conservative. See
|
||||
// <https://www.ralfj.de/blog/2022/04/11/provenance-exposed.html>
|
||||
Rvalue::Cast(CastKind::PointerExposeAddress, _, _) => false,
|
||||
Rvalue::Cast(CastKind::PointerExposeProvenance, _, _) => false,
|
||||
|
||||
Rvalue::Use(_)
|
||||
| Rvalue::CopyForDeref(_)
|
||||
|
@ -1309,8 +1309,8 @@ pub enum Rvalue<'tcx> {
|
||||
pub enum CastKind {
|
||||
/// An exposing pointer to address cast. A cast between a pointer and an integer type, or
|
||||
/// between a function pointer and an integer type.
|
||||
/// See the docs on `expose_addr` for more details.
|
||||
PointerExposeAddress,
|
||||
/// See the docs on `expose_provenance` for more details.
|
||||
PointerExposeProvenance,
|
||||
/// An address-to-pointer cast that picks up an exposed provenance.
|
||||
/// See the docs on `with_exposed_provenance` for more details.
|
||||
PointerWithExposedProvenance,
|
||||
|
@ -83,7 +83,7 @@ pub fn mir_cast_kind<'tcx>(from_ty: Ty<'tcx>, cast_ty: Ty<'tcx>) -> mir::CastKin
|
||||
let cast = CastTy::from_ty(cast_ty);
|
||||
let cast_kind = match (from, cast) {
|
||||
(Some(CastTy::Ptr(_) | CastTy::FnPtr), Some(CastTy::Int(_))) => {
|
||||
mir::CastKind::PointerExposeAddress
|
||||
mir::CastKind::PointerExposeProvenance
|
||||
}
|
||||
(Some(CastTy::Int(_)), Some(CastTy::Ptr(_))) => mir::CastKind::PointerWithExposedProvenance,
|
||||
(_, Some(CastTy::DynStar)) => mir::CastKind::DynStar,
|
||||
|
@ -434,7 +434,7 @@ impl<'tcx> Validator<'_, 'tcx> {
|
||||
Rvalue::ThreadLocalRef(_) => return Err(Unpromotable),
|
||||
|
||||
// ptr-to-int casts are not possible in consts and thus not promotable
|
||||
Rvalue::Cast(CastKind::PointerExposeAddress, _, _) => return Err(Unpromotable),
|
||||
Rvalue::Cast(CastKind::PointerExposeProvenance, _, _) => return Err(Unpromotable),
|
||||
|
||||
// all other casts including int-to-ptr casts are fine, they just use the integer value
|
||||
// at pointer type.
|
||||
|
@ -985,7 +985,7 @@ fn build_fn_ptr_addr_shim<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId, self_ty: Ty<'t
|
||||
let locals = local_decls_for_sig(&sig, span);
|
||||
|
||||
let source_info = SourceInfo::outermost(span);
|
||||
// FIXME: use `expose_addr` once we figure out whether function pointers have meaningful provenance.
|
||||
// FIXME: use `expose_provenance` once we figure out whether function pointers have meaningful provenance.
|
||||
let rvalue = Rvalue::Cast(
|
||||
CastKind::FnPtrToPtr,
|
||||
Operand::Move(Place::from(Local::new(1))),
|
||||
|
@ -267,7 +267,7 @@ impl<'tcx> Stable<'tcx> for mir::CastKind {
|
||||
fn stable(&self, tables: &mut Tables<'_>) -> Self::T {
|
||||
use rustc_middle::mir::CastKind::*;
|
||||
match self {
|
||||
PointerExposeAddress => stable_mir::mir::CastKind::PointerExposeAddress,
|
||||
PointerExposeProvenance => stable_mir::mir::CastKind::PointerExposeAddress,
|
||||
PointerWithExposedProvenance => stable_mir::mir::CastKind::PointerWithExposedProvenance,
|
||||
PointerCoercion(c) => stable_mir::mir::CastKind::PointerCoercion(c.stable(tables)),
|
||||
DynStar => stable_mir::mir::CastKind::DynStar,
|
||||
|
@ -1659,7 +1659,7 @@ symbols! {
|
||||
simd_cttz,
|
||||
simd_div,
|
||||
simd_eq,
|
||||
simd_expose_addr,
|
||||
simd_expose_provenance,
|
||||
simd_extract,
|
||||
simd_fabs,
|
||||
simd_fcos,
|
||||
|
@ -971,6 +971,7 @@ pub enum PointerCoercion {
|
||||
|
||||
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
|
||||
pub enum CastKind {
|
||||
// FIXME(smir-rename): rename this to PointerExposeProvenance
|
||||
PointerExposeAddress,
|
||||
PointerWithExposedProvenance,
|
||||
PointerCoercion(PointerCoercion),
|
||||
|
@ -2438,8 +2438,8 @@ impl Display for char {
|
||||
#[stable(feature = "rust1", since = "1.0.0")]
|
||||
impl<T: ?Sized> Pointer for *const T {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> Result {
|
||||
// Cast is needed here because `.expose_addr()` requires `T: Sized`.
|
||||
pointer_fmt_inner((*self as *const ()).expose_addr(), f)
|
||||
// Cast is needed here because `.expose_provenance()` requires `T: Sized`.
|
||||
pointer_fmt_inner((*self as *const ()).expose_provenance(), f)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -540,6 +540,10 @@ extern "rust-intrinsic" {
|
||||
/// `T` must be a vector of pointers.
|
||||
///
|
||||
/// `U` must be a vector of `usize` with the same length as `T`.
|
||||
#[cfg(not(bootstrap))]
|
||||
#[rustc_nounwind]
|
||||
pub fn simd_expose_provenance<T, U>(ptr: T) -> U;
|
||||
#[cfg(bootstrap)]
|
||||
#[rustc_nounwind]
|
||||
pub fn simd_expose_addr<T, U>(ptr: T) -> U;
|
||||
|
||||
@ -660,5 +664,7 @@ extern "rust-intrinsic" {
|
||||
pub fn simd_flog<T>(a: T) -> T;
|
||||
}
|
||||
|
||||
#[cfg(bootstrap)]
|
||||
pub use simd_expose_addr as simd_expose_provenance;
|
||||
#[cfg(bootstrap)]
|
||||
pub use simd_from_exposed_addr as simd_with_exposed_provenance;
|
||||
|
@ -136,7 +136,7 @@ impl<T: ?Sized> *const T {
|
||||
#[unstable(feature = "ptr_to_from_bits", issue = "91126")]
|
||||
#[deprecated(
|
||||
since = "1.67.0",
|
||||
note = "replaced by the `expose_addr` method, or update your code \
|
||||
note = "replaced by the `expose_provenance` method, or update your code \
|
||||
to follow the strict provenance rules using its APIs"
|
||||
)]
|
||||
#[inline(always)]
|
||||
@ -187,7 +187,7 @@ impl<T: ?Sized> *const T {
|
||||
///
|
||||
/// If using those APIs is not possible because there is no way to preserve a pointer with the
|
||||
/// required provenance, then Strict Provenance might not be for you. Use pointer-integer casts
|
||||
/// or [`expose_addr`][pointer::expose_addr] and [`with_exposed_provenance`][with_exposed_provenance]
|
||||
/// or [`expose_provenance`][pointer::expose_provenance] and [`with_exposed_provenance`][with_exposed_provenance]
|
||||
/// instead. However, note that this makes your code less portable and less amenable to tools
|
||||
/// that check for compliance with the Rust memory model.
|
||||
///
|
||||
@ -210,8 +210,8 @@ impl<T: ?Sized> *const T {
|
||||
unsafe { mem::transmute(self.cast::<()>()) }
|
||||
}
|
||||
|
||||
/// Gets the "address" portion of the pointer, and 'exposes' the "provenance" part for future
|
||||
/// use in [`with_exposed_provenance`][].
|
||||
/// Exposes the "provenance" part of the pointer for future use in
|
||||
/// [`with_exposed_provenance`][] and returns the "address" portion.
|
||||
///
|
||||
/// This is equivalent to `self as usize`, which semantically discards *provenance* and
|
||||
/// *address-space* information. Furthermore, this (like the `as` cast) has the implicit
|
||||
@ -238,7 +238,7 @@ impl<T: ?Sized> *const T {
|
||||
#[must_use]
|
||||
#[inline(always)]
|
||||
#[unstable(feature = "exposed_provenance", issue = "95228")]
|
||||
pub fn expose_addr(self) -> usize {
|
||||
pub fn expose_provenance(self) -> usize {
|
||||
// FIXME(strict_provenance_magic): I am magic and should be a compiler intrinsic.
|
||||
self.cast::<()>() as usize
|
||||
}
|
||||
|
@ -340,8 +340,8 @@
|
||||
//! clear where a satisfying unambiguous semantics can be defined for Exposed Provenance.
|
||||
//! Furthermore, Exposed Provenance will not work (well) with tools like [Miri] and [CHERI].
|
||||
//!
|
||||
//! Exposed Provenance is provided by the [`expose_addr`] and [`with_exposed_provenance`] methods, which
|
||||
//! are meant to replace `as` casts between pointers and integers. [`expose_addr`] is a lot like
|
||||
//! Exposed Provenance is provided by the [`expose_provenance`] and [`with_exposed_provenance`] methods,
|
||||
//! which are meant to replace `as` casts between pointers and integers. [`expose_provenance`] is a lot like
|
||||
//! [`addr`], but additionally adds the provenance of the pointer to a global list of 'exposed'
|
||||
//! provenances. (This list is purely conceptual, it exists for the purpose of specifying Rust but
|
||||
//! is not materialized in actual executions, except in tools like [Miri].) [`with_exposed_provenance`]
|
||||
@ -355,9 +355,9 @@
|
||||
//! there is *no* previously 'exposed' provenance that justifies the way the returned pointer will
|
||||
//! be used, the program has undefined behavior.
|
||||
//!
|
||||
//! Using [`expose_addr`] or [`with_exposed_provenance`] (or the `as` casts) means that code is
|
||||
//! Using [`expose_provenance`] or [`with_exposed_provenance`] (or the `as` casts) means that code is
|
||||
//! *not* following Strict Provenance rules. The goal of the Strict Provenance experiment is to
|
||||
//! determine how far one can get in Rust without the use of [`expose_addr`] and
|
||||
//! determine how far one can get in Rust without the use of [`expose_provenance`] and
|
||||
//! [`with_exposed_provenance`], and to encourage code to be written with Strict Provenance APIs only.
|
||||
//! Maximizing the amount of such code is a major win for avoiding specification complexity and to
|
||||
//! facilitate adoption of tools like [CHERI] and [Miri] that can be a big help in increasing the
|
||||
@ -374,7 +374,7 @@
|
||||
//! [`map_addr`]: pointer::map_addr
|
||||
//! [`addr`]: pointer::addr
|
||||
//! [`ptr::dangling`]: core::ptr::dangling
|
||||
//! [`expose_addr`]: pointer::expose_addr
|
||||
//! [`expose_provenance`]: pointer::expose_provenance
|
||||
//! [`with_exposed_provenance`]: with_exposed_provenance
|
||||
//! [Miri]: https://github.com/rust-lang/miri
|
||||
//! [CHERI]: https://www.cl.cam.ac.uk/research/security/ctsrd/cheri/
|
||||
@ -663,7 +663,7 @@ pub const fn dangling_mut<T>() -> *mut T {
|
||||
///
|
||||
/// This is a more rigorously specified alternative to `addr as *const T`. The provenance of the
|
||||
/// returned pointer is that of *any* pointer that was previously exposed by passing it to
|
||||
/// [`expose_addr`][pointer::expose_addr], or a `ptr as usize` cast. In addition, memory which is
|
||||
/// [`expose_provenance`][pointer::expose_provenance], or a `ptr as usize` cast. In addition, memory which is
|
||||
/// outside the control of the Rust abstract machine (MMIO registers, for example) is always
|
||||
/// considered to be exposed, so long as this memory is disjoint from memory that will be used by
|
||||
/// the abstract machine such as the stack, heap, and statics.
|
||||
@ -711,7 +711,7 @@ where
|
||||
///
|
||||
/// This is a more rigorously specified alternative to `addr as *mut T`. The provenance of the
|
||||
/// returned pointer is that of *any* pointer that was previously passed to
|
||||
/// [`expose_addr`][pointer::expose_addr] or a `ptr as usize` cast. If there is no previously
|
||||
/// [`expose_provenance`][pointer::expose_provenance] or a `ptr as usize` cast. If there is no previously
|
||||
/// 'exposed' provenance that justifies the way this pointer will be used, the program has undefined
|
||||
/// behavior. Note that there is no algorithm that decides which provenance will be used. You can
|
||||
/// think of this as "guessing" the right provenance, and the guess will be "maximally in your
|
||||
|
@ -142,7 +142,7 @@ impl<T: ?Sized> *mut T {
|
||||
#[unstable(feature = "ptr_to_from_bits", issue = "91126")]
|
||||
#[deprecated(
|
||||
since = "1.67.0",
|
||||
note = "replaced by the `expose_addr` method, or update your code \
|
||||
note = "replaced by the `expose_provenance` method, or update your code \
|
||||
to follow the strict provenance rules using its APIs"
|
||||
)]
|
||||
#[inline(always)]
|
||||
@ -194,7 +194,7 @@ impl<T: ?Sized> *mut T {
|
||||
///
|
||||
/// If using those APIs is not possible because there is no way to preserve a pointer with the
|
||||
/// required provenance, then Strict Provenance might not be for you. Use pointer-integer casts
|
||||
/// or [`expose_addr`][pointer::expose_addr] and [`with_exposed_provenance`][with_exposed_provenance]
|
||||
/// or [`expose_provenance`][pointer::expose_provenance] and [`with_exposed_provenance`][with_exposed_provenance]
|
||||
/// instead. However, note that this makes your code less portable and less amenable to tools
|
||||
/// that check for compliance with the Rust memory model.
|
||||
///
|
||||
@ -217,8 +217,8 @@ impl<T: ?Sized> *mut T {
|
||||
unsafe { mem::transmute(self.cast::<()>()) }
|
||||
}
|
||||
|
||||
/// Gets the "address" portion of the pointer, and 'exposes' the "provenance" part for future
|
||||
/// use in [`with_exposed_provenance`][].
|
||||
/// Exposes the "provenance" part of the pointer for future use in
|
||||
/// [`with_exposed_provenance`][] and returns the "address" portion.
|
||||
///
|
||||
/// This is equivalent to `self as usize`, which semantically discards *provenance* and
|
||||
/// *address-space* information. Furthermore, this (like the `as` cast) has the implicit
|
||||
@ -242,10 +242,9 @@ impl<T: ?Sized> *mut T {
|
||||
/// API and its claimed semantics are part of [Exposed Provenance][super#exposed-provenance].
|
||||
///
|
||||
/// [`with_exposed_provenance_mut`]: with_exposed_provenance_mut
|
||||
#[must_use]
|
||||
#[inline(always)]
|
||||
#[unstable(feature = "exposed_provenance", issue = "95228")]
|
||||
pub fn expose_addr(self) -> usize {
|
||||
pub fn expose_provenance(self) -> usize {
|
||||
// FIXME(strict_provenance_magic): I am magic and should be a compiler intrinsic.
|
||||
self.cast::<()>() as usize
|
||||
}
|
||||
|
@ -50,9 +50,9 @@ pub trait SimdConstPtr: Copy + Sealed {
|
||||
/// Equivalent to calling [`pointer::with_addr`] on each element.
|
||||
fn with_addr(self, addr: Self::Usize) -> Self;
|
||||
|
||||
/// Gets the "address" portion of the pointer, and "exposes" the provenance part for future use
|
||||
/// in [`Self::with_exposed_provenance`].
|
||||
fn expose_addr(self) -> Self::Usize;
|
||||
/// Exposes the "provenance" part of the pointer for future use in
|
||||
/// [`Self::with_exposed_provenance`] and returns the "address" portion.
|
||||
fn expose_provenance(self) -> Self::Usize;
|
||||
|
||||
/// Convert an address back to a pointer, picking up a previously "exposed" provenance.
|
||||
///
|
||||
@ -131,9 +131,9 @@ where
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn expose_addr(self) -> Self::Usize {
|
||||
fn expose_provenance(self) -> Self::Usize {
|
||||
// Safety: `self` is a pointer vector
|
||||
unsafe { core::intrinsics::simd::simd_expose_addr(self) }
|
||||
unsafe { core::intrinsics::simd::simd_expose_provenance(self) }
|
||||
}
|
||||
|
||||
#[inline]
|
||||
|
@ -47,9 +47,9 @@ pub trait SimdMutPtr: Copy + Sealed {
|
||||
/// Equivalent to calling [`pointer::with_addr`] on each element.
|
||||
fn with_addr(self, addr: Self::Usize) -> Self;
|
||||
|
||||
/// Gets the "address" portion of the pointer, and "exposes" the provenance part for future use
|
||||
/// in [`Self::with_exposed_provenance`].
|
||||
fn expose_addr(self) -> Self::Usize;
|
||||
/// Exposes the "provenance" part of the pointer for future use in
|
||||
/// [`Self::with_exposed_provenance`] and returns the "address" portion.
|
||||
fn expose_provenance(self) -> Self::Usize;
|
||||
|
||||
/// Convert an address back to a pointer, picking up a previously "exposed" provenance.
|
||||
///
|
||||
@ -128,9 +128,9 @@ where
|
||||
}
|
||||
|
||||
#[inline]
|
||||
fn expose_addr(self) -> Self::Usize {
|
||||
fn expose_provenance(self) -> Self::Usize {
|
||||
// Safety: `self` is a pointer vector
|
||||
unsafe { core::intrinsics::simd::simd_expose_addr(self) }
|
||||
unsafe { core::intrinsics::simd::simd_expose_provenance(self) }
|
||||
}
|
||||
|
||||
#[inline]
|
||||
|
@ -32,10 +32,10 @@ macro_rules! common_tests {
|
||||
);
|
||||
}
|
||||
|
||||
fn expose_addr<const LANES: usize>() {
|
||||
fn expose_provenance<const LANES: usize>() {
|
||||
test_helpers::test_unary_elementwise(
|
||||
&Simd::<*$constness u32, LANES>::expose_addr,
|
||||
&<*$constness u32>::expose_addr,
|
||||
&Simd::<*$constness u32, LANES>::expose_provenance,
|
||||
&<*$constness u32>::expose_provenance,
|
||||
&|_| true,
|
||||
);
|
||||
}
|
||||
|
@ -29,7 +29,7 @@ impl Thread {
|
||||
let p = Box::into_raw(Box::new(p));
|
||||
let tid = abi::spawn2(
|
||||
thread_start,
|
||||
p.expose_addr(),
|
||||
p.expose_provenance(),
|
||||
abi::Priority::into(abi::NORMAL_PRIO),
|
||||
stack,
|
||||
core_id,
|
||||
|
@ -181,7 +181,7 @@ impl Thread {
|
||||
abi::acre_tsk(&abi::T_CTSK {
|
||||
// Activate this task immediately
|
||||
tskatr: abi::TA_ACT,
|
||||
exinf: p_inner.as_ptr().expose_addr() as abi::EXINF,
|
||||
exinf: p_inner.as_ptr().expose_provenance() as abi::EXINF,
|
||||
// The entry point
|
||||
task: Some(trampoline),
|
||||
// Inherit the calling task's base priority
|
||||
|
@ -149,7 +149,7 @@ fn check_rvalue<'tcx>(
|
||||
Err((span, "unsizing casts are not allowed in const fn".into()))
|
||||
}
|
||||
},
|
||||
Rvalue::Cast(CastKind::PointerExposeAddress, _, _) => {
|
||||
Rvalue::Cast(CastKind::PointerExposeProvenance, _, _) => {
|
||||
Err((span, "casting pointers to ints is unstable in const fn".into()))
|
||||
},
|
||||
Rvalue::Cast(CastKind::DynStar, _, _) => {
|
||||
|
@ -18,8 +18,8 @@ use reuse_pool::ReusePool;
|
||||
|
||||
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
|
||||
pub enum ProvenanceMode {
|
||||
/// We support `expose_addr`/`with_exposed_provenance` via "wildcard" provenance.
|
||||
/// However, we want on `with_exposed_provenance` to alert the user of the precision loss.
|
||||
/// We support `expose_provenance`/`with_exposed_provenance` via "wildcard" provenance.
|
||||
/// However, we warn on `with_exposed_provenance` to alert the user of the precision loss.
|
||||
Default,
|
||||
/// Like `Default`, but without the warning.
|
||||
Permissive,
|
||||
|
@ -514,7 +514,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> {
|
||||
dest.transmute(this.machine.layouts.uint(dest.layout.size).unwrap(), this)?;
|
||||
this.write_int(res, &dest)?;
|
||||
}
|
||||
"cast" | "as" | "cast_ptr" | "expose_addr" | "with_exposed_provenance" => {
|
||||
"cast" | "as" | "cast_ptr" | "expose_provenance" | "with_exposed_provenance" => {
|
||||
let [op] = check_arg_count(args)?;
|
||||
let (op, op_len) = this.operand_to_simd(op)?;
|
||||
let (dest, dest_len) = this.mplace_to_simd(dest)?;
|
||||
@ -524,7 +524,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> {
|
||||
let unsafe_cast = intrinsic_name == "cast";
|
||||
let safe_cast = intrinsic_name == "as";
|
||||
let ptr_cast = intrinsic_name == "cast_ptr";
|
||||
let expose_cast = intrinsic_name == "expose_addr";
|
||||
let expose_cast = intrinsic_name == "expose_provenance";
|
||||
let from_exposed_cast = intrinsic_name == "with_exposed_provenance";
|
||||
|
||||
for i in 0..dest_len {
|
||||
@ -557,7 +557,7 @@ pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriInterpCxExt<'mir, 'tcx> {
|
||||
this.ptr_to_ptr(&op, dest.layout)?,
|
||||
// Ptr/Int casts
|
||||
(ty::RawPtr(..), ty::Int(_) | ty::Uint(_)) if expose_cast =>
|
||||
this.pointer_expose_address_cast(&op, dest.layout)?,
|
||||
this.pointer_expose_provenance_cast(&op, dest.layout)?,
|
||||
(ty::Int(_) | ty::Uint(_), ty::RawPtr(..)) if from_exposed_cast =>
|
||||
this.pointer_with_exposed_provenance_cast(&op, dest.layout)?,
|
||||
// Error otherwise
|
||||
|
@ -4,6 +4,6 @@
|
||||
fn main() {
|
||||
let x = 42;
|
||||
let xptr = &x as *const i32;
|
||||
let xptr_invalid = std::ptr::without_provenance::<i32>(xptr.expose_addr());
|
||||
let xptr_invalid = std::ptr::without_provenance::<i32>(xptr.expose_provenance());
|
||||
let _val = unsafe { *xptr_invalid }; //~ ERROR: is a dangling pointer
|
||||
}
|
||||
|
@ -6,7 +6,7 @@
|
||||
fn main() {
|
||||
let mut x = 0;
|
||||
let _fool = &mut x as *mut i32; // this would have fooled the old untagged pointer logic
|
||||
let addr = (&x as *const i32).expose_addr();
|
||||
let addr = (&x as *const i32).expose_provenance();
|
||||
let ptr = std::ptr::with_exposed_provenance_mut::<i32>(addr);
|
||||
unsafe { *ptr = 0 }; //~ ERROR: /write access using <wildcard> .* no exposed tags have suitable permission in the borrow stack/
|
||||
}
|
||||
|
@ -7,6 +7,6 @@ use std::simd::prelude::*;
|
||||
fn main() {
|
||||
// Pointer casts
|
||||
let _val: Simd<*const u8, 4> = Simd::<*const i32, 4>::splat(ptr::null()).cast();
|
||||
let addrs = Simd::<*const i32, 4>::splat(ptr::null()).expose_addr();
|
||||
let addrs = Simd::<*const i32, 4>::splat(ptr::null()).expose_provenance();
|
||||
let _ptrs = Simd::<*const i32, 4>::with_exposed_provenance(addrs);
|
||||
}
|
||||
|
@ -10,7 +10,7 @@ fn ptr_roundtrip_out_of_bounds() {
|
||||
let x: i32 = 3;
|
||||
let x_ptr = &x as *const i32;
|
||||
|
||||
let x_usize = x_ptr.wrapping_offset(128).expose_addr();
|
||||
let x_usize = x_ptr.wrapping_offset(128).expose_provenance();
|
||||
|
||||
let ptr = ptr::with_exposed_provenance::<i32>(x_usize).wrapping_offset(-128);
|
||||
assert_eq!(unsafe { *ptr }, 3);
|
||||
@ -24,8 +24,8 @@ fn ptr_roundtrip_confusion() {
|
||||
let x_ptr = &x as *const i32;
|
||||
let y_ptr = &y as *const i32;
|
||||
|
||||
let x_usize = x_ptr.expose_addr();
|
||||
let y_usize = y_ptr.expose_addr();
|
||||
let x_usize = x_ptr.expose_provenance();
|
||||
let y_usize = y_ptr.expose_provenance();
|
||||
|
||||
let ptr = ptr::with_exposed_provenance::<i32>(y_usize);
|
||||
let ptr = ptr.with_addr(x_usize);
|
||||
@ -37,7 +37,7 @@ fn ptr_roundtrip_imperfect() {
|
||||
let x: u8 = 3;
|
||||
let x_ptr = &x as *const u8;
|
||||
|
||||
let x_usize = x_ptr.expose_addr() + 128;
|
||||
let x_usize = x_ptr.expose_provenance() + 128;
|
||||
|
||||
let ptr = ptr::with_exposed_provenance::<u8>(x_usize).wrapping_offset(-128);
|
||||
assert_eq!(unsafe { *ptr }, 3);
|
||||
@ -48,7 +48,7 @@ fn ptr_roundtrip_null() {
|
||||
let x = &42;
|
||||
let x_ptr = x as *const i32;
|
||||
let x_null_ptr = x_ptr.with_addr(0); // addr 0, but still the provenance of x
|
||||
let null = x_null_ptr.expose_addr();
|
||||
let null = x_null_ptr.expose_provenance();
|
||||
assert_eq!(null, 0);
|
||||
|
||||
let x_null_ptr_copy = ptr::with_exposed_provenance::<i32>(null); // just a roundtrip, so has provenance of x (angelically)
|
||||
|
@ -17,7 +17,7 @@ fn example(variant: bool) {
|
||||
unsafe {
|
||||
fn not_so_innocent(x: &mut u32) -> usize {
|
||||
let x_raw4 = x as *mut u32;
|
||||
x_raw4.expose_addr()
|
||||
x_raw4.expose_provenance()
|
||||
}
|
||||
|
||||
let mut c = 42u32;
|
||||
@ -26,7 +26,7 @@ fn example(variant: bool) {
|
||||
// stack: [..., Unique(1)]
|
||||
|
||||
let x_raw2 = x_unique1 as *mut u32;
|
||||
let x_raw2_addr = x_raw2.expose_addr();
|
||||
let x_raw2_addr = x_raw2.expose_provenance();
|
||||
// stack: [..., Unique(1), SharedRW(2)]
|
||||
|
||||
let x_unique3 = &mut *x_raw2;
|
||||
|
@ -9,7 +9,7 @@ fn main() {
|
||||
|
||||
// Expose the allocation and use the exposed pointer, creating an unknown bottom
|
||||
unsafe {
|
||||
let p: *mut u8 = ptr::with_exposed_provenance::<u8>(ptr.expose_addr()) as *mut u8;
|
||||
let p: *mut u8 = ptr::with_exposed_provenance::<u8>(ptr.expose_provenance()) as *mut u8;
|
||||
*p = 1;
|
||||
}
|
||||
|
||||
|
@ -19,7 +19,7 @@
|
||||
StorageLive(_3);
|
||||
_3 = const main::FOO;
|
||||
_2 = &raw const (*_3);
|
||||
_1 = move _2 as usize (PointerExposeAddress);
|
||||
_1 = move _2 as usize (PointerExposeProvenance);
|
||||
StorageDead(_2);
|
||||
StorageDead(_3);
|
||||
StorageLive(_4);
|
@ -19,7 +19,7 @@
|
||||
StorageLive(_3);
|
||||
_3 = const main::FOO;
|
||||
_2 = &raw const (*_3);
|
||||
_1 = move _2 as usize (PointerExposeAddress);
|
||||
_1 = move _2 as usize (PointerExposeProvenance);
|
||||
StorageDead(_2);
|
||||
StorageDead(_3);
|
||||
StorageLive(_4);
|
@ -4,12 +4,12 @@
|
||||
#[inline(never)]
|
||||
fn read(_: usize) { }
|
||||
|
||||
// EMIT_MIR pointer_expose_address.main.GVN.diff
|
||||
// EMIT_MIR pointer_expose_provenance.main.GVN.diff
|
||||
fn main() {
|
||||
// CHECK-LABEL: fn main(
|
||||
// CHECK: [[ptr:_.*]] = const main::FOO;
|
||||
// CHECK: [[ref:_.*]] = &raw const (*[[ptr]]);
|
||||
// CHECK: [[x:_.*]] = move [[ref]] as usize (PointerExposeAddress);
|
||||
// CHECK: [[x:_.*]] = move [[ref]] as usize (PointerExposeProvenance);
|
||||
// CHECK: = read([[x]])
|
||||
const FOO: &i32 = &1;
|
||||
let x = FOO as *const i32 as usize;
|
@ -14,7 +14,7 @@
|
||||
StorageLive(_2);
|
||||
StorageLive(_3);
|
||||
_3 = main as fn() (PointerCoercion(ReifyFnPointer));
|
||||
_2 = move _3 as usize (PointerExposeAddress);
|
||||
_2 = move _3 as usize (PointerExposeProvenance);
|
||||
StorageDead(_3);
|
||||
_1 = move _2 as *const fn() (PointerWithExposedProvenance);
|
||||
StorageDead(_2);
|
||||
|
@ -4,7 +4,7 @@
|
||||
fn main() {
|
||||
// CHECK-LABEL: fn main(
|
||||
// CHECK: [[ptr:_.*]] = main as fn() (PointerCoercion(ReifyFnPointer));
|
||||
// CHECK: [[addr:_.*]] = move [[ptr]] as usize (PointerExposeAddress);
|
||||
// CHECK: [[addr:_.*]] = move [[ptr]] as usize (PointerExposeProvenance);
|
||||
// CHECK: [[back:_.*]] = move [[addr]] as *const fn() (PointerWithExposedProvenance);
|
||||
let _ = main as usize as *const fn();
|
||||
}
|
||||
|
@ -19,12 +19,12 @@
|
||||
StorageLive(_2);
|
||||
StorageLive(_3);
|
||||
_3 = _1;
|
||||
_2 = move _3 as usize (PointerExposeAddress);
|
||||
_2 = move _3 as usize (PointerExposeProvenance);
|
||||
StorageDead(_3);
|
||||
StorageLive(_4);
|
||||
StorageLive(_5);
|
||||
_5 = _1;
|
||||
_4 = move _5 as isize (PointerExposeAddress);
|
||||
_4 = move _5 as isize (PointerExposeProvenance);
|
||||
StorageDead(_5);
|
||||
_0 = const ();
|
||||
StorageDead(_4);
|
||||
|
@ -5,8 +5,8 @@
|
||||
// EMIT_MIR provenance_soundness.pointer_to_int.DeadStoreElimination-initial.diff
|
||||
fn pointer_to_int(p: *mut i32) {
|
||||
// CHECK-LABEL: fn pointer_to_int(
|
||||
// CHECK: {{_.*}} = {{.*}} as usize (PointerExposeAddress);
|
||||
// CHECK: {{_.*}} = {{.*}} as isize (PointerExposeAddress);
|
||||
// CHECK: {{_.*}} = {{.*}} as usize (PointerExposeProvenance);
|
||||
// CHECK: {{_.*}} = {{.*}} as isize (PointerExposeProvenance);
|
||||
let _x = p as usize;
|
||||
let _y = p as isize;
|
||||
}
|
||||
|
@ -1,7 +1,7 @@
|
||||
- // MIR for `expose_addr` before SimplifyLocals-before-const-prop
|
||||
+ // MIR for `expose_addr` after SimplifyLocals-before-const-prop
|
||||
- // MIR for `expose_provenance` before SimplifyLocals-before-const-prop
|
||||
+ // MIR for `expose_provenance` after SimplifyLocals-before-const-prop
|
||||
|
||||
fn expose_addr(_1: *const usize) -> () {
|
||||
fn expose_provenance(_1: *const usize) -> () {
|
||||
debug p => _1;
|
||||
let mut _0: ();
|
||||
let _2: usize;
|
||||
@ -11,7 +11,7 @@
|
||||
StorageLive(_2);
|
||||
StorageLive(_3);
|
||||
_3 = _1;
|
||||
_2 = move _3 as usize (PointerExposeAddress);
|
||||
_2 = move _3 as usize (PointerExposeProvenance);
|
||||
StorageDead(_3);
|
||||
StorageDead(_2);
|
||||
_0 = const ();
|
@ -63,8 +63,8 @@ fn t4() -> u32 {
|
||||
unsafe { X + 1 }
|
||||
}
|
||||
|
||||
// EMIT_MIR simplify_locals.expose_addr.SimplifyLocals-before-const-prop.diff
|
||||
fn expose_addr(p: *const usize) {
|
||||
// EMIT_MIR simplify_locals.expose_provenance.SimplifyLocals-before-const-prop.diff
|
||||
fn expose_provenance(p: *const usize) {
|
||||
// Used pointer to address cast. Has a side effect of exposing the provenance.
|
||||
p as usize;
|
||||
}
|
||||
@ -78,5 +78,5 @@ fn main() {
|
||||
t2();
|
||||
t3();
|
||||
t4();
|
||||
expose_addr(&0);
|
||||
expose_provenance(&0);
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ error: under strict provenance it is considered bad style to cast pointer `*cons
|
||||
LL | let addr: usize = &x as *const u8 as usize;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_addr()` instead
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_provenance()` instead
|
||||
note: the lint level is defined here
|
||||
--> $DIR/lint-strict-provenance-lossy-casts.rs:2:9
|
||||
|
|
||||
@ -21,7 +21,7 @@ error: under strict provenance it is considered bad style to cast pointer `*cons
|
||||
LL | let addr_32bit = &x as *const u8 as u32;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_addr()` instead
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_provenance()` instead
|
||||
help: use `.addr()` to obtain the address of a pointer
|
||||
|
|
||||
LL | let addr_32bit = (&x as *const u8).addr() as u32;
|
||||
@ -35,7 +35,7 @@ LL | let ptr_addr = ptr as usize;
|
||||
| |
|
||||
| help: use `.addr()` to obtain the address of a pointer: `.addr()`
|
||||
|
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_addr()` instead
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_provenance()` instead
|
||||
|
||||
error: under strict provenance it is considered bad style to cast pointer `*const u8` to integer `u32`
|
||||
--> $DIR/lint-strict-provenance-lossy-casts.rs:16:26
|
||||
@ -45,7 +45,7 @@ LL | let ptr_addr_32bit = ptr as u32;
|
||||
| |
|
||||
| help: use `.addr()` to obtain the address of a pointer: `.addr() as u32`
|
||||
|
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_addr()` instead
|
||||
= help: if you can't comply with strict provenance and need to expose the pointer provenance you can use `.expose_provenance()` instead
|
||||
|
||||
error: aborting due to 4 previous errors
|
||||
|
||||
|
@ -4,7 +4,7 @@
|
||||
|
||||
extern "rust-intrinsic" {
|
||||
fn simd_cast_ptr<T, U>(x: T) -> U;
|
||||
fn simd_expose_addr<T, U>(x: T) -> U;
|
||||
fn simd_expose_provenance<T, U>(x: T) -> U;
|
||||
fn simd_with_exposed_provenance<T, U>(x: T) -> U;
|
||||
}
|
||||
|
||||
@ -22,7 +22,7 @@ fn main() {
|
||||
// change constness and type
|
||||
let const_ptrs: V<*const u8> = simd_cast_ptr(ptrs);
|
||||
|
||||
let exposed_addr: V<usize> = simd_expose_addr(const_ptrs);
|
||||
let exposed_addr: V<usize> = simd_expose_provenance(const_ptrs);
|
||||
|
||||
let with_exposed_provenance: V<*mut i8> = simd_with_exposed_provenance(exposed_addr);
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user