Calling a C++ DLL from a C# program. Unexpected behaviour

G

Guest

Hi there!

I’m having a strange problem with a c++ dll that is called from a c#
program. The dll wraps a large piece of c++ software that uses exceptions for
its error-signalling. To keep the exception mechanism away from the c# end,
all functions in the dll are embedded in catch-all blocks that return ‘false’
if anything throws an exception. Using a c++ program as the caller, the dll
can be shown to work and return false on an exception.

Now, the fun part: If I use c# to access the function, it returns ‘true’
every time an exception occurs. If I step into the dll, using the mixed-mode
debugger, the results are pretty interesting. Upon stepping over the line
that will case an exception to be thrown, the debugger jumps back to the c#
code, as if the function returned. It does not enter the exception handler,
like it did with c++ code calling the function.

I get this behaviour with all similar code.

FWIW, the DllImport lines look like this: [DllImport("somedll.dll",
CharSet=CharSet.Ansi)]

I would really appreciate some help, as this is a major showstopper for us.

Thanks in advance,

Ulf
 
R

Richard Grimes [MVP]

Ascaron said:
Now, the fun part: If I use c# to access the function, it returns
'true' every time an exception occurs. If I step into the dll, using
the mixed-mode debugger, the results are pretty interesting. Upon
stepping over the line that will case an exception to be thrown, the
debugger jumps back to the c# code, as if the function returned. It
does not enter the exception handler, like it did with c++ code
calling the function.

Can you give the complete prototype of one of the methods you are
calling?

I suspect that this is a marshalling problem. If I do this:

// C++
extern "C" __declspec(dllexport) bool Test()
{
try
{
throw 1;
}
catch(...)
{ return false;}
return true;
}
// C#
class Tester
{
[DllImport("lib")]
public static extern bool Test();
}

I find that Tester.Test() returns true, whereas, as you say, it should
return false. If I change the C++ to:

extern "C" __declspec(dllexport) BOOL Test()
{
try
{
throw 1;
}
catch(...)
{ return FALSE;}
return TRUE;
}

then Tester.Test() returns false, as it should.

I don't know what is happening here, because if I remove the try/catch
block from Test version with bool (and return false), then it works as
expected.

Richard
 
G

Guest

Hello Richard

Thanks for your reply, this solved the problem perfectly. Still it left us
wondering why ;)

Cheers

Ulf


Richard Grimes said:
Ascaron said:
Now, the fun part: If I use c# to access the function, it returns
'true' every time an exception occurs. If I step into the dll, using
the mixed-mode debugger, the results are pretty interesting. Upon
stepping over the line that will case an exception to be thrown, the
debugger jumps back to the c# code, as if the function returned. It
does not enter the exception handler, like it did with c++ code
calling the function.

Can you give the complete prototype of one of the methods you are
calling?

I suspect that this is a marshalling problem. If I do this:

// C++
extern "C" __declspec(dllexport) bool Test()
{
try
{
throw 1;
}
catch(...)
{ return false;}
return true;
}
// C#
class Tester
{
[DllImport("lib")]
public static extern bool Test();
}

I find that Tester.Test() returns true, whereas, as you say, it should
return false. If I change the C++ to:

extern "C" __declspec(dllexport) BOOL Test()
{
try
{
throw 1;
}
catch(...)
{ return FALSE;}
return TRUE;
}

then Tester.Test() returns false, as it should.

I don't know what is happening here, because if I remove the try/catch
block from Test version with bool (and return false), then it works as
expected.

Richard
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top