From cd082954993dc917df0191f00bd47c5ab0d9a0fb Mon Sep 17 00:00:00 2001 From: triton Date: Tue, 23 Jul 2013 20:03:09 +0100 Subject: [PATCH] Use a map to keep track of anonymous declarations else we cannot refer to them later when needed. This could lead to self-referencing problems when parsing (and stack overflows!). --- src/AST/Namespace.cs | 9 +++++++++ src/Parser/Parser.cpp | 21 +++++++++++++++++++-- 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/src/AST/Namespace.cs b/src/AST/Namespace.cs index 06d92267..e70e3a96 100644 --- a/src/AST/Namespace.cs +++ b/src/AST/Namespace.cs @@ -20,6 +20,9 @@ namespace CppSharp.AST public List Variables; public List Events; + // Used to keep track of anonymous declarations. + public Dictionary Anonymous; + public TranslationUnit TranslationUnit { get @@ -41,6 +44,12 @@ namespace CppSharp.AST Typedefs = new List(); Variables = new List(); Events = new List(); + Anonymous = new Dictionary(); + } + + public Declaration FindAnonymous(ulong key) + { + return Anonymous.ContainsKey(key) ? Anonymous[key] : null; } public Namespace FindNamespace(string name) diff --git a/src/Parser/Parser.cpp b/src/Parser/Parser.cpp index 7584be79..c60cfb48 100644 --- a/src/Parser/Parser.cpp +++ b/src/Parser/Parser.cpp @@ -379,14 +379,30 @@ CppSharp::AST::Class^ Parser::WalkRecordCXX(clang::CXXRecordDecl* Record) assert(NS && "Expected a valid namespace"); bool isCompleteDefinition = Record->isCompleteDefinition(); - auto Name = marshalString(GetTagDeclName(Record)); - auto RC = NS->FindClass(Name, isCompleteDefinition, /*Create=*/false); + + CppSharp::AST::Class^ RC = nullptr; + + auto Name = marshalString(GetTagDeclName(Record)); + auto HasEmptyName = Record->getDeclName().isEmpty(); + + if (HasEmptyName) + { + if (auto AR = NS->FindAnonymous((uint64_t)Record)) + RC = safe_cast(AR); + } + else + { + RC = NS->FindClass(Name, isCompleteDefinition, /*Create=*/false); + } if (RC) return RC; RC = NS->FindClass(Name, isCompleteDefinition, /*Create=*/true); + if (HasEmptyName) + NS->Anonymous[(uint64_t)Record] = RC; + if (!isCompleteDefinition) return RC; @@ -467,6 +483,7 @@ CppSharp::AST::Class^ Parser::WalkRecordCXX(clang::CXXRecordDecl* Record) break; } case Decl::IndirectField: // FIXME: Handle indirect fields + break; default: { auto Decl = WalkDeclaration(D);