Package: Exp2StmTrans

Exp2StmTrans

nameinstructionbranchcomplexitylinemethod
Exp2StmTrans(IterationVarPrefixes, TransAssistantIR, CounterData, ILanguageIterator, Exp2StmVarPrefixes)
M: 0 C: 24
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 8
100%
M: 0 C: 1
100%
assignToVar(AIdentifierVarExpIR, SExpIR)
M: 0 C: 14
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 4
100%
M: 0 C: 1
100%
caseAAndBoolBinaryExpIR(AAndBoolBinaryExpIR)
M: 0 C: 33
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 7
100%
M: 0 C: 1
100%
caseACasesExpIR(ACasesExpIR)
M: 0 C: 145
100%
M: 0 C: 4
100%
M: 0 C: 3
100%
M: 0 C: 30
100%
M: 0 C: 1
100%
caseACompMapExpIR(ACompMapExpIR)
M: 0 C: 78
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 17
100%
M: 0 C: 1
100%
caseACompSeqExpIR(ACompSeqExpIR)
M: 0 C: 102
100%
M: 0 C: 4
100%
M: 0 C: 3
100%
M: 0 C: 20
100%
M: 0 C: 1
100%
caseACompSetExpIR(ACompSetExpIR)
M: 0 C: 78
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 17
100%
M: 0 C: 1
100%
caseAExists1QuantifierExpIR(AExists1QuantifierExpIR)
M: 0 C: 103
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 22
100%
M: 0 C: 1
100%
caseAExistsQuantifierExpIR(AExistsQuantifierExpIR)
M: 0 C: 90
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 18
100%
M: 0 C: 1
100%
caseAForAllQuantifierExpIR(AForAllQuantifierExpIR)
M: 0 C: 90
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 18
100%
M: 0 C: 1
100%
caseAIotaExpIR(AIotaExpIR)
M: 10 C: 79
89%
M: 1 C: 1
50%
M: 1 C: 1
50%
M: 1 C: 16
94%
M: 0 C: 1
100%
caseALetBeStExpIR(ALetBeStExpIR)
M: 20 C: 176
90%
M: 1 C: 5
83%
M: 1 C: 3
75%
M: 3 C: 35
92%
M: 0 C: 1
100%
caseALetDefExpIR(ALetDefExpIR)
M: 0 C: 75
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 17
100%
M: 0 C: 1
100%
caseAOrBoolBinaryExpIR(AOrBoolBinaryExpIR)
M: 3 C: 30
91%
M: 1 C: 1
50%
M: 1 C: 1
50%
M: 1 C: 6
86%
M: 0 C: 1
100%
caseARecordModExpIR(ARecordModExpIR)
M: 0 C: 173
100%
M: 0 C: 6
100%
M: 0 C: 4
100%
M: 0 C: 30
100%
M: 0 C: 1
100%
caseATernaryIfExpIR(ATernaryIfExpIR)
M: 0 C: 137
100%
M: 0 C: 2
100%
M: 0 C: 2
100%
M: 0 C: 31
100%
M: 0 C: 1
100%
consAndExpCheck(AAndBoolBinaryExpIR, String)
M: 0 C: 50
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 12
100%
M: 0 C: 1
100%
consExists1QuantifierStrategy(SExpIR, ITempVarGen, String)
M: 0 C: 15
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
consIotaStrategy(SExpIR, ITempVarGen, String, String, SExpIR)
M: 0 C: 16
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
consLetBeStStrategy(SExpIR, STypeIR, ITempVarGen)
M: 0 C: 13
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
consMapCompStrategy(AMapletExpIR, SExpIR, STypeIR, ITempVarGen, String)
M: 0 C: 15
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
consOrExpCheck(AOrBoolBinaryExpIR, String)
M: 0 C: 57
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 13
100%
M: 0 C: 1
100%
consOrdinaryQuantifierStrategy(SExpIR, ITempVarGen, String, TransAssistantIR, OrdinaryQuantifier, ILanguageIterator, IterationVarPrefixes)
M: 0 C: 11
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
consSeqCompStrategy(SExpIR, SExpIR, STypeIR, ITempVarGen, String)
M: 0 C: 15
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
consSetCompStrategy(SExpIR, SExpIR, STypeIR, ITempVarGen, String)
M: 0 C: 15
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
M: 0 C: 1
100%
filterBindList(INode, List)
M: 18 C: 25
58%
M: 1 C: 3
75%
M: 1 C: 2
67%
M: 2 C: 6
75%
M: 0 C: 1
100%
getCol(SMultipleBindIR)
M: 2 C: 14
88%
M: 1 C: 3
75%
M: 1 C: 2
67%
M: 1 C: 4
80%
M: 0 C: 1
100%
handleLogicExp(SBoolBinaryExpIR, SStmIR, SStmIR, String)
M: 0 C: 52
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 11
100%
M: 0 C: 1
100%
replaceCompWithTransformation(SStmIR, ABlockStmIR, STypeIR, String, SExpIR)
M: 0 C: 26
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 7
100%
M: 0 C: 1
100%
transform(SStmIR, ABlockStmIR, SExpIR, SExpIR)
M: 0 C: 16
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 4
100%
M: 0 C: 1
100%
transformBoolBinaryExp(SBoolBinaryExpIR, SStmIR)
M: 0 C: 13
100%
M: 0 C: 4
100%
M: 0 C: 3
100%
M: 0 C: 2
100%
M: 0 C: 1
100%
visitBoolBinary(SBoolBinaryExpIR)
M: 0 C: 13
100%
M: 0 C: 0
100%
M: 0 C: 1
100%
M: 0 C: 4
100%
M: 0 C: 1
100%

