CallGraph.h revision f20288c91601dd3fbab6362a3400a0e6c472795f
1f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org//== CallGraph.cpp - Call graph building ------------------------*- C++ -*--==// 2f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// 3f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// The LLVM Compiler Infrastructure 4f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// 5f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// This file is distributed under the University of Illinois Open Source 6f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// License. See LICENSE.TXT for details. 7f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// 8f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org//===----------------------------------------------------------------------===// 9f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// 10f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// This file defined the CallGraph and CallGraphNode classes. 11f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org// 12f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org//===----------------------------------------------------------------------===// 13f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 14f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#ifndef LLVM_CLANG_ANALYSIS_CALLGRAPH 15f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#define LLVM_CLANG_ANALYSIS_CALLGRAPH 16f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 17f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include "clang/Index/ASTLocation.h" 18f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include "clang/Index/Entity.h" 19f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include "clang/Index/Program.h" 20f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include "llvm/ADT/DenseMap.h" 21f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include "llvm/ADT/GraphTraits.h" 22f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include "llvm/ADT/STLExtras.h" 23f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include <vector> 24f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org#include <map> 25f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 26f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.orgnamespace clang { 27f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 28f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.orgclass CallGraphNode { 29f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org idx::Entity F; 30f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef std::pair<idx::ASTLocation, CallGraphNode*> CallRecord; 31f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org std::vector<CallRecord> CalledFunctions; 32f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 33f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.orgpublic: 3483a60f3561a5a6d75f0044cf3161424d511f4066kwiberg@webrtc.org CallGraphNode(idx::Entity f) : F(f) {} 35f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 36f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef std::vector<CallRecord>::iterator iterator; 37f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef std::vector<CallRecord>::const_iterator const_iterator; 38f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 39f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org iterator begin() { return CalledFunctions.begin(); } 40f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org iterator end() { return CalledFunctions.end(); } 41f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org const_iterator begin() const { return CalledFunctions.begin(); } 42f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org const_iterator end() const { return CalledFunctions.end(); } 43f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 44f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org void addCallee(idx::ASTLocation L, CallGraphNode *Node) { 45f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org CalledFunctions.push_back(std::make_pair(L, Node)); 46f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org } 47f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 48f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org bool hasCallee() const { return begin() != end(); } 49f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 50f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org std::string getName() const { return F.getPrintableName(); } 51f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 52f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org Decl *getDecl(ASTContext &Ctx) const { return F.getDecl(Ctx); } 53f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org}; 54f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 55f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.orgclass CallGraph { 56f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org /// Program manages all Entities. 57f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org idx::Program Prog; 58f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 59f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef std::map<idx::Entity, CallGraphNode *> FunctionMapTy; 60f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 61f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org /// FunctionMap owns all CallGraphNodes. 62f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org FunctionMapTy FunctionMap; 63f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 64f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org /// CallerCtx maps a caller to its ASTContext. 65f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org llvm::DenseMap<CallGraphNode *, ASTContext *> CallerCtx; 66f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 67f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org /// Root node is the 'main' function or 0. 68f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org CallGraphNode *Root; 69f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 70f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org /// ExternalCallingNode has edges to all external functions. 71f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org CallGraphNode *ExternalCallingNode; 72f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 73f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.orgpublic: 74f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org CallGraph(); 75f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org ~CallGraph(); 76f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 77f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef FunctionMapTy::iterator iterator; 78f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef FunctionMapTy::const_iterator const_iterator; 79f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 80f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org iterator begin() { return FunctionMap.begin(); } 81f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org iterator end() { return FunctionMap.end(); } 82f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org const_iterator begin() const { return FunctionMap.begin(); } 83f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org const_iterator end() const { return FunctionMap.end(); } 84f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 85f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org CallGraphNode *getRoot() { return Root; } 86f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 87f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org CallGraphNode *getExternalCallingNode() { return ExternalCallingNode; } 88f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 89f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org void addTU(ASTContext &AST); 90f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 91f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org idx::Program &getProgram() { return Prog; } 92f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 93f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org CallGraphNode *getOrInsertFunction(idx::Entity F); 94f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 95f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org Decl *getDecl(CallGraphNode *Node); 96f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 97f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org void print(llvm::raw_ostream &os); 98f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org void dump(); 99f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 100f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org void ViewCallGraph() const; 101f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org}; 102f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 103f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org} // end clang namespace 104f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 105f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.orgnamespace llvm { 106f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 107f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.orgtemplate <> struct GraphTraits<clang::CallGraph> { 108f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef clang::CallGraph GraphType; 109f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef clang::CallGraphNode NodeType; 110f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org 111f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef std::pair<clang::idx::ASTLocation, NodeType*> CGNPairTy; 112f6e0404878530323f642d00b758b4d6105969c93turaj@webrtc.org typedef std::pointer_to_unary_function<CGNPairTy, NodeType*> CGNDerefFun; 113 114 typedef mapped_iterator<NodeType::iterator, CGNDerefFun> ChildIteratorType; 115 116 static NodeType *getEntryNode(GraphType *CG) { 117 return CG->getExternalCallingNode(); 118 } 119 120 static ChildIteratorType child_begin(NodeType *N) { 121 return map_iterator(N->begin(), CGNDerefFun(CGNDeref)); 122 } 123 static ChildIteratorType child_end(NodeType *N) { 124 return map_iterator(N->end(), CGNDerefFun(CGNDeref)); 125 } 126 127 typedef std::pair<clang::idx::Entity, NodeType*> PairTy; 128 typedef std::pointer_to_unary_function<PairTy, NodeType*> DerefFun; 129 130 typedef mapped_iterator<GraphType::const_iterator, DerefFun> nodes_iterator; 131 132 static nodes_iterator nodes_begin(const GraphType &CG) { 133 return map_iterator(CG.begin(), DerefFun(CGDeref)); 134 } 135 static nodes_iterator nodes_end(const GraphType &CG) { 136 return map_iterator(CG.end(), DerefFun(CGDeref)); 137 } 138 139 static NodeType *CGNDeref(CGNPairTy P) { return P.second; } 140 141 static NodeType *CGDeref(PairTy P) { return P.second; } 142}; 143 144} // end llvm namespace 145 146#endif 147