Show error message popup on assertion error in client

Add assertion handler function to base system. Set handler in client to show a message box on assertion errors.
This commit is contained in:
Robert Müller 2023-05-03 20:28:37 +02:00
parent 00b7bc5bfd
commit ccfca141d4
3 changed files with 26 additions and 1 deletions

View file

@ -169,6 +169,7 @@ static NETSOCKET_INTERNAL invalid_socket = {NETTYPE_INVALID, -1, -1, -1};
#define AF_WEBSOCKET_INET (0xee) #define AF_WEBSOCKET_INET (0xee)
std::atomic_bool dbg_assert_failing = false; std::atomic_bool dbg_assert_failing = false;
DBG_ASSERT_HANDLER dbg_assert_handler;
bool dbg_assert_has_failed() bool dbg_assert_has_failed()
{ {
@ -179,8 +180,17 @@ void dbg_assert_imp(const char *filename, int line, int test, const char *msg)
{ {
if(!test) if(!test)
{ {
const bool already_failing = dbg_assert_has_failed();
dbg_assert_failing.store(true, std::memory_order_release); dbg_assert_failing.store(true, std::memory_order_release);
dbg_msg("assert", "%s(%d): %s", filename, line, msg); char error[256];
str_format(error, sizeof(error), "%s(%d): %s", filename, line, msg);
dbg_msg("assert", "%s", error);
if(!already_failing)
{
DBG_ASSERT_HANDLER handler = dbg_assert_handler;
if(handler)
handler(error);
}
log_global_logger_finish(); log_global_logger_finish();
dbg_break(); dbg_break();
} }
@ -195,6 +205,11 @@ void dbg_break()
#endif #endif
} }
void dbg_assert_set_handler(DBG_ASSERT_HANDLER handler)
{
dbg_assert_handler = std::move(handler);
}
void dbg_msg(const char *sys, const char *fmt, ...) void dbg_msg(const char *sys, const char *fmt, ...)
{ {
va_list args; va_list args;

View file

@ -108,6 +108,9 @@ bool dbg_assert_has_failed();
void void
dbg_break(); dbg_break();
typedef std::function<void(const char *message)> DBG_ASSERT_HANDLER;
void dbg_assert_set_handler(DBG_ASSERT_HANDLER handler);
/** /**
* Prints a debug message. * Prints a debug message.
* *

View file

@ -4534,6 +4534,7 @@ int main(int argc, const char **argv)
CWindowsComLifecycle WindowsComLifecycle(true); CWindowsComLifecycle WindowsComLifecycle(true);
#endif #endif
CCmdlineFix CmdlineFix(&argc, &argv); CCmdlineFix CmdlineFix(&argc, &argv);
bool Silent = false; bool Silent = false;
bool RandInitFailed = false; bool RandInitFailed = false;
@ -4582,6 +4583,12 @@ int main(int argc, const char **argv)
pKernel->RegisterInterface(pClient, false); pKernel->RegisterInterface(pClient, false);
pClient->RegisterInterfaces(); pClient->RegisterInterfaces();
dbg_assert_set_handler([pClient](const char *pMsg) {
char aMessage[256];
str_format(aMessage, sizeof(aMessage), "An assertion error occured. Please write down or take a screenshot of the following information and report this error.\n\n%s", pMsg);
pClient->ShowMessageBox("Assertion Error", aMessage);
});
// create the components // create the components
IEngine *pEngine = CreateEngine(GAME_NAME, pFutureConsoleLogger, 2); IEngine *pEngine = CreateEngine(GAME_NAME, pFutureConsoleLogger, 2);
IConsole *pConsole = CreateConsole(CFGFLAG_CLIENT).release(); IConsole *pConsole = CreateConsole(CFGFLAG_CLIENT).release();