Beispiel #1
0
/* Load FMI 1.0 Model Exchange functions */
static jm_status_enu_t fmi1_capi_load_me_fcn(fmi1_capi_t* fmu)
{
	jm_status_enu_t jm_status = jm_status_success;

	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Loading functions for the model exchange interface"); 

	LOAD_DLL_FUNCTION(fmiGetModelTypesPlatform);
	LOAD_DLL_FUNCTION(fmiInstantiateModel);
	LOAD_DLL_FUNCTION(fmiFreeModelInstance);
	LOAD_DLL_FUNCTION(fmiSetTime);
	LOAD_DLL_FUNCTION(fmiSetContinuousStates);
	LOAD_DLL_FUNCTION(fmiCompletedIntegratorStep);
	LOAD_DLL_FUNCTION(fmiInitialize);
	LOAD_DLL_FUNCTION(fmiGetDerivatives);
	LOAD_DLL_FUNCTION(fmiGetEventIndicators);
	LOAD_DLL_FUNCTION(fmiEventUpdate);
	LOAD_DLL_FUNCTION(fmiGetContinuousStates);
	LOAD_DLL_FUNCTION(fmiGetNominalContinuousStates);
	LOAD_DLL_FUNCTION(fmiGetStateValueReferences);
	LOAD_DLL_FUNCTION(fmiTerminate);

	LOAD_DLL_FUNCTION(fmiGetVersion);
	LOAD_DLL_FUNCTION(fmiSetDebugLogging);
	LOAD_DLL_FUNCTION(fmiSetReal);
	LOAD_DLL_FUNCTION(fmiSetInteger);
	LOAD_DLL_FUNCTION(fmiSetBoolean);
	LOAD_DLL_FUNCTION(fmiSetString);
	LOAD_DLL_FUNCTION(fmiGetReal);
	LOAD_DLL_FUNCTION(fmiGetInteger);
	LOAD_DLL_FUNCTION(fmiGetBoolean);
	LOAD_DLL_FUNCTION(fmiGetString);

	return jm_status; 
}
Beispiel #2
0
jm_status_enu_t jm_rmdir(jm_callbacks* cb, const char* dir) {
#ifdef WIN32
	const char* fmt_cmd = "rmdir /s /q %s";
#else
    const char* fmt_cmd = "rm -rf %s";
#endif
    char * buf = (char*)cb->calloc(sizeof(char), strlen(dir)+strlen(fmt_cmd)+1);
	if(!cb) {
		cb = jm_get_default_callbacks();
	}
	if(!buf) {
	    jm_log_error(cb,module,"Could not allocate memory");
		return jm_status_error;
	}
    sprintf(buf, fmt_cmd, dir);/*safe*/
#ifdef WIN32
	{
		char* ch = buf+strlen(fmt_cmd) - 2;
		while(*ch) {
			if(*ch == '/') *ch = '\\';
			ch++;
		}
	}
#endif
    jm_log_verbose(cb,module,"Removing %s", dir);
    if(system(buf)) {
	    jm_log_error(cb,module,"Error removing %s (%s)", dir, strerror(errno));
		return jm_status_error;
	}
    cb->free(buf);
	return jm_status_success;
}
int fmi2_xml_handle_InitialUnknowns(fmi2_xml_parser_context_t *context, const char* data) {
    if (!data) {
        jm_log_verbose(context->callbacks, module, "Parsing XML element InitialUnknowns");
        /*  reset handles for the elements that are specific under InitialUnknowns */
        fmi2_xml_set_element_handle(context, "Unknown", FMI2_XML_ELM_ID(InitialUnknown));
    }
    return 0;
}
Beispiel #4
0
fmi1_import_t* fmi1_import_parse_xml( fmi_import_context_t* context, const char* dirPath) {
	char* xmlPath; 
	char absPath[FILENAME_MAX + 2];
	jm_callbacks* cb;
	fmi1_import_t* fmu;

	if(!context) return 0;

	cb = context->callbacks; 
	
	xmlPath =  fmi_import_get_model_description_path(dirPath, context->callbacks);

	fmu = fmi1_import_allocate(context->callbacks);

	if(!fmu) {
		context->callbacks->free(xmlPath);
		return 0;
	}
	
	jm_log_verbose( cb, "FMILIB", "Parsing model description XML");

	if(fmi1_xml_parse_model_description( fmu->md, xmlPath)) {
		fmi1_import_free(fmu);
		cb->free(xmlPath);
		return 0;
	}
	cb->free(xmlPath);
	
	fmu->dirPath =  (char*)cb->calloc(strlen(dirPath) + 1, sizeof(char));

	if(jm_get_dir_abspath(cb, dirPath, absPath, FILENAME_MAX + 2)) {
		fmu->location = fmi_import_create_URL_from_abs_path(cb, absPath);
	}
	
	if ((fmu->dirPath == NULL) || (fmu->location == 0)){
		jm_log_fatal( cb, "FMILIB", "Could not allocated memory");
		fmi1_import_free(fmu);
		cb->free(xmlPath);
		return 0;
	}
	strcpy(fmu->dirPath, dirPath);

	jm_log_verbose( cb, "FMILIB", "Parsing finished successfully");

	return fmu;
}
Beispiel #5
0
fmi2_import_t* fmi2_import_parse_xml( fmi_import_context_t* context, const char* dirPath, fmi2_xml_callbacks_t* xml_callbacks) {
	char* xmlPath;
	char absPath[FILENAME_MAX + 2];
	fmi2_import_t* fmu = 0;

	if(strlen(dirPath) + 20 > FILENAME_MAX) {
		jm_log_fatal(context->callbacks, module, "Directory path for FMU is too long");
		return 0;
	}

	xmlPath =  fmi_import_get_model_description_path(dirPath, context->callbacks);
	fmu = fmi2_import_allocate(context->callbacks);

	if(!fmu) {
		context->callbacks->free(xmlPath);
		return 0;
	}

	if(jm_get_dir_abspath(context->callbacks, dirPath, absPath, FILENAME_MAX + 2)) {
		size_t len = strlen(absPath);
		strcpy(absPath + len, FMI_FILE_SEP "resources");
		fmu->resourceLocation = fmi_import_create_URL_from_abs_path(context->callbacks, absPath);
	}
	fmu->dirPath =  context->callbacks->malloc(strlen(dirPath) + 1);
	if (!fmu->dirPath ||  !fmu->resourceLocation) {
		jm_log_fatal( context->callbacks, "FMILIB", "Could not allocated memory");
		fmi2_import_free(fmu);
		context->callbacks->free(xmlPath);
		return 0;
	}
	strcpy(fmu->dirPath, dirPath);

	jm_log_verbose( context->callbacks, "FMILIB", "Parsing model description XML");

	if(fmi2_xml_parse_model_description( fmu->md, xmlPath, xml_callbacks)) {
		fmi2_import_free(fmu);
		fmu = 0;
	}
	context->callbacks->free(xmlPath);

	if(fmu)
		jm_log_verbose( context->callbacks, "FMILIB", "Parsing finished successfully");

	return fmu;
}
/* Load FMI 2.0 Model Exchange functions */
static jm_status_enu_t fmi2_capi_load_me_fcn(fmi2_capi_t* fmu, unsigned int capabilities[])
{
	jm_status_enu_t jm_status = jm_status_success;

	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Loading functions for the model exchange interface");

	jm_status = fmi2_capi_load_common_fcn(fmu, capabilities);
		/* Getting and setting the internal FMU state */
/*   typedef fmi2Status fmi2GetFMUstateTYPE           (fmi2Component, fmi2FMUstate*);
   typedef fmi2Status fmi2SetFMUstateTYPE           (fmi2Component, fmi2FMUstate);
   typedef fmi2Status fmi2FreeFMUstateTYPE          (fmi2Component, fmi2FMUstate*);
   typedef fmi2Status fmi2SerializedFMUstateSizeTYPE(fmi2Component, fmi2FMUstate, size_t*);
   typedef fmi2Status fmi2SerializeFMUstateTYPE     (fmi2Component, fmi2FMUstate, fmi2Byte[], size_t);
   typedef fmi2Status fmi2DeSerializeFMUstateTYPE   (fmi2Component, const fmi2Byte[], size_t, fmi2FMUstate*); */
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2GetFMUstate,fmi2_me_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2SetFMUstate,fmi2_me_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2FreeFMUstate,fmi2_me_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2SerializedFMUstateSize,fmi2_me_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2SerializeFMUstate,fmi2_me_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2DeSerializeFMUstate,fmi2_me_canSerializeFMUstate);

