]> git.lizzy.rs Git - rust.git/commitdiff
rip out everything but `MirPass`, move the logic into suites
authorNiko Matsakis <niko@alum.mit.edu>
Mon, 1 May 2017 17:46:35 +0000 (13:46 -0400)
committerNiko Matsakis <niko@alum.mit.edu>
Tue, 2 May 2017 20:21:55 +0000 (16:21 -0400)
src/librustc/mir/transform.rs
src/librustc/ty/maps.rs
src/librustc_mir/callgraph.rs
src/librustc_mir/transform/dump_mir.rs
src/librustc_mir/transform/inline.rs
src/librustc_mir/transform/interprocedural.rs
src/librustc_mir/transform/mod.rs
src/librustc_mir/transform/qualify_consts.rs

index 28b34459b30f988422c7556d2aa6d47cccb7a28e..df6f98297d0222ab2c27c5d334b31a9113213ec6 100644 (file)
@@ -15,7 +15,6 @@
 use hir::map::DefPathData;
 use mir::{Mir, Promoted};
 use ty::TyCtxt;
-use std::cell::Ref;
 use std::rc::Rc;
 use syntax::ast::NodeId;
 
@@ -83,29 +82,6 @@ pub fn default_name<T: ?Sized>() -> Cow<'static, str> {
     }
 }
 
-/// Gives you access to various bits of state during your MIR pass.
-pub trait MirCtxt<'a, 'tcx: 'a> {
-    fn tcx(&self) -> TyCtxt<'a, 'tcx, 'tcx>;
-    fn def_id(&self) -> DefId;
-    fn suite(&self) -> MirSuite;
-    fn pass_num(&self) -> MirPassIndex;
-    fn source(&self) -> MirSource;
-
-    // Get a read-only view on the MIR of this def-id from the
-    // previous pass.
-    fn read_previous_mir(&self) -> Ref<'tcx, Mir<'tcx>>;
-
-    // Steal the MIR of this def-id from the previous pass; any future
-    // attempt to access the MIR from the previous pass is a bug.
-    fn steal_previous_mir(&self) -> Mir<'tcx>;
-
-    // Same as `read_previous_mir()`, but for any def-id you want.
-    fn read_previous_mir_of(&self, def_id: DefId) -> Ref<'tcx, Mir<'tcx>>;
-
-    // Same as `steal_previous_mir()`, but for any def-id you want.
-    fn steal_previous_mir_of(&self, def_id: DefId) -> Mir<'tcx>;
-}
-
 #[derive(Copy, Clone, Debug, PartialEq, Eq, Hash, PartialOrd, Ord)]
 pub struct MirSuite(pub usize);
 
@@ -125,26 +101,19 @@ pub trait MirCtxt<'a, 'tcx: 'a> {
 /// the hook will be invoked once per output.
 pub trait PassHook {
     fn on_mir_pass<'a, 'tcx: 'a>(&self,
-                                 mir_cx: &MirCtxt<'a, 'tcx>,
-                                 mir: Option<(DefId, &Mir<'tcx>)>);
+                                 tcx: TyCtxt<'a, 'tcx, 'tcx>,
+                                 suite: MirSuite,
+                                 pass_num: MirPassIndex,
+                                 pass_name: &str,
+                                 source: MirSource,
+                                 mir: &Mir<'tcx>,
+                                 is_after: bool);
 }
 
 /// The full suite of types that identifies a particular
 /// application of a pass to a def-id.
 pub type PassId = (MirSuite, MirPassIndex, DefId);
 
-/// A streamlined trait that you can implement to create an
-/// intraprocedural pass; the pass will be invoked to process the MIR
-/// with the given `def_id`.  This lets you do things before we fetch
-/// the MIR itself. You may prefer `MirPass`, which is even more streamlined.
-pub trait DefIdPass {
-    fn name<'a>(&'a self) -> Cow<'a, str> {
-        default_name::<Self>()
-    }
-
-    fn run_pass<'a, 'tcx: 'a>(&self, mir_cx: &MirCtxt<'a, 'tcx>) -> Mir<'tcx>;
-}
-
 /// A streamlined trait that you can implement to create a pass; the
 /// pass will be named after the type, and it will consist of a main
 /// loop that goes over each available MIR and applies `run_pass`.
