RecordElementReferenceValue.java

package edu.udel.cis.vsl.tass.dynamic.impl.value;

import edu.udel.cis.vsl.tass.dynamic.IF.type.RecordValueTypeIF;
import edu.udel.cis.vsl.tass.dynamic.IF.type.ReferenceValueTypeIF;
import edu.udel.cis.vsl.tass.dynamic.IF.value.RecordElementReferenceValueIF;
import edu.udel.cis.vsl.tass.dynamic.IF.value.ReferenceValueIF;
import edu.udel.cis.vsl.tass.dynamic.IF.value.VariableReferenceValueIF;
import edu.udel.cis.vsl.tass.dynamic.impl.type.ValueTypeFactory;
import edu.udel.cis.vsl.tass.morph.Morphic;

public class RecordElementReferenceValue extends ReferenceValue implements
		RecordElementReferenceValueIF {

	private static int classHashCode = RecordElementReferenceValue.class
			.hashCode();

	private int fieldIndex;

	private VariableReferenceValueIF variableReference;

	public RecordElementReferenceValue(ReferenceValueIF parent, int fieldIndex,
			ReferenceValueTypeIF valueType) {
		super(parent, valueType);
		this.fieldIndex = fieldIndex;
		variableReference = parent.variableReference();
	}

	@Override
	public int fieldIndex() {
		return fieldIndex;
	}

	@Override
	public String toString() {
		RecordValueTypeIF recordValueType = (RecordValueTypeIF) parent()
				.valueType().baseType();
		String fieldName = recordValueType.type().fieldName(fieldIndex);

		return parent() + "." + fieldName;
	}

	public String fieldName() {
		return ((RecordValueTypeIF) parent().valueType().baseType()).type()
				.fieldName(fieldIndex);
	}

	public String fullName() {
		String result;
		ReferenceValueIF parent = parent();

		if (parent instanceof RecordElementReferenceValue) {
			result = ((RecordElementReferenceValue) parent).fullName() + "_"
					+ fieldName();
		} else if (parent instanceof VariableReferenceValue) {
			result = ((VariableReferenceValue) parent).fullName() + "_"
					+ fieldName();
		} else {
			throw new RuntimeException("Object does not have full name:\n"
					+ this);
		}
		return result;
	}

	@Override
	public VariableReferenceValueIF variableReference() {
		return variableReference;
	}

	@Override
	protected boolean computeEquals(Morphic component) {
		if (!super.computeEquals(component))
			return false;
		if (component instanceof RecordElementReferenceValue) {
			RecordElementReferenceValue that = (RecordElementReferenceValue) component;

			return fieldIndex == that.fieldIndex;
		}
		return false;
	}

	@Override
	public boolean isNull() {
		return false;
	}

	@Override
	protected int computeHashCode() {
		return super.computeHashCode() + classHashCode + fieldIndex;
	}

	@Override
	protected void commitChildren() {
		super.commitChildren();
		variableReference.commit();
	}

	@Override
	protected void canonicalizeChildren(ValueFactory valueFactory,
			ValueTypeFactory typeFactory) {
		super.canonicalizeChildren(valueFactory, typeFactory);
		if (!variableReference.isCanonic())
			variableReference = parent().variableReference();
	}
}