1e5dd7070Spatrick //===--- CGDebugInfo.h - DebugInfo for LLVM CodeGen -------------*- C++ -*-===// 2e5dd7070Spatrick // 3e5dd7070Spatrick // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4e5dd7070Spatrick // See https://llvm.org/LICENSE.txt for license information. 5e5dd7070Spatrick // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6e5dd7070Spatrick // 7e5dd7070Spatrick //===----------------------------------------------------------------------===// 8e5dd7070Spatrick // 9e5dd7070Spatrick // This is the source-level debug info generator for llvm translation. 10e5dd7070Spatrick // 11e5dd7070Spatrick //===----------------------------------------------------------------------===// 12e5dd7070Spatrick 13e5dd7070Spatrick #ifndef LLVM_CLANG_LIB_CODEGEN_CGDEBUGINFO_H 14e5dd7070Spatrick #define LLVM_CLANG_LIB_CODEGEN_CGDEBUGINFO_H 15e5dd7070Spatrick 16e5dd7070Spatrick #include "CGBuilder.h" 17e5dd7070Spatrick #include "clang/AST/DeclCXX.h" 18e5dd7070Spatrick #include "clang/AST/Expr.h" 19e5dd7070Spatrick #include "clang/AST/ExternalASTSource.h" 20ec727ea7Spatrick #include "clang/AST/PrettyPrinter.h" 21e5dd7070Spatrick #include "clang/AST/Type.h" 22e5dd7070Spatrick #include "clang/AST/TypeOrdering.h" 23e5dd7070Spatrick #include "clang/Basic/CodeGenOptions.h" 24ec727ea7Spatrick #include "clang/Basic/Module.h" 25e5dd7070Spatrick #include "clang/Basic/SourceLocation.h" 26e5dd7070Spatrick #include "llvm/ADT/DenseMap.h" 27e5dd7070Spatrick #include "llvm/ADT/DenseSet.h" 28e5dd7070Spatrick #include "llvm/IR/DIBuilder.h" 29e5dd7070Spatrick #include "llvm/IR/DebugInfo.h" 30e5dd7070Spatrick #include "llvm/IR/ValueHandle.h" 31e5dd7070Spatrick #include "llvm/Support/Allocator.h" 32*12c85518Srobert #include <optional> 33e5dd7070Spatrick 34e5dd7070Spatrick namespace llvm { 35e5dd7070Spatrick class MDNode; 36e5dd7070Spatrick } 37e5dd7070Spatrick 38e5dd7070Spatrick namespace clang { 39e5dd7070Spatrick class ClassTemplateSpecializationDecl; 40e5dd7070Spatrick class GlobalDecl; 41e5dd7070Spatrick class ModuleMap; 42e5dd7070Spatrick class ObjCInterfaceDecl; 43e5dd7070Spatrick class UsingDecl; 44e5dd7070Spatrick class VarDecl; 45e5dd7070Spatrick enum class DynamicInitKind : unsigned; 46e5dd7070Spatrick 47e5dd7070Spatrick namespace CodeGen { 48e5dd7070Spatrick class CodeGenModule; 49e5dd7070Spatrick class CodeGenFunction; 50e5dd7070Spatrick class CGBlockInfo; 51e5dd7070Spatrick 52e5dd7070Spatrick /// This class gathers all debug information during compilation and is 53e5dd7070Spatrick /// responsible for emitting to llvm globals or pass directly to the 54e5dd7070Spatrick /// backend. 55e5dd7070Spatrick class CGDebugInfo { 56e5dd7070Spatrick friend class ApplyDebugLocation; 57e5dd7070Spatrick friend class SaveAndRestoreLocation; 58e5dd7070Spatrick CodeGenModule &CGM; 59e5dd7070Spatrick const codegenoptions::DebugInfoKind DebugKind; 60e5dd7070Spatrick bool DebugTypeExtRefs; 61e5dd7070Spatrick llvm::DIBuilder DBuilder; 62e5dd7070Spatrick llvm::DICompileUnit *TheCU = nullptr; 63e5dd7070Spatrick ModuleMap *ClangModuleMap = nullptr; 64ec727ea7Spatrick ASTSourceDescriptor PCHDescriptor; 65e5dd7070Spatrick SourceLocation CurLoc; 66e5dd7070Spatrick llvm::MDNode *CurInlinedAt = nullptr; 67e5dd7070Spatrick llvm::DIType *VTablePtrType = nullptr; 68e5dd7070Spatrick llvm::DIType *ClassTy = nullptr; 69e5dd7070Spatrick llvm::DICompositeType *ObjTy = nullptr; 70e5dd7070Spatrick llvm::DIType *SelTy = nullptr; 71e5dd7070Spatrick #define IMAGE_TYPE(ImgType, Id, SingletonId, Access, Suffix) \ 72e5dd7070Spatrick llvm::DIType *SingletonId = nullptr; 73e5dd7070Spatrick #include "clang/Basic/OpenCLImageTypes.def" 74e5dd7070Spatrick llvm::DIType *OCLSamplerDITy = nullptr; 75e5dd7070Spatrick llvm::DIType *OCLEventDITy = nullptr; 76e5dd7070Spatrick llvm::DIType *OCLClkEventDITy = nullptr; 77e5dd7070Spatrick llvm::DIType *OCLQueueDITy = nullptr; 78e5dd7070Spatrick llvm::DIType *OCLNDRangeDITy = nullptr; 79e5dd7070Spatrick llvm::DIType *OCLReserveIDDITy = nullptr; 80e5dd7070Spatrick #define EXT_OPAQUE_TYPE(ExtType, Id, Ext) \ 81e5dd7070Spatrick llvm::DIType *Id##Ty = nullptr; 82e5dd7070Spatrick #include "clang/Basic/OpenCLExtensionTypes.def" 83e5dd7070Spatrick 84e5dd7070Spatrick /// Cache of previously constructed Types. 85e5dd7070Spatrick llvm::DenseMap<const void *, llvm::TrackingMDRef> TypeCache; 86e5dd7070Spatrick 87e5dd7070Spatrick std::map<llvm::StringRef, llvm::StringRef, std::greater<llvm::StringRef>> 88e5dd7070Spatrick DebugPrefixMap; 89e5dd7070Spatrick 90e5dd7070Spatrick /// Cache that maps VLA types to size expressions for that type, 91e5dd7070Spatrick /// represented by instantiated Metadata nodes. 92e5dd7070Spatrick llvm::SmallDenseMap<QualType, llvm::Metadata *> SizeExprCache; 93e5dd7070Spatrick 94e5dd7070Spatrick /// Callbacks to use when printing names and types. 95e5dd7070Spatrick class PrintingCallbacks final : public clang::PrintingCallbacks { 96e5dd7070Spatrick const CGDebugInfo &Self; 97e5dd7070Spatrick 98e5dd7070Spatrick public: PrintingCallbacks(const CGDebugInfo & Self)99e5dd7070Spatrick PrintingCallbacks(const CGDebugInfo &Self) : Self(Self) {} remapPath(StringRef Path)100e5dd7070Spatrick std::string remapPath(StringRef Path) const override { 101e5dd7070Spatrick return Self.remapDIPath(Path); 102e5dd7070Spatrick } 103e5dd7070Spatrick }; 104e5dd7070Spatrick PrintingCallbacks PrintCB = {*this}; 105e5dd7070Spatrick 106e5dd7070Spatrick struct ObjCInterfaceCacheEntry { 107e5dd7070Spatrick const ObjCInterfaceType *Type; 108e5dd7070Spatrick llvm::DIType *Decl; 109e5dd7070Spatrick llvm::DIFile *Unit; ObjCInterfaceCacheEntryObjCInterfaceCacheEntry110e5dd7070Spatrick ObjCInterfaceCacheEntry(const ObjCInterfaceType *Type, llvm::DIType *Decl, 111e5dd7070Spatrick llvm::DIFile *Unit) 112e5dd7070Spatrick : Type(Type), Decl(Decl), Unit(Unit) {} 113e5dd7070Spatrick }; 114e5dd7070Spatrick 115e5dd7070Spatrick /// Cache of previously constructed interfaces which may change. 116e5dd7070Spatrick llvm::SmallVector<ObjCInterfaceCacheEntry, 32> ObjCInterfaceCache; 117e5dd7070Spatrick 118e5dd7070Spatrick /// Cache of forward declarations for methods belonging to the interface. 119e5dd7070Spatrick /// The extra bit on the DISubprogram specifies whether a method is 120e5dd7070Spatrick /// "objc_direct". 121e5dd7070Spatrick llvm::DenseMap<const ObjCInterfaceDecl *, 122e5dd7070Spatrick std::vector<llvm::PointerIntPair<llvm::DISubprogram *, 1>>> 123e5dd7070Spatrick ObjCMethodCache; 124e5dd7070Spatrick 125e5dd7070Spatrick /// Cache of references to clang modules and precompiled headers. 126e5dd7070Spatrick llvm::DenseMap<const Module *, llvm::TrackingMDRef> ModuleCache; 127e5dd7070Spatrick 128e5dd7070Spatrick /// List of interfaces we want to keep even if orphaned. 129e5dd7070Spatrick std::vector<void *> RetainedTypes; 130e5dd7070Spatrick 131e5dd7070Spatrick /// Cache of forward declared types to RAUW at the end of compilation. 132e5dd7070Spatrick std::vector<std::pair<const TagType *, llvm::TrackingMDRef>> ReplaceMap; 133e5dd7070Spatrick 134e5dd7070Spatrick /// Cache of replaceable forward declarations (functions and 135e5dd7070Spatrick /// variables) to RAUW at the end of compilation. 136e5dd7070Spatrick std::vector<std::pair<const DeclaratorDecl *, llvm::TrackingMDRef>> 137e5dd7070Spatrick FwdDeclReplaceMap; 138e5dd7070Spatrick 139e5dd7070Spatrick /// Keep track of our current nested lexical block. 140e5dd7070Spatrick std::vector<llvm::TypedTrackingMDRef<llvm::DIScope>> LexicalBlockStack; 141e5dd7070Spatrick llvm::DenseMap<const Decl *, llvm::TrackingMDRef> RegionMap; 142e5dd7070Spatrick /// Keep track of LexicalBlockStack counter at the beginning of a 143e5dd7070Spatrick /// function. This is used to pop unbalanced regions at the end of a 144e5dd7070Spatrick /// function. 145e5dd7070Spatrick std::vector<unsigned> FnBeginRegionCount; 146e5dd7070Spatrick 147e5dd7070Spatrick /// This is a storage for names that are constructed on demand. For 148e5dd7070Spatrick /// example, C++ destructors, C++ operators etc.. 149e5dd7070Spatrick llvm::BumpPtrAllocator DebugInfoNames; 150e5dd7070Spatrick StringRef CWDName; 151e5dd7070Spatrick 152e5dd7070Spatrick llvm::DenseMap<const char *, llvm::TrackingMDRef> DIFileCache; 153e5dd7070Spatrick llvm::DenseMap<const FunctionDecl *, llvm::TrackingMDRef> SPCache; 154e5dd7070Spatrick /// Cache declarations relevant to DW_TAG_imported_declarations (C++ 155*12c85518Srobert /// using declarations and global alias variables) that aren't covered 156*12c85518Srobert /// by other more specific caches. 157e5dd7070Spatrick llvm::DenseMap<const Decl *, llvm::TrackingMDRef> DeclCache; 158*12c85518Srobert llvm::DenseMap<const Decl *, llvm::TrackingMDRef> ImportedDeclCache; 159e5dd7070Spatrick llvm::DenseMap<const NamespaceDecl *, llvm::TrackingMDRef> NamespaceCache; 160e5dd7070Spatrick llvm::DenseMap<const NamespaceAliasDecl *, llvm::TrackingMDRef> 161e5dd7070Spatrick NamespaceAliasCache; 162e5dd7070Spatrick llvm::DenseMap<const Decl *, llvm::TypedTrackingMDRef<llvm::DIDerivedType>> 163e5dd7070Spatrick StaticDataMemberCache; 164e5dd7070Spatrick 165a9ac8606Spatrick using ParamDecl2StmtTy = llvm::DenseMap<const ParmVarDecl *, const Stmt *>; 166a9ac8606Spatrick using Param2DILocTy = 167a9ac8606Spatrick llvm::DenseMap<const ParmVarDecl *, llvm::DILocalVariable *>; 168a9ac8606Spatrick 169a9ac8606Spatrick /// The key is coroutine real parameters, value is coroutine move parameters. 170a9ac8606Spatrick ParamDecl2StmtTy CoroutineParameterMappings; 171a9ac8606Spatrick /// The key is coroutine real parameters, value is DIVariable in LLVM IR. 172a9ac8606Spatrick Param2DILocTy ParamDbgMappings; 173a9ac8606Spatrick 174e5dd7070Spatrick /// Helper functions for getOrCreateType. 175e5dd7070Spatrick /// @{ 176e5dd7070Spatrick /// Currently the checksum of an interface includes the number of 177e5dd7070Spatrick /// ivars and property accessors. 178e5dd7070Spatrick llvm::DIType *CreateType(const BuiltinType *Ty); 179e5dd7070Spatrick llvm::DIType *CreateType(const ComplexType *Ty); 180*12c85518Srobert llvm::DIType *CreateType(const BitIntType *Ty); 181e5dd7070Spatrick llvm::DIType *CreateQualifiedType(QualType Ty, llvm::DIFile *Fg); 182*12c85518Srobert llvm::DIType *CreateQualifiedType(const FunctionProtoType *Ty, 183*12c85518Srobert llvm::DIFile *Fg); 184e5dd7070Spatrick llvm::DIType *CreateType(const TypedefType *Ty, llvm::DIFile *Fg); 185e5dd7070Spatrick llvm::DIType *CreateType(const TemplateSpecializationType *Ty, 186e5dd7070Spatrick llvm::DIFile *Fg); 187e5dd7070Spatrick llvm::DIType *CreateType(const ObjCObjectPointerType *Ty, llvm::DIFile *F); 188e5dd7070Spatrick llvm::DIType *CreateType(const PointerType *Ty, llvm::DIFile *F); 189e5dd7070Spatrick llvm::DIType *CreateType(const BlockPointerType *Ty, llvm::DIFile *F); 190e5dd7070Spatrick llvm::DIType *CreateType(const FunctionType *Ty, llvm::DIFile *F); 191e5dd7070Spatrick /// Get structure or union type. 192e5dd7070Spatrick llvm::DIType *CreateType(const RecordType *Tyg); 193e5dd7070Spatrick llvm::DIType *CreateTypeDefinition(const RecordType *Ty); 194e5dd7070Spatrick llvm::DICompositeType *CreateLimitedType(const RecordType *Ty); 195e5dd7070Spatrick void CollectContainingType(const CXXRecordDecl *RD, 196e5dd7070Spatrick llvm::DICompositeType *CT); 197e5dd7070Spatrick /// Get Objective-C interface type. 198e5dd7070Spatrick llvm::DIType *CreateType(const ObjCInterfaceType *Ty, llvm::DIFile *F); 199e5dd7070Spatrick llvm::DIType *CreateTypeDefinition(const ObjCInterfaceType *Ty, 200e5dd7070Spatrick llvm::DIFile *F); 201e5dd7070Spatrick /// Get Objective-C object type. 202e5dd7070Spatrick llvm::DIType *CreateType(const ObjCObjectType *Ty, llvm::DIFile *F); 203e5dd7070Spatrick llvm::DIType *CreateType(const ObjCTypeParamType *Ty, llvm::DIFile *Unit); 204e5dd7070Spatrick 205e5dd7070Spatrick llvm::DIType *CreateType(const VectorType *Ty, llvm::DIFile *F); 206ec727ea7Spatrick llvm::DIType *CreateType(const ConstantMatrixType *Ty, llvm::DIFile *F); 207e5dd7070Spatrick llvm::DIType *CreateType(const ArrayType *Ty, llvm::DIFile *F); 208e5dd7070Spatrick llvm::DIType *CreateType(const LValueReferenceType *Ty, llvm::DIFile *F); 209e5dd7070Spatrick llvm::DIType *CreateType(const RValueReferenceType *Ty, llvm::DIFile *Unit); 210e5dd7070Spatrick llvm::DIType *CreateType(const MemberPointerType *Ty, llvm::DIFile *F); 211e5dd7070Spatrick llvm::DIType *CreateType(const AtomicType *Ty, llvm::DIFile *F); 212e5dd7070Spatrick llvm::DIType *CreateType(const PipeType *Ty, llvm::DIFile *F); 213e5dd7070Spatrick /// Get enumeration type. 214e5dd7070Spatrick llvm::DIType *CreateEnumType(const EnumType *Ty); 215e5dd7070Spatrick llvm::DIType *CreateTypeDefinition(const EnumType *Ty); 216e5dd7070Spatrick /// Look up the completed type for a self pointer in the TypeCache and 217e5dd7070Spatrick /// create a copy of it with the ObjectPointer and Artificial flags 218e5dd7070Spatrick /// set. If the type is not cached, a new one is created. This should 219e5dd7070Spatrick /// never happen though, since creating a type for the implicit self 220e5dd7070Spatrick /// argument implies that we already parsed the interface definition 221e5dd7070Spatrick /// and the ivar declarations in the implementation. 222e5dd7070Spatrick llvm::DIType *CreateSelfType(const QualType &QualTy, llvm::DIType *Ty); 223e5dd7070Spatrick /// @} 224e5dd7070Spatrick 225e5dd7070Spatrick /// Get the type from the cache or return null type if it doesn't 226e5dd7070Spatrick /// exist. 227e5dd7070Spatrick llvm::DIType *getTypeOrNull(const QualType); 228e5dd7070Spatrick /// Return the debug type for a C++ method. 229e5dd7070Spatrick /// \arg CXXMethodDecl is of FunctionType. This function type is 230e5dd7070Spatrick /// not updated to include implicit \c this pointer. Use this routine 231e5dd7070Spatrick /// to get a method type which includes \c this pointer. 232e5dd7070Spatrick llvm::DISubroutineType *getOrCreateMethodType(const CXXMethodDecl *Method, 233*12c85518Srobert llvm::DIFile *F); 234e5dd7070Spatrick llvm::DISubroutineType * 235e5dd7070Spatrick getOrCreateInstanceMethodType(QualType ThisPtr, const FunctionProtoType *Func, 236*12c85518Srobert llvm::DIFile *Unit); 237e5dd7070Spatrick llvm::DISubroutineType * 238e5dd7070Spatrick getOrCreateFunctionType(const Decl *D, QualType FnType, llvm::DIFile *F); 239e5dd7070Spatrick /// \return debug info descriptor for vtable. 240e5dd7070Spatrick llvm::DIType *getOrCreateVTablePtrType(llvm::DIFile *F); 241e5dd7070Spatrick 242e5dd7070Spatrick /// \return namespace descriptor for the given namespace decl. 243e5dd7070Spatrick llvm::DINamespace *getOrCreateNamespace(const NamespaceDecl *N); 244e5dd7070Spatrick llvm::DIType *CreatePointerLikeType(llvm::dwarf::Tag Tag, const Type *Ty, 245e5dd7070Spatrick QualType PointeeTy, llvm::DIFile *F); 246e5dd7070Spatrick llvm::DIType *getOrCreateStructPtrType(StringRef Name, llvm::DIType *&Cache); 247e5dd7070Spatrick 248e5dd7070Spatrick /// A helper function to create a subprogram for a single member 249e5dd7070Spatrick /// function GlobalDecl. 250e5dd7070Spatrick llvm::DISubprogram *CreateCXXMemberFunction(const CXXMethodDecl *Method, 251e5dd7070Spatrick llvm::DIFile *F, 252e5dd7070Spatrick llvm::DIType *RecordTy); 253e5dd7070Spatrick 254e5dd7070Spatrick /// A helper function to collect debug info for C++ member 255e5dd7070Spatrick /// functions. This is used while creating debug info entry for a 256e5dd7070Spatrick /// Record. 257e5dd7070Spatrick void CollectCXXMemberFunctions(const CXXRecordDecl *Decl, llvm::DIFile *F, 258e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &E, 259e5dd7070Spatrick llvm::DIType *T); 260e5dd7070Spatrick 261e5dd7070Spatrick /// A helper function to collect debug info for C++ base 262e5dd7070Spatrick /// classes. This is used while creating debug info entry for a 263e5dd7070Spatrick /// Record. 264e5dd7070Spatrick void CollectCXXBases(const CXXRecordDecl *Decl, llvm::DIFile *F, 265e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &EltTys, 266e5dd7070Spatrick llvm::DIType *RecordTy); 267e5dd7070Spatrick 268e5dd7070Spatrick /// Helper function for CollectCXXBases. 269e5dd7070Spatrick /// Adds debug info entries for types in Bases that are not in SeenTypes. 270e5dd7070Spatrick void CollectCXXBasesAux( 271e5dd7070Spatrick const CXXRecordDecl *RD, llvm::DIFile *Unit, 272e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &EltTys, llvm::DIType *RecordTy, 273e5dd7070Spatrick const CXXRecordDecl::base_class_const_range &Bases, 274e5dd7070Spatrick llvm::DenseSet<CanonicalDeclPtr<const CXXRecordDecl>> &SeenTypes, 275e5dd7070Spatrick llvm::DINode::DIFlags StartingFlags); 276e5dd7070Spatrick 277*12c85518Srobert struct TemplateArgs { 278*12c85518Srobert const TemplateParameterList *TList; 279*12c85518Srobert llvm::ArrayRef<TemplateArgument> Args; 280*12c85518Srobert }; 281e5dd7070Spatrick /// A helper function to collect template parameters. 282*12c85518Srobert llvm::DINodeArray CollectTemplateParams(std::optional<TemplateArgs> Args, 283e5dd7070Spatrick llvm::DIFile *Unit); 284e5dd7070Spatrick /// A helper function to collect debug info for function template 285e5dd7070Spatrick /// parameters. 286e5dd7070Spatrick llvm::DINodeArray CollectFunctionTemplateParams(const FunctionDecl *FD, 287e5dd7070Spatrick llvm::DIFile *Unit); 288e5dd7070Spatrick 289e5dd7070Spatrick /// A helper function to collect debug info for function template 290e5dd7070Spatrick /// parameters. 291e5dd7070Spatrick llvm::DINodeArray CollectVarTemplateParams(const VarDecl *VD, 292e5dd7070Spatrick llvm::DIFile *Unit); 293e5dd7070Spatrick 294*12c85518Srobert std::optional<TemplateArgs> GetTemplateArgs(const VarDecl *) const; 295*12c85518Srobert std::optional<TemplateArgs> GetTemplateArgs(const RecordDecl *) const; 296*12c85518Srobert std::optional<TemplateArgs> GetTemplateArgs(const FunctionDecl *) const; 297*12c85518Srobert 298e5dd7070Spatrick /// A helper function to collect debug info for template 299e5dd7070Spatrick /// parameters. 300*12c85518Srobert llvm::DINodeArray CollectCXXTemplateParams(const RecordDecl *TS, 301e5dd7070Spatrick llvm::DIFile *F); 302e5dd7070Spatrick 303*12c85518Srobert /// A helper function to collect debug info for btf_decl_tag annotations. 304*12c85518Srobert llvm::DINodeArray CollectBTFDeclTagAnnotations(const Decl *D); 305*12c85518Srobert 306e5dd7070Spatrick llvm::DIType *createFieldType(StringRef name, QualType type, 307e5dd7070Spatrick SourceLocation loc, AccessSpecifier AS, 308e5dd7070Spatrick uint64_t offsetInBits, uint32_t AlignInBits, 309e5dd7070Spatrick llvm::DIFile *tunit, llvm::DIScope *scope, 310*12c85518Srobert const RecordDecl *RD = nullptr, 311*12c85518Srobert llvm::DINodeArray Annotations = nullptr); 312e5dd7070Spatrick 313e5dd7070Spatrick llvm::DIType *createFieldType(StringRef name, QualType type, 314e5dd7070Spatrick SourceLocation loc, AccessSpecifier AS, 315e5dd7070Spatrick uint64_t offsetInBits, llvm::DIFile *tunit, 316e5dd7070Spatrick llvm::DIScope *scope, 317e5dd7070Spatrick const RecordDecl *RD = nullptr) { 318e5dd7070Spatrick return createFieldType(name, type, loc, AS, offsetInBits, 0, tunit, scope, 319e5dd7070Spatrick RD); 320e5dd7070Spatrick } 321e5dd7070Spatrick 322e5dd7070Spatrick /// Create new bit field member. 323e5dd7070Spatrick llvm::DIType *createBitFieldType(const FieldDecl *BitFieldDecl, 324e5dd7070Spatrick llvm::DIScope *RecordTy, 325e5dd7070Spatrick const RecordDecl *RD); 326e5dd7070Spatrick 327e5dd7070Spatrick /// Helpers for collecting fields of a record. 328e5dd7070Spatrick /// @{ 329e5dd7070Spatrick void CollectRecordLambdaFields(const CXXRecordDecl *CXXDecl, 330e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &E, 331e5dd7070Spatrick llvm::DIType *RecordTy); 332e5dd7070Spatrick llvm::DIDerivedType *CreateRecordStaticField(const VarDecl *Var, 333e5dd7070Spatrick llvm::DIType *RecordTy, 334e5dd7070Spatrick const RecordDecl *RD); 335e5dd7070Spatrick void CollectRecordNormalField(const FieldDecl *Field, uint64_t OffsetInBits, 336e5dd7070Spatrick llvm::DIFile *F, 337e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &E, 338e5dd7070Spatrick llvm::DIType *RecordTy, const RecordDecl *RD); 339e5dd7070Spatrick void CollectRecordNestedType(const TypeDecl *RD, 340e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &E); 341e5dd7070Spatrick void CollectRecordFields(const RecordDecl *Decl, llvm::DIFile *F, 342e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &E, 343e5dd7070Spatrick llvm::DICompositeType *RecordTy); 344e5dd7070Spatrick 345e5dd7070Spatrick /// If the C++ class has vtable info then insert appropriate debug 346e5dd7070Spatrick /// info entry in EltTys vector. 347e5dd7070Spatrick void CollectVTableInfo(const CXXRecordDecl *Decl, llvm::DIFile *F, 348a9ac8606Spatrick SmallVectorImpl<llvm::Metadata *> &EltTys); 349e5dd7070Spatrick /// @} 350e5dd7070Spatrick 351e5dd7070Spatrick /// Create a new lexical block node and push it on the stack. 352e5dd7070Spatrick void CreateLexicalBlock(SourceLocation Loc); 353e5dd7070Spatrick 354e5dd7070Spatrick /// If target-specific LLVM \p AddressSpace directly maps to target-specific 355e5dd7070Spatrick /// DWARF address space, appends extended dereferencing mechanism to complex 356e5dd7070Spatrick /// expression \p Expr. Otherwise, does nothing. 357e5dd7070Spatrick /// 358e5dd7070Spatrick /// Extended dereferencing mechanism is has the following format: 359e5dd7070Spatrick /// DW_OP_constu <DWARF Address Space> DW_OP_swap DW_OP_xderef 360e5dd7070Spatrick void AppendAddressSpaceXDeref(unsigned AddressSpace, 361*12c85518Srobert SmallVectorImpl<uint64_t> &Expr) const; 362e5dd7070Spatrick 363e5dd7070Spatrick /// A helper function to collect debug info for the default elements of a 364e5dd7070Spatrick /// block. 365e5dd7070Spatrick /// 366e5dd7070Spatrick /// \returns The next available field offset after the default elements. 367e5dd7070Spatrick uint64_t collectDefaultElementTypesForBlockPointer( 368e5dd7070Spatrick const BlockPointerType *Ty, llvm::DIFile *Unit, 369e5dd7070Spatrick llvm::DIDerivedType *DescTy, unsigned LineNo, 370e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &EltTys); 371e5dd7070Spatrick 372e5dd7070Spatrick /// A helper function to collect debug info for the default fields of a 373e5dd7070Spatrick /// block. 374e5dd7070Spatrick void collectDefaultFieldsForBlockLiteralDeclare( 375e5dd7070Spatrick const CGBlockInfo &Block, const ASTContext &Context, SourceLocation Loc, 376e5dd7070Spatrick const llvm::StructLayout &BlockLayout, llvm::DIFile *Unit, 377e5dd7070Spatrick SmallVectorImpl<llvm::Metadata *> &Fields); 378e5dd7070Spatrick 379e5dd7070Spatrick public: 380e5dd7070Spatrick CGDebugInfo(CodeGenModule &CGM); 381e5dd7070Spatrick ~CGDebugInfo(); 382e5dd7070Spatrick 383e5dd7070Spatrick void finalize(); 384e5dd7070Spatrick 385e5dd7070Spatrick /// Remap a given path with the current debug prefix map 386e5dd7070Spatrick std::string remapDIPath(StringRef) const; 387e5dd7070Spatrick 388e5dd7070Spatrick /// Register VLA size expression debug node with the qualified type. registerVLASizeExpression(QualType Ty,llvm::Metadata * SizeExpr)389e5dd7070Spatrick void registerVLASizeExpression(QualType Ty, llvm::Metadata *SizeExpr) { 390e5dd7070Spatrick SizeExprCache[Ty] = SizeExpr; 391e5dd7070Spatrick } 392e5dd7070Spatrick 393e5dd7070Spatrick /// Module debugging: Support for building PCMs. 394e5dd7070Spatrick /// @{ 395e5dd7070Spatrick /// Set the main CU's DwoId field to \p Signature. 396e5dd7070Spatrick void setDwoId(uint64_t Signature); 397e5dd7070Spatrick 398e5dd7070Spatrick /// When generating debug information for a clang module or 399e5dd7070Spatrick /// precompiled header, this module map will be used to determine 400e5dd7070Spatrick /// the module of origin of each Decl. setModuleMap(ModuleMap & MMap)401e5dd7070Spatrick void setModuleMap(ModuleMap &MMap) { ClangModuleMap = &MMap; } 402e5dd7070Spatrick 403e5dd7070Spatrick /// When generating debug information for a clang module or 404e5dd7070Spatrick /// precompiled header, this module map will be used to determine 405e5dd7070Spatrick /// the module of origin of each Decl. setPCHDescriptor(ASTSourceDescriptor PCH)406ec727ea7Spatrick void setPCHDescriptor(ASTSourceDescriptor PCH) { PCHDescriptor = PCH; } 407e5dd7070Spatrick /// @} 408e5dd7070Spatrick 409e5dd7070Spatrick /// Update the current source location. If \arg loc is invalid it is 410e5dd7070Spatrick /// ignored. 411e5dd7070Spatrick void setLocation(SourceLocation Loc); 412e5dd7070Spatrick 413e5dd7070Spatrick /// Return the current source location. This does not necessarily correspond 414e5dd7070Spatrick /// to the IRBuilder's current DebugLoc. getLocation()415e5dd7070Spatrick SourceLocation getLocation() const { return CurLoc; } 416e5dd7070Spatrick 417e5dd7070Spatrick /// Update the current inline scope. All subsequent calls to \p EmitLocation 418e5dd7070Spatrick /// will create a location with this inlinedAt field. setInlinedAt(llvm::MDNode * InlinedAt)419e5dd7070Spatrick void setInlinedAt(llvm::MDNode *InlinedAt) { CurInlinedAt = InlinedAt; } 420e5dd7070Spatrick 421e5dd7070Spatrick /// \return the current inline scope. getInlinedAt()422e5dd7070Spatrick llvm::MDNode *getInlinedAt() const { return CurInlinedAt; } 423e5dd7070Spatrick 424e5dd7070Spatrick // Converts a SourceLocation to a DebugLoc 425e5dd7070Spatrick llvm::DebugLoc SourceLocToDebugLoc(SourceLocation Loc); 426e5dd7070Spatrick 427e5dd7070Spatrick /// Emit metadata to indicate a change in line/column information in 428e5dd7070Spatrick /// the source file. If the location is invalid, the previous 429e5dd7070Spatrick /// location will be reused. 430e5dd7070Spatrick void EmitLocation(CGBuilderTy &Builder, SourceLocation Loc); 431e5dd7070Spatrick 432*12c85518Srobert QualType getFunctionType(const FunctionDecl *FD, QualType RetTy, 433*12c85518Srobert const SmallVectorImpl<const VarDecl *> &Args); 434*12c85518Srobert 435e5dd7070Spatrick /// Emit a call to llvm.dbg.function.start to indicate 436e5dd7070Spatrick /// start of a new function. 437e5dd7070Spatrick /// \param Loc The location of the function header. 438e5dd7070Spatrick /// \param ScopeLoc The location of the function body. 439a9ac8606Spatrick void emitFunctionStart(GlobalDecl GD, SourceLocation Loc, 440e5dd7070Spatrick SourceLocation ScopeLoc, QualType FnType, 441a9ac8606Spatrick llvm::Function *Fn, bool CurFnIsThunk); 442e5dd7070Spatrick 443e5dd7070Spatrick /// Start a new scope for an inlined function. 444e5dd7070Spatrick void EmitInlineFunctionStart(CGBuilderTy &Builder, GlobalDecl GD); 445e5dd7070Spatrick /// End an inlined function scope. 446e5dd7070Spatrick void EmitInlineFunctionEnd(CGBuilderTy &Builder); 447e5dd7070Spatrick 448e5dd7070Spatrick /// Emit debug info for a function declaration. 449e5dd7070Spatrick /// \p Fn is set only when a declaration for a debug call site gets created. 450e5dd7070Spatrick void EmitFunctionDecl(GlobalDecl GD, SourceLocation Loc, 451e5dd7070Spatrick QualType FnType, llvm::Function *Fn = nullptr); 452e5dd7070Spatrick 453e5dd7070Spatrick /// Emit debug info for an extern function being called. 454e5dd7070Spatrick /// This is needed for call site debug info. 455e5dd7070Spatrick void EmitFuncDeclForCallSite(llvm::CallBase *CallOrInvoke, 456e5dd7070Spatrick QualType CalleeType, 457e5dd7070Spatrick const FunctionDecl *CalleeDecl); 458e5dd7070Spatrick 459e5dd7070Spatrick /// Constructs the debug code for exiting a function. 460e5dd7070Spatrick void EmitFunctionEnd(CGBuilderTy &Builder, llvm::Function *Fn); 461e5dd7070Spatrick 462e5dd7070Spatrick /// Emit metadata to indicate the beginning of a new lexical block 463e5dd7070Spatrick /// and push the block onto the stack. 464e5dd7070Spatrick void EmitLexicalBlockStart(CGBuilderTy &Builder, SourceLocation Loc); 465e5dd7070Spatrick 466e5dd7070Spatrick /// Emit metadata to indicate the end of a new lexical block and pop 467e5dd7070Spatrick /// the current block. 468e5dd7070Spatrick void EmitLexicalBlockEnd(CGBuilderTy &Builder, SourceLocation Loc); 469e5dd7070Spatrick 470e5dd7070Spatrick /// Emit call to \c llvm.dbg.declare for an automatic variable 471e5dd7070Spatrick /// declaration. 472e5dd7070Spatrick /// Returns a pointer to the DILocalVariable associated with the 473e5dd7070Spatrick /// llvm.dbg.declare, or nullptr otherwise. 474e5dd7070Spatrick llvm::DILocalVariable * 475e5dd7070Spatrick EmitDeclareOfAutoVariable(const VarDecl *Decl, llvm::Value *AI, 476e5dd7070Spatrick CGBuilderTy &Builder, 477e5dd7070Spatrick const bool UsePointerValue = false); 478e5dd7070Spatrick 479e5dd7070Spatrick /// Emit call to \c llvm.dbg.label for an label. 480e5dd7070Spatrick void EmitLabel(const LabelDecl *D, CGBuilderTy &Builder); 481e5dd7070Spatrick 482e5dd7070Spatrick /// Emit call to \c llvm.dbg.declare for an imported variable 483e5dd7070Spatrick /// declaration in a block. 484e5dd7070Spatrick void EmitDeclareOfBlockDeclRefVariable( 485e5dd7070Spatrick const VarDecl *variable, llvm::Value *storage, CGBuilderTy &Builder, 486e5dd7070Spatrick const CGBlockInfo &blockInfo, llvm::Instruction *InsertPoint = nullptr); 487e5dd7070Spatrick 488e5dd7070Spatrick /// Emit call to \c llvm.dbg.declare for an argument variable 489e5dd7070Spatrick /// declaration. 490a9ac8606Spatrick llvm::DILocalVariable *EmitDeclareOfArgVariable(const VarDecl *Decl, 491a9ac8606Spatrick llvm::Value *AI, 492a9ac8606Spatrick unsigned ArgNo, 493a9ac8606Spatrick CGBuilderTy &Builder); 494e5dd7070Spatrick 495e5dd7070Spatrick /// Emit call to \c llvm.dbg.declare for the block-literal argument 496e5dd7070Spatrick /// to a block invocation function. 497e5dd7070Spatrick void EmitDeclareOfBlockLiteralArgVariable(const CGBlockInfo &block, 498e5dd7070Spatrick StringRef Name, unsigned ArgNo, 499e5dd7070Spatrick llvm::AllocaInst *LocalAddr, 500e5dd7070Spatrick CGBuilderTy &Builder); 501e5dd7070Spatrick 502e5dd7070Spatrick /// Emit information about a global variable. 503e5dd7070Spatrick void EmitGlobalVariable(llvm::GlobalVariable *GV, const VarDecl *Decl); 504e5dd7070Spatrick 505e5dd7070Spatrick /// Emit a constant global variable's debug info. 506e5dd7070Spatrick void EmitGlobalVariable(const ValueDecl *VD, const APValue &Init); 507e5dd7070Spatrick 508e5dd7070Spatrick /// Emit information about an external variable. 509e5dd7070Spatrick void EmitExternalVariable(llvm::GlobalVariable *GV, const VarDecl *Decl); 510e5dd7070Spatrick 511*12c85518Srobert /// Emit information about global variable alias. 512*12c85518Srobert void EmitGlobalAlias(const llvm::GlobalValue *GV, const GlobalDecl Decl); 513*12c85518Srobert 514e5dd7070Spatrick /// Emit C++ using directive. 515e5dd7070Spatrick void EmitUsingDirective(const UsingDirectiveDecl &UD); 516e5dd7070Spatrick 517e5dd7070Spatrick /// Emit the type explicitly casted to. 518e5dd7070Spatrick void EmitExplicitCastType(QualType Ty); 519e5dd7070Spatrick 520a9ac8606Spatrick /// Emit the type even if it might not be used. 521a9ac8606Spatrick void EmitAndRetainType(QualType Ty); 522a9ac8606Spatrick 523a9ac8606Spatrick /// Emit a shadow decl brought in by a using or using-enum 524a9ac8606Spatrick void EmitUsingShadowDecl(const UsingShadowDecl &USD); 525a9ac8606Spatrick 526e5dd7070Spatrick /// Emit C++ using declaration. 527e5dd7070Spatrick void EmitUsingDecl(const UsingDecl &UD); 528e5dd7070Spatrick 529a9ac8606Spatrick /// Emit C++ using-enum declaration. 530a9ac8606Spatrick void EmitUsingEnumDecl(const UsingEnumDecl &UD); 531a9ac8606Spatrick 532e5dd7070Spatrick /// Emit an @import declaration. 533e5dd7070Spatrick void EmitImportDecl(const ImportDecl &ID); 534e5dd7070Spatrick 535*12c85518Srobert /// DebugInfo isn't attached to string literals by default. While certain 536*12c85518Srobert /// aspects of debuginfo aren't useful for string literals (like a name), it's 537*12c85518Srobert /// nice to be able to symbolize the line and column information. This is 538*12c85518Srobert /// especially useful for sanitizers, as it allows symbolization of 539*12c85518Srobert /// heap-buffer-overflows on constant strings. 540*12c85518Srobert void AddStringLiteralDebugInfo(llvm::GlobalVariable *GV, 541*12c85518Srobert const StringLiteral *S); 542*12c85518Srobert 543e5dd7070Spatrick /// Emit C++ namespace alias. 544e5dd7070Spatrick llvm::DIImportedEntity *EmitNamespaceAlias(const NamespaceAliasDecl &NA); 545e5dd7070Spatrick 546e5dd7070Spatrick /// Emit record type's standalone debug info. 547e5dd7070Spatrick llvm::DIType *getOrCreateRecordType(QualType Ty, SourceLocation L); 548e5dd7070Spatrick 549e5dd7070Spatrick /// Emit an Objective-C interface type standalone debug info. 550e5dd7070Spatrick llvm::DIType *getOrCreateInterfaceType(QualType Ty, SourceLocation Loc); 551e5dd7070Spatrick 552e5dd7070Spatrick /// Emit standalone debug info for a type. 553e5dd7070Spatrick llvm::DIType *getOrCreateStandaloneType(QualType Ty, SourceLocation Loc); 554e5dd7070Spatrick 555e5dd7070Spatrick /// Add heapallocsite metadata for MSAllocator calls. 556ec727ea7Spatrick void addHeapAllocSiteMetadata(llvm::CallBase *CallSite, QualType AllocatedTy, 557e5dd7070Spatrick SourceLocation Loc); 558e5dd7070Spatrick 559e5dd7070Spatrick void completeType(const EnumDecl *ED); 560e5dd7070Spatrick void completeType(const RecordDecl *RD); 561e5dd7070Spatrick void completeRequiredType(const RecordDecl *RD); 562e5dd7070Spatrick void completeClassData(const RecordDecl *RD); 563e5dd7070Spatrick void completeClass(const RecordDecl *RD); 564e5dd7070Spatrick 565e5dd7070Spatrick void completeTemplateDefinition(const ClassTemplateSpecializationDecl &SD); 566e5dd7070Spatrick void completeUnusedClass(const CXXRecordDecl &D); 567e5dd7070Spatrick 568e5dd7070Spatrick /// Create debug info for a macro defined by a #define directive or a macro 569e5dd7070Spatrick /// undefined by a #undef directive. 570e5dd7070Spatrick llvm::DIMacro *CreateMacro(llvm::DIMacroFile *Parent, unsigned MType, 571e5dd7070Spatrick SourceLocation LineLoc, StringRef Name, 572e5dd7070Spatrick StringRef Value); 573e5dd7070Spatrick 574e5dd7070Spatrick /// Create debug info for a file referenced by an #include directive. 575e5dd7070Spatrick llvm::DIMacroFile *CreateTempMacroFile(llvm::DIMacroFile *Parent, 576e5dd7070Spatrick SourceLocation LineLoc, 577e5dd7070Spatrick SourceLocation FileLoc); 578e5dd7070Spatrick getParamDbgMappings()579a9ac8606Spatrick Param2DILocTy &getParamDbgMappings() { return ParamDbgMappings; } getCoroutineParameterMappings()580a9ac8606Spatrick ParamDecl2StmtTy &getCoroutineParameterMappings() { 581a9ac8606Spatrick return CoroutineParameterMappings; 582a9ac8606Spatrick } 583a9ac8606Spatrick 584e5dd7070Spatrick private: 585e5dd7070Spatrick /// Emit call to llvm.dbg.declare for a variable declaration. 586e5dd7070Spatrick /// Returns a pointer to the DILocalVariable associated with the 587e5dd7070Spatrick /// llvm.dbg.declare, or nullptr otherwise. 588e5dd7070Spatrick llvm::DILocalVariable *EmitDeclare(const VarDecl *decl, llvm::Value *AI, 589*12c85518Srobert std::optional<unsigned> ArgNo, 590*12c85518Srobert CGBuilderTy &Builder, 591*12c85518Srobert const bool UsePointerValue = false); 592*12c85518Srobert 593*12c85518Srobert /// Emit call to llvm.dbg.declare for a binding declaration. 594*12c85518Srobert /// Returns a pointer to the DILocalVariable associated with the 595*12c85518Srobert /// llvm.dbg.declare, or nullptr otherwise. 596*12c85518Srobert llvm::DILocalVariable *EmitDeclare(const BindingDecl *decl, llvm::Value *AI, 597*12c85518Srobert std::optional<unsigned> ArgNo, 598e5dd7070Spatrick CGBuilderTy &Builder, 599e5dd7070Spatrick const bool UsePointerValue = false); 600e5dd7070Spatrick 601e5dd7070Spatrick struct BlockByRefType { 602e5dd7070Spatrick /// The wrapper struct used inside the __block_literal struct. 603e5dd7070Spatrick llvm::DIType *BlockByRefWrapper; 604e5dd7070Spatrick /// The type as it appears in the source code. 605e5dd7070Spatrick llvm::DIType *WrappedType; 606e5dd7070Spatrick }; 607e5dd7070Spatrick 608a9ac8606Spatrick std::string GetName(const Decl*, bool Qualified = false) const; 609a9ac8606Spatrick 610e5dd7070Spatrick /// Build up structure info for the byref. See \a BuildByRefType. 611e5dd7070Spatrick BlockByRefType EmitTypeForVarWithBlocksAttr(const VarDecl *VD, 612e5dd7070Spatrick uint64_t *OffSet); 613e5dd7070Spatrick 614e5dd7070Spatrick /// Get context info for the DeclContext of \p Decl. 615e5dd7070Spatrick llvm::DIScope *getDeclContextDescriptor(const Decl *D); 616e5dd7070Spatrick /// Get context info for a given DeclContext \p Decl. 617e5dd7070Spatrick llvm::DIScope *getContextDescriptor(const Decl *Context, 618e5dd7070Spatrick llvm::DIScope *Default); 619e5dd7070Spatrick 620e5dd7070Spatrick llvm::DIScope *getCurrentContextDescriptor(const Decl *Decl); 621e5dd7070Spatrick 622e5dd7070Spatrick /// Create a forward decl for a RecordType in a given context. 623e5dd7070Spatrick llvm::DICompositeType *getOrCreateRecordFwdDecl(const RecordType *, 624e5dd7070Spatrick llvm::DIScope *); 625e5dd7070Spatrick 626e5dd7070Spatrick /// Return current directory name. 627e5dd7070Spatrick StringRef getCurrentDirname(); 628e5dd7070Spatrick 629e5dd7070Spatrick /// Create new compile unit. 630e5dd7070Spatrick void CreateCompileUnit(); 631e5dd7070Spatrick 632e5dd7070Spatrick /// Compute the file checksum debug info for input file ID. 633*12c85518Srobert std::optional<llvm::DIFile::ChecksumKind> 634*12c85518Srobert computeChecksum(FileID FID, SmallString<64> &Checksum) const; 635e5dd7070Spatrick 636e5dd7070Spatrick /// Get the source of the given file ID. 637*12c85518Srobert std::optional<StringRef> getSource(const SourceManager &SM, FileID FID); 638e5dd7070Spatrick 639e5dd7070Spatrick /// Convenience function to get the file debug info descriptor for the input 640e5dd7070Spatrick /// location. 641e5dd7070Spatrick llvm::DIFile *getOrCreateFile(SourceLocation Loc); 642e5dd7070Spatrick 643e5dd7070Spatrick /// Create a file debug info descriptor for a source file. 644e5dd7070Spatrick llvm::DIFile * 645e5dd7070Spatrick createFile(StringRef FileName, 646*12c85518Srobert std::optional<llvm::DIFile::ChecksumInfo<StringRef>> CSInfo, 647*12c85518Srobert std::optional<StringRef> Source); 648e5dd7070Spatrick 649e5dd7070Spatrick /// Get the type from the cache or create a new type if necessary. 650e5dd7070Spatrick llvm::DIType *getOrCreateType(QualType Ty, llvm::DIFile *Fg); 651e5dd7070Spatrick 652e5dd7070Spatrick /// Get a reference to a clang module. If \p CreateSkeletonCU is true, 653e5dd7070Spatrick /// this also creates a split dwarf skeleton compile unit. 654ec727ea7Spatrick llvm::DIModule *getOrCreateModuleRef(ASTSourceDescriptor Mod, 655e5dd7070Spatrick bool CreateSkeletonCU); 656e5dd7070Spatrick 657e5dd7070Spatrick /// DebugTypeExtRefs: If \p D originated in a clang module, return it. 658e5dd7070Spatrick llvm::DIModule *getParentModuleOrNull(const Decl *D); 659e5dd7070Spatrick 660e5dd7070Spatrick /// Get the type from the cache or create a new partial type if 661e5dd7070Spatrick /// necessary. 662a9ac8606Spatrick llvm::DICompositeType *getOrCreateLimitedType(const RecordType *Ty); 663e5dd7070Spatrick 664e5dd7070Spatrick /// Create type metadata for a source language type. 665e5dd7070Spatrick llvm::DIType *CreateTypeNode(QualType Ty, llvm::DIFile *Fg); 666e5dd7070Spatrick 667e5dd7070Spatrick /// Create new member and increase Offset by FType's size. 668e5dd7070Spatrick llvm::DIType *CreateMemberType(llvm::DIFile *Unit, QualType FType, 669e5dd7070Spatrick StringRef Name, uint64_t *Offset); 670e5dd7070Spatrick 671e5dd7070Spatrick /// Retrieve the DIDescriptor, if any, for the canonical form of this 672e5dd7070Spatrick /// declaration. 673e5dd7070Spatrick llvm::DINode *getDeclarationOrDefinition(const Decl *D); 674e5dd7070Spatrick 675e5dd7070Spatrick /// \return debug info descriptor to describe method 676e5dd7070Spatrick /// declaration for the given method definition. 677e5dd7070Spatrick llvm::DISubprogram *getFunctionDeclaration(const Decl *D); 678e5dd7070Spatrick 679e5dd7070Spatrick /// \return debug info descriptor to the describe method declaration 680e5dd7070Spatrick /// for the given method definition. 681e5dd7070Spatrick /// \param FnType For Objective-C methods, their type. 682e5dd7070Spatrick /// \param LineNo The declaration's line number. 683e5dd7070Spatrick /// \param Flags The DIFlags for the method declaration. 684e5dd7070Spatrick /// \param SPFlags The subprogram-spcific flags for the method declaration. 685e5dd7070Spatrick llvm::DISubprogram * 686e5dd7070Spatrick getObjCMethodDeclaration(const Decl *D, llvm::DISubroutineType *FnType, 687e5dd7070Spatrick unsigned LineNo, llvm::DINode::DIFlags Flags, 688e5dd7070Spatrick llvm::DISubprogram::DISPFlags SPFlags); 689e5dd7070Spatrick 690e5dd7070Spatrick /// \return debug info descriptor to describe in-class static data 691e5dd7070Spatrick /// member declaration for the given out-of-class definition. If D 692e5dd7070Spatrick /// is an out-of-class definition of a static data member of a 693e5dd7070Spatrick /// class, find its corresponding in-class declaration. 694e5dd7070Spatrick llvm::DIDerivedType * 695e5dd7070Spatrick getOrCreateStaticDataMemberDeclarationOrNull(const VarDecl *D); 696e5dd7070Spatrick 697e5dd7070Spatrick /// Helper that either creates a forward declaration or a stub. 698e5dd7070Spatrick llvm::DISubprogram *getFunctionFwdDeclOrStub(GlobalDecl GD, bool Stub); 699e5dd7070Spatrick 700e5dd7070Spatrick /// Create a subprogram describing the forward declaration 701e5dd7070Spatrick /// represented in the given FunctionDecl wrapped in a GlobalDecl. 702e5dd7070Spatrick llvm::DISubprogram *getFunctionForwardDeclaration(GlobalDecl GD); 703e5dd7070Spatrick 704e5dd7070Spatrick /// Create a DISubprogram describing the function 705e5dd7070Spatrick /// represented in the given FunctionDecl wrapped in a GlobalDecl. 706e5dd7070Spatrick llvm::DISubprogram *getFunctionStub(GlobalDecl GD); 707e5dd7070Spatrick 708e5dd7070Spatrick /// Create a global variable describing the forward declaration 709e5dd7070Spatrick /// represented in the given VarDecl. 710e5dd7070Spatrick llvm::DIGlobalVariable * 711e5dd7070Spatrick getGlobalVariableForwardDeclaration(const VarDecl *VD); 712e5dd7070Spatrick 713e5dd7070Spatrick /// Return a global variable that represents one of the collection of global 714e5dd7070Spatrick /// variables created for an anonmyous union. 715e5dd7070Spatrick /// 716e5dd7070Spatrick /// Recursively collect all of the member fields of a global 717e5dd7070Spatrick /// anonymous decl and create static variables for them. The first 718e5dd7070Spatrick /// time this is called it needs to be on a union and then from 719e5dd7070Spatrick /// there we can have additional unnamed fields. 720e5dd7070Spatrick llvm::DIGlobalVariableExpression * 721e5dd7070Spatrick CollectAnonRecordDecls(const RecordDecl *RD, llvm::DIFile *Unit, 722e5dd7070Spatrick unsigned LineNo, StringRef LinkageName, 723e5dd7070Spatrick llvm::GlobalVariable *Var, llvm::DIScope *DContext); 724e5dd7070Spatrick 725e5dd7070Spatrick 726e5dd7070Spatrick /// Return flags which enable debug info emission for call sites, provided 727e5dd7070Spatrick /// that it is supported and enabled. 728e5dd7070Spatrick llvm::DINode::DIFlags getCallSiteRelatedAttrs() const; 729e5dd7070Spatrick 730e5dd7070Spatrick /// Get the printing policy for producing names for debug info. 731e5dd7070Spatrick PrintingPolicy getPrintingPolicy() const; 732e5dd7070Spatrick 733e5dd7070Spatrick /// Get function name for the given FunctionDecl. If the name is 734e5dd7070Spatrick /// constructed on demand (e.g., C++ destructor) then the name is 735e5dd7070Spatrick /// stored on the side. 736e5dd7070Spatrick StringRef getFunctionName(const FunctionDecl *FD); 737e5dd7070Spatrick 738e5dd7070Spatrick /// Returns the unmangled name of an Objective-C method. 739e5dd7070Spatrick /// This is the display name for the debugging info. 740e5dd7070Spatrick StringRef getObjCMethodName(const ObjCMethodDecl *FD); 741e5dd7070Spatrick 742e5dd7070Spatrick /// Return selector name. This is used for debugging 743e5dd7070Spatrick /// info. 744e5dd7070Spatrick StringRef getSelectorName(Selector S); 745e5dd7070Spatrick 746e5dd7070Spatrick /// Get class name including template argument list. 747e5dd7070Spatrick StringRef getClassName(const RecordDecl *RD); 748e5dd7070Spatrick 749e5dd7070Spatrick /// Get the vtable name for the given class. 750e5dd7070Spatrick StringRef getVTableName(const CXXRecordDecl *Decl); 751e5dd7070Spatrick 752e5dd7070Spatrick /// Get the name to use in the debug info for a dynamic initializer or atexit 753e5dd7070Spatrick /// stub function. 754e5dd7070Spatrick StringRef getDynamicInitializerName(const VarDecl *VD, 755e5dd7070Spatrick DynamicInitKind StubKind, 756e5dd7070Spatrick llvm::Function *InitFn); 757e5dd7070Spatrick 758e5dd7070Spatrick /// Get line number for the location. If location is invalid 759e5dd7070Spatrick /// then use current location. 760e5dd7070Spatrick unsigned getLineNumber(SourceLocation Loc); 761e5dd7070Spatrick 762e5dd7070Spatrick /// Get column number for the location. If location is 763e5dd7070Spatrick /// invalid then use current location. 764e5dd7070Spatrick /// \param Force Assume DebugColumnInfo option is true. 765e5dd7070Spatrick unsigned getColumnNumber(SourceLocation Loc, bool Force = false); 766e5dd7070Spatrick 767e5dd7070Spatrick /// Collect various properties of a FunctionDecl. 768e5dd7070Spatrick /// \param GD A GlobalDecl whose getDecl() must return a FunctionDecl. 769e5dd7070Spatrick void collectFunctionDeclProps(GlobalDecl GD, llvm::DIFile *Unit, 770e5dd7070Spatrick StringRef &Name, StringRef &LinkageName, 771e5dd7070Spatrick llvm::DIScope *&FDContext, 772e5dd7070Spatrick llvm::DINodeArray &TParamsArray, 773e5dd7070Spatrick llvm::DINode::DIFlags &Flags); 774e5dd7070Spatrick 775e5dd7070Spatrick /// Collect various properties of a VarDecl. 776e5dd7070Spatrick void collectVarDeclProps(const VarDecl *VD, llvm::DIFile *&Unit, 777e5dd7070Spatrick unsigned &LineNo, QualType &T, StringRef &Name, 778e5dd7070Spatrick StringRef &LinkageName, 779e5dd7070Spatrick llvm::MDTuple *&TemplateParameters, 780e5dd7070Spatrick llvm::DIScope *&VDContext); 781e5dd7070Spatrick 782e5dd7070Spatrick /// Allocate a copy of \p A using the DebugInfoNames allocator 783e5dd7070Spatrick /// and return a reference to it. If multiple arguments are given the strings 784e5dd7070Spatrick /// are concatenated. 785e5dd7070Spatrick StringRef internString(StringRef A, StringRef B = StringRef()) { 786e5dd7070Spatrick char *Data = DebugInfoNames.Allocate<char>(A.size() + B.size()); 787e5dd7070Spatrick if (!A.empty()) 788e5dd7070Spatrick std::memcpy(Data, A.data(), A.size()); 789e5dd7070Spatrick if (!B.empty()) 790e5dd7070Spatrick std::memcpy(Data + A.size(), B.data(), B.size()); 791e5dd7070Spatrick return StringRef(Data, A.size() + B.size()); 792e5dd7070Spatrick } 793e5dd7070Spatrick }; 794e5dd7070Spatrick 795e5dd7070Spatrick /// A scoped helper to set the current debug location to the specified 796e5dd7070Spatrick /// location or preferred location of the specified Expr. 797e5dd7070Spatrick class ApplyDebugLocation { 798e5dd7070Spatrick private: 799e5dd7070Spatrick void init(SourceLocation TemporaryLocation, bool DefaultToEmpty = false); 800e5dd7070Spatrick ApplyDebugLocation(CodeGenFunction &CGF, bool DefaultToEmpty, 801e5dd7070Spatrick SourceLocation TemporaryLocation); 802e5dd7070Spatrick 803e5dd7070Spatrick llvm::DebugLoc OriginalLocation; 804e5dd7070Spatrick CodeGenFunction *CGF; 805e5dd7070Spatrick 806e5dd7070Spatrick public: 807e5dd7070Spatrick /// Set the location to the (valid) TemporaryLocation. 808e5dd7070Spatrick ApplyDebugLocation(CodeGenFunction &CGF, SourceLocation TemporaryLocation); 809e5dd7070Spatrick ApplyDebugLocation(CodeGenFunction &CGF, const Expr *E); 810e5dd7070Spatrick ApplyDebugLocation(CodeGenFunction &CGF, llvm::DebugLoc Loc); ApplyDebugLocation(ApplyDebugLocation && Other)811e5dd7070Spatrick ApplyDebugLocation(ApplyDebugLocation &&Other) : CGF(Other.CGF) { 812e5dd7070Spatrick Other.CGF = nullptr; 813e5dd7070Spatrick } 814e5dd7070Spatrick ApplyDebugLocation &operator=(ApplyDebugLocation &&) = default; 815e5dd7070Spatrick 816e5dd7070Spatrick ~ApplyDebugLocation(); 817e5dd7070Spatrick 818e5dd7070Spatrick /// Apply TemporaryLocation if it is valid. Otherwise switch 819e5dd7070Spatrick /// to an artificial debug location that has a valid scope, but no 820e5dd7070Spatrick /// line information. 821e5dd7070Spatrick /// 822e5dd7070Spatrick /// Artificial locations are useful when emitting compiler-generated 823e5dd7070Spatrick /// helper functions that have no source location associated with 824e5dd7070Spatrick /// them. The DWARF specification allows the compiler to use the 825e5dd7070Spatrick /// special line number 0 to indicate code that can not be 826e5dd7070Spatrick /// attributed to any source location. Note that passing an empty 827e5dd7070Spatrick /// SourceLocation to CGDebugInfo::setLocation() will result in the 828e5dd7070Spatrick /// last valid location being reused. CreateArtificial(CodeGenFunction & CGF)829e5dd7070Spatrick static ApplyDebugLocation CreateArtificial(CodeGenFunction &CGF) { 830e5dd7070Spatrick return ApplyDebugLocation(CGF, false, SourceLocation()); 831e5dd7070Spatrick } 832e5dd7070Spatrick /// Apply TemporaryLocation if it is valid. Otherwise switch 833e5dd7070Spatrick /// to an artificial debug location that has a valid scope, but no 834e5dd7070Spatrick /// line information. 835e5dd7070Spatrick static ApplyDebugLocation CreateDefaultArtificial(CodeGenFunction & CGF,SourceLocation TemporaryLocation)836e5dd7070Spatrick CreateDefaultArtificial(CodeGenFunction &CGF, 837e5dd7070Spatrick SourceLocation TemporaryLocation) { 838e5dd7070Spatrick return ApplyDebugLocation(CGF, false, TemporaryLocation); 839e5dd7070Spatrick } 840e5dd7070Spatrick 841e5dd7070Spatrick /// Set the IRBuilder to not attach debug locations. Note that 842e5dd7070Spatrick /// passing an empty SourceLocation to \a CGDebugInfo::setLocation() 843e5dd7070Spatrick /// will result in the last valid location being reused. Note that 844e5dd7070Spatrick /// all instructions that do not have a location at the beginning of 845e5dd7070Spatrick /// a function are counted towards to function prologue. CreateEmpty(CodeGenFunction & CGF)846e5dd7070Spatrick static ApplyDebugLocation CreateEmpty(CodeGenFunction &CGF) { 847e5dd7070Spatrick return ApplyDebugLocation(CGF, true, SourceLocation()); 848e5dd7070Spatrick } 849e5dd7070Spatrick }; 850e5dd7070Spatrick 851e5dd7070Spatrick /// A scoped helper to set the current debug location to an inlined location. 852e5dd7070Spatrick class ApplyInlineDebugLocation { 853e5dd7070Spatrick SourceLocation SavedLocation; 854e5dd7070Spatrick CodeGenFunction *CGF; 855e5dd7070Spatrick 856e5dd7070Spatrick public: 857e5dd7070Spatrick /// Set up the CodeGenFunction's DebugInfo to produce inline locations for the 858e5dd7070Spatrick /// function \p InlinedFn. The current debug location becomes the inlined call 859e5dd7070Spatrick /// site of the inlined function. 860e5dd7070Spatrick ApplyInlineDebugLocation(CodeGenFunction &CGF, GlobalDecl InlinedFn); 861e5dd7070Spatrick /// Restore everything back to the original state. 862e5dd7070Spatrick ~ApplyInlineDebugLocation(); 863e5dd7070Spatrick }; 864e5dd7070Spatrick 865e5dd7070Spatrick } // namespace CodeGen 866e5dd7070Spatrick } // namespace clang 867e5dd7070Spatrick 868e5dd7070Spatrick #endif // LLVM_CLANG_LIB_CODEGEN_CGDEBUGINFO_H 869