/* Getting directional derivatives */
/*   typedef fmi2Status fmi2GetDirectionalDerivativeTYPE(fmi2Component, const fmi2ValueReference[], size_t,
                                                                   const fmi2ValueReference[], size_t,
                                                                   const fmi2Real[], fmi2Real[]); */
    LOAD_DLL_FUNCTION_WITH_FLAG(fmi2GetDirectionalDerivative,fmi2_me_providesDirectionalDerivatives);

/* Enter and exit the different modes */
/*   typedef fmi2Status fmi2EnterEventModeTYPE         (fmi2Component);
   typedef fmi2Status fmi2NewDiscreteStatesTYPE      (fmi2Component, fmi2EventInfo*);
   typedef fmi2Status fmi2EnterContinuousTimeModeTYPE(fmi2Component);
   typedef fmi2Status fmi2CompletedIntegratorStepTYPE(fmi2Component, fmi2Boolean, fmi2Boolean*, fmi2Boolean*);*/
	LOAD_DLL_FUNCTION(fmi2EnterEventMode);
	LOAD_DLL_FUNCTION(fmi2NewDiscreteStates);
	LOAD_DLL_FUNCTION(fmi2EnterContinuousTimeMode);
	LOAD_DLL_FUNCTION(fmi2CompletedIntegratorStep);

/* Providing independent variables and re-initialization of caching */
   /*typedef fmi2Status fmi2SetTimeTYPE            (fmi2Component, fmi2Real);
   typedef fmi2Status fmi2SetContinuousStatesTYPE(fmi2Component, const fmi2Real[], size_t);*/
	LOAD_DLL_FUNCTION(fmi2SetTime);
	LOAD_DLL_FUNCTION(fmi2SetContinuousStates);

/* Evaluation of the model equations */

