소스 검색

Round built-in function and round block added.

au@andreasunger.net 14 년 전
부모
커밋
74a7b4c9b3
20개의 변경된 파일357개의 추가작업 그리고 38개의 파일을 삭제
  1. 5 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/BuiltinFunctionGeneratorLookupTable.java
  2. 1 1
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/IFunctionGenerator.java
  3. 97 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/internal/RoundFunctionGenerator.java
  4. 7 2
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/SumFunctionGenerator.java
  5. 5 1
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/internal/util/CastToFixedPointHelper.java
  6. 59 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/internal/util/Caster.java
  7. 13 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.computation.engine/src/org/eclipselabs/mscript/computation/engine/value/Binary64Value.java
  8. 30 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.computation.engine/src/org/eclipselabs/mscript/computation/engine/value/FixedPointValue.java
  9. 2 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.computation.engine/src/org/eclipselabs/mscript/computation/engine/value/ISimpleNumericValue.java
  10. 4 23
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/il/builtin/BuiltinFunctionDescriptor.java
  11. 1 1
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/il/builtin/ISignature.java
  12. 1 1
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/il/builtin/Signature.java
  13. 51 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/internal/il/builtin/RoundSignature.java
  14. 30 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/internal/il/builtin/UnitSignature.java
  15. 1 1
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/ExpressionValueEvaluator.java
  16. 2 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/BuiltinFunctionLookupTable.java
  17. 1 1
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/IFunction.java
  18. 36 0
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/RoundFunction.java
  19. 7 4
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/SumFunction.java
  20. 4 3
      org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/UnitFunction.java

+ 5 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/BuiltinFunctionGeneratorLookupTable.java

@@ -11,6 +11,7 @@
 
 package org.eclipselabs.mscript.codegen.c;
 
+import org.eclipselabs.mscript.codegen.c.internal.RoundFunctionGenerator;
 import org.eclipselabs.mscript.language.il.builtin.BuiltinFunctionDescriptor;
 
 /**
@@ -23,6 +24,10 @@ public class BuiltinFunctionGeneratorLookupTable implements IBuiltinFunctionGene
 	 * @see org.eclipselabs.mscript.codegen.c.IBuiltinFunctionGeneratorLookupTable#getFunctionGenerator(org.eclipselabs.mscript.language.il.builtin.BuiltinFunctionDescriptor)
 	 */
 	public IFunctionGenerator getFunctionGenerator(BuiltinFunctionDescriptor builtinFunctionDescriptor) {
+		switch (builtinFunctionDescriptor) {
+		case ROUND:
+			return new RoundFunctionGenerator();
+		}
 		return null;
 	}
 	

+ 1 - 1
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/IFunctionGenerator.java

@@ -21,6 +21,6 @@ import org.eclipselabs.mscript.language.ast.Expression;
  */
 public interface IFunctionGenerator {
 
-	void generate(IMscriptGeneratorContext context, IVariableAccessStrategy variableAccessStrategy, List<Expression> arguments);
+	void generate(IMscriptGeneratorContext context, IVariableAccessStrategy variableAccessStrategy, List<? extends Expression> arguments);
 	
 }

+ 97 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/internal/RoundFunctionGenerator.java

