LLVM  4.0.0
DebugHandlerBase.cpp
Go to the documentation of this file.
1 //===-- llvm/lib/CodeGen/AsmPrinter/DebugHandlerBase.cpp -------*- C++ -*--===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // Common functionality for different debug information format backends.
11 // LLVM currently supports DWARF and CodeView.
12 //
13 //===----------------------------------------------------------------------===//
14 
15 #include "DebugHandlerBase.h"
20 #include "llvm/IR/DebugInfo.h"
21 #include "llvm/MC/MCStreamer.h"
23 
24 using namespace llvm;
25 
27 
28 // Each LexicalScope has first instruction and last instruction to mark
29 // beginning and end of a scope respectively. Create an inverse map that list
30 // scopes starts (and ends) with an instruction. One instruction may start (or
31 // end) multiple scopes. Ignore scopes that are not reachable.
35  while (!WorkList.empty()) {
36  LexicalScope *S = WorkList.pop_back_val();
37 
38  const SmallVectorImpl<LexicalScope *> &Children = S->getChildren();
39  if (!Children.empty())
40  WorkList.append(Children.begin(), Children.end());
41 
42  if (S->isAbstractScope())
43  continue;
44 
45  for (const InsnRange &R : S->getRanges()) {
46  assert(R.first && "InsnRange does not have first instruction!");
47  assert(R.second && "InsnRange does not have second instruction!");
48  requestLabelBeforeInsn(R.first);
49  requestLabelAfterInsn(R.second);
50  }
51  }
52 }
53 
54 // Return Label preceding the instruction.
56  MCSymbol *Label = LabelsBeforeInsn.lookup(MI);
57  assert(Label && "Didn't insert label before instruction");
58  return Label;
59 }
60 
61 // Return Label immediately following the instruction.
63  return LabelsAfterInsn.lookup(MI);
64 }
65 
67  const DIExpression *P2) {
68  auto Fragment1 = *P1->getFragmentInfo();
69  auto Fragment2 = *P2->getFragmentInfo();
70  unsigned l1 = Fragment1.OffsetInBits;
71  unsigned l2 = Fragment2.OffsetInBits;
72  unsigned r1 = l1 + Fragment1.SizeInBits;
73  unsigned r2 = l2 + Fragment2.SizeInBits;
74  if (r1 <= l2)
75  return -1;
76  else if (r2 <= l1)
77  return 1;
78  else
79  return 0;
80 }
81 
83  const DIExpression *P2) {
84  if (!P1->isFragment() || !P2->isFragment())
85  return true;
86  return fragmentCmp(P1, P2) == 0;
87 }
88 
89 /// If this type is derived from a base type then return base type size.
91  DIType *Ty = TyRef.resolve();
92  assert(Ty);
94  if (!DDTy)
95  return Ty->getSizeInBits();
96 
97  unsigned Tag = DDTy->getTag();
98 
99  if (Tag != dwarf::DW_TAG_member && Tag != dwarf::DW_TAG_typedef &&
100  Tag != dwarf::DW_TAG_const_type && Tag != dwarf::DW_TAG_volatile_type &&
101  Tag != dwarf::DW_TAG_restrict_type && Tag != dwarf::DW_TAG_atomic_type)
102  return DDTy->getSizeInBits();
103 
104  DIType *BaseType = DDTy->getBaseType().resolve();
105 
106  assert(BaseType && "Unexpected invalid base type");
107 
108  // If this is a derived type, go ahead and get the base type, unless it's a
109  // reference then it's just the size of the field. Pointer types have no need
110  // of this since they're a different type of qualification on the type.
111  if (BaseType->getTag() == dwarf::DW_TAG_reference_type ||
112  BaseType->getTag() == dwarf::DW_TAG_rvalue_reference_type)
113  return Ty->getSizeInBits();
114 
115  return getBaseTypeSize(BaseType);
116 }
117 
119  // Grab the lexical scopes for the function, if we don't have any of those
120  // then we're not going to be able to do anything.
121  LScopes.initialize(*MF);
122  if (LScopes.empty())
123  return;
124 
125  // Make sure that each lexical scope will have a begin/end label.
127 
128  // Calculate history for local variables.
129  assert(DbgValues.empty() && "DbgValues map wasn't cleaned!");
131  DbgValues);
132 
133  // Request labels for the full history.
134  for (const auto &I : DbgValues) {
135  const auto &Ranges = I.second;
136  if (Ranges.empty())
137  continue;
138 
139  // The first mention of a function argument gets the CurrentFnBegin
140  // label, so arguments are visible when breaking at function entry.
141  const DILocalVariable *DIVar = Ranges.front().first->getDebugVariable();
142  if (DIVar->isParameter() &&
143  getDISubprogram(DIVar->getScope())->describes(MF->getFunction())) {
144  LabelsBeforeInsn[Ranges.front().first] = Asm->getFunctionBegin();
145  if (Ranges.front().first->getDebugExpression()->isFragment()) {
146  // Mark all non-overlapping initial fragments.
147  for (auto I = Ranges.begin(); I != Ranges.end(); ++I) {
148  const DIExpression *Fragment = I->first->getDebugExpression();
149  if (std::all_of(Ranges.begin(), I,
151  return !fragmentsOverlap(
152  Fragment, Pred.first->getDebugExpression());
153  }))
154  LabelsBeforeInsn[I->first] = Asm->getFunctionBegin();
155  else
156  break;
157  }
158  }
159  }
160 
161  for (const auto &Range : Ranges) {
162  requestLabelBeforeInsn(Range.first);
163  if (Range.second)
164  requestLabelAfterInsn(Range.second);
165  }
166  }
167 
168  PrevInstLoc = DebugLoc();
170 }
171 
173  if (!MMI->hasDebugInfo())
174  return;
175 
176  assert(CurMI == nullptr);
177  CurMI = MI;
178 
179  // Insert labels where requested.
181  LabelsBeforeInsn.find(MI);
182 
183  // No label needed.
184  if (I == LabelsBeforeInsn.end())
185  return;
186 
187  // Label already assigned.
188  if (I->second)
189  return;
190 
191  if (!PrevLabel) {
193  Asm->OutStreamer->EmitLabel(PrevLabel);
194  }
195  I->second = PrevLabel;
196 }
197 
199  if (!MMI->hasDebugInfo())
200  return;
201 
202  assert(CurMI != nullptr);
203  // Don't create a new label after DBG_VALUE instructions.
204  // They don't generate code.
205  if (!CurMI->isDebugValue()) {
206  PrevLabel = nullptr;
208  }
209 
211  LabelsAfterInsn.find(CurMI);
212  CurMI = nullptr;
213 
214  // No label needed.
215  if (I == LabelsAfterInsn.end())
216  return;
217 
218  // Label already assigned.
219  if (I->second)
220  return;
221 
222  // We need a label after this instruction.
223  if (!PrevLabel) {
225  Asm->OutStreamer->EmitLabel(PrevLabel);
226  }
227  I->second = PrevLabel;
228 }
229 
231  DbgValues.clear();
232  LabelsBeforeInsn.clear();
233  LabelsAfterInsn.clear();
234 }
void calculateDbgValueHistory(const MachineFunction *MF, const TargetRegisterInfo *TRI, DbgValueHistoryMap &Result)
static void r2(uint32_t &A, uint32_t &B, uint32_t &C, uint32_t &D, uint32_t &E, int I, uint32_t *Buf)
Definition: SHA1.cpp:55
std::unique_ptr< MCStreamer > OutStreamer
This is the MCStreamer object for the file we are generating.
Definition: AsmPrinter.h:84
MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...
Definition: MCSymbol.h:39
DILocalScope * getScope() const
Get the local scope for this variable.
const MachineFunction * MF
The current machine function.
Definition: AsmPrinter.h:87
SmallVectorImpl< InsnRange > & getRanges()
Definition: LexicalScopes.h:65
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly...
Definition: STLExtras.h:736
A debug info location.
Definition: DebugLoc.h:34
const Function * getFunction() const
getFunction - Return the LLVM function that this machine code represents
std::pair< const MachineInstr *, const MachineInstr * > InstrRange
LexicalScope - This class is used to track scope information.
Definition: LexicalScopes.h:45
const MachineInstr * CurMI
If nonnull, stores the current machine instruction we're processing.
DebugLoc PrevInstLoc
Previous instruction's location information.
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
SmallVectorImpl< LexicalScope * > & getChildren()
Definition: LexicalScopes.h:64
DbgValueHistoryMap DbgValues
History of DBG_VALUE and clobber instructions for each user variable.
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
Definition: APFloat.h:32
void beginFunction(const MachineFunction *MF) override
Gather pre-function debug information.
Holds a subclass of DINode.
bool hasDebugInfo() const
Returns true if valid debug info is present.
DISubprogram * getDISubprogram(const MDNode *Scope)
Find subprogram that is enclosing this scope.
Definition: DebugInfo.cpp:34
LLVM_NODISCARD bool empty() const
Definition: SmallVector.h:60
LexicalScope * getCurrentFunctionScope() const
getCurrentFunctionScope - Return lexical scope for the current function.
DebugHandlerBase(AsmPrinter *A)
void identifyScopeMarkers()
Indentify instructions that are marking the beginning of or ending of a scope.
void initialize(const MachineFunction &)
initialize - Scan machine function and constuct lexical scope nest, resets the instance if necessary...
static Optional< FragmentInfo > getFragmentInfo(expr_op_iterator Start, expr_op_iterator End)
Retrieve the details of this fragment expression.
DenseMap< const MachineInstr *, MCSymbol * > LabelsAfterInsn
Maps instruction with label emitted after instruction.
void requestLabelBeforeInsn(const MachineInstr *MI)
Ensure that a label will be emitted before MI.
bool isFragment() const
Return whether this is a piece of an aggregate variable.
const MachineBasicBlock * getParent() const
Definition: MachineInstr.h:131
bool isDebugValue() const
Definition: MachineInstr.h:777
MCSymbol * createTempSymbol(bool CanBeUnnamed=true)
Create and return a new assembler temporary symbol with a unique but unspecified name.
Definition: MCContext.cpp:218
static bool fragmentsOverlap(const DIExpression *P1, const DIExpression *P2)
Determine whether two variable fragments overlap.
const MachineBasicBlock * PrevInstBB
LLVM_ATTRIBUTE_ALWAYS_INLINE iterator begin()
Definition: SmallVector.h:115
AsmPrinter * Asm
Target of debug info emission.
This class is intended to be used as a driving class for all asm writers.
Definition: AsmPrinter.h:67
DenseMap< const MachineInstr *, MCSymbol * > LabelsBeforeInsn
Maps instruction with label emitted before instruction.
void beginInstruction(const MachineInstr *MI) override
Process beginning of an instruction.
bool isAbstractScope() const
Definition: LexicalScopes.h:63
void endFunction(const MachineFunction *MF) override
Gather post-function debug information.
static void r1(uint32_t &A, uint32_t &B, uint32_t &C, uint32_t &D, uint32_t &E, int I, uint32_t *Buf)
Definition: SHA1.cpp:49
void append(in_iter in_start, in_iter in_end)
Add the specified range to the end of the SmallVector.
Definition: SmallVector.h:392
MCSymbol * getLabelAfterInsn(const MachineInstr *MI)
Return Label immediately following the instruction.
unsigned getTag() const
Base class for types.
const MCContext & getContext() const
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small...
Definition: SmallVector.h:843
LLVM_NODISCARD T pop_back_val()
Definition: SmallVector.h:382
DWARF expression.
void requestLabelAfterInsn(const MachineInstr *MI)
Ensure that a label will be emitted after MI.
Representation of each machine instruction.
Definition: MachineInstr.h:52
LLVM_ATTRIBUTE_ALWAYS_INLINE iterator end()
Definition: SmallVector.h:119
MCSymbol * getFunctionBegin() const
Definition: AsmPrinter.h:168
#define I(x, y, z)
Definition: MD5.cpp:54
uint64_t getSizeInBits() const
LLVM_NODISCARD std::enable_if<!is_simple_type< Y >::value, typename cast_retty< X, const Y >::ret_type >::type dyn_cast(const Y &Val)
Definition: Casting.h:287
std::pair< const MachineInstr *, const MachineInstr * > InsnRange
InsnRange - This is used to track range of instructions with identical lexical scope.
Definition: LexicalScopes.h:34
void endInstruction() override
Process end of an instruction.
MCSymbol * getLabelBeforeInsn(const MachineInstr *MI)
Return Label preceding the instruction.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
static int fragmentCmp(const DIExpression *P1, const DIExpression *P2)
Determine the relative position of the fragments described by P1 and P2.
MachineModuleInfo * MMI
Collected machine module information.
static uint64_t getBaseTypeSize(const DITypeRef TyRef)
If this type is derived from a base type then return base type size.
IRTranslator LLVM IR MI
virtual const TargetRegisterInfo * getRegisterInfo() const
getRegisterInfo - If register information is available, return it.
static GCRegistry::Add< ErlangGC > A("erlang","erlang-compatible garbage collector")
bool empty()
empty - Return true if there is any lexical scope information available.