Skip to content

Commit fe43d0b

Browse files
author
Davide Italiano
committed
[Demangler] Add convenience functions to ask about types.
And use them in the reflection library (TypeRef). These were private to `TypeRef.cpp` but can be moved to the demangler as they can be of general use, and we can use them from lldb (which has homemade versions of the functions as well). Bonus point, it probably makes sense for these helpers to live in the demangler anyway. <rdar://problem/37710513>
1 parent 4d9e1b0 commit fe43d0b

File tree

3 files changed

+118
-75
lines changed

3 files changed

+118
-75
lines changed

include/swift/Demangling/Demangle.h

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -246,6 +246,31 @@ bool isSwiftSymbol(const char *mangledName);
246246
/// This does not include the old (<= swift 3.x) mangling prefix "_T".
247247
llvm::StringRef dropSwiftManglingPrefix(llvm::StringRef mangledName);
248248

249+
/// Returns true if the mangled name is an alias type name.
250+
///
251+
/// \param mangledName A null-terminated string containing a mangled name.
252+
bool isAlias(llvm::StringRef mangledName);
253+
254+
/// Returns true if the mangled name is a class type name.
255+
///
256+
/// \param mangledName A null-terminated string containing a mangled name.
257+
bool isClass(llvm::StringRef mangledName);
258+
259+
/// Returns true if the mangled name is an enum type name.
260+
///
261+
/// \param mangledName A null-terminated string containing a mangled name.
262+
bool isEnum(llvm::StringRef mangledName);
263+
264+
/// Returns true if the mangled name is a protocol type name.
265+
///
266+
/// \param mangledName A null-terminated string containing a mangled name.
267+
bool isProtocol(llvm::StringRef mangledName);
268+
269+
/// Returns true if the mangled name is a structure type name.
270+
///
271+
/// \param mangledName A null-terminated string containing a mangled name.
272+
bool isStruct(llvm::StringRef mangledName);
273+
249274
/// Returns true if the mangled name has the old scheme of function type
250275
/// mangling where labels are part of the type.
251276
///

lib/Demangling/Demangler.cpp

Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -168,6 +168,94 @@ llvm::StringRef swift::Demangle::dropSwiftManglingPrefix(StringRef mangledName){
168168
return mangledName.drop_front(getManglingPrefixLength(mangledName));
169169
}
170170

