Fix unused_unsafe with compiler-generated unsafe
This commit is contained in:
parent
39260f6d49
commit
b07bb6d698
@ -494,6 +494,8 @@ pub fn generator_kind(&self) -> Option<GeneratorKind> {
|
||||
#[derive(Copy, Clone, PartialEq, Eq, Debug, TyEncodable, TyDecodable, HashStable)]
|
||||
pub enum Safety {
|
||||
Safe,
|
||||
/// Unsafe because of compiler-generated unsafe code, like `await` desugaring
|
||||
BuiltinUnsafe,
|
||||
/// Unsafe because of an unsafe fn
|
||||
FnUnsafe,
|
||||
/// Unsafe because of an `unsafe` block
|
||||
|
@ -114,6 +114,7 @@ pub struct Adt<'tcx> {
|
||||
#[derive(Copy, Clone, Debug, HashStable)]
|
||||
pub enum BlockSafety {
|
||||
Safe,
|
||||
BuiltinUnsafe,
|
||||
ExplicitUnsafe(hir::HirId),
|
||||
}
|
||||
|
||||
|
@ -321,6 +321,7 @@ fn register_violations(
|
||||
}
|
||||
false
|
||||
}
|
||||
Safety::BuiltinUnsafe => true,
|
||||
Safety::ExplicitUnsafe(hir_id) => {
|
||||
// mark unsafe block as used if there are any unsafe operations inside
|
||||
if !violations.is_empty() {
|
||||
|
@ -214,6 +214,7 @@ fn update_source_scope_for_safety_mode(&mut self, span: Span, safety_mode: Block
|
||||
debug!("update_source_scope_for({:?}, {:?})", span, safety_mode);
|
||||
let new_unsafety = match safety_mode {
|
||||
BlockSafety::Safe => None,
|
||||
BlockSafety::BuiltinUnsafe => Some(Safety::BuiltinUnsafe),
|
||||
BlockSafety::ExplicitUnsafe(hir_id) => {
|
||||
match self.in_scope_unsafe {
|
||||
Safety::Safe => {}
|
||||
|
@ -29,11 +29,7 @@ struct UnsafetyVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'tcx> UnsafetyVisitor<'_, 'tcx> {
|
||||
fn in_safety_context<R>(
|
||||
&mut self,
|
||||
safety_context: SafetyContext,
|
||||
f: impl FnOnce(&mut Self) -> R,
|
||||
) {
|
||||
fn in_safety_context(&mut self, safety_context: SafetyContext, f: impl FnOnce(&mut Self)) {
|
||||
if let (
|
||||
SafetyContext::UnsafeBlock { span: enclosing_span, .. },
|
||||
SafetyContext::UnsafeBlock { span: block_span, hir_id, .. },
|
||||
@ -63,7 +59,6 @@ fn in_safety_context<R>(
|
||||
);
|
||||
}
|
||||
self.safety_context = prev_context;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
@ -71,6 +66,7 @@ fn requires_unsafe(&mut self, span: Span, kind: UnsafeOpKind) {
|
||||
let (description, note) = kind.description_and_note();
|
||||
let unsafe_op_in_unsafe_fn_allowed = self.unsafe_op_in_unsafe_fn_allowed();
|
||||
match self.safety_context {
|
||||
SafetyContext::BuiltinUnsafeBlock => {}
|
||||
SafetyContext::UnsafeBlock { ref mut used, .. } => {
|
||||
if !self.body_unsafety.is_unsafe() || !unsafe_op_in_unsafe_fn_allowed {
|
||||
// Mark this block as useful
|
||||
@ -142,13 +138,23 @@ fn thir(&self) -> &'a Thir<'tcx> {
|
||||
}
|
||||
|
||||
fn visit_block(&mut self, block: &Block) {
|
||||
if let BlockSafety::ExplicitUnsafe(hir_id) = block.safety_mode {
|
||||
self.in_safety_context(
|
||||
SafetyContext::UnsafeBlock { span: block.span, hir_id, used: false },
|
||||
|this| visit::walk_block(this, block),
|
||||
);
|
||||
} else {
|
||||
visit::walk_block(self, block);
|
||||
match block.safety_mode {
|
||||
// compiler-generated unsafe code should not count towards the usefulness of
|
||||
// an outer unsafe block
|
||||
BlockSafety::BuiltinUnsafe => {
|
||||
self.in_safety_context(SafetyContext::BuiltinUnsafeBlock, |this| {
|
||||
visit::walk_block(this, block)
|
||||
});
|
||||
}
|
||||
BlockSafety::ExplicitUnsafe(hir_id) => {
|
||||
self.in_safety_context(
|
||||
SafetyContext::UnsafeBlock { span: block.span, hir_id, used: false },
|
||||
|this| visit::walk_block(this, block),
|
||||
);
|
||||
}
|
||||
BlockSafety::Safe => {
|
||||
visit::walk_block(self, block);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -250,6 +256,7 @@ fn visit_expr(&mut self, expr: &Expr<'tcx>) {
|
||||
#[derive(Clone, Copy)]
|
||||
enum SafetyContext {
|
||||
Safe,
|
||||
BuiltinUnsafeBlock,
|
||||
UnsafeFn,
|
||||
UnsafeBlock { span: Span, hir_id: hir::HirId, used: bool },
|
||||
}
|
||||
|
@ -26,7 +26,12 @@ impl<'tcx> Cx<'tcx> {
|
||||
expr: block.expr.map(|expr| self.mirror_expr(expr)),
|
||||
safety_mode: match block.rules {
|
||||
hir::BlockCheckMode::DefaultBlock => BlockSafety::Safe,
|
||||
hir::BlockCheckMode::UnsafeBlock(..) => BlockSafety::ExplicitUnsafe(block.hir_id),
|
||||
hir::BlockCheckMode::UnsafeBlock(hir::UnsafeSource::CompilerGenerated) => {
|
||||
BlockSafety::BuiltinUnsafe
|
||||
}
|
||||
hir::BlockCheckMode::UnsafeBlock(hir::UnsafeSource::UserProvided) => {
|
||||
BlockSafety::ExplicitUnsafe(block.hir_id)
|
||||
}
|
||||
},
|
||||
}
|
||||
}
|
||||
|
@ -1,11 +1,11 @@
|
||||
error: unnecessary `unsafe` block
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:9:5
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:9:9
|
||||
|
|
||||
LL | unsafe { println!("foo"); }
|
||||
| ^^^^^^ unnecessary `unsafe` block
|
||||
LL | unsafe { async {}.await; }
|
||||
| ^^^^^^ unnecessary `unsafe` block
|
||||
|
|
||||
note: the lint level is defined here
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:6:9
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:5:9
|
||||
|
|
||||
LL | #![deny(unused_unsafe)]
|
||||
| ^^^^^^^^^^^^^
|
||||
|
@ -1,10 +1,11 @@
|
||||
// issue #12418
|
||||
|
||||
// edition:2018
|
||||
// revisions: mir thir
|
||||
// [thir]compile-flags: -Z thir-unsafeck
|
||||
|
||||
#![deny(unused_unsafe)]
|
||||
|
||||
fn main() {
|
||||
unsafe { println!("foo"); } //~ ERROR unnecessary `unsafe`
|
||||
let _ = async {
|
||||
unsafe { async {}.await; } //~ ERROR unnecessary `unsafe`
|
||||
};
|
||||
}
|
||||
|
@ -1,11 +1,11 @@
|
||||
error: unnecessary `unsafe` block
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:9:5
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:9:9
|
||||
|
|
||||
LL | unsafe { println!("foo"); }
|
||||
| ^^^^^^ unnecessary `unsafe` block
|
||||
LL | unsafe { async {}.await; }
|
||||
| ^^^^^^ unnecessary `unsafe` block
|
||||
|
|
||||
note: the lint level is defined here
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:6:9
|
||||
--> $DIR/unsafe-around-compiler-generated-unsafe.rs:5:9
|
||||
|
|
||||
LL | #![deny(unused_unsafe)]
|
||||
| ^^^^^^^^^^^^^
|
||||
|
Loading…
Reference in New Issue
Block a user