@@ -159,32 +128,11 @@ fn run_pass<'a, 'tcx>(&self,
                           mir: &mut Mir<'tcx>);
 }
 
-impl<T: MirPass> DefIdPass for T {
-    fn name<'a>(&'a self) -> Cow<'a, str> {
-        MirPass::name(self)
-    }
-
-    fn run_pass<'a, 'tcx: 'a>(&self, mir_cx: &MirCtxt<'a, 'tcx>) -> Mir<'tcx> {
-        let tcx = mir_cx.tcx();
-        let source = mir_cx.source();
-        let mut mir = mir_cx.steal_previous_mir();
-        MirPass::run_pass(self, tcx, source, &mut mir);
-
-        let item_id = source.item_id();
-        for (promoted_index, promoted_mir) in mir.promoted.iter_enumerated_mut() {
-            let promoted_source = MirSource::Promoted(item_id, promoted_index);
-            MirPass::run_pass(self, tcx, promoted_source, promoted_mir);
-        }
-
-        mir
-    }
-}
-
 /// A manager for MIR passes.
 #[derive(Clone)]
 pub struct Passes {
     pass_hooks: Vec<Rc<PassHook>>,
-    suites: Vec<Vec<Rc<DefIdPass>>>,
+    suites: Vec<Vec<Rc<MirPass>>>,
 }
 
 /// The number of "pass suites" that we have:
@@ -212,7 +160,7 @@ pub fn new() -> Passes {
     }
 
     /// Pushes a built-in pass.
-    pub fn push_pass<T: DefIdPass + 'static>(&mut self, suite: MirSuite, pass: T) {
+    pub fn push_pass<T: MirPass + 'static>(&mut self, suite: MirSuite, pass: T) {
         self.suites[suite.0].push(Rc::new(pass));
     }
 
@@ -225,7 +173,7 @@ pub fn len_passes(&self, suite: MirSuite) -> usize {
         self.suites[suite.0].len()
     }
 
