From 5fe0a9c77c1f32e90f7d80c4faf24659725ca569 Mon Sep 17 00:00:00 2001 From: Sergey Bogolepov <1580082+sbogolepov@users.noreply.github.com> Date: Mon, 27 Aug 2018 19:03:08 +0300 Subject: [PATCH] Handle init-time exceptions on all targets. (#1931) --- runtime/src/main/cpp/Exceptions.cpp | 6 +- runtime/src/main/cpp/Exceptions.h | 2 +- .../kotlin/konan/target/ClangArgs.kt | 70 ++++++++++++++----- 3 files changed, 59 insertions(+), 19 deletions(-) diff --git a/runtime/src/main/cpp/Exceptions.cpp b/runtime/src/main/cpp/Exceptions.cpp index d4b83aaaf1f..8677335f42d 100644 --- a/runtime/src/main/cpp/Exceptions.cpp +++ b/runtime/src/main/cpp/Exceptions.cpp @@ -172,7 +172,9 @@ void ThrowException(KRef exception) { #endif } -#if KONAN_OBJC_INTEROP +// Some libstdc++-based targets has limited support for std::current_exception and other C++11 functions. +// This restriction can be lifted later when toolchains will be updated. +#if KONAN_HAS_CXX11_EXCEPTION_FUNCTIONS void ReportUnhandledException(KRef e); @@ -180,6 +182,7 @@ static void (*oldTerminateHandler)() = nullptr; static void KonanTerminateHandler() { auto currentException = std::current_exception(); + RuntimeCheck(oldTerminateHandler != nullptr, "Underlying exception handler is not set."); if (!currentException) { // No current exception. oldTerminateHandler(); @@ -205,7 +208,6 @@ void SetKonanTerminateHandler() { if (oldTerminateHandler != nullptr) return; // Already initialized. - oldTerminateHandler = std::get_terminate(); // If termination happens between `set_terminate` and assignment. oldTerminateHandler = std::set_terminate(&KonanTerminateHandler); } diff --git a/runtime/src/main/cpp/Exceptions.h b/runtime/src/main/cpp/Exceptions.h index 7546da6efea..b0472311ea1 100644 --- a/runtime/src/main/cpp/Exceptions.h +++ b/runtime/src/main/cpp/Exceptions.h @@ -31,7 +31,7 @@ void ThrowException(KRef exception); void SetKonanTerminateHandler(); -// The functions below are implemented in Kotlin (at package konan.internal). +// The functions below are implemented in Kotlin (at package kotlin.native.internal). // Throws null pointer exception. Context is evaluated from caller's address. void RUNTIME_NORETURN ThrowNullPointerException(); diff --git a/shared/src/main/kotlin/org/jetbrains/kotlin/konan/target/ClangArgs.kt b/shared/src/main/kotlin/org/jetbrains/kotlin/konan/target/ClangArgs.kt index c88bfd068d2..a75eb2a3a55 100644 --- a/shared/src/main/kotlin/org/jetbrains/kotlin/konan/target/ClangArgs.kt +++ b/shared/src/main/kotlin/org/jetbrains/kotlin/konan/target/ClangArgs.kt @@ -120,44 +120,82 @@ class ClangArgs(private val configurables: Configurables) : Configurables by con val clangArgsSpecificForKonanSources get() = when (target) { KonanTarget.LINUX_X64 -> - listOf("-DUSE_GCC_UNWIND=1", "-DUSE_ELF_SYMBOLS=1", "-DELFSIZE=64") + listOf("-DUSE_GCC_UNWIND=1", + "-DUSE_ELF_SYMBOLS=1", + "-DELFSIZE=64", + "-DKONAN_HAS_CXX11_EXCEPTION_FUNCTIONS=1") KonanTarget.LINUX_ARM32_HFP -> - listOf("-DUSE_GCC_UNWIND=1", "-DUSE_ELF_SYMBOLS=1", "-DELFSIZE=32") + listOf("-DUSE_GCC_UNWIND=1", + "-DUSE_ELF_SYMBOLS=1", + "-DELFSIZE=32") KonanTarget.LINUX_MIPS32 -> - listOf("-DUSE_GCC_UNWIND=1", "-DUSE_ELF_SYMBOLS=1", "-DELFSIZE=32") + listOf("-DUSE_GCC_UNWIND=1", + "-DUSE_ELF_SYMBOLS=1", + "-DELFSIZE=32") KonanTarget.LINUX_MIPSEL32 -> - listOf("-DUSE_GCC_UNWIND=1", "-DUSE_ELF_SYMBOLS=1", "-DELFSIZE=32") + listOf("-DUSE_GCC_UNWIND=1", + "-DUSE_ELF_SYMBOLS=1", + "-DELFSIZE=32") KonanTarget.MINGW_X64 -> - listOf("-DUSE_GCC_UNWIND=1", "-DUSE_PE_COFF_SYMBOLS=1", "-DKONAN_WINDOWS=1", "-DKONAN_NO_MEMMEM=1") + listOf("-DUSE_GCC_UNWIND=1", + "-DUSE_PE_COFF_SYMBOLS=1", + "-DKONAN_WINDOWS=1", + "-DKONAN_NO_MEMMEM=1", + "-DKONAN_HAS_CXX11_EXCEPTION_FUNCTIONS=1") KonanTarget.MACOS_X64 -> - listOf("-DKONAN_OSX=1", "-DKONAN_OBJC_INTEROP=1") + listOf("-DKONAN_OSX=1", + "-DKONAN_OBJC_INTEROP=1", + "-DKONAN_HAS_CXX11_EXCEPTION_FUNCTIONS=1") KonanTarget.IOS_ARM32, KonanTarget.IOS_ARM64 -> - listOf("-DKONAN_OBJC_INTEROP=1") + listOf("-DKONAN_OBJC_INTEROP=1", + "-DKONAN_HAS_CXX11_EXCEPTION_FUNCTIONS=1") KonanTarget.IOS_X64 -> - listOf("-DKONAN_OBJC_INTEROP=1") + listOf("-DKONAN_OBJC_INTEROP=1", + "-DKONAN_HAS_CXX11_EXCEPTION_FUNCTIONS=1") KonanTarget.ANDROID_ARM32 -> - listOf("-D__ANDROID__", "-DUSE_GCC_UNWIND=1", "-DUSE_ELF_SYMBOLS=1", "-DELFSIZE=32", "-DKONAN_ANDROID") + listOf("-D__ANDROID__", + "-DUSE_GCC_UNWIND=1", + "-DUSE_ELF_SYMBOLS=1", + "-DELFSIZE=32", + "-DKONAN_ANDROID") KonanTarget.ANDROID_ARM64 -> - listOf("-D__ANDROID__", "-DUSE_GCC_UNWIND=1", "-DUSE_ELF_SYMBOLS=1", "-DELFSIZE=64", "-DKONAN_ANDROID") + listOf("-D__ANDROID__", + "-DUSE_GCC_UNWIND=1", + "-DUSE_ELF_SYMBOLS=1", + "-DELFSIZE=64", + "-DKONAN_ANDROID", + "-DKONAN_HAS_CXX11_EXCEPTION_FUNCTIONS=1") KonanTarget.WASM32 -> - listOf("-DKONAN_WASM=1", "-DKONAN_NO_FFI=1", "-DKONAN_NO_THREADS=1", "-DKONAN_NO_EXCEPTIONS=1", - "-DKONAN_INTERNAL_DLMALLOC=1", "-DKONAN_INTERNAL_SNPRINTF=1", - "-DKONAN_INTERNAL_NOW=1", "-DKONAN_NO_MEMMEM", "-DKONAN_NO_CTORS_SECTION=1") + listOf("-DKONAN_WASM=1", + "-DKONAN_NO_FFI=1", + "-DKONAN_NO_THREADS=1", + "-DKONAN_NO_EXCEPTIONS=1", + "-DKONAN_INTERNAL_DLMALLOC=1", + "-DKONAN_INTERNAL_SNPRINTF=1", + "-DKONAN_INTERNAL_NOW=1", + "-DKONAN_NO_MEMMEM", + "-DKONAN_NO_CTORS_SECTION=1") is KonanTarget.ZEPHYR -> - listOf( "-DKONAN_ZEPHYR=1", "-DKONAN_NO_FFI=1", "-DKONAN_NO_THREADS=1", "-DKONAN_NO_EXCEPTIONS=1", - "-DKONAN_NO_MATH=1", "-DKONAN_INTERNAL_SNPRINTF=1", "-DKONAN_INTERNAL_NOW=1", - "-DKONAN_NO_MEMMEM=1", "-DKONAN_NO_CTORS_SECTION=1") + listOf( "-DKONAN_ZEPHYR=1", + "-DKONAN_NO_FFI=1", + "-DKONAN_NO_THREADS=1", + "-DKONAN_NO_EXCEPTIONS=1", + "-DKONAN_NO_MATH=1", + "-DKONAN_INTERNAL_SNPRINTF=1", + "-DKONAN_INTERNAL_NOW=1", + "-DKONAN_NO_MEMMEM=1", + "-DKONAN_NO_CTORS_SECTION=1") } private val host = HostManager.host