summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorjkohnlein2008-03-18 12:08:39 (EDT)
committer jkohnlein2008-03-18 12:08:39 (EDT)
commitc4da40e86a4af79156cb3824d3dfa2545140aedc (patch)
treef3627c715cd1683a5568093b7ca035104456ad09
parent5d1af9127648ce0f874530fb603475f77d9f86f2 (diff)
downloadorg.eclipse.xpand-c4da40e86a4af79156cb3824d3dfa2545140aedc.zip
org.eclipse.xpand-c4da40e86a4af79156cb3824d3dfa2545140aedc.tar.gz
org.eclipse.xpand-c4da40e86a4af79156cb3824d3dfa2545140aedc.tar.bz2
- first "Durchstich": parse, map and execute simple xtend expression
-rw-r--r--plugins/org.eclipse.xpand3.common/model/built-in.xmi26
-rw-r--r--plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3FileUtil.java30
-rw-r--r--plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3Util.java19
-rw-r--r--plugins/org.eclipse.xpand3.parser/TODO.txt2
-rw-r--r--plugins/org.eclipse.xpand3.parser/src/org/eclipse/xpand3/parser/ParseFacade.java7
-rw-r--r--plugins/org.eclipse.xpand3/META-INF/MANIFEST.MF2
-rw-r--r--plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/BackendAstUtil.java32
-rw-r--r--plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Declaration2Backend.java86
-rw-r--r--plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Expression2Backend.java192
-rw-r--r--plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Xpand3MiddleEnd.java41
-rw-r--r--plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/functions/SourceDefinedFunction.java72
-rw-r--r--plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/types/CompositeTypesystem.java355
-rw-r--r--tests/org.eclipse.xpand3.parser.tests/src/org/eclipse/xpand3/frontend/parser/node2ast/ParseStuff.java14
-rw-r--r--tests/org.eclipse.xpand3.tests/META-INF/MANIFEST.MF3
-rw-r--r--tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/MiddleEndTest.java48
-rw-r--r--tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/test.ext3
16 files changed, 599 insertions, 333 deletions
diff --git a/plugins/org.eclipse.xpand3.common/model/built-in.xmi b/plugins/org.eclipse.xpand3.common/model/built-in.xmi
index 32b3891..1c2e773 100644
--- a/plugins/org.eclipse.xpand3.common/model/built-in.xmi
+++ b/plugins/org.eclipse.xpand3.common/model/built-in.xmi
@@ -1,19 +1,19 @@
<?xml version="1.0" encoding="ASCII"?>
<staticTypesystem:Model xmi:version="2.0" xmlns:xmi="http://www.omg.org/XMI" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:staticTypesystem="http://www.eclipse.org/m2t/xpand3/staticTypesystem" xsi:schemaLocation="http://www.eclipse.org/m2t/xpand3/staticTypesystem static_typesystem.ecore">
- <declarations name="Object"/>
- <declarations name="Boolean">
+ <declarations name="Object" uniqueID="{builtin}Object"/>
+ <declarations name="Boolean" uniqueID="{builtin}Boolean">
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="Integer">
+ <declarations name="Integer" uniqueID="{builtin}Integer">
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="Real">
+ <declarations name="Real" uniqueID="{builtin}Real">
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="String">
+ <declarations name="String" uniqueID="{builtin}String">
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="Collection">
+ <declarations name="Collection" uniqueID="{builtin}Collection">
<properties name="size">
<type xsi:type="staticTypesystem:Type" declaredType="//@declarations.2"/>
</properties>
@@ -23,19 +23,19 @@
<declaredTypeParameters name="T"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="List">
+ <declarations name="List" uniqueID="{builtin}List">
<declaredTypeParameters name="T"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.5">
<actualTypeArguments xsi:type="staticTypesystem:TypeVariable" declaredTypeParameter="//@declarations.6/@declaredTypeParameters.0"/>
</superTypes>
</declarations>
- <declarations name="Set">
+ <declarations name="Set" uniqueID="{builtin}Set">
<declaredTypeParameters name="T"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.5">
<actualTypeArguments xsi:type="staticTypesystem:TypeVariable" declaredTypeParameter="//@declarations.7/@declaredTypeParameters.0"/>
</superTypes>
</declarations>
- <declarations name="Map">
+ <declarations name="Map" uniqueID="{builtin}Map">
<properties name="size">
<type xsi:type="staticTypesystem:Type" declaredType="//@declarations.2"/>
</properties>
@@ -46,7 +46,7 @@
<declaredTypeParameters name="M"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="Type">
+ <declarations name="Type" uniqueID="{builtin}Type">
<properties name="name">
<type xsi:type="staticTypesystem:Type" declaredType="//@declarations.4"/>
</properties>
@@ -60,15 +60,15 @@
<declaredTypeParameters name="T"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="Property">
+ <declarations name="Property" uniqueID="{builtin}Property">
<declaredTypeParameters name="T"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="StaticProperty">
+ <declarations name="StaticProperty" uniqueID="{builtin}StaticProperty">
<declaredTypeParameters name="T"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
- <declarations name="Function">
+ <declarations name="Function" uniqueID="{builtin}Function">
<declaredTypeParameters name="T"/>
<superTypes xsi:type="staticTypesystem:Type" declaredType="//@declarations.0"/>
</declarations>
diff --git a/plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3FileUtil.java b/plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3FileUtil.java
new file mode 100644
index 0000000..dbae02b
--- /dev/null
+++ b/plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3FileUtil.java
@@ -0,0 +1,30 @@
+package org.eclipse.xpand3.util;
+
+import java.io.InputStream;
+
+public class Xpand3FileUtil {
+
+ public static final String CHECK_EXTENSION = ".chk";
+ public static final String XPAND_EXTENSION = ".xpt";
+ public static final String XTEND_EXTENSION = ".ext";
+
+ public static final String[] SUPPORTED_EXTENSIONS = new String[] {
+ XTEND_EXTENSION, XPAND_EXTENSION, CHECK_EXTENSION };
+
+ public static InputStream getXpand3FileAsStream(String xpandFileName,
+ Object context) {
+ if (xpandFileName == null || "".equals(xpandFileName)) {
+ return null;
+ }
+ xpandFileName = xpandFileName.replace(SyntaxConstants.NS_DELIM, "/");
+ Loader classLoader = LoaderFactory.getClassLoader(context);
+ InputStream resourceAsStream = classLoader
+ .getResourceAsStream(xpandFileName);
+ int index = 0;
+ while (resourceAsStream == null && index < SUPPORTED_EXTENSIONS.length) {
+ resourceAsStream = classLoader.getResourceAsStream(xpandFileName
+ + SUPPORTED_EXTENSIONS[index++]);
+ }
+ return resourceAsStream;
+ }
+}
diff --git a/plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3Util.java b/plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3Util.java
deleted file mode 100644
index 3b59906..0000000
--- a/plugins/org.eclipse.xpand3.common/src/org/eclipse/xpand3/util/Xpand3Util.java
+++ /dev/null
@@ -1,19 +0,0 @@
-package org.eclipse.xpand3.util;
-
-public class Xpand3Util {
-
- public static final String TEMPLATE_EXTENSION = null;
-
- public static String normalizeXpandResourceName(String xpandName) {
- if (xpandName == null)
- return null;
-
- if (!xpandName.endsWith("." + TEMPLATE_EXTENSION))
- xpandName += "." + TEMPLATE_EXTENSION;
-
- xpandName = xpandName.replace(SyntaxConstants.NS_DELIM, "/");
-
- return xpandName;
- }
-
-}
diff --git a/plugins/org.eclipse.xpand3.parser/TODO.txt b/plugins/org.eclipse.xpand3.parser/TODO.txt
index 6d0911b..ca5acdb 100644
--- a/plugins/org.eclipse.xpand3.parser/TODO.txt
+++ b/plugins/org.eclipse.xpand3.parser/TODO.txt
@@ -3,8 +3,8 @@ TODO
- Whitespace handling
- node size
- incremental parsing
-- profiling and optimization
- Java mapping
DONE
- "create" identifier
+- profiling and optimization
diff --git a/plugins/org.eclipse.xpand3.parser/src/org/eclipse/xpand3/parser/ParseFacade.java b/plugins/org.eclipse.xpand3.parser/src/org/eclipse/xpand3/parser/ParseFacade.java
index 19dc784..4f5de21 100644
--- a/plugins/org.eclipse.xpand3.parser/src/org/eclipse/xpand3/parser/ParseFacade.java
+++ b/plugins/org.eclipse.xpand3.parser/src/org/eclipse/xpand3/parser/ParseFacade.java
@@ -26,9 +26,8 @@ public class ParseFacade {
return null;
}
Node2AstTransformer node2AstTransformer = new Node2AstTransformer();
- node2AstTransformer.doSwitch(rootNode);
- File file = (File) rootNode;
- file.setFileName(fileName);
- return file;
+ File astFile = (File) node2AstTransformer.doSwitch(rootNode);
+ astFile.setFileName(fileName);
+ return astFile;
}
}
diff --git a/plugins/org.eclipse.xpand3/META-INF/MANIFEST.MF b/plugins/org.eclipse.xpand3/META-INF/MANIFEST.MF
index 3f59a7f..b7d1aad 100644
--- a/plugins/org.eclipse.xpand3/META-INF/MANIFEST.MF
+++ b/plugins/org.eclipse.xpand3/META-INF/MANIFEST.MF
@@ -10,7 +10,7 @@ Bundle-RequiredExecutionEnvironment: J2SE-1.5
Require-Bundle: org.antlr.patched;bundle-version="3.0.0",
org.eclipse.core.runtime,
org.eclipse.emf.ecore;visibility:=reexport,
- org.eclipse.xtend.backend;bundle-version="0.7.0",
+ org.eclipse.xtend.backend;bundle-version="0.7.0";visibility:=reexport,
org.junit,
org.eclipse.emf.ecore.xmi;bundle-version="2.3.0",
org.eclipse.xpand3.frontend,
diff --git a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/BackendAstUtil.java b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/BackendAstUtil.java
index ec4eea3..fed8186 100644
--- a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/BackendAstUtil.java
+++ b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/BackendAstUtil.java
@@ -15,6 +15,7 @@
*/
package org.eclipse.xpand3.middlend;
+import org.eclipse.xpand3.Identifier;
import org.eclipse.xpand3.SyntaxElement;
import org.eclipse.xtend.backend.common.SourcePos;
@@ -31,4 +32,35 @@ public class BackendAstUtil {
return new SourcePos(se.getFileName(), se.getFileName(), se.getLine());
}
+ public static String operationName(Identifier operatorIdentifier) {
+ String operator = operatorIdentifier.getValue();
+ if ("+".equals(operator)) {
+ return "operatorPlus";
+ } else if ("-".equals(operator)) {
+ return "operatorMinus";
+ } else if ("*".equals(operator)) {
+ return "operatorMult";
+ } else if ("/".equals(operator)) {
+ return "operatorDiv";
+ } else if ("%".equals(operator)) {
+ return "operatorMod";
+ } else if ("==".equals(operator)) {
+ return "operatorEquals";
+ } else if ("!=".equals(operator)) {
+ return "operatorNotEquals";
+ } else if ("<".equals(operator)) {
+ return "operatorLess";
+ } else if ("<=".equals(operator)) {
+ return "operatorLessOrEquals";
+ } else if (">".equals(operator)) {
+ return "operatorGreater";
+ } else if (">=".equals(operator)) {
+ return "operatorGreaterOrEquals";
+ } else if ("implies".equals(operator)) {
+ return "operatorImplies";
+ } else if ("!".equals(operator)) {
+ return "operatorNot";
+ }
+ return null;
+ }
}
diff --git a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Declaration2Backend.java b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Declaration2Backend.java
index 3e9e8b1..2cecf34 100644
--- a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Declaration2Backend.java
+++ b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Declaration2Backend.java
@@ -35,7 +35,10 @@ import org.eclipse.xpand3.declaration.ExtensionAspect;
import org.eclipse.xpand3.declaration.JavaExtension;
import org.eclipse.xpand3.declaration.util.DeclarationSwitch;
import org.eclipse.xpand3.statement.AbstractStatement;
+import org.eclipse.xtend.backend.aop.AdviceParamType;
import org.eclipse.xtend.backend.aop.AroundAdvice;
+import org.eclipse.xtend.backend.aop.ExecutionPointcut;
+import org.eclipse.xtend.backend.aop.Pointcut;
import org.eclipse.xtend.backend.common.BackendType;
import org.eclipse.xtend.backend.common.ExpressionBase;
import org.eclipse.xtend.backend.common.Function;
@@ -63,7 +66,28 @@ public class Declaration2Backend extends DeclarationSwitch<Object> {
return xpand3MiddleEnd.getStatement2Backend();
}
- private Function createSourceDefinedFunctionFromAbstractDeclaration(
+ private Pointcut createPointcutFromAspect(AbstractAspect aspect) {
+ String functionNamePattern = aspect.getPointcut().getValue();
+ EList<DeclaredParameter> declaredParams = aspect.getParams();
+ int numDeclaredParams = declaredParams.size();
+ List<Pair<String, AdviceParamType>> params = new ArrayList<Pair<String, AdviceParamType>>(
+ numDeclaredParams);
+ for (DeclaredParameter declaredParam : declaredParams) {
+ String paramName = declaredParam.getName().getValue();
+ BackendType backendType = xpand3MiddleEnd
+ .backendTypeForName(declaredParam.getType());
+ AdviceParamType adviceParamType = new AdviceParamType(backendType,
+ true);
+ // TODO: including subtypes
+ params.add(new Pair<String, AdviceParamType>(paramName,
+ adviceParamType));
+ }
+ Pointcut pointcut = new ExecutionPointcut(functionNamePattern, params,
+ false, null);
+ return pointcut;
+ }
+
+ private Function createFunctionFromDeclaration(
AbstractDeclaration declaration, String name, ExpressionBase body,
boolean isCached, Pair<String, BackendType>... additionalParameters) {
EList<DeclaredParameter> declaredParams = declaration.getParams();
@@ -82,22 +106,24 @@ public class Declaration2Backend extends DeclarationSwitch<Object> {
paramBackendTypes.add(xpand3MiddleEnd
.backendTypeForName(declaredParam.getType()));
}
- ExpressionBase guard = getExpression2Backend().doSwitch(
- declaration.getGuard());
+ ExpressionBase guard = null;
+ if (declaration.getGuard() != null) {
+ guard = getExpression2Backend().doSwitch(declaration.getGuard());
+ }
return new SourceDefinedFunction(name, paramNames, paramBackendTypes,
body, isCached, guard);
}
- private SequenceExpression createSequenceExpressionFromStatementBody(
- Definition object) {
- List<ExpressionBase> bodyExpressions = new ArrayList<ExpressionBase>(
- object.getBody().size());
- for (AbstractStatement bodyStatement : object.getBody()) {
- bodyExpressions.add(getStatement2Backend().doSwitch(bodyStatement));
+ private SequenceExpression createSequenceExpressionFromStatements(
+ SyntaxElement object, List<AbstractStatement> statements) {
+ List<ExpressionBase> expressions = new ArrayList<ExpressionBase>(
+ statements.size());
+ for (AbstractStatement bodyStatement : statements) {
+ expressions.add(getStatement2Backend().doSwitch(bodyStatement));
}
// TODO: what exactly is source position?
SequenceExpression sequenceExpression = new SequenceExpression(
- bodyExpressions, getSourcePos(object));
+ expressions, getSourcePos(object));
return sequenceExpression;
}
@@ -110,8 +136,7 @@ public class Declaration2Backend extends DeclarationSwitch<Object> {
ExpressionBase body = getExpression2Backend().doSwitch(
check.getConstraint());
// TODO: how to handle errorSeverity, message and feature
- return createSourceDefinedFunctionFromAbstractDeclaration(check, "",
- body, false);
+ return createFunctionFromDeclaration(check, "", body, false);
}
@Override
@@ -119,22 +144,25 @@ public class Declaration2Backend extends DeclarationSwitch<Object> {
ExpressionBase body = getExpression2Backend().doSwitch(
createExtension.getBody());
// TODO: return type (currently not in frontend AST model)
- return createSourceDefinedFunctionFromAbstractDeclaration(
- createExtension, createExtension.getName().getValue(), body,
- true);
+ return createFunctionFromDeclaration(createExtension, createExtension
+ .getName().getValue(), body, true);
}
@Override
public Object caseDefinition(Definition definition) {
- SequenceExpression sequenceExpression = createSequenceExpressionFromStatementBody(definition);
- return createSourceDefinedFunctionFromAbstractDeclaration(definition,
- definition.getName().getValue(), sequenceExpression, false);
+ SequenceExpression sequenceExpression = createSequenceExpressionFromStatements(
+ definition, definition.getBody());
+ return createFunctionFromDeclaration(definition, definition.getName()
+ .getValue(), sequenceExpression, false);
}
@Override
- public AroundAdvice caseDefinitionAspect(DefinitionAspect object) {
- throw new RuntimeException("Not implemented yet");
- // TODO
+ public AroundAdvice caseDefinitionAspect(DefinitionAspect definitionAspect) {
+ Pointcut pointcut = createPointcutFromAspect(definitionAspect);
+ // TODO isCached, varargs
+ SequenceExpression body = createSequenceExpressionFromStatements(
+ definitionAspect, definitionAspect.getBody());
+ return new AroundAdvice(body, pointcut, false);
}
@Override
@@ -143,17 +171,17 @@ public class Declaration2Backend extends DeclarationSwitch<Object> {
extension.getBody());
boolean isCached = extension.isCached();
// TODO: return type (currently not in frontend AST model)
- return createSourceDefinedFunctionFromAbstractDeclaration(extension,
- extension.getName().getValue(), body, isCached);
+ return createFunctionFromDeclaration(extension, extension.getName()
+ .getValue(), body, isCached);
}
@Override
- public AroundAdvice caseExtensionAspect(ExtensionAspect object) {
- throw new RuntimeException("Not implemented yet");
- // TODO
- // ExpressionBase body =
- // getExpression2Backend().doSwitch(object.getExpression());
- // return new AroundAdvice(body);
+ public AroundAdvice caseExtensionAspect(ExtensionAspect extensionAspect) {
+ ExpressionBase body = getExpression2Backend().doSwitch(
+ extensionAspect.getExpression());
+ Pointcut pointcut = createPointcutFromAspect(extensionAspect);
+ // TODO isCached, varargs
+ return new AroundAdvice(body, pointcut, false);
}
@Override
diff --git a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Expression2Backend.java b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Expression2Backend.java
index e8f9b93..e6527b8 100644
--- a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Expression2Backend.java
+++ b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Expression2Backend.java
@@ -27,21 +27,33 @@ import org.eclipse.xpand3.analyzation.TypeSystem;
import org.eclipse.xpand3.expression.AbstractExpression;
import org.eclipse.xpand3.expression.BinaryOperation;
import org.eclipse.xpand3.expression.BooleanLiteral;
+import org.eclipse.xpand3.expression.BooleanOperation;
+import org.eclipse.xpand3.expression.Case;
import org.eclipse.xpand3.expression.Cast;
import org.eclipse.xpand3.expression.ChainExpression;
+import org.eclipse.xpand3.expression.CollectionExpression;
import org.eclipse.xpand3.expression.ConstructorCallExpression;
import org.eclipse.xpand3.expression.FeatureCall;
+import org.eclipse.xpand3.expression.GlobalVarExpression;
+import org.eclipse.xpand3.expression.IfExpression;
import org.eclipse.xpand3.expression.IntegerLiteral;
+import org.eclipse.xpand3.expression.LetExpression;
import org.eclipse.xpand3.expression.ListLiteral;
+import org.eclipse.xpand3.expression.Literal;
import org.eclipse.xpand3.expression.NullLiteral;
+import org.eclipse.xpand3.expression.OperationCall;
import org.eclipse.xpand3.expression.RealLiteral;
import org.eclipse.xpand3.expression.StringLiteral;
+import org.eclipse.xpand3.expression.SwitchExpression;
+import org.eclipse.xpand3.expression.TypeSelectExpression;
+import org.eclipse.xpand3.expression.UnaryOperation;
import org.eclipse.xpand3.expression.util.ExpressionSwitch;
import org.eclipse.xpand3.staticTypesystem.Type;
import org.eclipse.xpand3.util.SyntaxConstants;
import org.eclipse.xtend.backend.common.ExpressionBase;
import org.eclipse.xtend.backend.common.SourcePos;
import org.eclipse.xtend.backend.expr.CreateUncachedExpression;
+import org.eclipse.xtend.backend.expr.InvocationOnWhateverExpression;
import org.eclipse.xtend.backend.expr.ListLiteralExpression;
import org.eclipse.xtend.backend.expr.LiteralExpression;
import org.eclipse.xtend.backend.expr.LocalVarEvalExpression;
@@ -58,7 +70,13 @@ import org.eclipse.xtend.backend.types.builtin.CollectionType;
public class Expression2Backend extends ExpressionSwitch<ExpressionBase> {
private TypeSystem frontendTypes = null;
- private AnalyzeContext ctx = null;
+ private AnalyzeContext ctx = new AnalyzeContext.AnalyzeContextImpl() {
+ // TODO: understand how to handle analyze contexts
+ @Override
+ public Var getVariable(String varName) {
+ return new Var(null);
+ }
+ };
private Xpand3MiddleEnd xpand3MiddleEnd;
public Expression2Backend(Xpand3MiddleEnd xpand3MiddleEnd) {
@@ -74,8 +92,15 @@ public class Expression2Backend extends ExpressionSwitch<ExpressionBase> {
}
@Override
- public ExpressionBase caseBinaryOperation(BinaryOperation object) {
- return super.caseBinaryOperation(object);
+ public ExpressionBase caseBinaryOperation(BinaryOperation binaryOperation) {
+ String operationName = BackendAstUtil.operationName(binaryOperation
+ .getOperator());
+ List<ExpressionBase> params = new ArrayList<ExpressionBase>(2);
+ params.add(doSwitch(binaryOperation.getLeft()));
+ params.add(doSwitch(binaryOperation.getRight()));
+ InvocationOnWhateverExpression invocationExpression = new InvocationOnWhateverExpression(
+ operationName, params, true, getSourcePos(binaryOperation));
+ return invocationExpression;
}
@Override
@@ -85,25 +110,41 @@ public class Expression2Backend extends ExpressionSwitch<ExpressionBase> {
}
@Override
- public ExpressionBase caseIntegerLiteral(IntegerLiteral lit) {
- return new LiteralExpression(
- new Long(lit.getLiteralValue().getValue()), getSourcePos(lit));
+ public ExpressionBase caseCast(Cast object) {
+ return doSwitch(object.getTarget());
}
@Override
- public ExpressionBase caseRealLiteral(RealLiteral lit) {
- return new LiteralExpression(new Double(lit.getLiteralValue()
- .getValue()), getSourcePos(lit));
+ public ExpressionBase caseChainExpression(ChainExpression expr) {
+ final List<ExpressionBase> result = new ArrayList<ExpressionBase>();
+ ChainExpression x = expr;
+ while (x != null) {
+ result.add(doSwitch(x.getFirst()));
+ if (x.getNext() instanceof ChainExpression) {
+ x = (ChainExpression) x.getNext();
+ } else {
+ result.add(doSwitch(expr.getNext()));
+ x = null;
+ }
+ }
+ return new SequenceExpression(result, getSourcePos(expr));
+ }
+
+ public ExpressionBase caseConstructorCallExpression(
+ ConstructorCallExpression expr) {
+ return new CreateUncachedExpression(xpand3MiddleEnd
+ .backendTypeForName(expr.getType()), getSourcePos(expr));
}
@Override
- public ExpressionBase caseNullLiteral(NullLiteral lit) {
- return new LiteralExpression(null, getSourcePos(lit));
+ public ExpressionBase caseFeatureCall(FeatureCall object) {
+ return convert(object);
}
@Override
- public ExpressionBase caseCast(Cast object) {
- return doSwitch(object.getTarget());
+ public ExpressionBase caseIntegerLiteral(IntegerLiteral lit) {
+ return new LiteralExpression(
+ new Long(lit.getLiteralValue().getValue()), getSourcePos(lit));
}
@Override
@@ -117,31 +158,122 @@ public class Expression2Backend extends ExpressionSwitch<ExpressionBase> {
}
@Override
+ public ExpressionBase caseNullLiteral(NullLiteral lit) {
+ return new LiteralExpression(null, getSourcePos(lit));
+ }
+
+ @Override
+ public ExpressionBase caseOperationCall(OperationCall object) {
+ ExpressionBase targetExpression = doSwitch(object.getTarget());
+ List<ExpressionBase> beParams = new ArrayList<ExpressionBase>(object
+ .getParams().size());
+ // TODO: Find out the difference between InvocationOnWhatever and
+ // InvocationOnObject
+ beParams.add(targetExpression);
+ for (AbstractExpression param : object.getParams()) {
+ beParams.add(doSwitch(param));
+ }
+ if (targetExpression instanceof LocalVarEvalExpression) {
+ // return new InvocationOnObjectExpression(
+ // object.getName().getValue(), beParams, false,
+ // getSourcePos(object));
+ return new InvocationOnWhateverExpression(object.getName()
+ .getValue(), beParams, true, getSourcePos(object));
+ } else {
+ return new InvocationOnWhateverExpression(object.getName()
+ .getValue(), beParams, true, getSourcePos(object));
+ }
+ }
+
+ @Override
+ public ExpressionBase caseRealLiteral(RealLiteral lit) {
+ return new LiteralExpression(new Double(lit.getLiteralValue()
+ .getValue()), getSourcePos(lit));
+ }
+
+ @Override
public ExpressionBase caseStringLiteral(StringLiteral lit) {
return new LiteralExpression(lit.getLiteralValue().getValue(),
getSourcePos(lit));
}
+ /*
+ * not yet implemented
+ */
@Override
- public ExpressionBase caseChainExpression(ChainExpression expr) {
- final List<ExpressionBase> result = new ArrayList<ExpressionBase>();
- ChainExpression x = expr;
- while (x != null) {
- result.add(doSwitch(x.getFirst()));
- if (x.getNext() instanceof ChainExpression) {
- x = (ChainExpression) x.getNext();
- } else {
- result.add(doSwitch(expr.getNext()));
- x = null;
- }
- }
- return new SequenceExpression(result, getSourcePos(expr));
+ public ExpressionBase caseBooleanOperation(BooleanOperation object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
}
- public ExpressionBase caseConstructorCallExpression(
- ConstructorCallExpression expr) {
- return new CreateUncachedExpression(xpand3MiddleEnd
- .backendTypeForName(expr.getType()), getSourcePos(expr));
+ @Override
+ public ExpressionBase caseCase(Case object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseCollectionExpression(CollectionExpression object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseGlobalVarExpression(GlobalVarExpression object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseIfExpression(IfExpression object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseLetExpression(LetExpression object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseLiteral(Literal object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseSwitchExpression(SwitchExpression object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseSyntaxElement(SyntaxElement object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseTypeSelectExpression(TypeSelectExpression object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ @Override
+ public ExpressionBase caseUnaryOperation(UnaryOperation object) {
+ throw new RuntimeException("Not implemented yet");
+ // TODO
+ }
+
+ /*
+ * abstract casess
+ */
+ @Override
+ public ExpressionBase caseAbstractExpression(AbstractExpression object) {
+ xpand3MiddleEnd.handleTransformationError(
+ "Method should never be called", null);
+ return null;
}
/**
diff --git a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Xpand3MiddleEnd.java b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Xpand3MiddleEnd.java
index db73068..8a51ee4 100644
--- a/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Xpand3MiddleEnd.java
+++ b/plugins/org.eclipse.xpand3/src/org/eclipse/xpand3/middlend/Xpand3MiddleEnd.java
@@ -9,13 +9,13 @@ import org.eclipse.xpand3.analyzation.TypeSystem;
import org.eclipse.xpand3.declaration.AbstractDeclaration;
import org.eclipse.xpand3.parser.ParseFacade;
import org.eclipse.xpand3.staticTypesystem.DeclaredType;
-import org.eclipse.xpand3.util.LoaderFactory;
-import org.eclipse.xpand3.util.Xpand3Util;
+import org.eclipse.xpand3.util.Xpand3FileUtil;
import org.eclipse.xtend.backend.aop.AroundAdvice;
import org.eclipse.xtend.backend.common.BackendType;
import org.eclipse.xtend.backend.common.BackendTypesystem;
import org.eclipse.xtend.backend.common.ExecutionContext;
import org.eclipse.xtend.backend.common.NamedFunction;
+import org.eclipse.xtend.backend.functions.SourceDefinedFunction;
import org.eclipse.xtend.middleend.MiddleEnd;
import org.eclipse.xtend.middleend.plugins.ImportedResource;
import org.eclipse.xtend.middleend.plugins.LanguageSpecificMiddleEnd;
@@ -39,9 +39,10 @@ public class Xpand3MiddleEnd implements LanguageSpecificMiddleEnd {
public Xpand3MiddleEnd() {
}
- public boolean canHandle(String resourceName) {
- // TODO Auto-generated method stub
- return false;
+ public boolean canHandle(String xpandFileName) {
+ InputStream xpand3FileAsStream = Xpand3FileUtil.getXpand3FileAsStream(
+ xpandFileName, executionContext);
+ return xpand3FileAsStream != null;
}
public String getName() {
@@ -49,26 +50,24 @@ public class Xpand3MiddleEnd implements LanguageSpecificMiddleEnd {
return null;
}
- public ParsedResource parseResource(String xpandResourceName) {
+ public ParsedResource parseResource(String xpandFileName) {
try {
- String normalizedXpandResourceName = Xpand3Util
- .normalizeXpandResourceName(xpandResourceName);
- InputStream resourceAsStream = LoaderFactory.getClassLoader(
- executionContext).getResourceAsStream(
- normalizedXpandResourceName);
- File xpandFile = ParseFacade.parseFile(normalizedXpandResourceName,
+ InputStream resourceAsStream = Xpand3FileUtil
+ .getXpand3FileAsStream(xpandFileName, executionContext);
+ File xpandFile = ParseFacade.parseFile(xpandFileName,
resourceAsStream);
ParsedResource parsedResource = new ParsedResource();
for (AbstractDeclaration declaration : xpandFile.getDeclarations()) {
Object beDeclaration = declaration2Backend
.doSwitch(declaration);
- if (beDeclaration instanceof NamedFunction) {
+ if (beDeclaration instanceof SourceDefinedFunction) {
+ SourceDefinedFunction beFunction = (SourceDefinedFunction) beDeclaration;
+ NamedFunction namedFunction = new NamedFunction(beFunction
+ .getName(), beFunction);
if (declaration.isIsPrivate()) {
- parsedResource.getPrivateFunctions().add(
- (NamedFunction) beDeclaration);
+ parsedResource.getPrivateFunctions().add(namedFunction);
} else {
- parsedResource.getPublicFunctions().add(
- (NamedFunction) beDeclaration);
+ parsedResource.getPublicFunctions().add(namedFunction);
}
} else if (beDeclaration instanceof AroundAdvice) {
parsedResource.getAdvice()
@@ -99,6 +98,8 @@ public class Xpand3MiddleEnd implements LanguageSpecificMiddleEnd {
expression2Backend = new Expression2Backend(this);
declaration2Backend = new Declaration2Backend(this);
statement2Backend = new Statement2Backend(this);
+ // TODO: which frontendTypeSystem?
+ frontendTypeSystem = TypeSystem.BUILTIN_TYPESYSTEM;
}
public BackendType backendTypeForName(Identifier name) {
@@ -107,14 +108,12 @@ public class Xpand3MiddleEnd implements LanguageSpecificMiddleEnd {
handleTransformationError("Couldn't resolve type for name '"
+ name.getValue() + "'", name);
}
- BackendType backendType = null;
- // TODO perform mapping
- // backendTypeSystem.findTypeForID(dt.getUniqueID());
+ BackendType backendType = backendTypeSystem.findType(dt.getUniqueID());
if (backendType == null) {
handleTransformationError("No backend type found for ID '"
+ dt.getUniqueID() + "'", name);
}
- return null;
+ return backendType;
}
public void handleTransformationError(String message, Identifier name) {
diff --git a/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/functions/SourceDefinedFunction.java b/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/functions/SourceDefinedFunction.java
index 5634018..ed95c11 100644
--- a/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/functions/SourceDefinedFunction.java
+++ b/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/functions/SourceDefinedFunction.java
@@ -18,49 +18,53 @@ import org.eclipse.xtend.backend.common.ExpressionBase;
import org.eclipse.xtend.backend.common.LocalVarContext;
import org.eclipse.xtend.backend.common.StacktraceEntry;
-
/**
*
* @author Arno Haase (http://www.haase-consulting.com)
*/
public final class SourceDefinedFunction extends AbstractFunction {
private final String _name;
- private final List<String> _paramNames;
- private final ExpressionBase _def;
+ private final List<String> _paramNames;
+ private final ExpressionBase _def;
+
+ public SourceDefinedFunction(String name, List<String> paramNames,
+ List<BackendType> paramTypes, ExpressionBase def, boolean cached,
+ ExpressionBase guard) {
+ super(guard, paramTypes, cached);
+ _name = name;
+ _paramNames = paramNames;
+ _def = def;
+ }
+
+ public Object invoke(ExecutionContext ctx, Object[] params) {
+ final LocalVarContext lvc = new LocalVarContext();
+ for (int i = 0; i < _paramNames.size(); i++) {
+ lvc.getLocalVars().put(_paramNames.get(i), params[i]);
+ }
+
+ final LocalVarContext oldLvc = ctx.getLocalVarContext();
+ try {
+ ctx.setLocalVarContext(lvc);
- public SourceDefinedFunction (String name, List<String> paramNames, List<BackendType> paramTypes, ExpressionBase def, boolean cached, ExpressionBase guard) {
- super (guard, paramTypes, cached);
- _name = name;
- _paramNames = paramNames;
- _def = def;
- }
+ if (ctx.isLogStacktrace())
+ ctx.getStacktrace()
+ .add(new StacktraceEntry(_def.getPos(), ctx));
- public Object invoke (ExecutionContext ctx, Object[] params) {
- final LocalVarContext lvc = new LocalVarContext ();
- for (int i=0; i<_paramNames.size(); i++) {
- lvc.getLocalVars().put(_paramNames.get(i), params[i]);
- }
-
- final LocalVarContext oldLvc = ctx.getLocalVarContext();
- try {
- ctx.setLocalVarContext(lvc);
-
- if (ctx.isLogStacktrace())
- ctx.getStacktrace().add (new StacktraceEntry (_def.getPos(), ctx));
-
- return _def.evaluate(ctx);
- }
- finally {
- if (ctx.isLogStacktrace())
- ctx.getStacktrace().remove (ctx.getStacktrace().size() - 1);
-
- ctx.setLocalVarContext(oldLvc);
- }
- }
+ return _def.evaluate(ctx);
+ } finally {
+ if (ctx.isLogStacktrace())
+ ctx.getStacktrace().remove(ctx.getStacktrace().size() - 1);
+
+ ctx.setLocalVarContext(oldLvc);
+ }
+ }
@Override
- public String toString () {
- return "SourceDefinedFunction '" + _name + "' " + getParameterTypes();
+ public String toString() {
+ return "SourceDefinedFunction '" + _name + "' " + getParameterTypes();
}
-}
+ public String getName() {
+ return _name;
+ }
+}
diff --git a/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/types/CompositeTypesystem.java b/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/types/CompositeTypesystem.java
index 3756ed8..aaf42ff 100644
--- a/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/types/CompositeTypesystem.java
+++ b/plugins/org.eclipse.xtend.backend/src/org/eclipse/xtend/backend/types/CompositeTypesystem.java
@@ -40,182 +40,191 @@ import org.eclipse.xtend.backend.types.java.internal.GlobalJavaBeansTypesystem;
import org.eclipse.xtend.backend.util.Cache;
import org.eclipse.xtend.backend.util.IdentityCache;
-
/**
- * This is the "normal" implementation of a backend type system - it can recursively
- * contain other type system implementations, and it contributes the built-in types.
+ * This is the "normal" implementation of a backend type system - it can
+ * recursively contain other type system implementations, and it contributes the
+ * built-in types.
*
* @author Arno Haase (http://www.haase-consulting.com)
*/
public final class CompositeTypesystem implements BackendTypesystem {
- private BackendTypesystem _rootTypesystem = this;
- private final List<BackendTypesystem> _inner = new ArrayList<BackendTypesystem>();
-
- private static final Map<String, BackendType> _typeByUniqueRepresentation = new HashMap<String, BackendType> ();
-
- static {
- _typeByUniqueRepresentation.put ("{builtin}Boolean", BooleanType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Collection", CollectionType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Double", DoubleType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Function", FunctionType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}List", ListType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Long", LongType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Map", MapType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Object", ObjectType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Property", PropertyType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Set", SetType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}StaticProperty", StaticPropertyType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}String", StringType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Type", TypeType.INSTANCE);
- _typeByUniqueRepresentation.put ("{builtin}Void", VoidType.INSTANCE);
- }
-
- private final BackendTypesystem _javaBeansTypesystem = new GlobalJavaBeansTypesystem ();
- {
- _javaBeansTypesystem.setRootTypesystem (_rootTypesystem);
- }
-
- private final IdentityCache<Object, BackendType> _typeByInstanceCache = new IdentityCache<Object, BackendType>() {
-
- @Override
- protected BackendType create (Object o) {
- if (o == null)
- return VoidType.INSTANCE;
-
- BackendType bestMatch = findSimpleBuiltinType (o.getClass());
- for (BackendTypesystem ts: _inner)
- bestMatch = bestMatch (bestMatch, ts.findType (o));
-
- if (bestMatch != null)
- return bestMatch;
-
- bestMatch = _javaBeansTypesystem.findType (o);
- if (bestMatch != null)
- return bestMatch;
-
- return ObjectType.INSTANCE;
- }
- };
-
- private final Cache<Class<?>, BackendType> _typeByClassCache = new Cache<Class<?>, BackendType>() {
- @Override
- protected BackendType create (Class<?> key) {
- BackendType bestMatch = findSimpleBuiltinType (key);
-
- for (BackendTypesystem ts : _inner)
- bestMatch = bestMatch (bestMatch, ts.findType(key));
-
- if (bestMatch != null)
- return bestMatch;
-
- final BackendType jbResult = _javaBeansTypesystem.findType (key);
- if (jbResult != null)
- return jbResult;
-
- return ObjectType.INSTANCE;
- }
- };
-
- private BackendType bestMatch (BackendType t1, BackendType t2) {
- if (t1 == null)
- return t2;
- if (t2 == null)
- return t1;
-
- if (t1.isAssignableFrom(t2))
- return t2;
- if (t2.isAssignableFrom(t1))
- return t1;
-
- throw new IllegalArgumentException ("no unique best match for types " + t1 + " and " + t2);
- }
-
- //TODO remove this - add "asBackendType" to frontend type instead
- public Collection<BackendTypesystem> getInner () {
- final Collection<BackendTypesystem> result = new ArrayList<BackendTypesystem> (_inner);
- result.add (_javaBeansTypesystem);
- return result;
- }
-
- public void register (BackendTypesystem ts) {
- _inner.add(ts);
- ts.setRootTypesystem (getRootTypesystem());
- }
-
- public BackendType findType (Object o) {
- return _typeByInstanceCache.get (o);
- }
-
- public BackendType findType (Class<?> cls) {
- return _typeByClassCache.get (cls);
- }
-
- public BackendType findType (String uniqueRepresentation) {
- final BackendType asBuiltin = _typeByUniqueRepresentation.get (uniqueRepresentation);
- if (asBuiltin != null)
- return asBuiltin;
-
- for (BackendTypesystem ts: _inner) {
- final BackendType t = ts.findType (uniqueRepresentation);
- if (t != null)
- return t;
- }
-
- return _javaBeansTypesystem.findType (uniqueRepresentation);
- }
-
- public BackendTypesystem getRootTypesystem () {
- return _rootTypesystem;
- }
-
- public void setRootTypesystem (BackendTypesystem ts) {
- _rootTypesystem = ts;
- for (BackendTypesystem child : _inner)
- child.setRootTypesystem(ts);
-
- _javaBeansTypesystem.setRootTypesystem (ts);
- }
-
- private BackendType findSimpleBuiltinType (Class<?> cls) {
- if (cls == null)
- return ObjectType.INSTANCE; // convenience handling e.g. for interface types whose Java supertype is 'null'
-
- if (List.class.isAssignableFrom (cls))
- return ListType.INSTANCE;
- if (Set.class.isAssignableFrom(cls))
- return SetType.INSTANCE;
- if (Collection.class.isAssignableFrom(cls))
- return CollectionType.INSTANCE;
-
- if (Map.class.isAssignableFrom(cls))
- return MapType.INSTANCE;
-
- if (CharSequence.class.isAssignableFrom(cls))
- return StringType.INSTANCE;
-
- if (cls == Boolean.class || cls == Boolean.TYPE)
- return BooleanType.INSTANCE;
-
- if (cls == Long.class || cls == Long.TYPE)
- return LongType.INSTANCE;
- if (cls == Double.class || cls == Double.TYPE)
- return DoubleType.INSTANCE;
-
- if (Function.class.isAssignableFrom(cls))
- return FunctionType.INSTANCE;
-
- if (cls == Void.TYPE)
- return VoidType.INSTANCE;
-
- if (BackendType.class.isAssignableFrom(cls))
- return TypeType.INSTANCE;
- if (Property.class.isAssignableFrom(cls))
- return PropertyType.INSTANCE;
- if (StaticProperty.class.isAssignableFrom(cls))
- return StaticPropertyType.INSTANCE;
-
- return null;
- }
+ private BackendTypesystem _rootTypesystem = this;
+ private final List<BackendTypesystem> _inner = new ArrayList<BackendTypesystem>();
+
+ private static final Map<String, BackendType> _typeByUniqueRepresentation = new HashMap<String, BackendType>();
+
+ static {
+ _typeByUniqueRepresentation.put("{builtin}Boolean",
+ BooleanType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Collection",
+ CollectionType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Double", DoubleType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Function",
+ FunctionType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}List", ListType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Long", LongType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Map", MapType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Object", ObjectType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Property",
+ PropertyType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Set", SetType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}StaticProperty",
+ StaticPropertyType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}String", StringType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Type", TypeType.INSTANCE);
+ _typeByUniqueRepresentation.put("{builtin}Void", VoidType.INSTANCE);
+ }
+
+ private final BackendTypesystem _javaBeansTypesystem = new GlobalJavaBeansTypesystem();
+ {
+ _javaBeansTypesystem.setRootTypesystem(_rootTypesystem);
+ }
+
+ private final IdentityCache<Object, BackendType> _typeByInstanceCache = new IdentityCache<Object, BackendType>() {
+
+ @Override
+ protected BackendType create(Object o) {
+ if (o == null)
+ return VoidType.INSTANCE;
+
+ BackendType bestMatch = findSimpleBuiltinType(o.getClass());
+ for (BackendTypesystem ts : _inner)
+ bestMatch = bestMatch(bestMatch, ts.findType(o));
+
+ if (bestMatch != null)
+ return bestMatch;
+
+ bestMatch = _javaBeansTypesystem.findType(o);
+ if (bestMatch != null)
+ return bestMatch;
+
+ return ObjectType.INSTANCE;
+ }
+ };
+
+ private final Cache<Class<?>, BackendType> _typeByClassCache = new Cache<Class<?>, BackendType>() {
+ @Override
+ protected BackendType create(Class<?> key) {
+ BackendType bestMatch = findSimpleBuiltinType(key);
+
+ for (BackendTypesystem ts : _inner)
+ bestMatch = bestMatch(bestMatch, ts.findType(key));
+
+ if (bestMatch != null)
+ return bestMatch;
+
+ final BackendType jbResult = _javaBeansTypesystem.findType(key);
+ if (jbResult != null)
+ return jbResult;
+
+ return ObjectType.INSTANCE;
+ }
+ };
+
+ private BackendType bestMatch(BackendType t1, BackendType t2) {
+ if (t1 == null)
+ return t2;
+ if (t2 == null)
+ return t1;
+
+ if (t1.isAssignableFrom(t2))
+ return t2;
+ if (t2.isAssignableFrom(t1))
+ return t1;
+
+ throw new IllegalArgumentException("no unique best match for types "
+ + t1 + " and " + t2);
+ }
+
+ // TODO remove this - add "asBackendType" to frontend type instead
+ public Collection<BackendTypesystem> getInner() {
+ final Collection<BackendTypesystem> result = new ArrayList<BackendTypesystem>(
+ _inner);
+ result.add(_javaBeansTypesystem);
+ return result;
+ }
+
+ public void register(BackendTypesystem ts) {
+ _inner.add(ts);
+ ts.setRootTypesystem(getRootTypesystem());
+ }
+
+ public BackendType findType(Object o) {
+ return _typeByInstanceCache.get(o);
+ }
+
+ public BackendType findType(Class<?> cls) {
+ return _typeByClassCache.get(cls);
+ }
+
+ public BackendType findType(String uniqueRepresentation) {
+ final BackendType asBuiltin = _typeByUniqueRepresentation
+ .get(uniqueRepresentation);
+ if (asBuiltin != null)
+ return asBuiltin;
+
+ for (BackendTypesystem ts : _inner) {
+ final BackendType t = ts.findType(uniqueRepresentation);
+ if (t != null)
+ return t;
+ }
+
+ return _javaBeansTypesystem.findType(uniqueRepresentation);
+ }
+
+ public BackendTypesystem getRootTypesystem() {
+ return _rootTypesystem;
+ }
+
+ public void setRootTypesystem(BackendTypesystem ts) {
+ _rootTypesystem = ts;
+ for (BackendTypesystem child : _inner)
+ child.setRootTypesystem(ts);
+
+ _javaBeansTypesystem.setRootTypesystem(ts);
+ }
+
+ private BackendType findSimpleBuiltinType(Class<?> cls) {
+ if (cls == null)
+ return ObjectType.INSTANCE; // convenience handling e.g. for
+ // interface types whose Java supertype
+ // is 'null'
+
+ if (List.class.isAssignableFrom(cls))
+ return ListType.INSTANCE;
+ if (Set.class.isAssignableFrom(cls))
+ return SetType.INSTANCE;
+ if (Collection.class.isAssignableFrom(cls))
+ return CollectionType.INSTANCE;
+
+ if (Map.class.isAssignableFrom(cls))
+ return MapType.INSTANCE;
+
+ if (CharSequence.class.isAssignableFrom(cls))
+ return StringType.INSTANCE;
+
+ if (cls == Boolean.class || cls == Boolean.TYPE)
+ return BooleanType.INSTANCE;
+
+ if (cls == Long.class || cls == Long.TYPE)
+ return LongType.INSTANCE;
+ if (cls == Double.class || cls == Double.TYPE)
+ return DoubleType.INSTANCE;
+ if (cls == Object.class || cls == ObjectType.class)
+ return ObjectType.INSTANCE;
+ if (Function.class.isAssignableFrom(cls))
+ return FunctionType.INSTANCE;
+
+ if (cls == Void.TYPE)
+ return VoidType.INSTANCE;
+
+ if (BackendType.class.isAssignableFrom(cls))
+ return TypeType.INSTANCE;
+ if (Property.class.isAssignableFrom(cls))
+ return PropertyType.INSTANCE;
+ if (StaticProperty.class.isAssignableFrom(cls))
+ return StaticPropertyType.INSTANCE;
+
+ return null;
+ }
}
-
-
diff --git a/tests/org.eclipse.xpand3.parser.tests/src/org/eclipse/xpand3/frontend/parser/node2ast/ParseStuff.java b/tests/org.eclipse.xpand3.parser.tests/src/org/eclipse/xpand3/frontend/parser/node2ast/ParseStuff.java
index 4ab1d3a..a231683 100644
--- a/tests/org.eclipse.xpand3.parser.tests/src/org/eclipse/xpand3/frontend/parser/node2ast/ParseStuff.java
+++ b/tests/org.eclipse.xpand3.parser.tests/src/org/eclipse/xpand3/frontend/parser/node2ast/ParseStuff.java
@@ -36,13 +36,6 @@ public class ParseStuff {
* @throws RecognitionException
*/
public static void main(String[] args) throws RecognitionException {
- // useNodeParser = false;
- // checkFor(1);
- // checkFor(10);
- // checkFor(100);
- // checkFor(1000);
- // checkFor(5000);
- // checkFor(50000);
useNodeParser = true;
checkFor(1);
checkFor(10);
@@ -50,6 +43,13 @@ public class ParseStuff {
checkFor(1000);
checkFor(5000);
checkFor(50000);
+ useNodeParser = false;
+ checkFor(1);
+ checkFor(10);
+ checkFor(100);
+ checkFor(1000);
+ checkFor(5000);
+ checkFor(50000);
}
diff --git a/tests/org.eclipse.xpand3.tests/META-INF/MANIFEST.MF b/tests/org.eclipse.xpand3.tests/META-INF/MANIFEST.MF
index d53e0f1..21773b0 100644
--- a/tests/org.eclipse.xpand3.tests/META-INF/MANIFEST.MF
+++ b/tests/org.eclipse.xpand3.tests/META-INF/MANIFEST.MF
@@ -8,4 +8,5 @@ Bundle-RequiredExecutionEnvironment: J2SE-1.5
Require-Bundle: org.junit,
org.eclipse.xpand3;bundle-version="0.9",
org.antlr.patched;bundle-version="3.0.0",
- org.eclipse.tmf.common.runtime;bundle-version="1.0.0"
+ org.eclipse.tmf.common.runtime;bundle-version="1.0.0",
+ org.eclipse.xpand3.common
diff --git a/tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/MiddleEndTest.java b/tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/MiddleEndTest.java
new file mode 100644
index 0000000..365e590
--- /dev/null
+++ b/tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/MiddleEndTest.java
@@ -0,0 +1,48 @@
+package org.eclipse.xpand3.middleend;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+
+import junit.framework.TestCase;
+
+import org.eclipse.xpand3.middlend.Xpand3MiddleEndFactory;
+import org.eclipse.xtend.backend.common.BackendType;
+import org.eclipse.xtend.backend.common.BackendTypesystem;
+import org.eclipse.xtend.backend.common.ExecutionContext;
+import org.eclipse.xtend.backend.common.Function;
+import org.eclipse.xtend.backend.common.FunctionDefContext;
+import org.eclipse.xtend.backend.types.CompositeTypesystem;
+import org.eclipse.xtend.middleend.MiddleEnd;
+import org.eclipse.xtend.middleend.MiddleEndFactory;
+import org.eclipse.xtend.middleend.plugins.LanguageSpecificMiddleEnd;
+import org.eclipse.xtend.middleend.plugins.LanguageSpecificMiddleEndFactory;
+
+public class MiddleEndTest extends TestCase {
+
+ public void testMiddleEnd() {
+ LanguageSpecificMiddleEndFactory xpand3MiddleEndFactory = new Xpand3MiddleEndFactory();
+ LanguageSpecificMiddleEnd xpand3MiddleEnd = xpand3MiddleEndFactory
+ .create(null);
+ BackendTypesystem backendTypesystem = new CompositeTypesystem();
+ ArrayList<LanguageSpecificMiddleEnd> langSpecMiddleEnds = new ArrayList<LanguageSpecificMiddleEnd>();
+ langSpecMiddleEnds.add(xpand3MiddleEnd);
+ MiddleEnd middleEnd = MiddleEndFactory.create(backendTypesystem,
+ langSpecMiddleEnds);
+
+ BackendType backendTypeObject = backendTypesystem.getRootTypesystem()
+ .findType("{builtin}Object");
+ assertNotNull(backendTypeObject);
+
+ FunctionDefContext functionDefContext = middleEnd
+ .getFunctions("org/eclipse/xpand3/middleend/test.ext");
+ ExecutionContext executionContext = middleEnd.getExecutionContext();
+ Function fooFunction = functionDefContext.getMatch(executionContext,
+ "foo", Arrays.asList(new BackendType[] { backendTypeObject,
+ backendTypeObject }));
+ assertNotNull(fooFunction);
+ Object result = fooFunction.invoke(executionContext, new Object[] {
+ "x", "y" });
+ assertNotNull(result);
+ assertFalse(((Boolean) result).booleanValue());
+ }
+}
diff --git a/tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/test.ext b/tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/test.ext
new file mode 100644
index 0000000..3c2b8db
--- /dev/null
+++ b/tests/org.eclipse.xpand3.tests/src/org/eclipse/xpand3/middleend/test.ext
@@ -0,0 +1,3 @@
+foo(Object this, Object that):
+ this.toString()==that.toString();
+ \ No newline at end of file