Coverage

1: /*
2: * #%~
3: * VDM Code Generator
4: * %%
5: * Copyright (C) 2008 - 2014 Overture
6: * %%
7: * This program is free software: you can redistribute it and/or modify
8: * it under the terms of the GNU General Public License as
9: * published by the Free Software Foundation, either version 3 of the
10: * License, or (at your option) any later version.
11: *
12: * This program is distributed in the hope that it will be useful,
13: * but WITHOUT ANY WARRANTY; without even the implied warranty of
14: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15: * GNU General Public License for more details.
16: *
17: * You should have received a copy of the GNU General Public
18: * License along with this program. If not, see
19: * <http://www.gnu.org/licenses/gpl-3.0.html>.
20: * #~%
21: */
22: package org.overture.codegen.trans;
23:
24: import java.util.LinkedList;
25: import java.util.List;
26:
27: import org.apache.log4j.Logger;
28: import org.overture.ast.patterns.ASetMultipleBind;
29: import org.overture.codegen.assistant.AssistantBase;
30: import org.overture.codegen.ir.*;
31: import org.overture.codegen.ir.analysis.AnalysisException;
32: import org.overture.codegen.ir.analysis.DepthFirstAnalysisAdaptor;
33: import org.overture.codegen.ir.declarations.AVarDeclIR;
34: import org.overture.codegen.ir.expressions.*;
35: import org.overture.codegen.ir.patterns.*;
36: import org.overture.codegen.ir.statements.AAssignToExpStmIR;
37: import org.overture.codegen.ir.statements.ABlockStmIR;
38: import org.overture.codegen.ir.statements.ACaseAltStmStmIR;
39: import org.overture.codegen.ir.statements.ACasesStmIR;
40: import org.overture.codegen.ir.statements.AIfStmIR;
41: import org.overture.codegen.ir.types.*;
42: import org.overture.codegen.ir.utils.AHeaderLetBeStIR;
43: import org.overture.codegen.trans.assistants.TransAssistantIR;
44: import org.overture.codegen.trans.comp.ComplexCompStrategy;
45: import org.overture.codegen.trans.comp.MapCompStrategy;
46: import org.overture.codegen.trans.comp.SeqCompStrategy;
47: import org.overture.codegen.trans.comp.SetCompStrategy;
48: import org.overture.codegen.trans.iota.IotaStrategy;
49: import org.overture.codegen.trans.iterator.ILanguageIterator;
50: import org.overture.codegen.trans.let.LetBeStStrategy;
51: import org.overture.codegen.trans.quantifier.CounterData;
52: import org.overture.codegen.trans.quantifier.Exists1QuantifierStrategy;
53: import org.overture.codegen.trans.quantifier.OrdinaryQuantifier;
54: import org.overture.codegen.trans.quantifier.OrdinaryQuantifierStrategy;
55:
56: public class Exp2StmTrans extends DepthFirstAnalysisAdaptor
57: {
58:         protected Logger log = Logger.getLogger(this.getClass().getName());
59:
60:         protected TransAssistantIR transAssistant;
61:         protected ILanguageIterator langIterator;
62:
63:         protected CounterData counterData;
64:         protected Exp2StmVarPrefixes prefixes;
65:         protected IterationVarPrefixes iteVarPrefixes;
66:
67:         public Exp2StmTrans(IterationVarPrefixes iteVarPrefixes,
68:                                                 TransAssistantIR transAssistant, CounterData counterData,
69:                                                 ILanguageIterator langIterator, Exp2StmVarPrefixes prefixes)
70:         {
71:                 this.transAssistant = transAssistant;
72:                 this.counterData = counterData;
73:                 this.langIterator = langIterator;
74:                 this.prefixes = prefixes;
75:                 this.iteVarPrefixes = iteVarPrefixes;
76:         }
77:
78:         @Override
79:         public void caseATernaryIfExpIR(ATernaryIfExpIR node)
80:                         throws AnalysisException
81:         {
82:                 SStmIR enclosingStm = transAssistant.findEnclosingStm(node);
83:
84:•                if (enclosingStm == null)
85:                 {
86:                         // TODO:
87:                         // Cases such as
88:                         // values
89:                         // public x = 1 + if 2 = 3 then 4 else 5 + 6;
90:                         // Will not be treated
91:                         return;
92:                 }
93:
94:                 String resultVarName = transAssistant.getInfo().getTempVarNameGen().nextVarName(prefixes.ternaryIfExp());
95:
96:                 AVarDeclIR resultDecl = transAssistant.consDecl(resultVarName, node.getType().clone(), transAssistant.getInfo().getExpAssistant().consUndefinedExp());
97:                 AIdentifierVarExpIR resultVar = transAssistant.getInfo().getExpAssistant().consIdVar(resultVarName, resultDecl.getType().clone());
98:
99:                 SExpIR condition = node.getCondition();
100:                 SExpIR trueValue = node.getTrueValue();
101:                 SExpIR falseValue = node.getFalseValue();
102:
103:                 AAssignToExpStmIR trueBranch = new AAssignToExpStmIR();
104:                 trueBranch.setTarget(resultVar.clone());
105:                 trueBranch.setExp(trueValue.clone());
106:
107:                 AAssignToExpStmIR falseBranch = new AAssignToExpStmIR();
108:                 falseBranch.setTarget(resultVar.clone());
109:                 falseBranch.setExp(falseValue);
110:
111:                 AIfStmIR ifStm = new AIfStmIR();
112:                 ifStm.setIfExp(condition.clone());
113:                 ifStm.setThenStm(trueBranch);
114:                 ifStm.setElseStm(falseBranch);
115:
116:                 ABlockStmIR replacementBlock = new ABlockStmIR();
117:
118:                 transAssistant.replaceNodeWith(node, resultVar);
119:                 transAssistant.replaceNodeWith(enclosingStm, replacementBlock);
120:
121:                 ABlockStmIR declBlock = new ABlockStmIR();
122:                 declBlock.getLocalDefs().add(resultDecl);
123:
124:                 replacementBlock.getStatements().add(declBlock);
125:                 replacementBlock.getStatements().add(ifStm);
126:                 replacementBlock.getStatements().add(enclosingStm);
127:
128:                 ifStm.getIfExp().apply(this);
129:                 trueBranch.getExp().apply(this);
130:                 falseBranch.getExp().apply(this);
131:         }
132:
133:         @Override
134:         public void caseAOrBoolBinaryExpIR(AOrBoolBinaryExpIR node)
135:                         throws AnalysisException
136:         {
137:                 // left || right
138:                 //
139:                 // is replaced with a variable expression 'orResult' that is
140:                 // computed as:
141:                 //
142:                 // boolean orResult = false;
143:                 // if (left)
144:                 // {
145:                 // orResult = true;
146:                 // }
147:                 // else
148:                 // {
149:                 // orResult = right;
150:                 // }
151:                 //
152:
153:                 SStmIR enclosingStm = transAssistant.findEnclosingStm(node);
154:
155:•                if (transformBoolBinaryExp(node, enclosingStm))
156:                 {
157:                         String resultName = transAssistant.getInfo().getTempVarNameGen().nextVarName(prefixes.orExp());
158:                         handleLogicExp(node, enclosingStm, consOrExpCheck(node, resultName), resultName);
159:                 } else
160:                 {
161:                         visitBoolBinary(node);
162:                 }
163:         }
164:
165:         @Override
166:         public void caseAAndBoolBinaryExpIR(AAndBoolBinaryExpIR node)
167:                         throws AnalysisException
168:         {
169:                 // left && right
170:                 //
171:                 // is replaced with a variable expression 'andResult' that is
172:                 // computed as:
173:                 //
174:                 // boolean andResult = false;
175:                 // if (left)
176:                 // {
177:                 // if (right)
178:                 // {
179:                 // andResult = true;
180:                 // }
181:                 // }
182:
183:                 SStmIR enclosingStm = transAssistant.findEnclosingStm(node);
184:
185:•                if (transformBoolBinaryExp(node, enclosingStm))
186:                 {
187:                         String resultName = transAssistant.getInfo().getTempVarNameGen().nextVarName(prefixes.andExp());
188:                         handleLogicExp(node, enclosingStm, consAndExpCheck(node, resultName), resultName);
189:                 } else
190:                 {
191:                         visitBoolBinary(node);
192:                 }
193:         }
194:
195:         @Override
196:         public void caseALetBeStExpIR(ALetBeStExpIR node) throws AnalysisException
197:         {
198:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "let be st expressions");
199:
200:                 AHeaderLetBeStIR header = node.getHeader();
201:                 SMultipleBindIR binding = header.getBinding();
202:                 SExpIR suchThat = header.getSuchThat();
203:
204:•                if(!(binding instanceof ASetMultipleBindIR || binding instanceof ASeqMultipleBindIR))
205:                 {
206:                         transAssistant.getInfo().addTransformationWarning(node.getHeader().getBinding(),
207:                                         "This transformation only works for 'let be st' " +
208:                                                         "expressions with with multiple set or sequence binds and not multiple type binds in '"
209:                                                         + this.getClass().getSimpleName() + "'");
210:                         return;
211:                 }
212:
213:                 STypeIR colType = getCol(binding).getType().clone();
214:
215:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
216:
217:                 LetBeStStrategy strategy = consLetBeStStrategy(suchThat, colType, tempVarNameGen);
218:
219:                 ABlockStmIR outerBlock = new ABlockStmIR();
220:
221:                 SExpIR letBeStResult = null;
222:
223:•                if (transAssistant.hasEmptySet(binding))
224:                 {
225:                         transAssistant.cleanUpBinding(binding);
226:                         letBeStResult = transAssistant.getInfo().getExpAssistant().consUndefinedExp();
227:                 } else
228:                 {
229:                         String var = tempVarNameGen.nextVarName(prefixes.letBeSt());
230:                         SExpIR value = node.getValue();
231:
232:                         AVarDeclIR resultDecl = transAssistant.consDecl(var, value.getType().clone(), transAssistant.getInfo().getExpAssistant().consUndefinedExp());
233:                         outerBlock.getLocalDefs().add(resultDecl);
234:
235:                         AAssignToExpStmIR setLetBeStResult = new AAssignToExpStmIR();
236:                         setLetBeStResult.setTarget(transAssistant.getInfo().getExpAssistant().consIdVar(var, value.getType().clone()));
237:                         setLetBeStResult.setExp(value);
238:                         outerBlock.getStatements().add(setLetBeStResult);
239:
240:                         AIdentifierVarExpIR varExpResult = new AIdentifierVarExpIR();
241:                         varExpResult.setType(value.getType().clone());
242:                         varExpResult.setIsLocal(true);
243:                         varExpResult.setName(var);
244:                         letBeStResult = varExpResult;
245:                 }
246:
247:                 // Replace the let be st expression with the result expression
248:                 transAssistant.replaceNodeWith(node, letBeStResult);
249:
250:                 LinkedList<SPatternIR> patterns = binding.getPatterns();
251:                 ABlockStmIR block = transAssistant.consIterationBlock(patterns, getCol(binding), tempVarNameGen, strategy, iteVarPrefixes);
252:                 outerBlock.getStatements().addFirst(block);
253:
254:                 // Replace the enclosing statement with the transformation
255:                 transAssistant.replaceNodeWith(enclosingStm, outerBlock);
256:
257:                 // And make sure to have the enclosing statement in the transformed tree
258:                 outerBlock.getStatements().add(enclosingStm);
259:                 outerBlock.apply(this);
260:
261:                 outerBlock.setScoped(transAssistant.getInfo().getStmAssistant().isScoped(outerBlock));
262:         }
263:
264:         private SExpIR getCol(SMultipleBindIR binding)
265:         {
266:•                if(binding instanceof ASetMultipleBindIR)
267:                 {
268:                         return ((ASetMultipleBindIR) binding).getSet();
269:                 }
270:•                else if(binding instanceof ASeqMultipleBindIR)
271:                 {
272:                         return ((ASeqMultipleBindIR) binding).getSeq();
273:                 }
274:
275:                 return null;
276:         }
277:
278:         public LetBeStStrategy consLetBeStStrategy(SExpIR suchThat, STypeIR colType, ITempVarGen tempVarNameGen) {
279:                 return new LetBeStStrategy(transAssistant, suchThat, colType, langIterator, tempVarNameGen, iteVarPrefixes);
280:         }
281:
282:         @Override
283:         public void caseARecordModExpIR(ARecordModExpIR node)
284:                         throws AnalysisException
285:         {
286:                 String recModifierName = transAssistant.getInfo().getTempVarNameGen().nextVarName(prefixes.recModExp());
287:
288:                 AVarDeclIR recDecl = transAssistant.consDecl(recModifierName, node.getType().clone(), node.getRec().clone());
289:                 ABlockStmIR declStm = new ABlockStmIR();
290:                 declStm.getLocalDefs().add(recDecl);
291:
292:                 AIdentifierVarExpIR recVar = transAssistant.getInfo().getExpAssistant().consIdVar(recModifierName, node.getType().clone());
293:
294:                 ABlockStmIR replacementBlock = new ABlockStmIR();
295:                 replacementBlock.getStatements().add(declStm);
296:
297:•                if(transAssistant.getInfo().getTypeAssistant().isIncompleteRecType(node.getRecType())) {
298:                         log.warn("Record type of mu_ expression '" + AssistantBase.getVdmNode(node) + "' has incomplete information." +
299:                                         " Record type name: " + node.getRecType().getName().getName() +
300:                                         ". Defining class of record type: " + node.getRecType().getName().getDefiningClass());
301:                 }
302:
303:•                for (ARecordModifierIR modifier : node.getModifiers())
304:                 {
305:                         String name = modifier.getName();
306:                         SExpIR value = modifier.getValue().clone();
307:
308:                         STypeIR fieldType;
309:
310:•                        if(transAssistant.getInfo().getTypeAssistant().isIncompleteRecType(node.getRecType()))
311:                         {
312:                                 fieldType = value.getType().clone();
313:                         }
314:                         else
315:                         {
316:                                 fieldType = transAssistant.getInfo().getTypeAssistant().getFieldType(transAssistant.getInfo().getClasses(), node.getRecType(), name);
317:                         }
318:
319:                         AFieldExpIR field = new AFieldExpIR();
320:                         field.setType(fieldType);
321:                         field.setObject(recVar.clone());
322:                         field.setMemberName(name);
323:
324:                         AAssignToExpStmIR assignment = new AAssignToExpStmIR();
325:                         assignment.setTarget(field);
326:                         assignment.setExp(value);
327:
328:                         replacementBlock.getStatements().add(assignment);
329:                 }
330:
331:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "record modification expression");
332:
333:                 transform(enclosingStm, replacementBlock, recVar.clone(), node);
334:
335:                 replacementBlock.apply(this);
336:         }
337:
338:         @Override
339:         public void caseACompMapExpIR(ACompMapExpIR node) throws AnalysisException
340:         {
341:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "map comprehension");
342:
343:                 AMapletExpIR first = node.getFirst();
344:                 SExpIR predicate = node.getPredicate();
345:                 STypeIR type = node.getType();
346:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
347:                 String var = tempVarNameGen.nextVarName(prefixes.mapComp());
348:
349:                 ComplexCompStrategy strategy = consMapCompStrategy(first, predicate, type, tempVarNameGen, var);
350:
351:                 List<SMultipleBindIR> bindings = filterBindList(node, node.getBindings());
352:
353:                 ABlockStmIR block = transAssistant.consComplexCompIterationBlock(bindings, tempVarNameGen, strategy, iteVarPrefixes);
354:
355:•                if (block.getStatements().isEmpty())
356:                 {
357:                         // In case the block has no statements the result of the map comprehension is the empty map
358:                         AEnumMapExpIR emptyMap = new AEnumMapExpIR();
359:                         emptyMap.setType(type.clone());
360:
361:                         // Replace the map comprehension with the empty map
362:                         transAssistant.replaceNodeWith(node, emptyMap);
363:                 } else
364:                 {
365:                         replaceCompWithTransformation(enclosingStm, block, type, var, node);
366:                 }
367:
368:                 block.apply(this);
369:         }
370:
371:         public MapCompStrategy consMapCompStrategy(AMapletExpIR first, SExpIR predicate, STypeIR type, ITempVarGen tempVarNameGen, String var) {
372:                 return new MapCompStrategy(transAssistant, first, predicate, var, type, langIterator, tempVarNameGen, iteVarPrefixes);
373:         }
374:
375:         @Override
376:         public void caseACompSetExpIR(ACompSetExpIR node) throws AnalysisException
377:         {
378:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "set comprehension");
379:
380:                 SExpIR first = node.getFirst();
381:                 SExpIR predicate = node.getPredicate();
382:                 STypeIR type = node.getType();
383:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
384:                 String var = tempVarNameGen.nextVarName(prefixes.setComp());
385:
386:                 ComplexCompStrategy strategy = consSetCompStrategy(first, predicate, type, tempVarNameGen, var);
387:
388:                 List<SMultipleBindIR> bindings = filterBindList(node, node.getBindings());
389:                 ABlockStmIR block = transAssistant.consComplexCompIterationBlock(bindings, tempVarNameGen, strategy, iteVarPrefixes);
390:
391:•                if (block.getStatements().isEmpty())
392:                 {
393:                         // In case the block has no statements the result of the set comprehension is the empty set
394:                         AEnumSetExpIR emptySet = new AEnumSetExpIR();
395:                         emptySet.setType(type.clone());
396:
397:                         // Replace the set comprehension with the empty set
398:                         transAssistant.replaceNodeWith(node, emptySet);
399:                 } else
400:                 {
401:                         replaceCompWithTransformation(enclosingStm, block, type, var, node);
402:                 }
403:
404:                 block.apply(this);
405:         }
406:
407:         public SetCompStrategy consSetCompStrategy(SExpIR first, SExpIR predicate, STypeIR type, ITempVarGen tempVarNameGen, String var) {
408:                 return new SetCompStrategy(transAssistant, first, predicate, var, type, langIterator, tempVarNameGen, iteVarPrefixes);
409:         }
410:
411:         @Override
412:         public void caseACompSeqExpIR(ACompSeqExpIR node) throws AnalysisException
413:         {
414:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "sequence comprehension");
415:
416:                 SExpIR first = node.getFirst();
417:                 SExpIR predicate = node.getPredicate();
418:                 STypeIR type = node.getType();
419:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
420:                 String var = tempVarNameGen.nextVarName(prefixes.seqComp());
421:
422:                 SeqCompStrategy strategy = consSeqCompStrategy(first, predicate, type, tempVarNameGen, var);
423:
424:•                if (transAssistant.isEmptySetSeq(node.getSetSeq()))
425:                 {
426:                         // In case the block has no statements the result of the sequence comprehension is the empty sequence
427:                         AEnumSeqExpIR emptySeq = new AEnumSeqExpIR();
428:                         emptySeq.setType(type.clone());
429:
430:                         // Replace the sequence comprehension with the empty sequence
431:                         transAssistant.replaceNodeWith(node, emptySeq);
432:                 } else
433:                 {
434:                         LinkedList<SPatternIR> patterns = new LinkedList<SPatternIR>();
435:
436:•                        if (node.getSetBind() != null)
437:                         {
438:                                 patterns.add(node.getSetBind().getPattern().clone());
439:                         } else
440:                         {
441:                                 patterns.add(node.getSeqBind().getPattern().clone());
442:                         }
443:
444:                         ABlockStmIR block = transAssistant.consIterationBlock(patterns, node.getSetSeq(), transAssistant.getInfo().getTempVarNameGen(), strategy, iteVarPrefixes);
445:
446:                         replaceCompWithTransformation(enclosingStm, block, type, var, node);
447:
448:                         block.apply(this);
449:                 }
450:         }
451:
452:         public SeqCompStrategy consSeqCompStrategy(SExpIR first, SExpIR predicate, STypeIR type, ITempVarGen tempVarNameGen, String var) {
453:                 return new SeqCompStrategy(transAssistant, first, predicate, var, type, langIterator, tempVarNameGen, iteVarPrefixes);
454:         }
455:
456:         @Override
457:         public void caseAForAllQuantifierExpIR(AForAllQuantifierExpIR node)
458:                         throws AnalysisException
459:         {
460:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "forall expression");
461:
462:                 SExpIR predicate = node.getPredicate();
463:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
464:                 String var = tempVarNameGen.nextVarName(prefixes.forAll());
465:
466:                 OrdinaryQuantifierStrategy strategy = consOrdinaryQuantifierStrategy(predicate, tempVarNameGen, var, transAssistant, OrdinaryQuantifier.FORALL, langIterator, iteVarPrefixes);
467:
468:                 List<SMultipleBindIR> multipleSetBinds = filterBindList(node, node.getBindList());
469:
470:                 ABlockStmIR block = transAssistant.consComplexCompIterationBlock(multipleSetBinds, tempVarNameGen, strategy, iteVarPrefixes);
471:
472:•                if (multipleSetBinds.isEmpty())
473:                 {
474:                         ABoolLiteralExpIR forAllResult = transAssistant.getInfo().getExpAssistant().consBoolLiteral(true);
475:                         transAssistant.replaceNodeWith(node, forAllResult);
476:                 } else
477:                 {
478:                         AIdentifierVarExpIR forAllResult = new AIdentifierVarExpIR();
479:                         forAllResult.setIsLocal(true);
480:                         forAllResult.setType(new ABoolBasicTypeIR());
481:                         forAllResult.setName(var);
482:
483:                         transform(enclosingStm, block, forAllResult, node);
484:                         block.apply(this);
485:                 }
486:         }
487:
488:         @Override
489:         public void caseAExistsQuantifierExpIR(AExistsQuantifierExpIR node)
490:                         throws AnalysisException
491:         {
492:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "exists expression");
493:
494:                 SExpIR predicate = node.getPredicate();
495:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
496:                 String var = tempVarNameGen.nextVarName(prefixes.exists());
497:
498:                 OrdinaryQuantifierStrategy strategy = consOrdinaryQuantifierStrategy(predicate, tempVarNameGen, var, transAssistant, OrdinaryQuantifier.EXISTS, langIterator, iteVarPrefixes);
499:
500:                 List<SMultipleBindIR> multipleSetBinds = filterBindList(node, node.getBindList());
501:
502:                 ABlockStmIR block = transAssistant.consComplexCompIterationBlock(multipleSetBinds, tempVarNameGen, strategy, iteVarPrefixes);
503:
504:•                if (multipleSetBinds.isEmpty())
505:                 {
506:                         ABoolLiteralExpIR existsResult = transAssistant.getInfo().getExpAssistant().consBoolLiteral(false);
507:                         transAssistant.replaceNodeWith(node, existsResult);
508:                 } else
509:                 {
510:                         AIdentifierVarExpIR existsResult = new AIdentifierVarExpIR();
511:                         existsResult.setIsLocal(true);
512:                         existsResult.setType(new ABoolBasicTypeIR());
513:                         existsResult.setName(var);
514:
515:                         transform(enclosingStm, block, existsResult, node);
516:                         block.apply(this);
517:                 }
518:         }
519:
520:         @Override
521:         public void caseAIotaExpIR(AIotaExpIR node) throws AnalysisException {
522:
523:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "iota expression");
524:
525:                 SExpIR predicate = node.getPredicate();
526:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
527:                 String resVarName = tempVarNameGen.nextVarName(prefixes.iota());
528:                 String counterName = tempVarNameGen.nextVarName(prefixes.iotaCounter());
529:
530:                 IotaStrategy strategy = consIotaStrategy(predicate, tempVarNameGen, resVarName, counterName, node.getPredicate());
531:
532:                 List<SMultipleBindIR> multipleSetBinds = filterBindList(node, node.getBindList());
533:
534:                 ABlockStmIR block = transAssistant.consComplexCompIterationBlock(multipleSetBinds, tempVarNameGen, strategy, iteVarPrefixes);
535:
536:•                if (multipleSetBinds.isEmpty())
537:                 {
538:                         transAssistant.replaceNodeWith(node, transAssistant.getInfo().getExpAssistant().consUndefinedExp());
539:                 } else
540:                 {
541:                         AIdentifierVarExpIR iotaResult = new AIdentifierVarExpIR();
542:                         iotaResult.setIsLocal(true);
543:                         iotaResult.setType(node.getType().clone());
544:                         iotaResult.setName(resVarName);
545:
546:                         transform(enclosingStm, block, iotaResult, node);
547:                         block.apply(this);
548:                 }
549:         }
550:
551:         public IotaStrategy consIotaStrategy(SExpIR pred, ITempVarGen tempVarNameGen, String resName, String counterName, SExpIR predicate) {
552:
553:                 return new IotaStrategy(transAssistant, predicate, resName, counterName, langIterator, tempVarNameGen, iteVarPrefixes, counterData);
554:         }
555:
556:         public OrdinaryQuantifierStrategy consOrdinaryQuantifierStrategy(SExpIR predicate, ITempVarGen tempVarNameGen, String var, TransAssistantIR transAssistant, OrdinaryQuantifier exists, ILanguageIterator langIterator, IterationVarPrefixes iteVarPrefixes) {
557:                 return new OrdinaryQuantifierStrategy(transAssistant, predicate, var, exists, langIterator, tempVarNameGen, iteVarPrefixes);
558:         }
559:
560:         @Override
561:         public void caseAExists1QuantifierExpIR(AExists1QuantifierExpIR node)
562:                         throws AnalysisException
563:         {
564:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "exists1 expression");
565:
566:                 SExpIR predicate = node.getPredicate();
567:                 ITempVarGen tempVarNameGen = transAssistant.getInfo().getTempVarNameGen();
568:                 String var = tempVarNameGen.nextVarName(prefixes.exists1());
569:
570:                 Exists1QuantifierStrategy strategy = consExists1QuantifierStrategy(predicate, tempVarNameGen, var);
571:
572:                 List<SMultipleBindIR> multipleSetBinds = filterBindList(node, node.getBindList());
573:
574:                 ABlockStmIR block = transAssistant.consComplexCompIterationBlock(multipleSetBinds, tempVarNameGen, strategy, iteVarPrefixes);
575:
576:•                if (multipleSetBinds.isEmpty())
577:                 {
578:                         ABoolLiteralExpIR exists1Result = transAssistant.getInfo().getExpAssistant().consBoolLiteral(false);
579:                         transAssistant.replaceNodeWith(node, exists1Result);
580:                 } else
581:                 {
582:                         AIdentifierVarExpIR counter = new AIdentifierVarExpIR();
583:                         counter.setType(new AIntNumericBasicTypeIR());
584:                         counter.setIsLocal(true);
585:                         counter.setName(var);
586:
587:                         AEqualsBinaryExpIR exists1Result = new AEqualsBinaryExpIR();
588:                         exists1Result.setType(new ABoolBasicTypeIR());
589:                         exists1Result.setLeft(counter);
590:                         exists1Result.setRight(transAssistant.getInfo().getExpAssistant().consIntLiteral(1));
591:
592:                         transform(enclosingStm, block, exists1Result, node);
593:                         block.apply(this);
594:                 }
595:         }
596:
597:         public Exists1QuantifierStrategy consExists1QuantifierStrategy(SExpIR predicate, ITempVarGen tempVarNameGen, String var) {
598:                 return new Exists1QuantifierStrategy(transAssistant, predicate, var, langIterator, tempVarNameGen, iteVarPrefixes, counterData);
599:         }
600:
601:         public void caseALetDefExpIR(ALetDefExpIR node) throws AnalysisException
602:         {
603:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "let def expression");
604:
605:                 SExpIR exp = node.getExp();
606:                 transAssistant.replaceNodeWith(node, exp);
607:
608:                 ABlockStmIR topBlock = new ABlockStmIR();
609:                 ABlockStmIR current = topBlock;
610:
611:•                for (AVarDeclIR local : node.getLocalDefs())
612:                 {
613:                         ABlockStmIR tmp = new ABlockStmIR();
614:                         tmp.getLocalDefs().add(local.clone());
615:                         current.getStatements().add(tmp);
616:                         current = tmp;
617:                 }
618:
619:                 transAssistant.replaceNodeWith(enclosingStm, topBlock);
620:                 topBlock.getStatements().add(enclosingStm);
621:
622:                 exp.apply(this);
623:                 topBlock.apply(this);
624:
625:                 topBlock.setScoped(transAssistant.getInfo().getStmAssistant().isScoped(topBlock));
626:         }
627:
628:         protected void replaceCompWithTransformation(SStmIR enclosingStm,
629:                                                                                                  ABlockStmIR block, STypeIR type, String var, SExpIR comp)
630:         {
631:                 AIdentifierVarExpIR compResult = new AIdentifierVarExpIR();
632:                 compResult.setType(type.clone());
633:                 compResult.setName(var);
634:                 compResult.setIsLambda(false);
635:                 compResult.setIsLocal(true);
636:
637:                 transform(enclosingStm, block, compResult, comp);
638:         }
639:
640:         protected void transform(SStmIR enclosingStm, ABlockStmIR block,
641:                                                          SExpIR nodeResult, SExpIR node)
642:         {
643:                 // Replace the node with the node result
644:                 transAssistant.replaceNodeWith(node, nodeResult);
645:
646:                 // Replace the enclosing statement with the transformation
647:                 transAssistant.replaceNodeWith(enclosingStm, block);
648:
649:                 // And make sure to have the enclosing statement in the transformed tree
650:                 block.getStatements().add(enclosingStm);
651:         }
652:
653:         protected AAssignToExpStmIR assignToVar(AIdentifierVarExpIR var, SExpIR exp)
654:         {
655:                 AAssignToExpStmIR assignment = new AAssignToExpStmIR();
656:                 assignment.setTarget(var.clone());
657:                 assignment.setExp(exp.clone());
658:
659:                 return assignment;
660:         }
661:
662:         @Override
663:         public void caseACasesExpIR(ACasesExpIR node) throws AnalysisException
664:         {
665:                 SStmIR enclosingStm = transAssistant.getEnclosingStm(node, "cases expression");
666:
667:                 AIdentifierPatternIR idPattern = new AIdentifierPatternIR();
668:                 IRInfo info = transAssistant.getInfo();
669:                 String casesExpResultName = info.getTempVarNameGen().nextVarName(prefixes.casesExp());
670:                 idPattern.setName(casesExpResultName);
671:
672:                 AVarDeclIR resultVarDecl = info.getDeclAssistant().consLocalVarDecl(node.getType().clone(), idPattern, info.getExpAssistant().consUndefinedExp());
673:
674:                 AIdentifierVarExpIR resultVar = new AIdentifierVarExpIR();
675:                 resultVar.setIsLocal(true);
676:                 resultVar.setIsLambda(false);
677:                 resultVar.setName(casesExpResultName);
678:                 resultVar.setType(node.getType().clone());
679:
680:                 ACasesStmIR casesStm = new ACasesStmIR();
681:                 casesStm.setExp(node.getExp().clone());
682:
683:•                for (ACaseAltExpExpIR altExp : node.getCases())
684:                 {
685:                         ACaseAltStmStmIR altStm = new ACaseAltStmStmIR();
686:                         altStm.setPattern(altExp.getPattern().clone());
687:                         altStm.setResult(assignToVar(resultVar, altExp.getResult()));
688:                         altStm.setPatternType(altExp.getPatternType().clone());
689:
690:                         casesStm.getCases().add(altStm);
691:                 }
692:
693:•                if (node.getOthers() != null)
694:                 {
695:                         casesStm.setOthers(assignToVar(resultVar, node.getOthers()));
696:                 }
697:
698:                 ABlockStmIR block = new ABlockStmIR();
699:
700:                 ABlockStmIR wrapperBlock = new ABlockStmIR();
701:                 wrapperBlock.getLocalDefs().add(resultVarDecl);
702:
703:                 block.getStatements().add(wrapperBlock);
704:                 block.getStatements().add(casesStm);
705:
706:                 transform(enclosingStm, block, resultVar, node);
707:
708:                 casesStm.apply(this);
709:         }
710:
711:         protected AIfStmIR consAndExpCheck(AAndBoolBinaryExpIR node,
712:                                                                          String andResultVarName)
713:         {
714:                 SExpIR left = node.getLeft().clone();
715:                 SExpIR right = node.getRight().clone();
716:
717:                 AIfStmIR leftCheck = new AIfStmIR();
718:                 leftCheck.setIfExp(left);
719:
720:                 AIfStmIR rightCheck = new AIfStmIR();
721:                 rightCheck.setIfExp(right);
722:
723:                 AAssignToExpStmIR assignAndVar = new AAssignToExpStmIR();
724:                 assignAndVar.setTarget(transAssistant.consBoolCheck(andResultVarName, false));
725:                 assignAndVar.setExp(transAssistant.getInfo().getAssistantManager().getExpAssistant().consBoolLiteral(true));
726:
727:                 rightCheck.setThenStm(assignAndVar);
728:
729:                 leftCheck.setThenStm(rightCheck);
730:
731:                 return leftCheck;
732:         }
733:
734:         protected SStmIR consOrExpCheck(AOrBoolBinaryExpIR node,
735:                                                                         String orResultVarName)
736:         {
737:                 SExpIR left = node.getLeft().clone();
738:                 SExpIR right = node.getRight().clone();
739:
740:                 AIfStmIR leftCheck = new AIfStmIR();
741:                 leftCheck.setIfExp(left);
742:
743:                 AAssignToExpStmIR setOrResultVarTrue = new AAssignToExpStmIR();
744:                 setOrResultVarTrue.setTarget(transAssistant.consBoolCheck(orResultVarName, false));
745:                 setOrResultVarTrue.setExp(transAssistant.getInfo().getAssistantManager().getExpAssistant().consBoolLiteral(true));
746:
747:                 leftCheck.setThenStm(setOrResultVarTrue);
748:
749:                 AAssignToExpStmIR setOrResultVarToRightExp = new AAssignToExpStmIR();
750:                 setOrResultVarToRightExp.setTarget(transAssistant.consBoolCheck(orResultVarName, false));
751:                 setOrResultVarToRightExp.setExp(right);
752:
753:                 leftCheck.setElseStm(setOrResultVarToRightExp);
754:
755:                 return leftCheck;
756:         }
757:
758:         protected boolean transformBoolBinaryExp(SBoolBinaryExpIR node,
759:                                                                                          SStmIR enclosingStm)
760:         {
761:                 // First condition: The enclosing statement can be 'null' if we only try to code generate an expression rather
762:                 // than
763:                 // a complete specification.
764:
765:•                return enclosingStm != null
766:•                                && !transAssistant.getInfo().getExpAssistant().isLoopCondition(node);
767:         }
768:
769:         protected void visitBoolBinary(SBoolBinaryExpIR node)
770:                         throws AnalysisException
771:         {
772:                 node.getLeft().apply(this);
773:                 node.getRight().apply(this);
774:                 node.getType().apply(this);
775:         }
776:
777:         protected void handleLogicExp(SBoolBinaryExpIR node, SStmIR enclosingStm,
778:                                                                  SStmIR checkBlock, String resultName) throws AnalysisException
779:         {
780:                 AVarDeclIR andResultDecl = transAssistant.consBoolVarDecl(resultName, false);
781:
782:                 ABlockStmIR declBlock = new ABlockStmIR();
783:                 declBlock.getLocalDefs().add(andResultDecl);
784:
785:                 ABlockStmIR replacementBlock = new ABlockStmIR();
786:
787:                 transAssistant.replaceNodeWith(enclosingStm, replacementBlock);
788:                 transAssistant.replaceNodeWith(node, transAssistant.consBoolCheck(resultName, false));
789:
790:                 replacementBlock.getStatements().add(declBlock);
791:                 replacementBlock.getStatements().add(checkBlock);
792:                 replacementBlock.getStatements().add(enclosingStm);
793:
794:                 replacementBlock.apply(this);
795:         }
796:
797:         protected List<SMultipleBindIR> filterBindList(INode node,
798:                                                                                                  List<SMultipleBindIR> bindList)
799:         {
800:                 List<SMultipleBindIR> multipleBinds = new LinkedList<SMultipleBindIR>();
801:
802:•                for (SMultipleBindIR b : bindList)
803:                 {
804:•                        if (b instanceof ATypeMultipleBindIR)
805:                         {
806:                                 transAssistant.getInfo().addTransformationWarning(node, "Transformation only works for "
807:                                                 + "expressions with multiple set binds and not multiple "
808:                                                 + "type binds in '" + this.getClass().getSimpleName()
809:                                                 + "'");
810:                         } else
811:                         {
812:                                 multipleBinds.add(b.clone());
813:                         }
814:                 }
815:
816:                 return multipleBinds;
817:         }
818: }