Commit 68a85331 authored by Nils Kaminski's avatar Nils Kaminski
Browse files

Extend dynamic connect and free for subinstances

parent 04a71759
......@@ -8,7 +8,7 @@
<groupId>de.monticore.lang.monticar</groupId>
<artifactId>embedded-montiarc-math-generator</artifactId>
<version>0.0.26-SNAPSHOT</version>
<version>0.1.3-SNAPSHOT</version>
<!-- == PROJECT DEPENDENCIES ============================================= -->
......@@ -25,7 +25,7 @@
<!--<Embedded-MontiArc-Math.version>0.0.19-SNAPSHOT</Embedded-MontiArc-Math.version>-->
<!--<tagging.version>0.0.4</tagging.version>-->
<Embedded-MontiArc-Math.version>0.1.3-SNAPSHOT</Embedded-MontiArc-Math.version>
<Embedded-MontiArc-Math.version>0.1.5-SNAPSHOT</Embedded-MontiArc-Math.version>
<!-- .. Libraries .................................................. -->
<guava.version>18.0</guava.version>
......@@ -227,6 +227,26 @@
<check/>
</configuration>
</plugin>
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>license-maven-plugin</artifactId>
<version>1.14</version>
<dependencies>
<dependency>
<groupId>org.apache.maven.doxia</groupId>
<artifactId>doxia-core</artifactId>
<version>1.6</version>
</dependency>
<dependency>
<groupId>org.apache.maven.doxia</groupId>
<artifactId>doxia-site-renderer</artifactId>
<version>1.6</version>
</dependency>
</dependencies>
</plugin>
</plugins>
</build>
......
package de.monticore.lang.monticar.generator.cpp;
import de.monticore.lang.monticar.generator.BluePrint;
import de.monticore.lang.monticar.generator.Method;
import de.monticore.lang.monticar.generator.TargetCodeInstruction;
import de.monticore.lang.monticar.generator.Variable;
import de.monticore.lang.monticar.generator.cpp.symbols.MathStringExpression;
import de.se_rwth.commons.logging.Log;
......@@ -81,7 +83,51 @@ public class BluePrintFixer {
if(!bluePrint.getVariable(String.format("__%s_connect_request", v.getNameWithoutArrayNamePart())).isPresent()){
bluePrint.addVariable(addConnectedRequestQueueForVariable(v.getNameWithoutArrayNamePart(), bluePrint));
}
if(!bluePrint.getVariable(String.format("__%s_free_request", v.getNameWithoutArrayNamePart())).isPresent()){
bluePrint.addVariable(addFreeRequestQueueForVariable(v.getNameWithoutArrayNamePart(), bluePrint));
}
if(!bluePrint.getMethod(v.getNameWithoutArrayNamePart()+"_has_connect_request").isPresent()){
Method m = new Method();
m.setName(v.getNameWithoutArrayNamePart()+"_has_connect_request");
m.setReturnTypeName("bool");
m.addInstruction(new TargetCodeInstruction(String.format("return !__%s_connect_request.empty();\n", v.getNameWithoutArrayNamePart())));
bluePrint.addMethod(m);
}
if(!bluePrint.getMethod(v.getNameWithoutArrayNamePart()+"_connect_request_front").isPresent()) {
Method m = new Method();
m.setName(v.getNameWithoutArrayNamePart()+"_connect_request_front");
m.setReturnTypeName("int");
m.addInstruction(new TargetCodeInstruction(String.format("int r = __%s_connect_request.front();\n", v.getNameWithoutArrayNamePart())));
m.addInstruction(new TargetCodeInstruction(String.format("__%s_connect_request.pop();\n", v.getNameWithoutArrayNamePart())));
m.addInstruction(new TargetCodeInstruction("return r;\n"));
bluePrint.addMethod(m);
}
// free part
if(!bluePrint.getMethod(v.getNameWithoutArrayNamePart()+"_has_free_request").isPresent()){
Method m = new Method();
m.setName(v.getNameWithoutArrayNamePart()+"_has_free_request");
m.setReturnTypeName("bool");
m.addInstruction(new TargetCodeInstruction(String.format("return !__%s_free_request.empty();\n", v.getNameWithoutArrayNamePart())));
bluePrint.addMethod(m);
}
if(!bluePrint.getMethod(v.getNameWithoutArrayNamePart()+"_free_request_front").isPresent()) {
Method m = new Method();
m.setName(v.getNameWithoutArrayNamePart()+"_free_request_front");
m.setReturnTypeName("int");
m.addInstruction(new TargetCodeInstruction(String.format("int r = __%s_free_request.front();\n", v.getNameWithoutArrayNamePart())));
m.addInstruction(new TargetCodeInstruction(String.format("__%s_free_request.pop();\n", v.getNameWithoutArrayNamePart())));
m.addInstruction(new TargetCodeInstruction(String.format("__%s_connected[r] = false;\n", v.getNameWithoutArrayNamePart())));
m.addInstruction(new TargetCodeInstruction("return r;\n"));
bluePrint.addMethod(m);
}
}
}
}
......@@ -99,4 +145,17 @@ public class BluePrintFixer {
return variable;
}
protected static Variable addFreeRequestQueueForVariable(String nameWithoutArray, BluePrint bluePrint){
Log.info("Adding __free_request variable for "+nameWithoutArray, "Dynamic Request Free Queue for Variable");
Variable variable = new Variable();
variable.setName("__"+nameWithoutArray+"_free_request");
variable.setTypeNameTargetLanguage("std::queue<int>");
variable.setPublic(false);
bluePrint.getMathInformationRegister().addVariable(variable);
return variable;
}
}
......@@ -136,7 +136,9 @@ public class LanguageUnitCPP extends LanguageUnit {
}
//class definition start
resultString += "class " + bluePrint.getName() + "{\n";
resultString += "class " + bluePrint.getName() ;
resultString += "{\n";
//const variables
for (String constString : bluePrint.getConsts())
......
......@@ -58,6 +58,8 @@ public class MathCommandRegisterCPP extends MathCommandRegister {
//for dynamic
registerMathCommand(new DynamicMathPortIsConnectedCommand());
registerMathCommand(new DynamicMathPortNewConnectCommand());
registerMathCommand(new DynamicMathPortFreeCommand());
}
/**
......
package de.monticore.lang.monticar.generator.cpp.commands;
import de.monticore.lang.math._symboltable.expression.MathExpressionSymbol;
import de.monticore.lang.math._symboltable.matrix.MathMatrixAccessSymbol;
import de.monticore.lang.math._symboltable.matrix.MathMatrixNameExpressionSymbol;
import de.monticore.lang.monticar.generator.*;
import de.monticore.lang.monticar.generator.cpp.BluePrintCPP;
import de.monticore.lang.monticar.generator.cpp.MathFunctionFixer;
import de.monticore.lang.monticar.generator.cpp.converter.ExecuteMethodGenerator;
import de.monticore.lang.monticar.generator.cpp.symbols.MathStringExpression;
import de.se_rwth.commons.logging.Log;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
public class DynamicMathPortFreeCommand extends MathCommand {
protected static int ports_free_functionID = 0;
public DynamicMathPortFreeCommand() {
setMathCommandName("ports_free");
}
@Override
protected void convert(MathExpressionSymbol mathExpressionSymbol, BluePrint bluePrint) {
ports_free_functionID++;
MathMatrixNameExpressionSymbol mathMatrixNameExpressionSymbol = (MathMatrixNameExpressionSymbol) mathExpressionSymbol;
List<MathMatrixAccessSymbol> symbols = mathMatrixNameExpressionSymbol.getMathMatrixAccessOperatorSymbol().getMathMatrixAccessSymbols();
if(symbols.size()%2 != 0){
Log.error("Ports_Free wrong number of arguments! Usage: ports_free(portA, indexA, portB, indexB, .....) ");
}
mathMatrixNameExpressionSymbol.setNameToAccess(" ");
for (MathMatrixAccessSymbol accessSymbol : symbols)
MathFunctionFixer.fixMathFunctions(accessSymbol, (BluePrintCPP) bluePrint);
String call = "__ports_free_"+ports_free_functionID;
Method connM = new Method();
connM.setName(call);
connM.setReturnTypeName("bool");
connM.setPublic(false);
call += "(";
TargetCodeInstruction tci = new TargetCodeInstruction("");
connM.addInstruction(tci);
int n = 0;
String idxTest = "";
for(int i = 0; i < symbols.size(); i += 2) {
String portName = ExecuteMethodGenerator.generateExecuteCode(symbols.get(i), new ArrayList<>());
String portIndex = ExecuteMethodGenerator.generateExecuteCode(symbols.get(i+1), new ArrayList<>());
Optional<Variable> portVar = bluePrint.getVariable(portName);
if(!portVar.isPresent()) {
Log.error("ports_connect: Can't find dynamic port "+portName);
}
Variable var = new Variable();
var.setName("idx"+n);
var.setTypeNameTargetLanguage("int");
connM.addParameter(var);
connM.addInstruction(new TargetCodeInstruction("__"+portName+"_free_request.push(idx"+n+");\n"));
connM.addInstruction(new TargetCodeInstruction("__"+portName+"_connected[idx"+n+"] = false;\n"));
idxTest += "(idx"+n+" < 0) || ("+portVar.get().getArraySize()+" <= idx"+n+") || (!__"+portName+"_connected[idx"+n+"])";
call += "("+portIndex+")-1";
if( (i+2) < symbols.size()){
call+=", ";
idxTest += " || ";
}
++n;
}
tci.setInstruction("if("+idxTest+"){return false;}");
connM.addInstruction(new TargetCodeInstruction("if(__parent != NULL){__parent_dynamic(__parent, false, true);}\n"));
connM.addInstruction(new TargetCodeInstruction("return true;\n"));
bluePrint.addMethod(connM);
List<MathMatrixAccessSymbol> newMatrixAccessSymbols = new ArrayList<>();
MathStringExpression stringExpression = new MathStringExpression(call+")",
mathMatrixNameExpressionSymbol.getMathMatrixAccessOperatorSymbol().getMathMatrixAccessSymbols());
newMatrixAccessSymbols.add(new MathMatrixAccessSymbol(stringExpression));
mathMatrixNameExpressionSymbol.getMathMatrixAccessOperatorSymbol().setMathMatrixAccessSymbols(newMatrixAccessSymbols);
}
}
......@@ -36,11 +36,17 @@ public class DynamicMathPortIsConnectedCommand extends MathCommand {
MathFunctionFixer.fixMathFunctions(accessSymbol, (BluePrintCPP) bluePrint);
// valueListString += ExecuteMethodGenerator.generateExecuteCode(mathExpressionSymbol, new ArrayList<String>());
String portinstanceName = ExecuteMethodGenerator.generateExecuteCode(symbols.get(0), new ArrayList<>());
String indexCall = ExecuteMethodGenerator.generateExecuteCode(symbols.get(1), new ArrayList<>());
if(!bluePrint.getVariable(portinstanceName).isPresent()){
Log.error("Is_Connected("+portinstanceName+"...) : Can't find port "+portinstanceName+"!");
}
List<MathMatrixAccessSymbol> newMatrixAccessSymbols = new ArrayList<>();
MathStringExpression stringExpression = new MathStringExpression("__"+portinstanceName+"_connected["+indexCall+"-1]",
mathMatrixNameExpressionSymbol.getMathMatrixAccessOperatorSymbol().getMathMatrixAccessSymbols());
......
package de.monticore.lang.monticar.generator.cpp.commands;
import de.monticore.lang.math._symboltable.expression.MathExpressionSymbol;
import de.monticore.lang.math._symboltable.matrix.MathMatrixAccessSymbol;
import de.monticore.lang.math._symboltable.matrix.MathMatrixNameExpressionSymbol;
import de.monticore.lang.monticar.generator.*;
import de.monticore.lang.monticar.generator.cpp.BluePrintCPP;
import de.monticore.lang.monticar.generator.cpp.MathFunctionFixer;
import de.monticore.lang.monticar.generator.cpp.converter.ExecuteMethodGenerator;
import de.monticore.lang.monticar.generator.cpp.symbols.MathStringExpression;
import de.se_rwth.commons.logging.Log;
import java.util.ArrayList;
import java.util.List;
import java.util.Optional;
public class DynamicMathPortNewConnectCommand extends MathCommand {
protected static int ports_connect_functionID = 0;
public DynamicMathPortNewConnectCommand() {
setMathCommandName("ports_connect");
}
@Override
protected void convert(MathExpressionSymbol mathExpressionSymbol, BluePrint bluePrint) {
ports_connect_functionID++;
MathMatrixNameExpressionSymbol mathMatrixNameExpressionSymbol = (MathMatrixNameExpressionSymbol) mathExpressionSymbol;
List<MathMatrixAccessSymbol> symbols = mathMatrixNameExpressionSymbol.getMathMatrixAccessOperatorSymbol().getMathMatrixAccessSymbols();
if(symbols.size() % 3 != 0){
// Log.error("Is connected wrong number of arguments! Usage for ports: isconnected(<PORT>, <INDEX>). Usage for component: isconnected(<INSTANCE>, <INDEX>)");
Log.error("Ports_Connect wrong number of arguments! Usage: ports_connect(port, out portID, initialValue) or ports_connect(a, out aID, aInit, b, out bID, bInit,...)");
}
mathMatrixNameExpressionSymbol.setNameToAccess(" ");
for (MathMatrixAccessSymbol accessSymbol : symbols)
MathFunctionFixer.fixMathFunctions(accessSymbol, (BluePrintCPP) bluePrint);
String call = "__ports_connect_"+ports_connect_functionID;
Method connM = new Method();
connM.setName(call);
connM.setReturnTypeName("bool");
connM.setPublic(false);
call += "(";
int n = 0;
String check = "";
String initSetter = "";
for(int i = 0; i < symbols.size(); i += 3){
String portName = ExecuteMethodGenerator.generateExecuteCode(symbols.get(i), new ArrayList<>());
String portResultId = ExecuteMethodGenerator.generateExecuteCode(symbols.get(i+1), new ArrayList<>());
String portInit = ExecuteMethodGenerator.generateExecuteCode(symbols.get(i+2), new ArrayList<>());
Variable var = new Variable();
var.setName("id"+n);
var.setTypeNameTargetLanguage("int*");
connM.addParameter(var);
var = new Variable();
var.setName("init"+n);
Optional<Variable> portVar = bluePrint.getVariable(portName);
if(portVar.isPresent()) {
var.setVariableType(portVar.get().getVariableType());
}else{
Log.error("ports_connect: Can't find dynamic port "+portName);
}
connM.addParameter(var);
call += "&"+portResultId+", "+portInit;
if( (i+3) < symbols.size()){
call+=", ";
}
connM.addInstruction(new TargetCodeInstruction(String.format("*id%d = dynamicconnect(%d, __%s_connected, &__%s_connect_request);\n",
n, portVar.get().getArraySize(), portName, portName)));
if(i > 0){
check += " || ";
}
check += "(*id"+n+" < 0)";
initSetter += portName+"[*id"+n+"] = init"+n+"; *id"+n+" = (*id"+n+")+1;\n";
}
connM.addInstruction(new TargetCodeInstruction("if("+check+"){ return false; }\n"));
connM.addInstruction(new TargetCodeInstruction(initSetter));
connM.addInstruction(new TargetCodeInstruction("if(__parent != NULL){__parent_dynamic(__parent, true, false);}\n"));
connM.addInstruction(new TargetCodeInstruction("return true;\n"));
bluePrint.addMethod(connM);
List<MathMatrixAccessSymbol> newMatrixAccessSymbols = new ArrayList<>();
MathStringExpression stringExpression = new MathStringExpression(call+")",
mathMatrixNameExpressionSymbol.getMathMatrixAccessOperatorSymbol().getMathMatrixAccessSymbols());
newMatrixAccessSymbols.add(new MathMatrixAccessSymbol(stringExpression));
mathMatrixNameExpressionSymbol.getMathMatrixAccessOperatorSymbol().setMathMatrixAccessSymbols(newMatrixAccessSymbols);
}
}
......@@ -67,7 +67,6 @@ public class ComponentConverter {
EventConverter.generateEvents(execute, componentSymbol, bluePrint, mathStatementsSymbol,generatorCPP, includeStrings);
extendInitMethod(componentSymbol, bluePrint, generatorCPP, includeStrings);
......@@ -75,6 +74,16 @@ public class ComponentConverter {
EventConverter.generatePVCNextMethod(bluePrint);
if(componentSymbol instanceof EMADynamicComponentInstanceSymbol){
if(((EMADynamicComponentInstanceSymbol) componentSymbol).isDynamic()){
// bluePrint.setHasSuperClass(Optional.of("__dynamicComponent"));
//TODO: ADD parent dynamic function pointer
addParentDynamicFunctionPointer(bluePrint);
bluePrint.addAdditionalIncludeString("DynamicHelper");
}
}
return bluePrint;
}
......@@ -107,6 +116,47 @@ public class ComponentConverter {
}
}
public static void addParentDynamicFunctionPointer(BluePrint bluePrint){
if(!bluePrint.getVariable("(*__parent_dynamic)(void)").isPresent()) {
Variable pd = new Variable();
pd.setTypeNameTargetLanguage("void*");
pd.setName("__parent");
pd.setPublic(false);
bluePrint.addVariable(pd);
pd = new Variable();
pd.setTypeNameTargetLanguage("void");
pd.setName("(*__parent_dynamic)(void* pt2parrent, bool dynFunc, bool freeFunc)");
pd.setPublic(false);
bluePrint.addVariable(pd);
if (bluePrint.getMethod("init").isPresent()) {
bluePrint.getMethod("init").get().addInstruction(new TargetCodeInstruction("__parent = NULL;\n"));
bluePrint.getMethod("init").get().addInstruction(new TargetCodeInstruction("__parent_dynamic = NULL;\n"));
}
if(!bluePrint.getMethod("set_Parent_Dynamic").isPresent()){
Method m = new Method();
m.setReturnTypeName("void");
m.setName("set_Parent_Dynamic");
pd = new Variable();
pd.setTypeNameTargetLanguage("void* ");
pd.setName("parentObj");
m.addParameter(pd);
pd = new Variable();
pd.setTypeNameTargetLanguage("void");
pd.setName("(*func)(void* pt2parrent, bool d, bool f)");
m.addParameter(pd);
m.addInstruction(new TargetCodeInstruction("__parent = parentObj;\n"));
m.addInstruction(new TargetCodeInstruction("__parent_dynamic = func;\n"));
bluePrint.addMethod(m);
}
}
}
public static Method generateInitMethod(EMAComponentInstanceSymbol componentSymbol, BluePrintCPP bluePrint, GeneratorCPP generatorCPP, List<String> includeStrings) {
Method method = new Method("init", "void");
bluePrint.addMethod(method);
......@@ -157,6 +207,12 @@ public class ComponentConverter {
String result = "";
result += GeneralHelperMethods.getTargetLanguageVariableInstanceName(subComponent.getName()) + ".init(" + parameterString + ");\n";
if((componentSymbol instanceof EMADynamicComponentInstanceSymbol) && (subComponent instanceof EMADynamicComponentInstanceSymbol)){
if(((EMADynamicComponentInstanceSymbol) componentSymbol).isDynamic() && ((EMADynamicComponentInstanceSymbol) subComponent).isDynamic()){
result += GeneralHelperMethods.getTargetLanguageVariableInstanceName(subComponent.getName()) +".set_Parent_Dynamic(this, dynamicWrapper);\n";
}
}
TargetCodeInstruction instruction = new TargetCodeInstruction(result);
method.addInstruction(instruction);
}
......
......@@ -193,7 +193,10 @@ public class EventConverter {
}
protected static String generateEventConditionEventPortConnectSymbol(EventPortExpressionConnectSymbol expressionConnectSymbol, EMAComponentInstanceSymbol componentSymbol, BluePrint bluePrint){
return "(!__"+expressionConnectSymbol.getName()+"_connect_request.empty())";
return "("+expressionConnectSymbol.getName()+"_has_connect_request())";
// return "(!__"+expressionConnectSymbol.getName()+"_connect_request.empty())";
}
......
......@@ -71,7 +71,7 @@ public class AbstractSymtab {
for (String m : modelPath) {
mp.addEntry(Paths.get(m));
}
LogConfig.init();//TODO comment for debug output
// LogConfig.init();//TODO comment for debug output
GlobalScope scope = new GlobalScope(mp, fam);
de.monticore.lang.monticar.Utils.addBuiltInTypes(scope);
......
......@@ -9,45 +9,45 @@
#define CONNECTION_H
template<typename T>
struct connection {
void *beforeComponent;
T *source;
T *target;
void *beforeComponent;
T *source;
T *target;
};
//template<typename T, typename T2>
//template<typename T, typename T2>
#endif
int dynamicconnect(int numPorts, bool* connected){
int port = -1;
for (port = 0; port < numPorts; ++port) {
if (!connected[port]) {
break;
}
}
if (port >= numPorts) {
//no free ports
return -1;
}
connected[port] = true;
return port;
int port = -1;
for (port = 0; port < numPorts; ++port) {
if (!connected[port]) {
break;
}
}
if (port >= numPorts) {
//no free ports
return -1;
}
connected[port] = true;
return port;
}
int dynamicconnect(int numPorts, bool* connected, std::queue<int>* request){
int port = dynamicconnect(numPorts, connected);
if(port >= 0){
request->push(port);
}
return port;
int port = dynamicconnect(numPorts, connected);
if(port >= 0){
request->push(port);
}
return port;
}
template<typename T>
void dynamicconnect_remove(std::vector<connection<T>>* vec, void* ac, T* source, T* target){
for(long i = vec->size()-1; i >= 0; --i){
connection<T> c = vec->at(i);
if( (c.beforeComponent == ac) && (c.source == source) && (c.target == target)){
vec->erase(vec->begin()+i);
}
}
for(long i = vec->size()-1; i >= 0; --i){
connection<T> c = vec->at(i);
if( (c.beforeComponent == ac) && (c.source == source) && (c.target == target)){
vec->erase(vec->begin()+i);
}
}
}
#endif /* DynamicHelper_h */