Skip to content

Commit f1c72cc

Browse files
Rollup merge of rust-lang#117972 - ouz-a:stable_debuginfo, r=celinval
Add VarDebugInfo to Stable MIR Previously we omitted `VarDebugInfo` because we didn't have `Projection` now that rust-lang#117517 is merged it's possible to add `VarDebugInfo` information in `Body`. This PR adds stable version of the `VarDebugInfo` to `Body` r? `@celinval`
2 parents baf4abf + 965f46b commit f1c72cc

File tree

3 files changed

+128
-6
lines changed

3 files changed

+128
-6
lines changed

Diff for: compiler/rustc_smir/src/rustc_smir/mod.rs

+54-1
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,10 @@ use rustc_middle::ty::{self, Instance, ParamEnv, Ty, TyCtxt, Variance};
1818
use rustc_span::def_id::{CrateNum, DefId, LOCAL_CRATE};
1919
use rustc_target::abi::FieldIdx;
2020
use stable_mir::mir::mono::InstanceDef;
21-
use stable_mir::mir::{Body, CopyNonOverlapping, Statement, UserTypeProjection, VariantIdx};
21+
use stable_mir::mir::{
22+
Body, ConstOperand, CopyNonOverlapping, Statement, UserTypeProjection, VarDebugInfoFragment,
23+
VariantIdx,
24+
};
2225
use stable_mir::ty::{
2326
AdtDef, AdtKind, ClosureDef, ClosureKind, Const, ConstId, ConstantKind, EarlyParamRegion,
2427
FloatTy, FnDef, GenericArgs, GenericParamDef, IntTy, LineInfo, Movability, RigidTy, Span,
@@ -412,17 +415,67 @@ impl<'tcx> Stable<'tcx> for mir::Body<'tcx> {
412415
})
413416
.collect(),
414417
self.arg_count,
418+
self.var_debug_info.iter().map(|info| info.stable(tables)).collect(),
415419
)
416420
}
417421
}
418422

423+
impl<'tcx> Stable<'tcx> for mir::VarDebugInfo<'tcx> {
424+
type T = stable_mir::mir::VarDebugInfo;
425+
fn stable(&self, tables: &mut Tables<'tcx>) -> Self::T {
426+
stable_mir::mir::VarDebugInfo {
427+
name: self.name.to_string(),
428+
source_info: self.source_info.stable(tables),
429+
composite: self.composite.as_ref().map(|composite| composite.stable(tables)),
430+
value: self.value.stable(tables),
431+
argument_index: self.argument_index,
432+
}
433+
}
434+
}
435+
419436
impl<'tcx> Stable<'tcx> for mir::Statement<'tcx> {
420437
type T = stable_mir::mir::Statement;
421438
fn stable(&self, tables: &mut Tables<'tcx>) -> Self::T {
422439
Statement { kind: self.kind.stable(tables), span: self.source_info.span.stable(tables) }
423440
}
424441
}
425442

