/*
* Copyright (c) 2005 Thomas Weise
*
* E-Mail : tweise@gmx.de
* Creation Date : 2005-11-28 06:09:33
* Original Filename: org.dgpf.automaton.expressions.Read.java
* Version : 2.2.1
* Last modification: 2006-05-08
* by: Thomas Weise
*
* License : GNU LESSER GENERAL PUBLIC LICENSE
* Version 2.1, February 1999
* You should have received a copy of this license along
* with this library; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston,
* MA 02111-1307, USA or download the license under
* http://www.gnu.org/copyleft/lesser.html.
*
* Warranty : This software is provided "as is" 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.
*/
package org.dgpf.gp.automaton.expressions;
import org.dgpf.gp.automaton.base.Automaton;
import org.dgpf.gp.automaton.base.Expression;
import org.dgpf.gp.automaton.search.ExpressionHandler;
/**
* The memory read access class.
*
* @author Thomas Weise
*/
public final class Read extends Expression
{
/**
* The serial version uid.
*/
private static final long serialVersionUID = 1;
/**
* The memory address to read from.
*/
private final int m_address ;
/**
* true
if the read should be indirect.
*/
private final boolean m_indirect ;
/**
* The count of predefined read instructions.
*/
private static final int RADIANT = 10;
/**
* The direct reads.
*/
private static final Read[] READ_DIR ;
/**
* The indirect reads.
*/
private static final Read[] READ_INDIR ;
static
{
int l_l;
READ_DIR = new Read[RADIANT+1];
READ_INDIR = new Read[RADIANT+1];
for(l_l = 0; l_l <= RADIANT; l_l++)
{
READ_DIR[l_l] = new Read(l_l, false);
READ_INDIR[l_l] = new Read(l_l, true);
}
}
/**
* The handler used by this class.
*/
public static final ExpressionHandler HANDLER =
ReadHandler.INSTANCE;
/**
* Create a new read expression.
* @param p_address The target address to read to.
* @param p_indirect true
if the read should be indirect.
*/
private Read(final int p_address,
final boolean p_indirect)
{
super(1);
this.m_address = p_address;
this.m_indirect = p_indirect;
}
/**
* Obtain the address which is used by this operation to read from.
* @return The address to read (directly or indirectly) from.
*/
public final int get_address ()
{
return this.m_address;
}
/**
* Returns true
if this operation is a indirect memory access.
* @return true
if and only if this operation represents an
* indirect memory access.
*/
public final boolean is_indirect ()
{
return this.m_indirect;
}
/**
* Create a new read expression.
* @param p_address The target address to read to.
* @param p_indirect true
if the read should be indirect.
* @return The new read expression.
*/
public static final Read create_read(final int p_address,
final boolean p_indirect)
{
if(p_address <= RADIANT)
{
return p_indirect ? READ_INDIR[p_address] : READ_DIR[p_address];
}
return new Read(p_address, p_indirect);
}
/**
* Obtain the count of memory cells this item needs.
* @return The count of memory cells this item needs.
*/
@Override
public final int get_memory_size ()
{
return (this.m_address+1);
}
/**
* This method is called when the construct is executed. It performs the
* work of the construct.
* @param p_automate The automate it is invoked on.
* @return The return value of the construct.
*/
@Override
public final int execute (final Automaton p_automate)
{
if(this.m_indirect)
{
return p_automate.read_rel(this.m_address);
}
return p_automate.read(this.m_address);
}
/**
* Store this objects content into a string builder.
* @param p_sb The string builder to store stuff into.
*/
@Override
public final void to_string (final StringBuilder p_sb)
{
boolean l_b;
l_b = this.m_indirect;
p_sb.append("mem[");
if(l_b) p_sb.append('[');
p_sb.append(this.m_address);
if(l_b) p_sb.append(']');
p_sb.append(']');
}
/**
* Checks wether this object is equal to another object.
* @param p_object The object to compare with.
* @return true
if and only if the two objects are exactly
* equal.
*/
@Override
public final boolean equals (final Object p_object)
{
Read l_be;
if(p_object == this) return true;
if(p_object instanceof Read)
{
l_be = ((Read)p_object);
if(l_be.m_address == this.m_address)
{
return (l_be.m_indirect == this.m_indirect);
}
}
return false;
}
/**
* Returns the genetic handler of the code construct.
* @return The genetic handler of the code construct.
*/
@Override
public final ExpressionHandler get_handler ()
{
return HANDLER;
}
}