1 #ifndef LLVM_SUPPORT_MICROSOFTDEMANGLENODES_H
2 #define LLVM_SUPPORT_MICROSOFTDEMANGLENODES_H
4 #include "llvm/Demangle/Compiler.h"
5 #include "llvm/Demangle/StringView.h"
11 namespace ms_demangle {
14 enum Qualifiers : uint8_t {
25 enum class StorageClass : uint8_t {
34 enum class PointerAffinity { None, Pointer, Reference, RValueReference };
35 enum class FunctionRefQualifier { None, Reference, RValueReference };
37 // Calling conventions
38 enum class CallingConv : uint8_t {
51 enum class ReferenceKind : uint8_t { None, LValueRef, RValueRef };
55 OF_NoCallingConvention = 1,
56 OF_NoTagSpecifier = 2,
60 enum class PrimitiveKind {
90 enum class IntrinsicFunctionKind : uint8_t {
92 New, // ?2 # operator new
93 Delete, // ?3 # operator delete
94 Assign, // ?4 # operator=
95 RightShift, // ?5 # operator>>
96 LeftShift, // ?6 # operator<<
97 LogicalNot, // ?7 # operator!
98 Equals, // ?8 # operator==
99 NotEquals, // ?9 # operator!=
100 ArraySubscript, // ?A # operator[]
101 Pointer, // ?C # operator->
102 Dereference, // ?D # operator*
103 Increment, // ?E # operator++
104 Decrement, // ?F # operator--
105 Minus, // ?G # operator-
106 Plus, // ?H # operator+
107 BitwiseAnd, // ?I # operator&
108 MemberPointer, // ?J # operator->*
109 Divide, // ?K # operator/
110 Modulus, // ?L # operator%
111 LessThan, // ?M operator<
112 LessThanEqual, // ?N operator<=
113 GreaterThan, // ?O operator>
114 GreaterThanEqual, // ?P operator>=
115 Comma, // ?Q operator,
116 Parens, // ?R operator()
117 BitwiseNot, // ?S operator~
118 BitwiseXor, // ?T operator^
119 BitwiseOr, // ?U operator|
120 LogicalAnd, // ?V operator&&
121 LogicalOr, // ?W operator||
122 TimesEqual, // ?X operator*=
123 PlusEqual, // ?Y operator+=
124 MinusEqual, // ?Z operator-=
125 DivEqual, // ?_0 operator/=
126 ModEqual, // ?_1 operator%=
127 RshEqual, // ?_2 operator>>=
128 LshEqual, // ?_3 operator<<=
129 BitwiseAndEqual, // ?_4 operator&=
130 BitwiseOrEqual, // ?_5 operator|=
131 BitwiseXorEqual, // ?_6 operator^=
132 VbaseDtor, // ?_D # vbase destructor
133 VecDelDtor, // ?_E # vector deleting destructor
134 DefaultCtorClosure, // ?_F # default constructor closure
135 ScalarDelDtor, // ?_G # scalar deleting destructor
136 VecCtorIter, // ?_H # vector constructor iterator
137 VecDtorIter, // ?_I # vector destructor iterator
138 VecVbaseCtorIter, // ?_J # vector vbase constructor iterator
139 VdispMap, // ?_K # virtual displacement map
140 EHVecCtorIter, // ?_L # eh vector constructor iterator
141 EHVecDtorIter, // ?_M # eh vector destructor iterator
142 EHVecVbaseCtorIter, // ?_N # eh vector vbase constructor iterator
143 CopyCtorClosure, // ?_O # copy constructor closure
144 LocalVftableCtorClosure, // ?_T # local vftable constructor closure
145 ArrayNew, // ?_U operator new[]
146 ArrayDelete, // ?_V operator delete[]
147 ManVectorCtorIter, // ?__A managed vector ctor iterator
148 ManVectorDtorIter, // ?__B managed vector dtor iterator
149 EHVectorCopyCtorIter, // ?__C EH vector copy ctor iterator
150 EHVectorVbaseCopyCtorIter, // ?__D EH vector vbase copy ctor iterator
151 VectorCopyCtorIter, // ?__G vector copy constructor iterator
152 VectorVbaseCopyCtorIter, // ?__H vector vbase copy constructor iterator
153 ManVectorVbaseCopyCtorIter, // ?__I managed vector vbase copy constructor
154 CoAwait, // ?__L co_await
155 Spaceship, // operator<=>
159 enum class SpecialIntrinsicKind {
170 DynamicAtexitDestructor,
172 RttiBaseClassDescriptor,
174 RttiClassHierarchyDescriptor,
175 RttiCompleteObjLocator,
177 LocalStaticThreadGuard,
181 enum FuncClass : uint16_t {
184 FC_Protected = 1 << 1,
191 FC_NoParameterList = 1 << 8,
192 FC_VirtualThisAdjust = 1 << 9,
193 FC_VirtualThisAdjustEx = 1 << 10,
194 FC_StaticThisAdjust = 1 << 11,
197 enum class TagKind { Class, Struct, Union, Enum };
199 enum class NodeKind {
206 VcallThunkIdentifier,
207 LocalStaticGuardIdentifier,
208 IntrinsicFunctionIdentifier,
209 ConversionOperatorIdentifier,
210 DynamicStructorIdentifier,
212 LiteralOperatorIdentifier,
221 TemplateParameterReference,
222 EncodedStringLiteral,
224 RttiBaseClassDescriptor,
225 LocalStaticGuardVariable,
232 explicit Node(NodeKind K) : Kind(K) {}
233 virtual ~Node() = default;
235 NodeKind kind() const { return Kind; }
237 virtual void output(OutputStream &OS, OutputFlags Flags) const = 0;
239 std::string toString(OutputFlags Flags = OF_Default) const;
246 struct PrimitiveTypeNode;
247 struct FunctionSignatureNode;
248 struct IdentifierNode;
249 struct NamedIdentifierNode;
250 struct VcallThunkIdentifierNode;
251 struct IntrinsicFunctionIdentifierNode;
252 struct LiteralOperatorIdentifierNode;
253 struct ConversionOperatorIdentifierNode;
254 struct StructorIdentifierNode;
255 struct ThunkSignatureNode;
256 struct PointerTypeNode;
257 struct ArrayTypeNode;
260 struct IntrinsicTypeNode;
261 struct NodeArrayNode;
262 struct QualifiedNameNode;
263 struct TemplateParameterReferenceNode;
264 struct EncodedStringLiteralNode;
265 struct IntegerLiteralNode;
266 struct RttiBaseClassDescriptorNode;
267 struct LocalStaticGuardVariableNode;
269 struct FunctionSymbolNode;
270 struct VariableSymbolNode;
271 struct SpecialTableSymbolNode;
273 struct TypeNode : public Node {
274 explicit TypeNode(NodeKind K) : Node(K) {}
276 virtual void outputPre(OutputStream &OS, OutputFlags Flags) const = 0;
277 virtual void outputPost(OutputStream &OS, OutputFlags Flags) const = 0;
279 void output(OutputStream &OS, OutputFlags Flags) const override {
280 outputPre(OS, Flags);
281 outputPost(OS, Flags);
284 void outputQuals(bool SpaceBefore, bool SpaceAfter) const;
286 Qualifiers Quals = Q_None;
289 struct PrimitiveTypeNode : public TypeNode {
290 explicit PrimitiveTypeNode(PrimitiveKind K)
291 : TypeNode(NodeKind::PrimitiveType), PrimKind(K) {}
293 void outputPre(OutputStream &OS, OutputFlags Flags) const;
294 void outputPost(OutputStream &OS, OutputFlags Flags) const {}
296 PrimitiveKind PrimKind;
299 struct FunctionSignatureNode : public TypeNode {
300 explicit FunctionSignatureNode(NodeKind K) : TypeNode(K) {}
301 FunctionSignatureNode() : TypeNode(NodeKind::FunctionSignature) {}
303 void outputPre(OutputStream &OS, OutputFlags Flags) const override;
304 void outputPost(OutputStream &OS, OutputFlags Flags) const override;
306 // Valid if this FunctionTypeNode is the Pointee of a PointerType or
307 // MemberPointerType.
308 PointerAffinity Affinity = PointerAffinity::None;
310 // The function's calling convention.
311 CallingConv CallConvention = CallingConv::None;
313 // Function flags (gloabl, public, etc)
314 FuncClass FunctionClass = FC_Global;
316 FunctionRefQualifier RefQualifier = FunctionRefQualifier::None;
318 // The return type of the function.
319 TypeNode *ReturnType = nullptr;
321 // True if this is a C-style ... varargs function.
322 bool IsVariadic = false;
324 // Function parameters
325 NodeArrayNode *Params = nullptr;
327 // True if the function type is noexcept
328 bool IsNoexcept = false;
331 struct IdentifierNode : public Node {
332 explicit IdentifierNode(NodeKind K) : Node(K) {}
334 NodeArrayNode *TemplateParams = nullptr;
337 void outputTemplateParameters(OutputStream &OS, OutputFlags Flags) const;
340 struct VcallThunkIdentifierNode : public IdentifierNode {
341 VcallThunkIdentifierNode() : IdentifierNode(NodeKind::VcallThunkIdentifier) {}
343 void output(OutputStream &OS, OutputFlags Flags) const override;
345 uint64_t OffsetInVTable = 0;
348 struct DynamicStructorIdentifierNode : public IdentifierNode {
349 DynamicStructorIdentifierNode()
350 : IdentifierNode(NodeKind::DynamicStructorIdentifier) {}
352 void output(OutputStream &OS, OutputFlags Flags) const override;
354 VariableSymbolNode *Variable = nullptr;
355 QualifiedNameNode *Name = nullptr;
356 bool IsDestructor = false;
359 struct NamedIdentifierNode : public IdentifierNode {
360 NamedIdentifierNode() : IdentifierNode(NodeKind::NamedIdentifier) {}
362 void output(OutputStream &OS, OutputFlags Flags) const override;
367 struct IntrinsicFunctionIdentifierNode : public IdentifierNode {
368 explicit IntrinsicFunctionIdentifierNode(IntrinsicFunctionKind Operator)
369 : IdentifierNode(NodeKind::IntrinsicFunctionIdentifier),
370 Operator(Operator) {}
372 void output(OutputStream &OS, OutputFlags Flags) const override;
374 IntrinsicFunctionKind Operator;
377 struct LiteralOperatorIdentifierNode : public IdentifierNode {
378 LiteralOperatorIdentifierNode()
379 : IdentifierNode(NodeKind::LiteralOperatorIdentifier) {}
381 void output(OutputStream &OS, OutputFlags Flags) const override;
386 struct LocalStaticGuardIdentifierNode : public IdentifierNode {
387 LocalStaticGuardIdentifierNode()
388 : IdentifierNode(NodeKind::LocalStaticGuardIdentifier) {}
390 void output(OutputStream &OS, OutputFlags Flags) const override;
392 uint32_t ScopeIndex = 0;
395 struct ConversionOperatorIdentifierNode : public IdentifierNode {
396 ConversionOperatorIdentifierNode()
397 : IdentifierNode(NodeKind::ConversionOperatorIdentifier) {}
399 void output(OutputStream &OS, OutputFlags Flags) const override;
401 // The type that this operator converts too.
402 TypeNode *TargetType = nullptr;
405 struct StructorIdentifierNode : public IdentifierNode {
406 StructorIdentifierNode() : IdentifierNode(NodeKind::StructorIdentifier) {}
407 explicit StructorIdentifierNode(bool IsDestructor)
408 : IdentifierNode(NodeKind::StructorIdentifier),
409 IsDestructor(IsDestructor) {}
411 void output(OutputStream &OS, OutputFlags Flags) const override;
413 // The name of the class that this is a structor of.
414 IdentifierNode *Class = nullptr;
415 bool IsDestructor = false;
418 struct ThunkSignatureNode : public FunctionSignatureNode {
419 ThunkSignatureNode() : FunctionSignatureNode(NodeKind::ThunkSignature) {}
421 void outputPre(OutputStream &OS, OutputFlags Flags) const override;
422 void outputPost(OutputStream &OS, OutputFlags Flags) const override;
424 struct ThisAdjustor {
425 uint32_t StaticOffset = 0;
426 int32_t VBPtrOffset = 0;
427 int32_t VBOffsetOffset = 0;
428 int32_t VtordispOffset = 0;
431 ThisAdjustor ThisAdjust;
434 struct PointerTypeNode : public TypeNode {
435 PointerTypeNode() : TypeNode(NodeKind::PointerType) {}
436 void outputPre(OutputStream &OS, OutputFlags Flags) const override;
437 void outputPost(OutputStream &OS, OutputFlags Flags) const override;
439 // Is this a pointer, reference, or rvalue-reference?
440 PointerAffinity Affinity = PointerAffinity::None;
442 // If this is a member pointer, this is the class that the member is in.
443 QualifiedNameNode *ClassParent = nullptr;
445 // Represents a type X in "a pointer to X", "a reference to X", or
446 // "rvalue-reference to X"
447 TypeNode *Pointee = nullptr;
450 struct TagTypeNode : public TypeNode {
451 explicit TagTypeNode(TagKind Tag) : TypeNode(NodeKind::TagType), Tag(Tag) {}
453 void outputPre(OutputStream &OS, OutputFlags Flags) const;
454 void outputPost(OutputStream &OS, OutputFlags Flags) const;
456 QualifiedNameNode *QualifiedName = nullptr;
460 struct ArrayTypeNode : public TypeNode {
461 ArrayTypeNode() : TypeNode(NodeKind::ArrayType) {}
463 void outputPre(OutputStream &OS, OutputFlags Flags) const;
464 void outputPost(OutputStream &OS, OutputFlags Flags) const;
466 void outputDimensionsImpl(OutputStream &OS, OutputFlags Flags) const;
467 void outputOneDimension(OutputStream &OS, OutputFlags Flags, Node *N) const;
469 // A list of array dimensions. e.g. [3,4,5] in `int Foo[3][4][5]`
470 NodeArrayNode *Dimensions = nullptr;
472 // The type of array element.
473 TypeNode *ElementType = nullptr;
476 struct IntrinsicNode : public TypeNode {
477 IntrinsicNode() : TypeNode(NodeKind::IntrinsicType) {}
478 void output(OutputStream &OS, OutputFlags Flags) const override {}
481 struct CustomTypeNode : public TypeNode {
482 CustomTypeNode() : TypeNode(NodeKind::Custom) {}
484 void outputPre(OutputStream &OS, OutputFlags Flags) const override;
485 void outputPost(OutputStream &OS, OutputFlags Flags) const override;
487 IdentifierNode *Identifier;
490 struct NodeArrayNode : public Node {
491 NodeArrayNode() : Node(NodeKind::NodeArray) {}
493 void output(OutputStream &OS, OutputFlags Flags) const override;
495 void output(OutputStream &OS, OutputFlags Flags, StringView Separator) const;
501 struct QualifiedNameNode : public Node {
502 QualifiedNameNode() : Node(NodeKind::QualifiedName) {}
504 void output(OutputStream &OS, OutputFlags Flags) const override;
506 NodeArrayNode *Components = nullptr;
508 IdentifierNode *getUnqualifiedIdentifier() {
509 Node *LastComponent = Components->Nodes[Components->Count - 1];
510 return static_cast<IdentifierNode *>(LastComponent);
514 struct TemplateParameterReferenceNode : public Node {
515 TemplateParameterReferenceNode()
516 : Node(NodeKind::TemplateParameterReference) {}
518 void output(OutputStream &OS, OutputFlags Flags) const override;
520 SymbolNode *Symbol = nullptr;
522 int ThunkOffsetCount = 0;
523 std::array<int64_t, 3> ThunkOffsets;
524 PointerAffinity Affinity = PointerAffinity::None;
525 bool IsMemberPointer = false;
528 struct IntegerLiteralNode : public Node {
529 IntegerLiteralNode() : Node(NodeKind::IntegerLiteral) {}
530 IntegerLiteralNode(uint64_t Value, bool IsNegative)
531 : Node(NodeKind::IntegerLiteral), Value(Value), IsNegative(IsNegative) {}
533 void output(OutputStream &OS, OutputFlags Flags) const override;
536 bool IsNegative = false;
539 struct RttiBaseClassDescriptorNode : public IdentifierNode {
540 RttiBaseClassDescriptorNode()
541 : IdentifierNode(NodeKind::RttiBaseClassDescriptor) {}
543 void output(OutputStream &OS, OutputFlags Flags) const override;
545 uint32_t NVOffset = 0;
546 int32_t VBPtrOffset = 0;
547 uint32_t VBTableOffset = 0;
551 struct SymbolNode : public Node {
552 explicit SymbolNode(NodeKind K) : Node(K) {}
553 void output(OutputStream &OS, OutputFlags Flags) const override;
554 QualifiedNameNode *Name = nullptr;
557 struct SpecialTableSymbolNode : public SymbolNode {
558 explicit SpecialTableSymbolNode()
559 : SymbolNode(NodeKind::SpecialTableSymbol) {}
561 void output(OutputStream &OS, OutputFlags Flags) const override;
562 QualifiedNameNode *TargetName = nullptr;
566 struct LocalStaticGuardVariableNode : public SymbolNode {
567 LocalStaticGuardVariableNode()
568 : SymbolNode(NodeKind::LocalStaticGuardVariable) {}
570 void output(OutputStream &OS, OutputFlags Flags) const override;
572 bool IsVisible = false;
575 struct EncodedStringLiteralNode : public SymbolNode {
576 EncodedStringLiteralNode() : SymbolNode(NodeKind::EncodedStringLiteral) {}
578 void output(OutputStream &OS, OutputFlags Flags) const override;
580 StringView DecodedString;
581 bool IsTruncated = false;
582 CharKind Char = CharKind::Char;
585 struct VariableSymbolNode : public SymbolNode {
586 VariableSymbolNode() : SymbolNode(NodeKind::VariableSymbol) {}
588 void output(OutputStream &OS, OutputFlags Flags) const override;
590 StorageClass SC = StorageClass::None;
591 TypeNode *Type = nullptr;
594 struct FunctionSymbolNode : public SymbolNode {
595 FunctionSymbolNode() : SymbolNode(NodeKind::FunctionSymbol) {}
597 void output(OutputStream &OS, OutputFlags Flags) const override;
599 FunctionSignatureNode *Signature = nullptr;
602 } // namespace ms_demangle