I've got a BIG problem when trying to call a dll, from a test console app!! I've written a simple dll that delegates calls to a 3rd party library, but is necessary because it will eventually be used in a C# app, & some 3rd party functions are actually in import libraries (inc. a DllMain, so i can't create my own), some are mapped via standard libs to dlls @ runtime.
(I've copied quite a bit of code below that should help to show what's going on)
When i call a function in the dll called SendMessageA i get a nasty error saying:
"Run-time check failure #0 - The value of ESP was not properly saved across a function call. This is usually a result of calling a function declared with one calling convention with a function pointer declared with a different calling convention"
But when i call another function called GetEnvironment everything's fine!!
CLIENT APP:
DLL STUFF:
The 3rd party stuff is always pretty painfull to work with & i'm not sure if they're doing something in their DllMain that's screwing around with memory or something!? Their functions perform communication & other things with an executable program, which is running from a mapped network drive.
I've tried changing the calling conventions of the dll function SendMessageA (inc. typedef) to __cdecl, but that didn't work.
Should i be using pointers to pointers?? I don't really know when & when not to use them!!
If anyone has ANY ideas then i'd really appreciate the help as i'm pretty stuck!!
(I've copied quite a bit of code below that should help to show what's going on)
When i call a function in the dll called SendMessageA i get a nasty error saying:
"Run-time check failure #0 - The value of ESP was not properly saved across a function call. This is usually a result of calling a function declared with one calling convention with a function pointer declared with a different calling convention"
But when i call another function called GetEnvironment everything's fine!!
CLIENT APP:
Code:
int _tmain(int argc, _TCHAR* argv[])
{
TCHAR szMsg[255];
long lRes = 0;
long lStatus = 0;
long lProcErr = 0;
OutputSystemRegisters();
cout << "Loading Uniface runtime API library..." << endl;
hModule = ::LoadLibrary("urtapi7.dll");
OutputSystemRegisters();
cout << "Enter message to send to Uniface:";
cin >> szMsg;
cout << "Sending message " << "\"" << szMsg << "\" to Uniface via the asynchronous interrupt trigger..." << endl;
UnifaceRuntimeApi::SendMessageA sendMessage = (UnifaceRuntimeApi::SendMessageA) ::GetProcAddress(hModule, "SendMessageA");
OutputSystemRegisters();
// * * * B A N G * * *
lRes = sendMessage(szMsg);
cout << "Message sent with status " << lRes << endl;
// just while testing...
TidyUp(); // (free uniface handles & free library)
return 0;
system("PAUSE");
cout << "Getting Uniface environment handle..." << endl;
GetEnvironment getEnv = (GetEnvironment) ::GetProcAddress(hModule, "GetEnvironment");
// get uniface environment...
// * * * T H I S W O R K S * * *
lRes = getEnv(&hUniEnv);
// etc...
DLL STUFF:
Code:
// ** used by client app **
typedef long (__stdcall *SendMessageA) (LPSTR sMessage);
typedef long (__stdcall *GetEnvironment) (int* phUniEnv);
// ** some dll code **
long __stdcall SendMessageA(LPSTR sMessage)
{
return uputames((unsigned char*) sMessage, (short) strlen(sMessage));
}
long __stdcall GetEnvironment(int* phUniEnv)
{
return ueopen((UHACT*) phUniEnv);
}
// ** 3rd party stuff **
extern long ueopen(UHACT *);
short __cdecl uputames(USTRING *pMsg, short sLen);
The 3rd party stuff is always pretty painfull to work with & i'm not sure if they're doing something in their DllMain that's screwing around with memory or something!? Their functions perform communication & other things with an executable program, which is running from a mapped network drive.
I've tried changing the calling conventions of the dll function SendMessageA (inc. typedef) to __cdecl, but that didn't work.
Should i be using pointers to pointers?? I don't really know when & when not to use them!!
If anyone has ANY ideas then i'd really appreciate the help as i'm pretty stuck!!