1 //===-------------------------- cxa_demangle.cpp --------------------------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is dual licensed under the MIT and the University of Illinois Open
6 // Source Licenses. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9
10 // FIXME: (possibly) incomplete list of features that clang mangles that this
11 // file does not yet support:
12 // - enable_if attribute
13 // - C++ modules TS
14 // - All C++14 and C++17 features
15
16 #define _LIBCPP_NO_EXCEPTIONS
17
18 #include "__cxxabi_config.h"
19
20 #include <vector>
21 #include <algorithm>
22 #include <numeric>
23 #include <cassert>
24 #include <cstdio>
25 #include <cstdlib>
26 #include <cstring>
27 #include <cctype>
28
29 #ifdef _MSC_VER
30 // snprintf is implemented in VS 2015
31 #if _MSC_VER < 1900
32 #define snprintf _snprintf_s
33 #endif
34 #endif
35
36 #ifndef NDEBUG
37 #if __has_attribute(noinline) && __has_attribute(used)
38 #define DUMP_METHOD __attribute__((noinline,used))
39 #else
40 #define DUMP_METHOD
41 #endif
42 #endif
43
44 namespace {
45
46 class StringView {
47 const char *First;
48 const char *Last;
49
50 public:
51 template <size_t N>
StringView(const char (& Str)[N])52 StringView(const char (&Str)[N]) : First(Str), Last(Str + N - 1) {}
StringView(const char * First_,const char * Last_)53 StringView(const char *First_, const char *Last_) : First(First_), Last(Last_) {}
StringView()54 StringView() : First(nullptr), Last(nullptr) {}
55
substr(size_t From,size_t To)56 StringView substr(size_t From, size_t To) {
57 if (To >= size())
58 To = size() - 1;
59 if (From >= size())
60 From = size() - 1;
61 return StringView(First + From, First + To);
62 }
63
dropFront(size_t N) const64 StringView dropFront(size_t N) const {
65 if (N >= size())
66 N = size() - 1;
67 return StringView(First + N, Last);
68 }
69
startsWith(StringView Str) const70 bool startsWith(StringView Str) const {
71 if (Str.size() > size())
72 return false;
73 return std::equal(Str.begin(), Str.end(), begin());
74 }
75
operator [](size_t Idx) const76 const char &operator[](size_t Idx) const { return *(begin() + Idx); }
77
begin() const78 const char *begin() const { return First; }
end() const79 const char *end() const { return Last; }
size() const80 size_t size() const { return static_cast<size_t>(Last - First); }
empty() const81 bool empty() const { return First == Last; }
82 };
83
operator ==(const StringView & LHS,const StringView & RHS)84 bool operator==(const StringView &LHS, const StringView &RHS) {
85 return LHS.size() == RHS.size() &&
86 std::equal(LHS.begin(), LHS.end(), RHS.begin());
87 }
88
89 // Stream that AST nodes write their string representation into after the AST
90 // has been parsed.
91 class OutputStream {
92 char *Buffer;
93 size_t CurrentPosition;
94 size_t BufferCapacity;
95
96 // Ensure there is at least n more positions in buffer.
grow(size_t N)97 void grow(size_t N) {
98 if (N + CurrentPosition >= BufferCapacity) {
99 BufferCapacity *= 2;
100 if (BufferCapacity < N + CurrentPosition)
101 BufferCapacity = N + CurrentPosition;
102 Buffer = static_cast<char *>(std::realloc(Buffer, BufferCapacity));
103 }
104 }
105
106 public:
OutputStream(char * StartBuf,size_t Size)107 OutputStream(char *StartBuf, size_t Size)
108 : Buffer(StartBuf), CurrentPosition(0), BufferCapacity(Size) {}
109
110 /// If a ParameterPackExpansion (or similar type) is encountered, the offset
111 /// into the pack that we're currently printing.
112 unsigned CurrentPackIndex = std::numeric_limits<unsigned>::max();
113
operator +=(StringView R)114 OutputStream &operator+=(StringView R) {
115 size_t Size = R.size();
116 if (Size == 0)
117 return *this;
118 grow(Size);
119 memmove(Buffer + CurrentPosition, R.begin(), Size);
120 CurrentPosition += Size;
121 return *this;
122 }
123
operator +=(char C)124 OutputStream &operator+=(char C) {
125 grow(1);
126 Buffer[CurrentPosition++] = C;
127 return *this;
128 }
129
getCurrentPosition() const130 size_t getCurrentPosition() const { return CurrentPosition; };
131
back() const132 char back() const {
133 return CurrentPosition ? Buffer[CurrentPosition - 1] : '\0';
134 }
135
empty() const136 bool empty() const { return CurrentPosition == 0; }
137
getBuffer()138 char *getBuffer() { return Buffer; }
getBufferEnd()139 char *getBufferEnd() { return Buffer + CurrentPosition - 1; }
getBufferCapacity()140 size_t getBufferCapacity() { return BufferCapacity; }
141 };
142
143 template <class T>
144 class SwapAndRestore {
145 T &Restore;
146 T OriginalValue;
147 public:
SwapAndRestore(T & Restore_,T NewVal)148 SwapAndRestore(T& Restore_, T NewVal)
149 : Restore(Restore_), OriginalValue(Restore) {
150 Restore = std::move(NewVal);
151 }
~SwapAndRestore()152 ~SwapAndRestore() { Restore = std::move(OriginalValue); }
153
154 SwapAndRestore(const SwapAndRestore &) = delete;
155 SwapAndRestore &operator=(const SwapAndRestore &) = delete;
156 };
157
158 // Base class of all AST nodes. The AST is built by the parser, then is
159 // traversed by the printLeft/Right functions to produce a demangled string.
160 class Node {
161 public:
162 enum Kind : unsigned char {
163 KDotSuffix,
164 KVendorExtQualType,
165 KQualType,
166 KConversionOperatorType,
167 KPostfixQualifiedType,
168 KNameType,
169 KAbiTagAttr,
170 KObjCProtoName,
171 KPointerType,
172 KLValueReferenceType,
173 KRValueReferenceType,
174 KPointerToMemberType,
175 KArrayType,
176 KFunctionType,
177 KFunctionEncoding,
178 KFunctionQualType,
179 KFunctionRefQualType,
180 KLiteralOperator,
181 KSpecialName,
182 KCtorVtableSpecialName,
183 KQualifiedName,
184 KEmptyName,
185 KVectorType,
186 KParameterPack,
187 KTemplateArgumentPack,
188 KParameterPackExpansion,
189 KTemplateArgs,
190 KNameWithTemplateArgs,
191 KGlobalQualifiedName,
192 KStdQualifiedName,
193 KExpandedSpecialSubstitution,
194 KSpecialSubstitution,
195 KCtorDtorName,
196 KDtorName,
197 KUnnamedTypeName,
198 KLambdaTypeName,
199 KExpr,
200 };
201
202 static constexpr unsigned NoParameterPack =
203 std::numeric_limits<unsigned>::max();
204 unsigned ParameterPackSize = NoParameterPack;
205
206 Kind K;
207
208 /// Three-way bool to track a cached value. Unknown is possible if this node
209 /// has an unexpanded parameter pack below it that may affect this cache.
210 enum class Cache : unsigned char { Yes, No, Unknown, };
211
212 /// Tracks if this node has a component on its right side, in which case we
213 /// need to call printRight.
214 Cache RHSComponentCache;
215
216 /// Track if this node is a (possibly qualified) array type. This can affect
217 /// how we format the output string.
218 Cache ArrayCache;
219
220 /// Track if this node is a (possibly qualified) function type. This can
221 /// affect how we format the output string.
222 Cache FunctionCache;
223
Node(Kind K_,unsigned ParameterPackSize_=NoParameterPack,Cache RHSComponentCache_=Cache::No,Cache ArrayCache_=Cache::No,Cache FunctionCache_=Cache::No)224 Node(Kind K_, unsigned ParameterPackSize_ = NoParameterPack,
225 Cache RHSComponentCache_ = Cache::No, Cache ArrayCache_ = Cache::No,
226 Cache FunctionCache_ = Cache::No)
227 : ParameterPackSize(ParameterPackSize_), K(K_),
228 RHSComponentCache(RHSComponentCache_), ArrayCache(ArrayCache_),
229 FunctionCache(FunctionCache_) {}
230
containsUnexpandedParameterPack() const231 bool containsUnexpandedParameterPack() const {
232 return ParameterPackSize != NoParameterPack;
233 }
234
hasRHSComponent(OutputStream & S) const235 bool hasRHSComponent(OutputStream &S) const {
236 if (RHSComponentCache != Cache::Unknown)
237 return RHSComponentCache == Cache::Yes;
238 return hasRHSComponentSlow(S);
239 }
240
hasArray(OutputStream & S) const241 bool hasArray(OutputStream &S) const {
242 if (ArrayCache != Cache::Unknown)
243 return ArrayCache == Cache::Yes;
244 return hasArraySlow(S);
245 }
246
hasFunction(OutputStream & S) const247 bool hasFunction(OutputStream &S) const {
248 if (FunctionCache != Cache::Unknown)
249 return FunctionCache == Cache::Yes;
250 return hasFunctionSlow(S);
251 }
252
getKind() const253 Kind getKind() const { return K; }
254
hasRHSComponentSlow(OutputStream &) const255 virtual bool hasRHSComponentSlow(OutputStream &) const { return false; }
hasArraySlow(OutputStream &) const256 virtual bool hasArraySlow(OutputStream &) const { return false; }
hasFunctionSlow(OutputStream &) const257 virtual bool hasFunctionSlow(OutputStream &) const { return false; }
258
259 /// If this node is a pack expansion that expands to 0 elements. This can have
260 /// an effect on how we should format the output.
261 bool isEmptyPackExpansion() const;
262
print(OutputStream & S) const263 void print(OutputStream &S) const {
264 printLeft(S);
265 if (RHSComponentCache != Cache::No)
266 printRight(S);
267 }
268
269 // Print the "left" side of this Node into OutputStream.
270 virtual void printLeft(OutputStream &) const = 0;
271
272 // Print the "right". This distinction is necessary to represent C++ types
273 // that appear on the RHS of their subtype, such as arrays or functions.
274 // Since most types don't have such a component, provide a default
275 // implemenation.
printRight(OutputStream &) const276 virtual void printRight(OutputStream &) const {}
277
getBaseName() const278 virtual StringView getBaseName() const { return StringView(); }
279
280 // Silence compiler warnings, this dtor will never be called.
281 virtual ~Node() = default;
282
283 #ifndef NDEBUG
dump() const284 DUMP_METHOD void dump() const {
285 char *Buffer = static_cast<char*>(std::malloc(1024));
286 OutputStream S(Buffer, 1024);
287 print(S);
288 S += '\0';
289 printf("Symbol dump for %p: %s\n", (const void*)this, S.getBuffer());
290 std::free(S.getBuffer());
291 }
292 #endif
293 };
294
295 class NodeArray {
296 Node **Elements;
297 size_t NumElements;
298
299 public:
NodeArray()300 NodeArray() : Elements(nullptr), NumElements(0) {}
NodeArray(Node ** Elements_,size_t NumElements_)301 NodeArray(Node **Elements_, size_t NumElements_)
302 : Elements(Elements_), NumElements(NumElements_) {}
303
empty() const304 bool empty() const { return NumElements == 0; }
size() const305 size_t size() const { return NumElements; }
306
begin() const307 Node **begin() const { return Elements; }
end() const308 Node **end() const { return Elements + NumElements; }
309
operator [](size_t Idx) const310 Node *operator[](size_t Idx) const { return Elements[Idx]; }
311
printWithComma(OutputStream & S) const312 void printWithComma(OutputStream &S) const {
313 bool FirstElement = true;
314 for (size_t Idx = 0; Idx != NumElements; ++Idx) {
315 if (Elements[Idx]->isEmptyPackExpansion())
316 continue;
317 if (!FirstElement)
318 S += ", ";
319 FirstElement = false;
320 Elements[Idx]->print(S);
321 }
322 }
323 };
324
325 class DotSuffix final : public Node {
326 const Node *Prefix;
327 const StringView Suffix;
328
329 public:
DotSuffix(Node * Prefix_,StringView Suffix_)330 DotSuffix(Node *Prefix_, StringView Suffix_)
331 : Node(KDotSuffix), Prefix(Prefix_), Suffix(Suffix_) {}
332
printLeft(OutputStream & s) const333 void printLeft(OutputStream &s) const override {
334 Prefix->print(s);
335 s += " (";
336 s += Suffix;
337 s += ")";
338 }
339 };
340
341 class VendorExtQualType final : public Node {
342 const Node *Ty;
343 StringView Ext;
344
345 public:
VendorExtQualType(Node * Ty_,StringView Ext_)346 VendorExtQualType(Node *Ty_, StringView Ext_)
347 : Node(KVendorExtQualType, Ty_->ParameterPackSize),
348 Ty(Ty_), Ext(Ext_) {}
349
printLeft(OutputStream & S) const350 void printLeft(OutputStream &S) const override {
351 Ty->print(S);
352 S += " ";
353 S += Ext;
354 }
355 };
356
357 enum Qualifiers {
358 QualNone = 0,
359 QualConst = 0x1,
360 QualVolatile = 0x2,
361 QualRestrict = 0x4,
362 };
363
addQualifiers(Qualifiers & Q1,Qualifiers Q2)364 void addQualifiers(Qualifiers &Q1, Qualifiers Q2) {
365 Q1 = static_cast<Qualifiers>(Q1 | Q2);
366 }
367
368 class QualType : public Node {
369 protected:
370 const Qualifiers Quals;
371 const Node *Child;
372
printQuals(OutputStream & S) const373 void printQuals(OutputStream &S) const {
374 if (Quals & QualConst)
375 S += " const";
376 if (Quals & QualVolatile)
377 S += " volatile";
378 if (Quals & QualRestrict)
379 S += " restrict";
380 }
381
382 public:
QualType(Node * Child_,Qualifiers Quals_)383 QualType(Node *Child_, Qualifiers Quals_)
384 : Node(KQualType, Child_->ParameterPackSize, Child_->RHSComponentCache,
385 Child_->ArrayCache, Child_->FunctionCache),
386 Quals(Quals_), Child(Child_) {}
387
hasRHSComponentSlow(OutputStream & S) const388 bool hasRHSComponentSlow(OutputStream &S) const override {
389 return Child->hasRHSComponent(S);
390 }
hasArraySlow(OutputStream & S) const391 bool hasArraySlow(OutputStream &S) const override {
392 return Child->hasArray(S);
393 }
hasFunctionSlow(OutputStream & S) const394 bool hasFunctionSlow(OutputStream &S) const override {
395 return Child->hasFunction(S);
396 }
397
printLeft(OutputStream & S) const398 void printLeft(OutputStream &S) const override {
399 Child->printLeft(S);
400 printQuals(S);
401 }
402
printRight(OutputStream & S) const403 void printRight(OutputStream &S) const override { Child->printRight(S); }
404 };
405
406 class ConversionOperatorType final : public Node {
407 const Node *Ty;
408
409 public:
ConversionOperatorType(Node * Ty_)410 ConversionOperatorType(Node *Ty_)
411 : Node(KConversionOperatorType, Ty_->ParameterPackSize), Ty(Ty_) {}
412
printLeft(OutputStream & S) const413 void printLeft(OutputStream &S) const override {
414 S += "operator ";
415 Ty->print(S);
416 }
417 };
418
419 class PostfixQualifiedType final : public Node {
420 const Node *Ty;
421 const StringView Postfix;
422
423 public:
PostfixQualifiedType(Node * Ty_,StringView Postfix_)424 PostfixQualifiedType(Node *Ty_, StringView Postfix_)
425 : Node(KPostfixQualifiedType, Ty_->ParameterPackSize),
426 Ty(Ty_), Postfix(Postfix_) {}
427
printLeft(OutputStream & s) const428 void printLeft(OutputStream &s) const override {
429 Ty->printLeft(s);
430 s += Postfix;
431 }
432 };
433
434 class NameType final : public Node {
435 const StringView Name;
436
437 public:
NameType(StringView Name_)438 NameType(StringView Name_) : Node(KNameType), Name(Name_) {}
439
getName() const440 StringView getName() const { return Name; }
getBaseName() const441 StringView getBaseName() const override { return Name; }
442
printLeft(OutputStream & s) const443 void printLeft(OutputStream &s) const override { s += Name; }
444 };
445
446 class AbiTagAttr final : public Node {
447 const Node* Base;
448 StringView Tag;
449 public:
AbiTagAttr(const Node * Base_,StringView Tag_)450 AbiTagAttr(const Node* Base_, StringView Tag_)
451 : Node(KAbiTagAttr, Base_->ParameterPackSize, Base_->RHSComponentCache,
452 Base_->ArrayCache, Base_->FunctionCache),
453 Base(Base_), Tag(Tag_) {}
454
printLeft(OutputStream & S) const455 void printLeft(OutputStream &S) const override {
456 Base->printLeft(S);
457 S += "[abi:";
458 S += Tag;
459 S += "]";
460 }
461 };
462
463 class ObjCProtoName : public Node {
464 Node *Ty;
465 StringView Protocol;
466
467 friend class PointerType;
468
469 public:
ObjCProtoName(Node * Ty_,StringView Protocol_)470 ObjCProtoName(Node *Ty_, StringView Protocol_)
471 : Node(KObjCProtoName), Ty(Ty_), Protocol(Protocol_) {}
472
isObjCObject() const473 bool isObjCObject() const {
474 return Ty->getKind() == KNameType &&
475 static_cast<NameType *>(Ty)->getName() == "objc_object";
476 }
477
printLeft(OutputStream & S) const478 void printLeft(OutputStream &S) const override {
479 Ty->print(S);
480 S += "<";
481 S += Protocol;
482 S += ">";
483 }
484 };
485
486 class PointerType final : public Node {
487 const Node *Pointee;
488
489 public:
PointerType(Node * Pointee_)490 PointerType(Node *Pointee_)
491 : Node(KPointerType, Pointee_->ParameterPackSize,
492 Pointee_->RHSComponentCache),
493 Pointee(Pointee_) {}
494
hasRHSComponentSlow(OutputStream & S) const495 bool hasRHSComponentSlow(OutputStream &S) const override {
496 return Pointee->hasRHSComponent(S);
497 }
498
printLeft(OutputStream & s) const499 void printLeft(OutputStream &s) const override {
500 // We rewrite objc_object<SomeProtocol>* into id<SomeProtocol>.
501 if (Pointee->getKind() != KObjCProtoName ||
502 !static_cast<const ObjCProtoName *>(Pointee)->isObjCObject()) {
503 Pointee->printLeft(s);
504 if (Pointee->hasArray(s))
505 s += " ";
506 if (Pointee->hasArray(s) || Pointee->hasFunction(s))
507 s += "(";
508 s += "*";
509 } else {
510 const auto *objcProto = static_cast<const ObjCProtoName *>(Pointee);
511 s += "id<";
512 s += objcProto->Protocol;
513 s += ">";
514 }
515 }
516
printRight(OutputStream & s) const517 void printRight(OutputStream &s) const override {
518 if (Pointee->getKind() != KObjCProtoName ||
519 !static_cast<const ObjCProtoName *>(Pointee)->isObjCObject()) {
520 if (Pointee->hasArray(s) || Pointee->hasFunction(s))
521 s += ")";
522 Pointee->printRight(s);
523 }
524 }
525 };
526
527 class LValueReferenceType final : public Node {
528 const Node *Pointee;
529
530 public:
LValueReferenceType(Node * Pointee_)531 LValueReferenceType(Node *Pointee_)
532 : Node(KLValueReferenceType, Pointee_->ParameterPackSize,
533 Pointee_->RHSComponentCache),
534 Pointee(Pointee_) {}
535
hasRHSComponentSlow(OutputStream & S) const536 bool hasRHSComponentSlow(OutputStream &S) const override {
537 return Pointee->hasRHSComponent(S);
538 }
539
printLeft(OutputStream & s) const540 void printLeft(OutputStream &s) const override {
541 Pointee->printLeft(s);
542 if (Pointee->hasArray(s))
543 s += " ";
544 if (Pointee->hasArray(s) || Pointee->hasFunction(s))
545 s += "(&";
546 else
547 s += "&";
548 }
printRight(OutputStream & s) const549 void printRight(OutputStream &s) const override {
550 if (Pointee->hasArray(s) || Pointee->hasFunction(s))
551 s += ")";
552 Pointee->printRight(s);
553 }
554 };
555
556 class RValueReferenceType final : public Node {
557 const Node *Pointee;
558
559 public:
RValueReferenceType(Node * Pointee_)560 RValueReferenceType(Node *Pointee_)
561 : Node(KRValueReferenceType, Pointee_->ParameterPackSize,
562 Pointee_->RHSComponentCache),
563 Pointee(Pointee_) {}
564
hasRHSComponentSlow(OutputStream & S) const565 bool hasRHSComponentSlow(OutputStream &S) const override {
566 return Pointee->hasRHSComponent(S);
567 }
568
printLeft(OutputStream & s) const569 void printLeft(OutputStream &s) const override {
570 Pointee->printLeft(s);
571 if (Pointee->hasArray(s))
572 s += " ";
573 if (Pointee->hasArray(s) || Pointee->hasFunction(s))
574 s += "(&&";
575 else
576 s += "&&";
577 }
578
printRight(OutputStream & s) const579 void printRight(OutputStream &s) const override {
580 if (Pointee->hasArray(s) || Pointee->hasFunction(s))
581 s += ")";
582 Pointee->printRight(s);
583 }
584 };
585
586 class PointerToMemberType final : public Node {
587 const Node *ClassType;
588 const Node *MemberType;
589
590 public:
PointerToMemberType(Node * ClassType_,Node * MemberType_)591 PointerToMemberType(Node *ClassType_, Node *MemberType_)
592 : Node(KPointerToMemberType,
593 std::min(MemberType_->ParameterPackSize,
594 ClassType_->ParameterPackSize),
595 MemberType_->RHSComponentCache),
596 ClassType(ClassType_), MemberType(MemberType_) {}
597
hasRHSComponentSlow(OutputStream & S) const598 bool hasRHSComponentSlow(OutputStream &S) const override {
599 return MemberType->hasRHSComponent(S);
600 }
601
printLeft(OutputStream & s) const602 void printLeft(OutputStream &s) const override {
603 MemberType->printLeft(s);
604 if (MemberType->hasArray(s) || MemberType->hasFunction(s))
605 s += "(";
606 else
607 s += " ";
608 ClassType->print(s);
609 s += "::*";
610 }
611
printRight(OutputStream & s) const612 void printRight(OutputStream &s) const override {
613 if (MemberType->hasArray(s) || MemberType->hasFunction(s))
614 s += ")";
615 MemberType->printRight(s);
616 }
617 };
618
619 class NodeOrString {
620 const void *First;
621 const void *Second;
622
623 public:
NodeOrString(StringView Str)624 /* implicit */ NodeOrString(StringView Str) {
625 const char *FirstChar = Str.begin();
626 const char *SecondChar = Str.end();
627 if (SecondChar == nullptr) {
628 assert(FirstChar == SecondChar);
629 ++FirstChar, ++SecondChar;
630 }
631 First = static_cast<const void *>(FirstChar);
632 Second = static_cast<const void *>(SecondChar);
633 }
634
NodeOrString(Node * N)635 /* implicit */ NodeOrString(Node *N)
636 : First(static_cast<const void *>(N)), Second(nullptr) {}
NodeOrString()637 NodeOrString() : First(nullptr), Second(nullptr) {}
638
isString() const639 bool isString() const { return Second && First; }
isNode() const640 bool isNode() const { return First && !Second; }
isEmpty() const641 bool isEmpty() const { return !First && !Second; }
642
asString() const643 StringView asString() const {
644 assert(isString());
645 return StringView(static_cast<const char *>(First),
646 static_cast<const char *>(Second));
647 }
648
asNode() const649 const Node *asNode() const {
650 assert(isNode());
651 return static_cast<const Node *>(First);
652 }
653 };
654
655 class ArrayType final : public Node {
656 Node *Base;
657 NodeOrString Dimension;
658
659 public:
ArrayType(Node * Base_,NodeOrString Dimension_)660 ArrayType(Node *Base_, NodeOrString Dimension_)
661 : Node(KArrayType, Base_->ParameterPackSize,
662 /*RHSComponentCache=*/Cache::Yes,
663 /*ArrayCache=*/Cache::Yes),
664 Base(Base_), Dimension(Dimension_) {
665 if (Dimension.isNode())
666 ParameterPackSize =
667 std::min(ParameterPackSize, Dimension.asNode()->ParameterPackSize);
668 }
669
670 // Incomplete array type.
ArrayType(Node * Base_)671 ArrayType(Node *Base_)
672 : Node(KArrayType, Base_->ParameterPackSize,
673 /*RHSComponentCache=*/Cache::Yes,
674 /*ArrayCache=*/Cache::Yes),
675 Base(Base_) {}
676
hasRHSComponentSlow(OutputStream &) const677 bool hasRHSComponentSlow(OutputStream &) const override { return true; }
hasArraySlow(OutputStream &) const678 bool hasArraySlow(OutputStream &) const override { return true; }
679
printLeft(OutputStream & S) const680 void printLeft(OutputStream &S) const override { Base->printLeft(S); }
681
printRight(OutputStream & S) const682 void printRight(OutputStream &S) const override {
683 if (S.back() != ']')
684 S += " ";
685 S += "[";
686 if (Dimension.isString())
687 S += Dimension.asString();
688 else if (Dimension.isNode())
689 Dimension.asNode()->print(S);
690 S += "]";
691 Base->printRight(S);
692 }
693 };
694
695 class FunctionType final : public Node {
696 Node *Ret;
697 NodeArray Params;
698
699 public:
FunctionType(Node * Ret_,NodeArray Params_)700 FunctionType(Node *Ret_, NodeArray Params_)
701 : Node(KFunctionType, Ret_->ParameterPackSize,
702 /*RHSComponentCache=*/Cache::Yes, /*ArrayCache=*/Cache::No,
703 /*FunctionCache=*/Cache::Yes),
704 Ret(Ret_), Params(Params_) {
705 for (Node *P : Params)
706 ParameterPackSize = std::min(ParameterPackSize, P->ParameterPackSize);
707 }
708
hasRHSComponentSlow(OutputStream &) const709 bool hasRHSComponentSlow(OutputStream &) const override { return true; }
hasFunctionSlow(OutputStream &) const710 bool hasFunctionSlow(OutputStream &) const override { return true; }
711
712 // Handle C++'s ... quirky decl grammer by using the left & right
713 // distinction. Consider:
714 // int (*f(float))(char) {}
715 // f is a function that takes a float and returns a pointer to a function
716 // that takes a char and returns an int. If we're trying to print f, start
717 // by printing out the return types's left, then print our parameters, then
718 // finally print right of the return type.
printLeft(OutputStream & S) const719 void printLeft(OutputStream &S) const override {
720 Ret->printLeft(S);
721 S += " ";
722 }
723
printRight(OutputStream & S) const724 void printRight(OutputStream &S) const override {
725 S += "(";
726 Params.printWithComma(S);
727 S += ")";
728 Ret->printRight(S);
729 }
730 };
731
732 class FunctionEncoding final : public Node {
733 const Node *Ret;
734 const Node *Name;
735 NodeArray Params;
736
737 public:
FunctionEncoding(Node * Ret_,Node * Name_,NodeArray Params_)738 FunctionEncoding(Node *Ret_, Node *Name_, NodeArray Params_)
739 : Node(KFunctionEncoding, NoParameterPack,
740 /*RHSComponentCache=*/Cache::Yes, /*ArrayCache=*/Cache::No,
741 /*FunctionCache=*/Cache::Yes),
742 Ret(Ret_), Name(Name_), Params(Params_) {
743 for (Node *P : Params)
744 ParameterPackSize = std::min(ParameterPackSize, P->ParameterPackSize);
745 if (Ret)
746 ParameterPackSize = std::min(ParameterPackSize, Ret->ParameterPackSize);
747 }
748
hasRHSComponentSlow(OutputStream &) const749 bool hasRHSComponentSlow(OutputStream &) const override { return true; }
hasFunctionSlow(OutputStream &) const750 bool hasFunctionSlow(OutputStream &) const override { return true; }
751
getName()752 Node *getName() { return const_cast<Node *>(Name); }
753
printLeft(OutputStream & S) const754 void printLeft(OutputStream &S) const override {
755 if (Ret) {
756 Ret->printLeft(S);
757 if (!Ret->hasRHSComponent(S))
758 S += " ";
759 }
760 Name->print(S);
761 }
762
printRight(OutputStream & S) const763 void printRight(OutputStream &S) const override {
764 S += "(";
765 Params.printWithComma(S);
766 S += ")";
767 if (Ret)
768 Ret->printRight(S);
769 }
770 };
771
772 enum FunctionRefQual : unsigned char {
773 FrefQualNone,
774 FrefQualLValue,
775 FrefQualRValue,
776 };
777
778 class FunctionRefQualType : public Node {
779 Node *Fn;
780 FunctionRefQual Quals;
781
782 friend class FunctionQualType;
783
784 public:
FunctionRefQualType(Node * Fn_,FunctionRefQual Quals_)785 FunctionRefQualType(Node *Fn_, FunctionRefQual Quals_)
786 : Node(KFunctionRefQualType, Fn_->ParameterPackSize,
787 /*RHSComponentCache=*/Cache::Yes, /*ArrayCache=*/Cache::No,
788 /*FunctionCache=*/Cache::Yes),
789 Fn(Fn_), Quals(Quals_) {}
790
hasFunctionSlow(OutputStream &) const791 bool hasFunctionSlow(OutputStream &) const override { return true; }
hasRHSComponentSlow(OutputStream &) const792 bool hasRHSComponentSlow(OutputStream &) const override { return true; }
793
printQuals(OutputStream & S) const794 void printQuals(OutputStream &S) const {
795 if (Quals == FrefQualLValue)
796 S += " &";
797 else
798 S += " &&";
799 }
800
printLeft(OutputStream & S) const801 void printLeft(OutputStream &S) const override { Fn->printLeft(S); }
802
printRight(OutputStream & S) const803 void printRight(OutputStream &S) const override {
804 Fn->printRight(S);
805 printQuals(S);
806 }
807 };
808
809 class FunctionQualType final : public QualType {
810 public:
FunctionQualType(Node * Child_,Qualifiers Quals_)811 FunctionQualType(Node *Child_, Qualifiers Quals_)
812 : QualType(Child_, Quals_) {
813 K = KFunctionQualType;
814 }
815
printLeft(OutputStream & S) const816 void printLeft(OutputStream &S) const override { Child->printLeft(S); }
817
printRight(OutputStream & S) const818 void printRight(OutputStream &S) const override {
819 if (Child->getKind() == KFunctionRefQualType) {
820 auto *RefQuals = static_cast<const FunctionRefQualType *>(Child);
821 RefQuals->Fn->printRight(S);
822 printQuals(S);
823 RefQuals->printQuals(S);
824 } else {
825 Child->printRight(S);
826 printQuals(S);
827 }
828 }
829 };
830
831 class LiteralOperator : public Node {
832 const Node *OpName;
833
834 public:
LiteralOperator(Node * OpName_)835 LiteralOperator(Node *OpName_)
836 : Node(KLiteralOperator, OpName_->ParameterPackSize), OpName(OpName_) {}
837
printLeft(OutputStream & S) const838 void printLeft(OutputStream &S) const override {
839 S += "operator\"\" ";
840 OpName->print(S);
841 }
842 };
843
844 class SpecialName final : public Node {
845 const StringView Special;
846 const Node *Child;
847
848 public:
SpecialName(StringView Special_,Node * Child_)849 SpecialName(StringView Special_, Node* Child_)
850 : Node(KSpecialName, Child_->ParameterPackSize), Special(Special_),
851 Child(Child_) {}
852
printLeft(OutputStream & S) const853 void printLeft(OutputStream &S) const override {
854 S += Special;
855 Child->print(S);
856 }
857 };
858
859 class CtorVtableSpecialName final : public Node {
860 const Node *FirstType;
861 const Node *SecondType;
862
863 public:
CtorVtableSpecialName(Node * FirstType_,Node * SecondType_)864 CtorVtableSpecialName(Node *FirstType_, Node *SecondType_)
865 : Node(KCtorVtableSpecialName, std::min(FirstType_->ParameterPackSize,
866 SecondType_->ParameterPackSize)),
867 FirstType(FirstType_), SecondType(SecondType_) {}
868
printLeft(OutputStream & S) const869 void printLeft(OutputStream &S) const override {
870 S += "construction vtable for ";
871 FirstType->print(S);
872 S += "-in-";
873 SecondType->print(S);
874 }
875 };
876
877 class QualifiedName final : public Node {
878 // qualifier::name
879 const Node *Qualifier;
880 const Node *Name;
881
882 public:
QualifiedName(Node * Qualifier_,Node * Name_)883 QualifiedName(Node* Qualifier_, Node* Name_)
884 : Node(KQualifiedName,
885 std::min(Qualifier_->ParameterPackSize, Name_->ParameterPackSize)),
886 Qualifier(Qualifier_), Name(Name_) {}
887
getBaseName() const888 StringView getBaseName() const override { return Name->getBaseName(); }
889
printLeft(OutputStream & S) const890 void printLeft(OutputStream &S) const override {
891 Qualifier->print(S);
892 S += "::";
893 Name->print(S);
894 }
895 };
896
897 class EmptyName : public Node {
898 public:
EmptyName()899 EmptyName() : Node(KEmptyName) {}
printLeft(OutputStream &) const900 void printLeft(OutputStream &) const override {}
901 };
902
903 class VectorType final : public Node {
904 const Node *BaseType;
905 const NodeOrString Dimension;
906 const bool IsPixel;
907
908 public:
VectorType(NodeOrString Dimension_)909 VectorType(NodeOrString Dimension_)
910 : Node(KVectorType), BaseType(nullptr), Dimension(Dimension_),
911 IsPixel(true) {
912 if (Dimension.isNode())
913 ParameterPackSize = Dimension.asNode()->ParameterPackSize;
914 }
VectorType(Node * BaseType_,NodeOrString Dimension_)915 VectorType(Node *BaseType_, NodeOrString Dimension_)
916 : Node(KVectorType, BaseType_->ParameterPackSize), BaseType(BaseType_),
917 Dimension(Dimension_), IsPixel(false) {
918 if (Dimension.isNode())
919 ParameterPackSize =
920 std::min(ParameterPackSize, Dimension.asNode()->ParameterPackSize);
921 }
922
printLeft(OutputStream & S) const923 void printLeft(OutputStream &S) const override {
924 if (IsPixel) {
925 S += "pixel vector[";
926 S += Dimension.asString();
927 S += "]";
928 } else {
929 BaseType->print(S);
930 S += " vector[";
931 if (Dimension.isNode())
932 Dimension.asNode()->print(S);
933 else if (Dimension.isString())
934 S += Dimension.asString();
935 S += "]";
936 }
937 }
938 };
939
940 /// An unexpanded parameter pack (either in the expression or type context). If
941 /// this AST is correct, this node will have a ParameterPackExpansion node above
942 /// it.
943 ///
944 /// This node is created when some <template-args> are found that apply to an
945 /// <encoding>, and is stored in the TemplateParams table. In order for this to
946 /// appear in the final AST, it has to referenced via a <template-param> (ie,
947 /// T_).
948 class ParameterPack final : public Node {
949 NodeArray Data;
950 public:
ParameterPack(NodeArray Data_)951 ParameterPack(NodeArray Data_)
952 : Node(KParameterPack, static_cast<unsigned>(Data_.size())), Data(Data_) {
953 ArrayCache = FunctionCache = RHSComponentCache = Cache::Unknown;
954 if (std::all_of(Data.begin(), Data.end(), [](Node* P) {
955 return P->ArrayCache == Cache::No;
956 }))
957 ArrayCache = Cache::No;
958 if (std::all_of(Data.begin(), Data.end(), [](Node* P) {
959 return P->FunctionCache == Cache::No;
960 }))
961 FunctionCache = Cache::No;
962 if (std::all_of(Data.begin(), Data.end(), [](Node* P) {
963 return P->RHSComponentCache == Cache::No;
964 }))
965 RHSComponentCache = Cache::No;
966 }
967
hasRHSComponentSlow(OutputStream & S) const968 bool hasRHSComponentSlow(OutputStream &S) const override {
969 size_t Idx = S.CurrentPackIndex;
970 return Idx < Data.size() && Data[Idx]->hasRHSComponent(S);
971 }
hasArraySlow(OutputStream & S) const972 bool hasArraySlow(OutputStream &S) const override {
973 size_t Idx = S.CurrentPackIndex;
974 return Idx < Data.size() && Data[Idx]->hasArray(S);
975 }
hasFunctionSlow(OutputStream & S) const976 bool hasFunctionSlow(OutputStream &S) const override {
977 size_t Idx = S.CurrentPackIndex;
978 return Idx < Data.size() && Data[Idx]->hasFunction(S);
979 }
980
printLeft(OutputStream & S) const981 void printLeft(OutputStream &S) const override {
982 size_t Idx = S.CurrentPackIndex;
983 if (Idx < Data.size())
984 Data[Idx]->printLeft(S);
985 }
printRight(OutputStream & S) const986 void printRight(OutputStream &S) const override {
987 size_t Idx = S.CurrentPackIndex;
988 if (Idx < Data.size())
989 Data[Idx]->printRight(S);
990 }
991 };
992
993 /// A variadic template argument. This node represents an occurance of
994 /// J<something>E in some <template-args>. It isn't itself unexpanded, unless
995 /// one of it's Elements is. The parser inserts a ParameterPack into the
996 /// TemplateParams table if the <template-args> this pack belongs to apply to an
997 /// <encoding>.
998 class TemplateArgumentPack final : public Node {
999 NodeArray Elements;
1000 public:
TemplateArgumentPack(NodeArray Elements_)1001 TemplateArgumentPack(NodeArray Elements_)
1002 : Node(KTemplateArgumentPack), Elements(Elements_) {
1003 for (Node *E : Elements)
1004 ParameterPackSize = std::min(E->ParameterPackSize, ParameterPackSize);
1005 }
1006
getElements() const1007 NodeArray getElements() const { return Elements; }
1008
printLeft(OutputStream & S) const1009 void printLeft(OutputStream &S) const override {
1010 Elements.printWithComma(S);
1011 }
1012 };
1013
1014 /// A pack expansion. Below this node, there are some unexpanded ParameterPacks
1015 /// which each have Child->ParameterPackSize elements.
1016 class ParameterPackExpansion final : public Node {
1017 const Node *Child;
1018
1019 public:
ParameterPackExpansion(Node * Child_)1020 ParameterPackExpansion(Node* Child_)
1021 : Node(KParameterPackExpansion), Child(Child_) {}
1022
getChild() const1023 const Node *getChild() const { return Child; }
1024
printLeft(OutputStream & S) const1025 void printLeft(OutputStream &S) const override {
1026 unsigned PackSize = Child->ParameterPackSize;
1027 if (PackSize == NoParameterPack) {
1028 Child->print(S);
1029 S += "...";
1030 return;
1031 }
1032
1033 SwapAndRestore<unsigned> SavePackIndex(S.CurrentPackIndex, 0);
1034 for (unsigned I = 0; I != PackSize; ++I) {
1035 if (I != 0)
1036 S += ", ";
1037 S.CurrentPackIndex = I;
1038 Child->print(S);
1039 }
1040 }
1041 };
1042
isEmptyPackExpansion() const1043 inline bool Node::isEmptyPackExpansion() const {
1044 if (getKind() == KParameterPackExpansion) {
1045 auto *AsPack = static_cast<const ParameterPackExpansion *>(this);
1046 return AsPack->getChild()->isEmptyPackExpansion();
1047 }
1048 if (getKind() == KTemplateArgumentPack) {
1049 auto *AsTemplateArg = static_cast<const TemplateArgumentPack *>(this);
1050 for (Node *E : AsTemplateArg->getElements())
1051 if (!E->isEmptyPackExpansion())
1052 return false;
1053 return true;
1054 }
1055 return ParameterPackSize == 0;
1056 }
1057
1058 class TemplateArgs final : public Node {
1059 NodeArray Params;
1060
1061 public:
TemplateArgs(NodeArray Params_)1062 TemplateArgs(NodeArray Params_) : Node(KTemplateArgs), Params(Params_) {
1063 for (Node *P : Params)
1064 ParameterPackSize = std::min(ParameterPackSize, P->ParameterPackSize);
1065 }
1066
getParams()1067 NodeArray getParams() { return Params; }
1068
printLeft(OutputStream & S) const1069 void printLeft(OutputStream &S) const override {
1070 S += "<";
1071 bool FirstElement = true;
1072 for (size_t Idx = 0, E = Params.size(); Idx != E; ++Idx) {
1073 if (Params[Idx]->isEmptyPackExpansion())
1074 continue;
1075 if (!FirstElement)
1076 S += ", ";
1077 FirstElement = false;
1078 Params[Idx]->print(S);
1079 }
1080 if (S.back() == '>')
1081 S += " ";
1082 S += ">";
1083 }
1084 };
1085
1086 class NameWithTemplateArgs final : public Node {
1087 // name<template_args>
1088 Node *Name;
1089 Node *TemplateArgs;
1090
1091 public:
NameWithTemplateArgs(Node * Name_,Node * TemplateArgs_)1092 NameWithTemplateArgs(Node *Name_, Node *TemplateArgs_)
1093 : Node(KNameWithTemplateArgs, std::min(Name_->ParameterPackSize,
1094 TemplateArgs_->ParameterPackSize)),
1095 Name(Name_), TemplateArgs(TemplateArgs_) {}
1096
getBaseName() const1097 StringView getBaseName() const override { return Name->getBaseName(); }
1098
printLeft(OutputStream & S) const1099 void printLeft(OutputStream &S) const override {
1100 Name->print(S);
1101 TemplateArgs->print(S);
1102 }
1103 };
1104
1105 class GlobalQualifiedName final : public Node {
1106 Node *Child;
1107
1108 public:
GlobalQualifiedName(Node * Child_)1109 GlobalQualifiedName(Node* Child_)
1110 : Node(KGlobalQualifiedName, Child_->ParameterPackSize), Child(Child_) {}
1111
getBaseName() const1112 StringView getBaseName() const override { return Child->getBaseName(); }
1113
printLeft(OutputStream & S) const1114 void printLeft(OutputStream &S) const override {
1115 S += "::";
1116 Child->print(S);
1117 }
1118 };
1119
1120 class StdQualifiedName final : public Node {
1121 Node *Child;
1122
1123 public:
StdQualifiedName(Node * Child_)1124 StdQualifiedName(Node *Child_)
1125 : Node(KStdQualifiedName, Child_->ParameterPackSize), Child(Child_) {}
1126
getBaseName() const1127 StringView getBaseName() const override { return Child->getBaseName(); }
1128
printLeft(OutputStream & S) const1129 void printLeft(OutputStream &S) const override {
1130 S += "std::";
1131 Child->print(S);
1132 }
1133 };
1134
1135 enum class SpecialSubKind {
1136 allocator,
1137 basic_string,
1138 string,
1139 istream,
1140 ostream,
1141 iostream,
1142 };
1143
1144 class ExpandedSpecialSubstitution final : public Node {
1145 SpecialSubKind SSK;
1146
1147 public:
ExpandedSpecialSubstitution(SpecialSubKind SSK_)1148 ExpandedSpecialSubstitution(SpecialSubKind SSK_)
1149 : Node(KExpandedSpecialSubstitution), SSK(SSK_) {}
1150
getBaseName() const1151 StringView getBaseName() const override {
1152 switch (SSK) {
1153 case SpecialSubKind::allocator:
1154 return StringView("allocator");
1155 case SpecialSubKind::basic_string:
1156 return StringView("basic_string");
1157 case SpecialSubKind::string:
1158 return StringView("basic_string");
1159 case SpecialSubKind::istream:
1160 return StringView("basic_istream");
1161 case SpecialSubKind::ostream:
1162 return StringView("basic_ostream");
1163 case SpecialSubKind::iostream:
1164 return StringView("basic_iostream");
1165 }
1166 _LIBCPP_UNREACHABLE();
1167 }
1168
printLeft(OutputStream & S) const1169 void printLeft(OutputStream &S) const override {
1170 switch (SSK) {
1171 case SpecialSubKind::allocator:
1172 S += "std::basic_string<char, std::char_traits<char>, "
1173 "std::allocator<char> >";
1174 break;
1175 case SpecialSubKind::basic_string:
1176 case SpecialSubKind::string:
1177 S += "std::basic_string<char, std::char_traits<char>, "
1178 "std::allocator<char> >";
1179 break;
1180 case SpecialSubKind::istream:
1181 S += "std::basic_istream<char, std::char_traits<char> >";
1182 break;
1183 case SpecialSubKind::ostream:
1184 S += "std::basic_ostream<char, std::char_traits<char> >";
1185 break;
1186 case SpecialSubKind::iostream:
1187 S += "std::basic_iostream<char, std::char_traits<char> >";
1188 break;
1189 }
1190 }
1191 };
1192
1193 class SpecialSubstitution final : public Node {
1194 public:
1195 SpecialSubKind SSK;
1196
SpecialSubstitution(SpecialSubKind SSK_)1197 SpecialSubstitution(SpecialSubKind SSK_)
1198 : Node(KSpecialSubstitution), SSK(SSK_) {}
1199
getBaseName() const1200 StringView getBaseName() const override {
1201 switch (SSK) {
1202 case SpecialSubKind::allocator:
1203 return StringView("allocator");
1204 case SpecialSubKind::basic_string:
1205 return StringView("basic_string");
1206 case SpecialSubKind::string:
1207 return StringView("string");
1208 case SpecialSubKind::istream:
1209 return StringView("istream");
1210 case SpecialSubKind::ostream:
1211 return StringView("ostream");
1212 case SpecialSubKind::iostream:
1213 return StringView("iostream");
1214 }
1215 _LIBCPP_UNREACHABLE();
1216 }
1217
printLeft(OutputStream & S) const1218 void printLeft(OutputStream &S) const override {
1219 switch (SSK) {
1220 case SpecialSubKind::allocator:
1221 S += "std::allocator";
1222 break;
1223 case SpecialSubKind::basic_string:
1224 S += "std::basic_string";
1225 break;
1226 case SpecialSubKind::string:
1227 S += "std::string";
1228 break;
1229 case SpecialSubKind::istream:
1230 S += "std::istream";
1231 break;
1232 case SpecialSubKind::ostream:
1233 S += "std::ostream";
1234 break;
1235 case SpecialSubKind::iostream:
1236 S += "std::iostream";
1237 break;
1238 }
1239 }
1240 };
1241
1242 class CtorDtorName final : public Node {
1243 const Node *Basename;
1244 const bool IsDtor;
1245
1246 public:
CtorDtorName(Node * Basename_,bool IsDtor_)1247 CtorDtorName(Node *Basename_, bool IsDtor_)
1248 : Node(KCtorDtorName, Basename_->ParameterPackSize),
1249 Basename(Basename_), IsDtor(IsDtor_) {}
1250
printLeft(OutputStream & S) const1251 void printLeft(OutputStream &S) const override {
1252 if (IsDtor)
1253 S += "~";
1254 S += Basename->getBaseName();
1255 }
1256 };
1257
1258 class DtorName : public Node {
1259 const Node *Base;
1260
1261 public:
DtorName(Node * Base_)1262 DtorName(Node *Base_) : Node(KDtorName), Base(Base_) {
1263 ParameterPackSize = Base->ParameterPackSize;
1264 }
1265
printLeft(OutputStream & S) const1266 void printLeft(OutputStream &S) const override {
1267 S += "~";
1268 Base->printLeft(S);
1269 }
1270 };
1271
1272 class UnnamedTypeName : public Node {
1273 const StringView Count;
1274
1275 public:
UnnamedTypeName(StringView Count_)1276 UnnamedTypeName(StringView Count_) : Node(KUnnamedTypeName), Count(Count_) {}
1277
printLeft(OutputStream & S) const1278 void printLeft(OutputStream &S) const override {
1279 S += "'unnamed";
1280 S += Count;
1281 S += "\'";
1282 }
1283 };
1284
1285 class LambdaTypeName : public Node {
1286 NodeArray Params;
1287 StringView Count;
1288
1289 public:
LambdaTypeName(NodeArray Params_,StringView Count_)1290 LambdaTypeName(NodeArray Params_, StringView Count_)
1291 : Node(KLambdaTypeName), Params(Params_), Count(Count_) {
1292 for (Node *P : Params)
1293 ParameterPackSize = std::min(ParameterPackSize, P->ParameterPackSize);
1294 }
1295
printLeft(OutputStream & S) const1296 void printLeft(OutputStream &S) const override {
1297 S += "\'lambda";
1298 S += Count;
1299 S += "\'(";
1300 Params.printWithComma(S);
1301 S += ")";
1302 }
1303 };
1304
1305 // -- Expression Nodes --
1306
1307 struct Expr : public Node {
Expr__anon9d46d5f30111::Expr1308 Expr() : Node(KExpr) {}
1309 };
1310
1311 class BinaryExpr : public Expr {
1312 const Node *LHS;
1313 const StringView InfixOperator;
1314 const Node *RHS;
1315
1316 public:
BinaryExpr(Node * LHS_,StringView InfixOperator_,Node * RHS_)1317 BinaryExpr(Node *LHS_, StringView InfixOperator_, Node *RHS_)
1318 : LHS(LHS_), InfixOperator(InfixOperator_), RHS(RHS_) {
1319 ParameterPackSize =
1320 std::min(LHS->ParameterPackSize, RHS->ParameterPackSize);
1321 }
1322
printLeft(OutputStream & S) const1323 void printLeft(OutputStream &S) const override {
1324 // might be a template argument expression, then we need to disambiguate
1325 // with parens.
1326 if (InfixOperator == ">")
1327 S += "(";
1328
1329 S += "(";
1330 LHS->print(S);
1331 S += ") ";
1332 S += InfixOperator;
1333 S += " (";
1334 RHS->print(S);
1335 S += ")";
1336
1337 if (InfixOperator == ">")
1338 S += ")";
1339 }
1340 };
1341
1342 class ArraySubscriptExpr : public Expr {
1343 const Node *Op1;
1344 const Node *Op2;
1345
1346 public:
ArraySubscriptExpr(Node * Op1_,Node * Op2_)1347 ArraySubscriptExpr(Node *Op1_, Node *Op2_) : Op1(Op1_), Op2(Op2_) {
1348 ParameterPackSize =
1349 std::min(Op1->ParameterPackSize, Op2->ParameterPackSize);
1350 }
1351
printLeft(OutputStream & S) const1352 void printLeft(OutputStream &S) const override {
1353 S += "(";
1354 Op1->print(S);
1355 S += ")[";
1356 Op2->print(S);
1357 S += "]";
1358 }
1359 };
1360
1361 class PostfixExpr : public Expr {
1362 const Node *Child;
1363 const StringView Operand;
1364
1365 public:
PostfixExpr(Node * Child_,StringView Operand_)1366 PostfixExpr(Node *Child_, StringView Operand_)
1367 : Child(Child_), Operand(Operand_) {
1368 ParameterPackSize = Child->ParameterPackSize;
1369 }
1370
printLeft(OutputStream & S) const1371 void printLeft(OutputStream &S) const override {
1372 S += "(";
1373 Child->print(S);
1374 S += ")";
1375 S += Operand;
1376 }
1377 };
1378
1379 class ConditionalExpr : public Expr {
1380 const Node *Cond;
1381 const Node *Then;
1382 const Node *Else;
1383
1384 public:
ConditionalExpr(Node * Cond_,Node * Then_,Node * Else_)1385 ConditionalExpr(Node *Cond_, Node *Then_, Node *Else_)
1386 : Cond(Cond_), Then(Then_), Else(Else_) {
1387 ParameterPackSize =
1388 std::min(Cond->ParameterPackSize,
1389 std::min(Then->ParameterPackSize, Else->ParameterPackSize));
1390 }
1391
printLeft(OutputStream & S) const1392 void printLeft(OutputStream &S) const override {
1393 S += "(";
1394 Cond->print(S);
1395 S += ") ? (";
1396 Then->print(S);
1397 S += ") : (";
1398 Else->print(S);
1399 S += ")";
1400 }
1401 };
1402
1403 class MemberExpr : public Expr {
1404 const Node *LHS;
1405 const StringView Kind;
1406 const Node *RHS;
1407
1408 public:
MemberExpr(Node * LHS_,StringView Kind_,Node * RHS_)1409 MemberExpr(Node *LHS_, StringView Kind_, Node *RHS_)
1410 : LHS(LHS_), Kind(Kind_), RHS(RHS_) {
1411 ParameterPackSize =
1412 std::min(LHS->ParameterPackSize, RHS->ParameterPackSize);
1413 }
1414
printLeft(OutputStream & S) const1415 void printLeft(OutputStream &S) const override {
1416 LHS->print(S);
1417 S += Kind;
1418 RHS->print(S);
1419 }
1420 };
1421
1422 class EnclosingExpr : public Expr {
1423 const StringView Prefix;
1424 const Node *Infix;
1425 const StringView Postfix;
1426
1427 public:
EnclosingExpr(StringView Prefix_,Node * Infix_,StringView Postfix_)1428 EnclosingExpr(StringView Prefix_, Node *Infix_, StringView Postfix_)
1429 : Prefix(Prefix_), Infix(Infix_), Postfix(Postfix_) {
1430 ParameterPackSize = Infix->ParameterPackSize;
1431 }
1432
printLeft(OutputStream & S) const1433 void printLeft(OutputStream &S) const override {
1434 S += Prefix;
1435 Infix->print(S);
1436 S += Postfix;
1437 }
1438 };
1439
1440 class CastExpr : public Expr {
1441 // cast_kind<to>(from)
1442 const StringView CastKind;
1443 const Node *To;
1444 const Node *From;
1445
1446 public:
CastExpr(StringView CastKind_,Node * To_,Node * From_)1447 CastExpr(StringView CastKind_, Node *To_, Node *From_)
1448 : CastKind(CastKind_), To(To_), From(From_) {
1449 ParameterPackSize =
1450 std::min(To->ParameterPackSize, From->ParameterPackSize);
1451 }
1452
printLeft(OutputStream & S) const1453 void printLeft(OutputStream &S) const override {
1454 S += CastKind;
1455 S += "<";
1456 To->printLeft(S);
1457 S += ">(";
1458 From->printLeft(S);
1459 S += ")";
1460 }
1461 };
1462
1463 class SizeofParamPackExpr : public Expr {
1464 Node *Pack;
1465
1466 public:
SizeofParamPackExpr(Node * Pack_)1467 SizeofParamPackExpr(Node *Pack_) : Pack(Pack_) {}
1468
printLeft(OutputStream & S) const1469 void printLeft(OutputStream &S) const override {
1470 S += "sizeof...(";
1471 ParameterPackExpansion PPE(Pack);
1472 PPE.printLeft(S);
1473 S += ")";
1474 }
1475 };
1476
1477 class CallExpr : public Expr {
1478 const Node *Callee;
1479 NodeArray Args;
1480
1481 public:
CallExpr(Node * Callee_,NodeArray Args_)1482 CallExpr(Node *Callee_, NodeArray Args_) : Callee(Callee_), Args(Args_) {
1483 for (Node *P : Args)
1484 ParameterPackSize = std::min(ParameterPackSize, P->ParameterPackSize);
1485 ParameterPackSize = std::min(ParameterPackSize, Callee->ParameterPackSize);
1486 }
1487
printLeft(OutputStream & S) const1488 void printLeft(OutputStream &S) const override {
1489 Callee->print(S);
1490 S += "(";
1491 Args.printWithComma(S);
1492 S += ")";
1493 }
1494 };
1495
1496 class NewExpr : public Expr {
1497 // new (expr_list) type(init_list)
1498 NodeArray ExprList;
1499 Node *Type;
1500 NodeArray InitList;
1501 bool IsGlobal; // ::operator new ?
1502 bool IsArray; // new[] ?
1503 public:
NewExpr(NodeArray ExprList_,Node * Type_,NodeArray InitList_,bool IsGlobal_,bool IsArray_)1504 NewExpr(NodeArray ExprList_, Node *Type_, NodeArray InitList_, bool IsGlobal_,
1505 bool IsArray_)
1506 : ExprList(ExprList_), Type(Type_), InitList(InitList_),
1507 IsGlobal(IsGlobal_), IsArray(IsArray_) {
1508 for (Node *E : ExprList)
1509 ParameterPackSize = std::min(ParameterPackSize, E->ParameterPackSize);
1510 for (Node *I : InitList)
1511 ParameterPackSize = std::min(ParameterPackSize, I->ParameterPackSize);
1512 if (Type)
1513 ParameterPackSize = std::min(ParameterPackSize, Type->ParameterPackSize);
1514 }
1515
printLeft(OutputStream & S) const1516 void printLeft(OutputStream &S) const override {
1517 if (IsGlobal)
1518 S += "::operator ";
1519 S += "new";
1520 if (IsArray)
1521 S += "[]";
1522 S += ' ';
1523 if (!ExprList.empty()) {
1524 S += "(";
1525 ExprList.printWithComma(S);
1526 S += ")";
1527 }
1528 Type->print(S);
1529 if (!InitList.empty()) {
1530 S += "(";
1531 InitList.printWithComma(S);
1532 S += ")";
1533 }
1534
1535 }
1536 };
1537
1538 class DeleteExpr : public Expr {
1539 Node *Op;
1540 bool IsGlobal;
1541 bool IsArray;
1542
1543 public:
DeleteExpr(Node * Op_,bool IsGlobal_,bool IsArray_)1544 DeleteExpr(Node *Op_, bool IsGlobal_, bool IsArray_)
1545 : Op(Op_), IsGlobal(IsGlobal_), IsArray(IsArray_) {
1546 ParameterPackSize = Op->ParameterPackSize;
1547 }
1548
printLeft(OutputStream & S) const1549 void printLeft(OutputStream &S) const override {
1550 if (IsGlobal)
1551 S += "::";
1552 S += "delete";
1553 if (IsArray)
1554 S += "[] ";
1555 Op->print(S);
1556 }
1557 };
1558
1559 class PrefixExpr : public Expr {
1560 StringView Prefix;
1561 Node *Child;
1562
1563 public:
PrefixExpr(StringView Prefix_,Node * Child_)1564 PrefixExpr(StringView Prefix_, Node *Child_) : Prefix(Prefix_), Child(Child_) {
1565 ParameterPackSize = Child->ParameterPackSize;
1566 }
1567
printLeft(OutputStream & S) const1568 void printLeft(OutputStream &S) const override {
1569 S += Prefix;
1570 S += "(";
1571 Child->print(S);
1572 S += ")";
1573 }
1574 };
1575
1576 class FunctionParam : public Expr {
1577 StringView Number;
1578
1579 public:
FunctionParam(StringView Number_)1580 FunctionParam(StringView Number_) : Number(Number_) {}
1581
printLeft(OutputStream & S) const1582 void printLeft(OutputStream &S) const override {
1583 S += "fp";
1584 S += Number;
1585 }
1586 };
1587
1588 class ConversionExpr : public Expr {
1589 const Node *Type;
1590 NodeArray Expressions;
1591
1592 public:
ConversionExpr(const Node * Type_,NodeArray Expressions_)1593 ConversionExpr(const Node *Type_, NodeArray Expressions_)
1594 : Type(Type_), Expressions(Expressions_) {
1595 for (Node *E : Expressions)
1596 ParameterPackSize = std::min(ParameterPackSize, E->ParameterPackSize);
1597 ParameterPackSize = std::min(ParameterPackSize, Type->ParameterPackSize);
1598 }
1599
printLeft(OutputStream & S) const1600 void printLeft(OutputStream &S) const override {
1601 S += "(";
1602 Type->print(S);
1603 S += ")(";
1604 Expressions.printWithComma(S);
1605 S += ")";
1606 }
1607 };
1608
1609 class ThrowExpr : public Expr {
1610 const Node *Op;
1611
1612 public:
ThrowExpr(Node * Op_)1613 ThrowExpr(Node *Op_) : Op(Op_) {
1614 ParameterPackSize = Op->ParameterPackSize;
1615 }
1616
printLeft(OutputStream & S) const1617 void printLeft(OutputStream &S) const override {
1618 S += "throw ";
1619 Op->print(S);
1620 }
1621 };
1622
1623 class BoolExpr : public Expr {
1624 bool Value;
1625
1626 public:
BoolExpr(bool Value_)1627 BoolExpr(bool Value_) : Value(Value_) {}
1628
printLeft(OutputStream & S) const1629 void printLeft(OutputStream &S) const override {
1630 S += Value ? StringView("true") : StringView("false");
1631 }
1632 };
1633
1634 class IntegerCastExpr : public Expr {
1635 // ty(integer)
1636 Node *Ty;
1637 StringView Integer;
1638
1639 public:
IntegerCastExpr(Node * Ty_,StringView Integer_)1640 IntegerCastExpr(Node *Ty_, StringView Integer_) : Ty(Ty_), Integer(Integer_) {
1641 ParameterPackSize = Ty->ParameterPackSize;
1642 }
1643
printLeft(OutputStream & S) const1644 void printLeft(OutputStream &S) const override {
1645 S += "(";
1646 Ty->print(S);
1647 S += ")";
1648 S += Integer;
1649 }
1650 };
1651
1652 class IntegerExpr : public Expr {
1653 StringView Type;
1654 StringView Value;
1655
1656 public:
IntegerExpr(StringView Type_,StringView Value_)1657 IntegerExpr(StringView Type_, StringView Value_) : Type(Type_), Value(Value_) {}
1658
printLeft(OutputStream & S) const1659 void printLeft(OutputStream &S) const override {
1660 if (Type.size() > 3) {
1661 S += "(";
1662 S += Type;
1663 S += ")";
1664 }
1665
1666 if (Value[0] == 'n') {
1667 S += "-";
1668 S += Value.dropFront(1);
1669 } else
1670 S += Value;
1671
1672 if (Type.size() <= 3)
1673 S += Type;
1674 }
1675 };
1676
1677 template <class Float> struct FloatData;
1678
1679 template <class Float> class FloatExpr : public Expr {
1680 const StringView Contents;
1681
1682 public:
FloatExpr(StringView Contents_)1683 FloatExpr(StringView Contents_) : Contents(Contents_) {}
1684
printLeft(OutputStream & s) const1685 void printLeft(OutputStream &s) const override {
1686 const char *first = Contents.begin();
1687 const char *last = Contents.end() + 1;
1688
1689 const size_t N = FloatData<Float>::mangled_size;
1690 if (static_cast<std::size_t>(last - first) > N) {
1691 last = first + N;
1692 union {
1693 Float value;
1694 char buf[sizeof(Float)];
1695 };
1696 const char *t = first;
1697 char *e = buf;
1698 for (; t != last; ++t, ++e) {
1699 unsigned d1 = isdigit(*t) ? static_cast<unsigned>(*t - '0')
1700 : static_cast<unsigned>(*t - 'a' + 10);
1701 ++t;
1702 unsigned d0 = isdigit(*t) ? static_cast<unsigned>(*t - '0')
1703 : static_cast<unsigned>(*t - 'a' + 10);
1704 *e = static_cast<char>((d1 << 4) + d0);
1705 }
1706 #if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__
1707 std::reverse(buf, e);
1708 #endif
1709 char num[FloatData<Float>::max_demangled_size] = {0};
1710 int n = snprintf(num, sizeof(num), FloatData<Float>::spec, value);
1711 s += StringView(num, num + n);
1712 }
1713 }
1714 };
1715
1716 class BumpPointerAllocator {
1717 struct BlockMeta {
1718 BlockMeta* Next;
1719 size_t Current;
1720 };
1721
1722 static constexpr size_t AllocSize = 4096;
1723 static constexpr size_t UsableAllocSize = AllocSize - sizeof(BlockMeta);
1724
1725 alignas(16) char InitialBuffer[AllocSize];
1726 BlockMeta* BlockList = nullptr;
1727
grow()1728 void grow() {
1729 char* NewMeta = new char[AllocSize];
1730 BlockList = new (NewMeta) BlockMeta{BlockList, 0};
1731 }
1732
allocateMassive(size_t NBytes)1733 void* allocateMassive(size_t NBytes) {
1734 NBytes += sizeof(BlockMeta);
1735 BlockMeta* NewMeta = reinterpret_cast<BlockMeta*>(new char[NBytes]);
1736 BlockList->Next = new (NewMeta) BlockMeta{BlockList->Next, 0};
1737 return static_cast<void*>(NewMeta + 1);
1738 }
1739
1740 public:
BumpPointerAllocator()1741 BumpPointerAllocator()
1742 : BlockList(new (InitialBuffer) BlockMeta{nullptr, 0}) {}
1743
allocate(size_t N)1744 void* allocate(size_t N) {
1745 N = (N + 15u) & ~15u;
1746 if (N + BlockList->Current >= UsableAllocSize) {
1747 if (N > UsableAllocSize)
1748 return allocateMassive(N);
1749 grow();
1750 }
1751 BlockList->Current += N;
1752 return static_cast<void*>(reinterpret_cast<char*>(BlockList + 1) +
1753 BlockList->Current - N);
1754 }
1755
~BumpPointerAllocator()1756 ~BumpPointerAllocator() {
1757 while (BlockList) {
1758 BlockMeta* Tmp = BlockList;
1759 BlockList = BlockList->Next;
1760 if (reinterpret_cast<char*>(Tmp) != InitialBuffer)
1761 delete[] reinterpret_cast<char*>(Tmp);
1762 }
1763 }
1764 };
1765
1766 template <class T, size_t N>
1767 class PODSmallVector {
1768 static_assert(std::is_pod<T>::value,
1769 "T is required to be a plain old data type");
1770
1771 T* First;
1772 T* Last;
1773 T* Cap;
1774 T Inline[N];
1775
isInline() const1776 bool isInline() const { return First == Inline; }
1777
clearInline()1778 void clearInline() {
1779 First = Inline;
1780 Last = Inline;
1781 Cap = Inline + N;
1782 }
1783
reserve(size_t NewCap)1784 void reserve(size_t NewCap) {
1785 size_t S = size();
1786 if (isInline()) {
1787 auto* Tmp = static_cast<T*>(std::malloc(NewCap * sizeof(T)));
1788 std::copy(First, Last, Tmp);
1789 First = Tmp;
1790 } else
1791 First = static_cast<T*>(std::realloc(First, NewCap * sizeof(T)));
1792 Last = First + S;
1793 Cap = First + NewCap;
1794 }
1795
1796 public:
PODSmallVector()1797 PODSmallVector() : First(Inline), Last(First), Cap(Inline + N) {}
1798
1799 PODSmallVector(const PODSmallVector&) = delete;
1800 PODSmallVector& operator=(const PODSmallVector&) = delete;
1801
PODSmallVector(PODSmallVector && Other)1802 PODSmallVector(PODSmallVector&& Other) : PODSmallVector() {
1803 if (Other.isInline()) {
1804 std::copy(Other.begin(), Other.end(), First);
1805 Last = First + Other.size();
1806 Other.clear();
1807 return;
1808 }
1809
1810 First = Other.First;
1811 Last = Other.Last;
1812 Cap = Other.Cap;
1813 Other.clearInline();
1814 }
1815
operator =(PODSmallVector && Other)1816 PODSmallVector& operator=(PODSmallVector&& Other) {
1817 if (Other.isInline()) {
1818 if (!isInline()) {
1819 std::free(First);
1820 clearInline();
1821 }
1822 std::copy(Other.begin(), Other.end(), First);
1823 Last = First + Other.size();
1824 Other.clear();
1825 return *this;
1826 }
1827
1828 if (isInline()) {
1829 First = Other.First;
1830 Last = Other.Last;
1831 Cap = Other.Cap;
1832 Other.clearInline();
1833 return *this;
1834 }
1835
1836 std::swap(First, Other.First);
1837 std::swap(Last, Other.Last);
1838 std::swap(Cap, Other.Cap);
1839 Other.clear();
1840 return *this;
1841 }
1842
push_back(const T & Elem)1843 void push_back(const T& Elem) {
1844 if (Last == Cap)
1845 reserve(size() * 2);
1846 *Last++ = Elem;
1847 }
1848
pop_back()1849 void pop_back() {
1850 assert(Last != First && "Popping empty vector!");
1851 --Last;
1852 }
1853
dropBack(size_t Index)1854 void dropBack(size_t Index) {
1855 assert(Index <= size() && "dropBack() can't expand!");
1856 Last = First + Index;
1857 }
1858
begin()1859 T* begin() { return First; }
end()1860 T* end() { return Last; }
1861
empty() const1862 bool empty() const { return First == Last; }
size() const1863 size_t size() const { return static_cast<size_t>(Last - First); }
back()1864 T& back() {
1865 assert(Last != First && "Calling back() on empty vector!");
1866 return *(Last - 1);
1867 }
operator [](size_t Index)1868 T& operator[](size_t Index) {
1869 assert(Index < size() && "Invalid access!");
1870 return *(begin() + Index);
1871 }
clear()1872 void clear() { Last = First; }
1873
~PODSmallVector()1874 ~PODSmallVector() {
1875 if (!isInline())
1876 std::free(First);
1877 }
1878 };
1879
1880 struct Db {
1881 const char *First;
1882 const char *Last;
1883
1884 // Name stack, this is used by the parser to hold temporary names that were
1885 // parsed. The parser colapses multiple names into new nodes to construct
1886 // the AST. Once the parser is finished, names.size() == 1.
1887 PODSmallVector<Node *, 32> Names;
1888
1889 // Substitution table. Itanium supports name substitutions as a means of
1890 // compression. The string "S42_" refers to the 44nd entry (base-36) in this
1891 // table.
1892 PODSmallVector<Node *, 32> Subs;
1893
1894 // Template parameter table. Like the above, but referenced like "T42_".
1895 // This has a smaller size compared to Subs and Names because it can be
1896 // stored on the stack.
1897 PODSmallVector<Node *, 8> TemplateParams;
1898
1899 Qualifiers CV = QualNone;
1900 FunctionRefQual RefQuals = FrefQualNone;
1901 unsigned EncodingDepth = 0;
1902 bool ParsedCtorDtorCV = false;
1903 bool TagTemplates = true;
1904 bool FixForwardReferences = false;
1905 bool TryToParseTemplateArgs = true;
1906
1907 BumpPointerAllocator ASTAllocator;
1908
make__anon9d46d5f30111::Db1909 template <class T, class... Args> T *make(Args &&... args) {
1910 return new (ASTAllocator.allocate(sizeof(T)))
1911 T(std::forward<Args>(args)...);
1912 }
1913
makeNodeArray__anon9d46d5f30111::Db1914 template <class It> NodeArray makeNodeArray(It begin, It end) {
1915 size_t sz = static_cast<size_t>(end - begin);
1916 void *mem = ASTAllocator.allocate(sizeof(Node *) * sz);
1917 Node **data = new (mem) Node *[sz];
1918 std::copy(begin, end, data);
1919 return NodeArray(data, sz);
1920 }
1921
popTrailingNodeArray__anon9d46d5f30111::Db1922 NodeArray popTrailingNodeArray(size_t FromPosition) {
1923 assert(FromPosition <= Names.size());
1924 NodeArray res =
1925 makeNodeArray(Names.begin() + (long)FromPosition, Names.end());
1926 Names.dropBack(FromPosition);
1927 return res;
1928 }
1929
consumeIf__anon9d46d5f30111::Db1930 bool consumeIf(StringView S) {
1931 if (StringView(First, Last).startsWith(S)) {
1932 First += S.size();
1933 return true;
1934 }
1935 return false;
1936 }
1937
consumeIf__anon9d46d5f30111::Db1938 bool consumeIf(char C) {
1939 if (First != Last && *First == C) {
1940 ++First;
1941 return true;
1942 }
1943 return false;
1944 }
1945
consume__anon9d46d5f30111::Db1946 char consume() { return First != Last ? *First++ : '\0'; }
1947
look__anon9d46d5f30111::Db1948 char look(unsigned Lookahead = 0) {
1949 if (static_cast<size_t>(Last - First) <= Lookahead)
1950 return '\0';
1951 return First[Lookahead];
1952 }
1953
numLeft__anon9d46d5f30111::Db1954 size_t numLeft() const { return static_cast<size_t>(Last - First); }
1955
1956 StringView parseNumber(bool AllowNegative = false);
1957 Qualifiers parseCVQualifiers();
1958 bool parsePositiveInteger(size_t *Out);
1959 StringView parseBareSourceName();
1960
1961 /// Parse the <expr> production.
1962 Node *parseExpr();
1963 Node *parsePrefixExpr(StringView Kind);
1964 Node *parseBinaryExpr(StringView Kind);
1965 Node *parseIntegerLiteral(StringView Lit);
1966 Node *parseExprPrimary();
1967 template <class Float> Node *parseFloatingLiteral();
1968 Node *parseFunctionParam();
1969 Node *parseNewExpr();
1970 Node *parseConversionExpr();
1971
1972 /// Parse the <type> production.
1973 Node *parseType();
1974 Node *parseFunctionType();
1975 Node *parseVectorType();
1976 Node *parseDecltype();
1977 Node *parseArrayType();
1978 Node *parsePointerToMemberType();
1979 Node *parseClassEnumType();
1980
1981 // FIXME: remove this when all the parse_* functions have been rewritten.
1982 template <const char *(*parse_fn)(const char *, const char *, Db &)>
legacyParse__anon9d46d5f30111::Db1983 Node *legacyParse() {
1984 size_t BeforeType = Names.size();
1985 const char *OrigFirst = First;
1986 const char *T = parse_fn(First, Last, *this);
1987 if (T == OrigFirst || BeforeType + 1 != Names.size())
1988 return nullptr;
1989 First = T;
1990 Node *R = Names.back();
1991 Names.pop_back();
1992 return R;
1993 }
1994 template <const char *(*parse_fn)(const char *, const char *, Db &, bool *)>
legacyParse__anon9d46d5f30111::Db1995 Node *legacyParse() {
1996 size_t BeforeType = Names.size();
1997 const char *OrigFirst = First;
1998 const char *T = parse_fn(First, Last, *this, nullptr);
1999 if (T == OrigFirst || BeforeType + 1 != Names.size())
2000 return nullptr;
2001 First = T;
2002 Node *R = Names.back();
2003 Names.pop_back();
2004 return R;
2005 }
2006 };
2007
parse_expression(const char * first,const char * last,Db & db)2008 const char *parse_expression(const char *first, const char *last, Db &db) {
2009 db.First = first;
2010 db.Last = last;
2011 Node *R = db.parseExpr();
2012 if (R == nullptr)
2013 return first;
2014 db.Names.push_back(R);
2015 return db.First;
2016 }
2017
parse_expr_primary(const char * first,const char * last,Db & db)2018 const char *parse_expr_primary(const char *first, const char *last, Db &db) {
2019 db.First = first;
2020 db.Last = last;
2021 Node *R = db.parseExprPrimary();
2022 if (R == nullptr)
2023 return first;
2024 db.Names.push_back(R);
2025 return db.First;
2026 }
2027
parse_type(const char * first,const char * last,Db & db)2028 const char *parse_type(const char *first, const char *last, Db &db) {
2029 db.First = first;
2030 db.Last = last;
2031 Node *R = db.parseType();
2032 if (R == nullptr)
2033 return first;
2034 db.Names.push_back(R);
2035 return db.First;
2036 }
2037
parse_decltype(const char * first,const char * last,Db & db)2038 const char *parse_decltype(const char *first, const char *last, Db &db) {
2039 db.First = first;
2040 db.Last = last;
2041 Node *R = db.parseDecltype();
2042 if (R == nullptr)
2043 return first;
2044 db.Names.push_back(R);
2045 return db.First;
2046 }
2047
2048 const char *parse_type(const char *first, const char *last, Db &db);
2049 const char *parse_encoding(const char *first, const char *last, Db &db);
2050 const char *parse_name(const char *first, const char *last, Db &db,
2051 bool *ends_with_template_args = 0);
2052 const char *parse_template_args(const char *first, const char *last, Db &db);
2053 const char *parse_template_param(const char *, const char *, Db &);
2054 const char *parse_operator_name(const char *first, const char *last, Db &db);
2055 const char *parse_unqualified_name(const char *first, const char *last, Db &db);
2056 const char *parse_decltype(const char *first, const char *last, Db &db);
2057 const char *parse_unresolved_name(const char *, const char *, Db &);
2058 const char *parse_substitution(const char *, const char *, Db &);
2059
2060 // <number> ::= [n] <non-negative decimal integer>
parseNumber(bool AllowNegative)2061 StringView Db::parseNumber(bool AllowNegative) {
2062 const char *Tmp = First;
2063 if (AllowNegative)
2064 consumeIf('n');
2065 if (numLeft() == 0 || !std::isdigit(*First))
2066 return StringView();
2067 while (numLeft() != 0 && std::isdigit(*First))
2068 ++First;
2069 return StringView(Tmp, First);
2070 }
2071
2072 // <positive length number> ::= [0-9]*
parsePositiveInteger(size_t * Out)2073 bool Db::parsePositiveInteger(size_t *Out) {
2074 *Out = 0;
2075 if (look() < '0' || look() > '9')
2076 return true;
2077 while (look() >= '0' && look() <= '9') {
2078 *Out *= 10;
2079 *Out += static_cast<size_t>(consume() - '0');
2080 }
2081 return false;
2082 }
2083
parseBareSourceName()2084 StringView Db::parseBareSourceName() {
2085 size_t Int = 0;
2086 if (parsePositiveInteger(&Int) || numLeft() < Int)
2087 return StringView();
2088 StringView R(First, First + Int);
2089 First += Int;
2090 return R;
2091 }
2092
2093 // <function-type> ::= F [Y] <bare-function-type> [<ref-qualifier>] E
2094 //
2095 // <ref-qualifier> ::= R # & ref-qualifier
2096 // <ref-qualifier> ::= O # && ref-qualifier
parseFunctionType()2097 Node *Db::parseFunctionType() {
2098 if (!consumeIf('F'))
2099 return nullptr;
2100 consumeIf('Y'); // extern "C"
2101 Node *ReturnType = parseType();
2102 if (ReturnType == nullptr)
2103 return nullptr;
2104
2105 FunctionRefQual ReferenceQualifier = FrefQualNone;
2106 size_t ParamsBegin = Names.size();
2107 while (true) {
2108 if (consumeIf('E'))
2109 break;
2110 if (consumeIf('v'))
2111 continue;
2112 if (consumeIf("RE")) {
2113 ReferenceQualifier = FrefQualLValue;
2114 break;
2115 }
2116 if (consumeIf("OE")) {
2117 ReferenceQualifier = FrefQualRValue;
2118 break;
2119 }
2120 Node *T = parseType();
2121 if (T == nullptr)
2122 return nullptr;
2123 Names.push_back(T);
2124 }
2125
2126 NodeArray Params = popTrailingNodeArray(ParamsBegin);
2127 Node *Fn = make<FunctionType>(ReturnType, Params);
2128 if (ReferenceQualifier != FrefQualNone)
2129 Fn = make<FunctionRefQualType>(Fn, ReferenceQualifier);
2130 return Fn;
2131 }
2132
2133 // extension:
2134 // <vector-type> ::= Dv <positive dimension number> _ <extended element type>
2135 // ::= Dv [<dimension expression>] _ <element type>
2136 // <extended element type> ::= <element type>
2137 // ::= p # AltiVec vector pixel
parseVectorType()2138 Node *Db::parseVectorType() {
2139 if (!consumeIf("Dv"))
2140 return nullptr;
2141 if (look() >= '1' && look() <= '9') {
2142 StringView DimensionNumber = parseNumber();
2143 if (!consumeIf('_'))
2144 return nullptr;
2145 if (consumeIf('p'))
2146 return make<VectorType>(DimensionNumber);
2147 Node *ElemType = parseType();
2148 if (ElemType == nullptr)
2149 return nullptr;
2150 return make<VectorType>(ElemType, DimensionNumber);
2151 }
2152
2153 if (!consumeIf('_')) {
2154 Node *DimExpr = parseExpr();
2155 if (!DimExpr)
2156 return nullptr;
2157 if (!consumeIf('_'))
2158 return nullptr;
2159 Node *ElemType = parseType();
2160 if (!ElemType)
2161 return nullptr;
2162 return make<VectorType>(ElemType, DimExpr);
2163 }
2164 Node *ElemType = parseType();
2165 if (!ElemType)
2166 return nullptr;
2167 return make<VectorType>(ElemType, StringView());
2168 }
2169
2170 // <decltype> ::= Dt <expression> E # decltype of an id-expression or class member access (C++0x)
2171 // ::= DT <expression> E # decltype of an expression (C++0x)
parseDecltype()2172 Node *Db::parseDecltype() {
2173 if (!consumeIf('D'))
2174 return nullptr;
2175 if (!consumeIf('t') && !consumeIf('T'))
2176 return nullptr;
2177 Node *E = parseExpr();
2178 if (E == nullptr)
2179 return nullptr;
2180 if (!consumeIf('E'))
2181 return nullptr;
2182 return make<EnclosingExpr>("decltype(", E, ")");
2183 }
2184
2185 // <array-type> ::= A <positive dimension number> _ <element type>
2186 // ::= A [<dimension expression>] _ <element type>
parseArrayType()2187 Node *Db::parseArrayType() {
2188 if (!consumeIf('A'))
2189 return nullptr;
2190
2191 if (std::isdigit(look())) {
2192 StringView Dimension = parseNumber();
2193 if (!consumeIf('_'))
2194 return nullptr;
2195 Node *Ty = parseType();
2196 if (Ty == nullptr)
2197 return nullptr;
2198 return make<ArrayType>(Ty, Dimension);
2199 }
2200
2201 if (!consumeIf('_')) {
2202 Node *DimExpr = parseExpr();
2203 if (DimExpr == nullptr)
2204 return nullptr;
2205 if (!consumeIf('_'))
2206 return nullptr;
2207 Node *ElementType = parseType();
2208 if (ElementType == nullptr)
2209 return nullptr;
2210 return make<ArrayType>(ElementType, DimExpr);
2211 }
2212
2213 Node *Ty = parseType();
2214 if (Ty == nullptr)
2215 return nullptr;
2216 return make<ArrayType>(Ty);
2217 }
2218
2219 // <pointer-to-member-type> ::= M <class type> <member type>
parsePointerToMemberType()2220 Node *Db::parsePointerToMemberType() {
2221 if (!consumeIf('M'))
2222 return nullptr;
2223 Node *ClassType = parseType();
2224 if (ClassType == nullptr)
2225 return nullptr;
2226 Node *MemberType = parseType();
2227 if (MemberType == nullptr)
2228 return nullptr;
2229 return make<PointerToMemberType>(ClassType, MemberType);
2230 }
2231
2232 // <class-enum-type> ::= <name> # non-dependent type name, dependent type name, or dependent typename-specifier
2233 // ::= Ts <name> # dependent elaborated type specifier using 'struct' or 'class'
2234 // ::= Tu <name> # dependent elaborated type specifier using 'union'
2235 // ::= Te <name> # dependent elaborated type specifier using 'enum'
parseClassEnumType()2236 Node *Db::parseClassEnumType() {
2237 // FIXME: try to parse the elaborated type specifiers here!
2238 return legacyParse<parse_name>();
2239 }
2240
2241 // <type> ::= <builtin-type>
2242 // ::= <qualified-type>
2243 // ::= <function-type>
2244 // ::= <class-enum-type>
2245 // ::= <array-type>
2246 // ::= <pointer-to-member-type>
2247 // ::= <template-param>
2248 // ::= <template-template-param> <template-args>
2249 // ::= <decltype>
2250 // ::= P <type> # pointer
2251 // ::= R <type> # l-value reference
2252 // ::= O <type> # r-value reference (C++11)
2253 // ::= C <type> # complex pair (C99)
2254 // ::= G <type> # imaginary (C99)
2255 // ::= <substitution> # See Compression below
2256 // extension ::= U <objc-name> <objc-type> # objc-type<identifier>
2257 // extension ::= <vector-type> # <vector-type> starts with Dv
2258 //
2259 // <objc-name> ::= <k0 number> objcproto <k1 number> <identifier> # k0 = 9 + <number of digits in k1> + k1
2260 // <objc-type> ::= <source-name> # PU<11+>objcproto 11objc_object<source-name> 11objc_object -> id<source-name>
parseType()2261 Node *Db::parseType() {
2262 Node *Result = nullptr;
2263
2264 switch (look()) {
2265 // ::= <qualified-type>
2266 case 'r':
2267 case 'V':
2268 case 'K': {
2269 Qualifiers Q = parseCVQualifiers();
2270 bool AppliesToFunction = look() == 'F';
2271
2272 Node *Child = parseType();
2273 if (Child == nullptr)
2274 return nullptr;
2275
2276 if (AppliesToFunction)
2277 Result = make<FunctionQualType>(Child, Q);
2278 else
2279 Result = make<QualType>(Child, Q);
2280
2281 // Itanium C++ ABI 5.1.5.3:
2282 // For the purposes of substitution, the CV-qualifiers and ref-qualifier
2283 // of a function type are an indivisible part of the type.
2284 if (AppliesToFunction)
2285 return Result;
2286 break;
2287 }
2288 // <extended-qualifier> ::= U <source-name> [<template-args>] # vendor extended type qualifier
2289 case 'U': {
2290 // FIXME: We should fold this into the cvr qualifier parsing above. This
2291 // currently adds too many entries into the substitution table if multiple
2292 // qualifiers are present on the same type, as all the qualifiers on a type
2293 // should just get one entry in the substitution table.
2294 ++First;
2295 StringView Qual = parseBareSourceName();
2296 if (Qual.empty())
2297 return nullptr;
2298
2299 // FIXME parse the optional <template-args> here!
2300
2301 Result = parseType();
2302 if (Result == nullptr)
2303 return nullptr;
2304
2305 // extension ::= U <objc-name> <objc-type> # objc-type<identifier>
2306 if (Qual.startsWith("objcproto")) {
2307 StringView ProtoSourceName = Qual.dropFront(std::strlen("objcproto"));
2308 StringView Proto;
2309 {
2310 SwapAndRestore<const char *> SaveFirst(First, ProtoSourceName.begin()),
2311 SaveLast(Last, ProtoSourceName.end());
2312 Proto = parseBareSourceName();
2313 }
2314 if (Proto.empty())
2315 return nullptr;
2316 Result = make<ObjCProtoName>(Result, Proto);
2317 } else
2318 Result = make<VendorExtQualType>(Result, Qual);
2319 break;
2320 }
2321 // <builtin-type> ::= v # void
2322 case 'v':
2323 ++First;
2324 return make<NameType>("void");
2325 // ::= w # wchar_t
2326 case 'w':
2327 ++First;
2328 return make<NameType>("wchar_t");
2329 // ::= b # bool
2330 case 'b':
2331 ++First;
2332 return make<NameType>("bool");
2333 // ::= c # char
2334 case 'c':
2335 ++First;
2336 return make<NameType>("char");
2337 // ::= a # signed char
2338 case 'a':
2339 ++First;
2340 return make<NameType>("signed char");
2341 // ::= h # unsigned char
2342 case 'h':
2343 ++First;
2344 return make<NameType>("unsigned char");
2345 // ::= s # short
2346 case 's':
2347 ++First;
2348 return make<NameType>("short");
2349 // ::= t # unsigned short
2350 case 't':
2351 ++First;
2352 return make<NameType>("unsigned short");
2353 // ::= i # int
2354 case 'i':
2355 ++First;
2356 return make<NameType>("int");
2357 // ::= j # unsigned int
2358 case 'j':
2359 ++First;
2360 return make<NameType>("unsigned int");
2361 // ::= l # long
2362 case 'l':
2363 ++First;
2364 return make<NameType>("long");
2365 // ::= m # unsigned long
2366 case 'm':
2367 ++First;
2368 return make<NameType>("unsigned long");
2369 // ::= x # long long, __int64
2370 case 'x':
2371 ++First;
2372 return make<NameType>("long long");
2373 // ::= y # unsigned long long, __int64
2374 case 'y':
2375 ++First;
2376 return make<NameType>("unsigned long long");
2377 // ::= n # __int128
2378 case 'n':
2379 ++First;
2380 return make<NameType>("__int128");
2381 // ::= o # unsigned __int128
2382 case 'o':
2383 ++First;
2384 return make<NameType>("unsigned __int128");
2385 // ::= f # float
2386 case 'f':
2387 ++First;
2388 return make<NameType>("float");
2389 // ::= d # double
2390 case 'd':
2391 ++First;
2392 return make<NameType>("double");
2393 // ::= e # long double, __float80
2394 case 'e':
2395 ++First;
2396 return make<NameType>("long double");
2397 // ::= g # __float128
2398 case 'g':
2399 ++First;
2400 return make<NameType>("__float128");
2401 // ::= z # ellipsis
2402 case 'z':
2403 ++First;
2404 return make<NameType>("...");
2405
2406 // <builtin-type> ::= u <source-name> # vendor extended type
2407 case 'u': {
2408 ++First;
2409 StringView Res = parseBareSourceName();
2410 if (Res.empty())
2411 return nullptr;
2412 return make<NameType>(Res);
2413 }
2414 case 'D':
2415 switch (look(1)) {
2416 // ::= Dd # IEEE 754r decimal floating point (64 bits)
2417 case 'd':
2418 First += 2;
2419 return make<NameType>("decimal64");
2420 // ::= De # IEEE 754r decimal floating point (128 bits)
2421 case 'e':
2422 First += 2;
2423 return make<NameType>("decimal128");
2424 // ::= Df # IEEE 754r decimal floating point (32 bits)
2425 case 'f':
2426 First += 2;
2427 return make<NameType>("decimal32");
2428 // ::= Dh # IEEE 754r half-precision floating point (16 bits)
2429 case 'h':
2430 First += 2;
2431 return make<NameType>("decimal16");
2432 // ::= Di # char32_t
2433 case 'i':
2434 First += 2;
2435 return make<NameType>("char32_t");
2436 // ::= Ds # char16_t
2437 case 's':
2438 First += 2;
2439 return make<NameType>("char16_t");
2440 // ::= Da # auto (in dependent new-expressions)
2441 case 'a':
2442 First += 2;
2443 return make<NameType>("auto");
2444 // ::= Dc # decltype(auto)
2445 case 'c':
2446 First += 2;
2447 return make<NameType>("decltype(auto)");
2448 // ::= Dn # std::nullptr_t (i.e., decltype(nullptr))
2449 case 'n':
2450 First += 2;
2451 return make<NameType>("std::nullptr_t");
2452
2453 // ::= <decltype>
2454 case 't':
2455 case 'T': {
2456 Result = parseDecltype();
2457 break;
2458 }
2459 // extension ::= <vector-type> # <vector-type> starts with Dv
2460 case 'v': {
2461 Result = parseVectorType();
2462 break;
2463 }
2464 // ::= Dp <type> # pack expansion (C++0x)
2465 case 'p': {
2466 First += 2;
2467 Node *Child = parseType();
2468 if (!Child)
2469 return nullptr;
2470 Result = make<ParameterPackExpansion>(Child);
2471 break;
2472 }
2473 }
2474 break;
2475 // ::= <function-type>
2476 case 'F': {
2477 Result = parseFunctionType();
2478 break;
2479 }
2480 // ::= <array-type>
2481 case 'A': {
2482 Result = parseArrayType();
2483 break;
2484 }
2485 // ::= <pointer-to-member-type>
2486 case 'M': {
2487 Result = parsePointerToMemberType();
2488 break;
2489 }
2490 // ::= <template-param>
2491 case 'T': {
2492 Result = legacyParse<parse_template_param>();
2493 if (Result == nullptr)
2494 return nullptr;
2495
2496 // Result could be either of:
2497 // <type> ::= <template-param>
2498 // <type> ::= <template-template-param> <template-args>
2499 //
2500 // <template-template-param> ::= <template-param>
2501 // ::= <substitution>
2502 //
2503 // If this is followed by some <template-args>, and we're permitted to
2504 // parse them, take the second production.
2505
2506 if (TryToParseTemplateArgs && look() == 'I') {
2507 Node *TA = legacyParse<parse_template_args>();
2508 if (TA == nullptr)
2509 return nullptr;
2510 Result = make<NameWithTemplateArgs>(Result, TA);
2511 }
2512 break;
2513 }
2514 // ::= P <type> # pointer
2515 case 'P': {
2516 ++First;
2517 Node *Ptr = parseType();
2518 if (Ptr == nullptr)
2519 return nullptr;
2520 Result = make<PointerType>(Ptr);
2521 break;
2522 }
2523 // ::= R <type> # l-value reference
2524 case 'R': {
2525 ++First;
2526 Node *Ref = parseType();
2527 if (Ref == nullptr)
2528 return nullptr;
2529 Result = make<LValueReferenceType>(Ref);
2530 break;
2531 }
2532 // ::= O <type> # r-value reference (C++11)
2533 case 'O': {
2534 ++First;
2535 Node *Ref = parseType();
2536 if (Ref == nullptr)
2537 return nullptr;
2538 Result = make<RValueReferenceType>(Ref);
2539 break;
2540 }
2541 // ::= C <type> # complex pair (C99)
2542 case 'C': {
2543 ++First;
2544 Node *P = parseType();
2545 if (P == nullptr)
2546 return nullptr;
2547 Result = make<PostfixQualifiedType>(P, " complex");
2548 break;
2549 }
2550 // ::= G <type> # imaginary (C99)
2551 case 'G': {
2552 ++First;
2553 Node *P = parseType();
2554 if (P == nullptr)
2555 return P;
2556 Result = make<PostfixQualifiedType>(P, " imaginary");
2557 break;
2558 }
2559 // ::= <substitution> # See Compression below
2560 case 'S': {
2561 if (look(1) && look(1) != 't') {
2562 Node *Sub = legacyParse<parse_substitution>();
2563 if (Sub == nullptr)
2564 return nullptr;
2565
2566 // Sub could be either of:
2567 // <type> ::= <substitution>
2568 // <type> ::= <template-template-param> <template-args>
2569 //
2570 // <template-template-param> ::= <template-param>
2571 // ::= <substitution>
2572 //
2573 // If this is followed by some <template-args>, and we're permitted to
2574 // parse them, take the second production.
2575
2576 if (TryToParseTemplateArgs && look() == 'I') {
2577 Node *TA = legacyParse<parse_template_args>();
2578 if (TA == nullptr)
2579 return nullptr;
2580 Result = make<NameWithTemplateArgs>(Sub, TA);
2581 break;
2582 }
2583
2584 // If all we parsed was a substitution, don't re-insert into the
2585 // substitution table.
2586 return Sub;
2587 }
2588 _LIBCPP_FALLTHROUGH();
2589 }
2590 // ::= <class-enum-type>
2591 default: {
2592 Result = parseClassEnumType();
2593 break;
2594 }
2595 }
2596
2597 // If we parsed a type, insert it into the substitution table. Note that all
2598 // <builtin-type>s and <substitution>s have already bailed out, because they
2599 // don't get substitutions.
2600 if (Result != nullptr)
2601 Subs.push_back(Result);
2602 return Result;
2603 }
2604
parsePrefixExpr(StringView Kind)2605 Node *Db::parsePrefixExpr(StringView Kind) {
2606 Node *E = parseExpr();
2607 if (E == nullptr)
2608 return nullptr;
2609 return make<PrefixExpr>(Kind, E);
2610 }
2611
parseBinaryExpr(StringView Kind)2612 Node *Db::parseBinaryExpr(StringView Kind) {
2613 Node *LHS = parseExpr();
2614 if (LHS == nullptr)
2615 return nullptr;
2616 Node *RHS = parseExpr();
2617 if (RHS == nullptr)
2618 return nullptr;
2619 return make<BinaryExpr>(LHS, Kind, RHS);
2620 }
2621
parseIntegerLiteral(StringView Lit)2622 Node *Db::parseIntegerLiteral(StringView Lit) {
2623 StringView Tmp = parseNumber(true);
2624 if (!Tmp.empty() && consumeIf('E'))
2625 return make<IntegerExpr>(Lit, Tmp);
2626 return nullptr;
2627 }
2628
parseCVQualifiers()2629 Qualifiers Db::parseCVQualifiers() {
2630 Qualifiers CVR = QualNone;
2631 if (consumeIf('r'))
2632 addQualifiers(CVR, QualRestrict);
2633 if (consumeIf('V'))
2634 addQualifiers(CVR, QualVolatile);
2635 if (consumeIf('K'))
2636 addQualifiers(CVR, QualConst);
2637 return CVR;
2638 }
2639
2640 // <function-param> ::= fp <top-level CV-Qualifiers> _ # L == 0, first parameter
2641 // ::= fp <top-level CV-Qualifiers> <parameter-2 non-negative number> _ # L == 0, second and later parameters
2642 // ::= fL <L-1 non-negative number> p <top-level CV-Qualifiers> _ # L > 0, first parameter
2643 // ::= fL <L-1 non-negative number> p <top-level CV-Qualifiers> <parameter-2 non-negative number> _ # L > 0, second and later parameters
parseFunctionParam()2644 Node *Db::parseFunctionParam() {
2645 if (consumeIf("fp")) {
2646 parseCVQualifiers();
2647 StringView Num = parseNumber();
2648 if (!consumeIf('_'))
2649 return nullptr;
2650 return make<FunctionParam>(Num);
2651 }
2652 if (consumeIf("fL")) {
2653 if (parseNumber().empty())
2654 return nullptr;
2655 if (!consumeIf('p'))
2656 return nullptr;
2657 parseCVQualifiers();
2658 StringView Num = parseNumber();
2659 if (!consumeIf('_'))
2660 return nullptr;
2661 return make<FunctionParam>(Num);
2662 }
2663 return nullptr;
2664 }
2665
2666 // [gs] nw <expression>* _ <type> E # new (expr-list) type
2667 // [gs] nw <expression>* _ <type> <initializer> # new (expr-list) type (init)
2668 // [gs] na <expression>* _ <type> E # new[] (expr-list) type
2669 // [gs] na <expression>* _ <type> <initializer> # new[] (expr-list) type (init)
2670 // <initializer> ::= pi <expression>* E # parenthesized initialization
parseNewExpr()2671 Node *Db::parseNewExpr() {
2672 bool Global = consumeIf("gs");
2673 bool IsArray = look(1) == 'a';
2674 if (!consumeIf("nw") && !consumeIf("na"))
2675 return nullptr;
2676 size_t Exprs = Names.size();
2677 while (!consumeIf('_')) {
2678 Node *Ex = parseExpr();
2679 if (Ex == nullptr)
2680 return nullptr;
2681 Names.push_back(Ex);
2682 }
2683 NodeArray ExprList = popTrailingNodeArray(Exprs);
2684 Node *Ty = parseType();
2685 if (Ty == nullptr)
2686 return Ty;
2687 if (consumeIf("pi")) {
2688 size_t InitsBegin = Names.size();
2689 while (!consumeIf('E')) {
2690 Node *Init = parseExpr();
2691 if (Init == nullptr)
2692 return Init;
2693 Names.push_back(Init);
2694 }
2695 NodeArray Inits = popTrailingNodeArray(InitsBegin);
2696 return make<NewExpr>(ExprList, Ty, Inits, Global, IsArray);
2697 } else if (!consumeIf('E'))
2698 return nullptr;
2699 return make<NewExpr>(ExprList, Ty, NodeArray(), Global, IsArray);
2700 }
2701
2702 // cv <type> <expression> # conversion with one argument
2703 // cv <type> _ <expression>* E # conversion with a different number of arguments
parseConversionExpr()2704 Node *Db::parseConversionExpr() {
2705 if (!consumeIf("cv"))
2706 return nullptr;
2707 Node *Ty;
2708 {
2709 SwapAndRestore<bool> SaveTemp(TryToParseTemplateArgs, false);
2710 Ty = parseType();
2711 }
2712
2713 if (Ty == nullptr)
2714 return nullptr;
2715
2716 if (consumeIf('_')) {
2717 size_t ExprsBegin = Names.size();
2718 while (!consumeIf('E')) {
2719 Node *E = parseExpr();
2720 if (E == nullptr)
2721 return E;
2722 Names.push_back(E);
2723 }
2724 NodeArray Exprs = popTrailingNodeArray(ExprsBegin);
2725 return make<ConversionExpr>(Ty, Exprs);
2726 }
2727
2728 Node *E[1] = {parseExpr()};
2729 if (E[0] == nullptr)
2730 return nullptr;
2731 return make<ConversionExpr>(Ty, makeNodeArray(E, E + 1));
2732 }
2733
2734 // <expr-primary> ::= L <type> <value number> E # integer literal
2735 // ::= L <type> <value float> E # floating literal
2736 // ::= L <string type> E # string literal
2737 // ::= L <nullptr type> E # nullptr literal (i.e., "LDnE")
2738 // FIXME: ::= L <type> <real-part float> _ <imag-part float> E # complex floating point literal (C 2000)
2739 // ::= L <mangled-name> E # external name
parseExprPrimary()2740 Node *Db::parseExprPrimary() {
2741 if (!consumeIf('L'))
2742 return nullptr;
2743 switch (look()) {
2744 case 'w':
2745 ++First;
2746 return parseIntegerLiteral("wchar_t");
2747 case 'b':
2748 if (consumeIf("b0E"))
2749 return make<BoolExpr>(0);
2750 if (consumeIf("b1E"))
2751 return make<BoolExpr>(1);
2752 return nullptr;
2753 case 'c':
2754 ++First;
2755 return parseIntegerLiteral("char");
2756 case 'a':
2757 ++First;
2758 return parseIntegerLiteral("signed char");
2759 case 'h':
2760 ++First;
2761 return parseIntegerLiteral("unsigned char");
2762 case 's':
2763 ++First;
2764 return parseIntegerLiteral("short");
2765 case 't':
2766 ++First;
2767 return parseIntegerLiteral("unsigned short");
2768 case 'i':
2769 ++First;
2770 return parseIntegerLiteral("");
2771 case 'j':
2772 ++First;
2773 return parseIntegerLiteral("u");
2774 case 'l':
2775 ++First;
2776 return parseIntegerLiteral("l");
2777 case 'm':
2778 ++First;
2779 return parseIntegerLiteral("ul");
2780 case 'x':
2781 ++First;
2782 return parseIntegerLiteral("ll");
2783 case 'y':
2784 ++First;
2785 return parseIntegerLiteral("ull");
2786 case 'n':
2787 ++First;
2788 return parseIntegerLiteral("__int128");
2789 case 'o':
2790 ++First;
2791 return parseIntegerLiteral("unsigned __int128");
2792 case 'f':
2793 ++First;
2794 return parseFloatingLiteral<float>();
2795 case 'd':
2796 ++First;
2797 return parseFloatingLiteral<double>();
2798 case 'e':
2799 ++First;
2800 return parseFloatingLiteral<long double>();
2801 case '_':
2802 if (consumeIf("_Z")) {
2803 Node *R = legacyParse<parse_encoding>();
2804 if (R != nullptr && consumeIf('E'))
2805 return R;
2806 }
2807 return nullptr;
2808 case 'T':
2809 // Invalid mangled name per
2810 // http://sourcerytools.com/pipermail/cxx-abi-dev/2011-August/002422.html
2811 return nullptr;
2812 default: {
2813 // might be named type
2814 Node *T = parseType();
2815 if (T == nullptr)
2816 return nullptr;
2817 StringView N = parseNumber();
2818 if (!N.empty()) {
2819 if (!consumeIf('E'))
2820 return nullptr;
2821 return make<IntegerCastExpr>(T, N);
2822 }
2823 if (consumeIf('E'))
2824 return T;
2825 return nullptr;
2826 }
2827 }
2828 }
2829
2830 // <expression> ::= <unary operator-name> <expression>
2831 // ::= <binary operator-name> <expression> <expression>
2832 // ::= <ternary operator-name> <expression> <expression> <expression>
2833 // ::= cl <expression>+ E # call
2834 // ::= cv <type> <expression> # conversion with one argument
2835 // ::= cv <type> _ <expression>* E # conversion with a different number of arguments
2836 // ::= [gs] nw <expression>* _ <type> E # new (expr-list) type
2837 // ::= [gs] nw <expression>* _ <type> <initializer> # new (expr-list) type (init)
2838 // ::= [gs] na <expression>* _ <type> E # new[] (expr-list) type
2839 // ::= [gs] na <expression>* _ <type> <initializer> # new[] (expr-list) type (init)
2840 // ::= [gs] dl <expression> # delete expression
2841 // ::= [gs] da <expression> # delete[] expression
2842 // ::= pp_ <expression> # prefix ++
2843 // ::= mm_ <expression> # prefix --
2844 // ::= ti <type> # typeid (type)
2845 // ::= te <expression> # typeid (expression)
2846 // ::= dc <type> <expression> # dynamic_cast<type> (expression)
2847 // ::= sc <type> <expression> # static_cast<type> (expression)
2848 // ::= cc <type> <expression> # const_cast<type> (expression)
2849 // ::= rc <type> <expression> # reinterpret_cast<type> (expression)
2850 // ::= st <type> # sizeof (a type)
2851 // ::= sz <expression> # sizeof (an expression)
2852 // ::= at <type> # alignof (a type)
2853 // ::= az <expression> # alignof (an expression)
2854 // ::= nx <expression> # noexcept (expression)
2855 // ::= <template-param>
2856 // ::= <function-param>
2857 // ::= dt <expression> <unresolved-name> # expr.name
2858 // ::= pt <expression> <unresolved-name> # expr->name
2859 // ::= ds <expression> <expression> # expr.*expr
2860 // ::= sZ <template-param> # size of a parameter pack
2861 // ::= sZ <function-param> # size of a function parameter pack
2862 // ::= sp <expression> # pack expansion
2863 // ::= tw <expression> # throw expression
2864 // ::= tr # throw with no operand (rethrow)
2865 // ::= <unresolved-name> # f(p), N::f(p), ::f(p),
2866 // # freestanding dependent name (e.g., T::x),
2867 // # objectless nonstatic member reference
2868 // ::= fL <binary-operator-name> <expression> <expression>
2869 // ::= fR <binary-operator-name> <expression> <expression>
2870 // ::= fl <binary-operator-name> <expression>
2871 // ::= fr <binary-operator-name> <expression>
2872 // ::= <expr-primary>
parseExpr()2873 Node *Db::parseExpr() {
2874 bool Global = consumeIf("gs");
2875 if (numLeft() < 2)
2876 return nullptr;
2877
2878 switch (*First) {
2879 case 'L':
2880 return parseExprPrimary();
2881 case 'T':
2882 return legacyParse<parse_template_param>();
2883 case 'f':
2884 return parseFunctionParam();
2885 case 'a':
2886 switch (First[1]) {
2887 case 'a':
2888 First += 2;
2889 return parseBinaryExpr("&&");
2890 case 'd':
2891 First += 2;
2892 return parsePrefixExpr("&");
2893 case 'n':
2894 First += 2;
2895 return parseBinaryExpr("&");
2896 case 'N':
2897 First += 2;
2898 return parseBinaryExpr("&=");
2899 case 'S':
2900 First += 2;
2901 return parseBinaryExpr("=");
2902 case 't': {
2903 First += 2;
2904 Node *Ty = parseType();
2905 if (Ty == nullptr)
2906 return nullptr;
2907 return make<EnclosingExpr>("alignof (", Ty, ")");
2908 }
2909 case 'z': {
2910 First += 2;
2911 Node *Ty = parseExpr();
2912 if (Ty == nullptr)
2913 return nullptr;
2914 return make<EnclosingExpr>("alignof (", Ty, ")");
2915 }
2916 }
2917 return nullptr;
2918 case 'c':
2919 switch (First[1]) {
2920 // cc <type> <expression> # const_cast<type>(expression)
2921 case 'c': {
2922 First += 2;
2923 Node *Ty = parseType();
2924 if (Ty == nullptr)
2925 return Ty;
2926 Node *Ex = parseExpr();
2927 if (Ex == nullptr)
2928 return Ex;
2929 return make<CastExpr>("const_cast", Ty, Ex);
2930 }
2931 // cl <expression>+ E # call
2932 case 'l': {
2933 First += 2;
2934 Node *Callee = parseExpr();
2935 if (Callee == nullptr)
2936 return Callee;
2937 size_t ExprsBegin = Names.size();
2938 while (!consumeIf('E')) {
2939 Node *E = parseExpr();
2940 if (E == nullptr)
2941 return E;
2942 Names.push_back(E);
2943 }
2944 return make<CallExpr>(Callee, popTrailingNodeArray(ExprsBegin));
2945 }
2946 case 'm':
2947 First += 2;
2948 return parseBinaryExpr(",");
2949 case 'o':
2950 First += 2;
2951 return parsePrefixExpr("~");
2952 case 'v':
2953 return parseConversionExpr();
2954 }
2955 return nullptr;
2956 case 'd':
2957 switch (First[1]) {
2958 case 'a': {
2959 First += 2;
2960 Node *Ex = parseExpr();
2961 if (Ex == nullptr)
2962 return Ex;
2963 return make<DeleteExpr>(Ex, Global, /*is_array=*/true);
2964 }
2965 case 'c': {
2966 First += 2;
2967 Node *T = parseType();
2968 if (T == nullptr)
2969 return T;
2970 Node *Ex = parseExpr();
2971 if (Ex == nullptr)
2972 return Ex;
2973 return make<CastExpr>("dynamic_cast", T, Ex);
2974 }
2975 case 'e':
2976 First += 2;
2977 return parsePrefixExpr("*");
2978 case 'l': {
2979 First += 2;
2980 Node *E = parseExpr();
2981 if (E == nullptr)
2982 return E;
2983 return make<DeleteExpr>(E, Global, /*is_array=*/false);
2984 }
2985 case 'n':
2986 return legacyParse<parse_unresolved_name>();
2987 case 's': {
2988 First += 2;
2989 Node *LHS = parseExpr();
2990 if (LHS == nullptr)
2991 return nullptr;
2992 Node *RHS = parseExpr();
2993 if (RHS == nullptr)
2994 return nullptr;
2995 return make<MemberExpr>(LHS, ".*", RHS);
2996 }
2997 case 't': {
2998 First += 2;
2999 Node *LHS = parseExpr();
3000 if (LHS == nullptr)
3001 return LHS;
3002 Node *RHS = parseExpr();
3003 if (RHS == nullptr)
3004 return nullptr;
3005 return make<MemberExpr>(LHS, ".", RHS);
3006 }
3007 case 'v':
3008 First += 2;
3009 return parseBinaryExpr("/");
3010 case 'V':
3011 First += 2;
3012 return parseBinaryExpr("/=");
3013 }
3014 return nullptr;
3015 case 'e':
3016 switch (First[1]) {
3017 case 'o':
3018 First += 2;
3019 return parseBinaryExpr("^");
3020 case 'O':
3021 First += 2;
3022 return parseBinaryExpr("^=");
3023 case 'q':
3024 First += 2;
3025 return parseBinaryExpr("==");
3026 }
3027 return nullptr;
3028 case 'g':
3029 switch (First[1]) {
3030 case 'e':
3031 First += 2;
3032 return parseBinaryExpr(">=");
3033 case 't':
3034 First += 2;
3035 return parseBinaryExpr(">");
3036 }
3037 return nullptr;
3038 case 'i':
3039 if (First[1] == 'x') {
3040 First += 2;
3041 Node *Base = parseExpr();
3042 if (Base == nullptr)
3043 return nullptr;
3044 Node *Index = parseExpr();
3045 if (Index == nullptr)
3046 return Index;
3047 return make<ArraySubscriptExpr>(Base, Index);
3048 }
3049 return nullptr;
3050 case 'l':
3051 switch (First[1]) {
3052 case 'e':
3053 First += 2;
3054 return parseBinaryExpr("<=");
3055 case 's':
3056 First += 2;
3057 return parseBinaryExpr("<<");
3058 case 'S':
3059 First += 2;
3060 return parseBinaryExpr("<<=");
3061 case 't':
3062 First += 2;
3063 return parseBinaryExpr("<");
3064 }
3065 return nullptr;
3066 case 'm':
3067 switch (First[1]) {
3068 case 'i':
3069 First += 2;
3070 return parseBinaryExpr("-");
3071 case 'I':
3072 First += 2;
3073 return parseBinaryExpr("-=");
3074 case 'l':
3075 First += 2;
3076 return parseBinaryExpr("*");
3077 case 'L':
3078 First += 2;
3079 return parseBinaryExpr("*=");
3080 case 'm':
3081 First += 2;
3082 if (consumeIf('_'))
3083 return parsePrefixExpr("--");
3084 Node *Ex = parseExpr();
3085 if (Ex == nullptr)
3086 return nullptr;
3087 return make<PostfixExpr>(Ex, "--");
3088 }
3089 return nullptr;
3090 case 'n':
3091 switch (First[1]) {
3092 case 'a':
3093 case 'w':
3094 return parseNewExpr();
3095 case 'e':
3096 First += 2;
3097 return parseBinaryExpr("!=");
3098 case 'g':
3099 First += 2;
3100 return parsePrefixExpr("-");
3101 case 't':
3102 First += 2;
3103 return parsePrefixExpr("!");
3104 case 'x':
3105 First += 2;
3106 Node *Ex = parseExpr();
3107 if (Ex == nullptr)
3108 return Ex;
3109 return make<EnclosingExpr>("noexcept (", Ex, ")");
3110 }
3111 return nullptr;
3112 case 'o':
3113 switch (First[1]) {
3114 case 'n':
3115 return legacyParse<parse_unresolved_name>();
3116 case 'o':
3117 First += 2;
3118 return parseBinaryExpr("||");
3119 case 'r':
3120 First += 2;
3121 return parseBinaryExpr("|");
3122 case 'R':
3123 First += 2;
3124 return parseBinaryExpr("|=");
3125 }
3126 return nullptr;
3127 case 'p':
3128 switch (First[1]) {
3129 case 'm':
3130 First += 2;
3131 return parseBinaryExpr("->*");
3132 case 'l':
3133 First += 2;
3134 return parseBinaryExpr("+");
3135 case 'L':
3136 First += 2;
3137 return parseBinaryExpr("+=");
3138 case 'p': {
3139 First += 2;
3140 if (consumeIf('_'))
3141 return parsePrefixExpr("++");
3142 Node *Ex = parseExpr();
3143 if (Ex == nullptr)
3144 return Ex;
3145 return make<PostfixExpr>(Ex, "++");
3146 }
3147 case 's':
3148 First += 2;
3149 return parsePrefixExpr("+");
3150 case 't': {
3151 First += 2;
3152 Node *L = parseExpr();
3153 if (L == nullptr)
3154 return nullptr;
3155 Node *R = parseExpr();
3156 if (R == nullptr)
3157 return nullptr;
3158 return make<MemberExpr>(L, "->", R);
3159 }
3160 }
3161 return nullptr;
3162 case 'q':
3163 if (First[1] == 'u') {
3164 First += 2;
3165 Node *Cond = parseExpr();
3166 if (Cond == nullptr)
3167 return nullptr;
3168 Node *LHS = parseExpr();
3169 if (LHS == nullptr)
3170 return nullptr;
3171 Node *RHS = parseExpr();
3172 if (RHS == nullptr)
3173 return nullptr;
3174 return make<ConditionalExpr>(Cond, LHS, RHS);
3175 }
3176 return nullptr;
3177 case 'r':
3178 switch (First[1]) {
3179 case 'c': {
3180 First += 2;
3181 Node *T = parseType();
3182 if (T == nullptr)
3183 return T;
3184 Node *Ex = parseExpr();
3185 if (Ex == nullptr)
3186 return Ex;
3187 return make<CastExpr>("reinterpret_cast", T, Ex);
3188 }
3189 case 'm':
3190 First += 2;
3191 return parseBinaryExpr("%");
3192 case 'M':
3193 First += 2;
3194 return parseBinaryExpr("%=");
3195 case 's':
3196 First += 2;
3197 return parseBinaryExpr(">>");
3198 case 'S':
3199 First += 2;
3200 return parseBinaryExpr(">>=");
3201 }
3202 return nullptr;
3203 case 's':
3204 switch (First[1]) {
3205 case 'c': {
3206 First += 2;
3207 Node *T = parseType();
3208 if (T == nullptr)
3209 return T;
3210 Node *Ex = parseExpr();
3211 if (Ex == nullptr)
3212 return Ex;
3213 return make<CastExpr>("static_cast", T, Ex);
3214 }
3215 case 'p': {
3216 First += 2;
3217 Node *Child = parseExpr();
3218 if (Child == nullptr)
3219 return nullptr;
3220 return make<ParameterPackExpansion>(Child);
3221 }
3222 case 'r':
3223 return legacyParse<parse_unresolved_name>();
3224 case 't': {
3225 First += 2;
3226 Node *Ty = parseType();
3227 if (Ty == nullptr)
3228 return Ty;
3229 return make<EnclosingExpr>("sizeof (", Ty, ")");
3230 }
3231 case 'z': {
3232 First += 2;
3233 Node *Ex = parseExpr();
3234 if (Ex == nullptr)
3235 return Ex;
3236 return make<EnclosingExpr>("sizeof (", Ex, ")");
3237 }
3238 case 'Z':
3239 First += 2;
3240 if (look() == 'T') {
3241 Node *R = legacyParse<parse_template_param>();
3242 if (R == nullptr)
3243 return nullptr;
3244 return make<SizeofParamPackExpr>(R);
3245 } else if (look() == 'f') {
3246 Node *FP = parseFunctionParam();
3247 if (FP == nullptr)
3248 return nullptr;
3249 return make<EnclosingExpr>("sizeof...", FP, ")");
3250 }
3251 return nullptr;
3252 }
3253 return nullptr;
3254 case 't':
3255 switch (First[1]) {
3256 case 'e': {
3257 First += 2;
3258 Node *Ex = parseExpr();
3259 if (Ex == nullptr)
3260 return Ex;
3261 return make<EnclosingExpr>("typeid (", Ex, ")");
3262 }
3263 case 'i': {
3264 First += 2;
3265 Node *Ty = parseType();
3266 if (Ty == nullptr)
3267 return Ty;
3268 return make<EnclosingExpr>("typeid (", Ty, ")");
3269 }
3270 case 'r':
3271 First += 2;
3272 return make<NameType>("throw");
3273 case 'w': {
3274 First += 2;
3275 Node *Ex = parseExpr();
3276 if (Ex == nullptr)
3277 return nullptr;
3278 return make<ThrowExpr>(Ex);
3279 }
3280 }
3281 return nullptr;
3282 case '1':
3283 case '2':
3284 case '3':
3285 case '4':
3286 case '5':
3287 case '6':
3288 case '7':
3289 case '8':
3290 case '9':
3291 return legacyParse<parse_unresolved_name>();
3292 }
3293 return nullptr;
3294 }
3295
3296 // <number> ::= [n] <non-negative decimal integer>
3297
3298 const char*
parse_number(const char * first,const char * last)3299 parse_number(const char* first, const char* last)
3300 {
3301 if (first != last)
3302 {
3303 const char* t = first;
3304 if (*t == 'n')
3305 ++t;
3306 if (t != last)
3307 {
3308 if (*t == '0')
3309 {
3310 first = t+1;
3311 }
3312 else if ('1' <= *t && *t <= '9')
3313 {
3314 first = t+1;
3315 while (first != last && std::isdigit(*first))
3316 ++first;
3317 }
3318 }
3319 }
3320 return first;
3321 }
3322
3323 template <class Float>
3324 struct FloatData;
3325
3326 template <>
3327 struct FloatData<float>
3328 {
3329 static const size_t mangled_size = 8;
3330 static const size_t max_demangled_size = 24;
3331 static constexpr const char* spec = "%af";
3332 };
3333
3334 constexpr const char* FloatData<float>::spec;
3335
3336 template <>
3337 struct FloatData<double>
3338 {
3339 static const size_t mangled_size = 16;
3340 static const size_t max_demangled_size = 32;
3341 static constexpr const char* spec = "%a";
3342 };
3343
3344 constexpr const char* FloatData<double>::spec;
3345
3346 template <>
3347 struct FloatData<long double>
3348 {
3349 #if defined(__mips__) && defined(__mips_n64) || defined(__aarch64__) || \
3350 defined(__wasm__)
3351 static const size_t mangled_size = 32;
3352 #elif defined(__arm__) || defined(__mips__) || defined(__hexagon__)
3353 static const size_t mangled_size = 16;
3354 #else
3355 static const size_t mangled_size = 20; // May need to be adjusted to 16 or 24 on other platforms
3356 #endif
3357 static const size_t max_demangled_size = 40;
3358 static constexpr const char *spec = "%LaL";
3359 };
3360
3361 constexpr const char *FloatData<long double>::spec;
3362
parseFloatingLiteral()3363 template <class Float> Node *Db::parseFloatingLiteral() {
3364 const size_t N = FloatData<Float>::mangled_size;
3365 if (numLeft() <= N)
3366 return nullptr;
3367 StringView Data(First, First + N);
3368 for (char C : Data)
3369 if (!std::isxdigit(C))
3370 return nullptr;
3371 First += N;
3372 if (!consumeIf('E'))
3373 return nullptr;
3374 return make<FloatExpr<Float>>(Data);
3375 }
3376
3377 // <positive length number> ::= [0-9]*
3378 const char*
parse_positive_integer(const char * first,const char * last,size_t * out)3379 parse_positive_integer(const char* first, const char* last, size_t* out)
3380 {
3381 if (first != last)
3382 {
3383 char c = *first;
3384 if (isdigit(c) && first+1 != last)
3385 {
3386 const char* t = first+1;
3387 size_t n = static_cast<size_t>(c - '0');
3388 for (c = *t; isdigit(c); c = *t)
3389 {
3390 n = n * 10 + static_cast<size_t>(c - '0');
3391 if (++t == last)
3392 return first;
3393 }
3394 *out = n;
3395 first = t;
3396 }
3397 }
3398 return first;
3399 }
3400
3401 // extension
3402 // <abi-tag-seq> ::= <abi-tag>*
3403 // <abi-tag> ::= B <positive length number> <identifier>
3404 const char*
parse_abi_tag_seq(const char * first,const char * last,Db & db)3405 parse_abi_tag_seq(const char* first, const char* last, Db& db)
3406 {
3407 while (first != last && *first == 'B' && first+1 != last)
3408 {
3409 size_t length;
3410 const char* t = parse_positive_integer(first+1, last, &length);
3411 if (t == first+1)
3412 return first;
3413 if (static_cast<size_t>(last - t) < length || db.Names.empty())
3414 return first;
3415 db.Names.back() = db.make<AbiTagAttr>(
3416 db.Names.back(), StringView(t, t + length));
3417 first = t + length;
3418 }
3419 return first;
3420 }
3421
3422 // <source-name> ::= <positive length number> <identifier> [<abi-tag-seq>]
3423 const char*
parse_source_name(const char * first,const char * last,Db & db)3424 parse_source_name(const char* first, const char* last, Db& db)
3425 {
3426 if (first != last)
3427 {
3428 size_t length;
3429 const char* t = parse_positive_integer(first, last, &length);
3430 if (t == first)
3431 return first;
3432 if (static_cast<size_t>(last - t) >= length)
3433 {
3434 StringView r(t, t + length);
3435 if (r.substr(0, 10) == "_GLOBAL__N")
3436 db.Names.push_back(db.make<NameType>("(anonymous namespace)"));
3437 else
3438 db.Names.push_back(db.make<NameType>(r));
3439 first = t + length;
3440 first = parse_abi_tag_seq(first, last, db);
3441 }
3442 }
3443 return first;
3444 }
3445
3446 // <substitution> ::= S <seq-id> _
3447 // ::= S_
3448 // <substitution> ::= Sa # ::std::allocator
3449 // <substitution> ::= Sb # ::std::basic_string
3450 // <substitution> ::= Ss # ::std::basic_string < char,
3451 // ::std::char_traits<char>,
3452 // ::std::allocator<char> >
3453 // <substitution> ::= Si # ::std::basic_istream<char, std::char_traits<char> >
3454 // <substitution> ::= So # ::std::basic_ostream<char, std::char_traits<char> >
3455 // <substitution> ::= Sd # ::std::basic_iostream<char, std::char_traits<char> >
3456
3457 const char*
parse_substitution(const char * first,const char * last,Db & db)3458 parse_substitution(const char* first, const char* last, Db& db)
3459 {
3460 if (last - first >= 2)
3461 {
3462 if (*first == 'S')
3463 {
3464 switch (first[1])
3465 {
3466 case 'a':
3467 db.Names.push_back(
3468 db.make<SpecialSubstitution>(
3469 SpecialSubKind::allocator));
3470 first += 2;
3471 break;
3472 case 'b':
3473 db.Names.push_back(
3474 db.make<SpecialSubstitution>(SpecialSubKind::basic_string));
3475 first += 2;
3476 break;
3477 case 's':
3478 db.Names.push_back(
3479 db.make<SpecialSubstitution>(
3480 SpecialSubKind::string));
3481 first += 2;
3482 break;
3483 case 'i':
3484 db.Names.push_back(db.make<SpecialSubstitution>(SpecialSubKind::istream));
3485 first += 2;
3486 break;
3487 case 'o':
3488 db.Names.push_back(db.make<SpecialSubstitution>(SpecialSubKind::ostream));
3489 first += 2;
3490 break;
3491 case 'd':
3492 db.Names.push_back(db.make<SpecialSubstitution>(SpecialSubKind::iostream));
3493 first += 2;
3494 break;
3495 case '_':
3496 if (!db.Subs.empty())
3497 {
3498 db.Names.push_back(db.Subs[0]);
3499 first += 2;
3500 }
3501 break;
3502 default:
3503 if (std::isdigit(first[1]) || std::isupper(first[1]))
3504 {
3505 size_t sub = 0;
3506 const char* t = first+1;
3507 if (std::isdigit(*t))
3508 sub = static_cast<size_t>(*t - '0');
3509 else
3510 sub = static_cast<size_t>(*t - 'A') + 10;
3511 for (++t; t != last && (std::isdigit(*t) || std::isupper(*t)); ++t)
3512 {
3513 sub *= 36;
3514 if (std::isdigit(*t))
3515 sub += static_cast<size_t>(*t - '0');
3516 else
3517 sub += static_cast<size_t>(*t - 'A') + 10;
3518 }
3519 if (t == last || *t != '_')
3520 return first;
3521 ++sub;
3522 if (sub < db.Subs.size())
3523 {
3524 db.Names.push_back(db.Subs[sub]);
3525 first = t+1;
3526 }
3527 }
3528 break;
3529 }
3530 }
3531 }
3532 return first;
3533 }
3534
3535 // <CV-Qualifiers> ::= [r] [V] [K]
3536
3537 const char*
parse_cv_qualifiers(const char * first,const char * last,Qualifiers & cv)3538 parse_cv_qualifiers(const char* first, const char* last, Qualifiers& cv)
3539 {
3540 cv = QualNone;
3541 if (first != last)
3542 {
3543 if (*first == 'r')
3544 {
3545 addQualifiers(cv, QualRestrict);
3546 ++first;
3547 }
3548 if (*first == 'V')
3549 {
3550 addQualifiers(cv, QualVolatile);
3551 ++first;
3552 }
3553 if (*first == 'K')
3554 {
3555 addQualifiers(cv, QualConst);
3556 ++first;
3557 }
3558 }
3559 return first;
3560 }
3561
3562 // <template-param> ::= T_ # first template parameter
3563 // ::= T <parameter-2 non-negative number> _
3564
3565 const char*
parse_template_param(const char * first,const char * last,Db & db)3566 parse_template_param(const char* first, const char* last, Db& db)
3567 {
3568 if (last - first >= 2)
3569 {
3570 if (*first == 'T')
3571 {
3572 if (first[1] == '_')
3573 {
3574 if (!db.TemplateParams.empty())
3575 {
3576 db.Names.push_back(db.TemplateParams[0]);
3577 first += 2;
3578 }
3579 else
3580 {
3581 db.Names.push_back(db.make<NameType>("T_"));
3582 first += 2;
3583 db.FixForwardReferences = true;
3584 }
3585 }
3586 else if (isdigit(first[1]))
3587 {
3588 const char* t = first+1;
3589 size_t sub = static_cast<size_t>(*t - '0');
3590 for (++t; t != last && isdigit(*t); ++t)
3591 {
3592 sub *= 10;
3593 sub += static_cast<size_t>(*t - '0');
3594 }
3595 if (t == last || *t != '_')
3596 return first;
3597 ++sub;
3598 if (sub < db.TemplateParams.size())
3599 {
3600 db.Names.push_back(db.TemplateParams[sub]);
3601 first = t+1;
3602 }
3603 else
3604 {
3605 db.Names.push_back(
3606 db.make<NameType>(StringView(first, t + 1)));
3607 first = t+1;
3608 db.FixForwardReferences = true;
3609 }
3610 }
3611 }
3612 }
3613 return first;
3614 }
3615
3616 // <simple-id> ::= <source-name> [ <template-args> ]
3617
3618 const char*
parse_simple_id(const char * first,const char * last,Db & db)3619 parse_simple_id(const char* first, const char* last, Db& db)
3620 {
3621 if (first != last)
3622 {
3623 const char* t = parse_source_name(first, last, db);
3624 if (t != first)
3625 {
3626 const char* t1 = parse_template_args(t, last, db);
3627 if (t1 != t)
3628 {
3629 if (db.Names.size() < 2)
3630 return first;
3631 auto args = db.Names.back();
3632 db.Names.pop_back();
3633 db.Names.back() =
3634 db.make<NameWithTemplateArgs>(db.Names.back(), args);
3635 }
3636 first = t1;
3637 }
3638 else
3639 first = t;
3640 }
3641 return first;
3642 }
3643
3644 // <unresolved-type> ::= <template-param>
3645 // ::= <decltype>
3646 // ::= <substitution>
3647
3648 const char*
parse_unresolved_type(const char * first,const char * last,Db & db)3649 parse_unresolved_type(const char* first, const char* last, Db& db)
3650 {
3651 if (first != last)
3652 {
3653 const char* t = first;
3654 switch (*first)
3655 {
3656 case 'T':
3657 {
3658 size_t k0 = db.Names.size();
3659 t = parse_template_param(first, last, db);
3660 size_t k1 = db.Names.size();
3661 if (t != first && k1 == k0 + 1)
3662 {
3663 db.Subs.push_back(db.Names.back());
3664 first = t;
3665 }
3666 else
3667 {
3668 for (; k1 != k0; --k1)
3669 db.Names.pop_back();
3670 }
3671 break;
3672 }
3673 case 'D':
3674 t = parse_decltype(first, last, db);
3675 if (t != first)
3676 {
3677 if (db.Names.empty())
3678 return first;
3679 db.Subs.push_back(db.Names.back());
3680 first = t;
3681 }
3682 break;
3683 case 'S':
3684 t = parse_substitution(first, last, db);
3685 if (t != first)
3686 first = t;
3687 else
3688 {
3689 if (last - first > 2 && first[1] == 't')
3690 {
3691 t = parse_unqualified_name(first+2, last, db);
3692 if (t != first+2)
3693 {
3694 if (db.Names.empty())
3695 return first;
3696 db.Names.back() =
3697 db.make<StdQualifiedName>(db.Names.back());
3698 db.Subs.push_back(db.Names.back());
3699 first = t;
3700 }
3701 }
3702 }
3703 break;
3704 }
3705 }
3706 return first;
3707 }
3708
3709 // <destructor-name> ::= <unresolved-type> # e.g., ~T or ~decltype(f())
3710 // ::= <simple-id> # e.g., ~A<2*N>
3711
3712 const char*
parse_destructor_name(const char * first,const char * last,Db & db)3713 parse_destructor_name(const char* first, const char* last, Db& db)
3714 {
3715 if (first != last)
3716 {
3717 const char* t = parse_unresolved_type(first, last, db);
3718 if (t == first)
3719 t = parse_simple_id(first, last, db);
3720 if (t != first)
3721 {
3722 if (db.Names.empty())
3723 return first;
3724 db.Names.back() = db.make<DtorName>(db.Names.back());
3725 first = t;
3726 }
3727 }
3728 return first;
3729 }
3730
3731 // <base-unresolved-name> ::= <simple-id> # unresolved name
3732 // extension ::= <operator-name> # unresolved operator-function-id
3733 // extension ::= <operator-name> <template-args> # unresolved operator template-id
3734 // ::= on <operator-name> # unresolved operator-function-id
3735 // ::= on <operator-name> <template-args> # unresolved operator template-id
3736 // ::= dn <destructor-name> # destructor or pseudo-destructor;
3737 // # e.g. ~X or ~X<N-1>
3738
3739 const char*
parse_base_unresolved_name(const char * first,const char * last,Db & db)3740 parse_base_unresolved_name(const char* first, const char* last, Db& db)
3741 {
3742 if (last - first >= 2)
3743 {
3744 if ((first[0] == 'o' || first[0] == 'd') && first[1] == 'n')
3745 {
3746 if (first[0] == 'o')
3747 {
3748 const char* t = parse_operator_name(first+2, last, db);
3749 if (t != first+2)
3750 {
3751 first = parse_template_args(t, last, db);
3752 if (first != t)
3753 {
3754 if (db.Names.size() < 2)
3755 return first;
3756 auto args = db.Names.back();
3757 db.Names.pop_back();
3758 db.Names.back() =
3759 db.make<NameWithTemplateArgs>(
3760 db.Names.back(), args);
3761 }
3762 }
3763 }
3764 else
3765 {
3766 const char* t = parse_destructor_name(first+2, last, db);
3767 if (t != first+2)
3768 first = t;
3769 }
3770 }
3771 else
3772 {
3773 const char* t = parse_simple_id(first, last, db);
3774 if (t == first)
3775 {
3776 t = parse_operator_name(first, last, db);
3777 if (t != first)
3778 {
3779 first = parse_template_args(t, last, db);
3780 if (first != t)
3781 {
3782 if (db.Names.size() < 2)
3783 return first;
3784 auto args = db.Names.back();
3785 db.Names.pop_back();
3786 db.Names.back() =
3787 db.make<NameWithTemplateArgs>(
3788 db.Names.back(), args);
3789 }
3790 }
3791 }
3792 else
3793 first = t;
3794 }
3795 }
3796 return first;
3797 }
3798
3799 // <unresolved-qualifier-level> ::= <simple-id>
3800
3801 const char*
parse_unresolved_qualifier_level(const char * first,const char * last,Db & db)3802 parse_unresolved_qualifier_level(const char* first, const char* last, Db& db)
3803 {
3804 return parse_simple_id(first, last, db);
3805 }
3806
3807 // <unresolved-name>
3808 // extension ::= srN <unresolved-type> [<template-args>] <unresolved-qualifier-level>* E <base-unresolved-name>
3809 // ::= [gs] <base-unresolved-name> # x or (with "gs") ::x
3810 // ::= [gs] sr <unresolved-qualifier-level>+ E <base-unresolved-name>
3811 // # A::x, N::y, A<T>::z; "gs" means leading "::"
3812 // ::= sr <unresolved-type> <base-unresolved-name> # T::x / decltype(p)::x
3813 // extension ::= sr <unresolved-type> <template-args> <base-unresolved-name>
3814 // # T::N::x /decltype(p)::N::x
3815 // (ignored) ::= srN <unresolved-type> <unresolved-qualifier-level>+ E <base-unresolved-name>
3816
3817 const char*
parse_unresolved_name(const char * first,const char * last,Db & db)3818 parse_unresolved_name(const char* first, const char* last, Db& db)
3819 {
3820 if (last - first > 2)
3821 {
3822 const char* t = first;
3823 bool global = false;
3824 if (t[0] == 'g' && t[1] == 's')
3825 {
3826 global = true;
3827 t += 2;
3828 }
3829 const char* t2 = parse_base_unresolved_name(t, last, db);
3830 if (t2 != t)
3831 {
3832 if (global)
3833 {
3834 if (db.Names.empty())
3835 return first;
3836 db.Names.back() =
3837 db.make<GlobalQualifiedName>(db.Names.back());
3838 }
3839 first = t2;
3840 }
3841 else if (last - t > 2 && t[0] == 's' && t[1] == 'r')
3842 {
3843 if (t[2] == 'N')
3844 {
3845 t += 3;
3846 const char* t1 = parse_unresolved_type(t, last, db);
3847 if (t1 == t || t1 == last)
3848 return first;
3849 t = t1;
3850 t1 = parse_template_args(t, last, db);
3851 if (t1 != t)
3852 {
3853 if (db.Names.size() < 2)
3854 return first;
3855 auto args = db.Names.back();
3856 db.Names.pop_back();
3857 db.Names.back() = db.make<NameWithTemplateArgs>(
3858 db.Names.back(), args);
3859 t = t1;
3860 if (t == last)
3861 {
3862 db.Names.pop_back();
3863 return first;
3864 }
3865 }
3866 while (*t != 'E')
3867 {
3868 t1 = parse_unresolved_qualifier_level(t, last, db);
3869 if (t1 == t || t1 == last || db.Names.size() < 2)
3870 return first;
3871 auto s = db.Names.back();
3872 db.Names.pop_back();
3873 db.Names.back() =
3874 db.make<QualifiedName>(db.Names.back(), s);
3875 t = t1;
3876 }
3877 ++t;
3878 t1 = parse_base_unresolved_name(t, last, db);
3879 if (t1 == t)
3880 {
3881 if (!db.Names.empty())
3882 db.Names.pop_back();
3883 return first;
3884 }
3885 if (db.Names.size() < 2)
3886 return first;
3887 auto s = db.Names.back();
3888 db.Names.pop_back();
3889 db.Names.back() =
3890 db.make<QualifiedName>(db.Names.back(), s);
3891 first = t1;
3892 }
3893 else
3894 {
3895 t += 2;
3896 const char* t1 = parse_unresolved_type(t, last, db);
3897 if (t1 != t)
3898 {
3899 t = t1;
3900 t1 = parse_template_args(t, last, db);
3901 if (t1 != t)
3902 {
3903 if (db.Names.size() < 2)
3904 return first;
3905 auto args = db.Names.back();
3906 db.Names.pop_back();
3907 db.Names.back() =
3908 db.make<NameWithTemplateArgs>(
3909 db.Names.back(), args);
3910 t = t1;
3911 }
3912 t1 = parse_base_unresolved_name(t, last, db);
3913 if (t1 == t)
3914 {
3915 if (!db.Names.empty())
3916 db.Names.pop_back();
3917 return first;
3918 }
3919 if (db.Names.size() < 2)
3920 return first;
3921 auto s = db.Names.back();
3922 db.Names.pop_back();
3923 db.Names.back() =
3924 db.make<QualifiedName>(db.Names.back(), s);
3925 first = t1;
3926 }
3927 else
3928 {
3929 t1 = parse_unresolved_qualifier_level(t, last, db);
3930 if (t1 == t || t1 == last)
3931 return first;
3932 t = t1;
3933 if (global)
3934 {
3935 if (db.Names.empty())
3936 return first;
3937 db.Names.back() =
3938 db.make<GlobalQualifiedName>(
3939 db.Names.back());
3940 }
3941 while (*t != 'E')
3942 {
3943 t1 = parse_unresolved_qualifier_level(t, last, db);
3944 if (t1 == t || t1 == last || db.Names.size() < 2)
3945 return first;
3946 auto s = db.Names.back();
3947 db.Names.pop_back();
3948 db.Names.back() = db.make<QualifiedName>(
3949 db.Names.back(), s);
3950 t = t1;
3951 }
3952 ++t;
3953 t1 = parse_base_unresolved_name(t, last, db);
3954 if (t1 == t)
3955 {
3956 if (!db.Names.empty())
3957 db.Names.pop_back();
3958 return first;
3959 }
3960 if (db.Names.size() < 2)
3961 return first;
3962 auto s = db.Names.back();
3963 db.Names.pop_back();
3964 db.Names.back() =
3965 db.make<QualifiedName>(db.Names.back(), s);
3966 first = t1;
3967 }
3968 }
3969 }
3970 }
3971 return first;
3972 }
3973
3974 // <operator-name>
3975 // ::= aa # &&
3976 // ::= ad # & (unary)
3977 // ::= an # &
3978 // ::= aN # &=
3979 // ::= aS # =
3980 // ::= cl # ()
3981 // ::= cm # ,
3982 // ::= co # ~
3983 // ::= cv <type> # (cast)
3984 // ::= da # delete[]
3985 // ::= de # * (unary)
3986 // ::= dl # delete
3987 // ::= dv # /
3988 // ::= dV # /=
3989 // ::= eo # ^
3990 // ::= eO # ^=
3991 // ::= eq # ==
3992 // ::= ge # >=
3993 // ::= gt # >
3994 // ::= ix # []
3995 // ::= le # <=
3996 // ::= li <source-name> # operator ""
3997 // ::= ls # <<
3998 // ::= lS # <<=
3999 // ::= lt # <
4000 // ::= mi # -
4001 // ::= mI # -=
4002 // ::= ml # *
4003 // ::= mL # *=
4004 // ::= mm # -- (postfix in <expression> context)
4005 // ::= na # new[]
4006 // ::= ne # !=
4007 // ::= ng # - (unary)
4008 // ::= nt # !
4009 // ::= nw # new
4010 // ::= oo # ||
4011 // ::= or # |
4012 // ::= oR # |=
4013 // ::= pm # ->*
4014 // ::= pl # +
4015 // ::= pL # +=
4016 // ::= pp # ++ (postfix in <expression> context)
4017 // ::= ps # + (unary)
4018 // ::= pt # ->
4019 // ::= qu # ?
4020 // ::= rm # %
4021 // ::= rM # %=
4022 // ::= rs # >>
4023 // ::= rS # >>=
4024 // ::= v <digit> <source-name> # vendor extended operator
4025 // extension ::= <operator-name> <abi-tag-seq>
4026 const char*
parse_operator_name(const char * first,const char * last,Db & db)4027 parse_operator_name(const char* first, const char* last, Db& db)
4028 {
4029 const char* original_first = first;
4030 if (last - first >= 2)
4031 {
4032 switch (first[0])
4033 {
4034 case 'a':
4035 switch (first[1])
4036 {
4037 case 'a':
4038 db.Names.push_back(db.make<NameType>("operator&&"));
4039 first += 2;
4040 break;
4041 case 'd':
4042 case 'n':
4043 db.Names.push_back(db.make<NameType>("operator&"));
4044 first += 2;
4045 break;
4046 case 'N':
4047 db.Names.push_back(db.make<NameType>("operator&="));
4048 first += 2;
4049 break;
4050 case 'S':
4051 db.Names.push_back(db.make<NameType>("operator="));
4052 first += 2;
4053 break;
4054 }
4055 break;
4056 case 'c':
4057 switch (first[1])
4058 {
4059 case 'l':
4060 db.Names.push_back(db.make<NameType>("operator()"));
4061 first += 2;
4062 break;
4063 case 'm':
4064 db.Names.push_back(db.make<NameType>("operator,"));
4065 first += 2;
4066 break;
4067 case 'o':
4068 db.Names.push_back(db.make<NameType>("operator~"));
4069 first += 2;
4070 break;
4071 case 'v':
4072 {
4073 bool TryToParseTemplateArgs = db.TryToParseTemplateArgs;
4074 db.TryToParseTemplateArgs = false;
4075 const char* t = parse_type(first+2, last, db);
4076 db.TryToParseTemplateArgs = TryToParseTemplateArgs;
4077 if (t != first+2)
4078 {
4079 if (db.Names.empty())
4080 return first;
4081 db.Names.back() =
4082 db.make<ConversionOperatorType>(db.Names.back());
4083 db.ParsedCtorDtorCV = true;
4084 first = t;
4085 }
4086 }
4087 break;
4088 }
4089 break;
4090 case 'd':
4091 switch (first[1])
4092 {
4093 case 'a':
4094 db.Names.push_back(db.make<NameType>("operator delete[]"));
4095 first += 2;
4096 break;
4097 case 'e':
4098 db.Names.push_back(db.make<NameType>("operator*"));
4099 first += 2;
4100 break;
4101 case 'l':
4102 db.Names.push_back(db.make<NameType>("operator delete"));
4103 first += 2;
4104 break;
4105 case 'v':
4106 db.Names.push_back(db.make<NameType>("operator/"));
4107 first += 2;
4108 break;
4109 case 'V':
4110 db.Names.push_back(db.make<NameType>("operator/="));
4111 first += 2;
4112 break;
4113 }
4114 break;
4115 case 'e':
4116 switch (first[1])
4117 {
4118 case 'o':
4119 db.Names.push_back(db.make<NameType>("operator^"));
4120 first += 2;
4121 break;
4122 case 'O':
4123 db.Names.push_back(db.make<NameType>("operator^="));
4124 first += 2;
4125 break;
4126 case 'q':
4127 db.Names.push_back(db.make<NameType>("operator=="));
4128 first += 2;
4129 break;
4130 }
4131 break;
4132 case 'g':
4133 switch (first[1])
4134 {
4135 case 'e':
4136 db.Names.push_back(db.make<NameType>("operator>="));
4137 first += 2;
4138 break;
4139 case 't':
4140 db.Names.push_back(db.make<NameType>("operator>"));
4141 first += 2;
4142 break;
4143 }
4144 break;
4145 case 'i':
4146 if (first[1] == 'x')
4147 {
4148 db.Names.push_back(db.make<NameType>("operator[]"));
4149 first += 2;
4150 }
4151 break;
4152 case 'l':
4153 switch (first[1])
4154 {
4155 case 'e':
4156 db.Names.push_back(db.make<NameType>("operator<="));
4157 first += 2;
4158 break;
4159 case 'i':
4160 {
4161 const char* t = parse_source_name(first+2, last, db);
4162 if (t != first+2)
4163 {
4164 if (db.Names.empty())
4165 return first;
4166 db.Names.back() =
4167 db.make<LiteralOperator>(db.Names.back());
4168 first = t;
4169 }
4170 }
4171 break;
4172 case 's':
4173 db.Names.push_back(db.make<NameType>("operator<<"));
4174 first += 2;
4175 break;
4176 case 'S':
4177 db.Names.push_back(db.make<NameType>("operator<<="));
4178 first += 2;
4179 break;
4180 case 't':
4181 db.Names.push_back(db.make<NameType>("operator<"));
4182 first += 2;
4183 break;
4184 }
4185 break;
4186 case 'm':
4187 switch (first[1])
4188 {
4189 case 'i':
4190 db.Names.push_back(db.make<NameType>("operator-"));
4191 first += 2;
4192 break;
4193 case 'I':
4194 db.Names.push_back(db.make<NameType>("operator-="));
4195 first += 2;
4196 break;
4197 case 'l':
4198 db.Names.push_back(db.make<NameType>("operator*"));
4199 first += 2;
4200 break;
4201 case 'L':
4202 db.Names.push_back(db.make<NameType>("operator*="));
4203 first += 2;
4204 break;
4205 case 'm':
4206 db.Names.push_back(db.make<NameType>("operator--"));
4207 first += 2;
4208 break;
4209 }
4210 break;
4211 case 'n':
4212 switch (first[1])
4213 {
4214 case 'a':
4215 db.Names.push_back(db.make<NameType>("operator new[]"));
4216 first += 2;
4217 break;
4218 case 'e':
4219 db.Names.push_back(db.make<NameType>("operator!="));
4220 first += 2;
4221 break;
4222 case 'g':
4223 db.Names.push_back(db.make<NameType>("operator-"));
4224 first += 2;
4225 break;
4226 case 't':
4227 db.Names.push_back(db.make<NameType>("operator!"));
4228 first += 2;
4229 break;
4230 case 'w':
4231 db.Names.push_back(db.make<NameType>("operator new"));
4232 first += 2;
4233 break;
4234 }
4235 break;
4236 case 'o':
4237 switch (first[1])
4238 {
4239 case 'o':
4240 db.Names.push_back(db.make<NameType>("operator||"));
4241 first += 2;
4242 break;
4243 case 'r':
4244 db.Names.push_back(db.make<NameType>("operator|"));
4245 first += 2;
4246 break;
4247 case 'R':
4248 db.Names.push_back(db.make<NameType>("operator|="));
4249 first += 2;
4250 break;
4251 }
4252 break;
4253 case 'p':
4254 switch (first[1])
4255 {
4256 case 'm':
4257 db.Names.push_back(db.make<NameType>("operator->*"));
4258 first += 2;
4259 break;
4260 case 'l':
4261 db.Names.push_back(db.make<NameType>("operator+"));
4262 first += 2;
4263 break;
4264 case 'L':
4265 db.Names.push_back(db.make<NameType>("operator+="));
4266 first += 2;
4267 break;
4268 case 'p':
4269 db.Names.push_back(db.make<NameType>("operator++"));
4270 first += 2;
4271 break;
4272 case 's':
4273 db.Names.push_back(db.make<NameType>("operator+"));
4274 first += 2;
4275 break;
4276 case 't':
4277 db.Names.push_back(db.make<NameType>("operator->"));
4278 first += 2;
4279 break;
4280 }
4281 break;
4282 case 'q':
4283 if (first[1] == 'u')
4284 {
4285 db.Names.push_back(db.make<NameType>("operator?"));
4286 first += 2;
4287 }
4288 break;
4289 case 'r':
4290 switch (first[1])
4291 {
4292 case 'm':
4293 db.Names.push_back(db.make<NameType>("operator%"));
4294 first += 2;
4295 break;
4296 case 'M':
4297 db.Names.push_back(db.make<NameType>("operator%="));
4298 first += 2;
4299 break;
4300 case 's':
4301 db.Names.push_back(db.make<NameType>("operator>>"));
4302 first += 2;
4303 break;
4304 case 'S':
4305 db.Names.push_back(db.make<NameType>("operator>>="));
4306 first += 2;
4307 break;
4308 }
4309 break;
4310 case 'v':
4311 if (std::isdigit(first[1]))
4312 {
4313 const char* t = parse_source_name(first+2, last, db);
4314 if (t != first+2)
4315 {
4316 if (db.Names.empty())
4317 return first;
4318 db.Names.back() =
4319 db.make<ConversionOperatorType>(db.Names.back());
4320 first = t;
4321 }
4322 }
4323 break;
4324 }
4325 }
4326
4327 if (original_first != first)
4328 first = parse_abi_tag_seq(first, last, db);
4329
4330 return first;
4331 }
4332
maybe_change_special_sub_name(Node * inp,Db & db)4333 Node* maybe_change_special_sub_name(Node* inp, Db& db)
4334 {
4335 if (inp->K != Node::KSpecialSubstitution)
4336 return inp;
4337 auto Kind = static_cast<SpecialSubstitution*>(inp)->SSK;
4338 switch (Kind)
4339 {
4340 case SpecialSubKind::string:
4341 case SpecialSubKind::istream:
4342 case SpecialSubKind::ostream:
4343 case SpecialSubKind::iostream:
4344 return db.make<ExpandedSpecialSubstitution>(Kind);
4345 default:
4346 break;
4347 }
4348 return inp;
4349 }
4350
4351 // <ctor-dtor-name> ::= C1 # complete object constructor
4352 // ::= C2 # base object constructor
4353 // ::= C3 # complete object allocating constructor
4354 // extension ::= C5 # ?
4355 // ::= D0 # deleting destructor
4356 // ::= D1 # complete object destructor
4357 // ::= D2 # base object destructor
4358 // extension ::= D5 # ?
4359 // extension ::= <ctor-dtor-name> <abi-tag-seq>
4360 const char*
parse_ctor_dtor_name(const char * first,const char * last,Db & db)4361 parse_ctor_dtor_name(const char* first, const char* last, Db& db)
4362 {
4363 if (last-first >= 2 && !db.Names.empty())
4364 {
4365 switch (first[0])
4366 {
4367 case 'C':
4368 switch (first[1])
4369 {
4370 case '1':
4371 case '2':
4372 case '3':
4373 case '5':
4374 if (db.Names.empty())
4375 return first;
4376 db.Names.back() =
4377 maybe_change_special_sub_name(db.Names.back(), db);
4378 db.Names.push_back(
4379 db.make<CtorDtorName>(db.Names.back(), false));
4380 first += 2;
4381 first = parse_abi_tag_seq(first, last, db);
4382 db.ParsedCtorDtorCV = true;
4383 break;
4384 }
4385 break;
4386 case 'D':
4387 switch (first[1])
4388 {
4389 case '0':
4390 case '1':
4391 case '2':
4392 case '5':
4393 if (db.Names.empty())
4394 return first;
4395 db.Names.push_back(
4396 db.make<CtorDtorName>(db.Names.back(), true));
4397 first += 2;
4398 first = parse_abi_tag_seq(first, last, db);
4399 db.ParsedCtorDtorCV = true;
4400 break;
4401 }
4402 break;
4403 }
4404 }
4405 return first;
4406 }
4407
4408 // <unnamed-type-name> ::= Ut [<nonnegative number>] _ [<abi-tag-seq>]
4409 // ::= <closure-type-name>
4410 //
4411 // <closure-type-name> ::= Ul <lambda-sig> E [ <nonnegative number> ] _
4412 //
4413 // <lambda-sig> ::= <parameter type>+ # Parameter types or "v" if the lambda has no parameters
4414 const char*
parse_unnamed_type_name(const char * first,const char * last,Db & db)4415 parse_unnamed_type_name(const char* first, const char* last, Db& db)
4416 {
4417 if (last - first > 2 && first[0] == 'U')
4418 {
4419 char type = first[1];
4420 switch (type)
4421 {
4422 case 't':
4423 {
4424 const char* t0 = first+2;
4425 if (t0 == last)
4426 return first;
4427 StringView count;
4428 if (std::isdigit(*t0))
4429 {
4430 const char* t1 = t0 + 1;
4431 while (t1 != last && std::isdigit(*t1))
4432 ++t1;
4433 count = StringView(t0, t1);
4434 t0 = t1;
4435 }
4436 if (t0 == last || *t0 != '_')
4437 return first;
4438 db.Names.push_back(db.make<UnnamedTypeName>(count));
4439 first = t0 + 1;
4440 first = parse_abi_tag_seq(first, last, db);
4441 }
4442 break;
4443 case 'l':
4444 {
4445 size_t begin_pos = db.Names.size();
4446 const char* t0 = first+2;
4447 NodeArray lambda_params;
4448 if (first[2] == 'v')
4449 {
4450 ++t0;
4451 }
4452 else
4453 {
4454 while (true)
4455 {
4456 const char* t1 = parse_type(t0, last, db);
4457 if (t1 == t0)
4458 break;
4459 t0 = t1;
4460 }
4461 if (db.Names.size() < begin_pos)
4462 return first;
4463 lambda_params = db.popTrailingNodeArray(begin_pos);
4464 }
4465 if (t0 == last || *t0 != 'E')
4466 return first;
4467 ++t0;
4468 if (t0 == last)
4469 return first;
4470 StringView count;
4471 if (std::isdigit(*t0))
4472 {
4473 const char* t1 = t0 + 1;
4474 while (t1 != last && std::isdigit(*t1))
4475 ++t1;
4476 count = StringView(t0, t1);
4477 t0 = t1;
4478 }
4479 if (t0 == last || *t0 != '_')
4480 return first;
4481 db.Names.push_back(db.make<LambdaTypeName>(lambda_params, count));
4482 first = t0 + 1;
4483 }
4484 break;
4485 }
4486 }
4487 return first;
4488 }
4489
4490 // <unqualified-name> ::= <operator-name>
4491 // ::= <ctor-dtor-name>
4492 // ::= <source-name>
4493 // ::= <unnamed-type-name>
4494
4495 const char*
parse_unqualified_name(const char * first,const char * last,Db & db)4496 parse_unqualified_name(const char* first, const char* last, Db& db)
4497 {
4498 if (first != last)
4499 {
4500 const char* t;
4501 switch (*first)
4502 {
4503 case 'C':
4504 case 'D':
4505 t = parse_ctor_dtor_name(first, last, db);
4506 if (t != first)
4507 first = t;
4508 break;
4509 case 'U':
4510 t = parse_unnamed_type_name(first, last, db);
4511 if (t != first)
4512 first = t;
4513 break;
4514 case '1':
4515 case '2':
4516 case '3':
4517 case '4':
4518 case '5':
4519 case '6':
4520 case '7':
4521 case '8':
4522 case '9':
4523 t = parse_source_name(first, last, db);
4524 if (t != first)
4525 first = t;
4526 break;
4527 default:
4528 t = parse_operator_name(first, last, db);
4529 if (t != first)
4530 first = t;
4531 break;
4532 };
4533 }
4534 return first;
4535 }
4536
4537 // <unscoped-name> ::= <unqualified-name>
4538 // ::= St <unqualified-name> # ::std::
4539 // extension ::= StL<unqualified-name>
4540
4541 const char*
parse_unscoped_name(const char * first,const char * last,Db & db)4542 parse_unscoped_name(const char* first, const char* last, Db& db)
4543 {
4544 if (last - first >= 2)
4545 {
4546 const char* t0 = first;
4547 bool St = false;
4548 if (first[0] == 'S' && first[1] == 't')
4549 {
4550 t0 += 2;
4551 St = true;
4552 if (t0 != last && *t0 == 'L')
4553 ++t0;
4554 }
4555 const char* t1 = parse_unqualified_name(t0, last, db);
4556 if (t1 != t0)
4557 {
4558 if (St)
4559 {
4560 if (db.Names.empty())
4561 return first;
4562 db.Names.back() =
4563 db.make<StdQualifiedName>(db.Names.back());
4564 }
4565 first = t1;
4566 }
4567 }
4568 return first;
4569 }
4570
4571 // <template-arg> ::= <type> # type or template
4572 // ::= X <expression> E # expression
4573 // ::= <expr-primary> # simple expressions
4574 // ::= J <template-arg>* E # argument pack
4575 // ::= LZ <encoding> E # extension
4576 const char*
parse_template_arg(const char * first,const char * last,Db & db)4577 parse_template_arg(const char* first, const char* last, Db& db)
4578 {
4579 if (first != last)
4580 {
4581 const char* t;
4582 switch (*first)
4583 {
4584 case 'X':
4585 t = parse_expression(first+1, last, db);
4586 if (t != first+1)
4587 {
4588 if (t != last && *t == 'E')
4589 first = t+1;
4590 }
4591 break;
4592 case 'J': {
4593 t = first+1;
4594 if (t == last)
4595 return first;
4596 size_t ArgsBegin = db.Names.size();
4597 while (*t != 'E')
4598 {
4599 const char* t1 = parse_template_arg(t, last, db);
4600 if (t1 == t)
4601 return first;
4602 t = t1;
4603 }
4604 NodeArray Args = db.popTrailingNodeArray(ArgsBegin);
4605 db.Names.push_back(db.make<TemplateArgumentPack>(Args));
4606 first = t+1;
4607 break;
4608 }
4609 case 'L':
4610 // <expr-primary> or LZ <encoding> E
4611 if (first+1 != last && first[1] == 'Z')
4612 {
4613 t = parse_encoding(first+2, last, db);
4614 if (t != first+2 && t != last && *t == 'E')
4615 first = t+1;
4616 }
4617 else
4618 first = parse_expr_primary(first, last, db);
4619 break;
4620 default:
4621 // <type>
4622 first = parse_type(first, last, db);
4623 break;
4624 }
4625 }
4626 return first;
4627 }
4628
4629 // <template-args> ::= I <template-arg>* E
4630 // extension, the abi says <template-arg>+
4631 const char*
parse_template_args(const char * first,const char * last,Db & db)4632 parse_template_args(const char* first, const char* last, Db& db)
4633 {
4634 if (last - first >= 2 && *first == 'I')
4635 {
4636 if (db.TagTemplates)
4637 db.TemplateParams.clear();
4638 const char* t = first+1;
4639 size_t begin_idx = db.Names.size();
4640 while (*t != 'E')
4641 {
4642 if (db.TagTemplates)
4643 {
4644 auto TmpParams = std::move(db.TemplateParams);
4645 size_t k0 = db.Names.size();
4646 const char* t1 = parse_template_arg(t, last, db);
4647 size_t k1 = db.Names.size();
4648 db.TemplateParams = std::move(TmpParams);
4649 if (t1 == t || t1 == last || k0 + 1 != k1)
4650 return first;
4651 Node *TableEntry = db.Names.back();
4652 if (TableEntry->getKind() == Node::KTemplateArgumentPack)
4653 TableEntry = db.make<ParameterPack>(
4654 static_cast<TemplateArgumentPack*>(TableEntry)
4655 ->getElements());
4656 db.TemplateParams.push_back(TableEntry);
4657 t = t1;
4658 continue;
4659 }
4660 size_t k0 = db.Names.size();
4661 const char* t1 = parse_template_arg(t, last, db);
4662 size_t k1 = db.Names.size();
4663 if (t1 == t || t1 == last || k0 > k1)
4664 return first;
4665 t = t1;
4666 }
4667 if (begin_idx > db.Names.size())
4668 return first;
4669 first = t + 1;
4670 auto *tp = db.make<TemplateArgs>(
4671 db.popTrailingNodeArray(begin_idx));
4672 db.Names.push_back(tp);
4673 }
4674 return first;
4675 }
4676
4677 // <nested-name> ::= N [<CV-Qualifiers>] [<ref-qualifier>] <prefix> <unqualified-name> E
4678 // ::= N [<CV-Qualifiers>] [<ref-qualifier>] <template-prefix> <template-args> E
4679 //
4680 // <prefix> ::= <prefix> <unqualified-name>
4681 // ::= <template-prefix> <template-args>
4682 // ::= <template-param>
4683 // ::= <decltype>
4684 // ::= # empty
4685 // ::= <substitution>
4686 // ::= <prefix> <data-member-prefix>
4687 // extension ::= L
4688 //
4689 // <template-prefix> ::= <prefix> <template unqualified-name>
4690 // ::= <template-param>
4691 // ::= <substitution>
4692
4693 const char*
parse_nested_name(const char * first,const char * last,Db & db,bool * ends_with_template_args)4694 parse_nested_name(const char* first, const char* last, Db& db,
4695 bool* ends_with_template_args)
4696 {
4697 if (first != last && *first == 'N')
4698 {
4699 Qualifiers cv;
4700 const char* t0 = parse_cv_qualifiers(first+1, last, cv);
4701 if (t0 == last)
4702 return first;
4703 db.RefQuals = FrefQualNone;
4704 if (*t0 == 'R')
4705 {
4706 db.RefQuals = FrefQualLValue;
4707 ++t0;
4708 }
4709 else if (*t0 == 'O')
4710 {
4711 db.RefQuals = FrefQualRValue;
4712 ++t0;
4713 }
4714 db.Names.push_back(db.make<EmptyName>());
4715 if (last - t0 >= 2 && t0[0] == 'S' && t0[1] == 't')
4716 {
4717 t0 += 2;
4718 db.Names.back() = db.make<NameType>("std");
4719 }
4720 if (t0 == last)
4721 return first;
4722 bool pop_subs = false;
4723 bool component_ends_with_template_args = false;
4724 while (*t0 != 'E')
4725 {
4726 component_ends_with_template_args = false;
4727 const char* t1;
4728 switch (*t0)
4729 {
4730 case 'S':
4731 if (t0 + 1 != last && t0[1] == 't')
4732 goto do_parse_unqualified_name;
4733 t1 = parse_substitution(t0, last, db);
4734 if (t1 != t0 && t1 != last)
4735 {
4736 if (db.Names.size() < 2)
4737 return first;
4738 auto name = db.Names.back();
4739 db.Names.pop_back();
4740 if (db.Names.back()->K != Node::KEmptyName)
4741 {
4742 db.Names.back() = db.make<QualifiedName>(
4743 db.Names.back(), name);
4744 db.Subs.push_back(db.Names.back());
4745 }
4746 else
4747 db.Names.back() = name;
4748 pop_subs = true;
4749 t0 = t1;
4750 }
4751 else
4752 return first;
4753 break;
4754 case 'T':
4755 t1 = parse_template_param(t0, last, db);
4756 if (t1 != t0 && t1 != last)
4757 {
4758 if (db.Names.size() < 2)
4759 return first;
4760 auto name = db.Names.back();
4761 db.Names.pop_back();
4762 if (db.Names.back()->K != Node::KEmptyName)
4763 db.Names.back() =
4764 db.make<QualifiedName>(db.Names.back(), name);
4765 else
4766 db.Names.back() = name;
4767 db.Subs.push_back(db.Names.back());
4768 pop_subs = true;
4769 t0 = t1;
4770 }
4771 else
4772 return first;
4773 break;
4774 case 'D':
4775 if (t0 + 1 != last && t0[1] != 't' && t0[1] != 'T')
4776 goto do_parse_unqualified_name;
4777 t1 = parse_decltype(t0, last, db);
4778 if (t1 != t0 && t1 != last)
4779 {
4780 if (db.Names.size() < 2)
4781 return first;
4782 auto name = db.Names.back();
4783 db.Names.pop_back();
4784 if (db.Names.back()->K != Node::KEmptyName)
4785 db.Names.back() =
4786 db.make<QualifiedName>(db.Names.back(), name);
4787 else
4788 db.Names.back() = name;
4789 db.Subs.push_back(db.Names.back());
4790 pop_subs = true;
4791 t0 = t1;
4792 }
4793 else
4794 return first;
4795 break;
4796 case 'I':
4797 t1 = parse_template_args(t0, last, db);
4798 if (t1 != t0 && t1 != last)
4799 {
4800 if (db.Names.size() < 2)
4801 return first;
4802 auto name = db.Names.back();
4803 db.Names.pop_back();
4804 db.Names.back() = db.make<NameWithTemplateArgs>(
4805 db.Names.back(), name);
4806 db.Subs.push_back(db.Names.back());
4807 t0 = t1;
4808 component_ends_with_template_args = true;
4809 }
4810 else
4811 return first;
4812 break;
4813 case 'L':
4814 if (++t0 == last)
4815 return first;
4816 break;
4817 default:
4818 do_parse_unqualified_name:
4819 t1 = parse_unqualified_name(t0, last, db);
4820 if (t1 != t0 && t1 != last)
4821 {
4822 if (db.Names.size() < 2)
4823 return first;
4824 auto name = db.Names.back();
4825 db.Names.pop_back();
4826 if (db.Names.back()->K != Node::KEmptyName)
4827 db.Names.back() =
4828 db.make<QualifiedName>(db.Names.back(), name);
4829 else
4830 db.Names.back() = name;
4831 db.Subs.push_back(db.Names.back());
4832 pop_subs = true;
4833 t0 = t1;
4834 }
4835 else
4836 return first;
4837 }
4838 }
4839 first = t0 + 1;
4840 db.CV = cv;
4841 if (pop_subs && !db.Subs.empty())
4842 db.Subs.pop_back();
4843 if (ends_with_template_args)
4844 *ends_with_template_args = component_ends_with_template_args;
4845 }
4846 return first;
4847 }
4848
4849 // <discriminator> := _ <non-negative number> # when number < 10
4850 // := __ <non-negative number> _ # when number >= 10
4851 // extension := decimal-digit+ # at the end of string
4852
4853 const char*
parse_discriminator(const char * first,const char * last)4854 parse_discriminator(const char* first, const char* last)
4855 {
4856 // parse but ignore discriminator
4857 if (first != last)
4858 {
4859 if (*first == '_')
4860 {
4861 const char* t1 = first+1;
4862 if (t1 != last)
4863 {
4864 if (std::isdigit(*t1))
4865 first = t1+1;
4866 else if (*t1 == '_')
4867 {
4868 for (++t1; t1 != last && std::isdigit(*t1); ++t1)
4869 ;
4870 if (t1 != last && *t1 == '_')
4871 first = t1 + 1;
4872 }
4873 }
4874 }
4875 else if (std::isdigit(*first))
4876 {
4877 const char* t1 = first+1;
4878 for (; t1 != last && std::isdigit(*t1); ++t1)
4879 ;
4880 if (t1 == last)
4881 first = last;
4882 }
4883 }
4884 return first;
4885 }
4886
4887 // <local-name> := Z <function encoding> E <entity name> [<discriminator>]
4888 // := Z <function encoding> E s [<discriminator>]
4889 // := Z <function encoding> Ed [ <parameter number> ] _ <entity name>
4890
4891 const char*
parse_local_name(const char * first,const char * last,Db & db,bool * ends_with_template_args)4892 parse_local_name(const char* first, const char* last, Db& db,
4893 bool* ends_with_template_args)
4894 {
4895 if (first != last && *first == 'Z')
4896 {
4897 const char* t = parse_encoding(first+1, last, db);
4898 if (t != first+1 && t != last && *t == 'E' && ++t != last)
4899 {
4900 switch (*t)
4901 {
4902 case 's':
4903 first = parse_discriminator(t+1, last);
4904 if (db.Names.empty())
4905 return first;
4906 db.Names.back() = db.make<QualifiedName>(
4907 db.Names.back(), db.make<NameType>("string literal"));
4908 break;
4909 case 'd':
4910 if (++t != last)
4911 {
4912 const char* t1 = parse_number(t, last);
4913 if (t1 != last && *t1 == '_')
4914 {
4915 t = t1 + 1;
4916 t1 = parse_name(t, last, db,
4917 ends_with_template_args);
4918 if (t1 != t)
4919 {
4920 if (db.Names.size() < 2)
4921 return first;
4922 auto name = db.Names.back();
4923 db.Names.pop_back();
4924 if (db.Names.empty())
4925 return first;
4926 db.Names.back() =
4927 db.make<QualifiedName>(db.Names.back(), name);
4928 first = t1;
4929 }
4930 else if (!db.Names.empty())
4931 db.Names.pop_back();
4932 }
4933 }
4934 break;
4935 default:
4936 {
4937 const char* t1 = parse_name(t, last, db,
4938 ends_with_template_args);
4939 if (t1 != t)
4940 {
4941 // parse but ignore discriminator
4942 first = parse_discriminator(t1, last);
4943 if (db.Names.size() < 2)
4944 return first;
4945 auto name = db.Names.back();
4946 db.Names.pop_back();
4947 if (db.Names.empty())
4948 return first;
4949 db.Names.back() =
4950 db.make<QualifiedName>(db.Names.back(), name);
4951 }
4952 else if (!db.Names.empty())
4953 db.Names.pop_back();
4954 }
4955 break;
4956 }
4957 }
4958 }
4959 return first;
4960 }
4961
4962 // <name> ::= <nested-name> // N
4963 // ::= <local-name> # See Scope Encoding below // Z
4964 // ::= <unscoped-template-name> <template-args>
4965 // ::= <unscoped-name>
4966
4967 // <unscoped-template-name> ::= <unscoped-name>
4968 // ::= <substitution>
4969
4970 const char*
parse_name(const char * first,const char * last,Db & db,bool * ends_with_template_args)4971 parse_name(const char* first, const char* last, Db& db,
4972 bool* ends_with_template_args)
4973 {
4974 if (last - first >= 2)
4975 {
4976 const char* t0 = first;
4977 // extension: ignore L here
4978 if (*t0 == 'L')
4979 ++t0;
4980 switch (*t0)
4981 {
4982 case 'N':
4983 {
4984 const char* t1 = parse_nested_name(t0, last, db,
4985 ends_with_template_args);
4986 if (t1 != t0)
4987 first = t1;
4988 break;
4989 }
4990 case 'Z':
4991 {
4992 const char* t1 = parse_local_name(t0, last, db,
4993 ends_with_template_args);
4994 if (t1 != t0)
4995 first = t1;
4996 break;
4997 }
4998 default:
4999 {
5000 const char* t1 = parse_unscoped_name(t0, last, db);
5001 if (t1 != t0)
5002 {
5003 if (t1 != last && *t1 == 'I') // <unscoped-template-name> <template-args>
5004 {
5005 if (db.Names.empty())
5006 return first;
5007 db.Subs.push_back(db.Names.back());
5008 t0 = t1;
5009 t1 = parse_template_args(t0, last, db);
5010 if (t1 != t0)
5011 {
5012 if (db.Names.size() < 2)
5013 return first;
5014 auto tmp = db.Names.back();
5015 db.Names.pop_back();
5016 if (db.Names.empty())
5017 return first;
5018 db.Names.back() =
5019 db.make<NameWithTemplateArgs>(
5020 db.Names.back(), tmp);
5021 first = t1;
5022 if (ends_with_template_args)
5023 *ends_with_template_args = true;
5024 }
5025 }
5026 else // <unscoped-name>
5027 first = t1;
5028 }
5029 else
5030 { // try <substitution> <template-args>
5031 t1 = parse_substitution(t0, last, db);
5032 if (t1 != t0 && t1 != last && *t1 == 'I')
5033 {
5034 t0 = t1;
5035 t1 = parse_template_args(t0, last, db);
5036 if (t1 != t0)
5037 {
5038 if (db.Names.size() < 2)
5039 return first;
5040 auto tmp = db.Names.back();
5041 db.Names.pop_back();
5042 if (db.Names.empty())
5043 return first;
5044 db.Names.back() =
5045 db.make<NameWithTemplateArgs>(
5046 db.Names.back(), tmp);
5047 first = t1;
5048 if (ends_with_template_args)
5049 *ends_with_template_args = true;
5050 }
5051 }
5052 }
5053 break;
5054 }
5055 }
5056 }
5057 return first;
5058 }
5059
5060 // <call-offset> ::= h <nv-offset> _
5061 // ::= v <v-offset> _
5062 //
5063 // <nv-offset> ::= <offset number>
5064 // # non-virtual base override
5065 //
5066 // <v-offset> ::= <offset number> _ <virtual offset number>
5067 // # virtual base override, with vcall offset
5068
5069 const char*
parse_call_offset(const char * first,const char * last)5070 parse_call_offset(const char* first, const char* last)
5071 {
5072 if (first != last)
5073 {
5074 switch (*first)
5075 {
5076 case 'h':
5077 {
5078 const char* t = parse_number(first + 1, last);
5079 if (t != first + 1 && t != last && *t == '_')
5080 first = t + 1;
5081 }
5082 break;
5083 case 'v':
5084 {
5085 const char* t = parse_number(first + 1, last);
5086 if (t != first + 1 && t != last && *t == '_')
5087 {
5088 const char* t2 = parse_number(++t, last);
5089 if (t2 != t && t2 != last && *t2 == '_')
5090 first = t2 + 1;
5091 }
5092 }
5093 break;
5094 }
5095 }
5096 return first;
5097 }
5098
5099 // <special-name> ::= TV <type> # virtual table
5100 // ::= TT <type> # VTT structure (construction vtable index)
5101 // ::= TI <type> # typeinfo structure
5102 // ::= TS <type> # typeinfo name (null-terminated byte string)
5103 // ::= Tc <call-offset> <call-offset> <base encoding>
5104 // # base is the nominal target function of thunk
5105 // # first call-offset is 'this' adjustment
5106 // # second call-offset is result adjustment
5107 // ::= T <call-offset> <base encoding>
5108 // # base is the nominal target function of thunk
5109 // ::= GV <object name> # Guard variable for one-time initialization
5110 // # No <type>
5111 // ::= TW <object name> # Thread-local wrapper
5112 // ::= TH <object name> # Thread-local initialization
5113 // extension ::= TC <first type> <number> _ <second type> # construction vtable for second-in-first
5114 // extension ::= GR <object name> # reference temporary for object
5115
5116 const char*
parse_special_name(const char * first,const char * last,Db & db)5117 parse_special_name(const char* first, const char* last, Db& db)
5118 {
5119 if (last - first > 2)
5120 {
5121 const char* t;
5122 switch (*first)
5123 {
5124 case 'T':
5125 switch (first[1])
5126 {
5127 case 'V':
5128 // TV <type> # virtual table
5129 t = parse_type(first+2, last, db);
5130 if (t != first+2)
5131 {
5132 if (db.Names.empty())
5133 return first;
5134 db.Names.back() =
5135 db.make<SpecialName>("vtable for ", db.Names.back());
5136 first = t;
5137 }
5138 break;
5139 case 'T':
5140 // TT <type> # VTT structure (construction vtable index)
5141 t = parse_type(first+2, last, db);
5142 if (t != first+2)
5143 {
5144 if (db.Names.empty())
5145 return first;
5146 db.Names.back() =
5147 db.make<SpecialName>("VTT for ", db.Names.back());
5148 first = t;
5149 }
5150 break;
5151 case 'I':
5152 // TI <type> # typeinfo structure
5153 t = parse_type(first+2, last, db);
5154 if (t != first+2)
5155 {
5156 if (db.Names.empty())
5157 return first;
5158 db.Names.back() =
5159 db.make<SpecialName>("typeinfo for ", db.Names.back());
5160 first = t;
5161 }
5162 break;
5163 case 'S':
5164 // TS <type> # typeinfo name (null-terminated byte string)
5165 t = parse_type(first+2, last, db);
5166 if (t != first+2)
5167 {
5168 if (db.Names.empty())
5169 return first;
5170 db.Names.back() =
5171 db.make<SpecialName>("typeinfo name for ", db.Names.back());
5172 first = t;
5173 }
5174 break;
5175 case 'c':
5176 // Tc <call-offset> <call-offset> <base encoding>
5177 {
5178 const char* t0 = parse_call_offset(first+2, last);
5179 if (t0 == first+2)
5180 break;
5181 const char* t1 = parse_call_offset(t0, last);
5182 if (t1 == t0)
5183 break;
5184 t = parse_encoding(t1, last, db);
5185 if (t != t1)
5186 {
5187 if (db.Names.empty())
5188 return first;
5189 db.Names.back() =
5190 db.make<SpecialName>("covariant return thunk to ",
5191 db.Names.back());
5192 first = t;
5193 }
5194 }
5195 break;
5196 case 'C':
5197 // extension ::= TC <first type> <number> _ <second type> # construction vtable for second-in-first
5198 t = parse_type(first+2, last, db);
5199 if (t != first+2)
5200 {
5201 const char* t0 = parse_number(t, last);
5202 if (t0 != t && t0 != last && *t0 == '_')
5203 {
5204 const char* t1 = parse_type(++t0, last, db);
5205 if (t1 != t0)
5206 {
5207 if (db.Names.size() < 2)
5208 return first;
5209 auto left = db.Names.back();
5210 db.Names.pop_back();
5211 if (db.Names.empty())
5212 return first;
5213 db.Names.back() = db.make<CtorVtableSpecialName>(
5214 left, db.Names.back());
5215 first = t1;
5216 }
5217 }
5218 }
5219 break;
5220 case 'W':
5221 // TW <object name> # Thread-local wrapper
5222 t = parse_name(first + 2, last, db);
5223 if (t != first + 2)
5224 {
5225 if (db.Names.empty())
5226 return first;
5227 db.Names.back() =
5228 db.make<SpecialName>("thread-local wrapper routine for ",
5229 db.Names.back());
5230 first = t;
5231 }
5232 break;
5233 case 'H':
5234 //TH <object name> # Thread-local initialization
5235 t = parse_name(first + 2, last, db);
5236 if (t != first + 2)
5237 {
5238 if (db.Names.empty())
5239 return first;
5240 db.Names.back() = db.make<SpecialName>(
5241 "thread-local initialization routine for ", db.Names.back());
5242 first = t;
5243 }
5244 break;
5245 default:
5246 // T <call-offset> <base encoding>
5247 {
5248 const char* t0 = parse_call_offset(first+1, last);
5249 if (t0 == first+1)
5250 break;
5251 t = parse_encoding(t0, last, db);
5252 if (t != t0)
5253 {
5254 if (db.Names.empty())
5255 return first;
5256 if (first[1] == 'v')
5257 {
5258 db.Names.back() =
5259 db.make<SpecialName>("virtual thunk to ",
5260 db.Names.back());
5261 first = t;
5262 }
5263 else
5264 {
5265 db.Names.back() =
5266 db.make<SpecialName>("non-virtual thunk to ",
5267 db.Names.back());
5268 first = t;
5269 }
5270 }
5271 }
5272 break;
5273 }
5274 break;
5275 case 'G':
5276 switch (first[1])
5277 {
5278 case 'V':
5279 // GV <object name> # Guard variable for one-time initialization
5280 t = parse_name(first+2, last, db);
5281 if (t != first+2)
5282 {
5283 if (db.Names.empty())
5284 return first;
5285 db.Names.back() =
5286 db.make<SpecialName>("guard variable for ", db.Names.back());
5287 first = t;
5288 }
5289 break;
5290 case 'R':
5291 // extension ::= GR <object name> # reference temporary for object
5292 t = parse_name(first+2, last, db);
5293 if (t != first+2)
5294 {
5295 if (db.Names.empty())
5296 return first;
5297 db.Names.back() =
5298 db.make<SpecialName>("reference temporary for ",
5299 db.Names.back());
5300 first = t;
5301 }
5302 break;
5303 }
5304 break;
5305 }
5306 }
5307 return first;
5308 }
5309
5310 template <class T>
5311 class save_value
5312 {
5313 T& restore_;
5314 T original_value_;
5315 public:
save_value(T & restore)5316 save_value(T& restore)
5317 : restore_(restore),
5318 original_value_(restore)
5319 {}
5320
~save_value()5321 ~save_value()
5322 {
5323 restore_ = std::move(original_value_);
5324 }
5325
5326 save_value(const save_value&) = delete;
5327 save_value& operator=(const save_value&) = delete;
5328 };
5329
5330 // <encoding> ::= <function name> <bare-function-type>
5331 // ::= <data name>
5332 // ::= <special-name>
5333
5334 const char*
parse_encoding(const char * first,const char * last,Db & db)5335 parse_encoding(const char* first, const char* last, Db& db)
5336 {
5337 if (first != last)
5338 {
5339 save_value<decltype(db.EncodingDepth)> su(db.EncodingDepth);
5340 ++db.EncodingDepth;
5341 save_value<decltype(db.TagTemplates)> sb(db.TagTemplates);
5342 if (db.EncodingDepth > 1)
5343 db.TagTemplates = true;
5344 save_value<decltype(db.ParsedCtorDtorCV)> sp(db.ParsedCtorDtorCV);
5345 db.ParsedCtorDtorCV = false;
5346 switch (*first)
5347 {
5348 case 'G':
5349 case 'T':
5350 first = parse_special_name(first, last, db);
5351 break;
5352 default:
5353 {
5354 bool ends_with_template_args = false;
5355 const char* t = parse_name(first, last, db,
5356 &ends_with_template_args);
5357 if (db.Names.empty())
5358 return first;
5359 Qualifiers cv = db.CV;
5360 FunctionRefQual ref = db.RefQuals;
5361 if (t != first)
5362 {
5363 if (t != last && *t != 'E' && *t != '.')
5364 {
5365 save_value<bool> sb2(db.TagTemplates);
5366 db.TagTemplates = false;
5367 const char* t2;
5368 if (db.Names.empty())
5369 return first;
5370 if (!db.Names.back())
5371 return first;
5372 Node* return_type = nullptr;
5373 if (!db.ParsedCtorDtorCV && ends_with_template_args)
5374 {
5375 t2 = parse_type(t, last, db);
5376 if (t2 == t)
5377 return first;
5378 if (db.Names.size() < 1)
5379 return first;
5380 return_type = db.Names.back();
5381 db.Names.pop_back();
5382 t = t2;
5383 }
5384
5385 Node* result = nullptr;
5386
5387 if (t != last && *t == 'v')
5388 {
5389 ++t;
5390 if (db.Names.empty())
5391 return first;
5392 Node* name = db.Names.back();
5393 db.Names.pop_back();
5394 result = db.make<FunctionEncoding>(
5395 return_type, name, NodeArray());
5396 }
5397 else
5398 {
5399 size_t params_begin = db.Names.size();
5400 while (true)
5401 {
5402 t2 = parse_type(t, last, db);
5403 if (t2 == t)
5404 break;
5405 t = t2;
5406 }
5407 if (db.Names.size() < params_begin)
5408 return first;
5409 NodeArray params =
5410 db.popTrailingNodeArray(params_begin);
5411 if (db.Names.empty())
5412 return first;
5413 Node* name = db.Names.back();
5414 db.Names.pop_back();
5415 result = db.make<FunctionEncoding>(
5416 return_type, name, params);
5417 }
5418 if (ref != FrefQualNone)
5419 result = db.make<FunctionRefQualType>(result, ref);
5420 if (cv != QualNone)
5421 result = db.make<FunctionQualType>(result, cv);
5422 db.Names.push_back(result);
5423 first = t;
5424 }
5425 else
5426 first = t;
5427 }
5428 break;
5429 }
5430 }
5431 }
5432 return first;
5433 }
5434
5435 // _block_invoke
5436 // _block_invoke<decimal-digit>+
5437 // _block_invoke_<decimal-digit>+
5438
5439 const char*
parse_block_invoke(const char * first,const char * last,Db & db)5440 parse_block_invoke(const char* first, const char* last, Db& db)
5441 {
5442 if (last - first >= 13)
5443 {
5444 // FIXME: strcmp?
5445 const char test[] = "_block_invoke";
5446 const char* t = first;
5447 for (int i = 0; i < 13; ++i, ++t)
5448 {
5449 if (*t != test[i])
5450 return first;
5451 }
5452 if (t != last)
5453 {
5454 if (*t == '_')
5455 {
5456 // must have at least 1 decimal digit
5457 if (++t == last || !std::isdigit(*t))
5458 return first;
5459 ++t;
5460 }
5461 // parse zero or more digits
5462 while (t != last && isdigit(*t))
5463 ++t;
5464 }
5465 if (db.Names.empty())
5466 return first;
5467 db.Names.back() =
5468 db.make<SpecialName>("invocation function for block in ",
5469 db.Names.back());
5470 first = t;
5471 }
5472 return first;
5473 }
5474
5475 // extension
5476 // <dot-suffix> := .<anything and everything>
5477
5478 const char*
parse_dot_suffix(const char * first,const char * last,Db & db)5479 parse_dot_suffix(const char* first, const char* last, Db& db)
5480 {
5481 if (first != last && *first == '.')
5482 {
5483 if (db.Names.empty())
5484 return first;
5485 db.Names.back() =
5486 db.make<DotSuffix>(db.Names.back(), StringView(first, last));
5487 first = last;
5488 }
5489 return first;
5490 }
5491
5492 enum {
5493 unknown_error = -4,
5494 invalid_args = -3,
5495 invalid_mangled_name,
5496 memory_alloc_failure,
5497 success
5498 };
5499
5500 // <block-involcaton-function> ___Z<encoding>_block_invoke
5501 // <block-involcaton-function> ___Z<encoding>_block_invoke<decimal-digit>+
5502 // <block-involcaton-function> ___Z<encoding>_block_invoke_<decimal-digit>+
5503 // <mangled-name> ::= _Z<encoding>
5504 // ::= <type>
5505 void
demangle(const char * first,const char * last,Db & db,int & status)5506 demangle(const char* first, const char* last, Db& db, int& status)
5507 {
5508 if (first >= last)
5509 {
5510 status = invalid_mangled_name;
5511 return;
5512 }
5513 if (*first == '_')
5514 {
5515 if (last - first >= 4)
5516 {
5517 if (first[1] == 'Z')
5518 {
5519 const char* t = parse_encoding(first+2, last, db);
5520 if (t != first+2 && t != last && *t == '.')
5521 t = parse_dot_suffix(t, last, db);
5522 if (t != last)
5523 status = invalid_mangled_name;
5524 }
5525 else if (first[1] == '_' && first[2] == '_' && first[3] == 'Z')
5526 {
5527 const char* t = parse_encoding(first+4, last, db);
5528 if (t != first+4 && t != last)
5529 {
5530 const char* t1 = parse_block_invoke(t, last, db);
5531 if (t1 != last)
5532 status = invalid_mangled_name;
5533 }
5534 else
5535 status = invalid_mangled_name;
5536 }
5537 else
5538 status = invalid_mangled_name;
5539 }
5540 else
5541 status = invalid_mangled_name;
5542 }
5543 else
5544 {
5545 const char* t = parse_type(first, last, db);
5546 if (t != last)
5547 status = invalid_mangled_name;
5548 }
5549 if (status == success && db.Names.empty())
5550 status = invalid_mangled_name;
5551 }
5552
5553 } // unnamed namespace
5554
5555
5556 namespace __cxxabiv1 {
5557 extern "C" _LIBCXXABI_FUNC_VIS char *
__cxa_demangle(const char * mangled_name,char * buf,size_t * n,int * status)5558 __cxa_demangle(const char *mangled_name, char *buf, size_t *n, int *status) {
5559 if (mangled_name == nullptr || (buf != nullptr && n == nullptr))
5560 {
5561 if (status)
5562 *status = invalid_args;
5563 return nullptr;
5564 }
5565
5566 size_t internal_size = buf != nullptr ? *n : 0;
5567 Db db;
5568 int internal_status = success;
5569 size_t len = std::strlen(mangled_name);
5570 demangle(mangled_name, mangled_name + len, db,
5571 internal_status);
5572
5573 if (internal_status == success && db.FixForwardReferences &&
5574 !db.TemplateParams.empty())
5575 {
5576 db.FixForwardReferences = false;
5577 db.TagTemplates = false;
5578 db.Names.clear();
5579 db.Subs.clear();
5580 demangle(mangled_name, mangled_name + len, db, internal_status);
5581 if (db.FixForwardReferences)
5582 internal_status = invalid_mangled_name;
5583 }
5584
5585 if (internal_status == success &&
5586 db.Names.back()->containsUnexpandedParameterPack())
5587 internal_status = invalid_mangled_name;
5588
5589 if (internal_status == success)
5590 {
5591 if (!buf)
5592 {
5593 internal_size = 1024;
5594 buf = static_cast<char*>(std::malloc(internal_size));
5595 }
5596
5597 if (buf)
5598 {
5599 OutputStream s(buf, internal_size);
5600 db.Names.back()->print(s);
5601 s += '\0';
5602 if (n) *n = s.getCurrentPosition();
5603 buf = s.getBuffer();
5604 }
5605 else
5606 internal_status = memory_alloc_failure;
5607 }
5608 else
5609 buf = nullptr;
5610 if (status)
5611 *status = internal_status;
5612 return buf;
5613 }
5614 } // __cxxabiv1
5615