/* Soot - a J*va Optimization Framework * Copyright (C) 2003 Jerome Miecznikowski * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 59 Temple Place - Suite 330, * Boston, MA 02111-1307, USA. */ package soot.dava.toolkits.base.finders; import soot.*; import soot.dava.*; import soot.util.*; import java.util.*; import soot.jimple.*; import soot.dava.internal.asg.*; import soot.dava.internal.SET.*; public class IfFinder implements FactFinder { public IfFinder( Singletons.Global g ) {} public static IfFinder v() { return G.v().soot_dava_toolkits_base_finders_IfFinder(); } public void find( DavaBody body, AugmentedStmtGraph asg, SETNode SET) throws RetriggerAnalysisException { Dava.v().log( "IfFinder::find()"); Iterator asgit = asg.iterator(); while (asgit.hasNext()) { AugmentedStmt as = (AugmentedStmt) asgit.next(); Stmt s = as.get_Stmt(); if (s instanceof IfStmt) { IfStmt ifs = (IfStmt) s; if (body.get_ConsumedConditions().contains( as)) continue; body.consume_Condition( as); AugmentedStmt succIf = asg.get_AugStmt( ifs.getTarget()), succElse = (AugmentedStmt) as.bsuccs.get(0); if (succIf == succElse) succElse = (AugmentedStmt) as.bsuccs.get(1); asg.calculate_Reachability( succIf, succElse, as); asg.calculate_Reachability( succElse, succIf, as); IterableSet fullBody = new IterableSet(), ifBody = find_Body( succIf, succElse), elseBody = find_Body( succElse, succIf); fullBody.add( as); fullBody.addAll( ifBody); fullBody.addAll( elseBody); Iterator enlit = body.get_ExceptionFacts().iterator(); while (enlit.hasNext()) { ExceptionNode en = (ExceptionNode) enlit.next(); IterableSet tryBody = en.get_TryBody(); if (tryBody.contains( as)) { Iterator fbit = fullBody.snapshotIterator(); while (fbit.hasNext()) { AugmentedStmt fbas = (AugmentedStmt) fbit.next(); if (tryBody.contains( fbas) == false) { fullBody.remove( fbas); if (ifBody.contains( fbas)) ifBody.remove( fbas); if (elseBody.contains( fbas)) elseBody.remove( fbas); } } } } SET.nest( new SETIfElseNode( as, fullBody, ifBody, elseBody)); } } } private IterableSet find_Body( AugmentedStmt targetBranch, AugmentedStmt otherBranch) { IterableSet body = new IterableSet(); if (targetBranch.get_Reachers().contains( otherBranch)) return body; LinkedList<AugmentedStmt> worklist = new LinkedList<AugmentedStmt>(); worklist.addLast( targetBranch); while (worklist.isEmpty() == false) { AugmentedStmt as = worklist.removeFirst(); if (body.contains( as) == false) { body.add( as); Iterator sit = as.csuccs.iterator(); while (sit.hasNext()) { AugmentedStmt sas = (AugmentedStmt) sit.next(); if ((sas.get_Reachers().contains( otherBranch) == false) && (sas.get_Dominators().contains( targetBranch) == true)) worklist.addLast( sas); } } } return body; } }