diff options
| author | Eduard-Mihai Burtescu <edy.burt@gmail.com> | 2018-11-26 21:40:05 +0200 |
|---|---|---|
| committer | Eduard-Mihai Burtescu <edy.burt@gmail.com> | 2019-04-23 23:35:21 +0300 |
| commit | 1525dc2146e3b85123f57e59adcee1908e57013f (patch) | |
| tree | 49733b00e4e0192f9fa4b76b2d9d66a75cb496e3 /src | |
| parent | e6ec968485080a704a4edc1e96c89359bd81550d (diff) | |
| download | rust-1525dc2146e3b85123f57e59adcee1908e57013f.tar.gz rust-1525dc2146e3b85123f57e59adcee1908e57013f.zip | |
rustc: dissuade compiler developers from misusing upvar debuginfo.
Diffstat (limited to 'src')
| -rw-r--r-- | src/librustc/mir/mod.rs | 18 | ||||
| -rw-r--r-- | src/librustc_codegen_ssa/mir/mod.rs | 11 | ||||
| -rw-r--r-- | src/librustc_mir/build/mod.rs | 18 | ||||
| -rw-r--r-- | src/librustc_mir/transform/inline.rs | 6 |
4 files changed, 29 insertions, 24 deletions
diff --git a/src/librustc/mir/mod.rs b/src/librustc/mir/mod.rs index 7c432c9c7eb..bf2a1eaafd6 100644 --- a/src/librustc/mir/mod.rs +++ b/src/librustc/mir/mod.rs @@ -146,7 +146,11 @@ pub struct Mir<'tcx> { /// Names and capture modes of all the closure upvars, assuming /// the first argument is either the closure or a reference to it. - pub upvar_decls: Vec<UpvarDecl>, + // NOTE(eddyb) This is *strictly* a temporary hack for codegen + // debuginfo generation, and will be removed at some point. + // Do **NOT** use it for anything else, upvar information should not be + // in the MIR, please rely on local crate HIR or other side-channels. + pub __upvar_debuginfo_codegen_only_do_not_use: Vec<UpvarDebuginfo>, /// Mark this MIR of a const context other than const functions as having converted a `&&` or /// `||` expression into `&` or `|` respectively. This is problematic because if we ever stop @@ -173,7 +177,7 @@ impl<'tcx> Mir<'tcx> { local_decls: LocalDecls<'tcx>, user_type_annotations: CanonicalUserTypeAnnotations<'tcx>, arg_count: usize, - upvar_decls: Vec<UpvarDecl>, + __upvar_debuginfo_codegen_only_do_not_use: Vec<UpvarDebuginfo>, span: Span, control_flow_destroyed: Vec<(Span, String)>, ) -> Self { @@ -197,7 +201,7 @@ impl<'tcx> Mir<'tcx> { local_decls, user_type_annotations, arg_count, - upvar_decls, + __upvar_debuginfo_codegen_only_do_not_use, spread_arg: None, span, cache: cache::Cache::new(), @@ -431,7 +435,7 @@ impl_stable_hash_for!(struct Mir<'tcx> { local_decls, user_type_annotations, arg_count, - upvar_decls, + __upvar_debuginfo_codegen_only_do_not_use, spread_arg, control_flow_destroyed, span, @@ -983,7 +987,7 @@ impl<'tcx> LocalDecl<'tcx> { /// A closure capture, with its name and mode. #[derive(Clone, Debug, RustcEncodable, RustcDecodable, HashStable)] -pub struct UpvarDecl { +pub struct UpvarDebuginfo { pub debug_name: Name, /// If true, the capture is behind a reference. @@ -3151,7 +3155,7 @@ CloneTypeFoldableAndLiftImpls! { MirPhase, Mutability, SourceInfo, - UpvarDecl, + UpvarDebuginfo, FakeReadCause, RetagKind, SourceScope, @@ -3173,7 +3177,7 @@ BraceStructTypeFoldableImpl! { local_decls, user_type_annotations, arg_count, - upvar_decls, + __upvar_debuginfo_codegen_only_do_not_use, spread_arg, control_flow_destroyed, span, diff --git a/src/librustc_codegen_ssa/mir/mod.rs b/src/librustc_codegen_ssa/mir/mod.rs index c9a6ff1a0c0..621c4e5d448 100644 --- a/src/librustc_codegen_ssa/mir/mod.rs +++ b/src/librustc_codegen_ssa/mir/mod.rs @@ -598,9 +598,10 @@ fn arg_local_refs<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>( tmp } }; + let upvar_debuginfo = &mir.__upvar_debuginfo_codegen_only_do_not_use; arg_scope.map(|scope| { // Is this a regular argument? - if arg_index > 0 || mir.upvar_decls.is_empty() { + if arg_index > 0 || upvar_debuginfo.is_empty() { // The Rust ABI passes indirect variables using a pointer and a manual copy, so we // need to insert a deref here, but the C ABI uses a pointer and a copy using the // byval attribute, for which LLVM always does the deref itself, @@ -638,16 +639,16 @@ fn arg_local_refs<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>( let (def_id, upvar_substs) = match closure_layout.ty.sty { ty::Closure(def_id, substs) => (def_id, UpvarSubsts::Closure(substs)), ty::Generator(def_id, substs, _) => (def_id, UpvarSubsts::Generator(substs)), - _ => bug!("upvar_decls with non-closure arg0 type `{}`", closure_layout.ty) + _ => bug!("upvar debuginfo with non-closure arg0 type `{}`", closure_layout.ty) }; let upvar_tys = upvar_substs.upvar_tys(def_id, tcx); let extra_locals = { - let upvars = mir.upvar_decls + let upvars = upvar_debuginfo .iter() .zip(upvar_tys) .enumerate() - .map(|(i, (decl, ty))| (i, decl.debug_name, decl.by_ref, ty)); + .map(|(i, (upvar, ty))| (i, upvar.debug_name, upvar.by_ref, ty)); let generator_fields = mir.generator_layout.as_ref().map(|generator_layout| { let (def_id, gen_substs) = match closure_layout.ty.sty { @@ -656,7 +657,7 @@ fn arg_local_refs<'a, 'tcx: 'a, Bx: BuilderMethods<'a, 'tcx>>( }; let state_tys = gen_substs.state_tys(def_id, tcx); - let upvar_count = mir.upvar_decls.len(); + let upvar_count = upvar_debuginfo.len(); generator_layout.fields .iter() .zip(state_tys) diff --git a/src/librustc_mir/build/mod.rs b/src/librustc_mir/build/mod.rs index cd2fa10927f..79e1d5daae1 100644 --- a/src/librustc_mir/build/mod.rs +++ b/src/librustc_mir/build/mod.rs @@ -375,7 +375,7 @@ struct Builder<'a, 'gcx: 'a+'tcx, 'tcx: 'a> { var_indices: HirIdMap<LocalsForNode>, local_decls: IndexVec<Local, LocalDecl<'tcx>>, canonical_user_type_annotations: ty::CanonicalUserTypeAnnotations<'tcx>, - upvar_decls: Vec<UpvarDecl>, + __upvar_debuginfo_codegen_only_do_not_use: Vec<UpvarDebuginfo>, upvar_mutbls: Vec<Mutability>, unit_temp: Option<Place<'tcx>>, @@ -631,7 +631,7 @@ fn construct_fn<'a, 'gcx, 'tcx, A>(hir: Cx<'a, 'gcx, 'tcx>, // closure and we stored in a map called upvar_list in TypeckTables indexed // with the closure's DefId. Here, we run through that vec of UpvarIds for // the given closure and use the necessary information to create UpvarDecl. - let upvar_decls: Vec<_> = hir_tables + let upvar_debuginfo: Vec<_> = hir_tables .upvar_list .get(&fn_def_id) .into_iter() @@ -644,14 +644,14 @@ fn construct_fn<'a, 'gcx, 'tcx, A>(hir: Cx<'a, 'gcx, 'tcx>, ty::UpvarCapture::ByValue => false, ty::UpvarCapture::ByRef(..) => true, }; - let mut decl = UpvarDecl { + let mut debuginfo = UpvarDebuginfo { debug_name: keywords::Invalid.name(), by_ref, }; let mut mutability = Mutability::Not; if let Some(Node::Binding(pat)) = tcx_hir.find(var_node_id) { if let hir::PatKind::Binding(_, _, ident, _) = pat.node { - decl.debug_name = ident.name; + debuginfo.debug_name = ident.name; if let Some(&bm) = hir.tables.pat_binding_modes().get(pat.hir_id) { if bm == ty::BindByValue(hir::MutMutable) { mutability = Mutability::Mut; @@ -664,7 +664,7 @@ fn construct_fn<'a, 'gcx, 'tcx, A>(hir: Cx<'a, 'gcx, 'tcx>, } } upvar_mutbls.push(mutability); - decl + debuginfo }) .collect(); @@ -674,7 +674,7 @@ fn construct_fn<'a, 'gcx, 'tcx, A>(hir: Cx<'a, 'gcx, 'tcx>, safety, return_ty, return_ty_span, - upvar_decls, + upvar_debuginfo, upvar_mutbls); let call_site_scope = region::Scope { @@ -778,7 +778,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { safety: Safety, return_ty: Ty<'tcx>, return_span: Span, - upvar_decls: Vec<UpvarDecl>, + __upvar_debuginfo_codegen_only_do_not_use: Vec<UpvarDebuginfo>, upvar_mutbls: Vec<Mutability>) -> Builder<'a, 'gcx, 'tcx> { let lint_level = LintLevel::Explicit(hir.root_lint_level); @@ -801,7 +801,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { 1, ), canonical_user_type_annotations: IndexVec::new(), - upvar_decls, + __upvar_debuginfo_codegen_only_do_not_use, upvar_mutbls, var_indices: Default::default(), unit_temp: None, @@ -837,7 +837,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> { self.local_decls, self.canonical_user_type_annotations, self.arg_count, - self.upvar_decls, + self.__upvar_debuginfo_codegen_only_do_not_use, self.fn_span, self.hir.control_flow_destroyed(), ) diff --git a/src/librustc_mir/transform/inline.rs b/src/librustc_mir/transform/inline.rs index 027ae70b06a..e96a40ad2f0 100644 --- a/src/librustc_mir/transform/inline.rs +++ b/src/librustc_mir/transform/inline.rs @@ -222,10 +222,10 @@ impl<'a, 'tcx> Inliner<'a, 'tcx> { debug!("should_inline({:?})", callsite); let tcx = self.tcx; - // Don't inline closures that have captures + // Don't inline closures that have capture debuginfo // FIXME: Handle closures better - if callee_mir.upvar_decls.len() > 0 { - debug!(" upvar decls present - not inlining"); + if callee_mir.__upvar_debuginfo_codegen_only_do_not_use.len() > 0 { + debug!(" upvar debuginfo present - not inlining"); return false; } |