@@ -0,0 +1,97 @@
+/****************************************************************************
+ * Copyright (c) 2008, 2011 Andreas Unger 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:
+ *    Andreas Unger - initial API and implementation 
+ ****************************************************************************/
+
+package org.eclipselabs.mscript.codegen.c.internal;
+
+import java.io.PrintWriter;
+import java.util.List;
+
+import org.eclipse.emf.ecore.util.EcoreUtil;
+import org.eclipselabs.mscript.codegen.c.ExpressionGenerator;
+import org.eclipselabs.mscript.codegen.c.IExpressionGenerator;
+import org.eclipselabs.mscript.codegen.c.IFunctionGenerator;
+import org.eclipselabs.mscript.codegen.c.IMscriptGeneratorContext;
+import org.eclipselabs.mscript.codegen.c.IVariableAccessStrategy;
+import org.eclipselabs.mscript.codegen.c.internal.util.Caster;
+import org.eclipselabs.mscript.codegen.c.util.MscriptGeneratorUtil;
+import org.eclipselabs.mscript.computation.computationmodel.FixedPointFormat;
+import org.eclipselabs.mscript.computation.computationmodel.FloatingPointFormat;
+import org.eclipselabs.mscript.computation.computationmodel.NumberFormat;
+import org.eclipselabs.mscript.language.ast.Expression;
+import org.eclipselabs.mscript.language.il.util.ILUtil;
+import org.eclipselabs.mscript.typesystem.DataType;
+import org.eclipselabs.mscript.typesystem.IntegerType;
+import org.eclipselabs.mscript.typesystem.NumericType;
+import org.eclipselabs.mscript.typesystem.TypeSystemFactory;
+
+/**
+ * @author Andreas Unger
+ *
+ */
+public class RoundFunctionGenerator implements IFunctionGenerator {
+
+	private final IExpressionGenerator expressionGenerator = new ExpressionGenerator();
+	
+	/* (non-Javadoc)
+	 * @see org.eclipselabs.mscript.codegen.c.IFunctionGenerator#generate(java.util.List)
+	 */
+	public void generate(final IMscriptGeneratorContext context, final IVariableAccessStrategy variableAccessStrategy, List<? extends Expression> arguments) {
+		final PrintWriter writer = new PrintWriter(context.getWriter());
+		
+		final Expression argument = arguments.get(0);
+		
+		final DataType argumentDataType = ILUtil.getDataType(argument);
+		if (!(argumentDataType instanceof NumericType)) {
+			throw new IllegalArgumentException();
+		}
+		
+		NumericType argumentNumericType = (NumericType) argumentDataType;
+		IntegerType resultDataType = TypeSystemFactory.eINSTANCE.createIntegerType();
+		resultDataType.setUnit(EcoreUtil.copy(argumentNumericType.getUnit()));
+		
+		NumberFormat numberFormat = context.getComputationModel().getNumberFormat(argumentDataType);
+		
+		if (numberFormat instanceof FixedPointFormat) {
+			final FixedPointFormat fixedPointFormat = (FixedPointFormat) numberFormat;
+			final int fractionLength = fixedPointFormat.getFractionLength();
+			new Caster() {
+				
+				@Override
+				protected void writeExpression() {
+					if (fractionLength > 0) {
+						writer.print("((");
+						expressionGenerator.generate(context, variableAccessStrategy, argument);
+						writer.printf(") + %d) & (%s) 0x%x", 1L << fractionLength - 1,
+								MscriptGeneratorUtil.getCDataType(context.getComputationModel(), argumentDataType),
+								(1L << fixedPointFormat.getWordSize()) - 1 >>> fractionLength << fractionLength);
+					} else {
+						expressionGenerator.generate(context, variableAccessStrategy, argument);
+					}
+				}
+				
+			}.cast(context, argumentDataType, resultDataType);
+		} else if (numberFormat instanceof FloatingPointFormat) {
+			new Caster() {
+				
+				@Override
+				protected void writeExpression() {
+					writer.print("floor((");
+					expressionGenerator.generate(context, variableAccessStrategy, argument);
+					writer.print(") + 0.5)");
+				}
+				
+			}.cast(context, argumentDataType, resultDataType);
+		} else {
+			throw new IllegalArgumentException();
+		}
+	}
+	
+}

+ 7 - 2
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/SumFunctionGenerator.java

@@ -9,11 +9,16 @@
  *    Andreas Unger - initial API and implementation 
  ****************************************************************************/
 
-package org.eclipselabs.mscript.codegen.c;
+package org.eclipselabs.mscript.codegen.c.internal;
 
 import java.io.PrintWriter;
 import java.util.List;
 
+import org.eclipselabs.mscript.codegen.c.ExpressionGenerator;
+import org.eclipselabs.mscript.codegen.c.IExpressionGenerator;
+import org.eclipselabs.mscript.codegen.c.IFunctionGenerator;
+import org.eclipselabs.mscript.codegen.c.IMscriptGeneratorContext;
+import org.eclipselabs.mscript.codegen.c.IVariableAccessStrategy;
 import org.eclipselabs.mscript.language.ast.Expression;
 import org.eclipselabs.mscript.language.il.util.ILUtil;
 import org.eclipselabs.mscript.typesystem.DataType;
