Окончательный управляемый обработчик исключений в смешанном собственном / управляемом исполняемом файле?

StackOverflow https://stackoverflow.com/questions/8704

Вопрос

У меня есть приложение MFC, скомпилированное с помощью / clr, и я пытаюсь реализовать окончательный обработчик для управляемых исключений, которые в противном случае не были бы перехвачены.Для собственных исключений переопределение CWinApp::ProcessWndProcException работает.

Два события, предложенные в книге Джеффа Статья CodeProject,Application.ThreadException и AppDomain.CurrentDomain.UnhandledException, не повышаются.

Кто-нибудь может предложить способ предоставить окончательный управляемый обработчик исключений для смешанного исполняемого файла?


Обновить:

Похоже, что эти обработчики исключений запускаются только после Application.Run или что-то подобное (есть разновидность рабочего потока, не могу вспомнить название.) Если вы хотите действительно глобально перехватывать управляемое исключение, вам нужно установить фильтр SEH.Ты не собираешься получать System.Exception и если вам нужен callstack, вам придется создать свой собственный walker.

В вопросе форума MSDN по этой теме было предложено переопределить достаточно низкоуровневую точку основного потока MFC в try ... catch (Exception^).Например, CWinApp::Run.Это может быть хорошим решением, но я не рассматривал какие-либо последствия для производительности или стабильности.У вас будет возможность войти в систему с помощью стека вызовов, прежде чем вы выйдете из системы, и вы сможете избежать поведения Windows unahndled exception по умолчанию.

Это было полезно?

Решение

Ознакомившись с Интернетом, вы обнаружите, что вам нужно установить фильтр, чтобы получать неуправляемые исключения, проходящие фильтры по пути в ваш домен приложения.От CLR и фильтры необработанных исключений:

Среда CLR использует механизм фильтрации необработанных исключений SEH для перехвата необработанных исключений.

Другие советы

Использование этих двух обработчиков исключений должно сработать.

Почему "должен"?

События не вызываются с помощью приведенного ниже:

extern "C" void wWinMainCRTStartup();

// managed entry point
[System::STAThread]
int managedEntry( void )
{
    FinalExceptionHandler^ handler = gcnew FinalExceptionHandler();

    Application::ThreadException += gcnew System::Threading::ThreadExceptionEventHandler(
                                        handler,
                                        &FinalExceptionHandler::OnThreadException);

    AppDomain::CurrentDomain->UnhandledException += gcnew UnhandledExceptionEventHandler(
                                                        handler,
                                                        &FinalExceptionHandler::OnAppDomainException);

    wWinMainCRTStartup();

    return 0;
}

// final thread exception handler implementation
void FinalExceptionHandler::OnThreadException( Object^ /* sender */, System::Threading::ThreadExceptionEventArgs^ t )
{
    LogWrapper::log->Error( "Unhandled managed thread exception.", t->Exception );
}

// final appdomain exception handler implementation
void FinalExceptionHandler::OnAppDomainException(System::Object ^, UnhandledExceptionEventArgs ^args)
{
    LogWrapper::log->Error( "Unhandled managed appdomain exception.", (Exception^)(args->ExceptionObject) );
}

BOOL CMyApp::InitInstance()
{
    throw gcnew Exception("test unhandled");
    return TRUE;
}

Использование этих двух обработчиков исключений должно сработать.Вы уверены, что добавили их в то место, где они будут вызываться и правильно установлены (т. Е. в вашем приложении управляемый точка входа - ты ведь ее вставил, верно?)

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top