|
#include <ntddk.h>
#include "veh.h"
// the prototype comes from winbase.h in Windows Server 2003 R2 SDK
PVOID WINAPI RtlAddVectoredExceptionHandler(
ULONG First,
PVECTORED_EXCEPTION_HANDLER Handler)
{
PVECTORED_EXCEPTION_NODE pCurrentNode = (PVECTORED_EXCEPTION_NODE)
RtlAllocateHeap( GetProcessHeap(), 0, sizeof(VECTORED_EXCEPTION_NODE) );
if (!pCurrentNode)
{
return 0;
}
pCurrentNode->pfnHandler = RtlEncodePointer(Handler); // encode for security
RtlEnterCriticalSection(&RtlpCalloutEntryLock);
if (First)
{
InsertHeadList(&RtlpCalloutEntryList, &pCurrentNode->ListEntry);
}
else
{
InsertTailList(&RtlpCalloutEntryList, &pCurrentNode->ListEntry);
}
RtlLeaveCriticalSection(&RtlpCalloutEntryLock);
return pCurrentNode;
}
// SDK document says Handler is PVOID, but according to the return value of
// AddVectoredExceptionHandler API, it is PVECTORED_EXCEPTION_NODE actually.
ULONG WINAPI RemoveVectoredExceptionHandler(PVOID Handler)
{
PVECTORED_EXCEPTION_NODE pCurrentNode, pRemovedNode;
BOOL bHandlerExist = FALSE;
RtlEnterCriticalSection(&RtlpCalloutEntryLock);
for (pCurrentNode = (PVECTORED_EXCEPTION_NODE)RtlpCalloutEntryList.Flink;
pCurrentNode != (PVECTORED_EXCEPTION_NODE)&RtlpCalloutEntryList;
pCurrentNode = (PVECTORED_EXCEPTION_NODE)pCurrentNode->ListEntry.Flink)
{
if (pCurrentNode == (PVECTORED_EXCEPTION_NODE)Handler)
{
pRemovedNode = pCurrentNode;
RemoveEntryList(&pCurrentNode->ListEntry);
bHandlerExist = TRUE;
break;
}
}
RtlLeaveCriticalSection(&RtlpCalloutEntryLock);
if (bHandlerExist)
{
RtlFreeHeap(GetProcessHeap(), 0, (LPVOID)pRemovedNode);
return 1;
}
return 0;
}
int WINAPI RtlCallVectoredExceptionHanlers(
PEXCEPTION_RECORD pExcptRec,
PCONTEXT pContext)
{
EXCEPTION_POINTERS ExceptionPointers;
// Is the list empty ?
if (RtlpCalloutEntryList.Flink == &RtlpCalloutEntryList)
{
return 0;
}
else
{
PVECTORED_EXCEPTION_NODE pCurrentNode;
BYTE retValue = 0;
ExceptionPointers.ExceptionRecord = pExcptRec;
ExceptionPointers.ContextRecord = pContext;
RtlEnterCriticalSection(&RtlpCalloutEntryLock);
for (pCurrentNode = (PVECTORED_EXCEPTION_NODE)RtlpCalloutEntryList.Flink;
pCurrentNode != (PVECTORED_EXCEPTION_NODE)&RtlpCalloutEntryList;
pCurrentNode = (PVECTORED_EXCEPTION_NODE)pCurrentNode->ListEntry.Flink)
{
LONG disposition = ((PVECTORED_EXCEPTION_HANDLER)(RtlDecodePointer(pCurrentNode->pfnHandler)))(&ExceptionPointers);
if (disposition == EXCEPTION_CONTINUE_EXECUTION)
{
retValue = 1;
break;
}
}
RtlLeaveCriticalSection(&RtlpCalloutEntryLock);
return retValue;
}
}
|
By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.
If a file you wish to view isn't highlighted, and is a text file (not binary), please
let us know and we'll add colourisation support for it.
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.