summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--libcxxabi/src/cxa_demangle.cpp26
-rw-r--r--libcxxabi/test/test_demangle.pass.cpp4
2 files changed, 17 insertions, 13 deletions
diff --git a/libcxxabi/src/cxa_demangle.cpp b/libcxxabi/src/cxa_demangle.cpp
index cbf04987afb..d642e67ffa8 100644
--- a/libcxxabi/src/cxa_demangle.cpp
+++ b/libcxxabi/src/cxa_demangle.cpp
@@ -2013,6 +2013,7 @@ struct Db {
bool TagTemplates = true;
bool FixForwardReferences = false;
bool TryToParseTemplateArgs = true;
+ bool ParsingLambdaParams = false;
BumpPointerAllocator ASTAllocator;
@@ -2270,6 +2271,7 @@ Node *Db::parseUnnamedTypeName(NameState *) {
}
if (consumeIf("Ul")) {
NodeArray Params;
+ SwapAndRestore<bool> SwapParams(ParsingLambdaParams, true);
if (!consumeIf("vE")) {
size_t ParamsBegin = Names.size();
do {
@@ -4658,20 +4660,20 @@ Node *Db::parseTemplateParam() {
if (!consumeIf('T'))
return nullptr;
- if (consumeIf('_')) {
- if (TemplateParams.empty()) {
- FixForwardReferences = true;
- return make<NameType>("FORWARD_REFERENCE");
- }
- return TemplateParams[0];
+ size_t Index = 0;
+ if (!consumeIf('_')) {
+ if (parsePositiveInteger(&Index))
+ return nullptr;
+ ++Index;
+ if (!consumeIf('_'))
+ return nullptr;
}
- size_t Index;
- if (parsePositiveInteger(&Index))
- return nullptr;
- ++Index;
- if (!consumeIf('_'))
- return nullptr;
+ // Itanium ABI 5.1.8: In a generic lambda, uses of auto in the parameter list
+ // are mangled as the corresponding artificial template type parameter.
+ if (ParsingLambdaParams)
+ return make<NameType>("auto");
+
if (Index >= TemplateParams.size()) {
FixForwardReferences = true;
return make<NameType>("FORWARD_REFERENCE");
diff --git a/libcxxabi/test/test_demangle.pass.cpp b/libcxxabi/test/test_demangle.pass.cpp
index b15555965d8..e7fb0cf9990 100644
--- a/libcxxabi/test/test_demangle.pass.cpp
+++ b/libcxxabi/test/test_demangle.pass.cpp
@@ -29604,7 +29604,7 @@ const char* cases[][2] =
{"PFvRmOE", "void (*)(unsigned long&) &&"},
{"_ZTW1x", "thread-local wrapper routine for x"},
{"_ZTHN3fooE", "thread-local initialization routine for foo"},
- {"_Z4algoIJiiiEEvZ1gEUlDpT_E_", "void algo<int, int, int>(g::'lambda'(int, int, int))"},
+
// attribute abi_tag
{"_Z1fB3foov", "f[abi:foo]()"},
{"_Z1fB3fooB3barv", "f[abi:foo][abi:bar]()"},
@@ -29725,6 +29725,8 @@ const char* cases[][2] =
{"_ZGRDC1x1yE_", "reference temporary for [x, y]"},
{"_ZGR1bIvE2_", "reference temporary for b<void>"},
+
+ {"_ZZ18test_assign_throwsI20small_throws_on_copyLb0EEvvENKUlRNSt3__13anyEOT_E_clIRS0_EEDaS3_S5_", "auto void test_assign_throws<small_throws_on_copy, false>()::'lambda'(std::__1::any&, auto&&)::operator()<small_throws_on_copy&>(std::__1::any&, auto&&) const"},
};
const unsigned N = sizeof(cases) / sizeof(cases[0]);
OpenPOWER on IntegriCloud