Check for ptr-to-int casts in const functions in THIR unsafeck
This commit is contained in:
parent
592fecbafb
commit
6b327aaa08
6 changed files with 105 additions and 14 deletions
|
@ -25,6 +25,7 @@ struct UnsafetyVisitor<'a, 'tcx> {
|
||||||
/// The `#[target_feature]` attributes of the body. Used for checking
|
/// The `#[target_feature]` attributes of the body. Used for checking
|
||||||
/// calls to functions with `#[target_feature]` (RFC 2396).
|
/// calls to functions with `#[target_feature]` (RFC 2396).
|
||||||
body_target_features: &'tcx Vec<Symbol>,
|
body_target_features: &'tcx Vec<Symbol>,
|
||||||
|
is_const: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'tcx> UnsafetyVisitor<'_, 'tcx> {
|
impl<'tcx> UnsafetyVisitor<'_, 'tcx> {
|
||||||
|
@ -187,6 +188,16 @@ impl<'a, 'tcx> Visitor<'a, 'tcx> for UnsafetyVisitor<'a, 'tcx> {
|
||||||
(Bound::Unbounded, Bound::Unbounded) => {}
|
(Bound::Unbounded, Bound::Unbounded) => {}
|
||||||
_ => self.requires_unsafe(expr.span, InitializingTypeWith),
|
_ => self.requires_unsafe(expr.span, InitializingTypeWith),
|
||||||
},
|
},
|
||||||
|
ExprKind::Cast { source } => {
|
||||||
|
let source = &self.thir[source];
|
||||||
|
if self.tcx.features().const_raw_ptr_to_usize_cast
|
||||||
|
&& self.is_const
|
||||||
|
&& (source.ty.is_unsafe_ptr() || source.ty.is_fn_ptr())
|
||||||
|
&& expr.ty.is_integral()
|
||||||
|
{
|
||||||
|
self.requires_unsafe(expr.span, CastOfPointerToInt);
|
||||||
|
}
|
||||||
|
}
|
||||||
_ => {}
|
_ => {}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -230,7 +241,6 @@ enum UnsafeOpKind {
|
||||||
CallToUnsafeFunction,
|
CallToUnsafeFunction,
|
||||||
UseOfInlineAssembly,
|
UseOfInlineAssembly,
|
||||||
InitializingTypeWith,
|
InitializingTypeWith,
|
||||||
#[allow(dead_code)] // FIXME
|
|
||||||
CastOfPointerToInt,
|
CastOfPointerToInt,
|
||||||
#[allow(dead_code)] // FIXME
|
#[allow(dead_code)] // FIXME
|
||||||
UseOfMutableStatic,
|
UseOfMutableStatic,
|
||||||
|
@ -331,6 +341,11 @@ pub fn check_unsafety<'tcx>(
|
||||||
let body_target_features = &tcx.codegen_fn_attrs(def_id).target_features;
|
let body_target_features = &tcx.codegen_fn_attrs(def_id).target_features;
|
||||||
let safety_context =
|
let safety_context =
|
||||||
if body_unsafety.is_unsafe() { SafetyContext::UnsafeFn } else { SafetyContext::Safe };
|
if body_unsafety.is_unsafe() { SafetyContext::UnsafeFn } else { SafetyContext::Safe };
|
||||||
|
let is_const = match tcx.hir().body_owner_kind(hir_id) {
|
||||||
|
hir::BodyOwnerKind::Closure => false,
|
||||||
|
hir::BodyOwnerKind::Fn => tcx.is_const_fn_raw(def_id.to_def_id()),
|
||||||
|
hir::BodyOwnerKind::Const | hir::BodyOwnerKind::Static(_) => true,
|
||||||
|
};
|
||||||
let mut visitor = UnsafetyVisitor {
|
let mut visitor = UnsafetyVisitor {
|
||||||
tcx,
|
tcx,
|
||||||
thir,
|
thir,
|
||||||
|
@ -338,6 +353,7 @@ pub fn check_unsafety<'tcx>(
|
||||||
hir_context: hir_id,
|
hir_context: hir_id,
|
||||||
body_unsafety,
|
body_unsafety,
|
||||||
body_target_features,
|
body_target_features,
|
||||||
|
is_const,
|
||||||
};
|
};
|
||||||
visitor.visit_expr(&thir[expr]);
|
visitor.visit_expr(&thir[expr]);
|
||||||
}
|
}
|
||||||
|
|
19
src/test/ui/cast/cast-ptr-to-int-const.mir.stderr
Normal file
19
src/test/ui/cast/cast-ptr-to-int-const.mir.stderr
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
error[E0133]: cast of pointer to int is unsafe and requires unsafe function or block
|
||||||
|
--> $DIR/cast-ptr-to-int-const.rs:10:9
|
||||||
|
|
|
||||||
|
LL | &Y as *const u32 as usize
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^ cast of pointer to int
|
||||||
|
|
|
||||||
|
= note: casting pointers to integers in constants
|
||||||
|
|
||||||
|
error[E0133]: cast of pointer to int is unsafe and requires unsafe function or block
|
||||||
|
--> $DIR/cast-ptr-to-int-const.rs:17:5
|
||||||
|
|
|
||||||
|
LL | &0 as *const i32 as usize
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^ cast of pointer to int
|
||||||
|
|
|
||||||
|
= note: casting pointers to integers in constants
|
||||||
|
|
||||||
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
|
For more information about this error, try `rustc --explain E0133`.
|
|
@ -1,25 +1,19 @@
|
||||||
// gate-test-const_raw_ptr_to_usize_cast
|
// revisions: mir thir
|
||||||
// revisions: with_feature without_feature
|
// [thir]compile-flags: -Z thir-unsafeck
|
||||||
|
|
||||||
#![cfg_attr(with_feature, feature(const_raw_ptr_to_usize_cast))]
|
#![feature(const_raw_ptr_to_usize_cast)]
|
||||||
|
|
||||||
fn main() {
|
fn main() {
|
||||||
const X: usize = unsafe {
|
|
||||||
main as usize //[without_feature]~ ERROR casting pointers to integers in constants is unstable
|
|
||||||
};
|
|
||||||
const Y: u32 = 0;
|
const Y: u32 = 0;
|
||||||
const Z: usize = unsafe {
|
|
||||||
&Y as *const u32 as usize //[without_feature]~ ERROR is unstable
|
|
||||||
};
|
|
||||||
// Cast in `const` without `unsafe` block
|
// Cast in `const` without `unsafe` block
|
||||||
const SAFE: usize = {
|
const SAFE: usize = {
|
||||||
&Y as *const u32 as usize //[without_feature]~ ERROR is unstable
|
&Y as *const u32 as usize
|
||||||
//[with_feature]~^ ERROR cast of pointer to int is unsafe and requires unsafe
|
//~^ ERROR cast of pointer to int is unsafe and requires unsafe
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
// Cast in `const fn` without `unsafe` block
|
// Cast in `const fn` without `unsafe` block
|
||||||
const fn test() -> usize {
|
const fn test() -> usize {
|
||||||
&0 as *const i32 as usize //[without_feature]~ ERROR is unstable
|
&0 as *const i32 as usize
|
||||||
//[with_feature]~^ ERROR cast of pointer to int is unsafe and requires unsafe
|
//~^ ERROR cast of pointer to int is unsafe and requires unsafe
|
||||||
}
|
}
|
||||||
|
|
19
src/test/ui/cast/cast-ptr-to-int-const.thir.stderr
Normal file
19
src/test/ui/cast/cast-ptr-to-int-const.thir.stderr
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
error[E0133]: cast of pointer to int is unsafe and requires unsafe function or block
|
||||||
|
--> $DIR/cast-ptr-to-int-const.rs:10:9
|
||||||
|
|
|
||||||
|
LL | &Y as *const u32 as usize
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^ cast of pointer to int
|
||||||
|
|
|
||||||
|
= note: casting pointers to integers in constants
|
||||||
|
|
||||||
|
error[E0133]: cast of pointer to int is unsafe and requires unsafe function or block
|
||||||
|
--> $DIR/cast-ptr-to-int-const.rs:17:5
|
||||||
|
|
|
||||||
|
LL | &0 as *const i32 as usize
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^ cast of pointer to int
|
||||||
|
|
|
||||||
|
= note: casting pointers to integers in constants
|
||||||
|
|
||||||
|
error: aborting due to 2 previous errors
|
||||||
|
|
||||||
|
For more information about this error, try `rustc --explain E0133`.
|
13
src/test/ui/cast/feature-gate-const_raw_ptr_to_usize_cast.rs
Normal file
13
src/test/ui/cast/feature-gate-const_raw_ptr_to_usize_cast.rs
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
fn main() {
|
||||||
|
const X: usize = unsafe {
|
||||||
|
main as usize //~ ERROR casting pointers to integers in constants is unstable
|
||||||
|
};
|
||||||
|
const Y: u32 = 0;
|
||||||
|
const Z: usize = unsafe {
|
||||||
|
&Y as *const u32 as usize //~ ERROR is unstable
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
const fn test() -> usize {
|
||||||
|
&0 as *const i32 as usize //~ ERROR is unstable
|
||||||
|
}
|
|
@ -0,0 +1,30 @@
|
||||||
|
error[E0658]: casting pointers to integers in constants is unstable
|
||||||
|
--> $DIR/feature-gate-const_raw_ptr_to_usize_cast.rs:3:9
|
||||||
|
|
|
||||||
|
LL | main as usize
|
||||||
|
| ^^^^^^^^^^^^^
|
||||||
|
|
|
||||||
|
= note: see issue #51910 <https://github.com/rust-lang/rust/issues/51910> for more information
|
||||||
|
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
|
||||||
|
|
||||||
|
error[E0658]: casting pointers to integers in constants is unstable
|
||||||
|
--> $DIR/feature-gate-const_raw_ptr_to_usize_cast.rs:7:9
|
||||||
|
|
|
||||||
|
LL | &Y as *const u32 as usize
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
||||||
|
= note: see issue #51910 <https://github.com/rust-lang/rust/issues/51910> for more information
|
||||||
|
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
|
||||||
|
|
||||||
|
error[E0658]: casting pointers to integers in constant functions is unstable
|
||||||
|
--> $DIR/feature-gate-const_raw_ptr_to_usize_cast.rs:12:5
|
||||||
|
|
|
||||||
|
LL | &0 as *const i32 as usize
|
||||||
|
| ^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||||
|
|
|
||||||
|
= note: see issue #51910 <https://github.com/rust-lang/rust/issues/51910> for more information
|
||||||
|
= help: add `#![feature(const_raw_ptr_to_usize_cast)]` to the crate attributes to enable
|
||||||
|
|
||||||
|
error: aborting due to 3 previous errors
|
||||||
|
|
||||||
|
For more information about this error, try `rustc --explain E0658`.
|
Loading…
Add table
Add a link
Reference in a new issue