40#include "llvm/ADT/DenseSet.h"
41#include "llvm/ADT/SmallVector.h"
42#include "llvm/ADT/StringExtras.h"
43#include "llvm/IR/Constants.h"
44#include "llvm/IR/DataLayout.h"
45#include "llvm/IR/DerivedTypes.h"
46#include "llvm/IR/Instructions.h"
47#include "llvm/IR/Intrinsics.h"
48#include "llvm/IR/Metadata.h"
49#include "llvm/IR/Module.h"
50#include "llvm/Support/MD5.h"
51#include "llvm/Support/Path.h"
52#include "llvm/Support/SHA1.h"
53#include "llvm/Support/SHA256.h"
54#include "llvm/Support/TimeProfiler.h"
61 if (TI.isAlignRequired())
89 llvm::dyn_cast_or_null<DeclRefExpr>(
Init->IgnoreUnlessSpelledInSource());
93 return llvm::dyn_cast_or_null<DecompositionDecl>(RefExpr->getDecl());
111 : CGM(CGM), DebugKind(CGM.getCodeGenOpts().getDebugInfo()),
112 DebugTypeExtRefs(CGM.getCodeGenOpts().DebugTypeExtRefs),
113 DBuilder(CGM.getModule()) {
118 assert(LexicalBlockStack.empty() &&
119 "Region stack mismatch, stack not empty!");
125 init(TemporaryLocation);
132 init(TemporaryLocation, DefaultToEmpty);
136 bool DefaultToEmpty) {
143 OriginalLocation = CGF->
Builder.getCurrentDebugLocation();
145 if (OriginalLocation && !DI->CGM.getExpressionLocationsEnabled())
148 if (TemporaryLocation.
isValid()) {
149 DI->EmitLocation(CGF->
Builder, TemporaryLocation);
153 if (DefaultToEmpty) {
154 CGF->
Builder.SetCurrentDebugLocation(llvm::DebugLoc());
159 assert(!DI->LexicalBlockStack.empty());
160 CGF->
Builder.SetCurrentDebugLocation(
161 llvm::DILocation::get(DI->LexicalBlockStack.back()->getContext(), 0, 0,
162 DI->LexicalBlockStack.back(), DI->getInlinedAt()));
176 OriginalLocation = CGF.
Builder.getCurrentDebugLocation();
178 CGF.
Builder.SetCurrentDebugLocation(std::move(
Loc));
185 CGF->
Builder.SetCurrentDebugLocation(std::move(OriginalLocation));
196 SavedLocation = DI.getLocation();
197 assert((DI.getInlinedAt() ==
198 CGF.
Builder.getCurrentDebugLocation()->getInlinedAt()) &&
199 "CGDebugInfo and IRBuilder are out of sync");
201 DI.EmitInlineFunctionStart(CGF.
Builder, InlinedFn);
209 DI.EmitLocation(CGF->
Builder, SavedLocation);
222 if (LexicalBlockStack.empty())
226 auto *
Scope = cast<llvm::DIScope>(LexicalBlockStack.back());
228 if (PCLoc.
isInvalid() ||
Scope->getFile() == getOrCreateFile(CurLoc))
231 if (
auto *LBF = dyn_cast<llvm::DILexicalBlockFile>(
Scope)) {
232 LexicalBlockStack.pop_back();
233 LexicalBlockStack.emplace_back(DBuilder.createLexicalBlockFile(
234 LBF->getScope(), getOrCreateFile(CurLoc)));
235 }
else if (isa<llvm::DILexicalBlock>(
Scope) ||
236 isa<llvm::DISubprogram>(
Scope)) {
237 LexicalBlockStack.pop_back();
238 LexicalBlockStack.emplace_back(
239 DBuilder.createLexicalBlockFile(
Scope, getOrCreateFile(CurLoc)));
243llvm::DIScope *CGDebugInfo::getDeclContextDescriptor(
const Decl *
D) {
244 llvm::DIScope *Mod = getParentModuleOrNull(
D);
249llvm::DIScope *CGDebugInfo::getContextDescriptor(
const Decl *Context,
254 auto I = RegionMap.find(Context);
255 if (I != RegionMap.end()) {
256 llvm::Metadata *
V = I->second;
257 return dyn_cast_or_null<llvm::DIScope>(
V);
261 if (
const auto *NSDecl = dyn_cast<NamespaceDecl>(Context))
262 return getOrCreateNamespace(NSDecl);
264 if (
const auto *RDecl = dyn_cast<RecordDecl>(Context))
265 if (!RDecl->isDependentType())
300StringRef CGDebugInfo::getFunctionName(
const FunctionDecl *FD) {
301 return internString(GetName(FD));
304StringRef CGDebugInfo::getObjCMethodName(
const ObjCMethodDecl *OMD) {
306 llvm::raw_svector_ostream OS(MethodName);
309 if (
const auto *OID = dyn_cast<ObjCImplementationDecl>(DC)) {
310 OS << OID->getName();
311 }
else if (
const auto *OID = dyn_cast<ObjCInterfaceDecl>(DC)) {
312 OS << OID->getName();
313 }
else if (
const auto *OC = dyn_cast<ObjCCategoryDecl>(DC)) {
314 if (OC->IsClassExtension()) {
315 OS << OC->getClassInterface()->getName();
317 OS << OC->getIdentifier()->getNameStart() <<
'('
318 << OC->getIdentifier()->getNameStart() <<
')';
320 }
else if (
const auto *OCD = dyn_cast<ObjCCategoryImplDecl>(DC)) {
321 OS << OCD->getClassInterface()->getName() <<
'(' << OCD->getName() <<
')';
325 return internString(OS.str());
328StringRef CGDebugInfo::getSelectorName(
Selector S) {
329 return internString(S.getAsString());
332StringRef CGDebugInfo::getClassName(
const RecordDecl *RD) {
333 if (isa<ClassTemplateSpecializationDecl>(RD)) {
335 return internString(GetName(RD));
341 return II->getName();
349 "Typedef should not be in another decl context!");
350 assert(
D->getDeclName().getAsIdentifierInfo() &&
351 "Typedef was not named!");
352 return D->getDeclName().getAsIdentifierInfo()->getName();
362 Name = DD->getName();
367 Name = TND->getName();
370 if (
const CXXRecordDecl *CXXRD = dyn_cast<CXXRecordDecl>(RD))
371 if (CXXRD->isLambda())
379 return internString(UnnamedType);
387std::optional<llvm::DIFile::ChecksumKind>
396 std::optional<llvm::MemoryBufferRef> MemBuffer =
SM.getBufferOrNone(FID);
400 auto Data = llvm::arrayRefFromStringRef(MemBuffer->getBuffer());
403 llvm::toHex(llvm::MD5::hash(
Data),
true, Checksum);
404 return llvm::DIFile::CSK_MD5;
406 llvm::toHex(llvm::SHA1::hash(
Data),
true, Checksum);
407 return llvm::DIFile::CSK_SHA1;
409 llvm::toHex(llvm::SHA256::hash(
Data),
true, Checksum);
410 return llvm::DIFile::CSK_SHA256;
412 llvm_unreachable(
"Unhandled DebugSrcHashKind enum");
415std::optional<StringRef> CGDebugInfo::getSource(
const SourceManager &
SM,
420 bool SourceInvalid =
false;
421 StringRef Source =
SM.getBufferData(FID, &SourceInvalid);
433 std::optional<llvm::DIFile::ChecksumInfo<StringRef>> CSInfo;
439 FileName = TheCU->getFile()->getFilename();
440 CSInfo = TheCU->getFile()->getChecksum();
446 FileName = TheCU->getFile()->getFilename();
454 auto It = DIFileCache.find(
FileName.data());
455 if (It != DIFileCache.end()) {
457 if (llvm::Metadata *
V = It->second)
458 return cast<llvm::DIFile>(
V);
464 std::optional<llvm::DIFile::ChecksumKind> CSKind =
465 computeChecksum(FID, Checksum);
467 CSInfo.emplace(*CSKind, Checksum);
472llvm::DIFile *CGDebugInfo::createFile(
474 std::optional<llvm::DIFile::ChecksumInfo<StringRef>> CSInfo,
475 std::optional<StringRef> Source) {
479 std::string CurDir =
remapDIPath(getCurrentDirname());
482 if (llvm::sys::path::is_absolute(RemappedFile)) {
485 auto FileIt = llvm::sys::path::begin(RemappedFile);
486 auto FileE = llvm::sys::path::end(RemappedFile);
487 auto CurDirIt = llvm::sys::path::begin(CurDir);
488 auto CurDirE = llvm::sys::path::end(CurDir);
489 for (; CurDirIt != CurDirE && *CurDirIt == *FileIt; ++CurDirIt, ++FileIt)
490 llvm::sys::path::append(DirBuf, *CurDirIt);
491 if (llvm::sys::path::root_path(DirBuf) == DirBuf) {
497 for (; FileIt != FileE; ++FileIt)
498 llvm::sys::path::append(FileBuf, *FileIt);
503 if (!llvm::sys::path::is_absolute(
FileName))
507 llvm::DIFile *F = DBuilder.createFile(
File, Dir, CSInfo, Source);
508 DIFileCache[
FileName.data()].reset(F);
515 if (llvm::sys::path::replace_path_prefix(
P, From, To))
517 return P.str().str();
524 return SM.getPresumedLoc(
Loc).getLine();
540StringRef CGDebugInfo::getCurrentDirname() {
544 if (!CWDName.empty())
546 llvm::ErrorOr<std::string> CWD =
550 return CWDName = internString(*CWD);
553void CGDebugInfo::CreateCompileUnit() {
555 std::optional<llvm::DIFile::ChecksumKind> CSKind;
556 std::optional<llvm::DIFile::ChecksumInfo<StringRef>> CSInfo;
569 std::string MainFileName = CGO.MainFileName;
570 if (MainFileName.empty())
571 MainFileName =
"<stdin>";
577 std::string MainFileDir;
579 SM.getFileEntryRefForID(
SM.getMainFileID())) {
580 MainFileDir = std::string(MainFile->getDir().getName());
581 if (!llvm::sys::path::is_absolute(MainFileName)) {
583 llvm::sys::path::Style Style =
586 ? llvm::sys::path::Style::windows_backslash
587 : llvm::sys::path::Style::posix)
588 : llvm::sys::path::Style::native;
589 llvm::sys::path::append(MainFileDirSS, Style, MainFileName);
590 MainFileName = std::string(
591 llvm::sys::path::remove_leading_dotslash(MainFileDirSS, Style));
598 if (MainFile->getName() == MainFileName &&
600 MainFile->getName().rsplit(
'.').second)
602 MainFileName = CGM.
getModule().getName().str();
604 CSKind = computeChecksum(
SM.getMainFileID(), Checksum);
608 llvm::dwarf::SourceLanguage LangTag;
611 LangTag = llvm::dwarf::DW_LANG_ObjC_plus_plus;
612 else if (CGO.DebugStrictDwarf && CGO.DwarfVersion < 5)
613 LangTag = llvm::dwarf::DW_LANG_C_plus_plus;
614 else if (LO.CPlusPlus14)
615 LangTag = llvm::dwarf::DW_LANG_C_plus_plus_14;
616 else if (LO.CPlusPlus11)
617 LangTag = llvm::dwarf::DW_LANG_C_plus_plus_11;
619 LangTag = llvm::dwarf::DW_LANG_C_plus_plus;
620 }
else if (LO.ObjC) {
621 LangTag = llvm::dwarf::DW_LANG_ObjC;
622 }
else if (LO.OpenCL && (!CGM.
getCodeGenOpts().DebugStrictDwarf ||
624 LangTag = llvm::dwarf::DW_LANG_OpenCL;
625 }
else if (LO.C11 && !(CGO.DebugStrictDwarf && CGO.DwarfVersion < 5)) {
626 LangTag = llvm::dwarf::DW_LANG_C11;
628 LangTag = llvm::dwarf::DW_LANG_C99;
630 LangTag = llvm::dwarf::DW_LANG_C89;
636 unsigned RuntimeVers = 0;
640 llvm::DICompileUnit::DebugEmissionKind EmissionKind;
642 case llvm::codegenoptions::NoDebugInfo:
643 case llvm::codegenoptions::LocTrackingOnly:
644 EmissionKind = llvm::DICompileUnit::NoDebug;
646 case llvm::codegenoptions::DebugLineTablesOnly:
647 EmissionKind = llvm::DICompileUnit::LineTablesOnly;
649 case llvm::codegenoptions::DebugDirectivesOnly:
650 EmissionKind = llvm::DICompileUnit::DebugDirectivesOnly;
652 case llvm::codegenoptions::DebugInfoConstructor:
653 case llvm::codegenoptions::LimitedDebugInfo:
654 case llvm::codegenoptions::FullDebugInfo:
655 case llvm::codegenoptions::UnusedTypeInfo:
656 EmissionKind = llvm::DICompileUnit::FullDebug;
667 CSInfo.emplace(*CSKind, Checksum);
668 llvm::DIFile *CUFile = DBuilder.createFile(
670 getSource(
SM,
SM.getMainFileID()));
672 StringRef Sysroot, SDK;
673 if (CGM.
getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::LLDB) {
675 auto B = llvm::sys::path::rbegin(Sysroot);
676 auto E = llvm::sys::path::rend(Sysroot);
678 std::find_if(B,
E, [](
auto SDK) {
return SDK.ends_with(
".sdk"); });
683 llvm::DICompileUnit::DebugNameTableKind NameTableKind =
684 static_cast<llvm::DICompileUnit::DebugNameTableKind
>(
685 CGOpts.DebugNameTable);
687 NameTableKind = llvm::DICompileUnit::DebugNameTableKind::None;
689 NameTableKind = llvm::DICompileUnit::DebugNameTableKind::Apple;
692 TheCU = DBuilder.createCompileUnit(
693 LangTag, CUFile, CGOpts.EmitVersionIdentMetadata ? Producer :
"",
694 LO.Optimize || CGOpts.PrepareForLTO || CGOpts.PrepareForThinLTO,
695 CGOpts.DwarfDebugFlags, RuntimeVers, CGOpts.SplitDwarfFile, EmissionKind,
696 DwoId, CGOpts.SplitDwarfInlining, CGOpts.DebugInfoForProfiling,
697 NameTableKind, CGOpts.DebugRangesBaseAddress,
remapDIPath(Sysroot), SDK);
700llvm::DIType *CGDebugInfo::CreateType(
const BuiltinType *BT) {
704#define BUILTIN_TYPE(Id, SingletonId)
705#define PLACEHOLDER_TYPE(Id, SingletonId) case BuiltinType::Id:
706#include "clang/AST/BuiltinTypes.def"
707 case BuiltinType::Dependent:
708 llvm_unreachable(
"Unexpected builtin type");
709 case BuiltinType::NullPtr:
710 return DBuilder.createNullPtrType();
711 case BuiltinType::Void:
713 case BuiltinType::ObjCClass:
716 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type,
717 "objc_class", TheCU, TheCU->getFile(), 0);
719 case BuiltinType::ObjCId: {
730 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type,
731 "objc_class", TheCU, TheCU->getFile(), 0);
735 auto *ISATy = DBuilder.createPointerType(ClassTy, Size);
737 ObjTy = DBuilder.createStructType(TheCU,
"objc_object", TheCU->getFile(), 0,
738 0, 0, llvm::DINode::FlagZero,
nullptr,
739 llvm::DINodeArray());
741 DBuilder.replaceArrays(
742 ObjTy, DBuilder.getOrCreateArray(&*DBuilder.createMemberType(
743 ObjTy,
"isa", TheCU->getFile(), 0, Size, 0, 0,
744 llvm::DINode::FlagZero, ISATy)));
747 case BuiltinType::ObjCSel: {
749 SelTy = DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type,
750 "objc_selector", TheCU,
751 TheCU->getFile(), 0);
755#define IMAGE_TYPE(ImgType, Id, SingletonId, Access, Suffix) \
756 case BuiltinType::Id: \
757 return getOrCreateStructPtrType("opencl_" #ImgType "_" #Suffix "_t", \
759#include "clang/Basic/OpenCLImageTypes.def"
760 case BuiltinType::OCLSampler:
761 return getOrCreateStructPtrType(
"opencl_sampler_t", OCLSamplerDITy);
762 case BuiltinType::OCLEvent:
763 return getOrCreateStructPtrType(
"opencl_event_t", OCLEventDITy);
764 case BuiltinType::OCLClkEvent:
765 return getOrCreateStructPtrType(
"opencl_clk_event_t", OCLClkEventDITy);
766 case BuiltinType::OCLQueue:
767 return getOrCreateStructPtrType(
"opencl_queue_t", OCLQueueDITy);
768 case BuiltinType::OCLReserveID:
769 return getOrCreateStructPtrType(
"opencl_reserve_id_t", OCLReserveIDDITy);
770#define EXT_OPAQUE_TYPE(ExtType, Id, Ext) \
771 case BuiltinType::Id: \
772 return getOrCreateStructPtrType("opencl_" #ExtType, Id##Ty);
773#include "clang/Basic/OpenCLExtensionTypes.def"
774#define HLSL_INTANGIBLE_TYPE(Name, Id, SingletonId) \
775 case BuiltinType::Id: \
776 return getOrCreateStructPtrType(#Name, SingletonId);
777#include "clang/Basic/HLSLIntangibleTypes.def"
779#define SVE_TYPE(Name, Id, SingletonId) case BuiltinType::Id:
780#include "clang/Basic/AArch64SVEACLETypes.def"
782 if (BT->
getKind() == BuiltinType::MFloat8) {
783 Encoding = llvm::dwarf::DW_ATE_unsigned_char;
787 return DBuilder.createBasicType(BTName, Size, Encoding);
791 BT->
getKind() == BuiltinType::SveCount
795 : CGM.getContext().getBuiltinVectorTypeInfo(BT);
802 "Unsupported number of vectors for svcount_t");
806 unsigned NumElems = Info.
EC.getKnownMinValue() * Info.
NumVectors;
812 llvm::Metadata *LowerBound, *UpperBound;
813 LowerBound = llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
815 if (Info.
EC.isScalable()) {
816 unsigned NumElemsPerVG = NumElems / 2;
818 {llvm::dwarf::DW_OP_constu, NumElemsPerVG, llvm::dwarf::DW_OP_bregx,
819 46, 0, llvm::dwarf::DW_OP_mul,
820 llvm::dwarf::DW_OP_constu, 1, llvm::dwarf::DW_OP_minus});
821 UpperBound = DBuilder.createExpression(
Expr);
823 UpperBound = llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
826 llvm::Metadata *Subscript = DBuilder.getOrCreateSubrange(
827 nullptr, LowerBound, UpperBound,
nullptr);
828 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscript);
829 llvm::DIType *ElemTy =
830 getOrCreateType(Info.
ElementType, TheCU->getFile());
832 return DBuilder.createVectorType( 0, Align, ElemTy,
837#define PPC_VECTOR_TYPE(Name, Id, size) \
838 case BuiltinType::Id:
839#include "clang/Basic/PPCTypes.def"
842#define RVV_TYPE(Name, Id, SingletonId) case BuiltinType::Id:
843#include "clang/Basic/RISCVVTypes.def"
848 unsigned ElementCount = Info.
EC.getKnownMinValue();
851 bool Fractional =
false;
853 unsigned FixedSize = ElementCount * SEW;
857 }
else if (FixedSize < 64) {
860 LMUL = 64 / FixedSize;
862 LMUL = FixedSize / 64;
870 {llvm::dwarf::DW_OP_bregx,
873 llvm::dwarf::DW_OP_constu,
875 llvm::dwarf::DW_OP_div, llvm::dwarf::DW_OP_constu, LMUL});
877 Expr.push_back(llvm::dwarf::DW_OP_div);
879 Expr.push_back(llvm::dwarf::DW_OP_mul);
881 Expr.append({llvm::dwarf::DW_OP_constu, 1, llvm::dwarf::DW_OP_minus});
884 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
886 auto *UpperBound = DBuilder.createExpression(
Expr);
887 llvm::Metadata *Subscript = DBuilder.getOrCreateSubrange(
888 nullptr, LowerBound, UpperBound,
nullptr);
889 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscript);
890 llvm::DIType *ElemTy =
891 getOrCreateType(Info.
ElementType, TheCU->getFile());
894 return DBuilder.createVectorType(0, Align, ElemTy,
898#define WASM_REF_TYPE(Name, MangledName, Id, SingletonId, AS) \
899 case BuiltinType::Id: { \
902 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type, \
903 MangledName, TheCU, TheCU->getFile(), 0); \
904 return SingletonId; \
906#include "clang/Basic/WebAssemblyReferenceTypes.def"
907#define AMDGPU_OPAQUE_PTR_TYPE(Name, Id, SingletonId, Width, Align, AS) \
908 case BuiltinType::Id: { \
911 DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type, Name, \
912 TheCU, TheCU->getFile(), 0); \
913 return SingletonId; \
915#define AMDGPU_NAMED_BARRIER_TYPE(Name, Id, SingletonId, Width, Align, Scope) \
916 case BuiltinType::Id: { \
919 DBuilder.createBasicType(Name, Width, llvm::dwarf::DW_ATE_unsigned); \
920 return SingletonId; \
922#include "clang/Basic/AMDGPUTypes.def"
923 case BuiltinType::UChar:
924 case BuiltinType::Char_U:
925 Encoding = llvm::dwarf::DW_ATE_unsigned_char;
927 case BuiltinType::Char_S:
928 case BuiltinType::SChar:
929 Encoding = llvm::dwarf::DW_ATE_signed_char;
931 case BuiltinType::Char8:
932 case BuiltinType::Char16:
933 case BuiltinType::Char32:
936 case BuiltinType::UShort:
937 case BuiltinType::UInt:
938 case BuiltinType::UInt128:
939 case BuiltinType::ULong:
940 case BuiltinType::WChar_U:
941 case BuiltinType::ULongLong:
942 Encoding = llvm::dwarf::DW_ATE_unsigned;
944 case BuiltinType::Short:
945 case BuiltinType::Int:
946 case BuiltinType::Int128:
947 case BuiltinType::Long:
948 case BuiltinType::WChar_S:
949 case BuiltinType::LongLong:
950 Encoding = llvm::dwarf::DW_ATE_signed;
952 case BuiltinType::Bool:
953 Encoding = llvm::dwarf::DW_ATE_boolean;
955 case BuiltinType::Half:
956 case BuiltinType::Float:
957 case BuiltinType::LongDouble:
958 case BuiltinType::Float16:
959 case BuiltinType::BFloat16:
960 case BuiltinType::Float128:
961 case BuiltinType::Double:
962 case BuiltinType::Ibm128:
968 Encoding = llvm::dwarf::DW_ATE_float;
970 case BuiltinType::ShortAccum:
971 case BuiltinType::Accum:
972 case BuiltinType::LongAccum:
973 case BuiltinType::ShortFract:
974 case BuiltinType::Fract:
975 case BuiltinType::LongFract:
976 case BuiltinType::SatShortFract:
977 case BuiltinType::SatFract:
978 case BuiltinType::SatLongFract:
979 case BuiltinType::SatShortAccum:
980 case BuiltinType::SatAccum:
981 case BuiltinType::SatLongAccum:
982 Encoding = llvm::dwarf::DW_ATE_signed_fixed;
984 case BuiltinType::UShortAccum:
985 case BuiltinType::UAccum:
986 case BuiltinType::ULongAccum:
987 case BuiltinType::UShortFract:
988 case BuiltinType::UFract:
989 case BuiltinType::ULongFract:
990 case BuiltinType::SatUShortAccum:
991 case BuiltinType::SatUAccum:
992 case BuiltinType::SatULongAccum:
993 case BuiltinType::SatUShortFract:
994 case BuiltinType::SatUFract:
995 case BuiltinType::SatULongFract:
996 Encoding = llvm::dwarf::DW_ATE_unsigned_fixed;
1003 return DBuilder.createBasicType(BTName, Size, Encoding);
1006llvm::DIType *CGDebugInfo::CreateType(
const BitIntType *Ty) {
1008 StringRef Name = Ty->
isUnsigned() ?
"unsigned _BitInt" :
"_BitInt";
1010 ? llvm::dwarf::DW_ATE_unsigned
1011 : llvm::dwarf::DW_ATE_signed;
1017llvm::DIType *CGDebugInfo::CreateType(
const ComplexType *Ty) {
1019 llvm::dwarf::TypeKind
Encoding = llvm::dwarf::DW_ATE_complex_float;
1021 Encoding = llvm::dwarf::DW_ATE_lo_user;
1024 return DBuilder.createBasicType(
"complex", Size, Encoding);
1038 return llvm::dwarf::DW_TAG_const_type;
1042 return llvm::dwarf::DW_TAG_volatile_type;
1046 return llvm::dwarf::DW_TAG_restrict_type;
1048 return (llvm::dwarf::Tag)0;
1051llvm::DIType *CGDebugInfo::CreateQualifiedType(
QualType Ty,
1052 llvm::DIFile *Unit) {
1062 assert(Qc.
empty() &&
"Unknown type qualifier for debug info");
1063 return getOrCreateType(
QualType(
T, 0), Unit);
1070 return DBuilder.createQualifiedType(Tag, FromTy);
1074 llvm::DIFile *Unit) {
1083 assert(Q.
empty() &&
"Unknown type qualifier for debug info");
1094 return DBuilder.createQualifiedType(Tag, FromTy);
1098 llvm::DIFile *Unit) {
1106 return CreatePointerLikeType(llvm::dwarf::DW_TAG_pointer_type, Ty,
1110llvm::DIType *CGDebugInfo::CreateType(
const PointerType *Ty,
1111 llvm::DIFile *Unit) {
1112 return CreatePointerLikeType(llvm::dwarf::DW_TAG_pointer_type, Ty,
1118 switch (TheCU->getSourceLanguage()) {
1119 case llvm::dwarf::DW_LANG_C_plus_plus:
1120 case llvm::dwarf::DW_LANG_C_plus_plus_11:
1121 case llvm::dwarf::DW_LANG_C_plus_plus_14:
1123 case llvm::dwarf::DW_LANG_ObjC_plus_plus:
1124 return isa<CXXRecordDecl>(TD) || isa<EnumDecl>(TD);
1152 llvm::DICompileUnit *TheCU) {
1170 llvm::DICompileUnit *TheCU) {
1176 if (
const auto *RD = dyn_cast<CXXRecordDecl>(TD))
1178 if (RD->isDynamicClass() &&
1191 llvm::dwarf::Tag Tag;
1193 Tag = llvm::dwarf::DW_TAG_structure_type;
1195 Tag = llvm::dwarf::DW_TAG_union_type;
1200 Tag = llvm::dwarf::DW_TAG_class_type;
1205llvm::DICompositeType *
1206CGDebugInfo::getOrCreateRecordFwdDecl(
const RecordType *Ty,
1207 llvm::DIScope *Ctx) {
1210 return cast<llvm::DICompositeType>(
T);
1211 llvm::DIFile *DefUnit = getOrCreateFile(RD->
getLocation());
1212 const unsigned Line =
1214 StringRef RDName = getClassName(RD);
1220 if (
D &&
D->isCompleteDefinition())
1223 llvm::DINode::DIFlags Flags = llvm::DINode::FlagFwdDecl;
1228 if (
const CXXRecordDecl *CXXRD = dyn_cast<CXXRecordDecl>(RD))
1229 if (!CXXRD->hasDefinition() ||
1230 (CXXRD->hasDefinition() && !CXXRD->isTrivial()))
1231 Flags |= llvm::DINode::FlagNonTrivial;
1238 llvm::DICompositeType *RetTy = DBuilder.createReplaceableCompositeType(
1242 if (
auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD))
1243 DBuilder.replaceArrays(RetTy, llvm::DINodeArray(),
1244 CollectCXXTemplateParams(TSpecial, DefUnit));
1245 ReplaceMap.emplace_back(
1246 std::piecewise_construct, std::make_tuple(Ty),
1247 std::make_tuple(
static_cast<llvm::Metadata *
>(RetTy)));
1251llvm::DIType *CGDebugInfo::CreatePointerLikeType(llvm::dwarf::Tag Tag,
1254 llvm::DIFile *Unit) {
1259 std::optional<unsigned> DWARFAddressSpace =
1265 BTFAttrTy = dyn_cast<BTFTagAttributedType>(
Atomic->getValueType());
1267 BTFAttrTy = dyn_cast<BTFTagAttributedType>(PointeeTy);
1270 StringRef
Tag = BTFAttrTy->
getAttr()->getBTFTypeTag();
1272 llvm::Metadata *Ops[2] = {
1273 llvm::MDString::get(CGM.
getLLVMContext(), StringRef(
"btf_type_tag")),
1275 Annots.insert(Annots.begin(),
1278 BTFAttrTy = dyn_cast<BTFTagAttributedType>(BTFAttrTy->
getWrappedType());
1281 llvm::DINodeArray Annotations =
nullptr;
1282 if (Annots.size() > 0)
1283 Annotations = DBuilder.getOrCreateArray(Annots);
1285 if (Tag == llvm::dwarf::DW_TAG_reference_type ||
1286 Tag == llvm::dwarf::DW_TAG_rvalue_reference_type)
1287 return DBuilder.createReferenceType(Tag, getOrCreateType(PointeeTy, Unit),
1288 Size, Align, DWARFAddressSpace);
1290 return DBuilder.createPointerType(getOrCreateType(PointeeTy, Unit), Size,
1291 Align, DWARFAddressSpace, StringRef(),
1295llvm::DIType *CGDebugInfo::getOrCreateStructPtrType(StringRef Name,
1296 llvm::DIType *&
Cache) {
1299 Cache = DBuilder.createForwardDecl(llvm::dwarf::DW_TAG_structure_type, Name,
1300 TheCU, TheCU->getFile(), 0);
1302 Cache = DBuilder.createPointerType(
Cache, Size);
1306uint64_t CGDebugInfo::collectDefaultElementTypesForBlockPointer(
1307 const BlockPointerType *Ty, llvm::DIFile *Unit, llvm::DIDerivedType *DescTy,
1320 EltTys.push_back(CreateMemberType(Unit, FType,
"__size", &FieldOffset));
1321 EltTys.push_back(CreateMemberType(Unit, FType,
"__align", &FieldOffset));
1324 EltTys.push_back(CreateMemberType(Unit, FType,
"__isa", &FieldOffset));
1326 EltTys.push_back(CreateMemberType(Unit, FType,
"__flags", &FieldOffset));
1327 EltTys.push_back(CreateMemberType(Unit, FType,
"__reserved", &FieldOffset));
1329 EltTys.push_back(CreateMemberType(Unit, FType,
"__FuncPtr", &FieldOffset));
1333 EltTys.push_back(DBuilder.createMemberType(
1334 Unit,
"__descriptor",
nullptr, LineNo, FieldSize, FieldAlign,
1335 FieldOffset, llvm::DINode::FlagZero, DescTy));
1336 FieldOffset += FieldSize;
1343 llvm::DIFile *Unit) {
1347 llvm::DINodeArray Elements;
1351 EltTys.push_back(CreateMemberType(Unit, FType,
"reserved", &FieldOffset));
1352 EltTys.push_back(CreateMemberType(Unit, FType,
"Size", &FieldOffset));
1354 Elements = DBuilder.getOrCreateArray(EltTys);
1357 llvm::DINode::DIFlags Flags = llvm::DINode::FlagAppleBlock;
1360 DBuilder.createStructType(Unit,
"__block_descriptor",
nullptr, 0,
1361 FieldOffset, 0, Flags,
nullptr, Elements);
1366 auto *DescTy = DBuilder.createPointerType(EltTy, Size);
1368 FieldOffset = collectDefaultElementTypesForBlockPointer(Ty, Unit, DescTy,
1371 Elements = DBuilder.getOrCreateArray(EltTys);
1377 EltTy = DBuilder.createStructType(Unit,
"",
nullptr, 0, FieldOffset, 0,
1378 Flags,
nullptr, Elements);
1380 return DBuilder.createPointerType(EltTy, Size);
1397 if (Param->isParameterPack()) {
1406 if (SubstArgs.empty()) {
1415 SpecArgs.push_back(SubstArgs.front());
1416 SubstArgs = SubstArgs.drop_front();
1422 llvm::DIFile *Unit) {
1427 if (isa<BuiltinTemplateDecl>(TD))
1430 const auto *
AliasDecl = cast<TypeAliasTemplateDecl>(TD)->getTemplatedDecl();
1435 llvm::raw_svector_ostream OS(NS);
1437 auto PP = getPrintingPolicy();
1464 auto ArgVector = ::GetTemplateArgs(TD, Ty);
1473 llvm::raw_string_ostream OS(Name);
1476 llvm::codegenoptions::DebugTemplateNamesKind::Simple ||
1477 !HasReconstitutableArgs(Args.Args))
1480 llvm::DIDerivedType *AliasTy = DBuilder.createTemplateAlias(
1481 Src, Name, getOrCreateFile(
Loc), getLineNumber(
Loc),
1482 getDeclContextDescriptor(
AliasDecl), CollectTemplateParams(Args, Unit));
1488 return DBuilder.createTypedef(Src, OS.str(), getOrCreateFile(
Loc),
1505 return llvm::DINode::FlagZero;
1509 return llvm::DINode::FlagPrivate;
1511 return llvm::DINode::FlagProtected;
1513 return llvm::DINode::FlagPublic;
1515 return llvm::DINode::FlagZero;
1517 llvm_unreachable(
"unexpected access enumerator");
1520llvm::DIType *CGDebugInfo::CreateType(
const TypedefType *Ty,
1521 llvm::DIFile *Unit) {
1522 llvm::DIType *Underlying =
1534 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(Ty->
getDecl());
1536 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
1538 if (isa<RecordDecl>(DC))
1541 return DBuilder.createTypedef(Underlying, Ty->
getDecl()->
getName(),
1542 getOrCreateFile(
Loc), getLineNumber(
Loc),
1543 getDeclContextDescriptor(Ty->
getDecl()), Align,
1544 Flags, Annotations);
1554 return llvm::dwarf::DW_CC_BORLAND_stdcall;
1556 return llvm::dwarf::DW_CC_BORLAND_msfastcall;
1558 return llvm::dwarf::DW_CC_BORLAND_thiscall;
1560 return llvm::dwarf::DW_CC_LLVM_vectorcall;
1562 return llvm::dwarf::DW_CC_BORLAND_pascal;
1564 return llvm::dwarf::DW_CC_LLVM_Win64;
1566 return llvm::dwarf::DW_CC_LLVM_X86_64SysV;
1570 return llvm::dwarf::DW_CC_LLVM_AAPCS;
1572 return llvm::dwarf::DW_CC_LLVM_AAPCS_VFP;
1574 return llvm::dwarf::DW_CC_LLVM_IntelOclBicc;
1576 return llvm::dwarf::DW_CC_LLVM_SpirFunction;
1579 return llvm::dwarf::DW_CC_LLVM_OpenCLKernel;
1581 return llvm::dwarf::DW_CC_LLVM_Swift;
1583 return llvm::dwarf::DW_CC_LLVM_SwiftTail;
1585 return llvm::dwarf::DW_CC_LLVM_PreserveMost;
1587 return llvm::dwarf::DW_CC_LLVM_PreserveAll;
1589 return llvm::dwarf::DW_CC_LLVM_X86RegCall;
1591 return llvm::dwarf::DW_CC_LLVM_M68kRTD;
1593 return llvm::dwarf::DW_CC_LLVM_PreserveNone;
1595 return llvm::dwarf::DW_CC_LLVM_RISCVVectorCall;
1601 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
1603 Flags |= llvm::DINode::FlagLValueReference;
1605 Flags |= llvm::DINode::FlagRValueReference;
1609llvm::DIType *CGDebugInfo::CreateType(
const FunctionType *Ty,
1610 llvm::DIFile *Unit) {
1611 const auto *FPT = dyn_cast<FunctionProtoType>(Ty);
1613 if (llvm::DIType *QTy = CreateQualifiedType(FPT, Unit))
1622 EltTys.push_back(getOrCreateType(Ty->
getReturnType(), Unit));
1624 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
1628 EltTys.push_back(DBuilder.createUnspecifiedParameter());
1631 for (
const QualType &ParamType : FPT->param_types())
1632 EltTys.push_back(getOrCreateType(ParamType, Unit));
1633 if (FPT->isVariadic())
1634 EltTys.push_back(DBuilder.createUnspecifiedParameter());
1637 llvm::DITypeRefArray EltTypeArray = DBuilder.getOrCreateTypeArray(EltTys);
1638 llvm::DIType *F = DBuilder.createSubroutineType(
1643llvm::DIDerivedType *
1644CGDebugInfo::createBitFieldType(
const FieldDecl *BitFieldDecl,
1645 llvm::DIScope *RecordTy,
const RecordDecl *RD) {
1646 StringRef Name = BitFieldDecl->
getName();
1648 if (BitFieldDecl->
hasAttr<PreferredTypeAttr>())
1649 Ty = BitFieldDecl->
getAttr<PreferredTypeAttr>()->getType();
1651 llvm::DIFile *VUnit = getOrCreateFile(
Loc);
1652 llvm::DIType *DebugType = getOrCreateType(Ty, VUnit);
1655 llvm::DIFile *
File = getOrCreateFile(
Loc);
1656 unsigned Line = getLineNumber(
Loc);
1661 assert(SizeInBits > 0 &&
"found named 0-width bitfield");
1670 uint64_t OffsetInBits = StorageOffsetInBits + Offset;
1672 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(BitFieldDecl);
1673 return DBuilder.createBitFieldMemberType(
1674 RecordTy, Name,
File,
Line, SizeInBits, OffsetInBits, StorageOffsetInBits,
1675 Flags, DebugType, Annotations);
1678llvm::DIDerivedType *CGDebugInfo::createBitFieldSeparatorIfNeeded(
1679 const FieldDecl *BitFieldDecl,
const llvm::DIDerivedType *BitFieldDI,
1707 if (PreviousFieldsDI.empty())
1711 auto *PreviousMDEntry =
1712 PreviousFieldsDI.empty() ? nullptr : PreviousFieldsDI.back();
1713 auto *PreviousMDField =
1714 dyn_cast_or_null<llvm::DIDerivedType>(PreviousMDEntry);
1715 if (!PreviousMDField || !PreviousMDField->isBitField() ||
1716 PreviousMDField->getSizeInBits() == 0)
1720 std::advance(PreviousBitfield, BitFieldDecl->
getFieldIndex() - 1);
1722 assert(PreviousBitfield->isBitField());
1725 if (!PreviousBitfield->isZeroLengthBitField(Context))
1728 QualType Ty = PreviousBitfield->getType();
1730 llvm::DIFile *VUnit = getOrCreateFile(
Loc);
1731 llvm::DIType *DebugType = getOrCreateType(Ty, VUnit);
1732 llvm::DIScope *RecordTy = BitFieldDI->getScope();
1734 llvm::DIFile *
File = getOrCreateFile(
Loc);
1735 unsigned Line = getLineNumber(
Loc);
1738 cast<llvm::ConstantInt>(BitFieldDI->getStorageOffsetInBits())
1741 llvm::DINode::DIFlags Flags =
1743 llvm::DINodeArray Annotations =
1744 CollectBTFDeclTagAnnotations(*PreviousBitfield);
1745 return DBuilder.createBitFieldMemberType(
1746 RecordTy,
"",
File,
Line, 0, StorageOffsetInBits, StorageOffsetInBits,
1747 Flags, DebugType, Annotations);
1750llvm::DIType *CGDebugInfo::createFieldType(
1752 uint64_t offsetInBits, uint32_t AlignInBits, llvm::DIFile *tunit,
1753 llvm::DIScope *scope,
const RecordDecl *RD, llvm::DINodeArray Annotations) {
1754 llvm::DIType *debugType = getOrCreateType(
type, tunit);
1757 llvm::DIFile *file = getOrCreateFile(loc);
1758 const unsigned line = getLineNumber(loc.
isValid() ? loc : CurLoc);
1761 auto Align = AlignInBits;
1762 if (!
type->isIncompleteArrayType()) {
1764 SizeInBits = TI.
Width;
1770 return DBuilder.createMemberType(scope, name, file, line, SizeInBits, Align,
1771 offsetInBits, flags, debugType, Annotations);
1775CGDebugInfo::createInlinedTrapSubprogram(StringRef FuncName,
1776 llvm::DIFile *FileScope) {
1780 llvm::DISubprogram *&SP = InlinedTrapFuncMap[FuncName];
1783 llvm::DISubroutineType *DIFnTy = DBuilder.createSubroutineType(
nullptr);
1784 SP = DBuilder.createFunction(
1785 FileScope, FuncName, StringRef(),
1786 FileScope, 0, DIFnTy,
1788 llvm::DINode::FlagArtificial,
1789 llvm::DISubprogram::SPFlagDefinition,
1790 nullptr,
nullptr,
nullptr);
1796void CGDebugInfo::CollectRecordLambdaFields(
1798 llvm::DIType *RecordTy) {
1804 unsigned fieldno = 0;
1807 I !=
E; ++I, ++Field, ++fieldno) {
1809 if (
C.capturesVariable()) {
1811 assert(!
Field->isBitField() &&
"lambdas don't have bitfield members!");
1813 StringRef VName =
V->getName();
1814 llvm::DIFile *VUnit = getOrCreateFile(
Loc);
1816 llvm::DIType *FieldType = createFieldType(
1818 layout.
getFieldOffset(fieldno), Align, VUnit, RecordTy, CXXDecl);
1819 elements.push_back(FieldType);
1820 }
else if (
C.capturesThis()) {
1826 llvm::DIFile *VUnit = getOrCreateFile(f->
getLocation());
1828 StringRef ThisName =
1830 llvm::DIType *fieldType = createFieldType(
1834 elements.push_back(fieldType);
1839llvm::DIDerivedType *
1840CGDebugInfo::CreateRecordStaticField(
const VarDecl *Var, llvm::DIType *RecordTy,
1845 llvm::DIFile *VUnit = getOrCreateFile(Var->
getLocation());
1846 llvm::DIType *VTy = getOrCreateType(Var->
getType(), VUnit);
1848 unsigned LineNumber = getLineNumber(Var->
getLocation());
1849 StringRef VName = Var->
getName();
1853 llvm::Constant *
C =
nullptr;
1859 if (
Value->isFloat())
1866 ? llvm::dwarf::DW_TAG_variable
1867 : llvm::dwarf::DW_TAG_member;
1869 llvm::DIDerivedType *GV = DBuilder.createStaticMemberType(
1870 RecordTy, VName, VUnit, LineNumber, VTy, Flags,
C, Tag, Align);
1875void CGDebugInfo::CollectRecordNormalField(
1876 const FieldDecl *field, uint64_t OffsetInBits, llvm::DIFile *tunit,
1883 if (
name.empty() && !
type->isRecordType())
1886 llvm::DIType *FieldType;
1888 llvm::DIDerivedType *BitFieldType;
1889 FieldType = BitFieldType = createBitFieldType(field, RecordTy, RD);
1890 if (llvm::DIType *Separator =
1891 createBitFieldSeparatorIfNeeded(field, BitFieldType, elements, RD))
1892 elements.push_back(Separator);
1895 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(field);
1898 OffsetInBits, Align, tunit, RecordTy, RD, Annotations);
1901 elements.push_back(FieldType);
1904void CGDebugInfo::CollectRecordNestedType(
1908 if (isa<InjectedClassNameType>(Ty))
1911 llvm::DIType *nestedType = getOrCreateType(Ty, getOrCreateFile(
Loc));
1912 elements.push_back(nestedType);
1915void CGDebugInfo::CollectRecordFields(
1916 const RecordDecl *record, llvm::DIFile *tunit,
1918 llvm::DICompositeType *RecordTy) {
1919 const auto *CXXDecl = dyn_cast<CXXRecordDecl>(record);
1921 if (CXXDecl && CXXDecl->
isLambda())
1922 CollectRecordLambdaFields(CXXDecl, elements, RecordTy);
1927 unsigned fieldNo = 0;
1931 for (
const auto *I : record->
decls())
1932 if (
const auto *
V = dyn_cast<VarDecl>(I)) {
1933 if (
V->hasAttr<NoDebugAttr>())
1939 isa<VarTemplateSpecializationDecl>(
V))
1942 if (isa<VarTemplatePartialSpecializationDecl>(
V))
1946 auto MI = StaticDataMemberCache.find(
V->getCanonicalDecl());
1947 if (MI != StaticDataMemberCache.end()) {
1948 assert(MI->second &&
1949 "Static data member declaration should still exist");
1950 elements.push_back(MI->second);
1952 auto Field = CreateRecordStaticField(
V, RecordTy, record);
1953 elements.push_back(Field);
1955 }
else if (
const auto *field = dyn_cast<FieldDecl>(I)) {
1956 CollectRecordNormalField(field, layout.
getFieldOffset(fieldNo), tunit,
1957 elements, RecordTy, record);
1964 if (
const auto *nestedType = dyn_cast<TypeDecl>(I)) {
1966 if (isa<RecordDecl>(I) &&
1967 cast<RecordDecl>(I)->isAnonymousStructOrUnion())
1969 if (!nestedType->isImplicit() &&
1970 nestedType->getDeclContext() == record)
1971 CollectRecordNestedType(nestedType, elements);
1977llvm::DISubroutineType *
1978CGDebugInfo::getOrCreateMethodType(
const CXXMethodDecl *Method,
1979 llvm::DIFile *Unit) {
1982 return cast_or_null<llvm::DISubroutineType>(
1989 return getOrCreateInstanceMethodType(ThisType,
Func, Unit);
1992llvm::DISubroutineType *CGDebugInfo::getOrCreateInstanceMethodType(
2008 const auto *OriginalFunc = cast<llvm::DISubroutineType>(
2010 Func->getReturnType(),
Func->getParamTypes(), EPI),
2012 llvm::DITypeRefArray Args = OriginalFunc->getTypeArray();
2013 assert(Args.size() &&
"Invalid number of arguments!");
2018 Elts.push_back(Args[0]);
2024 llvm::DIType *ThisPtrType = getOrCreateType(ThisPtr, Unit);
2026 ThisPtrType = DBuilder.createObjectPointerType(ThisPtrType);
2027 Elts.push_back(ThisPtrType);
2031 for (
unsigned i = 1, e = Args.size(); i != e; ++i)
2032 Elts.push_back(Args[i]);
2034 llvm::DITypeRefArray EltTypeArray = DBuilder.getOrCreateTypeArray(Elts);
2036 return DBuilder.createSubroutineType(EltTypeArray, OriginalFunc->getFlags(),
2043 if (
const auto *NRD = dyn_cast<CXXRecordDecl>(RD->
getDeclContext()))
2050llvm::DISubprogram *CGDebugInfo::CreateCXXMemberFunction(
2051 const CXXMethodDecl *Method, llvm::DIFile *Unit, llvm::DIType *RecordTy) {
2053 isa<CXXConstructorDecl>(Method) || isa<CXXDestructorDecl>(Method);
2055 StringRef MethodName = getFunctionName(Method);
2056 llvm::DISubroutineType *MethodTy = getOrCreateMethodType(Method, Unit);
2060 StringRef MethodLinkageName;
2070 llvm::DIFile *MethodDefUnit =
nullptr;
2071 unsigned MethodLine = 0;
2073 MethodDefUnit = getOrCreateFile(Method->
getLocation());
2074 MethodLine = getLineNumber(Method->
getLocation());
2078 llvm::DIType *ContainingType =
nullptr;
2079 unsigned VIndex = 0;
2080 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
2081 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
2086 SPFlags |= llvm::DISubprogram::SPFlagPureVirtual;
2088 SPFlags |= llvm::DISubprogram::SPFlagVirtual;
2093 if (!isa<CXXDestructorDecl>(Method))
2098 const auto *DD = dyn_cast<CXXDestructorDecl>(Method);
2110 Flags |= llvm::DINode::FlagIntroducedVirtual;
2119 ContainingType = RecordTy;
2123 SPFlags |= llvm::DISubprogram::SPFlagDeleted;
2126 Flags |= llvm::DINode::FlagNoReturn;
2129 Flags |= llvm::DINode::FlagStaticMember;
2131 Flags |= llvm::DINode::FlagArtificial;
2133 if (
const auto *CXXC = dyn_cast<CXXConstructorDecl>(Method)) {
2134 if (CXXC->isExplicit())
2135 Flags |= llvm::DINode::FlagExplicit;
2136 }
else if (
const auto *CXXC = dyn_cast<CXXConversionDecl>(Method)) {
2137 if (CXXC->isExplicit())
2138 Flags |= llvm::DINode::FlagExplicit;
2141 Flags |= llvm::DINode::FlagPrototyped;
2143 Flags |= llvm::DINode::FlagLValueReference;
2145 Flags |= llvm::DINode::FlagRValueReference;
2147 SPFlags |= llvm::DISubprogram::SPFlagLocalToUnit;
2149 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
2153 if (DebugKind == llvm::codegenoptions::DebugInfoConstructor)
2157 llvm::DINodeArray TParamsArray = CollectFunctionTemplateParams(Method, Unit);
2158 llvm::DISubprogram *SP = DBuilder.createMethod(
2159 RecordTy, MethodName, MethodLinkageName, MethodDefUnit, MethodLine,
2160 MethodTy, VIndex,
ThisAdjustment, ContainingType, Flags, SPFlags,
2161 TParamsArray.get());
2168void CGDebugInfo::CollectCXXMemberFunctions(
2175 for (
const auto *I : RD->
decls()) {
2176 const auto *Method = dyn_cast<CXXMethodDecl>(I);
2200 EltTys.push_back(MI == SPCache.end()
2201 ? CreateCXXMemberFunction(Method, Unit, RecordTy)
2202 :
static_cast<llvm::Metadata *
>(MI->second));
2206void CGDebugInfo::CollectCXXBases(
const CXXRecordDecl *RD, llvm::DIFile *Unit,
2208 llvm::DIType *RecordTy) {
2209 llvm::DenseSet<CanonicalDeclPtr<const CXXRecordDecl>> SeenTypes;
2210 CollectCXXBasesAux(RD, Unit, EltTys, RecordTy, RD->
bases(), SeenTypes,
2211 llvm::DINode::FlagZero);
2216 CollectCXXBasesAux(RD, Unit, EltTys, RecordTy, RD->
vbases(), SeenTypes,
2217 llvm::DINode::FlagIndirectVirtualBase);
2221void CGDebugInfo::CollectCXXBasesAux(
2226 llvm::DINode::DIFlags StartingFlags) {
2228 for (
const auto &BI : Bases) {
2231 if (!SeenTypes.insert(
Base).second)
2233 auto *BaseTy = getOrCreateType(BI.getType(), Unit);
2234 llvm::DINode::DIFlags BFlags = StartingFlags;
2238 if (BI.isVirtual()) {
2255 BFlags |= llvm::DINode::FlagVirtual;
2262 llvm::DIType *DTy = DBuilder.createInheritance(RecordTy, BaseTy, BaseOffset,
2263 VBPtrOffset, BFlags);
2264 EltTys.push_back(DTy);
2269CGDebugInfo::CollectTemplateParams(std::optional<TemplateArgs> OArgs,
2270 llvm::DIFile *Unit) {
2272 return llvm::DINodeArray();
2273 TemplateArgs &Args = *OArgs;
2275 for (
unsigned i = 0, e = Args.Args.size(); i != e; ++i) {
2280 Name = Args.TList->getParam(i)->getName();
2284 llvm::DIType *TTy = getOrCreateType(TA.
getAsType(), Unit);
2285 TemplateParams.push_back(DBuilder.createTemplateTypeParameter(
2286 TheCU, Name, TTy, defaultParameter));
2291 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2292 TheCU, Name, TTy, defaultParameter,
2298 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2299 llvm::Constant *
V =
nullptr;
2306 if (
const auto *VD = dyn_cast<VarDecl>(
D))
2310 else if (
const auto *MD = dyn_cast<CXXMethodDecl>(
D);
2311 MD && MD->isImplicitObjectMemberFunction())
2313 else if (
const auto *FD = dyn_cast<FunctionDecl>(
D))
2317 else if (
const auto *MPT =
2318 dyn_cast<MemberPointerType>(
T.getTypePtr())) {
2326 }
else if (
const auto *GD = dyn_cast<MSGuidDecl>(
D)) {
2328 }
else if (
const auto *TPO = dyn_cast<TemplateParamObjectDecl>(
D)) {
2335 assert(
V &&
"Failed to find template parameter pointer");
2336 V =
V->stripPointerCasts();
2338 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2339 TheCU, Name, TTy, defaultParameter, cast_or_null<llvm::Constant>(
V)));
2343 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2344 llvm::Constant *
V =
nullptr;
2347 if (
const auto *MPT = dyn_cast<MemberPointerType>(
T.getTypePtr()))
2353 if (MPT->isMemberDataPointer())
2356 V = llvm::ConstantInt::get(CGM.
Int8Ty, 0);
2357 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2358 TheCU, Name, TTy, defaultParameter,
V));
2362 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2365 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2366 TheCU, Name, TTy, defaultParameter,
V));
2369 std::string QualName;
2370 llvm::raw_string_ostream OS(QualName);
2372 OS, getPrintingPolicy());
2373 TemplateParams.push_back(DBuilder.createTemplateTemplateParameter(
2374 TheCU, Name,
nullptr, QualName, defaultParameter));
2378 TemplateParams.push_back(DBuilder.createTemplateParameterPack(
2379 TheCU, Name,
nullptr,
2388 assert(
V &&
"Expression in template argument isn't constant");
2389 llvm::DIType *TTy = getOrCreateType(
T, Unit);
2390 TemplateParams.push_back(DBuilder.createTemplateValueParameter(
2391 TheCU, Name, TTy, defaultParameter,
V->stripPointerCasts()));
2397 "These argument types shouldn't exist in concrete types");
2400 return DBuilder.getOrCreateArray(TemplateParams);
2403std::optional<CGDebugInfo::TemplateArgs>
2404CGDebugInfo::GetTemplateArgs(
const FunctionDecl *FD)
const {
2412 return std::nullopt;
2414std::optional<CGDebugInfo::TemplateArgs>
2415CGDebugInfo::GetTemplateArgs(
const VarDecl *VD)
const {
2419 auto *TS = dyn_cast<VarTemplateSpecializationDecl>(VD);
2421 return std::nullopt;
2424 auto TA = TS->getTemplateArgs().asArray();
2425 return {{TList, TA}};
2427std::optional<CGDebugInfo::TemplateArgs>
2428CGDebugInfo::GetTemplateArgs(
const RecordDecl *RD)
const {
2429 if (
auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD)) {
2434 TSpecial->getSpecializedTemplate()->getTemplateParameters();
2436 return {{TPList, TAList.
asArray()}};
2438 return std::nullopt;
2442CGDebugInfo::CollectFunctionTemplateParams(
const FunctionDecl *FD,
2443 llvm::DIFile *Unit) {
2444 return CollectTemplateParams(GetTemplateArgs(FD), Unit);
2447llvm::DINodeArray CGDebugInfo::CollectVarTemplateParams(
const VarDecl *VL,
2448 llvm::DIFile *Unit) {
2449 return CollectTemplateParams(GetTemplateArgs(VL), Unit);
2452llvm::DINodeArray CGDebugInfo::CollectCXXTemplateParams(
const RecordDecl *RD,
2453 llvm::DIFile *Unit) {
2454 return CollectTemplateParams(GetTemplateArgs(RD), Unit);
2457llvm::DINodeArray CGDebugInfo::CollectBTFDeclTagAnnotations(
const Decl *
D) {
2463 llvm::Metadata *Ops[2] = {
2464 llvm::MDString::get(CGM.
getLLVMContext(), StringRef(
"btf_decl_tag")),
2466 Annotations.push_back(llvm::MDNode::get(CGM.
getLLVMContext(), Ops));
2468 return DBuilder.getOrCreateArray(Annotations);
2471llvm::DIType *CGDebugInfo::getOrCreateVTablePtrType(llvm::DIFile *Unit) {
2473 return VTablePtrType;
2478 llvm::Metadata *STy = getOrCreateType(Context.
IntTy, Unit);
2479 llvm::DITypeRefArray SElements = DBuilder.getOrCreateTypeArray(STy);
2480 llvm::DIType *SubTy = DBuilder.createSubroutineType(SElements);
2483 std::optional<unsigned> DWARFAddressSpace =
2486 llvm::DIType *vtbl_ptr_type = DBuilder.createPointerType(
2487 SubTy, Size, 0, DWARFAddressSpace,
"__vtbl_ptr_type");
2488 VTablePtrType = DBuilder.createPointerType(vtbl_ptr_type, Size);
2489 return VTablePtrType;
2492StringRef CGDebugInfo::getVTableName(
const CXXRecordDecl *RD) {
2497StringRef CGDebugInfo::getDynamicInitializerName(
const VarDecl *VD,
2499 llvm::Function *InitFn) {
2504 return InitFn->getName();
2514 llvm::raw_svector_ostream OS(QualifiedGV);
2516 std::tie(Quals, GVName) = OS.str().rsplit(
"::");
2518 std::swap(Quals, GVName);
2522 llvm::raw_svector_ostream OS(InitName);
2524 OS << Quals <<
"::";
2529 llvm_unreachable(
"not an initializer");
2531 OS <<
"`dynamic initializer for '";
2534 OS <<
"`dynamic atexit destructor for '";
2541 if (
const auto *VTpl = dyn_cast<VarTemplateSpecializationDecl>(VD)) {
2543 getPrintingPolicy());
2548 return internString(OS.str());
2551void CGDebugInfo::CollectVTableInfo(
const CXXRecordDecl *RD, llvm::DIFile *Unit,
2568 llvm::DIType *VPtrTy =
nullptr;
2571 if (NeedVTableShape) {
2576 unsigned VSlotCount =
2578 unsigned VTableWidth = PtrWidth * VSlotCount;
2580 std::optional<unsigned> DWARFAddressSpace =
2584 llvm::DIType *VTableType = DBuilder.createPointerType(
2585 nullptr, VTableWidth, 0, DWARFAddressSpace,
"__vtbl_ptr_type");
2586 EltTys.push_back(VTableType);
2589 VPtrTy = DBuilder.createPointerType(VTableType, PtrWidth);
2597 VPtrTy = getOrCreateVTablePtrType(Unit);
2600 llvm::DIType *VPtrMember =
2601 DBuilder.createMemberType(Unit, getVTableName(RD), Unit, 0, Size, 0, 0,
2602 llvm::DINode::FlagArtificial, VPtrTy);
2603 EltTys.push_back(VPtrMember);
2609 llvm::DIType *
T = getOrCreateType(RTy, getOrCreateFile(
Loc));
2621 assert(!
D.isNull() &&
"null type");
2622 llvm::DIType *
T = getOrCreateType(
D, getOrCreateFile(
Loc));
2623 assert(
T &&
"could not create debug info for type");
2625 RetainedTypes.push_back(
D.getAsOpaquePtr());
2633 llvm::codegenoptions::DebugLineTablesOnly)
2639 node = getOrCreateType(AllocatedTy, getOrCreateFile(
Loc));
2641 CI->setMetadata(
"heapallocsite", node);
2645 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
2649 auto I = TypeCache.find(TyPtr);
2650 if (I == TypeCache.end() || !cast<llvm::DIType>(I->second)->isForwardDecl())
2652 llvm::DIType *Res = CreateTypeDefinition(Ty->
castAs<
EnumType>());
2653 assert(!Res->isForwardDecl());
2654 TypeCache[TyPtr].reset(Res);
2658 if (DebugKind > llvm::codegenoptions::LimitedDebugInfo ||
2665 if (RD->
hasAttr<DLLImportAttr>())
2668 if (MD->hasAttr<DLLImportAttr>())
2681 if (
auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD)) {
2691 if (
auto *TD = dyn_cast<ClassTemplateSpecializationDecl>(CXXDecl))
2692 Explicit = TD->isExplicitInstantiationOrSpecialization();
2706 if (
auto *CXXRD = dyn_cast<CXXRecordDecl>(RD))
2707 if (CXXRD->isDynamicClass() &&
2709 llvm::GlobalValue::AvailableExternallyLinkage &&
2720 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
2724 auto I = TypeCache.find(TyPtr);
2725 if (I != TypeCache.end() && !cast<llvm::DIType>(I->second)->isForwardDecl())
2732 assert(!Res->isForwardDecl());
2733 TypeCache[TyPtr].reset(Res);
2740 if (!Tmpl->isImplicit() && Tmpl->isThisDeclarationADefinition() &&
2741 !MD->getMemberSpecializationInfo()->isExplicitSpecialization())
2764 if (Ctor->isCopyOrMoveConstructor())
2766 if (!Ctor->isDeleted())
2785 if (DebugKind == llvm::codegenoptions::DebugLineTablesOnly)
2788 if (DebugKind > llvm::codegenoptions::LimitedDebugInfo ||
2789 RD->
hasAttr<StandaloneDebugAttr>())
2792 if (!LangOpts.CPlusPlus)
2798 const auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD);
2814 if (
const auto *SD = dyn_cast<ClassTemplateSpecializationDecl>(RD))
2815 Spec = SD->getSpecializationKind();
2824 if ((DebugKind == llvm::codegenoptions::DebugInfoConstructor) &&
2836 llvm::DIType *
T = getTypeOrNull(Ty);
2837 if (
T &&
T->isForwardDecl())
2841llvm::DIType *CGDebugInfo::CreateType(
const RecordType *Ty) {
2843 llvm::DIType *
T = cast_or_null<llvm::DIType>(getTypeOrNull(
QualType(Ty, 0)));
2847 T = getOrCreateRecordFwdDecl(Ty, getDeclContextDescriptor(RD));
2851 auto [Def, Pref] = CreateTypeDefinition(Ty);
2853 return Pref ? Pref : Def;
2856llvm::DIType *CGDebugInfo::GetPreferredNameType(
const CXXRecordDecl *RD,
2857 llvm::DIFile *Unit) {
2861 auto const *PNA = RD->
getAttr<PreferredNameAttr>();
2865 return getOrCreateType(PNA->getTypedefType(), Unit);
2868std::pair<llvm::DIType *, llvm::DIType *>
2869CGDebugInfo::CreateTypeDefinition(
const RecordType *Ty) {
2873 llvm::DIFile *DefUnit = getOrCreateFile(RD->
getLocation());
2881 llvm::DICompositeType *FwdDecl = getOrCreateLimitedType(Ty);
2884 if (!
D || !
D->isCompleteDefinition())
2885 return {FwdDecl,
nullptr};
2887 if (
const auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD))
2888 CollectContainingType(CXXDecl, FwdDecl);
2891 LexicalBlockStack.emplace_back(&*FwdDecl);
2892 RegionMap[Ty->
getDecl()].reset(FwdDecl);
2902 const auto *CXXDecl = dyn_cast<CXXRecordDecl>(RD);
2904 CollectCXXBases(CXXDecl, DefUnit, EltTys, FwdDecl);
2905 CollectVTableInfo(CXXDecl, DefUnit, EltTys);
2909 CollectRecordFields(RD, DefUnit, EltTys, FwdDecl);
2910 if (CXXDecl && !CGM.
getCodeGenOpts().DebugOmitUnreferencedMethods)
2911 CollectCXXMemberFunctions(CXXDecl, DefUnit, EltTys, FwdDecl);
2913 LexicalBlockStack.pop_back();
2914 RegionMap.erase(Ty->
getDecl());
2916 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
2917 DBuilder.replaceArrays(FwdDecl, Elements);
2919 if (FwdDecl->isTemporary())
2921 llvm::MDNode::replaceWithPermanent(llvm::TempDICompositeType(FwdDecl));
2923 RegionMap[Ty->
getDecl()].reset(FwdDecl);
2925 if (CGM.
getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::LLDB)
2926 if (
auto *PrefDI = GetPreferredNameType(CXXDecl, DefUnit))
2927 return {FwdDecl, PrefDI};
2929 return {FwdDecl,
nullptr};
2933 llvm::DIFile *Unit) {
2939 llvm::DIFile *Unit) {
2944 return DBuilder.createTypedef(
2947 getDeclContextDescriptor(Ty->
getDecl()));
2975 llvm::DIFile *Unit) {
2981 static_cast<llvm::dwarf::SourceLanguage
>(TheCU->getSourceLanguage());
2986 if (DebugTypeExtRefs &&
ID->isFromASTFile() &&
ID->getDefinition() &&
2987 !
ID->getImplementation())
2988 return DBuilder.createForwardDecl(
2989 llvm::dwarf::DW_TAG_structure_type,
ID->getName(),
2990 getDeclContextDescriptor(ID), Unit, 0, RuntimeLang);
2993 llvm::DIFile *DefUnit = getOrCreateFile(
ID->getLocation());
2994 unsigned Line = getLineNumber(
ID->getLocation());
3000 llvm::DIScope *Mod = getParentModuleOrNull(ID);
3001 llvm::DIType *FwdDecl = DBuilder.createReplaceableCompositeType(
3002 llvm::dwarf::DW_TAG_structure_type,
ID->getName(), Mod ? Mod : TheCU,
3003 DefUnit,
Line, RuntimeLang);
3004 ObjCInterfaceCache.push_back(ObjCInterfaceCacheEntry(Ty, FwdDecl, Unit));
3008 return CreateTypeDefinition(Ty, Unit);
3012 bool CreateSkeletonCU) {
3017 auto ModRef = ModuleCache.find(M);
3018 if (ModRef != ModuleCache.end())
3019 return cast<llvm::DIModule>(ModRef->second);
3024 llvm::raw_svector_ostream OS(ConfigMacros);
3028 for (
auto &M : PPOpts.Macros) {
3031 const std::string &
Macro = M.first;
3032 bool Undef = M.second;
3033 OS <<
"\"-" << (Undef ?
'U' :
'D');
3034 for (
char c : Macro)
3049 bool IsRootModule = M ? !M->
Parent :
true;
3053 if (CreateSkeletonCU && IsRootModule && Mod.
getASTFile().empty() && M)
3055 "clang module without ASTFile must be specified by -fmodule-name");
3058 auto RemapPath = [
this](StringRef
Path) -> std::string {
3060 StringRef Relative(Remapped);
3061 StringRef CompDir = TheCU->getDirectory();
3062 if (Relative.consume_front(CompDir))
3063 Relative.consume_front(llvm::sys::path::get_separator());
3065 return Relative.str();
3068 if (CreateSkeletonCU && IsRootModule && !Mod.
getASTFile().empty()) {
3075 Signature = ModSig.truncatedValue();
3081 if (!llvm::sys::path::is_absolute(Mod.
getASTFile())) {
3083 PCM = getCurrentDirname();
3087 llvm::sys::path::append(PCM, Mod.
getASTFile());
3088 DIB.createCompileUnit(
3089 TheCU->getSourceLanguage(),
3092 TheCU->getProducer(),
false, StringRef(), 0, RemapPath(PCM),
3093 llvm::DICompileUnit::FullDebug, Signature);
3098 IsRootModule ? nullptr
3101 std::string IncludePath = Mod.
getPath().str();
3102 llvm::DIModule *DIMod =
3104 RemapPath(IncludePath));
3105 ModuleCache[M].reset(DIMod);
3110 llvm::DIFile *Unit) {
3112 llvm::DIFile *DefUnit = getOrCreateFile(
ID->getLocation());
3113 unsigned Line = getLineNumber(
ID->getLocation());
3114 unsigned RuntimeLang = TheCU->getSourceLanguage();
3120 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
3121 if (
ID->getImplementation())
3122 Flags |= llvm::DINode::FlagObjcClassComplete;
3124 llvm::DIScope *Mod = getParentModuleOrNull(ID);
3125 llvm::DICompositeType *RealDecl = DBuilder.createStructType(
3126 Mod ? Mod : Unit,
ID->getName(), DefUnit,
Line, Size, Align, Flags,
3127 nullptr, llvm::DINodeArray(), RuntimeLang);
3130 TypeCache[QTy.getAsOpaquePtr()].reset(RealDecl);
3133 LexicalBlockStack.emplace_back(RealDecl);
3134 RegionMap[Ty->
getDecl()].reset(RealDecl);
3141 llvm::DIType *SClassTy =
3146 llvm::DIType *InhTag = DBuilder.createInheritance(RealDecl, SClassTy, 0, 0,
3147 llvm::DINode::FlagZero);
3148 EltTys.push_back(InhTag);
3154 llvm::DIFile *PUnit = getOrCreateFile(
Loc);
3155 unsigned PLine = getLineNumber(
Loc);
3158 llvm::MDNode *PropertyNode = DBuilder.createObjCProperty(
3159 PD->getName(), PUnit, PLine,
3161 : getSelectorName(PD->getGetterName()),
3163 : getSelectorName(PD->getSetterName()),
3164 PD->getPropertyAttributes(), getOrCreateType(PD->getType(), PUnit));
3165 EltTys.push_back(PropertyNode);
3170 typedef std::pair<char, const IdentifierInfo *> IsClassAndIdent;
3174 llvm::DenseSet<IsClassAndIdent> PropertySet;
3177 return std::make_pair(PD->isClassProperty(), PD->getIdentifier());
3180 for (
auto *PD : ClassExt->properties()) {
3181 PropertySet.insert(GetIsClassAndIdent(PD));
3184 for (
const auto *PD :
ID->properties()) {
3187 if (!PropertySet.insert(GetIsClassAndIdent(PD)).second)
3194 unsigned FieldNo = 0;
3196 Field =
Field->getNextIvar(), ++FieldNo) {
3197 llvm::DIType *FieldTy = getOrCreateType(
Field->getType(), Unit);
3201 StringRef FieldName =
Field->getName();
3204 if (FieldName.empty())
3208 llvm::DIFile *FieldDefUnit = getOrCreateFile(
Field->getLocation());
3209 unsigned FieldLine = getLineNumber(
Field->getLocation());
3217 FieldSize =
Field->isBitField()
3228 if (
Field->isBitField()) {
3239 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
3241 Flags = llvm::DINode::FlagProtected;
3243 Flags = llvm::DINode::FlagPrivate;
3245 Flags = llvm::DINode::FlagPublic;
3247 if (
Field->isBitField())
3248 Flags |= llvm::DINode::FlagBitField;
3250 llvm::MDNode *PropertyNode =
nullptr;
3253 ImpD->FindPropertyImplIvarDecl(
Field->getIdentifier())) {
3256 llvm::DIFile *PUnit = getOrCreateFile(
Loc);
3257 unsigned PLine = getLineNumber(
Loc);
3260 PropertyNode = DBuilder.createObjCProperty(
3261 PD->getName(), PUnit, PLine,
3264 : getSelectorName(PD->getGetterName()),
3267 : getSelectorName(PD->getSetterName()),
3268 PD->getPropertyAttributes(),
3269 getOrCreateType(PD->getType(), PUnit));
3273 FieldTy = DBuilder.createObjCIVar(FieldName, FieldDefUnit, FieldLine,
3274 FieldSize, FieldAlign, FieldOffset, Flags,
3275 FieldTy, PropertyNode);
3276 EltTys.push_back(FieldTy);
3279 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
3280 DBuilder.replaceArrays(RealDecl, Elements);
3282 LexicalBlockStack.pop_back();
3286llvm::DIType *CGDebugInfo::CreateType(
const VectorType *Ty,
3287 llvm::DIFile *Unit) {
3305 llvm::DIType *ElementTy = getOrCreateType(Ty->
getElementType(), Unit);
3308 llvm::Metadata *Subscript;
3310 auto SizeExpr = SizeExprCache.find(QTy);
3311 if (SizeExpr != SizeExprCache.end())
3312 Subscript = DBuilder.getOrCreateSubrange(
3313 SizeExpr->getSecond() ,
nullptr ,
3314 nullptr ,
nullptr );
3317 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3318 llvm::Type::getInt64Ty(CGM.
getLLVMContext()), Count ? Count : -1));
3319 Subscript = DBuilder.getOrCreateSubrange(
3320 CountNode ,
nullptr ,
nullptr ,
3323 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscript);
3328 return DBuilder.createVectorType(Size, Align, ElementTy, SubscriptArray);
3332 llvm::DIFile *Unit) {
3336 llvm::DIType *ElementTy = getOrCreateType(Ty->
getElementType(), Unit);
3342 auto *ColumnCountNode =
3343 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3345 auto *RowCountNode =
3346 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3348 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3349 ColumnCountNode ,
nullptr ,
nullptr ,
3351 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3352 RowCountNode ,
nullptr ,
nullptr ,
3354 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscripts);
3355 return DBuilder.createArrayType(Size, Align, ElementTy, SubscriptArray);
3358llvm::DIType *CGDebugInfo::CreateType(
const ArrayType *Ty, llvm::DIFile *Unit) {
3363 if (
const auto *VAT = dyn_cast<VariableArrayType>(Ty)) {
3387 while ((Ty = dyn_cast<ArrayType>(EltTy))) {
3396 if (
const auto *CAT = dyn_cast<ConstantArrayType>(Ty))
3397 Count = CAT->getZExtSize();
3398 else if (
const auto *VAT = dyn_cast<VariableArrayType>(Ty)) {
3399 if (
Expr *Size = VAT->getSizeExpr()) {
3402 Count =
Result.Val.getInt().getExtValue();
3406 auto SizeNode = SizeExprCache.find(EltTy);
3407 if (SizeNode != SizeExprCache.end())
3408 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3409 SizeNode->getSecond() ,
nullptr ,
3410 nullptr ,
nullptr ));
3413 llvm::ConstantAsMetadata::get(llvm::ConstantInt::getSigned(
3415 Subscripts.push_back(DBuilder.getOrCreateSubrange(
3416 CountNode ,
nullptr ,
nullptr ,
3422 llvm::DINodeArray SubscriptArray = DBuilder.getOrCreateArray(Subscripts);
3424 return DBuilder.createArrayType(Size, Align, getOrCreateType(EltTy, Unit),
3429 llvm::DIFile *Unit) {
3430 return CreatePointerLikeType(llvm::dwarf::DW_TAG_reference_type, Ty,
3435 llvm::DIFile *Unit) {
3436 llvm::dwarf::Tag
Tag = llvm::dwarf::DW_TAG_rvalue_reference_type;
3440 Tag = llvm::dwarf::DW_TAG_reference_type;
3442 return CreatePointerLikeType(Tag, Ty, Ty->
getPointeeType(), Unit);
3447 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
3457 Flags |= llvm::DINode::FlagSingleInheritance;
3460 Flags |= llvm::DINode::FlagMultipleInheritance;
3463 Flags |= llvm::DINode::FlagVirtualInheritance;
3473 return DBuilder.createMemberPointerType(
3479 return DBuilder.createMemberPointerType(
3480 getOrCreateInstanceMethodType(
3483 ClassType,
Size, 0, Flags);
3486llvm::DIType *CGDebugInfo::CreateType(
const AtomicType *Ty, llvm::DIFile *
U) {
3488 return DBuilder.createQualifiedType(llvm::dwarf::DW_TAG_atomic_type, FromTy);
3491llvm::DIType *CGDebugInfo::CreateType(
const PipeType *Ty, llvm::DIFile *
U) {
3500llvm::DIType *CGDebugInfo::CreateEnumType(
const EnumType *Ty) {
3512 bool isImportedFromModule =
3524 llvm::DIScope *EDContext = getDeclContextDescriptor(ED);
3525 llvm::DIFile *DefUnit = getOrCreateFile(ED->
getLocation());
3526 llvm::TempDIScope TmpContext(DBuilder.createReplaceableCompositeType(
3527 llvm::dwarf::DW_TAG_enumeration_type,
"", TheCU, DefUnit, 0));
3530 StringRef EDName = ED->
getName();
3531 llvm::DIType *RetTy = DBuilder.createReplaceableCompositeType(
3532 llvm::dwarf::DW_TAG_enumeration_type, EDName, EDContext, DefUnit,
Line,
3533 0, Size, Align, llvm::DINode::FlagFwdDecl,
Identifier);
3535 ReplaceMap.emplace_back(
3536 std::piecewise_construct, std::make_tuple(Ty),
3537 std::make_tuple(
static_cast<llvm::Metadata *
>(RetTy)));
3541 return CreateTypeDefinition(Ty);
3544llvm::DIType *CGDebugInfo::CreateTypeDefinition(
const EnumType *Ty) {
3557 assert(ED &&
"An enumeration definition is required");
3559 Enumerators.push_back(
3560 DBuilder.createEnumerator(
Enum->getName(),
Enum->getInitVal()));
3564 llvm::DINodeArray EltArray = DBuilder.getOrCreateArray(Enumerators);
3566 llvm::DIFile *DefUnit = getOrCreateFile(ED->
getLocation());
3568 llvm::DIScope *EnumContext = getDeclContextDescriptor(ED);
3569 llvm::DIType *ClassTy = getOrCreateType(ED->
getIntegerType(), DefUnit);
3570 return DBuilder.createEnumerationType(
3571 EnumContext, ED->
getName(), DefUnit,
Line, Size, Align, EltArray, ClassTy,
3577 StringRef Name, StringRef
Value) {
3578 unsigned Line = LineLoc.
isInvalid() ? 0 : getLineNumber(LineLoc);
3585 llvm::DIFile *FName = getOrCreateFile(FileLoc);
3586 unsigned Line = LineLoc.
isInvalid() ? 0 : getLineNumber(LineLoc);
3587 return DBuilder.createTempMacroFile(
Parent,
Line, FName);
3591 llvm::DebugLoc TrapLocation, StringRef
Category, StringRef FailureMsg) {
3599 FuncName += FailureMsg;
3601 llvm::DISubprogram *TrapSP =
3602 createInlinedTrapSubprogram(FuncName, TrapLocation->getFile());
3604 TrapSP, TrapLocation);
3614 Quals += InnerQuals;
3618 return C.getQualifiedType(
T.getTypePtr(), Quals);
3619 case Type::TemplateSpecialization: {
3620 const auto *Spec = cast<TemplateSpecializationType>(
T);
3621 if (Spec->isTypeAlias())
3622 return C.getQualifiedType(
T.getTypePtr(), Quals);
3626 case Type::TypeOfExpr:
3627 T = cast<TypeOfExprType>(
T)->getUnderlyingExpr()->getType();
3630 T = cast<TypeOfType>(
T)->getUnmodifiedType();
3632 case Type::Decltype:
3633 T = cast<DecltypeType>(
T)->getUnderlyingType();
3635 case Type::UnaryTransform:
3636 T = cast<UnaryTransformType>(
T)->getUnderlyingType();
3638 case Type::Attributed:
3639 T = cast<AttributedType>(
T)->getEquivalentType();
3641 case Type::BTFTagAttributed:
3642 T = cast<BTFTagAttributedType>(
T)->getWrappedType();
3644 case Type::CountAttributed:
3645 T = cast<CountAttributedType>(
T)->
desugar();
3647 case Type::Elaborated:
3648 T = cast<ElaboratedType>(
T)->getNamedType();
3651 T = cast<UsingType>(
T)->getUnderlyingType();
3654 T = cast<ParenType>(
T)->getInnerType();
3656 case Type::MacroQualified:
3657 T = cast<MacroQualifiedType>(
T)->getUnderlyingType();
3659 case Type::SubstTemplateTypeParm:
3660 T = cast<SubstTemplateTypeParmType>(
T)->getReplacementType();
3663 case Type::DeducedTemplateSpecialization: {
3664 QualType DT = cast<DeducedType>(
T)->getDeducedType();
3665 assert(!DT.
isNull() &&
"Undeduced types shouldn't reach here.");
3669 case Type::PackIndexing: {
3670 T = cast<PackIndexingType>(
T)->getSelectedType();
3673 case Type::Adjusted:
3676 T = cast<AdjustedType>(
T)->getAdjustedType();
3680 assert(
T != LastT &&
"Type unwrapping failed to unwrap!");
3685llvm::DIType *CGDebugInfo::getTypeOrNull(
QualType Ty) {
3688 if (It != TypeCache.end()) {
3690 if (llvm::Metadata *
V = It->second)
3691 return cast<llvm::DIType>(
V);
3703 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly ||
3713llvm::DIType *CGDebugInfo::getOrCreateType(
QualType Ty, llvm::DIFile *Unit) {
3717 llvm::TimeTraceScope TimeScope(
"DebugType", [&]() {
3719 llvm::raw_string_ostream OS(Name);
3720 Ty.
print(OS, getPrintingPolicy());
3727 if (
auto *
T = getTypeOrNull(Ty))
3730 llvm::DIType *Res = CreateTypeNode(Ty, Unit);
3731 void *TyPtr = Ty.getAsOpaquePtr();
3734 TypeCache[TyPtr].reset(Res);
3739llvm::DIModule *CGDebugInfo::getParentModuleOrNull(
const Decl *
D) {
3747 auto Info = Reader->getSourceDescriptor(Idx);
3749 return getOrCreateModuleRef(*Info,
true);
3750 }
else if (ClangModuleMap) {
3764 return getOrCreateModuleRef(Info,
false);
3767 return getOrCreateModuleRef(PCHDescriptor,
false);
3774llvm::DIType *CGDebugInfo::CreateTypeNode(
QualType Ty, llvm::DIFile *Unit) {
3777 return CreateQualifiedType(Ty, Unit);
3781#define TYPE(Class, Base)
3782#define ABSTRACT_TYPE(Class, Base)
3783#define NON_CANONICAL_TYPE(Class, Base)
3784#define DEPENDENT_TYPE(Class, Base) case Type::Class:
3785#include "clang/AST/TypeNodes.inc"
3786 llvm_unreachable(
"Dependent types cannot show up in debug information");
3788 case Type::ExtVector:
3790 return CreateType(cast<VectorType>(Ty), Unit);
3791 case Type::ConstantMatrix:
3792 return CreateType(cast<ConstantMatrixType>(Ty), Unit);
3793 case Type::ObjCObjectPointer:
3794 return CreateType(cast<ObjCObjectPointerType>(Ty), Unit);
3795 case Type::ObjCObject:
3796 return CreateType(cast<ObjCObjectType>(Ty), Unit);
3797 case Type::ObjCTypeParam:
3798 return CreateType(cast<ObjCTypeParamType>(Ty), Unit);
3799 case Type::ObjCInterface:
3800 return CreateType(cast<ObjCInterfaceType>(Ty), Unit);
3802 return CreateType(cast<BuiltinType>(Ty));
3804 return CreateType(cast<ComplexType>(Ty));
3806 return CreateType(cast<PointerType>(Ty), Unit);
3807 case Type::BlockPointer:
3808 return CreateType(cast<BlockPointerType>(Ty), Unit);
3810 return CreateType(cast<TypedefType>(Ty), Unit);
3812 return CreateType(cast<RecordType>(Ty));
3814 return CreateEnumType(cast<EnumType>(Ty));
3815 case Type::FunctionProto:
3816 case Type::FunctionNoProto:
3817 return CreateType(cast<FunctionType>(Ty), Unit);
3818 case Type::ConstantArray:
3819 case Type::VariableArray:
3820 case Type::IncompleteArray:
3821 case Type::ArrayParameter:
3822 return CreateType(cast<ArrayType>(Ty), Unit);
3824 case Type::LValueReference:
3825 return CreateType(cast<LValueReferenceType>(Ty), Unit);
3826 case Type::RValueReference:
3827 return CreateType(cast<RValueReferenceType>(Ty), Unit);
3829 case Type::MemberPointer:
3830 return CreateType(cast<MemberPointerType>(Ty), Unit);
3833 return CreateType(cast<AtomicType>(Ty), Unit);
3836 return CreateType(cast<BitIntType>(Ty));
3838 return CreateType(cast<PipeType>(Ty), Unit);
3840 case Type::TemplateSpecialization:
3841 return CreateType(cast<TemplateSpecializationType>(Ty), Unit);
3842 case Type::HLSLAttributedResource:
3843 return CreateType(cast<HLSLAttributedResourceType>(Ty), Unit);
3845 case Type::CountAttributed:
3847 case Type::Attributed:
3848 case Type::BTFTagAttributed:
3849 case Type::Adjusted:
3851 case Type::DeducedTemplateSpecialization:
3852 case Type::Elaborated:
3855 case Type::MacroQualified:
3856 case Type::SubstTemplateTypeParm:
3857 case Type::TypeOfExpr:
3859 case Type::Decltype:
3860 case Type::PackIndexing:
3861 case Type::UnaryTransform:
3865 llvm_unreachable(
"type should have been unwrapped!");
3868llvm::DICompositeType *
3869CGDebugInfo::getOrCreateLimitedType(
const RecordType *Ty) {
3872 auto *
T = cast_or_null<llvm::DICompositeType>(getTypeOrNull(QTy));
3877 if (
T && !
T->isForwardDecl())
3881 llvm::DICompositeType *Res = CreateLimitedType(Ty);
3886 DBuilder.replaceArrays(Res,
T ?
T->getElements() : llvm::DINodeArray());
3889 TypeCache[QTy.getAsOpaquePtr()].reset(Res);
3894llvm::DICompositeType *CGDebugInfo::CreateLimitedType(
const RecordType *Ty) {
3898 StringRef RDName = getClassName(RD);
3900 llvm::DIFile *DefUnit =
nullptr;
3903 DefUnit = getOrCreateFile(
Loc);
3907 llvm::DIScope *RDContext = getDeclContextDescriptor(RD);
3911 auto *
T = cast_or_null<llvm::DICompositeType>(
3919 if (!
D || !
D->isCompleteDefinition())
3920 return getOrCreateRecordFwdDecl(Ty, RDContext);
3933 auto Flags = llvm::DINode::FlagZero;
3934 if (
auto CXXRD = dyn_cast<CXXRecordDecl>(RD)) {
3936 Flags |= llvm::DINode::FlagTypePassByReference;
3938 Flags |= llvm::DINode::FlagTypePassByValue;
3941 if (!CXXRD->isTrivial())
3942 Flags |= llvm::DINode::FlagNonTrivial;
3945 if (CXXRD->isAnonymousStructOrUnion())
3946 Flags |= llvm::DINode::FlagExportSymbols;
3949 dyn_cast<CXXRecordDecl>(CXXRD->getDeclContext()));
3952 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(
D);
3953 llvm::DICompositeType *RealDecl = DBuilder.createReplaceableCompositeType(
3959 switch (RealDecl->getTag()) {
3961 llvm_unreachable(
"invalid composite type tag");
3963 case llvm::dwarf::DW_TAG_array_type:
3964 case llvm::dwarf::DW_TAG_enumeration_type:
3973 case llvm::dwarf::DW_TAG_structure_type:
3974 case llvm::dwarf::DW_TAG_union_type:
3975 case llvm::dwarf::DW_TAG_class_type:
3978 llvm::MDNode::replaceWithDistinct(llvm::TempDICompositeType(RealDecl));
3982 RegionMap[Ty->
getDecl()].reset(RealDecl);
3985 if (
const auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD))
3986 DBuilder.replaceArrays(RealDecl, llvm::DINodeArray(),
3987 CollectCXXTemplateParams(TSpecial, DefUnit));
3991void CGDebugInfo::CollectContainingType(
const CXXRecordDecl *RD,
3992 llvm::DICompositeType *RealDecl) {
3994 llvm::DIType *ContainingType =
nullptr;
4006 ContainingType = getOrCreateType(
QualType(PBase->getTypeForDecl(), 0),
4009 ContainingType = RealDecl;
4011 DBuilder.replaceVTableHolder(RealDecl, ContainingType);
4014llvm::DIType *CGDebugInfo::CreateMemberType(llvm::DIFile *Unit,
QualType FType,
4015 StringRef Name, uint64_t *Offset) {
4016 llvm::DIType *FieldTy = CGDebugInfo::getOrCreateType(FType, Unit);
4020 DBuilder.createMemberType(Unit, Name, Unit, 0, FieldSize, FieldAlign,
4021 *Offset, llvm::DINode::FlagZero, FieldTy);
4022 *Offset += FieldSize;
4026void CGDebugInfo::collectFunctionDeclProps(
GlobalDecl GD, llvm::DIFile *Unit,
4028 StringRef &LinkageName,
4029 llvm::DIScope *&FDContext,
4030 llvm::DINodeArray &TParamsArray,
4031 llvm::DINode::DIFlags &Flags) {
4033 Name = getFunctionName(FD);
4038 Flags |= llvm::DINode::FlagPrototyped;
4042 if (LinkageName == Name ||
4047 DebugKind <= llvm::codegenoptions::DebugLineTablesOnly))
4048 LinkageName = StringRef();
4053 (DebugKind == llvm::codegenoptions::DebugLineTablesOnly &&
4057 FDContext = getOrCreateNamespace(NSDecl);
4060 llvm::DIScope *Mod = getParentModuleOrNull(RDecl);
4061 FDContext = getContextDescriptor(RDecl, Mod ? Mod : TheCU);
4067 Flags |= llvm::DINode::FlagNoReturn;
4069 TParamsArray = CollectFunctionTemplateParams(FD, Unit);
4073void CGDebugInfo::collectVarDeclProps(
const VarDecl *VD, llvm::DIFile *&Unit,
4075 StringRef &Name, StringRef &LinkageName,
4076 llvm::MDTuple *&TemplateParameters,
4077 llvm::DIScope *&VDContext) {
4086 llvm::APInt ConstVal(32, 1);
4097 if (LinkageName == Name)
4098 LinkageName = StringRef();
4100 if (isa<VarTemplateSpecializationDecl>(VD)) {
4101 llvm::DINodeArray parameterNodes = CollectVarTemplateParams(VD, &*Unit);
4102 TemplateParameters = parameterNodes.get();
4104 TemplateParameters =
nullptr;
4124 llvm::DIScope *Mod = getParentModuleOrNull(VD);
4125 VDContext = getContextDescriptor(cast<Decl>(DC), Mod ? Mod : TheCU);
4128llvm::DISubprogram *CGDebugInfo::getFunctionFwdDeclOrStub(
GlobalDecl GD,
4130 llvm::DINodeArray TParamsArray;
4131 StringRef Name, LinkageName;
4132 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
4133 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
4135 llvm::DIFile *Unit = getOrCreateFile(
Loc);
4136 llvm::DIScope *DContext = Unit;
4137 unsigned Line = getLineNumber(
Loc);
4138 collectFunctionDeclProps(GD, Unit, Name, LinkageName, DContext, TParamsArray,
4140 auto *FD = cast<FunctionDecl>(GD.
getDecl());
4145 ArgTypes.push_back(Parm->getType());
4151 SPFlags |= llvm::DISubprogram::SPFlagLocalToUnit;
4153 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
4156 Flags |= getCallSiteRelatedAttrs();
4157 SPFlags |= llvm::DISubprogram::SPFlagDefinition;
4158 return DBuilder.createFunction(
4159 DContext, Name, LinkageName, Unit,
Line,
4160 getOrCreateFunctionType(GD.
getDecl(), FnType, Unit), 0, Flags, SPFlags,
4161 TParamsArray.get(), getFunctionDeclaration(FD));
4164 llvm::DISubprogram *SP = DBuilder.createTempFunctionFwdDecl(
4165 DContext, Name, LinkageName, Unit,
Line,
4166 getOrCreateFunctionType(GD.
getDecl(), FnType, Unit), 0, Flags, SPFlags,
4167 TParamsArray.get(), getFunctionDeclaration(FD));
4169 FwdDeclReplaceMap.emplace_back(std::piecewise_construct,
4170 std::make_tuple(CanonDecl),
4171 std::make_tuple(SP));
4175llvm::DISubprogram *CGDebugInfo::getFunctionForwardDeclaration(
GlobalDecl GD) {
4176 return getFunctionFwdDeclOrStub(GD,
false);
4179llvm::DISubprogram *CGDebugInfo::getFunctionStub(
GlobalDecl GD) {
4180 return getFunctionFwdDeclOrStub(GD,
true);
4183llvm::DIGlobalVariable *
4184CGDebugInfo::getGlobalVariableForwardDeclaration(
const VarDecl *VD) {
4186 StringRef Name, LinkageName;
4188 llvm::DIFile *Unit = getOrCreateFile(
Loc);
4189 llvm::DIScope *DContext = Unit;
4190 unsigned Line = getLineNumber(
Loc);
4191 llvm::MDTuple *TemplateParameters =
nullptr;
4193 collectVarDeclProps(VD, Unit,
Line,
T, Name, LinkageName, TemplateParameters,
4196 auto *GV = DBuilder.createTempGlobalVariableFwdDecl(
4197 DContext, Name, LinkageName, Unit,
Line, getOrCreateType(
T, Unit),
4199 FwdDeclReplaceMap.emplace_back(
4200 std::piecewise_construct,
4202 std::make_tuple(
static_cast<llvm::Metadata *
>(GV)));
4206llvm::DINode *CGDebugInfo::getDeclarationOrDefinition(
const Decl *
D) {
4211 if (
const auto *TD = dyn_cast<TypeDecl>(
D))
4216 if (I != DeclCache.end()) {
4218 if (
auto *GVE = dyn_cast_or_null<llvm::DIGlobalVariableExpression>(N))
4219 return GVE->getVariable();
4220 return cast<llvm::DINode>(N);
4227 if (IE != ImportedDeclCache.end()) {
4228 auto N = IE->second;
4229 if (
auto *GVE = dyn_cast_or_null<llvm::DIImportedEntity>(N))
4230 return cast<llvm::DINode>(GVE);
4231 return dyn_cast_or_null<llvm::DINode>(N);
4236 if (
const auto *FD = dyn_cast<FunctionDecl>(
D))
4237 return getFunctionForwardDeclaration(FD);
4238 else if (
const auto *VD = dyn_cast<VarDecl>(
D))
4239 return getGlobalVariableForwardDeclaration(VD);
4244llvm::DISubprogram *CGDebugInfo::getFunctionDeclaration(
const Decl *
D) {
4245 if (!
D || DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
4248 const auto *FD = dyn_cast<FunctionDecl>(
D);
4253 auto *S = getDeclContextDescriptor(
D);
4256 if (MI == SPCache.end()) {
4258 return CreateCXXMemberFunction(MD, getOrCreateFile(MD->getLocation()),
4259 cast<llvm::DICompositeType>(S));
4262 if (MI != SPCache.end()) {
4263 auto *SP = dyn_cast_or_null<llvm::DISubprogram>(MI->second);
4264 if (SP && !SP->isDefinition())
4268 for (
auto *NextFD : FD->
redecls()) {
4269 auto MI = SPCache.find(NextFD->getCanonicalDecl());
4270 if (MI != SPCache.end()) {
4271 auto *SP = dyn_cast_or_null<llvm::DISubprogram>(MI->second);
4272 if (SP && !SP->isDefinition())
4279llvm::DISubprogram *CGDebugInfo::getObjCMethodDeclaration(
4280 const Decl *
D, llvm::DISubroutineType *FnType,
unsigned LineNo,
4281 llvm::DINode::DIFlags Flags, llvm::DISubprogram::DISPFlags SPFlags) {
4282 if (!
D || DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
4285 const auto *OMD = dyn_cast<ObjCMethodDecl>(
D);
4293 SPFlags |= llvm::DISubprogram::SPFlagObjCDirect;
4303 auto It = TypeCache.find(QTy.getAsOpaquePtr());
4304 if (It == TypeCache.end())
4306 auto *InterfaceType = cast<llvm::DICompositeType>(It->second);
4307 llvm::DISubprogram *FD = DBuilder.createFunction(
4308 InterfaceType, getObjCMethodName(OMD), StringRef(),
4309 InterfaceType->getFile(), LineNo, FnType, LineNo, Flags, SPFlags);
4310 DBuilder.finalizeSubprogram(FD);
4317llvm::DISubroutineType *CGDebugInfo::getOrCreateFunctionType(
const Decl *
D,
4322 if (!
D || (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly &&
4326 return DBuilder.createSubroutineType(DBuilder.getOrCreateTypeArray({}));
4328 if (
const auto *Method = dyn_cast<CXXMethodDecl>(
D))
4329 return getOrCreateMethodType(Method, F);
4334 if (
const auto *OMethod = dyn_cast<ObjCMethodDecl>(
D)) {
4339 QualType ResultTy = OMethod->getReturnType();
4344 QualType(OMethod->getClassInterface()->getTypeForDecl(), 0));
4346 Elts.push_back(getOrCreateType(ResultTy, F));
4349 if (
auto *SelfDecl = OMethod->getSelfDecl())
4350 SelfDeclTy = SelfDecl->getType();
4351 else if (
auto *FPT = dyn_cast<FunctionProtoType>(FnType))
4354 if (!SelfDeclTy.
isNull())
4356 CreateSelfType(SelfDeclTy, getOrCreateType(SelfDeclTy, F)));
4358 Elts.push_back(DBuilder.createArtificialType(
4361 for (
const auto *PI : OMethod->parameters())
4362 Elts.push_back(getOrCreateType(PI->getType(), F));
4364 if (OMethod->isVariadic())
4365 Elts.push_back(DBuilder.createUnspecifiedParameter());
4367 llvm::DITypeRefArray EltTypeArray = DBuilder.getOrCreateTypeArray(Elts);
4368 return DBuilder.createSubroutineType(EltTypeArray, llvm::DINode::FlagZero,
4374 if (
const auto *FD = dyn_cast<FunctionDecl>(
D))
4375 if (FD->isVariadic()) {
4377 EltTys.push_back(getOrCreateType(FD->getReturnType(), F));
4378 if (
const auto *FPT = dyn_cast<FunctionProtoType>(FnType))
4380 EltTys.push_back(getOrCreateType(ParamType, F));
4381 EltTys.push_back(DBuilder.createUnspecifiedParameter());
4382 llvm::DITypeRefArray EltTypeArray = DBuilder.getOrCreateTypeArray(EltTys);
4383 return DBuilder.createSubroutineType(EltTypeArray, llvm::DINode::FlagZero,
4387 return cast<llvm::DISubroutineType>(getOrCreateType(FnType, F));
4396 CC = SrcFnTy->getCallConv();
4398 for (
const VarDecl *VD : Args)
4399 ArgTypes.push_back(VD->
getType());
4406 llvm::Function *Fn,
bool CurFuncIsThunk) {
4408 StringRef LinkageName;
4410 FnBeginRegionCount.push_back(LexicalBlockStack.size());
4413 bool HasDecl = (
D !=
nullptr);
4415 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
4416 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
4417 llvm::DIFile *Unit = getOrCreateFile(
Loc);
4418 llvm::DIScope *FDContext = Unit;
4419 llvm::DINodeArray TParamsArray;
4422 LinkageName = Fn->getName();
4423 }
else if (
const auto *FD = dyn_cast<FunctionDecl>(
D)) {
4425 auto FI = SPCache.find(FD->getCanonicalDecl());
4426 if (FI != SPCache.end()) {
4427 auto *SP = dyn_cast_or_null<llvm::DISubprogram>(FI->second);
4428 if (SP && SP->isDefinition()) {
4429 LexicalBlockStack.emplace_back(SP);
4430 RegionMap[
D].reset(SP);
4434 collectFunctionDeclProps(GD, Unit, Name, LinkageName, FDContext,
4435 TParamsArray, Flags);
4436 }
else if (
const auto *OMD = dyn_cast<ObjCMethodDecl>(
D)) {
4437 Name = getObjCMethodName(OMD);
4438 Flags |= llvm::DINode::FlagPrototyped;
4439 }
else if (isa<VarDecl>(
D) &&
4445 Name = Fn->getName();
4447 if (isa<BlockDecl>(
D))
4450 Flags |= llvm::DINode::FlagPrototyped;
4452 if (Name.starts_with(
"\01"))
4453 Name = Name.substr(1);
4455 assert((!
D || !isa<VarDecl>(
D) ||
4457 "Unexpected DynamicInitKind !");
4460 isa<VarDecl>(
D) || isa<CapturedDecl>(
D)) {
4461 Flags |= llvm::DINode::FlagArtificial;
4467 Flags |= llvm::DINode::FlagThunk;
4469 if (Fn->hasLocalLinkage())
4470 SPFlags |= llvm::DISubprogram::SPFlagLocalToUnit;
4472 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
4474 llvm::DINode::DIFlags FlagsForDef = Flags | getCallSiteRelatedAttrs();
4475 llvm::DISubprogram::DISPFlags SPFlagsForDef =
4476 SPFlags | llvm::DISubprogram::SPFlagDefinition;
4478 const unsigned LineNo = getLineNumber(
Loc.
isValid() ?
Loc : CurLoc);
4479 unsigned ScopeLine = getLineNumber(ScopeLoc);
4480 llvm::DISubroutineType *DIFnType = getOrCreateFunctionType(
D, FnType, Unit);
4481 llvm::DISubprogram *
Decl =
nullptr;
4482 llvm::DINodeArray Annotations =
nullptr;
4484 Decl = isa<ObjCMethodDecl>(
D)
4485 ? getObjCMethodDeclaration(
D, DIFnType, LineNo, Flags, SPFlags)
4486 : getFunctionDeclaration(
D);
4487 Annotations = CollectBTFDeclTagAnnotations(
D);
4495 llvm::DISubprogram *SP = DBuilder.createFunction(
4496 FDContext, Name, LinkageName, Unit, LineNo, DIFnType, ScopeLine,
4497 FlagsForDef, SPFlagsForDef, TParamsArray.get(),
Decl,
nullptr,
4499 Fn->setSubprogram(SP);
4503 if (HasDecl && isa<FunctionDecl>(
D))
4507 LexicalBlockStack.emplace_back(SP);
4510 RegionMap[
D].reset(SP);
4514 QualType FnType, llvm::Function *Fn) {
4516 StringRef LinkageName;
4522 llvm::TimeTraceScope TimeScope(
"DebugFunction", [&]() {
4523 return GetName(
D,
true);
4526 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
4527 llvm::DIFile *Unit = getOrCreateFile(
Loc);
4528 bool IsDeclForCallSite = Fn ?
true :
false;
4529 llvm::DIScope *FDContext =
4530 IsDeclForCallSite ? Unit : getDeclContextDescriptor(
D);
4531 llvm::DINodeArray TParamsArray;
4532 if (isa<FunctionDecl>(
D)) {
4534 collectFunctionDeclProps(GD, Unit, Name, LinkageName, FDContext,
4535 TParamsArray, Flags);
4536 }
else if (
const auto *OMD = dyn_cast<ObjCMethodDecl>(
D)) {
4537 Name = getObjCMethodName(OMD);
4538 Flags |= llvm::DINode::FlagPrototyped;
4540 llvm_unreachable(
"not a function or ObjC method");
4542 if (!Name.empty() && Name[0] ==
'\01')
4543 Name = Name.substr(1);
4546 Flags |= llvm::DINode::FlagArtificial;
4551 unsigned LineNo = getLineNumber(
Loc);
4552 unsigned ScopeLine = 0;
4553 llvm::DISubprogram::DISPFlags SPFlags = llvm::DISubprogram::SPFlagZero;
4555 SPFlags |= llvm::DISubprogram::SPFlagOptimized;
4557 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(
D);
4558 llvm::DISubroutineType *STy = getOrCreateFunctionType(
D, FnType, Unit);
4559 llvm::DISubprogram *SP = DBuilder.createFunction(
4560 FDContext, Name, LinkageName, Unit, LineNo, STy, ScopeLine, Flags,
4561 SPFlags, TParamsArray.get(),
nullptr,
nullptr, Annotations);
4567 if (
auto *FD = dyn_cast<FunctionDecl>(
D)) {
4568 llvm::DITypeRefArray ParamTypes = STy->getTypeArray();
4571 llvm::DINodeArray ParamAnnotations = CollectBTFDeclTagAnnotations(PD);
4572 DBuilder.createParameterVariable(
4573 SP, PD->getName(), ArgNo, Unit, LineNo, ParamTypes[ArgNo],
true,
4574 llvm::DINode::FlagZero, ParamAnnotations);
4580 if (IsDeclForCallSite)
4581 Fn->setSubprogram(SP);
4583 DBuilder.finalizeSubprogram(SP);
4591 auto *
Func = CallOrInvoke->getCalledFunction();
4594 if (
Func->getSubprogram())
4599 if (CalleeDecl->
hasAttr<NoDebugAttr>() ||
4600 getCallSiteRelatedAttrs() == llvm::DINode::FlagZero)
4611 const auto *FD = cast<FunctionDecl>(GD.
getDecl());
4613 auto FI = SPCache.find(FD->getCanonicalDecl());
4614 llvm::DISubprogram *SP =
nullptr;
4615 if (FI != SPCache.end())
4616 SP = dyn_cast_or_null<llvm::DISubprogram>(FI->second);
4617 if (!SP || !SP->isDefinition())
4618 SP = getFunctionStub(GD);
4619 FnBeginRegionCount.push_back(LexicalBlockStack.size());
4620 LexicalBlockStack.emplace_back(SP);
4626 assert(CurInlinedAt &&
"unbalanced inline scope stack");
4635 if (CurLoc.isInvalid() || CurLoc.isMacroID() || LexicalBlockStack.empty())
4638 llvm::MDNode *
Scope = LexicalBlockStack.back();
4639 Builder.SetCurrentDebugLocation(
4640 llvm::DILocation::get(CGM.
getLLVMContext(), getLineNumber(CurLoc),
4641 getColumnNumber(CurLoc),
Scope, CurInlinedAt));
4645 llvm::MDNode *Back =
nullptr;
4646 if (!LexicalBlockStack.empty())
4647 Back = LexicalBlockStack.back().get();
4648 LexicalBlockStack.emplace_back(DBuilder.createLexicalBlock(
4649 cast<llvm::DIScope>(Back), getOrCreateFile(CurLoc), getLineNumber(CurLoc),
4650 getColumnNumber(CurLoc)));
4653void CGDebugInfo::AppendAddressSpaceXDeref(
4655 std::optional<unsigned> DWARFAddressSpace =
4657 if (!DWARFAddressSpace)
4660 Expr.push_back(llvm::dwarf::DW_OP_constu);
4661 Expr.push_back(*DWARFAddressSpace);
4662 Expr.push_back(llvm::dwarf::DW_OP_swap);
4663 Expr.push_back(llvm::dwarf::DW_OP_xderef);
4672 Builder.SetCurrentDebugLocation(llvm::DILocation::get(
4674 LexicalBlockStack.back(), CurInlinedAt));
4676 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
4680 CreateLexicalBlock(
Loc);
4685 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
4690 if (DebugKind <= llvm::codegenoptions::DebugLineTablesOnly)
4693 LexicalBlockStack.pop_back();
4697 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
4698 unsigned RCount = FnBeginRegionCount.back();
4699 assert(RCount <= LexicalBlockStack.size() &&
"Region stack mismatch");
4702 while (LexicalBlockStack.size() != RCount) {
4705 LexicalBlockStack.pop_back();
4707 FnBeginRegionCount.pop_back();
4709 if (Fn && Fn->getSubprogram())
4710 DBuilder.finalizeSubprogram(Fn->getSubprogram());
4713CGDebugInfo::BlockByRefType
4714CGDebugInfo::EmitTypeForVarWithBlocksAttr(
const VarDecl *VD,
4715 uint64_t *XOffset) {
4718 uint64_t FieldSize, FieldOffset;
4719 uint32_t FieldAlign;
4721 llvm::DIFile *Unit = getOrCreateFile(VD->
getLocation());
4726 EltTys.push_back(CreateMemberType(Unit, FType,
"__isa", &FieldOffset));
4727 EltTys.push_back(CreateMemberType(Unit, FType,
"__forwarding", &FieldOffset));
4729 EltTys.push_back(CreateMemberType(Unit, FType,
"__flags", &FieldOffset));
4730 EltTys.push_back(CreateMemberType(Unit, FType,
"__size", &FieldOffset));
4733 if (HasCopyAndDispose) {
4736 CreateMemberType(Unit, FType,
"__copy_helper", &FieldOffset));
4738 CreateMemberType(Unit, FType,
"__destroy_helper", &FieldOffset));
4740 bool HasByrefExtendedLayout;
4743 HasByrefExtendedLayout) &&
4744 HasByrefExtendedLayout) {
4747 CreateMemberType(Unit, FType,
"__byref_variable_layout", &FieldOffset));
4756 CharUnits NumPaddingBytes = AlignedOffsetInBytes - FieldOffsetInBytes;
4759 llvm::APInt pad(32, NumPaddingBytes.
getQuantity());
4762 EltTys.push_back(CreateMemberType(Unit, FType,
"", &FieldOffset));
4767 llvm::DIType *WrappedTy = getOrCreateType(FType, Unit);
4771 *XOffset = FieldOffset;
4772 llvm::DIType *FieldTy = DBuilder.createMemberType(
4773 Unit, VD->
getName(), Unit, 0, FieldSize, FieldAlign, FieldOffset,
4774 llvm::DINode::FlagZero, WrappedTy);
4775 EltTys.push_back(FieldTy);
4776 FieldOffset += FieldSize;
4778 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
4779 return {DBuilder.createStructType(Unit,
"", Unit, 0, FieldOffset, 0,
4780 llvm::DINode::FlagZero,
nullptr, Elements),
4784llvm::DILocalVariable *CGDebugInfo::EmitDeclare(
const VarDecl *VD,
4785 llvm::Value *Storage,
4786 std::optional<unsigned> ArgNo,
4788 const bool UsePointerValue) {
4790 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
4791 if (VD->
hasAttr<NoDebugAttr>())
4796 llvm::DIFile *Unit =
nullptr;
4797 if (!VarIsArtificial)
4801 if (VD->
hasAttr<BlocksAttr>())
4802 Ty = EmitTypeForVarWithBlocksAttr(VD, &XOffset).WrappedType;
4804 Ty = getOrCreateType(VD->
getType(), Unit);
4814 if (!VarIsArtificial) {
4819 llvm::DINode::DIFlags Flags = llvm::DINode::FlagZero;
4820 if (VarIsArtificial)
4821 Flags |= llvm::DINode::FlagArtificial;
4826 AppendAddressSpaceXDeref(AddressSpace,
Expr);
4830 if (
const auto *IPD = dyn_cast<ImplicitParamDecl>(VD)) {
4833 Flags |= llvm::DINode::FlagObjectPointer;
4840 auto *
Scope = cast<llvm::DIScope>(LexicalBlockStack.back());
4841 StringRef Name = VD->
getName();
4842 if (!Name.empty()) {
4848 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
4853 Expr.push_back(llvm::dwarf::DW_OP_deref);
4854 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
4859 }
else if (
const auto *RT = dyn_cast<RecordType>(VD->
getType())) {
4871 for (
const auto *Field : RD->
fields()) {
4872 llvm::DIType *FieldTy = getOrCreateType(
Field->getType(), Unit);
4873 StringRef FieldName =
Field->getName();
4876 if (FieldName.empty() && !isa<RecordType>(
Field->getType()))
4881 auto *
D = DBuilder.createAutoVariable(
4883 Flags | llvm::DINode::FlagArtificial, FieldAlign);
4886 DBuilder.insertDeclare(Storage,
D, DBuilder.createExpression(
Expr),
4890 Builder.GetInsertBlock());
4898 if (UsePointerValue) {
4899 assert(!llvm::is_contained(
Expr, llvm::dwarf::DW_OP_deref) &&
4900 "Debug info already contains DW_OP_deref.");
4901 Expr.push_back(llvm::dwarf::DW_OP_deref);
4905 llvm::DILocalVariable *
D =
nullptr;
4907 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(VD);
4908 D = DBuilder.createParameterVariable(
Scope, Name, *ArgNo, Unit,
Line, Ty,
4919 auto RemapCoroArgToLocalVar = [&]() -> llvm::DILocalVariable * {
4922 if (!isa<llvm::DISubprogram>(
Scope) || !
Scope->isDistinct())
4925 auto Iter = llvm::find_if(CoroutineParameterMappings, [&](
auto &Pair) {
4926 Stmt *StmtPtr =
const_cast<Stmt *
>(Pair.second);
4927 if (
DeclStmt *DeclStmtPtr = dyn_cast<DeclStmt>(StmtPtr)) {
4930 if (VD == dyn_cast_or_null<VarDecl>(
Decl))
4936 if (
Iter != CoroutineParameterMappings.end()) {
4938 auto Iter2 = llvm::find_if(ParamDbgMappings, [&](
auto &DbgPair) {
4939 return DbgPair.first == PD && DbgPair.second->getScope() ==
Scope;
4941 if (Iter2 != ParamDbgMappings.end())
4942 return const_cast<llvm::DILocalVariable *
>(Iter2->second);
4948 D = RemapCoroArgToLocalVar();
4951 D = DBuilder.createAutoVariable(
Scope, Name, Unit,
Line, Ty,
4955 DBuilder.insertDeclare(Storage,
D, DBuilder.createExpression(
Expr),
4958 Builder.GetInsertBlock());
4963llvm::DILocalVariable *CGDebugInfo::EmitDeclare(
const BindingDecl *BD,
4964 llvm::Value *Storage,
4965 std::optional<unsigned> ArgNo,
4967 const bool UsePointerValue) {
4969 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
4970 if (BD->
hasAttr<NoDebugAttr>())
4977 llvm::DIFile *Unit = getOrCreateFile(BD->
getLocation());
4978 llvm::DIType *Ty = getOrCreateType(BD->
getType(), Unit);
4989 AppendAddressSpaceXDeref(AddressSpace,
Expr);
4994 if (UsePointerValue) {
4995 assert(!llvm::is_contained(
Expr, llvm::dwarf::DW_OP_deref) &&
4996 "Debug info already contains DW_OP_deref.");
4997 Expr.push_back(llvm::dwarf::DW_OP_deref);
5002 StringRef Name = BD->
getName();
5003 auto *
Scope = cast<llvm::DIScope>(LexicalBlockStack.back());
5005 llvm::DILocalVariable *
D = DBuilder.createAutoVariable(
5007 llvm::DINode::FlagZero, Align);
5010 if (
const FieldDecl *FD = dyn_cast<FieldDecl>(ME->getMemberDecl())) {
5011 const unsigned fieldIndex = FD->getFieldIndex();
5017 if (FD->isBitField()) {
5024 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5030 ? llvm::dwarf::DW_OP_LLVM_extract_bits_sext
5031 : llvm::dwarf::DW_OP_LLVM_extract_bits_zext);
5036 Expr.push_back(std::min((uint64_t)Info.
Size, TypeSize));
5037 }
else if (fieldOffset != 0) {
5039 "Unexpected non-bitfield with non-byte-aligned offset");
5040 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5046 dyn_cast<ArraySubscriptExpr>(BD->
getBinding())) {
5047 if (
const IntegerLiteral *IL = dyn_cast<IntegerLiteral>(ASE->getIdx())) {
5048 const uint64_t value = IL->getValue().getZExtValue();
5052 Expr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5061 DBuilder.insertDeclare(Storage,
D, DBuilder.createExpression(
Expr),
5064 Builder.GetInsertBlock());
5069llvm::DILocalVariable *
5072 const bool UsePointerValue) {
5075 if (
auto *DD = dyn_cast<DecompositionDecl>(VD)) {
5076 for (
auto *B : DD->bindings()) {
5077 EmitDeclare(B, Storage, std::nullopt, Builder,
5085 return EmitDeclare(VD, Storage, std::nullopt, Builder, UsePointerValue);
5090 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5095 auto *
Scope = cast<llvm::DIScope>(LexicalBlockStack.back());
5096 llvm::DIFile *Unit = getOrCreateFile(
D->
getLocation());
5102 StringRef Name =
D->getName();
5109 DBuilder.insertLabel(L,
5111 Scope, CurInlinedAt),
5112 Builder.GetInsertBlock());
5115llvm::DIType *CGDebugInfo::CreateSelfType(
const QualType &QualTy,
5117 llvm::DIType *CachedTy = getTypeOrNull(QualTy);
5120 return DBuilder.createObjectPointerType(Ty);
5125 const CGBlockInfo &blockInfo, llvm::Instruction *InsertPoint) {
5127 assert(!LexicalBlockStack.empty() &&
"Region stack mismatch, stack empty!");
5129 if (Builder.GetInsertBlock() ==
nullptr)
5131 if (VD->
hasAttr<NoDebugAttr>())
5134 bool isByRef = VD->
hasAttr<BlocksAttr>();
5136 uint64_t XOffset = 0;
5137 llvm::DIFile *Unit = getOrCreateFile(VD->
getLocation());
5140 Ty = EmitTypeForVarWithBlocksAttr(VD, &XOffset).WrappedType;
5142 Ty = getOrCreateType(VD->
getType(), Unit);
5146 if (
const auto *IPD = dyn_cast<ImplicitParamDecl>(VD))
5148 Ty = CreateSelfType(VD->
getType(), Ty);
5151 const unsigned Line =
5162 addr.push_back(llvm::dwarf::DW_OP_deref);
5163 addr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5166 addr.push_back(llvm::dwarf::DW_OP_deref);
5167 addr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5172 addr.push_back(llvm::dwarf::DW_OP_deref);
5173 addr.push_back(llvm::dwarf::DW_OP_plus_uconst);
5181 auto *
D = DBuilder.createAutoVariable(
5182 cast<llvm::DILocalScope>(LexicalBlockStack.back()), VD->
getName(), Unit,
5183 Line, Ty,
false, llvm::DINode::FlagZero, Align);
5187 LexicalBlockStack.back(), CurInlinedAt);
5188 auto *
Expr = DBuilder.createExpression(addr);
5190 DBuilder.insertDeclare(Storage,
D,
Expr, DL, InsertPoint);
5192 DBuilder.insertDeclare(Storage,
D,
Expr, DL, Builder.GetInsertBlock());
5195llvm::DILocalVariable *
5198 bool UsePointerValue) {
5200 return EmitDeclare(VD, AI, ArgNo, Builder, UsePointerValue);
5204struct BlockLayoutChunk {
5205 uint64_t OffsetInBits;
5208bool operator<(
const BlockLayoutChunk &l,
const BlockLayoutChunk &r) {
5209 return l.OffsetInBits < r.OffsetInBits;
5213void CGDebugInfo::collectDefaultFieldsForBlockLiteralDeclare(
5215 const llvm::StructLayout &BlockLayout, llvm::DIFile *Unit,
5222 BlockLayout.getElementOffsetInBits(0),
5225 BlockLayout.getElementOffsetInBits(1),
5229 BlockLayout.getElementOffsetInBits(0),
5232 BlockLayout.getElementOffsetInBits(1),
5236 BlockLayout.getElementOffsetInBits(2), Unit, Unit));
5237 auto *FnTy =
Block.getBlockExpr()->getFunctionType();
5239 Fields.push_back(createFieldType(
"__FuncPtr", FnPtrType,
Loc,
AS_public,
5240 BlockLayout.getElementOffsetInBits(3),
5242 Fields.push_back(createFieldType(
5247 Loc,
AS_public, BlockLayout.getElementOffsetInBits(4), Unit, Unit));
5254 llvm::AllocaInst *Alloca,
5262 llvm::DIFile *tunit = getOrCreateFile(loc);
5263 unsigned line = getLineNumber(loc);
5264 unsigned column = getColumnNumber(loc);
5269 const llvm::StructLayout *blockLayout =
5273 collectDefaultFieldsForBlockLiteralDeclare(block,
C, loc, *blockLayout, tunit,
5282 BlockLayoutChunk chunk;
5283 chunk.OffsetInBits =
5284 blockLayout->getElementOffsetInBits(block.
CXXThisIndex);
5285 chunk.Capture =
nullptr;
5286 chunks.push_back(chunk);
5290 for (
const auto &capture :
blockDecl->captures()) {
5291 const VarDecl *variable = capture.getVariable();
5298 BlockLayoutChunk chunk;
5299 chunk.OffsetInBits =
5300 blockLayout->getElementOffsetInBits(captureInfo.
getIndex());
5301 chunk.Capture = &capture;
5302 chunks.push_back(chunk);
5306 llvm::array_pod_sort(chunks.begin(), chunks.end());
5308 for (
const BlockLayoutChunk &Chunk : chunks) {
5309 uint64_t offsetInBits = Chunk.OffsetInBits;
5316 cast_or_null<CXXMethodDecl>(
blockDecl->getNonClosureContext()))
5318 else if (
auto *RDecl = dyn_cast<CXXRecordDecl>(
blockDecl->getParent()))
5321 llvm_unreachable(
"unexpected block declcontext");
5323 fields.push_back(createFieldType(
"this",
type, loc,
AS_public,
5324 offsetInBits, tunit, tunit));
5329 StringRef name = variable->
getName();
5331 llvm::DIType *fieldType;
5333 TypeInfo PtrInfo =
C.getTypeInfo(
C.VoidPtrTy);
5338 EmitTypeForVarWithBlocksAttr(variable, &xoffset).BlockByRefWrapper;
5339 fieldType = DBuilder.createPointerType(fieldType, PtrInfo.
Width);
5340 fieldType = DBuilder.createMemberType(tunit, name, tunit, line,
5341 PtrInfo.
Width, Align, offsetInBits,
5342 llvm::DINode::FlagZero, fieldType);
5346 offsetInBits, Align, tunit, tunit);
5348 fields.push_back(fieldType);
5352 llvm::raw_svector_ostream(typeName)
5355 llvm::DINodeArray fieldsArray = DBuilder.getOrCreateArray(fields);
5357 llvm::DIType *
type =
5358 DBuilder.createStructType(tunit, typeName.str(), tunit, line,
5360 llvm::DINode::FlagZero,
nullptr, fieldsArray);
5364 llvm::DINode::DIFlags flags = llvm::DINode::FlagArtificial;
5365 auto *scope = cast<llvm::DILocalScope>(LexicalBlockStack.back());
5368 auto *debugVar = DBuilder.createParameterVariable(
5369 scope, Name, ArgNo, tunit, line,
type, CGM.
getLangOpts().Optimize, flags);
5372 DBuilder.insertDeclare(Alloca, debugVar, DBuilder.createExpression(),
5374 column, scope, CurInlinedAt),
5375 Builder.GetInsertBlock());
5378llvm::DIDerivedType *
5379CGDebugInfo::getOrCreateStaticDataMemberDeclarationOrNull(
const VarDecl *
D) {
5380 if (!
D || !
D->isStaticDataMember())
5384 if (MI != StaticDataMemberCache.end()) {
5385 assert(MI->second &&
"Static data member declaration should still exist");
5392 auto *Ctxt = cast<llvm::DICompositeType>(getDeclContextDescriptor(
D));
5393 return CreateRecordStaticField(
D, Ctxt, cast<RecordDecl>(DC));
5396llvm::DIGlobalVariableExpression *CGDebugInfo::CollectAnonRecordDecls(
5397 const RecordDecl *RD, llvm::DIFile *Unit,
unsigned LineNo,
5398 StringRef LinkageName, llvm::GlobalVariable *Var, llvm::DIScope *DContext) {
5399 llvm::DIGlobalVariableExpression *GVE =
nullptr;
5401 for (
const auto *Field : RD->
fields()) {
5402 llvm::DIType *FieldTy = getOrCreateType(Field->getType(), Unit);
5403 StringRef FieldName = Field->getName();
5406 if (FieldName.empty()) {
5407 if (
const auto *RT = dyn_cast<RecordType>(Field->getType()))
5408 GVE = CollectAnonRecordDecls(RT->getDecl(), Unit, LineNo, LinkageName,
5413 GVE = DBuilder.createGlobalVariableExpression(
5414 DContext, FieldName, LinkageName, Unit, LineNo, FieldTy,
5415 Var->hasLocalLinkage());
5416 Var->addDebugInfo(GVE);
5428 const auto *RD = dyn_cast<CXXRecordDecl>(RT->
getDecl());
5433 auto *TSpecial = dyn_cast<ClassTemplateSpecializationDecl>(RD);
5441 case TemplateArgument::Pack:
5442 return ReferencesAnonymousEntity(TA.getPackAsArray());
5443 case TemplateArgument::Type: {
5444 struct ReferencesAnonymous
5445 : public RecursiveASTVisitor<ReferencesAnonymous> {
5446 bool RefAnon = false;
5447 bool VisitRecordType(RecordType *RT) {
5448 if (ReferencesAnonymousEntity(RT)) {
5455 ReferencesAnonymous RT;
5456 RT.TraverseType(TA.getAsType());
5469 bool Reconstitutable =
true;
5471 Reconstitutable =
false;
5475 Reconstitutable =
false;
5478 bool VisitType(
Type *
T) {
5482 Reconstitutable =
false;
5487 bool TraverseEnumType(
EnumType *ET) {
5490 if (
const auto *ED = dyn_cast<EnumDecl>(ET->
getDecl())) {
5492 Reconstitutable =
false;
5496 Reconstitutable =
false;
5506 return Reconstitutable;
5510 Reconstitutable =
false;
5520 ReconstitutableType
T;
5522 return T.Reconstitutable;
5525bool CGDebugInfo::HasReconstitutableArgs(
5529 case TemplateArgument::Template:
5536 case TemplateArgument::Declaration:
5545 case TemplateArgument::NullPtr:
5549 case TemplateArgument::Pack:
5552 return HasReconstitutableArgs(TA.getPackAsArray());
5553 case TemplateArgument::Integral:
5558 return TA.getAsIntegral().getBitWidth() <= 64 &&
5559 IsReconstitutableType(TA.getIntegralType());
5560 case TemplateArgument::StructuralValue:
5562 case TemplateArgument::Type:
5563 return IsReconstitutableType(TA.getAsType());
5564 case TemplateArgument::Expression:
5565 return IsReconstitutableType(TA.getAsExpr()->getType());
5567 llvm_unreachable(
"Other, unresolved, template arguments should "
5568 "not be seen here");
5573std::string CGDebugInfo::GetName(
const Decl *
D,
bool Qualified)
const {
5575 llvm::raw_string_ostream OS(Name);
5576 const NamedDecl *ND = dyn_cast<NamedDecl>(
D);
5579 llvm::codegenoptions::DebugTemplateNamesKind TemplateNamesKind =
5583 TemplateNamesKind = llvm::codegenoptions::DebugTemplateNamesKind::Full;
5585 std::optional<TemplateArgs> Args;
5587 bool IsOperatorOverload =
false;
5588 if (
auto *RD = dyn_cast<CXXRecordDecl>(ND)) {
5589 Args = GetTemplateArgs(RD);
5590 }
else if (
auto *FD = dyn_cast<FunctionDecl>(ND)) {
5591 Args = GetTemplateArgs(FD);
5593 IsOperatorOverload |=
5596 }
else if (
auto *VD = dyn_cast<VarDecl>(ND)) {
5597 Args = GetTemplateArgs(VD);
5621 bool Reconstitutable =
5622 Args && HasReconstitutableArgs(Args->Args) && !IsOperatorOverload;
5626 if (TemplateNamesKind == llvm::codegenoptions::DebugTemplateNamesKind::Full ||
5630 bool Mangled = TemplateNamesKind ==
5631 llvm::codegenoptions::DebugTemplateNamesKind::Mangled;
5637 std::string EncodedOriginalName;
5638 llvm::raw_string_ostream EncodedOriginalNameOS(EncodedOriginalName);
5646 std::string CanonicalOriginalName;
5647 llvm::raw_string_ostream OriginalOS(CanonicalOriginalName);
5649 assert(EncodedOriginalName == CanonicalOriginalName);
5662 llvm::TimeTraceScope TimeScope(
"DebugGlobalVariable", [&]() {
5663 return GetName(
D,
true);
5669 if (Cached != DeclCache.end())
5670 return Var->addDebugInfo(
5671 cast<llvm::DIGlobalVariableExpression>(Cached->second));
5674 llvm::DIFile *Unit =
nullptr;
5675 llvm::DIScope *DContext =
nullptr;
5677 StringRef DeclName, LinkageName;
5679 llvm::MDTuple *TemplateParameters =
nullptr;
5680 collectVarDeclProps(
D, Unit, LineNo,
T, DeclName, LinkageName,
5681 TemplateParameters, DContext);
5685 llvm::DIGlobalVariableExpression *GVE =
nullptr;
5693 "unnamed non-anonymous struct or union?");
5694 GVE = CollectAnonRecordDecls(RD, Unit, LineNo, LinkageName, Var, DContext);
5704 else if (
D->
hasAttr<CUDAConstantAttr>())
5708 AppendAddressSpaceXDeref(AddressSpace,
Expr);
5710 llvm::DINodeArray Annotations = CollectBTFDeclTagAnnotations(
D);
5711 GVE = DBuilder.createGlobalVariableExpression(
5712 DContext, DeclName, LinkageName, Unit, LineNo, getOrCreateType(
T, Unit),
5713 Var->hasLocalLinkage(),
true,
5714 Expr.empty() ?
nullptr : DBuilder.createExpression(
Expr),
5715 getOrCreateStaticDataMemberDeclarationOrNull(
D), TemplateParameters,
5716 Align, Annotations);
5717 Var->addDebugInfo(GVE);
5724 if (VD->
hasAttr<NoDebugAttr>())
5726 llvm::TimeTraceScope TimeScope(
"DebugConstGlobalVariable", [&]() {
5727 return GetName(VD,
true);
5732 llvm::DIFile *Unit = getOrCreateFile(VD->
getLocation());
5733 StringRef Name = VD->
getName();
5734 llvm::DIType *Ty = getOrCreateType(VD->
getType(), Unit);
5736 if (
const auto *ECD = dyn_cast<EnumConstantDecl>(VD)) {
5737 const auto *ED = cast<EnumDecl>(ECD->getDeclContext());
5738 assert(isa<EnumType>(ED->
getTypeForDecl()) &&
"Enum without EnumType?");
5751 llvm::DIType *EDTy =
5753 assert (EDTy->getTag() == llvm::dwarf::DW_TAG_enumeration_type);
5764 auto *VarD = dyn_cast<VarDecl>(VD);
5765 if (VarD && VarD->isStaticDataMember()) {
5766 auto *RD = cast<RecordDecl>(VarD->getDeclContext());
5767 getDeclContextDescriptor(VarD);
5772 RetainedTypes.push_back(
5777 llvm::DIScope *DContext = getDeclContextDescriptor(VD);
5779 auto &GV = DeclCache[VD];
5783 llvm::DIExpression *InitExpr = createConstantValueExpression(VD,
Init);
5784 llvm::MDTuple *TemplateParameters =
nullptr;
5786 if (isa<VarTemplateSpecializationDecl>(VD))
5788 llvm::DINodeArray parameterNodes = CollectVarTemplateParams(VarD, &*Unit);
5789 TemplateParameters = parameterNodes.get();
5792 GV.reset(DBuilder.createGlobalVariableExpression(
5793 DContext, Name, StringRef(), Unit, getLineNumber(VD->
getLocation()), Ty,
5794 true,
true, InitExpr, getOrCreateStaticDataMemberDeclarationOrNull(VarD),
5795 TemplateParameters, Align));
5805 llvm::DIFile *Unit = getOrCreateFile(
D->
getLocation());
5806 StringRef Name =
D->getName();
5807 llvm::DIType *Ty = getOrCreateType(
D->getType(), Unit);
5809 llvm::DIScope *DContext = getDeclContextDescriptor(
D);
5810 llvm::DIGlobalVariableExpression *GVE =
5811 DBuilder.createGlobalVariableExpression(
5812 DContext, Name, StringRef(), Unit, getLineNumber(
D->
getLocation()),
5813 Ty,
false,
false,
nullptr,
nullptr,
nullptr, Align);
5814 Var->addDebugInfo(GVE);
5822 llvm::codegenoptions::DebugLineTablesOnly)
5825 llvm::DILocation *DIL =
Value->getDebugLoc().get();
5829 llvm::DIFile *Unit = DIL->getFile();
5830 llvm::DIType *
Type = getOrCreateType(Ty, Unit);
5835 if (llvm::LoadInst *Load = dyn_cast<llvm::LoadInst>(
Value)) {
5836 llvm::Value *Var = Load->getPointerOperand();
5841 auto DeclareTypeMatches = [&](
auto *DbgDeclare) {
5842 return DbgDeclare->getVariable()->getType() ==
Type;
5844 if (any_of(llvm::findDbgDeclares(Var), DeclareTypeMatches) ||
5845 any_of(llvm::findDVRDeclares(Var), DeclareTypeMatches))
5849 llvm::DILocalVariable *
D =
5850 DBuilder.createAutoVariable(LexicalBlockStack.back(),
"",
nullptr, 0,
5851 Type,
false, llvm::DINode::FlagArtificial);
5853 if (
auto InsertPoint =
Value->getInsertionPointAfterDef()) {
5854 DBuilder.insertDbgValueIntrinsic(
Value,
D, DBuilder.createExpression(), DIL,
5867 const auto *
D = cast<ValueDecl>(GD.
getDecl());
5886 if (!(DI = getDeclarationOrDefinition(
5887 AliaseeDecl.getCanonicalDecl().getDecl())))
5890 llvm::DIScope *DContext = getDeclContextDescriptor(
D);
5893 llvm::DIImportedEntity *ImportDI = DBuilder.createImportedDeclaration(
5894 DContext, DI, getOrCreateFile(
Loc), getLineNumber(
Loc),
D->getName());
5907 llvm::DIFile *
File = getOrCreateFile(
Loc);
5908 llvm::DIGlobalVariableExpression *Debug =
5909 DBuilder.createGlobalVariableExpression(
5910 nullptr, StringRef(), StringRef(), getOrCreateFile(
Loc),
5911 getLineNumber(
Loc), getOrCreateType(S->getType(),
File),
true);
5912 GV->addDebugInfo(Debug);
5915llvm::DIScope *CGDebugInfo::getCurrentContextDescriptor(
const Decl *
D) {
5916 if (!LexicalBlockStack.empty())
5917 return LexicalBlockStack.back();
5918 llvm::DIScope *Mod = getParentModuleOrNull(
D);
5919 return getContextDescriptor(
D, Mod ? Mod : TheCU);
5931 DBuilder.createImportedModule(
5933 getOrCreateNamespace(NSDecl), getOrCreateFile(
Loc), getLineNumber(
Loc));
5938 if (llvm::DINode *
Target =
5941 DBuilder.createImportedDeclaration(
5943 getOrCreateFile(
Loc), getLineNumber(
Loc));
5951 "We shouldn't be codegening an invalid UsingDecl containing no decls");
5953 for (
const auto *USD : UD.
shadows()) {
5958 if (
const auto *FD = dyn_cast<FunctionDecl>(USD->getUnderlyingDecl()))
5959 if (
const auto *AT = FD->getType()
5962 if (AT->getDeducedType().isNull())
5976 "We shouldn't be codegening an invalid UsingEnumDecl"
5977 " containing no decls");
5979 for (
const auto *USD : UD.
shadows())
5984 if (CGM.
getCodeGenOpts().getDebuggerTuning() != llvm::DebuggerKind::LLDB)
5986 if (
Module *M = ID.getImportedModule()) {
5988 auto Loc = ID.getLocation();
5989 DBuilder.createImportedDeclaration(
5990 getCurrentContextDescriptor(cast<Decl>(ID.getDeclContext())),
5991 getOrCreateModuleRef(Info, DebugTypeExtRefs), getOrCreateFile(
Loc),
5992 getLineNumber(
Loc));
5996llvm::DIImportedEntity *
6000 auto &VH = NamespaceAliasCache[&NA];
6002 return cast<llvm::DIImportedEntity>(VH);
6003 llvm::DIImportedEntity *R;
6005 if (
const auto *Underlying =
6008 R = DBuilder.createImportedDeclaration(
6013 R = DBuilder.createImportedDeclaration(
6022CGDebugInfo::getOrCreateNamespace(
const NamespaceDecl *NSDecl) {
6026 auto I = NamespaceCache.find(NSDecl);
6027 if (I != NamespaceCache.end())
6028 return cast<llvm::DINamespace>(I->second);
6030 llvm::DIScope *Context = getDeclContextDescriptor(NSDecl);
6032 llvm::DINamespace *NS =
6033 DBuilder.createNameSpace(Context, NSDecl->
getName(), NSDecl->
isInline());
6034 NamespaceCache[NSDecl].reset(NS);
6039 assert(TheCU &&
"no main compile unit");
6040 TheCU->setDWOId(Signature);
6046 for (
size_t i = 0; i != ObjCInterfaceCache.size(); ++i) {
6047 ObjCInterfaceCacheEntry
E = ObjCInterfaceCache[i];
6048 llvm::DIType *Ty =
E.Type->getDecl()->getDefinition()
6049 ? CreateTypeDefinition(
E.Type,
E.Unit)
6051 DBuilder.replaceTemporary(llvm::TempDIType(
E.Decl), Ty);
6055 for (
const auto &
P : ObjCMethodCache) {
6056 if (
P.second.empty())
6059 QualType QTy(
P.first->getTypeForDecl(), 0);
6061 assert(It != TypeCache.end());
6063 llvm::DICompositeType *InterfaceDecl =
6064 cast<llvm::DICompositeType>(It->second);
6066 auto CurElts = InterfaceDecl->getElements();
6070 for (
auto &SubprogramDirect :
P.second)
6071 if (CGM.
getCodeGenOpts().DwarfVersion >= 5 || SubprogramDirect.getInt())
6072 EltTys.push_back(SubprogramDirect.getPointer());
6074 llvm::DINodeArray Elements = DBuilder.getOrCreateArray(EltTys);
6075 DBuilder.replaceArrays(InterfaceDecl, Elements);
6078 for (
const auto &
P : ReplaceMap) {
6080 auto *Ty = cast<llvm::DIType>(
P.second);
6081 assert(Ty->isForwardDecl());
6083 auto It = TypeCache.find(
P.first);
6084 assert(It != TypeCache.end());
6087 DBuilder.replaceTemporary(llvm::TempDIType(Ty),
6088 cast<llvm::DIType>(It->second));
6091 for (
const auto &
P : FwdDeclReplaceMap) {
6093 llvm::TempMDNode FwdDecl(cast<llvm::MDNode>(
P.second));
6094 llvm::Metadata *Repl;
6096 auto It = DeclCache.find(
P.first);
6100 if (It == DeclCache.end())
6105 if (
auto *GVE = dyn_cast_or_null<llvm::DIGlobalVariableExpression>(Repl))
6106 Repl = GVE->getVariable();
6107 DBuilder.replaceTemporary(std::move(FwdDecl), cast<llvm::MDNode>(Repl));
6112 for (
auto &RT : RetainedTypes)
6113 if (
auto MD = TypeCache[RT])
6114 DBuilder.retainType(cast<llvm::DIType>(MD));
6116 DBuilder.finalize();
6122 if (
auto *DieTy = getOrCreateType(Ty, TheCU->getFile()))
6123 DBuilder.retainType(DieTy);
6128 if (
auto *DieTy = getOrCreateType(Ty, TheCU->getFile()))
6129 DBuilder.retainType(DieTy);
6133 if (LexicalBlockStack.empty())
6134 return llvm::DebugLoc();
6136 llvm::MDNode *
Scope = LexicalBlockStack.back();
6141llvm::DINode::DIFlags CGDebugInfo::getCallSiteRelatedAttrs()
const {
6145 DebugKind == llvm::codegenoptions::NoDebugInfo ||
6146 DebugKind == llvm::codegenoptions::LocTrackingOnly)
6147 return llvm::DINode::FlagZero;
6152 bool SupportsDWARFv4Ext =
6154 (CGM.
getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::LLDB ||
6155 CGM.
getCodeGenOpts().getDebuggerTuning() == llvm::DebuggerKind::GDB);
6157 if (!SupportsDWARFv4Ext && CGM.
getCodeGenOpts().DwarfVersion < 5)
6158 return llvm::DINode::FlagZero;
6160 return llvm::DINode::FlagAllCallsDescribed;
6171 return DBuilder.createConstantValueExpression(
6172 Val.
getFloat().bitcastToAPInt().getZExtValue());
6177 llvm::APSInt
const &ValInt = Val.
getInt();
6178 std::optional<uint64_t> ValIntOpt;
6179 if (ValInt.isUnsigned())
6180 ValIntOpt = ValInt.tryZExtValue();
6181 else if (
auto tmp = ValInt.trySExtValue())
6184 ValIntOpt =
static_cast<uint64_t
>(*tmp);
6187 return DBuilder.createConstantValueExpression(ValIntOpt.value());
Defines the clang::ASTContext interface.
static bool IsReconstitutableType(QualType QT)
static void stripUnusedQualifiers(Qualifiers &Q)
static bool hasCXXMangling(const TagDecl *TD, llvm::DICompileUnit *TheCU)
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 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 uint32_t getDeclAlignIfRequired(const Decl *D, const ASTContext &Ctx)
static bool hasExplicitMemberDefinition(CXXRecordDecl::method_iterator I, CXXRecordDecl::method_iterator End)
static bool canUseCtorHoming(const CXXRecordDecl *RD)
static bool hasDefaultGetterName(const ObjCPropertyDecl *PD, const ObjCMethodDecl *Getter)
static bool isClassOrMethodDLLImport(const CXXRecordDecl *RD)
Return true if the class or any of its methods are marked dllimport.
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 unsigned getDwarfCC(CallingConv CC)
static bool ReferencesAnonymousEntity(ArrayRef< TemplateArgument > Args)
Defines the C++ Decl subclasses, other than those for templates (found in DeclTemplate....
Defines the C++ template declaration subclasses.
llvm::MachO::Target Target
constexpr llvm::StringRef ClangTrapPrefix
static const NamedDecl * getDefinition(const Decl *D)
Defines the SourceManager interface.
Defines version macros and version-related utility functions for Clang.
__device__ __2f16 float c
APValue - This class implements a discriminated union of [uninitialized] [APSInt] [APFloat],...
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.
BuiltinVectorTypeInfo getBuiltinVectorTypeInfo(const BuiltinType *VecTy) const
Returns the element type, element count and number of vectors (in case of tuple) for a builtin vector...
SourceManager & getSourceManager()
TranslationUnitDecl * getTranslationUnitDecl() const
TypedefNameDecl * getTypedefNameForUnnamedTagDecl(const TagDecl *TD)
uint64_t getFieldOffset(const ValueDecl *FD) const
Get the offset of a FieldDecl or IndirectFieldDecl, in bits.
QualType getObjCInterfaceType(const ObjCInterfaceDecl *Decl, ObjCInterfaceDecl *PrevDecl=nullptr) const
getObjCInterfaceType - Return the unique reference to the type for the specified ObjC interface decl.
QualType getRecordType(const RecordDecl *Decl) const
const ASTRecordLayout & getASTRecordLayout(const RecordDecl *D) const
Get or compute information about the layout of the specified record (struct/union/class) D,...
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
QualType getEnumType(const EnumDecl *Decl) const
QualType getBlockDescriptorExtendedType() const
Gets the struct used to keep track of the extended descriptor for pointer to blocks.
QualType getLValueReferenceType(QualType T, bool SpelledAsLValue=true) const
Return the uniqued reference to the type for an lvalue reference to the specified type.
bool BlockRequiresCopying(QualType Ty, const VarDecl *D)
Returns true iff we need copy/dispose helpers for the given type.
QualType getTypeDeclType(const TypeDecl *Decl, const TypeDecl *PrevDecl=nullptr) const
Return the unique reference to the type for the specified type declaration.
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.
QualType getObjCInstanceType()
Retrieve the Objective-C "instancetype" type, if already known; otherwise, returns a NULL type;.
const ASTRecordLayout & getASTObjCInterfaceLayout(const ObjCInterfaceDecl *D) const
Get or compute information about the layout of the specified Objective-C interface.
QualType getBaseElementType(const ArrayType *VAT) const
Return the innermost element type of an array type.
QualType getObjCSelType() const
Retrieve the type that corresponds to the predefined Objective-C 'SEL' type.
CanQualType UnsignedLongTy
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.
int64_t toBits(CharUnits CharSize) const
Convert a size in characters to a size in bits.
const clang::PrintingPolicy & getPrintingPolicy() const
QualType getObjCIdType() const
Represents the Objective-CC id type.
const ArrayType * getAsArrayType(QualType T) const
Type Query functions.
uint64_t getTypeSize(QualType T) const
Return the size of the specified (complete) type T, in bits.
CanQualType UnsignedCharTy
DeclaratorDecl * getDeclaratorForUnnamedTagDecl(const TagDecl *TD)
QualType getFunctionType(QualType ResultTy, ArrayRef< QualType > Args, const FunctionProtoType::ExtProtoInfo &EPI) const
Return a normal function type with a typed argument list.
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.
unsigned getTargetAddressSpace(LangAS AS) const
unsigned getTypeAlign(QualType T) const
Return the ABI-specified alignment of a (complete) type T, in bits.
uint64_t getCharWidth() const
Return the size of the character type, in bits.
ASTRecordLayout - This class contains layout information for one RecordDecl, which is a struct/union/...
uint64_t getFieldOffset(unsigned FieldNo) const
getFieldOffset - Get the offset of the given field index, in bits.
CharUnits getVBPtrOffset() const
getVBPtrOffset - Get the offset for virtual base table pointer.
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
ArraySubscriptExpr - [C99 6.5.2.1] Array Subscripting.
Represents an array type, per C99 6.7.5.2 - Array Declarators.
QualType getElementType() const
QualType getValueType() const
Gets the type contained by this atomic type, i.e.
const BTFTypeTagAttr * getAttr() const
QualType getWrappedType() const
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.
A fixed int type of a specified bitwidth.
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
This class is used for builtin types like 'int'.
StringRef getName(const PrintingPolicy &Policy) const
Represents a C++ constructor within a class.
Represents a static or instance method of a struct/union/class.
unsigned size_overridden_methods() const
RefQualifierKind getRefQualifier() const
Retrieve the ref-qualifier associated with this method.
const CXXRecordDecl * getParent() const
Return the parent of this method declaration, which is the class in which this method is defined.
QualType getThisType() const
Return the type of the this pointer.
CXXMethodDecl * getCanonicalDecl() override
Retrieves the "canonical" declaration of the given declaration.
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).
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
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
llvm::iterator_range< base_class_const_iterator > base_class_const_range
A wrapper class around a pointer that always points to its canonical declaration.
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...
llvm::SmallVector< std::pair< std::string, std::string >, 0 > DebugPrefixMap
std::string CoverageNotesFile
The filename with path we use for coverage notes files.
std::string CoverageDataFile
The filename with path we use for coverage data files.
std::string DebugCompilationDir
The string to embed in debug information as the current working directory.
bool hasReducedDebugInfo() const
Check if type and variable info should be emitted.
bool hasMaybeUnusedDebugInfo() const
Check if maybe unused type info should be emitted.
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
virtual CharUnits getVirtualFunctionPrologueThisAdjustment(GlobalDecl GD)
Get the ABI-specific "this" parameter adjustment to apply in the prologue of a virtual function.
@ RAA_Indirect
Pass it as a pointer to temporary memory.
virtual llvm::Constant * EmitNullMemberPointer(const MemberPointerType *MPT)
Create a null member pointer of the given type.
virtual RecordArgABI getRecordArgABI(const CXXRecordDecl *RD) const =0
Returns how an argument of the given record type should be passed.
virtual llvm::Constant * EmitMemberDataPointer(const MemberPointerType *MPT, CharUnits offset)
Create a member pointer for the given field.
virtual llvm::Constant * EmitMemberFunctionPointer(const CXXMethodDecl *MD)
Create a member pointer for the given method.
MangleContext & getMangleContext()
Gets the mangle context.
llvm::MDNode * getInlinedAt() const
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 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 setInlinedAt(llvm::MDNode *InlinedAt)
Update the current inline scope.
void completeUnusedClass(const CXXRecordDecl &D)
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 EmitFuncDeclForCallSite(llvm::CallBase *CallOrInvoke, QualType CalleeType, const FunctionDecl *CalleeDecl)
Emit debug info for an extern function being called.
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.
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 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 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 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 directi...
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...
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.
unsigned ComputeBitfieldBitOffset(CodeGen::CodeGenModule &CGM, const ObjCInterfaceDecl *ID, const ObjCIvarDecl *Ivar)
CGRecordLayout - This class handles struct and union layout info while lowering AST types to LLVM typ...
const CGBitFieldInfo & getBitFieldInfo(const FieldDecl *FD) const
Return the BitFieldInfo that corresponds to the field FD.
CodeGenFunction - This class organizes the per-function state that is used while generating LLVM code...
CGDebugInfo * getDebugInfo()
This class organizes the cross-function state that is used while generating LLVM code.
const PreprocessorOptions & getPreprocessorOpts() const
ConstantAddress GetAddrOfMSGuidDecl(const MSGuidDecl *GD)
Get the address of a GUID.
llvm::Module & getModule() const
llvm::Constant * GetAddrOfFunction(GlobalDecl GD, llvm::Type *Ty=nullptr, bool ForVTable=false, bool DontDefer=false, ForDefinition_t IsForDefinition=NotForDefinition)
Return the address of the given function.
const IntrusiveRefCntPtr< llvm::vfs::FileSystem > & getFileSystem() const
const LangOptions & getLangOpts() const
int getUniqueBlockCount()
Fetches the global unique block count.
CodeGenTypes & getTypes()
const TargetInfo & getTarget() const
const llvm::DataLayout & getDataLayout() const
CGCXXABI & getCXXABI() const
ItaniumVTableContext & getItaniumVTableContext()
ASTContext & getContext() const
ConstantAddress GetAddrOfTemplateParamObject(const TemplateParamObjectDecl *TPO)
Get the address of a template parameter object.
llvm::Constant * GetAddrOfGlobalVar(const VarDecl *D, llvm::Type *Ty=nullptr, ForDefinition_t IsForDefinition=NotForDefinition)
Return the llvm::Constant for the address of the given global variable.
MicrosoftVTableContext & getMicrosoftVTableContext()
const HeaderSearchOptions & getHeaderSearchOpts() const
const TargetCodeGenInfo & getTargetCodeGenInfo()
const CodeGenOptions & getCodeGenOpts() const
StringRef getMangledName(GlobalDecl GD)
llvm::LLVMContext & getLLVMContext()
CGObjCRuntime & getObjCRuntime()
Return a reference to the configured Objective-C runtime.
llvm::GlobalVariable::LinkageTypes getVTableLinkage(const CXXRecordDecl *RD)
Return the appropriate linkage for the vtable, VTT, and type information of the given class.
const GlobalDecl getMangledNameDecl(StringRef)
const CGRecordLayout & getCGRecordLayout(const RecordDecl *)
getCGRecordLayout - Return record layout info for the given record decl.
unsigned getTargetAddressSpace(QualType T) const
llvm::Constant * getPointer() const
llvm::Constant * emitAbstract(const Expr *E, QualType T)
Emit the result of the given expression as an abstract constant, asserting that it succeeded.
virtual bool shouldEmitDWARFBitFieldSeparators() const
Complex values, per C99 6.2.5p11.
Represents a concrete matrix type with constant number of rows and columns.
unsigned getNumColumns() const
Returns the number of columns in the matrix.
unsigned getNumRows() const
Returns the number of rows in the matrix.
specific_decl_iterator - Iterates over a subrange of declarations stored in a DeclContext,...
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
DeclContext * getParent()
getParent - Returns the containing DeclContext.
DeclContext * getEnclosingNamespaceContext()
Retrieve the nearest enclosing namespace context.
decl_range decls() const
decls_begin/decls_end - Iterate over the declarations stored in this context.
DeclStmt - Adaptor class for mixing declarations with statements and expressions.
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.
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.
Represents a ValueDecl that came out of a declarator.
enumerator_range enumerators() const
bool isScoped() const
Returns true if this is a C++11 scoped enumeration.
QualType getIntegerType() const
Return the integer type this enum decl corresponds to.
EnumDecl * getDefinition() const
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of enums.
EnumDecl * getDecl() 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...
Represents a member of a struct/union/class.
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...
An opaque identifier used by SourceManager which refers to a source file (MemoryBuffer) along with it...
static InputKind getInputKindForExtension(StringRef Extension)
getInputKindForExtension - Return the appropriate input kind for a file extension.
Represents a function declaration or definition.
bool hasCXXExplicitFunctionObjectParameter() const
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.
bool isDeleted() const
Whether this function has been deleted.
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.
bool isPureVirtual() const
Whether this virtual function is pure, i.e.
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
QualType getWrappedType() const
One of these records is kept for each identifier that is lexed.
Describes a module import declaration, which makes the contents of the named module visible in the cu...
uint64_t getMethodVTableIndex(GlobalDecl GD)
Locate a virtual function in the vtable.
CharUnits getVirtualBaseOffsetOffset(const CXXRecordDecl *RD, const CXXRecordDecl *VBase)
Return the offset in chars (relative to the vtable address point) where the offset of the virtual bas...
An lvalue reference type, per C++11 [dcl.ref].
Represents the declaration of a label.
Describes the capture of a variable or of this, or of a C++1y init-capture.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
std::string ModuleName
The module currently being compiled as specified by -fmodule-name.
clang::ObjCRuntime ObjCRuntime
bool UseTargetPathSeparator
Indicates whether to use target's platform-specific file separator when FILE macro is used and when c...
virtual std::string getLambdaString(const CXXRecordDecl *Lambda)=0
virtual void mangleCXXRTTIName(QualType T, raw_ostream &, bool NormalizeIntegers=false)=0
QualType getElementType() const
Returns type of the elements being stored in the matrix.
MemberExpr - [C99 6.5.2.3] Structure and Union Members.
A pointer to member type per C++ 8.3.3 - Pointers to members.
CXXRecordDecl * getMostRecentCXXRecordDecl() const
QualType getPointeeType() const
const Type * getClass() const
unsigned getVBTableIndex(const CXXRecordDecl *Derived, const CXXRecordDecl *VBase)
Returns the index of VBase in the vbtable of Derived.
MethodVFTableLocation getMethodVFTableLocation(GlobalDecl GD)
const VTableLayout & getVFTableLayout(const CXXRecordDecl *RD, CharUnits VFPtrOffset)
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.
NamedDecl * 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.
ObjCCategoryDecl - Represents a category declaration.
ObjCImplementationDecl - Represents a class definition - this is where method definitions are specifi...
Represents an ObjC class declaration.
ObjCImplementationDecl * getImplementation() const
Interfaces are the core concept in Objective-C for object oriented design.
ObjCInterfaceDecl * getDecl() const
Get the declaration of this interface.
ObjCIvarDecl - Represents an ObjC instance variable.
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()
Represents a pointer to an Objective C object.
bool isObjCQualifiedIdType() const
True if this is equivalent to 'id.
QualType getPointeeType() const
Gets the type pointed to by this ObjC pointer.
Represents a class type in Objective C.
QualType getBaseType() const
Gets the base type of this object type.
Represents one property declaration in an Objective-C interface.
ObjCPropertyImplDecl - Represents implementation declaration of a property in a class or category imp...
bool isNonFragile() const
Does this runtime follow the set of implied behaviors for a "non-fragile" ABI?
Represents a type parameter type in Objective C.
ObjCTypeParamDecl * getDecl() const
Represents a parameter to a function.
QualType getElementType() const
PointerType - C99 6.7.5.1 - Pointer Declarators.
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.
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
A qualifier set is used to build a set of qualifiers.
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()
An rvalue reference type, per C++11 [dcl.ref].
Represents a struct/union/class.
field_iterator field_end() const
field_range fields() const
RecordDecl * getDefinition() const
Returns the RecordDecl that actually defines this struct/union/class.
bool isAnonymousStructOrUnion() const
Whether this is an anonymous struct or union.
field_iterator field_begin() const
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
RecordDecl * getDecl() const
A class that does preorder or postorder depth-first traversal on the entire Clang AST and visits each...
redecl_range redecls() const
Returns an iterator range for all the redeclarations of the same decl.
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.
Smart pointer class that efficiently represents Objective-C method names.
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.
PresumedLoc getPresumedLoc(SourceLocation Loc, bool UseLineDirectives=true) const
Returns the "presumed" location of a SourceLocation specifies.
SourceLocation getExpansionLoc(SourceLocation Loc) const
Given a SourceLocation object Loc, return the expansion location referenced by the ID.
Stmt - This represents one statement.
StringLiteral - This represents a string literal expression, e.g.
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 * getDecl() const
bool isMicrosoft() const
Is this ABI an MSVC-compatible ABI?
bool isItaniumFamily() const
Does this ABI generally fall into the Itanium family of ABIs?
virtual std::optional< unsigned > getDWARFAddressSpace(unsigned AddressSpace) const
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
uint64_t getPointerWidth(LangAS AddrSpace) const
Return the width of pointers on this target, for the specified address space.
virtual unsigned getVtblPtrAddressSpace() const
uint64_t getPointerAlign(LangAS AddrSpace) const
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
A template argument list.
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.
void print(raw_ostream &OS, const PrintingPolicy &Policy, Qualified Qual=Qualified::AsWritten) const
Print the template name.
Stores a list of template parameters for a TemplateDecl and its derived classes.
ArrayRef< NamedDecl * > asArray()
Represents a type template specialization; the template must be a class template, a type alias templa...
QualType getAliasedType() const
Get the aliased type, if this is a specialization of a type alias template.
ArrayRef< TemplateArgument > template_arguments() const
TemplateName getTemplateName() const
Retrieve the name of the template that we are specializing.
bool isTypeAlias() const
Determine if this template specialization type is for a type alias template that has been substituted...
Represents a declaration of a type.
const Type * getTypeForDecl() const
The base class of the type hierarchy.
bool isIncompleteArrayType() const
const T * castAs() const
Member-template castAs<specific type>.
bool isReferenceType() const
bool isExtVectorBoolType() const
AutoType * getContainedAutoType() const
Get the AutoType whose type will be deduced for a variable with an initializer of this type.
bool isInstantiationDependentType() const
Determine whether this type is an instantiation-dependent type, meaning that the type involves a temp...
bool isMemberDataPointerType() const
bool isBitIntType() 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
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
Base class for declarations which introduce a typedef-name.
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.
APValue * evaluateValue() const
Attempt to evaluate the value of the initializer attached to this declaration, and produce notes expl...
bool isStaticDataMember() const
Determines whether this is a static data member.
const Expr * getInit() const
bool isEscapingByref() const
Indicates the capture is a __block variable that is captured by a block that can potentially escape (...
Declaration of a variable template.
Represents a GCC generic vector type.
unsigned getNumElements() const
QualType getElementType() const
@ Type
The l-value was considered opaque, so the alignment was determined from a type.
const internal::VariadicAllOfMatcher< Type > type
Matches Types in the clang AST.
const internal::VariadicDynCastAllOfMatcher< Decl, BlockDecl > blockDecl
Matches block declarations.
The JSON file list parser is used to communicate input to InstallAPI.
@ RQ_LValue
An lvalue ref-qualifier was provided (&).
@ RQ_RValue
An rvalue ref-qualifier was provided (&&).
bool operator<(DeclarationName LHS, DeclarationName RHS)
Ordering on two declaration names.
@ Result
The result type of a method or function.
bool isNoexceptExceptionSpec(ExceptionSpecificationType ESpecType)
@ Dtor_Deleting
Deleting dtor.
const FunctionProtoType * T
void printTemplateArgumentList(raw_ostream &OS, ArrayRef< TemplateArgument > Args, const PrintingPolicy &Policy, const TemplateParameterList *TPL=nullptr)
Print a template argument list, including the '<' and '>' enclosing the template arguments.
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
@ 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,...
AccessSpecifier
A C++ access specifier (public, private, protected), plus the special value "none" which means differ...
Structure with information about how a bitfield should be accessed.
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.
llvm::IntegerType * Int8Ty
i8, i16, i32, and i64
unsigned char PointerWidthInBits
The width of a pointer into the generic address space.
EvalResult is a struct with detailed info about an evaluated expression.
Extra information about a function prototype.
uint64_t Index
Method's index in the vftable.
Describes how types, statements, expressions, and declarations should be printed.
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 PrintCanonicalTypes
Whether to print types as written or canonically.
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.
A this pointer adjustment.