|
1 | 1 | use rustc_data_structures::fx::FxHashSet;
|
2 | 2 | use rustc_errors::struct_span_err;
|
3 | 3 | use rustc_hir as hir;
|
| 4 | +use rustc_hir::def::DefKind; |
4 | 5 | use rustc_hir::def_id::{DefId, LocalDefId};
|
5 | 6 | use rustc_hir::hir_id::HirId;
|
6 | 7 | use rustc_hir::intravisit;
|
@@ -134,6 +135,28 @@ impl<'tcx> Visitor<'tcx> for UnsafetyChecker<'_, 'tcx> {
|
134 | 135 | self.super_rvalue(rvalue, location);
|
135 | 136 | }
|
136 | 137 |
|
| 138 | + fn visit_operand(&mut self, op: &Operand<'tcx>, location: Location) { |
| 139 | + if let Operand::Constant(constant) = op { |
| 140 | + let maybe_uneval = match constant.literal { |
| 141 | + ConstantKind::Val(..) | ConstantKind::Ty(_) => None, |
| 142 | + ConstantKind::Unevaluated(uv, _) => Some(uv), |
| 143 | + }; |
| 144 | + |
| 145 | + if let Some(uv) = maybe_uneval { |
| 146 | + if uv.promoted.is_none() { |
| 147 | + let def_id = uv.def.def_id_for_type_of(); |
| 148 | + if self.tcx.def_kind(def_id) == DefKind::InlineConst { |
| 149 | + let local_def_id = def_id.expect_local(); |
| 150 | + let UnsafetyCheckResult { violations, used_unsafe_blocks, .. } = |
| 151 | + self.tcx.unsafety_check_result(local_def_id); |
| 152 | + self.register_violations(violations, used_unsafe_blocks.iter().copied()); |
| 153 | + } |
| 154 | + } |
| 155 | + } |
| 156 | + } |
| 157 | + self.super_operand(op, location); |
| 158 | + } |
| 159 | + |
137 | 160 | fn visit_place(&mut self, place: &Place<'tcx>, context: PlaceContext, _location: Location) {
|
138 | 161 | // On types with `scalar_valid_range`, prevent
|
139 | 162 | // * `&mut x.field`
|
@@ -410,6 +433,12 @@ impl<'tcx> intravisit::Visitor<'tcx> for UnusedUnsafeVisitor<'_, 'tcx> {
|
410 | 433 | intravisit::walk_block(self, block);
|
411 | 434 | }
|
412 | 435 |
|
| 436 | + fn visit_anon_const(&mut self, c: &'tcx hir::AnonConst) { |
| 437 | + if matches!(self.tcx.def_kind(c.def_id), DefKind::InlineConst) { |
| 438 | + self.visit_body(self.tcx.hir().body(c.body)) |
| 439 | + } |
| 440 | + } |
| 441 | + |
413 | 442 | fn visit_fn(
|
414 | 443 | &mut self,
|
415 | 444 | fk: intravisit::FnKind<'tcx>,
|
@@ -484,7 +513,7 @@ fn unsafety_check_result<'tcx>(
|
484 | 513 | let mut checker = UnsafetyChecker::new(body, def.did, tcx, param_env);
|
485 | 514 | checker.visit_body(&body);
|
486 | 515 |
|
487 |
| - let unused_unsafes = (!tcx.is_closure(def.did.to_def_id())) |
| 516 | + let unused_unsafes = (!tcx.is_typeck_child(def.did.to_def_id())) |
488 | 517 | .then(|| check_unused_unsafe(tcx, def.did, &checker.used_unsafe_blocks));
|
489 | 518 |
|
490 | 519 | tcx.arena.alloc(UnsafetyCheckResult {
|
@@ -516,8 +545,8 @@ fn report_unused_unsafe(tcx: TyCtxt<'_>, kind: UnusedUnsafe, id: HirId) {
|
516 | 545 | pub fn check_unsafety(tcx: TyCtxt<'_>, def_id: LocalDefId) {
|
517 | 546 | debug!("check_unsafety({:?})", def_id);
|
518 | 547 |
|
519 |
| - // closures are handled by their parent fn. |
520 |
| - if tcx.is_closure(def_id.to_def_id()) { |
| 548 | + // closures and inline consts are handled by their parent fn. |
| 549 | + if tcx.is_typeck_child(def_id.to_def_id()) { |
521 | 550 | return;
|
522 | 551 | }
|
523 | 552 |
|
|
0 commit comments