@@ -30,7 +35,7 @@ public class SumFunctionGenerator implements IFunctionGenerator {
 	/* (non-Javadoc)
 	 * @see org.eclipselabs.mscript.codegen.c.IFunctionGenerator#generate(java.util.List)
 	 */
-	public void generate(IMscriptGeneratorContext context, IVariableAccessStrategy variableAccessStrategy, List<Expression> arguments) {
+	public void generate(IMscriptGeneratorContext context, IVariableAccessStrategy variableAccessStrategy, List<? extends Expression> arguments) {
 		PrintWriter writer = new PrintWriter(context.getWriter());
 		
 		Expression argument = arguments.get(0);

+ 5 - 1
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/internal/util/CastToFixedPointHelper.java

@@ -72,7 +72,11 @@ public abstract class CastToFixedPointHelper extends ComputationModelSwitch<Bool
 	@Override
 	public Boolean caseFixedPointFormat(FixedPointFormat fixedPointFormat) {
 		if (wordSize != fixedPointFormat.getWordSize()) {
-			writer.printf("((%s) (", getCDataType());
+			if (fractionLength < fixedPointFormat.getFractionLength()) {
+				writer.printf("(%s) ((", getCDataType());
+			} else {
+				writer.printf("((%s) (", getCDataType());
+			}
 		}
 		if (fractionLength != fixedPointFormat.getFractionLength()) {
 			if (wordSize == fixedPointFormat.getWordSize()) {

+ 59 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.codegen.c/src/org/eclipselabs/mscript/codegen/c/internal/util/Caster.java

@@ -0,0 +1,59 @@
+/****************************************************************************
+ * Copyright (c) 2008, 2011 Andreas Unger 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:
+ *    Andreas Unger - initial API and implementation 
+ ****************************************************************************/
+
+package org.eclipselabs.mscript.codegen.c.internal.util;
+
+import org.eclipselabs.mscript.codegen.c.IMscriptGeneratorContext;
+import org.eclipselabs.mscript.computation.computationmodel.FixedPointFormat;
+import org.eclipselabs.mscript.computation.computationmodel.FloatingPointFormat;
+import org.eclipselabs.mscript.computation.computationmodel.NumberFormat;
+import org.eclipselabs.mscript.typesystem.DataType;
+import org.eclipselabs.mscript.typesystem.NumericType;
+
+/**
+ * @author Andreas Unger
+ *
+ */
+public abstract class Caster {
+
+	public void cast(IMscriptGeneratorContext context, DataType expressionDataType, DataType targetDataType) {
+		if (targetDataType instanceof NumericType) {
+			NumberFormat numberFormat = context.getComputationModel().getNumberFormat(targetDataType);
+			if (numberFormat instanceof FloatingPointFormat) {
+				new CastToFloatingPointHelper(context, expressionDataType, (FloatingPointFormat) numberFormat) {
+					
+					@Override
+					protected void writeExpression() {
+						Caster.this.writeExpression();
+					}
+					
+				}.cast();
+			} else if (numberFormat instanceof FixedPointFormat) {
+				FixedPointFormat fixedPointFormat = (FixedPointFormat) numberFormat;
+				new CastToFixedPointHelper(context, expressionDataType, fixedPointFormat.getWordSize(), fixedPointFormat.getFractionLength()) {
+
+					@Override
+					protected void writeExpression() {
+						Caster.this.writeExpression();
+					}
+					
+				}.cast();
+			} else {
+				throw new IllegalArgumentException();
+			}
+		} else {
+			writeExpression();
+		}
+	}
+	
+	protected abstract void writeExpression();
+	
+}

+ 13 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.computation.engine/src/org/eclipselabs/mscript/computation/engine/value/Binary64Value.java

@@ -20,7 +20,9 @@ import org.eclipselabs.mscript.computation.computationmodel.NumberFormat;
 import org.eclipselabs.mscript.computation.computationmodel.util.ComputationModelUtil;
 import org.eclipselabs.mscript.computation.engine.IComputationContext;
 import org.eclipselabs.mscript.typesystem.DataType;
+import org.eclipselabs.mscript.typesystem.IntegerType;
 import org.eclipselabs.mscript.typesystem.NumericType;
+import org.eclipselabs.mscript.typesystem.TypeSystemFactory;
 
 /**
  * @author Andreas Unger
@@ -126,6 +128,17 @@ public class Binary64Value extends AbstractNumericValue implements ISimpleNumeri
 		return new BooleanValue(getContext(), value != otherBinary64Value.value);
 	}
 	
+	/* (non-Javadoc)
+	 * @see org.eclipselabs.mscript.computation.engine.value.ISimpleNumericValue#round()
+	 */
+	public IValue round() {
+		IntegerType resultDataType = TypeSystemFactory.eINSTANCE.createIntegerType();
+		resultDataType.setUnit(EcoreUtil.copy(getDataType().getUnit()));
+		
+		NumberFormat numberFormat = getContext().getComputationModel().getNumberFormat(resultDataType);
+		return new Binary64Value(getContext(), resultDataType, getNumberFormat(), Math.round(value)).cast(numberFormat);
+	}
+	
 	protected AbstractNumericValue cast(NumberFormat numberFormat) {
 		if (EcoreUtil.equals(numberFormat, getNumberFormat())) {
 			return this;

+ 30 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.computation.engine/src/org/eclipselabs/mscript/computation/engine/value/FixedPointValue.java

@@ -23,7 +23,9 @@ import org.eclipselabs.mscript.computation.computationmodel.util.ComputationMode
 import org.eclipselabs.mscript.computation.engine.IComputationContext;
 import org.eclipselabs.mscript.computation.engine.OverflowInfo;
 import org.eclipselabs.mscript.typesystem.DataType;
+import org.eclipselabs.mscript.typesystem.IntegerType;
 import org.eclipselabs.mscript.typesystem.NumericType;
+import org.eclipselabs.mscript.typesystem.TypeSystemFactory;
 
 /**
  * @author Andreas Unger
@@ -190,6 +192,34 @@ public class FixedPointValue extends AbstractNumericValue implements ISimpleNume
 		return new BooleanValue(getContext(), rawValue != otherFixedPointValue.rawValue);
 	}
 	
+	/* (non-Javadoc)
+	 * @see org.eclipselabs.mscript.computation.engine.value.ISimpleNumericValue#round()
+	 */
+	public IValue round() {
+		/*
+		 *  TODO: This needs to be reworked
+		 */
+		
+		IntegerType resultDataType = TypeSystemFactory.eINSTANCE.createIntegerType();
+		resultDataType.setUnit(EcoreUtil.copy(getDataType().getUnit()));
+		
+		FixedPointValue value;
+
+		int fractionLength = getNumberFormat().getFractionLength();
+		if (fractionLength == 0) {
+			value = this;
+		} else {
+			long resultRawValue = rawValue + (1L << fractionLength - 1); // + 0.5
+			long truncatedResult = truncate(resultRawValue, getNumberFormat().getWordSize());
+			if (truncatedResult != resultRawValue) {
+				getContext().getOverflowMonitor().handleOverflow(new OverflowInfo());
+			}
+			value = new FixedPointValue(getContext(), resultDataType, getNumberFormat(), truncatedResult >> fractionLength << fractionLength);
+		}
+		
+		return value.cast(getContext().getComputationModel().getNumberFormat(resultDataType));
+	}
+	
 	protected AbstractNumericValue cast(NumberFormat numberFormat) {
 		if (EcoreUtil.equals(numberFormat, getNumberFormat())) {
 			return this;

+ 2 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.computation.engine/src/org/eclipselabs/mscript/computation/engine/value/ISimpleNumericValue.java

@@ -17,6 +17,8 @@ package org.eclipselabs.mscript.computation.engine.value;
  */
 public interface ISimpleNumericValue extends INumericValue {
 
+	IValue round();
+	
 	double doubleValue();
 	
 	long longValue();

+ 4 - 23
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/il/builtin/BuiltinFunctionDescriptor.java

@@ -11,11 +11,11 @@
 
 package org.eclipselabs.mscript.language.il.builtin;
 
-import java.util.Collections;
 import java.util.List;
 
+import org.eclipselabs.mscript.language.internal.il.builtin.RoundSignature;
+import org.eclipselabs.mscript.language.internal.il.builtin.UnitSignature;
 import org.eclipselabs.mscript.typesystem.DataType;
-import org.eclipselabs.mscript.typesystem.TypeSystemFactory;
 
 /**
  * @author Andreas Unger
@@ -23,28 +23,9 @@ import org.eclipselabs.mscript.typesystem.TypeSystemFactory;
  */
 public enum BuiltinFunctionDescriptor {
 	
-	UNIT(
-			"unit",
-			new Signature(
-					Collections.<DataType>singletonList(TypeSystemFactory.eINSTANCE.createRealType()),
-					TypeSystemFactory.eINSTANCE.createUnitType()));
+	UNIT("unit", new UnitSignature()),
+	ROUND("round", new RoundSignature());
 	
-//	SUM(
-//			"sum",
-//			new ISignature() {
-//				
-//				public List<DataType> evaluateOutputParameterDataTypes(DataType targetDataType, List<DataType> inputDataTypes) {
-//					if (targetDataType instanceof TensorType && inputDataTypes.isEmpty()) {
-//						TensorType tensorType = (TensorType) targetDataType;
-//						if (tensorType.getDimensionality() == 1) {
-//							return Collections.<DataType>singletonList(tensorType.getElementType());
-//						}
-//					}
-//					return null;
-//				}
-//				
-//			});
-
 	private String name;
 	private ISignature signature;
 

+ 1 - 1
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/il/builtin/ISignature.java

@@ -21,6 +21,6 @@ import org.eclipselabs.mscript.typesystem.DataType;
  */
 public interface ISignature {
 
-	List<DataType> evaluateOutputParameterDataTypes(List<DataType> inputParameterDataTypes);
+	List<DataType> evaluateOutputParameterDataTypes(List<? extends DataType> inputParameterDataTypes);
 	
 }

+ 1 - 1
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/il/builtin/Signature.java

@@ -41,7 +41,7 @@ public class Signature implements ISignature {
 	/* (non-Javadoc)
 	 * @see org.eclipselabs.mscript.language.imperativemodel.util.ISignature#evaluateOutputDataTypes(java.util.List)
 	 */
-	public List<DataType> evaluateOutputParameterDataTypes(List<DataType> inputParameterDataTypes) {
+	public List<DataType> evaluateOutputParameterDataTypes(List<? extends DataType> inputParameterDataTypes) {
 		if (this.inputParameterDataTypes == inputParameterDataTypes) {
 			return outputParameterDataTypes;
 		}

+ 51 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/internal/il/builtin/RoundSignature.java

@@ -0,0 +1,51 @@
+/****************************************************************************
+ * Copyright (c) 2008, 2011 Andreas Unger 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:
+ *    Andreas Unger - initial API and implementation 
+ ****************************************************************************/
+
+package org.eclipselabs.mscript.language.internal.il.builtin;
+
+import java.util.Collections;
+import java.util.List;
+
+import org.eclipse.emf.ecore.util.EcoreUtil;
+import org.eclipselabs.mscript.language.il.builtin.ISignature;
+import org.eclipselabs.mscript.typesystem.DataType;
+import org.eclipselabs.mscript.typesystem.IntegerType;
+import org.eclipselabs.mscript.typesystem.NumericType;
+import org.eclipselabs.mscript.typesystem.RealType;
+import org.eclipselabs.mscript.typesystem.TypeSystemFactory;
+
+/**
+ * @author Andreas Unger
+ *
+ */
+public class RoundSignature implements ISignature {
+
+	/* (non-Javadoc)
+	 * @see org.eclipselabs.mscript.language.il.builtin.ISignature#evaluateOutputParameterDataTypes(java.util.List)
+	 */
+	public List<DataType> evaluateOutputParameterDataTypes(List<? extends DataType> inputParameterDataTypes) {
+		if (inputParameterDataTypes.size() != 1) {
+			return null;
+		}
+		
+		DataType inputDataType = inputParameterDataTypes.get(0);
+		
+		if (inputDataType instanceof RealType || inputDataType instanceof IntegerType) {
+			NumericType inputNumericType = (NumericType) inputDataType;
+			IntegerType outputDataType = TypeSystemFactory.eINSTANCE.createIntegerType();
+			outputDataType.setUnit(EcoreUtil.copy(inputNumericType.getUnit()));
+			return Collections.<DataType>singletonList(outputDataType);
+		}
+		
+		return null;
+	}
+
+}

+ 30 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/internal/il/builtin/UnitSignature.java

@@ -0,0 +1,30 @@
+/****************************************************************************
+ * Copyright (c) 2008, 2011 Andreas Unger 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:
+ *    Andreas Unger - initial API and implementation 
+ ****************************************************************************/
+
+package org.eclipselabs.mscript.language.internal.il.builtin;
+
+import java.util.Collections;
+
+import org.eclipselabs.mscript.language.il.builtin.Signature;
+import org.eclipselabs.mscript.typesystem.DataType;
+import org.eclipselabs.mscript.typesystem.TypeSystemFactory;
+
+/**
+ * @author Andreas Unger
+ *
+ */
+public class UnitSignature extends Signature {
+
+	public UnitSignature() {
+		super(Collections.<DataType>singletonList(TypeSystemFactory.eINSTANCE.createRealType()), TypeSystemFactory.eINSTANCE.createUnitType());
+	}
+
+}

+ 1 - 1
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/ExpressionValueEvaluator.java

@@ -531,7 +531,7 @@ public class ExpressionValueEvaluator implements IExpressionValueEvaluator {
 					if (descriptor != null) {
 						IFunction behavior = builtinFunctionLookupTable.getFunction(descriptor);
 						if (behavior != null) {
-							return behavior.call(context, argumentValues);
+							return behavior.call(context, argumentValues).get(0);
 						}
 					}
 				}

+ 2 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/BuiltinFunctionLookupTable.java

@@ -26,6 +26,8 @@ public class BuiltinFunctionLookupTable implements IBuiltinFunctionLookupTable {
 		switch (descriptor) {
 		case UNIT:
 			return new UnitFunction();
+		case ROUND:
+			return new RoundFunction();
 		}
 		return null;
 	}

+ 1 - 1
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/IFunction.java

@@ -24,6 +24,6 @@ import org.eclipselabs.mscript.language.interpreter.IInterpreterContext;
  */
 public interface IFunction {
 
-	IValue call(IInterpreterContext context, List<IValue> arguments);
+	List<IValue> call(IInterpreterContext context, List<? extends IValue> arguments);
 	
 }

+ 36 - 0
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/RoundFunction.java

@@ -0,0 +1,36 @@
+/****************************************************************************
+ * Copyright (c) 2008, 2010 Andreas Unger 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:
+ *    Andreas Unger - initial API and implementation 
+ ****************************************************************************/
+
+package org.eclipselabs.mscript.language.interpreter.builtin;
+
+import java.util.Collections;
+import java.util.List;
+
+import org.eclipselabs.mscript.computation.engine.value.ISimpleNumericValue;
+import org.eclipselabs.mscript.computation.engine.value.IValue;
+import org.eclipselabs.mscript.language.interpreter.IInterpreterContext;
+
+/**
+ * @author Andreas Unger
+ *
+ */
+public class RoundFunction implements IFunction {
+
+	public List<IValue> call(IInterpreterContext context, List<? extends IValue> arguments) {
+		IValue argument = arguments.get(0);
+		if (argument instanceof ISimpleNumericValue) {
+			IValue result = ((ISimpleNumericValue) argument).round();
+			return Collections.singletonList(result);
+		}
+		throw new IllegalArgumentException();
+	}
+	
+}

+ 7 - 4
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/SumFunction.java

@@ -11,6 +11,7 @@
 
 package org.eclipselabs.mscript.language.interpreter.builtin;
 
+import java.util.Collections;
 import java.util.List;
 
 import org.eclipselabs.mscript.computation.engine.value.IValue;
@@ -23,7 +24,7 @@ import org.eclipselabs.mscript.language.interpreter.IInterpreterContext;
  */
 public class SumFunction implements IFunction {
 
-	public IValue call(IInterpreterContext context, List<IValue> arguments) {
+	public List<IValue> call(IInterpreterContext context, List<? extends IValue> arguments) {
 		IValue argument = arguments.get(0);
 		if (argument instanceof VectorValue) {
 			VectorValue vectorValue = (VectorValue) argument;
@@ -35,10 +36,12 @@ public class SumFunction implements IFunction {
 					result = result.add(vectorValue.get(i));
 				}
 			}
-			// TODO: check for null and return 0
-			return result;
+			if (result == null) {
+				throw new IllegalArgumentException();
+			}
+			return Collections.singletonList(result);
 		}
-		return null;
+		throw new IllegalArgumentException();
 	}
 	
 }

+ 4 - 3
org.eclipselabs.mscript/plugins/org.eclipselabs.mscript.language/src/org/eclipselabs/mscript/language/interpreter/builtin/UnitFunction.java

@@ -11,6 +11,7 @@
 
 package org.eclipselabs.mscript.language.interpreter.builtin;
 
+import java.util.Collections;
 import java.util.List;
 
 import org.eclipse.emf.ecore.util.EcoreUtil;
@@ -25,13 +26,13 @@ import org.eclipselabs.mscript.typesystem.NumericType;
  */
 public class UnitFunction implements IFunction {
 
-	public IValue call(IInterpreterContext context, List<IValue> arguments) {
+	public List<IValue> call(IInterpreterContext context, List<? extends IValue> arguments) {
 		IValue argument = arguments.get(0);
 		if (argument.getDataType() instanceof NumericType) {
 			NumericType numericType = (NumericType) argument.getDataType();
-			return new UnitValue(context.getComputationContext(), EcoreUtil.copy(numericType.getUnit()));
+			return Collections.<IValue>singletonList(new UnitValue(context.getComputationContext(), EcoreUtil.copy(numericType.getUnit())));
 		}
-		return null;
+		throw new IllegalArgumentException();
 	}
 	
 }