logic: fixed bug where anonymous symbols were only partly named like the enclosing typedef
* removed post processing for anonymous typedefs. The storage transformation did not work in cases where the typedef is recorded in a previously indexed header. No type information was recorded while indexing the header a second time. But this type information would have been required by the transformation.
This commit is contained in:
@@ -77,9 +77,6 @@ add_files(
|
||||
data/parser/cxx/PreprocessorCallbacks.h
|
||||
data/parser/cxx/utilityClang.cpp
|
||||
data/parser/cxx/utilityClang.h
|
||||
|
||||
data/storage/StorageTransformationAnonymousTypedef.cpp
|
||||
data/storage/StorageTransformationAnonymousTypedef.h
|
||||
|
||||
project/IncludeDirective.cpp
|
||||
project/IncludeDirective.h
|
||||
|
||||
@@ -6,14 +6,12 @@ IndexerCommandCxx::IndexerCommandCxx(
|
||||
const std::set<FilePath>& excludedPaths,
|
||||
const std::vector<FilePath>& systemHeaderSearchPaths,
|
||||
const std::vector<FilePath>& frameworkSearchPaths,
|
||||
const std::vector<std::string>& compilerFlags,
|
||||
const bool shouldApplyAnonymousTypedefTransformation
|
||||
const std::vector<std::string>& compilerFlags
|
||||
)
|
||||
: IndexerCommand(sourceFilePath, indexedPaths, excludedPaths)
|
||||
, m_systemHeaderSearchPaths(systemHeaderSearchPaths)
|
||||
, m_frameworkSearchPaths(frameworkSearchPaths)
|
||||
, m_compilerFlags(compilerFlags)
|
||||
, m_shouldApplyAnonymousTypedefTransformation(shouldApplyAnonymousTypedefTransformation)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -57,8 +55,3 @@ std::vector<std::string> IndexerCommandCxx::getCompilerFlags() const
|
||||
{
|
||||
return m_compilerFlags;
|
||||
}
|
||||
|
||||
bool IndexerCommandCxx::shouldApplyAnonymousTypedefTransformation() const
|
||||
{
|
||||
return m_shouldApplyAnonymousTypedefTransformation;
|
||||
}
|
||||
|
||||
@@ -18,8 +18,7 @@ public:
|
||||
const std::set<FilePath>& excludedPaths,
|
||||
const std::vector<FilePath>& systemHeaderSearchPaths,
|
||||
const std::vector<FilePath>& frameworkSearchPaths,
|
||||
const std::vector<std::string>& compilerFlags,
|
||||
const bool shouldApplyAnonymousTypedefTransformation);
|
||||
const std::vector<std::string>& compilerFlags);
|
||||
|
||||
virtual ~IndexerCommandCxx();
|
||||
virtual size_t getByteSize(size_t stringSize) const override;
|
||||
@@ -28,13 +27,10 @@ public:
|
||||
std::vector<FilePath> getFrameworkSearchPaths() const;
|
||||
std::vector<std::string> getCompilerFlags() const;
|
||||
|
||||
bool shouldApplyAnonymousTypedefTransformation() const;
|
||||
|
||||
private:
|
||||
std::vector<FilePath> m_systemHeaderSearchPaths;
|
||||
std::vector<FilePath> m_frameworkSearchPaths;
|
||||
std::vector<std::string> m_compilerFlags;
|
||||
bool m_shouldApplyAnonymousTypedefTransformation;
|
||||
};
|
||||
|
||||
#endif // INDEXER_COMMAND_CXXL_H
|
||||
|
||||
@@ -46,10 +46,9 @@ IndexerCommandCxxCdb::IndexerCommandCxxCdb(
|
||||
const FilePath& workingDirectory,
|
||||
const std::vector<std::string>& compilerFlags,
|
||||
const std::vector<FilePath>& systemHeaderSearchPaths,
|
||||
const std::vector<FilePath>& frameworkSearchPaths,
|
||||
const bool shouldApplyAnonymousTypedefTransformation
|
||||
const std::vector<FilePath>& frameworkSearchPaths
|
||||
)
|
||||
: IndexerCommandCxx(sourceFilePath, indexedPaths, excludedPaths, systemHeaderSearchPaths, frameworkSearchPaths, compilerFlags, shouldApplyAnonymousTypedefTransformation)
|
||||
: IndexerCommandCxx(sourceFilePath, indexedPaths, excludedPaths, systemHeaderSearchPaths, frameworkSearchPaths, compilerFlags)
|
||||
, m_workingDirectory(workingDirectory)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -27,8 +27,7 @@ public:
|
||||
const FilePath& workingDirectory,
|
||||
const std::vector<std::string>& compilerFlags,
|
||||
const std::vector<FilePath>& systemHeaderSearchPaths,
|
||||
const std::vector<FilePath>& frameworkSearchPaths,
|
||||
const bool shouldApplyAnonymousTypedefTransformation);
|
||||
const std::vector<FilePath>& frameworkSearchPaths);
|
||||
|
||||
virtual ~IndexerCommandCxxCdb();
|
||||
|
||||
|
||||
@@ -12,10 +12,9 @@ IndexerCommandCxxManual::IndexerCommandCxxManual(
|
||||
const std::string& languageStandard,
|
||||
const std::vector<FilePath>& systemHeaderSearchPaths,
|
||||
const std::vector<FilePath>& frameworkSearchPaths,
|
||||
const std::vector<std::string>& compilerFlags,
|
||||
const bool shouldApplyAnonymousTypedefTransformation
|
||||
const std::vector<std::string>& compilerFlags
|
||||
)
|
||||
: IndexerCommandCxx(sourceFilePath, indexedPaths, excludedPaths, systemHeaderSearchPaths, frameworkSearchPaths, compilerFlags, shouldApplyAnonymousTypedefTransformation)
|
||||
: IndexerCommandCxx(sourceFilePath, indexedPaths, excludedPaths, systemHeaderSearchPaths, frameworkSearchPaths, compilerFlags)
|
||||
, m_languageStandard(languageStandard)
|
||||
{
|
||||
}
|
||||
|
||||
@@ -18,8 +18,7 @@ public:
|
||||
const std::string& languageStandard,
|
||||
const std::vector<FilePath>& systemHeaderSearchPaths,
|
||||
const std::vector<FilePath>& frameworkSearchPaths,
|
||||
const std::vector<std::string>& compilerFlags,
|
||||
const bool shouldApplyAnonymousTypedefTransformation);
|
||||
const std::vector<std::string>& compilerFlags);
|
||||
|
||||
virtual ~IndexerCommandCxxManual();
|
||||
|
||||
|
||||
@@ -5,7 +5,6 @@
|
||||
|
||||
#include "data/indexer/Indexer.h"
|
||||
#include "data/parser/ParserClientImpl.h"
|
||||
#include "data/storage/StorageTransformationAnonymousTypedef.h"
|
||||
#include "utility/file/FileRegister.h"
|
||||
|
||||
template <typename IndexerCommandType, typename ParserType>
|
||||
@@ -55,11 +54,6 @@ std::shared_ptr<IntermediateStorage> IndexerCxx<IndexerCommandType, ParserType>:
|
||||
return std::shared_ptr<IntermediateStorage>();
|
||||
}
|
||||
|
||||
if (indexerCommand->shouldApplyAnonymousTypedefTransformation())
|
||||
{
|
||||
StorageTransformationAnonymousTypedef::transform(storage);
|
||||
}
|
||||
|
||||
return storage;
|
||||
}
|
||||
|
||||
|
||||
@@ -194,7 +194,6 @@ void CxxAstVisitorComponentIndexer::visitTagDecl(clang::TagDecl* d)
|
||||
symbolKind
|
||||
);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -441,7 +440,7 @@ void CxxAstVisitorComponentIndexer::visitTypedefDecl(clang::TypedefDecl* d)
|
||||
{
|
||||
m_client->recordSymbol(
|
||||
getAstVisitor()->getDeclNameCache()->getValue(d),
|
||||
SYMBOL_TYPEDEF,
|
||||
d->getAnonDeclWithTypedefName() == NULL ? SYMBOL_TYPEDEF : utility::convertTagKind(d->getAnonDeclWithTypedefName()->getTagKind()),
|
||||
getParseLocation(d->getLocation()),
|
||||
utility::convertAccessSpecifier(d->getAccess()),
|
||||
utility::isImplicit(d) ? DEFINITION_IMPLICIT : DEFINITION_EXPLICIT
|
||||
@@ -455,7 +454,7 @@ void CxxAstVisitorComponentIndexer::visitTypeAliasDecl(clang::TypeAliasDecl* d)
|
||||
{
|
||||
m_client->recordSymbol(
|
||||
getAstVisitor()->getDeclNameCache()->getValue(d),
|
||||
SYMBOL_TYPEDEF,
|
||||
d->getAnonDeclWithTypedefName() == NULL ? SYMBOL_TYPEDEF : utility::convertTagKind(d->getAnonDeclWithTypedefName()->getTagKind()),
|
||||
getParseLocation(d->getLocation()),
|
||||
utility::convertAccessSpecifier(d->getAccess()),
|
||||
utility::isImplicit(d) ? DEFINITION_IMPLICIT : DEFINITION_EXPLICIT
|
||||
|
||||
@@ -171,6 +171,14 @@ std::shared_ptr<CxxDeclName> CxxDeclNameResolver::getDeclName(const clang::Named
|
||||
ScopedSwitcher<const clang::NamedDecl*> switcher(m_currentDecl, declaration);
|
||||
|
||||
std::string declNameString = declaration->getNameAsString();
|
||||
if (const clang::TagDecl* tagDecl = clang::dyn_cast_or_null<clang::TagDecl>(declaration))
|
||||
{
|
||||
if (const clang::TypedefNameDecl* typedefNameDecl = tagDecl->getTypedefNameForAnonDecl())
|
||||
{
|
||||
declNameString = typedefNameDecl->getNameAsString();
|
||||
}
|
||||
}
|
||||
|
||||
if (const clang::TypeAliasDecl* typeAliasDecl = clang::dyn_cast_or_null<clang::TypeAliasDecl>(declaration))
|
||||
{
|
||||
clang::TypeAliasTemplateDecl* templatedDeclaration = typeAliasDecl->getDescribedAliasTemplate();
|
||||
|
||||
@@ -1,112 +0,0 @@
|
||||
#include "data/storage/StorageTransformationAnonymousTypedef.h"
|
||||
|
||||
#include <map>
|
||||
|
||||
#include "data/graph/Node.h"
|
||||
#include "data/name/NameDelimiterType.h"
|
||||
#include "data/storage/IntermediateStorage.h"
|
||||
#include "utility/logging/logging.h"
|
||||
#include "utility/utilityString.h"
|
||||
|
||||
void StorageTransformationAnonymousTypedef::transform(std::shared_ptr<IntermediateStorage> storage)
|
||||
{
|
||||
LOG_INFO("Applying storage transformation to rename anonymous types inside typedefs.");
|
||||
|
||||
if (!storage)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
std::vector<StorageNode> nodes = storage->getStorageNodes();
|
||||
std::vector<StorageEdge> edges = storage->getStorageEdges();
|
||||
std::vector<StorageOccurrence> occurrences = storage->getStorageOccurrences();
|
||||
|
||||
std::map<Id, Id> nodesToMerge;
|
||||
std::map<std::string, std::string> nodesToRename;
|
||||
|
||||
{
|
||||
std::map<Id, StorageNode> typedefNodes;
|
||||
std::map<Id, StorageNode> anonymousTypeNodes;
|
||||
|
||||
for (const StorageNode& node : nodes)
|
||||
{
|
||||
const NodeType::Type nodeType = utility::intToType(node.type);
|
||||
if (nodeType & NodeType::NODE_TYPEDEF)
|
||||
{
|
||||
typedefNodes.insert(std::pair<Id, StorageNode>(node.id, node));
|
||||
}
|
||||
else if(nodeType & (NodeType::NODE_STRUCT | NodeType::NODE_CLASS | NodeType::NODE_ENUM | NodeType::NODE_UNION))
|
||||
{
|
||||
const NameHierarchy nameHierarchy = NameHierarchy::deserialize(node.serializedName);
|
||||
if (nameHierarchy.back() && utility::isPrefix("anonymous ", nameHierarchy.back()->getName()))
|
||||
{
|
||||
anonymousTypeNodes.insert(std::pair<Id, StorageNode>(node.id, node));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (const StorageEdge& edge : edges)
|
||||
{
|
||||
if (Edge::intToType(edge.type) & Edge::EDGE_TYPE_USAGE)
|
||||
{
|
||||
std::map<Id, StorageNode>::const_iterator itAnonymousTypeNodes = anonymousTypeNodes.find(edge.targetNodeId);
|
||||
if (itAnonymousTypeNodes != anonymousTypeNodes.end())
|
||||
{
|
||||
std::map<Id, StorageNode>::const_iterator itTypedefNodes = typedefNodes.find(edge.sourceNodeId);
|
||||
if (itTypedefNodes != typedefNodes.end())
|
||||
{
|
||||
nodesToMerge.insert(std::pair<Id, Id>(itTypedefNodes->first, itAnonymousTypeNodes->first));
|
||||
nodesToRename.insert(std::pair<std::string, std::string>(itAnonymousTypeNodes->second.serializedName, itTypedefNodes->second.serializedName));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// remove typedef nodes that refer to anonymous types
|
||||
// and rename anonymous types to typedef name
|
||||
for (size_t i = 0; i < nodes.size(); i++)
|
||||
{
|
||||
if (nodesToMerge.find(nodes[i].id) != nodesToMerge.end())
|
||||
{
|
||||
nodes.erase(nodes.begin() + i);
|
||||
i--;
|
||||
}
|
||||
else
|
||||
{
|
||||
for (std::map<std::string, std::string>::const_iterator it = nodesToRename.begin(); it != nodesToRename.end(); it++)
|
||||
{
|
||||
if (utility::isPrefix(it->first, nodes[i].serializedName))
|
||||
{
|
||||
nodes[i].serializedName = it->second + nodes[i].serializedName.substr(it->first.size());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// redirect edges that pointed to removed nodes
|
||||
for (StorageEdge& edge : edges)
|
||||
{
|
||||
std::map<Id, Id>::const_iterator it = nodesToMerge.find(edge.targetNodeId);
|
||||
if (it != nodesToMerge.end())
|
||||
{
|
||||
edge.targetNodeId = it->second;
|
||||
}
|
||||
}
|
||||
|
||||
// relink source locations of removed nodes
|
||||
for (StorageOccurrence& occurrence : occurrences)
|
||||
{
|
||||
std::map<Id, Id>::const_iterator it = nodesToMerge.find(occurrence.elementId);
|
||||
if (it != nodesToMerge.end())
|
||||
{
|
||||
occurrence.elementId = it->second;
|
||||
}
|
||||
}
|
||||
|
||||
storage->setStorageNodes(nodes);
|
||||
storage->setStorageEdges(edges);
|
||||
storage->setStorageOccurrences(occurrences);
|
||||
|
||||
LOG_INFO("Renamed " + std::to_string(nodesToRename.size()) + " types.");
|
||||
}
|
||||
@@ -1,14 +0,0 @@
|
||||
#ifndef STORAGE_TRANSFORMATION_ANONYMOUS_TYPEDEF_H
|
||||
#define STORAGE_TRANSFORMATION_ANONYMOUS_TYPEDEF_H
|
||||
|
||||
#include <memory>
|
||||
|
||||
class IntermediateStorage;
|
||||
|
||||
class StorageTransformationAnonymousTypedef
|
||||
{
|
||||
public:
|
||||
static void transform(std::shared_ptr<IntermediateStorage> storage);
|
||||
};
|
||||
|
||||
#endif // STORAGE_TRANSFORMATION_ANONYMOUS_TYPEDEF_H
|
||||
@@ -118,8 +118,7 @@ std::vector<std::shared_ptr<IndexerCommand>> SourceGroupCxxCdb::getIndexerComman
|
||||
FilePath(command.Directory),
|
||||
currentCompilerFlags,
|
||||
systemHeaderSearchPaths,
|
||||
frameworkSearchPaths,
|
||||
m_settings->getShouldApplyAnonymousTypedefTransformation()
|
||||
frameworkSearchPaths
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -65,8 +65,7 @@ std::vector<std::shared_ptr<IndexerCommand>> SourceGroupCxxEmpty::getIndexerComm
|
||||
m_settings->getStandard(),
|
||||
systemHeaderSearchPaths,
|
||||
frameworkSearchPaths,
|
||||
compilerFlags,
|
||||
m_settings->getShouldApplyAnonymousTypedefTransformation()
|
||||
compilerFlags
|
||||
));
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user