public int compare(Loop loop1, Loop loop2) { Collection<Stmt> stmts1 = loop1.getLoopStatements(); Collection<Stmt> stmts2 = loop2.getLoopStatements(); if(stmts1.equals(stmts2)) { assert loop1.getHead().equals(loop2.getHead()); //should really have the same head then //equal (same) loops return 0; } else if(stmts1.containsAll(stmts2)) { //1 superset of 2 return 1; } else if(stmts2.containsAll(stmts1)) { //1 subset of 2 return -1; } //overlap (?) or disjoint: order does not matter; //however we must *not* return 0 as this would only keep one of the two loops; //hence, return 1 return 1; }
private static Collection<Loop> computeLoops(Body b) { LoopFinder loopFinder = new LoopFinder(); loopFinder.transform(b); Collection<Loop> loops = loopFinder.loops(); return loops; }
public boolean hasNestedLoops() { //TODO could be speeded up by just comparing two consecutive //loops returned by the iterator LoopNestTreeComparator comp = new LoopNestTreeComparator(); for (Loop loop1 : this) { for (Loop loop2 : this) { if(comp.compare(loop1, loop2)!=0) { return true; } } } return false; }
/** * Builds a loop nest tree from a mapping from loop headers to statements in the loop. */ public LoopNestTree(Collection<Loop> loops) { super(new LoopNestTreeComparator()); addAll(loops); }
@Override protected void internalTransform(Body methodBody, String phaseName, Map<String, String> options) { // Find loop statements in this method body Set<Stmt> loopEntryStmts = new HashSet<Stmt>(); Set<Stmt> loopExitStmts = new HashSet<Stmt>(); LoopNestTree loopNestTree = new LoopNestTree(methodBody); for (Loop loop : loopNestTree) { loopEntryStmts.add(loop.getHead()); loopExitStmts.addAll(loop.targetsOfLoopExit((Stmt)(loop.getLoopExits().toArray()[0]))); } Iterator<Unit> unitIterator = methodBody.getUnits().snapshotIterator(); while(unitIterator.hasNext()) { // Read each program statement as Jimple Stmt sootStmt = (Stmt)unitIterator.next(); // If the current statement exits a loop, mark it if((loopLevel > 0) && loopExitStmts.contains(sootStmt)) { loopLevel--; } // If the current statement enters a loop, mark it if(loopEntryStmts.contains(sootStmt)) { loopLevel++; } checkAccessStmt(sootStmt, methodBody.getMethod()); checkSynchronizationStmt(sootStmt); // If a new thread variable has been created, save the variable and wait for it's .start() method checkThreadCreationStmt(sootStmt); // Check if thread.start() was called. If so, save the type Value startedRunnable = null; if ((startedRunnable = checkThreadStartStmt(sootStmt)) != null) { // .start() was called on this Runnable. Save it. Type runnableType = innerRunnable.get(startedRunnable); if(runnableType != null) { startedRunnables.add(new ThreadProperties(startedRunnable, runnableType, sootStmt, (loopLevel > 0))); //System.out.println("Saving runnable value "+startedRunnable+" at "+sootStmt); } } } }