我正在编写一个C ++ win32应用程序并遇到一个奇怪的外观,即访问冲突指令不会总是导致应用程序崩溃,这取决于插入指令的位置!这是我遇到的情况:我使用了第三方库,如果我把*(int * 0)= 0;在该库的一个特殊过载功能中,程序不会崩溃,并且会跳过某些指令,导致程序运行异常。代码如下:
void CMainWnd::InitWindow(){
//other constructions
(*(int *)0) = 0;//access violation
//other construction which is under *(int *0)=0; in InitWindow scope will not be executed.
//.....
}
我想该库已经使用了一些SEH技术,因此搜索库代码库并没有找到任何相关的API。
那么,发生了什么?
-----分裂线----------
感谢DanielSęk提示之后所有人的回应。我在这里添加更多细节。这是崩溃函数调用堆栈。
duidemo_d.exe!crash() Line 73 C++
duidemo_d.exe!CMainWnd::InitWindow() Line 89 C++
DuiLib_d.dll!DuiLib::WindowImplBase::OnCreate(unsigned int uMsg, unsigned int wParam, long lParam, int & bHandled) Line 313 C++
DuiLib_d.dll!DuiLib::WindowImplBase::HandleMessage(unsigned int uMsg, unsigned int wParam, long lParam) Line 359 C++
DuiLib_d.dll!DuiLib::CWindowWnd::__WndProc(HWND__ * hWnd, unsigned int uMsg, unsigned int wParam, long lParam) Line 436 C++
这里是如何调用 DuiLib_d.dll!DuiLib :: CWindowWnd :: __ WndProc 。注册一个窗口类,其中包含 WNDCLASS :: lpfnWndProc = CWindowWnd :: __ WndProc 随后用于调用CreateWindow或CreateWindowEx函数。
------分裂线-----
我之所以做这个测试的原因是我想抓住我的程序中发生的每一个意想不到的事情并将其转储,调试它,弄清楚它是如何发生的并解决它,最后减少一个bug。如果在wndproc中发生异常exceotion code,我的catch方法似乎不能正常工作。以下是我创建转储文件的方法。 WinMain 后调用 SetUnhandledExceptionFilter 。
SetUnhandledExceptionFilter((LPTOP_LEVEL_EXCEPTION_FILTER)CallBackCrashHandler);
//dump
LONG CallBackCrashHandler(EXCEPTION_POINTERS* pException)
{
//write dump
HANDLE hFile = CreateFile(gBugReport->m_dumpFilePath.data(), GENERIC_READ | GENERIC_WRITE,
0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
MINIDUMP_EXCEPTION_INFORMATION l_eInfo;
l_eInfo.ThreadId = GetCurrentThreadId();
l_eInfo.ExceptionPointers = pException;
l_eInfo.ClientPointers = FALSE;
MiniDumpWriteDump(
GetCurrentProcess(),
GetCurrentProcessId(),
hFile,
MiniDumpNormal,
pException ? &l_eInfo : NULL,
NULL,
NULL);
CloseHandle(hFile);
return EXCEPTION_EXECUTE_HANDLER;
}