-    pub fn pass(&self, suite: MirSuite, pass: MirPassIndex) -> &DefIdPass {
+    pub fn pass(&self, suite: MirSuite, pass: MirPassIndex) -> &MirPass {
         &*self.suites[suite.0][pass.0]
     }
 
index b37dbc6411baf82ce6e4319d08e757dff8d09c31..b3ca61550d7c3e373d1b68bcdc5a088e7964a912 100644 (file)
@@ -818,7 +818,7 @@ fn default() -> Self {
     /// manually, you're doing it wrong.
     ///
     /// See the README for the `mir` module for details.
-    [multi] mir_pass: mir_pass((MirSuite, MirPassIndex, DefId)) -> &'tcx Steal<mir::Mir<'tcx>>,
+    [] mir_pass: mir_pass((MirSuite, MirPassIndex, DefId)) -> &'tcx Steal<mir::Mir<'tcx>>,
 
     /// MIR after our optimization passes have run. This is MIR that is ready
     /// for trans. This is also the only query that can fetch non-local MIR, at present.
index ef271d8b836eba478115418a67493ccd5eb6a59c..977b9d2e994473d8c6e66c14b309ecf66719f032 100644 (file)
@@ -30,7 +30,7 @@ pub struct CallGraph {
 }
 
 impl CallGraph {
-    pub fn build<'a, 'mir, 'tcx>(cx: &mut InterproceduralCx<'a, 'mir, 'tcx>) -> CallGraph {
+    pub fn build<'a, 'tcx>(cx: &mut InterproceduralCx<'a, 'tcx>) -> CallGraph {
         let mut callgraph = CallGraph {
             node_map: DefIdMap(),
             graph: graph::Graph::new()
index b895a21558594a0ea13d563b15eb10e99544ef54..67a3281dba48b0afacda60f88445690337336920 100644 (file)
 use std::fs::File;
 use std::io;
 
-use rustc::hir::def_id::DefId;
 use rustc::mir::Mir;
-use rustc::mir::transform::{DefIdPass, MirCtxt, MirSource, PassHook};
+use rustc::mir::transform::{MirPass, MirPassIndex, MirSource, MirSuite, PassHook};
 use rustc::session::config::{OutputFilenames, OutputType};
 use rustc::ty::TyCtxt;
 use util as mir_util;
 
 pub struct Marker(pub &'static str);
 
-impl DefIdPass for Marker {
+impl MirPass for Marker {
     fn name<'a>(&'a self) -> Cow<'a, str> {
         Cow::Borrowed(self.0)
     }
 
-    fn run_pass<'a, 'tcx: 'a>(&self, mir_cx: &MirCtxt<'a, 'tcx>) -> Mir<'tcx> {
-        mir_cx.steal_previous_mir()
+    fn run_pass<'a, 'tcx>(&self,
+                          _tcx: TyCtxt<'a, 'tcx, 'tcx>,
+                          _source: MirSource,
+                          _mir: &mut Mir<'tcx>)
+    {
     }
 }
 
@@ -49,37 +51,21 @@ fn fmt(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
 
 impl PassHook for DumpMir {
     fn on_mir_pass<'a, 'tcx: 'a>(&self,
-                                 mir_cx: &MirCtxt<'a, 'tcx>,
-                                 mir: Option<(DefId, &Mir<'tcx>)>)
+                                 tcx: TyCtxt<'a, 'tcx, 'tcx>,
+                                 suite: MirSuite,
+                                 pass_num: MirPassIndex,
+                                 pass_name: &str,
+                                 source: MirSource,
+                                 mir: &Mir<'tcx>,
+                                 is_after: bool)
     {
-        let tcx = mir_cx.tcx();
-        let suite = mir_cx.suite();
-        let pass_num = mir_cx.pass_num();
-        let pass = tcx.mir_passes.pass(suite, pass_num);
-        let name = &pass.name();
-        let source = match mir {
-            None => mir_cx.source(),
-            Some((def_id, _)) => {
-                let id = tcx.hir.as_local_node_id(def_id)
-                                .expect("mir source requires local def-id");
-                MirSource::from_node(tcx, id)
-            }
-        };
-        if mir_util::dump_enabled(tcx, name, source) {
-            let previous_mir;
-            let mir_to_dump = match mir {
-                Some((_, m)) => m,
-                None => {
-                    previous_mir = mir_cx.read_previous_mir();
-                    &*previous_mir
-                }
-            };
+        if mir_util::dump_enabled(tcx, pass_name, source) {
             mir_util::dump_mir(tcx,
                                Some((suite, pass_num)),
-                               name,
-                               &Disambiguator { is_after: mir.is_some() },
+                               pass_name,
+                               &Disambiguator { is_after },
                                source,
-                               mir_to_dump);
+                               mir);
         }
     }
 }
index 2323b55951d7618578bac57893f32f66706c55b3..caa2aa74ede199c4b912ecad81b0957a26c28f98 100644 (file)
@@ -18,7 +18,7 @@
 
 use rustc::dep_graph::DepNode;
 use rustc::mir::*;
-use rustc::mir::transform::{MirCtxt, MirSource, PassId};
+use rustc::mir::transform::{MirSource, PassId};
 use rustc::mir::visit::*;
 use rustc::traits;
 use rustc::ty::{self, Ty, TyCtxt};
 pub struct Inline;
 
 pub trait Pass {
-    fn run_pass<'a, 'tcx: 'a>(&self, mir_cx: &MirCtxt<'a, 'tcx>)
+    fn run_pass<'a, 'tcx: 'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>)
                               -> Multi<PassId, &'tcx Steal<Mir<'tcx>>>;
 }
 
 impl Pass for Inline {
-    fn run_pass<'a, 'tcx: 'a>(&self, mir_cx: &MirCtxt<'a, 'tcx>)
+    fn run_pass<'a, 'tcx: 'a>(&self, tcx: TyCtxt<'a, 'tcx, 'tcx>)
                               -> Multi<PassId, &'tcx Steal<Mir<'tcx>>> {
-        let tcx = mir_cx.tcx();
-        if tcx.sess.opts.debugging_opts.mir_opt_level < 2 {
-            return Multi::from(tcx.alloc_steal_mir(mir_cx.steal_previous_mir()));
-        }
-
-        let mut cx = InterproceduralCx::new(mir_cx);
+        let mut cx = InterproceduralCx::new(tcx);
 
         let callgraph = callgraph::CallGraph::build(&mut cx);
 
@@ -72,8 +67,8 @@ fn run_pass<'a, 'tcx: 'a>(&self, mir_cx: &MirCtxt<'a, 'tcx>)
     }
 }
 
-struct Inliner<'mir, 'tcx: 'mir> {
-    tcx: TyCtxt<'mir, 'tcx, 'tcx>,
+struct Inliner<'a, 'tcx: 'a> {
+    tcx: TyCtxt<'a, 'tcx, 'tcx>,
 }
 
 #[derive(Copy, Clone)]
@@ -85,11 +80,11 @@ struct CallSite<'tcx> {
     location: SourceInfo,
 }
 
-impl<'mir, 'tcx> Inliner<'mir, 'tcx> {
-    fn inline_scc<'a>(&mut self,
-                      cx: &mut InterproceduralCx<'a, 'mir, 'tcx>,
-                      callgraph: &callgraph::CallGraph,
-                      scc: &[graph::NodeIndex]) -> bool {
+impl<'a, 'tcx> Inliner<'a, 'tcx> {
+    fn inline_scc(&mut self,
+                  cx: &mut InterproceduralCx<'a, 'tcx>,
+                  callgraph: &callgraph::CallGraph,
+                  scc: &[graph::NodeIndex]) -> bool {
         let tcx = self.tcx;
         let mut callsites = Vec::new();
         let mut in_scc = DefIdSet();
index 02d2b357e043e94bfbfe9e35e77543a5350553aa..7a2645567e24e8b8a45ffe16fe08f58a0c0ef6a6 100644 (file)
@@ -10,7 +10,7 @@
 
 use rustc::hir::def_id::DefId;
 use rustc::mir::Mir;
-use rustc::mir::transform::{MirCtxt, PassId};
+use rustc::mir::transform::{PassId};
 use rustc::ty::steal::Steal;
 use rustc::ty::TyCtxt;
 use rustc_data_structures::fx::FxHashMap;
 /// stolen and so forth. It is more of a placeholder meant to get
 /// inlining up and going again, and is probably going to need heavy
 /// revision as we scale up to more interesting optimizations.
-pub struct InterproceduralCx<'a, 'mir: 'a, 'tcx: 'mir> {
-    pub tcx: TyCtxt<'mir, 'tcx, 'tcx>,
-    pub mir_cx: &'a MirCtxt<'mir, 'tcx>,
+pub struct InterproceduralCx<'a, 'tcx: 'a> {
+    pub tcx: TyCtxt<'a, 'tcx, 'tcx>,
     local_cache: FxHashMap<DefId, Mir<'tcx>>,
 }
 
-impl<'a, 'mir, 'tcx> InterproceduralCx<'a, 'mir, 'tcx> {
-    pub fn new(mir_cx: &'a MirCtxt<'mir, 'tcx>) -> Self {
+impl<'a, 'tcx> InterproceduralCx<'a, 'tcx> {
+    pub fn new(tcx: TyCtxt<'a, 'tcx, 'tcx>) -> Self {
         InterproceduralCx {
-            mir_cx,
-            tcx: mir_cx.tcx(),
+            tcx: tcx,
             local_cache: FxHashMap::default(),
         }
     }
 
     pub fn into_local_mirs(self) -> Vec<(PassId, &'tcx Steal<Mir<'tcx>>)> {
-        let tcx = self.tcx;
-        let suite = self.mir_cx.suite();
-        let pass_num = self.mir_cx.pass_num();
-        self.local_cache.into_iter()
-                        .map(|(def_id, mir)| {
-                            let mir = tcx.alloc_steal_mir(mir);
-                            ((suite, pass_num, def_id), mir)
-                        })
-                        .collect()
+        unimplemented!()
     }
 
     /// Ensures that the mir for `def_id` is available, if it can be
@@ -93,8 +83,6 @@ pub fn mir(&self, def_id: DefId) -> Option<&Mir<'tcx>> {
 
     pub fn mir_mut(&mut self, def_id: DefId) -> &mut Mir<'tcx> {
         assert!(def_id.is_local(), "cannot get mutable mir of remote entry");
-        let mir_cx = self.mir_cx;
-        self.local_cache.entry(def_id)
-                        .or_insert_with(|| mir_cx.steal_previous_mir_of(def_id))
+        unimplemented!()
     }
 }
index feef7a197c59df346381df6d58da1073d3edc1b6..dc67c6f1ef45f168567d396245a5b653e6c476bb 100644 (file)
 
 use rustc::hir::def_id::DefId;
 use rustc::mir::Mir;
-use rustc::mir::transform::{MirCtxt, MirPassIndex, MirSuite, MirSource, MIR_OPTIMIZED, PassId};
+use rustc::mir::transform::{MirPassIndex, MirSuite, MirSource, MIR_VALIDATED, MIR_OPTIMIZED};
+use rustc::ty::{self, TyCtxt};
 use rustc::ty::steal::Steal;
-use rustc::ty::TyCtxt;
-use rustc::ty::maps::{Multi, Providers};
-use std::cell::Ref;
+use rustc::ty::maps::Providers;
+use syntax_pos::DUMMY_SP;
 
 pub mod simplify_branches;
 pub mod simplify;
@@ -51,6 +51,20 @@ fn mir_suite<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                        -> &'tcx Steal<Mir<'tcx>>
 {
     let passes = &tcx.mir_passes;
+
+    if suite == MIR_VALIDATED {
+        let id = tcx.hir.as_local_node_id(def_id).expect("mir source requires local def-id");
+        let source = MirSource::from_node(tcx, id);
+        if let MirSource::Const(_) = source {
+            // Ensure that we compute the `mir_const_qualif` for
+            // constants at this point, before we do any further
+            // optimization (and before we steal the previous
+            // MIR). We don't directly need the result, so we can
+            // just force it.
+            ty::queries::mir_const_qualif::force(tcx, DUMMY_SP, def_id);
+        }
+    }
+
     let len = passes.len_passes(suite);
     assert!(len > 0, "no passes in {:?}", suite);
     tcx.mir_pass((suite, MirPassIndex(len - 1), def_id))
@@ -58,82 +72,36 @@ fn mir_suite<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
 
 fn mir_pass<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
                       (suite, pass_num, def_id): (MirSuite, MirPassIndex, DefId))
-                      -> Multi<PassId, &'tcx Steal<Mir<'tcx>>>
+                      -> &'tcx Steal<Mir<'tcx>>
 {
     let passes = &tcx.mir_passes;
     let pass = passes.pass(suite, pass_num);
-    let mir_ctxt = MirCtxtImpl { tcx, pass_num, suite, def_id };
 
-    for hook in passes.hooks() {
-        hook.on_mir_pass(&mir_ctxt, None);
-    }
+    let id = tcx.hir.as_local_node_id(def_id).expect("mir source requires local def-id");
+    let source = MirSource::from_node(tcx, id);
 
-    let mir = pass.run_pass(&mir_ctxt);
+    let mut mir = {
+        let MirSuite(suite) = suite;
+        let MirPassIndex(pass_num) = pass_num;
+        if pass_num > 0 {
+            tcx.mir_pass((MirSuite(suite), MirPassIndex(pass_num - 1), def_id)).steal()
+        } else if suite > 0 {
+            tcx.mir_suite((MirSuite(suite - 1), def_id)).steal()
+        } else {
+            tcx.mir_build(def_id).steal()
+        }
+    };
 
     for hook in passes.hooks() {
-        hook.on_mir_pass(&mir_ctxt, Some((def_id, &mir)));
-    }
-
-    Multi::from(tcx.alloc_steal_mir(mir))
-}
-
-struct MirCtxtImpl<'a, 'tcx: 'a> {
-    tcx: TyCtxt<'a, 'tcx, 'tcx>,
-    pass_num: MirPassIndex,
-    suite: MirSuite,
-    def_id: DefId
-}
-
-impl<'a, 'tcx> MirCtxt<'a, 'tcx> for MirCtxtImpl<'a, 'tcx> {
-    fn tcx(&self) -> TyCtxt<'a, 'tcx, 'tcx> {
-        self.tcx
-    }
-
-    fn suite(&self) -> MirSuite {
-        self.suite
-    }
-
-    fn pass_num(&self) -> MirPassIndex {
-        self.pass_num
-    }
-
-    fn def_id(&self) -> DefId {
-        self.def_id
-    }
-
-    fn source(&self) -> MirSource {
-        let id = self.tcx.hir.as_local_node_id(self.def_id)
-                             .expect("mir source requires local def-id");
-        MirSource::from_node(self.tcx, id)
-    }
-
-    fn read_previous_mir(&self) -> Ref<'tcx, Mir<'tcx>> {
-        self.previous_mir(self.def_id).borrow()
+        hook.on_mir_pass(tcx, suite, pass_num, &pass.name(), source, &mir, false);
     }
 
-    fn steal_previous_mir(&self) -> Mir<'tcx> {
-        self.previous_mir(self.def_id).steal()
-    }
+    pass.run_pass(tcx, source, &mut mir);
 
-    fn read_previous_mir_of(&self, def_id: DefId) -> Ref<'tcx, Mir<'tcx>> {
-        self.previous_mir(def_id).borrow()
+    for hook in passes.hooks() {
+        hook.on_mir_pass(tcx, suite, pass_num, &pass.name(), source, &mir, true);
     }
 
-    fn steal_previous_mir_of(&self, def_id: DefId) -> Mir<'tcx> {
-        self.previous_mir(def_id).steal()
-    }
+    tcx.alloc_steal_mir(mir)
 }
 
-impl<'a, 'tcx> MirCtxtImpl<'a, 'tcx> {
-    fn previous_mir(&self, def_id: DefId) -> &'tcx Steal<Mir<'tcx>> {
-        let MirSuite(suite) = self.suite;
-        let MirPassIndex(pass_num) = self.pass_num;
-        if pass_num > 0 {
-            self.tcx.mir_pass((MirSuite(suite), MirPassIndex(pass_num - 1), def_id))
-        } else if suite > 0 {
-            self.tcx.mir_suite((MirSuite(suite - 1), def_id))
-        } else {
-            self.tcx.mir_build(def_id)
-        }
-    }
-}
index c2d2e113f56e419d68391a6e01e6b7f0b7a9ddca..cd37372c2f1229754d51dc2caf105407063b06a2 100644 (file)
@@ -26,7 +26,7 @@
 use rustc::ty::maps::Providers;
 use rustc::mir::*;
 use rustc::mir::traversal::ReversePostorder;
-use rustc::mir::transform::{DefIdPass, MirCtxt, MirSource, MIR_CONST};
+use rustc::mir::transform::{MirPass, MirSource, MIR_CONST};
 use rustc::mir::visit::{LvalueContext, Visitor};
 use rustc::middle::lang_items;
 use syntax::abi::Abi;
@@ -938,34 +938,11 @@ fn qualify_const_item<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
 
 pub struct QualifyAndPromoteConstants;
 
-impl DefIdPass for QualifyAndPromoteConstants {
-    fn run_pass<'a, 'tcx: 'a>(&self, mir_cx: &MirCtxt<'a, 'tcx>) -> Mir<'tcx> {
-        let tcx = mir_cx.tcx();
-        match mir_cx.source() {
-            MirSource::Const(_) => {
-                // Ensure that we compute the `mir_const_qualif` for
-                // constants at this point, before we do any further
-                // optimization (and before we steal the previous
-                // MIR). We don't directly need the result, so we can
-                // just force it.
-                ty::queries::mir_const_qualif::force(tcx, DUMMY_SP, mir_cx.def_id());
-                mir_cx.steal_previous_mir()
-            }
-
-            src => {
-                let mut mir = mir_cx.steal_previous_mir();
-                self.run_pass(tcx, src, &mut mir);
-                mir
-            }
-        }
-    }
-}
-
-impl<'a, 'tcx> QualifyAndPromoteConstants {
-    fn run_pass(&self,
-                tcx: TyCtxt<'a, 'tcx, 'tcx>,
-                src: MirSource,
-                mir: &mut Mir<'tcx>) {
+impl MirPass for QualifyAndPromoteConstants {
+    fn run_pass<'a, 'tcx>(&self,
+                          tcx: TyCtxt<'a, 'tcx, 'tcx>,
+                          src: MirSource,
+                          mir: &mut Mir<'tcx>) {
         let id = src.item_id();
         let def_id = tcx.hir.local_def_id(id);
         let mode = match src {