blob: 2eb6f3acd000553e3377cb31f217837068477e32 [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 Wendling57fbba42010-04-05 22:59:21 +000017#include "llvm/Constants.h"
Bill Wendling0310d762009-05-15 09:23:25 +000018#include "llvm/Module.h"
David Greeneb2c66fc2009-08-19 21:52:55 +000019#include "llvm/CodeGen/MachineFunction.h"
Bill Wendling0310d762009-05-15 09:23:25 +000020#include "llvm/CodeGen/MachineModuleInfo.h"
Chris Lattnerb7db7332010-03-09 01:58:53 +000021#include "llvm/MC/MCAsmInfo.h"
Chris Lattnera87dea42009-07-31 18:48:30 +000022#include "llvm/MC/MCSection.h"
Chris Lattner6c2f9e12009-08-19 05:49:37 +000023#include "llvm/MC/MCStreamer.h"
Chris Lattnerb7db7332010-03-09 01:58:53 +000024#include "llvm/MC/MCSymbol.h"
Chris Lattner45111d12010-01-16 21:57:06 +000025#include "llvm/Target/Mangler.h"
Bill Wendling0310d762009-05-15 09:23:25 +000026#include "llvm/Target/TargetData.h"
27#include "llvm/Target/TargetFrameInfo.h"
Chris Lattnerf0144122009-07-28 03:13:23 +000028#include "llvm/Target/TargetLoweringObjectFile.h"
Chris Lattner9d1c1ad2010-04-04 18:06:11 +000029#include "llvm/Target/TargetMachine.h"
Chris Lattnerf0144122009-07-28 03:13:23 +000030#include "llvm/Target/TargetRegisterInfo.h"
Devang Patel2a4a3b72010-04-19 19:14:02 +000031#include "llvm/Target/TargetOptions.h"
Chris Lattner74e41f92010-04-05 05:24:55 +000032#include "llvm/Analysis/DebugInfo.h"
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +000033#include "llvm/ADT/STLExtras.h"
Chris Lattner23132b12009-08-24 03:52:50 +000034#include "llvm/ADT/StringExtras.h"
Devang Pateleac9c072010-04-27 19:46:33 +000035#include "llvm/Support/CommandLine.h"
Daniel Dunbar6e4bdfc2009-10-13 06:47:08 +000036#include "llvm/Support/Debug.h"
37#include "llvm/Support/ErrorHandling.h"
Devang Patel3139fcf2010-01-26 21:39:14 +000038#include "llvm/Support/ValueHandle.h"
Chris Lattner0ad9c912010-01-22 22:09:00 +000039#include "llvm/Support/FormattedStream.h"
Chris Lattnera87dea42009-07-31 18:48:30 +000040#include "llvm/Support/Timer.h"
41#include "llvm/System/Path.h"
Bill Wendling0310d762009-05-15 09:23:25 +000042using namespace llvm;
43
Devang Pateleac9c072010-04-27 19:46:33 +000044static cl::opt<bool> PrintDbgScope("print-dbgscope", cl::Hidden,
45 cl::desc("Print DbgScope information for each machine instruction"));
46
47static cl::opt<bool> DisableDebugInfoPrinting("disable-debug-info-print", cl::Hidden,
48 cl::desc("Disable debug info printing"));
49
Dan Gohman281d65d2010-05-07 01:08:53 +000050static cl::opt<bool> UnknownLocations("use-unknown-locations", cl::Hidden,
51 cl::desc("Make an absense of debug location information explicit."),
52 cl::init(false));
53
Bill Wendling5f017e82010-04-07 09:28:04 +000054namespace {
55 const char *DWARFGroupName = "DWARF Emission";
56 const char *DbgTimerName = "DWARF Debug Writer";
57} // end anonymous namespace
58
Bill Wendling0310d762009-05-15 09:23:25 +000059//===----------------------------------------------------------------------===//
60
61/// Configuration values for initial hash set sizes (log2).
62///
Bill Wendling0310d762009-05-15 09:23:25 +000063static const unsigned InitAbbreviationsSetSize = 9; // log2(512)
Bill Wendling0310d762009-05-15 09:23:25 +000064
65namespace llvm {
66
67//===----------------------------------------------------------------------===//
68/// CompileUnit - This dwarf writer support class manages information associate
69/// with a source file.
Nick Lewycky5f9843f2009-11-17 08:11:44 +000070class CompileUnit {
Bill Wendling0310d762009-05-15 09:23:25 +000071 /// ID - File identifier for source.
72 ///
73 unsigned ID;
74
75 /// Die - Compile unit debug information entry.
76 ///
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +000077 const OwningPtr<DIE> CUDie;
Bill Wendling0310d762009-05-15 09:23:25 +000078
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +000079 /// IndexTyDie - An anonymous type for index type. Owned by CUDie.
Devang Patel6f01d9c2009-11-21 00:31:03 +000080 DIE *IndexTyDie;
81
Bill Wendling0310d762009-05-15 09:23:25 +000082 /// GVToDieMap - Tracks the mapping of unit level debug informaton
83 /// variables to debug information entries.
Devang Patele4b27562009-08-28 23:24:31 +000084 /// FIXME : Rename GVToDieMap -> NodeToDieMap
Devang Patele9f8f5e2010-05-07 20:54:48 +000085 DenseMap<const MDNode *, DIE *> GVToDieMap;
Bill Wendling0310d762009-05-15 09:23:25 +000086
87 /// GVToDIEEntryMap - Tracks the mapping of unit level debug informaton
88 /// descriptors to debug information entries using a DIEEntry proxy.
Devang Patele4b27562009-08-28 23:24:31 +000089 /// FIXME : Rename
Devang Patele9f8f5e2010-05-07 20:54:48 +000090 DenseMap<const MDNode *, DIEEntry *> GVToDIEEntryMap;
Bill Wendling0310d762009-05-15 09:23:25 +000091
92 /// Globals - A map of globally visible named entities for this unit.
93 ///
94 StringMap<DIE*> Globals;
95
Devang Patel193f7202009-11-24 01:14:22 +000096 /// GlobalTypes - A map of globally visible types for this unit.
97 ///
98 StringMap<DIE*> GlobalTypes;
99
Bill Wendling0310d762009-05-15 09:23:25 +0000100public:
101 CompileUnit(unsigned I, DIE *D)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000102 : ID(I), CUDie(D), IndexTyDie(0) {}
Bill Wendling0310d762009-05-15 09:23:25 +0000103
104 // Accessors.
Devang Patel193f7202009-11-24 01:14:22 +0000105 unsigned getID() const { return ID; }
Jeffrey Yasskind0f393d2010-03-11 18:29:55 +0000106 DIE* getCUDie() const { return CUDie.get(); }
Devang Patel193f7202009-11-24 01:14:22 +0000107 const StringMap<DIE*> &getGlobals() const { return Globals; }
108 const StringMap<DIE*> &getGlobalTypes() const { return GlobalTypes; }
Bill Wendling0310d762009-05-15 09:23:25 +0000109
110 /// hasContent - Return true if this compile unit has something to write out.
111 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000112 bool hasContent() const { return !CUDie->getChildren().empty(); }
Bill Wendling0310d762009-05-15 09:23:25 +0000113
Devang Patel2c4ceb12009-11-21 02:48:08 +0000114 /// addGlobal - Add a new global entity to the compile unit.
Bill Wendling0310d762009-05-15 09:23:25 +0000115 ///
Benjamin Kramerbbb88db2010-03-31 20:15:45 +0000116 void addGlobal(StringRef Name, DIE *Die) { Globals[Name] = Die; }
Bill Wendling0310d762009-05-15 09:23:25 +0000117
Devang Patel193f7202009-11-24 01:14:22 +0000118 /// addGlobalType - Add a new global type to the compile unit.
119 ///
Benjamin Kramerbbb88db2010-03-31 20:15:45 +0000120 void addGlobalType(StringRef Name, DIE *Die) {
Devang Patel193f7202009-11-24 01:14:22 +0000121 GlobalTypes[Name] = Die;
122 }
123
Devang Patel017d1212009-11-20 21:37:22 +0000124 /// getDIE - Returns the debug information entry map slot for the
Bill Wendling0310d762009-05-15 09:23:25 +0000125 /// specified debug variable.
Devang Patele9f8f5e2010-05-07 20:54:48 +0000126 DIE *getDIE(const MDNode *N) { return GVToDieMap.lookup(N); }
Jim Grosbach31ef40e2009-11-21 23:12:12 +0000127
Devang Patel017d1212009-11-20 21:37:22 +0000128 /// insertDIE - Insert DIE into the map.
Devang Patele9f8f5e2010-05-07 20:54:48 +0000129 void insertDIE(const MDNode *N, DIE *D) {
Devang Patel017d1212009-11-20 21:37:22 +0000130 GVToDieMap.insert(std::make_pair(N, D));
131 }
Bill Wendling0310d762009-05-15 09:23:25 +0000132
Devang Patel017d1212009-11-20 21:37:22 +0000133 /// getDIEEntry - Returns the debug information entry for the speciefied
134 /// debug variable.
Devang Patele9f8f5e2010-05-07 20:54:48 +0000135 DIEEntry *getDIEEntry(const MDNode *N) {
136 DenseMap<const MDNode *, DIEEntry *>::iterator I = GVToDIEEntryMap.find(N);
Devang Patel6404e4e2009-12-15 19:16:48 +0000137 if (I == GVToDIEEntryMap.end())
138 return NULL;
139 return I->second;
140 }
Devang Patel017d1212009-11-20 21:37:22 +0000141
142 /// insertDIEEntry - Insert debug information entry into the map.
Devang Patele9f8f5e2010-05-07 20:54:48 +0000143 void insertDIEEntry(const MDNode *N, DIEEntry *E) {
Devang Patel017d1212009-11-20 21:37:22 +0000144 GVToDIEEntryMap.insert(std::make_pair(N, E));
Bill Wendling0310d762009-05-15 09:23:25 +0000145 }
146
Devang Patel2c4ceb12009-11-21 02:48:08 +0000147 /// addDie - Adds or interns the DIE to the compile unit.
Bill Wendling0310d762009-05-15 09:23:25 +0000148 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000149 void addDie(DIE *Buffer) {
150 this->CUDie->addChild(Buffer);
Bill Wendling0310d762009-05-15 09:23:25 +0000151 }
Devang Patel6f01d9c2009-11-21 00:31:03 +0000152
153 // getIndexTyDie - Get an anonymous type for index type.
154 DIE *getIndexTyDie() {
155 return IndexTyDie;
156 }
157
Jim Grosbach7ab38df2009-11-22 19:20:36 +0000158 // setIndexTyDie - Set D as anonymous type for index which can be reused
159 // later.
Devang Patel6f01d9c2009-11-21 00:31:03 +0000160 void setIndexTyDie(DIE *D) {
161 IndexTyDie = D;
162 }
163
Bill Wendling0310d762009-05-15 09:23:25 +0000164};
165
166//===----------------------------------------------------------------------===//
167/// DbgVariable - This class is used to track local variable information.
168///
Devang Patelf76a3d62009-11-16 21:53:40 +0000169class DbgVariable {
Bill Wendling0310d762009-05-15 09:23:25 +0000170 DIVariable Var; // Variable Descriptor.
Devang Patel53bb5c92009-11-10 23:06:00 +0000171 DIE *TheDIE;
Bill Wendling0310d762009-05-15 09:23:25 +0000172public:
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000173 // AbsVar may be NULL.
Devang Patel26c1e562010-05-20 16:36:41 +0000174 DbgVariable(DIVariable V) : Var(V), TheDIE(0) {}
Bill Wendling0310d762009-05-15 09:23:25 +0000175
176 // Accessors.
Devang Patel53bb5c92009-11-10 23:06:00 +0000177 DIVariable getVariable() const { return Var; }
Devang Patel53bb5c92009-11-10 23:06:00 +0000178 void setDIE(DIE *D) { TheDIE = D; }
179 DIE *getDIE() const { return TheDIE; }
Bill Wendling0310d762009-05-15 09:23:25 +0000180};
181
182//===----------------------------------------------------------------------===//
Devang Pateleac9c072010-04-27 19:46:33 +0000183/// DbgRange - This is used to track range of instructions with identical
184/// debug info scope.
185///
186typedef std::pair<const MachineInstr *, const MachineInstr *> DbgRange;
187
188//===----------------------------------------------------------------------===//
Bill Wendling0310d762009-05-15 09:23:25 +0000189/// DbgScope - This class is used to track scope information.
190///
Devang Patelf76a3d62009-11-16 21:53:40 +0000191class DbgScope {
Bill Wendling0310d762009-05-15 09:23:25 +0000192 DbgScope *Parent; // Parent to this scope.
Jim Grosbach31ef40e2009-11-21 23:12:12 +0000193 DIDescriptor Desc; // Debug info descriptor for scope.
Devang Patel3139fcf2010-01-26 21:39:14 +0000194 // Location at which this scope is inlined.
Devang Patele9f8f5e2010-05-07 20:54:48 +0000195 AssertingVH<const MDNode> InlinedAtLocation;
Devang Patel53bb5c92009-11-10 23:06:00 +0000196 bool AbstractScope; // Abstract Scope
Devang Pateld38dd112009-10-01 18:25:23 +0000197 const MachineInstr *LastInsn; // Last instruction of this scope.
198 const MachineInstr *FirstInsn; // First instruction of this scope.
Devang Pateleac9c072010-04-27 19:46:33 +0000199 unsigned DFSIn, DFSOut;
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000200 // Scopes defined in scope. Contents not owned.
201 SmallVector<DbgScope *, 4> Scopes;
202 // Variables declared in scope. Contents owned.
203 SmallVector<DbgVariable *, 8> Variables;
Devang Pateleac9c072010-04-27 19:46:33 +0000204 SmallVector<DbgRange, 4> Ranges;
Owen Anderson04c05f72009-06-24 22:53:20 +0000205 // Private state for dump()
206 mutable unsigned IndentLevel;
Bill Wendling0310d762009-05-15 09:23:25 +0000207public:
Devang Patele9f8f5e2010-05-07 20:54:48 +0000208 DbgScope(DbgScope *P, DIDescriptor D, const MDNode *I = 0)
Devang Patel53bb5c92009-11-10 23:06:00 +0000209 : Parent(P), Desc(D), InlinedAtLocation(I), AbstractScope(false),
Devang Pateleac9c072010-04-27 19:46:33 +0000210 LastInsn(0), FirstInsn(0),
211 DFSIn(0), DFSOut(0), IndentLevel(0) {}
Bill Wendling0310d762009-05-15 09:23:25 +0000212 virtual ~DbgScope();
213
214 // Accessors.
215 DbgScope *getParent() const { return Parent; }
Devang Patel53bb5c92009-11-10 23:06:00 +0000216 void setParent(DbgScope *P) { Parent = P; }
Bill Wendling0310d762009-05-15 09:23:25 +0000217 DIDescriptor getDesc() const { return Desc; }
Devang Patele9f8f5e2010-05-07 20:54:48 +0000218 const MDNode *getInlinedAt() const { return InlinedAtLocation; }
219 const MDNode *getScopeNode() const { return Desc; }
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000220 const SmallVector<DbgScope *, 4> &getScopes() { return Scopes; }
221 const SmallVector<DbgVariable *, 8> &getVariables() { return Variables; }
Devang Pateleac9c072010-04-27 19:46:33 +0000222 const SmallVector<DbgRange, 4> &getRanges() { return Ranges; }
223
224 /// openInsnRange - This scope covers instruction range starting from MI.
225 void openInsnRange(const MachineInstr *MI) {
226 if (!FirstInsn)
227 FirstInsn = MI;
228
229 if (Parent)
230 Parent->openInsnRange(MI);
231 }
232
233 /// extendInsnRange - Extend the current instruction range covered by
234 /// this scope.
235 void extendInsnRange(const MachineInstr *MI) {
236 assert (FirstInsn && "MI Range is not open!");
237 LastInsn = MI;
238 if (Parent)
239 Parent->extendInsnRange(MI);
240 }
241
242 /// closeInsnRange - Create a range based on FirstInsn and LastInsn collected
243 /// until now. This is used when a new scope is encountered while walking
244 /// machine instructions.
245 void closeInsnRange(DbgScope *NewScope = NULL) {
246 assert (LastInsn && "Last insn missing!");
247 Ranges.push_back(DbgRange(FirstInsn, LastInsn));
248 FirstInsn = NULL;
249 LastInsn = NULL;
250 // If Parent dominates NewScope then do not close Parent's instruction
251 // range.
252 if (Parent && (!NewScope || !Parent->dominates(NewScope)))
253 Parent->closeInsnRange(NewScope);
254 }
255
Devang Patel53bb5c92009-11-10 23:06:00 +0000256 void setAbstractScope() { AbstractScope = true; }
257 bool isAbstractScope() const { return AbstractScope; }
Devang Pateleac9c072010-04-27 19:46:33 +0000258
259 // Depth First Search support to walk and mainpluate DbgScope hierarchy.
260 unsigned getDFSOut() const { return DFSOut; }
261 void setDFSOut(unsigned O) { DFSOut = O; }
262 unsigned getDFSIn() const { return DFSIn; }
263 void setDFSIn(unsigned I) { DFSIn = I; }
264 bool dominates(const DbgScope *S) {
265 if (S == this)
266 return true;
267 if (DFSIn < S->getDFSIn() && DFSOut > S->getDFSOut())
268 return true;
269 return false;
270 }
Devang Patel53bb5c92009-11-10 23:06:00 +0000271
Devang Patel2c4ceb12009-11-21 02:48:08 +0000272 /// addScope - Add a scope to the scope.
Bill Wendling0310d762009-05-15 09:23:25 +0000273 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000274 void addScope(DbgScope *S) { Scopes.push_back(S); }
Bill Wendling0310d762009-05-15 09:23:25 +0000275
Devang Patel2c4ceb12009-11-21 02:48:08 +0000276 /// addVariable - Add a variable to the scope.
Bill Wendling0310d762009-05-15 09:23:25 +0000277 ///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000278 void addVariable(DbgVariable *V) { Variables.push_back(V); }
Bill Wendling0310d762009-05-15 09:23:25 +0000279
Bill Wendling0310d762009-05-15 09:23:25 +0000280#ifndef NDEBUG
281 void dump() const;
282#endif
283};
Devang Pateleac9c072010-04-27 19:46:33 +0000284
Chris Lattnerea761862010-04-05 04:09:20 +0000285} // end llvm namespace
Bill Wendling0310d762009-05-15 09:23:25 +0000286
287#ifndef NDEBUG
288void DbgScope::dump() const {
David Greenef83adbc2009-12-24 00:31:35 +0000289 raw_ostream &err = dbgs();
Chris Lattnerc281de12009-08-23 00:51:00 +0000290 err.indent(IndentLevel);
Devang Patele9f8f5e2010-05-07 20:54:48 +0000291 const MDNode *N = Desc;
Devang Patel53bb5c92009-11-10 23:06:00 +0000292 N->dump();
Devang Patel53bb5c92009-11-10 23:06:00 +0000293 if (AbstractScope)
294 err << "Abstract Scope\n";
Bill Wendling0310d762009-05-15 09:23:25 +0000295
296 IndentLevel += 2;
Devang Patel53bb5c92009-11-10 23:06:00 +0000297 if (!Scopes.empty())
298 err << "Children ...\n";
Bill Wendling0310d762009-05-15 09:23:25 +0000299 for (unsigned i = 0, e = Scopes.size(); i != e; ++i)
300 if (Scopes[i] != this)
301 Scopes[i]->dump();
302
303 IndentLevel -= 2;
304}
305#endif
306
Bill Wendling0310d762009-05-15 09:23:25 +0000307DbgScope::~DbgScope() {
Bill Wendling0310d762009-05-15 09:23:25 +0000308 for (unsigned j = 0, M = Variables.size(); j < M; ++j)
309 delete Variables[j];
Bill Wendling0310d762009-05-15 09:23:25 +0000310}
311
Chris Lattner49cd6642010-04-05 05:11:15 +0000312DwarfDebug::DwarfDebug(AsmPrinter *A, Module *M)
Devang Patel163a9f72010-05-10 22:49:55 +0000313 : Asm(A), MMI(Asm->MMI), FirstCU(0),
Chris Lattner994cb122010-04-05 03:52:55 +0000314 AbbreviationsSet(InitAbbreviationsSetSize),
Devang Patelf2548ca2010-04-16 23:33:45 +0000315 CurrentFnDbgScope(0), PrevLabel(NULL) {
Chris Lattnerbc733f52010-03-13 02:17:42 +0000316 NextStringPoolNumber = 0;
Chris Lattner9c69e285532010-04-04 22:59:04 +0000317
Chris Lattner4ad1efe2010-04-04 23:10:38 +0000318 DwarfFrameSectionSym = DwarfInfoSectionSym = DwarfAbbrevSectionSym = 0;
319 DwarfStrSectionSym = TextSectionSym = 0;
Devang Pateleac9c072010-04-27 19:46:33 +0000320 DwarfDebugRangeSectionSym = 0;
321 FunctionBeginSym = 0;
Torok Edwin9c421072010-04-07 10:44:46 +0000322 if (TimePassesIsEnabled) {
323 NamedRegionTimer T(DbgTimerName, DWARFGroupName);
324 beginModule(M);
325 } else {
326 beginModule(M);
327 }
Bill Wendling0310d762009-05-15 09:23:25 +0000328}
329DwarfDebug::~DwarfDebug() {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000330 for (unsigned j = 0, M = DIEBlocks.size(); j < M; ++j)
331 DIEBlocks[j]->~DIEBlock();
Bill Wendling0310d762009-05-15 09:23:25 +0000332}
333
Chris Lattnerbc733f52010-03-13 02:17:42 +0000334MCSymbol *DwarfDebug::getStringPoolEntry(StringRef Str) {
335 std::pair<MCSymbol*, unsigned> &Entry = StringPool[Str];
336 if (Entry.first) return Entry.first;
337
338 Entry.second = NextStringPoolNumber++;
Chris Lattnerc0215722010-04-04 19:25:43 +0000339 return Entry.first = Asm->GetTempSymbol("string", Entry.second);
Chris Lattnerbc733f52010-03-13 02:17:42 +0000340}
341
342
Devang Patel2c4ceb12009-11-21 02:48:08 +0000343/// assignAbbrevNumber - Define a unique number for the abbreviation.
Bill Wendling0310d762009-05-15 09:23:25 +0000344///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000345void DwarfDebug::assignAbbrevNumber(DIEAbbrev &Abbrev) {
Bill Wendling0310d762009-05-15 09:23:25 +0000346 // Profile the node so that we can make it unique.
347 FoldingSetNodeID ID;
348 Abbrev.Profile(ID);
349
350 // Check the set for priors.
351 DIEAbbrev *InSet = AbbreviationsSet.GetOrInsertNode(&Abbrev);
352
353 // If it's newly added.
354 if (InSet == &Abbrev) {
355 // Add to abbreviation list.
356 Abbreviations.push_back(&Abbrev);
357
358 // Assign the vector position + 1 as its number.
359 Abbrev.setNumber(Abbreviations.size());
360 } else {
361 // Assign existing abbreviation number.
362 Abbrev.setNumber(InSet->getNumber());
363 }
364}
365
Devang Patel2c4ceb12009-11-21 02:48:08 +0000366/// createDIEEntry - Creates a new DIEEntry to be a proxy for a debug
Bill Wendling995f80a2009-05-20 23:24:48 +0000367/// information entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000368DIEEntry *DwarfDebug::createDIEEntry(DIE *Entry) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000369 DIEEntry *Value = new (DIEValueAllocator) DIEEntry(Entry);
Bill Wendling0310d762009-05-15 09:23:25 +0000370 return Value;
371}
372
Devang Patel2c4ceb12009-11-21 02:48:08 +0000373/// addUInt - Add an unsigned integer attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000374///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000375void DwarfDebug::addUInt(DIE *Die, unsigned Attribute,
Bill Wendling0310d762009-05-15 09:23:25 +0000376 unsigned Form, uint64_t Integer) {
377 if (!Form) Form = DIEInteger::BestForm(false, 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 Patel2c4ceb12009-11-21 02:48:08 +0000382/// addSInt - Add an signed integer attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000383///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000384void DwarfDebug::addSInt(DIE *Die, unsigned Attribute,
Bill Wendling0310d762009-05-15 09:23:25 +0000385 unsigned Form, int64_t Integer) {
386 if (!Form) Form = DIEInteger::BestForm(true, Integer);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000387 DIEValue *Value = new (DIEValueAllocator) DIEInteger(Integer);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000388 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000389}
390
Devang Patel69f57b12009-12-02 15:25:16 +0000391/// addString - Add a string attribute data and value. DIEString only
392/// keeps string reference.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000393void DwarfDebug::addString(DIE *Die, unsigned Attribute, unsigned Form,
Chris Lattner4cf202b2010-01-23 03:11:46 +0000394 StringRef String) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000395 DIEValue *Value = new (DIEValueAllocator) DIEString(String);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000396 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000397}
398
Devang Patel2c4ceb12009-11-21 02:48:08 +0000399/// addLabel - Add a Dwarf label attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000400///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000401void DwarfDebug::addLabel(DIE *Die, unsigned Attribute, unsigned Form,
Chris Lattnerb98b1bf2010-03-08 22:23:36 +0000402 const MCSymbol *Label) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000403 DIEValue *Value = new (DIEValueAllocator) DIELabel(Label);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000404 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000405}
406
Devang Patel2c4ceb12009-11-21 02:48:08 +0000407/// addDelta - Add a label delta attribute data and value.
Bill Wendling0310d762009-05-15 09:23:25 +0000408///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000409void DwarfDebug::addDelta(DIE *Die, unsigned Attribute, unsigned Form,
Chris Lattnerb98b1bf2010-03-08 22:23:36 +0000410 const MCSymbol *Hi, const MCSymbol *Lo) {
Benjamin Kramer345ef342010-03-31 19:34:01 +0000411 DIEValue *Value = new (DIEValueAllocator) DIEDelta(Hi, Lo);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000412 Die->addValue(Attribute, Form, Value);
Bill Wendling0310d762009-05-15 09:23:25 +0000413}
414
Chris Lattner74e41f92010-04-05 05:24:55 +0000415/// addDIEEntry - Add a DIE attribute data and value.
416///
417void DwarfDebug::addDIEEntry(DIE *Die, unsigned Attribute, unsigned Form,
418 DIE *Entry) {
419 Die->addValue(Attribute, Form, createDIEEntry(Entry));
420}
421
422
Devang Patel2c4ceb12009-11-21 02:48:08 +0000423/// addBlock - Add block data.
Bill Wendling0310d762009-05-15 09:23:25 +0000424///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000425void DwarfDebug::addBlock(DIE *Die, unsigned Attribute, unsigned Form,
Bill Wendling0310d762009-05-15 09:23:25 +0000426 DIEBlock *Block) {
Chris Lattnera37d5382010-04-05 00:18:22 +0000427 Block->ComputeSize(Asm);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000428 DIEBlocks.push_back(Block); // Memoize so we can call the destructor later on.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000429 Die->addValue(Attribute, Block->BestForm(), Block);
Bill Wendling0310d762009-05-15 09:23:25 +0000430}
431
Devang Patel2c4ceb12009-11-21 02:48:08 +0000432/// addSourceLine - Add location information to specified debug information
Bill Wendling0310d762009-05-15 09:23:25 +0000433/// entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000434void DwarfDebug::addSourceLine(DIE *Die, const DIVariable *V) {
Devang Patelc665a512010-05-07 23:33:41 +0000435 // Verify variable.
436 if (!V->Verify())
Bill Wendling0310d762009-05-15 09:23:25 +0000437 return;
438
439 unsigned Line = V->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000440 unsigned FileID = GetOrCreateSourceID(V->getContext().getDirectory(),
441 V->getContext().getFilename());
Bill Wendling0310d762009-05-15 09:23:25 +0000442 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000443 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
444 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Bill Wendling0310d762009-05-15 09:23:25 +0000445}
446
Devang Patel2c4ceb12009-11-21 02:48:08 +0000447/// addSourceLine - Add location information to specified debug information
Bill Wendling0310d762009-05-15 09:23:25 +0000448/// entry.
Devang Patela49d8772010-05-07 23:19:07 +0000449void DwarfDebug::addSourceLine(DIE *Die, const DIGlobalVariable *G) {
Devang Patelc665a512010-05-07 23:33:41 +0000450 // Verify global variable.
451 if (!G->Verify())
Bill Wendling0310d762009-05-15 09:23:25 +0000452 return;
453
454 unsigned Line = G->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000455 unsigned FileID = GetOrCreateSourceID(G->getContext().getDirectory(),
456 G->getContext().getFilename());
Bill Wendling0310d762009-05-15 09:23:25 +0000457 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000458 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
459 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Bill Wendling0310d762009-05-15 09:23:25 +0000460}
Devang Patel82dfc0c2009-08-31 22:47:13 +0000461
Devang Patel2c4ceb12009-11-21 02:48:08 +0000462/// addSourceLine - Add location information to specified debug information
Devang Patel82dfc0c2009-08-31 22:47:13 +0000463/// entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000464void DwarfDebug::addSourceLine(DIE *Die, const DISubprogram *SP) {
Devang Patelc665a512010-05-07 23:33:41 +0000465 // Verify subprogram.
466 if (!SP->Verify())
Devang Patel82dfc0c2009-08-31 22:47:13 +0000467 return;
Caroline Ticec6f9d622009-09-11 18:25:54 +0000468 // If the line number is 0, don't add it.
469 if (SP->getLineNumber() == 0)
470 return;
471
Devang Patel82dfc0c2009-08-31 22:47:13 +0000472 unsigned Line = SP->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000473 if (!SP->getContext().Verify())
474 return;
Devang Patel9bb59a22010-03-24 21:30:35 +0000475 unsigned FileID = GetOrCreateSourceID(SP->getDirectory(),
476 SP->getFilename());
Devang Patel82dfc0c2009-08-31 22:47:13 +0000477 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000478 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
479 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Devang Patel82dfc0c2009-08-31 22:47:13 +0000480}
481
Devang Patel2c4ceb12009-11-21 02:48:08 +0000482/// addSourceLine - Add location information to specified debug information
Devang Patel82dfc0c2009-08-31 22:47:13 +0000483/// entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000484void DwarfDebug::addSourceLine(DIE *Die, const DIType *Ty) {
Devang Patelc665a512010-05-07 23:33:41 +0000485 // Verify type.
486 if (!Ty->Verify())
Bill Wendling0310d762009-05-15 09:23:25 +0000487 return;
488
489 unsigned Line = Ty->getLineNumber();
Devang Patel77bf2952010-03-08 22:02:50 +0000490 if (!Ty->getContext().Verify())
491 return;
492 unsigned FileID = GetOrCreateSourceID(Ty->getContext().getDirectory(),
493 Ty->getContext().getFilename());
Bill Wendling0310d762009-05-15 09:23:25 +0000494 assert(FileID && "Invalid file id");
Devang Patel2c4ceb12009-11-21 02:48:08 +0000495 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
496 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
Bill Wendling0310d762009-05-15 09:23:25 +0000497}
498
Devang Patel6404e4e2009-12-15 19:16:48 +0000499/// addSourceLine - Add location information to specified debug information
500/// entry.
501void DwarfDebug::addSourceLine(DIE *Die, const DINameSpace *NS) {
Devang Patelc665a512010-05-07 23:33:41 +0000502 // Verify namespace.
503 if (!NS->Verify())
Devang Patel6404e4e2009-12-15 19:16:48 +0000504 return;
505
506 unsigned Line = NS->getLineNumber();
507 StringRef FN = NS->getFilename();
508 StringRef Dir = NS->getDirectory();
509
510 unsigned FileID = GetOrCreateSourceID(Dir, FN);
511 assert(FileID && "Invalid file id");
512 addUInt(Die, dwarf::DW_AT_decl_file, 0, FileID);
513 addUInt(Die, dwarf::DW_AT_decl_line, 0, Line);
514}
515
Caroline Ticedc8f6042009-08-31 21:19:37 +0000516/* Byref variables, in Blocks, are declared by the programmer as
517 "SomeType VarName;", but the compiler creates a
518 __Block_byref_x_VarName struct, and gives the variable VarName
519 either the struct, or a pointer to the struct, as its type. This
520 is necessary for various behind-the-scenes things the compiler
521 needs to do with by-reference variables in blocks.
522
523 However, as far as the original *programmer* is concerned, the
524 variable should still have type 'SomeType', as originally declared.
525
526 The following function dives into the __Block_byref_x_VarName
527 struct to find the original type of the variable. This will be
528 passed back to the code generating the type for the Debug
529 Information Entry for the variable 'VarName'. 'VarName' will then
530 have the original type 'SomeType' in its debug information.
531
532 The original type 'SomeType' will be the type of the field named
533 'VarName' inside the __Block_byref_x_VarName struct.
534
535 NOTE: In order for this to not completely fail on the debugger
536 side, the Debug Information Entry for the variable VarName needs to
537 have a DW_AT_location that tells the debugger how to unwind through
538 the pointers and __Block_byref_x_VarName struct to find the actual
Devang Patel2c4ceb12009-11-21 02:48:08 +0000539 value of the variable. The function addBlockByrefType does this. */
Caroline Ticedc8f6042009-08-31 21:19:37 +0000540
541/// Find the type the programmer originally declared the variable to be
542/// and return that type.
543///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000544DIType DwarfDebug::getBlockByrefType(DIType Ty, std::string Name) {
Caroline Ticedc8f6042009-08-31 21:19:37 +0000545
546 DIType subType = Ty;
547 unsigned tag = Ty.getTag();
548
549 if (tag == dwarf::DW_TAG_pointer_type) {
Devang Patel2db49d72010-05-07 18:11:54 +0000550 DIDerivedType DTy = DIDerivedType(Ty);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000551 subType = DTy.getTypeDerivedFrom();
552 }
553
Devang Patel2db49d72010-05-07 18:11:54 +0000554 DICompositeType blockStruct = DICompositeType(subType);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000555 DIArray Elements = blockStruct.getTypeArray();
556
Caroline Ticedc8f6042009-08-31 21:19:37 +0000557 for (unsigned i = 0, N = Elements.getNumElements(); i < N; ++i) {
558 DIDescriptor Element = Elements.getElement(i);
Devang Patel2db49d72010-05-07 18:11:54 +0000559 DIDerivedType DT = DIDerivedType(Element);
Devang Patel65dbc902009-11-25 17:36:49 +0000560 if (Name == DT.getName())
Caroline Ticedc8f6042009-08-31 21:19:37 +0000561 return (DT.getTypeDerivedFrom());
562 }
563
564 return Ty;
565}
566
Devang Patel2c4ceb12009-11-21 02:48:08 +0000567/// addComplexAddress - Start with the address based on the location provided,
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000568/// and generate the DWARF information necessary to find the actual variable
569/// given the extra address information encoded in the DIVariable, starting from
570/// the starting location. Add the DWARF information to the die.
571///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000572void DwarfDebug::addComplexAddress(DbgVariable *&DV, DIE *Die,
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000573 unsigned Attribute,
574 const MachineLocation &Location) {
575 const DIVariable &VD = DV->getVariable();
576 DIType Ty = VD.getType();
577
578 // Decode the original location, and use that as the start of the byref
579 // variable's location.
Chris Lattnerd38fee82010-04-05 00:13:49 +0000580 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000581 unsigned Reg = RI->getDwarfRegNum(Location.getReg(), false);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000582 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000583
584 if (Location.isReg()) {
585 if (Reg < 32) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000586 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_reg0 + Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000587 } else {
588 Reg = Reg - dwarf::DW_OP_reg0;
Devang Patel2c4ceb12009-11-21 02:48:08 +0000589 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
590 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000591 }
592 } else {
593 if (Reg < 32)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000594 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000595 else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000596 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_bregx);
597 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000598 }
599
Devang Patel2c4ceb12009-11-21 02:48:08 +0000600 addUInt(Block, 0, dwarf::DW_FORM_sdata, Location.getOffset());
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000601 }
602
603 for (unsigned i = 0, N = VD.getNumAddrElements(); i < N; ++i) {
604 uint64_t Element = VD.getAddrElement(i);
605
606 if (Element == DIFactory::OpPlus) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000607 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
608 addUInt(Block, 0, dwarf::DW_FORM_udata, VD.getAddrElement(++i));
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000609 } else if (Element == DIFactory::OpDeref) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000610 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000611 } else llvm_unreachable("unknown DIFactory Opcode");
612 }
613
614 // Now attach the location information to the DIE.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000615 addBlock(Die, Attribute, 0, Block);
Mike Stump3e4c9bd2009-09-30 00:08:22 +0000616}
617
Caroline Ticedc8f6042009-08-31 21:19:37 +0000618/* Byref variables, in Blocks, are declared by the programmer as "SomeType
619 VarName;", but the compiler creates a __Block_byref_x_VarName struct, and
620 gives the variable VarName either the struct, or a pointer to the struct, as
621 its type. This is necessary for various behind-the-scenes things the
622 compiler needs to do with by-reference variables in Blocks.
623
624 However, as far as the original *programmer* is concerned, the variable
625 should still have type 'SomeType', as originally declared.
626
Devang Patel2c4ceb12009-11-21 02:48:08 +0000627 The function getBlockByrefType dives into the __Block_byref_x_VarName
Caroline Ticedc8f6042009-08-31 21:19:37 +0000628 struct to find the original type of the variable, which is then assigned to
629 the variable's Debug Information Entry as its real type. So far, so good.
630 However now the debugger will expect the variable VarName to have the type
631 SomeType. So we need the location attribute for the variable to be an
Daniel Dunbarf612ff62009-09-19 20:40:05 +0000632 expression that explains to the debugger how to navigate through the
Caroline Ticedc8f6042009-08-31 21:19:37 +0000633 pointers and struct to find the actual variable of type SomeType.
634
635 The following function does just that. We start by getting
636 the "normal" location for the variable. This will be the location
637 of either the struct __Block_byref_x_VarName or the pointer to the
638 struct __Block_byref_x_VarName.
639
640 The struct will look something like:
641
642 struct __Block_byref_x_VarName {
643 ... <various fields>
644 struct __Block_byref_x_VarName *forwarding;
645 ... <various other fields>
646 SomeType VarName;
647 ... <maybe more fields>
648 };
649
650 If we are given the struct directly (as our starting point) we
651 need to tell the debugger to:
652
653 1). Add the offset of the forwarding field.
654
Dan Gohmanf451cb82010-02-10 16:03:48 +0000655 2). Follow that pointer to get the real __Block_byref_x_VarName
Caroline Ticedc8f6042009-08-31 21:19:37 +0000656 struct to use (the real one may have been copied onto the heap).
657
658 3). Add the offset for the field VarName, to find the actual variable.
659
660 If we started with a pointer to the struct, then we need to
661 dereference that pointer first, before the other steps.
662 Translating this into DWARF ops, we will need to append the following
663 to the current location description for the variable:
664
665 DW_OP_deref -- optional, if we start with a pointer
666 DW_OP_plus_uconst <forward_fld_offset>
667 DW_OP_deref
668 DW_OP_plus_uconst <varName_fld_offset>
669
670 That is what this function does. */
671
Devang Patel2c4ceb12009-11-21 02:48:08 +0000672/// addBlockByrefAddress - Start with the address based on the location
Caroline Ticedc8f6042009-08-31 21:19:37 +0000673/// provided, and generate the DWARF information necessary to find the
674/// actual Block variable (navigating the Block struct) based on the
675/// starting location. Add the DWARF information to the die. For
676/// more information, read large comment just above here.
677///
Devang Patel2c4ceb12009-11-21 02:48:08 +0000678void DwarfDebug::addBlockByrefAddress(DbgVariable *&DV, DIE *Die,
Daniel Dunbar00564992009-09-19 20:40:14 +0000679 unsigned Attribute,
680 const MachineLocation &Location) {
Caroline Ticedc8f6042009-08-31 21:19:37 +0000681 const DIVariable &VD = DV->getVariable();
682 DIType Ty = VD.getType();
683 DIType TmpTy = Ty;
684 unsigned Tag = Ty.getTag();
685 bool isPointer = false;
686
Devang Patel65dbc902009-11-25 17:36:49 +0000687 StringRef varName = VD.getName();
Caroline Ticedc8f6042009-08-31 21:19:37 +0000688
689 if (Tag == dwarf::DW_TAG_pointer_type) {
Devang Patel2db49d72010-05-07 18:11:54 +0000690 DIDerivedType DTy = DIDerivedType(Ty);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000691 TmpTy = DTy.getTypeDerivedFrom();
692 isPointer = true;
693 }
694
Devang Patel2db49d72010-05-07 18:11:54 +0000695 DICompositeType blockStruct = DICompositeType(TmpTy);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000696
Daniel Dunbar00564992009-09-19 20:40:14 +0000697 // Find the __forwarding field and the variable field in the __Block_byref
698 // struct.
Daniel Dunbar00564992009-09-19 20:40:14 +0000699 DIArray Fields = blockStruct.getTypeArray();
700 DIDescriptor varField = DIDescriptor();
701 DIDescriptor forwardingField = DIDescriptor();
Caroline Ticedc8f6042009-08-31 21:19:37 +0000702
Daniel Dunbar00564992009-09-19 20:40:14 +0000703 for (unsigned i = 0, N = Fields.getNumElements(); i < N; ++i) {
704 DIDescriptor Element = Fields.getElement(i);
Devang Patel2db49d72010-05-07 18:11:54 +0000705 DIDerivedType DT = DIDerivedType(Element);
Devang Patel65dbc902009-11-25 17:36:49 +0000706 StringRef fieldName = DT.getName();
707 if (fieldName == "__forwarding")
Daniel Dunbar00564992009-09-19 20:40:14 +0000708 forwardingField = Element;
Devang Patel65dbc902009-11-25 17:36:49 +0000709 else if (fieldName == varName)
Daniel Dunbar00564992009-09-19 20:40:14 +0000710 varField = Element;
711 }
Daniel Dunbarf612ff62009-09-19 20:40:05 +0000712
Daniel Dunbar00564992009-09-19 20:40:14 +0000713 // Get the offsets for the forwarding field and the variable field.
Chris Lattner1d65ba72010-03-31 06:06:37 +0000714 unsigned forwardingFieldOffset =
Devang Patel2db49d72010-05-07 18:11:54 +0000715 DIDerivedType(forwardingField).getOffsetInBits() >> 3;
Chris Lattner1d65ba72010-03-31 06:06:37 +0000716 unsigned varFieldOffset =
Devang Patel2db49d72010-05-07 18:11:54 +0000717 DIDerivedType(varField).getOffsetInBits() >> 3;
Caroline Ticedc8f6042009-08-31 21:19:37 +0000718
Mike Stump7e3720d2009-09-24 23:21:26 +0000719 // Decode the original location, and use that as the start of the byref
720 // variable's location.
Chris Lattnerd38fee82010-04-05 00:13:49 +0000721 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Daniel Dunbar00564992009-09-19 20:40:14 +0000722 unsigned Reg = RI->getDwarfRegNum(Location.getReg(), false);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000723 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Caroline Ticedc8f6042009-08-31 21:19:37 +0000724
Daniel Dunbar00564992009-09-19 20:40:14 +0000725 if (Location.isReg()) {
726 if (Reg < 32)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000727 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_reg0 + Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000728 else {
729 Reg = Reg - dwarf::DW_OP_reg0;
Devang Patel2c4ceb12009-11-21 02:48:08 +0000730 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
731 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000732 }
733 } else {
734 if (Reg < 32)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000735 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000736 else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000737 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_bregx);
738 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Daniel Dunbar00564992009-09-19 20:40:14 +0000739 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000740
Devang Patel2c4ceb12009-11-21 02:48:08 +0000741 addUInt(Block, 0, dwarf::DW_FORM_sdata, Location.getOffset());
Daniel Dunbar00564992009-09-19 20:40:14 +0000742 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000743
Mike Stump7e3720d2009-09-24 23:21:26 +0000744 // If we started with a pointer to the __Block_byref... struct, then
Daniel Dunbar00564992009-09-19 20:40:14 +0000745 // the first thing we need to do is dereference the pointer (DW_OP_deref).
Daniel Dunbar00564992009-09-19 20:40:14 +0000746 if (isPointer)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000747 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000748
Daniel Dunbar00564992009-09-19 20:40:14 +0000749 // Next add the offset for the '__forwarding' field:
750 // DW_OP_plus_uconst ForwardingFieldOffset. Note there's no point in
751 // adding the offset if it's 0.
Daniel Dunbar00564992009-09-19 20:40:14 +0000752 if (forwardingFieldOffset > 0) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000753 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
754 addUInt(Block, 0, dwarf::DW_FORM_udata, forwardingFieldOffset);
Daniel Dunbar00564992009-09-19 20:40:14 +0000755 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000756
Daniel Dunbar00564992009-09-19 20:40:14 +0000757 // Now dereference the __forwarding field to get to the real __Block_byref
758 // struct: DW_OP_deref.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000759 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000760
Daniel Dunbar00564992009-09-19 20:40:14 +0000761 // Now that we've got the real __Block_byref... struct, add the offset
762 // for the variable's field to get to the location of the actual variable:
763 // DW_OP_plus_uconst varFieldOffset. Again, don't add if it's 0.
Daniel Dunbar00564992009-09-19 20:40:14 +0000764 if (varFieldOffset > 0) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000765 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
766 addUInt(Block, 0, dwarf::DW_FORM_udata, varFieldOffset);
Daniel Dunbar00564992009-09-19 20:40:14 +0000767 }
Caroline Ticedc8f6042009-08-31 21:19:37 +0000768
Daniel Dunbar00564992009-09-19 20:40:14 +0000769 // Now attach the location information to the DIE.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000770 addBlock(Die, Attribute, 0, Block);
Caroline Ticedc8f6042009-08-31 21:19:37 +0000771}
772
Devang Patel2c4ceb12009-11-21 02:48:08 +0000773/// addAddress - Add an address attribute to a die based on the location
Bill Wendling0310d762009-05-15 09:23:25 +0000774/// provided.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000775void DwarfDebug::addAddress(DIE *Die, unsigned Attribute,
Bill Wendling0310d762009-05-15 09:23:25 +0000776 const MachineLocation &Location) {
Chris Lattnerd38fee82010-04-05 00:13:49 +0000777 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Bill Wendling0310d762009-05-15 09:23:25 +0000778 unsigned Reg = RI->getDwarfRegNum(Location.getReg(), false);
Benjamin Kramer345ef342010-03-31 19:34:01 +0000779 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Bill Wendling0310d762009-05-15 09:23:25 +0000780
781 if (Location.isReg()) {
782 if (Reg < 32) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000783 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_reg0 + Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000784 } else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000785 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_regx);
786 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000787 }
788 } else {
789 if (Reg < 32) {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000790 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_breg0 + Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000791 } else {
Devang Patel2c4ceb12009-11-21 02:48:08 +0000792 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_bregx);
793 addUInt(Block, 0, dwarf::DW_FORM_udata, Reg);
Bill Wendling0310d762009-05-15 09:23:25 +0000794 }
795
Devang Patel2c4ceb12009-11-21 02:48:08 +0000796 addUInt(Block, 0, dwarf::DW_FORM_sdata, Location.getOffset());
Bill Wendling0310d762009-05-15 09:23:25 +0000797 }
798
Devang Patel2c4ceb12009-11-21 02:48:08 +0000799 addBlock(Die, Attribute, 0, Block);
Bill Wendling0310d762009-05-15 09:23:25 +0000800}
801
Devang Patela43098d2010-04-28 01:03:09 +0000802/// addRegisterAddress - Add register location entry in variable DIE.
Devang Patel26c1e562010-05-20 16:36:41 +0000803bool DwarfDebug::addRegisterAddress(DIE *Die, const MCSymbol *VS,
Devang Patela43098d2010-04-28 01:03:09 +0000804 const MachineOperand &MO) {
805 assert (MO.isReg() && "Invalid machine operand!");
806 if (!MO.getReg())
807 return false;
808 MachineLocation Location;
809 Location.set(MO.getReg());
810 addAddress(Die, dwarf::DW_AT_location, Location);
Devang Patel26c1e562010-05-20 16:36:41 +0000811 if (VS)
Devang Patela43098d2010-04-28 01:03:09 +0000812 addLabel(Die, dwarf::DW_AT_start_scope, dwarf::DW_FORM_addr, VS);
813 return true;
814}
815
816/// addConstantValue - Add constant value entry in variable DIE.
Devang Patel26c1e562010-05-20 16:36:41 +0000817bool DwarfDebug::addConstantValue(DIE *Die, const MCSymbol *VS,
Devang Patela43098d2010-04-28 01:03:09 +0000818 const MachineOperand &MO) {
819 assert (MO.isImm() && "Invalid machine operand!");
820 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
821 unsigned Imm = MO.getImm();
822 addUInt(Block, 0, dwarf::DW_FORM_udata, Imm);
823 addBlock(Die, dwarf::DW_AT_const_value, 0, Block);
Devang Patel26c1e562010-05-20 16:36:41 +0000824 if (VS)
Devang Patela43098d2010-04-28 01:03:09 +0000825 addLabel(Die, dwarf::DW_AT_start_scope, dwarf::DW_FORM_addr, VS);
826 return true;
827}
828
829/// addConstantFPValue - Add constant value entry in variable DIE.
Devang Patel26c1e562010-05-20 16:36:41 +0000830bool DwarfDebug::addConstantFPValue(DIE *Die, const MCSymbol *VS,
Devang Patela43098d2010-04-28 01:03:09 +0000831 const MachineOperand &MO) {
832 assert (MO.isFPImm() && "Invalid machine operand!");
833 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
834 APFloat FPImm = MO.getFPImm()->getValueAPF();
835
836 // Get the raw data form of the floating point.
837 const APInt FltVal = FPImm.bitcastToAPInt();
838 const char *FltPtr = (const char*)FltVal.getRawData();
839
840 int NumBytes = FltVal.getBitWidth() / 8; // 8 bits per byte.
841 bool LittleEndian = Asm->getTargetData().isLittleEndian();
842 int Incr = (LittleEndian ? 1 : -1);
843 int Start = (LittleEndian ? 0 : NumBytes - 1);
844 int Stop = (LittleEndian ? NumBytes : -1);
845
846 // Output the constant to DWARF one byte at a time.
847 for (; Start != Stop; Start += Incr)
848 addUInt(Block, 0, dwarf::DW_FORM_data1,
849 (unsigned char)0xFF & FltPtr[Start]);
850
851 addBlock(Die, dwarf::DW_AT_const_value, 0, Block);
Devang Patel26c1e562010-05-20 16:36:41 +0000852 if (VS)
853 addLabel(Die, dwarf::DW_AT_start_scope, dwarf::DW_FORM_addr, VS);
Devang Patela43098d2010-04-28 01:03:09 +0000854 return true;
855}
856
857
Devang Patelc366f832009-12-10 19:14:49 +0000858/// addToContextOwner - Add Die into the list of its context owner's children.
859void DwarfDebug::addToContextOwner(DIE *Die, DIDescriptor Context) {
Devang Patel3c91b052010-03-08 20:52:55 +0000860 if (Context.isType()) {
Devang Patel2db49d72010-05-07 18:11:54 +0000861 DIE *ContextDIE = getOrCreateTypeDIE(DIType(Context));
Devang Patelc366f832009-12-10 19:14:49 +0000862 ContextDIE->addChild(Die);
Devang Patel6404e4e2009-12-15 19:16:48 +0000863 } else if (Context.isNameSpace()) {
Devang Patel2db49d72010-05-07 18:11:54 +0000864 DIE *ContextDIE = getOrCreateNameSpace(DINameSpace(Context));
Devang Patel6404e4e2009-12-15 19:16:48 +0000865 ContextDIE->addChild(Die);
Devang Patel163a9f72010-05-10 22:49:55 +0000866 } else if (DIE *ContextDIE = getCompileUnit(Context)->getDIE(Context))
Devang Patelc366f832009-12-10 19:14:49 +0000867 ContextDIE->addChild(Die);
868 else
Devang Patel163a9f72010-05-10 22:49:55 +0000869 getCompileUnit(Context)->addDie(Die);
Devang Patelc366f832009-12-10 19:14:49 +0000870}
871
Devang Patel16ced732009-12-10 18:05:33 +0000872/// getOrCreateTypeDIE - Find existing DIE or create new DIE for the
873/// given DIType.
874DIE *DwarfDebug::getOrCreateTypeDIE(DIType Ty) {
Devang Patel163a9f72010-05-10 22:49:55 +0000875 CompileUnit *TypeCU = getCompileUnit(Ty);
876 DIE *TyDIE = TypeCU->getDIE(Ty);
Devang Patel16ced732009-12-10 18:05:33 +0000877 if (TyDIE)
878 return TyDIE;
879
880 // Create new type.
881 TyDIE = new DIE(dwarf::DW_TAG_base_type);
Devang Patel163a9f72010-05-10 22:49:55 +0000882 TypeCU->insertDIE(Ty, TyDIE);
Devang Patel16ced732009-12-10 18:05:33 +0000883 if (Ty.isBasicType())
Devang Patel2db49d72010-05-07 18:11:54 +0000884 constructTypeDIE(*TyDIE, DIBasicType(Ty));
Devang Patel16ced732009-12-10 18:05:33 +0000885 else if (Ty.isCompositeType())
Devang Patel2db49d72010-05-07 18:11:54 +0000886 constructTypeDIE(*TyDIE, DICompositeType(Ty));
Devang Patel16ced732009-12-10 18:05:33 +0000887 else {
888 assert(Ty.isDerivedType() && "Unknown kind of DIType");
Devang Patel2db49d72010-05-07 18:11:54 +0000889 constructTypeDIE(*TyDIE, DIDerivedType(Ty));
Devang Patel16ced732009-12-10 18:05:33 +0000890 }
891
Devang Patelc366f832009-12-10 19:14:49 +0000892 addToContextOwner(TyDIE, Ty.getContext());
Devang Patel16ced732009-12-10 18:05:33 +0000893 return TyDIE;
894}
895
Devang Patel2c4ceb12009-11-21 02:48:08 +0000896/// addType - Add a new type attribute to the specified entity.
Devang Patel8a241142009-12-09 18:24:21 +0000897void DwarfDebug::addType(DIE *Entity, DIType Ty) {
Devang Patel9c004872010-05-07 21:45:47 +0000898 if (!Ty.Verify())
Bill Wendling0310d762009-05-15 09:23:25 +0000899 return;
900
901 // Check for pre-existence.
Devang Patel163a9f72010-05-10 22:49:55 +0000902 CompileUnit *TypeCU = getCompileUnit(Ty);
903 DIEEntry *Entry = TypeCU->getDIEEntry(Ty);
Bill Wendling0310d762009-05-15 09:23:25 +0000904 // If it exists then use the existing value.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000905 if (Entry) {
906 Entity->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, Entry);
Bill Wendling0310d762009-05-15 09:23:25 +0000907 return;
908 }
909
Bill Wendling0310d762009-05-15 09:23:25 +0000910 // Construct type.
Devang Patel16ced732009-12-10 18:05:33 +0000911 DIE *Buffer = getOrCreateTypeDIE(Ty);
Bill Wendling0310d762009-05-15 09:23:25 +0000912
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000913 // Set up proxy.
914 Entry = createDIEEntry(Buffer);
Devang Patel163a9f72010-05-10 22:49:55 +0000915 TypeCU->insertDIEEntry(Ty, Entry);
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +0000916
Devang Patel2c4ceb12009-11-21 02:48:08 +0000917 Entity->addValue(dwarf::DW_AT_type, dwarf::DW_FORM_ref4, Entry);
Bill Wendling0310d762009-05-15 09:23:25 +0000918}
919
Devang Patel2c4ceb12009-11-21 02:48:08 +0000920/// constructTypeDIE - Construct basic type die from DIBasicType.
Devang Patel8a241142009-12-09 18:24:21 +0000921void DwarfDebug::constructTypeDIE(DIE &Buffer, DIBasicType BTy) {
Bill Wendling0310d762009-05-15 09:23:25 +0000922 // Get core information.
Devang Patel65dbc902009-11-25 17:36:49 +0000923 StringRef Name = BTy.getName();
Bill Wendling0310d762009-05-15 09:23:25 +0000924 Buffer.setTag(dwarf::DW_TAG_base_type);
Devang Patel2c4ceb12009-11-21 02:48:08 +0000925 addUInt(&Buffer, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
Bill Wendling0310d762009-05-15 09:23:25 +0000926 BTy.getEncoding());
927
928 // Add name if not anonymous or intermediate type.
Devang Patel65dbc902009-11-25 17:36:49 +0000929 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000930 addString(&Buffer, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Bill Wendling0310d762009-05-15 09:23:25 +0000931 uint64_t Size = BTy.getSizeInBits() >> 3;
Devang Patel2c4ceb12009-11-21 02:48:08 +0000932 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, Size);
Bill Wendling0310d762009-05-15 09:23:25 +0000933}
934
Devang Patel2c4ceb12009-11-21 02:48:08 +0000935/// constructTypeDIE - Construct derived type die from DIDerivedType.
Devang Patel8a241142009-12-09 18:24:21 +0000936void DwarfDebug::constructTypeDIE(DIE &Buffer, DIDerivedType DTy) {
Bill Wendling0310d762009-05-15 09:23:25 +0000937 // Get core information.
Devang Patel65dbc902009-11-25 17:36:49 +0000938 StringRef Name = DTy.getName();
Bill Wendling0310d762009-05-15 09:23:25 +0000939 uint64_t Size = DTy.getSizeInBits() >> 3;
940 unsigned Tag = DTy.getTag();
941
942 // FIXME - Workaround for templates.
943 if (Tag == dwarf::DW_TAG_inheritance) Tag = dwarf::DW_TAG_reference_type;
944
945 Buffer.setTag(Tag);
946
947 // Map to main type, void will not have a type.
948 DIType FromTy = DTy.getTypeDerivedFrom();
Devang Patel8a241142009-12-09 18:24:21 +0000949 addType(&Buffer, FromTy);
Bill Wendling0310d762009-05-15 09:23:25 +0000950
951 // Add name if not anonymous or intermediate type.
Devang Pateldeea5642009-11-30 23:56:56 +0000952 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000953 addString(&Buffer, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Bill Wendling0310d762009-05-15 09:23:25 +0000954
955 // Add size if non-zero (derived types might be zero-sized.)
956 if (Size)
Devang Patel2c4ceb12009-11-21 02:48:08 +0000957 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, Size);
Bill Wendling0310d762009-05-15 09:23:25 +0000958
959 // Add source line info if available and TyDesc is not a forward declaration.
Devang Patel05f6fa82009-11-23 18:43:37 +0000960 if (!DTy.isForwardDecl())
Devang Patel2c4ceb12009-11-21 02:48:08 +0000961 addSourceLine(&Buffer, &DTy);
Bill Wendling0310d762009-05-15 09:23:25 +0000962}
963
Devang Patel2c4ceb12009-11-21 02:48:08 +0000964/// constructTypeDIE - Construct type DIE from DICompositeType.
Devang Patel8a241142009-12-09 18:24:21 +0000965void DwarfDebug::constructTypeDIE(DIE &Buffer, DICompositeType CTy) {
Bill Wendling0310d762009-05-15 09:23:25 +0000966 // Get core information.
Devang Patel65dbc902009-11-25 17:36:49 +0000967 StringRef Name = CTy.getName();
Bill Wendling0310d762009-05-15 09:23:25 +0000968
969 uint64_t Size = CTy.getSizeInBits() >> 3;
970 unsigned Tag = CTy.getTag();
971 Buffer.setTag(Tag);
972
973 switch (Tag) {
974 case dwarf::DW_TAG_vector_type:
975 case dwarf::DW_TAG_array_type:
Devang Patel8a241142009-12-09 18:24:21 +0000976 constructArrayTypeDIE(Buffer, &CTy);
Bill Wendling0310d762009-05-15 09:23:25 +0000977 break;
978 case dwarf::DW_TAG_enumeration_type: {
979 DIArray Elements = CTy.getTypeArray();
980
981 // Add enumerators to enumeration type.
982 for (unsigned i = 0, N = Elements.getNumElements(); i < N; ++i) {
983 DIE *ElemDie = NULL;
Devang Patel2db49d72010-05-07 18:11:54 +0000984 DIDescriptor Enum(Elements.getElement(i));
Devang Patel3c91b052010-03-08 20:52:55 +0000985 if (Enum.isEnumerator()) {
Devang Patel2db49d72010-05-07 18:11:54 +0000986 ElemDie = constructEnumTypeDIE(DIEnumerator(Enum));
Devang Patel2c4ceb12009-11-21 02:48:08 +0000987 Buffer.addChild(ElemDie);
Devang Patelc5254722009-10-09 17:51:49 +0000988 }
Bill Wendling0310d762009-05-15 09:23:25 +0000989 }
990 }
991 break;
992 case dwarf::DW_TAG_subroutine_type: {
993 // Add return type.
994 DIArray Elements = CTy.getTypeArray();
995 DIDescriptor RTy = Elements.getElement(0);
Devang Patel2db49d72010-05-07 18:11:54 +0000996 addType(&Buffer, DIType(RTy));
Bill Wendling0310d762009-05-15 09:23:25 +0000997
998 // Add prototype flag.
Devang Patel2c4ceb12009-11-21 02:48:08 +0000999 addUInt(&Buffer, dwarf::DW_AT_prototyped, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001000
1001 // Add arguments.
1002 for (unsigned i = 1, N = Elements.getNumElements(); i < N; ++i) {
1003 DIE *Arg = new DIE(dwarf::DW_TAG_formal_parameter);
1004 DIDescriptor Ty = Elements.getElement(i);
Devang Patel2db49d72010-05-07 18:11:54 +00001005 addType(Arg, DIType(Ty));
Devang Patel2c4ceb12009-11-21 02:48:08 +00001006 Buffer.addChild(Arg);
Bill Wendling0310d762009-05-15 09:23:25 +00001007 }
1008 }
1009 break;
1010 case dwarf::DW_TAG_structure_type:
1011 case dwarf::DW_TAG_union_type:
1012 case dwarf::DW_TAG_class_type: {
1013 // Add elements to structure type.
1014 DIArray Elements = CTy.getTypeArray();
1015
1016 // A forward struct declared type may not have elements available.
Devang Patel3c91b052010-03-08 20:52:55 +00001017 unsigned N = Elements.getNumElements();
1018 if (N == 0)
Bill Wendling0310d762009-05-15 09:23:25 +00001019 break;
1020
1021 // Add elements to structure type.
Devang Patel3c91b052010-03-08 20:52:55 +00001022 for (unsigned i = 0; i < N; ++i) {
Bill Wendling0310d762009-05-15 09:23:25 +00001023 DIDescriptor Element = Elements.getElement(i);
1024 DIE *ElemDie = NULL;
Devang Patel3c91b052010-03-08 20:52:55 +00001025 if (Element.isSubprogram())
Devang Patel2db49d72010-05-07 18:11:54 +00001026 ElemDie = createSubprogramDIE(DISubprogram(Element));
Devang Patel3c91b052010-03-08 20:52:55 +00001027 else if (Element.isVariable()) {
Devang Patel2db49d72010-05-07 18:11:54 +00001028 DIVariable DV(Element);
Devang Patel1ee0cb92010-01-30 01:08:30 +00001029 ElemDie = new DIE(dwarf::DW_TAG_variable);
1030 addString(ElemDie, dwarf::DW_AT_name, dwarf::DW_FORM_string,
1031 DV.getName());
1032 addType(ElemDie, DV.getType());
1033 addUInt(ElemDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
1034 addUInt(ElemDie, dwarf::DW_AT_external, dwarf::DW_FORM_flag, 1);
1035 addSourceLine(ElemDie, &DV);
Devang Patel3c91b052010-03-08 20:52:55 +00001036 } else if (Element.isDerivedType())
Devang Patel2db49d72010-05-07 18:11:54 +00001037 ElemDie = createMemberDIE(DIDerivedType(Element));
Devang Patel3c91b052010-03-08 20:52:55 +00001038 else
1039 continue;
Devang Patel2c4ceb12009-11-21 02:48:08 +00001040 Buffer.addChild(ElemDie);
Bill Wendling0310d762009-05-15 09:23:25 +00001041 }
1042
Devang Patela1ba2692009-08-27 23:51:51 +00001043 if (CTy.isAppleBlockExtension())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001044 addUInt(&Buffer, dwarf::DW_AT_APPLE_block, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001045
1046 unsigned RLang = CTy.getRunTimeLang();
1047 if (RLang)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001048 addUInt(&Buffer, dwarf::DW_AT_APPLE_runtime_class,
Bill Wendling0310d762009-05-15 09:23:25 +00001049 dwarf::DW_FORM_data1, RLang);
Devang Patelb5544992010-01-26 21:16:06 +00001050
1051 DICompositeType ContainingType = CTy.getContainingType();
Devang Patel2db49d72010-05-07 18:11:54 +00001052 if (DIDescriptor(ContainingType).isCompositeType())
Devang Patelb5544992010-01-26 21:16:06 +00001053 addDIEEntry(&Buffer, dwarf::DW_AT_containing_type, dwarf::DW_FORM_ref4,
Devang Patel2db49d72010-05-07 18:11:54 +00001054 getOrCreateTypeDIE(DIType(ContainingType)));
Bill Wendling0310d762009-05-15 09:23:25 +00001055 break;
1056 }
1057 default:
1058 break;
1059 }
1060
1061 // Add name if not anonymous or intermediate type.
Devang Patel65dbc902009-11-25 17:36:49 +00001062 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001063 addString(&Buffer, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Bill Wendling0310d762009-05-15 09:23:25 +00001064
Devang Patel8cbb6122010-01-29 18:34:58 +00001065 if (Tag == dwarf::DW_TAG_enumeration_type || Tag == dwarf::DW_TAG_class_type ||
Bill Wendling0310d762009-05-15 09:23:25 +00001066 Tag == dwarf::DW_TAG_structure_type || Tag == dwarf::DW_TAG_union_type) {
1067 // Add size if non-zero (derived types might be zero-sized.)
1068 if (Size)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001069 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, Size);
Bill Wendling0310d762009-05-15 09:23:25 +00001070 else {
1071 // Add zero size if it is not a forward declaration.
1072 if (CTy.isForwardDecl())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001073 addUInt(&Buffer, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001074 else
Devang Patel2c4ceb12009-11-21 02:48:08 +00001075 addUInt(&Buffer, dwarf::DW_AT_byte_size, 0, 0);
Bill Wendling0310d762009-05-15 09:23:25 +00001076 }
1077
1078 // Add source line info if available.
1079 if (!CTy.isForwardDecl())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001080 addSourceLine(&Buffer, &CTy);
Bill Wendling0310d762009-05-15 09:23:25 +00001081 }
1082}
1083
Devang Patel2c4ceb12009-11-21 02:48:08 +00001084/// constructSubrangeDIE - Construct subrange DIE from DISubrange.
1085void DwarfDebug::constructSubrangeDIE(DIE &Buffer, DISubrange SR, DIE *IndexTy){
Bill Wendling0310d762009-05-15 09:23:25 +00001086 int64_t L = SR.getLo();
1087 int64_t H = SR.getHi();
1088 DIE *DW_Subrange = new DIE(dwarf::DW_TAG_subrange_type);
1089
Devang Patel2c4ceb12009-11-21 02:48:08 +00001090 addDIEEntry(DW_Subrange, dwarf::DW_AT_type, dwarf::DW_FORM_ref4, IndexTy);
Devang Patel6325a532009-08-14 20:59:16 +00001091 if (L)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001092 addSInt(DW_Subrange, dwarf::DW_AT_lower_bound, 0, L);
Devang Pateld55224c2009-12-04 23:10:24 +00001093 addSInt(DW_Subrange, dwarf::DW_AT_upper_bound, 0, H);
Bill Wendling0310d762009-05-15 09:23:25 +00001094
Devang Patel2c4ceb12009-11-21 02:48:08 +00001095 Buffer.addChild(DW_Subrange);
Bill Wendling0310d762009-05-15 09:23:25 +00001096}
1097
Devang Patel2c4ceb12009-11-21 02:48:08 +00001098/// constructArrayTypeDIE - Construct array type DIE from DICompositeType.
Devang Patel8a241142009-12-09 18:24:21 +00001099void DwarfDebug::constructArrayTypeDIE(DIE &Buffer,
Bill Wendling0310d762009-05-15 09:23:25 +00001100 DICompositeType *CTy) {
1101 Buffer.setTag(dwarf::DW_TAG_array_type);
1102 if (CTy->getTag() == dwarf::DW_TAG_vector_type)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001103 addUInt(&Buffer, dwarf::DW_AT_GNU_vector, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001104
1105 // Emit derived type.
Devang Patel8a241142009-12-09 18:24:21 +00001106 addType(&Buffer, CTy->getTypeDerivedFrom());
Bill Wendling0310d762009-05-15 09:23:25 +00001107 DIArray Elements = CTy->getTypeArray();
1108
Devang Patel6f01d9c2009-11-21 00:31:03 +00001109 // Get an anonymous type for index type.
Devang Patel163a9f72010-05-10 22:49:55 +00001110 CompileUnit *TheCU = getCompileUnit(*CTy);
1111 DIE *IdxTy = TheCU->getIndexTyDie();
Devang Patel6f01d9c2009-11-21 00:31:03 +00001112 if (!IdxTy) {
1113 // Construct an anonymous type for index type.
1114 IdxTy = new DIE(dwarf::DW_TAG_base_type);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001115 addUInt(IdxTy, dwarf::DW_AT_byte_size, 0, sizeof(int32_t));
1116 addUInt(IdxTy, dwarf::DW_AT_encoding, dwarf::DW_FORM_data1,
Devang Patel6f01d9c2009-11-21 00:31:03 +00001117 dwarf::DW_ATE_signed);
Devang Patel163a9f72010-05-10 22:49:55 +00001118 TheCU->addDie(IdxTy);
1119 TheCU->setIndexTyDie(IdxTy);
Devang Patel6f01d9c2009-11-21 00:31:03 +00001120 }
Bill Wendling0310d762009-05-15 09:23:25 +00001121
1122 // Add subranges to array type.
1123 for (unsigned i = 0, N = Elements.getNumElements(); i < N; ++i) {
1124 DIDescriptor Element = Elements.getElement(i);
1125 if (Element.getTag() == dwarf::DW_TAG_subrange_type)
Devang Patel2db49d72010-05-07 18:11:54 +00001126 constructSubrangeDIE(Buffer, DISubrange(Element), IdxTy);
Bill Wendling0310d762009-05-15 09:23:25 +00001127 }
1128}
1129
Devang Patel2c4ceb12009-11-21 02:48:08 +00001130/// constructEnumTypeDIE - Construct enum type DIE from DIEnumerator.
Devang Patel3c91b052010-03-08 20:52:55 +00001131DIE *DwarfDebug::constructEnumTypeDIE(DIEnumerator ETy) {
Bill Wendling0310d762009-05-15 09:23:25 +00001132 DIE *Enumerator = new DIE(dwarf::DW_TAG_enumerator);
Devang Patel3c91b052010-03-08 20:52:55 +00001133 StringRef Name = ETy.getName();
Devang Patel2c4ceb12009-11-21 02:48:08 +00001134 addString(Enumerator, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Devang Patel3c91b052010-03-08 20:52:55 +00001135 int64_t Value = ETy.getEnumValue();
Devang Patel2c4ceb12009-11-21 02:48:08 +00001136 addSInt(Enumerator, dwarf::DW_AT_const_value, dwarf::DW_FORM_sdata, Value);
Bill Wendling0310d762009-05-15 09:23:25 +00001137 return Enumerator;
1138}
1139
Devang Patel351ca332010-01-05 01:46:14 +00001140/// getRealLinkageName - If special LLVM prefix that is used to inform the asm
1141/// printer to not emit usual symbol prefix before the symbol name is used then
1142/// return linkage name after skipping this special LLVM prefix.
1143static StringRef getRealLinkageName(StringRef LinkageName) {
1144 char One = '\1';
1145 if (LinkageName.startswith(StringRef(&One, 1)))
1146 return LinkageName.substr(1);
1147 return LinkageName;
1148}
1149
Devang Patel2c4ceb12009-11-21 02:48:08 +00001150/// createGlobalVariableDIE - Create new DIE using GV.
Devang Patel8a241142009-12-09 18:24:21 +00001151DIE *DwarfDebug::createGlobalVariableDIE(const DIGlobalVariable &GV) {
Jim Grosbach7ab38df2009-11-22 19:20:36 +00001152 // If the global variable was optmized out then no need to create debug info
1153 // entry.
Devang Patel84c73e92009-11-06 17:58:12 +00001154 if (!GV.getGlobal()) return NULL;
Devang Patel65dbc902009-11-25 17:36:49 +00001155 if (GV.getDisplayName().empty()) return NULL;
Devang Patel465c3be2009-11-06 01:30:04 +00001156
Bill Wendling0310d762009-05-15 09:23:25 +00001157 DIE *GVDie = new DIE(dwarf::DW_TAG_variable);
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001158 addString(GVDie, dwarf::DW_AT_name, dwarf::DW_FORM_string,
Devang Patel5ccdd102009-09-29 18:40:58 +00001159 GV.getDisplayName());
1160
Devang Patel65dbc902009-11-25 17:36:49 +00001161 StringRef LinkageName = GV.getLinkageName();
Devang Patel351ca332010-01-05 01:46:14 +00001162 if (!LinkageName.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001163 addString(GVDie, dwarf::DW_AT_MIPS_linkage_name, dwarf::DW_FORM_string,
Devang Patel351ca332010-01-05 01:46:14 +00001164 getRealLinkageName(LinkageName));
1165
Devang Patel8a241142009-12-09 18:24:21 +00001166 addType(GVDie, GV.getType());
Bill Wendling0310d762009-05-15 09:23:25 +00001167 if (!GV.isLocalToUnit())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001168 addUInt(GVDie, dwarf::DW_AT_external, dwarf::DW_FORM_flag, 1);
1169 addSourceLine(GVDie, &GV);
Devang Patelb71a16d2009-10-05 23:22:08 +00001170
Bill Wendling0310d762009-05-15 09:23:25 +00001171 return GVDie;
1172}
1173
Devang Patel2c4ceb12009-11-21 02:48:08 +00001174/// createMemberDIE - Create new member DIE.
Devang Patel8a241142009-12-09 18:24:21 +00001175DIE *DwarfDebug::createMemberDIE(const DIDerivedType &DT) {
Bill Wendling0310d762009-05-15 09:23:25 +00001176 DIE *MemberDie = new DIE(DT.getTag());
Devang Patel65dbc902009-11-25 17:36:49 +00001177 StringRef Name = DT.getName();
1178 if (!Name.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001179 addString(MemberDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
Devang Patel65dbc902009-11-25 17:36:49 +00001180
Devang Patel8a241142009-12-09 18:24:21 +00001181 addType(MemberDie, DT.getTypeDerivedFrom());
Bill Wendling0310d762009-05-15 09:23:25 +00001182
Devang Patel2c4ceb12009-11-21 02:48:08 +00001183 addSourceLine(MemberDie, &DT);
Bill Wendling0310d762009-05-15 09:23:25 +00001184
Benjamin Kramer345ef342010-03-31 19:34:01 +00001185 DIEBlock *MemLocationDie = new (DIEValueAllocator) DIEBlock();
Devang Patel2c4ceb12009-11-21 02:48:08 +00001186 addUInt(MemLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus_uconst);
Devang Patel33db5082009-11-04 22:06:12 +00001187
Bill Wendling0310d762009-05-15 09:23:25 +00001188 uint64_t Size = DT.getSizeInBits();
Devang Patel61ecbd12009-11-04 23:48:00 +00001189 uint64_t FieldSize = DT.getOriginalTypeSize();
Bill Wendling0310d762009-05-15 09:23:25 +00001190
1191 if (Size != FieldSize) {
1192 // Handle bitfield.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001193 addUInt(MemberDie, dwarf::DW_AT_byte_size, 0, DT.getOriginalTypeSize()>>3);
1194 addUInt(MemberDie, dwarf::DW_AT_bit_size, 0, DT.getSizeInBits());
Bill Wendling0310d762009-05-15 09:23:25 +00001195
1196 uint64_t Offset = DT.getOffsetInBits();
Bill Wendling0310d762009-05-15 09:23:25 +00001197 uint64_t AlignMask = ~(DT.getAlignInBits() - 1);
1198 uint64_t HiMark = (Offset + FieldSize) & AlignMask;
Benjamin Kramer3d594fd2010-01-07 17:50:57 +00001199 uint64_t FieldOffset = (HiMark - FieldSize);
Bill Wendling0310d762009-05-15 09:23:25 +00001200 Offset -= FieldOffset;
1201
1202 // Maybe we need to work from the other end.
Chris Lattnerd38fee82010-04-05 00:13:49 +00001203 if (Asm->getTargetData().isLittleEndian())
1204 Offset = FieldSize - (Offset + Size);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001205 addUInt(MemberDie, dwarf::DW_AT_bit_offset, 0, Offset);
Bill Wendling0310d762009-05-15 09:23:25 +00001206
Devang Patel33db5082009-11-04 22:06:12 +00001207 // Here WD_AT_data_member_location points to the anonymous
1208 // field that includes this bit field.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001209 addUInt(MemLocationDie, 0, dwarf::DW_FORM_udata, FieldOffset >> 3);
Devang Patel33db5082009-11-04 22:06:12 +00001210
1211 } else
1212 // This is not a bitfield.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001213 addUInt(MemLocationDie, 0, dwarf::DW_FORM_udata, DT.getOffsetInBits() >> 3);
Devang Patel33db5082009-11-04 22:06:12 +00001214
Devang Patelc1dc8ff2010-02-03 20:08:48 +00001215 if (DT.getTag() == dwarf::DW_TAG_inheritance
1216 && DT.isVirtual()) {
1217
1218 // For C++, virtual base classes are not at fixed offset. Use following
1219 // expression to extract appropriate offset from vtable.
1220 // BaseAddr = ObAddr + *((*ObAddr) - Offset)
1221
Benjamin Kramer345ef342010-03-31 19:34:01 +00001222 DIEBlock *VBaseLocationDie = new (DIEValueAllocator) DIEBlock();
Devang Patelc1dc8ff2010-02-03 20:08:48 +00001223 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_dup);
1224 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
1225 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
1226 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_udata, DT.getOffsetInBits());
1227 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_minus);
1228 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_deref);
1229 addUInt(VBaseLocationDie, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_plus);
1230
1231 addBlock(MemberDie, dwarf::DW_AT_data_member_location, 0,
1232 VBaseLocationDie);
1233 } else
1234 addBlock(MemberDie, dwarf::DW_AT_data_member_location, 0, MemLocationDie);
Bill Wendling0310d762009-05-15 09:23:25 +00001235
1236 if (DT.isProtected())
Devang Patel5d11eb02009-12-03 19:11:07 +00001237 addUInt(MemberDie, dwarf::DW_AT_accessibility, dwarf::DW_FORM_flag,
Bill Wendling0310d762009-05-15 09:23:25 +00001238 dwarf::DW_ACCESS_protected);
1239 else if (DT.isPrivate())
Devang Patel5d11eb02009-12-03 19:11:07 +00001240 addUInt(MemberDie, dwarf::DW_AT_accessibility, dwarf::DW_FORM_flag,
Bill Wendling0310d762009-05-15 09:23:25 +00001241 dwarf::DW_ACCESS_private);
Devang Patel5d11eb02009-12-03 19:11:07 +00001242 else if (DT.getTag() == dwarf::DW_TAG_inheritance)
1243 addUInt(MemberDie, dwarf::DW_AT_accessibility, dwarf::DW_FORM_flag,
1244 dwarf::DW_ACCESS_public);
1245 if (DT.isVirtual())
1246 addUInt(MemberDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_flag,
1247 dwarf::DW_VIRTUALITY_virtual);
Bill Wendling0310d762009-05-15 09:23:25 +00001248 return MemberDie;
1249}
1250
Devang Patelffe966c2009-12-14 16:18:45 +00001251/// createSubprogramDIE - Create new DIE using SP.
1252DIE *DwarfDebug::createSubprogramDIE(const DISubprogram &SP, bool MakeDecl) {
Devang Patel163a9f72010-05-10 22:49:55 +00001253 CompileUnit *SPCU = getCompileUnit(SP);
1254 DIE *SPDie = SPCU->getDIE(SP);
Devang Patelffe966c2009-12-14 16:18:45 +00001255 if (SPDie)
1256 return SPDie;
1257
1258 SPDie = new DIE(dwarf::DW_TAG_subprogram);
Devang Patel1eac3e72010-03-02 17:58:15 +00001259 // Constructors and operators for anonymous aggregates do not have names.
Devang Patel6b506cb2010-03-02 01:26:20 +00001260 if (!SP.getName().empty())
1261 addString(SPDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, SP.getName());
Bill Wendling0310d762009-05-15 09:23:25 +00001262
Devang Patel65dbc902009-11-25 17:36:49 +00001263 StringRef LinkageName = SP.getLinkageName();
Devang Patel351ca332010-01-05 01:46:14 +00001264 if (!LinkageName.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001265 addString(SPDie, dwarf::DW_AT_MIPS_linkage_name, dwarf::DW_FORM_string,
Devang Patel351ca332010-01-05 01:46:14 +00001266 getRealLinkageName(LinkageName));
1267
Devang Patel2c4ceb12009-11-21 02:48:08 +00001268 addSourceLine(SPDie, &SP);
Bill Wendling0310d762009-05-15 09:23:25 +00001269
Bill Wendling0310d762009-05-15 09:23:25 +00001270 // Add prototyped tag, if C or ObjC.
1271 unsigned Lang = SP.getCompileUnit().getLanguage();
1272 if (Lang == dwarf::DW_LANG_C99 || Lang == dwarf::DW_LANG_C89 ||
1273 Lang == dwarf::DW_LANG_ObjC)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001274 addUInt(SPDie, dwarf::DW_AT_prototyped, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001275
1276 // Add Return Type.
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001277 DICompositeType SPTy = SP.getType();
1278 DIArray Args = SPTy.getTypeArray();
Bill Wendling0310d762009-05-15 09:23:25 +00001279 unsigned SPTag = SPTy.getTag();
Devang Patel5d11eb02009-12-03 19:11:07 +00001280
Devang Patel3c91b052010-03-08 20:52:55 +00001281 if (Args.getNumElements() == 0 || SPTag != dwarf::DW_TAG_subroutine_type)
Devang Patel8a241142009-12-09 18:24:21 +00001282 addType(SPDie, SPTy);
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001283 else
Devang Patel2db49d72010-05-07 18:11:54 +00001284 addType(SPDie, DIType(Args.getElement(0)));
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001285
Devang Patel5d11eb02009-12-03 19:11:07 +00001286 unsigned VK = SP.getVirtuality();
1287 if (VK) {
1288 addUInt(SPDie, dwarf::DW_AT_virtuality, dwarf::DW_FORM_flag, VK);
Benjamin Kramer345ef342010-03-31 19:34:01 +00001289 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Devang Patel5d11eb02009-12-03 19:11:07 +00001290 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_constu);
1291 addUInt(Block, 0, dwarf::DW_FORM_data1, SP.getVirtualIndex());
1292 addBlock(SPDie, dwarf::DW_AT_vtable_elem_location, 0, Block);
Devang Patel622b0262010-01-19 06:19:05 +00001293 ContainingTypeMap.insert(std::make_pair(SPDie,
Devang Patel2db49d72010-05-07 18:11:54 +00001294 SP.getContainingType()));
Devang Patel5d11eb02009-12-03 19:11:07 +00001295 }
1296
Devang Patelffe966c2009-12-14 16:18:45 +00001297 if (MakeDecl || !SP.isDefinition()) {
Devang Patel2c4ceb12009-11-21 02:48:08 +00001298 addUInt(SPDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
Bill Wendling0310d762009-05-15 09:23:25 +00001299
1300 // Add arguments. Do not add arguments for subprogram definition. They will
Devang Patel1d5cc1d2009-12-03 01:25:38 +00001301 // be handled while processing variables.
1302 DICompositeType SPTy = SP.getType();
1303 DIArray Args = SPTy.getTypeArray();
1304 unsigned SPTag = SPTy.getTag();
1305
Bill Wendling0310d762009-05-15 09:23:25 +00001306 if (SPTag == dwarf::DW_TAG_subroutine_type)
1307 for (unsigned i = 1, N = Args.getNumElements(); i < N; ++i) {
1308 DIE *Arg = new DIE(dwarf::DW_TAG_formal_parameter);
Devang Patel2db49d72010-05-07 18:11:54 +00001309 DIType ATy = DIType(DIType(Args.getElement(i)));
Devang Patelb4645642010-02-06 01:02:37 +00001310 addType(Arg, ATy);
1311 if (ATy.isArtificial())
1312 addUInt(Arg, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001313 SPDie->addChild(Arg);
Bill Wendling0310d762009-05-15 09:23:25 +00001314 }
1315 }
1316
Devang Patel4e0d19d2010-02-03 19:57:19 +00001317 if (SP.isArtificial())
1318 addUInt(SPDie, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
1319
Devang Patelccff8122010-04-30 19:38:23 +00001320 if (!SP.isLocalToUnit())
1321 addUInt(SPDie, dwarf::DW_AT_external, dwarf::DW_FORM_flag, 1);
Devang Patel2a4a3b72010-04-19 19:14:02 +00001322
Devang Patelccff8122010-04-30 19:38:23 +00001323 if (SP.isOptimized())
1324 addUInt(SPDie, dwarf::DW_AT_APPLE_optimized, dwarf::DW_FORM_flag, 1);
1325
Devang Patelccff8122010-04-30 19:38:23 +00001326 // DW_TAG_inlined_subroutine may refer to this DIE.
Devang Patel163a9f72010-05-10 22:49:55 +00001327 SPCU->insertDIE(SP, SPDie);
Devang Patelccff8122010-04-30 19:38:23 +00001328
Bill Wendling0310d762009-05-15 09:23:25 +00001329 return SPDie;
1330}
1331
Devang Patele9f8f5e2010-05-07 20:54:48 +00001332DbgScope *DwarfDebug::getOrCreateAbstractScope(const MDNode *N) {
Chris Lattnered7a77b2010-03-31 05:36:29 +00001333 assert(N && "Invalid Scope encoding!");
Devang Patel53bb5c92009-11-10 23:06:00 +00001334
1335 DbgScope *AScope = AbstractScopes.lookup(N);
1336 if (AScope)
1337 return AScope;
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001338
Devang Patel53bb5c92009-11-10 23:06:00 +00001339 DbgScope *Parent = NULL;
1340
1341 DIDescriptor Scope(N);
1342 if (Scope.isLexicalBlock()) {
1343 DILexicalBlock DB(N);
1344 DIDescriptor ParentDesc = DB.getContext();
Devang Patel2db49d72010-05-07 18:11:54 +00001345 Parent = getOrCreateAbstractScope(ParentDesc);
Devang Patel53bb5c92009-11-10 23:06:00 +00001346 }
1347
1348 AScope = new DbgScope(Parent, DIDescriptor(N), NULL);
1349
1350 if (Parent)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001351 Parent->addScope(AScope);
Devang Patel53bb5c92009-11-10 23:06:00 +00001352 AScope->setAbstractScope();
1353 AbstractScopes[N] = AScope;
1354 if (DIDescriptor(N).isSubprogram())
1355 AbstractScopesList.push_back(AScope);
1356 return AScope;
1357}
Devang Patelaf9e8472009-10-01 20:31:14 +00001358
Devang Patel5f094002010-04-06 23:53:48 +00001359/// isSubprogramContext - Return true if Context is either a subprogram
1360/// or another context nested inside a subprogram.
Devang Patele9f8f5e2010-05-07 20:54:48 +00001361static bool isSubprogramContext(const MDNode *Context) {
Devang Patel5f094002010-04-06 23:53:48 +00001362 if (!Context)
1363 return false;
1364 DIDescriptor D(Context);
1365 if (D.isSubprogram())
1366 return true;
1367 if (D.isType())
Devang Patel2db49d72010-05-07 18:11:54 +00001368 return isSubprogramContext(DIType(Context).getContext());
Devang Patel5f094002010-04-06 23:53:48 +00001369 return false;
1370}
1371
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001372/// updateSubprogramScopeDIE - Find DIE for the given subprogram and
Devang Patel2c4ceb12009-11-21 02:48:08 +00001373/// attach appropriate DW_AT_low_pc and DW_AT_high_pc attributes.
1374/// If there are global variables in this scope then create and insert
1375/// DIEs for these variables.
Devang Patele9f8f5e2010-05-07 20:54:48 +00001376DIE *DwarfDebug::updateSubprogramScopeDIE(const MDNode *SPNode) {
Devang Patel163a9f72010-05-10 22:49:55 +00001377 CompileUnit *SPCU = getCompileUnit(SPNode);
1378 DIE *SPDie = SPCU->getDIE(SPNode);
Chris Lattnerd38fee82010-04-05 00:13:49 +00001379 assert(SPDie && "Unable to find subprogram DIE!");
1380 DISubprogram SP(SPNode);
Chris Lattner206d61e2010-03-13 07:26:18 +00001381
Chris Lattnerd38fee82010-04-05 00:13:49 +00001382 // There is not any need to generate specification DIE for a function
1383 // defined at compile unit level. If a function is defined inside another
1384 // function then gdb prefers the definition at top level and but does not
1385 // expect specification DIE in parent function. So avoid creating
1386 // specification DIE for a function defined inside a function.
1387 if (SP.isDefinition() && !SP.getContext().isCompileUnit() &&
Devang Patel5f094002010-04-06 23:53:48 +00001388 !SP.getContext().isFile() &&
Devang Patel2db49d72010-05-07 18:11:54 +00001389 !isSubprogramContext(SP.getContext())) {
Chris Lattnerd38fee82010-04-05 00:13:49 +00001390 addUInt(SPDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
1391
1392 // Add arguments.
1393 DICompositeType SPTy = SP.getType();
1394 DIArray Args = SPTy.getTypeArray();
1395 unsigned SPTag = SPTy.getTag();
1396 if (SPTag == dwarf::DW_TAG_subroutine_type)
1397 for (unsigned i = 1, N = Args.getNumElements(); i < N; ++i) {
1398 DIE *Arg = new DIE(dwarf::DW_TAG_formal_parameter);
Devang Patel2db49d72010-05-07 18:11:54 +00001399 DIType ATy = DIType(DIType(Args.getElement(i)));
Chris Lattnerd38fee82010-04-05 00:13:49 +00001400 addType(Arg, ATy);
1401 if (ATy.isArtificial())
1402 addUInt(Arg, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
1403 SPDie->addChild(Arg);
1404 }
1405 DIE *SPDeclDie = SPDie;
1406 SPDie = new DIE(dwarf::DW_TAG_subprogram);
1407 addDIEEntry(SPDie, dwarf::DW_AT_specification, dwarf::DW_FORM_ref4,
1408 SPDeclDie);
Devang Patel163a9f72010-05-10 22:49:55 +00001409 SPCU->addDie(SPDie);
Chris Lattnerd38fee82010-04-05 00:13:49 +00001410 }
1411
1412 addLabel(SPDie, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr,
1413 Asm->GetTempSymbol("func_begin", Asm->getFunctionNumber()));
1414 addLabel(SPDie, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr,
1415 Asm->GetTempSymbol("func_end", Asm->getFunctionNumber()));
1416 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
1417 MachineLocation Location(RI->getFrameRegister(*Asm->MF));
1418 addAddress(SPDie, dwarf::DW_AT_frame_base, Location);
Devang Patelb4645642010-02-06 01:02:37 +00001419
Chris Lattnerd38fee82010-04-05 00:13:49 +00001420 return SPDie;
Devang Patel53bb5c92009-11-10 23:06:00 +00001421}
1422
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001423/// constructLexicalScope - Construct new DW_TAG_lexical_block
Devang Patel2c4ceb12009-11-21 02:48:08 +00001424/// for this scope and attach DW_AT_low_pc/DW_AT_high_pc labels.
1425DIE *DwarfDebug::constructLexicalScopeDIE(DbgScope *Scope) {
Devang Pateleac9c072010-04-27 19:46:33 +00001426
1427 DIE *ScopeDIE = new DIE(dwarf::DW_TAG_lexical_block);
1428 if (Scope->isAbstractScope())
1429 return ScopeDIE;
1430
1431 const SmallVector<DbgRange, 4> &Ranges = Scope->getRanges();
1432 if (Ranges.empty())
1433 return 0;
1434
1435 SmallVector<DbgRange, 4>::const_iterator RI = Ranges.begin();
1436 if (Ranges.size() > 1) {
1437 // .debug_range section has not been laid out yet. Emit offset in
1438 // .debug_range as a uint, size 4, for now. emitDIE will handle
1439 // DW_AT_ranges appropriately.
1440 addUInt(ScopeDIE, dwarf::DW_AT_ranges, dwarf::DW_FORM_data4,
1441 DebugRangeSymbols.size() * Asm->getTargetData().getPointerSize());
1442 for (SmallVector<DbgRange, 4>::const_iterator RI = Ranges.begin(),
1443 RE = Ranges.end(); RI != RE; ++RI) {
1444 DebugRangeSymbols.push_back(LabelsBeforeInsn.lookup(RI->first));
1445 DebugRangeSymbols.push_back(LabelsAfterInsn.lookup(RI->second));
1446 }
1447 DebugRangeSymbols.push_back(NULL);
1448 DebugRangeSymbols.push_back(NULL);
1449 return ScopeDIE;
1450 }
1451
1452 MCSymbol *Start = LabelsBeforeInsn.lookup(RI->first);
1453 MCSymbol *End = LabelsAfterInsn.lookup(RI->second);
1454
Devang Patelaead63c2010-03-29 22:59:58 +00001455 if (Start == 0 || End == 0) return 0;
Devang Patel53bb5c92009-11-10 23:06:00 +00001456
Chris Lattnerb7db7332010-03-09 01:58:53 +00001457 assert(Start->isDefined() && "Invalid starting label for an inlined scope!");
1458 assert(End->isDefined() && "Invalid end label for an inlined scope!");
Chris Lattnera34ec2292010-03-09 01:51:43 +00001459
Devang Pateleac9c072010-04-27 19:46:33 +00001460 addLabel(ScopeDIE, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr, Start);
1461 addLabel(ScopeDIE, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr, End);
Devang Patel53bb5c92009-11-10 23:06:00 +00001462
1463 return ScopeDIE;
1464}
1465
Devang Patel2c4ceb12009-11-21 02:48:08 +00001466/// constructInlinedScopeDIE - This scope represents inlined body of
1467/// a function. Construct DIE to represent this concrete inlined copy
1468/// of the function.
1469DIE *DwarfDebug::constructInlinedScopeDIE(DbgScope *Scope) {
Devang Pateleac9c072010-04-27 19:46:33 +00001470
1471 const SmallVector<DbgRange, 4> &Ranges = Scope->getRanges();
1472 assert (Ranges.empty() == false
1473 && "DbgScope does not have instruction markers!");
1474
1475 // FIXME : .debug_inlined section specification does not clearly state how
1476 // to emit inlined scope that is split into multiple instruction ranges.
1477 // For now, use first instruction range and emit low_pc/high_pc pair and
1478 // corresponding .debug_inlined section entry for this pair.
1479 SmallVector<DbgRange, 4>::const_iterator RI = Ranges.begin();
1480 MCSymbol *StartLabel = LabelsBeforeInsn.lookup(RI->first);
1481 MCSymbol *EndLabel = LabelsAfterInsn.lookup(RI->second);
1482
1483 if (StartLabel == 0 || EndLabel == 0) {
1484 assert (0 && "Unexpected Start and End labels for a inlined scope!");
1485 return 0;
1486 }
Chris Lattnerb7db7332010-03-09 01:58:53 +00001487 assert(StartLabel->isDefined() &&
Chris Lattnera34ec2292010-03-09 01:51:43 +00001488 "Invalid starting label for an inlined scope!");
Chris Lattnerb7db7332010-03-09 01:58:53 +00001489 assert(EndLabel->isDefined() &&
Chris Lattnera34ec2292010-03-09 01:51:43 +00001490 "Invalid end label for an inlined scope!");
Devang Pateleac9c072010-04-27 19:46:33 +00001491
Devang Patel3c91b052010-03-08 20:52:55 +00001492 if (!Scope->getScopeNode())
Devang Patel0ef3fa62010-03-08 19:20:38 +00001493 return NULL;
Devang Patel3c91b052010-03-08 20:52:55 +00001494 DIScope DS(Scope->getScopeNode());
Devang Patel53bb5c92009-11-10 23:06:00 +00001495 DIE *ScopeDIE = new DIE(dwarf::DW_TAG_inlined_subroutine);
1496
Devang Patel2db49d72010-05-07 18:11:54 +00001497 DISubprogram InlinedSP = getDISubprogram(DS);
Devang Patel163a9f72010-05-10 22:49:55 +00001498 CompileUnit *TheCU = getCompileUnit(InlinedSP);
1499 DIE *OriginDIE = TheCU->getDIE(InlinedSP);
Chris Lattnered7a77b2010-03-31 05:36:29 +00001500 assert(OriginDIE && "Unable to find Origin DIE!");
Devang Patel2c4ceb12009-11-21 02:48:08 +00001501 addDIEEntry(ScopeDIE, dwarf::DW_AT_abstract_origin,
Devang Patel53bb5c92009-11-10 23:06:00 +00001502 dwarf::DW_FORM_ref4, OriginDIE);
1503
Chris Lattner6ed0f902010-03-09 00:31:02 +00001504 addLabel(ScopeDIE, dwarf::DW_AT_low_pc, dwarf::DW_FORM_addr, StartLabel);
Chris Lattnerb7db7332010-03-09 01:58:53 +00001505 addLabel(ScopeDIE, dwarf::DW_AT_high_pc, dwarf::DW_FORM_addr, EndLabel);
Devang Patel53bb5c92009-11-10 23:06:00 +00001506
1507 InlinedSubprogramDIEs.insert(OriginDIE);
1508
1509 // Track the start label for this inlined function.
Devang Patele9f8f5e2010-05-07 20:54:48 +00001510 DenseMap<const MDNode *, SmallVector<InlineInfoLabels, 4> >::iterator
Devang Patel2db49d72010-05-07 18:11:54 +00001511 I = InlineInfo.find(InlinedSP);
Devang Patel53bb5c92009-11-10 23:06:00 +00001512
1513 if (I == InlineInfo.end()) {
Devang Patel2db49d72010-05-07 18:11:54 +00001514 InlineInfo[InlinedSP].push_back(std::make_pair(StartLabel,
Jim Grosbach7ab38df2009-11-22 19:20:36 +00001515 ScopeDIE));
Devang Patel2db49d72010-05-07 18:11:54 +00001516 InlinedSPNodes.push_back(InlinedSP);
Devang Patel53bb5c92009-11-10 23:06:00 +00001517 } else
Chris Lattner6ed0f902010-03-09 00:31:02 +00001518 I->second.push_back(std::make_pair(StartLabel, ScopeDIE));
Devang Patel53bb5c92009-11-10 23:06:00 +00001519
Devang Patel53bb5c92009-11-10 23:06:00 +00001520 DILocation DL(Scope->getInlinedAt());
Devang Patel163a9f72010-05-10 22:49:55 +00001521 addUInt(ScopeDIE, dwarf::DW_AT_call_file, 0, TheCU->getID());
Devang Patel2c4ceb12009-11-21 02:48:08 +00001522 addUInt(ScopeDIE, dwarf::DW_AT_call_line, 0, DL.getLineNumber());
Devang Patel53bb5c92009-11-10 23:06:00 +00001523
1524 return ScopeDIE;
1525}
1526
Devang Patel2c4ceb12009-11-21 02:48:08 +00001527
1528/// constructVariableDIE - Construct a DIE for the given DbgVariable.
Devang Patel8a241142009-12-09 18:24:21 +00001529DIE *DwarfDebug::constructVariableDIE(DbgVariable *DV, DbgScope *Scope) {
Devang Patel53bb5c92009-11-10 23:06:00 +00001530 // Get the descriptor.
1531 const DIVariable &VD = DV->getVariable();
Devang Patel65dbc902009-11-25 17:36:49 +00001532 StringRef Name = VD.getName();
1533 if (Name.empty())
Devang Patel3fb6bd62009-11-13 02:25:26 +00001534 return NULL;
Devang Patel53bb5c92009-11-10 23:06:00 +00001535
1536 // Translate tag to proper Dwarf tag. The result variable is dropped for
1537 // now.
1538 unsigned Tag;
1539 switch (VD.getTag()) {
1540 case dwarf::DW_TAG_return_variable:
1541 return NULL;
1542 case dwarf::DW_TAG_arg_variable:
1543 Tag = dwarf::DW_TAG_formal_parameter;
1544 break;
1545 case dwarf::DW_TAG_auto_variable: // fall thru
1546 default:
1547 Tag = dwarf::DW_TAG_variable;
1548 break;
1549 }
1550
1551 // Define variable debug information entry.
1552 DIE *VariableDie = new DIE(Tag);
1553
Devang Patel53bb5c92009-11-10 23:06:00 +00001554 DIE *AbsDIE = NULL;
Devang Patel26c1e562010-05-20 16:36:41 +00001555 DenseMap<const DbgVariable *, const DbgVariable *>::iterator
1556 V2AVI = VarToAbstractVarMap.find(DV);
1557 if (V2AVI != VarToAbstractVarMap.end())
1558 AbsDIE = V2AVI->second->getDIE();
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001559
Devang Patel26c1e562010-05-20 16:36:41 +00001560 if (AbsDIE)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001561 addDIEEntry(VariableDie, dwarf::DW_AT_abstract_origin,
Devang Patel53bb5c92009-11-10 23:06:00 +00001562 dwarf::DW_FORM_ref4, AbsDIE);
Devang Patel53bb5c92009-11-10 23:06:00 +00001563 else {
Devang Patel2c4ceb12009-11-21 02:48:08 +00001564 addString(VariableDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, Name);
1565 addSourceLine(VariableDie, &VD);
Devang Patel53bb5c92009-11-10 23:06:00 +00001566
1567 // Add variable type.
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001568 // FIXME: isBlockByrefVariable should be reformulated in terms of complex
Devang Patel53bb5c92009-11-10 23:06:00 +00001569 // addresses instead.
1570 if (VD.isBlockByrefVariable())
Devang Patel8a241142009-12-09 18:24:21 +00001571 addType(VariableDie, getBlockByrefType(VD.getType(), Name));
Devang Patel53bb5c92009-11-10 23:06:00 +00001572 else
Devang Patel8a241142009-12-09 18:24:21 +00001573 addType(VariableDie, VD.getType());
Devang Patel53bb5c92009-11-10 23:06:00 +00001574 }
1575
1576 // Add variable address.
1577 if (!Scope->isAbstractScope()) {
Devang Patel90a48ad2010-03-15 18:33:46 +00001578 // Check if variable is described by DBG_VALUE instruction.
Devang Patel26c1e562010-05-20 16:36:41 +00001579 DenseMap<const DbgVariable *, const MachineInstr *>::iterator DVI =
1580 DbgVariableToDbgInstMap.find(DV);
1581 if (DVI != DbgVariableToDbgInstMap.end()) {
1582 const MachineInstr *DVInsn = DVI->second;
1583 const MCSymbol *DVLabel = findVariableLabel(DV);
Devang Patela43098d2010-04-28 01:03:09 +00001584 bool updated = false;
1585 // FIXME : Handle getNumOperands != 3
1586 if (DVInsn->getNumOperands() == 3) {
1587 if (DVInsn->getOperand(0).isReg())
Devang Patel26c1e562010-05-20 16:36:41 +00001588 updated = addRegisterAddress(VariableDie, DVLabel, DVInsn->getOperand(0));
Devang Patela43098d2010-04-28 01:03:09 +00001589 else if (DVInsn->getOperand(0).isImm())
Devang Patel26c1e562010-05-20 16:36:41 +00001590 updated = addConstantValue(VariableDie, DVLabel, DVInsn->getOperand(0));
Devang Patela43098d2010-04-28 01:03:09 +00001591 else if (DVInsn->getOperand(0).isFPImm())
Devang Patel26c1e562010-05-20 16:36:41 +00001592 updated = addConstantFPValue(VariableDie, DVLabel, DVInsn->getOperand(0));
Devang Patel28ff35d2010-04-28 01:39:28 +00001593 } else {
1594 MachineLocation Location = Asm->getDebugValueLocation(DVInsn);
1595 if (Location.getReg()) {
1596 addAddress(VariableDie, dwarf::DW_AT_location, Location);
Devang Patel26c1e562010-05-20 16:36:41 +00001597 if (DVLabel)
Devang Patel28ff35d2010-04-28 01:39:28 +00001598 addLabel(VariableDie, dwarf::DW_AT_start_scope, dwarf::DW_FORM_addr,
Devang Patel26c1e562010-05-20 16:36:41 +00001599 DVLabel);
Devang Patel28ff35d2010-04-28 01:39:28 +00001600 updated = true;
1601 }
Devang Patela43098d2010-04-28 01:03:09 +00001602 }
1603 if (!updated) {
1604 // If variableDie is not updated then DBG_VALUE instruction does not
1605 // have valid variable info.
1606 delete VariableDie;
1607 return NULL;
1608 }
1609 }
1610 else {
Devang Patel90a48ad2010-03-15 18:33:46 +00001611 MachineLocation Location;
1612 unsigned FrameReg;
Chris Lattnerd38fee82010-04-05 00:13:49 +00001613 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Devang Patel26c1e562010-05-20 16:36:41 +00001614 int FI = 0;
1615 if (findVariableFrameIndex(DV, &FI)) {
1616 int Offset = RI->getFrameIndexReference(*Asm->MF, FI, FrameReg);
Devang Patel98e1cac2010-05-14 21:01:35 +00001617 Location.set(FrameReg, Offset);
1618
1619 if (VD.hasComplexAddress())
1620 addComplexAddress(DV, VariableDie, dwarf::DW_AT_location, Location);
1621 else if (VD.isBlockByrefVariable())
1622 addBlockByrefAddress(DV, VariableDie, dwarf::DW_AT_location, Location);
1623 else
1624 addAddress(VariableDie, dwarf::DW_AT_location, Location);
1625 }
Devang Patel90a48ad2010-03-15 18:33:46 +00001626 }
Devang Patel53bb5c92009-11-10 23:06:00 +00001627 }
Devang Patelb4645642010-02-06 01:02:37 +00001628
1629 if (Tag == dwarf::DW_TAG_formal_parameter && VD.getType().isArtificial())
1630 addUInt(VariableDie, dwarf::DW_AT_artificial, dwarf::DW_FORM_flag, 1);
Devang Patel53bb5c92009-11-10 23:06:00 +00001631 DV->setDIE(VariableDie);
1632 return VariableDie;
1633
1634}
Devang Patel2c4ceb12009-11-21 02:48:08 +00001635
Devang Patel193f7202009-11-24 01:14:22 +00001636void DwarfDebug::addPubTypes(DISubprogram SP) {
1637 DICompositeType SPTy = SP.getType();
1638 unsigned SPTag = SPTy.getTag();
1639 if (SPTag != dwarf::DW_TAG_subroutine_type)
1640 return;
1641
1642 DIArray Args = SPTy.getTypeArray();
Devang Patel193f7202009-11-24 01:14:22 +00001643 for (unsigned i = 0, e = Args.getNumElements(); i != e; ++i) {
Devang Patel2db49d72010-05-07 18:11:54 +00001644 DIType ATy(Args.getElement(i));
Devang Patel9c004872010-05-07 21:45:47 +00001645 if (!ATy.Verify())
Devang Patel193f7202009-11-24 01:14:22 +00001646 continue;
1647 DICompositeType CATy = getDICompositeType(ATy);
Devang Patel2db49d72010-05-07 18:11:54 +00001648 if (DIDescriptor(CATy).Verify() && !CATy.getName().empty()
Devang Patel50d80e32010-04-13 20:35:04 +00001649 && !CATy.isForwardDecl()) {
Devang Patel163a9f72010-05-10 22:49:55 +00001650 CompileUnit *TheCU = getCompileUnit(CATy);
1651 if (DIEEntry *Entry = TheCU->getDIEEntry(CATy))
1652 TheCU->addGlobalType(CATy.getName(), Entry->getEntry());
Devang Patel193f7202009-11-24 01:14:22 +00001653 }
1654 }
1655}
1656
Devang Patel2c4ceb12009-11-21 02:48:08 +00001657/// constructScopeDIE - Construct a DIE for this scope.
1658DIE *DwarfDebug::constructScopeDIE(DbgScope *Scope) {
Devang Patel3c91b052010-03-08 20:52:55 +00001659 if (!Scope || !Scope->getScopeNode())
1660 return NULL;
1661
1662 DIScope DS(Scope->getScopeNode());
1663 DIE *ScopeDIE = NULL;
1664 if (Scope->getInlinedAt())
1665 ScopeDIE = constructInlinedScopeDIE(Scope);
1666 else if (DS.isSubprogram()) {
1667 if (Scope->isAbstractScope())
Devang Patel163a9f72010-05-10 22:49:55 +00001668 ScopeDIE = getCompileUnit(DS)->getDIE(DS);
Devang Patel3c91b052010-03-08 20:52:55 +00001669 else
Devang Patel2db49d72010-05-07 18:11:54 +00001670 ScopeDIE = updateSubprogramScopeDIE(DS);
Devang Patel3c91b052010-03-08 20:52:55 +00001671 }
Devang Patelaead63c2010-03-29 22:59:58 +00001672 else
Devang Patel3c91b052010-03-08 20:52:55 +00001673 ScopeDIE = constructLexicalScopeDIE(Scope);
Devang Patelaead63c2010-03-29 22:59:58 +00001674 if (!ScopeDIE) return NULL;
Devang Patel3c91b052010-03-08 20:52:55 +00001675
Devang Patel53bb5c92009-11-10 23:06:00 +00001676 // Add variables to scope.
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00001677 const SmallVector<DbgVariable *, 8> &Variables = Scope->getVariables();
Devang Patel53bb5c92009-11-10 23:06:00 +00001678 for (unsigned i = 0, N = Variables.size(); i < N; ++i) {
Devang Patel8a241142009-12-09 18:24:21 +00001679 DIE *VariableDIE = constructVariableDIE(Variables[i], Scope);
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001680 if (VariableDIE)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001681 ScopeDIE->addChild(VariableDIE);
Devang Patel53bb5c92009-11-10 23:06:00 +00001682 }
1683
1684 // Add nested scopes.
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00001685 const SmallVector<DbgScope *, 4> &Scopes = Scope->getScopes();
Devang Patel53bb5c92009-11-10 23:06:00 +00001686 for (unsigned j = 0, M = Scopes.size(); j < M; ++j) {
1687 // Define the Scope debug information entry.
Devang Patel2c4ceb12009-11-21 02:48:08 +00001688 DIE *NestedDIE = constructScopeDIE(Scopes[j]);
Jim Grosbach31ef40e2009-11-21 23:12:12 +00001689 if (NestedDIE)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001690 ScopeDIE->addChild(NestedDIE);
Devang Patel53bb5c92009-11-10 23:06:00 +00001691 }
Devang Patel193f7202009-11-24 01:14:22 +00001692
1693 if (DS.isSubprogram())
Devang Patel2db49d72010-05-07 18:11:54 +00001694 addPubTypes(DISubprogram(DS));
Devang Patel193f7202009-11-24 01:14:22 +00001695
1696 return ScopeDIE;
Devang Patel53bb5c92009-11-10 23:06:00 +00001697}
1698
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001699/// GetOrCreateSourceID - Look up the source id with the given directory and
1700/// source file names. If none currently exists, create a new id and insert it
1701/// in the SourceIds map. This can update DirectoryNames and SourceFileNames
1702/// maps as well.
Chris Lattner1d65ba72010-03-31 06:06:37 +00001703unsigned DwarfDebug::GetOrCreateSourceID(StringRef DirName, StringRef FileName){
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001704 unsigned DId;
1705 StringMap<unsigned>::iterator DI = DirectoryIdMap.find(DirName);
1706 if (DI != DirectoryIdMap.end()) {
1707 DId = DI->getValue();
1708 } else {
1709 DId = DirectoryNames.size() + 1;
1710 DirectoryIdMap[DirName] = DId;
1711 DirectoryNames.push_back(DirName);
1712 }
1713
1714 unsigned FId;
1715 StringMap<unsigned>::iterator FI = SourceFileIdMap.find(FileName);
1716 if (FI != SourceFileIdMap.end()) {
1717 FId = FI->getValue();
1718 } else {
1719 FId = SourceFileNames.size() + 1;
1720 SourceFileIdMap[FileName] = FId;
1721 SourceFileNames.push_back(FileName);
1722 }
1723
1724 DenseMap<std::pair<unsigned, unsigned>, unsigned>::iterator SI =
1725 SourceIdMap.find(std::make_pair(DId, FId));
1726 if (SI != SourceIdMap.end())
1727 return SI->second;
1728
1729 unsigned SrcId = SourceIds.size() + 1; // DW_AT_decl_file cannot be 0.
1730 SourceIdMap[std::make_pair(DId, FId)] = SrcId;
1731 SourceIds.push_back(std::make_pair(DId, FId));
1732
1733 return SrcId;
1734}
1735
Devang Patel6404e4e2009-12-15 19:16:48 +00001736/// getOrCreateNameSpace - Create a DIE for DINameSpace.
1737DIE *DwarfDebug::getOrCreateNameSpace(DINameSpace NS) {
Devang Patel163a9f72010-05-10 22:49:55 +00001738 CompileUnit *TheCU = getCompileUnit(NS);
1739 DIE *NDie = TheCU->getDIE(NS);
Devang Patel6404e4e2009-12-15 19:16:48 +00001740 if (NDie)
1741 return NDie;
1742 NDie = new DIE(dwarf::DW_TAG_namespace);
Devang Patel163a9f72010-05-10 22:49:55 +00001743 TheCU->insertDIE(NS, NDie);
Devang Patel6404e4e2009-12-15 19:16:48 +00001744 if (!NS.getName().empty())
1745 addString(NDie, dwarf::DW_AT_name, dwarf::DW_FORM_string, NS.getName());
1746 addSourceLine(NDie, &NS);
1747 addToContextOwner(NDie, NS.getContext());
1748 return NDie;
1749}
1750
Devang Patel163a9f72010-05-10 22:49:55 +00001751/// constructCompileUnit - Create new CompileUnit for the given
1752/// metadata node with tag DW_TAG_compile_unit.
Devang Patele9f8f5e2010-05-07 20:54:48 +00001753void DwarfDebug::constructCompileUnit(const MDNode *N) {
Devang Patele4b27562009-08-28 23:24:31 +00001754 DICompileUnit DIUnit(N);
Devang Patel65dbc902009-11-25 17:36:49 +00001755 StringRef FN = DIUnit.getFilename();
1756 StringRef Dir = DIUnit.getDirectory();
Devang Patel5ccdd102009-09-29 18:40:58 +00001757 unsigned ID = GetOrCreateSourceID(Dir, FN);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001758
1759 DIE *Die = new DIE(dwarf::DW_TAG_compile_unit);
Devang Patel2c4ceb12009-11-21 02:48:08 +00001760 addString(Die, dwarf::DW_AT_producer, dwarf::DW_FORM_string,
Devang Patel5ccdd102009-09-29 18:40:58 +00001761 DIUnit.getProducer());
Devang Patel2c4ceb12009-11-21 02:48:08 +00001762 addUInt(Die, dwarf::DW_AT_language, dwarf::DW_FORM_data1,
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001763 DIUnit.getLanguage());
Devang Patel2c4ceb12009-11-21 02:48:08 +00001764 addString(Die, dwarf::DW_AT_name, dwarf::DW_FORM_string, FN);
Devang Patel5098da02010-04-26 22:54:28 +00001765 // Use DW_AT_entry_pc instead of DW_AT_low_pc/DW_AT_high_pc pair. This
1766 // simplifies debug range entries.
1767 addUInt(Die, dwarf::DW_AT_entry_pc, dwarf::DW_FORM_data4, 0);
Devang Patel4a602ca2010-03-22 23:11:36 +00001768 // DW_AT_stmt_list is a offset of line number information for this
1769 // compile unit in debug_line section. It is always zero when only one
1770 // compile unit is emitted in one object file.
1771 addUInt(Die, dwarf::DW_AT_stmt_list, dwarf::DW_FORM_data4, 0);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001772
Devang Patel65dbc902009-11-25 17:36:49 +00001773 if (!Dir.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001774 addString(Die, dwarf::DW_AT_comp_dir, dwarf::DW_FORM_string, Dir);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001775 if (DIUnit.isOptimized())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001776 addUInt(Die, dwarf::DW_AT_APPLE_optimized, dwarf::DW_FORM_flag, 1);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001777
Devang Patel65dbc902009-11-25 17:36:49 +00001778 StringRef Flags = DIUnit.getFlags();
1779 if (!Flags.empty())
Devang Patel2c4ceb12009-11-21 02:48:08 +00001780 addString(Die, dwarf::DW_AT_APPLE_flags, dwarf::DW_FORM_string, Flags);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001781
1782 unsigned RVer = DIUnit.getRunTimeVersion();
1783 if (RVer)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001784 addUInt(Die, dwarf::DW_AT_APPLE_major_runtime_vers,
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001785 dwarf::DW_FORM_data1, RVer);
1786
Devang Patel163a9f72010-05-10 22:49:55 +00001787 CompileUnit *NewCU = new CompileUnit(ID, Die);
1788 if (!FirstCU)
1789 FirstCU = NewCU;
1790 CUMap.insert(std::make_pair(N, NewCU));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001791}
1792
Devang Patel163a9f72010-05-10 22:49:55 +00001793/// getCompielUnit - Get CompileUnit DIE.
1794CompileUnit *DwarfDebug::getCompileUnit(const MDNode *N) const {
1795 assert (N && "Invalid DwarfDebug::getCompileUnit argument!");
1796 DIDescriptor D(N);
1797 const MDNode *CUNode = NULL;
1798 if (D.isCompileUnit())
1799 CUNode = N;
1800 else if (D.isSubprogram())
1801 CUNode = DISubprogram(N).getCompileUnit();
1802 else if (D.isType())
1803 CUNode = DIType(N).getCompileUnit();
1804 else if (D.isGlobalVariable())
1805 CUNode = DIGlobalVariable(N).getCompileUnit();
1806 else if (D.isVariable())
1807 CUNode = DIVariable(N).getCompileUnit();
1808 else if (D.isNameSpace())
1809 CUNode = DINameSpace(N).getCompileUnit();
1810 else if (D.isFile())
1811 CUNode = DIFile(N).getCompileUnit();
1812 else
1813 return FirstCU;
1814
1815 DenseMap<const MDNode *, CompileUnit *>::const_iterator I
1816 = CUMap.find(CUNode);
1817 if (I == CUMap.end())
1818 return FirstCU;
1819 return I->second;
1820}
1821
1822
1823/// constructGlobalVariableDIE - Construct global variable DIE.
Devang Patele9f8f5e2010-05-07 20:54:48 +00001824void DwarfDebug::constructGlobalVariableDIE(const MDNode *N) {
Devang Patele4b27562009-08-28 23:24:31 +00001825 DIGlobalVariable DI_GV(N);
Daniel Dunbarf612ff62009-09-19 20:40:05 +00001826
Devang Patel905cf5e2009-09-04 23:59:07 +00001827 // If debug information is malformed then ignore it.
1828 if (DI_GV.Verify() == false)
1829 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001830
1831 // Check for pre-existence.
Devang Patel163a9f72010-05-10 22:49:55 +00001832 CompileUnit *TheCU = getCompileUnit(N);
1833 if (TheCU->getDIE(DI_GV))
Devang Patel13e16b62009-06-26 01:49:18 +00001834 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001835
Devang Patel8a241142009-12-09 18:24:21 +00001836 DIE *VariableDie = createGlobalVariableDIE(DI_GV);
Devang Pateledb45632009-12-10 23:25:41 +00001837 if (!VariableDie)
1838 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001839
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001840 // Add to map.
Devang Patel163a9f72010-05-10 22:49:55 +00001841 TheCU->insertDIE(N, VariableDie);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001842
1843 // Add to context owner.
Devang Patelc9b16cc2010-01-15 01:12:22 +00001844 DIDescriptor GVContext = DI_GV.getContext();
1845 // Do not create specification DIE if context is either compile unit
1846 // or a subprogram.
Chris Lattner1d65ba72010-03-31 06:06:37 +00001847 if (DI_GV.isDefinition() && !GVContext.isCompileUnit() &&
Devang Patel5f094002010-04-06 23:53:48 +00001848 !GVContext.isFile() &&
Devang Patel2db49d72010-05-07 18:11:54 +00001849 !isSubprogramContext(GVContext)) {
Devang Patel6404e4e2009-12-15 19:16:48 +00001850 // Create specification DIE.
1851 DIE *VariableSpecDIE = new DIE(dwarf::DW_TAG_variable);
1852 addDIEEntry(VariableSpecDIE, dwarf::DW_AT_specification,
1853 dwarf::DW_FORM_ref4, VariableDie);
Benjamin Kramer345ef342010-03-31 19:34:01 +00001854 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Devang Patel6404e4e2009-12-15 19:16:48 +00001855 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_addr);
Chris Lattner4faf59a2010-03-08 22:31:46 +00001856 addLabel(Block, 0, dwarf::DW_FORM_udata,
Chris Lattnerdeb0cba2010-03-12 21:09:07 +00001857 Asm->Mang->getSymbol(DI_GV.getGlobal()));
Devang Patel6404e4e2009-12-15 19:16:48 +00001858 addBlock(VariableSpecDIE, dwarf::DW_AT_location, 0, Block);
Devang Patel8581e012010-02-09 01:58:33 +00001859 addUInt(VariableDie, dwarf::DW_AT_declaration, dwarf::DW_FORM_flag, 1);
Devang Patel163a9f72010-05-10 22:49:55 +00001860 TheCU->addDie(VariableSpecDIE);
Devang Patel6404e4e2009-12-15 19:16:48 +00001861 } else {
Benjamin Kramer345ef342010-03-31 19:34:01 +00001862 DIEBlock *Block = new (DIEValueAllocator) DIEBlock();
Devang Patel6404e4e2009-12-15 19:16:48 +00001863 addUInt(Block, 0, dwarf::DW_FORM_data1, dwarf::DW_OP_addr);
Chris Lattner4faf59a2010-03-08 22:31:46 +00001864 addLabel(Block, 0, dwarf::DW_FORM_udata,
Chris Lattnerdeb0cba2010-03-12 21:09:07 +00001865 Asm->Mang->getSymbol(DI_GV.getGlobal()));
Devang Patel6404e4e2009-12-15 19:16:48 +00001866 addBlock(VariableDie, dwarf::DW_AT_location, 0, Block);
1867 }
Devang Patelc9b16cc2010-01-15 01:12:22 +00001868 addToContextOwner(VariableDie, GVContext);
Devang Patelc366f832009-12-10 19:14:49 +00001869
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001870 // Expose as global. FIXME - need to check external flag.
Devang Patel163a9f72010-05-10 22:49:55 +00001871 TheCU->addGlobal(DI_GV.getName(), VariableDie);
Devang Patel193f7202009-11-24 01:14:22 +00001872
1873 DIType GTy = DI_GV.getType();
Devang Patel50d80e32010-04-13 20:35:04 +00001874 if (GTy.isCompositeType() && !GTy.getName().empty()
1875 && !GTy.isForwardDecl()) {
Devang Patel163a9f72010-05-10 22:49:55 +00001876 DIEEntry *Entry = TheCU->getDIEEntry(GTy);
Chris Lattnered7a77b2010-03-31 05:36:29 +00001877 assert(Entry && "Missing global type!");
Devang Patel163a9f72010-05-10 22:49:55 +00001878 TheCU->addGlobalType(GTy.getName(), Entry->getEntry());
Devang Patel193f7202009-11-24 01:14:22 +00001879 }
Devang Patel13e16b62009-06-26 01:49:18 +00001880 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001881}
1882
Devang Patel163a9f72010-05-10 22:49:55 +00001883/// construct SubprogramDIE - Construct subprogram DIE.
Devang Patele9f8f5e2010-05-07 20:54:48 +00001884void DwarfDebug::constructSubprogramDIE(const MDNode *N) {
Devang Patele4b27562009-08-28 23:24:31 +00001885 DISubprogram SP(N);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001886
Stuart Hastings639336e2010-04-06 21:38:29 +00001887 // Check for pre-existence.
Devang Patel163a9f72010-05-10 22:49:55 +00001888 CompileUnit *TheCU = getCompileUnit(N);
1889 if (TheCU->getDIE(N))
Stuart Hastings639336e2010-04-06 21:38:29 +00001890 return;
1891
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001892 if (!SP.isDefinition())
1893 // This is a method declaration which will be handled while constructing
1894 // class type.
Devang Patel13e16b62009-06-26 01:49:18 +00001895 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001896
Stuart Hastings639336e2010-04-06 21:38:29 +00001897 DIE *SubprogramDie = createSubprogramDIE(SP);
1898
1899 // Add to map.
Devang Patel163a9f72010-05-10 22:49:55 +00001900 TheCU->insertDIE(N, SubprogramDie);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001901
1902 // Add to context owner.
Devang Patel6404e4e2009-12-15 19:16:48 +00001903 addToContextOwner(SubprogramDie, SP.getContext());
Devang Patel0000fad2009-12-08 23:21:45 +00001904
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001905 // Expose as global.
Devang Patel163a9f72010-05-10 22:49:55 +00001906 TheCU->addGlobal(SP.getName(), SubprogramDie);
Devang Patel193f7202009-11-24 01:14:22 +00001907
Devang Patel13e16b62009-06-26 01:49:18 +00001908 return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001909}
1910
Devang Patel2c4ceb12009-11-21 02:48:08 +00001911/// beginModule - Emit all Dwarf sections that should come prior to the
Daniel Dunbar00564992009-09-19 20:40:14 +00001912/// content. Create global DIEs and emit initial debug info sections.
1913/// This is inovked by the target AsmPrinter.
Chris Lattner75f50722010-04-04 07:48:20 +00001914void DwarfDebug::beginModule(Module *M) {
Devang Pateleac9c072010-04-27 19:46:33 +00001915 if (DisableDebugInfoPrinting)
1916 return;
1917
Devang Patel78ab9e22009-07-30 18:56:46 +00001918 DebugInfoFinder DbgFinder;
1919 DbgFinder.processModule(*M);
Devang Patel13e16b62009-06-26 01:49:18 +00001920
Chris Lattnerd850ac72010-04-05 02:19:28 +00001921 bool HasDebugInfo = false;
1922
1923 // Scan all the compile-units to see if there are any marked as the main unit.
1924 // if not, we do not generate debug info.
1925 for (DebugInfoFinder::iterator I = DbgFinder.compile_unit_begin(),
1926 E = DbgFinder.compile_unit_end(); I != E; ++I) {
1927 if (DICompileUnit(*I).isMain()) {
1928 HasDebugInfo = true;
1929 break;
1930 }
1931 }
1932
1933 if (!HasDebugInfo) return;
1934
1935 // Tell MMI that we have debug info.
1936 MMI->setDebugInfoAvailability(true);
1937
Chris Lattnerbe15beb2010-04-04 23:17:54 +00001938 // Emit initial sections.
Chris Lattnerd850ac72010-04-05 02:19:28 +00001939 EmitSectionLabels();
Chris Lattnerbe15beb2010-04-04 23:17:54 +00001940
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001941 // Create all the compile unit DIEs.
Devang Patel78ab9e22009-07-30 18:56:46 +00001942 for (DebugInfoFinder::iterator I = DbgFinder.compile_unit_begin(),
1943 E = DbgFinder.compile_unit_end(); I != E; ++I)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001944 constructCompileUnit(*I);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001945
Devang Patel53bb5c92009-11-10 23:06:00 +00001946 // Create DIEs for each subprogram.
Devang Patel78ab9e22009-07-30 18:56:46 +00001947 for (DebugInfoFinder::iterator I = DbgFinder.subprogram_begin(),
1948 E = DbgFinder.subprogram_end(); I != E; ++I)
Devang Patel2c4ceb12009-11-21 02:48:08 +00001949 constructSubprogramDIE(*I);
Devang Patel13e16b62009-06-26 01:49:18 +00001950
Devang Patelc366f832009-12-10 19:14:49 +00001951 // Create DIEs for each global variable.
1952 for (DebugInfoFinder::iterator I = DbgFinder.global_variable_begin(),
1953 E = DbgFinder.global_variable_end(); I != E; ++I)
1954 constructGlobalVariableDIE(*I);
1955
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001956 // Prime section data.
Chris Lattnerf0144122009-07-28 03:13:23 +00001957 SectionMap.insert(Asm->getObjFileLowering().getTextSection());
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001958
1959 // Print out .file directives to specify files for .loc directives. These are
1960 // printed out early so that they precede any .loc directives.
Chris Lattnerd38fee82010-04-05 00:13:49 +00001961 if (Asm->MAI->hasDotLocAndDotFile()) {
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001962 for (unsigned i = 1, e = getNumSourceIds()+1; i != e; ++i) {
1963 // Remember source id starts at 1.
1964 std::pair<unsigned, unsigned> Id = getSourceDirectoryAndFileIds(i);
Chris Lattner0ad9c912010-01-22 22:09:00 +00001965 // FIXME: don't use sys::path for this! This should not depend on the
1966 // host.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001967 sys::Path FullPath(getSourceDirectoryName(Id.first));
1968 bool AppendOk =
1969 FullPath.appendComponent(getSourceFileName(Id.second));
1970 assert(AppendOk && "Could not append filename to directory!");
1971 AppendOk = false;
Chris Lattnera6594fc2010-01-25 18:58:59 +00001972 Asm->OutStreamer.EmitDwarfFileDirective(i, FullPath.str());
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001973 }
1974 }
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001975}
1976
Devang Patel2c4ceb12009-11-21 02:48:08 +00001977/// endModule - Emit all Dwarf sections that should come after the content.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001978///
Devang Patel2c4ceb12009-11-21 02:48:08 +00001979void DwarfDebug::endModule() {
Devang Patel163a9f72010-05-10 22:49:55 +00001980 if (!FirstCU) return;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001981
Devang Patel53bb5c92009-11-10 23:06:00 +00001982 // Attach DW_AT_inline attribute with inlined subprogram DIEs.
1983 for (SmallPtrSet<DIE *, 4>::iterator AI = InlinedSubprogramDIEs.begin(),
1984 AE = InlinedSubprogramDIEs.end(); AI != AE; ++AI) {
1985 DIE *ISP = *AI;
Devang Patel2c4ceb12009-11-21 02:48:08 +00001986 addUInt(ISP, dwarf::DW_AT_inline, 0, dwarf::DW_INL_inlined);
Devang Patel53bb5c92009-11-10 23:06:00 +00001987 }
1988
Devang Patele9f8f5e2010-05-07 20:54:48 +00001989 for (DenseMap<DIE *, const MDNode *>::iterator CI = ContainingTypeMap.begin(),
Devang Patel5d11eb02009-12-03 19:11:07 +00001990 CE = ContainingTypeMap.end(); CI != CE; ++CI) {
1991 DIE *SPDie = CI->first;
Devang Patele9f8f5e2010-05-07 20:54:48 +00001992 const MDNode *N = dyn_cast_or_null<MDNode>(CI->second);
Devang Patel5d11eb02009-12-03 19:11:07 +00001993 if (!N) continue;
Devang Patel163a9f72010-05-10 22:49:55 +00001994 DIE *NDie = getCompileUnit(N)->getDIE(N);
Devang Patel5d11eb02009-12-03 19:11:07 +00001995 if (!NDie) continue;
1996 addDIEEntry(SPDie, dwarf::DW_AT_containing_type, dwarf::DW_FORM_ref4, NDie);
Devang Patel5d11eb02009-12-03 19:11:07 +00001997 }
1998
Bill Wendlingf0fb9872009-05-20 23:19:06 +00001999 // Standard sections final addresses.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002000 Asm->OutStreamer.SwitchSection(Asm->getObjFileLowering().getTextSection());
Chris Lattnerc0215722010-04-04 19:25:43 +00002001 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("text_end"));
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002002 Asm->OutStreamer.SwitchSection(Asm->getObjFileLowering().getDataSection());
Chris Lattnerc0215722010-04-04 19:25:43 +00002003 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("data_end"));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002004
2005 // End text sections.
2006 for (unsigned i = 1, N = SectionMap.size(); i <= N; ++i) {
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002007 Asm->OutStreamer.SwitchSection(SectionMap[i]);
Chris Lattnerc0215722010-04-04 19:25:43 +00002008 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("section_end", i));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002009 }
2010
2011 // Emit common frame information.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002012 emitCommonDebugFrame();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002013
2014 // Emit function debug frame information
2015 for (std::vector<FunctionDebugFrameInfo>::iterator I = DebugFrames.begin(),
2016 E = DebugFrames.end(); I != E; ++I)
Devang Patel2c4ceb12009-11-21 02:48:08 +00002017 emitFunctionDebugFrame(*I);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002018
2019 // Compute DIE offsets and sizes.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002020 computeSizeAndOffsets();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002021
2022 // Emit all the DIEs into a debug info section
Devang Patel2c4ceb12009-11-21 02:48:08 +00002023 emitDebugInfo();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002024
2025 // Corresponding abbreviations into a abbrev section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002026 emitAbbreviations();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002027
2028 // Emit source line correspondence into a debug line section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002029 emitDebugLines();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002030
2031 // Emit info into a debug pubnames section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002032 emitDebugPubNames();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002033
Devang Patel193f7202009-11-24 01:14:22 +00002034 // Emit info into a debug pubtypes section.
2035 emitDebugPubTypes();
2036
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002037 // Emit info into a debug loc section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002038 emitDebugLoc();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002039
2040 // Emit info into a debug aranges section.
2041 EmitDebugARanges();
2042
2043 // Emit info into a debug ranges section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002044 emitDebugRanges();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002045
2046 // Emit info into a debug macinfo section.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002047 emitDebugMacInfo();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002048
2049 // Emit inline info.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002050 emitDebugInlineInfo();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002051
Chris Lattnerbc733f52010-03-13 02:17:42 +00002052 // Emit info into a debug str section.
2053 emitDebugStr();
2054
Devang Patel163a9f72010-05-10 22:49:55 +00002055 for (DenseMap<const MDNode *, CompileUnit *>::iterator I = CUMap.begin(),
2056 E = CUMap.end(); I != E; ++I)
2057 delete I->second;
2058 FirstCU = NULL; // Reset for the next Module, if any.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002059}
2060
Devang Patel53bb5c92009-11-10 23:06:00 +00002061/// findAbstractVariable - Find abstract variable, if any, associated with Var.
Devang Patel26c1e562010-05-20 16:36:41 +00002062DbgVariable *DwarfDebug::findAbstractVariable(DIVariable &Var,
Chris Lattnerde4845c2010-04-02 19:42:39 +00002063 DebugLoc ScopeLoc) {
Devang Patel53bb5c92009-11-10 23:06:00 +00002064
Devang Patel2db49d72010-05-07 18:11:54 +00002065 DbgVariable *AbsDbgVariable = AbstractVariables.lookup(Var);
Devang Patel53bb5c92009-11-10 23:06:00 +00002066 if (AbsDbgVariable)
2067 return AbsDbgVariable;
2068
Devang Patel2db49d72010-05-07 18:11:54 +00002069 LLVMContext &Ctx = Var->getContext();
Chris Lattnerde4845c2010-04-02 19:42:39 +00002070 DbgScope *Scope = AbstractScopes.lookup(ScopeLoc.getScope(Ctx));
Devang Patel53bb5c92009-11-10 23:06:00 +00002071 if (!Scope)
2072 return NULL;
2073
Devang Patel26c1e562010-05-20 16:36:41 +00002074 AbsDbgVariable = new DbgVariable(Var);
Devang Patel2c4ceb12009-11-21 02:48:08 +00002075 Scope->addVariable(AbsDbgVariable);
Devang Patel2db49d72010-05-07 18:11:54 +00002076 AbstractVariables[Var] = AbsDbgVariable;
Devang Patel53bb5c92009-11-10 23:06:00 +00002077 return AbsDbgVariable;
2078}
2079
Devang Patelee432862010-05-20 19:57:06 +00002080/// collectVariableInfoFromMMITable - Collect variable information from
2081/// side table maintained by MMI.
2082void
2083DwarfDebug::collectVariableInfoFromMMITable(const MachineFunction * MF,
2084 SmallPtrSet<const MDNode *, 16> &Processed) {
Chris Lattnerd38fee82010-04-05 00:13:49 +00002085 const LLVMContext &Ctx = Asm->MF->getFunction()->getContext();
Devang Patele717faa2009-10-06 01:26:37 +00002086 MachineModuleInfo::VariableDbgInfoMapTy &VMap = MMI->getVariableDbgInfo();
2087 for (MachineModuleInfo::VariableDbgInfoMapTy::iterator VI = VMap.begin(),
2088 VE = VMap.end(); VI != VE; ++VI) {
Devang Patele9f8f5e2010-05-07 20:54:48 +00002089 const MDNode *Var = VI->first;
Devang Patel53bb5c92009-11-10 23:06:00 +00002090 if (!Var) continue;
Devang Patel98e1cac2010-05-14 21:01:35 +00002091 Processed.insert(Var);
Chris Lattnerde4845c2010-04-02 19:42:39 +00002092 DIVariable DV(Var);
2093 const std::pair<unsigned, DebugLoc> &VP = VI->second;
Devang Patel53bb5c92009-11-10 23:06:00 +00002094
Chris Lattnerde4845c2010-04-02 19:42:39 +00002095 DbgScope *Scope = 0;
Devang Patele9f8f5e2010-05-07 20:54:48 +00002096 if (const MDNode *IA = VP.second.getInlinedAt(Ctx))
Chris Lattnerde4845c2010-04-02 19:42:39 +00002097 Scope = ConcreteScopes.lookup(IA);
2098 if (Scope == 0)
2099 Scope = DbgScopeMap.lookup(VP.second.getScope(Ctx));
2100
Devang Patelfb0ee432009-11-10 23:20:04 +00002101 // If variable scope is not found then skip this variable.
Chris Lattnerde4845c2010-04-02 19:42:39 +00002102 if (Scope == 0)
Devang Patelfb0ee432009-11-10 23:20:04 +00002103 continue;
Devang Patel53bb5c92009-11-10 23:06:00 +00002104
Devang Patel26c1e562010-05-20 16:36:41 +00002105 DbgVariable *AbsDbgVariable = findAbstractVariable(DV, VP.second);
2106 DbgVariable *RegVar = new DbgVariable(DV);
2107 recordVariableFrameIndex(RegVar, VP.first);
Devang Patel2c4ceb12009-11-21 02:48:08 +00002108 Scope->addVariable(RegVar);
Devang Patel26c1e562010-05-20 16:36:41 +00002109 if (AbsDbgVariable) {
2110 recordVariableFrameIndex(AbsDbgVariable, VP.first);
2111 VarToAbstractVarMap[RegVar] = AbsDbgVariable;
2112 }
Devang Patele717faa2009-10-06 01:26:37 +00002113 }
Devang Patelee432862010-05-20 19:57:06 +00002114}
Devang Patel90a48ad2010-03-15 18:33:46 +00002115
Devang Patelee432862010-05-20 19:57:06 +00002116/// collectVariableInfo - Populate DbgScope entries with variables' info.
2117void DwarfDebug::collectVariableInfo(const MachineFunction *MF) {
2118 SmallPtrSet<const MDNode *, 16> Processed;
2119
2120 /// collection info from MMI table.
2121 collectVariableInfoFromMMITable(MF, Processed);
2122
2123 SmallVector<const MachineInstr *, 8> DbgValues;
Devang Patel90a48ad2010-03-15 18:33:46 +00002124 // Collect variable information from DBG_VALUE machine instructions;
Chris Lattnerd38fee82010-04-05 00:13:49 +00002125 for (MachineFunction::const_iterator I = Asm->MF->begin(), E = Asm->MF->end();
Devang Patelee432862010-05-20 19:57:06 +00002126 I != E; ++I)
Devang Patel90a48ad2010-03-15 18:33:46 +00002127 for (MachineBasicBlock::const_iterator II = I->begin(), IE = I->end();
2128 II != IE; ++II) {
2129 const MachineInstr *MInsn = II;
Chris Lattner14d750d2010-03-31 05:39:57 +00002130 if (!MInsn->isDebugValue())
Devang Patel90a48ad2010-03-15 18:33:46 +00002131 continue;
Devang Patelaead63c2010-03-29 22:59:58 +00002132
Devang Patel0f9d9522010-04-27 20:54:45 +00002133 // Ignore Undef values.
Devang Patel97303ee2010-04-27 22:04:41 +00002134 if (MInsn->getOperand(0).isReg() && !MInsn->getOperand(0).getReg())
Devang Patel0f9d9522010-04-27 20:54:45 +00002135 continue;
2136
Devang Patelee432862010-05-20 19:57:06 +00002137 DbgValues.push_back(MInsn);
2138 }
Devang Patel90a48ad2010-03-15 18:33:46 +00002139
Devang Patelee432862010-05-20 19:57:06 +00002140 for(SmallVector<const MachineInstr *, 8>::iterator I = DbgValues.begin(),
2141 E = DbgValues.end(); I != E; ++I) {
2142 const MachineInstr *MInsn = *I;
Devang Patel90a48ad2010-03-15 18:33:46 +00002143
Devang Patelee432862010-05-20 19:57:06 +00002144 DIVariable DV(MInsn->getOperand(MInsn->getNumOperands() - 1).getMetadata());
2145 if (Processed.count(DV) != 0)
2146 continue;
2147
Devang Patelee432862010-05-20 19:57:06 +00002148 DbgScope *Scope = findDbgScope(MInsn);
Devang Patelc0c5a262010-05-21 00:10:20 +00002149 if (!Scope && DV.getTag() == dwarf::DW_TAG_arg_variable)
2150 Scope = CurrentFnDbgScope;
Devang Patelee432862010-05-20 19:57:06 +00002151 // If variable scope is not found then skip this variable.
Devang Patelc0c5a262010-05-21 00:10:20 +00002152 if (!Scope)
Devang Patelee432862010-05-20 19:57:06 +00002153 continue;
2154
2155 Processed.insert(DV);
Devang Patelee432862010-05-20 19:57:06 +00002156 DbgVariable *RegVar = new DbgVariable(DV);
Devang Patelee432862010-05-20 19:57:06 +00002157 DbgVariableToDbgInstMap[RegVar] = MInsn;
2158 Scope->addVariable(RegVar);
Devang Patelc0c5a262010-05-21 00:10:20 +00002159 if (DV.getTag() != dwarf::DW_TAG_arg_variable)
2160 DbgValueStartMap[MInsn] = RegVar;
2161 if (DbgVariable *AbsVar = findAbstractVariable(DV, MInsn->getDebugLoc())) {
2162 DbgVariableToDbgInstMap[AbsVar] = MInsn;
2163 VarToAbstractVarMap[RegVar] = AbsVar;
Devang Patel90a48ad2010-03-15 18:33:46 +00002164 }
2165 }
Devang Patel98e1cac2010-05-14 21:01:35 +00002166
2167 // Collect info for variables that were optimized out.
2168 if (NamedMDNode *NMD =
2169 MF->getFunction()->getParent()->getNamedMetadata("llvm.dbg.lv")) {
2170 for (unsigned i = 0, e = NMD->getNumOperands(); i != e; ++i) {
2171 DIVariable DV(cast_or_null<MDNode>(NMD->getOperand(i)));
Devang Patelee432862010-05-20 19:57:06 +00002172 if (!DV || !Processed.insert(DV))
Devang Patel98e1cac2010-05-14 21:01:35 +00002173 continue;
2174 DbgScope *Scope = DbgScopeMap.lookup(DV.getContext());
2175 if (Scope)
Devang Patel26c1e562010-05-20 16:36:41 +00002176 Scope->addVariable(new DbgVariable(DV));
Devang Patel98e1cac2010-05-14 21:01:35 +00002177 }
2178 }
2179
Devang Patele717faa2009-10-06 01:26:37 +00002180}
2181
Devang Patel553881b2010-03-29 17:20:31 +00002182/// beginScope - Process beginning of a scope.
2183void DwarfDebug::beginScope(const MachineInstr *MI) {
Devang Patel553881b2010-03-29 17:20:31 +00002184 // Check location.
2185 DebugLoc DL = MI->getDebugLoc();
Dan Gohman1cc0d622010-05-05 23:41:32 +00002186 if (DL.isUnknown()) {
Dan Gohman281d65d2010-05-07 01:08:53 +00002187 if (UnknownLocations) {
2188 // This instruction has no debug location. If the preceding instruction
2189 // did, emit debug location information to indicate that the debug
2190 // location is now unknown.
2191 MCSymbol *Label = NULL;
2192 if (DL == PrevInstLoc)
2193 Label = PrevLabel;
2194 else {
2195 Label = recordSourceLine(DL.getLine(), DL.getCol(), 0);
2196 PrevInstLoc = DL;
2197 PrevLabel = Label;
Devang Patelf4ccaea2010-05-19 21:26:53 +00002198 }
Devang Patel461a6462010-05-19 21:58:28 +00002199
Devang Patel26c1e562010-05-20 16:36:41 +00002200 // If this instruction begins a scope then note down corresponding label
2201 // even if previous label is reused.
Devang Patel461a6462010-05-19 21:58:28 +00002202 if (InsnsBeginScopeSet.count(MI) != 0)
2203 LabelsBeforeInsn[MI] = Label;
Dan Gohman281d65d2010-05-07 01:08:53 +00002204 }
Dan Gohman75395842010-05-06 00:29:41 +00002205
Devang Patel553881b2010-03-29 17:20:31 +00002206 return;
Dan Gohman1cc0d622010-05-05 23:41:32 +00002207 }
Devang Patel553881b2010-03-29 17:20:31 +00002208
Devang Patele9f8f5e2010-05-07 20:54:48 +00002209 const MDNode *Scope = DL.getScope(Asm->MF->getFunction()->getContext());
Chris Lattnerde4845c2010-04-02 19:42:39 +00002210
2211 // FIXME: Should only verify each scope once!
2212 if (!DIScope(Scope).Verify())
Devang Patel553881b2010-03-29 17:20:31 +00002213 return;
Devang Patel553881b2010-03-29 17:20:31 +00002214
Devang Patelaead63c2010-03-29 22:59:58 +00002215 // DBG_VALUE instruction establishes new value.
Chris Lattner14d750d2010-03-31 05:39:57 +00002216 if (MI->isDebugValue()) {
Devang Patelaead63c2010-03-29 22:59:58 +00002217 DenseMap<const MachineInstr *, DbgVariable *>::iterator DI
2218 = DbgValueStartMap.find(MI);
2219 if (DI != DbgValueStartMap.end()) {
Devang Pateleac9c072010-04-27 19:46:33 +00002220 MCSymbol *Label = NULL;
2221 if (DL == PrevInstLoc)
2222 Label = PrevLabel;
2223 else {
2224 Label = recordSourceLine(DL.getLine(), DL.getCol(), Scope);
2225 PrevInstLoc = DL;
2226 PrevLabel = Label;
2227 }
Devang Patel26c1e562010-05-20 16:36:41 +00002228 DbgVariableLabelsMap[DI->second] = Label;
Devang Patelaead63c2010-03-29 22:59:58 +00002229 }
Devang Patel7ed63112010-03-30 18:07:00 +00002230 return;
Devang Patelaead63c2010-03-29 22:59:58 +00002231 }
2232
Devang Patel553881b2010-03-29 17:20:31 +00002233 // Emit a label to indicate location change. This is used for line
Devang Pateleac9c072010-04-27 19:46:33 +00002234 // table even if this instruction does not start a new scope.
2235 MCSymbol *Label = NULL;
2236 if (DL == PrevInstLoc)
2237 Label = PrevLabel;
2238 else {
2239 Label = recordSourceLine(DL.getLine(), DL.getCol(), Scope);
2240 PrevInstLoc = DL;
2241 PrevLabel = Label;
2242 }
Devang Patel553881b2010-03-29 17:20:31 +00002243
Devang Patel26c1e562010-05-20 16:36:41 +00002244 // If this instruction begins a scope then note down corresponding label
2245 // even if previous label is reused.
Devang Patel461a6462010-05-19 21:58:28 +00002246 if (InsnsBeginScopeSet.count(MI) != 0)
2247 LabelsBeforeInsn[MI] = Label;
Devang Patel0d20ac82009-10-06 01:50:42 +00002248}
2249
Devang Patel2c4ceb12009-11-21 02:48:08 +00002250/// endScope - Process end of a scope.
2251void DwarfDebug::endScope(const MachineInstr *MI) {
Devang Patel1c246352010-04-08 16:50:29 +00002252 if (InsnsEndScopeSet.count(MI) != 0) {
2253 // Emit a label if this instruction ends a scope.
2254 MCSymbol *Label = MMI->getContext().CreateTempSymbol();
2255 Asm->OutStreamer.EmitLabel(Label);
Devang Pateleac9c072010-04-27 19:46:33 +00002256 LabelsAfterInsn[MI] = Label;
Devang Patel1c246352010-04-08 16:50:29 +00002257 }
Devang Patel53bb5c92009-11-10 23:06:00 +00002258}
2259
Devang Pateleac9c072010-04-27 19:46:33 +00002260/// getOrCreateDbgScope - Create DbgScope for the scope.
Devang Patele9f8f5e2010-05-07 20:54:48 +00002261DbgScope *DwarfDebug::getOrCreateDbgScope(const MDNode *Scope, const MDNode *InlinedAt) {
Devang Patel53bb5c92009-11-10 23:06:00 +00002262 if (!InlinedAt) {
2263 DbgScope *WScope = DbgScopeMap.lookup(Scope);
2264 if (WScope)
Devang Pateleac9c072010-04-27 19:46:33 +00002265 return WScope;
Devang Patel53bb5c92009-11-10 23:06:00 +00002266 WScope = new DbgScope(NULL, DIDescriptor(Scope), NULL);
2267 DbgScopeMap.insert(std::make_pair(Scope, WScope));
Devang Pateleac9c072010-04-27 19:46:33 +00002268 if (DIDescriptor(Scope).isLexicalBlock()) {
2269 DbgScope *Parent =
Devang Patel2db49d72010-05-07 18:11:54 +00002270 getOrCreateDbgScope(DILexicalBlock(Scope).getContext(), NULL);
Devang Pateleac9c072010-04-27 19:46:33 +00002271 WScope->setParent(Parent);
2272 Parent->addScope(WScope);
2273 }
2274
2275 if (!WScope->getParent()) {
2276 StringRef SPName = DISubprogram(Scope).getLinkageName();
2277 if (SPName == Asm->MF->getFunction()->getName())
2278 CurrentFnDbgScope = WScope;
2279 }
2280
2281 return WScope;
Devang Patel53bb5c92009-11-10 23:06:00 +00002282 }
2283
2284 DbgScope *WScope = DbgScopeMap.lookup(InlinedAt);
2285 if (WScope)
Devang Pateleac9c072010-04-27 19:46:33 +00002286 return WScope;
Devang Patel53bb5c92009-11-10 23:06:00 +00002287
2288 WScope = new DbgScope(NULL, DIDescriptor(Scope), InlinedAt);
2289 DbgScopeMap.insert(std::make_pair(InlinedAt, WScope));
2290 DILocation DL(InlinedAt);
Devang Pateleac9c072010-04-27 19:46:33 +00002291 DbgScope *Parent =
Devang Patel2db49d72010-05-07 18:11:54 +00002292 getOrCreateDbgScope(DL.getScope(), DL.getOrigLocation());
Devang Pateleac9c072010-04-27 19:46:33 +00002293 WScope->setParent(Parent);
2294 Parent->addScope(WScope);
2295
2296 ConcreteScopes[InlinedAt] = WScope;
2297 getOrCreateAbstractScope(Scope);
2298
2299 return WScope;
Devang Patel0d20ac82009-10-06 01:50:42 +00002300}
2301
Devang Pateleac9c072010-04-27 19:46:33 +00002302/// hasValidLocation - Return true if debug location entry attached with
2303/// machine instruction encodes valid location info.
2304static bool hasValidLocation(LLVMContext &Ctx,
2305 const MachineInstr *MInsn,
Devang Patele9f8f5e2010-05-07 20:54:48 +00002306 const MDNode *&Scope, const MDNode *&InlinedAt) {
Devang Pateleac9c072010-04-27 19:46:33 +00002307 if (MInsn->isDebugValue())
2308 return false;
2309 DebugLoc DL = MInsn->getDebugLoc();
2310 if (DL.isUnknown()) return false;
2311
Devang Patele9f8f5e2010-05-07 20:54:48 +00002312 const MDNode *S = DL.getScope(Ctx);
Devang Pateleac9c072010-04-27 19:46:33 +00002313
2314 // There is no need to create another DIE for compile unit. For all
2315 // other scopes, create one DbgScope now. This will be translated
2316 // into a scope DIE at the end.
2317 if (DIScope(S).isCompileUnit()) return false;
2318
2319 Scope = S;
2320 InlinedAt = DL.getInlinedAt(Ctx);
2321 return true;
2322}
2323
2324/// calculateDominanceGraph - Calculate dominance graph for DbgScope
2325/// hierarchy.
2326static void calculateDominanceGraph(DbgScope *Scope) {
2327 assert (Scope && "Unable to calculate scop edominance graph!");
2328 SmallVector<DbgScope *, 4> WorkStack;
2329 WorkStack.push_back(Scope);
2330 unsigned Counter = 0;
2331 while (!WorkStack.empty()) {
2332 DbgScope *WS = WorkStack.back();
2333 const SmallVector<DbgScope *, 4> &Children = WS->getScopes();
2334 bool visitedChildren = false;
2335 for (SmallVector<DbgScope *, 4>::const_iterator SI = Children.begin(),
2336 SE = Children.end(); SI != SE; ++SI) {
2337 DbgScope *ChildScope = *SI;
2338 if (!ChildScope->getDFSOut()) {
2339 WorkStack.push_back(ChildScope);
2340 visitedChildren = true;
2341 ChildScope->setDFSIn(++Counter);
2342 break;
2343 }
2344 }
2345 if (!visitedChildren) {
2346 WorkStack.pop_back();
2347 WS->setDFSOut(++Counter);
2348 }
2349 }
2350}
2351
2352/// printDbgScopeInfo - Print DbgScope info for each machine instruction.
2353static
2354void printDbgScopeInfo(LLVMContext &Ctx, const MachineFunction *MF,
2355 DenseMap<const MachineInstr *, DbgScope *> &MI2ScopeMap)
2356{
2357#ifndef NDEBUG
2358 unsigned PrevDFSIn = 0;
2359 for (MachineFunction::const_iterator I = MF->begin(), E = MF->end();
2360 I != E; ++I) {
2361 for (MachineBasicBlock::const_iterator II = I->begin(), IE = I->end();
2362 II != IE; ++II) {
2363 const MachineInstr *MInsn = II;
Devang Patele9f8f5e2010-05-07 20:54:48 +00002364 const MDNode *Scope = NULL;
2365 const MDNode *InlinedAt = NULL;
Devang Pateleac9c072010-04-27 19:46:33 +00002366
2367 // Check if instruction has valid location information.
2368 if (hasValidLocation(Ctx, MInsn, Scope, InlinedAt)) {
2369 dbgs() << " [ ";
2370 if (InlinedAt)
2371 dbgs() << "*";
2372 DenseMap<const MachineInstr *, DbgScope *>::iterator DI =
2373 MI2ScopeMap.find(MInsn);
2374 if (DI != MI2ScopeMap.end()) {
2375 DbgScope *S = DI->second;
2376 dbgs() << S->getDFSIn();
2377 PrevDFSIn = S->getDFSIn();
2378 } else
2379 dbgs() << PrevDFSIn;
2380 } else
2381 dbgs() << " [ x" << PrevDFSIn;
2382 dbgs() << " ]";
2383 MInsn->dump();
2384 }
2385 dbgs() << "\n";
2386 }
2387#endif
2388}
Devang Patel2c4ceb12009-11-21 02:48:08 +00002389/// extractScopeInformation - Scan machine instructions in this function
Chris Lattner14d750d2010-03-31 05:39:57 +00002390/// and collect DbgScopes. Return true, if at least one scope was found.
Chris Lattnereec791a2010-01-26 23:18:02 +00002391bool DwarfDebug::extractScopeInformation() {
Devang Patelaf9e8472009-10-01 20:31:14 +00002392 // If scope information was extracted using .dbg intrinsics then there is not
2393 // any need to extract these information by scanning each instruction.
2394 if (!DbgScopeMap.empty())
2395 return false;
2396
Dan Gohman314bf7c2010-04-23 01:18:53 +00002397 // Scan each instruction and create scopes. First build working set of scopes.
Devang Pateleac9c072010-04-27 19:46:33 +00002398 LLVMContext &Ctx = Asm->MF->getFunction()->getContext();
2399 SmallVector<DbgRange, 4> MIRanges;
2400 DenseMap<const MachineInstr *, DbgScope *> MI2ScopeMap;
Devang Patele9f8f5e2010-05-07 20:54:48 +00002401 const MDNode *PrevScope = NULL;
2402 const MDNode *PrevInlinedAt = NULL;
Devang Pateleac9c072010-04-27 19:46:33 +00002403 const MachineInstr *RangeBeginMI = NULL;
2404 const MachineInstr *PrevMI = NULL;
Chris Lattnerd38fee82010-04-05 00:13:49 +00002405 for (MachineFunction::const_iterator I = Asm->MF->begin(), E = Asm->MF->end();
Devang Patelaf9e8472009-10-01 20:31:14 +00002406 I != E; ++I) {
2407 for (MachineBasicBlock::const_iterator II = I->begin(), IE = I->end();
2408 II != IE; ++II) {
2409 const MachineInstr *MInsn = II;
Devang Patele9f8f5e2010-05-07 20:54:48 +00002410 const MDNode *Scope = NULL;
2411 const MDNode *InlinedAt = NULL;
Devang Pateleac9c072010-04-27 19:46:33 +00002412
2413 // Check if instruction has valid location information.
2414 if (!hasValidLocation(Ctx, MInsn, Scope, InlinedAt)) {
2415 PrevMI = MInsn;
2416 continue;
2417 }
Chris Lattnerde4845c2010-04-02 19:42:39 +00002418
Devang Pateleac9c072010-04-27 19:46:33 +00002419 // If scope has not changed then skip this instruction.
2420 if (Scope == PrevScope && PrevInlinedAt == InlinedAt) {
2421 PrevMI = MInsn;
2422 continue;
2423 }
2424
2425 if (RangeBeginMI) {
2426 // If we have alread seen a beginning of a instruction range and
2427 // current instruction scope does not match scope of first instruction
2428 // in this range then create a new instruction range.
2429 DbgRange R(RangeBeginMI, PrevMI);
2430 MI2ScopeMap[RangeBeginMI] = getOrCreateDbgScope(PrevScope, PrevInlinedAt);
2431 MIRanges.push_back(R);
2432 }
2433
2434 // This is a beginning of a new instruction range.
2435 RangeBeginMI = MInsn;
Chris Lattnerde4845c2010-04-02 19:42:39 +00002436
Devang Pateleac9c072010-04-27 19:46:33 +00002437 // Reset previous markers.
2438 PrevMI = MInsn;
2439 PrevScope = Scope;
2440 PrevInlinedAt = InlinedAt;
Devang Patel53bb5c92009-11-10 23:06:00 +00002441 }
2442 }
2443
Devang Pateleac9c072010-04-27 19:46:33 +00002444 // Create last instruction range.
2445 if (RangeBeginMI && PrevMI && PrevScope) {
2446 DbgRange R(RangeBeginMI, PrevMI);
2447 MIRanges.push_back(R);
2448 MI2ScopeMap[RangeBeginMI] = getOrCreateDbgScope(PrevScope, PrevInlinedAt);
Devang Patelaf9e8472009-10-01 20:31:14 +00002449 }
Devang Pateleac9c072010-04-27 19:46:33 +00002450
Devang Patel344130e2010-01-04 20:44:00 +00002451 if (!CurrentFnDbgScope)
2452 return false;
2453
Devang Pateleac9c072010-04-27 19:46:33 +00002454 calculateDominanceGraph(CurrentFnDbgScope);
2455 if (PrintDbgScope)
2456 printDbgScopeInfo(Ctx, Asm->MF, MI2ScopeMap);
2457
2458 // Find ranges of instructions covered by each DbgScope;
2459 DbgScope *PrevDbgScope = NULL;
2460 for (SmallVector<DbgRange, 4>::const_iterator RI = MIRanges.begin(),
2461 RE = MIRanges.end(); RI != RE; ++RI) {
2462 const DbgRange &R = *RI;
2463 DbgScope *S = MI2ScopeMap.lookup(R.first);
2464 assert (S && "Lost DbgScope for a machine instruction!");
2465 if (PrevDbgScope && !PrevDbgScope->dominates(S))
2466 PrevDbgScope->closeInsnRange(S);
2467 S->openInsnRange(R.first);
2468 S->extendInsnRange(R.second);
2469 PrevDbgScope = S;
2470 }
2471
2472 if (PrevDbgScope)
2473 PrevDbgScope->closeInsnRange();
Devang Patelaf9e8472009-10-01 20:31:14 +00002474
Devang Patele37b0c62010-04-08 18:43:56 +00002475 identifyScopeMarkers();
Devang Patel6122a4d2010-04-08 15:37:09 +00002476
2477 return !DbgScopeMap.empty();
2478}
2479
Devang Pateleac9c072010-04-27 19:46:33 +00002480/// identifyScopeMarkers() -
2481/// Each DbgScope has first instruction and last instruction to mark beginning
2482/// and end of a scope respectively. Create an inverse map that list scopes
2483/// starts (and ends) with an instruction. One instruction may start (or end)
2484/// multiple scopes. Ignore scopes that are not reachable.
Devang Patele37b0c62010-04-08 18:43:56 +00002485void DwarfDebug::identifyScopeMarkers() {
Devang Patel42aafd72010-01-20 02:05:23 +00002486 SmallVector<DbgScope *, 4> WorkList;
2487 WorkList.push_back(CurrentFnDbgScope);
2488 while (!WorkList.empty()) {
Chris Lattner14d750d2010-03-31 05:39:57 +00002489 DbgScope *S = WorkList.pop_back_val();
Devang Pateleac9c072010-04-27 19:46:33 +00002490
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002491 const SmallVector<DbgScope *, 4> &Children = S->getScopes();
Devang Patel42aafd72010-01-20 02:05:23 +00002492 if (!Children.empty())
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002493 for (SmallVector<DbgScope *, 4>::const_iterator SI = Children.begin(),
Devang Patel42aafd72010-01-20 02:05:23 +00002494 SE = Children.end(); SI != SE; ++SI)
2495 WorkList.push_back(*SI);
2496
Devang Patel53bb5c92009-11-10 23:06:00 +00002497 if (S->isAbstractScope())
2498 continue;
Devang Pateleac9c072010-04-27 19:46:33 +00002499
2500 const SmallVector<DbgRange, 4> &Ranges = S->getRanges();
2501 if (Ranges.empty())
2502 continue;
2503 for (SmallVector<DbgRange, 4>::const_iterator RI = Ranges.begin(),
2504 RE = Ranges.end(); RI != RE; ++RI) {
Devang Patel461a6462010-05-19 21:58:28 +00002505 assert(RI->first && "DbgRange does not have first instruction!");
2506 assert(RI->second && "DbgRange does not have second instruction!");
2507 InsnsBeginScopeSet.insert(RI->first);
Devang Pateleac9c072010-04-27 19:46:33 +00002508 InsnsEndScopeSet.insert(RI->second);
2509 }
Devang Patelaf9e8472009-10-01 20:31:14 +00002510 }
Devang Patelaf9e8472009-10-01 20:31:14 +00002511}
2512
Dan Gohman084751c2010-04-20 00:37:27 +00002513/// FindFirstDebugLoc - Find the first debug location in the function. This
2514/// is intended to be an approximation for the source position of the
2515/// beginning of the function.
2516static DebugLoc FindFirstDebugLoc(const MachineFunction *MF) {
2517 for (MachineFunction::const_iterator I = MF->begin(), E = MF->end();
2518 I != E; ++I)
2519 for (MachineBasicBlock::const_iterator MBBI = I->begin(), MBBE = I->end();
2520 MBBI != MBBE; ++MBBI) {
2521 DebugLoc DL = MBBI->getDebugLoc();
2522 if (!DL.isUnknown())
2523 return DL;
2524 }
2525 return DebugLoc();
2526}
2527
Devang Patel2c4ceb12009-11-21 02:48:08 +00002528/// beginFunction - Gather pre-function debug information. Assumes being
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002529/// emitted immediately after the function entry point.
Chris Lattnereec791a2010-01-26 23:18:02 +00002530void DwarfDebug::beginFunction(const MachineFunction *MF) {
Chris Lattner994cb122010-04-05 03:52:55 +00002531 if (!MMI->hasDebugInfo()) return;
Bill Wendling5f017e82010-04-07 09:28:04 +00002532 if (!extractScopeInformation()) return;
Chris Lattnera909d662010-03-29 20:38:20 +00002533
Devang Patel98e1cac2010-05-14 21:01:35 +00002534 collectVariableInfo(MF);
Devang Patel60b35bd2009-10-06 18:37:31 +00002535
Devang Pateleac9c072010-04-27 19:46:33 +00002536 FunctionBeginSym = Asm->GetTempSymbol("func_begin",
2537 Asm->getFunctionNumber());
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002538 // Assumes in correct section after the entry point.
Devang Pateleac9c072010-04-27 19:46:33 +00002539 Asm->OutStreamer.EmitLabel(FunctionBeginSym);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002540
2541 // Emit label for the implicitly defined dbg.stoppoint at the start of the
2542 // function.
Dan Gohman084751c2010-04-20 00:37:27 +00002543 DebugLoc FDL = FindFirstDebugLoc(MF);
Chris Lattnerde4845c2010-04-02 19:42:39 +00002544 if (FDL.isUnknown()) return;
2545
Devang Patele9f8f5e2010-05-07 20:54:48 +00002546 const MDNode *Scope = FDL.getScope(MF->getFunction()->getContext());
Chris Lattnerde4845c2010-04-02 19:42:39 +00002547
2548 DISubprogram SP = getDISubprogram(Scope);
2549 unsigned Line, Col;
2550 if (SP.Verify()) {
2551 Line = SP.getLineNumber();
2552 Col = 0;
2553 } else {
2554 Line = FDL.getLine();
2555 Col = FDL.getCol();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002556 }
Chris Lattnerde4845c2010-04-02 19:42:39 +00002557
2558 recordSourceLine(Line, Col, Scope);
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002559}
2560
Devang Patel2c4ceb12009-11-21 02:48:08 +00002561/// endFunction - Gather and emit post-function debug information.
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002562///
Chris Lattnereec791a2010-01-26 23:18:02 +00002563void DwarfDebug::endFunction(const MachineFunction *MF) {
Bill Wendling5f017e82010-04-07 09:28:04 +00002564 if (!MMI->hasDebugInfo() || DbgScopeMap.empty()) return;
Devang Patel70d75ca2009-11-12 19:02:56 +00002565
Devang Patel344130e2010-01-04 20:44:00 +00002566 if (CurrentFnDbgScope) {
2567 // Define end label for subprogram.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002568 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("func_end",
2569 Asm->getFunctionNumber()));
Devang Patel344130e2010-01-04 20:44:00 +00002570
2571 // Get function line info.
2572 if (!Lines.empty()) {
2573 // Get section line info.
2574 unsigned ID = SectionMap.insert(Asm->getCurrentSection());
2575 if (SectionSourceLines.size() < ID) SectionSourceLines.resize(ID);
2576 std::vector<SrcLineInfo> &SectionLineInfos = SectionSourceLines[ID-1];
2577 // Append the function info to section info.
2578 SectionLineInfos.insert(SectionLineInfos.end(),
2579 Lines.begin(), Lines.end());
2580 }
2581
2582 // Construct abstract scopes.
2583 for (SmallVector<DbgScope *, 4>::iterator AI = AbstractScopesList.begin(),
2584 AE = AbstractScopesList.end(); AI != AE; ++AI)
2585 constructScopeDIE(*AI);
2586
Devang Patel9c488372010-05-04 06:15:30 +00002587 DIE *CurFnDIE = constructScopeDIE(CurrentFnDbgScope);
Devang Patel344130e2010-01-04 20:44:00 +00002588
Devang Patel9c488372010-05-04 06:15:30 +00002589 if (!DisableFramePointerElim(*MF))
2590 addUInt(CurFnDIE, dwarf::DW_AT_APPLE_omit_frame_ptr,
2591 dwarf::DW_FORM_flag, 1);
2592
2593
Chris Lattnerd38fee82010-04-05 00:13:49 +00002594 DebugFrames.push_back(FunctionDebugFrameInfo(Asm->getFunctionNumber(),
Devang Patel344130e2010-01-04 20:44:00 +00002595 MMI->getFrameMoves()));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002596 }
2597
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002598 // Clear debug info
Devang Patelf54b8522010-01-19 01:26:02 +00002599 CurrentFnDbgScope = NULL;
Devang Patel26c1e562010-05-20 16:36:41 +00002600 DbgVariableToFrameIndexMap.clear();
2601 VarToAbstractVarMap.clear();
2602 DbgVariableToDbgInstMap.clear();
2603 DbgVariableLabelsMap.clear();
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002604 DeleteContainerSeconds(DbgScopeMap);
Devang Patel461a6462010-05-19 21:58:28 +00002605 InsnsBeginScopeSet.clear();
Devang Patel51424712010-04-09 16:04:20 +00002606 InsnsEndScopeSet.clear();
Devang Patelaead63c2010-03-29 22:59:58 +00002607 DbgValueStartMap.clear();
Devang Patelf54b8522010-01-19 01:26:02 +00002608 ConcreteScopes.clear();
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002609 DeleteContainerSeconds(AbstractScopes);
Devang Patelf54b8522010-01-19 01:26:02 +00002610 AbstractScopesList.clear();
Jeffrey Yasskin5c213dc2010-03-12 17:45:06 +00002611 AbstractVariables.clear();
Devang Pateleac9c072010-04-27 19:46:33 +00002612 LabelsBeforeInsn.clear();
2613 LabelsAfterInsn.clear();
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002614 Lines.clear();
Devang Patelf2548ca2010-04-16 23:33:45 +00002615 PrevLabel = NULL;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002616}
2617
Devang Patel26c1e562010-05-20 16:36:41 +00002618/// recordVariableFrameIndex - Record a variable's index.
2619void DwarfDebug::recordVariableFrameIndex(const DbgVariable *V, int Index) {
2620 assert (V && "Invalid DbgVariable!");
2621 DbgVariableToFrameIndexMap[V] = Index;
2622}
2623
2624/// findVariableFrameIndex - Return true if frame index for the variable
2625/// is found. Update FI to hold value of the index.
2626bool DwarfDebug::findVariableFrameIndex(const DbgVariable *V, int *FI) {
2627 assert (V && "Invalid DbgVariable!");
2628 DenseMap<const DbgVariable *, int>::iterator I =
2629 DbgVariableToFrameIndexMap.find(V);
2630 if (I == DbgVariableToFrameIndexMap.end())
2631 return false;
2632 *FI = I->second;
2633 return true;
2634}
2635
2636/// findVariableLabel - Find MCSymbol for the variable.
2637const MCSymbol *DwarfDebug::findVariableLabel(const DbgVariable *V) {
2638 DenseMap<const DbgVariable *, const MCSymbol *>::iterator I
2639 = DbgVariableLabelsMap.find(V);
2640 if (I == DbgVariableLabelsMap.end())
2641 return NULL;
2642 else return I->second;
2643}
2644
Devang Patelee432862010-05-20 19:57:06 +00002645/// findDbgScope - Find DbgScope for the debug loc attached with an
2646/// instruction.
2647DbgScope *DwarfDebug::findDbgScope(const MachineInstr *MInsn) {
2648 DbgScope *Scope = NULL;
2649 LLVMContext &Ctx =
2650 MInsn->getParent()->getParent()->getFunction()->getContext();
2651 DebugLoc DL = MInsn->getDebugLoc();
2652
2653 if (DL.isUnknown())
2654 return Scope;
2655
2656 if (const MDNode *IA = DL.getInlinedAt(Ctx))
2657 Scope = ConcreteScopes.lookup(IA);
2658 if (Scope == 0)
2659 Scope = DbgScopeMap.lookup(DL.getScope(Ctx));
2660
2661 return Scope;
2662}
2663
2664
Chris Lattnerc6087842010-03-09 04:54:43 +00002665/// recordSourceLine - Register a source line with debug info. Returns the
2666/// unique label that was emitted and which provides correspondence to
2667/// the source line list.
Devang Patele9f8f5e2010-05-07 20:54:48 +00002668MCSymbol *DwarfDebug::recordSourceLine(unsigned Line, unsigned Col, const MDNode *S) {
Devang Patel65dbc902009-11-25 17:36:49 +00002669 StringRef Dir;
2670 StringRef Fn;
Devang Patelf84548d2009-10-05 18:03:19 +00002671
Dan Gohman1cc0d622010-05-05 23:41:32 +00002672 unsigned Src = 1;
2673 if (S) {
2674 DIDescriptor Scope(S);
Devang Patelf84548d2009-10-05 18:03:19 +00002675
Dan Gohman1cc0d622010-05-05 23:41:32 +00002676 if (Scope.isCompileUnit()) {
2677 DICompileUnit CU(S);
2678 Dir = CU.getDirectory();
2679 Fn = CU.getFilename();
2680 } else if (Scope.isSubprogram()) {
2681 DISubprogram SP(S);
2682 Dir = SP.getDirectory();
2683 Fn = SP.getFilename();
2684 } else if (Scope.isLexicalBlock()) {
2685 DILexicalBlock DB(S);
2686 Dir = DB.getDirectory();
2687 Fn = DB.getFilename();
2688 } else
2689 assert(0 && "Unexpected scope info");
2690
2691 Src = GetOrCreateSourceID(Dir, Fn);
2692 }
2693
Chris Lattner63d78362010-03-14 08:36:50 +00002694 MCSymbol *Label = MMI->getContext().CreateTempSymbol();
Chris Lattner25b68c62010-03-14 08:15:55 +00002695 Lines.push_back(SrcLineInfo(Line, Col, Src, Label));
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002696
Chris Lattnerc6087842010-03-09 04:54:43 +00002697 Asm->OutStreamer.EmitLabel(Label);
2698 return Label;
Bill Wendlingf0fb9872009-05-20 23:19:06 +00002699}
2700
Bill Wendling829e67b2009-05-20 23:22:40 +00002701//===----------------------------------------------------------------------===//
2702// Emit Methods
2703//===----------------------------------------------------------------------===//
2704
Devang Patel2c4ceb12009-11-21 02:48:08 +00002705/// computeSizeAndOffset - Compute the size and offset of a DIE.
Bill Wendling94d04b82009-05-20 23:21:38 +00002706///
Jim Grosbach7ab38df2009-11-22 19:20:36 +00002707unsigned
2708DwarfDebug::computeSizeAndOffset(DIE *Die, unsigned Offset, bool Last) {
Bill Wendling94d04b82009-05-20 23:21:38 +00002709 // Get the children.
2710 const std::vector<DIE *> &Children = Die->getChildren();
2711
2712 // If not last sibling and has children then add sibling offset attribute.
Jeffrey Yasskin638fe8d2010-03-22 18:47:14 +00002713 if (!Last && !Children.empty())
Benjamin Kramer345ef342010-03-31 19:34:01 +00002714 Die->addSiblingOffset(DIEValueAllocator);
Bill Wendling94d04b82009-05-20 23:21:38 +00002715
2716 // Record the abbreviation.
Devang Patel2c4ceb12009-11-21 02:48:08 +00002717 assignAbbrevNumber(Die->getAbbrev());
Bill Wendling94d04b82009-05-20 23:21:38 +00002718
2719 // Get the abbreviation for this DIE.
2720 unsigned AbbrevNumber = Die->getAbbrevNumber();
2721 const DIEAbbrev *Abbrev = Abbreviations[AbbrevNumber - 1];
2722
2723 // Set DIE offset
2724 Die->setOffset(Offset);
2725
2726 // Start the size with the size of abbreviation code.
Chris Lattneraf76e592009-08-22 20:48:53 +00002727 Offset += MCAsmInfo::getULEB128Size(AbbrevNumber);
Bill Wendling94d04b82009-05-20 23:21:38 +00002728
2729 const SmallVector<DIEValue*, 32> &Values = Die->getValues();
2730 const SmallVector<DIEAbbrevData, 8> &AbbrevData = Abbrev->getData();
2731
2732 // Size the DIE attribute values.
2733 for (unsigned i = 0, N = Values.size(); i < N; ++i)
2734 // Size attribute value.
Chris Lattnera37d5382010-04-05 00:18:22 +00002735 Offset += Values[i]->SizeOf(Asm, AbbrevData[i].getForm());
Bill Wendling94d04b82009-05-20 23:21:38 +00002736
2737 // Size the DIE children if any.
2738 if (!Children.empty()) {
2739 assert(Abbrev->getChildrenFlag() == dwarf::DW_CHILDREN_yes &&
2740 "Children flag not set");
2741
2742 for (unsigned j = 0, M = Children.size(); j < M; ++j)
Devang Patel2c4ceb12009-11-21 02:48:08 +00002743 Offset = computeSizeAndOffset(Children[j], Offset, (j + 1) == M);
Bill Wendling94d04b82009-05-20 23:21:38 +00002744
2745 // End of children marker.
2746 Offset += sizeof(int8_t);
2747 }
2748
2749 Die->setSize(Offset - Die->getOffset());
2750 return Offset;
2751}
2752
Devang Patel2c4ceb12009-11-21 02:48:08 +00002753/// computeSizeAndOffsets - Compute the size and offset of all the DIEs.
Bill Wendling94d04b82009-05-20 23:21:38 +00002754///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002755void DwarfDebug::computeSizeAndOffsets() {
Devang Patel163a9f72010-05-10 22:49:55 +00002756 unsigned PrevOffset = 0;
2757 for (DenseMap<const MDNode *, CompileUnit *>::iterator I = CUMap.begin(),
2758 E = CUMap.end(); I != E; ++I) {
2759 // Compute size of compile unit header.
2760 static unsigned Offset = PrevOffset +
2761 sizeof(int32_t) + // Length of Compilation Unit Info
2762 sizeof(int16_t) + // DWARF version number
2763 sizeof(int32_t) + // Offset Into Abbrev. Section
2764 sizeof(int8_t); // Pointer Size (in bytes)
2765 computeSizeAndOffset(I->second->getCUDie(), Offset, true);
2766 PrevOffset = Offset;
2767 }
Bill Wendling94d04b82009-05-20 23:21:38 +00002768}
2769
Chris Lattner11b8f302010-04-04 23:02:02 +00002770/// EmitSectionSym - Switch to the specified MCSection and emit an assembler
2771/// temporary label to it if SymbolStem is specified.
Chris Lattner9c69e285532010-04-04 22:59:04 +00002772static MCSymbol *EmitSectionSym(AsmPrinter *Asm, const MCSection *Section,
Chris Lattner11b8f302010-04-04 23:02:02 +00002773 const char *SymbolStem = 0) {
Chris Lattner9c69e285532010-04-04 22:59:04 +00002774 Asm->OutStreamer.SwitchSection(Section);
Chris Lattner11b8f302010-04-04 23:02:02 +00002775 if (!SymbolStem) return 0;
2776
Chris Lattner9c69e285532010-04-04 22:59:04 +00002777 MCSymbol *TmpSym = Asm->GetTempSymbol(SymbolStem);
2778 Asm->OutStreamer.EmitLabel(TmpSym);
2779 return TmpSym;
2780}
2781
2782/// EmitSectionLabels - Emit initial Dwarf sections with a label at
2783/// the start of each one.
Chris Lattnerfa070b02010-04-04 22:33:59 +00002784void DwarfDebug::EmitSectionLabels() {
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002785 const TargetLoweringObjectFile &TLOF = Asm->getObjFileLowering();
Daniel Dunbarf612ff62009-09-19 20:40:05 +00002786
Bill Wendling94d04b82009-05-20 23:21:38 +00002787 // Dwarf sections base addresses.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002788 if (Asm->MAI->doesDwarfRequireFrameSection()) {
Chris Lattner9c69e285532010-04-04 22:59:04 +00002789 DwarfFrameSectionSym =
2790 EmitSectionSym(Asm, TLOF.getDwarfFrameSection(), "section_debug_frame");
2791 }
Bill Wendling94d04b82009-05-20 23:21:38 +00002792
Chris Lattner9c69e285532010-04-04 22:59:04 +00002793 DwarfInfoSectionSym =
2794 EmitSectionSym(Asm, TLOF.getDwarfInfoSection(), "section_info");
2795 DwarfAbbrevSectionSym =
2796 EmitSectionSym(Asm, TLOF.getDwarfAbbrevSection(), "section_abbrev");
Chris Lattner11b8f302010-04-04 23:02:02 +00002797 EmitSectionSym(Asm, TLOF.getDwarfARangesSection());
Chris Lattner9c69e285532010-04-04 22:59:04 +00002798
2799 if (const MCSection *MacroInfo = TLOF.getDwarfMacroInfoSection())
Chris Lattner11b8f302010-04-04 23:02:02 +00002800 EmitSectionSym(Asm, MacroInfo);
Bill Wendling94d04b82009-05-20 23:21:38 +00002801
Chris Lattner11b8f302010-04-04 23:02:02 +00002802 EmitSectionSym(Asm, TLOF.getDwarfLineSection());
2803 EmitSectionSym(Asm, TLOF.getDwarfLocSection());
2804 EmitSectionSym(Asm, TLOF.getDwarfPubNamesSection());
2805 EmitSectionSym(Asm, TLOF.getDwarfPubTypesSection());
Chris Lattner9c69e285532010-04-04 22:59:04 +00002806 DwarfStrSectionSym =
2807 EmitSectionSym(Asm, TLOF.getDwarfStrSection(), "section_str");
Devang Patelf2548ca2010-04-16 23:33:45 +00002808 DwarfDebugRangeSectionSym = EmitSectionSym(Asm, TLOF.getDwarfRangesSection(),
2809 "debug_range");
Bill Wendling94d04b82009-05-20 23:21:38 +00002810
Chris Lattner9c69e285532010-04-04 22:59:04 +00002811 TextSectionSym = EmitSectionSym(Asm, TLOF.getTextSection(), "text_begin");
Chris Lattner4ad1efe2010-04-04 23:10:38 +00002812 EmitSectionSym(Asm, TLOF.getDataSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002813}
2814
Devang Patel2c4ceb12009-11-21 02:48:08 +00002815/// emitDIE - Recusively Emits a debug information entry.
Bill Wendling94d04b82009-05-20 23:21:38 +00002816///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002817void DwarfDebug::emitDIE(DIE *Die) {
Bill Wendling94d04b82009-05-20 23:21:38 +00002818 // Get the abbreviation for this DIE.
2819 unsigned AbbrevNumber = Die->getAbbrevNumber();
2820 const DIEAbbrev *Abbrev = Abbreviations[AbbrevNumber - 1];
2821
Bill Wendling94d04b82009-05-20 23:21:38 +00002822 // Emit the code (index) for the abbreviation.
Chris Lattner3f53c832010-04-04 18:52:31 +00002823 if (Asm->isVerbose())
Chris Lattner894d75a2010-01-22 23:18:42 +00002824 Asm->OutStreamer.AddComment("Abbrev [" + Twine(AbbrevNumber) + "] 0x" +
2825 Twine::utohexstr(Die->getOffset()) + ":0x" +
2826 Twine::utohexstr(Die->getSize()) + " " +
2827 dwarf::TagString(Abbrev->getTag()));
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002828 Asm->EmitULEB128(AbbrevNumber);
Bill Wendling94d04b82009-05-20 23:21:38 +00002829
Jeffrey Yasskin638fe8d2010-03-22 18:47:14 +00002830 const SmallVector<DIEValue*, 32> &Values = Die->getValues();
Bill Wendling94d04b82009-05-20 23:21:38 +00002831 const SmallVector<DIEAbbrevData, 8> &AbbrevData = Abbrev->getData();
2832
2833 // Emit the DIE attribute values.
2834 for (unsigned i = 0, N = Values.size(); i < N; ++i) {
2835 unsigned Attr = AbbrevData[i].getAttribute();
2836 unsigned Form = AbbrevData[i].getForm();
2837 assert(Form && "Too many attributes for DIE (check abbreviation)");
2838
Chris Lattner3f53c832010-04-04 18:52:31 +00002839 if (Asm->isVerbose())
Chris Lattnera8013622010-01-24 18:54:17 +00002840 Asm->OutStreamer.AddComment(dwarf::AttributeString(Attr));
2841
Bill Wendling94d04b82009-05-20 23:21:38 +00002842 switch (Attr) {
2843 case dwarf::DW_AT_sibling:
Devang Patel2c4ceb12009-11-21 02:48:08 +00002844 Asm->EmitInt32(Die->getSiblingOffset());
Bill Wendling94d04b82009-05-20 23:21:38 +00002845 break;
2846 case dwarf::DW_AT_abstract_origin: {
2847 DIEEntry *E = cast<DIEEntry>(Values[i]);
2848 DIE *Origin = E->getEntry();
Devang Patel53bb5c92009-11-10 23:06:00 +00002849 unsigned Addr = Origin->getOffset();
Bill Wendling94d04b82009-05-20 23:21:38 +00002850 Asm->EmitInt32(Addr);
2851 break;
2852 }
Devang Patelf2548ca2010-04-16 23:33:45 +00002853 case dwarf::DW_AT_ranges: {
2854 // DW_AT_range Value encodes offset in debug_range section.
2855 DIEInteger *V = cast<DIEInteger>(Values[i]);
2856 Asm->EmitLabelOffsetDifference(DwarfDebugRangeSectionSym,
2857 V->getValue(),
2858 DwarfDebugRangeSectionSym,
2859 4);
2860 break;
2861 }
Bill Wendling94d04b82009-05-20 23:21:38 +00002862 default:
2863 // Emit an attribute using the defined form.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002864 Values[i]->EmitValue(Asm, Form);
Bill Wendling94d04b82009-05-20 23:21:38 +00002865 break;
2866 }
Bill Wendling94d04b82009-05-20 23:21:38 +00002867 }
2868
2869 // Emit the DIE children if any.
2870 if (Abbrev->getChildrenFlag() == dwarf::DW_CHILDREN_yes) {
2871 const std::vector<DIE *> &Children = Die->getChildren();
2872
2873 for (unsigned j = 0, M = Children.size(); j < M; ++j)
Devang Patel2c4ceb12009-11-21 02:48:08 +00002874 emitDIE(Children[j]);
Bill Wendling94d04b82009-05-20 23:21:38 +00002875
Chris Lattner3f53c832010-04-04 18:52:31 +00002876 if (Asm->isVerbose())
Chris Lattner233f52b2010-03-09 23:52:58 +00002877 Asm->OutStreamer.AddComment("End Of Children Mark");
2878 Asm->EmitInt8(0);
Bill Wendling94d04b82009-05-20 23:21:38 +00002879 }
2880}
2881
Devang Patel8a241142009-12-09 18:24:21 +00002882/// emitDebugInfo - Emit the debug info section.
Bill Wendling94d04b82009-05-20 23:21:38 +00002883///
Devang Patel8a241142009-12-09 18:24:21 +00002884void DwarfDebug::emitDebugInfo() {
2885 // Start debug info section.
2886 Asm->OutStreamer.SwitchSection(
2887 Asm->getObjFileLowering().getDwarfInfoSection());
Devang Patel163a9f72010-05-10 22:49:55 +00002888 for (DenseMap<const MDNode *, CompileUnit *>::iterator I = CUMap.begin(),
2889 E = CUMap.end(); I != E; ++I) {
2890 CompileUnit *TheCU = I->second;
2891 DIE *Die = TheCU->getCUDie();
2892
2893 // Emit the compile units header.
2894 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("info_begin",
2895 TheCU->getID()));
2896
2897 // Emit size of content not including length itself
2898 unsigned ContentSize = Die->getSize() +
2899 sizeof(int16_t) + // DWARF version number
2900 sizeof(int32_t) + // Offset Into Abbrev. Section
2901 sizeof(int8_t) + // Pointer Size (in bytes)
2902 sizeof(int32_t); // FIXME - extra pad for gdb bug.
2903
2904 Asm->OutStreamer.AddComment("Length of Compilation Unit Info");
2905 Asm->EmitInt32(ContentSize);
2906 Asm->OutStreamer.AddComment("DWARF version number");
2907 Asm->EmitInt16(dwarf::DWARF_VERSION);
2908 Asm->OutStreamer.AddComment("Offset Into Abbrev. Section");
2909 Asm->EmitSectionOffset(Asm->GetTempSymbol("abbrev_begin"),
2910 DwarfAbbrevSectionSym);
2911 Asm->OutStreamer.AddComment("Address Size (in bytes)");
2912 Asm->EmitInt8(Asm->getTargetData().getPointerSize());
2913
2914 emitDIE(Die);
2915 // FIXME - extra padding for gdb bug.
2916 Asm->OutStreamer.AddComment("4 extra padding bytes for GDB");
2917 Asm->EmitInt8(0);
2918 Asm->EmitInt8(0);
2919 Asm->EmitInt8(0);
2920 Asm->EmitInt8(0);
2921 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("info_end", TheCU->getID()));
2922 }
Bill Wendling94d04b82009-05-20 23:21:38 +00002923}
2924
Devang Patel2c4ceb12009-11-21 02:48:08 +00002925/// emitAbbreviations - Emit the abbreviation section.
Bill Wendling94d04b82009-05-20 23:21:38 +00002926///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002927void DwarfDebug::emitAbbreviations() const {
Bill Wendling94d04b82009-05-20 23:21:38 +00002928 // Check to see if it is worth the effort.
2929 if (!Abbreviations.empty()) {
2930 // Start the debug abbrev section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002931 Asm->OutStreamer.SwitchSection(
2932 Asm->getObjFileLowering().getDwarfAbbrevSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002933
Chris Lattnerc0215722010-04-04 19:25:43 +00002934 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("abbrev_begin"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002935
2936 // For each abbrevation.
2937 for (unsigned i = 0, N = Abbreviations.size(); i < N; ++i) {
2938 // Get abbreviation data
2939 const DIEAbbrev *Abbrev = Abbreviations[i];
2940
2941 // Emit the abbrevations code (base 1 index.)
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002942 Asm->EmitULEB128(Abbrev->getNumber(), "Abbreviation Code");
Bill Wendling94d04b82009-05-20 23:21:38 +00002943
2944 // Emit the abbreviations data.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002945 Abbrev->Emit(Asm);
Bill Wendling94d04b82009-05-20 23:21:38 +00002946 }
2947
2948 // Mark end of abbreviations.
Chris Lattner7e1a8f82010-04-04 19:09:29 +00002949 Asm->EmitULEB128(0, "EOM(3)");
Bill Wendling94d04b82009-05-20 23:21:38 +00002950
Chris Lattnerc0215722010-04-04 19:25:43 +00002951 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("abbrev_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00002952 }
2953}
2954
Devang Patel2c4ceb12009-11-21 02:48:08 +00002955/// emitEndOfLineMatrix - Emit the last address of the section and the end of
Bill Wendling94d04b82009-05-20 23:21:38 +00002956/// the line matrix.
2957///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002958void DwarfDebug::emitEndOfLineMatrix(unsigned SectionEnd) {
Bill Wendling94d04b82009-05-20 23:21:38 +00002959 // Define last address of section.
Chris Lattner233f52b2010-03-09 23:52:58 +00002960 Asm->OutStreamer.AddComment("Extended Op");
2961 Asm->EmitInt8(0);
2962
2963 Asm->OutStreamer.AddComment("Op size");
Chris Lattnerd38fee82010-04-05 00:13:49 +00002964 Asm->EmitInt8(Asm->getTargetData().getPointerSize() + 1);
Chris Lattner233f52b2010-03-09 23:52:58 +00002965 Asm->OutStreamer.AddComment("DW_LNE_set_address");
2966 Asm->EmitInt8(dwarf::DW_LNE_set_address);
2967
2968 Asm->OutStreamer.AddComment("Section end label");
Chris Lattnerd85fc6e2010-03-10 01:17:49 +00002969
Chris Lattnerc0215722010-04-04 19:25:43 +00002970 Asm->OutStreamer.EmitSymbolValue(Asm->GetTempSymbol("section_end",SectionEnd),
Chris Lattnerd38fee82010-04-05 00:13:49 +00002971 Asm->getTargetData().getPointerSize(),
2972 0/*AddrSpace*/);
Bill Wendling94d04b82009-05-20 23:21:38 +00002973
2974 // Mark end of matrix.
Chris Lattner233f52b2010-03-09 23:52:58 +00002975 Asm->OutStreamer.AddComment("DW_LNE_end_sequence");
2976 Asm->EmitInt8(0);
Chris Lattner0ad9c912010-01-22 22:09:00 +00002977 Asm->EmitInt8(1);
Chris Lattner894d75a2010-01-22 23:18:42 +00002978 Asm->EmitInt8(1);
Bill Wendling94d04b82009-05-20 23:21:38 +00002979}
2980
Devang Patel2c4ceb12009-11-21 02:48:08 +00002981/// emitDebugLines - Emit source line information.
Bill Wendling94d04b82009-05-20 23:21:38 +00002982///
Devang Patel2c4ceb12009-11-21 02:48:08 +00002983void DwarfDebug::emitDebugLines() {
Bill Wendling94d04b82009-05-20 23:21:38 +00002984 // If the target is using .loc/.file, the assembler will be emitting the
2985 // .debug_line table automatically.
Chris Lattnerd38fee82010-04-05 00:13:49 +00002986 if (Asm->MAI->hasDotLocAndDotFile())
Bill Wendling94d04b82009-05-20 23:21:38 +00002987 return;
2988
2989 // Minimum line delta, thus ranging from -10..(255-10).
2990 const int MinLineDelta = -(dwarf::DW_LNS_fixed_advance_pc + 1);
2991 // Maximum line delta, thus ranging from -10..(255-10).
2992 const int MaxLineDelta = 255 + MinLineDelta;
2993
2994 // Start the dwarf line section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00002995 Asm->OutStreamer.SwitchSection(
2996 Asm->getObjFileLowering().getDwarfLineSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00002997
2998 // Construct the section header.
Chris Lattner233f52b2010-03-09 23:52:58 +00002999 Asm->OutStreamer.AddComment("Length of Source Line Info");
Chris Lattnera6437182010-04-04 19:58:12 +00003000 Asm->EmitLabelDifference(Asm->GetTempSymbol("line_end"),
3001 Asm->GetTempSymbol("line_begin"), 4);
Chris Lattnerc0215722010-04-04 19:25:43 +00003002 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_begin"));
Bill Wendling94d04b82009-05-20 23:21:38 +00003003
Chris Lattner233f52b2010-03-09 23:52:58 +00003004 Asm->OutStreamer.AddComment("DWARF version number");
3005 Asm->EmitInt16(dwarf::DWARF_VERSION);
Bill Wendling94d04b82009-05-20 23:21:38 +00003006
Chris Lattner233f52b2010-03-09 23:52:58 +00003007 Asm->OutStreamer.AddComment("Prolog Length");
Chris Lattnera6437182010-04-04 19:58:12 +00003008 Asm->EmitLabelDifference(Asm->GetTempSymbol("line_prolog_end"),
3009 Asm->GetTempSymbol("line_prolog_begin"), 4);
Chris Lattnerc0215722010-04-04 19:25:43 +00003010 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_prolog_begin"));
Bill Wendling94d04b82009-05-20 23:21:38 +00003011
Chris Lattner233f52b2010-03-09 23:52:58 +00003012 Asm->OutStreamer.AddComment("Minimum Instruction Length");
3013 Asm->EmitInt8(1);
3014 Asm->OutStreamer.AddComment("Default is_stmt_start flag");
3015 Asm->EmitInt8(1);
3016 Asm->OutStreamer.AddComment("Line Base Value (Special Opcodes)");
3017 Asm->EmitInt8(MinLineDelta);
3018 Asm->OutStreamer.AddComment("Line Range Value (Special Opcodes)");
3019 Asm->EmitInt8(MaxLineDelta);
3020 Asm->OutStreamer.AddComment("Special Opcode Base");
3021 Asm->EmitInt8(-MinLineDelta);
Bill Wendling94d04b82009-05-20 23:21:38 +00003022
3023 // Line number standard opcode encodings argument count
Chris Lattner233f52b2010-03-09 23:52:58 +00003024 Asm->OutStreamer.AddComment("DW_LNS_copy arg count");
3025 Asm->EmitInt8(0);
3026 Asm->OutStreamer.AddComment("DW_LNS_advance_pc arg count");
3027 Asm->EmitInt8(1);
3028 Asm->OutStreamer.AddComment("DW_LNS_advance_line arg count");
3029 Asm->EmitInt8(1);
3030 Asm->OutStreamer.AddComment("DW_LNS_set_file arg count");
3031 Asm->EmitInt8(1);
3032 Asm->OutStreamer.AddComment("DW_LNS_set_column arg count");
3033 Asm->EmitInt8(1);
3034 Asm->OutStreamer.AddComment("DW_LNS_negate_stmt arg count");
3035 Asm->EmitInt8(0);
3036 Asm->OutStreamer.AddComment("DW_LNS_set_basic_block arg count");
3037 Asm->EmitInt8(0);
3038 Asm->OutStreamer.AddComment("DW_LNS_const_add_pc arg count");
3039 Asm->EmitInt8(0);
3040 Asm->OutStreamer.AddComment("DW_LNS_fixed_advance_pc arg count");
3041 Asm->EmitInt8(1);
Bill Wendling94d04b82009-05-20 23:21:38 +00003042
3043 // Emit directories.
3044 for (unsigned DI = 1, DE = getNumSourceDirectories()+1; DI != DE; ++DI) {
Chris Lattner4cf202b2010-01-23 03:11:46 +00003045 const std::string &Dir = getSourceDirectoryName(DI);
Chris Lattner3f53c832010-04-04 18:52:31 +00003046 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("Directory");
Chris Lattner4cf202b2010-01-23 03:11:46 +00003047 Asm->OutStreamer.EmitBytes(StringRef(Dir.c_str(), Dir.size()+1), 0);
Bill Wendling94d04b82009-05-20 23:21:38 +00003048 }
3049
Chris Lattner233f52b2010-03-09 23:52:58 +00003050 Asm->OutStreamer.AddComment("End of directories");
3051 Asm->EmitInt8(0);
Bill Wendling94d04b82009-05-20 23:21:38 +00003052
3053 // Emit files.
3054 for (unsigned SI = 1, SE = getNumSourceIds()+1; SI != SE; ++SI) {
3055 // Remember source id starts at 1.
3056 std::pair<unsigned, unsigned> Id = getSourceDirectoryAndFileIds(SI);
Chris Lattner4cf202b2010-01-23 03:11:46 +00003057 const std::string &FN = getSourceFileName(Id.second);
Chris Lattner3f53c832010-04-04 18:52:31 +00003058 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("Source");
Chris Lattner4cf202b2010-01-23 03:11:46 +00003059 Asm->OutStreamer.EmitBytes(StringRef(FN.c_str(), FN.size()+1), 0);
3060
Chris Lattner7e1a8f82010-04-04 19:09:29 +00003061 Asm->EmitULEB128(Id.first, "Directory #");
3062 Asm->EmitULEB128(0, "Mod date");
3063 Asm->EmitULEB128(0, "File size");
Bill Wendling94d04b82009-05-20 23:21:38 +00003064 }
3065
Chris Lattner233f52b2010-03-09 23:52:58 +00003066 Asm->OutStreamer.AddComment("End of files");
3067 Asm->EmitInt8(0);
Bill Wendling94d04b82009-05-20 23:21:38 +00003068
Chris Lattnerc0215722010-04-04 19:25:43 +00003069 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_prolog_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00003070
3071 // A sequence for each text section.
3072 unsigned SecSrcLinesSize = SectionSourceLines.size();
3073
3074 for (unsigned j = 0; j < SecSrcLinesSize; ++j) {
3075 // Isolate current sections line info.
3076 const std::vector<SrcLineInfo> &LineInfos = SectionSourceLines[j];
3077
Bill Wendling94d04b82009-05-20 23:21:38 +00003078 // Dwarf assumes we start with first line of first source file.
3079 unsigned Source = 1;
3080 unsigned Line = 1;
3081
3082 // Construct rows of the address, source, line, column matrix.
3083 for (unsigned i = 0, N = LineInfos.size(); i < N; ++i) {
3084 const SrcLineInfo &LineInfo = LineInfos[i];
Chris Lattner25b68c62010-03-14 08:15:55 +00003085 MCSymbol *Label = LineInfo.getLabel();
Chris Lattnerb9130602010-03-14 02:20:58 +00003086 if (!Label->isDefined()) continue; // Not emitted, in dead code.
Bill Wendling94d04b82009-05-20 23:21:38 +00003087
Chris Lattner0d9d70f2010-03-09 23:38:23 +00003088 if (Asm->isVerbose()) {
Chris Lattner188a87d2010-03-10 01:04:13 +00003089 std::pair<unsigned, unsigned> SrcID =
Bill Wendling94d04b82009-05-20 23:21:38 +00003090 getSourceDirectoryAndFileIds(LineInfo.getSourceID());
Chris Lattner188a87d2010-03-10 01:04:13 +00003091 Asm->OutStreamer.AddComment(Twine(getSourceDirectoryName(SrcID.first)) +
Chris Lattner49f618a2010-03-10 02:29:31 +00003092 "/" +
3093 Twine(getSourceFileName(SrcID.second)) +
Chris Lattner188a87d2010-03-10 01:04:13 +00003094 ":" + Twine(LineInfo.getLine()));
Bill Wendling94d04b82009-05-20 23:21:38 +00003095 }
3096
3097 // Define the line address.
Chris Lattner233f52b2010-03-09 23:52:58 +00003098 Asm->OutStreamer.AddComment("Extended Op");
3099 Asm->EmitInt8(0);
3100 Asm->OutStreamer.AddComment("Op size");
Chris Lattnerd38fee82010-04-05 00:13:49 +00003101 Asm->EmitInt8(Asm->getTargetData().getPointerSize() + 1);
Chris Lattner233f52b2010-03-09 23:52:58 +00003102
3103 Asm->OutStreamer.AddComment("DW_LNE_set_address");
3104 Asm->EmitInt8(dwarf::DW_LNE_set_address);
3105
3106 Asm->OutStreamer.AddComment("Location label");
Chris Lattnerd38fee82010-04-05 00:13:49 +00003107 Asm->OutStreamer.EmitSymbolValue(Label,
3108 Asm->getTargetData().getPointerSize(),
Chris Lattnerb9130602010-03-14 02:20:58 +00003109 0/*AddrSpace*/);
Chris Lattnerd85fc6e2010-03-10 01:17:49 +00003110
Bill Wendling94d04b82009-05-20 23:21:38 +00003111 // If change of source, then switch to the new source.
3112 if (Source != LineInfo.getSourceID()) {
3113 Source = LineInfo.getSourceID();
Chris Lattner233f52b2010-03-09 23:52:58 +00003114 Asm->OutStreamer.AddComment("DW_LNS_set_file");
3115 Asm->EmitInt8(dwarf::DW_LNS_set_file);
Chris Lattner7e1a8f82010-04-04 19:09:29 +00003116 Asm->EmitULEB128(Source, "New Source");
Bill Wendling94d04b82009-05-20 23:21:38 +00003117 }
3118
3119 // If change of line.
3120 if (Line != LineInfo.getLine()) {
3121 // Determine offset.
3122 int Offset = LineInfo.getLine() - Line;
3123 int Delta = Offset - MinLineDelta;
3124
3125 // Update line.
3126 Line = LineInfo.getLine();
3127
3128 // If delta is small enough and in range...
3129 if (Delta >= 0 && Delta < (MaxLineDelta - 1)) {
3130 // ... then use fast opcode.
Chris Lattner233f52b2010-03-09 23:52:58 +00003131 Asm->OutStreamer.AddComment("Line Delta");
3132 Asm->EmitInt8(Delta - MinLineDelta);
Bill Wendling94d04b82009-05-20 23:21:38 +00003133 } else {
3134 // ... otherwise use long hand.
Chris Lattner233f52b2010-03-09 23:52:58 +00003135 Asm->OutStreamer.AddComment("DW_LNS_advance_line");
Bill Wendling94d04b82009-05-20 23:21:38 +00003136 Asm->EmitInt8(dwarf::DW_LNS_advance_line);
Chris Lattner7e1a8f82010-04-04 19:09:29 +00003137 Asm->EmitSLEB128(Offset, "Line Offset");
Chris Lattner233f52b2010-03-09 23:52:58 +00003138 Asm->OutStreamer.AddComment("DW_LNS_copy");
3139 Asm->EmitInt8(dwarf::DW_LNS_copy);
Bill Wendling94d04b82009-05-20 23:21:38 +00003140 }
3141 } else {
3142 // Copy the previous row (different address or source)
Chris Lattner233f52b2010-03-09 23:52:58 +00003143 Asm->OutStreamer.AddComment("DW_LNS_copy");
3144 Asm->EmitInt8(dwarf::DW_LNS_copy);
Bill Wendling94d04b82009-05-20 23:21:38 +00003145 }
3146 }
3147
Devang Patel2c4ceb12009-11-21 02:48:08 +00003148 emitEndOfLineMatrix(j + 1);
Bill Wendling94d04b82009-05-20 23:21:38 +00003149 }
3150
3151 if (SecSrcLinesSize == 0)
3152 // Because we're emitting a debug_line section, we still need a line
3153 // table. The linker and friends expect it to exist. If there's nothing to
3154 // put into it, emit an empty table.
Devang Patel2c4ceb12009-11-21 02:48:08 +00003155 emitEndOfLineMatrix(1);
Bill Wendling94d04b82009-05-20 23:21:38 +00003156
Chris Lattnerc0215722010-04-04 19:25:43 +00003157 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("line_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00003158}
3159
Devang Patel2c4ceb12009-11-21 02:48:08 +00003160/// emitCommonDebugFrame - Emit common frame info into a debug frame section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003161///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003162void DwarfDebug::emitCommonDebugFrame() {
Chris Lattnerd38fee82010-04-05 00:13:49 +00003163 if (!Asm->MAI->doesDwarfRequireFrameSection())
Bill Wendling94d04b82009-05-20 23:21:38 +00003164 return;
3165
Chris Lattnerd38fee82010-04-05 00:13:49 +00003166 int stackGrowth = Asm->getTargetData().getPointerSize();
3167 if (Asm->TM.getFrameInfo()->getStackGrowthDirection() ==
3168 TargetFrameInfo::StackGrowsDown)
3169 stackGrowth *= -1;
Bill Wendling94d04b82009-05-20 23:21:38 +00003170
3171 // Start the dwarf frame section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003172 Asm->OutStreamer.SwitchSection(
3173 Asm->getObjFileLowering().getDwarfFrameSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003174
Chris Lattnerc0215722010-04-04 19:25:43 +00003175 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_frame_common"));
Chris Lattner233f52b2010-03-09 23:52:58 +00003176 Asm->OutStreamer.AddComment("Length of Common Information Entry");
Chris Lattnera6437182010-04-04 19:58:12 +00003177 Asm->EmitLabelDifference(Asm->GetTempSymbol("debug_frame_common_end"),
3178 Asm->GetTempSymbol("debug_frame_common_begin"), 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00003179
Chris Lattnerc0215722010-04-04 19:25:43 +00003180 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_frame_common_begin"));
Chris Lattner233f52b2010-03-09 23:52:58 +00003181 Asm->OutStreamer.AddComment("CIE Identifier Tag");
Bill Wendling94d04b82009-05-20 23:21:38 +00003182 Asm->EmitInt32((int)dwarf::DW_CIE_ID);
Chris Lattner233f52b2010-03-09 23:52:58 +00003183 Asm->OutStreamer.AddComment("CIE Version");
Bill Wendling94d04b82009-05-20 23:21:38 +00003184 Asm->EmitInt8(dwarf::DW_CIE_VERSION);
Chris Lattner233f52b2010-03-09 23:52:58 +00003185 Asm->OutStreamer.AddComment("CIE Augmentation");
Chris Lattner4cf202b2010-01-23 03:11:46 +00003186 Asm->OutStreamer.EmitIntValue(0, 1, /*addrspace*/0); // nul terminator.
Chris Lattner7e1a8f82010-04-04 19:09:29 +00003187 Asm->EmitULEB128(1, "CIE Code Alignment Factor");
3188 Asm->EmitSLEB128(stackGrowth, "CIE Data Alignment Factor");
Chris Lattner233f52b2010-03-09 23:52:58 +00003189 Asm->OutStreamer.AddComment("CIE RA Column");
Chris Lattnerd38fee82010-04-05 00:13:49 +00003190 const TargetRegisterInfo *RI = Asm->TM.getRegisterInfo();
Bill Wendling94d04b82009-05-20 23:21:38 +00003191 Asm->EmitInt8(RI->getDwarfRegNum(RI->getRARegister(), false));
Bill Wendling94d04b82009-05-20 23:21:38 +00003192
3193 std::vector<MachineMove> Moves;
3194 RI->getInitialFrameState(Moves);
3195
Chris Lattner02b86b92010-04-04 23:41:46 +00003196 Asm->EmitFrameMoves(Moves, 0, false);
Bill Wendling94d04b82009-05-20 23:21:38 +00003197
Chris Lattner059ea132010-04-28 01:05:45 +00003198 Asm->EmitAlignment(2);
Chris Lattnerc0215722010-04-04 19:25:43 +00003199 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_frame_common_end"));
Bill Wendling94d04b82009-05-20 23:21:38 +00003200}
3201
Devang Patel2c4ceb12009-11-21 02:48:08 +00003202/// emitFunctionDebugFrame - Emit per function frame info into a debug frame
Bill Wendling94d04b82009-05-20 23:21:38 +00003203/// section.
Chris Lattner206d61e2010-03-13 07:26:18 +00003204void DwarfDebug::
3205emitFunctionDebugFrame(const FunctionDebugFrameInfo &DebugFrameInfo) {
Chris Lattnerd38fee82010-04-05 00:13:49 +00003206 if (!Asm->MAI->doesDwarfRequireFrameSection())
Bill Wendling94d04b82009-05-20 23:21:38 +00003207 return;
3208
3209 // Start the dwarf frame section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003210 Asm->OutStreamer.SwitchSection(
3211 Asm->getObjFileLowering().getDwarfFrameSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003212
Chris Lattner233f52b2010-03-09 23:52:58 +00003213 Asm->OutStreamer.AddComment("Length of Frame Information Entry");
Chris Lattner206d61e2010-03-13 07:26:18 +00003214 MCSymbol *DebugFrameBegin =
Chris Lattnerc0215722010-04-04 19:25:43 +00003215 Asm->GetTempSymbol("debug_frame_begin", DebugFrameInfo.Number);
Chris Lattner206d61e2010-03-13 07:26:18 +00003216 MCSymbol *DebugFrameEnd =
Chris Lattnerc0215722010-04-04 19:25:43 +00003217 Asm->GetTempSymbol("debug_frame_end", DebugFrameInfo.Number);
Chris Lattnera6437182010-04-04 19:58:12 +00003218 Asm->EmitLabelDifference(DebugFrameEnd, DebugFrameBegin, 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00003219
Chris Lattner206d61e2010-03-13 07:26:18 +00003220 Asm->OutStreamer.EmitLabel(DebugFrameBegin);
Bill Wendling94d04b82009-05-20 23:21:38 +00003221
Chris Lattner233f52b2010-03-09 23:52:58 +00003222 Asm->OutStreamer.AddComment("FDE CIE offset");
Chris Lattner6189ed12010-04-04 23:25:33 +00003223 Asm->EmitSectionOffset(Asm->GetTempSymbol("debug_frame_common"),
3224 DwarfFrameSectionSym);
Bill Wendling94d04b82009-05-20 23:21:38 +00003225
Chris Lattner233f52b2010-03-09 23:52:58 +00003226 Asm->OutStreamer.AddComment("FDE initial location");
Chris Lattnerc0215722010-04-04 19:25:43 +00003227 MCSymbol *FuncBeginSym =
3228 Asm->GetTempSymbol("func_begin", DebugFrameInfo.Number);
Chris Lattnerfb658072010-03-13 07:40:56 +00003229 Asm->OutStreamer.EmitSymbolValue(FuncBeginSym,
Chris Lattnerd38fee82010-04-05 00:13:49 +00003230 Asm->getTargetData().getPointerSize(),
3231 0/*AddrSpace*/);
Chris Lattnerd85fc6e2010-03-10 01:17:49 +00003232
3233
Chris Lattner233f52b2010-03-09 23:52:58 +00003234 Asm->OutStreamer.AddComment("FDE address range");
Chris Lattnera6437182010-04-04 19:58:12 +00003235 Asm->EmitLabelDifference(Asm->GetTempSymbol("func_end",DebugFrameInfo.Number),
Chris Lattnerd38fee82010-04-05 00:13:49 +00003236 FuncBeginSym, Asm->getTargetData().getPointerSize());
Bill Wendling94d04b82009-05-20 23:21:38 +00003237
Chris Lattner02b86b92010-04-04 23:41:46 +00003238 Asm->EmitFrameMoves(DebugFrameInfo.Moves, FuncBeginSym, false);
Bill Wendling94d04b82009-05-20 23:21:38 +00003239
Chris Lattner059ea132010-04-28 01:05:45 +00003240 Asm->EmitAlignment(2);
Chris Lattner206d61e2010-03-13 07:26:18 +00003241 Asm->OutStreamer.EmitLabel(DebugFrameEnd);
Bill Wendling94d04b82009-05-20 23:21:38 +00003242}
3243
Devang Patel8a241142009-12-09 18:24:21 +00003244/// emitDebugPubNames - Emit visible names into a debug pubnames section.
3245///
3246void DwarfDebug::emitDebugPubNames() {
Devang Patel163a9f72010-05-10 22:49:55 +00003247 for (DenseMap<const MDNode *, CompileUnit *>::iterator I = CUMap.begin(),
3248 E = CUMap.end(); I != E; ++I) {
3249 CompileUnit *TheCU = I->second;
3250 // Start the dwarf pubnames section.
3251 Asm->OutStreamer.SwitchSection(
3252 Asm->getObjFileLowering().getDwarfPubNamesSection());
Chris Lattner4cf202b2010-01-23 03:11:46 +00003253
Devang Patel163a9f72010-05-10 22:49:55 +00003254 Asm->OutStreamer.AddComment("Length of Public Names Info");
3255 Asm->EmitLabelDifference(
3256 Asm->GetTempSymbol("pubnames_end", TheCU->getID()),
3257 Asm->GetTempSymbol("pubnames_begin", TheCU->getID()), 4);
3258
3259 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubnames_begin",
3260 TheCU->getID()));
3261
3262 Asm->OutStreamer.AddComment("DWARF Version");
3263 Asm->EmitInt16(dwarf::DWARF_VERSION);
3264
3265 Asm->OutStreamer.AddComment("Offset of Compilation Unit Info");
3266 Asm->EmitSectionOffset(Asm->GetTempSymbol("info_begin", TheCU->getID()),
3267 DwarfInfoSectionSym);
3268
3269 Asm->OutStreamer.AddComment("Compilation Unit Length");
3270 Asm->EmitLabelDifference(Asm->GetTempSymbol("info_end", TheCU->getID()),
3271 Asm->GetTempSymbol("info_begin", TheCU->getID()),
3272 4);
3273
3274 const StringMap<DIE*> &Globals = TheCU->getGlobals();
3275 for (StringMap<DIE*>::const_iterator
3276 GI = Globals.begin(), GE = Globals.end(); GI != GE; ++GI) {
3277 const char *Name = GI->getKeyData();
3278 DIE *Entity = GI->second;
3279
3280 Asm->OutStreamer.AddComment("DIE offset");
3281 Asm->EmitInt32(Entity->getOffset());
3282
3283 if (Asm->isVerbose())
3284 Asm->OutStreamer.AddComment("External Name");
3285 Asm->OutStreamer.EmitBytes(StringRef(Name, strlen(Name)+1), 0);
3286 }
3287
3288 Asm->OutStreamer.AddComment("End Mark");
3289 Asm->EmitInt32(0);
3290 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubnames_end",
3291 TheCU->getID()));
Bill Wendling94d04b82009-05-20 23:21:38 +00003292 }
Bill Wendling94d04b82009-05-20 23:21:38 +00003293}
3294
Devang Patel193f7202009-11-24 01:14:22 +00003295void DwarfDebug::emitDebugPubTypes() {
Devang Patel163a9f72010-05-10 22:49:55 +00003296 for (DenseMap<const MDNode *, CompileUnit *>::iterator I = CUMap.begin(),
3297 E = CUMap.end(); I != E; ++I) {
3298 CompileUnit *TheCU = I->second;
3299 // Start the dwarf pubnames section.
3300 Asm->OutStreamer.SwitchSection(
3301 Asm->getObjFileLowering().getDwarfPubTypesSection());
3302 Asm->OutStreamer.AddComment("Length of Public Types Info");
3303 Asm->EmitLabelDifference(
3304 Asm->GetTempSymbol("pubtypes_end", TheCU->getID()),
3305 Asm->GetTempSymbol("pubtypes_begin", TheCU->getID()), 4);
Chris Lattner4cf202b2010-01-23 03:11:46 +00003306
Devang Patel163a9f72010-05-10 22:49:55 +00003307 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubtypes_begin",
3308 TheCU->getID()));
3309
3310 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("DWARF Version");
3311 Asm->EmitInt16(dwarf::DWARF_VERSION);
3312
3313 Asm->OutStreamer.AddComment("Offset of Compilation Unit Info");
3314 Asm->EmitSectionOffset(Asm->GetTempSymbol("info_begin", TheCU->getID()),
3315 DwarfInfoSectionSym);
3316
3317 Asm->OutStreamer.AddComment("Compilation Unit Length");
3318 Asm->EmitLabelDifference(Asm->GetTempSymbol("info_end", TheCU->getID()),
3319 Asm->GetTempSymbol("info_begin", TheCU->getID()),
3320 4);
3321
3322 const StringMap<DIE*> &Globals = TheCU->getGlobalTypes();
3323 for (StringMap<DIE*>::const_iterator
3324 GI = Globals.begin(), GE = Globals.end(); GI != GE; ++GI) {
3325 const char *Name = GI->getKeyData();
3326 DIE * Entity = GI->second;
3327
3328 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("DIE offset");
3329 Asm->EmitInt32(Entity->getOffset());
3330
3331 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("External Name");
3332 Asm->OutStreamer.EmitBytes(StringRef(Name, GI->getKeyLength()+1), 0);
3333 }
3334
3335 Asm->OutStreamer.AddComment("End Mark");
3336 Asm->EmitInt32(0);
3337 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("pubtypes_end",
3338 TheCU->getID()));
Devang Patel193f7202009-11-24 01:14:22 +00003339 }
Devang Patel193f7202009-11-24 01:14:22 +00003340}
3341
Devang Patel2c4ceb12009-11-21 02:48:08 +00003342/// emitDebugStr - Emit visible names into a debug str section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003343///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003344void DwarfDebug::emitDebugStr() {
Bill Wendling94d04b82009-05-20 23:21:38 +00003345 // Check to see if it is worth the effort.
Chris Lattner0d9d70f2010-03-09 23:38:23 +00003346 if (StringPool.empty()) return;
3347
3348 // Start the dwarf str section.
3349 Asm->OutStreamer.SwitchSection(
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003350 Asm->getObjFileLowering().getDwarfStrSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003351
Chris Lattnerbc733f52010-03-13 02:17:42 +00003352 // Get all of the string pool entries and put them in an array by their ID so
3353 // we can sort them.
3354 SmallVector<std::pair<unsigned,
3355 StringMapEntry<std::pair<MCSymbol*, unsigned> >*>, 64> Entries;
3356
3357 for (StringMap<std::pair<MCSymbol*, unsigned> >::iterator
3358 I = StringPool.begin(), E = StringPool.end(); I != E; ++I)
3359 Entries.push_back(std::make_pair(I->second.second, &*I));
3360
3361 array_pod_sort(Entries.begin(), Entries.end());
3362
3363 for (unsigned i = 0, e = Entries.size(); i != e; ++i) {
Chris Lattner0d9d70f2010-03-09 23:38:23 +00003364 // Emit a label for reference from debug information entries.
Chris Lattnerbc733f52010-03-13 02:17:42 +00003365 Asm->OutStreamer.EmitLabel(Entries[i].second->getValue().first);
Chris Lattner0d9d70f2010-03-09 23:38:23 +00003366
3367 // Emit the string itself.
Chris Lattnerbc733f52010-03-13 02:17:42 +00003368 Asm->OutStreamer.EmitBytes(Entries[i].second->getKey(), 0/*addrspace*/);
Bill Wendling94d04b82009-05-20 23:21:38 +00003369 }
3370}
3371
Devang Patel2c4ceb12009-11-21 02:48:08 +00003372/// emitDebugLoc - Emit visible names into a debug loc section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003373///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003374void DwarfDebug::emitDebugLoc() {
Bill Wendling94d04b82009-05-20 23:21:38 +00003375 // Start the dwarf loc section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003376 Asm->OutStreamer.SwitchSection(
3377 Asm->getObjFileLowering().getDwarfLocSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003378}
3379
3380/// EmitDebugARanges - Emit visible names into a debug aranges section.
3381///
3382void DwarfDebug::EmitDebugARanges() {
3383 // Start the dwarf aranges section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003384 Asm->OutStreamer.SwitchSection(
3385 Asm->getObjFileLowering().getDwarfARangesSection());
Bill Wendling94d04b82009-05-20 23:21:38 +00003386}
3387
Devang Patel2c4ceb12009-11-21 02:48:08 +00003388/// emitDebugRanges - Emit visible names into a debug ranges section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003389///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003390void DwarfDebug::emitDebugRanges() {
Bill Wendling94d04b82009-05-20 23:21:38 +00003391 // Start the dwarf ranges section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003392 Asm->OutStreamer.SwitchSection(
Devang Patelf2548ca2010-04-16 23:33:45 +00003393 Asm->getObjFileLowering().getDwarfRangesSection());
Devang Pateleac9c072010-04-27 19:46:33 +00003394 unsigned char Size = Asm->getTargetData().getPointerSize();
3395 for (SmallVector<const MCSymbol *, 8>::iterator
3396 I = DebugRangeSymbols.begin(), E = DebugRangeSymbols.end();
3397 I != E; ++I) {
3398 if (*I)
3399 Asm->OutStreamer.EmitSymbolValue(const_cast<MCSymbol*>(*I), Size, 0);
Devang Patelf2548ca2010-04-16 23:33:45 +00003400 else
Devang Pateleac9c072010-04-27 19:46:33 +00003401 Asm->OutStreamer.EmitIntValue(0, Size, /*addrspace*/0);
Devang Patelf2548ca2010-04-16 23:33:45 +00003402 }
Bill Wendling94d04b82009-05-20 23:21:38 +00003403}
3404
Devang Patel2c4ceb12009-11-21 02:48:08 +00003405/// emitDebugMacInfo - Emit visible names into a debug macinfo section.
Bill Wendling94d04b82009-05-20 23:21:38 +00003406///
Devang Patel2c4ceb12009-11-21 02:48:08 +00003407void DwarfDebug::emitDebugMacInfo() {
Daniel Dunbarf612ff62009-09-19 20:40:05 +00003408 if (const MCSection *LineInfo =
Chris Lattner18a4c162009-08-02 07:24:22 +00003409 Asm->getObjFileLowering().getDwarfMacroInfoSection()) {
Bill Wendling94d04b82009-05-20 23:21:38 +00003410 // Start the dwarf macinfo section.
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003411 Asm->OutStreamer.SwitchSection(LineInfo);
Bill Wendling94d04b82009-05-20 23:21:38 +00003412 }
3413}
3414
Devang Patel2c4ceb12009-11-21 02:48:08 +00003415/// emitDebugInlineInfo - Emit inline info using following format.
Bill Wendling94d04b82009-05-20 23:21:38 +00003416/// Section Header:
3417/// 1. length of section
3418/// 2. Dwarf version number
3419/// 3. address size.
3420///
3421/// Entries (one "entry" for each function that was inlined):
3422///
3423/// 1. offset into __debug_str section for MIPS linkage name, if exists;
3424/// otherwise offset into __debug_str for regular function name.
3425/// 2. offset into __debug_str section for regular function name.
3426/// 3. an unsigned LEB128 number indicating the number of distinct inlining
3427/// instances for the function.
3428///
3429/// The rest of the entry consists of a {die_offset, low_pc} pair for each
3430/// inlined instance; the die_offset points to the inlined_subroutine die in the
3431/// __debug_info section, and the low_pc is the starting address for the
3432/// inlining instance.
Devang Patel2c4ceb12009-11-21 02:48:08 +00003433void DwarfDebug::emitDebugInlineInfo() {
Chris Lattnerd38fee82010-04-05 00:13:49 +00003434 if (!Asm->MAI->doesDwarfUsesInlineInfoSection())
Bill Wendling94d04b82009-05-20 23:21:38 +00003435 return;
3436
Devang Patel163a9f72010-05-10 22:49:55 +00003437 if (!FirstCU)
Bill Wendling94d04b82009-05-20 23:21:38 +00003438 return;
3439
Chris Lattner6c2f9e12009-08-19 05:49:37 +00003440 Asm->OutStreamer.SwitchSection(
3441 Asm->getObjFileLowering().getDwarfDebugInlineSection());
Chris Lattner0ad9c912010-01-22 22:09:00 +00003442
Chris Lattner233f52b2010-03-09 23:52:58 +00003443 Asm->OutStreamer.AddComment("Length of Debug Inlined Information Entry");
Chris Lattnera6437182010-04-04 19:58:12 +00003444 Asm->EmitLabelDifference(Asm->GetTempSymbol("debug_inlined_end", 1),
3445 Asm->GetTempSymbol("debug_inlined_begin", 1), 4);
Bill Wendling94d04b82009-05-20 23:21:38 +00003446
Chris Lattnerc0215722010-04-04 19:25:43 +00003447 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_inlined_begin", 1));
Bill Wendling94d04b82009-05-20 23:21:38 +00003448
Chris Lattner233f52b2010-03-09 23:52:58 +00003449 Asm->OutStreamer.AddComment("Dwarf Version");
3450 Asm->EmitInt16(dwarf::DWARF_VERSION);
3451 Asm->OutStreamer.AddComment("Address Size (in bytes)");
Chris Lattnerd38fee82010-04-05 00:13:49 +00003452 Asm->EmitInt8(Asm->getTargetData().getPointerSize());
Bill Wendling94d04b82009-05-20 23:21:38 +00003453
Devang Patele9f8f5e2010-05-07 20:54:48 +00003454 for (SmallVector<const MDNode *, 4>::iterator I = InlinedSPNodes.begin(),
Devang Patel53bb5c92009-11-10 23:06:00 +00003455 E = InlinedSPNodes.end(); I != E; ++I) {
Jim Grosbach31ef40e2009-11-21 23:12:12 +00003456
Devang Patele9f8f5e2010-05-07 20:54:48 +00003457 const MDNode *Node = *I;
3458 DenseMap<const MDNode *, SmallVector<InlineInfoLabels, 4> >::iterator II
Jim Grosbach7ab38df2009-11-22 19:20:36 +00003459 = InlineInfo.find(Node);
Devang Patel53bb5c92009-11-10 23:06:00 +00003460 SmallVector<InlineInfoLabels, 4> &Labels = II->second;
Devang Patele4b27562009-08-28 23:24:31 +00003461 DISubprogram SP(Node);
Devang Patel65dbc902009-11-25 17:36:49 +00003462 StringRef LName = SP.getLinkageName();
3463 StringRef Name = SP.getName();
Bill Wendling94d04b82009-05-20 23:21:38 +00003464
Chris Lattner233f52b2010-03-09 23:52:58 +00003465 Asm->OutStreamer.AddComment("MIPS linkage name");
Chris Lattner4cf202b2010-01-23 03:11:46 +00003466 if (LName.empty()) {
3467 Asm->OutStreamer.EmitBytes(Name, 0);
3468 Asm->OutStreamer.EmitIntValue(0, 1, 0); // nul terminator.
3469 } else
Chris Lattner6189ed12010-04-04 23:25:33 +00003470 Asm->EmitSectionOffset(getStringPoolEntry(getRealLinkageName(LName)),
3471 DwarfStrSectionSym);
Devang Patel53bb5c92009-11-10 23:06:00 +00003472
Chris Lattner233f52b2010-03-09 23:52:58 +00003473 Asm->OutStreamer.AddComment("Function name");
Chris Lattner6189ed12010-04-04 23:25:33 +00003474 Asm->EmitSectionOffset(getStringPoolEntry(Name), DwarfStrSectionSym);
Chris Lattner7e1a8f82010-04-04 19:09:29 +00003475 Asm->EmitULEB128(Labels.size(), "Inline count");
Bill Wendling94d04b82009-05-20 23:21:38 +00003476
Devang Patel53bb5c92009-11-10 23:06:00 +00003477 for (SmallVector<InlineInfoLabels, 4>::iterator LI = Labels.begin(),
Bill Wendling94d04b82009-05-20 23:21:38 +00003478 LE = Labels.end(); LI != LE; ++LI) {
Chris Lattner3f53c832010-04-04 18:52:31 +00003479 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("DIE offset");
Chris Lattner6ed0f902010-03-09 00:31:02 +00003480 Asm->EmitInt32(LI->second->getOffset());
Bill Wendling94d04b82009-05-20 23:21:38 +00003481
Chris Lattner3f53c832010-04-04 18:52:31 +00003482 if (Asm->isVerbose()) Asm->OutStreamer.AddComment("low_pc");
Chris Lattnerd38fee82010-04-05 00:13:49 +00003483 Asm->OutStreamer.EmitSymbolValue(LI->first,
3484 Asm->getTargetData().getPointerSize(),0);
Bill Wendling94d04b82009-05-20 23:21:38 +00003485 }
3486 }
3487
Chris Lattnerc0215722010-04-04 19:25:43 +00003488 Asm->OutStreamer.EmitLabel(Asm->GetTempSymbol("debug_inlined_end", 1));
Bill Wendling94d04b82009-05-20 23:21:38 +00003489}