Skip to content

Commit 4bc4d51

Browse files
authored
[Demangle] demangle builtin type transformations (#65902)
Fixed: #62127 https://reviews.llvm.org/D116203 introduced several compiler builtin equivalents of the unary type traits. In some cases (e.g. template) those builtin will be dependent and need to be mangle. This patch add the check for `u{builtin}I{type}E` to demangle it. Reviewed By: rjmccall Differential Revision: https://reviews.llvm.org/D148465
1 parent 6d9b963 commit 4bc4d51

File tree

5 files changed

+63
-2
lines changed

5 files changed

+63
-2
lines changed

libcxxabi/src/demangle/ItaniumDemangle.h

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -534,6 +534,23 @@ class ElaboratedTypeSpefType : public Node {
534534
}
535535
};
536536

537+
class TransformedType : public Node {
538+
std::string_view Transform;
539+
Node *BaseType;
540+
public:
541+
TransformedType(std::string_view Transform_, Node *BaseType_)
542+
: Node(KTransformedType), Transform(Transform_), BaseType(BaseType_) {}
543+
544+
template<typename Fn> void match(Fn F) const { F(Transform, BaseType); }
545+
546+
void printLeft(OutputBuffer &OB) const override {
547+
OB += Transform;
548+
OB += '(';
549+
BaseType->print(OB);
550+
OB += ')';
551+
}
552+
};
553+
537554
struct AbiTagAttr : Node {
538555
Node *Base;
539556
std::string_view Tag;
@@ -4125,7 +4142,15 @@ Node *AbstractManglingParser<Derived, Alloc>::parseType() {
41254142
// Typically, <builtin-type>s are not considered substitution candidates,
41264143
// but the exception to that exception is vendor extended types (Itanium C++
41274144
// ABI 5.9.1).
4128-
Result = make<NameType>(Res);
4145+
if (consumeIf('I')) {
4146+
Node *BaseType = parseType();
4147+
if (BaseType == nullptr)
4148+
return nullptr;
4149+
if (!consumeIf('E'))
4150+
return nullptr;
4151+
Result = make<TransformedType>(Res, BaseType);
4152+
} else
4153+
Result = make<NameType>(Res);
41294154
break;
41304155
}
41314156
case 'D':

libcxxabi/src/demangle/ItaniumNodes.def

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ NODE(QualType)
1919
NODE(ConversionOperatorType)
2020
NODE(PostfixQualifiedType)
2121
NODE(ElaboratedTypeSpefType)
22+
NODE(TransformedType)
2223
NODE(NameType)
2324
NODE(AbiTagAttr)
2425
NODE(EnableIfAttr)

libcxxabi/test/test_demangle.pass.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30161,6 +30161,15 @@ const char* cases[][2] =
3016130161
" std::allocator<char>>::basic_string()"},
3016230162
{"_ZN1SB8ctor_tagC2Ev", "S[abi:ctor_tag]::S()"},
3016330163
{"_ZN1SB8ctor_tagD2Ev", "S[abi:ctor_tag]::~S()"},
30164+
30165+
// clang builtin type transform
30166+
{"_Z2f5IiEvu22__add_lvalue_referenceIT_E", "void f5<int>(__add_lvalue_reference(int))"},
30167+
{"_Z2f5IiEvu13__add_pointerIT_E", "void f5<int>(__add_pointer(int))"},
30168+
{"_Z2f5IiEvu7__decayIT_E", "void f5<int>(__decay(int))"},
30169+
{"_Z2f5IjEvu13__make_signedIT_E", "void f5<unsigned int>(__make_signed(unsigned int))"},
30170+
{"_Z2f5IKiEvu14__remove_constIT_E", "void f5<int const>(__remove_const(int const))"},
30171+
{"_Z2f5IPiEvu16__remove_pointerIT_E", "void f5<int*>(__remove_pointer(int*))"},
30172+
{"_Z2f5IiEvu14__remove_cvrefIT_E", "void f5<int>(__remove_cvref(int))"},
3016430173
};
3016530174

3016630175
const unsigned N = sizeof(cases) / sizeof(cases[0]);

llvm/include/llvm/Demangle/ItaniumDemangle.h

Lines changed: 26 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -533,6 +533,23 @@ class ElaboratedTypeSpefType : public Node {
533533
}
534534
};
535535

536+
class TransformedType : public Node {
537+
std::string_view Transform;
538+
Node *BaseType;
539+
public:
540+
TransformedType(std::string_view Transform_, Node *BaseType_)
541+
: Node(KTransformedType), Transform(Transform_), BaseType(BaseType_) {}
542+
543+
template<typename Fn> void match(Fn F) const { F(Transform, BaseType); }
544+
545+
void printLeft(OutputBuffer &OB) const override {
546+
OB += Transform;
547+
OB += '(';
548+
BaseType->print(OB);
549+
OB += ')';
550+
}
551+
};
552+
536553
struct AbiTagAttr : Node {
537554
Node *Base;
538555
std::string_view Tag;
@@ -4124,7 +4141,15 @@ Node *AbstractManglingParser<Derived, Alloc>::parseType() {
41244141
// Typically, <builtin-type>s are not considered substitution candidates,
41254142
// but the exception to that exception is vendor extended types (Itanium C++
41264143
// ABI 5.9.1).
4127-
Result = make<NameType>(Res);
4144+
if (consumeIf('I')) {
4145+
Node *BaseType = parseType();
4146+
if (BaseType == nullptr)
4147+
return nullptr;
4148+
if (!consumeIf('E'))
4149+
return nullptr;
4150+
Result = make<TransformedType>(Res, BaseType);
4151+
} else
4152+
Result = make<NameType>(Res);
41284153
break;
41294154
}
41304155
case 'D':

llvm/include/llvm/Demangle/ItaniumNodes.def

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ NODE(QualType)
1919
NODE(ConversionOperatorType)
2020
NODE(PostfixQualifiedType)
2121
NODE(ElaboratedTypeSpefType)
22+
NODE(TransformedType)
2223
NODE(NameType)
2324
NODE(AbiTagAttr)
2425
NODE(EnableIfAttr)

0 commit comments

Comments
 (0)