Start line:  
End line:  

Snippet Preview

Snippet HTML Code

Stack Overflow Questions
  /* Soot - a J*va Optimization Framework
   * Copyright (C) 2003, 2004 Ondrej Lhotak
   *
   * 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.jimple.toolkits.pointer;
 import java.util.*;
 import soot.*;
 import soot.util.*;
 import soot.jimple.*;

A flow analysis that detects redundant cast checks.
 
     Map unitToKill = new HashMap();
     Map unitToGenFallThrough = new HashMap();
     Map unitToGenBranch = new HashMap();
 
     public CastCheckEliminator(BriefUnitGraph cfg) {
         super(cfg);
         makeInitialSet();
         doAnalysis();
         tagCasts();
     }

    
Put the results of the analysis into tags in cast statements.
 
     protected void tagCasts() {
         forIterator sIt = ((UnitGraph)).getBody().getUnits().iterator(); sIt.hasNext(); ) {
             final Stmt s = (StmtsIt.next();
             ifs instanceof AssignStmt ) {
                 AssignStmt as = (AssignStmts;
                 Value rhs = as.getRightOp();
                 ifrhs instanceof CastExpr ) {
                     CastExpr cast = (CastExprrhs;
                     Type t = cast.getCastType();
                     ift instanceof RefType ) {
                         ifcast.getOp() instanceof Local ) {
                             Local l = (Localcast.getOp(); 
                             LocalTypeSet set = (LocalTypeSet.get(s);
                             s.addTagnew CastCheckTagset.getset.indexOf(
                                     l, (RefTypet ) ) ) );
                         } else {
                             NullConstant nc = (NullConstantcast.getOp();
                             s.addTagnew CastCheckTagtrue ) );
                         }
                     }
                 }
             }
         }
     }

    
Find all the locals of reference type and all the types used in casts to initialize the mapping from locals and types to bits in the bit vector in LocalTypeSet.
 
     protected void makeInitialSet() {
         // Find all locals of reference type
         Chain locals = ((UnitGraph)).getBody().getLocals();
         List<LocalrefLocals = new ArrayList<Local>();
         forIterator lIt = locals.iterator(); lIt.hasNext(); ) {
             final Local l = (LocallIt.next();
             ifl.getType() instanceof RefType ) {
                 refLocals.addl );
             }
         }
 
         // Find types of all casts
         List<Typetypes = new ArrayList<Type>();
         forIterator sIt = ((UnitGraph)).getBody().getUnits().iterator(); sIt.hasNext(); ) {
             final Stmt s = (StmtsIt.next();
             ifs instanceof AssignStmt ) {
                 AssignStmt as = (AssignStmts;
                 Value rhs = as.getRightOp();
                 ifrhs instanceof CastExpr ) {
                     Type t = ( (CastExprrhs ).getCastType();
                     ift instanceof RefType && !types.containst ) ) {
                         types.addt );
                     }
                 }
             }
         }
         
          = new LocalTypeSetrefLocalstypes );
     }
    

    
Returns a new, aggressive (local,type) set.
    protected Object newInitialFlow() {
        LocalTypeSet ret = (LocalTypeSet.clone();
        ret.setAllBits();
        return ret;
    }

    
This is the flow function as described in the assignment write-up.
    protected void flowThroughObject inValueUnit unitList outFallValues,
                                List outBranchValues ) 
    {
        final LocalTypeSet in = (LocalTypeSetinValue;
        final LocalTypeSet out = (LocalTypeSetin.clone();
        LocalTypeSet outBranch = out// aliased to out unless unit is IfStmt
        final Stmt stmt = (Stmtunit;
        
        // First kill all locals defined in this statement
        forIterator bIt = stmt.getDefBoxes().iterator(); bIt.hasNext(); ) {
            final ValueBox b = (ValueBoxbIt.next();
            Value v = b.getValue();
            ifv instanceof Local && v.getType() instanceof RefType ) {
                out.killLocal( (Localv );
            }
        }
        
        // An AssignStmt may be a new, a simple copy, or a cast
        ifstmt instanceof AssignStmt ) {
            AssignStmt astmt = (AssignStmtstmt;
            Value rhs = astmt.getRightOp();
            Value lhs = astmt.getLeftOp();
            iflhs instanceof Local && rhs.getType() instanceof RefType ) {
                Local l = (Locallhs;
                ifrhs instanceof NewExpr ) {
                    out.localMustBeSubtypeOfl, (RefTyperhs.getType() );
                } else ifrhs instanceof CastExpr ) {
                    CastExpr cast = (CastExprrhs;
                    Type castType = cast.getCastType();
                    ifcastType instanceof RefType 
                    &&  cast.getOp() instanceof Local ) {
                        RefType refType = (RefTypecastType;
                        Local opLocal = (Localcast.getOp();
                        out.localCopylopLocal );
                        out.localMustBeSubtypeOflrefType );
                        out.localMustBeSubtypeOfopLocalrefType );
                    }
                } else ifrhs instanceof Local ) {
                    out.localCopyl, (Localrhs );
                }
            }
            
            // Handle if statements
        } else ifstmt instanceof IfStmt ) {
            IfStmt ifstmt = (IfStmtstmt;
            
            // This do ... while(false) is here so I can break out of it rather
            // than having to have seven nested if statements. Silly people who
            // took goto's out of the language... <grumble> <grumble>
            do {
                if.getPredsOfstmt ).size() != 1 ) break;
                Object predecessor = .getPredsOfstmt ).get(0);
                if( !( predecessor instanceof AssignStmt ) ) break;
                AssignStmt pred = (AssignStmtpredecessor;
                if( !(pred.getRightOp() instanceof InstanceOfExpr ) ) break;
                InstanceOfExpr iofexpr = (InstanceOfExprpred.getRightOp();
                if( !(iofexpr.getCheckType() instanceof RefType ) ) break;
                if( !(iofexpr.getOp() instanceof Local ) ) break;
                ConditionExpr c = (ConditionExprifstmt.getCondition();
                if( !c.getOp1().equalspred.getLeftOp() ) ) break;
                if( !( c.getOp2() instanceof IntConstant ) ) break;
                if( ( (IntConstantc.getOp2() ). != 0 ) break;
                ifc instanceof NeExpr ) {
                    // The IfStmt is like this:
                    // if x instanceof t goto somewhere_else
                    // So x is of type t on the taken branch
                    outBranch = (LocalTypeSetout.clone();
                    outBranch.localMustBeSubtypeOf( (Localiofexpr.getOp(),
                                                    (RefTypeiofexpr.getCheckType() );
                } else ifc instanceof EqExpr ) {
                    // The IfStmt is like this:
                    // if !(x instanceof t) goto somewhere_else
                    // So x is of type t on the fallthrough branch
                    outBranch = (LocalTypeSetout.clone();
                    out.localMustBeSubtypeOf( (Localiofexpr.getOp(),
                                              (RefTypeiofexpr.getCheckType() );
                }
            } whilefalse );
        }
        
        // Now copy the computed (local,type) set to all successors
        forIterator it = outFallValues.iterator(); it.hasNext(); ) {
            copyoutit.next() );
        }
        forIterator it = outBranchValues.iterator(); it.hasNext(); ) {
            copyoutBranchit.next() );
        }
    }
    protected void copyObject sourceObject dest ) {
        LocalTypeSet s = (LocalTypeSetsource;
        LocalTypeSet d = (LocalTypeSetdest;
        d.ands );
        d.ors );
    }
    // The merge operator is set intersection.
    protected void mergeObject in1Object in2Object out ) {
        LocalTypeSet o = (LocalTypeSetout;
        o.setAllBits();
        o.and( (LocalTypeSetin1 );
        o.and( (LocalTypeSetin2 );
    }
    
    
Returns a new, aggressive (local,type) set.
    protected Object entryInitialFlow() {
        LocalTypeSet ret = (LocalTypeSet.clone();
        return ret;
    }
New to GrepCode? Check out our FAQ X