[libcxx-commits] [libcxxabi] [libcxxabi][ItaniumDemangle] Demangle explicitly named object parameters (PR #72881)
Michael Buch via libcxx-commits
libcxx-commits at lists.llvm.org
Fri Nov 24 05:07:48 PST 2023
https://github.com/Michael137 updated https://github.com/llvm/llvm-project/pull/72881
>From d9243de8658011c20db84dd091d7d76a8751ad06 Mon Sep 17 00:00:00 2001
From: Michael Buch <michaelbuch12 at gmail.com>
Date: Sat, 18 Nov 2023 12:54:38 +0000
Subject: [PATCH 1/3] [libcxxabi][ItaniumDemangle] Demangle explicitly named
object parameters
---
libcxxabi/src/demangle/ItaniumDemangle.h | 30 +++++++++++++++++-------
libcxxabi/test/test_demangle.pass.cpp | 10 ++++++++
2 files changed, 32 insertions(+), 8 deletions(-)
diff --git a/libcxxabi/src/demangle/ItaniumDemangle.h b/libcxxabi/src/demangle/ItaniumDemangle.h
index 2336b84da293bcc..f9a0c059e86e8bd 100644
--- a/libcxxabi/src/demangle/ItaniumDemangle.h
+++ b/libcxxabi/src/demangle/ItaniumDemangle.h
@@ -2780,6 +2780,7 @@ template <typename Derived, typename Alloc> struct AbstractManglingParser {
Qualifiers CVQualifiers = QualNone;
FunctionRefQual ReferenceQualifier = FrefQualNone;
size_t ForwardTemplateRefsBegin;
+ bool HasExplicitObjectParameter = false;
NameState(AbstractManglingParser *Enclosing)
: ForwardTemplateRefsBegin(Enclosing->ForwardTemplateRefs.size()) {}
@@ -3438,15 +3439,25 @@ AbstractManglingParser<Derived, Alloc>::parseNestedName(NameState *State) {
if (!consumeIf('N'))
return nullptr;
- Qualifiers CVTmp = parseCVQualifiers();
- if (State) State->CVQualifiers = CVTmp;
+ // 'H' specifies that the encoding that follows
+ // has an explicit object parameter.
+ if (!consumeIf('H')) {
+ Qualifiers CVTmp = parseCVQualifiers();
+ if (State)
+ State->CVQualifiers = CVTmp;
- if (consumeIf('O')) {
- if (State) State->ReferenceQualifier = FrefQualRValue;
- } else if (consumeIf('R')) {
- if (State) State->ReferenceQualifier = FrefQualLValue;
- } else {
- if (State) State->ReferenceQualifier = FrefQualNone;
+ if (consumeIf('O')) {
+ if (State)
+ State->ReferenceQualifier = FrefQualRValue;
+ } else if (consumeIf('R')) {
+ if (State)
+ State->ReferenceQualifier = FrefQualLValue;
+ } else {
+ if (State)
+ State->ReferenceQualifier = FrefQualNone;
+ }
+ } else if (State) {
+ State->HasExplicitObjectParameter = true;
}
Node *SoFar = nullptr;
@@ -5424,6 +5435,9 @@ Node *AbstractManglingParser<Derived, Alloc>::parseEncoding() {
return nullptr;
Names.push_back(Ty);
} while (!IsEndOfEncoding() && look() != 'Q');
+ // Ignore the explicit 'this' parameter.
+ if (NameInfo.HasExplicitObjectParameter)
+ ++ParamsBegin;
Params = popTrailingNodeArray(ParamsBegin);
}
diff --git a/libcxxabi/test/test_demangle.pass.cpp b/libcxxabi/test/test_demangle.pass.cpp
index 77741a952850ab9..a6b6d45a3783bb1 100644
--- a/libcxxabi/test/test_demangle.pass.cpp
+++ b/libcxxabi/test/test_demangle.pass.cpp
@@ -30174,6 +30174,16 @@ const char* cases[][2] =
{"_Z2f5IKiEvu14__remove_constIT_E", "void f5<int const>(__remove_const(int const))"},
{"_Z2f5IPiEvu16__remove_pointerIT_E", "void f5<int*>(__remove_pointer(int*))"},
{"_Z2f5IiEvu14__remove_cvrefIT_E", "void f5<int>(__remove_cvref(int))"},
+
+ // C++23 explicit object parameter
+ {"_ZNH3Foo3fooES_i", "Foo::foo(int)"},
+ {"_ZNH3Foo3fooERKS_i", "Foo::foo(int)"},
+ {"_ZNH1X3fooIRS_EEvOT_i", "void X::foo<X&>(int)"},
+ {"_ZZNH2ns3Foo3fooES0_iENH4Foo24foo2EOKS1_", "ns::Foo::foo(int)::Foo2::foo2()" },
+ {"_ZNH2ns3FooB7Foo_tag3fooB7foo_tagERKS0_i", "ns::Foo[abi:Foo_tag]::foo[abi:foo_tag](int)" },
+ {"_ZZN3Foo3fooEiENH4Foo24foo2EOKS0_", "Foo::foo(int)::Foo2::foo2()"},
+ {"_ZZNH3Foo3fooES_iENK4Foo24foo2Ev", "Foo::foo(int)::Foo2::foo2() const" },
+ {"_ZNH3FooclERKS_", "Foo::operator()()"},
};
const unsigned N = sizeof(cases) / sizeof(cases[0]);
>From b728f87399c15c08d1bd1e338a695a3ab3fe3344 Mon Sep 17 00:00:00 2001
From: Michael Buch <michaelbuch12 at gmail.com>
Date: Fri, 24 Nov 2023 12:47:01 +0000
Subject: [PATCH 2/3] fixup! print the explicit parameter
---
libcxxabi/src/demangle/ItaniumDemangle.h | 32 +++++++++++++++++++++---
libcxxabi/src/demangle/ItaniumNodes.def | 1 +
libcxxabi/test/test_demangle.pass.cpp | 16 ++++++------
3 files changed, 38 insertions(+), 11 deletions(-)
diff --git a/libcxxabi/src/demangle/ItaniumDemangle.h b/libcxxabi/src/demangle/ItaniumDemangle.h
index f9a0c059e86e8bd..57dda9b42106a56 100644
--- a/libcxxabi/src/demangle/ItaniumDemangle.h
+++ b/libcxxabi/src/demangle/ItaniumDemangle.h
@@ -890,6 +890,27 @@ class DynamicExceptionSpec : public Node {
}
};
+/// Represents the explicitly named object parameter.
+/// E.g.,
+/// \code{.cpp}
+/// struct Foo {
+/// void bar(this Foo && self);
+/// };
+/// \endcode
+class ExplicitObjectParameter final : public Node {
+ Node *Base;
+
+public:
+ ExplicitObjectParameter(Node *Base_)
+ : Node(KExplicitObjectParameter, Cache::Yes), Base(Base_) {}
+
+ template <typename Fn> void match(Fn F) const { F(Base); }
+
+ void printLeft(OutputBuffer &OB) const override { OB += "this "; }
+
+ void printRight(OutputBuffer &OB) const override { Base->print(OB); }
+};
+
class FunctionEncoding final : public Node {
const Node *Ret;
const Node *Name;
@@ -5433,11 +5454,16 @@ Node *AbstractManglingParser<Derived, Alloc>::parseEncoding() {
Node *Ty = getDerived().parseType();
if (Ty == nullptr)
return nullptr;
+
+ const bool IsFirstParam = (Names.size() - ParamsBegin) == 0;
+ if (NameInfo.HasExplicitObjectParameter && IsFirstParam)
+ Ty = make<ExplicitObjectParameter>(Ty);
+
+ if (Ty == nullptr)
+ return nullptr;
+
Names.push_back(Ty);
} while (!IsEndOfEncoding() && look() != 'Q');
- // Ignore the explicit 'this' parameter.
- if (NameInfo.HasExplicitObjectParameter)
- ++ParamsBegin;
Params = popTrailingNodeArray(ParamsBegin);
}
diff --git a/libcxxabi/src/demangle/ItaniumNodes.def b/libcxxabi/src/demangle/ItaniumNodes.def
index e27c111de3389c5..18f5d52b47e9113 100644
--- a/libcxxabi/src/demangle/ItaniumNodes.def
+++ b/libcxxabi/src/demangle/ItaniumNodes.def
@@ -99,5 +99,6 @@ NODE(RequiresExpr)
NODE(ExprRequirement)
NODE(TypeRequirement)
NODE(NestedRequirement)
+NODE(ExplicitObjectParameter)
#undef NODE
diff --git a/libcxxabi/test/test_demangle.pass.cpp b/libcxxabi/test/test_demangle.pass.cpp
index a6b6d45a3783bb1..bf5473ee7eb8a2f 100644
--- a/libcxxabi/test/test_demangle.pass.cpp
+++ b/libcxxabi/test/test_demangle.pass.cpp
@@ -30176,14 +30176,14 @@ const char* cases[][2] =
{"_Z2f5IiEvu14__remove_cvrefIT_E", "void f5<int>(__remove_cvref(int))"},
// C++23 explicit object parameter
- {"_ZNH3Foo3fooES_i", "Foo::foo(int)"},
- {"_ZNH3Foo3fooERKS_i", "Foo::foo(int)"},
- {"_ZNH1X3fooIRS_EEvOT_i", "void X::foo<X&>(int)"},
- {"_ZZNH2ns3Foo3fooES0_iENH4Foo24foo2EOKS1_", "ns::Foo::foo(int)::Foo2::foo2()" },
- {"_ZNH2ns3FooB7Foo_tag3fooB7foo_tagERKS0_i", "ns::Foo[abi:Foo_tag]::foo[abi:foo_tag](int)" },
- {"_ZZN3Foo3fooEiENH4Foo24foo2EOKS0_", "Foo::foo(int)::Foo2::foo2()"},
- {"_ZZNH3Foo3fooES_iENK4Foo24foo2Ev", "Foo::foo(int)::Foo2::foo2() const" },
- {"_ZNH3FooclERKS_", "Foo::operator()()"},
+ {"_ZNH3Foo3fooES_i", "Foo::foo(this Foo, int)"},
+ {"_ZNH3Foo3fooERKS_i", "Foo::foo(this Foo const&, int)"},
+ {"_ZNH1X3fooIRS_EEvOT_i", "void X::foo<X&>(this X&, int)"},
+ {"_ZZNH2ns3Foo3fooES0_iENH4Foo24foo2EOKS1_", "ns::Foo::foo(this ns::Foo, int)::Foo2::foo2(this Foo2 const&&)" },
+ {"_ZNH2ns3FooB7Foo_tag3fooB7foo_tagERKS0_i", "ns::Foo[abi:Foo_tag]::foo[abi:foo_tag](this ns::Foo[abi:Foo_tag] const&, int)" },
+ {"_ZZN3Foo3fooEiENH4Foo24foo2EOKS0_", "Foo::foo(int)::Foo2::foo2(this Foo2 const&&)"},
+ {"_ZZNH3Foo3fooES_iENK4Foo24foo2Ev", "Foo::foo(this Foo, int)::Foo2::foo2() const" },
+ {"_ZNH3FooclERKS_", "Foo::operator()(this Foo const&)"},
};
const unsigned N = sizeof(cases) / sizeof(cases[0]);
>From 9b1dde91ff6cbadc8f9645709f493f38ff5f6d1f Mon Sep 17 00:00:00 2001
From: Michael Buch <michaelbuch12 at gmail.com>
Date: Fri, 24 Nov 2023 13:03:59 +0000
Subject: [PATCH 3/3] fixup! assert nullness in ExplicitObjectParamter
constructor
---
libcxxabi/src/demangle/ItaniumDemangle.h | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/libcxxabi/src/demangle/ItaniumDemangle.h b/libcxxabi/src/demangle/ItaniumDemangle.h
index 57dda9b42106a56..4874fdfeb67398c 100644
--- a/libcxxabi/src/demangle/ItaniumDemangle.h
+++ b/libcxxabi/src/demangle/ItaniumDemangle.h
@@ -902,7 +902,9 @@ class ExplicitObjectParameter final : public Node {
public:
ExplicitObjectParameter(Node *Base_)
- : Node(KExplicitObjectParameter, Cache::Yes), Base(Base_) {}
+ : Node(KExplicitObjectParameter, Cache::Yes), Base(Base_) {
+ assert(Base != nullptr);
+ }
template <typename Fn> void match(Fn F) const { F(Base); }
More information about the libcxx-commits
mailing list