1 package org.simantics.scl.compiler.elaboration.query;
3 import java.util.Arrays;
5 import org.simantics.scl.compiler.elaboration.contexts.TranslationContext;
6 import org.simantics.scl.compiler.elaboration.contexts.TypingContext;
7 import org.simantics.scl.compiler.elaboration.expressions.EApply;
8 import org.simantics.scl.compiler.elaboration.expressions.EVar;
9 import org.simantics.scl.compiler.elaboration.expressions.Expression;
10 import org.simantics.scl.compiler.elaboration.expressions.Variable;
11 import org.simantics.scl.compiler.elaboration.query.pre.QPreExists;
12 import org.simantics.scl.compiler.elaboration.query.pre.QPreGuard;
13 import org.simantics.scl.compiler.errors.Locations;
15 import gnu.trove.map.hash.TObjectIntHashMap;
16 import gnu.trove.set.hash.TIntHashSet;
18 public abstract class QAbstractCombiner extends Query {
19 public Query[] queries;
21 public QAbstractCombiner(Query[] queries) {
22 this.queries = queries;
26 public Query resolve(TranslationContext context) {
27 Query modifiedQuery = handleExistsStatement(context);
28 if(modifiedQuery != null)
29 return modifiedQuery.resolve(context);
31 for(int i=0;i<queries.length;++i)
32 queries[i] = queries[i].resolve(context);
36 private QPreExists handleExistsStatement(TranslationContext context) {
37 if(queries.length == 0)
39 if(!(queries[0] instanceof QPreGuard))
41 Expression exp = ((QPreGuard)queries[0]).guard;
42 if(!(exp instanceof EApply))
44 EApply apply = (EApply)exp;
45 if(!(apply.getFunction() instanceof EVar))
47 if(!((EVar)apply.getFunction()).name.equals("exists"))
50 queries = Arrays.copyOfRange(queries, 1, queries.length);
52 Expression[] pars = apply.getParameters();
53 String[] variableNames = new String[pars.length];
54 for(int i=0;i<pars.length;++i) {
55 if(pars[i] instanceof EVar)
56 variableNames[i] = ((EVar)pars[i]).name;
58 context.getErrorLog().log(pars[i].getLocation(), "Exists statement may only contain variables as parameters.");
62 return new QPreExists(variableNames, this);
66 public void checkType(TypingContext context) {
67 for(Query query : queries)
68 query.checkType(context);
72 public void collectVars(TObjectIntHashMap<Variable> allVars, TIntHashSet vars) {
73 for(Query query : queries)
74 query.collectVars(allVars, vars);
78 public void setLocationDeep(long loc) {
79 if(location == Locations.NO_LOCATION) {
81 for(Query query : queries)
82 query.setLocationDeep(loc);