blob: 684b0cd92c714d59e8bff558c7fb93a69b8b48f2 [file] [log] [blame]
Bill Wendling0310d762009-05-15 09:23:25 +00001//===-- llvm/CodeGen/DwarfDebug.cpp - Dwarf Debug Framework ---------------===//
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// This file contains support for writing dwarf debug info into asm files.
11//
12//===----------------------------------------------------------------------===//
Chris Lattner6cde3e62010-03-09 00:39:24 +000013
Devang Patele4b27562009-08-28 23:24:31 +000014#define DEBUG_TYPE "dwarfdebug"
Bill Wendling0310d762009-05-15 09:23:25 +000015#include "DwarfDebug.h"
Chris Lattner74e41f92010-04-05 05:24:55 +000016#include "DIE.h"
Bill Wendling0310d762009-05-15 09:23:25 +000017#include "llvm/Module.h"
David Greeneb2c66fc2009-08-19 21:52:55 +000018#include "llvm/CodeGen/MachineFunction.h"
Bill Wendling0310d762009-05-15 09:23:25 +000019#include "llvm/CodeGen/MachineModuleInfo.h"
Chris Lattnerb7db7332010-03-09 01:58:53 +000020#include "llvm/MC/MCAsmInfo.h"
Chris Lattnera87dea42009-07-31 18:48:30 +000021#include "llvm/MC/MCSection.h"
Chris Lattner6c2f9e12009-08-19 05:49:37 +000022#include "llvm/MC/MCStreamer.h"
Chris Lattnerb7db7332010-03-09 01:58:53 +000023#include "llvm/MC/MCSymbol.h"
Chris Lattner45111d12010-01-16 21:57:06 +000024#include "llvm/Target/Mangler.h"
Bill Wendling0310d762009-05-15 09:23:25 +000025#include "llvm/Target/TargetData.h"
26#include "llvm/Target/TargetFrameInfo.h"
Chris Lattnerf0144122009-07-28 03:13:23 +000027#include "llvm/Target/TargetLoweringObjectFile.h"
Chris Lattner9d1c1ad2010-04-04 18:06:11 +000028#include "llvm/Target/TargetMachine.h"
Chris Lattnerf0144122009-07-28 03:13:23 +000029#include "llvm/Target/TargetRegisterInfo.h"
Chris Lattner74e41f92010-04-05 05:24:55 +000030#include "llvm/Analysis/DebugInfo.h"
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +000031#include "llvm/ADT/STLExtras.h"
Chris Lattner23132b12009-08-24 03:52:50 +000032#include "llvm/ADT/StringExtras.h"
Daniel Dunbar6e4bdfc2009-10-13 06:47:08 +000033#include "llvm/Support/Debug.h"
34#include "llvm/Support/ErrorHandling.h"
Devang Patel3139fcf2010-01-26 21:39:14 +000035#include "llvm/Support/ValueHandle.h"
Chris Lattner0ad9c912010-01-22 22:09:00 +000036#include "llvm/Support/FormattedStream.h"
Chris Lattnera87dea42009-07-31 18:48:30 +000037#include "llvm/Support/Timer.h"
38#include "llvm/System/Path.h"
Bill Wendling0310d762009-05-15 09:23:25 +000039using namespace llvm;
40
Bill Wendling0310d762009-05-15 09:23:25 +000041//===----------------------------------------------------------------------===//
42
43/// Configuration values for initial hash set sizes (log2).
44///
Bill Wendling0310d762009-05-15 09:23:25 +000045static const unsigned InitAbbreviationsSetSize = 9; // log2(512)
Bill Wendling0310d762009-05-15 09:23:25 +000046
47namespace llvm {
48
49//===----------------------------------------------------------------------===//
50/// CompileUnit - This dwarf writer support class manages information associate
51/// with a source file.
Nick Lewycky5f9843f2009-11-17 08:11:44 +000052class CompileUnit {
Bill Wendling0310d762009-05-15 09:23:25 +000053 /// ID - File identifier for source.
54 ///
55 unsigned ID;
56
57 /// Die - Compile unit debug information entry.
58 ///
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +000059 const OwningPtr<DIE> CUDie;
Bill Wendling0310d762009-05-15 09:23:25 +000060
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +000061 /// IndexTyDie - An anonymous type for index type. Owned by CUDie.
Devang Patel6f01d9c2009-11-21 00:31:03 +000062 DIE *IndexTyDie;
63
Bill Wendling0310d762009-05-15 09:23:25 +000064 /// GVToDieMap - Tracks the mapping of unit level debug informaton
65 /// variables to debug information entries.
Devang Patele4b27562009-08-28 23:24:31 +000066 /// FIXME : Rename GVToDieMap -> NodeToDieMap
Devang Patel622b0262010-01-19 06:19:05 +000067 DenseMap<MDNode *, DIE *> GVToDieMap;
Bill Wendling0310d762009-05-15 09:23:25 +000068
69 /// GVToDIEEntryMap - Tracks the mapping of unit level debug informaton
70 /// descriptors to debug information entries using a DIEEntry proxy.
Devang Patele4b27562009-08-28 23:24:31 +000071 /// FIXME : Rename
Devang Patel622b0262010-01-19 06:19:05 +000072 DenseMap<MDNode *, DIEEntry *> GVToDIEEntryMap;
Bill Wendling0310d762009-05-15 09:23:25 +000073
74 /// Globals - A map of globally visible named entities for this unit.
75 ///
76 StringMap<DIE*> Globals;
77
Devang Patel193f7202009-11-24 01:14:22 +000078 /// GlobalTypes - A map of globally visible types for this unit.
79 ///
80 StringMap<DIE*> GlobalTypes;
81
Bill Wendling0310d762009-05-15 09:23:25 +000082public:
83 CompileUnit(unsigned I, DIE *D)
Devang Patel2c4ceb12009-11-21 02:48:08 +000084 : ID(I), CUDie(D), IndexTyDie(0) {}
Bill Wendling0310d762009-05-15 09:23:25 +000085
86 // Accessors.
Devang Patel193f7202009-11-24 01:14:22 +000087 unsigned getID() const { return ID; }
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +000088 DIE* getCUDie() const { return CUDie.get(); }
Devang Patel193f7202009-11-24 01:14:22 +000089 const StringMap<DIE*> &getGlobals() const { return Globals; }
90 const StringMap<DIE*> &getGlobalTypes() const { return GlobalTypes; }
Bill Wendling0310d762009-05-15 09:23:25 +000091
92 /// hasContent - Return true if this compile unit has something to write out.
93 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +000094 bool hasContent() const { return !CUDie->getChildren().empty(); }
Bill Wendling0310d762009-05-15 09:23:25 +000095
Devang Patel2c4ceb12009-11-21 02:48:08 +000096 /// addGlobal - Add a new global entity to the compile unit.
Bill Wendling0310d762009-05-15 09:23:25 +000097 ///
Benjamin Kramerbbb88db2010-03-31 20:15:45 +000098 void addGlobal(StringRef Name, DIE *Die) { Globals[Name] = Die; }
Bill Wendling0310d762009-05-15 09:23:25 +000099
Devang Patel193f7202009-11-24 01:14:22 +0000100 /// addGlobalType - Add a new global type to the compile unit.
101 ///
Benjamin Kramerbbb88db2010-03-31 20:15:45 +0000102 void addGlobalType(StringRef Name, DIE *Die) {
Devang Patel193f7202009-11-24 01:14:22 +0000103 GlobalTypes[Name] = Die;
104 }
105
Devang Patel017d1212009-11-20 21:37:22 +0000106 /// getDIE - Returns the debug information entry map slot for the
Bill Wendling0310d762009-05-15 09:23:25 +0000107 /// specified debug variable.
Devang Patel017d1212009-11-20 21:37:22 +0000108 DIE *getDIE(MDNode *N) { return GVToDieMap.lookup(N); }
Jim Grosbach31ef40e2009-11-21 23:12:12 +0000109
Devang Patel017d1212009-11-20 21:37:22 +0000110 /// insertDIE - Insert DIE into the map.
111 void insertDIE(MDNode *N, DIE *D) {
112 GVToDieMap.insert(std::make_pair(N, D));
113 }
Bill Wendling0310d762009-05-15 09:23:25 +0000114
Devang Patel017d1212009-11-20 21:37:22 +0000115 /// getDIEEntry - Returns the debug information entry for the speciefied
116 /// debug variable.
Devang Patel6404e4e2009-12-15 19:16:48 +0000117 DIEEntry *getDIEEntry(MDNode *N) {
Devang Patel622b0262010-01-19 06:19:05 +0000118 DenseMap<MDNode *, DIEEntry *>::iterator I = GVToDIEEntryMap.find(N);
Devang Patel6404e4e2009-12-15 19:16:48 +0000119 if (I == GVToDIEEntryMap.end())
120 return NULL;
121 return I->second;
122 }
Devang Patel017d1212009-11-20 21:37:22 +0000123
124 /// insertDIEEntry - Insert debug information entry into the map.
125 void insertDIEEntry(MDNode *N, DIEEntry *E) {
126 GVToDIEEntryMap.insert(std::make_pair(N, E));
Bill Wendling0310d762009-05-15 09:23:25 +0000127 }
128
Devang Patel2c4ceb12009-11-21 02:48:08 +0000129 /// addDie - Adds or interns the DIE to the compile unit.
Bill Wendling0310d762009-05-15 09:23:25 +0000130 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000131 void addDie(DIE *Buffer) {
132 this->CUDie->addChild(Buffer);
Bill Wendling0310d762009-05-15 09:23:25 +0000133 }
Devang Patel6f01d9c2009-11-21 00:31:03 +0000134
135 // getIndexTyDie - Get an anonymous type for index type.
136 DIE *getIndexTyDie() {
137 return IndexTyDie;
138 }
139
Jim Grosbach7ab38df2009-11-22 19:20:36 +0000140 // setIndexTyDie - Set D as anonymous type for index which can be reused
141 // later.
Devang Patel6f01d9c2009-11-21 00:31:03 +0000142 void setIndexTyDie(DIE *D) {
143 IndexTyDie = D;
144 }
145
Bill Wendling0310d762009-05-15 09:23:25 +0000146};
147
148//===----------------------------------------------------------------------===//
149/// DbgVariable - This class is used to track local variable information.
150///
Devang Patelf76a3d62009-11-16 21:53:40 +0000151class DbgVariable {
Bill Wendling0310d762009-05-15 09:23:25 +0000152 DIVariable Var; // Variable Descriptor.
153 unsigned FrameIndex; // Variable frame index.
Devang Patel90a48ad2010-03-15 18:33:46 +0000154 const MachineInstr *DbgValueMInsn; // DBG_VALUE
Devang Patelaead63c2010-03-29 22:59:58 +0000155 // DbgValueLabel - DBG_VALUE is effective from this label.
156 MCSymbol *DbgValueLabel;
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000157 DbgVariable *const AbstractVar; // Abstract variable for this variable.
Devang Patel53bb5c92009-11-10 23:06:00 +0000158 DIE *TheDIE;
Bill Wendling0310d762009-05-15 09:23:25 +0000159public:
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000160 // AbsVar may be NULL.
161 DbgVariable(DIVariable V, unsigned I, DbgVariable *AbsVar)
Devang Patelaead63c2010-03-29 22:59:58 +0000162 : Var(V), FrameIndex(I), DbgValueMInsn(0),
163 DbgValueLabel(0), AbstractVar(AbsVar), TheDIE(0) {}
Devang Patel90a48ad2010-03-15 18:33:46 +0000164 DbgVariable(DIVariable V, const MachineInstr *MI, DbgVariable *AbsVar)
Devang Patelaead63c2010-03-29 22:59:58 +0000165 : Var(V), FrameIndex(0), DbgValueMInsn(MI), DbgValueLabel(0),
166 AbstractVar(AbsVar), TheDIE(0)
Devang Patel90a48ad2010-03-15 18:33:46 +0000167 {}
Bill Wendling0310d762009-05-15 09:23:25 +0000168
169 // Accessors.
Devang Patel53bb5c92009-11-10 23:06:00 +0000170 DIVariable getVariable() const { return Var; }
171 unsigned getFrameIndex() const { return FrameIndex; }
Devang Patel90a48ad2010-03-15 18:33:46 +0000172 const MachineInstr *getDbgValue() const { return DbgValueMInsn; }
Devang Patelaead63c2010-03-29 22:59:58 +0000173 MCSymbol *getDbgValueLabel() const { return DbgValueLabel; }
174 void setDbgValueLabel(MCSymbol *L) { DbgValueLabel = L; }
Devang Patel53bb5c92009-11-10 23:06:00 +0000175 DbgVariable *getAbstractVariable() const { return AbstractVar; }
176 void setDIE(DIE *D) { TheDIE = D; }
177 DIE *getDIE() const { return TheDIE; }
Bill Wendling0310d762009-05-15 09:23:25 +0000178};
179
180//===----------------------------------------------------------------------===//
181/// DbgScope - This class is used to track scope information.
182///
Devang Patelf76a3d62009-11-16 21:53:40 +0000183class DbgScope {
Bill Wendling0310d762009-05-15 09:23:25 +0000184 DbgScope *Parent; // Parent to this scope.
Jim Grosbach31ef40e2009-11-21 23:12:12 +0000185 DIDescriptor Desc; // Debug info descriptor for scope.
Devang Patel3139fcf2010-01-26 21:39:14 +0000186 // Location at which this scope is inlined.
187 AssertingVH<MDNode> InlinedAtLocation;
Devang Patel53bb5c92009-11-10 23:06:00 +0000188 bool AbstractScope; // Abstract Scope
Chris Lattnerb7db7332010-03-09 01:58:53 +0000189 MCSymbol *StartLabel; // Label ID of the beginning of scope.
190 MCSymbol *EndLabel; // Label ID of the end of scope.
Devang Pateld38dd112009-10-01 18:25:23 +0000191 const MachineInstr *LastInsn; // Last instruction of this scope.
192 const MachineInstr *FirstInsn; // First instruction of this scope.
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000193 // Scopes defined in scope. Contents not owned.
194 SmallVector<DbgScope *, 4> Scopes;
195 // Variables declared in scope. Contents owned.
196 SmallVector<DbgVariable *, 8> Variables;
Daniel Dunbarf612ff62009-09-19 20:40:05 +0000197
Owen Anderson04c05f72009-06-24 22:53:20 +0000198 // Private state for dump()
199 mutable unsigned IndentLevel;
Bill Wendling0310d762009-05-15 09:23:25 +0000200public:
Devang Patelc90aefe2009-10-14 21:08:09 +0000201 DbgScope(DbgScope *P, DIDescriptor D, MDNode *I = 0)
Devang Patel53bb5c92009-11-10 23:06:00 +0000202 : Parent(P), Desc(D), InlinedAtLocation(I), AbstractScope(false),
Chris Lattnerb7db7332010-03-09 01:58:53 +0000203 StartLabel(0), EndLabel(0),
Devang Patelc90aefe2009-10-14 21:08:09 +0000204 LastInsn(0), FirstInsn(0), IndentLevel(0) {}
Bill Wendling0310d762009-05-15 09:23:25 +0000205 virtual ~DbgScope();
206
207 // Accessors.
208 DbgScope *getParent() const { return Parent; }
Devang Patel53bb5c92009-11-10 23:06:00 +0000209 void setParent(DbgScope *P) { Parent = P; }
Bill Wendling0310d762009-05-15 09:23:25 +0000210 DIDescriptor getDesc() const { return Desc; }
Chris Lattnerbc733f52010-03-13 02:17:42 +0000211 MDNode *getInlinedAt() const { return InlinedAtLocation; }
Devang Patel53bb5c92009-11-10 23:06:00 +0000212 MDNode *getScopeNode() const { return Desc.getNode(); }
Chris Lattnerb7db7332010-03-09 01:58:53 +0000213 MCSymbol *getStartLabel() const { return StartLabel; }
214 MCSymbol *getEndLabel() const { return EndLabel; }
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000215 const SmallVector<DbgScope *, 4> &getScopes() { return Scopes; }
216 const SmallVector<DbgVariable *, 8> &getVariables() { return Variables; }
Chris Lattnerb7db7332010-03-09 01:58:53 +0000217 void setStartLabel(MCSymbol *S) { StartLabel = S; }
218 void setEndLabel(MCSymbol *E) { EndLabel = E; }
Devang Pateld38dd112009-10-01 18:25:23 +0000219 void setLastInsn(const MachineInstr *MI) { LastInsn = MI; }
220 const MachineInstr *getLastInsn() { return LastInsn; }
221 void setFirstInsn(const MachineInstr *MI) { FirstInsn = MI; }
Devang Patel53bb5c92009-11-10 23:06:00 +0000222 void setAbstractScope() { AbstractScope = true; }
223 bool isAbstractScope() const { return AbstractScope; }
Devang Pateld38dd112009-10-01 18:25:23 +0000224 const MachineInstr *getFirstInsn() { return FirstInsn; }
Devang Patel53bb5c92009-11-10 23:06:00 +0000225
Devang Patel2c4ceb12009-11-21 02:48:08 +0000226 /// addScope - Add a scope to the scope.
Bill Wendling0310d762009-05-15 09:23:25 +0000227 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000228 void addScope(DbgScope *S) { Scopes.push_back(S); }
Bill Wendling0310d762009-05-15 09:23:25 +0000229
Devang Patel2c4ceb12009-11-21 02:48:08 +0000230 /// addVariable - Add a variable to the scope.
Bill Wendling0310d762009-05-15 09:23:25 +0000231 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000232 void addVariable(DbgVariable *V) { Variables.push_back(V); }
Bill Wendling0310d762009-05-15 09:23:25 +0000233
Devang Patel344130e2010-01-04 20:44:00 +0000234 void fixInstructionMarkers(DenseMap<const MachineInstr *,
235 unsigned> &MIIndexMap) {
Chris Lattnered7a77b2010-03-31 05:36:29 +0000236 assert(getFirstInsn() && "First instruction is missing!");
Devang Patel344130e2010-01-04 20:44:00 +0000237
238 // Use the end of last child scope as end of this scope.
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000239 const SmallVector<DbgScope *, 4> &Scopes = getScopes();
Devang Patelee890ed2010-01-05 16:59:17 +0000240 const MachineInstr *LastInsn = getFirstInsn();
Devang Patel344130e2010-01-04 20:44:00 +0000241 unsigned LIndex = 0;
242 if (Scopes.empty()) {
Chris Lattnered7a77b2010-03-31 05:36:29 +0000243 assert(getLastInsn() && "Inner most scope does not have last insn!");
Devang Patel344130e2010-01-04 20:44:00 +0000244 return;
245 }
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000246 for (SmallVector<DbgScope *, 4>::const_iterator SI = Scopes.begin(),
Devang Patel344130e2010-01-04 20:44:00 +0000247 SE = Scopes.end(); SI != SE; ++SI) {
248 DbgScope *DS = *SI;
249 DS->fixInstructionMarkers(MIIndexMap);
250 const MachineInstr *DSLastInsn = DS->getLastInsn();
251 unsigned DSI = MIIndexMap[DSLastInsn];
252 if (DSI > LIndex) {
253 LastInsn = DSLastInsn;
254 LIndex = DSI;
255 }
256 }
Devang Patel22fb4b22010-02-17 02:20:34 +0000257
258 unsigned CurrentLastInsnIndex = 0;
259 if (const MachineInstr *CL = getLastInsn())
260 CurrentLastInsnIndex = MIIndexMap[CL];
261 unsigned FIndex = MIIndexMap[getFirstInsn()];
262
263 // Set LastInsn as the last instruction for this scope only if
264 // it follows
265 // 1) this scope's first instruction and
266 // 2) current last instruction for this scope, if any.
267 if (LIndex >= CurrentLastInsnIndex && LIndex >= FIndex)
268 setLastInsn(LastInsn);
Devang Patelaf9e8472009-10-01 20:31:14 +0000269 }
270
Bill Wendling0310d762009-05-15 09:23:25 +0000271#ifndef NDEBUG
272 void dump() const;
273#endif
274};
Chris Lattnerea761862010-04-05 04:09:20 +0000275
276} // end llvm namespace
Bill Wendling0310d762009-05-15 09:23:25 +0000277
278#ifndef NDEBUG
279void DbgScope::dump() const {
David Greenef83adbc2009-12-24 00:31:35 +0000280 raw_ostream &err = dbgs();
Chris Lattnerc281de12009-08-23 00:51:00 +0000281 err.indent(IndentLevel);
Devang Patel53bb5c92009-11-10 23:06:00 +0000282 MDNode *N = Desc.getNode();
283 N->dump();
Chris Lattnerb7db7332010-03-09 01:58:53 +0000284 err << " [" << StartLabel << ", " << EndLabel << "]\n";
Devang Patel53bb5c92009-11-10 23:06:00 +0000285 if (AbstractScope)
286 err << "Abstract Scope\n";
Bill Wendling0310d762009-05-15 09:23:25 +0000287
288 IndentLevel += 2;
Devang Patel53bb5c92009-11-10 23:06:00 +0000289 if (!Scopes.empty())
290 err << "Children ...\n";
Bill Wendling0310d762009-05-15 09:23:25 +0000291 for (unsigned i = 0, e = Scopes.size(); i != e; ++i)
292 if (Scopes[i] != this)
293 Scopes[i]->dump();
294
295 IndentLevel -= 2;
296}
297#endif
298
Bill Wendling0310d762009-05-15 09:23:25 +0000299DbgScope::~DbgScope() {
Bill Wendling0310d762009-05-15 09:23:25 +0000300 for (unsigned j = 0, M = Variables.size(); j < M; ++j)
301 delete Variables[j];
Bill Wendling0310d762009-05-15 09:23:25 +0000302}
303
Chris Lattner49cd6642010-04-05 05:11:15 +0000304DwarfDebug::DwarfDebug(AsmPrinter *A, Module *M)
Chris Lattnerd38fee82010-04-05 00:13:49 +0000305 : Asm(A), MMI(Asm->MMI), ModuleCU(0),
Chris Lattner994cb122010-04-05 03:52:55 +0000306 AbbreviationsSet(InitAbbreviationsSetSize),
Chris Lattnerde4845c2010-04-02 19:42:39 +0000307 CurrentFnDbgScope(0), DebugTimer(0) {
Chris Lattnerbc733f52010-03-13 02:17:42 +0000308 NextStringPoolNumber = 0;
Chris Lattner9c69e285532010-04-04 22:59:04 +0000309
Chris Lattner4ad1efe2010-04-04 23:10:38 +0000310 DwarfFrameSectionSym = DwarfInfoSectionSym = DwarfAbbrevSectionSym = 0;
311 DwarfStrSectionSym = TextSectionSym = 0;
Chris Lattner9c69e285532010-04-04 22:59:04 +0000312
Bill Wendling0310d762009-05-15 09:23:25 +0000313 if (TimePassesIsEnabled)
Chris Lattner0b86a6f2009-12-28 07:41:18 +0000314 DebugTimer = new Timer("Dwarf Debug Writer");
Chris Lattner49cd6642010-04-05 05:11:15 +0000315
316 beginModule(M);
Bill Wendling0310d762009-05-15 09:23:25 +0000317}
318DwarfDebug::~DwarfDebug() {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000319 for (unsigned j = 0, M = DIEBlocks.size(); j < M; ++j)
320 DIEBlocks[j]->~DIEBlock();
Bill Wendling0310d762009-05-15 09:23:25 +0000321
Bill Wendling0310d762009-05-15 09:23:25 +0000322 delete DebugTimer;
323}
324
Chris Lattnerbc733f52010-03-13 02:17:42 +0000325MCSymbol *DwarfDebug::getStringPoolEntry(StringRef Str) {
326 std::pair<MCSymbol*, unsigned> &Entry = StringPool[Str];
327 if (Entry.first) return Entry.first;
328
329 Entry.second = NextStringPoolNumber++;
Chris Lattnerc0215722010-04-04 19:25:43 +0000330 return Entry.first = Asm->GetTempSymbol("string", Entry.second);
Chris Lattnerbc733f52010-03-13 02:17:42 +0000331}
332
333
Devang Patel2c4ceb12009-11-21 02:48:08 +0000334/// assignAbbrevNumber - Define a unique number for the abbreviation.
Bill Wendling0310d762009-05-15 09:23:25 +0000335///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000336void DwarfDebug::assignAbbrevNumber(DIEAbbrev &Abbrev) {
Bill Wendling0310d762009-05-15 09:23:25 +0000337 // Profile the node so that we can make it unique.
338 FoldingSetNodeID ID;
339 Abbrev.Profile(ID);
340
341 // Check the set for priors.
342 DIEAbbrev *InSet = AbbreviationsSet.GetOrInsertNode(&Abbrev);
343
344 // If it's newly added.
345 if (InSet == &Abbrev) {
346 // Add to abbreviation list.
347 Abbreviations.push_back(&Abbrev);
348
349 // Assign the vector position + 1 as its number.
350 Abbrev.setNumber(Abbreviations.size());
351 } else {
352 // Assign existing abbreviation number.
353 Abbrev.setNumber(InSet->getNumber());
354 }
355}
356
Devang Patel2c4ceb12009-11-21 02:48:08 +0000357/// createDIEEntry - Creates a new DIEEntry to be a proxy for a debug
Bill Wendling995f80a2009-05-20 23:24:48 +0000358/// information entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000359DIEEntry *DwarfDebug::createDIEEntry(DIE *Entry) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000360 DIEEntry *Value = new (DIEValueAllocator) DIEEntry(Entry);
Bill Wendling0310d762009-05-15 09:23:25 +0000361 return Value;
362}
363
Devang Patel2c4ceb12009-11-21 02:48:08 +0000364/// addUInt - Add an unsigned integer attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000365///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000366void DwarfDebug::addUInt(DIE *Die, unsigned Attribute,
Bill Wendling0310d762009-05-15 09:23:25 +0000367 unsigned Form, uint64_t Integer) {
368 if (!Form) Form = DIEInteger::BestForm(false, Integer);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000369 DIEValue *Value = new (DIEValueAllocator) DIEInteger(Integer);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000370 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000371}
372
Devang Patel2c4ceb12009-11-21 02:48:08 +0000373/// addSInt - Add an signed integer attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000374///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000375void DwarfDebug::addSInt(DIE *Die, unsigned Attribute,
Bill Wendling0310d762009-05-15 09:23:25 +0000376 unsigned Form, int64_t Integer) {
377 if (!Form) Form = DIEInteger::BestForm(true, Integer);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000378 DIEValue *Value = new (DIEValueAllocator) DIEInteger(Integer);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000379 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000380}
381
Devang Patel69f57b12009-12-02 15:25:16 +0000382/// addString - Add a string attribute data and value. DIEString only
383/// keeps string reference.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000384void DwarfDebug::addString(DIE *Die, unsigned Attribute, unsigned Form,
Chris Lattner4cf202b2010-01-23 03:11:46 +0000385 StringRef String) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000386 DIEValue *Value = new (DIEValueAllocator) DIEString(String);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000387 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000388}
389
Devang Patel2c4ceb12009-11-21 02:48:08 +0000390/// addLabel - Add a Dwarf label attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000391///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000392void DwarfDebug::addLabel(DIE *Die, unsigned Attribute, unsigned Form,
Chris Lattnerb98b1bf2010-03-08 22:23:36 +0000393 const MCSymbol *Label) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000394 DIEValue *Value = new (DIEValueAllocator) DIELabel(Label);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000395 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000396}
397
Devang Patel2c4ceb12009-11-21 02:48:08 +0000398/// addDelta - Add a label delta attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000399///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000400void DwarfDebug::addDelta(DIE *Die, unsigned Attribute, unsigned Form,
Chris Lattnerb98b1bf2010-03-08 22:23:36 +0000401 const MCSymbol *Hi, const MCSymbol *Lo) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000402 DIEValue *Value = new (DIEValueAllocator) DIEDelta(Hi, Lo);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000403 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000404}
405
Chris Lattner74e41f92010-04-05 05:24:55 +0000406/// addDIEEntry - Add a DIE attribute data and value.
407///
408void DwarfDebug::addDIEEntry(DIE *Die, unsigned Attribute, unsigned Form,
409 DIE *Entry) {
410 Die->addValue(Attribute, Form, createDIEEntry(Entry));
411}
412
413
Devang Patel2c4ceb12009-11-21 02:48:08 +0000414/// addBlock - Add block data.
Bill Wendling0310d762009-05-15 09:23:25 +0000415///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000416void DwarfDebug::addBlock(DIE *Die, unsigned Attribute, unsigned Form,
Bill Wendling0310d762009-05-15 09:23:25 +0000417 DIEBlock *Block) {
Chris Lattnera37d5382010-04-05 00:18:22 +0000418 Block->ComputeSize(Asm);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000419 DIEBlocks.push_back(Block); // Memoize so we can call the destructor later on.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000420 Die->addValue(Attribute, Block->BestForm(), Block);
Bill Wendling0310d762009-05-15 09:23:25 +0000421}
422
Devang Patel2c4ceb12009-11-21 02:48:08 +0000423/// addSourceLine - Add location information to specified debug information
Bill Wendling0310d762009-05-15 09:23:25 +0000424/// entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000425void DwarfDebug::addSourceLine(DIE *Die, const DIVariable *V) {
Bill Wendling0310d762009-05-15 09:23:25 +0000426 // If there is no compile unit specified, don't add a line #.
Devang Patel3c91b052010-03-08 20:52:55 +0000427 if (!V->getCompileUnit().Verify())
Bill Wendling0310d762009-05-15 09:23:25 +0000428 return;
429
430 unsigned Line = V->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000431 unsigned FileID = GetOrCreateSourceID(V->getContext().getDirectory(),
432 V->getContext().getFilename());
Bill Wendling0310d762009-05-15 09:23:25 +0000433 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000434 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
435 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Bill Wendling0310d762009-05-15 09:23:25 +0000436}
437
Devang Patel2c4ceb12009-11-21 02:48:08 +0000438/// addSourceLine - Add location information to specified debug information
Bill Wendling0310d762009-05-15 09:23:25 +0000439/// entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000440void DwarfDebug::addSourceLine(DIE *Die, const DIGlobal *G) {
Bill Wendling0310d762009-05-15 09:23:25 +0000441 // If there is no compile unit specified, don't add a line #.
Devang Patel3c91b052010-03-08 20:52:55 +0000442 if (!G->getCompileUnit().Verify())
Bill Wendling0310d762009-05-15 09:23:25 +0000443 return;
444
445 unsigned Line = G->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000446 unsigned FileID = GetOrCreateSourceID(G->getContext().getDirectory(),
447 G->getContext().getFilename());
Bill Wendling0310d762009-05-15 09:23:25 +0000448 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000449 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
450 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Bill Wendling0310d762009-05-15 09:23:25 +0000451}
Devang Patel82dfc0c2009-08-31 22:47:13 +0000452
Devang Patel2c4ceb12009-11-21 02:48:08 +0000453/// addSourceLine - Add location information to specified debug information
Devang Patel82dfc0c2009-08-31 22:47:13 +0000454/// entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000455void DwarfDebug::addSourceLine(DIE *Die, const DISubprogram *SP) {
Devang Patel82dfc0c2009-08-31 22:47:13 +0000456 // If there is no compile unit specified, don't add a line #.
Devang Patel3c91b052010-03-08 20:52:55 +0000457 if (!SP->getCompileUnit().Verify())
Devang Patel82dfc0c2009-08-31 22:47:13 +0000458 return;
Caroline Ticec6f9d622009-09-11 18:25:54 +0000459 // If the line number is 0, don't add it.
460 if (SP->getLineNumber() == 0)
461 return;
462
Devang Patel82dfc0c2009-08-31 22:47:13 +0000463 unsigned Line = SP->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000464 if (!SP->getContext().Verify())
465 return;
Devang Patel9bb59a22010-03-24 21:30:35 +0000466 unsigned FileID = GetOrCreateSourceID(SP->getDirectory(),
467 SP->getFilename());
Devang Patel82dfc0c2009-08-31 22:47:13 +0000468 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000469 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
470 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Devang Patel82dfc0c2009-08-31 22:47:13 +0000471}
472
Devang Patel2c4ceb12009-11-21 02:48:08 +0000473/// addSourceLine - Add location information to specified debug information
Devang Patel82dfc0c2009-08-31 22:47:13 +0000474/// entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000475void DwarfDebug::addSourceLine(DIE *Die, const DIType *Ty) {
Bill Wendling0310d762009-05-15 09:23:25 +0000476 // If there is no compile unit specified, don't add a line #.
477 DICompileUnit CU = Ty->getCompileUnit();
Devang Patel3c91b052010-03-08 20:52:55 +0000478 if (!CU.Verify())
Bill Wendling0310d762009-05-15 09:23:25 +0000479 return;
480
481 unsigned Line = Ty->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000482 if (!Ty->getContext().Verify())
483 return;
484 unsigned FileID = GetOrCreateSourceID(Ty->getContext().getDirectory(),
485 Ty->getContext().getFilename());
Bill Wendling0310d762009-05-15 09:23:25 +0000486 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000487 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
488 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Bill Wendling0310d762009-05-15 09:23:25 +0000489}
490
Devang Patel6404e4e2009-12-15 19:16:48 +0000491/// addSourceLine - Add location information to specified debug information
492/// entry.
493void DwarfDebug::addSourceLine(DIE *Die, const DINameSpace *NS) {
494 // If there is no compile unit specified, don't add a line #.
Devang Patel3c91b052010-03-08 20:52:55 +0000495 if (!NS->getCompileUnit().Verify())
Devang Patel6404e4e2009-12-15 19:16:48 +0000496 return;
497
498 unsigned Line = NS->getLineNumber();
499 StringRef FN = NS->getFilename();
500 StringRef Dir = NS->getDirectory();
501
502 unsigned FileID = GetOrCreateSourceID(Dir, FN);
503 assert(FileID && "Invalid file id");
504 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
505 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
506}
507
Caroline Ticedc8f6042009-08-31 21:19:37 +0000508/* Byref variables, in Blocks, are declared by the programmer as
509 "SomeType VarName;", but the compiler creates a
510 __Block_byref_x_VarName struct, and gives the variable VarName
511 either the struct, or a pointer to the struct, as its type. This
512 is necessary for various behind-the-scenes things the compiler
513 needs to do with by-reference variables in blocks.
514
515 However, as far as the original *programmer* is concerned, the
516 variable should still have type 'SomeType', as originally declared.
517
518 The following function dives into the __Block_byref_x_VarName
519 struct to find the original type of the variable. This will be
520 passed back to the code generating the type for the Debug
521 Information Entry for the variable 'VarName'. 'VarName' will then
522 have the original type 'SomeType' in its debug information.
523
524 The original type 'SomeType' will be the type of the field named
525 'VarName' inside the __Block_byref_x_VarName struct.
526
527 NOTE: In order for this to not completely fail on the debugger
528 side, the Debug Information Entry for the variable VarName needs to
529 have a DW_AT_location that tells the debugger how to unwind through
530 the pointers and __Block_byref_x_VarName struct to find the actual
Devang Patel2c4ceb12009-11-21 02:48:08 +0000531 value of the variable. The function addBlockByrefType does this. */
Caroline Ticedc8f6042009-08-31 21:19:37 +0000532
533/// Find the type the programmer originally declared the variable to be
534/// and return that type.
535///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000536DIType DwarfDebug::getBlockByrefType(DIType Ty, std::string Name) {
Caroline Ticedc8f6042009-08-31 21:19:37 +0000537
538 DIType subType = Ty;
539 unsigned tag = Ty.getTag();
540
541 if (tag == dwarf::DW_TAG_pointer_type) {
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000542 DIDerivedType DTy = DIDerivedType(Ty.getNode());
Caroline Ticedc8f6042009-08-31 21:19:37 +0000543 subType = DTy.getTypeDerivedFrom();
544 }
545
546 DICompositeType blockStruct = DICompositeType(subType.getNode());
Caroline Ticedc8f6042009-08-31 21:19:37 +0000547 DIArray Elements = blockStruct.getTypeArray();
548
Caroline Ticedc8f6042009-08-31 21:19:37 +0000549 for (unsigned i = 0, N = Elements.getNumElements(); i < N; ++i) {
550 DIDescriptor Element = Elements.getElement(i);
551 DIDerivedType DT = DIDerivedType(Element.getNode());
Devang Patel65dbc902009-11-25 17:36:49 +0000552 if (Name == DT.getName())
Caroline Ticedc8f6042009-08-31 21:19:37 +0000553 return (DT.getTypeDerivedFrom());
554 }
555
556 return Ty;
557}
558
Devang Patel2c4ceb12009-11-21 02:48:08 +0000559/// addComplexAddress - Start with the address based on the location provided,
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000560/// and generate the DWARF information necessary to find the actual variable
561/// given the extra address information encoded in the DIVariable, starting from
562/// the starting location. Add the DWARF information to the die.
563///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000564void DwarfDebug::addComplexAddress(DbgVariable *&DV, DIE *Die,
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000565 unsigned Attribute,
566 const MachineLocation &Location) {
567 const DIVariable &VD = DV->getVariable();
568 DIType Ty = VD.getType();
569
570 // Decode the original location, and use that as the start of the byref
571 // variable's location.
Chris Lattnerd38fee82010-04-05 00:13:49 +0000572 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000573 unsigned Reg = RI->getDwarfRegNum(Location.getReg(), false);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000574 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000575
576 if (Location.isReg()) {
577 if (Reg < 32) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000578 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_reg0 + Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000579 } else {
580 Reg = Reg - dwarf::DW_OP_reg0;
Devang Patel2c4ceb12009-11-21 02:48:08 +0000581 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
582 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000583 }
584 } else {
585 if (Reg < 32)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000586 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000587 else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000588 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_bregx);
589 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000590 }
591
Devang Patel2c4ceb12009-11-21 02:48:08 +0000592 addUInt(Block, 0, dwarf::DW_FORM_sdata, Location.getOffset());
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000593 }
594
595 for (unsigned i = 0, N = VD.getNumAddrElements(); i < N; ++i) {
596 uint64_t Element = VD.getAddrElement(i);
597
598 if (Element == DIFactory::OpPlus) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000599 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
600 addUInt(Block, 0, dwarf::DW_FORM_udata, VD.getAddrElement(++i));
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000601 } else if (Element == DIFactory::OpDeref) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000602 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000603 } else llvm_unreachable("unknown DIFactory Opcode");
604 }
605
606 // Now attach the location information to the DIE.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000607 addBlock(Die, Attribute, 0, Block);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000608}
609
Caroline Ticedc8f6042009-08-31 21:19:37 +0000610/* Byref variables, in Blocks, are declared by the programmer as "SomeType
611 VarName;", but the compiler creates a __Block_byref_x_VarName struct, and
612 gives the variable VarName either the struct, or a pointer to the struct, as
613 its type. This is necessary for various behind-the-scenes things the
614 compiler needs to do with by-reference variables in Blocks.
615
616 However, as far as the original *programmer* is concerned, the variable
617 should still have type 'SomeType', as originally declared.
618
Devang Patel2c4ceb12009-11-21 02:48:08 +0000619 The function getBlockByrefType dives into the __Block_byref_x_VarName
Caroline Ticedc8f6042009-08-31 21:19:37 +0000620 struct to find the original type of the variable, which is then assigned to
621 the variable's Debug Information Entry as its real type. So far, so good.
622 However now the debugger will expect the variable VarName to have the type
623 SomeType. So we need the location attribute for the variable to be an
Daniel Dunbarf612ff62009-09-19 20:40:05 +0000624 expression that explains to the debugger how to navigate through the
Caroline Ticedc8f6042009-08-31 21:19:37 +0000625 pointers and struct to find the actual variable of type SomeType.
626
627 The following function does just that. We start by getting
628 the "normal" location for the variable. This will be the location
629 of either the struct __Block_byref_x_VarName or the pointer to the
630 struct __Block_byref_x_VarName.
631
632 The struct will look something like:
633
634 struct __Block_byref_x_VarName {
635 ... <various fields>
636 struct __Block_byref_x_VarName *forwarding;
637 ... <various other fields>
638 SomeType VarName;
639 ... <maybe more fields>
640 };
641
642 If we are given the struct directly (as our starting point) we
643 need to tell the debugger to:
644
645 1). Add the offset of the forwarding field.
646
Dan Gohmanf451cb82010-02-10 16:03:48 +0000647 2). Follow that pointer to get the real __Block_byref_x_VarName
Caroline Ticedc8f6042009-08-31 21:19:37 +0000648 struct to use (the real one may have been copied onto the heap).
649
650 3). Add the offset for the field VarName, to find the actual variable.
651
652 If we started with a pointer to the struct, then we need to
653 dereference that pointer first, before the other steps.
654 Translating this into DWARF ops, we will need to append the following
655 to the current location description for the variable:
656
657 DW_OP_deref -- optional, if we start with a pointer
658 DW_OP_plus_uconst <forward_fld_offset>
659 DW_OP_deref
660 DW_OP_plus_uconst <varName_fld_offset>
661
662 That is what this function does. */
663
Devang Patel2c4ceb12009-11-21 02:48:08 +0000664/// addBlockByrefAddress - Start with the address based on the location
Caroline Ticedc8f6042009-08-31 21:19:37 +0000665/// provided, and generate the DWARF information necessary to find the
666/// actual Block variable (navigating the Block struct) based on the
667/// starting location. Add the DWARF information to the die. For
668/// more information, read large comment just above here.
669///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000670void DwarfDebug::addBlockByrefAddress(DbgVariable *&DV, DIE *Die,
Daniel Dunbar00564992009-09-19 20:40:14 +0000671 unsigned Attribute,
672 const MachineLocation &Location) {
Caroline Ticedc8f6042009-08-31 21:19:37 +0000673 const DIVariable &VD = DV->getVariable();
674 DIType Ty = VD.getType();
675 DIType TmpTy = Ty;
676 unsigned Tag = Ty.getTag();
677 bool isPointer = false;
678
Devang Patel65dbc902009-11-25 17:36:49 +0000679 StringRef varName = VD.getName();
Caroline Ticedc8f6042009-08-31 21:19:37 +0000680
681 if (Tag == dwarf::DW_TAG_pointer_type) {
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000682 DIDerivedType DTy = DIDerivedType(Ty.getNode());
Caroline Ticedc8f6042009-08-31 21:19:37 +0000683 TmpTy = DTy.getTypeDerivedFrom();
684 isPointer = true;
685 }
686
687 DICompositeType blockStruct = DICompositeType(TmpTy.getNode());
688
Daniel Dunbar00564992009-09-19 20:40:14 +0000689 // Find the __forwarding field and the variable field in the __Block_byref
690 // struct.
Daniel Dunbar00564992009-09-19 20:40:14 +0000691 DIArray Fields = blockStruct.getTypeArray();
692 DIDescriptor varField = DIDescriptor();
693 DIDescriptor forwardingField = DIDescriptor();
Caroline Ticedc8f6042009-08-31 21:19:37 +0000694
Daniel Dunbar00564992009-09-19 20:40:14 +0000695 for (unsigned i = 0, N = Fields.getNumElements(); i < N; ++i) {
696 DIDescriptor Element = Fields.getElement(i);
697 DIDerivedType DT = DIDerivedType(Element.getNode());
Devang Patel65dbc902009-11-25 17:36:49 +0000698 StringRef fieldName = DT.getName();
699 if (fieldName == "__forwarding")
Daniel Dunbar00564992009-09-19 20:40:14 +0000700 forwardingField = Element;
Devang Patel65dbc902009-11-25 17:36:49 +0000701 else if (fieldName == varName)
Daniel Dunbar00564992009-09-19 20:40:14 +0000702 varField = Element;
703 }
Daniel Dunbarf612ff62009-09-19 20:40:05 +0000704
Daniel Dunbar00564992009-09-19 20:40:14 +0000705 // Get the offsets for the forwarding field and the variable field.
Chris Lattner1d65ba72010-03-31 06:06:37 +0000706 unsigned forwardingFieldOffset =
Daniel Dunbar00564992009-09-19 20:40:14 +0000707 DIDerivedType(forwardingField.getNode()).getOffsetInBits() >> 3;
Chris Lattner1d65ba72010-03-31 06:06:37 +0000708 unsigned varFieldOffset =
Daniel Dunbar00564992009-09-19 20:40:14 +0000709 DIDerivedType(varField.getNode()).getOffsetInBits() >> 3;
Caroline Ticedc8f6042009-08-31 21:19:37 +0000710
Mike Stump7e3720d2009-09-24 23:21:26 +0000711 // Decode the original location, and use that as the start of the byref
712 // variable's location.
Chris Lattnerd38fee82010-04-05 00:13:49 +0000713 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Daniel Dunbar00564992009-09-19 20:40:14 +0000714 unsigned Reg = RI->getDwarfRegNum(Location.getReg(), false);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000715 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Caroline Ticedc8f6042009-08-31 21:19:37 +0000716
Daniel Dunbar00564992009-09-19 20:40:14 +0000717 if (Location.isReg()) {
718 if (Reg < 32)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000719 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_reg0 + Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000720 else {
721 Reg = Reg - dwarf::DW_OP_reg0;
Devang Patel2c4ceb12009-11-21 02:48:08 +0000722 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
723 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000724 }
725 } else {
726 if (Reg < 32)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000727 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000728 else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000729 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_bregx);
730 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000731 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000732
Devang Patel2c4ceb12009-11-21 02:48:08 +0000733 addUInt(Block, 0, dwarf::DW_FORM_sdata, Location.getOffset());
Daniel Dunbar00564992009-09-19 20:40:14 +0000734 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000735
Mike Stump7e3720d2009-09-24 23:21:26 +0000736 // If we started with a pointer to the __Block_byref... struct, then
Daniel Dunbar00564992009-09-19 20:40:14 +0000737 // the first thing we need to do is dereference the pointer (DW_OP_deref).
Daniel Dunbar00564992009-09-19 20:40:14 +0000738 if (isPointer)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000739 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000740
Daniel Dunbar00564992009-09-19 20:40:14 +0000741 // Next add the offset for the '__forwarding' field:
742 // DW_OP_plus_uconst ForwardingFieldOffset. Note there's no point in
743 // adding the offset if it's 0.
Daniel Dunbar00564992009-09-19 20:40:14 +0000744 if (forwardingFieldOffset > 0) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000745 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
746 addUInt(Block, 0, dwarf::DW_FORM_udata, forwardingFieldOffset);
Daniel Dunbar00564992009-09-19 20:40:14 +0000747 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000748
Daniel Dunbar00564992009-09-19 20:40:14 +0000749 // Now dereference the __forwarding field to get to the real __Block_byref
750 // struct: DW_OP_deref.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000751 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000752
Daniel Dunbar00564992009-09-19 20:40:14 +0000753 // Now that we've got the real __Block_byref... struct, add the offset
754 // for the variable's field to get to the location of the actual variable:
755 // DW_OP_plus_uconst varFieldOffset. Again, don't add if it's 0.
Daniel Dunbar00564992009-09-19 20:40:14 +0000756 if (varFieldOffset > 0) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000757 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
758 addUInt(Block, 0, dwarf::DW_FORM_udata, varFieldOffset);
Daniel Dunbar00564992009-09-19 20:40:14 +0000759 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000760
Daniel Dunbar00564992009-09-19 20:40:14 +0000761 // Now attach the location information to the DIE.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000762 addBlock(Die, Attribute, 0, Block);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000763}
764
Devang Patel2c4ceb12009-11-21 02:48:08 +0000765/// addAddress - Add an address attribute to a die based on the location
Bill Wendling0310d762009-05-15 09:23:25 +0000766/// provided.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000767void DwarfDebug::addAddress(DIE *Die, unsigned Attribute,
Bill Wendling0310d762009-05-15 09:23:25 +0000768 const MachineLocation &Location) {
Chris Lattnerd38fee82010-04-05 00:13:49 +0000769 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Bill Wendling0310d762009-05-15 09:23:25 +0000770 unsigned Reg = RI->getDwarfRegNum(Location.getReg(), false);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000771 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Bill Wendling0310d762009-05-15 09:23:25 +0000772
773 if (Location.isReg()) {
774 if (Reg < 32) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000775 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_reg0 + Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000776 } else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000777 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_regx);
778 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000779 }
780 } else {
781 if (Reg < 32) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000782 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000783 } else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000784 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_bregx);
785 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000786 }
787
Devang Patel2c4ceb12009-11-21 02:48:08 +0000788 addUInt(Block, 0, dwarf::DW_FORM_sdata, Location.getOffset());
Bill Wendling0310d762009-05-15 09:23:25 +0000789 }
790
Devang Patel2c4ceb12009-11-21 02:48:08 +0000791 addBlock(Die, Attribute, 0, Block);
Bill Wendling0310d762009-05-15 09:23:25 +0000792}
793
Devang Patelc366f832009-12-10 19:14:49 +0000794/// addToContextOwner - Add Die into the list of its context owner's children.
795void DwarfDebug::addToContextOwner(DIE *Die, DIDescriptor Context) {
Devang Patel3c91b052010-03-08 20:52:55 +0000796 if (Context.isType()) {
Devang Patelc366f832009-12-10 19:14:49 +0000797 DIE *ContextDIE = getOrCreateTypeDIE(DIType(Context.getNode()));
798 ContextDIE->addChild(Die);
Devang Patel6404e4e2009-12-15 19:16:48 +0000799 } else if (Context.isNameSpace()) {
800 DIE *ContextDIE = getOrCreateNameSpace(DINameSpace(Context.getNode()));
801 ContextDIE->addChild(Die);
Devang Patelc366f832009-12-10 19:14:49 +0000802 } else if (DIE *ContextDIE = ModuleCU->getDIE(Context.getNode()))
803 ContextDIE->addChild(Die);
804 else
805 ModuleCU->addDie(Die);
806}
807
Devang Patel16ced732009-12-10 18:05:33 +0000808/// getOrCreateTypeDIE - Find existing DIE or create new DIE for the
809/// given DIType.
810DIE *DwarfDebug::getOrCreateTypeDIE(DIType Ty) {
811 DIE *TyDIE = ModuleCU->getDIE(Ty.getNode());
812 if (TyDIE)
813 return TyDIE;
814
815 // Create new type.
816 TyDIE = new DIE(dwarf::DW_TAG_base_type);
817 ModuleCU->insertDIE(Ty.getNode(), TyDIE);
818 if (Ty.isBasicType())
819 constructTypeDIE(*TyDIE, DIBasicType(Ty.getNode()));
820 else if (Ty.isCompositeType())
821 constructTypeDIE(*TyDIE, DICompositeType(Ty.getNode()));
822 else {
823 assert(Ty.isDerivedType() && "Unknown kind of DIType");
824 constructTypeDIE(*TyDIE, DIDerivedType(Ty.getNode()));
825 }
826
Devang Patelc366f832009-12-10 19:14:49 +0000827 addToContextOwner(TyDIE, Ty.getContext());
Devang Patel16ced732009-12-10 18:05:33 +0000828 return TyDIE;
829}
830
Devang Patel2c4ceb12009-11-21 02:48:08 +0000831/// addType - Add a new type attribute to the specified entity.
Devang Patel8a241142009-12-09 18:24:21 +0000832void DwarfDebug::addType(DIE *Entity, DIType Ty) {
Devang Patel3c91b052010-03-08 20:52:55 +0000833 if (!Ty.isValid())
Bill Wendling0310d762009-05-15 09:23:25 +0000834 return;
835
836 // Check for pre-existence.
Devang Patel8a241142009-12-09 18:24:21 +0000837 DIEEntry *Entry = ModuleCU->getDIEEntry(Ty.getNode());
Bill Wendling0310d762009-05-15 09:23:25 +0000838 // If it exists then use the existing value.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000839 if (Entry) {
840 Entity->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, Entry);
Bill Wendling0310d762009-05-15 09:23:25 +0000841 return;
842 }
843
Bill Wendling0310d762009-05-15 09:23:25 +0000844 // Construct type.
Devang Patel16ced732009-12-10 18:05:33 +0000845 DIE *Buffer = getOrCreateTypeDIE(Ty);
Bill Wendling0310d762009-05-15 09:23:25 +0000846
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000847 // Set up proxy.
848 Entry = createDIEEntry(Buffer);
849 ModuleCU->insertDIEEntry(Ty.getNode(), Entry);
850
Devang Patel2c4ceb12009-11-21 02:48:08 +0000851 Entity->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, Entry);
Bill Wendling0310d762009-05-15 09:23:25 +0000852}
853
Devang Patel2c4ceb12009-11-21 02:48:08 +0000854/// constructTypeDIE - Construct basic type die from DIBasicType.
Devang Patel8a241142009-12-09 18:24:21 +0000855void DwarfDebug::constructTypeDIE(DIE &Buffer, DIBasicType BTy) {
Bill Wendling0310d762009-05-15 09:23:25 +0000856 // Get core information.
Devang Patel65dbc902009-11-25 17:36:49 +0000857 StringRef Name = BTy.getName();
Bill Wendling0310d762009-05-15 09:23:25 +0000858 Buffer.setTag(dwarf::DW_TAG_base_type);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000859 addUInt(&Buffer, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
Bill Wendling0310d762009-05-15 09:23:25 +0000860 BTy.getEncoding());
861
862 // Add name if not anonymous or intermediate type.
Devang Patel65dbc902009-11-25 17:36:49 +0000863 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000864 addString(&Buffer, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Bill Wendling0310d762009-05-15 09:23:25 +0000865 uint64_t Size = BTy.getSizeInBits() >> 3;
Devang Patel2c4ceb12009-11-21 02:48:08 +0000866 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, Size);
Bill Wendling0310d762009-05-15 09:23:25 +0000867}
868
Devang Patel2c4ceb12009-11-21 02:48:08 +0000869/// constructTypeDIE - Construct derived type die from DIDerivedType.
Devang Patel8a241142009-12-09 18:24:21 +0000870void DwarfDebug::constructTypeDIE(DIE &Buffer, DIDerivedType DTy) {
Bill Wendling0310d762009-05-15 09:23:25 +0000871 // Get core information.
Devang Patel65dbc902009-11-25 17:36:49 +0000872 StringRef Name = DTy.getName();
Bill Wendling0310d762009-05-15 09:23:25 +0000873 uint64_t Size = DTy.getSizeInBits() >> 3;
874 unsigned Tag = DTy.getTag();
875
876 // FIXME - Workaround for templates.
877 if (Tag == dwarf::DW_TAG_inheritance) Tag = dwarf::DW_TAG_reference_type;
878
879 Buffer.setTag(Tag);
880
881 // Map to main type, void will not have a type.
882 DIType FromTy = DTy.getTypeDerivedFrom();
Devang Patel8a241142009-12-09 18:24:21 +0000883 addType(&Buffer, FromTy);
Bill Wendling0310d762009-05-15 09:23:25 +0000884
885 // Add name if not anonymous or intermediate type.
Devang Pateldeea5642009-11-30 23:56:56 +0000886 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000887 addString(&Buffer, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Bill Wendling0310d762009-05-15 09:23:25 +0000888
889 // Add size if non-zero (derived types might be zero-sized.)
890 if (Size)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000891 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, Size);
Bill Wendling0310d762009-05-15 09:23:25 +0000892
893 // Add source line info if available and TyDesc is not a forward declaration.
Devang Patel05f6fa82009-11-23 18:43:37 +0000894 if (!DTy.isForwardDecl())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000895 addSourceLine(&Buffer, &DTy);
Bill Wendling0310d762009-05-15 09:23:25 +0000896}
897
Devang Patel2c4ceb12009-11-21 02:48:08 +0000898/// constructTypeDIE - Construct type DIE from DICompositeType.
Devang Patel8a241142009-12-09 18:24:21 +0000899void DwarfDebug::constructTypeDIE(DIE &Buffer, DICompositeType CTy) {
Bill Wendling0310d762009-05-15 09:23:25 +0000900 // Get core information.
Devang Patel65dbc902009-11-25 17:36:49 +0000901 StringRef Name = CTy.getName();
Bill Wendling0310d762009-05-15 09:23:25 +0000902
903 uint64_t Size = CTy.getSizeInBits() >> 3;
904 unsigned Tag = CTy.getTag();
905 Buffer.setTag(Tag);
906
907 switch (Tag) {
908 case dwarf::DW_TAG_vector_type:
909 case dwarf::DW_TAG_array_type:
Devang Patel8a241142009-12-09 18:24:21 +0000910 constructArrayTypeDIE(Buffer, &CTy);
Bill Wendling0310d762009-05-15 09:23:25 +0000911 break;
912 case dwarf::DW_TAG_enumeration_type: {
913 DIArray Elements = CTy.getTypeArray();
914
915 // Add enumerators to enumeration type.
916 for (unsigned i = 0, N = Elements.getNumElements(); i < N; ++i) {
917 DIE *ElemDie = NULL;
Devang Patel3c91b052010-03-08 20:52:55 +0000918 DIDescriptor Enum(Elements.getElement(i).getNode());
919 if (Enum.isEnumerator()) {
920 ElemDie = constructEnumTypeDIE(DIEnumerator(Enum.getNode()));
Devang Patel2c4ceb12009-11-21 02:48:08 +0000921 Buffer.addChild(ElemDie);
Devang Patelc5254722009-10-09 17:51:49 +0000922 }
Bill Wendling0310d762009-05-15 09:23:25 +0000923 }
924 }
925 break;
926 case dwarf::DW_TAG_subroutine_type: {
927 // Add return type.
928 DIArray Elements = CTy.getTypeArray();
929 DIDescriptor RTy = Elements.getElement(0);
Devang Patel8a241142009-12-09 18:24:21 +0000930 addType(&Buffer, DIType(RTy.getNode()));
Bill Wendling0310d762009-05-15 09:23:25 +0000931
932 // Add prototype flag.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000933 addUInt(&Buffer, dwarf::DW_AT_prototyped, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +0000934
935 // Add arguments.
936 for (unsigned i = 1, N = Elements.getNumElements(); i < N; ++i) {
937 DIE *Arg = new DIE(dwarf::DW_TAG_formal_parameter);
938 DIDescriptor Ty = Elements.getElement(i);
Devang Patel8a241142009-12-09 18:24:21 +0000939 addType(Arg, DIType(Ty.getNode()));
Devang Patel2c4ceb12009-11-21 02:48:08 +0000940 Buffer.addChild(Arg);
Bill Wendling0310d762009-05-15 09:23:25 +0000941 }
942 }
943 break;
944 case dwarf::DW_TAG_structure_type:
945 case dwarf::DW_TAG_union_type:
946 case dwarf::DW_TAG_class_type: {
947 // Add elements to structure type.
948 DIArray Elements = CTy.getTypeArray();
949
950 // A forward struct declared type may not have elements available.
Devang Patel3c91b052010-03-08 20:52:55 +0000951 unsigned N = Elements.getNumElements();
952 if (N == 0)
Bill Wendling0310d762009-05-15 09:23:25 +0000953 break;
954
955 // Add elements to structure type.
Devang Patel3c91b052010-03-08 20:52:55 +0000956 for (unsigned i = 0; i < N; ++i) {
Bill Wendling0310d762009-05-15 09:23:25 +0000957 DIDescriptor Element = Elements.getElement(i);
958 DIE *ElemDie = NULL;
Devang Patel3c91b052010-03-08 20:52:55 +0000959 if (Element.isSubprogram())
Devang Patelffe966c2009-12-14 16:18:45 +0000960 ElemDie = createSubprogramDIE(DISubprogram(Element.getNode()));
Devang Patel3c91b052010-03-08 20:52:55 +0000961 else if (Element.isVariable()) {
Devang Patel1ee0cb92010-01-30 01:08:30 +0000962 DIVariable DV(Element.getNode());
963 ElemDie = new DIE(dwarf::DW_TAG_variable);
964 addString(ElemDie, dwarf::DW_AT_name, dwarf::DW_FORM_string,
965 DV.getName());
966 addType(ElemDie, DV.getType());
967 addUInt(ElemDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
968 addUInt(ElemDie, dwarf::DW_AT_external, dwarf::DW_FORM_flag, 1);
969 addSourceLine(ElemDie, &DV);
Devang Patel3c91b052010-03-08 20:52:55 +0000970 } else if (Element.isDerivedType())
Devang Patel8a241142009-12-09 18:24:21 +0000971 ElemDie = createMemberDIE(DIDerivedType(Element.getNode()));
Devang Patel3c91b052010-03-08 20:52:55 +0000972 else
973 continue;
Devang Patel2c4ceb12009-11-21 02:48:08 +0000974 Buffer.addChild(ElemDie);
Bill Wendling0310d762009-05-15 09:23:25 +0000975 }
976
Devang Patela1ba2692009-08-27 23:51:51 +0000977 if (CTy.isAppleBlockExtension())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000978 addUInt(&Buffer, dwarf::DW_AT_APPLE_block, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +0000979
980 unsigned RLang = CTy.getRunTimeLang();
981 if (RLang)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000982 addUInt(&Buffer, dwarf::DW_AT_APPLE_runtime_class,
Bill Wendling0310d762009-05-15 09:23:25 +0000983 dwarf::DW_FORM_data1, RLang);
Devang Patelb5544992010-01-26 21:16:06 +0000984
985 DICompositeType ContainingType = CTy.getContainingType();
Devang Patel3c91b052010-03-08 20:52:55 +0000986 if (DIDescriptor(ContainingType.getNode()).isCompositeType())
Devang Patelb5544992010-01-26 21:16:06 +0000987 addDIEEntry(&Buffer, dwarf::DW_AT_containing_type, dwarf::DW_FORM_ref4,
988 getOrCreateTypeDIE(DIType(ContainingType.getNode())));
Bill Wendling0310d762009-05-15 09:23:25 +0000989 break;
990 }
991 default:
992 break;
993 }
994
995 // Add name if not anonymous or intermediate type.
Devang Patel65dbc902009-11-25 17:36:49 +0000996 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000997 addString(&Buffer, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Bill Wendling0310d762009-05-15 09:23:25 +0000998
Devang Patel8cbb6122010-01-29 18:34:58 +0000999 if (Tag == dwarf::DW_TAG_enumeration_type || Tag == dwarf::DW_TAG_class_type ||
Bill Wendling0310d762009-05-15 09:23:25 +00001000 Tag == dwarf::DW_TAG_structure_type || Tag == dwarf::DW_TAG_union_type) {
1001 // Add size if non-zero (derived types might be zero-sized.)
1002 if (Size)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001003 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, Size);
Bill Wendling0310d762009-05-15 09:23:25 +00001004 else {
1005 // Add zero size if it is not a forward declaration.
1006 if (CTy.isForwardDecl())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001007 addUInt(&Buffer, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001008 else
Devang Patel2c4ceb12009-11-21 02:48:08 +00001009 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, 0);
Bill Wendling0310d762009-05-15 09:23:25 +00001010 }
1011
1012 // Add source line info if available.
1013 if (!CTy.isForwardDecl())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001014 addSourceLine(&Buffer, &CTy);
Bill Wendling0310d762009-05-15 09:23:25 +00001015 }
1016}
1017
Devang Patel2c4ceb12009-11-21 02:48:08 +00001018/// constructSubrangeDIE - Construct subrange DIE from DISubrange.
1019void DwarfDebug::constructSubrangeDIE(DIE &Buffer, DISubrange SR, DIE *IndexTy){
Bill Wendling0310d762009-05-15 09:23:25 +00001020 int64_t L = SR.getLo();
1021 int64_t H = SR.getHi();
1022 DIE *DW_Subrange = new DIE(dwarf::DW_TAG_subrange_type);
1023
Devang Patel2c4ceb12009-11-21 02:48:08 +00001024 addDIEEntry(DW_Subrange, dwarf::DW_AT_type, dwarf::DW_FORM_ref4, IndexTy);
Devang Patel6325a532009-08-14 20:59:16 +00001025 if (L)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001026 addSInt(DW_Subrange, dwarf::DW_AT_lower_bound, 0, L);
Devang Pateld55224c2009-12-04 23:10:24 +00001027 addSInt(DW_Subrange, dwarf::DW_AT_upper_bound, 0, H);
Bill Wendling0310d762009-05-15 09:23:25 +00001028
Devang Patel2c4ceb12009-11-21 02:48:08 +00001029 Buffer.addChild(DW_Subrange);
Bill Wendling0310d762009-05-15 09:23:25 +00001030}
1031
Devang Patel2c4ceb12009-11-21 02:48:08 +00001032/// constructArrayTypeDIE - Construct array type DIE from DICompositeType.
Devang Patel8a241142009-12-09 18:24:21 +00001033void DwarfDebug::constructArrayTypeDIE(DIE &Buffer,
Bill Wendling0310d762009-05-15 09:23:25 +00001034 DICompositeType *CTy) {
1035 Buffer.setTag(dwarf::DW_TAG_array_type);
1036 if (CTy->getTag() == dwarf::DW_TAG_vector_type)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001037 addUInt(&Buffer, dwarf::DW_AT_GNU_vector, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001038
1039 // Emit derived type.
Devang Patel8a241142009-12-09 18:24:21 +00001040 addType(&Buffer, CTy->getTypeDerivedFrom());
Bill Wendling0310d762009-05-15 09:23:25 +00001041 DIArray Elements = CTy->getTypeArray();
1042
Devang Patel6f01d9c2009-11-21 00:31:03 +00001043 // Get an anonymous type for index type.
Devang Patel8a241142009-12-09 18:24:21 +00001044 DIE *IdxTy = ModuleCU->getIndexTyDie();
Devang Patel6f01d9c2009-11-21 00:31:03 +00001045 if (!IdxTy) {
1046 // Construct an anonymous type for index type.
1047 IdxTy = new DIE(dwarf::DW_TAG_base_type);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001048 addUInt(IdxTy, dwarf::DW_AT_byte_size, 0, sizeof(int32_t));
1049 addUInt(IdxTy, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
Devang Patel6f01d9c2009-11-21 00:31:03 +00001050 dwarf::DW_ATE_signed);
Devang Patel8a241142009-12-09 18:24:21 +00001051 ModuleCU->addDie(IdxTy);
1052 ModuleCU->setIndexTyDie(IdxTy);
Devang Patel6f01d9c2009-11-21 00:31:03 +00001053 }
Bill Wendling0310d762009-05-15 09:23:25 +00001054
1055 // Add subranges to array type.
1056 for (unsigned i = 0, N = Elements.getNumElements(); i < N; ++i) {
1057 DIDescriptor Element = Elements.getElement(i);
1058 if (Element.getTag() == dwarf::DW_TAG_subrange_type)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001059 constructSubrangeDIE(Buffer, DISubrange(Element.getNode()), IdxTy);
Bill Wendling0310d762009-05-15 09:23:25 +00001060 }
1061}
1062
Devang Patel2c4ceb12009-11-21 02:48:08 +00001063/// constructEnumTypeDIE - Construct enum type DIE from DIEnumerator.
Devang Patel3c91b052010-03-08 20:52:55 +00001064DIE *DwarfDebug::constructEnumTypeDIE(DIEnumerator ETy) {
Bill Wendling0310d762009-05-15 09:23:25 +00001065 DIE *Enumerator = new DIE(dwarf::DW_TAG_enumerator);
Devang Patel3c91b052010-03-08 20:52:55 +00001066 StringRef Name = ETy.getName();
Devang Patel2c4ceb12009-11-21 02:48:08 +00001067 addString(Enumerator, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Devang Patel3c91b052010-03-08 20:52:55 +00001068 int64_t Value = ETy.getEnumValue();
Devang Patel2c4ceb12009-11-21 02:48:08 +00001069 addSInt(Enumerator, dwarf::DW_AT_const_value, dwarf::DW_FORM_sdata, Value);
Bill Wendling0310d762009-05-15 09:23:25 +00001070 return Enumerator;
1071}
1072
Devang Patel351ca332010-01-05 01:46:14 +00001073/// getRealLinkageName - If special LLVM prefix that is used to inform the asm
1074/// printer to not emit usual symbol prefix before the symbol name is used then
1075/// return linkage name after skipping this special LLVM prefix.
1076static StringRef getRealLinkageName(StringRef LinkageName) {
1077 char One = '\1';
1078 if (LinkageName.startswith(StringRef(&One, 1)))
1079 return LinkageName.substr(1);
1080 return LinkageName;
1081}
1082
Devang Patel2c4ceb12009-11-21 02:48:08 +00001083/// createGlobalVariableDIE - Create new DIE using GV.
Devang Patel8a241142009-12-09 18:24:21 +00001084DIE *DwarfDebug::createGlobalVariableDIE(const DIGlobalVariable &GV) {
Jim Grosbach7ab38df2009-11-22 19:20:36 +00001085 // If the global variable was optmized out then no need to create debug info
1086 // entry.
Devang Patel84c73e92009-11-06 17:58:12 +00001087 if (!GV.getGlobal()) return NULL;
Devang Patel65dbc902009-11-25 17:36:49 +00001088 if (GV.getDisplayName().empty()) return NULL;
Devang Patel465c3be2009-11-06 01:30:04 +00001089
Bill Wendling0310d762009-05-15 09:23:25 +00001090 DIE *GVDie = new DIE(dwarf::DW_TAG_variable);
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001091 addString(GVDie, dwarf::DW_AT_name, dwarf::DW_FORM_string,
Devang Patel5ccdd102009-09-29 18:40:58 +00001092 GV.getDisplayName());
1093
Devang Patel65dbc902009-11-25 17:36:49 +00001094 StringRef LinkageName = GV.getLinkageName();
Devang Patel351ca332010-01-05 01:46:14 +00001095 if (!LinkageName.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001096 addString(GVDie, dwarf::DW_AT_MIPS_linkage_name, dwarf::DW_FORM_string,
Devang Patel351ca332010-01-05 01:46:14 +00001097 getRealLinkageName(LinkageName));
1098
Devang Patel8a241142009-12-09 18:24:21 +00001099 addType(GVDie, GV.getType());
Bill Wendling0310d762009-05-15 09:23:25 +00001100 if (!GV.isLocalToUnit())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001101 addUInt(GVDie, dwarf::DW_AT_external, dwarf::DW_FORM_flag, 1);
1102 addSourceLine(GVDie, &GV);
Devang Patelb71a16d2009-10-05 23:22:08 +00001103
Bill Wendling0310d762009-05-15 09:23:25 +00001104 return GVDie;
1105}
1106
Devang Patel2c4ceb12009-11-21 02:48:08 +00001107/// createMemberDIE - Create new member DIE.
Devang Patel8a241142009-12-09 18:24:21 +00001108DIE *DwarfDebug::createMemberDIE(const DIDerivedType &DT) {
Bill Wendling0310d762009-05-15 09:23:25 +00001109 DIE *MemberDie = new DIE(DT.getTag());
Devang Patel65dbc902009-11-25 17:36:49 +00001110 StringRef Name = DT.getName();
1111 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001112 addString(MemberDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Devang Patel65dbc902009-11-25 17:36:49 +00001113
Devang Patel8a241142009-12-09 18:24:21 +00001114 addType(MemberDie, DT.getTypeDerivedFrom());
Bill Wendling0310d762009-05-15 09:23:25 +00001115
Devang Patel2c4ceb12009-11-21 02:48:08 +00001116 addSourceLine(MemberDie, &DT);
Bill Wendling0310d762009-05-15 09:23:25 +00001117
Benjamin Kramer345ef342010-03-31 19:34:01 +00001118 DIEBlock *MemLocationDie = new (DIEValueAllocator) DIEBlock();
Devang Patel2c4ceb12009-11-21 02:48:08 +00001119 addUInt(MemLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
Devang Patel33db5082009-11-04 22:06:12 +00001120
Bill Wendling0310d762009-05-15 09:23:25 +00001121 uint64_t Size = DT.getSizeInBits();
Devang Patel61ecbd12009-11-04 23:48:00 +00001122 uint64_t FieldSize = DT.getOriginalTypeSize();
Bill Wendling0310d762009-05-15 09:23:25 +00001123
1124 if (Size != FieldSize) {
1125 // Handle bitfield.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001126 addUInt(MemberDie, dwarf::DW_AT_byte_size, 0, DT.getOriginalTypeSize()>>3);
1127 addUInt(MemberDie, dwarf::DW_AT_bit_size, 0, DT.getSizeInBits());
Bill Wendling0310d762009-05-15 09:23:25 +00001128
1129 uint64_t Offset = DT.getOffsetInBits();
Bill Wendling0310d762009-05-15 09:23:25 +00001130 uint64_t AlignMask = ~(DT.getAlignInBits() - 1);
1131 uint64_t HiMark = (Offset + FieldSize) & AlignMask;
Benjamin Kramer3d594fd2010-01-07 17:50:57 +00001132 uint64_t FieldOffset = (HiMark - FieldSize);
Bill Wendling0310d762009-05-15 09:23:25 +00001133 Offset -= FieldOffset;
1134
1135 // Maybe we need to work from the other end.
Chris Lattnerd38fee82010-04-05 00:13:49 +00001136 if (Asm->getTargetData().isLittleEndian())
1137 Offset = FieldSize - (Offset + Size);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001138 addUInt(MemberDie, dwarf::DW_AT_bit_offset, 0, Offset);
Bill Wendling0310d762009-05-15 09:23:25 +00001139
Devang Patel33db5082009-11-04 22:06:12 +00001140 // Here WD_AT_data_member_location points to the anonymous
1141 // field that includes this bit field.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001142 addUInt(MemLocationDie, 0, dwarf::DW_FORM_udata, FieldOffset >> 3);
Devang Patel33db5082009-11-04 22:06:12 +00001143
1144 } else
1145 // This is not a bitfield.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001146 addUInt(MemLocationDie, 0, dwarf::DW_FORM_udata, DT.getOffsetInBits() >> 3);
Devang Patel33db5082009-11-04 22:06:12 +00001147
Devang Patelc1dc8ff2010-02-03 20:08:48 +00001148 if (DT.getTag() == dwarf::DW_TAG_inheritance
1149 && DT.isVirtual()) {
1150
1151 // For C++, virtual base classes are not at fixed offset. Use following
1152 // expression to extract appropriate offset from vtable.
1153 // BaseAddr = ObAddr + *((*ObAddr) - Offset)
1154
Benjamin Kramer345ef342010-03-31 19:34:01 +00001155 DIEBlock *VBaseLocationDie = new (DIEValueAllocator) DIEBlock();
Devang Patelc1dc8ff2010-02-03 20:08:48 +00001156 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_dup);
1157 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
1158 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
1159 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_udata, DT.getOffsetInBits());
1160 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_minus);
1161 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
1162 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus);
1163
1164 addBlock(MemberDie, dwarf::DW_AT_data_member_location, 0,
1165 VBaseLocationDie);
1166 } else
1167 addBlock(MemberDie, dwarf::DW_AT_data_member_location, 0, MemLocationDie);
Bill Wendling0310d762009-05-15 09:23:25 +00001168
1169 if (DT.isProtected())
Devang Patel5d11eb02009-12-03 19:11:07 +00001170 addUInt(MemberDie, dwarf::DW_AT_accessibility, dwarf::DW_FORM_flag,
Bill Wendling0310d762009-05-15 09:23:25 +00001171 dwarf::DW_ACCESS_protected);
1172 else if (DT.isPrivate())
Devang Patel5d11eb02009-12-03 19:11:07 +00001173 addUInt(MemberDie, dwarf::DW_AT_accessibility, dwarf::DW_FORM_flag,
Bill Wendling0310d762009-05-15 09:23:25 +00001174 dwarf::DW_ACCESS_private);
Devang Patel5d11eb02009-12-03 19:11:07 +00001175 else if (DT.getTag() == dwarf::DW_TAG_inheritance)
1176 addUInt(MemberDie, dwarf::DW_AT_accessibility, dwarf::DW_FORM_flag,
1177 dwarf::DW_ACCESS_public);
1178 if (DT.isVirtual())
1179 addUInt(MemberDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_flag,
1180 dwarf::DW_VIRTUALITY_virtual);
Bill Wendling0310d762009-05-15 09:23:25 +00001181 return MemberDie;
1182}
1183
Devang Patelffe966c2009-12-14 16:18:45 +00001184/// createSubprogramDIE - Create new DIE using SP.
1185DIE *DwarfDebug::createSubprogramDIE(const DISubprogram &SP, bool MakeDecl) {
1186 DIE *SPDie = ModuleCU->getDIE(SP.getNode());
1187 if (SPDie)
1188 return SPDie;
1189
1190 SPDie = new DIE(dwarf::DW_TAG_subprogram);
Devang Patel1eac3e72010-03-02 17:58:15 +00001191 // Constructors and operators for anonymous aggregates do not have names.
Devang Patel6b506cb2010-03-02 01:26:20 +00001192 if (!SP.getName().empty())
1193 addString(SPDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, SP.getName());
Bill Wendling0310d762009-05-15 09:23:25 +00001194
Devang Patel65dbc902009-11-25 17:36:49 +00001195 StringRef LinkageName = SP.getLinkageName();
Devang Patel351ca332010-01-05 01:46:14 +00001196 if (!LinkageName.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001197 addString(SPDie, dwarf::DW_AT_MIPS_linkage_name, dwarf::DW_FORM_string,
Devang Patel351ca332010-01-05 01:46:14 +00001198 getRealLinkageName(LinkageName));
1199
Devang Patel2c4ceb12009-11-21 02:48:08 +00001200 addSourceLine(SPDie, &SP);
Bill Wendling0310d762009-05-15 09:23:25 +00001201
Bill Wendling0310d762009-05-15 09:23:25 +00001202 // Add prototyped tag, if C or ObjC.
1203 unsigned Lang = SP.getCompileUnit().getLanguage();
1204 if (Lang == dwarf::DW_LANG_C99 || Lang == dwarf::DW_LANG_C89 ||
1205 Lang == dwarf::DW_LANG_ObjC)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001206 addUInt(SPDie, dwarf::DW_AT_prototyped, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001207
1208 // Add Return Type.
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001209 DICompositeType SPTy = SP.getType();
1210 DIArray Args = SPTy.getTypeArray();
Bill Wendling0310d762009-05-15 09:23:25 +00001211 unsigned SPTag = SPTy.getTag();
Devang Patel5d11eb02009-12-03 19:11:07 +00001212
Devang Patel3c91b052010-03-08 20:52:55 +00001213 if (Args.getNumElements() == 0 || SPTag != dwarf::DW_TAG_subroutine_type)
Devang Patel8a241142009-12-09 18:24:21 +00001214 addType(SPDie, SPTy);
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001215 else
Devang Patel8a241142009-12-09 18:24:21 +00001216 addType(SPDie, DIType(Args.getElement(0).getNode()));
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001217
Devang Patel5d11eb02009-12-03 19:11:07 +00001218 unsigned VK = SP.getVirtuality();
1219 if (VK) {
1220 addUInt(SPDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_flag, VK);
Benjamin Kramer345ef342010-03-31 19:34:01 +00001221 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Devang Patel5d11eb02009-12-03 19:11:07 +00001222 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
1223 addUInt(Block, 0, dwarf::DW_FORM_data1, SP.getVirtualIndex());
1224 addBlock(SPDie, dwarf::DW_AT_vtable_elem_location, 0, Block);
Devang Patel622b0262010-01-19 06:19:05 +00001225 ContainingTypeMap.insert(std::make_pair(SPDie,
1226 SP.getContainingType().getNode()));
Devang Patel5d11eb02009-12-03 19:11:07 +00001227 }
1228
Devang Patelffe966c2009-12-14 16:18:45 +00001229 if (MakeDecl || !SP.isDefinition()) {
Devang Patel2c4ceb12009-11-21 02:48:08 +00001230 addUInt(SPDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001231
1232 // Add arguments. Do not add arguments for subprogram definition. They will
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001233 // be handled while processing variables.
1234 DICompositeType SPTy = SP.getType();
1235 DIArray Args = SPTy.getTypeArray();
1236 unsigned SPTag = SPTy.getTag();
1237
Bill Wendling0310d762009-05-15 09:23:25 +00001238 if (SPTag == dwarf::DW_TAG_subroutine_type)
1239 for (unsigned i = 1, N = Args.getNumElements(); i < N; ++i) {
1240 DIE *Arg = new DIE(dwarf::DW_TAG_formal_parameter);
Devang Patelb4645642010-02-06 01:02:37 +00001241 DIType ATy = DIType(DIType(Args.getElement(i).getNode()));
1242 addType(Arg, ATy);
1243 if (ATy.isArtificial())
1244 addUInt(Arg, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001245 SPDie->addChild(Arg);
Bill Wendling0310d762009-05-15 09:23:25 +00001246 }
1247 }
1248
Devang Patel4e0d19d2010-02-03 19:57:19 +00001249 if (SP.isArtificial())
1250 addUInt(SPDie, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
1251
Bill Wendling0310d762009-05-15 09:23:25 +00001252 // DW_TAG_inlined_subroutine may refer to this DIE.
Devang Patel8a241142009-12-09 18:24:21 +00001253 ModuleCU->insertDIE(SP.getNode(), SPDie);
Bill Wendling0310d762009-05-15 09:23:25 +00001254 return SPDie;
1255}
1256
Devang Patel8935d902010-04-01 17:16:48 +00001257/// getUpdatedDbgScope - Find DbgScope assicated with the instruction.
1258/// Update scope hierarchy. Create abstract scope if required.
Devang Patel53bb5c92009-11-10 23:06:00 +00001259DbgScope *DwarfDebug::getUpdatedDbgScope(MDNode *N, const MachineInstr *MI,
Chris Lattnered7a77b2010-03-31 05:36:29 +00001260 MDNode *InlinedAt) {
1261 assert(N && "Invalid Scope encoding!");
1262 assert(MI && "Missing machine instruction!");
Devang Patel8935d902010-04-01 17:16:48 +00001263 bool isAConcreteScope = InlinedAt != 0;
Devang Patel53bb5c92009-11-10 23:06:00 +00001264
1265 DbgScope *NScope = NULL;
1266
1267 if (InlinedAt)
1268 NScope = DbgScopeMap.lookup(InlinedAt);
1269 else
1270 NScope = DbgScopeMap.lookup(N);
Chris Lattnered7a77b2010-03-31 05:36:29 +00001271 assert(NScope && "Unable to find working scope!");
Devang Patel53bb5c92009-11-10 23:06:00 +00001272
1273 if (NScope->getFirstInsn())
1274 return NScope;
Devang Patelaf9e8472009-10-01 20:31:14 +00001275
1276 DbgScope *Parent = NULL;
Devang Patel8935d902010-04-01 17:16:48 +00001277 if (isAConcreteScope) {
Devang Patelc90aefe2009-10-14 21:08:09 +00001278 DILocation IL(InlinedAt);
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001279 Parent = getUpdatedDbgScope(IL.getScope().getNode(), MI,
Devang Patel53bb5c92009-11-10 23:06:00 +00001280 IL.getOrigLocation().getNode());
Chris Lattnered7a77b2010-03-31 05:36:29 +00001281 assert(Parent && "Unable to find Parent scope!");
Devang Patel53bb5c92009-11-10 23:06:00 +00001282 NScope->setParent(Parent);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001283 Parent->addScope(NScope);
Devang Patel53bb5c92009-11-10 23:06:00 +00001284 } else if (DIDescriptor(N).isLexicalBlock()) {
1285 DILexicalBlock DB(N);
Devang Patel3c91b052010-03-08 20:52:55 +00001286 Parent = getUpdatedDbgScope(DB.getContext().getNode(), MI, InlinedAt);
1287 NScope->setParent(Parent);
1288 Parent->addScope(NScope);
Devang Patelc90aefe2009-10-14 21:08:09 +00001289 }
Devang Patelaf9e8472009-10-01 20:31:14 +00001290
Devang Patelbdf45cb2009-10-27 20:47:17 +00001291 NScope->setFirstInsn(MI);
Devang Patelaf9e8472009-10-01 20:31:14 +00001292
Devang Patel53bb5c92009-11-10 23:06:00 +00001293 if (!Parent && !InlinedAt) {
Devang Patel39ae3ff2009-11-11 00:31:36 +00001294 StringRef SPName = DISubprogram(N).getLinkageName();
Chris Lattnerd38fee82010-04-05 00:13:49 +00001295 if (SPName == Asm->MF->getFunction()->getName())
Devang Patel39ae3ff2009-11-11 00:31:36 +00001296 CurrentFnDbgScope = NScope;
Devang Patel53bb5c92009-11-10 23:06:00 +00001297 }
Devang Patelaf9e8472009-10-01 20:31:14 +00001298
Devang Patel8935d902010-04-01 17:16:48 +00001299 if (isAConcreteScope) {
Devang Patel53bb5c92009-11-10 23:06:00 +00001300 ConcreteScopes[InlinedAt] = NScope;
1301 getOrCreateAbstractScope(N);
1302 }
1303
Devang Patelbdf45cb2009-10-27 20:47:17 +00001304 return NScope;
Devang Patelaf9e8472009-10-01 20:31:14 +00001305}
1306
Devang Patel53bb5c92009-11-10 23:06:00 +00001307DbgScope *DwarfDebug::getOrCreateAbstractScope(MDNode *N) {
Chris Lattnered7a77b2010-03-31 05:36:29 +00001308 assert(N && "Invalid Scope encoding!");
Devang Patel53bb5c92009-11-10 23:06:00 +00001309
1310 DbgScope *AScope = AbstractScopes.lookup(N);
1311 if (AScope)
1312 return AScope;
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001313
Devang Patel53bb5c92009-11-10 23:06:00 +00001314 DbgScope *Parent = NULL;
1315
1316 DIDescriptor Scope(N);
1317 if (Scope.isLexicalBlock()) {
1318 DILexicalBlock DB(N);
1319 DIDescriptor ParentDesc = DB.getContext();
Devang Patel3c91b052010-03-08 20:52:55 +00001320 Parent = getOrCreateAbstractScope(ParentDesc.getNode());
Devang Patel53bb5c92009-11-10 23:06:00 +00001321 }
1322
1323 AScope = new DbgScope(Parent, DIDescriptor(N), NULL);
1324
1325 if (Parent)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001326 Parent->addScope(AScope);
Devang Patel53bb5c92009-11-10 23:06:00 +00001327 AScope->setAbstractScope();
1328 AbstractScopes[N] = AScope;
1329 if (DIDescriptor(N).isSubprogram())
1330 AbstractScopesList.push_back(AScope);
1331 return AScope;
1332}
Devang Patelaf9e8472009-10-01 20:31:14 +00001333
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001334/// updateSubprogramScopeDIE - Find DIE for the given subprogram and
Devang Patel2c4ceb12009-11-21 02:48:08 +00001335/// attach appropriate DW_AT_low_pc and DW_AT_high_pc attributes.
1336/// If there are global variables in this scope then create and insert
1337/// DIEs for these variables.
1338DIE *DwarfDebug::updateSubprogramScopeDIE(MDNode *SPNode) {
Chris Lattnerd38fee82010-04-05 00:13:49 +00001339 DIE *SPDie = ModuleCU->getDIE(SPNode);
1340 assert(SPDie && "Unable to find subprogram DIE!");
1341 DISubprogram SP(SPNode);
Chris Lattner206d61e2010-03-13 07:26:18 +00001342
Chris Lattnerd38fee82010-04-05 00:13:49 +00001343 // There is not any need to generate specification DIE for a function
1344 // defined at compile unit level. If a function is defined inside another
1345 // function then gdb prefers the definition at top level and but does not
1346 // expect specification DIE in parent function. So avoid creating
1347 // specification DIE for a function defined inside a function.
1348 if (SP.isDefinition() && !SP.getContext().isCompileUnit() &&
1349 !SP.getContext().isFile() && !SP.getContext().isSubprogram()) {
1350 addUInt(SPDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
1351
1352 // Add arguments.
1353 DICompositeType SPTy = SP.getType();
1354 DIArray Args = SPTy.getTypeArray();
1355 unsigned SPTag = SPTy.getTag();
1356 if (SPTag == dwarf::DW_TAG_subroutine_type)
1357 for (unsigned i = 1, N = Args.getNumElements(); i < N; ++i) {
1358 DIE *Arg = new DIE(dwarf::DW_TAG_formal_parameter);
1359 DIType ATy = DIType(DIType(Args.getElement(i).getNode()));
1360 addType(Arg, ATy);
1361 if (ATy.isArtificial())
1362 addUInt(Arg, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
1363 SPDie->addChild(Arg);
1364 }
1365 DIE *SPDeclDie = SPDie;
1366 SPDie = new DIE(dwarf::DW_TAG_subprogram);
1367 addDIEEntry(SPDie, dwarf::DW_AT_specification, dwarf::DW_FORM_ref4,
1368 SPDeclDie);
1369 ModuleCU->addDie(SPDie);
1370 }
1371
1372 addLabel(SPDie, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr,
1373 Asm->GetTempSymbol("func_begin", Asm->getFunctionNumber()));
1374 addLabel(SPDie, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr,
1375 Asm->GetTempSymbol("func_end", Asm->getFunctionNumber()));
1376 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
1377 MachineLocation Location(RI->getFrameRegister(*Asm->MF));
1378 addAddress(SPDie, dwarf::DW_AT_frame_base, Location);
Devang Patelb4645642010-02-06 01:02:37 +00001379
Chris Lattnerd38fee82010-04-05 00:13:49 +00001380 if (!DISubprogram(SPNode).isLocalToUnit())
1381 addUInt(SPDie, dwarf::DW_AT_external, dwarf::DW_FORM_flag, 1);
1382
1383 return SPDie;
Devang Patel53bb5c92009-11-10 23:06:00 +00001384}
1385
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001386/// constructLexicalScope - Construct new DW_TAG_lexical_block
Devang Patel2c4ceb12009-11-21 02:48:08 +00001387/// for this scope and attach DW_AT_low_pc/DW_AT_high_pc labels.
1388DIE *DwarfDebug::constructLexicalScopeDIE(DbgScope *Scope) {
Chris Lattnerb7db7332010-03-09 01:58:53 +00001389 MCSymbol *Start = Scope->getStartLabel();
1390 MCSymbol *End = Scope->getEndLabel();
Devang Patelaead63c2010-03-29 22:59:58 +00001391 if (Start == 0 || End == 0) return 0;
Devang Patel53bb5c92009-11-10 23:06:00 +00001392
Chris Lattnerb7db7332010-03-09 01:58:53 +00001393 assert(Start->isDefined() && "Invalid starting label for an inlined scope!");
1394 assert(End->isDefined() && "Invalid end label for an inlined scope!");
Chris Lattnera34ec2292010-03-09 01:51:43 +00001395
Devang Patel53bb5c92009-11-10 23:06:00 +00001396 DIE *ScopeDIE = new DIE(dwarf::DW_TAG_lexical_block);
1397 if (Scope->isAbstractScope())
1398 return ScopeDIE;
1399
Devang Patel2c4ceb12009-11-21 02:48:08 +00001400 addLabel(ScopeDIE, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr,
Chris Lattnerd38fee82010-04-05 00:13:49 +00001401 Start ? Start : Asm->GetTempSymbol("func_begin",
1402 Asm->getFunctionNumber()));
Devang Patel2c4ceb12009-11-21 02:48:08 +00001403 addLabel(ScopeDIE, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr,
Chris Lattnerd38fee82010-04-05 00:13:49 +00001404 End ? End : Asm->GetTempSymbol("func_end",Asm->getFunctionNumber()));
Devang Patel53bb5c92009-11-10 23:06:00 +00001405
1406 return ScopeDIE;
1407}
1408
Devang Patel2c4ceb12009-11-21 02:48:08 +00001409/// constructInlinedScopeDIE - This scope represents inlined body of
1410/// a function. Construct DIE to represent this concrete inlined copy
1411/// of the function.
1412DIE *DwarfDebug::constructInlinedScopeDIE(DbgScope *Scope) {
Chris Lattnerb7db7332010-03-09 01:58:53 +00001413 MCSymbol *StartLabel = Scope->getStartLabel();
1414 MCSymbol *EndLabel = Scope->getEndLabel();
Devang Patelaead63c2010-03-29 22:59:58 +00001415 if (StartLabel == 0 || EndLabel == 0) return 0;
Chris Lattner6c7dfc02010-03-09 04:48:35 +00001416
Chris Lattnerb7db7332010-03-09 01:58:53 +00001417 assert(StartLabel->isDefined() &&
Chris Lattnera34ec2292010-03-09 01:51:43 +00001418 "Invalid starting label for an inlined scope!");
Chris Lattnerb7db7332010-03-09 01:58:53 +00001419 assert(EndLabel->isDefined() &&
Chris Lattnera34ec2292010-03-09 01:51:43 +00001420 "Invalid end label for an inlined scope!");
Devang Patel3c91b052010-03-08 20:52:55 +00001421 if (!Scope->getScopeNode())
Devang Patel0ef3fa62010-03-08 19:20:38 +00001422 return NULL;
Devang Patel3c91b052010-03-08 20:52:55 +00001423 DIScope DS(Scope->getScopeNode());
Devang Patel53bb5c92009-11-10 23:06:00 +00001424 DIE *ScopeDIE = new DIE(dwarf::DW_TAG_inlined_subroutine);
1425
1426 DISubprogram InlinedSP = getDISubprogram(DS.getNode());
Devang Patel017d1212009-11-20 21:37:22 +00001427 DIE *OriginDIE = ModuleCU->getDIE(InlinedSP.getNode());
Chris Lattnered7a77b2010-03-31 05:36:29 +00001428 assert(OriginDIE && "Unable to find Origin DIE!");
Devang Patel2c4ceb12009-11-21 02:48:08 +00001429 addDIEEntry(ScopeDIE, dwarf::DW_AT_abstract_origin,
Devang Patel53bb5c92009-11-10 23:06:00 +00001430 dwarf::DW_FORM_ref4, OriginDIE);
1431
Chris Lattner6ed0f902010-03-09 00:31:02 +00001432 addLabel(ScopeDIE, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr, StartLabel);
Chris Lattnerb7db7332010-03-09 01:58:53 +00001433 addLabel(ScopeDIE, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr, EndLabel);
Devang Patel53bb5c92009-11-10 23:06:00 +00001434
1435 InlinedSubprogramDIEs.insert(OriginDIE);
1436
1437 // Track the start label for this inlined function.
Devang Patel622b0262010-01-19 06:19:05 +00001438 DenseMap<MDNode *, SmallVector<InlineInfoLabels, 4> >::iterator
Devang Patel53bb5c92009-11-10 23:06:00 +00001439 I = InlineInfo.find(InlinedSP.getNode());
1440
1441 if (I == InlineInfo.end()) {
Chris Lattner6ed0f902010-03-09 00:31:02 +00001442 InlineInfo[InlinedSP.getNode()].push_back(std::make_pair(StartLabel,
Jim Grosbach7ab38df2009-11-22 19:20:36 +00001443 ScopeDIE));
Devang Patel53bb5c92009-11-10 23:06:00 +00001444 InlinedSPNodes.push_back(InlinedSP.getNode());
1445 } else
Chris Lattner6ed0f902010-03-09 00:31:02 +00001446 I->second.push_back(std::make_pair(StartLabel, ScopeDIE));
Devang Patel53bb5c92009-11-10 23:06:00 +00001447
Devang Patel53bb5c92009-11-10 23:06:00 +00001448 DILocation DL(Scope->getInlinedAt());
Devang Patel2c4ceb12009-11-21 02:48:08 +00001449 addUInt(ScopeDIE, dwarf::DW_AT_call_file, 0, ModuleCU->getID());
1450 addUInt(ScopeDIE, dwarf::DW_AT_call_line, 0, DL.getLineNumber());
Devang Patel53bb5c92009-11-10 23:06:00 +00001451
1452 return ScopeDIE;
1453}
1454
Devang Patel2c4ceb12009-11-21 02:48:08 +00001455
1456/// constructVariableDIE - Construct a DIE for the given DbgVariable.
Devang Patel8a241142009-12-09 18:24:21 +00001457DIE *DwarfDebug::constructVariableDIE(DbgVariable *DV, DbgScope *Scope) {
Devang Patel53bb5c92009-11-10 23:06:00 +00001458 // Get the descriptor.
1459 const DIVariable &VD = DV->getVariable();
Devang Patel65dbc902009-11-25 17:36:49 +00001460 StringRef Name = VD.getName();
1461 if (Name.empty())
Devang Patel3fb6bd62009-11-13 02:25:26 +00001462 return NULL;
Devang Patel53bb5c92009-11-10 23:06:00 +00001463
1464 // Translate tag to proper Dwarf tag. The result variable is dropped for
1465 // now.
1466 unsigned Tag;
1467 switch (VD.getTag()) {
1468 case dwarf::DW_TAG_return_variable:
1469 return NULL;
1470 case dwarf::DW_TAG_arg_variable:
1471 Tag = dwarf::DW_TAG_formal_parameter;
1472 break;
1473 case dwarf::DW_TAG_auto_variable: // fall thru
1474 default:
1475 Tag = dwarf::DW_TAG_variable;
1476 break;
1477 }
1478
1479 // Define variable debug information entry.
1480 DIE *VariableDie = new DIE(Tag);
1481
1482
1483 DIE *AbsDIE = NULL;
1484 if (DbgVariable *AV = DV->getAbstractVariable())
1485 AbsDIE = AV->getDIE();
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001486
Devang Patel53bb5c92009-11-10 23:06:00 +00001487 if (AbsDIE) {
1488 DIScope DS(Scope->getScopeNode());
1489 DISubprogram InlinedSP = getDISubprogram(DS.getNode());
Devang Patel017d1212009-11-20 21:37:22 +00001490 DIE *OriginSPDIE = ModuleCU->getDIE(InlinedSP.getNode());
Daniel Dunbarc0326792009-11-11 03:09:50 +00001491 (void) OriginSPDIE;
Chris Lattnered7a77b2010-03-31 05:36:29 +00001492 assert(OriginSPDIE && "Unable to find Origin DIE for the SP!");
Devang Patel53bb5c92009-11-10 23:06:00 +00001493 DIE *AbsDIE = DV->getAbstractVariable()->getDIE();
Chris Lattnered7a77b2010-03-31 05:36:29 +00001494 assert(AbsDIE && "Unable to find Origin DIE for the Variable!");
Devang Patel2c4ceb12009-11-21 02:48:08 +00001495 addDIEEntry(VariableDie, dwarf::DW_AT_abstract_origin,
Devang Patel53bb5c92009-11-10 23:06:00 +00001496 dwarf::DW_FORM_ref4, AbsDIE);
1497 }
1498 else {
Devang Patel2c4ceb12009-11-21 02:48:08 +00001499 addString(VariableDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
1500 addSourceLine(VariableDie, &VD);
Devang Patel53bb5c92009-11-10 23:06:00 +00001501
1502 // Add variable type.
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001503 // FIXME: isBlockByrefVariable should be reformulated in terms of complex
Devang Patel53bb5c92009-11-10 23:06:00 +00001504 // addresses instead.
1505 if (VD.isBlockByrefVariable())
Devang Patel8a241142009-12-09 18:24:21 +00001506 addType(VariableDie, getBlockByrefType(VD.getType(), Name));
Devang Patel53bb5c92009-11-10 23:06:00 +00001507 else
Devang Patel8a241142009-12-09 18:24:21 +00001508 addType(VariableDie, VD.getType());
Devang Patel53bb5c92009-11-10 23:06:00 +00001509 }
1510
1511 // Add variable address.
1512 if (!Scope->isAbstractScope()) {
Devang Patel90a48ad2010-03-15 18:33:46 +00001513 // Check if variable is described by DBG_VALUE instruction.
1514 if (const MachineInstr *DbgValueInsn = DV->getDbgValue()) {
1515 if (DbgValueInsn->getNumOperands() == 3) {
1516 // FIXME : Handle getNumOperands != 3
1517 if (DbgValueInsn->getOperand(0).getType()
1518 == MachineOperand::MO_Register
1519 && DbgValueInsn->getOperand(0).getReg()) {
1520 MachineLocation Location;
1521 Location.set(DbgValueInsn->getOperand(0).getReg());
1522 addAddress(VariableDie, dwarf::DW_AT_location, Location);
Devang Patelaead63c2010-03-29 22:59:58 +00001523 if (MCSymbol *VS = DV->getDbgValueLabel())
1524 addLabel(VariableDie, dwarf::DW_AT_start_scope, dwarf::DW_FORM_addr,
1525 VS);
Devang Patel90a48ad2010-03-15 18:33:46 +00001526 } else if (DbgValueInsn->getOperand(0).getType() ==
1527 MachineOperand::MO_Immediate) {
Benjamin Kramer345ef342010-03-31 19:34:01 +00001528 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Devang Patel90a48ad2010-03-15 18:33:46 +00001529 unsigned Imm = DbgValueInsn->getOperand(0).getImm();
1530 addUInt(Block, 0, dwarf::DW_FORM_udata, Imm);
1531 addBlock(VariableDie, dwarf::DW_AT_const_value, 0, Block);
Devang Patelaead63c2010-03-29 22:59:58 +00001532 if (MCSymbol *VS = DV->getDbgValueLabel())
1533 addLabel(VariableDie, dwarf::DW_AT_start_scope, dwarf::DW_FORM_addr,
1534 VS);
Devang Patel90a48ad2010-03-15 18:33:46 +00001535 } else {
1536 //FIXME : Handle other operand types.
1537 delete VariableDie;
1538 return NULL;
1539 }
1540 }
1541 } else {
1542 MachineLocation Location;
1543 unsigned FrameReg;
Chris Lattnerd38fee82010-04-05 00:13:49 +00001544 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
1545 int Offset = RI->getFrameIndexReference(*Asm->MF, DV->getFrameIndex(),
Chris Lattner1d65ba72010-03-31 06:06:37 +00001546 FrameReg);
Devang Patel90a48ad2010-03-15 18:33:46 +00001547 Location.set(FrameReg, Offset);
1548
1549 if (VD.hasComplexAddress())
1550 addComplexAddress(DV, VariableDie, dwarf::DW_AT_location, Location);
1551 else if (VD.isBlockByrefVariable())
1552 addBlockByrefAddress(DV, VariableDie, dwarf::DW_AT_location, Location);
1553 else
1554 addAddress(VariableDie, dwarf::DW_AT_location, Location);
1555 }
Devang Patel53bb5c92009-11-10 23:06:00 +00001556 }
Devang Patelb4645642010-02-06 01:02:37 +00001557
1558 if (Tag == dwarf::DW_TAG_formal_parameter && VD.getType().isArtificial())
1559 addUInt(VariableDie, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
Devang Patel53bb5c92009-11-10 23:06:00 +00001560 DV->setDIE(VariableDie);
1561 return VariableDie;
1562
1563}
Devang Patel2c4ceb12009-11-21 02:48:08 +00001564
Devang Patel193f7202009-11-24 01:14:22 +00001565void DwarfDebug::addPubTypes(DISubprogram SP) {
1566 DICompositeType SPTy = SP.getType();
1567 unsigned SPTag = SPTy.getTag();
1568 if (SPTag != dwarf::DW_TAG_subroutine_type)
1569 return;
1570
1571 DIArray Args = SPTy.getTypeArray();
Devang Patel193f7202009-11-24 01:14:22 +00001572 for (unsigned i = 0, e = Args.getNumElements(); i != e; ++i) {
1573 DIType ATy(Args.getElement(i).getNode());
Devang Patel3c91b052010-03-08 20:52:55 +00001574 if (!ATy.isValid())
Devang Patel193f7202009-11-24 01:14:22 +00001575 continue;
1576 DICompositeType CATy = getDICompositeType(ATy);
Devang Patel3c91b052010-03-08 20:52:55 +00001577 if (DIDescriptor(CATy.getNode()).Verify() && !CATy.getName().empty()) {
Devang Patel193f7202009-11-24 01:14:22 +00001578 if (DIEEntry *Entry = ModuleCU->getDIEEntry(CATy.getNode()))
1579 ModuleCU->addGlobalType(CATy.getName(), Entry->getEntry());
1580 }
1581 }
1582}
1583
Devang Patel2c4ceb12009-11-21 02:48:08 +00001584/// constructScopeDIE - Construct a DIE for this scope.
1585DIE *DwarfDebug::constructScopeDIE(DbgScope *Scope) {
Devang Patel3c91b052010-03-08 20:52:55 +00001586 if (!Scope || !Scope->getScopeNode())
1587 return NULL;
1588
1589 DIScope DS(Scope->getScopeNode());
1590 DIE *ScopeDIE = NULL;
1591 if (Scope->getInlinedAt())
1592 ScopeDIE = constructInlinedScopeDIE(Scope);
1593 else if (DS.isSubprogram()) {
1594 if (Scope->isAbstractScope())
1595 ScopeDIE = ModuleCU->getDIE(DS.getNode());
1596 else
1597 ScopeDIE = updateSubprogramScopeDIE(DS.getNode());
1598 }
Devang Patelaead63c2010-03-29 22:59:58 +00001599 else
Devang Patel3c91b052010-03-08 20:52:55 +00001600 ScopeDIE = constructLexicalScopeDIE(Scope);
Devang Patelaead63c2010-03-29 22:59:58 +00001601 if (!ScopeDIE) return NULL;
Devang Patel3c91b052010-03-08 20:52:55 +00001602
Devang Patel53bb5c92009-11-10 23:06:00 +00001603 // Add variables to scope.
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00001604 const SmallVector<DbgVariable *, 8> &Variables = Scope->getVariables();
Devang Patel53bb5c92009-11-10 23:06:00 +00001605 for (unsigned i = 0, N = Variables.size(); i < N; ++i) {
Devang Patel8a241142009-12-09 18:24:21 +00001606 DIE *VariableDIE = constructVariableDIE(Variables[i], Scope);
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001607 if (VariableDIE)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001608 ScopeDIE->addChild(VariableDIE);
Devang Patel53bb5c92009-11-10 23:06:00 +00001609 }
1610
1611 // Add nested scopes.
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00001612 const SmallVector<DbgScope *, 4> &Scopes = Scope->getScopes();
Devang Patel53bb5c92009-11-10 23:06:00 +00001613 for (unsigned j = 0, M = Scopes.size(); j < M; ++j) {
1614 // Define the Scope debug information entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001615 DIE *NestedDIE = constructScopeDIE(Scopes[j]);
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001616 if (NestedDIE)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001617 ScopeDIE->addChild(NestedDIE);
Devang Patel53bb5c92009-11-10 23:06:00 +00001618 }
Devang Patel193f7202009-11-24 01:14:22 +00001619
1620 if (DS.isSubprogram())
1621 addPubTypes(DISubprogram(DS.getNode()));
1622
1623 return ScopeDIE;
Devang Patel53bb5c92009-11-10 23:06:00 +00001624}
1625
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001626/// GetOrCreateSourceID - Look up the source id with the given directory and
1627/// source file names. If none currently exists, create a new id and insert it
1628/// in the SourceIds map. This can update DirectoryNames and SourceFileNames
1629/// maps as well.
Chris Lattner1d65ba72010-03-31 06:06:37 +00001630unsigned DwarfDebug::GetOrCreateSourceID(StringRef DirName, StringRef FileName){
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001631 unsigned DId;
1632 StringMap<unsigned>::iterator DI = DirectoryIdMap.find(DirName);
1633 if (DI != DirectoryIdMap.end()) {
1634 DId = DI->getValue();
1635 } else {
1636 DId = DirectoryNames.size() + 1;
1637 DirectoryIdMap[DirName] = DId;
1638 DirectoryNames.push_back(DirName);
1639 }
1640
1641 unsigned FId;
1642 StringMap<unsigned>::iterator FI = SourceFileIdMap.find(FileName);
1643 if (FI != SourceFileIdMap.end()) {
1644 FId = FI->getValue();
1645 } else {
1646 FId = SourceFileNames.size() + 1;
1647 SourceFileIdMap[FileName] = FId;
1648 SourceFileNames.push_back(FileName);
1649 }
1650
1651 DenseMap<std::pair<unsigned, unsigned>, unsigned>::iterator SI =
1652 SourceIdMap.find(std::make_pair(DId, FId));
1653 if (SI != SourceIdMap.end())
1654 return SI->second;
1655
1656 unsigned SrcId = SourceIds.size() + 1; // DW_AT_decl_file cannot be 0.
1657 SourceIdMap[std::make_pair(DId, FId)] = SrcId;
1658 SourceIds.push_back(std::make_pair(DId, FId));
1659
1660 return SrcId;
1661}
1662
Devang Patel6404e4e2009-12-15 19:16:48 +00001663/// getOrCreateNameSpace - Create a DIE for DINameSpace.
1664DIE *DwarfDebug::getOrCreateNameSpace(DINameSpace NS) {
1665 DIE *NDie = ModuleCU->getDIE(NS.getNode());
1666 if (NDie)
1667 return NDie;
1668 NDie = new DIE(dwarf::DW_TAG_namespace);
1669 ModuleCU->insertDIE(NS.getNode(), NDie);
1670 if (!NS.getName().empty())
1671 addString(NDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, NS.getName());
1672 addSourceLine(NDie, &NS);
1673 addToContextOwner(NDie, NS.getContext());
1674 return NDie;
1675}
1676
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +00001677void DwarfDebug::constructCompileUnit(MDNode *N) {
Devang Patele4b27562009-08-28 23:24:31 +00001678 DICompileUnit DIUnit(N);
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +00001679 // Use first compile unit marked as isMain as the compile unit for this
1680 // module.
1681 if (ModuleCU || !DIUnit.isMain())
1682 return;
Devang Patel65dbc902009-11-25 17:36:49 +00001683 StringRef FN = DIUnit.getFilename();
1684 StringRef Dir = DIUnit.getDirectory();
Devang Patel5ccdd102009-09-29 18:40:58 +00001685 unsigned ID = GetOrCreateSourceID(Dir, FN);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001686
1687 DIE *Die = new DIE(dwarf::DW_TAG_compile_unit);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001688 addString(Die, dwarf::DW_AT_producer, dwarf::DW_FORM_string,
Devang Patel5ccdd102009-09-29 18:40:58 +00001689 DIUnit.getProducer());
Devang Patel2c4ceb12009-11-21 02:48:08 +00001690 addUInt(Die, dwarf::DW_AT_language, dwarf::DW_FORM_data1,
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001691 DIUnit.getLanguage());
Devang Patel2c4ceb12009-11-21 02:48:08 +00001692 addString(Die, dwarf::DW_AT_name, dwarf::DW_FORM_string, FN);
Chris Lattner9c69e285532010-04-04 22:59:04 +00001693 addLabel(Die, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr, TextSectionSym);
Devang Patel4a602ca2010-03-22 23:11:36 +00001694 addLabel(Die, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr,
Chris Lattnerc0215722010-04-04 19:25:43 +00001695 Asm->GetTempSymbol("text_end"));
Devang Patel4a602ca2010-03-22 23:11:36 +00001696 // DW_AT_stmt_list is a offset of line number information for this
1697 // compile unit in debug_line section. It is always zero when only one
1698 // compile unit is emitted in one object file.
1699 addUInt(Die, dwarf::DW_AT_stmt_list, dwarf::DW_FORM_data4, 0);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001700
Devang Patel65dbc902009-11-25 17:36:49 +00001701 if (!Dir.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001702 addString(Die, dwarf::DW_AT_comp_dir, dwarf::DW_FORM_string, Dir);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001703 if (DIUnit.isOptimized())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001704 addUInt(Die, dwarf::DW_AT_APPLE_optimized, dwarf::DW_FORM_flag, 1);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001705
Devang Patel65dbc902009-11-25 17:36:49 +00001706 StringRef Flags = DIUnit.getFlags();
1707 if (!Flags.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001708 addString(Die, dwarf::DW_AT_APPLE_flags, dwarf::DW_FORM_string, Flags);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001709
1710 unsigned RVer = DIUnit.getRunTimeVersion();
1711 if (RVer)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001712 addUInt(Die, dwarf::DW_AT_APPLE_major_runtime_vers,
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001713 dwarf::DW_FORM_data1, RVer);
1714
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +00001715 assert(!ModuleCU &&
1716 "ModuleCU assigned since the top of constructCompileUnit");
1717 ModuleCU = new CompileUnit(ID, Die);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001718}
1719
Devang Patel2c4ceb12009-11-21 02:48:08 +00001720void DwarfDebug::constructGlobalVariableDIE(MDNode *N) {
Devang Patele4b27562009-08-28 23:24:31 +00001721 DIGlobalVariable DI_GV(N);
Daniel Dunbarf612ff62009-09-19 20:40:05 +00001722
Devang Patel905cf5e2009-09-04 23:59:07 +00001723 // If debug information is malformed then ignore it.
1724 if (DI_GV.Verify() == false)
1725 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001726
1727 // Check for pre-existence.
Devang Patel017d1212009-11-20 21:37:22 +00001728 if (ModuleCU->getDIE(DI_GV.getNode()))
Devang Patel13e16b62009-06-26 01:49:18 +00001729 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001730
Devang Patel8a241142009-12-09 18:24:21 +00001731 DIE *VariableDie = createGlobalVariableDIE(DI_GV);
Devang Pateledb45632009-12-10 23:25:41 +00001732 if (!VariableDie)
1733 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001734
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001735 // Add to map.
Devang Patel017d1212009-11-20 21:37:22 +00001736 ModuleCU->insertDIE(N, VariableDie);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001737
1738 // Add to context owner.
Devang Patelc9b16cc2010-01-15 01:12:22 +00001739 DIDescriptor GVContext = DI_GV.getContext();
1740 // Do not create specification DIE if context is either compile unit
1741 // or a subprogram.
Chris Lattner1d65ba72010-03-31 06:06:37 +00001742 if (DI_GV.isDefinition() && !GVContext.isCompileUnit() &&
1743 !GVContext.isFile() && !GVContext.isSubprogram()) {
Devang Patel6404e4e2009-12-15 19:16:48 +00001744 // Create specification DIE.
1745 DIE *VariableSpecDIE = new DIE(dwarf::DW_TAG_variable);
1746 addDIEEntry(VariableSpecDIE, dwarf::DW_AT_specification,
1747 dwarf::DW_FORM_ref4, VariableDie);
Benjamin Kramer345ef342010-03-31 19:34:01 +00001748 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Devang Patel6404e4e2009-12-15 19:16:48 +00001749 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_addr);
Chris Lattner4faf59a2010-03-08 22:31:46 +00001750 addLabel(Block, 0, dwarf::DW_FORM_udata,
Chris Lattnerdeb0cba2010-03-12 21:09:07 +00001751 Asm->Mang->getSymbol(DI_GV.getGlobal()));
Devang Patel6404e4e2009-12-15 19:16:48 +00001752 addBlock(VariableSpecDIE, dwarf::DW_AT_location, 0, Block);
Devang Patel8581e012010-02-09 01:58:33 +00001753 addUInt(VariableDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
Devang Patel6404e4e2009-12-15 19:16:48 +00001754 ModuleCU->addDie(VariableSpecDIE);
1755 } else {
Benjamin Kramer345ef342010-03-31 19:34:01 +00001756 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Devang Patel6404e4e2009-12-15 19:16:48 +00001757 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_addr);
Chris Lattner4faf59a2010-03-08 22:31:46 +00001758 addLabel(Block, 0, dwarf::DW_FORM_udata,
Chris Lattnerdeb0cba2010-03-12 21:09:07 +00001759 Asm->Mang->getSymbol(DI_GV.getGlobal()));
Devang Patel6404e4e2009-12-15 19:16:48 +00001760 addBlock(VariableDie, dwarf::DW_AT_location, 0, Block);
1761 }
Devang Patelc9b16cc2010-01-15 01:12:22 +00001762 addToContextOwner(VariableDie, GVContext);
Devang Patelc366f832009-12-10 19:14:49 +00001763
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001764 // Expose as global. FIXME - need to check external flag.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001765 ModuleCU->addGlobal(DI_GV.getName(), VariableDie);
Devang Patel193f7202009-11-24 01:14:22 +00001766
1767 DIType GTy = DI_GV.getType();
Devang Patel65dbc902009-11-25 17:36:49 +00001768 if (GTy.isCompositeType() && !GTy.getName().empty()) {
Devang Patel193f7202009-11-24 01:14:22 +00001769 DIEEntry *Entry = ModuleCU->getDIEEntry(GTy.getNode());
Chris Lattnered7a77b2010-03-31 05:36:29 +00001770 assert(Entry && "Missing global type!");
Devang Patel193f7202009-11-24 01:14:22 +00001771 ModuleCU->addGlobalType(GTy.getName(), Entry->getEntry());
1772 }
Devang Patel13e16b62009-06-26 01:49:18 +00001773 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001774}
1775
Devang Patel2c4ceb12009-11-21 02:48:08 +00001776void DwarfDebug::constructSubprogramDIE(MDNode *N) {
Devang Patele4b27562009-08-28 23:24:31 +00001777 DISubprogram SP(N);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001778
Stuart Hastingsf8df8142010-03-31 23:08:46 +00001779 // Check for pre-existence.
1780 if (ModuleCU->getDIE(N))
1781 return;
1782
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001783 if (!SP.isDefinition())
1784 // This is a method declaration which will be handled while constructing
1785 // class type.
Devang Patel13e16b62009-06-26 01:49:18 +00001786 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001787
Stuart Hastingsf8df8142010-03-31 23:08:46 +00001788 DIE *SubprogramDie = createSubprogramDIE(SP);
1789
1790 // Add to map.
1791 ModuleCU->insertDIE(N, SubprogramDie);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001792
1793 // Add to context owner.
Devang Patel6404e4e2009-12-15 19:16:48 +00001794 addToContextOwner(SubprogramDie, SP.getContext());
Devang Patel0000fad2009-12-08 23:21:45 +00001795
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001796 // Expose as global.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001797 ModuleCU->addGlobal(SP.getName(), SubprogramDie);
Devang Patel193f7202009-11-24 01:14:22 +00001798
Devang Patel13e16b62009-06-26 01:49:18 +00001799 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001800}
1801
Devang Patel2c4ceb12009-11-21 02:48:08 +00001802/// beginModule - Emit all Dwarf sections that should come prior to the
Daniel Dunbar00564992009-09-19 20:40:14 +00001803/// content. Create global DIEs and emit initial debug info sections.
1804/// This is inovked by the target AsmPrinter.
Chris Lattner75f50722010-04-04 07:48:20 +00001805void DwarfDebug::beginModule(Module *M) {
Chris Lattnera909d662010-03-29 20:38:20 +00001806 TimeRegion Timer(DebugTimer);
Chris Lattnerd850ac72010-04-05 02:19:28 +00001807
Devang Patel78ab9e22009-07-30 18:56:46 +00001808 DebugInfoFinder DbgFinder;
1809 DbgFinder.processModule(*M);
Devang Patel13e16b62009-06-26 01:49:18 +00001810
Chris Lattnerd850ac72010-04-05 02:19:28 +00001811 bool HasDebugInfo = false;
1812
1813 // Scan all the compile-units to see if there are any marked as the main unit.
1814 // if not, we do not generate debug info.
1815 for (DebugInfoFinder::iterator I = DbgFinder.compile_unit_begin(),
1816 E = DbgFinder.compile_unit_end(); I != E; ++I) {
1817 if (DICompileUnit(*I).isMain()) {
1818 HasDebugInfo = true;
1819 break;
1820 }
1821 }
1822
1823 if (!HasDebugInfo) return;
1824
1825 // Tell MMI that we have debug info.
1826 MMI->setDebugInfoAvailability(true);
1827
Chris Lattnerbe15beb2010-04-04 23:17:54 +00001828 // Emit initial sections.
Chris Lattnerd850ac72010-04-05 02:19:28 +00001829 EmitSectionLabels();
Chris Lattnerbe15beb2010-04-04 23:17:54 +00001830
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001831 // Create all the compile unit DIEs.
Devang Patel78ab9e22009-07-30 18:56:46 +00001832 for (DebugInfoFinder::iterator I = DbgFinder.compile_unit_begin(),
1833 E = DbgFinder.compile_unit_end(); I != E; ++I)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001834 constructCompileUnit(*I);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001835
Devang Patel53bb5c92009-11-10 23:06:00 +00001836 // Create DIEs for each subprogram.
Devang Patel78ab9e22009-07-30 18:56:46 +00001837 for (DebugInfoFinder::iterator I = DbgFinder.subprogram_begin(),
1838 E = DbgFinder.subprogram_end(); I != E; ++I)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001839 constructSubprogramDIE(*I);
Devang Patel13e16b62009-06-26 01:49:18 +00001840
Devang Patelc366f832009-12-10 19:14:49 +00001841 // Create DIEs for each global variable.
1842 for (DebugInfoFinder::iterator I = DbgFinder.global_variable_begin(),
1843 E = DbgFinder.global_variable_end(); I != E; ++I)
1844 constructGlobalVariableDIE(*I);
1845
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001846 // Prime section data.
Chris Lattnerf0144122009-07-28 03:13:23 +00001847 SectionMap.insert(Asm->getObjFileLowering().getTextSection());
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001848
1849 // Print out .file directives to specify files for .loc directives. These are
1850 // printed out early so that they precede any .loc directives.
Chris Lattnerd38fee82010-04-05 00:13:49 +00001851 if (Asm->MAI->hasDotLocAndDotFile()) {
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001852 for (unsigned i = 1, e = getNumSourceIds()+1; i != e; ++i) {
1853 // Remember source id starts at 1.
1854 std::pair<unsigned, unsigned> Id = getSourceDirectoryAndFileIds(i);
Chris Lattner0ad9c912010-01-22 22:09:00 +00001855 // FIXME: don't use sys::path for this! This should not depend on the
1856 // host.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001857 sys::Path FullPath(getSourceDirectoryName(Id.first));
1858 bool AppendOk =
1859 FullPath.appendComponent(getSourceFileName(Id.second));
1860 assert(AppendOk && "Could not append filename to directory!");
1861 AppendOk = false;
Chris Lattnera6594fc2010-01-25 18:58:59 +00001862 Asm->OutStreamer.EmitDwarfFileDirective(i, FullPath.str());
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001863 }
1864 }
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001865}
1866
Devang Patel2c4ceb12009-11-21 02:48:08 +00001867/// endModule - Emit all Dwarf sections that should come after the content.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001868///
Devang Patel2c4ceb12009-11-21 02:48:08 +00001869void DwarfDebug::endModule() {
Devang Patel6f3dc922009-10-06 00:03:14 +00001870 if (!ModuleCU)
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001871 return;
1872
Chris Lattnera909d662010-03-29 20:38:20 +00001873 TimeRegion Timer(DebugTimer);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001874
Devang Patel53bb5c92009-11-10 23:06:00 +00001875 // Attach DW_AT_inline attribute with inlined subprogram DIEs.
1876 for (SmallPtrSet<DIE *, 4>::iterator AI = InlinedSubprogramDIEs.begin(),
1877 AE = InlinedSubprogramDIEs.end(); AI != AE; ++AI) {
1878 DIE *ISP = *AI;
Devang Patel2c4ceb12009-11-21 02:48:08 +00001879 addUInt(ISP, dwarf::DW_AT_inline, 0, dwarf::DW_INL_inlined);
Devang Patel53bb5c92009-11-10 23:06:00 +00001880 }
1881
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001882 // Insert top level DIEs.
1883 for (SmallVector<DIE *, 4>::iterator TI = TopLevelDIEsVector.begin(),
1884 TE = TopLevelDIEsVector.end(); TI != TE; ++TI)
1885 ModuleCU->getCUDie()->addChild(*TI);
1886
Devang Patel622b0262010-01-19 06:19:05 +00001887 for (DenseMap<DIE *, MDNode *>::iterator CI = ContainingTypeMap.begin(),
Devang Patel5d11eb02009-12-03 19:11:07 +00001888 CE = ContainingTypeMap.end(); CI != CE; ++CI) {
1889 DIE *SPDie = CI->first;
1890 MDNode *N = dyn_cast_or_null<MDNode>(CI->second);
1891 if (!N) continue;
1892 DIE *NDie = ModuleCU->getDIE(N);
1893 if (!NDie) continue;
1894 addDIEEntry(SPDie, dwarf::DW_AT_containing_type, dwarf::DW_FORM_ref4, NDie);
Devang Patelf8b72ca2010-01-15 00:26:31 +00001895 // FIXME - This is not the correct approach.
Chris Lattner1d65ba72010-03-31 06:06:37 +00001896 //addDIEEntry(NDie, dwarf::DW_AT_containing_type, dwarf::DW_FORM_ref4, NDie
Devang Patel5d11eb02009-12-03 19:11:07 +00001897 }
1898
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001899 // Standard sections final addresses.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00001900 Asm->OutStreamer.SwitchSection(Asm->getObjFileLowering().getTextSection());
Chris Lattnerc0215722010-04-04 19:25:43 +00001901 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("text_end"));
Chris Lattner6c2f9e12009-08-19 05:49:37 +00001902 Asm->OutStreamer.SwitchSection(Asm->getObjFileLowering().getDataSection());
Chris Lattnerc0215722010-04-04 19:25:43 +00001903 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("data_end"));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001904
1905 // End text sections.
1906 for (unsigned i = 1, N = SectionMap.size(); i <= N; ++i) {
Chris Lattner6c2f9e12009-08-19 05:49:37 +00001907 Asm->OutStreamer.SwitchSection(SectionMap[i]);
Chris Lattnerc0215722010-04-04 19:25:43 +00001908 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("section_end", i));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001909 }
1910
1911 // Emit common frame information.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001912 emitCommonDebugFrame();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001913
1914 // Emit function debug frame information
1915 for (std::vector<FunctionDebugFrameInfo>::iterator I = DebugFrames.begin(),
1916 E = DebugFrames.end(); I != E; ++I)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001917 emitFunctionDebugFrame(*I);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001918
1919 // Compute DIE offsets and sizes.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001920 computeSizeAndOffsets();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001921
1922 // Emit all the DIEs into a debug info section
Devang Patel2c4ceb12009-11-21 02:48:08 +00001923 emitDebugInfo();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001924
1925 // Corresponding abbreviations into a abbrev section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001926 emitAbbreviations();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001927
1928 // Emit source line correspondence into a debug line section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001929 emitDebugLines();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001930
1931 // Emit info into a debug pubnames section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001932 emitDebugPubNames();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001933
Devang Patel193f7202009-11-24 01:14:22 +00001934 // Emit info into a debug pubtypes section.
1935 emitDebugPubTypes();
1936
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001937 // Emit info into a debug loc section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001938 emitDebugLoc();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001939
1940 // Emit info into a debug aranges section.
1941 EmitDebugARanges();
1942
1943 // Emit info into a debug ranges section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001944 emitDebugRanges();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001945
1946 // Emit info into a debug macinfo section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001947 emitDebugMacInfo();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001948
1949 // Emit inline info.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001950 emitDebugInlineInfo();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001951
Chris Lattnerbc733f52010-03-13 02:17:42 +00001952 // Emit info into a debug str section.
1953 emitDebugStr();
1954
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +00001955 delete ModuleCU;
1956 ModuleCU = NULL; // Reset for the next Module, if any.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001957}
1958
Devang Patel53bb5c92009-11-10 23:06:00 +00001959/// findAbstractVariable - Find abstract variable, if any, associated with Var.
Jim Grosbach7ab38df2009-11-22 19:20:36 +00001960DbgVariable *DwarfDebug::findAbstractVariable(DIVariable &Var,
1961 unsigned FrameIdx,
Chris Lattnerde4845c2010-04-02 19:42:39 +00001962 DebugLoc ScopeLoc) {
Devang Patel53bb5c92009-11-10 23:06:00 +00001963
1964 DbgVariable *AbsDbgVariable = AbstractVariables.lookup(Var.getNode());
1965 if (AbsDbgVariable)
1966 return AbsDbgVariable;
1967
Chris Lattnerde4845c2010-04-02 19:42:39 +00001968 LLVMContext &Ctx = Var.getNode()->getContext();
1969 DbgScope *Scope = AbstractScopes.lookup(ScopeLoc.getScope(Ctx));
Devang Patel53bb5c92009-11-10 23:06:00 +00001970 if (!Scope)
1971 return NULL;
1972
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00001973 AbsDbgVariable = new DbgVariable(Var, FrameIdx,
1974 NULL /* No more-abstract variable*/);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001975 Scope->addVariable(AbsDbgVariable);
Devang Patel53bb5c92009-11-10 23:06:00 +00001976 AbstractVariables[Var.getNode()] = AbsDbgVariable;
1977 return AbsDbgVariable;
1978}
1979
Devang Patel90a48ad2010-03-15 18:33:46 +00001980/// findAbstractVariable - Find abstract variable, if any, associated with Var.
1981/// FIXME : Refactor findAbstractVariable.
1982DbgVariable *DwarfDebug::findAbstractVariable(DIVariable &Var,
1983 const MachineInstr *MI,
Chris Lattnerde4845c2010-04-02 19:42:39 +00001984 DebugLoc ScopeLoc) {
Devang Patel90a48ad2010-03-15 18:33:46 +00001985
1986 DbgVariable *AbsDbgVariable = AbstractVariables.lookup(Var.getNode());
1987 if (AbsDbgVariable)
1988 return AbsDbgVariable;
1989
Chris Lattnerde4845c2010-04-02 19:42:39 +00001990 LLVMContext &Ctx = Var.getNode()->getContext();
1991 DbgScope *Scope = AbstractScopes.lookup(ScopeLoc.getScope(Ctx));
Devang Patel90a48ad2010-03-15 18:33:46 +00001992 if (!Scope)
1993 return NULL;
1994
Devang Patelaead63c2010-03-29 22:59:58 +00001995 AbsDbgVariable = new DbgVariable(Var, MI,
Devang Patel90a48ad2010-03-15 18:33:46 +00001996 NULL /* No more-abstract variable*/);
1997 Scope->addVariable(AbsDbgVariable);
1998 AbstractVariables[Var.getNode()] = AbsDbgVariable;
Devang Patelaead63c2010-03-29 22:59:58 +00001999 DbgValueStartMap[MI] = AbsDbgVariable;
Devang Patel90a48ad2010-03-15 18:33:46 +00002000 return AbsDbgVariable;
2001}
2002
Devang Patel2c4ceb12009-11-21 02:48:08 +00002003/// collectVariableInfo - Populate DbgScope entries with variables' info.
2004void DwarfDebug::collectVariableInfo() {
Chris Lattnerd38fee82010-04-05 00:13:49 +00002005 const LLVMContext &Ctx = Asm->MF->getFunction()->getContext();
Chris Lattnerde4845c2010-04-02 19:42:39 +00002006
Devang Patele717faa2009-10-06 01:26:37 +00002007 MachineModuleInfo::VariableDbgInfoMapTy &VMap = MMI->getVariableDbgInfo();
2008 for (MachineModuleInfo::VariableDbgInfoMapTy::iterator VI = VMap.begin(),
2009 VE = VMap.end(); VI != VE; ++VI) {
Devang Patelbc5201f2010-01-22 22:52:10 +00002010 MDNode *Var = VI->first;
Devang Patel53bb5c92009-11-10 23:06:00 +00002011 if (!Var) continue;
Chris Lattnerde4845c2010-04-02 19:42:39 +00002012 DIVariable DV(Var);
2013 const std::pair<unsigned, DebugLoc> &VP = VI->second;
Devang Patel53bb5c92009-11-10 23:06:00 +00002014
Chris Lattnerde4845c2010-04-02 19:42:39 +00002015 DbgScope *Scope = 0;
2016 if (MDNode *IA = VP.second.getInlinedAt(Ctx))
2017 Scope = ConcreteScopes.lookup(IA);
2018 if (Scope == 0)
2019 Scope = DbgScopeMap.lookup(VP.second.getScope(Ctx));
2020
Devang Patelfb0ee432009-11-10 23:20:04 +00002021 // If variable scope is not found then skip this variable.
Chris Lattnerde4845c2010-04-02 19:42:39 +00002022 if (Scope == 0)
Devang Patelfb0ee432009-11-10 23:20:04 +00002023 continue;
Devang Patel53bb5c92009-11-10 23:06:00 +00002024
Chris Lattnerde4845c2010-04-02 19:42:39 +00002025 DbgVariable *AbsDbgVariable = findAbstractVariable(DV, VP.first, VP.second);
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002026 DbgVariable *RegVar = new DbgVariable(DV, VP.first, AbsDbgVariable);
Devang Patel2c4ceb12009-11-21 02:48:08 +00002027 Scope->addVariable(RegVar);
Devang Patele717faa2009-10-06 01:26:37 +00002028 }
Devang Patel90a48ad2010-03-15 18:33:46 +00002029
2030 // Collect variable information from DBG_VALUE machine instructions;
Chris Lattnerd38fee82010-04-05 00:13:49 +00002031 for (MachineFunction::const_iterator I = Asm->MF->begin(), E = Asm->MF->end();
Devang Patel90a48ad2010-03-15 18:33:46 +00002032 I != E; ++I) {
2033 for (MachineBasicBlock::const_iterator II = I->begin(), IE = I->end();
2034 II != IE; ++II) {
2035 const MachineInstr *MInsn = II;
Chris Lattner14d750d2010-03-31 05:39:57 +00002036 if (!MInsn->isDebugValue())
Devang Patel90a48ad2010-03-15 18:33:46 +00002037 continue;
Devang Patelaead63c2010-03-29 22:59:58 +00002038
Devang Patel90a48ad2010-03-15 18:33:46 +00002039 // FIXME : Lift this restriction.
2040 if (MInsn->getNumOperands() != 3)
2041 continue;
Chris Lattner870cfcf2010-03-31 03:34:40 +00002042 DIVariable DV((MDNode*)(MInsn->getOperand(MInsn->getNumOperands()
2043 - 1).getMetadata()));
Devang Patel90a48ad2010-03-15 18:33:46 +00002044 if (DV.getTag() == dwarf::DW_TAG_arg_variable) {
2045 // FIXME Handle inlined subroutine arguments.
2046 DbgVariable *ArgVar = new DbgVariable(DV, MInsn, NULL);
2047 CurrentFnDbgScope->addVariable(ArgVar);
Devang Patelaead63c2010-03-29 22:59:58 +00002048 DbgValueStartMap[MInsn] = ArgVar;
Devang Patel90a48ad2010-03-15 18:33:46 +00002049 continue;
2050 }
2051
2052 DebugLoc DL = MInsn->getDebugLoc();
2053 if (DL.isUnknown()) continue;
Chris Lattnerde4845c2010-04-02 19:42:39 +00002054 DbgScope *Scope = 0;
2055 if (MDNode *IA = DL.getInlinedAt(Ctx))
2056 Scope = ConcreteScopes.lookup(IA);
2057 if (Scope == 0)
2058 Scope = DbgScopeMap.lookup(DL.getScope(Ctx));
2059
Devang Patel90a48ad2010-03-15 18:33:46 +00002060 // If variable scope is not found then skip this variable.
Chris Lattnerde4845c2010-04-02 19:42:39 +00002061 if (Scope == 0)
Devang Patel90a48ad2010-03-15 18:33:46 +00002062 continue;
2063
Chris Lattnerde4845c2010-04-02 19:42:39 +00002064 DbgVariable *AbsDbgVariable = findAbstractVariable(DV, MInsn, DL);
Devang Patel90a48ad2010-03-15 18:33:46 +00002065 DbgVariable *RegVar = new DbgVariable(DV, MInsn, AbsDbgVariable);
Devang Patelaead63c2010-03-29 22:59:58 +00002066 DbgValueStartMap[MInsn] = RegVar;
Devang Patel90a48ad2010-03-15 18:33:46 +00002067 Scope->addVariable(RegVar);
2068 }
2069 }
Devang Patele717faa2009-10-06 01:26:37 +00002070}
2071
Devang Patel553881b2010-03-29 17:20:31 +00002072/// beginScope - Process beginning of a scope.
2073void DwarfDebug::beginScope(const MachineInstr *MI) {
Devang Patel553881b2010-03-29 17:20:31 +00002074 // Check location.
2075 DebugLoc DL = MI->getDebugLoc();
2076 if (DL.isUnknown())
2077 return;
Devang Patel553881b2010-03-29 17:20:31 +00002078
2079 // Check and update last known location info.
Chris Lattnerde4845c2010-04-02 19:42:39 +00002080 if (DL == PrevInstLoc)
2081 return;
2082
Chris Lattnerd38fee82010-04-05 00:13:49 +00002083 MDNode *Scope = DL.getScope(Asm->MF->getFunction()->getContext());
Chris Lattnerde4845c2010-04-02 19:42:39 +00002084
2085 // FIXME: Should only verify each scope once!
2086 if (!DIScope(Scope).Verify())
Devang Patel553881b2010-03-29 17:20:31 +00002087 return;
Devang Patel553881b2010-03-29 17:20:31 +00002088
Devang Patelaead63c2010-03-29 22:59:58 +00002089 // DBG_VALUE instruction establishes new value.
Chris Lattner14d750d2010-03-31 05:39:57 +00002090 if (MI->isDebugValue()) {
Devang Patelaead63c2010-03-29 22:59:58 +00002091 DenseMap<const MachineInstr *, DbgVariable *>::iterator DI
2092 = DbgValueStartMap.find(MI);
2093 if (DI != DbgValueStartMap.end()) {
Chris Lattnerde4845c2010-04-02 19:42:39 +00002094 MCSymbol *Label = recordSourceLine(DL.getLine(), DL.getCol(), Scope);
2095 PrevInstLoc = DL;
Devang Patelaead63c2010-03-29 22:59:58 +00002096 DI->second->setDbgValueLabel(Label);
2097 }
Devang Patel7ed63112010-03-30 18:07:00 +00002098 return;
Devang Patelaead63c2010-03-29 22:59:58 +00002099 }
2100
Devang Patel553881b2010-03-29 17:20:31 +00002101 // Emit a label to indicate location change. This is used for line
2102 // table even if this instruction does start a new scope.
Chris Lattnerde4845c2010-04-02 19:42:39 +00002103 MCSymbol *Label = recordSourceLine(DL.getLine(), DL.getCol(), Scope);
2104 PrevInstLoc = DL;
Devang Patel553881b2010-03-29 17:20:31 +00002105
2106 // update DbgScope if this instruction starts a new scope.
Devang Patel0d20ac82009-10-06 01:50:42 +00002107 InsnToDbgScopeMapTy::iterator I = DbgScopeBeginMap.find(MI);
2108 if (I == DbgScopeBeginMap.end())
2109 return;
Devang Patel553881b2010-03-29 17:20:31 +00002110
Dan Gohman277207e2009-11-23 21:30:55 +00002111 ScopeVector &SD = I->second;
Devang Patel53bb5c92009-11-10 23:06:00 +00002112 for (ScopeVector::iterator SDI = SD.begin(), SDE = SD.end();
Jim Grosbach31ef40e2009-11-21 23:12:12 +00002113 SDI != SDE; ++SDI)
Chris Lattnerc6087842010-03-09 04:54:43 +00002114 (*SDI)->setStartLabel(Label);
Devang Patel0d20ac82009-10-06 01:50:42 +00002115}
2116
Devang Patel2c4ceb12009-11-21 02:48:08 +00002117/// endScope - Process end of a scope.
2118void DwarfDebug::endScope(const MachineInstr *MI) {
Devang Patel553881b2010-03-29 17:20:31 +00002119 // Ignore DBG_VALUE instruction.
Chris Lattner14d750d2010-03-31 05:39:57 +00002120 if (MI->isDebugValue())
Devang Patel553881b2010-03-29 17:20:31 +00002121 return;
2122
2123 // Check location.
2124 DebugLoc DL = MI->getDebugLoc();
2125 if (DL.isUnknown())
2126 return;
Chris Lattnerde4845c2010-04-02 19:42:39 +00002127
Devang Patel553881b2010-03-29 17:20:31 +00002128 // Emit a label and update DbgScope if this instruction ends a scope.
Devang Patel0d20ac82009-10-06 01:50:42 +00002129 InsnToDbgScopeMapTy::iterator I = DbgScopeEndMap.find(MI);
Devang Patel8a4087d2009-10-06 03:15:38 +00002130 if (I == DbgScopeEndMap.end())
Devang Patel0d20ac82009-10-06 01:50:42 +00002131 return;
Chris Lattnerde4845c2010-04-02 19:42:39 +00002132
Chris Lattner63d78362010-03-14 08:36:50 +00002133 MCSymbol *Label = MMI->getContext().CreateTempSymbol();
Chris Lattnerb7db7332010-03-09 01:58:53 +00002134 Asm->OutStreamer.EmitLabel(Label);
Devang Patel53bb5c92009-11-10 23:06:00 +00002135
Chris Lattnerb7db7332010-03-09 01:58:53 +00002136 SmallVector<DbgScope*, 2> &SD = I->second;
Devang Patel0d20ac82009-10-06 01:50:42 +00002137 for (SmallVector<DbgScope *, 2>::iterator SDI = SD.begin(), SDE = SD.end();
Jim Grosbach31ef40e2009-11-21 23:12:12 +00002138 SDI != SDE; ++SDI)
Chris Lattnerb7db7332010-03-09 01:58:53 +00002139 (*SDI)->setEndLabel(Label);
Devang Patel53bb5c92009-11-10 23:06:00 +00002140 return;
2141}
2142
2143/// createDbgScope - Create DbgScope for the scope.
2144void DwarfDebug::createDbgScope(MDNode *Scope, MDNode *InlinedAt) {
Devang Patel53bb5c92009-11-10 23:06:00 +00002145 if (!InlinedAt) {
2146 DbgScope *WScope = DbgScopeMap.lookup(Scope);
2147 if (WScope)
2148 return;
2149 WScope = new DbgScope(NULL, DIDescriptor(Scope), NULL);
2150 DbgScopeMap.insert(std::make_pair(Scope, WScope));
Jim Grosbach31ef40e2009-11-21 23:12:12 +00002151 if (DIDescriptor(Scope).isLexicalBlock())
Devang Patel2f105c62009-11-11 00:18:40 +00002152 createDbgScope(DILexicalBlock(Scope).getContext().getNode(), NULL);
Devang Patel53bb5c92009-11-10 23:06:00 +00002153 return;
2154 }
2155
2156 DbgScope *WScope = DbgScopeMap.lookup(InlinedAt);
2157 if (WScope)
2158 return;
2159
2160 WScope = new DbgScope(NULL, DIDescriptor(Scope), InlinedAt);
2161 DbgScopeMap.insert(std::make_pair(InlinedAt, WScope));
2162 DILocation DL(InlinedAt);
2163 createDbgScope(DL.getScope().getNode(), DL.getOrigLocation().getNode());
Devang Patel0d20ac82009-10-06 01:50:42 +00002164}
2165
Devang Patel2c4ceb12009-11-21 02:48:08 +00002166/// extractScopeInformation - Scan machine instructions in this function
Chris Lattner14d750d2010-03-31 05:39:57 +00002167/// and collect DbgScopes. Return true, if at least one scope was found.
Chris Lattnereec791a2010-01-26 23:18:02 +00002168bool DwarfDebug::extractScopeInformation() {
Devang Patelaf9e8472009-10-01 20:31:14 +00002169 // If scope information was extracted using .dbg intrinsics then there is not
2170 // any need to extract these information by scanning each instruction.
2171 if (!DbgScopeMap.empty())
2172 return false;
2173
Devang Patel344130e2010-01-04 20:44:00 +00002174 DenseMap<const MachineInstr *, unsigned> MIIndexMap;
2175 unsigned MIIndex = 0;
Chris Lattnerd38fee82010-04-05 00:13:49 +00002176 LLVMContext &Ctx = Asm->MF->getFunction()->getContext();
Chris Lattnerde4845c2010-04-02 19:42:39 +00002177
Devang Patel53bb5c92009-11-10 23:06:00 +00002178 // Scan each instruction and create scopes. First build working set of scopes.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002179 for (MachineFunction::const_iterator I = Asm->MF->begin(), E = Asm->MF->end();
Devang Patelaf9e8472009-10-01 20:31:14 +00002180 I != E; ++I) {
2181 for (MachineBasicBlock::const_iterator II = I->begin(), IE = I->end();
2182 II != IE; ++II) {
2183 const MachineInstr *MInsn = II;
Devang Patel90a48ad2010-03-15 18:33:46 +00002184 // FIXME : Remove DBG_VALUE check.
Chris Lattner14d750d2010-03-31 05:39:57 +00002185 if (MInsn->isDebugValue()) continue;
Devang Patel344130e2010-01-04 20:44:00 +00002186 MIIndexMap[MInsn] = MIIndex++;
Chris Lattnerde4845c2010-04-02 19:42:39 +00002187
Devang Patelaf9e8472009-10-01 20:31:14 +00002188 DebugLoc DL = MInsn->getDebugLoc();
Devang Patel53bb5c92009-11-10 23:06:00 +00002189 if (DL.isUnknown()) continue;
Chris Lattnerde4845c2010-04-02 19:42:39 +00002190
2191 MDNode *Scope = DL.getScope(Ctx);
2192
Devang Patelaf9e8472009-10-01 20:31:14 +00002193 // There is no need to create another DIE for compile unit. For all
Jim Grosbach31ef40e2009-11-21 23:12:12 +00002194 // other scopes, create one DbgScope now. This will be translated
Devang Patelaf9e8472009-10-01 20:31:14 +00002195 // into a scope DIE at the end.
Chris Lattnerde4845c2010-04-02 19:42:39 +00002196 if (DIScope(Scope).isCompileUnit()) continue;
2197 createDbgScope(Scope, DL.getInlinedAt(Ctx));
Devang Patel53bb5c92009-11-10 23:06:00 +00002198 }
2199 }
2200
Devang Patelc8e77642010-04-01 22:47:29 +00002201
Devang Patel53bb5c92009-11-10 23:06:00 +00002202 // Build scope hierarchy using working set of scopes.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002203 for (MachineFunction::const_iterator I = Asm->MF->begin(), E = Asm->MF->end();
Devang Patel53bb5c92009-11-10 23:06:00 +00002204 I != E; ++I) {
2205 for (MachineBasicBlock::const_iterator II = I->begin(), IE = I->end();
2206 II != IE; ++II) {
2207 const MachineInstr *MInsn = II;
Devang Patel90a48ad2010-03-15 18:33:46 +00002208 // FIXME : Remove DBG_VALUE check.
Chris Lattner14d750d2010-03-31 05:39:57 +00002209 if (MInsn->isDebugValue()) continue;
Devang Patel53bb5c92009-11-10 23:06:00 +00002210 DebugLoc DL = MInsn->getDebugLoc();
Chris Lattnerde4845c2010-04-02 19:42:39 +00002211 if (DL.isUnknown()) continue;
2212
2213 MDNode *Scope = DL.getScope(Ctx);
2214 if (Scope == 0) continue;
2215
Devang Patel53bb5c92009-11-10 23:06:00 +00002216 // There is no need to create another DIE for compile unit. For all
Jim Grosbach31ef40e2009-11-21 23:12:12 +00002217 // other scopes, create one DbgScope now. This will be translated
Devang Patel53bb5c92009-11-10 23:06:00 +00002218 // into a scope DIE at the end.
Chris Lattnerde4845c2010-04-02 19:42:39 +00002219 if (DIScope(Scope).isCompileUnit()) continue;
2220 DbgScope *DScope = getUpdatedDbgScope(Scope, MInsn, DL.getInlinedAt(Ctx));
2221 DScope->setLastInsn(MInsn);
Devang Patelaf9e8472009-10-01 20:31:14 +00002222 }
2223 }
2224
Devang Patel344130e2010-01-04 20:44:00 +00002225 if (!CurrentFnDbgScope)
2226 return false;
2227
2228 CurrentFnDbgScope->fixInstructionMarkers(MIIndexMap);
Devang Patelaf9e8472009-10-01 20:31:14 +00002229
2230 // Each scope has first instruction and last instruction to mark beginning
2231 // and end of a scope respectively. Create an inverse map that list scopes
2232 // starts (and ends) with an instruction. One instruction may start (or end)
Devang Patel42aafd72010-01-20 02:05:23 +00002233 // multiple scopes. Ignore scopes that are not reachable.
2234 SmallVector<DbgScope *, 4> WorkList;
2235 WorkList.push_back(CurrentFnDbgScope);
2236 while (!WorkList.empty()) {
Chris Lattner14d750d2010-03-31 05:39:57 +00002237 DbgScope *S = WorkList.pop_back_val();
Devang Patel42aafd72010-01-20 02:05:23 +00002238
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002239 const SmallVector<DbgScope *, 4> &Children = S->getScopes();
Devang Patel42aafd72010-01-20 02:05:23 +00002240 if (!Children.empty())
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002241 for (SmallVector<DbgScope *, 4>::const_iterator SI = Children.begin(),
Devang Patel42aafd72010-01-20 02:05:23 +00002242 SE = Children.end(); SI != SE; ++SI)
2243 WorkList.push_back(*SI);
2244
Devang Patel53bb5c92009-11-10 23:06:00 +00002245 if (S->isAbstractScope())
2246 continue;
Devang Patelaf9e8472009-10-01 20:31:14 +00002247 const MachineInstr *MI = S->getFirstInsn();
Chris Lattnered7a77b2010-03-31 05:36:29 +00002248 assert(MI && "DbgScope does not have first instruction!");
Devang Patelaf9e8472009-10-01 20:31:14 +00002249
2250 InsnToDbgScopeMapTy::iterator IDI = DbgScopeBeginMap.find(MI);
2251 if (IDI != DbgScopeBeginMap.end())
2252 IDI->second.push_back(S);
2253 else
Devang Patel53bb5c92009-11-10 23:06:00 +00002254 DbgScopeBeginMap[MI].push_back(S);
Devang Patelaf9e8472009-10-01 20:31:14 +00002255
2256 MI = S->getLastInsn();
Chris Lattnered7a77b2010-03-31 05:36:29 +00002257 assert(MI && "DbgScope does not have last instruction!");
Devang Patelaf9e8472009-10-01 20:31:14 +00002258 IDI = DbgScopeEndMap.find(MI);
2259 if (IDI != DbgScopeEndMap.end())
2260 IDI->second.push_back(S);
2261 else
Devang Patel53bb5c92009-11-10 23:06:00 +00002262 DbgScopeEndMap[MI].push_back(S);
Devang Patelaf9e8472009-10-01 20:31:14 +00002263 }
2264
2265 return !DbgScopeMap.empty();
2266}
2267
Devang Patel2c4ceb12009-11-21 02:48:08 +00002268/// beginFunction - Gather pre-function debug information. Assumes being
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002269/// emitted immediately after the function entry point.
Chris Lattnereec791a2010-01-26 23:18:02 +00002270void DwarfDebug::beginFunction(const MachineFunction *MF) {
Chris Lattner994cb122010-04-05 03:52:55 +00002271 if (!MMI->hasDebugInfo()) return;
Chris Lattnerd38fee82010-04-05 00:13:49 +00002272
2273 TimeRegion Timer(DebugTimer);
Chris Lattnereec791a2010-01-26 23:18:02 +00002274 if (!extractScopeInformation())
Devang Patel60b35bd2009-10-06 18:37:31 +00002275 return;
Chris Lattnera909d662010-03-29 20:38:20 +00002276
Devang Patel2c4ceb12009-11-21 02:48:08 +00002277 collectVariableInfo();
Devang Patel60b35bd2009-10-06 18:37:31 +00002278
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002279 // Assumes in correct section after the entry point.
Chris Lattnerc0215722010-04-04 19:25:43 +00002280 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("func_begin",
Chris Lattnerd38fee82010-04-05 00:13:49 +00002281 Asm->getFunctionNumber()));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002282
2283 // Emit label for the implicitly defined dbg.stoppoint at the start of the
2284 // function.
Devang Patelac1ceb32009-10-09 22:42:28 +00002285 DebugLoc FDL = MF->getDefaultDebugLoc();
Chris Lattnerde4845c2010-04-02 19:42:39 +00002286 if (FDL.isUnknown()) return;
2287
2288 MDNode *Scope = FDL.getScope(MF->getFunction()->getContext());
2289
2290 DISubprogram SP = getDISubprogram(Scope);
2291 unsigned Line, Col;
2292 if (SP.Verify()) {
2293 Line = SP.getLineNumber();
2294 Col = 0;
2295 } else {
2296 Line = FDL.getLine();
2297 Col = FDL.getCol();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002298 }
Chris Lattnerde4845c2010-04-02 19:42:39 +00002299
2300 recordSourceLine(Line, Col, Scope);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002301}
2302
Devang Patel2c4ceb12009-11-21 02:48:08 +00002303/// endFunction - Gather and emit post-function debug information.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002304///
Chris Lattnereec791a2010-01-26 23:18:02 +00002305void DwarfDebug::endFunction(const MachineFunction *MF) {
Chris Lattner74e41f92010-04-05 05:24:55 +00002306 if (!MMI->hasDebugInfo() ||
2307 DbgScopeMap.empty()) return;
Chris Lattnera909d662010-03-29 20:38:20 +00002308
2309 TimeRegion Timer(DebugTimer);
Devang Patel70d75ca2009-11-12 19:02:56 +00002310
Devang Patel344130e2010-01-04 20:44:00 +00002311 if (CurrentFnDbgScope) {
2312 // Define end label for subprogram.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002313 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("func_end",
2314 Asm->getFunctionNumber()));
Devang Patel344130e2010-01-04 20:44:00 +00002315
2316 // Get function line info.
2317 if (!Lines.empty()) {
2318 // Get section line info.
2319 unsigned ID = SectionMap.insert(Asm->getCurrentSection());
2320 if (SectionSourceLines.size() < ID) SectionSourceLines.resize(ID);
2321 std::vector<SrcLineInfo> &SectionLineInfos = SectionSourceLines[ID-1];
2322 // Append the function info to section info.
2323 SectionLineInfos.insert(SectionLineInfos.end(),
2324 Lines.begin(), Lines.end());
2325 }
2326
2327 // Construct abstract scopes.
2328 for (SmallVector<DbgScope *, 4>::iterator AI = AbstractScopesList.begin(),
2329 AE = AbstractScopesList.end(); AI != AE; ++AI)
2330 constructScopeDIE(*AI);
2331
2332 constructScopeDIE(CurrentFnDbgScope);
2333
Chris Lattnerd38fee82010-04-05 00:13:49 +00002334 DebugFrames.push_back(FunctionDebugFrameInfo(Asm->getFunctionNumber(),
Devang Patel344130e2010-01-04 20:44:00 +00002335 MMI->getFrameMoves()));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002336 }
2337
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002338 // Clear debug info
Devang Patelf54b8522010-01-19 01:26:02 +00002339 CurrentFnDbgScope = NULL;
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002340 DeleteContainerSeconds(DbgScopeMap);
Devang Patelf54b8522010-01-19 01:26:02 +00002341 DbgScopeBeginMap.clear();
2342 DbgScopeEndMap.clear();
Devang Patelaead63c2010-03-29 22:59:58 +00002343 DbgValueStartMap.clear();
Devang Patelf54b8522010-01-19 01:26:02 +00002344 ConcreteScopes.clear();
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002345 DeleteContainerSeconds(AbstractScopes);
Devang Patelf54b8522010-01-19 01:26:02 +00002346 AbstractScopesList.clear();
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002347 AbstractVariables.clear();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002348 Lines.clear();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002349}
2350
Chris Lattnerc6087842010-03-09 04:54:43 +00002351/// recordSourceLine - Register a source line with debug info. Returns the
2352/// unique label that was emitted and which provides correspondence to
2353/// the source line list.
2354MCSymbol *DwarfDebug::recordSourceLine(unsigned Line, unsigned Col, MDNode *S) {
Chris Lattnera909d662010-03-29 20:38:20 +00002355 TimeRegion Timer(DebugTimer);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002356
Devang Patel65dbc902009-11-25 17:36:49 +00002357 StringRef Dir;
2358 StringRef Fn;
Devang Patelf84548d2009-10-05 18:03:19 +00002359
2360 DIDescriptor Scope(S);
2361 if (Scope.isCompileUnit()) {
2362 DICompileUnit CU(S);
2363 Dir = CU.getDirectory();
2364 Fn = CU.getFilename();
2365 } else if (Scope.isSubprogram()) {
2366 DISubprogram SP(S);
2367 Dir = SP.getDirectory();
2368 Fn = SP.getFilename();
2369 } else if (Scope.isLexicalBlock()) {
2370 DILexicalBlock DB(S);
2371 Dir = DB.getDirectory();
2372 Fn = DB.getFilename();
2373 } else
Chris Lattner206d61e2010-03-13 07:26:18 +00002374 assert(0 && "Unexpected scope info");
Devang Patelf84548d2009-10-05 18:03:19 +00002375
2376 unsigned Src = GetOrCreateSourceID(Dir, Fn);
Chris Lattner63d78362010-03-14 08:36:50 +00002377 MCSymbol *Label = MMI->getContext().CreateTempSymbol();
Chris Lattner25b68c62010-03-14 08:15:55 +00002378 Lines.push_back(SrcLineInfo(Line, Col, Src, Label));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002379
Chris Lattnerc6087842010-03-09 04:54:43 +00002380 Asm->OutStreamer.EmitLabel(Label);
2381 return Label;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002382}
2383
2384/// getOrCreateSourceID - Public version of GetOrCreateSourceID. This can be
2385/// timed. Look up the source id with the given directory and source file
2386/// names. If none currently exists, create a new id and insert it in the
2387/// SourceIds map. This can update DirectoryNames and SourceFileNames maps as
2388/// well.
2389unsigned DwarfDebug::getOrCreateSourceID(const std::string &DirName,
2390 const std::string &FileName) {
Chris Lattnera909d662010-03-29 20:38:20 +00002391 TimeRegion Timer(DebugTimer);
2392 return GetOrCreateSourceID(DirName.c_str(), FileName.c_str());
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002393}
2394
Bill Wendling829e67b2009-05-20 23:22:40 +00002395//===----------------------------------------------------------------------===//
2396// Emit Methods
2397//===----------------------------------------------------------------------===//
2398
Devang Patel2c4ceb12009-11-21 02:48:08 +00002399/// computeSizeAndOffset - Compute the size and offset of a DIE.
Bill Wendling94d04b82009-05-20 23:21:38 +00002400///
Jim Grosbach7ab38df2009-11-22 19:20:36 +00002401unsigned
2402DwarfDebug::computeSizeAndOffset(DIE *Die, unsigned Offset, bool Last) {
Bill Wendling94d04b82009-05-20 23:21:38 +00002403 // Get the children.
2404 const std::vector<DIE *> &Children = Die->getChildren();
2405
2406 // If not last sibling and has children then add sibling offset attribute.
Jeffrey Yasskin638fe8d2010-03-22 18:47:14 +00002407 if (!Last && !Children.empty())
Benjamin Kramer345ef342010-03-31 19:34:01 +00002408 Die->addSiblingOffset(DIEValueAllocator);
Bill Wendling94d04b82009-05-20 23:21:38 +00002409
2410 // Record the abbreviation.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002411 assignAbbrevNumber(Die->getAbbrev());
Bill Wendling94d04b82009-05-20 23:21:38 +00002412
2413 // Get the abbreviation for this DIE.
2414 unsigned AbbrevNumber = Die->getAbbrevNumber();
2415 const DIEAbbrev *Abbrev = Abbreviations[AbbrevNumber - 1];
2416
2417 // Set DIE offset
2418 Die->setOffset(Offset);
2419
2420 // Start the size with the size of abbreviation code.
Chris Lattneraf76e592009-08-22 20:48:53 +00002421 Offset += MCAsmInfo::getULEB128Size(AbbrevNumber);
Bill Wendling94d04b82009-05-20 23:21:38 +00002422
2423 const SmallVector<DIEValue*, 32> &Values = Die->getValues();
2424 const SmallVector<DIEAbbrevData, 8> &AbbrevData = Abbrev->getData();
2425
2426 // Size the DIE attribute values.
2427 for (unsigned i = 0, N = Values.size(); i < N; ++i)
2428 // Size attribute value.
Chris Lattnera37d5382010-04-05 00:18:22 +00002429 Offset += Values[i]->SizeOf(Asm, AbbrevData[i].getForm());
Bill Wendling94d04b82009-05-20 23:21:38 +00002430
2431 // Size the DIE children if any.
2432 if (!Children.empty()) {
2433 assert(Abbrev->getChildrenFlag() == dwarf::DW_CHILDREN_yes &&
2434 "Children flag not set");
2435
2436 for (unsigned j = 0, M = Children.size(); j < M; ++j)
Devang Patel2c4ceb12009-11-21 02:48:08 +00002437 Offset = computeSizeAndOffset(Children[j], Offset, (j + 1) == M);
Bill Wendling94d04b82009-05-20 23:21:38 +00002438
2439 // End of children marker.
2440 Offset += sizeof(int8_t);
2441 }
2442
2443 Die->setSize(Offset - Die->getOffset());
2444 return Offset;
2445}
2446
Devang Patel2c4ceb12009-11-21 02:48:08 +00002447/// computeSizeAndOffsets - Compute the size and offset of all the DIEs.
Bill Wendling94d04b82009-05-20 23:21:38 +00002448///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002449void DwarfDebug::computeSizeAndOffsets() {
Bill Wendling94d04b82009-05-20 23:21:38 +00002450 // Compute size of compile unit header.
2451 static unsigned Offset =
2452 sizeof(int32_t) + // Length of Compilation Unit Info
2453 sizeof(int16_t) + // DWARF version number
2454 sizeof(int32_t) + // Offset Into Abbrev. Section
2455 sizeof(int8_t); // Pointer Size (in bytes)
2456
Devang Patel2c4ceb12009-11-21 02:48:08 +00002457 computeSizeAndOffset(ModuleCU->getCUDie(), Offset, true);
Devang Patel1dbc7712009-06-29 20:45:18 +00002458 CompileUnitOffsets[ModuleCU] = 0;
Bill Wendling94d04b82009-05-20 23:21:38 +00002459}
2460
Chris Lattner11b8f302010-04-04 23:02:02 +00002461/// EmitSectionSym - Switch to the specified MCSection and emit an assembler
2462/// temporary label to it if SymbolStem is specified.
Chris Lattner9c69e285532010-04-04 22:59:04 +00002463static MCSymbol *EmitSectionSym(AsmPrinter *Asm, const MCSection *Section,
Chris Lattner11b8f302010-04-04 23:02:02 +00002464 const char *SymbolStem = 0) {
Chris Lattner9c69e285532010-04-04 22:59:04 +00002465 Asm->OutStreamer.SwitchSection(Section);
Chris Lattner11b8f302010-04-04 23:02:02 +00002466 if (!SymbolStem) return 0;
2467
Chris Lattner9c69e285532010-04-04 22:59:04 +00002468 MCSymbol *TmpSym = Asm->GetTempSymbol(SymbolStem);
2469 Asm->OutStreamer.EmitLabel(TmpSym);
2470 return TmpSym;
2471}
2472
2473/// EmitSectionLabels - Emit initial Dwarf sections with a label at
2474/// the start of each one.
Chris Lattnerfa070b02010-04-04 22:33:59 +00002475void DwarfDebug::EmitSectionLabels() {
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002476 const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
Daniel Dunbarf612ff62009-09-19 20:40:05 +00002477
Bill Wendling94d04b82009-05-20 23:21:38 +00002478 // Dwarf sections base addresses.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002479 if (Asm->MAI->doesDwarfRequireFrameSection()) {
Chris Lattner9c69e285532010-04-04 22:59:04 +00002480 DwarfFrameSectionSym =
2481 EmitSectionSym(Asm, TLOF.getDwarfFrameSection(), "section_debug_frame");
2482 }
Bill Wendling94d04b82009-05-20 23:21:38 +00002483
Chris Lattner9c69e285532010-04-04 22:59:04 +00002484 DwarfInfoSectionSym =
2485 EmitSectionSym(Asm, TLOF.getDwarfInfoSection(), "section_info");
2486 DwarfAbbrevSectionSym =
2487 EmitSectionSym(Asm, TLOF.getDwarfAbbrevSection(), "section_abbrev");
Chris Lattner11b8f302010-04-04 23:02:02 +00002488 EmitSectionSym(Asm, TLOF.getDwarfARangesSection());
Chris Lattner9c69e285532010-04-04 22:59:04 +00002489
2490 if (const MCSection *MacroInfo = TLOF.getDwarfMacroInfoSection())
Chris Lattner11b8f302010-04-04 23:02:02 +00002491 EmitSectionSym(Asm, MacroInfo);
Bill Wendling94d04b82009-05-20 23:21:38 +00002492
Chris Lattner11b8f302010-04-04 23:02:02 +00002493 EmitSectionSym(Asm, TLOF.getDwarfLineSection());
2494 EmitSectionSym(Asm, TLOF.getDwarfLocSection());
2495 EmitSectionSym(Asm, TLOF.getDwarfPubNamesSection());
2496 EmitSectionSym(Asm, TLOF.getDwarfPubTypesSection());
Chris Lattner9c69e285532010-04-04 22:59:04 +00002497 DwarfStrSectionSym =
2498 EmitSectionSym(Asm, TLOF.getDwarfStrSection(), "section_str");
Chris Lattner11b8f302010-04-04 23:02:02 +00002499 EmitSectionSym(Asm, TLOF.getDwarfRangesSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002500
Chris Lattner9c69e285532010-04-04 22:59:04 +00002501 TextSectionSym = EmitSectionSym(Asm, TLOF.getTextSection(), "text_begin");
Chris Lattner4ad1efe2010-04-04 23:10:38 +00002502 EmitSectionSym(Asm, TLOF.getDataSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002503}
2504
Devang Patel2c4ceb12009-11-21 02:48:08 +00002505/// emitDIE - Recusively Emits a debug information entry.
Bill Wendling94d04b82009-05-20 23:21:38 +00002506///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002507void DwarfDebug::emitDIE(DIE *Die) {
Bill Wendling94d04b82009-05-20 23:21:38 +00002508 // Get the abbreviation for this DIE.
2509 unsigned AbbrevNumber = Die->getAbbrevNumber();
2510 const DIEAbbrev *Abbrev = Abbreviations[AbbrevNumber - 1];
2511
Bill Wendling94d04b82009-05-20 23:21:38 +00002512 // Emit the code (index) for the abbreviation.
Chris Lattner3f53c832010-04-04 18:52:31 +00002513 if (Asm->isVerbose())
Chris Lattner894d75a2010-01-22 23:18:42 +00002514 Asm->OutStreamer.AddComment("Abbrev [" + Twine(AbbrevNumber) + "] 0x" +
2515 Twine::utohexstr(Die->getOffset()) + ":0x" +
2516 Twine::utohexstr(Die->getSize()) + " " +
2517 dwarf::TagString(Abbrev->getTag()));
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002518 Asm->EmitULEB128(AbbrevNumber);
Bill Wendling94d04b82009-05-20 23:21:38 +00002519
Jeffrey Yasskin638fe8d2010-03-22 18:47:14 +00002520 const SmallVector<DIEValue*, 32> &Values = Die->getValues();
Bill Wendling94d04b82009-05-20 23:21:38 +00002521 const SmallVector<DIEAbbrevData, 8> &AbbrevData = Abbrev->getData();
2522
2523 // Emit the DIE attribute values.
2524 for (unsigned i = 0, N = Values.size(); i < N; ++i) {
2525 unsigned Attr = AbbrevData[i].getAttribute();
2526 unsigned Form = AbbrevData[i].getForm();
2527 assert(Form && "Too many attributes for DIE (check abbreviation)");
2528
Chris Lattner3f53c832010-04-04 18:52:31 +00002529 if (Asm->isVerbose())
Chris Lattnera8013622010-01-24 18:54:17 +00002530 Asm->OutStreamer.AddComment(dwarf::AttributeString(Attr));
2531
Bill Wendling94d04b82009-05-20 23:21:38 +00002532 switch (Attr) {
2533 case dwarf::DW_AT_sibling:
Devang Patel2c4ceb12009-11-21 02:48:08 +00002534 Asm->EmitInt32(Die->getSiblingOffset());
Bill Wendling94d04b82009-05-20 23:21:38 +00002535 break;
2536 case dwarf::DW_AT_abstract_origin: {
2537 DIEEntry *E = cast<DIEEntry>(Values[i]);
2538 DIE *Origin = E->getEntry();
Devang Patel53bb5c92009-11-10 23:06:00 +00002539 unsigned Addr = Origin->getOffset();
Bill Wendling94d04b82009-05-20 23:21:38 +00002540 Asm->EmitInt32(Addr);
2541 break;
2542 }
2543 default:
2544 // Emit an attribute using the defined form.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002545 Values[i]->EmitValue(Asm, Form);
Bill Wendling94d04b82009-05-20 23:21:38 +00002546 break;
2547 }
Bill Wendling94d04b82009-05-20 23:21:38 +00002548 }
2549
2550 // Emit the DIE children if any.
2551 if (Abbrev->getChildrenFlag() == dwarf::DW_CHILDREN_yes) {
2552 const std::vector<DIE *> &Children = Die->getChildren();
2553
2554 for (unsigned j = 0, M = Children.size(); j < M; ++j)
Devang Patel2c4ceb12009-11-21 02:48:08 +00002555 emitDIE(Children[j]);
Bill Wendling94d04b82009-05-20 23:21:38 +00002556
Chris Lattner3f53c832010-04-04 18:52:31 +00002557 if (Asm->isVerbose())
Chris Lattner233f52b2010-03-09 23:52:58 +00002558 Asm->OutStreamer.AddComment("End Of Children Mark");
2559 Asm->EmitInt8(0);
Bill Wendling94d04b82009-05-20 23:21:38 +00002560 }
2561}
2562
Devang Patel8a241142009-12-09 18:24:21 +00002563/// emitDebugInfo - Emit the debug info section.
Bill Wendling94d04b82009-05-20 23:21:38 +00002564///
Devang Patel8a241142009-12-09 18:24:21 +00002565void DwarfDebug::emitDebugInfo() {
2566 // Start debug info section.
2567 Asm->OutStreamer.SwitchSection(
2568 Asm->getObjFileLowering().getDwarfInfoSection());
2569 DIE *Die = ModuleCU->getCUDie();
Bill Wendling94d04b82009-05-20 23:21:38 +00002570
2571 // Emit the compile units header.
Chris Lattnerc0215722010-04-04 19:25:43 +00002572 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("info_begin",
2573 ModuleCU->getID()));
Bill Wendling94d04b82009-05-20 23:21:38 +00002574
2575 // Emit size of content not including length itself
2576 unsigned ContentSize = Die->getSize() +
2577 sizeof(int16_t) + // DWARF version number
2578 sizeof(int32_t) + // Offset Into Abbrev. Section
2579 sizeof(int8_t) + // Pointer Size (in bytes)
2580 sizeof(int32_t); // FIXME - extra pad for gdb bug.
2581
Chris Lattner233f52b2010-03-09 23:52:58 +00002582 Asm->OutStreamer.AddComment("Length of Compilation Unit Info");
2583 Asm->EmitInt32(ContentSize);
2584 Asm->OutStreamer.AddComment("DWARF version number");
2585 Asm->EmitInt16(dwarf::DWARF_VERSION);
2586 Asm->OutStreamer.AddComment("Offset Into Abbrev. Section");
Chris Lattner6189ed12010-04-04 23:25:33 +00002587 Asm->EmitSectionOffset(Asm->GetTempSymbol("abbrev_begin"),
2588 DwarfAbbrevSectionSym);
Chris Lattner233f52b2010-03-09 23:52:58 +00002589 Asm->OutStreamer.AddComment("Address Size (in bytes)");
Chris Lattnerd38fee82010-04-05 00:13:49 +00002590 Asm->EmitInt8(Asm->getTargetData().getPointerSize());
Bill Wendling94d04b82009-05-20 23:21:38 +00002591
Devang Patel2c4ceb12009-11-21 02:48:08 +00002592 emitDIE(Die);
Bill Wendling94d04b82009-05-20 23:21:38 +00002593 // FIXME - extra padding for gdb bug.
Chris Lattner233f52b2010-03-09 23:52:58 +00002594 Asm->OutStreamer.AddComment("4 extra padding bytes for GDB");
2595 Asm->EmitInt8(0);
2596 Asm->EmitInt8(0);
2597 Asm->EmitInt8(0);
2598 Asm->EmitInt8(0);
Chris Lattnerc0215722010-04-04 19:25:43 +00002599 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("info_end", ModuleCU->getID()));
Bill Wendling94d04b82009-05-20 23:21:38 +00002600}
2601
Devang Patel2c4ceb12009-11-21 02:48:08 +00002602/// emitAbbreviations - Emit the abbreviation section.
Bill Wendling94d04b82009-05-20 23:21:38 +00002603///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002604void DwarfDebug::emitAbbreviations() const {
Bill Wendling94d04b82009-05-20 23:21:38 +00002605 // Check to see if it is worth the effort.
2606 if (!Abbreviations.empty()) {
2607 // Start the debug abbrev section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002608 Asm->OutStreamer.SwitchSection(
2609 Asm->getObjFileLowering().getDwarfAbbrevSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002610
Chris Lattnerc0215722010-04-04 19:25:43 +00002611 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("abbrev_begin"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002612
2613 // For each abbrevation.
2614 for (unsigned i = 0, N = Abbreviations.size(); i < N; ++i) {
2615 // Get abbreviation data
2616 const DIEAbbrev *Abbrev = Abbreviations[i];
2617
2618 // Emit the abbrevations code (base 1 index.)
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002619 Asm->EmitULEB128(Abbrev->getNumber(), "Abbreviation Code");
Bill Wendling94d04b82009-05-20 23:21:38 +00002620
2621 // Emit the abbreviations data.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002622 Abbrev->Emit(Asm);
Bill Wendling94d04b82009-05-20 23:21:38 +00002623 }
2624
2625 // Mark end of abbreviations.
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002626 Asm->EmitULEB128(0, "EOM(3)");
Bill Wendling94d04b82009-05-20 23:21:38 +00002627
Chris Lattnerc0215722010-04-04 19:25:43 +00002628 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("abbrev_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002629 }
2630}
2631
Devang Patel2c4ceb12009-11-21 02:48:08 +00002632/// emitEndOfLineMatrix - Emit the last address of the section and the end of
Bill Wendling94d04b82009-05-20 23:21:38 +00002633/// the line matrix.
2634///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002635void DwarfDebug::emitEndOfLineMatrix(unsigned SectionEnd) {
Bill Wendling94d04b82009-05-20 23:21:38 +00002636 // Define last address of section.
Chris Lattner233f52b2010-03-09 23:52:58 +00002637 Asm->OutStreamer.AddComment("Extended Op");
2638 Asm->EmitInt8(0);
2639
2640 Asm->OutStreamer.AddComment("Op size");
Chris Lattnerd38fee82010-04-05 00:13:49 +00002641 Asm->EmitInt8(Asm->getTargetData().getPointerSize() + 1);
Chris Lattner233f52b2010-03-09 23:52:58 +00002642 Asm->OutStreamer.AddComment("DW_LNE_set_address");
2643 Asm->EmitInt8(dwarf::DW_LNE_set_address);
2644
2645 Asm->OutStreamer.AddComment("Section end label");
Chris Lattnerd85fc6e2010-03-10 01:17:49 +00002646
Chris Lattnerc0215722010-04-04 19:25:43 +00002647 Asm->OutStreamer.EmitSymbolValue(Asm->GetTempSymbol("section_end",SectionEnd),
Chris Lattnerd38fee82010-04-05 00:13:49 +00002648 Asm->getTargetData().getPointerSize(),
2649 0/*AddrSpace*/);
Bill Wendling94d04b82009-05-20 23:21:38 +00002650
2651 // Mark end of matrix.
Chris Lattner233f52b2010-03-09 23:52:58 +00002652 Asm->OutStreamer.AddComment("DW_LNE_end_sequence");
2653 Asm->EmitInt8(0);
Chris Lattner0ad9c912010-01-22 22:09:00 +00002654 Asm->EmitInt8(1);
Chris Lattner894d75a2010-01-22 23:18:42 +00002655 Asm->EmitInt8(1);
Bill Wendling94d04b82009-05-20 23:21:38 +00002656}
2657
Devang Patel2c4ceb12009-11-21 02:48:08 +00002658/// emitDebugLines - Emit source line information.
Bill Wendling94d04b82009-05-20 23:21:38 +00002659///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002660void DwarfDebug::emitDebugLines() {
Bill Wendling94d04b82009-05-20 23:21:38 +00002661 // If the target is using .loc/.file, the assembler will be emitting the
2662 // .debug_line table automatically.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002663 if (Asm->MAI->hasDotLocAndDotFile())
Bill Wendling94d04b82009-05-20 23:21:38 +00002664 return;
2665
2666 // Minimum line delta, thus ranging from -10..(255-10).
2667 const int MinLineDelta = -(dwarf::DW_LNS_fixed_advance_pc + 1);
2668 // Maximum line delta, thus ranging from -10..(255-10).
2669 const int MaxLineDelta = 255 + MinLineDelta;
2670
2671 // Start the dwarf line section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002672 Asm->OutStreamer.SwitchSection(
2673 Asm->getObjFileLowering().getDwarfLineSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002674
2675 // Construct the section header.
Chris Lattner233f52b2010-03-09 23:52:58 +00002676 Asm->OutStreamer.AddComment("Length of Source Line Info");
Chris Lattnera6437182010-04-04 19:58:12 +00002677 Asm->EmitLabelDifference(Asm->GetTempSymbol("line_end"),
2678 Asm->GetTempSymbol("line_begin"), 4);
Chris Lattnerc0215722010-04-04 19:25:43 +00002679 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_begin"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002680
Chris Lattner233f52b2010-03-09 23:52:58 +00002681 Asm->OutStreamer.AddComment("DWARF version number");
2682 Asm->EmitInt16(dwarf::DWARF_VERSION);
Bill Wendling94d04b82009-05-20 23:21:38 +00002683
Chris Lattner233f52b2010-03-09 23:52:58 +00002684 Asm->OutStreamer.AddComment("Prolog Length");
Chris Lattnera6437182010-04-04 19:58:12 +00002685 Asm->EmitLabelDifference(Asm->GetTempSymbol("line_prolog_end"),
2686 Asm->GetTempSymbol("line_prolog_begin"), 4);
Chris Lattnerc0215722010-04-04 19:25:43 +00002687 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_prolog_begin"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002688
Chris Lattner233f52b2010-03-09 23:52:58 +00002689 Asm->OutStreamer.AddComment("Minimum Instruction Length");
2690 Asm->EmitInt8(1);
2691 Asm->OutStreamer.AddComment("Default is_stmt_start flag");
2692 Asm->EmitInt8(1);
2693 Asm->OutStreamer.AddComment("Line Base Value (Special Opcodes)");
2694 Asm->EmitInt8(MinLineDelta);
2695 Asm->OutStreamer.AddComment("Line Range Value (Special Opcodes)");
2696 Asm->EmitInt8(MaxLineDelta);
2697 Asm->OutStreamer.AddComment("Special Opcode Base");
2698 Asm->EmitInt8(-MinLineDelta);
Bill Wendling94d04b82009-05-20 23:21:38 +00002699
2700 // Line number standard opcode encodings argument count
Chris Lattner233f52b2010-03-09 23:52:58 +00002701 Asm->OutStreamer.AddComment("DW_LNS_copy arg count");
2702 Asm->EmitInt8(0);
2703 Asm->OutStreamer.AddComment("DW_LNS_advance_pc arg count");
2704 Asm->EmitInt8(1);
2705 Asm->OutStreamer.AddComment("DW_LNS_advance_line arg count");
2706 Asm->EmitInt8(1);
2707 Asm->OutStreamer.AddComment("DW_LNS_set_file arg count");
2708 Asm->EmitInt8(1);
2709 Asm->OutStreamer.AddComment("DW_LNS_set_column arg count");
2710 Asm->EmitInt8(1);
2711 Asm->OutStreamer.AddComment("DW_LNS_negate_stmt arg count");
2712 Asm->EmitInt8(0);
2713 Asm->OutStreamer.AddComment("DW_LNS_set_basic_block arg count");
2714 Asm->EmitInt8(0);
2715 Asm->OutStreamer.AddComment("DW_LNS_const_add_pc arg count");
2716 Asm->EmitInt8(0);
2717 Asm->OutStreamer.AddComment("DW_LNS_fixed_advance_pc arg count");
2718 Asm->EmitInt8(1);
Bill Wendling94d04b82009-05-20 23:21:38 +00002719
2720 // Emit directories.
2721 for (unsigned DI = 1, DE = getNumSourceDirectories()+1; DI != DE; ++DI) {
Chris Lattner4cf202b2010-01-23 03:11:46 +00002722 const std::string &Dir = getSourceDirectoryName(DI);
Chris Lattner3f53c832010-04-04 18:52:31 +00002723 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("Directory");
Chris Lattner4cf202b2010-01-23 03:11:46 +00002724 Asm->OutStreamer.EmitBytes(StringRef(Dir.c_str(), Dir.size()+1), 0);
Bill Wendling94d04b82009-05-20 23:21:38 +00002725 }
2726
Chris Lattner233f52b2010-03-09 23:52:58 +00002727 Asm->OutStreamer.AddComment("End of directories");
2728 Asm->EmitInt8(0);
Bill Wendling94d04b82009-05-20 23:21:38 +00002729
2730 // Emit files.
2731 for (unsigned SI = 1, SE = getNumSourceIds()+1; SI != SE; ++SI) {
2732 // Remember source id starts at 1.
2733 std::pair<unsigned, unsigned> Id = getSourceDirectoryAndFileIds(SI);
Chris Lattner4cf202b2010-01-23 03:11:46 +00002734 const std::string &FN = getSourceFileName(Id.second);
Chris Lattner3f53c832010-04-04 18:52:31 +00002735 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("Source");
Chris Lattner4cf202b2010-01-23 03:11:46 +00002736 Asm->OutStreamer.EmitBytes(StringRef(FN.c_str(), FN.size()+1), 0);
2737
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002738 Asm->EmitULEB128(Id.first, "Directory #");
2739 Asm->EmitULEB128(0, "Mod date");
2740 Asm->EmitULEB128(0, "File size");
Bill Wendling94d04b82009-05-20 23:21:38 +00002741 }
2742
Chris Lattner233f52b2010-03-09 23:52:58 +00002743 Asm->OutStreamer.AddComment("End of files");
2744 Asm->EmitInt8(0);
Bill Wendling94d04b82009-05-20 23:21:38 +00002745
Chris Lattnerc0215722010-04-04 19:25:43 +00002746 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_prolog_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002747
2748 // A sequence for each text section.
2749 unsigned SecSrcLinesSize = SectionSourceLines.size();
2750
2751 for (unsigned j = 0; j < SecSrcLinesSize; ++j) {
2752 // Isolate current sections line info.
2753 const std::vector<SrcLineInfo> &LineInfos = SectionSourceLines[j];
2754
Bill Wendling94d04b82009-05-20 23:21:38 +00002755 // Dwarf assumes we start with first line of first source file.
2756 unsigned Source = 1;
2757 unsigned Line = 1;
2758
2759 // Construct rows of the address, source, line, column matrix.
2760 for (unsigned i = 0, N = LineInfos.size(); i < N; ++i) {
2761 const SrcLineInfo &LineInfo = LineInfos[i];
Chris Lattner25b68c62010-03-14 08:15:55 +00002762 MCSymbol *Label = LineInfo.getLabel();
Chris Lattnerb9130602010-03-14 02:20:58 +00002763 if (!Label->isDefined()) continue; // Not emitted, in dead code.
Bill Wendling94d04b82009-05-20 23:21:38 +00002764
Caroline Ticec6f9d622009-09-11 18:25:54 +00002765 if (LineInfo.getLine() == 0) continue;
2766
Chris Lattner0d9d70f2010-03-09 23:38:23 +00002767 if (Asm->isVerbose()) {
Chris Lattner188a87d2010-03-10 01:04:13 +00002768 std::pair<unsigned, unsigned> SrcID =
Bill Wendling94d04b82009-05-20 23:21:38 +00002769 getSourceDirectoryAndFileIds(LineInfo.getSourceID());
Chris Lattner188a87d2010-03-10 01:04:13 +00002770 Asm->OutStreamer.AddComment(Twine(getSourceDirectoryName(SrcID.first)) +
Chris Lattner49f618a2010-03-10 02:29:31 +00002771 "/" +
2772 Twine(getSourceFileName(SrcID.second)) +
Chris Lattner188a87d2010-03-10 01:04:13 +00002773 ":" + Twine(LineInfo.getLine()));
Bill Wendling94d04b82009-05-20 23:21:38 +00002774 }
2775
2776 // Define the line address.
Chris Lattner233f52b2010-03-09 23:52:58 +00002777 Asm->OutStreamer.AddComment("Extended Op");
2778 Asm->EmitInt8(0);
2779 Asm->OutStreamer.AddComment("Op size");
Chris Lattnerd38fee82010-04-05 00:13:49 +00002780 Asm->EmitInt8(Asm->getTargetData().getPointerSize() + 1);
Chris Lattner233f52b2010-03-09 23:52:58 +00002781
2782 Asm->OutStreamer.AddComment("DW_LNE_set_address");
2783 Asm->EmitInt8(dwarf::DW_LNE_set_address);
2784
2785 Asm->OutStreamer.AddComment("Location label");
Chris Lattnerd38fee82010-04-05 00:13:49 +00002786 Asm->OutStreamer.EmitSymbolValue(Label,
2787 Asm->getTargetData().getPointerSize(),
Chris Lattnerb9130602010-03-14 02:20:58 +00002788 0/*AddrSpace*/);
Chris Lattnerd85fc6e2010-03-10 01:17:49 +00002789
Bill Wendling94d04b82009-05-20 23:21:38 +00002790 // If change of source, then switch to the new source.
2791 if (Source != LineInfo.getSourceID()) {
2792 Source = LineInfo.getSourceID();
Chris Lattner233f52b2010-03-09 23:52:58 +00002793 Asm->OutStreamer.AddComment("DW_LNS_set_file");
2794 Asm->EmitInt8(dwarf::DW_LNS_set_file);
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002795 Asm->EmitULEB128(Source, "New Source");
Bill Wendling94d04b82009-05-20 23:21:38 +00002796 }
2797
2798 // If change of line.
2799 if (Line != LineInfo.getLine()) {
2800 // Determine offset.
2801 int Offset = LineInfo.getLine() - Line;
2802 int Delta = Offset - MinLineDelta;
2803
2804 // Update line.
2805 Line = LineInfo.getLine();
2806
2807 // If delta is small enough and in range...
2808 if (Delta >= 0 && Delta < (MaxLineDelta - 1)) {
2809 // ... then use fast opcode.
Chris Lattner233f52b2010-03-09 23:52:58 +00002810 Asm->OutStreamer.AddComment("Line Delta");
2811 Asm->EmitInt8(Delta - MinLineDelta);
Bill Wendling94d04b82009-05-20 23:21:38 +00002812 } else {
2813 // ... otherwise use long hand.
Chris Lattner233f52b2010-03-09 23:52:58 +00002814 Asm->OutStreamer.AddComment("DW_LNS_advance_line");
Bill Wendling94d04b82009-05-20 23:21:38 +00002815 Asm->EmitInt8(dwarf::DW_LNS_advance_line);
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002816 Asm->EmitSLEB128(Offset, "Line Offset");
Chris Lattner233f52b2010-03-09 23:52:58 +00002817 Asm->OutStreamer.AddComment("DW_LNS_copy");
2818 Asm->EmitInt8(dwarf::DW_LNS_copy);
Bill Wendling94d04b82009-05-20 23:21:38 +00002819 }
2820 } else {
2821 // Copy the previous row (different address or source)
Chris Lattner233f52b2010-03-09 23:52:58 +00002822 Asm->OutStreamer.AddComment("DW_LNS_copy");
2823 Asm->EmitInt8(dwarf::DW_LNS_copy);
Bill Wendling94d04b82009-05-20 23:21:38 +00002824 }
2825 }
2826
Devang Patel2c4ceb12009-11-21 02:48:08 +00002827 emitEndOfLineMatrix(j + 1);
Bill Wendling94d04b82009-05-20 23:21:38 +00002828 }
2829
2830 if (SecSrcLinesSize == 0)
2831 // Because we're emitting a debug_line section, we still need a line
2832 // table. The linker and friends expect it to exist. If there's nothing to
2833 // put into it, emit an empty table.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002834 emitEndOfLineMatrix(1);
Bill Wendling94d04b82009-05-20 23:21:38 +00002835
Chris Lattnerc0215722010-04-04 19:25:43 +00002836 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002837}
2838
Devang Patel2c4ceb12009-11-21 02:48:08 +00002839/// emitCommonDebugFrame - Emit common frame info into a debug frame section.
Bill Wendling94d04b82009-05-20 23:21:38 +00002840///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002841void DwarfDebug::emitCommonDebugFrame() {
Chris Lattnerd38fee82010-04-05 00:13:49 +00002842 if (!Asm->MAI->doesDwarfRequireFrameSection())
Bill Wendling94d04b82009-05-20 23:21:38 +00002843 return;
2844
Chris Lattnerd38fee82010-04-05 00:13:49 +00002845 int stackGrowth = Asm->getTargetData().getPointerSize();
2846 if (Asm->TM.getFrameInfo()->getStackGrowthDirection() ==
2847 TargetFrameInfo::StackGrowsDown)
2848 stackGrowth *= -1;
Bill Wendling94d04b82009-05-20 23:21:38 +00002849
2850 // Start the dwarf frame section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002851 Asm->OutStreamer.SwitchSection(
2852 Asm->getObjFileLowering().getDwarfFrameSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002853
Chris Lattnerc0215722010-04-04 19:25:43 +00002854 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_frame_common"));
Chris Lattner233f52b2010-03-09 23:52:58 +00002855 Asm->OutStreamer.AddComment("Length of Common Information Entry");
Chris Lattnera6437182010-04-04 19:58:12 +00002856 Asm->EmitLabelDifference(Asm->GetTempSymbol("debug_frame_common_end"),
2857 Asm->GetTempSymbol("debug_frame_common_begin"), 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00002858
Chris Lattnerc0215722010-04-04 19:25:43 +00002859 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_frame_common_begin"));
Chris Lattner233f52b2010-03-09 23:52:58 +00002860 Asm->OutStreamer.AddComment("CIE Identifier Tag");
Bill Wendling94d04b82009-05-20 23:21:38 +00002861 Asm->EmitInt32((int)dwarf::DW_CIE_ID);
Chris Lattner233f52b2010-03-09 23:52:58 +00002862 Asm->OutStreamer.AddComment("CIE Version");
Bill Wendling94d04b82009-05-20 23:21:38 +00002863 Asm->EmitInt8(dwarf::DW_CIE_VERSION);
Chris Lattner233f52b2010-03-09 23:52:58 +00002864 Asm->OutStreamer.AddComment("CIE Augmentation");
Chris Lattner4cf202b2010-01-23 03:11:46 +00002865 Asm->OutStreamer.EmitIntValue(0, 1, /*addrspace*/0); // nul terminator.
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002866 Asm->EmitULEB128(1, "CIE Code Alignment Factor");
2867 Asm->EmitSLEB128(stackGrowth, "CIE Data Alignment Factor");
Chris Lattner233f52b2010-03-09 23:52:58 +00002868 Asm->OutStreamer.AddComment("CIE RA Column");
Chris Lattnerd38fee82010-04-05 00:13:49 +00002869 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Bill Wendling94d04b82009-05-20 23:21:38 +00002870 Asm->EmitInt8(RI->getDwarfRegNum(RI->getRARegister(), false));
Bill Wendling94d04b82009-05-20 23:21:38 +00002871
2872 std::vector<MachineMove> Moves;
2873 RI->getInitialFrameState(Moves);
2874
Chris Lattner02b86b92010-04-04 23:41:46 +00002875 Asm->EmitFrameMoves(Moves, 0, false);
Bill Wendling94d04b82009-05-20 23:21:38 +00002876
2877 Asm->EmitAlignment(2, 0, 0, false);
Chris Lattnerc0215722010-04-04 19:25:43 +00002878 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_frame_common_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002879}
2880
Devang Patel2c4ceb12009-11-21 02:48:08 +00002881/// emitFunctionDebugFrame - Emit per function frame info into a debug frame
Bill Wendling94d04b82009-05-20 23:21:38 +00002882/// section.
Chris Lattner206d61e2010-03-13 07:26:18 +00002883void DwarfDebug::
2884emitFunctionDebugFrame(const FunctionDebugFrameInfo &DebugFrameInfo) {
Chris Lattnerd38fee82010-04-05 00:13:49 +00002885 if (!Asm->MAI->doesDwarfRequireFrameSection())
Bill Wendling94d04b82009-05-20 23:21:38 +00002886 return;
2887
2888 // Start the dwarf frame section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002889 Asm->OutStreamer.SwitchSection(
2890 Asm->getObjFileLowering().getDwarfFrameSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002891
Chris Lattner233f52b2010-03-09 23:52:58 +00002892 Asm->OutStreamer.AddComment("Length of Frame Information Entry");
Chris Lattner206d61e2010-03-13 07:26:18 +00002893 MCSymbol *DebugFrameBegin =
Chris Lattnerc0215722010-04-04 19:25:43 +00002894 Asm->GetTempSymbol("debug_frame_begin", DebugFrameInfo.Number);
Chris Lattner206d61e2010-03-13 07:26:18 +00002895 MCSymbol *DebugFrameEnd =
Chris Lattnerc0215722010-04-04 19:25:43 +00002896 Asm->GetTempSymbol("debug_frame_end", DebugFrameInfo.Number);
Chris Lattnera6437182010-04-04 19:58:12 +00002897 Asm->EmitLabelDifference(DebugFrameEnd, DebugFrameBegin, 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00002898
Chris Lattner206d61e2010-03-13 07:26:18 +00002899 Asm->OutStreamer.EmitLabel(DebugFrameBegin);
Bill Wendling94d04b82009-05-20 23:21:38 +00002900
Chris Lattner233f52b2010-03-09 23:52:58 +00002901 Asm->OutStreamer.AddComment("FDE CIE offset");
Chris Lattner6189ed12010-04-04 23:25:33 +00002902 Asm->EmitSectionOffset(Asm->GetTempSymbol("debug_frame_common"),
2903 DwarfFrameSectionSym);
Bill Wendling94d04b82009-05-20 23:21:38 +00002904
Chris Lattner233f52b2010-03-09 23:52:58 +00002905 Asm->OutStreamer.AddComment("FDE initial location");
Chris Lattnerc0215722010-04-04 19:25:43 +00002906 MCSymbol *FuncBeginSym =
2907 Asm->GetTempSymbol("func_begin", DebugFrameInfo.Number);
Chris Lattnerfb658072010-03-13 07:40:56 +00002908 Asm->OutStreamer.EmitSymbolValue(FuncBeginSym,
Chris Lattnerd38fee82010-04-05 00:13:49 +00002909 Asm->getTargetData().getPointerSize(),
2910 0/*AddrSpace*/);
Chris Lattnerd85fc6e2010-03-10 01:17:49 +00002911
2912
Chris Lattner233f52b2010-03-09 23:52:58 +00002913 Asm->OutStreamer.AddComment("FDE address range");
Chris Lattnera6437182010-04-04 19:58:12 +00002914 Asm->EmitLabelDifference(Asm->GetTempSymbol("func_end",DebugFrameInfo.Number),
Chris Lattnerd38fee82010-04-05 00:13:49 +00002915 FuncBeginSym, Asm->getTargetData().getPointerSize());
Bill Wendling94d04b82009-05-20 23:21:38 +00002916
Chris Lattner02b86b92010-04-04 23:41:46 +00002917 Asm->EmitFrameMoves(DebugFrameInfo.Moves, FuncBeginSym, false);
Bill Wendling94d04b82009-05-20 23:21:38 +00002918
2919 Asm->EmitAlignment(2, 0, 0, false);
Chris Lattner206d61e2010-03-13 07:26:18 +00002920 Asm->OutStreamer.EmitLabel(DebugFrameEnd);
Bill Wendling94d04b82009-05-20 23:21:38 +00002921}
2922
Devang Patel8a241142009-12-09 18:24:21 +00002923/// emitDebugPubNames - Emit visible names into a debug pubnames section.
2924///
2925void DwarfDebug::emitDebugPubNames() {
2926 // Start the dwarf pubnames section.
2927 Asm->OutStreamer.SwitchSection(
2928 Asm->getObjFileLowering().getDwarfPubNamesSection());
2929
Chris Lattner233f52b2010-03-09 23:52:58 +00002930 Asm->OutStreamer.AddComment("Length of Public Names Info");
Chris Lattnera6437182010-04-04 19:58:12 +00002931 Asm->EmitLabelDifference(
2932 Asm->GetTempSymbol("pubnames_end", ModuleCU->getID()),
2933 Asm->GetTempSymbol("pubnames_begin", ModuleCU->getID()), 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00002934
Chris Lattnerc0215722010-04-04 19:25:43 +00002935 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubnames_begin",
2936 ModuleCU->getID()));
Bill Wendling94d04b82009-05-20 23:21:38 +00002937
Chris Lattner233f52b2010-03-09 23:52:58 +00002938 Asm->OutStreamer.AddComment("DWARF Version");
2939 Asm->EmitInt16(dwarf::DWARF_VERSION);
Bill Wendling94d04b82009-05-20 23:21:38 +00002940
Chris Lattner233f52b2010-03-09 23:52:58 +00002941 Asm->OutStreamer.AddComment("Offset of Compilation Unit Info");
Chris Lattner6189ed12010-04-04 23:25:33 +00002942 Asm->EmitSectionOffset(Asm->GetTempSymbol("info_begin", ModuleCU->getID()),
2943 DwarfInfoSectionSym);
Bill Wendling94d04b82009-05-20 23:21:38 +00002944
Chris Lattner233f52b2010-03-09 23:52:58 +00002945 Asm->OutStreamer.AddComment("Compilation Unit Length");
Chris Lattnera6437182010-04-04 19:58:12 +00002946 Asm->EmitLabelDifference(Asm->GetTempSymbol("info_end", ModuleCU->getID()),
2947 Asm->GetTempSymbol("info_begin", ModuleCU->getID()),
2948 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00002949
Devang Patel8a241142009-12-09 18:24:21 +00002950 const StringMap<DIE*> &Globals = ModuleCU->getGlobals();
Bill Wendling94d04b82009-05-20 23:21:38 +00002951 for (StringMap<DIE*>::const_iterator
2952 GI = Globals.begin(), GE = Globals.end(); GI != GE; ++GI) {
2953 const char *Name = GI->getKeyData();
Chris Lattner233f52b2010-03-09 23:52:58 +00002954 DIE *Entity = GI->second;
Bill Wendling94d04b82009-05-20 23:21:38 +00002955
Chris Lattner233f52b2010-03-09 23:52:58 +00002956 Asm->OutStreamer.AddComment("DIE offset");
2957 Asm->EmitInt32(Entity->getOffset());
Chris Lattner4cf202b2010-01-23 03:11:46 +00002958
Chris Lattner3f53c832010-04-04 18:52:31 +00002959 if (Asm->isVerbose())
Chris Lattner4cf202b2010-01-23 03:11:46 +00002960 Asm->OutStreamer.AddComment("External Name");
2961 Asm->OutStreamer.EmitBytes(StringRef(Name, strlen(Name)+1), 0);
Bill Wendling94d04b82009-05-20 23:21:38 +00002962 }
2963
Chris Lattner233f52b2010-03-09 23:52:58 +00002964 Asm->OutStreamer.AddComment("End Mark");
2965 Asm->EmitInt32(0);
Chris Lattnerc0215722010-04-04 19:25:43 +00002966 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubnames_end",
2967 ModuleCU->getID()));
Bill Wendling94d04b82009-05-20 23:21:38 +00002968}
2969
Devang Patel193f7202009-11-24 01:14:22 +00002970void DwarfDebug::emitDebugPubTypes() {
Devang Patelf3a03762009-11-24 19:18:41 +00002971 // Start the dwarf pubnames section.
2972 Asm->OutStreamer.SwitchSection(
2973 Asm->getObjFileLowering().getDwarfPubTypesSection());
Chris Lattner233f52b2010-03-09 23:52:58 +00002974 Asm->OutStreamer.AddComment("Length of Public Types Info");
Chris Lattnera6437182010-04-04 19:58:12 +00002975 Asm->EmitLabelDifference(
2976 Asm->GetTempSymbol("pubtypes_end", ModuleCU->getID()),
2977 Asm->GetTempSymbol("pubtypes_begin", ModuleCU->getID()), 4);
Devang Patel193f7202009-11-24 01:14:22 +00002978
Chris Lattnerc0215722010-04-04 19:25:43 +00002979 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubtypes_begin",
2980 ModuleCU->getID()));
Devang Patel193f7202009-11-24 01:14:22 +00002981
Chris Lattner3f53c832010-04-04 18:52:31 +00002982 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("DWARF Version");
Devang Patele3d6d222010-02-02 03:47:27 +00002983 Asm->EmitInt16(dwarf::DWARF_VERSION);
Devang Patel193f7202009-11-24 01:14:22 +00002984
Chris Lattner233f52b2010-03-09 23:52:58 +00002985 Asm->OutStreamer.AddComment("Offset of Compilation ModuleCU Info");
Chris Lattner6189ed12010-04-04 23:25:33 +00002986 Asm->EmitSectionOffset(Asm->GetTempSymbol("info_begin", ModuleCU->getID()),
2987 DwarfInfoSectionSym);
Devang Patel193f7202009-11-24 01:14:22 +00002988
Chris Lattner233f52b2010-03-09 23:52:58 +00002989 Asm->OutStreamer.AddComment("Compilation ModuleCU Length");
Chris Lattnera6437182010-04-04 19:58:12 +00002990 Asm->EmitLabelDifference(Asm->GetTempSymbol("info_end", ModuleCU->getID()),
2991 Asm->GetTempSymbol("info_begin", ModuleCU->getID()),
2992 4);
Devang Patel193f7202009-11-24 01:14:22 +00002993
2994 const StringMap<DIE*> &Globals = ModuleCU->getGlobalTypes();
2995 for (StringMap<DIE*>::const_iterator
2996 GI = Globals.begin(), GE = Globals.end(); GI != GE; ++GI) {
2997 const char *Name = GI->getKeyData();
2998 DIE * Entity = GI->second;
2999
Chris Lattner3f53c832010-04-04 18:52:31 +00003000 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("DIE offset");
Devang Patele3d6d222010-02-02 03:47:27 +00003001 Asm->EmitInt32(Entity->getOffset());
Chris Lattner4cf202b2010-01-23 03:11:46 +00003002
Chris Lattner3f53c832010-04-04 18:52:31 +00003003 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("External Name");
Devang Patel31acb892010-02-02 03:37:03 +00003004 Asm->OutStreamer.EmitBytes(StringRef(Name, GI->getKeyLength()+1), 0);
Devang Patel193f7202009-11-24 01:14:22 +00003005 }
3006
Chris Lattner233f52b2010-03-09 23:52:58 +00003007 Asm->OutStreamer.AddComment("End Mark");
3008 Asm->EmitInt32(0);
Chris Lattnerc0215722010-04-04 19:25:43 +00003009 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubtypes_end",
3010 ModuleCU->getID()));
Devang Patel193f7202009-11-24 01:14:22 +00003011}
3012
Devang Patel2c4ceb12009-11-21 02:48:08 +00003013/// emitDebugStr - Emit visible names into a debug str section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003014///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003015void DwarfDebug::emitDebugStr() {
Bill Wendling94d04b82009-05-20 23:21:38 +00003016 // Check to see if it is worth the effort.
Chris Lattner0d9d70f2010-03-09 23:38:23 +00003017 if (StringPool.empty()) return;
3018
3019 // Start the dwarf str section.
3020 Asm->OutStreamer.SwitchSection(
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003021 Asm->getObjFileLowering().getDwarfStrSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003022
Chris Lattnerbc733f52010-03-13 02:17:42 +00003023 // Get all of the string pool entries and put them in an array by their ID so
3024 // we can sort them.
3025 SmallVector<std::pair<unsigned,
3026 StringMapEntry<std::pair<MCSymbol*, unsigned> >*>, 64> Entries;
3027
3028 for (StringMap<std::pair<MCSymbol*, unsigned> >::iterator
3029 I = StringPool.begin(), E = StringPool.end(); I != E; ++I)
3030 Entries.push_back(std::make_pair(I->second.second, &*I));
3031
3032 array_pod_sort(Entries.begin(), Entries.end());
3033
3034 for (unsigned i = 0, e = Entries.size(); i != e; ++i) {
Chris Lattner0d9d70f2010-03-09 23:38:23 +00003035 // Emit a label for reference from debug information entries.
Chris Lattnerbc733f52010-03-13 02:17:42 +00003036 Asm->OutStreamer.EmitLabel(Entries[i].second->getValue().first);
Chris Lattner0d9d70f2010-03-09 23:38:23 +00003037
3038 // Emit the string itself.
Chris Lattnerbc733f52010-03-13 02:17:42 +00003039 Asm->OutStreamer.EmitBytes(Entries[i].second->getKey(), 0/*addrspace*/);
Bill Wendling94d04b82009-05-20 23:21:38 +00003040 }
3041}
3042
Devang Patel2c4ceb12009-11-21 02:48:08 +00003043/// emitDebugLoc - Emit visible names into a debug loc section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003044///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003045void DwarfDebug::emitDebugLoc() {
Bill Wendling94d04b82009-05-20 23:21:38 +00003046 // Start the dwarf loc section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003047 Asm->OutStreamer.SwitchSection(
3048 Asm->getObjFileLowering().getDwarfLocSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003049}
3050
3051/// EmitDebugARanges - Emit visible names into a debug aranges section.
3052///
3053void DwarfDebug::EmitDebugARanges() {
3054 // Start the dwarf aranges section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003055 Asm->OutStreamer.SwitchSection(
3056 Asm->getObjFileLowering().getDwarfARangesSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003057}
3058
Devang Patel2c4ceb12009-11-21 02:48:08 +00003059/// emitDebugRanges - Emit visible names into a debug ranges section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003060///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003061void DwarfDebug::emitDebugRanges() {
Bill Wendling94d04b82009-05-20 23:21:38 +00003062 // Start the dwarf ranges section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003063 Asm->OutStreamer.SwitchSection(
3064 Asm->getObjFileLowering().getDwarfRangesSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003065}
3066
Devang Patel2c4ceb12009-11-21 02:48:08 +00003067/// emitDebugMacInfo - Emit visible names into a debug macinfo section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003068///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003069void DwarfDebug::emitDebugMacInfo() {
Daniel Dunbarf612ff62009-09-19 20:40:05 +00003070 if (const MCSection *LineInfo =
Chris Lattner18a4c162009-08-02 07:24:22 +00003071 Asm->getObjFileLowering().getDwarfMacroInfoSection()) {
Bill Wendling94d04b82009-05-20 23:21:38 +00003072 // Start the dwarf macinfo section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003073 Asm->OutStreamer.SwitchSection(LineInfo);
Bill Wendling94d04b82009-05-20 23:21:38 +00003074 }
3075}
3076
Devang Patel2c4ceb12009-11-21 02:48:08 +00003077/// emitDebugInlineInfo - Emit inline info using following format.
Bill Wendling94d04b82009-05-20 23:21:38 +00003078/// Section Header:
3079/// 1. length of section
3080/// 2. Dwarf version number
3081/// 3. address size.
3082///
3083/// Entries (one "entry" for each function that was inlined):
3084///
3085/// 1. offset into __debug_str section for MIPS linkage name, if exists;
3086/// otherwise offset into __debug_str for regular function name.
3087/// 2. offset into __debug_str section for regular function name.
3088/// 3. an unsigned LEB128 number indicating the number of distinct inlining
3089/// instances for the function.
3090///
3091/// The rest of the entry consists of a {die_offset, low_pc} pair for each
3092/// inlined instance; the die_offset points to the inlined_subroutine die in the
3093/// __debug_info section, and the low_pc is the starting address for the
3094/// inlining instance.
Devang Patel2c4ceb12009-11-21 02:48:08 +00003095void DwarfDebug::emitDebugInlineInfo() {
Chris Lattnerd38fee82010-04-05 00:13:49 +00003096 if (!Asm->MAI->doesDwarfUsesInlineInfoSection())
Bill Wendling94d04b82009-05-20 23:21:38 +00003097 return;
3098
Devang Patel1dbc7712009-06-29 20:45:18 +00003099 if (!ModuleCU)
Bill Wendling94d04b82009-05-20 23:21:38 +00003100 return;
3101
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003102 Asm->OutStreamer.SwitchSection(
3103 Asm->getObjFileLowering().getDwarfDebugInlineSection());
Chris Lattner0ad9c912010-01-22 22:09:00 +00003104
Chris Lattner233f52b2010-03-09 23:52:58 +00003105 Asm->OutStreamer.AddComment("Length of Debug Inlined Information Entry");
Chris Lattnera6437182010-04-04 19:58:12 +00003106 Asm->EmitLabelDifference(Asm->GetTempSymbol("debug_inlined_end", 1),
3107 Asm->GetTempSymbol("debug_inlined_begin", 1), 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00003108
Chris Lattnerc0215722010-04-04 19:25:43 +00003109 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_inlined_begin", 1));
Bill Wendling94d04b82009-05-20 23:21:38 +00003110
Chris Lattner233f52b2010-03-09 23:52:58 +00003111 Asm->OutStreamer.AddComment("Dwarf Version");
3112 Asm->EmitInt16(dwarf::DWARF_VERSION);
3113 Asm->OutStreamer.AddComment("Address Size (in bytes)");
Chris Lattnerd38fee82010-04-05 00:13:49 +00003114 Asm->EmitInt8(Asm->getTargetData().getPointerSize());
Bill Wendling94d04b82009-05-20 23:21:38 +00003115
Devang Patel53bb5c92009-11-10 23:06:00 +00003116 for (SmallVector<MDNode *, 4>::iterator I = InlinedSPNodes.begin(),
3117 E = InlinedSPNodes.end(); I != E; ++I) {
Jim Grosbach31ef40e2009-11-21 23:12:12 +00003118
Devang Patel53bb5c92009-11-10 23:06:00 +00003119 MDNode *Node = *I;
Devang Patel622b0262010-01-19 06:19:05 +00003120 DenseMap<MDNode *, SmallVector<InlineInfoLabels, 4> >::iterator II
Jim Grosbach7ab38df2009-11-22 19:20:36 +00003121 = InlineInfo.find(Node);
Devang Patel53bb5c92009-11-10 23:06:00 +00003122 SmallVector<InlineInfoLabels, 4> &Labels = II->second;
Devang Patele4b27562009-08-28 23:24:31 +00003123 DISubprogram SP(Node);
Devang Patel65dbc902009-11-25 17:36:49 +00003124 StringRef LName = SP.getLinkageName();
3125 StringRef Name = SP.getName();
Bill Wendling94d04b82009-05-20 23:21:38 +00003126
Chris Lattner233f52b2010-03-09 23:52:58 +00003127 Asm->OutStreamer.AddComment("MIPS linkage name");
Chris Lattner4cf202b2010-01-23 03:11:46 +00003128 if (LName.empty()) {
3129 Asm->OutStreamer.EmitBytes(Name, 0);
3130 Asm->OutStreamer.EmitIntValue(0, 1, 0); // nul terminator.
3131 } else
Chris Lattner6189ed12010-04-04 23:25:33 +00003132 Asm->EmitSectionOffset(getStringPoolEntry(getRealLinkageName(LName)),
3133 DwarfStrSectionSym);
Devang Patel53bb5c92009-11-10 23:06:00 +00003134
Chris Lattner233f52b2010-03-09 23:52:58 +00003135 Asm->OutStreamer.AddComment("Function name");
Chris Lattner6189ed12010-04-04 23:25:33 +00003136 Asm->EmitSectionOffset(getStringPoolEntry(Name), DwarfStrSectionSym);
Chris Lattner7e1a8f82010-04-04 19:09:29 +00003137 Asm->EmitULEB128(Labels.size(), "Inline count");
Bill Wendling94d04b82009-05-20 23:21:38 +00003138
Devang Patel53bb5c92009-11-10 23:06:00 +00003139 for (SmallVector<InlineInfoLabels, 4>::iterator LI = Labels.begin(),
Bill Wendling94d04b82009-05-20 23:21:38 +00003140 LE = Labels.end(); LI != LE; ++LI) {
Chris Lattner3f53c832010-04-04 18:52:31 +00003141 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("DIE offset");
Chris Lattner6ed0f902010-03-09 00:31:02 +00003142 Asm->EmitInt32(LI->second->getOffset());
Bill Wendling94d04b82009-05-20 23:21:38 +00003143
Chris Lattner3f53c832010-04-04 18:52:31 +00003144 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("low_pc");
Chris Lattnerd38fee82010-04-05 00:13:49 +00003145 Asm->OutStreamer.EmitSymbolValue(LI->first,
3146 Asm->getTargetData().getPointerSize(),0);
Bill Wendling94d04b82009-05-20 23:21:38 +00003147 }
3148 }
3149
Chris Lattnerc0215722010-04-04 19:25:43 +00003150 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_inlined_end", 1));
Bill Wendling94d04b82009-05-20 23:21:38 +00003151}