41#include "llvm/ADT/DenseSet.h"
42#include "llvm/ADT/SmallVector.h"
43#include "llvm/ADT/StringExtras.h"
44#include "llvm/IR/Constants.h"
45#include "llvm/IR/DataLayout.h"
46#include "llvm/IR/DerivedTypes.h"
47#include "llvm/IR/Instruction.h"
48#include "llvm/IR/Instructions.h"
49#include "llvm/IR/Intrinsics.h"
50#include "llvm/IR/Metadata.h"
51#include "llvm/IR/Module.h"
52#include "llvm/Support/MD5.h"
53#include "llvm/Support/Path.h"
54#include "llvm/Support/SHA1.h"
55#include "llvm/Support/SHA256.h"
56#include "llvm/Support/TimeProfiler.h"
71 if (TI.isAlignRequired())
99 llvm::dyn_cast_or_null<DeclRefExpr>(
Init->IgnoreUnlessSpelledInSource());
103 return llvm::dyn_cast_or_null<DecompositionDecl>(RefExpr->getDecl());
127 if (!llvm::isa<ParmVarDecl>(VD))
137 if (!Method->isImplicit() || !Method->isPropertyAccessor())
148 : CGM(CGM), DebugKind(CGM.getCodeGenOpts().getDebugInfo()),
149 DebugTypeExtRefs(CGM.getCodeGenOpts().DebugTypeExtRefs),
150 DBuilder(CGM.getModule()) {
155 assert(LexicalBlockStack.empty() &&
156 "Region stack mismatch, stack not empty!");
159void CGDebugInfo::addInstSourceAtomMetadata(llvm::Instruction *I,
160 uint64_t Group, uint8_t Rank) {
161 if (!I->getDebugLoc() || Group == 0 || !I->getDebugLoc()->getLine())
165 Rank = std::min<uint8_t>(Rank, 7);
167 const llvm::DebugLoc &DL = I->getDebugLoc();
172 if (DL->getAtomGroup() && DL->getAtomRank() && DL->getAtomRank() < Rank) {
173 Group = DL->getAtomGroup();
174 Rank = DL->getAtomRank();
179 KeyInstructionsInfo.HighestEmittedAtom =
180 std::max(Group, KeyInstructionsInfo.HighestEmittedAtom);
183 llvm::DILocation *NewDL = llvm::DILocation::get(
184 I->getContext(), DL.getLine(), DL.getCol(), DL.getScope(),
185 DL.getInlinedAt(), DL.isImplicitCode(), Group, Rank);
186 I->setDebugLoc(NewDL);
190 llvm::Value *Backup) {
192 KeyInstructionsInfo.CurrentAtom);
198 if (!Group || !CGM.getCodeGenOpts().DebugKeyInstructions)
201 llvm::DISubprogram *SP = KeyInstruction->getFunction()->getSubprogram();
202 if (!SP || !SP->getKeyInstructionsEnabled())
205 addInstSourceAtomMetadata(KeyInstruction, Group, 1);
207 llvm::Instruction *BackupI =
208 llvm::dyn_cast_or_null<llvm::Instruction>(Backup);
213 addInstSourceAtomMetadata(BackupI, Group, 2);
219 while (
auto *Cast = dyn_cast<llvm::CastInst>(BackupI)) {
220 BackupI = dyn_cast<llvm::Instruction>(Cast->getOperand(0));
223 addInstSourceAtomMetadata(BackupI, Group, Rank++);
229 KeyInstructionsInfo.NextAtom = 1;
230 KeyInstructionsInfo.HighestEmittedAtom = 0;
231 KeyInstructionsInfo.CurrentAtom = 0;
237 OriginalAtom = DI->KeyInstructionsInfo.CurrentAtom;
238 DI->KeyInstructionsInfo.CurrentAtom = DI->KeyInstructionsInfo.NextAtom++;
246 DI->KeyInstructionsInfo.NextAtom =
247 std::min(DI->KeyInstructionsInfo.HighestEmittedAtom + 1,
248 DI->KeyInstructionsInfo.NextAtom);
250 DI->KeyInstructionsInfo.CurrentAtom = OriginalAtom;
256 init(TemporaryLocation);
263 init(TemporaryLocation, DefaultToEmpty);
267 bool DefaultToEmpty) {
274 OriginalLocation = CGF->
Builder.getCurrentDebugLocation();
276 if (OriginalLocation && !DI->CGM.getExpressionLocationsEnabled())
279 if (TemporaryLocation.
isValid()) {
280 DI->EmitLocation(CGF->
Builder, TemporaryLocation);
284 if (DefaultToEmpty) {
285 CGF->Builder.SetCurrentDebugLocation(llvm::DebugLoc());
290 assert(!DI->LexicalBlockStack.empty());
291 CGF->Builder.SetCurrentDebugLocation(
292 llvm::DILocation::get(DI->LexicalBlockStack.back()->getContext(), 0, 0,
293 DI->LexicalBlockStack.back(), DI->getInlinedAt()));
303 if (!CGF.getDebugInfo()) {
307 OriginalLocation = CGF.Builder.getCurrentDebugLocation();
311 if (Loc->getAtomGroup())
312 Loc = llvm::DILocation::get(Loc->getContext(), Loc.getLine(),
313 Loc->getColumn(), Loc->getScope(),
314 Loc->getInlinedAt(), Loc.isImplicitCode());
315 CGF.Builder.SetCurrentDebugLocation(std::move(Loc));
323 CGF->Builder.SetCurrentDebugLocation(std::move(OriginalLocation));
329 if (!CGF.getDebugInfo()) {
333 auto &DI = *CGF.getDebugInfo();
334 SavedLocation = DI.getLocation();
335 assert((DI.getInlinedAt() ==
336 CGF.Builder.getCurrentDebugLocation()->getInlinedAt()) &&
337 "CGDebugInfo and IRBuilder are out of sync");
339 DI.EmitInlineFunctionStart(CGF.Builder, InlinedFn);
345 auto &DI = *CGF->getDebugInfo();
346 DI.EmitInlineFunctionEnd(CGF->Builder);
347 DI.EmitLocation(CGF->Builder, SavedLocation);
357 if (CurLoc != NewLoc) {
359 CurLocFile =
nullptr;
368 if (CGM.getCodeGenOpts().DebugColumnInfo)
370 CurLocFile = getOrCreateFile(CurLoc);
376 if (LexicalBlockStack.empty())
380 if (!CurLocFile ||
Scope->getFile() == CurLocFile)
383 if (
auto *LBF = dyn_cast<llvm::DILexicalBlockFile>(
Scope)) {
384 LexicalBlockStack.pop_back();
385 LexicalBlockStack.emplace_back(
386 DBuilder.createLexicalBlockFile(LBF->getScope(), CurLocFile));
389 LexicalBlockStack.pop_back();
390 LexicalBlockStack.emplace_back(
391 DBuilder.createLexicalBlockFile(
Scope, CurLocFile));
395llvm::DIScope *CGDebugInfo::getDeclContextDescriptor(
const Decl *D) {
396 llvm::DIScope *Mod = getParentModuleOrNull(D);
401llvm::DIScope *CGDebugInfo::getContextDescriptor(
const Decl *Context,
406 auto I = RegionMap.find(Context);
407 if (I != RegionMap.end()) {
408 llvm::Metadata *
V = I->second;
409 return dyn_cast_or_null<llvm::DIScope>(
V);
413 if (
const auto *NSDecl = dyn_cast<NamespaceDecl>(Context))
414 return getOrCreateNamespace(NSDecl);
416 if (
const auto *RDecl = dyn_cast<RecordDecl>(Context))
417 if (!RDecl->isDependentType())
423PrintingPolicy CGDebugInfo::getPrintingPolicy()
const {
424 PrintingPolicy PP = CGM.getContext().getPrintingPolicy();
431 if (CGM.getCodeGenOpts().EmitCodeView) {
453StringRef CGDebugInfo::getFunctionName(
const FunctionDecl *FD,
454 bool *NameIsSimplified) {
455 return internString(GetName(FD,
false, NameIsSimplified));
458StringRef CGDebugInfo::getObjCMethodName(
const ObjCMethodDecl *OMD) {
459 SmallString<256> MethodName;
460 llvm::raw_svector_ostream
OS(MethodName);
463 if (
const auto *OID = dyn_cast<ObjCImplementationDecl>(DC)) {
464 OS << OID->getName();
465 }
else if (
const auto *OID = dyn_cast<ObjCInterfaceDecl>(DC)) {
466 OS << OID->getName();
467 }
else if (
const auto *OC = dyn_cast<ObjCCategoryDecl>(DC)) {
468 if (OC->IsClassExtension()) {
469 OS << OC->getClassInterface()->getName();
471 OS << OC->getIdentifier()->getNameStart() <<
'('
472 << OC->getIdentifier()->getNameStart() <<
')';
474 }
else if (
const auto *OCD = dyn_cast<ObjCCategoryImplDecl>(DC)) {
475 OS << OCD->getClassInterface()->getName() <<
'(' << OCD->getName() <<
')';
479 return internString(
OS.str());
482StringRef CGDebugInfo::getSelectorName(Selector S) {
486StringRef CGDebugInfo::getClassName(
const RecordDecl *RD,
487 bool *NameIsSimplified) {
490 return internString(GetName(RD,
false, NameIsSimplified));
496 return II->getName();
501 if (CGM.getCodeGenOpts().EmitCodeView) {
504 "Typedef should not be in another decl context!");
505 assert(D->getDeclName().getAsIdentifierInfo() &&
506 "Typedef was not named!");
507 return D->getDeclName().getAsIdentifierInfo()->getName();
510 if (CGM.getLangOpts().CPlusPlus) {
513 ASTContext &Context = CGM.getContext();
517 Name = DD->getName();
518 else if (
const TypedefNameDecl *TND =
522 Name = TND->getName();
525 if (
const CXXRecordDecl *CXXRD = dyn_cast<CXXRecordDecl>(RD))
526 if (CXXRD->isLambda())
528 CGM.getCXXABI().getMangleContext().getLambdaString(CXXRD));
531 SmallString<256> UnnamedType(
"<unnamed-type-");
534 return internString(UnnamedType);
542std::optional<llvm::DIFile::ChecksumKind>
543CGDebugInfo::computeChecksum(FileID FID, SmallString<64> &Checksum)
const {
546 if (!CGM.getCodeGenOpts().EmitCodeView &&
547 CGM.getCodeGenOpts().DwarfVersion < 5)
550 SourceManager &SM = CGM.getContext().getSourceManager();
551 std::optional<llvm::MemoryBufferRef> MemBuffer = SM.
getBufferOrNone(FID);
555 auto Data = llvm::arrayRefFromStringRef(MemBuffer->getBuffer());
556 switch (CGM.getCodeGenOpts().getDebugSrcHash()) {
558 llvm::toHex(llvm::MD5::hash(
Data),
true, Checksum);
559 return llvm::DIFile::CSK_MD5;
561 llvm::toHex(llvm::SHA1::hash(
Data),
true, Checksum);
562 return llvm::DIFile::CSK_SHA1;
564 llvm::toHex(llvm::SHA256::hash(
Data),
true, Checksum);
565 return llvm::DIFile::CSK_SHA256;
569 llvm_unreachable(
"Unhandled DebugSrcHashKind enum");
572std::optional<StringRef> CGDebugInfo::getSource(
const SourceManager &SM,
574 if (!CGM.getCodeGenOpts().EmbedSource)
577 bool SourceInvalid =
false;
586llvm::DIFile *CGDebugInfo::getOrCreateFile(SourceLocation Loc) {
587 SourceManager &SM = CGM.getContext().getSourceManager();
590 std::optional<llvm::DIFile::ChecksumInfo<StringRef>> CSInfo;
596 FileName = TheCU->getFile()->getFilename();
597 CSInfo = TheCU->getFile()->getChecksum();
600 if (Loc == CurLoc && CurLocFile)
607 FileName = TheCU->getFile()->getFilename();
615 auto It = DIFileCache.find(
FileName.data());
616 if (It != DIFileCache.end()) {
618 if (llvm::Metadata *
V = It->second)
623 SmallString<64> Checksum;
625 std::optional<llvm::DIFile::ChecksumKind> CSKind =
626 computeChecksum(FID, Checksum);
628 CSInfo.emplace(*CSKind, Checksum);
634llvm::DIFile *CGDebugInfo::createFile(
636 std::optional<llvm::DIFile::ChecksumInfo<StringRef>> CSInfo,
637 std::optional<StringRef> Source) {
641 std::string CurDir =
remapDIPath(getCurrentDirname());
642 SmallString<128> DirBuf;
643 SmallString<128> FileBuf;
644 if (llvm::sys::path::is_absolute(RemappedFile)) {
647 auto FileIt = llvm::sys::path::begin(RemappedFile);
648 auto FileE = llvm::sys::path::end(RemappedFile);
649 auto CurDirIt = llvm::sys::path::begin(CurDir);
650 auto CurDirE = llvm::sys::path::end(CurDir);
651 for (; CurDirIt != CurDirE && *CurDirIt == *FileIt; ++CurDirIt, ++FileIt)
652 llvm::sys::path::append(DirBuf, *CurDirIt);
653 if (llvm::sys::path::root_path(DirBuf) == DirBuf) {
659 for (; FileIt != FileE; ++FileIt)
660 llvm::sys::path::append(FileBuf, *FileIt);
665 if (!llvm::sys::path::is_absolute(
FileName))
669 llvm::DIFile *F = DBuilder.createFile(
File, Dir, CSInfo, Source);
670 DIFileCache[
FileName.data()].reset(F);
676 for (
auto &[From, To] : llvm::reverse(CGM.getCodeGenOpts().DebugPrefixMap))
677 if (llvm::sys::path::replace_path_prefix(P, From, To))
679 return P.str().str();
687 if (DebugLoc == CurLoc)
702 if (DebugLoc == CurLoc)
708StringRef CGDebugInfo::getCurrentDirname() {
716 assert(CGO.DwarfVersion <= 5);
718 llvm::dwarf::SourceLanguage LangTag;
721 LangTag = llvm::dwarf::DW_LANG_HLSL;
723 LangTag = llvm::dwarf::DW_LANG_HIP;
725 LangTag = llvm::dwarf::DW_LANG_ObjC_plus_plus;
726 else if (CGO.DebugStrictDwarf && CGO.DwarfVersion < 5)
727 LangTag = llvm::dwarf::DW_LANG_C_plus_plus;
728 else if (LO.CPlusPlus14)
729 LangTag = llvm::dwarf::DW_LANG_C_plus_plus_14;
730 else if (LO.CPlusPlus11)
731 LangTag = llvm::dwarf::DW_LANG_C_plus_plus_11;
733 LangTag = llvm::dwarf::DW_LANG_C_plus_plus;
734 }
else if (LO.ObjC) {
735 LangTag = llvm::dwarf::DW_LANG_ObjC;
736 }
else if (LO.OpenCL && (!CGO.DebugStrictDwarf || CGO.DwarfVersion >= 5)) {
737 LangTag = llvm::dwarf::DW_LANG_OpenCL;
738 }
else if (LO.C11 && !(CGO.DebugStrictDwarf && CGO.DwarfVersion < 5)) {
739 LangTag = llvm::dwarf::DW_LANG_C11;
741 LangTag = llvm::dwarf::DW_LANG_C99;
743 LangTag = llvm::dwarf::DW_LANG_C89;
749static llvm::DISourceLanguageName
758 llvm::dwarf::SourceLanguageName LangTag;
761 LangTag = llvm::dwarf::DW_LNAME_HLSL;
763 LangTag = llvm::dwarf::DW_LNAME_HIP;
764 }
else if (LO.ObjC) {
765 LangTag = llvm::dwarf::DW_LNAME_ObjC_plus_plus;
767 LangTag = llvm::dwarf::DW_LNAME_C_plus_plus;
770 }
else if (LO.ObjC) {
771 LangTag = llvm::dwarf::DW_LNAME_ObjC;
772 }
else if (LO.OpenCL) {
773 LangTag = llvm::dwarf::DW_LNAME_OpenCL_C;
775 LangTag = llvm::dwarf::DW_LNAME_C;
779 return llvm::DISourceLanguageName(LangTag, LangVersion);
782void CGDebugInfo::CreateCompileUnit() {
783 SmallString<64> Checksum;
784 std::optional<llvm::DIFile::ChecksumKind> CSKind;
785 std::optional<llvm::DIFile::ChecksumInfo<StringRef>> CSInfo;
795 SourceManager &SM = CGM.getContext().getSourceManager();
796 auto &CGO = CGM.getCodeGenOpts();
797 const LangOptions &LO = CGM.getLangOpts();
798 std::string MainFileName = CGO.MainFileName;
799 if (MainFileName.empty())
800 MainFileName =
"<stdin>";
806 std::string MainFileDir;
809 MainFileDir = std::string(MainFile->getDir().getName());
810 if (!llvm::sys::path::is_absolute(MainFileName)) {
811 llvm::SmallString<1024> MainFileDirSS(MainFileDir);
812 llvm::sys::path::Style Style =
814 ? (CGM.getTarget().
getTriple().isOSWindows()
815 ? llvm::sys::path::Style::windows_backslash
816 : llvm::sys::path::Style::posix)
817 : llvm::sys::path::Style::native;
818 llvm::sys::path::append(MainFileDirSS, Style, MainFileName);
819 MainFileName = std::string(
820 llvm::sys::path::remove_leading_dotslash(MainFileDirSS, Style));
827 if (MainFile->getName() == MainFileName &&
829 MainFile->getName().rsplit(
'.').second)
831 MainFileName = CGM.getModule().getName().str();
840 unsigned RuntimeVers = 0;
844 llvm::DICompileUnit::DebugEmissionKind EmissionKind;
846 case llvm::codegenoptions::NoDebugInfo:
847 case llvm::codegenoptions::LocTrackingOnly:
848 EmissionKind = llvm::DICompileUnit::NoDebug;
850 case llvm::codegenoptions::DebugLineTablesOnly:
851 EmissionKind = llvm::DICompileUnit::LineTablesOnly;
853 case llvm::codegenoptions::DebugDirectivesOnly:
854 EmissionKind = llvm::DICompileUnit::DebugDirectivesOnly;
856 case llvm::codegenoptions::DebugInfoConstructor:
857 case llvm::codegenoptions::LimitedDebugInfo:
858 case llvm::codegenoptions::FullDebugInfo:
859 case llvm::codegenoptions::UnusedTypeInfo:
860 EmissionKind = llvm::DICompileUnit::FullDebug;
865 auto &CGOpts = CGM.getCodeGenOpts();
871 CSInfo.emplace(*CSKind, Checksum);
872 llvm::DIFile *CUFile = DBuilder.createFile(
876 StringRef Sysroot, SDK;
877 if (CGM.getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::LLDB) {
878 StringRef FullSysroot = CGM.getHeaderSearchOpts().Sysroot;
879 if (CGM.getCodeGenOpts().DebugRecordSysroot)
880 Sysroot = FullSysroot;
881 auto B = llvm::sys::path::rbegin(FullSysroot);
882 auto E = llvm::sys::path::rend(FullSysroot);
884 std::find_if(B, E, [](
auto SDK) {
return SDK.ends_with(
".sdk"); });
889 llvm::DICompileUnit::DebugNameTableKind NameTableKind =
890 static_cast<llvm::DICompileUnit::DebugNameTableKind
>(
891 CGOpts.DebugNameTable);
892 if (CGM.getTarget().getTriple().isNVPTX())
893 NameTableKind = llvm::DICompileUnit::DebugNameTableKind::None;
894 else if (CGM.getTarget().getTriple().getVendor() == llvm::Triple::Apple)
895 NameTableKind = llvm::DICompileUnit::DebugNameTableKind::Apple;
898 TheCU = DBuilder.createCompileUnit(
900 CGOpts.EmitVersionIdentMetadata ? Producer :
"",
901 CGOpts.OptimizationLevel != 0 || CGOpts.PrepareForLTO ||
902 CGOpts.PrepareForThinLTO,
903 CGOpts.DwarfDebugFlags, RuntimeVers, CGOpts.SplitDwarfFile, EmissionKind,
904 DwoId, CGOpts.SplitDwarfInlining, CGOpts.DebugInfoForProfiling,
905 NameTableKind, CGOpts.DebugRangesBaseAddress,
remapDIPath(Sysroot), SDK);
908llvm::DIType *CGDebugInfo::CreateType(
const BuiltinType *BT) {
912#define BUILTIN_TYPE(Id, SingletonId)
913#define PLACEHOLDER_TYPE(Id, SingletonId) case BuiltinType::Id:
914#include "clang/AST/BuiltinTypes.def"
915 case BuiltinType::Dependent:
916 llvm_unreachable(
"Unexpected builtin type");
917 case BuiltinType::NullPtr:
918 return DBuilder.createNullPtrType();
919 case BuiltinType::Void:
921 case BuiltinType::ObjCClass:
924 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type,
925 "objc_class", TheCU, TheCU->getFile(), 0);
927 case BuiltinType::ObjCId: {
938 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type,
939 "objc_class", TheCU, TheCU->getFile(), 0);
941 unsigned Size = CGM.getContext().getTypeSize(CGM.getContext().VoidPtrTy);
943 auto *ISATy = DBuilder.createPointerType(ClassTy, Size);
945 ObjTy = DBuilder.createStructType(TheCU,
"objc_object", TheCU->getFile(), 0,
946 (uint64_t)0, 0, llvm::DINode::FlagZero,
947 nullptr, llvm::DINodeArray());
949 DBuilder.replaceArrays(
950 ObjTy, DBuilder.getOrCreateArray(&*DBuilder.createMemberType(
951 ObjTy,
"isa", TheCU->getFile(), 0, Size, 0, 0,
952 llvm::DINode::FlagZero, ISATy)));
955 case BuiltinType::ObjCSel: {
957 SelTy = DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type,
958 "objc_selector", TheCU,
959 TheCU->getFile(), 0);
963#define IMAGE_TYPE(ImgType, Id, SingletonId, Access, Suffix) \
964 case BuiltinType::Id: \
965 return getOrCreateStructPtrType("opencl_" #ImgType "_" #Suffix "_t", \
967#include "clang/Basic/OpenCLImageTypes.def"
968 case BuiltinType::OCLSampler:
969 return getOrCreateStructPtrType(
"opencl_sampler_t", OCLSamplerDITy);
970 case BuiltinType::OCLEvent:
971 return getOrCreateStructPtrType(
"opencl_event_t", OCLEventDITy);
972 case BuiltinType::OCLClkEvent:
973 return getOrCreateStructPtrType(
"opencl_clk_event_t", OCLClkEventDITy);
974 case BuiltinType::OCLQueue:
975 return getOrCreateStructPtrType(
"opencl_queue_t", OCLQueueDITy);
976 case BuiltinType::OCLReserveID:
977 return getOrCreateStructPtrType(
"opencl_reserve_id_t", OCLReserveIDDITy);
978#define EXT_OPAQUE_TYPE(ExtType, Id, Ext) \
979 case BuiltinType::Id: \
980 return getOrCreateStructPtrType("opencl_" #ExtType, Id##Ty);
981#include "clang/Basic/OpenCLExtensionTypes.def"
982#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) \
983 case BuiltinType::Id: \
984 return getOrCreateStructPtrType(#Name, SingletonId);
985#include "clang/Basic/HLSLIntangibleTypes.def"
987#define SVE_TYPE(Name, Id, SingletonId) case BuiltinType::Id:
988#include "clang/Basic/AArch64ACLETypes.def"
990 if (BT->
getKind() == BuiltinType::MFloat8) {
991 Encoding = llvm::dwarf::DW_ATE_unsigned_char;
992 BTName = BT->
getName(CGM.getLangOpts());
995 return DBuilder.createBasicType(BTName, Size, Encoding);
997 ASTContext::BuiltinVectorTypeInfo Info =
999 BT->
getKind() == BuiltinType::SveCount
1000 ? ASTContext::BuiltinVectorTypeInfo(
1001 CGM.getContext().BoolTy, llvm::ElementCount::getFixed(16),
1003 : CGM.getContext().getBuiltinVectorTypeInfo(BT);
1010 "Unsupported number of vectors for svcount_t");
1012 unsigned NumElems = Info.
EC.getKnownMinValue() * Info.
NumVectors;
1013 llvm::Metadata *BitStride =
nullptr;
1014 if (BT->
getKind() == BuiltinType::SveBool) {
1015 Info.
ElementType = CGM.getContext().UnsignedCharTy;
1016 BitStride = llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
1017 llvm::Type::getInt64Ty(CGM.getLLVMContext()), 1));
1018 }
else if (BT->
getKind() == BuiltinType::SveCount) {
1020 Info.
ElementType = CGM.getContext().UnsignedCharTy;
1023 llvm::Metadata *LowerBound, *UpperBound;
1024 LowerBound = llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
1025 llvm::Type::getInt64Ty(CGM.getLLVMContext()), 0));
1026 if (Info.
EC.isScalable()) {
1027 unsigned NumElemsPerVG = NumElems / 2;
1028 SmallVector<uint64_t, 9> Expr(
1029 {llvm::dwarf::DW_OP_constu, NumElemsPerVG, llvm::dwarf::DW_OP_bregx,
1030 46, 0, llvm::dwarf::DW_OP_mul,
1031 llvm::dwarf::DW_OP_constu, 1, llvm::dwarf::DW_OP_minus});
1032 UpperBound = DBuilder.createExpression(Expr);
1034 UpperBound = llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
1035 llvm::Type::getInt64Ty(CGM.getLLVMContext()), NumElems - 1));
1037 llvm::Metadata *Subscript = DBuilder.getOrCreateSubrange(
1038 nullptr, LowerBound, UpperBound,
nullptr);
1039 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscript);
1040 llvm::DIType *ElemTy =
1041 getOrCreateType(Info.
ElementType, TheCU->getFile());
1043 return DBuilder.createVectorType( 0, Align, ElemTy,
1044 SubscriptArray, BitStride);
1048#define PPC_VECTOR_TYPE(Name, Id, size) \
1049 case BuiltinType::Id:
1050#include "clang/Basic/PPCTypes.def"
1053#define RVV_TYPE(Name, Id, SingletonId) case BuiltinType::Id:
1054#include "clang/Basic/RISCVVTypes.def"
1056 ASTContext::BuiltinVectorTypeInfo Info =
1057 CGM.getContext().getBuiltinVectorTypeInfo(BT);
1059 unsigned ElementCount = Info.
EC.getKnownMinValue();
1060 unsigned SEW = CGM.getContext().getTypeSize(Info.
ElementType);
1062 bool Fractional =
false;
1065 unsigned FixedSize = ElementCount * SEW;
1066 if (Info.
ElementType == CGM.getContext().BoolTy) {
1069 }
else if (FixedSize < 64) {
1072 LMUL = 64 / FixedSize;
1074 LMUL = FixedSize / 64;
1078 SmallVector<uint64_t, 12> Expr(
1082 {llvm::dwarf::DW_OP_bregx,
1085 llvm::dwarf::DW_OP_constu,
1087 llvm::dwarf::DW_OP_div, llvm::dwarf::DW_OP_constu, LMUL});
1089 Expr.push_back(llvm::dwarf::DW_OP_div);
1091 Expr.push_back(llvm::dwarf::DW_OP_mul);
1094 Expr.append({llvm::dwarf::DW_OP_constu, NFIELDS, llvm::dwarf::DW_OP_mul});
1096 Expr.append({llvm::dwarf::DW_OP_constu, 1, llvm::dwarf::DW_OP_minus});
1099 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
1100 llvm::Type::getInt64Ty(CGM.getLLVMContext()), 0));
1101 auto *UpperBound = DBuilder.createExpression(Expr);
1102 llvm::Metadata *Subscript = DBuilder.getOrCreateSubrange(
1103 nullptr, LowerBound, UpperBound,
nullptr);
1104 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscript);
1105 llvm::DIType *ElemTy =
1106 getOrCreateType(Info.
ElementType, TheCU->getFile());
1109 return DBuilder.createVectorType(0, Align, ElemTy,
1113#define WASM_REF_TYPE(Name, MangledName, Id, SingletonId, AS) \
1114 case BuiltinType::Id: { \
1117 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type, \
1118 MangledName, TheCU, TheCU->getFile(), 0); \
1119 return SingletonId; \
1121#include "clang/Basic/WebAssemblyReferenceTypes.def"
1122#define AMDGPU_OPAQUE_PTR_TYPE(Name, Id, SingletonId, Width, Align, AS) \
1123 case BuiltinType::Id: { \
1126 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type, Name, \
1127 TheCU, TheCU->getFile(), 0); \
1128 return SingletonId; \
1130#define AMDGPU_NAMED_BARRIER_TYPE(Name, Id, SingletonId, Width, Align, Scope) \
1131 case BuiltinType::Id: { \
1134 DBuilder.createBasicType(Name, Width, llvm::dwarf::DW_ATE_unsigned); \
1135 return SingletonId; \
1137#define AMDGPU_FEATURE_PREDICATE_TYPE(Name, Id, SingletonId, Width, Align) \
1138 case BuiltinType::Id: { \
1141 DBuilder.createBasicType(Name, Width, llvm::dwarf::DW_ATE_boolean); \
1142 return SingletonId; \
1144#include "clang/Basic/AMDGPUTypes.def"
1145#define SPIRV_TYPE(Name, Id, SingletonId) \
1146 case BuiltinType::Id: \
1147 return getOrCreateStructPtrType(Name, SingletonId);
1148#include "clang/Basic/SPIRVTypes.def"
1149 case BuiltinType::UChar:
1150 case BuiltinType::Char_U:
1151 Encoding = llvm::dwarf::DW_ATE_unsigned_char;
1153 case BuiltinType::Char_S:
1154 case BuiltinType::SChar:
1155 Encoding = llvm::dwarf::DW_ATE_signed_char;
1157 case BuiltinType::Char8:
1158 case BuiltinType::Char16:
1159 case BuiltinType::Char32:
1160 Encoding = llvm::dwarf::DW_ATE_UTF;
1162 case BuiltinType::UShort:
1163 case BuiltinType::UInt:
1164 case BuiltinType::UInt128:
1165 case BuiltinType::ULong:
1166 case BuiltinType::WChar_U:
1167 case BuiltinType::ULongLong:
1168 Encoding = llvm::dwarf::DW_ATE_unsigned;
1170 case BuiltinType::Short:
1171 case BuiltinType::Int:
1172 case BuiltinType::Int128:
1173 case BuiltinType::Long:
1174 case BuiltinType::WChar_S:
1175 case BuiltinType::LongLong:
1176 Encoding = llvm::dwarf::DW_ATE_signed;
1178 case BuiltinType::Bool:
1179 Encoding = llvm::dwarf::DW_ATE_boolean;
1181 case BuiltinType::Half:
1182 case BuiltinType::Float:
1183 case BuiltinType::LongDouble:
1184 case BuiltinType::Float16:
1185 case BuiltinType::BFloat16:
1186 case BuiltinType::Float128:
1187 case BuiltinType::Double:
1188 case BuiltinType::Ibm128:
1194 Encoding = llvm::dwarf::DW_ATE_float;
1196 case BuiltinType::ShortAccum:
1197 case BuiltinType::Accum:
1198 case BuiltinType::LongAccum:
1199 case BuiltinType::ShortFract:
1200 case BuiltinType::Fract:
1201 case BuiltinType::LongFract:
1202 case BuiltinType::SatShortFract:
1203 case BuiltinType::SatFract:
1204 case BuiltinType::SatLongFract:
1205 case BuiltinType::SatShortAccum:
1206 case BuiltinType::SatAccum:
1207 case BuiltinType::SatLongAccum:
1208 Encoding = llvm::dwarf::DW_ATE_signed_fixed;
1210 case BuiltinType::UShortAccum:
1211 case BuiltinType::UAccum:
1212 case BuiltinType::ULongAccum:
1213 case BuiltinType::UShortFract:
1214 case BuiltinType::UFract:
1215 case BuiltinType::ULongFract:
1216 case BuiltinType::SatUShortAccum:
1217 case BuiltinType::SatUAccum:
1218 case BuiltinType::SatULongAccum:
1219 case BuiltinType::SatUShortFract:
1220 case BuiltinType::SatUFract:
1221 case BuiltinType::SatULongFract:
1222 Encoding = llvm::dwarf::DW_ATE_unsigned_fixed;
1226 BTName = BT->
getName(CGM.getLangOpts());
1229 return DBuilder.createBasicType(BTName, Size, Encoding);
1232llvm::DIType *CGDebugInfo::CreateType(
const BitIntType *Ty) {
1233 SmallString<32> Name;
1234 llvm::raw_svector_ostream
OS(Name);
1235 OS << (Ty->
isUnsigned() ?
"unsigned _BitInt(" :
"_BitInt(")
1238 ? llvm::dwarf::DW_ATE_unsigned
1239 : llvm::dwarf::DW_ATE_signed;
1240 return DBuilder.createBasicType(Name, CGM.getContext().getTypeSize(Ty),
1241 Encoding, llvm::DINode::FlagZero, 0,
1245llvm::DIType *CGDebugInfo::CreateType(
const OverflowBehaviorType *Ty,
1247 return getOrCreateType(Ty->getUnderlyingType(), U);
1250llvm::DIType *CGDebugInfo::CreateType(
const ComplexType *Ty) {
1252 llvm::dwarf::TypeKind
Encoding = llvm::dwarf::DW_ATE_complex_float;
1254 Encoding = llvm::dwarf::DW_ATE_lo_user;
1257 return DBuilder.createBasicType(
"complex", Size, Encoding);
1271 return llvm::dwarf::DW_TAG_const_type;
1275 return llvm::dwarf::DW_TAG_volatile_type;
1279 return llvm::dwarf::DW_TAG_restrict_type;
1281 return (llvm::dwarf::Tag)0;
1284llvm::DIType *CGDebugInfo::CreateQualifiedType(QualType Ty,
1285 llvm::DIFile *Unit) {
1286 QualifierCollector Qc;
1300 bool AuthenticatesNullValues =
1303 assert(Qc.
empty() &&
"Unknown type qualifier for debug info");
1304 llvm::DIType *FromTy = getOrCreateType(QualType(
T, 0), Unit);
1305 return DBuilder.createPtrAuthQualifiedType(FromTy, Key, IsDiscr,
1306 ExtraDiscr, IsaPointer,
1307 AuthenticatesNullValues);
1309 assert(Qc.
empty() &&
"Unknown type qualifier for debug info");
1310 return getOrCreateType(QualType(
T, 0), Unit);
1314 auto *FromTy = getOrCreateType(Qc.
apply(CGM.getContext(),
T), Unit);
1318 return DBuilder.createQualifiedType(Tag, FromTy);
1321llvm::DIType *CGDebugInfo::CreateQualifiedType(
const FunctionProtoType *F,
1322 llvm::DIFile *Unit) {
1331 assert(Q.
empty() &&
"Unknown type qualifier for debug info");
1336 getOrCreateType(CGM.getContext().getFunctionType(F->
getReturnType(),
1342 return DBuilder.createQualifiedType(Tag, FromTy);
1345llvm::DIType *CGDebugInfo::CreateType(
const ObjCObjectPointerType *Ty,
1346 llvm::DIFile *Unit) {
1352 return getOrCreateType(CGM.getContext().getObjCIdType(), Unit);
1354 return CreatePointerLikeType(llvm::dwarf::DW_TAG_pointer_type, Ty,
1358llvm::DIType *CGDebugInfo::CreateType(
const PointerType *Ty,
1359 llvm::DIFile *Unit) {
1360 return CreatePointerLikeType(llvm::dwarf::DW_TAG_pointer_type, Ty,
1366 case llvm::dwarf::DW_LANG_C_plus_plus:
1367 case llvm::dwarf::DW_LANG_C_plus_plus_11:
1368 case llvm::dwarf::DW_LANG_C_plus_plus_14:
1369 case llvm::dwarf::DW_LANG_HIP:
1371 case llvm::dwarf::DW_LANG_ObjC_plus_plus:
1381 case llvm::dwarf::DW_LNAME_C_plus_plus:
1382 case llvm::dwarf::DW_LNAME_HIP:
1384 case llvm::dwarf::DW_LNAME_ObjC_plus_plus:
1395 if (llvm::DISourceLanguageName SourceLang = TheCU->getSourceLanguage();
1396 SourceLang.hasVersionedName())
1398 static_cast<llvm::dwarf::SourceLanguageName
>(SourceLang.getName()),
1402 static_cast<llvm::dwarf::SourceLanguage
>(SourceLang.getName()),
1428 llvm::DICompileUnit *TheCU) {
1446 llvm::DICompileUnit *TheCU) {
1452 if (
const auto *RD = dyn_cast<CXXRecordDecl>(TD))
1454 if (RD->isDynamicClass() &&
1460 llvm::raw_svector_ostream Out(Identifier);
1467 llvm::dwarf::Tag Tag;
1469 Tag = llvm::dwarf::DW_TAG_structure_type;
1471 Tag = llvm::dwarf::DW_TAG_union_type;
1476 Tag = llvm::dwarf::DW_TAG_class_type;
1481llvm::DICompositeType *
1482CGDebugInfo::getOrCreateRecordFwdDecl(
const RecordType *Ty,
1483 llvm::DIScope *Ctx) {
1485 if (llvm::DIType *
T = getTypeOrNull(QualType(Ty, 0)))
1487 llvm::DIFile *DefUnit = getOrCreateFile(RD->
getLocation());
1488 const unsigned Line =
1490 StringRef RDName = getClassName(RD);
1497 Size = CGM.getContext().getTypeSize(Ty);
1499 llvm::DINode::DIFlags Flags = llvm::DINode::FlagFwdDecl;
1504 if (
const CXXRecordDecl *CXXRD = dyn_cast<CXXRecordDecl>(RD))
1505 if (!CXXRD->hasDefinition() ||
1506 (CXXRD->hasDefinition() && !CXXRD->isTrivial()))
1507 Flags |= llvm::DINode::FlagNonTrivial;
1510 SmallString<256> Identifier;
1512 if (CGM.getCodeGenOpts().hasReducedDebugInfo())
1514 llvm::DICompositeType *RetTy = DBuilder.createReplaceableCompositeType(
1517 if (CGM.getCodeGenOpts().DebugFwdTemplateParams)
1518 if (
auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD))
1519 DBuilder.replaceArrays(RetTy, llvm::DINodeArray(),
1520 CollectCXXTemplateParams(TSpecial, DefUnit));
1521 ReplaceMap.emplace_back(
1522 std::piecewise_construct, std::make_tuple(Ty),
1523 std::make_tuple(
static_cast<llvm::Metadata *
>(RetTy)));
1527llvm::DIType *CGDebugInfo::CreatePointerLikeType(llvm::dwarf::Tag Tag,
1530 llvm::DIFile *Unit) {
1535 std::optional<unsigned> DWARFAddressSpace =
1536 CGM.getTarget().getDWARFAddressSpace(
1537 CGM.getTypes().getTargetAddressSpace(PointeeTy));
1539 if (Tag == llvm::dwarf::DW_TAG_reference_type ||
1540 Tag == llvm::dwarf::DW_TAG_rvalue_reference_type) {
1541 return DBuilder.createReferenceType(Tag, getOrCreateType(PointeeTy, Unit),
1542 Size, Align, DWARFAddressSpace);
1544 SmallVector<llvm::Metadata *, 4> Annots;
1545 CollectBTFTypeTagAnnotations(PointeeTy, Annots);
1547 llvm::DINodeArray Annotations =
nullptr;
1548 if (Annots.size() > 0)
1549 Annotations = DBuilder.getOrCreateArray(Annots);
1550 return DBuilder.createPointerType(getOrCreateType(PointeeTy, Unit), Size,
1551 Align, DWARFAddressSpace, StringRef(),
1556llvm::DIType *CGDebugInfo::getOrCreateStructPtrType(StringRef Name,
1557 llvm::DIType *&
Cache) {
1560 Cache = DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type, Name,
1561 TheCU, TheCU->getFile(), 0);
1562 unsigned Size = CGM.getContext().getTypeSize(CGM.getContext().VoidPtrTy);
1563 Cache = DBuilder.createPointerType(
Cache, Size);
1567uint64_t CGDebugInfo::collectDefaultElementTypesForBlockPointer(
1568 const BlockPointerType *Ty, llvm::DIFile *Unit, llvm::DIDerivedType *DescTy,
1569 unsigned LineNo, SmallVectorImpl<llvm::Metadata *> &EltTys) {
1579 if (CGM.getLangOpts().OpenCL) {
1580 FType = CGM.getContext().IntTy;
1581 EltTys.push_back(CreateMemberType(Unit, FType,
"__size", &FieldOffset));
1582 EltTys.push_back(CreateMemberType(Unit, FType,
"__align", &FieldOffset));
1584 FType = CGM.getContext().getPointerType(CGM.getContext().VoidTy);
1585 EltTys.push_back(CreateMemberType(Unit, FType,
"__isa", &FieldOffset));
1586 FType = CGM.getContext().IntTy;
1587 EltTys.push_back(CreateMemberType(Unit, FType,
"__flags", &FieldOffset));
1588 EltTys.push_back(CreateMemberType(Unit, FType,
"__reserved", &FieldOffset));
1590 EltTys.push_back(CreateMemberType(Unit, FType,
"__FuncPtr", &FieldOffset));
1591 FType = CGM.getContext().getPointerType(CGM.getContext().VoidTy);
1592 uint64_t FieldSize = CGM.getContext().getTypeSize(Ty);
1593 uint32_t FieldAlign = CGM.getContext().getTypeAlign(Ty);
1594 EltTys.push_back(DBuilder.createMemberType(
1595 Unit,
"__descriptor",
nullptr, LineNo, FieldSize, FieldAlign,
1596 FieldOffset, llvm::DINode::FlagZero, DescTy));
1597 FieldOffset += FieldSize;
1603llvm::DIType *CGDebugInfo::CreateType(
const BlockPointerType *Ty,
1604 llvm::DIFile *Unit) {
1605 SmallVector<llvm::Metadata *, 8> EltTys;
1608 llvm::DINodeArray Elements;
1611 FType = CGM.getContext().UnsignedLongTy;
1612 EltTys.push_back(CreateMemberType(Unit, FType,
"reserved", &FieldOffset));
1613 EltTys.push_back(CreateMemberType(Unit, FType,
"Size", &FieldOffset));
1615 Elements = DBuilder.getOrCreateArray(EltTys);
1618 llvm::DINode::DIFlags Flags = llvm::DINode::FlagAppleBlock;
1621 DBuilder.createStructType(Unit,
"__block_descriptor",
nullptr, 0,
1622 FieldOffset, 0, Flags,
nullptr, Elements);
1627 auto *DescTy = DBuilder.createPointerType(EltTy, Size);
1629 FieldOffset = collectDefaultElementTypesForBlockPointer(Ty, Unit, DescTy,
1632 Elements = DBuilder.getOrCreateArray(EltTys);
1638 EltTy = DBuilder.createStructType(Unit,
"",
nullptr, 0, FieldOffset, 0,
1639 Flags,
nullptr, Elements);
1641 return DBuilder.createPointerType(EltTy, Size);
1644static llvm::SmallVector<TemplateArgument>
1646 assert(Ty->isTypeAlias());
1655 ArrayRef SubstArgs = Ty->template_arguments();
1658 if (Param->isParameterPack()) {
1667 if (SubstArgs.empty()) {
1676 SpecArgs.push_back(SubstArgs.front());
1677 SubstArgs = SubstArgs.drop_front();
1682llvm::DIType *CGDebugInfo::CreateType(
const TemplateSpecializationType *Ty,
1683 llvm::DIFile *Unit) {
1684 assert(Ty->isTypeAlias());
1685 llvm::DIType *Src = getOrCreateType(Ty->getAliasedType(), Unit);
1687 const TemplateDecl *TD = Ty->getTemplateName().getAsTemplateDecl();
1695 SmallString<128> NS;
1696 llvm::raw_svector_ostream
OS(NS);
1698 auto PP = getPrintingPolicy();
1701 SourceLocation Loc =
AliasDecl->getLocation();
1703 if (CGM.getCodeGenOpts().DebugTemplateAlias) {
1704 auto ArgVector = ::GetTemplateArgs(TD, Ty);
1713 llvm::raw_string_ostream
OS(Name);
1715 if (CGM.getCodeGenOpts().getDebugSimpleTemplateNames() !=
1716 llvm::codegenoptions::DebugTemplateNamesKind::Simple ||
1717 !HasReconstitutableArgs(Args.Args))
1718 printTemplateArgumentList(OS, Args.Args, PP);
1720 llvm::DIDerivedType *AliasTy = DBuilder.createTemplateAlias(
1721 Src, Name, getOrCreateFile(Loc), getLineNumber(Loc),
1722 getDeclContextDescriptor(
AliasDecl), CollectTemplateParams(Args, Unit));
1726 printTemplateArgumentList(OS, Ty->template_arguments(), PP,
1728 return DBuilder.createTypedef(Src,
OS.str(), getOrCreateFile(Loc),
1745 return llvm::DINode::FlagZero;
1749 return llvm::DINode::FlagPrivate;
1751 return llvm::DINode::FlagProtected;
1753 return llvm::DINode::FlagPublic;
1755 return llvm::DINode::FlagZero;
1757 llvm_unreachable(
"unexpected access enumerator");
1760llvm::DIType *CGDebugInfo::CreateType(
const TypedefType *Ty,
1761 llvm::DIFile *Unit) {
1762 llvm::DIType *Underlying =
1778 SmallVector<llvm::Metadata *, 4> Annots;
1779 llvm::DINodeArray Annotations;
1781 CollectBTFDeclTagAnnotations(Ty->
getDecl(), Annots);
1782 if (!Annots.empty())
1783 Annotations = DBuilder.getOrCreateArray(Annots);
1785 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
1790 return DBuilder.createTypedef(Underlying, Ty->
getDecl()->
getName(),
1791 getOrCreateFile(Loc), getLineNumber(Loc),
1792 getDeclContextDescriptor(Ty->
getDecl()), Align,
1793 Flags, Annotations);
1801 if (
T.isSPIROrSPIRV())
1802 return llvm::dwarf::DW_CC_LLVM_SpirFunction;
1807 return llvm::dwarf::DW_CC_BORLAND_stdcall;
1809 return llvm::dwarf::DW_CC_BORLAND_msfastcall;
1811 return llvm::dwarf::DW_CC_BORLAND_thiscall;
1813 return llvm::dwarf::DW_CC_LLVM_vectorcall;
1815 return llvm::dwarf::DW_CC_BORLAND_pascal;
1817 return llvm::dwarf::DW_CC_LLVM_Win64;
1819 return llvm::dwarf::DW_CC_LLVM_X86_64SysV;
1823 return llvm::dwarf::DW_CC_LLVM_AAPCS;
1825 return llvm::dwarf::DW_CC_LLVM_AAPCS_VFP;
1827 return llvm::dwarf::DW_CC_LLVM_IntelOclBicc;
1829 return llvm::dwarf::DW_CC_LLVM_SpirFunction;
1831 return llvm::dwarf::DW_CC_LLVM_DeviceKernel;
1833 return llvm::dwarf::DW_CC_LLVM_Swift;
1835 return llvm::dwarf::DW_CC_LLVM_SwiftTail;
1837 return llvm::dwarf::DW_CC_LLVM_PreserveMost;
1839 return llvm::dwarf::DW_CC_LLVM_PreserveAll;
1841 return llvm::dwarf::DW_CC_LLVM_X86RegCall;
1843 return llvm::dwarf::DW_CC_LLVM_M68kRTD;
1845 return llvm::dwarf::DW_CC_LLVM_PreserveNone;
1847 return llvm::dwarf::DW_CC_LLVM_RISCVVectorCall;
1848#define CC_VLS_CASE(ABI_VLEN) case CC_RISCVVLSCall_##ABI_VLEN:
1862 return llvm::dwarf::DW_CC_LLVM_RISCVVLSCall;
1868 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
1870 Flags |= llvm::DINode::FlagLValueReference;
1872 Flags |= llvm::DINode::FlagRValueReference;
1876llvm::DIType *CGDebugInfo::CreateType(
const FunctionType *Ty,
1877 llvm::DIFile *Unit) {
1878 const auto *FPT = dyn_cast<FunctionProtoType>(Ty);
1880 if (llvm::DIType *QTy = CreateQualifiedType(FPT, Unit))
1886 SmallVector<llvm::Metadata *, 16> EltTys;
1889 EltTys.push_back(getOrCreateType(Ty->
getReturnType(), Unit));
1891 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
1895 EltTys.push_back(DBuilder.createUnspecifiedParameter());
1898 for (
const QualType &ParamType : FPT->param_types())
1899 EltTys.push_back(getOrCreateType(ParamType, Unit));
1900 if (FPT->isVariadic())
1901 EltTys.push_back(DBuilder.createUnspecifiedParameter());
1904 llvm::DITypeArray EltTypeArray = DBuilder.getOrCreateTypeArray(EltTys);
1905 llvm::DIType *F = DBuilder.createSubroutineType(
1906 EltTypeArray, Flags,
1911llvm::DIDerivedType *
1912CGDebugInfo::createBitFieldType(
const FieldDecl *BitFieldDecl,
1913 llvm::DIScope *RecordTy,
const RecordDecl *RD) {
1914 StringRef Name = BitFieldDecl->
getName();
1915 QualType Ty = BitFieldDecl->
getType();
1916 if (BitFieldDecl->
hasAttr<PreferredTypeAttr>())
1919 llvm::DIFile *VUnit = getOrCreateFile(Loc);
1920 llvm::DIType *DebugType = getOrCreateType(Ty, VUnit);
1923 llvm::DIFile *
File = getOrCreateFile(Loc);
1924 unsigned Line = getLineNumber(Loc);
1926 const CGBitFieldInfo &BitFieldInfo =
1927 CGM.getTypes().getCGRecordLayout(RD).getBitFieldInfo(BitFieldDecl);
1929 assert(SizeInBits > 0 &&
"found named 0-width bitfield");
1936 if (CGM.getDataLayout().isBigEndian())
1938 uint64_t OffsetInBits = StorageOffsetInBits + Offset;
1940 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(BitFieldDecl);
1941 return DBuilder.createBitFieldMemberType(
1942 RecordTy, Name,
File,
Line, SizeInBits, OffsetInBits, StorageOffsetInBits,
1943 Flags, DebugType, Annotations);
1946llvm::DIDerivedType *CGDebugInfo::createBitFieldSeparatorIfNeeded(
1947 const FieldDecl *BitFieldDecl,
const llvm::DIDerivedType *BitFieldDI,
1948 llvm::ArrayRef<llvm::Metadata *> PreviousFieldsDI,
const RecordDecl *RD) {
1950 if (!CGM.getTargetCodeGenInfo().shouldEmitDWARFBitFieldSeparators())
1975 if (PreviousFieldsDI.empty())
1979 auto *PreviousMDEntry =
1980 PreviousFieldsDI.empty() ?
nullptr : PreviousFieldsDI.back();
1981 auto *PreviousMDField =
1982 dyn_cast_or_null<llvm::DIDerivedType>(PreviousMDEntry);
1983 if (!PreviousMDField || !PreviousMDField->isBitField() ||
1984 PreviousMDField->getSizeInBits() == 0)
1988 std::advance(PreviousBitfield, BitFieldDecl->
getFieldIndex() - 1);
1990 assert(PreviousBitfield->isBitField());
1992 if (!PreviousBitfield->isZeroLengthBitField())
1995 QualType Ty = PreviousBitfield->getType();
1996 SourceLocation Loc = PreviousBitfield->getLocation();
1997 llvm::DIFile *VUnit = getOrCreateFile(Loc);
1998 llvm::DIType *DebugType = getOrCreateType(Ty, VUnit);
1999 llvm::DIScope *RecordTy = BitFieldDI->getScope();
2001 llvm::DIFile *
File = getOrCreateFile(Loc);
2002 unsigned Line = getLineNumber(Loc);
2008 llvm::DINode::DIFlags Flags =
2010 llvm::DINodeArray Annotations =
2011 CollectBTFDeclTagAnnotations(*PreviousBitfield);
2012 return DBuilder.createBitFieldMemberType(
2013 RecordTy,
"",
File,
Line, 0, StorageOffsetInBits, StorageOffsetInBits,
2014 Flags, DebugType, Annotations);
2017llvm::DIType *CGDebugInfo::createFieldType(
2019 uint64_t offsetInBits,
uint32_t AlignInBits, llvm::DIFile *tunit,
2020 llvm::DIScope *scope,
const RecordDecl *RD, llvm::DINodeArray Annotations) {
2021 llvm::DIType *debugType = getOrCreateType(
type, tunit);
2024 llvm::DIFile *file = getOrCreateFile(loc);
2025 const unsigned line = getLineNumber(loc.
isValid() ? loc : CurLoc);
2028 auto Align = AlignInBits;
2029 if (!
type->isIncompleteArrayType()) {
2030 TypeInfo TI = CGM.getContext().getTypeInfo(
type);
2031 SizeInBits = TI.
Width;
2037 return DBuilder.createMemberType(scope, name, file, line, SizeInBits, Align,
2038 offsetInBits, flags, debugType, Annotations);
2042CGDebugInfo::createInlinedSubprogram(StringRef FuncName,
2043 llvm::DIFile *FileScope) {
2047 llvm::DISubprogram *&SP = InlinedSubprogramMap[FuncName];
2050 llvm::DISubroutineType *DIFnTy = DBuilder.createSubroutineType(
nullptr);
2051 SP = DBuilder.createFunction(
2052 FileScope, FuncName, StringRef(),
2053 FileScope, 0, DIFnTy,
2055 llvm::DINode::FlagArtificial,
2056 llvm::DISubprogram::SPFlagDefinition,
2057 nullptr,
nullptr,
nullptr,
2058 nullptr, StringRef(),
2059 CGM.getCodeGenOpts().DebugKeyInstructions);
2066CGDebugInfo::GetLambdaCaptureName(
const LambdaCapture &
Capture) {
2068 return CGM.getCodeGenOpts().EmitCodeView ?
"__this" :
"this";
2070 assert(
Capture.capturesVariable());
2072 const ValueDecl *CaptureDecl =
Capture.getCapturedVar();
2073 assert(CaptureDecl &&
"Expected valid decl for captured variable.");
2075 return CaptureDecl->
getName();
2078void CGDebugInfo::CollectRecordLambdaFields(
2079 const CXXRecordDecl *CXXDecl, SmallVectorImpl<llvm::Metadata *> &elements,
2080 llvm::DIType *RecordTy) {
2085 unsigned fieldno = 0;
2088 I != E; ++I, ++Field, ++fieldno) {
2089 const LambdaCapture &
Capture = *I;
2091 CGM.getContext().getASTRecordLayout(CXXDecl).getFieldOffset(fieldno);
2093 assert(!
Field->isBitField() &&
"lambdas don't have bitfield members!");
2103 Loc =
Field->getLocation();
2104 }
else if (
Capture.capturesVariable()) {
2107 const ValueDecl *CaptureDecl =
Capture.getCapturedVar();
2108 assert(CaptureDecl &&
"Expected valid decl for captured variable.");
2115 llvm::DIFile *VUnit = getOrCreateFile(Loc);
2117 elements.push_back(createFieldType(
2119 Field->getAccess(), FieldOffset, Align, VUnit, RecordTy, CXXDecl));
2125template <
typename T>
2126static llvm::Constant *
2137 return llvm::ConstantDataArray::get(Ctx, Vals);
2150 const QualType ElemQTy = ArrayTy->getElementType();
2157 switch (ElemBitWidth) {
2173llvm::DIDerivedType *
2174CGDebugInfo::CreateRecordStaticField(
const VarDecl *Var, llvm::DIType *RecordTy,
2175 const RecordDecl *RD) {
2179 llvm::DIFile *VUnit = getOrCreateFile(Var->
getLocation());
2180 llvm::DIType *VTy = getOrCreateType(Var->
getType(), VUnit);
2182 unsigned LineNumber = getLineNumber(Var->
getLocation());
2183 StringRef VName = Var->
getName();
2187 llvm::Constant *
C =
nullptr;
2192 C = llvm::ConstantInt::get(CGM.getLLVMContext(),
Value->getInt());
2193 if (
Value->isFloat())
2194 C = llvm::ConstantFP::get(CGM.getLLVMContext(),
Value->getFloat());
2195 if (
Value->isArray())
2201 auto Tag = CGM.getCodeGenOpts().DwarfVersion >= 5
2202 ? llvm::dwarf::DW_TAG_variable
2203 : llvm::dwarf::DW_TAG_member;
2205 llvm::DIDerivedType *GV = DBuilder.createStaticMemberType(
2206 RecordTy, VName, VUnit, LineNumber, VTy, Flags,
C, Tag, Align);
2211void CGDebugInfo::CollectRecordNormalField(
2212 const FieldDecl *field, uint64_t OffsetInBits, llvm::DIFile *tunit,
2213 SmallVectorImpl<llvm::Metadata *> &elements, llvm::DIType *RecordTy,
2214 const RecordDecl *RD) {
2219 if (
name.empty() && !
type->isRecordType())
2222 llvm::DIType *FieldType;
2224 llvm::DIDerivedType *BitFieldType;
2225 FieldType = BitFieldType = createBitFieldType(field, RecordTy, RD);
2226 if (llvm::DIType *Separator =
2227 createBitFieldSeparatorIfNeeded(field, BitFieldType, elements, RD))
2228 elements.push_back(Separator);
2231 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(field);
2234 OffsetInBits, Align, tunit, RecordTy, RD, Annotations);
2237 elements.push_back(FieldType);
2240void CGDebugInfo::CollectRecordNestedType(
2241 const TypeDecl *TD, SmallVectorImpl<llvm::Metadata *> &elements) {
2242 QualType Ty = CGM.getContext().getTypeDeclType(TD);
2249 if (llvm::DIType *nestedType = getOrCreateType(Ty, getOrCreateFile(Loc)))
2250 elements.push_back(nestedType);
2253void CGDebugInfo::CollectRecordFields(
2254 const RecordDecl *record, llvm::DIFile *tunit,
2255 SmallVectorImpl<llvm::Metadata *> &elements,
2256 llvm::DICompositeType *RecordTy) {
2257 const auto *CXXDecl = dyn_cast<CXXRecordDecl>(record);
2259 if (CXXDecl && CXXDecl->
isLambda())
2260 CollectRecordLambdaFields(CXXDecl, elements, RecordTy);
2262 const ASTRecordLayout &layout = CGM.getContext().getASTRecordLayout(record);
2265 unsigned fieldNo = 0;
2269 for (
const auto *I : record->
decls())
2270 if (
const auto *
V = dyn_cast<VarDecl>(I)) {
2271 if (
V->hasAttr<NoDebugAttr>())
2276 if (CGM.getCodeGenOpts().EmitCodeView &&
2284 auto MI = StaticDataMemberCache.find(
V->getCanonicalDecl());
2285 if (MI != StaticDataMemberCache.end()) {
2286 assert(MI->second &&
2287 "Static data member declaration should still exist");
2288 elements.push_back(MI->second);
2290 auto Field = CreateRecordStaticField(
V, RecordTy, record);
2291 elements.push_back(Field);
2293 }
else if (
const auto *field = dyn_cast<FieldDecl>(I)) {
2294 CollectRecordNormalField(field, layout.
getFieldOffset(fieldNo), tunit,
2295 elements, RecordTy, record);
2299 }
else if (CGM.getCodeGenOpts().EmitCodeView) {
2302 if (
const auto *nestedType = dyn_cast<TypeDecl>(I)) {
2307 if (!nestedType->isImplicit() &&
2308 nestedType->getDeclContext() == record)
2309 CollectRecordNestedType(nestedType, elements);
2315llvm::DISubroutineType *
2316CGDebugInfo::getOrCreateMethodType(
const CXXMethodDecl *
Method,
2317 llvm::DIFile *Unit) {
2318 const FunctionProtoType *
Func =
Method->getType()->getAs<FunctionProtoType>();
2320 return cast_or_null<llvm::DISubroutineType>(
2321 getOrCreateType(QualType(
Func, 0), Unit));
2324 if (!
Method->hasCXXExplicitFunctionObjectParameter())
2325 ThisType =
Method->getThisType();
2327 return getOrCreateInstanceMethodType(ThisType,
Func, Unit);
2330llvm::DISubroutineType *CGDebugInfo::getOrCreateMethodTypeForDestructor(
2331 const CXXMethodDecl *
Method, llvm::DIFile *Unit, QualType FNType) {
2332 const FunctionProtoType *
Func = FNType->
getAs<FunctionProtoType>();
2334 return getOrCreateInstanceMethodType(
Method->getThisType(),
Func, Unit,
true);
2337llvm::DISubroutineType *
2338CGDebugInfo::getOrCreateInstanceMethodType(QualType ThisPtr,
2339 const FunctionProtoType *
Func,
2340 llvm::DIFile *Unit,
bool SkipFirst) {
2341 FunctionProtoType::ExtProtoInfo EPI =
Func->getExtProtoInfo();
2356 getOrCreateType(CGM.getContext().getFunctionType(
2357 Func->getReturnType(),
Func->getParamTypes(), EPI),
2359 llvm::DITypeArray Args = OriginalFunc->getTypeArray();
2360 assert(Args.size() &&
"Invalid number of arguments!");
2362 SmallVector<llvm::Metadata *, 16> Elts;
2365 Elts.push_back(Args[0]);
2367 const bool HasExplicitObjectParameter = ThisPtr.
isNull();
2371 if (!HasExplicitObjectParameter) {
2372 llvm::DIType *ThisPtrType = getOrCreateType(ThisPtr, Unit);
2375 DBuilder.createObjectPointerType(ThisPtrType,
true);
2376 Elts.push_back(ThisPtrType);
2380 for (
unsigned i = (SkipFirst ? 2 : 1), e = Args.size(); i < e; ++i)
2381 Elts.push_back(Args[i]);
2384 if (HasExplicitObjectParameter) {
2385 assert(Elts.size() >= 2 && Args.size() >= 2 &&
2386 "Expected at least return type and object parameter.");
2387 Elts[1] = DBuilder.createObjectPointerType(Args[1],
false);
2390 llvm::DITypeArray EltTypeArray = DBuilder.getOrCreateTypeArray(Elts);
2392 return DBuilder.createSubroutineType(
2393 EltTypeArray, OriginalFunc->getFlags(),
2400 if (
const auto *NRD = dyn_cast<CXXRecordDecl>(RD->
getDeclContext()))
2408CGDebugInfo::GetMethodLinkageName(
const CXXMethodDecl *
Method)
const {
2411 const bool IsCtorOrDtor =
2414 if (IsCtorOrDtor && !CGM.getCodeGenOpts().DebugStructorDeclLinkageNames)
2421 if (IsCtorOrDtor && !CGM.getTarget().getCXXABI().hasConstructorVariants())
2424 if (
const auto *Ctor = llvm::dyn_cast<CXXConstructorDecl>(
Method))
2427 if (
const auto *Dtor = llvm::dyn_cast<CXXDestructorDecl>(
Method))
2430 return CGM.getMangledName(
Method);
2433bool CGDebugInfo::shouldGenerateVirtualCallSite()
const {
2436 (CGM.getCodeGenOpts().DwarfVersion >= 5));
2439llvm::DISubprogram *CGDebugInfo::CreateCXXMemberFunction(
2440 const CXXMethodDecl *
Method, llvm::DIFile *Unit, llvm::DIType *RecordTy) {
2443 StringRef MethodName = getFunctionName(
Method);
2444 llvm::DISubroutineType *MethodTy = getOrCreateMethodType(
Method, Unit);
2446 StringRef MethodLinkageName;
2453 MethodLinkageName = GetMethodLinkageName(
Method);
2456 llvm::DIFile *MethodDefUnit =
nullptr;
2457 unsigned MethodLine = 0;
2458 if (!
Method->isImplicit()) {
2459 MethodDefUnit = getOrCreateFile(
Method->getLocation());
2460 MethodLine = getLineNumber(
Method->getLocation());
2464 llvm::DIType *ContainingType =
nullptr;
2465 unsigned VIndex = 0;
2466 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
2467 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
2468 int ThisAdjustment = 0;
2471 if (
Method->isPureVirtual())
2472 SPFlags |= llvm::DISubprogram::SPFlagPureVirtual;
2474 SPFlags |= llvm::DISubprogram::SPFlagVirtual;
2476 if (CGM.getTarget().getCXXABI().isItaniumFamily()) {
2480 VIndex = CGM.getItaniumVTableContext().getMethodVTableIndex(
Method);
2484 const auto *DD = dyn_cast<CXXDestructorDecl>(
Method);
2487 DD, CGM.getContext().getTargetInfo().emitVectorDeletingDtors(
2488 CGM.getContext().getLangOpts())
2492 MethodVFTableLocation ML =
2493 CGM.getMicrosoftVTableContext().getMethodVFTableLocation(GD);
2501 if (
Method->size_overridden_methods() == 0)
2502 Flags |= llvm::DINode::FlagIntroducedVirtual;
2507 ThisAdjustment = CGM.getCXXABI()
2508 .getVirtualFunctionPrologueThisAdjustment(GD)
2511 ContainingType = RecordTy;
2514 if (
Method->getCanonicalDecl()->isDeleted())
2515 SPFlags |= llvm::DISubprogram::SPFlagDeleted;
2517 if (
Method->isNoReturn())
2518 Flags |= llvm::DINode::FlagNoReturn;
2521 Flags |= llvm::DINode::FlagStaticMember;
2522 if (
Method->isImplicit())
2523 Flags |= llvm::DINode::FlagArtificial;
2525 if (
const auto *CXXC = dyn_cast<CXXConstructorDecl>(
Method)) {
2526 if (CXXC->isExplicit())
2527 Flags |= llvm::DINode::FlagExplicit;
2528 }
else if (
const auto *CXXC = dyn_cast<CXXConversionDecl>(
Method)) {
2529 if (CXXC->isExplicit())
2530 Flags |= llvm::DINode::FlagExplicit;
2532 if (
Method->hasPrototype())
2533 Flags |= llvm::DINode::FlagPrototyped;
2535 Flags |= llvm::DINode::FlagLValueReference;
2537 Flags |= llvm::DINode::FlagRValueReference;
2538 if (!
Method->isExternallyVisible())
2539 SPFlags |= llvm::DISubprogram::SPFlagLocalToUnit;
2540 if (CGM.getCodeGenOpts().OptimizationLevel != 0)
2541 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
2545 if (DebugKind == llvm::codegenoptions::DebugInfoConstructor)
2546 if (
const CXXConstructorDecl *CD = dyn_cast<CXXConstructorDecl>(
Method))
2549 llvm::DINodeArray TParamsArray = CollectFunctionTemplateParams(
Method, Unit);
2550 llvm::DISubprogram *SP = DBuilder.createMethod(
2551 RecordTy, MethodName, MethodLinkageName, MethodDefUnit, MethodLine,
2552 MethodTy, VIndex, ThisAdjustment, ContainingType, Flags, SPFlags,
2553 TParamsArray.get(),
nullptr,
2554 CGM.getCodeGenOpts().DebugKeyInstructions);
2556 SPCache[
Method->getCanonicalDecl()].reset(SP);
2561void CGDebugInfo::CollectCXXMemberFunctions(
2562 const CXXRecordDecl *RD, llvm::DIFile *Unit,
2563 SmallVectorImpl<llvm::Metadata *> &EltTys, llvm::DIType *RecordTy) {
2568 for (
const auto *I : RD->
decls()) {
2569 const auto *
Method = dyn_cast<CXXMethodDecl>(I);
2583 if (
Method->getType()->castAs<FunctionProtoType>()->getContainedAutoType())
2592 auto MI = SPCache.find(
Method->getCanonicalDecl());
2593 EltTys.push_back(MI == SPCache.end()
2594 ? CreateCXXMemberFunction(
Method, Unit, RecordTy)
2595 :
static_cast<llvm::Metadata *
>(MI->second));
2599void CGDebugInfo::CollectCXXBases(
const CXXRecordDecl *RD, llvm::DIFile *Unit,
2600 SmallVectorImpl<llvm::Metadata *> &EltTys,
2601 llvm::DIType *RecordTy) {
2602 llvm::DenseSet<CanonicalDeclPtr<const CXXRecordDecl>> SeenTypes;
2603 CollectCXXBasesAux(RD, Unit, EltTys, RecordTy, RD->
bases(), SeenTypes,
2604 llvm::DINode::FlagZero);
2608 if (CGM.getCodeGenOpts().EmitCodeView) {
2609 CollectCXXBasesAux(RD, Unit, EltTys, RecordTy, RD->
vbases(), SeenTypes,
2610 llvm::DINode::FlagIndirectVirtualBase);
2614void CGDebugInfo::CollectCXXBasesAux(
2615 const CXXRecordDecl *RD, llvm::DIFile *Unit,
2616 SmallVectorImpl<llvm::Metadata *> &EltTys, llvm::DIType *RecordTy,
2618 llvm::DenseSet<CanonicalDeclPtr<const CXXRecordDecl>> &SeenTypes,
2619 llvm::DINode::DIFlags StartingFlags) {
2620 const ASTRecordLayout &RL = CGM.getContext().getASTRecordLayout(RD);
2621 for (
const auto &BI : Bases) {
2624 BI.getType()->castAsCanonical<RecordType>()->getDecl())
2626 if (!SeenTypes.insert(Base).second)
2628 auto *BaseTy = getOrCreateType(BI.getType(), Unit);
2629 llvm::DINode::DIFlags BFlags = StartingFlags;
2633 if (BI.isVirtual()) {
2634 if (CGM.getTarget().getCXXABI().isItaniumFamily()) {
2637 BaseOffset = 0 - CGM.getItaniumVTableContext()
2638 .getVirtualBaseOffsetOffset(RD, Base)
2644 4 * CGM.getMicrosoftVTableContext().getVBTableIndex(RD, Base);
2645 VBPtrOffset = CGM.getContext()
2646 .getASTRecordLayout(RD)
2650 BFlags |= llvm::DINode::FlagVirtual;
2657 llvm::DIType *DTy = DBuilder.createInheritance(RecordTy, BaseTy, BaseOffset,
2658 VBPtrOffset, BFlags);
2659 EltTys.push_back(DTy);
2664CGDebugInfo::CollectTemplateParams(std::optional<TemplateArgs> OArgs,
2665 llvm::DIFile *Unit) {
2667 return llvm::DINodeArray();
2668 TemplateArgs &Args = *OArgs;
2669 SmallVector<llvm::Metadata *, 16> TemplateParams;
2670 for (
unsigned i = 0, e = Args.Args.size(); i != e; ++i) {
2671 const TemplateArgument &TA = Args.Args[i];
2675 Name = Args.TList->getParam(i)->getName();
2679 llvm::DIType *TTy = getOrCreateType(TA.
getAsType(), Unit);
2680 TemplateParams.push_back(DBuilder.createTemplateTypeParameter(
2681 TheCU, Name, TTy, defaultParameter));
2686 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2687 TheCU, Name, TTy, defaultParameter,
2688 llvm::ConstantInt::get(CGM.getLLVMContext(), TA.
getAsIntegral())));
2693 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2694 llvm::Constant *
V =
nullptr;
2697 if (!CGM.getLangOpts().CUDA || CGM.getLangOpts().CUDAIsDevice ||
2698 !D->
hasAttr<CUDADeviceAttr>()) {
2701 if (
const auto *VD = dyn_cast<VarDecl>(D))
2702 V = CGM.GetAddrOfGlobalVar(VD);
2705 else if (
const auto *MD = dyn_cast<CXXMethodDecl>(D);
2706 MD && MD->isImplicitObjectMemberFunction())
2707 V = CGM.getCXXABI().EmitMemberFunctionPointer(MD);
2708 else if (
const auto *FD = dyn_cast<FunctionDecl>(D))
2709 V = CGM.GetAddrOfFunction(FD);
2712 else if (
const auto *MPT =
2713 dyn_cast<MemberPointerType>(
T.getTypePtr())) {
2717 uint64_t fieldOffset = CGM.getContext().getFieldOffset(D);
2719 CGM.getContext().toCharUnitsFromBits((int64_t)fieldOffset);
2720 V = CGM.getCXXABI().EmitMemberDataPointer(MPT, chars);
2721 }
else if (
const auto *GD = dyn_cast<MSGuidDecl>(D)) {
2722 V = CGM.GetAddrOfMSGuidDecl(GD).getPointer();
2723 }
else if (
const auto *TPO = dyn_cast<TemplateParamObjectDecl>(D)) {
2725 V = ConstantEmitter(CGM).emitAbstract(
2726 SourceLocation(), TPO->getValue(), TPO->getType());
2728 V = CGM.GetAddrOfTemplateParamObject(TPO).getPointer();
2730 assert(
V &&
"Failed to find template parameter pointer");
2731 V =
V->stripPointerCasts();
2733 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2734 TheCU, Name, TTy, defaultParameter, cast_or_null<llvm::Constant>(
V)));
2738 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2739 llvm::Constant *
V =
nullptr;
2742 if (
const auto *MPT = dyn_cast<MemberPointerType>(
T.getTypePtr()))
2748 if (MPT->isMemberDataPointer())
2749 V = CGM.getCXXABI().EmitNullMemberPointer(MPT);
2751 V = llvm::ConstantInt::get(CGM.Int8Ty, 0);
2752 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2753 TheCU, Name, TTy, defaultParameter,
V));
2757 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2758 llvm::Constant *
V = ConstantEmitter(CGM).emitAbstract(
2760 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2761 TheCU, Name, TTy, defaultParameter,
V));
2764 std::string QualName;
2765 llvm::raw_string_ostream
OS(QualName);
2767 OS, getPrintingPolicy());
2768 TemplateParams.push_back(DBuilder.createTemplateTemplateParameter(
2769 TheCU, Name,
nullptr, QualName, defaultParameter));
2773 TemplateParams.push_back(DBuilder.createTemplateParameterPack(
2774 TheCU, Name,
nullptr,
2781 T = CGM.getContext().getLValueReferenceType(
T);
2782 llvm::Constant *
V = ConstantEmitter(CGM).emitAbstract(E,
T);
2783 assert(
V &&
"Expression in template argument isn't constant");
2784 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2785 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2786 TheCU, Name, TTy, defaultParameter,
V->stripPointerCasts()));
2792 "These argument types shouldn't exist in concrete types");
2795 return DBuilder.getOrCreateArray(TemplateParams);
2798std::optional<CGDebugInfo::TemplateArgs>
2799CGDebugInfo::GetTemplateArgs(
const FunctionDecl *FD)
const {
2807 return std::nullopt;
2809std::optional<CGDebugInfo::TemplateArgs>
2810CGDebugInfo::GetTemplateArgs(
const VarDecl *VD)
const {
2814 auto *TS = dyn_cast<VarTemplateSpecializationDecl>(VD);
2816 return std::nullopt;
2817 VarTemplateDecl *
T = TS->getSpecializedTemplate();
2818 const TemplateParameterList *TList =
T->getTemplateParameters();
2819 auto TA = TS->getTemplateArgs().asArray();
2820 return {{TList, TA}};
2822std::optional<CGDebugInfo::TemplateArgs>
2823CGDebugInfo::GetTemplateArgs(
const RecordDecl *RD)
const {
2824 if (
auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD)) {
2828 TemplateParameterList *TPList =
2829 TSpecial->getSpecializedTemplate()->getTemplateParameters();
2830 const TemplateArgumentList &TAList = TSpecial->getTemplateArgs();
2831 return {{TPList, TAList.
asArray()}};
2833 return std::nullopt;
2837CGDebugInfo::CollectFunctionTemplateParams(
const FunctionDecl *FD,
2838 llvm::DIFile *Unit) {
2839 return CollectTemplateParams(GetTemplateArgs(FD), Unit);
2842llvm::DINodeArray CGDebugInfo::CollectVarTemplateParams(
const VarDecl *VL,
2843 llvm::DIFile *Unit) {
2844 return CollectTemplateParams(GetTemplateArgs(VL), Unit);
2847llvm::DINodeArray CGDebugInfo::CollectCXXTemplateParams(
const RecordDecl *RD,
2848 llvm::DIFile *Unit) {
2849 return CollectTemplateParams(GetTemplateArgs(RD), Unit);
2852void CGDebugInfo::CollectBTFDeclTagAnnotations(
2853 const Decl *D, SmallVectorImpl<llvm::Metadata *> &Annotations) {
2855 llvm::Metadata *Ops[2] = {
2856 llvm::MDString::get(CGM.getLLVMContext(), StringRef(
"btf_decl_tag")),
2857 llvm::MDString::get(CGM.getLLVMContext(), I->getBTFDeclTag())};
2858 Annotations.push_back(llvm::MDNode::get(CGM.getLLVMContext(), Ops));
2862llvm::DINodeArray CGDebugInfo::CollectBTFDeclTagAnnotations(
const Decl *D) {
2863 if (!D->
hasAttr<BTFDeclTagAttr>())
2866 SmallVector<llvm::Metadata *, 4> Annotations;
2867 CollectBTFDeclTagAnnotations(D, Annotations);
2868 return DBuilder.getOrCreateArray(Annotations);
2871void CGDebugInfo::CollectBTFTypeTagAnnotations(
2872 QualType Ty, SmallVectorImpl<llvm::Metadata *> &Annotations) {
2873 const BTFTagAttributedType *BTFAttrTy;
2875 BTFAttrTy = dyn_cast<BTFTagAttributedType>(
Atomic->getValueType());
2877 BTFAttrTy = dyn_cast<BTFTagAttributedType>(Ty);
2880 StringRef
Tag = BTFAttrTy->getAttr()->getBTFTypeTag();
2882 llvm::Metadata *Ops[2] = {
2883 llvm::MDString::get(CGM.getLLVMContext(), StringRef(
"btf_type_tag")),
2884 llvm::MDString::get(CGM.getLLVMContext(), Tag)};
2885 Annotations.insert(Annotations.begin(),
2886 llvm::MDNode::get(CGM.getLLVMContext(), Ops));
2888 BTFAttrTy = dyn_cast<BTFTagAttributedType>(BTFAttrTy->getWrappedType());
2892llvm::DIType *CGDebugInfo::getOrCreateVTablePtrType(llvm::DIFile *Unit) {
2894 return VTablePtrType;
2896 ASTContext &Context = CGM.getContext();
2899 llvm::Metadata *STy = getOrCreateType(Context.
IntTy, Unit);
2900 llvm::DITypeArray SElements = DBuilder.getOrCreateTypeArray(STy);
2901 llvm::DIType *SubTy = DBuilder.createSubroutineType(SElements);
2903 unsigned VtblPtrAddressSpace = CGM.getTarget().getVtblPtrAddressSpace();
2904 std::optional<unsigned> DWARFAddressSpace =
2905 CGM.getTarget().getDWARFAddressSpace(VtblPtrAddressSpace);
2907 llvm::DIType *vtbl_ptr_type = DBuilder.createPointerType(
2908 SubTy, Size, 0, DWARFAddressSpace,
"__vtbl_ptr_type");
2909 VTablePtrType = DBuilder.createPointerType(vtbl_ptr_type, Size);
2910 return VTablePtrType;
2913StringRef CGDebugInfo::getVTableName(
const CXXRecordDecl *RD) {
2925 if (!CGM.getTarget().getCXXABI().isItaniumFamily())
2927 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
2937 if (CGM.getTarget().getTriple().isOSBinFormatCOFF() &&
2938 VTable->isDeclarationForLinker())
2942 StringRef SymbolName =
"__clang_vtable";
2944 QualType VoidPtr = Context.getPointerType(Context.VoidTy);
2953 llvm::DIScope *DContext = getContextDescriptor(RD, TheCU);
2955 llvm::DIFile *Unit = getOrCreateFile(Loc);
2956 llvm::DIType *VTy = getOrCreateType(VoidPtr, Unit);
2958 llvm::DINode::FlagArtificial;
2959 auto Tag = CGM.getCodeGenOpts().DwarfVersion >= 5
2960 ? llvm::dwarf::DW_TAG_variable
2961 : llvm::dwarf::DW_TAG_member;
2962 llvm::DIDerivedType *DT = DBuilder.createStaticMemberType(
2963 Ctxt, SymbolName, Unit, 0, VTy, Flags,
2967 unsigned PAlign = CGM.getVtableGlobalVarAlignment();
2971 llvm::DIGlobalVariableExpression *GVE =
2972 DBuilder.createGlobalVariableExpression(
2973 TheCU, SymbolName, VTable->getName(), Unit, 0,
2974 getOrCreateType(VoidPtr, Unit), VTable->hasLocalLinkage(),
2975 true,
nullptr, DT,
nullptr,
2977 VTable->addDebugInfo(GVE);
2980StringRef CGDebugInfo::getDynamicInitializerName(
const VarDecl *VD,
2982 llvm::Function *InitFn) {
2987 return InitFn->getName();
2997 llvm::raw_svector_ostream OS(QualifiedGV);
2999 std::tie(Quals, GVName) = OS.str().rsplit(
"::");
3001 std::swap(Quals, GVName);
3005 llvm::raw_svector_ostream OS(InitName);
3007 OS << Quals <<
"::";
3012 llvm_unreachable(
"not an initializer");
3014 OS <<
"`dynamic initializer for '";
3017 OS <<
"`dynamic atexit destructor for '";
3024 if (
const auto *VTpl = dyn_cast<VarTemplateSpecializationDecl>(VD)) {
3025 printTemplateArgumentList(OS, VTpl->getTemplateArgs().asArray(),
3026 getPrintingPolicy());
3031 return internString(
OS.str());
3034void CGDebugInfo::CollectVTableInfo(
const CXXRecordDecl *RD, llvm::DIFile *Unit,
3035 SmallVectorImpl<llvm::Metadata *> &EltTys) {
3044 const ASTRecordLayout &RL = CGM.getContext().getASTRecordLayout(RD);
3051 llvm::DIType *VPtrTy =
nullptr;
3052 bool NeedVTableShape = CGM.getCodeGenOpts().EmitCodeView &&
3053 CGM.getTarget().getCXXABI().isMicrosoft();
3054 if (NeedVTableShape) {
3056 CGM.getContext().getTypeSize(CGM.getContext().VoidPtrTy);
3057 const VTableLayout &VFTLayout =
3058 CGM.getMicrosoftVTableContext().getVFTableLayout(RD,
CharUnits::Zero());
3059 unsigned VSlotCount =
3061 unsigned VTableWidth = PtrWidth * VSlotCount;
3062 unsigned VtblPtrAddressSpace = CGM.getTarget().getVtblPtrAddressSpace();
3063 std::optional<unsigned> DWARFAddressSpace =
3064 CGM.getTarget().getDWARFAddressSpace(VtblPtrAddressSpace);
3067 llvm::DIType *VTableType = DBuilder.createPointerType(
3068 nullptr, VTableWidth, 0, DWARFAddressSpace,
"__vtbl_ptr_type");
3069 EltTys.push_back(VTableType);
3072 VPtrTy = DBuilder.createPointerType(VTableType, PtrWidth);
3080 VPtrTy = getOrCreateVTablePtrType(Unit);
3082 unsigned Size = CGM.getContext().getTypeSize(CGM.getContext().VoidPtrTy);
3083 llvm::DIType *VPtrMember =
3084 DBuilder.createMemberType(Unit, getVTableName(RD), Unit, 0, Size, 0, 0,
3085 llvm::DINode::FlagArtificial, VPtrTy);
3086 EltTys.push_back(VPtrMember);
3091 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
3092 llvm::DIType *
T = getOrCreateType(RTy, getOrCreateFile(Loc));
3103 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
3104 assert(!D.
isNull() &&
"null type");
3105 llvm::DIType *
T = getOrCreateType(D, getOrCreateFile(Loc));
3106 assert(
T &&
"could not create debug info for type");
3115 if (CGM.getCodeGenOpts().getDebugInfo() <=
3116 llvm::codegenoptions::DebugLineTablesOnly)
3120 node = llvm::MDNode::get(CGM.getLLVMContext(), {});
3122 node = getOrCreateType(AllocatedTy, getOrCreateFile(Loc));
3124 CI->setMetadata(
"heapallocsite", node);
3128 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
3130 CanQualType Ty = CGM.getContext().getCanonicalTagType(ED);
3132 auto I = TypeCache.find(TyPtr);
3135 llvm::DIType *Res = CreateTypeDefinition(dyn_cast<EnumType>(Ty));
3136 assert(!Res->isForwardDecl());
3137 TypeCache[TyPtr].reset(Res);
3141 if (DebugKind > llvm::codegenoptions::LimitedDebugInfo ||
3142 !CGM.getLangOpts().CPlusPlus)
3148 if (RD->
hasAttr<DLLImportAttr>())
3151 if (MD->hasAttr<DLLImportAttr>())
3164 if (
auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD)) {
3174 if (
auto *TD = dyn_cast<ClassTemplateSpecializationDecl>(CXXDecl))
3175 Explicit = TD->isExplicitInstantiationOrSpecialization();
3179 if (CXXDecl->
fields().empty())
3189 if (
auto *CXXRD = dyn_cast<CXXRecordDecl>(RD))
3190 if (CXXRD->isDynamicClass() &&
3191 CGM.getVTableLinkage(CXXRD) ==
3192 llvm::GlobalValue::AvailableExternallyLinkage &&
3203 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
3205 CanQualType Ty = CGM.getContext().getCanonicalTagType(RD);
3207 auto I = TypeCache.find(TyPtr);
3214 auto [Res, PrefRes] = CreateTypeDefinition(dyn_cast<RecordType>(Ty));
3215 assert(!Res->isForwardDecl());
3216 TypeCache[TyPtr].reset(Res);
3223 if (!Tmpl->isImplicit() && Tmpl->isThisDeclarationADefinition() &&
3224 !MD->getMemberSpecializationInfo()->isExplicitSpecialization())
3247 if (Ctor->isCopyOrMoveConstructor())
3249 if (!Ctor->isDeleted())
3268 if (DebugKind == llvm::codegenoptions::DebugLineTablesOnly)
3271 if (DebugKind > llvm::codegenoptions::LimitedDebugInfo ||
3272 RD->
hasAttr<StandaloneDebugAttr>())
3275 if (!LangOpts.CPlusPlus)
3281 const auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD);
3297 if (
const auto *SD = dyn_cast<ClassTemplateSpecializationDecl>(RD))
3298 Spec = SD->getSpecializationKind();
3307 if ((DebugKind == llvm::codegenoptions::DebugInfoConstructor) &&
3318 CanQualType Ty = CGM.getContext().getCanonicalTagType(RD);
3319 llvm::DIType *
T = getTypeOrNull(Ty);
3320 if (
T &&
T->isForwardDecl())
3324llvm::DIType *CGDebugInfo::CreateType(
const RecordType *Ty) {
3326 llvm::DIType *
T = cast_or_null<llvm::DIType>(getTypeOrNull(
QualType(Ty, 0)));
3330 T = getOrCreateRecordFwdDecl(Ty, getDeclContextDescriptor(RD));
3334 auto [Def, Pref] = CreateTypeDefinition(Ty);
3336 return Pref ? Pref : Def;
3339llvm::DIType *CGDebugInfo::GetPreferredNameType(
const CXXRecordDecl *RD,
3340 llvm::DIFile *Unit) {
3344 auto const *PNA = RD->
getAttr<PreferredNameAttr>();
3348 return getOrCreateType(PNA->getTypedefType(), Unit);
3351std::pair<llvm::DIType *, llvm::DIType *>
3352CGDebugInfo::CreateTypeDefinition(
const RecordType *Ty) {
3356 llvm::DIFile *DefUnit = getOrCreateFile(RD->
getLocation());
3364 llvm::DICompositeType *FwdDecl = getOrCreateLimitedType(Ty);
3368 return {FwdDecl,
nullptr};
3370 if (
const auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD))
3371 CollectContainingType(CXXDecl, FwdDecl);
3374 LexicalBlockStack.emplace_back(&*FwdDecl);
3375 RegionMap[RD].reset(FwdDecl);
3378 SmallVector<llvm::Metadata *, 16> EltTys;
3385 const auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD);
3387 CollectCXXBases(CXXDecl, DefUnit, EltTys, FwdDecl);
3388 CollectVTableInfo(CXXDecl, DefUnit, EltTys);
3392 CollectRecordFields(RD, DefUnit, EltTys, FwdDecl);
3393 if (CXXDecl && !CGM.getCodeGenOpts().DebugOmitUnreferencedMethods)
3394 CollectCXXMemberFunctions(CXXDecl, DefUnit, EltTys, FwdDecl);
3396 LexicalBlockStack.pop_back();
3397 RegionMap.erase(RD);
3399 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
3400 DBuilder.replaceArrays(FwdDecl, Elements);
3402 if (FwdDecl->isTemporary())
3404 llvm::MDNode::replaceWithPermanent(llvm::TempDICompositeType(FwdDecl));
3406 RegionMap[RD].reset(FwdDecl);
3408 if (CGM.getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::LLDB)
3409 if (
auto *PrefDI = GetPreferredNameType(CXXDecl, DefUnit))
3410 return {FwdDecl, PrefDI};
3412 return {FwdDecl,
nullptr};
3415llvm::DIType *CGDebugInfo::CreateType(
const ObjCObjectType *Ty,
3416 llvm::DIFile *Unit) {
3418 return getOrCreateType(Ty->getBaseType(), Unit);
3421llvm::DIType *CGDebugInfo::CreateType(
const ObjCTypeParamType *Ty,
3422 llvm::DIFile *Unit) {
3424 SourceLocation Loc = Ty->getDecl()->getLocation();
3427 return DBuilder.createTypedef(
3428 getOrCreateType(Ty->getDecl()->getUnderlyingType(), Unit),
3429 Ty->getDecl()->getName(), getOrCreateFile(Loc), getLineNumber(Loc),
3430 getDeclContextDescriptor(Ty->getDecl()));
3457llvm::DIType *CGDebugInfo::CreateType(
const ObjCInterfaceType *Ty,
3458 llvm::DIFile *Unit) {
3463 auto RuntimeLang =
static_cast<llvm::dwarf::SourceLanguage
>(
3464 TheCU->getSourceLanguage().getUnversionedName());
3469 if (DebugTypeExtRefs &&
ID->isFromASTFile() &&
ID->getDefinition() &&
3470 !
ID->getImplementation())
3471 return DBuilder.createForwardDecl(
3472 llvm::dwarf::DW_TAG_structure_type,
ID->getName(),
3473 getDeclContextDescriptor(ID), Unit, 0, RuntimeLang);
3476 llvm::DIFile *DefUnit = getOrCreateFile(
ID->getLocation());
3477 unsigned Line = getLineNumber(
ID->getLocation());
3481 ObjCInterfaceDecl *Def =
ID->getDefinition();
3483 llvm::DIScope *Mod = getParentModuleOrNull(ID);
3484 llvm::DIType *FwdDecl = DBuilder.createReplaceableCompositeType(
3485 llvm::dwarf::DW_TAG_structure_type,
ID->getName(), Mod ? Mod : TheCU,
3486 DefUnit,
Line, RuntimeLang);
3487 ObjCInterfaceCache.push_back(ObjCInterfaceCacheEntry(Ty, FwdDecl, Unit));
3491 return CreateTypeDefinition(Ty, Unit);
3494llvm::DIModule *CGDebugInfo::getOrCreateModuleRef(ASTSourceDescriptor Mod,
3495 bool CreateSkeletonCU) {
3500 auto ModRef = ModuleCache.find(M);
3501 if (ModRef != ModuleCache.end())
3505 SmallString<128> ConfigMacros;
3507 llvm::raw_svector_ostream
OS(ConfigMacros);
3508 const auto &PPOpts = CGM.getPreprocessorOpts();
3511 for (
auto &M : PPOpts.Macros) {
3514 const std::string &
Macro = M.first;
3515 bool Undef = M.second;
3516 OS <<
"\"-" << (Undef ?
'U' :
'D');
3517 for (
char c :
Macro)
3532 bool IsRootModule = M ? !M->
Parent :
true;
3536 if (CreateSkeletonCU && IsRootModule && Mod.
getASTFile().empty() && M)
3537 assert(StringRef(M->
Name).starts_with(CGM.getLangOpts().ModuleName) &&
3538 "clang module without ASTFile must be specified by -fmodule-name");
3541 auto RemapPath = [
this](StringRef Path) -> std::string {
3543 StringRef Relative(Remapped);
3544 StringRef CompDir = TheCU->getDirectory();
3545 if (CompDir.empty())
3548 if (Relative.consume_front(CompDir))
3549 Relative.consume_front(llvm::sys::path::get_separator());
3551 return Relative.str();
3554 if (CreateSkeletonCU && IsRootModule && !Mod.
getASTFile().empty()) {
3561 Signature = ModSig.truncatedValue();
3565 llvm::DIBuilder DIB(CGM.getModule());
3567 if (!llvm::sys::path::is_absolute(Mod.
getASTFile())) {
3568 if (CGM.getHeaderSearchOpts().ModuleFileHomeIsCwd)
3569 PCM = getCurrentDirname();
3573 llvm::sys::path::append(PCM, Mod.
getASTFile());
3574 DIB.createCompileUnit(
3575 TheCU->getSourceLanguage(),
3578 TheCU->getProducer(),
false, StringRef(), 0, RemapPath(PCM),
3579 llvm::DICompileUnit::FullDebug, Signature);
3583 llvm::DIModule *Parent =
3585 : getOrCreateModuleRef(ASTSourceDescriptor(*M->
Parent),
3587 StringRef IncludePath = Mod.
getPath();
3588 if (!CGM.getCodeGenOpts().DebugRecordSysroot) {
3589 StringRef Sysroot = CGM.getHeaderSearchOpts().Sysroot;
3590 if (!Sysroot.empty() && IncludePath.starts_with(Sysroot))
3593 llvm::DIModule *DIMod =
3594 DBuilder.createModule(Parent, Mod.
getModuleName(), ConfigMacros,
3595 RemapPath(IncludePath));
3596 ModuleCache[M].reset(DIMod);
3600llvm::DIType *CGDebugInfo::CreateTypeDefinition(
const ObjCInterfaceType *Ty,
3601 llvm::DIFile *Unit) {
3603 llvm::DIFile *DefUnit = getOrCreateFile(
ID->getLocation());
3604 unsigned Line = getLineNumber(
ID->getLocation());
3606 unsigned RuntimeLang = TheCU->getSourceLanguage().getUnversionedName();
3612 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
3613 if (
ID->getImplementation())
3614 Flags |= llvm::DINode::FlagObjcClassComplete;
3616 llvm::DIScope *Mod = getParentModuleOrNull(ID);
3617 llvm::DICompositeType *RealDecl = DBuilder.createStructType(
3618 Mod ? Mod : Unit,
ID->getName(), DefUnit,
Line, Size, Align, Flags,
3619 nullptr, llvm::DINodeArray(), RuntimeLang);
3621 QualType QTy(Ty, 0);
3622 TypeCache[QTy.getAsOpaquePtr()].reset(RealDecl);
3625 LexicalBlockStack.emplace_back(RealDecl);
3626 RegionMap[Ty->
getDecl()].reset(RealDecl);
3629 SmallVector<llvm::Metadata *, 16> EltTys;
3631 ObjCInterfaceDecl *SClass =
ID->getSuperClass();
3633 llvm::DIType *SClassTy =
3634 getOrCreateType(CGM.getContext().getObjCInterfaceType(SClass), Unit);
3638 llvm::DIType *InhTag = DBuilder.createInheritance(RealDecl, SClassTy, 0, 0,
3639 llvm::DINode::FlagZero);
3640 EltTys.push_back(InhTag);
3644 auto AddProperty = [&](
const ObjCPropertyDecl *PD) {
3645 SourceLocation Loc = PD->getLocation();
3646 llvm::DIFile *PUnit = getOrCreateFile(Loc);
3647 unsigned PLine = getLineNumber(Loc);
3648 ObjCMethodDecl *Getter = PD->getGetterMethodDecl();
3649 ObjCMethodDecl *Setter = PD->getSetterMethodDecl();
3650 llvm::MDNode *PropertyNode = DBuilder.createObjCProperty(
3651 PD->getName(), PUnit, PLine,
3653 : getSelectorName(PD->getGetterName()),
3655 : getSelectorName(PD->getSetterName()),
3656 PD->getPropertyAttributes(), getOrCreateType(PD->getType(), PUnit));
3657 EltTys.push_back(PropertyNode);
3662 typedef std::pair<char, const IdentifierInfo *> IsClassAndIdent;
3666 llvm::DenseSet<IsClassAndIdent> PropertySet;
3668 auto GetIsClassAndIdent = [](
const ObjCPropertyDecl *PD) {
3669 return std::make_pair(PD->isClassProperty(), PD->getIdentifier());
3671 for (
const ObjCCategoryDecl *ClassExt :
ID->known_extensions())
3672 for (
auto *PD : ClassExt->properties()) {
3673 PropertySet.insert(GetIsClassAndIdent(PD));
3676 for (
const auto *PD :
ID->properties()) {
3679 if (!PropertySet.insert(GetIsClassAndIdent(PD)).second)
3685 const ASTRecordLayout &RL = CGM.getContext().getASTObjCInterfaceLayout(ID);
3686 unsigned FieldNo = 0;
3687 for (ObjCIvarDecl *Field =
ID->all_declared_ivar_begin(); Field;
3688 Field =
Field->getNextIvar(), ++FieldNo) {
3689 llvm::DIType *FieldTy = getOrCreateType(
Field->getType(), Unit);
3693 StringRef FieldName =
Field->getName();
3696 if (FieldName.empty())
3700 llvm::DIFile *FieldDefUnit = getOrCreateFile(
Field->getLocation());
3701 unsigned FieldLine = getLineNumber(
Field->getLocation());
3702 QualType FType =
Field->getType();
3709 FieldSize =
Field->isBitField() ?
Field->getBitWidthValue()
3710 : CGM.getContext().getTypeSize(FType);
3715 if (CGM.getLangOpts().ObjCRuntime.isNonFragile()) {
3719 if (
Field->isBitField()) {
3721 CGM.getObjCRuntime().ComputeBitfieldBitOffset(CGM, ID, Field);
3722 FieldOffset %= CGM.getContext().getCharWidth();
3730 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
3732 Flags = llvm::DINode::FlagProtected;
3734 Flags = llvm::DINode::FlagPrivate;
3736 Flags = llvm::DINode::FlagPublic;
3738 if (
Field->isBitField())
3739 Flags |= llvm::DINode::FlagBitField;
3741 llvm::MDNode *PropertyNode =
nullptr;
3742 if (ObjCImplementationDecl *ImpD =
ID->getImplementation()) {
3743 if (ObjCPropertyImplDecl *PImpD =
3744 ImpD->FindPropertyImplIvarDecl(
Field->getIdentifier())) {
3745 if (ObjCPropertyDecl *PD = PImpD->getPropertyDecl()) {
3746 SourceLocation Loc = PD->getLocation();
3747 llvm::DIFile *PUnit = getOrCreateFile(Loc);
3748 unsigned PLine = getLineNumber(Loc);
3749 ObjCMethodDecl *Getter = PImpD->getGetterMethodDecl();
3750 ObjCMethodDecl *Setter = PImpD->getSetterMethodDecl();
3751 PropertyNode = DBuilder.createObjCProperty(
3752 PD->getName(), PUnit, PLine,
3755 : getSelectorName(PD->getGetterName()),
3758 : getSelectorName(PD->getSetterName()),
3759 PD->getPropertyAttributes(),
3760 getOrCreateType(PD->getType(), PUnit));
3764 FieldTy = DBuilder.createObjCIVar(FieldName, FieldDefUnit, FieldLine,
3765 FieldSize, FieldAlign, FieldOffset, Flags,
3766 FieldTy, PropertyNode);
3767 EltTys.push_back(FieldTy);
3770 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
3771 DBuilder.replaceArrays(RealDecl, Elements);
3773 LexicalBlockStack.pop_back();
3777llvm::DIType *CGDebugInfo::CreateType(
const VectorType *Ty,
3778 llvm::DIFile *Unit) {
3786 auto &Ctx = CGM.getContext();
3791 QualType CharVecTy =
3793 return CreateType(CharVecTy->
getAs<VectorType>(), Unit);
3796 llvm::DIType *ElementTy = getOrCreateType(Ty->
getElementType(), Unit);
3799 llvm::Metadata *Subscript;
3800 QualType QTy(Ty, 0);
3801 auto SizeExpr = SizeExprCache.find(QTy);
3802 if (SizeExpr != SizeExprCache.end())
3803 Subscript = DBuilder.getOrCreateSubrange(
3804 SizeExpr->getSecond() ,
nullptr ,
3805 nullptr ,
nullptr );
3808 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3809 llvm::Type::getInt64Ty(CGM.getLLVMContext()), Count ? Count : -1));
3810 Subscript = DBuilder.getOrCreateSubrange(
3811 CountNode ,
nullptr ,
nullptr ,
3814 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscript);
3819 return DBuilder.createVectorType(Size, Align, ElementTy, SubscriptArray);
3822llvm::DIType *CGDebugInfo::CreateType(
const ConstantMatrixType *Ty,
3823 llvm::DIFile *Unit) {
3827 llvm::DIType *ElementTy = getOrCreateType(Ty->
getElementType(), Unit);
3832 llvm::SmallVector<llvm::Metadata *, 2> Subscripts;
3833 auto *ColumnCountNode =
3834 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3835 llvm::Type::getInt64Ty(CGM.getLLVMContext()), Ty->
getNumColumns()));
3836 auto *RowCountNode =
3837 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3838 llvm::Type::getInt64Ty(CGM.getLLVMContext()), Ty->
getNumRows()));
3839 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3840 ColumnCountNode ,
nullptr ,
nullptr ,
3842 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3843 RowCountNode ,
nullptr ,
nullptr ,
3845 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscripts);
3846 return DBuilder.createArrayType(Size, Align, ElementTy, SubscriptArray);
3849llvm::DIType *CGDebugInfo::CreateType(
const ArrayType *Ty, llvm::DIFile *Unit) {
3854 if (
const auto *VAT = dyn_cast<VariableArrayType>(Ty)) {
3869 Size = CGM.getContext().getTypeSize(Ty);
3876 SmallVector<llvm::Metadata *, 8> Subscripts;
3877 QualType EltTy(Ty, 0);
3878 while ((Ty = dyn_cast<ArrayType>(EltTy))) {
3887 if (
const auto *CAT = dyn_cast<ConstantArrayType>(Ty))
3888 Count = CAT->getZExtSize();
3889 else if (
const auto *VAT = dyn_cast<VariableArrayType>(Ty)) {
3890 if (Expr *Size = VAT->getSizeExpr()) {
3892 if (
Size->EvaluateAsInt(
Result, CGM.getContext()))
3893 Count =
Result.Val.getInt().getExtValue();
3897 auto SizeNode = SizeExprCache.find(EltTy);
3898 if (SizeNode != SizeExprCache.end())
3899 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3900 SizeNode->getSecond() ,
nullptr ,
3901 nullptr ,
nullptr ));
3904 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3905 llvm::Type::getInt64Ty(CGM.getLLVMContext()), Count));
3906 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3907 CountNode ,
nullptr ,
nullptr ,
3913 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscripts);
3915 return DBuilder.createArrayType(Size, Align, getOrCreateType(EltTy, Unit),
3919llvm::DIType *CGDebugInfo::CreateType(
const LValueReferenceType *Ty,
3920 llvm::DIFile *Unit) {
3921 return CreatePointerLikeType(llvm::dwarf::DW_TAG_reference_type, Ty,
3925llvm::DIType *CGDebugInfo::CreateType(
const RValueReferenceType *Ty,
3926 llvm::DIFile *Unit) {
3927 llvm::dwarf::Tag
Tag = llvm::dwarf::DW_TAG_rvalue_reference_type;
3929 if (CGM.getCodeGenOpts().DebugStrictDwarf &&
3930 CGM.getCodeGenOpts().DwarfVersion < 4)
3931 Tag = llvm::dwarf::DW_TAG_reference_type;
3933 return CreatePointerLikeType(Tag, Ty, Ty->
getPointeeType(), Unit);
3936llvm::DIType *CGDebugInfo::CreateType(
const MemberPointerType *Ty,
3938 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
3942 Size = CGM.getContext().getTypeSize(Ty);
3945 if (CGM.getTarget().getCXXABI().isMicrosoft()) {
3948 Flags |= llvm::DINode::FlagSingleInheritance;
3951 Flags |= llvm::DINode::FlagMultipleInheritance;
3954 Flags |= llvm::DINode::FlagVirtualInheritance;
3964 llvm::DIType *ClassType = getOrCreateType(
T, U);
3966 return DBuilder.createMemberPointerType(
3970 const FunctionProtoType *FPT =
3972 return DBuilder.createMemberPointerType(
3973 getOrCreateInstanceMethodType(
3976 ClassType, Size, 0, Flags);
3979llvm::DIType *CGDebugInfo::CreateType(
const AtomicType *Ty, llvm::DIFile *U) {
3981 return DBuilder.createQualifiedType(llvm::dwarf::DW_TAG_atomic_type, FromTy);
3984llvm::DIType *CGDebugInfo::CreateType(
const PipeType *Ty, llvm::DIFile *U) {
3988llvm::DIType *CGDebugInfo::CreateType(
const HLSLAttributedResourceType *Ty,
3990 return getOrCreateType(Ty->getWrappedType(), U);
3993llvm::DIType *CGDebugInfo::CreateType(
const HLSLInlineSpirvType *Ty,
4000 const EnumType *Ty) {
4012llvm::DIType *CGDebugInfo::CreateEnumType(
const EnumType *Ty) {
4015 bool isImportedFromModule =
4016 DebugTypeExtRefs && ED->isFromASTFile() && ED->getDefinition();
4020 if (isImportedFromModule || !ED->getDefinition()) {
4027 llvm::DIScope *EDContext = getDeclContextDescriptor(ED);
4028 llvm::DIFile *DefUnit = getOrCreateFile(ED->getLocation());
4029 llvm::TempDIScope TmpContext(DBuilder.createReplaceableCompositeType(
4030 llvm::dwarf::DW_TAG_enumeration_type,
"", TheCU, DefUnit, 0));
4032 unsigned Line = getLineNumber(ED->getLocation());
4033 StringRef EDName = ED->getName();
4034 llvm::DIType *RetTy = DBuilder.createReplaceableCompositeType(
4035 llvm::dwarf::DW_TAG_enumeration_type, EDName, EDContext, DefUnit,
Line,
4036 0, Size, Align, llvm::DINode::FlagFwdDecl, Identifier);
4038 ReplaceMap.emplace_back(
4039 std::piecewise_construct, std::make_tuple(Ty),
4040 std::make_tuple(
static_cast<llvm::Metadata *
>(RetTy)));
4044 return CreateTypeDefinition(Ty);
4047llvm::DIType *CGDebugInfo::CreateTypeDefinition(
const EnumType *Ty) {
4050 SmallVector<llvm::Metadata *, 16> Enumerators;
4051 ED = ED->getDefinition();
4052 assert(ED &&
"An enumeration definition is required");
4053 for (
const auto *
Enum : ED->enumerators()) {
4054 Enumerators.push_back(
4055 DBuilder.createEnumerator(
Enum->getName(),
Enum->getInitVal()));
4058 std::optional<EnumExtensibilityAttr::Kind> EnumKind;
4059 if (
auto *Attr = ED->getAttr<EnumExtensibilityAttr>())
4060 EnumKind = Attr->getExtensibility();
4063 llvm::DINodeArray EltArray = DBuilder.getOrCreateArray(Enumerators);
4065 llvm::DIFile *DefUnit = getOrCreateFile(ED->getLocation());
4066 unsigned Line = getLineNumber(ED->getLocation());
4067 llvm::DIScope *EnumContext = getDeclContextDescriptor(ED);
4068 llvm::DIType *ClassTy = getOrCreateType(ED->getIntegerType(), DefUnit);
4069 return DBuilder.createEnumerationType(
4070 EnumContext, ED->getName(), DefUnit,
Line, Size, Align, EltArray, ClassTy,
4071 0, Identifier, ED->isScoped(), EnumKind);
4076 StringRef Name, StringRef
Value) {
4077 unsigned Line = LineLoc.
isInvalid() ? 0 : getLineNumber(LineLoc);
4078 return DBuilder.createMacro(Parent,
Line, MType, Name,
Value);
4084 llvm::DIFile *FName = getOrCreateFile(FileLoc);
4085 unsigned Line = LineLoc.
isInvalid() ? 0 : getLineNumber(LineLoc);
4086 return DBuilder.createTempMacroFile(Parent,
Line, FName);
4091 llvm::DISubprogram *SynthSubprogram) {
4092 return llvm::DILocation::get(CGM.getLLVMContext(), 0, 0,
4093 SynthSubprogram, ParentLocation);
4098 StringRef SynthFuncName,
4099 llvm::DIFile *SynthFile) {
4100 llvm::DISubprogram *SP = createInlinedSubprogram(SynthFuncName, SynthFile);
4105 llvm::DebugLoc TrapLocation, StringRef Category, StringRef FailureMsg) {
4111 FuncName += Category;
4113 FuncName += FailureMsg;
4116 TrapLocation->getFile());
4126 Quals += InnerQuals;
4128 switch (
T->getTypeClass()) {
4130 return C.getQualifiedType(
T.getTypePtr(), Quals);
4133 case Type::InjectedClassName:
4134 return C.getQualifiedType(
T->getCanonicalTypeUnqualified().getTypePtr(),
4136 case Type::TemplateSpecialization: {
4138 if (Spec->isTypeAlias())
4139 return C.getQualifiedType(
T.getTypePtr(), Quals);
4140 T = Spec->desugar();
4143 case Type::TypeOfExpr:
4149 case Type::Decltype:
4152 case Type::UnaryTransform:
4155 case Type::Attributed:
4158 case Type::BTFTagAttributed:
4161 case Type::CountAttributed:
4170 case Type::MacroQualified:
4173 case Type::SubstTemplateTypeParm:
4177 case Type::DeducedTemplateSpecialization: {
4179 assert(!DT.
isNull() &&
"Undeduced types shouldn't reach here.");
4183 case Type::PackIndexing: {
4187 case Type::Adjusted:
4194 assert(
T != LastT &&
"Type unwrapping failed to unwrap!");
4199llvm::DIType *CGDebugInfo::getTypeOrNull(QualType Ty) {
4202 if (It != TypeCache.end()) {
4204 if (llvm::Metadata *
V = It->second)
4217 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly ||
4224 RetainedTypes.push_back(
4225 CGM.getContext().getCanonicalTagType(&D).getAsOpaquePtr());
4228llvm::DIType *CGDebugInfo::getOrCreateType(
QualType Ty, llvm::DIFile *Unit) {
4232 llvm::TimeTraceScope TimeScope(
"DebugType", [&]() {
4234 llvm::raw_string_ostream OS(Name);
4235 Ty.
print(OS, getPrintingPolicy());
4242 if (
auto *
T = getTypeOrNull(Ty))
4245 llvm::DIType *Res = CreateTypeNode(Ty, Unit);
4246 void *TyPtr = Ty.getAsOpaquePtr();
4249 TypeCache[TyPtr].reset(Res);
4254llvm::DIModule *CGDebugInfo::getParentModuleOrNull(
const Decl *D) {
4262 auto Info = Reader->getSourceDescriptor(Idx);
4264 return getOrCreateModuleRef(*Info,
true);
4265 }
else if (ClangModuleMap) {
4278 auto Info = ASTSourceDescriptor(*M);
4279 return getOrCreateModuleRef(Info,
false);
4282 return getOrCreateModuleRef(PCHDescriptor,
false);
4289llvm::DIType *CGDebugInfo::CreateTypeNode(QualType Ty, llvm::DIFile *Unit) {
4292 return CreateQualifiedType(Ty, Unit);
4296#define TYPE(Class, Base)
4297#define ABSTRACT_TYPE(Class, Base)
4298#define NON_CANONICAL_TYPE(Class, Base)
4299#define DEPENDENT_TYPE(Class, Base) case Type::Class:
4300#include "clang/AST/TypeNodes.inc"
4301 llvm_unreachable(
"Dependent types cannot show up in debug information");
4303 case Type::ExtVector:
4306 case Type::ConstantMatrix:
4308 case Type::ObjCObjectPointer:
4310 case Type::ObjCObject:
4312 case Type::ObjCTypeParam:
4314 case Type::ObjCInterface:
4322 case Type::BlockPointer:
4330 case Type::FunctionProto:
4331 case Type::FunctionNoProto:
4333 case Type::ConstantArray:
4334 case Type::VariableArray:
4335 case Type::IncompleteArray:
4336 case Type::ArrayParameter:
4339 case Type::LValueReference:
4341 case Type::RValueReference:
4344 case Type::MemberPointer:
4352 case Type::OverflowBehavior:
4357 case Type::TemplateSpecialization:
4359 case Type::HLSLAttributedResource:
4361 case Type::HLSLInlineSpirv:
4363 case Type::PredefinedSugar:
4365 case Type::CountAttributed:
4366 case Type::LateParsedAttr:
4368 case Type::Attributed:
4369 case Type::BTFTagAttributed:
4370 case Type::Adjusted:
4372 case Type::DeducedTemplateSpecialization:
4375 case Type::MacroQualified:
4376 case Type::SubstTemplateTypeParm:
4377 case Type::TypeOfExpr:
4379 case Type::Decltype:
4380 case Type::PackIndexing:
4381 case Type::UnaryTransform:
4385 llvm_unreachable(
"type should have been unwrapped!");
4388llvm::DICompositeType *
4389CGDebugInfo::getOrCreateLimitedType(
const RecordType *Ty) {
4390 QualType QTy(Ty, 0);
4392 auto *
T = cast_or_null<llvm::DICompositeType>(getTypeOrNull(QTy));
4397 if (
T && !
T->isForwardDecl())
4401 llvm::DICompositeType *Res = CreateLimitedType(Ty);
4406 DBuilder.replaceArrays(Res,
T ?
T->getElements() : llvm::DINodeArray());
4409 TypeCache[QTy.getAsOpaquePtr()].reset(Res);
4414llvm::DICompositeType *CGDebugInfo::CreateLimitedType(
const RecordType *Ty) {
4416 bool NameIsSimplified =
false;
4419 StringRef RDName = getClassName(RD, &NameIsSimplified);
4421 llvm::DIFile *DefUnit =
nullptr;
4424 DefUnit = getOrCreateFile(Loc);
4425 Line = getLineNumber(Loc);
4428 llvm::DIScope *RDContext = getDeclContextDescriptor(RD);
4432 auto *
T = cast_or_null<llvm::DICompositeType>(
4433 getTypeOrNull(CGM.getContext().getCanonicalTagType(RD)));
4441 return getOrCreateRecordFwdDecl(Ty, RDContext);
4454 auto Flags = llvm::DINode::FlagZero;
4455 if (NameIsSimplified)
4456 Flags |= llvm::DINode::FlagNameIsSimplified;
4457 if (
auto CXXRD = dyn_cast<CXXRecordDecl>(RD)) {
4459 Flags |= llvm::DINode::FlagTypePassByReference;
4461 Flags |= llvm::DINode::FlagTypePassByValue;
4464 if (!CXXRD->isTrivial())
4465 Flags |= llvm::DINode::FlagNonTrivial;
4468 if (CXXRD->isAnonymousStructOrUnion())
4469 Flags |= llvm::DINode::FlagExportSymbols;
4472 dyn_cast<CXXRecordDecl>(CXXRD->getDeclContext()));
4475 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(D);
4476 llvm::DICompositeType *RealDecl = DBuilder.createReplaceableCompositeType(
4478 Flags, Identifier, Annotations);
4482 switch (RealDecl->getTag()) {
4484 llvm_unreachable(
"invalid composite type tag");
4486 case llvm::dwarf::DW_TAG_array_type:
4487 case llvm::dwarf::DW_TAG_enumeration_type:
4492 if (Identifier.empty())
4496 case llvm::dwarf::DW_TAG_structure_type:
4497 case llvm::dwarf::DW_TAG_union_type:
4498 case llvm::dwarf::DW_TAG_class_type:
4501 llvm::MDNode::replaceWithDistinct(llvm::TempDICompositeType(RealDecl));
4505 if (
auto *CTSD = dyn_cast<ClassTemplateSpecializationDecl>(Ty->getDecl())) {
4506 CXXRecordDecl *TemplateDecl =
4507 CTSD->getSpecializedTemplate()->getTemplatedDecl();
4508 RegionMap[TemplateDecl].reset(RealDecl);
4510 RegionMap[RD].reset(RealDecl);
4512 TypeCache[QualType(Ty, 0).getAsOpaquePtr()].reset(RealDecl);
4514 if (
const auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD))
4515 DBuilder.replaceArrays(RealDecl, llvm::DINodeArray(),
4516 CollectCXXTemplateParams(TSpecial, DefUnit));
4520void CGDebugInfo::CollectContainingType(
const CXXRecordDecl *RD,
4521 llvm::DICompositeType *RealDecl) {
4523 llvm::DIType *ContainingType =
nullptr;
4524 const ASTRecordLayout &RL = CGM.getContext().getASTRecordLayout(RD);
4528 const ASTRecordLayout &BRL = CGM.getContext().getASTRecordLayout(PBase);
4535 CanQualType T = CGM.getContext().getCanonicalTagType(PBase);
4536 ContainingType = getOrCreateType(
T, getOrCreateFile(RD->
getLocation()));
4538 ContainingType = RealDecl;
4540 DBuilder.replaceVTableHolder(RealDecl, ContainingType);
4543llvm::DIType *CGDebugInfo::CreateMemberType(llvm::DIFile *Unit, QualType FType,
4544 StringRef Name, uint64_t *Offset) {
4545 llvm::DIType *FieldTy = CGDebugInfo::getOrCreateType(FType, Unit);
4546 uint64_t FieldSize = CGM.getContext().getTypeSize(FType);
4549 DBuilder.createMemberType(Unit, Name, Unit, 0, FieldSize, FieldAlign,
4550 *Offset, llvm::DINode::FlagZero, FieldTy);
4551 *Offset += FieldSize;
4555void CGDebugInfo::collectFunctionDeclProps(GlobalDecl GD, llvm::DIFile *Unit,
4557 StringRef &LinkageName,
4558 llvm::DIScope *&FDContext,
4559 llvm::DINodeArray &TParamsArray,
4560 llvm::DINode::DIFlags &Flags) {
4562 bool NameIsSimplified =
false;
4563 Name = getFunctionName(FD, &NameIsSimplified);
4564 if (NameIsSimplified)
4565 Flags |= llvm::DINode::FlagNameIsSimplified;
4566 Name = getFunctionName(FD);
4569 LinkageName = CGM.getMangledName(GD);
4571 Flags |= llvm::DINode::FlagPrototyped;
4575 if (LinkageName == Name ||
4576 (CGM.getCodeGenOpts().CoverageNotesFile.empty() &&
4577 CGM.getCodeGenOpts().CoverageDataFile.empty() &&
4578 !CGM.getCodeGenOpts().DebugInfoForProfiling &&
4579 !CGM.getCodeGenOpts().PseudoProbeForProfiling &&
4580 DebugKind <= llvm::codegenoptions::DebugLineTablesOnly))
4581 LinkageName = StringRef();
4585 if (CGM.getCodeGenOpts().hasReducedDebugInfo() ||
4586 (DebugKind == llvm::codegenoptions::DebugLineTablesOnly &&
4587 CGM.getCodeGenOpts().EmitCodeView)) {
4588 if (
const NamespaceDecl *NSDecl =
4590 FDContext = getOrCreateNamespace(NSDecl);
4591 else if (
const RecordDecl *RDecl =
4593 llvm::DIScope *Mod = getParentModuleOrNull(RDecl);
4594 FDContext = getContextDescriptor(RDecl, Mod ? Mod : TheCU);
4597 if (CGM.getCodeGenOpts().hasReducedDebugInfo()) {
4600 Flags |= llvm::DINode::FlagNoReturn;
4602 TParamsArray = CollectFunctionTemplateParams(FD, Unit);
4606void CGDebugInfo::collectVarDeclProps(
const VarDecl *VD, llvm::DIFile *&Unit,
4607 unsigned &LineNo, QualType &
T,
4608 StringRef &Name, StringRef &LinkageName,
4609 llvm::MDTuple *&TemplateParameters,
4610 llvm::DIScope *&VDContext) {
4619 llvm::APInt ConstVal(32, 1);
4620 QualType ET = CGM.getContext().getAsArrayType(
T)->getElementType();
4622 T = CGM.getContext().getConstantArrayType(ET, ConstVal,
nullptr,
4629 LinkageName = CGM.getMangledName(VD);
4630 if (LinkageName == Name)
4631 LinkageName = StringRef();
4634 llvm::DINodeArray parameterNodes = CollectVarTemplateParams(VD, &*Unit);
4635 TemplateParameters = parameterNodes.get();
4637 TemplateParameters =
nullptr;
4643 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
4644 VDContext = LexicalBlockStack.back();
4663 DC = CGM.getContext().getTranslationUnitDecl();
4665 llvm::DIScope *Mod = getParentModuleOrNull(VD);
4666 VDContext = getContextDescriptor(
cast<Decl>(DC), Mod ? Mod : TheCU);
4669llvm::DISubprogram *CGDebugInfo::getFunctionFwdDeclOrStub(GlobalDecl GD,
4671 llvm::DINodeArray TParamsArray;
4672 StringRef Name, LinkageName;
4673 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
4674 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
4676 llvm::DIFile *Unit = getOrCreateFile(Loc);
4677 llvm::DIScope *DContext = Unit;
4678 unsigned Line = getLineNumber(Loc);
4679 collectFunctionDeclProps(GD, Unit, Name, LinkageName, DContext, TParamsArray,
4684 SmallVector<QualType, 16> ArgTypes;
4685 for (
const ParmVarDecl *Parm : FD->
parameters())
4686 ArgTypes.push_back(Parm->getType());
4689 QualType FnType = CGM.getContext().getFunctionType(
4690 FD->
getReturnType(), ArgTypes, FunctionProtoType::ExtProtoInfo(CC));
4692 SPFlags |= llvm::DISubprogram::SPFlagLocalToUnit;
4693 if (CGM.getCodeGenOpts().OptimizationLevel != 0)
4694 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
4698 SPFlags |= llvm::DISubprogram::SPFlagDefinition;
4699 return DBuilder.createFunction(
4700 DContext, Name, LinkageName, Unit,
Line,
4701 getOrCreateFunctionType(GD.
getDecl(), FnType, Unit), 0, Flags, SPFlags,
4702 TParamsArray.get(), getFunctionDeclaration(FD),
nullptr,
4704 CGM.getCodeGenOpts().DebugKeyInstructions);
4707 llvm::DISubprogram *SP = DBuilder.createTempFunctionFwdDecl(
4708 DContext, Name, LinkageName, Unit,
Line,
4709 getOrCreateFunctionType(GD.
getDecl(), FnType, Unit), 0, Flags, SPFlags,
4710 TParamsArray.get(), getFunctionDeclaration(FD));
4712 FwdDeclReplaceMap.emplace_back(std::piecewise_construct,
4713 std::make_tuple(CanonDecl),
4714 std::make_tuple(SP));
4718llvm::DISubprogram *CGDebugInfo::getFunctionForwardDeclaration(GlobalDecl GD) {
4719 return getFunctionFwdDeclOrStub(GD,
false);
4722llvm::DISubprogram *CGDebugInfo::getFunctionStub(GlobalDecl GD) {
4723 return getFunctionFwdDeclOrStub(GD,
true);
4726llvm::DIGlobalVariable *
4727CGDebugInfo::getGlobalVariableForwardDeclaration(
const VarDecl *VD) {
4729 StringRef Name, LinkageName;
4731 llvm::DIFile *Unit = getOrCreateFile(Loc);
4732 llvm::DIScope *DContext = Unit;
4733 unsigned Line = getLineNumber(Loc);
4734 llvm::MDTuple *TemplateParameters =
nullptr;
4736 collectVarDeclProps(VD, Unit,
Line,
T, Name, LinkageName, TemplateParameters,
4739 auto *GV = DBuilder.createTempGlobalVariableFwdDecl(
4740 DContext, Name, LinkageName, Unit,
Line, getOrCreateType(
T, Unit),
4742 FwdDeclReplaceMap.emplace_back(
4743 std::piecewise_construct,
4745 std::make_tuple(
static_cast<llvm::Metadata *
>(GV)));
4749llvm::DINode *CGDebugInfo::getDeclarationOrDefinition(
const Decl *D) {
4754 if (
const auto *TD = dyn_cast<TypeDecl>(D)) {
4755 QualType Ty = CGM.getContext().getTypeDeclType(TD);
4756 return getOrCreateType(Ty, getOrCreateFile(TD->
getLocation()));
4760 if (I != DeclCache.end()) {
4762 if (
auto *GVE = dyn_cast_or_null<llvm::DIGlobalVariableExpression>(N))
4763 return GVE->getVariable();
4771 if (IE != ImportedDeclCache.end()) {
4772 auto N = IE->second;
4773 if (
auto *GVE = dyn_cast_or_null<llvm::DIImportedEntity>(N))
4775 return dyn_cast_or_null<llvm::DINode>(N);
4780 if (
const auto *FD = dyn_cast<FunctionDecl>(D))
4781 return getFunctionForwardDeclaration(FD);
4782 else if (
const auto *VD = dyn_cast<VarDecl>(D))
4783 return getGlobalVariableForwardDeclaration(VD);
4788llvm::DISubprogram *CGDebugInfo::getFunctionDeclaration(
const Decl *D) {
4789 if (!D || DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
4792 const auto *FD = dyn_cast<FunctionDecl>(D);
4797 auto *S = getDeclContextDescriptor(D);
4800 if (MI == SPCache.end()) {
4802 return CreateCXXMemberFunction(MD, getOrCreateFile(MD->getLocation()),
4806 if (MI != SPCache.end()) {
4807 auto *SP = dyn_cast_or_null<llvm::DISubprogram>(MI->second);
4808 if (SP && !SP->isDefinition())
4812 for (
auto *NextFD : FD->
redecls()) {
4813 auto MI = SPCache.find(NextFD->getCanonicalDecl());
4814 if (MI != SPCache.end()) {
4815 auto *SP = dyn_cast_or_null<llvm::DISubprogram>(MI->second);
4816 if (SP && !SP->isDefinition())
4823llvm::DISubprogram *CGDebugInfo::getObjCMethodDeclaration(
4824 const Decl *D, llvm::DISubroutineType *FnType,
unsigned LineNo,
4825 llvm::DINode::DIFlags Flags, llvm::DISubprogram::DISPFlags SPFlags) {
4826 if (!D || DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
4829 const auto *OMD = dyn_cast<ObjCMethodDecl>(D);
4833 if (CGM.getCodeGenOpts().DwarfVersion < 5 && !OMD->
isDirectMethod())
4837 SPFlags |= llvm::DISubprogram::SPFlagObjCDirect;
4846 QualType QTy(
ID->getTypeForDecl(), 0);
4847 auto It = TypeCache.find(QTy.getAsOpaquePtr());
4848 if (It == TypeCache.end())
4851 llvm::DISubprogram *FD = DBuilder.createFunction(
4852 InterfaceType, getObjCMethodName(OMD), StringRef(),
4853 InterfaceType->getFile(), LineNo, FnType, LineNo, Flags, SPFlags);
4854 DBuilder.finalizeSubprogram(FD);
4861llvm::DISubroutineType *CGDebugInfo::getOrCreateFunctionType(
const Decl *D,
4866 if (!D || (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly &&
4867 !CGM.getCodeGenOpts().EmitCodeView))
4870 return DBuilder.createSubroutineType(DBuilder.getOrCreateTypeArray({}));
4872 if (
const auto *
Method = dyn_cast<CXXDestructorDecl>(D)) {
4875 return getOrCreateMethodTypeForDestructor(
Method, F, FnType);
4878 if (
const auto *
Method = dyn_cast<CXXMethodDecl>(D))
4879 return getOrCreateMethodType(
Method, F);
4881 const auto *FTy = FnType->
getAs<FunctionType>();
4884 if (
const auto *OMethod = dyn_cast<ObjCMethodDecl>(D)) {
4886 SmallVector<llvm::Metadata *, 16> Elts;
4889 QualType ResultTy = OMethod->getReturnType();
4892 if (ResultTy == CGM.getContext().getObjCInstanceType())
4893 ResultTy = CGM.getContext().getPointerType(
4894 QualType(OMethod->getClassInterface()->getTypeForDecl(), 0));
4896 Elts.push_back(getOrCreateType(ResultTy, F));
4898 QualType SelfDeclTy;
4899 if (
auto *SelfDecl = OMethod->getSelfDecl())
4900 SelfDeclTy = SelfDecl->getType();
4901 else if (
auto *FPT = dyn_cast<FunctionProtoType>(FnType))
4904 if (!SelfDeclTy.
isNull())
4906 CreateSelfType(SelfDeclTy, getOrCreateType(SelfDeclTy, F)));
4908 Elts.push_back(DBuilder.createArtificialType(
4909 getOrCreateType(CGM.getContext().getObjCSelType(), F)));
4911 for (
const auto *PI : OMethod->parameters())
4912 Elts.push_back(getOrCreateType(PI->getType(), F));
4914 if (OMethod->isVariadic())
4915 Elts.push_back(DBuilder.createUnspecifiedParameter());
4917 llvm::DITypeArray EltTypeArray = DBuilder.getOrCreateTypeArray(Elts);
4918 return DBuilder.createSubroutineType(
4919 EltTypeArray, llvm::DINode::FlagZero,
4920 getDwarfCC(CC, CGM.getTarget().getTriple()));
4925 if (
const auto *FD = dyn_cast<FunctionDecl>(D))
4926 if (FD->isVariadic()) {
4927 SmallVector<llvm::Metadata *, 16> EltTys;
4928 EltTys.push_back(getOrCreateType(FD->getReturnType(), F));
4929 if (
const auto *FPT = dyn_cast<FunctionProtoType>(FnType))
4931 EltTys.push_back(getOrCreateType(ParamType, F));
4932 EltTys.push_back(DBuilder.createUnspecifiedParameter());
4933 llvm::DITypeArray EltTypeArray = DBuilder.getOrCreateTypeArray(EltTys);
4934 return DBuilder.createSubroutineType(
4935 EltTypeArray, llvm::DINode::FlagZero,
4936 getDwarfCC(CC, CGM.getTarget().getTriple()));
4948 CC = SrcFnTy->getCallConv();
4950 for (
const VarDecl *VD : Args)
4951 ArgTypes.push_back(VD->
getType());
4952 return CGM.getContext().getFunctionType(RetTy, ArgTypes,
4958 llvm::Function *Fn,
bool CurFuncIsThunk) {
4960 StringRef LinkageName;
4962 FnBeginRegionCount.push_back(LexicalBlockStack.size());
4965 bool HasDecl = (D !=
nullptr);
4967 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
4968 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
4969 llvm::DIFile *Unit = getOrCreateFile(Loc);
4970 llvm::DIScope *FDContext = Unit;
4971 llvm::DINodeArray TParamsArray;
4972 bool KeyInstructions = CGM.getCodeGenOpts().DebugKeyInstructions;
4975 LinkageName = Fn->getName();
4976 }
else if (
const auto *FD = dyn_cast<FunctionDecl>(D)) {
4978 auto FI = SPCache.find(FD->getCanonicalDecl());
4979 if (FI != SPCache.end()) {
4980 auto *SP = dyn_cast_or_null<llvm::DISubprogram>(FI->second);
4981 if (SP && SP->isDefinition()) {
4982 LexicalBlockStack.emplace_back(SP);
4983 RegionMap[D].reset(SP);
4987 collectFunctionDeclProps(GD, Unit, Name, LinkageName, FDContext,
4988 TParamsArray, Flags);
4991 KeyInstructions && !isa_and_present<CoroutineBodyStmt>(FD->getBody());
4992 }
else if (
const auto *OMD = dyn_cast<ObjCMethodDecl>(D)) {
4993 Name = getObjCMethodName(OMD);
4994 Flags |= llvm::DINode::FlagPrototyped;
5000 if (Name != Fn->getName())
5001 LinkageName = Fn->getName();
5003 Name = Fn->getName();
5008 Flags |= llvm::DINode::FlagPrototyped;
5010 Name.consume_front(
"\01");
5014 "Unexpected DynamicInitKind !");
5018 Flags |= llvm::DINode::FlagArtificial;
5024 Flags |= llvm::DINode::FlagThunk;
5026 if (Fn->hasLocalLinkage())
5027 SPFlags |= llvm::DISubprogram::SPFlagLocalToUnit;
5028 if (CGM.getCodeGenOpts().OptimizationLevel != 0)
5029 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
5032 llvm::DISubprogram::DISPFlags SPFlagsForDef =
5033 SPFlags | llvm::DISubprogram::SPFlagDefinition;
5035 const unsigned LineNo = getLineNumber(Loc.
isValid() ? Loc : CurLoc);
5036 unsigned ScopeLine = getLineNumber(ScopeLoc);
5037 llvm::DISubroutineType *DIFnType = getOrCreateFunctionType(D, FnType, Unit);
5038 llvm::DISubprogram *
Decl =
nullptr;
5039 llvm::DINodeArray Annotations =
nullptr;
5042 ? getObjCMethodDeclaration(D, DIFnType, LineNo, Flags, SPFlags)
5043 : getFunctionDeclaration(D);
5044 Annotations = CollectBTFDeclTagAnnotations(D);
5052 llvm::DISubprogram *SP = DBuilder.createFunction(
5053 FDContext, Name, LinkageName, Unit, LineNo, DIFnType, ScopeLine,
5054 FlagsForDef, SPFlagsForDef, TParamsArray.get(),
Decl,
nullptr,
5055 Annotations,
"", KeyInstructions);
5056 Fn->setSubprogram(SP);
5065 LexicalBlockStack.emplace_back(SP);
5068 RegionMap[D].reset(SP);
5072 QualType FnType, llvm::Function *Fn) {
5074 StringRef LinkageName;
5080 llvm::TimeTraceScope TimeScope(
"DebugFunction", [&]() {
5081 return GetName(D,
true);
5084 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
5085 llvm::DIFile *Unit = getOrCreateFile(Loc);
5086 bool IsDeclForCallSite = Fn ?
true :
false;
5087 llvm::DIScope *FDContext =
5088 IsDeclForCallSite ? Unit : getDeclContextDescriptor(D);
5089 llvm::DINodeArray TParamsArray;
5092 collectFunctionDeclProps(GD, Unit, Name, LinkageName, FDContext,
5093 TParamsArray, Flags);
5094 }
else if (
const auto *OMD = dyn_cast<ObjCMethodDecl>(D)) {
5095 Name = getObjCMethodName(OMD);
5096 Flags |= llvm::DINode::FlagPrototyped;
5098 llvm_unreachable(
"not a function or ObjC method");
5100 Name.consume_front(
"\01");
5103 Flags |= llvm::DINode::FlagArtificial;
5108 unsigned LineNo = getLineNumber(Loc);
5109 unsigned ScopeLine = 0;
5110 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
5111 if (CGM.getCodeGenOpts().OptimizationLevel != 0)
5112 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
5114 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(D);
5115 llvm::DISubroutineType *STy = getOrCreateFunctionType(D, FnType, Unit);
5117 assert(~SPFlags & llvm::DISubprogram::SPFlagDefinition);
5118 llvm::DISubprogram *SP = DBuilder.createFunction(
5119 FDContext, Name, LinkageName, Unit, LineNo, STy, ScopeLine, Flags,
5120 SPFlags, TParamsArray.get(),
nullptr,
nullptr, Annotations,
5126 if (IsDeclForCallSite && CGM.getTarget().getTriple().isBPF()) {
5127 if (
auto *FD = dyn_cast<FunctionDecl>(D)) {
5128 llvm::DITypeArray ParamTypes = STy->getTypeArray();
5131 llvm::DINodeArray ParamAnnotations = CollectBTFDeclTagAnnotations(PD);
5132 DBuilder.createParameterVariable(
5133 SP, PD->getName(), ArgNo, Unit, LineNo, ParamTypes[ArgNo],
true,
5134 llvm::DINode::FlagZero, ParamAnnotations);
5140 if (IsDeclForCallSite)
5141 Fn->setSubprogram(SP);
5145 llvm::CallBase *CI) {
5146 if (!shouldGenerateVirtualCallSite())
5152 assert(CI &&
"Invalid Call Instruction.");
5153 if (!CI->isIndirectCall())
5157 if (llvm::DISubprogram *MD = getFunctionDeclaration(FD))
5158 CI->setMetadata(llvm::LLVMContext::MD_call_target, MD);
5166 auto *
Func = dyn_cast<llvm::Function>(CallOrInvoke->getCalledOperand());
5169 if (
Func->getSubprogram())
5177 if (CalleeDecl->
hasAttr<NoDebugAttr>() ||
5192 auto FI = SPCache.find(FD->getCanonicalDecl());
5193 llvm::DISubprogram *SP =
nullptr;
5194 if (FI != SPCache.end())
5195 SP = dyn_cast_or_null<llvm::DISubprogram>(FI->second);
5196 if (!SP || !SP->isDefinition())
5197 SP = getFunctionStub(GD);
5198 FnBeginRegionCount.push_back(LexicalBlockStack.size());
5199 LexicalBlockStack.emplace_back(SP);
5205 assert(CurInlinedAt &&
"unbalanced inline scope stack");
5214 if (CurLoc.isInvalid() ||
5215 (CGM.getCodeGenOpts().DebugInfoMacroExpansionLoc && CurLoc.isMacroID()) ||
5216 LexicalBlockStack.empty())
5219 llvm::MDNode *
Scope = LexicalBlockStack.back();
5220 Builder.SetCurrentDebugLocation(llvm::DILocation::get(
5221 CGM.getLLVMContext(), CurLocLine, CurLocColumn,
Scope, CurInlinedAt));
5225 llvm::MDNode *Back =
nullptr;
5226 if (!LexicalBlockStack.empty())
5227 Back = LexicalBlockStack.back().get();
5228 LexicalBlockStack.emplace_back(DBuilder.createLexicalBlock(
5230 getColumnNumber(CurLoc)));
5233void CGDebugInfo::AppendAddressSpaceXDeref(
5235 std::optional<unsigned> DWARFAddressSpace =
5237 if (!DWARFAddressSpace)
5240 Expr.push_back(llvm::dwarf::DW_OP_constu);
5241 Expr.push_back(*DWARFAddressSpace);
5242 Expr.push_back(llvm::dwarf::DW_OP_swap);
5243 Expr.push_back(llvm::dwarf::DW_OP_xderef);
5252 Builder.SetCurrentDebugLocation(llvm::DILocation::get(
5253 CGM.getLLVMContext(), getLineNumber(Loc), getColumnNumber(Loc),
5254 LexicalBlockStack.back(), CurInlinedAt));
5256 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
5260 CreateLexicalBlock(Loc);
5265 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5270 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
5273 LexicalBlockStack.pop_back();
5277 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5278 unsigned RCount = FnBeginRegionCount.back();
5279 assert(RCount <= LexicalBlockStack.size() &&
"Region stack mismatch");
5282 while (LexicalBlockStack.size() != RCount) {
5285 LexicalBlockStack.pop_back();
5287 FnBeginRegionCount.pop_back();
5289 if (Fn && Fn->getSubprogram())
5290 DBuilder.finalizeSubprogram(Fn->getSubprogram());
5293CGDebugInfo::BlockByRefType
5294CGDebugInfo::EmitTypeForVarWithBlocksAttr(
const VarDecl *VD,
5295 uint64_t *XOffset) {
5298 uint64_t FieldSize, FieldOffset;
5299 uint32_t FieldAlign;
5301 llvm::DIFile *Unit = getOrCreateFile(VD->
getLocation());
5306 EltTys.push_back(CreateMemberType(Unit, FType,
"__isa", &FieldOffset));
5307 EltTys.push_back(CreateMemberType(Unit, FType,
"__forwarding", &FieldOffset));
5309 EltTys.push_back(CreateMemberType(Unit, FType,
"__flags", &FieldOffset));
5310 EltTys.push_back(CreateMemberType(Unit, FType,
"__size", &FieldOffset));
5313 if (HasCopyAndDispose) {
5316 CreateMemberType(Unit, FType,
"__copy_helper", &FieldOffset));
5318 CreateMemberType(Unit, FType,
"__destroy_helper", &FieldOffset));
5320 bool HasByrefExtendedLayout;
5323 HasByrefExtendedLayout) &&
5324 HasByrefExtendedLayout) {
5327 CreateMemberType(Unit, FType,
"__byref_variable_layout", &FieldOffset));
5336 CharUnits NumPaddingBytes = AlignedOffsetInBytes - FieldOffsetInBytes;
5339 llvm::APInt pad(32, NumPaddingBytes.
getQuantity());
5342 EltTys.push_back(CreateMemberType(Unit, FType,
"", &FieldOffset));
5347 llvm::DIType *WrappedTy = getOrCreateType(FType, Unit);
5348 FieldSize = CGM.getContext().getTypeSize(FType);
5349 FieldAlign = CGM.getContext().toBits(Align);
5351 *XOffset = FieldOffset;
5352 llvm::DIType *FieldTy = DBuilder.createMemberType(
5353 Unit, VD->
getName(), Unit, 0, FieldSize, FieldAlign, FieldOffset,
5354 llvm::DINode::FlagZero, WrappedTy);
5355 EltTys.push_back(FieldTy);
5356 FieldOffset += FieldSize;
5358 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
5359 return {DBuilder.createStructType(Unit,
"", Unit, 0, FieldOffset, 0,
5360 llvm::DINode::FlagZero,
nullptr, Elements),
5364llvm::DILocalVariable *CGDebugInfo::EmitDeclare(
const VarDecl *VD,
5365 llvm::Value *Storage,
5366 std::optional<unsigned> ArgNo,
5368 const bool UsePointerValue) {
5369 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
5370 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5371 if (VD->
hasAttr<NoDebugAttr>())
5376 llvm::DIFile *Unit =
nullptr;
5377 if (!VarIsArtificial)
5381 if (VD->
hasAttr<BlocksAttr>())
5382 Ty = EmitTypeForVarWithBlocksAttr(VD, &XOffset).WrappedType;
5384 Ty = getOrCreateType(VD->
getType(), Unit);
5394 if (!VarIsArtificial) {
5398 SmallVector<uint64_t, 13> Expr;
5399 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
5406 Flags |= llvm::DINode::FlagArtificial;
5410 unsigned AddressSpace = CGM.getTypes().getTargetAddressSpace(VD->
getType());
5411 AppendAddressSpaceXDeref(AddressSpace, Expr);
5415 if (
const auto *IPD = dyn_cast<ImplicitParamDecl>(VD)) {
5418 Flags |= llvm::DINode::FlagObjectPointer;
5419 }
else if (
const auto *PVD = dyn_cast<ParmVarDecl>(VD)) {
5420 if (PVD->isExplicitObjectParameter())
5421 Flags |= llvm::DINode::FlagObjectPointer;
5429 StringRef Name = VD->
getName();
5430 if (!Name.empty()) {
5436 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5438 offset = CGM.getContext().toCharUnitsFromBits(
5441 Expr.push_back(llvm::dwarf::DW_OP_deref);
5442 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5444 offset = CGM.getContext().toCharUnitsFromBits(XOffset);
5447 }
else if (
const auto *RT = dyn_cast<RecordType>(VD->
getType())) {
5459 for (
const auto *Field : RD->
fields()) {
5460 llvm::DIType *FieldTy = getOrCreateType(
Field->getType(), Unit);
5461 StringRef FieldName =
Field->getName();
5469 auto *D = DBuilder.createAutoVariable(
5470 Scope, FieldName, Unit,
Line, FieldTy,
5471 CGM.getCodeGenOpts().OptimizationLevel != 0,
5472 Flags | llvm::DINode::FlagArtificial, FieldAlign);
5475 DBuilder.insertDeclare(Storage, D, DBuilder.createExpression(Expr),
5476 llvm::DILocation::get(CGM.getLLVMContext(),
Line,
5479 Builder.GetInsertBlock());
5487 if (UsePointerValue) {
5488 assert(!llvm::is_contained(Expr, llvm::dwarf::DW_OP_deref) &&
5489 "Debug info already contains DW_OP_deref.");
5490 Expr.push_back(llvm::dwarf::DW_OP_deref);
5494 llvm::DILocalVariable *D =
nullptr;
5496 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(VD);
5497 D = DBuilder.createParameterVariable(
5498 Scope, Name, *ArgNo, Unit,
Line, Ty,
5499 CGM.getCodeGenOpts().OptimizationLevel != 0, Flags, Annotations);
5508 auto RemapCoroArgToLocalVar = [&]() -> llvm::DILocalVariable * {
5514 auto Iter = llvm::find_if(CoroutineParameterMappings, [&](
auto &Pair) {
5515 Stmt *StmtPtr =
const_cast<Stmt *
>(Pair.second);
5516 if (DeclStmt *DeclStmtPtr = dyn_cast<DeclStmt>(StmtPtr)) {
5517 DeclGroupRef DeclGroup = DeclStmtPtr->getDeclGroup();
5519 if (VD == dyn_cast_or_null<VarDecl>(
Decl))
5525 if (Iter != CoroutineParameterMappings.end()) {
5526 ParmVarDecl *PD =
const_cast<ParmVarDecl *
>(Iter->first);
5527 auto Iter2 = llvm::find_if(ParamDbgMappings, [&](
auto &DbgPair) {
5528 return DbgPair.first == PD && DbgPair.second->getScope() == Scope;
5530 if (Iter2 != ParamDbgMappings.end())
5531 return const_cast<llvm::DILocalVariable *
>(Iter2->second);
5537 D = RemapCoroArgToLocalVar();
5540 D = DBuilder.createAutoVariable(
5541 Scope, Name, Unit,
Line, Ty,
5542 CGM.getCodeGenOpts().OptimizationLevel != 0, Flags, Align);
5545 DBuilder.insertDeclare(Storage, D, DBuilder.createExpression(Expr),
5546 llvm::DILocation::get(CGM.getLLVMContext(),
Line,
5547 Column, Scope, CurInlinedAt),
5548 Builder.GetInsertBlock());
5553llvm::DILocalVariable *CGDebugInfo::EmitDeclare(
const BindingDecl *BD,
5554 llvm::Value *Storage,
5555 std::optional<unsigned> ArgNo,
5557 const bool UsePointerValue) {
5558 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
5559 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5560 if (BD->
hasAttr<NoDebugAttr>())
5567 llvm::DIFile *Unit = getOrCreateFile(BD->
getLocation());
5568 llvm::DIType *Ty = getOrCreateType(BD->
getType(), Unit);
5576 unsigned AddressSpace = CGM.getTypes().getTargetAddressSpace(BD->
getType());
5578 SmallVector<uint64_t, 3> Expr;
5579 AppendAddressSpaceXDeref(AddressSpace, Expr);
5584 if (UsePointerValue) {
5585 assert(!llvm::is_contained(Expr, llvm::dwarf::DW_OP_deref) &&
5586 "Debug info already contains DW_OP_deref.");
5587 Expr.push_back(llvm::dwarf::DW_OP_deref);
5592 StringRef Name = BD->
getName();
5595 llvm::DILocalVariable *D = DBuilder.createAutoVariable(
5596 Scope, Name, Unit,
Line, Ty, CGM.getCodeGenOpts().OptimizationLevel != 0,
5597 llvm::DINode::FlagZero, Align);
5599 if (
const MemberExpr *ME = dyn_cast<MemberExpr>(BD->
getBinding())) {
5600 if (
const FieldDecl *FD = dyn_cast<FieldDecl>(ME->getMemberDecl())) {
5601 const unsigned fieldIndex = FD->getFieldIndex();
5602 const clang::CXXRecordDecl *parent =
5603 (
const CXXRecordDecl *)FD->getParent();
5604 const ASTRecordLayout &layout =
5605 CGM.getContext().getASTRecordLayout(parent);
5607 if (FD->isBitField()) {
5608 const CGRecordLayout &RL =
5609 CGM.getTypes().getCGRecordLayout(FD->getParent());
5614 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5620 ? llvm::dwarf::DW_OP_LLVM_extract_bits_sext
5621 : llvm::dwarf::DW_OP_LLVM_extract_bits_zext);
5622 Expr.push_back(Info.
Offset);
5625 const uint64_t TypeSize = CGM.getContext().getTypeSize(BD->
getType());
5626 Expr.push_back(std::min((uint64_t)Info.
Size, TypeSize));
5627 }
else if (fieldOffset != 0) {
5628 assert(fieldOffset % CGM.getContext().getCharWidth() == 0 &&
5629 "Unexpected non-bitfield with non-byte-aligned offset");
5630 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5632 CGM.getContext().toCharUnitsFromBits(fieldOffset).getQuantity());
5635 }
else if (
const ArraySubscriptExpr *ASE =
5636 dyn_cast<ArraySubscriptExpr>(BD->
getBinding())) {
5637 if (
const IntegerLiteral *IL = dyn_cast<IntegerLiteral>(ASE->getIdx())) {
5638 const uint64_t value = IL->getValue().getZExtValue();
5639 const uint64_t typeSize = CGM.getContext().getTypeSize(BD->
getType());
5642 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5643 Expr.push_back(CGM.getContext()
5644 .toCharUnitsFromBits(value * typeSize)
5651 DBuilder.insertDeclare(Storage, D, DBuilder.createExpression(Expr),
5652 llvm::DILocation::get(CGM.getLLVMContext(),
Line,
5653 Column, Scope, CurInlinedAt),
5654 Builder.GetInsertBlock());
5659llvm::DILocalVariable *
5662 const bool UsePointerValue) {
5663 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
5665 if (
auto *DD = dyn_cast<DecompositionDecl>(VD)) {
5667 EmitDeclare(B, Storage, std::nullopt, Builder,
5674 return EmitDeclare(VD, Storage, std::nullopt, Builder, UsePointerValue);
5678 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
5679 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5681 if (D->
hasAttr<NoDebugAttr>())
5685 llvm::DIFile *Unit = getOrCreateFile(D->
getLocation());
5691 StringRef Name = D->
getName();
5697 CGM.getCodeGenOpts().OptimizationLevel != 0);
5700 DBuilder.insertLabel(L,
5701 llvm::DILocation::get(CGM.getLLVMContext(),
Line,
Column,
5702 Scope, CurInlinedAt),
5703 Builder.GetInsertBlock()->end());
5706llvm::DIType *CGDebugInfo::CreateSelfType(
const QualType &QualTy,
5708 llvm::DIType *CachedTy = getTypeOrNull(QualTy);
5711 return DBuilder.createObjectPointerType(Ty,
true);
5716 const CGBlockInfo &blockInfo, llvm::Instruction *InsertPoint) {
5717 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
5718 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5720 if (Builder.GetInsertBlock() ==
nullptr)
5722 if (VD->
hasAttr<NoDebugAttr>())
5725 bool isByRef = VD->
hasAttr<BlocksAttr>();
5727 uint64_t XOffset = 0;
5728 llvm::DIFile *Unit = getOrCreateFile(VD->
getLocation());
5731 Ty = EmitTypeForVarWithBlocksAttr(VD, &XOffset).WrappedType;
5733 Ty = getOrCreateType(VD->
getType(), Unit);
5737 if (
const auto *IPD = dyn_cast<ImplicitParamDecl>(VD))
5739 Ty = CreateSelfType(VD->
getType(), Ty);
5742 const unsigned Line =
5746 const llvm::DataLayout &target = CGM.getDataLayout();
5753 addr.push_back(llvm::dwarf::DW_OP_deref);
5754 addr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5757 addr.push_back(llvm::dwarf::DW_OP_deref);
5758 addr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5761 CGM.getContext().toCharUnitsFromBits(target.getPointerSizeInBits(0));
5763 addr.push_back(llvm::dwarf::DW_OP_deref);
5764 addr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5766 offset = CGM.getContext().toCharUnitsFromBits(XOffset);
5772 auto *D = DBuilder.createAutoVariable(
5774 Line, Ty,
false, llvm::DINode::FlagZero, Align);
5777 auto DL = llvm::DILocation::get(CGM.getLLVMContext(),
Line,
Column,
5778 LexicalBlockStack.back(), CurInlinedAt);
5779 auto *
Expr = DBuilder.createExpression(addr);
5781 DBuilder.insertDeclare(Storage, D,
Expr, DL, InsertPoint->getIterator());
5783 DBuilder.insertDeclare(Storage, D,
Expr, DL, Builder.GetInsertBlock());
5786llvm::DILocalVariable *
5789 bool UsePointerValue) {
5790 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
5791 return EmitDeclare(VD, AI, ArgNo, Builder, UsePointerValue);
5795struct BlockLayoutChunk {
5796 uint64_t OffsetInBits;
5799bool operator<(
const BlockLayoutChunk &l,
const BlockLayoutChunk &r) {
5800 return l.OffsetInBits < r.OffsetInBits;
5804void CGDebugInfo::collectDefaultFieldsForBlockLiteralDeclare(
5806 const llvm::StructLayout &BlockLayout, llvm::DIFile *Unit,
5807 SmallVectorImpl<llvm::Metadata *> &Fields) {
5811 if (CGM.getLangOpts().OpenCL) {
5812 Fields.push_back(createFieldType(
"__size", Context.
IntTy, Loc,
AS_public,
5813 BlockLayout.getElementOffsetInBits(0),
5815 Fields.push_back(createFieldType(
"__align", Context.
IntTy, Loc,
AS_public,
5816 BlockLayout.getElementOffsetInBits(1),
5820 BlockLayout.getElementOffsetInBits(0),
5822 Fields.push_back(createFieldType(
"__flags", Context.
IntTy, Loc,
AS_public,
5823 BlockLayout.getElementOffsetInBits(1),
5827 BlockLayout.getElementOffsetInBits(2), Unit, Unit));
5828 auto *FnTy =
Block.getBlockExpr()->getFunctionType();
5829 auto FnPtrType = CGM.getContext().getPointerType(FnTy->desugar());
5830 Fields.push_back(createFieldType(
"__FuncPtr", FnPtrType, Loc,
AS_public,
5831 BlockLayout.getElementOffsetInBits(3),
5833 Fields.push_back(createFieldType(
5838 Loc,
AS_public, BlockLayout.getElementOffsetInBits(4), Unit, Unit));
5845 llvm::AllocaInst *Alloca,
5847 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
5853 llvm::DIFile *tunit = getOrCreateFile(loc);
5854 unsigned line = getLineNumber(loc);
5855 unsigned column = getColumnNumber(loc);
5860 const llvm::StructLayout *blockLayout =
5864 collectDefaultFieldsForBlockLiteralDeclare(block,
C, loc, *blockLayout, tunit,
5873 BlockLayoutChunk chunk;
5874 chunk.OffsetInBits =
5875 blockLayout->getElementOffsetInBits(block.
CXXThisIndex);
5876 chunk.Capture =
nullptr;
5877 chunks.push_back(chunk);
5881 for (
const auto &capture :
blockDecl->captures()) {
5882 const VarDecl *variable = capture.getVariable();
5889 BlockLayoutChunk chunk;
5890 chunk.OffsetInBits =
5891 blockLayout->getElementOffsetInBits(captureInfo.
getIndex());
5892 chunk.Capture = &capture;
5893 chunks.push_back(chunk);
5897 llvm::array_pod_sort(chunks.begin(), chunks.end());
5899 for (
const BlockLayoutChunk &Chunk : chunks) {
5900 uint64_t offsetInBits = Chunk.OffsetInBits;
5907 cast_or_null<CXXMethodDecl>(
blockDecl->getNonClosureContext()))
5909 else if (
auto *RDecl = dyn_cast<CXXRecordDecl>(
blockDecl->getParent()))
5910 type = CGM.getContext().getCanonicalTagType(RDecl);
5912 llvm_unreachable(
"unexpected block declcontext");
5914 fields.push_back(createFieldType(
"this",
type, loc,
AS_public,
5915 offsetInBits, tunit, tunit));
5920 StringRef name = variable->
getName();
5922 llvm::DIType *fieldType;
5924 TypeInfo PtrInfo =
C.getTypeInfo(
C.VoidPtrTy);
5929 EmitTypeForVarWithBlocksAttr(variable, &xoffset).BlockByRefWrapper;
5930 fieldType = DBuilder.createPointerType(fieldType, PtrInfo.
Width);
5931 fieldType = DBuilder.createMemberType(tunit, name, tunit, line,
5932 PtrInfo.
Width, Align, offsetInBits,
5933 llvm::DINode::FlagZero, fieldType);
5937 offsetInBits, Align, tunit, tunit);
5939 fields.push_back(fieldType);
5943 llvm::raw_svector_ostream(typeName)
5944 <<
"__block_literal_" << CGM.getUniqueBlockCount();
5946 llvm::DINodeArray fieldsArray = DBuilder.getOrCreateArray(fields);
5948 llvm::DIType *
type =
5949 DBuilder.createStructType(tunit, typeName.str(), tunit, line,
5950 CGM.getContext().toBits(block.
BlockSize), 0,
5951 llvm::DINode::FlagZero,
nullptr, fieldsArray);
5952 type = DBuilder.createPointerType(
type, CGM.PointerWidthInBits);
5955 llvm::DINode::DIFlags flags = llvm::DINode::FlagArtificial;
5959 auto *debugVar = DBuilder.createParameterVariable(
5960 scope, Name, ArgNo, tunit, line,
type,
5961 CGM.getCodeGenOpts().OptimizationLevel != 0, flags);
5964 DBuilder.insertDeclare(Alloca, debugVar, DBuilder.createExpression(),
5965 llvm::DILocation::get(CGM.getLLVMContext(), line,
5966 column, scope, CurInlinedAt),
5967 Builder.GetInsertBlock());
5970llvm::DIDerivedType *
5971CGDebugInfo::getOrCreateStaticDataMemberDeclarationOrNull(
const VarDecl *D) {
5976 if (MI != StaticDataMemberCache.end()) {
5977 assert(MI->second &&
"Static data member declaration should still exist");
5988llvm::DIGlobalVariableExpression *CGDebugInfo::CollectAnonRecordDecls(
5989 const RecordDecl *RD, llvm::DIFile *Unit,
unsigned LineNo,
5990 StringRef LinkageName, llvm::GlobalVariable *Var, llvm::DIScope *DContext) {
5991 llvm::DIGlobalVariableExpression *GVE =
nullptr;
5993 for (
const auto *Field : RD->
fields()) {
5994 llvm::DIType *FieldTy = getOrCreateType(Field->getType(), Unit);
5995 StringRef FieldName = Field->getName();
5998 if (FieldName.empty()) {
5999 if (
const auto *RT = dyn_cast<RecordType>(Field->getType()))
6000 GVE = CollectAnonRecordDecls(RT->getDecl()->getDefinitionOrSelf(), Unit,
6001 LineNo, LinkageName, Var, DContext);
6005 GVE = DBuilder.createGlobalVariableExpression(
6006 DContext, FieldName, LinkageName, Unit, LineNo, FieldTy,
6007 Var->hasLocalLinkage());
6008 Var->addDebugInfo(GVE);
6020 const auto *RD = dyn_cast<CXXRecordDecl>(RT->getDecl());
6025 auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD);
6036 struct ReferencesAnonymous
6038 bool RefAnon =
false;
6039 bool VisitRecordType(RecordType *RT) {
6047 ReferencesAnonymous RT;
6060struct ReconstitutableType :
public RecursiveASTVisitor<ReconstitutableType> {
6061 bool Reconstitutable =
true;
6062 bool VisitVectorType(VectorType *FT) {
6063 Reconstitutable =
false;
6066 bool VisitAtomicType(AtomicType *FT) {
6067 Reconstitutable =
false;
6070 bool TraverseEnumType(EnumType *ET,
bool =
false) {
6073 const EnumDecl *ED = ET->getDecl();
6075 Reconstitutable =
false;
6079 Reconstitutable =
false;
6084 bool VisitFunctionProtoType(FunctionProtoType *FT) {
6088 return Reconstitutable;
6090 bool VisitRecordType(RecordType *RT,
bool =
false) {
6092 Reconstitutable =
false;
6102 ReconstitutableType
T;
6104 return T.Reconstitutable;
6107bool CGDebugInfo::HasReconstitutableArgs(
6108 ArrayRef<TemplateArgument> Args)
const {
6109 return llvm::all_of(Args, [&](
const TemplateArgument &TA) {
6149 llvm_unreachable(
"Other, unresolved, template arguments should "
6150 "not be seen here");
6155std::string CGDebugInfo::GetName(
const Decl *D,
bool Qualified,
6156 bool *NameIsSimplified)
const {
6158 llvm::raw_string_ostream
OS(Name);
6159 const NamedDecl *ND = dyn_cast<NamedDecl>(D);
6162 llvm::codegenoptions::DebugTemplateNamesKind TemplateNamesKind =
6163 CGM.getCodeGenOpts().getDebugSimpleTemplateNames();
6165 if (!CGM.getCodeGenOpts().hasReducedDebugInfo())
6166 TemplateNamesKind = llvm::codegenoptions::DebugTemplateNamesKind::Full;
6168 std::optional<TemplateArgs> Args;
6170 bool IsOperatorOverload =
false;
6171 if (
auto *RD = dyn_cast<CXXRecordDecl>(ND)) {
6172 Args = GetTemplateArgs(RD);
6173 }
else if (
auto *FD = dyn_cast<FunctionDecl>(ND)) {
6174 Args = GetTemplateArgs(FD);
6176 IsOperatorOverload |=
6179 }
else if (
auto *VD = dyn_cast<VarDecl>(ND)) {
6180 Args = GetTemplateArgs(VD);
6204 bool Reconstitutable =
6205 Args && HasReconstitutableArgs(Args->Args) && !IsOperatorOverload;
6207 PrintingPolicy PP = getPrintingPolicy();
6209 if (TemplateNamesKind == llvm::codegenoptions::DebugTemplateNamesKind::Full ||
6214 if (NameIsSimplified)
6215 *NameIsSimplified =
true;
6216 bool Mangled = TemplateNamesKind ==
6217 llvm::codegenoptions::DebugTemplateNamesKind::Mangled;
6223 std::string EncodedOriginalName;
6224 llvm::raw_string_ostream EncodedOriginalNameOS(EncodedOriginalName);
6229 printTemplateArgumentList(OS, Args->Args, PP);
6230 printTemplateArgumentList(EncodedOriginalNameOS, Args->Args, PP);
6232 std::string CanonicalOriginalName;
6233 llvm::raw_string_ostream OriginalOS(CanonicalOriginalName);
6235 assert(EncodedOriginalName == CanonicalOriginalName);
6244 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
6245 if (D->
hasAttr<NoDebugAttr>())
6248 llvm::TimeTraceScope TimeScope(
"DebugGlobalVariable", [&]() {
6249 return GetName(D,
true);
6255 if (Cached != DeclCache.end())
6256 return Var->addDebugInfo(
6260 llvm::DIFile *Unit =
nullptr;
6261 llvm::DIScope *DContext =
nullptr;
6263 StringRef DeclName, LinkageName;
6265 llvm::MDTuple *TemplateParameters =
nullptr;
6266 collectVarDeclProps(D, Unit, LineNo,
T, DeclName, LinkageName,
6267 TemplateParameters, DContext);
6271 llvm::DIGlobalVariableExpression *GVE =
nullptr;
6276 if (
T->isUnionType() && DeclName.empty()) {
6277 const auto *RD =
T->castAsRecordDecl();
6279 "unnamed non-anonymous struct or union?");
6280 GVE = CollectAnonRecordDecls(RD, Unit, LineNo, LinkageName, Var, DContext);
6285 unsigned AddressSpace = CGM.getTypes().getTargetAddressSpace(D->
getType());
6286 if (CGM.getLangOpts().CUDA && CGM.getLangOpts().CUDAIsDevice) {
6287 if (D->
hasAttr<CUDASharedAttr>())
6290 else if (D->
hasAttr<CUDAConstantAttr>())
6294 AppendAddressSpaceXDeref(AddressSpace,
Expr);
6296 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(D);
6297 GVE = DBuilder.createGlobalVariableExpression(
6298 DContext, DeclName, LinkageName, Unit, LineNo, getOrCreateType(
T, Unit),
6299 Var->hasLocalLinkage(),
true,
6300 Expr.empty() ?
nullptr : DBuilder.createExpression(
Expr),
6301 getOrCreateStaticDataMemberDeclarationOrNull(D), TemplateParameters,
6302 Align, Annotations);
6303 Var->addDebugInfo(GVE);
6309 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
6310 if (VD->
hasAttr<NoDebugAttr>())
6312 llvm::TimeTraceScope TimeScope(
"DebugConstGlobalVariable", [&]() {
6313 return GetName(VD,
true);
6318 llvm::DIFile *Unit = getOrCreateFile(VD->
getLocation());
6319 StringRef Name = VD->
getName();
6320 llvm::DIType *Ty = getOrCreateType(VD->
getType(), Unit);
6322 if (
const auto *ECD = dyn_cast<EnumConstantDecl>(VD)) {
6324 if (CGM.getCodeGenOpts().EmitCodeView) {
6335 CanQualType T = CGM.getContext().getCanonicalTagType(ED);
6336 [[maybe_unused]] llvm::DIType *EDTy = getOrCreateType(
T, Unit);
6337 assert(EDTy->getTag() == llvm::dwarf::DW_TAG_enumeration_type);
6347 auto *VarD = dyn_cast<VarDecl>(VD);
6348 if (VarD && VarD->isStaticDataMember()) {
6350 getDeclContextDescriptor(VarD);
6355 RetainedTypes.push_back(
6356 CGM.getContext().getCanonicalTagType(RD).getAsOpaquePtr());
6360 llvm::DIScope *DContext = getDeclContextDescriptor(VD);
6362 auto &GV = DeclCache[VD];
6366 llvm::DIExpression *InitExpr = createConstantValueExpression(VD,
Init);
6367 llvm::MDTuple *TemplateParameters =
nullptr;
6371 llvm::DINodeArray parameterNodes = CollectVarTemplateParams(VarD, &*Unit);
6372 TemplateParameters = parameterNodes.get();
6375 GV.reset(DBuilder.createGlobalVariableExpression(
6376 DContext, Name, StringRef(), Unit, getLineNumber(VD->
getLocation()), Ty,
6377 true,
true, InitExpr, getOrCreateStaticDataMemberDeclarationOrNull(VarD),
6378 TemplateParameters, Align));
6383 assert(CGM.getCodeGenOpts().hasReducedDebugInfo());
6384 if (D->
hasAttr<NoDebugAttr>())
6388 llvm::DIFile *Unit = getOrCreateFile(D->
getLocation());
6389 StringRef Name = D->
getName();
6390 llvm::DIType *Ty = getOrCreateType(D->
getType(), Unit);
6392 llvm::DIScope *DContext = getDeclContextDescriptor(D);
6393 llvm::DIGlobalVariableExpression *GVE =
6394 DBuilder.createGlobalVariableExpression(
6395 DContext, Name, StringRef(), Unit, getLineNumber(D->
getLocation()),
6396 Ty,
false,
false,
nullptr,
nullptr,
nullptr, Align);
6397 Var->addDebugInfo(GVE);
6404 if (CGM.getCodeGenOpts().getDebugInfo() <=
6405 llvm::codegenoptions::DebugLineTablesOnly)
6408 llvm::DILocation *DIL =
Value->getDebugLoc().get();
6412 llvm::DIFile *Unit = DIL->getFile();
6413 llvm::DIType *
Type = getOrCreateType(Ty, Unit);
6418 if (llvm::LoadInst *Load = dyn_cast<llvm::LoadInst>(
Value)) {
6419 llvm::Value *Var = Load->getPointerOperand();
6424 auto DeclareTypeMatches = [&](llvm::DbgVariableRecord *DbgDeclare) {
6425 return DbgDeclare->getVariable()->getType() ==
Type;
6427 if (any_of(llvm::findDVRDeclares(Var), DeclareTypeMatches))
6431 llvm::DILocalVariable *D =
6432 DBuilder.createAutoVariable(LexicalBlockStack.back(),
"",
nullptr, 0,
6433 Type,
false, llvm::DINode::FlagArtificial);
6435 if (
auto InsertPoint =
Value->getInsertionPointAfterDef()) {
6436 DBuilder.insertDbgValue(
Value, D, DBuilder.createExpression(), DIL,
6446 if (!CGM.getCodeGenOpts().hasReducedDebugInfo())
6450 if (D->
hasAttr<NoDebugAttr>())
6453 auto AliaseeDecl = CGM.getMangledNameDecl(GV->getName());
6468 if (!(DI = getDeclarationOrDefinition(
6469 AliaseeDecl.getCanonicalDecl().getDecl())))
6472 llvm::DIScope *DContext = getDeclContextDescriptor(D);
6475 llvm::DIImportedEntity *ImportDI = DBuilder.createImportedDeclaration(
6476 DContext, DI, getOrCreateFile(Loc), getLineNumber(Loc), D->getName());
6490 llvm::DIFile *
File = getOrCreateFile(Loc);
6491 llvm::DIGlobalVariableExpression *Debug =
6492 DBuilder.createGlobalVariableExpression(
6493 nullptr, StringRef(), StringRef(), getOrCreateFile(Loc),
6494 getLineNumber(Loc), getOrCreateType(S->
getType(),
File),
true);
6495 GV->addDebugInfo(Debug);
6498llvm::DIScope *CGDebugInfo::getCurrentContextDescriptor(
const Decl *D) {
6499 if (!LexicalBlockStack.empty())
6500 return LexicalBlockStack.back();
6501 llvm::DIScope *Mod = getParentModuleOrNull(D);
6502 return getContextDescriptor(D, Mod ? Mod : TheCU);
6506 if (!CGM.getCodeGenOpts().hasReducedDebugInfo())
6510 CGM.getCodeGenOpts().DebugExplicitImport) {
6514 DBuilder.createImportedModule(
6516 getOrCreateNamespace(NSDecl), getOrCreateFile(Loc), getLineNumber(Loc));
6521 if (llvm::DINode *
Target =
6524 DBuilder.createImportedDeclaration(
6526 getOrCreateFile(Loc), getLineNumber(Loc));
6531 if (!CGM.getCodeGenOpts().hasReducedDebugInfo())
6534 "We shouldn't be codegening an invalid UsingDecl containing no decls");
6536 for (
const auto *USD : UD.
shadows()) {
6541 if (
const auto *FD = dyn_cast<FunctionDecl>(USD->getUnderlyingDecl()))
6542 if (
const auto *AT = FD->getType()
6545 if (AT->getDeducedType().isNull())
6556 if (!CGM.getCodeGenOpts().hasReducedDebugInfo())
6559 "We shouldn't be codegening an invalid UsingEnumDecl"
6560 " containing no decls");
6562 for (
const auto *USD : UD.
shadows())
6567 if (CGM.getCodeGenOpts().getDebuggerTuning() != llvm::DebuggerKind::LLDB)
6569 if (
Module *M = ID.getImportedModule()) {
6571 auto Loc = ID.getLocation();
6572 DBuilder.createImportedDeclaration(
6573 getCurrentContextDescriptor(
cast<Decl>(ID.getDeclContext())),
6574 getOrCreateModuleRef(Info, DebugTypeExtRefs), getOrCreateFile(Loc),
6575 getLineNumber(Loc));
6579llvm::DIImportedEntity *
6581 if (!CGM.getCodeGenOpts().hasReducedDebugInfo())
6583 auto &VH = NamespaceAliasCache[&NA];
6586 llvm::DIImportedEntity *R;
6588 if (
const auto *Underlying =
6591 R = DBuilder.createImportedDeclaration(
6594 getLineNumber(Loc), NA.
getName());
6596 R = DBuilder.createImportedDeclaration(
6599 getOrCreateFile(Loc), getLineNumber(Loc), NA.
getName());
6605CGDebugInfo::getOrCreateNamespace(
const NamespaceDecl *NSDecl) {
6609 auto I = NamespaceCache.find(NSDecl);
6610 if (I != NamespaceCache.end())
6613 llvm::DIScope *Context = getDeclContextDescriptor(NSDecl);
6615 llvm::DINamespace *NS =
6616 DBuilder.createNameSpace(Context, NSDecl->
getName(), NSDecl->
isInline());
6617 NamespaceCache[NSDecl].reset(NS);
6622 assert(TheCU &&
"no main compile unit");
6623 TheCU->setDWOId(Signature);
6629 for (
size_t i = 0; i != ObjCInterfaceCache.size(); ++i) {
6630 ObjCInterfaceCacheEntry E = ObjCInterfaceCache[i];
6632 ? CreateTypeDefinition(E.Type, E.Unit)
6634 DBuilder.replaceTemporary(llvm::TempDIType(E.Decl), Ty);
6638 for (
const auto &P : ObjCMethodCache) {
6639 if (P.second.empty())
6642 QualType QTy(P.first->getTypeForDecl(), 0);
6644 assert(It != TypeCache.end());
6646 llvm::DICompositeType *InterfaceDecl =
6649 auto CurElts = InterfaceDecl->getElements();
6653 for (
auto &SubprogramDirect : P.second)
6654 if (CGM.getCodeGenOpts().DwarfVersion >= 5 || SubprogramDirect.getInt())
6655 EltTys.push_back(SubprogramDirect.getPointer());
6657 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
6658 DBuilder.replaceArrays(InterfaceDecl, Elements);
6661 for (
const auto &P : ReplaceMap) {
6664 assert(Ty->isForwardDecl());
6666 auto It = TypeCache.find(P.first);
6667 assert(It != TypeCache.end());
6670 DBuilder.replaceTemporary(llvm::TempDIType(Ty),
6674 for (
const auto &P : FwdDeclReplaceMap) {
6677 llvm::Metadata *Repl;
6679 auto It = DeclCache.find(P.first);
6683 if (It == DeclCache.end())
6688 if (
auto *GVE = dyn_cast_or_null<llvm::DIGlobalVariableExpression>(Repl))
6689 Repl = GVE->getVariable();
6695 for (
auto &RT : RetainedTypes)
6696 if (
auto MD = TypeCache[RT])
6699 DBuilder.finalize();
6704 if (CGM.getCodeGenOpts().hasReducedDebugInfo())
6705 if (
auto *DieTy = getOrCreateType(Ty, TheCU->getFile()))
6706 DBuilder.retainType(DieTy);
6710 if (CGM.getCodeGenOpts().hasMaybeUnusedDebugInfo())
6711 if (
auto *DieTy = getOrCreateType(Ty, TheCU->getFile()))
6712 DBuilder.retainType(DieTy);
6716 if (LexicalBlockStack.empty())
6717 return llvm::DebugLoc();
6719 llvm::MDNode *
Scope = LexicalBlockStack.back();
6720 return llvm::DILocation::get(CGM.getLLVMContext(), getLineNumber(Loc),
6721 getColumnNumber(Loc),
Scope);
6727 if (CGM.getCodeGenOpts().OptimizationLevel == 0 ||
6728 DebugKind == llvm::codegenoptions::NoDebugInfo ||
6729 DebugKind == llvm::codegenoptions::LocTrackingOnly ||
6730 !CGM.getCodeGenOpts().DebugCallSiteInfo)
6731 return llvm::DINode::FlagZero;
6736 bool SupportsDWARFv4Ext =
6737 CGM.getCodeGenOpts().DwarfVersion == 4 &&
6738 (CGM.getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::LLDB ||
6739 CGM.getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::GDB);
6741 if (!SupportsDWARFv4Ext && CGM.getCodeGenOpts().DwarfVersion < 5)
6742 return llvm::DINode::FlagZero;
6744 return llvm::DINode::FlagAllCallsDescribed;
6755 return DBuilder.createConstantValueExpression(
6756 Val.
getFloat().bitcastToAPInt().getZExtValue());
6761 llvm::APSInt
const &ValInt = Val.
getInt();
6762 std::optional<uint64_t> ValIntOpt;
6763 if (ValInt.isUnsigned())
6764 ValIntOpt = ValInt.tryZExtValue();
6765 else if (
auto tmp = ValInt.trySExtValue())
6768 ValIntOpt =
static_cast<uint64_t
>(*tmp);
6771 return DBuilder.createConstantValueExpression(ValIntOpt.value());
6776CodeGenFunction::LexicalScope::LexicalScope(CodeGenFunction &
CGF,
6778 : RunCleanupsScope(
CGF), Range(Range), ParentScope(
CGF.CurLexicalScope) {
6779 CGF.CurLexicalScope =
this;
6781 DI->EmitLexicalBlockStart(
CGF.Builder, Range.getBegin());
6786 DI->EmitLexicalBlockEnd(
CGF.Builder, Range.getEnd());
6799#define SANITIZER_CHECK(Enum, Name, Version, Msg) \
6801 Label = "__ubsan_check_" #Name; \
6805#undef SANITIZER_CHECK
6816#define SANITIZER(NAME, ID) \
6817 case SanitizerKind::SO_##ID: \
6818 Label = "__ubsan_check_" NAME; \
6820#include "clang/Basic/Sanitizers.def"
6822 llvm_unreachable(
"unexpected sanitizer kind");
6827 for (
unsigned int i = 0; i < Label.length(); i++)
6828 if (!std::isalpha(Label[i]))
6837 llvm::DILocation *CheckDebugLoc =
Builder.getCurrentDebugLocation();
6839 if (!DI || !CheckDebugLoc)
6840 return CheckDebugLoc;
6841 const auto &AnnotateDebugInfo =
6842 CGM.getCodeGenOpts().SanitizeAnnotateDebugInfo;
6843 if (AnnotateDebugInfo.empty())
6844 return CheckDebugLoc;
6847 if (Ordinals.size() == 1)
6852 if (any_of(Ordinals, [&](
auto Ord) {
return AnnotateDebugInfo.has(Ord); })) {
6856 llvm::DIFile *
File = llvm::DIFile::get(
CGM.getLLVMContext(),
6857 "ubsan_interface.h",
6859 return DI->CreateSyntheticInlineAt(CheckDebugLoc, Label,
File);
6862 return CheckDebugLoc;
6870 assert(!CGF->IsSanitizerScope);
6871 CGF->IsSanitizerScope =
true;
6875 assert(CGF->IsSanitizerScope);
6876 CGF->IsSanitizerScope =
false;
Defines the clang::ASTContext interface.
static bool IsReconstitutableType(QualType QT)
static void stripUnusedQualifiers(Qualifiers &Q)
static std::string SanitizerOrdinalToCheckLabel(SanitizerKind::SanitizerOrdinal Ordinal)
static llvm::Constant * buildConstantDataArrayFromElements(llvm::LLVMContext &Ctx, const APValue &Arr)
Build an llvm::ConstantDataArray from the initialized elements of an APValue array,...
static unsigned getDwarfCC(CallingConv CC, const llvm::Triple &T)
static std::string SanitizerHandlerToCheckLabel(SanitizerHandler Handler)
static bool IsObjCSynthesizedPropertyExplicitParameter(VarDecl const *VD)
Returns true if the specified variable VD is an explicit parameter of a synthesized Objective-C prope...
static bool IsArtificial(VarDecl const *VD)
Returns true if VD is a compiler-generated variable and should be treated as artificial for the purpo...
static bool needsTypeIdentifier(const TagDecl *TD, CodeGenModule &CGM, llvm::DICompileUnit *TheCU)
static bool shouldOmitDefinition(llvm::codegenoptions::DebugInfoKind DebugKind, bool DebugTypeExtRefs, const RecordDecl *RD, const LangOptions &LangOpts)
static llvm::DINode::DIFlags getAccessFlag(AccessSpecifier Access, const RecordDecl *RD)
Convert an AccessSpecifier into the corresponding DINode flag.
static llvm::DINode::DIFlags getRefFlags(const FunctionProtoType *Func)
static QualType UnwrapTypeForDebugInfo(QualType T, const ASTContext &C)
static SourceLocation getMacroDebugLoc(const CodeGenModule &CGM, SourceLocation Loc)
static llvm::dwarf::Tag getTagForRecord(const RecordDecl *RD)
static llvm::SmallVector< TemplateArgument > GetTemplateArgs(const TemplateDecl *TD, const TemplateSpecializationType *Ty)
static bool isFunctionLocalClass(const CXXRecordDecl *RD)
isFunctionLocalClass - Return true if CXXRecordDecl is defined inside a function.
static bool hasCXXMangling(llvm::dwarf::SourceLanguage Lang, bool IsTagDecl)
static uint32_t getDeclAlignIfRequired(const Decl *D, const ASTContext &Ctx)
static bool hasExplicitMemberDefinition(CXXRecordDecl::method_iterator I, CXXRecordDecl::method_iterator End)
static auto getEnumInfo(CodeGenModule &CGM, llvm::DICompileUnit *TheCU, const EnumType *Ty)
static bool canUseCtorHoming(const CXXRecordDecl *RD)
static bool hasDefaultGetterName(const ObjCPropertyDecl *PD, const ObjCMethodDecl *Getter)
static llvm::Constant * tryEmitConstexprArrayAsConstant(CodeGenModule &CGM, const VarDecl *Var, const APValue *Value)
Try to create an llvm::Constant for a constexpr array of integer elements.
static bool isClassOrMethodDLLImport(const CXXRecordDecl *RD)
Return true if the class or any of its methods are marked dllimport.
static llvm::DISourceLanguageName GetDISourceLanguageName(const CodeGenModule &CGM)
static uint32_t getTypeAlignIfRequired(const Type *Ty, const ASTContext &Ctx)
static bool hasDefaultSetterName(const ObjCPropertyDecl *PD, const ObjCMethodDecl *Setter)
static bool isDefinedInClangModule(const RecordDecl *RD)
Does a type definition exist in an imported clang module?
static llvm::dwarf::Tag getNextQualifier(Qualifiers &Q)
static bool IsDecomposedVarDecl(VarDecl const *VD)
Returns true if VD is a a holding variable (aka a VarDecl retrieved using BindingDecl::getHoldingVar)...
static SmallString< 256 > getTypeIdentifier(const TagType *Ty, CodeGenModule &CGM, llvm::DICompileUnit *TheCU)
static bool ReferencesAnonymousEntity(ArrayRef< TemplateArgument > Args)
static llvm::dwarf::SourceLanguage GetSourceLanguage(const CodeGenModule &CGM)
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....
Defines the C++ template declaration subclasses.
#define CC_VLS_CASE(ABI_VLEN)
Defines the LambdaCapture class.
constexpr llvm::StringRef ClangTrapPrefix
static StringRef getTriple(const Command &Job)
#define LIST_SANITIZER_CHECKS
static const NamedDecl * getDefinition(const Decl *D)
Defines the SourceManager interface.
Defines version macros and version-related utility functions for Clang.
APValue - This class implements a discriminated union of [uninitialized] [APSInt] [APFloat],...
bool hasArrayFiller() const
APValue & getArrayInitializedElt(unsigned I)
unsigned getArrayInitializedElts() const
APValue & getArrayFiller()
unsigned getArraySize() const
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
bool getByrefLifetime(QualType Ty, Qualifiers::ObjCLifetime &Lifetime, bool &HasByrefExtendedLayout) const
Returns true, if given type has a known lifetime.
SourceManager & getSourceManager()
const ConstantArrayType * getAsConstantArrayType(QualType T) const
TypedefNameDecl * getTypedefNameForUnnamedTagDecl(const TagDecl *TD)
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
QualType getBlockDescriptorExtendedType() const
Gets the struct used to keep track of the extended descriptor for pointer to blocks.
bool BlockRequiresCopying(QualType Ty, const VarDecl *D)
Returns true iff we need copy/dispose helpers for the given type.
QualType getConstantArrayType(QualType EltTy, const llvm::APInt &ArySize, const Expr *SizeExpr, ArraySizeModifier ASM, unsigned IndexTypeQuals) const
Return the unique reference to the type for a constant array of the specified element type.
TypeInfo getTypeInfo(const Type *T) const
Get the size and alignment of the specified complete type in bits.
QualType getBlockDescriptorType() const
Gets the struct used to keep track of the descriptor for pointer to blocks.
CharUnits getDeclAlign(const Decl *D, bool ForAlignof=false) const
Return a conservative estimate of the alignment of the specified decl D.
uint64_t getTypeSize(QualType T) const
Return the size of the specified (complete) type T, in bits.
DeclaratorDecl * getDeclaratorForUnnamedTagDecl(const TagDecl *TD)
CharUnits toCharUnitsFromBits(int64_t BitSize) const
Convert a size in bits to a size in characters.
ExternalASTSource * getExternalSource() const
Retrieve a pointer to the external AST source associated with this AST context, if any.
CanQualType getCanonicalTagType(const TagDecl *TD) const
uint64_t getFieldOffset(unsigned FieldNo) const
getFieldOffset - Get the offset of the given field index, in bits.
CharUnits getBaseClassOffset(const CXXRecordDecl *Base) const
getBaseClassOffset - Get the offset, in chars, for the given base class.
const CXXRecordDecl * getPrimaryBase() const
getPrimaryBase - Get the primary base for this record.
bool hasExtendableVFPtr() const
hasVFPtr - Does this class have a virtual function table pointer that can be extended by a derived cl...
bool isPrimaryBaseVirtual() const
isPrimaryBaseVirtual - Get whether the primary base for this record is virtual or not.
Abstracts clang modules and precompiled header files and holds everything needed to generate debug in...
Module * getModuleOrNull() const
ASTFileSignature getSignature() const
StringRef getASTFile() const
StringRef getPath() const
std::string getModuleName() const
QualType getElementType() const
QualType getValueType() const
Gets the type contained by this atomic type, i.e.
unsigned shadow_size() const
Return the number of shadowed declarations associated with this using declaration.
shadow_range shadows() const
A binding in a decomposition declaration.
Expr * getBinding() const
Get the expression to which this declaration is bound.
unsigned getNumBits() const
A class which contains all the information about a particular captured value.
bool isByRef() const
Whether this is a "by ref" capture, i.e.
Capture(VarDecl *variable, bool byRef, bool nested, Expr *copy)
VarDecl * getVariable() const
The variable being captured.
Represents a block literal declaration, which is like an unnamed FunctionDecl.
QualType getPointeeType() const
StringRef getName(const PrintingPolicy &Policy) const
Represents a C++ constructor within a class.
Represents a static or instance method of a struct/union/class.
QualType getThisType() const
Return the type of the this pointer.
Represents a C++ struct/union/class.
bool isAggregate() const
Determine whether this class is an aggregate (C++ [dcl.init.aggr]), which is a class with no user-dec...
bool hasTrivialDefaultConstructor() const
Determine whether this class has a trivial default constructor (C++11 [class.ctor]p5).
llvm::iterator_range< base_class_const_iterator > base_class_const_range
specific_decl_iterator< CXXMethodDecl > method_iterator
Iterator access to method members.
bool isLambda() const
Determine whether this class describes a lambda function object.
capture_const_iterator captures_end() const
method_range methods() const
bool hasConstexprNonCopyMoveConstructor() const
Determine whether this class has at least one constexpr constructor other than the copy or move const...
method_iterator method_begin() const
Method begin iterator.
TemplateSpecializationKind getTemplateSpecializationKind() const
Determine whether this particular class is a specialization or instantiation of a class template or m...
base_class_range vbases()
bool isDynamicClass() const
const LambdaCapture * capture_const_iterator
MSInheritanceModel getMSInheritanceModel() const
Returns the inheritance model used for this record.
bool hasDefinition() const
method_iterator method_end() const
Method past-the-end iterator.
capture_const_iterator captures_begin() const
CXXRecordDecl * getDefinitionOrSelf() const
void * getAsOpaquePtr() const
Retrieve the internal representation of this canonical type.
CharUnits - This is an opaque type for sizes expressed in character units.
bool isPositive() const
isPositive - Test whether the quantity is greater than zero.
bool isZero() const
isZero - Test whether the quantity equals zero.
QuantityType getQuantity() const
getQuantity - Get the raw integer representation of this quantity.
static CharUnits fromQuantity(QuantityType Quantity)
fromQuantity - Construct a CharUnits quantity from a raw integer type.
CharUnits alignTo(const CharUnits &Align) const
alignTo - Returns the next integer (mod 2**64) that is greater than or equal to this quantity and is ...
static CharUnits Zero()
Zero - Construct a CharUnits quantity of zero.
Represents a class template specialization, which refers to a class template with a given set of temp...
CodeGenOptions - Track various options which control how the code is optimized and passed to the back...
std::string DebugCompilationDir
The string to embed in debug information as the current working directory.
A scoped helper to set the current debug location to the specified location or preferred location of ...
ApplyInlineDebugLocation(CodeGenFunction &CGF, GlobalDecl InlinedFn)
Set up the CodeGenFunction's DebugInfo to produce inline locations for the function InlinedFn.
~ApplyInlineDebugLocation()
Restore everything back to the original state.
unsigned getIndex() const
CGBlockInfo - Information to generate a block literal.
unsigned CXXThisIndex
The field index of 'this' within the block, if there is one.
const BlockDecl * getBlockDecl() const
llvm::StructType * StructureType
const Capture & getCapture(const VarDecl *var) const
@ RAA_Indirect
Pass it as a pointer to temporary memory.
MangleContext & getMangleContext()
Gets the mangle context.
This class gathers all debug information during compilation and is responsible for emitting to llvm g...
void addInstToCurrentSourceAtom(llvm::Instruction *KeyInstruction, llvm::Value *Backup)
Add KeyInstruction and an optional Backup instruction to the current atom group, created using ApplyA...
llvm::DIType * getOrCreateStandaloneType(QualType Ty, SourceLocation Loc)
Emit standalone debug info for a type.
void EmitLocation(CGBuilderTy &Builder, SourceLocation Loc)
Emit metadata to indicate a change in line/column information in the source file.
void completeFunction()
Reset internal state.
void EmitGlobalAlias(const llvm::GlobalValue *GV, const GlobalDecl Decl)
Emit information about global variable alias.
void EmitLabel(const LabelDecl *D, CGBuilderTy &Builder)
Emit call to llvm.dbg.label for an label.
void EmitGlobalVariable(llvm::GlobalVariable *GV, const VarDecl *Decl)
Emit information about a global variable.
void completeUnusedClass(const CXXRecordDecl &D)
void setInlinedAt(llvm::DILocation *InlinedAt)
Update the current inline scope.
void EmitUsingShadowDecl(const UsingShadowDecl &USD)
Emit a shadow decl brought in by a using or using-enum.
void EmitUsingEnumDecl(const UsingEnumDecl &UD)
Emit C++ using-enum declaration.
void EmitFunctionEnd(CGBuilderTy &Builder, llvm::Function *Fn)
Constructs the debug code for exiting a function.
void EmitUsingDecl(const UsingDecl &UD)
Emit C++ using declaration.
llvm::DIMacroFile * CreateTempMacroFile(llvm::DIMacroFile *Parent, SourceLocation LineLoc, SourceLocation FileLoc)
Create debug info for a file referenced by an include directive.
void completeTemplateDefinition(const ClassTemplateSpecializationDecl &SD)
void EmitExternalVariable(llvm::GlobalVariable *GV, const VarDecl *Decl)
Emit information about an external variable.
llvm::DINode::DIFlags getCallSiteRelatedAttrs() const
Return flags which enable debug info emission for call sites, provided that it is supported and enabl...
void emitFunctionStart(GlobalDecl GD, SourceLocation Loc, SourceLocation ScopeLoc, QualType FnType, llvm::Function *Fn, bool CurFnIsThunk)
Emit a call to llvm.dbg.function.start to indicate start of a new function.
llvm::DILocalVariable * EmitDeclareOfArgVariable(const VarDecl *Decl, llvm::Value *AI, unsigned ArgNo, CGBuilderTy &Builder, bool UsePointerValue=false)
Emit call to llvm.dbg.declare for an argument variable declaration.
void emitVTableSymbol(llvm::GlobalVariable *VTable, const CXXRecordDecl *RD)
Emit symbol for debugger that holds the pointer to the vtable.
void EmitLexicalBlockEnd(CGBuilderTy &Builder, SourceLocation Loc)
Emit metadata to indicate the end of a new lexical block and pop the current block.
void EmitUsingDirective(const UsingDirectiveDecl &UD)
Emit C++ using directive.
void addInstToSpecificSourceAtom(llvm::Instruction *KeyInstruction, llvm::Value *Backup, uint64_t Atom)
Add KeyInstruction and an optional Backup instruction to the atom group Atom.
void completeRequiredType(const RecordDecl *RD)
void EmitAndRetainType(QualType Ty)
Emit the type even if it might not be used.
void EmitInlineFunctionEnd(CGBuilderTy &Builder)
End an inlined function scope.
void EmitFunctionDecl(GlobalDecl GD, SourceLocation Loc, QualType FnType, llvm::Function *Fn=nullptr)
Emit debug info for a function declaration.
void AddStringLiteralDebugInfo(llvm::GlobalVariable *GV, const StringLiteral *S)
DebugInfo isn't attached to string literals by default.
llvm::DILocalVariable * EmitDeclareOfAutoVariable(const VarDecl *Decl, llvm::Value *AI, CGBuilderTy &Builder, const bool UsePointerValue=false)
Emit call to llvm.dbg.declare for an automatic variable declaration.
void completeClassData(const RecordDecl *RD)
void EmitFuncDeclForCallSite(llvm::CallBase *CallOrInvoke, QualType CalleeType, GlobalDecl CalleeGlobalDecl)
Emit debug info for an extern function being called.
void EmitInlineFunctionStart(CGBuilderTy &Builder, GlobalDecl GD)
Start a new scope for an inlined function.
void EmitImportDecl(const ImportDecl &ID)
Emit an @import declaration.
void EmitDeclareOfBlockLiteralArgVariable(const CGBlockInfo &block, StringRef Name, unsigned ArgNo, llvm::AllocaInst *LocalAddr, CGBuilderTy &Builder)
Emit call to llvm.dbg.declare for the block-literal argument to a block invocation function.
llvm::DebugLoc SourceLocToDebugLoc(SourceLocation Loc)
CGDebugInfo(CodeGenModule &CGM)
void completeClass(const RecordDecl *RD)
void EmitLexicalBlockStart(CGBuilderTy &Builder, SourceLocation Loc)
Emit metadata to indicate the beginning of a new lexical block and push the block onto the stack.
void setLocation(SourceLocation Loc)
Update the current source location.
llvm::DIMacro * CreateMacro(llvm::DIMacroFile *Parent, unsigned MType, SourceLocation LineLoc, StringRef Name, StringRef Value)
Create debug info for a macro defined by a define directive or a macro undefined by a undef directive...
llvm::DILocation * CreateTrapFailureMessageFor(llvm::DebugLoc TrapLocation, StringRef Category, StringRef FailureMsg)
Create a debug location from TrapLocation that adds an artificial inline frame where the frame name i...
llvm::DIType * getOrCreateRecordType(QualType Ty, SourceLocation L)
Emit record type's standalone debug info.
void EmitPseudoVariable(CGBuilderTy &Builder, llvm::Instruction *Value, QualType Ty)
Emit a pseudo variable and debug info for an intermediate value if it does not correspond to a variab...
void addCallTargetIfVirtual(const FunctionDecl *FD, llvm::CallBase *CI)
Add call target information.
std::string remapDIPath(StringRef) const
Remap a given path with the current debug prefix map.
void EmitExplicitCastType(QualType Ty)
Emit the type explicitly casted to.
void addHeapAllocSiteMetadata(llvm::CallBase *CallSite, QualType AllocatedTy, SourceLocation Loc)
Add heapallocsite metadata for MSAllocator calls.
void setDwoId(uint64_t Signature)
Module debugging: Support for building PCMs.
QualType getFunctionType(const FunctionDecl *FD, QualType RetTy, const SmallVectorImpl< const VarDecl * > &Args)
llvm::DIType * getOrCreateInterfaceType(QualType Ty, SourceLocation Loc)
Emit an Objective-C interface type standalone debug info.
void completeType(const EnumDecl *ED)
void EmitDeclareOfBlockDeclRefVariable(const VarDecl *variable, llvm::Value *storage, CGBuilderTy &Builder, const CGBlockInfo &blockInfo, llvm::Instruction *InsertPoint=nullptr)
Emit call to llvm.dbg.declare for an imported variable declaration in a block.
llvm::DIImportedEntity * EmitNamespaceAlias(const NamespaceAliasDecl &NA)
Emit C++ namespace alias.
llvm::DILocation * getInlinedAt() const
llvm::DILocation * CreateSyntheticInlineAt(llvm::DebugLoc ParentLocation, llvm::DISubprogram *SynthSubprogram)
Create a debug location from Location that adds an artificial inline frame where the frame name is Fu...
const CGBitFieldInfo & getBitFieldInfo(const FieldDecl *FD) const
Return the BitFieldInfo that corresponds to the field FD.
~LexicalScope()
Exit this cleanup scope, emitting any accumulated cleanups.
void ForceCleanup()
Force the emission of cleanups now, instead of waiting until this object is destroyed.
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
CGDebugInfo * getDebugInfo()
llvm::DILocation * SanitizerAnnotateDebugInfo(ArrayRef< SanitizerKind::SanitizerOrdinal > Ordinals, SanitizerHandler Handler)
Returns debug info, with additional annotation if CGM.getCodeGenOpts().SanitizeAnnotateDebugInfo[Ordi...
This class organizes the cross-function state that is used while generating LLVM code.
const LangOptions & getLangOpts() const
const TargetInfo & getTarget() const
CGCXXABI & getCXXABI() const
ASTContext & getContext() const
const CodeGenOptions & getCodeGenOpts() const
llvm::LLVMContext & getLLVMContext()
llvm::GlobalVariable::LinkageTypes getVTableLinkage(const CXXRecordDecl *RD)
Return the appropriate linkage for the vtable, VTT, and type information of the given class.
SanitizerDebugLocation(CodeGenFunction *CGF, ArrayRef< SanitizerKind::SanitizerOrdinal > Ordinals, SanitizerHandler Handler)
~SanitizerDebugLocation()
unsigned getNumColumns() const
Returns the number of columns in the matrix.
unsigned getNumRows() const
Returns the number of rows in the matrix.
DeclContext * getEnclosingNamespaceContext()
Retrieve the nearest enclosing namespace context.
decl_range decls() const
decls_begin/decls_end - Iterate over the declarations stored in this context.
Decl - This represents one declaration (or definition), e.g.
ASTContext & getASTContext() const LLVM_READONLY
bool isImplicit() const
isImplicit - Indicates whether the declaration was implicitly generated by the implementation.
unsigned getMaxAlignment() const
getMaxAlignment - return the maximum alignment specified by attributes on this decl,...
Module * getOwningModule() const
Get the module that owns this declaration (for visibility purposes).
bool isFromASTFile() const
Determine whether this declaration came from an AST file (such as a precompiled header or module) rat...
llvm::iterator_range< specific_attr_iterator< T > > specific_attrs() const
SourceLocation getLocation() const
DeclContext * getDeclContext()
AccessSpecifier getAccess() const
DeclContext * getLexicalDeclContext()
getLexicalDeclContext - The declaration context where this Decl was lexically declared (LexicalDC).
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
const LangOptions & getLangOpts() const LLVM_READONLY
Helper to get the language options from the ASTContext.
unsigned getOwningModuleID() const
Retrieve the global ID of the module that owns this particular declaration.
bool isObjCZeroArgSelector() const
@ CXXConversionFunctionName
Selector getObjCSelector() const
Get the Objective-C selector stored in this declaration name.
bool isObjCOneArgSelector() const
NameKind getNameKind() const
Determine what kind of name this is.
bool isComplete() const
Returns true if this can be considered a complete type.
EnumDecl * getDefinitionOrSelf() const
This represents one expression.
SourceLocation getExprLoc() const LLVM_READONLY
getExprLoc - Return the preferred location for the arrow when diagnosing a problem with a generic exp...
bool isBitField() const
Determines whether this field is a bitfield.
unsigned getFieldIndex() const
Returns the index of this field within its record, as appropriate for passing to ASTRecordLayout::get...
static InputKind getInputKindForExtension(StringRef Extension)
getInputKindForExtension - Return the appropriate input kind for a file extension.
Represents a function declaration or definition.
bool isInlined() const
Determine whether this function should be inlined, because it is either marked "inline" or "constexpr...
bool isNoReturn() const
Determines whether this function is known to be 'noreturn', through an attribute on its declaration o...
QualType getReturnType() const
ArrayRef< ParmVarDecl * > parameters() const
bool hasPrototype() const
Whether this function has a prototype, either because one was explicitly written or because it was "i...
FunctionTemplateSpecializationInfo * getTemplateSpecializationInfo() const
If this function is actually a function template specialization, retrieve information about this func...
FunctionDecl * getCanonicalDecl() override
Retrieves the "canonical" declaration of the given declaration.
const TemplateArgumentList * getTemplateSpecializationArgs() const
Retrieve the template arguments used to produce this function template specialization from the primar...
@ TK_FunctionTemplateSpecialization
TemplatedKind getTemplatedKind() const
What kind of templated function this is.
redecl_range redecls() const
Returns an iterator range for all the redeclarations of the same decl.
FunctionDecl * getInstantiatedFromMemberFunction() const
If this function is an instantiation of a member function of a class template specialization,...
Represents a prototype with parameter type info, e.g.
ExceptionSpecificationType getExceptionSpecType() const
Get the kind of exception specification on this function.
unsigned getNumParams() const
QualType getParamType(unsigned i) const
ExtProtoInfo getExtProtoInfo() const
ArrayRef< QualType > getParamTypes() const
ArrayRef< QualType > param_types() const
FunctionTemplateDecl * getTemplate() const
Retrieve the template from which this function was specialized.
FunctionType - C99 6.7.5.3 - Function Declarators.
bool getNoReturnAttr() const
Determine whether this function type includes the GNU noreturn attribute.
CallingConv getCallConv() const
QualType getReturnType() const
GlobalDecl - represents a global declaration.
GlobalDecl getCanonicalDecl() const
DynamicInitKind getDynamicInitKind() const
const Decl * getDecl() const
Describes a module import declaration, which makes the contents of the named module visible in the cu...
Represents the declaration of a label.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
clang::ObjCRuntime ObjCRuntime
bool UseTargetPathSeparator
Indicates whether to use target's platform-specific file separator when FILE macro is used and when c...
std::optional< uint32_t > getCPlusPlusLangStd() const
Returns the most applicable C++ standard-compliant language version code.
std::optional< uint32_t > getCLangStd() const
Returns the most applicable C standard-compliant language version code.
virtual void mangleCXXRTTIName(QualType T, raw_ostream &, bool NormalizeIntegers=false)=0
QualType getElementType() const
Returns type of the elements being stored in the matrix.
CXXRecordDecl * getMostRecentCXXRecordDecl() const
Note: this can trigger extra deserialization when external AST sources are used.
QualType getPointeeType() const
Describes a module or submodule.
Module * Parent
The parent of this module.
std::string Name
The name of this module.
This represents a decl that may have a name.
NamedDecl * getUnderlyingDecl()
Looks through UsingDecls and ObjCCompatibleAliasDecls for the underlying named decl.
IdentifierInfo * getIdentifier() const
Get the identifier that names this declaration, if there is one.
StringRef getName() const
Get the name of identifier for this declaration as a StringRef.
DeclarationName getDeclName() const
Get the actual, stored name of the declaration, which may be a special name.
std::string getNameAsString() const
Get a human-readable name for the declaration, even if it is one of the special kinds of names (C++ c...
virtual void getNameForDiagnostic(raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const
Appends a human-readable name for this declaration into the given stream.
void printQualifiedName(raw_ostream &OS) const
Returns a human-readable qualified name for this declaration, like A::B::i, for i being member of nam...
bool isExternallyVisible() const
Represents a C++ namespace alias.
NamespaceBaseDecl * getAliasedNamespace() const
Retrieve the namespace that this alias refers to, which may either be a NamespaceDecl or a NamespaceA...
Represent a C++ namespace.
bool isAnonymousNamespace() const
Returns true if this is an anonymous namespace declaration.
bool isInline() const
Returns true if this is an inline namespace declaration.
ObjCImplementationDecl * getImplementation() const
ObjCInterfaceDecl * getDefinition()
Retrieve the definition of this class, or NULL if this class has been forward-declared (with @class) ...
ObjCInterfaceDecl * getDecl() const
Get the declaration of this interface.
ObjCMethodDecl - Represents an instance or class method declaration.
bool isDirectMethod() const
True if the method is tagged as objc_direct.
Selector getSelector() const
bool isInstanceMethod() const
ObjCInterfaceDecl * getClassInterface()
bool isObjCQualifiedIdType() const
True if this is equivalent to 'id.
QualType getPointeeType() const
Gets the type pointed to by this ObjC pointer.
Represents one property declaration in an Objective-C interface.
bool isNonFragile() const
Does this runtime follow the set of implied behaviors for a "non-fragile" ABI?
Represents a parameter to a function.
QualType getElementType() const
bool isIsaPointer() const
bool authenticatesNullValues() const
bool isAddressDiscriminated() const
unsigned getExtraDiscriminator() const
QualType getPointeeType() const
Represents an unpacked "presumed" location which can be presented to the user.
unsigned getColumn() const
Return the presumed column number of this location.
const char * getFilename() const
Return the presumed filename of this location.
unsigned getLine() const
Return the presumed line number of this location.
bool isInvalid() const
Return true if this object is invalid or uninitialized.
A (possibly-)qualified type.
QualType getDesugaredType(const ASTContext &Context) const
Return the specified type with any "sugar" removed from the type.
bool hasLocalQualifiers() const
Determine whether this particular QualType instance has any qualifiers, without looking through any t...
bool isNull() const
Return true if this QualType doesn't point to a type yet.
const Type * getTypePtr() const
Retrieves a pointer to the underlying (unqualified) type.
void print(raw_ostream &OS, const PrintingPolicy &Policy, const Twine &PlaceHolder=Twine(), unsigned Indentation=0) const
void * getAsOpaquePtr() const
const Type * strip(QualType type)
Collect any qualifiers on the given type and return an unqualified type.
QualType apply(const ASTContext &Context, QualType QT) const
Apply the collected qualifiers to the given type.
The collection of all-type qualifiers we support.
static Qualifiers removeCommonQualifiers(Qualifiers &L, Qualifiers &R)
Returns the common set of qualifiers while removing them from the given sets.
void removeObjCLifetime()
void removeAddressSpace()
PointerAuthQualifier getPointerAuth() const
Represents a struct/union/class.
field_range fields() const
RecordDecl * getDefinition() const
Returns the RecordDecl that actually defines this struct/union/class.
specific_decl_iterator< FieldDecl > field_iterator
RecordDecl * getDefinitionOrSelf() const
bool isAnonymousStructOrUnion() const
Whether this is an anonymous struct or union.
field_iterator field_begin() const
A class that does preorder or postorder depth-first traversal on the entire Clang AST and visits each...
QualType getPointeeType() const
Scope - A scope is a transient data structure that is used while parsing the program.
static SmallString< 64 > constructSetterName(StringRef Name)
Return the default setter name for the given identifier.
StringRef getNameForSlot(unsigned argIndex) const
Retrieve the name at a given position in the selector.
std::string getAsString() const
Derive the full selector name (e.g.
Encodes a location in the source.
bool isValid() const
Return true if this is a valid SourceLocation object.
This class handles loading and caching of source files into memory.
FileID getFileID(SourceLocation SpellingLoc) const
Return the FileID for a SourceLocation.
PresumedLoc getPresumedLoc(SourceLocation Loc, bool UseLineDirectives=true) const
Returns the "presumed" location of a SourceLocation specifies.
OptionalFileEntryRef getFileEntryRefForID(FileID FID) const
Returns the FileEntryRef for the provided FileID.
SourceLocation getFileLoc(SourceLocation Loc) const
Given Loc, if it is a macro location return the expansion location or the spelling location,...
StringRef getBufferData(FileID FID, bool *Invalid=nullptr) const
Return a StringRef to the source buffer data for the specified FileID.
FileID getMainFileID() const
Returns the FileID of the main source file.
SourceLocation getExpansionLoc(SourceLocation Loc) const
Given a SourceLocation object Loc, return the expansion location referenced by the ID.
std::optional< llvm::MemoryBufferRef > getBufferOrNone(FileID FID, SourceLocation Loc=SourceLocation()) const
Return the buffer for the specified FileID.
A trivial tuple used to represent a source range.
StringLiteral - This represents a string literal expression, e.g.
SourceLocation getStrTokenLoc(unsigned TokNum) const
Get one of the string literal token.
Represents the declaration of a struct/union/class/enum.
bool isCompleteDefinition() const
Return true if this decl has its body fully specified.
TypedefNameDecl * getTypedefNameForAnonDecl() const
bool isCompleteDefinitionRequired() const
Return true if this complete decl is required to be complete for some existing use.
TagDecl * getDefinitionOrSelf() const
virtual std::optional< unsigned > getDWARFAddressSpace(unsigned AddressSpace) const
uint64_t getPointerAlign(LangAS AddrSpace) const
ArrayRef< TemplateArgument > asArray() const
Produce this as an array ref.
Represents a template argument.
ArrayRef< TemplateArgument > getPackAsArray() const
Return the array of arguments in this template argument pack.
QualType getStructuralValueType() const
Get the type of a StructuralValue.
QualType getParamTypeForDecl() const
Expr * getAsExpr() const
Retrieve the template argument as an expression.
QualType getAsType() const
Retrieve the type for a type template argument.
llvm::APSInt getAsIntegral() const
Retrieve the template argument as an integral value.
QualType getNullPtrType() const
Retrieve the type for null non-type template argument.
TemplateName getAsTemplate() const
Retrieve the template name for a template name argument.
QualType getIntegralType() const
Retrieve the type of the integral value.
bool getIsDefaulted() const
If returns 'true', this TemplateArgument corresponds to a default template parameter.
ValueDecl * getAsDecl() const
Retrieve the declaration for a declaration non-type template argument.
@ Declaration
The template argument is a declaration that was provided for a pointer, reference,...
@ Template
The template argument is a template name that was provided for a template template parameter.
@ StructuralValue
The template argument is a non-type template argument that can't be represented by the special-case D...
@ Pack
The template argument is actually a parameter pack.
@ TemplateExpansion
The template argument is a pack expansion of a template name that was provided for a template templat...
@ NullPtr
The template argument is a null pointer or null pointer to member that was provided for a non-type te...
@ Type
The template argument is a type.
@ Null
Represents an empty template argument, e.g., one that has not been deduced.
@ Integral
The template argument is an integral value stored in an llvm::APSInt that was provided for an integra...
@ Expression
The template argument is an expression, and we've not resolved it to one of the other forms yet,...
ArgKind getKind() const
Return the kind of stored template argument.
const APValue & getAsStructuralValue() const
Get the value of a StructuralValue.
The base class of all kinds of template declarations (e.g., class, function, etc.).
TemplateParameterList * getTemplateParameters() const
Get the list of template parameters.
TemplateDecl * getAsTemplateDecl(bool IgnoreDeduced=false) const
Retrieve the underlying template declaration that this template name refers to, if known.
ArrayRef< NamedDecl * > asArray()
The base class of the type hierarchy.
bool isPackedVectorBoolType(const ASTContext &ctx) const
bool isIncompleteArrayType() const
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
bool isIntegerType() const
isIntegerType() does not include complex integers (a GCC extension).
const T * castAs() const
Member-template castAs<specific type>.
bool isReferenceType() const
AutoType * getContainedAutoType() const
Get the AutoType whose type will be deduced for a variable with an initializer of this type.
bool isMemberDataPointerType() const
bool isComplexIntegerType() const
bool isIncompleteType(NamedDecl **Def=nullptr) const
Types are partitioned into 3 broad categories (C99 6.2.5p1): object types, function types,...
TypeClass getTypeClass() const
const T * getAs() const
Member-template getAs<specific type>'.
bool isRecordType() const
QualType getUnderlyingType() const
TypedefNameDecl * getDecl() const
Represents a C++ using-declaration.
Represents C++ using-directive.
NamespaceDecl * getNominatedNamespace()
Returns the namespace nominated by this using-directive.
Represents a C++ using-enum-declaration.
Represents a shadow declaration implicitly introduced into a scope by a (resolved) using-declaration ...
static bool hasVtableSlot(const CXXMethodDecl *MD)
Determine whether this function should be assigned a vtable slot.
ArrayRef< VTableComponent > vtable_components() const
Represent the declaration of a variable (in which case it is an lvalue) a function (in which case it ...
Represents a variable declaration or definition.
VarDecl * getCanonicalDecl() override
Retrieves the "canonical" declaration of the given declaration.
bool isStaticDataMember() const
Determines whether this is a static data member.
bool isStaticLocal() const
Returns true if a variable with function scope is a static local variable.
const Expr * getInit() const
const APValue * evaluateValue() const
Attempt to evaluate the value of the initializer attached to this declaration, and produce notes expl...
bool isEscapingByref() const
Indicates the capture is a __block variable that is captured by a block that can potentially escape (...
unsigned getNumElements() const
QualType getElementType() const
@ Type
The l-value was considered opaque, so the alignment was determined from a type.
@ Decl
The l-value was an access to a declared entity or something equivalently strong, like the address of ...
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
const internal::VariadicDynCastAllOfMatcher< Decl, BlockDecl > blockDecl
Matches block declarations.
@ OS
Indicates that the tracking object is a descendant of a referenced-counted OSObject,...
Top level wrappers for InstallAPI frontend operations.
CanQual< Type > CanQualType
Represents a canonical, potentially-qualified type.
@ Ctor_Unified
GCC-style unified dtor.
bool isa(CodeGen::Address addr)
CustomizableOptional< FileEntryRef > OptionalFileEntryRef
if(T->getSizeExpr()) TRY_TO(TraverseStmt(const_cast< Expr * >(T -> getSizeExpr())))
@ RQ_LValue
An lvalue ref-qualifier was provided (&).
@ RQ_RValue
An rvalue ref-qualifier was provided (&&).
AccessSpecifier
A C++ access specifier (public, private, protected), plus the special value "none" which means differ...
nullptr
This class represents a compute construct, representing a 'Kind' of ‘parallel’, 'serial',...
bool operator<(DeclarationName LHS, DeclarationName RHS)
Ordering on two declaration names.
@ Module
Module linkage, which indicates that the entity can be referred to from other translation units withi...
@ Default
Set to the current date and time.
@ Result
The result type of a method or function.
const FunctionProtoType * T
bool isNoexceptExceptionSpec(ExceptionSpecificationType ESpecType)
@ Dtor_VectorDeleting
Vector deleting dtor.
@ Dtor_Unified
GCC-style unified dtor.
@ Dtor_Deleting
Deleting dtor.
TemplateSpecializationKind
Describes the kind of template specialization that a particular template specialization declaration r...
@ TSK_ExplicitInstantiationDeclaration
This template specialization was instantiated from a template due to an explicit instantiation declar...
@ TSK_Undeclared
This template specialization was formed from a template-id but has not yet been declared,...
CallingConv
CallingConv - Specifies the calling convention that a function uses.
@ Generic
not a target-specific vector type
U cast(CodeGen::Address addr)
@ Enum
The "enum" keyword introduces the elaborated-type-specifier.
@ CXXThis
Parameter for C++ 'this' argument.
@ ObjCSelf
Parameter for Objective-C 'self' argument.
std::string getClangFullVersion()
Retrieves a string representing the complete clang version, which includes the clang version number,...
__packed_splat4 __packed_splat2 __packed_splat8 __packed_splat4 __packed_splat2 __packed_splat4 __packed_splat2 __packed_splat8 __packed_splat4 uint32_t
CharUnits StorageOffset
The offset of the bitfield storage from the start of the struct.
unsigned Offset
The offset within a contiguous run of bitfields that are represented as a single "field" within the L...
unsigned Size
The total size of the bit-field, in bits.
unsigned StorageSize
The storage size in bits which should be used when accessing this bitfield.
unsigned IsSigned
Whether the bit-field is signed.
Extra information about a function prototype.
uint64_t Index
Method's index in the vftable.
unsigned PrettyEnums
Whether to print enumerators with a matching enumerator name or via cast.
unsigned MSVCFormatting
Use whitespace and punctuation like MSVC does.
unsigned SplitTemplateClosers
Whether nested templates must be closed like 'a<b<c> >' rather than 'a<b<c>>'.
unsigned AlwaysIncludeTypeForTemplateArgument
Whether to use type suffixes (eg: 1U) on integral non-type template parameters.
unsigned UsePreferredNames
Whether to use C++ template preferred_name attributes when printing templates.
unsigned UseEnumerators
Whether to print enumerator non-type template parameters with a matching enumerator name or via cast ...
unsigned SuppressInlineNamespace
Suppress printing parts of scope specifiers that correspond to inline namespaces.
const PrintingCallbacks * Callbacks
Callbacks to use to allow the behavior of printing to be customized.
unsigned PrintAsCanonical
Whether to print entities as written or canonically.