From 96cae19233de5deee9a593113d4acea17cbb8afd Mon Sep 17 00:00:00 2001 From: bdemsky Date: Fri, 19 May 2006 21:34:46 +0000 Subject: [PATCH] Wrote callgraph. Working on flag analysis. --- Robust/src/Analysis/CallGraph/CallGraph.java | 105 +++++++++++++++++++ Robust/src/Analysis/Flag/FlagAnalysis.java | 16 +++ Robust/src/Analysis/Flag/FlagState.java | 37 +++++++ Robust/src/IR/Tree/SemanticCheck.java | 12 +++ Robust/src/Makefile | 5 +- 5 files changed, 173 insertions(+), 2 deletions(-) create mode 100644 Robust/src/Analysis/CallGraph/CallGraph.java create mode 100644 Robust/src/Analysis/Flag/FlagAnalysis.java create mode 100644 Robust/src/Analysis/Flag/FlagState.java diff --git a/Robust/src/Analysis/CallGraph/CallGraph.java b/Robust/src/Analysis/CallGraph/CallGraph.java new file mode 100644 index 00000000..2b08617f --- /dev/null +++ b/Robust/src/Analysis/CallGraph/CallGraph.java @@ -0,0 +1,105 @@ +package Analysis.CallGraph; +import IR.State; +import IR.Flat.FlatMethod; +import IR.Flat.FlatNode; +import IR.Flat.FlatCall; +import IR.Flat.FKind; +import java.util.*; +import IR.ClassDescriptor; +import IR.MethodDescriptor; + +public class CallGraph { + State state; + Hashtable methods; + Hashtable methodmap; + + public CallGraph(State state) { + this.state=state; + methods=new Hashtable(); + methodmap=new Hashtable(); + buildMethodTable(); + buildGraph(); + } + + private void buildMethodTable() { + //Iterator through classes + Iterator it=state.getClassSymbolTable().getDescriptorsIterator(); + while(it.hasNext()) { + ClassDescriptor cn=(ClassDescriptor)it.next(); + Iterator methodit=cn.getMethods(); + //Iterator through methods + while(methodit.hasNext()) { + MethodDescriptor md=(MethodDescriptor)methodit.next(); + if (md.isStatic()||md.getReturnType()==null) + continue; + ClassDescriptor superdesc=cn.getSuperDesc(); + if (superdesc!=null) { + Set possiblematches=superdesc.getMethodTable().getSet(md.getSymbol()); + boolean foundmatch=false; + for(Iterator matchit=possiblematches.iterator();matchit.hasNext();) { + MethodDescriptor matchmd=(MethodDescriptor)matchit.next(); + if (md.matches(matchmd)) { + if (!methods.containsKey(matchmd)) + methods.put(matchmd,new HashSet()); + ((HashSet)methods.get(matchmd)).add(md); + break; + } + } + } + } + } + } + + /** Given a call to MethodDescriptor, lists the methods which + could actually be called due to virtual dispatch. */ + public Set getMethods(MethodDescriptor md) { + HashSet ns=new HashSet(); + ns.add(md); + Set s=(Set)methods.get(md); + if (s!=null) + for(Iterator it=s.iterator();it.hasNext();) { + MethodDescriptor md2=(MethodDescriptor)it.next(); + ns.addAll(getMethods(md2)); + } + return ns; + } + + private void buildGraph() { + Iterator it=state.getClassSymbolTable().getDescriptorsIterator(); + while(it.hasNext()) { + ClassDescriptor cn=(ClassDescriptor)it.next(); + Iterator methodit=cn.getMethods(); + //Iterator through methods + while(methodit.hasNext()) { + MethodDescriptor md=(MethodDescriptor)methodit.next(); + analyzeMethod(md); + } + } + } + + private void analyzeMethod(MethodDescriptor md) { + FlatMethod fm=state.getMethodFlat(md); + HashSet toexplore=new HashSet(); + toexplore.add(fm); + HashSet explored=new HashSet(); + //look at all the nodes in the flat representation + while(!toexplore.isEmpty()) { + FlatNode fn=(FlatNode)(toexplore.iterator()).next(); + toexplore.remove(fn); + explored.add(fn); + for(int i=0;i