//----------------------------BEGIN LICENSE----------------------------
/* 
 * Willow : the Open Source WorkFlow Project
 * Distributable under GNU LGPL license by gun.org
 *
 * Copyright (C) 2004-2010 huihoo.org 
 * Copyright (C) 2004-2010  ZosaTapo <dertyang@hotmail.com> 
 * 
 * ====================================================================
 * Project Homepage : http://www.huihoo.org/willow
 * Source Forge     : http://sourceforge.net/projects/huihoo
 * Mailing list     : willow@lists.sourceforge.net 
 */
//----------------------------END  LICENSE----------------------------
package org.huihoo.god4j.editor;

import org.apache.xerces.xni.parser.XMLComponent;
import org.huihoo.god4j.editor.elements.XPDLActualParameter;
import org.huihoo.god4j.editor.elements.XPDLDataField;
import org.huihoo.god4j.editor.elements.XPDLFormalParameter;
import org.huihoo.god4j.editor.elements.atoms.XPDLBasicType;
import org.huihoo.god4j.editor.elements.atoms.XPDLDataType;
import org.huihoo.god4j.editor.elements.set.XPDLActualParameters;
import org.huihoo.god4j.editor.elements.set.XPDLFormalParameters;

/**
 * @author liangce
 *
 * To change the template for this generated type comment go to
 * Window - Preferences - Java - Code Generation - Code and Comments
 */
public class XPDLUtils
{
	/**
		* Checks if formal and actual parameters are matched by number and by type.
		* @return 0 - if parameters are matched, 1 - if numbere of formal and
		* actual parameters is not the same, 2 - if types of parameters are not
		* matched
		*/
	public static int checkParameterMatching(XPDLFormalParameters fps, XPDLActualParameters aps)
	{
		if (fps == null || aps == null || fps.size() != aps.size())
		{
			return 1;
		}

		for (int i = 0; i < fps.size(); i++)
		{
			XPDLFormalParameter fp = (XPDLFormalParameter) fps.findComponent(i);
			XPDLActualParameter ap = (XPDLActualParameter) aps.findComponent(i);

			String fpMode = fp.get("Mode").getValue().toString();

			// if the formal parameter mode is IN, do not check validity because
			// that could be expression written in any scripting language
			if (fpMode.equals("IN"))
				continue;

			// find the type of formal param.
			XPDLDataType fpdt = (XPDLDataType) fp.get("DataType");
			XPDLComplexChoice fpdtt = (XPDLComplexChoice) fpdt.get("Type");
			XMLComponent fpType = (XMLComponent) fpdtt.getChoosen();

			// find the type of actual param.
			Object apWRD = ap.getValue();
			XMLComponent apType = null;
			if ((apWRD instanceof XPDLDataField) || (apWRD instanceof XPDLFormalParameter))
			{
				XPDLDataType apdt = (XPDLDataType) ((XPDLCollectionComponent) apWRD).get("DataType");
				XPDLComplexChoice apdtt = (XPDLComplexChoice) apdt.get("Type");
				apType = (XMLComponent) apdtt.getChoosen();
			}

			// if the actual parameter is an expression, and the mode is not
			// IN, return 2, which signals that parameter types don't match
			if (apType == null)
			{
				return 2;
			}

			if (fpType.getClass().equals(apType.getClass()))
			{
				// if this is BasicType check for subtype matching
				if (fpType instanceof XPDLBasicType)
				{
					XPDLAttribute fpAT = (XPDLAttribute) ((XPDLBasicType) fpType).get("Type");
					XPDLAttribute apAT = (XPDLAttribute) ((XPDLBasicType) apType).get("Type");
					if (!fpAT.getValue().toString().equals(apAT.getValue().toString()))
					{
						return 2;
					}
				}

			}
			else
			{
				return 2;
			}
		}
		return 0;
	}
}
