📄 cmseh.cpp
字号:
#include <windows.h>
#include <stdio.h>
#include <DbgHelp.h>
#include "CMSeh.h"
using namespace MatrixCore::System;
BOOL CMSeh::m_bMiniDump = TRUE;
CMSeh::CMSeh(int iID_ErrWindow,BOOL bMiniDump)
:m_pFilter(0)
{
m_bMiniDump = bMiniDump;
SetErrorMode(iID_ErrWindow);
SetUnhandledExceptionFilter((LPTOP_LEVEL_EXCEPTION_FILTER)HandleDebugEvent);
}
CMSeh::~CMSeh()
{
}
BOOL CMSeh::GetLogicalAddress(PVOID addr, PTSTR szModule, DWORD len, DWORD §ion, DWORD &offset)
{
MEMORY_BASIC_INFORMATION mbi;
if(!VirtualQuery(addr, &mbi, sizeof(mbi))) return FALSE;
DWORD hMod = (DWORD)mbi.AllocationBase;
if(!GetModuleFileName((HMODULE)hMod, szModule, len)) return FALSE;
PIMAGE_DOS_HEADER pDosHdr = (PIMAGE_DOS_HEADER)hMod;
PIMAGE_NT_HEADERS pNtHdr = (PIMAGE_NT_HEADERS)(hMod + pDosHdr->e_lfanew);
PIMAGE_SECTION_HEADER pSection = IMAGE_FIRST_SECTION(pNtHdr);
DWORD rva = (DWORD)addr - hMod; // RVA is offset from module load address
for(unsigned i = 0; i < pNtHdr->FileHeader.NumberOfSections; i++, pSection++)
{
DWORD sectionStart = pSection->VirtualAddress;
DWORD sectionEnd = sectionStart + max(pSection->SizeOfRawData, pSection->Misc.VirtualSize);
if((rva >= sectionStart) && (rva <= sectionEnd))
{
section = i + 1;
offset = rva - sectionStart;
return TRUE;
}
}
return FALSE;
}
void CMSeh::PrintStack(CONTEXT *pCtx)
{
DWORD pc = pCtx->Eip;
PDWORD pFrame, pPrevFrame;
char WriteBuf[256];
pFrame = (PDWORD)pCtx->Ebp;
do
{
char szModule[MAX_PATH] = {0,};
DWORD section = 0, offset = 0;
GetLogicalAddress((PVOID)pc, szModule, sizeof(szModule), section, offset);
sprintf(WriteBuf,"%08X %08X %04X:%08X %s\n", pc, pFrame, section, offset, szModule);
WriteSeh(OUTPUTFILENAME,WriteBuf);
pc = pFrame[1];
pPrevFrame = pFrame;
pFrame = (PDWORD)pFrame[0];
if((DWORD)pFrame & 3) break;
if(pFrame <= pPrevFrame) break;
if(IsBadWritePtr(pFrame, sizeof(PVOID) * 2)) break;
} while(TRUE);
};
BOOL CMSeh::WriteSeh(char *cFn,char* cBuf)
{
FILE *pFile;
char cBuffer[8096];
char cTmpBuf[512];
ZeroMemory(cBuffer, sizeof(cBuffer));
pFile = fopen(cFn, "at");
if (pFile == NULL)
{
MessageBox(NULL,"FILE OPEN ERR!!!","WARNNING",MB_OK);
return FALSE;
}
fwrite(cBuf, 1, strlen(cBuf), pFile);
fclose(pFile);
return TRUE;
}
BOOL CMSeh::CrashExceptionDump(PEXCEPTION_POINTERS ExceptionInfo, const char* szDumpFileName)
{
HANDLE hFile = CreateFile(szDumpFileName,
GENERIC_WRITE,
0,
NULL,
CREATE_ALWAYS,
FILE_ATTRIBUTE_NORMAL,
NULL);
if (hFile)
{
MINIDUMP_EXCEPTION_INFORMATION eInfo;
eInfo.ThreadId = GetCurrentThreadId();
eInfo.ExceptionPointers = ExceptionInfo;
eInfo.ClientPointers = FALSE;
MINIDUMP_CALLBACK_INFORMATION cbMiniDump;
cbMiniDump.CallbackRoutine = NULL;
cbMiniDump.CallbackParam = 0;
MiniDumpWriteDump(
GetCurrentProcess(),
GetCurrentProcessId(),
hFile,
MiniDumpNormal,
ExceptionInfo ? &eInfo : NULL,
NULL,
NULL);
}
CloseHandle(hFile);
return EXCEPTION_EXECUTE_HANDLER;
}
LONG _stdcall CMSeh::HandleDebugEvent(LPEXCEPTION_POINTERS lpEP)
{
PVOID exceptionAddress = lpEP->ExceptionRecord->ExceptionAddress;
DWORD exceptionCode = lpEP->ExceptionRecord->ExceptionCode;
char sStatus[256];
char writebuf[256];
SYSTEMTIME SysTime;
switch (exceptionCode)
{
case STATUS_WAIT_0:
strcpy(sStatus,"Wait 0");
break;
case STATUS_ABANDONED_WAIT_0:
strcpy(sStatus,"Abandoned Wait 0");
break;
case STATUS_USER_APC:
strcpy(sStatus,"User APC");
break;
case STATUS_TIMEOUT:
strcpy(sStatus,"Timeout");
break;
case STATUS_PENDING:
strcpy(sStatus,"Pending");
break;
case STATUS_SEGMENT_NOTIFICATION:
return DBG_EXCEPTION_NOT_HANDLED;
case STATUS_GUARD_PAGE_VIOLATION:
strcpy(sStatus,"Guard Page Violation");
break;
case STATUS_DATATYPE_MISALIGNMENT:
strcpy(sStatus,"Data Type Misalignment");
break;
case STATUS_BREAKPOINT:
return DBG_EXCEPTION_NOT_HANDLED;
case STATUS_SINGLE_STEP:
return DBG_EXCEPTION_NOT_HANDLED;
case STATUS_ACCESS_VIOLATION:
strcpy(sStatus,"Access Violation");
break;
case STATUS_IN_PAGE_ERROR:
strcpy(sStatus,"In Page Error");
break;
case STATUS_NO_MEMORY:
strcpy(sStatus,"No Memory");
break;
case STATUS_ILLEGAL_INSTRUCTION:
strcpy(sStatus,"Illegal Instruction");
break;
case STATUS_NONCONTINUABLE_EXCEPTION:
strcpy(sStatus,"Noncontinuable Exception");
break;
case STATUS_INVALID_DISPOSITION:
strcpy(sStatus,"Invalid Disposition");
break;
case STATUS_ARRAY_BOUNDS_EXCEEDED:
strcpy(sStatus,"Array Bounds Exceeded");
break;
case STATUS_FLOAT_DENORMAL_OPERAND:
strcpy(sStatus,"Float Denormal Operand");
break;
case STATUS_FLOAT_DIVIDE_BY_ZERO:
strcpy(sStatus,"Divide by Zero");
break;
case STATUS_FLOAT_INEXACT_RESULT:
strcpy(sStatus,"Float Inexact Result");
break;
case STATUS_FLOAT_INVALID_OPERATION:
strcpy(sStatus,"Float Invalid Operation");
break;
case STATUS_FLOAT_OVERFLOW:
strcpy(sStatus,"Float Overflow");
break;
case STATUS_FLOAT_STACK_CHECK:
strcpy(sStatus,"Float Stack Check");
break;
case STATUS_FLOAT_UNDERFLOW:
strcpy(sStatus,"Float Uderflow");
break;
case STATUS_INTEGER_DIVIDE_BY_ZERO:
strcpy(sStatus,"Integer Divide by Zero");
break;
case STATUS_INTEGER_OVERFLOW:
strcpy(sStatus,"Integer Overflow");
break;
case STATUS_PRIVILEGED_INSTRUCTION:
strcpy(sStatus,"Privileged Instruction");
break;
case STATUS_STACK_OVERFLOW:
strcpy(sStatus,"Stack Overflow");
break;
case STATUS_CONTROL_C_EXIT:
strcpy(sStatus,"Ctrl+C Exit");
break;
default:
strcpy(sStatus,"C++ Exception");
break;
}//switch
GetLocalTime(&SysTime);
sprintf(writebuf, "\n%04d:%02d:%02d:%02d:%02d:%02d\t",SysTime.wYear,SysTime.wMonth,SysTime.wDay,SysTime.wHour,SysTime.wMinute, SysTime.wSecond);
WriteSeh(OUTPUTFILENAME,writebuf);
WriteSeh(OUTPUTFILENAME,"***UNHANDLED EXCEPTION****\n");
sprintf(writebuf,"Reason: %s At Address %p\n\n",sStatus,exceptionAddress);
WriteSeh(OUTPUTFILENAME,writebuf);
PrintStack(lpEP->ContextRecord);
char cDumpFileNmae[MAX_PATH];
sprintf(cDumpFileNmae, "%02d_%02d_%02d_%02d_%02d",SysTime.wMonth,SysTime.wDay,SysTime.wHour,SysTime.wMinute, SysTime.wSecond);
strcat(cDumpFileNmae,".dmp");
// 固聪 待橇
if(m_bMiniDump == TRUE)
CrashExceptionDump(lpEP,cDumpFileNmae);
//if (m_pFilter)
// m_pFilter(lpEP);
::MessageBox(NULL,"Seh!!!!!!!!!",cDumpFileNmae,MB_OK);
return EXCEPTION_CONTINUE_SEARCH;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -