/*******************************************************************************
 * Copyright (c) 2001, 2005 IBM Corporation and others.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     IBM Corporation - initial API and implementation
 *******************************************************************************/
package org.eclipse.jem.internal.proxy.initParser;
/*
 *  $RCSfile: Static.java,v $
 *  $Revision: 1.4 $  $Date: 2005/08/24 20:39:07 $ 
 */


import java.io.*;
import java.lang.reflect.Array;
import java.util.*;

public class Static extends Expression {
	protected static final HashMap sPrimitiveTypes;
	
	static {
		sPrimitiveTypes = new HashMap(10);
		sPrimitiveTypes.put("byte", Byte.TYPE); //$NON-NLS-1$
		sPrimitiveTypes.put("char", Character.TYPE); //$NON-NLS-1$
		sPrimitiveTypes.put("short", Short.TYPE); //$NON-NLS-1$
		sPrimitiveTypes.put("int", Integer.TYPE); //$NON-NLS-1$
		sPrimitiveTypes.put("long", Long.TYPE); //$NON-NLS-1$
		sPrimitiveTypes.put("float", Float.TYPE);		 //$NON-NLS-1$
		sPrimitiveTypes.put("double", Double.TYPE); //$NON-NLS-1$
	}

	protected ArrayList arrayDimensions;
	protected List fArrayArguments;
	protected StringWriter typeWriter = new StringWriter();
	protected boolean completedWithPeriod = false;
	protected char[] completionToken;
	public Class type;
	protected boolean isComplete;

