ROSE 0.11.145.192
CallGraph.h
1
2#ifndef CALL_GRAPH_H
3#define CALL_GRAPH_H
4
5#include <GraphDotOutput.h>
6#include <VirtualGraphCreate.h>
7
8#include "AstDiagnostics.h"
9
10#include <sstream>
11#include <iostream>
12#include <string>
13#include <functional>
14#include <queue>
15#include <boost/foreach.hpp>
16#include <boost/unordered_map.hpp>
17
18#include "ClassHierarchyGraph.h"
19
20class FunctionData;
21
22// DQ (1/31/2006): Changed name and made global function type symbol table a static data member.
23// extern SgFunctionTypeTable Sgfunc_type_table;
24// This header has to be here since it uses type SgFunctionDeclarationPtrList
25
26//AS(090707) Added the CallTargetSet namespace to replace the CallGraphFunctionSolver class
27namespace CallTargetSet
28{
41 std::vector<SgFunctionDeclaration*> solveFunctionPointerCall ( SgPointerDerefExp *);
42
43 // returns the list of declarations of all functions that may get called via a member function pointer
44 std::vector<SgFunctionDeclaration*> solveMemberFunctionPointerCall ( SgExpression *,ClassHierarchyWrapper * );
45
60 Rose_STL_Container<SgFunctionDeclaration*> solveFunctionPointerCallsFunctional(SgNode* node, SgFunctionType* functionType );
61
62 // returns the list of declarations of all functions that may get called via a
63 // member function (non/polymorphic) call
64 std::vector<SgFunctionDeclaration*> solveMemberFunctionCall (
65 SgClassType *, ClassHierarchyWrapper *, SgMemberFunctionDeclaration *, bool , bool includePureVirtualFunc = false );
66
68 std::vector<SgFunctionDeclaration*> solveConstructorInitializer ( SgConstructorInitializer* sgCtorInit);
69
71 ROSE_DLL_API void getPropertiesForExpression(SgExpression* exp,
72 ClassHierarchyWrapper* classHierarchy,
73 Rose_STL_Container<SgFunctionDeclaration*>& propList,
74 bool includePureVirtualFunc = false);
75
80 void getDefinitionsForExpression(SgExpression* exp,
81 ClassHierarchyWrapper* classHierarchy,
82 Rose_STL_Container<SgFunctionDefinition*>& calleeList);
83
86 void getDeclarationsForExpression(SgExpression* exp,
87 ClassHierarchyWrapper* classHierarchy,
88 Rose_STL_Container<SgFunctionDeclaration*>& calleeList,
89 bool includePureVirtualFunc = false);
90
91 // Gets a vector of SgExpressions that are associated with the current SgFunctionDefinition.
92 // This functionality is necessary for virtual, interprocedural control flow graphs. However,
93 // it is costly and should be used infrequently (or optimized!).
94 void getExpressionsForDefinition(SgFunctionDefinition* targetDef,
95 ClassHierarchyWrapper* classHierarchy,
96 Rose_STL_Container<SgExpression*>& exps);
97
98 // Gets the latest implementation of the member function from the ancestor hierarchy
99 SgFunctionDeclaration * getFirstVirtualFunctionDefinitionFromAncestors(SgClassType *crtClass,
100 SgMemberFunctionDeclaration *memberFunctionDeclaration,
101 ClassHierarchyWrapper *classHierarchy);
102
103};
104
105class ROSE_DLL_API FunctionData
106{
107 public:
108
109 bool hasDefinition;
110
111 bool isDefined ();
112
113 FunctionData(SgFunctionDeclaration* functionDeclaration, SgProject *project, ClassHierarchyWrapper * );
114
116 Rose_STL_Container<SgFunctionDeclaration *> functionList;
117
118 SgFunctionDeclaration* functionDeclaration;
119
120 Rose_STL_Container<SgMemberFunctionDeclaration*> *findPointsToVirtualFunctions ( SgMemberFunctionDeclaration * );
121 bool compareFunctionDeclarations( SgFunctionDeclaration *f1, SgFunctionDeclaration *f2 );
122};
123
126{
127 using result_type = bool;
128 result_type operator() (SgFunctionDeclaration* node) const; // always return true
129};
130
132// Liao, 6/17/2012
133struct ROSE_DLL_API builtinFilter
134{
135 using result_type = bool;
136 result_type operator() (SgFunctionDeclaration* node) const;
137};
138
139class ROSE_DLL_API CallGraphBuilder
140{
141 public:
146 template<typename Predicate>
147 void buildCallGraph(Predicate pred);
150 //void classifyCallGraph();
151
152 //We map each function to the corresponding graph node
153 boost::unordered_map<SgFunctionDeclaration*, SgGraphNode*>& getGraphNodesMapping(){ return graphNodes; }
154
159
160 private:
161 SgProject *project;
163 //We map each function to the corresponding graph node
164 typedef boost::unordered_map<SgFunctionDeclaration*, SgGraphNode*> GraphNodes;
165 GraphNodes graphNodes;
166
167};
169//TODO this function is not defined? If so, need to be removed.
170// AstDOTGeneration::writeIncidenceGraphToDOTFile() is used instead in the tutorial. Liao 6/17/2012
171void GenerateDotGraph ( SgIncidenceDirectedGraph *graph, std::string fileName );
172
174{
175 using result_type = Rose_STL_Container<SgNode*>;
176 result_type operator()(SgNode* node);
177};
178
179template<typename Predicate>
180void
182{
183 // Adds additional constraints to the predicate. It makes no sense to analyze non-instantiated templates.
184 struct isSelected {
185 Predicate &pred;
186 isSelected(Predicate &pred): pred(pred) {}
187 bool operator()(SgNode *node) {
188 SgFunctionDeclaration *f = isSgFunctionDeclaration(node);
189 // TV (10/26/2018): FIXME ROSE-1487
190 // assert(!f || f==f->get_firstNondefiningDeclaration()); // node uniqueness test
191#if 0
192 // DQ (8/25/2016): This is not a meaningful test since all functions will be in the memory pool, including template functions and template member functions.
193 if(isSgTemplateFunctionDeclaration(f)||isSgTemplateMemberFunctionDeclaration(f)) {
194 std::cerr<<"Error: CallGraphBuilder: call referring to node "<<f->class_name()<<" :: function-name:"<<f->get_qualified_name()<<std::endl;
195 }
196#endif
197 return f && f==f->get_firstNondefiningDeclaration() && !isSgTemplateMemberFunctionDeclaration(f) && !isSgTemplateFunctionDeclaration(f) && pred(f);
198 }
199 };
200
201 // Add nodes to the graph by querying the memory pool for function declarations, mapping them to unique declarations
202 // that can be used as keys in a map (using get_firstNondefiningDeclaration()), and filtering according to the predicate.
203 graph = new SgIncidenceDirectedGraph();
204 std::vector<FunctionData> callGraphData;
205 ClassHierarchyWrapper classHierarchy(project);
206 graphNodes.clear();
207 VariantVector vv(V_SgFunctionDeclaration);
209 std::vector<SgNode*> fdecl_nodes = NodeQuery::queryMemoryPool(defFunc, &vv);
210 BOOST_FOREACH(SgNode *node, fdecl_nodes) {
211 SgFunctionDeclaration *fdecl = isSgFunctionDeclaration(node);
212 SgFunctionDeclaration *unique = isSgFunctionDeclaration(fdecl->get_firstNondefiningDeclaration());
213#if 0 //debug
214 printf ("In buildCallGraph(): loop over functions from memory pool: fdecl = %p = %s name = %s \n",fdecl,fdecl->class_name().c_str(),fdecl->get_name().str());
215 printf ("In buildCallGraph(): loop over functions from memory pool: unique = %p = %s name = %s \n",unique,unique->class_name().c_str(),unique->get_name().str());
216#endif
217 if (isSelected(pred)(unique) && hasGraphNodeFor(unique) == NULL)
218 {
219#if 0 //debug
220 printf ("Collect function calls in unique function: unique = %p \n",unique);
221#endif
222 FunctionData fdata(unique, project, &classHierarchy); // computes functions called by unique
223 callGraphData.push_back(fdata);
224 std::string functionName = unique->get_qualified_name().getString();
225 SgGraphNode *graphNode = new SgGraphNode(functionName);
226 graphNode->set_SgNode(unique);
227 graphNodes[unique] = graphNode;
228 graph->addNode(graphNode);
229 printf("Added function %s %p\n", functionName.c_str(), unique);
230 }
231 else
232 {
233#if 0 //debug
234 printf ("Function not selected for processing: unique = %p \n",unique);
235 printf (" --- isSelected(pred)(unique) = %s \n",isSelected(pred)(unique) ? "true" : "false");
236 printf (" --- graphNodes.find(unique)==graphNodes.end() = %s \n",graphNodes.find(unique)==graphNodes.end() ? "true" : "false");
237#endif
238 }
239 }
240
241 // Add edges to the graph
242 BOOST_FOREACH(FunctionData &currentFunction, callGraphData) {
243 SgFunctionDeclaration* curFuncDecl = currentFunction.functionDeclaration;
244 std::string curFuncName = curFuncDecl->get_qualified_name().getString();
245 SgGraphNode * srcNode = hasGraphNodeFor(currentFunction.functionDeclaration);
246 ROSE_ASSERT(srcNode != NULL);
247 std::vector<SgFunctionDeclaration*> & callees = currentFunction.functionList;
248 BOOST_FOREACH(SgFunctionDeclaration * callee, callees) {
249 if (isSelected(pred)(callee)) {
250 SgGraphNode * dstNode = getGraphNodeFor(callee); //getGraphNode here, see function comment
251 ROSE_ASSERT(dstNode != NULL);
252 if (graph->checkIfDirectedGraphEdgeExists(srcNode, dstNode) == false)
253 graph->addDirectedEdge(srcNode, dstNode);
254 }
255 }
256 }
257}
258
259// endif for CALL_GRAPH_H
260#endif
261
SgIncidenceDirectedGraph * getGraph()
Grab the call graph built.
SgGraphNode * hasGraphNodeFor(SgFunctionDeclaration *fdecl) const
Retrieve the node matching a function declaration using firstNondefiningDeclaration (does not work ac...
void buildCallGraph()
Default builder filtering nothing in the call graph.
SgGraphNode * getGraphNodeFor(SgFunctionDeclaration *fdecl) const
Retrieve the node matching a function declaration (using mangled name to resolve across translation u...
Rose_STL_Container< SgFunctionDeclaration * > functionList
All the callees of this function.
Definition CallGraph.h:116
This class represents the call of a class constructor to initialize a variable. For example "Foo foo;...
SgDeclarationStatement * get_firstNondefiningDeclaration() const
This is an access function for the SgDeclarationStatement::p_firstNondefiningDeclaration data member ...
This class represents the notion of an expression. Expressions are derived from SgLocatedNodes,...
This class represents the concept of a function declaration statement.
virtual std::string class_name() const override
returns a string representing the class name
This class represents the concept of a scope in C++ (e.g. global scope, fuction scope,...
This class represents a type for all functions.
SgGraphNode * addNode(const std::string &name="", SgNode *sg_node=NULL)
Support for adding SgGraphNode to SgGraph.
SgDirectedGraphEdge * addDirectedEdge(SgGraphNode *a, SgGraphNode *b, const std::string &name="")
Support for adding SgGraphEdge to SgGraph.
This class represents the concept of a member function declaration statement.
This class represents the base class for all IR nodes within Sage III.
This class represents a source project, with a list of SgFile objects and global information about th...
A function object to filter out builtin functions in a call graph (only non-builtin functions will be...
Definition CallGraph.h:134
A function object to be used as a predicate to filter out functions in a call graph: it does not filt...
Definition CallGraph.h:126