xref: /freebsd/contrib/llvm-project/llvm/include/llvm/Demangle/MicrosoftDemangleNodes.h (revision 700637cbb5e582861067a11aaca4d053546871d2)
1 //===- MicrosoftDemangleNodes.h ---------------------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // This file defines the AST nodes used in the MSVC demangler.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #ifndef LLVM_DEMANGLE_MICROSOFTDEMANGLENODES_H
14 #define LLVM_DEMANGLE_MICROSOFTDEMANGLENODES_H
15 
16 #include <array>
17 #include <cstdint>
18 #include <string>
19 #include <string_view>
20 
21 namespace llvm {
22 namespace itanium_demangle {
23 class OutputBuffer;
24 }
25 }
26 
27 using llvm::itanium_demangle::OutputBuffer;
28 
29 namespace llvm {
30 namespace ms_demangle {
31 
32 // Storage classes
33 enum Qualifiers : uint8_t {
34   Q_None = 0,
35   Q_Const = 1 << 0,
36   Q_Volatile = 1 << 1,
37   Q_Far = 1 << 2,
38   Q_Huge = 1 << 3,
39   Q_Unaligned = 1 << 4,
40   Q_Restrict = 1 << 5,
41   Q_Pointer64 = 1 << 6
42 };
43 
44 enum class StorageClass : uint8_t {
45   None,
46   PrivateStatic,
47   ProtectedStatic,
48   PublicStatic,
49   Global,
50   FunctionLocalStatic,
51 };
52 
53 enum class PointerAffinity { None, Pointer, Reference, RValueReference };
54 enum class FunctionRefQualifier { None, Reference, RValueReference };
55 
56 // Calling conventions
57 enum class CallingConv : uint8_t {
58   None,
59   Cdecl,
60   Pascal,
61   Thiscall,
62   Stdcall,
63   Fastcall,
64   Clrcall,
65   Eabi,
66   Vectorcall,
67   Regcall,
68   Swift,      // Clang-only
69   SwiftAsync, // Clang-only
70 };
71 
72 enum class ReferenceKind : uint8_t { None, LValueRef, RValueRef };
73 
74 enum OutputFlags {
75   OF_Default = 0,
76   OF_NoCallingConvention = 1,
77   OF_NoTagSpecifier = 2,
78   OF_NoAccessSpecifier = 4,
79   OF_NoMemberType = 8,
80   OF_NoReturnType = 16,
81   OF_NoVariableType = 32,
82 };
83 
84 // Types
85 enum class PrimitiveKind {
86   Void,
87   Bool,
88   Char,
89   Schar,
90   Uchar,
91   Char8,
92   Char16,
93   Char32,
94   Short,
95   Ushort,
96   Int,
97   Uint,
98   Long,
99   Ulong,
100   Int64,
101   Uint64,
102   Wchar,
103   Float,
104   Double,
105   Ldouble,
106   Nullptr,
107   Auto,
108   DecltypeAuto,
109 };
110 
111 enum class CharKind {
112   Char,
113   Char16,
114   Char32,
115   Wchar,
116 };
117 
118 enum class IntrinsicFunctionKind : uint8_t {
119   None,
120   New,                        // ?2 # operator new
121   Delete,                     // ?3 # operator delete
122   Assign,                     // ?4 # operator=
123   RightShift,                 // ?5 # operator>>
124   LeftShift,                  // ?6 # operator<<
125   LogicalNot,                 // ?7 # operator!
126   Equals,                     // ?8 # operator==
127   NotEquals,                  // ?9 # operator!=
128   ArraySubscript,             // ?A # operator[]
129   Pointer,                    // ?C # operator->
130   Dereference,                // ?D # operator*
131   Increment,                  // ?E # operator++
132   Decrement,                  // ?F # operator--
133   Minus,                      // ?G # operator-
134   Plus,                       // ?H # operator+
135   BitwiseAnd,                 // ?I # operator&
136   MemberPointer,              // ?J # operator->*
137   Divide,                     // ?K # operator/
138   Modulus,                    // ?L # operator%
139   LessThan,                   // ?M operator<
140   LessThanEqual,              // ?N operator<=
141   GreaterThan,                // ?O operator>
142   GreaterThanEqual,           // ?P operator>=
143   Comma,                      // ?Q operator,
144   Parens,                     // ?R operator()
145   BitwiseNot,                 // ?S operator~
146   BitwiseXor,                 // ?T operator^
147   BitwiseOr,                  // ?U operator|
148   LogicalAnd,                 // ?V operator&&
149   LogicalOr,                  // ?W operator||
150   TimesEqual,                 // ?X operator*=
151   PlusEqual,                  // ?Y operator+=
152   MinusEqual,                 // ?Z operator-=
153   DivEqual,                   // ?_0 operator/=
154   ModEqual,                   // ?_1 operator%=
155   RshEqual,                   // ?_2 operator>>=
156   LshEqual,                   // ?_3 operator<<=
157   BitwiseAndEqual,            // ?_4 operator&=
158   BitwiseOrEqual,             // ?_5 operator|=
159   BitwiseXorEqual,            // ?_6 operator^=
160   VbaseDtor,                  // ?_D # vbase destructor
161   VecDelDtor,                 // ?_E # vector deleting destructor
162   DefaultCtorClosure,         // ?_F # default constructor closure
163   ScalarDelDtor,              // ?_G # scalar deleting destructor
164   VecCtorIter,                // ?_H # vector constructor iterator
165   VecDtorIter,                // ?_I # vector destructor iterator
166   VecVbaseCtorIter,           // ?_J # vector vbase constructor iterator
167   VdispMap,                   // ?_K # virtual displacement map
168   EHVecCtorIter,              // ?_L # eh vector constructor iterator
169   EHVecDtorIter,              // ?_M # eh vector destructor iterator
170   EHVecVbaseCtorIter,         // ?_N # eh vector vbase constructor iterator
171   CopyCtorClosure,            // ?_O # copy constructor closure
172   LocalVftableCtorClosure,    // ?_T # local vftable constructor closure
173   ArrayNew,                   // ?_U operator new[]
174   ArrayDelete,                // ?_V operator delete[]
175   ManVectorCtorIter,          // ?__A managed vector ctor iterator
176   ManVectorDtorIter,          // ?__B managed vector dtor iterator
177   EHVectorCopyCtorIter,       // ?__C EH vector copy ctor iterator
178   EHVectorVbaseCopyCtorIter,  // ?__D EH vector vbase copy ctor iterator
179   VectorCopyCtorIter,         // ?__G vector copy constructor iterator
180   VectorVbaseCopyCtorIter,    // ?__H vector vbase copy constructor iterator
181   ManVectorVbaseCopyCtorIter, // ?__I managed vector vbase copy constructor
182   CoAwait,                    // ?__L operator co_await
183   Spaceship,                  // ?__M operator<=>
184   MaxIntrinsic
185 };
186 
187 enum class SpecialIntrinsicKind {
188   None,
189   Vftable,
190   Vbtable,
191   Typeof,
192   VcallThunk,
193   LocalStaticGuard,
194   StringLiteralSymbol,
195   UdtReturning,
196   Unknown,
197   DynamicInitializer,
198   DynamicAtexitDestructor,
199   RttiTypeDescriptor,
200   RttiBaseClassDescriptor,
201   RttiBaseClassArray,
202   RttiClassHierarchyDescriptor,
203   RttiCompleteObjLocator,
204   LocalVftable,
205   LocalStaticThreadGuard,
206 };
207 
208 // Function classes
209 enum FuncClass : uint16_t {
210   FC_None = 0,
211   FC_Public = 1 << 0,
212   FC_Protected = 1 << 1,
213   FC_Private = 1 << 2,
214   FC_Global = 1 << 3,
215   FC_Static = 1 << 4,
216   FC_Virtual = 1 << 5,
217   FC_Far = 1 << 6,
218   FC_ExternC = 1 << 7,
219   FC_NoParameterList = 1 << 8,
220   FC_VirtualThisAdjust = 1 << 9,
221   FC_VirtualThisAdjustEx = 1 << 10,
222   FC_StaticThisAdjust = 1 << 11,
223 };
224 
225 enum class TagKind { Class, Struct, Union, Enum };
226 
227 enum class NodeKind {
228   Unknown,
229 
230   SymbolStart,
231   Md5Symbol = SymbolStart,
232   EncodedStringLiteral,
233   FunctionSymbol,
234   LocalStaticGuardVariable,
235   SpecialTableSymbol,
236   VariableSymbol,
237   SymbolEnd = VariableSymbol,
238 
239   IdentifierStart,
240   ConversionOperatorIdentifier = IdentifierStart,
241   DynamicStructorIdentifier,
242   IntrinsicFunctionIdentifier,
243   LiteralOperatorIdentifier,
244   LocalStaticGuardIdentifier,
245   NamedIdentifier,
246   RttiBaseClassDescriptor,
247   StructorIdentifier,
248   VcallThunkIdentifier,
249   IdentifierEnd = VcallThunkIdentifier,
250 
251   TypeStart,
252   ArrayType = TypeStart,
253   Custom,
254 
255   FunctionSignature,
256   ThunkSignature,
257   FunctionSignatureEnd = ThunkSignature,
258 
259   IntrinsicType,
260   PointerType,
261   PrimitiveType,
262   TagType,
263   TypeEnd = TagType,
264 
265   PointerAuthQualifier,
266 
267   IntegerLiteral,
268 
269   NodeArray,
270 
271   QualifiedName,
272 
273   TemplateParameterReference,
274 };
275 
276 struct Node {
NodeNode277   explicit Node(NodeKind K) : Kind(K) {}
278   virtual ~Node() = default;
279 
kindNode280   NodeKind kind() const { return Kind; }
281 
282   virtual void output(OutputBuffer &OB, OutputFlags Flags) const = 0;
283 
284   std::string toString(OutputFlags Flags = OF_Default) const;
285 
286 private:
287   NodeKind Kind;
288 };
289 
290 struct TypeNode;
291 struct PrimitiveTypeNode;
292 struct FunctionSignatureNode;
293 struct IdentifierNode;
294 struct NamedIdentifierNode;
295 struct VcallThunkIdentifierNode;
296 struct IntrinsicFunctionIdentifierNode;
297 struct LiteralOperatorIdentifierNode;
298 struct ConversionOperatorIdentifierNode;
299 struct StructorIdentifierNode;
300 struct ThunkSignatureNode;
301 struct PointerTypeNode;
302 struct ArrayTypeNode;
303 struct TagTypeNode;
304 struct NodeArrayNode;
305 struct QualifiedNameNode;
306 struct TemplateParameterReferenceNode;
307 struct EncodedStringLiteralNode;
308 struct IntegerLiteralNode;
309 struct RttiBaseClassDescriptorNode;
310 struct LocalStaticGuardVariableNode;
311 struct SymbolNode;
312 struct FunctionSymbolNode;
313 struct VariableSymbolNode;
314 struct SpecialTableSymbolNode;
315 struct PointerAuthQualifierNode;
316 
317 struct TypeNode : public Node {
TypeNodeTypeNode318   explicit TypeNode(NodeKind K) : Node(K) {}
319 
320   virtual void outputPre(OutputBuffer &OB, OutputFlags Flags) const = 0;
321   virtual void outputPost(OutputBuffer &OB, OutputFlags Flags) const = 0;
322 
outputTypeNode323   void output(OutputBuffer &OB, OutputFlags Flags) const override {
324     outputPre(OB, Flags);
325     outputPost(OB, Flags);
326   }
327 
classofTypeNode328   static bool classof(const Node *N) {
329     return N->kind() >= NodeKind::TypeStart && N->kind() <= NodeKind::TypeEnd;
330   }
331 
332   Qualifiers Quals = Q_None;
333 };
334 
335 struct PrimitiveTypeNode : public TypeNode {
PrimitiveTypeNodePrimitiveTypeNode336   explicit PrimitiveTypeNode(PrimitiveKind K)
337       : TypeNode(NodeKind::PrimitiveType), PrimKind(K) {}
338 
339   void outputPre(OutputBuffer &OB, OutputFlags Flags) const override;
outputPostPrimitiveTypeNode340   void outputPost(OutputBuffer &OB, OutputFlags Flags) const override {}
341 
classofPrimitiveTypeNode342   static bool classof(const Node *N) {
343     return N->kind() == NodeKind::PrimitiveType;
344   }
345 
346   PrimitiveKind PrimKind;
347 };
348 
349 struct FunctionSignatureNode : public TypeNode {
FunctionSignatureNodeFunctionSignatureNode350   explicit FunctionSignatureNode(NodeKind K) : TypeNode(K) {}
FunctionSignatureNodeFunctionSignatureNode351   FunctionSignatureNode() : TypeNode(NodeKind::FunctionSignature) {}
352 
353   void outputPre(OutputBuffer &OB, OutputFlags Flags) const override;
354   void outputPost(OutputBuffer &OB, OutputFlags Flags) const override;
355 
classofFunctionSignatureNode356   static bool classof(const Node *N) {
357     return N->kind() >= NodeKind::FunctionSignature &&
358            N->kind() <= NodeKind::FunctionSignatureEnd;
359   }
360 
361   // Valid if this FunctionTypeNode is the Pointee of a PointerType or
362   // MemberPointerType.
363   PointerAffinity Affinity = PointerAffinity::None;
364 
365   // The function's calling convention.
366   CallingConv CallConvention = CallingConv::None;
367 
368   // Function flags (global, public, etc)
369   FuncClass FunctionClass = FC_Global;
370 
371   FunctionRefQualifier RefQualifier = FunctionRefQualifier::None;
372 
373   // The return type of the function.
374   TypeNode *ReturnType = nullptr;
375 
376   // True if this is a C-style ... varargs function.
377   bool IsVariadic = false;
378 
379   // Function parameters
380   NodeArrayNode *Params = nullptr;
381 
382   // True if the function type is noexcept.
383   bool IsNoexcept = false;
384 };
385 
386 struct IdentifierNode : public Node {
IdentifierNodeIdentifierNode387   explicit IdentifierNode(NodeKind K) : Node(K) {}
388 
classofIdentifierNode389   static bool classof(const Node *N) {
390     return N->kind() >= NodeKind::IdentifierStart &&
391            N->kind() <= NodeKind::IdentifierEnd;
392   }
393 
394   NodeArrayNode *TemplateParams = nullptr;
395 
396 protected:
397   void outputTemplateParameters(OutputBuffer &OB, OutputFlags Flags) const;
398 };
399 
400 struct VcallThunkIdentifierNode : public IdentifierNode {
VcallThunkIdentifierNodeVcallThunkIdentifierNode401   VcallThunkIdentifierNode() : IdentifierNode(NodeKind::VcallThunkIdentifier) {}
402 
403   void output(OutputBuffer &OB, OutputFlags Flags) const override;
404 
classofVcallThunkIdentifierNode405   static bool classof(const Node *N) {
406     return N->kind() == NodeKind::VcallThunkIdentifier;
407   }
408 
409   uint64_t OffsetInVTable = 0;
410 };
411 
412 struct DynamicStructorIdentifierNode : public IdentifierNode {
DynamicStructorIdentifierNodeDynamicStructorIdentifierNode413   DynamicStructorIdentifierNode()
414       : IdentifierNode(NodeKind::DynamicStructorIdentifier) {}
415 
416   void output(OutputBuffer &OB, OutputFlags Flags) const override;
417 
classofDynamicStructorIdentifierNode418   static bool classof(const Node *N) {
419     return N->kind() == NodeKind::DynamicStructorIdentifier;
420   }
421 
422   VariableSymbolNode *Variable = nullptr;
423   QualifiedNameNode *Name = nullptr;
424   bool IsDestructor = false;
425 };
426 
427 struct NamedIdentifierNode : public IdentifierNode {
NamedIdentifierNodeNamedIdentifierNode428   NamedIdentifierNode() : IdentifierNode(NodeKind::NamedIdentifier) {}
429 
430   void output(OutputBuffer &OB, OutputFlags Flags) const override;
431 
classofNamedIdentifierNode432   static bool classof(const Node *N) {
433     return N->kind() == NodeKind::NamedIdentifier;
434   }
435 
436   std::string_view Name;
437 };
438 
439 struct IntrinsicFunctionIdentifierNode : public IdentifierNode {
IntrinsicFunctionIdentifierNodeIntrinsicFunctionIdentifierNode440   explicit IntrinsicFunctionIdentifierNode(IntrinsicFunctionKind Operator)
441       : IdentifierNode(NodeKind::IntrinsicFunctionIdentifier),
442         Operator(Operator) {}
443 
444   void output(OutputBuffer &OB, OutputFlags Flags) const override;
445 
classofIntrinsicFunctionIdentifierNode446   static bool classof(const Node *N) {
447     return N->kind() == NodeKind::IntrinsicFunctionIdentifier;
448   }
449 
450   IntrinsicFunctionKind Operator;
451 };
452 
453 struct LiteralOperatorIdentifierNode : public IdentifierNode {
LiteralOperatorIdentifierNodeLiteralOperatorIdentifierNode454   LiteralOperatorIdentifierNode()
455       : IdentifierNode(NodeKind::LiteralOperatorIdentifier) {}
456 
457   void output(OutputBuffer &OB, OutputFlags Flags) const override;
458 
classofLiteralOperatorIdentifierNode459   static bool classof(const Node *N) {
460     return N->kind() == NodeKind::LiteralOperatorIdentifier;
461   }
462 
463   std::string_view Name;
464 };
465 
466 struct LocalStaticGuardIdentifierNode : public IdentifierNode {
LocalStaticGuardIdentifierNodeLocalStaticGuardIdentifierNode467   LocalStaticGuardIdentifierNode()
468       : IdentifierNode(NodeKind::LocalStaticGuardIdentifier) {}
469 
470   void output(OutputBuffer &OB, OutputFlags Flags) const override;
471 
classofLocalStaticGuardIdentifierNode472   static bool classof(const Node *N) {
473     return N->kind() == NodeKind::LocalStaticGuardIdentifier;
474   }
475 
476   bool IsThread = false;
477   uint32_t ScopeIndex = 0;
478 };
479 
480 struct ConversionOperatorIdentifierNode : public IdentifierNode {
ConversionOperatorIdentifierNodeConversionOperatorIdentifierNode481   ConversionOperatorIdentifierNode()
482       : IdentifierNode(NodeKind::ConversionOperatorIdentifier) {}
483 
484   void output(OutputBuffer &OB, OutputFlags Flags) const override;
485 
classofConversionOperatorIdentifierNode486   static bool classof(const Node *N) {
487     return N->kind() == NodeKind::ConversionOperatorIdentifier;
488   }
489 
490   // The type that this operator converts too.
491   TypeNode *TargetType = nullptr;
492 };
493 
494 struct StructorIdentifierNode : public IdentifierNode {
StructorIdentifierNodeStructorIdentifierNode495   StructorIdentifierNode() : IdentifierNode(NodeKind::StructorIdentifier) {}
StructorIdentifierNodeStructorIdentifierNode496   explicit StructorIdentifierNode(bool IsDestructor)
497       : IdentifierNode(NodeKind::StructorIdentifier),
498         IsDestructor(IsDestructor) {}
499 
500   void output(OutputBuffer &OB, OutputFlags Flags) const override;
501 
classofStructorIdentifierNode502   static bool classof(const Node *N) {
503     return N->kind() == NodeKind::StructorIdentifier;
504   }
505 
506   // The name of the class that this is a structor of.
507   IdentifierNode *Class = nullptr;
508   bool IsDestructor = false;
509 };
510 
511 struct ThunkSignatureNode : public FunctionSignatureNode {
ThunkSignatureNodeThunkSignatureNode512   ThunkSignatureNode() : FunctionSignatureNode(NodeKind::ThunkSignature) {}
513 
514   void outputPre(OutputBuffer &OB, OutputFlags Flags) const override;
515   void outputPost(OutputBuffer &OB, OutputFlags Flags) const override;
516 
classofThunkSignatureNode517   static bool classof(const Node *N) {
518     return N->kind() == NodeKind::ThunkSignature;
519   }
520 
521   struct ThisAdjustor {
522     uint32_t StaticOffset = 0;
523     int32_t VBPtrOffset = 0;
524     int32_t VBOffsetOffset = 0;
525     int32_t VtordispOffset = 0;
526   };
527 
528   ThisAdjustor ThisAdjust;
529 };
530 
531 struct PointerTypeNode : public TypeNode {
PointerTypeNodePointerTypeNode532   PointerTypeNode() : TypeNode(NodeKind::PointerType) {}
533   void outputPre(OutputBuffer &OB, OutputFlags Flags) const override;
534   void outputPost(OutputBuffer &OB, OutputFlags Flags) const override;
535 
classofPointerTypeNode536   static bool classof(const Node *N) {
537     return N->kind() == NodeKind::PointerType;
538   }
539 
540   // Is this a pointer, reference, or rvalue-reference?
541   PointerAffinity Affinity = PointerAffinity::None;
542 
543   // If this is a member pointer, this is the class that the member is in.
544   QualifiedNameNode *ClassParent = nullptr;
545 
546   PointerAuthQualifierNode *PointerAuthQualifier = nullptr;
547 
548   // Represents a type X in "a pointer to X", "a reference to X", or
549   // "rvalue-reference to X"
550   TypeNode *Pointee = nullptr;
551 };
552 
553 struct TagTypeNode : public TypeNode {
TagTypeNodeTagTypeNode554   explicit TagTypeNode(TagKind Tag) : TypeNode(NodeKind::TagType), Tag(Tag) {}
555 
556   void outputPre(OutputBuffer &OB, OutputFlags Flags) const override;
557   void outputPost(OutputBuffer &OB, OutputFlags Flags) const override;
558 
classofTagTypeNode559   static bool classof(const Node *N) { return N->kind() == NodeKind::TagType; }
560 
561   QualifiedNameNode *QualifiedName = nullptr;
562   TagKind Tag;
563 };
564 
565 struct ArrayTypeNode : public TypeNode {
ArrayTypeNodeArrayTypeNode566   ArrayTypeNode() : TypeNode(NodeKind::ArrayType) {}
567 
568   void outputPre(OutputBuffer &OB, OutputFlags Flags) const override;
569   void outputPost(OutputBuffer &OB, OutputFlags Flags) const override;
570 
571   void outputDimensionsImpl(OutputBuffer &OB, OutputFlags Flags) const;
572   void outputOneDimension(OutputBuffer &OB, OutputFlags Flags, Node *N) const;
573 
classofArrayTypeNode574   static bool classof(const Node *N) {
575     return N->kind() == NodeKind::ArrayType;
576   }
577 
578   // A list of array dimensions.  e.g. [3,4,5] in `int Foo[3][4][5]`
579   NodeArrayNode *Dimensions = nullptr;
580 
581   // The type of array element.
582   TypeNode *ElementType = nullptr;
583 };
584 
585 struct IntrinsicNode : public TypeNode {
IntrinsicNodeIntrinsicNode586   IntrinsicNode() : TypeNode(NodeKind::IntrinsicType) {}
outputIntrinsicNode587   void output(OutputBuffer &OB, OutputFlags Flags) const override {}
588 
classofIntrinsicNode589   static bool classof(const Node *N) {
590     return N->kind() == NodeKind::IntrinsicType;
591   }
592 };
593 
594 struct CustomTypeNode : public TypeNode {
CustomTypeNodeCustomTypeNode595   CustomTypeNode() : TypeNode(NodeKind::Custom) {}
596 
597   void outputPre(OutputBuffer &OB, OutputFlags Flags) const override;
598   void outputPost(OutputBuffer &OB, OutputFlags Flags) const override;
599 
classofCustomTypeNode600   static bool classof(const Node *N) { return N->kind() == NodeKind::Custom; }
601 
602   IdentifierNode *Identifier = nullptr;
603 };
604 
605 struct NodeArrayNode : public Node {
NodeArrayNodeNodeArrayNode606   NodeArrayNode() : Node(NodeKind::NodeArray) {}
607 
608   void output(OutputBuffer &OB, OutputFlags Flags) const override;
609 
610   void output(OutputBuffer &OB, OutputFlags Flags,
611               std::string_view Separator) const;
612 
classofNodeArrayNode613   static bool classof(const Node *N) {
614     return N->kind() == NodeKind::NodeArray;
615   }
616 
617   Node **Nodes = nullptr;
618   size_t Count = 0;
619 };
620 
621 struct QualifiedNameNode : public Node {
QualifiedNameNodeQualifiedNameNode622   QualifiedNameNode() : Node(NodeKind::QualifiedName) {}
623 
624   void output(OutputBuffer &OB, OutputFlags Flags) const override;
625 
classofQualifiedNameNode626   static bool classof(const Node *N) {
627     return N->kind() == NodeKind::QualifiedName;
628   }
629 
630   NodeArrayNode *Components = nullptr;
631 
getUnqualifiedIdentifierQualifiedNameNode632   IdentifierNode *getUnqualifiedIdentifier() {
633     Node *LastComponent = Components->Nodes[Components->Count - 1];
634     return static_cast<IdentifierNode *>(LastComponent);
635   }
636 };
637 
638 struct TemplateParameterReferenceNode : public Node {
TemplateParameterReferenceNodeTemplateParameterReferenceNode639   TemplateParameterReferenceNode()
640       : Node(NodeKind::TemplateParameterReference) {}
641 
642   void output(OutputBuffer &OB, OutputFlags Flags) const override;
643 
classofTemplateParameterReferenceNode644   static bool classof(const Node *N) {
645     return N->kind() == NodeKind::TemplateParameterReference;
646   }
647 
648   SymbolNode *Symbol = nullptr;
649 
650   int ThunkOffsetCount = 0;
651   std::array<int64_t, 3> ThunkOffsets;
652   PointerAffinity Affinity = PointerAffinity::None;
653   bool IsMemberPointer = false;
654 };
655 
656 struct IntegerLiteralNode : public Node {
IntegerLiteralNodeIntegerLiteralNode657   IntegerLiteralNode() : Node(NodeKind::IntegerLiteral) {}
IntegerLiteralNodeIntegerLiteralNode658   IntegerLiteralNode(uint64_t Value, bool IsNegative)
659       : Node(NodeKind::IntegerLiteral), Value(Value), IsNegative(IsNegative) {}
660 
661   void output(OutputBuffer &OB, OutputFlags Flags) const override;
662 
classofIntegerLiteralNode663   static bool classof(const Node *N) {
664     return N->kind() == NodeKind::IntegerLiteral;
665   }
666 
667   uint64_t Value = 0;
668   bool IsNegative = false;
669 };
670 
671 struct RttiBaseClassDescriptorNode : public IdentifierNode {
RttiBaseClassDescriptorNodeRttiBaseClassDescriptorNode672   RttiBaseClassDescriptorNode()
673       : IdentifierNode(NodeKind::RttiBaseClassDescriptor) {}
674 
675   void output(OutputBuffer &OB, OutputFlags Flags) const override;
676 
classofRttiBaseClassDescriptorNode677   static bool classof(const Node *N) {
678     return N->kind() == NodeKind::RttiBaseClassDescriptor;
679   }
680 
681   uint32_t NVOffset = 0;
682   int32_t VBPtrOffset = 0;
683   uint32_t VBTableOffset = 0;
684   uint32_t Flags = 0;
685 };
686 
687 struct SymbolNode : public Node {
SymbolNodeSymbolNode688   explicit SymbolNode(NodeKind K) : Node(K) {}
689   void output(OutputBuffer &OB, OutputFlags Flags) const override;
690 
classofSymbolNode691   static bool classof(const Node *N) {
692     return N->kind() >= NodeKind::SymbolStart &&
693            N->kind() <= NodeKind::SymbolEnd;
694   }
695 
696   QualifiedNameNode *Name = nullptr;
697 };
698 
699 struct SpecialTableSymbolNode : public SymbolNode {
SpecialTableSymbolNodeSpecialTableSymbolNode700   explicit SpecialTableSymbolNode()
701       : SymbolNode(NodeKind::SpecialTableSymbol) {}
702 
703   void output(OutputBuffer &OB, OutputFlags Flags) const override;
704 
classofSpecialTableSymbolNode705   static bool classof(const Node *N) {
706     return N->kind() == NodeKind::SpecialTableSymbol;
707   }
708 
709   QualifiedNameNode *TargetName = nullptr;
710   Qualifiers Quals = Qualifiers::Q_None;
711 };
712 
713 struct LocalStaticGuardVariableNode : public SymbolNode {
LocalStaticGuardVariableNodeLocalStaticGuardVariableNode714   LocalStaticGuardVariableNode()
715       : SymbolNode(NodeKind::LocalStaticGuardVariable) {}
716 
717   void output(OutputBuffer &OB, OutputFlags Flags) const override;
718 
classofLocalStaticGuardVariableNode719   static bool classof(const Node *N) {
720     return N->kind() == NodeKind::LocalStaticGuardVariable;
721   }
722 
723   bool IsVisible = false;
724 };
725 
726 struct EncodedStringLiteralNode : public SymbolNode {
EncodedStringLiteralNodeEncodedStringLiteralNode727   EncodedStringLiteralNode() : SymbolNode(NodeKind::EncodedStringLiteral) {}
728 
729   void output(OutputBuffer &OB, OutputFlags Flags) const override;
730 
classofEncodedStringLiteralNode731   static bool classof(const Node *N) {
732     return N->kind() == NodeKind::EncodedStringLiteral;
733   }
734 
735   std::string_view DecodedString;
736   bool IsTruncated = false;
737   CharKind Char = CharKind::Char;
738 };
739 
740 struct VariableSymbolNode : public SymbolNode {
VariableSymbolNodeVariableSymbolNode741   VariableSymbolNode() : SymbolNode(NodeKind::VariableSymbol) {}
742 
743   void output(OutputBuffer &OB, OutputFlags Flags) const override;
744 
classofVariableSymbolNode745   static bool classof(const Node *N) {
746     return N->kind() == NodeKind::VariableSymbol;
747   }
748 
749   StorageClass SC = StorageClass::None;
750   TypeNode *Type = nullptr;
751 };
752 
753 struct FunctionSymbolNode : public SymbolNode {
FunctionSymbolNodeFunctionSymbolNode754   FunctionSymbolNode() : SymbolNode(NodeKind::FunctionSymbol) {}
755 
756   void output(OutputBuffer &OB, OutputFlags Flags) const override;
757 
classofFunctionSymbolNode758   static bool classof(const Node *N) {
759     return N->kind() == NodeKind::FunctionSymbol;
760   }
761 
762   FunctionSignatureNode *Signature = nullptr;
763 };
764 
765 struct PointerAuthQualifierNode : public Node {
PointerAuthQualifierNodePointerAuthQualifierNode766   PointerAuthQualifierNode() : Node(NodeKind::PointerAuthQualifier) {}
767 
768   // __ptrauth takes three arguments:
769   //  - key
770   //  - isAddressDiscriminated
771   //  - extra discriminator
772   static constexpr unsigned NumArgs = 3;
773   typedef std::array<uint64_t, NumArgs> ArgArray;
774 
775   void output(OutputBuffer &OB, OutputFlags Flags) const override;
776 
classofPointerAuthQualifierNode777   static bool classof(const Node *N) {
778     return N->kind() == NodeKind::PointerAuthQualifier;
779   }
780 
781   // List of arguments.
782   NodeArrayNode *Components = nullptr;
783 };
784 
785 } // namespace ms_demangle
786 } // namespace llvm
787 
788 #endif
789