| 1 19 20 23 24 27 28 package soot.dava.toolkits.base.AST.transformations; 29 30 import soot.*; 31 import java.util.*; 32 import soot.jimple.*; 33 import soot.util.Chain; 34 import soot.dava.DavaBody; 36 import soot.dava.DecompilationException; 37 import soot.dava.internal.AST.*; 38 import soot.dava.internal.asg.*; 39 import soot.dava.toolkits.base.AST.analysis.*; 40 import soot.dava.toolkits.base.AST.traversals.*; 42 43 52 53 public class LocalVariableCleaner extends DepthFirstAdapter { 54 public final boolean DEBUG = false; 55 56 57 ASTNode AST; 58 59 ASTUsesAndDefs useDefs; 60 61 ASTParentNodeFinder parentOf; 62 63 public LocalVariableCleaner(ASTNode AST) { 64 super(); 65 this.AST = AST; 66 parentOf = new ASTParentNodeFinder(); 67 AST.apply(parentOf); 68 } 69 70 public LocalVariableCleaner(boolean verbose, ASTNode AST) { 71 super(verbose); 72 this.AST = AST; 73 parentOf = new ASTParentNodeFinder(); 74 AST.apply(parentOf); 75 } 76 77 83 public void outASTMethodNode(ASTMethodNode node) { 84 boolean redo = false; 85 86 useDefs = new ASTUsesAndDefs(AST); AST.apply(useDefs); 88 89 Iterator decIt = node.getDeclaredLocals().iterator(); 91 92 ArrayList removeList = new ArrayList(); 93 while (decIt.hasNext()) { 94 96 Local var = (Local) decIt.next(); 97 98 List defs = getDefs(var); 99 100 if (defs.size() == 0) { 102 removeList.add(var); 104 } else { 105 107 Iterator defIt = defs.iterator(); 109 110 while (defIt.hasNext()) { 111 DefinitionStmt ds = (DefinitionStmt) defIt.next(); 112 113 if (canRemoveDef(ds)) { 114 redo = removeStmt(ds); 118 } 119 } 121 } } 124 Iterator remIt = removeList.iterator(); 126 while (remIt.hasNext()) { 127 Local removeLocal = (Local) remIt.next(); 128 node.removeDeclaredLocal(removeLocal); 129 130 135 if(AST instanceof ASTMethodNode){ 137 DavaBody body = ((ASTMethodNode)AST).getDavaBody(); 139 if(DEBUG){ 140 System.out.println("body information"); 141 System.out.println("Control local is: "+body.get_ControlLocal()); 142 System.out.println("his locals are: "+body.get_ThisLocals()); 143 System.out.println("Param Map is: "+body.get_ParamMap()); 144 System.out.println("Locals are:"+body.getLocals()); 145 } 146 Chain localChain = body.getLocals(); 147 localChain.remove(removeLocal); 148 } 149 else 150 throw new DecompilationException("found AST which is not a methodNode"); 151 152 153 154 155 if(DEBUG) 156 System.out.println("Removed"+removeLocal); 157 redo = true; 158 } 159 160 if (redo) { 161 outASTMethodNode(node); 163 } 164 } 165 166 171 public boolean canRemoveDef(DefinitionStmt ds) { 172 List uses = useDefs.getDUChain(ds); 173 174 if (uses.size() != 0) 175 return false; 176 177 if (ds.getRightOp() instanceof Local 179 || ds.getRightOp() instanceof Constant) 180 return true; 181 182 return false; 183 } 184 185 188 public List getDefs(Local var) { 189 List toReturn = new ArrayList(); 190 191 HashMap dU = useDefs.getDUHashMap(); 192 Iterator it = dU.keySet().iterator(); 193 while (it.hasNext()) { 194 DefinitionStmt s = (DefinitionStmt) it.next(); 195 Value left = s.getLeftOp(); 196 if (left instanceof Local) { 197 if (((Local) left).getName().compareTo(var.getName()) == 0) 198 toReturn.add(s); 199 } 200 } 201 return toReturn; 202 } 203 204 public boolean removeStmt(Stmt stmt) { 205 Object tempParent = parentOf.getParentOf(stmt); 206 if (tempParent == null) { 207 return false; 209 } 210 211 ASTNode parent = (ASTNode) tempParent; 213 214 if (!(parent instanceof ASTStatementSequenceNode)) { 216 return false; 218 } 219 ASTStatementSequenceNode parentNode = (ASTStatementSequenceNode) parent; 220 221 ArrayList newSequence = new ArrayList(); 222 List stmts = parentNode.getStatements(); 223 int size = stmts.size(); 224 Iterator it = stmts.iterator(); 225 while (it.hasNext()) { 226 AugmentedStmt as = (AugmentedStmt) it.next(); 227 Stmt s = as.get_Stmt(); 228 if (s.toString().compareTo(stmt.toString()) != 0) { 229 newSequence.add(as); 231 } 232 } 233 parentNode.setStatements(newSequence); 235 if (newSequence.size() < size) 236 return true; 238 return false; } 240 241 } | Popular Tags |