]> gerrit.simantics Code Review - simantics/fmil.git/blob - org.simantics.fmil.core/native/FMUSimulator/fmi_util.c.txt
Add atomic counter for instanceName and update README, fix loadFMU
[simantics/fmil.git] / org.simantics.fmil.core / native / FMUSimulator / fmi_util.c.txt
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 <assert.h>
17 #include <string.h>
18 #include <stdio.h>
19 #include <FMI/fmi_util.h>
20 #include <FMI/fmi_zip_unzip.h>
21
22
23 char* fmi_construct_dll_dir_name(jm_callbacks* callbacks, const char* fmu_unzipped_path) {
24         char* dir_path;
25         size_t len;
26
27         assert( fmu_unzipped_path && callbacks);
28
29         len = 
30                 strlen(fmu_unzipped_path) + strlen(FMI_FILE_SEP)
31                 + strlen(FMI_BINARIES) + strlen(FMI_FILE_SEP) 
32                 + strlen(FMI_PLATFORM) + strlen(FMI_FILE_SEP) + 1;
33
34         dir_path = (char*)callbacks->malloc(len);
35         if (dir_path == NULL) {
36                 jm_log_fatal(callbacks, "FMIUT", "Failed to allocate memory.");
37                 return NULL;
38         }
39
40         sprintf(dir_path, "%s%s%s%s%s%s", fmu_unzipped_path, FMI_FILE_SEP, FMI_BINARIES, FMI_FILE_SEP, FMI_PLATFORM, FMI_FILE_SEP);/*safe */
41
42         return dir_path;
43 }
44
45 char* fmi_construct_dll_file_name(jm_callbacks* callbacks, const char* dll_dir_name, const char* model_identifier) {
46         char* fname;
47         size_t len;
48         assert(callbacks && model_identifier);
49         len = 
50                 strlen(dll_dir_name) +
51                 strlen(model_identifier) 
52                 + strlen(FMI_DLL_EXT) + 1;
53         fname = (char*)callbacks->malloc(len);
54         if (fname == NULL) {
55                 jm_log_fatal(callbacks, "FMIUT", "Failed to allocate memory.");
56                 return NULL;
57         }
58         sprintf(fname, "%s%s%s", dll_dir_name, model_identifier, FMI_DLL_EXT);/*safe */
59
60         return fname;
61 }
62
63 #include <stdio.h>
64 #include <stdlib.h>
65 #include <stdarg.h>
66 #include <string.h>
67 #include <errno.h>
68
69 #include <fmilib.h>
70
71 #ifdef __cplusplus
72 extern "C" {
73 #endif
74
75 typedef struct {
76         char *name;
77         char *description;
78         char *declaredType;
79         long vr;
80         /* 0 = real
81         // 1 = integer
82         // 2 = boolean
83         // 3 = string
84         // 4 = enumeration */
85         int type;
86         /* 0 = constant
87         // 1 = parameter
88         // 2 = discrete
89         // 3 = continuous
90         // 4 = unknown */
91         int variability;
92         /* 0 = input
93         // 1 = output
94         // 2 = internal
95         // 3 = none
96         // 4 = unknown */
97         int causality;
98 } FMIL_Variable;
99
100 typedef struct {
101         char *name;
102         char *description;
103         char *quantity;
104         char *unit;
105 } FMIL_DeclaredType;
106
107 #ifdef _MSC_VER
108 #define DLLEXPORT __declspec(dllexport)
109 #elif __GNUC__
110 #define DLLEXPORT __attribute__((visibility("default")))
111 #pragma warning Using GNUC default visibility
112 #else
113 #define DLLEXPORT
114 #pragma warning Empty dynamic link EXPORT defined
115 #endif
116
117 DLLEXPORT int FMI_CS_LOAD(const char *zipFilePath, const char *unzipFolder, void **fmuPointer, int *fmuVersion, const char **error);
118
119 DLLEXPORT int FMI1_CS_UNLOAD(void* fmu, const char **error);
120 DLLEXPORT FMIL_Variable *FMI1_CS_GET_VARIABLES(void* fmu, int *count, const char **error);
121 DLLEXPORT FMIL_DeclaredType *FMI1_CS_GET_DECLARED_TYPES(void* fmu, int *count, const char **error);
122 DLLEXPORT int FMI1_CS_INSTANTIATE(void* fmu, const char *instanceName, const char **error);
123 DLLEXPORT int FMI1_CS_INITIALIZE(void* fmu, const char **error);
124 DLLEXPORT int FMI1_CS_STEP(void* fmu, double masterTime, double stepSize, const char **error);
125 DLLEXPORT int FMI1_CS_SET_REAL(void* fmu, int vr, double value, const char **error);
126 DLLEXPORT double FMI1_CS_GET_REAL(void* fmu, int vr, const char **error);
127 DLLEXPORT int FMI1_CS_GET_REALS(void* fmu, int *vrs, double *values, int count, const char **error);
128
129 DLLEXPORT int FMI2_CS_UNLOAD(void* fmu, const char **error);
130 DLLEXPORT FMIL_Variable *FMI2_CS_GET_VARIABLES(void* fmu, int *count, const char **error);
131 DLLEXPORT FMIL_DeclaredType *FMI2_CS_GET_DECLARED_TYPES(void* fmu, int *count, const char **error);
132 DLLEXPORT int FMI2_CS_INSTANTIATE(void* fmu, const char *instanceName, const char **error);
133 DLLEXPORT int FMI2_CS_INITIALIZE(void* fmu, const char **error);
134 DLLEXPORT int FMI2_CS_STEP(void* fmu, double masterTime, double stepSize, const char **error);
135 DLLEXPORT int FMI2_CS_SET_REAL(void* fmu, int vr, double value, const char **error);
136 DLLEXPORT double FMI2_CS_GET_REAL(void* fmu, int vr, const char **error);
137 DLLEXPORT int FMI2_CS_GET_REALS(void* fmu, int *vrs, double *values, int count, const char **error);
138
139 #ifdef __cplusplus
140 }
141 #endif
142
143 #define BUFFER 4096
144
145 /* Logger function used by the C-API */
146 void importlogger(jm_callbacks* c, jm_string module, jm_log_level_enu_t log_level, jm_string message)
147 {
148         printf("module = %s, log level = %d: %s\n", module, log_level, message);
149 }
150
151 /* Logger function used by the FMU internally */
152 void fmilogger(fmi1_component_t c, fmi1_string_t instanceName, fmi1_status_t status, fmi1_string_t category, fmi1_string_t message, ...)
153 {
154         char msg[BUFFER];
155     int len;
156         va_list argp;   
157         va_start(argp, message);
158         /*len=jm_vsnprintf(msg, BUFFER, message, argp);
159         printf("fmiStatus = %d;  %s (%s): %s\n", status, instanceName, category, msg);
160     if(len > BUFFER) {
161         printf("Warning: message was trancated");
162     }*/
163 }
164
165 int FMI_CS_LOAD(const char *zipFilePath, const char *unzipFolder, void **fmuPointer, int *fmuVersion, const char **error) {
166
167         fmi1_callback_functions_t callBackFunctions;
168         fmi2_callback_functions_t callBackFunctions2;
169         fmi_import_context_t* context;
170         fmi_version_enu_t version;
171     jm_status_enu_t status;
172         fmi1_import_t *fmu;
173         fmi2_import_t *fmu2;
174         jm_callbacks* callbacks;
175
176         callbacks = (jm_callbacks *)calloc(1, sizeof(jm_callbacks));
177
178         callbacks->malloc = malloc;
179     callbacks->calloc = calloc;
180     callbacks->realloc = realloc;
181     callbacks->free = free;
182     callbacks->logger = importlogger;
183 #ifdef _DEBUG
184     callbacks->log_level = jm_log_level_debug;
185 #else
186         callbacks->log_level = jm_log_level_warning;
187 #endif
188     callbacks->context = 0;
189
190         context = fmi_import_allocate_context(callbacks);
191
192         version = fmi_import_get_fmi_version(context, zipFilePath, unzipFolder);
193
194         if (version == fmi_version_1_enu ) {
195                 fmu = fmi1_import_parse_xml(context, unzipFolder);
196                 if (fmi1_import_get_fmu_kind(fmu) != fmi1_fmu_kind_enu_cs_standalone && fmi1_import_get_fmu_kind(fmu) != fmi1_fmu_kind_enu_cs_tool) {
197                         *error = "Provided FMU is version 1 but wrong type me (Model Exchange) when it should be cs (Co-Simulation)";
198                         return 2; /* wrong type, should be co-simulation */
199                 }
200                 
201                 callBackFunctions.logger = fmilogger;
202                 callBackFunctions.allocateMemory = calloc;
203                 callBackFunctions.freeMemory = free;
204
205                 status = fmi1_import_create_dllfmu(fmu, callBackFunctions, 0);
206                 if (status == jm_status_error) {
207                         *error = fmi1_import_get_last_error(fmu);
208                         return 3;
209                 }
210
211                 *fmuPointer = fmu;
212                 *fmuVersion = 1;
213         } else if (version == fmi_version_2_0_enu) {
214                 fmu2 = fmi2_import_parse_xml(context, unzipFolder, 0);
215
216                 if (fmi2_import_get_fmu_kind(fmu2) != fmi1_fmu_kind_enu_cs_standalone && fmi2_import_get_fmu_kind(fmu2) != fmi1_fmu_kind_enu_cs_tool) {
217                         *error = "Provided FMU is version 2.0 but wrong type me (Model Exchange) when it should be cs (Co-Simulation)";
218                         return 2; /* wrong type, should be co-simulation */
219                 }
220
221                 callBackFunctions2.logger = fmi2_log_forwarding;
222                 callBackFunctions2.allocateMemory = calloc;
223                 callBackFunctions2.freeMemory = free;
224                 callBackFunctions2.componentEnvironment = fmu2;
225
226                 status = fmi2_import_create_dllfmu(fmu2, fmi2_fmu_kind_cs, &callBackFunctions2);
227                 if (status == jm_status_error) {
228                         *error = fmi2_import_get_last_error(fmu2);
229                         return 3;
230                 }
231                 
232                 *fmuPointer = fmu2;
233                 *fmuVersion = 2;
234         } else {
235             *error = "Couldn't find version of FMU - possibly incorrect file!";
236             return 1;
237         }
238         
239         fmi_import_free_context(context);
240
241         return 0; /* success */
242 }
243
244 int FMI1_CS_UNLOAD(void *fmu_, const char **error) {
245         fmi1_import_t *fmu = (fmi1_import_t *)fmu_;
246         fmi1_import_destroy_dllfmu(fmu);
247         fmi1_import_free(fmu);
248         return 0;
249 }
250
251 int FMI2_CS_UNLOAD(void *fmu_, const char **error) {
252         fmi2_import_t *fmu = (fmi2_import_t *)fmu_;
253         fmi2_import_destroy_dllfmu(fmu);
254         fmi2_import_free(fmu);
255         return 0;
256 }
257
258 /*
259  if(!vt) {
260         printf("No type definition\n");
261         return;
262     }
263
264     quan = fmi1_import_get_type_quantity(vt);
265
266     printf("Type %s\n description: %s\n",  fmi1_import_get_type_name(vt), fmi1_import_get_type_description(vt));
267
268     printf("Base type: %s\n", fmi1_base_type_to_string(fmi1_import_get_base_type(vt)));
269
270     if(quan) {
271         printf("Quantity: %s\n", quan);
272     }
273     switch(fmi1_import_get_base_type(vt)) {
274     case fmi1_base_type_real: {
275         fmi1_import_real_typedef_t* rt = fmi1_import_get_type_as_real(vt);
276         fmi1_real_t min = fmi1_import_get_real_type_min(rt);
277         fmi1_real_t max = fmi1_import_get_real_type_max(rt);
278         fmi1_real_t nom = fmi1_import_get_real_type_nominal(rt);
279         fmi1_import_unit_t* u = fmi1_import_get_real_type_unit(rt);
280         fmi1_import_display_unit_t* du = fmi1_import_get_type_display_unit(rt);
281
282         printf("Min %g, max %g, nominal %g\n", min, max, nom);
283
284         if(u) {
285             printf("Unit: %s\n", fmi1_import_get_unit_name(u));
286         }
287         if(du) {
288             printf("Display unit: %s, gain: %g, offset: %g, is relative: %s",
289                    fmi1_import_get_display_unit_name(du),
290                    fmi1_import_get_display_unit_gain(du),
291                    fmi1_import_get_display_unit_offset(du),
292                    fmi1_import_get_real_type_is_relative_quantity(rt)?"yes":"no"
293                    );
294         }
295
296         break;
297     }
298     case fmi1_base_type_int:{
299         fmi1_import_integer_typedef_t* it = fmi1_import_get_type_as_int(vt);
300         int min = fmi1_import_get_integer_type_min(it);
301         int max = fmi1_import_get_integer_type_max(it);
302         printf("Min %d, max %d\n", min, max);
303         break;
304     }
305     case fmi1_base_type_bool:{
306         break;
307     }
308     case fmi1_base_type_str:{
309         break;
310     }
311     case fmi1_base_type_enum:{
312         fmi1_import_enumeration_typedef_t* et = fmi1_import_get_type_as_enum(vt);
313         int min = fmi1_import_get_enum_type_min(et);
314         int max = fmi1_import_get_enum_type_max(et);
315         printf("Min %d, max %d\n", min, max);
316         {
317             size_t ni;
318                         unsigned i;
319             ni = fmi1_import_get_enum_type_size(et);
320                         i = (unsigned)(ni);
321                         assert( i == ni);
322             printf("There are %u items \n",(unsigned)ni);
323             for(i = 0; i < ni; i++) {
324                 printf("[%u] %s (%s) \n", (unsigned)i+1, fmi1_import_get_enum_type_item_name(et, i), fmi1_import_get_enum_type_item_description(et, i));
325             }
326         }
327         break;
328     }
329     default:
330         printf("Error in fmiGetBaseType()\n");
331     }
332 */
333
334
335 FMIL_Variable *FMI1_CS_GET_VARIABLES(void *fmu, int *count, const char **error) {
336
337     int i;
338         FMIL_Variable *result;
339     fmi1_import_variable_list_t* vl = fmi1_import_get_variable_list((fmi1_import_t *)fmu);
340         fmi1_import_variable_typedef_t* type;
341
342     count[0] = fmi1_import_get_variable_list_size(vl);
343
344         result = (FMIL_Variable *)malloc(count[0]*sizeof(FMIL_Variable));
345
346     for(i = 0; i < count[0]; i++) {
347
348         fmi1_import_variable_t* var = fmi1_import_get_variable(vl, i);
349         if(!var) {
350
351                         printf("Something wrong with variable %d \n",i);
352                         return 0;
353
354                 } else {
355
356                         result[i].name = fmi1_import_get_variable_name(var);
357                         result[i].description = fmi1_import_get_variable_description(var);
358
359                         switch  (fmi1_import_get_variability(var)) {
360                         case fmi1_variability_enu_constant:
361                                 result[i].variability = 0;
362                                 break;
363                         case fmi1_variability_enu_parameter:
364                                 result[i].variability = 1;
365                                 break;
366                         case fmi1_variability_enu_discrete:
367                                 result[i].variability = 2;
368                                 break;
369                         case fmi1_variability_enu_continuous:
370                                 result[i].variability = 3;
371                                 break;
372                         case fmi1_variability_enu_unknown:
373                                 result[i].variability = 4;
374                                 break;
375                         }
376
377                         switch  (fmi1_import_get_causality(var)) {
378                         case fmi1_causality_enu_input:
379                                 result[i].causality = 0;
380                                 break;
381                         case fmi1_causality_enu_output:
382                                 result[i].causality = 1;
383                                 break;
384                         case fmi1_causality_enu_internal:
385                                 result[i].causality = 2;
386                                 break;
387                         case fmi1_causality_enu_none:
388                                 result[i].causality = 3;
389                                 break;
390                         case fmi1_causality_enu_unknown:
391                                 result[i].causality = 4;
392                                 break;
393                         }
394
395                         switch  (fmi1_import_get_variable_base_type(var)) {
396                         case fmi1_base_type_real:
397                                 result[i].type = 0;
398                                 break;
399                         case fmi1_base_type_int:
400                                 result[i].type = 1;
401                                 break;
402                         case fmi1_base_type_bool:
403                                 result[i].type = 2;
404                                 break;
405                         case fmi1_base_type_str:
406                                 result[i].type = 3;
407                                 break;
408                         case fmi1_base_type_enum:
409                                 result[i].type = 4;
410                                 break;
411                         }
412                         
413                         result[i].vr = fmi1_import_get_variable_vr(var);
414
415                         type = fmi1_import_get_variable_declared_type(var);
416                         if(type) {
417                                 result[i].declaredType = fmi1_import_get_type_name(type);
418                         } else {
419                                 result[i].declaredType = 0;
420                         }
421
422                 }
423
424     }
425
426     fmi1_import_free_variable_list(vl);
427
428         return result;
429
430 }
431
432 FMIL_Variable *FMI2_CS_GET_VARIABLES(void *fmu, int *count, const char **error) {
433
434     int i;
435         FMIL_Variable *result;
436     fmi2_import_variable_list_t* vl = fmi2_import_get_variable_list((fmi2_import_t *)fmu, 0);
437         fmi2_import_variable_typedef_t* type;
438
439     count[0] = fmi2_import_get_variable_list_size(vl);
440
441         result = (FMIL_Variable *)malloc(count[0]*sizeof(FMIL_Variable));
442
443     for(i = 0; i < count[0]; i++) {
444
445         fmi2_import_variable_t* var = fmi2_import_get_variable(vl, i);
446         if(!var) {
447
448                         printf("Something wrong with variable %d \n",i);
449                         return 0;
450
451                 } else {
452
453                         result[i].name = fmi2_import_get_variable_name(var);
454                         result[i].description = fmi2_import_get_variable_description(var);
455
456                         switch  (fmi2_import_get_variability(var)) {
457                         case fmi2_variability_enu_constant:
458                                 result[i].variability = 0;
459                                 break;
460                         case fmi2_variability_enu_fixed:
461                         case fmi2_variability_enu_tunable:
462                                 result[i].variability = 1;
463                                 break;
464                         case fmi2_variability_enu_discrete:
465                                 result[i].variability = 2;
466                                 break;
467                         case fmi2_variability_enu_continuous:
468                                 result[i].variability = 3;
469                                 break;
470                         case fmi2_variability_enu_unknown:
471                                 result[i].variability = 4;
472                                 break;
473                         }
474
475                         switch  (fmi2_import_get_causality(var)) {
476                         case fmi2_causality_enu_input:
477                                 result[i].causality = 0;
478                                 break;
479                         case fmi2_causality_enu_output:
480                                 result[i].causality = 1;
481                                 break;
482                         case fmi2_causality_enu_local:
483                                 result[i].causality = 2;
484                                 break;
485                         case fmi2_causality_enu_independent:
486                                 result[i].causality = 3;
487                                 break;
488                         case fmi2_causality_enu_unknown:
489                                 result[i].causality = 4;
490                                 break;
491                         }
492
493                         switch  (fmi2_import_get_variable_base_type(var)) {
494                         case fmi2_base_type_real:
495                                 result[i].type = 0;
496                                 break;
497                         case fmi2_base_type_int:
498                                 result[i].type = 1;
499                                 break;
500                         case fmi2_base_type_bool:
501                                 result[i].type = 2;
502                                 break;
503                         case fmi2_base_type_str:
504                                 result[i].type = 3;
505                                 break;
506                         case fmi2_base_type_enum:
507                                 result[i].type = 4;
508                                 break;
509                         }
510                         
511                         result[i].vr = fmi2_import_get_variable_vr(var);
512
513                         type = fmi2_import_get_variable_declared_type(var);
514                         if(type) {
515                                 result[i].declaredType = fmi2_import_get_type_name(type);
516                         } else {
517                                 result[i].declaredType = 0;
518                         }
519
520                 }
521
522     }
523
524     fmi2_import_free_variable_list(vl);
525
526         return result;
527
528 }
529
530 FMIL_DeclaredType *FMI1_CS_GET_DECLARED_TYPES(void *fmu, int *count, const char **error) {
531
532         FMIL_DeclaredType *result;
533     fmi1_import_type_definitions_t* td = fmi1_import_get_type_definitions((fmi1_import_t *)fmu);
534         fmi1_import_variable_typedef_t* type;
535     unsigned i, ntd = (unsigned)fmi1_import_get_type_definition_number(td);
536
537     count[0] = ntd;
538
539         result = (FMIL_DeclaredType *)malloc(count[0]*sizeof(FMIL_DeclaredType));
540
541     for(i = 0; i < ntd; i++) {
542       type = fmi1_import_get_typedef(td, i);
543       result[i].name = fmi1_import_get_type_name(type);
544       result[i].description = fmi1_import_get_type_description(type);
545           result[i].quantity = fmi1_import_get_type_quantity(type);
546       result[i].unit = 0;
547
548           switch(fmi1_import_get_base_type(type)) {
549                    case fmi1_base_type_real: {
550                                 fmi1_import_real_typedef_t* rt = fmi1_import_get_type_as_real(type);
551                         fmi1_import_unit_t* u = fmi1_import_get_real_type_unit(rt);
552                                 if(u) result[i].unit = fmi1_import_get_unit_name(u);
553                    }
554           }
555
556     }
557
558         return result;
559
560 }
561
562 FMIL_DeclaredType *FMI2_CS_GET_DECLARED_TYPES(void *fmu, int *count, const char **error) {
563
564         FMIL_DeclaredType *result;
565     fmi2_import_type_definitions_t* td = fmi2_import_get_type_definitions((fmi2_import_t *)fmu);
566         fmi2_import_variable_typedef_t* type;
567     unsigned i, ntd = (unsigned)fmi2_import_get_type_definition_number(td);
568
569     count[0] = ntd;
570
571         result = (FMIL_DeclaredType *)malloc(count[0]*sizeof(FMIL_DeclaredType));
572
573     for(i = 0; i < ntd; i++) {
574       type = fmi2_import_get_typedef(td, i);
575       result[i].name = fmi2_import_get_type_name(type);
576       result[i].description = fmi2_import_get_type_description(type);
577           result[i].quantity = fmi2_import_get_type_quantity(type);
578       result[i].unit = 0;
579
580           switch(fmi2_import_get_base_type(type)) {
581                    case fmi2_base_type_real: {
582                                 fmi2_import_real_typedef_t* rt = fmi2_import_get_type_as_real(type);
583                         fmi2_import_unit_t* u = fmi2_import_get_real_type_unit(rt);
584                                 if(u) result[i].unit = fmi2_import_get_unit_name(u);
585                    }
586           }
587
588     }
589
590         return result;
591
592 }
593
594 int FMI1_CS_INSTANTIATE(void *fmu, const char *instanceName, const char **error) {
595
596         fmi1_string_t fmuLocation;
597         fmi1_string_t mimeType;
598         fmi1_real_t timeout;
599         fmi1_boolean_t visible;
600         fmi1_boolean_t interactive;
601         fmi1_boolean_t loggingOn;
602
603         jm_status_enu_t jmstatus;
604
605         fmuLocation = "";
606         mimeType = "";
607         timeout = 0;
608         visible = fmi1_false;
609         interactive = fmi1_false;
610         loggingOn = fmi1_true;
611
612         jmstatus = fmi1_import_instantiate_slave((fmi1_import_t*)fmu, instanceName, NULL, NULL, timeout, fmi1_false, fmi1_false);
613         if (jmstatus == jm_status_error) {
614                 *error = fmi1_import_get_last_error((fmi1_import_t*)fmu);
615                 return 1;
616         }
617         return 0;
618 }
619
620 int FMI2_CS_INSTANTIATE(void *fmu, const char *instanceName, const char **error) {
621
622         fmi2_string_t fmuLocation;
623         fmi2_string_t mimeType;
624         fmi2_real_t timeout;
625         fmi2_boolean_t visible;
626         fmi2_boolean_t interactive;
627         fmi2_boolean_t loggingOn;
628         jm_status_enu_t jmstatus;
629
630         fmuLocation = "";
631         mimeType = "";
632         timeout = 0;
633         visible = fmi2_false;
634         jmstatus = fmi2_import_instantiate((fmi2_import_t*)fmu, instanceName, fmi2_cosimulation, NULL, visible);
635         if (jmstatus == jm_status_error) {
636                 *error = fmi2_import_get_last_error((fmi2_import_t*)fmu);
637                 return 1;
638         }
639         return 0;
640 }
641
642 int FMI1_CS_INITIALIZE(void *fmu, const char **error) {
643
644         fmi1_status_t status;
645         fmi1_real_t tStart;
646         fmi1_real_t tStop;
647         fmi1_boolean_t StopTimeDefined;
648
649         tStart = 0;
650         tStop = 10;
651         StopTimeDefined = fmi1_false;
652
653         status = fmi1_import_initialize_slave((fmi1_import_t *)fmu, tStart, StopTimeDefined, tStop);
654         if (status == fmi1_status_error || status == fmi1_status_fatal) {
655                 printf("fmi1_capi_initialize_slave:              Failed\n");
656                 return 0;
657         } else {
658                 printf("fmi1_capi_initialize_slave:              Success\n");
659         }
660         return 0;
661
662 }
663
664 int FMI2_CS_INITIALIZE(void *fmu, const char **error) {
665
666         fmi2_real_t tStart;
667         fmi2_real_t tStop;
668         fmi2_boolean_t StopTimeDefined;
669         fmi2_real_t relativeTol = 1e-4;
670
671         fmi2_status_t fmistatus;
672
673         tStart = 0;
674         tStop = 10;
675         StopTimeDefined = fmi1_false;
676
677         fmistatus = fmi2_import_setup_experiment((fmi2_import_t*)fmu, fmi2_true, relativeTol, tStart, StopTimeDefined, tStop);
678     if(fmistatus != fmi2_status_ok) {
679         *error = ("fmi2_import_setup_experiment failed\n");
680                 return 1;
681     }
682
683     fmistatus = fmi2_import_enter_initialization_mode((fmi2_import_t*)fmu);
684     if(fmistatus != fmi2_status_ok) {
685         *error = ("fmi2_import_enter_initialization_mode failed\n");
686                 return 1;
687     }
688
689     fmistatus = fmi2_import_exit_initialization_mode((fmi2_import_t*)fmu);
690     if(fmistatus != fmi2_status_ok) {
691         *error = ("fmi2_import_exit_initialization_mode failed\n");
692                 return 1;
693     }   
694
695         return 0;
696 }
697
698 int FMI1_CS_STEP(void *fmu, double masterTime, double stepSize, const char **error) {
699
700     fmi1_status_t status;
701
702         status = fmi1_import_do_step((fmi1_import_t *)fmu, (fmi1_real_t)masterTime, (fmi1_real_t)stepSize, fmi1_true);
703         if (status == fmi1_status_error || status == fmi1_status_fatal) {
704                 *error = "Error happened during stepping!";
705                 return 1;
706         }
707         return 0;
708 }
709
710 int FMI2_CS_STEP(void *fmu, double masterTime, double stepSize, const char **error) {
711
712     fmi2_status_t status;
713
714         status = fmi2_import_do_step((fmi2_import_t *)fmu, (fmi2_real_t)masterTime, (fmi2_real_t)stepSize, fmi2_true);
715         if (status == fmi2_status_error || status == fmi2_status_fatal) {
716                 *error = "Error happened during stepping!";
717                 return 1;
718         }
719         return 0;
720 }
721
722 int FMI1_CS_SET_REAL(void *fmu, int valueId, double value, const char **error) {
723
724         fmi1_status_t status;
725
726         fmi1_value_reference_t vr = valueId;
727         status = fmi1_import_set_real((fmi1_import_t *)fmu, &vr, 1, &value);
728         if (status == fmi1_status_error || status == fmi1_status_fatal) {
729                 *error = "Error happened during setting real value!";
730                 return 1;
731         }
732         return 0;
733 }
734
735 int FMI2_CS_SET_REAL(void *fmu, int valueId, double value, const char **error) {
736
737         fmi2_status_t status;
738
739         fmi2_value_reference_t vr = valueId;
740         status = fmi2_import_set_real((fmi2_import_t *)fmu, &vr, 1, &value);
741         if (status == fmi2_status_error || status == fmi2_status_fatal) {
742                 *error = "Error happened during setting real value!";
743                 return 1;
744         }
745         return 0;
746 }
747
748 double FMI1_CS_GET_REAL(void *fmu, int valueReference, const char **error) {
749
750         fmi1_value_reference_t vr = valueReference;
751         fmi1_real_t value;
752
753         fmi1_status_t status;
754
755         status = fmi1_import_get_real((fmi1_import_t *)fmu, &vr, 1, &value);
756         if (status == fmi1_status_error || status == fmi1_status_fatal) {
757                 *error = "Error happened during getting real value!";
758         }
759         return value;
760 }
761
762 double FMI2_CS_GET_REAL(void *fmu, int valueReference, const char **error) {
763
764         fmi2_value_reference_t vr = valueReference;
765         fmi2_real_t value;
766
767         fmi2_status_t status;
768
769         status = fmi2_import_get_real((fmi2_import_t *)fmu, &vr, 1, &value);
770         if (status == fmi2_status_error || status == fmi2_status_fatal) {
771                 *error = "Error happened during setting real value!";
772         }
773         return value;
774 }
775
776 int FMI1_CS_GET_REALS(void *fmu, int *valueReferences, double *result, int count, const char **error) {
777
778         fmi1_value_reference_t *vrs = (fmi1_value_reference_t*) valueReferences;
779         fmi1_real_t value;
780
781         fmi1_status_t status;
782
783         status = fmi1_import_get_real((fmi1_import_t *)fmu, vrs, count, result);
784         if (status == fmi1_status_error || status == fmi1_status_fatal) {
785                 *error = "Error happened during getting reals value!";
786         }
787         return 0;
788 }
789
790 int FMI2_CS_GET_REALS(void *fmu, int *valueReferences, double *result, int count, const char **error) {
791
792         fmi2_value_reference_t *vrs = (fmi2_value_reference_t*) valueReferences;
793         fmi2_real_t value;
794
795         fmi2_status_t status;
796
797         status = fmi2_import_get_real((fmi2_import_t *)fmu, vrs, count, result);
798         if (status == fmi2_status_error || status == fmi2_status_fatal) {
799                 *error = "Error happened during getting reals value!";
800         }
801         return 0;
802
803 }