22#include "llvm/ADT/StringExtras.h"
23#include "llvm/Support/raw_ostream.h"
43 if (
const UsingType *UT = dyn_cast<UsingType>(Ty)) {
48 if (
const ParenType *PT = dyn_cast<ParenType>(Ty)) {
59 dyn_cast<SubstTemplateTypeParmType>(Ty)) {
69 if (
const AdjustedType *AT = dyn_cast<AdjustedType>(Ty)) {
74 if (
const AutoType *AT = dyn_cast<AutoType>(Ty)) {
83 if (
const FunctionType *FT = dyn_cast<FunctionType>(Ty)) {
84 bool DesugarReturn =
false;
85 QualType SugarRT = FT->getReturnType();
92 bool DesugarArgument =
false;
98 if (
auto nullability =
107 if (DesugarReturn || DesugarArgument) {
118 dyn_cast<TemplateSpecializationType>(Ty)) {
119 if (!TST->isTypeAlias()) {
120 bool DesugarArgument =
false;
130 if (DesugarArgument) {
133 TST->getTemplateName(), Args, QT);
139 if (
const auto *AT = dyn_cast<ArrayType>(Ty)) {
142 if (
const auto *CAT = dyn_cast<ConstantArrayType>(AT))
144 ElementTy, CAT->getSize(), CAT->getSizeExpr(),
145 CAT->getSizeModifier(), CAT->getIndexTypeCVRQualifiers());
146 else if (
const auto *VAT = dyn_cast<VariableArrayType>(AT))
148 ElementTy, VAT->getSizeExpr(), VAT->getSizeModifier(),
149 VAT->getIndexTypeCVRQualifiers(), VAT->getBracketsRange());
150 else if (
const auto *DSAT = dyn_cast<DependentSizedArrayType>(AT))
152 ElementTy, DSAT->getSizeExpr(), DSAT->getSizeModifier(),
153 DSAT->getIndexTypeCVRQualifiers(), DSAT->getBracketsRange());
154 else if (
const auto *IAT = dyn_cast<IncompleteArrayType>(AT))
156 IAT->getIndexTypeCVRQualifiers());
158 llvm_unreachable(
"Unhandled array type");
176 bool IsSugar =
false;
178#define ABSTRACT_TYPE(Class, Base)
179#define TYPE(Class, Base) \
181const Class##Type *CTy = cast<Class##Type>(Ty); \
182if (CTy->isSugared()) { \
184Underlying = CTy->desugar(); \
188#include "clang/AST/TypeNodes.inc"
197 if (isa<VectorType>(Underlying))
202 if (
const TypedefType *QTT = dyn_cast<TypedefType>(QT))
203 if (UTT->getDecl()->getTypedefNameForAnonDecl() == QTT->getDecl())
226 if (Ty->getBaseType().getTypePtr() != Ty && !ShouldAKA) {
230 BaseType, Ty->getTypeArgsAsWritten(),
232 Ty->isKindOfTypeAsWritten());
236 return QC.
apply(Context, QT);
268 bool ForceAKA =
false;
273 for (
const intptr_t &QualTypeVal : QualTypeVals) {
281 if (CompareCanTy == CanTy)
284 bool ShouldAKA =
false;
287 std::string CompareDesugarStr =
289 if (CompareS != S && CompareDesugarStr != S)
292 std::string CompareCanS =
295 if (CompareCanS == CanS)
304 bool Repeated =
false;
305 for (
const auto &PrevArg : PrevArgs) {
320 bool ShouldAKA =
false;
322 if (ShouldAKA || ForceAKA) {
323 if (DesugaredTy == Ty) {
328 S =
"'" + S +
"' (aka '" + akaStr +
"')";
337 std::string DecoratedString;
338 llvm::raw_string_ostream OS(DecoratedString);
339 const char *Values = VTy->getNumElements() > 1 ?
"values" :
"value";
340 OS <<
"'" << S <<
"' (vector of " << VTy->getNumElements() <<
" '"
342 <<
"' " << Values <<
")";
343 return DecoratedString;
353 bool PrintFromType,
bool ElideType,
367 size_t OldEnd = Output.size();
368 llvm::raw_svector_ostream OS(Output);
369 bool NeedQuotes =
true;
372 default: llvm_unreachable(
"unknown ArgumentKind");
374 assert(Modifier.empty() && Argument.empty() &&
375 "Invalid modifier for Qualifiers argument");
379 OS << (Context.
getLangOpts().OpenCL ?
"default" :
"generic");
380 OS <<
" address space";
382 OS <<
"address space";
383 OS <<
" '" << S <<
"'";
389 assert(Modifier.empty() && Argument.empty() &&
390 "Invalid modifier for Qualifiers argument");
425 Modifier = StringRef();
426 Argument = StringRef();
431 assert(Modifier.empty() && Argument.empty() &&
432 "Invalid modifier for QualType argument");
440 if (Modifier ==
"objcclass" && Argument.empty())
442 else if (Modifier ==
"objcinstance" && Argument.empty())
445 assert(Modifier.empty() && Argument.empty() &&
446 "Invalid modifier for DeclarationName argument");
453 if (Modifier ==
"q" && Argument.empty())
456 assert(Modifier.empty() && Argument.empty() &&
457 "Invalid modifier for NamedDecl* argument");
472 assert(DC &&
"Should never have a null declaration context");
478 OS <<
"the global namespace";
480 OS <<
"the global scope";
482 OS <<
"block literal";
484 OS <<
"lambda expression";
488 PrevArgs, QualTypeVals);
490 assert(isa<NamedDecl>(DC) &&
"Expected a NamedDecl");
492 if (isa<NamespaceDecl>(ND))
494 else if (isa<ObjCMethodDecl>(ND))
496 else if (isa<FunctionDecl>(ND))
506 const Attr *At =
reinterpret_cast<Attr *
>(Val);
507 assert(At &&
"Received null Attr object!");
515 Output.insert(Output.begin()+OldEnd,
'\'');
516 Output.push_back(
'\'');
581 FromIntegerAndToDeclaration,
582 FromDeclarationAndToInteger
589 struct TemplateArgumentInfo {
593 bool IsValidInt =
false;
594 Expr *ArgExpr =
nullptr;
597 bool NeedAddressOf =
false;
598 bool IsNullPtr =
false;
599 bool IsDefault =
false;
609 unsigned NextNode = 0;
612 unsigned ChildNode = 0;
615 unsigned ParentNode = 0;
617 TemplateArgumentInfo FromArgInfo, ToArgInfo;
622 DiffNode(
unsigned ParentNode = 0) : ParentNode(ParentNode) {}
629 unsigned CurrentNode;
633 unsigned NextFreeNode;
639 DiffTree() : CurrentNode(0), NextFreeNode(1), ReadNode(0) {
640 FlatTree.push_back(DiffNode());
646 bool FromDefault,
bool ToDefault) {
647 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
648 FlatTree[CurrentNode].Kind = Template;
649 FlatTree[CurrentNode].FromArgInfo.TD = FromTD;
650 FlatTree[CurrentNode].ToArgInfo.TD = ToTD;
651 FlatTree[CurrentNode].FromArgInfo.Qual = FromQual;
652 FlatTree[CurrentNode].ToArgInfo.Qual = ToQual;
653 SetDefault(FromDefault, ToDefault);
658 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
659 FlatTree[CurrentNode].Kind =
Type;
660 FlatTree[CurrentNode].FromArgInfo.ArgType = FromType;
661 FlatTree[CurrentNode].ToArgInfo.ArgType = ToType;
662 SetDefault(FromDefault, ToDefault);
665 void SetExpressionDiff(
Expr *FromExpr,
Expr *ToExpr,
bool FromDefault,
667 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
669 FlatTree[CurrentNode].FromArgInfo.ArgExpr = FromExpr;
670 FlatTree[CurrentNode].ToArgInfo.ArgExpr = ToExpr;
671 SetDefault(FromDefault, ToDefault);
675 bool FromDefault,
bool ToDefault) {
676 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
677 FlatTree[CurrentNode].Kind = TemplateTemplate;
678 FlatTree[CurrentNode].FromArgInfo.TD = FromTD;
679 FlatTree[CurrentNode].ToArgInfo.TD = ToTD;
680 SetDefault(FromDefault, ToDefault);
683 void SetIntegerDiff(
const llvm::APSInt &FromInt,
const llvm::APSInt &ToInt,
684 bool IsValidFromInt,
bool IsValidToInt,
686 Expr *FromExpr,
Expr *ToExpr,
bool FromDefault,
688 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
689 FlatTree[CurrentNode].Kind =
Integer;
690 FlatTree[CurrentNode].FromArgInfo.Val = FromInt;
691 FlatTree[CurrentNode].ToArgInfo.Val = ToInt;
692 FlatTree[CurrentNode].FromArgInfo.IsValidInt = IsValidFromInt;
693 FlatTree[CurrentNode].ToArgInfo.IsValidInt = IsValidToInt;
694 FlatTree[CurrentNode].FromArgInfo.ArgType = FromIntType;
695 FlatTree[CurrentNode].ToArgInfo.ArgType = ToIntType;
696 FlatTree[CurrentNode].FromArgInfo.ArgExpr = FromExpr;
697 FlatTree[CurrentNode].ToArgInfo.ArgExpr = ToExpr;
698 SetDefault(FromDefault, ToDefault);
702 bool FromAddressOf,
bool ToAddressOf,
703 bool FromNullPtr,
bool ToNullPtr,
Expr *FromExpr,
704 Expr *ToExpr,
bool FromDefault,
bool ToDefault) {
705 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
707 FlatTree[CurrentNode].FromArgInfo.VD = FromValueDecl;
708 FlatTree[CurrentNode].ToArgInfo.VD = ToValueDecl;
709 FlatTree[CurrentNode].FromArgInfo.NeedAddressOf = FromAddressOf;
710 FlatTree[CurrentNode].ToArgInfo.NeedAddressOf = ToAddressOf;
711 FlatTree[CurrentNode].FromArgInfo.IsNullPtr = FromNullPtr;
712 FlatTree[CurrentNode].ToArgInfo.IsNullPtr = ToNullPtr;
713 FlatTree[CurrentNode].FromArgInfo.ArgExpr = FromExpr;
714 FlatTree[CurrentNode].ToArgInfo.ArgExpr = ToExpr;
715 SetDefault(FromDefault, ToDefault);
718 void SetFromDeclarationAndToIntegerDiff(
719 ValueDecl *FromValueDecl,
bool FromAddressOf,
bool FromNullPtr,
720 Expr *FromExpr,
const llvm::APSInt &ToInt,
bool IsValidToInt,
721 QualType ToIntType,
Expr *ToExpr,
bool FromDefault,
bool ToDefault) {
722 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
723 FlatTree[CurrentNode].Kind = FromDeclarationAndToInteger;
724 FlatTree[CurrentNode].FromArgInfo.VD = FromValueDecl;
725 FlatTree[CurrentNode].FromArgInfo.NeedAddressOf = FromAddressOf;
726 FlatTree[CurrentNode].FromArgInfo.IsNullPtr = FromNullPtr;
727 FlatTree[CurrentNode].FromArgInfo.ArgExpr = FromExpr;
728 FlatTree[CurrentNode].ToArgInfo.Val = ToInt;
729 FlatTree[CurrentNode].ToArgInfo.IsValidInt = IsValidToInt;
730 FlatTree[CurrentNode].ToArgInfo.ArgType = ToIntType;
731 FlatTree[CurrentNode].ToArgInfo.ArgExpr = ToExpr;
732 SetDefault(FromDefault, ToDefault);
735 void SetFromIntegerAndToDeclarationDiff(
736 const llvm::APSInt &FromInt,
bool IsValidFromInt,
QualType FromIntType,
738 bool ToNullPtr,
Expr *ToExpr,
bool FromDefault,
bool ToDefault) {
739 assert(FlatTree[CurrentNode].Kind == Invalid &&
"Node is not empty.");
740 FlatTree[CurrentNode].Kind = FromIntegerAndToDeclaration;
741 FlatTree[CurrentNode].FromArgInfo.Val = FromInt;
742 FlatTree[CurrentNode].FromArgInfo.IsValidInt = IsValidFromInt;
743 FlatTree[CurrentNode].FromArgInfo.ArgType = FromIntType;
744 FlatTree[CurrentNode].FromArgInfo.ArgExpr = FromExpr;
745 FlatTree[CurrentNode].ToArgInfo.VD = ToValueDecl;
746 FlatTree[CurrentNode].ToArgInfo.NeedAddressOf = ToAddressOf;
747 FlatTree[CurrentNode].ToArgInfo.IsNullPtr = ToNullPtr;
748 FlatTree[CurrentNode].ToArgInfo.ArgExpr = ToExpr;
749 SetDefault(FromDefault, ToDefault);
753 void SetDefault(
bool FromDefault,
bool ToDefault) {
754 assert((!FromDefault || !ToDefault) &&
"Both arguments cannot be default.");
755 FlatTree[CurrentNode].FromArgInfo.IsDefault = FromDefault;
756 FlatTree[CurrentNode].ToArgInfo.IsDefault = ToDefault;
760 void SetSame(
bool Same) {
761 FlatTree[CurrentNode].Same =
Same;
765 void SetKind(DiffKind Kind) {
766 FlatTree[CurrentNode].Kind =
Kind;
771 assert(FlatTree[CurrentNode].Kind != Invalid &&
772 "Cannot exit node before setting node information.");
773 CurrentNode = FlatTree[CurrentNode].ParentNode;
779 assert(FlatTree[CurrentNode].Kind == Template &&
780 "Only Template nodes can have children nodes.");
781 FlatTree.push_back(DiffNode(CurrentNode));
782 DiffNode &
Node = FlatTree[CurrentNode];
783 if (
Node.ChildNode == 0) {
785 Node.ChildNode = NextFreeNode;
790 for (i =
Node.ChildNode; FlatTree[i].NextNode != 0;
791 i = FlatTree[i].NextNode) {
793 FlatTree[i].NextNode = NextFreeNode;
795 CurrentNode = NextFreeNode;
801 void StartTraverse() {
803 CurrentNode = NextFreeNode;
809 ReadNode = FlatTree[ReadNode].ParentNode;
814 assert(FlatTree[ReadNode].Kind == Template &&
"Unexpected kind.");
815 FromTD = FlatTree[ReadNode].FromArgInfo.TD;
816 ToTD = FlatTree[ReadNode].ToArgInfo.TD;
817 FromQual = FlatTree[ReadNode].FromArgInfo.Qual;
818 ToQual = FlatTree[ReadNode].ToArgInfo.Qual;
822 assert(FlatTree[ReadNode].Kind ==
Type &&
"Unexpected kind");
823 FromType = FlatTree[ReadNode].FromArgInfo.ArgType;
824 ToType = FlatTree[ReadNode].ToArgInfo.ArgType;
827 void GetExpressionDiff(
Expr *&FromExpr,
Expr *&ToExpr) {
828 assert(FlatTree[ReadNode].Kind ==
Expression &&
"Unexpected kind");
829 FromExpr = FlatTree[ReadNode].FromArgInfo.ArgExpr;
830 ToExpr = FlatTree[ReadNode].ToArgInfo.ArgExpr;
834 assert(FlatTree[ReadNode].Kind == TemplateTemplate &&
"Unexpected kind.");
835 FromTD = FlatTree[ReadNode].FromArgInfo.TD;
836 ToTD = FlatTree[ReadNode].ToArgInfo.TD;
839 void GetIntegerDiff(llvm::APSInt &FromInt, llvm::APSInt &ToInt,
840 bool &IsValidFromInt,
bool &IsValidToInt,
843 assert(FlatTree[ReadNode].Kind == Integer &&
"Unexpected kind.");
844 FromInt = FlatTree[ReadNode].FromArgInfo.Val;
845 ToInt = FlatTree[ReadNode].ToArgInfo.Val;
846 IsValidFromInt = FlatTree[ReadNode].FromArgInfo.IsValidInt;
847 IsValidToInt = FlatTree[ReadNode].ToArgInfo.IsValidInt;
848 FromIntType = FlatTree[ReadNode].FromArgInfo.ArgType;
849 ToIntType = FlatTree[ReadNode].ToArgInfo.ArgType;
850 FromExpr = FlatTree[ReadNode].FromArgInfo.ArgExpr;
851 ToExpr = FlatTree[ReadNode].ToArgInfo.ArgExpr;
855 bool &FromAddressOf,
bool &ToAddressOf,
856 bool &FromNullPtr,
bool &ToNullPtr,
Expr *&FromExpr,
858 assert(FlatTree[ReadNode].Kind == Declaration &&
"Unexpected kind.");
859 FromValueDecl = FlatTree[ReadNode].FromArgInfo.VD;
860 ToValueDecl = FlatTree[ReadNode].ToArgInfo.VD;
861 FromAddressOf = FlatTree[ReadNode].FromArgInfo.NeedAddressOf;
862 ToAddressOf = FlatTree[ReadNode].ToArgInfo.NeedAddressOf;
863 FromNullPtr = FlatTree[ReadNode].FromArgInfo.IsNullPtr;
864 ToNullPtr = FlatTree[ReadNode].ToArgInfo.IsNullPtr;
865 FromExpr = FlatTree[ReadNode].FromArgInfo.ArgExpr;
866 ToExpr = FlatTree[ReadNode].ToArgInfo.ArgExpr;
869 void GetFromDeclarationAndToIntegerDiff(
870 ValueDecl *&FromValueDecl,
bool &FromAddressOf,
bool &FromNullPtr,
871 Expr *&FromExpr, llvm::APSInt &ToInt,
bool &IsValidToInt,
873 assert(FlatTree[ReadNode].Kind == FromDeclarationAndToInteger &&
875 FromValueDecl = FlatTree[ReadNode].FromArgInfo.VD;
876 FromAddressOf = FlatTree[ReadNode].FromArgInfo.NeedAddressOf;
877 FromNullPtr = FlatTree[ReadNode].FromArgInfo.IsNullPtr;
878 FromExpr = FlatTree[ReadNode].FromArgInfo.ArgExpr;
879 ToInt = FlatTree[ReadNode].ToArgInfo.Val;
880 IsValidToInt = FlatTree[ReadNode].ToArgInfo.IsValidInt;
881 ToIntType = FlatTree[ReadNode].ToArgInfo.ArgType;
882 ToExpr = FlatTree[ReadNode].ToArgInfo.ArgExpr;
885 void GetFromIntegerAndToDeclarationDiff(
886 llvm::APSInt &FromInt,
bool &IsValidFromInt,
QualType &FromIntType,
888 bool &ToNullPtr,
Expr *&ToExpr) {
889 assert(FlatTree[ReadNode].Kind == FromIntegerAndToDeclaration &&
891 FromInt = FlatTree[ReadNode].FromArgInfo.Val;
892 IsValidFromInt = FlatTree[ReadNode].FromArgInfo.IsValidInt;
893 FromIntType = FlatTree[ReadNode].FromArgInfo.ArgType;
894 FromExpr = FlatTree[ReadNode].FromArgInfo.ArgExpr;
895 ToValueDecl = FlatTree[ReadNode].ToArgInfo.VD;
896 ToAddressOf = FlatTree[ReadNode].ToArgInfo.NeedAddressOf;
897 ToNullPtr = FlatTree[ReadNode].ToArgInfo.IsNullPtr;
898 ToExpr = FlatTree[ReadNode].ToArgInfo.ArgExpr;
903 return FlatTree[ReadNode].FromArgInfo.IsDefault;
908 return FlatTree[ReadNode].ToArgInfo.IsDefault;
913 return FlatTree[ReadNode].Same;
918 return FlatTree[ReadNode].ChildNode != 0;
923 ReadNode = FlatTree[ReadNode].ChildNode;
928 bool AdvanceSibling() {
929 if (FlatTree[ReadNode].NextNode == 0)
932 ReadNode = FlatTree[ReadNode].NextNode;
937 bool HasNextSibling() {
938 return FlatTree[ReadNode].NextNode != 0;
948 return FlatTree[ReadNode].Kind;
965 struct InternalIterator {
983 : TST(TST), Index(0), CurrentTA(nullptr), EndTA(nullptr) {
997 if (CurrentTA != EndTA)
return;
1005 bool isValid()
const {
return TST; }
1008 bool isEnd()
const {
1009 assert(TST &&
"InternalIterator is invalid with a null TST.");
1014 InternalIterator &operator++() {
1015 assert(TST &&
"InternalIterator is invalid with a null TST.");
1021 if (CurrentTA != EndTA) {
1023 if (CurrentTA != EndTA)
1043 if (CurrentTA != EndTA)
1051 assert(TST &&
"InternalIterator is invalid with a null TST.");
1052 assert(!isEnd() &&
"Index exceeds number of arguments.");
1053 if (CurrentTA == EndTA)
1060 pointer operator->()
const {
1061 assert(TST &&
"InternalIterator is invalid with a null TST.");
1066 InternalIterator SugaredIterator;
1067 InternalIterator DesugaredIterator;
1071 : SugaredIterator(TST),
1073 (TST->isSugared() && !TST->isTypeAlias())
1074 ? GetTemplateSpecializationType(Context, TST->desugar())
1078 TSTiterator &operator++() {
1080 if (DesugaredIterator.isValid())
1081 ++DesugaredIterator;
1087 return *SugaredIterator;
1091 pointer operator->()
const {
1096 bool isEnd()
const {
1097 return SugaredIterator.isEnd();
1102 bool hasDesugaredTA()
const {
1103 return DesugaredIterator.isValid() && !DesugaredIterator.isEnd();
1107 reference getDesugaredTA()
const {
1108 assert(DesugaredIterator.isValid() &&
1109 "Desugared TemplateArgument should not be used.");
1110 return *DesugaredIterator;
1124 Ty = SubstType->getReplacementType();
1132 dyn_cast<ClassTemplateSpecializationDecl>(RT->
getDecl());
1156 FromArgTST = GetTemplateSpecializationType(Context, FromType);
1157 ToArgTST = GetTemplateSpecializationType(Context, ToType);
1159 if (!FromArgTST || !ToArgTST)
1162 if (!hasSameTemplate(FromArgTST, ToArgTST))
1169 void DiffTypes(
const TSTiterator &FromIter,
const TSTiterator &ToIter) {
1170 QualType FromType = GetType(FromIter);
1173 bool FromDefault = FromIter.isEnd() && !FromType.
isNull();
1174 bool ToDefault = ToIter.isEnd() && !ToType.
isNull();
1178 if (OnlyPerformTypeDiff(Context, FromType, ToType, FromArgTST, ToArgTST)) {
1179 Tree.SetTypeDiff(FromType, ToType, FromDefault, ToDefault);
1183 assert(FromArgTST && ToArgTST &&
1184 "Both template specializations need to be valid.");
1191 FromQual, ToQual, FromDefault, ToDefault);
1192 DiffTemplate(FromArgTST, ToArgTST);
1198 void DiffTemplateTemplates(
const TSTiterator &FromIter,
1199 const TSTiterator &ToIter) {
1203 ToIter.isEnd() && ToDecl);
1209 static void InitializeNonTypeDiffVariables(
ASTContext &Context,
1210 const TSTiterator &
Iter,
1212 llvm::APSInt &
Value,
bool &HasInt,
1213 QualType &IntType,
bool &IsNullPtr,
1215 bool &NeedAddressOf) {
1216 if (!
Iter.isEnd()) {
1217 switch (
Iter->getKind()) {
1226 IntType =
Iter->getIntegralType();
1229 VD =
Iter->getAsDecl();
1234 NeedAddressOf =
true;
1241 E =
Iter->getAsExpr();
1247 llvm_unreachable(
"TemplateArgument kind is not expected for NTTP");
1249 llvm_unreachable(
"TemplateArgument kind should be handled elsewhere");
1251 }
else if (!
Default->isParameterPack()) {
1252 E =
Default->getDefaultArgument().getArgument().getAsExpr();
1255 if (!
Iter.hasDesugaredTA())
1275 NeedAddressOf =
true;
1292 llvm_unreachable(
"TemplateArgument kind is not expected for NTTP");
1294 llvm_unreachable(
"TemplateArgument kind should be handled elsewhere");
1296 llvm_unreachable(
"Unexpected TemplateArgument kind");
1301 void DiffNonTypes(
const TSTiterator &FromIter,
const TSTiterator &ToIter,
1304 Expr *FromExpr =
nullptr, *ToExpr =
nullptr;
1305 llvm::APSInt FromInt, ToInt;
1307 ValueDecl *FromValueDecl =
nullptr, *ToValueDecl =
nullptr;
1308 bool HasFromInt =
false, HasToInt =
false, FromNullPtr =
false,
1309 ToNullPtr =
false, NeedFromAddressOf =
false, NeedToAddressOf =
false;
1310 InitializeNonTypeDiffVariables(
1311 Context, FromIter, FromDefaultNonTypeDecl, FromInt, HasFromInt,
1312 FromIntType, FromNullPtr, FromExpr, FromValueDecl, NeedFromAddressOf);
1313 InitializeNonTypeDiffVariables(Context, ToIter, ToDefaultNonTypeDecl, ToInt,
1314 HasToInt, ToIntType, ToNullPtr, ToExpr,
1315 ToValueDecl, NeedToAddressOf);
1317 bool FromDefault = FromIter.isEnd() &&
1318 (FromExpr || FromValueDecl || HasFromInt || FromNullPtr);
1319 bool ToDefault = ToIter.isEnd() &&
1320 (ToExpr || ToValueDecl || HasToInt || ToNullPtr);
1322 bool FromDeclaration = FromValueDecl || FromNullPtr;
1323 bool ToDeclaration = ToValueDecl || ToNullPtr;
1325 if (FromDeclaration && HasToInt) {
1326 Tree.SetFromDeclarationAndToIntegerDiff(
1327 FromValueDecl, NeedFromAddressOf, FromNullPtr, FromExpr, ToInt,
1328 HasToInt, ToIntType, ToExpr, FromDefault, ToDefault);
1329 Tree.SetSame(
false);
1334 if (HasFromInt && ToDeclaration) {
1335 Tree.SetFromIntegerAndToDeclarationDiff(
1336 FromInt, HasFromInt, FromIntType, FromExpr, ToValueDecl,
1337 NeedToAddressOf, ToNullPtr, ToExpr, FromDefault, ToDefault);
1338 Tree.SetSame(
false);
1342 if (HasFromInt || HasToInt) {
1343 Tree.SetIntegerDiff(FromInt, ToInt, HasFromInt, HasToInt, FromIntType,
1344 ToIntType, FromExpr, ToExpr, FromDefault, ToDefault);
1345 if (HasFromInt && HasToInt) {
1352 if (FromDeclaration || ToDeclaration) {
1353 Tree.SetDeclarationDiff(FromValueDecl, ToValueDecl, NeedFromAddressOf,
1354 NeedToAddressOf, FromNullPtr, ToNullPtr, FromExpr,
1355 ToExpr, FromDefault, ToDefault);
1356 bool BothNull = FromNullPtr && ToNullPtr;
1357 bool SameValueDecl =
1358 FromValueDecl && ToValueDecl &&
1359 NeedFromAddressOf == NeedToAddressOf &&
1361 Tree.SetSame(BothNull || SameValueDecl);
1365 assert((FromExpr || ToExpr) &&
"Both template arguments cannot be empty.");
1366 Tree.SetExpressionDiff(FromExpr, ToExpr, FromDefault, ToDefault);
1367 Tree.SetSame(IsEqualExpr(Context, FromExpr, ToExpr));
1379 unsigned TotalArgs = 0;
1380 for (TSTiterator FromIter(Context, FromTST), ToIter(Context, ToTST);
1381 !FromIter.isEnd() || !ToIter.isEnd(); ++TotalArgs) {
1387 unsigned FromParamIndex = std::min(TotalArgs, ParamsFrom->
size() - 1);
1388 unsigned ToParamIndex = std::min(TotalArgs, ParamsTo->
size() - 1);
1393 "Parameter Decl are not the same kind.");
1395 if (isa<TemplateTypeParmDecl>(FromParamND)) {
1396 DiffTypes(FromIter, ToIter);
1397 }
else if (isa<TemplateTemplateParmDecl>(FromParamND)) {
1398 DiffTemplateTemplates(FromIter, ToIter);
1399 }
else if (isa<NonTypeTemplateParmDecl>(FromParamND)) {
1401 cast<NonTypeTemplateParmDecl>(FromParamND);
1403 cast<NonTypeTemplateParmDecl>(ToParamND);
1404 DiffNonTypes(FromIter, ToIter, FromDefaultNonTypeDecl,
1405 ToDefaultNonTypeDecl);
1407 llvm_unreachable(
"Unexpected Decl type.");
1417 static void makeTemplateList(
1421 TemplateList.push_back(TST);
1443 if (hasSameBaseTemplate(FromTST, ToTST))
1450 makeTemplateList(FromTemplateList, FromTST);
1451 makeTemplateList(ToTemplateList, ToTST);
1454 FromIter = FromTemplateList.rbegin(), FromEnd = FromTemplateList.rend(),
1455 ToIter = ToTemplateList.rbegin(), ToEnd = ToTemplateList.rend();
1458 if (!hasSameBaseTemplate(*FromIter, *ToIter))
1464 for (; FromIter != FromEnd && ToIter != ToEnd; ++FromIter, ++ToIter) {
1465 if (!hasSameBaseTemplate(*FromIter, *ToIter))
1469 FromTST = FromIter[-1];
1479 return Iter->getAsType();
1480 if (
Iter.hasDesugaredTA())
1481 return Iter.getDesugaredTA().getAsType();
1489 return Iter->getAsTemplate().getAsTemplateDecl();
1490 if (
Iter.hasDesugaredTA())
1491 return Iter.getDesugaredTA().getAsTemplate().getAsTemplateDecl();
1499 if (FromExpr == ToExpr)
1502 if (!FromExpr || !ToExpr)
1505 llvm::FoldingSetNodeID FromID, ToID;
1506 FromExpr->
Profile(FromID, Context,
true);
1507 ToExpr->
Profile(ToID, Context,
true);
1508 return FromID == ToID;
1516 void TreeToString(
int Indent = 1) {
1519 OS.indent(2 * Indent);
1525 switch (
Tree.GetKind()) {
1526 case DiffTree::Invalid:
1527 llvm_unreachable(
"Template diffing failed with bad DiffNode");
1528 case DiffTree::Type: {
1530 Tree.GetTypeDiff(FromType, ToType);
1531 PrintTypeNames(FromType, ToType,
Tree.FromDefault(),
Tree.ToDefault(),
1535 case DiffTree::Expression: {
1536 Expr *FromExpr, *ToExpr;
1537 Tree.GetExpressionDiff(FromExpr, ToExpr);
1538 PrintExpr(FromExpr, ToExpr,
Tree.FromDefault(),
Tree.ToDefault(),
1542 case DiffTree::TemplateTemplate: {
1544 Tree.GetTemplateTemplateDiff(FromTD, ToTD);
1545 PrintTemplateTemplate(FromTD, ToTD,
Tree.FromDefault(),
1546 Tree.ToDefault(),
Tree.NodeIsSame());
1549 case DiffTree::Integer: {
1550 llvm::APSInt FromInt, ToInt;
1551 Expr *FromExpr, *ToExpr;
1552 bool IsValidFromInt, IsValidToInt;
1554 Tree.GetIntegerDiff(FromInt, ToInt, IsValidFromInt, IsValidToInt,
1555 FromIntType, ToIntType, FromExpr, ToExpr);
1556 PrintAPSInt(FromInt, ToInt, IsValidFromInt, IsValidToInt, FromIntType,
1557 ToIntType, FromExpr, ToExpr,
Tree.FromDefault(),
1558 Tree.ToDefault(),
Tree.NodeIsSame());
1561 case DiffTree::Declaration: {
1563 bool FromAddressOf, ToAddressOf;
1564 bool FromNullPtr, ToNullPtr;
1565 Expr *FromExpr, *ToExpr;
1566 Tree.GetDeclarationDiff(FromValueDecl, ToValueDecl, FromAddressOf,
1567 ToAddressOf, FromNullPtr, ToNullPtr, FromExpr,
1569 PrintValueDecl(FromValueDecl, ToValueDecl, FromAddressOf, ToAddressOf,
1570 FromNullPtr, ToNullPtr, FromExpr, ToExpr,
1571 Tree.FromDefault(),
Tree.ToDefault(),
Tree.NodeIsSame());
1574 case DiffTree::FromDeclarationAndToInteger: {
1583 Tree.GetFromDeclarationAndToIntegerDiff(
1584 FromValueDecl, FromAddressOf, FromNullPtr, FromExpr, ToInt,
1585 IsValidToInt, ToIntType, ToExpr);
1586 assert((FromValueDecl || FromNullPtr) && IsValidToInt);
1587 PrintValueDeclAndInteger(FromValueDecl, FromAddressOf, FromNullPtr,
1588 FromExpr,
Tree.FromDefault(), ToInt, ToIntType,
1589 ToExpr,
Tree.ToDefault());
1592 case DiffTree::FromIntegerAndToDeclaration: {
1593 llvm::APSInt FromInt;
1594 bool IsValidFromInt;
1601 Tree.GetFromIntegerAndToDeclarationDiff(
1602 FromInt, IsValidFromInt, FromIntType, FromExpr, ToValueDecl,
1603 ToAddressOf, ToNullPtr, ToExpr);
1604 assert(IsValidFromInt && (ToValueDecl || ToNullPtr));
1605 PrintIntegerAndValueDecl(FromInt, FromIntType, FromExpr,
1606 Tree.FromDefault(), ToValueDecl, ToAddressOf,
1607 ToNullPtr, ToExpr,
Tree.ToDefault());
1610 case DiffTree::Template: {
1614 Tree.GetTemplateDiff(FromTD, ToTD, FromQual, ToQual);
1616 PrintQualifiers(FromQual, ToQual);
1618 if (!
Tree.HasChildren()) {
1627 unsigned NumElideArgs = 0;
1628 bool AllArgsElided =
true;
1631 if (
Tree.NodeIsSame()) {
1635 AllArgsElided =
false;
1636 if (NumElideArgs > 0) {
1637 PrintElideArgs(NumElideArgs, Indent);
1642 TreeToString(Indent);
1643 if (
Tree.HasNextSibling())
1645 }
while (
Tree.AdvanceSibling());
1646 if (NumElideArgs > 0) {
1650 PrintElideArgs(NumElideArgs, Indent);
1666 assert(!IsBold &&
"Attempting to bold text that is already bold.");
1674 assert(IsBold &&
"Attempting to remove bold from unbold text.");
1686 bool FromDefault,
bool ToDefault,
bool Same) {
1688 "Only one template argument may be missing.");
1700 PrintQualifiers(FromQual, ToQual);
1705 std::string FromTypeStr = FromType.
isNull() ?
"(no argument)"
1707 std::string ToTypeStr = ToType.
isNull() ?
"(no argument)"
1711 if (FromTypeStr == ToTypeStr) {
1712 const auto *FromElTy = dyn_cast<ElaboratedType>(FromType),
1713 *ToElTy = dyn_cast<ElaboratedType>(ToType);
1714 if (FromElTy || ToElTy) {
1715 std::string FromNamedTypeStr =
1716 FromElTy ? FromElTy->getNamedType().getAsString(Policy)
1718 std::string ToNamedTypeStr =
1719 ToElTy ? ToElTy->getNamedType().getAsString(Policy) : ToTypeStr;
1720 if (FromNamedTypeStr != ToNamedTypeStr) {
1721 FromTypeStr = FromNamedTypeStr;
1722 ToTypeStr = ToNamedTypeStr;
1727 std::string FromCanTypeStr =
1730 if (FromCanTypeStr != ToCanTypeStr) {
1731 FromTypeStr = FromCanTypeStr;
1732 ToTypeStr = ToCanTypeStr;
1737 if (PrintTree) OS <<
'[';
1738 OS << (FromDefault ?
"(default) " :
"");
1743 OS <<
" != " << (ToDefault ?
"(default) " :
"");
1753 void PrintExpr(
const Expr *FromExpr,
const Expr *ToExpr,
bool FromDefault,
1754 bool ToDefault,
bool Same) {
1755 assert((FromExpr || ToExpr) &&
1756 "Only one template argument may be missing.");
1758 PrintExpr(FromExpr);
1759 }
else if (!PrintTree) {
1760 OS << (FromDefault ?
"(default) " :
"");
1762 PrintExpr(FromExpr);
1765 OS << (FromDefault ?
"[(default) " :
"[");
1767 PrintExpr(FromExpr);
1769 OS <<
" != " << (ToDefault ?
"(default) " :
"");
1778 void PrintExpr(
const Expr *
E) {
1783 OS <<
"(no argument)";
1789 bool FromDefault,
bool ToDefault,
bool Same) {
1790 assert((FromTD || ToTD) &&
"Only one template argument may be missing.");
1792 std::string FromName =
1793 std::string(FromTD ? FromTD->
getName() :
"(no argument)");
1794 std::string ToName = std::string(ToTD ? ToTD->
getName() :
"(no argument)");
1795 if (FromTD && ToTD && FromName == ToName) {
1802 }
else if (!PrintTree) {
1803 OS << (FromDefault ?
"(default) template " :
"template ");
1808 OS << (FromDefault ?
"[(default) template " :
"[template ");
1812 OS <<
" != " << (ToDefault ?
"(default) template " :
"template ");
1822 void PrintAPSInt(
const llvm::APSInt &FromInt,
const llvm::APSInt &ToInt,
1823 bool IsValidFromInt,
bool IsValidToInt,
QualType FromIntType,
1825 bool FromDefault,
bool ToDefault,
bool Same) {
1826 assert((IsValidFromInt || IsValidToInt) &&
1827 "Only one integral argument may be missing.");
1831 OS << ((FromInt == 0) ?
"false" :
"true");
1838 bool PrintType = IsValidFromInt && IsValidToInt &&
1842 OS << (FromDefault ?
"(default) " :
"");
1843 PrintAPSInt(FromInt, FromExpr, IsValidFromInt, FromIntType, PrintType);
1845 OS << (FromDefault ?
"[(default) " :
"[");
1846 PrintAPSInt(FromInt, FromExpr, IsValidFromInt, FromIntType, PrintType);
1847 OS <<
" != " << (ToDefault ?
"(default) " :
"");
1848 PrintAPSInt(ToInt, ToExpr, IsValidToInt, ToIntType, PrintType);
1855 void PrintAPSInt(
const llvm::APSInt &Val,
Expr *
E,
bool Valid,
1856 QualType IntType,
bool PrintType) {
1859 if (HasExtraInfo(
E)) {
1875 OS << ((Val == 0) ?
"false" :
"true");
1882 OS <<
"(no argument)";
1889 bool HasExtraInfo(
Expr *
E) {
1890 if (!
E)
return false;
1894 if (isa<IntegerLiteral>(
E))
return false;
1897 if (UO->getOpcode() == UO_Minus)
1898 if (isa<IntegerLiteral>(UO->getSubExpr()))
1901 if (isa<CXXBoolLiteralExpr>(
E))
1907 void PrintValueDecl(
ValueDecl *VD,
bool AddressOf,
Expr *
E,
bool NullPtr) {
1911 else if (
auto *TPO = dyn_cast<TemplateParamObjectDecl>(VD)) {
1915 TPO->getType().getUnqualifiedType().print(OS, Policy);
1916 TPO->printAsInit(OS, Policy);
1924 if (
E && !isa<CXXNullPtrLiteralExpr>(
E)) {
1944 OS <<
"(no argument)";
1950 bool FromAddressOf,
bool ToAddressOf,
bool FromNullPtr,
1951 bool ToNullPtr,
Expr *FromExpr,
Expr *ToExpr,
1952 bool FromDefault,
bool ToDefault,
bool Same) {
1953 assert((FromValueDecl || FromNullPtr || ToValueDecl || ToNullPtr) &&
1954 "Only one Decl argument may be NULL");
1957 PrintValueDecl(FromValueDecl, FromAddressOf, FromExpr, FromNullPtr);
1958 }
else if (!PrintTree) {
1959 OS << (FromDefault ?
"(default) " :
"");
1961 PrintValueDecl(FromValueDecl, FromAddressOf, FromExpr, FromNullPtr);
1964 OS << (FromDefault ?
"[(default) " :
"[");
1966 PrintValueDecl(FromValueDecl, FromAddressOf, FromExpr, FromNullPtr);
1968 OS <<
" != " << (ToDefault ?
"(default) " :
"");
1970 PrintValueDecl(ToValueDecl, ToAddressOf, ToExpr, ToNullPtr);
1978 void PrintValueDeclAndInteger(
ValueDecl *VD,
bool NeedAddressOf,
1979 bool IsNullPtr,
Expr *VDExpr,
bool DefaultDecl,
1980 const llvm::APSInt &Val,
QualType IntType,
1981 Expr *IntExpr,
bool DefaultInt) {
1983 OS << (DefaultDecl ?
"(default) " :
"");
1985 PrintValueDecl(VD, NeedAddressOf, VDExpr, IsNullPtr);
1988 OS << (DefaultDecl ?
"[(default) " :
"[");
1990 PrintValueDecl(VD, NeedAddressOf, VDExpr, IsNullPtr);
1992 OS <<
" != " << (DefaultInt ?
"(default) " :
"");
1993 PrintAPSInt(Val, IntExpr,
true , IntType,
false );
2000 void PrintIntegerAndValueDecl(
const llvm::APSInt &Val,
QualType IntType,
2002 bool NeedAddressOf,
bool IsNullPtr,
2003 Expr *VDExpr,
bool DefaultDecl) {
2005 OS << (DefaultInt ?
"(default) " :
"");
2006 PrintAPSInt(Val, IntExpr,
true , IntType,
false );
2008 OS << (DefaultInt ?
"[(default) " :
"[");
2009 PrintAPSInt(Val, IntExpr,
true , IntType,
false );
2010 OS <<
" != " << (DefaultDecl ?
"(default) " :
"");
2012 PrintValueDecl(VD, NeedAddressOf, VDExpr, IsNullPtr);
2019 void PrintElideArgs(
unsigned NumElideArgs,
unsigned Indent) {
2022 for (
unsigned i = 0; i < Indent; ++i)
2025 if (NumElideArgs == 0)
return;
2026 if (NumElideArgs == 1)
2029 OS <<
"[" << NumElideArgs <<
" * ...]";
2039 if (FromQual == ToQual) {
2040 PrintQualifier(FromQual,
false);
2060 if (CommonQual.
empty() && FromQual.
empty()) {
2062 OS <<
"(no qualifiers) ";
2065 PrintQualifier(CommonQual,
false);
2066 PrintQualifier(FromQual,
true);
2071 OS <<
"(no qualifiers)";
2074 PrintQualifier(CommonQual,
false,
2076 PrintQualifier(ToQual,
true,
2081 PrintQualifier(CommonQual,
false);
2082 PrintQualifier(FromQual,
true);
2086 void PrintQualifier(
Qualifiers Q,
bool ApplyBold,
2087 bool AppendSpaceIfNonEmpty =
true) {
2088 if (Q.
empty())
return;
2089 if (ApplyBold)
Bold();
2090 Q.
print(OS, Policy, AppendSpaceIfNonEmpty);
2091 if (ApplyBold) Unbold();
2097 QualType ToType,
bool PrintTree,
bool PrintFromType,
2098 bool ElideType,
bool ShowColor)
2100 Policy(Context.getLangOpts()),
2101 ElideType(ElideType),
2102 PrintTree(PrintTree),
2103 ShowColor(ShowColor),
2105 FromTemplateType(PrintFromType ? FromType : ToType),
2106 ToTemplateType(PrintFromType ? ToType : FromType),
2112 void DiffTemplate() {
2117 GetTemplateSpecializationType(Context, FromTemplateType);
2119 GetTemplateSpecializationType(Context, ToTemplateType);
2122 if (!FromOrigTST || !ToOrigTST)
2126 if (!hasSameTemplate(FromOrigTST, ToOrigTST)) {
2136 FromQual, ToQual,
false ,
2139 DiffTemplate(FromOrigTST, ToOrigTST);
2146 Tree.StartTraverse();
2151 assert(!IsBold &&
"Bold is applied to end of string.");
2162 bool PrintFromType,
bool ElideType,
2165 PrintFromType =
true;
2166 TemplateDiff TD(OS, Context, FromType, ToType, PrintTree, PrintFromType,
Defines the clang::ASTContext interface.
static bool FormatTemplateTypeDiff(ASTContext &Context, QualType FromType, QualType ToType, bool PrintTree, bool PrintFromType, bool ElideType, bool ShowColors, raw_ostream &OS)
FormatTemplateTypeDiff - A helper static function to start the template diff and return the properly ...
static std::string ConvertTypeToDiagnosticString(ASTContext &Context, QualType Ty, ArrayRef< DiagnosticsEngine::ArgumentValue > PrevArgs, ArrayRef< intptr_t > QualTypeVals)
Convert the given type to a string suitable for printing as part of a diagnostic.
This file provides some common utility functions for processing Lambda related AST Constructs.
clang::CharUnits operator*(clang::CharUnits::QuantityType Scale, const clang::CharUnits &CU)
Defines the C++ template declaration subclasses.
Defines the clang::Expr interface and subclasses for C++ expressions.
static std::string toString(const clang::SanitizerSet &Sanitizers)
Produce a string containing comma-separated names of sanitizers in Sanitizers set.
C Language Family Type Representation.
const NamedDecl * FromDecl
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
QualType getRValueReferenceType(QualType T) const
Return the uniqued reference to the type for an rvalue reference to the specified type.
QualType getAttributedType(attr::Kind attrKind, QualType modifiedType, QualType equivalentType) const
QualType getBuiltinVaListType() const
Retrieve the type of the __builtin_va_list type.
QualType getObjCClassType() const
Represents the Objective-C Class type.
QualType getTemplateSpecializationType(TemplateName T, ArrayRef< TemplateArgument > Args, QualType Canon=QualType()) const
QualType getBuiltinMSVaListType() const
Retrieve the type of the __builtin_ms_va_list type.
QualType getVariableArrayType(QualType EltTy, Expr *NumElts, ArraySizeModifier ASM, unsigned IndexTypeQuals, SourceRange Brackets) const
Return a non-unique reference to the type for a variable array of the specified element type.
QualType getFunctionNoProtoType(QualType ResultTy, const FunctionType::ExtInfo &Info) const
Return a K&R style C function type like 'int()'.
bool hasSameType(QualType T1, QualType T2) const
Determine whether the given types T1 and T2 are equivalent.
QualType getPointerType(QualType T) const
Return the uniqued reference to the type for a pointer to the specified type.
QualType getLValueReferenceType(QualType T, bool SpelledAsLValue=true) const
Return the uniqued reference to the type for an lvalue reference to the specified 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.
const LangOptions & getLangOpts() const
QualType getObjCProtoType() const
Retrieve the type of the Objective-C Protocol class.
QualType getObjCSelType() const
Retrieve the type that corresponds to the predefined Objective-C 'SEL' type.
QualType getObjCObjectPointerType(QualType OIT) const
Return a ObjCObjectPointerType type for the given ObjCObjectType.
QualType getObjCObjectType(QualType Base, ObjCProtocolDecl *const *Protocols, unsigned NumProtocols) const
Legacy interface: cannot provide type arguments or __kindof.
const clang::PrintingPolicy & getPrintingPolicy() const
QualType getDependentSizedArrayType(QualType EltTy, Expr *NumElts, ArraySizeModifier ASM, unsigned IndexTypeQuals, SourceRange Brackets) const
Return a non-unique reference to the type for a dependently-sized array of the specified element type...
QualType getObjCIdType() const
Represents the Objective-CC id type.
QualType getFunctionType(QualType ResultTy, ArrayRef< QualType > Args, const FunctionProtoType::ExtProtoInfo &EPI) const
Return a normal function type with a typed argument list.
QualType getIncompleteArrayType(QualType EltTy, ArraySizeModifier ASM, unsigned IndexTypeQuals) const
Return a unique reference to the type for an incomplete array of the specified element type.
Represents a type which was implicitly adjusted by the semantic engine for arbitrary reasons.
Attr - This represents one attribute.
const char * getSpelling() const
An attributed type is a type to which a type attribute has been applied.
static Kind getNullabilityAttrKind(NullabilityKind kind)
Retrieve the attribute kind corresponding to the given nullability kind.
static std::optional< NullabilityKind > stripOuterNullability(QualType &T)
Strip off the top-level nullability annotation on the given type, if it's there.
Represents a C++11 auto or C++14 decltype(auto) type, possibly constrained by a type-constraint.
Represents a class template specialization, which refers to a class template with a given set of temp...
ClassTemplateDecl * getSpecializedTemplate() const
Retrieve the template that this specialization specializes.
const TemplateArgumentList & getTemplateArgs() const
Retrieve the template arguments of the class template specialization.
DeclContext - This is used only as base class of specific decl types that can act as declaration cont...
bool isTranslationUnit() const
virtual Decl * getCanonicalDecl()
Retrieves the "canonical" declaration of the given declaration.
static DeclarationName getFromOpaqueInteger(uintptr_t P)
Get a declaration name from an opaque integer returned by getAsOpaqueInteger.
@ ak_nameddecl
NamedDecl *.
@ ak_declcontext
DeclContext *.
@ ak_addrspace
address space
@ ak_qualtype_pair
pair<QualType, QualType>
@ ak_declarationname
DeclarationName.
@ ak_nestednamespec
NestedNameSpecifier *.
Represents a type that was referred to using an elaborated type keyword, e.g., struct S,...
This represents one expression.
Expr * IgnoreImpCasts() LLVM_READONLY
Skip past any implicit casts which might surround this expression until reaching a fixed point.
Represents a prototype with parameter type info, e.g.
ExtProtoInfo getExtProtoInfo() const
ArrayRef< QualType > param_types() const
FunctionType - C99 6.7.5.3 - Function Declarators.
An lvalue reference type, per C++11 [dcl.ref].
Sugar type that represents a type that was qualified by a qualifier written as a macro invocation.
This represents a decl that may have a name.
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 getQualifiedNameAsString() const
virtual void getNameForDiagnostic(raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const
Appends a human-readable name for this declaration into the given stream.
virtual void printName(raw_ostream &OS, const PrintingPolicy &Policy) const
Pretty-print the unqualified name of this declaration.
Represents a C++ nested name specifier, such as "\::std::vector<int>::".
void print(raw_ostream &OS, const PrintingPolicy &Policy, bool ResolveTemplateArguments=false) const
Print this nested name specifier to the given output stream.
NonTypeTemplateParmDecl - Declares a non-type template parameter, e.g., "Size" in.
Represents a pointer to an Objective C object.
Represents a class type in Objective C.
Sugar for parentheses used when specifying types.
PointerType - C99 6.7.5.1 - Pointer Declarators.
A (possibly-)qualified type.
QualType getLocalUnqualifiedType() const
Return this type with all of the instance-specific qualifiers removed, but without removing any quali...
bool isNull() const
Return true if this QualType doesn't point to a type yet.
static QualType getFromOpaquePtr(const void *Ptr)
Qualifiers getQualifiers() const
Retrieve the set of qualifiers applied to this type.
void print(raw_ostream &OS, const PrintingPolicy &Policy, const Twine &PlaceHolder=Twine(), unsigned Indentation=0) const
QualType getCanonicalType() const
static std::string getAsString(SplitQualType split, const PrintingPolicy &Policy)
Qualifiers getLocalQualifiers() const
Retrieve the set of qualifiers local to this particular QualType instance, not including any qualifie...
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 print(raw_ostream &OS, const PrintingPolicy &Policy, bool appendSpaceIfNonEmpty=false) const
std::string getAsString() const
static Qualifiers fromOpaqueValue(uint64_t opaque)
static std::string getAddrSpaceAsString(LangAS AS)
An rvalue reference type, per C++11 [dcl.ref].
A helper class that allows the use of isa/cast/dyncast to detect TagType objects of structs/unions/cl...
RecordDecl * getDecl() const
void printPretty(raw_ostream &OS, PrinterHelper *Helper, const PrintingPolicy &Policy, unsigned Indentation=0, StringRef NewlineSymbol="\n", const ASTContext *Context=nullptr) const
void Profile(llvm::FoldingSetNodeID &ID, const ASTContext &Context, bool Canonical, bool ProfileLambdaExpr=false) const
Produce a unique representation of the given statement.
Represents the result of substituting a type for a template type parameter.
ArrayRef< TemplateArgument > asArray() const
Produce this as an array ref.
Represents a template argument.
QualType getParamTypeForDecl() const
Expr * getAsExpr() const
Retrieve the template argument as an expression.
pack_iterator pack_end() const
Iterator referencing one past the last argument of a template argument pack.
pack_iterator pack_begin() const
Iterator referencing the first argument of a template argument pack.
llvm::APSInt getAsIntegral() const
Retrieve the template argument as an integral value.
QualType getIntegralType() const
Retrieve the type of the integral value.
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.
The base class of all kinds of template declarations (e.g., class, function, etc.).
TemplateParameterList * getTemplateParameters() const
Get the list of template parameters.
Represents a C++ template name within the type system.
TemplateDecl * getAsTemplateDecl() const
Retrieve the underlying template declaration that this template name refers to, if known.
Stores a list of template parameters for a TemplateDecl and its derived classes.
NamedDecl * getParam(unsigned Idx)
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.
The base class of the type hierarchy.
bool isBooleanType() const
bool isPointerType() const
QualType getPointeeType() const
If this is a pointer, ObjC object pointer, or block pointer, this returns the respective pointee.
TypeClass getTypeClass() const
const T * getAs() const
Member-template getAs<specific type>'.
UnaryOperator - This represents the unary-expression's (except sizeof and alignof),...
Represent the declaration of a variable (in which case it is an lvalue) a function (in which case it ...
Represents a GCC generic vector type.
The JSON file list parser is used to communicate input to InstallAPI.
QualType desugarForDiagnostic(ASTContext &Context, QualType QT, bool &ShouldAKA)
Returns a desugared version of the QualType, and marks ShouldAKA as true whenever we remove significa...
bool isLambdaCallOperator(const CXXMethodDecl *MD)
LangAS
Defines the address space values used by the address space qualifier of QualType.
const char ToggleHighlight
Special character that the diagnostic printer will use to toggle the bold attribute.
void FormatASTNodeDiagnosticArgument(DiagnosticsEngine::ArgumentKind Kind, intptr_t Val, StringRef Modifier, StringRef Argument, ArrayRef< DiagnosticsEngine::ArgumentValue > PrevArgs, SmallVectorImpl< char > &Output, void *Cookie, ArrayRef< intptr_t > QualTypeVals)
DiagnosticsEngine argument formatting function for diagnostics that involve AST nodes.
__INTPTR_TYPE__ intptr_t
A signed integer type with the property that any valid pointer to void can be converted to this type,...
Describes how types, statements, expressions, and declarations should be printed.
unsigned TemplateDiffUsed