	public boolean isProcessingArrayDimension;
/**
 * Create an unknown expression
 */
public Static(ClassLoader aClassLoader){
	fClassLoader = aClassLoader;
}
public Static(char[] aToken,char delimiter,ClassLoader aClassLoader){
	
	fClassLoader = aClassLoader;
	try { 
		typeWriter.write(aToken);
	} catch ( IOException exc ) {};
	checkForValidType();
	if ( type == null && delimiter == DelimiterPeriod ){
		typeWriter.write(DelimiterPeriod);
	}
		
}
public Static(char[] aToken,char delimiter,ClassLoader aClassLoader,boolean isArray){
	this(aToken,delimiter,aClassLoader);
	isProcessingArrayDimension = true;
	arrayDimensions = new ArrayList(1);
	arrayDimensions.add(new Statement(aClassLoader));
}

public boolean isComplete(){
	return isComplete;
}
public boolean isArray(){
	return arrayDimensions != null;
}
/**
 * See whether or not we have a valid type
 * This uses the class loader given to us if one specified.  The reason for this
 * is that Eclipse uses a special plugin class loader and when we are running
 * in a VM inside eclipse ( e.g. for IDEVM proxy stuff ) we must have
 * reference to the plugin that is using us otherwise we can't load its classes
 */
protected void checkForValidType(){

	type = (Class) sPrimitiveTypes.get(typeWriter.toString());
	if (type == null)
		try {
			if ( fClassLoader == null ) {
				type = Class.forName(typeWriter.toString());
			} else {
				type = fClassLoader.loadClass(typeWriter.toString());
			}
		} catch ( ClassNotFoundException exc ) {
			try {
				type = Class.forName("java.lang." + typeWriter.toString()); //$NON-NLS-1$
				StringWriter writer = new StringWriter();
				writer.write(type.getName());
				typeWriter = writer;
			} catch ( ClassNotFoundException exc1 ) {}
		} catch ( NoClassDefFoundError exc ) {
			// A mismatch in some way. Found a class, probably different case. One possibility
			// is found a class, but this was really a package. So class and package with same name
			// but different case caused this to occur. [46376].
		}
	
}
/**
 * If we have any static methods return the result of evaluating them against the type
 */
public Object evaluate() {

	// If we are an array but haven't created it do so
	if ( isArray() ) {
		if ( array == null ) {
			evaluateArray();
		}
		return array;
	} else {
		if ( type != null ) { 
			return type;
		} else { 
			// If we have no type then we are some kind incomplete expression that cannot be evaluted
			throw new RuntimeException();
		}
	}
}
/**
 * The type of us is either simply the class, or if we are an array then we must create the java.lang.reflect.Array
 * using the reflective APIs
 */
protected Object array;
public Class getTypeClass() {

	if ( isArray() ) {
		if ( array == null ) {
			// Do not evaluate the array and return its class.  Instead just work out the class by our type
			// and number of dimensions
			Object result = Array.newInstance(type,getNumberOfDimensions());
			return result.getClass();
		} else { 
			return array.getClass();
		}
	} else { 
		return type;
	}
}

protected String getTypeClassName() {
	return typeWriter.toString();
}
public Class getPrimitiveTypeClass(){
	return type;
}
protected int[] getNumberOfDimensions(){
	List dimensions = new ArrayList(1);
	dimensions.add(new Integer(fArrayArguments.size()));
	((MessageArgument)fArrayArguments.get(0)).contributeArgumentNumber(dimensions);
	// The total number of arguments is a set of Integer objects in the dimensions list
	// convert this to an int[]
	int[] intDimensions = new int[dimensions.size()];
	for (int i = 0; i < dimensions.size(); i++) {
		intDimensions[i] = ((Integer)dimensions.get(i)).intValue();
	}
	return intDimensions;
}
/**
 * Evaluate the array
 */
protected void evaluateArray(){
	if ( fArrayArguments != null ) { 
		// If the array isn't declared with a size but this is supplied with argument these will be in the fArrayArguments
		// new int[] { 2 ,3 } will have the constructor arguments supplied as two message arguments with 
		if ( array == null ) {
			// The size of the array arguments is our array size, however for a multi arg array we need
			// to find the size of any nested arrays within arguments themselves, e.g. 
			// new int[][] { {2,3} , {3,4} } then we have two array arguments, each of which is a MessageArgument
			// whose statement is an ArrayArguments that has two arguments, etc...
			// To find the number of arguments we create a list that we add our number of arguments to, and then
			// pass this all the way up the arguments chain using contributeArgumentNumber(List) so that each element
			// can add to the list the number of arguments ( if any ) that they have.  
			array = Array.newInstance(type,getNumberOfDimensions());
			// Set the elements in the array to be the result of evaluating the constructor arguments
			for (int i = 0; i < fArrayArguments.size(); i++) {
				Expression expression = (Expression)fArrayArguments.get(i);
				try {	
					Object element = expression.evaluate();
					Array.set(array,i,element);
				} catch ( Exception exc ) {
					// Any evaluation exceptions should be thrown back
					throw new RuntimeException();
				}
			}
		}
	} else if ( arrayDimensions != null ) {
		// To get the class of a reflective array we must actually first create it and then ask it for its class
		// The array Dimensions are present if the array was explicitly declared with a size, e.g. new int[2][3]
		// will have to arrayDimensions that represent the expressions 2 and 3 ( as NumberLiteral instances )
		if ( array == null ) {
			// Evaluate all of the arrayDimensions.  These should be integers
			int[] dimensionSizes = new int[arrayDimensions.size()];
			for (int i = 0; i < dimensionSizes.length; i++) {
				try { 
					Integer dimensionSize = (Integer) ((Expression)arrayDimensions.get(i)).evaluate();
					dimensionSizes[i] = dimensionSize.intValue();
				} catch ( Exception exc ) {
					throw new RuntimeException();
				}
			}
			// For a multi arg array we need to create using the static method on array that takes an int[] that represents
			// the number of dimensions, e.g. for new String[2][3] we do Array.newInstance(String.class,new int[] { 2 , 3 };
			array = Array.newInstance(type,dimensionSizes);
		}
	}
}
/**
 * If the token is a period then it could either be part of the type or else a static method call
 */
public Expression push(char[] token , char delimiter ) {

	// If we don't yet have a valid type then see if we now do
	if (type == null){
		try { 
			typeWriter.write(token);
		} catch ( IOException exc ) {};
		checkForValidType();
		// If we got a valid type and a period then remember it
		if ( delimiter == DelimiterPeriod ) {
			if (type != null) {
				completedWithPeriod = true;
				return this;
			}
		}		
	}
	
	if ( arrayDimensions != null && isProcessingArrayDimension ) {
		Expression lastArrayDimension = (Expression)arrayDimensions.get(arrayDimensions.size()-1);
		lastArrayDimension.push(token,delimiter);
		if ( delimiter == DelimiterCloseSquareBrace && isProcessingArrayDimension ) {
			isProcessingArrayDimension = false;
		}
		return this;
	}
	
	if ( delimiter == DelimiterOpenSquareBrace && !isProcessingArrayDimension ) {
		if ( arrayDimensions == null ) arrayDimensions = new ArrayList(1);
		Statement statement = new Statement(fClassLoader);
		arrayDimensions.add(statement);
		isProcessingArrayDimension = true;
		return this;		
	}
	
	// If we have a type and the delimiter is a ( then it must be a message beginning
	if ( type != null ) {
		if (delimiter == DelimiterOpenParen) {
			isComplete = true;
			return new Message( this , token , fClassLoader );
		} else if (completedWithPeriod){
			isComplete = true;
			Field field = new Field(this,token,fClassLoader);
			// If our token is a ), ' ' or , then the field is completed,
			// otherwise leave it open so it will process the remaining tokens
//			if (delimiter == DelimiterCloseParen || delimiter == DelimiterSpace || delimiter == DelimiterComma) {
			if (delimiter == DelimiterCloseParen || delimiter == DelimiterComma) {
				field.isComplete = true;
			}
			return field;
		}
	}
			
	// We are still looking for a type so append a .
	if ( type == null ) {
		typeWriter.write('.');
	}
	return this;
}
public String toString(){

	StringWriter writer = new StringWriter();
	writer.write("Static "); //$NON-NLS-1$
	if ( type == null ) { 
		writer.write("(Incomplete) {"); //$NON-NLS-1$
	} else {
		writer.write("(Complete) {"); //$NON-NLS-1$
	}
	writer.write(typeWriter.toString());
	writer.write("}"); //$NON-NLS-1$
	if ( arrayDimensions != null ) {
		writer.write(" array dimensions="); //$NON-NLS-1$
		writer.write(new Integer(arrayDimensions.size()).toString());
	}
	if ( fArrayArguments != null ) {	
		writer.write(" array dimensions="); //$NON-NLS-1$
		writer.write(new Integer(fArrayArguments.size()).toString());
	}
	return writer.toString();

}

public boolean isPrimitive() {
	return getTypeClass().isPrimitive();
}
public void setArrayArguments(List arguments) {
	fArrayArguments = arguments;
}
}
