/*
* Copyright 2013 Guidewire Software, Inc.
*/
package gw.internal.gosu.parser.expressions;
import gw.config.CommonServices;
import gw.lang.parser.expressions.IBitshiftExpression;
import gw.lang.reflect.IType;
import gw.lang.reflect.java.JavaTypes;
/**
* Represents a bitshift expression in the Gosu grammar:
* <pre>
* <i>bitshift-expression</i>
* <additive-expression>
* <bitshift-expression> <b><<</b> <additive-expression>
* <bitsfhit-expression> <b>>></b> <additive-expression>
* <bitshift-expression> <b>>>></b> <additive-expression>
* </pre>
* <p/>
*
* @see gw.lang.parser.IGosuParser
*/
public final class BitshiftExpression extends ArithmeticExpression implements IBitshiftExpression
{
/**
* Evaluate the expression.
*/
public Object evaluate()
{
if( !isCompileTimeConstant() )
{
return super.evaluate();
}
Object lhsValue = getLHS().evaluate();
if( lhsValue == null )
{
return null;
}
Object rhsValue = getRHS().evaluate();
if( rhsValue == null )
{
return null;
}
IType type = getType();
if( getOperator().equals( "<<" ) )
{
if( type == JavaTypes.pINT() )
{
return CommonServices.getCoercionManager().makeIntegerFrom( lhsValue ) << CommonServices.getCoercionManager().makeIntegerFrom( rhsValue );
}
if( type == JavaTypes.pLONG() )
{
return makeLong( CommonServices.getCoercionManager().makeLongFrom( lhsValue ) << CommonServices.getCoercionManager().makeIntegerFrom( rhsValue ) );
}
throw new UnsupportedNumberTypeException(type);
}
if( getOperator().equals( ">>" ) )
{
if( type == JavaTypes.pINT() )
{
return CommonServices.getCoercionManager().makeIntegerFrom( lhsValue ) >> CommonServices.getCoercionManager().makeIntegerFrom( rhsValue );
}
if( type == JavaTypes.pLONG() )
{
return makeLong( CommonServices.getCoercionManager().makeLongFrom( lhsValue ) >> CommonServices.getCoercionManager().makeIntegerFrom( rhsValue ) );
}
throw new UnsupportedNumberTypeException(type);
}
if( getOperator().equals( ">>>" ) )
{
if( type == JavaTypes.pINT() )
{
return CommonServices.getCoercionManager().makeIntegerFrom( lhsValue ) >>> CommonServices.getCoercionManager().makeIntegerFrom( rhsValue );
}
if( type == JavaTypes.pLONG() )
{
return makeLong( CommonServices.getCoercionManager().makeLongFrom( lhsValue ) >>> CommonServices.getCoercionManager().makeIntegerFrom( rhsValue ) );
}
throw new UnsupportedNumberTypeException(type);
}
throw new UnsupportedNumberTypeException(type);
}
}