summaryrefslogtreecommitdiff
path: root/lib/Demangle
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2019-10-23 17:51:42 +0000
committerDimitry Andric <dim@FreeBSD.org>2019-10-23 17:51:42 +0000
commit1d5ae1026e831016fc29fd927877c86af904481f (patch)
tree2cdfd12620fcfa5d9e4a0389f85368e8e36f63f9 /lib/Demangle
parente6d1592492a3a379186bfb02bd0f4eda0669c0d5 (diff)
Notes
Diffstat (limited to 'lib/Demangle')
-rw-r--r--lib/Demangle/ItaniumDemangle.cpp10
-rw-r--r--lib/Demangle/MicrosoftDemangle.cpp32
-rw-r--r--lib/Demangle/MicrosoftDemangleNodes.cpp51
3 files changed, 70 insertions, 23 deletions
diff --git a/lib/Demangle/ItaniumDemangle.cpp b/lib/Demangle/ItaniumDemangle.cpp
index 5c99c70e3cc63..760d28b3ab9db 100644
--- a/lib/Demangle/ItaniumDemangle.cpp
+++ b/lib/Demangle/ItaniumDemangle.cpp
@@ -174,6 +174,16 @@ struct DumpVisitor {
return printStr("SpecialSubKind::iostream");
}
}
+ void print(TemplateParamKind TPK) {
+ switch (TPK) {
+ case TemplateParamKind::Type:
+ return printStr("TemplateParamKind::Type");
+ case TemplateParamKind::NonType:
+ return printStr("TemplateParamKind::NonType");
+ case TemplateParamKind::Template:
+ return printStr("TemplateParamKind::Template");
+ }
+ }
void newLine() {
printStr("\n");
diff --git a/lib/Demangle/MicrosoftDemangle.cpp b/lib/Demangle/MicrosoftDemangle.cpp
index bf7d77638f34e..c681d6e25b879 100644
--- a/lib/Demangle/MicrosoftDemangle.cpp
+++ b/lib/Demangle/MicrosoftDemangle.cpp
@@ -783,8 +783,26 @@ SymbolNode *Demangler::demangleMD5Name(StringView &MangledName) {
return S;
}
+SymbolNode *Demangler::demangleTypeinfoName(StringView &MangledName) {
+ assert(MangledName.startsWith('.'));
+ MangledName.consumeFront('.');
+
+ TypeNode *T = demangleType(MangledName, QualifierMangleMode::Result);
+ if (Error || !MangledName.empty()) {
+ Error = true;
+ return nullptr;
+ }
+ return synthesizeVariable(Arena, T, "`RTTI Type Descriptor Name'");
+}
+
// Parser entry point.
SymbolNode *Demangler::parse(StringView &MangledName) {
+ // Typeinfo names are strings stored in RTTI data. They're not symbol names.
+ // It's still useful to demangle them. They're the only demangled entity
+ // that doesn't start with a "?" but a ".".
+ if (MangledName.startsWith('.'))
+ return demangleTypeinfoName(MangledName);
+
if (MangledName.startsWith("??@"))
return demangleMD5Name(MangledName);
@@ -2161,7 +2179,7 @@ NodeArrayNode *Demangler::demangleFunctionParameterList(StringView &MangledName,
NodeArrayNode *
Demangler::demangleTemplateParameterList(StringView &MangledName) {
- NodeList *Head;
+ NodeList *Head = nullptr;
NodeList **Current = &Head;
size_t Count = 0;
@@ -2328,12 +2346,22 @@ char *llvm::microsoftDemangle(const char *MangledName, char *Buf, size_t *N,
if (Flags & MSDF_DumpBackrefs)
D.dumpBackReferences();
+ OutputFlags OF = OF_Default;
+ if (Flags & MSDF_NoCallingConvention)
+ OF = OutputFlags(OF | OF_NoCallingConvention);
+ if (Flags & MSDF_NoAccessSpecifier)
+ OF = OutputFlags(OF | OF_NoAccessSpecifier);
+ if (Flags & MSDF_NoReturnType)
+ OF = OutputFlags(OF | OF_NoReturnType);
+ if (Flags & MSDF_NoMemberType)
+ OF = OutputFlags(OF | OF_NoMemberType);
+
if (D.Error)
InternalStatus = demangle_invalid_mangled_name;
else if (!initializeOutputStream(Buf, N, S, 1024))
InternalStatus = demangle_memory_alloc_failure;
else {
- AST->output(S, OF_Default);
+ AST->output(S, OF);
S += '\0';
if (N != nullptr)
*N = S.getCurrentPosition();
diff --git a/lib/Demangle/MicrosoftDemangleNodes.cpp b/lib/Demangle/MicrosoftDemangleNodes.cpp
index 63ca475ec1fed..9cee975231a2a 100644
--- a/lib/Demangle/MicrosoftDemangleNodes.cpp
+++ b/lib/Demangle/MicrosoftDemangleNodes.cpp
@@ -120,8 +120,6 @@ std::string Node::toString(OutputFlags Flags) const {
return {OS.getBuffer()};
}
-void TypeNode::outputQuals(bool SpaceBefore, bool SpaceAfter) const {}
-
void PrimitiveTypeNode::outputPre(OutputStream &OS, OutputFlags Flags) const {
switch (PrimKind) {
OUTPUT_ENUM_CLASS_VALUE(PrimitiveKind, Void, "void");
@@ -380,24 +378,28 @@ void LiteralOperatorIdentifierNode::output(OutputStream &OS,
void FunctionSignatureNode::outputPre(OutputStream &OS,
OutputFlags Flags) const {
- if (FunctionClass & FC_Public)
- OS << "public: ";
- if (FunctionClass & FC_Protected)
- OS << "protected: ";
- if (FunctionClass & FC_Private)
- OS << "private: ";
-
- if (!(FunctionClass & FC_Global)) {
- if (FunctionClass & FC_Static)
- OS << "static ";
+ if (!(Flags & OF_NoAccessSpecifier)) {
+ if (FunctionClass & FC_Public)
+ OS << "public: ";
+ if (FunctionClass & FC_Protected)
+ OS << "protected: ";
+ if (FunctionClass & FC_Private)
+ OS << "private: ";
}
- if (FunctionClass & FC_Virtual)
- OS << "virtual ";
- if (FunctionClass & FC_ExternC)
- OS << "extern \"C\" ";
+ if (!(Flags & OF_NoMemberType)) {
+ if (!(FunctionClass & FC_Global)) {
+ if (FunctionClass & FC_Static)
+ OS << "static ";
+ }
+ if (FunctionClass & FC_Virtual)
+ OS << "virtual ";
+
+ if (FunctionClass & FC_ExternC)
+ OS << "extern \"C\" ";
+ }
- if (ReturnType) {
+ if (!(Flags & OF_NoReturnType) && ReturnType) {
ReturnType->outputPre(OS, Flags);
OS << " ";
}
@@ -440,7 +442,7 @@ void FunctionSignatureNode::outputPost(OutputStream &OS,
else if (RefQualifier == FunctionRefQualifier::RValueReference)
OS << " &&";
- if (ReturnType)
+ if (!(Flags & OF_NoReturnType) && ReturnType)
ReturnType->outputPost(OS, Flags);
}
@@ -582,19 +584,26 @@ void FunctionSymbolNode::output(OutputStream &OS, OutputFlags Flags) const {
}
void VariableSymbolNode::output(OutputStream &OS, OutputFlags Flags) const {
+ const char *AccessSpec = nullptr;
+ bool IsStatic = true;
switch (SC) {
case StorageClass::PrivateStatic:
- OS << "private: static ";
+ AccessSpec = "private";
break;
case StorageClass::PublicStatic:
- OS << "public: static ";
+ AccessSpec = "public";
break;
case StorageClass::ProtectedStatic:
- OS << "protected: static ";
+ AccessSpec = "protected";
break;
default:
+ IsStatic = false;
break;
}
+ if (!(Flags & OF_NoAccessSpecifier) && AccessSpec)
+ OS << AccessSpec << ": ";
+ if (!(Flags & OF_NoMemberType) && IsStatic)
+ OS << "static ";
if (Type) {
Type->outputPre(OS, Flags);