1 19 20 25 26 27 28 29 30 31 package soot.jimple.toolkits.base; 32 import soot.options.*; 33 34 import soot.*; 35 import soot.toolkits.scalar.*; 36 import soot.jimple.*; 37 import soot.toolkits.graph.*; 38 import soot.grimp.*; 39 import soot.util.*; 40 import java.util.*; 41 import soot.tagkit.*; 42 43 public class JimpleConstructorFolder extends BodyTransformer 44 { 45 48 50 public void internalTransform(Body b, String phaseName, Map options) 51 { 52 JimpleBody body = (JimpleBody)b; 53 54 if(Options.v().verbose()) 55 G.v().out.println("[" + body.getMethod().getName() + 56 "] Folding Jimple constructors..."); 57 58 Chain units = body.getUnits(); 59 List stmtList = new ArrayList(); 60 stmtList.addAll(units); 61 62 Iterator it = stmtList.iterator(); 63 Iterator nextStmtIt = stmtList.iterator(); 64 nextStmtIt.next(); 66 67 ExceptionalUnitGraph graph = new ExceptionalUnitGraph(body); 68 69 LocalDefs localDefs = new SmartLocalDefs( graph, new SimpleLiveLocals(graph)); 70 LocalUses localUses = new SimpleLocalUses(graph, localDefs); 71 72 73 while (it.hasNext()) 74 { 75 Stmt s = (Stmt)it.next(); 76 77 if (!(s instanceof AssignStmt)) 78 continue; 79 80 81 Value lhs = ((AssignStmt)s).getLeftOp(); 83 if (!(lhs instanceof Local)) 84 continue; 85 86 Value rhs = ((AssignStmt)s).getRightOp(); 87 if (!(rhs instanceof NewExpr)) 88 continue; 89 90 91 if (nextStmtIt.hasNext()){ 95 Stmt next = (Stmt)nextStmtIt.next(); 96 if (next instanceof InvokeStmt){ 97 InvokeStmt invoke = (InvokeStmt)next; 98 99 if (invoke.getInvokeExpr() instanceof SpecialInvokeExpr && 100 invoke.getInvokeExpr().getMethodRef().name().equals(SootMethod.constructorName)) { 101 SpecialInvokeExpr invokeExpr = (SpecialInvokeExpr)invoke.getInvokeExpr(); 102 if (invokeExpr.getBase() == lhs){ 103 continue; 104 } 105 } 106 } 107 } 108 109 List lu = localUses.getUsesOf((DefinitionStmt)s); 110 Iterator luIter = lu.iterator(); 111 boolean MadeNewInvokeExpr = false; 112 113 while (luIter.hasNext()) 114 { 115 Unit use = ((UnitValueBoxPair)(luIter.next())).unit; 116 if (!(use instanceof InvokeStmt)) 117 continue; 118 InvokeStmt is = (InvokeStmt)use; 119 if (!(is.getInvokeExpr() instanceof SpecialInvokeExpr) || 120 !(is.getInvokeExpr().getMethodRef().name().equals(SootMethod.constructorName)) || 121 lhs != ((SpecialInvokeExpr)is.getInvokeExpr()).getBase()) 122 continue; 123 124 AssignStmt constructStmt = Jimple.v().newAssignStmt 126 (((DefinitionStmt)s).getLeftOp(), ((DefinitionStmt)s).getRightOp()); 127 constructStmt.setRightOp 128 (Jimple.v().newNewExpr 129 (((NewExpr)rhs).getBaseType())); 130 MadeNewInvokeExpr = true; 131 132 use.redirectJumpsToThisTo(constructStmt); 134 units.insertBefore(constructStmt, use); 136 if (s.hasTag("SourceLnPosTag")){ 137 constructStmt.addTag((SourceLnPosTag)s.getTag("SourceLnPosTag")); 138 } 139 } 140 if (MadeNewInvokeExpr) 141 { 142 units.remove(s); 143 } 144 } 145 } 146 } 147 | Popular Tags |