123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470 |
- package be.uantwerpen.ansymo.semanticadaptation.cg.cpp
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.Assignment
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.BoolLiteral
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.CompositeOutputFunction
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.DataRule
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.Declaration
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.If
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.InRulesBlock
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.IntLiteral
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.IsSet
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.LValueDeclaration
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.Literal
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.Multi
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.Neg
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.OutRulesBlock
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.RealLiteral
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.RuleCondition
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.SingleVarDeclaration
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.StateTransitionFunction
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.Variable
- import be.uantwerpen.ansymo.semanticadaptation.semanticAdaptation.util.SemanticAdaptationSwitch
- import java.util.LinkedHashMap
- import java.util.List
- import org.eclipse.emf.ecore.EObject
- import java.util.ArrayList
- import java.util.Optional
- abstract class InOutRulesConditionSwitch extends SemanticAdaptationSwitch<ReturnInformation> {
- protected var LinkedHashMap<String, Pair<SVType, Object>> globalVars = newLinkedHashMap();
- protected var LinkedHashMap<String, GlobalInOutVariable> globalVars2 = newLinkedHashMap();
- private var Pair<SVType, Object> lastVal;
- protected final String adaptationName;
- protected final String adaptationClassName;
- private Integer count = 0;
- private final String functionPrefix;
- protected List<String> functionSignatures = newArrayList();
- protected String externalVariableOwner;
- protected final LinkedHashMap<String, LinkedHashMap<String, MappedScalarVariable>> mSVars;
- protected ArrayList<ConnectedVariable> conVars = newArrayList();
- protected final LinkedHashMap<String, SAScalarVariable> SASVs;
- protected boolean inRuleCondition;
- protected boolean inRuleTransition;
- protected boolean inRuleOutput;
- new(
- String adaptationClassName,
- String adaptationName,
- String functionPrefix,
- LinkedHashMap<String, LinkedHashMap<String, MappedScalarVariable>> mSVars,
- LinkedHashMap<String, SAScalarVariable> SASVs
- ) {
- this.SASVs = SASVs;
- this.adaptationName = adaptationName;
- this.adaptationClassName = adaptationClassName;
- this.functionPrefix = functionPrefix;
- this.mSVars = mSVars;
- }
- /*
- * UTILITY FUNCTIONS
- */
- private def Object convertTypeToObject(SVType type, Literal object) {
- switch (type) {
- case Real: {
- return (object as RealLiteral).value.doubleValue;
- }
- case Integer: {
- return (object as IntLiteral).value;
- }
- case Boolean: {
- return Boolean.parseBoolean((object as BoolLiteral).value);
- }
- default: {
- }
- }
- }
- public def getVars() { return this.globalVars; }
- /**
- * This function adds a header style function signature to the list <i>functionsignatures</i>
- * and returns the source style function signature
- */
- protected def String createFunctionSignature(String functionName, String type) {
- val functionSignature = this.functionPrefix + functionName + this.count + "()";
- this.functionSignatures.add(type + " " + functionSignature + ";");
- return type + " " + this.adaptationClassName + "::" + functionSignature;
- }
- def void incrementCount() {
- this.count++;
- }
- /*
- * COMPILATION FUNCTIONS
- */
- override ReturnInformation caseOutRulesBlock(OutRulesBlock object) {
- var retVal = new ReturnInformation();
- // Get the global variables added to globalVars
- for (gVar : object.globalOutVars) {
- doSwitch(gVar)
- }
- for (dataRule : object.eAllContents.toIterable.filter(DataRule)) {
- this.incrementCount;
- retVal.appendCode(doSwitch(dataRule).code);
- }
- return retVal;
- // var cpp = ""
- // for (gVar : object.globalOutVars) {
- // doSwitch(gVar)
- // }
- // for (dataRule : object.eAllContents.toIterable.filter(DataRule)) {
- // this.incrementCount;
- // cpp += doSwitch(dataRule);
- // }
- // return cpp;
- }
- override ReturnInformation caseInRulesBlock(InRulesBlock object) {
- var retVal = new ReturnInformation();
- // Get the global variables added to globalVars
- for (gVar : object.globalInVars) {
- doSwitch(gVar)
- }
- for (DataRule dataRule : object.eAllContents.toIterable.filter(DataRule)) {
- // This is used for naming each datarule
- this.incrementCount;
- retVal.appendCode(doSwitch(dataRule).code);
- }
- return retVal;
- // var cpp = ""
- // for (gVar : object.globalInVars) {
- // doSwitch(gVar)
- // }
- // for (DataRule dataRule : object.eAllContents.toIterable.filter(DataRule)) {
- // this.incrementCount;
- // cpp += doSwitch(dataRule);
- // }
- // return cpp;
- }
- override ReturnInformation caseDataRule(DataRule object) {
- var retVal = new ReturnInformation();
- retVal.code = '''«inRuleCondition = true»
- «doSwitch(object.condition).code»
- «inRuleCondition = false»
- «inRuleTransition = true»
- «doSwitch(object.statetransitionfunction).code»
- «inRuleTransition = false»
- «inRuleOutput = true»
- «doSwitch(object.outputfunction).code»
- «inRuleOutput = false»
- '''
- return retVal;
- // return '''
- // «doSwitch(object.condition)»
- // «doSwitch(object.statetransitionfunction)»
- // «doSwitch(object.outputfunction)»
- // '''
- }
- override ReturnInformation caseRuleCondition(RuleCondition object) {
- var retVal = new ReturnInformation();
- val functionSignature = createFunctionSignature("condition", "bool");
- retVal.code = '''
- «functionSignature»{
- return «doSwitch(object.condition).code»;
- }
- ''';
- return retVal;
- // val functionSignature = createFunctionSignature("condition", "bool");
- // '''
- // «functionSignature»{
- // return «doSwitch(object.condition)»;
- // }
- // ''';
- }
- override ReturnInformation caseStateTransitionFunction(StateTransitionFunction object) {
- var retVal = new ReturnInformation();
- val functionSig = createFunctionSignature("body", "void");
- retVal.code = '''
- «functionSig»{
- «IF object.expression !== null»
- «doSwitch(object.expression).code»
- «ENDIF»
- «IF object.statements !== null»
- «FOR stm : object.statements»
- «doSwitch(stm).code»
- «ENDFOR»
- «ENDIF»
- «IF object.assignment !== null»
- «doSwitch(object.assignment).code»
- «ENDIF»
- }
- ''';
- return retVal;
- // val functionSig = createFunctionSignature("body", "void");
- // '''
- // «functionSig»{
- // «IF object.expression !== null»
- // «doSwitch(object.expression)»
- // «ENDIF»
- // «IF object.statements !== null»
- // «FOR stm : object.statements»
- // «doSwitch(stm)»
- // «ENDFOR»
- // «ENDIF»
- // «IF object.assignment !== null»
- // «doSwitch(object.assignment)»
- // «ENDIF»
- // }
- // ''';
- }
- override ReturnInformation defaultCase(EObject object) {
- var retVal = new ReturnInformation();
- retVal.code = '''[«object.class»]''';
- return retVal;
- // return '''[«object.class»]''';
- }
- override ReturnInformation caseIf(If object) {
- var retVal = new ReturnInformation();
- retVal.code = '''
- if(«doSwitch(object.ifcondition)»){
- «FOR stm : object.ifstatements»
- «doSwitch(stm).code»
- «ENDFOR»
- }
- ''';
- return retVal;
- // return '''
- // if(«doSwitch(object.ifcondition)»){
- // «FOR stm : object.ifstatements»
- // «doSwitch(stm)»
- // «ENDFOR»
- // }
- // ''';
- }
- private def calcConSaSvData(SAScalarVariable SASV, ReturnInformation rI) {
- if (SASV !== null) {
- if (rI.typeIsSet) {
- SASV.type = rI.type;
- SASV.variability = Optional.of(Conversions.fmiTypeToVariability(rI.type));
- return;
- } else if (rI.conGlobVar !== null) {
- SASV.type = rI.conGlobVar.type;
- SASV.variability = Optional.of(Conversions.fmiTypeToVariability(rI.conGlobVar.type));
- return;
- }
- }
- throw new Exception("Not enough information to determine content of the SASV: " + SASV.name);
- }
- override ReturnInformation caseAssignment(Assignment object) {
- var retVal = new ReturnInformation();
- var lValSwitch = doSwitch(object.lvalue);
- var rValSwitch = doSwitch(object.expr);
- // Here we set the information necessary to create a scalar variables in the model description for the SA.
- if (inRuleTransition) {
- if (rValSwitch.conSaSv !== null) {
- calcConSaSvData(rValSwitch.conSaSv, lValSwitch);
- }
- } else if (inRuleOutput) {
- calcConSaSvData(lValSwitch.conSaSv, rValSwitch);
- }
- retVal.code = '''«lValSwitch.code» = «rValSwitch.code»;''';
- return retVal;
- // return '''«doSwitch(object.lvalue)» = «doSwitch(object.expr)»;'''
- }
- override ReturnInformation caseMulti(Multi object) {
-
- val doSwitchLeft = doSwitch(object.left);
- val doSwitchRight = doSwitch(object.right);
- var retVal = new ReturnInformation(doSwitchLeft, doSwitchRight);
- retVal.code = '''«doSwitch(object.left).code» * «doSwitch(object.right).code»''';
- return retVal;
- // return '''«doSwitch(object.left)» * «doSwitch(object.right)»''';
- }
- override ReturnInformation caseNeg(Neg object) {
-
- var doSwitch = doSwitch(object.right);
- var retVal = new ReturnInformation(doSwitch);
- retVal.code = doSwitch.code;
- return retVal;
- // return '''-«doSwitch(object.right)»'''
- }
- override ReturnInformation caseSingleVarDeclaration(SingleVarDeclaration object) {
- var retVal = new ReturnInformation();
- retVal.code = '''«object.name»''';
- return retVal;
- // var returnVal = '''«object.name»'''
- // return returnVal;
- }
- override ReturnInformation caseCompositeOutputFunction(CompositeOutputFunction object) {
- var retVal = new ReturnInformation();
- val functionSig = createFunctionSignature("flush", "void");
- retVal.code = '''
- «functionSig»{
- «FOR stm : object.statements»
- «doSwitch(stm).code»
- «ENDFOR»
- }
- ''';
- return retVal;
- // val functionSig = createFunctionSignature("flush", "void");
- // val returnVal = '''
- // «functionSig»{
- // «FOR stm : object.statements»
- // «doSwitch(stm)»
- // «ENDFOR»
- // }
- // ''';
- // return returnVal;
- }
- override ReturnInformation caseVariable(Variable object) {
- var retVal = new ReturnInformation();
- if (object.owner === null || object.owner.name == this.adaptationName) {
- retVal.code = '''this->«object.ref.name»''';
- if (SASVs.containsKey(object.ref.name)) {
- retVal.conSaSv = SASVs.get(object.ref.name);
- } else if (globalVars2.containsKey(object.ref.name)) {
- retVal.conGlobVar = globalVars2.get(object.ref.name);
- }
- } else {
- // TODO: Extract the correct variable here
- this.externalVariableOwner = object.owner.name;
- retVal.code = '''«doSwitch(object.ref).code»''';
- }
- return retVal;
- // if (object.owner === null || object.owner.name == this.adaptationName) {
- // return '''this->«object.ref.name»''';
- // } else {
- // this.externalVariableOwner = object.owner.name;
- // return '''«doSwitch(object.ref)»''';
- // }
- }
- override ReturnInformation caseLValueDeclaration(LValueDeclaration object) {
- var retVal = new ReturnInformation();
- retVal.code = '''«object.name»''';
- return retVal;
- // return '''«object.name»'''
- }
- /*
- * This is out var and in var declarations.
- */
- override ReturnInformation caseDeclaration(Declaration object) {
- var retVal2 = new ReturnInformation();
- for (decl : object.declarations) {
- var doSwitchRes = doSwitch(decl.expr);
- retVal2.appendCode(doSwitchRes.code);
- var globVar = new GlobalInOutVariable();
- globVar.name = decl.name;
- globVar.value = doSwitchRes.value;
- globVar.type = doSwitchRes.type;
- globalVars2.put(decl.name, globVar);
- }
- return retVal2;
- // var returnVal = "";
- //
- // for (decl : object.declarations) {
- // returnVal += doSwitch(decl.expr);
- // globalVars.put(decl.name, lastVal);
- // }
- // return returnVal;
- }
- override ReturnInformation caseIsSet(IsSet object) {
- var retInfo = new ReturnInformation();
- // retInfo.type = SVType.Real;
- // retInfo.value = convertTypeToObject(retInfo.type, object);
- retInfo.code = '''this->isSet«(object.args as Variable).ref.name»''';
- return retInfo;
- // return '''this->isSet«(object.args as Variable).ref.name»'''
- }
- override ReturnInformation caseRealLiteral(RealLiteral object) {
- var retInfo = new ReturnInformation();
- retInfo.type = SVType.Real;
- retInfo.value = convertTypeToObject(retInfo.type, object);
- retInfo.code = '''«object.value»''';
- return retInfo;
- // lastVal = convertType(SVType.Real, object);
- // return '''«object.value»''';
- }
- override ReturnInformation caseIntLiteral(IntLiteral object) {
- var retInfo = new ReturnInformation();
- retInfo.type = SVType.Integer;
- retInfo.value = convertTypeToObject(retInfo.type, object);
- retInfo.code = '''«object.value»''';
- return retInfo;
- // return '''«object.value»''';
- }
- override ReturnInformation caseBoolLiteral(BoolLiteral object) {
- var retInfo = new ReturnInformation();
- retInfo.type = SVType.Boolean;
- retInfo.value = convertTypeToObject(retInfo.type, object);
- retInfo.code = '''«object.value»''';
- return retInfo;
- // return '''«object.value»''';
- }
- // private def Pair<SVType, Object> convertType(SVType type, Literal object) {
- // switch (type) {
- // case Real: {
- // return type -> (object as RealLiteral).value.doubleValue;
- // }
- // default: {
- // }
- // }
- // }
- }
|