FMI Library: part of JModelica.org
fmi1_logger_test.c
Go to the documentation of this file.
1 /*
2  Copyright (C) 2012 Modelon AB
3 
4  This program is free software: you can redistribute it and/or modify
5  it under the terms of the BSD style license.
6 
7  This program is distributed in the hope that it will be useful,
8  but WITHOUT ANY WARRANTY; without even the implied warranty of
9  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  FMILIB_License.txt file for more details.
11 
12  You should have received a copy of the FMILIB_License.txt file
13  along with this program. If not, contact Modelon AB <http://www.modelon.com>.
14 */
15 
16 #include <stdio.h>
17 #include <stdlib.h>
18 #include <stdarg.h>
19 #include <assert.h>
20 
21 #include "config_test.h"
22 #include <fmilib.h>
24 #include <JM/jm_portability.h>
25 
26 FILE* logFile;
27 
28 void logger(jm_callbacks* c, jm_string module, jm_log_level_enu_t log_level, jm_string message) {
29  char buf[10000];
30  const char* loadingstr = "Loading '";
31  /* need to replace platform specific message with a standard one */
32  if( (log_level == jm_log_level_info) &&
33  (strcmp(module, "FMILIB") == 0) &&
34  (strncmp(message, "Loading '", strlen(loadingstr)) == 0)
35  )
36  {
37  jm_snprintf(buf, 10000, "[INFO][FMILIB] Loading '-----' binary with '------' platform types\n");
38  }
39  else
40  jm_snprintf(buf, 10000, "[%s][%s] %s\n", jm_log_level_to_string(log_level), module, message);
41  printf("%s", buf);
42  fprintf(logFile, "%s", buf);
43 }
44 
45 void do_exit(int code)
46 {
47  /* getchar();*/
48  exit(code);
49 }
50 
52 {
53  fmi1_status_t fmistatus;
54  jm_status_enu_t jmstatus;
55 
56  jmstatus = fmi1_import_instantiate_model(fmu, "LoggerTesting");
57  if (jmstatus == jm_status_error) {
58  printf("fmi1_import_instantiate_model failed\n");
59  do_exit(CTEST_RETURN_FAIL);
60  }
61 
62  /* Logger message to print: */
63  {
64  fmi1_value_reference_t* vr;
65  size_t n;
66  size_t k;
67  const char* str[] = {
68  "###### Reals ######",
69  "OK HIGHT = #r0#", /* HIGHT */
70  "OK HIGHT_SPEED = #r1#", /* HIGHT_SPEED */
71  "OK GRAVITY = #r2#", /* GRAVITY */
72  "OK BOUNCE_COF = #r3#", /* BOUNCE_COF */
73  "Bad reference #r0",
74  "Bad reference #r-0",
75  "Bad reference #r-1",
76  "Bad reference #r100#",
77  "###### Integers ######",
78  "OK LOGGER_TEST_INTEGER = #i0#", /* LOGGER_TEST_INTEGER */
79  "Bad reference #i0",
80  "Bad reference #i-0",
81  "Bad reference #i-1",
82  "Bad reference #i100#",
83  "###### Booleans ######",
84  "OK LOGGER_TEST_BOOLEAN = #b0#", /* LOGGER_TEST_BOOLEAN */
85  "Bad reference #b0",
86  "Bad reference #b-0",
87  "Bad reference #b-1",
88  "Bad reference #b100#",
89  "###### Strings ######",
90  "OK LOGGER_TEST = #s0#", /* LOGGER_TEST */
91  "Bad reference #s0",
92  "Bad reference #s-0",
93  "Bad reference #s-1",
94  "Bad reference #s100#"
95  };
96 
97  n = sizeof(str)/sizeof(*str);
98  vr = calloc(n, sizeof(fmi1_value_reference_t));
99  for (k = 0; k < n; k++) {
100  vr[k] = VAR_S_LOGGER_TEST;
101  }
102 
103  fmistatus = fmi1_import_set_string(fmu, vr, n, str);
104  if(fmistatus != fmi1_status_ok) {
105  abort();
106  }
107 
108  { /* Print a really big message */
109 
110 #define MESSAGE_SIZE_TO_EXPAND_AND_PRINT 3000 /* Using fixed size since the log message is printed to a file and compared */
111 #if JM_MAX_ERROR_MESSAGE_SIZE + 200 > MESSAGE_SIZE_TO_EXPAND_AND_PRINT
112 #error This test triggers the logger function to allocate more memory than the default size JM_MAX_ERROR_MESSAGE_SIZE. If you change JM_MAX_ERROR_MESSAGE_SIZE, please update this test.
113 #endif
114  char longmessage[MESSAGE_SIZE_TO_EXPAND_AND_PRINT];
115  const char* str[1];
116 
117  str[0] = (const char*)&longmessage;
118  {
119  fmi1_value_reference_t vr = VAR_S_LOGGER_TEST;
120  int k;
121  char repmsg[] = "#r0# "; /* HIGHT */
122  for (k = 0; k < sizeof(longmessage)/sizeof(*longmessage) - 1; k++) {
123  longmessage[k] = repmsg[k%(sizeof(repmsg)/sizeof(*repmsg) - 1)];
124  }
125  longmessage[k] = '\0';
126 
127  fmistatus = fmi1_import_set_string(fmu, &vr, 1, str);
128  if(fmistatus != fmi1_status_ok) {
129  abort();
130  }
131  }
132  }
133 
134  free(vr);
135  }
136 
137 
139  return 0;
140 }
141 
142 int main(int argc, char *argv[])
143 {
144  fmi1_callback_functions_t callBackFunctions;
145  const char* FMUPath;
146  const char* tmpPath;
148  fmi_import_context_t* context;
149  fmi_version_enu_t version;
150  jm_status_enu_t status;
151  int register_active_fmu;
152  fmi1_import_t* fmu;
153  char* outfile;
154 
155  if(argc < 4) {
156  printf("Usage: %s <fmu_file> <temporary_dir> <output_file>\n", argv[0]);
157  do_exit(CTEST_RETURN_FAIL);
158  }
159 
160  FMUPath = argv[1];
161  tmpPath = argv[2];
162  outfile = argv[3];
163 
164  logFile = fopen(outfile, "wb");
165 
166  if(!logFile) {
167  printf("Could not open output file %s\n", outfile);
168  do_exit(CTEST_RETURN_FAIL);
169  }
170 
171  callbacks.malloc = malloc;
172  callbacks.calloc = calloc;
173  callbacks.realloc = realloc;
174  callbacks.free = free;
175  callbacks.logger = logger;
176  callbacks.log_level = jm_log_level_info;
177  callbacks.context = 0;
178 
179  callBackFunctions.logger = fmi1_log_forwarding;
180  callBackFunctions.allocateMemory = calloc;
181  callBackFunctions.freeMemory = free;
182 
183 #ifdef FMILIB_GENERATE_BUILD_STAMP
184  printf("Library build stamp:\n%s\n", fmilib_get_build_stamp());
185 #endif
186 
187  context = fmi_import_allocate_context(&callbacks);
188 
189  version = fmi_import_get_fmi_version(context, FMUPath, tmpPath);
190 
191  if(version != fmi_version_1_enu) {
192  printf("Only version 1.0 is supported so far\n");
193  do_exit(CTEST_RETURN_FAIL);
194  }
195 
196  fmu = fmi1_import_parse_xml(context, tmpPath);
197 
198  if(!fmu) {
199  printf("Error parsing XML, exiting\n");
200  do_exit(CTEST_RETURN_FAIL);
201  }
202 
203  register_active_fmu = 1; /* Must be used to use our logger. (jm standard prints to strerr which does not generate out put test file) */
204  status = fmi1_import_create_dllfmu(fmu, callBackFunctions, register_active_fmu);
205  if (status == jm_status_error) {
206  printf("Could not create the DLL loading mechanism(C-API test).\n");
207  do_exit(CTEST_RETURN_FAIL);
208  }
209 
210  test_logger(fmu);
211 
213 
214  fmi1_import_free(fmu);
215  fmi_import_free_context(context);
216  fclose(logFile);
217  return 0;
218 }
219 
220 
FMILIB_EXPORT jm_status_enu_t fmi1_import_instantiate_model(fmi1_import_t *fmu, fmi1_string_t instanceName)
Wrapper for the FMI function fmiInstantiateModel(...)
jm_calloc_f calloc
Allocate zero initialized memory.
Definition: jm_callbacks.h:77
size_t jm_callbacks * c
Non-critical issues.
Definition: jm_types.h:56
FMILIB_EXPORT int jm_snprintf(char *str, size_t size, const char *fmt,...)
C89 compatible implementation of C99 snprintf.
int test_logger(fmi1_import_t *fmu)
fmi_version_enu_t
Suported versions of FMI standard.
Definition: fmi_version.h:34
fmi1_callback_logger_ft logger
FMILIB_EXPORT const char * jm_log_level_to_string(jm_log_level_enu_t level)
Convert log level into a string.
#define MESSAGE_SIZE_TO_EXPAND_AND_PRINT
jm_log_level_enu_t
Log levels supported via the logger functions in jm_callbacks.
Definition: jm_types.h:51
fmi1_callback_allocate_memory_ft allocateMemory
FMILIB_EXPORT void fmi1_log_forwarding(fmi1_component_t c, fmi1_string_t instanceName, fmi1_status_t status, fmi1_string_t category, fmi1_string_t message,...)
An implementation of FMI 1.0 logger that forwards the messages to logger function inside jm_callbacks...
FILE * logFile
FMILIB_EXPORT void fmi1_import_destroy_dllfmu(fmi1_import_t *fmu)
Free a C-API struct. All memory allocated since the struct was created is freed.
jm_log_level_enu_t log_level
Logging level.
Definition: jm_callbacks.h:85
v callbacks
#define VAR_S_LOGGER_TEST
fmi1_capi_t * fmu
fmi1_status_t
int main(int argc, char *argv[])
FMILIB_EXPORT jm_status_enu_t fmi1_import_create_dllfmu(fmi1_import_t *fmu, fmi1_callback_functions_t callBackFunctions, int registerGlobally)
Create a C-API struct. The C-API struct is a placeholder for the FMI DLL functions.
FMILIB_EXPORT fmi1_import_t * fmi1_import_parse_xml(fmi_import_context_t *c, const char *dirName)
Parse FMI 1.0 XML file found in the directory dirName.
Include file to be used in client applications of the FMI Library.
jm_malloc_f malloc
Allocate non-initialized memory.
Definition: jm_callbacks.h:75
FMILIB_EXPORT fmi1_status_t fmi1_import_set_string(fmi1_import_t *fmu, const fmi1_value_reference_t vr[], size_t nvr, const fmi1_string_t value[])
Wrapper for the FMI function fmiSetString(...)
jm_voidp context
Arbitrary context pointer passed to the logger function.
Definition: jm_callbacks.h:87
const char * jm_string
A constant string.
Definition: jm_types.h:33
The callbacks struct is sent to all the modules in the library.
Definition: jm_callbacks.h:73
struct fmi_xml_context_t fmi_import_context_t
FMI version independent library context. Opaque struct returned from fmi_import_allocate_context() ...
FMILIB_EXPORT fmi_import_context_t * fmi_import_allocate_context(jm_callbacks *callbacks)
Create fmi_import_context_t structure.
fmi1_callback_free_memory_ft freeMemory
struct fmi1_import_t fmi1_import_t
FMU version 1.0 object.
void logger(jm_callbacks *c, jm_string module, jm_log_level_enu_t log_level, jm_string message)
FMILIB_EXPORT fmi_version_enu_t fmi_import_get_fmi_version(fmi_import_context_t *c, const char *fileName, const char *dirName)
Unzip an FMU specified by the fileName into directory dirName and parse XML to get FMI standard versi...
FMILIB_EXPORT void fmi_import_free_context(fmi_import_context_t *c)
Free memory allocated for the library context.
jm_realloc_f realloc
Re-allocate memory.
Definition: jm_callbacks.h:79
void do_exit(int code)
jm_status_enu_t
Return status codes.
Definition: jm_types.h:44
FMILIB_EXPORT void fmi1_import_free(fmi1_import_t *fmu)
Release the memory allocated.
FMILIB_EXPORT void fmi1_import_free_model_instance(fmi1_import_t *fmu)
Wrapper for the FMI function fmiFreeModelInstance(...)
jm_free_f free
Free-allocated memory.
Definition: jm_callbacks.h:81
jm_logger_f logger
Logging callback.
Definition: jm_callbacks.h:83