/*
   typedef fmi2Status fmi2GetDerivativesTYPE               (fmi2Component, fmi2Real[], size_t);
   typedef fmi2Status fmi2GetEventIndicatorsTYPE           (fmi2Component, fmi2Real[], size_t);
   typedef fmi2Status fmi2GetContinuousStatesTYPE          (fmi2Component, fmi2Real[], size_t);
   typedef fmi2Status fmi2GetNominalsOfContinuousStatesTYPE(fmi2Component, fmi2Real[], size_t);*/
	LOAD_DLL_FUNCTION(fmi2GetDerivatives);
	LOAD_DLL_FUNCTION(fmi2GetEventIndicators);
	LOAD_DLL_FUNCTION(fmi2GetContinuousStates);
	LOAD_DLL_FUNCTION(fmi2GetNominalsOfContinuousStates);

	return jm_status;
}
int fmi1_xml_handle_VendorAnnotations(fmi1_xml_parser_context_t *context, const char* data) {
    if(!data) {
 		jm_log_verbose(context->callbacks, module, "Parsing XML element VendorAnnotations");
	}
    else {
        /* might give out a warning if(data[0] != 0) */
    }
    return 0;
}
fmi2_status_t fmi2_capi_setup_experiment(fmi2_capi_t* fmu,
    fmi2_boolean_t tolerance_defined, fmi2_real_t tolerance,
    fmi2_real_t start_time, fmi2_boolean_t stop_time_defined,
    fmi2_real_t stop_time)
{
    assert(fmu); assert(fmu->c);
    jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Calling fmi2SetupExperiment");
    return fmu->fmi2SetupExperiment(fmu->c, tolerance_defined, tolerance,
                                   start_time, stop_time_defined, stop_time);
}
Beispiel #9
0
fmi1_component_t fmi1_capi_instantiate_model(fmi1_capi_t* fmu, fmi1_string_t instanceName, fmi1_string_t GUID, fmi1_boolean_t loggingOn)
{
	fmi1_me_callback_functions_t cb;
	assert(fmu);
	cb.logger = fmu->callBackFunctions.logger;
    cb.allocateMemory = fmu->callBackFunctions.allocateMemory;
    cb.freeMemory = fmu->callBackFunctions.freeMemory;
	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Calling fmiInstantiateModel");
	return fmu->c = fmu->fmiInstantiateModel(instanceName, GUID, cb, loggingOn);
}
jm_status_enu_t fmi2_capi_load_dll(fmi2_capi_t* fmu)
{
	assert(fmu && fmu->dllPath);
	fmu->dllHandle = jm_portability_load_dll_handle(fmu->dllPath); /* Load the shared library */
	if (fmu->dllHandle == NULL) {
		jm_log_fatal(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Could not load the FMU binary: %s", jm_portability_get_last_dll_error());
		return jm_status_error;
	} else {
		jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Loaded FMU binary from %s", fmu->dllPath);
		return jm_status_success;
	}
}
/* Load FMI 2.0 Co-Simulation functions */
static jm_status_enu_t fmi2_capi_load_cs_fcn(fmi2_capi_t* fmu, unsigned int capabilities[])
{
	jm_status_enu_t jm_status = jm_status_success;

	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Loading functions for the co-simulation interface");

	jm_status = fmi2_capi_load_common_fcn(fmu, capabilities);

	/* Getting and setting the internal FMU state */
/*   typedef fmi2Status fmi2GetFMUstateTYPE           (fmi2Component, fmi2FMUstate*);
   typedef fmi2Status fmi2SetFMUstateTYPE           (fmi2Component, fmi2FMUstate);
   typedef fmi2Status fmi2FreeFMUstateTYPE          (fmi2Component, fmi2FMUstate*);
   typedef fmi2Status fmi2SerializedFMUstateSizeTYPE(fmi2Component, fmi2FMUstate, size_t*);
   typedef fmi2Status fmi2SerializeFMUstateTYPE     (fmi2Component, fmi2FMUstate, fmi2Byte[], size_t);
   typedef fmi2Status fmi2DeSerializeFMUstateTYPE   (fmi2Component, const fmi2Byte[], size_t, fmi2FMUstate*); */
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2GetFMUstate,fmi2_cs_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2SetFMUstate,fmi2_cs_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2FreeFMUstate,fmi2_cs_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2SerializedFMUstateSize,fmi2_cs_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2SerializeFMUstate,fmi2_cs_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmi2DeSerializeFMUstate,fmi2_cs_canSerializeFMUstate);

/* Getting directional derivatives */
/*   typedef fmi2Status fmi2GetDirectionalDerivativeTYPE(fmi2Component, const fmi2ValueReference[], size_t,
                                                                   const fmi2ValueReference[], size_t,
                                                                   const fmi2Real[], fmi2Real[]);*/
    LOAD_DLL_FUNCTION_WITH_FLAG(fmi2GetDirectionalDerivative,fmi2_cs_providesDirectionalDerivatives);

/* Simulating the slave */
/*   typedef fmi2Status fmi2SetRealInputDerivativesTYPE (fmi2Component, const fmi2ValueReference [], size_t, const fmi2Integer [], const fmi2Real []);
   typedef fmi2Status fmi2GetRealOutputDerivativesTYPE(fmi2Component, const fmi2ValueReference [], size_t, const fmi2Integer [], fmi2Real []); */
	LOAD_DLL_FUNCTION(fmi2SetRealInputDerivatives);
	LOAD_DLL_FUNCTION(fmi2GetRealOutputDerivatives);

/*   typedef fmi2Status fmi2DoStepTYPE     (fmi2Component, fmi2Real, fmi2Real, fmi2Boolean);
   typedef fmi2Status fmi2CancelStepTYPE (fmi2Component); */
	LOAD_DLL_FUNCTION(fmi2CancelStep);
	LOAD_DLL_FUNCTION(fmi2DoStep);

/* Inquire slave status */
/*   typedef fmi2Status fmi2GetStatusTYPE       (fmi2Component, const fmi2StatusKind, fmi2Status* );
   typedef fmi2Status fmi2GetRealStatusTYPE   (fmi2Component, const fmi2StatusKind, fmi2Real*   );
   typedef fmi2Status fmi2GetIntegerStatusTYPE(fmi2Component, const fmi2StatusKind, fmi2Integer*);
   typedef fmi2Status fmi2GetBooleanStatusTYPE(fmi2Component, const fmi2StatusKind, fmi2Boolean*);
   typedef fmi2Status fmi2GetStringStatusTYPE (fmi2Component, const fmi2StatusKind, fmi2String* ); */
	LOAD_DLL_FUNCTION(fmi2GetStatus);
	LOAD_DLL_FUNCTION(fmi2GetRealStatus);
	LOAD_DLL_FUNCTION(fmi2GetIntegerStatus);
	LOAD_DLL_FUNCTION(fmi2GetBooleanStatus);
	LOAD_DLL_FUNCTION(fmi2GetStringStatus);

	return jm_status;
}
int fmi1_xml_handle_UnitDefinitions(fmi1_xml_parser_context_t *context, const char* data) {
    fmi1_xml_model_description_t* md = context->modelDescription;
    if(!data) {
 		jm_log_verbose(context->callbacks, module, "Parsing XML element UnitDefinitions");
	}
    else {
        jm_vector_qsort(jm_named_ptr)(&(md->unitDefinitions),jm_compare_named);
        jm_vector_qsort(jm_named_ptr)(&(md->displayUnitDefinitions),jm_compare_named);
        /* might give out a warning if(data[0] != 0) */
    }
    return 0;
}
Beispiel #13
0
void fmi1_import_free(fmi1_import_t* fmu) {
    jm_callbacks* cb = fmu->callbacks;

	if(!fmu) return;
	jm_log_verbose( fmu->callbacks, "FMILIB", "Releasing allocated library resources");	

	fmi1_import_destroy_dllfmu(fmu);
	fmi1_xml_free_model_description(fmu->md);
	jm_vector_free_data(char)(&fmu->logMessageBuffer);

	cb->free(fmu->dirPath);
	cb->free(fmu->location);
    cb->free(fmu);
}
int fmi2_xml_handle_Derivatives(fmi2_xml_parser_context_t *context, const char* data) {
    if (!data) {
        jm_log_verbose(context->callbacks, module, "Parsing XML element Derivatives");
        /*  reset handles for the elements that are specific under Derivatives */
        fmi2_xml_set_element_handle(context, "Unknown", FMI2_XML_ELM_ID(DerivativeUnknown));
    }
    else {
        fmi2_xml_model_description_t* md = context->modelDescription;
        fmi2_xml_model_structure_t* ms = md->modelStructure;
        /* count the number of continuous states as the number of <Unknown> elements under <Derivatives> */
        md->numberOfContinuousStates = jm_vector_get_size(jm_voidp)(&ms->derivatives);
    }
    return 0;
}
void fmi2_import_destroy_dllfmu(fmi2_import_t* fmu) {
	
	if (fmu == NULL) {
		return;
	}

	
	if(fmu -> capi) {
		jm_log_verbose(fmu->callbacks, module, "Releasing FMU CAPI interface"); 

		/* Free DLL handle */
		fmi2_capi_free_dll(fmu -> capi);

		/* Destroy the C-API struct */
		fmi2_capi_destroy_dllfmu(fmu -> capi);

		fmu -> capi = NULL;
	}
}
Beispiel #16
0
/* Load FMI 1.0 Co-Simulation functions */
static jm_status_enu_t fmi1_capi_load_cs_fcn(fmi1_capi_t* fmu)
{
	jm_status_enu_t jm_status = jm_status_success;

	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Loading functions for the co-simulation interface"); 

	/* Workaround for Dymola 2012 and SimulationX 3.x */
	if (fmi1_capi_get_fcn(fmu, "fmiGetTypesPlatform",(jm_dll_function_ptr*)&fmu->fmiGetTypesPlatform) == jm_status_error) {
		jm_log_warning(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Could not load the FMI function 'fmiGetTypesPlatform'. %s. Trying to load fmiGetModelTypesPlatform instead.", jm_portability_get_last_dll_error());
		jm_status = jm_status_warning;
		if (fmi1_capi_get_fcn(fmu, "fmiGetModelTypesPlatform", (jm_dll_function_ptr*)&fmu->fmiGetTypesPlatform) == jm_status_error) {
			jm_log_error(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Could not load the FMI function 'fmiGetModelTypesPlatform'. %s", jm_portability_get_last_dll_error());
			jm_status = jm_status_error;
		}
	}

	LOAD_DLL_FUNCTION(fmiInstantiateSlave);
	LOAD_DLL_FUNCTION(fmiInitializeSlave);
	LOAD_DLL_FUNCTION(fmiTerminateSlave);
	LOAD_DLL_FUNCTION(fmiResetSlave);
	LOAD_DLL_FUNCTION(fmiFreeSlaveInstance);
	LOAD_DLL_FUNCTION(fmiSetRealInputDerivatives);
	LOAD_DLL_FUNCTION(fmiGetRealOutputDerivatives);
	LOAD_DLL_FUNCTION(fmiCancelStep);
	LOAD_DLL_FUNCTION(fmiDoStep);
	LOAD_DLL_FUNCTION(fmiGetStatus);
	LOAD_DLL_FUNCTION(fmiGetRealStatus);
	LOAD_DLL_FUNCTION(fmiGetIntegerStatus);
	LOAD_DLL_FUNCTION(fmiGetBooleanStatus);
	LOAD_DLL_FUNCTION(fmiGetStringStatus);

	LOAD_DLL_FUNCTION(fmiGetVersion);
	LOAD_DLL_FUNCTION(fmiSetDebugLogging);
	LOAD_DLL_FUNCTION(fmiSetReal);
	LOAD_DLL_FUNCTION(fmiSetInteger);
	LOAD_DLL_FUNCTION(fmiSetBoolean);
	LOAD_DLL_FUNCTION(fmiSetString);
	LOAD_DLL_FUNCTION(fmiGetReal);
	LOAD_DLL_FUNCTION(fmiGetInteger);
	LOAD_DLL_FUNCTION(fmiGetBoolean);
	LOAD_DLL_FUNCTION(fmiGetString);
	return jm_status; 
}
int fmi1_xml_handle_fmiModelDescription(fmi1_xml_parser_context_t *context, const char* data) {
    jm_name_ID_map_t namingConventionMap[] = {{"flat",fmi1_naming_enu_flat},{"structured", fmi1_naming_enu_structured},{0,0}};
    fmi1_xml_model_description_t* md = context->modelDescription;
    if(!data) {
        if(context -> currentElmID != fmi1_xml_elmID_none) {
            fmi1_xml_parse_fatal(context, "fmi1_xml_model_description must be the root XML element");
            return -1;
        }
		jm_log_verbose(context->callbacks, module, "Parsing XML element fmiModelDescription");
        /* process the attributes */
        return (
                    /* <xs:attribute name="fmiVersion" type="xs:normalizedString" use="required" fixed="1.0"/> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_fmiVersion, 1, &(md->fmi1_xml_standard_version)) ||
                    /* <xs:attribute name="modelName" type="xs:normalizedString" use="required"> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_modelName, 1, &(md->modelName)) ||
                    /* <xs:attribute name="modelIdentifier" type="xs:normalizedString" use="required"> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_modelIdentifier, 1, &(md->modelIdentifier)) ||
                    /* <xs:attribute name="guid" type="xs:normalizedString" use="required"> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_guid, 1, &(md->GUID)) ||
                    /* <xs:attribute name="description" type="xs:string"/> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_description, 0, &(md->description)) ||
                    /* <xs:attribute name="author" type="xs:string"/> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_author, 0, &(md->author)) ||
                    /* <xs:attribute name="version" type="xs:normalizedString"> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_version, 0, &(md->version)) ||
                    /* <xs:attribute name="generationTool" type="xs:normalizedString"/> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_generationTool, 0, &(md->generationTool)) ||
                    /* <xs:attribute name="generationDateAndTime" type="xs:dateTime"/> */
                    fmi1_xml_set_attr_string(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_generationDateAndTime, 0, &(md->generationDateAndTime)) ||
                    /* <xs:attribute name="variableNamingConvention" use="optional" default="flat"> */
                    fmi1_xml_set_attr_enum(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_variableNamingConvention, 0, (unsigned*)&(md->namingConvension), fmi1_naming_enu_flat, namingConventionMap) ||
                    /* <xs:attribute name="numberOfContinuousStates" type="xs:unsignedInt" use="required"/> */
                    fmi1_xml_set_attr_uint(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_numberOfContinuousStates, 1, &(md->numberOfContinuousStates),0) ||
                    /* <xs:attribute name="numberOfEventIndicators" type="xs:unsignedInt" use="required"/> */
                    fmi1_xml_set_attr_uint(context, fmi1_xml_elmID_fmiModelDescription, fmi_attr_id_numberOfEventIndicators, 1, &(md->numberOfEventIndicators),0)
                    );
    }
    else {
        /* don't do anything. might give out a warning if(data[0] != 0) */
        return 0;
    }
}
fmi_version_enu_t fmi_import_get_fmi_version( fmi_import_context_t* c, const char* fileName, const char* dirName) {
	fmi_version_enu_t ret = fmi_version_unknown_enu;
	jm_status_enu_t status;
	char* mdpath;
	jm_log_verbose(c->callbacks, MODULE, "Detecting FMI standard version");
	if(!fileName || !*fileName) {
		jm_log_fatal(c->callbacks, MODULE, "No FMU filename specified");
		return fmi_version_unknown_enu;
	}
	if(!dirName || !*dirName) {
		jm_log_fatal(c->callbacks, MODULE, "No temporary directory name specified");
		return fmi_version_unknown_enu;
	}
	status = fmi_zip_unzip(fileName, dirName, c->callbacks);
	if(status == jm_status_error) return fmi_version_unknown_enu;
	mdpath = fmi_import_get_model_description_path(dirName, c->callbacks);
	ret = fmi_xml_get_fmi_version(c, mdpath);
	jm_log_info(c->callbacks, MODULE, "XML specifies FMI standard version %s", fmi_version_to_string(ret));
	c->callbacks->free(mdpath);
	return ret;
}
jm_status_enu_t fmi2_capi_free_dll(fmi2_capi_t* fmu)
{
	if (fmu == NULL) {
		return jm_status_error; /* Return without writing any log message */
	}

	if (fmu->dllHandle) {
		jm_status_enu_t status =
			(fmu->debugMode != 0) ?
                /* When running valgrind this may be convenient to track mem leaks */
                jm_status_success:
                jm_portability_free_dll_handle(fmu->dllHandle);
		fmu->dllHandle = 0;
		if (status == jm_status_error) { /* Free the library handle */
			jm_log(fmu->callbacks, FMI_CAPI_MODULE_NAME, jm_log_level_error, "Could not free the FMU binary: %s", jm_portability_get_last_dll_error());
			return jm_status_error;
		} else {
			jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Successfully unloaded FMU binary");
			return jm_status_success;
		}
	}
	return jm_status_success;
}
int fmi2_xml_handle_ModelStructure(fmi2_xml_parser_context_t *context, const char* data) {
    fmi2_xml_model_description_t* md = context->modelDescription;
    if(!data) {
		jm_log_verbose(context->callbacks, module,"Parsing XML element ModelStructure");
		/** allocate model structure */
		md->modelStructure = fmi2_xml_allocate_model_structure(md->callbacks);
		if(!md->modelStructure) {
				fmi2_xml_parse_fatal(context, module, "Could not allocate memory");
				return -1;
		}
    }
    else {
		/** make sure model structure information is consistent */

		if(!fmi2_xml_check_model_structure(md)) {
			fmi2_xml_parse_fatal(context, "Model structure is not valid due to detected errors. Cannot continue.");
			return -1;
		}
/*		md->numberOfContinuousStates = jm_vector_get_size(jm_voidp)(&md->modelStructure->states); */

    }
    return 0;
}
fmi_import_context_t* fmi_import_allocate_context( jm_callbacks* callbacks) {
	jm_log_verbose(callbacks, MODULE, "Allocating FMIL context");
	return fmi_xml_allocate_context(callbacks);
}
Beispiel #22
0
const char* fmi1_capi_get_model_types_platform(fmi1_capi_t* fmu)
{
	assert(fmu);
	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Calling fmiGetModelTypesPlatform");
	return fmu->fmiGetModelTypesPlatform();
}
Beispiel #23
0
fmi1_status_t fmi1_capi_initialize(fmi1_capi_t* fmu, fmi1_boolean_t toleranceControlled, fmi1_real_t relativeTolerance, fmi1_event_info_t* eventInfo)
{
	assert(fmu);
	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Calling fmiInitialize");
	return fmu->fmiInitialize(fmu->c, toleranceControlled, relativeTolerance, eventInfo);	
}
Beispiel #24
0
void fmi1_capi_free_model_instance(fmi1_capi_t* fmu)
{
	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Calling fmiFreeModelInstance");
	fmu->fmiFreeModelInstance(fmu->c);
}
Beispiel #25
0
/* Load FMI 2.0 Co-Simulation functions */
static jm_status_enu_t fmi2_capi_load_cs_fcn(fmi2_capi_t* fmu, unsigned int capabilities[])
{
	jm_status_enu_t jm_status = jm_status_success;

	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Loading functions for the co-simulation interface"); 

	jm_status = fmi2_capi_load_common_fcn(fmu, capabilities);

	/* Getting and setting the internal FMU state */
/*   typedef fmiStatus fmiGetFMUstateTYPE           (fmiComponent, fmiFMUstate*);
   typedef fmiStatus fmiSetFMUstateTYPE           (fmiComponent, fmiFMUstate);
   typedef fmiStatus fmiFreeFMUstateTYPE          (fmiComponent, fmiFMUstate*);
   typedef fmiStatus fmiSerializedFMUstateSizeTYPE(fmiComponent, fmiFMUstate, size_t*);
   typedef fmiStatus fmiSerializeFMUstateTYPE     (fmiComponent, fmiFMUstate, fmiByte[], size_t);
   typedef fmiStatus fmiDeSerializeFMUstateTYPE   (fmiComponent, const fmiByte[], size_t, fmiFMUstate*); */
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiGetFMUstate,fmi2_cs_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiSetFMUstate,fmi2_cs_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiFreeFMUstate,fmi2_cs_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiSerializedFMUstateSize,fmi2_cs_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiSerializeFMUstate,fmi2_cs_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiDeSerializeFMUstate,fmi2_cs_canSerializeFMUstate);

/* Getting partial derivatives */
/*   typedef fmiStatus fmiGetPartialDerivativesTYPE   (fmiComponent, setMatrixElement, void*, void*, void*, void*);
   typedef fmiStatus fmiGetDirectionalDerivativeTYPE(fmiComponent, const fmiValueReference[], size_t,
                                                                   const fmiValueReference[], size_t,
                                                                   const fmiReal[], fmiReal[]); */
    /*???  LOAD_DLL_FUNCTION_WITH_FLAG(fmiGetDirectionalDerivative,fmi2_cs_providesDirectionalDerivatives); */

/* Creation and destruction of slave instances */
/*   typedef fmiComponent fmiInstantiateSlaveTYPE (fmiString, fmiString, fmiString, const fmiCallbackFunctions*, fmiBoolean, fmiBoolean);
   typedef void         fmiFreeSlaveInstanceTYPE(fmiComponent); */
    LOAD_DLL_FUNCTION(fmiInstantiateSlave);
	LOAD_DLL_FUNCTION(fmiFreeSlaveInstance);

/* Simulating the slave */
/*   typedef fmiStatus fmiInitializeSlaveTYPE(fmiComponent, fmiReal, fmiReal, fmiBoolean, fmiReal);
   typedef fmiStatus fmiTerminateSlaveTYPE (fmiComponent);
   typedef fmiStatus fmiResetSlaveTYPE     (fmiComponent); */
	LOAD_DLL_FUNCTION(fmiInitializeSlave);
	LOAD_DLL_FUNCTION(fmiTerminateSlave);
	LOAD_DLL_FUNCTION(fmiResetSlave);

/*   typedef fmiStatus fmiSetRealInputDerivativesTYPE (fmiComponent, const fmiValueReference [], size_t, const fmiInteger [], const fmiReal []);
   typedef fmiStatus fmiGetRealOutputDerivativesTYPE(fmiComponent, const fmiValueReference [], size_t, const fmiInteger [], fmiReal []); */
	LOAD_DLL_FUNCTION(fmiSetRealInputDerivatives);
	LOAD_DLL_FUNCTION(fmiGetRealOutputDerivatives);

/*   typedef fmiStatus fmiDoStepTYPE     (fmiComponent, fmiReal, fmiReal, fmiBoolean);
   typedef fmiStatus fmiCancelStepTYPE (fmiComponent); */
	LOAD_DLL_FUNCTION(fmiCancelStep);
	LOAD_DLL_FUNCTION(fmiDoStep);

/* Inquire slave status */
/*   typedef fmiStatus fmiGetStatusTYPE       (fmiComponent, const fmiStatusKind, fmiStatus* );
   typedef fmiStatus fmiGetRealStatusTYPE   (fmiComponent, const fmiStatusKind, fmiReal*   );
   typedef fmiStatus fmiGetIntegerStatusTYPE(fmiComponent, const fmiStatusKind, fmiInteger*);
   typedef fmiStatus fmiGetBooleanStatusTYPE(fmiComponent, const fmiStatusKind, fmiBoolean*);
   typedef fmiStatus fmiGetStringStatusTYPE (fmiComponent, const fmiStatusKind, fmiString* ); */
	LOAD_DLL_FUNCTION(fmiGetStatus);
	LOAD_DLL_FUNCTION(fmiGetRealStatus);
	LOAD_DLL_FUNCTION(fmiGetIntegerStatus);
	LOAD_DLL_FUNCTION(fmiGetBooleanStatus);
	LOAD_DLL_FUNCTION(fmiGetStringStatus);

	return jm_status; 
}
Beispiel #26
0
jm_status_enu_t fmi1_cs_simulate(fmu_check_data_t* cdata)
{	
	fmi1_status_t fmistatus;
	jm_status_enu_t jmstatus = jm_status_success;
	jm_callbacks* cb = &cdata->callbacks;

	fmi1_import_t* fmu = cdata->fmu1;
	fmi1_string_t fmuGUID = fmi1_import_get_GUID(fmu);
	fmi1_string_t mimeType;
	fmi1_real_t timeout = 0.0;
	fmi1_boolean_t visible = fmi1_false;
	fmi1_boolean_t interactive = fmi1_false;

	fmi1_real_t tstart = fmi1_import_get_default_experiment_start(fmu);
	fmi1_real_t tcur = tstart;
	fmi1_real_t hstep;
	fmi1_real_t tend = fmi1_import_get_default_experiment_stop(fmu);
	fmi1_boolean_t StopTimeDefined = fmi1_true;

	mimeType = fmi1_import_get_mime_type(fmu);
	if(	(cdata->fmu1_kind == fmi1_fmu_kind_enu_cs_standalone) 
		|| !mimeType || !mimeType[0])
	{
		mimeType = "application/x-fmu-sharedlibrary";
	}
	else {
		if(	strcmp(mimeType, "application/x-fmu-sharedlibrary") != 0 )
		{
			jm_log_info(cb, fmu_checker_module,"The FMU requests simulator with MIME type '%s'.", mimeType);
			printf("\nPlease, start a simulator program for MIME type '%s'\nPress enter to continue.\n", mimeType);
			getchar();
		}
	}
	if(cdata->stopTime > 0) {
		tend = cdata->stopTime;
	}
	if(cdata->stepSize > 0) {
		hstep = cdata->stepSize;
	}
	else {
		hstep = (tend - tstart) / cdata->numSteps;
	}

	cdata->instanceName = "Test FMI 1.0 CS";
	jm_log_verbose(cb, fmu_checker_module, "Checker will instantiate the slave with \n"
		"\tFMU location ='%s'\n\tMIME type = '%s'", cdata->fmuLocation, mimeType);
	jmstatus = fmi1_import_instantiate_slave(fmu, cdata->instanceName, cdata->fmuLocation, mimeType, timeout, visible, interactive);
	if (jmstatus == jm_status_error) {
		jm_log_fatal(cb, fmu_checker_module, "Could not instantiate the model");
		return jm_status_error;
	}

	fmistatus = fmi1_import_initialize_slave(fmu, tstart, StopTimeDefined, tend);
	if((fmistatus == fmi1_status_ok) || (fmistatus == fmi1_status_warning)) {
		jm_log_info(cb, fmu_checker_module, "Initialized FMU for simulation starting at time %g", tstart);
		fmistatus = fmi1_status_ok;
	}
	else {
			jm_log_fatal(cb, fmu_checker_module, "Failed to initialize FMU for simulation (FMU status: %s)", fmi1_status_to_string(fmistatus));
			jmstatus = jm_status_error;
	}

	if(jmstatus != jm_status_error) {
		jm_log_verbose(cb, fmu_checker_module, "Writing simulation output for start time");
		if(fmi1_write_csv_data(cdata, tstart) != jm_status_success){
			jmstatus = jm_status_error;
		}
	}
	while ((tcur < tend) && (jmstatus != jm_status_error)) {
		fmi1_boolean_t newStep = fmi1_true;
		fmi1_real_t tnext = tcur + hstep;
		if(tnext > tend - 1e-3*hstep) { /* last step should be on tend */
			hstep = tend - tcur;
			tnext = tend;
		}

		jm_log_verbose(cb, fmu_checker_module, "Simulation step from time: %g until: %g", tcur, tnext);

		fmistatus = fmi1_import_do_step(fmu, tcur, hstep, newStep);

		tcur = tnext;

		if(fmi1_write_csv_data(cdata, tcur) != jm_status_success){
			jmstatus = jm_status_error;
		}

		if((fmistatus == fmi1_status_ok) || (fmistatus == fmi1_status_warning)) {
			fmistatus = fmi1_status_ok;
		}
		else 
			jmstatus = jm_status_error;
	}

	if((fmistatus != fmi1_status_ok) && (fmistatus != fmi1_status_warning)) {
		jm_log_fatal(cb, fmu_checker_module, "Simulation loop terminated  at time %g since FMU returned status: %s", tcur, fmi1_status_to_string(fmistatus));
		jmstatus = jm_status_error;
	}
	else if(jmstatus != jm_status_error) {
 		 jm_log_info(cb, fmu_checker_module, "Simulation finished successfully at time %g", tcur);
	}

	fmistatus = fmi1_import_terminate_slave(fmu);

	if(  fmistatus != fmi1_status_ok) {
		 jm_log_error(cb, fmu_checker_module, "fmiTerminateSlave returned status: %s", fmi1_status_to_string(fmistatus));
	}

	fmi1_import_free_slave_instance(fmu);

	return jmstatus;
}
fmi2_status_t fmi2_capi_exit_initialization_mode(fmi2_capi_t* fmu)
{
    assert(fmu); assert(fmu->c);
    jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Calling fmi2ExitInitializationMode");
    return fmu->fmi2ExitInitializationMode(fmu->c);
}
Beispiel #28
0
/* Load FMI 1.0 Model Exchange functions */
static jm_status_enu_t fmi2_capi_load_me_fcn(fmi2_capi_t* fmu, unsigned int capabilities[])
{
	jm_status_enu_t jm_status = jm_status_success;

	jm_log_verbose(fmu->callbacks, FMI_CAPI_MODULE_NAME, "Loading functions for the model exchange interface"); 

	jm_status = fmi2_capi_load_common_fcn(fmu, capabilities);
		/* Getting and setting the internal FMU state */
/*   typedef fmiStatus fmiGetFMUstateTYPE           (fmiComponent, fmiFMUstate*);
   typedef fmiStatus fmiSetFMUstateTYPE           (fmiComponent, fmiFMUstate);
   typedef fmiStatus fmiFreeFMUstateTYPE          (fmiComponent, fmiFMUstate*);
   typedef fmiStatus fmiSerializedFMUstateSizeTYPE(fmiComponent, fmiFMUstate, size_t*);
   typedef fmiStatus fmiSerializeFMUstateTYPE     (fmiComponent, fmiFMUstate, fmiByte[], size_t);
   typedef fmiStatus fmiDeSerializeFMUstateTYPE   (fmiComponent, const fmiByte[], size_t, fmiFMUstate*); */
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiGetFMUstate,fmi2_me_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiSetFMUstate,fmi2_me_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiFreeFMUstate,fmi2_me_canGetAndSetFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiSerializedFMUstateSize,fmi2_me_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiSerializeFMUstate,fmi2_me_canSerializeFMUstate);
   LOAD_DLL_FUNCTION_WITH_FLAG(fmiDeSerializeFMUstate,fmi2_me_canSerializeFMUstate);

/* Getting partial derivatives */
/*   typedef fmiStatus fmiGetPartialDerivativesTYPE   (fmiComponent, setMatrixElement, void*, void*, void*, void*);
   typedef fmiStatus fmiGetDirectionalDerivativeTYPE(fmiComponent, const fmiValueReference[], size_t,
                                                                   const fmiValueReference[], size_t,
                                                                   const fmiReal[], fmiReal[]); */
    LOAD_DLL_FUNCTION_WITH_FLAG(fmiGetDirectionalDerivative,fmi2_me_providesDirectionalDerivatives); 

	/* Creation and destruction of model instances and setting debug status */
   /*typedef fmiComponent fmiInstantiateModelTYPE (fmiString, fmiString, fmiString, const fmiCallbackFunctions*, fmiBoolean, fmiBoolean);
    typedef void         fmiFreeModelInstanceTYPE(fmiComponent);*/
	LOAD_DLL_FUNCTION(fmiInstantiateModel);
	LOAD_DLL_FUNCTION(fmiFreeModelInstance);

/* Providing independent variables and re-initialization of caching */
   /*typedef fmiStatus fmiSetTimeTYPE                (fmiComponent, fmiReal);
   typedef fmiStatus fmiSetContinuousStatesTYPE    (fmiComponent, const fmiReal[], size_t);
   typedef fmiStatus fmiCompletedIntegratorStepTYPE(fmiComponent, fmiBoolean*); */
	LOAD_DLL_FUNCTION(fmiSetTime);
	LOAD_DLL_FUNCTION(fmiSetContinuousStates);
	LOAD_DLL_FUNCTION(fmiCompletedIntegratorStep);

/* Evaluation of the model equations */
/*   typedef fmiStatus fmiInitializeModelTYPE        (fmiComponent, fmiBoolean, fmiReal, fmiEventInfo*);
   typedef fmiStatus fmiEventUpdateTYPE            (fmiComponent, fmiBoolean, fmiEventInfo*);
   typedef fmiStatus fmiCompletedEventIterationTYPE(fmiComponent);
   typedef fmiStatus fmiTerminateTYPE              (fmiComponent); */
	LOAD_DLL_FUNCTION(fmiInitializeModel);
	LOAD_DLL_FUNCTION(fmiEventUpdate);
	LOAD_DLL_FUNCTION_WITH_FLAG(fmiCompletedEventIteration, fmi2_me_completedEventIterationIsProvided);
	LOAD_DLL_FUNCTION(fmiTerminate);

/*
   typedef fmiStatus fmiGetDerivativesTYPE            (fmiComponent, fmiReal[], size_t);
   typedef fmiStatus fmiGetEventIndicatorsTYPE        (fmiComponent, fmiReal[], size_t);
   typedef fmiStatus fmiGetContinuousStatesTYPE       (fmiComponent, fmiReal[], size_t);
   typedef fmiStatus fmiGetNominalContinuousStatesTYPE(fmiComponent, fmiReal[], size_t);
   typedef fmiStatus fmiGetStateValueReferencesTYPE   (fmiComponent, fmiValueReference[], size_t); */
	LOAD_DLL_FUNCTION(fmiGetDerivatives);
	LOAD_DLL_FUNCTION(fmiGetEventIndicators);
	LOAD_DLL_FUNCTION(fmiGetContinuousStates);
	LOAD_DLL_FUNCTION(fmiGetNominalContinuousStates);
	LOAD_DLL_FUNCTION(fmiGetStateValueReferences);

   
	return jm_status; 
}
/* Load and destroy functions */
jm_status_enu_t fmi2_import_create_dllfmu(fmi2_import_t* fmu, fmi2_fmu_kind_enu_t fmuKind, const fmi2_callback_functions_t* callBackFunctions) {

	char curDir[FILENAME_MAX + 2];
	char* dllDirPath = 0;
	char* dllFileName = 0;
	const char* modelIdentifier;
	fmi2_callback_functions_t defaultCallbacks;

	if (fmu == NULL) {
		assert(0);
		return jm_status_error;
	}

	if(fmu -> capi) {
		if(fmi2_capi_get_fmu_kind(fmu -> capi) == fmuKind) {
			jm_log_warning(fmu->callbacks, module, "FMU binary is already loaded"); 
			return jm_status_success;
		}
		else
			fmi2_import_destroy_dllfmu(fmu);		
	}

	if(fmuKind == fmi2_fmu_kind_me)
		modelIdentifier = fmi2_import_get_model_identifier_ME(fmu);
	else 	if(fmuKind == fmi2_fmu_kind_cs)
		modelIdentifier = fmi2_import_get_model_identifier_CS(fmu);
	else {
		assert(0);
		return jm_status_error;
	}

	if (modelIdentifier == NULL) {
		jm_log_error(fmu->callbacks, module, "No model identifier given");
		return jm_status_error;
	}

	if( jm_portability_get_current_working_directory(curDir, FILENAME_MAX+1) != jm_status_success) {
		jm_log_warning(fmu->callbacks, module, "Could not get current working directory (%s)", strerror(errno));
		curDir[0] = 0;
	};

	dllDirPath = fmi_construct_dll_dir_name(fmu->callbacks, fmu->dirPath);
	dllFileName = fmi_construct_dll_file_name(fmu->callbacks, dllDirPath, modelIdentifier);

	if (!dllDirPath ||!dllFileName) {
		fmu->callbacks->free(dllDirPath);
		return jm_status_error;
	}

	if(!callBackFunctions) {
		jm_callbacks* cb = fmu->callbacks;
		defaultCallbacks.allocateMemory = cb->calloc;
		defaultCallbacks.freeMemory = cb->free;
		defaultCallbacks.componentEnvironment = fmu;
		defaultCallbacks.logger = fmi2_log_forwarding;
		defaultCallbacks.stepFinished = 0;
		callBackFunctions = &defaultCallbacks;
	}

	if(jm_portability_set_current_working_directory(dllDirPath) != jm_status_success) {
		jm_log_fatal(fmu->callbacks, module, "Could not change to the DLL directory %s", dllDirPath);
		if(ENOENT == errno)
			jm_log_fatal(fmu->callbacks, module, "No binary for this platform?");
		else
			jm_log_fatal(fmu->callbacks, module, "System error: %s", strerror(errno));
	}
	else {
		/* Allocate memory for the C-API struct */
		fmu -> capi = fmi2_capi_create_dllfmu(fmu->callbacks, dllFileName, modelIdentifier, callBackFunctions, fmuKind);
	}


	/* Load the DLL handle */
	if (fmu -> capi) {
		jm_log_info(fmu->callbacks, module, 
			"Loading '" FMI_PLATFORM "' binary with '%s' platform types", fmi2_get_types_platform() );

		if(fmi2_capi_load_dll(fmu -> capi) == jm_status_error) {		
			fmi2_capi_destroy_dllfmu(fmu -> capi);
			fmu -> capi = NULL;
		}
	}

	if(curDir[0] && (jm_portability_set_current_working_directory(curDir) != jm_status_success)) {
		jm_log_error(fmu->callbacks, module, "Could not restore current working directory (%s)", strerror(errno));
	}

	fmu->callbacks->free((jm_voidp)dllDirPath);
	fmu->callbacks->free((jm_voidp)dllFileName);

	if (fmu -> capi == NULL) {
		return jm_status_error;
	}


	/* Load the DLL functions */
	if (fmi2_capi_load_fcn(fmu -> capi, fmi2_xml_get_capabilities(fmu->md)) == jm_status_error) {
		fmi2_capi_free_dll(fmu -> capi);			
		fmi2_capi_destroy_dllfmu(fmu -> capi);
		fmu -> capi = NULL;
		return jm_status_error;
	}
	jm_log_verbose(fmu->callbacks, module, "Successfully loaded all the interface functions"); 

	return jm_status_success;
}