📄 exceptionmgr.cpp
字号:
//
// FILE: ExceptionMgr.cpp
//
// Copyright (c) 1997 by Aaron Michael Cohen and Mike Woodring
//
/////////////////////////////////////////////////////////////////////////
#include <windows.h>
#include <stdio.h>
#include "ExceptionMgr.h"
CMclCritSec CExceptionManager::s_CritSec;
CExceptionManager *CExceptionManager::s_pThis = 0;
CExceptionManager::CExceptionManager()
{
if( !s_pThis )
{
s_pThis = this;
m_pfxnPrevUnhandledExceptionFilter = SetUnhandledExceptionFilter(UnhandledExceptionFilter);
}
else
{
m_pfxnPrevUnhandledExceptionFilter = 0;
}
}
CExceptionManager::~CExceptionManager()
{
if( m_pfxnPrevUnhandledExceptionFilter )
{
SetUnhandledExceptionFilter(m_pfxnPrevUnhandledExceptionFilter);
m_pfxnPrevUnhandledExceptionFilter = 0;
s_pThis = 0;
}
}
void CExceptionManager::NotifyException( DWORD dwExceptionCode )
{
CMclAutoLock Lock(s_CritSec);
printf("[tid 0x%08lx] NotifyException\n", GetCurrentThreadId());
NotifyHandlers(CExceptionHandler::THREAD_EXCEPTION, dwExceptionCode);
}
LONG WINAPI CExceptionManager::UnhandledExceptionFilter( PEXCEPTION_POINTERS pExceptionInfo )
{
CMclAutoLock Lock(s_CritSec);
printf("[tid 0x%08lx] UnhandledExceptionFilter\n", GetCurrentThreadId());
s_pThis->NotifyHandlers(CExceptionHandler::UNHANDLED_EXCEPTION, pExceptionInfo->ExceptionRecord->ExceptionCode);
return(EXCEPTION_EXECUTE_HANDLER);
}
BOOL CExceptionManager::RegisterHandler( CExceptionHandler *pHandler )
{
CMclAutoLock Lock(s_CritSec);
printf("[tid 0x%08lx] RegisterHandler 0x%x\n", GetCurrentThreadId(), pHandler);
return m_RegisteredHandlers.PutOnTailOfList(pHandler);
}
void CExceptionManager::ForEachHandler( PHANDLER_ITERATOR pfxnIterator, DWORD dwArg1, DWORD dwArg2, DWORD dwArg3 )
{
CMclLinkedList<CExceptionHandler *> Handlers;
CExceptionHandler *pHandler = 0;
// Call the iterator for each handler in the list of
// registered handlers.
//
while( m_RegisteredHandlers.GetFromHeadOfList(pHandler, 0) )
{
if( pfxnIterator(pHandler, dwArg1, dwArg2, dwArg3) )
{
// Keep this handler on the list of registered handlers.
//
Handlers.PutOnTailOfList(pHandler);
}
}
// Restore the list of registered handlers.
//
while( Handlers.GetFromHeadOfList(pHandler, 0) )
{
m_RegisteredHandlers.PutOnTailOfList(pHandler);
}
}
void CExceptionManager::UnregisterHandler( CExceptionHandler *pHandler )
{
CMclAutoLock Lock(s_CritSec);
printf("[tid 0x%08lx] UnregisterHandler 0x%x\n", GetCurrentThreadId(), pHandler);
ForEachHandler(RemoveHandler, (DWORD)pHandler);
}
void CExceptionManager::NotifyHandlers
(
CExceptionHandler::NOTIFICATION_CONTEXT Context,
DWORD dwExceptionCode
)
{
CMclAutoLock Lock(s_CritSec);
ForEachHandler(NotifyHandler, (DWORD)Context, dwExceptionCode, (DWORD)this);
}
BOOL CExceptionManager::RemoveHandler
(
CExceptionHandler *pHandler,
DWORD dwArg1, // CExceptionHandler *pTargetHandlerToRemove
DWORD dwArg2, // Not used
DWORD dwArg3 // Not used
)
{
// This function returns TRUE to keep the given handler in the list
// of handler and FALSE to indicate that the given handler matches
// the handler to be removed from the list.
//
return BOOL(pHandler != (CExceptionHandler *)dwArg1);
}
BOOL CExceptionManager::NotifyHandler
(
CExceptionHandler *pHandler,
DWORD dwArg1, // CExceptionHandler::NOTIFICATION_CONTEXT
DWORD dwArg2, // Exception code
DWORD dwArg3 // CExceptionManager *pThis
)
{
CExceptionManager *pThis = (CExceptionManager *)dwArg3;
printf("[tid 0x%08lx] Notifying handler 0x%x\n", GetCurrentThreadId(), pHandler);
// Call the pure virtual notification function, which is implemented
// by derived versions of the CExceptionManager class.
//
pThis->NotifyExceptionHandler(
pHandler,
(CExceptionHandler::NOTIFICATION_CONTEXT)dwArg1,
dwArg2
);
return(TRUE); // Keep all handlers in the list.
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -