From b33d1e26b220062e23bb202c6765663c157d971b Mon Sep 17 00:00:00 2001 From: Wesley Wiser Date: Wed, 7 Dec 2022 13:47:51 -0500 Subject: [PATCH] Make `debuginfo_offset_calcuation` generic so we can resuse the logic This will allow us to separate the act of calculating the offsets from creating LLVM IR that performs the actions. --- .../rustc_codegen_ssa/src/mir/debuginfo.rs | 51 +++++++++++++++---- 1 file changed, 41 insertions(+), 10 deletions(-) diff --git a/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs b/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs index 22e9eeea255..8935d42548f 100644 --- a/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs +++ b/compiler/rustc_codegen_ssa/src/mir/debuginfo.rs @@ -3,12 +3,12 @@ use rustc_index::vec::IndexVec; use rustc_middle::middle::codegen_fn_attrs::CodegenFnAttrFlags; use rustc_middle::mir; use rustc_middle::ty; +use rustc_middle::ty::layout::TyAndLayout; use rustc_middle::ty::layout::{HasTyCtxt, LayoutOf}; use rustc_session::config::DebugInfo; use rustc_span::symbol::{kw, Symbol}; use rustc_span::{BytePos, Span}; -use rustc_target::abi::Abi; -use rustc_target::abi::Size; +use rustc_target::abi::{Abi, Size, VariantIdx}; use super::operand::{OperandRef, OperandValue}; use super::place::PlaceRef; @@ -76,6 +76,33 @@ impl<'tcx, S: Copy, L: Copy> DebugScope { } } +trait DebugInfoOffsetLocation<'tcx, Bx> { + fn deref(&self, bx: &mut Bx) -> Self; + fn layout(&self) -> TyAndLayout<'tcx>; + fn project_field(&self, bx: &mut Bx, field: mir::Field) -> Self; + fn downcast(&self, bx: &mut Bx, variant: VariantIdx) -> Self; +} + +impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> DebugInfoOffsetLocation<'tcx, Bx> + for PlaceRef<'tcx, Bx::Value> +{ + fn deref(&self, bx: &mut Bx) -> Self { + bx.load_operand(*self).deref(bx.cx()) + } + + fn layout(&self) -> TyAndLayout<'tcx> { + self.layout + } + + fn project_field(&self, bx: &mut Bx, field: mir::Field) -> Self { + PlaceRef::project_field(*self, bx, field.index()) + } + + fn downcast(&self, bx: &mut Bx, variant: VariantIdx) -> Self { + self.project_downcast(bx, variant) + } +} + struct DebugInfoOffset { /// Offset from the `base` used to calculate the debuginfo offset. direct_offset: Size, @@ -86,12 +113,17 @@ struct DebugInfoOffset { result: T, } -fn calculate_debuginfo_offset<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>( +fn calculate_debuginfo_offset< + 'a, + 'tcx, + Bx: BuilderMethods<'a, 'tcx>, + L: DebugInfoOffsetLocation<'tcx, Bx>, +>( bx: &mut Bx, local: mir::Local, var: &PerLocalVarDebugInfo<'tcx, Bx::DIVariable>, - base: PlaceRef<'tcx, Bx::Value>, -) -> DebugInfoOffset> { + base: L, +) -> DebugInfoOffset { let mut direct_offset = Size::ZERO; // FIXME(eddyb) use smallvec here. let mut indirect_offsets = vec![]; @@ -101,16 +133,15 @@ fn calculate_debuginfo_offset<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>>( match *elem { mir::ProjectionElem::Deref => { indirect_offsets.push(Size::ZERO); - place = bx.load_operand(place).deref(bx.cx()); + place = place.deref(bx); } mir::ProjectionElem::Field(field, _) => { - let i = field.index(); let offset = indirect_offsets.last_mut().unwrap_or(&mut direct_offset); - *offset += place.layout.fields.offset(i); - place = place.project_field(bx, i); + *offset += place.layout().fields.offset(field.index()); + place = place.project_field(bx, field); } mir::ProjectionElem::Downcast(_, variant) => { - place = place.project_downcast(bx, variant); + place = place.downcast(bx, variant); } _ => span_bug!( var.source_info.span,