diff --git a/src/lib/CMakeLists.txt b/src/lib/CMakeLists.txt index 5c0ac7ee..bceb96cf 100644 --- a/src/lib/CMakeLists.txt +++ b/src/lib/CMakeLists.txt @@ -73,6 +73,8 @@ add_files( data/graph/token_component/TokenComponent.cpp data/graph/token_component/TokenComponent.h + data/graph/token_component/TokenComponentAbstraction.cpp + data/graph/token_component/TokenComponentAbstraction.h data/graph/token_component/TokenComponentAccess.cpp data/graph/token_component/TokenComponentAccess.h data/graph/token_component/TokenComponentConst.cpp diff --git a/src/lib/data/Storage.cpp b/src/lib/data/Storage.cpp index 26ca60fe..c0bd601c 100644 --- a/src/lib/data/Storage.cpp +++ b/src/lib/data/Storage.cpp @@ -174,6 +174,7 @@ Id Storage::onMethodParsed( LOG_ERROR("Method needs to have access type [public, protected, private] but has none."); } addAccess(node, access); + addAbstraction(node, abstraction); addTokenLocation(node, location); addTokenLocation(node, scopeLocation, true); @@ -655,6 +656,31 @@ TokenComponentAccess* Storage::addAccess(Node* node, ParserClient::AccessType ac return nullptr; } +TokenComponentAbstraction::AbstractionType Storage::convertAbstractionType(ParserClient::AbstractionType abstraction) const +{ + switch (abstraction) + { + case ABSTRACTION_VIRTUAL: + return TokenComponentAbstraction::ABSTRACTION_VIRTUAL; + case ABSTRACTION_PURE_VIRTUAL: + return TokenComponentAbstraction::ABSTRACTION_PURE_VIRTUAL; + case ABSTRACTION_NONE: + return TokenComponentAbstraction::ABSTRACTION_NONE; + } +} + +TokenComponentAbstraction* Storage::addAbstraction(Node* node, ParserClient::AbstractionType abstraction) +{ + if (abstraction != ABSTRACTION_NONE) + { + std::shared_ptr ptr = + std::make_shared(convertAbstractionType(abstraction)); + node->addComponentAbstraction(ptr); + return ptr.get(); + } + return nullptr; +} + Edge* Storage::addTypeEdge(Node* node, Edge::EdgeType edgeType, const DataType& type) { Node* typeNode = m_graph.createNodeHierarchy(type.getRawTypeName()); diff --git a/src/lib/data/Storage.h b/src/lib/data/Storage.h index f4575a9c..59bd6ccc 100644 --- a/src/lib/data/Storage.h +++ b/src/lib/data/Storage.h @@ -7,6 +7,7 @@ #include "data/access/GraphAccess.h" #include "data/access/LocationAccess.h" #include "data/graph/Graph.h" +#include "data/graph/token_component/TokenComponentAbstraction.h" #include "data/graph/token_component/TokenComponentAccess.h" #include "data/location/TokenLocationCollection.h" #include "data/parser/ParserClient.h" @@ -97,6 +98,10 @@ protected: private: TokenComponentAccess::AccessType convertAccessType(ParserClient::AccessType access) const; TokenComponentAccess* addAccess(Node* node, ParserClient::AccessType access); + + TokenComponentAbstraction::AbstractionType convertAbstractionType(ParserClient::AbstractionType abstraction) const; + TokenComponentAbstraction* addAbstraction(Node* node, ParserClient::AbstractionType abstraction); + Edge* addTypeEdge(Node* node, Edge::EdgeType edgeType, const DataType& type); Edge* addTypeEdge(Node* node, Edge::EdgeType edgeType, const ParseTypeUsage& typeUsage); TokenLocation* addTokenLocation(Token* token, const ParseLocation& location, bool isScope = false); diff --git a/src/lib/data/graph/Node.cpp b/src/lib/data/graph/Node.cpp index b9da6ee2..1d52af43 100644 --- a/src/lib/data/graph/Node.cpp +++ b/src/lib/data/graph/Node.cpp @@ -2,6 +2,7 @@ #include +#include "data/graph/token_component/TokenComponentAbstraction.h" #include "data/graph/token_component/TokenComponentConst.h" #include "data/graph/token_component/TokenComponentStatic.h" #include "data/graph/token_component/TokenComponentSignature.h" @@ -196,6 +197,22 @@ bool Node::isEdge() const return false; } +void Node::addComponentAbstraction(std::shared_ptr component) +{ + if (getComponent()) + { + LOG_ERROR("TokenComponentAbstraction has been set before!"); + } + else if (!isType(NODE_METHOD)) + { + LOG_ERROR("TokenComponentAbstraction can't be set on node of type: " + getTypeString()); + } + else + { + addComponent(component); + } +} + void Node::addComponentConst(std::shared_ptr component) { if (getComponent()) diff --git a/src/lib/data/graph/Node.h b/src/lib/data/graph/Node.h index ac1ff85b..8ac77649 100644 --- a/src/lib/data/graph/Node.h +++ b/src/lib/data/graph/Node.h @@ -9,6 +9,7 @@ #include "data/graph/Edge.h" #include "data/graph/Token.h" +class TokenComponentAbstraction; class TokenComponentConst; class TokenComponentStatic; class TokenComponentSignature; @@ -65,6 +66,7 @@ public: virtual bool isEdge() const; // Component setters. + void addComponentAbstraction(std::shared_ptr component); void addComponentConst(std::shared_ptr component); void addComponentStatic(std::shared_ptr component); void addComponentSignature(std::shared_ptr component); diff --git a/src/lib/data/graph/token_component/TokenComponentAbstraction.cpp b/src/lib/data/graph/token_component/TokenComponentAbstraction.cpp new file mode 100644 index 00000000..b87d3900 --- /dev/null +++ b/src/lib/data/graph/token_component/TokenComponentAbstraction.cpp @@ -0,0 +1,34 @@ +#include "data/graph/token_component/TokenComponentAbstraction.h" + +TokenComponentAbstraction::TokenComponentAbstraction(AbstractionType abstraction) + : m_abstraction(abstraction) +{ +} + +TokenComponentAbstraction::~TokenComponentAbstraction() +{ +} + +std::shared_ptr TokenComponentAbstraction::copy() const +{ + return std::make_shared(*this); +} + +TokenComponentAbstraction::AbstractionType TokenComponentAbstraction::getAbstraction() const +{ + return m_abstraction; +} + +std::string TokenComponentAbstraction::getAbstractionString() const +{ + switch (m_abstraction) + { + case ABSTRACTION_VIRTUAL: + return "virtual"; + case ABSTRACTION_PURE_VIRTUAL: + return "pure virtual"; + case ABSTRACTION_NONE: + return ""; + } + return ""; +} diff --git a/src/lib/data/graph/token_component/TokenComponentAbstraction.h b/src/lib/data/graph/token_component/TokenComponentAbstraction.h new file mode 100644 index 00000000..3ad45c07 --- /dev/null +++ b/src/lib/data/graph/token_component/TokenComponentAbstraction.h @@ -0,0 +1,31 @@ +#ifndef TOKEN_COMPONENT_ABSTRACTION_H +#define TOKEN_COMPONENT_ABSTRACTION_H + +#include + +#include "data/graph/token_component/TokenComponent.h" + +class TokenComponentAbstraction + : public TokenComponent +{ +public: + enum AbstractionType + { + ABSTRACTION_VIRTUAL, + ABSTRACTION_PURE_VIRTUAL, + ABSTRACTION_NONE + }; + + TokenComponentAbstraction(AbstractionType abstraction); + virtual ~TokenComponentAbstraction(); + + virtual std::shared_ptr copy() const; + + AbstractionType getAbstraction() const; + std::string getAbstractionString() const; + +private: + const AbstractionType m_abstraction; +}; + +#endif // TOKEN_COMPONENT_ABSTRACTION_H diff --git a/src/lib/data/graph/token_component/TokenComponentAccess.h b/src/lib/data/graph/token_component/TokenComponentAccess.h index 61a28f33..6db6d1e3 100644 --- a/src/lib/data/graph/token_component/TokenComponentAccess.h +++ b/src/lib/data/graph/token_component/TokenComponentAccess.h @@ -1,5 +1,5 @@ -#ifndef TOKEN_COMPONENT_ACCESS -#define TOKEN_COMPONENT_ACCESS +#ifndef TOKEN_COMPONENT_ACCESS_H +#define TOKEN_COMPONENT_ACCESS_H #include @@ -23,11 +23,10 @@ public: virtual std::shared_ptr copy() const; AccessType getAccess() const; - std::string getAccessString() const; private: const AccessType m_access; }; -#endif // TOKEN_COMPONENT_ACCESS +#endif // TOKEN_COMPONENT_ACCESS_H diff --git a/src/lib/data/graph/token_component/TokenComponentConst.h b/src/lib/data/graph/token_component/TokenComponentConst.h index 301041ce..9a694ae2 100644 --- a/src/lib/data/graph/token_component/TokenComponentConst.h +++ b/src/lib/data/graph/token_component/TokenComponentConst.h @@ -1,5 +1,5 @@ -#ifndef TOKEN_COMPONENT_CONST -#define TOKEN_COMPONENT_CONST +#ifndef TOKEN_COMPONENT_CONST_H +#define TOKEN_COMPONENT_CONST_H #include "data/graph/token_component/TokenComponent.h" @@ -10,4 +10,4 @@ public: virtual std::shared_ptr copy() const; }; -#endif // TOKEN_COMPONENT_CONST +#endif // TOKEN_COMPONENT_CONST_H diff --git a/src/lib/data/graph/token_component/TokenComponentDataType.h b/src/lib/data/graph/token_component/TokenComponentDataType.h index 5f1c3eae..46c46e36 100644 --- a/src/lib/data/graph/token_component/TokenComponentDataType.h +++ b/src/lib/data/graph/token_component/TokenComponentDataType.h @@ -1,5 +1,5 @@ -#ifndef TOKEN_COMPONENT_DATA_TYPE -#define TOKEN_COMPONENT_DATA_TYPE +#ifndef TOKEN_COMPONENT_DATA_TYPE_H +#define TOKEN_COMPONENT_DATA_TYPE_H #include "data/graph/token_component/TokenComponent.h" #include "data/type/DataTypeModifierStack.h" @@ -24,4 +24,4 @@ private: const DataTypeModifierStack m_modifierStack; }; -#endif // TOKEN_COMPONENT_DATA_TYPE +#endif // TOKEN_COMPONENT_DATA_TYPE_H diff --git a/src/lib/data/graph/token_component/TokenComponentSignature.h b/src/lib/data/graph/token_component/TokenComponentSignature.h index bbd0384e..60cff55f 100644 --- a/src/lib/data/graph/token_component/TokenComponentSignature.h +++ b/src/lib/data/graph/token_component/TokenComponentSignature.h @@ -1,5 +1,5 @@ -#ifndef TOKEN_COMPONENT_SIGNATURE -#define TOKEN_COMPONENT_SIGNATURE +#ifndef TOKEN_COMPONENT_SIGNATURE_H +#define TOKEN_COMPONENT_SIGNATURE_H #include @@ -20,4 +20,4 @@ private: const std::string m_signature; }; -#endif // TOKEN_COMPONENT_SIGNATURE +#endif // TOKEN_COMPONENT_SIGNATURE_H diff --git a/src/lib/data/graph/token_component/TokenComponentStatic.h b/src/lib/data/graph/token_component/TokenComponentStatic.h index c8d1d2d9..72013126 100644 --- a/src/lib/data/graph/token_component/TokenComponentStatic.h +++ b/src/lib/data/graph/token_component/TokenComponentStatic.h @@ -1,5 +1,5 @@ -#ifndef TOKEN_COMPONENT_STATIC -#define TOKEN_COMPONENT_STATIC +#ifndef TOKEN_COMPONENT_STATIC_H +#define TOKEN_COMPONENT_STATIC_H #include "data/graph/token_component/TokenComponent.h" @@ -10,4 +10,4 @@ public: virtual std::shared_ptr copy() const; }; -#endif // TOKEN_COMPONENT_STATIC +#endif // TOKEN_COMPONENT_STATIC_H diff --git a/src/test/CxxParserTestSuite.h b/src/test/CxxParserTestSuite.h index 3d36c2ca..19d5cf12 100644 --- a/src/test/CxxParserTestSuite.h +++ b/src/test/CxxParserTestSuite.h @@ -258,6 +258,20 @@ public: TS_ASSERT_EQUALS(client->methods[1], "public void B::B() <6:1 <6:4 6:4> 8:1>"); } + void test_cxx_parser_finds_virtual_method() + { + std::shared_ptr client = parseCode( + "class B\n" + "{\n" + "public:\n" + " virtual void process();\n" + "};\n" + ); + + TS_ASSERT_EQUALS(client->methods.size(), 1); + TS_ASSERT_EQUALS(client->methods[0], "public virtual void B::process() <4:15 4:21>"); + } + void test_cxx_parser_finds_pure_virtual_method() { std::shared_ptr client = parseCode( diff --git a/src/test/StorageTestSuite.h b/src/test/StorageTestSuite.h index 425e0573..1144c8a4 100644 --- a/src/test/StorageTestSuite.h +++ b/src/test/StorageTestSuite.h @@ -1,5 +1,6 @@ #include "cxxtest/TestSuite.h" +#include "data/graph/token_component/TokenComponentAbstraction.h" #include "data/graph/token_component/TokenComponentAccess.h" #include "data/graph/token_component/TokenComponentSignature.h" #include "data/graph/token_component/TokenComponentStatic.h" @@ -257,6 +258,12 @@ public: TS_ASSERT_EQUALS(node->getFullName(), "Class::isMethod"); TS_ASSERT_EQUALS(node->getType(), Node::NODE_METHOD); + TS_ASSERT(node->getComponent()); + TS_ASSERT_EQUALS( + node->getComponent()->getAbstraction(), + TokenComponentAbstraction::ABSTRACTION_VIRTUAL + ); + Edge* memberEdge = node->getMemberEdge(); TS_ASSERT(memberEdge); TS_ASSERT_EQUALS(memberEdge->getType(), Edge::EDGE_MEMBER);