171+
static bool isAliasNode(Demangle::NodePointer Node) {
172+
switch (Node->getKind()) {
173+
case Demangle::Node::Kind::Type:
174+
return isAliasNode(Node->getChild(0));
175+
case Demangle::Node::Kind::TypeAlias:
176+
return true;
177+
default:
178+
return false;
179+
}
180+
llvm_unreachable("Unhandled node kind!");
181+
}
182+
183+
bool swift::Demangle::isAlias(llvm::StringRef mangledName) {
184+
Demangle::Demangler Dem;
185+
return isAliasNode(Dem.demangleType(mangledName));
186+
}
187+
188+
static bool isClassNode(Demangle::NodePointer Node) {
189+
switch (Node->getKind()) {
190+
case Demangle::Node::Kind::Type:
191+
return isClassNode(Node->getChild(0));
192+
case Demangle::Node::Kind::Class:
193+
case Demangle::Node::Kind::BoundGenericClass:
194+
return true;
195+
default:
196+
return false;
197+
}
198+
llvm_unreachable("Unhandled node kind!");
199+
}
200+
201+
bool swift::Demangle::isClass(llvm::StringRef mangledName) {
202+
Demangle::Demangler Dem;
203+
return isClassNode(Dem.demangleType(mangledName));
204+
}
205+
206+
static bool isEnumNode(Demangle::NodePointer Node) {
207+
switch (Node->getKind()) {
208+
case Demangle::Node::Kind::Type:
209+
return isEnumNode(Node->getChild(0));
210+
case Demangle::Node::Kind::Enum:
211+
case Demangle::Node::Kind::BoundGenericEnum:
212+
return true;
213+
default:
214+
return false;
215+
}
216+
llvm_unreachable("Unhandled node kind!");
217+
}
218+
219+
bool swift::Demangle::isEnum(llvm::StringRef mangledName) {
220+
Demangle::Demangler Dem;
221+
return isEnumNode(Dem.demangleType(mangledName));
222+
}
223+
224+
static bool isProtocolNode(Demangle::NodePointer Node) {
225+
switch (Node->getKind()) {
226+
case Demangle::Node::Kind::Type:
227+
return isProtocolNode(Node->getChild(0));
228+
case Demangle::Node::Kind::Protocol:
229+
return true;
230+
default:
231+
return false;
232+
}
233+
llvm_unreachable("Unhandled node kind!");
234+
}
235+
236+
bool swift::Demangle::isProtocol(llvm::StringRef mangledName) {
237+
Demangle::Demangler Dem;
238+
return isProtocolNode(Dem.demangleType(dropSwiftManglingPrefix(mangledName)));
239+
}
240+
241+
static bool isStructNode(Demangle::NodePointer Node) {
242+
switch (Node->getKind()) {
243+
case Demangle::Node::Kind::Type:
244+
return isStructNode(Node->getChild(0));
245+
case Demangle::Node::Kind::Structure:
246+
case Demangle::Node::Kind::BoundGenericStructure:
247+
return true;
248+
default:
249+
return false;
250+
}
251+
llvm_unreachable("Unhandled node kind!");
252+
}
253+
254+
bool swift::Demangle::isStruct(llvm::StringRef mangledName) {
255+
Demangle::Demangler Dem;
256+
return isStructNode(Dem.demangleType(mangledName));
257+
}
258+
171259
namespace swift {
172260
namespace Demangle {
173261

stdlib/public/Reflection/TypeRef.cpp

Lines changed: 5 additions & 75 deletions
Original file line numberDiff line numberDiff line change
@@ -420,92 +420,22 @@ GenericArgumentMap TypeRef::getSubstMap() const {
420420
return Substitutions;
421421
}
422422

423-
namespace {
424-
bool isStruct(Demangle::NodePointer Node) {
425-
switch (Node->getKind()) {
426-
case Demangle::Node::Kind::Type:
427-
return isStruct(Node->getChild(0));
428-
case Demangle::Node::Kind::Structure:
429-
case Demangle::Node::Kind::BoundGenericStructure:
430-
return true;
431-
default:
432-
return false;
433-
}
434-
}
435-
bool isEnum(Demangle::NodePointer Node) {
436-
switch (Node->getKind()) {
437-
case Demangle::Node::Kind::Type:
438-
return isEnum(Node->getChild(0));
439-
case Demangle::Node::Kind::Enum:
440-
case Demangle::Node::Kind::BoundGenericEnum:
441-
return true;
442-
default:
443-
return false;
444-
}
445-
}
446-
bool isClass(Demangle::NodePointer Node) {
447-
switch (Node->getKind()) {
448-
case Demangle::Node::Kind::Type:
449-
return isClass(Node->getChild(0));
450-
case Demangle::Node::Kind::Class:
451-
case Demangle::Node::Kind::BoundGenericClass:
452-
return true;
453-
default:
454-
return false;
455-
}
456-
}
457-
bool isProtocol(Demangle::NodePointer Node) {
458-
switch (Node->getKind()) {
459-
case Demangle::Node::Kind::Type:
460-
return isProtocol(Node->getChild(0));
461-
case Demangle::Node::Kind::Protocol:
462-
return true;
463-
default:
464-
return false;
465-
}
466-
}
467-
468-
bool isAlias(Demangle::NodePointer Node) {
469-
switch (Node->getKind()) {
470-
case Demangle::Node::Kind::Type:
471-
return isAlias(Node->getChild(0));
472-
case Demangle::Node::Kind::TypeAlias:
473-
return true;
474-
default:
475-
return false;
476-
}
477-
}
478-
} // end anonymous namespace
479-
480423
bool NominalTypeTrait::isStruct() const {
481-
Demangle::Demangler Dem;
482-
Demangle::NodePointer Demangled = Dem.demangleType(MangledName);
483-
return ::isStruct(Demangled);
424+
return Demangle::isStruct(MangledName);
484425
}
485426

486-
bool NominalTypeTrait::isEnum() const {
487-
Demangle::Demangler Dem;
488-
Demangle::NodePointer Demangled = Dem.demangleType(MangledName);
489-
return ::isEnum(Demangled);
490-
}
427+
bool NominalTypeTrait::isEnum() const { return Demangle::isEnum(MangledName); }
491428

492429
bool NominalTypeTrait::isClass() const {
493-
Demangle::Demangler Dem;
494-
Demangle::NodePointer Demangled = Dem.demangleType(MangledName);
495-
return ::isClass(Demangled);
430+
return Demangle::isClass(MangledName);
496431
}
497432

498433
bool NominalTypeTrait::isProtocol() const {
499-
Demangle::Demangler Dem;
500-
StringRef adjustedMangledName = Demangle::dropSwiftManglingPrefix(MangledName);
501-
Demangle::NodePointer Demangled = Dem.demangleType(adjustedMangledName);
502-
return ::isProtocol(Demangled);
434+
return Demangle::isProtocol(MangledName);
503435
}
504436

505437
bool NominalTypeTrait::isAlias() const {
506-
Demangle::Demangler Dem;
507-
Demangle::NodePointer Demangled = Dem.demangleType(MangledName);
508-
return ::isAlias(Demangled);
438+
return Demangle::isAlias(MangledName);
509439
}
510440

511441
/// Visitor class to set the WasAbstract flag of any MetatypeTypeRefs

0 commit comments

Comments
 (0)