diff options
-rw-r--r-- | absl/debugging/internal/demangle.cc | 3 | ||||
-rw-r--r-- | absl/debugging/internal/demangle_test.cc | 16 |
2 files changed, 18 insertions, 1 deletions
diff --git a/absl/debugging/internal/demangle.cc b/absl/debugging/internal/demangle.cc index 6e6a1acc..40a55c7d 100644 --- a/absl/debugging/internal/demangle.cc +++ b/absl/debugging/internal/demangle.cc @@ -760,6 +760,7 @@ static bool ParseNestedName(State *state) { // <prefix> ::= <prefix> <unqualified-name> // ::= <template-prefix> <template-args> // ::= <template-param> +// ::= <decltype> // ::= <substitution> // ::= # empty // <template-prefix> ::= <prefix> <(template) unqualified-name> @@ -771,7 +772,7 @@ static bool ParsePrefix(State *state) { bool has_something = false; while (true) { MaybeAppendSeparator(state); - if (ParseTemplateParam(state) || + if (ParseTemplateParam(state) || ParseDecltype(state) || ParseSubstitution(state, /*accept_std=*/true) || ParseUnscopedName(state) || (ParseOneCharToken(state, 'M') && ParseUnnamedTypeName(state))) { diff --git a/absl/debugging/internal/demangle_test.cc b/absl/debugging/internal/demangle_test.cc index ff68f69a..96051d31 100644 --- a/absl/debugging/internal/demangle_test.cc +++ b/absl/debugging/internal/demangle_test.cc @@ -477,6 +477,22 @@ TEST(Demangle, DependentMemberOperatorCall) { EXPECT_STREQ("f<>()", tmp); } +TEST(Demangle, TypeNestedUnderDecltype) { + char tmp[80]; + + // Source: + // + // template <class T> struct S { using t = int; }; + // template <class T> decltype(S<T>{})::t f() { return {}; } + // void g() { f<int>(); } + // + // Full LLVM demangling of the instantiation of f: + // + // decltype(S<int>{})::t f<int>() + EXPECT_TRUE(Demangle("_Z1fIiENDTtl1SIT_EEE1tEv", tmp, sizeof(tmp))); + EXPECT_STREQ("f<>()", tmp); +} + // Test subobject-address template parameters. TEST(Demangle, SubobjectAddresses) { char tmp[80]; |