16#ifndef DEMANGLE_ITANIUMDEMANGLE_H
17#define DEMANGLE_ITANIUMDEMANGLE_H
35#pragma clang diagnostic push
36#pragma clang diagnostic ignored "-Wunused-template"
42 static_assert(std::is_trivially_copyable<T>::value,
43 "T is required to be a trivially copyable type");
44 static_assert(std::is_trivially_default_constructible<T>::value,
45 "T is required to be trivially default constructible");
46 static_assert(
N > 0,
"PODSmallVector requires a non-zero inline capacity");
52 bool isInline()
const {
return First == Inline; }
60 void reserve(
size_t NewCap) {
63 auto *Tmp =
static_cast<T *
>(std::malloc(NewCap *
sizeof(
T)));
66 std::copy(First, Last, Tmp);
69 First =
static_cast<T *
>(std::realloc(First, NewCap *
sizeof(
T)));
84 if (Other.isInline()) {
85 std::copy(Other.begin(), Other.end(), First);
86 Last = First + Other.size();
98 if (Other.isInline()) {
103 std::copy(Other.begin(), Other.end(), First);
104 Last = First + Other.size();
139 Last = First + Index;
145 bool empty()
const {
return First == Last; }
146 size_t size()
const {
return static_cast<size_t>(Last - First); }
153 return *(
begin() + Index);
170#define NODE(NodeKind) K##NodeKind,
171#include "ItaniumNodes.def"
233 template<
typename Fn>
void visit(Fn
F)
const;
277 bool StrictlyWorse =
false)
const {
290 OB.printRight(*
this);
335 : Elements(Elements_), NumElements(NumElements_) {}
337 bool empty()
const {
return NumElements == 0; }
338 size_t size()
const {
return NumElements; }
341 Node **
end()
const {
return Elements + NumElements; }
346 bool FirstElement =
true;
347 for (
size_t Idx = 0; Idx != NumElements; ++Idx) {
348 size_t BeforeComma = OB.getCurrentPosition();
351 size_t AfterComma = OB.getCurrentPosition();
356 if (AfterComma == OB.getCurrentPosition()) {
357 OB.setCurrentPosition(BeforeComma);
361 FirstElement =
false;
381 const std::string_view Suffix;
385 :
Node(KDotSuffix), Prefix(Prefix_), Suffix(Suffix_) {}
387 template<
typename Fn>
void match(Fn
F)
const {
F(Prefix, Suffix); }
399 std::string_view Ext;
404 :
Node(KVendorExtQualType), Ty(Ty_), Ext(Ext_), TA(TA_) {}
407 std::string_view
getExt()
const {
return Ext; }
410 template <
typename Fn>
void match(Fn
F)
const {
F(Ty, Ext, TA); }
464 return Child->hasRHSComponent(OB);
467 return Child->hasArray(OB);
470 return Child->hasFunction(OB);
474 OB.printLeft(*
Child);
486 :
Node(KConversionOperatorType), Ty(Ty_) {}
488 template<
typename Fn>
void match(Fn
F)
const {
F(Ty); }
498 const std::string_view Postfix;
502 :
Node(KPostfixQualifiedType), Ty(Ty_), Postfix(Postfix_) {}
504 template<
typename Fn>
void match(Fn
F)
const {
F(Ty, Postfix); }
513 const std::string_view Name;
518 template<
typename Fn>
void match(Fn
F)
const {
F(Name); }
520 std::string_view
getName()
const {
return Name; }
532 :
Node(KBitIntType), Size(Size_), Signed(Signed_) {}
534 template <
typename Fn>
void match(Fn
F)
const {
F(Size, Signed); }
541 Size->printAsOperand(OB);
547 std::string_view Kind;
551 :
Node(KElaboratedTypeSpefType), Kind(Kind_), Child(Child_) {}
553 template<
typename Fn>
void match(Fn
F)
const {
F(Kind, Child); }
563 std::string_view Transform;
567 :
Node(KTransformedType), Transform(Transform_), BaseType(BaseType_) {}
569 template<
typename Fn>
void match(Fn
F)
const {
F(Transform, BaseType); }
604 :
Node(KEnableIfAttr), Conditions(Conditions_) {}
606 template<
typename Fn>
void match(Fn
F)
const {
F(Conditions); }
609 OB +=
" [enable_if:";
610 Conditions.printWithComma(OB);
617 std::string_view Protocol;
621 :
Node(KObjCProtoName), Ty(Ty_), Protocol(Protocol_) {}
623 template<
typename Fn>
void match(Fn
F)
const {
F(Ty, Protocol); }
626 return Ty->getKind() == KNameType &&
650 template<
typename Fn>
void match(Fn
F)
const {
F(Pointee); }
653 return Pointee->hasRHSComponent(OB);
658 if (Pointee->getKind() != KObjCProtoName ||
660 OB.printLeft(*Pointee);
661 if (Pointee->hasArray(OB))
663 if (Pointee->hasArray(OB) || Pointee->hasFunction(OB))
667 const auto *objcProto =
static_cast<const ObjCProtoName *
>(Pointee);
669 OB += objcProto->getProtocol();
675 if (Pointee->getKind() != KObjCProtoName ||
677 if (Pointee->hasArray(OB) || Pointee->hasFunction(OB))
679 OB.printRight(*Pointee);
694 mutable bool Printing =
false;
703 std::pair<ReferenceKind, const Node *> collapse(
OutputBuffer &OB)
const {
704 auto SoFar = std::make_pair(RK, Pointee);
709 const Node *SN = SoFar.second->getSyntaxNode(OB);
710 if (SN->
getKind() != KReferenceType)
713 SoFar.second = RT->Pointee;
714 SoFar.first = std::min(SoFar.first, RT->RK);
718 if (Prev.
size() > 1 && SoFar.second == Prev[(Prev.
size() - 1) / 2]) {
720 SoFar.second =
nullptr;
730 Pointee(Pointee_), RK(RK_) {}
732 template<
typename Fn>
void match(Fn
F)
const {
F(Pointee, RK); }
735 return Pointee->hasRHSComponent(OB);
742 std::pair<ReferenceKind, const Node *> Collapsed = collapse(OB);
743 if (!Collapsed.second)
745 OB.printLeft(*Collapsed.second);
746 if (Collapsed.second->hasArray(OB))
748 if (Collapsed.second->hasArray(OB) || Collapsed.second->hasFunction(OB))
757 std::pair<ReferenceKind, const Node *> Collapsed = collapse(OB);
758 if (!Collapsed.second)
760 if (Collapsed.second->hasArray(OB) || Collapsed.second->hasFunction(OB))
762 OB.printRight(*Collapsed.second);
767 const Node *ClassType;
768 const Node *MemberType;
773 ClassType(ClassType_), MemberType(MemberType_) {}
775 template<
typename Fn>
void match(Fn
F)
const {
F(ClassType, MemberType); }
778 return MemberType->hasRHSComponent(OB);
782 OB.printLeft(*MemberType);
783 if (MemberType->hasArray(OB) || MemberType->hasFunction(OB))
787 ClassType->print(OB);
792 if (MemberType->hasArray(OB) || MemberType->hasFunction(OB))
794 OB.printRight(*MemberType);
807 Base(Base_), Dimension(Dimension_) {}
809 template<
typename Fn>
void match(Fn
F)
const {
F(Base, Dimension); }
817 if (OB.back() !=
']')
821 Dimension->print(OB);
823 OB.printRight(*Base);
827 const NodeArray &Elements)
const override {
828 if (Base->getKind() == KNameType &&
830 return Elements.printAsString(OB);
841 const Node *ExceptionSpec;
846 :
Node(KFunctionType,
849 Ret(Ret_), Params(Params_), CVQuals(CVQuals_), RefQual(RefQual_),
850 ExceptionSpec(ExceptionSpec_) {}
852 template<
typename Fn>
void match(Fn
F)
const {
853 F(Ret, Params, CVQuals, RefQual, ExceptionSpec);
873 Params.printWithComma(OB);
889 if (ExceptionSpec !=
nullptr) {
891 ExceptionSpec->print(OB);
901 template<
typename Fn>
void match(Fn
F)
const {
F(E); }
906 E->printAsOperand(OB);
915 :
Node(KDynamicExceptionSpec), Types(Types_) {}
917 template<
typename Fn>
void match(Fn
F)
const {
F(Types); }
922 Types.printWithComma(OB);
939 :
Node(KExplicitObjectParameter), Base(Base_) {
942 "Creating an ExplicitObjectParameter without a valid Base Node.");
945 template <
typename Fn>
void match(Fn
F)
const {
F(Base); }
958 const Node *Requires;
964 const Node *Attrs_,
const Node *Requires_,
966 :
Node(KFunctionEncoding,
969 Ret(Ret_), Name(Name_), Params(Params_), Attrs(Attrs_),
970 Requires(Requires_), CVQuals(CVQuals_), RefQual(RefQual_) {}
972 template<
typename Fn>
void match(Fn
F)
const {
973 F(Ret, Name, Params, Attrs, Requires, CVQuals, RefQual);
991 if (!Ret->hasRHSComponent(OB))
1000 Params.printWithComma(OB);
1004 OB.printRight(*Ret);
1018 if (Attrs !=
nullptr)
1021 if (Requires !=
nullptr) {
1023 Requires->print(OB);
1038 OB +=
"operator\"\" ";
1044 const std::string_view Special;
1049 :
Node(KSpecialName), Special(Special_), Child(Child_) {}
1051 template<
typename Fn>
void match(Fn
F)
const {
F(Special, Child); }
1060 const Node *FirstType;
1061 const Node *SecondType;
1065 :
Node(KCtorVtableSpecialName),
1066 FirstType(FirstType_), SecondType(SecondType_) {}
1068 template<
typename Fn>
void match(Fn
F)
const {
F(FirstType, SecondType); }
1071 OB +=
"construction vtable for ";
1072 FirstType->print(OB);
1074 SecondType->print(OB);
1101 :
Node(KMemberLikeFriendName),
Qual(Qual_),
Name(Name_) {}
1123 template <
typename Fn>
void match(Fn
F)
const {
1172 const Node *Qualifier;
1177 :
Node(KQualifiedName), Qualifier(Qualifier_), Name(Name_) {}
1179 template<
typename Fn>
void match(Fn
F)
const {
F(Qualifier, Name); }
1181 std::string_view
getBaseName()
const override {
return Name->getBaseName(); }
1184 Qualifier->print(OB);
1191 const Node *BaseType;
1192 const Node *Dimension;
1196 :
Node(KVectorType), BaseType(BaseType_), Dimension(Dimension_) {}
1201 template<
typename Fn>
void match(Fn
F)
const {
F(BaseType, Dimension); }
1204 BaseType->print(OB);
1207 Dimension->print(OB);
1213 const Node *Dimension;
1217 :
Node(KPixelVectorType), Dimension(Dimension_) {}
1219 template<
typename Fn>
void match(Fn
F)
const {
F(Dimension); }
1223 OB +=
"pixel vector[";
1224 Dimension->print(OB);
1230 const Node *Dimension;
1234 :
Node(KBinaryFPType), Dimension(Dimension_) {}
1236 template<
typename Fn>
void match(Fn
F)
const {
F(Dimension); }
1240 Dimension->print(OB);
1258 :
Node(KSyntheticTemplateParamName), Kind(Kind_), Index(Index_) {}
1260 template<
typename Fn>
void match(Fn
F)
const {
F(Kind, Index); }
1285 :
Node(KTemplateParamQualifiedArg), Param(Param_), Arg(Arg_) {}
1287 template <
typename Fn>
void match(Fn
F)
const {
F(Param, Arg); }
1303 :
Node(KTypeTemplateParamDecl,
Cache::
Yes), Name(Name_) {}
1305 template<
typename Fn>
void match(Fn
F)
const {
F(Name); }
1320 Constraint(Constraint_), Name(Name_) {}
1322 template<
typename Fn>
void match(Fn
F)
const {
F(Constraint, Name); }
1325 Constraint->print(OB);
1339 :
Node(KNonTypeTemplateParamDecl,
Cache::
Yes), Name(Name_), Type(Type_) {}
1341 template<
typename Fn>
void match(Fn
F)
const {
F(Name, Type); }
1344 OB.printLeft(*Type);
1345 if (!Type->hasRHSComponent(OB))
1351 OB.printRight(*Type);
1364 :
Node(KTemplateTemplateParamDecl,
Cache::
Yes), Name(Name_),
1365 Params(Params_), Requires(Requires_) {}
1367 template <
typename Fn>
void match(Fn
F)
const {
F(Name, Params, Requires); }
1372 Params.printWithComma(OB);
1373 OB +=
"> typename ";
1378 if (Requires !=
nullptr) {
1380 Requires->print(OB);
1391 :
Node(KTemplateParamPackDecl,
Cache::
Yes), Param(Param_) {}
1393 template<
typename Fn>
void match(Fn
F)
const {
F(Param); }
1396 OB.printLeft(*Param);
1417 if (OB.CurrentPackMax == std::numeric_limits<unsigned>::max()) {
1418 OB.CurrentPackMax =
static_cast<unsigned>(Data.size());
1419 OB.CurrentPackIndex = 0;
1426 if (std::all_of(Data.begin(), Data.end(),
1427 [](
Node *
P) { return P->getArrayCache() == Cache::No; }))
1429 if (std::all_of(Data.begin(), Data.end(),
1430 [](
Node *
P) { return P->getFunctionCache() == Cache::No; }))
1432 if (std::all_of(Data.begin(), Data.end(), [](
Node *
P) {
1433 return P->getRHSComponentCache() == Cache::No;
1438 template<
typename Fn>
void match(Fn
F)
const {
F(Data); }
1441 initializePackExpansion(OB);
1442 size_t Idx = OB.CurrentPackIndex;
1443 return Idx < Data.size() && Data[Idx]->hasRHSComponent(OB);
1446 initializePackExpansion(OB);
1447 size_t Idx = OB.CurrentPackIndex;
1448 return Idx < Data.size() && Data[Idx]->hasArray(OB);
1451 initializePackExpansion(OB);
1452 size_t Idx = OB.CurrentPackIndex;
1453 return Idx < Data.size() && Data[Idx]->hasFunction(OB);
1456 initializePackExpansion(OB);
1457 size_t Idx = OB.CurrentPackIndex;
1458 return Idx < Data.size() ? Data[Idx]->getSyntaxNode(OB) :
this;
1462 initializePackExpansion(OB);
1463 size_t Idx = OB.CurrentPackIndex;
1464 if (Idx < Data.size())
1465 OB.printLeft(*Data[Idx]);
1468 initializePackExpansion(OB);
1469 size_t Idx = OB.CurrentPackIndex;
1470 if (Idx < Data.size())
1471 OB.printRight(*Data[Idx]);
1484 :
Node(KTemplateArgumentPack), Elements(Elements_) {}
1486 template<
typename Fn>
void match(Fn
F)
const {
F(Elements); }
1491 Elements.printWithComma(OB);
1502 :
Node(KParameterPackExpansion), Child(Child_) {}
1504 template<
typename Fn>
void match(Fn
F)
const {
F(Child); }
1509 constexpr unsigned Max = std::numeric_limits<unsigned>::max();
1512 size_t StreamPos = OB.getCurrentPosition();
1520 if (OB.CurrentPackMax == Max) {
1527 if (OB.CurrentPackMax == 0) {
1528 OB.setCurrentPosition(StreamPos);
1533 for (
unsigned I = 1,
E = OB.CurrentPackMax;
I <
E; ++
I) {
1535 OB.CurrentPackIndex =
I;
1542 const Node *Pattern;
1547 :
Node(KPackIndexing), Pattern(Pattern_), Index(Index_) {}
1549 template <
typename Fn>
void match(Fn
F)
const {
F(Pattern, Index); }
1557 OB.printLeft(*Index);
1568 :
Node(KTemplateArgs), Params(Params_), Requires(Requires_) {}
1570 template<
typename Fn>
void match(Fn
F)
const {
F(Params, Requires); }
1577 Params.printWithComma(OB);
1619 template<
typename Fn>
void match(Fn
F)
const =
delete;
1625 return Ref->hasRHSComponent(OB);
1631 return Ref->hasArray(OB);
1637 return Ref->hasFunction(OB);
1643 return Ref->getSyntaxNode(OB);
1656 OB.printRight(*
Ref);
1683 :
Node(KGlobalQualifiedName), Child(Child_) {}
1685 template<
typename Fn>
void match(Fn
F)
const {
F(Child); }
1687 std::string_view
getBaseName()
const override {
return Child->getBaseName(); }
1726 return {
"allocator"};
1728 return {
"basic_string"};
1730 return {
"basic_string"};
1732 return {
"basic_istream"};
1734 return {
"basic_ostream"};
1736 return {
"basic_iostream"};
1745 OB <<
"<char, std::char_traits<char>";
1747 OB <<
", std::allocator<char>";
1765 SV.remove_prefix(
sizeof(
"basic_") - 1);
1780 const Node *Basename;
1786 :
Node(KCtorDtorName), Basename(Basename_), IsDtor(IsDtor_),
1787 Variant(Variant_) {}
1789 template<
typename Fn>
void match(Fn
F)
const {
F(Basename, IsDtor, Variant); }
1794 OB += Basename->getBaseName();
1804 template<
typename Fn>
void match(Fn
F)
const {
F(Base); }
1808 OB.printLeft(*Base);
1813 const std::string_view Count;
1817 :
Node(KUnnamedTypeName), Count(Count_) {}
1819 template<
typename Fn>
void match(Fn
F)
const {
F(Count); }
1830 const Node *Requires1;
1832 const Node *Requires2;
1833 std::string_view Count;
1838 std::string_view Count_)
1839 :
Node(KClosureTypeName), TemplateParams(TemplateParams_),
1840 Requires1(Requires1_), Params(Params_), Requires2(Requires2_),
1843 template<
typename Fn>
void match(Fn
F)
const {
1844 F(TemplateParams, Requires1, Params, Requires2, Count);
1848 if (!TemplateParams.empty()) {
1851 TemplateParams.printWithComma(OB);
1854 if (Requires1 !=
nullptr) {
1856 Requires1->print(OB);
1860 Params.printWithComma(OB);
1862 if (Requires2 !=
nullptr) {
1864 Requires2->print(OB);
1881 :
Node(KStructuredBindingName), Bindings(Bindings_) {}
1883 template<
typename Fn>
void match(Fn
F)
const {
F(Bindings); }
1887 Bindings.printWithComma(OB);
1896 const std::string_view InfixOperator;
1902 :
Node(KBinaryExpr, Prec_), LHS(LHS_), InfixOperator(InfixOperator_),
1905 template <
typename Fn>
void match(Fn
F)
const {
1912 bool ParenAll = !OB.isInParensInTemplateArgs() &&
1913 (InfixOperator ==
">" || InfixOperator ==
">>");
1920 if (!(InfixOperator ==
","))
1922 OB += InfixOperator;
1936 :
Node(KArraySubscriptExpr, Prec_), Op1(Op1_), Op2(Op2_) {}
1938 template <
typename Fn>
void match(Fn
F)
const {
1945 Op2->printAsOperand(OB);
1952 const std::string_view Operator;
1956 :
Node(KPostfixExpr, Prec_), Child(Child_), Operator(Operator_) {}
1958 template <
typename Fn>
void match(Fn
F)
const {
1976 :
Node(KConditionalExpr, Prec_), Cond(Cond_), Then(Then_), Else(Else_) {}
1978 template <
typename Fn>
void match(Fn
F)
const {
1985 Then->printAsOperand(OB);
1993 const std::string_view Kind;
1999 :
Node(KMemberExpr, Prec_), LHS(LHS_), Kind(Kind_), RHS(RHS_) {}
2001 template <
typename Fn>
void match(Fn
F)
const {
2014 const Node *SubExpr;
2015 std::string_view Offset;
2021 std::string_view Offset_,
NodeArray UnionSelectors_,
2022 bool OnePastTheEnd_)
2023 :
Node(KSubobjectExpr), Type(Type_), SubExpr(SubExpr_), Offset(Offset_),
2024 UnionSelectors(UnionSelectors_), OnePastTheEnd(OnePastTheEnd_) {}
2026 template<
typename Fn>
void match(Fn
F)
const {
2027 F(Type, SubExpr, Offset, UnionSelectors, OnePastTheEnd);
2034 OB +=
" at offset ";
2035 if (Offset.empty()) {
2037 }
else if (Offset[0] ==
'n') {
2039 OB += std::string_view(Offset.data() + 1, Offset.size() - 1);
2048 const std::string_view Prefix;
2050 const std::string_view Postfix;
2055 :
Node(KEnclosingExpr, Prec_), Prefix(Prefix_), Infix(Infix_) {}
2057 template <
typename Fn>
void match(Fn
F)
const {
2072 const std::string_view CastKind;
2079 :
Node(KCastExpr, Prec_), CastKind(CastKind_), To(To_), From(From_) {}
2081 template <
typename Fn>
void match(Fn
F)
const {
2094 From->printAsOperand(OB);
2104 :
Node(KSizeofParamPackExpr), Pack(Pack_) {}
2106 template<
typename Fn>
void match(Fn
F)
const {
F(Pack); }
2124 :
Node(KCallExpr, Prec_), Callee(Callee_), Args(Args_),
2125 IsParen(IsParen_) {}
2127 template <
typename Fn>
void match(Fn
F)
const {
2138 Args.printWithComma(OB);
2152 bool IsArray_,
Prec Prec_)
2153 :
Node(KNewExpr, Prec_), ExprList(ExprList_), Type(Type_),
2154 InitList(InitList_), IsGlobal(IsGlobal_), IsArray(IsArray_) {}
2156 template<
typename Fn>
void match(Fn
F)
const {
2166 if (!ExprList.empty()) {
2168 ExprList.printWithComma(OB);
2173 if (!InitList.empty()) {
2175 InitList.printWithComma(OB);
2188 :
Node(KDeleteExpr, Prec_), Op(Op_), IsGlobal(IsGlobal_),
2189 IsArray(IsArray_) {}
2191 template <
typename Fn>
void match(Fn
F)
const {
2207 std::string_view Prefix;
2212 :
Node(KPrefixExpr, Prec_), Prefix(Prefix_), Child(Child_) {}
2214 template <
typename Fn>
void match(Fn
F)
const {
2225 std::string_view Number;
2229 :
Node(KFunctionParam), Number(Number_) {}
2231 template<
typename Fn>
void match(Fn
F)
const {
F(Number); }
2245 :
Node(KConversionExpr, Prec_), Type(Type_), Expressions(Expressions_) {}
2247 template <
typename Fn>
void match(Fn
F)
const {
2256 Expressions.printWithComma(OB);
2263 const Node *SubExpr;
2264 std::string_view Offset;
2268 std::string_view Offset_,
Prec Prec_)
2269 :
Node(KPointerToMemberConversionExpr, Prec_), Type(Type_),
2270 SubExpr(SubExpr_), Offset(Offset_) {}
2272 template <
typename Fn>
void match(Fn
F)
const {
2291 :
Node(KInitListExpr), Ty(Ty_), Inits(Inits_) {}
2293 template<
typename Fn>
void match(Fn
F)
const {
F(Ty, Inits); }
2297 if (Ty->printInitListAsType(OB, Inits))
2302 Inits.printWithComma(OB);
2313 :
Node(KBracedExpr), Elem(Elem_), Init(Init_), IsArray(IsArray_) {}
2315 template<
typename Fn>
void match(Fn
F)
const {
F(Elem, Init, IsArray); }
2326 if (Init->getKind() != KBracedExpr && Init->getKind() != KBracedRangeExpr)
2338 :
Node(KBracedRangeExpr), First(First_), Last(Last_), Init(Init_) {}
2340 template<
typename Fn>
void match(Fn
F)
const {
F(First, Last, Init); }
2348 if (Init->getKind() != KBracedExpr && Init->getKind() != KBracedRangeExpr)
2355 const Node *Pack, *Init;
2356 std::string_view OperatorName;
2360 FoldExpr(
bool IsLeftFold_, std::string_view OperatorName_,
const Node *Pack_,
2362 :
Node(KFoldExpr), Pack(Pack_), Init(Init_), OperatorName(OperatorName_),
2363 IsLeftFold(IsLeftFold_) {}
2365 template<
typename Fn>
void match(Fn
F)
const {
2366 F(IsLeftFold, OperatorName, Pack, Init);
2370 auto PrintPack = [&] {
2380 if (!IsLeftFold || Init !=
nullptr) {
2386 OB <<
" " << OperatorName <<
" ";
2389 if (IsLeftFold || Init !=
nullptr) {
2391 OB <<
" " << OperatorName <<
" ";
2407 template<
typename Fn>
void match(Fn
F)
const {
F(Op); }
2421 template<
typename Fn>
void match(Fn
F)
const {
F(Value); }
2424 OB += Value ? std::string_view(
"true") : std::string_view(
"false");
2434 template<
typename Fn>
void match(Fn
F)
const {
F(Type); }
2449 template<
typename Fn>
void match(Fn
F)
const {
F(Type); }
2453 if (Type->getKind() == KClosureTypeName)
2462 std::string_view Integer;
2466 :
Node(KEnumLiteral), Ty(Ty_), Integer(Integer_) {}
2468 template<
typename Fn>
void match(Fn
F)
const {
F(Ty, Integer); }
2475 if (Integer[0] ==
'n')
2476 OB <<
'-' << std::string_view(Integer.data() + 1, Integer.size() - 1);
2483 std::string_view Type;
2484 std::string_view Value;
2488 :
Node(KIntegerLiteral), Type(Type_), Value(Value_) {}
2490 template<
typename Fn>
void match(Fn
F)
const {
F(Type, Value); }
2493 if (Type.size() > 3) {
2499 if (Value[0] ==
'n')
2500 OB <<
'-' << std::string_view(Value.data() + 1, Value.size() - 1);
2504 if (Type.size() <= 3)
2508 std::string_view
value()
const {
return Value; }
2516 :
Node(KRequiresExpr), Parameters(Parameters_),
2517 Requirements(Requirements_) {}
2519 template<
typename Fn>
void match(Fn
F)
const {
F(Parameters, Requirements); }
2523 if (!Parameters.empty()) {
2526 Parameters.printWithComma(OB);
2531 for (
const Node *Req : Requirements) {
2542 const Node *TypeConstraint;
2545 const Node *TypeConstraint_)
2546 :
Node(KExprRequirement), Expr(Expr_), IsNoexcept(IsNoexcept_),
2547 TypeConstraint(TypeConstraint_) {}
2549 template <
typename Fn>
void match(Fn
F)
const {
2550 F(Expr, IsNoexcept, TypeConstraint);
2555 if (IsNoexcept || TypeConstraint)
2558 if (IsNoexcept || TypeConstraint)
2562 if (TypeConstraint) {
2564 TypeConstraint->print(OB);
2574 :
Node(KTypeRequirement), Type(Type_) {}
2576 template <
typename Fn>
void match(Fn
F)
const {
F(Type); }
2586 const Node *Constraint;
2589 :
Node(KNestedRequirement), Constraint(Constraint_) {}
2591 template <
typename Fn>
void match(Fn
F)
const {
F(Constraint); }
2595 Constraint->print(OB);
2604 return Node::KFloatLiteral;
2607 return Node::KDoubleLiteral;
2610 return Node::KLongDoubleLiteral;
2615 const std::string_view Contents;
2617 static constexpr Kind KindForClass =
2622 :
Node(KindForClass), Contents(Contents_) {}
2624 template<
typename Fn>
void match(Fn
F)
const {
F(Contents); }
2628 if (Contents.size() >=
N) {
2631 char buf[
sizeof(Float)];
2633 const char *t = Contents.data();
2634 const char *last = t +
N;
2636 for (; t != last; ++t, ++e) {
2637 unsigned d1 = isdigit(*t) ?
static_cast<unsigned>(*t -
'0')
2638 :
static_cast<unsigned>(*t -
'a' + 10);
2640 unsigned d0 = isdigit(*t) ?
static_cast<unsigned>(*t -
'0')
2641 :
static_cast<unsigned>(*t -
'a' + 10);
2642 *e =
static_cast<char>((d1 << 4) + d0);
2644#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__
2645 std::reverse(buf, e);
2649 OB += std::string_view(num, n);
2660template<
typename Fn>
2665 return F(static_cast<const X *>(this));
2666#include "ItaniumNodes.def"
2674 template <> struct NodeKind<X> { \
2675 static constexpr Node::Kind Kind = Node::K##X; \
2676 static constexpr const char *name() { return #X; } \
2678#include "ItaniumNodes.def"
2681 auto StartPos = OB.getCurrentPosition();
2682 auto Fail = [&OB, StartPos] {
2683 OB.setCurrentPosition(StartPos);
2688 bool LastWasNumericEscape =
false;
2689 for (
const Node *Element : *
this) {
2690 if (Element->
getKind() != Node::KIntegerLiteral)
2692 int integer_value = 0;
2693 for (
char c :
static_cast<const IntegerLiteral *
>(Element)->value()) {
2694 if (c <
'0' || c >
'9' || integer_value > 25)
2696 integer_value *= 10;
2697 integer_value += c -
'0';
2699 if (integer_value > 255)
2703 if (LastWasNumericEscape) {
2704 if ((integer_value >=
'0' && integer_value <=
'9') ||
2705 (integer_value >=
'a' && integer_value <=
'f') ||
2706 (integer_value >=
'A' && integer_value <=
'F')) {
2711 LastWasNumericEscape =
false;
2714 switch (integer_value) {
2747 if (integer_value < 32 || integer_value == 127) {
2748 constexpr char Hex[] =
"0123456789ABCDEF";
2750 if (integer_value > 7)
2752 if (integer_value >= 16)
2753 OB += Hex[integer_value >> 4];
2754 OB += Hex[integer_value & 0xF];
2755 LastWasNumericEscape =
true;
2760 OB += (
char)integer_value;
2788 size_t OldNumTemplateParamLists;
2793 : Parser(TheParser),
2795 Parser->TemplateParams.push_back(&Params);
2798 DEMANGLE_ASSERT(Parser->TemplateParams.size() >= OldNumTemplateParamLists,
2800 Parser->TemplateParams.shrinkToSize(OldNumTemplateParamLists);
2824 OldParams = std::move(Parser->TemplateParams);
2825 OldOuterParams = std::move(Parser->OuterTemplateParams);
2826 Parser->TemplateParams.clear();
2827 Parser->OuterTemplateParams.clear();
2830 Parser->TemplateParams = std::move(OldParams);
2831 Parser->OuterTemplateParams = std::move(OldOuterParams);
2853 void reset(
const char *First_,
const char *Last_) {
2863 NumSyntheticTemplateParameter = 0;
2872 size_t sz =
static_cast<size_t>(end - begin);
2875 std::copy(begin, end,
data);
2883 Names.shrinkToSize(FromPosition);
2905 char look(
unsigned Lookahead = 0)
const {
2906 if (
static_cast<size_t>(
Last -
First) <= Lookahead)
2908 return First[Lookahead];
2926 return look() ==
'T' &&
2927 std::string_view(
"yptnk").find(
look(1)) != std::string_view::npos;
2975 size_t I = State.ForwardTemplateRefsBegin;
2977 for (;
I <
E; ++
I) {
3034 return *
this < Other.Enc;
3037 return Enc[0] < Peek[0] || (
Enc[0] == Peek[0] &&
Enc[1] < Peek[1]);
3040 return Enc[0] == Peek[0] &&
Enc[1] == Peek[1];
3046 std::string_view Res =
Name;
3049 "operator name does not start with 'operator'");
3050 Res.remove_prefix(
sizeof(
"operator") - 1);
3052 Res.remove_prefix(1);
3086template <
typename Derived,
typename Alloc>
3093 Node *Result =
nullptr;
3094 bool IsSubst =
false;
3096 Result =
getDerived().parseUnscopedName(State, &IsSubst);
3100 if (
look() ==
'I') {
3104 Subs.push_back(Result);
3109 State->EndsWithTemplateArgs =
true;
3111 }
else if (IsSubst) {
3122template <
typename Derived,
typename Alloc>
3127 if (Encoding ==
nullptr || !
consumeIf(
'E'))
3153 if (Entity ==
nullptr)
3162template <
typename Derived,
typename Alloc>
3167 Node *Std =
nullptr;
3174 Node *Res =
nullptr;
3176 if (
look() ==
'S') {
3180 if (S->
getKind() == Node::KModuleName)
3182 else if (IsSubst && Std ==
nullptr) {
3190 if (Res ==
nullptr || Std !=
nullptr) {
3203template <
typename Derived,
typename Alloc>
3209 bool IsMemberLikeFriend = Scope &&
consumeIf(
'F');
3214 if (
look() >=
'1' &&
look() <=
'9') {
3215 Result =
getDerived().parseSourceName(State);
3216 }
else if (
look() ==
'U') {
3217 Result =
getDerived().parseUnnamedTypeName(State);
3220 size_t BindingsBegin =
Names.size();
3228 }
else if (
look() ==
'C' ||
look() ==
'D') {
3230 if (Scope ==
nullptr ||
Module !=
nullptr)
3232 Result =
getDerived().parseCtorDtorName(Scope, State);
3234 Result =
getDerived().parseOperatorName(State);
3237 if (Result !=
nullptr &&
Module !=
nullptr)
3239 if (Result !=
nullptr)
3241 if (Result !=
nullptr && IsMemberLikeFriend)
3243 else if (Result !=
nullptr && Scope !=
nullptr)
3254template <
typename Derived,
typename Alloc>
3277template <
typename Derived,
typename Alloc>
3282 if (State !=
nullptr)
3296 size_t ParamsBegin =
Names.size();
3328 if (TempParams.
empty())
3331 Node *Requires1 =
nullptr;
3333 Requires1 =
getDerived().parseConstraintExpr();
3334 if (Requires1 ==
nullptr)
3344 }
while (
look() !=
'E' &&
look() !=
'Q');
3348 Node *Requires2 =
nullptr;
3350 Requires2 =
getDerived().parseConstraintExpr();
3351 if (Requires2 ==
nullptr)
3374template <
typename Derived,
typename Alloc>
3379 if (
numLeft() < Length || Length == 0)
3381 std::string_view Name(
First, Length);
3389template <
typename Derived,
typename Alloc>
3401 "operator co_await"},
3413 "operator delete[]"},
3461 "reinterpret_cast"},
3473template <
typename Derived,
typename Alloc>
3479template <
typename Derived,
typename Alloc>
3487 size_t lower = 0u, upper =
NumOps - 1;
3488 while (upper != lower) {
3489 size_t middle = (upper + lower) / 2;
3505template <
typename Derived,
typename Alloc>
3521 if (State) State->CtorDtorConversion =
true;
3545 if (
look() >=
'0' &&
look() <=
'9') {
3568template <
typename Derived,
typename Alloc>
3572 if (SoFar->
getKind() == Node::KSpecialSubstitution) {
3585 int Variant =
look() -
'0';
3587 if (State) State->CtorDtorConversion =
true;
3595 if (
look() ==
'D' && (
look(1) ==
'0' ||
look(1) ==
'1' ||
look(1) ==
'2' ||
3596 look(1) ==
'4' ||
look(1) ==
'5')) {
3597 int Variant =
look(1) -
'0';
3599 if (State) State->CtorDtorConversion =
true;
3625template <
typename Derived,
typename Alloc>
3636 State->CVQualifiers = CVTmp;
3649 State->HasExplicitObjectParameter =
true;
3652 Node *SoFar =
nullptr;
3656 State->EndsWithTemplateArgs =
false;
3658 if (
look() ==
'T') {
3660 if (SoFar !=
nullptr)
3663 }
else if (
look() ==
'I') {
3665 if (SoFar ==
nullptr)
3670 if (SoFar->
getKind() == Node::KNameWithTemplateArgs)
3676 State->EndsWithTemplateArgs =
true;
3678 }
else if (
look() ==
'D' && (
look(1) ==
't' ||
look(1) ==
'T')) {
3680 if (SoFar !=
nullptr)
3686 if (
look() ==
'S') {
3689 if (
look(1) ==
't') {
3697 if (S->
getKind() == Node::KModuleName) {
3699 }
else if (SoFar !=
nullptr) {
3711 if (SoFar ==
nullptr)
3713 Subs.push_back(SoFar);
3720 if (SoFar ==
nullptr ||
Subs.empty())
3728template <
typename Derived,
typename Alloc>
3733 if (
look() ==
'I') {
3744template <
typename Derived,
typename Alloc>
3747 if (std::isdigit(
look()))
3751 if (Result ==
nullptr)
3759template <
typename Derived,
typename Alloc>
3761 if (
look() ==
'T') {
3768 if (
look() ==
'D') {
3785template <
typename Derived,
typename Alloc>
3787 if (std::isdigit(
look()))
3796 if (Oper ==
nullptr)
3798 if (
look() ==
'I') {
3819template <
typename Derived,
typename Alloc>
3821 Node *SoFar =
nullptr;
3827 if (SoFar ==
nullptr)
3830 if (
look() ==
'I') {
3841 if (Qual ==
nullptr)
3849 if (Base ==
nullptr)
3856 SoFar =
getDerived().parseBaseUnresolvedName();
3857 if (SoFar ==
nullptr)
3865 if (std::isdigit(
look())) {
3868 if (Qual ==
nullptr)
3884 if (SoFar ==
nullptr)
3887 if (
look() ==
'I') {
3900 if (Base ==
nullptr)
3907template <
typename Derived,
typename Alloc>
3921template <
typename Alloc,
typename Derived>
3924 const char *Tmp =
First;
3928 return std::string_view();
3931 return std::string_view(Tmp,
First - Tmp);
3935template <
typename Alloc,
typename Derived>
3940 while (
look() >=
'0' &&
look() <=
'9') {
3942 *Out +=
static_cast<size_t>(
consume() -
'0');
3947template <
typename Alloc,
typename Derived>
3965template <
typename Derived,
typename Alloc>
3969 Node *ExceptionSpec =
nullptr;
3982 size_t SpecsBegin =
Names.size();
4001 if (ReturnType ==
nullptr)
4005 size_t ParamsBegin =
Names.size();
4027 ReferenceQualifier, ExceptionSpec);
4035template <
typename Derived,
typename Alloc>
4039 if (
look() >=
'1' &&
look() <=
'9') {
4041 if (!DimensionNumber)
4048 if (ElemType ==
nullptr)
4072template <
typename Derived,
typename Alloc>
4088template <
typename Derived,
typename Alloc>
4093 Node *Dimension =
nullptr;
4095 if (std::isdigit(
look())) {
4103 if (DimExpr ==
nullptr)
4107 Dimension = DimExpr;
4117template <
typename Derived,
typename Alloc>
4122 if (ClassType ==
nullptr)
4125 if (MemberType ==
nullptr)
4134template <
typename Derived,
typename Alloc>
4136 std::string_view ElabSpef;
4138 ElabSpef =
"struct";
4145 if (Name ==
nullptr)
4148 if (!ElabSpef.empty())
4157template <
typename Derived,
typename Alloc>
4166 constexpr size_t Len =
sizeof(
"objcproto") - 1;
4167 std::string_view ProtoSourceName(Qual.data() + Len, Qual.size() - Len);
4168 std::string_view Proto;
4171 SaveLast(
Last, &*ProtoSourceName.rbegin() + 1);
4177 if (Child ==
nullptr)
4183 if (
look() ==
'I') {
4190 if (Child ==
nullptr)
4224template <
typename Derived,
typename Alloc>
4226 Node *Result =
nullptr;
4233 unsigned AfterQuals = 0;
4234 if (
look(AfterQuals) ==
'r') ++AfterQuals;
4235 if (
look(AfterQuals) ==
'V') ++AfterQuals;
4236 if (
look(AfterQuals) ==
'K') ++AfterQuals;
4238 if (
look(AfterQuals) ==
'F' ||
4239 (
look(AfterQuals) ==
'D' &&
4240 (
look(AfterQuals + 1) ==
'o' ||
look(AfterQuals + 1) ==
'O' ||
4241 look(AfterQuals + 1) ==
'w' ||
look(AfterQuals + 1) ==
'x'))) {
4381 if (!DimensionNumber)
4440 if (
look(1) ==
'A') {
4460 if (
look(1) ==
'R') {
4524 std::string_view Kind =
look(1) ==
'k' ?
" auto" :
" decltype(auto)";
4590 Result =
getDerived().parsePointerToMemberType();
4596 if (
look(1) ==
's' ||
look(1) ==
'u' ||
look(1) ==
'e') {
4602 if (Result ==
nullptr)
4616 Subs.push_back(Result);
4671 if (
look(1) !=
't') {
4672 bool IsSubst =
false;
4673 Result =
getDerived().parseUnscopedName(
nullptr, &IsSubst);
4689 Subs.push_back(Result);
4694 }
else if (IsSubst) {
4713 if (Result !=
nullptr)
4714 Subs.push_back(Result);
4718template <
typename Derived,
typename Alloc>
4728template <
typename Derived,
typename Alloc>
4741template <
typename Derived,
typename Alloc>
4743 std::string_view Lit) {
4751template <
typename Alloc,
typename Derived>
4768template <
typename Derived,
typename Alloc>
4795template <
typename Derived,
typename Alloc>
4809 size_t ExprsBegin =
Names.size();
4821 if (
E[0] ==
nullptr)
4833template <
typename Derived,
typename Alloc>
4840 return getDerived().parseIntegerLiteral(
"wchar_t");
4849 return getDerived().parseIntegerLiteral(
"char");
4852 return getDerived().parseIntegerLiteral(
"signed char");
4855 return getDerived().parseIntegerLiteral(
"unsigned char");
4858 return getDerived().parseIntegerLiteral(
"short");
4861 return getDerived().parseIntegerLiteral(
"unsigned short");
4867 return getDerived().parseIntegerLiteral(
"u");
4870 return getDerived().parseIntegerLiteral(
"l");
4873 return getDerived().parseIntegerLiteral(
"ul");
4876 return getDerived().parseIntegerLiteral(
"ll");
4879 return getDerived().parseIntegerLiteral(
"ull");
4882 return getDerived().parseIntegerLiteral(
"__int128");
4885 return getDerived().parseIntegerLiteral(
"unsigned __int128");
4894#if defined(__powerpc__) || defined(__s390__)
4953template <
typename Derived,
typename Alloc>
4955 if (
look() ==
'd') {
4960 if (
Field ==
nullptr)
4963 if (Init ==
nullptr)
4970 if (Index ==
nullptr)
4973 if (Init ==
nullptr)
4980 if (RangeBegin ==
nullptr)
4983 if (RangeEnd ==
nullptr)
4986 if (Init ==
nullptr)
5000template <
typename Derived,
typename Alloc>
5005 bool IsLeftFold =
false, HasInitializer =
false;
5011 HasInitializer =
true;
5014 HasInitializer =
true;
5029 && Op->getName().back() ==
'*')))
5033 if (Pack ==
nullptr)
5036 Node *Init =
nullptr;
5037 if (HasInitializer) {
5039 if (Init ==
nullptr)
5043 if (IsLeftFold && Init)
5052template <
typename Derived,
typename Alloc>
5062 std::string_view Offset =
getDerived().parseNumber(
true);
5072template <
typename Derived,
typename Alloc>
5080 std::string_view Offset =
getDerived().parseNumber(
true);
5081 size_t SelectorsBegin =
Names.size();
5086 Names.push_back(Selector);
5095template <
typename Derived,
typename Alloc>
5104template <
typename Derived,
typename Alloc>
5109 size_t ParamsBegin =
Names.size();
5112 if (
Type ==
nullptr)
5122 size_t ReqsBegin =
Names.size();
5124 Node *Constraint =
nullptr;
5128 if (Expr ==
nullptr)
5131 Node *TypeReq =
nullptr;
5134 if (TypeReq ==
nullptr)
5141 if (
Type ==
nullptr)
5153 if (NestedReq ==
nullptr)
5157 if (Constraint ==
nullptr)
5159 Names.push_back(Constraint);
5210template <
typename Derived,
typename Alloc>
5216 auto Sym = Op->getSymbol();
5217 switch (Op->getKind()) {
5220 return getDerived().parseBinaryExpr(Sym, Op->getPrecedence());
5223 return getDerived().parsePrefixExpr(Sym, Op->getPrecedence());
5227 return getDerived().parsePrefixExpr(Sym, Op->getPrecedence());
5236 if (Base ==
nullptr)
5239 if (Index ==
nullptr)
5259 size_t Exprs =
Names.size();
5264 Names.push_back(Ex);
5271 size_t InitsBegin =
Names.size();
5276 if (Init ==
nullptr)
5278 Names.push_back(Init);
5282 Op->getFlag(), Op->getPrecedence());
5290 Op->getPrecedence());
5295 if (Callee ==
nullptr)
5297 size_t ExprsBegin =
Names.size();
5305 Op->getFlag(), Op->getPrecedence());
5317 size_t ExprsBegin =
Names.size();
5328 if (!IsMany && Exprs.
size() != 1)
5335 if (
Cond ==
nullptr)
5378 if (
look() ==
'f') {
5380 if (
look(1) ==
'p' || (
look(1) ==
'L' && std::isdigit(
look(2))))
5385 size_t InitsBegin =
Names.size();
5402 if (
look() ==
'r' && (
look(1) ==
'q' ||
look(1) ==
'Q'))
5408 if (Child ==
nullptr)
5415 if (Pattern ==
nullptr)
5418 if (Index ==
nullptr)
5423 if (
look() ==
'T') {
5435 size_t ArgsBegin =
Names.size();
5440 Names.push_back(Arg);
5451 size_t InitsBegin =
Names.size();
5477 bool IsUUID =
false;
5479 if (Name->getBaseName() ==
"__uuidof") {
5488 size_t ExprsBegin =
Names.size();
5490 if (
UUID ==
nullptr)
5506 return getDerived().parseUnresolvedName(Global);
5517template <
typename Alloc,
typename Derived>
5550template <
typename Derived,
typename Alloc>
5603 if (Encoding ==
nullptr)
5612 if (FirstType ==
nullptr)
5617 if (SecondType ==
nullptr)
5625 if (Name ==
nullptr)
5633 if (Name ==
nullptr)
5640 bool IsVirt =
look() ==
'v';
5644 if (BaseEncoding ==
nullptr)
5658 if (Name ==
nullptr)
5668 if (Name ==
nullptr)
5695template <
typename Derived,
typename Alloc>
5701 if (
look() ==
'G' ||
look() ==
'T')
5704 auto IsEndOfEncoding = [&] {
5713 if (Name ==
nullptr)
5719 if (IsEndOfEncoding())
5732 Node *Attrs =
nullptr;
5734 size_t BeforeArgs =
Names.size();
5739 Names.push_back(Arg);
5746 Node *ReturnType =
nullptr;
5749 if (ReturnType ==
nullptr)
5755 size_t ParamsBegin =
Names.size();
5761 const bool IsFirstParam = ParamsBegin ==
Names.size();
5768 Names.push_back(Ty);
5769 }
while (!IsEndOfEncoding() &&
look() !=
'Q');
5773 Node *Requires =
nullptr;
5775 Requires =
getDerived().parseConstraintExpr();
5785template <
class Float>
5793 static constexpr const char*
spec =
"%af";
5801 static constexpr const char*
spec =
"%a";
5807#if __LDBL_MANT_DIG__ == 113 || __LDBL_MANT_DIG__ == 106
5808 static const size_t mangled_size = 32;
5809#elif __LDBL_MANT_DIG__ == 53 || defined(_MSC_VER)
5812 static const size_t mangled_size = 16;
5813#elif __LDBL_MANT_DIG__ == 64
5814 static const size_t mangled_size = 20;
5816#error Unknown size for __LDBL_MANT_DIG__
5824 static constexpr const char *
spec =
"%LaL";
5827template <
typename Alloc,
typename Derived>
5828template <
class Float>
5833 std::string_view Data(
First,
N);
5835 if (!(
C >=
'0' &&
C <=
'9') && !(
C >=
'a' &&
C <=
'f'))
5844template <
typename Alloc,
typename Derived>
5846 if (!(
look() >=
'0' &&
look() <=
'9') &&
5852 if (
look() >=
'0' &&
look() <=
'9') {
5854 Id +=
static_cast<size_t>(
look() -
'0');
5855 }
else if (
look() >=
'A' &&
look() <=
'Z') {
5857 Id +=
static_cast<size_t>(
look() -
'A') + 10;
5877template <
typename Derived,
typename Alloc>
5882 if (
look() >=
'a' &&
look() <=
'z') {
5915 if (WithTags != SpecialSub) {
5916 Subs.push_back(WithTags);
5917 SpecialSub = WithTags;
5943template <
typename Derived,
typename Alloc>
5945 const char *Begin =
First;
6013template <
typename Derived,
typename Alloc>
6061 size_t ParamsBegin =
Names.size();
6063 Node *Requires =
nullptr;
6070 Requires =
getDerived().parseConstraintExpr();
6071 if (Requires ==
nullptr || !
consumeIf(
'E'))
6096template <
typename Derived,
typename Alloc>
6108 size_t ArgsBegin =
Names.size();
6113 Names.push_back(Arg);
6120 if (
look(1) ==
'Z') {
6149template <
typename Derived,
typename Alloc>
6163 size_t ArgsBegin =
Names.size();
6164 Node *Requires =
nullptr;
6170 Names.push_back(Arg);
6172 if (Arg->
getKind() == Node::KTemplateParamQualifiedArg) {
6176 if (Arg->
getKind() == Node::KTemplateArgumentPack) {
6187 Names.push_back(Arg);
6190 Requires =
getDerived().parseConstraintExpr();
6206template <
typename Derived,
typename Alloc>
6208 bool AllocToken =
consumeIf(
"__alloc_token_");
6217 if (Encoding ==
nullptr)
6219 if (
look() ==
'.') {
6233 if (Encoding ==
nullptr || !
consumeIf(
"_block_invoke"))
6251template <
typename Alloc>
6263#if defined(__clang__)
6264#pragma clang diagnostic pop
static GCRegistry::Add< ShadowStackGC > C("shadow-stack", "Very portable GC for uncooperative code generators")
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
DXIL Resource Implicit Binding
#define DEMANGLE_ABI
DEMANGLE_ABI is the export/visibility macro used to mark symbols declared in llvm/Demangle as exporte...
#define DEMANGLE_DUMP_METHOD
#define DEMANGLE_FALLTHROUGH
#define DEMANGLE_NAMESPACE_END
#define DEMANGLE_ASSERT(__expr, __msg)
#define DEMANGLE_NAMESPACE_BEGIN
#define DEMANGLE_UNREACHABLE
Fixup Statepoint Caller Saved
DEMANGLE_ABI const char * parse_discriminator(const char *first, const char *last)
Qualifiers operator|=(Qualifiers &Q1, Qualifiers Q2)
const AbstractManglingParser< Derived, Alloc >::OperatorInfo AbstractManglingParser< Derived, Alloc >::Ops[]
FloatLiteralImpl< long double > LongDoubleLiteral
FloatLiteralImpl< float > FloatLiteral
FloatLiteralImpl< double > DoubleLiteral
Machine Check Debug Module
OptimizedStructLayoutField Field
static StringRef getName(Value *V)
const SmallVectorImpl< MachineOperand > & Cond
BaseType
A given derived pointer can have multiple base pointers through phi/selects.
std::pair< llvm::MachO::Target, std::string > UUID
static bool consume(InternalInstruction *insn, T &ptr)
SaveTemplateParams(AbstractManglingParser *TheParser)
TemplateParamList * params()
~ScopedTemplateParamList()
ScopedTemplateParamList(AbstractManglingParser *TheParser)
void printLeft(OutputBuffer &OB) const override
ArraySubscriptExpr(const Node *Op1_, const Node *Op2_, Prec Prec_)
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
bool printInitListAsType(OutputBuffer &OB, const NodeArray &Elements) const override
bool hasArraySlow(OutputBuffer &) const override
ArrayType(const Node *Base_, Node *Dimension_)
bool hasRHSComponentSlow(OutputBuffer &) const override
BinaryExpr(const Node *LHS_, std::string_view InfixOperator_, const Node *RHS_, Prec Prec_)
void printLeft(OutputBuffer &OB) const override
BinaryFPType(const Node *Dimension_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
BitIntType(const Node *Size_, bool Signed_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
BracedExpr(const Node *Elem_, const Node *Init_, bool IsArray_)
void printLeft(OutputBuffer &OB) const override
BracedRangeExpr(const Node *First_, const Node *Last_, const Node *Init_)
void printLeft(OutputBuffer &OB) const override
CallExpr(const Node *Callee_, NodeArray Args_, bool IsParen_, Prec Prec_)
CastExpr(std::string_view CastKind_, const Node *To_, const Node *From_, Prec Prec_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
void printDeclarator(OutputBuffer &OB) const
ClosureTypeName(NodeArray TemplateParams_, const Node *Requires1_, NodeArray Params_, const Node *Requires2_, std::string_view Count_)
void printLeft(OutputBuffer &OB) const override
ConditionalExpr(const Node *Cond_, const Node *Then_, const Node *Else_, Prec Prec_)
ConstrainedTypeTemplateParamDecl(Node *Constraint_, Node *Name_)
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
ConversionExpr(const Node *Type_, NodeArray Expressions_, Prec Prec_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
ConversionOperatorType(const Node *Ty_)
CtorDtorName(const Node *Basename_, bool IsDtor_, int Variant_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
CtorVtableSpecialName(const Node *FirstType_, const Node *SecondType_)
void printLeft(OutputBuffer &OB) const override
DeleteExpr(Node *Op_, bool IsGlobal_, bool IsArray_, Prec Prec_)
DotSuffix(const Node *Prefix_, std::string_view Suffix_)
void printLeft(OutputBuffer &OB) const override
DtorName(const Node *Base_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
DynamicExceptionSpec(NodeArray Types_)
ElaboratedTypeSpefType(std::string_view Kind_, Node *Child_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
EnableIfAttr(NodeArray Conditions_)
void printLeft(OutputBuffer &OB) const override
EnclosingExpr(std::string_view Prefix_, const Node *Infix_, Prec Prec_=Prec::Primary)
void printLeft(OutputBuffer &OB) const override
EnumLiteral(const Node *Ty_, std::string_view Integer_)
std::string_view getBaseName() const override
bool isInstantiation() const
ExpandedSpecialSubstitution(SpecialSubKind SSK_)
ExpandedSpecialSubstitution(SpecialSubKind SSK_, Kind K_)
ExplicitObjectParameter(Node *Base_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
ExprRequirement(const Node *Expr_, bool IsNoexcept_, const Node *TypeConstraint_)
void printLeft(OutputBuffer &OB) const override
FloatLiteralImpl(std::string_view Contents_)
void printLeft(OutputBuffer &OB) const override
FoldExpr(bool IsLeftFold_, std::string_view OperatorName_, const Node *Pack_, const Node *Init_)
void printRight(OutputBuffer &OB) const override
Qualifiers getCVQuals() const
FunctionRefQual getRefQual() const
const Node * getAttrs() const
const Node * getReturnType() const
bool hasRHSComponentSlow(OutputBuffer &) const override
const Node * getRequires() const
void printLeft(OutputBuffer &OB) const override
const Node * getName() const
bool hasFunctionSlow(OutputBuffer &) const override
FunctionEncoding(const Node *Ret_, const Node *Name_, NodeArray Params_, const Node *Attrs_, const Node *Requires_, Qualifiers CVQuals_, FunctionRefQual RefQual_)
NodeArray getParams() const
void printLeft(OutputBuffer &OB) const override
FunctionParam(std::string_view Number_)
void printLeft(OutputBuffer &OB) const override
FunctionType(const Node *Ret_, NodeArray Params_, Qualifiers CVQuals_, FunctionRefQual RefQual_, const Node *ExceptionSpec_)
bool hasRHSComponentSlow(OutputBuffer &) const override
void printRight(OutputBuffer &OB) const override
bool hasFunctionSlow(OutputBuffer &) const override
GlobalQualifiedName(Node *Child_)
std::string_view getBaseName() const override
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
InitListExpr(const Node *Ty_, NodeArray Inits_)
std::string_view value() const
IntegerLiteral(std::string_view Type_, std::string_view Value_)
void printLeft(OutputBuffer &OB) const override
LambdaExpr(const Node *Type_)
void printLeft(OutputBuffer &OB) const override
LiteralOperator(const Node *OpName_)
void printLeft(OutputBuffer &OB) const override
MemberExpr(const Node *LHS_, std::string_view Kind_, const Node *RHS_, Prec Prec_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
NameType(std::string_view Name_)
std::string_view getBaseName() const override
std::string_view getName() const
void printLeft(OutputBuffer &OB) const override
NestedRequirement(const Node *Constraint_)
NewExpr(NodeArray ExprList_, Node *Type_, NodeArray InitList_, bool IsGlobal_, bool IsArray_, Prec Prec_)
void printLeft(OutputBuffer &OB) const override
NodeArray(Node **Elements_, size_t NumElements_)
void printWithComma(OutputBuffer &OB) const
bool printAsString(OutputBuffer &OB) const
Node * operator[](size_t Idx) const
void print(OutputBuffer &OB) const
Prec getPrecedence() const
Prec
Operator precedence for expression nodes.
virtual bool printInitListAsType(OutputBuffer &, const NodeArray &) const
void visit(Fn F) const
Visit the most-derived object corresponding to this object.
void printAsOperand(OutputBuffer &OB, Prec P=Prec::Default, bool StrictlyWorse=false) const
Node(Kind K_, Cache RHSComponentCache_, Cache ArrayCache_=Cache::No, Cache FunctionCache_=Cache::No)
bool hasRHSComponent(OutputBuffer &OB) const
DEMANGLE_DUMP_METHOD void dump() const
friend class OutputBuffer
bool hasFunction(OutputBuffer &OB) const
Cache
Three-way bool to track a cached value.
Node(Kind K_, Prec Precedence_=Prec::Primary, Cache RHSComponentCache_=Cache::No, Cache ArrayCache_=Cache::No, Cache FunctionCache_=Cache::No)
Cache getRHSComponentCache() const
bool hasArray(OutputBuffer &OB) const
Cache getArrayCache() const
virtual bool hasRHSComponentSlow(OutputBuffer &) const
Cache ArrayCache
Track if this node is a (possibly qualified) array type.
virtual bool hasArraySlow(OutputBuffer &) const
virtual std::string_view getBaseName() const
virtual const Node * getSyntaxNode(OutputBuffer &) const
virtual bool hasFunctionSlow(OutputBuffer &) const
Cache getFunctionCache() const
Cache RHSComponentCache
Tracks if this node has a component on its right side, in which case we need to call printRight.
Cache FunctionCache
Track if this node is a (possibly qualified) function type.
NoexceptSpec(const Node *E_)
void printLeft(OutputBuffer &OB) const override
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
NonTypeTemplateParamDecl(Node *Name_, Node *Type_)
bool isObjCObject() const
ObjCProtoName(const Node *Ty_, std::string_view Protocol_)
void printLeft(OutputBuffer &OB) const override
std::string_view getProtocol() const
virtual void printRight(const Node &N)
virtual void printLeft(const Node &N)
Called by the demangler when printing the demangle tree.
PODSmallVector & operator=(PODSmallVector &&Other)
PODSmallVector(const PODSmallVector &)=delete
void push_back(const T &Elem)
PODSmallVector & operator=(const PODSmallVector &)=delete
PODSmallVector(PODSmallVector &&Other)
void shrinkToSize(size_t Index)
T & operator[](size_t Index)
PackIndexing(const Node *Pattern_, const Node *Index_)
void printLeft(OutputBuffer &OB) const override
const Node * getChild() const
ParameterPackExpansion(const Node *Child_)
void printLeft(OutputBuffer &OB) const override
ParameterPack(NodeArray Data_)
void printRight(OutputBuffer &OB) const override
bool hasArraySlow(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
const Node * getSyntaxNode(OutputBuffer &OB) const override
bool hasFunctionSlow(OutputBuffer &OB) const override
bool hasRHSComponentSlow(OutputBuffer &OB) const override
PixelVectorType(const Node *Dimension_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
PointerToMemberConversionExpr(const Node *Type_, const Node *SubExpr_, std::string_view Offset_, Prec Prec_)
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
bool hasRHSComponentSlow(OutputBuffer &OB) const override
PointerToMemberType(const Node *ClassType_, const Node *MemberType_)
bool hasRHSComponentSlow(OutputBuffer &OB) const override
PointerType(const Node *Pointee_)
const Node * getPointee() const
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
PostfixExpr(const Node *Child_, std::string_view Operator_, Prec Prec_)
void printLeft(OutputBuffer &OB) const override
PostfixQualifiedType(const Node *Ty_, std::string_view Postfix_)
void printLeft(OutputBuffer &OB) const override
PrefixExpr(std::string_view Prefix_, Node *Child_, Prec Prec_)
void printLeft(OutputBuffer &OB) const override
bool hasFunctionSlow(OutputBuffer &OB) const override
QualType(const Node *Child_, Qualifiers Quals_)
void printLeft(OutputBuffer &OB) const override
void printQuals(OutputBuffer &OB) const
Qualifiers getQuals() const
void printRight(OutputBuffer &OB) const override
const Node * getChild() const
bool hasRHSComponentSlow(OutputBuffer &OB) const override
bool hasArraySlow(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
std::string_view getBaseName() const override
QualifiedName(const Node *Qualifier_, const Node *Name_)
void printLeft(OutputBuffer &OB) const override
bool hasRHSComponentSlow(OutputBuffer &OB) const override
ReferenceType(const Node *Pointee_, ReferenceKind RK_)
void printRight(OutputBuffer &OB) const override
RequiresExpr(NodeArray Parameters_, NodeArray Requirements_)
void printLeft(OutputBuffer &OB) const override
SizeofParamPackExpr(const Node *Pack_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
SpecialName(std::string_view Special_, const Node *Child_)
std::string_view getBaseName() const override
SpecialSubstitution(SpecialSubKind SSK_)
void printLeft(OutputBuffer &OB) const override
StringLiteral(const Node *Type_)
void printLeft(OutputBuffer &OB) const override
StructuredBindingName(NodeArray Bindings_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
SubobjectExpr(const Node *Type_, const Node *SubExpr_, std::string_view Offset_, NodeArray UnionSelectors_, bool OnePastTheEnd_)
void printLeft(OutputBuffer &OB) const override
SyntheticTemplateParamName(TemplateParamKind Kind_, unsigned Index_)
TemplateArgs(NodeArray Params_, Node *Requires_)
void printLeft(OutputBuffer &OB) const override
A variadic template argument.
void printLeft(OutputBuffer &OB) const override
TemplateArgumentPack(NodeArray Elements_)
NodeArray getElements() const
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
TemplateParamPackDecl(Node *Param_)
TemplateParamQualifiedArg(Node *Param_, Node *Arg_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
TemplateTemplateParamDecl(Node *Name_, NodeArray Params_, Node *Requires_)
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
ThrowExpr(const Node *Op_)
TypeRequirement(const Node *Type_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
TypeTemplateParamDecl(Node *Name_)
void printRight(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
UnnamedTypeName(std::string_view Count_)
VectorType(const Node *BaseType_, const Node *Dimension_)
const Node * getDimension() const
void printLeft(OutputBuffer &OB) const override
const Node * getBaseType() const
VendorExtQualType(const Node *Ty_, std::string_view Ext_, const Node *TA_)
void printLeft(OutputBuffer &OB) const override
std::string_view getExt() const
const Node * getTA() const
const Node * getTy() const
constexpr Node::Kind getFloatLiteralKind(float *)
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
void printLeft(OutputBuffer &OB) const override
AbiTagAttr(Node *Base_, std::string_view Tag_)
std::string_view getBaseName() const override
Holds some extra information about a <name> that is being parsed.
bool HasExplicitObjectParameter
bool EndsWithTemplateArgs
NameState(AbstractManglingParser *Enclosing)
size_t ForwardTemplateRefsBegin
FunctionRefQual ReferenceQualifier
constexpr OperatorInfo(const char(&E)[3], OIKind K, bool F, Node::Prec P, const char *N)
Node::Prec getPrecedence() const
bool operator<(const OperatorInfo &Other) const
std::string_view getName() const
bool operator==(const char *Peek) const
bool operator!=(const char *Peek) const
bool operator<(const char *Peek) const
std::string_view getSymbol() const
bool parseModuleNameOpt(ModuleName *&Module)
Node * parseSubstitution()
PODSmallVector< Node *, 32 > Subs
PODSmallVector< Node *, 8 > TemplateParamList
Node * parseFloatingLiteral()
void reset(const char *First_, const char *Last_)
Node * parseClassEnumType()
Node * parseBaseUnresolvedName()
bool HasIncompleteTemplateParameterTracking
Node * parseSubobjectExpr()
PODSmallVector< ForwardTemplateReference *, 4 > ForwardTemplateRefs
Node * parseConversionExpr()
PODSmallVector< Node *, 32 > Names
Node * parseConstraintExpr()
bool isTemplateParamDecl()
Node * parseTemplateArgs(bool TagTemplates=false)
Node * parseSpecialName()
Node * parseTemplateParam()
Node * parseType()
Parse the <type> production.
Node * parseTemplateParamDecl(TemplateParamList *Params)
Qualifiers parseCVQualifiers()
Node * parsePrefixExpr(std::string_view Kind, Node::Prec Prec)
bool PermitForwardTemplateReferences
Node * parseUnresolvedName(bool Global)
Parse the <unresolved-name> production.
Node * parsePointerToMemberConversionExpr(Node::Prec Prec)
Node * parsePointerToMemberType()
bool resolveForwardTemplateRefs(NameState &State)
Node * parseIntegerLiteral(std::string_view Lit)
Node * make(Args &&... args)
bool parseSeqId(size_t *Out)
Node * parseEncoding(bool ParseParams=true)
Node * parseName(NameState *State=nullptr)
Parse the <name> production>
Node * parseBinaryExpr(std::string_view Kind, Node::Prec Prec)
std::string_view parseNumber(bool AllowNegative=false)
TemplateParamList OuterTemplateParams
Node * parse(bool ParseParams=true)
Top-level entry point into the parser.
Node * parseFunctionType()
static const OperatorInfo Ops[]
Node * parseDestructorName()
NodeArray makeNodeArray(It begin, It end)
Node * parseLocalName(NameState *State)
AbstractManglingParser(const char *First_, const char *Last_)
Node * parseRequiresExpr()
char look(unsigned Lookahead=0) const
bool parsePositiveInteger(size_t *Out)
Node * parseExprPrimary()
Node * parseQualifiedType()
Node * parseCtorDtorName(Node *&SoFar, NameState *State)
Node * parseExpr()
Parse the <expression> production.
Node * parseAbiTags(Node *N)
Node * parseNestedName(NameState *State)
unsigned NumSyntheticTemplateParameters[3]
Node * parseSourceName(NameState *State)
Node * parseUnscopedName(NameState *State, bool *isSubstName)
size_t ParsingLambdaParamsAtLevel
Node * parseTemplateArg()
bool TryToParseTemplateArgs
bool consumeIf(std::string_view S)
Node * parseUnqualifiedName(NameState *State, Node *Scope, ModuleName *Module)
std::string_view parseBareSourceName()
NodeArray popTrailingNodeArray(size_t FromPosition)
Node * parseFunctionParam()
PODSmallVector< TemplateParamList *, 4 > TemplateParams
const OperatorInfo * parseOperatorEncoding()
Node * parseUnresolvedType()
Node * parseOperatorName(NameState *State)
Node * parseUnnamedTypeName(NameState *State)
static const size_t NumOps
static const size_t mangled_size
static const size_t max_demangled_size
static constexpr const char * spec
static constexpr const char * spec
static const size_t mangled_size
static const size_t max_demangled_size
static const size_t max_demangled_size
static constexpr const char * spec
A forward-reference to a template argument that was not known at the point where the template paramet...
const Node * getSyntaxNode(OutputBuffer &OB) const override
bool hasRHSComponentSlow(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
bool hasFunctionSlow(OutputBuffer &OB) const override
bool hasArraySlow(OutputBuffer &OB) const override
void printRight(OutputBuffer &OB) const override
ForwardTemplateReference(size_t Index_)
void match(Fn F) const =delete
LocalName(Node *Encoding_, Node *Entity_)
void printLeft(OutputBuffer &OB) const override
std::string_view getBaseName() const override
MemberLikeFriendName(Node *Qual_, Node *Name_)
void printLeft(OutputBuffer &OB) const override
std::string_view getBaseName() const override
void printLeft(OutputBuffer &OB) const override
ModuleEntity(ModuleName *Module_, Node *Name_)
void printLeft(OutputBuffer &OB) const override
ModuleName(ModuleName *Parent_, Node *Name_, bool IsPartition_=false)
void printLeft(OutputBuffer &OB) const override
std::string_view getBaseName() const override
NameWithTemplateArgs(Node *Name_, Node *TemplateArgs_)
std::string_view getBaseName() const override
NestedName(Node *Qual_, Node *Name_)
void printLeft(OutputBuffer &OB) const override
void printLeft(OutputBuffer &OB) const override
NodeArrayNode(NodeArray Array_)
Determine the kind of a node from its type.