Flush emulation logs after exceptions

A lot of logs are incomplete due to being unable to flush inside the signal handler, now we flush after any exceptions so that there is a guarantee of any exceptions being logged as this is crucial for proper debugging.
This commit is contained in:
PixelyIon 2022-04-10 13:19:50 +05:30
parent 62ba180550
commit ea00f1bb82
4 changed files with 13 additions and 0 deletions

View File

@ -177,6 +177,7 @@ namespace skyline::kernel::type {
__builtin_unreachable(); __builtin_unreachable();
} catch (const std::exception &e) { } catch (const std::exception &e) {
Logger::Error(e.what()); Logger::Error(e.what());
Logger::EmulationContext.Flush();
if (id) { if (id) {
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);
@ -186,6 +187,7 @@ namespace skyline::kernel::type {
} catch (const signal::SignalException &e) { } catch (const signal::SignalException &e) {
if (e.signal != SIGINT) { if (e.signal != SIGINT) {
Logger::Error(e.what()); Logger::Error(e.what());
Logger::EmulationContext.Flush();
if (id) { if (id) {
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);

View File

@ -41,10 +41,14 @@ namespace skyline::nce {
} catch (const signal::SignalException &e) { } catch (const signal::SignalException &e) {
if (e.signal != SIGINT) { if (e.signal != SIGINT) {
Logger::ErrorNoPrefix("{} (SVC: {})\nStack Trace:{}", e.what(), svc.name, state.loader->GetStackTrace(e.frames)); Logger::ErrorNoPrefix("{} (SVC: {})\nStack Trace:{}", e.what(), svc.name, state.loader->GetStackTrace(e.frames));
Logger::EmulationContext.Flush();
if (state.thread->id) { if (state.thread->id) {
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);
} }
} else {
Logger::EmulationContext.Flush();
} }
abi::__cxa_end_catch(); // We call this prior to the longjmp to cause the exception object to be destroyed abi::__cxa_end_catch(); // We call this prior to the longjmp to cause the exception object to be destroyed
std::longjmp(state.thread->originalCtx, true); std::longjmp(state.thread->originalCtx, true);
@ -60,6 +64,8 @@ namespace skyline::nce {
else else
Logger::ErrorNoPrefix("{} (SVC: 0x{:X})\nStack Trace:{}", e.what(), svcId, state.loader->GetStackTrace()); Logger::ErrorNoPrefix("{} (SVC: 0x{:X})\nStack Trace:{}", e.what(), svcId, state.loader->GetStackTrace());
Logger::EmulationContext.Flush();
if (state.thread->id) { if (state.thread->id) {
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);
@ -94,6 +100,7 @@ namespace skyline::nce {
cpuContext += fmt::format("\n X{:<2}: 0x{:<16X} X{:<2}: 0x{:X}", index, mctx.regs[index], index + 1, mctx.regs[index + 1]); cpuContext += fmt::format("\n X{:<2}: 0x{:<16X} X{:<2}: 0x{:X}", index, mctx.regs[index], index + 1, mctx.regs[index + 1]);
Logger::Error("Thread #{} has crashed due to signal: {}\nStack Trace:{}\nCPU Context:{}", state.thread->id, strsignal(signal), trace, cpuContext); Logger::Error("Thread #{} has crashed due to signal: {}\nStack Trace:{}\nCPU Context:{}", state.thread->id, strsignal(signal), trace, cpuContext);
Logger::EmulationContext.Flush();
if (state.thread->id) { if (state.thread->id) {
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});

View File

@ -346,11 +346,13 @@ namespace skyline::soc::gm20b {
} catch (const signal::SignalException &e) { } catch (const signal::SignalException &e) {
if (e.signal != SIGINT) { if (e.signal != SIGINT) {
Logger::Error("{}\nStack Trace:{}", e.what(), state.loader->GetStackTrace(e.frames)); Logger::Error("{}\nStack Trace:{}", e.what(), state.loader->GetStackTrace(e.frames));
Logger::EmulationContext.Flush();
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);
} }
} catch (const std::exception &e) { } catch (const std::exception &e) {
Logger::Error(e.what()); Logger::Error(e.what());
Logger::EmulationContext.Flush();
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);
} }

View File

@ -126,11 +126,13 @@ namespace skyline::soc::host1x {
} catch (const signal::SignalException &e) { } catch (const signal::SignalException &e) {
if (e.signal != SIGINT) { if (e.signal != SIGINT) {
Logger::Error("{}\nStack Trace:{}", e.what(), state.loader->GetStackTrace(e.frames)); Logger::Error("{}\nStack Trace:{}", e.what(), state.loader->GetStackTrace(e.frames));
Logger::EmulationContext.Flush();
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);
} }
} catch (const std::exception &e) { } catch (const std::exception &e) {
Logger::Error(e.what()); Logger::Error(e.what());
Logger::EmulationContext.Flush();
signal::BlockSignal({SIGINT}); signal::BlockSignal({SIGINT});
state.process->Kill(false); state.process->Kill(false);
} }