@@ -413,10 +413,11 @@ namespace detail {
413
413
| operator
414
414
| name
415
415
| lambda
416
+ | unnamed
416
417
417
418
function-pointer := "(" pointer-refs-junk symbol ")"
418
419
419
- pointer-refs-junk := { function-pointer-modifier } { pointer-refs }
420
+ pointer-refs-junk := { function-pointer-modifier } { pointer-refs } { ignored-identifier }
420
421
421
422
anonymous-namespace := "(anonymous namespace)" | "`anonymous namespace'"
422
423
@@ -445,6 +446,9 @@ namespace detail {
445
446
| LITERAL // 'lambda*' or `symbol'
446
447
| "<" IDENTIFIER ">" // lambda_*
447
448
449
+ unnamed := "{" "unnamed" "#" LITERAL "}"
450
+ | LITERAL // 'unnamed*'
451
+
448
452
balanced-punctuation := "(" balanced-punctuation-innards ")"
449
453
| "[" balanced-punctuation-innards "]"
450
454
| "<" balanced-punctuation-innards ">"
@@ -695,17 +699,30 @@ namespace detail {
695
699
return did_consume;
696
700
}
697
701
698
- NODISCARD Result<bool , parse_error> accept_lambda () {
702
+ NODISCARD Result<bool , parse_error> accept_lambda_or_unnamed () {
699
703
// LLVM does main::'lambda'<...>(...)::operator()<...>(...) -- apparently this can be 'lambda<count>'
700
704
// GCC does main::{lambda<...>(...)#1}::operator()<...>(...)
701
705
// MSVC does `int main(void)'::`2'::<lambda_1>::operator()<...>(...)
702
706
// https://github.com/llvm/llvm-project/blob/90beda2aba3cac34052827c560449fcb184c7313/libcxxabi/src/demangle/ItaniumDemangle.h#L1848-L1850 TODO: What about the count?
703
707
// https://github.com/gcc-mirror/gcc/blob/b76f1fb7bf8a7b66b8acd469309257f8b18c0c51/libiberty/cp-demangle.c#L6210-L6251 TODO: What special characters can appear?
704
708
TRY_TOK (opening_brace, tokenizer.accept ({token_type::punctuation, " {" }));
705
709
if (opening_brace) {
710
+ optional<token> token1;
711
+ optional<token> token2;
706
712
TRY_TOK (lambda_token, tokenizer.accept ({token_type::identifier, " lambda" }));
707
- if (!lambda_token) {
708
- return parse_error{};
713
+ if (lambda_token) {
714
+ token1 = lambda_token;
715
+ } else {
716
+ TRY_TOK (unnamed_token, tokenizer.accept ({token_type::identifier, " unnamed" }));
717
+ if (!unnamed_token) {
718
+ return parse_error{};
719
+ }
720
+ TRY_TOK (type_token, tokenizer.accept ({token_type::identifier, " type" }));
721
+ if (!type_token) {
722
+ return parse_error{};
723
+ }
724
+ token1 = unnamed_token;
725
+ token2 = type_token;
709
726
}
710
727
TRY_PARSE (consume_punctuation (), (void )0 );
711
728
TRY_TOK (hash_token, tokenizer.accept ({token_type::punctuation, " #" }));
@@ -721,7 +738,10 @@ namespace detail {
721
738
return parse_error{};
722
739
}
723
740
append_output ({token_type::punctuation, " <" });
724
- append_output (lambda_token.unwrap ());
741
+ append_output (token1.unwrap ());
742
+ if (token2) {
743
+ append_output (token2.unwrap ());
744
+ }
725
745
append_output (hash_token.unwrap ());
726
746
append_output (discriminator_token.unwrap ());
727
747
append_output ({token_type::punctuation, " >" });
@@ -731,7 +751,10 @@ namespace detail {
731
751
if (
732
752
maybe_literal_token
733
753
&& maybe_literal_token.unwrap ().type == token_type::literal
734
- && maybe_literal_token.unwrap ().str .starts_with (" 'lambda" )
754
+ && (
755
+ maybe_literal_token.unwrap ().str .starts_with (" 'lambda" )
756
+ || maybe_literal_token.unwrap ().str .starts_with (" 'unnamed" )
757
+ )
735
758
&& maybe_literal_token.unwrap ().str .ends_with (" '" )
736
759
) {
737
760
tokenizer.advance ();
@@ -822,7 +845,10 @@ namespace detail {
822
845
} else if (
823
846
next
824
847
&& next.unwrap ().type == token_type::identifier
825
- && is_microsoft_calling_convention (next.unwrap ().str )
848
+ && (
849
+ is_microsoft_calling_convention (next.unwrap ().str )
850
+ || is_ignored_identifier (next.unwrap ().str )
851
+ )
826
852
) {
827
853
tokenizer.advance ();
828
854
} else {
@@ -851,7 +877,7 @@ namespace detail {
851
877
TRY_PARSE (accept_anonymous_namespace (), return true );
852
878
TRY_PARSE (accept_operator (), return true );
853
879
TRY_PARSE (accept_identifier_token (), return true );
854
- TRY_PARSE (accept_lambda (), return true );
880
+ TRY_PARSE (accept_lambda_or_unnamed (), return true );
855
881
return false ;
856
882
}
857
883
0 commit comments