Skip to content

Commit

Permalink
- Converted options.cpp to C89 code, and made it more memory-efficient
Browse files Browse the repository at this point in the history
- Added option -clock=CPU (or -clock=RT) for the simulation executable (in case the user wants a different clock on Linux)


git-svn-id: https://openmodelica.org/svn/OpenModelica/trunk@15253 f25d12d1-65f4-0310-ae8a-bbce733d8d8e
  • Loading branch information
sjoelund committed Feb 21, 2013
1 parent a307afc commit a4250b3
Show file tree
Hide file tree
Showing 7 changed files with 105 additions and 65 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -31,32 +31,25 @@
#include "options.h"
#include "omc_error.h"

#include <string>

using namespace std;
#include <string.h>
#include <stdio.h>

int checkCommandLineArguments(int argc, char **argv)
{
for(int i=1; i<argc; ++i)
int i,j;
for(i=1; i<argc; ++i)
{
int error = 1; /* first, suggest an error anyway */
string tmpStr = string(argv[i]);

for(int j=1; j<FLAG_MAX; ++j)
int found=0;
for(j=1; j<FLAG_MAX; ++j)
{
if(tmpStr == ("-" + string(FLAG_NAME[j])))
{
if(FLAG_TYPE[j] == FLAG_TYPE_FLAG)
error = 0;
else if((FLAG_TYPE[j] == FLAG_TYPE_FLAG_VALUE) && (++i < argc))
error = 0;
if (((FLAG_TYPE[j] == FLAG_TYPE_FLAG) && flagSet(FLAG_NAME[j],1,argv+i)) ||
((FLAG_TYPE[j] == FLAG_TYPE_FLAG_VALUE) && flagSet(FLAG_NAME[j],1,argv+i) && (++i < argc)) ||
((FLAG_TYPE[j] == FLAG_TYPE_OPTION) && optionSet(FLAG_NAME[j],1,argv+i))) {
found=1;
break;
}
else if(tmpStr.substr(0,tmpStr.find("=")) == ("-" + string(FLAG_NAME[j])))
error = 0;
}

if(error)
{
if (!found) {
WARNING1(LOG_STDOUT, "invalid command line option: %s", argv[i]);
return 1;
}
Expand All @@ -67,46 +60,40 @@ int checkCommandLineArguments(int argc, char **argv)

int flagSet(const char *option, int argc, char** argv)
{
for(int i=0; i<argc;i++)
int i;
for (i=0; i<argc;i++)
{
if(("-"+string(option)) == string(argv[i]))
if (argv[i][0] == '-' && 0==strcmp(option,argv[i]+1))
return 1;
}
return 0;
}

int optionSet(const char *option, int argc, char** argv)
{
for(int i=0; i<argc;i++)
{
string tmpStr=string(argv[i]);
if(("-"+string(option)) == (tmpStr.substr(0,tmpStr.find("="))))
return 1;
}
return 0;
return getOption(option,argc,argv) != NULL;
}

/* returns the value of a flag on the form -flagname=value */
const string* getOption(const char *option, int argc, char **argv)
const char* getOption(const char *option, int argc, char **argv)
{
for(int i=0; i<argc;i++)
{
string tmpStr=string(argv[i]);
if(("-"+string(option)) == (tmpStr.substr(0,tmpStr.find("="))))
return new string(tmpStr.substr(tmpStr.find("=")+1));
int optLen = strlen(option), i;
for (i=0; i<argc;i++) {
if (argv[i][0] == '-' && 0==strncmp(option,argv[i]+1,optLen) && argv[i][optLen+1]=='=') {
return argv[i]+optLen+2;
}
}
return NULL;
}

/* returns the value of a flag on the form -flagname value */
const string* getFlagValue(const char *option, int argc, char **argv)
const char* getFlagValue(const char *option, int argc, char **argv)
{
for(int i=0; i<argc;i++)
int i;
for(i=0; i<argc-1;i++)
{
string tmpStr=string(argv[i]);
if(("-"+string(option)) == string(argv[i]))
if(argc > i+1)
return new string(argv[i+1]);
if (argv[i][0] == '-' && 0==strcmp(option,argv[i]+1))
return argv[i+1];
}
return NULL;
}
11 changes: 8 additions & 3 deletions SimulationRuntime/c/simulation/options.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,14 +32,19 @@
#ifndef OPTIONS_H
#define OPTIONS_H

#include <string>
#include "simulation_options.h"

#ifdef __cplusplus
extern "C" {
#endif
int checkCommandLineArguments(int argc, char **argv);

int flagSet(const char*, int, char**); /* -f */
int optionSet(const char *option, int argc, char** argv); /* -f=value */
const std::string* getOption(const char*, int, char **); /* -f=value; returns NULL if not found */
const std::string* getFlagValue(const char *, int , char **); /* -f value; returns NULL if not found */
const char* getOption(const char*, int, char **); /* -f=value; returns NULL if not found */
const char* getFlagValue(const char *, int , char **); /* -f value; returns NULL if not found */
#ifdef __cplusplus
}
#endif

#endif
58 changes: 41 additions & 17 deletions SimulationRuntime/c/simulation/simulation_runtime.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -155,7 +155,8 @@ void setTermMsg(const char *msg)
*/
void setGlobalVerboseLevel(int argc, char**argv)
{
const string *flags = getOption("lv", argc, argv);
const char *cflags = getOption("lv", argc, argv);
const string *flags = cflags ? new string(cflags) : NULL;
int i;
int error;

Expand Down Expand Up @@ -249,7 +250,8 @@ void setGlobalVerboseLevel(int argc, char**argv)

int getNonlinearSolverMethod(int argc, char**argv)
{
const string *method = getOption("nls", argc, argv);
const char *cflags = getOption("nls", argc, argv);
const string *method = cflags ? new string(cflags) : NULL;

if(!method)
return NS_HYBRID; /* default method */
Expand All @@ -273,7 +275,8 @@ int getNonlinearSolverMethod(int argc, char**argv)

int getlinearSolverMethod(int argc, char**argv)
{
const string *method = getOption("ls", argc, argv);
const char *cflags = getOption("ls", argc, argv);
const string *method = cflags ? new string(cflags) : NULL;

if(!method)
return LS_LAPACK; /* default method */
Expand Down Expand Up @@ -382,7 +385,7 @@ int startNonInteractiveSimulation(int argc, char**argv, DATA* data)

/* linear model option is set : <-l lintime> */
int create_linearmodel = optionSet("l", argc, argv);
string* lintime = (string*) getOption("l", argc, argv);
const char* lintime = getOption("l", argc, argv);

/* activated measure time option with LOG_STATS */
if((ACTIVE_STREAM(LOG_STATS) || flagSet("cpu", argc, argv)) && !measure_time_flag)
Expand All @@ -394,6 +397,23 @@ int startNonInteractiveSimulation(int argc, char**argv, DATA* data)
/* calc numStep */
data->simulationInfo.numSteps = static_cast<modelica_integer>((data->simulationInfo.stopTime - data->simulationInfo.startTime)/data->simulationInfo.stepSize);

{ /* Setup the clock */
enum omc_rt_clock_t clock = OMC_CLOCK_REALTIME;
const char *clockName;
if (clockName=getOption("clock",argc,argv)) {
if (0==strcmp(clockName,"CPU")) {
clock = OMC_CLOCK_CPUTIME;
} else if (0==strcmp(clockName,"RT")) {
clock = OMC_CLOCK_REALTIME;
} else {
WARNING1(LOG_STDOUT, "[unknown clock-type] got %s, expected CPU|RT. Defaulting to RT.", clockName);
}
}
if (rt_set_clock(clock)) {
WARNING1(LOG_STDOUT, "Chosen clock-type not available for the current platform. Defaulting to real-time.", clockName);
}
}

if(measure_time_flag)
{
modelInfoXmlInit(&data->modelData.modelDataXml);
Expand All @@ -410,13 +430,13 @@ int startNonInteractiveSimulation(int argc, char**argv, DATA* data)
if(lintime == NULL)
data->simulationInfo.stopTime = data->simulationInfo.startTime;
else
data->simulationInfo.stopTime = atof(lintime->c_str());
data->simulationInfo.stopTime = atof(lintime);
INFO1(LOG_STDOUT, "Linearization will performed at point of time: %f", data->simulationInfo.stopTime);
}

if(optionSet("s", argc, argv))
{
const string *method = getOption("s", argc, argv);
const string *method = new string(getOption("s", argc, argv));
if(method)
{
data->simulationInfo.solverMethod = method->c_str();
Expand All @@ -442,25 +462,29 @@ int startNonInteractiveSimulation(int argc, char**argv, DATA* data)
string outputVariablesAtEnd = "";
int cpuTime = flagSet("cpu", argc, argv);

if(optionSet("iim", argc, argv))
init_initMethod = *getOption("iim", argc, argv);
if(optionSet("iom", argc, argv))
init_optiMethod = *getOption("iom", argc, argv);
if(optionSet("iif", argc, argv))
init_file = *getOption("iif", argc, argv);
if(optionSet("iim", argc, argv)) {
init_initMethod = getOption("iim", argc, argv);
}
if(optionSet("iom", argc, argv)) {
init_optiMethod = getOption("iom", argc, argv);
}
if(optionSet("iif", argc, argv)) {
init_file = getOption("iif", argc, argv);
}
if(optionSet("iit", argc, argv))
{
init_time_string = *getOption("iit", argc, argv);
init_time_string = getOption("iit", argc, argv);
init_time = atof(init_time_string.c_str());
}
if(optionSet("ils", argc, argv))
{
init_lambda_steps_string = *getOption("ils", argc, argv);
init_lambda_steps_string = getOption("ils", argc, argv);
init_lambda_steps = atoi(init_lambda_steps_string.c_str());
}

if(flagSet("output", argc, argv))
outputVariablesAtEnd = *getFlagValue("output", argc, argv);
if(flagSet("output", argc, argv)) {
outputVariablesAtEnd = getFlagValue("output", argc, argv);
}

retVal = callSolver(data, result_file_cstr, init_initMethod, init_optiMethod, init_file, init_time, init_lambda_steps, outputVariablesAtEnd, cpuTime);

Expand Down Expand Up @@ -644,7 +668,7 @@ int initRuntimeAndSimulation(int argc, char**argv, DATA *data)

if(optionSet("help", argc, argv))
{
std::string option = *getOption("help", argc, argv);
std::string option = getOption("help", argc, argv);

for(i=1; i<FLAG_MAX; ++i)
{
Expand Down
21 changes: 18 additions & 3 deletions SimulationRuntime/c/util/rtclock.c
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,10 @@ double rt_total(int ix) {

#if defined(__MINGW32__) || defined(_MSC_VER)

int rt_set_clock(omc_rt_clock_t newClock) {
return newClock != OMC_CLOCK_REALTIME;
}

static LARGE_INTEGER performance_frequency;

void rt_tick(int ix) {
Expand Down Expand Up @@ -181,6 +185,10 @@ double rtclock_value (LARGE_INTEGER tp) {

#elif defined(__APPLE_CC__)

int rt_set_clock(omc_rt_clock_t newClock) {
return newClock != OMC_CLOCK_REALTIME;
}

void rt_tick(int ix) {
tick_tp[ix] = mach_absolute_time();
rt_clock_ncall[ix]++;
Expand Down Expand Up @@ -233,14 +241,21 @@ int rtclock_compare(uint64_t t1, uint64_t t2) {

#else

static clockid_t omc_clock = CLOCK_MONOTONIC_RAW;

int rt_set_clock(enum omc_rt_clock_t newClock) {
omc_clock = newClock == OMC_CLOCK_REALTIME ? CLOCK_MONOTONIC_RAW : CLOCK_PROCESS_CPUTIME_ID;
return 0;
}

void rt_tick(int ix) {
clock_gettime(CLOCK_MONOTONIC, &tick_tp[ix]);
clock_gettime(omc_clock, &tick_tp[ix]);
rt_clock_ncall[ix]++;
}

double rt_tock(int ix) {
struct timespec tock_tp = {0,0};
clock_gettime(CLOCK_MONOTONIC, &tock_tp);
clock_gettime(omc_clock, &tock_tp);
return (tock_tp.tv_sec - tick_tp[ix].tv_sec) + (tock_tp.tv_nsec - tick_tp[ix].tv_nsec)*1e-9;
}

Expand Down Expand Up @@ -270,7 +285,7 @@ void rt_clear_total(int ix)

void rt_accumulate(int ix) {
struct timespec tock_tp = {0,0};
clock_gettime(CLOCK_MONOTONIC, &tock_tp);
clock_gettime(omc_clock, &tock_tp);
acc_tp[ix].tv_sec += tock_tp.tv_sec -tick_tp[ix].tv_sec;
acc_tp[ix].tv_nsec += tock_tp.tv_nsec-tick_tp[ix].tv_nsec;
if(acc_tp[ix].tv_nsec >= 1e9) {
Expand Down
6 changes: 6 additions & 0 deletions SimulationRuntime/c/util/rtclock.h
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,12 @@ extern "C" {
#define SIM_PROF_ACC_EQ(ix) rt_accumulate(ix+SIM_TIMER_FIRST_FUNCTION+data->modelData.modelDataXml.nFunctions)
#define SIM_PROF_ADD_NCALL_EQ(ix,num) rt_add_ncall(ix+SIM_TIMER_FIRST_FUNCTION+data->modelData.modelDataXml.nFunctions,num)

enum omc_rt_clock_t {
OMC_CLOCK_REALTIME, /* CLOCK_MONOTONIC_RAW if available; else CLOCK_MONOTONIC */
OMC_CLOCK_CPUTIME /* Per-process CPU-time */
};

int rt_set_clock(enum omc_rt_clock_t clockType); /* non-zero on failure */
void rt_init(int numTimer);

void rt_tick(int ix);
Expand Down
6 changes: 4 additions & 2 deletions SimulationRuntime/c/util/simulation_options.c
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@

const char *FLAG_NAME[FLAG_MAX] = {
"LOG_UNKNOWN",

/* FLAG_CLOCK */ "clock",
/* FLAG_CPU */ "cpu",
/* FLAG_F */ "f",
/* FLAG_HELP */ "help",
Expand All @@ -58,7 +58,7 @@ const char *FLAG_NAME[FLAG_MAX] = {

const char *FLAG_DESC[FLAG_MAX] = {
"unknown",

/* FLAG_CLOCK */ "selects the type of clock to use -clock=RT or -clock=CPU",
/* FLAG_CPU */ "dumps the cpu-time into the results-file",
/* FLAG_F */ "value specifies a new setup XML file to the generated simulation code",
/* FLAG_HELP */ "get deteiled information the specifies the command-line flag",
Expand All @@ -85,6 +85,7 @@ const char *FLAG_DESC[FLAG_MAX] = {
const char *FLAG_DETAILED_DESC[FLAG_MAX] = {
"unknown",

/* FLAG_CLOCK */ "selects the type of clock to use -clock=RT or -clock=CPU\n RT=monotonic real-time clock, CPU=process-based CPU-time",
/* FLAG_CPU */ " - dumps the cpu-time into the result-file\n - $cpuTime is the variable name inside the result-file",
/* FLAG_F */ "value specifies a new setup XML file to the generated simulation code",
/* FLAG_HELP */ "get deteiled information the specifies the command-line flag\n e.g. -help=f prints detaild information for command-line flag f",
Expand All @@ -111,6 +112,7 @@ const char *FLAG_DETAILED_DESC[FLAG_MAX] = {
const int FLAG_TYPE[FLAG_MAX] = {
FLAG_TYPE_UNKNOWN,

/* FLAG_CLOCK */ FLAG_TYPE_OPTION,
/* FLAG_CPU */ FLAG_TYPE_FLAG,
/* FLAG_F */ FLAG_TYPE_OPTION,
/* FLAG_HELP */ FLAG_TYPE_OPTION,
Expand Down
1 change: 1 addition & 0 deletions SimulationRuntime/c/util/simulation_options.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ enum _FLAG
{
FLAG_UNKNOWN = 0,

FLAG_CLOCK,
FLAG_CPU,
FLAG_F,
FLAG_HELP,
Expand Down

0 comments on commit a4250b3

Please sign in to comment.