1
Fork 0

Rollup merge of #86517 - camsteffen:unused-unsafe-async, r=LeSeulArtichaut

Fix `unused_unsafe` around `await`

Enables `unused_unsafe` lint for `unsafe { future.await }`.

The existing test for this is `unsafe { println!() }`, so I assume that `println!` used to contain compiler-generated unsafe but this is no longer true, and so the existing test is broken. I replaced the test with `unsafe { ...await }`. I believe `await` is currently the only instance of compiler-generated unsafe.

Reverts some parts of #85421, but the issue predates that PR.
This commit is contained in:
Yuki Okushi 2021-06-22 20:01:05 +09:00 committed by GitHub
commit 8ec4e7dfdd
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
9 changed files with 43 additions and 25 deletions

View file

@ -214,6 +214,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
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 => {}

View file

@ -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 @@ impl<'tcx> UnsafetyVisitor<'_, 'tcx> {
);
}
self.safety_context = prev_context;
return;
}
}
@ -71,6 +66,7 @@ impl<'tcx> UnsafetyVisitor<'_, 'tcx> {
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 @@ impl<'a, 'tcx> Visitor<'a, 'tcx> for UnsafetyVisitor<'a, '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 @@ impl<'a, 'tcx> Visitor<'a, 'tcx> for UnsafetyVisitor<'a, 'tcx> {
#[derive(Clone, Copy)]
enum SafetyContext {
Safe,
BuiltinUnsafeBlock,
UnsafeFn,
UnsafeBlock { span: Span, hir_id: hir::HirId, used: bool },
}

View file

@ -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)
}
},
}
}