import java.util.ArrayList;
-import org.junit.runners.ParentRunner;
import org.simantics.scl.compiler.compilation.CompilationContext;
import org.simantics.scl.compiler.elaboration.chr.plan.CHRSearchPlan;
import org.simantics.scl.compiler.elaboration.chr.planning.QueryPlanningContext;
import gnu.trove.set.hash.TIntHashSet;
public class CHRRule extends Symbol {
+ public CHRRuleset parentRuleset;
public int priority;
public CHRQuery head;
public CHRQuery body;
}
public void compile(CompilationContext compilationContext, CHRConstraint initConstraint) {
- boolean hasActiveLiteral = false;
+ boolean hasLocalActiveLiteral = false;
for(int i=0;i<head.literals.length;++i) {
CHRLiteral literal = head.literals[i];
if(literal.passive)
body.createEnforcePlan(context, priority);
addPlan(new CHRSearchPlan(constraint, activeFact, context.getPlanOps()));
- hasActiveLiteral = true;
+ if(constraint.parentRuleset == parentRuleset)
+ hasLocalActiveLiteral = true;
}
- if(!hasActiveLiteral) {
+ if(!hasLocalActiveLiteral) {
Variable activeFact = new Variable("activeFact", initConstraint.factType);
QueryPlanningContext context = new QueryPlanningContext(compilationContext, existentialVariables);
if(!head.createQueryPlan(context, null, -1))
import org.simantics.scl.compiler.constants.NoRepConstant;
import org.simantics.scl.compiler.constants.generic.CallJava;
import org.simantics.scl.compiler.constants.generic.MethodRef.FieldRef;
+import org.simantics.scl.compiler.constants.generic.MethodRef.ObjectMethodRef;
import org.simantics.scl.compiler.constants.generic.MethodRef.SetFieldRef;
import org.simantics.scl.compiler.elaboration.chr.analysis.CHRConstraintGGInfo;
import org.simantics.scl.compiler.elaboration.chr.analysis.UsageAnalysis;
import org.simantics.scl.compiler.internal.codegen.references.IVal;
import org.simantics.scl.compiler.internal.codegen.ssa.SSAFunction;
import org.simantics.scl.compiler.internal.codegen.types.StandardTypeConstructor;
+import org.simantics.scl.compiler.internal.codegen.utils.Constants;
import org.simantics.scl.compiler.internal.codegen.writer.CodeWriter;
import org.simantics.scl.compiler.internal.parsing.Symbol;
import org.simantics.scl.compiler.types.TCon;
import org.simantics.scl.compiler.types.TVar;
import org.simantics.scl.compiler.types.Type;
import org.simantics.scl.compiler.types.Types;
-import org.simantics.scl.runtime.chr.CHRContext;
import gnu.trove.map.hash.THashMap;
import gnu.trove.map.hash.TObjectIntHashMap;
public TCon runtimeRulesetType;
public BoundVar runtimeRulesetVariable;
public TypeDesc runtimeRulesetTypeDesc;
- public Constant readCurrentId;
- public Constant writeCurrentId;
+
+ public static final Constant READ_CURRENT_ID = new CallJava(TVar.EMPTY_ARRAY, Types.PROC, Types.INTEGER, new Type[] {Types.CHRContext},
+ null, new FieldRef(CHRCodeGenerationConstants.CHRContext_name, "currentId", CHRRuntimeRulesetCodeGenerator.FACT_ID_TYPE), null);
+ public static final Constant WRITE_CURRENT_ID = new CallJava(TVar.EMPTY_ARRAY, Types.PROC, Types.UNIT, new Type[] {Types.CHRContext, Types.INTEGER},
+ null, new SetFieldRef(CHRCodeGenerationConstants.CHRContext_name, "currentId", CHRRuntimeRulesetCodeGenerator.FACT_ID_TYPE), null);
+ public static final Constant GENERATE_ID = new CallJava(TVar.EMPTY_ARRAY, Types.PROC, Types.INTEGER, new Type[] {Types.CHRContext},
+ null, new ObjectMethodRef(false, CHRCodeGenerationConstants.CHRContext_name, "generateId", CHRRuntimeRulesetCodeGenerator.FACT_ID_TYPE, Constants.EMPTY_TYPEDESC_ARRAY), null);
// FIXME remove and change the parameter of Expression.toVal
private CompilationContext cachedContext;
runtimeRulesetVariable = new BoundVar(runtimeRulesetType);
for(CHRConstraint constraint : constraints)
constraint.initializeCodeGeneration(context, this);
- readCurrentId = new CallJava(TVar.EMPTY_ARRAY, Types.PROC, Types.INTEGER, new Type[] {Types.CHRContext},
- null, new FieldRef(CHRCodeGenerationConstants.CHRContext_name, "currentId", CHRRuntimeRulesetCodeGenerator.FACT_ID_TYPE), null);
- writeCurrentId = new CallJava(TVar.EMPTY_ARRAY, Types.PROC, Types.UNIT, new Type[] {Types.CHRContext, Types.INTEGER},
- null, new SetFieldRef(CHRCodeGenerationConstants.CHRContext_name, "currentId", CHRRuntimeRulesetCodeGenerator.FACT_ID_TYPE), null);
if(createTypeDesc && context.module != null) // for unit testing
context.module.addTypeDescriptor(runtimeRulesetType.name, new StandardTypeConstructor(runtimeRulesetType, TVar.EMPTY_ARRAY, runtimeRulesetTypeDesc));
}
new JavaMethod(true, runtimeRulesetClassName, "initialize", Types.PROC, Types.UNIT, new Type[] {runtimeRulesetType, Types.CHRContext}),
object.getTarget(), chrContext);
}
- IVal initFact = w.apply(location, initConstraint.constructor, IntegerConstant.ZERO);
+ IVal initFact = w.apply(location, initConstraint.constructor, w.apply(location, GENERATE_ID, chrContext));
w.apply(location, initConstraint.addProcedure, runtimeRulesetVariable, chrContext, initFact);
w.apply(location, ACTIVATE, chrContext, new IntegerConstant(Integer.MAX_VALUE));
if(deinitializer != null) {
literal.collectEnforceEffects(effects);
}
}
+
+ public void addRule(CHRRule rule) {
+ rules.add(rule);
+ rule.parentRuleset = this;
+ }
}
public IVal generateNewId(long location, CodeWriter w) {
if(currentId == null)
- currentId = w.apply(location, ruleset.readCurrentId, contextVar);
+ currentId = w.apply(location, CHRRuleset.READ_CURRENT_ID, contextVar);
IVal result = currentId;
currentId = w.apply(location, IncreaseByOne.INSTANCE, currentId);
return result;
@Override
public void generateCode(CompilationContext context, PlanContext planContext, CodeWriter w) {
if(planContext.currentId != null) {
- w.apply(location, planContext.ruleset.writeCurrentId, planContext.contextVar, planContext.currentId);
+ w.apply(location, CHRRuleset.WRITE_CURRENT_ID, planContext.contextVar, planContext.currentId);
planContext.currentId = null;
w.apply(location, CHRRuleset.ACTIVATE, planContext.contextVar, new IntegerConstant(priority+planContext.ruleset.initialPriorityNumber));
}
for(int i=begin;i<end;++i) {
Statement statement = statements.get(i);
if(statement instanceof CHRStatement)
- ruleset.rules.add(CHRTranslation.convertCHRStatement(context, (CHRStatement)statement));
+ ruleset.addRule(CHRTranslation.convertCHRStatement(context, (CHRStatement)statement));
else if(statement instanceof ConstraintStatement)
ruleset.constraints.add(CHRTranslation.convertConstraintStatement(context, (ConstraintStatement)statement));
else if(statement instanceof IncludeStatement)
public class ModuleCompilationOptions {
public static final ModuleCompilationOptions STANDARD_OPTIONS = new ModuleCompilationOptions(false);
+ public static final ModuleCompilationOptions SILENT = new ModuleCompilationOptions(false);
- public final boolean computeCoverage;
+ static {
+ SILENT.silent = true;
+ }
+
+ public boolean computeCoverage;
+ public boolean silent = false;
public ModuleCompilationOptions(boolean computeCoverage) {
this.computeCoverage = computeCoverage;
package org.simantics.scl.compiler.module.options;
+@FunctionalInterface
public interface ModuleCompilationOptionsAdvisor {
ModuleCompilationOptions getOptions(String moduleName);
}
if(compiler.getErrorLog().hasNoErrors())
return new Success<Module>(compiler.getModule());
else {
- LOGGER.error("While compiling " + getModuleName() + ":");
- LOGGER.error(CompilationErrorFormatter.toString(getSourceReader(null), compiler.getErrorLog().getErrors()));
+ if(!options.silent)
+ LOGGER.error("While compiling " + getModuleName() + ":\n " +
+ CompilationErrorFormatter.toString(getSourceReader(null), compiler.getErrorLog().getErrors()).replaceAll("\n", "\n "));
return new Failure(compiler.getErrorLog().getErrors());
}
} catch (IOException e) {
+ if(!options.silent)
+ LOGGER.error("Compilation of module " + moduleName + " failed.", e);
return new Failure(e);
}
}
public class CHRContext {
public CHRPriority topPriority;
- public int currentId = 1;
+ public int currentId = 0;
public void activate(int maxPriority) {
//System.out.println("--- ACTIVATE " + maxPriority + "---------------------------------------------");
}
//System.out.println("--- FINISHED " + maxPriority + "---------------------------------------------");
}
+
+ public int generateId() {
+ return currentId++;
+ }
}
--- /dev/null
+package org.simantics.scl.runtime.reporting;
+
+import java.io.IOException;
+import java.io.Writer;
+
+public class WriterSCLReportingHandler extends AbstractSCLReportingHandler {
+ private final Writer writer;
+
+ public WriterSCLReportingHandler(Writer writer) {
+ this.writer = writer;
+ }
+
+ @Override
+ public void print(String text) {
+ try {
+ writer.write(text);
+ writer.write('\n');
+ } catch(IOException e) {
+ e.printStackTrace();
+ }
+ }
+}
import java.io.IOException;
import java.io.InputStream;
+import java.io.StringWriter;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.Arrays;
import org.simantics.scl.compiler.errors.Failure;
import org.simantics.scl.compiler.module.ImportDeclaration;
import org.simantics.scl.compiler.module.Module;
+import org.simantics.scl.compiler.module.options.ModuleCompilationOptions;
import org.simantics.scl.compiler.module.repository.ModuleRepository;
import org.simantics.scl.compiler.module.repository.UpdateListener;
import org.simantics.scl.compiler.source.ModuleSource;
import org.simantics.scl.compiler.source.StringModuleSource;
import org.simantics.scl.compiler.source.repository.MapModuleSourceRepository;
import org.simantics.scl.compiler.top.ValueNotFound;
+import org.simantics.scl.runtime.SCLContext;
+import org.simantics.scl.runtime.reporting.SCLReportingHandler;
+import org.simantics.scl.runtime.reporting.WriterSCLReportingHandler;
public class TestBase {
return ImportDeclaration.ONLY_BUILTINS;
}
};
- ModuleRepository testEnvironment = new ModuleRepository(
+ ModuleRepository testRepository = new ModuleRepository(
PRELUDE_MODULE_REPOSITORY,
new MapModuleSourceRepository(moduleSources));
+ testRepository.setAdvisor(moduleName -> ModuleCompilationOptions.SILENT);
int lastId = moduleNames.length-1;
- Failable<Module> result = testEnvironment.getModule(moduleNames[lastId]);
+ Failable<Module> result = testRepository.getModule(moduleNames[lastId]);
if(!result.didSucceed())
return ((Failure)result).toString(moduleTexts[lastId]);
else {
- Object main = testEnvironment.getRuntimeModule(moduleNames[lastId]).getResult().getValue("main");
- return String.valueOf(main);
+ SCLContext context = SCLContext.getCurrent();
+ StringWriter writer = new StringWriter();
+ Object oldReportingHandler = context.put(SCLReportingHandler.REPORTING_HANDLER, new WriterSCLReportingHandler(writer));
+ try {
+ Object main = testRepository.getRuntimeModule(moduleNames[lastId]).getResult().getValue("main");
+ writer.write(String.valueOf(main));
+ return writer.toString();
+ } finally {
+ context.put(SCLReportingHandler.REPORTING_HANDLER, oldReportingHandler);
+ }
}
}
Edge ?x ?y => MList.add answer (?x, ?y)
--
+Remove loop (5,5)
+Remove dangling edge (3,5)
+Remove node 5
+Simplify path (1,2,3)
+Simplify path (1,3,4)
[(1,4), (1,4)]
--
import "StandardLibrary"
A ?x, not A (?x+1) => A (?x-1)
True => A 0
--
-()
-
-
+0
+()
\ No newline at end of file
addSet set 1
printSet set
--
-()
+added 1
+added 2
+added 1
+removed duplicate 1
+printing 2
+printing 1
+()
\ No newline at end of file
True => X 2
True => X 1
--
-()
+A 1
+B 1
+A 2
+B 2
+()
\ No newline at end of file
x := True
print (evalV f)
--
+("x" `UntilF` "y")
+false
+false
+("x" `UntilF` "y")
()
\ No newline at end of file
Fib 0 1
Fib 1 1
--
-()
+21 -> 11
+20 -> 11
+19 -> 10
+18 -> 10
+17 -> 9
+16 -> 9
+15 -> 8
+14 -> 8
+13 -> 7
+12 -> 7
+11 -> 6
+10 -> 6
+9 -> 5
+8 -> 5
+7 -> 4
+6 -> 4
+5 -> 3
+4 -> 3
+3 -> 2
+2 -> 2
+1 -> 1
+0 -> 1
+()
\ No newline at end of file
main = transformation OneShotForward where
--
-()
+20 -> 10946
+19 -> 6765
+18 -> 4181
+17 -> 2584
+16 -> 1597
+15 -> 987
+14 -> 610
+13 -> 377
+12 -> 233
+11 -> 144
+10 -> 89
+9 -> 55
+8 -> 34
+7 -> 21
+6 -> 13
+5 -> 8
+4 -> 5
+3 -> 3
+2 -> 2
+1 -> 1
+0 -> 1
+()
\ No newline at end of file
main = transformation OneShotForward where
--
-()
+11 -> 2, 1
+10 -> 1, 2
+9 -> 2, 1
+8 -> 1, 2
+7 -> 2, 1
+6 -> 1, 2
+5 -> 2, 1
+4 -> 1, 2
+3 -> 2, 1
+2 -> 1, 2
+1 -> 2, 1
+0 -> 1, 2
+()
\ No newline at end of file
main = transformation OneShotForward where
--
-()
+Hello world!
+()
\ No newline at end of file
main = transformation OneShotForward where
--
-()
+A
+B
+C
+()
\ No newline at end of file