C#不捕获非托管C ++ DLL中的未处理的异常 [英] C# not catching unhandled exceptions from unmanaged C++ dll
问题描述
我遇到的问题是并不是所有类型都被抓住。所以如果我创建以下并执行C#应用程序,那么dll会抛出一个错误,整个应用程序终止。任何想法?
这是在VS2005中创建的,并使用.Net框架v2
C ++ - Test.h
#ifndef INC_TEST_H
#define INC_TEST_H
externC__declspec(dllexport) void ProcessBadCall();
#endif
C ++ - Test.cpp
#include< iostream>
#include< vector>
使用namespace std;
void ProcessBadCall()
{
vector< int> myValues;
int a = myValues [1];
cout<<< a< ENDL;
}
C# - Program.cs
$ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $ $))))))))))))))))))))))))))))))))))) ;
static void Main(string [] args)
{
try
{
ProcessBadCall();
}
catch(SEHException ex)
{
Console.WriteLine(SEH Exception:{0},ex.Message);
}
catch(Exception ex)
{
Console.WriteLine(Exception:{0},ex.Message);
}
}
}
正在编译dll具有以下编译器标志的发布配置。
/ O2 / GL / DWIN32/ DNDEBUG/ D
_CRT_SECURE_NO_WARNINGS/ D
_UNICODE/ DUNICODE/ D_WINDLL
/ FD / EHa / MD / FoRelease\
/ FdRelease\ vc80.pdb/ W4 / WX / nologo
/ c / Wp64 / Zi / TP / errorReport:提示
尝试使用 ExternalException
class捕获:
而且,尝试编译非托管C ++ DLL与异步异常处理(/ EHa)。
看起来你在你的DLL中获得了一个读取访问冲突,这是一种异步异常。
AFAIK,只有.NET v4及更高版本被禁用默认情况下传送异步异常。即使这样,您可以将appCode中的legacyCorruptedStateExceptionsPolicy = true添加到启用它。在这之前,它会自动启用(检查你在app.config中是否设置为false)。
请注意,这是我个人认为您的非托管DLL中的AV本质上是坏的(和危险的)反正,这可能是.NET的简单终止应用程序的正确行为。尝试抛出std :: exception。如果您坚持捕获异步异常,最好的方法是将一个thunking DLL包裹在可能的buggy函数调用的调用周围。再次,高度/不/推荐(尽管我可以看到它如何在调试不正常的DLL中有用)。
I've got an unmanaged C++ dll which is being called from a C# app, I'm trying to get the C# app to catch all exceptions so that in the event of the dll failing due to an unmanaged exception then the user will get a half-decent error message (the C# app is a web service implementing it's own http handler).
The problem I have is that not all types are being caught. So if I create the following and execute the C# app then the dll throws an error and the entire application terminates. Any ideas?
This is being created in VS2005 and using .Net framework v2
C++ - Test.h
#ifndef INC_TEST_H
#define INC_TEST_H
extern "C" __declspec(dllexport) void ProcessBadCall();
#endif
C++ - Test.cpp
#include <iostream>
#include <vector>
using namespace std;
void ProcessBadCall()
{
vector<int> myValues;
int a = myValues[1];
cout << a << endl;
}
C# - Program.cs
class Program
{
[DllImport("Test.dll", EntryPoint="ProcessBadCall")]
static extern void ProcessBadCall();
static void Main(string[] args)
{
try
{
ProcessBadCall();
}
catch (SEHException ex)
{
Console.WriteLine("SEH Exception: {0}", ex.Message);
}
catch (Exception ex)
{
Console.WriteLine("Exception: {0}", ex.Message);
}
}
}
The dll is being compiled under the release configuration with the following compiler flags.
/O2 /GL /D "WIN32" /D "NDEBUG" /D "_CRT_SECURE_NO_WARNINGS" /D "_UNICODE" /D "UNICODE" /D "_WINDLL" /FD /EHa /MD /Fo"Release\" /Fd"Release\vc80.pdb" /W4 /WX /nologo /c /Wp64 /Zi /TP /errorReport:prompt
Try catching using the ExternalException
class:
And, try compiling your unmanaged C++ DLL with asynchronous exception handling (/EHa). It looks like you're getting a Read Access Violation in your DLL which is a type of async exception.
AFAIK, only .NET v4 and above disables the delivery of async exceptions by default. Even then, you could add legacyCorruptedStateExceptionsPolicy=true to the app.config to enable it. Prior to that, it's automatically enabled (check that you have got it set to false in app.config).
Note that it's my personal believe that AVs in your unmanaged DLL is inherently bad (and dangerous) anyway and it's probably the right behavior for .NET to simply terminate the app. Try throwing std::exception instead. If you insists on catching async exceptions, the best way would be to have a thunking DLL which wraps try-catch-all around the call to potentially buggy function calls. Again, highly /not/ recommended (although I can see how it would be useful in debugging the misbehaving DLL).
这篇关于C#不捕获非托管C ++ DLL中的未处理的异常的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!