mirror of
https://github.com/beefytech/Beef.git
synced 2025-06-08 03:28:20 +02:00
Added ability to catch llvm errs(), shared crashcatcher object
This commit is contained in:
parent
76e29d385b
commit
f1eafa8d81
4 changed files with 274 additions and 113 deletions
|
@ -1,5 +1,4 @@
|
|||
#include "CrashCatcher.h"
|
||||
#include "../util/CritSect.h"
|
||||
#include "../util/Dictionary.h"
|
||||
#include <commdlg.h>
|
||||
#include <time.h>
|
||||
|
@ -51,15 +50,7 @@ static SYMFUNCTIONTABLEACCESSPROC gSymFunctionTableAccess = NULL;
|
|||
static SYMGETMODULEBASEPROC gSymGetModuleBase = NULL;
|
||||
static SYMGETSYMFROMADDRPROC gSymGetSymFromAddr = NULL;
|
||||
static SYMGETLINEFROMADDR gSymGetLineFromAddr = NULL;
|
||||
static Array<CrashInfoFunc> gCrashInfoFuncs;
|
||||
static StringT<0> gCrashInfo;
|
||||
static bool gCrashed = false;
|
||||
extern CritSect gBfpCritSect;
|
||||
|
||||
static EXCEPTION_POINTERS* gExceptionPointers = NULL;
|
||||
static LPTOP_LEVEL_EXCEPTION_FILTER gPreviousFilter = NULL;
|
||||
|
||||
static bool gDebugError = false;
|
||||
|
||||
static bool CreateMiniDump(EXCEPTION_POINTERS* pep, const StringImpl& filePath);
|
||||
|
||||
|
@ -162,7 +153,6 @@ struct
|
|||
{ 0xFFFFFFFF, "" }
|
||||
};
|
||||
|
||||
static bool gUseDefaultFonts;
|
||||
static HFONT gDialogFont;
|
||||
static HFONT gBoldFont;
|
||||
static String gErrorTitle;
|
||||
|
@ -171,10 +161,9 @@ static HWND gDebugButtonWindow = NULL;
|
|||
static HWND gYesButtonWindow = NULL;
|
||||
static HWND gNoButtonWindow = NULL;
|
||||
static bool gExiting = false;
|
||||
static BfpCrashReportKind gCrashReportKind = BfpCrashReportKind_Default;
|
||||
|
||||
static LRESULT CALLBACK SEHWindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
{
|
||||
switch (uMsg)
|
||||
{
|
||||
case WM_COMMAND:
|
||||
|
@ -198,7 +187,7 @@ static LRESULT CALLBACK SEHWindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARA
|
|||
|
||||
if (::GetSaveFileNameW(&openFileName))
|
||||
{
|
||||
CreateMiniDump(gExceptionPointers, UTF8Encode(fileName));
|
||||
CreateMiniDump(CrashCatcher::Get()->mExceptionPointers, UTF8Encode(fileName));
|
||||
}
|
||||
}
|
||||
else if (hwndCtl == gNoButtonWindow)
|
||||
|
@ -207,7 +196,7 @@ static LRESULT CALLBACK SEHWindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARA
|
|||
}
|
||||
else if (hwndCtl == gDebugButtonWindow)
|
||||
{
|
||||
gDebugError = true;
|
||||
CrashCatcher::Get()->mDebugError = true;
|
||||
gExiting = true;
|
||||
}
|
||||
}
|
||||
|
@ -222,6 +211,8 @@ static LRESULT CALLBACK SEHWindowProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARA
|
|||
|
||||
static void ShowErrorDialog(const StringImpl& errorTitle, const StringImpl& errorText)
|
||||
{
|
||||
bool gUseDefaultFonts;
|
||||
|
||||
HINSTANCE gHInstance = ::GetModuleHandle(NULL);
|
||||
|
||||
OSVERSIONINFO aVersionInfo;
|
||||
|
@ -247,7 +238,6 @@ static void ShowErrorDialog(const StringImpl& errorTitle, const StringImpl& erro
|
|||
gErrorTitle = errorTitle;
|
||||
gErrorText = errorText;
|
||||
|
||||
|
||||
WNDCLASSW wc;
|
||||
wc.style = 0;
|
||||
wc.cbClsExtra = 0;
|
||||
|
@ -810,18 +800,18 @@ static String GetVersion(const StringImpl& fileName)
|
|||
|
||||
static void DoHandleDebugEvent(LPEXCEPTION_POINTERS lpEP)
|
||||
{
|
||||
if (gCrashed)
|
||||
if (CrashCatcher::Get()->mCrashed)
|
||||
return;
|
||||
gCrashed = true;
|
||||
CrashCatcher::Get()->mCrashed = true;
|
||||
|
||||
HMODULE hMod = GetModuleHandleA(NULL);
|
||||
|
||||
PIMAGE_DOS_HEADER pDosHdr = (PIMAGE_DOS_HEADER)hMod;
|
||||
PIMAGE_NT_HEADERS pNtHdr = (PIMAGE_NT_HEADERS)((uint8*)hMod + pDosHdr->e_lfanew);
|
||||
bool isCLI = pNtHdr->OptionalHeader.Subsystem == IMAGE_SUBSYSTEM_WINDOWS_CUI;
|
||||
if (gCrashReportKind == BfpCrashReportKind_GUI)
|
||||
if (CrashCatcher::Get()->mCrashReportKind == BfpCrashReportKind_GUI)
|
||||
isCLI = false;
|
||||
else if ((gCrashReportKind == BfpCrashReportKind_Console) || (gCrashReportKind == BfpCrashReportKind_PrintOnly))
|
||||
else if ((CrashCatcher::Get()->mCrashReportKind == BfpCrashReportKind_Console) || (CrashCatcher::Get()->mCrashReportKind == BfpCrashReportKind_PrintOnly))
|
||||
isCLI = true;
|
||||
|
||||
bool hasImageHelp = LoadImageHelp();
|
||||
|
@ -858,12 +848,12 @@ static void DoHandleDebugEvent(LPEXCEPTION_POINTERS lpEP)
|
|||
aDebugDump += StrFormat("Crash minidump saved as %s\n", crashPath.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
for (auto func : gCrashInfoFuncs)
|
||||
|
||||
for (auto func : CrashCatcher::Get()->mCrashInfoFuncs)
|
||||
func();
|
||||
|
||||
aDebugDump.Append(gCrashInfo);
|
||||
|
||||
aDebugDump.Append(CrashCatcher::Get()->mCrashInfo);
|
||||
|
||||
for (int i = 0; i < (int)aDebugDump.length(); i++)
|
||||
{
|
||||
char c = aDebugDump[i];
|
||||
|
@ -994,26 +984,31 @@ static void DoHandleDebugEvent(LPEXCEPTION_POINTERS lpEP)
|
|||
|
||||
CrashCatcher::CrashCatcher()
|
||||
{
|
||||
|
||||
mCrashed = false;
|
||||
mInitialized = false;
|
||||
mExceptionPointers = NULL;
|
||||
mPreviousFilter = NULL;
|
||||
mDebugError = false;
|
||||
mCrashReportKind = BfpCrashReportKind_Default;
|
||||
}
|
||||
|
||||
static long __stdcall SEHFilter(LPEXCEPTION_POINTERS lpExceptPtr)
|
||||
{
|
||||
OutputDebugStrF("SEH Filter! CraskReportKind:%d\n", gCrashReportKind);
|
||||
OutputDebugStrF("SEH Filter! CraskReportKind:%d\n", CrashCatcher::Get()->mCrashReportKind);
|
||||
|
||||
if (gCrashReportKind == BfpCrashReportKind_None)
|
||||
if (CrashCatcher::Get()->mCrashReportKind == BfpCrashReportKind_None)
|
||||
{
|
||||
OutputDebugStrF("Silent Exiting\n");
|
||||
::TerminateProcess(GetCurrentProcess(), lpExceptPtr->ExceptionRecord->ExceptionCode);
|
||||
}
|
||||
|
||||
AutoCrit autoCrit(gBfpCritSect);
|
||||
AutoCrit autoCrit(CrashCatcher::Get()->mBfpCritSect);
|
||||
//::ExitProcess();
|
||||
//quick_exit(1);
|
||||
|
||||
if (!gCrashed)
|
||||
if (!CrashCatcher::Get()->mCrashed)
|
||||
{
|
||||
gExceptionPointers = lpExceptPtr;
|
||||
CrashCatcher::Get()->mExceptionPointers = lpExceptPtr;
|
||||
//CreateMiniDump(lpExceptPtr);
|
||||
DoHandleDebugEvent(lpExceptPtr);
|
||||
}
|
||||
|
@ -1021,7 +1016,7 @@ static long __stdcall SEHFilter(LPEXCEPTION_POINTERS lpExceptPtr)
|
|||
//if (!gDebugError)
|
||||
//SetErrorMode(SEM_NOGPFAULTERRORBOX);
|
||||
|
||||
if (gCrashReportKind == BfpCrashReportKind_PrintOnly)
|
||||
if (CrashCatcher::Get()->mCrashReportKind == BfpCrashReportKind_PrintOnly)
|
||||
{
|
||||
::TerminateProcess(GetCurrentProcess(), lpExceptPtr->ExceptionRecord->ExceptionCode);
|
||||
}
|
||||
|
@ -1039,9 +1034,13 @@ static long __stdcall VectorExceptionHandler(LPEXCEPTION_POINTERS lpExceptPtr)
|
|||
|
||||
|
||||
void CrashCatcher::Init()
|
||||
{
|
||||
gPreviousFilter = SetUnhandledExceptionFilter(SEHFilter);
|
||||
OutputDebugStrF("Setting SEH filter %p\n", gPreviousFilter);
|
||||
{
|
||||
if (mInitialized)
|
||||
return;
|
||||
|
||||
mPreviousFilter = SetUnhandledExceptionFilter(SEHFilter);
|
||||
OutputDebugStrF("Setting SEH filter %p\n", mPreviousFilter);
|
||||
mInitialized = true;
|
||||
|
||||
// OutputDebugStrF("AddVectoredExceptionHandler 2\n");
|
||||
// AddVectoredExceptionHandler(0, VectorExceptionHandler);
|
||||
|
@ -1065,30 +1064,33 @@ void CrashCatcher::Test()
|
|||
|
||||
void CrashCatcher::AddCrashInfoFunc(CrashInfoFunc crashInfoFunc)
|
||||
{
|
||||
AutoCrit autoCrit(gBfpCritSect);
|
||||
gCrashInfoFuncs.Add(crashInfoFunc);
|
||||
AutoCrit autoCrit(mBfpCritSect);
|
||||
mCrashInfoFuncs.Add(crashInfoFunc);
|
||||
}
|
||||
|
||||
void CrashCatcher::AddInfo(const StringImpl& str)
|
||||
{
|
||||
AutoCrit autoCrit(gBfpCritSect);
|
||||
gCrashInfo.Append(str);
|
||||
AutoCrit autoCrit(mBfpCritSect);
|
||||
mCrashInfo.Append(str);
|
||||
if (!str.EndsWith('\n'))
|
||||
mCrashInfo.Append('\n');
|
||||
}
|
||||
|
||||
void CrashCatcher::Crash(const StringImpl& str)
|
||||
{
|
||||
OutputDebugStrF("CrashCatcher::Crash\n");
|
||||
|
||||
gBfpCritSect.Lock();
|
||||
gCrashInfo.Append(str);
|
||||
mBfpCritSect.Lock();
|
||||
mCrashInfo.Append(str);
|
||||
mCrashInfo.Append("\n");
|
||||
|
||||
if (gPreviousFilter == NULL)
|
||||
if (mPreviousFilter == NULL)
|
||||
{
|
||||
// A little late, but install handler now so we can catch this crash
|
||||
Init();
|
||||
}
|
||||
|
||||
gBfpCritSect.Unlock();
|
||||
mBfpCritSect.Unlock();
|
||||
|
||||
|
||||
__debugbreak();
|
||||
|
@ -1104,11 +1106,74 @@ void CrashCatcher::Crash(const StringImpl& str)
|
|||
{
|
||||
|
||||
}*/
|
||||
|
||||
|
||||
exit(1);
|
||||
}
|
||||
|
||||
void CrashCatcher::SetCrashReportKind(BfpCrashReportKind crashReportKind)
|
||||
{
|
||||
gCrashReportKind = crashReportKind;
|
||||
mCrashReportKind = crashReportKind;
|
||||
}
|
||||
|
||||
struct CrashCatchMemory
|
||||
{
|
||||
public:
|
||||
CrashCatcher* mBpManager;
|
||||
int mABIVersion;
|
||||
};
|
||||
|
||||
#define CRASHCATCH_ABI_VERSION 1
|
||||
|
||||
static CrashCatcher* sCrashCatcher = NULL;
|
||||
CrashCatcher* CrashCatcher::Get()
|
||||
{
|
||||
if (sCrashCatcher != NULL)
|
||||
return sCrashCatcher;
|
||||
|
||||
char mutexName[128];
|
||||
sprintf(mutexName, "BfCrashCatch_mutex_%d", GetCurrentProcessId());
|
||||
char memName[128];
|
||||
sprintf(memName, "BfCrashCatch_mem_%d", GetCurrentProcessId());
|
||||
|
||||
auto mutex = ::CreateMutexA(NULL, TRUE, mutexName);
|
||||
if (mutex != NULL)
|
||||
{
|
||||
HANDLE fileMapping = ::OpenFileMappingA(FILE_MAP_ALL_ACCESS, FALSE, memName);
|
||||
if (fileMapping != NULL)
|
||||
{
|
||||
CrashCatchMemory* sharedMem = (CrashCatchMemory*)MapViewOfFile(fileMapping, FILE_MAP_ALL_ACCESS, 0, 0, sizeof(CrashCatchMemory));
|
||||
if (sharedMem != NULL)
|
||||
{
|
||||
if (sharedMem->mABIVersion == CRASHCATCH_ABI_VERSION)
|
||||
sCrashCatcher = sharedMem->mBpManager;
|
||||
::UnmapViewOfFile(sharedMem);
|
||||
}
|
||||
::CloseHandle(fileMapping);
|
||||
}
|
||||
else
|
||||
{
|
||||
fileMapping = ::CreateFileMappingA(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, sizeof(CrashCatchMemory), memName);
|
||||
if (fileMapping != NULL)
|
||||
{
|
||||
CrashCatchMemory* sharedMem = (CrashCatchMemory*)MapViewOfFile(fileMapping, FILE_MAP_ALL_ACCESS, 0, 0, sizeof(CrashCatchMemory));
|
||||
if (sharedMem != NULL)
|
||||
{
|
||||
sCrashCatcher = new CrashCatcher();
|
||||
sharedMem->mBpManager = sCrashCatcher;
|
||||
sharedMem->mABIVersion = CRASHCATCH_ABI_VERSION;
|
||||
::UnmapViewOfFile(sharedMem);
|
||||
::ReleaseMutex(mutex);
|
||||
}
|
||||
else
|
||||
{
|
||||
::CloseHandle(fileMapping);
|
||||
::CloseHandle(mutex);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (sCrashCatcher == NULL)
|
||||
sCrashCatcher = new CrashCatcher();
|
||||
return sCrashCatcher;
|
||||
}
|
|
@ -1,6 +1,7 @@
|
|||
#pragma once
|
||||
|
||||
#include "../../BeefySysLib/Common.h"
|
||||
#include "../util/CritSect.h"
|
||||
|
||||
NS_BF_BEGIN
|
||||
|
||||
|
@ -8,6 +9,17 @@ typedef void(*CrashInfoFunc)();
|
|||
|
||||
class CrashCatcher
|
||||
{
|
||||
public:
|
||||
Array<CrashInfoFunc> mCrashInfoFuncs;
|
||||
StringT<0> mCrashInfo;
|
||||
bool mCrashed;
|
||||
bool mInitialized;
|
||||
CritSect mBfpCritSect;
|
||||
EXCEPTION_POINTERS* mExceptionPointers;
|
||||
LPTOP_LEVEL_EXCEPTION_FILTER mPreviousFilter;
|
||||
bool mDebugError;
|
||||
BfpCrashReportKind mCrashReportKind;
|
||||
|
||||
public:
|
||||
CrashCatcher();
|
||||
|
||||
|
@ -17,7 +29,9 @@ public:
|
|||
|
||||
void Test();
|
||||
void Crash(const StringImpl& str);
|
||||
void SetCrashReportKind(BfpCrashReportKind crashReportKind);
|
||||
void SetCrashReportKind(BfpCrashReportKind crashReportKind);
|
||||
|
||||
static CrashCatcher* Get();
|
||||
};
|
||||
|
||||
NS_BF_END
|
||||
|
|
|
@ -23,8 +23,6 @@
|
|||
|
||||
#include "util/AllocDebug.h"
|
||||
|
||||
//kernel32.lib;user32.lib;gdi32.lib;winspool.lib;comdlg32.lib;advapi32.lib;shell32.lib;ole32.lib;oleaut32.lib;uuid.lib;odbc32.lib;odbccp32.lib;%(AdditionalDependencies)
|
||||
|
||||
#pragma comment(lib, "ole32.lib")
|
||||
#pragma comment(lib, "shell32.lib")
|
||||
#pragma comment(lib, "user32.lib")
|
||||
|
@ -47,10 +45,6 @@ struct WindowsSharedInfo
|
|||
|
||||
static WindowsSharedInfo* gGlobalPlatformInfo = NULL;
|
||||
static HANDLE gGlobalMutex = 0;
|
||||
static CrashCatcher gCrashCatcher;
|
||||
|
||||
//#define HANDLE_TO_BFPFILE(val) ((BfpFile*)(val))
|
||||
//#define BFPFILE_TO_HANDLE(val) ((HANDLE)(val))
|
||||
|
||||
#define STATUS_INFO_LENGTH_MISMATCH 0xc0000004
|
||||
typedef LONG KPRIORITY;
|
||||
|
@ -950,11 +944,10 @@ BFP_EXPORT void BFP_CALLTYPE BfpSystem_Init(int version, BfpSystemInitFlags flag
|
|||
// Then we install our abort handler.
|
||||
signal(SIGABRT, &AbortHandler);
|
||||
|
||||
gCrashCatcher.Init();
|
||||
|
||||
CrashCatcher::Get()->Init();
|
||||
if ((flags & BfpSystemInitFlag_SilentCrash) != 0)
|
||||
gCrashCatcher.SetCrashReportKind(BfpCrashReportKind_None);
|
||||
}
|
||||
CrashCatcher::Get()->SetCrashReportKind(BfpCrashReportKind_None);
|
||||
}
|
||||
}
|
||||
|
||||
BFP_EXPORT void BFP_CALLTYPE BfpSystem_SetCommandLine(int argc, char** argv)
|
||||
|
@ -964,17 +957,17 @@ BFP_EXPORT void BFP_CALLTYPE BfpSystem_SetCommandLine(int argc, char** argv)
|
|||
|
||||
BFP_EXPORT void BFP_CALLTYPE BfpSystem_SetCrashReportKind(BfpCrashReportKind crashReportKind)
|
||||
{
|
||||
gCrashCatcher.SetCrashReportKind(crashReportKind);
|
||||
CrashCatcher::Get()->SetCrashReportKind(crashReportKind);
|
||||
}
|
||||
|
||||
BFP_EXPORT void BFP_CALLTYPE BfpSystem_AddCrashInfoFunc(BfpCrashInfoFunc crashInfoFunc)
|
||||
{
|
||||
gCrashCatcher.AddCrashInfoFunc(crashInfoFunc);
|
||||
CrashCatcher::Get()->AddCrashInfoFunc(crashInfoFunc);
|
||||
}
|
||||
|
||||
BFP_EXPORT void BFP_CALLTYPE BfpSystem_AddCrashInfo(const char* str)
|
||||
{
|
||||
gCrashCatcher.AddInfo(str);
|
||||
CrashCatcher::Get()->AddInfo(str);
|
||||
}
|
||||
|
||||
BFP_EXPORT void BFP_CALLTYPE BfpSystem_Shutdown()
|
||||
|
@ -1077,9 +1070,9 @@ BFP_EXPORT uint64 BFP_CALLTYPE BfpSystem_InterlockedCompareExchange64(uint64* pt
|
|||
BFP_EXPORT void BFP_CALLTYPE BfpSystem_FatalError(const char* error, const char* title)
|
||||
{
|
||||
if (title != NULL)
|
||||
gCrashCatcher.Crash(String(title) + "\n" + String(error));
|
||||
CrashCatcher::Get()->Crash(String(title) + "\n" + String(error));
|
||||
else
|
||||
gCrashCatcher.Crash(error);
|
||||
CrashCatcher::Get()->Crash(error);
|
||||
}
|
||||
|
||||
BFP_EXPORT void BFP_CALLTYPE BfpSystem_GetCommandLine(char* outStr, int* inOutStrSize, BfpSystemResult* outResult)
|
||||
|
|
|
@ -2,6 +2,8 @@
|
|||
#include "BfModule.h"
|
||||
#include "BeefySysLib/util/BeefPerf.h"
|
||||
#include "BeefySysLib/util/Hash.h"
|
||||
#include <io.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4141)
|
||||
|
@ -215,6 +217,147 @@ static llvm::Attribute::AttrKind LLVMMapAttribute(BfIRAttribute attr)
|
|||
return llvm::Attribute::None;
|
||||
}
|
||||
|
||||
#ifdef BF_PLATFORM_WINDOWS
|
||||
struct BfTempFile
|
||||
{
|
||||
String mContents;
|
||||
String mFilePath;
|
||||
CritSect mCritSect;
|
||||
FILE* mFP;
|
||||
|
||||
BfTempFile()
|
||||
{
|
||||
mFP = NULL;
|
||||
}
|
||||
|
||||
~BfTempFile()
|
||||
{
|
||||
if (mFP != NULL)
|
||||
fclose(mFP);
|
||||
if (!mFilePath.IsEmpty())
|
||||
::DeleteFileW(UTF8Decode(mFilePath).c_str());
|
||||
}
|
||||
|
||||
bool Create()
|
||||
{
|
||||
AutoCrit autoCrit(mCritSect);
|
||||
if (mFP != NULL)
|
||||
return false;
|
||||
|
||||
WCHAR wPath[4096];
|
||||
wPath[0] = 0;
|
||||
::GetTempPathW(4096, wPath);
|
||||
|
||||
WCHAR wFilePath[4096];
|
||||
wFilePath[0] = 0;
|
||||
GetTempFileNameW(wPath, L"bftmp", 0, wFilePath);
|
||||
|
||||
mFilePath = UTF8Encode(wFilePath);
|
||||
mFP = _wfopen(wFilePath, L"w+D");
|
||||
return mFP != NULL;
|
||||
}
|
||||
|
||||
String GetContents()
|
||||
{
|
||||
AutoCrit autoCrit(mCritSect);
|
||||
|
||||
if (mFP != NULL)
|
||||
{
|
||||
fseek(mFP, 0, SEEK_END);
|
||||
int size = (int)ftell(mFP);
|
||||
fseek(mFP, 0, SEEK_SET);
|
||||
|
||||
char* str = new char[size];
|
||||
int readSize = (int)fread(str, 1, size, mFP);
|
||||
mContents.Append(str, readSize);
|
||||
delete [] str;
|
||||
fclose(mFP);
|
||||
mFP = NULL;
|
||||
|
||||
::DeleteFileW(UTF8Decode(mFilePath).c_str());
|
||||
}
|
||||
return mContents;
|
||||
}
|
||||
};
|
||||
|
||||
static BfTempFile gTempFile;
|
||||
|
||||
static void AddStdErrCrashInfo()
|
||||
{
|
||||
String tempContents = gTempFile.GetContents();
|
||||
if (!tempContents.IsEmpty())
|
||||
BfpSystem_AddCrashInfo(tempContents.c_str());
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
///
|
||||
|
||||
BfIRCodeGen::BfIRCodeGen()
|
||||
{
|
||||
mStream = NULL;
|
||||
mBfIRBuilder = NULL;
|
||||
|
||||
mNopInlineAsm = NULL;
|
||||
mAsmObjectCheckAsm = NULL;
|
||||
mHasDebugLoc = false;
|
||||
mAttrSet = NULL;
|
||||
mIRBuilder = NULL;
|
||||
mDIBuilder = NULL;
|
||||
mDICompileUnit = NULL;
|
||||
mActiveFunction = NULL;
|
||||
|
||||
mLLVMContext = new llvm::LLVMContext();
|
||||
mLLVMModule = NULL;
|
||||
mIsCodeView = false;
|
||||
mCmdCount = 0;
|
||||
|
||||
#ifdef BF_PLATFORM_WINDOWS
|
||||
if (::GetStdHandle(STD_ERROR_HANDLE) == 0)
|
||||
{
|
||||
if (gTempFile.Create())
|
||||
{
|
||||
_dup2(fileno(gTempFile.mFP), 2);
|
||||
BfpSystem_AddCrashInfoFunc(AddStdErrCrashInfo);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
BfIRCodeGen::~BfIRCodeGen()
|
||||
{
|
||||
mDebugLoc = llvm::DebugLoc();
|
||||
mSavedDebugLocs.Clear();
|
||||
|
||||
delete mStream;
|
||||
delete mIRBuilder;
|
||||
delete mDIBuilder;
|
||||
delete mLLVMModule;
|
||||
delete mLLVMContext;
|
||||
}
|
||||
|
||||
void BfIRCodeGen::Fail(const StringImpl& error)
|
||||
{
|
||||
if (mFailed)
|
||||
return;
|
||||
|
||||
if (mHasDebugLoc)
|
||||
{
|
||||
auto dbgLoc = mIRBuilder->getCurrentDebugLocation();
|
||||
if (dbgLoc)
|
||||
{
|
||||
llvm::DIFile* file = NULL;
|
||||
if (llvm::DIScope* scope = llvm::dyn_cast<llvm::DIScope>(dbgLoc.getScope()))
|
||||
{
|
||||
BfIRCodeGenBase::Fail(StrFormat("%s at line %d:%d in %s/%s", error.c_str(), dbgLoc.getLine(), dbgLoc.getCol(), scope->getDirectory().data(), scope->getFilename().data()));
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
BfIRCodeGenBase::Fail(error);
|
||||
}
|
||||
|
||||
void BfIRCodeGen::PrintModule()
|
||||
{
|
||||
Beefy::debug_ostream os;
|
||||
|
@ -362,60 +505,6 @@ void BfIRCodeGen::SetResult(int id, llvm::MDNode* md)
|
|||
mResults.TryAdd(id, entry);
|
||||
}
|
||||
|
||||
BfIRCodeGen::BfIRCodeGen()
|
||||
{
|
||||
mStream = NULL;
|
||||
mBfIRBuilder = NULL;
|
||||
|
||||
mNopInlineAsm = NULL;
|
||||
mAsmObjectCheckAsm = NULL;
|
||||
mHasDebugLoc = false;
|
||||
mAttrSet = NULL;
|
||||
mIRBuilder = NULL;
|
||||
mDIBuilder = NULL;
|
||||
mDICompileUnit = NULL;
|
||||
mActiveFunction = NULL;
|
||||
|
||||
mLLVMContext = new llvm::LLVMContext();
|
||||
mLLVMModule = NULL;
|
||||
mIsCodeView = false;
|
||||
mCmdCount = 0;
|
||||
}
|
||||
|
||||
BfIRCodeGen::~BfIRCodeGen()
|
||||
{
|
||||
mDebugLoc = llvm::DebugLoc();
|
||||
mSavedDebugLocs.Clear();
|
||||
|
||||
delete mStream;
|
||||
delete mIRBuilder;
|
||||
delete mDIBuilder;
|
||||
delete mLLVMModule;
|
||||
delete mLLVMContext;
|
||||
}
|
||||
|
||||
void BfIRCodeGen::Fail(const StringImpl& error)
|
||||
{
|
||||
if (mFailed)
|
||||
return;
|
||||
|
||||
if (mHasDebugLoc)
|
||||
{
|
||||
auto dbgLoc = mIRBuilder->getCurrentDebugLocation();
|
||||
if (dbgLoc)
|
||||
{
|
||||
llvm::DIFile* file = NULL;
|
||||
if (llvm::DIScope* scope = llvm::dyn_cast<llvm::DIScope>(dbgLoc.getScope()))
|
||||
{
|
||||
BfIRCodeGenBase::Fail(StrFormat("%s at line %d:%d in %s/%s", error.c_str(), dbgLoc.getLine(), dbgLoc.getCol(), scope->getDirectory().data(), scope->getFilename().data()));
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
BfIRCodeGenBase::Fail(error);
|
||||
}
|
||||
|
||||
void BfIRCodeGen::ProcessBfIRData(const BfSizedArray<uint8>& buffer)
|
||||
{
|
||||
struct InlineAsmErrorHook
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue