1 //===--- llvm/Analysis/DebugInfo.h - Debug Information Helpers --*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file defines a bunch of datatypes that are useful for creating and 11 // walking debug info in LLVM IR form. They essentially provide wrappers around 12 // the information in the global variables that's needed when constructing the 13 // DWARF information. 14 // 15 //===----------------------------------------------------------------------===// 16 17 #ifndef LLVM_ANALYSIS_DEBUGINFO_H 18 #define LLVM_ANALYSIS_DEBUGINFO_H 19 20 #include "llvm/ADT/SmallVector.h" 21 #include "llvm/ADT/SmallPtrSet.h" 22 #include "llvm/ADT/StringRef.h" 23 #include "llvm/Support/Dwarf.h" 24 25 namespace llvm { 26 class BasicBlock; 27 class Constant; 28 class Function; 29 class GlobalVariable; 30 class Module; 31 class Type; 32 class Value; 33 class DbgDeclareInst; 34 class Instruction; 35 class MDNode; 36 class NamedMDNode; 37 class LLVMContext; 38 class raw_ostream; 39 40 class DIFile; 41 class DISubprogram; 42 class DILexicalBlock; 43 class DILexicalBlockFile; 44 class DIVariable; 45 class DIType; 46 47 /// DIDescriptor - A thin wraper around MDNode to access encoded debug info. 48 /// This should not be stored in a container, because underly MDNode may 49 /// change in certain situations. 50 class DIDescriptor { 51 public: 52 enum { 53 FlagPrivate = 1 << 0, 54 FlagProtected = 1 << 1, 55 FlagFwdDecl = 1 << 2, 56 FlagAppleBlock = 1 << 3, 57 FlagBlockByrefStruct = 1 << 4, 58 FlagVirtual = 1 << 5, 59 FlagArtificial = 1 << 6, 60 FlagExplicit = 1 << 7, 61 FlagPrototyped = 1 << 8, 62 FlagObjcClassComplete = 1 << 9 63 }; 64 protected: 65 const MDNode *DbgNode; 66 67 StringRef getStringField(unsigned Elt) const; getUnsignedField(unsigned Elt)68 unsigned getUnsignedField(unsigned Elt) const { 69 return (unsigned)getUInt64Field(Elt); 70 } 71 uint64_t getUInt64Field(unsigned Elt) const; 72 DIDescriptor getDescriptorField(unsigned Elt) const; 73 74 template <typename DescTy> getFieldAs(unsigned Elt)75 DescTy getFieldAs(unsigned Elt) const { 76 return DescTy(getDescriptorField(Elt)); 77 } 78 79 GlobalVariable *getGlobalVariableField(unsigned Elt) const; 80 Constant *getConstantField(unsigned Elt) const; 81 Function *getFunctionField(unsigned Elt) const; 82 83 public: DIDescriptor()84 explicit DIDescriptor() : DbgNode(0) {} DIDescriptor(const MDNode * N)85 explicit DIDescriptor(const MDNode *N) : DbgNode(N) {} 86 explicit DIDescriptor(const DIFile F); 87 explicit DIDescriptor(const DISubprogram F); 88 explicit DIDescriptor(const DILexicalBlockFile F); 89 explicit DIDescriptor(const DILexicalBlock F); 90 explicit DIDescriptor(const DIVariable F); 91 explicit DIDescriptor(const DIType F); 92 Verify()93 bool Verify() const { return DbgNode != 0; } 94 95 operator MDNode *() const { return const_cast<MDNode*>(DbgNode); } 96 MDNode *operator ->() const { return const_cast<MDNode*>(DbgNode); } 97 getVersion()98 unsigned getVersion() const { 99 return getUnsignedField(0) & LLVMDebugVersionMask; 100 } 101 getTag()102 unsigned getTag() const { 103 return getUnsignedField(0) & ~LLVMDebugVersionMask; 104 } 105 106 /// print - print descriptor. 107 void print(raw_ostream &OS) const; 108 109 /// dump - print descriptor to dbgs() with a newline. 110 void dump() const; 111 112 bool isDerivedType() const; 113 bool isCompositeType() const; 114 bool isBasicType() const; 115 bool isVariable() const; 116 bool isSubprogram() const; 117 bool isGlobalVariable() const; 118 bool isScope() const; 119 bool isFile() const; 120 bool isCompileUnit() const; 121 bool isNameSpace() const; 122 bool isLexicalBlockFile() const; 123 bool isLexicalBlock() const; 124 bool isSubrange() const; 125 bool isEnumerator() const; 126 bool isType() const; 127 bool isGlobal() const; 128 bool isUnspecifiedParameter() const; 129 bool isTemplateTypeParameter() const; 130 bool isTemplateValueParameter() const; 131 }; 132 133 /// DISubrange - This is used to represent ranges, for array bounds. 134 class DISubrange : public DIDescriptor { 135 public: DIDescriptor(N)136 explicit DISubrange(const MDNode *N = 0) : DIDescriptor(N) {} 137 getLo()138 int64_t getLo() const { return (int64_t)getUInt64Field(1); } getHi()139 int64_t getHi() const { return (int64_t)getUInt64Field(2); } 140 }; 141 142 /// DIArray - This descriptor holds an array of descriptors. 143 class DIArray : public DIDescriptor { 144 public: 145 explicit DIArray(const MDNode *N = 0) DIDescriptor(N)146 : DIDescriptor(N) {} 147 148 unsigned getNumElements() const; getElement(unsigned Idx)149 DIDescriptor getElement(unsigned Idx) const { 150 return getDescriptorField(Idx); 151 } 152 }; 153 154 /// DIScope - A base class for various scopes. 155 class DIScope : public DIDescriptor { 156 public: DIDescriptor(N)157 explicit DIScope(const MDNode *N = 0) : DIDescriptor (N) {} ~DIScope()158 virtual ~DIScope() {} 159 160 StringRef getFilename() const; 161 StringRef getDirectory() const; 162 }; 163 164 /// DICompileUnit - A wrapper for a compile unit. 165 class DICompileUnit : public DIScope { 166 public: DIScope(N)167 explicit DICompileUnit(const MDNode *N = 0) : DIScope(N) {} 168 getLanguage()169 unsigned getLanguage() const { return getUnsignedField(2); } getFilename()170 StringRef getFilename() const { return getStringField(3); } getDirectory()171 StringRef getDirectory() const { return getStringField(4); } getProducer()172 StringRef getProducer() const { return getStringField(5); } 173 174 /// isMain - Each input file is encoded as a separate compile unit in LLVM 175 /// debugging information output. However, many target specific tool chains 176 /// prefer to encode only one compile unit in an object file. In this 177 /// situation, the LLVM code generator will include debugging information 178 /// entities in the compile unit that is marked as main compile unit. The 179 /// code generator accepts maximum one main compile unit per module. If a 180 /// module does not contain any main compile unit then the code generator 181 /// will emit multiple compile units in the output object file. 182 isMain()183 bool isMain() const { return getUnsignedField(6) != 0; } isOptimized()184 bool isOptimized() const { return getUnsignedField(7) != 0; } getFlags()185 StringRef getFlags() const { return getStringField(8); } getRunTimeVersion()186 unsigned getRunTimeVersion() const { return getUnsignedField(9); } 187 188 DIArray getEnumTypes() const; 189 DIArray getRetainedTypes() const; 190 DIArray getSubprograms() const; 191 DIArray getGlobalVariables() const; 192 193 /// Verify - Verify that a compile unit is well formed. 194 bool Verify() const; 195 196 /// print - print compile unit. 197 void print(raw_ostream &OS) const; 198 199 /// dump - print compile unit to dbgs() with a newline. 200 void dump() const; 201 }; 202 203 /// DIFile - This is a wrapper for a file. 204 class DIFile : public DIScope { 205 public: DIScope(N)206 explicit DIFile(const MDNode *N = 0) : DIScope(N) { 207 if (DbgNode && !isFile()) 208 DbgNode = 0; 209 } getFilename()210 StringRef getFilename() const { return getStringField(1); } getDirectory()211 StringRef getDirectory() const { return getStringField(2); } getCompileUnit()212 DICompileUnit getCompileUnit() const{ 213 assert (getVersion() <= LLVMDebugVersion10 && "Invalid CompileUnit!"); 214 return getFieldAs<DICompileUnit>(3); 215 } 216 }; 217 218 /// DIEnumerator - A wrapper for an enumerator (e.g. X and Y in 'enum {X,Y}'). 219 /// FIXME: it seems strange that this doesn't have either a reference to the 220 /// type/precision or a file/line pair for location info. 221 class DIEnumerator : public DIDescriptor { 222 public: DIDescriptor(N)223 explicit DIEnumerator(const MDNode *N = 0) : DIDescriptor(N) {} 224 getName()225 StringRef getName() const { return getStringField(1); } getEnumValue()226 uint64_t getEnumValue() const { return getUInt64Field(2); } 227 }; 228 229 /// DIType - This is a wrapper for a type. 230 /// FIXME: Types should be factored much better so that CV qualifiers and 231 /// others do not require a huge and empty descriptor full of zeros. 232 class DIType : public DIScope { 233 public: 234 protected: 235 // This ctor is used when the Tag has already been validated by a derived 236 // ctor. DIType(const MDNode * N,bool,bool)237 DIType(const MDNode *N, bool, bool) : DIScope(N) {} 238 239 public: 240 241 /// Verify - Verify that a type descriptor is well formed. 242 bool Verify() const; 243 public: 244 explicit DIType(const MDNode *N); DIType()245 explicit DIType() {} ~DIType()246 virtual ~DIType() {} 247 getContext()248 DIScope getContext() const { return getFieldAs<DIScope>(1); } getName()249 StringRef getName() const { return getStringField(2); } getCompileUnit()250 DICompileUnit getCompileUnit() const{ 251 assert (getVersion() <= LLVMDebugVersion10 && "Invalid getCompileUnit!"); 252 if (getVersion() == llvm::LLVMDebugVersion7) 253 return getFieldAs<DICompileUnit>(3); 254 255 return getFieldAs<DIFile>(3).getCompileUnit(); 256 } getFile()257 DIFile getFile() const { return getFieldAs<DIFile>(3); } getLineNumber()258 unsigned getLineNumber() const { return getUnsignedField(4); } getSizeInBits()259 uint64_t getSizeInBits() const { return getUInt64Field(5); } getAlignInBits()260 uint64_t getAlignInBits() const { return getUInt64Field(6); } 261 // FIXME: Offset is only used for DW_TAG_member nodes. Making every type 262 // carry this is just plain insane. getOffsetInBits()263 uint64_t getOffsetInBits() const { return getUInt64Field(7); } getFlags()264 unsigned getFlags() const { return getUnsignedField(8); } isPrivate()265 bool isPrivate() const { 266 return (getFlags() & FlagPrivate) != 0; 267 } isProtected()268 bool isProtected() const { 269 return (getFlags() & FlagProtected) != 0; 270 } isForwardDecl()271 bool isForwardDecl() const { 272 return (getFlags() & FlagFwdDecl) != 0; 273 } 274 // isAppleBlock - Return true if this is the Apple Blocks extension. isAppleBlockExtension()275 bool isAppleBlockExtension() const { 276 return (getFlags() & FlagAppleBlock) != 0; 277 } isBlockByrefStruct()278 bool isBlockByrefStruct() const { 279 return (getFlags() & FlagBlockByrefStruct) != 0; 280 } isVirtual()281 bool isVirtual() const { 282 return (getFlags() & FlagVirtual) != 0; 283 } isArtificial()284 bool isArtificial() const { 285 return (getFlags() & FlagArtificial) != 0; 286 } isObjcClassComplete()287 bool isObjcClassComplete() const { 288 return (getFlags() & FlagObjcClassComplete) != 0; 289 } isValid()290 bool isValid() const { 291 return DbgNode && (isBasicType() || isDerivedType() || isCompositeType()); 292 } getDirectory()293 StringRef getDirectory() const { 294 if (getVersion() == llvm::LLVMDebugVersion7) 295 return getCompileUnit().getDirectory(); 296 297 return getFieldAs<DIFile>(3).getDirectory(); 298 } getFilename()299 StringRef getFilename() const { 300 if (getVersion() == llvm::LLVMDebugVersion7) 301 return getCompileUnit().getFilename(); 302 303 return getFieldAs<DIFile>(3).getFilename(); 304 } 305 306 /// isUnsignedDIType - Return true if type encoding is unsigned. 307 bool isUnsignedDIType(); 308 309 /// replaceAllUsesWith - Replace all uses of debug info referenced by 310 /// this descriptor. 311 void replaceAllUsesWith(DIDescriptor &D); 312 void replaceAllUsesWith(MDNode *D); 313 314 /// print - print type. 315 void print(raw_ostream &OS) const; 316 317 /// dump - print type to dbgs() with a newline. 318 void dump() const; 319 }; 320 321 /// DIBasicType - A basic type, like 'int' or 'float'. 322 class DIBasicType : public DIType { 323 public: DIType(N)324 explicit DIBasicType(const MDNode *N = 0) : DIType(N) {} 325 getEncoding()326 unsigned getEncoding() const { return getUnsignedField(9); } 327 328 /// Verify - Verify that a basic type descriptor is well formed. 329 bool Verify() const; 330 331 /// print - print basic type. 332 void print(raw_ostream &OS) const; 333 334 /// dump - print basic type to dbgs() with a newline. 335 void dump() const; 336 }; 337 338 /// DIDerivedType - A simple derived type, like a const qualified type, 339 /// a typedef, a pointer or reference, etc. 340 class DIDerivedType : public DIType { 341 protected: DIDerivedType(const MDNode * N,bool,bool)342 explicit DIDerivedType(const MDNode *N, bool, bool) 343 : DIType(N, true, true) {} 344 public: 345 explicit DIDerivedType(const MDNode *N = 0) DIType(N,true,true)346 : DIType(N, true, true) {} 347 getTypeDerivedFrom()348 DIType getTypeDerivedFrom() const { return getFieldAs<DIType>(9); } 349 350 /// getOriginalTypeSize - If this type is derived from a base type then 351 /// return base type size. 352 uint64_t getOriginalTypeSize() const; 353 getObjCPropertyName()354 StringRef getObjCPropertyName() const { return getStringField(10); } getObjCPropertyGetterName()355 StringRef getObjCPropertyGetterName() const { 356 return getStringField(11); 357 } getObjCPropertySetterName()358 StringRef getObjCPropertySetterName() const { 359 return getStringField(12); 360 } isReadOnlyObjCProperty()361 bool isReadOnlyObjCProperty() { 362 return (getUnsignedField(13) & dwarf::DW_APPLE_PROPERTY_readonly) != 0; 363 } isReadWriteObjCProperty()364 bool isReadWriteObjCProperty() { 365 return (getUnsignedField(13) & dwarf::DW_APPLE_PROPERTY_readwrite) != 0; 366 } isAssignObjCProperty()367 bool isAssignObjCProperty() { 368 return (getUnsignedField(13) & dwarf::DW_APPLE_PROPERTY_assign) != 0; 369 } isRetainObjCProperty()370 bool isRetainObjCProperty() { 371 return (getUnsignedField(13) & dwarf::DW_APPLE_PROPERTY_retain) != 0; 372 } isCopyObjCProperty()373 bool isCopyObjCProperty() { 374 return (getUnsignedField(13) & dwarf::DW_APPLE_PROPERTY_copy) != 0; 375 } isNonAtomicObjCProperty()376 bool isNonAtomicObjCProperty() { 377 return (getUnsignedField(13) & dwarf::DW_APPLE_PROPERTY_nonatomic) != 0; 378 } 379 380 /// Verify - Verify that a derived type descriptor is well formed. 381 bool Verify() const; 382 383 /// print - print derived type. 384 void print(raw_ostream &OS) const; 385 386 /// dump - print derived type to dbgs() with a newline. 387 void dump() const; 388 }; 389 390 /// DICompositeType - This descriptor holds a type that can refer to multiple 391 /// other types, like a function or struct. 392 /// FIXME: Why is this a DIDerivedType?? 393 class DICompositeType : public DIDerivedType { 394 public: 395 explicit DICompositeType(const MDNode *N = 0) DIDerivedType(N,true,true)396 : DIDerivedType(N, true, true) { 397 if (N && !isCompositeType()) 398 DbgNode = 0; 399 } 400 getTypeArray()401 DIArray getTypeArray() const { return getFieldAs<DIArray>(10); } getRunTimeLang()402 unsigned getRunTimeLang() const { return getUnsignedField(11); } getContainingType()403 DICompositeType getContainingType() const { 404 return getFieldAs<DICompositeType>(12); 405 } getTemplateParams()406 DIArray getTemplateParams() const { return getFieldAs<DIArray>(13); } 407 408 /// Verify - Verify that a composite type descriptor is well formed. 409 bool Verify() const; 410 411 /// print - print composite type. 412 void print(raw_ostream &OS) const; 413 414 /// dump - print composite type to dbgs() with a newline. 415 void dump() const; 416 }; 417 418 /// DITemplateTypeParameter - This is a wrapper for template type parameter. 419 class DITemplateTypeParameter : public DIDescriptor { 420 public: DIDescriptor(N)421 explicit DITemplateTypeParameter(const MDNode *N = 0) : DIDescriptor(N) {} 422 getContext()423 DIScope getContext() const { return getFieldAs<DIScope>(1); } getName()424 StringRef getName() const { return getStringField(2); } getType()425 DIType getType() const { return getFieldAs<DIType>(3); } getFilename()426 StringRef getFilename() const { 427 return getFieldAs<DIFile>(4).getFilename(); 428 } getDirectory()429 StringRef getDirectory() const { 430 return getFieldAs<DIFile>(4).getDirectory(); 431 } getLineNumber()432 unsigned getLineNumber() const { return getUnsignedField(5); } getColumnNumber()433 unsigned getColumnNumber() const { return getUnsignedField(6); } 434 }; 435 436 /// DITemplateValueParameter - This is a wrapper for template value parameter. 437 class DITemplateValueParameter : public DIDescriptor { 438 public: DIDescriptor(N)439 explicit DITemplateValueParameter(const MDNode *N = 0) : DIDescriptor(N) {} 440 getContext()441 DIScope getContext() const { return getFieldAs<DIScope>(1); } getName()442 StringRef getName() const { return getStringField(2); } getType()443 DIType getType() const { return getFieldAs<DIType>(3); } getValue()444 uint64_t getValue() const { return getUInt64Field(4); } getFilename()445 StringRef getFilename() const { 446 return getFieldAs<DIFile>(5).getFilename(); 447 } getDirectory()448 StringRef getDirectory() const { 449 return getFieldAs<DIFile>(5).getDirectory(); 450 } getLineNumber()451 unsigned getLineNumber() const { return getUnsignedField(6); } getColumnNumber()452 unsigned getColumnNumber() const { return getUnsignedField(7); } 453 }; 454 455 /// DISubprogram - This is a wrapper for a subprogram (e.g. a function). 456 class DISubprogram : public DIScope { 457 public: DIScope(N)458 explicit DISubprogram(const MDNode *N = 0) : DIScope(N) {} 459 getContext()460 DIScope getContext() const { return getFieldAs<DIScope>(2); } getName()461 StringRef getName() const { return getStringField(3); } getDisplayName()462 StringRef getDisplayName() const { return getStringField(4); } getLinkageName()463 StringRef getLinkageName() const { return getStringField(5); } getCompileUnit()464 DICompileUnit getCompileUnit() const{ 465 assert (getVersion() <= LLVMDebugVersion10 && "Invalid getCompileUnit!"); 466 if (getVersion() == llvm::LLVMDebugVersion7) 467 return getFieldAs<DICompileUnit>(6); 468 469 return getFieldAs<DIFile>(6).getCompileUnit(); 470 } getLineNumber()471 unsigned getLineNumber() const { return getUnsignedField(7); } getType()472 DICompositeType getType() const { return getFieldAs<DICompositeType>(8); } 473 474 /// getReturnTypeName - Subprogram return types are encoded either as 475 /// DIType or as DICompositeType. getReturnTypeName()476 StringRef getReturnTypeName() const { 477 DICompositeType DCT(getFieldAs<DICompositeType>(8)); 478 if (DCT.Verify()) { 479 DIArray A = DCT.getTypeArray(); 480 DIType T(A.getElement(0)); 481 return T.getName(); 482 } 483 DIType T(getFieldAs<DIType>(8)); 484 return T.getName(); 485 } 486 487 /// isLocalToUnit - Return true if this subprogram is local to the current 488 /// compile unit, like 'static' in C. isLocalToUnit()489 unsigned isLocalToUnit() const { return getUnsignedField(9); } isDefinition()490 unsigned isDefinition() const { return getUnsignedField(10); } 491 getVirtuality()492 unsigned getVirtuality() const { return getUnsignedField(11); } getVirtualIndex()493 unsigned getVirtualIndex() const { return getUnsignedField(12); } 494 getContainingType()495 DICompositeType getContainingType() const { 496 return getFieldAs<DICompositeType>(13); 497 } isArtificial()498 unsigned isArtificial() const { 499 if (getVersion() <= llvm::LLVMDebugVersion8) 500 return getUnsignedField(14); 501 return (getUnsignedField(14) & FlagArtificial) != 0; 502 } 503 /// isPrivate - Return true if this subprogram has "private" 504 /// access specifier. isPrivate()505 bool isPrivate() const { 506 if (getVersion() <= llvm::LLVMDebugVersion8) 507 return false; 508 return (getUnsignedField(14) & FlagPrivate) != 0; 509 } 510 /// isProtected - Return true if this subprogram has "protected" 511 /// access specifier. isProtected()512 bool isProtected() const { 513 if (getVersion() <= llvm::LLVMDebugVersion8) 514 return false; 515 return (getUnsignedField(14) & FlagProtected) != 0; 516 } 517 /// isExplicit - Return true if this subprogram is marked as explicit. isExplicit()518 bool isExplicit() const { 519 if (getVersion() <= llvm::LLVMDebugVersion8) 520 return false; 521 return (getUnsignedField(14) & FlagExplicit) != 0; 522 } 523 /// isPrototyped - Return true if this subprogram is prototyped. isPrototyped()524 bool isPrototyped() const { 525 if (getVersion() <= llvm::LLVMDebugVersion8) 526 return false; 527 return (getUnsignedField(14) & FlagPrototyped) != 0; 528 } 529 530 unsigned isOptimized() const; 531 getFilename()532 StringRef getFilename() const { 533 if (getVersion() == llvm::LLVMDebugVersion7) 534 return getCompileUnit().getFilename(); 535 536 return getFieldAs<DIFile>(6).getFilename(); 537 } 538 getDirectory()539 StringRef getDirectory() const { 540 if (getVersion() == llvm::LLVMDebugVersion7) 541 return getCompileUnit().getFilename(); 542 543 return getFieldAs<DIFile>(6).getDirectory(); 544 } 545 546 /// Verify - Verify that a subprogram descriptor is well formed. 547 bool Verify() const; 548 549 /// print - print subprogram. 550 void print(raw_ostream &OS) const; 551 552 /// dump - print subprogram to dbgs() with a newline. 553 void dump() const; 554 555 /// describes - Return true if this subprogram provides debugging 556 /// information for the function F. 557 bool describes(const Function *F); 558 getFunction()559 Function *getFunction() const { return getFunctionField(16); } getTemplateParams()560 DIArray getTemplateParams() const { return getFieldAs<DIArray>(17); } getFunctionDeclaration()561 DISubprogram getFunctionDeclaration() const { 562 return getFieldAs<DISubprogram>(18); 563 } 564 MDNode *getVariablesNodes() const; 565 DIArray getVariables() const; 566 }; 567 568 /// DIGlobalVariable - This is a wrapper for a global variable. 569 class DIGlobalVariable : public DIDescriptor { 570 public: DIDescriptor(N)571 explicit DIGlobalVariable(const MDNode *N = 0) : DIDescriptor(N) {} 572 getContext()573 DIScope getContext() const { return getFieldAs<DIScope>(2); } getName()574 StringRef getName() const { return getStringField(3); } getDisplayName()575 StringRef getDisplayName() const { return getStringField(4); } getLinkageName()576 StringRef getLinkageName() const { return getStringField(5); } getCompileUnit()577 DICompileUnit getCompileUnit() const{ 578 assert (getVersion() <= LLVMDebugVersion10 && "Invalid getCompileUnit!"); 579 if (getVersion() == llvm::LLVMDebugVersion7) 580 return getFieldAs<DICompileUnit>(6); 581 582 DIFile F = getFieldAs<DIFile>(6); 583 return F.getCompileUnit(); 584 } getFilename()585 StringRef getFilename() const { 586 if (getVersion() <= llvm::LLVMDebugVersion10) 587 return getContext().getFilename(); 588 return getFieldAs<DIFile>(6).getFilename(); 589 } getDirectory()590 StringRef getDirectory() const { 591 if (getVersion() <= llvm::LLVMDebugVersion10) 592 return getContext().getDirectory(); 593 return getFieldAs<DIFile>(6).getDirectory(); 594 595 } 596 getLineNumber()597 unsigned getLineNumber() const { return getUnsignedField(7); } getType()598 DIType getType() const { return getFieldAs<DIType>(8); } isLocalToUnit()599 unsigned isLocalToUnit() const { return getUnsignedField(9); } isDefinition()600 unsigned isDefinition() const { return getUnsignedField(10); } 601 getGlobal()602 GlobalVariable *getGlobal() const { return getGlobalVariableField(11); } getConstant()603 Constant *getConstant() const { return getConstantField(11); } 604 605 /// Verify - Verify that a global variable descriptor is well formed. 606 bool Verify() const; 607 608 /// print - print global variable. 609 void print(raw_ostream &OS) const; 610 611 /// dump - print global variable to dbgs() with a newline. 612 void dump() const; 613 }; 614 615 /// DIVariable - This is a wrapper for a variable (e.g. parameter, local, 616 /// global etc). 617 class DIVariable : public DIDescriptor { 618 public: 619 explicit DIVariable(const MDNode *N = 0) DIDescriptor(N)620 : DIDescriptor(N) {} 621 getContext()622 DIScope getContext() const { return getFieldAs<DIScope>(1); } getName()623 StringRef getName() const { return getStringField(2); } getCompileUnit()624 DICompileUnit getCompileUnit() const{ 625 assert (getVersion() <= LLVMDebugVersion10 && "Invalid getCompileUnit!"); 626 if (getVersion() == llvm::LLVMDebugVersion7) 627 return getFieldAs<DICompileUnit>(3); 628 629 DIFile F = getFieldAs<DIFile>(3); 630 return F.getCompileUnit(); 631 } getLineNumber()632 unsigned getLineNumber() const { 633 return (getUnsignedField(4) << 8) >> 8; 634 } getArgNumber()635 unsigned getArgNumber() const { 636 unsigned L = getUnsignedField(4); 637 return L >> 24; 638 } getType()639 DIType getType() const { return getFieldAs<DIType>(5); } 640 641 /// isArtificial - Return true if this variable is marked as "artificial". isArtificial()642 bool isArtificial() const { 643 if (getVersion() <= llvm::LLVMDebugVersion8) 644 return false; 645 return (getUnsignedField(6) & FlagArtificial) != 0; 646 } 647 648 /// getInlinedAt - If this variable is inlined then return inline location. 649 MDNode *getInlinedAt() const; 650 651 /// Verify - Verify that a variable descriptor is well formed. 652 bool Verify() const; 653 654 /// HasComplexAddr - Return true if the variable has a complex address. hasComplexAddress()655 bool hasComplexAddress() const { 656 return getNumAddrElements() > 0; 657 } 658 659 unsigned getNumAddrElements() const; 660 getAddrElement(unsigned Idx)661 uint64_t getAddrElement(unsigned Idx) const { 662 if (getVersion() <= llvm::LLVMDebugVersion8) 663 return getUInt64Field(Idx+6); 664 if (getVersion() == llvm::LLVMDebugVersion9) 665 return getUInt64Field(Idx+7); 666 return getUInt64Field(Idx+8); 667 } 668 669 /// isBlockByrefVariable - Return true if the variable was declared as 670 /// a "__block" variable (Apple Blocks). isBlockByrefVariable()671 bool isBlockByrefVariable() const { 672 return getType().isBlockByrefStruct(); 673 } 674 675 /// isInlinedFnArgument - Return trule if this variable provides debugging 676 /// information for an inlined function arguments. 677 bool isInlinedFnArgument(const Function *CurFn); 678 679 /// print - print variable. 680 void print(raw_ostream &OS) const; 681 682 void printExtendedName(raw_ostream &OS) const; 683 684 /// dump - print variable to dbgs() with a newline. 685 void dump() const; 686 }; 687 688 /// DILexicalBlock - This is a wrapper for a lexical block. 689 class DILexicalBlock : public DIScope { 690 public: DIScope(N)691 explicit DILexicalBlock(const MDNode *N = 0) : DIScope(N) {} getContext()692 DIScope getContext() const { return getFieldAs<DIScope>(1); } getLineNumber()693 unsigned getLineNumber() const { return getUnsignedField(2); } getColumnNumber()694 unsigned getColumnNumber() const { return getUnsignedField(3); } getDirectory()695 StringRef getDirectory() const { 696 StringRef dir = getFieldAs<DIFile>(4).getDirectory(); 697 return !dir.empty() ? dir : getContext().getDirectory(); 698 } getFilename()699 StringRef getFilename() const { 700 StringRef filename = getFieldAs<DIFile>(4).getFilename(); 701 return !filename.empty() ? filename : getContext().getFilename(); 702 } 703 }; 704 705 /// DILexicalBlockFile - This is a wrapper for a lexical block with 706 /// a filename change. 707 class DILexicalBlockFile : public DIScope { 708 public: DIScope(N)709 explicit DILexicalBlockFile(const MDNode *N = 0) : DIScope(N) {} getContext()710 DIScope getContext() const { return getScope().getContext(); } getLineNumber()711 unsigned getLineNumber() const { return getScope().getLineNumber(); } getColumnNumber()712 unsigned getColumnNumber() const { return getScope().getColumnNumber(); } getDirectory()713 StringRef getDirectory() const { 714 StringRef dir = getFieldAs<DIFile>(2).getDirectory(); 715 return !dir.empty() ? dir : getContext().getDirectory(); 716 } getFilename()717 StringRef getFilename() const { 718 StringRef filename = getFieldAs<DIFile>(2).getFilename(); 719 assert(!filename.empty() && "Why'd you create this then?"); 720 return filename; 721 } getScope()722 DILexicalBlock getScope() const { return getFieldAs<DILexicalBlock>(1); } 723 }; 724 725 /// DINameSpace - A wrapper for a C++ style name space. 726 class DINameSpace : public DIScope { 727 public: DIScope(N)728 explicit DINameSpace(const MDNode *N = 0) : DIScope(N) {} getContext()729 DIScope getContext() const { return getFieldAs<DIScope>(1); } getName()730 StringRef getName() const { return getStringField(2); } getDirectory()731 StringRef getDirectory() const { 732 return getFieldAs<DIFile>(3).getDirectory(); 733 } getFilename()734 StringRef getFilename() const { 735 return getFieldAs<DIFile>(3).getFilename(); 736 } getCompileUnit()737 DICompileUnit getCompileUnit() const{ 738 assert (getVersion() <= LLVMDebugVersion10 && "Invalid getCompileUnit!"); 739 if (getVersion() == llvm::LLVMDebugVersion7) 740 return getFieldAs<DICompileUnit>(3); 741 742 return getFieldAs<DIFile>(3).getCompileUnit(); 743 } getLineNumber()744 unsigned getLineNumber() const { return getUnsignedField(4); } 745 bool Verify() const; 746 }; 747 748 /// DILocation - This object holds location information. This object 749 /// is not associated with any DWARF tag. 750 class DILocation : public DIDescriptor { 751 public: DILocation(const MDNode * N)752 explicit DILocation(const MDNode *N) : DIDescriptor(N) { } 753 getLineNumber()754 unsigned getLineNumber() const { return getUnsignedField(0); } getColumnNumber()755 unsigned getColumnNumber() const { return getUnsignedField(1); } getScope()756 DIScope getScope() const { return getFieldAs<DIScope>(2); } getOrigLocation()757 DILocation getOrigLocation() const { return getFieldAs<DILocation>(3); } getFilename()758 StringRef getFilename() const { return getScope().getFilename(); } getDirectory()759 StringRef getDirectory() const { return getScope().getDirectory(); } 760 bool Verify() const; 761 }; 762 763 /// getDISubprogram - Find subprogram that is enclosing this scope. 764 DISubprogram getDISubprogram(const MDNode *Scope); 765 766 /// getDICompositeType - Find underlying composite type. 767 DICompositeType getDICompositeType(DIType T); 768 769 /// isSubprogramContext - Return true if Context is either a subprogram 770 /// or another context nested inside a subprogram. 771 bool isSubprogramContext(const MDNode *Context); 772 773 /// getOrInsertFnSpecificMDNode - Return a NameMDNode that is suitable 774 /// to hold function specific information. 775 NamedMDNode *getOrInsertFnSpecificMDNode(Module &M, DISubprogram SP); 776 777 /// getFnSpecificMDNode - Return a NameMDNode, if available, that is 778 /// suitable to hold function specific information. 779 NamedMDNode *getFnSpecificMDNode(const Module &M, DISubprogram SP); 780 781 /// createInlinedVariable - Create a new inlined variable based on current 782 /// variable. 783 /// @param DV Current Variable. 784 /// @param InlinedScope Location at current variable is inlined. 785 DIVariable createInlinedVariable(MDNode *DV, MDNode *InlinedScope, 786 LLVMContext &VMContext); 787 788 /// cleanseInlinedVariable - Remove inlined scope from the variable. 789 DIVariable cleanseInlinedVariable(MDNode *DV, LLVMContext &VMContext); 790 791 class DebugInfoFinder { 792 public: 793 /// processModule - Process entire module and collect debug info 794 /// anchors. 795 void processModule(Module &M); 796 797 private: 798 /// processType - Process DIType. 799 void processType(DIType DT); 800 801 /// processLexicalBlock - Process DILexicalBlock. 802 void processLexicalBlock(DILexicalBlock LB); 803 804 /// processSubprogram - Process DISubprogram. 805 void processSubprogram(DISubprogram SP); 806 807 /// processDeclare - Process DbgDeclareInst. 808 void processDeclare(DbgDeclareInst *DDI); 809 810 /// processLocation - Process DILocation. 811 void processLocation(DILocation Loc); 812 813 /// addCompileUnit - Add compile unit into CUs. 814 bool addCompileUnit(DICompileUnit CU); 815 816 /// addGlobalVariable - Add global variable into GVs. 817 bool addGlobalVariable(DIGlobalVariable DIG); 818 819 // addSubprogram - Add subprgoram into SPs. 820 bool addSubprogram(DISubprogram SP); 821 822 /// addType - Add type into Tys. 823 bool addType(DIType DT); 824 825 public: 826 typedef SmallVector<MDNode *, 8>::const_iterator iterator; compile_unit_begin()827 iterator compile_unit_begin() const { return CUs.begin(); } compile_unit_end()828 iterator compile_unit_end() const { return CUs.end(); } subprogram_begin()829 iterator subprogram_begin() const { return SPs.begin(); } subprogram_end()830 iterator subprogram_end() const { return SPs.end(); } global_variable_begin()831 iterator global_variable_begin() const { return GVs.begin(); } global_variable_end()832 iterator global_variable_end() const { return GVs.end(); } type_begin()833 iterator type_begin() const { return TYs.begin(); } type_end()834 iterator type_end() const { return TYs.end(); } 835 compile_unit_count()836 unsigned compile_unit_count() const { return CUs.size(); } global_variable_count()837 unsigned global_variable_count() const { return GVs.size(); } subprogram_count()838 unsigned subprogram_count() const { return SPs.size(); } type_count()839 unsigned type_count() const { return TYs.size(); } 840 841 private: 842 SmallVector<MDNode *, 8> CUs; // Compile Units 843 SmallVector<MDNode *, 8> SPs; // Subprograms 844 SmallVector<MDNode *, 8> GVs; // Global Variables; 845 SmallVector<MDNode *, 8> TYs; // Types 846 SmallPtrSet<MDNode *, 64> NodesSeen; 847 }; 848 } // end namespace llvm 849 850 #endif 851