about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorEduard-Mihai Burtescu <edy.burt@gmail.com>2020-06-25 20:58:33 +0300
committerEduard-Mihai Burtescu <edy.burt@gmail.com>2020-07-02 16:49:09 +0300
commit883ece499fef22b4703f5b04133bb2beff08c794 (patch)
tree9dbd19d802d25362c543043edacba314155e3087 /src
parent1b58ab73fdd97bde191e7d639c36849aad2b941c (diff)
downloadrust-883ece499fef22b4703f5b04133bb2beff08c794.tar.gz
rust-883ece499fef22b4703f5b04133bb2beff08c794.zip
rustc_passes/dead: avoid using TypeckTables::empty for MarkSymbolVisitor.
Diffstat (limited to 'src')
-rw-r--r--src/librustc_passes/dead.rs45
1 files changed, 26 insertions, 19 deletions
diff --git a/src/librustc_passes/dead.rs b/src/librustc_passes/dead.rs
index 503fbb64db8..87348894a5a 100644
--- a/src/librustc_passes/dead.rs
+++ b/src/librustc_passes/dead.rs
@@ -37,10 +37,10 @@ fn should_explore(tcx: TyCtxt<'_>, hir_id: hir::HirId) -> bool {
     }
 }
 
-struct MarkSymbolVisitor<'a, 'tcx> {
+struct MarkSymbolVisitor<'tcx> {
     worklist: Vec<hir::HirId>,
     tcx: TyCtxt<'tcx>,
-    tables: &'a ty::TypeckTables<'tcx>,
+    maybe_typeck_tables: Option<&'tcx ty::TypeckTables<'tcx>>,
     live_symbols: FxHashSet<hir::HirId>,
     repr_has_repr_c: bool,
     in_pat: bool,
@@ -50,7 +50,15 @@ struct MarkSymbolVisitor<'a, 'tcx> {
     struct_constructors: FxHashMap<hir::HirId, hir::HirId>,
 }
 
-impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
+impl<'tcx> MarkSymbolVisitor<'tcx> {
+    /// Gets the type-checking side-tables for the current body.
+    /// As this will ICE if called outside bodies, only call when working with
+    /// `Expr` or `Pat` nodes (they are guaranteed to be found only in bodies).
+    #[track_caller]
+    fn tables(&self) -> &'tcx ty::TypeckTables<'tcx> {
+        self.maybe_typeck_tables.expect("`MarkSymbolVisitor::tables` called outside of body")
+    }
+
     fn check_def_id(&mut self, def_id: DefId) {
         if let Some(def_id) = def_id.as_local() {
             let hir_id = self.tcx.hir().as_local_hir_id(def_id);
@@ -107,7 +115,7 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
     }
 
     fn lookup_and_handle_method(&mut self, id: hir::HirId) {
-        if let Some(def_id) = self.tables.type_dependent_def_id(id) {
+        if let Some(def_id) = self.tables().type_dependent_def_id(id) {
             self.check_def_id(def_id);
         } else {
             bug!("no type-dependent def for method");
@@ -115,9 +123,9 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
     }
 
     fn handle_field_access(&mut self, lhs: &hir::Expr<'_>, hir_id: hir::HirId) {
-        match self.tables.expr_ty_adjusted(lhs).kind {
+        match self.tables().expr_ty_adjusted(lhs).kind {
             ty::Adt(def, _) => {
-                let index = self.tcx.field_index(hir_id, self.tables);
+                let index = self.tcx.field_index(hir_id, self.tables());
                 self.insert_def_id(def.non_enum_variant().fields[index].did);
             }
             ty::Tuple(..) => {}
@@ -131,7 +139,7 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
         res: Res,
         pats: &[hir::FieldPat<'_>],
     ) {
-        let variant = match self.tables.node_type(lhs.hir_id).kind {
+        let variant = match self.tables().node_type(lhs.hir_id).kind {
             ty::Adt(adt, _) => adt.variant_of_res(res),
             _ => span_bug!(lhs.span, "non-ADT in struct pattern"),
         };
@@ -139,7 +147,7 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
             if let PatKind::Wild = pat.pat.kind {
                 continue;
             }
-            let index = self.tcx.field_index(pat.hir_id, self.tables);
+            let index = self.tcx.field_index(pat.hir_id, self.tables());
             self.insert_def_id(variant.fields[index].did);
         }
     }
@@ -204,14 +212,14 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
     fn mark_as_used_if_union(&mut self, adt: &ty::AdtDef, fields: &[hir::Field<'_>]) {
         if adt.is_union() && adt.non_enum_variant().fields.len() > 1 && adt.did.is_local() {
             for field in fields {
-                let index = self.tcx.field_index(field.hir_id, self.tables);
+                let index = self.tcx.field_index(field.hir_id, self.tables());
                 self.insert_def_id(adt.non_enum_variant().fields[index].did);
             }
         }
     }
 }
 
-impl<'a, 'tcx> Visitor<'tcx> for MarkSymbolVisitor<'a, 'tcx> {
+impl<'tcx> Visitor<'tcx> for MarkSymbolVisitor<'tcx> {
     type Map = intravisit::ErasedMap<'tcx>;
 
     fn nested_visit_map(&mut self) -> intravisit::NestedVisitorMap<Self::Map> {
@@ -219,11 +227,10 @@ impl<'a, 'tcx> Visitor<'tcx> for MarkSymbolVisitor<'a, 'tcx> {
     }
 
     fn visit_nested_body(&mut self, body: hir::BodyId) {
-        let old_tables = self.tables;
-        self.tables = self.tcx.body_tables(body);
+        let old_maybe_typeck_tables = self.maybe_typeck_tables.replace(self.tcx.body_tables(body));
         let body = self.tcx.hir().body(body);
         self.visit_body(body);
-        self.tables = old_tables;
+        self.maybe_typeck_tables = old_maybe_typeck_tables;
     }
 
     fn visit_variant_data(
@@ -248,7 +255,7 @@ impl<'a, 'tcx> Visitor<'tcx> for MarkSymbolVisitor<'a, 'tcx> {
     fn visit_expr(&mut self, expr: &'tcx hir::Expr<'tcx>) {
         match expr.kind {
             hir::ExprKind::Path(ref qpath @ hir::QPath::TypeRelative(..)) => {
-                let res = self.tables.qpath_res(qpath, expr.hir_id);
+                let res = self.tables().qpath_res(qpath, expr.hir_id);
                 self.handle_res(res);
             }
             hir::ExprKind::MethodCall(..) => {
@@ -258,9 +265,9 @@ impl<'a, 'tcx> Visitor<'tcx> for MarkSymbolVisitor<'a, 'tcx> {
                 self.handle_field_access(&lhs, expr.hir_id);
             }
             hir::ExprKind::Struct(ref qpath, ref fields, _) => {
-                let res = self.tables.qpath_res(qpath, expr.hir_id);
+                let res = self.tables().qpath_res(qpath, expr.hir_id);
                 self.handle_res(res);
-                if let ty::Adt(ref adt, _) = self.tables.expr_ty(expr).kind {
+                if let ty::Adt(ref adt, _) = self.tables().expr_ty(expr).kind {
                     self.mark_as_used_if_union(adt, fields);
                 }
             }
@@ -283,11 +290,11 @@ impl<'a, 'tcx> Visitor<'tcx> for MarkSymbolVisitor<'a, 'tcx> {
     fn visit_pat(&mut self, pat: &'tcx hir::Pat<'tcx>) {
         match pat.kind {
             PatKind::Struct(ref path, ref fields, _) => {
-                let res = self.tables.qpath_res(path, pat.hir_id);
+                let res = self.tables().qpath_res(path, pat.hir_id);
                 self.handle_field_pattern_match(pat, res, fields);
             }
             PatKind::Path(ref qpath) => {
-                let res = self.tables.qpath_res(qpath, pat.hir_id);
+                let res = self.tables().qpath_res(qpath, pat.hir_id);
                 self.handle_res(res);
             }
             _ => (),
@@ -473,7 +480,7 @@ fn find_live<'tcx>(
     let mut symbol_visitor = MarkSymbolVisitor {
         worklist,
         tcx,
-        tables: &ty::TypeckTables::empty(None),
+        maybe_typeck_tables: None,
         live_symbols: Default::default(),
         repr_has_repr_c: false,
         in_pat: false,