diff options
10 files changed, 91 insertions, 4 deletions
diff --git a/plugins/org.eclipse.qvtd.codegen/src/org/eclipse/qvtd/codegen/qvti/analyzer/QVTiCGCachingAnalysis.java b/plugins/org.eclipse.qvtd.codegen/src/org/eclipse/qvtd/codegen/qvti/analyzer/QVTiCGCachingAnalysis.java new file mode 100644 index 000000000..490799ecf --- /dev/null +++ b/plugins/org.eclipse.qvtd.codegen/src/org/eclipse/qvtd/codegen/qvti/analyzer/QVTiCGCachingAnalysis.java @@ -0,0 +1,41 @@ +/******************************************************************************* + * Copyright (c) 2017 Willink Transformations 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: + * E.D.Willink - initial API and implementation + *******************************************************************************/ +package org.eclipse.qvtd.codegen.qvti.analyzer; + +import org.eclipse.jdt.annotation.NonNull; +import org.eclipse.ocl.examples.codegen.analyzer.CGCachingAnalysis; +import org.eclipse.ocl.examples.codegen.cgmodel.CGConstraint; +import org.eclipse.ocl.examples.codegen.cgmodel.CGOperation; +import org.eclipse.ocl.examples.codegen.cgmodel.CGPackage; +import org.eclipse.ocl.pivot.utilities.TreeIterable; +import org.eclipse.qvtd.codegen.qvticgmodel.CGMapping; + +public class QVTiCGCachingAnalysis extends CGCachingAnalysis +{ + public QVTiCGCachingAnalysis(@NonNull CGPackage cgPackage) { + super(cgPackage); + } + + @Override + public void analyze() { + for (@NonNull Object object : new TreeIterable(cgPackage, true)) { + if (object instanceof CGConstraint) { + analyzeElement((CGConstraint)object); + } + else if (object instanceof CGMapping) { + analyzeElement((CGMapping)object); + } + else if (object instanceof CGOperation) { + analyzeElement((CGOperation)object); + } + } + } +}
\ No newline at end of file diff --git a/plugins/org.eclipse.qvtd.codegen/src/org/eclipse/qvtd/codegen/qvti/java/QVTiCodeGenerator.java b/plugins/org.eclipse.qvtd.codegen/src/org/eclipse/qvtd/codegen/qvti/java/QVTiCodeGenerator.java index c8b73784b..d884c4d1b 100644 --- a/plugins/org.eclipse.qvtd.codegen/src/org/eclipse/qvtd/codegen/qvti/java/QVTiCodeGenerator.java +++ b/plugins/org.eclipse.qvtd.codegen/src/org/eclipse/qvtd/codegen/qvti/java/QVTiCodeGenerator.java @@ -23,6 +23,7 @@ import org.eclipse.jdt.annotation.NonNull; import org.eclipse.jdt.annotation.Nullable; import org.eclipse.ocl.examples.codegen.analyzer.AnalysisVisitor; import org.eclipse.ocl.examples.codegen.analyzer.BoxingAnalyzer; +import org.eclipse.ocl.examples.codegen.analyzer.CGCachingAnalysis; import org.eclipse.ocl.examples.codegen.analyzer.DependencyVisitor; import org.eclipse.ocl.examples.codegen.analyzer.FieldingAnalyzer; import org.eclipse.ocl.examples.codegen.analyzer.NameManager; @@ -43,6 +44,7 @@ import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiAnalysisVisitor; import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiAnalyzer; import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiBoxingAnalyzer; import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiCG2StringVisitor; +import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiCGCachingAnalysis; import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiDependencyVisitor; import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiFieldingAnalyzer; import org.eclipse.qvtd.codegen.qvti.analyzer.QVTiReferencesVisitor; @@ -97,6 +99,11 @@ public class QVTiCodeGenerator extends JavaCodeGenerator return new QVTiCG2JavaVisitor(this, cgPackage, sortedGlobals); } + @Override + protected @NonNull CGCachingAnalysis createCGCachingAnalysis(@NonNull CGPackage cgPackage) { + return new QVTiCGCachingAnalysis(cgPackage); + } + protected @NonNull CGPackage createCGPackage() { QVTiAS2CGVisitor pivot2CGVisitor = createAS2CGVisitor(cgAnalyzer, getGlobalContext()); CGTransformation cgTransformation = (CGTransformation) ClassUtil.nonNullState(transformation.accept(pivot2CGVisitor)); diff --git a/plugins/org.eclipse.qvtd.compiler/src/org/eclipse/qvtd/compiler/internal/qvts2qvti/QVTs2QVTi.java b/plugins/org.eclipse.qvtd.compiler/src/org/eclipse/qvtd/compiler/internal/qvts2qvti/QVTs2QVTi.java index c6046991c..bf660f7f0 100644 --- a/plugins/org.eclipse.qvtd.compiler/src/org/eclipse/qvtd/compiler/internal/qvts2qvti/QVTs2QVTi.java +++ b/plugins/org.eclipse.qvtd.compiler/src/org/eclipse/qvtd/compiler/internal/qvts2qvti/QVTs2QVTi.java @@ -41,6 +41,7 @@ import org.eclipse.qvtd.pivot.qvtbase.utilities.QVTbaseEnvironmentFactory; import org.eclipse.qvtd.pivot.qvtimperative.ImperativeModel; import org.eclipse.qvtd.pivot.qvtimperative.ImperativeTypedModel; import org.eclipse.qvtd.pivot.qvtimperative.QVTimperativePackage; +import org.eclipse.qvtd.pivot.qvtimperative.evaluation.QVTiCachingAnalysis; import org.eclipse.qvtd.pivot.qvtimperative.utilities.QVTimperativeHelper; import org.eclipse.qvtd.pivot.qvtschedule.ScheduledRegion; import org.eclipse.qvtd.pivot.qvtschedule.utilities.SymbolNameReservation; @@ -137,6 +138,7 @@ public class QVTs2QVTi extends QVTimperativeHelper Transformation transformation = scheduleManager.getTransformation(); QVTs2QVTiVisitor visitor = new QVTs2QVTiVisitor(problemHandler, this, transformation, symbolNameReservation); Transformation qvtiTransformation = (Transformation)scheduledRegion.accept(visitor); + assert qvtiTransformation != null; NamedElement qvtiChild = qvtiTransformation; for (org.eclipse.ocl.pivot.Package qvtmPackage = transformation.getOwningPackage(); qvtmPackage != null; qvtmPackage = qvtmPackage.getOwningPackage()) { org.eclipse.ocl.pivot.@NonNull Package qvtiPackage = createPackage(ClassUtil.nonNull(qvtmPackage.getName()), qvtmPackage.getNsPrefix(), qvtmPackage.getURI()); @@ -149,6 +151,7 @@ public class QVTs2QVTi extends QVTimperativeHelper qvtiChild = qvtiPackage; } model.getOwnedPackages().add((org.eclipse.ocl.pivot.Package)qvtiChild); + QVTiCachingAnalysis.analyze(qvtiTransformation); } public @NonNull Model transform(@NonNull ScheduledRegion scheduledRegion) { diff --git a/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/BasicQVTiExecutor.java b/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/BasicQVTiExecutor.java index a3c35d625..c15a3ef4a 100644 --- a/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/BasicQVTiExecutor.java +++ b/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/BasicQVTiExecutor.java @@ -40,6 +40,7 @@ import org.eclipse.ocl.pivot.evaluation.EvaluationEnvironment; import org.eclipse.ocl.pivot.evaluation.EvaluationVisitor; import org.eclipse.ocl.pivot.internal.complete.StandardLibraryInternal; import org.eclipse.ocl.pivot.internal.evaluation.AbstractExecutor; +import org.eclipse.ocl.pivot.internal.evaluation.CachingAnalysis; import org.eclipse.ocl.pivot.internal.messages.PivotMessagesInternal; import org.eclipse.ocl.pivot.labels.ILabelGenerator; import org.eclipse.ocl.pivot.utilities.ClassUtil; @@ -350,6 +351,9 @@ public abstract class BasicQVTiExecutor extends AbstractExecutor implements QVTi OCLExpression ownedExpression = newStatement.getOwnedExpression(); if (ownedExpression != null) { Object initValue = ownedExpression.accept(undecoratedVisitor); + if (newStatement.isCacheNeeded()) { + CachingAnalysis.initCaching(newStatement, initValue); + } getEvaluationEnvironment().add(newStatement, initValue); replace(newStatement, initValue); ImperativeTypedModel typedModel = newStatement.getReferredTypedModel(); diff --git a/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/QVTiCachingAnalysis.java b/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/QVTiCachingAnalysis.java new file mode 100644 index 000000000..fe8f1d2e3 --- /dev/null +++ b/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/QVTiCachingAnalysis.java @@ -0,0 +1,25 @@ +package org.eclipse.qvtd.pivot.qvtimperative.evaluation; + +import org.eclipse.jdt.annotation.NonNull; +import org.eclipse.ocl.pivot.Element; +import org.eclipse.ocl.pivot.internal.evaluation.CachingAnalysis; +import org.eclipse.qvtd.pivot.qvtbase.Rule; +import org.eclipse.qvtd.pivot.qvtbase.Transformation; +import org.eclipse.qvtd.pivot.qvtbase.utilities.QVTbaseUtil; + +/** + * The CachingAnalysis sets VariableDeclaration.cacheNeeded for colletion variables that are accessed more than once. + */ +public class QVTiCachingAnalysis extends CachingAnalysis +{ + public static void analyze(@NonNull Transformation qvtiTransformation) { + for (@NonNull Rule rule : QVTbaseUtil.getRule(qvtiTransformation)) { + QVTiCachingAnalysis cachingAnalysis = new QVTiCachingAnalysis(rule); + cachingAnalysis.analyze(); + } + } + + protected QVTiCachingAnalysis(@NonNull Element rootElement) { + super(rootElement); + } +}
\ No newline at end of file diff --git a/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/QVTiEvaluationVisitor.java b/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/QVTiEvaluationVisitor.java index e84bc076a..d86c5a288 100644 --- a/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/QVTiEvaluationVisitor.java +++ b/plugins/org.eclipse.qvtd.pivot.qvtimperative/src/org/eclipse/qvtd/pivot/qvtimperative/evaluation/QVTiEvaluationVisitor.java @@ -23,6 +23,7 @@ import org.eclipse.ocl.pivot.Type; import org.eclipse.ocl.pivot.VariableDeclaration; import org.eclipse.ocl.pivot.ids.CollectionTypeId; import org.eclipse.ocl.pivot.internal.evaluation.BasicEvaluationVisitor; +import org.eclipse.ocl.pivot.internal.evaluation.CachingAnalysis; import org.eclipse.ocl.pivot.utilities.ClassUtil; import org.eclipse.ocl.pivot.utilities.NameUtil; import org.eclipse.ocl.pivot.utilities.PivotUtil; @@ -301,6 +302,9 @@ public class QVTiEvaluationVisitor extends BasicEvaluationVisitor implements IQV assert name != null; if (ownedExpression != null) { Object initValue = ownedExpression.accept(undecoratedVisitor); + if (object.isCacheNeeded()) { + CachingAnalysis.initCaching(object, initValue); + } connection = interval.createConnection(name, ownedExpression.getTypeId(), object.isIsStrict()); if (initValue != null) { for (Object value : (Iterable<?>)initValue) { @@ -338,6 +342,9 @@ public class QVTiEvaluationVisitor extends BasicEvaluationVisitor implements IQV } else { initValue = ownedExpression.accept(undecoratedVisitor); + if (asStatement.isCacheNeeded()) { + CachingAnalysis.initCaching(asStatement, initValue); + } if (asStatement.isIsCheck()) { Type guardType = asStatement.getType(); Type valueType = idResolver.getDynamicTypeOf(initValue); diff --git a/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfKindOperation.java b/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfKindOperation.java index e96f637af..ac30f84ec 100644 --- a/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfKindOperation.java +++ b/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfKindOperation.java @@ -40,6 +40,6 @@ public class ModelObjectsOfKindOperation extends AbstractBinaryOperation } TypedModelInstance typedModelInstance = (TypedModelInstance)sourceVal; Iterable<@NonNull ? extends Object> results = typedModelInstance.getObjectsOfKind(type); - return createCollectionValue((CollectionTypeId)returnTypeId, true, (Collection<@Nullable ? extends Object>) results); + return createCollectionOfAll((CollectionTypeId)returnTypeId, true, (Collection<@Nullable ? extends Object>) results); } } diff --git a/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfTypeOperation.java b/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfTypeOperation.java index 4b1c636ea..fee78efb9 100644 --- a/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfTypeOperation.java +++ b/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/ModelObjectsOfTypeOperation.java @@ -40,6 +40,6 @@ public class ModelObjectsOfTypeOperation extends AbstractBinaryOperation } TypedModelInstance typedModelInstance = (TypedModelInstance)sourceVal; Iterable<@NonNull ? extends Object> results = typedModelInstance.getObjectsOfType(type); - return createCollectionValue((CollectionTypeId)returnTypeId, true, (Collection<@Nullable ? extends Object>) results); + return createCollectionOfAll((CollectionTypeId)returnTypeId, true, (Collection<@Nullable ? extends Object>) results); } } diff --git a/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/RootObjectsOperation.java b/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/RootObjectsOperation.java index 5ec3dca5c..0bcd98af7 100644 --- a/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/RootObjectsOperation.java +++ b/plugins/org.eclipse.qvtd.runtime/src/org/eclipse/qvtd/runtime/library/model/RootObjectsOperation.java @@ -39,6 +39,6 @@ public class RootObjectsOperation extends AbstractUnaryOperation } TypedModelInstance typedModelInstance = (TypedModelInstance)sourceVal; Iterable<@NonNull ? extends Object> results = typedModelInstance.getRootObjects(); - return createCollectionValue((CollectionTypeId)returnTypeId, true, (Collection<@Nullable ? extends Object>) results); + return createCollectionOfAll((CollectionTypeId)returnTypeId, true, (Collection<@Nullable ? extends Object>) results); } } diff --git a/tests/org.eclipse.qvtd.xtext.qvtimperative.tests/src/org/eclipse/qvtd/xtext/qvtimperative/tests/QVTiInterpreterTests.java b/tests/org.eclipse.qvtd.xtext.qvtimperative.tests/src/org/eclipse/qvtd/xtext/qvtimperative/tests/QVTiInterpreterTests.java index 06a3d1da2..1f20e8d54 100644 --- a/tests/org.eclipse.qvtd.xtext.qvtimperative.tests/src/org/eclipse/qvtd/xtext/qvtimperative/tests/QVTiInterpreterTests.java +++ b/tests/org.eclipse.qvtd.xtext.qvtimperative.tests/src/org/eclipse/qvtd/xtext/qvtimperative/tests/QVTiInterpreterTests.java @@ -416,7 +416,7 @@ public class QVTiInterpreterTests extends LoadTestCase TestUtil.doCompleteOCLSetup(); URI oclURI = ClassUtil.nonNullState(URI.createPlatformResourceURI("/org.eclipse.qvtd.pivot.qvtimperative/model/QVTimperative.ocl", true)); QVTiEnvironmentFactory environmentFactory = myQVT.getEnvironmentFactory(); - environmentFactory.setEvaluationTracingEnabled(true); + // environmentFactory.setEvaluationTracingEnabled(true); // CompleteOCLEObjectValidator completeOCLEObjectValidator1 = new CompleteOCLEObjectValidator(QVTimperativePackage.eINSTANCE, oclURI, metaModelManager); @SuppressWarnings("unused") CompleteOCLEObjectValidator completeOCLEObjectValidator2 = new CompleteOCLEObjectValidator(ClassUtil.nonNullState(QVTimperativePackage.eINSTANCE), oclURI, environmentFactory); |