Go Premium for a chance to win a PS4. Enter to Win

x
  • Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 1372
  • Last Modified:

How to force CLR not to handle Exceptions from unmanaged code ?

Hi experts...
I have managed code in C# calling unmanaged code from a DLL written in C++.
Every time an Exception is thrown by unmanaged code, this exception is handled by C# directly.
How to force to handle the exception by the DLL itself, instead of C# ?

example attached below.
   
//C# code
[DllImport("some.dll")]
    public static extern int A();
static int Main()
{
    try {
        A();
    } catch {
        // handle exception by managed code
    }
}
 
// C++ code
extern "C" __declspec(dllexport) int A();
int B(void);
 
int A()
{
    try {
        B();
    } catch (...) {
        // handle exception by unamanged code
        // how to handle the exeption here ???
    }
}
 
int B()
{
    // throw some exception
    throw;
}

Open in new window

0
darkriser
Asked:
darkriser
  • 5
  • 3
1 Solution
 
Jens FiedererCommented:
Are you able to rewrite the DLL?

If so, make sure you catch the error.

If not, you could avoid calling the DLL from C#, but only from ANOTHER unmanaged DLL that calls it, catching all errors.

Obviously, you aren't going to change the DLL itself without changing the DLL.
0
 
darkriserAuthor Commented:
Yes, of course I can rewrite the DLL. But how to achieve my requirements?

The problem is, that as soon as the C# code detects some exception inside my unmanaged DLL, it immediately skips the catch block inside the DLL and starts the C# catch block. Therefore I'm unable to handle exceptions inside my unmanaged DLL.
0
 
Jens FiedererCommented:
Maybe you should be throwing SOMETHING instead of a naked throw?

When I use your code as written, I crash with "application has asked the runtime to terminate it in an unusual way" .

But when I throw (for example) an int,  I get a usable function.

See snippet.
C++
 
extern "C" __declspec(dllexport) int A();
int B(int);
 
int A(int parm)
{
    try {
		if (parm == 1) 
		{
			return B(parm);
		}
    } catch (int exc) {
        return exc;
	} catch (...) {
		return 100;
	}
 
	return parm*2;
}
 
int B(int parm)
{
    // throw some exception
    throw parm*3;
}
 
# C# test program
namespace usemanaged
{
    
    class Program
    {
        [DllImport("unmanageddll.dll", EntryPoint = "A",
        ExactSpelling = false, CallingConvention = CallingConvention.Cdecl)]
        static extern int A(int parm);
 
        static void Main(string[] args)
        {
            while (true)
            {
                int parm = int.Parse(Console.ReadLine());
 
                int z = A(parm);
                Console.WriteLine(z.ToString());
            }
        }
    }
}

Open in new window

0
Nothing ever in the clear!

This technical paper will help you implement VMware’s VM encryption as well as implement Veeam encryption which together will achieve the nothing ever in the clear goal. If a bad guy steals VMs, backups or traffic they get nothing.

 
Jens FiedererCommented:
'a naked call to "throw;" will terminate the program if not invoked during the execution of a catch-handler.'

according to
http://www.velocityreviews.com/forums/t282888-abort-instead-of-throwing-exceptions.html
0
 
darkriserAuthor Commented:
That's a good point.
But my problem is a little bit different (haven't mentioned this in my orig post, my fault).
What if unmanaged DLL fails in accessing dynamically allocated memory (trying to access element outside array's boundary)? Then I receive following error from C# directly and catch(...) block inside the DLL is ignored. How to catch this type of error within the DLL?

An unhandled exception of type 'System.AccessViolationException' occurred in Test.exe

Additional information: Attempted to read or write protected memory. This is often an indication that other memory is corrupt.
0
 
Jens FiedererCommented:
If you are using Visual Studio to compile your C++ dll, there is a project option under C/C++ code generation called "Enable C++ Exceptions".

When I had it set to "Yes (/EHsc)" my C++ did not catch the exception.
But when I had it set to "Yes With SEH Exceptions (/EHa)" my C++ DID catch the exception in the unmanaged code.
0
 
darkriserAuthor Commented:
I have missed this option because it is written in very small font :-)
No, seriously, this is what I've been looking for.
Thanks many times.
0
 
Jens FiedererCommented:
Glad to help, that was a fun one.
0

Featured Post

VIDEO: THE CONCERTO CLOUD FOR HEALTHCARE

Modern healthcare requires a modern cloud. View this brief video to understand how the Concerto Cloud for Healthcare can help your organization.

  • 5
  • 3
Tackle projects and never again get stuck behind a technical roadblock.
Join Now