blob: 3996c26d78c75c1df007b9d8b638288ba03afd09 [file]
/*
* Copyright 2010-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license
* that can be found in the LICENSE file.
*/
#include "KAssert.h"
#include <array>
#include <cinttypes>
#include <cstdarg>
#include <cstdlib>
#include "std_support/Span.hpp"
#include "CallsChecker.hpp"
#include "Format.h"
#include "Porting.h"
#include "StackTrace.hpp"
#include "CrashHandler.hpp"
using namespace kotlin;
namespace {
THREAD_LOCAL_VARIABLE bool assertionReportInProgress = false;
void PrintAssert(bool allowStacktrace, const char* location, const char* format, std::va_list args) noexcept {
CallsCheckerIgnoreGuard ignoreCallsChecker;
if (assertionReportInProgress) {
// WARNING: avoid anything that can assert ar panic here
konan::consoleErrorf("An attempt to report an assertion lead to another failure:\n");
// now try to print the information we have in the simplest way possible
if (location != nullptr) {
konan::consoleErrorf("%s: ", location);
}
// do not bother with format string expansion
konan::consoleErrorf("%s\n", format);
return;
}
AutoReset recursionGuard(&assertionReportInProgress, true);
std::array<char, 1024> bufferStorage;
std_support::span<char> buffer(bufferStorage);
buffer = FormatToSpan(buffer, "[tid#%" PRIuPTR "] ", konan::currentThreadId());
// Write the title with a source location.
if (location != nullptr) {
buffer = FormatToSpan(buffer, "%s: runtime assert: ", location);
} else {
buffer = FormatToSpan(buffer, "runtime assert: ");
}
// Write the message.
buffer = VFormatToSpan(buffer, format, args);
konan::consoleErrorUtf8(bufferStorage.data(), bufferStorage.size() - buffer.size());
konan::consoleErrorf("\n");
if (allowStacktrace) {
kotlin::PrintStackTraceStderr();
}
}
} // namespace
void internal::RuntimeAssertFailedLog(bool allowStacktrace, const char* location, const char* format, ...) {
std::va_list args;
va_start(args, format);
PrintAssert(allowStacktrace, location, format, args);
va_end(args);
}
RUNTIME_NORETURN void internal::RuntimeAssertFailedPanic(bool allowStacktrace, const char* location, const char* format, ...) {
std::va_list args;
va_start(args, format);
PrintAssert(allowStacktrace, location, format, args);
va_end(args);
kotlin::writeMinidump();
std::abort();
}