Start line:  
End line:  

Snippet Preview

Snippet HTML Code

Stack Overflow Questions
  /* Soot - a J*va Optimization Framework
   * Copyright (C) 2008 Ben Bellamy 
   * 
   * All rights reserved.
   *
   * 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.typing.fast;
 
 import java.util.*;
 import soot.*;
 import soot.jimple.*;

Author(s):
Ben Bellamy
 
 public class AugEvalFunction implements IEvalFunction
 {
 	private JimpleBody jb;
 	
 	{
 		this. = jb;
 	}
 	
 	public Collection<Typeeval(Typing tgValue exprStmt stmt)
 	{
 		return new SingletonList<Type>(eval_(tgexprstmtthis.));
 	}
 
 	public static Type eval_(Typing tgValue exprStmt stmtJimpleBody jb)
 	{
 		
 		if ( expr instanceof ThisRef )
 			return ((ThisRef)expr).getType();
 		else if ( expr instanceof ParameterRef )
 			return ((ParameterRef)expr).getType();
 		else if ( expr instanceof Local ) {
 			Local ex = (Localexpr;
 			//changed to prevent null pointer exception in case of phantom classes where a null typing is encountered
 			//syed 
 			if (tg == nullreturn null
 			else return tg.get(ex);
 		}
 		else if ( expr instanceof BinopExpr )
 		{
 			BinopExpr be = (BinopExpr)expr;
 			
 			Value opl = be.getOp1(), opr = be.getOp2();
 			Type tl = eval_(tgoplstmtjb), tr = eval_(tgoprstmtjb);
 
 			if ( expr instanceof CmpExpr
 				|| expr instanceof CmpgExpr
 				|| expr instanceof CmplExpr )
 				return ByteType.v();
 			else if ( expr instanceof GeExpr
 				|| expr instanceof GtExpr
 				|| expr instanceof LeExpr
 				|| expr instanceof LtExpr
 				|| expr instanceof EqExpr
 				|| expr instanceof NeExpr )
 				return BooleanType.v();
 			else if ( expr instanceof ShlExpr )
 			{
 				if ( tl instanceof IntegerType )
 					return IntType.v();
 				else return tl;
 			}
 			else if ( expr instanceof ShrExpr
 				|| expr instanceof UshrExpr )
 				return tl;
 			else if ( expr instanceof AddExpr
 				|| expr instanceof SubExpr
 				|| expr instanceof MulExpr
 				|| expr instanceof DivExpr
 				|| expr instanceof RemExpr )
 			{
 				if ( tl instanceof IntegerType )
 					return IntType.v();
 				else return tl;
 			}
 			else if ( expr instanceof AndExpr
 				|| expr instanceof OrExpr
 				|| expr instanceof XorExpr )
 			{
 				if ( tl instanceof IntegerType && tr instanceof IntegerType )
				{
					if ( tl instanceof BooleanType )
					{
						if ( tr instanceof BooleanType )
							return BooleanType.v();
						else return tr;
					}
					else if ( tr instanceof BooleanType )
						return tl;
					else
					{
						Collection<Typers = AugHierarchy.lcas_(tltr);
						// AugHierarchy.lcas_ is single-valued
						for ( Type r : rs )
							return r;
						throw new RuntimeException();
					}
				}
				else return tl;
			}
			else throw new RuntimeException(
					"Unhandled binary expression: " + expr);
		}
		else if ( expr instanceof NegExpr )
		{
			Type t = eval_(tg, ((NegExpr)expr).getOp(), stmtjb);
			if ( t instanceof IntegerType )
			{
				/* Here I repeat the behaviour of the original type assigner,
				but is it right? For example, -128 is a byte, but -(-128) is
				not! --BRB */
				if ( t instanceof Integer1Type
					|| t instanceof BooleanType
					|| t instanceof Integer127Type
					|| t instanceof ByteType )
					return ByteType.v();
				else if ( t instanceof ShortType
					|| t instanceof Integer32767Type )
					return ShortType.v();
				else
					return IntType.v();
			}
			else
				return t;
		}
		else if ( expr instanceof CaughtExceptionRef )
		{
			RefType r = null;
			for ( Iterator i = TrapManager.getExceptionTypesOf(
				stmtjb).iterator(); i.hasNext(); )
			{
				RefType t = (RefType)i.next();
				if ( r == null )
					r = t;
				else
					/* In theory, we could have multiple exception types 
					pointing here. The JLS requires the exception parameter be a *subclass* of Throwable, so we do not need to worry about multiple inheritance. */
					r = BytecodeHierarchy.lcsc(rt);
			}
			if ( r == null )
				throw new RuntimeException(
					"Exception reference used other than as the first "
"statement of an exception handler.");
			return r;
		}
		else if ( expr instanceof ArrayRef )
		{
			Local av = (Local)((ArrayRef)expr).getBase();
			Type at = tg.get(av);
			if ( at instanceof ArrayType )
				return ((ArrayType)at).getElementType();
			else if ( at instanceof BottomType || at instanceof NullType )
				return BottomType.v();
			else throw new RuntimeException(
				"Base of array reference is not an array!");
		}
		else if ( expr instanceof NewArrayExpr )
		else if ( expr instanceof NewMultiArrayExpr )
			return ((NewMultiArrayExpr)expr).getBaseType();
		else if ( expr instanceof CastExpr )
			return ((CastExpr)expr).getCastType();
		else if ( expr instanceof InstanceOfExpr )
			return BooleanType.v();
		else if ( expr instanceof LengthExpr )
			return IntType.v();
		else if ( expr instanceof InvokeExpr )
			return ((InvokeExpr)expr).getMethodRef().returnType();
		else if ( expr instanceof NewExpr )
			return ((NewExpr)expr).getBaseType();
		else if ( expr instanceof FieldRef )
		    // RoboVM note: Fix for field resolution failures
                    try {
			return ((FieldRef)expr).getField().getType();
		    } catch (ResolutionFailedException e) {
		        return ((FieldRef)expr).getType();
		    }
		else if ( expr instanceof DoubleConstant )
			return DoubleType.v();
		else if ( expr instanceof FloatConstant )
			return FloatType.v();
		else if ( expr instanceof IntConstant )
		{
			int value = ((IntConstant)expr).;
			if ( value >= 0 && value < 2 )
				return Integer1Type.v();
			else if ( value >= 2 && value < 128 )
				return Integer127Type.v();
			else if ( value >= -128 && value < 0 )
				return ByteType.v();
			else if ( value >= 128 && value < 32768 )
				return Integer32767Type.v();
			else if ( value >= -32768 && value < -128 )
				return ShortType.v();
			else if ( value >= 32768 && value < 65536 )
				return CharType.v();
			else return IntType.v();
		}
		else if ( expr instanceof LongConstant )
			return LongType.v();
		else if ( expr instanceof NullConstant )
			return NullType.v();
		else if ( expr instanceof StringConstant )
			return RefType.v("java.lang.String");
		else if ( expr instanceof ClassConstant )
			return RefType.v("java.lang.Class");
		else throw new RuntimeException("Unhandled expression: " + expr);
	}
New to GrepCode? Check out our FAQ X