443+
impl<'tcx> Stable<'tcx> for mir::SourceInfo {
444+
type T = stable_mir::mir::SourceInfo;
445+
fn stable(&self, tables: &mut Tables<'tcx>) -> Self::T {
446+
stable_mir::mir::SourceInfo { span: self.span.stable(tables), scope: self.scope.into() }
447+
}
448+
}
449+
450+
impl<'tcx> Stable<'tcx> for mir::VarDebugInfoFragment<'tcx> {
451+
type T = stable_mir::mir::VarDebugInfoFragment;
452+
fn stable(&self, tables: &mut Tables<'tcx>) -> Self::T {
453+
VarDebugInfoFragment {
454+
ty: self.ty.stable(tables),
455+
projection: self.projection.iter().map(|e| e.stable(tables)).collect(),
456+
}
457+
}
458+
}
459+
460+
impl<'tcx> Stable<'tcx> for mir::VarDebugInfoContents<'tcx> {
461+
type T = stable_mir::mir::VarDebugInfoContents;
462+
fn stable(&self, tables: &mut Tables<'tcx>) -> Self::T {
463+
match self {
464+
mir::VarDebugInfoContents::Place(place) => {
465+
stable_mir::mir::VarDebugInfoContents::Place(place.stable(tables))
466+
}
467+
mir::VarDebugInfoContents::Const(const_operand) => {
468+
let op = ConstOperand {
469+
span: const_operand.span.stable(tables),
470+
user_ty: const_operand.user_ty.map(|index| index.as_usize()),
471+
const_: const_operand.const_.stable(tables),
472+
};
473+
stable_mir::mir::VarDebugInfoContents::Const(op)
474+
}
475+
}
476+
}
477+
}
478+
426479
impl<'tcx> Stable<'tcx> for mir::StatementKind<'tcx> {
427480
type T = stable_mir::mir::StatementKind;
428481
fn stable(&self, tables: &mut Tables<'tcx>) -> Self::T {

Diff for: compiler/stable_mir/src/mir/body.rs

+47-4
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
use crate::mir::pretty::{function_body, pretty_statement};
22
use crate::ty::{AdtDef, ClosureDef, Const, CoroutineDef, GenericArgs, Movability, Region, Ty};
3-
use crate::Opaque;
4-
use crate::Span;
3+
use crate::{Opaque, Span, Symbol};
54
use std::io;
65
/// The SMIR representation of a single function.
76
#[derive(Clone, Debug)]
@@ -17,21 +16,29 @@ pub struct Body {
1716

1817
// The number of arguments this function takes.
1918
pub(super) arg_count: usize,
19+
20+
// Debug information pertaining to user variables, including captures.
21+
pub(super) var_debug_info: Vec<VarDebugInfo>,
2022
}
2123

2224
impl Body {
2325
/// Constructs a `Body`.
2426
///
2527
/// A constructor is required to build a `Body` from outside the crate
2628
/// because the `arg_count` and `locals` fields are private.
27-
pub fn new(blocks: Vec<BasicBlock>, locals: LocalDecls, arg_count: usize) -> Self {
29+
pub fn new(
30+
blocks: Vec<BasicBlock>,
31+
locals: LocalDecls,
32+
arg_count: usize,
33+
var_debug_info: Vec<VarDebugInfo>,
34+
) -> Self {
2835
// If locals doesn't contain enough entries, it can lead to panics in
2936
// `ret_local`, `arg_locals`, and `inner_locals`.
3037
assert!(
3138
locals.len() > arg_count,
3239
"A Body must contain at least a local for the return value and each of the function's arguments"
3340
);
34-
Self { blocks, locals, arg_count }
41+
Self { blocks, locals, arg_count, var_debug_info }
3542
}
3643

3744
/// Return local that holds this function's return value.
@@ -425,6 +432,42 @@ pub struct Place {
425432
pub projection: Vec<ProjectionElem>,
426433
}
427434

435+
#[derive(Clone, Debug, Eq, PartialEq)]
436+
pub struct VarDebugInfo {
437+
pub name: Symbol,
438+
pub source_info: SourceInfo,
439+
pub composite: Option<VarDebugInfoFragment>,
440+
pub value: VarDebugInfoContents,
441+
pub argument_index: Option<u16>,
442+
}
443+
444+
pub type SourceScope = u32;
445+
446+
#[derive(Clone, Debug, Eq, PartialEq)]
447+
pub struct SourceInfo {
448+
pub span: Span,
449+
pub scope: SourceScope,
450+
}
451+
452+
#[derive(Clone, Debug, Eq, PartialEq)]
453+
pub struct VarDebugInfoFragment {
454+
pub ty: Ty,
455+
pub projection: Vec<ProjectionElem>,
456+
}
457+
458+
#[derive(Clone, Debug, Eq, PartialEq)]
459+
pub enum VarDebugInfoContents {
460+
Place(Place),
461+
Const(ConstOperand),
462+
}
463+
464+
#[derive(Clone, Debug, Eq, PartialEq)]
465+
pub struct ConstOperand {
466+
pub span: Span,
467+
pub user_ty: Option<UserTypeAnnotationIndex>,
468+
pub const_: Const,
469+
}
470+
428471
// In MIR ProjectionElem is parameterized on the second Field argument and the Index argument. This
429472
// is so it can be used for both Places (for which the projection elements are of type
430473
// ProjectionElem<Local, Ty>) and user-provided type annotations (for which the projection elements

Diff for: compiler/stable_mir/src/mir/visit.rs

+27-1
Original file line numberDiff line numberDiff line change
@@ -128,8 +128,12 @@ pub trait MirVisitor {
128128
self.super_assert_msg(msg, location)
129129
}
130130

131+
fn visit_var_debug_info(&mut self, var_debug_info: &VarDebugInfo) {
132+
self.super_var_debug_info(var_debug_info);
133+
}
134+
131135
fn super_body(&mut self, body: &Body) {
132-
let Body { blocks, locals: _, arg_count } = body;
136+
let Body { blocks, locals: _, arg_count, var_debug_info } = body;
133137

134138
for bb in blocks {
135139
self.visit_basic_block(bb);
@@ -145,6 +149,10 @@ pub trait MirVisitor {
145149
for (idx, arg) in body.inner_locals().iter().enumerate() {
146150
self.visit_local_decl(idx + local_start, arg)
147151
}
152+
153+
for info in var_debug_info.iter() {
154+
self.visit_var_debug_info(info);
155+
}
148156
}
149157

150158
fn super_basic_block(&mut self, bb: &BasicBlock) {
@@ -382,6 +390,24 @@ pub trait MirVisitor {
382390
let _ = args;
383391
}
384392

393+
fn super_var_debug_info(&mut self, var_debug_info: &VarDebugInfo) {
394+
let VarDebugInfo { source_info, composite, value, name: _, argument_index: _ } =
395+
var_debug_info;
396+
self.visit_span(&source_info.span);
397+
let location = Location(source_info.span);
398+
if let Some(composite) = composite {
399+
self.visit_ty(&composite.ty, location);
400+
}
401+
match value {
402+
VarDebugInfoContents::Place(place) => {
403+
self.visit_place(place, PlaceContext::NON_USE, location);
404+
}
405+
VarDebugInfoContents::Const(constant) => {
406+
self.visit_const(&constant.const_, location);
407+
}
408+
}
409+
}
410+
385411
fn super_assert_msg(&mut self, msg: &AssertMessage, location: Location) {
386412
match msg {
387413
AssertMessage::BoundsCheck { len, index } => {

0 commit comments

Comments
 (0)