question

Mischa Spelt avatar image
4 Likes"
Mischa Spelt asked anthony.johnson commented

Returning string from C++ user command

I'm importing an old (7.x) DLL to 17.0 and running into some problems with user commands returning a string. We used to write functions like

visible double DLL_GetDateTimeString( FLEXSIMINTERFACE )
{
  stringreturn( "Hello world!" );
  return 0;
}

but that does not seem to work anymore. The documentation states that as of FlexSim 2016 one can "simply" return a string from the user command, but I tried a couple of options such as

visible std::string DLL_GetDateTimeString( FLEXSIMINTERFACE )
{
  return std::string("Hello world!");
}

and

visible char* DLL_GetDateTimeString( FLEXSIMINTERFACE )
{
  std::string result = "Hello world!";
  return apchar( result );
}

or

visible const char* DLL_GetDateTimeString( FLEXSIMINTERFACE )
{
  std::string result = "Hello world!";
  return result.c_str();
}

but they break the stack or give me nonsense output, respectively.

Could you provide an example of how to return strings from a DLL function in version 2017?

FlexSim 17.0.0
user commandc++stringdll functions
5 |100000

Up to 12 attachments (including images) can be used with a maximum of 23.8 MiB each and 47.7 MiB total.

1 Answer

Phil BoBo avatar image
4 Likes"
Phil BoBo answered anthony.johnson commented

Change your function definition to return a Variant:

__declspec(dllexport) Variant DLL_GetDateTimeString(FLEXSIMINTERFACE)
{
  return std::string("Hello world!");
}


return-string.jpg (159.4 KiB)
· 2
5 |100000

Up to 12 attachments (including images) can be used with a maximum of 23.8 MiB each and 47.7 MiB total.

Mischa Spelt avatar image Mischa Spelt commented ·

Thanks @phil.bobo, tried that but then I get an exception as soon as I try to use the parameters. Turns out that the definition of the visible macro in basicmacros.h that we were using is still defined as

#define visible extern "C" __declspec(dllexport)

which is appropriate for functions returning double, but when returning Variant the function needs to have C++ linkage.

Replacing "visible" with "__declspec(dllexport)" as per your example solved the problem.

2 Likes 2 ·
anthony.johnson avatar image anthony.johnson ♦♦ Mischa Spelt commented ·

Mischa, you are correct and this is by design. Dll functions that use the old method of returning a double should always be declared as visible double MyFunc(FLEXSIMINTERFACE) whereas functions that use the new method of returning a Variant should use __declspec(dllexport) Variant MyFunc(FLEXSIMINTERFACE). FlexSim detects whether the function is exported as a name-mangled c++ function (__declspec(dllexport)) or as a simple c function (visible). If it is the former, FlexSim assumes the function returns a Variant. If it is the latter, FlexSim assumes the function returns a double.

3 Likes 3 ·