Skip to content
This repository was archived by the owner on May 18, 2019. It is now read-only.

Commit cfb2366

Browse files
sjoelundOpenModelica-Hudson
authored andcommitted
Add logFormat=xmltcp
logFormat=xmltcp requires a port to be passed and changes the format of the status sent periodically to be an XML message. All messages are buffered and sent when the message is finished in order to always send complete XML fragments to OMEdit.
1 parent e02bbf2 commit cfb2366

File tree

9 files changed

+191
-115
lines changed

9 files changed

+191
-115
lines changed

SimulationRuntime/c/simulation/options.c

Lines changed: 10 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030

3131
#include "options.h"
3232
#include "util/omc_error.h"
33+
#include "simulation_runtime.h"
3334

3435
#include <string.h>
3536
#include <stdio.h>
@@ -50,22 +51,19 @@ int helpFlagSet(int argc, char** argv)
5051
int setLogFormat(int argc, char** argv)
5152
{
5253
const char* value = getOption(FLAG_NAME[FLAG_LOG_FORMAT], argc, argv);
53-
if(NULL == value)
54+
if (NULL == value) {
5455
value = getFlagValue(FLAG_NAME[FLAG_LOG_FORMAT], argc, argv);
56+
}
5557

56-
if (NULL != value)
57-
{
58-
if (0 == strcmp(value, "xml"))
59-
{
58+
if (NULL != value) {
59+
if (0 == strcmp(value, "xml")) {
6060
setStreamPrintXML(1);
61-
}
62-
else if (0 == strcmp(value, "text"))
63-
{
61+
} else if (0 == strcmp(value, "xmltcp")) {
62+
setStreamPrintXML(2);
63+
} else if (0 == strcmp(value, "text")) {
6464
setStreamPrintXML(0);
65-
}
66-
else
67-
{
68-
warningStreamPrint(LOG_STDOUT, 0, "invalid command line option: -logFormat=%s, expected text or xml", value);
65+
} else {
66+
warningStreamPrint(LOG_STDOUT, 0, "invalid command line option: -logFormat=%s, expected text, xml, or xmltcp", value);
6967
return 1;
7068
}
7169
}

SimulationRuntime/c/simulation/simulation_runtime.cpp

Lines changed: 159 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,7 @@ using namespace std;
9494
#ifndef NO_INTERACTIVE_DEPENDENCY
9595
Socket sim_communication_port;
9696
static int sim_communication_port_open = 0;
97+
static int isXMLTCP=0;
9798
#endif
9899

99100
extern "C" {
@@ -861,24 +862,25 @@ int initRuntimeAndSimulation(int argc, char**argv, DATA *data, threadData_t *thr
861862

862863
sim_noemit = omc_flag[FLAG_NOEMIT];
863864

864-
// ppriv - NO_INTERACTIVE_DEPENDENCY - for simpler debugging in Visual Studio
865-
866865
#ifndef NO_INTERACTIVE_DEPENDENCY
867-
if(omc_flag[FLAG_PORT])
868-
{
866+
if(omc_flag[FLAG_PORT]) {
869867
std::istringstream stream(omc_flagValue[FLAG_PORT]);
870868
int port;
871869
stream >> port;
872870
sim_communication_port_open = 1;
873871
sim_communication_port_open &= sim_communication_port.create();
874872
sim_communication_port_open &= sim_communication_port.connect("127.0.0.1", port);
875873

876-
if(0 != strcmp("ia", data->simulationInfo->outputFormat))
877-
{
878-
communicateStatus("Starting", 0.0);
874+
if(0 != strcmp("ia", data->simulationInfo->outputFormat)) {
875+
communicateStatus("Starting", 0.0, data->simulationInfo->startTime, 0);
879876
}
880877
}
881878
#endif
879+
if (isXMLTCP && !sim_communication_port_open) {
880+
errorStreamPrint(LOG_STDOUT, 0, "xmltcp log format requires a TCP-port to be passed (and successfully open)");
881+
EXIT(1);
882+
}
883+
// ppriv - NO_INTERACTIVE_DEPENDENCY - for simpler debugging in Visual Studio
882884

883885
return 0;
884886
}
@@ -899,20 +901,6 @@ void SimulationRuntime_printStatus(int sig)
899901
printf("</status>\n");
900902
}
901903

902-
void communicateStatus(const char *phase, double completionPercent /*0.0 to 1.0*/)
903-
{
904-
#ifndef NO_INTERACTIVE_DEPENDENCY
905-
if(sim_communication_port_open)
906-
{
907-
std::stringstream s;
908-
s << (int)(completionPercent*10000) << " " << phase << endl;
909-
std::string str(s.str());
910-
sim_communication_port.send(str);
911-
// cout << str;
912-
}
913-
#endif
914-
}
915-
916904
void communicateMsg(char id, unsigned int size, const char *data)
917905
{
918906
#ifndef NO_INTERACTIVE_DEPENDENCY
@@ -992,4 +980,154 @@ const char* prettyPrintNanoSec(int64_t ns, int *v)
992980
}
993981
#endif
994982

983+
#ifndef NO_INTERACTIVE_DEPENDENCY
984+
static std::stringstream xmlTcpStream;
985+
static int numOpenTags=0;
986+
987+
static void printEscapedXMLTCP(std::stringstream *s, const char *msg)
988+
{
989+
while (*msg) {
990+
if (*msg == '&') {
991+
*s << "&amp;";
992+
} else if (*msg == '<') {
993+
*s << "&lt;";
994+
} else if (*msg == '>') {
995+
*s << "&gt;";
996+
} else if (*msg == '"') {
997+
*s << "&quot;";
998+
} else {
999+
*s << *msg;
1000+
}
1001+
msg++;
1002+
}
1003+
}
1004+
1005+
static inline void sendXMLTCPIfClosed()
1006+
{
1007+
if (numOpenTags==0) {
1008+
sim_communication_port.send(xmlTcpStream.str());
1009+
xmlTcpStream.clear();
1010+
}
1011+
}
1012+
1013+
static void messageXMLTCP(int type, int stream, int indentNext, char *msg, int subline, const int *indexes)
1014+
{
1015+
xmlTcpStream << "<message stream=\"" << LOG_STREAM_NAME[stream] << "\" type=\"" << LOG_TYPE_DESC[type] << "\" text=\"";
1016+
printEscapedXMLTCP(&xmlTcpStream, msg);
1017+
if (indexes) {
1018+
int i;
1019+
xmlTcpStream << "\">\n";
1020+
for (i=1; i<=*indexes; i++) {
1021+
xmlTcpStream << "<used index=\"" << indexes[i] << "%d\" />\n";
1022+
}
1023+
if (!indentNext) {
1024+
xmlTcpStream << "</message>\n";
1025+
}
1026+
} else {
1027+
xmlTcpStream << (indentNext ? "\">\n" : "\" />\n");
1028+
}
1029+
sendXMLTCPIfClosed();
1030+
}
1031+
1032+
static void messageCloseXMLTCP(int stream)
1033+
{
1034+
if (ACTIVE_STREAM(stream)) {
1035+
numOpenTags--;
1036+
xmlTcpStream << "</message>\n";
1037+
sendXMLTCPIfClosed();
1038+
}
1039+
}
1040+
1041+
static void messageCloseXMLTCPWarning(int stream)
1042+
{
1043+
if (ACTIVE_WARNING_STREAM(stream)) {
1044+
numOpenTags--;
1045+
xmlTcpStream << "</message>\n";
1046+
sendXMLTCPIfClosed();
1047+
}
1048+
}
1049+
#endif
1050+
1051+
static void printEscapedXML(const char *msg)
1052+
{
1053+
while (*msg) {
1054+
if (*msg == '&') fputs("&amp;", stdout);
1055+
else if (*msg == '<') fputs("&lt;", stdout);
1056+
else if (*msg == '>') fputs("&gt;", stdout);
1057+
else if (*msg == '"') fputs("&quot;", stdout);
1058+
else fputc(*msg, stdout);
1059+
msg++;
1060+
}
1061+
}
1062+
1063+
static void messageXML(int type, int stream, int indentNext, char *msg, int subline, const int *indexes)
1064+
{
1065+
printf("<message stream=\"%s\" type=\"%s\" text=\"", LOG_STREAM_NAME[stream], LOG_TYPE_DESC[type]);
1066+
printEscapedXML(msg);
1067+
if (indexes) {
1068+
int i;
1069+
printf("\">\n");
1070+
for (i=1; i<=*indexes; i++) {
1071+
printf("<used index=\"%d\" />\n", indexes[i]);
1072+
}
1073+
if (!indentNext) {
1074+
fputs("</message>\n",stdout);
1075+
}
1076+
} else {
1077+
fputs(indentNext ? "\">\n" : "\" />\n", stdout);
1078+
}
1079+
fflush(stdout);
1080+
}
1081+
1082+
static void messageCloseXML(int stream)
1083+
{
1084+
if (ACTIVE_STREAM(stream)) {
1085+
fputs("</message>\n", stdout);
1086+
fflush(stdout);
1087+
}
1088+
}
1089+
1090+
static void messageCloseXMLWarning(int stream)
1091+
{
1092+
if (ACTIVE_WARNING_STREAM(stream)) {
1093+
fputs("</message>\n", stdout);
1094+
fflush(stdout);
1095+
}
1096+
}
1097+
1098+
void setStreamPrintXML(int isXML)
1099+
{
1100+
if (isXML==1) {
1101+
messageFunction = messageXML;
1102+
messageClose = messageCloseXML;
1103+
messageCloseWarning = messageCloseXMLWarning;
1104+
#ifndef NO_INTERACTIVE_DEPENDENCY
1105+
} else if (isXML==2) {
1106+
messageFunction = messageXMLTCP;
1107+
messageClose = messageCloseXMLTCP;
1108+
messageCloseWarning = messageCloseXMLTCPWarning;
1109+
isXMLTCP = 1;
1110+
#endif
1111+
} else {
1112+
/* Already set... */
1113+
}
1114+
}
1115+
1116+
void communicateStatus(const char *phase, double completionPercent /*0.0 to 1.0*/, double currentTime, double currentStepSize)
1117+
{
1118+
#ifndef NO_INTERACTIVE_DEPENDENCY
1119+
if (sim_communication_port_open && isXMLTCP) {
1120+
std::stringstream s;
1121+
s << "<status phase=\"" << phase << "\" currentStepSize=\"" << currentStepSize << "\" time=\"" << currentTime << "\" progress=\"" << (int)(completionPercent*10000) << "\" />" << std::endl;
1122+
std::string str(s.str());
1123+
sim_communication_port.send(str);
1124+
} else if (sim_communication_port_open) {
1125+
std::stringstream s;
1126+
s << (int)(completionPercent*10000) << " " << phase << endl;
1127+
std::string str(s.str());
1128+
sim_communication_port.send(str);
1129+
}
1130+
#endif
1131+
}
1132+
9951133
} // extern "C"

SimulationRuntime/c/simulation/simulation_runtime.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,7 @@ extern const char* getNameString(const char** ptr);
7474
extern double getSimulationStepSize();
7575
extern void printSimulationStepSize(double in_stepSize, double time);
7676

77-
extern void communicateStatus(const char *phase, double completionPercent);
77+
extern void communicateStatus(const char *phase, double completionPercent, double currentTime, double currentStepSize);
7878
extern void communicateMsg(char id, unsigned int size, const char *data);
7979

8080
/* the main function of the simulation runtime!
@@ -86,6 +86,8 @@ extern int _main_SimulationRuntime(int argc, char**argv, DATA *data, threadData_
8686
const char* prettyPrintNanoSec(int64_t ns, int *v);
8787
#endif
8888

89+
void setStreamPrintXML(int isXML);
90+
8991
#ifdef __cplusplus
9092
}
9193
#endif

SimulationRuntime/c/simulation/solver/perform_qss_simulation.c

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -211,7 +211,7 @@ int prefixedName_performQSSSimulation(DATA* data, threadData_t *threadData, SOLV
211211
while(solverInfo->currentTime < simInfo->stopTime)
212212
{
213213
modelica_integer success = 0;
214-
uinteger k = 0, j = 0;
214+
uinteger k = 0, j = 0;
215215

216216
threadData->currentErrorStage = ERROR_SIMULATION;
217217
omc_alloc_interface.collect_a_little();
@@ -280,9 +280,8 @@ int prefixedName_performQSSSimulation(DATA* data, threadData_t *threadData, SOLV
280280
tqp[ind] = tq[ind] + dTnextQ;
281281
nQh[ind] = nextQ;
282282

283-
if (0 != strcmp("ia", data->simulationInfo->outputFormat))
284-
{
285-
communicateStatus("Running", (solverInfo->currentTime-simInfo->startTime)/(simInfo->stopTime-simInfo->startTime));
283+
if (0 != strcmp("ia", data->simulationInfo->outputFormat)) {
284+
communicateStatus("Running", (solverInfo->currentTime-simInfo->startTime)/(simInfo->stopTime-simInfo->startTime), solverInfo->currentTime, 0.0);
286285
}
287286

288287
/* get the derivatives depending on state[ind] */

SimulationRuntime/c/simulation/solver/perform_simulation.c

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -141,9 +141,8 @@ static int simulationStep(DATA* data, threadData_t *threadData, SOLVER_INFO* sol
141141
{
142142
SIMULATION_INFO *simInfo = data->simulationInfo;
143143

144-
if(0 != strcmp("ia", data->simulationInfo->outputFormat))
145-
{
146-
communicateStatus("Running", (solverInfo->currentTime - simInfo->startTime)/(simInfo->stopTime - simInfo->startTime));
144+
if(0 != strcmp("ia", data->simulationInfo->outputFormat)) {
145+
communicateStatus("Running", (solverInfo->currentTime - simInfo->startTime)/(simInfo->stopTime - simInfo->startTime), solverInfo->currentTime, solverInfo->currentStepSize);
147146
}
148147
return solver_main_step(data, threadData, solverInfo);
149148
}

SimulationRuntime/c/simulation/solver/solver_main.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -548,7 +548,7 @@ int finishSimulation(DATA* data, threadData_t *threadData, SOLVER_INFO* solverIn
548548
}
549549

550550
if (0 != strcmp("ia", data->simulationInfo->outputFormat)) {
551-
communicateStatus("Finished", 1);
551+
communicateStatus("Finished", 1, solverInfo->currentTime, solverInfo->currentStepSize);
552552
}
553553

554554
/* we have output variables in the command line -output a,b,c */

0 commit comments

Comments
 (0)