Skip to content

Commit bc0fd08

Browse files
committed
rustc_mir: track inlined callees in SourceScopeData.
1 parent 7f741ee commit bc0fd08

File tree

14 files changed

+87
-38
lines changed

14 files changed

+87
-38
lines changed

src/librustc/mir/mod.rs

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,7 @@ pub struct Body<'tcx> {
111111

112112
/// A list of source scopes; these are referenced by statements
113113
/// and used for debuginfo. Indexed by a `SourceScope`.
114-
pub source_scopes: IndexVec<SourceScope, SourceScopeData>,
114+
pub source_scopes: IndexVec<SourceScope, SourceScopeData<'tcx>>,
115115

116116
/// The yield type of the function, if it is a generator.
117117
pub yield_ty: Option<Ty<'tcx>>,
@@ -178,7 +178,7 @@ pub struct Body<'tcx> {
178178
impl<'tcx> Body<'tcx> {
179179
pub fn new(
180180
basic_blocks: IndexVec<BasicBlock, BasicBlockData<'tcx>>,
181-
source_scopes: IndexVec<SourceScope, SourceScopeData>,
181+
source_scopes: IndexVec<SourceScope, SourceScopeData<'tcx>>,
182182
local_decls: LocalDecls<'tcx>,
183183
user_type_annotations: CanonicalUserTypeAnnotations<'tcx>,
184184
arg_count: usize,
@@ -1969,11 +1969,16 @@ rustc_index::newtype_index! {
19691969
}
19701970
}
19711971

1972-
#[derive(Clone, Debug, RustcEncodable, RustcDecodable, HashStable)]
1973-
pub struct SourceScopeData {
1972+
#[derive(Clone, Debug, RustcEncodable, RustcDecodable, HashStable, TypeFoldable)]
1973+
pub struct SourceScopeData<'tcx> {
19741974
pub span: Span,
19751975
pub parent_scope: Option<SourceScope>,
19761976

1977+
/// Whether this scope is the root of a scope tree of another body,
1978+
/// inlined into this body by the MIR inliner.
1979+
/// `ty::Instance` is the callee, and the `Span` is the call site.
1980+
pub inlined: Option<(ty::Instance<'tcx>, Span)>,
1981+
19771982
/// Crate-local information for this source scope, that can't (and
19781983
/// needn't) be tracked across crates.
19791984
pub local_data: ClearCrossCrate<SourceScopeLocalData>,
@@ -2683,7 +2688,6 @@ CloneTypeFoldableAndLiftImpls! {
26832688
FakeReadCause,
26842689
RetagKind,
26852690
SourceScope,
2686-
SourceScopeData,
26872691
SourceScopeLocalData,
26882692
UserTypeAnnotationIndex,
26892693
}

src/librustc/mir/visit.rs

Lines changed: 30 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@ macro_rules! make_mir_visitor {
9494
}
9595

9696
fn visit_source_scope_data(&mut self,
97-
scope_data: & $($mutability)? SourceScopeData) {
97+
scope_data: & $($mutability)? SourceScopeData<'tcx>) {
9898
self.super_source_scope_data(scope_data);
9999
}
100100

@@ -329,17 +329,45 @@ macro_rules! make_mir_visitor {
329329
}
330330
}
331331

332-
fn super_source_scope_data(&mut self, scope_data: & $($mutability)? SourceScopeData) {
332+
fn super_source_scope_data(
333+
&mut self,
334+
scope_data: & $($mutability)? SourceScopeData<'tcx>,
335+
) {
333336
let SourceScopeData {
334337
span,
335338
parent_scope,
339+
inlined,
336340
local_data: _,
337341
} = scope_data;
338342

339343
self.visit_span(span);
340344
if let Some(parent_scope) = parent_scope {
341345
self.visit_source_scope(parent_scope);
342346
}
347+
if let Some((callee, callsite_span)) = inlined {
348+
let location = START_BLOCK.start_location();
349+
350+
self.visit_span(callsite_span);
351+
352+
let ty::Instance { def: callee_def, substs: callee_substs } = callee;
353+
match callee_def {
354+
ty::InstanceDef::Item(_def_id) |
355+
ty::InstanceDef::Intrinsic(_def_id) |
356+
ty::InstanceDef::VtableShim(_def_id) |
357+
ty::InstanceDef::ReifyShim(_def_id) |
358+
ty::InstanceDef::Virtual(_def_id, _) |
359+
ty::InstanceDef::ClosureOnceShim { call_once: _def_id } |
360+
ty::InstanceDef::DropGlue(_def_id, None) => {}
361+
362+
ty::InstanceDef::FnPtrShim(_def_id, ty) |
363+
ty::InstanceDef::DropGlue(_def_id, Some(ty)) |
364+
ty::InstanceDef::CloneShim(_def_id, ty) => {
365+
// FIXME(eddyb) use a better `TyContext` here.
366+
self.visit_ty(ty, TyContext::Location(location));
367+
}
368+
}
369+
self.visit_substs(callee_substs, location);
370+
}
343371
}
344372

345373
fn super_statement(&mut self,

src/librustc_mir/shim.rs

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -253,7 +253,12 @@ fn new_body<'tcx>(
253253
Body::new(
254254
basic_blocks,
255255
IndexVec::from_elem_n(
256-
SourceScopeData { span, parent_scope: None, local_data: ClearCrossCrate::Clear },
256+
SourceScopeData {
257+
span,
258+
parent_scope: None,
259+
inlined: None,
260+
local_data: ClearCrossCrate::Clear,
261+
},
257262
1,
258263
),
259264
local_decls,

src/librustc_mir/transform/const_prop.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -284,7 +284,7 @@ struct ConstPropagator<'mir, 'tcx> {
284284
param_env: ParamEnv<'tcx>,
285285
// FIXME(eddyb) avoid cloning these two fields more than once,
286286
// by accessing them through `ecx` instead.
287-
source_scopes: IndexVec<SourceScope, SourceScopeData>,
287+
source_scopes: IndexVec<SourceScope, SourceScopeData<'tcx>>,
288288
local_decls: IndexVec<Local, LocalDecl<'tcx>>,
289289
ret: Option<OpTy<'tcx, ()>>,
290290
// Because we have `MutVisitor` we can't obtain the `SourceInfo` from a `Location`. So we store

src/librustc_mir/transform/inline.rs

Lines changed: 5 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -107,7 +107,7 @@ impl Inliner<'tcx> {
107107
let callee_node_id = self.tcx.hir().as_local_node_id(callsite.callee.def_id());
108108

109109
let callee_body = if let Some(callee_node_id) = callee_node_id {
110-
// Avoid a cycle here by only using `optimized_mir` only if we have
110+
// Avoid a cycle here by only using `instance_mir` only if we have
111111
// a lower node id than the callee. This ensures that the callee will
112112
// not inline us. This trick only works without incremental compilation.
113113
// So don't do it if that is enabled.
@@ -414,15 +414,11 @@ impl Inliner<'tcx> {
414414
for mut scope in callee_body.source_scopes.iter().cloned() {
415415
if scope.parent_scope.is_none() {
416416
scope.parent_scope = Some(callsite.source_info.scope);
417-
// FIXME(eddyb) is this really needed?
418-
// (also note that it's always overwritten below)
419-
scope.span = callee_body.span;
420-
}
421417

422-
// FIXME(eddyb) this doesn't seem right at all.
423-
// The inlined source scopes should probably be annotated as
424-
// such, but also contain all of the original information.
425-
scope.span = callsite.source_info.span;
418+
// Mark the outermost callee scope as an inlined one.
419+
assert_eq!(scope.inlined, None);
420+
scope.inlined = Some((callsite.callee, callsite.source_info.span));
421+
}
426422

427423
let idx = caller_body.source_scopes.push(scope);
428424
scope_map.push(idx);

src/librustc_mir/util/pretty.rs

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -495,8 +495,23 @@ fn write_scope_tree(
495495
};
496496

497497
for &child in children {
498-
assert_eq!(body.source_scopes[child].parent_scope, Some(parent));
499-
writeln!(w, "{0:1$}scope {2} {{", "", indent, child.index())?;
498+
let child_data = &body.source_scopes[child];
499+
assert_eq!(child_data.parent_scope, Some(parent));
500+
501+
if let Some((callee, callsite_span)) = child_data.inlined {
502+
let indented_header =
503+
format!("{0:1$}scope {2} (inlined {3}) {{", "", indent, child.index(), callee);
504+
writeln!(
505+
w,
506+
"{0:1$} // at {2}",
507+
indented_header,
508+
ALIGN,
509+
tcx.sess.source_map().span_to_string(callsite_span),
510+
)?;
511+
} else {
512+
writeln!(w, "{0:1$}scope {2} {{", "", indent, child.index())?;
513+
}
514+
500515
write_scope_tree(tcx, body, scope_tree, w, child, depth + 1)?;
501516
writeln!(w, "{0:1$}}}", "", depth * INDENT.len())?;
502517
}

src/librustc_mir_build/build/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -299,7 +299,7 @@ struct Builder<'a, 'tcx> {
299299

300300
/// The vector of all scopes that we have created thus far;
301301
/// we track this for debuginfo later.
302-
source_scopes: IndexVec<SourceScope, SourceScopeData>,
302+
source_scopes: IndexVec<SourceScope, SourceScopeData<'tcx>>,
303303
source_scope: SourceScope,
304304

305305
/// The guard-context: each time we build the guard expression for

src/librustc_mir_build/build/scope.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -684,6 +684,7 @@ impl<'a, 'tcx> Builder<'a, 'tcx> {
684684
self.source_scopes.push(SourceScopeData {
685685
span,
686686
parent_scope: Some(parent),
687+
inlined: None,
687688
local_data: ClearCrossCrate::Set(scope_local_data),
688689
})
689690
}

src/test/mir-opt/inline/inline-closure-borrows-arg.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ fn foo<T: Copy>(_t: T, q: &i32) -> i32 {
3030
// let mut _9: &i32;
3131
// scope 1 {
3232
// debug x => _3;
33-
// scope 2 {
33+
// scope 2 (inlined foo::<T>::{{closure}}#0) {
3434
// debug r => _8;
3535
// debug _s => _9;
3636
// }

src/test/mir-opt/inline/inline-closure-captures.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ fn foo<T: Copy>(t: T, q: i32) -> (i32, T) {
2626
// let mut _11: i32;
2727
// scope 1 {
2828
// debug x => _3;
29-
// scope 2 {
29+
// scope 2 (inlined foo::<T>::{{closure}}#0) {
3030
// debug _q => _11;
3131
// debug q => (*((*_6).0: &i32));
3232
// debug t => (*((*_6).1: &T));

src/test/mir-opt/inline/inline-closure.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ fn foo<T: Copy>(_t: T, q: i32) -> i32 {
2626
// let mut _9: i32;
2727
// scope 1 {
2828
// debug x => _3;
29-
// scope 2 {
29+
// scope 2 (inlined foo::<T>::{{closure}}#0) {
3030
// debug _t => _8;
3131
// debug _q => _9;
3232
// }

src/test/mir-opt/inline/inline-into-box-place.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ fn main() {
4848
// scope 1 {
4949
// debug _x => _1;
5050
// }
51-
// scope 2 {
51+
// scope 2 (inlined std::vec::Vec::<u32>::new) {
5252
// }
5353
// bb0: {
5454
// StorageLive(_1);

src/test/mir-opt/inline/inline-specialization.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ impl<T> Foo for Vec<T> {
3636
// scope 1 {
3737
// debug x => _1;
3838
// }
39-
// scope 2 {
39+
// scope 2 (inlined <std::vec::Vec<()> as Foo>::bar) {
4040
// }
4141
// bb0: {
4242
// StorageLive(_1);

src/test/mir-opt/simplify_try.rs

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -28,10 +28,10 @@ fn main() {
2828
// scope 2 {
2929
// debug err => _6;
3030
// scope 3 {
31-
// scope 7 {
31+
// scope 7 (inlined <i32 as std::convert::From<i32>>::from) {
3232
// debug t => _6;
3333
// }
34-
// scope 8 {
34+
// scope 8 (inlined <std::result::Result<u32, i32> as std::ops::Try>::from_error) {
3535
// debug v => _6;
3636
// let mut _12: i32;
3737
// }
@@ -42,7 +42,7 @@ fn main() {
4242
// scope 5 {
4343
// }
4444
// }
45-
// scope 6 {
45+
// scope 6 (inlined <std::result::Result<u32, i32> as std::ops::Try>::into_result) {
4646
// debug self => _1;
4747
// }
4848
// bb0: {
@@ -87,10 +87,10 @@ fn main() {
8787
// scope 2 {
8888
// debug err => _6;
8989
// scope 3 {
90-
// scope 7 {
90+
// scope 7 (inlined <i32 as std::convert::From<i32>>::from) {
9191
// debug t => _6;
9292
// }
93-
// scope 8 {
93+
// scope 8 (inlined <std::result::Result<u32, i32> as std::ops::Try>::from_error) {
9494
// debug v => _6;
9595
// let mut _12: i32;
9696
// }
@@ -101,7 +101,7 @@ fn main() {
101101
// scope 5 {
102102
// }
103103
// }
104-
// scope 6 {
104+
// scope 6 (inlined <std::result::Result<u32, i32> as std::ops::Try>::into_result) {
105105
// debug self => _1;
106106
// }
107107
// bb0: {
@@ -146,10 +146,10 @@ fn main() {
146146
// scope 2 {
147147
// debug err => _6;
148148
// scope 3 {
149-
// scope 7 {
149+
// scope 7 (inlined <i32 as std::convert::From<i32>>::from) {
150150
// debug t => _6;
151151
// }
152-
// scope 8 {
152+
// scope 8 (inlined <std::result::Result<u32, i32> as std::ops::Try>::from_error) {
153153
// debug v => _6;
154154
// let mut _12: i32;
155155
// }
@@ -160,7 +160,7 @@ fn main() {
160160
// scope 5 {
161161
// }
162162
// }
163-
// scope 6 {
163+
// scope 6 (inlined <std::result::Result<u32, i32> as std::ops::Try>::into_result) {
164164
// debug self => _1;
165165
// }
166166
// bb0: {
@@ -192,10 +192,10 @@ fn main() {
192192
// scope 2 {
193193
// debug err => _3;
194194
// scope 3 {
195-
// scope 7 {
195+
// scope 7 (inlined <i32 as std::convert::From<i32>>::from) {
196196
// debug t => _3;
197197
// }
198-
// scope 8 {
198+
// scope 8 (inlined <std::result::Result<u32, i32> as std::ops::Try>::from_error) {
199199
// debug v => _3;
200200
// }
201201
// }
@@ -205,7 +205,7 @@ fn main() {
205205
// scope 5 {
206206
// }
207207
// }
208-
// scope 6 {
208+
// scope 6 (inlined <std::result::Result<u32, i32> as std::ops::Try>::into_result) {
209209
// debug self => _1;
210210
// }
211211
// bb0: {

0 commit comments

Comments
 (0)